码迷,mamicode.com
首页 > 编程语言 > 详细

unity3d 纹理的精灵动画效果

时间:2014-12-08 15:44:26      阅读:302      评论:0      收藏:0      [点我收藏+]

标签:游戏开发   unity3d   cg语言   shader   屏幕特效   

精灵动画,顾名思义是一种动画效果,我们用到的贴图是类似胶卷一样的,把每一帧都放在一张图上,

然后通过变换uv值进行位移切换,

如果你之前没有进行过uv相关的变换,可以查看上一篇文章 unity3d 纹理贴图移动特效


首先我们需要一个张这样的贴图

bubuko.com,布布扣


然后建立一个shader


先声明变量
_TexWidth  贴图总宽度
_CellAmount  一张图上包含几个动作(有几个小图片)
_Speed  动画的速度


	Properties {
		_MainTex ("Base (RGB)", 2D) = "white" {}
		_TexWidth ("Sheet Width", float) = 0.0
		_CellAmount ("Cell Amount", float) = 0.0//有几个画面
		_Speed ("Speed", Range(0.01, 32)) = 12
	}

主要的操作也是在surf函数中进行
需要一点数学的知识。。。。

先浏览一下局部变量

float2 spriteUV   贴图的uv坐标
float cellPixelWidth     贴图中的一个小画面的宽度
        
float cellUVPercentage     小画面占整个贴图的比率,小画面个数越少比率越大
    
float timeVal    当前该显示的小图片位数(就是该显示哪个小图片了)
float xValue   贴图uv中的x坐标值


		void surf (Input IN, inout SurfaceOutput o) {

			float2 spriteUV = IN.uv_MainTex;
			float cellPixelWidth = _TexWidth/_CellAmount;//一个小画面的宽度
			float cellUVPercentage = cellPixelWidth/_TexWidth;//小画面占大画面比率,个数越少比率越大
			float timeVal = fmod(_Time.y * _Speed, _CellAmount);
			timeVal = ceil(timeVal);//向上取整,得到一个小于CellAmount的整数
			float xValue = spriteUV.x;			xValue += cellUVPercentage * timeVal * _CellAmount;//
			xValue *= cellUVPercentage;//对uv进行缩放
			spriteUV = float2(xValue, spriteUV.y);
			half4 c = tex2D (_MainTex, spriteUV);
			o.Albedo = c.rgb;
			o.Alpha = c.a;
		}

一个小画面的宽度
 = 总宽度 / 小图片数目
cellPixelWidth = _TexWidth/_CellAmount;


小画面占整个贴图的比率 = 一个小画面的宽度 / 整个贴图宽度
cellUVPercentage = cellPixelWidth/_TexWidth


对时间*速度与小图片数目取余,得到的就是一个小于小图片数目的数,正好就是当前该显示的图片位数
fmod(x,y)取余函数,返回一个x/y 的浮点型余数
timeVal = fmod(_Time.y * _Speed, _CellAmount)
    
但是是fmod()得到的是一个浮点数值,不是一个整数值,
我们就用ceil()这个函数对它进行向上取整
timeVal = ceil(timeVal)

初始化xValue贴图uv中的x坐标值
float xValue = spriteUV.x

进行偏移,得到当前小图片的uv位置        
xValue += cellUVPercentage * timeVal * _CellAmount

然后必须对uv进行缩放才能看到一张小图片
xValue *= cellUVPercentage

然后得到最终uv值进行纹理渲染


最终得到这样的结果:


bubuko.com,布布扣



shader代码如下:



Shader "Custom/testShader" {
	Properties {
		_MainTex ("Base (RGB)", 2D) = "white" {}
		_TexWidth ("Sheet Width", float) = 0.0
		_CellAmount ("Cell Amount", float) = 0.0//有几个画面
		_Speed ("Speed", Range(0.01, 32)) = 12
	}
	SubShader {
		Tags { "RenderType"="Opaque" }
		LOD 200

			CGPROGRAM
#pragma surface surf Lambert
			float _TexWidth;
		float _CellAmount;
		float _Speed;

		sampler2D _MainTex;


		struct Input {
			float2 uv_MainTex;
		};

		void surf (Input IN, inout SurfaceOutput o) {

			float2 spriteUV = IN.uv_MainTex;
			float cellPixelWidth = _TexWidth/_CellAmount;//一个小画面的宽度
			float cellUVPercentage = cellPixelWidth/_TexWidth;//小画面占大画面比率,个数越少比率越大
			float timeVal = fmod(_Time.y * _Speed, _CellAmount);
			timeVal = ceil(timeVal);//向上取整,得到一个小于CellAmount的整数
			float xValue = spriteUV.x;			xValue += cellUVPercentage * timeVal * _CellAmount;//
			xValue *= cellUVPercentage;//对uv进行缩放
			spriteUV = float2(xValue, spriteUV.y);
			half4 c = tex2D (_MainTex, spriteUV);
			o.Albedo = c.rgb;
			o.Alpha = c.a;
		}
		ENDCG
	} 
	FallBack "Diffuse"
}



                                                                                                             -------- by wolf96

unity3d 纹理的精灵动画效果

标签:游戏开发   unity3d   cg语言   shader   屏幕特效   

原文地址:http://blog.csdn.net/wolf96/article/details/41802905

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!