Frage

Ich versuche mit OnTouchListener Doppel-Tap-Ereignisse zu fangen. Ich denke, ich würde eine lange Zeit für motionEvent.action_down und einen anderen Lang für einen zweiten MotionEvent.action_down festlegen und die Zeit zwischen den beiden messen und dann etwas damit tun. Es fällt mir jedoch schwer herauszufinden, wie ich genau das annimmt. Ich benutze Switch Cases, um Multitouch -Ereignisse aufzunehmen. Ich würde es also lieber nicht versuchen, dies umzusetzen, um gestikeTector zu implementieren (und leider ist es unmöglich, sowohl OnTouchListener als auch gestikeTector gleichzeitig zu implementieren). Alle Ideen würden sehr helfen:

i.setOnTouchListener(new OnTouchListener() {

        public boolean onTouch(View v, MotionEvent event) {


                  ImageView i = (ImageView) v;

                  switch (event.getAction() & MotionEvent.ACTION_MASK) {


                  case MotionEvent.ACTION_DOWN:
                      long firstTouch = System.currentTimeMillis();
                     ///how to grab the second action_down????

                     break;
War es hilfreich?

Lösung

Ich habe dieses Problem früher angesprochen. Dabei wird ein Handler verwendet, um eine bestimmte Zeit zu warten, um auf den zweiten Klick zu warten: Wie kann ich ein einzelnes Klickereignis erstellen und auf das Ereignis doppelklicken, wenn die Menüschaltfläche gedrückt wird?

Andere Tipps

In Ihrer Klassendefinition:

public class main_activity extends Activity
{
    //variable for counting two successive up-down events
   int clickCount = 0;
    //variable for storing the time of first click
   long startTime;
    //variable for calculating the total time
   long duration;
    //constant for defining the time duration between the click that can be considered as double-tap
   static final int MAX_DURATION = 500;
}

Dann in Ihrem Klassenkörper:

OnTouchListener MyOnTouchListener = new OnTouchListener()
{
    @Override
    public boolean onTouch (View v, MotionEvent event)
    {
        switch(event.getAction() & MotionEvent.ACTION_MASK)
        {
        case MotionEvent.ACTION_DOWN:
            startTime = System.currentTimeMillis();
            clickCount++;
            break;
        case MotionEvent.ACTION_UP:
            long time = System.currentTimeMillis() - startTime;
            duration=  duration + time;
            if(clickCount == 2)
            {
                if(duration<= MAX_DURATION)
                {
                    Toast.makeText(captureActivity.this, "double tap",Toast.LENGTH_LONG).show();
                }
                clickCount = 0;
                duration = 0;
                break;             
            }
        }
    return true;    
    }
}

Dies wurde aus einer Antwort in: Doubletap in Android durch https://stackoverflow.com/users/1395802/karn

Mit der Helfer Class SimplegestaRelistener, die den Gesturelistener und OndoubletapListener implementiert, brauchen Sie nicht viel zu tun.

yourView.setOnTouchListener(new OnTouchListener() {
private GestureDetector gestureDetector = new GestureDetector(Test.this, new GestureDetector.SimpleOnGestureListener() {
    @Override
    public boolean onDoubleTap(MotionEvent e) {
        Log.d("TEST", "onDoubleTap");
        return super.onDoubleTap(e);
    }
    ... // implement here other callback methods like onFling, onScroll as necessary
});

@Override
public boolean onTouch(View v, MotionEvent event) {
    Log.d("TEST", "Raw event: " + event.getAction() + ", (" + event.getRawX() + ", " + event.getRawY() + ")");
    gestureDetector.onTouchEvent(event);
    return true;
}});

Das ist viel einfacher:

//variable for storing the time of first click
long startTime;
//constant for defining the time duration between the click that can be considered as double-tap
static final int MAX_DURATION = 200;

    if (event.getAction() == MotionEvent.ACTION_UP) {

        startTime = System.currentTimeMillis();             
    }
    else if (event.getAction() == MotionEvent.ACTION_DOWN) {

        if(System.currentTimeMillis() - startTime <= MAX_DURATION)
        {
            //DOUBLE TAP
        }       
    }

Hier ist meine Lösung.

Es war wichtig für mich, eine schnelle und klare Trennung von "Single Tap" und "Double Tap" zu haben. Ich habe es versucht GestureDetector Erstens hatte aber sehr schlechte Ergebnisse. Vielleicht ein Ergebnis meiner verschachtelten Verwendung von Scrollviews - wer weiß ...

Ich konzentriere mich auf MotionEvent.ACTION_UP und die ID des abgebildeten Elements. Um den ersten Hahn am Leben zu erhalten, benutze ich a Handler Senden einer verzögerten Nachricht (350 ms), damit der Benutzer einige Zeit hat, um seinen zweiten Tipp auf die zu platzieren ImageView. Wenn der Benutzer ein zweites Tippen auf ein Element mit der identischen ID platziert habe, nehme ich diese als doppelt tippen, entfernen Sie die verzögerte Nachricht und rennen Sie meinen benutzerdefinierten Code für "Double Tap". Wenn der Benutzer ein Element mit einer anderen ID ein Tipp platzierte, nehme ich dies als neuen Tippen und erstelle ein anderes Handler dafür.

Klasse Globale Variablen

private int tappedItemId = -1;
Handler myTapHandler;
final Context ctx = this;

Codebeispiel

ImageView iv = new ImageView(getApplicationContext());
//[...]
iv.setId(i*1000+n);
iv.setOnTouchListener(new View.OnTouchListener() {

@Override
public boolean onTouch(View v, MotionEvent event) {

   switch (event.getAction()) {

      case MotionEvent.ACTION_UP: {

         //active 'tap handler' for current id?
         if(myTapHandler != null && myTapHandler.hasMessages(v.getId())) {

            // clean up (to avoid single tap msg to be send and handled)
            myTapHandler.removeMessages(tappedItemId);
            tappedItemId = -1;

            //run 'double tap' custom code
            Toast.makeText(ScrollView.this, "double tap on "+v.getId(), Toast.LENGTH_SHORT).show();

            return true;
         } else {
            tappedItemId = v.getId();
            myTapHandler = new Handler(){
               public void handleMessage(Message msg){
                  Toast.makeText(ctx, "single tap on "+ tappedItemId + " msg 'what': " + msg.what, Toast.LENGTH_SHORT).show();
               }
            };

            Message msg = Message.obtain();
            msg.what = tappedItemId;
            msg.obj = new Runnable() {
               public void run() {
                  //clean up
                  tappedItemId = -1;
               }
            };
            myTouchHandler.sendMessageDelayed(msg, 350); //350ms delay (= time to tap twice on the same element)
         }
         break;
      }
   }

   return true;
 }
});
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top