对象在旋转时缩小 javascript
Object shrinks when rotated javascript
我一直在开发一个基本的游戏引擎,只是为了学习这个过程,但我的旋转功能遇到了问题。
它工作正常,只是对象缩小并出现反转。
这里 jsfiddle 说明了我的观点。
我认为问题出在轮换代码本身,但我并不肯定。
function Rotation(vec, rot){
if(Math.acos((vec.x + vec.y + vec.z -1)/2) === 0) { return vec; }
var qVec = new Quaternion(vec.x, vec.y, vec.z, 0);
qVec = Quaternions.multiply(qVec, rot);
qVec = Quaternions.multiply(qVec, rot.conjugate());
return new Vector3(qVec.x, qVec.y, qVec.z);
}
两件事:
首先,旋转四元数没有归一化,所以它的逆和它的共轭是不一样的。四元数的旋转定义为:
其中 q
是您旋转的矢量,p
是您旋转的矢量,p'
是最终旋转的矢量。
所以这是用q的逆定义的,定义为conjugate(q) / magnitude(q)^2
。在 q 归一化的情况下,magnitude(q)^2 == 1
,所以它与只乘以共轭是一样的。
还要注意这里的操作顺序。 Quat 乘法 不可交换 所以它们的顺序很重要。
您可以通过标准化旋转四元数和固定操作顺序来解决此问题:
var qVec = new Quaternion(vec.x, vec.y, vec.z, 0);
qVec = Quaternions.multiply(rot.normalize(), qVec);
qVec = Quaternions.multiply(qVec, rot.conjugate());
return new Vector3(qVec.x, qVec.y, qVec.z);
其次,您要将旋转 quat 定义为垂直于要围绕其旋转的平面。在这种情况下,您想要绕 x-y 平面旋转。 z轴垂直于这个平面,所以我们要定义沿z轴的旋转向量:
function update(){
for(var i = 0; i < gameObjects.length; i++){
gameObjects[i].rotation = euler(new Vector3(0, 0, frames/100));
}
}
通过这些更改,我能够使盒子正确旋转。
(至于为什么它会扩展 up/down,我不是 100% 确定。仍在尝试弄清楚。)
我一直在开发一个基本的游戏引擎,只是为了学习这个过程,但我的旋转功能遇到了问题。
它工作正常,只是对象缩小并出现反转。
这里 jsfiddle 说明了我的观点。
我认为问题出在轮换代码本身,但我并不肯定。
function Rotation(vec, rot){
if(Math.acos((vec.x + vec.y + vec.z -1)/2) === 0) { return vec; }
var qVec = new Quaternion(vec.x, vec.y, vec.z, 0);
qVec = Quaternions.multiply(qVec, rot);
qVec = Quaternions.multiply(qVec, rot.conjugate());
return new Vector3(qVec.x, qVec.y, qVec.z);
}
两件事:
首先,旋转四元数没有归一化,所以它的逆和它的共轭是不一样的。四元数的旋转定义为:
其中 q
是您旋转的矢量,p
是您旋转的矢量,p'
是最终旋转的矢量。
所以这是用q的逆定义的,定义为conjugate(q) / magnitude(q)^2
。在 q 归一化的情况下,magnitude(q)^2 == 1
,所以它与只乘以共轭是一样的。
还要注意这里的操作顺序。 Quat 乘法 不可交换 所以它们的顺序很重要。
您可以通过标准化旋转四元数和固定操作顺序来解决此问题:
var qVec = new Quaternion(vec.x, vec.y, vec.z, 0);
qVec = Quaternions.multiply(rot.normalize(), qVec);
qVec = Quaternions.multiply(qVec, rot.conjugate());
return new Vector3(qVec.x, qVec.y, qVec.z);
其次,您要将旋转 quat 定义为垂直于要围绕其旋转的平面。在这种情况下,您想要绕 x-y 平面旋转。 z轴垂直于这个平面,所以我们要定义沿z轴的旋转向量:
function update(){
for(var i = 0; i < gameObjects.length; i++){
gameObjects[i].rotation = euler(new Vector3(0, 0, frames/100));
}
}
通过这些更改,我能够使盒子正确旋转。
(至于为什么它会扩展 up/down,我不是 100% 确定。仍在尝试弄清楚。)