npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@vysmo/easings

v0.2.0

Published

Curated easing catalog (40+ named curves) + parametric builders (spring, bezier, wiggle, rough, anticipate) + composition modifiers (chain, reverse, mirror, yoyo, blend, slice). Pure math, zero deps. CSS export via toCSSLinear / toCSSBezier; reduced-motio

Downloads

370

Readme

@vysmo/easings

22 easing families (linear, power1–4, sine, circ, expo, smooth, back, elastic, bounce, steps, bezier, spring, rough, wiggle, slow, anticipate, expoScale, gravity, breathe) + composition modifiers (chain, reverse, mirror, yoyo, blend, slice). Pure math, zero deps. CSS export via toCSSLinear / toCSSBezier; reduced-motion helpers; GSAP-style string parser.

Live curves explorer · Source

Install

pnpm add @vysmo/easings

Quick start

In JavaScript — pass any easing as the ease option:

import { animate } from "@vysmo/animations";
import { power2Out } from "@vysmo/easings";

animate({
  from: 0,
  to: 1,
  duration: 600,
  ease: power2Out,
  onUpdate: (v) => element.style.opacity = String(v),
});

In CSS — bake any easing into a linear() string:

import { toCSSLinear } from "@vysmo/easings/css";
import { spring } from "@vysmo/easings";

const ease = spring.with({ stiffness: 220, damping: 18 });

document.documentElement.style.setProperty(
  "--ease-pop",
  toCSSLinear(ease, 32),
);

Every export is just a (t: number) => number (an EasingFn). Use with animate(), your own rAF loop, baked to CSS, or anything that takes an easing function. Parametric easings like spring.with({ ... }) and bezier(0.25, 0.1, 0.25, 1) return the same shape — see the catalog below for every option.

Catalog

Every shipped easing with its variants and parameters. The catalog mirrors the playground at vysmo.com/easings/docs#catalog. Categorisation tracks the authoring shape — Core (constant curves), Parametric (curves with .with({ ... })), Builder (factory functions).

Core

linear

No easing — constant velocity.

Export: linear

power1

Quadratic (t²). Mildest power curve.

Variants: power1In · power1Out · power1InOut

power2 (cubic)

Cubic (t³). Workhorse default — CSS's ease is close to power2.out.

Variants: power2In · power2Out · power2InOut

power3 (quart)

Quartic (t⁴). More pronounced easing.

Variants: power3In · power3Out · power3InOut

power4 (quint)

Quintic (t⁵). Dramatic acceleration.

Variants: power4In · power4Out · power4InOut

sine

Sinusoidal (cos/sin-based). Soft and natural.

Variants: sineIn · sineOut · sineInOut

circ

Circular arc. Sharp at one end, flat at the other.

Variants: circIn · circOut · circInOut

expo

Exponential (2^). Extreme — near-zero until the last moments, or vice versa.

Variants: expoIn · expoOut · expoInOut

smooth

Hermite smoothstep (3t² - 2t³). Zero velocity at both endpoints — smoother joins than power2.inOut for chained animations.

Variants: smoothIn · smoothOut · smoothInOut

Parametric

back

Overshoots the target then returns. Classic 'pull-back' motion.

Variants: backIn · backOut · backInOut

| Prop | Type | Default | Values | |---|---|---|---| | overshoot | number | 1.70158 | 0 – 5, step 0.01 |

elastic

Spring-like oscillation. Two knobs: amplitude (peak height) and period (frequency).

Variants: elasticIn · elasticOut · elasticInOut

| Prop | Type | Default | Values | |---|---|---|---| | amplitude | number | 1 | 0.1 – 5, step 0.01 | | period | number | 0.3 | 0.05 – 1, step 0.01 |

bounce

Ball-drop pattern. Four decaying bounces.

Variants: bounceIn · bounceOut · bounceInOut

steps

Discrete staircase. CSS-compatible step positions.

Export: steps

| Prop | Type | Default | Values | |---|---|---|---| | count | number | 5 | 1 – 30, step 1 | | position | enum | end | end · start · none |

Builder

bezier

CSS cubic-bezier. Paste a cubic-bezier() value from CSS or design tools.

Export: bezier

| Prop | Type | Default | Values | |---|---|---|---| | p1x | number | 0.42 | 0 – 1, step 0.01 | | p1y | number | 0 | -2 – 2, step 0.01 | | p2x | number | 0.58 | 0 – 1, step 0.01 | | p2y | number | 1 | -2 – 2, step 0.01 |

spring

Physics-based spring. Stiffness × damping × mass = feel.

Export: spring

| Prop | Type | Default | Values | |---|---|---|---| | stiffness | number | 170 | 10 – 1000, step 5 | | damping | number | 26 | 1 – 100, step 1 | | mass | number | 1 | 0.1 – 10, step 0.1 | | velocity | number | 0 | -20 – 20, step 0.5 |

rough

Jittery noise layered on a base curve. Great for gritty / handheld feel.

Export: rough

| Prop | Type | Default | Values | |---|---|---|---| | strength | number | 0.15 | 0 – 0.5, step 0.01 | | points | number | 20 | 5 – 60, step 1 | | taper | enum | both | none · in · out · both | | seed | number | 42 | 1 – 999, step 1 |

wiggle

Oscillates between -1 and 1 across [0, 1]. For shake / vibration effects.

Export: wiggle

| Prop | Type | Default | Values | |---|---|---|---| | wiggles | number | 10 | 1 – 30, step 1 | | type | enum | easeOut | easeOut · easeInOut · anticipate · uniform |

slow

Linear middle section flanked by power-eased edges. For slow-motion feel.

Export: slow

| Prop | Type | Default | Values | |---|---|---|---| | linearRatio | number | 0.7 | 0 – 1, step 0.01 | | power | number | 0.7 | 0 – 5, step 0.1 |

