1 /*
2  * Copyright 2019 Google Inc.
3  *
4  * Use of this source code is governed by a BSD-style license that can be
5  * found in the LICENSE file.
6  */
7 
8 #ifndef GrDawnProgramBuilder_DEFINED
9 #define GrDawnProgramBuilder_DEFINED
10 
11 #include "src/gpu/GrSPIRVUniformHandler.h"
12 #include "src/gpu/GrSPIRVVaryingHandler.h"
13 #include "src/gpu/dawn/GrDawnProgramDataManager.h"
14 #include "src/sksl/SkSLCompiler.h"
15 #include "dawn/webgpu_cpp.h"
16 #include "src/gpu/glsl/GrGLSLProgramBuilder.h"
17 
18 #include <vector>
19 
20 class GrPipeline;
21 
22 struct GrDawnProgram : public SkRefCnt {
23     struct RenderTargetState {
24         SkISize         fRenderTargetSize;
25         GrSurfaceOrigin fRenderTargetOrigin;
26 
RenderTargetStateGrDawnProgram::RenderTargetState27         RenderTargetState() { this->invalidate(); }
invalidateGrDawnProgram::RenderTargetState28         void invalidate() {
29             fRenderTargetSize.fWidth = -1;
30             fRenderTargetSize.fHeight = -1;
31             fRenderTargetOrigin = (GrSurfaceOrigin) -1;
32         }
33 
34         /**
35          * Gets a float4 that adjusts the position from Skia device coords to GL's normalized device
36          * coords. Assuming the transformed position, pos, is a homogeneous float3, the vec, v, is
37          * applied as such:
38          * pos.x = dot(v.xy, pos.xz)
39          * pos.y = dot(v.zw, pos.yz)
40          */
getRTAdjustmentVecGrDawnProgram::RenderTargetState41         void getRTAdjustmentVec(float* destVec) {
42             destVec[0] = 2.f / fRenderTargetSize.fWidth;
43             destVec[1] = -1.f;
44             if (kTopLeft_GrSurfaceOrigin == fRenderTargetOrigin) {
45                 destVec[2] = -2.f / fRenderTargetSize.fHeight;
46                 destVec[3] = 1.f;
47             } else {
48                 destVec[2] = 2.f / fRenderTargetSize.fHeight;
49                 destVec[3] = -1.f;
50             }
51         }
52     };
53     typedef GrGLSLBuiltinUniformHandles BuiltinUniformHandles;
GrDawnProgramGrDawnProgram54     GrDawnProgram(const GrSPIRVUniformHandler::UniformInfoArray& uniforms,
55                   uint32_t uniformBufferSize)
56       : fDataManager(uniforms, uniformBufferSize) {
57     }
58     std::unique_ptr<GrGLSLGeometryProcessor> fGeometryProcessor;
59     std::unique_ptr<GrGLSLXferProcessor> fXferProcessor;
60     std::vector<std::unique_ptr<GrGLSLFragmentProcessor>> fFPImpls;
61     std::vector<wgpu::BindGroupLayout> fBindGroupLayouts;
62     wgpu::RenderPipeline fRenderPipeline;
63     GrDawnProgramDataManager fDataManager;
64     RenderTargetState fRenderTargetState;
65     BuiltinUniformHandles fBuiltinUniformHandles;
66 
67     void setRenderTargetState(const GrRenderTarget*, GrSurfaceOrigin);
68     wgpu::BindGroup setUniformData(GrDawnGpu*, const GrRenderTarget*, const GrProgramInfo&);
69     wgpu::BindGroup setTextures(GrDawnGpu*,
70                                 const GrGeometryProcessor&,
71                                 const GrPipeline&,
72                                 const GrSurfaceProxy* const geomProcTextures[]);
73 };
74 
75 class GrDawnProgramBuilder : public GrGLSLProgramBuilder {
76 public:
77     static sk_sp<GrDawnProgram> Build(GrDawnGpu*,
78                                       GrRenderTarget*,
79                                       const GrProgramInfo&,
80                                       wgpu::TextureFormat colorFormat,
81                                       bool hasDepthStencil,
82                                       wgpu::TextureFormat depthStencilFormat,
83                                       GrProgramDesc*);
84     const GrCaps* caps() const override;
uniformHandler()85     GrGLSLUniformHandler* uniformHandler() override { return &fUniformHandler; }
uniformHandler()86     const GrGLSLUniformHandler* uniformHandler() const override { return &fUniformHandler; }
varyingHandler()87     GrGLSLVaryingHandler* varyingHandler() override { return &fVaryingHandler; }
88 
gpu()89     GrDawnGpu* gpu() const { return fGpu; }
90 
91     SkSL::Compiler* shaderCompiler() const override;
92 
93 private:
94     GrDawnProgramBuilder(GrDawnGpu*,
95                          const GrProgramInfo&,
96                          GrProgramDesc*);
97     wgpu::ShaderModule createShaderModule(const GrGLSLShaderBuilder&, SkSL::ProgramKind,
98                                           bool flipY, SkSL::Program::Inputs* inputs);
99     GrDawnGpu*             fGpu;
100     GrSPIRVVaryingHandler   fVaryingHandler;
101     GrSPIRVUniformHandler   fUniformHandler;
102 
103     using INHERITED = GrGLSLProgramBuilder;
104 };
105 #endif
106