YuShaN Posted October 22, 2015 Share Posted October 22, 2015 Hi everyone, I made a game with one only state. It's running good but music load slow. So I trying change it to many state(for loading source at a state before start game). But at state game (this state run game). I got at error at line 118 (this.enemy = this.enemyGroup.getFirstExists(false);) Uncaught TypeError: Cannot read property 'getFirstExists' of undefinedbut at line 107 (this.playerBullet = this.playerBulletGroup.getFirstExists(false) that method .getFirstExists run normal ( when i remove function lauchEnemy & line 67 (this.game.time.events.add(2000, this.launchEnemy);) i can move and shoot normal no error). Someone help me . Thank you for reading. This is my code BasicGame.Game = function (game) { // When a State is added to Phaser it automatically has the following properties set on it, even if they already exist: this.game; // a reference to the currently running game this.add; // used to add sprites, text, groups, etc this.camera; // a reference to the game camera this.cache; // the game cache this.input; // the global input manager (you can access this.input.keyboard, this.input.mouse, as well from it) this.load; // for preloading assets this.math; // lots of useful common math operations this.sound; // the sound manager - add a sound, play one, set-up markers, etc this.stage; // the game stage this.time; // the clock this.tweens; // the tween manager this.world; // the game world this.particles; // the particle manager this.physics; // the physics manager this.rnd; // the repeatable random number generator // You can use any of these from any function within this State. // But do consider them as being 'reserved words', i.e. don't create a property for your own game called "world" or you'll over-write the world reference. this.background; this.player; this.playerBullet; this.playerBulletGroup; this.shoot; this.enemy; this.enemyGroup; this.cursors; this.bulletTimer = 0; this.enemyTimer;};BasicGame.Game.prototype = { create: function () { // Background background = this.game.add.tileSprite(0, 0, 500, 600, 'background'); // Player this.player = this.game.add.sprite(300, 300, 'cirno'); this.player.anchor.setTo(0.5, 0.5); this.game.physics.enable(this.player, Phaser.Physics.ARCADE); // Player BulletGroup this.playerBulletGroup = this.game.add.group(); this.playerBulletGroup.enableBody = true; this.playerBulletGroup.physicsBodyType = Phaser.Physics.ARCADE; this.playerBulletGroup.createMultiple(200, 'bullet'); this.playerBulletGroup.setAll('anchor.x', 0.5); this.playerBulletGroup.setAll('anchor.y', 1); this.playerBulletGroup.setAll('outOfBoundsKill', true); this.playerBulletGroup.setAll('checkWorldBounds', true); this.playerBulletGroup.forEach(function(enemy){ enemy.body.setSize(15, 70); }); // Enemy this.enemyGroup = this.game.add.group(); this.enemyGroup.enableBody = true; this.enemyGroup.physicsBodyType = Phaser.Physics.ARCADE; this.enemyGroup.createMultiple(10, 'luna'); this.enemyGroup.setAll('anchor.x', 0.5); this.enemyGroup.setAll('anchor.y', 0.5); this.enemyGroup.setAll('outOfBoundsKill', true); this.enemyGroup.setAll('checkWorldBounds', true); this.enemyGroup.forEach(function(enemy){ enemy.body.setSize(30, 30); }); // Lauch enemy this.game.time.events.add(2000, this.launchEnemy); // Key input this.cursors = this.game.input.keyboard.createCursorKeys(); this.shoot = this.game.input.keyboard.addKey(Phaser.Keyboard.Z); }, update: function () { // scroll bg background.tilePosition.y += 1; // Reset velocity & set size this.player.body.velocity.setTo(0, 0); this.player.body.setSize(10, 10); if (this.cursors.left.isDown && !this.cursors.right.isDown) { if(this.player.x >50){ this.player.body.velocity.x = -300; } } else if (this.cursors.right.isDown && !this.cursors.left.isDown) { if (this.player.x < 450){ this.player.body.velocity.x = 300; } } if (this.cursors.up.isDown && !this.cursors.down.isDown) { if(this.player.y >50){ this.player.body.velocity.y = -300; } } else if (this.cursors.down.isDown && !this.cursors.up.isDown) { if (this.player.y < this.game.height - 50){ this.player.body.velocity.y = 300; } } // Fire bullet if (this.player.alive && this.shoot.isDown) { this.fireBullet(); } }, fireBullet: function() { if (this.game.time.now > this.bulletTimer) { this.playerBullet = this.playerBulletGroup.getFirstExists(false); if (this.playerBullet) { this.playerBullet.alpha = 0.5; this.playerBullet.reset(this.player.x, this.player.y); this.playerBullet.body.velocity.y = -800; this.bulletTimer = this.game.time.now + 80; } } }, launchEnemy: function() { this.enemy = this.enemyGroup.getFirstExists(false); if (this.enemy) { this.enemy.reset(this.game.rnd.integerInRange(0, 480), -10); this.enemy.body.velocity.x = this.game.rnd.integerInRange(-200, 200); if (this.enemy.body.velocity.x >0) { this.enemy.scale.x = -1; } else { this.enemy.scale.x = 1; } this.enemy.body.velocity.y = this.game.rnd.integerInRange(10, 50); } // time creat enemy this.enemyTimer = this.game.time.events.add(this.game.rnd.integerInRange(1500, 3000), this.launchEnemy); }} Link to comment Share on other sites More sharing options...
chongdashu Posted October 22, 2015 Share Posted October 22, 2015 The reason why it's failing is because the this variable in launchEnemy() is pointing to the Window element of the page. You will need to set the context argument (3rd argument ) when adding event callbacks to make sure that methods you reference are then called back in the context of the game state, and now the window. For e.g.,this.game.time.events.add(2000, this.launchEnemy);should bethis.game.time.events.add(2000, this.launchEnemy, this);Similarly, this:this.enemyTimer = this.game.time.events.add(this.game.rnd.integerInRange(1500, 3000), this.launchEnemy);should be:this.enemyTimer = this.game.time.events.add(this.game.rnd.integerInRange(1500, 3000), this.launchEnemy, this);I have a working example of your code (but without your resources) at this jsFiddle: https://jsfiddle.net/chongdashu/79tf3t6n/ Hope it helps! YuShaN and drhayes 2 Link to comment Share on other sites More sharing options...
YuShaN Posted October 22, 2015 Author Share Posted October 22, 2015 The reason why it's failing is because the this variable in launchEnemy() is pointing to the Window element of the page. You will need to set the context argument (3rd argument ) when adding event callbacks to make sure that methods you reference are then called back in the context of the game state, and now the window. For e.g.,this.game.time.events.add(2000, this.launchEnemy);should bethis.game.time.events.add(2000, this.launchEnemy, this);Similarly, this:this.enemyTimer = this.game.time.events.add(this.game.rnd.integerInRange(1500, 3000), this.launchEnemy);should be:this.enemyTimer = this.game.time.events.add(this.game.rnd.integerInRange(1500, 3000), this.launchEnemy, this);I have a working example of your code (but without your resources) at this jsFiddle: https://jsfiddle.net/chongdashu/79tf3t6n/ Hope it helps!Thank you so much. Can I add you. I have many questions need help Link to comment Share on other sites More sharing options...
Recommended Posts