2015-11-08 73 views
2

随着SceneKit,我看到的节点中,向其中一个照相机连接,具有为:eulerAngles(弧度角SCNVector3)和取向(SCNQuaternion)SceneKit,突出沿摄像机朝向的一个节点

我cameraNode是在0 ,0,0,并可随时改变其方向。

我需要做的hitTestWithSegmentFromPoint ... ...尖山

fromPoint总是已知的。

但是我需要根据摄像机方向来投影位于摄像机线条中的很远的点。

我的思想还没有正确地抓住四元数,而且我没有基于eulerAngles获得任何地方。

回答

3

使用一些线性代数

func findNextPoint(p0: SCNVector3, direction: SCNVector3) -> SCNVector3{ 

    var x = Float() 
    var y = Float() 
    var z = Float() 
    let t = 100 as Float 

    x = p0.x + t * direction.x 
    y = p0.y + t * direction.y 
    z = p0.z + t * direction.z 

    let result = SCNVector3Make(x, y, z) 
    return result 

} 

这里使用P0为出发点,那么,找到你想要在一个给定方向的下一个点。 t是矢量的长度,或者你想从p0行进的距离。

要找到相机指向的方向,您必须旋转并乘以旋转矩阵。

func calculateCameraDirection(cameraNode: SCNNode) -> GLKVector3 { 

    let x = -cameraNode.rotation.x 
    let y = -cameraNode.rotation.y 
    let z = -cameraNode.rotation.z 
    let w = cameraNode.rotation.w 

    let cameraRotationMatrix = GLKMatrix3Make(cos(w) + pow(x, 2) * (1 - cos(w)), 
     x * y * (1 - cos(w)) - z * sin(w), 
     x * z * (1 - cos(w)) + y*sin(w), 

     y*x*(1-cos(w)) + z*sin(w), 
     cos(w) + pow(y, 2) * (1 - cos(w)), 
     y*z*(1-cos(w)) - x*sin(w), 

     z*x*(1 - cos(w)) - y*sin(w), 
     z*y*(1 - cos(w)) + x*sin(w), 
     cos(w) + pow(z, 2) * (1 - cos(w))) 

    let cameraDirection = GLKMatrix3MultiplyVector3(cameraRotationMatrix, GLKVector3Make(0.0, 0.0, -1.0)) 

    return cameraDirection 

} 

然后你只需要使用两个坐标来执行hitTest。在这种情况下,我使用了rayTestWithSegmentFromPoint:ToPoint,但您可以使用其他类型的测试,例如hitTestWithSegmentFromPoint:toPoint:。

func raycastTest(cameraDirection: GLKVector3) -> SCNVector3{ 

    let nextPoint = findNextPoint(cameraNode.position, direction: SCNVector3Make(cameraDirection.x, cameraDirection.y, cameraDirection.z)) 
    let hitTest = sceneView.scene!.physicsWorld.rayTestWithSegmentFromPoint(cameraNode.position, toPoint: nextPoint, options: nil) 

    if hitTest.count > 0 { 
     return (hitTest.first?.worldCoordinates)! 
    }else{ 
     return nextPoint 
    } 
} 
+0

非常非常感谢@KeyChainDude,我发现另一种方法由具有farNode作为相机的子节点,因此所有的旋转将它影响到,然后将它的坐标。但我会切换到这一个。 –