YuShaN Posted October 30, 2015 Share Posted October 30, 2015 I make a enemy who fire 3 bullets a time then have a short delay before fire again. This is my code var state = this;var i = 3;this.enemy.update = function() { if (!this.lastShot) { this.lastShot = 0; } if(i > 0) { this.bullet = state.bulletGroup.getFirstExists(false); if (this.bullet && this.alive && this.y > 0 && state.game.time.now > 300 + this.lastShot){ this.lastShot = state.game.time.now; this.bullet.reset(this.x, this.y + this.height / 2); this.bullet.damageAmount = 20; this.angle = state.game.physics.arcade.moveToObject(this.bullet, state.player, 150); this.bullet.angle = state.game.math.radToDeg(this.angle); } i--; } if(i == 0) { state.delay = state.game.time.now; } if(state.game.time.now > state.delay + 2000) { i = 3; }}But it don't have a delay time per 3 bullets. Someone help me. Thank you. Link to comment Share on other sites More sharing options...
jmp909 Posted October 30, 2015 Share Posted October 30, 2015 can you make an example on jsfiddle or http://phaser.io/sandbox/ ? you can use assets from the examples site eg http://phaser.io/examples/v2/games/invaders has a bullet you can usgame.load.baseURL = 'http://examples.phaser.io/assets/';game.load.crossOrigin = 'anonymous';game.load.image('enemyBullet', 'games/invaders/enemy-bullet.png'); Link to comment Share on other sites More sharing options...
drhayes Posted October 30, 2015 Share Posted October 30, 2015 I would use timers for the whole thing:// Put this the state's create method.state.game.time.events.add(2000, this.fireBullet, this, 3);// This is a member function of your state, I guess?fireBullet: function(numBullets) { if (numBullets <= 0) { this.game.time.events.add(2000, this.fireBullet, this, 3); return; } // Code to fire a bullet goes here... this.game.time.events.add(150, this.fireBullet, this, numBullets - 1);}That first line says "in 2000 milliseconds, call fireBullet and pass it the number 3". When that timer actually goes off and calls "fireBullet", then it'll shoot a bullet and then immediately set up another timer to fire in 150 milliseconds... this time, passing 2. This'll happen again, but it'll pass 1. The last time it passes 0, which causes it to set up a 2000 millisecond timer to fire the three bullets again later. chongdashu 1 Link to comment Share on other sites More sharing options...
YuShaN Posted October 31, 2015 Author Share Posted October 31, 2015 Here is my code http://phaser.io/sandbox/edit/gEWHWQCY Link to comment Share on other sites More sharing options...
chongdashu Posted October 31, 2015 Share Posted October 31, 2015 @drhayes and @jmp909 have both suggested better alternatives to the way that you are currently handling this. You might want to consider them after getting it to work! Anyway, there are two problems in your code. Problem 1Your variable i is never decrementing below 3. Try putting a console.log(i); after if (i > 0) in fireBullet(). You will see that it never drops.So let's take a look at where i is ever modified. Since it's not being modified in fireBullet()'s loop, it has to be in the update() of your Sprite.There is a check for if (game.time.now > delay) { i = 3; } so it's likely in here.You will realize that if you put a console.log(delay), that delay is always zero!That's because delay is initialized to zero. And since game.time.now is always > delay, it's always going to set i=3. No other pieces of code is going to runSo what you need to do is to set the value of delay if you enter that block, so that you will not always be in it. Setting it to delay = game.time.now + 2000; works.Problem 2Now, if you run it, you will notice that firing never restarts again.This is because of the code if (i==0){ delay = game.time.now + 2000; }So what happens when i==0? It just keeps setting the delay later and later and later by executing the code above.And since game.time.now is always < delay, i will never get set to 3.So what you need to do is to set the value of i to some other value apart from zero or three. Putting i=-1; in there works. Hope it helps! And hope this breakdown of steps undertaken helps point to ways to narrow down problems for future issues! For reference, here is the fixed create() code that you need:var bullets;var bullet;var shoot;var sprite;var bulletTimer = 0;var i = 3;var delay = 0;function create() { sprite = game.add.sprite(100, 200, 'phaser'); sprite.anchor.setTo(0.5, 0.5); sprite.update = function() { if (i==0){ delay = game.time.now + 2000; i = -1; // Problem 2: without this, delay is always > this.game.time.now, and i would always == 0 } if (game.time.now > delay) { i = 3; delay = game.time.now + 2000; // Problem 1: without this, i is always == 3. } } bullets = game.add.group(); bullets.enableBody = true; bullets.physicsBodyType = Phaser.Physics.ARCADE; bullets.createMultiple(200, 'bullet'); bullets.setAll('anchor.x', 0.5); bullets.setAll('anchor.y', 1); bullets.setAll('outOfBoundsKill', true); bullets.setAll('checkWorldBounds', true); bullets.forEach(function(enemy){ enemy.body.setSize(15, 70); }); shoot = game.input.keyboard.addKey(Phaser.Keyboard.Z);}function fireBullet() { var BULLET_SPEED = 600; var BULLET_SPACING = 10; if(i>0) { console.log(i); if (game.time.now > bulletTimer) { bullet = bullets.getFirstExists(false); if (bullet) { bullet.reset(sprite.x, sprite.y); bullet.body.velocity.x = BULLET_SPEED; bulletTimer = game.time.now + BULLET_SPACING; } i--; } }} YuShaN and drhayes 2 Link to comment Share on other sites More sharing options...
YuShaN Posted October 31, 2015 Author Share Posted October 31, 2015 @drhayes and @jmp909 have both suggested better alternatives to the way that you are currently handling this. You might want to consider them after getting it to work! Anyway, there are two problems in your code. Problem 1Your variable i is never decrementing below 3. Try putting a console.log(i); after if (i > 0) in fireBullet(). You will see that it never drops.So let's take a look at where i is ever modified. Since it's not being modified in fireBullet()'s loop, it has to be in the update() of your Sprite.There is a check for if (game.time.now > delay) { i = 3; } so it's likely in here.You will realize that if you put a console.log(delay), that delay is always zero!That's because delay is initialized to zero. And since game.time.now is always > delay, it's always going to set i=3. No other pieces of code is going to runSo what you need to do is to set the value of delay if you enter that block, so that you will not always be in it. Setting it to delay = game.time.now + 2000; works.Problem 2Now, if you run it, you will notice that firing never restarts again.This is because of the code if (i==0){ delay = game.time.now + 2000; }So what happens when i==0? It just keeps setting the delay later and later and later by executing the code above.And since game.time.now is always < delay, i will never get set to 3.So what you need to do is to set the value of i to some other value apart from zero or three. Putting i=-1; in there works. Hope it helps! And hope this breakdown of steps undertaken helps point to ways to narrow down problems for future issues! For reference, here is the fixed create() code that you need:var bullets;var bullet;var shoot;var sprite;var bulletTimer = 0;var i = 3;var delay = 0;function create() { sprite = game.add.sprite(100, 200, 'phaser'); sprite.anchor.setTo(0.5, 0.5); sprite.update = function() { if (i==0){ delay = game.time.now + 2000; i = -1; // Problem 2: without this, delay is always > this.game.time.now, and i would always == 0 } if (game.time.now > delay) { i = 3; delay = game.time.now + 2000; // Problem 1: without this, i is always == 3. } } bullets = game.add.group(); bullets.enableBody = true; bullets.physicsBodyType = Phaser.Physics.ARCADE; bullets.createMultiple(200, 'bullet'); bullets.setAll('anchor.x', 0.5); bullets.setAll('anchor.y', 1); bullets.setAll('outOfBoundsKill', true); bullets.setAll('checkWorldBounds', true); bullets.forEach(function(enemy){ enemy.body.setSize(15, 70); }); shoot = game.input.keyboard.addKey(Phaser.Keyboard.Z);}function fireBullet() { var BULLET_SPEED = 600; var BULLET_SPACING = 10; if(i>0) { console.log(i); if (game.time.now > bulletTimer) { bullet = bullets.getFirstExists(false); if (bullet) { bullet.reset(sprite.x, sprite.y); bullet.body.velocity.x = BULLET_SPEED; bulletTimer = game.time.now + BULLET_SPACING; } i--; } }}It's working now. Thank you so much. Link to comment Share on other sites More sharing options...
Recommended Posts