I'm working on a shmup game and have an enemy that shoots a bullet at the player. I want the bullet to keep moving towards the player's x/y even after the player has moved. So keep the object move towards a single point.
If anyone has a method or math they can share, I'd appreciate it.
I guess this type of thing is great for all sorts of purposes, not just bullets. :)
This is a cartridge who explains how to draw a line (from one start point to an end point). You can use the enemy position as start point and the target location as end point. You may have to adapt the looping process to move step by step. In hope this help.
If I have some time in the next coming days, I will make a sample with a lot of enemies firing at a moving target. This is a good subject. Thanks for asking :-)
Actually, you don't want the bullet to hit the player for sure, do you? So, the bullet has a moving vector. With every step, you'll calculate the vector between the bullet and the player and you add a fraction of this to the bullets moving vector. This should do the trick and the fraction says, how hard it is to dodge the bullet.
Yes I agree with SunSailor on the fact that you probably don't want the bullet to follow the player perfectly. What you want is a system based on angles and which uses linear interpolation (lerp).
Here is how I would go about it:
Each bullet has its current angle stored.
Each frame, you will calculate each bullet's new angle towards the player, using atan2().
Then, you will update its angle with an angle lerp (which is kinda tricky but best).
And finally you will move the bullet with cos() and sin()!
And here is a code sample!
--I'm assuming you are storing the bullet's position and angle in an array function update_bullet(bullet) --first, the new angle toward the player: local newangle = atan2(player.x-bullet.x, player.y-bullet.y) --then the lerp bullet.angle = angle_lerp(bullet.angle, newangle, 0.1) --then you move the bullet bullet.x += bullet.speed * cos(bullet.angle) bullet.y += bullet.speed * sin(bullet.angle) end function angle_lerp(angle1, angle2, t) angle1=angle1%1 angle2=angle2%1 if abs(angle1-angle2)>0.5 then if angle1>angle2 then angle2+=1 else angle1+=1 end end return ((1-t)*angle1+t*angle2)%1 end
I hope this helps! ;D
Still speaking in vectors - (angle and velocity) if you start slow, turn slow and accelerate constantly, you'll have a homing missile that flies by if you wait and step aside.
If you turn gradually and cap the speed you get a smarter projectile that can achieve orbit around its target.
If you keep it slowish and just aim dead at the player every update, you get a threat that has to be dealt with directly. (by shooting it or running it into an obstacle)
Cool, thanks for all the tips and snippets, everyone. I'll check out those methods and see how they work. I figure a "homing" method will work the same for a fixed point too, just the target x/y doesn't changing.
And just because I'm sure it will come up, is there a nice way to angle sprites the same way? So if there's a missile sprite that I want to angle along the path as it moves.
I don't see a parameter option in the spr() function for angle, just coordinates
Best way to have rotated sprites is to have them rotated in the sprite sheet before having to use them. You can make your own functions to rotate the sprite using trigonometry but they will become very heavy very fast if you use them multiple times every frame.
I took Tarsevol_Dog's methods and made a quick little cart to show the example. You can move the green dot with the arrows and the yellow bullet will follow.
[Please log in to post a comment]