Exemplo n.º 1
0
def get_all_possible_board_states(turn_num, primary_state, secondary_state):
    """
    Loops through all possible states of the board starting from the turn_num provided and ending on the last turn.
     Finally, collates them in a list

    :param turn_num: type: int
    The number of moves on the board

    :param primary_state: type: int
    The state of the player that had the first move, HUMAN_STATE or BOT_STATE

    :param secondary_state: type: int
    The state of the player that had the second move, HUMAN_STATE or BOT_STATE

    :return: type: list
    Containing all the possible board states given a turn number
    """
    # Check for valid turn number
    if turn_num < 0 or turn_num > 9:
        raise ValueError("Turn number must be between 0 and 9")

    # Return blank board for turn 0
    if not turn_num:
        return create_board()

    boards = []
    temp_boards = []

    board = create_board()

    # Player for that turn number
    for move in combinations(get_possible_moves(board), ceil(turn_num / 2)):
        temp_boards.append(deepcopy(board))
        for row, box in move:
            temp_boards[-1][row][
                box] = secondary_state if turn_num % 2 == 0 else primary_state

    # Other player
    for board in temp_boards:
        for move in combinations(get_possible_moves(board),
                                 floor(turn_num / 2)):
            boards.append(deepcopy(board))
            for row, box in move:
                boards[-1][row][
                    box] = primary_state if turn_num % 2 == 0 else secondary_state

            # Remove all won/terminal board states
            if win_check(boards[-1]):
                del boards[-1]

    return boards
def test_blank_board():
    """
    Testing for result consistency between the 3 approaches to minimax algorithm
    Testing algorithm result from evaluating a blank board
    """
    board = create_board()

    minimax_result = minimax(board, get_depth(board), True)
    minimax_soft_alpha_beta_result = minimax_soft_alpha_beta(
        board, get_depth(board), True, -inf, +inf)
    minimax_alpha_beta_result = minimax_alpha_beta(board, get_depth(board),
                                                   True, -inf, +inf)

    assert minimax_result == minimax_soft_alpha_beta_result

    assert minimax_alpha_beta_result[0] == minimax_result[0]
    assert minimax_alpha_beta_result[1][0] in minimax_result[1]
Exemplo n.º 3
0
 def __init__(self, name):
     Player.__init__(self, name)
     self.city_edges, self.edges = board.create_board()
     self.path = None
     self.path_costs = {}
     self.edge_costs = {}
     self.all_paths = []
     self.info = None
     self.edge_claims = None
     self.action_history = []
     self.cards_needed = Counter()
     self.remaining_edge = []
     self.path_clear = False
     # self.gui = None
     self.opponent_name = []
     self.player_cars_count = {}
     self.possible_cards = []
     self.bug_showed = False
Exemplo n.º 4
0
def main():
    """
    The main function of the application.
    Creates the board, players and loop their turns infinitely until a winner is found.
    """
    # Introduction
    print(
        "Welcome to the game of Tic Tac Toe, your opponent is a bot running the Minimax algorithm"
    )

    # Create Tic Tac Toe board
    board = create_board()

    # Create players
    human_mark, bot_mark = choose_mark()
    bot = Player(bot=True, state=BOT_STATE, mark=bot_mark)
    human = Player(bot=False, state=HUMAN_STATE, mark=human_mark)

    # Random starting player
    players = [human, bot]
    random.shuffle(players)

    # Loop turns
    while True:
        for player in players:
            print("\n{}'s turn".format(
                player_name := "Bot" if player.bot else "Human"))
            move = player.make_move(board)
            update_board(board, move, player)
            display_board(board, players)

            # Break infinite loop under conditions
            if win_check(board):
                return print("Game over. {} wins!".format(player_name))
            elif is_board_full(board):
                return print("Game over. Draw!")
Exemplo n.º 5
0
def main():
    """
    The main function of the game.
    Responsible for the setup of game window properties, creating players, scheduling scenes in the game, recording
    player statistics and looping the game.
    """
    # Setup game
    screen, clock = setup_game()

    # Create list of players
    players = []
    # Define whose turn
    player = None

    # Define stats recording
    records = {
        # Record turn number
        'turn_num': 0,
        # Record bot wins
        'bot_win': 0,
        # Record human wins
        'human_win': 0,
        # Record draws
        'draw': 0
    }

    # Define screen states
    intro = True
    game = True

    # Create a blank Tic Tac Toe board
    board = create_board()

    # Game loop
    while True:
        # tick rate
        clock.tick(30)

        mouse_position = pygame.mouse.get_pos()
        mouse_clicked = False

        for event in pygame.event.get():
            # Break loop if window is closed
            if event.type == pygame.QUIT:
                pygame.quit()
                sys.exit()

            # Break loop if ESC key is pressed
            elif event.type == pygame.KEYDOWN:
                if event.key == pygame.K_ESCAPE:
                    pygame.quit()
                    sys.exit()

            elif event.type == pygame.MOUSEBUTTONDOWN:
                mouse_clicked = True

        # White background/clear previous objects
        screen.fill(color_to_rgb("white"))

        if intro:
            # Draw selection screen
            interface_items = selection_screen(screen, mouse_position)
            render_items_to_screen(screen, interface_items)

            # Handle user input
            if mouse_clicked:
                human_input_selection_screen_handler(interface_items, players,
                                                     mouse_position)

            # Proceed to next screen if user selected a choice & assign players
            if players:
                # Unpack players
                bot, human = players[0], players[1]

                # Random starting player
                player = random.choice(players)

                # Move on to game screen
                intro = False
        elif game:
            # Game scene
            # Draw board information
            interface_items = board_information(screen, records)
            render_items_to_screen(screen, interface_items)

            # Draw tic tac toe board
            interface_items = game_board(screen, board, players)
            render_items_to_screen(screen, interface_items)

            # Check if game is finished
            if win_check(board):
                # Game is finished
                # Highlight the winning row
                interface_items = highlight_win(interface_items, board)
                render_items_to_screen(screen, interface_items)

                # Add delay
                post_game_delay()

                # Record stats
                record_win(player, records)

                # Reset board
                board = create_board()

                # Next game, random starting turn again
                player = random.choice(players)
            elif is_board_full(board):
                # Game is finished

                # Add delay
                post_game_delay()

                # Record stats
                record_draw(records)

                # Reset board
                board = create_board()

                # Next game, random starting turn again
                player = random.choice(players)
            else:
                # Game not finished
                # Make a move (bot/human)
                if player.bot:
                    # Bot turn
                    bot_move_input_handler(board, bot)
                else:
                    if mouse_clicked:
                        # Human turn
                        human_move_input_handler(board, interface_items,
                                                 mouse_position, human)

                # Cycle turns
                if get_turn_number(board) != records["turn_num"]:
                    if not win_check(board) and not is_board_full(board):
                        # Subsequent turns
                        player = human if player.bot else bot
                        records["turn_num"] = get_turn_number(board)

        # Update screen
        pygame.display.update()
