英文:
How to make a transparent object that casts a shadow in SceneKit?
问题
我需要在SceneKit中创建一个透明的物体,可以投射阴影。我尝试了所有的纹理设置,但没有得到积极的结果。如果完全隐藏物体的纹理,阴影就会消失。
我需要获得阴影而不显示物体,但我不明白如何做到这一点。
英文:
I need to make a transparent object in SceneKit that casts a shadow. I tried going through all the texture settings, but I didn't get a positive result. If you completely hide the textures of the object, the shadow disappears.
I need to get a shadow without displaying an object and I don't understand how to do it.
答案1
得分: 0
阴影捕捉器
要创建一个在SceneKit中投射阴影的不可见对象,请使用.shadowOnly
光照模型。
import SceneKit
import Cocoa
class ViewController: NSViewController {
override func viewDidLoad() {
super.viewDidLoad()
let sceneView = self.view as! SCNView
sceneView.scene = SCNScene()
sceneView.backgroundColor = .darkGray
sceneView.allowsCameraControl = true
let lightNode = SCNNode()
lightNode.light = SCNLight()
lightNode.light?.type = .directional
lightNode.light?.castsShadow = true
lightNode.eulerAngles.x = -.pi/4
sceneView.scene?.rootNode.addChildNode(lightNode)
let sphere = SCNNode(geometry: SCNSphere(radius: 2))
sphere.geometry?.firstMaterial?.lightingModel = .shadowOnly // 1
sphere.geometry?.firstMaterial?.colorBufferWriteMask = [] // 2
sphere.geometry?.firstMaterial?.transparencyMode = .rgbZero // 3
sceneView.scene?.rootNode.addChildNode(sphere)
let plane = SCNNode(geometry: SCNPlane(width: 10, height: 10))
plane.position.y = -2
plane.eulerAngles.x = -.pi/2
sceneView.scene?.rootNode.addChildNode(plane)
}
}
如果您只需要阴影捕捉器(即透明平面),请将以下行添加到您的代码中:
plane.geometry?.firstMaterial?.lightingModel = .shadowOnly
要控制阴影的透明度,请使用以下属性:
lightNode.light?.shadowColor = NSColor(white: 0, alpha: 0.5)
英文:
Shadow catcher
To make an invisible object that casts a shadow in SceneKit, use .shadowOnly
lighting model.
import SceneKit
import Cocoa
class ViewController: NSViewController {
override func viewDidLoad() {
super.viewDidLoad()
let sceneView = self.view as! SCNView
sceneView.scene = SCNScene()
sceneView.backgroundColor = .darkGray
sceneView.allowsCameraControl = true
let lightNode = SCNNode()
lightNode.light = SCNLight()
lightNode.light?.type = .directional
lightNode.light?.castsShadow = true
lightNode.eulerAngles.x = -.pi/4
sceneView.scene?.rootNode.addChildNode(lightNode)
let sphere = SCNNode(geometry: SCNSphere(radius: 2))
sphere.geometry?.firstMaterial?.lightingModel = .shadowOnly // 1
sphere.geometry?.firstMaterial?.colorBufferWriteMask = [] // 2
sphere.geometry?.firstMaterial?.transparencyMode = .rgbZero // 3
sceneView.scene?.rootNode.addChildNode(sphere)
let plane = SCNNode(geometry: SCNPlane(width: 10, height: 10))
plane.position.y = -2
plane.eulerAngles.x = -.pi/2
sceneView.scene?.rootNode.addChildNode(plane)
}
}
If you need just a shadow catcher (i.e. transparent plane) add the following line to your code:
plane.geometry?.firstMaterial?.lightingModel = .shadowOnly
To control shadow's transparency use this property:
lightNode.light?.shadowColor = NSColor(white: 0, alpha: 0.5)
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论