SceneKit:如何将节点的移动限制在本地的一个轴上,而不是整个世界

问题描述

使用 SCNTransformConstraint.positionConstraint 在世界空间中防止节点在一个轴(X、Y 或 Z)上的移动被其他力移动非常容易,如下所示:

let zPosition = node.position.z

let strafingConstraint = SCNTransformConstraint.positionConstraint(inWorldspace: true,with: {(_ node: SCNNode,_ position: SCNVector3) -> SCNVector3 in
         localPosition = position
         localPosition.z = zPosition
         return localPosition
})

node.constraints = [strafingConstraint];

然而,这在世界空间中限制了它。如果我只想让节点不再在其局部 Z 轴上移动,而不管其方向如何,那么它只能在其局部 X 和 Y 轴上移动,我该怎么办?有没有办法使用 .convertPosition(:from:) 或 .convertPosition(:to:) 函数来做到这一点?有没有更好的办法?

解决方法

这可能是在不使用 SNCConstraint 的情况下将节点固定到特定轴的另一种方法。

使用 updateAtTime 委托函数在每一帧内调整节点的 z 位置:

func renderer(_ renderer: SCNSceneRenderer,updateAtTime time: TimeInterval) {
    node.position.z = 0.0 // or wherever you want to have it
}

(如果你的节点有一个物理实体,你应该只在实体类型 = .kinematc 时改变它的位置)