using System; using System.Collections; using System.Collections.Generic; using UnityEngine; using Cysharp.Threading.Tasks; using System.Threading; using System.Threading.Tasks; using Unity.Mathematics; namespace BITKit.Animations { public class UnityAnimator : MonoBehaviour, IAnimator { [System.Serializable] public record AnimatorPlayEvent { public string stateName; public int index; } [System.Serializable] public class AnimatorLayerInfo { public string stateName; public string fullStateName; public AnimatorStateInfo currentState = new(); public event Action onStateEnter; public event Action onStateExit; public void OnStateEnter(string name) { onStateEnter?.Invoke(name); } public void OnStateExit(string name) { onStateExit?.Invoke(name); } } [Header(Constant.Header.Components)] public Animator animator; [Header(Constant.Header.State)] public bool isMatchingTarget; public AnimatorLayerInfo this[int index] { get { if (layerInfos.Count <= index) { for (int i = layerInfos.Count - 1; i < index; i++) { layerInfos.Add(new()); } } return layerInfos[index]; } } public List layerInfos = new(); [Header(Constant.Header.InternalVariables)] private readonly Dictionary _registryStates=new (); public void CrossFade(string name, float duration, int index = 0, float normalizedTimeOffset = 0) { animator.CrossFade(name, duration, index); } public void Play(string name, int index = -1, float normalizedTimeOffset = 0) { name = name.Replace(".", "_"); if (_registryStates.TryGetValue(name, out var stateInfo) && stateInfo.variables?.Length > 0) { name = stateInfo.variables.Random(); } animator.Play(name, index, normalizedTimeOffset); } public void Play(string name) { Play(name,-1,0); } public void OnStateEnter(int index, string name) { this[index].fullStateName = name; foreach (var item in name.Split(".")) { name = item; break; } this[index].stateName = name; this[index].OnStateEnter(name); } public void OnStateExit(int index, string name) { this[index].OnStateExit(name); } public float3 GetRootVelocity() { return animator.velocity; } private void Start() { foreach (var x in animator.GetBehaviours()) { _registryStates.TryAdd(x.stateName, x); } } private void Update() { int index = 0; foreach (var x in layerInfos) { x.currentState = animator.GetCurrentAnimatorStateInfo(index++); } isMatchingTarget = animator.isMatchingTarget; } } }