在我的pygame中,我有一个带有for循环的几个矩形。我有一个由圆形物体代表的玩家。它看起来像这样:
因此玩家可以使用箭头键移动,这会使每个键移动一个点。最终玩家不应该移动到这些矩形之外。所以每次他们搬家我想检查: 如果(任何绘制的矩形包含一个玩家):返回True否则返回False。
有没有简单的方法可以做到这一点?或者我应该彻底改变我的做法?
这是我现在拥有的这个例子的代码:
import pygame
pygame.init()
#grid
w = 25
h = 25
m = 2
size = (550, 700)
screen = pygame.display.set_mode(size)
screen.fill((255, 255, 255))
class Player:
def __init__(self):
self.x = 149
self.y = 14
self.r = 10
def draw(self):
pygame.draw.circle(screen, (255, 0, 0), (self.x, self.y), self.r)
def update(self,event):
if event.key == pygame.K_LEFT:
screen.fill((250, 250, 250))
self.x -= 27
self.draw()
elif event.key == pygame.K_RIGHT:
screen.fill((250, 250, 250))
self.x += 27
self.draw()
elif event.key == pygame.K_UP:
screen.fill((250, 250, 250))
self.y -= 27
self.draw()
elif event.key == pygame.K_DOWN:
screen.fill((250, 250, 250))
self.y += 27
self.draw()
player1 = Player()
player1.draw()
done = False
while not done:
for event in pygame.event.get():
if event.type == pygame.QUIT:
done = True
elif event.type == pygame.KEYDOWN:
player1.update(event)
for row in range(5):
for col in range(5):
if row == 0 or row == 4 or col == 0 or col == 4:
pygame.draw.rect(screen, (0,0,0), ((w + m) * col + m, ((h + m) * row + m), w, h), 1)
pygame.display.flip()
有一个 Rect.contains(Rect)函数,但如果一个矩形包含另一个矩形,则会检查它。是否可能有这样的函数基本上说:选择所有现有的矩形并检查它们是否包含(选择矩形)?
任何提示或帮助都绝对赞赏。如果这是完全错误的做法,请告诉我。
问候。
答案 0 :(得分:1)
您可以将circle
视为rectangle
。如果将所有对象视为矩形,则需要较少的计算(CPU功率)来检查冲突。
您必须创建包含所有矩形的列表,以便您可以使用此列表检查圈子位置 - 然后您可以使用circle_rect.colliderect(some_rect)
import pygame
# --- constants ---
#grid
W = 25
H = 25
M = 2
SIZE = (550, 700)
BLACK = ( 0, 0, 0)
WHITE = (255, 255, 255)
RED = (255, 0, 0)
FPS = 25
# --- classes ---
class Player:
def __init__(self):
# to keep position and size
self.rect = pygame.Rect(0, 0, 20, 20)
# set start position
self.rect.center = 149, 14
self.r = 10
def draw(self):
pygame.draw.circle(screen, RED, self.rect.center, self.r)
def update(self, event):
# create copy of position
newrect = self.rect.copy()
# move "copy" to new position
if event.key == pygame.K_LEFT:
newrect.x -= 27
elif event.key == pygame.K_RIGHT:
newrect.x += 27
elif event.key == pygame.K_UP:
newrect.y -= 27
elif event.key == pygame.K_DOWN:
newrect.y += 27
# check if "copy" is still in rectangles
for rectangle in all_rectangles:
if newrect.colliderect(rectangle):
# now you can set new position
self.rect = newrect
# don't check other rectangles
break
# --- main ---
# - init -
pygame.init()
screen = pygame.display.set_mode(SIZE)
screen_rect = screen.get_rect()
# - objects -
player1 = Player()
# create list with rectangles (but not draw them)
all_rectangles = []
for row in range(5):
for col in range(5):
if row == 0 or row == 4 or col == 0 or col == 4:
all_rectangles.append( pygame.Rect((W + M) * col + M, ((H + M) * row + M), W, H) )
# - mainloop -
clock = pygame.time.Clock()
done = False
while not done:
# - events (without draws) -
for event in pygame.event.get():
if event.type == pygame.QUIT:
done = True
elif event.type == pygame.KEYDOWN:
player1.update(event)
# - draw everything in one place -
screen.fill(WHITE)
for rectangle in all_rectangles:
pygame.draw.rect(screen, BLACK, rectangle, 1)
player1.draw()
pygame.display.flip()
# - FPS - keep the same speed on all computers -
clock.tick(FPS)
# - end -
pygame.quit()
BTW:您可以使用row
,col
代替x
,y
来保留矩形位置和圆位(并检查碰撞) )并且在绘制时仅将row/col
转换为x/y
。您还可以使用矩形创建列表,如
all_rectangles = [
"######",
"# #",
"# #",
"# #",
"######",
]
然后创建地图会更容易。
修改强>
map = [
"######## #######",
"# #### #",
"# # # #",
"# ######## #",
"###### # #",
" # #####",
" # # ",
" ############ ",
]
all_rectangles = []
for r, row in enumerate(map):
for c, item in enumerate(row):
if item == '#':
all_rectangles.append(pygame.Rect((W + M) * c + M, ((H + M) * r + M), W, H))