U3D_TobaccoWarehouseISMDTSy.../Assets/Framework/Scripts/Runtime/Engine/Engine.Animation/AnimNode.cs

221 lines
4.4 KiB
C#

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Playables;
using UnityEngine.Animations;
namespace MotionFramework.Experimental.Animation
{
public abstract class AnimNode
{
private readonly PlayableGraph _graph;
private Playable _source;
private Playable _parent;
private float _fadeSpeed = 0f;
private float _fadeWeight = 0f;
private bool _isFading = false;
/// <summary>
/// 是否已经连接
/// </summary>
public bool IsConnect { get; private set; } = false;
/// <summary>
/// 输入端口
/// </summary>
public int InputPort { private set; get; }
/// <summary>
/// 是否已经完成
/// If the duration of the playable is set, when the time of the playable reaches its duration during playback this flag will be set to true.
/// </summary>
public bool IsDone
{
get
{
return _source.IsDone();
}
}
/// <summary>
/// 是否有效
/// if the Playable is properly constructed by the PlayableGraph and has not been destroyed, false otherwise.
/// </summary>
public bool IsValid
{
get
{
return _source.IsValid();
}
}
/// <summary>
/// 是否正在播放中
/// </summary>
public bool IsPlaying
{
get
{
return _source.GetPlayState() == PlayState.Playing;
}
}
/// <summary>
/// 时间轴
/// </summary>
public float Time
{
set
{
_source.SetTime(value);
}
get
{
return (float)_source.GetTime();
}
}
/// <summary>
/// 播放速度
/// </summary>
public float Speed
{
set
{
_source.SetSpeed(value);
}
get
{
return (float)_source.GetSpeed();
}
}
/// <summary>
/// 权重值
/// </summary>
public float Weight
{
set
{
_parent.SetInputWeight(InputPort, value);
}
get
{
return _parent.GetInputWeight(InputPort);
}
}
public AnimNode(PlayableGraph graph)
{
_graph = graph;
}
public virtual void Update(float deltaTime)
{
if (_isFading)
{
Weight = Mathf.MoveTowards(Weight, _fadeWeight, _fadeSpeed * deltaTime);
if (Mathf.Approximately(Weight, _fadeWeight))
{
_isFading = false;
}
}
}
public virtual void Destroy()
{
if (IsValid)
{
_graph.DestroySubgraph(_source);
}
}
public virtual void PlayNode()
{
// NOTE : When playing, the local time of this Playable will be updated during the evaluation of the PlayableGraph.
_source.Play();
// NOTE : Changes a flag indicating that a playable has completed its operation.
// Playable that reach the end of their duration are automatically marked as done.
_source.SetDone(false);
}
public virtual void PauseNode()
{
// NOTE : When paused, the local time of this Playable will not be updated during the evaluation of the PlayableGraph.
_source.Pause();
// NOTE : Changes a flag indicating that a playable has completed its operation.
// Playable that reach the end of their duration are automatically marked as done.
_source.SetDone(true);
}
public virtual void ResetNode()
{
_fadeSpeed = 0;
_fadeWeight = 0;
_isFading = false;
Time = 0;
Speed = 1;
Weight = 0;
}
/// <summary>
/// 连接到父节点
/// </summary>
/// <param name="parent">父节点对象</param>
/// <param name="inputPort">父节点上的输入端口</param>
public void Connect(Playable parent, int parentInputPort)
{
if (IsConnect)
throw new System.Exception("AnimNode is connected.");
_parent = parent;
InputPort = parentInputPort;
// 重置节点
ResetNode();
// 连接
_graph.Connect(_source, 0, parent, parentInputPort);
IsConnect = true;
}
/// <summary>
/// 同父节点断开连接
/// </summary>
public void Disconnect()
{
if (IsConnect == false)
throw new System.Exception("AnimNode is disconnected.");
// 断开
_graph.Disconnect(_parent, InputPort);
IsConnect = false;
}
/// <summary>
/// 开始权重值过渡
/// </summary>
/// <param name="destWeight">目标权重值</param>
/// <param name="fadeDuration">过渡时间</param>
public void StartWeightFade(float destWeight, float fadeDuration)
{
if (fadeDuration <= 0)
{
Weight = destWeight;
_isFading = false;
return;
}
//注意:保持统一的渐变速度
_fadeSpeed = 1f / fadeDuration;
_fadeWeight = destWeight;
_isFading = true;
}
protected void SetSourcePlayable(Playable playable)
{
_source = playable;
}
}
}