1
votes

I am creating a game that randomly displays circles onto a canvas. The circles objects are added to an array and whenever the player collides with one of them I want to remove that object. Here is my code currently for the collision -

    for(var i = 0; i < currentGame.items.length; i++)
    {
        if (player1.x < currentGame.items[i].x + currentGame.items[i].radius*2  && player1.x + currentGame.items[i].radius*2  > currentGame.items[i].x &&
                player1.y < currentGame.items[i].y + currentGame.items[i].radius*2 && player1.y + player1.car.height > currentGame.items[i].y) {
            currentGame.score++;
            position = currentGame.items.indexOf(i);
            currentGame.items.splice(position, 1);
        }
    }

This code works fine when the player hits the last circle that has been added to the array/canvas. However, if the player hits circles that are in the middle of the array then all the subsequant items of the array will also be removed (not the previous ones). The players score will be increased by however many circles get deleted. This suggests that when one of the circles is removed the items are shifted down and take the place of the one just deleted, including taking it's position coordinates so then the player collides with all of them and they are all then deleted.

I don't know how to fix this, or if I am using splice incorrectly.

Here is my code for adding to the array -

function createItem(){
    item1 = new itemSmall();
    item1.x = Math.floor(Math.random()*((currentGame.windowWidth - 40)-40+1)+40);
    item1.y = Math.floor(Math.random()*((currentGame.windowHeight - 40)-40+1)+40);
    item1.fillStyle = "rgb(200,80,200)";
    item1.lineWidth = 4; //Stroke Thickness
    item1.strokeStyle = "rgb(255,215,0)";

    currentGame.items.push(item1);
}

items is stored here (I removed everything else from this object for clarity) -

function gameValues(){
    this.items = [];
}
currentGame = new gameValues();
1
console.log the object as you are looping and you will see whyPW Kad

1 Answers

1
votes

It is quite common to run into trouble when modifying an array which you are looping.

For example, if you remove the item at position i, then the later items will shift left, so the next item will now sit in position i, but because the next iteration of your loop inspects i+1, that item will be skipped!

Now you could do i--; after the splice, to ensure you inspect the new item in position i on the next iteration, but a simpler solution is simply to loop backwards. Then operations which affect the rest of the list will not be an issue.

for(var i = currentGame.items.length; i--; )

Anyway, I am concerned by something else in your code:

        position = currentGame.items.indexOf(i);

Don't we already know that the position of the current item is i? This indexOf searches the list for an item with the value i. I imagine position will get the value -1 when the indexOf search fails. I think what you really mean here is:

        var position = i;

Finally, if you don't enjoy console.log you can try putting this inside your if block:

        debugger;

That manually sets a breakpoint in your code, so you can inspect the values of the variables to see what is going wrong. You will need to have your browser's debugger or "dev tools" panel open. Don't forget to remove the statement when you are finished!