TypeScript
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/110/three.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/stats.js/r16/Stats.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/require.js/2.3.6/require.min.js"></script>
CSS
html, body {
margin: 0;
overflow: hidden;
width: 100%;
height: 100%;
position: relative;
}
.canvasWebGL {
position: absolute;
top: 0%;
width: 100%;
height: 100%;
}
.canvas2D {
position: absolute;
top: 50%;
width: 100%;
height: 100%;
}
JavaScript
var camera, scene, renderer, vp, stats;
var canv2D, texCopy;
var vec0 = new THREE.Vector2(0, 0);
var scene2 = new THREE.Scene();
scene2.add(
new THREE.Mesh(
new THREE.PlaneBufferGeometry( 12.6, 12.6 /* some ~tg(fov/2) here */ ),
new THREE.ShaderMaterial({
vertexShader: `
varying vec2 vUv;
void main() {
vUv = uv;
gl_Position = projectionMatrix * modelViewMatrix * vec4(position, 1.0);
}`,
fragmentShader: `
varying vec2 vUv;
uniform sampler2D map;
void main() {
gl_FragColor.rgb = 1.0 - texture2D( map, vUv ).rgb;
gl_FragColor.a = 1.0;
}`,
uniforms: {
map: { /* tbd */ }
}
})
)
);
// Init WebGL stuff
function init() {
// WebGL Renderer
vp = new THREE.Vector2(window.innerWidth, window.innerHeight);
renderer = new THREE.WebGLRenderer({antialias: true});
renderer.setSize(vp.x, vp.y);
renderer.domElement.classList.add("canvasWebGL");
scene2.children[0].scale.x = vp.x / vp.y;
// scene
scene = new THREE.Scene();
scene.background = new THREE.Color(0xe1e1e1);
// camera
camera = new THREE.PerspectiveCamera(35, vp.x / vp.y, 0.05, 100);
camera.position.z = 20;
// stats
stats = new Stats();
// torus
const torus = new THREE.Mesh(
new THREE.TorusKnotBufferGeometry( 2, 0.8, 100, 16 ),
new THREE.MeshNormalMaterial()
);
scene.add(torus);
// Make texture with Uint8Array as source
texCopy = new THREE.DataTexture(
null, vp.x, vp.y, THREE.RGBFormat
);
// append all to DOM
document.body.appendChild(renderer.domElement);
document.body.appendChild(stats.domElement);
}
function animate(s) {
scene.children[0].rotation.set(
s / 1000, s / 777, s / 1000
);
// Render scene to canvas
renderer.render(scene, camera);
// Copy canvas buffer to texCopy
renderer.copyFramebufferToTexture ( vec0, texCopy, 0 );
// Draw some cheap "next pass"
scene2.children[0].material.uniforms.map.value = texCopy;
...