Remotion 教程 01:为什么用 React 生成视频
如果你会 React,又想做可复用、可批量生成的视频,Remotion 是一个很自然的选择。
它不是让你在网页里播放动画再录屏,而是让你用 React 组件描述视频画面。Remotion 会按照固定帧率,一帧一帧渲染这些组件,最后合成视频文件。
这篇先不讲复杂生态,也不讲 AI 成片。我们先解决第一件事:Remotion 到底是什么,一个视频入口怎么定义,为什么 frame 是视频动画的核心。
Remotion 适合什么
Remotion 可以理解为“用 React 写视频”的工具链。你写的仍然是组件、props、样式和 TypeScript,但最终产物不是网页,而是视频。
它适合这些场景:
- 图文短视频模板
- 产品介绍视频
- 口播字幕视频
- 数据报告视频
- AI 批量生成视频
- 需要参数化换标题、换素材、换主题色的视频
传统剪辑软件适合一次性创作。Remotion 更适合把视频做成模板:输入不同数据,生成不同视频。
它和网页动画有什么不同
网页动画通常关心“浏览器经过了多少时间”。例如 CSS transition、CSS animation、Motion 的 runtime 动画,都很适合网页交互。
但视频生成更关心这些问题:
第 0 帧是什么画面?
第 1 帧是什么画面?
第 2 帧是什么画面?Remotion 会把 React 组件放到浏览器里渲染,但它最终要得到的是一张张确定的画面。只要输入数据和帧号一样,同一帧就应该得到同样的结果。
这就是后面会反复出现的原则:
用 frame 决定画面状态一个视频入口叫 Composition
在 Remotion 里,一个可预览、可渲染的视频入口叫 Composition。
你可以把它理解成“一个视频模板的注册信息”。它会告诉 Remotion:
- 这个视频叫什么
- 由哪个 React 组件负责画面
- 总共有多少帧
- 每秒多少帧
- 输出尺寸是多少
最小形式大概是这样:
<Composition
id="CoreBasics"
component={CoreBasics}
durationInFrames={150}
fps={30}
width={1920}
height={1080}
/>这段配置表示:
id="CoreBasics":视频入口名称component={CoreBasics}:画面由CoreBasics组件渲染durationInFrames={150}:总共 150 帧fps={30}:每秒 30 帧width={1920}/height={1080}:输出 1080p 横屏视频
150 帧除以 30fps,就是 5 秒。
组件怎么知道当前是第几帧
视频画面最终还是 React 组件。不同的是,组件里可以用 useCurrentFrame() 拿到当前帧号:
const frame = useCurrentFrame();如果 Remotion 正在渲染第 0 帧,frame 就是 0。
如果正在渲染第 60 帧,frame 就是 60。
拿到 frame 之后,就可以把帧号转换成透明度、位移、缩放、旋转等样式值。
例如:
const opacity = interpolate(frame, [24, 44], [0, 1], {
extrapolateLeft: "clamp",
extrapolateRight: "clamp",
});这段代码表示:
- 第 24 帧之前,透明度是 0
- 第 24 到第 44 帧之间,透明度从 0 变成 1
- 第 44 帧之后,透明度保持 1
这里没有 CSS transition。每一帧的透明度都是由当前 frame 算出来的。
Sequence 用来安排时间轴
除了让元素渐显,视频里还经常需要安排“某段内容从第几帧开始出现”。
Remotion 里可以用 Sequence:
<Sequence from={36}>
<div>这段内容从第 36 帧开始出现</div>
</Sequence>from={36} 表示里面的内容从第 36 帧开始进入时间轴。
它不是让浏览器等待真实时间,而是告诉 Remotion:这段内容在视频时间轴上的起点是第 36 帧。
完整最小示例
前面讲完概念后,再看一个完整例子会更清楚。
这个例子包含两个文件:
src/Root.tsx
src/CoreBasics.tsx先注册视频入口:
// src/Root.tsx
import { Composition } from "remotion";
import { CoreBasics } from "./CoreBasics";
export const RemotionRoot = () => {
return (
<Composition
id="CoreBasics"
component={CoreBasics}
durationInFrames={150}
fps={30}
width={1920}
height={1080}
/>
);
};再写真正的画面组件:
// src/CoreBasics.tsx
import React from "react";
import {
AbsoluteFill,
Sequence,
interpolate,
useCurrentFrame,
} from "remotion";
export const CoreBasics: React.FC = () => {
const frame = useCurrentFrame();
const opacity = interpolate(frame, [24, 44], [0, 1], {
extrapolateLeft: "clamp",
extrapolateRight: "clamp",
});
return (
<AbsoluteFill
style={{
backgroundColor: "#f8fafc",
padding: 96,
fontFamily: "Inter, sans-serif",
}}
>
<h1 style={{ margin: 0, fontSize: 72 }}>
视频由一帧一帧组成
</h1>
<Sequence from={36}>
<div
style={{
marginTop: 120,
display: "grid",
gridTemplateColumns: "repeat(4, 1fr)",
gap: 24,
opacity,
}}
>
{["Composition", "fps", "frame", "Sequence"].map((label) => (
<div
key={label}
style={{
padding: 32,
borderRadius: 8,
backgroundColor: "#2563eb",
color: "white",
fontSize: 34,
fontWeight: 800,
textAlign: "center",
}}
>
{label}
</div>
))}
</div>
</Sequence>
</AbsoluteFill>
);
};这段代码做了几件事:
Composition注册了一个 5 秒、30fps、1920x1080 的视频CoreBasics是真正的画面组件useCurrentFrame()拿到当前帧号interpolate()把帧号转换成透明度Sequence from={36}让卡片从第 36 帧开始出现- 数组
map()生成四张概念卡片
怎么创建项目
新项目可以用官方脚手架创建:
npx create-video@latest脚手架会让你选择模板。创建完成后进入项目目录,安装依赖并启动 Remotion Studio:
npm install
npm run devnpm run dev 会打开 Remotion Studio。你可以在左侧选择 Composition,在中间预览画面,在时间轴上拖动帧号。
如果要渲染视频,可以用:
npx remotion render CoreBasics安装后有哪些关键文件
Remotion 项目看起来像一个 React 项目,但有几个文件最值得先看。
package.json
package.json 里有项目命令和依赖。常见命令包括:
{
"scripts": {
"dev": "remotion studio",
"build": "remotion bundle",
"lint": "eslint src && tsc"
}
}dev 用来启动 Studio。真正渲染视频时,可以使用:
npx remotion render CoreBasicssrc/index.ts
src/index.ts 是 Remotion 的入口文件。它会把根组件注册给 Remotion,平时不需要频繁改,但它决定项目从哪里启动。
src/Root.tsx
src/Root.tsx 是新手最应该先看的文件。它决定 Studio 左侧有哪些视频入口,也就是项目里注册了哪些 Composition。
画面组件
Composition 只负责注册入口,真正显示画面的代码通常会拆到单独组件里。比如上面的最小示例是 src/CoreBasics.tsx,配套示例里对应的是 src/lessons/CoreBasics.tsx。
你会在这些组件里看到 useCurrentFrame()、interpolate()、Sequence 这类代码。它们负责把当前帧号转换成画面状态。
public/
public/ 放静态素材,例如图片、音频、视频。在 Remotion 组件里可以用 staticFile() 引用这些素材。
remotion.config.ts
remotion.config.ts 是 Remotion 配置文件。它会影响打包、渲染和一些生态能力,比如 Tailwind、Skia 或自定义 webpack 配置。
一开始不需要深入配置文件,但要知道它是项目渲染能力的配置入口。
配套示例怎么看
这组文章有一个可运行的示例项目。第一节对应:
Composition: LessonCoreBasics
文件: src/lessons/CoreBasics.tsx示例项目为了复用样式,把标题组件、颜色和布局拆到了 src/course/ 目录。所以项目里的文件会比上面的最小示例多一些封装,但核心逻辑是一样的:
Root.tsx 注册 Composition
Composition 指向 React 组件
组件用 frame 计算画面
Remotion 把每一帧合成视频打开 LessonCoreBasics 后,可以做两个小练习:
- 把四张卡片的顺序前后交换。
- 把其中一张卡片的颜色换成黄色。
然后在 Studio 里拖动时间轴。只要停在同一帧,画面就应该始终稳定。
下一篇继续讲这个稳定性的来源:为什么 Remotion 动画必须由 frame 决定。