.X3D
格式有一个有趣的旋转系统。与包含X
,Y
和Z
轴周围的旋转值的大多数格式不同,.X3D
给出一个标准化的方向向量,然后给出一个弧度值,以围绕该轴旋转。
示例:
The axis to rotate around: 0.000000 0.465391 0.885105
Rotation around that axis (in radians): 3.141593
我有从弧度到度数的转换,但我需要这些值的XYZ
周围的旋转值。
答案 0 :(得分:0)
我们可以构建基本矩阵变换的序列,以围绕角度轴旋转。设轴单位向量为w
,角度为Theta
。辅助值:
V = Sqrt(wx*wx + wz*wz)
W = Sqrt(wx*wx + wy*wy + wz*wz) //1 for unit dir vector
Cos(Alpha) = wz/V
Sin(Alpha) = wx/V
Cos(Beta) = V/W
Sin(Beta) = wy/W
Transformation sequence:
Ry(-Alpha) //rotation matrix about Y-axis by angle -Alpha
Rx(Beta)
Rz(Theta)
Rx(-Beta)
Ry(Alpha)
注意,对于is是与Y平行的,应该使用关于Y的常用旋转矩阵(考虑方向符号),因为V值为零。
存在相当复杂的Rodrigues' rotation formula用于计算旋转矩阵,该旋转矩阵对应于围绕由单位矢量w指定的固定轴的角度θ的旋转。
显式矩阵here(奇怪的格式化图片):
答案 1 :(得分:0)
下面的 C++ 函数围绕提供的中心旋转一个点,并使用另一个向量(单位)作为轴来旋转。 下面的代码感谢 Glenn Murray 提供了 Link 中提供的公式。这是经过测试的,并且按预期完美运行。 注意:当角度为正且单位向量为{0,0,1}时,它向右旋转,基本上旋转在右侧,轴为{x-forward,y-right,z-up}
void RotateVectorAroundPointAndAxis(Vector3D YourPoint, Vector3D PreferedCenter, Vector3D UnitDirection, float Angle, Vector3D& ReturnVector)
{
float SinVal = sin(Angle * 0.01745329251);
float CosVal = cos(Angle * 0.01745329251);
float OneMinSin = 1.0f - SinVal;
float OneMinCos = 1.0f - CosVal;
UnitDirection = GetUnitVector(UnitDirection, { 0,0,0 });// This Function Gets unit Vector From InputVector - DesiredCenter
float Temp = (UnitDirection.x * YourPoint.x) + (UnitDirection.y * YourPoint.y) + (UnitDirection.z * YourPoint.z);
ReturnVector.x = (PreferedCenter.x * (UnitDirection.y * UnitDirection.y)) - (UnitDirection.x * (((-PreferedCenter.y * UnitDirection.y) + (-PreferedCenter.z * UnitDirection.z)) - Temp));
ReturnVector.y = (PreferedCenter.y * (UnitDirection.x * UnitDirection.x)) - (UnitDirection.y * (((-PreferedCenter.x * UnitDirection.x) + (-PreferedCenter.z * UnitDirection.z)) - Temp));
ReturnVector.z = (PreferedCenter.z * (UnitDirection.x * UnitDirection.x)) - (UnitDirection.z * (((-PreferedCenter.x * UnitDirection.x) + (-PreferedCenter.y * UnitDirection.y)) - Temp));
ReturnVector.x = (ReturnVector.x * OneMinCos) + (YourPoint.x * CosVal);
ReturnVector.y = (ReturnVector.y * OneMinCos) + (YourPoint.y * CosVal);
ReturnVector.z = (ReturnVector.z * OneMinCos) + (YourPoint.z * CosVal);
ReturnVector.x += (-(PreferedCenter.z * UnitDirection.y) + (PreferedCenter.y * UnitDirection.z) - (UnitDirection.z * YourPoint.y) + (UnitDirection.y * YourPoint.z)) * SinVal;
ReturnVector.y += ( (PreferedCenter.z * UnitDirection.x) - (PreferedCenter.x * UnitDirection.z) + (UnitDirection.z * YourPoint.x) - (UnitDirection.x * YourPoint.z)) * SinVal;
ReturnVector.z += (-(PreferedCenter.y * UnitDirection.x) + (PreferedCenter.x * UnitDirection.y) - (UnitDirection.y * YourPoint.x) + (UnitDirection.x * YourPoint.y)) * SinVal;
}