[Shader] Unity 渲染管线架构

56 篇文章 2 订阅

1.0.7. | 渲染管线架构

在当前版本的Unity中,渲染管线分为三种类型:Built-in RP, Universal
RP(以前版本称为轻量级)和High Definition RP。

值得问我们自己的是,什么是渲染管线? 要回答这个问题,我们首先要了解“管线”的概念。

管线是执行更重要的任务操作的一系列阶段。 那么渲染管线指的是什么? 让我们将这个概念视为多边形对象(例如扩展名为 .fbx 的对象)渲染到我们的计算机屏幕上必须采取的完整过程; 它就像一个物体穿过超级马里奥管道直到到达最终目的地。 因此,每个渲染管道都有其特征,并且根据我们使用的类型:材质属性、光源、纹理以及着色器内部发生的所有功能,将影响屏幕上对象的外观和优化。

现在,这个过程是如何发生的? 为此,我们必须谈谈基本的渲染管线架构。 Unity将该架构分为四个阶段:应用、几何处理、光栅化和像素处理

请注意,这对应于实时渲染引擎的渲染管道的基本模型。 上述每个阶段都有我们接下来定义的线程。

在这里插入图片描述
(图 1.0.7a. 逻辑渲染管线)

1.0.8. | 应用阶段.

应用程序阶段从 CPU 开始,负责场景中发生的各种操作,例如:

• 碰撞检测。
• 纹理动画。
• 键盘输入。
• 鼠标输入等。

它的功能是读取内存中存储的数据以生成图元(例如三角形、直线、顶点)。 在应用阶段结束时,所有这些信息都被发送到几何处理阶段,以通过矩阵乘法生成顶点变换。

在这里插入图片描述
(图1.0.8a)

1.0.9. | 几何处理阶段.

CPU 向 GPU 请求我们在计算机屏幕上看到的图像。 这些请求分两个主要步骤执行:

  1. 渲染状态已配置,对应于从几何图形处理到像素处理的一系列阶段。
  2. 然后,该对象被绘制在屏幕上。

几何处理阶段发生在 GPU 上,负责对象的顶点处理。 该阶段分为四个子过程:顶点着色、投影、裁剪和屏幕映射

在这里插入图片描述
(图1.0.p)

当基元已在应用程序阶段组装完毕后,顶点着色(通常称为顶点着色器阶段)将处理两个主要任务:

  1. 它计算对象顶点的位置
  2. 将其位置转换到不同的空间坐标,以便将它们投影到计算机屏幕上。

此外,在此子流程中,我们可以选择要传递到以下阶段的属性。 这意味着在顶点着色器阶段,我们可以包含法线、切线、UV 坐标等。

投影和剪裁作为该过程的一部分发生,其根据场景中相机的属性而变化。 值得一提的是,整个渲染过程仅发生在相机视锥体(也称为视图空间)内的那些元素。

投影和裁剪将取决于我们的相机,如果它设置为透视或正交(平行)。 为了理解这个过程,我们假设场景中有一个球体,其中一半位于相机的视锥体之外,因此只有位于视锥体内的球体区域才会被投影并随后被剪裁 屏幕,即球体中看不见的区域在渲染过程中将被丢弃。

在这里插入图片描述
(图1.0.9b)

一旦我们将剪切的对象放入内存中,它们就会被发送到屏幕映射(屏幕映射)。 在此阶段,场景中的三维对象将转换为屏幕坐标,也称为窗口坐标。

1.1.0. | 光栅化阶段.

我们的第三阶段对应于光栅化。 此时,我们的对象有了屏幕坐标(2D 坐标),现在我们必须寻找投影区域中的像素。 查找屏幕上对象占据的所有像素的过程称为光栅化。 这个过程可以看作是场景中的对象和屏幕上的像素之间的同步步骤。

对于每个对象,光栅化器执行两个过程:

  1. 三角形设置。
  2. 三角形遍历。(Triangle traversal.)

