Search code examples
objective-cmacosscenekitlight

SceneKit avoid lighting on specific node


In SceneKit I'm building a node made of lines to draw the XYZ axes at the center of the scene, like in Cinema4D.

cinema4D

I would like these 3 nodes not to participate to the global lighting and be viewable even if the light is dark / inexistent / too strong. In the picture below you can see that the Z axis appears too heavily lighten and can't be seen.

my software

Is there a way to stop a node participating to the scene's lighting, like with category masks for physics?

In this case, how would the node be lighten in order for it to appear anyway?


Solution

  • SCNLight has a categoryBitMask property. This lets you choose which nodes are affected by the light (Although this is ignored for ambient lights). You could have 2 light source categories, one for your main scene, and another that only affects your lines.

    Here is a simple example with 2 nodes, each lit with a different colour light:

    struct LightType {
        static let light1:Int = 0x1 << 1
        static let light2:Int = 0x1 << 2
    }
    
    class GameViewController: UIViewController {
    
        override func viewDidLoad() {
            super.viewDidLoad()
    
            let scene = SCNScene(named: "art.scnassets/scene.scn")!
    
            let lightNode1 = SCNNode()
            lightNode1.light = SCNLight()
            lightNode1.light!.type = .omni
            lightNode1.light!.color = UIColor.yellow
            lightNode1.position = SCNVector3(x: 0, y: 10, z: 10)
            lightNode1.light!.categoryBitMask = LightType.light1
            scene.rootNode.addChildNode(lightNode1)
    
            let lightNode2 = SCNNode()
            lightNode2.light = SCNLight()
            lightNode2.light!.type = .omni
            lightNode2.light!.color = UIColor.red
            lightNode2.position = SCNVector3(x: 0, y: 10, z: 10)
            lightNode2.light!.categoryBitMask = LightType.light2
            scene.rootNode.addChildNode(lightNode2)
    
            let sphere1 = scene.rootNode.childNode(withName: "sphere1", recursively: true)!
            sphere1.categoryBitMask = LightType.light1
            let sphere2 = scene.rootNode.childNode(withName: "sphere2", recursively: true)!
            sphere2.categoryBitMask = LightType.light2
    
            let scnView = self.view as! SCNView
            scnView.scene = scene
        }
    }
    

    enter image description here