Один щелчок активирует несколько кнопок при наложении - PullRequest
3 голосов
/ 17 июня 2020

Хорошо, так что да, я понимаю, что я собираюсь отобразить много кода.

Моя проблема: я делаю зомб-шутер ie, в котором вы главный герой наверху здания, и вы должны нажимать на зомби, когда они прибывают волнами. Моя текущая проблема заключается в том, что всякий раз, когда несколько зомби накладываются друг на друга, я могу убить их обоих (или столько же перекрывающихся) одним щелчком, потому что технически все их хитбоксы сталкиваются.

Если это проблема более серьезная, чем предполагалось, я бы хотел, чтобы кто-нибудь просто сказал это.

import pygame
import random
import time

pygame.init()
#Setting Variables
screenW = 1020
screenH = 630
x = 125
y = 164
width = 50
height = 50
velocity = 5
wave = 2
GOLD = (255, 215, 0)
BLACK = (0, 0, 0)
RED = (255, 0, 0)
GREEN = (0, 128, 0)
wallHealth = 0
zombieKilled = 0


class ZombieChars():
    def __init__(self):
        self.damage = 0
        self.vel = 5
        self.x_change = random.randrange(2,5)
        self.y_change = 1
        self.height = 120
        self.width = 149
        self.color = random.sample(range(250), 4)
        self.image = pygame.Surface([self.width, self.height], pygame.HWSURFACE, 32)
        self.rect = self.image.get_rect(topleft = (random.randrange(900, 1150), 330))
        #pygame.draw.rect(self.image, (self.color), (self.x, self.y, self.width, self.height))

    def draw(self):
        window.blit(ZombieWalking, self.rect.topleft)

    def update(self):
        if self.rect.x >= 364:
            self.rect.x -= self.x_change
        else:
            self.rect.x -= 0

    def wallHP(self):
        global wallHealth
        if self.rect.x < 365:
            self.damage += 1
        if self.damage == 30:
            self.damage = 0
            wallHealth += 1


    def death(self):
        global zombieKilled
        if event.type == pygame.MOUSEBUTTONDOWN:
            gunShot.play()
            mouse_pos = event.pos
            if self.rect.collidepoint(mouse_pos):
                self.rect.x = 5000
                self.rect.x -= self.x_change
                zombieHit.play()
                zombieKilled += 1
                print(zombieKilled)

    def waveCounter(self):
        global wave
        print(wave)
        if wave == zombieKilled / 2:
            wave = 2



#FPS
clock = pygame.time.Clock()
clock.tick(60)

#Screen
window = pygame.display.set_mode((screenW,screenH))
pygame.display.set_caption(("Zombie Shooter"))


#Image Loading
bg = pygame.image.load("bg.jpg")
mainmenu = pygame.image.load("mainmenu.jpg")
ZombieWalking = pygame.image.load("Sprites/AAIdle.png")

#Sound Loading
gunShot = pygame.mixer.Sound('sounds/gunShot.wav')
zombieHit = pygame.mixer.Sound('sounds/zombieHit.wav')
gameMusic = pygame.mixer.music.load('sounds/gameMusic.mp3')
menuMusic = pygame.mixer.music.load('sounds/menuMusic.mp3')



zombies = ZombieChars()

my_list = []
for zombs in range(wave):
    my_object = ZombieChars()
    my_list.append(my_object)
def text_objects(text, font):
    textSurface = font.render(text, True, BLACK)
    return textSurface, textSurface.get_rect()

smallText = pygame.font.Font('freesansbold.ttf', 30)
tinyText = pygame.font.Font('freesansbold.ttf', 20)

TextSurf3, TextRect3 = text_objects("Wave: " + str(wave), smallText)
TextRect3.center = ((1020 / 2), (50))


#Main Loop
run = True
mainMenu = True
pygame.mixer.music.play()
global event
while mainMenu == True:

    window.blit(mainmenu, (0,0))
    pygame.display.flip()
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False   #if x is pressed dont run game
            mainMenu = False
    keys = pygame.key.get_pressed()
    if keys[pygame.K_a]:
        mainMenu = False  #if a is pressed run game


def wallHPBar():
    pygame.draw.rect(window, GREEN, (20, 20, 100, 10))
    if wallHealth == 0:
        pass
    if wallHealth == 1:
        pygame.draw.rect(window, RED, (20, 20, 25, 10))
    if wallHealth == 2:
        pygame.draw.rect(window, RED, (20, 20, 50, 10))
    if wallHealth == 3:
        pygame.draw.rect(window, RED, (20, 20, 75, 10))
    if wallHealth >= 4:
        pygame.draw.rect(window, RED, (20, 20, 100, 10))

def overlapKill():
    if zombieKilled == 1:
        print("oh my goodness we going")
    if zombieKilled == 2:
        print("we 2 ")
while run:
    pygame.mixer.music.stop()
    window.blit(bg, (0, 0))
    window.blit(TextSurf3, TextRect3)
    wallHPBar()
    pygame.time.delay(25)

    for zombie in my_list:
        zombie.draw()
        zombie.update()
        zombie.death()
        zombie.wallHP()
        zombie.waveCounter()

    pygame.display.flip()
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False

Спасибо.

Ответы [ 2 ]

4 голосов
/ 17 июня 2020

Объект Zomb ie не должен иметь дело с пользовательским вводом. Обработайте щелчок за пределами зомба ie, тогда внешний код решит, «израсходован» ли щелчок.

class ZombieChars ():

[ ... ]

def death( self, mouse_position ):
    killed = False
    global zombieKilled
    if self.rect.collidepoint( mouse_position ):
        self.rect.x = 5000
        self.rect.x -= self.x_change
        zombieHit.play()
        zombieKilled += 1
        print(zombieKilled)
        killed = True
    return killed

Затем в вашем main l oop, прекратить обработку попаданий, как только будет найдено первое:

### Main Loop
while not exiting:

    for event in pygame.event.get():
        if ( event.type == pygame.QUIT ):
            exiting = True
        elif ( event.type == pygame.MOUSEBUTTONDOWN ):
            gunShot.play()
            mouse_pos = event.pos
            for zombie in my_list:
                if ( zombie.death( mouse_pos ) ):
                    break   # stop on first hit
4 голосов
/ 17 июня 2020

Удалите обработку событий из метода death и верните логическое значение, которое указывает, был ли убит зомб ie:

class ZombieChars():
    # [...]

    def death(self):
        global zombieKilled
        mouse_pos = pygame.mouse.get_pos()
        if self.rect.collidepoint(mouse_pos):
            self.rect.x = 5000
            self.rect.x -= self.x_change
            zombieHit.play()
            zombieKilled += 1
            print(zombieKilled)
            return True
        return False

Выполните обработку события pygame.MOUSEBUTTONDOWN в событии l oop и оцените, был ли убит зомб ie в al oop. break l oop когда зомб ie убит. Таким образом, только один зомб ie может быть убит за один клик:

while run:
    # [...]

    pygame.display.flip()
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            run = False 

        if event.type == pygame.MOUSEBUTTONDOWN:
            gunShot.play()
            for zombie in (reversed):
                if zombie.death():
                    break


    for zombie in my_list:
        zombie.draw()
        zombie.update()
        # zombie.death() <--- DELETE
        zombie.wallHP()
        zombie.waveCounter()
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...