Unity Shader - if 和 keyword 的指令比较

文章目录

  • 环境
  • TestingIf4Sample
    • [unity shaderlab 中的 TestingIf4Sample.shader](#unity shaderlab 中的 TestingIf4Sample.shader)
    • [graphics analyzer 中的 TestingIf4Sample.glsl](#graphics analyzer 中的 TestingIf4Sample.glsl)
  • TestingKW4Sample
    • [unity shaderlab 中的 TestingKW4Sample.shader](#unity shaderlab 中的 TestingKW4Sample.shader)
    • [graphics analyzer 中的 TestingKW4Sample.glsl](#graphics analyzer 中的 TestingKW4Sample.glsl)
  • 比较

环境

Unity : 2020.3.37f1

Pipeline : BRP


TestingIf4Sample

下面是 shaderlab 和 arm mobile studio 中的 graphics analyzer 的 glsl 代码


unity shaderlab 中的 TestingIf4Sample.shader

c 复制代码
// Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)

Shader "TestingIf4Sample"
{
    Properties
    {
        _A_Tex ("A Texture", 2D) = "white" {}
        _B_Tex ("B Texture", 2D) = "white" {}
        _USE_TEX_A ("Using Tex A", Float) = 1.0
    }
    SubShader
    {
        Tags
        {
            "Queue"="Geometry"
            "RenderType"="Opaque"
        }
        Pass
        {
            Name "Default"
        CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma target 2.0
            #include "UnityCG.cginc"
            struct appdata_t
            {
                float4 vertex   : POSITION;
                float2 texcoord : TEXCOORD0;
            };
            struct v2f
            {
                float4 vertex   : SV_POSITION;
                float2 texcoord  : TEXCOORD0;
            };
            sampler2D _A_Tex;
            sampler2D _B_Tex;
            fixed _USE_TEX_A;
            v2f vert(appdata_t v)
            {
                v2f OUT;
                float4 vPosition = UnityObjectToClipPos(v.vertex);
                OUT.vertex = vPosition;
                OUT.texcoord = v.texcoord.xy;
                return OUT;
            }
            fixed4 frag(v2f IN) : SV_Target
            {
                return _USE_TEX_A == 1.0 ? tex2D(_A_Tex, IN.texcoord) : tex2D(_B_Tex, IN.texcoord);
            }
        ENDCG
        }
    }
}

graphics analyzer 中的 TestingIf4Sample.glsl

VS

c 复制代码
#version 320 es

precision highp float;
precision highp int;
#define HLSLCC_ENABLE_UNIFORM_BUFFERS 1
#if HLSLCC_ENABLE_UNIFORM_BUFFERS
#define UNITY_UNIFORM
#else
#define UNITY_UNIFORM uniform
#endif
#define UNITY_SUPPORTS_UNIFORM_LOCATION 1
#if UNITY_SUPPORTS_UNIFORM_LOCATION
#define UNITY_LOCATION(x) layout(location = x)
#define UNITY_BINDING(x) layout(binding = x, std140)
#else
#define UNITY_LOCATION(x)
#define UNITY_BINDING(x) layout(std140)
#endif
uniform 	mediump float _USE_TEX_A;
UNITY_LOCATION(0) uniform mediump sampler2D _A_Tex;
UNITY_LOCATION(1) uniform mediump sampler2D _B_Tex;
in highp vec2 vs_TEXCOORD0;
layout(location = 0) out mediump vec4 SV_Target0;
vec4 u_xlat0;
bool u_xlatb0;
vec4 u_xlat1;
vec4 u_xlat2;
void main()
{
#ifdef UNITY_ADRENO_ES3
    u_xlatb0 = !!(_USE_TEX_A==1.0);
#else
    u_xlatb0 = _USE_TEX_A==1.0;
#endif
    u_xlat1 = texture(_A_Tex, vs_TEXCOORD0.xy);
    u_xlat2 = texture(_B_Tex, vs_TEXCOORD0.xy);
    u_xlat0 = (bool(u_xlatb0)) ? u_xlat1 : u_xlat2;
    SV_Target0 = u_xlat0;
    return;
}

FS

c 复制代码
#version 320 es

precision highp float;
precision highp int;
#define HLSLCC_ENABLE_UNIFORM_BUFFERS 1
#if HLSLCC_ENABLE_UNIFORM_BUFFERS
#define UNITY_UNIFORM
#else
#define UNITY_UNIFORM uniform
#endif
#define UNITY_SUPPORTS_UNIFORM_LOCATION 1
#if UNITY_SUPPORTS_UNIFORM_LOCATION
#define UNITY_LOCATION(x) layout(location = x)
#define UNITY_BINDING(x) layout(binding = x, std140)
#else
#define UNITY_LOCATION(x)
#define UNITY_BINDING(x) layout(std140)
#endif
uniform 	mediump float _USE_TEX_A;
UNITY_LOCATION(0) uniform mediump sampler2D _A_Tex;
UNITY_LOCATION(1) uniform mediump sampler2D _B_Tex;
in highp vec2 vs_TEXCOORD0;
layout(location = 0) out mediump vec4 SV_Target0;
vec4 u_xlat0;
bool u_xlatb0;
vec4 u_xlat1;
vec4 u_xlat2;
void main()
{
#ifdef UNITY_ADRENO_ES3
    u_xlatb0 = !!(_USE_TEX_A==1.0);
#else
    u_xlatb0 = _USE_TEX_A==1.0;
#endif
    u_xlat1 = texture(_A_Tex, vs_TEXCOORD0.xy);
    u_xlat2 = texture(_B_Tex, vs_TEXCOORD0.xy);
    u_xlat0 = (bool(u_xlatb0)) ? u_xlat1 : u_xlat2;
    SV_Target0 = u_xlat0;
    return;
}

TestingKW4Sample


下面是 shaderlab 和 glsl


unity shaderlab 中的 TestingKW4Sample.shader

c 复制代码
// Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)

Shader "TestingKW4Sample"
{
    Properties
    {
        _A_Tex ("A Texture", 2D) = "white" {}
        _B_Tex ("B Texture", 2D) = "white" {}
        [Toggle(_USE_TEX_A)]_USE_TEX_A ("Using Tex A", Float) = 1.0
    }
    SubShader
    {
        Tags
        {
            "Queue"="Geometry"
            "RenderType"="Opaque"
        }
        Pass
        {
            Name "Default"
        CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma target 2.0
            #pragma multi_compile _ _USE_TEX_A
            #include "UnityCG.cginc"
            struct appdata_t
            {
                float4 vertex   : POSITION;
                float2 texcoord : TEXCOORD0;
            };
            struct v2f
            {
                float4 vertex   : SV_POSITION;
                float2 texcoord  : TEXCOORD0;
            };
            sampler2D _A_Tex;
            sampler2D _B_Tex;
            v2f vert(appdata_t v)
            {
                v2f OUT;
                float4 vPosition = UnityObjectToClipPos(v.vertex);
                OUT.vertex = vPosition;
                OUT.texcoord = v.texcoord.xy;
                return OUT;
            }
            fixed4 frag(v2f IN) : SV_Target
            {
                #ifdef _USE_TEX_A
                    return tex2D(_A_Tex, IN.texcoord);
                #else
                    return tex2D(_B_Tex, IN.texcoord);
                #endif
            }
        ENDCG
        }
    }
}

graphics analyzer 中的 TestingKW4Sample.glsl

VS: 和上面的一样,就不复制上来的

主要看 FS:

c 复制代码
#version 320 es

precision highp float;
precision highp int;
#define UNITY_SUPPORTS_UNIFORM_LOCATION 1
#if UNITY_SUPPORTS_UNIFORM_LOCATION
#define UNITY_LOCATION(x) layout(location = x)
#define UNITY_BINDING(x) layout(binding = x, std140)
#else
#define UNITY_LOCATION(x)
#define UNITY_BINDING(x) layout(std140)
#endif
UNITY_LOCATION(0) uniform mediump sampler2D _A_Tex;
in highp vec2 vs_TEXCOORD0;
layout(location = 0) out mediump vec4 SV_Target0;
mediump vec4 u_xlat16_0;
void main()
{
    u_xlat16_0 = texture(_A_Tex, vs_TEXCOORD0.xy);
    SV_Target0 = u_xlat16_0;
    return;
}

比较

if 是指令实打实存在的

kw 原理是 macro 的 define,是在预编辑级别的分支,因此指令少一些也很正常

if 的推荐使用 记得是 if ... else ... 中 cycles 在 < 4 cycles 的,可以使用 if

否则还是使用 kw 的写法

下面的示例是 texture 的 sample,也就是 T unit 的采样

我印象中记得: (到时我再补回来,或是看到的大佬可以指导一下、分享一下资料)

  • register op: 1 cycles
  • sfu : 4~6 (忘记了)
  • texture sample : 300+ cyles

因此 T unit 优化是非常有必要的

相关推荐
Artistation Game1 天前
九、怪物行为逻辑
游戏·unity·游戏引擎
百里香酚兰1 天前
【AI学习笔记】基于Unity+DeepSeek开发的一些BUG记录&解决方案
人工智能·学习·unity·大模型·deepseek
dangoxiba1 天前
[Unity Demo]从零开始制作空洞骑士Hollow Knight第十三集:制作小骑士的接触地刺复活机制以及完善地图的可交互对象
游戏·unity·visualstudio·c#·游戏引擎
先生沉默先2 天前
使用Materialize制作unity的贴图,Materialize的简单教程,Materialize学习日志
学习·unity·贴图
十画_8242 天前
Visual Studio 小技巧记录
unity·visual studio
red_redemption2 天前
cpp,git,unity学习
git·unity·游戏引擎
tealcwu2 天前
【Unity踩坑】Unity更新Google Play结算库
unity·游戏引擎
先生沉默先2 天前
unity 默认渲染管线材质球的材质通道,材质球的材质通道
unity·游戏引擎·材质
白鹭float.2 天前
【Unity AI】基于 WebSocket 和 讯飞星火大模型
人工智能·websocket·unity
一个程序员(●—●)2 天前
Unity各个操作功能+基本游戏物体创建与编辑+Unity场景概念及文件导入导出
unity·游戏引擎