class Scoreboard:
    def __init__(self, ai_settings, screen, stats):
        self.screen = screen
        self.screen_rect = screen.get_rect()
        self.ai_settings = ai_settings
        self.stats = stats
        self.text_color = (255, 255, 0)
        self.font = SysFont(None, 48)
        self.score_image = None
        self.score_rect = None
        self.high_score_image = None
        self.high_score_rect = None
        self.level_image = None
        self.level_rect = None
        self.ships = None
        self.prep_score()
        self.prep_high_score()
        self.prep_level()
        self.prep_ships()

    def prep_score(self):
        rounded_score = int(round(self.stats.score, -1))
        score_str = 'Score: {:,}'.format(rounded_score)
        self.score_image = self.font.render(score_str, True, self.text_color,
                                            self.ai_settings.bg_color)
        self.score_rect = self.score_image.get_rect()
        self.score_rect.right = self.screen_rect.right - 20
        self.score_rect.top = 20

    def prep_high_score(self):
        high_score = int(round(self.stats.high_score, -1))
        high_score_str = 'High Score: {:,}'.format(high_score)
        self.high_score_image = self.font.render(high_score_str, True,
                                                 self.text_color,
                                                 self.ai_settings.bg_color)
        self.high_score_rect = self.high_score_image.get_rect()
        self.high_score_rect.centerx = self.screen_rect.centerx
        self.high_score_rect.top = self.score_rect.top

    def prep_level(self):
        self.level_image = self.font.render('Level: ' + str(self.stats.level),
                                            True, self.text_color,
                                            self.ai_settings.bg_color)
        self.level_rect = self.level_image.get_rect()
        self.level_rect.right = self.score_rect.right
        self.level_rect.top = self.score_rect.bottom + 10

    def prep_ships(self):
        self.ships = Group()
        for ship_number in range(self.stats.ships_left):
            ship = Ship(self.ai_settings, self.screen)
            ship.rect.x = 10 + ship_number * (ship.rect.width + 5)
            ship.rect.y = 10
            self.ships.add(ship)

    def show_score(self):
        self.screen.blit(self.score_image, self.score_rect)
        self.screen.blit(self.high_score_image, self.high_score_rect)
        self.screen.blit(self.level_image, self.level_rect)
        self.ships.draw(self.screen)
