Problema de clic de objeto personalizado en android

He creado una vista de encargo en androide para exhibir la bola en la pantalla. Ahora lo que quiero es cuando toco esa pelota que debería explotar en cuatro partes y cada parte debe mover cuatro direcciones diferentes, es decir, arriba, abajo, izquierda, derecha. Sé que tengo que establecer el oyente tacto para detectar toque en bola, pero luego cómo crear un efecto de explosión? Este problema se resuelve ahora . Estoy mostrando múltiples bolas en la pantalla para que el usuario puede hacer clic en él y explotarlos.

Esta es mi vista personalizada:

public class BallView extends View { private float x; private float y; private final int r; public BallView(Context context, float x1, float y1, int r) { super(context); this.x = x1; this.y = y1; this.r = r; } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); canvas.drawCircle(x, y, r, mPaint); } } 

SmallBall con propiedades similares excepto una que es la dirección y un método de explosión para moverlo en dirección y bandera de animación para detener su movimiento.

 private final int direction; private boolean anim; public void explode() { // plus or minus x/y based on direction and stop animation if anim flag is false invalidate(); } 

Mi xml de diseño es como sigue:

 <?xml version="1.0" encoding="utf-8"?> <FrameLayout android:id="@+id/main_view" xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:background="#FF66FF33" /> 

Estoy agregando BallView y SmallBall a la clase de actividad de la siguiente manera:

 final FrameLayout mainFrameLayout = (FrameLayout) findViewById(R.id.main_frame_layout); SmallBall[] smallBalls = new SmallBall[4]; smallBalls[0] = new SmallBall(getApplicationContext(), 105, 100, 10, 1, false); smallBalls[0].setVisibility(View.GONE); mainFrameLayout .addView(smallBalls[0]); // create and add other 3 balls with different directions. BallView ball = new BallView(getApplicationContext(), 100, 100, 25, smallBalls); listener = new MyListener(ball); ball.setOnClickListener(listener); mainFrameLayout.addView(ball); 

Estoy agregando múltiples BallView y su matriz relativa SmallBall en diferentes posiciones. Ahora lo que pasa, no importa dónde hago clic en la última pantalla de BallView empieza a explotar. Después de que el segundo pasado, y así sucesivamente. Así que aquí hay 2 problemas:

  1. ¿Por qué llamar al evento onClick / onTouch sin importar dónde haga clic en la pantalla? Debería llamar al evento de escucha cuando haga clic en BallView particular.
  2. Y en segundo lugar, ¿por qué BallView comienza a explotar de manera inversa de cómo se añaden al diseño?

Mi clase de escucha:

 public void onClick(View v) { BallView ballView = (BallView) v; ballView.setVisibility(View.GONE); //get small balls associated with this ball. //loop through small ball and call their explode method. } 

He recortado el código debido a la limitación de caracteres en cuestión.

No creo que necesites codificar todo esto en un lienzo. Puedes llamar a ball.setVisibility(View.GONE) en el Touch Listener y mostrar 4 bolas extras usando smallBall.setVisibility(View.Visible) para cada bola pequeña. De esta manera usted podría esconder la bola grande y puede demostrar las bolas pequeñas. Ahora para el efecto del movimiento, puede haber un método en cada smallBall donde la dirección necesita ser pasado y usted puede llamarla como este smallBall.explode (dirección). La implementación del método podría ser

 explode(int direction){//can be String if(direction=NORTH) y--; //other condition checks } 

El método de explosión comenzará a cambiar su coordenada xey, en base a la dirección pasada. Espero que esto te dé una pista sobre cómo implementarlo.

Aceptar, el problema es durante la creación de BallView y SmalBall como objetos de View . Creo que puedo explicar completamente esto lo suficientemente bien, así que tenga paciencia conmigo:

Un buen lugar para empezar es con un pastel en capas. Piense en estar en la cocina y hacer un pastel como este: añadir una capa a la vez. En primer lugar la capa de chocolate, y luego la capa de vainilla y luego otra capa de chocolate. ¿Suena bien? Bien.

Por lo tanto, hay una gran cantidad de círculos que se dibujan en un Canvas y por separado, los objetos Ball se agregan como View s. Tenga en cuenta que un lienzo representa simplemente un rectángulo con el que el usuario puede interactuar y está asociado con una View – el FrameLayout en su código. Para todos los efectos, el Canvas está llenando completamente FrameLayout . En tu aplicación, el Canvas es la capa inferior de la torta, que rellena tanto el ancho como la altura de ContentView (o pan).

Cada llamada a m.addView(View v) es esencialmente colocar una nueva View v encima de sin embargo muchos objetos View ya están contenidos en m . En términos de pastel, cada llamada a addView está agregando otra capa a nuestro pastel de capas.

En tu proyecto, quieres añadir una capa a la torta, pero no la tienes que llenar la bandeja entera. Usted quiere poner un par de fresas en la parte superior, no desea una capa completa de fresa.

Por lo tanto, de forma predeterminada, los objetos BallView ocupan toda la pantalla. Cada uno se está apilando encima del siguiente, llenando el lienzo entero. Al hacer clic, elimina el último – porque el último está en la parte superior, y está ocupando el ancho y la altura del lienzo completo – y es en realidad la única bola que el usuario puede hacer clic en.

Así que tienes que decirle a tus objetos BallView View que sean del mismo tamaño que el círculo que BallView en el objeto Canvas .

Por lo tanto, hay un par de cuestiones aquí:

Sólo puede hacer un posicionamiento absoluto con un RelativeLayout . Si desea que el BallView el usuario puede hacer clic en para estar en la parte superior del círculo que se dibuja en el lienzo, necesita una manera de decirle al BallView donde se encuentra y cambiar esa posición dinámicamente. Actualmente estás usando un FrameLayout , que es necesario para el Canvas , así que en tu XML, agrega una pantalla completa <RelativeLayout> . Y luego, en su código, agregue los objetos BallView a este RelativeLayout lugar.

Y luego, FINALMENTE:

Ven aqui:

Establecer la posición absoluta de una vista

¡Buena suerte!

Todo esto está sucediendo porque no se especifica LayoutParameters del objeto Ball. Lo que sucede aquí es cuando se agrega un objeto Ball a Layout que toma espacio de todo el diseño y por eso reacciona para hacer clic en cualquier parte de la pantalla.

Ahora para el segundo tema, la razón es la misma. Suponga que la situación de las placas, que siempre sale de manera LIFO. Aquí todo el objeto de la bola cubre la pantalla entera así que considérelos como placas, así que qué usted está haciendo está poniendo placas encima de eachother. Y es por eso que reacciona al método onClick de la última pelota primero y luego al último último y así sucesivamente.

Por lo tanto, ambos problemas se resolverán después de configurar los parámetros de diseño adecuados para los objetos Ball.

FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.