Search code examples
pythonpython-3.xpygame

Hitboxes don't stay in place they just move


I'm making game about gathering trees and killing zombies.

When I'm walking on a map, tree hitboxes don't stay in place, they just move with screen.
I'm trying to fix that, but I don't know how to do so.

I'm a new to python and would be grateful if someone help me.

Here is the code.

#imports
import pygame
import random

#window settings
window_size = (600, 600)
window = pygame.display.set_mode(window_size)

#background settings
background = pygame.image.load("Images/Background8.2.png")
background_x = -450
background_y = -450

#camera settings
camera_x = 0
camera_y = 0

#player settings
class Player:
    def __init__(self):
        self.image = pygame.image.load("Images/Player2.1.png")
        self.x_cord = 250
        self.y_cord = 250
        self.width = 35
        self.height = 60
        self.velocity = 3
        self.hitbox = pygame.Rect(self.x_cord, self.y_cord, self.width, self.height)
    def tick(self, keys):
        global camera_x
        global camera_y
        if keys[pygame.K_d]:
            self.x_cord += self.velocity
            self.image = pygame.image.load("Images/Player2.1.png")
            camera_x += self.velocity
        if keys[pygame.K_a]:
            self.x_cord -= self.velocity
            self.image = pygame.image.load("Images/Player2.2.png")
            camera_x -= self.velocity
        if keys[pygame.K_w]:
            self.y_cord -= self.velocity
            camera_y -= self.velocity
        if keys[pygame.K_s]:
            self.y_cord += self.velocity
            camera_y += self.velocity
        if self.x_cord >= 2800:
            self.x_cord -= self.velocity
            camera_x -= self.velocity
        if self.x_cord <= -200:
            self.x_cord += self.velocity
            camera_x += self.velocity
        if self.y_cord <= -200:
            self.y_cord += self.velocity
            camera_y += self.velocity
        if self.y_cord >= 2800:
            self.y_cord -= self.velocity
            camera_y -= self.velocity
        self.hitbox = pygame.Rect(self.x_cord - camera_x + 30, self.y_cord - camera_y + 20, self.width, self.height)

    def draw(self):
        window.blit(self.image, (self.x_cord - camera_x, self.y_cord - camera_y))
        pygame.draw.rect(window, (255, 0, 0), self.hitbox, 2)

class Tree:
    def __init__(self):
        self.image = pygame.image.load("Images/Tree1.png")
        self.x_cord = random.randint(0, 100)
        self.y_cord = random.randint(0, 100)
        self.width = 50
        self.height = 100
        self.hitbox = pygame.Rect(self.x_cord + 75, self.y_cord + 125, self.width, self.height)

    def tick(self):
        self.hitbox = pygame.Rect(self.x_cord, self.y_cord, self.width, self.height)
    def draw(self):
        window.blit(self.image, (self.x_cord - camera_x, self.y_cord - camera_y))
        pygame.draw.rect(window, (255, 0, 0), self.hitbox, 2)

#main loop
def game():
    player = Player()
    run_game = True
    trees = []
    for _ in range(1):
        trees.append(Tree())
    while run_game:
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                quit(0)
        
        keys = pygame.key.get_pressed()
        for tree in trees:
            if player.hitbox.colliderect(tree.hitbox):
                quit(0)

        window.blit(background, (background_x -camera_x, background_y -camera_y))
        for tree in trees:
            tree.draw()
        player.draw()
        player.tick(keys)
        pygame.display.update()


if __name__ == "__main__":
    game()

Screenshots



Solution

  • The position of the tree image depends on the camera so the position of the hitbox must also depend on the camera:

    class Tree:
        def __init__(self):
            self.image = pygame.image.load("Images/Tree1.png")
            self.x_cord = random.randint(0, 100)
            self.y_cord = random.randint(0, 100)
            self.width = 50
            self.height = 100
            self.hitbox = pygame.Rect(self.x_cord + 75, self.y_cord + 125, self.width, self.height)
    
        def tick(self):
            self.hitbox.x = self.x_cord + 75 - camera_x
            self.hitbox.y = self.y_cord + 125 - camera_y
    
        def draw(self):
            self.tick()
            window.blit(self.image, (self.x_cord - camera_x, self.y_cord - camera_y))
            pygame.draw.rect(window, (255, 0, 0), self.hitbox, 2)