Unity3D Shader 之透视效果XRay
2024-01-07 21:13:47
    		
1、
Shader "Unlit/XRay"
{
	Properties
	{
		_MainTex("Texture", 2D) = "white" {}
	// 漫反射
	_Diffuse("Diffuse", COLOR) = (1,1,1,1)
		// XRay 效果
		_XRayColor("XRay Color", COLOR) = (0,1,1,1)
		_XRayPower("XRay Power", Range(0.00001,3)) = 0.001
	}
		SubShader
	{
		Tags { "Queue" = "Geometry+1000" "RenderType" = "Opaque" }
		LOD 100
		Pass
		{
		Stencil {
				Ref 254
				Comp Always
				Pass Replace
				ZFail Keep
			}
			CGPROGRAM
			#pragma vertex vert
			#pragma fragment frag
			#include "UnityCG.cginc"
			#include "Lighting.cginc"
			struct v2f
			{
				float4 vertex : SV_POSITION;
		float2 uv : TEXCOORD0;
		float3 worldNormal:TEXCOORD1;
		float3 worldPos:TEXCOORD2;
			};
			sampler2D _MainTex;
			float4 _MainTex_ST;
			float4 _Diffuse;
		float _Steps;
		float _ToonLerpWeight;
		float4 _RimColor;
		float _RimPower;
			v2f vert(appdata_base v)
			{
				v2f o;
				o.vertex = UnityObjectToClipPos(v.vertex);
				o.worldNormal = UnityObjectToWorldNormal(v.normal);
				o.worldPos = mul(unity_ObjectToWorld,v.vertex);
				o.uv = TRANSFORM_TEX(v.texcoord,_MainTex);
				return o;
			}
			fixed4 frag(v2f i) : SV_Target
			{
				// 环境光
				float3 ambient = UNITY_LIGHTMODEL_AMBIENT;
				// 贴图的本色
				fixed3 albedo = tex2D(_MainTex, i.uv).rgb;
				// 视野方向
				float3 viewDir = normalize(UnityWorldSpaceViewDir(i.worldPos));
				// 漫反射
				fixed3 worldLightDir = UnityWorldSpaceLightDir(i.worldPos);
				float halfLambert = dot(worldLightDir,i.worldNormal) * 0.5 + 0.5;
				// 最终漫反射
				fixed3 diffuse = _LightColor0.rgb * albedo * _Diffuse.rgb * halfLambert;
				return fixed4(ambient + diffuse,1);
			}
			ENDCG
		}
		Pass{
			Tags{"ForceNoShadowCasting" = "true"}
			Name "XRay"
				// 添加 混合效果 注意渲染顺序 Queue
				Blend SrcAlpha one
				// 关闭深度写入
				ZWrite off
				ZTest Greater  // 表示大于的时候显示(目的显示墙后面的物体)
				//使用Stencil进行过滤,该Shader的第一个Pass中我们向Stencil Buffer中写入一个值254,在Xray的pass中,如果stencil的值为254,则不再绘制效果
				Stencil {
					Ref 254
					Comp NotEqual
					Pass Keep
					ZFail Keep
				}
				CGPROGRAM
				#pragma vertex vert
				#pragma fragment frag
				#include "UnityCG.cginc"
				float4 _XRayColor;
				float _XRayPower;
				struct v2f {
					float4 vertex :SV_POSITION;
					//方法一,得到世界点,再到片元中计算视野方向
					//float3 worldPos:TEXCOORD0;
					//float3 worldNormal:TEXCOORD1;
					//方法二,放在Object空间下计算
					float3 viewDir:TEXCOORD0;
					float3 normal:TEXCOORD1;
				};
				v2f vert(appdata_base v) {
					v2f o;
					o.vertex = UnityObjectToClipPos(v.vertex);
					// 方法一,得到世界点,再到片元中计算视野方向
					//o.worldNormal = UnityObjectToWorldNormal(v.normal);
					//o.worldPos = mul(unity_ObjectToWorld,v.vertex);
					// 方法二,把视野方向在模型中就计算出来
					//o.worldNormal = UnityObjectToWorldNormal(v.normal);
					o.viewDir = ObjSpaceViewDir(v.vertex);
					o.normal = v.normal;
					return o;
				}
				float4 frag(v2f i) :SV_Target{
					/// 通过视野方向和世界法线方向求得边沿(视野方向和世界法线方向 垂直为边缘)
					// 方法一,得到世界点,再到片元中计算视野方向
					//float3 worldNormal = normalize(i.worldNormal);
					//float3 viewDir = normalize(UnityWorldSpaceViewDir(i.worldPos));
					// 方法二,把视野方向在模型中就计算出来
					float3 worldNormal = normalize(i.normal);
					float3 viewDir = normalize(i.viewDir);
					// 边缘
					float rim = 1 - dot(worldNormal,viewDir);  // 1- 让边沿为 1
					return _XRayColor * pow(rim,1 / _XRayPower);
				}
				ENDCG
			}
	}
		FallBack "Diffuse"
}2、
Shader "Unity/XRay"
{
    Properties
    {
        _MainTex("Texture", 2D) = "white" {}
        _Diffuse("Color",Color) = (1,1,1,1)
        _XRayColor("XRayColor",Color) = (1,1,1,1)
        _XRayPower("XRayPower",float) = 0
    }
        SubShader
        {
            Tags {"Queue" = "Geometry+1000" "RenderType" = "Opaque" }
            LOD 100
            //Xray效果
            Pass
            {
                Name "Xray"
                //忽略阴影,半透明物体不需要阴影,可开启此功能
                Tags{ "ForceNoShadowCasting" = "true" }
            //开启混合
            Blend SrcAlpha One
            //不进行任何颜色信息写入
            ZWrite Off
            //大于深度缓冲池中的颜色深度的片元才进行处理 其他的全部舍弃
            ZTest Greater
            CGPROGRAM
            #pragma vertex vert 
            #pragma fragment frag 
            #include "UnityCG.cginc"
            #include "Lighting.cginc"
            float4 _XRayColor;
            float _XRayPower;
            struct v2f
            {
                float4 vertex:SV_POSITION;
                float3 normal:TEXCOORD0;
                float3 viewDir:TEXCOORD1;
            };
            v2f vert(appdata_base v)
            {
                v2f o;
                o.vertex = UnityObjectToClipPos(v.vertex);
                o.normal = v.normal;
                o.viewDir = ObjSpaceViewDir(v.vertex);
                return o;
            };
            fixed4 frag(v2f i) :SV_TARGET
            {
                float3 NormalDir = normalize(i.normal);
                float3 ViewDir = normalize(i.viewDir);
                float rim = 1 - saturate(dot(NormalDir,ViewDir));
                float4 rimColor = _XRayColor * pow(rim,1 / _XRayPower);
                return rimColor;
            };
            ENDCG
        }
            //正常的漫反射渲染
            Pass
            {
                CGPROGRAM
                #pragma vertex vert
                #pragma fragment frag 
                #include "UnityCG.cginc"
                #include "Lighting.cginc"
                sampler2D _MainTex;
                float4 _MainTex_ST;
                float3 _Diffuse;
                struct v2f
                {
                    float4 vertex:SV_POSITION;
                    float2 uv:TEXCOORD0;
                    float3 worldPos:TEXCOORD1;
                    float3 worldNormal:TEXCOORD2;
                };
                v2f vert(appdata_base v)
                {
                    v2f o;
                    o.vertex = UnityObjectToClipPos(v.vertex);
                    o.uv = TRANSFORM_TEX(v.texcoord,_MainTex);
                    o.worldPos = mul(unity_ObjectToWorld,v.vertex);
                    o.worldNormal = UnityObjectToWorldNormal(v.normal);
                    return o;
                };
                fixed4 frag(v2f i) :SV_TARGET
                {
                    float3 worldNormalDir = normalize(i.worldNormal);
                    float3 WorldLightDir = normalize(UnityWorldSpaceLightDir(i.worldNormal));
                    float3 texColor = tex2D(_MainTex,i.uv);
                    float3 ambient = UNITY_LIGHTMODEL_AMBIENT.rgb * texColor.rgb;
                    float3 diffuse = _LightColor0.rgb * _Diffuse.rgb * texColor.rgb * (dot(worldNormalDir,WorldLightDir) * 0.5 + 0.5);
                    float3 color = diffuse + ambient;
                    return fixed4(color,1);
                };
                ENDCG
           }
        }
            Fallback "Diffuse"
}3、Highlight Plus - All in One Outline & Selection Effects
Highlight Plus - All in One Outline & Selection Effects | VFX Shaders | Unity Asset Store
    			文章来源:https://blog.csdn.net/yangzhen_010/article/details/135385543
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。 如若内容造成侵权/违法违规/事实不符,请联系我的编程经验分享网邮箱:veading@qq.com进行投诉反馈,一经查实,立即删除!
    	本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。 如若内容造成侵权/违法违规/事实不符,请联系我的编程经验分享网邮箱:veading@qq.com进行投诉反馈,一经查实,立即删除!