Three.jsはWebGL表現を簡単に実現できるライブラリ。それでもやはり自前でシェーダを記述すると表現の幅が広がる。Three.jsには自作シェーダを適用可能なRawShaderMaterialとShaderMaterialのクラスがあり、前者は完全に全てのシェーダを自前で記述、後者はシェーダに送られてくる変数等の記述を補間してくれる機能を持つ。
SceneにFogを適用すると距離に応じて遠方をぼかし、Three.js標準機能で作成したMeshも遠ざかれば自動的にFogの適用を受ける。しかし自作シェーダを適用したMeshには、必要な記述を加えないとFogが適用されない。
この記事ではShaderMaterialを使用してMeshを作成したときに、そのMeshに対してFogを適用するための記述がわかったのでメモとして残す。
#SceneにFogを適用する
作成済みのSceneにFogを適用する。Fogは色指定が必須。
const scene = new THREE.Scene();
scene.fog = new THREE.Fog( 0x000000 );
#Uniform変数にFogパラメータを組み込む
Three.jsが保持するFogの情報をUniform変数に組み込む。
const uniforms = THREE.UniformsUtils.merge([
THREE.UniformsLib.fog,
{
//ここには自前で追加するUniform変数を記述
}
]);
#ShaderMaterialを作る
Fogを有効にする
const material = new THREE.ShaderMaterial({
'vertexShader' : vShader, //頂点シェーダの文字列
'fragmentShader' : fShader, //フラグメントシェーダの文字列
'uniforms' : uniforms, //前項で作成したUniform変数
'fog' : true //Fogを適用することを伝える
});
#頂点シェーダに記述を追加する
#includeはThree.jsのための記述(GLSL標準でない)
#include <fog_pars_vertex> //main関数の外に記述
void main () {
//自前の記述
//以下の2行を追加
//positionを変更している場合は変更した値を割り当てる
vec4 mvPosition = modelViewMatrix * vec4( position, 1.0 );
#include <fog_vertex>
}
#フラグメントシェーダに記述を追加する
gl_FragColorで出力色決定後にFogを適用する
#include <fog_pars_fragment> //main関数の外に記述
void main () {
//自前の記述(最後にgl_FragColorで出力色が決まるはず)
//以下の1行を追加(gl_FragColorの後)
#include <fog_fragment>
}
#最後に
人によって記述方法が違う(いろいろな記述があった)。これが一番Three.jsのお作法に則っているような気がした。