예제 #1
0
    def update(self, dt, enemy_bullets, ship):
        """ Update movement, animation and shooting

        :param dt: time between frames
        :param enemy_bullets: Sprite group
        :param ship: Sprite - player
        :return: Nothing
        """
        # Stage 1
        if self.stage == 1:
            if self.animate(self.animation1, self.animation1_start, dt):
                if self.health < 2000:
                    self.stage = 2
                    self.init_animation(self.animation2_start)
                    self.calculate_movement(self.animation2)

            # Shooting
            if self.animation_frame == 5:
                if time() > self.shoot_timer1:
                    position = [
                        self.rect.left + 34 + (12 * self.canon),
                        self.rect.centery + 50
                    ]
                    target = [ship.rect.centerx, ship.rect.centery]
                    enemy_bullets.add(EnemyBullet(position, 0.15, 2, target))
                    SFX().blaster2.play()

                    self.canon += 1
                    if self.canon > 4:
                        self.canon = 1
                        self.shoot_timer1 = time() + 1
                    else:
                        self.shoot_timer1 = time() + 0.25

        # Stage 2
        elif self.stage == 2:
            self.animate(self.animation2, self.animation2_start, dt)

            # Shooting
            if self.animation_frame == 5:
                if time() > self.shoot_timer1:
                    enemy_bullets.add(
                        EnemyBullet(
                            [self.rect.left + 46, self.rect.centery + 50],
                            0.15, 2, -30))
                    enemy_bullets.add(
                        EnemyBullet(
                            [self.rect.left + 58, self.rect.centery + 50],
                            0.15, 2, -10))
                    enemy_bullets.add(
                        EnemyBullet(
                            [self.rect.left + 70, self.rect.centery + 50],
                            0.15, 2, 10))
                    enemy_bullets.add(
                        EnemyBullet(
                            [self.rect.left + 82, self.rect.centery + 50],
                            0.15, 2, 30))
                    SFX().blaster2.play()
                    self.shoot_timer1 = time() + 0.8
예제 #2
0
    def check_collisions(self):
        # Check collisions between bullets and enemies, bullets get removed automatically
        dict = pygame.sprite.groupcollide(self.level.enemies, self.bullets,
                                          False, True,
                                          pygame.sprite.collide_mask)
        for enemy in dict.keys():
            # Create effects on impacting bullets
            for bullet in dict[enemy]:
                self.effects.add(
                    hit.Hit([bullet.rect.centerx, bullet.rect.top]))

            enemy.hit()
            if enemy.health <= 0:
                if enemy.pickup:
                    self.pickups.add(
                        enemy.pickup([enemy.rect.centerx, enemy.rect.centery]))
                self.effects.add(
                    hit.Explosion([enemy.rect.centerx, enemy.rect.centery]))
                self.status.score += enemy.reward
                self.level.enemies.remove(enemy)
                SFX().boom1.play()

        # check collisions between player and enemy bullets
        dict = pygame.sprite.spritecollide(self.ship, self.enemy_bullets, True,
                                           pygame.sprite.collide_mask)
        for bullet in dict:
            self.effects.add(hit.Hit([bullet.rect.centerx,
                                      bullet.rect.bottom]))
            self.ship.hit()
            self.status.lives -= 1
            SFX().boom1.play()

        # Check collisions between player and enemies
        list = pygame.sprite.spritecollide(self.ship, self.level.enemies,
                                           False, pygame.sprite.collide_mask)
        for enemy in list:
            self.effects.add(
                hit.Explosion([enemy.rect.centerx, enemy.rect.centery]))
            self.ship.hit()
            self.level.enemies.remove(enemy)
            self.status.lives -= 1
            SFX().boom1.play()

        # Check collisions between player and pickups
        list = pygame.sprite.spritecollide(self.ship, self.pickups, False)
        for pickup in list:
            pickup.pickup(self.status)
