Как обнаружить SingleTap в onInterceptTouchEvent (MotionEvent)?

Я хочу, чтобы ListView перехватывал все события, кроме SingleTap.

Сначала я сделал код ниже

  private float startX;
    private float startY;

    @Override
    public boolean onInterceptTouchEvent(MotionEvent event) {
         if (event.getAction() == MotionEvent.ACTION_DOWN ) {
             Log.d("intercept", "down");
            startX = event.getX();
            startY = event.getY();


        }
        if (event.getAction() == MotionEvent.ACTION_UP) {
             Log.d("intercept", "up");
            float deltaX = Math.abs(event.getX() - startX);
            float deltaY = Math.abs(event.getY() - startY);
            if(deltaX<5 && deltaY<5){

                return false;
            }

        }

       return super.onInterceptTouchEvent(event);
    }

Благодаря этому я смог увидеть, что я действительно обнаруживаю singleTap (intercept-down и intercep-up в LogCat), но он блокирует мой список для обработки других ходов. После этого я меняю return super.onInterceptTouchEvent(event); на return true и все остальные ходы работают. Проблема в том, что я больше не мог обнаружить singleTap. Я вижу, что intercept-down в Logcat, но не intercept-up. Я уже пробовал этот другой код без успеха.

import android.content.Context;
import android.support.v4.view.GestureDetectorCompat;
import android.util.AttributeSet;
import android.util.Log;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.widget.ListView;


public class SwipeListView extends ListView  {
    Context context;
    private GestureDetectorCompat mDetector;
    public SwipeListView(Context context) {
        super(context);
    }

    public SwipeListView(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public SwipeListView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }

    public void setContext(Context context){
        this.context= context;
        mDetector = new GestureDetectorCompat(context, new MyGestureListener());
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent event) {
        return !onTouchEvent(event);
    }
    @Override
    public boolean onTouchEvent(MotionEvent e) {
        return mDetector.onTouchEvent(e);
    }

    class MyGestureListener extends GestureDetector.SimpleOnGestureListener {
        private static final String DEBUG_TAG = "Gestures";

        @Override
        public boolean onDown(MotionEvent event) {
            Log.e(DEBUG_TAG,"onDown: " + event.toString());
            return true;
        }

        @Override
        public boolean onSingleTapConfirmed(MotionEvent event) {
            Log.e(DEBUG_TAG, "onSingleTap: " + event.toString());
            return true;
        }
    }
}

Кто-нибудь может помочь мне правильно определить singleTap?


person user3249186    schedule 04.02.2014    source источник
comment
stackoverflow.com/questions/13324250/   -  person Pararth    schedule 04.02.2014
comment
Я старался. Это не сработало. Фактически, оно блокирует все клики. Не могли бы вы снова посмотреть код и помочь мне найти, что я делаю неправильно? Я отредактировал и разместил весь класс.   -  person user3249186    schedule 04.02.2014
comment
Кажется, я понял, что происходит, но не знаю, как решить. MyGestureListener фиксирует только Down. Журнал показывает только последовательность даунов, но ни одного подтверждения одиночного касания.   -  person user3249186    schedule 04.02.2014
comment
вызовите mDetector.onTouchEvent в dispatchTouchEvent, обязательно вызовите super.dispatchTouchEvent   -  person pskink    schedule 04.02.2014
comment
Не работал. Если я вызову просто dispatchTouchEvent так, как вы сказали, работает только SingleTap, но список не перехватывает другие события   -  person user3249186    schedule 04.02.2014
comment
@user3249186 переопределить только dispatchTouchEvent, удалить другие методы   -  person pskink    schedule 04.02.2014
comment
Проблема в том, что мне нужно, чтобы onInterceptTouchEvent (событие MotionEvent) возвращало false только тогда, когда событие является SingleTap, но метод возвращает false, как только onDown возвращает true, и блокирует пользовательский интерфейс для кликов, потому что нет полного события для обработки.   -  person user3249186    schedule 04.02.2014
comment
@user3249186 user3249186 вы сказали, что хотите перехватывать все сенсорные события ListView: dispatchTouchEvent — это то место, которое вы ищете   -  person pskink    schedule 04.02.2014
comment
Я удалил и переопределил таким образом. @Override public boolean dispatchTouchEvent(MotionEvent ev) { this.mDetector.onTouchEvent(ev); вернуть super.dispatchTouchEvent(ev); }   -  person user3249186    schedule 04.02.2014
comment
@ user3249186 именно то, что я имел в виду   -  person pskink    schedule 04.02.2014
comment
@pskink Я не хочу их всех перехватывать. Я хочу, чтобы ребенок обрабатывал SingleTap. С помощью dispatchTouchEvent он позволяет дочернему элементу обрабатывать SingleTap, но не позволяет родителю обрабатывать пролистывание.   -  person user3249186    schedule 04.02.2014
comment
провести? какой свайп? Вы не упомянули о каких-либо ударах раньше. чего именно вы хотите добиться?   -  person pskink    schedule 04.02.2014
comment
Я работаю с библиотекой для реализации функции SwipeToDismiss. Я хочу запустить Intent, когда я тоже нажимаю на элемент списка. Но когда я устанавливаю OnClickListener для элементов списка, он потребляет событие, и я больше не могу прокручивать, чтобы закрыть.   -  person user3249186    schedule 04.02.2014


Ответы (1)


Между тем, попробуйте это с вашим кодом,
Пробовали ли вы: вернуть true из касания вниз/вверх с помощью:

public boolean onTouchEvent(MotionEvent e) {
    return gestureScanner.onTouchEvent(e);
}

public boolean onSingleTapConfirmed(MotionEvent e) { 

   //this works for me

    return true; 
}

public boolean onDown(MotionEvent e) { return true; }


public void onLongPress(MotionEvent e) {
    //

}
person Pararth    schedule 04.02.2014
comment
Я редактирую код с помощью этой попытки. Кажется, я знаю, в чем проблема. Похоже, что это обрабатывается с помощью Down, как будто это полное MotionEvent. Он не ждет, пока SingleTap завершится, чтобы вернуть true. - person user3249186; 04.02.2014