三角形设置负责生成将发送到三角形遍历的数据。 它包括屏幕上对象边缘的方程。 三角形遍历列出了多边形对象区域覆盖的像素。 这样就生成了一组称为“碎片(fragments)”的像素。 然而,这个词多次使用来指代单个像素。

1.1.1. | 像素处理阶段.

使用先前过程中的插值,当所有像素准备好投影到屏幕上时,最后阶段开始。 此时,片段着色器阶段(也称为像素着色器阶段)开始并负责每个像素的可见性。 基本上它的作用是计算像素的最终颜色,然后将其发送到颜色缓冲区。

在这里插入图片描述
(图 1.1.1a。几何体覆盖的区域被转换为屏幕上的像素。)

1.1.2. | 渲染管道的类型

我们已经知道,Unity 中有三种类型的渲染管道。 默认情况下,我们可以找到一个Built-in RP,它对应于软件中最古老的引擎,而Universal RP和High Definition RP则属于一种称为Scriptable RP的渲染管线,它更先进,并经过预先优化以获得更好的图形性能。
在这里插入图片描述
(图1.1.2a。当我们在Unity中创建一个新项目时,我们可以在这三种渲染引擎之间进行选择。我们的选择取决于手头项目的需求)

不管渲染管线如何,如果我们想在屏幕上生成图像,就必须经过“管线”。

管线可以有不同的处理路径。 这些被称为渲染路径; 就好像 1.0.7 节中的示例管道有不止一种方法可以到达目的地。

渲染路径对应于与照明和着色对象相关的一系列操作。 这使我们能够以图形方式处理照明场景(例如具有定向光和球体的场景)。

这些路径的示例包括前向渲染、延迟着色、传统延迟和传统顶点光照。 其中每一个都有不同的功能和性能特征。

在Unity中,默认的渲染路径对应的是前向渲染; 这是 Unity 中包含的三种管道渲染类型的初始路径。 这是因为它具有更大的显卡兼容性和光照计算限制,使其成为更优化的过程。

请注意,在Universal RP 中,我们只能使用前向作为渲染路径,而High Definition RP 允许使用前向或延迟着色进行照明材质渲染。
在这里插入图片描述
(图1.1.2b。要在内置渲染管道中选择渲染路径,我们必须进入hierarchy,选择主相机,然后在属性“Rendering Path”中我们可以根据项目的需要更改配置 )。

为了理解这个概念,我们假设场景中有一个“对象”和一个“直射光”。 光和物体之间的相互作用基于两点,它们是。

  1. 照明特性。
  2. 材料特性。

这两个元素之间的相互作用称为光照模型( lighting model )

基本光照模型对应于三种不同属性的总和,即环境颜色、漫反射和镜面反射。

光照计算在着色器内进行,可以按顶点或按片段进行。 当光照按顶点计算时,称为逐顶点光照,在顶点着色器阶段执行;同样,当按片段计算光照时,称为逐片段或逐像素着色器,在片段着色器阶段执行 。

1.1.3. | 前向渲染

前向是默认渲染路径,支持材质的所有典型特征(例如法线贴图、像素光照、阴影等)。 该渲染路径有两个不同的代码编写passes,我们可以在着色器中使用它们,第一个base pass和第二个additional pass。

在base pass中,我们可以定义 ForwardBase 光照模式,在 additional pass 中,我们可以定义 ForwardAdd 光照模式。 两者都是具有光照计算功能的着色器的特征函数。 base pass可以按像素处理定向光,如果场景中有多个定向光,则将使用最亮的光。 此外,base pass还可以处理光探针、全局照明和环境照明(Skylight)。

正如其名称所示,additional pass可以处理每个像素的“附加灯光”或影响对象的阴影,这是什么意思? 如果场景中有两个灯光,则我们的对象将仅受其中之一的影响,但是,如果我们为此配置定义了additional pass,则它将受到两者的影响。

