shader中的序列幀動畫屬於紋理動畫中的一種,主要原理是將給定的紋理進行等分,再根據時間的變化循環播放等分中的一部分。app
名稱 | 類型 | 描述 |
_Time | float4 | (t/20,t,2t,3t) 其中t爲自該場景加載所通過時間 |
_SinTime | float4 | (t/8,t/4,t/2,t) 其中t爲自該場景加載所通過時間的正弦值 |
_CosTime | float4 | (t/8,t/4,t/2,t) 其中t爲自該場景加載所通過時間的餘弦值 |
unity_DeltaTime | float4 | (dt,1/dt,sdt,1/sdt) 其中dt爲時間增量,sdt爲時間增量的平滑值 |
腳本以下:動畫
1 Shader "MyUnlit/FrameAnimation" 2 { 3 Properties 4 { 5 _Color("Color Tint",color)=(1,1,1,1) 6 _MainTex ("Texture", 2D) = "white" {} 7 _CutX("CutX Amount",float)=4 8 _CutY("CutY Amount",float)=4 9 _Speed("Speed",range(1,100))=30 10 } 11 SubShader 12 { 13 //通常序列幀動畫的紋理會帶有Alpha通道,所以要按透明效果渲染,須要設置標籤,關閉深度寫入,使用並設置混合 14 Tags { "RenderType"="transparent" "queue"="transparent" "ignoreprojector"="true" } 15 ZWrite off 16 blend srcalpha oneminussrcalpha 17 18 Pass 19 { 20 Tags{"lightmode"="forwardbase"} 21 22 CGPROGRAM 23 #pragma vertex vert 24 #pragma fragment frag 25 #pragma multi_compile_fog 26 27 #include "UnityCG.cginc" 28 29 struct appdata 30 { 31 float4 vertex : POSITION; 32 float2 uv : TEXCOORD0; 33 }; 34 35 struct v2f 36 { 37 float2 uv : TEXCOORD0; 38 UNITY_FOG_COORDS(1) 39 float4 vertex : SV_POSITION; 40 }; 41 42 sampler2D _MainTex; 43 float4 _MainTex_ST; 44 fixed4 _Color; 45 float _CutX; 46 float _CutY; 47 float _Speed; 48 49 v2f vert (appdata v) 50 { 51 v2f o; 52 o.vertex = UnityObjectToClipPos(v.vertex); 53 o.uv = TRANSFORM_TEX(v.uv, _MainTex); 54 UNITY_TRANSFER_FOG(o,o.vertex); 55 return o; 56 } 57 58 fixed4 frag (v2f i) : SV_Target 59 { 60 //取得整數的時間 61 float time = floor(_Time.y*_Speed); 62 //整除部分爲行(由於播放順序是從左到右,先行後列) 63 float row = floor(time / _CutX); 64 //餘數部分爲列 65 float column = time - row * _CutX; 66 67 //計算偏移值,其中u向爲列索引值,v向爲行索引的相反數(播放原點是左上角,而uv採樣原點是左下角,因此v向偏移應該取反) 68 half2 uv = i.uv + half2(column,-row); 69 //除以行列獲得最終的採樣值 70 uv.x /= _CutX; 71 uv.y /= _CutY; 72 73 fixed4 col = tex2D(_MainTex,uv); 74 col.rgb *= _Color; 75 UNITY_APPLY_FOG(i.fogCoord, col); 76 return col; 77 } 78 ENDCG 79 } 80 } 81 FallBack "Transparent/VertexLit" 82 }