class Connect4GetCurrentPlayerTest(unittest.TestCase):
    """Tests the Game's get_current_player method."""

    def setUp(self):
        self.game = Game()
        self.game.add_player("Tiffany", "\u25cb")
        self.game.add_player("Kyle", "\u25cf")

    def tearDown(self):
        del self.game

    def test_player_one(self):
        """
        Ensures the Game returns the first Player if turn is even
        :return: Returns None
        """
        self.game.turn = 8
        current_player = self.game.get_current_player()
        self.assertEqual(current_player, Player("Tiffany", "\u25cb"))

    def test_player_two(self):
        """
        Ensures the Game returns the second Player if turn is odd
        :return: Returns None
        """
        self.game.turn = 17
        current_player = self.game.get_current_player()
        self.assertEqual(current_player, Player("Kyle", "\u25cf"))
예제 #2
0
class Connect4UpdatePlayerTest(unittest.TestCase):
    """Tests the Game's update_player method."""
    def setUp(self):
        self.game = Game()
        self.game.add_player("Tiffany", "\u25cb")
        self.game.add_player("Kyle", "\u25cf")

    def tearDown(self):
        del self.game

    def test_update_player(self):
        """
        Ensures that the game increments the turn when asked.
        :return: Returns None
        """
        self.game.update_player()
        self.assertEqual(self.game.turn, 1, "Fails to increment Game.turn")
예제 #3
0
class Connect4UpdateBoardTest(unittest.TestCase):
    """Tests the Game.update_board method."""
    def setUp(self):
        self.game = Game()
        self.game.add_player("Tiffany", "\u25cb")
        self.game.add_player("Kyle", "\u25cf")

    def tearDown(self):
        del self.game

    def test_with_token_one(self):
        """
        Ensures that an initial token correctly places in a column.
        :return: Returns None
        """
        self.game.update_board(4)

        board = [[" "] * 6, [" "] * 6, [" "] * 6, [" "] * 6,
                 ["\u25cb"] + [" "] * 5, [" "] * 6, [" "] * 6]

        self.assertEqual(self.game.board, board,
                         "Fails to update first in column correctly")

    def test_with_token_two(self):
        """
        Ensures that a second token correctly places in a column.
        :return: Returns None
        """
        self.game.update_board(4)
        self.game.turn += 1
        self.game.update_board(4)

        board = [[" "] * 6, [" "] * 6, [" "] * 6, [" "] * 6,
                 ["\u25cb"] + ["\u25cf"] + [" "] * 4, [" "] * 6, [" "] * 6]

        self.assertEqual(self.game.board, board,
                         "Fails to update first in column correctly")
예제 #4
0
class Connect4:
    """The Controller for the Connect 4 game."""
    def __init__(self):
        self.view = View()
        self.model = Game()

    def main(self):

        # Clear the console, and print the instructions.
        self.view.show_instructions()

        # Create the two players
        self.create_player('\u25cf')
        self.create_player('\u25cb')

        self.view.welcome_players(self.model.get_current_player().name)

        while not self.update_player():
            move = -1
            msg = ""
            while move < 0:
                self.view.print_board(self.model.get_board())
                move = self.get_move(self.model.get_current_player().name, msg)
                if self.check_move(self.model.get_board(), move):
                    row = self.model.update_board(move)
                    self.model.get_board()[move][row] = ' '
                    self.view.animate_turn(
                        move, row,
                        self.model.get_current_player().token,
                        self.model.get_board())
                else:
                    msg = "That move is not legal; the column is full."
                    move = -1
            is_won = self.winner_check(self.model.get_board(),
                                       self.model.get_current_player().token)
            if is_won:
                self.view.declare_awesome(self.model.get_current_player().name)
                break
        else:
            self.view.declare_sadness()

    def create_player(self, token):
        """
        Create a player by prompting for their name,
        and then storing that in the model Game.
        :param token: color this player's pieces will be
        :return: Returns None
        """
        name = self.view.get_player_name()
        self.model.add_player(name, token)

    def get_move(self, name, msg=""):
        """
        Gets a move from the user to pass to the game.
        :return: the column of Player's choice (int)
        """
        return self.view.get_player_move(name, msg) - 1

    def check_move(self, board, column):
        """
        Verifies that a chosen move is legal.
        :param board: current state of the game board
        :param column: which column the player wants
        :return: whether the move is legal (bool)
        """
        # Check to make sure the column is not full.
        if board[column][5] == ' ':
            return True

        return False

    def winner_check(self, board, token):
        """
        Looks to see if the player that just moved won.
        :param board: current state of the game board
        :return: whether the move is legal (bool)
        """

        # Vertical
        # for each column, make it a string, look for substring of four in a row
        for col in board:
            if (token * 4) in ''.join(col):
                return True

        # Horizontal
        for i in range(6):
            if (token * 4) in ''.join(column[i] for column in board):
                return True

        # Diagonal Right

        for i, j in product(range(4), range(3)):
            if (token * 4) in ''.join(board[i + k][j + k] for k in range(4)):
                return True

        # Diagonal Left
        for i, j in product(range(4), range(3, 6)):
            if (token * 4) in ''.join(board[i + k][j - k] for k in range(4)):
                return True

        # No solution found, so return False
        return False

    def update_player(self):
        """
        Asks the game to update the turn and whether the
        game has ended in a tie.
        :return: whether the game ended in a tie (bool)
        """
        self.model.update_player()

        if self.model.turn == 42:
            return True

        return False