unityShader屏幕后期效果-运动模糊

运动模糊的实现有很多种方法。
一种方法是利用一块累积缓存(accumulation buffer)来混和多张连续的图像,当物体快速移动产生多张图像后,我们取最后的平均值作为最后的运动模糊图像,但是这种做法意味着在同一帧渲染多次场景,会造成很大的消耗。
另一种方法是创建和使用速度缓存(velocity buffer)这个缓存存储了各个像素当前的运动速度,利用该值决定模糊的方向和大小

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class MotionBlur : PostEffectsBase
{
    public Shader motionBlurShader;
    private Material motionBlurMaterial = null;
    public Material material
    {
        get
        {
            motionBlurMaterial = CheckShaderAndCreateMaterial(motionBlurShader, motionBlurMaterial);
            return motionBlurMaterial;
        }
    }
    //运动模糊在混合图像时使用的模糊参数
    [Range(0.0f, 0.9f)]
    public float blurAmount = 0.5f;
    //保存之前图像叠加的效果
    private RenderTexture accumulationTexture;
    private void OnDisable()
    {
        DestroyImmediate(accumulationTexture);
    }

    void OnRenderImage(RenderTexture source, RenderTexture destination)
    {
        if (material != null)
        {
            if (accumulationTexture == null ||
                accumulationTexture.width != source.width ||
                accumulationTexture.height != source.height)
            {
                DestroyImmediate(accumulationTexture);
                accumulationTexture = new RenderTexture(source.width, source.height, 0);
                //即这个变量不会显示在Hierarchy,也不会保存
                accumulationTexture.hideFlags = HideFlags.HideAndDontSave;
                Graphics.Blit(source, accumulationTexture);
            }
            //恢复操作
            accumulationTexture.MarkRestoreExpected();
            material.SetFloat("_BlurAmount", 1.0f - blurAmount);
            Graphics.Blit(source, accumulationTexture, material);
            Graphics.Blit(accumulationTexture, destination);
        }
        else
        {
            Graphics.Blit(source,destination);
        }
    }
}
Shader "Hidden/MotionBlur"
{
    Properties
    {
        _MainTex ("Texture", 2D) = "white" {}
		_BlurAmount("Blur Amount",float) = 1.0
	}
		SubShader
		{

			CGINCLUDE
			 #include "UnityCG.cginc"
			sampler2D _MainTex;
		    fixed _BlurAmount;
			struct v2f
			{
				half2 uv : TEXCOORD0;
				float4 pos : SV_POSITION;	
		     };
			v2f vert(appdata_img v)
			{
				v2f o;
				o.pos = UnityObjectToClipPos(v.vertex);
				o.uv = v.texcoord;
				return o;
			}
			fixed4 fragRGB(v2f i) : SV_Target
			{
			return fixed4(tex2D(_MainTex,i.uv).rgb,_BlurAmount);
			}
			half4 fragA(v2f i) : SV_Target
			{
			return tex2D(_MainTex,i.uv);
			}
		ENDCG
		ZTest Always  Cull Off ZWrite Off
        Pass
        {
			Blend SrcAlpha OneMinusSrcAlpha
			ColorMask RGB
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment fragRGB           
            ENDCG
        }
			Pass
			{
				Blend One Zero
				ColorMask A
				CGPROGRAM
				#pragma vertex vert
				#pragma fragment fragA          
				ENDCG
			}
    }
			Fallback  Off
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值