How to invert just z axis of incoming quaternion
Hi everyone,
I'm super new to using VR/AR/Unity and have been seriously struggling to figure how to solve this issue. I'm currently using the Vive trackers and a base station and have been plugging the tracker coordinates (as seen by the base station) into unity on a camera object. Unfortunately, the rotational data isn't lining up. When I rotate the tracker on the z axis, everything works well, but when I rotate it either on the x or y axis, the camera angle changes in the opposite direction.
After playing around with things, I figured out that unity and the vive base station share a Y and X axis, but the z axis is inverted (i.e. right-handed vs left-handed coordinate systems: https://www.evl.uic.edu/ralph/508S98/coordinates.html). Knowing this, position is no problem (I can just negate the z values), but I can't figure out rotation.
So far I've thought about:
1 - converting R-handed quaternions from the trackers into a L-handed quaternions in unity – but apparently there are no such thing as left and right handed quaternions. I did read that it can matter which coordinate system you derive your quaternions from, though. So I wasn't really sure what to make of it and a lot of the math was over my head.
2 - converting my 3x3 basis matrix from the trackers into a left-handed system. I've tried negating the Z base vector, which didn't work. I tried switching the Z and Y base vector columns, which also didn't work.
3 - converting to euler angles from my R-handed quaternion, negating the x and y axis rotations, and converting back to quaternion, but when I tried to use euler angles I couldn't even get good results simply converting from quaternion to euler and back (without changing anything). Everything was erratic and unstable (code attempt for that:)
Tracker tr = DataCapture.instance.tracker1;
Vector3 trEulers = tr.rotQuat.eulerAngles;
transform.rotation = Quaternion.Euler(trEulers.y, trEulers.z, trEulers.x); //from documentation: The x, y, and z angles represent a rotation z degrees around the z axis, x degrees around the x axis, and y degrees around the y axis (in that order).
Does anyone have any good suggestions on getting from my R-handed tracking rotational info to the L-handed system in unity? Thanks!
Answer by HMSMakerspace · Aug 08, 2017 at 01:02 AM
Figured it out! If anyone runs into this problem, the solution was to take the basis matrix and negate the following values:
[ x1 x2 -x3 ]
[ y1 y2 -y3 ]
[-z1 -z2 z3 ]
I honestly don't understand why it works (would love an explanation if someone has one), but I found it in the steamVR libraries when they pull in their tracker data. Looks like it would flip the the first two base vectors over the x-y plane, and then the third one and flip it over both the x-z and y-z planes. Somehow it totally fixes the handedness of the data.
Apparently I didn't actually have to change the coordinate system from R-handed to L-handed at all. Applying the above negative signs to the basis matrix simply results in the inverse of all the rotations applied to the tracker.
Your answer
![](https://koobas.hobune.stream/wayback/20220612132159im_/https://answers.unity.com/themes/thub/images/avi.jpg)
Follow this Question
Related Questions
Rotate an object to a position only through one axis 1 Answer
Add +1 each time a sphere turns 1 degree on it's axis 0 Answers
Quaternions to EulerAngles weird x-axis interaction 1 Answer
Euler Angles in code / inspector different (both local & global) 1 Answer
How to find the 'longitude' of a collision location on a sphere collider? 0 Answers