如何获取相机的世界Y平面并取反?实现按Q/E后修改cameraDir.y的需求
问题解决方案
1. 获取相机世界Y平面并取反
相机的世界空间Y轴向量,可通过将本地Y轴((0,1,0))应用相机的四元数转换得到;取反操作直接对该向量分量乘以-1即可:
// 获取相机世界Y轴向量 const cameraWorldY = new THREE.Vector3(0, 1, 0).applyQuaternion(this._params.camera.quaternion); // 取反得到反向Y轴向量 const invertedCameraWorldY = cameraWorldY.multiplyScalar(-1);
如果是要让相机绕自身Y轴完成180度翻转(即“取反Y平面”),直接用相机原四元数乘以绕Y轴π弧度的旋转四元数即可,这也是你代码中已用到的逻辑:
_A.set(0, 1, 0); _Q.setFromAxisAngle(_A, Math.PI); _R.multiply(_Q); // _R为相机原四元数,相乘后得到翻转后的四元数
2. 实现Q/E按键后的cameraDir Y值设置需求
根据需求,按下Q或E键后,需让cameraDir保持在相机的Y=0平面(即相机局部空间的X-Z平面),替代原代码中世界空间下的cameraDir.y = 0逻辑。修改后的完整代码如下:
if (input._keys.a) { _R.copy(this._params.camera.quaternion); if (input._keys.q) { _A.set(0, 0, 1); _Q.setFromAxisAngle(_A, 0.5 * Math.PI * timeInSeconds); _R.multiply(_Q); this._params.camera.quaternion.copy(_R); } if (input._keys.e) { _A.set(0, 0, -1); _Q.setFromAxisAngle(_A, 0.5 * Math.PI * timeInSeconds); _R.multiply(_Q); this._params.camera.quaternion.copy(_R); } // 将cameraDir约束到相机的Y=0平面 const localCameraDir = cameraDir.clone().applyQuaternion(this._params.camera.quaternion.invert()); localCameraDir.y = 0; // 相机局部空间Y分量置0 localCameraDir.normalize(); cameraDir.copy(localCameraDir).applyQuaternion(this._params.camera.quaternion); _A.set(0, 1, 0); // over Y _Q.setFromAxisAngle(_A, Math.PI); _R.multiply(_Q); controlObject.quaternion.copy(_R); } if (!input._keys.a) { cameraDir.y = 0; cameraDir.normalize(); controlObject.quaternion.setFromUnitVectors(from, cameraDir); }
核心逻辑说明
- 把世界空间的
cameraDir转换到相机局部空间(通过相机四元数的逆运算) - 在局部空间将Y分量设为0,确保方向处于相机的X-Z平面(即相机的Y=0平面)
- 将处理后的向量转换回世界空间,重新赋值给
cameraDir
内容的提问来源于stack exchange,提问作者cubesareneat
相关产品推荐
相关产品推荐

