AttributeError: объект 'pygame.Rect' не имеет атрибута 'rect', ошибка при выполнении коллизии - PullRequest
2 голосов
/ 01 апреля 2020

Так что я пытаюсь сделать обнаружение столкновений для моей игры, используя экземпляры. Вот код:

class Paddle:
def __init__(self, x, y, width, height, rect):
    self.x = x
    self.y = y
    self.width = width
    self.height = height
    self.rect = pygame.rect.Rect(x, y, width, height)
class Ball:
    coordinateX = 600
    coordinateY = 300
    velocity = [random.randint(0,1),random.randint(-1,1)]

player = (Paddle(1100, 300, 10, 30, (1100, 300, 10, 30)))
enemy = Paddle(100, 300, 10, 30, (100, 30, 10, 30))
ball = (Ball.coordinateX, Ball.coordinateY, 15)

И позже:

ballRect = pygame.rect.Rect(Ball.coordinateX, Ball.coordinateY, 10, 10)
if pygame.sprite.collide_rect(player, ballRect):
    bounce()

Ответы [ 3 ]

2 голосов
/ 01 апреля 2020

Как подсказывает имя модуля "sprite", функция pygame.sprite.collide_rect и все другие функции обнаружения столкновений ожидают Sprite экземпляров в качестве аргументов.

Посмотрите документацию :

pygame.sprite.collide_rect()
Обнаружение столкновений между двумя спрайтами с использованием rects.
collide_rect(left, right) -> bool

Тесты на столкновение между двумя спрайтами. Использует функцию Pygame Rect Colliderect для расчета столкновения. Предназначен для передачи в качестве функции обратного вызова с коллизиями в функции * collide. Спрайты должны иметь атрибуты "rect".

(Кроме того, обычно вы не используете эту функцию напрямую, но вместе с Group).

Так что либо начните использовать класс Sprite (что вам и следует делать), либо используйте функции, предоставляемые классом Rect, например colliderect:

colliderect()
проверка, если два прямоугольника перекрываются
colliderect(Rect) -> bool

Возвращает true, если какая-либо часть любого прямоугольника перекрывается (кроме верхнего + нижнего или левого + правого краев ).

2 голосов
/ 01 апреля 2020

Прежде всего, при создании атрибута rect для вашего шара, он должен быть self.rect = pygame.Rect(x, y, width, height) (при условии, что вы импортируете Pygame с import pygame). Это должно обработать ваш AttributeError. То же самое касается ваших ballRect, ballRect = pygame.Rect(Ball.coordinateX, Ball.coordinateY, 10, 10).

Далее вы используете неправильную функцию обнаружения столкновений прямоугольника. pygame.sprite относится к чему-то совершенно другому в Pygame (его объектам Sprite), и ни ваш класс Ball, ни Paddle не являются спрайтами Pygame из написанного вами кода. Таким образом, вызывать pygame.sprite.collide_rect() здесь не имеет смысла.

Вместо этого вы должны просто использовать rect.colliderect, например, так:

if rect.colliderect(other_rect):
    # Colliding!
    print("Stop touching me!")

или в вашем случае:

if player.rect.colliderect(ballRect):
    bounce()

Кроме того, вам не нужно передавать rect в качестве аргумента для вашей Paddle инициализации, потому что он никогда не используется. rect объекта полностью сгенерирован из других ваших аргументов.

Наконец, ваш класс Ball и код создания экземпляра кажутся немного не соответствующими. Вы должны сгенерировать и инициализировать его, как вы делаете для Paddle.

РЕДАКТИРОВАТЬ И последнее. В pygame, когда вы создаете объект с атрибутом rect, вам больше не нужно присваивать объекту значения x и y, потому что всякий раз, когда они вам понадобятся, скажем, в blit, вы можете просто передать rect напрямую (или rect.x и rect.y в некоторых крайних случаях) в качестве аргумента position, и pygame прекрасно справится с остальными.

Вот как должен выглядеть ваш код (с исправлено еще несколько вещей):

class Paddle():
    def __init__(self, x, y, width, height):
        self.width = width
        self.height = height
        self.rect = pygame.Rect(x, y, width, height)

class Ball():
    def __init__(self, x, y, width, height):
        self.rect = pygame.Rect(x, y, width, height)
        self.velocity = [random.randint(0,1),random.randint(-1,1)]

player = Paddle(1100, 300, 10, 30)
enemy = Paddle(100, 300, 10, 30)
ball = Ball(600, 300, 10, 10)

# Other stuff

# Collision checking
if player.rect.colliderect(ball.rect):
    bounce()
1 голос
/ 01 апреля 2020

Согласно документации , pygame.sprite.collide_rect() используется для обнаружения столкновения между двумя спрайтами , однако вы передаете объект pygame.rect.Rect() и Paddle object.

Итак, вам нужно создать два объекта, используя pygame.sprite.Sprite, а затем обнаружить столкновение между ними, если вы хотите использовать pygame.sprite.collide_rect()

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...