这里需要3个脚本1.脚本部分
后处理脚本主要做的是两件事,第一件是获取需要的shader,生成材质,第二件是通过OnRenderImage使用材质处理屏幕效果。第一步具有一些普遍性,不管是什么后处理效果,都要有这一步相同的操作,所以我们将该步骤抽离出来,创建一个后处理效果的基类PostEffectBase,代码如下 1. - using UnityEngine;
- using System.Collections;
-
- //非运行时也触发效果
- [ExecuteInEditMode]
- //屏幕后处理特效一般都需要绑定在摄像机上
- [RequireComponent(typeof(Camera))]
- //提供一个后处理的基类,主要功能在于直接通过Inspector面板拖入shader,生成shader对应的材质
- public class PostEffectBase : MonoBehaviour {
-
- //Inspector面板上直接拖入
- public Shader shader = null;
- private Material _material = null;
- public Material _Material
- {
- get
- {
- if (_material == null)
- _material = GenerateMaterial(shader);
- return _material;
- }
- }
-
- //根据shader创建用于屏幕特效的材质
- protected Material GenerateMaterial(Shader shader)
- {
- if (shader == null)
- return null;
- //需要判断shader是否支持
- if (shader.isSupported == false)
- return null;
- Material material = new Material(shader);
- material.hideFlags = HideFlags.DontSave;
- if (material)
- return material;
- return null;
- }
-
- }
C#脚本 - using UnityEngine;
- using System.Collections;
-
- [ExecuteInEditMode]
- public class DepthTextureTest : PostEffectBase
- {
- void OnEnable()
- {
- GetComponent<Camera>().depthTextureMode |= DepthTextureMode.Depth;
- }
-
- void OnDisable()
- {
- GetComponent<Camera>().depthTextureMode &= ~DepthTextureMode.Depth;
- }
-
- void OnRenderImage(RenderTexture source, RenderTexture destination)
- {
- if (_Material)
- {
- Graphics.Blit(source, destination, _Material);
- }
- }
- }
shader部分: - Shader "Custom/DepthTest" {
-
- CGINCLUDE
- #include "UnityCG.cginc"
-
- //仍然要声明一下_CameraDepthTexture这个变量,虽然Unity这个变量是unity内部赋值
- sampler2D _CameraDepthTexture;
- sampler2D _MainTex;
- float4 _MainTex_TexelSize;
-
- struct v2f
- {
- float4 pos : SV_POSITION;
- float2 uv : TEXCOORD0;
- };
-
- v2f vert(appdata_img v)
- {
- v2f o;
- o.pos = mul(UNITY_MATRIX_MVP, v.vertex);
- o.uv.x=1-v.texcoord.x;//x轴对称
- o.uv.y=v.texcoord.y;
-
- return o;
- }
-
- fixed4 frag(v2f i) : SV_Target
- {
- //直接根据UV坐标取该点的深度值
- float depth = SAMPLE_DEPTH_TEXTURE(_CameraDepthTexture, 1 - i.uv);
- //将深度值变为线性01空间
- //靠近摄像机的白,远离的黑
- depth = 1-Linear01Depth(depth);
- return float4(depth, depth, depth, 1);
- }
-
- ENDCG
-
- SubShader
- {
- Pass
- {
-
- ZTest Off
- Cull Off
- ZWrite Off
- Fog{ Mode Off }
-
- CGPROGRAM
- #pragma vertex vert
- #pragma fragment frag
- ENDCG
- }
-
- }
- }
找一个场景,将该脚本挂在摄像机并赋予材质。(注:PostEffectBase类为后处理基类,在之前的文章中有详细实现,此处不予贴出),找到一个场景,我们测试一下:
这张图中,我把摄像机的远裁剪面调整到了50这一比较小的距离,这样,图中的远近信息显示得更加明显
|