Ich habe gerade versucht, ein Array von Vertex-Positionen an den Vertex-Shader zu senden.
Das ist mein JS-Codeausschnitt:
const vertices = new Float32Array([0, 0.5, 0, 1, -0.5, -0.5, 0, 2, 0.5, -0.5, 0, 1]); const vertexBuffer = device.createBuffer({ // equal to 48 size: vertices.byteLength, usage: GPUBufferUsage.VERTEX | GPUBufferUsage.COPY_DST, }); device.queue.writeBuffer(vertexBuffer, 0, vertices); const vertexBuffers = [ { attributes: [ { shaderLocation: 0, offset: 0, format: "float32x4", }, ], arrayStride: 16, stepMode: "vertex", }, ];
Float32Array hat eine Länge von 12, also 48 Bytes. Ich erhalte jedoch die Fehlermeldung, dass ich 192 Bytes benötige:
Vertex-Bereich (erster: 0, Anzahl: 12) erfordert einen größeren Puffer (192) als die gebundene Puffergröße (48) des Vertex-Puffers an Steckplatz 0, mit einem Schritt von 16. - Codierung [RenderPassEncoder].Draw(12, 1, 0, 0).
Das ist vielleicht nicht relevant für die Frage, aber für den Kontext ist dies mein Shader-Programm:
@vertex fn vMain(@location(0) vertexPosition: vec4<f32>, @builtin(vertex_index) vertexIndex: u32) -> @builtin(position) vec4<f32> { var positions = array<vec4<f32>, 3>( vec4<f32>(0, 0.5, 0, 1), vec4<f32>(-0.5, -0.5, 0, 2), vec4<f32>(0.5, -0.5, 0, 1), ); return positions[vertexIndex]; } @fragment fn fMain() -> @location(0) vec4<f32> { return vec4<f32>(1, 1, 1, 1); }
Es wird kein Vertex-Array verwendet, sondern ich verwende es nur, um anzuzeigen, ob alles fehlerfrei läuft. Wenn ich die Puffergröße in Zeile 3 des Snippets von vertices.byteLength
更改为 368
ändere, funktioniert es einwandfrei und rendert ein Dreieck. Jeder Wert unter 368 führt zu einem Fehler.
Nach weiteren Tests stellte ich fest, dass eine Verdoppelung der Größe des Float32Array durch Hinzufügen von 4 Floats pro Scheitelpunkt und Ändern des Schritts auf 32 dazu führen würde, dass WebGPU angibt, dass ich 768 Bytes benötige.
您将
arrayStride
设置为 32,这意味着每个顶点将占用 32 个字节(https://developer.mozilla.org/en-US/docs/Web/API/WebGPU_API#define_and_create_the_render_pipeline)。从你的顶点布局来看,这应该是 16,因为你只定义了一种格式
float32x4
= 16 字节。从错误消息 (
Draw(12, 1, 0, 0)
) 来看,您似乎正在尝试绘制 12 个顶点。这意味着预期的总缓冲区大小为:12*32 = 368。根据您的格式,这可能应该是Draw(3, 1, 0, 0)
。这样你的 vertexBuffer 就可以被分割成 3 个顶点,每个顶点的位置值为vec4<f32>