一、2D轮转图的制作
本质和3D轮转图的制作是差不多的。只不过是预制体变成了Image,同时需要算一个缩放比来显示前后的效果。因为没有z轴
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
using DG.Tweening;
using System;
using Newtonsoft.Json;
using System.IO;
public class Goods
{
public string path;
public string name;
public int id;
}
public class Lesson7 : MonoBehaviour, IDragHandler, IEndDragHandler
{
public Image prefab;
public int num;
private List<Goods> list = new List<Goods>();
private float area, r, ang, moveAng, cutSpeed = 500, max = 1, min = 0.5f, oppo = -6, dis = 100;
private List<Image> list_img = new List<Image>();
private List<RectTransform> list_rect = new List<RectTransform>();
public Button btn_right, btn_left;
// Start is called before the first frame update
private void Awake()
{
GetJsonData();
Rect rect = prefab.GetComponent<RectTransform>().rect;
area = (rect.width + dis) * num;
r = area / (Mathf.PI * 2);
ang = Mathf.PI * 2 / num;
}
private void GetJsonData()
{
string path = Application.dataPath + "/Resources/Img.json";
string str = File.ReadAllText(path);
list = JsonConvert.DeserializeObject<List<Goods>>(str);
}
void Start()
{
for (int i = 0; i < num; i++)
{
Image obj = Instantiate(prefab, transform);
obj.gameObject.SetActive(true);
obj.sprite = Resources.Load<Sprite>(list[i].path);
list_img.Add(obj);
list_rect.Add(obj.rectTransform);
}
Move();
btn_right.onClick.AddListener(() =>
{
ResetImg(1);
});
btn_left.onClick.AddListener(() =>
{
ResetImg(-1);
});
}
private void Move()
{
for (int i = 0; i < num; i++)
{
float x = Mathf.Sin(i * ang + moveAng) * r;
float y = Mathf.Cos(i * ang + moveAng) * r;
list_img[i].rectTransform.anchoredPosition = new Vector2(x, y / oppo);
float _dis = (y + r) / (2 * r);
float _size = (max - min) * _dis + min;
list_img[i].rectTransform.localScale = Vector3.one * _size;
}
list_rect.Sort((a, b) =>
{
if (a.localScale.y > b.localScale.y)
{
return 1;
}
else if (a.localScale.y < b.localScale.y)
{
return -1;
}
else
{
return 0;
}
});
for (int i = 0; i < num; i++)
{
list_rect[i].SetAsLastSibling();
}
}
public void OnDrag(PointerEventData eventData)
{
float _x = eventData.delta.x;
moveAng += _x / r;
Move();
}
public void OnEndDrag(PointerEventData eventData)
{
float _x = eventData.delta.x;
float speed = Mathf.Abs(_x) / cutSpeed;
DOTween.To((x) =>
{
moveAng += x / r;
Move();
}, _x, 0, speed).OnComplete(() =>
{
ResetImg(0);
});
}
private void ResetImg(int v)
{
float addAng = v * ang;
float imgAng = list_rect[num - 1].anchoredPosition.x / r + addAng;
float moveDis = imgAng * r;
float speed = Mathf.Abs(moveDis) / cutSpeed;
DOTween.To((x) =>
{
moveAng = x;
Move();
},moveAng,moveAng- imgAng, speed);
}
}