Javascript 相对于平面的运动
我当前的相机代码有问题。在我的应用程序中,我可以旋转正在查看的模型,但也需要能够行走模型。这意味着用户可以更改模型的相对方向,但仍需要相对于模型平面进行行走和旋转 例如,想象一下,像一座建筑物一样,正面看模型,这样您就可以看到建筑物的侧面。在这种情况下,如果用户按W键,他们将更靠近建筑物。现在,他们可以选择旋转模型的俯仰,这样他们现在可以看到模型的屋顶,或者用户可以选择向上看,然后向下看地面。在这种情况下,击打W需要保持现有高度,并向屏幕顶部移动。通常,运动需要感觉好像是相对于模型的平面行走,即使该平面已相对于您的视点旋转 左右看也存在同样的问题。假设您再次查看建筑的侧面,然后按箭头键向右或向左查看。此时的旋转与模型位于同一平面内。但是,如果用户旋转模型的俯仰以查看屋顶,那么他们会向右看,它会围绕摄影机的位置旋转,看起来就像模型在旋转,而不仅仅是旋转。想象一下站在地上向下看。摄像机的旋转看起来像是世界在旋转,但这不是我得到的。我让模型旋转离开,就像你旋转眼睛看天空一样 这是我的更新功能Javascript 相对于平面的运动,javascript,math,graphics,webgl,Javascript,Math,Graphics,Webgl,我当前的相机代码有问题。在我的应用程序中,我可以旋转正在查看的模型,但也需要能够行走模型。这意味着用户可以更改模型的相对方向,但仍需要相对于模型平面进行行走和旋转 例如,想象一下,像一座建筑物一样,正面看模型,这样您就可以看到建筑物的侧面。在这种情况下,如果用户按W键,他们将更靠近建筑物。现在,他们可以选择旋转模型的俯仰,这样他们现在可以看到模型的屋顶,或者用户可以选择向上看,然后向下看地面。在这种情况下,击打W需要保持现有高度,并向屏幕顶部移动。通常,运动需要感觉好像是相对于模型的平面行走,即
mat4.identity(this.eyeMatrix);
mat4.identity(this.orbitMatrix);
mat4.identity(this.mvMatrix);
mat4.fromRotationTranslation(eyeMatrix, this.eyeRotation, [0, 0, 0]);
mat4.fromRotationTranslation(orbitMatrix, this.orbitRotation, [0, 0, 0]);
mat4.translate(this.mvMatrix, this.mvMatrix, this.orbit);
mat4.multiply(this.mvMatrix, this.mvMatrix, this.orbitMatrix);
mat4.translate(this.mvMatrix, this.mvMatrix, this.eye);
mat4.multiply(this.mvMatrix, this.mvMatrix, this.eyeMatrix);
this.getModelViewMatrix();
this.getProjectionMatrix();
this.getNormalMatrix();
其中,轨道和眼睛是vec3,轨道和眼睛矩阵是mat4,眼睛旋转和轨道旋转是四元数
我有一个用于更改动态观察方向的工具:
this.orbitYaw += yawAmount;
this.orbitPitch += pitchAmount;
var orbitRotation = this.orbitRotation;
var rotPitch = this.createOrbitPitchRotation();
quat.copy(orbitRotation, rotPitch);
var rotYaw = quat.create();
quat.setAxisAngle(rotYaw, this.up, this.orbitYaw);
quat.multiply(orbitRotation, rotYaw, orbitRotation);
this.update();
var rotYaw = quat.create();
quat.setAxisAngle(rotYaw, this.up, yawAmount);
quat.multiply(this.eyeRotation, rotYaw, this.eyeRotation);
quat.rotateX(this.eyeRotation, this.eyeRotation, pitchAmount);
quat.normalize(this.eyeRotation, this.eyeRotation);
this.update();
我有一个改变眼睛方向的方法:
this.orbitYaw += yawAmount;
this.orbitPitch += pitchAmount;
var orbitRotation = this.orbitRotation;
var rotPitch = this.createOrbitPitchRotation();
quat.copy(orbitRotation, rotPitch);
var rotYaw = quat.create();
quat.setAxisAngle(rotYaw, this.up, this.orbitYaw);
quat.multiply(orbitRotation, rotYaw, orbitRotation);
this.update();
var rotYaw = quat.create();
quat.setAxisAngle(rotYaw, this.up, yawAmount);
quat.multiply(this.eyeRotation, rotYaw, this.eyeRotation);
quat.rotateX(this.eyeRotation, this.eyeRotation, pitchAmount);
quat.normalize(this.eyeRotation, this.eyeRotation);
this.update();
最后,我有一个改变眼睛向前位置的方法:
function moveEye(direction, velocity) {
vec3.scale(direction, direction, velocity);
vec3.add(this.eye, this.eye, direction);
this.update();
};
function moveEyeForward(velocity) {
var dir = vec3.fromValues(0, 0, 0);
var right = this.getEyeRightVector();
vec3.cross(dir, right, this.up);
vec3.normalize(dir, dir);
this.moveEye(dir, velocity);
this.update();
};
function getEyeRightVector() {
var q = this.eyeRotation;
var qx = q[0], qy = q[1], qz = q[2], qw = q[3];
var x = 1 - 2 * (qy * qy + qz * qz);
var y = 2 * (qx * qy + qw * qz);
var z = 2 * (qx * qz - qw * qy);
return vec3.fromValues(x, y, z);
};
所以问题是,我如何确保眼球运动始终相对于模型平面相对于轨道旋转平面
…如果要独立于视图方向移动,为什么不在moveEyeForward中执行类似moveEyevec3.fromValues0、0、1、velocity的操作?它需要在模型平面内移动。只要模型平面平行于z轴,沿z方向移动将沿模型平面移动。但如果旋转模型,使模型的向上方向平行于z轴,则沿z轴移动眼睛将导致向下移动到模型,而不是沿地面。然后将方向向量与模型的世界矩阵相乘。