Exemplo n.º 6
0
    def __init__(self, x_size=20, y_size=10):

        print('initializing gui')

        img = mpimg.imread('../gui/world2.png')
        plt.ion()  # uncomment to let go of string
        self.fig = plt.figure(
            figsize=(x_size, y_size))  # uncomment to let go of string
        imgplot = plt.imshow(img)
        plt.xlim([0, 1080])
        plt.ylim([700, 0])
        imgplot.axes.get_xaxis().set_visible(False)
        imgplot.axes.get_yaxis().set_visible(False)
        self.needs_reset = False

        # imgplot = plt.imdraw(img)
        self.place_cities()
        self.plot_board()
        self.set_colors()

        [city_edges, edges] = create_board()

        x_offset = 5
        y_offset = 5

        # Plot the edges for connecting cities
        for index1, edge in enumerate(edges):
            offset = 0
            for index2, edge2 in enumerate(edges):
                # Check if this is a double edge
                if edge.city1 is edge2.city1 and edge.city2 is edge2.city2 and edge is not edge2:
                    if (index1 > index2):
                        offset = -1
                    else:
                        offset = 1

            x_1 = []
            y_1 = []
            x_1.append(self.cities[edge.city1][0] + offset * x_offset)
            y_1.append(self.cities[edge.city1][1] + offset * y_offset)
            x_1.append(self.cities[edge.city2][0] + offset * x_offset)
            y_1.append(self.cities[edge.city2][1] + offset * y_offset)
            self.edge_colors[edge] = plt.plot(x_1, y_1,
                                              self.colors[edge.color])
            plt.setp(self.edge_colors[edge], linewidth=4)

            x_mean = (x_1[0] + x_1[1]) / 2
            y_mean = (y_1[0] + y_1[1]) / 2
            self.edge_means[edge] = [x_mean, y_mean]

            self.edge_weights[edge] = plt.plot(x_mean, y_mean, 'go')
            plt.setp(self.edge_weights[edge], 'ms', 15.0)
            self.edge_numbers[edge] = plt.text(x_mean - 5,
                                               y_mean + 5,
                                               str(edge.cost),
                                               fontdict=None)

        for city in self.cities:
            self.city_points[city] = plt.plot(self.cities[city][0],
                                              self.cities[city][1], 'ro')
            self.city_texts[city] = plt.text(self.cities[city][0] - 5,
                                             self.cities[city][1] + 5,
                                             '',
                                             fontdict=None)

        # Plot the numbers of cards player 1 and 2 have
        # First for player 1
        x = 705
        y = 33
        i = 0
        for i in range(9):
            self.player_1_cards[str(i)] = plt.text(x, y, '0', fontdict=None)
            x = x + 22
        self.p1_score = plt.text(x + 77, y, '0', fontdict=None)
        self.p1_cars = plt.text(x + 22, y, '0', fontdict=None)

        # Next for player 2
        x = 705
        y = 103
        i = 0
        for i in range(9):
            self.player_2_cards[str(i)] = plt.text(x, y, '0', fontdict=None)
            x = x + 22
        self.p2_score = plt.text(x + 77, y, '0', fontdict=None)
        self.p2_cars = plt.text(x + 22, y, '0', fontdict=None)

        self.cards['0'] = mpimg.imread('../gui/red.png')
        self.cards['1'] = mpimg.imread('../gui/orange.png')
        self.cards['2'] = mpimg.imread('../gui/blue.png')
        self.cards['3'] = mpimg.imread('../gui/yellow.png')
        self.cards['4'] = mpimg.imread('../gui/green.png')
        self.cards['5'] = mpimg.imread('../gui/pink.png')
        self.cards['6'] = mpimg.imread('../gui/black.png')
        self.cards['7'] = mpimg.imread('../gui/white.png')
        self.cards['8'] = mpimg.imread('../gui/wild.png')

        i = 0
        x = 0.858
        y = 0.78
        for i in range(5):
            self.table_card_slots.append(
                self.fig.add_axes([x, y - 0.020 * i, 0.034, 0.016],
                                  'auto_scale_on'))
            self.table_card_slots[i].get_xaxis().set_visible(False)
            self.table_card_slots[i].get_yaxis().set_visible(False)
        plt.draw()