예제 #3
0
파일: avatar.py 프로젝트: Sk00g/arena
 def _generate_blood_sfx(self):
     start = random.randrange(4) * 6
     angle = random.randrange(0, 180)
     return SFX('assets/sfx/bloodSheet.png', (12, 2), (64, 64),
                self.sprite.get_position() + BLOOD_OFFSET,
                start,
                start + 6,
                rotation=angle)
예제 #4
0
 def fire_bullet(self):
     # Set shooting flag
     self.ship.shooting = True
     # Set shooting timer
     self.ship.shooting_timer = time() + 0.1
     # Add bullet
     if len(self.bullets) < CFG().bullet_count:
         self.bullets.add(Bullet(self.ship))
         SFX().blaster1.play()
예제 #5
0
파일: battle_scene.py 프로젝트: Sk00g/arena
    def _select_avatar(self, selection):
        active_units = self.left_units if self.active == "left" else self.right_units

        if self.current_phase == BattlePhase.ORDER:
            if selection in active_units:
                self._clear_selection()

                self.selected_avatar = selection
                selection.cell.set_fill_color(CellColor.ORANGE)
                selection.cell.set_border_color(CellColor.ORANGE_HIGHLIGHT)
                self.selection_arrow.position = (selection.sprite.get_center() + ARROW_OFFSET)
                self._update_panels()

        elif self.current_phase == BattlePhase.TARGET and self.selected_action == BattleAction.ATTACK:
            if not selection in active_units:
                self.unit_orders[self.selected_avatar] = { "order": BattleAction.ATTACK, "target": selection }
                x, y = selection.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/retaliate.png', (16, 1), (64, 64), (x - 10, y - 50), 0, 15, frame_speed=80)
                self.current_phase = BattlePhase.ORDER
                self._select_action(BattleAction.NEXT_UNIT)

        elif self.current_phase == BattlePhase.TARGET and self.selected_action == BattleAction.DEFEND:
            # Units that are defended by an ally can't also defend an ally
            if self._avatar_is_defended_by_ally(self.selected_avatar) and selection != self.selected_avatar:
                # error message
                return

            # Each unit can be only be defended by one ally at a time
            if self._avatar_is_defended_by_ally(selection):
                # error message
                return

            # Cannot defend an ally that is also defending a different ally
            if selection in self.unit_orders and self.unit_orders[selection]['order'] == BattleAction.DEFEND:
                # error message
                return

            if selection in active_units:
                self.unit_orders[self.selected_avatar] = {"order": BattleAction.DEFEND, "target": selection}
                x, y = selection.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/shield.png', (10, 1), (64, 64), (x - 10, y - 50), 0, 9, frame_speed=80)
                self.current_phase = BattlePhase.ORDER
                self._select_action(BattleAction.NEXT_UNIT)
예제 #6
0
파일: battle_scene.py 프로젝트: Sk00g/arena
    def _select_action(self, action):
        active_units = self.left_units if self.active == "left" else self.right_units

        if self.current_phase == BattlePhase.ORDER:
            if action == BattleAction.ATTACK:
                self.current_phase = BattlePhase.TARGET
                FloatingText.create_new(FloatingText("attack", self.selected_avatar.sprite.get_center(), [255] * 4))
                self.selected_action = BattleAction.ATTACK
                self._update_panels()
            elif action == BattleAction.DEFEND:
                self.current_phase = BattlePhase.TARGET
                FloatingText.create_new(FloatingText("defend", self.selected_avatar.sprite.get_center(), [255] * 4))
                self.selected_action = BattleAction.DEFEND
                self._update_panels()
            elif action == BattleAction.NEXT_UNIT:
                empty_unit = False
                for unit in active_units:
                    if not unit in self.unit_orders:
                        empty_unit = True
                if not empty_unit:
                    self._end_turn()
                    return

                if not self.selected_avatar:
                    self._select_avatar(active_units[0])
                else:
                    index = active_units.index(self.selected_avatar)
                    index += 1 if index < (len(active_units) - 1) else -index
                    self._select_avatar(active_units[index])
            elif action == BattleAction.GUARD:
                FloatingText.create_new(FloatingText("guard", self.selected_avatar.sprite.get_center(), [255] * 4))
                x, y = self.selected_avatar.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/shield.png', (10, 1), (64, 64), (x - 10, y - 50), 0, 9,
                                      frame_speed=80)
                self.unit_orders[self.selected_avatar] = { "order": BattleAction.GUARD, "target": None }
                self._select_action(BattleAction.NEXT_UNIT)

        elif self.current_phase == BattlePhase.TARGET:
            if action == BattleAction.CANCEL:
                self.current_phase = BattlePhase.ORDER
                self._update_panels()
