1 /*
2 * Copyright (c) 2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #ifndef API_RENDER_DEVICE_ISHADER_MANAGER_H
17 #define API_RENDER_DEVICE_ISHADER_MANAGER_H
18
19 #include <base/containers/string_view.h>
20 #include <base/containers/vector.h>
21 #include <core/json/json.h>
22 #include <core/namespace.h>
23 #include <render/device/intf_shader_pipeline_binder.h>
24 #include <render/device/pipeline_layout_desc.h>
25 #include <render/device/pipeline_state_desc.h>
26 #include <render/namespace.h>
27 #include <render/resource_handle.h>
28
RENDER_BEGIN_NAMESPACE()29 RENDER_BEGIN_NAMESPACE()
30
31 /** \addtogroup group_ishadermanager
32 * @{
33 */
34 /** Shader manager interface.
35 * Not internally synchronized.
36 *
37 * Shaders are automatically loaded from json files with LoadShaderFiles(prefix).
38 * One can explicitly (Re)LoadShaderFile(...) but LoadShaderFiles would be preferred method.
39 * Beware that shader manager is not internally synchronized. Create methods should only be called before
40 * calling RenderFrame (and not in render nodes).
41 *
42 * Loading shader data:
43 * By default shader data is loaded from default paths:
44 * Shaders "<prefix>shaders://"
45 * Shader states ""<prefix>shaderstates://";
46 * Vertex input declarations "<prefix>vertexinputdeclarations://"
47 * Pipeline layouts "<prefix>pipelinelayouts://"
48 *
49 * Naming of shader resources
50 * Shaders: .shader
51 * Shader states (graphics state): .shadergs
52 * Vertex input declaration: .shadervid
53 * Pipeline layout: .shaderpl
54 *
55 * Calling LoadShaderFiles effectively does the previous.
56 * In application one needs to load all plugin shader assets.
57 * This enables faster loading times when one can control if and when default shader files are needed.
58 *
59 * LoadShaderFile(uri)
60 * Loads a specified shader data file. Identifies the type and loads it's data.
61 *
62 * Shaders are created with default name which is the path.
63 *
64 * Methods that have a name as a parameter print error message if resource not found.
65 * Methods that have a handle as a parameter return invalid handles or default data if not found.
66 *
67 * Shader language is (vulkan):
68 * #version 460 core
69 * #extension GL_ARB_separate_shader_objects : enable
70 * #extension GL_ARB_shading_language_420pack : enable
71 *
72 * Default specilization that can be used (handled automatically):
73 * layout(constant_id = 0) const uint CORE_BACKEND_TYPE = 0;
74 * Vulkan: CORE_BACKEND_TYPE = 0
75 * GL and GLES: CORE_BACKEND_TYPE = 1
76 *
77 * NOTE: Do not set this automatically.
78 *
79 * Specialization constant ids need to be smaller than 256.
80 * Engine uses special low level specializations with ids 256+.
81 * Prefer using every id from zero onwards.
82
83 */
84 class IShaderManager {
85 public:
86 struct ShaderModulePath {
87 /* Shader module path */
88 BASE_NS::string_view path;
89 /* Shader stage flags */
90 ShaderStageFlags shaderStageFlags { 0u };
91 };
92 struct ComputeShaderCreateInfo {
93 /* Path, used as a name */
94 BASE_NS::string_view path;
95 /* Shader modules for this shader */
96 BASE_NS::array_view<const ShaderModulePath> shaderPaths;
97
98 /* Optional pipeline layout handle */
99 RenderHandle pipelineLayout;
100 /* Optional render slot mask */
101 uint32_t renderSlotId { ~0u };
102 /* Optional category id */
103 uint32_t categoryId { ~0u };
104 };
105 struct ShaderCreateInfo {
106 /* Path, used as a name */
107 BASE_NS::string_view path;
108 /* Shader modules for this shader */
109 BASE_NS::array_view<const ShaderModulePath> shaderPaths;
110
111 /* Optional default graphics state handle for the shader */
112 RenderHandle graphicsState;
113 /* Optional pipeline layout handle */
114 RenderHandle pipelineLayout;
115 /* Optional vertex input declaration handle */
116 RenderHandle vertexInputDeclaration;
117 /* Optional render slot mask */
118 uint32_t renderSlotId { ~0u };
119 /* Optional category id */
120 uint32_t categoryId { ~0u };
121 };
122 struct PipelineLayoutCreateInfo {
123 /* Path, used as a name */
124 BASE_NS::string_view path;
125 /* Reference to pipeline layout */
126 const PipelineLayout& pipelineLayout;
127 /* Render slot id */
128 uint32_t renderSlotId { ~0U };
129 /* Render slot id */
130 bool renderSlotDefault { false };
131 };
132 struct GraphicsStateCreateInfo {
133 /* Path, used as a name */
134 BASE_NS::string_view path;
135 /* Reference to graphics state */
136 const GraphicsState& graphicsState;
137 };
138 struct GraphicsStateVariantCreateInfo {
139 /* Render slot for the variant */
140 BASE_NS::string_view renderSlot;
141 /* Variant name for the graphics state */
142 BASE_NS::string_view variant;
143 /* Base graphics state name */
144 BASE_NS::string_view baseShaderState;
145 /* Base graphics state variant name */
146 BASE_NS::string_view baseVariant;
147 /* Forced graphics state flags */
148 GraphicsStateFlags stateFlags { 0u };
149 /* Render slot default */
150 bool renderSlotDefault { false };
151 };
152 struct VertexInputDeclarationCreateInfo {
153 /* Path, used as a name */
154 BASE_NS::string_view path;
155 /* Reference to vertex input declaration view */
156 const VertexInputDeclarationView vertexInputDeclarationView;
157 /* Render slot id */
158 uint32_t renderSlotId { ~0U };
159 /* Render slot default */
160 bool renderSlotDefault { false };
161 };
162 /* Id Description which can be fetched for handle */
163 struct IdDesc {
164 /* Unique path */
165 BASE_NS::string path;
166 /* Variant name */
167 BASE_NS::string variant;
168 /* Display name */
169 BASE_NS::string displayName;
170 /* Category name */
171 BASE_NS::string category;
172 /* Render slot id */
173 BASE_NS::string renderSlot;
174 /* Frame index when the shader was loaded. (Can be used as a "timestamp" for caching) */
175 uint64_t frameIndex { 0 };
176 };
177 /* Render slot data. Used for default render slot data handles */
178 struct RenderSlotData {
179 /** Render slot ID */
180 uint32_t renderSlotId { ~0u };
181 /** Shader handle */
182 RENDER_NS::RenderHandleReference shader;
183 /** Graphics state handle */
184 RENDER_NS::RenderHandleReference graphicsState;
185 /** Pipeline layout handle */
186 RENDER_NS::RenderHandleReference pipelineLayout;
187 /** Vertex input declaration */
188 RENDER_NS::RenderHandleReference vertexInputDeclaration;
189 };
190
191 /* Shader files loading */
192 struct ShaderFilePathDesc {
193 /* Shaders path */
194 BASE_NS::string_view shaderPath;
195 /* Shader states path */
196 BASE_NS::string_view shaderStatePath;
197 /* Pipeline layouts path */
198 BASE_NS::string_view pipelineLayoutPath;
199 /* Vertex input declarations path */
200 BASE_NS::string_view vertexInputDeclarationPath;
201 };
202
203 struct ShaderStateLoaderVariantData {
204 BASE_NS::string renderSlot;
205 BASE_NS::string variantName;
206
207 BASE_NS::string baseShaderState;
208 BASE_NS::string baseVariantName;
209
210 GraphicsStateFlags stateFlags { 0U };
211 bool renderSlotDefaultState { false };
212 };
213
214 /** Describes a single shader variant. */
215 struct ShaderVariant {
216 bool renderSlotDefaultShader { false };
217 BASE_NS::string variantName;
218 BASE_NS::string displayName;
219
220 struct ShaderSpvInfo {
221 BASE_NS::string shaderSpvPath;
222 ShaderStageFlags shaderType;
223 };
224 BASE_NS::vector<ShaderSpvInfo> shaders;
225
226 BASE_NS::string vertexInputDeclaration;
227 BASE_NS::string pipelineLayout;
228 GraphicsState graphicsState;
229
230 BASE_NS::string renderSlot;
231 BASE_NS::string shaderFileStr;
232 BASE_NS::string materialMetadata;
233
234 GraphicsStateFlags stateFlags { 0U };
235
236 /** Own base shader uri */
237 BASE_NS::string ownBaseShader;
238 /** Separate base shader with other shader uri */
239 BASE_NS::string addBaseShader;
240 };
241
242 struct ShaderOutWriteResult {
243 /* error message, if any exists */
244 BASE_NS::string error;
245 bool success { false };
246 /* the shader as json string */
247 BASE_NS::string result;
248 };
249 struct ShaderGraphicsStateSaveInfo {
250 /* states, outputs one file with stateName as file name */
251 BASE_NS::string stateName;
252 /* states */
253 BASE_NS::vector<GraphicsState> states;
254 /* state variants */
255 BASE_NS::vector<ShaderStateLoaderVariantData> stateVariants;
256 };
257
258 struct ShaderVertexInputDeclarationsSaveInfo {
259 /* vertex input declarations, outputs vid file */
260 BASE_NS::string vidName;
261 /* vertex input declaration view */
262 VertexInputDeclarationView vid;
263 };
264
265 struct ShaderPipelineLayoutSaveInfo {
266 /* pipeline layouts, outputs single layout file */
267 BASE_NS::string layoutName;
268 /* pipeline layout */
269 PipelineLayout layout;
270 };
271
272 struct ShaderVariantsSaveInfo {
273 /* shader variants, outputs one file with shaderName as file name */
274 BASE_NS::string shaderName;
275 /* category if any */
276 BASE_NS::string category;
277 /* shaders */
278 BASE_NS::vector<ShaderVariant> shaders;
279 };
280
281 /** Shader data for typically needed shader data in render nodes
282 */
283 struct ShaderData {
284 /** Shader handle */
285 RenderHandle shader;
286 /** Pipeline layout handle */
287 RenderHandle pipelineLayout;
288 /** Pipeline layout data */
289 PipelineLayout pipelineLayoutData;
290 };
291 /** Graphics shader data for typically needed shader data in render nodes
292 */
293 struct GraphicsShaderData {
294 /** Shader handle */
295 RenderHandle shader;
296 /** Graphics state handle */
297 RenderHandle graphicsState;
298 /** Pipeline layout handle */
299 RenderHandle pipelineLayout;
300 /** vertex input layout handle */
301 RenderHandle vertexInputDeclaration;
302 /** Pipeline layout data */
303 PipelineLayout pipelineLayoutData;
304 };
305
306 /** Get render handle reference of raw handle.
307 * @param handle Raw render handle
308 * @return Returns A render handle reference for the handle.
309 */
310 virtual RenderHandleReference Get(const RenderHandle& handle) const = 0;
311
312 /** Create a compute shader. Prefer loading shaders from json files.
313 * @param createInfo A create info with valid parameters.
314 * @return Returns compute shader gpu resource handle.
315 */
316 virtual RenderHandleReference CreateComputeShader(const ComputeShaderCreateInfo& createInfo) = 0;
317
318 /** Create a compute shader with a variant name. Prefer loading shaders from json files.
319 * @param createInfo A create info with valid parameters.
320 * @param additionalBaseShaderPath An additional base shader path/name from where the variant will be found as
321 * well.
322 * @param variantName A variant name.
323 * @return Returns compute shader gpu resource handle.
324 */
325 virtual RenderHandleReference CreateComputeShader(const ComputeShaderCreateInfo& createInfo,
326 const BASE_NS::string_view additionalBaseShaderPath, const BASE_NS::string_view variantName) = 0;
327
328 /** Create a shader. Prefer loading shaders from json files.
329 * @param createInfo A create info with valid parameters.
330 * @return Returns shader gpu resource handle.
331 */
332 virtual RenderHandleReference CreateShader(const ShaderCreateInfo& createInfo) = 0;
333
334 /** Create a shader. Prefer loading shaders from json files.
335 * @param createInfo A create info with valid parameters.
336 * @param additionalBaseShaderPath An additional base shader path/name from where the variant will be found as
337 * well.
338 * @param variantName A variant name.
339 * @return Returns shader gpu resource handle.
340 */
341 virtual RenderHandleReference CreateShader(const ShaderCreateInfo& createInfo,
342 const BASE_NS::string_view additionalBaseShaderPath, const BASE_NS::string_view variantName) = 0;
343
344 /** Create a pipeline layout. Prefer loading pipeline layouts from json files.
345 * @param createInfo A pipeline layout create info.
346 * @return Returns pipeline layout render handle.
347 */
348 virtual RenderHandleReference CreatePipelineLayout(const PipelineLayoutCreateInfo& createInfo) = 0;
349
350 /** Create a vertex input declaration. Prefer laoding vertex input declaration from json files.
351 * @param createInfo A vertex input declaration create info.
352 * @return Returns vertex input declaration handle.
353 */
354 virtual RenderHandleReference CreateVertexInputDeclaration(const VertexInputDeclarationCreateInfo& createInfo) = 0;
355
356 /** Create a graphics state. Prefer loading graphics states from json files.
357 * @param name Unique name of the graphics state. (Optional name, can be empty string view)
358 * @param createInfo A graphics state create info.
359 * @return Returns graphics state render handle.
360 */
361 virtual RenderHandleReference CreateGraphicsState(const GraphicsStateCreateInfo& createInfo) = 0;
362
363 /** Create a graphics state with additional variant info. Prefer loading graphics states from json files.
364 * @param createInfo A graphics state create info.
365 * @param variantCreateInfo A create info for shader graphics state variant.
366 * @return Returns graphics state render handle.
367 */
368 virtual RenderHandleReference CreateGraphicsState(
369 const GraphicsStateCreateInfo& createInfo, const GraphicsStateVariantCreateInfo& variantCreateInfo) = 0;
370
371 /** Create a render slot id for render slot name. If render slot already created for the name the slot id is
372 * returned.
373 * @param name Unique name of the render slot id.
374 * @return Returns render slot id for the name.
375 */
376 virtual uint32_t CreateRenderSlotId(const BASE_NS::string_view name) = 0;
377
378 /** Set render slot default data.
379 * @param renderSlotData Render slot data.
380 */
381 virtual void SetRenderSlotData(const RenderSlotData& renderSlotData) = 0;
382
383 /** Get shader handle.
384 * @param path Path/Name of the shader.
385 * @return Returns shader handle.
386 */
387 virtual RenderHandleReference GetShaderHandle(const BASE_NS::string_view path) const = 0;
388
389 /** Get shader variant handle. One can fetch and explicit handle to variant.
390 * @param path Path/Name of the base shader.
391 * @param variantName Name of variant.
392 * @return Returns shader gpu resource handle.
393 */
394 virtual RenderHandleReference GetShaderHandle(
395 const BASE_NS::string_view path, const BASE_NS::string_view variantName) const = 0;
396
397 /** Get shader handle. Tries to find a shader variant for provided render slot id.
398 * @param handle Shader handle.
399 * @param renderSlotId Render slot id.
400 * @return Returns shader handle for given render slot id.
401 */
402 virtual RenderHandleReference GetShaderHandle(
403 const RenderHandleReference& handle, const uint32_t renderSlotId) const = 0;
404
405 /** Get shaders
406 * @param renderSlotId Id of render slot
407 * @return Returns shader handles for given render slot id.
408 */
409 virtual BASE_NS::vector<RenderHandleReference> GetShaders(const uint32_t renderSlotId) const = 0;
410
411 /** Get graphics state based on path name
412 * @param path Path/Name of the graphics state
413 */
414 virtual RenderHandleReference GetGraphicsStateHandle(const BASE_NS::string_view path) const = 0;
415
416 /** Get graphics state based on name and variant name
417 * @param path Path/Name of the graphics state
418 * @param name Variant name of the graphics state
419 */
420 virtual RenderHandleReference GetGraphicsStateHandle(
421 const BASE_NS::string_view path, const BASE_NS::string_view variantName) const = 0;
422
423 /** Get graphics state handle. Tries to find a graphics state variant for provided render slot id.
424 * Returns the given handle if it's own slot matches.
425 * @param handle Graphics state handle.
426 * @param renderSlotId Render slot id.
427 * @return Returns shader handle for given render slot id.
428 */
429 virtual RenderHandleReference GetGraphicsStateHandle(
430 const RenderHandleReference& handle, const uint32_t renderSlotId) const = 0;
431
432 /** Get graphics state based on graphics state hash.
433 * @param hash A hash created with HashGraphicsState().
434 * @return Graphics state handle.
435 */
436 virtual RenderHandleReference GetGraphicsStateHandleByHash(const uint64_t hash) const = 0;
437
438 /** Get graphics state handle based on shader handle. The default graphics in shader json.
439 * @param handle Valid shader handle.
440 * @return Graphics state handle.
441 */
442 virtual RenderHandleReference GetGraphicsStateHandleByShaderHandle(const RenderHandleReference& handle) const = 0;
443
444 /** Get graphics state.
445 * @param handle Graphics state render handle.
446 * @return Graphics state for the handle.
447 */
448 virtual GraphicsState GetGraphicsState(const RenderHandleReference& handle) const = 0;
449
450 /** Get graphics states.
451 * @param renderSlotId Id of render slot.
452 * @return Returns all graphics state handles for the render slot id.
453 */
454 virtual BASE_NS::vector<RenderHandleReference> GetGraphicsStates(const uint32_t renderSlotId) const = 0;
455
456 /** Get render slot ID
457 * @param renderSlot Name of render slot
458 * @return render slot id if found (~0u invalid)
459 */
460 virtual uint32_t GetRenderSlotId(const BASE_NS::string_view renderSlot) const = 0;
461
462 /** Get render slot ID.
463 * @param handle Handle of shader or graphics state.
464 * @return render slot id if found (~0u invalid)
465 */
466 virtual uint32_t GetRenderSlotId(const RenderHandleReference& handle) const = 0;
467
468 /** Get render slot data. Get default data of render slot.
469 * @param renderSlotId Render slot id.
470 * @return render slot data.
471 */
472 virtual RenderSlotData GetRenderSlotData(const uint32_t renderSlotId) const = 0;
473
474 /** Get render slot name.
475 * @param renderSlotId Render slot id.
476 * @return render slot name.
477 */
478 virtual BASE_NS::string GetRenderSlotName(const uint32_t renderSlotId) const = 0;
479
480 /** Get vertex input declaration handle by shader handle.
481 * @param handle A handle of the shader which vertex input declaration data handle will be returned.
482 * @return Returns a data handle for vertex input declaration.
483 */
484 virtual RenderHandleReference GetVertexInputDeclarationHandleByShaderHandle(
485 const RenderHandleReference& handle) const = 0;
486
487 /** Get vertex input declaration handle by vertex input declaration name.
488 * @param path Path/Name of the vertex input declaration given in data.
489 * @return Returns a data handle for vertex input declaration.
490 */
491 virtual RenderHandleReference GetVertexInputDeclarationHandle(const BASE_NS::string_view path) const = 0;
492
493 /** Get vertex input declaration view by vertex input declaration data handle.
494 * The return value should not be hold into as it contains array_views to data which my change.
495 * @param handle A handle to the vertex input declaration data.
496 * @return Returns a view to vertex input declaration data.
497 */
498 virtual VertexInputDeclarationView GetVertexInputDeclarationView(const RenderHandleReference& handle) const = 0;
499
500 /** Get pipeline layout handle by shader handle.
501 * @param handle A handle of the shader which pipeline layout data handle will be returned.
502 * @return Returns a handle to pipeline layout.
503 */
504 virtual RenderHandleReference GetPipelineLayoutHandleByShaderHandle(const RenderHandleReference& handle) const = 0;
505
506 /** Get pipeline layout by shader or compute shader pipeline layout handle.
507 * @param handle A handle to pipeline layout.
508 * @return Returns a const reference to pipeline layout.
509 */
510 virtual PipelineLayout GetPipelineLayout(const RenderHandleReference& handle) const = 0;
511
512 /** Get pipeline layout handle by pipeline layout name.
513 * @param path Path/Name of the pipeline layout.
514 * @return Returns a handle to pipeline layout.
515 */
516 virtual RenderHandleReference GetPipelineLayoutHandle(const BASE_NS::string_view path) const = 0;
517
518 /** Get pipeline layout handle for reflected shader data.
519 * @param handle A handle to a valid shader or compute shader.
520 * @return Returns a handle to pipeline layout.
521 */
522 virtual RenderHandleReference GetReflectionPipelineLayoutHandle(const RenderHandleReference& handle) const = 0;
523
524 /** Get pipeline layout reflected from the shader or compute shader pipeline layout handle.
525 * @param handle A handle to a valid shader or compute shader.
526 * @return Returns a const reference to pipeline layout.
527 */
528 virtual PipelineLayout GetReflectionPipelineLayout(const RenderHandleReference& handle) const = 0;
529
530 /** Get specialization reflected from the given shader.
531 * @param handle A handle to a valid shader or compute shader.
532 * @return Returns a view to shader specialization. The struct should not be holded unto.
533 */
534 virtual ShaderSpecializationConstantView GetReflectionSpecialization(const RenderHandleReference& handle) const = 0;
535
536 /** Get vertex input declaration reflected from the shader. (Zero values if shader does not have one)
537 * @param handle A handle to a valid shader.
538 * @return Returns a view to vertex input declaration view. The struct should not be holded unto.
539 */
540 virtual VertexInputDeclarationView GetReflectionVertexInputDeclaration(
541 const RenderHandleReference& handle) const = 0;
542
543 /** Get thread group size of a given shader. (Zero values if shader does not have thread group)
544 * @param handle A handle to a valid compute shader.
545 * @return Returns a shader thread group size.
546 */
547 virtual ShaderThreadGroup GetReflectionThreadGroupSize(const RenderHandleReference& handle) const = 0;
548
549 /** Hash graphics state.
550 * @return Returns a hash for shader related graphics state.
551 */
552 virtual uint64_t HashGraphicsState(const GraphicsState& graphicsState) const = 0;
553
554 /** Checks if resource is a compute shader */
555 virtual bool IsComputeShader(const RenderHandleReference& handle) const = 0;
556 /** Checks if resource is a shader */
557 virtual bool IsShader(const RenderHandleReference& handle) const = 0;
558
559 /** Load shader files.
560 * Looks for json files under paths for shaders, shader states, vertex input declarations, and pipeline
561 * layouts. Creates resources based on loaded data.
562 * NOTE: does not re-create shader modules if the module with the same spv has already been done.
563 * @param desc Paths to shader files
564 */
565 virtual void LoadShaderFiles(const ShaderFilePathDesc& desc) = 0;
566
567 /** Load shader file and create resources.
568 * NOTE: beware that shader json files can refer to names (not uris) of other shader resources (like pipeline
569 * layout) and they need to be loaded before hand. Prefer using LoadShaderFiles() or automatic loading of shaders.
570 * @param uri A uri to a valid shader data json file.
571 */
572 virtual void LoadShaderFile(const BASE_NS::string_view uri) = 0;
573
574 /** Save graphics state
575 * @param saveInfo Struct containing all the required info to build json
576 * @return Returrn ShaderOutWriteResult which contains result
577 */
578 virtual ShaderOutWriteResult SaveShaderGraphicsState(const ShaderGraphicsStateSaveInfo& saveInfo) = 0;
579
580 /** Save vertex input declaration
581 * @param saveInfo Struct containing all the required info to build json
582 * @return Returrn ShaderOutWriteResult which contains result
583 */
584 virtual ShaderOutWriteResult SaveShaderVertexInputDeclaration(
585 const ShaderVertexInputDeclarationsSaveInfo& saveInfo) = 0;
586
587 /** Save pipeline layout
588 * @param saveInfo Struct containing all the required info to build json
589 * @return Returrn ShaderOutWriteResult which contains result
590 */
591 virtual ShaderOutWriteResult SaveShaderPipelineLayout(const ShaderPipelineLayoutSaveInfo& saveInfo) = 0;
592
593 /** Save pipeline layout
594 * @param saveInfo Struct containing all the required info to build json
595 * @return Returrn ShaderOutWriteResult which contains result
596 */
597 virtual ShaderOutWriteResult SaveShaderVariants(const ShaderVariantsSaveInfo& saveInfo) = 0;
598
599 /** Unload shader files.
600 * Looks for json files under paths for shaders, shader states, vertex input declarations, and pipeline
601 * layouts. Unloads/Destroys the shaders.
602 * @param desc Paths to shader files
603 */
604 virtual void UnloadShaderFiles(const ShaderFilePathDesc& desc) = 0;
605
606 /** Get json string.
607 * @param handle A handle to a valid shader.
608 * @return Returns string view of loaded shader file.
609 */
610 virtual const BASE_NS::string_view GetShaderFile(const RenderHandleReference& handle) const = 0;
611
612 /** Get material metadata for the shader.
613 * @param handle A handle to a valid shader.
614 * @return Returns available metadata as JSON.
615 */
616 virtual const CORE_NS::json::value* GetMaterialMetadata(const RenderHandleReference& handle) const = 0;
617
618 /** Destroy shader data handle (shaders, pipeline layouts, shader states, vertex input declarations).
619 * @param handle A handle to a valid shader (pl, state, vid).
620 */
621 virtual void Destroy(const RenderHandleReference& handle) = 0;
622
623 /** Get shaders based on render handle (pipeline layout, vertex input declaration, graphics state).
624 * Based on ShaderStageFlags searches for valid shaders.
625 * Not fast operation and should not be queried every frame.
626 * @param handle A handle to a valid render handle (pl, vid).
627 * @param shaderStateFlags Flags for specific shaders.
628 * @return Returns All shaders that use the specific handle.
629 */
630 virtual BASE_NS::vector<RenderHandleReference> GetShaders(
631 const RenderHandleReference& handle, const ShaderStageFlags shaderStageFlags) const = 0;
632
633 /** Get IdDesc for a RenderHandle.
634 * @param handle A handle to a valid render handle.
635 * @return Returns IdDesc for a given handle.
636 */
637 virtual IdDesc GetIdDesc(const RenderHandleReference& handle) const = 0;
638
639 /** Get frame update index for a RenderHandle.
640 * @param handle A handle to a valid render handle.
641 * @return Returns frame index.
642 */
643 virtual uint64_t GetFrameIndex(const RenderHandleReference& handle) const = 0;
644
645 /** Reload shader file and create resources.
646 * NOTE: Force re-creates shader modules from spv -files in shader json.
647 * NOTE: Do not call on perf-critical path.
648 * NOTE: beware that shader json files can refer to names (not uris) of other shader resources (like pipeline
649 * layout) and they need to be loaded before hand. Prefer using LoadShaderFiles() or automatic loading of shaders.
650 * @param uri A uri to a valid shader data json file.
651 */
652 virtual void ReloadShaderFile(const BASE_NS::string_view uri) = 0;
653
654 /** Get all shaders.
655 * @return vector of all shaders.
656 */
657 virtual BASE_NS::vector<RenderHandleReference> GetShaders() const = 0;
658
659 /** Get all graphics states.
660 * @return vector of all graphics states.
661 */
662 virtual BASE_NS::vector<RenderHandleReference> GetGraphicsStates() const = 0;
663
664 /** Get all pipeline layouts.
665 * @return vector of all pipeline layouts.
666 */
667 virtual BASE_NS::vector<RenderHandleReference> GetPipelineLayouts() const = 0;
668
669 /** Get all vertex input declarations.
670 * @return vector of all vertex input declarations.
671 */
672 virtual BASE_NS::vector<RenderHandleReference> GetVertexInputDeclarations() const = 0;
673
674 /** Create shader pipeline binder.
675 * @param handle Shader handle.
676 * @return Returns shader pipeline binder.
677 */
678 virtual IShaderPipelineBinder::Ptr CreateShaderPipelineBinder(const RenderHandleReference& handle) const = 0;
679
680 /** Create shader pipeline binder.
681 * @param handle Shader handle.
682 * @param plHandle Enforced pipeline layout handle.
683 * @return Returns shader pipeline binder.
684 */
685 virtual IShaderPipelineBinder::Ptr CreateShaderPipelineBinder(
686 const RenderHandleReference& handle, const RenderHandleReference& plHandle) const = 0;
687
688 /** Create shader pipeline binder.
689 * @param handle Shader handle.
690 * @param pipelineLayout Enforced pipeline layout.
691 * @return Returns shader pipeline binder.
692 */
693 virtual IShaderPipelineBinder::Ptr CreateShaderPipelineBinder(
694 const RenderHandleReference& handle, const PipelineLayout& pipelineLayout) const = 0;
695
696 /** Compatibility flags */
697 enum CompatibilityFlagBits {
698 /** Is compatible */
699 COMPATIBLE_BIT = 0x00000001,
700 /** Exact match */
701 EXACT_BIT = 0x00000002,
702 };
703 /** Container for compatibility flag flag bits */
704 using CompatibilityFlags = uint32_t;
705
706 /** Check compatibility of render resources.
707 * @param lhs The base for compatibility check.
708 * @param rhs The one which will be compared against the base.
709 * @return Returns compatibility flags.
710 */
711 virtual CompatibilityFlags GetCompatibilityFlags(
712 const RenderHandleReference& lhs, const RenderHandleReference& rhs) const = 0;
713
714 /** Check forced graphics states. Can be set for render slot variants.
715 * @param handle Graphics state or shader handle. Faster to check with graphics state handle.
716 * @return Returns forced graphics state flags.
717 */
718 virtual GraphicsStateFlags GetForcedGraphicsStateFlags(const RenderHandleReference& handle) const = 0;
719
720 /** Check forced graphics states. Can be set for render slot variants.
721 * @param renderSlotId Render slot id. Find the base graphics state and checks the forced flags
722 * @return Returns forced graphics state flags.
723 */
724 virtual GraphicsStateFlags GetForcedGraphicsStateFlags(const uint32_t renderSlotId) const = 0;
725
726 protected:
727 IShaderManager() = default;
728 virtual ~IShaderManager() = default;
729
730 IShaderManager(const IShaderManager&) = delete;
731 IShaderManager& operator=(const IShaderManager&) = delete;
732 IShaderManager(IShaderManager&&) = delete;
733 IShaderManager& operator=(IShaderManager&&) = delete;
734 };
735
736 /** IRenderNodeShaderManager.
737 * Shader manager interface to be used inside render nodes.
738 *
739 * Some methods use faster path (no locking).
740 * Some methods are not available like creation methods
741 */
742 class IRenderNodeShaderManager {
743 public:
744 /** Get shader handle (any type).
745 * @param path Path/Name of the shader.
746 * @return Returns shader handle.
747 */
748 virtual RenderHandle GetShaderHandle(const BASE_NS::string_view path) const = 0;
749
750 /** Get shader handle.
751 * @param path Path/Name of the shader.
752 * @param variantName Name of the variant.
753 * @return Returns shader gpu resource handle.
754 */
755 virtual RenderHandle GetShaderHandle(
756 const BASE_NS::string_view path, const BASE_NS::string_view variantName) const = 0;
757
758 /** Get shader handle. Tries to find variant of shader with given render slot id.
759 * @param handle Shader handle.
760 * @param renderSlotId Render slot id.
761 * @return Returns shader gpu resource handle for given slot.
762 */
763 virtual RenderHandle GetShaderHandle(const RenderHandle& handle, const uint32_t renderSlotId) const = 0;
764
765 /** Get shaders
766 * @param renderSlotId Id of render slot
767 */
768 virtual BASE_NS::vector<RenderHandle> GetShaders(const uint32_t renderSlotId) const = 0;
769
770 /** Get graphics state based on name
771 * @param path Path/Name of the graphics state
772 */
773 virtual RenderHandle GetGraphicsStateHandle(const BASE_NS::string_view path) const = 0;
774
775 /** Get graphics state based on name
776 * @param path Path/Name of the graphics state
777 * @param variantName Variant name of the graphics state
778 */
779 virtual RenderHandle GetGraphicsStateHandle(
780 const BASE_NS::string_view path, const BASE_NS::string_view variantName) const = 0;
781
782 /** Get graphics state handle. Tries to find variant of graphics state with given render slot id.
783 * Returns the given handle if its render slot id matches.
784 * @param handle Graphics state handle.
785 * @param renderSlotId Render slot id.
786 * @return Returns shader graphics state handle for given slot.
787 */
788 virtual RenderHandle GetGraphicsStateHandle(const RenderHandle& handle, const uint32_t renderSlotId) const = 0;
789
790 /** Get graphics state based on graphics state hash
791 * @param hash A hash created with HashGraphicsState()
792 */
793 virtual RenderHandle GetGraphicsStateHandleByHash(const uint64_t hash) const = 0;
794
795 /** Get graphics state handle based on shader handle
796 * @param handle Valid shader handle.
797 */
798 virtual RenderHandle GetGraphicsStateHandleByShaderHandle(const RenderHandle& handle) const = 0;
799
800 /** Get graphics state
801 * @param handle Graphics state render handle
802 */
803 virtual const GraphicsState& GetGraphicsState(const RenderHandle& handle) const = 0;
804
805 /** Get render slot ID
806 * @param renderSlot Name of render slot
807 * @return render slot id if found (~0u invalid)
808 */
809 virtual uint32_t GetRenderSlotId(const BASE_NS::string_view renderSlot) const = 0;
810
811 /** Get render slot ID
812 * @param handle Handle to resource
813 * @return render slot mask if found (0 invalid)
814 */
815 virtual uint32_t GetRenderSlotId(const RenderHandle& handle) const = 0;
816
817 /** Get render slot data. Get default data of render slot.
818 * @param renderSlotId Render slot id.
819 * @return render slot data.
820 */
821 virtual IShaderManager::RenderSlotData GetRenderSlotData(const uint32_t renderSlotId) const = 0;
822
823 /** Get vertex input declaration handle by shader handle.
824 * @param handle A handle of the shader which vertex input declaration data handle will be returned.
825 * @return Returns a data handle for vertex input declaration.
826 */
827 virtual RenderHandle GetVertexInputDeclarationHandleByShaderHandle(const RenderHandle& handle) const = 0;
828
829 /** Get vertex input declaration handle by vertex input declaration name.
830 * @param path Path/Name of the vertex input declaration given in data.
831 * @return Returns a data handle for vertex input declaration.
832 */
833 virtual RenderHandle GetVertexInputDeclarationHandle(const BASE_NS::string_view path) const = 0;
834
835 /** Get vertex input declaration view by vertex input declaration data handle.
836 * The return value should not be hold into as it contains array_views to data which my change.
837 * @param handle A handle to the vertex input declaration data.
838 * @return Returns a view to vertex input declaration data.
839 */
840 virtual VertexInputDeclarationView GetVertexInputDeclarationView(const RenderHandle& handle) const = 0;
841
842 /** Get pipeline layout handle by shader handle.
843 * @param handle A handle of the shader which pipeline layout data handle will be returned.
844 * @return Returns a handle to pipeline layout.
845 */
846 virtual RenderHandle GetPipelineLayoutHandleByShaderHandle(const RenderHandle& handle) const = 0;
847
848 /** Get pipeline layout by shader or compute shader pipeline layout handle.
849 * @param handle A handle to pipeline layout.
850 * @return Returns a const reference to pipeline layout.
851 */
852 virtual const PipelineLayout& GetPipelineLayout(const RenderHandle& handle) const = 0;
853
854 /** Get pipeline layout handle by pipeline layout name.
855 * @param path Path/Name of the pipeline layout.
856 * @return Returns a handle to pipeline layout.
857 */
858 virtual RenderHandle GetPipelineLayoutHandle(const BASE_NS::string_view path) const = 0;
859
860 /** Get pipeline layout handle for the shader reflection pipeline layout.
861 * @param handle A handle to a valid shader or compute shader.
862 * @return Returns a render handle to pipeline layout.
863 */
864 virtual RenderHandle GetReflectionPipelineLayoutHandle(const RenderHandle& handle) const = 0;
865
866 /** Get pipeline layout reflected from the shader or compute shader pipeline layout handle.
867 * @param handle A handle to a valid shader or compute shader.
868 * @return Returns a const reference to pipeline layout.
869 */
870 virtual const PipelineLayout& GetReflectionPipelineLayout(const RenderHandle& handle) const = 0;
871
872 /** Get specialization reflected from the given shader.
873 * @param handle A handle to a valid shader or compute shader.
874 * @return Returns a view to shader specialization. The struct should not be holded unto.
875 */
876 virtual ShaderSpecializationConstantView GetReflectionSpecialization(const RenderHandle& handle) const = 0;
877
878 /** Get vertex input declaration reflected from the shader. (Zero values if shader does not have one)
879 * @param handle A handle to a valid shader.
880 * @return Returns a view to vertex input declaration view. The struct should not be holded unto.
881 */
882 virtual VertexInputDeclarationView GetReflectionVertexInputDeclaration(const RenderHandle& handle) const = 0;
883
884 /** Get thread group size of a given shader. (Zero values if shader does not have thread group)
885 * @param handle A handle to a valid compute shader.
886 * @return Returns a shader thread group size.
887 */
888 virtual ShaderThreadGroup GetReflectionThreadGroupSize(const RenderHandle& handle) const = 0;
889
890 /** Hash graphics state.
891 * @return Returns a hash for shader related graphics state.
892 */
893 virtual uint64_t HashGraphicsState(const GraphicsState& graphicsState) const = 0;
894
895 /** Simple check if handle is valid or invalid */
896 virtual bool IsValid(const RenderHandle& handle) const = 0;
897 /** Checks if resource is a compute shader */
898 virtual bool IsComputeShader(const RenderHandle& handle) const = 0;
899 /** Checks if resource is a shader */
900 virtual bool IsShader(const RenderHandle& handle) const = 0;
901
902 /** Get shaders based on render handle (pipeline layout, vertex input declaration, graphics state).
903 * Not fast operation and should not be queried every frame.
904 * @param handle A handle to a valid render handle (pl, vid).
905 * @param shaderStateFlags Flags for specific shaders.
906 * @return Returns All shaders that use the specific handle.
907 */
908 virtual BASE_NS::vector<RenderHandle> GetShaders(
909 const RenderHandle& handle, const ShaderStageFlags shaderStageFlags) const = 0;
910
911 /** Check compatibility of render resources.
912 * @param lhs The base for compatibility check.
913 * @param rhs The one which will be compared against the base.
914 * @return Returns compatibility flags.
915 */
916 virtual IShaderManager::CompatibilityFlags GetCompatibilityFlags(
917 const RenderHandle& lhs, const RenderHandle& rhs) const = 0;
918
919 /** Check forced graphics states. Can be set for render slot variants.
920 * @param handle Graphics state or shader handle. Faster to check with graphics state handle.
921 * @return Returns forced graphics state flags.
922 */
923 virtual GraphicsStateFlags GetForcedGraphicsStateFlags(const RenderHandle& handle) const = 0;
924
925 /** Check forced graphics states. Can be set for render slot variants.
926 * @param renderSlotId Render slot id. Find the base graphics state and checks the forced flags
927 * @return Returns forced graphics state flags.
928 */
929 virtual GraphicsStateFlags GetForcedGraphicsStateFlags(const uint32_t renderSlotId) const = 0;
930
931 /** Get typical shader data fetched with the shader.
932 * @name name Name of the shader.
933 * @return shader data.
934 */
935 virtual IShaderManager::ShaderData GetShaderDataByShaderName(const BASE_NS::string_view name) const = 0;
936
937 /** Get typical shader data fetched with the shader.
938 * @name handle Handle of the shader.
939 * @return shader data.
940 */
941 virtual IShaderManager::ShaderData GetShaderDataByShaderHandle(const RenderHandle handle) const = 0;
942
943 /** Get typical graphics shader data fetched with the shader.
944 * @name handle Handle of the shader.
945 * @return graphics shader data.
946 */
947 virtual IShaderManager::GraphicsShaderData GetGraphicsShaderDataByShaderHandle(const RenderHandle handle) const = 0;
948
949 /** Get IdDesc for a RenderHandle.
950 * @param handle A handle to a valid render handle.
951 * @return Returns IdDesc for a given handle.
952 */
953 virtual IShaderManager::IdDesc GetIdDesc(const RenderHandle& handle) const = 0;
954
955 protected:
956 IRenderNodeShaderManager() = default;
957 virtual ~IRenderNodeShaderManager() = default;
958
959 IRenderNodeShaderManager(const IRenderNodeShaderManager&) = delete;
960 IRenderNodeShaderManager& operator=(const IRenderNodeShaderManager&) = delete;
961 IRenderNodeShaderManager(IRenderNodeShaderManager&&) = delete;
962 IRenderNodeShaderManager& operator=(IRenderNodeShaderManager&&) = delete;
963 };
964 /** @} */
965 RENDER_END_NAMESPACE()
966
967 #endif // API_RENDER_DEVICE_ISHADER_MANAGER_H
968