def blit_sprite(self, sprite: 'sprites.AbstractSprite'):
        if sprite is None:
            return
        elif isinstance(sprite, sprites.MultiSprite):
            for spr in sprite.all_sprites():
                self.blit_sprite(spr)
        else:
            mult = self._get_render_mult()
            offs = (self.camera_xy[0] * mult,
                    self.camera_xy[1] * mult)

            if isinstance(sprite, sprites.ImageSprite):
                if sprite.model() is not None:
                    src_rect_on_atlas = sprite.model().rect()
                    dest_rect_in_world = sprite.rect()

                    surf = self._get_drawing_surface()
                    dest_rect = [dest_rect_in_world[0] * mult * self.camera_scale[0] - offs[0],
                                 dest_rect_in_world[1] * mult * self.camera_scale[1] - offs[1],
                                 dest_rect_in_world[2] * mult * self.camera_scale[0],
                                 dest_rect_in_world[3] * mult * self.camera_scale[1]]

                    if (src_rect_on_atlas[2] == dest_rect[2]
                            and src_rect_on_atlas[3] == dest_rect[3]
                            and sprite.rotation() == 0
                            and sprite.xflip() is False
                            and sprite.color() == (1, 1, 1)):
                        # already the correct size, just blit it
                        surf.blit(self.cached_texture_atlas, (dest_rect[0], dest_rect[1]), src_rect_on_atlas)
                    else:
                        subsurf = self.cached_texture_atlas.subsurface(src_rect_on_atlas)
                        orig_subsurf = subsurf
                        if sprite.xflip():
                            subsurf = pygame.transform.flip(subsurf, True, False)

                        if sprite.rotation() == 0:
                            subsurf = subsurf.copy()
                        elif sprite.rotation() == 1:
                            subsurf = pygame.transform.rotate(subsurf, -90)
                        elif sprite.rotation() == 2:
                            subsurf = pygame.transform.rotate(subsurf, -180)
                        else:
                            subsurf = pygame.transform.rotate(subsurf, -270)

                        if sprite.color() != (1, 1, 1):
                            if subsurf == orig_subsurf:
                                subsurf = subsurf.copy()
                            color255 = tuple(util.bound(int(c * 256), 0, 255) for c in sprite.color())
                            subsurf.fill(color255, [0, 0, subsurf.get_width(), subsurf.get_height()], pygame.BLEND_MULT)

                        xformed = pygame.transform.scale(subsurf, (int(dest_rect[2]), int(dest_rect[3])))
                        surf.blit(xformed, (dest_rect[0], dest_rect[1]))
            elif isinstance(sprite, sprites.TriangleSprite):
                surf = self._get_drawing_surface()
                color255 = list(util.bound(int(c * 256), 0, 255) for c in sprite.color())
                xformed_pts = [(p[0] * mult - offs[0], p[1] * mult - offs[1]) for p in sprite.points()]
                pygame.draw.polygon(surf, color255, xformed_pts)
Beispiel #2
0
 def _get_temp_zoom_prog(self):
     if self._temp_zoom_idx is None:
         return 0
     elif self._use_temp_zoom:
         return util.bound(
             self._temp_zoom_tick_count / self._temp_zoom_delay, 0, 1)
     else:
         return util.bound(
             1 - self._temp_zoom_tick_count / self._temp_zoom_delay, 0, 1)
Beispiel #3
0
def draw_with_transparency(src_sheet, src_rect, dest_sheet, dest_pos, alpha):
    """
    :param alpha: a value from [0.0, 1.0] where 0.0 is fully transparent
    """
    draw_wtih_color_xform(
        src_sheet, src_rect, dest_sheet, dest_pos, lambda color:
        (color[0], color[1], color[2], util.bound(color[3] * alpha, 0, 1)))
Beispiel #4
0
    def adjust_base_zoom(self, dz: int):
        old_center = self.get_camera_center_in_world(ignore_temp_zoom=True)

        new_zoom_idx = util.bound(int(self._base_zoom_idx + dz), 0,
                                  len(_ZOOM_LEVELS) - 1)
        self._base_zoom_idx = new_zoom_idx
        self.set_camera_center_in_world(old_center)
