studio simpleongesturelistener recognition android swipe gesture-recognition

android - recognition - gesturedetector simpleongesturelistener



Android: Cómo manejar gestos de barrido de derecha a izquierda (19)

Ampliando la respuesta de Mirek, para el caso en el que desea utilizar los gestos de deslizamiento dentro de una vista de desplazamiento. De forma predeterminada, la escucha táctil para la vista de desplazamiento se deshabilita y, por lo tanto, la acción de desplazamiento no ocurre. Para solucionar esto, debe anular el método dispatchTouchEvent de la Activity y devolver la versión heredada de este método una vez que haya terminado con su propio oyente.

Para hacer algunas modificaciones al código de Mirek: agrego un getter para el gestureDetector de gestureDetector en OnSwipeTouchListener .

public GestureDetector getGestureDetector(){ return gestureDetector; }

Declare el OnSwipeTouchListener dentro de la Actividad como un campo de toda la clase.

OnSwipeTouchListener onSwipeTouchListener;

Modificar el código de uso en consecuencia:

onSwipeTouchListener = new OnSwipeTouchListener(MyActivity.this) { public void onSwipeTop() { Toast.makeText(MyActivity.this, "top", Toast.LENGTH_SHORT).show(); } public void onSwipeRight() { Toast.makeText(MyActivity.this, "right", Toast.LENGTH_SHORT).show(); } public void onSwipeLeft() { Toast.makeText(MyActivity.this, "left", Toast.LENGTH_SHORT).show(); } public void onSwipeBottom() { Toast.makeText(MyActivity.this, "bottom", Toast.LENGTH_SHORT).show(); } }); imageView.setOnTouchListener(onSwipeTouchListener);

Y anule el método dispatchTouchEvent dentro de la Activity :

@Override public boolean dispatchTouchEvent(MotionEvent ev){ swipeListener.getGestureDetector().onTouchEvent(ev); return super.dispatchTouchEvent(ev); }

Ahora tanto las acciones de desplazamiento como de deslizamiento deberían funcionar.

Quiero que mi aplicación reconozca cuando un usuario pasa de derecha a izquierda en la pantalla del teléfono.

¿Como hacer esto?


El último impl solo funciona con esto:

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


El uso de la respuesta de Edward Brey en Kotlin.

view.setOnTouchListener(object: OnSwipeTouchListener(this) { override fun onSwipeLeft() { super.onSwipeLeft() } override fun onSwipeRight() { super.onSwipeRight() } } )


Este código detecta deslizamientos a la izquierda y a la derecha, evita las llamadas a la API en desuso y tiene otras mejoras varias sobre las respuestas anteriores.

/** * Detects left and right swipes across a view. */ public class OnSwipeTouchListener implements OnTouchListener { private final GestureDetector gestureDetector; public OnSwipeTouchListener(Context context) { gestureDetector = new GestureDetector(context, new GestureListener()); } public void onSwipeLeft() { } public void onSwipeRight() { } public boolean onTouch(View v, MotionEvent event) { return gestureDetector.onTouchEvent(event); } private final class GestureListener extends SimpleOnGestureListener { private static final int SWIPE_DISTANCE_THRESHOLD = 100; private static final int SWIPE_VELOCITY_THRESHOLD = 100; @Override public boolean onDown(MotionEvent e) { return true; } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { float distanceX = e2.getX() - e1.getX(); float distanceY = e2.getY() - e1.getY(); if (Math.abs(distanceX) > Math.abs(distanceY) && Math.abs(distanceX) > SWIPE_DISTANCE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (distanceX > 0) onSwipeRight(); else onSwipeLeft(); return true; } return false; } } }

Úsalo así:

