예제 #1
0
def random_magic_weapon(dungeon_level=1):
    item = random_weapon(dungeon_level=dungeon_level)

    dice = randint(1, 1000)

    item.add_component(IdentifiableWeapon(item.base_name), "identifiable")

    naming = Naming(item.base_name)

    if (dice <= 500):
        naming.prefix = "Remarkable"
        item.color = COLORS.get('equipment_uncommon')
        item.equippable.number_of_dice = 2
    elif (dice <= 750):
        naming.prefix = "Excellent"
        item.color = COLORS.get('equipment_rare')
        item.equippable.number_of_dice = 3
    elif (dice <= 900):
        naming.prefix = "Exceptional"
        item.color = COLORS.get('equipment_epic')
        item.equippable.number_of_dice = 4
    elif (dice <= 950):
        naming.prefix = "Phenomenal"
        item.color = COLORS.get('equipment_legendary')
        item.equippable.number_of_dice = 5
    else:
        create_unique_weapon(item)

    item.add_component(naming, 'naming')

    add_random_weapon_ablity(item)

    return item
예제 #2
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=False, block_sight=False):
        super(CavernFloor, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_cavern_floor')
        self.out_of_fov_color = COLORS.get('dark_cavern_floor')
        self.name = "Cavern floor"
        self.char = choice([',', '`', ';', "'"])
예제 #3
0
 def update_and_draw_layout(self):
     for x, y in self:
         wall = self.is_wall(x, y)
         if self.visible(x, y):
             if wall:
                 self.update_and_draw_char(x,
                                           y,
                                           ' ',
                                           fg=None,
                                           bg=COLORS.get('light_wall'))
             else:
                 self.update_and_draw_char(x,
                                           y,
                                           ' ',
                                           fg=None,
                                           bg=COLORS.get('light_ground'))
             self.explored[x, y] = True
         elif self.explored[x, y]:
             if wall:
                 self.update_and_draw_char(x,
                                           y,
                                           ' ',
                                           fg=None,
                                           bg=COLORS.get('dark_wall'))
             else:
                 self.update_and_draw_char(x,
                                           y,
                                           ' ',
                                           fg=None,
                                           bg=COLORS.get('dark_ground'))
예제 #4
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=True, block_sight=True):
        super(CorridorWall, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_cavern_wall')
        self.out_of_fov_color = COLORS.get('dark_cavern_wall')
        self.name = "Corridor wall"
        self.char = '#'
예제 #5
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=False, block_sight=False):
        super(InternalDoor, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_door_tile')
        self.out_of_fov_color = COLORS.get('dark_door_tile')
        self.name = "Room Floor"
        self.char = '.'
예제 #6
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=False, block_sight=False):
        super(CorridorFloor, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_room_floor')
        self.out_of_fov_color = COLORS.get('dark_room_floor')
        self.name = "Corridor floor"
        self.char = '.'
예제 #7
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=True, block_sight=True):
        super(RoomWall, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_room_wall')
        self.out_of_fov_color = COLORS.get('dark_room_wall')
        self.name = "Wall"
        self.char = '#'
예제 #8
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=False, block_sight=False):
        super(ShallowWater, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_shallow_water')
        self.out_of_fov_color = COLORS.get('dark_shallow_water')
        self.name = "Shallow water"
        self.char = chr(247)
예제 #9
0
파일: game_map.py 프로젝트: kmonaghan/rogue
    def place_stairs(self):
        exit = find(lambda room: room.name == 'exit', self.current_level.rooms)

        if (exit):
            x, y = exit.center

            self.down_stairs = Entity(Point(x, y),
                                      '>',
                                      'Stairs',
                                      COLORS.get('stairs'),
                                      render_order=RenderOrder.STAIRS,
                                      always_visible=True)
            self.down_stairs.add_component(Stairs(self.dungeon_level + 1),
                                           "stairs")

            self.current_level.add_entity(self.down_stairs)

        entrance = find(lambda room: room.name == 'entrance',
                        self.current_level.rooms)

        if (entrance):
            x, y = entrance.center

            self.up_stairs = Entity(Point(x, y),
                                    '<',
                                    'Stairs',
                                    COLORS.get('stairs'),
                                    render_order=RenderOrder.STAIRS,
                                    always_visible=True)
            self.up_stairs.add_component(Stairs(self.dungeon_level - 1),
                                         "stairs")

            self.current_level.add_entity(self.up_stairs)
예제 #10
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=True, block_sight=False):
        super(DeepWater, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_deep_water')
        self.out_of_fov_color = COLORS.get('dark_deep_water')
        self.name = "Deep water"
        self.char = chr(247)
예제 #11
0
파일: tome.py 프로젝트: kmonaghan/rogue
def lightning(**kwargs):
    '''Cast a lightning bolt.

    A bolt does ELECTRIC damage to all damagable entities in a line. The line is
    drawn between the caster, through the target point and stops when it hits a
    blocking tile.

    Parameters
    ----------
    kwargs:
       caster (Entity): Entity that initiated the spell.
       game_map (GameMap): Current game map.
       number_of_dice (int): number of die to roll.
       target_x (int): x co-ordinate.
       target_y (int): y co-ordinate.
       type_of_dice (int): Type of die to roll.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    caster = kwargs.get('caster')
    game_map = kwargs.get('game_map')
    number_of_dice = kwargs.get('number_of_dice')
    target_x = kwargs.get('target_x')
    target_y = kwargs.get('target_y')
    type_of_dice = kwargs.get('type_of_dice')

    ray = bresenham_ray(game_map, (caster.x, caster.y), (target_x, target_y))

    results = []

    ray.pop(0)  #first item is caster xy

    for x, y in ray:
        entities = game_map.current_level.entities.get_entities_in_position(
            (x, y))
        for entity in entities:
            if entity.health and not entity.health.dead:
                damage = die_roll(number_of_dice, type_of_dice)
                results.append({
                    ResultTypes.MESSAGE:
                    Message(
                        f"A lighting bolt strikes the {entity.name} with a loud crack of thunder!",
                        COLORS.get('effect_text'),
                        target=entity,
                        type=MessageType.EFFECT)
                })
                damage_results, total_damage = entity.health.take_damage(
                    damage, caster, DamageType.ELECTRIC)
                results.append({
                    ResultTypes.MESSAGE:
                    Message(f"{entity.name} takes {str(total_damage)} damage.",
                            COLORS.get('damage_text'))
                })
                results.extend(damage_results)

    return results
예제 #12
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked=False, block_sight=False):
        super(FungalCavernFloor, self).__init__(blocked, block_sight)

        self.fov_color = COLORS.get('light_cavern_floor')
        self.out_of_fov_color = COLORS.get('dark_cavern_floor')
        self.foreground_color = COLORS.get('light_fungal_cavern_floor')
        self.name = "Fungus covered cavern floor"
        self.char = '"'
예제 #13
0
 def render_dijkstra(self, dijkstra, console: Console) -> None:
     dijkstra = np.where(dijkstra == np.iinfo(np.int32).max, -1, dijkstra)
     max_distance = np.amax(dijkstra)
     for (x, y), value in np.ndenumerate(self.grid):
         if dijkstra[x, y] > 0:
             console.bg[x, y] = tcod.color_lerp(
                 COLORS.get('dijkstra_near'), COLORS.get('dijkstra_far'),
                 0.9 * dijkstra[x, y] / max_distance)
예제 #14
0
파일: tome.py 프로젝트: kmonaghan/rogue
def fireball(**kwargs):
    '''Cast a fireball.

    Does FIRE damage to all damagable entities in a circle centered on the
    target point.

    Parameters
    ----------
    kwargs:
       caster (Entity): Entity that initiated the spell.
       game_map (GameMap): Current game map.
       number_of_dice (int): number of die to roll.
       radius (int): radius of the spell effect.
       target_x (int): x co-ordinate.
       target_y (int): y co-ordinate.
       type_of_dice (int): Type of die to roll.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    caster = kwargs.get('caster')
    game_map = kwargs.get('game_map')
    number_of_dice = kwargs.get('number_of_dice')
    radius = kwargs.get('radius')
    target_x = kwargs.get('target_x')
    target_y = kwargs.get('target_y')
    type_of_dice = kwargs.get('type_of_dice')

    results = []

    if not game_map.current_level.fov[target_x, target_y]:
        results.append({
            ResultTypes.MESSAGE:
            Message('You cannot target a tile outside your field of view.',
                    COLORS.get('neutral_text'))
        })
        return results

    results.append({
        ResultTypes.MESSAGE:
        Message(
            'The fireball explodes, burning everything within {0} tiles!'.
            format(radius), COLORS.get('effect_text'))
    })

    #TODO: refactor, this is probably horribly inefficent
    for entity in game_map.current_level.entities:
        if entity.point.distance_to(Point(
                target_x, target_y)) <= radius and entity.health:
            damage = die_roll(number_of_dice, type_of_dice)
            damage_results, total_damage = entity.health.take_damage(
                damage, caster, DamageType.FIRE)
            results.extend(damage_results)

    return results
예제 #15
0
파일: health.py 프로젝트: kmonaghan/rogue
    def display_color(self):

        if (self.health_percentage <= HealthStates.NEAR_DEATH):
            return COLORS.get('health_near_death')
        elif (self.health_percentage <= HealthStates.INJURED):
            return COLORS.get('health_injured')
        elif (self.health_percentage <= HealthStates.BARELY_INJURED):
            return COLORS.get('health_barely_injured')

        return self.owner.color
예제 #16
0
파일: death.py 프로젝트: kmonaghan/rogue
    def npc_death(self, game_map):

        self.owner.char = '%'
        self.owner.color = COLORS.get('corpse')
        self.owner.blocks = False
        self.owner.render_order = RenderOrder.CORPSE
        pubsub.pubsub.add_message(
            pubsub.Publish(None,
                           pubsub.PubSubTypes.MESSAGE,
                           message=Message('You died!',
                                           COLORS.get('failure_text'))))

        return GameStates.GAME_OVER
예제 #17
0
 def use(self, player):
     results = []
     if player.harmable.hp == player.harmable.max_hp:
         message = Message('You are already at full health.', 
                           COLORS.get('white'))
         results.append({'item_consumed': (False, self.owner), 
                         'message': message})
     else:
         message = Message('You wounds start to heal.', 
                           COLORS.get('green'))
         results.append({'item_consumed': (True, self.owner),
                         'heal': (player, self.healing),
                         'message': message,
                         'animation': (Animations.HEALTH_POTION, player)})
     return results
예제 #18
0
def orc(point=None, dungeon_level=1):
    #create an orc
    health_component = Health(20)
    ai_component = BasicNPC()

    npc = Character(point,
                    'O',
                    'orc',
                    COLORS.get('orc'),
                    ai=ai_component,
                    species=Species.ORC,
                    health=health_component,
                    act_energy=5)

    npc.add_component(Offence(base_power=10), 'offence')
    npc.add_component(Defence(defence=4), 'defence')
    npc.add_component(Level(xp_value=10), 'level')

    npc.movement.routing_avoid.extend(npc_avoid)

    item = equipment.create_weapon('shortsword')
    item.lootable = False

    npc.inventory.add_item(item)
    npc.equipment.toggle_equip(item)

    return npc
예제 #19
0
def waterblast(game_map, center, *, radius=4, damage=6, user=None):
    """Create a blast of water centered at a position of a given radius.

    The waterblast both deals damage, and floods all tiles within a given
    radius.
    """
    results = []
    harmable_within_radius = (get_all_entities_with_component_within_radius(
        center, game_map, "harmable", radius))
    for entity in (x for x in harmable_within_radius if x != user):
        text = f"The {entity.name} is caught in a waterblast!"
        message = Message(text, COLORS.get('white'))
        results.append({
            ResultTypes.DAMAGE: (entity, None, damage, [Elements.WATER]),
            ResultTypes.MESSAGE:
            message
        })
    blast_coordinates = coordinates_within_circle(center, radius)
    for coord in blast_coordinates:
        if game_map.walkable[coord]:
            entities = get_all_entities_of_type_within_radius(
                coord, game_map, EntityTypes.TERRAIN, 0)
            for entity in entities:
                results.append({ResultTypes.REMOVE_ENTITY: entity})
            water = Water.make(game_map, coord[0], coord[1])
            results.append({ResultTypes.ADD_ENTITY: water})
    results.append(
        {ResultTypes.ANIMATION: (Animations.WATERBLAST, center, radius)})
    return results
예제 #20
0
파일: tome.py 프로젝트: kmonaghan/rogue
def change_power(**kwargs):
    '''Cast increase power.

    Update an entity's power by [number_of_dice]D[type_of_dice].

    Parameters
    ----------
    kwargs:
       caster (Entity): Entity that initiated the spell.
       number_of_dice (int): number of die to roll.
       target (Entity): The entity that is being targetted by the spell.
       type_of_dice (int): Type of die to roll.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    caster = kwargs.get('caster')
    number_of_dice = kwargs.get('number_of_dice')
    target = kwargs.get('target')
    type_of_dice = kwargs.get('type_of_dice')

    results = []

    extra = die_roll(number_of_dice, type_of_dice)
    target.offence.base_power = target.offence.base_power + extra
    results.append({
        ResultTypes.MESSAGE:
        Message('You feel like you can take anything on!',
                COLORS.get('success_text'))
    })

    return results
예제 #21
0
파일: tome.py 프로젝트: kmonaghan/rogue
def antidote(**kwargs):
    '''Cast antidote.

    Remove poisoned component from an entity (if it exists).

    Parameters
    ----------
    kwargs:
       target (Entity): The entity that is being targetted by the spell.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    target = kwargs.get('target')

    results = []

    if target.poisoned:
        results.extend(target.poisoned.end())

    results.append({
        ResultTypes.MESSAGE:
        Message(f"{target.name} feels clensed.",
                COLORS.get('success_text'),
                target=target,
                type=MessageType.EFFECT)
    })

    return results
예제 #22
0
파일: tome.py 프로젝트: kmonaghan/rogue
def identify(**kwargs):
    '''Cast identify.

    If and entity has the Identifiable component and identifiable.identified is
    FALSE, switch to TRUE and print out a description of the entity.

    Parameters
    ----------
    kwargs:
       target (Entity): The entity that is being targetted by the spell.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    target = kwargs.get('target')

    results = []

    if target.identifiable and not target.identifiable.identified:
        target.identifiable.identified = True

    results.append({
        ResultTypes.MESSAGE:
        Message(f"The item is a {target.name}", COLORS.get('effect_text'))
    })
    if target.identifiable.common_ident:
        results.append({ResultTypes.COMMON_IDENT: target.base_name})

    return results
예제 #23
0
파일: tome.py 프로젝트: kmonaghan/rogue
def mapping(**kwargs):
    '''Cast mapping.

    Reveal the entire game map.

    Parameters
    ----------
    kwargs:
       game_map (GameMap): Current game map.

    Returns
    -------
    results (list)
        Results of casting the spell.
    '''
    game_map = kwargs.get('game_map')

    results = []

    game_map.current_level.explored = np.full(
        game_map.current_level.grid.shape, 1, dtype=np.int8)

    results.append({
        ResultTypes.MESSAGE:
        Message('The scroll contains a map of immediate area.',
                COLORS.get('success_text'))
    })
    results.append({ResultTypes.FOV_RECOMPUTE: True})

    return results
예제 #24
0
 def render_entity_detail(self, highlighted_path, target,
                          console: Console) -> None:
     if highlighted_path:
         for x, y in highlighted_path:
             console.bg[x, y] = COLORS.get('show_entity_track')
     if target:
         console.bg[target.x, target.y] = tcod.black
예제 #25
0
파일: tile.py 프로젝트: kmonaghan/rogue
    def __init__(self, blocked, block_sight=None):
        self.blocked = blocked

        # By default, if a tile is blocked, it also blocks sight
        if block_sight is None:
            block_sight = blocked

        self.block_sight = block_sight
        self.walkable = not self.blocked
        self.explored = False
        self.fov_color = COLORS.get('light_default')
        self.out_of_fov_color = COLORS.get('dark_default')
        self.foreground_color = COLORS.get('foreground_default')
        self.name = "Tile"
        self.char = " "
        self._glyph = None
예제 #26
0
    def tick(self, game_map):
        results = []
        coords = coordinates_within_circle((self.owner.x, self.owner.y),
                                           self.range)
        for coord in coords:
            entities = game_map.current_level.entities.get_entities_in_position(
                coord)
            if entities:
                for entity in entities:
                    if entity == self.owner:
                        continue

                    if not entity.animate:
                        continue

                    if entity.health:
                        damage = die_roll(self.number_of_dice,
                                          self.type_of_dice)
                        damage_results, total_damage = entity.health.take_damage(
                            damage, self.owner, self.damage_type)
                        if total_damage > 0:
                            msg = Message(
                                f"{entity.name} takes {str(damage)} damage from {self.owner.name}'s {self.name}.",
                                COLORS.get('damage_text'),
                                target=entity,
                                type=MessageType.EFFECT)
                            results.extend(damage_results)
                            results.extend([{ResultTypes.MESSAGE: msg}])

        return results
예제 #27
0
    def end(self):
        results = []
        if not self.owner.health.dead:
            results.append({
                ResultTypes.MESSAGE:
                Message(
                    f"{self.owner.name.title()} has regained their composure",
                    COLORS.get('effect_text'),
                    target=self.owner,
                    type=MessageType.EFFECT)
            })
            self.owner.health.base_max_hp -= self.health_modifier
            damage_results, total_damage = self.owner.health.take_damage(
                self.health_modifier)
            results.extend(damage_results)

            self.owner.deregister_turn(self.uuid)

            try:
                self.owner.del_component('berserk')
            except AttributeError:
                logging.info(
                    f"tried to remove berserk from {self.owner.name} - {self.owner.uuid}"
                )

        return results
예제 #28
0
def bat(point=None, dungeon_level=1):
    health_component = Health(4)

    creature = Character(point,
                         'B',
                         'bat',
                         COLORS.get('bat'),
                         ai=PredatorNPC(species=Species.INSECT),
                         species=Species.BAT,
                         health=health_component,
                         act_energy=3)

    creature.add_component(Offence(base_power=1), 'offence')
    creature.add_component(Defence(defence=1), 'defence')
    creature.add_component(Level(xp_value=10), 'level')

    teeth = equipment.teeth()
    teeth.lootable = False

    creature.inventory.add_item(teeth)
    creature.equipment.toggle_equip(teeth)

    if randint(1, 100) >= 70:
        equipment.add_lifedrain(teeth)
        creature.add_component(Naming(creature.base_name, prefix='Vampiric'),
                               'naming')

    return creature
예제 #29
0
파일: poisoned.py 프로젝트: kmonaghan/rogue
    def end(self):
        results = []

        if self.owner:
            try:
                self.owner.del_component("poisoned")
            except AttributeError:
                logging.info(
                    f"Tried to remove poison from {self.owner.name} - {self.owner.uuid}"
                )
        else:
            logging.info('****No owner to poisoned - already deleted?')

        self.owner.deregister_turn(self.uuid)

        if not self.owner.health.dead:
            results.append({
                ResultTypes.MESSAGE:
                Message(
                    f"The poison has run its course in {self.owner.name.title()}",
                    COLORS.get('effect_text'),
                    target=self.owner,
                    type=MessageType.EFFECT)
            })

        return results
예제 #30
0
def rat(point=None, dungeon_level=1):
    health_component = Health(4)

    creature = Character(point,
                         'R',
                         'rat',
                         COLORS.get('rat'),
                         ai=PredatorNPC(species=Species.EGG),
                         species=Species.RAT,
                         health=health_component,
                         act_energy=3)

    creature.add_component(Offence(base_power=1), 'offence')
    creature.add_component(Defence(defence=1), 'defence')
    creature.add_component(Level(xp_value=10), 'level')

    creature.movement.routing_avoid.extend(creature_avoid)

    teeth = equipment.teeth()
    teeth.lootable = False

    creature.inventory.add_item(teeth)
    creature.equipment.toggle_equip(teeth)

    pubsub.pubsub.subscribe(
        pubsub.Subscription(creature, pubsub.PubSubTypes.ATTACKED, rat_swarm))

    return creature