Reputation: 195
I don't understand why my camera doesn't slerp back. When I refresh the page, it slerps once. Then after that, it doesn't do anything if I move my mousewheel. I expect it to slerp back forward (as I scroll up and down) between the x quaternions.
export default class Experience {
constructor(options = {}) {
//...
this.camera = new Camera();
this.renderer = new Renderer(this.canvas);
this.scrollTargetPosition = new THREE.Quaternion();
this.scrollTargetPosition.setFromAxisAngle(new THREE.Vector3(0, 0, 1),0);
this.onMouseScroll();
this.animate();
}
onMouseScroll() {
window.addEventListener("wheel", (event) => {
if (event.wheelDelta > 0) {
this.scrollTargetPosition.x = 0;
} else {
this.scrollTargetPosition.x = Math.PI / 2;
}
console.log("Target: " + this.scrollTargetPosition.x); //Pictures below
console.log("Camera: " + this.camera.quaternion.x);
});
}
animate() {
this.camera.quaternion.slerp(this.scrollTargetPosition, 0.9);
requestAnimationFrame(this.animate.bind(this));
this.renderer.render(this.scene, this.camera);
}
}
Here's what the console.log's look like if I scroll up a bunch of times:
and if I scroll down:
Upvotes: 0
Views: 1110
Reputation: 28462
The main problem is that you're treating a Quaternion as if it were Euler angles, and they are hugely different.
Quaternion.x is not the x-axis rotation in radians. Quaternions are made up of a 4-dimensional combination of imaginary and real numbers, so its x, y, z, w
properties are better left alone. Instead, use the utility methods that performs the task you need. The method below sets the x-axis rotation to 0 or 90 degrees:
onMouseScroll() {
let xAxis = new THREE.Vector3(1, 0, 0);
window.addEventListener("wheel", (event) => {
if (event.wheelDelta > 0) {
this.scrollTargetPosition.setFromAxisAngle(xAxis, 0);
} else {
this.scrollTargetPosition.setFromAxisAngle(xAxis, Math.PI / 2);
}
});
}
After that, you should be able to perform your spherical interpolation as expected, however I recommend you replace the 0.9
with a smaller number like 0.1
, otherwise it'll pop into place too quickly:
this.camera.quaternion.slerp(this.scrollTargetPosition, 0.9);
Upvotes: 3