diff options
-rw-r--r-- | ChangeLog | 26 | ||||
-rw-r--r-- | java/awt/Component.java | 4 | ||||
-rw-r--r-- | java/awt/Container.java | 19 | ||||
-rw-r--r-- | java/awt/EventQueue.java | 22 | ||||
-rw-r--r-- | java/awt/LightweightDispatcher.java | 56 | ||||
-rw-r--r-- | java/awt/Toolkit.java | 26 |
6 files changed, 114 insertions, 39 deletions
@@ -1,3 +1,29 @@ +2006-02-28 Roman Kennke <kennke@aicas.com> + + * java/awt/Component.java + (dispatchEventImpl): Let the Toolkit dispatch global events. + * java/awt/Container.java + (dispatchEventImpl): Let the LightweightDispatcher handle events + first. + * java/awt/EventQueue.java + (dispatchEvent): Don't do the global event dispatching here. This + is moved to the Component. + (globalDispatchEvent): Moved this method to Toolkit. + * java/awt/LightweightDispatcher.java + (instances): New field. + (getInstance): New method. Delivers an instance of + LightweightDispatcher. + (LightweightDispatcher): Made default constructor private. + (dispatchEvent): New method. Replaces the eventDispatched method. + This now returns true when the event was actually dispatched. + (eventDispatched): Replaced by dispatchEvent. + (handleMouseEvent): Send MOUSE_CLICKED to the same component that + received the last MOUSE_RELEASED. + * java/awt/Toolkit.java + (Toolkit): Don't register LightweightDispatcher as global event + handler. + (globalDispatchEvent): Moved here from EventQueue. + 2006-02-27 David Daney <ddaney@avtrex.com> PR classpath/25851 diff --git a/java/awt/Component.java b/java/awt/Component.java index e824c4dd6..667cf430e 100644 --- a/java/awt/Component.java +++ b/java/awt/Component.java @@ -4921,6 +4921,10 @@ p * <li>the set of backward traversal keys void dispatchEventImpl(AWTEvent e) { + // Give toolkit a chance to dispatch the event + // to globally registered listeners. + Toolkit.getDefaultToolkit().globalDispatchEvent(e); + // This boolean tells us not to process focus events when the focus // opposite component is the same as the focus component. boolean ignoreFocus = diff --git a/java/awt/Container.java b/java/awt/Container.java index 004698847..3cb245043 100644 --- a/java/awt/Container.java +++ b/java/awt/Container.java @@ -1711,13 +1711,18 @@ public class Container extends Component void dispatchEventImpl(AWTEvent e) { - if ((e.id <= ContainerEvent.CONTAINER_LAST - && e.id >= ContainerEvent.CONTAINER_FIRST) - && (containerListener != null - || (eventMask & AWTEvent.CONTAINER_EVENT_MASK) != 0)) - processEvent(e); - else - super.dispatchEventImpl(e); + boolean dispatched = + LightweightDispatcher.getInstance().dispatchEvent(e); + if (! dispatched) + { + if ((e.id <= ContainerEvent.CONTAINER_LAST + && e.id >= ContainerEvent.CONTAINER_FIRST) + && (containerListener != null + || (eventMask & AWTEvent.CONTAINER_EVENT_MASK) != 0)) + processEvent(e); + else + super.dispatchEventImpl(e); + } } /** diff --git a/java/awt/EventQueue.java b/java/awt/EventQueue.java index 72dcf7046..235ad2ac1 100644 --- a/java/awt/EventQueue.java +++ b/java/awt/EventQueue.java @@ -38,7 +38,6 @@ exception statement from your version. */ package java.awt; -import java.awt.event.AWTEventListenerProxy; import java.awt.event.ActionEvent; import java.awt.event.InputEvent; import java.awt.event.InputMethodEvent; @@ -460,8 +459,6 @@ public class EventQueue else if (evt instanceof InvocationEvent) lastWhen = ((InvocationEvent) evt).getWhen(); - globalDispatchEvent(evt); - if (evt instanceof ActiveEvent) { ActiveEvent active_evt = (ActiveEvent) evt; @@ -485,25 +482,6 @@ public class EventQueue } /** - * Dispatches events to listeners registered to the current Toolkit. - * - * @param ev the event to dispatch - */ - private void globalDispatchEvent(AWTEvent ev) - { - Toolkit toolkit = Toolkit.getDefaultToolkit(); - // We do not use the accessor methods here because they create new - // arrays each time. We must be very efficient, so we access this directly. - AWTEventListenerProxy[] l = toolkit.awtEventListeners; - for (int i = 0; i < l.length; ++i) - { - AWTEventListenerProxy proxy = l[i]; - if ((proxy.getEventMask() & AWTEvent.eventIdToMask(ev.getID())) != 0) - proxy.eventDispatched(ev); - } - } - - /** * Returns the timestamp of the most recent event that had a timestamp, or * the initialization time of the event queue if no events have been fired. * At present, only <code>InputEvent</code>s, <code>ActionEvent</code>s, diff --git a/java/awt/LightweightDispatcher.java b/java/awt/LightweightDispatcher.java index 1eccb5d5d..6573b128e 100644 --- a/java/awt/LightweightDispatcher.java +++ b/java/awt/LightweightDispatcher.java @@ -40,8 +40,8 @@ package java.awt; import gnu.java.awt.AWTUtilities; -import java.awt.event.AWTEventListener; import java.awt.event.MouseEvent; +import java.util.WeakHashMap; /** * Redispatches mouse events to lightweight components. The native peers know @@ -52,10 +52,16 @@ import java.awt.event.MouseEvent; * @author Roman Kennke (kennke@aicas.com) */ class LightweightDispatcher - implements AWTEventListener { /** + * Maps thread groups to lightweight dispatcher instances. We need to + * have one instance per thread group so that 2 or more applets or otherwise + * separated applications (like in OSGI) do not interfer with each other. + */ + private static WeakHashMap instances = new WeakHashMap(); + + /** * The component that is the start of a mouse dragging. All MOUSE_DRAGGED * events that follow the initial press must have the source set to this, * as well as the MOUSE_RELEASED event following the dragging. @@ -69,17 +75,49 @@ class LightweightDispatcher private Component lastTarget; /** + * Returns an instance of LightweightDispatcher for the current thread's + * thread group. + * + * @return an instance of LightweightDispatcher for the current thread's + * thread group + */ + static LightweightDispatcher getInstance() + { + Thread t = Thread.currentThread(); + ThreadGroup tg = t.getThreadGroup(); + LightweightDispatcher instance = (LightweightDispatcher) instances.get(tg); + if (instance == null) + { + instance = new LightweightDispatcher(); + instances.put(tg, instance); + } + return instance; + } + + /** + * Creates a new LightweightDispatcher. This is private to prevent access + * from outside. Use {@link #getInstance()} instead. + */ + private LightweightDispatcher() + { + // Nothing to do here. + } + + /** * Receives notification if a mouse event passes along the eventqueue. * * @param event the event */ - public void eventDispatched(AWTEvent event) + public boolean dispatchEvent(AWTEvent event) { + boolean dispatched = false; if (event instanceof MouseEvent && event.getSource() instanceof Window) { MouseEvent mouseEvent = (MouseEvent) event; handleMouseEvent(mouseEvent); + dispatched = true; } + return dispatched; } /** @@ -116,8 +154,6 @@ class LightweightDispatcher ev.isPopupTrigger()); target.dispatchEvent(mouseEntered); } - lastTarget = target; - switch (ev.getID()) { @@ -129,6 +165,14 @@ class LightweightDispatcher target = dragTarget; dragTarget = null; break; + case MouseEvent.MOUSE_CLICKED: + // When we receive a MOUSE_CLICKED, we set the target to the + // previous target, which must have been a MOUSE_RELEASED event. + // This is necessary for the case when the MOUSE_RELEASED has + // caused the original target (like an internal component) go + // away. + target = lastTarget; + break; case MouseEvent.MOUSE_DRAGGED: target = dragTarget; break; @@ -137,6 +181,8 @@ class LightweightDispatcher break; } + lastTarget = target; + Point targetCoordinates = AWTUtilities.convertPoint(window, ev.getX(), ev.getY(), target); int dx = targetCoordinates.x - ev.getX(); diff --git a/java/awt/Toolkit.java b/java/awt/Toolkit.java index debc8e340..b60715527 100644 --- a/java/awt/Toolkit.java +++ b/java/awt/Toolkit.java @@ -128,11 +128,7 @@ public abstract class Toolkit */ public Toolkit() { - awtEventListeners = new AWTEventListenerProxy[1]; - awtEventListeners[0] = - new AWTEventListenerProxy(AWTEvent.MOUSE_EVENT_MASK - | AWTEvent.MOUSE_MOTION_EVENT_MASK, - new LightweightDispatcher()); + awtEventListeners = new AWTEventListenerProxy[0]; } /** @@ -1186,6 +1182,26 @@ public abstract class Toolkit return (AWTEventListener[] ) l.toArray(new AWTEventListener[l.size()]); } + + /** + * Dispatches events to listeners registered to this Toolkit. This is called + * by {@link Component#dispatchEventImpl(AWTEvent)} in order to dispatch + * events globally. + * + * @param ev the event to dispatch + */ + void globalDispatchEvent(AWTEvent ev) + { + // We do not use the accessor methods here because they create new + // arrays each time. We must be very efficient, so we access this directly. + for (int i = 0; i < awtEventListeners.length; ++i) + { + AWTEventListenerProxy proxy = awtEventListeners[i]; + if ((proxy.getEventMask() & AWTEvent.eventIdToMask(ev.getID())) != 0) + proxy.eventDispatched(ev); + } + } + /** * @since 1.3 */ |