SceneKit:是否可以在透明对象上投射阴影?
SceneKit: Is it possible to cast an shadow on an Transparent Object?
我正试图在 OSX 上的 SceneKit 中的一个完全透明的平面上投射阴影。几个小时以来我一直在努力解决这个问题,但没有找到任何解决方案。
我的目的是生成几个对象的屏幕截图,这些对象具有透明背景和不可见平面上的阴影。
你对我如何用苹果 SceneKit 做这个有什么建议吗?
我是否必须编写自己的着色器,我可以使用着色器修改器来实现它,还是可以使用内置功能?
我没有你的问题的答案,但我有一个解决方法:
- 渲染场景并将图像保存在内存中
- 将对象中的所有 material 更改为纯黑色,无镜面反射
- 将飞机和天空更改为全白material,将灯光更改为白色
- 将场景渲染到另一个图像
- 在第二张图片上,应用
CIColorInvert
和 CIMaskToAlpha
Core Image 滤镜
- 使用 Core Image 将 Alpha Mask 应用于第一个渲染。
您将获得具有正确 Alpha 通道和透明阴影的图像。您需要调整 material 和灯光以获得您想要的结果。
阴影的边缘可能会变亮,唯一的解决方法是将其渲染为另一幅图像,并在 Mask to Alpha 步骤后用黑色填充它。
更新:
我为任何需要的人找到了替代解决方案:
- 在3D模型下创建一个白色平面,注意平面颜色必须是纯白色
- 将飞机 material 的混合模式设置为
SCNBlendModeMultiply
。
- 将飞机 material 的灯光模型设置为
SCNLightingModelLambert
。
这是可行的,因为任何颜色乘以白色 (1, ,1, 1) return 本身并且兰伯特光模型不会考虑定向光,所以平面将始终是背景色,看起来像透明的。这个解决方案的另一个好处是你不需要改变光的阴影渲染模式。
对于曾经检查过 Xcode 的人。
首先,在您的模型下添加一个平面。然后阻止它写入 colorBuffer。
其次,将光照模型的阴影渲染模式更改为延迟。请注意,您必须使用可以投射阴影的光。
Oily Guo,你的解决方案有效。这里的解决方案在代码中:
光源配置:
light.shadowColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0.4)
light.shadowMode = .deferred
对于地板(即对象下方的 SCNFloor):
material.diffuse.contents = UIColor.white
material.colorBufferWriteMask = SCNColorMask(rawValue: 0)
我正试图在 OSX 上的 SceneKit 中的一个完全透明的平面上投射阴影。几个小时以来我一直在努力解决这个问题,但没有找到任何解决方案。
我的目的是生成几个对象的屏幕截图,这些对象具有透明背景和不可见平面上的阴影。
你对我如何用苹果 SceneKit 做这个有什么建议吗?
我是否必须编写自己的着色器,我可以使用着色器修改器来实现它,还是可以使用内置功能?
我没有你的问题的答案,但我有一个解决方法:
- 渲染场景并将图像保存在内存中
- 将对象中的所有 material 更改为纯黑色,无镜面反射
- 将飞机和天空更改为全白material,将灯光更改为白色
- 将场景渲染到另一个图像
- 在第二张图片上,应用
CIColorInvert
和CIMaskToAlpha
Core Image 滤镜 - 使用 Core Image 将 Alpha Mask 应用于第一个渲染。
您将获得具有正确 Alpha 通道和透明阴影的图像。您需要调整 material 和灯光以获得您想要的结果。
阴影的边缘可能会变亮,唯一的解决方法是将其渲染为另一幅图像,并在 Mask to Alpha 步骤后用黑色填充它。
更新:
我为任何需要的人找到了替代解决方案:
- 在3D模型下创建一个白色平面,注意平面颜色必须是纯白色
- 将飞机 material 的混合模式设置为
SCNBlendModeMultiply
。 - 将飞机 material 的灯光模型设置为
SCNLightingModelLambert
。
这是可行的,因为任何颜色乘以白色 (1, ,1, 1) return 本身并且兰伯特光模型不会考虑定向光,所以平面将始终是背景色,看起来像透明的。这个解决方案的另一个好处是你不需要改变光的阴影渲染模式。
对于曾经检查过 Xcode 的人。
首先,在您的模型下添加一个平面。然后阻止它写入 colorBuffer。
其次,将光照模型的阴影渲染模式更改为延迟。请注意,您必须使用可以投射阴影的光。
Oily Guo,你的解决方案有效。这里的解决方案在代码中:
光源配置:
light.shadowColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0.4)
light.shadowMode = .deferred
对于地板(即对象下方的 SCNFloor):
material.diffuse.contents = UIColor.white
material.colorBufferWriteMask = SCNColorMask(rawValue: 0)