我需要帮助删除一个对象,我的意思是删除,而不是绘制或其他事情。到目前为止我的代码如下:
def detect_collision(player_pos, enemy_pos):
p_x = player_pos[0]
p_y = player_pos[1]
e_x = enemy_pos[0]
e_y = enemy_pos[1]
if (e_x >= p_x and e_x < (p_x + player_size)) or (p_x >= e_x and p_x < (e_x+enemy_size)):
if (e_y >= p_y and e_y < (p_y + player_size)) or (p_y >= e_y and p_y < (e_y+enemy_size)):
return True
return False
def bullets():
b_x = player_pos[0]
b_y = player_pos[1]
keep_going = True
pygame.draw.rect(screen, TEAL, (b_x, b_y, 15, 50))
while keep_going:
b_y += 75
if detect_collision(player_pos, enemy_pos):
# deleting part here
这就是我的玩家和敌人的原因:
enemy_size = 50
enemy_pos = [random.randint(0,WIDTH-enemy_size), 0]
enemy_list = [enemy_pos]
def drop_enemies(enemy_list):
delay = random.random()
if len(enemy_list) < 10 and delay < 0.1:
x_pos = random.randint(0,WIDTH-enemy_size)
y_pos = 0
enemy_list.append([x_pos, y_pos])
def draw_enemies(enemy_list):
for enemy_pos in enemy_list:
pygame.draw.rect(screen, RED, (enemy_pos[0], enemy_pos[1],
enemy_size, enemy_size))
def update_enemy_positions(enemy_list, score):
for idx, enemy_pos in enumerate(enemy_list):
if enemy_pos[1] >= 0 and enemy_pos[1] < HEIGHT:
enemy_pos[1] += SPEED
else:
enemy_list.pop(idx)
score += 1
return score
播放器部分:
player_size = 50
player_pos = [WIDTH/2, HEIGHT-2*player_size]
pygame.draw.rect(screen, TEAL, (player_pos[0], player_pos[1], player_size,
player_size))
所以,这就是我制造子弹,玩家和敌人的方式。请忽略其余的,因为我的帖子中有很多代码,所以需要它。
嗨,嗨,嗨
发布于 2020-07-30 10:46:51
解决问题的最好方法是学习如何使用Sprite
objects in pygame。与Group
对象一起,它们已经可以开箱即用地做你想做的事情了。
简而言之,您的“敌人”应该是某个Sprite
子类的实例,您可以将其添加到Group
的实例中(而不是构建您自己的enemy_list
)。当你想要敌人死的时候,你可以对它调用kill()
方法,这将把它从Group
中删除。这用于将其从游戏中删除,因为您应该使用Group
对象上的方法来更新和绘制它包含的所有精灵(但不是那些已被杀死的精灵)。
发布于 2020-07-30 10:52:26
查看Sprites和SpriteGroups来跟踪游戏中的实体将是有益的。他们有一堆内置的功能,可以让事情变得更容易。
这是我的一个演示,它对精灵进行分组,移除那些与鼠标指针冲突的精灵:
import random
import pygame
screen_width, screen_height = 640, 480
def get_random_position():
"""return a random (x,y) position in the screen"""
return (
random.randint(0, screen_width - 1), # randint includes both endpoints.
random.randint(0, screen_height - 1),
)
color_list = ["red", "orange", "yellow", "green", "cyan", "blue", "blueviolet"]
colors = [pygame.color.Color(c) for c in color_list]
class PowerUp(pygame.sprite.Sprite):
def __init__(self):
pygame.sprite.Sprite.__init__(self)
width, height = 64, 32
self.color = random.choice(colors)
self.image = pygame.Surface([width, height])
self.image.fill(self.color)
# Fetch the rectangle object that has the dimensions of the image
self.rect = self.image.get_rect()
# then move to a random position
self.update()
def update(self):
# move to a random position
self.rect.center = get_random_position()
if __name__ == "__main__":
pygame.init()
screen = pygame.display.set_mode((screen_width, screen_height))
pygame.display.set_caption("Sprite Group Collision Demo")
clock = pygame.time.Clock() # for limiting FPS
FPS = 60
exit_demo = False
# create a sprite group to track the power ups.
power_ups = pygame.sprite.Group()
for _ in range(10):
power_ups.add(PowerUp()) # create a new power up and add it to the group.
# main loop
while not exit_demo:
for event in pygame.event.get():
if event.type == pygame.QUIT:
exit_demo = True
elif event.type == pygame.KEYDOWN:
if event.key == pygame.K_ESCAPE:
exit_demo = True
elif event.key == pygame.K_SPACE:
power_ups.update()
elif event.type == pygame.MOUSEBUTTONUP:
for _ in range(10):
power_ups.add(PowerUp())
# Update State: check for collisions
for p in power_ups:
if p.rect.collidepoint(pygame.mouse.get_pos()):
power_ups.remove(p)
# draw background
screen.fill(pygame.Color("black")) # use black background
# draw sprites
power_ups.draw(screen)
# update screen
pygame.display.update()
clock.tick(FPS)
pygame.quit()
quit()
单击鼠标按钮可以创建更多的精灵,按空格键可以随机化它们的位置。
子弹精灵的update()
方法会根据它的速度来调整精灵的位置,例如self.rect.x += SPEED
,你需要在每个游戏循环中调用子弹精灵组的.update()
方法。
发布于 2020-07-30 10:59:14
好的,所以你在enemy_list
里有一份敌人位置的清单。这是一个很好的开始。我没有看到bullet_list
,所以我假设一次只有一颗子弹,定位在b_x
,b_y
。
因此,此程序的主循环可能如下所示:
### Main Loop
while not game_over:
# handle user input
# move the player
# move the bullet (if any)
# move the enemies
# if there's a bullet, did it hit an enemy?
# remove enemy hit from enemy_list
# Did an enemy in enemy_list, hit the player?
# do game-over
# clear the screen
# paint the player
# paint the bullet (if any)
# paint every enemy in enemy_list
敌人的碰撞和列表的删除可能看起来像下面这样。(我已经尝试尽可能地匹配您的代码的外观。)
# if a bullet is on-screen (non 0,0), see if it hits an enemy
if ( b_x != 0 and b_y != 0 ):
hit_enemy_idx = None
for idx, enemy_pos in enumerate( enemy_list ):
# check for collision
if detect_collision( ( b_x, b_y ), enemy_pos ):
hit_enemy = idx # note the enemy index
b_x, b_y = 0, 0 # erase the bullet
break # exit the loop when hit found
# If the bullet hit an enemy, remove from list
if hit_enemy_idx != None:
del( enemy_list[ hit_enemy_idx ] ) # delete hit enemy from list
我们对敌人列表进行迭代,检查是否存在冲突。一旦发现命中,它将保存被命中的敌人的索引,并停止循环。
下一步是从列表中删除敌人。我在一个单独的代码块中编写了这段代码,而不是将它放在循环中的break
之前。这是因为当您在迭代时更改列表时,可能会出现意想不到的结果。在这种特殊的情况下,它应该是可以的,但作为一个初学者,这是需要警惕的。
https://stackoverflow.com/questions/63164953
复制相似问题