Unity 3D轮转图,带惯性和自动对齐

需要用到DoTween插件

1.创建空对象,声明预制体,数量,半径,角度,游戏性对象和transform(用于对其)的集合

public GameObject prefabs;
    public int num;
    public float r;
    public float angle;
    public List<GameObject> list = new List<GameObject>();
    public List<Transform> sort = new List<Transform>();

 这里的prefab用了默认生成的球体

2. 在预制体上添加脚本Item,脚本内声明先前空物体上的脚本(这里是CreatRoll)

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class Item : MonoBehaviour
{
    public CreatRoll creat;

    private void OnMouseDrag()//鼠标拖拽中
    {
        Vector3 pos=Camera.main.WorldToScreenPoint(transform.position);
        Vector3 next = Camera.main.ScreenToWorldPoint(new Vector3(Input.mousePosition.x,
            Input.mousePosition.y,
            pos.z));

        float dis= transform.position.x-next.x;
        creat.OnDrag(dis);
    }

    private void OnMouseUp()//鼠标结束拖拽
    {
        Vector3 pos = Camera.main.WorldToScreenPoint(transform.position);
        Vector3 next = Camera.main.ScreenToWorldPoint(new Vector3(Input.mousePosition.x,
            Input.mousePosition.y,
            pos.z));

        float dis = transform.position.x - next.x;
        creat.Inertia(dis);
    }
}

3.在空物体的脚本中写Start方法,根据数字生成预制体,以及设置预制体的父类,位置,脚本内的Creat等

void Start()
    {
        angle = 2 * Mathf.PI / num;
        for (int i = 0; i < num; i++)
        {
            float x = Mathf.Sin(i * angle) * r;
            float z = Mathf.Cos(i * angle) * r;
            GameObject go = Instantiate(prefabs);
            go.transform.SetParent(transform);
            go.transform.localPosition = new Vector3(x, 0, z);
            go.GetComponent<Item>().creat = this;
            list.Add(go);
            sort.Add(go.transform);
        }
    }

4.在空对象里设置allang,为拖拽时需要旋转的弧度

float angall = 0;

5.设置OnDrag脚本,在拖拽物体时调用(预制体的 OnMouseDrag)

 public void OnDrag(float dis)
    {
        float ang = dis / r;
        angall += ang;
        for (int i = 0; i < num; i++)
        {
            float x = Mathf.Sin(i * angle + angall) * r;
            float z = Mathf.Cos(i * angle + angall) * r;
            list[i].transform.localPosition = new Vector3(x, 0, z);
        }
    }

6.设置OnDrag脚本,在松开时调用(预制体的 OnMouseUp)

public void Inertia(float dis)
    {
        DOTween.To(() => dis, t => OnDrag(t), 0, 2).SetEase(Ease.Linear).OnComplete(() =>
        {
            sort.Sort((a, b) => (int)(a.localPosition.z - b.localPosition.z));
            float ang = Mathf.Asin(sort[0].transform.localPosition.x/r);
            DOTween.To(() => angall, t =>
            {
                for (int i = 0; i < num; i++)
                {
                    float x = Mathf.Sin(i * angle + t) * r;
                    float z = Mathf.Cos(i * angle + t) * r;
                    list[i].transform.localPosition = new Vector3(x, 0, z);
                }
            }
            , angall+ang, 1);
        });
    }

完成DOTween移动以后,通过对比排序获得预制体中位置z值最小的一个,用Asin获得弧度,再用DoTween实现回到应在的位置

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值