swift 无法旋转ARKit中的SCNNode

ddrv8njm  于 2022-12-10  发布在  Swift
关注(0)|答案(2)|浏览(193)

我试图在y轴上旋转SCNNode,使我的节点(箭头)指向正确的方向。每个箭头都需要指向我收到的路线的下一个位置。2路线的检索工作正常。
节点被添加到场景的rootNode中。在某个时刻,我遍历一个节点阵列,将它们定位在场景中,并对节点应用缩放(基于距离),这一切都是正确的。但是,当我应用旋转时,这没有任何效果。旋转是通过修改节点的rotation属性来完成的:

directionNode.rotation = SCNVector4(x:0, y:1:, z:0, w:Float(bearing))

这并没有达到预期的效果.我也尝试过使用runAction方法,同样没有效果:

directionNode.runAction(SCNAction.rotateBy(x: 0, y: CGFloat(bearing), z: 0, duration: 0))

下面是定位和缩放节点的代码。

for i in 0...(directionNodes.count - 1) {

    let directionNode = directionNodes[i]
    let translation = MatrixHelper.transformMatrix(for: matrix_identity_float4x4, 
                                        originLocation: startingLocation, 
                                              location: directionNode.location)
    let position = SCNVector3.positionFromTransform(translation)
    let distance = directionNode.location.distance(from: startingLocation)

    DispatchQueue.main.async {
        let scale = 100 / Float(distance)
        directionNode.scale = SCNVector3(x: scale, y: scale, z: scale)
        directionNode.anchor = ARAnchor(transform: translation)
        directionNode.position = position

        if (i < (self.directionNodes.count - 1)) {
            // Apply rotation to the arrow
            let successiveStepLocation = self.directionNodes[i + 1].location!
            let bearing = directionNode.location.bearingToLocationRadian(successiveStepLocation)
            // rotate
            directionNode.rotation = SCNVector4(x:0, y:1:, z:0, w:Float(bearing))
        }
    }
}

这都 Package 在SCNTransaction中。
有谁能告诉我为什么节点的旋转不起作用吗?任何帮助都非常感谢。

[编辑]:我忘了提到我尝试旋转的3D箭头对象总是指向同一个方向。即使当我“绕着它走”时,箭头总是指向(在我的情况下)左边。也许这有助于解决我的问题...

jckbn6z7

jckbn6z71#

**更新:我认为问题出在您使用的singleSided着色器上。您看到的是模型不可见的一面。只需为您的几何体启用doubleSided**材质:

directionNode.geometry?.firstMaterial?.isDoubleSided = true

需要使用以弧度表示的值(有效范围为-6.28+6.28)。
物体旋转的方向是很重要的〉〉CWCCW。当旋转Angular 为+.pi时,你看不到single-sided几何体(***在某个Angular ***)。
其工作方式如下:

myNode.rotation = SCNVector4(x: 0, y: -1, z: 0, w: (.pi * 3) / 2)

...当您也使用SCNAction时(不要忘记指定持续时间):

let action = SCNAction.repeatForever(SCNAction.rotate(by: -.pi, 
                                                  around: SCNVector3(0,1,0), 
                                                duration: 1.75))
myNode.runAction(action)

...当您也使用SCNTransaction时:

let previousTransform = myNode.transform
let rotate = SCNMatrix4MakeRotation(0, 1, 0, (-Float.pi/2))

SCNTransaction.begin()
SCNTransaction.animationDuration = 3.75
myNode.transform = SCNMatrix4Mult(rotate, previousTransform)
SCNTransaction.commit()

vu8f3i0k

vu8f3i0k2#

非常感谢你的回答,帮助我了解了很多不同的旋转方式。
然而,事实证明,节点上有一个约束,如下所示:

let billboardConstraint = SCNBillboardConstraint()
billboardConstraint.freeAxes = SCNBillboardAxis.Y
constraints = [billboardConstraint]

注解这段代码使旋转工作正常。相当愚蠢...
根据文档,SCNBillboardConstraint使对象的z轴总是指向pointOfView节点。但是我不太理解这里的freeAxes属性。默认类型是all,所以它不会相对于视点旋转。所以如果我只设置Y约束类型,我只能在X和Z轴上应用旋转?或者我错了?

相关问题