3289 }
3290 }
3291 }
3292 }
3293
3294 if (reset) {
3295 KeyboardFocusManager.setMostRecentFocusOwner(window, null);
3296 }
3297 }
3298
3299 void clearCurrentFocusCycleRootOnHide() {
3300 KeyboardFocusManager kfm =
3301 KeyboardFocusManager.getCurrentKeyboardFocusManager();
3302 Container cont = kfm.getCurrentFocusCycleRoot();
3303
3304 if (cont == this || isParentOf(cont)) {
3305 kfm.setGlobalCurrentFocusCycleRootPriv(null);
3306 }
3307 }
3308
3309 final Container getTraversalRoot() {
3310 if (isFocusCycleRoot()) {
3311 return findTraversalRoot();
3312 }
3313
3314 return super.getTraversalRoot();
3315 }
3316
3317 /**
3318 * Sets the focus traversal policy that will manage keyboard traversal of
3319 * this Container's children, if this Container is a focus cycle root. If
3320 * the argument is null, this Container inherits its policy from its focus-
3321 * cycle-root ancestor. If the argument is non-null, this policy will be
3322 * inherited by all focus-cycle-root children that have no keyboard-
3323 * traversal policy of their own (as will, recursively, their focus-cycle-
3324 * root children).
3325 * <p>
3326 * If this Container is not a focus cycle root, the policy will be
3327 * remembered, but will not be used or inherited by this or any other
3328 * Containers until this Container is made a focus cycle root.
4394 * container
4395 */
4396 private static final int LWD_MOUSE_DRAGGED_OVER = 1500;
4397
4398 private static final PlatformLogger eventLog = PlatformLogger.getLogger("java.awt.event.LightweightDispatcher");
4399
4400 LightweightDispatcher(Container nativeContainer) {
4401 this.nativeContainer = nativeContainer;
4402 mouseEventTarget = null;
4403 eventMask = 0;
4404 }
4405
4406 /*
4407 * Clean up any resources allocated when dispatcher was created;
4408 * should be called from Container.removeNotify
4409 */
4410 void dispose() {
4411 //System.out.println("Disposing lw dispatcher");
4412 stopListeningForOtherDrags();
4413 mouseEventTarget = null;
4414 }
4415
4416 /**
4417 * Enables events to subcomponents.
4418 */
4419 void enableEvents(long events) {
4420 eventMask |= events;
4421 }
4422
4423 /**
4424 * Dispatches an event to a sub-component if necessary, and
4425 * returns whether or not the event was forwarded to a
4426 * sub-component.
4427 *
4428 * @param e the event
4429 */
4430 boolean dispatchEvent(AWTEvent e) {
4431 boolean ret = false;
4432
4433 /*
4485 /**
4486 * This method attempts to distribute a mouse event to a lightweight
4487 * component. It tries to avoid doing any unnecessary probes down
4488 * into the component tree to minimize the overhead of determining
4489 * where to route the event, since mouse movement events tend to
4490 * come in large and frequent amounts.
4491 */
4492 private boolean processMouseEvent(MouseEvent e) {
4493 int id = e.getID();
4494 Component mouseOver = // sensitive to mouse events
4495 nativeContainer.getMouseEventTarget(e.getX(), e.getY(),
4496 Container.INCLUDE_SELF);
4497
4498 trackMouseEnterExit(mouseOver, e);
4499
4500 // 4508327 : MOUSE_CLICKED should only go to the recipient of
4501 // the accompanying MOUSE_PRESSED, so don't reset mouseEventTarget on a
4502 // MOUSE_CLICKED.
4503 if (!isMouseGrab(e) && id != MouseEvent.MOUSE_CLICKED) {
4504 mouseEventTarget = (mouseOver != nativeContainer) ? mouseOver: null;
4505 }
4506
4507 if (mouseEventTarget != null) {
4508 switch (id) {
4509 case MouseEvent.MOUSE_ENTERED:
4510 case MouseEvent.MOUSE_EXITED:
4511 break;
4512 case MouseEvent.MOUSE_PRESSED:
4513 retargetMouseEvent(mouseEventTarget, id, e);
4514 break;
4515 case MouseEvent.MOUSE_RELEASED:
4516 retargetMouseEvent(mouseEventTarget, id, e);
4517 break;
4518 case MouseEvent.MOUSE_CLICKED:
4519 // 4508327: MOUSE_CLICKED should never be dispatched to a Component
4520 // other than that which received the MOUSE_PRESSED event. If the
4521 // mouse is now over a different Component, don't dispatch the event.
4522 // The previous fix for a similar problem was associated with bug
4523 // 4155217.
4524 if (mouseOver == mouseEventTarget) {
4532 if (isMouseGrab(e)) {
4533 retargetMouseEvent(mouseEventTarget, id, e);
4534 }
4535 break;
4536 case MouseEvent.MOUSE_WHEEL:
4537 // This may send it somewhere that doesn't have MouseWheelEvents
4538 // enabled. In this case, Component.dispatchEventImpl() will
4539 // retarget the event to a parent that DOES have the events enabled.
4540 if (eventLog.isLoggable(PlatformLogger.FINEST) && (mouseOver != null)) {
4541 eventLog.finest("retargeting mouse wheel to " +
4542 mouseOver.getName() + ", " +
4543 mouseOver.getClass());
4544 }
4545 retargetMouseEvent(mouseOver, id, e);
4546 break;
4547 }
4548 //Consuming of wheel events is implemented in "retargetMouseEvent".
4549 if (id != MouseEvent.MOUSE_WHEEL) {
4550 e.consume();
4551 }
4552 }
4553 return e.isConsumed();
4554 }
4555
4556 private boolean processDropTargetEvent(SunDropTargetEvent e) {
4557 int id = e.getID();
4558 int x = e.getX();
4559 int y = e.getY();
4560
4561 /*
4562 * Fix for BugTraq ID 4395290.
4563 * It is possible that SunDropTargetEvent's Point is outside of the
4564 * native container bounds. In this case we truncate coordinates.
4565 */
4566 if (!nativeContainer.contains(x, y)) {
4567 final Dimension d = nativeContainer.getSize();
4568 if (d.width <= x) {
4569 x = d.width - 1;
4570 } else if (x < 0) {
4571 x = 0;
4875
4876 /**
4877 * This variable is not used, but kept for serialization compatibility
4878 */
4879 private Component focus;
4880
4881 /**
4882 * The current subcomponent being hosted by this windowed
4883 * component that has events being forwarded to it. If this
4884 * is null, there are currently no events being forwarded to
4885 * a subcomponent.
4886 */
4887 private transient Component mouseEventTarget;
4888
4889 /**
4890 * The last component entered
4891 */
4892 private transient Component targetLastEntered;
4893
4894 /**
4895 * Is the mouse over the native container
4896 */
4897 private transient boolean isMouseInNativeContainer = false;
4898
4899 /**
4900 * This variable is not used, but kept for serialization compatibility
4901 */
4902 private Cursor nativeCursor;
4903
4904 /**
4905 * The event mask for contained lightweight components. Lightweight
4906 * components need a windowed container to host window-related
4907 * events. This separate mask indicates events that have been
4908 * requested by contained lightweight components without effecting
4909 * the mask of the windowed component itself.
4910 */
4911 private long eventMask;
4912
4913 /**
4914 * The kind of events routed to lightweight components from windowed
4915 * hosts.
4916 */
4917 private static final long PROXY_EVENT_MASK =
4918 AWTEvent.FOCUS_EVENT_MASK |
4919 AWTEvent.KEY_EVENT_MASK |
4920 AWTEvent.MOUSE_EVENT_MASK |
4921 AWTEvent.MOUSE_MOTION_EVENT_MASK |
4922 AWTEvent.MOUSE_WHEEL_EVENT_MASK;
4923
4924 private static final long MOUSE_MASK =
4925 AWTEvent.MOUSE_EVENT_MASK |
4926 AWTEvent.MOUSE_MOTION_EVENT_MASK |
4927 AWTEvent.MOUSE_WHEEL_EVENT_MASK;
4928 }
|
3289 }
3290 }
3291 }
3292 }
3293
3294 if (reset) {
3295 KeyboardFocusManager.setMostRecentFocusOwner(window, null);
3296 }
3297 }
3298
3299 void clearCurrentFocusCycleRootOnHide() {
3300 KeyboardFocusManager kfm =
3301 KeyboardFocusManager.getCurrentKeyboardFocusManager();
3302 Container cont = kfm.getCurrentFocusCycleRoot();
3303
3304 if (cont == this || isParentOf(cont)) {
3305 kfm.setGlobalCurrentFocusCycleRootPriv(null);
3306 }
3307 }
3308
3309 @Override
3310 void clearLightweightDispatcherOnRemove(Component removedComponent) {
3311 if (dispatcher != null) {
3312 dispatcher.removeReferences(removedComponent);
3313 } else {
3314 //It is a Lightweight Container, should clear parent`s Dispatcher
3315 super.clearLightweightDispatcherOnRemove(removedComponent);
3316 }
3317 }
3318
3319 final Container getTraversalRoot() {
3320 if (isFocusCycleRoot()) {
3321 return findTraversalRoot();
3322 }
3323
3324 return super.getTraversalRoot();
3325 }
3326
3327 /**
3328 * Sets the focus traversal policy that will manage keyboard traversal of
3329 * this Container's children, if this Container is a focus cycle root. If
3330 * the argument is null, this Container inherits its policy from its focus-
3331 * cycle-root ancestor. If the argument is non-null, this policy will be
3332 * inherited by all focus-cycle-root children that have no keyboard-
3333 * traversal policy of their own (as will, recursively, their focus-cycle-
3334 * root children).
3335 * <p>
3336 * If this Container is not a focus cycle root, the policy will be
3337 * remembered, but will not be used or inherited by this or any other
3338 * Containers until this Container is made a focus cycle root.
4404 * container
4405 */
4406 private static final int LWD_MOUSE_DRAGGED_OVER = 1500;
4407
4408 private static final PlatformLogger eventLog = PlatformLogger.getLogger("java.awt.event.LightweightDispatcher");
4409
4410 LightweightDispatcher(Container nativeContainer) {
4411 this.nativeContainer = nativeContainer;
4412 mouseEventTarget = null;
4413 eventMask = 0;
4414 }
4415
4416 /*
4417 * Clean up any resources allocated when dispatcher was created;
4418 * should be called from Container.removeNotify
4419 */
4420 void dispose() {
4421 //System.out.println("Disposing lw dispatcher");
4422 stopListeningForOtherDrags();
4423 mouseEventTarget = null;
4424 targetLastEntered = null;
4425 }
4426
4427 /**
4428 * Enables events to subcomponents.
4429 */
4430 void enableEvents(long events) {
4431 eventMask |= events;
4432 }
4433
4434 /**
4435 * Dispatches an event to a sub-component if necessary, and
4436 * returns whether or not the event was forwarded to a
4437 * sub-component.
4438 *
4439 * @param e the event
4440 */
4441 boolean dispatchEvent(AWTEvent e) {
4442 boolean ret = false;
4443
4444 /*
4496 /**
4497 * This method attempts to distribute a mouse event to a lightweight
4498 * component. It tries to avoid doing any unnecessary probes down
4499 * into the component tree to minimize the overhead of determining
4500 * where to route the event, since mouse movement events tend to
4501 * come in large and frequent amounts.
4502 */
4503 private boolean processMouseEvent(MouseEvent e) {
4504 int id = e.getID();
4505 Component mouseOver = // sensitive to mouse events
4506 nativeContainer.getMouseEventTarget(e.getX(), e.getY(),
4507 Container.INCLUDE_SELF);
4508
4509 trackMouseEnterExit(mouseOver, e);
4510
4511 // 4508327 : MOUSE_CLICKED should only go to the recipient of
4512 // the accompanying MOUSE_PRESSED, so don't reset mouseEventTarget on a
4513 // MOUSE_CLICKED.
4514 if (!isMouseGrab(e) && id != MouseEvent.MOUSE_CLICKED) {
4515 mouseEventTarget = (mouseOver != nativeContainer) ? mouseOver: null;
4516 isCleaned = false;
4517 }
4518
4519 if (mouseEventTarget != null) {
4520 switch (id) {
4521 case MouseEvent.MOUSE_ENTERED:
4522 case MouseEvent.MOUSE_EXITED:
4523 break;
4524 case MouseEvent.MOUSE_PRESSED:
4525 retargetMouseEvent(mouseEventTarget, id, e);
4526 break;
4527 case MouseEvent.MOUSE_RELEASED:
4528 retargetMouseEvent(mouseEventTarget, id, e);
4529 break;
4530 case MouseEvent.MOUSE_CLICKED:
4531 // 4508327: MOUSE_CLICKED should never be dispatched to a Component
4532 // other than that which received the MOUSE_PRESSED event. If the
4533 // mouse is now over a different Component, don't dispatch the event.
4534 // The previous fix for a similar problem was associated with bug
4535 // 4155217.
4536 if (mouseOver == mouseEventTarget) {
4544 if (isMouseGrab(e)) {
4545 retargetMouseEvent(mouseEventTarget, id, e);
4546 }
4547 break;
4548 case MouseEvent.MOUSE_WHEEL:
4549 // This may send it somewhere that doesn't have MouseWheelEvents
4550 // enabled. In this case, Component.dispatchEventImpl() will
4551 // retarget the event to a parent that DOES have the events enabled.
4552 if (eventLog.isLoggable(PlatformLogger.FINEST) && (mouseOver != null)) {
4553 eventLog.finest("retargeting mouse wheel to " +
4554 mouseOver.getName() + ", " +
4555 mouseOver.getClass());
4556 }
4557 retargetMouseEvent(mouseOver, id, e);
4558 break;
4559 }
4560 //Consuming of wheel events is implemented in "retargetMouseEvent".
4561 if (id != MouseEvent.MOUSE_WHEEL) {
4562 e.consume();
4563 }
4564 } else if (isCleaned && id != MouseEvent.MOUSE_WHEEL) {
4565 //After mouseEventTarget was removed and cleaned should consume all events
4566 //until new mouseEventTarget is found
4567 e.consume();
4568 }
4569 return e.isConsumed();
4570 }
4571
4572 private boolean processDropTargetEvent(SunDropTargetEvent e) {
4573 int id = e.getID();
4574 int x = e.getX();
4575 int y = e.getY();
4576
4577 /*
4578 * Fix for BugTraq ID 4395290.
4579 * It is possible that SunDropTargetEvent's Point is outside of the
4580 * native container bounds. In this case we truncate coordinates.
4581 */
4582 if (!nativeContainer.contains(x, y)) {
4583 final Dimension d = nativeContainer.getSize();
4584 if (d.width <= x) {
4585 x = d.width - 1;
4586 } else if (x < 0) {
4587 x = 0;
4891
4892 /**
4893 * This variable is not used, but kept for serialization compatibility
4894 */
4895 private Component focus;
4896
4897 /**
4898 * The current subcomponent being hosted by this windowed
4899 * component that has events being forwarded to it. If this
4900 * is null, there are currently no events being forwarded to
4901 * a subcomponent.
4902 */
4903 private transient Component mouseEventTarget;
4904
4905 /**
4906 * The last component entered
4907 */
4908 private transient Component targetLastEntered;
4909
4910 /**
4911 * Indicates whether {@code mouseEventTarget} was removed and nulled
4912 */
4913 private transient boolean isCleaned;
4914
4915 /**
4916 * Is the mouse over the native container
4917 */
4918 private transient boolean isMouseInNativeContainer = false;
4919
4920 /**
4921 * This variable is not used, but kept for serialization compatibility
4922 */
4923 private Cursor nativeCursor;
4924
4925 /**
4926 * The event mask for contained lightweight components. Lightweight
4927 * components need a windowed container to host window-related
4928 * events. This separate mask indicates events that have been
4929 * requested by contained lightweight components without effecting
4930 * the mask of the windowed component itself.
4931 */
4932 private long eventMask;
4933
4934 /**
4935 * The kind of events routed to lightweight components from windowed
4936 * hosts.
4937 */
4938 private static final long PROXY_EVENT_MASK =
4939 AWTEvent.FOCUS_EVENT_MASK |
4940 AWTEvent.KEY_EVENT_MASK |
4941 AWTEvent.MOUSE_EVENT_MASK |
4942 AWTEvent.MOUSE_MOTION_EVENT_MASK |
4943 AWTEvent.MOUSE_WHEEL_EVENT_MASK;
4944
4945 private static final long MOUSE_MASK =
4946 AWTEvent.MOUSE_EVENT_MASK |
4947 AWTEvent.MOUSE_MOTION_EVENT_MASK |
4948 AWTEvent.MOUSE_WHEEL_EVENT_MASK;
4949
4950 void removeReferences(Component removedComponent) {
4951 if (mouseEventTarget == removedComponent) {
4952 isCleaned = true;
4953 mouseEventTarget = null;
4954 }
4955 if (targetLastEntered == removedComponent) {
4956 targetLastEntered = null;
4957 }
4958 }
4959 }
|