Unity Shader之动态阴影
2017-08-29 11:59
381 查看
动态阴影在Unity中,默认是使用ShadowMap,原理是通过生成投影深度图来比较,但是由于在移动平台对深度浮点值计算的限制,使得ShadowMap技术在移动平台要么效果不理想,要么需要消耗大量的计算。
所以常见的处理移动平台阴影的方式是使用RenderTexture + 投影,如王者荣耀中的实时阴影。
具体的方式是先渲染一张RenderTexture,这张RenderTexture包含了要显示阴影的对象,可以通过Layer设置,来剔除不显示阴影的对象。然后将这张RenderTexture设置给投影和材质。
第一步:
创建一个GameObject,上面添加Projector组件和Camera组件,两个组件和参数设置成一样,最好是使用正交方式。
Camera的clear flag设置为Solid,显示为白色,Camera的Layer mask只设置要生成阴影的那个层级
Projector 的Ignore layers设置来和 Camera的Layer mask一样,目的是投影不要投到了角色身上。
第二步:
创建一张RenderTexture,当然你也可以通过代码来创建,我这里是直接在unity中创建的,大小256*256,如果不够清晰,可以设置到512,格式设置为RGB565,Warp Mode为Clamp,Filter Mode为Bilinear。
将这张RenderTexture设置给上面的Camera
第三步:
创建一个Shader,用于渲染成RenderTexture,最简单的Shader就行
再创建一个Shader,用于显示投影
创建一个材质,给它添加Projector/Multiply这个Shader,然后把这个材质拖到投影的材质处。
最后一步:
编写脚本,主要用于通过自定义的shader来生成一张RenderTexture
public Projector proj;
public Camera projCam;
public Shader shadowShader;
// Use this for initialization
void Start () {
projCam.enabled = false;
}
// Update is called once per frame
void LateUpdate () {
if(proj && projCam){
projCam.aspect = proj.aspectRatio;
projCam.RenderWithShader(shadowShader,null);
}
}
总结:主要步骤,就是通过一个单独的相机渲染一张RenderTexture给投影,投影再将这张RenderTexture投到地面上。
但是有一定的局限,要投影的物品穿过了地面,投影计算也会计算地面以下的,最后显示出来就有错。
所以常见的处理移动平台阴影的方式是使用RenderTexture + 投影,如王者荣耀中的实时阴影。
具体的方式是先渲染一张RenderTexture,这张RenderTexture包含了要显示阴影的对象,可以通过Layer设置,来剔除不显示阴影的对象。然后将这张RenderTexture设置给投影和材质。
第一步:
创建一个GameObject,上面添加Projector组件和Camera组件,两个组件和参数设置成一样,最好是使用正交方式。
Camera的clear flag设置为Solid,显示为白色,Camera的Layer mask只设置要生成阴影的那个层级
Projector 的Ignore layers设置来和 Camera的Layer mask一样,目的是投影不要投到了角色身上。
第二步:
创建一张RenderTexture,当然你也可以通过代码来创建,我这里是直接在unity中创建的,大小256*256,如果不够清晰,可以设置到512,格式设置为RGB565,Warp Mode为Clamp,Filter Mode为Bilinear。
将这张RenderTexture设置给上面的Camera
第三步:
创建一个Shader,用于渲染成RenderTexture,最简单的Shader就行
Shader "Unlit/Shadow" { Properties { _ShadowColor ("Main Color", COLOR) = (0.5, 0.5, 0.5, 1) } SubShader { Pass { Color [_ShadowColor] } } }
再创建一个Shader,用于显示投影
Shader "Projector/Multiply" { Properties { _ShadowTex ("Cookie", 2D) = "gray" { TexGen ObjectLinear } _FalloffTex ("FallOff", 2D) = "white" { TexGen ObjectLinear } } Subshader { Tags { "RenderType"="Transparent-1" } Pass { ZWrite Off Fog { Color (1, 1, 1) } AlphaTest Less 1 ColorMask RGB Blend DstColor Zero Offset -1, -1 CGPROGRAM #pragma vertex vert #pragma fragment frag #pragma fragmentoption ARB_precision_hint_fastest #include "UnityCG.cginc" struct v2f { float4 pos : SV_POSITION; float4 uv_Main : TEXCOORD0; float4 uv_Clip : TEXCOORD1; }; sampler2D _ShadowTex; sampler2D _FalloffTex; float4x4 unity_Projector; float4x4 unity_ProjectorClip; v2f vert(appdata_tan v) { v2f o; o.pos = UnityObjectToClipPos (v.vertex); o.uv_Main = mul (unity_Projector, v.vertex); o.uv_Clip = mul (unity_ProjectorClip, v.vertex); return o; } half4 frag (v2f i) : COLOR { half4 tex = tex2Dproj(_ShadowTex, i.uv_Main); half4 falloff = tex2D(_FalloffTex, i.uv_Clip.xy); tex = lerp(float4(1,1,1,1),tex,falloff.a); return tex; } ENDCG } } }
创建一个材质,给它添加Projector/Multiply这个Shader,然后把这个材质拖到投影的材质处。
最后一步:
编写脚本,主要用于通过自定义的shader来生成一张RenderTexture
public Projector proj;
public Camera projCam;
public Shader shadowShader;
// Use this for initialization
void Start () {
projCam.enabled = false;
}
// Update is called once per frame
void LateUpdate () {
if(proj && projCam){
projCam.aspect = proj.aspectRatio;
projCam.RenderWithShader(shadowShader,null);
}
}
总结:主要步骤,就是通过一个单独的相机渲染一张RenderTexture给投影,投影再将这张RenderTexture投到地面上。
但是有一定的局限,要投影的物品穿过了地面,投影计算也会计算地面以下的,最后显示出来就有错。
相关文章推荐
- Unity优化大全(六)之 GPU-动态阴影和Shader
- Unity优化大全(五)之 GPU-动态阴影和Shader
- Unity优化大全(六)之 GPU-动态阴影和Shader
- Unity里vertexShader里压扁模型来实现比较low的阴影
- Unity shader学习之Alpha Test的阴影
- 【Unity3D】利用Shader以及更改Mesh实现2D游戏的动态阴影效果
- Unity Shader Forge学习笔记(一):只显示阴影的shader
- UnityShader之创建动态纹理
- unity在定制的shader里面如何添加阴影
- UnityShader中级篇——使物体接受阴影
- unity 动态改变所有子物体的shader
- Unity移动端动态阴影总结
- Unity 2D Toolkit中动态改变Animated Sprite的Shader
- unity里面动态的替换shader
- Unity Shader特效——人物模型动态光特效
- Unity移动端动态阴影
- Unity shader学习之阴影
- Unity Shader 学习笔记(14) 阴影
- 【Unity Shader】结合Projector和Rendertexture实现实时阴影
- Unity 实时 半透明 阴影 shader