How To Animate Camera.lookAt using Three JS

2020-05-15 05:08发布

I have a scene which renders a board with several objects. Clicking on one of the objects and by use of object picking I can get the object and animate the cameras position to sit in an 'overhead' view of the object. Then using the camera.lookAt method I can force the camera to look directly at the object.

I am noticing a quick jump at the start of my animation when calling camera.lookAt within the onUpdate method as it initially has a large distance to rotate to look at the object selected. Each subsequent call to camera.lookAt is tiny in comparison and is animated nicely.

// Position the camera to fit
var tween = new TWEEN.Tween(camera.position).to({
    x: selectedObject.position.x,
    y: selectedObject.position.y,
    z: 1
}).easing(TWEEN.Easing.Quadratic.InOut).onUpdate(function() {
    camera.lookAt(selectedObject.position);
}).onComplete(function() {
    camera.lookAt(selectedObject.position);
}).start();

Is there any way to animate the method or will I have to manually transform the matrix values of the camera to look at my selected object?

Here is a fiddle with an example. It uses WebGLRenderer so please use a suitable browser.

http://jsfiddle.net/fungus1487/SMLwa/

Thanks for any help.

2条回答
来,给爷笑一个
2楼-- · 2020-05-15 05:22

WestLangley's answer works but seems oddly lengthy. I used the following with a pre-defined position(xyz) and target(xyz). Using perspective camera and trackball controls.

new TWEEN.Tween( camera.position ).to( {
    x: position.x,
    y: position.y,
    z: position.z}, 600 )
  .easing( TWEEN.Easing.Sinusoidal.EaseInOut).start();
new TWEEN.Tween( controls.target ).to( {
    x: target.x,
    y: target.y,
    z: target.z}, 600 )
  .easing( TWEEN.Easing.Sinusoidal.EaseInOut).start();
查看更多
走好不送
3楼-- · 2020-05-15 05:46

One thing you can do is tween both the camera position and the camera target (which you have to define).

var tween = new TWEEN.Tween( camera.position )
    .to( {
        x: selectedObject.position.x,
        y: selectedObject.position.y,
        z: 1
    } )
    .easing( TWEEN.Easing.Linear.None ).onUpdate( function () {

        camera.lookAt( camera.target );

    } )
    .onComplete( function () {

        camera.lookAt( selectedObject.position );

    } )
    .start();

var tween = new TWEEN.Tween( camera.target )
    .to( {
        x: selectedObject.position.x,
        y: selectedObject.position.y,
        z: 0
    } )
    .easing( TWEEN.Easing.Linear.None )
    .onUpdate( function () {

    } )
    .onComplete( function () {

        camera.lookAt( selectedObject.position );

    } )
    .start();

It's a little tricky, because the tween's need to run exactly concurrently, and they don't... This is the reason for the camera.lookAt() call in the second tween.

查看更多
登录 后发表回答