An anime.js v4 animate call with duration 1250 and delay stagger(65), drawn as one bar per card on a time axis: card 24 settles at 2,745 ms, and card 59 settles at 5,020 ms, just past the five-second WCAG 2.2.2 line. The sum shown is 65 × 58 + 1250.

Anime.js for dynamic websites: how to use v4 with motion that respects users

Most anime.js tutorials still teach v3, so the code fails before a frame runs. Here is the v4 shape that works, the guard that keeps it kind to people who ask for less motion, and the sum that tells you when a list moves for too long.

What is anime.js, and how do you use it for dynamic websites?#

Anime.js is a free JavaScript animation library; in v4 you import animate, createTimeline and stagger by name, pass the targets first, and wrap the motion in a scope that honours reduced motion.

Its README calls it "a fast, multipurpose and lightweight JavaScript animation library". Because it moves CSS properties, SVG, DOM attributes and plain objects, it fits most front ends. And the npm page lists the MIT License, so a commercial site may use it.

So what is anime.js v4 like to write? First, there is no global anime object any more. Instead, each feature is its own import, and the targets come first in the call. Then a scope decides whether the motion plays at all, and that is the step most tutorials skip.

Why use anime.js for dynamic websites at all?#

The anime.js documentation, read in October 2026, sizes the full animate() at 10KB and its Web Animation API version at 3KB, so a dynamic website loads only the motion it imports.

Show data table
Size of each animate() build, as printed by the anime.js Animation documentation, read October 2026.
Item Value
animate(), the JavaScript engine 10 KB
waapi.animate(), the Web Animation API version 3 KB

The Web Animation API build covers simple tweens at 3KB, and the full engine adds timelines at 10KB.

Size of each animate() build Size of each animate() build, as printed by the anime.js Animation documentation, read October 2026. Anime.js (Julian Garnier), Animation documentation, accessed October 2026

A dynamic website adds content after the first load, such as search results or a growing feed. Because anime.js takes a selector or a list of elements, one call animates whatever is on the page when it runs. So a timeline can sequence a panel, and a stagger can reveal a fresh batch of results one by one.

And scroll is covered too. The onScroll page passes a ScrollObserver into the autoplay setting, so an element moves when it scrolls into view. Meanwhile, waapi.animate() hands the work to the browser, and the docs say it "covers most of the basic API". So pick the small build for simple tweens (one value animated from a start to an end) and the full engine for timelines.

Which official anime.js v4 pages should you build from?#

Build from the official pages in this order: installation, animate(), stagger, timeline add() and the Scope mediaQueries parameter, then MDN's prefers-reduced-motion entry.

  1. Page 1

    Installation: npm install animejs, the module import and the CDN forms.

  2. Page 2

    Animation: the animate(targets, parameters) call.

  3. Page 3

    Time staggering: stagger() on delay.

  4. Page 4

    Timeline add(): timeline.add(targets, parameters, position).

  5. Page 5

    Scope mediaQueries: the reduceMotion query and self.matches.

  6. Page 6

    MDN on prefers-reduced-motion: what the reduce value means.

The six pages, in order: Installation, Animation, Time staggering, Timeline add(), Scope mediaQueries, MDN on prefers-reduced-motion.

For older code, the migration guide is the seventh page.

How do you write your first anime.js v4 animation?#

Install animejs, import animate and stagger by name, and pass the targets as the first argument, because v4 has no global anime object and no targets key.

The migration guide says it plainly: "The targets parameter has been replaced by the mandatory Targets argument of the animate function." The code below assumes a bundler such as Vite or esbuild, which the installation page names. Without one, import from https://esm.sh/animejs instead.

javascript
// Step 1: npm install animejs (then bundle with Vite or esbuild)
// Step 2: import each function you use by name
import { animate, stagger, createTimeline } from 'animejs';

// Step 3: targets first, then parameters; stagger the delay
animate('.card', {
  opacity: [0, 1],
  y: [24, 0],
  duration: 1250,
  delay: stagger(65),
  ease: 'inOutQuint',
});

// Step 4: sequence on a timeline; an optional third argument sets the start
createTimeline()
  .add('.panel-title', { opacity: [0, 1], duration: 600 })
  .add('.panel-body', { opacity: [0, 1], duration: 600 });

