anim-skill · End-to-End Animation Generation
One topic in, one video out. Frames are fully drawn by code (Remotion + React), with no dependency on stock libraries, generative video models, or external images.
Style is a plugin, voice is a plugin, the pipeline is fixed. Adding a new style does not change the pipeline; swapping the voice engine does not change the pipeline.
When to Use
- "Create an explainer animation for X"
- "Turn this document/lesson plan into a video"
- "Add narration to this video"
- "Remake it in X style"
- "Check this video for flickering or empty scenes"
Do not use for: live-action footage, talking-head videos, 3D rendering (use Blender for that).
Input: Two Modes, Determine First
| Mode | Trigger | Extra Step |
|---|---|---|
| A · Topic-Driven | User gives only a topic keyword or phrase | First do research (facts, figures, common misconceptions), then proceed to design |
| B · Document-Driven | User already provides a topic document (lesson plan, white paper, PPT script) | First do refinement and correction (fill data, unify terminology, mark paragraphs that cannot be visualized), then proceed to design |
After determining, restate the plan before acting: I am in A/B mode, making an N-second video, in style X, for audience Y. If two of these are unclear, ask before guessing.
Six Stages (Order Is Fixed, No Skipping)
0 PREFLIGHT → 1 Content → 2 Storyboard → 3 Build → 4 Voiceover → 5 Accept & Deliver
↑ ↓
└── Rework ←───────────────────┘
0 · PREFLIGHT (One-Time, 2 Minutes)
node <skill>/scripts/preflight.mjs
Check node / npm / ffmpeg / browser; list available voice engines on this machine. If anything is missing, state it clearly. Don't wait until rendering to find out.
1 · Content (A: Research / B: Refine)
Output research.md: one-sentence thesis, 3–6 supporting facts, figures with sources, mistakes to avoid, audience knowns and unknowns.
- Mode A: Fact-checking first. Every figure must have a source; if not found, mark as "pending confirmation" — never invent.
- Mode B: Keep the original text, only supplement. Mark sentences that cannot be visualized (animation can only depict actions, comparisons, changes).
2 · Storyboard
Output plan.md (format in references/storyboard.md): one line per shot — frame range, visual, motion primitives, subtitle.
Hard criteria (rewrite if not met):
- Each shot has one protagonist, occupying ≥1/3 of the content area height (graphic ≥170px, large text ≥96px and full line ≥300px)
- The protagonist enters on beat 1 or 2
- Only three size classes: protagonist ≥170 / supporting 60–110 / annotation 22–30
- At least one "highlight moment" per video (thesis sentence, protagonist entrance, closing payoff — pick one). Do not pad with decorations.
3 · Build
node <skill>/scripts/scaffold.mjs <project-dir> --title "Title" --style <style-id>
Following the style brief (styles/index.json), write src/scenes/*.tsx and connect them with <Series>.
Iron Rules (violation will break rendering or crash the video):
- Everything must derive from
useCurrentFrame(). Forbidden:Math.random(),Date.now(),setStatecounters. For randomness, use deterministic hashing:hash(seed) = fract(sin(seed*127.1+311.7)*43758.5453). - Every
interpolate()must include{extrapolateLeft:'clamp', extrapolateRight:'clamp'}. Miss one, and frames outside the shot will fly out. - No CSS
transition/animation/@keyframes. Use onlyinterpolateandspringfor motion. - No external assets or heavy libraries (three.js / GSAP / images). Draw everything with SVG and CSS gradients.
- Maximum 12 SVG blur primitives per frame, maximum 15
filter: blur()elements, or rendering will be ten times slower.
4 · Voiceover (Optional)
node <skill>/scripts/srt.mjs <project-dir> # Generate SRT from storyboard
python <skill>/scripts/narrate.py <video> --provider edge|volc --voice <id>
- Can deliver without voiceover (e.g., for classroom use when teacher explains).
- With voiceover: generate SRT first, then synthesize. Timeline is derived from rendered frame numbers, not estimates.
- Engine is a plugin; see
references/voice.md.
5 · Acceptance and Delivery
python <skill>/scripts/qc.py <video> # Empty scenes / object size
python <skill>/scripts/qc_flicker.py <video> # Flicker / hard cut detection
Two hard metrics (see references/qc.md):
- Empty scene: largest object in content area <110px for >45 frames → defect; <80px → blocker
- Flicker: luminance offset from local median >6 (0/1 jump) → defect
Delivery package: <slug>.mp4, <slug>.srt, plan.md, research.md, src/ (editable project), README.md (how to modify, how to re-render).
Style Plugins
styles/index.json contains 15 built-in styles. Each is an executable brief (background color, ink color, seven-color palette, stroke width, jitter, glow, texture, font, character, projection readability, suitability).
Usage: --style neon / --style paper / --style crayon …
Adding a new style: append one entry to index.json and place a brief in styles/. No need to change the pipeline, scripts, or templates. See the extension contract in references/styles.md.
Style selection tip: first filter by "projection readability" (can the back rows see it?), then by "character". Paper/crayon suit young children; neon/minimal suit classrooms with poor projectors.
Voice Plugins
Two built-in providers:
| Provider | Cost | Requirements | Notes |
|---|---|---|---|
edge | Free | None | Microsoft Azure neural voice, more broadcast-like |
volc | 0.0003 CNY/character | APPID + API Key | Doubao voice, close to human; free credits for new accounts |
Adding a new engine: implement synthesize(text, voice) -> mp3 bytes and register it in scripts/tts/<provider>.py. narrate.py does not need changes. See references/voice.md.
Pre-Delivery Self-Check (Check Each Item)
-
remotion renderexit code 0,ffprobeframe count = design frame count -
qc.pyhas no blockers;qc_flicker.pyhas no peaks except at chapter hard cuts - All
interpolatecalls include clamp (grep -c "interpolate("=grep -c "extrapolateLeft") - No
Math.random/Date.now/ CSS animation - Subtitles match visuals (check 3 beat frames)
- Chinese fonts exist on this machine (otherwise rendering will show squares)
Quick Reference
node scripts/preflight.mjs
node scripts/scaffold.mjs ./videos/my-film --title "Title" --style paper --seconds 20
cd videos/my-film && npm install
node <skill>/scripts/render.mjs . main out/my-film.mp4
node <skill>/scripts/srt.mjs .
python <skill>/scripts/narrate.py out/my-film.mp4 --provider volc --voice zh_female_cancan_uranus_bigtts
python <skill>/scripts/qc.py out/my-film-volc.mp4
Details in references/: pipeline.md (each stage expanded), storyboard.md (storyboard template), styles.md (style catalog and extension), voice.md (voice and extension), qc.md (acceptance criteria), render-env.md (environment pitfalls: Windows sandbox, TEMP, browser path, ffmpeg parameters).