Trying to make an enemy in pygame that shoots bullets in a straight line in pygame. I’ve managed to make the enemy shoot, but it shoots a constant beam of bullets instead of spacing them out. Is there any way to space out the bullets?
This is the class for the enemy
class Boss(pygame.sprite.Sprite):
def __init__(self):
pygame.sprite.Sprite.__init__(self)
self.image = pygame.Surface((100, 70))
self.image.fill(white)
self.rect = self.image.get_rect()
self.rect.centerx = WIDTH / 2
self.rect.y = (WIDTH / 2) - 500
self.speedy = 3
def update(self):
self.rect.y += self.speedy
if self.rect.y >= 30:
self.rect.y = 30
def shoot(self):
bossbullet = Bossbullet(self.rect.centerx, self.rect.bottom)
all_sprites.add(bossbullet)
bossbullets.add(bossbullet)
class Bossbullet(pygame.sprite.Sprite):
def __init__(self, x, y):
pygame.sprite.Sprite.__init__(self)
self.image = pygame.Surface((10, 20))
self.image.fill(white)
self.rect = self.image.get_rect()
self.rect.bottom = y
self.rect.centerx = x
self.speedy = -10
def update(self):
self.rect.y -= self.speedy
if self.rect.bottom < 0:
self.kill()
all_sprites = pygame.sprite.Group()
boss = Boss()
all_sprites.add(boss)
bossbullets = pygame.sprite.Group()
this is the loop in which the game runs and the enemy shoots
running = True
while running:
clock.tick(FPS)
if boss.rect.y >= 30:
boss.shoot()
Answers:
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
Method 1
I recommend to use a timer event. Use pygame.time.set_timer() to repeatedly create an USEREVENT. e.g.:
milliseconds_delay = 500 # 0.5 seconds
bullet_event = pygame.USEREVENT + 1
pygame.time.set_timer(bullet_event, milliseconds_delay)
Note, in pygame customer events can be defined. Each event needs a unique id. The ids for the user events have to start at pygame.USEREVENT. In this case pygame.USEREVENT+1 is the event id for the timer event, which spawns the bullets.
Create a new bullet when the event occurs in the event loop:
running = True
while running:
clock.tick(FPS)
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
elif event.type == bullet_event:
if boss.rect.y >= 30:
boss.shoot()
is there any way to make it so the enemy pauses for a while after..let’s say 5 shots, then starts shooting again after the pause
The timer event can be stopped by passing 0 to the time parameter. e.g.:
delay_time = 500 # 0.5 seconds
pause_time = 3000 # 3 seconds
bullet_event = pygame.USEREVENT + 1
pygame.time.set_timer(bullet_event, delay_time)
no_shots = 0
running = True
while running:
clock.tick(FPS)
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
elif event.type == bullet_event:
if boss.rect.y >= 30:
boss.shoot()
# change the timer event time
if no_shots == 0:
pygame.time.set_timer(bullet_event, delay_time)
no_shots += 1
if no_shots == 5:
pygame.time.set_timer(bullet_event, pause_time)
no_shots = 0
killed = # [...] set state when killed
# stop timer
if killed:
pygame.time.set_timer(bullet_event, 0)
All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0