Trying to animate a sprite Phaser 3 from spritesheet - getting error cannot read property 'frame' of undefined

Viewed 2753

EDIT: fixed issue. Fix in comments.

new to coding here and I've been making progress on a first attempt at a game. All has worked so far with simple googling but I've encountered an issue when I've gone to play my first animation.

I've loaded the player's sprite from a spritesheet and that shows fine, but when I play the animation the game freezes and I get the following error in the console: 'phaser.min.js:1 Uncaught TypeError: Cannot read property 'frame' of undefined'.

The animation creation is in create().

the .play('run') animation I'm trying to play is in update(), when player presses the left key.

Any tips?! Thanks so much in advance.


class GameScene extends Phaser.Scene {
    constructor() {
        super ({ key: 'GameScene' })
    }


 preload () {
    this.load.image('platform', 'ASSETS/Acesprite/sandPlatform.png');
    this.load.image('food1', 'ASSETS/Food1.png');
    this.load.image('food2', 'ASSETS/Food2.png');
    this.load.image('food3', 'ASSETS/Food3.png');
    this.load.image('food4', 'ASSETS/Food4.png');
//  this.load.image('background', 'ASSETS/Acesprite/backgroundImage .png')
    this.load.image('musselsTips', 'ASSETS/Acesprite/musselsTips.png')
    this.load.image('continueButton', 'ASSETS/Acesprite/continueButton.png')
    this.load.spritesheet('kelp2', 'ASSETS/Acesprite/Kelp2-Sheet.png', {
        frameWidth: 43,
        frameHeight: 267,
        endFrame: 1
    });
    this.load.spritesheet('kelp1','ASSETS/Acesprite/Kelp1-sheet.png', {
        frameWidth: 69,
        frameHeight: 369,
        endFrame: 1
    });
    this.load.spritesheet('crabby', 'ASSETS/Acesprite/ColonelCrabs-Sheet.png', {
        frameWidth: 52,
        frameHeight: 40,
    });

}

