@luma.gl/webgpu 9.0.0-beta.1 → 9.0.0-beta.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/adapter/helpers/get-bind-group.js +1 -1
- package/dist/adapter/helpers/get-bind-group.js.map +1 -1
- package/dist/adapter/helpers/get-vertex-buffer-layout.js +4 -4
- package/dist/adapter/helpers/get-vertex-buffer-layout.js.map +1 -1
- package/dist/adapter/resources/webgpu-render-pipeline.d.ts.map +1 -1
- package/dist/adapter/resources/webgpu-render-pipeline.js +3 -5
- package/dist/adapter/resources/webgpu-render-pipeline.js.map +1 -1
- package/dist/adapter/resources/webgpu-shader.d.ts.map +1 -1
- package/dist/adapter/resources/webgpu-shader.js +1 -0
- package/dist/adapter/resources/webgpu-shader.js.map +1 -1
- package/dist/adapter/resources/webgpu-vertex-array.d.ts +2 -2
- package/dist/adapter/resources/webgpu-vertex-array.d.ts.map +1 -1
- package/dist/adapter/resources/webgpu-vertex-array.js +3 -3
- package/dist/adapter/resources/webgpu-vertex-array.js.map +1 -1
- package/dist/dist.dev.js +30 -15
- package/dist/index.cjs +18 -19
- package/dist.min.js +15 -15
- package/package.json +3 -3
- package/src/adapter/helpers/get-bind-group.ts +1 -1
- package/src/adapter/helpers/get-vertex-buffer-layout.ts +4 -4
- package/src/adapter/resources/webgpu-render-pipeline.ts +17 -16
- package/src/adapter/resources/webgpu-shader.ts +3 -0
- package/src/adapter/resources/webgpu-vertex-array.ts +4 -4
|
@@ -10,7 +10,7 @@ export function getBindGroup(device, bindGroupLayout, shaderLayout, bindings) {
|
|
|
10
10
|
});
|
|
11
11
|
}
|
|
12
12
|
export function getShaderLayoutBinding(shaderLayout, bindingName) {
|
|
13
|
-
const bindingLayout = shaderLayout.bindings.find(binding => binding.name === bindingName);
|
|
13
|
+
const bindingLayout = shaderLayout.bindings.find(binding => binding.name === bindingName || `${binding.name}uniforms` === bindingName.toLocaleLowerCase());
|
|
14
14
|
if (!bindingLayout) {
|
|
15
15
|
log.warn(`Binding ${bindingName} not set: Not found in shader layout.`)();
|
|
16
16
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"get-bind-group.js","names":["Buffer","Sampler","Texture","log","cast","makeBindGroupLayout","device","layout","bindings","Error","getBindGroup","bindGroupLayout","shaderLayout","entries","getBindGroupEntries","createBindGroup","getShaderLayoutBinding","bindingName","bindingLayout","find","binding","name","warn","value","Object","push","getBindGroupEntry","location","index","resource","buffer","handle","createView","label"],"sources":["../../../src/adapter/helpers/get-bind-group.ts"],"sourcesContent":["// luma.gl, MIT license\nimport type {ShaderLayout, BindingDeclaration, Binding} from '@luma.gl/core';\nimport {Buffer, Sampler, Texture, log, cast} from '@luma.gl/core';\nimport type {WebGPUBuffer} from '../resources/webgpu-buffer';\nimport type {WebGPUSampler} from '../resources/webgpu-sampler';\nimport type {WebGPUTexture} from '../resources/webgpu-texture';\n\n/**\n * Create a WebGPU \"bind group layout\" from an array of luma.gl bindings\n * @note bind groups can be automatically generated by WebGPU.\n */\nexport function makeBindGroupLayout(\n device: GPUDevice,\n layout: GPUBindGroupLayout,\n bindings: Binding[]\n): GPUBindGroupLayout {\n throw new Error('not implemented');\n // return device.createBindGroupLayout({\n // layout,\n // entries: getBindGroupEntries(bindings)\n // })\n}\n\n/**\n * Create a WebGPU \"bind group\" from an array of luma.gl bindings\n */\nexport function getBindGroup(\n device: GPUDevice,\n bindGroupLayout: GPUBindGroupLayout,\n shaderLayout: ShaderLayout,\n bindings: Record<string, Binding>\n): GPUBindGroup {\n const entries = getBindGroupEntries(bindings, shaderLayout);\n return device.createBindGroup({\n layout: bindGroupLayout,\n entries\n });\n}\n\nexport function getShaderLayoutBinding(\n shaderLayout: ShaderLayout,\n bindingName: string\n): BindingDeclaration {\n const bindingLayout = shaderLayout.bindings.find(binding => binding.name === bindingName);\n if (!bindingLayout) {\n log.warn(`Binding ${bindingName} not set: Not found in shader layout.`)();\n }\n return bindingLayout;\n}\n\n/**\n * @param bindings\n * @returns\n */\nfunction getBindGroupEntries(\n bindings: Record<string, Binding>,\n shaderLayout: ShaderLayout\n): GPUBindGroupEntry[] {\n const entries: GPUBindGroupEntry[] = [];\n\n for (const [bindingName, value] of Object.entries(bindings)) {\n const bindingLayout = getShaderLayoutBinding(shaderLayout, bindingName);\n if (bindingLayout) {\n entries.push(getBindGroupEntry(value, bindingLayout.location));\n }\n }\n\n return entries;\n}\n\nfunction getBindGroupEntry(binding: Binding, index: number): GPUBindGroupEntry {\n if (binding instanceof Buffer) {\n return {\n binding: index,\n resource: {\n buffer: cast<WebGPUBuffer>(binding).handle\n }\n };\n }\n if (binding instanceof Sampler) {\n return {\n binding: index,\n resource: cast<WebGPUSampler>(binding).handle\n };\n } else if (binding instanceof Texture) {\n return {\n binding: index,\n resource: cast<WebGPUTexture>(binding).handle.createView({label: 'bind-group-auto-created'})\n };\n }\n throw new Error('invalid binding');\n}\n"],"mappings":"AAEA,SAAQA,MAAM,EAAEC,OAAO,EAAEC,OAAO,EAAEC,GAAG,EAAEC,IAAI,QAAO,eAAe;AASjE,OAAO,SAASC,mBAAmBA,CACjCC,MAAiB,EACjBC,MAA0B,EAC1BC,QAAmB,EACC;EACpB,MAAM,IAAIC,KAAK,CAAC,iBAAiB,CAAC;AAKpC;AAKA,OAAO,SAASC,YAAYA,CAC1BJ,MAAiB,EACjBK,eAAmC,EACnCC,YAA0B,EAC1BJ,QAAiC,EACnB;EACd,MAAMK,OAAO,GAAGC,mBAAmB,CAACN,QAAQ,EAAEI,YAAY,CAAC;EAC3D,OAAON,MAAM,CAACS,eAAe,CAAC;IAC5BR,MAAM,EAAEI,eAAe;IACvBE;EACF,CAAC,CAAC;AACJ;AAEA,OAAO,SAASG,sBAAsBA,CACpCJ,YAA0B,EAC1BK,WAAmB,EACC;EACpB,MAAMC,aAAa,GAAGN,YAAY,CAACJ,QAAQ,CAACW,IAAI,CAACC,OAAO,IAAIA,OAAO,CAACC,IAAI,KAAKJ,WAAW,CAAC;
|
|
1
|
+
{"version":3,"file":"get-bind-group.js","names":["Buffer","Sampler","Texture","log","cast","makeBindGroupLayout","device","layout","bindings","Error","getBindGroup","bindGroupLayout","shaderLayout","entries","getBindGroupEntries","createBindGroup","getShaderLayoutBinding","bindingName","bindingLayout","find","binding","name","toLocaleLowerCase","warn","value","Object","push","getBindGroupEntry","location","index","resource","buffer","handle","createView","label"],"sources":["../../../src/adapter/helpers/get-bind-group.ts"],"sourcesContent":["// luma.gl, MIT license\nimport type {ShaderLayout, BindingDeclaration, Binding} from '@luma.gl/core';\nimport {Buffer, Sampler, Texture, log, cast} from '@luma.gl/core';\nimport type {WebGPUBuffer} from '../resources/webgpu-buffer';\nimport type {WebGPUSampler} from '../resources/webgpu-sampler';\nimport type {WebGPUTexture} from '../resources/webgpu-texture';\n\n/**\n * Create a WebGPU \"bind group layout\" from an array of luma.gl bindings\n * @note bind groups can be automatically generated by WebGPU.\n */\nexport function makeBindGroupLayout(\n device: GPUDevice,\n layout: GPUBindGroupLayout,\n bindings: Binding[]\n): GPUBindGroupLayout {\n throw new Error('not implemented');\n // return device.createBindGroupLayout({\n // layout,\n // entries: getBindGroupEntries(bindings)\n // })\n}\n\n/**\n * Create a WebGPU \"bind group\" from an array of luma.gl bindings\n */\nexport function getBindGroup(\n device: GPUDevice,\n bindGroupLayout: GPUBindGroupLayout,\n shaderLayout: ShaderLayout,\n bindings: Record<string, Binding>\n): GPUBindGroup {\n const entries = getBindGroupEntries(bindings, shaderLayout);\n return device.createBindGroup({\n layout: bindGroupLayout,\n entries\n });\n}\n\nexport function getShaderLayoutBinding(\n shaderLayout: ShaderLayout,\n bindingName: string\n): BindingDeclaration {\n const bindingLayout = shaderLayout.bindings.find(binding => binding.name === bindingName || `${binding.name}uniforms` === bindingName.toLocaleLowerCase());\n if (!bindingLayout) {\n log.warn(`Binding ${bindingName} not set: Not found in shader layout.`)();\n }\n return bindingLayout;\n}\n\n/**\n * @param bindings\n * @returns\n */\nfunction getBindGroupEntries(\n bindings: Record<string, Binding>,\n shaderLayout: ShaderLayout\n): GPUBindGroupEntry[] {\n const entries: GPUBindGroupEntry[] = [];\n\n for (const [bindingName, value] of Object.entries(bindings)) {\n const bindingLayout = getShaderLayoutBinding(shaderLayout, bindingName);\n if (bindingLayout) {\n entries.push(getBindGroupEntry(value, bindingLayout.location));\n }\n }\n\n return entries;\n}\n\nfunction getBindGroupEntry(binding: Binding, index: number): GPUBindGroupEntry {\n if (binding instanceof Buffer) {\n return {\n binding: index,\n resource: {\n buffer: cast<WebGPUBuffer>(binding).handle\n }\n };\n }\n if (binding instanceof Sampler) {\n return {\n binding: index,\n resource: cast<WebGPUSampler>(binding).handle\n };\n } else if (binding instanceof Texture) {\n return {\n binding: index,\n resource: cast<WebGPUTexture>(binding).handle.createView({label: 'bind-group-auto-created'})\n };\n }\n throw new Error('invalid binding');\n}\n"],"mappings":"AAEA,SAAQA,MAAM,EAAEC,OAAO,EAAEC,OAAO,EAAEC,GAAG,EAAEC,IAAI,QAAO,eAAe;AASjE,OAAO,SAASC,mBAAmBA,CACjCC,MAAiB,EACjBC,MAA0B,EAC1BC,QAAmB,EACC;EACpB,MAAM,IAAIC,KAAK,CAAC,iBAAiB,CAAC;AAKpC;AAKA,OAAO,SAASC,YAAYA,CAC1BJ,MAAiB,EACjBK,eAAmC,EACnCC,YAA0B,EAC1BJ,QAAiC,EACnB;EACd,MAAMK,OAAO,GAAGC,mBAAmB,CAACN,QAAQ,EAAEI,YAAY,CAAC;EAC3D,OAAON,MAAM,CAACS,eAAe,CAAC;IAC5BR,MAAM,EAAEI,eAAe;IACvBE;EACF,CAAC,CAAC;AACJ;AAEA,OAAO,SAASG,sBAAsBA,CACpCJ,YAA0B,EAC1BK,WAAmB,EACC;EACpB,MAAMC,aAAa,GAAGN,YAAY,CAACJ,QAAQ,CAACW,IAAI,CAACC,OAAO,IAAIA,OAAO,CAACC,IAAI,KAAKJ,WAAW,IAAK,GAAEG,OAAO,CAACC,IAAK,UAAS,KAAKJ,WAAW,CAACK,iBAAiB,CAAC,CAAC,CAAC;EAC1J,IAAI,CAACJ,aAAa,EAAE;IAClBf,GAAG,CAACoB,IAAI,CAAE,WAAUN,WAAY,uCAAsC,CAAC,CAAC,CAAC;EAC3E;EACA,OAAOC,aAAa;AACtB;AAMA,SAASJ,mBAAmBA,CAC1BN,QAAiC,EACjCI,YAA0B,EACL;EACrB,MAAMC,OAA4B,GAAG,EAAE;EAEvC,KAAK,MAAM,CAACI,WAAW,EAAEO,KAAK,CAAC,IAAIC,MAAM,CAACZ,OAAO,CAACL,QAAQ,CAAC,EAAE;IAC3D,MAAMU,aAAa,GAAGF,sBAAsB,CAACJ,YAAY,EAAEK,WAAW,CAAC;IACvE,IAAIC,aAAa,EAAE;MACjBL,OAAO,CAACa,IAAI,CAACC,iBAAiB,CAACH,KAAK,EAAEN,aAAa,CAACU,QAAQ,CAAC,CAAC;IAChE;EACF;EAEA,OAAOf,OAAO;AAChB;AAEA,SAASc,iBAAiBA,CAACP,OAAgB,EAAES,KAAa,EAAqB;EAC7E,IAAIT,OAAO,YAAYpB,MAAM,EAAE;IAC7B,OAAO;MACLoB,OAAO,EAAES,KAAK;MACdC,QAAQ,EAAE;QACRC,MAAM,EAAE3B,IAAI,CAAegB,OAAO,CAAC,CAACY;MACtC;IACF,CAAC;EACH;EACA,IAAIZ,OAAO,YAAYnB,OAAO,EAAE;IAC9B,OAAO;MACLmB,OAAO,EAAES,KAAK;MACdC,QAAQ,EAAE1B,IAAI,CAAgBgB,OAAO,CAAC,CAACY;IACzC,CAAC;EACH,CAAC,MAAM,IAAIZ,OAAO,YAAYlB,OAAO,EAAE;IACrC,OAAO;MACLkB,OAAO,EAAES,KAAK;MACdC,QAAQ,EAAE1B,IAAI,CAAgBgB,OAAO,CAAC,CAACY,MAAM,CAACC,UAAU,CAAC;QAACC,KAAK,EAAE;MAAyB,CAAC;IAC7F,CAAC;EACH;EACA,MAAM,IAAIzB,KAAK,CAAC,iBAAiB,CAAC;AACpC"}
|
|
@@ -16,7 +16,7 @@ export function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
16
16
|
for (const attributeMapping of mapping.attributes) {
|
|
17
17
|
const attributeName = attributeMapping.attribute;
|
|
18
18
|
const attributeLayout = findAttributeLayout(shaderLayout, attributeName, usedAttributes);
|
|
19
|
-
stepMode = attributeLayout.stepMode || 'vertex';
|
|
19
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith('instance') ? 'instance' : 'vertex');
|
|
20
20
|
vertexAttributes.push({
|
|
21
21
|
format: getWebGPUVertexFormat(attributeMapping.format || mapping.format),
|
|
22
22
|
offset: attributeMapping.byteOffset,
|
|
@@ -30,7 +30,7 @@ export function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
30
30
|
continue;
|
|
31
31
|
}
|
|
32
32
|
byteStride = decodeVertexFormat(mapping.format).byteLength;
|
|
33
|
-
stepMode = attributeLayout.stepMode || 'vertex';
|
|
33
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith('instance') ? 'instance' : 'vertex');
|
|
34
34
|
vertexAttributes.push({
|
|
35
35
|
format: getWebGPUVertexFormat(mapping.format),
|
|
36
36
|
offset: 0,
|
|
@@ -39,7 +39,7 @@ export function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
39
39
|
}
|
|
40
40
|
vertexBufferLayouts.push({
|
|
41
41
|
arrayStride: mapping.byteStride || byteStride,
|
|
42
|
-
stepMode
|
|
42
|
+
stepMode,
|
|
43
43
|
attributes: vertexAttributes
|
|
44
44
|
});
|
|
45
45
|
}
|
|
@@ -47,7 +47,7 @@ export function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
47
47
|
if (!usedAttributes.has(attribute.name)) {
|
|
48
48
|
vertexBufferLayouts.push({
|
|
49
49
|
arrayStride: decodeVertexFormat('float32x3').byteLength,
|
|
50
|
-
stepMode: attribute.stepMode || 'vertex',
|
|
50
|
+
stepMode: attribute.stepMode || (attribute.name.startsWith('instance') ? 'instance' : 'vertex'),
|
|
51
51
|
attributes: [{
|
|
52
52
|
format: getWebGPUVertexFormat('float32x3'),
|
|
53
53
|
offset: 0,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"get-vertex-buffer-layout.js","names":["log","decodeVertexFormat","getWebGPUVertexFormat","format","endsWith","Error","getVertexBufferLayout","shaderLayout","bufferLayout","vertexBufferLayouts","usedAttributes","Set","mapping","vertexAttributes","stepMode","byteStride","attributes","attributeMapping","attributeName","attribute","attributeLayout","findAttributeLayout","push","offset","byteOffset","shaderLocation","location","byteLength","
|
|
1
|
+
{"version":3,"file":"get-vertex-buffer-layout.js","names":["log","decodeVertexFormat","getWebGPUVertexFormat","format","endsWith","Error","getVertexBufferLayout","shaderLayout","bufferLayout","vertexBufferLayouts","usedAttributes","Set","mapping","vertexAttributes","stepMode","byteStride","attributes","attributeMapping","attributeName","attribute","attributeLayout","findAttributeLayout","name","startsWith","push","offset","byteOffset","shaderLocation","location","byteLength","arrayStride","has","getBufferSlots","bufferSlot","bufferSlots","interleaved","add","attributeNames","find","warn"],"sources":["../../../src/adapter/helpers/get-vertex-buffer-layout.ts"],"sourcesContent":["// luma.gl, MIT license\nimport type {ShaderLayout, BufferLayout, AttributeDeclaration, VertexFormat} from '@luma.gl/core';\nimport {log, decodeVertexFormat} from '@luma.gl/core';\n// import {getAttributeInfosFromLayouts} from '@luma.gl/core';\n\n/** Throw error on any WebGL-only vertex formats */\nfunction getWebGPUVertexFormat(format: VertexFormat): GPUVertexFormat {\n if (format.endsWith('-webgl')) {\n throw new Error(`WebGPU does not support vertex format ${format}`);\n }\n return format as GPUVertexFormat;\n}\n\n/**\n * Build a WebGPU vertex buffer layout intended for use in a GPURenderPassDescriptor.\n * Converts luma.gl attribute definitions to a WebGPU GPUVertexBufferLayout[] array\n * @param layout\n * @param bufferLayout The buffer map is optional\n * @returns WebGPU layout intended for a GPURenderPassDescriptor.\n */\nexport function getVertexBufferLayout(\n shaderLayout: ShaderLayout,\n bufferLayout: BufferLayout[]\n): GPUVertexBufferLayout[] {\n const vertexBufferLayouts: GPUVertexBufferLayout[] = [];\n const usedAttributes = new Set<string>();\n\n // First handle any buffers mentioned in `bufferLayout`\n for (const mapping of bufferLayout) {\n // Build vertex attributes for one buffer\n const vertexAttributes: GPUVertexAttribute[] = [];\n\n // TODO verify that all stepModes for one buffer are the same\n let stepMode: 'vertex' | 'instance' = 'vertex';\n let byteStride = 0;\n // interleaved mapping {..., attributes: [{...}, ...]}\n if (mapping.attributes) {\n // const arrayStride = mapping.byteStride; TODO\n for (const attributeMapping of mapping.attributes) {\n const attributeName = attributeMapping.attribute;\n const attributeLayout = findAttributeLayout(shaderLayout, attributeName, usedAttributes);\n\n stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith('instance') ? 'instance' : 'vertex');\n vertexAttributes.push({\n format: getWebGPUVertexFormat(attributeMapping.format || mapping.format),\n offset: attributeMapping.byteOffset,\n shaderLocation: attributeLayout.location\n });\n\n byteStride += decodeVertexFormat(mapping.format).byteLength;\n }\n // non-interleaved mapping (just set offset and stride)\n } else {\n const attributeLayout = findAttributeLayout(shaderLayout, mapping.name, usedAttributes);\n if (!attributeLayout) {\n continue; // eslint-disable-line no-continue\n }\n byteStride = decodeVertexFormat(mapping.format).byteLength;\n\n stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith('instance') ? 'instance' : 'vertex');\n vertexAttributes.push({\n format: getWebGPUVertexFormat(mapping.format),\n // We only support 0 offset for non-interleaved buffer layouts\n offset: 0,\n shaderLocation: attributeLayout.location\n });\n }\n\n // Store all the attribute bindings for one buffer\n vertexBufferLayouts.push({\n arrayStride: mapping.byteStride || byteStride,\n stepMode,\n attributes: vertexAttributes\n });\n }\n\n // Add any non-mapped attributes - TODO - avoid hardcoded types\n for (const attribute of shaderLayout.attributes) {\n if (!usedAttributes.has(attribute.name)) {\n vertexBufferLayouts.push({\n arrayStride: decodeVertexFormat('float32x3').byteLength,\n stepMode: attribute.stepMode || (attribute.name.startsWith('instance') ? 'instance' : 'vertex'),\n attributes: [\n {\n format: getWebGPUVertexFormat('float32x3'),\n offset: 0,\n shaderLocation: attribute.location\n }\n ]\n });\n }\n }\n\n return vertexBufferLayouts;\n}\n\nexport function getBufferSlots(\n shaderLayout: ShaderLayout,\n bufferLayout: BufferLayout[]\n): Record<string, number> {\n const usedAttributes = new Set<string>();\n let bufferSlot = 0;\n const bufferSlots: Record<string, number> = {};\n\n // First handle any buffers mentioned in `bufferLayout`\n for (const mapping of bufferLayout) {\n // interleaved mapping {..., attributes: [{...}, ...]}\n if ('attributes' in mapping) {\n for (const interleaved of mapping.attributes) {\n usedAttributes.add(interleaved.attribute);\n }\n // non-interleaved mapping (just set offset and stride)\n } else {\n usedAttributes.add(mapping.name);\n }\n bufferSlots[mapping.name] = bufferSlot++;\n }\n\n // Add any non-mapped attributes\n for (const attribute of shaderLayout.attributes) {\n if (!usedAttributes.has(attribute.name)) {\n bufferSlots[attribute.name] = bufferSlot++;\n }\n }\n\n return bufferSlots;\n}\n\n/**\n * Looks up an attribute in the ShaderLayout.\n * @throws if name is not in ShaderLayout\n * @throws if name has already been referenced\n */\nfunction findAttributeLayout(\n shaderLayout: ShaderLayout,\n name: string,\n attributeNames: Set<string>\n): AttributeDeclaration {\n const attribute = shaderLayout.attributes.find(attribute => attribute.name === name);\n if (!attribute) {\n log.warn(`Unknown attribute ${name}`)();\n return null;\n }\n if (attributeNames.has(name)) {\n throw new Error(`Duplicate attribute ${name}`);\n }\n attributeNames.add(name);\n return attribute;\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-render-pipeline.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-render-pipeline.ts"],"names":[],"mappings":";AAEA,OAAO,KAAK,EAAC,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,WAAW,EAAC,MAAM,eAAe,CAAC;AAClF,OAAO,EAAC,cAAc,EAAE,mBAAmB,EAA2B,MAAM,eAAe,CAAC;AAS5F,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAEnD,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,iBAAiB,CAAC;AAKlD,2DAA2D;AAC3D,qBAAa,oBAAqB,SAAQ,cAAc;IACtD,MAAM,EAAE,YAAY,CAAC;IACrB,MAAM,EAAE,iBAAiB,CAAC;IAE1B,EAAE,EAAE,YAAY,CAAC;IACjB,EAAE,EAAE,YAAY,GAAG,IAAI,CAAQ;IAO/B,4CAA4C;IAC5C,OAAO,CAAC,gBAAgB,CAAmC;IAC3D,OAAO,CAAC,UAAU,CAA6B;gBAEnC,MAAM,EAAE,YAAY,EAAE,KAAK,EAAE,mBAAmB;IAoBnD,OAAO,IAAI,IAAI;IAiCxB,WAAW,CAAC,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;
|
|
1
|
+
{"version":3,"file":"webgpu-render-pipeline.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-render-pipeline.ts"],"names":[],"mappings":";AAEA,OAAO,KAAK,EAAC,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,WAAW,EAAC,MAAM,eAAe,CAAC;AAClF,OAAO,EAAC,cAAc,EAAE,mBAAmB,EAA2B,MAAM,eAAe,CAAC;AAS5F,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAEnD,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,iBAAiB,CAAC;AAKlD,2DAA2D;AAC3D,qBAAa,oBAAqB,SAAQ,cAAc;IACtD,MAAM,EAAE,YAAY,CAAC;IACrB,MAAM,EAAE,iBAAiB,CAAC;IAE1B,EAAE,EAAE,YAAY,CAAC;IACjB,EAAE,EAAE,YAAY,GAAG,IAAI,CAAQ;IAO/B,4CAA4C;IAC5C,OAAO,CAAC,gBAAgB,CAAmC;IAC3D,OAAO,CAAC,UAAU,CAA6B;gBAEnC,MAAM,EAAE,YAAY,EAAE,KAAK,EAAE,mBAAmB;IAoBnD,OAAO,IAAI,IAAI;IAiCxB,WAAW,CAAC,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IASpD,WAAW,CAAC,QAAQ,EAAE,MAAM,CAAC,MAAM,EAAE,YAAY,CAAC,GAAG,IAAI;IAMzD,IAAI,CAAC,OAAO,EAAE;QACZ,UAAU,EAAE,UAAU,CAAC;QACvB,WAAW,EAAE,WAAW,CAAC;QACzB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,aAAa,CAAC,EAAE,MAAM,CAAC;QACvB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,aAAa,CAAC,EAAE,MAAM,CAAC;QACvB,UAAU,CAAC,EAAE,MAAM,CAAC;KACrB,GAAG,IAAI;IA2CR,iDAAiD;IACjD,aAAa;IAeb;;OAEG;IACH,SAAS,CAAC,4BAA4B;CAyFvC"}
|
|
@@ -27,11 +27,7 @@ export class WebGPURenderPipeline extends RenderPipeline {
|
|
|
27
27
|
}
|
|
28
28
|
destroy() {}
|
|
29
29
|
setBindings(bindings) {
|
|
30
|
-
|
|
31
|
-
Object.assign(this.props.bindings, bindings);
|
|
32
|
-
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
33
|
-
this._bindGroup = getBindGroup(this.device.handle, this._bindGroupLayout, this.props.shaderLayout, this.props.bindings);
|
|
34
|
-
}
|
|
30
|
+
Object.assign(this.props.bindings, bindings);
|
|
35
31
|
}
|
|
36
32
|
setUniforms(uniforms) {
|
|
37
33
|
if (!isObjectEmpty(uniforms)) {
|
|
@@ -54,6 +50,8 @@ export class WebGPURenderPipeline extends RenderPipeline {
|
|
|
54
50
|
options.vertexArray.unbindAfterRender(options.renderPass);
|
|
55
51
|
}
|
|
56
52
|
_getBindGroup() {
|
|
53
|
+
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
54
|
+
this._bindGroup = this._bindGroup || getBindGroup(this.device.handle, this._bindGroupLayout, this.props.shaderLayout, this.props.bindings);
|
|
57
55
|
return this._bindGroup;
|
|
58
56
|
}
|
|
59
57
|
_getRenderPipelineDescriptor() {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-render-pipeline.js","names":["RenderPipeline","cast","log","isObjectEmpty","applyParametersToRenderPipelineDescriptor","getWebGPUTextureFormat","getBindGroup","getVertexBufferLayout","WebGPURenderPipeline","constructor","device","props","handle","vs","fs","_bindGroupLayout","_bindGroup","descriptor","_getRenderPipelineDescriptor","groupCollapsed","id","probe","JSON","stringify","groupEnd","createRenderPipeline","label","destroy","setBindings","bindings","Object","assign","getBindGroupLayout","shaderLayout","setUniforms","uniforms","Error","draw","options","webgpuRenderPass","renderPass","getDefaultRenderPass","setPipeline","bindGroup","_getBindGroup","setBindGroup","vertexArray","bindBeforeRender","indexCount","drawIndexed","instanceCount","firstIndex","baseVertex","firstInstance","vertexCount","unbindAfterRender","vertex","module","entryPoint","vsEntryPoint","buffers","bufferLayout","fragment","_this$device","fsEntryPoint","targets","format","canvasContext","topology","primitive","layout","parameters"],"sources":["../../../src/adapter/resources/webgpu-render-pipeline.ts"],"sourcesContent":["// luma.gl MIT license\n\nimport type {Binding, UniformValue, RenderPass, VertexArray} from '@luma.gl/core';\nimport {RenderPipeline, RenderPipelineProps, cast, log, isObjectEmpty} from '@luma.gl/core';\nimport {applyParametersToRenderPipelineDescriptor} from '../helpers/webgpu-parameters';\nimport {getWebGPUTextureFormat} from '../helpers/convert-texture-format';\nimport {getBindGroup} from '../helpers/get-bind-group';\nimport {getVertexBufferLayout} from '../helpers/get-vertex-buffer-layout';\n// import {convertAttributesVertexBufferToLayout} from '../helpers/get-vertex-buffer-layout';\n// import {mapAccessorToWebGPUFormat} from './helpers/accessor-to-format';\n// import type {BufferAccessors} from './webgpu-pipeline';\n\nimport type {WebGPUDevice} from '../webgpu-device';\n// import type {WebGPUBuffer} from './webgpu-buffer';\nimport type {WebGPUShader} from './webgpu-shader';\nimport type {WebGPURenderPass} from './webgpu-render-pass';\n\n// RENDER PIPELINE\n\n/** Creates a new render pipeline when parameters change */\nexport class WebGPURenderPipeline extends RenderPipeline {\n device: WebGPUDevice;\n handle: GPURenderPipeline;\n\n vs: WebGPUShader;\n fs: WebGPUShader | null = null;\n\n // private _bufferSlots: Record<string, number>;\n // private _buffers: Buffer[];\n // private _firstIndex: number;\n // private _lastIndex: number;\n\n /** For internal use to create BindGroups */\n private _bindGroupLayout: GPUBindGroupLayout | null = null;\n private _bindGroup: GPUBindGroup | null = null;\n\n constructor(device: WebGPUDevice, props: RenderPipelineProps) {\n super(device, props);\n this.device = device;\n this.handle = this.props.handle as GPURenderPipeline;\n if (!this.handle) {\n const descriptor = this._getRenderPipelineDescriptor();\n log.groupCollapsed(1, `new WebGPURenderPipeline(${this.id})`)();\n log.probe(1, JSON.stringify(descriptor, null, 2))();\n log.groupEnd(1)();\n this.handle = this.device.handle.createRenderPipeline(descriptor); \n }\n this.handle.label = this.props.id;\n\n this.vs = cast<WebGPUShader>(props.vs);\n this.fs = cast<WebGPUShader>(props.fs);\n\n // this._bufferSlots = getBufferSlots(this.props.shaderLayout, this.props.bufferLayout);\n // this._buffers = new Array<Buffer>(Object.keys(this._bufferSlots).length).fill(null);\n }\n\n override destroy(): void {\n // WebGPURenderPipeline has no destroy method.\n }\n\n // setIndexBuffer(indexBuffer: Buffer): void {\n // this._indexBuffer = cast<WebGPUBuffer>(indexBuffer);\n // }\n\n /*\n setAttributes(attributes: Record<string, Buffer>): void {\n for (const [name, buffer] of Object.entries(attributes)) {\n const bufferIndex = this._bufferSlots[name];\n if (bufferIndex >= 0) {\n this._buffers[bufferIndex] = buffer;\n } else {\n throw new Error(\n `Setting attribute '${name}' not listed in shader layout for program ${this.id}`\n );\n }\n }\n // for (let i = 0; i < this._bufferSlots.length; ++i) {\n // const bufferName = this._bufferSlots[i];\n // if (attributes[bufferName]) {\n // this.handle\n // }\n // }\n }\n */\n\n // setConstantAttributes(attributes: Record<string, TypedArray>): void {\n // throw new Error('not implemented');\n // }\n\n setBindings(bindings: Record<string, Binding>): void {\n if (!isObjectEmpty(this.props.bindings)) {\n // Do we want to save things on CPU side?\n Object.assign(this.props.bindings, bindings);\n\n // Get hold of the bind group layout. We don't want to do this unless we know there is at least one bind group\n this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);\n\n // Set up the bindings\n this._bindGroup = getBindGroup(\n this.device.handle,\n this._bindGroupLayout,\n this.props.shaderLayout,\n this.props.bindings\n );\n }\n }\n\n setUniforms(uniforms: Record<string, UniformValue>): void {\n if (!isObjectEmpty(uniforms)) {\n throw new Error('WebGPU does not support uniforms');\n }\n }\n\n draw(options: {\n renderPass: RenderPass;\n vertexArray: VertexArray;\n vertexCount?: number;\n indexCount?: number;\n instanceCount?: number;\n firstVertex?: number;\n firstIndex?: number;\n firstInstance?: number;\n baseVertex?: number;\n }): void {\n const webgpuRenderPass: WebGPURenderPass =\n cast<WebGPURenderPass>(options.renderPass) || this.device.getDefaultRenderPass();\n\n // Set pipeline\n webgpuRenderPass.handle.setPipeline(this.handle);\n\n // Set bindings (uniform buffers, textures etc)\n const bindGroup = this._getBindGroup();\n if (bindGroup) {\n webgpuRenderPass.handle.setBindGroup(0, bindGroup);\n }\n\n\n // Set attributes\n // Note: Rebinds constant attributes before each draw call\n options.vertexArray.bindBeforeRender(options.renderPass);\n\n // Draw\n if (options.indexCount) {\n webgpuRenderPass.handle.drawIndexed(\n options.indexCount,\n options.instanceCount,\n options.firstIndex,\n options.baseVertex,\n options.firstInstance\n );\n } else {\n webgpuRenderPass.handle.draw(\n options.vertexCount || 0,\n options.instanceCount || 1, // If 0, nothing will be drawn\n options.firstInstance\n );\n }\n\n // Note: Rebinds constant attributes before each draw call\n options.vertexArray.unbindAfterRender(options.renderPass);\n }\n\n // _getBuffers() {\n // return this._buffers;\n // }\n\n /** Return a bind group created by setBindings */\n _getBindGroup() {\n // assert(this._bindGroup);\n return this._bindGroup;\n }\n\n /** \n * Populate the complex WebGPU GPURenderPipelineDescriptor \n */\n protected _getRenderPipelineDescriptor() {\n // Set up the vertex stage\n const vertex: GPUVertexState = {\n module: cast<WebGPUShader>(this.props.vs).handle,\n entryPoint: this.props.vsEntryPoint || 'main',\n buffers: getVertexBufferLayout(this.props.shaderLayout, this.props.bufferLayout)\n };\n\n // Set up the fragment stage\n let fragment: GPUFragmentState | undefined;\n if (this.props.fs) {\n fragment = {\n module: cast<WebGPUShader>(this.props.fs).handle,\n entryPoint: this.props.fsEntryPoint || 'main',\n targets: [\n {\n // TODO exclamation mark hack!\n format: getWebGPUTextureFormat(this.device?.canvasContext?.format)\n }\n ]\n };\n }\n\n // WebGPU has more restrictive topology support than WebGL\n switch (this.props.topology) {\n case 'triangle-fan-webgl':\n case 'line-loop-webgl':\n throw new Error(`WebGPU does not support primitive topology ${this.props.topology}`);\n default:\n }\n\n // Create a partially populated descriptor\n const descriptor: GPURenderPipelineDescriptor = {\n vertex,\n fragment,\n primitive: {\n topology: this.props.topology\n },\n layout: 'auto'\n };\n\n // Set parameters on the descriptor\n applyParametersToRenderPipelineDescriptor(descriptor, this.props.parameters);\n\n return descriptor;\n }\n\n /**\n _setAttributeBuffers(webgpuRenderPass: WebGPURenderPass) {\n if (this._indexBuffer) {\n webgpuRenderPass.handle.setIndexBuffer(this._indexBuffer.handle, this._indexBuffer.props.indexType);\n }\n\n const buffers = this._getBuffers();\n for (let i = 0; i < buffers.length; ++i) {\n const buffer = cast<WebGPUBuffer>(buffers[i]);\n if (!buffer) {\n const attribute = this.props.shaderLayout.attributes.find(\n (attribute) => attribute.location === i\n );\n throw new Error(\n `No buffer provided for attribute '${attribute?.name || ''}' in Model '${this.props.id}'`\n );\n }\n webgpuRenderPass.handle.setVertexBuffer(i, buffer.handle);\n }\n\n // TODO - HANDLE buffer maps\n /*\n for (const [bufferName, attributeMapping] of Object.entries(this.props.bufferLayout)) {\n const buffer = cast<WebGPUBuffer>(this.props.attributes[bufferName]);\n if (!buffer) {\n log.warn(`Missing buffer for buffer map ${bufferName}`)();\n continue;\n }\n\n if ('location' in attributeMapping) {\n // @ts-expect-error TODO model must not depend on webgpu\n renderPass.handle.setVertexBuffer(layout.location, buffer.handle);\n } else {\n for (const [bufferName, mapping] of Object.entries(attributeMapping)) {\n // @ts-expect-error TODO model must not depend on webgpu\n renderPass.handle.setVertexBuffer(field.location, buffer.handle);\n }\n }\n }\n *\n }\n */\n}\n"],"mappings":"AAGA,SAAQA,cAAc,EAAuBC,IAAI,EAAEC,GAAG,EAAEC,aAAa,QAAO,eAAe;AAAC,SACpFC,yCAAyC;AAAA,SACzCC,sBAAsB;AAAA,SACtBC,YAAY;AAAA,SACZC,qBAAqB;AAa7B,OAAO,MAAMC,oBAAoB,SAASR,cAAc,CAAC;EAgBvDS,WAAWA,CAACC,MAAoB,EAAEC,KAA0B,EAAE;IAC5D,KAAK,CAACD,MAAM,EAAEC,KAAK,CAAC;IAAC,KAhBvBD,MAAM;IAAA,KACNE,MAAM;IAAA,KAENC,EAAE;IAAA,KACFC,EAAE,GAAwB,IAAI;IAAA,KAQtBC,gBAAgB,GAA8B,IAAI;IAAA,KAClDC,UAAU,GAAwB,IAAI;IAI5C,IAAI,CAACN,MAAM,GAAGA,MAAM;IACpB,IAAI,CAACE,MAAM,GAAG,IAAI,CAACD,KAAK,CAACC,MAA2B;IACpD,IAAI,CAAC,IAAI,CAACA,MAAM,EAAE;MAChB,MAAMK,UAAU,GAAG,IAAI,CAACC,4BAA4B,CAAC,CAAC;MACtDhB,GAAG,CAACiB,cAAc,CAAC,CAAC,EAAG,4BAA2B,IAAI,CAACC,EAAG,GAAE,CAAC,CAAC,CAAC;MAC/DlB,GAAG,CAACmB,KAAK,CAAC,CAAC,EAAEC,IAAI,CAACC,SAAS,CAACN,UAAU,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;MACnDf,GAAG,CAACsB,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC;MACjB,IAAI,CAACZ,MAAM,GAAG,IAAI,CAACF,MAAM,CAACE,MAAM,CAACa,oBAAoB,CAACR,UAAU,CAAC;IACnE;IACA,IAAI,CAACL,MAAM,CAACc,KAAK,GAAG,IAAI,CAACf,KAAK,CAACS,EAAE;IAEjC,IAAI,CAACP,EAAE,GAAGZ,IAAI,CAAeU,KAAK,CAACE,EAAE,CAAC;IACtC,IAAI,CAACC,EAAE,GAAGb,IAAI,CAAeU,KAAK,CAACG,EAAE,CAAC;EAIxC;EAESa,OAAOA,CAAA,EAAS,CAEzB;EA+BAC,WAAWA,CAACC,QAAiC,EAAQ;IACnD,IAAI,CAAC1B,aAAa,CAAC,IAAI,CAACQ,KAAK,CAACkB,QAAQ,CAAC,EAAE;MAEvCC,MAAM,CAACC,MAAM,CAAC,IAAI,CAACpB,KAAK,CAACkB,QAAQ,EAAEA,QAAQ,CAAC;MAG5C,IAAI,CAACd,gBAAgB,GAAG,IAAI,CAACA,gBAAgB,IAAI,IAAI,CAACH,MAAM,CAACoB,kBAAkB,CAAC,CAAC,CAAC;MAGlF,IAAI,CAAChB,UAAU,GAAGV,YAAY,CAC5B,IAAI,CAACI,MAAM,CAACE,MAAM,EAClB,IAAI,CAACG,gBAAgB,EACrB,IAAI,CAACJ,KAAK,CAACsB,YAAY,EACvB,IAAI,CAACtB,KAAK,CAACkB,QACb,CAAC;IACH;EACF;EAEAK,WAAWA,CAACC,QAAsC,EAAQ;IACxD,IAAI,CAAChC,aAAa,CAACgC,QAAQ,CAAC,EAAE;MAC5B,MAAM,IAAIC,KAAK,CAAC,kCAAkC,CAAC;IACrD;EACF;EAEAC,IAAIA,CAACC,OAUJ,EAAQ;IACP,MAAMC,gBAAkC,GACtCtC,IAAI,CAAmBqC,OAAO,CAACE,UAAU,CAAC,IAAI,IAAI,CAAC9B,MAAM,CAAC+B,oBAAoB,CAAC,CAAC;IAGlFF,gBAAgB,CAAC3B,MAAM,CAAC8B,WAAW,CAAC,IAAI,CAAC9B,MAAM,CAAC;IAGhD,MAAM+B,SAAS,GAAG,IAAI,CAACC,aAAa,CAAC,CAAC;IACtC,IAAID,SAAS,EAAE;MACbJ,gBAAgB,CAAC3B,MAAM,CAACiC,YAAY,CAAC,CAAC,EAAEF,SAAS,CAAC;IACpD;IAKAL,OAAO,CAACQ,WAAW,CAACC,gBAAgB,CAACT,OAAO,CAACE,UAAU,CAAC;IAGxD,IAAIF,OAAO,CAACU,UAAU,EAAE;MACtBT,gBAAgB,CAAC3B,MAAM,CAACqC,WAAW,CACjCX,OAAO,CAACU,UAAU,EAClBV,OAAO,CAACY,aAAa,EACrBZ,OAAO,CAACa,UAAU,EAClBb,OAAO,CAACc,UAAU,EAClBd,OAAO,CAACe,aACV,CAAC;IACH,CAAC,MAAM;MACLd,gBAAgB,CAAC3B,MAAM,CAACyB,IAAI,CAC1BC,OAAO,CAACgB,WAAW,IAAI,CAAC,EACxBhB,OAAO,CAACY,aAAa,IAAI,CAAC,EAC1BZ,OAAO,CAACe,aACV,CAAC;IACH;IAGAf,OAAO,CAACQ,WAAW,CAACS,iBAAiB,CAACjB,OAAO,CAACE,UAAU,CAAC;EAC3D;EAOAI,aAAaA,CAAA,EAAG;IAEd,OAAO,IAAI,CAAC5B,UAAU;EACxB;EAKUE,4BAA4BA,CAAA,EAAG;IAEvC,MAAMsC,MAAsB,GAAG;MAC7BC,MAAM,EAAExD,IAAI,CAAe,IAAI,CAACU,KAAK,CAACE,EAAE,CAAC,CAACD,MAAM;MAChD8C,UAAU,EAAE,IAAI,CAAC/C,KAAK,CAACgD,YAAY,IAAI,MAAM;MAC7CC,OAAO,EAAErD,qBAAqB,CAAC,IAAI,CAACI,KAAK,CAACsB,YAAY,EAAE,IAAI,CAACtB,KAAK,CAACkD,YAAY;IACjF,CAAC;IAGD,IAAIC,QAAsC;IAC1C,IAAI,IAAI,CAACnD,KAAK,CAACG,EAAE,EAAE;MAAA,IAAAiD,YAAA;MACjBD,QAAQ,GAAG;QACTL,MAAM,EAAExD,IAAI,CAAe,IAAI,CAACU,KAAK,CAACG,EAAE,CAAC,CAACF,MAAM;QAChD8C,UAAU,EAAE,IAAI,CAAC/C,KAAK,CAACqD,YAAY,IAAI,MAAM;QAC7CC,OAAO,EAAE,CACP;UAEEC,MAAM,EAAE7D,sBAAsB,EAAA0D,YAAA,GAAC,IAAI,CAACrD,MAAM,cAAAqD,YAAA,gBAAAA,YAAA,GAAXA,YAAA,CAAaI,aAAa,cAAAJ,YAAA,uBAA1BA,YAAA,CAA4BG,MAAM;QACnE,CAAC;MAEL,CAAC;IACH;IAGA,QAAQ,IAAI,CAACvD,KAAK,CAACyD,QAAQ;MACzB,KAAK,oBAAoB;MACzB,KAAK,iBAAiB;QACpB,MAAM,IAAIhC,KAAK,CAAE,8CAA6C,IAAI,CAACzB,KAAK,CAACyD,QAAS,EAAC,CAAC;MACtF;IACF;IAGA,MAAMnD,UAAuC,GAAG;MAC9CuC,MAAM;MACNM,QAAQ;MACRO,SAAS,EAAE;QACTD,QAAQ,EAAE,IAAI,CAACzD,KAAK,CAACyD;MACvB,CAAC;MACDE,MAAM,EAAE;IACV,CAAC;IAGDlE,yCAAyC,CAACa,UAAU,EAAE,IAAI,CAACN,KAAK,CAAC4D,UAAU,CAAC;IAE5E,OAAOtD,UAAU;EACnB;AA4CF"}
|
|
1
|
+
{"version":3,"file":"webgpu-render-pipeline.js","names":["RenderPipeline","cast","log","isObjectEmpty","applyParametersToRenderPipelineDescriptor","getWebGPUTextureFormat","getBindGroup","getVertexBufferLayout","WebGPURenderPipeline","constructor","device","props","handle","vs","fs","_bindGroupLayout","_bindGroup","descriptor","_getRenderPipelineDescriptor","groupCollapsed","id","probe","JSON","stringify","groupEnd","createRenderPipeline","label","destroy","setBindings","bindings","Object","assign","setUniforms","uniforms","Error","draw","options","webgpuRenderPass","renderPass","getDefaultRenderPass","setPipeline","bindGroup","_getBindGroup","setBindGroup","vertexArray","bindBeforeRender","indexCount","drawIndexed","instanceCount","firstIndex","baseVertex","firstInstance","vertexCount","unbindAfterRender","getBindGroupLayout","shaderLayout","vertex","module","entryPoint","vsEntryPoint","buffers","bufferLayout","fragment","_this$device","fsEntryPoint","targets","format","canvasContext","topology","primitive","layout","parameters"],"sources":["../../../src/adapter/resources/webgpu-render-pipeline.ts"],"sourcesContent":["// luma.gl MIT license\n\nimport type {Binding, UniformValue, RenderPass, VertexArray} from '@luma.gl/core';\nimport {RenderPipeline, RenderPipelineProps, cast, log, isObjectEmpty} from '@luma.gl/core';\nimport {applyParametersToRenderPipelineDescriptor} from '../helpers/webgpu-parameters';\nimport {getWebGPUTextureFormat} from '../helpers/convert-texture-format';\nimport {getBindGroup} from '../helpers/get-bind-group';\nimport {getVertexBufferLayout} from '../helpers/get-vertex-buffer-layout';\n// import {convertAttributesVertexBufferToLayout} from '../helpers/get-vertex-buffer-layout';\n// import {mapAccessorToWebGPUFormat} from './helpers/accessor-to-format';\n// import type {BufferAccessors} from './webgpu-pipeline';\n\nimport type {WebGPUDevice} from '../webgpu-device';\n// import type {WebGPUBuffer} from './webgpu-buffer';\nimport type {WebGPUShader} from './webgpu-shader';\nimport type {WebGPURenderPass} from './webgpu-render-pass';\n\n// RENDER PIPELINE\n\n/** Creates a new render pipeline when parameters change */\nexport class WebGPURenderPipeline extends RenderPipeline {\n device: WebGPUDevice;\n handle: GPURenderPipeline;\n\n vs: WebGPUShader;\n fs: WebGPUShader | null = null;\n\n // private _bufferSlots: Record<string, number>;\n // private _buffers: Buffer[];\n // private _firstIndex: number;\n // private _lastIndex: number;\n\n /** For internal use to create BindGroups */\n private _bindGroupLayout: GPUBindGroupLayout | null = null;\n private _bindGroup: GPUBindGroup | null = null;\n\n constructor(device: WebGPUDevice, props: RenderPipelineProps) {\n super(device, props);\n this.device = device;\n this.handle = this.props.handle as GPURenderPipeline;\n if (!this.handle) {\n const descriptor = this._getRenderPipelineDescriptor();\n log.groupCollapsed(1, `new WebGPURenderPipeline(${this.id})`)();\n log.probe(1, JSON.stringify(descriptor, null, 2))();\n log.groupEnd(1)();\n this.handle = this.device.handle.createRenderPipeline(descriptor); \n }\n this.handle.label = this.props.id;\n\n this.vs = cast<WebGPUShader>(props.vs);\n this.fs = cast<WebGPUShader>(props.fs);\n\n // this._bufferSlots = getBufferSlots(this.props.shaderLayout, this.props.bufferLayout);\n // this._buffers = new Array<Buffer>(Object.keys(this._bufferSlots).length).fill(null);\n }\n\n override destroy(): void {\n // WebGPURenderPipeline has no destroy method.\n }\n\n // setIndexBuffer(indexBuffer: Buffer): void {\n // this._indexBuffer = cast<WebGPUBuffer>(indexBuffer);\n // }\n\n /*\n setAttributes(attributes: Record<string, Buffer>): void {\n for (const [name, buffer] of Object.entries(attributes)) {\n const bufferIndex = this._bufferSlots[name];\n if (bufferIndex >= 0) {\n this._buffers[bufferIndex] = buffer;\n } else {\n throw new Error(\n `Setting attribute '${name}' not listed in shader layout for program ${this.id}`\n );\n }\n }\n // for (let i = 0; i < this._bufferSlots.length; ++i) {\n // const bufferName = this._bufferSlots[i];\n // if (attributes[bufferName]) {\n // this.handle\n // }\n // }\n }\n */\n\n // setConstantAttributes(attributes: Record<string, TypedArray>): void {\n // throw new Error('not implemented');\n // }\n\n setBindings(bindings: Record<string, Binding>): void {\n // if (isObjectEmpty(bindings)) {\n // return;\n // }\n\n // Do we want to save things on CPU side?\n Object.assign(this.props.bindings, bindings);\n }\n\n setUniforms(uniforms: Record<string, UniformValue>): void {\n if (!isObjectEmpty(uniforms)) {\n throw new Error('WebGPU does not support uniforms');\n }\n }\n\n draw(options: {\n renderPass: RenderPass;\n vertexArray: VertexArray;\n vertexCount?: number;\n indexCount?: number;\n instanceCount?: number;\n firstVertex?: number;\n firstIndex?: number;\n firstInstance?: number;\n baseVertex?: number;\n }): void {\n const webgpuRenderPass: WebGPURenderPass =\n cast<WebGPURenderPass>(options.renderPass) || this.device.getDefaultRenderPass();\n\n // Set pipeline\n webgpuRenderPass.handle.setPipeline(this.handle);\n\n // Set bindings (uniform buffers, textures etc)\n const bindGroup = this._getBindGroup();\n if (bindGroup) {\n webgpuRenderPass.handle.setBindGroup(0, bindGroup);\n }\n\n\n // Set attributes\n // Note: Rebinds constant attributes before each draw call\n options.vertexArray.bindBeforeRender(options.renderPass);\n\n // Draw\n if (options.indexCount) {\n webgpuRenderPass.handle.drawIndexed(\n options.indexCount,\n options.instanceCount,\n options.firstIndex,\n options.baseVertex,\n options.firstInstance\n );\n } else {\n webgpuRenderPass.handle.draw(\n options.vertexCount || 0,\n options.instanceCount || 1, // If 0, nothing will be drawn\n options.firstInstance\n );\n }\n\n // Note: Rebinds constant attributes before each draw call\n options.vertexArray.unbindAfterRender(options.renderPass);\n }\n\n // _getBuffers() {\n // return this._buffers;\n // }\n\n /** Return a bind group created by setBindings */\n _getBindGroup() {\n // Get hold of the bind group layout. We don't want to do this unless we know there is at least one bind group\n this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);\n\n // Set up the bindings\n this._bindGroup = this._bindGroup || getBindGroup(\n this.device.handle,\n this._bindGroupLayout,\n this.props.shaderLayout,\n this.props.bindings\n );\n\n return this._bindGroup;\n }\n\n /** \n * Populate the complex WebGPU GPURenderPipelineDescriptor \n */\n protected _getRenderPipelineDescriptor() {\n // Set up the vertex stage\n const vertex: GPUVertexState = {\n module: cast<WebGPUShader>(this.props.vs).handle,\n entryPoint: this.props.vsEntryPoint || 'main',\n buffers: getVertexBufferLayout(this.props.shaderLayout, this.props.bufferLayout)\n };\n\n // Set up the fragment stage\n let fragment: GPUFragmentState | undefined;\n if (this.props.fs) {\n fragment = {\n module: cast<WebGPUShader>(this.props.fs).handle,\n entryPoint: this.props.fsEntryPoint || 'main',\n targets: [\n {\n // TODO exclamation mark hack!\n format: getWebGPUTextureFormat(this.device?.canvasContext?.format)\n }\n ]\n };\n }\n\n // WebGPU has more restrictive topology support than WebGL\n switch (this.props.topology) {\n case 'triangle-fan-webgl':\n case 'line-loop-webgl':\n throw new Error(`WebGPU does not support primitive topology ${this.props.topology}`);\n default:\n }\n\n // Create a partially populated descriptor\n const descriptor: GPURenderPipelineDescriptor = {\n vertex,\n fragment,\n primitive: {\n topology: this.props.topology\n },\n layout: 'auto'\n };\n\n // Set parameters on the descriptor\n applyParametersToRenderPipelineDescriptor(descriptor, this.props.parameters);\n\n return descriptor;\n }\n\n /**\n _setAttributeBuffers(webgpuRenderPass: WebGPURenderPass) {\n if (this._indexBuffer) {\n webgpuRenderPass.handle.setIndexBuffer(this._indexBuffer.handle, this._indexBuffer.props.indexType);\n }\n\n const buffers = this._getBuffers();\n for (let i = 0; i < buffers.length; ++i) {\n const buffer = cast<WebGPUBuffer>(buffers[i]);\n if (!buffer) {\n const attribute = this.props.shaderLayout.attributes.find(\n (attribute) => attribute.location === i\n );\n throw new Error(\n `No buffer provided for attribute '${attribute?.name || ''}' in Model '${this.props.id}'`\n );\n }\n webgpuRenderPass.handle.setVertexBuffer(i, buffer.handle);\n }\n\n // TODO - HANDLE buffer maps\n /*\n for (const [bufferName, attributeMapping] of Object.entries(this.props.bufferLayout)) {\n const buffer = cast<WebGPUBuffer>(this.props.attributes[bufferName]);\n if (!buffer) {\n log.warn(`Missing buffer for buffer map ${bufferName}`)();\n continue;\n }\n\n if ('location' in attributeMapping) {\n // @ts-expect-error TODO model must not depend on webgpu\n renderPass.handle.setVertexBuffer(layout.location, buffer.handle);\n } else {\n for (const [bufferName, mapping] of Object.entries(attributeMapping)) {\n // @ts-expect-error TODO model must not depend on webgpu\n renderPass.handle.setVertexBuffer(field.location, buffer.handle);\n }\n }\n }\n *\n }\n */\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-shader.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-shader.ts"],"names":[],"mappings":";AAGA,OAAO,KAAK,EAAC,WAAW,EAAE,eAAe,EAAC,MAAM,eAAe,CAAC;AAChE,OAAO,EAAC,MAAM,EAAM,MAAM,eAAe,CAAC;AAC1C,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAEnD,MAAM,MAAM,iBAAiB,GAAG,WAAW,GAAG;IAC5C,MAAM,CAAC,EAAE,eAAe,CAAC;CAC1B,CAAC;AAEF;;GAEG;AACH,qBAAa,YAAa,SAAQ,MAAM;IACtC,QAAQ,CAAC,MAAM,EAAE,YAAY,CAAC;IAC9B,QAAQ,CAAC,MAAM,EAAE,eAAe,CAAC;gBAErB,MAAM,EAAE,YAAY,EAAE,KAAK,EAAE,iBAAiB;IAYpD,sBAAsB,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC;
|
|
1
|
+
{"version":3,"file":"webgpu-shader.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-shader.ts"],"names":[],"mappings":";AAGA,OAAO,KAAK,EAAC,WAAW,EAAE,eAAe,EAAC,MAAM,eAAe,CAAC;AAChE,OAAO,EAAC,MAAM,EAAM,MAAM,eAAe,CAAC;AAC1C,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAEnD,MAAM,MAAM,iBAAiB,GAAG,WAAW,GAAG;IAC5C,MAAM,CAAC,EAAE,eAAe,CAAC;CAC1B,CAAC;AAEF;;GAEG;AACH,qBAAa,YAAa,SAAQ,MAAM;IACtC,QAAQ,CAAC,MAAM,EAAE,YAAY,CAAC;IAC9B,QAAQ,CAAC,MAAM,EAAE,eAAe,CAAC;gBAErB,MAAM,EAAE,YAAY,EAAE,KAAK,EAAE,iBAAiB;IAYpD,sBAAsB,CAAC,UAAU,EAAE,OAAO,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,OAAO,CAAC,IAAI,CAAC;IAcxE,OAAO,IAAI,IAAI;IAKxB,+CAA+C;IACzC,kBAAkB,IAAI,OAAO,CAAC,SAAS,eAAe,EAAE,CAAC;IAO/D,SAAS,CAAC,YAAY,IAAI,eAAe;CAuB1C"}
|
|
@@ -13,6 +13,7 @@ export class WebGPUShader extends Shader {
|
|
|
13
13
|
async _checkCompilationError(errorScope) {
|
|
14
14
|
const error = await errorScope;
|
|
15
15
|
if (error) {
|
|
16
|
+
this.debugShader();
|
|
16
17
|
const shaderLog = await this.getCompilationInfo();
|
|
17
18
|
log.error(`Shader compilation error: ${error.message}`, shaderLog)();
|
|
18
19
|
throw new Error(`Shader compilation error: ${error.message}`);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-shader.js","names":["Shader","log","WebGPUShader","constructor","device","props","handle","pushErrorScope","createHandle","label","id","_checkCompilationError","popErrorScope","errorScope","error","shaderLog","getCompilationInfo","message","Error","destroy","compilationInfo","messages","source","stage","language","includes","createShaderModule","code","transform","glsl","glslang","compileGLSL"],"sources":["../../../src/adapter/resources/webgpu-shader.ts"],"sourcesContent":["// luma.gl, MIT license\n// Copyright (c) vis.gl contributors\n\nimport type {ShaderProps, CompilerMessage} from '@luma.gl/core';\nimport {Shader, log} from '@luma.gl/core';\nimport type {WebGPUDevice} from '../webgpu-device';\n\nexport type WebGPUShaderProps = ShaderProps & {\n handle?: GPUShaderModule;\n};\n\n/**\n * Immutable shader\n */\nexport class WebGPUShader extends Shader {\n readonly device: WebGPUDevice;\n readonly handle: GPUShaderModule;\n\n constructor(device: WebGPUDevice, props: WebGPUShaderProps) {\n super(device, props);\n this.device = device;\n\n this.device.handle.pushErrorScope('validation');\n\n this.handle = this.props.handle || this.createHandle();\n this.handle.label = this.props.id;\n\n this._checkCompilationError(this.device.handle.popErrorScope());\n }\n\n async _checkCompilationError(errorScope: Promise<GPUError | null>): Promise<void> {\n const error = await errorScope as GPUValidationError;\n if (error) {\n const shaderLog = await this.getCompilationInfo();\n log.error(`Shader compilation error: ${error.message}`, shaderLog)();\n // Note: Even though this error is asynchronous and thrown after the constructor completes,\n // it will result in a useful stack trace leading back to the constructor\n throw new Error(`Shader compilation error: ${error.message}`);\n }\n }\n\n override destroy(): void {\n // Note: WebGPU does not offer a method to destroy shaders\n // this.handle.destroy();\n }\n\n /** Returns compilation info for this shader */\n async getCompilationInfo(): Promise<readonly CompilerMessage[]> {\n const compilationInfo = await this.handle.getCompilationInfo();\n return compilationInfo.messages;\n }\n\n // PRIVATE METHODS\n\n protected createHandle(): GPUShaderModule {\n const {source, stage} = this.props;\n\n let language = this.props.language;\n // Compile from src\n if (language === 'auto') {\n // wgsl uses C++ \"auto\" style arrow notation\n language = source.includes('->') ? 'wgsl' : 'glsl';\n }\n\n switch(language) {\n case 'wgsl':\n return this.device.handle.createShaderModule({code: source});\n case 'glsl':\n return this.device.handle.createShaderModule({\n code: source,\n // @ts-expect-error\n transform: (glsl) => this.device.glslang.compileGLSL(glsl, stage)\n });\n default:\n throw new Error(language);\n }\n }\n}\n"],"mappings":"AAIA,SAAQA,MAAM,EAAEC,GAAG,QAAO,eAAe;AAUzC,OAAO,MAAMC,YAAY,SAASF,MAAM,CAAC;EAIvCG,WAAWA,CAACC,MAAoB,EAAEC,KAAwB,EAAE;IAC1D,KAAK,CAACD,MAAM,EAAEC,KAAK,CAAC;IAAC,KAJdD,MAAM;IAAA,KACNE,MAAM;IAIb,IAAI,CAACF,MAAM,GAAGA,MAAM;IAEpB,IAAI,CAACA,MAAM,CAACE,MAAM,CAACC,cAAc,CAAC,YAAY,CAAC;IAE/C,IAAI,CAACD,MAAM,GAAG,IAAI,CAACD,KAAK,CAACC,MAAM,IAAI,IAAI,CAACE,YAAY,CAAC,CAAC;IACtD,IAAI,CAACF,MAAM,CAACG,KAAK,GAAG,IAAI,CAACJ,KAAK,CAACK,EAAE;IAEjC,IAAI,CAACC,sBAAsB,CAAC,IAAI,CAACP,MAAM,CAACE,MAAM,CAACM,aAAa,CAAC,CAAC,CAAC;EACjE;EAEA,MAAMD,sBAAsBA,CAACE,UAAoC,EAAiB;IAChF,MAAMC,KAAK,GAAG,MAAMD,UAAgC;IACpD,IAAIC,KAAK,EAAE;
|
|
1
|
+
{"version":3,"file":"webgpu-shader.js","names":["Shader","log","WebGPUShader","constructor","device","props","handle","pushErrorScope","createHandle","label","id","_checkCompilationError","popErrorScope","errorScope","error","debugShader","shaderLog","getCompilationInfo","message","Error","destroy","compilationInfo","messages","source","stage","language","includes","createShaderModule","code","transform","glsl","glslang","compileGLSL"],"sources":["../../../src/adapter/resources/webgpu-shader.ts"],"sourcesContent":["// luma.gl, MIT license\n// Copyright (c) vis.gl contributors\n\nimport type {ShaderProps, CompilerMessage} from '@luma.gl/core';\nimport {Shader, log} from '@luma.gl/core';\nimport type {WebGPUDevice} from '../webgpu-device';\n\nexport type WebGPUShaderProps = ShaderProps & {\n handle?: GPUShaderModule;\n};\n\n/**\n * Immutable shader\n */\nexport class WebGPUShader extends Shader {\n readonly device: WebGPUDevice;\n readonly handle: GPUShaderModule;\n\n constructor(device: WebGPUDevice, props: WebGPUShaderProps) {\n super(device, props);\n this.device = device;\n\n this.device.handle.pushErrorScope('validation');\n\n this.handle = this.props.handle || this.createHandle();\n this.handle.label = this.props.id;\n\n this._checkCompilationError(this.device.handle.popErrorScope());\n }\n\n async _checkCompilationError(errorScope: Promise<GPUError | null>): Promise<void> {\n const error = await errorScope as GPUValidationError;\n if (error) {\n // The `Shader` base class will determine if debug window should be opened based on props\n this.debugShader();\n\n const shaderLog = await this.getCompilationInfo();\n log.error(`Shader compilation error: ${error.message}`, shaderLog)();\n // Note: Even though this error is asynchronous and thrown after the constructor completes,\n // it will result in a useful stack trace leading back to the constructor\n throw new Error(`Shader compilation error: ${error.message}`);\n }\n }\n\n override destroy(): void {\n // Note: WebGPU does not offer a method to destroy shaders\n // this.handle.destroy();\n }\n\n /** Returns compilation info for this shader */\n async getCompilationInfo(): Promise<readonly CompilerMessage[]> {\n const compilationInfo = await this.handle.getCompilationInfo();\n return compilationInfo.messages;\n }\n\n // PRIVATE METHODS\n\n protected createHandle(): GPUShaderModule {\n const {source, stage} = this.props;\n\n let language = this.props.language;\n // Compile from src\n if (language === 'auto') {\n // wgsl uses C++ \"auto\" style arrow notation\n language = source.includes('->') ? 'wgsl' : 'glsl';\n }\n\n switch(language) {\n case 'wgsl':\n return this.device.handle.createShaderModule({code: source});\n case 'glsl':\n return this.device.handle.createShaderModule({\n code: source,\n // @ts-expect-error\n transform: (glsl) => this.device.glslang.compileGLSL(glsl, stage)\n });\n default:\n throw new Error(language);\n }\n }\n}\n"],"mappings":"AAIA,SAAQA,MAAM,EAAEC,GAAG,QAAO,eAAe;AAUzC,OAAO,MAAMC,YAAY,SAASF,MAAM,CAAC;EAIvCG,WAAWA,CAACC,MAAoB,EAAEC,KAAwB,EAAE;IAC1D,KAAK,CAACD,MAAM,EAAEC,KAAK,CAAC;IAAC,KAJdD,MAAM;IAAA,KACNE,MAAM;IAIb,IAAI,CAACF,MAAM,GAAGA,MAAM;IAEpB,IAAI,CAACA,MAAM,CAACE,MAAM,CAACC,cAAc,CAAC,YAAY,CAAC;IAE/C,IAAI,CAACD,MAAM,GAAG,IAAI,CAACD,KAAK,CAACC,MAAM,IAAI,IAAI,CAACE,YAAY,CAAC,CAAC;IACtD,IAAI,CAACF,MAAM,CAACG,KAAK,GAAG,IAAI,CAACJ,KAAK,CAACK,EAAE;IAEjC,IAAI,CAACC,sBAAsB,CAAC,IAAI,CAACP,MAAM,CAACE,MAAM,CAACM,aAAa,CAAC,CAAC,CAAC;EACjE;EAEA,MAAMD,sBAAsBA,CAACE,UAAoC,EAAiB;IAChF,MAAMC,KAAK,GAAG,MAAMD,UAAgC;IACpD,IAAIC,KAAK,EAAE;MAET,IAAI,CAACC,WAAW,CAAC,CAAC;MAElB,MAAMC,SAAS,GAAG,MAAM,IAAI,CAACC,kBAAkB,CAAC,CAAC;MACjDhB,GAAG,CAACa,KAAK,CAAE,6BAA4BA,KAAK,CAACI,OAAQ,EAAC,EAAEF,SAAS,CAAC,CAAC,CAAC;MAGpE,MAAM,IAAIG,KAAK,CAAE,6BAA4BL,KAAK,CAACI,OAAQ,EAAC,CAAC;IAC/D;EACF;EAESE,OAAOA,CAAA,EAAS,CAGzB;EAGA,MAAMH,kBAAkBA,CAAA,EAAwC;IAC9D,MAAMI,eAAe,GAAG,MAAM,IAAI,CAACf,MAAM,CAACW,kBAAkB,CAAC,CAAC;IAC9D,OAAOI,eAAe,CAACC,QAAQ;EACjC;EAIUd,YAAYA,CAAA,EAAoB;IACxC,MAAM;MAACe,MAAM;MAAEC;IAAK,CAAC,GAAG,IAAI,CAACnB,KAAK;IAElC,IAAIoB,QAAQ,GAAG,IAAI,CAACpB,KAAK,CAACoB,QAAQ;IAElC,IAAIA,QAAQ,KAAK,MAAM,EAAE;MAEvBA,QAAQ,GAAGF,MAAM,CAACG,QAAQ,CAAC,IAAI,CAAC,GAAG,MAAM,GAAG,MAAM;IACpD;IAEA,QAAOD,QAAQ;MACb,KAAK,MAAM;QACT,OAAO,IAAI,CAACrB,MAAM,CAACE,MAAM,CAACqB,kBAAkB,CAAC;UAACC,IAAI,EAAEL;QAAM,CAAC,CAAC;MAC9D,KAAK,MAAM;QACT,OAAO,IAAI,CAACnB,MAAM,CAACE,MAAM,CAACqB,kBAAkB,CAAC;UAC3CC,IAAI,EAAEL,MAAM;UAEZM,SAAS,EAAGC,IAAI,IAAK,IAAI,CAAC1B,MAAM,CAAC2B,OAAO,CAACC,WAAW,CAACF,IAAI,EAAEN,KAAK;QAClE,CAAC,CAAC;MACJ;QACE,MAAM,IAAIL,KAAK,CAACM,QAAQ,CAAC;IAC7B;EACF;AACF"}
|
|
@@ -16,8 +16,8 @@ export declare class WebGPUVertexArray extends VertexArray {
|
|
|
16
16
|
* Must be a Buffer bound to buffer with usage bit Buffer.INDEX set.
|
|
17
17
|
*/
|
|
18
18
|
setIndexBuffer(buffer: Buffer | null): void;
|
|
19
|
-
/** Set a
|
|
20
|
-
setBuffer(
|
|
19
|
+
/** Set a bufferSlot in vertex attributes array to a buffer, enables the bufferSlot, sets divisor */
|
|
20
|
+
setBuffer(bufferSlot: number, buffer: Buffer): void;
|
|
21
21
|
/** Set a location in vertex attributes array to a constant value, disables the location */
|
|
22
22
|
setConstant(location: number, value: TypedArray): void;
|
|
23
23
|
bindBeforeRender(renderPass: RenderPass, firstIndex?: number, indexCount?: number): void;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-vertex-array.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-vertex-array.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAC,MAAM,EAAE,MAAM,EAAE,gBAAgB,EAAE,UAAU,EAAE,UAAU,EAAC,MAAM,eAAe,CAAC;AAC5F,OAAO,EAAC,WAAW,EAAM,MAAM,eAAe,CAAC;AAG/C,OAAO,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAK9C,gCAAgC;AAChC,qBAAa,iBAAkB,SAAQ,WAAW;IAChD,IAAa,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,MAAM,CAE1C;IAED,QAAQ,CAAC,MAAM,EAAE,YAAY,CAAC;IAC9B,kDAAkD;IAClD,QAAQ,CAAC,MAAM,EAAE,KAAK,CAAC;IAEvB,6EAA6E;IAC7E,MAAM,CAAC,gCAAgC,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO;gBAKpD,MAAM,EAAE,YAAY,EAAE,KAAK,CAAC,EAAE,gBAAgB;IAKjD,OAAO,IAAI,IAAI;IAExB;;;OAGG;IACH,cAAc,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI;IAK3C,
|
|
1
|
+
{"version":3,"file":"webgpu-vertex-array.d.ts","sourceRoot":"","sources":["../../../src/adapter/resources/webgpu-vertex-array.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAC,MAAM,EAAE,MAAM,EAAE,gBAAgB,EAAE,UAAU,EAAE,UAAU,EAAC,MAAM,eAAe,CAAC;AAC5F,OAAO,EAAC,WAAW,EAAM,MAAM,eAAe,CAAC;AAG/C,OAAO,EAAC,YAAY,EAAC,MAAM,kBAAkB,CAAC;AAK9C,gCAAgC;AAChC,qBAAa,iBAAkB,SAAQ,WAAW;IAChD,IAAa,CAAC,MAAM,CAAC,WAAW,CAAC,IAAI,MAAM,CAE1C;IAED,QAAQ,CAAC,MAAM,EAAE,YAAY,CAAC;IAC9B,kDAAkD;IAClD,QAAQ,CAAC,MAAM,EAAE,KAAK,CAAC;IAEvB,6EAA6E;IAC7E,MAAM,CAAC,gCAAgC,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO;gBAKpD,MAAM,EAAE,YAAY,EAAE,KAAK,CAAC,EAAE,gBAAgB;IAKjD,OAAO,IAAI,IAAI;IAExB;;;OAGG;IACH,cAAc,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI;IAK3C,oGAAoG;IACpG,SAAS,CAAC,UAAU,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI;IASnD,2FAA2F;IAClF,WAAW,CAAC,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,UAAU,GAAG,IAAI;IAItD,gBAAgB,CAAC,UAAU,EAAE,UAAU,EAAE,UAAU,CAAC,EAAE,MAAM,EAAE,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI;IAkBxF,iBAAiB,CAAC,UAAU,EAAE,UAAU,GAAG,IAAI;CAKzD"}
|
|
@@ -19,8 +19,8 @@ export class WebGPUVertexArray extends VertexArray {
|
|
|
19
19
|
setIndexBuffer(buffer) {
|
|
20
20
|
this.indexBuffer = buffer;
|
|
21
21
|
}
|
|
22
|
-
setBuffer(
|
|
23
|
-
this.attributes[
|
|
22
|
+
setBuffer(bufferSlot, buffer) {
|
|
23
|
+
this.attributes[bufferSlot] = buffer;
|
|
24
24
|
}
|
|
25
25
|
setConstant(location, value) {
|
|
26
26
|
log.warn(`${this.id} constant attributes not supported on WebGPU`);
|
|
@@ -35,7 +35,7 @@ export class WebGPUVertexArray extends VertexArray {
|
|
|
35
35
|
for (let location = 0; location < this.maxVertexAttributes; location++) {
|
|
36
36
|
const webgpuBuffer = this.attributes[location];
|
|
37
37
|
if (webgpuBuffer !== null && webgpuBuffer !== void 0 && webgpuBuffer.handle) {
|
|
38
|
-
log.warn(
|
|
38
|
+
log.warn(`setting vertex buffer ${location}`, webgpuBuffer === null || webgpuBuffer === void 0 ? void 0 : webgpuBuffer.handle)();
|
|
39
39
|
webgpuRenderPass.handle.setVertexBuffer(location, webgpuBuffer === null || webgpuBuffer === void 0 ? void 0 : webgpuBuffer.handle);
|
|
40
40
|
}
|
|
41
41
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"webgpu-vertex-array.js","names":["VertexArray","log","getBrowser","_Symbol$toStringTag","Symbol","toStringTag","WebGPUVertexArray","isConstantAttributeZeroSupported","device","info","type","constructor","props","handle","destroy","setIndexBuffer","buffer","indexBuffer","setBuffer","
|
|
1
|
+
{"version":3,"file":"webgpu-vertex-array.js","names":["VertexArray","log","getBrowser","_Symbol$toStringTag","Symbol","toStringTag","WebGPUVertexArray","isConstantAttributeZeroSupported","device","info","type","constructor","props","handle","destroy","setIndexBuffer","buffer","indexBuffer","setBuffer","bufferSlot","attributes","setConstant","location","value","warn","id","bindBeforeRender","renderPass","firstIndex","indexCount","webgpuRenderPass","webgpuIndexBuffer","indexType","maxVertexAttributes","webgpuBuffer","setVertexBuffer","unbindAfterRender"],"sources":["../../../src/adapter/resources/webgpu-vertex-array.ts"],"sourcesContent":["// luma.gl, MIT license\n// Copyright (c) vis.gl contributors\n\nimport type {Device, Buffer, VertexArrayProps, RenderPass, TypedArray} from '@luma.gl/core';\nimport {VertexArray, log} from '@luma.gl/core';\nimport {getBrowser} from '@probe.gl/env';\n\nimport {WebGPUDevice} from '../webgpu-device';\nimport {WebGPUBuffer} from '../resources/webgpu-buffer';\n\nimport {WebGPURenderPass} from './webgpu-render-pass';\n\n/** VertexArrayObject wrapper */\nexport class WebGPUVertexArray extends VertexArray {\n override get [Symbol.toStringTag](): string {\n return 'WebGPUVertexArray';\n }\n\n readonly device: WebGPUDevice;\n /** Vertex Array is a helper class under WebGPU */\n readonly handle: never;\n\n /** * Attribute 0 can not be disable on most desktop OpenGL based browsers */\n static isConstantAttributeZeroSupported(device: Device): boolean {\n return device.info.type === 'webgl2' || getBrowser() === 'Chrome';\n }\n\n // Create a VertexArray\n constructor(device: WebGPUDevice, props?: VertexArrayProps) {\n super(device, props);\n this.device = device;\n }\n\n override destroy(): void {}\n\n /**\n * Set an elements buffer, for indexed rendering.\n * Must be a Buffer bound to buffer with usage bit Buffer.INDEX set. \n */\n setIndexBuffer(buffer: Buffer | null): void {\n // assert(!elementBuffer || elementBuffer.glTarget === GL.ELEMENT_ARRAY_BUFFER, ERR_ELEMENTS);\n this.indexBuffer = buffer;\n }\n\n /** Set a bufferSlot in vertex attributes array to a buffer, enables the bufferSlot, sets divisor */\n setBuffer(bufferSlot: number, buffer: Buffer): void {\n // Sanity check target\n // if (buffer.glUsage === GL.ELEMENT_ARRAY_BUFFER) {\n // throw new Error('Use setIndexBuffer');\n // }\n\n this.attributes[bufferSlot] = buffer;\n }\n\n /** Set a location in vertex attributes array to a constant value, disables the location */\n override setConstant(location: number, value: TypedArray): void {\n log.warn(`${this.id} constant attributes not supported on WebGPU`)\n }\n\n override bindBeforeRender(renderPass: RenderPass, firstIndex?: number, indexCount?: number): void {\n const webgpuRenderPass = renderPass as WebGPURenderPass;\n const webgpuIndexBuffer = this.indexBuffer as WebGPUBuffer;\n if (webgpuIndexBuffer?.handle) {\n // Note we can't unset an index buffer\n log.warn('setting index buffer', webgpuIndexBuffer?.handle, webgpuIndexBuffer?.indexType)();\n webgpuRenderPass.handle.setIndexBuffer(webgpuIndexBuffer?.handle, webgpuIndexBuffer?.indexType);\n }\n for (let location = 0; location < this.maxVertexAttributes; location++) {\n const webgpuBuffer = this.attributes[location] as WebGPUBuffer;\n if (webgpuBuffer?.handle) {\n log.warn(`setting vertex buffer ${location}`,webgpuBuffer?.handle)();\n webgpuRenderPass.handle.setVertexBuffer(location, webgpuBuffer?.handle);\n }\n }\n // TODO - emit warnings/errors/throw if constants have been set on this vertex array\n }\n\n override unbindAfterRender(renderPass: RenderPass): void {\n // On WebGPU we don't need to unbind. \n // In fact we can't easily do it. setIndexBuffer/setVertexBuffer don't accept null.\n // Unbinding presumably happens automatically when the render pass is ended.\n }\n}\n"],"mappings":";AAIA,SAAQA,WAAW,EAAEC,GAAG,QAAO,eAAe;AAC9C,SAAQC,UAAU,QAAO,eAAe;AAACC,mBAAA,GASzBC,MAAM,CAACC,WAAW;AADlC,OAAO,MAAMC,iBAAiB,SAASN,WAAW,CAAC;EACjD,KAAAG,mBAAA,IAA4C;IAC1C,OAAO,mBAAmB;EAC5B;EAOA,OAAOI,gCAAgCA,CAACC,MAAc,EAAW;IAC/D,OAAOA,MAAM,CAACC,IAAI,CAACC,IAAI,KAAK,QAAQ,IAAIR,UAAU,CAAC,CAAC,KAAK,QAAQ;EACnE;EAGAS,WAAWA,CAACH,MAAoB,EAAEI,KAAwB,EAAE;IAC1D,KAAK,CAACJ,MAAM,EAAEI,KAAK,CAAC;IAAC,KAXdJ,MAAM;IAAA,KAENK,MAAM;IAUb,IAAI,CAACL,MAAM,GAAGA,MAAM;EACtB;EAESM,OAAOA,CAAA,EAAS,CAAC;EAM1BC,cAAcA,CAACC,MAAqB,EAAQ;IAE1C,IAAI,CAACC,WAAW,GAAGD,MAAM;EAC3B;EAGAE,SAASA,CAACC,UAAkB,EAAEH,MAAc,EAAQ;IAMlD,IAAI,CAACI,UAAU,CAACD,UAAU,CAAC,GAAGH,MAAM;EACtC;EAGSK,WAAWA,CAACC,QAAgB,EAAEC,KAAiB,EAAQ;IAC9DtB,GAAG,CAACuB,IAAI,CAAE,GAAE,IAAI,CAACC,EAAG,8CAA6C,CAAC;EACpE;EAESC,gBAAgBA,CAACC,UAAsB,EAAEC,UAAmB,EAAEC,UAAmB,EAAQ;IAChG,MAAMC,gBAAgB,GAAGH,UAA8B;IACvD,MAAMI,iBAAiB,GAAG,IAAI,CAACd,WAA2B;IAC1D,IAAIc,iBAAiB,aAAjBA,iBAAiB,eAAjBA,iBAAiB,CAAElB,MAAM,EAAE;MAE7BZ,GAAG,CAACuB,IAAI,CAAC,sBAAsB,EAAEO,iBAAiB,aAAjBA,iBAAiB,uBAAjBA,iBAAiB,CAAElB,MAAM,EAAEkB,iBAAiB,aAAjBA,iBAAiB,uBAAjBA,iBAAiB,CAAEC,SAAS,CAAC,CAAC,CAAC;MAC3FF,gBAAgB,CAACjB,MAAM,CAACE,cAAc,CAACgB,iBAAiB,aAAjBA,iBAAiB,uBAAjBA,iBAAiB,CAAElB,MAAM,EAAEkB,iBAAiB,aAAjBA,iBAAiB,uBAAjBA,iBAAiB,CAAEC,SAAS,CAAC;IACjG;IACA,KAAK,IAAIV,QAAQ,GAAG,CAAC,EAAEA,QAAQ,GAAG,IAAI,CAACW,mBAAmB,EAAEX,QAAQ,EAAE,EAAE;MACtE,MAAMY,YAAY,GAAG,IAAI,CAACd,UAAU,CAACE,QAAQ,CAAiB;MAC9D,IAAIY,YAAY,aAAZA,YAAY,eAAZA,YAAY,CAAErB,MAAM,EAAE;QACxBZ,GAAG,CAACuB,IAAI,CAAE,yBAAwBF,QAAS,EAAC,EAACY,YAAY,aAAZA,YAAY,uBAAZA,YAAY,CAAErB,MAAM,CAAC,CAAC,CAAC;QACpEiB,gBAAgB,CAACjB,MAAM,CAACsB,eAAe,CAACb,QAAQ,EAAEY,YAAY,aAAZA,YAAY,uBAAZA,YAAY,CAAErB,MAAM,CAAC;MACzE;IACF;EAEF;EAESuB,iBAAiBA,CAACT,UAAsB,EAAQ,CAIzD;AACF"}
|
package/dist/dist.dev.js
CHANGED
|
@@ -1038,7 +1038,19 @@ var __exports__ = (() => {
|
|
|
1038
1038
|
readPixelsToArrayWebGL(source, options) {
|
|
1039
1039
|
throw new Error("not implemented");
|
|
1040
1040
|
}
|
|
1041
|
-
|
|
1041
|
+
readPixelsToBufferWebGL(source, options) {
|
|
1042
|
+
throw new Error("not implemented");
|
|
1043
|
+
}
|
|
1044
|
+
setParametersWebGL(parameters) {
|
|
1045
|
+
throw new Error("not implemented");
|
|
1046
|
+
}
|
|
1047
|
+
getParametersWebGL(parameters) {
|
|
1048
|
+
throw new Error("not implemented");
|
|
1049
|
+
}
|
|
1050
|
+
withParametersWebGL(parameters, func) {
|
|
1051
|
+
throw new Error("not implemented");
|
|
1052
|
+
}
|
|
1053
|
+
clearWebGL(options) {
|
|
1042
1054
|
throw new Error("not implemented");
|
|
1043
1055
|
}
|
|
1044
1056
|
_getBufferProps(props) {
|
|
@@ -1425,7 +1437,8 @@ ${numberedLines}${positionIndicator}${message.type.toUpperCase()}: ${message.mes
|
|
|
1425
1437
|
return numberedLines;
|
|
1426
1438
|
}
|
|
1427
1439
|
function getNumberedLine(line, lineNum, options) {
|
|
1428
|
-
|
|
1440
|
+
const escapedLine = options?.html ? escapeHTML(line) : line;
|
|
1441
|
+
return `${padLeft(String(lineNum), 4)}: ${escapedLine}${options?.html ? "<br/>" : "\n"}`;
|
|
1429
1442
|
}
|
|
1430
1443
|
function padLeft(string, paddedLength) {
|
|
1431
1444
|
let result = "";
|
|
@@ -1434,6 +1447,9 @@ ${numberedLines}${positionIndicator}${message.type.toUpperCase()}: ${message.mes
|
|
|
1434
1447
|
}
|
|
1435
1448
|
return result + string;
|
|
1436
1449
|
}
|
|
1450
|
+
function escapeHTML(unsafe) {
|
|
1451
|
+
return unsafe.replaceAll("&", "&").replaceAll("<", "<").replaceAll(">", ">").replaceAll('"', """).replaceAll("'", "'");
|
|
1452
|
+
}
|
|
1437
1453
|
|
|
1438
1454
|
// ../core/src/lib/compiler-log/get-shader-info.ts
|
|
1439
1455
|
function getShaderInfo(source, defaultName) {
|
|
@@ -2236,6 +2252,7 @@ ${htmlLog}
|
|
|
2236
2252
|
async _checkCompilationError(errorScope) {
|
|
2237
2253
|
const error = await errorScope;
|
|
2238
2254
|
if (error) {
|
|
2255
|
+
this.debugShader();
|
|
2239
2256
|
const shaderLog = await this.getCompilationInfo();
|
|
2240
2257
|
log.error(`Shader compilation error: ${error.message}`, shaderLog)();
|
|
2241
2258
|
throw new Error(`Shader compilation error: ${error.message}`);
|
|
@@ -2416,7 +2433,7 @@ ${htmlLog}
|
|
|
2416
2433
|
});
|
|
2417
2434
|
}
|
|
2418
2435
|
function getShaderLayoutBinding(shaderLayout, bindingName) {
|
|
2419
|
-
const bindingLayout = shaderLayout.bindings.find((binding) => binding.name === bindingName);
|
|
2436
|
+
const bindingLayout = shaderLayout.bindings.find((binding) => binding.name === bindingName || `${binding.name}uniforms` === bindingName.toLocaleLowerCase());
|
|
2420
2437
|
if (!bindingLayout) {
|
|
2421
2438
|
log.warn(`Binding ${bindingName} not set: Not found in shader layout.`)();
|
|
2422
2439
|
}
|
|
@@ -2475,7 +2492,7 @@ ${htmlLog}
|
|
|
2475
2492
|
for (const attributeMapping of mapping.attributes) {
|
|
2476
2493
|
const attributeName = attributeMapping.attribute;
|
|
2477
2494
|
const attributeLayout = findAttributeLayout(shaderLayout, attributeName, usedAttributes);
|
|
2478
|
-
stepMode = attributeLayout.stepMode || "vertex";
|
|
2495
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith("instance") ? "instance" : "vertex");
|
|
2479
2496
|
vertexAttributes.push({
|
|
2480
2497
|
format: getWebGPUVertexFormat(attributeMapping.format || mapping.format),
|
|
2481
2498
|
offset: attributeMapping.byteOffset,
|
|
@@ -2489,7 +2506,7 @@ ${htmlLog}
|
|
|
2489
2506
|
continue;
|
|
2490
2507
|
}
|
|
2491
2508
|
byteStride = decodeVertexFormat(mapping.format).byteLength;
|
|
2492
|
-
stepMode = attributeLayout.stepMode || "vertex";
|
|
2509
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith("instance") ? "instance" : "vertex");
|
|
2493
2510
|
vertexAttributes.push({
|
|
2494
2511
|
format: getWebGPUVertexFormat(mapping.format),
|
|
2495
2512
|
offset: 0,
|
|
@@ -2498,7 +2515,7 @@ ${htmlLog}
|
|
|
2498
2515
|
}
|
|
2499
2516
|
vertexBufferLayouts.push({
|
|
2500
2517
|
arrayStride: mapping.byteStride || byteStride,
|
|
2501
|
-
stepMode
|
|
2518
|
+
stepMode,
|
|
2502
2519
|
attributes: vertexAttributes
|
|
2503
2520
|
});
|
|
2504
2521
|
}
|
|
@@ -2506,7 +2523,7 @@ ${htmlLog}
|
|
|
2506
2523
|
if (!usedAttributes.has(attribute.name)) {
|
|
2507
2524
|
vertexBufferLayouts.push({
|
|
2508
2525
|
arrayStride: decodeVertexFormat("float32x3").byteLength,
|
|
2509
|
-
stepMode: attribute.stepMode || "vertex",
|
|
2526
|
+
stepMode: attribute.stepMode || (attribute.name.startsWith("instance") ? "instance" : "vertex"),
|
|
2510
2527
|
attributes: [{
|
|
2511
2528
|
format: getWebGPUVertexFormat("float32x3"),
|
|
2512
2529
|
offset: 0,
|
|
@@ -2553,11 +2570,7 @@ ${htmlLog}
|
|
|
2553
2570
|
destroy() {
|
|
2554
2571
|
}
|
|
2555
2572
|
setBindings(bindings) {
|
|
2556
|
-
|
|
2557
|
-
Object.assign(this.props.bindings, bindings);
|
|
2558
|
-
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
2559
|
-
this._bindGroup = getBindGroup(this.device.handle, this._bindGroupLayout, this.props.shaderLayout, this.props.bindings);
|
|
2560
|
-
}
|
|
2573
|
+
Object.assign(this.props.bindings, bindings);
|
|
2561
2574
|
}
|
|
2562
2575
|
setUniforms(uniforms) {
|
|
2563
2576
|
if (!isObjectEmpty(uniforms)) {
|
|
@@ -2580,6 +2593,8 @@ ${htmlLog}
|
|
|
2580
2593
|
options.vertexArray.unbindAfterRender(options.renderPass);
|
|
2581
2594
|
}
|
|
2582
2595
|
_getBindGroup() {
|
|
2596
|
+
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
2597
|
+
this._bindGroup = this._bindGroup || getBindGroup(this.device.handle, this._bindGroupLayout, this.props.shaderLayout, this.props.bindings);
|
|
2583
2598
|
return this._bindGroup;
|
|
2584
2599
|
}
|
|
2585
2600
|
_getRenderPipelineDescriptor() {
|
|
@@ -2805,8 +2820,8 @@ ${htmlLog}
|
|
|
2805
2820
|
setIndexBuffer(buffer) {
|
|
2806
2821
|
this.indexBuffer = buffer;
|
|
2807
2822
|
}
|
|
2808
|
-
setBuffer(
|
|
2809
|
-
this.attributes[
|
|
2823
|
+
setBuffer(bufferSlot, buffer) {
|
|
2824
|
+
this.attributes[bufferSlot] = buffer;
|
|
2810
2825
|
}
|
|
2811
2826
|
setConstant(location, value) {
|
|
2812
2827
|
log.warn(`${this.id} constant attributes not supported on WebGPU`);
|
|
@@ -2821,7 +2836,7 @@ ${htmlLog}
|
|
|
2821
2836
|
for (let location = 0; location < this.maxVertexAttributes; location++) {
|
|
2822
2837
|
const webgpuBuffer = this.attributes[location];
|
|
2823
2838
|
if (webgpuBuffer?.handle) {
|
|
2824
|
-
log.warn(
|
|
2839
|
+
log.warn(`setting vertex buffer ${location}`, webgpuBuffer?.handle)();
|
|
2825
2840
|
webgpuRenderPass.handle.setVertexBuffer(location, webgpuBuffer?.handle);
|
|
2826
2841
|
}
|
|
2827
2842
|
}
|
package/dist/index.cjs
CHANGED
|
@@ -381,6 +381,7 @@ var WebGPUShader = class extends import_core5.Shader {
|
|
|
381
381
|
async _checkCompilationError(errorScope) {
|
|
382
382
|
const error = await errorScope;
|
|
383
383
|
if (error) {
|
|
384
|
+
this.debugShader();
|
|
384
385
|
const shaderLog = await this.getCompilationInfo();
|
|
385
386
|
import_core5.log.error(`Shader compilation error: ${error.message}`, shaderLog)();
|
|
386
387
|
throw new Error(`Shader compilation error: ${error.message}`);
|
|
@@ -613,7 +614,7 @@ function getBindGroup(device, bindGroupLayout, shaderLayout, bindings) {
|
|
|
613
614
|
});
|
|
614
615
|
}
|
|
615
616
|
function getShaderLayoutBinding(shaderLayout, bindingName) {
|
|
616
|
-
const bindingLayout = shaderLayout.bindings.find((binding) => binding.name === bindingName);
|
|
617
|
+
const bindingLayout = shaderLayout.bindings.find((binding) => binding.name === bindingName || `${binding.name}uniforms` === bindingName.toLocaleLowerCase());
|
|
617
618
|
if (!bindingLayout) {
|
|
618
619
|
import_core6.log.warn(`Binding ${bindingName} not set: Not found in shader layout.`)();
|
|
619
620
|
}
|
|
@@ -671,7 +672,7 @@ function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
671
672
|
for (const attributeMapping of mapping.attributes) {
|
|
672
673
|
const attributeName = attributeMapping.attribute;
|
|
673
674
|
const attributeLayout = findAttributeLayout(shaderLayout, attributeName, usedAttributes);
|
|
674
|
-
stepMode = attributeLayout.stepMode || "vertex";
|
|
675
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith("instance") ? "instance" : "vertex");
|
|
675
676
|
vertexAttributes.push({
|
|
676
677
|
format: getWebGPUVertexFormat(attributeMapping.format || mapping.format),
|
|
677
678
|
offset: attributeMapping.byteOffset,
|
|
@@ -685,7 +686,7 @@ function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
685
686
|
continue;
|
|
686
687
|
}
|
|
687
688
|
byteStride = (0, import_core7.decodeVertexFormat)(mapping.format).byteLength;
|
|
688
|
-
stepMode = attributeLayout.stepMode || "vertex";
|
|
689
|
+
stepMode = attributeLayout.stepMode || (attributeLayout.name.startsWith("instance") ? "instance" : "vertex");
|
|
689
690
|
vertexAttributes.push({
|
|
690
691
|
format: getWebGPUVertexFormat(mapping.format),
|
|
691
692
|
// We only support 0 offset for non-interleaved buffer layouts
|
|
@@ -695,7 +696,7 @@ function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
695
696
|
}
|
|
696
697
|
vertexBufferLayouts.push({
|
|
697
698
|
arrayStride: mapping.byteStride || byteStride,
|
|
698
|
-
stepMode
|
|
699
|
+
stepMode,
|
|
699
700
|
attributes: vertexAttributes
|
|
700
701
|
});
|
|
701
702
|
}
|
|
@@ -703,7 +704,7 @@ function getVertexBufferLayout(shaderLayout, bufferLayout) {
|
|
|
703
704
|
if (!usedAttributes.has(attribute.name)) {
|
|
704
705
|
vertexBufferLayouts.push({
|
|
705
706
|
arrayStride: (0, import_core7.decodeVertexFormat)("float32x3").byteLength,
|
|
706
|
-
stepMode: attribute.stepMode || "vertex",
|
|
707
|
+
stepMode: attribute.stepMode || (attribute.name.startsWith("instance") ? "instance" : "vertex"),
|
|
707
708
|
attributes: [
|
|
708
709
|
{
|
|
709
710
|
format: getWebGPUVertexFormat("float32x3"),
|
|
@@ -786,16 +787,7 @@ var WebGPURenderPipeline = class extends import_core8.RenderPipeline {
|
|
|
786
787
|
// throw new Error('not implemented');
|
|
787
788
|
// }
|
|
788
789
|
setBindings(bindings) {
|
|
789
|
-
|
|
790
|
-
Object.assign(this.props.bindings, bindings);
|
|
791
|
-
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
792
|
-
this._bindGroup = getBindGroup(
|
|
793
|
-
this.device.handle,
|
|
794
|
-
this._bindGroupLayout,
|
|
795
|
-
this.props.shaderLayout,
|
|
796
|
-
this.props.bindings
|
|
797
|
-
);
|
|
798
|
-
}
|
|
790
|
+
Object.assign(this.props.bindings, bindings);
|
|
799
791
|
}
|
|
800
792
|
setUniforms(uniforms) {
|
|
801
793
|
if (!(0, import_core8.isObjectEmpty)(uniforms)) {
|
|
@@ -833,6 +825,13 @@ var WebGPURenderPipeline = class extends import_core8.RenderPipeline {
|
|
|
833
825
|
// }
|
|
834
826
|
/** Return a bind group created by setBindings */
|
|
835
827
|
_getBindGroup() {
|
|
828
|
+
this._bindGroupLayout = this._bindGroupLayout || this.handle.getBindGroupLayout(0);
|
|
829
|
+
this._bindGroup = this._bindGroup || getBindGroup(
|
|
830
|
+
this.device.handle,
|
|
831
|
+
this._bindGroupLayout,
|
|
832
|
+
this.props.shaderLayout,
|
|
833
|
+
this.props.bindings
|
|
834
|
+
);
|
|
836
835
|
return this._bindGroup;
|
|
837
836
|
}
|
|
838
837
|
/**
|
|
@@ -1174,9 +1173,9 @@ var WebGPUVertexArray = class extends import_core12.VertexArray {
|
|
|
1174
1173
|
setIndexBuffer(buffer) {
|
|
1175
1174
|
this.indexBuffer = buffer;
|
|
1176
1175
|
}
|
|
1177
|
-
/** Set a
|
|
1178
|
-
setBuffer(
|
|
1179
|
-
this.attributes[
|
|
1176
|
+
/** Set a bufferSlot in vertex attributes array to a buffer, enables the bufferSlot, sets divisor */
|
|
1177
|
+
setBuffer(bufferSlot, buffer) {
|
|
1178
|
+
this.attributes[bufferSlot] = buffer;
|
|
1180
1179
|
}
|
|
1181
1180
|
/** Set a location in vertex attributes array to a constant value, disables the location */
|
|
1182
1181
|
setConstant(location, value) {
|
|
@@ -1192,7 +1191,7 @@ var WebGPUVertexArray = class extends import_core12.VertexArray {
|
|
|
1192
1191
|
for (let location = 0; location < this.maxVertexAttributes; location++) {
|
|
1193
1192
|
const webgpuBuffer = this.attributes[location];
|
|
1194
1193
|
if (webgpuBuffer == null ? void 0 : webgpuBuffer.handle) {
|
|
1195
|
-
import_core12.log.warn(
|
|
1194
|
+
import_core12.log.warn(`setting vertex buffer ${location}`, webgpuBuffer == null ? void 0 : webgpuBuffer.handle)();
|
|
1196
1195
|
webgpuRenderPass.handle.setVertexBuffer(location, webgpuBuffer == null ? void 0 : webgpuBuffer.handle);
|
|
1197
1196
|
}
|
|
1198
1197
|
}
|