Blocking State Machine for turn-based system

Hi,

My goal is to create a Go game on Unity, but I’m having trouble in designing the turn-based system.
I followed this tutorial to implement a simple state machine for turn-based system, but it seems that I can’t block the switch statement to wait for a player finishing his turn.

The thing is I’d like to implement player vs. player and player vs. ai as simple as possible. I created two gameObjects : player and opponent, so that I can AddComponent the proper script I need (player or AI) in the opponent’s gameobject

I know i’m not supposed to block an Update() function, and coroutines aren’t the solution I need. I really need to split my turn-based system step by step :

1 - Player turn, he has to place a
pawn on the board

2 - Opponent turn, if this is a
player, simply places a pawn on the
board, else if this is an AI, runs an
algorithm then places a pawn on the
board.

My second problem is that, to represent the board, I have a grid of tiles which have an Highlighter script in it to “highlight” the pawn placement. The color is dependant from the turn (player or opponent), and I’m afraid that if I block in the turn-based system, it’ll block the Highlighter script (which contains Unity functions like OnMouseOver etc…)

Could anyone help me solving this ? :slight_smile:

Have a good day !

I don’t know if you need to make a state machine. To me it just sounds like you tell a player script that it is their turn and when the player is done, they tell the game they ended the turn.

public Material highlight;
public Player player1, player2;
Player current;

void Start()
{
    current = player1;
    current.BeginTurn(this); // tell the player its their turn
}

void Update()
{
    if (highlight && current)
        highlight.color = current.color; // set material color to players color
}

public void EndTurn() // called by the current player
{
    SwapPlayer();
    current.BeginTurn(this); // tell the next player to have a go at it
}

void SwapPlayer()
{
    current = current == player1 ? player2 : player1;
}

And to make it work with a human, AI or whatever you can think of, subclass player to the concrete type.

public class HumanPlayer : Player
{
    void Update() {
         if (!hasTurn)
             return;
         // if you need updates etc
    }
}

public class AIPlayer : Player
{
     public Board board;
     public override void BeginTurn(Game game)
     {
          AIEngine.PerformBestMove(board);
          game.EndTurn();
     }
}

Done. Thanks to @Statement who guided me to a simple process. :slight_smile:

I have :

  • a GamePreferences gameobject with static instance which contains preferences (pawn colors, ai or player) stored trough scenes (instead of Prefabs)
  • a TurnBasedSystem gameobject with static instance which stores both entities (player and opponent)
  • Player & Opponent gameobjects which contains the StartTurn() method (so they can interact with EndTurn() method from static TurnBasedSystem when they finished their turn)
  • and a Highlighter script attached to each tile of my board to make a “ghost pawn” while hovering over a tile

Highlighter consumes TurnBasedSystem to know which player is playin to get the matching pawn color.