Example #1
0
def main():
    screen = p.display.set_mode((WIDTH, HEIGHT))
    clock = p.time.Clock()
    screen.fill(p.Color(WHITE))
    gs = GameState()  # gs is the game state
    validMoves = gs.getValidMoves()
    moveMade = False
    loadImages()  # we are only loading the images once in pygame
    running = True
    sqSelected = ()  # keeps track of the last user mouse clicks
    playerClicks = []  # keeps track of the last player clicks
    while running:
        for e in p.event.get():
            if e.type == p.QUIT:
                running = False
            # mouse key handlers
            elif e.type == p.MOUSEBUTTONDOWN:
                location = p.mouse.get_pos()  # location of x and y
                col = location[0] // SQ_SIZE
                row = location[1] // SQ_SIZE
                if sqSelected == (row, col):
                    sqSelected = ()
                    playerClicks = []
                # if the player clicks on a chess piece
                else:
                    sqSelected = (row, col)
                    playerClicks.append(
                        sqSelected
                    )  # this appends both the 1st and the 2nd clicks
                if len(playerClicks) == 2:  # if the user made 2 mouse clicks
                    move = Move(playerClicks[0], playerClicks[1], gs.board)
                    print(
                        str(move.getChessNotation()) + ' id: ' +
                        str(move.moveID))

                    for i in range(len(validMoves)):
                        if move == validMoves[i]:
                            gs.makeMove(validMoves[i])
                            moveMade = True
                            sqSelected = ()
                            playerClicks = []  # resets user clicks
                    if not moveMade:
                        playerClicks = [sqSelected]

            # keyboard handlers
            elif e.type == p.KEYDOWN:
                if e.key == p.K_z:  # the undo key
                    gs.undoMove()
                    moveMade = True

        if moveMade:
            validMoves = gs.getValidMoves()
            moveMade = False

        drawGameState(screen, gs)
        clock.tick(MAX_FPS)
        p.display.flip()
Example #2
0
def minimax(board: GameState, alpha: float, beta: float, maximizer: bool,
            curDepth: int, max_depth: int) -> Tuple[float, Move]:
    """
        returns an integer score and move which is the best current player can get
    """
    if board.is_game_over():
        if board.staleMate:
            return 0, None
        if board.checkMate:
            return (-inf if maximizer else +inf), None
    if curDepth == max_depth:
        return evaluate(board, not (board.whiteToMove ^ maximizer)), None

    # sending inf so that the branch is ignored by parent
    if final_move is not None and time() - stime > timeout:
        return +inf if maximizer else -inf, None

    moves = list(board.getValidMoves())
    # moves.sort(key=move_score, reverse=True)
    assert moves != []
    best_move = None
    if maximizer:
        best_score = -inf

        def is_better_score(curr, currbest):
            return curr >= currbest

        def update_AB(score):
            nonlocal alpha
            alpha = max(alpha, score)

    else:
        best_score = +inf

        def is_better_score(curr, currbest):
            return curr <= currbest

        def update_AB(score):
            nonlocal beta
            beta = min(beta, score)

    for move in moves:
        board.makeMove(move, by_AI=True)
        global moves_cnt
        moves_cnt += 1
        curr_score, _ = minimax(board, alpha, beta, not maximizer,
                                curDepth + 1, max_depth)
        board.undoMove()
        if is_better_score(curr_score, best_score):
            best_score = curr_score
            best_move = move
            update_AB(best_score)
            if alpha >= beta:
                break

    return best_score, best_move
Example #3
0
def minimax(board: GameState, moves: List[Move], alpha: float, beta: float, maximizer: bool, curDepth: int, max_depth: int, moves_line: List[Move]) -> Tuple[float, Move, List[Move]]:
    """
        returns an integer score and move which is the best current player can get
    """
    if board.is_game_over():
        moves_line.append(None)
        if board.staleMate:
            return 0, None, moves_line
        if board.checkMate:
            return (-inf if maximizer else +inf), None, moves_line
    if curDepth == max_depth:
        return evaluate(board, not(board.whiteToMove ^ maximizer)), None, moves_line

    # sending inf so that the branch is ignored by parent
    if final_move is not None and time() - stime > timeout:
        moves_line.append(None)
        return +inf if maximizer else -inf, None, moves_line

    # moves = list(board.getValidMoves())
    assert moves != []
    best_move = None
    best_line = []
    best_score = -inf if maximizer else +inf

    for move in moves:
        board.makeMove(move, by_AI=True)
        moves_line.append(move)
        global moves_cnt
        moves_cnt += 1
        curr_score, _, curr_line = minimax(
            board, board.getValidMoves(), alpha, beta, not maximizer, curDepth+1, max_depth, moves_line[:])
        board.undoMove()
        moves_line.pop()
        if maximizer:
            if curr_score >= best_score:
                best_score, best_move, best_line = curr_score, move, curr_line
            alpha = max(alpha, best_score)
        else:
            if curr_score <= best_score:
                best_score, best_move, best_line = curr_score, move, curr_line
            beta = min(beta, best_score)

        if alpha >= beta:
            break

    return best_score, best_move, best_line