RickyTheCoder RickyTheCoder - 4 months ago 21
iOS Question

How to rotate an SCNBox

I'm trying to rotate an

SCNBox
I created using
swipe gestures
. For example, when I swipe right the box should rotate 90degs in the
Y-axis
and -90degs when I swipe left. To achieve this I have been using the node's
SCNAction.rotateByX
method to perform the rotation animation. Now the problem I'm having is when rotating along either the
X-axis
or
Z-axis
after a rotation in the
Y-axis
and vice-versa is that the positions of the axes change.

What I have notice is that any rotation perform on either of the X,Y,Z axes changes the direction in which the other axes point.

Example: Default position

enter image description here

Then after a rotation in the
Z-axis
:

enter image description here

Of course this pose a problem because now when I
swipe left or right
I no longer get the desire effect because the
X-axis
and
Y-axis
have now swapped positions. What I would like to know is why does this happen? and is there anyway to perform the rotation animation without it affecting the other axes?

I apologize for my lack of understanding on this subject as this is my first go at 3d graphics.

Answer

I had the same issue, here's what I use to give the desired behavior:

func panGesture(sender: UIPanGestureRecognizer) {
    let translation = sender.translationInView(sender.view!)

    let pan_x = Float(translation.x)
    let pan_y = Float(-translation.y)
    let anglePan = sqrt(pow(pan_x,2)+pow(pan_y,2))*(Float)(M_PI)/180.0
    var rotVector = SCNVector4()

    rotVector.x = -pan_y
    rotVector.y = pan_x
    rotVector.z = 0
    rotVector.w = anglePan

    // apply to your model container node
    boxNode.rotation = rotVector

    if(sender.state == UIGestureRecognizerState.Ended) {
        let currentPivot = boxNode.pivot
        let changePivot = SCNMatrix4Invert(boxNode.transform)
        boxNode.pivot = SCNMatrix4Mult(changePivot, currentPivot)
        boxNode.transform = SCNMatrix4Identity
    }
}