So each card starts 65 ms after the one before it. Then the timeline fades the title in, and the body follows. When new content arrives later, call the same animate() on the new elements once they are in the page.

How do you make anime.js respect prefers-reduced-motion?#

Wrap the animations in createScope with a reduceMotion media query and set the duration to 0 when it matches, the pattern the anime.js Scope documentation itself prints.

The Scope mediaQueries page "Defines the media queries to match for conditionally refreshing the Scope" when a match changes. And MDN says the reduce value "Indicates that a user has enabled the setting on their device for reduced motion."

DiagramWhy a stylesheet reset never reaches an anime.js tween, and where the scope guard stops it. From the anime.js Scope documentation, MDN and W3C SCR40, read 10 October 2026.
javascript
import { createScope, animate, stagger } from 'animejs';

createScope({
  mediaQueries: { reduceMotion: '(prefers-reduced-motion)' },
}).add(self => {
  const { reduceMotion } = self.matches;
  animate('.card', {
    opacity: [0, 1],
    y: [24, 0],
    duration: reduceMotion ? 0 : 1250,
    delay: reduceMotion ? 0 : stagger(65),
  });
});

Why not trust the CSS reset in your stylesheet? Because that reset sets durations in CSS, while anime.js sets each frame from JavaScript, so the reset never reaches the tween. The W3C technique SCR40 takes this route: read the media query in JavaScript and stop the motion there. It supports WCAG 2.3.3, Animation from Interactions, a Level AAA criterion. Also, since the scope refreshes on a change, a user who turns the setting on mid-visit gets still content at once.

How long does an anime.js stagger run before it passes five seconds?#

In this worked example, at the anime.js README's 65 ms per element and 1250 ms duration, 24 cards settle at 2,745 ms and 59 cards run 5,020 ms, past five seconds. That five-second line is set by WCAG 2.2.2, which the W3C WAI publishes.

Total time is the step times the element count less one, plus the duration, starting from the first element (a stagger starts each element one fixed step after the one before). For instance, with the anime.js README values read on 10 October 2026, 24 cards give 65 × 23 + 1250, or 2,745 ms in this example. And 59 cards give 65 × 58 + 1250, or 5,020 ms.

Show data table
Stagger run time at 65 ms per element and 1250 ms duration, the anime.js README example values, read October 2026; arithmetic, staggering from the first element.
Stage Milliseconds until the last element settles
4 elements 1,445 ms
12 elements 1,965 ms
24 elements 2,745 ms
48 elements 4,305 ms
58 elements 4,955 ms
59 elements 5,020 ms

At 65 ms a step and 1250 ms a tween, the run passes 5,000 ms between 58 and 59 cards.

Stagger run time by element count Stagger run time at 65 ms per element and 1250 ms duration, the anime.js README example values, read October 2026; arithmetic, staggering from the first element. Arithmetic from the anime.js (Julian Garnier) README example values, accessed October 2026. Modelled, not measured

Why does that line matter? WCAG 2.2.2, Pause, Stop, Hide, is a Level A criterion. It asks for a way to pause, stop or hide moving content that starts on its own, "lasts more than five seconds", and runs beside other content. Still, a one-time card reveal may not meet all three conditions. However, a looping list can, and the count that tips it is easy to miss.

When your stagger passes five seconds

Set your element count, stagger step and duration, and see when the last element settles and how far past five seconds it runs. Modelled, not measured.

Your stagger

measured on this projectan assumption, change it

Staggers from the first element at the anime.js README example values; the five-second line is the one WCAG 2.2.2 draws.

Milliseconds until the last element settles

2,745

Milliseconds past the five-second line
0

An illustrative model of the worked example above, not a measurement.

In practice, shorten the step as the list grows, or stagger only the cards in view. Either way, the guard above still drops it all to zero for anyone who asked.

Which websites are built with anime.js?#

The Wappalyzer anime.js page, read on 10 October 2026, ranks its top sites by traffic, and riverside.com and several TikTok business sites follow. So an anime.js website is a common production choice, not a demo.

Also, the project is maintained. The GitHub releases page, read on 10 October 2026, lists v4.5.0 as the newest release, published on 22 June. So the API you write against today is current.

Should you use anime.js or Motion?#

Choose anime.js for framework-free pages that sequence and stagger many elements, and Motion when a React or Vue app wants declarative components and a site-wide reducedMotion setting.

