UI特效裁剪

NGUI中并没有提供特效裁剪的功能,这个需要我们自己实现了。
不过实现起来也容易。
我们先来看一下,NGUI的裁剪原理(这里我就不写了,直接上链接)
https://blog.csdn.net/tkokof1/article/details/52089289
知道裁剪原理之后我们自己就可以仿照NGUI的做法,将panel的裁剪信息传到特效Shader中实现裁剪,你完全可以不参考这种方式自己实现。
这里我只是实现了一个父panel的裁剪,多个panel的话就会出现不正确,不过一般情况下不会出panel之间交叉裁剪。

脚本代码

using UnityEngine;
using System.Collections;

public class UIParticalClip : MonoBehaviour
{

    private UIPanel mPanel;
    private Renderer[] mSenderers;
    private bool mRefresh = false;
    void Start()
    {
        mRefresh = false;
        mPanel = gameObject.GetComponentInParent<UIPanel>();
        mSenderers = gameObject.GetComponentsInChildren<Renderer>();

        if (mPanel != null)
        {
            mPanel.onClipMove += SetClip;
        }
    }

    void Update()
    {
        if (mRefresh == false)
        {
            mRefresh = true;
            SetClip(mPanel);
        }
    }

    void SetClip(UIPanel panel)
    {
        if (panel == null)
        {
            return;
        }
        if (mSenderers == null)
        {
            return;
        }
        Vector2 soft = panel.clipSoftness;

        var panelWorldCorners = panel.worldCorners;
        var leftBottom = panelWorldCorners[0];
        var rightTop = panelWorldCorners[2];
        var center = Vector3.Lerp(leftBottom, rightTop, 0.5f);
        var z = rightTop.x - leftBottom.x;
        var w = rightTop.y - leftBottom.y;
        var cr = new Vector4(center.x, center.y, z * 0.5f, w * 0.5f);

        Vector2 sharpness = new Vector2(1000.0f, 1000.0f);
        //if (soft.x > 0f) sharpness.x = cr.z / soft.x;
        //if (soft.y > 0f) sharpness.y = cr.w / soft.y;

        foreach (Renderer render in mSenderers)
        {
            if (render != null)
            {
                render.material.SetVector("_ClipRange0", new Vector4(-cr.x / cr.z, -cr.y / cr.w, 1f / cr.z, 1f / cr.w));
                render.material.SetVector("_ClipArgs0", new Vector2(sharpness.x, sharpness.y));
            }
        }
    }
}

Shader代码

Shader "Particle/UIParticleClip" {

	Properties {
		_TintColor ("Tint Color", Color) = (0.5,0.5,0.5,0.5)
		_MainTex ("Particle Texture", 2D) = "white" {}
		_ClipRange0 ("_ClipRange0",Vector) = (0.0, 0.0, 0.0, 0.0)
		_ClipArgs0 ("_ClipArgs0",Vector) = (1000.0, 1000.0, 0.0, 0.0)
	}

    SubShader {
    	Tags { "Queue"="Transparent" "IgnoreProjector"="True" "RenderType"="Transparent" }
    	Blend SrcAlpha One
    	Fog { Mode off }
    	ColorMask RGBA
    	Cull Off Lighting Off ZWrite Off

	    Pass {
		    CGPROGRAM
		    #pragma vertex vert
		    #pragma fragment frag
		    #pragma multi_compile_particles

		    #include "UnityCG.cginc"

		    sampler2D _MainTex;
		    fixed4 _TintColor;
			float4 _ClipRange0;
			float4 _ClipArgs0;

		    struct appdata_t {
			    half4 vertex : POSITION;
			    fixed4 color : COLOR;
			    half2 texcoord : TEXCOORD0;
		    };

		    struct v2f {
			    float4 vertex : SV_POSITION;
			    fixed4 color : COLOR;
			    half3 texcoord : TEXCOORD0;
				float2 worldPos : TEXCOORD1;
		    };
		
		    float4 _MainTex_ST;

		    v2f vert (appdata_t v)
		    {
			    v2f o;
			    o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);
			    o.color = v.color;
			    o.texcoord.xy = TRANSFORM_TEX(v.texcoord,_MainTex);
				o.texcoord.z = 0;

				o.worldPos = v.vertex.xy * _ClipRange0.zw + _ClipRange0.xy;
				
			    return o;
		    }
		
		    fixed4 frag (v2f i) : SV_Target
		    {
				// Softness factor
				float2 factor = (float2(1.0, 1.0) - abs(i.worldPos)) * _ClipArgs0;
			
			    fixed4 col = 2.0f * i.color * _TintColor * tex2D(_MainTex, i.texcoord.xy);
				
				col.a *= clamp( min(factor.x, factor.y), 0.0, 1.0);
			    return col;
		    }
		    ENDCG 
	    }
    }
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值