如何在特定位置移除精灵?

时间:2015-06-05 08:05:39

标签: java libgdx position sprite

我的精灵是在一个随机的时间产生的,在向上生成向上移动直到它们到达某个位置然后它们应被移除。这就是我一直想做的事情,但我总是得到一个错误。

//this method is called at random time
 public void newEnemy(){
        Sprite enemy= Pools.obtain(Sprite.class);
        enemy.set(enemySpr);
        enemy.setPosition(200,150);
        enemies.add(enemy);
    }



//removing the enemy
 while (enemyIterator.hasNext()){
  Sprite nextEnemy=enemyIterator.next();//<--error here,this is line 66  
           if(enemySpr.getY()+enemySpr.getHeight()>=treeObj.treeSpr.getY()){
               removeEnemy(nextEnemy);
           }
       }



//removeEnemy method
public void removeEnemy(Sprite sprite){
        enemies.remove(sprite);
        Pools.free(sprite);
    }



//this is the error there I get:

Exception in thread "LWJGL Application" java.util.ConcurrentModificationException
   at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:901)
   at java.util.ArrayList$Itr.next(ArrayList.java:851)
   at com.dreamroad.savethetree.EnemyClass.update(EnemyClass.java:66)
   at com.dreamroad.savethetree.MyGdxGame.render(MyGdxGame.java:51)
   at com.badlogic.gdx.backends.lwjgl.LwjglApplication.mainLoop(LwjglApplication.java:215)
   at com.badlogic.gdx.backends.lwjgl.LwjglApplication$1.run(LwjglApplication.java:120)

Process finished with exit code 0

我认为这就是我收到错误的原因,但我不确定:

public void draw(SpriteBatch batch){
        for(Sprite drawEnemy:enemies) {    //enemies is the ArrayList
            drawEnemy.draw(batch);
            drawEnemy.translateY(deltaTime * movement);
        }
    }

2 个答案:

答案 0 :(得分:1)

正如Subler所说,这里的问题是你在迭代它的同时试图从列表中删除某些东西。

然而,这是一个更容易的解决方案。只需在迭代器上调用remove()即可。这将删除迭代器的当前元素。

//removing the enemy
while (enemyIterator.hasNext()) {

    Sprite nextEnemy = enemyIterator.next();
    if(enemySpr.getY() + enemySpr.getHeight() >= treeObj.treeSpr.getY()) {
        enemyIterator.remove();
        Pools.free(nextEnemy);
    }
}

答案 1 :(得分:0)

问题在于你试图删除当前正在迭代的列表中的某些东西,我在这种情况下总是做的事情是创建一个额外的列表,其中包含应删除的Sprite,然后迭代列表后(或者,在更新方法结束时,或类似的东西)删除它们

一个简短的代码示例,说明了我的想法:

//removing the enemy
//Initialize a list to store the sprites to be removed
List<Sprite> toBeRemovedSprites = new ArrayList<Sprite>();
while (enemyIterator.hasNext()){
    Sprite nextEnemy=enemyIterator.next(); //I get the error here..<--
    if(enemySpr.getY()+enemySpr.getHeight()>=treeObj.treeSpr.getY()){
        removeEnemy(nextEnemy);
        toBeRemovedSprites.add(nextEnemy);
    }
}
//Remove the sprites that should be deleted, after iterating over the list
for(Sprite s : toBeRemovedSprites){
    enemies.remove(s);
}



//removeEnemy method
public void removeEnemy(Sprite sprite){
    //Remove this line that removes the sprite from the list
    //enemies.remove(sprite);
    Pools.free(sprite);
}

你可以做的另一件事就是使用迭代器的remove函数, 想象它看起来像这样:

//removing the enemy
while (enemyIterator.hasNext()){
    Sprite nextEnemy=enemyIterator.next(); //I get the error here..<--
    if(enemySpr.getY()+enemySpr.getHeight()>=treeObj.treeSpr.getY()){
        removeEnemy(nextEnemy, enemyIterator);
    }
}



//removeEnemy method
public void removeEnemy(Sprite sprite, Iterator<Sprite> enemyIterator){
    //Change the line to remove using the iterator
    //enemies.remove(sprite);
    enemyIterator.remove();
    Pools.free(sprite);
}