Text Animator
After Effects text animator: range and wiggly selectors drive per-character, per-word or per-line position, scale, rotation, opacity, blur, tracking and fill over measured layout. Install with npx remotion-ui@latest add text-animator.
PrimitiveMotion graphicsAdvanced
$ npx remotion-ui@latest add text-animatorAn animator declares what selected glyphs should become — lower, blurred, rotated, recoloured — and a selector decides how much of that each glyph gets. You animate the selector, usually its offset, so one keyframe pair moves a whole line. The preview has no per-glyph keyframes at all. Four animators overlap in time: a Smooth range passes through as a wave; a Smooth range intersected with a Wiggly selector makes a tremor that only exists inside a travelling window; a line-basis range breathes the second line's tracking; and a word-basis Triangle range leans whole words forward in turn.
Selectors. range: start / end / offset (0–1, or unit indices with units: "index"), shape (square, ramp-up, ramp-down, triangle, round, smooth), easeHigh / easeLow, smoothness, randomizeOrder + seed, amount, and a combine mode (add, subtract, intersect, min, max, difference). wiggly: minAmount / maxAmount, wigglesPerSecond, correlation, phases and seed. Ramps are one-sided as in AE, so a sweeping offset reveals a line and leaves it revealed.
Properties apply in proportion to the selection: position, scale, rotation, skew, opacity, blur, tracking, fill and characterOffset. basedOn picks the unit: characters (spaces count), characters excluding spaces, words or lines. anchorGrouping pivots scale and rotation on each glyph, its word, its line or the whole block.
Layout is measured. The component waits for the font, measures each word by its prefixes (so kerning survives), wraps without ever splitting a word, and shrinks the type only when a single word cannot fit. Animated tracking pushes real neighbours and re-centres the line. Pass waitForFont={waitUntilDone} from loadFont() so measurement waits for exactly your face; without it the component waits up to 1.5s for a loaded face of the primary family.
Long blocks stay cheap. Glyphs no animator is touching render as plain per-word text, and blurred glyphs share one filter per line and half-pixel blur step. On a 2,500-glyph block the component costs ~2ms per frame over plain text, down from ~27ms.
Usage
import { TextAnimator } from "@/remotion/primitives/text-animator";
import { easyEase } from "@/remotion/lib/ae-motion";
<TextAnimator
text="Every letter keeps its own clock"
animators={[
{
basedOn: "characters-excluding-spaces",
properties: { position: [0, 60], rotation: 12, opacity: 0, blur: 12 },
selectors: [
{ shape: "ramp-up", start: 0, end: 0.3, offset: [easyEase(0, -0.3), easyEase(45, 1)] },
],
},
]}
/>Selectors: range (start/end/offset, shape square|ramp-up|ramp-down|triangle|round|smooth, easeHigh/easeLow, randomizeOrder, mode, amount) and wiggly. Installs @remotion/layout-utils.
Agent notes
Install first, then import the copied source component locally. AI guide →
@/remotion/primitives/text-animator- Use when: After Effects-style motion graphics built from composable, keyframeable operators.
- Customize: text, animators, fontSize, fontFamily, plus copied source for timing, layout, colors, and typography.
- Rule: do not import this component from the
remotion-uinpm package; it is copied into your project.
Usage
import { TextAnimator } from "@/remotion/primitives/text-animator";
import { easyEase } from "@/remotion/lib/ae-motion";
<TextAnimator
text="Every letter keeps its own clock"
animators={[
{
properties: { position: [0, 60], opacity: 0, blur: 12 },
selectors: [{ shape: "ramp-up", start: 0, end: 0.3, offset: [easyEase(0, -0.3), easyEase(45, 1)] }],
},
]}
/>API Reference
| Prop | Type | Default | Description |
|---|---|---|---|
| text* | string | - | Copy. \n forces a line break; words wrap at maxWidth and never split. |
| animators | TextAnimatorLayer[] | [] | { properties, selectors?, basedOn? }. Properties: position, scale, rotation, skew, opacity, blur, tracking, fill, characterOffset. |
| fontSize | number | - | Defaults to 84px at 1080 wide, scaled. Shrinks only if one word cannot fit. |
| fontFamily | string | "Inter, system-ui, sans-serif" | The render waits for this face before measuring. |
| fontWeight | number | 700 | Weight used for measuring and drawing. |
| color | string | "#f4f4f5" | Base fill before any animator recolours a glyph. |
| lineHeight | number | 1.12 | Multiple of the font size. |
| letterSpacing | number | -0.02 | Base tracking in em. |
| align | "left" | "center" | "right" | "center" | Line alignment; follows animated tracking. |
| maxWidth | number | - | Wrap width. Defaults to 84% of the composition width. |
| anchorGrouping | "character" | "word" | "line" | "all" | "character" | Pivot for scale and rotation. |
| waitForFont | () => Promise<unknown> | - | Resolves when the face is loaded — pass waitUntilDone from loadFont. Without it, waits up to 1.5s for a loaded face of the primary family. |
| frame | number | - | Render this frame instead of the current one. |
Related
Shape Layer
After Effects shape layer with an ordered operator stack — trim paths, repeater, offset paths, wiggle paths, zig-zag and pucker & bloat — evaluated per frame as pure geometry. Install with npx remotion-ui@latest add shape-layer.
Effector Field
Cinema 4D MoGraph cloner and effectors: clone any element into a grid, radial or linear arrangement and let animatable spherical, linear or noise falloff fields drive each clone. Install with npx remotion-ui@latest add effector-field.