using System.Collections.Generic; using UnityEngine; // This class inherits from MonoBehaviour so it can be attached to a GameObject. public class StateMachine : MonoBehaviour { // A Stack is used to manage states. The top of the stack is the current state. // This allows for easily returning to previous states by "popping" the current one. public Stack States { get; set; } private void Awake() { // Initialize the stack when the object is created. States = new Stack(); } private void Update() { // Each frame, execute the logic of the current state (if one exists). State currentState = GetCurrentState(); if (currentState != null) { currentState.Execute(); } } // Pushes a new state onto the stack, making it the current state. public void PushState(System.Action active, System.Action onEnter, System.Action onExit) { // Run the OnExit method of the old state before adding the new one. if (GetCurrentState() != null) { GetCurrentState().OnExit(); } // Create the new state and push it to the stack. State state = new State(active, onEnter, onExit); States.Push(state); // Run the OnEnter method for the new current state. GetCurrentState().OnEnter(); } // Removes the current state from the stack, returning to the one below it. public void PopState() { if (GetCurrentState() != null) { GetCurrentState().OnExit(); States.Pop(); // Run the OnEnter of the newly revealed state. if (GetCurrentState() != null) { GetCurrentState().OnEnter(); } } } // A helper method to safely get the state at the top of the stack. private State GetCurrentState() { // Uses a ternary operator to return the top state or null if the stack is empty. return States.Count > 0 ? States.Peek() : null; } }