Example #1
0
    def fill(self, window, worlds, location_pools, item_pools):
        world = worlds[self.id]
        for (location_name, record) in pattern_dict_items(self.locations):
            if record.item is None:
                continue

            player_id = self.id if record.player is None else record.player - 1

            location_matcher = lambda loc: loc.world.id == world.id and loc.name == location_name
            location = pull_first_element(location_pools, location_matcher)
            if location is None:
                try:
                    location = LocationFactory(location_name)
                except KeyError:
                    raise RuntimeError('Unknown location in world %d: %s' %
                                       (world.id + 1, name))
                if location.type == 'Boss':
                    continue
                else:
                    raise RuntimeError(
                        'Location already filled in world %d: %s' %
                        (self.id + 1, location_name))

            try:
                item = self.pool_remove_item(item_pools,
                                             record.item,
                                             1,
                                             world_id=player_id)[0]
            except KeyError:
                try:
                    self.pool_remove_item(item_pools,
                                          "#Junk",
                                          1,
                                          world_id=player_id)
                    item_matcher = lambda item: pattern_matcher(record.item)(
                        item.name)
                    item = random.choice(
                        list(ItemIterator(item_matcher, worlds[player_id])))
                except KeyError:
                    raise RuntimeError(
                        'Too many items were added to world %d, and not enough junk is available to be removed.'
                        % (self.id + 1))

            if record.price is not None:
                item.price = record.price
            location.world.push_item(location, item, True)
            if item.advancement:
                playthrough = Playthrough.max_explore(
                    [world.state for world in worlds],
                    itertools.chain.from_iterable(item_pools))
                if not playthrough.can_beat_game(False):
                    raise FillError(
                        '%s in world %d is not reachable without %s in world %d!'
                        %
                        (location.name, self.id + 1, item.name, player_id + 1))
            window.fillcount += 1
            window.update_progress(5 + (
                (window.fillcount / window.locationcount) * 30))
 def pool_replace_item(self, item_pools, item_group, player_id, new_item,
                       worlds):
     removed_item = self.pool_remove_item(item_pools,
                                          item_group,
                                          1,
                                          world_id=player_id)[0]
     item_matcher = lambda item: pattern_matcher(new_item)(item.name)
     if self.item_pool[removed_item.name].count > 1:
         self.item_pool[removed_item.name].count -= 1
     else:
         del self.item_pool[removed_item.name]
     return random.choice(
         list(ItemIterator(item_matcher, worlds[player_id])))
Example #3
0
 def pool_replace_item(self, item_pools, item_group, player_id, new_item, worlds):
     removed_item = self.pool_remove_item(item_pools, item_group, 1, world_id=player_id)[0]
     item_matcher = lambda item: pattern_matcher(new_item)(item.name)
     if self.item_pool[removed_item.name].count > 1:
         self.item_pool[removed_item.name].count -= 1
     else:
         del self.item_pool[removed_item.name]
     if new_item == "#Junk":
         if self.distribution.settings.enable_distribution_file:
             return ItemFactory(get_junk_item(1, self.base_pool, self.item_pool))[0]
         else:  # Generator settings that add junk to the pool should not be strict about the item_pool definitions
             return ItemFactory(get_junk_item(1))[0]
     return random.choice(list(ItemIterator(item_matcher, worlds[player_id])))
Example #4
0
    def pool_add_item(self, pool, item_name, count):
        if item_name == '#Junk':
            added_items = get_junk_item(count, pool=pool, plando_pool=self.item_pool)
        elif is_pattern(item_name):
            add_matcher = lambda item: pattern_matcher(item_name)(item.name)
            candidates = [
                item.name for item in ItemIterator(predicate=add_matcher)
                if item.name not in self.item_pool or self.item_pool[item.name].count != 0
            ]  # Only allow items to be candidates if they haven't been set to 0
            if len(candidates) == 0:
                raise RuntimeError("Unknown item, or item set to 0 in the item pool could not be added: " + item_name)
            added_items = random_choices(candidates, k=count)
        else:
            if not IsItem(item_name):
                raise RuntimeError("Unknown item could not be added: " + item_name)
            added_items = [item_name] * count

        for item in added_items:
            pool.append(item)

        return added_items
    def pool_add_item(self, pool, item_name, count):
        added_items = []
        if item_name == '#Junk':
            added_items = get_junk_item(count)
        elif is_pattern(item_name):
            add_matcher = lambda item: pattern_matcher(item_name)(item.name)
            candidates = [
                item.name for item in ItemIterator(predicate=add_matcher)
            ]
            if len(candidates) == 0:
                raise RuntimeError("Unknown item could not be added: " +
                                   item_name)
            added_items = random_choices(candidates, k=count)
        else:
            if not IsItem(item_name):
                raise RuntimeError("Unknown item could not be added: " +
                                   item_name)
            added_items = [item_name] * count

        for item in added_items:
            pool.append(item)

        return added_items