I want to create an interactive 2D video using three.js and maintain the aspect ratio of the video when resizing the browser window.
Here is the code I am currently using:
var camera, scene, renderer;
var texture_placeholder,
distance = 500;
init();
render();
function init() {
var container, mesh;
container = document.getElementById('container');
camera = new THREE.PerspectiveCamera(90, 1, 0.1, 50000);
camera.target = new THREE.Vector3(0, 0, 0);
scene = new THREE.Scene();
var videoRatio = 16 / 9;
var geometry = new THREE.PlaneBufferGeometry(1.7, 1);
var video = document.createElement('video');
video.width = 960;
video.height = 540;
video.autoplay = true;
video.loop = true;
video.mute = true;
video.setAttribute('crossorigin', 'anonymous');
video.src = "http://commondatastorage.googleapis.com/gtv-videos-bucket/sample/BigBuckBunny.mp4"
var texture = new THREE.VideoTexture(video);
texture.minFilter = THREE.LinearFilter;
texture.format = THREE.RGBFormat;
var material = new THREE.MeshBasicMaterial({
map: texture
});
video.onplay = function() {
onWindowResize();
}
mesh = new THREE.Mesh(geometry, material);
scene.add(mesh);
renderer = new THREE.WebGLRenderer({
depth: true
});
renderer.setPixelRatio(window.devicePixelRatio);
renderer.setSize(window.innerWidth, window.innerHeight);
container.appendChild(renderer.domElement);
window.addEventListener('resize', onWindowResize, false);
var playBtn = document.getElementById("play_btn").onclick = function() {
console.log("[DEBUG] play button clicked");
video.play();
renderer.setSize(window.innerWidth, window.innerHeight);
}
}
function onWindowResize() {
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
console.log("[DEBUG] onWindowResize");
}
function render() {
requestAnimationFrame(render);
update();
}
function update() {
camera.updateProjectionMatrix();
camera.position.z = 0.5;
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.render(scene, camera);
}
<script src="//cdnjs.cloudflare.com/ajax/libs/three.js/109/three.js"></script>
<button id="play_btn">play</button>
<div id="container"></div>
Check out the Codepen demo here: https://codepen.io/mr1985/pen/OJVOKgY
I am currently using an iframe to solve the issue with maintaining aspect ratio, but I would prefer to handle it directly with three.js. Here is the code for my iframe for reference:
<style>
.iframe-container {
overflow: hidden;
padding-top: 56.25%;
position: relative;
}
.iframe-container iframe {
border: 0;
height: 100%;
left: 0;
position: absolute;
top: 0;
width: 100%;
}
</style>
<div class="iframe-container">
<iframe width="960" height="540" src="http://localhost:8000/mini_player.html" frameborder="0" allowfullscreen scrolling="no"</iframe>
</div>
Any assistance on this matter would be greatly appreciated.