<ThreeCanvas>
React Three Fiber 的 <Canvas /> 的一个封装器,它与 Remotions useCurrentFrame() 同步。
🌐 A wrapper for React Three Fiber's <Canvas /> which synchronizes with Remotions useCurrentFrame().
由于 React Three Fiber 是一个自定义渲染器,通常环绕它的 React 上下文在其内部不起作用。这通常会破坏在 Remotion 中使用它,但这个组件封装了上下文,所以你可以像预期那样编写你的标记。
🌐 Since React Three Fiber is a custom renderer, normally the React contexts that surround it don't work inside. This would normally break the usage of it in Remotion, but this component wraps the contexts so you can write your markup as expected.
与其使用 React Three Fiber 的 useFrame API,你可以(并且必须)使用 Remotion 的 useCurrentFrame API 完全以声明式方式编写你的动画。这将确保你可以在时间轴上前后拖动并暂停动画。
🌐 Instead of using React Three Fibers useFrame API, you can (and must) write your animations fully declaratively using Remotions useCurrentFrame API. This will ensure that you can scrub back and forth in the timeline and pause the animation.
浏览器错误通常会导致布局被破坏,因为我们在 Studio 中对画布应用了 scale 转换。为了解决这个问题,<ThreeCanvas /> 需要设置 width 和 height 属性。
🌐 A browser bug would normally cause the layout to be broken because we apply a scale transform to the canvas in the Studio. To work around this problem, the <ThreeCanvas /> requires the width and height props to be set.
示例
🌐 Example
一个旋转、颜色变化、缩放的立方体。这个示例也可以在 Remotion 仓库的 examples 文件夹中找到。
🌐 A spinning, color changing, scaling cube. This example can also be found in the examples folder of the Remotion repo.
import {ThreeCanvas } from '@remotion/three';
import {interpolate , useCurrentFrame , useVideoConfig } from 'remotion';
const ThreeBasic : React .FC = () => {
const frame = useCurrentFrame ();
const {width , height } = useVideoConfig ();
return (
<ThreeCanvas
orthographic ={false}
width ={width }
height ={height }
style ={{
backgroundColor : 'white',
}}
camera ={{fov : 75, position : [0, 0, 470]}}
>
<ambientLight intensity ={0.15} />
<pointLight args ={[undefined , 0.4]} position ={[200, 200, 0]} />
<mesh position ={[0, 0, 0]} rotation ={[frame * 0.06 * 0.5, frame * 0.07 * 0.5, frame * 0.08 * 0.5]} scale ={interpolate (Math .sin (frame / 10), [-1, 1], [0.8, 1.2])}>
<boxGeometry args ={[100, 100, 100]} />
<meshStandardMaterial color ={[Math .sin (frame * 0.12) * 0.5 + 0.5, Math .cos (frame * 0.11) * 0.5 + 0.5, Math .sin (frame * 0.08) * 0.5 + 0.5]} />
</mesh >
</ThreeCanvas >
);
};
export default ThreeBasic ;frameloop 在渲染过程中的行为
🌐 frameloop behavior during rendering
在渲染过程中,<ThreeCanvas> 会将 frameloop 属性覆盖为 'never',无论你传入什么。这意味着 Three.js 场景不会自动重新渲染——它仅会在通过 advance() 触发时按需重新渲染。
🌐 During rendering, <ThreeCanvas> overrides the frameloop prop to 'never' regardless of what you pass. This means the Three.js scene will not re-render on its own — it is only re-rendered on demand via advance().
如果你异步更新纹理(例如,从 <Video> onVideoFrame 回调),你必须调用 advance(performance.now()) 而不是 invalidate() 来在捕获帧之前同步重新渲染场景。完整示例见 使用视频作为纹理 。
🌐 If you update textures asynchronously (e.g. from a <Video> onVideoFrame callback), you must call advance(performance.now()) instead of invalidate() to synchronously re-render the scene before the frame is captured. See Using a video as a texture for a full example.
<Sequence>注释
🌐 Note on <Sequence>
默认情况下,<Sequence> 会返回一个 <div> 组件,而 <ThreeCanvas> 内不允许使用该组件。为避免错误,请将 layout="none" 传递给 <Sequence>。
🌐 A <Sequence> by default will return a <div> component which is not allowed inside a <ThreeCanvas>. To avoid an error, pass layout="none" to <Sequence>.
在 <ThreeCanvas> 内使用视频
🌐 Using videos inside a <ThreeCanvas>
你可以使用 这个 方法创建一个由 <Video> 支持的 Three.js 纹理。
🌐 You can create a Three.js texture backed by a <Video> by using this approach.
另请参阅
🌐 See also