zoukankan      html  css  js  c++  java
  • Unity3d之流光效果

    所谓流光效果,如一个图片上一条刀光从左闪到右边,以下为实现代码:

    c#代码:

    using System;
    using UnityEngine;
    
    public class WalkLightEffect : MonoBehaviour
    {
        public Texture MainTex;
        public Texture LightTex;
        public float Duration;
        public float LightULen;
        public Vector2 Size;
    
        bool m_play;
        float m_timer;
        float m_t1;
    
        void Awake()
        {
            if (MainTex == null)
                throw new ArgumentNullException("MainTex");
            if (LightTex == null)
                throw new ArgumentNullException("LightTex");
            if (Duration <= 0)
                throw new ArgumentException("Duration");
            if (LightULen <= 0 || LightULen >= 1)
                throw new ArgumentException("LightULen <= 0 || LightULen >= 1");
            if (Size.x <= 0 || Size.y <= 0)
                throw new ArgumentException("Size.x <= 0 || Size.y <= 0");
    
            GenerateRenderer();
    
            m_t1 = (1 - LightULen) * Duration;
        }
    
        void GenerateRenderer()
        {
            // Mesh
            Mesh mesh = new Mesh();
            mesh.vertices = new Vector3[4] 
                { 
                    new Vector2(-Size.x/2,Size.y/2),
                    new Vector2(Size.x/2,Size.y/2),
                    new Vector2(-Size.x/2,-Size.y/2),
                    new Vector2(Size.x/2,-Size.y/2),
                };
            mesh.triangles = new int[6] { 0, 1, 2, 2, 1, 3 };
            mesh.uv = new Vector2[4] 
                { 
                    new Vector2(0,1),
                    new Vector2(1,1),
                    new Vector2(0,0),
                    new Vector2(1,0),
                };
    
            mesh.Optimize();
    
            var mf = gameObject.AddComponent<MeshFilter>();
            mf.mesh = mesh;
    
            // Material
            var mat = new Material(Shader.Find("Bleach/WalkLight"));
            mat.SetTexture("_MainTex", MainTex);
            mat.SetFloat("_LightLen", LightULen);
    
            var mr = gameObject.AddComponent<MeshRenderer>();
            mr.sharedMaterial = mat;
        }
    
        void Update()
        {
            if (m_play)
            {
                renderer.material.SetFloat("_TimeRate", m_timer / Duration);
    
                m_timer += Time.deltaTime;
    
                if (m_timer > Duration)
                    m_timer = 0;
                else if (m_timer > m_t1)
                    renderer.material.SetFloat("_ReachBoundary", 1);
                else
                    renderer.material.SetFloat("_ReachBoundary", -1);
            }
        }
    
        public bool Play
        {
            set
            {
                renderer.material.SetTexture("_LightTex", value ? LightTex : null);
                m_timer = 0;
                m_play = value;
            }
        }
    }

    shader代码:

    Shader "Bleach/WalkLight"
    {
        Properties
        {
            _MainTex ("Main", 2D) = "white" {}
            _LightTex("Light", 2D) = "black" {}
            _LightLen("Light Length", float) = 0
        }
        
        SubShader
        {
            Pass
            {
                Tags { "RenderType"="Opaque" }
                LOD 200
                
                Cull Off
                                                    
                CGPROGRAM
                #pragma vertex vert
                #pragma fragment frag
    
                uniform sampler2D _MainTex;
                uniform sampler2D _LightTex;
                uniform    fixed _LightLen;
                
                uniform fixed _ReachBoundary;     // 小于0表示未到边界,大于0表示到达边界
                uniform fixed _TimeRate;        // 时间/周期
                
                struct Data
                {
                    fixed4 vertex:POSITION;
                    fixed2 texcoord:TEXCOORD0;
                };
                
                struct V2F
                {
                    fixed4 pos:SV_POSITION;
                    fixed2 uv:TEXCOORD0;
                };
                
                V2F vert(Data v)
                {
                    V2F o;
                    o.pos=mul(UNITY_MATRIX_MVP,v.vertex);
                    o.uv=v.texcoord;
                    return o;
                }    
                
                fixed4 frag(V2F i):COLOR 
                {
                    fixed4 main = tex2D(_MainTex,i.uv);
                    fixed x = _ReachBoundary>0 && i.uv.x<_LightLen? i.uv.x+1 : i.uv.x;
                    fixed lightU = (x - _TimeRate)/_LightLen;            // u=(x-timer/Duration)/_LightLen;
                    fixed4 light = tex2D(_LightTex,float2(lightU,i.uv.y));
                    
                    return lerp(main,light,light.a);
                }
                                
                ENDCG
            }
        }
        
        FallBack "Diffuse"
    }

    转载请注明出处:http://www.cnblogs.com/jietian331/p/4748644.html

  • 相关阅读:
    KMP算法之查找模式串在源串中出现的次数
    快速排序算法分析
    排序算法的稳定性分析(转)
    动态规划之最优二叉搜索树(算法导论)
    动态规划之最长公共子序列(算法导论)
    动态规划原理(算法导论)
    动态规划之钢条切割(算法导论)
    动态规划之矩阵链相乘问题(算法导论)
    HNU 13064 Cuckoo for Hashing解题报告 North America
    HNU 13081 Even Up Solitaire解题报告
  • 原文地址:https://www.cnblogs.com/jietian331/p/4748644.html
Copyright © 2011-2022 走看看