Finite state machines - How would you implement this?

Playing around with finite state machines for controlling unit behaviors in an RTS type game.

Often I can have a state such as “MoveToGuardPosition” and another called “LookingForEnemies”. But the problem is that sometimes I need a bit of both. For example while performing the “MoveToGuardPosition” state I also need to look for enemies (+ other things), if not they can freely attack my unit which will continue executing his “MoveToGuardPosition” state until reaching his destination.

One way to solve this is of course to check for units in the “MoveToGuardPosition” state. But soon a lot of code gets duplicated to many different states.

Is there a good solution to this? What would you do? I know of behavior trees, but how is this generally solved when using FSMs?

maybe this can give you a direction: http://www.youtube.com/watch?v=o6CaB-hmqoE&feature=youtu.be

Typically if there is stuff an agent needs to perform regardless of what else he’s doing (like, for instance, being aware of his surroundings and if enemies are nearby) then you would put that in a Global State that is executed regardless of what the current state is.

Think more object oriented? Make your method to target enemies, and a method to attack targets. (Then you already have targets and you can add a method to modify movement based on the presence of a target and the desired behaviur: run away, move into range, stop when in range…) and call these methods in the state based on flags. Is it an attack move? run the attack method too. No? Just run the basic movement method - no target acquisition or attack. You can store the methods in a central location and use them in all of your states.

What I did here, that I thought worked out pretty well, was to have a generic FSM class, that manages two things: States and Events.

States are, well, states… They have callbacks for update, fixedUpdate, lateUpdate, and for Enter and Leave events. Those all come in from the FSM class.

Events are objects that define transitions between states. They also have callbacks, one that returns a bool for evaluating a condition (which causes the event transition to happen), and another for when the event fires. Events are added to states (through the FSM), and can be added to multiple states, or to all states excluding a few given ones (very useful this).

So, basically it works on a simple loop, that just calls the updates on the current state, and for each event assigned to it, calls the updates on that too, and runs each event’s condition evaluation. If that evaluation passes, it switches to the next state (defined on the Event), calling the Leave and Enter methods on the appropriate states.

What makes this very handy, is that because all states are just collections of callbacks, you can assign methods that do things to each state, and multiple states can share the same methods.

For instance, if I have a method that controls character movement on the ground, I can assign that method to any state in which the character is movable on the ground. Similarly, if I have a ‘jump’ event, I can assign that event to multiple states, like idling on the ground, walking, and running. That way, you don’t repeat any code at all. You just assign the same methods to multiple states and events, however you want.

It takes some thinking to organize it all before coding, but then again, all FSMs do.

Cheers

Interesting solution :slight_smile:

What I basically did in the end is a simplified version of what you propose. I basically put all shared things in methods in a static class. Each method then returns true or false if that condition was a success or fail. For example “StateBehaviors.TryFindEnemyUnit(…)” if it did it will return true and I will for example not continue doing a “TryFindEnemyBuilding”. Works well enough, but I am sure better methods such as yours exist. However it’s hard to find methods (using FSMs) that are commonly known or used, maybe because they don’t exist because in the end most create their own solutions such as yours or mine :slight_smile:

Also one thing I like with my state code is that I never use Update() or FixedUpdate() etc instead I use coroutines so that I don’t have to run them as often. But then my states are mostly related to behavior (searching for enemies etc) rather than updating animations. When switching states I always make a .StopAllCoroutines() “under the hood” which works great and makes the code a lot cleaner for state transitions.

Have you looked at PlayMaker?

You can integrate it into your existing scripts and vice versa.