天天看点

Unity Shader - Predefined Shader preprocessor macros 着色器预处理宏Predefined Shader preprocessor macros

目录:Unity Shader - 知识点目录(先占位,后续持续更新)

原文:Predefined Shader preprocessor macros

版本:2019.1

Predefined Shader preprocessor macros

着色器预处理宏

Unity 编译 shader programs 期间的一些预处理宏。

(本篇的宏介绍随便看看就好,要想深入了解,还是直接看Unity得.cginc代码更好理解,主要看看不是宏介绍的其他内容)

Target platform

目标平台

目标平台
SHADER_API_D3D11 Direct3D 11
SHADER_API_GLCORE 桌面版OpenGL “core” (GL 3/4)
SHADER_API_GLES OpenGL ES 2.0
SHADER_API_GLES3 OpenGL ES 3.0/3.1
SHADER_API_METAL iOS/Mac Metal
SHADER_API_VULKAN Vulkan
SHADER_API_D3D11_9X Universal Windows Platform(UWP平台) Direct3D 11 “feature level 9.x”
SHADER_API_PS4 PlayStation 4.也会定义 SHADER_API_PSSL
SHADER_API_XBOXONE Xbox One

SHADER_API_MOBILE 为常用的移动平台定义(GLES,GLES3,METAL)。

另外,SHADER_TARGET_GLSL 定于在着色器语言为GLSL的平台(对 OpenGL/GLES 平台来说该宏都会定义)。

Shader target model

着色器目标模型