예제 #2
0
class Button:
    def __init__(self, ai_settings, screen, msg):
        self.ai_settings = ai_settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # Dimensions and properties of the button
        self.width, self.height = 200, 50
        self.button_color = (0, 255, 0)
        self.text_color = (255, 255, 255)
        self.font = SysFont(None, 48)
        # Build button rect and center it
        self.rect = Rect(0, 0, self.width, self.height)
        self.rect.center = self.screen_rect.center
        # Prep button message only once
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(msg)

    def prep_msg(self, msg):
        """Turn msg into a rendered image and center it on the button"""
        self.msg_image = self.font.render(msg, True, self.text_color,
                                          self.button_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.center = self.rect.center

    def draw_button(self):
        """Draw button and then draw message"""
        self.screen.fill(self.button_color, self.rect)
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #3
0
class Title:
    """Represents the title text to be displayed on screen"""
    def __init__(self,
                 bg_color,
                 screen,
                 text,
                 text_size=50,
                 text_color=(255, 0, 0)):
        self.bg_color = bg_color
        self.screen = screen
        self.text = text
        self.text_color = text_color
        self.font = SysFont(None, text_size)
        self.image = None
        self.image_rect = None

    def prep_image(self):
        """Render the subtitle text as an image"""
        self.image = self.font.render(self.text, True, self.text_color,
                                      self.bg_color)
        self.image_rect = self.image.get_rect()

    def blitme(self):
        """Draw the subtitle's image to the screen"""
        self.screen.blit(self.image, self.image_rect)
예제 #4
0
class Button:
    def __init__(self, ai_settings: Settings, screen: SurfaceType, msg: str):
        self._screen = screen
        self._screen_rect = screen.get_rect()

        self._width, self._height = 200, 50
        self._button_color = (0, 255, 0)
        self._text_color = (255, 255, 255)
        self._font = SysFont(None, 48)

        self.rect = pygame.Rect(0, 0, self._width, self._height)
        self.rect.center = self._screen_rect.center

        self._prep_msg(msg)

    def _prep_msg(self, message: str):
        # print(self._text_color, self._button_color, sep=" -> ")

        self._msg_image = self._font.render(message, True, self._text_color,
                                            self._button_color)

        self._msg_image_rect = self._msg_image.get_rect()
        self._msg_image_rect.center = self.rect.center

    def draw_button(self):
        self._screen.fill(self._button_color, self.rect)
        self._screen.blit(self._msg_image, self._msg_image_rect)
예제 #5
0
class Titletext:
    # Text
    def __init__(self,
                 bg_color,
                 screen,
                 text,
                 text_size=56,
                 text_color=(0, 0, 0)):
        self.bg_color = bg_color
        self.screen = screen
        self.text = text
        self.text_color = text_color
        self.font = SysFont(None, text_size)
        self.image = None
        self.image_rect = None

    def prep_image(self):

        self.image = self.font.render(self.text, True, self.text_color,
                                      self.bg_color)
        self.image_rect = self.image.get_rect()

    def blitme(self):

        self.screen.blit(self.image, self.image_rect)
예제 #6
0
class Label(Component):
    def __init__(self,
                 location=(0, 0),
                 size=(0, 0),
                 caption="",
                 font=None,
                 fontColor=(255, 255, 255),
                 fixedToCaption=True):
        super(Label, self).__init__(location=location, size=size)

        self.__font = SysFont('arial', 20) if (font == None) else font
        self.fixedToCaption = fixedToCaption
        self.caption = caption
        self.fontColor = fontColor

        Label.graphicInit(self)

    def graphicInit(self):
        self.writeCaption()

    def writeCaption(self):
        if self.fixedToCaption:
            self.fixToCaption()
        else:
            self.reset()
            captionSurface = self.__font.render(self.__caption, True,
                                                self.fontColor)
            self.blit(captionSurface, (0, 0))

    def fixToCaption(self):
        captionSurface = self.__font.render(self.caption, True, self.fontColor)
        self.width = captionSurface.get_size()[0]
        self.height = captionSurface.get_size()[1]

        self.reset()
        self.blit(captionSurface, (0, 0))
예제 #7
0
class Fruit(Sprite):
    def __init__(self, screen):
        super(Fruit, self).__init__()
        self.screen = screen
        ss = SpriteSheet.spritesheet('images/Fruits.png')
        self.fruits = [ss.image_at((0,0,32,32)),
                       ss.image_at((32,0,32,32)),
                       ss.image_at((64,0,32,32)),
                       ss.image_at((96,0,32,32)),
                       ss.image_at((128,0,32,32))]
        self.values = [100, 300, 500, 700, 1000]
        index = random.randint(0,4)
        img, self.value = self.fruits[index], self.values[index]
        img = pygame.transform.scale(img, (25, 25))
        self.rect = img.get_rect()
        self.image = img
        self.rect.x, self.rect.y = 1000,1000 # hide fruit offscreen
        self.font = SysFont(None, 32, italic=True)
        self.score_image = self.font.render(str(self.value), True, (255, 255, 255), (0,0,0))

        self.randomint = 101
        self.fruitspawned = False
        self.destroyed = False

        # how long to show score
        self.frames = 0

    def blitfruit(self):
        if(not self.destroyed):
            if(pygame.time.get_ticks() % 1000 <= 1 and not self.fruitspawned):
                self.randomint = random.randint(1,100)
            if(self.randomint <= 20): # 20% chance of fruit spawn
                self.rect.x, self.rect.y = 312, 364
                self.screen.blit(self.image, self.rect)
                self.fruitspawned = True
        elif(self.frames <= 60 and self.destroyed):
            self.screen.blit(self.score_image, self.rect)
            self.frames += 1
        if(self.frames > 60):
            self.frames = 0
            self.rect.x, self.rect.y = 1000, 1000  # hide fruit offscreen

    def fruitReset(self):
        self.destroyed = False  # make getting the fruit possible again for the next stage
        self.fruitspawned = False
        self.randomint = 101
예제 #8
0
class Button:
    """Initialize button"""
    def __init__(self, settings, screen, msg, y_factor=0.60):
        self.settings = settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # set button
        self.button_color = (51, 161, 201)
        self.text_color = (255, 255, 255)
        self.alt_color = (187, 255, 255)
        self.font = SysFont(None, 48)
        self.y_factor = y_factor

        # set message
        self.msg = msg
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(self.text_color)

    def check_button(self, mouse_x, mouse_y):
        """check clicked button event"""
        if self.msg_image_rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def alter_text_color(self, mouse_x, mouse_y):
        """update button when pressed"""
        if self.check_button(mouse_x, mouse_y):
            self.prep_msg(self.alt_color)
        else:
            self.prep_msg(self.text_color)

    def prep_msg(self, color):
        """initialize message"""
        self.msg_image = self.font.render(self.msg, True, color,
                                          self.settings.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.centerx = (self.settings.screen_width // 2)
        self.msg_image_rect.centery = int(self.settings.screen_height *
                                          self.y_factor)

    def draw_button(self):
        """display"""
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #9
0
class Button:
    """Represents a click-able button style text, with altering text color"""
    def __init__(self, settings, screen, msg, y_factor=0.65):
        self.settings = settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # Dimensions and properties of the button
        self.button_color = (0, 255, 0)
        self.text_color = (255, 255, 255)
        self.alt_color = (0, 255, 0)
        self.font = SysFont(None, 48)
        self.y_factor = y_factor

        # Prep button message
        self.msg = msg
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(self.text_color)

    def check_button(self, mouse_x, mouse_y):
        """Check if the given button has been pressed"""
        if self.msg_image_rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def alter_text_color(self, mouse_x, mouse_y):
        """Change text color if the mouse coordinates collide with the button"""
        if self.check_button(mouse_x, mouse_y):
            self.prep_msg(self.alt_color)
        else:
            self.prep_msg(self.text_color)

    def prep_msg(self, color):
        """Turn msg into a rendered image and center it on the button"""
        self.msg_image = self.font.render(self.msg, True, color,
                                          self.settings.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.centerx = (self.settings.screen_width // 2)
        self.msg_image_rect.centery = int(self.settings.screen_height *
                                          self.y_factor)

    def draw_button(self):
        """blit message to the screen"""
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #10
0
class Button:
    # button text
    def __init__(self, settings, screen, msg, y_factor=0.65):
        self.settings = settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # Dimensions and properties of the button
        self.button_color = (0, 0, 0)
        self.text_color = (0, 0, 0)
        self.alt_color = (0, 0, 255)
        self.font = SysFont(None, 48)
        self.y_factor = y_factor

        # Prep button message
        self.msg = msg
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(self.text_color)

    def check_button(self, mouse_x, mouse_y):
        # check for button input
        if self.msg_image_rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def change_text_color(self, mouse_x, mouse_y):
        # change button color
        if self.check_button(mouse_x, mouse_y):
            self.prep_msg(self.alt_color)
        else:
            self.prep_msg(self.text_color)

    def prep_msg(self, color):
        # prep msg image
        self.msg_image = self.font.render(self.msg, True, color,
                                          self.settings.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.centerx = (self.settings.screen_width // 2)
        self.msg_image_rect.centery = int(self.settings.screen_height *
                                          self.y_factor)

    def draw_button(self):
        # draw the button
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #11
0
class Button:
    def __init__(self, settings, screen, msg, y_factor=0.65):
        self.settings = settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # Dimensions of the buttons
        self.button_color = (0, 255, 0)
        self.text_color = (255, 255, 255)
        self.alt_color = (0, 255, 0)
        self.font = SysFont(None, 48)
        self.y_factor = y_factor

        # Prep button message
        self.msg = msg
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(self.text_color)

    def check_button(self, mouse_x, mouse_y):
        # check for button clicks
        if self.msg_image_rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def alter_text_color(self, mouse_x, mouse_y):
        # change color of button is mouse hits it
        if self.check_button(mouse_x, mouse_y):
            self.prep_msg(self.alt_color)
        else:
            self.prep_msg(self.text_color)

    def prep_msg(self, color):
        # make the writing an image that sits on the button
        self.msg_image = self.font.render(self.msg, True, color,
                                          self.settings.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.centerx = (self.settings.screen_width // 2)
        self.msg_image_rect.centery = int(self.settings.screen_height *
                                          self.y_factor)

    def draw_button(self):
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #12
0
class Button:
    def __init__(self, settings, screen, msg, y_factor=0.65):
        self.settings = settings
        self.screen = screen
        self.screen_rect = screen.get_rect()

        self.button_color = (0, 255, 0)
        self.text_color = (255, 255, 255)
        self.alt_color = (0, 255, 0)
        self.font = SysFont(None, 48)
        self.y_factor = y_factor

        self.msg = msg
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(self.text_color)

    def check_button(self, mouse_x, mouse_y):

        if self.msg_image_rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def alter_text_color(self, mouse_x, mouse_y):

        if self.check_button(mouse_x, mouse_y):
            self.prep_msg(self.alt_color)
        else:
            self.prep_msg(self.text_color)

    def prep_msg(self, color):

        self.msg_image = self.font.render(self.msg, True, color,
                                          self.settings.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.centerx = (self.settings.screen_width // 2)
        self.msg_image_rect.centery = int(self.settings.screen_height *
                                          self.y_factor)

    def draw_button(self):

        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #13
0
class Subtitle:
    """Represents the subtitle text displayed on startup"""
    def __init__(self, bg_color, screen):
        self.bg_color = bg_color
        self.screen = screen
        self.text = 'AI -- No Walls'
        self.text_color = (0, 255, 0)
        self.font = SysFont(None, 36)
        self.image = None
        self.image_rect = None

    def prep_image(self):
        """Render the subtitle text as an image"""
        self.image = self.font.render(self.text, True, self.text_color,
                                      self.bg_color)
        self.image_rect = self.image.get_rect()

    def blitme(self):
        """Draw the subtitle's image to the screen"""
        self.screen.blit(self.image, self.image_rect)
예제 #14
0
class Button:
    """Represents a click-able button"""
    def __init__(self, config, screen, msg):
        self.config = config
        self.screen = screen
        self.screen_rect = screen.get_rect()

        # Dimensions and properties of the button
        self.button_color = (0, 255, 0)
        self.text_color = (255, 255, 255)
        self.font = SysFont(None, 48)
        # Build button rect and center it
        self.width, self.height = self.font.size(msg)
        self.width, self.height = (self.width +
                                   self.width / 4), (self.height +
                                                     self.height / 4)
        self.rect = Rect(0, 0, self.width, self.height)
        self.rect.centerx = (self.config.screen_width // 2)
        self.rect.centery = int(self.config.screen_height * 0.75)
        # Prep button message only once
        self.msg_image, self.msg_image_rect = None, None
        self.prep_msg(msg)

    def check_button(self, mouse_x, mouse_y):
        """Check if the given button has been pressed"""
        if self.rect.collidepoint(mouse_x, mouse_y):
            return True
        else:
            return False

    def prep_msg(self, msg):
        """Turn msg into a rendered image and center it on the button"""
        self.msg_image = self.font.render(msg, True, self.text_color,
                                          self.config.bg_color)
        self.msg_image_rect = self.msg_image.get_rect()
        self.msg_image_rect.center = self.rect.center

    def draw_button(self):
        """Draw button and then draw message"""
        draw.rect(self.screen, self.button_color, self.rect, 3)
        self.screen.blit(self.msg_image, self.msg_image_rect)
예제 #15
0
class Ufo(pygame.sprite.Sprite):

    def __init__(self, ai_settings, screen, sound=True):
        super().__init__()

        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.UFO_pts
        self.score = None

        self.image = [pygame.image.load('images/face.png'),
                      pygame.image.load('images/face1.png'),
                      pygame.image.load('images/face2.png'),
                      pygame.image.load('images/face3.png')]
        self.image_index = 0
        self.image = self.image[self.image_index]
        self.rect = self.image.get_rect()
        self.score_image = None
        self.font = SysFont(None, 32, bold=True)
        self.prep_score()

        self.death_frames = [pygame.image.load('images/deaths/deadface.png'),
                             pygame.image.load('images/deaths/deadface1.png'),
                             pygame.image.load('images/deaths/deadface2.png'),
                             pygame.image.load('images/deaths/deadface3.png'),
                             pygame.image.load('images/deaths/deadface4.png'),
                             pygame.image.load('images/deaths/deadface5.png')]
        self.death_index = None
        # self.death_frames.append(pygame.image.load('images/deaths/deadface.png'))
        self.death_frames.append(self.score_image)
        self.last_frame = None
        self.wait_interval = 500

        self.entrance_sound = pygame.mixer.Sound('sound/UFO_entrance.wav')
        self.death_sound = pygame.mixer.Sound('sound/UFO_death.wav')
        self.entrance_sound.set_volume(0.6)
        self.channel = ai_settings.ufo_channel

        self.speed = ai_settings.ufo_spd * (choice([-1, 1]))
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        self.dead = False

        if sound:
            self.channel.play(self.entrance_sound, loops=-1)

    def kill(self):
        self.channel.stop()
        super().kill()

    def death_begins(self):
        self.channel.stop()
        self.channel.play(self.death_sound)
        self.dead = True
        self.death_index = 0
        self.image = self.death_frames[self.death_index]
        self.last_frame = pygame.time.get_ticks()

    def score(self):
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 0, 0), self.ai_settings.bg_color)

    def update(self):
        if not self.dead:
            # if abs(self.last_frame - time) > 1000:
                # self.last_frame = time
                # self.image_index = (self.image_index + 1) % len(self.images)
                # self.image = self.images[self.image_index]
            self.rect.x += self.speed
            if self.speed > 0 and self.rect.left > self.ai_settings.screen_width:
                self.kill()
            elif self.rect.right < 0:
                self.kill()
        else:
            time = pygame.time.get_ticks()
            if abs(time - self.last_frame) > self.wait_interval:
                self.last_frame = time
                self.death_index += 1
                if self.death_index >= len(self.death_frames):
                    self.kill()
                else:
                    self.image = self.death_frames[self.death_index]
                    self.wait_interval += 500

    def get_score(self):
        # get random score of ufo pt value
        self.score = choice(self.possible_scores)
        return self.score

    def blitme(self):
        self.screen.blit(self.image, self.rect)
예제 #16
0
class Plotter:
    def __init__(self, bot: 'Bot'):
        self.bot = bot
        self.bot.add_callback(self.run)
        pygame.init()
        self.win_size = (bot.game.map.width * CELL_SIZE,
                         bot.game.map.height * CELL_SIZE)
        self.update_display_size()
        pygame.mouse.set_cursor(*pygame.cursors.tri_right)
        self.font = SysFont("vcrosdmono", 16)
        self.clock = pygame.time.Clock()
        self.speed_up = DEFAULT_SPEEDUP
        self.pause = False
        self.selected = None

    def run(self):
        self.clock.tick(int(FPS * self.speed_up) if not self.pause else 60)

        keys_mod = pygame.key.get_mods()
        for e in pygame.event.get():
            if e.type == pygame.QUIT:
                raise SystemExit("QUIT")
            elif e.type == pygame.KEYDOWN:
                self.key_handler(e, keys_mod)
            elif e.type == pygame.KEYUP:
                self.key_handler(e, keys_mod, True)
            if e.type == pygame.MOUSEBUTTONUP:
                self.mouse_handler(e)

        self.screen.fill(BLACK)
        if not self.selected:
            self.draw_halite()
        else:
            self.draw_selected()
        self.draw_bases()
        self.draw_ships()

        label = self.font.render(self.info, 0, (255, 0, 0))
        self.screen.blit(label, (0, 0))
        mouse = pygame.mouse.get_pos()
        pos = mul_tuple(mouse, 1 / CELL_SIZE, integer=True)
        halite_hover = self.font.render(
            str(self.bot.game.map[pos].halite_amount), 0, GREY)
        self.screen.blit(halite_hover, mouse)

        display.update()
        return not self.pause

    def draw_halite(self):
        # halite = [[cell.halite_amount for cell in row] for row in self.bot.game.map.cells]
        # halite = blur(halite, 1, 5)
        # positions = [[cell.position for cell in row] for row in self.bot.game.map.cells]
        # field = [[MapCell(positions[i][j], halite[i][j]) for j in range(len(halite[0]))] for i in range(len(halite))]
        # for cell in chain(*field):
        for cell in self.bot.game.map:
            halite = cell.halite_amount / constants.MAX_HALITE
            color = mul_tuple((255, 255, 255), min(halite, 1), integer=True)
            if "gbh_norm" in self.bot.debug_maps:
                r, g, b = color
                k = 1 - self.bot.debug_maps["gbh_norm"][cell.position.y][
                    cell.position.x]
                g *= k
                b *= k
                color = r, g, b
            pygame.draw.rect(self.screen, color, pos2rect(cell.position))

    def draw_selected(self):
        if isinstance(self.selected, Ship):
            debug = self.bot.debug_maps.get(self.selected.id, None)
            if not debug:
                self.draw_halite()
                return
            max_value = max(debug.values())
            for position, halite in debug.items():
                pygame.draw.rect(
                    self.screen,
                    mul_tuple((255, 255, 255),
                              halite / max_value,
                              integer=True), pos2rect(position))

    def draw_ships(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for ship in player.get_ships():
                # noinspection PyTypeChecker
                is_selected = self.selected is None or self.selected.id == ship.id
                p = ship.position * CELL_SIZE + (CELL_SIZE // 2,
                                                 CELL_SIZE // 2)
                pygame.draw.circle(
                    self.screen,
                    mul_tuple(color, 1.2 if is_selected else .1, integer=True),
                    (p.x, p.y), round(CELL_SIZE / 2.5))
                self.screen.blit(self.font.render(str(ship.id), 0, GREY),
                                 (p.x, p.y))
                if ship.halite_amount:
                    pygame.draw.circle(
                        self.screen,
                        mul_tuple(WHITE,
                                  1 if is_selected else .1,
                                  integer=True), (p.x, p.y),
                        round(CELL_SIZE / 2.5 *
                              (ship.halite_amount / constants.MAX_HALITE)))
                if is_selected and self.bot.ships_targets.get(ship, None):
                    target = self.bot.ships_targets[ship]
                    if isinstance(target, Position):
                        points = (ship.position, target)
                    else:
                        points = [ship.position, *target]

                    pygame.draw.lines(self.screen, color, False, [
                        tuple(point * CELL_SIZE + CELL_SIZE // 2)
                        for point in points
                    ], 1)

    def draw_bases(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for base in (player.shipyard, ):
                pygame.draw.rect(self.screen, color, pos2rect(base.position),
                                 1)

    def update_display_size(self):
        self.screen = display.set_mode(self.win_size,
                                       pygame.DOUBLEBUF | pygame.RESIZABLE)
        display.flip()

    def key_handler(self, e, m: int, up=False):
        if not up:
            logging.debug(f"Press {e.unicode}")
            if m & pygame.KMOD_ALT and e.key == pygame.K_F4:
                raise SystemExit("QUIT")
            elif e.unicode == ',':  # '<'
                self.speed_up /= 2
            elif e.unicode == '.':  # '>'
                self.speed_up *= 2
            elif e.key == pygame.K_SPACE:
                self.pause = not self.pause

    def mouse_handler(self, e):
        map_pos = tuple(map(int, mul_tuple(e.pos, 1 / CELL_SIZE)))
        cell = self.bot.game.map[map_pos]
        logging.info(f"Cell: pos={cell.position} halite={cell.halite_amount}")
        if cell.ship:
            ship = cell.ship
            logging.info(f"Ship: id={ship.id} halite={ship.halite_amount}")
            if ship.owner == self.bot.game.me.id:
                self.selected = ship
        else:
            self.selected = None

    @property
    def info(self):
        if self.selected:
            load = (1 -
                    self.selected.halite_amount / constants.MAX_HALITE) * 100
        else:
            load = 0
        return f"{self.bot.game.turn_number}/{constants.MAX_TURNS} X{self.speed_up:.0f} |" \
               f" G: {len(self.bot.game.players[0].get_ships()):>2d} {self.bot.game.players[0].halite_amount:>5d} | " \
               f" R: {len(self.bot.game.players[1].get_ships()):>2d} {self.bot.game.players[1].halite_amount:>5d}" \
               + (f" | selected: #{self.selected.id} {load:>2.0f}%"
                  if self.selected else "")
예제 #17
0
class Plotter:
    VIEWS = [
        "__default__",
        "gbh_norm",
        "dropoff",
        "dropoff_2",
        "ships_mask",
    ]

    def __init__(self, bot: 'Bot'):
        self.bot = bot
        self.bot.add_callback(self.run)
        pygame.init()
        self.win_size = (bot.game.map.width * CELL_SIZE,
                         bot.game.map.height * CELL_SIZE)
        self.update_display_size()
        pygame.mouse.set_cursor(*pygame.cursors.tri_right)
        self.font = SysFont("vcrosdmono", 16)
        self.clock = pygame.time.Clock()
        self.speed_up = DEFAULT_SPEEDUP
        self.pause = False
        self.selected = None
        self.current_view = self.VIEWS[0]

    def run(self):
        self.clock.tick(int(FPS * self.speed_up) if not self.pause else 60)

        keys_mod = pygame.key.get_mods()
        for e in pygame.event.get():
            if e.type == pygame.QUIT:
                raise SystemExit("QUIT")
            elif e.type == pygame.KEYDOWN:
                self.key_handler(e, keys_mod)
            elif e.type == pygame.KEYUP:
                self.key_handler(e, keys_mod, True)
            if e.type == pygame.MOUSEBUTTONUP:
                self.mouse_handler(e)

        self.screen.fill(BLACK)
        if self.current_view == "__default__":
            if not self.selected:
                self.draw_halite()
            else:
                self.draw_selected()
        else:
            self.drop_custom_map(self.current_view)
        self.draw_bases()
        self.draw_ships()

        height = 0
        for info in self.info:
            label = self.font.render(info, 0, WHITE)
            self.screen.blit(label, (0, height))
            height += label.get_height() + 2
        mouse = pygame.mouse.get_pos()
        pos = mul_tuple(mouse, 1 / CELL_SIZE, integer=True)
        halite_hover = self.font.render(
            str(self.bot.game.map[pos].halite_amount), 0, GREY)
        self.screen.blit(halite_hover, mouse)

        display.update()
        return not self.pause

    def draw_halite(self):
        # halite = [[cell.halite_amount for cell in row] for row in self.bot.game.map.cells]
        # halite = blur(halite, 1, 5)
        # positions = [[cell.position for cell in row] for row in self.bot.game.map.cells]
        # field = [[MapCell(positions[i][j], halite[i][j]) for j in range(len(halite[0]))] for i in range(len(halite))]
        # for cell in chain(*field):
        for cell in self.bot.game.map:
            halite = cell.halite_amount / constants.MAX_HALITE
            color = mul_tuple((255, 255, 255), min(halite, 1), integer=True)
            if "gbh_norm" in self.bot.debug_maps:
                r, g, b = color
                k = 1 - self.bot.debug_maps["gbh_norm"][cell.position.y][
                    cell.position.x]
                g *= k
                b *= k
                color = r, g, b
            pygame.draw.rect(self.screen, color, pos2rect(cell.position))

    def draw_selected(self):
        if isinstance(self.selected, Ship):
            debug_map = self.bot.debug_maps.get(self.selected.id, None)
            if debug_map is None:
                self.draw_halite()
                return
            max_value = debug_map.max()
            it = np.nditer(debug_map, ['multi_index'])
            while not it.finished:
                halite = it[0]
                position = Position(*reversed(it.multi_index))
                pygame.draw.rect(
                    self.screen,
                    mul_tuple((255, 255, 255),
                              halite / max_value,
                              integer=True), pos2rect(position))
                it.iternext()

    def draw_ships(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for ship in player.get_ships():
                # noinspection PyTypeChecker
                is_selected = self.selected is None or self.selected.id == ship.id
                p = ship.position * CELL_SIZE + (CELL_SIZE // 2,
                                                 CELL_SIZE // 2)
                pygame.draw.circle(
                    self.screen,
                    mul_tuple(color, 1.2 if is_selected else .1, integer=True),
                    (p.x, p.y), round(CELL_SIZE / 2.5))
                self.screen.blit(self.font.render(str(ship.id), 0, GREY),
                                 (p.x, p.y))
                if ship.halite_amount:
                    pygame.draw.circle(
                        self.screen,
                        mul_tuple(WHITE,
                                  1 if is_selected else .1,
                                  integer=True), (p.x, p.y),
                        round(CELL_SIZE / 2.5 *
                              (ship.halite_amount / constants.MAX_HALITE)))
                if is_selected and self.bot.ship_manager.targets.get(
                        ship, None):
                    target = self.bot.ship_manager.targets[ship]
                    if isinstance(target, Position):
                        points = (ship.position, target)
                    else:
                        points = [ship.position, *target]

                    pygame.draw.lines(self.screen, color, False, [
                        tuple(point * CELL_SIZE + CELL_SIZE // 2)
                        for point in points
                    ], 1)

    def draw_bases(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for base in (player.shipyard, *player.get_dropoffs()):
                pygame.draw.rect(self.screen, color, pos2rect(base.position),
                                 1)

    def drop_custom_map(self, view):
        debug_map = self.bot.debug_maps.get(view, None)
        if debug_map is None:
            self.draw_halite()
            return
        max_value = debug_map.max()
        min_value = debug_map.min()
        it = np.nditer(debug_map, ['multi_index'])
        while not it.finished:
            halite = it[0]
            position = Position(*reversed(it.multi_index))
            k = (max_value - min_value) or .1
            pygame.draw.rect(
                self.screen,
                mul_tuple((255, 255, 255), (halite - min_value) / k,
                          integer=True), pos2rect(position))
            it.iternext()

    def update_display_size(self):
        self.screen = display.set_mode(self.win_size,
                                       pygame.DOUBLEBUF | pygame.RESIZABLE)
        display.flip()

    def key_handler(self, e, m: int, up=False):
        if not up:
            logging.debug(f"Press {e.unicode}")
            if m & pygame.KMOD_ALT and e.key == pygame.K_F4:
                raise SystemExit("QUIT")
            elif e.unicode == ',':  # '<'
                self.speed_up /= 2
            elif e.unicode == '.':  # '>'
                self.speed_up *= 2
            elif e.key == pygame.K_SPACE:
                self.pause = not self.pause
            elif '0' <= e.unicode <= '9':
                code = int(e.unicode)
                if code == 0:
                    code = 9
                else:
                    code -= 1
                self.current_view = self.VIEWS[code]

    def mouse_handler(self, e):
        map_pos = tuple(map(int, mul_tuple(e.pos, 1 / CELL_SIZE)))
        cell = self.bot.game.map[map_pos]
        logging.info(f"Cell: pos={cell.position} halite={cell.halite_amount}")
        if cell.ship:
            ship = cell.ship
            logging.info(f"Ship: id={ship.id} halite={ship.halite_amount}")
            if ship.owner == self.bot.game.me.id:
                self.selected = ship
        else:
            self.selected = None

    @property
    def info(self):
        gmap = self.bot.game.map
        if self.selected:
            load = (1 -
                    self.selected.halite_amount / constants.MAX_HALITE) * 100
        else:
            load = 0

        total = gmap.total_halite
        info = [
            f"{self.bot.game.turn_number:>3d}/{constants.MAX_TURNS} X{self.speed_up:.0f} "
            f"{total:>6.0f} {total / gmap.initial_halite:>3.0%} ({self.bot.ship_fill_k:.1f})"
        ]

        players = [
            f"{color}: {len(p.get_ships()):>2d} {p.halite_amount:>5d}"
            for color, p in zip("GRBC", self.bot.game.players.values())
        ]
        info.append(f"{players[0]} | {players[1]}")
        if len(players) > 2:
            info.append(f"{players[2]} | {players[3]}")

        if self.selected:
            info.append(f":> selected: #{self.selected.id} {load:>2.0f}%")

        return info
예제 #18
0
class Ufo(pygame.sprite.Sprite):

    def __init__(self, ai_settings, screen, sound=True):
        super().__init__()
        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.ufo_point_values
        self.score = None

        self.image = pygame.image.load('resources/Images/UFO Alien-1.png')
        self.rect = self.image.get_rect()
        self.score_image = None
        self.font = SysFont(None, 32, italic=True)
        self.prep_score()

        self.death_frames = []
        self.death_index = None
        self.death_frames.append(pygame.image.load('resources/Images/UFO Alien-3.png'))
        self.death_frames.append(self.score_image)
        self.last_frame = None
        self.wait_interval = 500

        self.entrance_sound = pygame.mixer.Sound('resources/Sounds/ufo_lowpitch.wav')
        self.death_sound = pygame.mixer.Sound('resources/Sounds/invaderkilled.wav')
        self.entrance_sound.set_volume(0.6)
        self.channel = ai_settings.ufo_channel

        self.speed = ai_settings.ufo_speed * (choice([-1, 1]))
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        self.dead = False

        if sound:
            self.channel.play(self.entrance_sound, loops=-1)

    def kill(self):
        self.channel.stop()
        super().kill()

    def begin_death(self):
        self.channel.stop()
        self.channel.play(self.death_sound)
        self.dead = True
        self.death_index = 0
        self.image = self.death_frames[self.death_index]
        self.last_frame = pygame.time.get_ticks()

    def get_score(self):
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 0, 0), self.ai_settings.bg_color)

    def update(self):
        if not self.dead:
            self.rect.x += self.speed
            if self.speed > 0 and self.rect.left > self.ai_settings.screen_width:
                self.kill()
            elif self.rect.right < 0:
                self.kill()
        else:
            time_test = pygame.time.get_ticks()
            if abs(time_test - self.last_frame) > self.wait_interval:
                self.last_frame = time_test
                self.death_index += 1
                if self.death_index >= len(self.death_frames):
                    self.kill()
                else:
                    self.image = self.death_frames[self.death_index]
                    self.wait_interval += 500

    def blitme(self):
        self.screen.blit(self.image, self.rect)
예제 #19
0
class UFO(pygame.sprite.Sprite):
    """Represents a UFO meant to move across the screen at random intervals"""
    def __init__(self, ai_settings, screen, sound=True):
        super().__init__()

        # Set screen
        self.sound = sound
        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.ufo_point_values
        self.score = None

        # Load Image
        self.image = pygame.image.load('images/ufo.png')
        self.rect = self.image.get_rect()
        self.score_image = None
        self.font = SysFont(None, 32, italic=True)
        self.prep_score()

        # Sound of UFO
        self.entrance_sound = pygame.mixer.Sound('sounds/ufo.wav')
        self.hit_sound = pygame.mixer.Sound('sounds/ufoHit.wav')
        self.entrance_sound.set_volume(0.6)
        self.channel = ai_settings.ufoRadio

        # Speed of UFO
        self.speed = ai_settings.ufo_speed * (choice([-1, 1]))

        # Starting Position with speed
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        # When UFO is inactive
        self.dead = False

        # When UFO hit
        self.hit_animated = []
        self.hit_index = None
        self.hit_animated.append(self.score_image)
        self.end_scene = None
        self.wait_interval = 200

    def blitme(self):
        self.screen.blit(self.image, self.rect)

    def hit_ufo(self):
        self.channel.stop()
        self.channel.play(self.hit_sound)
        self.dead = True
        self.hit_index = 0
        self.image = self.hit_animated[self.hit_index]
        self.end_scene = pygame.time.get_ticks()

    def died(self):
        self.channel.stop()
        super().kill()

    def get_score(self):
        """Get any score"""
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 223, 0), self.ai_settings.bg_color)

    def update(self):
        """Update the UFO functions"""

        # When ufo is not yet dead manage the speed
        if not self.dead:
            self.rect.x += self.speed
            if self.speed > 0 and self.rect.left > self.ai_settings.screen_width:
                self.died()
            elif self.rect.right < 0:
                self.died()
        else:
            # Random movements of ufo
            timer = pygame.time.get_ticks()
            if abs(timer - self.end_scene) > self.wait_interval:
                self.end_scene = timer
                self.hit_index += 1
                if self.hit_index >= len(self.hit_animated):
                    self.died()
                else:
                    # When UFO get hit the image animates through
                    self.image = self.hit_animated[self.hit_index]
                    self.wait_interval += 200
예제 #20
0
class Ufo(Sprite):
    """Represents a UFO meant to move across the screen at random intervals."""
    def __init__(self, ai_settings, screen):
        """Initialize ufo settings."""
        super().__init__()

        # screen, settings, score values
        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.ufo_points
        self.score = None

        # images, score text
        self.image = pygame.image.load('images/ufo.png')
        self.rect = self.image.get_rect()
        self.score_image = None
        self.font = SysFont(None, 32, italic=True)
        self.prep_score()

        # death frames
        self.death_frames = []
        self.death_index = None
        self.death_frames.append(
            pygame.image.load('images/ufo_death/ufo_death.png'))
        self.death_frames.append(self.score_image)
        self.last_frame = None
        self.wait_interval = 500

        # sound
        self.entrance_sound = pygame.mixer.Sound('sounds/ufo_sound.wav')
        self.death_sound = pygame.mixer.Sound('sounds/ufo_death.wav')
        self.entrance_sound.set_volume(0.6)
        self.channel = ai_settings.ufo_channel

        # initial position, speed/direction
        self.speed = ai_settings.ufo_speed_factor * (choice([-1, 1]))
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        # death flag
        self.dead = False

        # Play sound while its on screen
        self.channel.play(self.entrance_sound, loops=-1)

    def kill(self):
        """Stop music if killed and remove ufo from group."""
        self.channel.stop()
        super().kill()

    def begin_death(self):
        self.channel.stop()
        self.channel.play(self.death_sound)
        self.dead = True
        self.death_index = 0
        self.image = self.death_frames[self.death_index]
        self.last_frame = pygame.time.get_ticks()

    def get_score(self):
        """Get a random score from the UFO's possible score values."""
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        """Prepare score pop up when killed."""
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 0, 0),
                                            self.ai_settings.bg_color)

    def update(self):
        """Update the ufo."""
        if not self.dead:
            self.rect.x += self.speed
            if self.speed > 0 and self.rect.left > self.ai_settings.screen_width:
                self.kill()
            elif self.rect.right < 0:
                self.kill()
        else:
            time_test = pygame.time.get_ticks()
            if abs(time_test - self.last_frame) > self.wait_interval:
                self.last_frame = time_test
                self.death_index += 1
                if self.death_index >= len(self.death_frames):
                    self.kill()
                else:
                    self.image = self.death_frames[self.death_index]
                    self.wait_interval += 350

    def blitme(self):
        """Draw ufo on screen."""
        self.screen.blit(self.image, self.rect)
예제 #21
0
class Ufo(pygame.sprite.Sprite):
    """Represents a UFO meant to move across the screen at random intervals"""
    def __init__(self, ai_settings, screen, sound=True):
        super().__init__()
        # screen, settings, score values
        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.ufo_point_values
        self.ufo_images = None
        self.image = None
        self.image_index = None
        self.death_index = None
        self.last_frame = None
        self.death_frames = None
        self.rect = None
        self.score = None

        self.score_image = None
        self.font = SysFont(None, 32, italic=True)
        self.prep_score()

        # sound
        self.entrance_sound = pygame.mixer.Sound('sound/ufoAppeared.wav')
        self.death_sound = pygame.mixer.Sound('sound/Gottem.wav')
        self.entrance_sound.set_volume(0.6)
        self.channel = ai_settings.ufo_channel

        # death flag
        self.dead = False

        # images, score text
        self.ufo_images = [
            pygame.image.load('images/Fish/Fish_0.png'),
            pygame.image.load('images/Fish/Fish_0.png'),
            pygame.image.load('images/Fish/Fish_1.png'),
            pygame.image.load('images/Fish/Fish_1.png'),
            pygame.image.load('images/Fish/Fish_2.png'),
            pygame.image.load('images/Fish/Fish_2.png'),
            pygame.image.load('images/Fish/Fish_3.png'),
            pygame.image.load('images/Fish/Fish_3.png'),
            pygame.image.load('images/Fish/Fish_4.png'),
            pygame.image.load('images/Fish/Fish_4.png'),
            pygame.image.load('images/Fish/Fish_5.png'),
            pygame.image.load('images/Fish/Fish_6.png'),
            pygame.image.load('images/Fish/Fish_6.png')
        ]
        # death frames
        self.death_frames = [
            pygame.image.load('images/Boom/Boom_0.png'),
            pygame.image.load('images/Boom/Boom_1.png'),
            pygame.image.load('images/Boom/Boom_2.png'),
            pygame.image.load('images/Boom/Boom_3.png'),
            pygame.image.load('images/Boom/Boom_4.png'),
            pygame.image.load('images/Boom/Boom_5.png'),
            pygame.image.load('images/Boom/Boom_6.png'),
            pygame.image.load('images/Boom/Boom_7.png'),
            pygame.image.load('images/Boom/Boom_8.png')
        ]
        self.death_frames.append(self.score_image)
        self.image_index = 0
        self.image = self.ufo_images[self.image_index]
        self.rect = self.image.get_rect()
        self.last_frame = pygame.time.get_ticks()

        # initial position, speed/direction
        self.speed = ai_settings.ufo_speed * (choice([-1, 1]))
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        self.last_frame = 0
        self.wait_interval = 0

        if sound:
            self.channel.play(self.entrance_sound, loops=-1)

    def kill(self):
        self.channel.stop()
        super().kill()

    def begin_death(self):
        self.channel.stop()
        self.channel.play(self.death_sound)
        self.dead = True
        self.death_index = 0
        self.image = self.death_frames[self.death_index]
        self.last_frame = 0

    def get_score(self):
        """Get a random score from the UFO's possible score values"""
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 0, 0),
                                            self.ai_settings.bg_color)

    def update(self):
        time_test = pygame.time.get_ticks()

        if not self.dead:
            if abs(self.last_frame - time_test) > 50:
                self.last_frame = time_test
                self.image_index = (self.image_index + 1) % len(
                    self.ufo_images)  # Loop over frames
                self.image = self.ufo_images[self.image_index]

        if not self.dead:
            self.rect.x += self.speed
            if self.speed > 0 and self.rect.left > self.ai_settings.screen_width:
                self.kill()
            elif self.rect.right < 0:
                self.kill()

        else:
            if abs(self.last_frame - time_test
                   ) > 100:  # At least 100 millisecond delay between frames
                self.last_frame = time_test  # Delay should ensure animation is perceivable at high fps
                self.death_index += 1
                if self.death_index >= len(self.death_frames):
                    self.kill()
                else:
                    self.image = self.death_frames[self.death_index]
                    self.wait_interval += 100

    def blitme(self):
        self.screen.blit(self.image, self.rect)
예제 #22
0
class Game:
    """
       Class with game settings/level loaders/game rules
          :self.width (int) width of game window;
          :self.height (int) - height of game window;
          :self.full_screen (int) - FULLSCREEN or 0;
          :self.fps (int) - frame per second;
          :self.caption (str) - window name;
          :self.active_game (bool) - if false - quit from game else game is running
          :self.background_path (str) - path to image background
          :self._screen (pygame.Surface) - screen where image will be drew
          :self.background_image (pygame.image) - background image
    """
    def __init__(self):
        self.width = 0
        self.height = 0
        self.full_screen = True
        self.fps = 0
        self.caption = 'Adventure'
        self.active_game = True
        self.statistics = False
        self.background_path = 'Gamedata/Backgrounds/fon.png'
        self.max_distance = 0
        self.total_distance = 0
        self.sound = True
        self.font = SysFont(None, 45)
        self._screen = None
        self._camera = None

    @staticmethod
    def _get_settings():
        """
        Method for getting game settings from file
        :return: settings_data (dict) - dict with game settings
        """
        settings_data = dict()
        with open('Gamedata/settings.txt', mode='r') as f:
            for line in f:
                line = line.split(':')
                parameter, value = line[0], int(line[-1])
                settings_data[parameter] = value
        return settings_data

    @property
    def background_image(self):
        return pygame.image.load(self.background_path)

    @property
    def clock_(self):
        return pygame.time.Clock()

    def set_screen(self):
        """
        Set screen with self.width, self.height and self.full_screen
        :return: None
        """

        self._screen = pygame.display.set_mode((self.width, self.height),
                                               self.full_screen)

    def set_camera(self):
        self._camera = Camera(camera_configure, (self.width, self.height))

    @staticmethod
    def _get_save_data():
        """
        Method for getting game saves from file
        :return: save_data (dict) - dict with save data
        """
        save_data = dict()
        with open('GameData/saves.txt', mode='r') as f:
            for line in f:
                line = line.split(':')
                save_data[line[0]] = int(line[-1])
        return save_data

    def _menu(self):
        """
        Menu level where player may choose settings/levels and etc.
        If self.active_game is True it means that game is running else
        exiting the game
        :return: None
        """

        ui_elems = self._load_menudata()
        while self.active_game:

            for event in pygame.event.get():
                if event.type == MOUSEBUTTONUP:
                    pos = pygame.mouse.get_pos()
                    for obj in ui_elems:
                        if obj.name == 'start' and obj.check_collision(
                                pos, self.sound):
                            self._game_loop()
                        if obj.name == 'music' and obj.check_collision(
                                pos, self.sound):
                            self.sound = not self.sound
                            obj.change_state()
                        if obj.name == 'trophy' and obj.check_collision(
                                pos, self.sound):
                            self._get_statistics(obj)
                        if obj.name == 'quit' and obj.check_collision(
                                pos, self.sound):
                            self.active_game = False

                if event.type == QUIT:
                    self.active_game = False

            self._screen.blit(self.background_image, (0, 0))
            for obj in ui_elems:
                self._screen.blit(obj.main_image, obj.left_up_corner)
            pygame.display.update()
            self.clock_.tick(self.fps)

        self._save_game()
        pygame.quit()

    def _load_game(self):
        """
        Load game with saved game settings and game status
        :return: None
        """

        settings = self._get_settings()
        for parameter, value in settings.items():
            if parameter == 'width':
                self.width = value
            elif parameter == 'height':
                self.height = value
            elif parameter == 'full_screen':
                self.full_screen = FULLSCREEN if value == 1 else 0
            elif parameter == 'fps':
                self.fps = value
            elif parameter == 'sound':
                self.sound = True if value == 1 else False
            else:
                raise ('Undefined parameter ' + str(parameter) +
                       ' in settings.txt')

        saves = self._get_save_data()
        for parameter, value in saves.items():
            if parameter == 'max_distance':
                self.max_distance = value
            elif parameter == 'total_distance':
                self.total_distance = value
            else:
                raise ('Undefined parameter ' + str(parameter) +
                       'in saves.txt')

        self.set_screen()

    @staticmethod
    def _load_menudata():
        """
        Load icons and its sounds for menu game
        :return: (arr) - ui_elems
        """

        data = [(['GameData/Menu/buttonStart.png'], 'start', (450, 384),
                 (90, 60), 'GameData/Sounds/MainButton.wav'),
                (['GameData/Menu/trophy.png'], 'trophy', (900, 50), (50, 50),
                 'GameData/Sounds/click.wav'),
                (['GameData/Menu/musicOn.png', 'GameData/Menu/musicOff.png'],
                 'music', (900, 100), (50, 50), 'GameData/Sounds/click.wav'),
                (['GameData/Menu/quit.png'], 'quit', (900, 150), (50, 50),
                 'GameData/Sounds/click.wav')]
        ui_elems = []
        for img_paths, name, coords, shape, sound_path in data:
            imgs = []
            for img_path in img_paths:
                img = pygame.image.load(img_path)
                imgs.append(img)
            ui_obj = UiObject(imgs, name, *coords, *shape, sound_path)
            ui_elems.append(ui_obj)
        return ui_elems

    def _game_loop(self):
        """
        Main loop with game where will be load main character, game mobs, ui levels and etc
        During the game all game objects will be drawn in self._screen
        Self.clock_ supports current self.fps
        :return: None
        """

        player = MainCharacter()
        level_generator = LevelGenerator(play_sounds=self.sound)
        dead_mobs = Group()
        self.set_camera()
        active_level = True
        result_session_was_saved = False
        while active_level:

            for event in pygame.event.get():
                if event.type == QUIT or (event.type == MOUSEBUTTONUP
                                          and player.is_dead):
                    active_level = False

            self._screen.blit(self.background_image, (0, 0))
            level_data = level_generator.draw_blocks(self._screen,
                                                     self._camera,
                                                     player.region)
            left_region = level_generator.get_left_region()

            level_blocks = level_data['level_blocks'].copy()
            level_blocks.add(level_data['mobs'])

            if not player.is_dead:
                player.move(self._screen, self._camera, left_region,
                            level_blocks)
            else:
                if not result_session_was_saved:
                    self._save_session_result(player)
                    result_session_was_saved = True
                self._get_end_game_caption()

            for entity in level_data['mobs']:
                if entity.live(self._screen, self._camera, level_blocks):
                    dead_mobs.add(entity)
                    level_generator.remove_objects(entity)

            for dead_entity in dead_mobs:
                if dead_entity.die(self._screen, self._camera):
                    dead_mobs.remove(dead_entity)

            self._draw_ui_elem(player)
            pygame.display.update()
            self._camera.update(player)
            self.clock_.tick(self.fps)

    def start_game(self):
        """
        Public method for starting the game
        :return: None
        """

        self._load_game()
        pygame.display.set_caption(self.caption)
        self._menu()

    def _get_end_game_caption(self):
        """
            Method for drawing end game caption
        :return: None
        """
        curr_font = self.font.render(GAME_OVER_CAPTION, 0, GREEN)
        self._screen.blit(curr_font,
                          (GAME_OVER_CAPTION_X, GAME_OVER_CAPTION_Y))

    def _save_session_result(self, player):
        """
            Method for saving session data
        :param player: (Player) - player object
        :return: None
        """
        self.max_distance = max(self.max_distance, player.max_distance)
        self.total_distance += player.max_distance

    def _draw_ui_elem(self, player):
        """
           Method for drawing ui elems in during the game (health and etc.)
        :param player: (Player) - player object
        :return: None
        """
        health_font = self.font.render(str(player.health), 0, GREEN)
        self._screen.blit(player.health_image,
                          (HEALTH_IMAGE_X, HEALTH_IMAGE_Y))
        self._screen.blit(health_font, (HEALTH_X, HEALTH_Y))

    def _get_statistics(self, trophy_obj):
        """
           Method for showing statistics to player
        :param trophy_obj: (UiObject)
        :return: None
        """
        self.statistics = True
        curr_font = self.font.render(
            THE_LONGEST_DISTANCE_CAPTION + str(self.max_distance), 0, GREEN)
        curr_font_2 = self.font.render(
            ALL_DISTANCE_CAPTION + str(self.total_distance), 0, GREEN)

        while self.statistics:

            for event in pygame.event.get():
                if event.type == MOUSEBUTTONUP:
                    pos = pygame.mouse.get_pos()
                    if trophy_obj.check_collision(pos, self.sound):
                        self.statistics = False

                if event.type == QUIT:
                    self.statistics = False

            self._screen.blit(self.background_image, (0, 0))

            self._screen.blit(curr_font,
                              (DISTANCE_CAPTION_X, DISTANCE_CAPTION_Y))
            self._screen.blit(curr_font_2,
                              (ALL_DISTANCE_CAPTION_X, ALL_DISTANCE_CAPTION_Y))
            self._screen.blit(trophy_obj.main_image, trophy_obj.left_up_corner)

            pygame.display.update()
            self.clock_.tick(self.fps)

    def _save_game(self):
        """
           Save statistics data and settings in the end of game.
        :return: None
        """
        settings = {
            'width': self.width,
            'height': self.height,
            'full_screen': self.full_screen,
            'fps': self.fps,
            'sound': self.sound
        }
        statistics = {
            'max_distance': self.max_distance,
            'total_distance': self.total_distance
        }

        with open('GameData/settings.txt', 'w') as f:
            for parameter, value in settings.items():
                if isinstance(value, bool):
                    value = 1 if value is True else 0
                if parameter == 'full_screen' and value != 0:
                    value = 1
                f.write(parameter + ': ' + str(value) + '\n')

        with open('GameData/saves.txt', 'w') as f:
            for parameter, value in statistics.items():
                f.write(parameter + ': ' + str(value) + '\n')
예제 #23
0
class Ufo(Sprite):
    """Represents a UFO meant to move across the screen at random intervals"""
    def __init__(self, ai_settings, screen, sound=True):
        super().__init__()
        # screen, settings, score values
        self.screen = screen
        self.ai_settings = ai_settings
        self.possible_scores = ai_settings.ufo_point_values
        self.score = None

        # images, score text
        self.ss = spritesheet('images/SpriteSheet.png')
        self.image = self.ss.image_at((64, 0, 32, 32))
        self.rect = self.image.get_rect()
        self.score_image = None
        self.font = SysFont(None, 32, italic=True)
        self.prep_score()

        # death frames
        self.death_frames = []
        self.death_index = None
        self.death_frames.append(self.ss.image_at((32, 64, 32, 32)))
        self.death_frames.append(self.score_image)
        self.last_frame = None
        self.wait_interval = 500

        # sound
        self.entrance_sound = pygame.mixer.Sound('sound/ufo_highpitch.wav')
        self.death_sound = pygame.mixer.Sound('sound/invaderkilled.wav')
        self.channel = pygame.mixer.Channel(3)
        self.channel.set_volume(0.01)

        # initial position, speed/direction
        self.speed = (choice([-1, 1]))
        self.rect.x = 0 if self.speed > 0 else ai_settings.screen_width
        self.rect.y = ai_settings.screen_height * 0.1

        # death flag
        self.dead = False

        if sound:
            self.channel.play(self.entrance_sound, loops=-1)

    def kill(self):
        self.channel.stop()
        super().kill()

    def death_animation(self):
        self.channel.stop()
        self.channel.play(self.death_sound)
        self.dead = True
        self.death_index = 0
        self.image = self.death_frames[self.death_index]
        self.last_frame = pygame.time.get_ticks()

    def get_score(self):
        """Get a random score from the UFO's possible score values"""
        self.score = choice(self.possible_scores)
        return self.score

    def prep_score(self):
        score_str = str(self.get_score())
        self.score_image = self.font.render(score_str, True, (255, 0, 0),
                                            self.ai_settings.bg_color)

    def update(self):
        if not self.dead:
            self.rect.x += self.speed
            screen_rect = self.screen.get_rect()
            if self.rect.left >= screen_rect.right and self.speed > 0:
                self.kill()
            elif self.rect.right <= screen_rect.left and self.speed < 0:
                self.kill()
        else:
            time_test = pygame.time.get_ticks()
            if abs(time_test - self.last_frame) > self.wait_interval:
                self.last_frame = time_test
                self.death_index += 1
                if self.death_index >= len(self.death_frames):
                    self.kill()
                else:
                    self.image = self.death_frames[self.death_index]
                    self.wait_interval += 500

    def blitme(self):
        self.screen.blit(self.image, self.rect)
예제 #24
0
class Ghosts(Sprite):
    def __init__(self, screen, color):
        super(Ghosts, self).__init__()
        self.color = color  # ghost type
        self.screen = screen
        self.height = 35
        self.width = 35
        self.reset()

        Cyan_sheet = SheetSprites.sheetSprites('images/Cyan.png')
        Yellow_sheet = SheetSprites.sheetSprites('images/Yellow.png')
        Pink_sheet = SheetSprites.sheetSprites('images/Pink.png')
        Red_sheet = SheetSprites.sheetSprites('images/Red.png')
        Scared_sheet = SheetSprites.sheetSprites('images/Ghost_power.png')
        Eyes_sheet = SheetSprites.sheetSprites('images/Ghost_die.png')

        self.left_image = []
        self.right_image = []
        self.up_image = []
        self.down_image = []
        self.Scared = [
            Scared_sheet.image_at((0, 0, 32, 38)),
            Scared_sheet.image_at((0, 38, 32, 38)),
            Scared_sheet.image_at((0, 76, 32, 38)),
            Scared_sheet.image_at((0, 114, 32, 38))
        ]
        self.eyes = [
            Eyes_sheet.image_at((0, 0, 23, 12)),
            Eyes_sheet.image_at((0, 12, 23, 12)),
            Eyes_sheet.image_at((0, 24, 23, 12)),
            Eyes_sheet.image_at((0, 36, 23, 12))
        ]

        if color == "red":
            self.left_image = [
                Red_sheet.image_at((0, 76, 32, 38)),
                Red_sheet.image_at((0, 228, 32, 38))
            ]
            self.right_image = [
                Red_sheet.image_at((0, 190, 32, 38)),
                Red_sheet.image_at((0, 266, 32, 38))
            ]
            self.up_image = [
                Red_sheet.image_at((0, 0, 32, 38)),
                Red_sheet.image_at((0, 114, 32, 38))
            ]
            self.down_image = [
                Red_sheet.image_at((0, 38, 32, 38)),
                Red_sheet.image_at((0, 152, 32, 38))
            ]
        elif color == "cyan":
            self.left_image = [
                Cyan_sheet.image_at((0, 76, 32, 38)),
                Cyan_sheet.image_at((0, 228, 32, 38))
            ]
            self.right_image = [
                Cyan_sheet.image_at((0, 190, 32, 38)),
                Cyan_sheet.image_at((0, 266, 32, 38))
            ]
            self.up_image = [
                Cyan_sheet.image_at((0, 0, 32, 38)),
                Cyan_sheet.image_at((0, 114, 32, 38))
            ]
            self.down_image = [
                Cyan_sheet.image_at((0, 38, 32, 38)),
                Cyan_sheet.image_at((0, 152, 32, 38))
            ]
        elif color == "Yellow":
            self.left_image = [
                Yellow_sheet.image_at((0, 76, 32, 38)),
                Yellow_sheet.image_at((0, 228, 32, 38))
            ]
            self.right_image = [
                Yellow_sheet.image_at((0, 190, 32, 38)),
                Yellow_sheet.image_at((0, 266, 32, 38))
            ]
            self.up_image = [
                Yellow_sheet.image_at((0, 0, 32, 38)),
                Yellow_sheet.image_at((0, 114, 32, 38))
            ]
            self.down_image = [
                Yellow_sheet.image_at((0, 38, 32, 38)),
                Yellow_sheet.image_at((0, 152, 32, 38))
            ]
        elif color == "pink":
            self.left_image = [
                Pink_sheet.image_at((0, 76, 32, 38)),
                Pink_sheet.image_at((0, 228, 32, 38))
            ]
            self.right_image = [
                Pink_sheet.image_at((0, 190, 32, 38)),
                Pink_sheet.image_at((0, 266, 32, 38))
            ]
            self.up_image = [
                Pink_sheet.image_at((0, 0, 32, 38)),
                Pink_sheet.image_at((0, 114, 32, 38))
            ]
            self.down_image = [
                Pink_sheet.image_at((0, 38, 32, 38)),
                Pink_sheet.image_at((0, 152, 32, 38))
            ]

        self.rect = pygame.transform.scale(
            self.up_image[0], (self.height, self.width)).get_rect()
        self.rect.x, self.rect.y = 330, 315
        self.rect.left -= self.rect.width
        self.rect.top -= self.rect.height
        self.image = [None, None]
        self.image = self.up_image

        self.moving_up = True
        self.moving_down = False
        self.moving_left = False
        self.moving_right = False

        self.last_move = "up/down"
        self.last_intersection = None

        self.speed = 1

        # ghosts are blue
        self.afraid = False

        # ghosts are eyes
        self.DEAD = False

        self.value = 0
        self.font = SysFont(None, 16, italic=True)
        self.score_image = self.font.render(str(self.value), True,
                                            (255, 255, 255), (0, 0, 0))

        # how long to show score
        self.frames = 0

    def update(self):
        if self.moving_left == True:
            self.rect.x -= self.speed
            self.image = self.left_image
        elif self.moving_right == True:
            self.rect.x += self.speed
            self.image = self.right_image
        elif self.moving_up == True:
            self.rect.y -= self.speed
            self.image = self.up_image
        elif self.moving_down == True:
            self.rect.y += self.speed
            self.image = self.down_image

    def blitghosts(self):
        if self.DEAD:
            if self.moving_left:
                self.screen.screen.blit(self.eyes[2], self.rect)
            elif self.moving_right:
                self.screen.screen.blit(self.eyes[3], self.rect)
            elif self.moving_up:
                self.screen.screen.blit(self.eyes[1], self.rect)
            elif self.moving_down:
                self.screen.screen.blit(self.eyes[0], self.rect)
        elif self.afraid:
            if self.frames <= 720:
                if pygame.time.get_ticks() % 200 <= 50:
                    self.screen.screen.blit(self.Scared[2], self.rect)
                elif pygame.time.get_ticks() % 200 <= 100:
                    self.screen.screen.blit(self.Scared[3], self.rect)
                elif pygame.time.get_ticks() % 200 <= 150:
                    self.screen.screen.blit(self.Scared[2], self.rect)
                else:
                    self.screen.blit(self.Scared[3], self.rect)
            elif self.frames <= 960:
                if pygame.time.get_ticks() % 200 <= 50:
                    self.screen.blit(self.Scared[0], self.rect)
                elif pygame.time.get_ticks() % 200 <= 100:
                    self.screen.blit(self.Scared[1], self.rect)
                elif pygame.time.get_ticks() % 200 <= 150:
                    self.screen.blit(self.Scared[2], self.rect)
                else:
                    self.screen.blit(self.Scared[3], self.rect)
        else:
            if pygame.time.get_ticks() % 200 <= 50:
                self.screen.blit(self.image[0], self.rect)
            elif pygame.time.get_ticks() % 200 <= 100:
                self.screen.blit(self.image[1], self.rect)
            elif pygame.time.get_ticks() % 200 <= 150:
                self.screen.blit(self.image[0], self.rect)
            else:
                self.screen.blit(self.image[1], self.rect)
        if self.frames <= 60 and self.DEAD:
            self.screen.blit(self.score_image, self.rect)
            self.frames += 1
        if self.frames <= 960 and self.afraid:
            self.frames += 1
        elif self.frames > 960 and self.afraid:
            self.afraid = False
            self.frames = 0

    def resetPosition(self):
        self.moving_up = True  # Start with the ghosts going up
        self.moving_down = False
        self.moving_left = False
        self.moving_right = False
        self.rect.x, self.rect.y = 300, 300

        self.afraid = False
        self.DEAD = False

    def reset(self):
        pass
예제 #25
0
class Plotter:
    def __init__(self, bot: 'Bot'):
        self.bot = bot
        self.bot.add_callback(self.run)
        pygame.init()
        self.win_size = (bot.game.map.width * CELL_SIZE, bot.game.map.height * CELL_SIZE)
        self.update_display_size()
        pygame.mouse.set_cursor(*pygame.cursors.tri_right)
        self.font = SysFont("vcrosdmono", 16)
        self.clock = pygame.time.Clock()
        self.speed_up = DEFAULT_SPEEDUP
        self.pause = False
        self.selected = None

    def run(self):
        self.clock.tick(int(FPS * self.speed_up) if not self.pause else 60)

        keys_mod = pygame.key.get_mods()
        for e in pygame.event.get():
            if e.type == pygame.QUIT:
                raise SystemExit("QUIT")
            elif e.type == pygame.KEYDOWN:
                self.key_handler(e, keys_mod)
            elif e.type == pygame.KEYUP:
                self.key_handler(e, keys_mod, True)
            if e.type == pygame.MOUSEBUTTONUP:
                self.mouse_handler(e)

        self.screen.fill(BLACK)
        if not self.selected:
            self.draw_halite()
        else:
            self.draw_selected()
        self.draw_bases()
        self.draw_ships()

        label = self.font.render(self.info, 0, (255, 0, 0))
        self.screen.blit(label, (0, 0))
        mouse = pygame.mouse.get_pos()
        pos = mul_tuple(mouse, 1 / CELL_SIZE, integer=True)
        halite_hover = self.font.render(str(self.bot.game.map[pos].halite_amount), 0, GREY)
        self.screen.blit(halite_hover, mouse)

        display.update()
        return not self.pause

    def draw_halite(self):
        for cell in self.bot.game.map:
            pygame.draw.rect(
                self.screen,
                mul_tuple((250, 250, 250), cell.halite_amount / constants.MAX_HALITE, integer=True),
                pos2rect(cell.position)
            )

    def draw_selected(self):
        if isinstance(self.selected, Ship):
            debug = self.bot.debug_maps.get(self.selected.id, None)
            if not debug:
                self.draw_halite()
                return
            max_value = max(debug.values())
            for position, halite in debug.items():
                pygame.draw.rect(
                    self.screen,
                    mul_tuple((255, 255, 255), halite / max_value, integer=True),
                    pos2rect(position)
                )

    def draw_ships(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for ship in player.get_ships():
                # noinspection PyTypeChecker
                p = ship.position * CELL_SIZE + (CELL_SIZE // 2, CELL_SIZE // 2)
                pygame.draw.circle(
                    self.screen,
                    color,
                    (p.x, p.y),
                    round(CELL_SIZE / 2.5)
                )
                self.screen.blit(self.font.render(str(ship.id), 0, GREY), (p.x, p.y))
                if ship.halite_amount:
                    pygame.draw.circle(
                        self.screen,
                        WHITE,
                        (p.x, p.y),
                        round(CELL_SIZE / 2.5 * (ship.halite_amount / constants.MAX_HALITE))
                    )
                if ship.target:
                    pygame.draw.lines(
                        self.screen,
                        mul_tuple(color, .7, integer=True),
                        False,
                        (
                            tuple(ship.position * CELL_SIZE + CELL_SIZE // 2),
                            tuple(ship.target * CELL_SIZE + CELL_SIZE // 2)
                        ),
                        1
                    )

    def draw_bases(self):
        for n, player in self.bot.game.players.items():
            color = PLAYERS[n]
            for base in (player.shipyard,):
                pygame.draw.rect(
                    self.screen,
                    color,
                    pos2rect(base.position),
                    1
                )

    def update_display_size(self):
        self.screen = display.set_mode(self.win_size, pygame.DOUBLEBUF | pygame.RESIZABLE)
        display.flip()

    def key_handler(self, e, m: int, up=False):
        if not up:
            logging.debug(f"Press {e.unicode}")
            if m & pygame.KMOD_ALT and e.key == pygame.K_F4:
                raise SystemExit("QUIT")
            elif e.unicode == ',':  # '<'
                self.speed_up /= 2
            elif e.unicode == '.':  # '>'
                self.speed_up *= 2
            elif e.key == pygame.K_SPACE:
                self.pause = not self.pause

    def mouse_handler(self, e):
        map_pos = tuple(map(int, mul_tuple(e.pos, 1 / CELL_SIZE)))
        cell = self.bot.game.map[map_pos]
        logging.info(f"Cell: pos={cell.position} halite={cell.halite_amount}")
        if cell.ship:
            ship = cell.ship
            logging.info(f"Ship: id={ship.id} halite={ship.halite_amount}")
            if ship.owner == self.bot.game.me.id:
                self.selected = ship
        else:
            self.selected = None

    @property
    def info(self):
        return f"{self.bot.game.turn_number}/{constants.MAX_TURNS} X{self.speed_up:.0f} |" \
               f" G: {self.bot.game.players[0].halite_amount:>5d} | " \
               f" R: {self.bot.game.players[1].halite_amount:>5d}"
예제 #26
0
class Scoreboard:
    def __init__(self, ai_settings: Settings, screen: SurfaceType,
                 stats: GameStats):
        self._screen = screen
        self._screen_rect = screen.get_rect()
        self._ai_settings = ai_settings
        self._stats = stats

        self._text_color = 90, 200, 50
        self._font = SysFont(None, 48)

        self.prep_score()
        self.prep_high_score()
        self.prep_level()
        self.prep_ships()

    def prep_score(self):
        rounded_score = int(round(self._stats.score, -1))
        score_str = "{:,}".format(rounded_score)

        self.score_image = self._font.render(score_str, True, self._text_color,
                                             self._ai_settings.bg_color)

        self._score_rect = self.score_image.get_rect()
        self._score_rect.right = self._screen_rect.right - 20
        self._score_rect.top = 20

    def prep_high_score(self):
        high_score = int(round(self._stats.high_score, -1))
        high_score_str = "{:,}".format(high_score)
        self._high_score_image = self._font.render(high_score_str, True,
                                                   self._text_color,
                                                   self._ai_settings.bg_color)

        # Center high score at the top of the screen
        self._high_score_rect = self._high_score_image.get_rect()
        self._high_score_rect.centerx = self._screen_rect.centerx
        self._high_score_rect.top = self._score_rect.top

    def prep_level(self):
        self._level_image = self._font.render(str(self._stats.level), True,
                                              self._text_color,
                                              self._ai_settings.bg_color)

        self._level_rect = self._level_image.get_rect()
        self._level_rect.right = self._score_rect.right
        self._level_rect.top = self._score_rect.bottom + 10

    def prep_ships(self):
        self.ships = Group()

        for ship_number in range(self._stats.ships_left):
            ship = Ship(self._ai_settings, self._screen)
            ship.rect.x = 10 + ship_number * ship.rect.width
            ship.rect.y = 10
            self.ships.add(ship)

    def show_score(self):
        self._screen.blit(self.score_image, self._score_rect)
        self._screen.blit(self._high_score_image, self._high_score_rect)
        self._screen.blit(self._level_image, self._level_rect)
        self.ships.draw(self._screen)
예제 #27
0
class Scoreboard:
    """Initialize sb"""
    def __init__(self, ai_settings, screen, stats):
        self.screen = screen
        self.screen_rect = screen.get_rect()
        self.ai_settings = ai_settings
        self.stats = stats

        # Font
        self.text_color = (238, 232, 170)
        self.font = SysFont(None, 48)

        # set score image
        self.score_image = None
        self.score_rect = None
        # set hs image
        self.hs_image = None
        self.hs_rect = None

        # level image
        self.level_image = None
        self.level_rect = None

        # ships left
        self.ships = None

        # initialize score, high score, level, ships
        self.prep_score()
        self.prep_hs()
        self.prep_level()
        self.prep_ships()

    def prep_score(self):
        """rendering score as image"""
        rounded_score = int(round(self.stats.score, -1))
        score_str = 'Score: {:,}'.format(rounded_score)
        self.score_image = self.font.render(score_str, True, self.text_color,
                                            self.ai_settings.bg_color)
        # Display the score in the top right corner
        self.score_rect = self.score_image.get_rect()
        self.score_rect.right = self.screen_rect.right - 20
        self.score_rect.top = 20

    def prep_hs(self):
        """Turn high score into a rendered image"""
        high_score = int(round(self.stats.hs, -1))
        high_score_str = 'High Score: {:,}'.format(high_score)
        self.hs_image = self.font.render(high_score_str, True, self.text_color,
                                         self.ai_settings.bg_color)
        # Center high score at top of the screen
        self.hs_rect = self.hs_image.get_rect()
        self.hs_rect.centerx = self.screen_rect.centerx
        self.hs_rect.top = self.score_rect.top

    def prep_level(self):
        """rendering level as image"""
        self.level_image = self.font.render('Level: ' + str(self.stats.level),
                                            True, self.text_color,
                                            self.ai_settings.bg_color)
        # Position level below score
        self.level_rect = self.level_image.get_rect()
        self.level_rect.right = self.score_rect.right
        self.level_rect.top = self.score_rect.bottom + 10

    def prep_ships(self):
        """display ship"""
        self.ships = Group()
        for ship_number in range(self.stats.ships_left):
            ship = Ship(self.ai_settings, self.screen)
            ship.rect.x = 10 + ship_number * (ship.rect.width + 5)
            ship.rect.y = 10
            self.ships.add(ship)

    def show_score(self):
        """display score"""
        self.screen.blit(self.score_image, self.score_rect)
        self.screen.blit(self.hs_image, self.hs_rect)
        self.screen.blit(self.level_image, self.level_rect)
        # display ships
        self.ships.draw(self.screen)
예제 #28
0
class Ghosts(Sprite):
    def __init__(self, screen, color):
        super(Ghosts, self).__init__()
        self.color = color # ghost type
        self.screen = screen
        self.height = 35
        self.width = 35

        Cyan_SS = SpriteSheet.spritesheet('images/Cyan/CyanSpriteSheet.png')
        Orange_SS = SpriteSheet.spritesheet('images/Orange/OrangeSpriteSheet.png')
        Pink_SS = SpriteSheet.spritesheet('images/Pink/PinkSpriteSheet.png')
        Red_SS = SpriteSheet.spritesheet('images/Red/RedSpriteSheet.png')
        Freight_ss = SpriteSheet.spritesheet('images/PowerPelletSpriteSheet.png')
        Eyes_ss = SpriteSheet.spritesheet('images/EyesSpriteSheet.png')

        self.left_image = []
        self.right_image = []
        self.up_image = []
        self.down_image = []
        self.freight = [Freight_ss.image_at((0,0,32,38)),
                        Freight_ss.image_at((0,38,32,38)),
                        Freight_ss.image_at((0,76,32,38)),
                        Freight_ss.image_at((0,114,32,38))]
        self.eyes = [Eyes_ss.image_at((0,0,23,12)),
                     Eyes_ss.image_at((0,12,23,12)),
                     Eyes_ss.image_at((0,24,23,12)),
                     Eyes_ss.image_at((0,36,23,12))]

        if color == "red":
            self.left_image = [Red_SS.image_at((0,76,32,38)),
                               Red_SS.image_at((0,228, 32,38))]
            self.right_image = [Red_SS.image_at((0, 190, 32, 38)),
                               Red_SS.image_at((0, 266, 32, 38))]
            self.up_image = [Red_SS.image_at((0, 0, 32, 38)),
                               Red_SS.image_at((0, 114, 32, 38))]
            self.down_image = [Red_SS.image_at((0, 38, 32, 38)),
                               Red_SS.image_at((0, 152, 32, 38))]
        elif color == "cyan":
            self.left_image = [Cyan_SS.image_at((0, 76, 32, 38)),
                               Cyan_SS.image_at((0, 228, 32, 38))]
            self.right_image = [Cyan_SS.image_at((0, 190, 32, 38)),
                                Cyan_SS.image_at((0, 266, 32, 38))]
            self.up_image = [Cyan_SS.image_at((0, 0, 32, 38)),
                             Cyan_SS.image_at((0, 114, 32, 38))]
            self.down_image = [Cyan_SS.image_at((0, 38, 32, 38)),
                               Cyan_SS.image_at((0, 152, 32, 38))]
        elif color == "orange":
            self.left_image = [Orange_SS.image_at((0, 76, 32, 38)),
                               Orange_SS.image_at((0, 228, 32, 38))]
            self.right_image = [Orange_SS.image_at((0, 190, 32, 38)),
                                Orange_SS.image_at((0, 266, 32, 38))]
            self.up_image = [Orange_SS.image_at((0, 0, 32, 38)),
                             Orange_SS.image_at((0, 114, 32, 38))]
            self.down_image = [Orange_SS.image_at((0, 38, 32, 38)),
                               Orange_SS.image_at((0, 152, 32, 38))]
        elif color == "pink":
            self.left_image = [Pink_SS.image_at((0, 76, 32, 38)),
                               Pink_SS.image_at((0, 228, 32, 38))]
            self.right_image = [Pink_SS.image_at((0, 190, 32, 38)),
                                Pink_SS.image_at((0, 266, 32, 38))]
            self.up_image = [Pink_SS.image_at((0, 0, 32, 38)),
                             Pink_SS.image_at((0, 114, 32, 38))]
            self.down_image = [Pink_SS.image_at((0, 38, 32, 38)),
                               Pink_SS.image_at((0, 152, 32, 38))]

        self.rect = pygame.transform.scale(self.up_image[0], (self.height, self.width)).get_rect()
        self.rect.x, self.rect.y = 330, 315
        self.rect.left -= self.rect.width
        self.rect.top -= self.rect.height
        self.image = [None, None] #image placeholder
        self.image = self.up_image #start with ghost looking up

        self.moving_up = True #Start with the ghosts going up
        self.moving_down = False
        self.moving_left = False
        self.moving_right = False

        self.last_move = "up/down"
        self.last_intersection = None

        self.speed = 1

        # ghosts are blue
        self.afraid = False

        # ghosts are eyes
        self.DEAD = False

        self.value = 0
        self.font = SysFont(None, 16, italic=True)
        self.score_image = self.font.render(str(self.value), True, (255, 255, 255), (0, 0, 0))

        # how long to show score
        self.frames = 0

    def update(self):
        if self.moving_left == True:
            self.rect.x -= self.speed
            self.image = self.left_image
        elif self.moving_right == True:
            self.rect.x += self.speed
            self.image = self.right_image
        elif self.moving_up == True:
            self.rect.y -= self.speed
            self.image = self.up_image
        elif self.moving_down == True:
            self.rect.y += self.speed
            self.image = self.down_image

    def blitghosts(self):
        if(self.DEAD):
            if(self.moving_left):
                self.screen.blit(self.eyes[2], self.rect)
            elif (self.moving_right):
                self.screen.blit(self.eyes[3], self.rect)
            elif (self.moving_up):
                self.screen.blit(self.eyes[1], self.rect)
            elif (self.moving_down):
                self.screen.blit(self.eyes[0], self.rect)
        elif(self.afraid):
            if(self.frames <= 720):
                if pygame.time.get_ticks() % 200 <= 50:
                    self.screen.blit(self.freight[2], self.rect)
                elif pygame.time.get_ticks() % 200 <= 100:
                    self.screen.blit(self.freight[3], self.rect)
                elif pygame.time.get_ticks() % 200 <= 150:
                    self.screen.blit(self.freight[2], self.rect)
                else:
                    self.screen.blit(self.freight[3], self.rect)
            elif(self.frames <= 960):
                if pygame.time.get_ticks() % 200 <= 50:
                    self.screen.blit(self.freight[0], self.rect)
                elif pygame.time.get_ticks() % 200 <= 100:
                    self.screen.blit(self.freight[1], self.rect)
                elif pygame.time.get_ticks() % 200 <= 150:
                    self.screen.blit(self.freight[2], self.rect)
                else:
                    self.screen.blit(self.freight[3], self.rect)
        else:
            if pygame.time.get_ticks() % 200 <= 50:
                self.screen.blit(self.image[0], self.rect)
            elif pygame.time.get_ticks() % 200 <= 100:
                self.screen.blit(self.image[1], self.rect)
            elif pygame.time.get_ticks() % 200 <= 150:
                self.screen.blit(self.image[0], self.rect)
            else:
                self.screen.blit(self.image[1], self.rect)
        if(self.frames <= 60 and self.DEAD):
            self.screen.blit(self.score_image, self.rect)
            self.frames += 1
        if(self.frames <= 960 and self.afraid):
            self.frames += 1
        elif(self.frames > 960 and self.afraid):
            self.afraid = False
            self.frames = 0

    def resetPosition(self):
        self.moving_up = True  # Start with the ghosts going up
        self.moving_down = False
        self.moving_left = False
        self.moving_right = False
        self.rect.x, self.rect.y = 300, 300

        self.afraid = False
        self.DEAD = False

    def playAfraidSound(self):
        mixer.Channel(1).play(pygame.mixer.Sound('sounds/ghosts_ambient.wav'))

    def playDeathSound(self):
        mixer.Channel(1).play(pygame.mixer.Sound('sounds/ghost_eaten.wav'))

    def playRetreatSound(self):
        mixer.Channel(1).play(pygame.mixer.Sound('sounds/ghosts_ambient_scared1.wav'))