class Mage(pygame.sprite.Sprite): def __init__(self, screen, name): super().__init__() self.image = self._load_image() self.screen = screen self.rect = self.image.get_rect() self.rect.x, self.rect.y = int(screen.get_size()[0] / 2), int(screen.get_size()[1] / 2) self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move, (0, -self.movement_speed)), K_s: (self.move, (0, self.movement_speed)), K_a: (self.move, (-self.movement_speed, 0)), K_d: (self.move, (self.movement_speed, 0)) } self.name_tag = Name_tag(name, font_size=int(self.rect.height / 3)) def _load_image(self, path="sprites/mage.png"): try: return pygame.image.load(path) except: image = pygame.Surface((50, 100)) image.fill((255, 255, 25)) return image def move(self, delta): """Moves the sprite on screen and updates sprite to face the right direction""" "Delta is a tuple" if delta[0] < 0 and self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right elif delta[0] > 0 and not self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right self.rect.x += delta[0] self.rect.y += delta[1] def press_key(self, key): """Gets function from keys_map and calls it with arguments stored in same dictionary""" if key in self.keys_map: self.keys_map[key][0](self.keys_map[key][1]) def update(self): self.rect.clamp_ip(self.screen.get_rect()) # Doesn't allow player to move beyond the screen # Calculate Y coordinate so it's right above sprite's head self.name_tag.update_pos((self.rect.left, self.rect.center[1] - self.rect.height / 2)) self.screen.blit(self.name_tag.marked_text_surface, self.name_tag.marked_text_rect) self.screen.blit(self.name_tag.text_surface, self.name_tag.text_rect)
def __init__(self, surface, level, name, type): super().__init__() self.image = self._load_image() self.rect = self.image.get_rect() self.name = name self.health = 100 # must be between 0 and 100 self.character_type = type self.level = level self.surface = surface self.banishing = False self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move_avatar, (0, -self.movement_speed)), K_s: (self.move_avatar, (0, self.movement_speed)), K_a: (self.move_avatar, (-self.movement_speed, 0)), K_d: (self.move_avatar, (self.movement_speed, 0)), } self.name_tag = Name_tag(name, self.surface, font_size=int(self.rect.height / 3)) self.collided = 0 # List of sprites which are in contact with player self.curent_tile = 0 # Tile occupied by player at the moment self.world_coords = (100, 100) self.health_bar = HealthBar(self, surface) self.spawn() self.projectiles = pygame.sprite.Group() logging.info("avatar {} spawned".format(self.name))
def __init__(self, screen, name): super().__init__() self.image = self._load_image() self.screen = screen self.rect = self.image.get_rect() self.rect.x, self.rect.y = int(screen.get_size()[0] / 2), int(screen.get_size()[1] / 2) self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move, (0, -self.movement_speed)), K_s: (self.move, (0, self.movement_speed)), K_a: (self.move, (-self.movement_speed, 0)), K_d: (self.move, (self.movement_speed, 0)) } self.name_tag = Name_tag(name, font_size=int(self.rect.height / 3))
def __init__(self, screen, level, name): super().__init__() self.level = level self.image = self._load_image() self.screen = screen self.rect = self.image.get_rect() self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move_character, (0, -self.movement_speed)), K_s: (self.move_character, (0, self.movement_speed)), K_a: (self.move_character, (-self.movement_speed, 0)), K_d: (self.move_character, (self.movement_speed, 0)) } self.name_tag = Name_tag(name, font_size=int(self.rect.height / 3)) self.collided = 0 # List of sprites which are in contact with player self.curent_tile = 0 # Tile occupied by player at the moment self.spawn()
class Avatar(pygame.sprite.Sprite): def __init__(self, surface, level, name, type): super().__init__() self.image = self._load_image() self.rect = self.image.get_rect() self.name = name self.health = 100 # must be between 0 and 100 self.character_type = type self.level = level self.surface = surface self.banishing = False self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move_avatar, (0, -self.movement_speed)), K_s: (self.move_avatar, (0, self.movement_speed)), K_a: (self.move_avatar, (-self.movement_speed, 0)), K_d: (self.move_avatar, (self.movement_speed, 0)), } self.name_tag = Name_tag(name, self.surface, font_size=int(self.rect.height / 3)) self.collided = 0 # List of sprites which are in contact with player self.curent_tile = 0 # Tile occupied by player at the moment self.world_coords = (100, 100) self.health_bar = HealthBar(self, surface) self.spawn() self.projectiles = pygame.sprite.Group() logging.info("avatar {} spawned".format(self.name)) def get_meta_data(self): return { "name": self.name, "world_coords": self.world_coords, "type": self.character_type, "health": self.health, } def _load_image(self, path="../game_sprites/"): path += "mage.png" try: return pygame.image.load(path).convert_alpha() except: image = pygame.Surface((50, 100)) image.fill((255, 255, 25)) return image def move_avatar(self, delta): """Moves the sprite on screen and updates sprite to face the right direction Delta is a tuple The method first assigns player's global position and then calculates where he should appear on the window""" new_world_x = self.world_coords[0] - delta[0] new_world_y = self.world_coords[1] - delta[1] if ( -self.level.LEVEL_WIDTH_PX <= new_world_x <= 0 and -self.level.LEVEL_HEIGHT_PX <= new_world_y <= 0 and self._check_pos(new_world_x, new_world_y) ): self.world_coords = [new_world_x, new_world_y] # Turn image right or left if delta[0] < 0 and self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right elif delta[0] > 0 and not self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right def press_key(self, key): """Key must be keyboard key defined in pygame.locals constants Gets function from keys_map and calls it with arguments stored in same dictionary""" if key in self.keys_map: self.keys_map[key][0](self.keys_map[key][1]) def update(self): # Update coordinates self.rect.center = (self.level.x_offset - self.world_coords[0], self.level.y_offset - self.world_coords[1]) self._check_map_borders() # Calculate text's Y coordinate so it's right above sprite's head self.name_tag.update_pos((self.rect.left, self.rect.center[1] - self.rect.height / 2 - 10)) self.name_tag.render() # Update Health Bar self.health_bar.update() # update projectiles self.projectiles.update() # if player is hit by an enemy projectile, the projectile is killed and player takes damage collided_projs = pygame.sprite.spritecollide(self, game_objects.projectiles, False) for proj in collided_projs: if proj not in self.projectiles: self.damage_health(10) proj.remove(game_objects.projectiles) def fire_projectile(self, velocity=0): projectile = Projectile(self.level, self.world_coords) if velocity: projectile.velocity = velocity else: projectile.velocity = [-((m - r) / 10) for m, r in zip(pygame.mouse.get_pos(), self.rect.center)] self.projectiles.add(projectile) game_objects.projectiles.add(projectile) def fire_char_projectile(self, velocity=0): pass def _check_pos(self, x, y): """This method returns false if player is colliding with unwalkable tiles""" x, y = int((-x) / self.level.TILE_SIZE), int(-y / self.level.TILE_SIZE) # logging.info("{}: x {}, y {}, width {} height {}".format(str(self.level.LEVEL[x * self.level.LEVEL_HEIGHT + y].walkable), # x, y, self.level.LEVEL_WIDTH, self.level.LEVEL_HEIGHT)) return self.level.LEVEL[x * self.level.LEVEL_HEIGHT + y].walkable def _check_map_borders(self): """This method is responsible for all actions related to player position""" # self.rect.clamp_ip(self.screen.get_rect()) # Doesn't allow player to move beyond the screen if self.rect.centerx >= self.surface.get_width() - self.level.marginx: self.level.move_map((-self.movement_speed, 0)) if self.rect.centerx <= self.level.marginx: self.level.move_map((self.movement_speed, 0)) if self.rect.centery >= self.surface.get_height() - self.level.marginy: self.level.move_map((0, -self.movement_speed)) if self.rect.centery <= self.level.marginy: self.level.move_map((0, self.movement_speed)) def spawn(self): """Spwans avatar in a random location on the map Warning, coordinates ust be divisible by player step, otherwise it will cause an array out of bounds exception near edge of the map""" # TODO fix a bug where player can be spawned in unwalkable tile. self.world_coords = [-self.movement_speed, -self.movement_speed] def damage_health(self, damage): self.health -= damage if self.health - damage >= 0 else self.health print("Health damaged")
class Mage(pygame.sprite.Sprite): def __init__(self, screen, level, name): super().__init__() self.level = level self.image = self._load_image() self.screen = screen self.rect = self.image.get_rect() self.velocity = [0, 0] self.movement_speed = 7 # number of pixels traveled per frame self.looking_right = 0 # Dictionary containing key bindings to functions and their arguments self.keys_map = { K_w: (self.move_character, (0, -self.movement_speed)), K_s: (self.move_character, (0, self.movement_speed)), K_a: (self.move_character, (-self.movement_speed, 0)), K_d: (self.move_character, (self.movement_speed, 0)) } self.name_tag = Name_tag(name, font_size=int(self.rect.height / 3)) self.collided = 0 # List of sprites which are in contact with player self.curent_tile = 0 # Tile occupied by player at the moment self.spawn() def _load_image(self, path="sprites/mage.png"): try: return pygame.image.load(path).convert_alpha() except: image = pygame.Surface((50, 100)) image.fill((255, 255, 25)) return image def move_character(self, delta): """Moves the sprite on screen and updates sprite to face the right direction Delta is a tuple""" # move self.rect.x += delta[0] self.rect.y += delta[1] # Turn image right or left if delta[0] < 0 and self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right elif delta[0] > 0 and not self.looking_right: self.image = pygame.transform.flip(self.image, 1, 0) self.looking_right = not self.looking_right def press_key(self, key): """Key must be keyboard key defined in pygame.locals constants Gets function from keys_map and calls it with arguments stored in same dictionary""" if key in self.keys_map: self.keys_map[key][0](self.keys_map[key][1]) def update(self): self.collided = pygame.sprite.spritecollide(self, self.level.sprite_group, False) # Check which tile player occupies now and if player tries to walk on unwalkable tile jesus_walking = False for tile in self.collided: if (tile.rect.left < self.rect.center[0] < tile.rect.right and tile.rect.bottom > self.rect.center[1] > tile.rect.top): self.curent_tile = tile if not tile.walkable: jesus_walking = True if jesus_walking: self.rect.clamp_ip(self.curent_tile) self._check_pos() self.rect.clamp_ip(self.screen.get_rect()) # Doesn't allow player to move beyond the screen # Calculate Y coordinate so it's right above sprite's head self.name_tag.update_pos((self.rect.left, self.rect.center[1] - self.rect.height / 2)) self.screen.blit(self.name_tag.marked_text_surface, self.name_tag.marked_text_rect) self.screen.blit(self.name_tag.text_surface, self.name_tag.text_rect) def _check_pos(self): """This method is responceble for all actions related to player position""" if self.rect.x >= self.screen.get_width() - self.level.margin: self.level.move_map((-self.movement_speed, 0)) if self.rect.x <= self.level.margin: self.level.move_map((self.movement_speed, 0)) if self.rect.y >= self.screen.get_height() - self.level.margin: self.level.move_map((0, -self.movement_speed)) if self.rect.y <= self.level.margin: self.level.move_map((0, self.movement_speed)) def spawn(self): self.rect.center = (random.randint(0, self.level.LEVEL_WIDTH_PX), random.randint(0, self.level.LEVEL_HEIGHT_PX))