ThreejsのCubeCameraとPostProcessingを使い、360度映像でよく使われる正距円筒図法(Equirectangular)でレンダリングできるようにした。キャプチャすれば360度動画も作れるだろう。
実装方法
こちら を参考にした(というかほぼパクリだ)。PostProcessingで使えるようにTHREE.ShaderPassに渡せるシェーダーとして書き直した。THREE.CubeCameraから、samplerCube(キューブ上のテクスチャ)が得られるので、それをglslのtextureCubeというメソッドを使って色取得&平面にマッピングしている(ようだ)。
//ref https://github.com/spite/THREE.CubemapToEquirectangular
THREE.EquirectanglarShader = {
uniforms: {
"map": { type: "t", value: null }
},
vertexShader: [
"varying vec2 vUv;",
"void main() {",
"vUv = vec2( 1.- uv.x, uv.y );",
"gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );",
"}"
].join("\n"),
fragmentShader: [
"uniform samplerCube map;",
"varying vec2 vUv;",
"#define M_PI 3.1415926535897932384626433832795",
"void main() {",
"vec2 uv = vUv;",
"float longitude = uv.x * 2. * M_PI - M_PI + M_PI / 2.;",
"float latitude = uv.y * M_PI;",
"vec3 dir = vec3(",
"- sin( longitude ) * sin( latitude ),",
"cos( latitude ),",
"- cos( longitude ) * sin( latitude )",
");",
"normalize( dir );",
"gl_FragColor = vec4( textureCube( map, dir ).rgb, 1. );",
"}"
].join("\n")
};
使い方
//準備
equirectanglerEffect = new THREE.ShaderPass( THREE.EquirectanglarShader );
effectComposer.addPass( equirectanglerEffect );
//毎フレームcube cameraの結果を渡す
cubeCamera.updateCubeMap(renderer,scene);
equirectanglerEffect.uniforms[ 'map' ].value = cubeCamera.renderTarget;
サンプルコード