2015-09-22 431 views
0

我剛剛開始學習three.js,並且遇到了一些麻煩,需要編寫一個函數,該函數以參數的形式獲取對象位置(Vector3)和時間(以毫秒爲單位),然後逐漸旋轉相機在那個時候面對它。基本上是內置lookAt方法的一個lerp版本。threejs:順利地將相機朝一個物體旋轉

首先我試着使用tweenjs來獲得平滑的旋轉過渡。對於開始和結束參數,我創建了一個虛擬對象並將其位置,旋轉和四元數設置爲與攝影機相同,然後我使用lookAt函數面向對象,並將其四元數存儲在新變量「targetQuaternion」。然後我使用這個變量作爲TWEEN.Tween方法中的目標參數來更新camera.quaternion。我已經嘗試過用四元數來避免gymbal鎖,然後旋轉,但沒有任何工作正常。

function rotateCameraToObject(object3D, time) { 

var cameraPosition = camera.position.clone();    // camera original position 
var cameraRotation = camera.rotation.clone();    // camera original rotation 
var cameraQuaternion = camera.quaternion.clone();   // camera original quaternion 

var dummyObject = new THREE.Object3D();      // dummy object 


// set dummyObject's position, rotation and quaternion the same as the camera 
dummyObject.position.set(cameraPosition.x, cameraPosition.y, cameraPosition.z); 
dummyObject.rotation.set(cameraRotation.x, cameraRotation.y, cameraRotation.z); 
dummyObject.quaternion.set(cameraQuaternion.x, cameraQuaternion.y, cameraQuaternion.z); 


// lookAt object3D 
dummyObject.lookAt(object3D); 

// store its quaternion in a variable 
var targetQuaternion = dummyObject.quaternion.clone(); 


// tween start object 
var tweenStart = { 
    x: cameraQuaternion.x, 
    y: cameraQuaternion.y, 
    z: cameraQuaternion.z, 
    w: cameraQuaternion.w 
}; 

//tween target object 
var tweenTarget = { 
    x: targetQuaternion.x, 
    y: targetQuaternion.y, 
    z: targetQuaternion.z, 
    w: targetQuaternion.w 
}; 

// tween stuff 
var tween = new TWEEN.Tween(tweenStart).to(tweenTarget, time); 

tween.onUpdate(function() { 
    camera.quaternion.x = tweenStart.x; 
    camera.quaternion.y = tweenStart.y; 
    camera.quaternion.z = tweenStart.z; 
    camera.quaternion.w = tweenStart.w; 
}); 

tween.start(); 

}

所以這是行不通的。

我也嘗試另一種方法,計算相機矢量和目標矢量和使用角度旋轉目標之間的角度:

function rotateCameraToObject(object3D, time) { 

// camera original position 
var cameraPosition = camera.position.clone(); 

// object3D position 
var objectPosition = object3D.position.clone(); 

// direction vector from camera towards object3D 
var direction = objectPosition.sub(cameraPosition); 

// compute Euler angle 
var angle = new THREE.Euler(); 
angle.setFromVector3(direction); 


/* 
* tween stuff  
*/ 
var start = { 
    x: camera.rotation.clone().x, 
    y: camera.rotation.clone().y, 
    z: camera.rotation.clone().z, 
} 

var end = { 
    x: angle._x, 
    y: angle._y, 
    z: angle._z, 
} 

var tween = new TWEEN.Tween(start).to(end, time); 

tween.onUpdate(function() { 
    camera.rotation.y = start.x; 
    camera.rotation.y = start.y; 
    camera.rotation.y = start.z; 
}); 

tween.start();  

}

這不起作用都不是,最終的相機向物體旋轉但旋轉不正確。

任何幫助?相機具有lerp旋轉功能的正確方法是什麼?

在此先感謝!

回答

0

你是否更新過動畫循環中的補間?

function animate() { 
    requestAnimationFrame(animate); 

    TWEEN.update(); 

    render(); 
} 

但是它可能會更好使用四元數,而不是旋轉轉對象 - 防止萬向節鎖定。 THREE.js提供了一個方便的函數來使用球面線性插值(slerp),而不是使用補間(lerp),它可以給你不希望的結果,最顯着的是在180度轉彎處。把它放在你的動畫循環中。

camera.quaternion.slerp(targetQuaternion,t); //t = normalized value 0 to 1 

然後,您可以吐溫牛逼給你你想要的寬鬆政策。