我穿着睡衣做了一个简单的井字游戏,但我遇到了一些错误 [英] Im making a simple TicTacToe in pyjama but I am running into some errors

查看:43
本文介绍了我穿着睡衣做了一个简单的井字游戏,但我遇到了一些错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

draw Board 函数有一个 if 语句来查看它应该绘制哪个颜色的圆圈.但是当单击鼠标按钮时,它会在右侧的 x 坐标中绘制圆圈,但在相反的 y 坐标中.此外,结尾有点奇怪,我想显示获胜者,然后使用 time.wait 等待,但它等待然后打印语句一秒钟.如果你能运行它,你就会明白.我也在寻找我可以做出的总体改进.

The draw Board functions has an if statement to see which colour circle it should draw. But when the mouse button is clicked it draws the circle in the right x coordinate but in the opposite y coordinate. Also, the end is a little bit weird I want to display the winner and then wait using time.wait but it waits and then prints the statement for a second. If you could run it, you would understand. I am also looking for general improvements that I could make.

import pygame, sys
import numpy as np
import math

pygame.init()
clock = pygame.time.Clock()

# Colours
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
RED = (255, 0, 0)
GREEN = (0, 255, 0)

ROW_COUNT = 3
COLUMN_COUNT = 3
SQUARE_SIZE = 100
RADIUS = int(SQUARE_SIZE/2 - 5)

WIDTH = COLUMN_COUNT * SQUARE_SIZE
HEIGHT = ROW_COUNT * SQUARE_SIZE

myfont = pygame.font.SysFont("monospace", 20)

PLAYER_COUNT = 2
screen = pygame.display.set_mode((WIDTH, HEIGHT))
screen.fill(WHITE)


class Player:
    def __init__(self, number):
        self.number = number


players = [Player(i) for i in range(1, PLAYER_COUNT + 1)]


class Board:
    def __init__(self):
        self.board_body = np.zeros((ROW_COUNT, COLUMN_COUNT), dtype=np.uint8)
        self.remaining_spaces = 9
        self.print_board()
        self.draw_board()

    def print_board(self):
        print(np.flip(self.board_body, 0))

    def draw_board(self):
        one_x, one_y, one_end_x, one_end_y, two_x, two_y, two_end_x, two_end_y = 100, 0, 100, 300, 0, 100, 300, 100
        for r in range(ROW_COUNT):
            for c in range(COLUMN_COUNT):
                pygame.draw.line(screen, BLACK, (one_x, one_y), (one_end_x, one_end_y), 3)
                one_x += 100
                one_end_x += 100
            pygame.draw.line(screen, BLACK, (two_x, two_y), (two_end_x, two_end_y), 3)
            two_y += 100
            two_end_y += 100

        for c in range(COLUMN_COUNT):
            for r in range(ROW_COUNT):
                if self.board_body[r][c] == 1:
                    pygame.draw.circle(screen, RED, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), HEIGHT - int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
                elif self.board_body[r][c] == 2:
                    pygame.draw.circle(screen, GREEN, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), HEIGHT - int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
    pygame.display.update()

    def check_empty_space_and_place(self, row, column, number):
        if self.board_body[row][column] == 0:
            self.board_body[row][column] = number
            self.remaining_spaces -= 1

    def check_winning_move(self, board, piece):
        # Horizontal
        for c in range(COLUMN_COUNT - 1):
            for r in range(ROW_COUNT - 1):
                if board[r - 1][c] == piece and board[r][c] == piece and board[r + 1][c] == piece:
                    return True

        # Vertical
        for c in range(0, COLUMN_COUNT - 1):
            for r in range(0, ROW_COUNT - 1):
                if board[r][c - 1] == piece and board[r][c] == piece and board[r][c + 1] == piece:
                    return True
        # Positively sloped diagonals
        for c in range(0, COLUMN_COUNT - 1):
            for r in range(0, ROW_COUNT - 1):
                if board[r][c] == piece and board[r + 1][c + 1] == piece and board[r + 2][c + 2] == piece:
                    return True

        # Negatively sloped diagonals
        for c in range(COLUMN_COUNT - 1):
            for r in range(ROW_COUNT - 1):
                if board[r + 1][c + 1] == piece and board[r][c] == piece and board[r - 1][c - 1] == piece:
                    return True


def next_player():
    while True:
        for player in players:
            yield player


player_generator = next_player()

board = Board()

run = True

