赞
踩
点关注不迷路,持续输出Unity
干货文章。
嗨,大家好,我是新发。最近在捣腾Unity
的ShaderGraph
插件,挺好玩的,我决定把我自己实验的所有效果记录到这篇博客中,附带完整高清的连线动态图,希望对想要学习ShaderGraph
的同学有所启发。
渲染管线也称渲染流水线,是显示芯片(GPU
)内部处理图形信号相互独立的并行的处理单位。
渲染管线流程包括下面几个步骤:顶点处理、面处理、光栅化、像素处理等。
Unity
内置的渲染管线,我们可以使用shader
来实现渲染管线中的某些步骤的逻辑。
Unity2018
中引入了可编程渲染管线(Scriptable Render Pipline
),简称SRP
,是一种在Unity
中通过C#
脚本配置和执行渲染的方式。
为什么需要SRP
?
Unity
内置的渲染管道只有Forward
和Deferred
两种。
Forward Shading
原理:每个作用于物体的像素光单独计算一次,drawCall随着物体与光照数量增加而成倍增加
优点:不受硬件限制
缺点:光照计算开销成倍增加随着光源和物体数量增加。
每个物体接受光照数量有限。
Deferred Shading
原理:物体颜色、法线、材质等信息先渲染到G-Buffer中,光照最后单独渲染,避免每个物体多个光照批次的问题
优点:作用于每个物体光照数量不再受到限制,光照计算不随着物体增加而增加
缺点:移动设备需要支持OpenGL3.0。
不支持MSAA。
半透明物体仍然使用前向渲染。
如上,这两种内置的管道各有优缺点 ,还有,我们看不到源代码,如果为了表现某种特殊的视觉效果修改起来非常不便。所以就有了SRP
的诞生。另外,根据项目的需求写合适的SRP
,也可以降低DrawCall
,提高运行效率。
SRP
引入了CommandBuffer
。
CommandBuffer,用于拓展Unity渲染管线。
包含一系列渲染命令,比如设置渲染目标,绘制网格等,并可以设置为在摄像机期间的各个点执行渲染。
下面是CommandBuffer
的一个简单的例子:(具体可看官方Github
的例子,传送门)
public override void Render(ScriptableRenderContext context, Camera[] cameras)
{
base.Render(context, cameras);
var cmd = new CommandBuffer();
cmd.ClearRenderTarget(true, true, m_ClearColor);
context.ExecuteCommandBuffer(cmd);
cmd.Release();
context.Submit();
}
自己定制渲染管线对编程要求很高,难度大。
所以Unity
提供里2个预制的管线:高清渲染管线(HDRP
,全称High Definition Render Pipleline
)、通用渲染管线(URP
,全称Universal Render Pipleline
),
注意,URP
的前身就是轻量级渲染管线LWRP
(全称Light Weight Render Pipleline
)。
在Unity2018
版本,Unity
为了提高引擎的画面表现,推出了High Definition Render Pipeline
,高清晰渲染管线,简称HDRP
。
HDRP
专注于高端图形渲染,针对高端硬件配置,像PC
、XBox
和Playstation
,其面向高逼真度的游戏、图形demo
和建筑渲染、超写实效果,以及所需的最佳图形效果,目前还不支持在手机移动端使用HDRP
。
想得到HDRP
的完美表现能力,需要大量的贴图,漫反射贴图、高光贴图、金属贴图、平滑贴图、AO
贴图、法线贴图、凹凸贴图、高度贴图等等,所以要做HDRP
流程需要非常长的时间和庞大的制作团队以及充足的预算。
在2019.3
版本中,Unity
将轻量渲染管线LWRP
重命名为通用渲染管线URP
,通用渲染管线是制作精美图形和显示效果的强力方案,并且同时支持多个平台。轻量渲染管线设计初时具有快捷、可伸缩的优点,可为所有移动端带来高质量的图形效果。URP
是Unity
未来的默认渲染方式。
Unity
官方将致力于改进通用渲染管线,为用户带来VFX Graph
、Shader Graph
、Custom Render Passes
及最新Post-Processing
的各种便利,实现等同甚至更好的品质与性能,且只需一次开发,便能在大量的平台上部署。
需要注意的是,通用渲染管线将不会取代或包括高清渲染管线(HDRP
)。
Unity2018
推出了一个可编程渲染管线工具ShaderGraph
,让开发者们可以通过可视化界面拖拽来实现着色器的创建和编辑。
目前ShaderGraph
支持的URP
通用渲染管线,也支持HDRP
高清渲染管线。
我们通过Unity
的PackageManager
安装ShaderGraph
,还需要安装对应的渲染管线工具包,比如要使用URP
通用渲染管线,则需要通过PackageManager
安装Universal RP
,如果要使用HDRP
高清渲染管线,则需要通过PackageManager
安装High Definition RP
。
安装了渲染管线工具包之后,就可以通过菜单 Assets - Create - Rendering
创建对应的渲染管线配置。
接着在Editor - Project Setting - Graphics
中的Scriptable Render Pipeline Settings
设置渲染管线配置文件。
如果是使用URP
,则设置URP
的渲染管线配置
如果是使用HDRP
,则设置HDRP
的渲染管线配置
然后,我们就可以创建对应的ShaderGraph
,愉快得进行连连看了。
我实验了一下URP
和HDRP
的效果,感受一下
先看URP
的效果
再看HDRP
的效果
首先除了安装ShaderGraph
本身外,还得安装渲染管线工具,以URP
渲染管线(工具包名叫Universal RP
)为例。
点击菜单Window - Package Manager
,打开Package Manager
窗口。
点击Packages
,选择Unity Registry
,
然后搜索Universal RP
,点击Install
按钮,等等安装完毕。
在Project
窗口中右键 - Create - Rendering - Universal Render Pipeline - Pipeline Asset (Forward Renderer)
,即可创建一个Pipeline Assets
资源:UniversalRenderPipelineAssets
。
点击菜单 Edit - Project Settings
,弹出Project Settings
窗口,点击Graphics
,将上面创建的UniversalRenderPipelineAssets
拖到Scriptable Render Pipeline Settings
中。
在Project
窗口中右键-Create-Shader-PBR Graph
,即可创建一个PBR Graph
脚本。
双击PBRShaderGraph
文件,即可打开编辑窗口
点击左上角的属性窗口中的+号
可以创建变量,这里我们创建一个Color
变量。
如下,出现了一个Color
变量,我们可以设置默认颜色,如下设置了红色
将变量拖动到操作区中
将Color
节点连到PBR Master
节点的Albedo
插槽中,即可看到预览窗口中的模型的表面已变成了红色。
点击Save Asset
即可保存ShaderGraph
文件。
创建一个Material
材质球:PBRTestMaterial
,然后直接将ShaderGraph
文件拖动到材质球文件上即可。
材质球上,可以看到我们在ShaderGraph
中创建的Color
变量,通过变量可以调整材质球的颜色。
在Hierachy
窗口中右键 - 3D Object - Capsule
,创建衣蛾胶囊体模型
将材质球赋值给胶囊体的材质属性中,即可看到胶囊体变成了红色
调整材质球的Color
变量,胶囊体的颜色也相应的发生变化。
原理:AlphaClip
的值如果比Alpha
的值大,则会不显示
进阶:在裁剪的基础上添加裁剪边缘光
首先利用Smoothstep
做出一个边缘渐变
Smoothstep:如果输入In的值分别在输入Edge1和Edge2的值之间,则返回0和1之间的平滑Hermite插值的结果。如果输入In的值小于输入Step1的值,则返回0;如果大于输入Step2的值,则返回1 。
然后将边缘渐变和颜色叠加,连到PBR Master
的发光插槽Emission
上
原理:AlphaClip
的值如果比Alpha
的值大,则会不显示
进阶:溶解边缘添加发光,原理就是对Noise
噪声做两个Step
,然后相减,再乘个颜色,连到Emission
发光节点上。
原理:Fresnel Effect
,菲涅耳效应,根据观察角度产生不同反射率从而对表面效果产生影响,当你靠近时,会反射更多的光。菲涅耳效应节点通过计算表面法线与视线方向的夹角来近似。这个角度越大,返回值越大。这种效果经常被用来实现边缘照明,这在很多艺术风格中都很常见。
进阶:带方向的菲涅尔边缘光效果
原理:使用Sample Gradient
设置几个阴影色块颜色
原理:通过Tilling And Offset
节点的Offset
来控制水纹的UV
偏移,然后再使用Lerp
将水纹和主贴图做一个线性差值
原理:使用一个向上的 Vector3
和 模型的 Normal Vertor
(法线向量) 点乘,得到的是 一个标量,表示模型法线向量和垂直向量的夹角(方向的相似度),然后通过 Step
过滤得到要显示白色的部分,将要显示的 白色部分再和一个噪声相乘后输入到Master
的Emission
发光槽中。
原理:由View Direction
视角移动, 引发Tilling And Offset
节点 移动 贴图,产生的效果。注意View Direction
使用Tangent
切线空间。该效果也可用于冰晶效果。
原理,使用Split
将UV
分开成x
和y
两个分类,对x
分类做一个噪音抖动,最后和y
再合并作用到主贴图的UV
上。
原理:使用Gradient Noise
随机噪声,再通过一个 Normal Vector
结点,代表垂直于物体的法向量,接着,对Position
进行一个叠加。
注意Normal Vector
和Position
的Space
都选择Object
空间
原理:通过噪声的UV
移动,形成一个动态移动的噪声,作用到Position
上,为了让旗的根部所以在通过一个UV
的x
分量来限制根部的噪音。
原理:Posterize
的作用是色调分离。
通过官方文档,我们可以知道Posterize
这个节点的公式为:
void Unity_Posterize_float4(float4 In, float4 Steps, out float4 Out)
{
Out = floor(In / (1 / Steps)) * (1 / Steps);
}
根据公式,我们也可以自己实现马赛克效果
原理:通过UV
的y
方向构造一个垂直渐变的UV
,作为噪声的Step
边缘,形成一条波浪,最后差值两个颜色,再用形状做裁切。
原理:通过两个Voronoi
的融合,得到类似火焰向上燃烧的形状,再通过UV
和一个Vector 2
的Distance
制造两个圆形区域,分别作为火焰内心和外围的区域,再合火焰形状相乘,最后再乘上颜色。
原理:使用Twirl
对Voronoi
产生一个旋涡形状。
原理:噪声通过Rectangle
后,可以形成类似闪电的形状。
一个UV
向下移动的噪声和一个UV
向上移动的噪声相加,再通过Rectangle
,则可以形成动态闪电效果。
原理:通过Fraction
获取Position
的y
分量得到一个条纹效果,再通过UV
移动得到一个扫描的效果,最后和菲涅尔效果叠加。
原理:通过UV
和Sine
构造一个圆心向外扩散的效果,再作用到贴图的UV
上。
具体实现参见我这篇文章:Unity ShaderGraph实现图片的高斯模糊效果
具体实现参见我这篇文章:Unity Unlit ShaderGraph实现与PBR的自发光贴图类似的叠加效果
具体实现参见我这篇文章:Unity ShaderGraph溶解效果运用到粒子系统中
具体实现参见我这篇文章:Unity使用ShaderGraph实现根据坐标控制溶解的位置,物体靠近局部溶解
具体实现参见我这篇文章:Unity ShaderGraph 2D描边效果、不规则描边效果
具体实现参见我这篇文章:Unity使用ShaderGraph配合粒子系统,制作子弹拖尾特效
具体实现参见我这篇文章:使用Unity ShaderGraph实现在模型涂鸦的效果
具体实现参见我这篇文章:使用Unity ShaderGraph实现刮刮乐的刮卡剔除效果
具体实现参见我这篇文章:【游戏开发实战】Unity使用ShaderGraph制作一个Loading水球(能量球 | UI | 2D | 特效 | URP)
工程地址:https://gitcode.net/linxinfa/urpcartoonwater
ShaderGraph
连线图如下,图片大家应该看不清,建议打开工程项目的CartoonWater.shadergraph
文件查看细节
注意需要开启Depth Texture
,
工程地址:https://gitcode.net/linxinfa/unityurpiceeffect
ShaderGraph
连线图如下,看不清图片建议打开工程项目的IceEffect.shadergraph
文件查看细节
具体实现见我这篇博客:https://blog.csdn.net/linxinfa/article/details/124578453
工程地址:https://gitcode.net/linxinfa/UnityShaderGraphPanelTransition
注:
Unity
版本:2021.3.1f1c1
,Universal RP
版本:12.1.6
待续
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。