【发布时间】:2020-04-13 19:06:01
【问题描述】:
我只是想用金属渲染一个红色方块,我正在从一个如下所示的顶点结构数组创建一个顶点缓冲区:
struct Vertex {
var position: SIMD3<Float>
var color: SIMD4<Float>
}
这是我渲染正方形的地方:
var vertices: [Vertex] = [
Vertex(position: [-0.5, -0.5, 0], color: [1, 0, 0, 1]),
Vertex(position: [-0.5, 0.5, 0], color: [1, 0, 0, 1]),
Vertex(position: [0.5, -0.5, 0], color: [1, 0, 0, 1]),
Vertex(position: [0.5, 0.5, 0], color: [1, 0, 0, 1])
]
var vertexBuffer: MTLBuffer?
func render(using renderCommandEncoder: MTLRenderCommandEncoder) {
if self.vertexBuffer == nil {
self.vertexBuffer = self.device.makeBuffer(
bytes: self.vertices,
length: MemoryLayout<Vertex>.stride * self.vertices.count,
options: []
)
}
if let vertexBuffer = self.vertexBuffer {
renderCommandEncoder.setRenderPipelineState(RenderPipelineStates.defaultState)
renderCommandEncoder.setVertexBuffer(vertexBuffer, offset: 0, index: 0)
renderCommandEncoder.drawPrimitives(type: .triangleStrip, vertexStart: 0, vertexCount: vertexBuffer.length / MemoryLayout<Vertex>.stride)
}
}
这是我的渲染管道状态:
let library = device.makeDefaultLibrary()!
let vertexShader = library.makeFunction(name: "basicVertexShader")
let fragmentShader = library.makeFunction(name: "basicFragmentShader")
let renderPipelineDescriptor = MTLRenderPipelineDescriptor()
renderPipelineDescriptor.colorAttachments[0].pixelFormat = .bgra8Unorm
renderPipelineDescriptor.vertexFunction = vertexShader
renderPipelineDescriptor.fragmentFunction = fragmentShader
renderPipelineDescriptor.sampleCount = 4
let vertexDescriptor = MTLVertexDescriptor()
vertexDescriptor.attributes[0].format = .float3
vertexDescriptor.attributes[0].bufferIndex = 0 // Position
vertexDescriptor.attributes[0].offset = 0
vertexDescriptor.attributes[1].format = .float4
vertexDescriptor.attributes[1].bufferIndex = 0 // Color
vertexDescriptor.attributes[1].offset = MemoryLayout<SIMD3<Float>>.stride
vertexDescriptor.layouts[0].stride = MemoryLayout<Vertex>.stride
renderPipelineDescriptor.vertexDescriptor = vertexDescriptor
self.defaultState = try! device.makeRenderPipelineState(descriptor: renderPipelineDescriptor)
顶点和片段着色器只是通过位置和颜色。出于某种原因,当它被渲染时,第一个顶点颜色的第一个浮点数作为一个非常小的值进入顶点着色器,有效地显示黑色。它只发生在数组中第一个顶点的红色值。
一个黑色顶点的红色正方形
我可以通过调试 GPU 帧看到第一个顶点的红色分量为 5E-41(本质上为 0)。
我不知道为什么会这样,当顶点被添加到顶点缓冲区时会发生这种情况。我猜它与我的渲染管道顶点描述符有关,但我无法弄清楚出了什么问题。感谢您的帮助!
【问题讨论】:
-
这很可能是this question 的副本。我鼓励您考虑那里的解决方法,并提交您自己的反馈以提高此错误的可见性。