view.setOnTouchListener(new OnSwipeTouchListener(context) { @Override public void onSwipeLeft() { // Whatever } });


La respuesta de @Mirek Rusin es muy buena. Pero, hay un pequeño error, y la reparación se requiere -

public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { boolean result = false; try { float diffY = e2.getY() - e1.getY(); float diffX = e2.getX() - e1.getX(); if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { if (getOnSwipeListener() != null) { getOnSwipeListener().onSwipeRight(); } } else { if (getOnSwipeListener() != null) { getOnSwipeListener().onSwipeLeft(); } } result = true; } } else if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { if (getOnSwipeListener() != null) { getOnSwipeListener().onSwipeBottom(); } } else { if (getOnSwipeListener() != null) { getOnSwipeListener().onSwipeTop(); } } result = true; }

¿Cuál es la diferencia? Establecemos resultado = verdadero, solo si hemos verificado que todos los requisitos (tanto SWIPE_THRESHOLD como SWIPE_VELOCITY_THRESHOLD están bien). Esto es importante si descartamos el barrido si no se cumplen algunos de los requisitos, y tenemos que hacer algo en el método OnTouchEvent de OnSwipeTouchListener.


Mi solución es similar a las anteriores, pero he resumido el manejo de gestos en una clase abstracta OnGestureRegisterListener.java , que incluye gestos de deslizar , hacer clic y hacer clic largo .

OnGestureRegisterListener.java

public abstract class OnGestureRegisterListener implements View.OnTouchListener { private final GestureDetector gestureDetector; private View view; public OnGestureRegisterListener(Context context) { gestureDetector = new GestureDetector(context, new GestureListener()); } @Override public boolean onTouch(View view, MotionEvent event) { this.view = view; return gestureDetector.onTouchEvent(event); } public abstract void onSwipeRight(View view); public abstract void onSwipeLeft(View view); public abstract void onSwipeBottom(View view); public abstract void onSwipeTop(View view); public abstract void onClick(View view); public abstract boolean onLongClick(View view); private final class GestureListener extends GestureDetector.SimpleOnGestureListener { private static final int SWIPE_THRESHOLD = 100; private static final int SWIPE_VELOCITY_THRESHOLD = 100; @Override public boolean onDown(MotionEvent e) { return true; } @Override public void onLongPress(MotionEvent e) { onLongClick(view); super.onLongPress(e); } @Override public boolean onSingleTapUp(MotionEvent e) { onClick(view); return super.onSingleTapUp(e); } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { boolean result = false; try { float diffY = e2.getY() - e1.getY(); float diffX = e2.getX() - e1.getX(); if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { onSwipeRight(view); } else { onSwipeLeft(view); } result = true; } } else if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { onSwipeBottom(view); } else { onSwipeTop(view); } result = true; } } catch (Exception exception) { exception.printStackTrace(); } return result; } } }

Y utilízalo así. Tenga en cuenta que también puede pasar fácilmente en su parámetro View .

