Learn how FSM_API uses decoupled state machines to run a

Learn how FSM_API uses decoupled state machines to run a "Fox and Dog" AI simulation.

Leader posted 3 min read

Implementing Behavior Trees with FSM_API: The Quick Brown Fox and Lazy Sleeping Dog Demo

Finite State Machines (FSMs) are a foundational pattern for organizing complex logic in software, from game AI to business workflows. The FSM_API library provides a high-performance, engine-agnostic C# solution for building and managing these systems with clarity and efficiency.

This article dives into the Quick Brown Fox and Lazy Sleeping Dog demo, an excellent, practical example found in the FSM_API public repository. It showcases how to implement simple, interacting AI agents, effectively decoupling agent data from agent behavior logic using the library's core features.


FSM_API Core Concepts in the Demo

Every behavioral entity in this simulation—the Fox and the Dog—relies on three core FSM_API concepts:

  1. The State Context (IStateContext): This is your actual game object (the Fox or the Dog), holding the data (e.g., Position, Speed, CollidedAgents) and implementing the transition methods. It must implement the IStateContext interface, which requires providing a Name and an IsValid property.
  2. The FSM Definition: This is the reusable blueprint of states (e.g., "Sleeping", "Walking") and the rules for transitioning between them.
  3. The FSM Instance: This is the live, active version of the blueprint, associated with a specific agent context. Both agents' FSMs are set up to run in the "Update" processing group.

The Lazy Sleeping Dog's Behavior

The LazySleepingDog class is initialized at Position = 3 and starts in the "Sleeping" state. Its FSM defines a classic threat response lifecycle:

State OnUpdate Action Transition Condition (to) Transition Target
Sleeping Console log: "...is sleeping!" IsAwake(context): CollidedAgents.Any() Awake
Awake Console log: "...is awake!" ShouldChase(context): VisibleAgents.Any(s => s is QuickBrownFox) Chasing
Chasing Position increases by Speed (set to 3 on enter) IsMangling(context): CollidedAgents.Any(s => s is QuickBrownFox) Mangling
Mangling Console log: "...is Mangling the fox!" N/A N/A

Crucially, in the "Mangling" state's OnEnterMangling handler, the dog directly uses the FSM_API to transition the collided agent's state (the Fox) to "Mangled":

// Inside OnEnterMangling for the dog
dog.CollidedAgents.FirstOrDefault()?.State.TransitionTo("Mangled"); 
````

-----

##  The Quick Brown Fox's Behavior

The `QuickBrownFox` starts at `Position = 0` and its FSM defines its attempts to flee the dog and reach a winning position:

| State | OnUpdate Action | Transition Condition (to) | Transition Target |
| :--- | :--- | :--- | :--- |
| **Walking** | `Position` increases by `Speed` (1) | `ShouldJump(context)`: `VisibleAgents` within 2 units | **Jumping** |
| **Jumping** | `Position` increases by `Speed` (1) | `ShouldLand(context)`: `Position` reaches `JumpEnd` (initial position + 2) | **Walking** |
| **Fleeing** | `Position` increases by `Speed` (set to 2 on enter) | N/A | N/A |
| **Mangled** | Console log: *"...is being mangled\!"* | N/A | N/A |

The Fox's ultimate defensive move is the transition to **"Fleeing"**, which is triggered by a direct collision with a `LazySleepingDog`. However, if the Dog catches it while fleeing, the Dog forces the Fox into the terminal **"Mangled"** state.

-----

##  The Simulation Loop (`SimpleDemoContext`)

The `SimpleDemoContext` acts as the game manager, controlling the flow of the entire application. It sets up the following structure:

1.  **Processing Groups:** It creates a **"Main"** group for the application's FSM (`AppFSM`) and an **"Update"** group where the agents' FSMs run.
2.  **Tick Logic:** The core simulation runs in `OnUpdateExecuting`:
      * It **clears** previous frame's agent data.
      * It performs **Vision and Collision** checks based on the agents' current `Position` and `Sight` range, populating the `VisibleAgents` and `CollidedAgents` lists.
      * It calls `FSM_API.Interaction.Update("Update")`. This single call iterates through and updates *all* FSM instances assigned to the "Update" group (the Fox and the Dog), triggering their `onUpdate` actions and checking their transition conditions.
3.  **Shutdown:** The application's `AppFSM` transitions to **"Shutdown"** if a key is pressed, if the Fox reaches the `WinPosition` (10), or if **any agent's state is "Mangled"**. The FSM\_API then manages the cleanup.

The `Program.cs` file initiates the simulation and loops the main update call until the application context becomes invalid. This structure demonstrates how FSM\_API cleanly separates an agent's **Data** (`IStateContext` properties) from its **Behavioral Logic** (the FSM Definition) and relies on a central **Simulation Tick** (`FSM_API.Interaction.Update()`) to drive complex, interactive AI.

-----

##  Stay Tuned for the Advanced Demo

This simple, 1D simulation laid the groundwork, but the next step is building a true environment\!

**Stay tuned for a follow-up article** where we'll use these **exact same agent FSMs** to create an **advanced 2D environment** with **multiple dogs and foxes** interacting simultaneously. This will highlight the true power of **decoupled FSM definitions**.

Follow us to stay informed\! And for much more content, advanced articles, and discussions about our vision for the **software for the singularity**, check out our:

[**Patreon Page**](https://www.patreon.com/TheSingularityWorkshop)

-----

## Get the Code

You can explore the full implementation of this FSM-driven AI simulation and the FSM\_API library structure by cloning the public repository:

[**https://github.com/TrentBest/SimpleDemos**](https://github.com/TrentBest/SimpleDemos)

If you read this far, tweet to the author to show them you care. Tweet a Thanks
0 votes
0 votes

More Posts

What Is “State” in JavaScript, and How to Use It in Your Projects

Michael Larocca - Sep 23

FSM_API by The Singularity Workshop

The Singularity Workshop - Oct 9

Popular platforms for online coding and development. How an AI Platform Uses Them to Export Code

Sunny - Sep 2

A Guide to Systems-Based Development

Trent Polack - Jul 16

Learn how to write GenAI applications with Java using the Spring AI framework and utilize RAG for improving answers.

Jennifer Reif - Sep 22, 2024
chevron_left