2

I'm making a simple game in pygame, in which you're supposed to dodge or shoot the targets that descend through the screen. So far, I've created the ship and managed to set the movement of both the bullet and the ship, as for their key bindings. However, the bullet's x coordinate doesn't seem to change at all, even though I've defined in the init method in the bullet class that the bullet x coordinate is equal to the ship x coordinate, therefore, the bullet would always be leaving the ship's position. Instead, the bullet always leaves the middle of the screen. I can't find the issue. Any help would be very much appreciated

import pygame, sys
pygame.init()

clock = pygame.time.Clock()

screen_width = 600
screen_height = 800

screen = pygame.display.set_mode((screen_width, screen_height))
pygame.display.set_caption("Space Race Game")

class ROCKET:
    def __init__(self):
        self.rocketImg = pygame.image.load("spaceship.png")
        self.rocket_x = screen_width/2 - 32
        self.rocket_y = screen_height/2 + 100

    def draw_rocket(self):
        screen.blit(self.rocketImg, (self.rocket_x, self.rocket_y))

    def move_rocket(self):
        key = pygame.key.get_pressed()

        if key[pygame.K_LEFT] and self.rocket_x + 15 > 0:
            self.rocket_x -= 5

        if key[pygame.K_RIGHT] and self.rocket_x < screen_width - 40:
            self.rocket_x += 5

class BULLET(ROCKET):
    def __init__(self):
        super().__init__()
        self.bullet_width = 10
        self.bullet_height = 20
        self.bullet_x = self.rocket_x + 25
        self.bullet_y = self.rocket_y
        self.move = [0, 0]
        self.bullet_speed = 5
        self.bullet_rect = pygame.Rect(self.bullet_x, self.bullet_y, self.bullet_width, self.bullet_height)

    def draw_bullet(self):
        key = pygame.key.get_pressed()

        if key[pygame.K_SPACE]:
            self.bullet_x = self.rocket_x
            self.move[1] = -1

        self.bullet_y += self.move[1] * self.bullet_speed
        self.bullet_rect.topleft = (self.bullet_x, self.bullet_y)

        if self.bullet_y < self.rocket_y - 10:
            pygame.draw.rect(screen, (0, 0, 0), self.bullet_rect)

        if self.bullet_y < - 20:
            self.bullet_y = self.rocket_y
            self.move[1] = 0

rocket = ROCKET()
bullet = BULLET()

while True:

    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            pygame.quit()
            sys.exit()

    screen.fill((255, 255, 255))
    rocket.draw_rocket()
    rocket.move_rocket()
    bullet.draw_bullet()


    pygame.display.flip()
    clock.tick(60)
  • I believe it's because you're not using an object instance of ROCKET, you're just inheriting from the class. So you'll always be using the lines `self.rocket_x = screen_width/2 - 32 self.rocket_y = screen_height/2 + 100` to define `self.bullet_x` and `self.bullet_y`. – M-Chen-3 Dec 21 '20 at 18:43

1 Answers1

1

You have to set the x-coordinate of the bullet by the current x-coordinate of the rocket.

Add an argument rocket to the method draw_bullet of the class BULLET. Make sure that you can only fire the bullet if the bullet has not yet been fired (self.move[1] == 0). Compute the center of the rocket and set the position of the bullet (rocket.rocket_x + self.rocketImg.get_width() // 2):

class BULLET(ROCKET):
    # [...]

    def draw_bullet(self, rocket):
        key = pygame.key.get_pressed()

        if key[pygame.K_SPACE] and self.move[1] == 0:
            rocket_center_x = rocket.rocket_x + self.rocketImg.get_width() // 2 
            self.bullet_x = rocket_center_x - self.bullet_width // 2
            self.move[1] = -1

        # [...]

Passe the instance of ROCKET to the method draw_bullet:

while True:
    # [...]

    bullet.draw_bullet(rocket)

    # [...]

If you want to fire multiple bullets, see the answers to the questions:

Rabbid76
  • 202,892
  • 27
  • 131
  • 174