本文介绍了Android中的自定义对象点击问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在Android中创建了一个自定义视图,以在屏幕上显示球。现在我想要的是当我触摸那个球,它应该爆炸四个部分,每个部分应该移动不同的四个方向,即上,下,左,右。我知道我必须设置触摸侦听器检测触摸球,但然后如何创建爆炸效果?。我在屏幕上显示多个球,以便用户可以点击它并爆炸。

I have created an custom view in android to display ball on screen. Now what I want is when I touch on that ball it should explode in four parts and every part should move different four directions ie up, down, left, right. I know I have to set touch listener to detect touch on ball but then how to create a explode effect?. I'm displaying multiple balls on screen so that user can click on it and explode them.

这是我的自定义视图:

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具有相似的属性

SmallBall with similar properties except one that is direction and an explode method to move it in direction and animation flag to stop it moving.

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();
}

我的布局xml如下:

<?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" />

我将BallView和SmallBall添加到活动类中,如下所示:

I'm adding BallView and SmallBall to activity class as follows:

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);

我在不同位置添加多个BallView及其相对的SmallBall数组。现在发生什么,无论我在哪里点击屏幕上次添加BallView开始爆炸。最后一秒,等等。所以这里有2个问题:

I'm adding multiple BallView and their relative SmallBall array at different positions. Now what happens no matter where I click on screen last added BallView starts to explode. After that second last, and so on. So here are 2 issues:


  1. 为什么不管我点击屏幕什么地方调用onClick / onTouch事件?它应该只调用监听器事件当我点击特定的BallView。

  2. 第二是为什么BallView以反向的方式开始爆炸,如何将它们添加到布局中。

我的监听器类:

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.
    }

推荐答案

OK,问题出现在创建 BallView SmalBall 作为查看对象。我想我可以充分解释这一点,所以忍受我:

OK, the problem is during the creation of BallView and SmalBall as View objects. I think I can fully explain this well enough, so bear with me:

一个好的开始是一个分层的蛋糕。想想站在厨房里做一个这样的蛋糕:一次添加一层。首先是巧克力层,然后是香草层,然后是另一个巧克力层。听起来不错?好的。

A good place to start is with a layered cake. Think about standing in the kitchen and making a cake like this: adding one layer at a time. First the chocolate layer, and then the vanilla layer and then another chocolate layer. Sound good? Alright.

因此,在 Canvas 上绘制了很多圈子, c> Ball 对象添加为查看。注意,Canvas仅仅代表一个用户可以交互的矩形,并且与 View - FrameLayout 你的代码。对于所有意图和目的, Canvas 完全填充 FrameLayout 。在你的应用程序中, Canvas 是蛋糕的底层 - 填充 ContentView (或盘)。

So, there are a lot of circles being drawn on a Canvas and seperately, Ball objects are added as Views. Note a Canvas simply represents a rectangle the user can interact with, and is associated with a View-- the FrameLayout in your code. For all intents and purposes, the Canvas is completely filling the FrameLayout. In your app, the Canvas is the bottom layer of the cake-- filling both the width and height of the ContentView (or pan).

每次调用 m.addView(View v)本质上都是放置一个新的 View在 m 中已经包含了许多 View 对象之上的就蛋糕而言, addView 的每一次调用都会向图层蛋糕中添加另一个图层。

Every call to m.addView(View v) is essentially placing a new View v on top of however many View objects are already contained in m. In terms of cake, every call to addView is adding another layer to our layer cake.

你想要添加一个图层到蛋糕,但没有它填满整个锅。

In your project, you want to add a layer to the cake but not have it fill up the entire pan. You want to put a couple strawberries on top, you don't want a full layer of strawberry.

所以,默认情况下,你的 BallView 对象占用整个屏幕。每一个都堆叠在下一个,填满整个画布。当您点击时,它会删除最后一个 - 因为最后一个在顶部,并占据整个画布的宽度和高度 - 实际上是只有球,用户可以

So, by default, your BallView objects are taking up the entire screen. Each on is piling on top of the next, filling up the entire canvas. When you click, it deletes the last one-- because the last one is on top, and is taking up the width and height of the entire canvas-- and is actually the only ball that the user can possibly click on.

所以你必须告诉你 BallView 查看对象与您在 Canvas 对象上绘制的圆的大小相同。

So you have to tell your BallView View objects to be the same size as the circle you are drawing on the Canvas object.

这里有几个问题:

您只能使用 RelativeLayout 进行绝对定位。如果你想要 BallView ,用户可以点击到在画布上绘制的圆圈的顶部,你需要一种方法来告诉 BallView 它所在的位置,并动态更改该位置。目前您正在使用 FrameLayout ,这是 Canvas 所必需的 - 因此在您的XML中,添加全屏< RelativeLayout> 。然后,在您的代码中,将 BallView 对象替换为 RelativeLayout

You can only do absolute positioning with a RelativeLayout. If you want the BallView the user can click on to be on top of the circle being drawn on the canvas, you need a way to tell the BallView where it is located, and change that position dynamically. Currently you are using a FrameLayout, which is necessary for the Canvas-- so in your XML, add a full screen <RelativeLayout>. And then, in your code, add the BallView objects to this RelativeLayout instead.

然后,最后:

前往这里:

在Android中设置视图的绝对位置 a>

祝你好运!

这篇关于Android中的自定义对象点击问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!