Beispiel #5
0
    def _handle_inputs(self):
        edits = inputs.get_instance().all_pressed_ascii_keys()

        text = self.text
        cursor_pos = self.cursor_pos

        jump_cursor = inputs.get_instance().was_pressed_two_way(
            pygame.K_HOME, pygame.K_END)
        if jump_cursor < 0:
            cursor_pos = 0
        elif jump_cursor > 0:
            cursor_pos = len(text)

        move_cursor = 0
        if inputs.get_instance().was_pressed_or_held_and_repeated(
                pygame.K_LEFT) and not inputs.get_instance().is_held(
                    pygame.K_RIGHT):
            move_cursor = -1
        if inputs.get_instance().was_pressed_or_held_and_repeated(
                pygame.K_RIGHT) and not inputs.get_instance().is_held(
                    pygame.K_LEFT):
            move_cursor = 1
        if move_cursor != 0:
            cursor_pos = util.bound(cursor_pos + move_cursor, 0, len(text))

        if inputs.get_instance().was_pressed_or_held_and_repeated(
                pygame.K_DELETE):
            text, cursor_pos = util.apply_ascii_edits_to_text(
                text, ["~delete~"], cursor_pos=cursor_pos)

        if not inputs.get_instance().was_pressed(
                pygame.K_BACKSPACE) and inputs.get_instance(
                ).was_pressed_or_held_and_repeated(pygame.K_BACKSPACE):
            # backspace is an ascii character, so if it was pressed this frame it'll be in edits
            text, cursor_pos = util.apply_ascii_edits_to_text(
                text, ["\b"], cursor_pos=cursor_pos)

        # TODO can't hold regular keys to make them repeat

        if len(edits) > 0:
            text, cursor_pos = util.apply_ascii_edits_to_text(
                text,
                edits,
                cursor_pos=cursor_pos,
                max_len=self.char_limit,
                allowlist=self.allowed_chars)
        self.text = text
        self.cursor_pos = cursor_pos
Beispiel #6
0
def resolve_explicit_song_id_from_level(explicit_song_id):
    if explicit_song_id in _SONG_MAPPINGS_FOR_LEVELS:
        return _SONG_MAPPINGS_FOR_LEVELS[explicit_song_id][0]
    else:
        try:
            # it should look like "sector_ab_2", in which case we need to extract "sector_ab" and 2.
            underscore_idx = explicit_song_id.rindex("_")
            key = explicit_song_id[0:underscore_idx]
            idx = int(explicit_song_id[underscore_idx + 1:]) - 1
            if key in _SONG_MAPPINGS_FOR_LEVELS:
                n_songs = len(_SONG_MAPPINGS_FOR_LEVELS[key])
                return _SONG_MAPPINGS_FOR_LEVELS[key][util.bound(
                    idx, -1, n_songs - 1)]
            else:
                print(
                    "WARN: unrecognized song id: {}".format(explicit_song_id))
        except Exception:
            print("WARN: song id couldn't be parsed: {}".format(
                explicit_song_id))

    # if we failed to resolve the explicit ID, just bail.
    return SILENCE
Beispiel #7
0
 def get_prog(self):
     if self.duration < 0:
         return 0
     else:
         return util.bound(self.ticks_active / self.duration, 0, 1)
 def set_clear_color(self, color):
     self.clear_color = tuple(util.bound(int(c * 256), 0, 255) for c in color)
Beispiel #9
0
def set_master_volume(val):
    global _MASTER_VOLUME, CURRENT_SONG
    if val != _MASTER_VOLUME:
        print("INFO: setting master music volume to {}".format(val))
        _MASTER_VOLUME = util.bound(val, 0.0, 1.0)
        pygame.mixer.music.set_volume(_MASTER_VOLUME * CURRENT_SONG.volume)
Beispiel #10
0
def set_volume(volume):
    global _MASTER_VOLUME
    _MASTER_VOLUME = util.bound(volume, 0.0, 1.0)