anticipate

Character-animation wind-up: dips backward (in), overshoots past target (out), or both (inOut). Framer Motion style.

Variants: anticipateIn · anticipateOut · anticipateInOut

| Prop | Type | Default | Values | |---|---|---|---| | overshoot | number | 1.525 | 0 – 5, step 0.01 |

expoScale

Maps [0, 1] for scale animations crossing large ratios (e.g. 0.1→100) so motion feels even.

Export: expoScale

| Prop | Type | Default | Values | |---|---|---|---| | startScale | number | 1 | 0.01 – 100, step 0.1 | | endScale | number | 100 | 0.01 – 1000, step 1 |

gravity

Continuously parameterised power-in. weight=0 floats (linear), weight=1 ≈ Earth fall (power2.in), higher = leaden. One knob instead of picking between named power curves.

Export: gravity

| Prop | Type | Default | Values | |---|---|---|---| | weight | number | 1 | 0 – 3, step 0.05 |

breathe

Continuous oscillation in [0, 1]. cycles=0.5 = single inhale (0 → 1). cycles=1 = inhale + exhale. For idle / ambient animations on opacity, scale, anything in [0, 1].

Export: breathe

| Prop | Type | Default | Values | |---|---|---|---| | cycles | number | 1 | 0.5 – 8, step 0.5 |

Spring presets shipped: gentleSpring, wobblySpring, stiffSpring, slowSpring, molassesSpring — all built on spring.with(...). The power family also exposes GSAP-compatible aliases: quadIn/Out/InOut, cubicIn/Out/InOut, quartIn/Out/InOut, quintIn/Out/InOut.

Composition modifiers

import {
  reverse, mirror, yoyo, chain, blend, slice,
  power2Out, sineInOut, bounceOut,
} from "@vysmo/easings";

reverse(power2Out);                  // play it backwards
mirror(power2Out);                   // half forward, half reversed
yoyo(sineInOut);                     // out then back — one full oscillation
blend(power2Out, sineInOut, 0.5);    // 50/50 mix at every t
slice(power2Out, 0.2, 0.8);          // use only the middle 60% of the curve

// chain takes an array of segments; each segment owns its own ease + duration.
chain([
  { ease: power2Out, duration: 0.4 },
  { ease: sineInOut, duration: 0.4 },
  { ease: bounceOut, duration: 0.2 },
]);

All modifiers return a fresh EasingFn — composable, side-effect-free.

CSS export

import { toCSSLinear, toCSSBezier, toCSSKeyframes, spring } from "@vysmo/easings";

// CSS `linear()` function — sample any EasingFn into a CSS-compatible curve.
// Second arg is the sample count (positional; default 40).
const css = toCSSLinear(spring.with({ stiffness: 100, damping: 10 }), 24);
// → "linear(0, 0.0123 4.17%, …)"

// Cubic-bezier control points → CSS cubic-bezier() exactly.
toCSSBezier(0.25, 0.1, 0.25, 1);
// → "cubic-bezier(0.25, 0.1, 0.25, 1)"

// Sample as @keyframes percentages for full-fidelity CSS animations.
// Signature: (name, property, valueForProgress, ease, samples?)
toCSSKeyframes(
  "pop",
  "transform",
  (p) => `scale(${1 + p * 0.5})`,
  spring.with({ stiffness: 200 }),
);

Reduced-motion helpers

import { prefersReducedMotion, respectReducedMotion, power2Out, linear } from "@vysmo/easings";

const ease = respectReducedMotion(power2Out, linear);
// → returns linear when prefers-reduced-motion is set, power2Out otherwise

if (prefersReducedMotion()) { /* skip the animation entirely */ }

GSAP-style string parser

import { parseEasing } from "@vysmo/easings/parse";

parseEasing("power2.out");                       // → power2Out
parseEasing("back.out(2)");                       // → backOut.with({ overshoot: 2 })
parseEasing("elastic.out(1.2, 0.4)");             // → elasticOut.with({ amplitude, period })
parseEasing("steps(5, start)");                   // → steps(5, "start")
parseEasing("cubic-bezier(0.42, 0, 0.58, 1)");    // → bezier(0.42, 0, 0.58, 1)

Useful when easings come from data (presets, JSON, AI agents, etc.) rather than source code.

Defining your own

import { defineEasing, defineParametricEasing } from "@vysmo/easings";

// Simple curve
export const easeWithDefaults = defineEasing("my-ease", (t) => 1 - Math.pow(1 - t, 5));

// Parametric (callable with defaults; .with(...) returns a tuned variant)
export const customSpring = defineParametricEasing(
  "my-spring",
  { stiffness: 100 },
  ({ stiffness }) => (t) => 1 - Math.pow(1 - t, stiffness / 50),
);

Endpoints are clamped exact (t ≤ 0 → 0, t ≥ 1 → 1) by default. Disable for steps("start")-style curves with { exactEndpoints: false }.

Subpath imports

Tree-shake what you ship by importing from subpaths:

import { parseEasing } from "@vysmo/easings/parse";
import { toCSSLinear } from "@vysmo/easings/css";
import { prefersReducedMotion } from "@vysmo/easings/reduced-motion";

/parse pulls in the registry; /css pulls in the CSS converters; /reduced-motion pulls in the media-query helper. The main entry tree-shakes cleanly when you only import a curve or two.

Characteristics

  • Pure math. No DOM, no rAF, no global state. Runs in Node, browser, web workers, deno, bun.
  • Zero runtime dependencies.
  • Tree-shakable. Importing one curve ships ~0.2 KB gzipped.
  • Endpoint-correct. All catalog curves clear f(0) === 0 and f(1) === 1. Property-tested across the catalog.

License

MIT.