2015-12-16 3 views
-2

Я здесь задаю вопрос для моего сына, который только что начал с Python. Он работает над простой игрой, где и вражеский корабль бросает ракеты, а игрок двигает щит, чтобы блокировать падающие ракеты от удара земли. Он добавил способность щита стрелять по пулям на корабле, чтобы уничтожить его (на данный момент установлено 3 удара), который, похоже, работает, но игра падает с этой точки с ошибкой: typeerror: Die() принимает ровно 1 позиционный аргумент (0 задано). Он довольно застрял, почему и я не много пользы прошло немного HTML :)Вражеский корабль здоровья - используя Pygame

Вот его код:

#Space Defence 
#Wes L-M 

#Players must defend the city from alien missiles and attack the mother ship 

from livewires import games, color 
import random 
import pygame 

games.init(screen_width = 1280, screen_height = 1024, fps = 50) 
pygame.display.set_mode((1280,1024),pygame.FULLSCREEN) 


class Killer(games.Sprite): 
    """ Makes a simple die methord for all the class's. """ 

    def die(self): 
     """ Destroy self. """ 
     self.destroy() 


class Collider(Killer): 
    """ A class that detects collisions. """ 
    def update(self): 
     """ Check for overlapping sprites. """ 
     super(Collider, self).update() 

     if self.overlapping_sprites: 
      for sprite in self.overlapping_sprites: 
       sprite.die() 
      self.die() 

    def die(self): 
     """ Destroy self and leave explosion behind. """ 
     new_explosion = Explosion(x = self.x, y = self.y) 
     games.screen.add(new_explosion) 
     self.destroy() 


class Collider_B(Killer): 
    """ A class that detects collisions for Bullet and Ship. """ 

    def update(self): 
     """ Check for overlapping sprites and take way from health. """ 
     super(Collider_B, self).update() 

     if self.overlapping_sprites: 
      for sprite in self.overlapping_sprites: 
       sprite.die() 
      self.die() 

    def die(self): 
     """ destroy self and leave differant explostion behind. """ 
     new_explosion = Explosion(x = self.x, y = self.y) 
     games.screen.add(new_explosion) 
     self.destroy() 


class Explosion(games.Animation): 
    """ Explosion animation. """ 
    images = ["explosion_1.bmp", 
       "explosion_2.bmp", 
       "explosion_3.bmp", 
       "explosion_4.bmp", 
       "explosion_5.bmp", 
       "explosion_6.bmp", 
       "explosion_7.bmp", 
       "explosion_8.bmp", 
       "explosion_9.bmp"] 

    def __init__(self, x, y): 
     super(Explosion, self).__init__(images = Explosion.images, 
             x = x, y = y, 
             repeat_interval = 6, n_repeats = 1, 
             is_collideable = False) 


class Shield(Killer): 
    """ 
    A Shield controlled by player to catch falling missiles. 
    """ 
    image = games.load_image("shield.bmp") 
    BULLET_DELAY = 20 

    def __init__(self, y = 800): 
     """ Initialize Shield object and create Text object for score. """ 
     super(Shield, self).__init__(image = Shield.image, 
            x = games.screen.width/2, 
            y = y) 
     self.bullet_wait = 0 

     self.score = games.Text(value = 0, size = 25, color = color.black, 
           top = 5, right = games.screen.width - 10, 
           is_collideable = False) 
     games.screen.add(self.score) 

    def update(self): 
     """ Use A and D to controll, SPACE too fire. """ 
     if games.keyboard.is_pressed(games.K_o): 
      self.x -= 12 
     if games.keyboard.is_pressed(games.K_p): 
      self.x += 12 

     if self.left < 0: 
      self. left = 0 

     if self.right > games.screen.width: 
      self.right = games.screen.width 

     self.Check_catch() 

     #fire bullets if spacebar is pressed 
     if games.keyboard.is_pressed(games.K_SPACE) and self.bullet_wait == 0: 
      new_bullet = Bullet(self.x, self.y) 
      games.screen.add(new_bullet) 
      self.bullet_wait = Shield.BULLET_DELAY 

     #if waiting until the shield can fire next, decrease wait 
     if self.bullet_wait > 0: 
      self.bullet_wait -= 1 

    def Check_catch(self): 
     """ Check if catch missiles. """ 
     for missile in self.overlapping_sprites: 
      self.score.value += 10 
      self.score.right = games.screen.width - 10 
      missile.handle_caught() 


