remotion-best-practices (remotion-dev/skills)
Remotion skill: same video quality as no skill and as one sentence of its rules, at 1.4x the tokens
22.9 / 30
Lift over no skill: -0.01
Situational: the lift -0.01 is under +1.0. Recommended needs a total of 22/30, output quality of 3.5, and a lift of +1.0.
SOTA
PassTested with Codex.
Covers Codex, Claude Code
Codex CLI 0.166 (SOTA tier): 18 graded runs. A pass here also covers Claude Code under our tier rule; it says nothing about the second tier.
Scores
Each dimension is 0 to 5 and the six add up to the total out of 30. 5 is better on every dimension. Cost 5 means cheap and fast. Install 5 means easy.
- Trigger reliability
- 5.0
- Lift over no skill
- 2.0
- Output quality
- 4.9
- Token and time cost
- 3.0
- Install and portability
- 4.0
- Safety
- 4.0
Security review
SafeStatic scan: 13 CRITICAL / 16 HIGH / 0 MEDIUM. Manual review: safe to run (no-network sandbox). A clean scan does not prove a skill safe.
Install
npx skills@latest add remotion-dev/skills --skill remotion-best-practices
Pinned commit: 30d4553ecd46fbc5212fd0ff006ae43af522158b
Tested: 2026-11-02
What we tested
- 15 s product teaser — In this Remotion project (React components in src/, composition id 'Main', rendered by npx remotion render src/index.ts Main) build a 15-second, 1920x1080, 30 fps product teaser for Tidepool, a monthly seaweed-snack subscription. Required on-screen text: the…
- 20 s animated bar-chart explainer — In this Remotion project (React components in src/, composition id 'Main', rendered by npx remotion render src/index.ts Main) build a 20-second, 1920x1080, 30 fps animated explainer: a bar chart of monthly revenue (Aug $42k, Sep $58k, Oct $71k). Title 'Reven…
- 30 s vertical captioned short — In this Remotion project (React components in src/, composition id 'Main', rendered by npx remotion render src/index.ts Main) build a 30-second vertical 1080x1920, 30 fps social short with burned-in captions. Captions, in order, each on screen for about 5 se…
Pros
- The skill was picked up without being named: Skill file read in 6/6 treatment runs.
- High absolute quality with the skill: 4.91 out of 5.
Cons
- No measurable lift over no skill (-0.01, inside the noise).
- A one-sentence prompt scored 4.89, against 4.91 with the skill (+0.02).
- The control already scores 4.91: a ceiling effect, so the test cannot show a lift.
- n=2 per task per arm; differences under about 1 point are noise.
Review
Codex CLI 0.166 (gpt-6-astra, low reasoning) on a Mac test machine, a fresh temporary project and temporary HOME/TMPDIR/caches per run, skill installed (treatment) or absent (control) or absent with the skill's core requirement squeezed into one sentence appended to the prompt (one-liner group), 2 runs per group per task, network off, /tmp writes blocked. The prompts never mention the skill (except the wording noted below). Environment: the project template (Remotion project with composition id Main) is the same for all groups. The sandbox has no network and no Remotion tooling, so none of the groups could start Studio or render; they wrote source only. We then rendered every project on a separate offline machine with Remotion 4.0.539. The skill's 'open the preview first' step could not happen.
Three-arm comparison
| Arm | Mean score (0-5) | Tokens per run |
|---|---|---|
| Without the skill | 4.91 | 159k |
| One-sentence prompt | 4.89 | 156k |
| With the skill | 4.91 | 217k |
Measured with Codex CLI over 18 runs, scored by rule-based checks with no LLM judge. Total 22.9 / 30, verdict Situational.
Verdict: Situational (22.9 / 30). Source: remotion-dev/skills, skills/remotion-best-practices, pinned at commit 30d4553. Install: npx skills@latest add remotion-dev/skills --skill remotion-best-practices. Licence: Remotion License (company use above 3 people needs a paid license; evaluation only).
What it is
The remotion-best-practices skill, the router of Remotion's official skill set (remotion-dev/skills, version 4.0.539, Remotion License). SKILL.md (about 600 words) sends the agent to sub-skills: create a video, markup best practices (drive animation with useCurrentFrame() and interpolate(), take fps from useVideoConfig(), no CSS transitions or Tailwind animation classes), maps, captions, studio, render and more. About 12 sub-skills of Markdown, two small local .mjs scripts. It also tells the agent to open the Remotion Studio preview and not to render unless asked.
How we tested
Codex CLI 0.166 (gpt-6-astra, low reasoning) on a Mac test machine, a fresh temporary project and temporary HOME/TMPDIR/caches per run, skill installed (treatment) or absent (control) or absent with the skill's core requirement squeezed into one sentence appended to the prompt (one-liner group), 2 runs per group per task, network off, /tmp writes blocked. The prompts never mention the skill (except the wording noted below).
Environment: the project template (Remotion project with composition id Main) is the same for all groups. The sandbox has no network and no Remotion tooling, so none of the groups could start Studio or render; they wrote source only. We then rendered every project on a separate offline machine with Remotion 4.0.539. The skill's 'open the preview first' step could not happen.
- 15 s product teaser — In this Remotion project (React components in src/, composition id 'Main', rendered by
npx remotion render src/index.ts Main) build a 15-second, 1920x1080, 30 fps product teaser for Tidepool, a monthly seaweed-snack subscription. Required on-screen text: the… - 20 s animated bar-chart explainer — In this Remotion project (React components in src/, composition id 'Main', rendered by
npx remotion render src/index.ts Main) build a 20-second, 1920x1080, 30 fps animated explainer: a bar chart of monthly revenue (Aug $42k, Sep $58k, Oct $71k). Title 'Reven… - 30 s vertical captioned short — In this Remotion project (React components in src/, composition id 'Main', rendered by
npx remotion render src/index.ts Main) build a 30-second vertical 1080x1920, 30 fps social short with burned-in captions. Captions, in order, each on screen for about 5 se…
Scoring is programmatic (hidden tests / planted-issue recall / constraint checks / render+OCR where relevant), 0–5 per run. No LLM judge decided any score.
Results
The one-liner given to the third group: "Drive every animation with useCurrentFrame() and interpolate()/spring() (never CSS transition/animation), take fps from useVideoConfig() and convert seconds to frames with it, and structure the video as <Sequence>/<Series> scenes inside the composition."
| Task | Control score | One-liner | With skill | Control tokens | One-liner tokens | With-skill tokens | Skill read |
|---|---|---|---|---|---|---|---|
| t1-teaser | 5.0 | 4.93 | 5.0 | 230k | 168k | 254k | 2/2 |
| t2-chart | 4.74 | 4.73 | 4.71 | 121k | 168k | 198k | 2/2 |
| t3-vertical | 5.0 | 5.0 | 5.0 | 124k | 129k | 197k | 2/2 |
Mean score: 4.91 without vs 4.91 with the skill (delta -0.01). Tokens per run: 159k vs 217k (1.36x); time 161s vs 177s. One-liner group: 4.89 (the skill's gain over the one-liner: +0.02; one-liner's own gain over no skill: -0.03); one-liner tokens 156k per run, so the skill costs 1.39x the one-liner.
What happened
- Video quality was the same. All 18 projects rendered at the right size, length and frame rate, and OCR found every required text (name, tagline, $14 / box, closing line, chart title, captions) in each of them. Mean score 4.91 without the skill, 4.89 with only a one-sentence version of its rules, 4.91 with the skill. The only points lost, in all groups, are the bar-chart explainer holding still for long stretches (15-23% of frames with motion) and two one-liner teasers with 48-52%.
- We viewed contact sheets of the teaser from all three groups: all look like finished product ads (cream and dark-green scenes, a pouch illustration, a price end card) and we could not rank them.
- The skill's main concrete rule was followed with or without it. Reading the source: in the 6 no-skill projects none calls
useVideoConfig()(they hard-code 30 fps), in all 6 skill projects and all 6 one-liner projects it is used, and no project in any group uses CSS transitions or keyframes. So the one sentence carried the same rule, and the agents already animate withuseCurrentFrame()andinterpolate()unprompted. - The skill is read every time (6/6 treatment runs) and costs more: 217k tokens per run against 159k without it (1.36x) and 156k with the one-liner (1.39x), 14 commands against 9. This is the smallest overhead of the three video skills we tested.
- Part of it could not run. The skill's first instruction is to start Remotion Studio and open a preview before building; with no network and no tooling that did not happen, so the result is the skill's text only.
Dimension scores
| Dimension | Score | Why |
|---|---|---|
| 1_output_quality | 4.91 | Mean score 4.91/5 with the skill (programmatic checks, see per-task table). |
| 2_lift_vs_no_skill | 1.99 | -0.01 points vs 4.91 without the skill (n=2 per task; under ~1 point is noise). |
| 3_trigger | 5.0 | Skill file read in 6/6 treatment runs. |
| 4_instructions_portability | 4 | Router skill with many sub-skill files; the 'open Studio first' rule needs a browser and a running dev server, which many agent sandboxes lack. |
| 5_efficiency | 3 | 1.36x tokens (217k vs 159k per run) and 1.10x time (177s vs 161s). |
| 6_safety_hygiene | 4 | Markdown plus two local .mjs scripts (no network, no exec); scanner hits are .env/process.env in documentation examples (Mapbox, ElevenLabs keys). Remotion License needs a paid licence for companies above three people. |
Limits of this test
- No Studio preview, no render and no Remotion CLI in the sandbox, so the skill's workflow was only partly exercised.
- Three code-drawn tasks (teaser, bar chart, vertical captioned short); video footage, audio, captions from speech, maps, Lottie, 3D and the SaaS rendering features were not tested.
- Renders are on Linux with a software GL and the check for motion is a crude frame-difference threshold; the chart task loses points in every group.
- The
useVideoConfigcounts come from reading the source and are not part of the 0-30 score. - Remotion License: free for individuals and companies of up to three people, paid above that; we only evaluated and are not redistributing.
- n = 2 per group per task: differences under about 1 point are noise.
- Rule-based scoring measures what the checks can see; it cannot judge taste or whether a result is the best possible.
Security
See security.md. Scan: 13 CRITICAL / 16 HIGH / 0 MEDIUM. Verdict: safe to run (no-network sandbox). A clean scan does not prove a skill safe.
Bottom line
For one-off code-drawn videos the skill made no measurable difference: the agent already writes sound Remotion code, and one sentence of the skill's key rule reproduced its small structural effect at about 0.7x the cost. It is cheap enough to leave installed if you build Remotion projects often (the sub-skills cover maps, captions and rendering that we did not test), but there is no evidence here that it improves a simple video.
Transcript
Run log for remotion-best-practices: Codex CLI, network off, per-run temp HOME/TMPDIR, one row per graded run. Columns: task, arm-run, score (0-5), tokens, seconds, checks passed, skill files the agent opened. t1-teaser control-1: score 5.0, tokens 258594, secs 285.6, checks 5/5, opened nothing t1-teaser control-2: score 5.0, tokens 202623, secs 189.4, checks 5/5, opened nothing t1-teaser oneliner-1: score 4.94, tokens 218510, secs 266.6, checks 5/5, opened nothing t1-teaser oneliner-2: score 4.92, tokens 118109, secs 174.8, checks 5/5, opened nothing t1-teaser treatment-1: score 5.0, tokens 217450, secs 209.8, checks 5/5, opened remotion-best-practices t1-teaser treatment-2: score 5.0, tokens 291582, secs 227.3, checks 5/5, opened remotion-best-practices t2-chart control-1: score 4.73, tokens 130647, secs 112.9, checks 4/5, opened nothing t2-chart control-2: score 4.74, tokens 112740, secs 110.9, checks 4/5, opened nothing t2-chart oneliner-1: score 4.73, tokens 140990, secs 152.9, checks 4/5, opened nothing
18 runs, 21 artifacts
Sample output
SOTA · With the skill: src/Tidepool.tsx (t1-teaser, run 1, Codex)
import React from 'react'; import {AbsoluteFill, Sequence, interpolate, Easing, useCurrentFrame, useVideoConfig} from 'remotion'; const cream = '#F6F1DF', ink = '#123E36', lime = '#D9EF79', orange = '#FF8552'; const serif = 'Georgia, "Times New Roman", serif'; const easing = {extrapolateLeft: 'clamp' as const, extrapolateRight: 'clamp' as const, easing: Easing.bezier(.16, 1, .3, 1)}; const Enter: React.FC<{children: React.ReactNode; delay?: number; style?: React.CSSProperties}> = ({children, delay = 0, style}) => { const f = useCurrentFrame(); return <div style={{...style, opacity: interpolate(f, [delay, delay + 18], [0, 1], easing), translate: `0 ${interpolate(f, [delay, delay + 23], [60, 0], easing)}px`}}>{children}</div>; }; const Wave = ({color = ink, bottom = -100}: {color?: string; bottom?: number}) => { const f = useCurrentFrame(); return <svg width="2200" height="300" viewBox="0 0 2200 300" style={{position: 'absolute', left: -100, bottom, translate: `${Math.sin(f / 65) * 65}px 0`}}><path d="M0 95 Q275 -15 550 95 T1100 95 T1650 95 T2200 95 V300 H0Z" fill={color}/><path d="M0 60 Q275 -50 550 60 T1100 60 T1650 60 T2200 60" fill="none" stroke={color} strokeWidth="2"/></svg>; }; const Pouch = () => { const f = useCurrentFrame(); return <div style={{width: 420, height: 610, position: 'relative', rotate: `${-7 + Math.sin(f / 40) * 1.5}deg`, translate: `0 ${Math.sin(f / 28) * 9}px`, filter: 'drop-shadow(18px 25px 0 rgba(18,62,54,.13))'}}> <svg width="420" height="610" viewBox="0 0 420 610" style={{position: 'absolute'}}> <path d="M26 5 H394 L382 55 L407 573 Q411 600 380 604 H40 Q9 600 13 573 L38 55Z" fill={lime} stroke={ink} strokeWidth="3"/> <path d="M29 18 H391 M32 29 H388 M35 43 H385 M22 577 H398 M22 587 H398" stroke={ink} strokeWidth="2" opacity=".35"/> <path d="M22 472 Q120 427 210 477 T399 477 L404 571 H16Z" fill={ink}/> <path d="M25 455 Q120 410 210 460 T397 460" fill="none" stroke={ink} strokeWidth="3"/> </svg> <div style={{position: 'absolute', top: 77, width: '100%', textAlign: 'center', color: ink}}> <div style={{fontSize: 65, fontFamily: serif, letterSpacing: -4}}>Tidepool</div> <div style={{fontSize: 15, letterSpacing: 4, marginTop: 15}}>SEAWEED SNACKS</div> <svg width="190" height="210" viewBox="0 0 190 210" fill="none" style={{marginTop: 18}}><path d="M96 203 C67 143 135 95 96 12 M96 164 C28 163 29 115 45 100 C48 138 85 116 96 164 M99 118 C157 119 163 70 143 59 C143 89 108 79 99 118 M100 71 C57 74 55 36 66 24 C72 49 94 37 100 71" stroke={ink} strokeWidth="9" strokeLinecap="round"/></svg> <div style={{fontSize: 18, letterSpacing: 3, marginTop: 9}}>A LITTLE OCEAN JOY</div> </div> <div style={{position: 'absolute', top: 513, width: '100%', textAlign: 'center', color: cream, fontSize: 20, letterSpacing: 3}}>CRISP • SAVORY • SEAWEED</div> </div>; }; const Chip = ({x, y, angle, index}: {x: number; y: number; angle: number; index: number}) => { const f = useCurrentFrame(); return <svg width="340" height="260" viewBox="0 0 260 200" style={{position: 'absolute', left: x, top: y, rotate: `${angle + Math.sin(f / 35 + index) * 6}deg`, translate: `0 [... excerpt: first 3200 of 8030 characters]