Skip to content

Cubic Bezier Generator for CSS Easing

Set two control points, see the easing curve drawn next to a ball that moves with it, and copy the cubic-bezier() transition rule in longhand and shorthand.

Runs in your browserFree, no sign-upLast reviewed

Settings

Pick a preset to load its control values, then fine-tune them below.

Results update automatically as you type.

Curve and live animation

CSS

.element {
  transition-property: transform;
  transition-duration: 1.4s;
  transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);
}

/* Shorthand */
.element {
  transition: transform 1.4s cubic-bezier(0.25, 0.1, 0.25, 1);
}

Values

Timing function
cubic-bezier(0.25, 0.1, 0.25, 1)
Control point 1
0.25, 0.1
Control point 2
0.25, 1
Character
Stays within range

Quick answers

What do the four numbers in cubic-bezier() mean?
They are the coordinates of two control points: cubic-bezier(x1, y1, x2, y2). The first pair shapes how the motion starts and the second pair how it ends. x is time and y is progress, both running from 0 at the start to 1 at the end.
What is the cubic-bezier for ease-in-out?
cubic-bezier(0.42, 0, 0.58, 1). The other CSS keywords are ease = cubic-bezier(0.25, 0.1, 0.25, 1), ease-in = cubic-bezier(0.42, 0, 1, 1), ease-out = cubic-bezier(0, 0, 0.58, 1) and linear = cubic-bezier(0, 0, 1, 1).
Can cubic-bezier values be negative or greater than 1?
The y values can. A y above 1 makes the animation overshoot its end value and settle back; a y below 0 makes it pull backward before moving forward. The x values must stay between 0 and 1, otherwise the whole declaration is invalid and ignored.
How do I make a bounce effect with cubic-bezier?
Use a y value above 1 for a single overshoot, for example cubic-bezier(0.34, 1.56, 0.64, 1). One cubic bezier can overshoot once at most at each end. A repeated bounce or elastic wobble needs @keyframes or the linear() easing function.
Which easing should I use for UI animations?
For elements entering or responding to a click, use a curve that starts fast and slows down, such as ease-out or cubic-bezier(0.22, 1, 0.36, 1). For elements leaving, an ease-in curve works. Keep ease-in-out for movement between two on-screen positions.
Is cubic-bezier used for animations as well as transitions?
Yes. The same function is a valid value for transition-timing-function and animation-timing-function. In a keyframe animation it applies to each interval between keyframes, not once across the whole animation.

Why use Cubic Bezier Generator

cubic-bezier(x1, y1, x2, y2) describes how a CSS transition or animation spreads its change over time. The curve always runs from (0, 0) to (1, 1); the four numbers place the two control points that bend it. The horizontal axis is time and the vertical axis is progress, so a steep stretch is fast and a flat stretch is slow. This generator has a slider for each of the four numbers, six presets, a Duration from 0.2 to 4 seconds and a choice of property. It draws the curve, loops a ball back and forth with that timing, and reports from the y values whether the curve overshoots, pulls back first or stays within range.

Cubic-bezier values for ease, ease-in, ease-out and ease-in-out

The first six rows are the options in Start from, with the timing function the tool outputs for each.

Preset or keywordTiming functionCharacter reported
easecubic-bezier(0.25, 0.1, 0.25, 1)Stays within range
ease-incubic-bezier(0.42, 0, 1, 1)Stays within range
ease-outcubic-bezier(0, 0, 0.58, 1)Stays within range
ease-in-outcubic-bezier(0.42, 0, 0.58, 1)Stays within range
Back out (overshoot)cubic-bezier(0.34, 1.56, 0.64, 1)Overshoots past the end
Anticipate (undershoot)cubic-bezier(0.36, -0.4, 0.66, -0.2)Pulls back before starting
linear (set with the sliders)cubic-bezier(0, 0, 1, 1)Stays within range

ease is the default timing function when a transition or animation does not name one.

Popular easing curves to enter with the sliders

Widely used named curves and the slider positions that reproduce them. The Character column is what the tool reports for those values.

CurveP1 x, P1 y, P2 x, P2 yFeelCharacter
Ease out cubic0.33, 1, 0.68, 1Quick start, gentle stopStays within range
Ease out quint0.22, 1, 0.36, 1Very fast start, long settleStays within range
Ease out expo0.16, 1, 0.3, 1Snaps most of the way, then glidesStays within range
Ease in cubic0.32, 0, 0.67, 0Slow start, fast finishStays within range
Ease in-out cubic0.65, 0, 0.35, 1Symmetrical with a strong middleStays within range
Material standard0.4, 0, 0.2, 1Brief acceleration, longer decelerationStays within range
Ease in back0.36, 0, 0.66, -0.56Dips backward, then accelerates awayPulls back before starting
Ease out back0.34, 1.56, 0.64, 1Passes the target and settlesOvershoots past the end
Ease in-out back0.68, -0.6, 0.32, 1.6Dips at the start and overshoots at the endOvershoots past the end

When a curve both dips below 0 and rises above 1, the tool reports the overshoot.

Generated transition CSS for three curves

Standard UI transition at 300ms

Start from Custom; P1 0.4, 0; P2 0.2, 1; Duration 0.3; Property transform

