效果:
【太妃糖耶】更新了一條視頻,快來圍觀!
序列圖動畫的實現
首先先了解下序列圖樣式的紋理圖片
如上圖一可在Shader中使用該圖片制作燃燒的火的動畫,但是如何實現呢?接下來一起來看一下吧
序列圖動畫的實現原理大概是順序采樣序列圖紋理中的每一個小格子塊,從最上方的左邊開始一直到最右邊然后再繼續下一行的采樣,從而形成動畫效果
所以序列圖動畫的實現分為兩個步驟:
1.首先采樣最上方左側小格子中的紋理
2.完成UV的走格,通過變化的UV來采樣對應的格子塊從而形成動畫效果
第一步:采樣最上方左側小格子中的紋理
o.uv = float2(v.uv.x/_Column,v.uv.y/_Row+1/_Row*(_Row-1));
其中_Row代表行數,_Column代表列數 (兩者必須為float類型)
上面的代碼相當于? ?v.uv.x=v.uv.x/_Column;? ? ? ?v.uv.y=v.uv.y/_Row+1/_Row*(_Row-1);
?v.uv.x=v.uv.x/_Column; 用原UV中U方向的值除以列數,得到新的U方向上的值(如果列數為3,U方向上的值則為(0,0.333))
v.uv.y=v.uv.y/_Row+1/_Row*(_Row-1); 用原UV中V方向的值除以行數,表示一個小格子中U方向的值。再加上1/_Row*(_Row-1)代表將U方向的值移動到原UV中V方向的最上側。
第二步:完成UV走格,通過變化的UV來采樣對應的格子塊從而形成動畫效果
首先我們可以用o.uv.x+=_Time.y;來看一下效果(可見不是我們想要的走格的效果)
- U方向的走格:?
o.uv.x += frac(floor(_Time.y*_Column*_Speed)/_Column);
floor(_Time.y*_Column)/_Column : 實現一秒之內完成一行的走格
- V方向的走格:?
?o.uv.y - = frac(floor(_Time.y*_Speed)/_Row);
floor(_Time.y)/_Row : 每秒向下偏移一格(用減法實現向下偏移)
?frac取小數的作用是優化紋理采樣,使得采樣紋理的UV在0-1的范圍內
?實現透貼效果
Tags{"Queue"="Transparent"}
當序列圖為透貼格式時,使用 Blend SrcAlpha OneMinusSrcAlpha 來實現背景透明
還可以在片元著色器中使用 c.rgb *= c.a;?, 透明區域的a通道中的值為0,所以此時透明背景就變為黑色,所以要配合 Blend One One 來使用
若序列圖的背景是黑色時,可以使用 Blend One One?
綜上所述,可以使用?c.rgb *= c.a?和?Blend One One 共同實現透貼圖片和黑底圖片的半透明效果
Shader"unity/UV"
{Properties{[NoScaleOffset]_MainTex("MainTex",2D)="white"{}_Row("Row",float)=1_Column("Column",float)=1_Speed("Speed",float)=3[Enum(Billaboard,1,VerticalBillaboard,0)]_BillaboardType("BillaboardType",int)=1}SubShader{Tags{"RenderPipeline"="UniversalPipeline""Queue"="Transparent"}//常用于透貼// Blend SrcAlpha OneMinusSrcAlpha//用于黑底圖片Blend One OnePass{HLSLPROGRAM#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Common.hlsl"#include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Color.hlsl"#include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl"#pragma vertex vert#pragma fragment fragTEXTURE2D(_MainTex);float4 _MainTex_ST;#define sampler_MainTex samplerState_Linear_RepeatSAMPLER(sampler_MainTex);CBUFFER_START(UnityPerMaterial)float _Row,_Column,_Speed;int _BillaboardType;CBUFFER_ENDstruct Attributes{float4 positionOS : POSITION;float2 uv : TEXCOORD;};struct Varyings{float4 positionCS : SV_POSITION;float2 uv : TEXCOORD;};Varyings vert(Attributes v){Varyings o = (Varyings)0;o.positionCS = TransformObjectToHClip(v.positionOS);o.uv = TRANSFORM_TEX(v.uv,_MainTex);//序列圖動畫的起始位置o.uv = float2(v.uv.x/_Column,v.uv.y/_Row+1/_Row*(_Row-1));//frac取小數的作用是優化紋理采樣,使得采樣紋理的UV在0-1的范圍內//U方向上的走格 floor(_Time.y*_Column)/_Column代表一秒鐘走完一行中的所以列的格子o.uv.x+=frac(floor(_Time.y*_Column*_Speed)/_Column);//V方向上的走格 floor(_Time.y)/_Row 代表每一秒走一行o.uv.y-=frac(floor(_Time.y*_Speed)/_Row);return o;}float4 frag(Varyings i):SV_Target{float4 c;float4 mainTex = SAMPLE_TEXTURE2D(_MainTex,sampler_MainTex,i.uv);c=mainTex;//用于透貼圖片消除Alpah為0的區域 Alpha=1為不透明,Alpha=0為透明c.rgb*=c.a;return c;}ENDHLSL}}}