Hi,
I’m building a 3D lobby with Blender and Three.js, with various doorways around my scene which, when clicked, will cause the camera to animate over to the doorway and open a popup. This is my first proper Three.js projects so i haven’t got much experience!
I’m using the Tween.js library to animate my camera positions on click, and it works fine when i include TWEEN.Update(); in a render loop. The problem is, because i’m using a render loop, my scene is rendering all the time when it really only needs to render when A) the user clicks a doorway to trigger the tween, or B) the OrbitControls are used.
If I remove the render loop I CAN get the the scene updating with OrbitControls using
controls.addEventListener( 'change', render);
However, I don’t know how to render the tween animation anymore. Could anybody point me in the right direction? i almost need a loop that only runs on demand and then stops.
My move function is included below. Target lookAt co-ordinates (TargetObject X,Y,Z) and camera position (camera X,Y,Z) and animation length in time (time) are passed into the function:
//ANIMATE CAMERA TO NEW POSITION
function moveTo(targetObjectX, targetObjectY, targetObjectZ, cameraX, cameraY, cameraZ, time) {
// SET START AND END POSITIONS FOR THE CAMERA
var from = {
x: camera.position.x,
y: camera.position.y,
z: camera.position.z,
lookx: currentTargetObjectX,
looky:currentTargetObjectY,
lookz:currentTargetObjectZ,
};
var to = {
x: cameraX,
y: cameraY,
z: cameraZ,
lookx:targetObjectX,
looky:targetObjectY,
lookz:targetObjectZ,
};
tween = new TWEEN.Tween(from)
.to(to, time)
.easing(TWEEN.Easing.Quadratic.InOut)
.onUpdate(function () {
// SET CAMERA POSITION AND ROTATION THAT THE CAMERA WILL START THE ANIMATION FROM
camera.position.set(from.x, from.y, from.z);
camera.lookAt(
from.lookx, from.looky, from.lookz
);
})
.onComplete(function () {
document.body.style.cursor = "default";
// OPEN AN INFORMATION POPUP IF REQUIRED
if (popUpOpen == true) {
setTimeout (function() {modalInner.classList.remove("hidden"); }, 300);
}
})
.start();
}
As I said the function worked fine when i included a render loop originally (below):
// ----------------- UPDATE FUNCTIONS (THESE DRAW THE SCENE AND UPDATE IT ON CHANGES) ------------------
// GAME LOGIC
var update = function( ){
TWEEN.update();
};
// DRAW SCENE
var render = function( ){
renderer.render( scene, camera);
};
// RUN GAME LOOP (UPDATE, RENDER, REPEAT)
var GameLoop = function( ) {
requestAnimationFrame (GameLoop);
update( );
render( );
};
// RUN UPDATE FUNCTION AT LEAST ONCE (IT WILL BE AUTOMATICALLY REPEATED WITHIN THE FUNCTION)
GameLoop( );
Any help will be gratefully received!