GoByte Skills Episode 21 of 27, track Motion libraries (3 of 3)

Easing: a function from progress to progress

GoByte Skills #21: an ease is just a function from progress to progress. Same distance, same duration, four curves, and at halftime one of them has already overshot the finish line. On purpose.

Arthur is one of GoByte's characters. This post was drafted by AI agents in Arthur's voice, then fact checked, run and edited by the GoByte team.

Back to top

An ease maps linear progress to eased progress, so the same distance can feel snappy or heavy.

Animation for GoByte Skills #21: One dot travels the same distance with four different curves.
Transcript

Four dots race the same distance in the same time with four eases and freeze at half time, showing how far each curve has carried them, one already past the line.

const { gsap } = require("gsap");

const names = ["none", "power2.in",
  "power2.out", "back.out"];
for (const name of names) {
  const ease = gsap.parseEase(name);
  const ys = [0, 0.25, 0.5, 0.75, 1]
    .map((p) => ease(p).toFixed(3));
  console.log(name.padEnd(10), ys.join(" "));
}
none       0.000 0.250 0.500 0.750 1.000
power2.in  0.000 0.016 0.125 0.422 1.000
power2.out 0.000 0.578 0.875 0.984 1.000
back.out   0.000 0.817 1.088 1.064 1.000

The mechanism#

A tween's clock never runs faster or slower. Each frame it computes linear progress p = elapsed / duration and writes from + (to - from) * ease(p). The ease is a plain function with one contract: ease(0) = 0 and ease(1) = 1. Duration and distance are fixed; the ease only decides where on the path you are at each instant. Speed is the slope of that curve.

Reading the table#

GSAP's power2 is cubic, not quadratic (power1 is quad, power2 cubic, power3 quartic). Halfway through a 1 second tween, power2.in has covered 12.5% of the distance and power2.out 87.5%. Same half second, opposite feelings. .out starts fast and lands soft, so it reads as responsive. .in starts slow and leaves fast, so it reads as heavy, like something with mass getting going.

Where it bends#

Nothing keeps the output inside [0, 1]. back.out peaks near 1.10 at p = 0.58, so a tween from 0 to 100 passes 110 before it settles. That overshoot is the point, but a property with a ceiling ignores it: opacity clamps at 1. steps(4) is a staircase, valid and discontinuous. And any function works, ease: (p) => p * p included: GSAP just calls it every frame, so a custom ease is one line you can unit test.

Rule of thumb#

Pick the curve by how the object should feel when it stops, then keep the duration. Linear motion is perfectly honest, which is exactly why it looks like a screensaver.

Report a mistake

Your product here? Partner with us

Back to top

Discussion

No comments yet. Signed in GoByte members with a verified e-mail can join. Community guidelines

Reading is open to everyone. Commenting and voting need a GoByte account with a verified e-mail.