while run:
    if board.remaining_spaces == 0:
        run = False
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()

        if event.type == pygame.MOUSEBUTTONDOWN:
            pos_of_mouse = pygame.mouse.get_pos()
            posx = pos_of_mouse[0]
            posy = pos_of_mouse[1]
            column = int(posx // SQUARE_SIZE)
            row = int(posy // SQUARE_SIZE)
            p = player_generator.__next__()
            board.check_empty_space_and_place(row, column, p.number)
            board.draw_board()
            if board.check_winning_move(board.board_body, p.number):
                label = myfont.render("Player {} wins!!!!".format(p.number), False, WHITE)
                screen.fill(BLACK)
                screen.blit(label, (20, 50))
                pygame.time.wait(3000)
                run = False

    board.print_board()
    pygame.display.update()
    clock.tick(60)```

推荐答案

在 PyGame 坐标系中,左上角是 (0, 0).您不必翻转 y 轴或从高度中减去 y 坐标.删除Board类的方法draw_board中的HEIGHT - :

In the PyGame coordinate system the top left is (0, 0). You don't have to flip the y-axis or subtract the y-coordinate from the height. Remove the term HEIGHT - in the method draw_board of the class Board:

class Board:
    # [...]

    def draw_board(self):
        # [...]

        for c in range(COLUMN_COUNT):
            for r in range(ROW_COUNT):
                if self.board_body[r][c] == 1:
                    pygame.draw.circle(screen, RED, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
                elif self.board_body[r][c] == 2:
                    pygame.draw.circle(screen, GREEN, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
        
        # [...]


如果只是等待一段时间,可以使用pygame.time.waitpygame.time.delay.但是,如果要显示消息然后等待一段时间,则需要事先更新显示.仅当 pygame.display.update()pygame.display.flip()叫做.此外,您必须通过 pygame 处理事件.event.pump(),在显示的更新在窗口中变得可见之前:
(参见 如何在 pygame 中等待一段时间?)

screen.fill(BLACK)
screen.blit(label, (20, 50))
pygame.display.flip()
pygame.event.pump()
pygame.time.wait(3000)


此外,在寻找获胜者时也存在一些错误.哟根本不需要嵌套循环.只有 2 条对角线.所以对角线不需要任何循环:


Also, there are some mistakes when looking for a winner. Yo don't need nestes loops at all. There are just 2 diagonals. So you don't need any loops for the diagonals:

class Board:
    # [...]

    def check_winning_move(self, board, piece):
        # Horizontal
        for c in range(COLUMN_COUNT):
            if board[0][c] == piece and board[1][c] == piece and board[2][c] == piece:
                return True

        # Vertical
        for r in range(ROW_COUNT):
            if board[r][0] == piece and board[r][1] == piece and board[r][2] == piece:
                return True

        # Positively sloped diagonals
        if board[0][0] == piece and board[1][1] == piece and board[2][2] == piece:
            return True

        # Negatively sloped diagonals
        if board[0][2] == piece and board[1][1] == piece and board[2][0] == piece:
            return True


另见 Pygame Tic Tak脚趾逻辑?我该怎么做.

完整代码:

import pygame, sys
import numpy as np
import math

pygame.init()
clock = pygame.time.Clock()

# Colours
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
RED = (255, 0, 0)
GREEN = (0, 255, 0)

ROW_COUNT = 3
COLUMN_COUNT = 3
SQUARE_SIZE = 100
RADIUS = int(SQUARE_SIZE/2 - 5)

WIDTH = COLUMN_COUNT * SQUARE_SIZE
HEIGHT = ROW_COUNT * SQUARE_SIZE

myfont = pygame.font.SysFont("monospace", 20)

PLAYER_COUNT = 2
screen = pygame.display.set_mode((WIDTH, HEIGHT))
screen.fill(WHITE)


class Player:
    def __init__(self, number):
        self.number = number


players = [Player(i) for i in range(1, PLAYER_COUNT + 1)]


class Board:
    def __init__(self):
        self.board_body = np.zeros((ROW_COUNT, COLUMN_COUNT), dtype=np.uint8)
        self.remaining_spaces = 9
        self.print_board()
        self.draw_board()

    def print_board(self):
        print(np.flip(self.board_body, 0))

    def draw_board(self):
        one_x, one_y, one_end_x, one_end_y, two_x, two_y, two_end_x, two_end_y = 100, 0, 100, 300, 0, 100, 300, 100
        for r in range(ROW_COUNT):
            for c in range(COLUMN_COUNT):
                pygame.draw.line(screen, BLACK, (one_x, one_y), (one_end_x, one_end_y), 3)
                one_x += 100
                one_end_x += 100
            pygame.draw.line(screen, BLACK, (two_x, two_y), (two_end_x, two_end_y), 3)
            two_y += 100
            two_end_y += 100

        for c in range(COLUMN_COUNT):
            for r in range(ROW_COUNT):
                if self.board_body[r][c] == 1:
                    pygame.draw.circle(screen, RED, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
                elif self.board_body[r][c] == 2:
                    pygame.draw.circle(screen, GREEN, (int(c * SQUARE_SIZE + SQUARE_SIZE / 2), int(r * SQUARE_SIZE + SQUARE_SIZE / 2)), RADIUS)
    pygame.display.update()

    def check_empty_space_and_place(self, row, column, number):
        if self.board_body[row][column] == 0:
            self.board_body[row][column] = number
            self.remaining_spaces -= 1

    def check_winning_move(self, board, piece):
        # Horizontal
        for c in range(COLUMN_COUNT):
            if board[0][c] == piece and board[1][c] == piece and board[2][c] == piece:
                return True

        # Vertical
        for r in range(ROW_COUNT):
            if board[r][0] == piece and board[r][1] == piece and board[r][2] == piece:
                return True

        # Positively sloped diagonals
        if board[0][0] == piece and board[1][1] == piece and board[2][2] == piece:
            return True

        # Negatively sloped diagonals
        if board[0][2] == piece and board[1][1] == piece and board[2][0] == piece:
            return True


def next_player():
    while True:
        for player in players:
            yield player


player_generator = next_player()

board = Board()

run = True

while run:
    if board.remaining_spaces == 0:
        run = False
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()

        if event.type == pygame.MOUSEBUTTONDOWN:
            pos_of_mouse = pygame.mouse.get_pos()
            posx = pos_of_mouse[0]
            posy = pos_of_mouse[1]
            column = int(posx // SQUARE_SIZE)
            row = int(posy // SQUARE_SIZE)
            p = player_generator.__next__()
            board.check_empty_space_and_place(row, column, p.number)
            board.draw_board()
            if board.check_winning_move(board.board_body, p.number):
                label = myfont.render("Player {} wins!!!!".format(p.number), False, WHITE)
                screen.fill(BLACK)
                screen.blit(label, (20, 50))
                pygame.display.flip()
                pygame.event.pump()
                pygame.time.wait(3000)

                run = False

    board.print_board()
    pygame.display.update()
    clock.tick(60)

这篇关于我穿着睡衣做了一个简单的井字游戏,但我遇到了一些错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