如何在Unity中获得2个四元数的相对旋转
How to get the relative rotation of 2 quaternions in Unity
我正在尝试分别使用两个 IMU 获取上臂和下臂之间的角度。我校准了两个 imu 并使用四元数来获取 Unity 3D 中上臂和下臂对象的全局方向。
Qimu1 = 来自位于下臂的 imu 的四元数
Qimu2 = 来自位于上臂的 imu 的四元数。
我在 Unity 中制作了两个对象,分别代表上臂和下臂。其中,下臂是上臂的子对象,并使用角色关节连接到上臂。
这是上臂的脚本:
if (Input.GetKeyDown(KeyCode.Space))
{
Qstart2 = Qimu2;
}
transform.localRotation = Qstart2 * Quaternion.Inverse(Qimu2);
下臂脚本:
if (Input.GetKeyDown(KeyCode.Space))
{
Qstart1 = Qimu1;
}
Qimu1new = Qstart1 * Quaternion.Inverse(Qimu1);
Quaternion Qdiff = Quaternion.Inverse(Qimu1new) * Qimu2;
transform.localRotation = Qdiff;
我想要获得的是使用 2 个 IMU 的 Unity3D 中手臂运动的视觉表示。现在,如果我保持肘部伸展,脚本就可以工作。但是一旦我开始弯曲我的肘部,小臂物体就会开始围绕同一轴连续旋转。
我们可以使用一些代数来计算下臂变换的相对旋转:
公式 Qstartx * Quaternion.Inverse(Qimux)
给出该部分相对于 body 的旋转:
upper arm's rotation relative to body = Qstart2 * Quaternion.Inverse(Qimu2)
lower arm's rotation relative to body = Qstart1 * Quaternion.Inverse(Qimu1)
我们知道,由于下臂是上臂的child:
lower arm's rotation relative to body
= upper arm's rotation relative to body * lowerArmTransform.relativeRotation
通过替换,我们可以确定:
Qstart1 * Quaternion.Inverse(Qimu1)
= (Qstart2 * Quaternion.Inverse(Qimu2)) * lowerArmTransform.relativeRotation
左边两边乘以Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2))
:
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * Qstart1
* Quaternion.Inverse(Qimu1)
= Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2))
* ( Qstart2 * Quaternion.Inverse(Qimu2) )
* lowerArmTransform.relativeRotation
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * ( Qstart2 * Quaternion.Inverse(Qimu2) )
取消:
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * Qstart1
* Quaternion.Inverse(Qimu1)
= lowerArmTransform.relativeRotation
由于Qimu1new = Qstart1 * Quaternion.Inverse(Qimu1);
,我们可以得出结论:
lowerArmTransform.relativeRotation = Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * Qimu1new;
我正在尝试分别使用两个 IMU 获取上臂和下臂之间的角度。我校准了两个 imu 并使用四元数来获取 Unity 3D 中上臂和下臂对象的全局方向。
Qimu1 = 来自位于下臂的 imu 的四元数
Qimu2 = 来自位于上臂的 imu 的四元数。
我在 Unity 中制作了两个对象,分别代表上臂和下臂。其中,下臂是上臂的子对象,并使用角色关节连接到上臂。
这是上臂的脚本:
if (Input.GetKeyDown(KeyCode.Space))
{
Qstart2 = Qimu2;
}
transform.localRotation = Qstart2 * Quaternion.Inverse(Qimu2);
下臂脚本:
if (Input.GetKeyDown(KeyCode.Space))
{
Qstart1 = Qimu1;
}
Qimu1new = Qstart1 * Quaternion.Inverse(Qimu1);
Quaternion Qdiff = Quaternion.Inverse(Qimu1new) * Qimu2;
transform.localRotation = Qdiff;
我想要获得的是使用 2 个 IMU 的 Unity3D 中手臂运动的视觉表示。现在,如果我保持肘部伸展,脚本就可以工作。但是一旦我开始弯曲我的肘部,小臂物体就会开始围绕同一轴连续旋转。
我们可以使用一些代数来计算下臂变换的相对旋转:
公式 Qstartx * Quaternion.Inverse(Qimux)
给出该部分相对于 body 的旋转:
upper arm's rotation relative to body = Qstart2 * Quaternion.Inverse(Qimu2)
lower arm's rotation relative to body = Qstart1 * Quaternion.Inverse(Qimu1)
我们知道,由于下臂是上臂的child:
lower arm's rotation relative to body
= upper arm's rotation relative to body * lowerArmTransform.relativeRotation
通过替换,我们可以确定:
Qstart1 * Quaternion.Inverse(Qimu1)
= (Qstart2 * Quaternion.Inverse(Qimu2)) * lowerArmTransform.relativeRotation
左边两边乘以Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2))
:
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * Qstart1
* Quaternion.Inverse(Qimu1)
= Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2))
* ( Qstart2 * Quaternion.Inverse(Qimu2) )
* lowerArmTransform.relativeRotation
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * ( Qstart2 * Quaternion.Inverse(Qimu2) )
取消:
Quaternion.Inverse(Qstart2 * Quaternion.Inverse(Qimu2)) * Qstart1
* Quaternion.Inverse(Qimu1)
= lowerArmTransform.relativeRotation
由于Qimu1new = Qstart1 * Quaternion.Inverse(Qimu1);
,我们可以得出结论: