unity3d软阴影和硬阴影的原理_【Unity Shader】平面阴影(Planar Shadow)
时间: 2023-06-24 07:09:26 浏览: 387
Unity3D中的软阴影和硬阴影都是基于光线跟踪的原理实现的,但实现方式有所不同。
软阴影:
软阴影的实现方式是通过在物体表面渲染一个半透明的阴影贴图来模拟光线的散射。首先需要将阴影贴图投射到场景中,然后在每个像素处计算出该像素被阴影覆盖的比例,最终将该比例用于混合原始颜色和阴影颜色。
硬阴影:
硬阴影的实现方式是通过在场景中投射光线,并根据光线是否与物体相交来判断物体是否处于阴影中。如果物体被阴影遮挡,则将该物体的颜色设为阴影颜色。这种方式相比软阴影更加真实,但也更加计算密集。
平面阴影:
平面阴影是一种特殊的阴影效果,可以模拟物体在平面上的投影。实现方式是首先计算出物体到平面的投影矩阵,然后将该矩阵应用到阴影贴图中,最终将阴影贴图与场景混合,即可实现平面阴影效果。
相关问题
unity 假阴影shader
以下是一种Unity假阴影Shader的实现方式:
```shader
Shader "Custom/FakeShadow" {
Properties {
_MainTex ("Texture", 2D) = "white" {}
_ShadowColor ("Shadow Color", Color) = (0, 0, 0, 0.5)
_ShadowOffset ("Shadow Offset", Range(0, 0.1)) = 0.01
}
SubShader {
Tags {"Queue"="Transparent" "RenderType"="Transparent"}
LOD 100
Pass {
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct appdata {
float4 vertex : POSITION;
float2 uv : TEXCOORD0;
};
struct v2f {
float2 uv : TEXCOORD0;
float4 vertex : SV_POSITION;
};
sampler2D _MainTex;
float4 _MainTex_ST;
float _ShadowOffset;
float4 _ShadowColor;
v2f vert (appdata v) {
v2f o;
o.vertex = UnityObjectToClipPos(v.vertex);
o.uv = TRANSFORM_TEX(v.uv, _MainTex);
return o;
}
fixed4 frag (v2f i) : SV_Target {
// 计算阴影纹理坐标
float2 shadowUV = i.uv - float2(_ShadowOffset, _ShadowOffset);
// 获取阴影纹理颜色
fixed4 shadowColor = tex2D(_MainTex, shadowUV);
// 计算最终颜色
fixed4 col = tex2D(_MainTex, i.uv);
col.rgb *= shadowColor.r;
col.rgb += _ShadowColor.rgb * (1 - shadowColor.r);
col.a *= shadowColor.r;
return col;
}
ENDCG
}
}
FallBack "Diffuse"
}
```
该Shader的实现方式是在原有的纹理上叠加一层阴影纹理,通过计算阴影纹理的颜色来实现假阴影的效果。其中,阴影纹理的坐标需要进行偏移,以避免阴影和物体重叠。用户可以通过修改_ShadowOffset属性来调整阴影的偏移量,通过修改_ShadowColor属性来调整阴影的颜色。
unity shader 镂空阴影
Unity的镂空阴影需要借助于Shader来实现。首先需要在模型的material中利用Shader进行渲染。常用的Shader包括Unlit/Transparent Cutout,Unlit/Transparent和Standard。
然后,在Shader中利用ZTest和ZWrite两个属性来控制阴影的显示。其中,ZTest参数用于控制深度测试,取值为“LessEqual”时表示只有深度小于等于当前像素深度时才通过测试;ZWrite参数用于控制深度写入,取值为“Off”时表示不进行深度写入,从而实现阴影的镂空效果。
具体实现可以参考以下代码片段:
Shader "Custom/CutoutShadow" {
Properties {
_Color ("Color", Color) = (1,1,1,1)
_MainTex ("Albedo (RGB)", 2D) = "white" {}
_Cutoff ("Alpha Cutoff", Range(0,1)) = 0.5
}
SubShader {
Tags { "Queue"="Transparent" "RenderType"="Transparent" }
LOD 100
Pass {
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include "UnityCG.cginc"
struct appdata {
float4 vertex : POSITION;
float2 uv : TEXCOORD0;
};
struct v2f {
float2 uv : TEXCOORD0;
float4 vertex : SV_POSITION;
};
sampler2D _MainTex;
float4 _MainTex_ST;
float4 _Color;
float _Cutoff;
v2f vert (appdata v) {
v2f o;
o.vertex = UnityObjectToClipPos(v.vertex);
o.uv = TRANSFORM_TEX(v.uv, _MainTex);
return o;
}
fixed4 frag (v2f i) : SV_Target {
fixed4 col = tex2D(_MainTex, i.uv) * _Color;
clip(col.a - _Cutoff);
return col;
}
ENDCG
}
}
FallBack "Diffuse"
}
其中,_Cutoff参数用于控制阴影的透明度阈值,取值越大表示模型的透明部分越少,反之越多。