透明效果(八)--模板测试实现透明效果

【本系列文章系学习 唐福幸《Unity ShaderLab 新手宝典》的笔记,包含个人理解,如有错误欢迎批评指出

透明效果

最终效果:
在这里插入图片描述

7.5 模板测试

在B物体上挖一个洞,形状是A物体的轮廓,所以要分别给A,B物体写脚本
A物体脚本:

Shader "Chapter7/Shader756A"
{
    SubShader
    {
        Tags { "Queue"="Geometry-1" }
        pass
        {
            Stencil
            {
                Ref 1    // 参照值,用来与缓存中已经存在的模板值进行比较的数值
                Comp Always  // 将参照值与模板值进行比较的方法,默认always
                Pass Replace  // 如果模板测试和深度测试都通过,当前像素的参照值写进缓存
            }

            // 只是为了传递轮廓,所以屏蔽所有颜色输出
            ColorMask 0
            ZWrite Off //关闭深度写入,关闭深度测试,如果关闭深度测试,颜色会被过滤掉

            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag

            float4 vert(in float4 vertex : POSITION) : SV_POSITION
            {
                float4 pos = UnityObjectToClipPos(vertex);//把模型坐标转换成裁切坐标
                return pos;
            }

            void frag(out fixed4 color : SV_Target)
            {
                color = fixed4(1,1,1,1);
            }
            ENDCG
        }        
    }
}

B物体脚本

Shader "Chapter7/Shader756B"
{
    Properties
    {
    //在B物体上挖一个洞,形状是A物体的轮廓,所以要分别给A,B物体写脚本
        _MainColor ("Main Color", Color) = (1,1,1,1)
        _MainTex ("Texture", 2D) = "white" {}
    }
    SubShader
    {
        Tags { "Queue"="Geometry" }

        Pass
        {
            Tags {"LightMode" = "ForwardBase"}//前向渲染
            Stencil
            {
                Ref 1
                Comp NotEqual//当和物体A的缓存值不相等的时候,再渲染
                Pass Keep//保持缓存中的模板值
            }
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag

            #include "UnityCG.cginc"
            #include "UnityLightingCommon.cginc"

            struct v2f
            {
                float4 worldPos : TEXCOORD0;
                float4 pos : SV_POSITION;
                float3 worldNormal : TEXCOORD1;
                float2 texcoord : TEXCOORD2;
            };

            sampler2D _MainTex;
            float4 _MainTex_ST;
            fixed4 _MainColor;

            v2f vert (appdata_base v)
            {
                v2f o;
                o.pos = UnityObjectToClipPos(v.vertex);
                o.worldPos = mul(unity_ObjectToWorld, v.vertex);//把v的顶点模型坐标转换成世界坐标

                //float3 worldNormal = ;
                o.worldNormal = normalize(UnityObjectToWorldNormal(v.normal));//把v的法线坐标转换成世界坐标
                o.texcoord = TRANSFORM_TEX(v.texcoord, _MainTex);//拿顶点的uv去和材质球的tiling和offset作运算,确保缩放和偏移
                return o;
            }

            fixed4 frag (v2f i) : SV_Target
            {
                float3 worldLight = UnityWorldSpaceLightDir(i.worldPos.xyz);//输入世界空间中的顶点坐标,返回世界空间中从该点到光源光照方向
                worldLight = normalize(worldLight);
                fixed NdotL = saturate(dot(i.worldNormal,worldLight));//saturate(x):如果x取值小于0,则返回值为0
                
                fixed4 color = tex2D(_MainTex,i.texcoord);//对贴图进行逐点采样,将rgb提取出来
                color.rgb *= _MainColor * NdotL * _LightColor0.rgb;//将贴图颜色和灯光颜色进行混合
                color.rgb += unity_AmbientSky.rgb;//再引入环境光颜色

                return color;
            }
            ENDCG
        }
    }
}

实现步骤:

在这里插入图片描述

  1. 创建一个胶囊体,位置归0,绑定带有A脚本的材质
  2. 创建一个正方体,位置归0,绑定带有B脚本的材质
  3. 在胶囊体后面放一个物体作为是否透明的参考
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值