class Ship(Killer): 
    """ 
    A ship which moves left and right, dropping shield. 
    """ 
    image = games.load_image("ship.bmp") 
    health = 3 

    def __init__(self, y = 55, speed = 3, odds_change = 200): 
     """ Initialize the Chef object. """ 
     super(Ship, self).__init__(image = Ship.image, 
            x = games.screen.width/2, 
            y = y, 
            dx = speed) 

     self.odds_change = odds_change 
     self.time_til_drop = 0 

    def update(self): 
     """ Determine if direction needs to be reversed. """ 
     if self.left < 0 or self.right > games.screen.width: 
      self.dx = -self.dx 
     elif random.randrange(self.odds_change) == 0: 
      self.dx = -self.dx 

     self.check_drop() 
     self.check_hit() 


    def check_drop(self): 
     """ Decrease countdown or drop missile reset countdown. """ 
     if self.time_til_drop > 0: 
      self.time_til_drop -= 1 
     else: 
      new_missile = Missile(x = self.x) 
      games.screen.add(new_missile) 

      #set buffer to approx 30% of missile height, regardless of missile speed 
      self.time_til_drop = int(new_missile.height * 1.3/Missile.speed) + 1 

    def check_hit(self): 
     """ Check if Bullet has hit. """ 
     for Bullet in self.overlapping_sprites: 
      Bullet.handle_hit() 


class Bullet(Collider_B): 
    """ A Bullet fired by the player's shield. """ 
    image = games.load_image("bullet.bmp") 
    BUFFER = -30 
    LIFETIME = 100 

    def __init__(self, shield_x, shield_y): 
     """ Initialize bullet sprite. """ 

     #bullet starting position 
     buffer_y = Bullet.BUFFER 
     x = shield_x 
     y = shield_y + buffer_y 

     #bullet speed 
     dx = random.choice([1, 0.5, 0.3, 0.1, 0, -0.1, -0.3, -0.5, -1]) 
     dy = -10 

     #create the bullet 
     super(Bullet, self).__init__(image = Bullet.image, 
            x = x, y = y, 
            dx = dx, dy = dy) 
     self.lifetime = Bullet.LIFETIME 

    def update(self): 
     """ Move the bullet. """ 

     #if lifetime is up, destroy missile 
     self.lifetime -= 1 
     if self.lifetime == 0: 
      self.destroy() 

    def handle_hit(self): 
     """ Handles what happens when hit by Bullet. """ 
     Ship.health -= 1 
     if Ship.health == 0: #ship loses health and eventually dies 
      Ship.die() 

     self.die() 


class Missile(Collider): 
    """ 
    A missile which falls to the ground. 
    """ 
    image = games.load_image("missile.bmp") 
    speed = 1 

    def __init__(self, x, y = 90): 
     """ Initialize a Missile object. """ 
     super(Missile, self).__init__(image = Missile.image, 
            x = x, y = y, 
            dy = random.randint(1, 4)) 
    def update(self): 
     """ Check if bottom edge has reached screen bottom. """ 
     if self.bottom > games.screen.height: 
      self.end_game() 
      self.die() 

    def handle_caught(self): 
     """ Destroy self if caught. """ 
     self.die() 

    def handle_hit(self): 
     """ Handle if missile gets hit... nothing. """ 

    def end_game(self): 
     """ End the games. """ 
     end_message = games.Message(value = "Game Over", 
            size = 90, 
            color = color.red, 
            x = games.screen.width/2, 
            y = games.screen.height/2, 
            lifetime = 5 * games.screen.fps, 
            after_death = games.screen.quit) 
     games.screen.add(end_message) 


