1 /*******************************************************************************
\r
2 * Copyright (c) 2007, 2010 Association for Decentralized Information Management
\r
3 * in Industry THTH ry.
\r
4 * All rights reserved. This program and the accompanying materials
\r
5 * are made available under the terms of the Eclipse Public License v1.0
\r
6 * which accompanies this distribution, and is available at
\r
7 * http://www.eclipse.org/legal/epl-v10.html
\r
10 * VTT Technical Research Centre of Finland - initial API and implementation
\r
11 *******************************************************************************/
\r
14 * @author Toni Kalajainen
\r
16 package org.simantics.scenegraph.g2d.events.adapter;
\r
18 import java.awt.event.InputEvent;
\r
19 import java.awt.event.MouseEvent;
\r
20 import java.awt.event.MouseListener;
\r
21 import java.awt.event.MouseMotionListener;
\r
22 import java.awt.event.MouseWheelEvent;
\r
23 import java.awt.event.MouseWheelListener;
\r
24 import java.awt.geom.Point2D;
\r
26 import org.simantics.scenegraph.g2d.events.EventDebugPolicy;
\r
27 import org.simantics.scenegraph.g2d.events.IEventHandler;
\r
28 import org.simantics.scenegraph.g2d.events.IEventQueue;
\r
29 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseButtonPressedEvent;
\r
30 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseButtonReleasedEvent;
\r
31 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseDoubleClickedEvent;
\r
32 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseEnterEvent;
\r
33 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseExitEvent;
\r
34 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseMovedEvent;
\r
35 import org.simantics.scenegraph.g2d.events.MouseEvent.MouseWheelMovedEvent;
\r
39 * Adapts AWT mouse events into G2D events.
\r
41 * Sends adapted events to IEventHandler
\r
43 public class AWTMouseEventAdapter extends AbstractEventAdapter implements MouseListener, MouseMotionListener, MouseWheelListener {
\r
45 private final boolean DEBUG = EventDebugPolicy.AWT_MOUSE_EVENT_ADAPTION;
\r
47 private final boolean IGNORE_CONSUMED_EVENTS = false;
\r
49 /** Mouse id of the default mouse */
\r
50 public static final int MOUSE_ID = 0;
\r
52 private final long [] pressTime = new long[5];
\r
54 int buttonStatus = 0;
\r
57 * create new adapter
\r
58 * @param sender the sender field in the events
\r
59 * @param delegator the target of the adapted events
\r
61 public AWTMouseEventAdapter(Object sender, IEventHandler delegator) {
\r
62 super(sender, delegator);
\r
66 * create new adapter
\r
67 * @param sender the sender field in the events
\r
70 public AWTMouseEventAdapter(Object sender, IEventQueue queue) {
\r
71 super(sender, queue);
\r
74 private Point2D getControlPosition(MouseEvent e)
\r
76 return new Point2D.Double(e.getX(), e.getY());
\r
79 private Point2D getScreenPosition(MouseEvent e)
\r
81 return e.getLocationOnScreen();
\r
84 private static int getStateMask(MouseEvent e) {
\r
85 int modifiers = e.getModifiersEx();
\r
87 if((modifiers & InputEvent.CTRL_DOWN_MASK) != 0)
\r
88 stateMask |= org.simantics.scenegraph.g2d.events.MouseEvent.CTRL_MASK;
\r
89 if((modifiers & InputEvent.ALT_DOWN_MASK) != 0)
\r
90 stateMask |= org.simantics.scenegraph.g2d.events.MouseEvent.ALT_MASK;
\r
91 if((modifiers & InputEvent.ALT_GRAPH_DOWN_MASK) != 0)
\r
92 stateMask |= org.simantics.scenegraph.g2d.events.MouseEvent.ALT_GRAPH_MASK;
\r
93 if((modifiers & InputEvent.SHIFT_DOWN_MASK) != 0)
\r
94 stateMask |= org.simantics.scenegraph.g2d.events.MouseEvent.SHIFT_MASK;
\r
98 private int getMouseButton(MouseEvent e)
\r
100 int awtMouseButton = e.getButton();
\r
101 if (awtMouseButton == MouseEvent.BUTTON1)
\r
102 return org.simantics.scenegraph.g2d.events.MouseEvent.LEFT_BUTTON;
\r
103 if (awtMouseButton == MouseEvent.BUTTON2)
\r
104 return org.simantics.scenegraph.g2d.events.MouseEvent.MIDDLE_BUTTON;
\r
105 if (awtMouseButton == MouseEvent.BUTTON3)
\r
106 return org.simantics.scenegraph.g2d.events.MouseEvent.RIGHT_BUTTON;
\r
107 return awtMouseButton;
\r
111 * Converts AWT {@link MouseEvent#getModifiersEx()} mouse button status to
\r
112 * G2D mouse button status. Only supports three buttons while AWT supports
\r
118 private int getButtonStatus(MouseEvent e) {
\r
119 int modex = e.getModifiersEx();
\r
121 status |= (modex & MouseEvent.BUTTON1_DOWN_MASK) != 0 ? org.simantics.scenegraph.g2d.events.MouseEvent.LEFT_MASK : 0;
\r
122 status |= (modex & MouseEvent.BUTTON2_DOWN_MASK) != 0 ? org.simantics.scenegraph.g2d.events.MouseEvent.MIDDLE_MASK : 0;
\r
123 status |= (modex & MouseEvent.BUTTON3_DOWN_MASK) != 0 ? org.simantics.scenegraph.g2d.events.MouseEvent.RIGHT_MASK : 0;
\r
128 public void mouseEntered(MouseEvent e) {
\r
129 if (IGNORE_CONSUMED_EVENTS) {
\r
130 if (e.isConsumed()) {
\r
132 System.out.println("AWT mouse entered but already consumed: " + e);
\r
137 System.out.println("AWT mouse entered: " + e);
\r
138 buttonStatus = getButtonStatus(e);
\r
139 MouseEnterEvent me = new MouseEnterEvent(sender, e.getWhen(), MOUSE_ID, buttonStatus, getStateMask(e), getControlPosition(e), getScreenPosition(e));
\r
144 public void mouseExited(MouseEvent e) {
\r
145 if (IGNORE_CONSUMED_EVENTS) {
\r
146 if (e.isConsumed()) {
\r
148 System.out.println("AWT mouse exited but already consumed: " + e);
\r
153 System.out.println("AWT mouse exited: " + e);
\r
155 MouseExitEvent me = new MouseExitEvent(sender, e.getWhen(), MOUSE_ID, buttonStatus, getStateMask(e), getControlPosition(e), getScreenPosition(e));
\r
160 public void mousePressed(MouseEvent e) {
\r
161 if (IGNORE_CONSUMED_EVENTS) {
\r
162 if (e.isConsumed()) {
\r
164 System.out.println("AWT mouse pressed but already consumed: " + e);
\r
169 System.out.println("AWT mouse pressed: " + e);
\r
171 int mouseButton = getMouseButton(e);
\r
172 if (mouseButton == MouseEvent.NOBUTTON) {
\r
173 // This is strange, seems to happen on Linux constantly when pressing buttons rapidly.
\r
174 //System.out.println("NO BUTTON EVENT: " + e);
\r
178 if (mouseButton<=pressTime.length) pressTime[mouseButton-1] = e.getWhen();
\r
179 buttonStatus |= 1 << (mouseButton-1);
\r
181 handleEvent(new MouseButtonPressedEvent(sender, e.getWhen(), MOUSE_ID,
\r
182 buttonStatus, getStateMask(e), mouseButton, getControlPosition(e), getScreenPosition(e)));
\r
183 if (e.getClickCount() == 2) {
\r
184 handleEvent(new MouseDoubleClickedEvent(sender, e.getWhen(),
\r
185 MOUSE_ID, buttonStatus, getStateMask(e), mouseButton, getControlPosition(e), getScreenPosition(e)));
\r
190 public void mouseReleased(MouseEvent e) {
\r
191 if (IGNORE_CONSUMED_EVENTS) {
\r
192 if (e.isConsumed()) {
\r
194 System.out.println("AWT mouse released but already consumed: " + e);
\r
199 System.out.println("AWT mouse released: " + e);
\r
201 int mouseButton = getMouseButton(e);
\r
202 if (mouseButton == MouseEvent.NOBUTTON) {
\r
203 // This is strange, seems to happen on Linux constantly when pressing buttons rapidly.
\r
204 //System.out.println("NO BUTTON EVENT: " + e);
\r
208 long holdTime = Long.MAX_VALUE;
\r
209 if (mouseButton<=pressTime.length)
\r
210 holdTime = e.getWhen() - pressTime[mouseButton-1];
\r
212 int stateMask = getStateMask(e);
\r
214 // This works around the problem of AWT putting the ALT_DOWN_MASK in the
\r
215 // mouse event extended modifiers when button 2 is pressed.
\r
216 if (mouseButton == org.simantics.scenegraph.g2d.events.MouseEvent.MIDDLE_BUTTON) {
\r
217 stateMask &= ~(org.simantics.scenegraph.g2d.events.MouseEvent.ALT_MASK);
\r
220 buttonStatus &=~ (1<<(mouseButton-1));
\r
221 MouseButtonReleasedEvent me = new MouseButtonReleasedEvent(sender, e.getWhen(), MOUSE_ID, buttonStatus, stateMask, mouseButton, holdTime, getControlPosition(e), getScreenPosition(e));
\r
226 public void mouseDragged(MouseEvent e) {
\r
227 if (IGNORE_CONSUMED_EVENTS) {
\r
228 if (e.isConsumed()) {
\r
230 System.out.println("AWT mouse dragged but already consumed: " + e);
\r
235 System.out.println("AWT mouse dragged: " + e);
\r
236 MouseMovedEvent me = new MouseMovedEvent(sender, e.getWhen(), MOUSE_ID, buttonStatus, getStateMask(e), getControlPosition(e), getScreenPosition(e));
\r
241 public void mouseMoved(MouseEvent e) {
\r
242 if (IGNORE_CONSUMED_EVENTS) {
\r
243 if (e.isConsumed()) {
\r
245 System.out.println("AWT mouse moved but already consumed: " + e);
\r
250 System.out.println("AWT mouse moved: " + e);
\r
251 MouseMovedEvent me = new MouseMovedEvent(sender, e.getWhen(), MOUSE_ID, buttonStatus, getStateMask(e), getControlPosition(e), getScreenPosition(e));
\r
256 public void mouseWheelMoved(MouseWheelEvent e) {
\r
257 if (IGNORE_CONSUMED_EVENTS) {
\r
258 if (e.isConsumed()) {
\r
260 System.out.println("AWT mouse wheel moved but already consumed: " + e);
\r
265 System.out.println("AWT mouse wheel moved: " + e);
\r
266 int wheelRotation = 0;
\r
267 if (e.getScrollType() == MouseWheelEvent.WHEEL_UNIT_SCROLL) {
\r
268 wheelRotation = -e.getUnitsToScroll();
\r
270 wheelRotation = -e.getWheelRotation();
\r
272 handleEvent(new MouseWheelMovedEvent(
\r
273 sender, e.getWhen(), MOUSE_ID, buttonStatus, getStateMask(e), getControlPosition(e), getScreenPosition(e),
\r
274 e.getScrollType(), e.getScrollAmount(), wheelRotation
\r
280 public void mouseClicked(MouseEvent e) {
\r
281 if (IGNORE_CONSUMED_EVENTS) {
\r
282 if (e.isConsumed()) {
\r
284 System.out.println("AWT mouse clicked but already consumed: " + e);
\r
289 System.out.println("AWT mouse clicked: " + e);
\r