我需要在iOS上生成256x1纹理。我有4种颜色,一端是红色,另一端是蓝色,另一端是蓝色,红色,绿色,黄色,蓝色,黄色和绿色分别在3/4和1/4位置。两者之间的颜色需要线性插值。我需要在Metal中使用此纹理在着色器代码中查找。在代码中生成此纹理的最简单方法是什么?
答案 0 :(得分:1)
由于MTKTextureLoader
当前不支持一维纹理的创建(至少自2016年以来就是一项功能要求),因此您需要手动创建纹理。
假设您已经加载了图像,则可以要求其提供CGImage
,然后使用此方法提取像素数据并将其加载到纹理中:
func texture1DForImage(_ cgImage: CGImage, device: MTLDevice) -> MTLTexture? {
let width = cgImage.width
let height = 0
let bytesPerRow = width * 4 // RGBA, 8 bits per component
let bitmapInfo: UInt32 = /* default byte order | */ CGImageAlphaInfo.premultipliedLast.rawValue
let colorSpace = CGColorSpace(name: CGColorSpace.sRGB)!
let context = CGContext(data: nil,
width: width,
height: height,
bitsPerComponent: 8,
bytesPerRow: bytesPerRow,
space: colorSpace,
bitmapInfo: bitmapInfo)!
let bounds = CGRect(x: 0, y: 0, width: width, height: height)
context.draw(cgImage, in: bounds)
guard let data = context.data?.bindMemory(to: UInt8.self, capacity: bytesPerRow) else { return nil }
let textureDescriptor = MTLTextureDescriptor.texture2DDescriptor(pixelFormat: .rgba8Unorm,
width: width,
height: height,
mipmapped: false)
textureDescriptor.textureType = .type1D
textureDescriptor.usage = [ .shaderRead ]
let texture = device.makeTexture(descriptor: textureDescriptor)!
texture.replace(region: MTLRegionMake1D(0, width), mipmapLevel: 0, withBytes: data, bytesPerRow: bytesPerRow)
return texture
}