React Three Fiber


title: "React Three Fiber" description: "React Three Fiberを使ってReactコンポーネントとしてシェーダーを管理する方法を学びます。" chapter: "10-threejs" order: 3 challenge: description: "useFrameフックを使って、マウスホバー時にメッシュが拡大するアニメーションを追加してください。hover状態を管理し、scaleを滑らかに変化させましょう。" hints:

  • "hover状態をuseStateで管理します。"
  • "meshのonPointerOverとonPointerOutイベントでhover状態を切り替えます。"
  • "useFrame内でscaleをlerpで滑らかに補間します。"

React Three Fiber

React Three Fiber (R3F) とは

React Three Fiber は、Three.jsをReactのコンポーネントとして扱えるようにするレンダラーです。宣言的にThree.jsのシーンを記述でき、Reactのライフサイクルと統合されます。

基本的なセットアップ

R3FではThree.jsのクラスがJSXタグになります:

  • THREE.Meshmesh タグ
  • THREE.BoxGeometryboxGeometry タグ
  • THREE.MeshStandardMaterialmeshStandardMaterial タグ

Canvas コンポーネントの中にこれらのタグを配置してシーンを構築します。

useFrameフック

useFrameは毎フレーム呼ばれるフックで、アニメーションに使います。コールバック関数は statedelta(前フレームからの経過時間)を受け取ります。

// useFrameのイメージ(擬似コード)
// state.clock -- 経過時間
// state.pointer -- マウス座標 (-1 to 1)
// delta -- 前フレームからの秒数
// meshRef.current.rotation.y += delta で毎フレーム回転

refを使ってメッシュの参照を取得し、useFrame内でプロパティを直接更新します。

R3FでShaderMaterialを使う

シェーダーのuniformはuseMemoで初期化し、useFrame内で毎フレーム更新します:

// R3FでのShaderMaterial使用パターン
// 1. useMemoでuniformsオブジェクトを作成
//    u_time, u_resolution を定義
// 2. useFrameで毎フレームuniformの値を更新
//    uniforms.u_time.value = clock.getElapsedTime()
// 3. JSXでshaderMaterialタグを使い、vertexShader, fragmentShader, uniformsを渡す

フラグメントシェーダーの例:

uniform float u_time;
varying vec2 vUv;
void main() {
    vec3 col = 0.5 + 0.5 * cos(u_time + vUv.xyx + vec3(0, 2, 4));
    gl_FragColor = vec4(col, 1.0);
}

dreiライブラリ

@react-three/dreiは便利なヘルパーコンポーネント集です:

  • OrbitControls -- マウスでカメラを操作
  • useTexture -- テクスチャの簡単読み込み
  • Environment -- 環境マッピング
  • Float -- ふわふわ浮遊アニメーション
  • Text -- 3Dテキスト表示

useThreeフック

シーンの情報にアクセスするフックです。size(キャンバスサイズ)、camera(カメラオブジェクト)、pointer(正規化されたマウス座標 -1から1)などの情報を取得できます。

まとめ

  • React Three FiberはThree.jsをReactコンポーネントとして宣言的に記述できる
  • useFrameで毎フレームの更新処理(アニメーション)を記述する
  • shaderMaterialタグでカスタムシェーダーをメッシュに適用できる
  • dreiライブラリが多くの便利なヘルパーを提供する