Eliminar partículas muertas
Parte de la sección Sonido y sensaciones del juego del Journey de Pygame de Coddy. Lección 11 de 23.
Una partícula muerta no se dibuja, pero sigue en la lista. En cada fotograma, el bucle la mueve y vuelve a reducir su vida. Haz clic 100 veces y la lista tendrá 2000 partículas que nadie puede ver, y el juego se volverá cada vez más lento. El contador de la parte superior lo muestra.
Elimina las partículas muertas una vez por fotograma, después de la actualización. La forma más clara consiste en crear una nueva lista con las partículas que siguen vivas:
particles = [p for p in particles if p["life"] > 0]Esto se lee así: la lista de cada p en particles cuya vida es superior a 0.
No elimines elementos de una lista mientras un bucle for recorre esa misma lista:
for p in particles:
if p["life"] <= 0:
particles.remove(p)Cuando se elimina un elemento, el siguiente ocupa su lugar y el bucle lo salta sin revisarlo. Aquí, todas las partículas de una ráfaga mueren en el mismo fotograma, así que la mitad se queda atrás cada vez. Crear una nueva lista nunca se salta ningún elemento.
Desafío
IntermedioCada clic crea 20 partículas que duran 30 fotogramas, y el contador nunca disminuye. Después del bucle de actualización, reemplaza particles por una lista que contenga solo las partículas cuyo life sea mayor que 0, para que el contador muestre Particles: 0 cuando termine una explosión.
Pruébalo tú mismo
import random
import pygame
pygame.init()
screen = pygame.display.set_mode((480, 360))
pygame.display.set_caption("Fireworks")
clock = pygame.time.Clock()
font = pygame.font.Font(None, 28)
particles = []
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
elif event.type == pygame.MOUSEBUTTONDOWN:
x, y = event.pos
for i in range(20):
particles.append({
"x": x,
"y": y,
"vx": random.uniform(-3, 3),
"vy": random.uniform(-3, 3),
"life": 30,
})
for p in particles:
p["x"] += p["vx"]
p["y"] += p["vy"]
p["life"] -= 1
screen.fill((20, 20, 36))
for p in particles:
if p["life"] > 0:
pygame.draw.circle(screen, (255, 160, 60), (p["x"], p["y"]), 3)
label = font.render(f"Particles: {len(particles)}", True, (240, 240, 240))
screen.blit(label, (10, 10))
pygame.display.flip()
clock.tick(60)
pygame.quit()
Esta lección incluye un breve cuestionario. Empieza la lección para responderlo y registrar tu progreso.
Todas las lecciones de Sonido y sensaciones del juego
1Efectos de sonido
Cargar un sonidoSonido al ocurrir un eventoVolumen del sonidoSonidos y teclas presionadas4Sacudida de pantalla y destello de impacto
Sacudida de pantallaDestello de impactoPausa tras el impactoMantén la sutileza6Pulir la Patrulla Estelar
Sonidos de la Patrulla EstelarChispas con cada impactoPractica por tu cuenta: Playground de Pygame