Unity进阶技术

使用 Dotween 跟随一个移动的物体

2021-01-22  本文已影响0人  烂醉花间dlitf

ChangeEndValue 参数解析

Changes the end value of a tween and rewinds it (without pausing it). Has no effect with tweens that are inside Sequences

意思就是说重新回到一开始的点,然后按照新的 Target 进行变换。

using UnityEngine;
using DG.Tweening;

public class NewBehaviourScript : MonoBehaviour
{
    public Transform target1;
    public Transform target2;
    public Transform move;
    private Tweener m_tweener;

    private void Start()
    {
        m_tweener = move.DOMove(target1.position, 10);
    }

    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            m_tweener.ChangeEndValue(target2.position);
        }
    }
}

第二个参数新的时间,看一下动图就可以明白了。一开始的移动时间是 10,新的移动时间是 1,所以就变得很快。

using UnityEngine;
using DG.Tweening;

public class NewBehaviourScript : MonoBehaviour
{
    public Transform target1;
    public Transform target2;
    public Transform move;
    private Tweener m_tweener;

    private void Start()
    {
        m_tweener = move.DOMove(target1.position, 10);
    }

    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            m_tweener.ChangeEndValue(target2.position,1);
        }

        if (m_tweener != null)
        {
            Debug.Log(m_tweener.IsPlaying());
        }
    }
}

第三个参数为 true 就是从当前状态直接到新状态,不需要 rewind。

using UnityEngine;
using DG.Tweening;

public class NewBehaviourScript : MonoBehaviour
{
    public Transform target1;
    public Transform target2;
    public Transform move;
    private Tweener m_tweener;

    private void Start()
    {
        m_tweener = move.DOMove(target1.position, 10);
    }

    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            m_tweener.ChangeEndValue(target2.position,1,true);
        }

        if (m_tweener != null)
        {
            Debug.Log(m_tweener.IsPlaying());
        }
    }
}

跟随一个移动的物体

了解这些之后,就可以写出像下面一样的代码使得一个物体一直跟随另一个移动的物体。

using UnityEngine;
using DG.Tweening;

public class NewBehaviourScript : MonoBehaviour
{
    public Transform target1;
    public Transform target2;
    public Transform move;
    private Tweener m_tweener;

    private void Start()
    {
        m_tweener = move.DOMove(target2.position, 10).OnUpdate(() =>
        {
            m_tweener.ChangeEndValue(target2.position, true);
        });
    }

    private void Update()
    {
        if (m_tweener != null)
        {
            Debug.Log(m_tweener.IsPlaying());
        }
    }
}

注意看 console 第四行的 bool 值,一直都会是 true,即使已经重合了,也不会结束。而且离目标越近就会越慢,因为假设之前 1 的路程用时为 1,第一次更新前进了 0.2,那么就会有 0.8 的路程依然用时为 1,最后就是 0.000000001 的路程依然用时为 1,所以速度在不断变慢。

可以使用下面的方法手动限制时间,这样可以保障在 10s 内,物体一直往目标前进,并在第 10s 停在当时目标的位置。有个缺陷就是 OnComplete 回调函数不会被调用了。

using UnityEngine;
using DG.Tweening;

public class NewBehaviourScript : MonoBehaviour
{
    public Transform target1;
    public Transform target2;
    public Transform move;
    private Tweener m_tweener;
    private float m_tweenerStartTime;

    private void Start()
    {
        float time = 10;
        m_tweenerStartTime = Time.time;
        m_tweener = move.DOMove(target2.position, time);
        m_tweener.OnUpdate(() =>
        {
            float tt = Mathf.Clamp(time - Time.time + m_tweenerStartTime, 0, time);
            m_tweener.ChangeEndValue(target2.position, tt, true);
            //if (tt <= float.Epsilon)
            //{
            //    m_tweener.Complete();
            //}
        });
        m_tweener.OnComplete(() =>
        {
            Debug.Log(Time.time - m_tweenerStartTime - m_tweenerStartTime);
        });
    }

    private void Update()
    {
        if (m_tweener != null)
        {
            Debug.Log(m_tweener.IsPlaying());
        }
    }
}
上一篇 下一篇

猜你喜欢

热点阅读