URP 无光照基本着色器
以下示例显示了一个兼容 URP 的基本着色器。此着色器使用着色器代码中预定义的颜色来填充网格形状。
要查看此着色器的实际效果,请将以下 ShaderLab 代码复制并粘贴到着色器资源中。
// 此着色器使用代码中预定义的颜色来填充网格形状。
Shader "Example/URPUnlitShaderBasic"
{
// Unity 着色器的 Properties 代码块。在此示例中,这个代码块为空,
// 因为在片元着色器代码中预定义了输出颜色。
Properties
{ }
// 包含 Shader 代码的 SubShader 代码块。
SubShader
{
// SubShader Tags 定义何时以及在何种条件下执行某个 SubShader 代码块
// 或某个通道。
Tags { "RenderType" = "Opaque" "RenderPipeline" = "UniversalPipeline" }
Pass
{
// HLSL 代码块。Unity SRP 使用 HLSL 语言。
HLSLPROGRAM
// 此行定义顶点着色器的名称。
#pragma vertex vert
// 此行定义片元着色器的名称。
#pragma fragment frag
// Core.hlsl 文件包含常用的 HLSL 宏和
// 函数的定义,还包含对其他 HLSL 文件(例如
// Common.hlsl、SpaceTransforms.hlsl 等)的 #include 引用。
#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
// 结构定义将定义它包含哪些变量。
// 此示例使用 Attributes 结构作为顶点着色器中的
// 输入结构。
struct Attributes
{
// positionOS 变量包含对象空间中的顶点
// 位置。
float4 positionOS : POSITION;
};
struct Varyings
{
// 此结构中的位置必须具有 SV_POSITION 语义。
float4 positionHCS : SV_POSITION;
};
// 顶点着色器定义具有在 Varyings 结构中定义的
// 属性。vert 函数的类型必须与它返回的类型(结构)
// 匹配。
Varyings vert(Attributes IN)
{
// 使用 Varyings 结构声明输出对象 (OUT)。
Varyings OUT;
// TransformObjectToHClip 函数将顶点位置
// 从对象空间变换到齐次裁剪空间。
OUT.positionHCS = TransformObjectToHClip(IN.positionOS.xyz);
// 返回输出。
return OUT;
}
// 片元着色器定义。
half4 frag() : SV_Target
{
// 定义颜色变量并返回它。
half4 customColor = half4(0.5, 0, 0, 1);
return customColor;
}
ENDHLSL
}
}
}
片元着色器将游戏对象着色为深红色(RGB 值 (0.5, 0, 0))。
下一节将介绍这个基本 Unity 着色器的结构。
基本的 ShaderLab 结构
Unity 着色器是用一种称为 ShaderLab 的 Unity 特有语言编写的。
此示例中的 Unity 着色器具有以下代码块:
Shader 代码块
ShaderLab 代码以 Shader
声明开头。
Shader "Example/URPUnlitShaderBasic"
此声明中的路径决定了 Unity 着色器在材质 Shader 菜单中的显示名称和位置。Shader.Find 方法也会使用这一路径。
Properties 代码块
Properties 代码块包含用户可在材质 Inspector 窗口中设置的属性的声明。
在此示例中,Properties 代码块为空,因为该 Unity 着色器不公开用户可定义的任何材质属性。
SubShader 代码块
一个 Unity 着色器源文件包含一个或多个 SubShader 代码块。渲染网格时,Unity 会选择与目标设备上的 GPU 兼容的第一个 SubShader。
SubShader 代码块可以选择性包含 SubShader Tags 代码块。应使用 Tags
关键字来声明 SubShader Tags 代码块。
Tags { "RenderType" = "Opaque" "RenderPipeline" = "UniversalPipeline" }
一个名为 RenderPipeline
的 SubShader 标签告诉 Unity 将此 SubShader 用于哪些渲染管线,而 UniversalPipeline
的值指示 Unity 应将此 SubShader 用于 URP。
要在不同的渲染管线中执行同一个着色器,请创建多个具有不同 RenderPipeline
标签值的 SubShader 代码块。要在 HDRP 中执行 SubShader 代码块,请将 RenderPipeline
标签设置为 HDRenderPipeline
,要在内置渲染管线中执行该代码块,请将 RenderPipeline
设置为空值。
有关 SubShader Tags 的更多信息,请参阅 ShaderLab:SubShader Tags。
Pass 代码块
在此示例中,有一个包含 HLSL 程序代码的 Pass 代码块。有关 Pass 代码块的更多信息,请参阅 ShaderLab:Pass。
Pass 代码块可以选择性包含 Pass 标签代码块。有关更多信息,请参阅 URP ShaderLab Pass 标签。
HLSLPROGRAM 代码块
此代码块包含 HLSL 程序代码。
注意:HLSL 语言是 URP 着色器的首选语言。
注意:URP 支持 CG 语言。如果在着色器中添加 CGPROGRAM/ENDCGPROGRAM 代码块,Unity 会自动包含来自内置渲染管线库的着色器。如果您添加来自 SRP 着色器库的着色器,某些 SRP 着色器宏和函数可能会与内置渲染管线着色器函数发生冲突。包含 CGPROGRAM 代码块的着色器与 SRP Batcher 不兼容。
以下代码块包含引用 Core.hlsl
文件的 #include
声明。
# include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
Core.hlsl
文件包含常用 HLSL 宏和函数的定义,还包含对其他 HLSL 文件(例如,Common.hlsl
和 SpaceTransforms.hlsl
)的 #include 引用。
例如,HLSL 代码中的顶点着色器使用 SpaceTransforms.hlsl
文件中的 TransformObjectToHClip
函数。该函数将顶点位置从对象空间变换到齐次空间:
Varyings vert(Attributes IN)
{
Varyings OUT;
OUT.positionHCS = TransformObjectToHClip(IN.positionOS.xyz);
return OUT;
}
以下这段基本 HLSL 代码中的片元着色器会输出代码中预定义的单一颜色:
half4 frag() : SV_Target
{
half4 customColor;
customColor = half4(0.5, 0, 0, 1);
return customColor;
}
带有颜色输入的 URP 无光照着色器一节介绍了如何在材质 Inspector 窗口中添加可编辑的颜色属性。