OnGestureRegisterListener onGestureRegisterListener = new OnGestureRegisterListener(this) { public void onSwipeRight(View view) { // Do something } public void onSwipeLeft(View view) { // Do something } public void onSwipeBottom(View view) { // Do something } public void onSwipeTop(View view) { // Do something } public void onClick(View view) { // Do something } public boolean onLongClick(View view) { // Do something return true; } }; Button button = findViewById(R.id.my_button); button.setOnTouchListener(onGestureRegisterListener);


Necesita algunas actualizaciones menores. Las variables no coinciden en el método onTouch y la clase de excepción no se importa. Tendría más sentido simplemente devolver falso desde onFling (), en lugar de iniciar una variable, asignarle un valor, no hacer nada con él y simplemente devolverlo.

Algunas partes del método onTouch son incorrectas. Ver view / motionEvent no se puede resolver con un deslizamiento variable

Un consejo útil que me habría ahorrado algo de tiempo y espero que pueda ayudar a otros: cuando use este método, solo desea agregar la etiqueta "implementos" a su clase OnSwipeTouchListener. Tu Actividad y Vista no lo están implementando. ¡Solo están aprovechando tu clase que ya lo hace!

+1 para Mirek porque su código todavía me dio lo que necesitaba para el mío :)


No necesitas esos complicados cálculos. simplemente usando GestureDetector en su OnGestureListener dentro de onFling :

MyGestureListener.java :

import android.util.Log; import android.view.GestureDetector; import android.view.MotionEvent; public class MyGestureListener implements GestureDetector.OnGestureListener{ private static final long VELOCITY_THRESHOLD = 3000; @Override public boolean onDown(final MotionEvent e){ return false; } @Override public void onShowPress(final MotionEvent e){ } @Override public boolean onSingleTapUp(final MotionEvent e){ return false; } @Override public boolean onScroll(final MotionEvent e1, final MotionEvent e2, final float distanceX, final float distanceY){ return false; } @Override public void onLongPress(final MotionEvent e){ } @Override public boolean onFling(final MotionEvent e1, final MotionEvent e2, final float velocityX, final float velocityY){ if(Math.abs(velocityX) < VELOCITY_THRESHOLD && Math.abs(velocityY) < VELOCITY_THRESHOLD){ return false;//if the fling is not fast enough then it''s just like drag } //if velocity in X direction is higher than velocity in Y direction, //then the fling is horizontal, else->vertical if(Math.abs(velocityX) > Math.abs(velocityY)){ if(velocityX >= 0){ Log.i("TAG", "swipe right"); }else{//if velocityX is negative, then it''s towards left Log.i("TAG", "swipe left"); } }else{ if(velocityY >= 0){ Log.i("TAG", "swipe down"); }else{ Log.i("TAG", "swipe up"); } } return true; } }

uso:

GestureDetector mDetector = new GestureDetector(MainActivity.this, new MyGestureListener()); view.setOnTouchListener(new View.OnTouchListener(){ @Override public boolean onTouch(final View v, final MotionEvent event){ return mDetector.onTouchEvent(event); } });


Para agregar un onClick también, esto es lo que hice.

.... // in OnSwipeTouchListener class private final class GestureListener extends SimpleOnGestureListener { .... // normal GestureListener code @Override public boolean onSingleTapConfirmed(MotionEvent e) { onClick(); // my method return super.onSingleTapConfirmed(e); } } // end GestureListener class public void onSwipeRight() { } public void onSwipeLeft() { } public void onSwipeTop() { } public void onSwipeBottom() { } public void onClick(){ } // as normal @Override public boolean onTouch(View v, MotionEvent event) { return gestureDetector.onTouchEvent(event); } } // end OnSwipeTouchListener class

Estoy usando Fragmentos, así que uso getActivity () para el contexto. Así es como lo implementé, y funciona.

myLayout.setOnTouchListener(new OnSwipeTouchListener(getActivity()) { public void onSwipeTop() { Toast.makeText(getActivity(), "top", Toast.LENGTH_SHORT).show(); } public void onSwipeRight() { Toast.makeText(getActivity(), "right", Toast.LENGTH_SHORT).show(); } public void onSwipeLeft() { Toast.makeText(getActivity(), "left", Toast.LENGTH_SHORT).show(); } public void onSwipeBottom() { Toast.makeText(getActivity(), "bottom", Toast.LENGTH_SHORT).show(); } public void onClick(){ Toast.makeText(getActivity(), "clicked", Toast.LENGTH_SHORT).show(); } });


Para tener Click Listener , DoubleClick Listener , OnLongPress Listener , Swipe Left , Swipe Right , Swipe Up , Swipe Down en Single View , debe setOnTouchListener . es decir,

view.setOnTouchListener(new OnSwipeTouchListener(MainActivity.this) { @Override public void onClick() { super.onClick(); // your on click here } @Override public void onDoubleClick() { super.onDoubleClick(); // your on onDoubleClick here } @Override public void onLongClick() { super.onLongClick(); // your on onLongClick here } @Override public void onSwipeUp() { super.onSwipeUp(); // your swipe up here } @Override public void onSwipeDown() { super.onSwipeDown(); // your swipe down here. } @Override public void onSwipeLeft() { super.onSwipeLeft(); // your swipe left here. } @Override public void onSwipeRight() { super.onSwipeRight(); // your swipe right here. } }); }

Para esto necesita la clase OnSwipeTouchListener que implementa OnTouchListener .

public class OnSwipeTouchListener implements View.OnTouchListener { private GestureDetector gestureDetector; public OnSwipeTouchListener(Context c) { gestureDetector = new GestureDetector(c, new GestureListener()); } public boolean onTouch(final View view, final MotionEvent motionEvent) { return gestureDetector.onTouchEvent(motionEvent); } private final class GestureListener extends GestureDetector.SimpleOnGestureListener { private static final int SWIPE_THRESHOLD = 100; private static final int SWIPE_VELOCITY_THRESHOLD = 100; @Override public boolean onDown(MotionEvent e) { return true; } @Override public boolean onSingleTapUp(MotionEvent e) { onClick(); return super.onSingleTapUp(e); } @Override public boolean onDoubleTap(MotionEvent e) { onDoubleClick(); return super.onDoubleTap(e); } @Override public void onLongPress(MotionEvent e) { onLongClick(); super.onLongPress(e); } // Determines the fling velocity and then fires the appropriate swipe event accordingly @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { boolean result = false; try { float diffY = e2.getY() - e1.getY(); float diffX = e2.getX() - e1.getX(); if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { onSwipeRight(); } else { onSwipeLeft(); } } } else { if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { onSwipeDown(); } else { onSwipeUp(); } } } } catch (Exception exception) { exception.printStackTrace(); } return result; } } public void onSwipeRight() { } public void onSwipeLeft() { } public void onSwipeUp() { } public void onSwipeDown() { } public void onClick() { } public void onDoubleClick() { } public void onLongClick() { } }


Si desea mostrar algunos botones con acciones cuando se desliza un elemento de la lista, hay muchas bibliotecas en Internet que tienen este comportamiento. Implementé la biblioteca que encontré en internet y estoy muy satisfecho. Es muy simple de usar y muy rápido. Mejoré la biblioteca original y agregué un nuevo detector de clics para el clic del elemento. También agregué una biblioteca impresionante de fuentes ( http://fortawesome.github.io/Font-Awesome/ ) y ahora puedes simplemente agregar un nuevo título de elemento y especificar el nombre del icono de fuente impresionante.

Here está el enlace github


Si también necesitas procesar eventos de click aquí algunas modificaciones:

public class OnSwipeTouchListener implements OnTouchListener { private final GestureDetector gestureDetector = new GestureDetector(new GestureListener()); public boolean onTouch(final View v, final MotionEvent event) { return gestureDetector.onTouchEvent(event); } private final class GestureListener extends SimpleOnGestureListener { private static final int SWIPE_THRESHOLD = 100; private static final int SWIPE_VELOCITY_THRESHOLD = 100; @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { boolean result = false; try { float diffY = e2.getY() - e1.getY(); float diffX = e2.getX() - e1.getX(); if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { result = onSwipeRight(); } else { result = onSwipeLeft(); } } } else { if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { result = onSwipeBottom(); } else { result = onSwipeTop(); } } } } catch (Exception exception) { exception.printStackTrace(); } return result; } } public boolean onSwipeRight() { return false; } public boolean onSwipeLeft() { return false; } public boolean onSwipeTop() { return false; } public boolean onSwipeBottom() { return false; } }

Y muestra de uso:

background.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View arg0) { toggleSomething(); } }); background.setOnTouchListener(new OnSwipeTouchListener() { public boolean onSwipeTop() { Toast.makeText(MainActivity.this, "top", Toast.LENGTH_SHORT).show(); return true; } public boolean onSwipeRight() { Toast.makeText(MainActivity.this, "right", Toast.LENGTH_SHORT).show(); return true; } public boolean onSwipeLeft() { Toast.makeText(MainActivity.this, "left", Toast.LENGTH_SHORT).show(); return true; } public boolean onSwipeBottom() { Toast.makeText(MainActivity.this, "bottom", Toast.LENGTH_SHORT).show(); return true; } });


Una pequeña modificación de la respuesta de @Mirek Rusin y ahora puedes detectar los toques multitáctiles. Este código está en Kotlin:

class OnSwipeTouchListener(ctx: Context, val onGesture: (gestureCode: Int) -> Unit) : OnTouchListener { private val SWIPE_THRESHOLD = 200 private val SWIPE_VELOCITY_THRESHOLD = 200 private val gestureDetector: GestureDetector var fingersCount = 0 fun resetFingers() { fingersCount = 0 } init { gestureDetector = GestureDetector(ctx, GestureListener()) } override fun onTouch(v: View, event: MotionEvent): Boolean { if (event.pointerCount > fingersCount) { fingersCount = event.pointerCount } return gestureDetector.onTouchEvent(event) } private inner class GestureListener : SimpleOnGestureListener() { override fun onDown(e: MotionEvent): Boolean { return true } override fun onFling(e1: MotionEvent, e2: MotionEvent, velocityX: Float, velocityY: Float): Boolean { var result = false try { val diffY = e2.y - e1.y val diffX = e2.x - e1.x if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { val gesture = when (fingersCount) { 1 -> Gesture.SWIPE_RIGHT 2 -> Gesture.TWO_FINGER_SWIPE_RIGHT 3 -> Gesture.THREE_FINGER_SWIPE_RIGHT else -> -1 } if (gesture > 0) { onGesture.invoke(gesture) } } else { val gesture = when (fingersCount) { 1 -> Gesture.SWIPE_LEFT 2 -> Gesture.TWO_FINGER_SWIPE_LEFT 3 -> Gesture.THREE_FINGER_SWIPE_LEFT else -> -1 } if (gesture > 0) { onGesture.invoke(gesture) } } resetFingers() } } else if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { val gesture = when (fingersCount) { 1 -> Gesture.SWIPE_DOWN 2 -> Gesture.TWO_FINGER_SWIPE_DOWN 3 -> Gesture.THREE_FINGER_SWIPE_DOWN else -> -1 } if (gesture > 0) { onGesture.invoke(gesture) } } else { val gesture = when (fingersCount) { 1 -> Gesture.SWIPE_UP 2 -> Gesture.TWO_FINGER_SWIPE_UP 3 -> Gesture.THREE_FINGER_SWIPE_UP else -> -1 } if (gesture > 0) { onGesture.invoke(gesture) } } resetFingers() } result = true } catch (exception: Exception) { exception.printStackTrace() } return result } }}

Donde Gesture.SWIPE_RIGHT y otros son identificadores enteros únicos del gesto que estoy usando para detectar una especie de gesto más adelante en mi actividad:

rootView?.setOnTouchListener(OnSwipeTouchListener(this, { gesture -> log(Gesture.parseName(this, gesture)) }))

Entonces, ver el gesto aquí es una variable entera que contiene el valor que he pasado antes.


Usa SwipeListView y deja que controle la detección de gestos por ti.


OnSwipeTouchListener.java :

import android.content.Context; import android.view.GestureDetector; import android.view.GestureDetector.SimpleOnGestureListener; import android.view.MotionEvent; import android.view.View; import android.view.View.OnTouchListener; public class OnSwipeTouchListener implements OnTouchListener { private final GestureDetector gestureDetector; public OnSwipeTouchListener (Context ctx){ gestureDetector = new GestureDetector(ctx, new GestureListener()); } @Override public boolean onTouch(View v, MotionEvent event) { return gestureDetector.onTouchEvent(event); } private final class GestureListener extends SimpleOnGestureListener { private static final int SWIPE_THRESHOLD = 100; private static final int SWIPE_VELOCITY_THRESHOLD = 100; @Override public boolean onDown(MotionEvent e) { return true; } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { boolean result = false; try { float diffY = e2.getY() - e1.getY(); float diffX = e2.getX() - e1.getX(); if (Math.abs(diffX) > Math.abs(diffY)) { if (Math.abs(diffX) > SWIPE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (diffX > 0) { onSwipeRight(); } else { onSwipeLeft(); } result = true; } } else if (Math.abs(diffY) > SWIPE_THRESHOLD && Math.abs(velocityY) > SWIPE_VELOCITY_THRESHOLD) { if (diffY > 0) { onSwipeBottom(); } else { onSwipeTop(); } result = true; } } catch (Exception exception) { exception.printStackTrace(); } return result; } } public void onSwipeRight() { } public void onSwipeLeft() { } public void onSwipeTop() { } public void onSwipeBottom() { } }

Uso:

imageView.setOnTouchListener(new OnSwipeTouchListener(MyActivity.this) { public void onSwipeTop() { Toast.makeText(MyActivity.this, "top", Toast.LENGTH_SHORT).show(); } public void onSwipeRight() { Toast.makeText(MyActivity.this, "right", Toast.LENGTH_SHORT).show(); } public void onSwipeLeft() { Toast.makeText(MyActivity.this, "left", Toast.LENGTH_SHORT).show(); } public void onSwipeBottom() { Toast.makeText(MyActivity.this, "bottom", Toast.LENGTH_SHORT).show(); } });


Aquí está el código de Android simple para detectar la dirección del gesto

En MainActivity.java y activity_main.xml , escriba el siguiente código:

MainActivity.java

import java.util.ArrayList; import android.app.Activity; import android.gesture.Gesture; import android.gesture.GestureLibraries; import android.gesture.GestureLibrary; import android.gesture.GestureOverlayView; import android.gesture.GestureOverlayView.OnGesturePerformedListener; import android.gesture.GestureStroke; import android.gesture.Prediction; import android.os.Bundle; import android.widget.Toast; public class MainActivity extends Activity implements OnGesturePerformedListener { GestureOverlayView gesture; GestureLibrary lib; ArrayList<Prediction> prediction; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); lib = GestureLibraries.fromRawResource(MainActivity.this, R.id.gestureOverlayView1); gesture = (GestureOverlayView) findViewById(R.id.gestureOverlayView1); gesture.addOnGesturePerformedListener(this); } @Override public void onGesturePerformed(GestureOverlayView overlay, Gesture gesture) { ArrayList<GestureStroke> strokeList = gesture.getStrokes(); // prediction = lib.recognize(gesture); float f[] = strokeList.get(0).points; String str = ""; if (f[0] < f[f.length - 2]) { str = "Right gesture"; } else if (f[0] > f[f.length - 2]) { str = "Left gesture"; } else { str = "no direction"; } Toast.makeText(getApplicationContext(), str, Toast.LENGTH_LONG).show(); } }

activity_main.xml

<android.gesture.GestureOverlayView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" xmlns:android1="http://schemas.android.com/apk/res/android" xmlns:android2="http://schemas.android.com/apk/res/android" android:id="@+id/gestureOverlayView1" android:layout_width="match_parent" android:layout_height="match_parent" android1:orientation="vertical" > <TextView android:id="@+id/textView1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Draw gesture" android:textAppearance="?android:attr/textAppearanceMedium" /> </android.gesture.GestureOverlayView>


El método de @Edward Brey funciona muy bien. Si a alguien también le gustaría copiar y pegar las importaciones para el OnSwipeTouchListener , aquí están:

import android.content.Context; import android.view.GestureDetector; import android.view.GestureDetector.SimpleOnGestureListener; import android.view.MotionEvent; import android.view.View; import android.view.View.OnTouchListener;


import android.content.Context import android.view.GestureDetector import android.view.GestureDetector.SimpleOnGestureListener import android.view.MotionEvent import android.view.View import android.view.View.OnTouchListener /** * Detects left and right swipes across a view. */ class OnSwipeTouchListener(context: Context, onSwipeCallBack: OnSwipeCallBack?) : OnTouchListener { private var gestureDetector : GestureDetector private var onSwipeCallBack: OnSwipeCallBack?=null init { gestureDetector = GestureDetector(context, GestureListener()) this.onSwipeCallBack = onSwipeCallBack!! } companion object { private val SWIPE_DISTANCE_THRESHOLD = 100 private val SWIPE_VELOCITY_THRESHOLD = 100 } /* fun onSwipeLeft() {} fun onSwipeRight() {}*/ override fun onTouch(v: View, event: MotionEvent): Boolean { return gestureDetector.onTouchEvent(event) } private inner class GestureListener : SimpleOnGestureListener() { override fun onDown(e: MotionEvent): Boolean { return true } override fun onFling(eve1: MotionEvent?, eve2: MotionEvent?, velocityX: Float, velocityY: Float): Boolean { try { if(eve1 != null&& eve2!= null) { val distanceX = eve2?.x - eve1?.x val distanceY = eve2?.y - eve1?.y if (Math.abs(distanceX) > Math.abs(distanceY) && Math.abs(distanceX) > SWIPE_DISTANCE_THRESHOLD && Math.abs(velocityX) > SWIPE_VELOCITY_THRESHOLD) { if (distanceX > 0) onSwipeCallBack!!.onSwipeLeftCallback() else onSwipeCallBack!!.onSwipeRightCallback() return true } } }catch (exception:Exception){ exception.printStackTrace() } return false } } }


public class TranslatorSwipeTouch implements OnTouchListener { private String TAG="TranslatorSwipeTouch"; @SuppressWarnings("deprecation") private GestureDetector detector=new GestureDetector(new TranslatorGestureListener()); @Override public boolean onTouch(View view, MotionEvent event) { return detector.onTouchEvent(event); } private class TranslatorGestureListener extends SimpleOnGestureListener { private final int GESTURE_THRESHOULD=100; private final int GESTURE_VELOCITY_THRESHOULD=100; @Override public boolean onDown(MotionEvent e) { return true; } @Override public boolean onFling(MotionEvent event1,MotionEvent event2,float velocityx,float velocityy) { try { float diffx=event2.getX()-event1.getX(); float diffy=event2.getY()-event1.getY(); if(Math.abs(diffx)>Math.abs(diffy)) { if(Math.abs(diffx)>GESTURE_THRESHOULD && Math.abs(velocityx)>GESTURE_VELOCITY_THRESHOULD) { if(diffx>0) { onSwipeRight(); } else { onSwipeLeft(); } } } else { if(Math.abs(diffy)>GESTURE_THRESHOULD && Math.abs(velocityy)>GESTURE_VELOCITY_THRESHOULD) { if(diffy>0) { onSwipeBottom(); } else { onSwipeTop(); } } } } catch(Exception e) { Log.d(TAG, ""+e.getMessage()); } return false; } public void onSwipeRight() { //Toast.makeText(this.getClass().get, "swipe right", Toast.LENGTH_SHORT).show(); Log.i(TAG, "Right"); } public void onSwipeLeft() { Log.i(TAG, "Left"); //Toast.makeText(MyActivity.this, "swipe left", Toast.LENGTH_SHORT).show(); } public void onSwipeTop() { Log.i(TAG, "Top"); //Toast.makeText(MyActivity.this, "swipe top", Toast.LENGTH_SHORT).show(); } public void onSwipeBottom() { Log.i(TAG, "Bottom"); //Toast.makeText(MyActivity.this, "swipe bottom", Toast.LENGTH_SHORT).show(); } } }