Обнаружение жестов на фрагменте

У меня есть Activity, который содержит один Fragment:

getFragmentManager().beginTransaction().add(android.R.id.content, fragment1).commit();

Мой вопрос в том, как я могу обнаружить жесты? Пробовал методом OnTouchListener, а также методом onInterceptTouchEvent. В основном я хочу обнаружить удары. Мой SwipeGestureDetector выглядит так:

public class SwipeGestureDetector extends SimpleOnGestureListener {

    // ...

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

    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
        try {
            if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) return false;

            if (e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
                // right to left swipe

            } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
                // left to right swipe

            }
        } catch (Exception e) {
            // nothing
        }
        return false;
    }
}

Затем я регистрирую его в своем Activity:

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        // ..

        SwipeGestureDetector swipeDetector = new SwipeGestureDetector();
        final GestureDetector detector = new GestureDetector(this, swipeDetector);
        findViewById(android.R.id.content).setOnTouchListener(new OnTouchListener() {

            @Override
            public boolean onTouch(View v, MotionEvent event) {
                return detector.onTouchEvent(event);
            }
        });
    }

К сожалению, жест смахивания не обнаружен. Как я могу достичь этого? Пожалуйста, не предлагайте использовать ViewPager, я не могу его использовать.


person WonderCsabo    schedule 16.11.2013    source источник
comment
Было ли это когда-либо решено?   -  person shanehoban    schedule 30.04.2014
comment
@WonderCsabo я использую его вот так ....... но он не работает .... пожалуйста, посмотрите ...... pastebin.com/n9JPGrCn   -  person Animesh Mangla    schedule 31.12.2015


Ответы (3)


Вот обходной путь, который я сделал для этой проблемы.

Мне пришлось переопределить метод dispatchTouchEvent() в моем файле Activity. Это вызывается, когда в окне происходит событие касания.

@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
    boolean handled = swipeDetector.onTouchEvent(ev);
    if (!handled) {
        return super.dispatchTouchEvent(ev);
    }

    return handled;
}
person WonderCsabo    schedule 30.04.2014

Ответ WonderCsabo не совсем сработал для меня. Проблема, с которой я столкнулся с этим кодом, заключалась в том, что внутри моей деятельности у меня был пейджер представления и фрагмент с несколькими кликабельными представлениями внутри него. Ни один из обработчиков кликов или свайпов не вызывался с этим кодом, поэтому он сломал мои вещи. Видимо обращались правда слишком часто. поэтому if (!handled) заблокировал пейджер и фрагмент от получения событий касания.

Итак, я попытался просто убрать оператор if, и теперь он, кажется, работает. Вот класс активности. У него есть просмотр пейджера и фрагмент

public class MyActivity extends Activity  {

private SectionsPagerAdapter sectionsPagerAdapter;
private ViewPager viewPager;
ArrayList<Class> tabsFragmentClasses = new ArrayList<Class>();
private GestureDetector gestureDetector;

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.ride_detail_activity);

    viewPager = (ViewPager) findViewById(R.id.pager);

    if (savedInstanceState == null) {
        getFragmentManager().beginTransaction()
                .add(R.id.container, new MyFragment(),"MyFragment")
                .commit();
    }

    gestureDetector = new GestureDetector(this,gestureListener);
}

GestureDetector.SimpleOnGestureListener gestureListener = new GestureDetector.SimpleOnGestureListener(){
    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
        final int SWIPE_MIN_DISTANCE = 120;
        final int SWIPE_MAX_OFF_PATH = 250;
        final int SWIPE_THRESHOLD_VELOCITY = 200;
        try {
            if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH)
                return false;
            if (e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE
                    && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
                Log.i("Tag", "Right to Left");
            } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE
                    && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
                Log.i("Tag", "Left to Right");
            }
        } catch (Exception e) {
            // nothing
        }
        return false;
    }

    @Override
    public boolean onDown(MotionEvent event) {
        return true;
    }
};

Теперь, если я закончу это, как описано в Документы по обнаружению общих жестов Android, я добавлю это код.

@Override 
public boolean onTouchEvent(MotionEvent event){ 
    gestureDetector.onTouchEvent(event);
    return super.onTouchEvent(event);
}

Проблема в том, что детектор жестов работает только там, где нет сенсорных представлений, таких как мой пейджер и кнопки. Вместо этого используйте этот код

@Override
public boolean dispatchTouchEvent(MotionEvent event){
    this.gestureDetector.onTouchEvent(event);
    return super.dispatchTouchEvent(event);
}

Затем происходит то, что представления во фрагменте и пейджер представления получают все события касания, как обычно, но я также получаю события жестов в своем слушателе.

person Marc    schedule 13.01.2015

Я только что переопределил метод GestureListener#onDown(), чтобы вернуть true

person theroom101    schedule 16.06.2020