1仕組みと動作原理
立脚する基盤は Remotion のフレーム決定性です。アニメーションは現在フレームの純粋関数であるため、任意のフレームを正確にレンダリング、diff、CI への統合が可能であり、シーク用ハーネスを設けずに正確なフレームを直接レンダリングできます。
Build real MP4/GIF/WebM videos in React. Every frame is a pure function of `useCurrentFrame()`, so output is deterministic, scrubbable, diffable, and renderable in CI. The code-first alternative to After Effects for templated and data-driven motion graphics.
コア API サーフェスは 4 つのプリミティブに集約されます:interpolate(時間→値変換、clamp 必須)、spring(物理ベースのイージング)、Sequence/Series(タイムライン配置)、Composition + zod schema(パラメータ化と編集可能な props)。
Always clamp `interpolate` unless an intentional overshoot is desired — by default it extrapolates linearly past the range, which produces opacity > 1 or negative values.
データ駆動は本技術の差別化ポイントです:durationInFrames は props から動的に計算でき(calculateMetadata)、データを一度定義すれば複数出力のレンダリングに対応し、「CSV 1 行/レコード 1 件につき動画 1 本」のユースケースに最適です。
To make duration data-dependent, use `calculateMetadata` on the Composition to compute `durationInFrames` from props (e.g. number of rows × frames per row) before render.
ヘッドレスレンダリングにはリアルタイムの音声クロックが存在しないため、音声やビートの同期には「オフライン検出を行い、タイムスタンプを props に焼き込む」手法が求められます。
Detect beats offline (e.g. with `web-audio-beat-detector` or aubio) and bake the timestamps into props — never analyze audio at render time, since headless rendering has no realtime audio clock.
決定性の規律は禁止リストとして明文化されています:Math.random、Date.now、タイマーは使用禁止であり、ランダム処理には Remotion の random(seed) を使用する必要があります。
- Never use `Math.random()`, `Date.now()`, or animation timers — they break determinism. Use `random(seed)` from Remotion for stable per-frame randomness.
コスト削減のため、検証ループは意図的に 2 段階に分割されています。まず開始/中間/終了フレームの PNG をレンダリングして個別に検査し、問題がないことを確認してから動画全体のエンコードを実施します。また、defaultProps ではなく「実際にリリースする props」を使用します。
**Verify loop — render stills → inspect → encode.** Render single frames first (cheap, no video encode), inspect them, and encode the full video only once the frames are right.
「レンダラーは嘘をつくが、ファイルは嘘をつかない」:最終成果物の検証は、エンコード済み MP4 のメタデータを直接読み取り、解像度や fps をアサートすることで行います(リポジトリの probe-mp4.sh スクリプトで ffprobe を使用して実装)。
# Renders lie; the file doesn't. This reads resolution / codec / fps / duration straight from the
データ駆動型やバッチ処理には専用の中間検収ステップが存在します:代表的な props で still 検査を実施した後に一括レンダリングを行うことで、同一のレイアウトバグが N 個生成されるのを防ぎます。
**Data-driven / batch**: verify ONE representative props set via stills *before* batch-rendering all rows — catch a layout bug once instead of N times.
reference ファイルは、CLI フラグ、プログラマティックなレンダリングループ、GLSL/Three.js の埋め込み、決定性チェックリストなど、エンジニアリングの実装面を網羅しています。
import {bundle} from '@remotion/bundler';
2コア機能
3外部依存関係
| Kind | Dependency / Endpoint |
|---|---|
| cli | npx remotion(studio / still / render / compositions),远程拉取 Remotion 工具链 |
| package | remotion(运行时)/ @remotion/renderer / @remotion/bundler |
| package | zod + @remotion/zod-types(props 类型安全与 Studio 可编辑) |
| package | @remotion/three + three(在视频里驱动 Three.js 场景) |
| package | @remotion/google-fonts(无头渲染下预载字体,避免字体跳变) |
| package | web-audio-beat-detector / aubio(离线节拍检测,产出烘进 props 的时间戳) |
| cli | ffprobe(probe-mp4.sh 读取成片真实规格)/ ffmpeg(contact-sheet.sh 拼接 still) |
| network | iart.ai 引流链接(文档内,非运行时调用) |
4推奨統制措置と判定根拠
- scripts/: ローカルスクリプトまたはコマンドの実行: npx remotion …(studio / still / render / compositions):必要に応じて npm から Remotion を取得して実行
- 网络端点: 外部ネットワークアクセスの宣言: 共有スクリプト自体には業務 API 呼び出しはありません。ネットワークアクセスはツールチェーンに起因し、npx が npm(registry.npmjs.org)から remotion および関連パッケージを取得します
- 本地工作目录: ファイルの読み書きと成果物出力: out/*.mp4、out/*.gif、out/*.webm(完成動画)
5二重目の独立検証
- [ok] 「无 seek harness、可直接渲染精确帧」的前提是否成立 — SKILL.md 与 reference 一以贯之地把确定性建立在「每帧是 useCurrentFrame 的纯函数」上,并用禁止清单(Math.random/Date.now/timers)+ random(seed) + delayRender/continueRender 兜住例外;因此 still --frame=N 能精确复现该帧。逻辑自洽,非空话。
- [ok] verify loop 的命令是否可执行(含末帧取值) — 命令为 `npx remotion still Promo out/f-start.png --frame=0` / --frame=75 / --frame=149,并注明「last frame = durationInFrames - 1」,另给 `npx remotion compositions` 用于反查 durationInFrames/fps。无未定义变量。
- [ok] probe-mp4.sh 的断言语义(首遍称「读真实 spec 并断言」) — 实读脚本:分辨率不等即 fail=1;fps 用 awk 容差 0.5 判定;codec 非 h264 只告警不 fail;末尾按 fail 决定 exit 0/1。首遍描述准确(未夸大「强制 h264」)。
- [discrepancy] scripts/ 路径语义(是否 skill 内自带) — SKILL.md 写 'Packaged helper (`scripts/`)',实际脚本在**仓库根** motion-design/scripts/,skills/remotion-video/ 目录内没有 scripts/(同仓库 after-effects 却自带 skills/after-effects/scripts/*.jsx)。按单 skill 粒度安装时,`scripts/contact-sheet.sh`、`scripts/probe-mp4.sh` 的相对路径可能解析不到;在仓库根工作则成立。属文档/打包口径问题,非功能缺陷。
- [ok] 外部依赖是否完整(含 reference 里的隐性依赖) — SKILL.md 显式提及 remotion、zod、@remotion/renderer、web-audio-beat-detector、aubio、staticFile;reference 补充 @remotion/bundler、@remotion/zod-types、@remotion/three、three、@remotion/google-fonts 与 --gl=angle/--scale/--concurrency 等旗标。已全部逐条登记;无未登记的第三方服务。
- [ok] 安全面:有无凭证/环境变量/隐蔽外发 — 全目录对 API_KEY/token/secret/env/curl/requests 零命中;脚本只做 ffprobe/ffmpeg 本地操作;网络面仅来自 npx 拉包与(reference 建议的)Google Fonts 预载。第一遍 orange 判定的依据(远程包依赖)成立,且未发现应升档的凭证/绕过行为。
- [ok] 数据驱动「先验一套代表 props」是否真的写进流程 — 'Data-driven / batch: verify ONE representative props set via stills before batch-rendering all rows' 位于 verify loop 小节内,且 Output contract 要求「渲染时用实际要发布的 props,而不是 defaultProps」('render with the SAME props you'll ship')。流程上有落点。
- [ok] 与 logo-animation 的 tier 路由一致性 — 本 skill 自述 'this is the heavy-tier counterpart to a web scene's ?t=N';logo-animation 侧写 'For web/SVG/Lottie delivery use this standalone-HTML loop; for a video logo sting, render via the remotion-video verify loop instead.'。两端互指一致。
6結論
3d9caacebfc580bf…