def main(): 
    """ Play the game. """ 
    city_image = games.load_image("Citybackground.jpg", transparent = False) 
    games.screen.background = city_image 

    #load and play theme music 
    games.music.load("Star-Command.mp3") 
    games.music.play(-1) 

    the_ship = Ship() 
    games.screen.add(the_ship) 

    the_shield = Shield() 
    games.screen.add(the_shield) 

    games.mouse.is_visible = False 

    games.screen.event_grab = True 
    games.screen.mainloop() 

#start it up!!!! 
main() 
+1

Ошибка возникает в функции с именем 'Die', но вам только показать код для 'die', поэтому мы не можем помочь. – stark

+0

Извините, я не понимаю вашего ответа ... Это все его код. Есть функция отсутствует? В TypeError имена die() (not Die) моей опечатки ...... – jckm2000

+0

Вот почему вы всегда должны копировать и вставлять. Вы теряете время, когда все смотрят на это сообщение, потому что он не отформатирован правильно, и вы перепечатали ошибку. – stark

ответ

1

Я получил его. Здесь:

def handle_hit(self): 
     """ Handles what happens when hit by Bullet. """ 
     Ship.health -= 1 
     if Ship.health == 0: #ship loses health and eventually dies 
      Ship.die() 

     self.die() 

Здесь вы пытаетесь вызвать метод экземпляра для класса. (вроде как пытаться отремонтировать сантехнику по чертежу дома) Ship Капитал относится к чертежу корабля, питон просто говорит вам, что он не знает, какой корабль должен убить (даже если есть только один корабль) ,

Попробуйте заменить его с этим:

def handle_hit(self): 
     """ Handles what happens when hit by Bullet. """ 
     the_ship.health -= 1 
     if the_ship.health == 0: #ship loses health and eventually dies 
      the_ship.die() 

     self.die() 

Также в main() оных:

global the_ship 

в верхней части функции

+0

это может быть одна проблема - 'the_ship' - это локальная переменная в' main() ';) – furas

+0

@furas Это не java, поэтому мы можем получить доступ к переменным за пределами области видимости. Ах, питон. :) –

+0

Для этого потребуется 'global the_ship' в' main() '. ОП может этого не знать. :) – furas

-1

этот код в корне неверно. Кроме того, что модуль «цвет» не существует внутри livewires (это «цвет»). Согласно коду OP пытается инициализировать библиотеку игр с шириной, высотой и fps. Быстрый поиск исходного кода показывает, что правильный вызов будет:

screen = games.Screen(width=1280, height=1024) 

Это означает, что код в основной функции не так, как он держит вызов на функции, которые не существуют. Кроме того, у меня нет ни малейшего намека на то, что OP нашел музыкальный модуль, так как второй быстрый поиск на github показывает, что в библиотеке livewires не отображается ссылка на «музыку». Модуль pygame, однако, содержит музыкальный проигрыватель, но не называется удаленно таким же образом, как подразумевает OP. Я не знаю, как OP когда-либо получал этот код для запуска.

Если по какой-то странной причине код работает для OP:

def handle_hit(self): 
    """ Handles what happens when hit by Bullet. """ 
    Ship.health -= 1 
    if Ship.health == 0: #ship loses health and eventually dies 
     Ship.die() 

    self.die() 

тоже неправильно, так как в этом коде он ссылается на корабль класса вместо экземпляра он создал. Лучшим решением, которое я могу дать OP в этом случае, является случайность всех вхождений корабля внутри метода handle_hit() в переменную экземпляра «the_ship»

+0

Не отправляйте ответ, если вы не отвечаете –

+0

@DamianChrzanowski Я ответил на его вопрос в последнем абзаце. Первые два абзаца на самом деле критиковали код и предлагают некоторое улучшение для запуска кода. –

+0

Достаточно справедливо, но это все еще скорее спекуляция. Во всяком случае, я не буду спорить –

Смежные вопросы