跳至主要內容

UnityShadow

LincZero大约 5 分钟

UnityShadow

目录

渲染流水线(流程顺序 - 新编并简化)

图2.2 渲染流水线中的三个概念阶段

概念流水线.png-16.9kB

应用阶段(Application Stage)(CPU实现)

准备好场景数据

(例如:摄像机位置、视锥体、场景中包含哪些模型、使用了哪些光源等等)

剔除不可见物体

为了提高渲染性能,需要作一个粗粒度剔除(culling)工作,剔除不可见物体不提交给集合阶段

(注:这里的不可见是指被隐藏而非被遮挡而不可见)

设置好每个模型的渲染状态

需要设置好每个模型的渲染状态(例如:使用的材质(漫反射颜色、高光反射颜色)、纹理、Shader等等)

从CPU过渡到GPU

把数据加载到到显存中

图2.3 渲染所需的数据(两张纹理以及3个网格)从硬盘最终加载到显存中。在渲染时,GPU可以快速访问这些数据

CopyDataToGPU.png-86.5kB

设置渲染状态

图2.4 在同一状态下渲染三个网格。由于没有更改渲染状态,因此三个网格的外观看起来像是同一种材质的物体

SetRenderState.png-157.1kB

调用Draw Call

图2.5 CPU通过调用Draw Call来告诉GPU开始进行一个渲染过程。一个Draw Call会指向本次调用需要渲染的图元列表

DrawCall.png-59.1kB

几何阶段(Geometry Stage)(GPU实现)

图2.6 GPU的渲染流水线实现。颜色表示了不同阶段的可配置性或可编程性

GPU流水线.png-82.2kB

顶点着色器(Vertex Shader)(可编程)

  • 主要工作:坐标变换、逐顶点光照

图2.7 GPU在每个输入的网格顶点上都会调用顶点着色器。顶点着色器必须进行顶点的坐标变换,需要时还可以计算和输出顶点的颜色。例如,我们可能需要进行逐顶点的光照

VertexShaderProcess.png-43kB

图2.8 顶点着色器会将模型顶点的位置变换到齐次裁剪坐标空间下,进行输出后再由硬件做透视除法得到NDC下的坐标

![Vertex Shader.png-34.9kB](01.%20渲染流水线.assets/Vertex Shader.png)

曲面细分着色器(Tessellation Shader)(可编程、可选)

  • 作用:细分图元

几何着色器(Geometry Shader)(可编程、可选)

  • 作用:执行逐图元(Per-Primitive)的着色操作,或者被用于产生更多的图元

裁剪(Clipping)(可配置)

  • 作用:将不在摄像机视野内的顶点裁剪掉,并剔除某些三角图元的面片

图2.9 只有在单位立方体的图元才需要被继续处理。因此,完全在单位立方体外部的图元(红色三角形)被舍弃,完全在单位立方体内部的图元(绿色三角形)将被保留。和单位立方体相交的图元(黄色三角形)会被裁剪,新的顶点会被生成,原来在外部的顶点会被舍弃

Clipping.png-25.5kB

屏幕映射(Screen Mapping)(固定)

  • 作用:负责把每个图元的坐标转换到屏幕坐标系(Screen Coordinates)中

图2.10 屏幕映射将x、y坐标从(-1, 1)范围转换到屏幕坐标系中

ScreenMapping.png-22.6kB

图2.11 OpenGL和DirectX的屏幕坐标系差异。对于一张512*512大小的图像,在OpenGL中其(0, 0)点在左下角,而在DirectX中其(0, 0)点在左上角

![Screen Mapping_OpenGL_DirectX.png-26.9kB](01.%20渲染流水线.assets/Screen Mapping_OpenGL_DirectX.png)

光栅化阶段(Rasterizer Stage)(GPU实现)

有两个重要的目标:计算每个图元覆盖了哪些像素,以及为这些像素计算它们的颜色

图2.6 GPU的渲染流水线实现。颜色表示了不同阶段的可配置性或可编程性

GPU流水线.png-82.2kB

三角形设置(Triangle Setup)(固定)

  • 作用:计算光栅化一个三角网格所需的信息(在此之前处理的都是图元中的点)

三角形遍历(Triangle Traversal)(固定)

  • 作用:检查每个像素是否被一个三角网格所覆盖,这个阶段也被称为扫描变换Scan Conversion

图2.12 三角形遍历的过程。根据几何阶段输出的顶点信息,最终得到该三角网格覆盖的像素位置。对应像素会生成一个片元,而片元中的状态是对三个顶点的信息进行插值得到的。例如,对图2.12中三个顶点的深度进行插值得到其重心位置对应的片元的深度值为-10.0

TriangleSetupAndTraversal.png-80kB

片元着色器(Fragment Shader)(可编程、可选)这步不太懂

  • 作用:完成一些渲染技术(例如纹理采样)

图2.12 三角形遍历的过程。根据几何阶段输出的顶点信息,最终得到该三角网格覆盖的像素位置。对应像素会生成一个片元,而片元中的状态是对三个顶点的信息进行插值得到的。例如,对图2.12中三个顶点的深度进行插值得到其重心位置对应的片元的深度值为-10.0

FragmentShader.png-42.4kB

逐片元操作(Per-Fragment Operations)(可配置)

  • 作用:逐片元(Per-Fragment Operations)的着色操作(例如修改颜色、深度缓冲、进行魂环等等)

图2.14 逐片元操作阶段所做的操作。只有通过了所有的测试后,新生成的片元才能和颜色缓冲区中已经存在的像素颜色进行混合,最后再写入颜色缓冲区中

![Per-fragment Operations.png-23.1kB](01.%20渲染流水线.assets/Per-fragment Operations.png)

模板测试(Stencil Test

图2.15 模板测试和深度测试的简化流程图

Stencil Test_Depth Test.png-93.5kB

深度测试(Depth Test

  • 深度测试补充:对于被其他物体遮挡的就不需要出现在屏幕上

混合(Blend

图2.16 混合操作的简化流程图

Blending.png-67.6kB