今天我們來用unity3d的UGUI來實現圖片的輪播,也就是經常在一些視頻網站上的一些圖片輪播。這次將使用到動畫插件DOTWEEN,主要目的也是爲了熟悉Dotween這個插件。圖片輪播的原理是比較簡單的,我將實現圖片特效輪播,也是看了別人的網站後想在UGUI上面實現以下,正好剛剛學習了Dotween,拿來練練手。
原理: 2張圖片疊加在一起,且開始狀態是2張圖片都爲一樣的圖片,切換之前,將後面的圖片先直接切換成其他圖片,然後對第一張圖片做出各種動畫操作(如將第一張圖片的透明度逐漸降低),這樣就可以特效的切換到其他圖片。我們直接看看案例圖如下:
用到的核心函數:
Sprite.Create(Texture2D texture, Rect rect, Vector2 pivot);
我們只需要關心這3個參數,其他默認即可。
Texture2D ,這個是我們圖片的資源,用resources.load加載即可。
Rect 這個是很關鍵的,自己可以動手實驗一下就明白了rect裏面的2個參數,第一個即是image空白框中顯示一張圖片的某一個大小爲第二個參數的位置。有點拗口,類似於HTML中css的Background-Position.
Vector2 直接爲vector2.zero即可。
具體步驟如下啦:
第一步:先把場景搭好,圖片上一共有32個小的image,左上角開始到左邊,然後第二行繼續(ps一下,如果你想適配不同的分辨率,image小圖片的錨點改成下面圖片中的一樣,每一個都要改額,記得圖片之間留一點點位置,感覺像網格一樣。好像Grid Layout Group這個組件可以直接來調整這樣的圖片網格樣式,沒用過,我就暫時不研究它了,如果嫌一個圖片一個圖片的改錨點麻煩,可以去研究一下這個組件,會玩之後可以來交流交流)如下圖,改成如下圖的面板:
第二步:給每個image添加Canvas Group,這是爲了給Dowteen來改變圖片透明度用的,就是改變裏面的Alpha
第三步:複製圖片中force,然後改名爲back,這就是原理中的第二張圖片,force就是第一張啦。
好準備開始寫代碼了。
“`
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using UnityEngine.UI;
using DG.Tweening;
///
/// 第一步,將背部圖片改爲需要播放的圖片
///第二步,將force的32個image,通過各種方式消失。
///第三步,將force的32個image的顯示的圖片改變爲back的image顯示的圖片
///第四步,將force的32個image復原(也就是將位置,透明度等復原,因爲2張圖片一樣,這裏復原肉眼是看不出來的)
/// 第五步,重複第一步。
///
public class ImageManager : MonoBehaviour {
List<List<GameObject>> forceList = new List<List<GameObject>>();
List<List<GameObject>> backList = new List<List<GameObject>>();
Dictionary<string, List<List<Sprite>>> spritePath = new Dictionary<string, List<List<Sprite>>>();
public int ImageNumber;
private float ImageWidth;
private float ImageHeight;
int currentImageNumber = 1;
void Start () {
//找到32張force圖片
int count = transform.FindChild("force").childCount;
for (int i = 0; i < count/8; i++) {
List<GameObject> list = new List<GameObject>();
for (int k = 0; k < count/4; k++) {
list.Add(transform.FindChild("force").GetChild(k+i*8).gameObject);
}
forceList.Add(list);
}
//找到32張back圖片
count = transform.FindChild("back").childCount;
for (int i = 0; i < count / 8; i++)
{
List<GameObject> list = new List<GameObject>();
for (int k = 0; k < count / 4; k++)
{
list.Add(transform.FindChild("back").GetChild(k + i * 8).gameObject);
}
backList.Add(list);
}
for (int name = 0; name <=ImageNumber; name++) {
Texture2D t2d = Resources.Load(name.ToString(), typeof(Texture2D)) as Texture2D;
List<List<Sprite>> spriteOneList = new List<List<Sprite>>();
for (int i = 0; i < 4; i++)
{
List<Sprite> iSpriteList = new List<Sprite>();
for (int k = 0; k < 8; k++)
{
iSpriteList.Add(Sprite.Create(t2d, new Rect(new Vector2(t2d.width / 8 * k, t2d.height / 4 * i), new Vector2(t2d.width / 8, t2d.height / 4)), new Vector2(0, 0)));
}
spriteOneList.Add(iSpriteList);
}
spritePath.Add(name.ToString(), spriteOneList);
}
ImageWidth = forceList[0][0].GetComponent<RectTransform>().rect.width;
ImageHeight = forceList[0][0].GetComponent<RectTransform>().rect.height;
SetSprite(1,true);
SetSprite(1,false);
StartChangeImage();
}
//設置force32張圖片的背景
public void SetSprite(int ImageName, bool force) {
List<List<Sprite>> spriteList;
spritePath.TryGetValue(ImageName.ToString(), out spriteList);
if (force)
{
for (int i = 0; i < 4; i++)
{
for (int k = 0; k < 8; k++)
{
forceList[3-i][k].GetComponent<Image>().sprite = spriteList[i][k];
}
}
}
else {
for (int i = 0; i < 4; i++)
{
for (int k = 0; k < 8; k++)
{
backList[3-i][k].GetComponent<Image>().sprite = spriteList[i][k];
}
}
}
}
//設置一張圖片背景////todo
public void SetOneSprite(GameObject crImageName,int ImageName, bool force,int k,int i)
{
List<List<Sprite>> spriteList;
spritePath.TryGetValue(ImageName.ToString(), out spriteList);
if (force)
{
crImageName.GetComponent<Image>().sprite = spriteList[3-i][k];
}
else
{
crImageName.GetComponent<Image>().sprite = spriteList[3-i][k];
}
}
int zy = 1;
//輪播
public void StartChangeImage() {
ResetForce();//復原force圖片,這張圖片應該是當前back顯示的圖片
currentImageNumber++;
if (currentImageNumber > ImageNumber)
{
currentImageNumber = 1;
}
SetSprite(currentImageNumber, false);//設置back圖片爲一下輪播的圖片
// StartImageAnim(Mathf.RoundToInt(Random.Range(1f,5f)));//改變動畫效果
StartImageAnim(zy++);
if (zy == 6) {
zy = 1;
}
Invoke("StartChangeImage", 5f);
}
//更換圖片
public void SetNextImage(List<GameObject> objArray,Sprite newSprite) {
for (int i = 0; i < objArray.Count; i++) {
objArray[i].GetComponent<Image>().sprite = newSprite;
}
}
//輪播動畫
public void StartImageAnim(int currentAnim) {
Invoke("AnimType" + currentAnim, 0);
}
//復原force
public void ResetForce() {
SetSprite(currentImageNumber,true);
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
forceList[i][k].GetComponent<CanvasGroup>().alpha = 1f;
forceList[i][k].GetComponent<RectTransform>().anchoredPosition = Vector2.zero;
forceList[i][k].GetComponent<RectTransform>().localScale= Vector3.one;
forceList[i][k].GetComponent<RectTransform>().localRotation = Quaternion.Euler(Vector3.zero);
}
}
}
//圖片輪播動畫的效果1
public void AnimType1() {
float Time = 0.2f;
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
forceList[i][k].GetComponent<CanvasGroup>().DOFade(0,1.2f).SetDelay(Time);
Time += 0.05f;
}
}
}
//圖片輪播動畫的效果2
public void AnimType5()
{
float Time = 0.25f;
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
forceList[i][k].GetComponent<RectTransform>().DOScale(0, 0.8f).SetEase(Ease.InBack).SetDelay(Time);
Time += 0.05f;
}
}
}
//圖片輪播動畫的效果3
public void AnimType3()
{
float Time = 0.25f;
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
forceList[i][k].GetComponent<RectTransform>().DOScale(0, 0.8f).SetEase(Ease.InCirc).SetDelay(Time);
Time += 0.05f;
}
}
}
//圖片輪播動畫的效果4
public void AnimType4()
{
float Time = 0.25f;
List<Tweener> tweenrs = new List<Tweener>();
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
Tweener tweenr = forceList[i][k].GetComponent<RectTransform>().DORotate(new Vector3(90, 0, 0), 0.8f,RotateMode.LocalAxisAdd).SetEase(Ease.InBack).SetDelay(Time);
Time += 0.05f;
}
}
}
//圖片輪播動畫的效果5
public void AnimType2()
{
float Time = 0.2f;
SetSprite(0,false);
for (int i = 0; i < forceList.Count; i++)
{
for (int k = 0; k < forceList[i].Count; k++)
{
GameObject obj = forceList[i][k];
int n = k;
int m = i;
Tweener tweener1 = forceList[i][k].GetComponent<RectTransform>().DOScale(0f, 0.4f).SetDelay(Time).OnComplete(()=>SetOneSprite(obj, currentImageNumber,true,n,m));
Tweener tweener2 = forceList[i][k].GetComponent<RectTransform>().DOScale(1f, 0.4f).SetEase(Ease.OutBack);
DOTween.Sequence().Append(tweener1).Append(tweener2);
Time += 0.03f;
}
}
}
}
輪播的圖片想要改成其他圖片,直接在Resources裏面添加圖片即可,名字從1到無限(如1.jpg)不要忘了修改面板上的圖片數量,我這裏有9張圖片,ImageNumber就 爲9;
需要項目學習的自己拿啦,下下下下下下下下下下下下下下下下。。。。。。。
http://pan.baidu.com/s/1eSl2NJk 密碼:lu90
下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下下。。。。。。。。。(遇到問題,可以討論額)