Cubic Bezier Generator

Design CSS easing curves visually. No server, no dependencies.

Presets

Control Points

x1
y1
x2
y2

CSS Value

cubic-bezier(0.25, 0.1, 0.25, 1)
0,01,1
Preview

Technical SEO

Expanded documentation

Cubic Bezier Generator: Engineering Precise CSS Animations

Motion design is not decoration — it is communication. A well-crafted easing curve tells the user that a modal is dismissible, that a button responds to touch, that a loading state is temporary. A poorly chosen ease-in-out applied uniformly to every transition communicates nothing but inattention. The cubic bezier generator gives you surgical control over every frame of your CSS animations.

The Mathematics of Easing Curves

A cubic Bézier curve is defined by four points: P0 (start), P1 (first control handle), P2 (second control handle), and P3 (end). In CSS cubic-bezier(), P0 is always (0, 0) and P3 is always (1, 1) — representing the start and end of both time and progress. You control only P1 and P2, each expressed as (x, y).

The parametric equations for a cubic Bézier curve are:

B(t) = (1−t)³·P0 + 3·(1−t)²·t·P1 + 3·(1−t)·t²·P2 + t³·P3

where t ∈ [0, 1]. The CSS animation engine samples this curve at each frame's time coordinate to determine progress. Because P1 and P2 can have y values outside [0, 1], the curve can overshoot — producing spring-like bounce effects that go beyond the final value before settling.

The x component of P1 and P2 must stay in [0, 1] (otherwise the function is not monotonic in time and the CSS spec disallows it). The y component has no such restriction, which is what enables elastic overshoot.

CSS Native Easing Functions vs. Custom Curves

CSS provides five named timing functions as syntactic sugar over cubic-bezier():

CSS keywordEquivalent cubic-bezier
linearcubic-bezier(0, 0, 1, 1)
easecubic-bezier(0.25, 0.1, 0.25, 1)
ease-incubic-bezier(0.42, 0, 1, 1)
ease-outcubic-bezier(0, 0, 0.58, 1)
ease-in-outcubic-bezier(0.42, 0, 0.58, 1)

These presets cover common cases, but real interfaces demand more nuance. A bottom sheet sliding up from below feels more natural with a sharp ease-out (cubic-bezier(0.16, 1, 0.3, 1)) that decelerates quickly near its target. A confirmation badge popping in benefits from gentle overshoot (cubic-bezier(0.34, 1.56, 0.64, 1)). No named function maps to these behaviours.

How to Use the Generator

Control points panel — Drag P1 (the lower handle) and P2 (the upper handle) on the SVG canvas, or type values directly into the coordinate inputs. The curve updates in real time.

Preset library — Eight curated presets cover the most common interaction patterns:

  • Snappy — fast start, smooth landing. Best for menus and drawers.
  • Elastic — mild overshoot. Best for scale or position entrances.
  • Bounce-soft — gentle deceleration with a single overshoot.
  • Anticipate — brief negative motion before the main movement, adds physicality.
  • Linear — constant velocity. Best for progress bars and loaders.

Animation preview — A dot traverses the curve in real time at the duration you set. Watch the velocity: steep sections mean fast motion, flat sections mean slow motion. The dot position on the vertical axis represents progress value (not just time), so overshoot is visible.

Copy button — Outputs the cubic-bezier(x1, y1, x2, y2) string ready to paste into any CSS property.

Where to Apply Custom Easing

/* Slide-in panel */
.panel {
  transform: translateX(-100%);
  transition: transform 320ms cubic-bezier(0.16, 1, 0.3, 1);
}
.panel.open {
  transform: translateX(0);
}

/* Scale entrance for dialogs */
.dialog {
  transform: scale(0.96);
  opacity: 0;
  transition:
    transform 200ms cubic-bezier(0.34, 1.56, 0.64, 1),
    opacity   150ms ease-out;
}
.dialog.visible {
  transform: scale(1);
  opacity: 1;
}

A key engineering practice: use different curves for enter and exit. Entrances should be fast-in (ease-out family) — the UI element rushes to the user. Exits should be fast-out (ease-in family) — the element retreats quickly so it does not block the next interaction.

CSS Animation vs. Web Animations API

cubic-bezier() works identically in both the CSS transition/animation syntax and the Web Animations API:

element.animate(
  [{ transform: 'translateY(20px)', opacity: 0 },
   { transform: 'translateY(0)',    opacity: 1 }],
  {
    duration: 300,
    easing: 'cubic-bezier(0.16, 1, 0.3, 1)',
    fill: 'forwards',
  }
);

The WAAPI gives you programmatic control (play, pause, reverse, finish) without toggling CSS classes. For orchestrated sequences — staggered list items, multi-step transitions — it is far more maintainable than layered CSS delays.

Best Practices for Production Motion

Match duration to distance. A tooltip appearing near the cursor needs only 150–180 ms. A full-screen modal entrance can afford 280–350 ms. Long durations with linear curves feel sluggish; short durations with aggressive easing feel jarring.

Respect prefers-reduced-motion. Always wrap non-essential animations:

@media (prefers-reduced-motion: reduce) {
  * { transition-duration: 0.01ms !important; animation-duration: 0.01ms !important; }
}

Do not animate layout properties. width, height, padding, top, and left trigger layout recalculation on every frame. Stick to transform and opacity, which are composited by the GPU and run on a separate thread.

Test on real devices. The browser DevTools animation inspector and throttled CPU mode reveal jank that is invisible at full speed on a development machine.

Comparing Easing Tools

ToolCustom curveLive previewCopy CSSOffline
This generator✓ (browser)
Chrome DevToolsManualRequires DevTools
cubic-bezier.com
Framer MotionVia code onlyVia renderingN/ARequires install

The developer utility here combines the key features in a single zero-setup interface, with the added benefit of curated presets that reflect real-world animation patterns rather than abstract demonstrations.