2D - Mortar fire projectile arc & moving target

So I am creating a tower defense game in 2D, though generally trying to go for a 2.5D look and feel to a degree.
I have a cannon/mortar tower that I am trying to fire the bomb and have it arc in the air like it would in real life (doesn’t have to be exact). However I cannot seem to get it to work correctly no matter how much I search or what I try.

  • First things first I am not currently using physics, I am not opposed to it by any means but when I had tried before my objects just fell through the bottom of the screen.

  • My other towers use Update and just move the transform position of the projectile to the target. My archer tower even has a slight arc in it’s projectiles but it doesn’t look the best honestly.

  • I can calculate where my target will be in X amount of seconds, so if I could calculate the travel time of the bomb then I could get the exact location. But since the target is moving and their distance from the mortar could drastically change in X seconds…how do I predict travel time when I won’t know the exact distance? I assume I have to fix the travel time of the projectile for every shot?

The script in the below link from Stephan-B comes pretty close (except for rotation which is meant for 3D space) but I run into issues due to #3 above.

Here is an example of my turret and potential radius it can fire in:

And if you would like an example of what I am looking for in the projectile motion, you can look at the cannon/mortar tower in the below kingdom rush game link. You will notice that the projectile lobs in any direction (even looks like its coming towards you at times when the creep is below the turret) and always seems to find its target.
http://kingdomrush.com/play/
Any help, pointers, examples would be greatly appreciated.

You can fake it very easily using an animation curve that acts as the height offset while lerping towards the target.


(Ignore the sprites, all I had loaded in my project 8D)

public class ArcFire : MonoBehaviour
{
   public AnimationCurve curve;
   public Transform target;

   private Vector3 start;
   private Coroutine coroutine;

   private void Awake()
   {
       start = transform.position;         
   }

   private void Update()
   {
       if(coroutine == null)
       {
           if(Input.GetKeyDown(KeyCode.Space) == true)
           {
               coroutine = StartCoroutine(Curve());
           }
       }
   }

   IEnumerator Curve()
   {
       float duration = 0.40f;
       float time = 0f;

       Vector3 end = target.position - (target.forward * 0.55f); // lead the target a bit to account for travel time, your math will vary
     
       while(time < duration)
       {
           time += Time.deltaTime;

           float linearT = time / duration;
           float heightT = curve.Evaluate(linearT);

           float height = Mathf.Lerp(0f, 3.0f, heightT); // change 3 to however tall you want the arc to be

           transform.position = Vector2.Lerp(start, end, linearT) + new Vector2(0f, height);

           yield return null;
       }

       // impact

       coroutine = null;
   }
}

If you’re unfamiliar with animation curves, here’s a primer I wrote a while back.

7 Likes

That’s awesome. I enjoyed reading your primer, too. ~ friendly passerby

1 Like

You are amazing! I had seen animation curves references in countless searches but none of them took the time to explain anything about them. And your primer was super helpful so thank you, I got it working like a charm.
I made some minor modifications for the target position since I can calculate their position at a particular point in time and am also going to use it for the archer shoot animation too!

Thanks again

1 Like

very nice

i need to replicate the movement of the one around the zero, how do you made it?

Grozz gave you the entire script above as well as a primer on animation curves.

Assuming you have worked through all of that material already yourself (right?), what part are you having trouble with?

ALSO: start a fresh thread for new problems please.

I understood that the provided code is about the emoticon curve. Reading the code it seems confirmed…
I would like to make the circular movement of one sprite around another that stay stationary. I managed to do that with RotateAround but doesn’t work well as the one in the gif.