How would I do this? I would like bullets that fire on a click, and go from the player to wherever the mouse was clicked… I have a method, but the speed of the bullet varies on how far away from the player you click, which is not desirable.
How can I make bullets go toward the mouse?
You need to get the direction from the player to the mouse, which can easily be done with FP.angle:
var angle:int = FP.angle(player.x, player.y, world.mouseX, world.mouseY)
Then with that angle, you can calculate the the x and y components of the bullet’s velocity:
x += BULLET_SPEED * Math.cos(angle * FP.RAD) * FP.elapsed
y += BULLET_SPEED * Math.sin(angle * FP.RAD) * FP.elapsed
Make sure you replace BULLET_SPEED with your desired speed.
To convert from degrees (which FP.angle returns) to radians (which you need to compute the x/y components) you have to multiply the degrees by PI/180. FP.RAD is a handy shortcut constant which equals PI/180.
Also, it might be useful to note that game items like bullets usually have a constant speed and trajectory that do not change during their lifetime, so to prevent unneeded calculation, you would calculate your x / y values once on instantiation and store them in member variable(s). So your update code may look like:
x += _velocityX;
y += _velocityY;
Thanks for pointing that out, added it now!
Oh, and what does an underscore before a variable mean?
The underscore means nothing, most programmers seem to use it to denote a member variable. I don’t really know if this is a standard or not but it usually seems the case. So, in example, a Bullet class may look something like this:
package
{
import net.flashpunk.Entity;
import net.flashpunk.FP;
import net.flashpunk.graphics.Image;
public class Bullet extends Entity
{
// constants are usually all uppercase
protected const BULLET_SPEED:Number = 100;
// member variables are usually preceeded with an underscore
protected var _velocityX:Number;
protected var _velocityY:Number;
public function Bullet()
{
// set graphic(s) here,
// take care of positioning and rotation on init()
}
// handy function to have for items that are constantly recycled
// (object pooling)
public function init(x:Number, y:Number, angle:Number):Bullet
{
this.x = x;
this.y = y;
_velocityX = BULLET_SPEED * Math.cos(angle * FP.RAD);
_velocityY = BULLET_SPEED * Math.sin(angle * FP.RAD);
Image(graphic).angle = angle;
return this;
}
override public function update():void
{
x += _velocityX * FP.elapsed;
y += _velocityY * FP.elapsed;
}
}
}
…
I was gonna post some optimisation tips here. Then I read MakotoNinja’s post.
I’m a dork.