예제 #7
0
파일: battle_scene.py 프로젝트: Sk00g/arena
    def __init__(self):
        GameScene.__init__(self)

        self.background = suie.Image(asset_manager.load_image('wcBattleBackground.png'), (0, 0))
        self.selection_arrow = SFX('assets/ui/rotatingArrow.png', (7, 2), (40, 40), (0, 0), 0, 13, True, frame_speed=80)
        self.action_sfx = None

        self.grid = Grid(Vector(suie.SCREEN_WIDTH // 2 - 168, 150), (7, 9))

        self.left_units = []
        self.right_units = []
        self.dead_units = []
        for i in range(3):
            self.left_units.append(factory.generate_avatar('footman', 12 + i))
            self.right_units.append(factory.generate_avatar('archer', 14 + i))

        self.executor = BattleExecutor(self.left_units, self.right_units, self.grid)

        self._arrange_units()

        self.current_phase = BattlePhase.ORDER
        self.active = "left"
        self.turn_count = 0

        """ Save unit orders in this dict. Ex/
        Avatar: { order: BattleAction.ATTACK, target: Avatar2 },
        Avatar2: { order: BattleAction.DEFEND, target: Avatar3 },  etc...
        """
        self.unit_orders = {}

        self.avatar_icons = []
        self.action_icons = []

        self.selected_avatar = None
        self.hovered_avatar = None
        self.selected_action = None

        self._setup_panels()
        self._start_turn('left')
예제 #8
0
    def update(self, dt, enemy_bullets, ship, status):
        """
        Updated level, background and enemies
        :param dt:
        :param enemy_bullets:
        :param ship:
        :return: True if the game should be running, False if not
        """
        if not SFX().is_music_playing():
            SFX().music_play(self.music)

        # If at the start of level show story
        if self.starting:
            if self.story.update('start'):
                return False
            # No more story - start level
            self.show_name = True
            self.timer = time() + 3
            self.starting = False
            self.enemy_hold = True

        # Show level name, hold enemies
        elif self.show_name:
            if self.timer > time():
                self.enemy_hold = True
            else:
                self.show_name = False

        # No more level + no more enemies
        if len(self.layout) == 0 and len(self.enemies) == 0:
            # Show end story
            if self.story.update('end'):
                return False

            # End level
            self.ending = True
            pygame.mixer.music.stop()
            return True

        # Background update
        self.background.update(dt, self.enemy_hold)

        # Enemy spawning and level progression
        if self.enemy_hold:
            if len(self.enemies) == 0:
                self.enemy_hold = False
        else:
            if self.timer < time() and len(self.layout) != 0:
                self.timer = time() + CFG().spawn_speed

                line = self.layout.pop(-1)
                position = 0
                for char in line:
                    position += 1
                    # If there is enemy calculate it's x position
                    if char != '-':
                        spacing = CFG().int_screen_width / CFG().level_width
                        pos_x = spacing * position - spacing / 2
                    # Stop spawning until all enemies are gone
                    if char == '_':
                        self.enemy_hold = True
                        break

                    if char == 'a':
                        self.enemies.add(asteroid.Asteroid(pos_x))

                    elif char == 's':
                        self.enemies.add(shifter.Shifter(pos_x))

                    elif char == '1':
                        self.enemies.add(boss.Boss1(status))

        # Enemy update
        self.enemies.update(dt, enemy_bullets, ship)

        # Get rid of enemies out of screen
        for sprite in self.enemies:
            if sprite.rect.top > CFG().int_screen_height:
                self.enemies.remove(sprite)

        return True
예제 #9
0
파일: battle_scene.py 프로젝트: Sk00g/arena
class BattleScene(GameScene):
    def __init__(self):
        GameScene.__init__(self)

        self.background = suie.Image(asset_manager.load_image('wcBattleBackground.png'), (0, 0))
        self.selection_arrow = SFX('assets/ui/rotatingArrow.png', (7, 2), (40, 40), (0, 0), 0, 13, True, frame_speed=80)
        self.action_sfx = None

        self.grid = Grid(Vector(suie.SCREEN_WIDTH // 2 - 168, 150), (7, 9))

        self.left_units = []
        self.right_units = []
        self.dead_units = []
        for i in range(3):
            self.left_units.append(factory.generate_avatar('footman', 12 + i))
            self.right_units.append(factory.generate_avatar('archer', 14 + i))

        self.executor = BattleExecutor(self.left_units, self.right_units, self.grid)

        self._arrange_units()

        self.current_phase = BattlePhase.ORDER
        self.active = "left"
        self.turn_count = 0

        """ Save unit orders in this dict. Ex/
        Avatar: { order: BattleAction.ATTACK, target: Avatar2 },
        Avatar2: { order: BattleAction.DEFEND, target: Avatar3 },  etc...
        """
        self.unit_orders = {}

        self.avatar_icons = []
        self.action_icons = []

        self.selected_avatar = None
        self.hovered_avatar = None
        self.selected_action = None

        self._setup_panels()
        self._start_turn('left')

        # self.grid.debug_fill()

    def _avatar_is_defended_by_ally(self, avatar):
        for ordered in self.unit_orders:
            if ordered == avatar:
                continue
            order = self.unit_orders[ordered]
            if order['order'] == BattleAction.DEFEND and order['target'] == avatar:
                return True

        return False

    def _avatar_has_order(self, avatar):
        return avatar in self.unit_orders

    def _start_turn(self, who):
        self.active = who
        if who == "left":
            self.turn_count += 1

        self.current_phase = BattlePhase.ORDER
        self.selected_avatar = None
        self.selected_action = None

        for unit in self.left_units + self.right_units:
            unit.cell.set_fill_color(CellColor.SHADOW)
            unit.cell.set_border_color(None)

        self._update_panels()

    def _end_execution_phase(self):
        self.unit_orders.clear()

        for unit in self.left_units:
            if not unit.is_alive():
                self.left_units.remove(unit)
                self.dead_units.append(unit)
        for unit in self.right_units:
            if not unit.is_alive():
                self.right_units.remove(unit)
                self.dead_units.append(unit)

        # Check for battle finish here
        self._start_turn('left')

    def _end_turn(self):
        if self.active == 'left':
            self._start_turn('right')
        else:
            self.selected_avatar = None
            self.current_phase = BattlePhase.EXECUTION
            self.executor.execute(self.unit_orders, self._end_execution_phase, self.turn_count)
            self._update_panels()

    def _lineup_units(self, unit_list, xcoord: int):
        size = len(unit_list)
        if size == 1:
            unit_list[0].set_cell(self.grid[xcoord, 3])
        elif size == 2:
            unit_list[0].set_cell(self.grid[xcoord, 2])
            unit_list[1].set_cell(self.grid[xcoord, 4])
        elif size == 3:
            unit_list[0].set_cell(self.grid[xcoord, 1])
            unit_list[1].set_cell(self.grid[xcoord, 3])
            unit_list[2].set_cell(self.grid[xcoord, 5])
        elif size == 4:
            unit_list[0].set_cell(self.grid[xcoord, 2])
            unit_list[1].set_cell(self.grid[xcoord, 3])
            unit_list[2].set_cell(self.grid[xcoord, 4])
            unit_list[3].set_cell(self.grid[xcoord, 5])
        elif size == 5:
            for i in range(5):
                unit_list[i].set_cell(self.grid[xcoord, i + 2])
        elif size == 6:
            for i in range(6):
                unit_list[i].set_cell(self.grid[xcoord, i + 1])

    def _arrange_units(self):
        for unit in self.left_units:
            unit.sprite.set_facing(Facing.RIGHT)
        for unit in self.right_units:
            unit.sprite.set_facing(Facing.LEFT)

        self._lineup_units(self.left_units, 0)
        self._lineup_units(self.right_units, 6)

    def _select_action(self, action):
        active_units = self.left_units if self.active == "left" else self.right_units

        if self.current_phase == BattlePhase.ORDER:
            if action == BattleAction.ATTACK:
                self.current_phase = BattlePhase.TARGET
                FloatingText.create_new(FloatingText("attack", self.selected_avatar.sprite.get_center(), [255] * 4))
                self.selected_action = BattleAction.ATTACK
                self._update_panels()
            elif action == BattleAction.DEFEND:
                self.current_phase = BattlePhase.TARGET
                FloatingText.create_new(FloatingText("defend", self.selected_avatar.sprite.get_center(), [255] * 4))
                self.selected_action = BattleAction.DEFEND
                self._update_panels()
            elif action == BattleAction.NEXT_UNIT:
                empty_unit = False
                for unit in active_units:
                    if not unit in self.unit_orders:
                        empty_unit = True
                if not empty_unit:
                    self._end_turn()
                    return

                if not self.selected_avatar:
                    self._select_avatar(active_units[0])
                else:
                    index = active_units.index(self.selected_avatar)
                    index += 1 if index < (len(active_units) - 1) else -index
                    self._select_avatar(active_units[index])
            elif action == BattleAction.GUARD:
                FloatingText.create_new(FloatingText("guard", self.selected_avatar.sprite.get_center(), [255] * 4))
                x, y = self.selected_avatar.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/shield.png', (10, 1), (64, 64), (x - 10, y - 50), 0, 9,
                                      frame_speed=80)
                self.unit_orders[self.selected_avatar] = { "order": BattleAction.GUARD, "target": None }
                self._select_action(BattleAction.NEXT_UNIT)

        elif self.current_phase == BattlePhase.TARGET:
            if action == BattleAction.CANCEL:
                self.current_phase = BattlePhase.ORDER
                self._update_panels()

    def _hover_avatar(self, avatar, flag: bool):
        if flag and not self.hovered_avatar:
            self.hovered_avatar = avatar

            if avatar == self.selected_avatar:
                return

            active_units = self.left_units if self.active == "left" else self.right_units

            if self.current_phase == BattlePhase.ORDER:
                color = CellColor.BLUE if avatar in active_units else CellColor.RED
                bcolor = CellColor.BLUE_HIGHLIGHT if avatar in active_units else CellColor.SHADOW_HIGHLIGHT
            elif self.current_phase == BattlePhase.TARGET:
                color = CellColor.GREEN if avatar in active_units else CellColor.RED
                bcolor = CellColor.GREEN_HIGHLIGHT if avatar in active_units else CellColor.RED_HIGHLIGHT
            elif self.current_phase in [BattlePhase.WAITING, BattlePhase.EXECUTION]:
                color, bcolor = CellColor.SHADOW, CellColor.SHADOW_HIGHLIGHT

            avatar.cell.set_fill_color(color)
            avatar.cell.set_border_color(bcolor)
        elif not flag:
            self.hovered_avatar = None

            if avatar == self.selected_avatar:
                return

            avatar.cell.set_fill_color(CellColor.SHADOW)
            avatar.cell.set_border_color(None)

    def _clear_selection(self):
        if self.selected_avatar:
            self.selected_avatar.cell.set_fill_color(CellColor.SHADOW)
            self.selected_avatar.cell.set_border_color(None)

        self.selected_avatar = None
        self._update_panels()

    def _select_avatar(self, selection):
        active_units = self.left_units if self.active == "left" else self.right_units

        if self.current_phase == BattlePhase.ORDER:
            if selection in active_units:
                self._clear_selection()

                self.selected_avatar = selection
                selection.cell.set_fill_color(CellColor.ORANGE)
                selection.cell.set_border_color(CellColor.ORANGE_HIGHLIGHT)
                self.selection_arrow.position = (selection.sprite.get_center() + ARROW_OFFSET)
                self._update_panels()

        elif self.current_phase == BattlePhase.TARGET and self.selected_action == BattleAction.ATTACK:
            if not selection in active_units:
                self.unit_orders[self.selected_avatar] = { "order": BattleAction.ATTACK, "target": selection }
                x, y = selection.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/retaliate.png', (16, 1), (64, 64), (x - 10, y - 50), 0, 15, frame_speed=80)
                self.current_phase = BattlePhase.ORDER
                self._select_action(BattleAction.NEXT_UNIT)

        elif self.current_phase == BattlePhase.TARGET and self.selected_action == BattleAction.DEFEND:
            # Units that are defended by an ally can't also defend an ally
            if self._avatar_is_defended_by_ally(self.selected_avatar) and selection != self.selected_avatar:
                # error message
                return

            # Each unit can be only be defended by one ally at a time
            if self._avatar_is_defended_by_ally(selection):
                # error message
                return

            # Cannot defend an ally that is also defending a different ally
            if selection in self.unit_orders and self.unit_orders[selection]['order'] == BattleAction.DEFEND:
                # error message
                return

            if selection in active_units:
                self.unit_orders[self.selected_avatar] = {"order": BattleAction.DEFEND, "target": selection}
                x, y = selection.sprite.get_center()
                self.action_sfx = SFX('assets/sfx/shield.png', (10, 1), (64, 64), (x - 10, y - 50), 0, 9, frame_speed=80)
                self.current_phase = BattlePhase.ORDER
                self._select_action(BattleAction.NEXT_UNIT)

    def _handle_events(self, event_list):
        for event in event_list:
            if event.type == KEYDOWN:
                if event.key == K_BACKSPACE:
                    if self.current_phase == BattlePhase.ORDER:
                        self._clear_selection()
                    elif self.current_phase == BattlePhase.TARGET:
                        self._select_action(BattleAction.CANCEL)
                elif event.key == K_TAB:
                    if self.current_phase == BattlePhase.ORDER:
                        self._select_action(BattleAction.NEXT_UNIT)

            elif event.type == MOUSEMOTION:
                x, y = pygame.mouse.get_pos()
                if self.hovered_avatar and not self.hovered_avatar.cell.get_rect().collidepoint(x, y):
                    self._hover_avatar(self.hovered_avatar, False)
                for unit in self.left_units + self.right_units:
                    if unit.cell.get_rect().collidepoint(x, y):
                        self._hover_avatar(unit, True)

            elif event.type == MOUSEBUTTONDOWN:
                for unit in self.left_units + self.right_units:
                    x, y = pygame.mouse.get_pos()
                    if unit.cell.get_rect().collidepoint(x, y):
                        self._select_avatar(unit)

    def update(self, event_list, elapsed):
        for unit in self.left_units:
            unit.update(elapsed)
        for unit in self.right_units:
            unit.update(elapsed)

        FloatingText.update_all(elapsed)
        self.hud_panel.update(event_list)

        if self.current_phase != BattlePhase.EXECUTION:
            self._handle_events(event_list)

        if self.current_phase == BattlePhase.EXECUTION:
            self.executor.update(event_list, elapsed)

    def draw(self, screen):
        self.background.draw(screen)
        self.grid.draw(screen)

        for unit in self.dead_units:
            unit.draw(screen)

        for unit in self.left_units + self.right_units:
            unit.draw(screen)

        if self.selected_avatar:
            self.selection_arrow.draw(screen)
        if self.action_sfx:
            self.action_sfx.draw(screen)

        FloatingText.draw_all(screen)
        self.hud_panel.draw(screen)

        if self.current_phase == BattlePhase.EXECUTION:
            self.executor.draw(screen)

    def cleanup(self):
        pass

    # --- HUD FUNCTIONALITY ---
    def _letter_from_order(self, order):
        if order == BattleAction.GUARD:
            return "G"
        elif order == BattleAction.DEFEND:
            return "D"
        elif order == BattleAction.ATTACK:
            return "A"

    def _update_panels(self):
        active_group = self.left_units if self.active == 'left' else self.right_units

        self.info_label.set_text("ACTIVE: %s | PHASE: %s | TURN #: %s" % (self.active, self.current_phase, self.turn_count))

        for icon in self.avatar_icons:
            self.lineup_panel.remove_child(icon)
        self.avatar_icons.clear()

        if self.current_phase == BattlePhase.ORDER:
            for i in range(len(active_group)):
                icon = suie.AvatarIcon((i * (suie.AvatarIcon.WIDTH + 2), 0), active_group[i])
                if active_group[i] == self.selected_avatar:
                    icon.highlight(True)
                if active_group[i] in self.unit_orders:
                    icon.set_action(self._letter_from_order(self.unit_orders[active_group[i]]["order"]))
                self.avatar_icons.append(icon)
                self.lineup_panel.add_child(icon)

        for icon in self.action_icons:
            self.action_panel.remove_child(icon)
        self.action_icons.clear()

        if self.current_phase == BattlePhase.ORDER and self.selected_avatar:
            self.action_icons.append(suie.ActionIcon((0, 0),
                                                     lambda: self._select_action(BattleAction.ATTACK),
                                                     "a", 116))
            self.action_icons.append(suie.ActionIcon((suie.ActionIcon.WIDTH + 2, 0),
                                                     lambda: self._select_action(BattleAction.DEFEND),
                                                     "d", 164))
            self.action_icons.append(suie.ActionIcon(((suie.ActionIcon.WIDTH + 2) * 2, 0),
                                                     lambda: self._select_action(BattleAction.NEXT_UNIT),
                                                     "n", 170))
            self.action_icons.append(suie.ActionIcon(((suie.ActionIcon.WIDTH + 2) * 3, 0),
                                                     lambda: self._select_action(BattleAction.GUARD),
                                                     "g", 172))

        elif self.current_phase == BattlePhase.TARGET and self.selected_avatar:
            self.action_icons.append(suie.ActionIcon((0, 0), lambda: self._select_action(BattleAction.CANCEL), "c", 91))

        for icon in self.action_icons:
            self.action_panel.add_child(icon)

    def _setup_panels(self):
        self.lineup_panel = suie.Panel((5, suie.SCREEN_HEIGHT - 90), (360, 80))

        border = suie.Border((0, 0), (80, 80))
        self.target_panel = suie.Panel((suie.SCREEN_WIDTH - 85, suie.SCREEN_HEIGHT - 85), (80, 80), [border])

        self.action_panel = suie.Panel((375, suie.SCREEN_HEIGHT - 85), (320, 80))

        border = suie.Border((0, 0), (600, 20))
        self.info_label = suie.Label((10, 6),
                           "ACTIVE: %s | PHASE: %s | TURN #: %s" % (self.active, self.current_phase, self.turn_count),
                           font_size=10)
        self.info_panel = suie.Panel((2, 2), (600, 20), [border, self.info_label])

        self.hud_panel = suie.Panel((0, 0), (suie.SCREEN_WIDTH, suie.SCREEN_HEIGHT),
                                    [self.info_panel, self.lineup_panel, self.target_panel, self.action_panel])