安卓AndEngine:简单的精灵碰撞(Android AndEngine: Simple spri

2019-10-17 05:57发布

我是新来AndEngine游戏开发(或者游戏开发一般)和我的工作很简单的游戏。 该设置是,我在比赛中4级主要的精灵:

一。)战机B)储罐C)步兵天。)炸弹

这场比赛是在当前的无限循环。 这架战斗机从左边出来,在屏幕上放大和出来便又连续每一秒。 坦克从屏幕左侧出来,使得它的方式在屏幕的中间,下降了一些步兵谁使他们在屏幕的右侧的方式。 然后,坦克将面临左,回到它来自何处。

玩家可以点击屏幕发动炸弹径直向下。 当它击中无论是坦克还是战士,在炸弹爆炸(留下爆炸的Sprite)和炸弹,以及它与(罐或士兵)碰撞的物体从场景分离。

我的困境是,我似乎无法解决涉及冲突的逻辑。 我的意思是肯定的,我得到的功能,但是我聪明很为难的逻辑。 下面是游戏本身的快照:

这里是我的代码段(此功能从onCreateScene更新处理程序调用:

    protected void checkTankCollision() {
    // TODO Auto-generated method stub

    int numCompares = bombGroup.getChildCount();
    for (int i = 0; i < numCompares; i++) {
        Sprite s = (Sprite) bombGroup.getChildByIndex(i);
        for (int j = 0; j < numCompares; j++) {
            Sprite s2 = (Sprite) tankGroup.getChildByIndex(j);
            if (s.collidesWith(s2)) {
                // boom
                AnimatedSprite boom = createExplosion();
                boom.setPosition(s.getX(), s.getY());
                getEngine().getScene().attachChild(boom);

                // WARNING: cannot detach from the list
                // while looping through the list
                final Sprite a = s;
                final Sprite b = s2;

                // this will do the action after the scene is done updating
                getEngine().getScene().postRunnable(new Runnable() {

                    @Override
                    public void run() {
                        a.detachSelf();
                        b.detachSelf();
                    }
                });
            }
        }
    }

}

游戏中强制关闭一些炸弹发射后。 它给出了一个IndexOutOfBoundsException异常错误。

这里的logcat的:

    09-22 00:12:14.565: E/AndroidRuntime(924): FATAL EXCEPTION: UpdateThread
    09-22 00:12:14.565: E/AndroidRuntime(924): java.lang.IndexOutOfBoundsException:  Invalid index 1, size is 1
    09-22 00:12:14.565: E/AndroidRuntime(924):  at  java.util.ArrayList.throwIndexOutOfBoundsException(ArrayList.java:251)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at java.util.ArrayList.get(ArrayList.java:304)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at  org.andengine.entity.Entity.getChildByIndex(Entity.java:612)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at com.cs119.bombthetank2.BombTankActivity.checkTankCollision(BombTankActivity.java:660)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at com.cs119.bombthetank2.BombTankActivity$4.onUpdate(BombTankActivity.java:194)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.engine.handler.UpdateHandlerList.onUpdate(UpdateHandlerList.java:47)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.entity.Entity.onManagedUpdate(Entity.java:1395)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.entity.scene.Scene.onManagedUpdate(Scene.java:284)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.entity.Entity.onUpdate(Entity.java:1167)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.engine.Engine.onUpdateScene(Engine.java:591)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.engine.Engine.onUpdate(Engine.java:586)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.engine.Engine.onTickUpdate(Engine.java:548)
    09-22 00:12:14.565: E/AndroidRuntime(924):  at org.andengine.engine.Engine$UpdateThread.run(Engine.java:820)

实体和场景活动是AndEngine的一部分,而且也确实没有办法有可能是有错误。 BombTheTank2是我的活动的名称,所以是的,错误是存在的。

Answer 1:

你似乎卸下精灵停止通过孩子的列表迭代之前。 让我们做它的清洁方式。 尝试这个:

protected void checkTankCollision() {
    int numCompares = bombGroup.getChildCount();
    final ArrayList<Sprite> toBeDetached = new ArrayList<Sprite>();
    for (int i = 0; i < numCompares; i++) {
        Sprite s = (Sprite) bombGroup.getChildByIndex(i);
        for (int j = 0; j < numCompares; j++) {
            Sprite s2 = (Sprite) tankGroup.getChildByIndex(j);
            if (s.collidesWith(s2)) {
                // boom
                AnimatedSprite boom = createExplosion();
                boom.setPosition(s.getX(), s.getY());
                getEngine().getScene().attachChild(boom);

                // WARNING: cannot detach from the list
                // while looping through the list
                toBeDetached.add(s);
                toBeDetached.add(s2);

            }
        }
    }
    runOnUpdateThread(new Runnable() {
        @Override
        public void run() {
            for (Sprite s : toBeDetached) {
                s.detachSelf();
            }
            toBeDetached.clear();
        }
    });
}

编辑:实际的问题是,别的地方 - 伊拉斯谟在坦克群不小心重复同样的次数会在炸弹小组。 解决的办法是检查坦克的数量和更早停止迭代。

我个人一直使用的for-each循环,除非我真的需要知道的指数,它救了我很多头疼的:-)



Answer 2:

我认为你需要做的UpdateThread的“分离”,所以不是这个

            getEngine().getScene().postRunnable(new Runnable() {

                @Override
                public void run() {
                    a.detachSelf();
                    b.detachSelf();
                }

尝试这个

runOnUpdateThread(new Runnable() {

                    @Override
                    public void run() {
                        a.detachSelf();
                        b.detachSelf();
                    }

每次分离的东西的时候,你应该减少你的numCompares价值,一旦你脱离一些持有这些实体的阵列是现在小。 既然你是在开始拉数组的长度,你最终会跑过数组的结束 - 这样你IndexOutOfBounds错误。 该剥离仍然需要在UpdateThread运行。



文章来源: Android AndEngine: Simple sprite collision