/// <inheritdoc/> public Player PlayerMove(Player player, Coordinate coordinate) { CheckGameStatus(); if (!players.Values.Contains(player)) { throw new NotValidValueException("Player " + player + " wasn't in initialization", ErrorCode.PLAYER_NOT_EXISTS); } try { grid.Set(coordinate.X, coordinate.Y, GetCellPlayer(player)); } catch (NotValidStateException nvse) { if (nvse.ErrorCode == ErrorCode.VALUE_ALREADY_EXISTS) { throw new PlayerMovementException("This cell is already in use", ErrorCode.MOVEMENT_ERROR_MUST_RETRY); } else { throw; } } CellPlayer checkedPlayer = grid.Check(); if (checkedPlayer != CellPlayer.NONE) { Player winner; bool winnerPlayer = players.TryGetValue(checkedPlayer, out winner); if (winnerPlayer) { throw new TicTacToeGameOverException(winner.Name + " wins", winner, true); } else { throw new NotValidStateException("There was a problem with players dictionary data", ErrorCode.OUT_OF_RANGE); } } if (grid.IsFull()) { throw new GameOverException("Game Over. None wins"); } return(GetNextPlayer(player)); }