
Three.jsの最も単純な例をソースデータとして使用します。
-それは回転する立方体になります。 3D効果をより明るくするために、観察者に向かってもう1つ前方への動きを追加しました。
3次元画像の2つの短縮を取得するために、このようなトリックを行います
各フレームのレンダリングループ内:
-カメラから画面ではなくテクスチャにシーンを描画します
-カメラを移動します(2番目の目の位置まで)
-シーンを異なるテクスチャに描画します
-これで、左目と右目用の写真ができました-左目が左の写真と右目を見るようにそれらを混ぜるだけです-3Dモニターの右の写真。
コードで説明する
(webgl_geometry_cubeの例の基本的なコードは意味がありません。追加したもののみを説明します)
更新:アナグリフをデモに追加していただきありがとうございます。赤青メガネを備えたどのモニターでも試用できます。
// function initORTscene() { //projection to screen rtTexture = new THREE.WebGLRenderTarget(window.innerWidth, window.innerHeight, { minFilter: THREE.LinearFilter, magFilter: THREE.NearestFilter, format: THREE.RGBFormat }); ltTexture = new THREE.WebGLRenderTarget(window.innerWidth, window.innerHeight, { minFilter: THREE.LinearFilter, magFilter: THREE.NearestFilter, format: THREE.RGBFormat }); // - materialScreen = new THREE.ShaderMaterial({ uniforms: { lRacurs: { type: "t", value: ltTexture }, rRacurs: { type: "t", value: rtTexture }, height: { type: "f", value: window.innerHeight } }, vertexShader: document.getElementById('vertexShader').textContent, fragmentShader: document.getElementById('fragmentShader').textContent, depthWrite: false }); // var plane = new THREE.PlaneGeometry(window.innerWidth, window.innerHeight); var offscreenMesh = new THREE.Mesh(plane, materialScreen); offscreenMesh.position.z = -1; //a little behind sceneORT = new THREE.Scene(); // , cameraORT = new THREE.OrthographicCamera(window.innerWidth / -2, window.innerWidth / 2, window.innerHeight / 2, window.innerHeight / -2, -10000, 10000); sceneORT.add(offscreenMesh); }
シェーダー
それらの中で、画面のピクセルで2つのテクスチャとフレームの高さを渡します
頂点シェーダーはポイントの位置を計算し、ピクセルシェーダーに渡します
偶数の垂直線があるかどうかを計算します。偶数線の場合は1つのテクスチャを使用し、奇数線の場合は別のテクスチャを使用します( この記事では、この方法で3D画像を作成する方法を書きました)
<script id="fragmentShader" type="x-shader/x-fragment"> varying vec2 vUv; uniform sampler2D rRacurs; uniform sampler2D lRacurs; uniform float height; void main() { //odd from left racurs, even from right float d = mod((floor(height*(vUv.y+1.0))),2.0); //odd or even, height - is new uniform to get viewport height if(d > 0.1) { gl_FragColor = texture2D( rRacurs, vUv ); } else { gl_FragColor = texture2D( lRacurs, vUv ); } } </script> <script id="vertexShader" type="x-shader/x-vertex"> varying vec2 vUv; void main() { vUv = uv; gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 ); } </script>
今私たちのシーンを描きます
var x = camera.position.x; var faceWidth = 5; // // camera.position.x = x + faceWidth / 2; renderer.render(scene, camera, rtTexture, true); // camera.position.x = x - faceWidth / 2; renderer.render(scene, camera, ltTexture, true); camera.position.x = x; // renderer.render(sceneORT, cameraORT);
以上です。
パッシブ3Dモニターの幸せな所有者は、 デモを見ることができます(通常のモニターでは、それほど美しくはありません)。 コードはgithubにあります
確かに30行のコードではなく、70行以下であり、3D画像を実装するのに必要なのはこれだけです。
faceWidthパラメーターは変更できます-大きいほど、3Dが強くなりますが、幾何学的な歪みが大きくなります。
このコードは、three.js(WebGL)で記述されたすべてのシーンに使用して、実際の3Dを追加できます。たとえば、javascriptの学習の一環として作成したゲームへのリンクを次に示します。
更新:このデモにアナギフ効果を追加してくれたKOLANICHに感謝します-これで、赤青メガネを備えた任意のモニターで視聴できます。 持っていないので確認できませんが、誰かがバグを確認して発見したら、プルリクエストを受け入れます。