SHADER_TARGET 使用一个数值来定义编译着色器模型(与 #pragma target 指令匹配)。如,当你的编译Shader model 3.0 的着色器,对应 SHADER_TARGET 为 30。你可以使用着色器代码来判断,例如:

#if SHADER_TARGET < 30
    // 比 shader model 3.0 底的版本
    // 限制很大的着色器兼容处理
#else
    // 硬件支持,则可以处理更好的方式
#endif
           

Unity version

Unity 版本

UNITY_VERSION 包含了Unity版本的数值。例如,UNITY_VERSION 为 501 对应着Unity 5.0.1。着可以用于版本比较,如果你需要在编写shader是需要使用不同unity版本的内置功能。例如,一个 #if UNITY_VERSION >= 500 的预处理检测,仅能在Unity 版本是5.0.0或是更高版本才行。

Shader stage being compiled

着色器编译阶段

预处理宏 SHADER_STAGE_VERTEX,SHADER_STAGE_FRAGMENT,SHADER_STAGE_DOMAIN,SHADER_STAGE_HULL,SHADER_STAGE_GEOMETRY,SHADER_STAGE_COMPUTE 将会在编译每个Shader阶段时被定义。通常将像素着色器和计算着色器共享着色器代码是,会很有用,这样可以处理一个稍微不太一样的情况。

Platform difference helpers

平台差异的辅助

不鼓励直接使用这些平台宏,因为它们并不总是有助于代码的未来验证。例如,如果您正在编写一个用于检查D3D11的着色器,您可能想要确保在将来,该检查将扩展到包含Vulkan。那么我们推荐使用Unity定义了的几个helper宏(在HLSLSupport.cginc中):

使用
UNITY_BRANCH 将其添加到条件语句之前,以告诉编译器应该将其编译成实际的分支。在HLSL平台上该宏会替换为[branch]。
UNITY_FLATTEN 在条件语句之前添加这个语句,告诉编译器应该将其平铺以避免实际的分支指令。在HLSL平台上该宏会替换为[flatten]。
UNITY_NO_SCREENSPACE_SHADOWS 定义在不使用级联屏幕空间阴影贴图(移动平台)的平台上。
UNITY_NO_LINEAR_COLORSPACE 定义在不支持线性颜色空间的平台(移动平台)上。
UNITY_NO_RGBM 定义在不使用RGBM压缩光映射的平台(移动平台)上。
UNITY_NO_DXT5nm 定义在不使用DXT5nm标准映射压缩(移动平台)的平台上。
UNITY_FRAMEBUFFER_FETCH_AVAILABLE 定义在"framebuffer color fetch"功能可用的平台上(通常是iOS平台——OpenGL es2.0、3.0和Metal)。
UNITY_USE_RGBA_FOR_POINT_SHADOWS 定义在平台上,点光源阴影贴图使用RGBA纹理编码的深度(其他平台使用单通道浮点纹理)。
UNITY_ATTEN_CHANNEL 定义包含数据的光衰减纹理通道;用于逐像素照明代码。定义为“r”或“a”。
UNITY_HALF_TEXEL_OFFSET 定义在要半texel偏移调整映射到像素的texel(如Direct3D 9)。
UNITY_UV_STARTS_AT_TOP 总是用值1或0来定义。值为1时,代表在纹理V坐标(纹理顶部)为0。类direct3d平台使用值为1(纹理顶部为0);类opengl平台使用0值(纹理顶部为1)。
UNITY_MIGHT_NOT_HAVE_DEPTH_Texture 定义平台是否可以通过手动将深度呈现到纹理中来模拟阴影映射或深度纹理。
UNITY_PROJ_COORD(a) 给定一个4分量向量,它返回一个适合于投影纹理读取的纹理坐标。在大多数平台上,这将直接返回传入参数的值。
UNITY_NEAR_CLIP_VALUE 定义为近切面的值。direct3d平台使用0.0,opengl平台使用-1.0。
UNITY_VPOS_TYPE 定义像素位置输入(VPOS)所需的数据类型:D3D9上的float2,其他地方的float4。
UNITY_CAN_COMPILE_TESSELLATION 当着色器编译器可用曲面细分着色器HLSL语法(目前只有D3D11)时定义。
UNITY_INITIALIZE_OUTPUT(type,name) 将给定类型的变量名初始化为零。
UNITY_COMPILER_HLSL,UNITY_COMPILER_HLSL2GLSL,UNITY_COMPILER_CG 指示使用哪个着色器编译器编译着色器——分别是:Microsoft的HLSL、HLSL到GLSL转换器和NVIDIA的Cg。有关更多细节,请参阅有关 shading Languages 的文档。如果您遇到处理编译器之间差异的非常特殊的着色器语法,并且希望为每个编译器编写不同的代码,那么可以使用这种方法。
UNITY_REVERSED_Z 定义在使用反向Z缓冲区的平台。存储的Z值在范围1…0而不是0…1。

Shadow mapping macros

阴影映射宏

定义与采样阴影贴图,在不同平台差别很大。Unity有一些宏可以辅助处理:

使用
UNITY_DECLARE_SHADOWMAP(tex) 声明一个名为“tex”的阴影贴图纹理变量。
UNITY_SAMPLE_SHADOW(tex,uv) 采样阴影贴图纹理“tex”在给定的“uv”坐标下(XY分量为纹理位置,Z分量为纹理深度用于比较)。返回float作为阴影因子0到1范围。
UNITY_SAMPLE_SHADOW_PROJ(tex,uv) 与上面类似,但是可以读取投影阴影映射。“uv”是一个float4,所有其他组件都除以.w进行采样。

注意:不是所有的显卡都支持shaodwmaps。使用 SystemInfo.SupportsRenderTextureFormat 来检测支持与否。

Constant buffer macros

常量缓存宏

Direct3D 11将所有着色器变量分组到"constant buffers"(常量缓冲区)中。多数Unity内置变量都已分类号了,但对于你自己的shader变量,根据更新的预期频率,最理想的还是将它们划分到constant buffers中。

使用 CBUFFER_START(name) 和 CBUFFER_END 宏:

CBUFFER_START(MyRarelyUpdatedVariables)
    float4 _SomeGlobalValue;
CBUFFER_END
           

Texture/Sampler declaration macros

纹理/采样器的宏定义

通常你使用 texture2D 在shader代码中成对定义一张纹理和采样器。然而某些平台(如:DX11),纹理和采样器都是对立的对象,且最大可采样器数量是非常有限的。Unity的一些宏定义了纹理,而没定义采样器,而采样一张纹理使用的采样器是来自另一种纹理的采样器。如果您最终遇到了采样器限制,并且您知道您的几个纹理实际上可以共享一个采样器(采样器定义纹理过滤和循环模式),那么可以使用这个功能。

使用
UNITY_DECLARE_TEX2D(name) 声明一个纹理和采样器对。
UNITY_DECLARE_TEX2D_NOSAMPLER(name) 声明一个没有采样器的纹理。
UNITY_DECLARE_TEX2DARRAY(name) 声明一个纹理数组采样器变量。
UNITY_SAMPLE_TEX2D(name,uv) 使用给定的纹理坐标从纹理和采样器对中采样。
UNITY_SAMPLE_TEX2D_SAMPLER(name,samplername,uv) 使用来自另一个纹理的samplername采样器来采样指定name纹理。
UNITY_SAMPLE_TEX2DARRAY(name,uv) 使用float3 UV从纹理数组中提取样本;坐标的z分量是数组元素索引。
UNITY_SAMPLE_TEX2DARRAY_LOD(name,uv,lod) 直接指定mipmap级别采样纹理数组。

了解更多相关信息,查看文档 Sampler States。

Surface Shader pass indicators

表面着色器pass的指示器

当Surface Shader被编译后,它们将生成许多不同的处理光照的pass代码。当编译每个pass,下面的宏列表中会有其一会变定义:

使用
UNITY_PASS_FORWARDBASE 正向渲染基础的PASS(主方向光,光照贴图,SH(球谐采样))。
UNITY_PASS_FORWARDADD 前向渲染叠加的PASS(每个光源有效时都将执行一次该PASS)。
UNITY_PASS_DEFERRED 延迟着色的PASS(渲染到G BUFFER)。
UNITY_PASS_SHADOWCASTER 阴影投影和深度纹理渲染的PASS。
UNITY_PASS_PREPASSBASE 旧版本的延迟照明的基础PASS(渲染法线和高光指数)。
UNITY_PASS_PREPASSFINAL 旧版本的延迟照明最终调整色调的PASS(应用于灯光和纹理)。

Disable Auto-Upgrade

禁止自动更新

UNITY_SHADER_NO_UPGRADE 允许你禁止Unity自动更新或修改你的shader文件。

See also

另请参阅

  • Built-in Shader include files
  • Built-in Shader variables
  • Vertex and Fragment program examples