transition: transform 0.3s cubic-bezier(0.4, 0, 0.2, 1);

Fade with a soft landing

Start from Custom; P1 0.22, 1; P2 0.36, 1; Duration 0.5; Property opacity

transition: opacity 0.5s cubic-bezier(0.22, 1, 0.36, 1);

Springy toggle

Start from Custom; P1 0.68, -0.6; P2 0.32, 1.6; Duration 0.6; Property all

transition: all 0.6s cubic-bezier(0.68, -0.6, 0.32, 1.6);

With an overshooting curve, animate transform. On properties that clamp, such as opacity above 1, the overshoot is not visible.

Default output when the page loads

Start from Custom; P1 0.25, 0.1; P2 0.25, 1; Duration 1.4; Property transform

transition-property: transform; transition-duration: 1.4s; transition-timing-function: cubic-bezier(0.25, 0.1, 0.25, 1);

These slider positions are the same curve as the ease keyword.

How to read an easing curve

Read the graph from the bottom-left corner to the top-right. Moving right is time passing; moving up is the property getting closer to its final value. The slope at any moment is the speed: where the line climbs steeply the element is moving fast, and where it runs nearly flat the element is barely changing.

P1 is attached to the start point, so it controls the launch. Pull P1 to the right along the bottom edge (a larger x with y at 0) and the curve hugs the floor at first, which is a slow start. Lift P1 upward and the motion begins quickly. P2 is attached to the end point and controls the arrival in the same way: P2 with y at 1 and a small x gives a long, gentle stop.

When a control point's y leaves the 0 to 1 range the curve itself can leave the box. Above the top edge the value goes past its target and comes back; below the bottom edge it first travels in the wrong direction. The y sliders here accept values from -1 to 2, which covers the usual back and anticipate curves. The graph leaves only a narrow margin around the 0 to 1 box, about 0.13 of its height, so a control point further out than that is cut off at the edge of the picture. That includes the 1.56 of the Back out preset. The moving ball and the copied CSS still use the full value.

What the generator does and does not do

  • The control points are set with sliders in steps of 0.01. The handles on the graph are not draggable.
  • While a preset is selected in Start from, its values are used and the four P sliders have no effect on the output. Switch back to Custom to use the sliders.
  • x values are held between 0 and 1, so the output is always a valid timing function.
  • Values are written to at most three decimal places.
  • Character is decided from the two y values alone: any y above 1 reports an overshoot and any y below 0 reports a pull back. It is not measured from the plotted curve, so check the graph and the ball for borderline values.
  • The CSS is a transition rule on .element. For a keyframe animation, copy the cubic-bezier() part into animation-timing-function.
  • steps(), linear() with multiple stops and spring physics are outside what a single cubic bezier can describe and are not generated.

Step by step

  1. 1

    Leave Start from on Custom (use the sliders) to shape your own curve, or pick a preset such as ease-out or Back out (overshoot) to use its values as they are.

  2. 2

    With Custom selected, move P1 x and P1 y to shape the start of the motion and P2 x and P2 y to shape the end. The x sliders run from 0 to 1 and the y sliders from -1 to 2.

  3. 3

    Set Duration and watch the ball in Curve and live animation. It runs forward and back, so you see the curve in both directions.

  4. 4

    Choose transform, opacity or all in Property to animate so the copied rule names the right property.

  5. 5

    Copy or download the CSS panel. It contains the three longhand transition properties and the one-line shorthand.

Frequently asked questions

What is the difference between ease and ease-in-out?
Both start and end gently, but ease is lopsided: it accelerates quickly and spends most of its time slowing down. ease-in-out is symmetrical, with equal acceleration and deceleration. ease feels more responsive for interface changes; ease-in-out suits looping or back-and-forth movement.
Why does my overshoot curve look clipped on some properties?
Some properties cannot go beyond their limits. Opacity stops at 1 and color channels are clamped, so the overshoot portion is flattened. Transforms, positions and sizes have no such ceiling and show the full motion.
How long should a transition last?
Small interface changes such as hovers, toggles and fades usually sit between 150 and 300 milliseconds. Larger movements across the screen can take 300 to 500 milliseconds. The more dramatic the curve, the shorter the duration should be, because a slow overshoot reads as a glitch.
Can I use different easing for opening and closing?
Yes. The timing function on the state being entered is the one used. Put a decelerating curve on the open state's rule and an accelerating one on the base rule, and the element eases out when it opens and eases in when it closes.
Does cubic-bezier affect performance?
No. The curve only changes how progress is calculated for each frame. Smoothness depends on which property is animated: transform and opacity can be handled by the compositor, while properties that trigger layout, such as width or top, cost more.
How do I respect users who prefer reduced motion?
Wrap expressive transitions in @media (prefers-reduced-motion: no-preference), or override them inside @media (prefers-reduced-motion: reduce) with a short fade or no transition. Overshoot and bounce are the kinds of motion that setting is meant to limit.
Can I paste values from a design tool?
Yes, if the tool gives four bezier numbers. Enter them in the order x1, y1, x2, y2 using P1 x, P1 y, P2 x and P2 y. The y sliders accept values from -1 to 2, so a curve with a more extreme overshoot has to be typed into the copied CSS by hand.

Looking for something else? Browse all css tools or see every tool.