LoginSignup
3
2

More than 5 years have passed since last update.

任意の回転から振り(Swing)と捻り(Twist)を取り出す

Last updated at Posted at 2019-04-06

元々は任意の回転から特定の軸に沿った捻りだけを取り出したかったのですがコレといった文献が見つからず、色々寄せ集めて作ったコードです。

DecomposeSwingTwist.cs
//------------------------------------------------------------
/// <summary>
/// QuaternionからTwistとSwingを取り出す
/// </summary>
/// <param name="q">与える回転(Local)</param>
/// <param name="twistAxis">捻りを取り出すための基準軸(Local)</param>
/// <param name="swing">分解したSwing回転(Local)</param>
/// <param name="twist">分解したTwist回転(Local)</param>
/// <seealso cref="http://www.euclideanspace.com/maths/geometry/rotations/for/decomposition/" />
/// <seealso cref="http://allenchou.net/2018/05/game-math-swing-twist-interpolation-sterp/" />
//------------------------------------------------------------
public static void DecomposeSwingTwist(Quaternion q, Vector3 
twistAxis, out Quaternion swing, out Quaternion twist) {
    // (rotation axis) * cos(angle / 2)
    Vector3 r = new Vector3(q.x, q.y, q.z);

    // singularity: rotation by 180 degree
    if (r.sqrMagnitude < Mathf.Epsilon) {
        Vector3 rotatedTwistAxis = q * twistAxis;
        Vector3 swingAxis = Vector3.Cross(twistAxis, rotatedTwistAxis);

        if (swingAxis.sqrMagnitude > Mathf.Epsilon) {
            float swingAngle = Vector3.Angle(twistAxis, 
rotatedTwistAxis);
            swing = Quaternion.AngleAxis(swingAngle, swingAxis);
        } else {
            // more singularity: rotation axis parallel to twist axis
            swing = Quaternion.identity;    // no swing
        }

        // always twist 180 degree on singularity
        twist = Quaternion.AngleAxis(180.0f, twistAxis);
    } else {
        // formula & proof:
        // http://www.euclideanspace.com/maths/geometry/rotations/for/decomposition/
        Vector3 p = Vector3.Project(r, twistAxis);
        twist = new Quaternion(p.x, p.y, p.z, q.w);
        twist = Quaternion.Normalize(twist);
        swing = q * Quaternion.Inverse(twist);
    }
}
3
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
2