Note that there are some explanatory texts on larger screens.

plurals
  1. POmultiTouch android | getting Action of each touch point
    text
    copied!<p>I am trying to handle multiTouch in android, my plan is to use 2 fingers in the app. I know how to use one touch point, but I am not sure about how to use more than one touch point.</p> <p>Here is my code, OnTouch:</p> <pre><code> public boolean onTouch(View view, MotionEvent event) { for(int i = 0; i &lt; event.getPointerCount(); i++){ float x = event.getX(i); float y = event.getY(i); // using the data here... //.... } return true; } </code></pre> <p>now after i get the x and y coordinates for each point, how would i get the action that happens? i want to use <code>event.getAction</code>, but it doesn't take a parameter such as the point index. how can i get the action type for each touch point?</p> <p>UPDATE: ok, so now i can successfully manage and handle two fingers, now, after I've done that, I made a simple class called <code>Finger</code> to handle each touch point, now whenever i have two fingers on the screen, and i try to remove one of them, and then move/remove the other finger, the game just crashes! </p> <p>OnTouch:</p> <pre><code>public boolean onTouch(View view, MotionEvent event) { int pointerCount = event.getPointerCount(); if(pointerCount &gt; 2){ pointerCount = 2; System.out.println("too many fingers!"); } // since i want to handle only two fingers, every other finger will be ignored. for (int i = 0; i &lt; pointerCount; i++) { float x = event.getX(i); float y = event.getY(i); int id = event.getPointerId(i); int action = event.getActionMasked(); int actionIndex = event.getActionIndex(); if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_DOWN) { if (fingers.get(i) == null) fingers.set(i, new Finger(x, y, id)); } if (fingers.get(i).type == Finger.SCREEN_FINGER) { switch (action) { case MotionEvent.ACTION_UP: fingers.set(i, null); System.out.println(id + " action_up!"); break; case MotionEvent.ACTION_POINTER_UP: fingers.set(i, null); System.out.println(id + " pointer_up!"); break; case MotionEvent.ACTION_MOVE: fingers.get(i).setPos(x, y); System.out.println(id + " action_move!, x: "+fingers.get(i).x+", y: "+fingers.get(i).y); break; default: } }else if (fingers.get(i).type == Finger.DPAD_FINGER) { switch (action) { case MotionEvent.ACTION_UP: fingers.set(i, null); System.out.println(id + " action_up! - dpad"); break; case MotionEvent.ACTION_POINTER_UP: fingers.set(i, null); System.out.println(id + " pointer_up! - dpad"); break; case MotionEvent.ACTION_MOVE: fingers.get(i).setPos(x, y); System.out.println(id + " action_move! - dpad, x: "+fingers.get(i).x+", y: "+fingers.get(i).y); break; default: } } } return true; } </code></pre> <p>i create a List for the Fingers:</p> <p>List fingers = new LinkedList();</p> <p>in the constructor i put:</p> <pre><code>fingers.add(0, null); fingers.add(1, null); </code></pre> <p>Finally, the Finger Class:</p> <pre><code>public class Finger { public final static int DPAD_FINGER = 0; public final static int SCREEN_FINGER = 1; public float x, y; public int type; public int id; public Finger(float x, float y,int id) { this.id = id; checkType(x, y); } public void checkType(float x, float y) { if(x&gt;Dpad.x &amp;&amp; x &lt; Dpad.x+Dpad.Width &amp;&amp; y&gt; Dpad.y &amp;&amp; y&lt;Dpad.y+Dpad.Height){ System.out.println("inside DPAD"); type = DPAD_FINGER; }else{ System.out.println("Outside DPAD"); type = SCREEN_FINGER; } } public void setPos(float x, float y){ this.x = x; this.y = y; } } </code></pre> <p>now when i do all that, everything is fine, until i remove one finger and move/remove the other one, i get the following error in the LogCat:</p> <pre><code> 05-18 15:22:03.812: E/InputEventReceiver(20124): Exception dispatching input event. 05-18 15:22:03.812: W/dalvikvm(20124): threadid=1: thread exiting with uncaught exception (group=0x41e00438) 05-18 15:22:03.822: E/AndroidRuntime(20124): FATAL EXCEPTION: main 05-18 15:22:03.822: E/AndroidRuntime(20124): java.lang.NullPointerException 05-18 15:22:03.822: E/AndroidRuntime(20124): at smellychiz.projects.ogc.util.ChizView$1.onTouch(ChizView.java:70) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.View.dispatchTouchEvent(View.java:7241) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2185) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1928) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2185) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1928) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:2185) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1928) 05-18 15:22:03.822: E/AndroidRuntime(20124): at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.java:2116) 05-18 15:22:03.822: E/AndroidRuntime(20124): at com.android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1469) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.app.Activity.dispatchTouchEvent(Activity.java:2477) 05-18 15:22:03.822: E/AndroidRuntime(20124): at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.java:2064) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.View.dispatchPointerEvent(View.java:7430) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl.deliverPointerEvent(ViewRootImpl.java:3457) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl.deliverInputEvent(ViewRootImpl.java:3389) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl.doProcessInputEvents(ViewRootImpl.java:4483) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl.enqueueInputEvent(ViewRootImpl.java:4461) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl$WindowInputEventReceiver.onInputEvent(ViewRootImpl.java:4565) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.InputEventReceiver.dispatchInputEvent(InputEventReceiver.java:171) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.InputEventReceiver.nativeConsumeBatchedInputEvents(Native Method) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.InputEventReceiver.consumeBatchedInputEvents(InputEventReceiver.java:163) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl.doConsumeBatchedInput(ViewRootImpl.java:4533) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.ViewRootImpl$ConsumeBatchedInputRunnable.run(ViewRootImpl.java:4584) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.Choreographer$CallbackRecord.run(Choreographer.java:725) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.Choreographer.doCallbacks(Choreographer.java:555) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.Choreographer.doFrame(Choreographer.java:523) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:711) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.os.Handler.handleCallback(Handler.java:615) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.os.Handler.dispatchMessage(Handler.java:92) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.os.Looper.loop(Looper.java:137) 05-18 15:22:03.822: E/AndroidRuntime(20124): at android.app.ActivityThread.main(ActivityThread.java:4950) 05-18 15:22:03.822: E/AndroidRuntime(20124): at java.lang.reflect.Method.invokeNative(Native Method) 05-18 15:22:03.822: E/AndroidRuntime(20124): at java.lang.reflect.Method.invoke(Method.java:511) 05-18 15:22:03.822: E/AndroidRuntime(20124): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1004) 05-18 15:22:03.822: E/AndroidRuntime(20124): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:771) 05-18 15:22:03.822: E/AndroidRuntime(20124): at dalvik.system.NativeStart.main(Native Method) </code></pre> <p>UPDATE: </p> <p>instead of re-setting the fingers and setting them to null and then re-setting them again, i just removed them when finger was up and re created them when finger was down and updated when the finger moved. Now it works perfectly fine!</p> <p>UPDATE....</p> <p>eventually the problem is not solved, even though the app does not crash, when one of the fingers get lifted, it acts as if both fingers get lifted. </p> <p>here is the current code of <code>onTouch</code> method:</p> <pre><code>public boolean onTouch(View view, MotionEvent event) { int pointerCount = event.getPointerCount(); if(pointerCount &gt; 2){ pointerCount = 2; System.out.println("too many fingers!"); } // since i want to handle only two fingers, every other finger will be ignored. for (int i = 0; i &lt; pointerCount; i++) { float x = event.getX(i); float y = event.getY(i); int id = event.getPointerId(i); int action = event.getActionMasked(); int actionIndex = event.getActionIndex(); if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_DOWN) { if (fingers.get(i) == null) fingers.add(i, new Finger(x, y, id)); } if (fingers.get(i).type == Finger.SCREEN_FINGER) { switch (action) { case MotionEvent.ACTION_UP: fingers.remove(i); System.out.println(id + " action_up!"); break; case MotionEvent.ACTION_POINTER_UP: fingers.remove(i); System.out.println(id + " pointer_up!"); break; case MotionEvent.ACTION_MOVE: fingers.get(i).setPos(x, y); System.out.println(id + " action_move!, x: "+fingers.get(i).x+", y: "+fingers.get(i).y); break; default: } }else if (fingers.get(i).type == Finger.DPAD_FINGER) { switch (action) { case MotionEvent.ACTION_UP: fingers.remove(i); System.out.println(id + " action_up! - dpad"); break; case MotionEvent.ACTION_POINTER_UP: fingers.remove(i); System.out.println(id + " pointer_up! - dpad"); break; case MotionEvent.ACTION_MOVE: fingers.get(i).setPos(x, y); System.out.println(id + " action_move! - dpad, x: "+fingers.get(i).x+", y: "+fingers.get(i).y); break; default: } } } </code></pre> <p>so whenever the one of the fingers get lifted, the logCat writes as if both fingers were lifted off the screen. any ideas? </p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload