using System; using System.Collections.Generic; #if UNITY_EDITOR using UnityEditor; using UnityEditor.UIElements; #endif using UnityEngine; using UnityEngine.UIElements; namespace BITKit.StateMachine { [Serializable] public abstract class MonoStateMachine { #if UNITY_EDITOR public abstract IState CurrentStateAsIState { get; } #endif } [Serializable] public class MonoStateMachine :MonoStateMachine , IStateMachine, IMonoProxy where TState : IState { public bool Enabled { get => _enabled; set { _enabled = value; if (CurrentState is null) return; if (value) { CurrentState.OnStateExit(null,null); } else { CurrentState.OnStateEntry(null); } } } public TState CurrentState { get; set; } public event Action OnStateChanged; [SerializeReference, SubclassSelector] public List states = new(); [SerializeField,ReadOnly] private string _currentStateName; public IDictionary StateDictionary { get; } = new Dictionary(); private bool _enabled; public void Initialize() { foreach (var state in states) { //state.TransitionState = InternalTransitionState; state.Initialize(); StateDictionary.Add(state.GetType(), state); } if (states.Count > 0) { TransitionState(states[0]); } } public void UpdateState() { if (Enabled) CurrentState?.OnStateUpdate(); } public void DisposeState() { } public void TransitionState() where State : TState { var nextState = StateDictionary.GetOrCreate(typeof(State)); TransitionState(nextState); } public void TransitionState(TState newState) { if (newState.Equals(CurrentState)) return; var oldState = CurrentState; if (oldState is not null) { oldState.OnStateExit(oldState, newState); oldState.Enabled = false; } newState.OnStateEntry(oldState); CurrentState = newState; OnStateChanged?.Invoke(oldState, newState); _currentStateName = newState.GetType().Name; newState.Enabled = true; } public override IState CurrentStateAsIState => CurrentState; } }