 create () {

    //this.add.image(0,0,'background').setOrigin(0,0);
    this.add.image(0, 570, 'platform').setOrigin(0,0);//to make platform lower down. quick fix. do this properly. 


    //creating platforms
    const platforms = this.physics.add.staticGroup();
    platforms.create(0, 550, 'platform').setOrigin(0,0).refreshBody();

    //creating player
    gameState.player = this.physics.add.sprite(400, 500, 'crabby').setScale(1.5);

    this.anims.create({
        key: 'run',
        frames: this.anims.generateFrameNumbers('crabby', { start: 0, end: 3 }),
        frameRate: 4,
        repeat: -1
      });


    //creating toxicity bar
    gameState.toxicityText = this.add.text( 20, 570, `Toxicity: ${gameState.toxicity} / 10`, { fontFamily: 'Seagull_Wine',fontSize: '15px', fill: '#000' })


    //creating score bar
    gameState.scoreText = this.add.text(250, 570, `Score: ${gameState.score}`, { fontFamily: 'Helvetica', fontSize: '15px', fill: '#000' })

    //adding boundaries and putting crabby on the platform
    gameState.player.setCollideWorldBounds(true);
    this.physics.add.collider(gameState.player, platforms)


    //creating food as a physics group and plastics 
    gameState.food = this.physics.add.group();  
    const foodList = ['food1', 'food2'];

    gameState.plastic = this.physics.add.group();
    const plasticList = ['food3', 'food4'];

//creating a random food and plastics at point X

    function foodGen() {
        const xCoord = Math.random() * 600
        let randomItem = foodList[Math.floor(Math.random() * 2)]
        gameState.food.create(xCoord, 10, randomItem)
    };
    function plasticGen() {
        const xCoord = Math.random() * 600
        let randomItem = plasticList[Math.floor(Math.random() * 2)]
        gameState.plastic.create(xCoord, 10, randomItem)
    };

    gameState.foodLoop = this.time.addEvent({ 
        delay: 600, 
        callback: foodGen,
        callbackScope: this, 
        loop: true });

    gameState.plasticLoop = this.time.addEvent({        
        delay: 1000, 
        callback: plasticGen,
        callbackScope: this, 
        loop: true 
    })


//  Adding a collision between Food and Crabby
    this.physics.add.collider(gameState.food, gameState.player, (player, food) => {
        gameState.score += 1;
        gameState.scoreText.setText(`Score: ${gameState.score}`)
        food.destroy();
        if (gameState.toxicity >= 0.25){
            gameState.toxicity -= 0.25;
            gameState.toxicityText.setText(`Toxicity: ${gameState.toxicity} / 10`);
        };


    });

// Adding a collision between crabby and plastic
    this.physics.add.collider(gameState.plastic, gameState.player, (player, plastic) => {
        gameState.toxicity += 2.5;
        gameState.toxicityText.setText(`Toxicity: ${gameState.toxicity} / 10`);
        plastic.destroy();
        this.physics.pause();
        gameState.plasticLoop.destroy();
        gameState.foodLoop.destroy(); 
        this.input.on('pointerup', () => {
            if (gameState.active === 'gameover'){
                gameState.toxicity = 0;
                gameState.score = 0;
                this.scene.restart();
            } else {

            }
        })

        if(gameState.toxicity >= 10){
            gameState.toxicityText.setText(`Toxicity: ${gameState.toxicity} / 10`);
            gameState.scoreText.setText(`Toxicity: ${gameState.toxicity} / 10`);
            gameState.deathX = player.x
            gameState.deathY = player.y
            this.scene.stop('GameScene');
            this.scene.start('EndScene');

        } else{
            this.add.image(400, 50, 'musselsTips').setOrigin(0.5, 0);
            const continueButton = this.add.image(400, 236, 'continueButton');
            let randText = randomTip();
            this.add.text(166, 80, randText, { fontSize: '15px', fill: '#000' });
            this.add.text(165, 79, randText, { fontSize: '15px', fill: '#f8ce5e' });

            continueButton.setInteractive();
            continueButton.on('pointerup', () => {
                this.scene.restart();
            })

        };


    })
//adding a collision between platform and food 
    this.physics.add.collider(gameState.food, platforms, (food, plat) => {
        food.destroy();
    });
//adding a collision between platform and plasticc 
    this.physics.add.collider(gameState.plastic, platforms, (plas, plat) => {
        plas.destroy();
    });


    //Mrs Mussels tip text
    const musselTipText = [ "I've got a sinking feeling that wasn't food… make \nsure not to eat plastic Mr Crabs… \nit isn't good for you.",
        "You're really coming out of your shell… \nand not in a good way… \ntry not to eat plastic Colonel.", "tip 3", "tip 4"
, "tip 5", "tip 6", "tip 7" ]

    function randomTip() {
        let randNum = Math.floor(Math.random() * musselTipText.length);
        return musselTipText[randNum];
    }

}//CREATE END



 update () {
    const cursors = this.input.keyboard.createCursorKeys();

    if(cursors.left.isDown){
        gameState.player.setVelocityX(-200);
        gameState.player.anims.play('run', true);

    } else if (cursors.right.isDown) {
        gameState.player.setVelocityX(200)
    } else {
        gameState.player.setVelocityX(0);
    }

    const pointer = this.input.activePointer; 
    const distancePointPlayer = Math.sqrt((pointer.x - gameState.player.x) * (pointer.x - gameState.player.x));

    if(pointer.isDown){
        if (distancePointPlayer < 20){

        } else if(pointer.x > gameState.player.x){
            gameState.player.setVelocityX(200)
        } else if(pointer.x < gameState.player.x){
            gameState.player.setVelocityX(-200);


        }
        };
}

}
1 Answers

Fixed: I was an idiot and loaded an image in another scene with the same key I loaded the spritesheet as! Didn't realise that would have an impact but the animation now works as intended.

Related