简体   繁体   中英

Combine more than 3 rotations (Quaternions)

I have a 3D point and the x,y,z rotations ( qInitial ) for that point. I want to rotate that point more (by some degrees that could be 0 up to 360) around y axis ( qYextra ). How can I calculate the final Euler rotation ( qResult.eulerAngles ) that is a combination of these 4 rotations (xyzy) ?

I have tried calculating the initial quaternion rotation, and the extra rotation to be applied. And then multiply these two quaternions. However, I get weird results (probably gimbal lock) .

Code in C#. Unity.

1. Quaternion qX = Quaternion.AngleAxis(rotationFromBvh.x,Vector3.right);

2. Quaternion qY = Quaternion.AngleAxis(rotationFromBvh.y,Vector3.up);

3. Quaternion qZ = Quaternion.AngleAxis(rotationFromBvh.z,Vector3.forward);

4. Quaternion qYextra = Quaternion.AngleAxis(angle,Vector3.up);

Quaternion qInitial = qY * qX * qZ; // Yes. This is the correct order.

qY*qX*qZ has exactly the same Euler x,y,z results as Quaternion.Euler(rotationFromBvh)

Quaternion qResult = qInitial * qYextra;

return qResult.eulerAngles;

I can confirm that the code works fine (no gimbal lock) when 4th rotation is 0 degrees ( qYextra = identity ). Meaning that qInitial is correct. So, the error might be due to the combination of those 2 rotations ( qInitial and qYextra ) OR due to the convertion from Quaternion to Euler .

EXAMPLE: ( qYextra angle is 120 degrees)

RESULTS:

qInitial.eulerAngles gives these results: applying_qInitial_rotation

qResult.eulerAngles gives these results: applying_qResult_rotation

EXPECTED RESULTS:

The expected results should be like qInitial but rotated 120 degrees around y.

Any suggestions? I haven't yet found a solution, and probably I won't.

In your question, you write:

How can I calculate the final Euler rotation that is a combination of these 4 rotations (xyzy)?

However, in your code, you write

Quaternion qInitial = qY * qX * qZ; // Multiply them in the correct order.

I don't know unity, but I would have expected that you would want the order of the rotations to match x, y, z, rather than y, x, z.

You stated that it works when the y-rotation is 0, in which case the place of the y-rotation in the order becomes irrelevant.

Do you get the correct result if you instead write the code below?

Quaternion qInitial = qX * qY * qZ; // Multiply them in the correct order.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM