I'm building a Unity plugin that supports different game-controller styles using a phone's orientation. I want to extract three angles describing how the phone is rotated, but I'm confused by deviceorientation: in portrait mode, rotating around what seems like one physical axis changes both gamma and alpha. Is there a reliable way to interpret these readings across different screen orientations? I'd also like to convert the result to quaternions for processing and then, if needed, convert it back into three angles without losing information.
4 Answers
The reported alpha, beta, and gamma values are Euler angles, not independent readings for three fixed world axes. They’re applied in a particular order, so rotating the device around one physical axis can change multiple values. This is expected behavior, and Euler angles can also run into gimbal lock.
A quaternion can be converted back to Euler angles, so you don’t permanently lose information by using one internally. However, the resulting three angles aren’t unique and may jump or become ambiguous near gimbal-lock positions. If the angles are only for display, conversion is fine; for gameplay and controller movement, keep the quaternion or use a rotation matrix internally.
That makes sense. I can use the quaternion for the actual controller logic and only convert to three angles when I need to show or export them.
If browser support allows it, the Generic Sensor API’s AbsoluteOrientationSensor is a cleaner option because it provides a quaternion directly. Otherwise, deviceorientation can still work, but you’ll need to apply the screen-orientation correction and carefully map the browser’s right-handed coordinate system to Unity’s left-handed one.
Convert the orientation to a quaternion as early as possible and perform the rotation math with quaternions instead of manipulating alpha, beta, and gamma directly. Also account for screen.orientation.angle or the equivalent screen rotation value, because deviceorientation is relative to the device and screen coordinate system. When sending the result to Unity, remember that browser coordinates and Unity use different axis conventions, so you’ll need an axis conversion.

So the values aren’t directly tied to fixed axes in the world? That explains why the readings change together when I rotate the phone.