Shader "Custom/Gaussian Blur" {
Properties
{
_MainTex( "Base (RGB)" , 2D) = "white" {}
_BlurSize( "Blur Size" , Float) = 1.0
}
SubShader
{
//在SubShader 块中利用CGINCLUDE 和 ENDCG 来定义一系列代码
//这些代码不需要包含在Pass语义块中,在使用时,我们只需要在Pass中指定需要
//使用的顶点着色器和片元着色器函数名即可。
//使用CGINCLUDE可以避免我们编写两个完全一样的frag函数
CGINCLUDE
#include "UnityCG.cginc"
sampler2D _MainTex;
half4 _MainTex_TexelSize;
float _BlurSize;
struct v2f
{
float4 pos : SV_POSITION;
half2 uv[5]: TEXCOORD0;
};
//利用5x5大小的高斯核对原图像进行高斯模糊。一个5x5的二维高斯核可以拆分成两个大小为5的一维高斯核,因此我们只需要计算5个纹理坐标即可。
v2f vertBlurVertical(appdata_img v)
{
v2f o;
o.pos = mul(UNITY_MATRIX_MVP, v.vertex);
half2 uv = v.texcoord;
//第一个坐标存储了当前的采样纹理。
o.uv[0] = uv;
//剩余四个坐标则是高斯模糊中对邻域采样时使用的纹理坐标。和属性_BlurSize相乘来控制采样距离。
o.uv[1] = uv + float2(0.0, _MainTex_TexelSize.y * 1.0) * _BlurSize;
o.uv[2] = uv - float2(0.0, _MainTex_TexelSize.y * 1.0) * _BlurSize;
o.uv[3] = uv + float2(0.0, _MainTex_TexelSize.y * 2.0) * _BlurSize;
o.uv[4] = uv - float2(0.0, _MainTex_TexelSize.y * 2.0) * _BlurSize;
return o;
}
v2f vertBlurHorizontal(appdata_img v)
{
v2f o;
o.pos = mul(UNITY_MATRIX_MVP, v.vertex);
half2 uv = v.texcoord;
o.uv[0] = uv;
o.uv[1] = uv + float2(_MainTex_TexelSize.x * 1.0, 0.0) * _BlurSize;
o.uv[2] = uv - float2(_MainTex_TexelSize.x * 1.0, 0.0) * _BlurSize;
o.uv[3] = uv + float2(_MainTex_TexelSize.x * 2.0, 0.0) * _BlurSize;
o.uv[4] = uv - float2(_MainTex_TexelSize.x * 2.0, 0.0) * _BlurSize;
return o;
}
//一个5x5的二维高斯核可以拆分成两个大小为5的一维高斯核,由于对称性,我们只需要记录3个高斯权重(weight)。
fixed4 fragBlur(v2f i) : SV_Target
{
float weight[3] = { 0.4026, 0.2442, 0.0545 };
//将结果值sum初始化为当前的像素值乘以权重值。
fixed3 sum = tex2D(_MainTex, i.uv[0]).rgb * weight[0];
for ( int it = 1; it < 3; it++) {
sum += tex2D(_MainTex, i.uv[it * 2 - 1]).rgb * weight[it];
sum += tex2D(_MainTex, i.uv[it * 2]).rgb * weight[it];
}
return fixed4(sum, 1.0);
}
ENDCG
ZTest Always Cull Off ZWrite Off
Pass {
NAME "GAUSSIAN_BLUR_VERTICAL"
CGPROGRAM
#pragma vertex vertBlurVertical
#pragma fragment fragBlur
ENDCG
}
Pass {
NAME "GAUSSIAN_BLUR_HORIZONTAL"
CGPROGRAM
#pragma vertex vertBlurHorizontal
#pragma fragment fragBlur
ENDCG
}
}
FallBack Off
}
|