I have a PerspectiveCamera
and control it with OrbitControls
. After my init()
function is called (this is just a cube, at world center), I call my animate()
function:
function animate() {
requestAnimationFrame(animate);
controls.update();
console.log('animation',controls.getAzimuthalAngle(), controls.getPolarAngle(),camera.position.x);
};
This nicely logs the values that I need, see screenshot below.
Question: Is there an elegant way to trigger/call a function if the user has not moved the camera position in the last second? I would prefer to wait x number of frames or seconds before that function is called.
In my actual application, that function will use the FileLoader
to load a new JSON file, and I do not want to retrieve that file while the user is still moving around and has not waited for about 1 second.
Just a quick idea, there might be way better solutions.
class CustomDelay{
constructor(){
this.timer = null;
}
Timeout(fun= ()=>{},ms){
clearTimeout(this.timer);
this.timer = setTimeout(()=>{
fun()
},ms)
}
}
const myDelay = new CustomDelay();
window.addEventListener('click', function () {
console.log('Clicked');
myDelay.Timeout(() => {
console.log('DELAY');
},1000);
});
You would have to call Timeout method every time you move your camera
1 Like
Thanks for your reply!
I have tried to plug your code into my project and it works for the click
event as you can see in my jsfiddle. I also tried to trigger the cameraOrbitChange()
function on the scroll
, wheel
, or mousewheel
events, but failed. As I am working on an Earth visualization, users will zoom in and out with the mousewheel, which should trigger a change in the camera position and update the map.
I apologize if my jsfiddle is not super cleaned up. Truly appreciate your help!
Edit: I just noticed that my three.js application starts as a small black box in the upper right corner, you just have to click-and-drag it and the cube will show up - not sure why that is…
I was thinking about this kind of check:
https://jsfiddle.net/szyt9nka/1/
const myDelay = new CustomDelay();
var camX = camera.position.x;
var camY = camera.position.y;
var camZ = camera.position.z;
function render() {
if (camX !== camera.position.x && camY !== camera.position.y && camZ !== camera.position.z) {
myDelay.Timeout(() => {
cameraOrbitChange();
}, 1000);
}
camX = camera.position.x;
camY = camera.position.y;
camZ = camera.position.z;
renderer.render(scene, camera);
}
but in your fiddle you’re rendering scene after camera update, so you could also use this code:
const myDelay = new CustomDelay();
function render() {
myDelay.Timeout(() => {
cameraOrbitChange();
}, 1000);
renderer.render(scene, camera);
}
Edit: black box shows up because you forgot to call render function
Thanks, @MateuszWis! This works beautifully. I updated my code with the render()
function you provided, and it works exactly as expected. Good stuff!