はじめに
Three.jsでGLBモデルを使った演出を作っていると、
「元の色・テクスチャが消えた」
「Shaderを使ったら全部真っ白になった」
「動かしたいのは形だけなのに見た目が壊れる」
という壁に必ずぶつかります。
今回は、
GLBの見た目を一切壊さずに「たれ感のある動き」だけを追加する方法を
実際にハマった失敗も含めて解説します。
やりたかったこと
parfaitの sauce.glb だけ に
垂れているような「ゆらゆら動く演出」を入れたい
元の色・テクスチャ・ライティングはそのまま
よくある失敗
最初にやりがちなのがこれ👇
obj.material = new THREE.ShaderMaterial(...)
これをやると…
GLBに設定された
ベースカラー
テクスチャ
ライティング情報
👉 すべて消える
結果、
「動くけど真っ白なモデル」 になります。
正解アプローチ
ShaderMaterialに置き換えない
Three.jsには便利な仕組みがあります。
onBeforeCompile
これを使うと
「元のマテリアルに、少しだけShaderを足す」 ことができます。
実装コード(最小構成)
① たれ演出を追加する関数
function enableSauceDrip(material) {
material.onBeforeCompile = (shader) => {
shader.uniforms.uTime = { value: 0 };
shader.vertexShader = shader.vertexShader.replace(
'#include <begin_vertex>',
`
#include <begin_vertex>
// 下に行くほど少し揺れる
float drip = smoothstep(0.1, -0.6, transformed.y);
transformed.y += sin(uTime) * drip * 0.01;
`
);
material.userData.shader = shader;
};
material.needsUpdate = true;
}
② sauce.glb だけに適用
model.traverse(obj => {
if (!obj.isMesh) return;
obj.castShadow = true;
obj.receiveShadow = true;
if (item.file === "sauce.glb") {
enableSauceDrip(obj.material);
}
});
③ アニメーションループ
parfaitGroup.traverse(obj => {
if (obj.isMesh && obj.material.userData.shader) {
obj.material.userData.shader.uniforms.uTime.value += 0.05;
}
});
結果
GLBの色・質感 → そのまま
ライティング → 崩れない
sauce だけ → 自然にたれる動き
他の具材 → 影響なし
Shader初心者でも
「これだけでいい」 という実装です。
まとめ
見た目を壊したくない場合
👉 ShaderMaterial は使わない
動きだけ足したい場合
👉 onBeforeCompile を使う
GLB演出は「置き換え」より「拡張」
Three.jsで
「ちょっとリッチな表現を入れたい」
そんなときに使えるテクニックです。
おわりに(ココナラ誘導用)
Three.js・GLB・Shaderを使った
Web向け演出・アニメーション実装の相談も受け付けています。
「こういう動きできる?」
「このモデルを動かしたい」など
お気軽にご相談ください。