该文档为学习文档,如有错误欢迎指正。
1. D3D11 Compute Shader概述
Compute Shader 是一个通用计算 Stage。它利用了GPU的并行处理器,实现大量线程并发执行。它可以独立于渲染管线之外,计算完成的数据可以在CPU回读;也可以结合到渲染管线中,利用GPU Buffer与其他Stage进行通信。
HLSL中的Compute Shader的编写:其main(参数:线程id)函数,实际上是单个线程的执行代码;main函数的参数,是线程的id标识,即用来定位该线程,以便于在Buffer中定位数据。
D3D11中Compute Shader 的执行:->Dispatch(线程组数量),即通知GPU执行多少线程组,并且执行完返回。
2. Unity和UE4 的Compute Shader 概述
(1) Unity
Unity 在编辑器中暴露了 *.shader(vertex shader、pixel shader)和*.compute(compute shader) ,可以直接在编辑器中创建并使用。其中Shader 在 Material被引用;而Compute Shader 独立使用。 Compute Shader 在Unity中2种类型的应用方式:
① 创建“*.compute”。编写hlsl代码。若需要与其他Shader通信,则编写C#代码实现通信,实际上就用公用Buffer。
② 隐含在VFX中被创建。Visual FX (Unity 的GPU 粒子的可视化编辑器),定义了一类新的资源*.vfx。这是一个gpu粒子资源。该资源可以包含若干个*.shader和若干个*.compute,并且这些隐含资源是unity根据编辑好的节点逻辑自动生成的。
(2) UE4
UE4在编辑器中没有暴露 Shader的概念,只有材质节点编辑器。Compute shader 与其他Stage的Shader一起被封装在了底层,各类Shader(VS、HS、DS、PS、GS、CS)用一个枚举来进行区别。而Compute Shader在UE4引擎代码中 主要被分成3类来使用
① MaterialShader:需要从材质中获取信息的Compute Shader。目前UE4.19里只有一个这样的Compute Shader;其他MaterailShader都为VS、HS、DS、PS、GS
② GlobalShader:全局的ComputeShader。这类ComputeShader有一百多个实例。(应用范围,摘录自UE使用到的一些文件名: ParticleBound、ParticleSort、GPUSkinCache、GPUSort、Morph、PostProcess、Shadow、DistanceFieldAO、DistanceFieldGI、DistanceFieldShadow等等)
③ NiagaraShader: Niagara是一个UE4自己的插件,一个粒子编辑器。与MaterialShader类似,它应该也是可以根据不同的粒子,生成不同的Shader。实际上它只有一个对应的shader文件,但是可以根据粒子编辑器的编辑,生成一个hlsl的函数,插入到这个shader文件已有的代码模板中,从而产生不同的compute shader。(在代码中有看到插入函数的代码拼接过程;产生不同的cs则暂为个人推测)
3. Compute Shader
(1) D3D11相关接口和相关Flag参数
(2) HLSL语法
① Buffer声明
Buffer类型:StructuredBuffer、RWStructuredBuffer、ByteAddressBuffer、RWByteAddressBuffer、AppendStructuredBuffer、ConsumeStructuredBuffer、IncrementCounter、DecrementCounter、TextureXD(应该还没列全)。其中“RW”前缀表示可读写
关键字groupshared:线程组内共享的buffer。
② 线程组内线程数量声明
[numthreads(x,,y,,z,)]
线程组的数量由D3D的接口Dispatch的参数来决定。
而一个线程组内线程的数量则在hlsl里确定,关键字为numthreads。组内线程数量 = x,*y,*z,
③ Main函数
为单个线程的执行代码
参数可以选取以下:
1) SV_GroupThreadID:(x,y,z)线程组内线程id
2) SV_GroupID:(x,y,z)线程组id
3) SV_DispatchThreadID:(x,y,z)在所有线程中的线程id
4) SV_GroupID:计算出来的线程组id(一个int)
4. Unity 的 Compute Shader
(1) Unity Compute Shader 文件内容
Unity关键字:Kernel(对应一个compute shader main 函数)
文件后缀:*.compute
语法:hlsl
(2) Unity C#ScriptingAPI 内Compute Shader相关
① 类ComputeShader
② 类ComputeBuffer
5. UE4 的Compute Shader
Compute Shader 被封装到了UE4的RHI(Render Hardware Interface)的各模块中;它的使用主要被封装在了UE4的Renderer模块中。
(1) RHI(Render Hardware Interface)
外部使用图形硬件的接口
① IRHIComputeContext:包含compute shader 执行时用到的接口
② IRHICommandContext:继承IRHIComputeContext。具体化为D3D11的话,包含了D3D11DeviceContext的内容
③ FDynamicRHI:具体化为D3D11的话,包含了D3D11Device的内容。可用于创建Buffer,创建Shader等等
(2) D3D11RHI
① FD3D11DynamicRHI。实现了接口IRHICommandContext和接口FDynamicRHI。
② FD3D11StateCacheBase
这是对D3D11中StateCache的封装。State包含了 VS、HS、DS、GS、PS、CS.
在渲染时,可以同时设置VS、HS、DS、GS、PS. 在使用CS时,可单独设置CS。
(3) Renderer模块中
① FShader
② FShaderReouseces:包含了Shader在RHI的指针
③ FMaterialShader:需要获取材质信息的Shader
④ FNiagaraShader:Niagara中使用的Shader;Niagara是一个粒子插件。
⑤ FGlobalShader:全局Shader
⑥ FMaterial:只能包含FMaterialShader。