How to avoid roll in SceneKit camera controlled by Core Motion?

自作多情 提交于 2019-12-21 12:54:08

问题


I'm setting my SceneKit camera to the current CMDeviceMotion attitude using the CMDeviceMotion extension described in this answer:

func deviceDidMove(motion: CMDeviceMotion?, error: NSError?) {
    if let motion = motion {
        let orientation = motion.gaze(atOrientation: UIApplication.sharedApplication().statusBarOrientation)
        cameraNode.orientation = orientation
    }
}

This works beautifully, however, I'd like to block the rotation (roll) and only allow the camera to turn around (yaw) and pitch.

I tried to convert the quaternion back to Euler angles and simply leave roll at 0:

cameraNode.eulerAngles = SCNVector3(
            x: orientation.pitch(),
            y: orientation.yaw(),
            z: 0)

However, this works for only one half of the yaw movement. For the other half, the camera is turned upside down. I suspect this is a Gimbal Lock issue involving Euler angles.

Quaternions are a bit like black magic for me, but is there a way to remove the roll component directly on the quaternion level so I can avoid Euler angles?

来源:https://stackoverflow.com/questions/39026329/how-to-avoid-roll-in-scenekit-camera-controlled-by-core-motion

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!