I’ve noticed when talking to various Unity users (and browsing the forums) there seems to be a bit of confusion about the purpose of the Lerp methods, and how and when to use them. This isn’t too surprising given that the documentation on Lerp is bizarre (it uses Time.time as a *t *value, something that by the end of this tutorial you’d know is somewhat odd). I’ve also supplied a Unity webplayer below to visualize how Lerp works.

*Lerp *stands for **L**in**e**a**r **Inter**p**olation. Unity has a family of Lerp methods that all function pretty much the same way but have different applications: Mathf.Lerp, Vector3.Lerp, Color.Lerp, and Quaternion.Lerp.

Lerp essentially lets you pick two values, a *from *and *to *value, and then select a *t *value that returns an interpolation between the from and to. The *t *value is clamped between 0 and 1 (regardless of what you put in the method as a parameter) so you can think of it like a percentage; 0.4 is 40%, 0.6 is 60%, and so on. This leads to the idea of thinking that when you run Lerp on a *from *and *to *values, you will get a value *t *percent between the two. Lets look at some examples.

Mathf.Lerp(0, 100, 0.5f)

This is trivial. We can read this as asking Lerp to give us the value 50% between 0 and 100. This will return 50.

Mathf.Lerp(50, 80, 0.3f)

This will return the value 30% between 50 and 80, which is 59. To make Lerp’s inner workings less opaque, you can actually verify these values using simple arithmetic. You really just need to get the range between the two values, multiply that by the *t *value and then add that to the *from *value. For the example above you would do.

range : 80 - 50 = 30 distance by t value : 30 * 0.3 = 9 interpolated value : 50 + 9 = 59

(The above is in pseudocode and not C#)

As stated above, the other Lerp methods work in pretty much the same way. Vector3.Lerp has you select two Vector3s for the *from *and *to *values, Color.Lerp uses Colors (duh), Quaternion.Lerp, rotations.

You don’t always have the luxury of having the *t *value easily supplied for you. Often when using Lerp you are attempting to relate two different values to each other. An example of this would be simulating camera shake when a player is nearby a cannon firing: the further the player is away from the cannon, the less the camera shakes. Therefore there is a clear relation between the *distance *the player is from the cannon and the *magnitude *of the camera shake. (This example is based on the cannons from the Mario 64 HD project I built, specifically the FiringCannon class.)

Unity supplies a method named InverseLerp. InverseLerp takes a *from *and *to *parameter, and then a *value *parameter which should be somewhere between *from *and *to. *I’ll do an example before we try it out on the camera shake problem stated above.

Mathf.InverseLerp(30, 60, 45);

We can read this as “how far is 45 between 30 and 60?” This will return 0.5, as 45 is halfway between 30 and 60.

For our cannon, lets assume we have some CameraShake(float magnitude) method that we will use. We will state that the maximum shake magnitude is 20, and the minimum is 0. We will also say that the maximum distance the player can be from the cannon and still feel the shake is 50, and the minimum 0. Let’s solve this.

float t = Mathf.InverseLerp(0, 50, Vector3.Distance(cannon.position, player.position));

Where *cannon *and *player *are Transforms. This will give us a *t *value that is 0 when the player is immediately beside the cannon, and 1 when the player’s distance is 50 or greater. We now need to get the proper shake magnitude.

Mathf.Lerp(20, 0, t);

You’ll notice that the *from *value is larger than the *to *value. This perfectly acceptable and is done because we want the shake magnitude to be a maximum when the player’s distance is 0 (and the *t *value is 0) and at a minimum when the player’s distance is 50 or greater (and the *t *value is 1). If for whatever reason you need the *from *value to be the smaller of the two, you can always invert *t *by subtracting it from 1.

I’ve added a demo below showing Lerping between two values (Mathf.Lerp), positions (Vector3.Lerp) and colors (Color.Lerp), with the *t *value controlled by the slider. Hopefully this will clear up how Lerp works and has demonstrated how useful a method it is.

Thank you Roystan… thank you so much, I really appreciate the hard work with your Mario 64-projekt. Much nostalgica, Very wow! I blogged about your website and linked to the game so people in Sweden also could be notified about it. I also read some of your blog-posts… Very interesting! You sir have a new follower 🙂 Have a great day! http://nerdpappan.se/nostalgi-varning-spela-mario-64-via-webblasaren

Thank you very much! Because of a tutorial (which was also wrong!) i always thought the time value determines how long it takes to lerp from a to b. So because of that i never understood the results when using the function! Keep up the work! (Your Mario 64 project looks amazing!)

Thank you very much Roystan for the great article, I knew how Lerp worked but didn’t know InverseLerp and also how elegantly this can be to used ot count damage.

I always counted it manually 😉

Like

float distanceToTarget = (target.position – player.position).magnitude;

float damageRange = maxDamage – minDamage;

float ratio = 1f – distanceToTarget / weaponRange;

ratio = Mathf.Max(0f, ratio);

var damage = ratio * damageRange + minWeaponDamage;