summaryrefslogtreecommitdiff
path: root/libjava/gnu/awt/LightweightRedirector.java
diff options
context:
space:
mode:
authorupstream source tree <ports@midipix.org>2015-03-15 20:14:05 -0400
committerupstream source tree <ports@midipix.org>2015-03-15 20:14:05 -0400
commit554fd8c5195424bdbcabf5de30fdc183aba391bd (patch)
tree976dc5ab7fddf506dadce60ae936f43f58787092 /libjava/gnu/awt/LightweightRedirector.java
downloadcbb-gcc-4.6.4-554fd8c5195424bdbcabf5de30fdc183aba391bd.tar.bz2
cbb-gcc-4.6.4-554fd8c5195424bdbcabf5de30fdc183aba391bd.tar.xz
obtained gcc-4.6.4.tar.bz2 from upstream website;upstream
verified gcc-4.6.4.tar.bz2.sig; imported gcc-4.6.4 source tree from verified upstream tarball. downloading a git-generated archive based on the 'upstream' tag should provide you with a source tree that is binary identical to the one extracted from the above tarball. if you have obtained the source via the command 'git clone', however, do note that line-endings of files in your working directory might differ from line-endings of the respective files in the upstream repository.
Diffstat (limited to 'libjava/gnu/awt/LightweightRedirector.java')
-rw-r--r--libjava/gnu/awt/LightweightRedirector.java183
1 files changed, 183 insertions, 0 deletions
diff --git a/libjava/gnu/awt/LightweightRedirector.java b/libjava/gnu/awt/LightweightRedirector.java
new file mode 100644
index 000000000..41dc12427
--- /dev/null
+++ b/libjava/gnu/awt/LightweightRedirector.java
@@ -0,0 +1,183 @@
+/* Copyright (C) 2000 Free Software Foundation
+
+ This file is part of libgcj.
+
+This software is copyrighted work licensed under the terms of the
+Libgcj License. Please consult the file "LIBGCJ_LICENSE" for
+details. */
+
+package gnu.awt;
+
+import java.awt.AWTEvent;
+import java.awt.AWTError;
+import java.awt.Component;
+import java.awt.Container;
+import java.awt.event.MouseEvent;
+import java.awt.event.InputEvent;
+
+/**
+ * Encapsulates the logic required to dispatch events to the correct
+ * component in a component tree that may contain lightweight
+ * components. Toolkits typically only identify heavyweight components
+ * as the source of events. This class redirects the events to the
+ * appropriate lightweight children of the heavyweight component.
+ */
+public class LightweightRedirector
+{
+ final static int LAST_BUTTON_NUMBER = 3;
+
+ /* We sacrifice one array element to allow the button number to
+ match the index of this array. */
+ Component[] releaseTargets = new Component[LAST_BUTTON_NUMBER+1];
+
+ /**
+ *
+ * Modifies or replaces the given event with an event that has been
+ * properly redirected. State of button presses are kept so that
+ * button releases can be redirected to the same component as the
+ * button press. It is required that all events are sent through
+ * this method in chronological order.
+ */
+ public AWTEvent redirect(AWTEvent event)
+ {
+ if (event instanceof MouseEvent)
+ return redirectMouse((MouseEvent) event);
+
+ /* In case we don't know how to redirect the event, simply return
+ the event unchanged. */
+ return event;
+ }
+
+ MouseEvent redirectMouse(MouseEvent event)
+ {
+ int button = getButtonNumber(event);
+ int id = event.getID();
+
+ Component heavySource = (Component) event.getSource();
+ Component source = heavySource;
+ int x = event.getX();
+ int y = event.getY();
+
+ if (id == MouseEvent.MOUSE_RELEASED)
+ {
+ Component target = releaseTargets[button];
+
+ if (target != null)
+ {
+ releaseTargets[button] = null;
+ source = target;
+
+ Component child = source;
+ while (child != heavySource)
+ {
+ x -= child.getX();
+ y -= child.getY();
+ child = child.getParent();
+ if (child == null)
+ System.err.println("warning, orphaned release target");
+ }
+ }
+ }
+ else
+ {
+ /* Find real component, and adjust source, x and y
+ accordingly. */
+
+ while (true)
+ {
+ Component parent = source;
+
+ Component child = parent.getComponentAt(x, y);
+
+ if (parent == child)
+ break;
+
+ // maybe ignoring would be better?
+ if (child == null)
+ {
+ String msg = "delivered event not within component. " +
+ "Heavyweight source was " + heavySource + ". " +
+ "Component was " + parent;
+ throw new AWTError(msg);
+ }
+ if (child.isLightweight())
+ {
+ // descend down to child
+ source = child;
+ x -= child.getX();
+ y -= child.getY();
+ }
+ else
+ {
+ System.err.println("warning: event delivered to wrong " +
+ "heavyweight component. Was " +
+ "delivered to " + source + ". " +
+ "Should have been delivered to " +
+ child + ". Maybe the native window " +
+ "system is bubbling events up the " +
+ "containment hierarchy.");
+ break;
+ }
+ }
+
+ /* ensure that the release event is delivered to the same
+ component as the press event. For most toolkits this is
+ only necessary for lightweight components, since the
+ underlying windowing system takes care of its heavyweight
+ components. */
+ if (id == MouseEvent.MOUSE_PRESSED)
+ releaseTargets[button] = source;
+ }
+
+
+ if (source == heavySource)
+ return event; // no change in event
+
+ // print warning for heavyweights
+ /* this warning can safely be removed if a toolkit that
+ needs heavyweight redirection support is ever created. */
+ if (!source.isLightweight())
+ System.err.println("warning: redirecting to heavyweight");
+
+ MouseEvent redirected = new MouseEvent(source, event.getID(),
+ event.getWhen(),
+ event.getModifiersEx(),
+ x, y,
+ event.getClickCount(),
+ event.isPopupTrigger());
+
+ return redirected;
+ }
+
+ /**
+ * Identifies the button number for an input event.
+ *
+ * @returns the button number, or 0 if no button modifier was set
+ * for the event.
+ */
+ int getButtonNumber(InputEvent event)
+ {
+ int modifiers = event.getModifiersEx();
+
+ modifiers &=
+ InputEvent.BUTTON1_DOWN_MASK |
+ InputEvent.BUTTON2_DOWN_MASK |
+ InputEvent.BUTTON3_DOWN_MASK;
+
+ switch (modifiers)
+ {
+ case InputEvent.BUTTON1_DOWN_MASK:
+ return 1;
+ case InputEvent.BUTTON2_DOWN_MASK:
+ return 2;
+ case InputEvent.BUTTON3_DOWN_MASK:
+ return 3;
+ case 0:
+ return 0;
+
+ default:
+ System.err.println("FIXME: multibutton event");
+ return 0;
+ }
+ }
+}