Android位置在2.X上不正确

时间:2013-11-16 11:44:14

标签: android onclick location

我将尝试尽可能详细地解释问题,但由于这是一个非常具体的问题,这将很难。但我已经完成了我的选择,并且真的不知道如何解决这个问题。

我正在创建一款Android游戏,用户可以按照正确的顺序点击图片,以进入下一个级别。我在屏幕上的随机位置生成这些图像,当用户点击图像时,它应该触发事件。在Android 4.0及更高版本上,这非常有效。但是,当我在较低版本上测试时,图像的位置似乎是正确的,但是当点击图像时,它会为不同的图像触发事件,或者根本不触发图像。此外,当您单击一个空白区域(通常位于左上角)时,它也会触发一个事件。我不确定它是低Android版本还是低屏幕分辨率。

代码

BubbleImage XML

这是图像的布局,onClickEvent直接设置为RelativeLayout而不是relativelayout中的ImageView

<?xml version="1.0" encoding="utf-8"?>
<com.timkranen.customui.BubbleImage xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/bubImgMain"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >

<ImageView
    android:id="@+id/bubbleImage"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:scaleType="fitXY"
    android:adjustViewBounds="true"
    android:src="@drawable/bubble_selector" />

    <TextView
    android:id="@+id/numberTxtView"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignTop="@+id/bubbleImage"
    android:layout_alignLeft="@+id/bubbleImage"
    android:layout_alignBottom="@+id/bubbleImage"
    android:layout_alignRight="@+id/bubbleImage"
    android:gravity="center"
    android:text="test"
    android:textColor="#fff"
    android:textSize="23sp" />

生成随机BubbleImages

对不起这里的长片代码,我应该提一下,我使用ninoldandroid库来获得正确的 旧版Android上的x / y坐标(ViewHelper类执行此操作):

  private void generateRandomView(int amount) {
    LayoutInflater inflater = (LayoutInflater) this
            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    for (int i = 0; i <= amount; i++) {
        // add imageview to layout
        BubbleImage rImg = (BubbleImage) inflater.inflate(
                R.layout.bubbleimage, null);
        rImg.setEnabled(false);
        rImg.setOnClickListener(new BubbleClick());
        bubbleImages.add(rImg);
        totalBubbles++;

        // create random number in between amount and 0
        int genNum = this.generateRandomNum(amount);
        rImg.setNumber(genNum);
        numbers.add(genNum);

        // determine the screen size
        screenSize = getScreenSize();
        screenSize.x = screenSize.x - screenSize.x / 4;
        screenSize.y = screenSize.y - ((screenSize.x / 4) * 3) + 20;

        // stick might throw a stackoverflow error if its called too much
        // but the game only needs to call it on level max
        // stackoverflowerror @ 10x on 300x300
        // stackoverflowerror @ 16x on 250x250
        // depends on screen size
        Point randomLoc = null;
        try {
            Random random = new Random();
            randomLoc = generateRandomLocation(screenSize, random);
        } catch (StackOverflowError e) {
            Toast.makeText(
                    this,
                    "BrainTest PRO encountered a fatal error caused by low memomory on your device. Restart the app and try again, if the error persists please report it to the developer.",
                    Toast.LENGTH_LONG).show();
            finish();
        }

        Resources r = getResources();


        RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(180,
                180);
        mainLayout.addView(rImg, params);

        ViewHelper.setTranslationX(rImg, (float) randomLoc.x);
        ViewHelper.setTranslationY(rImg, (float) randomLoc.y);

        // scalefactor on basis of screensize
        float scaleFactor = 1.2f;
        ViewHelper.setScaleX(rImg, scaleFactor);
        ViewHelper.setScaleY(rImg, scaleFactor);

生成随机位置方法

我认为我不需要澄清generateRandomNum()但我必须澄清这个方法,它是一个递归方法,进入循环直到生成的图像不再碰撞

  private Point generateRandomLocation(Point dimensions, Random random) {

    // generate random x
    int x = random.nextInt((dimensions.x - 0) + 1);

    // generate random y
    int y = random.nextInt((dimensions.y - 0) + 1);

    Point location = new Point(x, y);

    if (!collision(location)) {
        return new Point(x, y);
    } else {
        return generateRandomLocation(dimensions, new Random());
    }

}

BubbleClick事件 这是事件发生,事件本身有效,但不会在正确的位置点火

 private class BubbleClick implements OnClickListener {

    private ScoreCalculator calculator;

    public BubbleClick() {
        calculator = new ScoreCalculator();
    }

    @Override
    public void onClick(View arg0) {
        BubbleImage clicked = (BubbleImage) arg0;
        Log.d("Clicked_bubble", "Num: " + clicked.getNumber() + " | X: " + ViewHelper.getTranslationX(clicked) + " | Y: " + ViewHelper.getTranslationY(clicked));
        ImageView clicked_img = (ImageView) clicked
                .findViewById(R.id.bubbleImage);
        if (currentClick == clicked.getNumber()) {
            if (previousBub != null) {
                GameActivity.this.drawLine(clicked);
            }

            // SUCCESFULL CLICK
            score += calculator.pointsPerBubble(currentLevel);
            scoreLabel.setText("Score: " + String.valueOf(score));
            // clicked_img.setImageResource(R.drawable.bubble_ok);
            clicked.setEnabled(false);
            previousBub = clicked;
            playPosSound();

            for (int i = 0; i <= clicked.getChildCount(); i++) {
                View child = clicked.getChildAt(i);
                if (child instanceof TextView) {
                    TextView txtView = (TextView) clicked.getChildAt(i);
                    txtView.setVisibility(View.VISIBLE);
                }
            }

            // check wether the last bubbleimage was clicked
            if (countListClick + 1 != numbers.size()) {
                countListClick++;
                currentClick = numbers.get(countListClick);
            } else {
                GameActivity.this.resetGame(true);
            }

        } else {
            // WRONG ATTEMPT
            clicked_img.setImageResource(R.drawable.bubble_wrong);
            scores.add(new Score(score, attempt));
            attempt++;
            if (attempt > 3) {
                // GAME OVER
                isGameOver = true;
                continueBut.setVisibility(View.INVISIBLE);
                GameActivity.this.gameOver();
            }

            previousBub = null;

            playNegSound();

            if (currentLevel > 0) {
                currentLevel--;
            }

            vibrate();

            for (int i = 0; i <= clicked.getChildCount(); i++) {
                View child = clicked.getChildAt(i);
                if (child instanceof TextView) {
                    TextView txtView = (TextView) clicked.getChildAt(i);
                    txtView.setVisibility(View.VISIBLE);
                }
            }

            // show all text and disable buttons
            if (bubbleImages != null) {
                for (BubbleImage bImg : bubbleImages) {
                    bImg.setEnabled(false);
                    for (int i = 0; i <= bImg.getChildCount(); i++) {
                        View childV = bImg.getChildAt(i);
                        if (childV instanceof TextView) {
                            TextView childView = (TextView) childV;
                            childView.setVisibility(View.VISIBLE);
                        }
                    }
                }
            }

            if (!isGameOver) {
                GameActivity.this.resetGame(false);
            }

            // GAME OVER

        }

    }

onClickListener的内容非常无关紧要,因为代码运行正常而不是在正确的时刻。有谁知道发生了什么事?

提前致谢!

1 个答案:

答案 0 :(得分:1)

因为这对我来说是一个真正的问题:

ViewHelper.getTranslation方法在2.x上的行为与在4.x上的行为不同,我使用的是Margins。