我们必须考虑的一点是每个照明pass都会生成一个单独的draw call。 draw call是每次我们想要在计算机屏幕上绘制元素时在 GPU 中进行的调用图形。 这些调用是需要大量计算的过程,因此需要将它们保持在尽可能低的水平,如果我们正在开发移动设备的项目,则更是如此。

为了理解这个概念,我们假设场景中有四个球体和一个定向光。 每个球体本质上都会生成对 GPU 的调用,这意味着它们每个球体默认都会生成独立的绘制调用。

同样,定向光会影响场景中找到的所有球体,因此,它将为每个球体生成额外的绘制调用,这主要是因为着色器中已包含第二个pass来计算阴影投影,因此, 四个球体加上单向光将总共生成八次绘制调用。

在这里插入图片描述
(图1.1.3a。在上图中,我们可以看到有光源时绘制调用的增加。计算包括环境颜色和光源作为对象)

确定 base pass 后,如果我们在着色器中添加另一个pass,那么我们将为每个对象添加一个新的绘制调用,因此,图形负载将显着增加。

有一些方法可以优化这个过程,我们将在本书后面讨论。 现在,我们将继续渲染路径概念。

1.1.4. | 延迟着色

此渲染路径确保只有一个照明pass计算场景中的每个光源,并且仅在受光源影响的像素中进行计算,所有这一切都是通过几何体和照明的分离实现的。 这是一个优势,因为我们可以生成大量影响不同对象的光线,从而提高最终渲染的保真度,但名义上会增加 GPU 上的每像素计算量。

虽然延迟着色在多光源计算方面优于前向着色,但它带来了一些硬件兼容性限制和问题。

1.1.5. | 我应该使用什么渲染引擎?

这是当今一个非常常见且反复出现的问题。

过去只有Built-in RP,因此无论是2D还是3D项目都非常容易启动。 然而,现在我们必须根据游戏的需求来启动我们的游戏,那么我们可能会想,我们如何知道我们的项目需要什么? 要回答这个问题,我们必须考虑以下因素:

  1. 如果我们要开发 PC 视频游戏,我们可以使用三个可用的 Unity 渲染管道中的任何一个,因为一般来说,PC 的计算能力比移动设备甚至游戏机更强。 那么,如果我们的视频游戏是针对 PC 的,我们是否需要以高清或中清晰度的图形方式观看它? 如果我们需要高清视频游戏,我们可以使用High Definition RP 和Built-in RP 来创建它。
  2. 如果我们希望我们的视频游戏具有中等清晰度的图形,我们可以使用Universal RP,或者像前面的情况一样; 也Built-in RP。 现在,为什么在这两种情况下都可以选择Built-in RP?

与之前的渲染管道不同,此渲染管道更加灵活,因此技术性更强,并且没有预先优化。 High Definition RP 已针对生成高端图形进行了预先优化,Universal RP 已针对中档图形进行了预先优化。

选择渲染管道时的另一个重要因素是着色器。 一般来说,在 High Definition RP 和 Universal RP 中,着色器都是在 Shader Graph 中创建的,Shader Graph 是一个包,其中包含一个接口,允许我们通过节点创建着色器,该节点有积极的一面和消极的一面。 一方面,我们可以通过节点直观地创建着色器,而无需在 HLSL 中编写代码,但是,另一方面,如果我们将 Unity 版本更新到生产中的较新版本(例如从 2019 年到 2020 年), 着色器很可能会停止编译,因为 Shader Graph 的版本和更新与 Unity 版本无关。

在 Unity 中创建着色器的最佳方法是通过 HLSL 语言,因为这样我们就可以确保我们的程序在不同的渲染管道中进行编译,并且无论 Unity 升级如何,都可以继续工作。 在本章后面,我们将详细回顾 HLSL 中程序的结构。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值