Popov72 4 лет назад
Родитель
Сommit
9913137a2e

+ 3 - 4
src/Engines/WebGPU/webgpuCacheSampler.ts

@@ -51,8 +51,7 @@ const filterNoMipToBits = [
 /** @hidden */
 export class WebGPUCacheSampler {
 
-    private static _samplers: { [hash: number]: GPUSampler } = {};
-
+    private _samplers: { [hash: number]: GPUSampler } = {};
     private _device: GPUDevice;
 
     constructor(device: GPUDevice) {
@@ -235,11 +234,11 @@ export class WebGPUCacheSampler {
     public getSampler(internalTexture: InternalTexture, bypassCache = false): GPUSampler {
         const hash = bypassCache ? 0 : WebGPUCacheSampler._GetSamplerHashCode(internalTexture);
 
-        let sampler = bypassCache ? undefined : WebGPUCacheSampler._samplers[hash];
+        let sampler = bypassCache ? undefined : this._samplers[hash];
         if (!sampler) {
             sampler =  this._device.createSampler(WebGPUCacheSampler._GetSamplerDescriptor(internalTexture));
             if (!bypassCache) {
-                WebGPUCacheSampler._samplers[hash] = sampler;
+                this._samplers[hash] = sampler;
             }
         }
 

+ 34 - 0
src/Engines/WebGPU/webgpuShaderManager.ts

@@ -0,0 +1,34 @@
+import { Effect } from "../../Materials/effect";
+import { IWebGPURenderPipelineStageDescriptor } from "./webgpuPipelineContext";
+
+/** @hidden */
+export class WebGPUShaderManager {
+
+    private _shaders: { [name: string]: IWebGPURenderPipelineStageDescriptor } = {};
+    private _device: GPUDevice;
+
+    constructor(device: GPUDevice) {
+        this._device = device;
+    }
+
+    public getCompiledShaders(name: string): IWebGPURenderPipelineStageDescriptor {
+        let shaders = this._shaders[name];
+        if (!shaders) {
+            shaders = this._shaders[name] = {
+                vertexStage: {
+                    module: this._device.createShaderModule({
+                        code: Effect.ShadersStore[name + "VertexShader"]
+                    }),
+                    entryPoint: 'main'
+                },
+                fragmentStage: {
+                    module: this._device.createShaderModule({
+                        code: Effect.ShadersStore[name + "PixelShader"]
+                    }),
+                    entryPoint: 'main'
+                }
+            };
+        }
+        return shaders;
+    }
+}

+ 5 - 0
src/Engines/WebGPU/webgpuShaderProcessors.ts

@@ -14,6 +14,11 @@ const _knownUBOs: { [key: string]: { setIndex: number, bindingIndex: number} } =
     "Light1": { setIndex: 0, bindingIndex: 6 },
     "Light2": { setIndex: 0, bindingIndex: 7 },
     "Light3": { setIndex: 0, bindingIndex: 8 },
+    "Light4": { setIndex: 0, bindingIndex: 9 },
+    "Light5": { setIndex: 0, bindingIndex: 10 },
+    "Light6": { setIndex: 0, bindingIndex: 11 },
+    "Light7": { setIndex: 0, bindingIndex: 12 },
+    "Light8": { setIndex: 0, bindingIndex: 13 },
     "Material": { setIndex: 1, bindingIndex: 0 },
     "Mesh": { setIndex: 1, bindingIndex: 1 },
 };

+ 17 - 49
src/Engines/webgpuEngine.ts

@@ -34,6 +34,10 @@ import { UniformBuffer } from '../Materials/uniformBuffer';
 import { WebGPURenderPassWrapper } from './WebGPU/webgpuRenderPassWrapper';
 import { IMultiRenderTargetOptions } from '../Materials/Textures/multiRenderTarget';
 import { WebGPUCacheSampler } from "./WebGPU/webgpuCacheSampler";
+import { WebGPUShaderManager } from "./WebGPU/webgpuShaderManager";
+
+import "../Shaders/clearQuad.vertex";
+import "../Shaders/clearQuad.fragment";
 
 declare type VideoTexture = import("../Materials/Textures/videoTexture").VideoTexture;
 declare type RenderTargetTexture = import("../Materials/Textures/renderTargetTexture").RenderTargetTexture;
@@ -162,13 +166,13 @@ export class WebGPUEngine extends Engine {
     private _mainPassSampleCount: number;
     private _textureHelper: WebGPUTextureHelper;
     private _bufferManager: WebGPUBufferManager;
+    private _shaderManager: WebGPUShaderManager;
     private _cacheSampler: WebGPUCacheSampler;
     private _emptyVertexBuffer: VertexBuffer;
     private _lastCachedWrapU: number;
     private _lastCachedWrapV: number;
     private _lastCachedWrapR: number;
     private _mrtAttachments: number[];
-    private _privateShaders: { [name: string]: IWebGPURenderPipelineStageDescriptor } = {};
     private _counters: {
         numPipelineDescriptorCreation: number;
         numBindGroupsCreation: number;
@@ -371,6 +375,7 @@ export class WebGPUEngine extends Engine {
             .then(() => {
                 this._bufferManager = new WebGPUBufferManager(this._device);
                 this._textureHelper = new WebGPUTextureHelper(this._device, this._glslang, this._bufferManager);
+                this._shaderManager = new WebGPUShaderManager(this._device);
                 this._cacheSampler = new WebGPUCacheSampler(this._device);
 
                 if (this.dbgVerboseLogsForFirstFrames) {
@@ -2829,6 +2834,7 @@ export class WebGPUEngine extends Engine {
 
         if (setClearStates && scissorIsActive) {
             this._applyScissor(this._currentRenderPass);
+            // TODO WEBGPU cache things, move this code somewhere else
             const pipeline = this._device.createRenderPipeline({
                 sampleCount: this._currentRenderTarget ? this._currentRenderTarget.samples : this._mainPassSampleCount,
                 primitiveTopology: WebGPUConstants.PrimitiveTopology.TriangleStrip,
@@ -2840,10 +2846,10 @@ export class WebGPUEngine extends Engine {
                     depthWriteEnabled: clearDepth,
                     depthCompare: WebGPUConstants.CompareFunction.Always,
                     format: this._depthTextureFormat,
-                    /*stencilFront: {
+                    stencilFront: {
                         compare: clearStencil ? WebGPUConstants.CompareFunction.Always : WebGPUConstants.CompareFunction.Never,
                         passOp: clearStencil ? WebGPUConstants.StencilOperation.Replace : WebGPUConstants.StencilOperation.Keep,
-                    },*/
+                    },
                     stencilReadMask: 0xFF,
                     stencilWriteMask: clearStencil ? 0xFF : 0,
                 },
@@ -2853,7 +2859,7 @@ export class WebGPUEngine extends Engine {
                     writeMask: clearColor ? WebGPUConstants.ColorWrite.All : 0,
                 }],
 
-                ...this._getCompiledShaders("clearQuad"),
+                ...this._shaderManager.getCompiledShaders("clearQuad"),
             });
 
             const bindGroupLayout = pipeline.getBindGroupLayout(0);
@@ -2875,55 +2881,17 @@ export class WebGPUEngine extends Engine {
                 }],
             });
 
+            this._currentRenderPass.setStencilReference(this._clearStencilValue);
             this._currentRenderPass.setPipeline(pipeline);
             this._currentRenderPass.setBindGroup(0, bindGroup);
             this._currentRenderPass.draw(4, 1, 0, 0);
 
-            this._bufferManager.releaseBuffer(buffer);
-        }
-    }
-
-    private _getCompiledShaders(name: string): IWebGPURenderPipelineStageDescriptor {
-        let shaders = this._privateShaders[name];
-        if (!shaders) {
-            const vertexShader = /*Effect.ShadersStore[name + "VertexShader"];*/`
-                #version 450
-
-                const vec2 pos[4] = vec2[4](vec2(-1.0f, 1.0f), vec2(1.0f, 1.0f), vec2(-1.0f, -1.0f), vec2(1.0f, -1.0f));
-
-                void main() {
-                    gl_Position = vec4(pos[gl_VertexIndex], 0.0, 1.0);
-                }
-            `;
-            const fragmentShader = /*Effect.ShadersStore[name + "PixelShader"];*/`
-                #version 450
-
-                layout(set = 0, binding = 0) uniform Uniforms {
-                    uniform vec4 color;
-                };
-
-                layout(location = 0) out vec4 outColor;
+            if (this._stencilState.stencilTest) {
+                this._getCurrentRenderPass().setStencilReference(this._stencilState.stencilFuncRef);
+            }
 
-                void main() {
-                    outColor = color;
-                }
-            `;
-            shaders = this._privateShaders[name] = {
-                vertexStage: {
-                    module: this._device.createShaderModule({
-                        code: this._glslang.compileGLSL(vertexShader, 'vertex')
-                    }),
-                    entryPoint: 'main'
-                },
-                fragmentStage: {
-                    module: this._device.createShaderModule({
-                        code: this._glslang.compileGLSL(fragmentShader, 'fragment')
-                    }),
-                    entryPoint: 'main'
-                }
-            };
+            this._bufferManager.releaseBuffer(buffer);
         }
-        return shaders;
     }
 
     private _endMainRenderPass(): void {
@@ -4007,13 +3975,13 @@ export class WebGPUEngine extends Engine {
         const bindGroups = this._getBindGroupsToRender();
         this._setRenderBindGroups(bindGroups);
 
-        if (this._stencilState.stencilTest) {
+        // TODO WEBGPU add dirty mechanism as for _alphaState._blendConstants
+        if (this._stencilState.stencilTest && renderPass !== this._bundleEncoder) {
             this._getCurrentRenderPass().setStencilReference(this._stencilState.stencilFuncRef);
         }
 
         // TODO WebGPU add back the dirty mechanism, but we need to distinguish between the main render pass and the RTT pass (if any)
         if (this._alphaState.alphaBlend /* && this._alphaState._isBlendConstantsDirty*/ && renderPass !== this._bundleEncoder) {
-            // TODO WebGPU. should use renderPass.
             this._getCurrentRenderPass().setBlendColor(this._alphaState._blendConstants as any);
         }
 

+ 8 - 7
src/Shaders/clearQuad.fragment.fx

@@ -1,11 +1,12 @@
-#version 450
-
-layout(set = 0, binding = 0) uniform Uniforms {
-    uniform vec4 color;
+[[block]] struct Uniforms {
+  [[offset(0)]] color : vec4<f32>;
 };
+[[binding(0), set(0)]] var<uniform> uniforms : Uniforms;
 
-layout(location = 0) out vec4 outColor;
+[[location(0)]] var<out> outColor : vec4<f32>;
 
-void main() {
-    outColor = color;
+[[stage(fragment)]]
+fn main() -> void {
+  outColor = uniforms.color;
+  return;
 }

+ 14 - 4
src/Shaders/clearQuad.vertex.fx

@@ -1,7 +1,17 @@
-#version 450
+// don't remove the CR before the = else it won't compile!
+const pos : array<vec2<f32>, 4>
+= array<vec2<f32>, 4>(
+    vec2<f32>(-1.0, 1.0),
+    vec2<f32>(1.0, 1.0),
+    vec2<f32>(-1.0, -1.0),
+    vec2<f32>(1.0, -1.0)
+);
 
-const vec2 pos[4] = vec2[4](vec2(-1.0f, 1.0f), vec2(1.0f, 1.0f), vec2(-1.0f, -1.0f), vec2(1.0f, -1.0f));
+[[builtin(position)]] var<out> position : vec4<f32>;
+[[builtin(vertex_idx)]] var<in> vertexIndex : i32;
 
-void main() {
-    gl_Position = vec4(pos[gl_VertexIndex], 0.0, 1.0);
+[[stage(vertex)]]
+fn main() -> void {
+    position = vec4<f32>(pos[vertexIndex], 0.0, 1.0);
+    return;
 }