1a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartapackage com.jme3.input.android;
2a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
3a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.content.Context;
4a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.opengl.GLSurfaceView;
5a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.util.AttributeSet;
6a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.view.GestureDetector;
7a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.view.KeyEvent;
8a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.view.MotionEvent;
9a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport android.view.ScaleGestureDetector;
10a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.KeyInput;
11a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.RawInputListener;
12a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.TouchInput;
13a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.event.MouseButtonEvent;
14a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.event.MouseMotionEvent;
15a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.event.TouchEvent;
16a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.input.event.TouchEvent.Type;
17a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.math.Vector2f;
18a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport com.jme3.util.RingBuffer;
19a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport java.util.HashMap;
20a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartaimport java.util.logging.Logger;
21a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
22a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta/**
23a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta * <code>AndroidInput</code> is one of the main components that connect jme with android. Is derived from GLSurfaceView and handles all Inputs
24a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta * @author larynx
25a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta *
26a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta */
27a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Bartapublic class AndroidInput extends GLSurfaceView implements
28a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchInput,
29a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        GestureDetector.OnGestureListener,
30a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        GestureDetector.OnDoubleTapListener,
31a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        ScaleGestureDetector.OnScaleGestureListener {
32a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
33a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    final private static int MAX_EVENTS = 1024;
34a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // Custom settings
35a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean mouseEventsEnabled = true;
36a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean mouseEventsInvertX = false;
37a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean mouseEventsInvertY = false;
38a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean keyboardEventsEnabled = false;
39a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean dontSendHistory = false;
40a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // Used to transfer events from android thread to GLThread
41a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    final private RingBuffer<TouchEvent> eventQueue = new RingBuffer<TouchEvent>(MAX_EVENTS);
42a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    final private RingBuffer<TouchEvent> eventPoolUnConsumed = new RingBuffer<TouchEvent>(MAX_EVENTS);
43a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    final private RingBuffer<TouchEvent> eventPool = new RingBuffer<TouchEvent>(MAX_EVENTS);
44a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    final private HashMap<Integer, Vector2f> lastPositions = new HashMap<Integer, Vector2f>();
45a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // Internal
46a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private ScaleGestureDetector scaledetector;
47a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private GestureDetector detector;
48a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private int lastX;
49a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private int lastY;
50a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private final static Logger logger = Logger.getLogger(AndroidInput.class.getName());
51a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private boolean isInitialized = false;
52a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private RawInputListener listener = null;
53a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private static final int[] ANDROID_TO_JME = {
54a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // unknown
55a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // key code soft left
56a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // key code soft right
57a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_HOME,
58a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_ESCAPE, // key back
59a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // key call
60a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // key endcall
61a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_0,
62a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_1,
63a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_2,
64a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_3,
65a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_4,
66a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_5,
67a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_6,
68a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_7,
69a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_8,
70a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_9,
71a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_MULTIPLY,
72a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // key pound
73a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_UP,
74a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_DOWN,
75a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_LEFT,
76a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RIGHT,
77a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RETURN, // dpad center
78a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // volume up
79a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // volume down
80a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_POWER, // power (?)
81a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // camera
82a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // clear
83a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_A,
84a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_B,
85a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_C,
86a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_D,
87a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_E,
88a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_F,
89a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_G,
90a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_H,
91a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_I,
92a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_J,
93a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_K,
94a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_L,
95a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_M,
96a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_N,
97a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_O,
98a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_P,
99a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_Q,
100a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_R,
101a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_S,
102a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_T,
103a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_U,
104a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_V,
105a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_W,
106a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_X,
107a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_Y,
108a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_Z,
109a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_COMMA,
110a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_PERIOD,
111a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_LMENU,
112a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RMENU,
113a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_LSHIFT,
114a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RSHIFT,
115a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //        0x0, // fn
116a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //        0x0, // cap (?)
117a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
118a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_TAB,
119a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_SPACE,
120a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // sym (?) symbol
121a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // explorer
122a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, // envelope
123a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RETURN, // newline/enter
124a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_DELETE,
125a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_GRAVE,
126a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_MINUS,
127a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_EQUALS,
128a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_LBRACKET,
129a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_RBRACKET,
130a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_BACKSLASH,
131a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_SEMICOLON,
132a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_APOSTROPHE,
133a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_SLASH,
134a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_AT, // at (@)
135a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_NUMLOCK, //0x0, // num
136a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, //headset hook
137a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0, //focus
138a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_ADD,
139a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        KeyInput.KEY_LMETA, //menu
140a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//notification
141a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//search
142a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media play/pause
143a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media stop
144a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media next
145a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media previous
146a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media rewind
147a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//media fastforward
148a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        0x0,//mute
149a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    };
150a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
151a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public AndroidInput(Context ctx, AttributeSet attribs) {
152a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        super(ctx, attribs);
153a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        detector = new GestureDetector(null, this, null, false);
154a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        scaledetector = new ScaleGestureDetector(ctx, this);
155a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
156a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
157a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
158a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public AndroidInput(Context ctx) {
159a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        super(ctx);
160a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        detector = new GestureDetector(null, this, null, false);
161a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        scaledetector = new ScaleGestureDetector(ctx, this);
162a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
163a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
164a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private TouchEvent getNextFreeTouchEvent() {
165a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return getNextFreeTouchEvent(false);
166a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
167a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
168a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    /**
169a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     * Fetches a touch event from the reuse pool
170a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     * @param wait if true waits for a reusable event to get available/released
171a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     * by an other thread, if false returns a new one if needed.
172a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     *
173a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     * @return a usable TouchEvent
174a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     */
175a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private TouchEvent getNextFreeTouchEvent(boolean wait) {
176a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent evt = null;
177a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        synchronized (eventPoolUnConsumed) {
178a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            int size = eventPoolUnConsumed.size();
179a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            while (size > 0) {
180a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                evt = eventPoolUnConsumed.pop();
181a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                if (!evt.isConsumed()) {
182a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    eventPoolUnConsumed.push(evt);
183a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    evt = null;
184a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                } else {
185a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    break;
186a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
187a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                size--;
188a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            }
189a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
190a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
191a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        if (evt == null) {
192a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            if (eventPool.isEmpty() && wait) {
193a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                logger.warning("eventPool buffer underrun");
194a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                boolean isEmpty;
195a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                do {
196a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    synchronized (eventPool) {
197a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        isEmpty = eventPool.isEmpty();
198a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
199a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    try {
200a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        Thread.sleep(50);
201a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    } catch (InterruptedException e) {
202a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
203a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                } while (isEmpty);
204a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                synchronized (eventPool) {
205a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    evt = eventPool.pop();
206a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
207a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            } else if (eventPool.isEmpty()) {
208a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                evt = new TouchEvent();
209a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                logger.warning("eventPool buffer underrun");
210a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            } else {
211a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                synchronized (eventPool) {
212a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    evt = eventPool.pop();
213a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
214a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            }
215a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
216a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return evt;
217a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
218a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
219a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    /**
220a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     * onTouchEvent gets called from android thread on touchpad events
221a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta     */
222a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
223a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onTouchEvent(MotionEvent event) {
224a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        boolean bWasHandled = false;
225a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch;
226a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //    System.out.println("native : " + event.getAction());
227a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        int action = event.getAction() & MotionEvent.ACTION_MASK;
228a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        int pointerIndex = (event.getAction() & MotionEvent.ACTION_POINTER_INDEX_MASK)
229a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                >> MotionEvent.ACTION_POINTER_INDEX_SHIFT;
230a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        int pointerId = event.getPointerId(pointerIndex);
231a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
232a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // final int historySize = event.getHistorySize();
233a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //final int pointerCount = event.getPointerCount();
234a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
235a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        switch (action) {
236a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_POINTER_DOWN:
237a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_DOWN:
238a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch = getNextFreeTouchEvent();
239a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.set(Type.DOWN, event.getX(pointerIndex), this.getHeight() - event.getY(pointerIndex), 0, 0);
240a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setPointerId(pointerId);
241a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setTime(event.getEventTime());
242a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setPressure(event.getPressure(pointerIndex));
243a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                processEvent(touch);
244a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
245a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                bWasHandled = true;
246a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                break;
247a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
248a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_POINTER_UP:
249a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_CANCEL:
250a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_UP:
251a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
252a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch = getNextFreeTouchEvent();
253a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.set(Type.UP, event.getX(pointerIndex), this.getHeight() - event.getY(pointerIndex), 0, 0);
254a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setPointerId(pointerId);
255a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setTime(event.getEventTime());
256a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                touch.setPressure(event.getPressure(pointerIndex));
257a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                processEvent(touch);
258a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
259a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
260a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                bWasHandled = true;
261a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                break;
262a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_MOVE:
263a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
264a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
265a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                // Convert all pointers into events
266a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                for (int p = 0; p < event.getPointerCount(); p++) {
267a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    Vector2f lastPos = lastPositions.get(pointerIndex);
268a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    if (lastPos == null) {
269a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        lastPos = new Vector2f(event.getX(pointerIndex), this.getHeight() - event.getY(pointerIndex));
270a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        lastPositions.put(pointerId, lastPos);
271a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
272a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    touch = getNextFreeTouchEvent();
273a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    touch.set(Type.MOVE, event.getX(pointerIndex), this.getHeight() - event.getY(pointerIndex), event.getX(pointerIndex) - lastPos.x, this.getHeight() - event.getY(pointerIndex) - lastPos.y);
274a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    touch.setPointerId(pointerId);
275a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    touch.setTime(event.getEventTime());
276a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    touch.setPressure(event.getPressure(pointerIndex));
277a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    processEvent(touch);
278a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    lastPos.set(event.getX(pointerIndex), this.getHeight() - event.getY(pointerIndex));
279a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
280a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                bWasHandled = true;
281a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                break;
282a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            case MotionEvent.ACTION_OUTSIDE:
283a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                break;
284a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
285a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
286a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
287a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Try to detect gestures
288a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.detector.onTouchEvent(event);
289a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.scaledetector.onTouchEvent(event);
290a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
291a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return bWasHandled;
292a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
293a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
294a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
295a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onKeyDown(int keyCode, KeyEvent event) {
296a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent evt;
297a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt = getNextFreeTouchEvent();
298a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.set(TouchEvent.Type.KEY_DOWN);
299a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setKeyCode(keyCode);
300a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setCharacters(event.getCharacters());
301a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setTime(event.getEventTime());
302a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
303a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Send the event
304a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(evt);
305a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
306a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Handle all keys ourself except Volume Up/Down
307a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        if ((keyCode == KeyEvent.KEYCODE_VOLUME_UP) || (keyCode == KeyEvent.KEYCODE_VOLUME_DOWN)) {
308a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            return false;
309a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        } else {
310a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            return true;
311a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
312a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
313a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
314a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
315a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onKeyUp(int keyCode, KeyEvent event) {
316a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent evt;
317a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt = getNextFreeTouchEvent();
318a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.set(TouchEvent.Type.KEY_UP);
319a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setKeyCode(keyCode);
320a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setCharacters(event.getCharacters());
321a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        evt.setTime(event.getEventTime());
322a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
323a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Send the event
324a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(evt);
325a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
326a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Handle all keys ourself except Volume Up/Down
327a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        if ((keyCode == KeyEvent.KEYCODE_VOLUME_UP) || (keyCode == KeyEvent.KEYCODE_VOLUME_DOWN)) {
328a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            return false;
329a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        } else {
330a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            return true;
331a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
332a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
333a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
334a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // -----------------------------------------
335a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // JME3 Input interface
336a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
337a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void initialize() {
338a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent item;
339a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        for (int i = 0; i < MAX_EVENTS; i++) {
340a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            item = new TouchEvent();
341a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            eventPool.push(item);
342a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
343a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        isInitialized = true;
344a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
345a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
346a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
347a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void destroy() {
348a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        isInitialized = false;
349a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
350a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        // Clean up queues
351a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        while (!eventPool.isEmpty()) {
352a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            eventPool.pop();
353a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
354a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        while (!eventQueue.isEmpty()) {
355a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            eventQueue.pop();
356a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
357a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
358a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
359a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
360a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean isInitialized() {
361a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return isInitialized;
362a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
363a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
364a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
365a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setInputListener(RawInputListener listener) {
366a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.listener = listener;
367a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
368a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
369a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
370a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public long getInputTimeNanos() {
371a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return System.nanoTime();
372a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
373a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // -----------------------------------------
374a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
375a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private void processEvent(TouchEvent event) {
376a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        synchronized (eventQueue) {
377a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            eventQueue.push(event);
378a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
379a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
380a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
381a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    //  ---------------  INSIDE GLThread  ---------------
382a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
383a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void update() {
384a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        generateEvents();
385a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
386a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
387a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    private void generateEvents() {
388a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        if (listener != null) {
389a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            TouchEvent event;
390a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            MouseButtonEvent btn;
391a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            int newX;
392a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            int newY;
393a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
394a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            while (!eventQueue.isEmpty()) {
395a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                synchronized (eventQueue) {
396a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    event = eventQueue.pop();
397a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
398a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                if (event != null) {
399a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    listener.onTouchEvent(event);
400a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
401a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    if (mouseEventsEnabled) {
402a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        if (mouseEventsInvertX) {
403a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            newX = this.getWidth() - (int) event.getX();
404a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        } else {
405a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            newX = (int) event.getX();
406a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        }
407a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
408a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        if (mouseEventsInvertY) {
409a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            newY = this.getHeight() - (int) event.getY();
410a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        } else {
411a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            newY = (int) event.getY();
412a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        }
413a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
414a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        switch (event.getType()) {
415a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            case DOWN:
416a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                // Handle mouse down event
417a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                btn = new MouseButtonEvent(0, true, newX, newY);
418a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                btn.setTime(event.getTime());
419a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                listener.onMouseButtonEvent(btn);
420a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                // Store current pos
421a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastX = -1;
422a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastY = -1;
423a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                break;
424a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
425a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            case UP:
426a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                // Handle mouse up event
427a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                btn = new MouseButtonEvent(0, false, newX, newY);
428a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                btn.setTime(event.getTime());
429a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                listener.onMouseButtonEvent(btn);
430a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                // Store current pos
431a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastX = -1;
432a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastY = -1;
433a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                break;
434a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
435a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                            case MOVE:
436a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                int dx;
437a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                int dy;
438a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                if (lastX != -1) {
439a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                    dx = newX - lastX;
440a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                    dy = newY - lastY;
441a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                } else {
442a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                    dx = 0;
443a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                    dy = 0;
444a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                }
445a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                MouseMotionEvent mot = new MouseMotionEvent(newX, newY, dx, dy, 0, 0);
446a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                mot.setTime(event.getTime());
447a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                listener.onMouseMotionEvent(mot);
448a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastX = newX;
449a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                lastY = newY;
450a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                                break;
451a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        }
452a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
453a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
454a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
455a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
456a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
457a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                if (event.isConsumed() == false) {
458a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    synchronized (eventPoolUnConsumed) {
459a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        eventPoolUnConsumed.push(event);
460a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
461a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
462a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                } else {
463a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    synchronized (eventPool) {
464a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                        eventPool.push(event);
465a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                    }
466a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta                }
467a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta            }
468a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
469a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        }
470a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
471a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    //  --------------- ENDOF INSIDE GLThread  ---------------
472a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
473a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // --------------- Gesture detected callback events  ---------------
474a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onDown(MotionEvent event) {
475a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return false;
476a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
477a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
478a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void onLongPress(MotionEvent event) {
479a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
480a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.LONGPRESSED, event.getX(), this.getHeight() - event.getY(), 0f, 0f);
481a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
482a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(event.getEventTime());
483a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
484a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
485a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
486a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onFling(MotionEvent event, MotionEvent event2, float vx, float vy) {
487a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
488a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.FLING, event.getX(), this.getHeight() - event.getY(), vx, vy);
489a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
490a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(event.getEventTime());
491a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
492a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
493a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return true;
494a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
495a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
496a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onSingleTapConfirmed(MotionEvent event) {
497a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //Nothing to do here the tap has already been detected.
498a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return false;
499a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
500a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
501a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onDoubleTap(MotionEvent event) {
502a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
503a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.DOUBLETAP, event.getX(), this.getHeight() - event.getY(), 0f, 0f);
504a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
505a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(event.getEventTime());
506a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
507a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return true;
508a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
509a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
510a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onDoubleTapEvent(MotionEvent event) {
511a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return false;
512a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
513a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
514a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onScaleBegin(ScaleGestureDetector scaleGestureDetector) {
515a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
516a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.SCALE_START, scaleGestureDetector.getFocusX(), scaleGestureDetector.getFocusY(), 0f, 0f);
517a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
518a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(scaleGestureDetector.getEventTime());
519a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleSpan(scaleGestureDetector.getCurrentSpan());
520a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleFactor(scaleGestureDetector.getScaleFactor());
521a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
522a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //    System.out.println("scaleBegin");
523a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
524a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return true;
525a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
526a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
527a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onScale(ScaleGestureDetector scaleGestureDetector) {
528a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
529a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.SCALE_MOVE, scaleGestureDetector.getFocusX(), this.getHeight() - scaleGestureDetector.getFocusY(), 0f, 0f);
530a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
531a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(scaleGestureDetector.getEventTime());
532a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleSpan(scaleGestureDetector.getCurrentSpan());
533a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleFactor(scaleGestureDetector.getScaleFactor());
534a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
535a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //   System.out.println("scale");
536a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
537a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return false;
538a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
539a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
540a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void onScaleEnd(ScaleGestureDetector scaleGestureDetector) {
541a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
542a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.SCALE_END, scaleGestureDetector.getFocusX(), this.getHeight() - scaleGestureDetector.getFocusY(), 0f, 0f);
543a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
544a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(scaleGestureDetector.getEventTime());
545a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleSpan(scaleGestureDetector.getCurrentSpan());
546a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setScaleFactor(scaleGestureDetector.getScaleFactor());
547a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
548a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
549a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
550a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
551a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
552a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.SCROLL, e1.getX(), this.getHeight() - e1.getY(), distanceX, distanceY * (-1));
553a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
554a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(e1.getEventTime());
555a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
556a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        //System.out.println("scroll " + e1.getPointerCount());
557a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return false;
558a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
559a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
560a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void onShowPress(MotionEvent event) {
561a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
562a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.SHOWPRESS, event.getX(), this.getHeight() - event.getY(), 0f, 0f);
563a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
564a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(event.getEventTime());
565a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
566a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
567a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
568a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean onSingleTapUp(MotionEvent event) {
569a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        TouchEvent touch = getNextFreeTouchEvent();
570a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.set(Type.TAP, event.getX(), this.getHeight() - event.getY(), 0f, 0f);
571a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setPointerId(0);
572a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        touch.setTime(event.getEventTime());
573a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        processEvent(touch);
574a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return true;
575a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
576a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
577a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
578a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setSimulateMouse(boolean simulate) {
579a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        mouseEventsEnabled = simulate;
580a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
581a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
582a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean getSimulateMouse() {
583a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return mouseEventsEnabled;
584a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
585a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
586a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
587a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setSimulateKeyboard(boolean simulate) {
588a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        keyboardEventsEnabled = simulate;
589a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
590a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
591a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    @Override
592a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setOmitHistoricEvents(boolean dontSendHistory) {
593a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.dontSendHistory = dontSendHistory;
594a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
595a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
596a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    // TODO: move to TouchInput
597a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean isMouseEventsEnabled() {
598a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return mouseEventsEnabled;
599a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
600a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
601a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setMouseEventsEnabled(boolean mouseEventsEnabled) {
602a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.mouseEventsEnabled = mouseEventsEnabled;
603a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
604a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
605a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean isMouseEventsInvertY() {
606a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return mouseEventsInvertY;
607a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
608a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
609a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setMouseEventsInvertY(boolean mouseEventsInvertY) {
610a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.mouseEventsInvertY = mouseEventsInvertY;
611a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
612a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
613a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public boolean isMouseEventsInvertX() {
614a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        return mouseEventsInvertX;
615a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
616a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta
617a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    public void setMouseEventsInvertX(boolean mouseEventsInvertX) {
618a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta        this.mouseEventsInvertX = mouseEventsInvertX;
619a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta    }
620a6b44658eb1c55295f132a36233a11aa2bd8f9cfScott Barta}
621