On npm the comparison is animejs vs motion, and both packages are MIT licensed. Motion's README offers "First-class React, JavaScript, and Vue packages" and notes that Framer Motion is now Motion. Its quick start, read on 10 October 2026, describes a mini animate() at 2.3kb. But Motion's npm page also sells Motion+, a paid licence for extra examples and premium APIs.

The real split is reduced motion. Motion's accessibility guide says that with reducedMotion="user" on MotionConfig, "all motion components will automatically disable transform and layout animations". So that is one switch for a whole React app. Anime.js has no such switch, so you write the scope guard around each group of animations. In return, its timelines and staggers are plain functions with no framework needed.

So the stack decides. For a static or server-rendered site, anime.js fits. For a React or Vue app built from components, Motion fits better. Other animation libraries exist, and the same test of stack and guard applies to them.

Anime.js against Motion on the same four fields, each from the library's own documentation, read 10 October 2026.

FieldAnime.jsMotion
Stack it servesFramework-free pages; timelines and staggers are plain functionsFirst-class React, JavaScript and Vue packages
Reduced motionYou write the scope guard around each group of animationsreducedMotion set to user on MotionConfig, one switch for a whole React app
Smallest buildwaapi.animate() at 3KBmini animate() at 2.3kb
LicenceMITMIT; Motion+ is a paid licence for extra examples and premium APIs

What breaks when you paste a v3 anime.js example into v4?#

Most pasted v3 examples break on the same renames: targets moves into the first argument, easing becomes ease without its prefix, and direction becomes the alternate and reversed flags.

The migration guide lists each change, and these break most copied code:

  1. Step 1: the import

    import anime from 'animejs' fails, because the global anime object is replaced by the animate import.

  2. Step 2: the targets

    targets: '.box' moves out of the object to the first argument.

  3. Step 3: the ease

    "The easing parameter has been renamed ease", so easing: 'easeOutQuad' becomes ease: 'outQuad'.

  4. Step 4: the direction

    direction: 'alternate' becomes alternate: true, and direction: 'reverse' becomes reversed: true.

  5. Step 5: the callbacks

    endDelay becomes loopDelay, and the change callback becomes onRender.

So port one line at a time against that list, starting at the import line, where v3 code fails first.

When is anime.js the wrong tool for a dynamic website?#

Use a CSS transition for a single hover or fade, and Motion inside a React app, because anime.js earns its import when you sequence or stagger many elements.

First, a button hover or one fade needs no library. A CSS transition does it, and a prefers-reduced-motion block in the same stylesheet guards it, as MDN shows. Second, React layout animation is Motion's home ground, with the switch built in. Third, if you need a few simple tweens and every kilobyte counts, pick a smaller build. On 10 October 2026, the anime.js docs printed 3KB for waapi.animate(), and Motion's quick start printed 2.3kb for its mini animate().

DiagramWhich tool fits which motion job, from the anime.js, Motion and MDN documentation, read 10 October 2026.

Where do motion and accessibility go next on your site?#

Reduced motion is one of several user settings a site must honour, so visible focus and the WCAG version that binds you are the next two reads.

For keyboard users, read focus vs focus-visible in CSS. Then see which motion criteria apply at your level in the WCAG guidelines comparison. For the wider picture, start with the introduction to web accessibility. If you want a second pair of eyes, see accessibility testing or UI and UX design. Still, the anime.js documentation and the six pages above are enough to build this on your own.

Questions this post answers

Is anime.js free to use on a commercial website?
Yes, the npm page lists anime.js under the MIT License, so a commercial website may use it. Its README, read on 10 October 2026, also calls the library 100% free, funded by sponsors.
How do you use anime.js for dynamic websites built in v4?
Install animejs, import animate and stagger by name, and call animate with the targets first. Then wrap that call in createScope with a reduceMotion media query.
Does anime.js v4 support prefers-reduced-motion?
Yes, through Scope: the mediaQueries example reads a reduceMotion match and sets the duration to 0. But you add that guard yourself, because it is not on by default.
Is anime.js better than Motion?
Neither is better everywhere. Anime.js suits framework-free sequencing and staggers, while Motion suits React or Vue components and offers a site-wide reducedMotion setting.

Keep reading