using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.Playables; using UnityEngine.Animations; namespace MotionFramework.Experimental.Animation { public sealed class AnimMixer : AnimNode { private const float HIDE_DURATION = 0.25f; private readonly List _states = new List(10); private AnimationMixerPlayable _mixer; private bool _isQuiting = false; /// /// 动画层级 /// public int Layer { private set; get; } public AnimMixer(PlayableGraph graph, int layer) : base(graph) { Layer = layer; _mixer = AnimationMixerPlayable.Create(graph); SetSourcePlayable(_mixer); } public override void Update(float deltaTime) { base.Update(deltaTime); for (int i = 0; i < _states.Count; i++) { var state = _states[i]; if (state != null) state.Update(deltaTime); } bool isAllDone = true; for (int i = 0; i < _states.Count; i++) { var state = _states[i]; if (state != null) { if (state.IsDone == false) isAllDone = false; } } // 当子节点都已经完成的时候断开连接 if (isAllDone && _isQuiting == false) { _isQuiting = true; StartWeightFade(0, HIDE_DURATION); } if (_isQuiting) { if (Mathf.Approximately(Weight, 0f)) DisconnectMixer(); } } /// /// 播放指定动画 /// public void Play(AnimState animState, float fadeDuration) { // 重新激活混合器 _isQuiting = false; StartWeightFade(1f, 0); if (IsContains(animState) == false) { // 优先插入到一个空位 int index = _states.FindIndex(s => s == null); if (index == -1) { // Increase input count int inputCount = _mixer.GetInputCount(); _mixer.SetInputCount(inputCount + 1); animState.Connect(_mixer, inputCount); _states.Add(animState); } else { animState.Connect(_mixer, index); _states[index] = animState; } } for (int i = 0; i < _states.Count; i++) { var state = _states[i]; if (state == null) continue; if (state == animState) { state.StartWeightFade(1f, fadeDuration); state.PlayNode(); } else { state.StartWeightFade(0f, fadeDuration); state.PauseNode(); } } } /// /// 停止指定动画,恢复为初始状态 /// public void Stop(string name) { AnimState state = FindState(name); if (state == null) return; state.PauseNode(); state.ResetNode(); } /// /// 暂停所有动画 /// public void PauseAll() { for (int i = 0; i < _states.Count; i++) { var state = _states[i]; if (state == null) continue; state.PauseNode(); } } /// /// 是否包含该动画 /// public bool IsContains(AnimNode node) { foreach (var state in _states) { if (state == node) return true; } return false; } /// /// 移除一个动画 /// public void RemoveState(string name) { var state = FindState(name); if (state == null) return; _states[state.InputPort] = null; state.Destroy(); } /// /// 获取指定的动画 /// /// 如果没有返回NULL private AnimState FindState(string name) { foreach (var state in _states) { if (state != null && state.Name == name) return state; } MotionLog.Warning($"Animation state doesn't exist : {name}"); return null; } private void DisconnectMixer() { for (int i = 0; i < _states.Count; i++) { var state = _states[i]; if (state == null) continue; state.Disconnect(); _states[i] = null; } Disconnect(); } } }