我有一个场景,其中有许多不同纹理的物体。由于某些原因,其中两个物体呈现出红色色调,即使它们的纹理没有红色。你仍然可以看到纹理中的图案,只是红色的阴影不同。(在模拟器上,这两个对象有黑白纹理,在设备上则呈现出红色阴影)。有人知道为什么会发生这种情况吗?其他物体都工作正常。
对于像 metalness
和 roughness
这样的材料属性,SceneKit 支持使用 1 通道(灰度)图像。为了节省内存,这些图像被保留为灰度纹理,而不是转换为在每个通道中具有相同数据的 RGB 纹理。
当您将此类图像用于“着色”材料属性(例如 diffuse
),SceneKit 将请求样本的红、绿和蓝分量,但绿色和蓝色始终为 0,因此该图像将呈现为红色。
不幸的是,一种解决方法是在图像编辑应用程序中重新处理纹理,使其保存为 RGB 而不是灰度。
您也可以尝试使用着色器修改器将灰度转换为 RGB:
_surface.diffuse.rgb = _surface.diffuse.rrr;
编辑
iOS 11起,使用单通道纹理时可以使用textureComponents
属性:
material.diffuse.textureComponents = .red
我遇到了用 (灰色) .png 图像作为 SCNMaterial
纹理加载的同样问题。
在模拟器上渲染正常。但在设备上,所有只有黑、白或灰色的图像都会呈现红色基色。
let texture = SCNMaterial()
texture.diffuse.contents = UIImage(named: "rgb image with only gray")
我通过从给定的UIImage
创建一个新的UIImage
来解决了这个问题:
let texture = SCNMaterial()
var newImage: UIImage?
if let textureImage = UIImage(named: "rgb image with only gray") {
UIGraphicsBeginImageContext(textureImage.size)
let width = textureImage.size.width
let height = textureImage.size.height
textureImage.draw(in: CGRect(x: 0, y: 0, width: width, height: height))
newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
}
texture.diffuse.contents = newImage
HTH
我遇到了一个与索引颜色PNG纹理相关的问题。
为了解决这个问题,我将索引颜色PNG转换为真彩色PNG。
这可能是一个NSImage的bug。当我使用CGImage加载PNG文件时,它没有引起任何问题。
let url = URL(fileURLWithPath: pngFileName, relativeTo: directoryPath)
// let reddishImage = NSImage(contentsOf: url)
let cgDataProvider = CGDataProvider(url: url as CFURL)!
let cgImage = CGImage(pngDataProviderSource: cgDataProvider, decode: nil, shouldInterpolate: false, intent: CGColorRenderingIntent.defaultIntent)!
let imageSize = CGSize(width: cgImage.width, height: cgImage.height)
let correctImage = NSImage(cgImage: cgImage, size: imageSize)