Stop sharing node geometry with its clone

When you create a copy of an object, the geometry and its properties (materials ...) are shared by this object.
In the Xcode script editor, you can easily disable this by setting Geometry Sharing(to Attributes Inspector) to Unshare.

I want to do the same programmatically, but cannot find any similar properties in the documentation SceneKit.
I found a similar entry where someone suggested copying an object, its geometry and its material. I tried to do this, but did not succeed.

This is an important part of my code:

let randomColors: [UIColor] = [UIColor.blue,  UIColor.red,  UIColor.yellow,  UIColor.gray]
let obstacleScene = SCNScene(named: "art.scnassets/Scenes/obstacleNormal.scn")
let obstacle = obstacleScene?.rootNode.childNode(withName: "obstacle", recursively: true)

for i in 1...15 {
    let randomPosition = SCNVector3(x: Float(i) * 3.5, y: 0.15, z: sign * Float(arc4random_uniform(UInt32(Int(playgroundZ/2 - 2.0))) + 1))
    let randomColor = randomColors[Int(arc4random_uniform(UInt32(3)))]

    let obstacleCopy = obstacle?.clone()
    obstacleCopy?.position = randomPosition
    obstacleCopy?.geometry?.materials.first?.diffuse.contents = randomColor
    obstacleCopy?.eulerAngles = SCNVector3(x: 10.0 * Float(i), y: Float(30 - i), z: 5.0 * Float(i) * sign) //malo na random

    obstacleCopy?.physicsBody = SCNPhysicsBody(type: .dynamic, shape: nil)
    obstacleCopy?.physicsBody?.isAffectedByGravity = false
    obstacleCopy?.physicsBody?.categoryBitMask = PhysicsCategory.obstacle
    obstacleCopy?.physicsBody?.collisionBitMask = PhysicsCategory.none
    obstacleCopy?.physicsBody?.contactTestBitMask = PhysicsCategory.car1 | PhysicsCategory.car2 | PhysicsCategory.barrier

    obstacleArray.append(obstacleCopy!)
    raceScene!.rootNode.addChildNode(obstacleCopy!)
}

, , .
, .

, , , , ?

+4
2

clone() API , node.

let newNode = node.clone()
newNode.geometry = node.geometry?.copy() as? SCNGeometry

, , , , - . , .

if let newMaterial = newNode.geometry?.materials.first.copy() as? SCNMaterial {
    //make changes to material
    newNode.geometry?.materials = [newMaterial]
}
+8

SCNNode, .

fileprivate func deepCopyNode(node: SCNNode) -> SCNNode {
    let clone = node.clone()
    clone.geometry = node.geometry?.copy() as? SCNGeometry
    if let g = node.geometry {
        clone.geometry?.materials = g.materials.map{ $0.copy() as! SCNMaterial }
    }
    return clone
}
0

Source: https://habr.com/ru/post/1656972/


All Articles