playcanvas
Version:
Open-source WebGL/WebGPU 3D engine for the web
58 lines (57 loc) • 1.73 kB
JavaScript
import { array } from "../../../core/array-utils.js";
import { TRACEID_COMPUTEPIPELINE_ALLOC } from "../../../core/constants.js";
import { hash32Fnv1a } from "../../../core/hash.js";
import { WebgpuPipeline } from "./webgpu-pipeline.js";
let _pipelineId = 0;
class CacheEntry {
pipeline = null;
hashes = null;
}
class WebgpuComputePipeline extends WebgpuPipeline {
lookupHashes = new Uint32Array(2);
cache = /* @__PURE__ */ new Map();
get(shader, bindGroupFormat) {
const lookupHashes = this.lookupHashes;
lookupHashes[0] = shader.impl.computeKey;
lookupHashes[1] = bindGroupFormat.impl.key;
const hash = hash32Fnv1a(lookupHashes);
let cacheEntries = this.cache.get(hash);
if (cacheEntries) {
for (let i = 0; i < cacheEntries.length; i++) {
const entry = cacheEntries[i];
if (array.equals(entry.hashes, lookupHashes)) {
return entry.pipeline;
}
}
}
const pipelineLayout = this.getPipelineLayout([bindGroupFormat.impl]);
const cacheEntry = new CacheEntry();
cacheEntry.hashes = new Uint32Array(lookupHashes);
cacheEntry.pipeline = this.create(shader, pipelineLayout);
if (cacheEntries) {
cacheEntries.push(cacheEntry);
} else {
cacheEntries = [cacheEntry];
}
this.cache.set(hash, cacheEntries);
return cacheEntry.pipeline;
}
create(shader, pipelineLayout) {
const wgpu = this.device.wgpu;
const webgpuShader = shader.impl;
const desc = {
compute: {
module: webgpuShader.getComputeShaderModule(),
entryPoint: webgpuShader.computeEntryPoint
},
// uniform / texture binding layout
layout: pipelineLayout
};
_pipelineId++;
const pipeline = wgpu.createComputePipeline(desc);
return pipeline;
}
}
export {
WebgpuComputePipeline
};