2012-06-30 16 views
7

Me gustaría que mi GestureOverlayView detecte gestos tanto horizontales como verticales.Gestos verticales y horizontales en Android

De http://android-developers.blogspot.com/2009/10/gestures-on-android-16.html

"orientación: indica la orientación de desplazamiento de los puntos de vista por debajo en este caso la lista se desplaza verticalmente, lo que significa que cualquier gestos horizontales (como action_delete) inmediatamente pueden ser reconocidos como un gesto.. Los gestos que comienzan con un trazo vertical deben contener al menos un componente horizontal para ser reconocido. En otras palabras, una simple línea vertical no puede reconocerse como un gesto ya que entraría en conflicto con el desplazamiento de la lista ".

parece una trampa-22, si el androide: la orientación se establece en vertical, sólo puedo tener golpes horizontales, y si el androide: la orientación se establece en horizontal, sólo puedo tener golpes verticales. ¿Cómo puedo evitar este requisito?

+2

¿Alguna vez encontró una solución para esto? – capcom

+0

No, todavía no hay ninguna solución para Android ... – Bashevis

+0

Vaya, ¿cómo hago lo que necesito? Realmente necesito hacer esto. Este tutorial se muestra arriba y abajo en Gestures Builder http://www.vogella.com/articles/AndroidGestures/article.html, aunque no se utiliza. Aquí está mi propia pregunta, si quieres echar un vistazo, http://stackoverflow.com/questions/14246998/detecting-vertical-gestures. No tiene sentido que no haya forma de hacerlo, otras aplicaciones usan este tipo de funcionalidad todo el tiempo. – capcom

Respuesta

5

Me encontré con este problema en un hackathon. No hay forma de que puedas resolverlo con GestureOverlayView, por lo que debes usar eventos de movimiento. Sin embargo, GestureOverlayView funciona con gestos ligeramente más "detallados", como un círculo. Lo que noté es que GestureOverlayView funciona mejor para figuras cerradas. Entonces, el sensor de movimientoEvent es. Encontré el código here. Modifiqué la respuesta de Gav para los golpes verticales también. No lo han probado, pero es positivo que funcione.

He aquí un ejemplo:

public class SelectFilterActivity extends Activity implements OnClickListener 
{ 

private static final int SWIPE_MIN_DISTANCE = 120; 
private static final int SWIPE_MAX_OFF_PATH = 250; 
private static final int SWIPE_THRESHOLD_VELOCITY = 200; 
private GestureDetector gestureDetector; 
View.OnTouchListener gestureListener; 

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

    /* ... */ 

    // Gesture detection 
    gestureDetector = new GestureDetector(new MyGestureDetector()); 
    gestureListener = new View.OnTouchListener() { 
     public boolean onTouch(View v, MotionEvent event) { 
      return gestureDetector.onTouchEvent(event); 
     } 
    }; 

} 

class MyGestureDetector extends SimpleOnGestureListener { 
    @Override 
    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { 
     try { 
      // downward swipe 
      if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH && Math.abs(velocityY) > SWIPE_THRESHOLD_VELOCITY) 
       Toast.makeText(SelectFilterActivity.this, "Downward Swipe", Toast.LENGTH_SHORT).show(); 
else if (Math.abs(e2.getY() - e1.getY()) > SWIPE_MAX_OFF_PATH && Math.abs(velocityY) > SWIPE_THRESHOLD_VELOCITY) 
       Toast.makeText(SelectFilterActivity.this, "Upward Swipe", Toast.LENGTH_SHORT).show(); 
      // right to left swipe 
      else if(e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
       Toast.makeText(SelectFilterActivity.this, "Left Swipe", Toast.LENGTH_SHORT).show(); 
      } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
       Toast.makeText(SelectFilterActivity.this, "Right Swipe", Toast.LENGTH_SHORT).show(); 
      } 
     } catch (Exception e) { 
      // nothing 
     } 
     return false; 
    } 

} 

Ahora añadirlo a las vistas en las que desee detección de las posturas,

// Do this for each view added to the grid 
    imageView.setOnClickListener(SelectFilterActivity.this); 
    imageView.setOnTouchListener(gestureListener); 

Saludos a Gav para el código!

+0

