UNPKG

playcanvas

Version:

Open-source WebGL/WebGPU 3D engine for the web

103 lines (102 loc) 3.58 kB
var __defProp = Object.defineProperty; var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value; var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value); import { semanticToLocation, TYPE_INT8, TYPE_UINT8, TYPE_INT16, TYPE_UINT16, TYPE_INT32, TYPE_UINT32, TYPE_FLOAT32, TYPE_FLOAT16 } from "../constants.js"; const gpuVertexFormats = []; gpuVertexFormats[TYPE_INT8] = "sint8"; gpuVertexFormats[TYPE_UINT8] = "uint8"; gpuVertexFormats[TYPE_INT16] = "sint16"; gpuVertexFormats[TYPE_UINT16] = "uint16"; gpuVertexFormats[TYPE_INT32] = "sint32"; gpuVertexFormats[TYPE_UINT32] = "uint32"; gpuVertexFormats[TYPE_FLOAT32] = "float32"; gpuVertexFormats[TYPE_FLOAT16] = "float16"; const gpuVertexFormatsNormalized = []; gpuVertexFormatsNormalized[TYPE_INT8] = "snorm8"; gpuVertexFormatsNormalized[TYPE_UINT8] = "unorm8"; gpuVertexFormatsNormalized[TYPE_INT16] = "snorm16"; gpuVertexFormatsNormalized[TYPE_UINT16] = "unorm16"; gpuVertexFormatsNormalized[TYPE_INT32] = "sint32"; gpuVertexFormatsNormalized[TYPE_UINT32] = "uint32"; gpuVertexFormatsNormalized[TYPE_FLOAT32] = "float32"; gpuVertexFormatsNormalized[TYPE_FLOAT16] = "float16"; class WebgpuVertexBufferLayout { constructor() { /** * @type {Map<string, GPUVertexBufferLayout[]>} * @private */ __publicField(this, "cache", /* @__PURE__ */ new Map()); } /** * Obtain a vertex layout of one or two vertex formats. * * @param {VertexFormat} vertexFormat0 - The first vertex format. * @param {VertexFormat} [vertexFormat1] - The second vertex format. * @returns {any[]} - The vertex layout. */ get(vertexFormat0, vertexFormat1 = null) { const key = this.getKey(vertexFormat0, vertexFormat1); let layout = this.cache.get(key); if (!layout) { layout = this.create(vertexFormat0, vertexFormat1); this.cache.set(key, layout); } return layout; } getKey(vertexFormat0, vertexFormat1 = null) { return `${vertexFormat0?.renderingHashString}-${vertexFormat1?.renderingHashString}`; } /** * @param {VertexFormat} vertexFormat0 - The first vertex format. * @param {VertexFormat} vertexFormat1 - The second vertex format. * @returns {any[]} - The vertex buffer layout. */ create(vertexFormat0, vertexFormat1) { const layout = []; const addFormat = (format) => { const interleaved = format.interleaved; const stepMode = format.instancing ? "instance" : "vertex"; let attributes = []; const elementCount = format.elements.length; for (let i = 0; i < elementCount; i++) { const element = format.elements[i]; const location = semanticToLocation[element.name]; const formatTable = element.normalize ? gpuVertexFormatsNormalized : gpuVertexFormats; attributes.push({ shaderLocation: location, offset: interleaved ? element.offset : 0, format: `${formatTable[element.dataType]}${element.numComponents > 1 ? `x${element.numComponents}` : ""}` }); if (!interleaved || i === elementCount - 1) { layout.push({ attributes, arrayStride: element.stride, stepMode }); attributes = []; } } }; if (vertexFormat0) { addFormat(vertexFormat0); } if (vertexFormat1) { addFormat(vertexFormat1); } return layout; } } export { WebgpuVertexBufferLayout };