THREE.js:为什么我的物体在沿着花键移动时会翻转?

时间:2014-07-28 14:05:45

标签: math three.js spline

从原始帖子Three.JS Object following a spline path - rotation / tangent issues & constant speed issue开始跟进,我仍然遇到问题,即对象在路径上的某些点翻转。

在这个小提琴上查看此事:http://jsfiddle.net/jayfield1979/T2t59/7/

function moveBox() {
if (counter <= 1) {

    box.position.x = spline.getPointAt(counter).x;
    box.position.y = spline.getPointAt(counter).y;

    tangent = spline.getTangentAt(counter).normalize();

    axis.cross(up, tangent).normalize();

    var radians = Math.acos(up.dot(tangent));

    box.quaternion.setFromAxisAngle(axis, radians);

    counter += 0.005
} else {
    counter = 0;
}

}

上面的代码是沿着定义的样条曲线路径移动我的对象(在这个例子中是一个椭圆)。 @WestLangley提到:“警告:如果两个向量是平行的,则交叉产品没有明确定义。”。

如您所见,从路径的形状来看,我将遇到许多平行向量。我能做些什么来阻止这种翻转吗?

1 个答案:

答案 0 :(得分:3)

回答标题中的原因问题。它发生的原因是在曲线的某些点上,矢量up(1,0,0)和切线是平行的。这意味着它们的叉积为零,四元数的构造失败。

你可以遵循WestLangley的建议。你真的希望向上方向是轨道所在平面的法线。

四元数旋转很难理解setFromAxisAngle函数绕轴旋转给定角度。

如果轨道位于X-Y平面,那么我们将要绕Z轴旋转。要查找角度,请使用Math.atan2查找切线的角度

var angle = Math.atan2(tangent.y,tangent.x);

把这个放在一起

var ZZ = new THREE.Vector3( 0, 0, 1 );

tangent = spline.getTangentAt(counter).normalize();
var angle = Math.atan2(tangent.y,tangent.x);    
box.quaternion.setFromAxisAngle(ZZ, angle);

如果轨道离开X-Y平面,事情就会变得棘手。