Ya he hecho esto en mi código, pero gracias por su respuesta. Lo que pasa es que quiero todos los gestos puramente verticales y horizontales, junto con todo lo que diseño desde gestureoverlayview. Claro, puedes hackear con motionevents para detectar un círculo y tal, pero es un verdadero dolor. No veo por qué esto es tan difícil de hacer en Android. De todos modos, +1 para una buena respuesta. Creo que terminaré quedándome con GestureDetector por ahora, e implementando algunos de mis propios gestos de multifunción para agregar funcionalidad extra en cuanto a gestos. – capcom

+0

También tenga en cuenta que cuando ofrecí la recompensa, mencioné específicamente que la respuesta no debe incluir GestureDetector. Pero muchas gracias, no obstante. – capcom

+0

@capcom En cualquier momento, pero avíseme si puede hacer funcionar gestureOverlayView. Intenté mucho, tuve que hacer gestos más complejos, los golpes simples no parecen funcionar. –

0
Tal vez no

la mejor manera de hacerlo, pero se puede reemplazar el comportamiento predeterminado mediante la extensión de GestureOverlayView

Se necesitaría para reemplazar el método private Rect touchMove(MotionEvent event) y deshacerse de la verificación de la orientación:

if (box.squareness > mGestureStrokeSquarenessTreshold || 
    (mOrientation == ORIENTATION_VERTICAL ? 
     angle < mGestureStrokeAngleThreshold : 
     angle > mGestureStrokeAngleThreshold)) { 

    mIsGesturing = true; 
    ... 
    ... 
} 

Es el único lugar donde se utiliza la orientación en absoluto, por lo que no es necesario realizar modificaciones exhaustivas. Solo un simple extender/anular.

Por supuesto, para hacerlo derecha, se añadiría un ORIENTATION_NONE y comprobar contra el que, al igual que lo hicieron para el Replicant Project, pero supongo que eso depende de si usted necesitará siempre la funcionalidad de nuevo.

+0

Parece interesante, definitivamente lo intentaré y te lo haré saber. – capcom

0

¿Has visto http://developer.android.com/training/gestures/index.html? Necesito un poco más de información sobre lo que estás tratando de hacer con los gestos horizontales y verticales para dar consejos más específicos. Pero es definitivamente posible tener un área táctil que haga una cosa con golpes horizontales y otra cosa con golpes verticales. Tampoco es importante que busque líneas rectas perfectas, ya que sus usuarios no podrán realizarlas.

Editar (1): ¿Has visto http://www.vogella.com/articles/AndroidGestures/article.html? Vogella parece estar implicando con su ejemplo que puede tener un gesto hacia arriba y gestos laterales en el GestureOverlayView. ¿Es esto lo que estas tratando de hacer?

+0

Ya he visto ese enlace. Lo que intento hacer es bastante simple: quiero usar gestos personalizados de la clase GestureOverlayView, junto con gestos verticales y horizontales. Sin embargo, esa clase no permite gestos "puramente" horizontales/verticales porque interpreta esas acciones como desplazables (afaik). No tengo ningún contenedor desplazable en mi opinión. Por puramente vertical/horizontal, en realidad no quiero decir que las líneas tengan una línea recta. Solo aproximadamente. No le estoy pidiendo al usuario que haga nada antinatural. Gracias. – capcom

+0

Mi pregunta, es el uso de los 2 gestos. Hay un 'GestureDetector' que puede reconocer los gestos de desplazamiento, que son los deslizamientos horizontales y verticales (incluso cuando no está desplazando el contenido de un contenedor). Hay una intercepción táctil que significa que una vista que contiene puede mantener los eventos de movimiento por sí misma en algunas situaciones y pasarlas a una vista secundaria en otras situaciones. –

+0

La complejidad de lo que desea hacer está relacionada con el hecho de que no puede esperar líneas rectas del usuario. No te estaba acusando de querer hacerlo. Sin embargo, significa que los gestos de "detección" deben ser restrictivos, de modo que se pueda tener la certeza de un gesto y, al mismo tiempo, permitir al usuario realizar trazos bruscos. –

5

Todo lo que tiene que hacer, es establecer la GestureStrokeAngleThreshold a un valor más cercano a 90 (utilicé 90f)

El valor por defecto de la threashold ángulo se 40.0f debido a lo cual sus simples gestos verticales pueden saltarse

+0

funcionó para mí. ") Gracias –

Cuestiones relacionadas