diff --git a/BaseClasses.py b/BaseClasses.py index d89147c9..245153af 100644 --- a/BaseClasses.py +++ b/BaseClasses.py @@ -514,6 +514,7 @@ class CollectionState(object): self.opened_doors = {player: set() for player in range(1, parent.players + 1)} self.dungeons_to_check = {player: defaultdict(dict) for player in range(1, parent.players + 1)} self.dungeon_limits = None + self.placing_item = None # self.trace = None def update_reachable_regions(self, player): @@ -787,7 +788,8 @@ class CollectionState(object): door_candidates.append(door.name) return door_candidates door_candidates, skip = [], set() - if state.world.accessibility[player] != 'locations' and remaining_keys == 0 and dungeon_name != 'Universal': + if (state.world.accessibility[player] != 'locations' and remaining_keys == 0 and dungeon_name != 'Universal' + and state.placing_item and state.placing_item.name == small_key_name): key_logic = state.world.key_logic[player][dungeon_name] for door, paired in key_logic.sm_doors.items(): if door.name in key_logic.door_rules: @@ -830,6 +832,7 @@ class CollectionState(object): player: defaultdict(dict, {name: copy.copy(checklist) for name, checklist in self.dungeons_to_check[player].items()}) for player in range(1, self.world.players + 1)} + ret.placing_item = self.placing_item return ret def apply_dungeon_exploration(self, rrp, player, dungeon_name, checklist): diff --git a/CLI.py b/CLI.py index fc70f8e9..cfb3f2eb 100644 --- a/CLI.py +++ b/CLI.py @@ -124,7 +124,7 @@ def parse_cli(argv, no_defaults=False): playerargs = parse_cli(shlex.split(getattr(ret, f"p{player}")), True) for name in ['logic', 'mode', 'swords', 'goal', 'difficulty', 'item_functionality', - 'flute_mode', 'bow_mode', 'take_any', + 'flute_mode', 'bow_mode', 'take_any', 'boots_hint', 'shuffle', 'door_shuffle', 'intensity', 'crystals_ganon', 'crystals_gt', 'openpyramid', 'mapshuffle', 'compassshuffle', 'keyshuffle', 'bigkeyshuffle', 'startinventory', 'usestartinventory', 'bombbag', 'overworld_map', 'restrict_boss_items', @@ -161,6 +161,7 @@ def parse_settings(): "retro": False, "bombbag": False, "mode": "open", + "boots_hint": False, "logic": "noglitches", "goal": "ganon", "crystals_gt": "7", diff --git a/Fill.py b/Fill.py index 8487c750..0a50470b 100644 --- a/Fill.py +++ b/Fill.py @@ -24,7 +24,6 @@ def promote_dungeon_items(world): item.advancement = True elif item.map or item.compass: item.priority = True - dungeon_tracking(world) def dungeon_tracking(world): @@ -35,7 +34,6 @@ def dungeon_tracking(world): def fill_dungeons_restrictive(world, shuffled_locations): - dungeon_tracking(world) # with shuffled dungeon items they are distributed as part of the normal item pool for item in world.get_items(): @@ -73,11 +71,13 @@ def fill_dungeons_restrictive(world, shuffled_locations): def fill_restrictive(world, base_state, locations, itempool, key_pool=None, single_player_placement=False, vanilla=False): - def sweep_from_pool(): + def sweep_from_pool(placing_item=None): new_state = base_state.copy() for item in itempool: new_state.collect(item, True) + new_state.placing_item = placing_item new_state.sweep_for_events() + new_state.placing_item = None return new_state unplaced_items = [] @@ -94,7 +94,7 @@ def fill_restrictive(world, base_state, locations, itempool, key_pool=None, sing while any(player_items.values()) and locations: items_to_place = [[itempool.remove(items[-1]), items.pop()][-1] for items in player_items.values() if items] - maximum_exploration_state = sweep_from_pool() + maximum_exploration_state = sweep_from_pool(placing_item=items_to_place[0]) has_beaten_game = world.has_beaten_game(maximum_exploration_state) for item_to_place in items_to_place: @@ -522,10 +522,17 @@ def fast_fill_helper(world, item_pool, fill_locations): def fast_fill(world, item_pool, fill_locations): - while item_pool and fill_locations: + config = world.item_pool_config + fast_pool = [x for x in item_pool if (x.name, x.player) not in config.restricted] + filtered_pool = [x for x in item_pool if (x.name, x.player) in config.restricted] + filtered_fill(world, filtered_pool, fill_locations) + while fast_pool and fill_locations: spot_to_fill = fill_locations.pop() - item_to_place = item_pool.pop() + item_to_place = fast_pool.pop() world.push_item(spot_to_fill, item_to_place, False) + item_pool.clear() + item_pool.extend(filtered_pool) + item_pool.extend(fast_pool) def fast_fill_pot_for_multiworld(world, item_pool, fill_locations): diff --git a/ItemList.py b/ItemList.py index 1a24bc5f..c17ce509 100644 --- a/ItemList.py +++ b/ItemList.py @@ -6,7 +6,7 @@ import RaceRandom as random from BaseClasses import Region, RegionType, Shop, ShopType, Location, CollectionState, PotItem from EntranceShuffle import connect_entrance from Regions import shop_to_location_table, retro_shops, shop_table_by_location, valid_pot_location -from Fill import FillError, fill_restrictive, get_dungeon_item_pool, is_dungeon_item +from Fill import FillError, fill_restrictive, get_dungeon_item_pool, track_dungeon_items, track_outside_keys from PotShuffle import vanilla_pots from Items import ItemFactory @@ -391,8 +391,16 @@ def generate_itempool(world, player): custom_medallions = medal_map[player] if 'Misery Mire' in custom_medallions: mm_medallion = custom_medallions['Misery Mire'] + if isinstance(mm_medallion, dict): + mm_medallion = random.choices(list(mm_medallion.keys()), list(mm_medallion.values()), k=1)[0] + if mm_medallion == 'Random': + mm_medallion = None if 'Turtle Rock' in custom_medallions: tr_medallion = custom_medallions['Turtle Rock'] + if isinstance(tr_medallion, dict): + tr_medallion = random.choices(list(tr_medallion.keys()), list(tr_medallion.values()), k=1)[0] + if tr_medallion == 'Random': + tr_medallion = None if not mm_medallion: mm_medallion = ['Ether', 'Quake', 'Bombos'][random.randint(0, 2)] if not tr_medallion: @@ -1261,31 +1269,86 @@ def fill_specific_items(world): for player, placement_list in placements.items(): for location, item in placement_list.items(): loc = world.get_location(location, player) - item_parts = item.split('#') - item_player = player if len(item_parts) < 2 else int(item_parts[1]) - item_name = item_parts[0] - event_flag = False - if is_dungeon_item(item_name, world, item_player): - item_to_place = next(x for x in dungeon_pool - if x.name == item_name and x.player == item_player) - dungeon_pool.remove(item_to_place) - event_flag = True - elif item_name in prize_set: - item_player = player # prizes must be for that player - item_to_place = ItemFactory(item_name, item_player) - prize_pool.remove(item_name) - event_flag = True - else: - item_to_place = next((x for x in world.itempool - if x.name == item_name and x.player == item_player), None) - if item_to_place is None: - item_to_place = ItemFactory(item_name, player) - else: - world.itempool.remove(item_to_place) - world.push_item(loc, item_to_place, False) - # track_outside_keys(item_to_place, spot_to_fill, world) - # track_dungeon_items(item_to_place, spot_to_fill, world) - loc.event = event_flag or item_to_place.advancement + item_to_place, event_flag = get_item_and_event_flag(item, world, player, + dungeon_pool, prize_set, prize_pool) + if item_to_place: + world.push_item(loc, item_to_place, False) + track_outside_keys(item_to_place, loc, world) + track_dungeon_items(item_to_place, loc, world) + loc.event = event_flag or item_to_place.advancement + advanced_placements = world.customizer.get_advanced_placements() + if advanced_placements: + for player, placement_list in advanced_placements.items(): + for placement in placement_list: + if placement['type'] == 'LocationGroup': + item = placement['item'] + item_to_place, event_flag = get_item_and_event_flag(item, world, player, + dungeon_pool, prize_set, prize_pool) + if not item_to_place: + continue + locations = placement['locations'] + handled = False + while not handled: + if isinstance(locations, dict): + chosen_loc = random.choices(list(locations.keys()), list(locations.values()), k=1)[0] + else: # if isinstance(locations, list): + chosen_loc = random.choice(locations) + if chosen_loc == 'Random': + if is_dungeon_item(item_to_place.name, world, item_to_place.player): + dungeon_pool.append(item_to_place) + elif item_to_place.name in prize_set: + prize_pool.append(item_to_place.name) + else: + world.itempool.append(item_to_place) + else: + loc = world.get_location(chosen_loc, player) + if loc.item: + continue + world.push_item(loc, item_to_place, False) + track_outside_keys(item_to_place, loc, world) + track_dungeon_items(item_to_place, loc, world) + loc.event = (event_flag or item_to_place.advancement + or item_to_place.bigkey or item_to_place.smallkey) + handled = True + elif placement['type'] == 'NotLocationGroup': + item = placement['item'] + item_parts = item.split('#') + item_player = player if len(item_parts) < 2 else int(item_parts[1]) + item_name = item_parts[0] + world.item_pool_config.restricted[(item_name, item_player)] = placement['locations'] + elif placement['type'] == 'PreferredLocationGroup': + item = placement['item'] + item_parts = item.split('#') + item_player = player if len(item_parts) < 2 else int(item_parts[1]) + item_name = item_parts[0] + world.item_pool_config.preferred[(item_name, item_player)] = placement['locations'] + + +def get_item_and_event_flag(item, world, player, dungeon_pool, prize_set, prize_pool): + item_parts = item.split('#') + item_player = player if len(item_parts) < 2 else int(item_parts[1]) + item_name = item_parts[0] + event_flag = False + if is_dungeon_item(item_name, world, item_player): + item_to_place = next(x for x in dungeon_pool + if x.name == item_name and x.player == item_player) + dungeon_pool.remove(item_to_place) + event_flag = True + elif item_name in prize_set: + item_player = player # prizes must be for that player + item_to_place = ItemFactory(item_name, item_player) + prize_pool.remove(item_name) + event_flag = True + else: + matcher = lambda x: x.name == item_name and x.player == item_player + if item_name == 'Bottle': + matcher = lambda x: x.name.startswith(item_name) and x.player == item_player + item_to_place = next((x for x in world.itempool if matcher(x)), None) + if item_to_place is None: + return None, event_flag + else: + world.itempool.remove(item_to_place) + return item_to_place, event_flag def is_dungeon_item(item, world, player): diff --git a/Items.py b/Items.py index da9d7385..76370548 100644 --- a/Items.py +++ b/Items.py @@ -83,7 +83,7 @@ item_table = {'Bow': (True, False, None, 0x0B, 200, 'You have\nchosen the\narche 'Arrows (5)': (False, False, None, 0x5A, 15, 'This will give\nyou five shots\nwith your bow!', 'and the arrow pack', 'stick-collecting kid', 'sewing kit for sale', 'fungus for arrows', 'archer boy sews again', 'five arrows'), 'Small Magic': (False, False, None, 0x45, 5, 'A bit of magic', 'and the bit of magic', 'bit-o-magic kid', 'magic bit for sale', 'fungus for magic', 'magic boy conjures again', 'a bit of magic'), 'Big Magic': (False, False, None, 0x5A, 40, 'A lot of magic', 'and lots of magic', 'lot-o-magic kid', 'magic refill for sale', 'fungus for magic', 'magic boy conjures again', 'a magic refill'), - 'Chicken': (False, False, None, 0x5A, 999, 'Cucco of Legend', 'and the legendary cucco', 'chicken kid', 'fried chicken for sale', 'fungus for chicken', 'cucco boy clucks again', 'a cucco'), + 'Chicken': (False, False, None, 0x5A, 5, 'Cucco of Legend', 'and the legendary cucco', 'chicken kid', 'fried chicken for sale', 'fungus for chicken', 'cucco boy clucks again', 'a cucco'), 'Bombs (3)': (False, False, None, 0x28, 15, 'I make things\ngo triple\nBOOM!!!', 'and the explosions', 'the bomb-holding kid', 'firecrackers for sale', 'blend fungus into bombs', '\'splosion boy explodes again', 'three bombs'), 'Bombs (10)': (False, False, None, 0x31, 50, 'I make things\ngo BOOM! Ten\ntimes!', 'and the explosions', 'the bomb-holding kid', 'firecrackers for sale', 'blend fungus into bombs', '\'splosion boy explodes again', 'ten bombs'), 'Bomb Upgrade (+10)': (False, False, None, 0x52, 100, 'Increase bomb\nstorage, low\nlow price', 'and the bomb bag', 'boom-enlarging kid', 'bomb boost for sale', 'the shroom goes boom', 'upgrade boy explodes more again', 'bomb capacity'), diff --git a/KeyDoorShuffle.py b/KeyDoorShuffle.py index 6d495aed..0a2ee5ac 100644 --- a/KeyDoorShuffle.py +++ b/KeyDoorShuffle.py @@ -301,10 +301,10 @@ def analyze_dungeon(key_layout, world, player): key_logic.bk_restricted.update(filter_big_chest(key_counter.free_locations)) # note to self: this is due to the enough_small_locations function in validate_key_layout_sub_loop # I don't like this exception here or there - elif available < possible_smalls and avail_bigs and non_big_locs > 0: - max_ctr = find_max_counter(key_layout) - bk_lockdown = [x for x in max_ctr.free_locations if x not in key_counter.free_locations] - key_logic.bk_restricted.update(filter_big_chest(bk_lockdown)) + # elif available < possible_smalls and avail_bigs and non_big_locs > 0: + # max_ctr = find_max_counter(key_layout) + # bk_lockdown = [x for x in max_ctr.free_locations if x not in key_counter.free_locations] + # key_logic.bk_restricted.update(filter_big_chest(bk_lockdown)) # try to relax the rules here? - smallest requirement that doesn't force a softlock child_queue = deque() for child in key_counter.child_doors.keys(): @@ -1489,7 +1489,7 @@ def validate_key_layout_sub_loop(key_layout, state, checked_states, flat_proposa # todo: allow more key shuffles - refine placement rules # if (not smalls_avail or available_small_locations == 0) and (state.big_key_opened or num_bigs == 0 or available_big_locations == 0): found_forced_bk = state.found_forced_bk() - smalls_done = not smalls_avail or not enough_small_locations(state, available_small_locations) + smalls_done = not smalls_avail # or not enough_small_locations(state, available_small_locations) bk_done = state.big_key_opened or num_bigs == 0 or (available_big_locations == 0 and not found_forced_bk) # prize door should not be opened if the boss is reachable - but not reached yet allow_for_prize_lock = (key_layout.prize_can_lock and diff --git a/Main.py b/Main.py index 68ef7583..8b239dbf 100644 --- a/Main.py +++ b/Main.py @@ -24,6 +24,7 @@ from RoomData import create_rooms from Rules import set_rules from Dungeons import create_dungeons from Fill import distribute_items_restrictive, promote_dungeon_items, fill_dungeons_restrictive, ensure_good_pots +from Fill import dungeon_tracking from Fill import sell_potions, sell_keys, balance_multiworld_progression, balance_money_progression, lock_shop_locations from ItemList import generate_itempool, difficulties, fill_prizes, customize_shops, fill_specific_items from Utils import output_path, parse_player_names @@ -69,9 +70,8 @@ def main(args, seed=None, fish=None): if args.customizer: customized = CustomSettings() customized.load_yaml(args.customizer) - seed = customized.determine_seed() - if seed: - seeded = True + seed = customized.determine_seed(seed) + seeded = True customized.adjust_args(args) world = World(args.multi, args.shuffle, args.door_shuffle, args.logic, args.mode, args.swords, args.difficulty, args.item_functionality, args.timer, args.progressive, args.goal, args.algorithm, @@ -89,6 +89,7 @@ def main(args, seed=None, fish=None): if args.securerandom: world.seed = ''.join(random.choice(string.ascii_uppercase + string.ascii_lowercase + string.digits) for _ in range(9)) + world.boots_hint = args.boots_hint.copy() world.remote_items = args.remote_items.copy() world.mapshuffle = args.mapshuffle.copy() world.compassshuffle = args.compassshuffle.copy() @@ -195,6 +196,16 @@ def main(args, seed=None, fish=None): item = ItemFactory(inv_item.strip(), p) if item: world.push_precollected(item) + if item.dungeon: + d = world.get_dungeon(item.dungeon, item.player) + match = next((i for i in d.all_items if i.name == item.name), None) + if match: + if match.map or match.compass: + d.dungeon_items.remove(match) + elif match.smallkey: + d.small_keys.remove(match) + elif match.bigkey: + d.big_key.remove(match) if args.print_custom_yaml: world.settings.record_info(world) @@ -258,6 +269,7 @@ def main(args, seed=None, fish=None): massage_item_pool(world) if args.print_custom_yaml: world.settings.record_item_pool(world) + dungeon_tracking(world) fill_specific_items(world) logger.info(world.fish.translate("cli", "cli", "placing.dungeon.prizes")) diff --git a/Rom.py b/Rom.py index 84560d46..f8b5b107 100644 --- a/Rom.py +++ b/Rom.py @@ -1084,9 +1084,14 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): rom.write_byte(0x178000 + i, random.randint(0, 255)) # shuffle prize packs - prizes = [0xD8, 0xD8, 0xD8, 0xD8, 0xD9, 0xD8, 0xD8, 0xD9, 0xDA, 0xD9, 0xDA, 0xDB, 0xDA, 0xD9, 0xDA, 0xDA, 0xE0, 0xDF, 0xDF, 0xDA, 0xE0, 0xDF, 0xD8, 0xDF, - 0xDC, 0xDC, 0xDC, 0xDD, 0xDC, 0xDC, 0xDE, 0xDC, 0xE1, 0xD8, 0xE1, 0xE2, 0xE1, 0xD8, 0xE1, 0xE2, 0xDF, 0xD9, 0xD8, 0xE1, 0xDF, 0xDC, 0xD9, 0xD8, - 0xD8, 0xE3, 0xE0, 0xDB, 0xDE, 0xD8, 0xDB, 0xE2, 0xD9, 0xDA, 0xDB, 0xD9, 0xDB, 0xD9, 0xDB] + prizes = [0xD8, 0xD8, 0xD8, 0xD8, 0xD9, 0xD8, 0xD8, 0xD9, + 0xDA, 0xD9, 0xDA, 0xDB, 0xDA, 0xD9, 0xDA, 0xDA, + 0xE0, 0xDF, 0xDF, 0xDA, 0xE0, 0xDF, 0xD8, 0xDF, + 0xDC, 0xDC, 0xDC, 0xDD, 0xDC, 0xDC, 0xDE, 0xDC, + 0xE1, 0xD8, 0xE1, 0xE2, 0xE1, 0xD8, 0xE1, 0xE2, + 0xDF, 0xD9, 0xD8, 0xE1, 0xDF, 0xDC, 0xD9, 0xD8, + 0xD8, 0xE3, 0xE0, 0xDB, 0xDE, 0xD8, 0xDB, 0xE2, + 0xD9, 0xDA, 0xDB, 0xD9, 0xDB, 0xD9, 0xDB] dig_prizes = [0xB2, 0xD8, 0xD8, 0xD8, 0xD8, 0xD8, 0xD8, 0xD8, 0xD8, 0xD9, 0xD9, 0xD9, 0xD9, 0xD9, 0xDA, 0xDA, 0xDA, 0xDA, 0xDA, 0xDB, 0xDB, 0xDB, 0xDB, 0xDB, 0xDC, 0xDC, 0xDC, 0xDC, 0xDC, @@ -1099,13 +1104,41 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): return [l[i:i+n] for i in range(0, len(l), n)] # randomize last 7 slots - prizes [-7:] = random.sample(prizes, 7) + possible_prizes = { + 'Small Heart': 0xD8, 'Fairy': 0xE3, + 'Rupee (1)': 0xD9, 'Rupees (5)': 0xDA, 'Rupees (20)': 0xDB, + 'Big Magic': 0xE0, 'Small Magic': 0xDF, + 'Single Bomb': 0xDC, 'Bombs (4)': 0xDD, + 'Bombs (8)': 0xDE, 'Arrows (5)': 0xE1, 'Arrows (10)': 0xE2 + } #weights, if desired 13, 1, 9, 7, 6, 3, 6, 7, 1, 2, 5, 3 + uniform_prizes = list(possible_prizes.values()) + prizes[-7:] = random.sample(prizes, 7) #shuffle order of 7 main packs packs = chunk(prizes[:56], 8) random.shuffle(packs) prizes[:56] = [drop for pack in packs for drop in pack] + if world.customizer: + drops = world.customizer.get_drops() + if drops: + for player, drop_config in drops.items(): + for pack_num in range(1, 8): + if f'Pack {pack_num}' in drop_config: + for prize, idx in enumerate(drop_config[f'Pack {pack_num}']): + chosen = random.choice(uniform_prizes) if prize == 'Random' else possible_prizes[prize] + prizes[(pack_num-1)*8 + idx] = chosen + for tree_pull_tier in range(1, 4): + if f'Tree Pull Tier {tree_pull_tier}' in drop_config: + prize = drop_config[f'Tree Pull Tier {tree_pull_tier}'] + chosen = random.choice(uniform_prizes) if prize == 'Random' else possible_prizes[prize] + prizes[63-tree_pull_tier] = chosen # (62 through 60 in reverse) + for key, pos in {'Crab Normal': 59, 'Crab Special': 58, 'Stun Prize': 57, 'Fish': 56}.items(): + if key in drop_config: + prize = drop_config[key] + chosen = random.choice(uniform_prizes) if prize == 'Random' else possible_prizes[prize] + prizes[pos] = chosen + if world.difficulty_adjustments[player] in ['hard', 'expert']: prize_replacements = {0xE0: 0xDF, # Fairy -> heart 0xE3: 0xD8} # Big magic -> small magic @@ -2290,7 +2323,24 @@ def write_strings(rom, world, player, team): if world.goal[player] in ['dungeons']: tt['sign_ganon'] = 'You need to complete all the dungeons.' - tt['uncle_leaving_text'] = Uncle_texts[random.randint(0, len(Uncle_texts) - 1)] + if world.boots_hint[player]: + starting_boots = next((i for i in world.precollected_items if i.player == player + and i.name == 'Pegasus Boots'), None) + if starting_boots: + uncle_text = 'Lonk! Boots\nare on\nyour feet.' + else: + boots_location = next((l for l in world.get_locations() + if l.player == player and l.item and l.item.name == 'Pegasus Boots'), None) + if boots_location: + district = next((d for k, d in world.districts[player].items() + if boots_location.name in d.locations), 'Zebes') + uncle_text = f'Lonk! Boots\nare in {district.name}' + else: + uncle_text = "I couldn't\nfind the Boots\ntoday.\nRIP me." + + tt['uncle_leaving_text'] = uncle_text + else: + tt['uncle_leaving_text'] = Uncle_texts[random.randint(0, len(Uncle_texts) - 1)] tt['end_triforce'] = "{NOBORDER}\n" + Triforce_texts[random.randint(0, len(Triforce_texts) - 1)] tt['bomb_shop_big_bomb'] = BombShop2_texts[random.randint(0, len(BombShop2_texts) - 1)] diff --git a/Rules.py b/Rules.py index fa07bd5a..9057ca68 100644 --- a/Rules.py +++ b/Rules.py @@ -2091,8 +2091,8 @@ def eval_small_key_door_main(state, door_name, dungeon, player): if ruleType == KeyRuleType.WorstCase: door_openable |= state.has_sm_key(key_logic.small_key_name, player, number) elif ruleType == KeyRuleType.AllowSmall: - if (door_rule.small_location.item and door_rule.small_location.item.name == key_logic.small_key_name - and door_rule.small_location.item.player == player): + small_loc_item = door_rule.small_location.item + if small_loc_item and small_loc_item.name == key_logic.small_key_name and small_loc_item.player == player: door_openable |= state.has_sm_key(key_logic.small_key_name, player, number) elif isinstance(ruleType, tuple): lock, lock_item = ruleType diff --git a/Text.py b/Text.py index 4da86b4c..bbd2697e 100644 --- a/Text.py +++ b/Text.py @@ -1716,7 +1716,7 @@ class TextTable(object): text['game_shooting_choice'] = CompressedTextMapper.convert("20 rupees.\n5 arrows.\nWin rupees!\nWant to play?\n ≥ Yes\n No\n{CHOICE}") text['game_shooting_yes'] = CompressedTextMapper.convert("Let's do this!") text['game_shooting_no'] = CompressedTextMapper.convert("Where are you going? Straight up!") - text['game_shooting_continue'] = CompressedTextMapper.convert("Keep playing?\n ≥ yes\n no\n{CHOICE}") + text['game_shooting_continue'] = CompressedTextMapper.convert("Keep playing?\n ≥ Yes\n No\n{CHOICE}") text['pond_of_wishing'] = CompressedTextMapper.convert("-Wishing Pond-\n\n On Vacation") text['pond_item_select'] = CompressedTextMapper.convert("Pick something\nto throw in.\n{ITEMSELECT}") text['pond_item_test'] = CompressedTextMapper.convert("You toss this?\n ≥ Yup\n Wrong\n{CHOICE}") diff --git a/docs/Customizer.md b/docs/Customizer.md index cb951fed..b95081bd 100644 --- a/docs/Customizer.md +++ b/docs/Customizer.md @@ -38,7 +38,7 @@ in each player section you can set up default settings for that player or you ca door_shuffle: basic ``` -Player 1's settings will be determined by rolling the mystery weights and player 2's setting will be default except for those two specified in his section. Each settings should be consistent with the CLI arguments. +Player 1's settings will be determined by rolling the mystery weights and player 2's setting will be default except for those two specified in his section. Each setting should be consistent with the CLI arguments. Simple weighted settings are supported here. If you need sub-weights though, use a separate yaml file. Start inventory is not supported here. It has a separate section. @@ -71,7 +71,21 @@ You may list each location for a player and the item you wish to place there. A Example: `Pegasus Boots#3` means the boots for player 3. - + + +### advanced_placements + +This must be defined by player. Each player number should be listed with the appropriate section. Each section is a list of placement rules. Each placement rule has a specific type. + +Supported Types: PlacementGroup, NotPlacmentGroup + +#### PlacementGroup + +You may define an item, and a list of locations. The locations may be weighted if desired. The item will be placed at one of the listed locations - this currently ignores logic. The item will be placed there. The special location 'Random' indicates that the item should be placed randomly, without any other consideration. This may be repeated for placement of multiple items like multiple bows or swords. + +#### NotPlacementGroup + +You may define an item and a list of locations that an item should not be placed at. This will apply to all items of that type. The logic is considered for this. If it is otherwise impossible, the item will be considered for the listed locations. This is important for small key layouts mostly, but it will try other locations first. ### entrances @@ -144,7 +158,7 @@ Misery Mire: Ether Turtle Rock: Quake ``` -Leave blank or omit if you wish it to be random. +Leave blank or omit if you wish it to be random. Alternatively, a weighted dictionary is supported and a 'Random' option ### bosses @@ -173,4 +187,27 @@ To start with multiple copies of progressive items, list them more than once. This conflicts with the mystery yaml, if specified. These start inventory items will be added after those are added. +### drops +This must be defined by player. You may have prize packs, tree pulls, crab drops, stun prizes, and the fish prize defined using the following keys: +``` +drops: + 1: + Pack 1 + - Small Heart + - Bombs (4) + - Random + - etc + Pack 2: (list) + ... + Pack 7: (list) + Tree Pull Tier 1: Single Bomb + Tree Pull Tier 2: Arrows (10) + Tree Pull Tier 3: Fairy + Crab Normal: Rupees (20) + Crab Special: Small Magic + Stun Prize: Bombs (8) + Fish: Big Magic +``` + +Prize packs expect a list of eight items each (anything not specified will be whatever randomization would have normally occurred). The special drops expect a single item. Packs 1 through 7 are supported. Prize pack 0 is not customizable. \ No newline at end of file diff --git a/docs/antivanilla.yaml b/docs/antivanilla.yaml new file mode 100644 index 00000000..38299e69 --- /dev/null +++ b/docs/antivanilla.yaml @@ -0,0 +1,1036 @@ +meta: + players: 1 +settings: + 1: + keysanity: True +advanced_placements: + 1: + - item: Green Pendant + locations: + - Eastern Palace - Prize + - Desert Palace - Prize + - Tower of Hera Palace - Prize + type: NotLocationGroup + - item: Blue Pendant + locations: + - Eastern Palace - Prize + - Desert Palace - Prize + - Tower of Hera Palace - Prize + type: NotLocationGroup + - item: Red Pendant + locations: + - Eastern Palace - Prize + - Desert Palace - Prize + - Tower of Hera Palace - Prize + type: NotLocationGroup + - item: Crystal 5 + locations: + - Ice Palace - Prize + - Misery Mire - Prize + type: NotLocationGroup + - item: Crystal 6 + locations: + - Ice Palace - Prize + - Misery Mire - Prize + type: NotLocationGroup + - item: Progressive Bow + locations: + - Eastern Palace - Big Chest + - Eastern Palace - Boss + - Eastern Palace - Cannonball Chest + - Eastern Palace - Big Key Chest + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + - Pyramid Fairy - Right + - Pyramid Fairy - Left + type: NotLocationGroup + - item: Book of Mudora + locations: + - Library + type: NotLocationGroup + - item: Hammer + locations: + - Palace of Darkness - Big Chest + - Palace of Darkness - Boss + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: NotLocationGroup + - item: Hookshot + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: NotLocationGroup + - item: Magic Mirror + locations: + - Old Man + type: NotLocationGroup + - item: Ocarina + locations: + - Flute Spot + type: NotLocationGroup + - item: Pegasus Boots + locations: + - Sahasrahla + type: NotLocationGroup + - item: Cape + locations: + - King's Tomb + type: NotLocationGroup + - item: Mushroom + locations: + - Mushroom + type: NotLocationGroup + - item: Shovel + locations: + - Stumpy + type: NotLocationGroup + - item: Lamp + locations: + - Link's House + - Secret Passage + - Zelda's Chest + type: NotLocationGroup + - item: Magic Powder + locations: + - Potion Shop + type: NotLocationGroup + - item: Moon Pearl + locations: + - Tower of Hera - Big Chest + - Tower of Hera - Boss + - Tower of Hera - Big Key Chest + - Tower of Hera - Compass Chest + - Tower of Hera - Map Chest + - Tower of Hera - Basement Cage + type: NotLocationGroup + - item: Cane of Somaria + locations: + - Misery Mire - Big Chest + - Misery Mire - Boss + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: NotLocationGroup + - item: Fire Rod + locations: + - Skull Woods - Big Chest + - Skull Woods - Boss + - Skull Woods - Big Key Chest + - Skull Woods - Compass Chest + - Skull Woods - Map Chest + - Skull Woods - Bridge Room + - Skull Woods - Pinball Room + - Skull Woods - Pot Prison + type: NotLocationGroup + - item: Flippers + locations: + - King Zora + type: NotLocationGroup + - item: Ice Rod + locations: + - Ice Rod Cave + type: NotLocationGroup + - item: Bombos + locations: + - Bombos Tablet + type: NotLocationGroup + - item: Ether + locations: + - Ether Tablet + type: NotLocationGroup + - item: Quake + locations: + - Catfish + type: NotLocationGroup + - item: Bottle + locations: + - Bottle Merchant + - Kakariko Tavern + - Purple Chest + - Hobo + type: NotLocationGroup + - item: Progressive Sword + locations: + - Link's Uncle + - Secret Passage + - Blacksmith + - Master Sword Pedestal + - Pyramid Fairy - Left + - Pyramid Fairy - Right + type: NotLocationGroup + - item: Progressive Glove + locations: + - Desert Palace - Big Chest + - Desert Palace - Boss + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + - Thieves' Town - Big Chest + - Thieves' Town - Boss + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Blind's Cell + - Thieves' Town - Ambush Chest + - Thieves' Town - Attic + type: NotLocationGroup + - item: Silver Arrows + locations: + - Pyramid Fairy - Right + - Pyramid Fairy - Left + type: NotLocationGroup + - item: Single Arrow + locations: + - Palace of Darkness - Dark Basement - Left + type: NotLocationGroup + - item: Arrows (10) + locations: + - Chicken House + - Mini Moldorm Cave - Far Right + - Sewers - Secret Room - Right + - Paradox Cave Upper - Right + - Mire Shed - Right + - Ganons Tower - Hope Room - Left + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + type: NotLocationGroup + - item: Bombs (3) + locations: + - Floodgate Chest + - Sahasrahla's Hut - Middle + - Kakariko Well - Bottom + - Superbunny Cave - Top + - Mini Moldorm Cave - Far Left + - Sewers - Secret Room - Left + - Paradox Cave Upper - Left + - Thieves' Town - Attic + - Ice Palace - Freezor Chest + - Palace of Darkness - Dark Maze - Top + - Ganons Tower - Hope Room - Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + type: NotLocationGroup + - item: Progressive Armor + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + - Ganons Tower - Big Chest + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: NotLocationGroup + - item: Blue Boomerang + locations: + - Hyrule Castle - Boomerang Chest + type: NotLocationGroup + - item: Red Boomerang + locations: + - Waterfall Fairy - Left + - Waterfall Fairy - Right + type: NotLocationGroup + - item: Progressive Shield + locations: + - Link's Uncle + - Secret Passage + - Waterfall Fairy - Right + - Waterfall Fairy - Left + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + type: NotLocationGroup + - item: Bug Catching Net + locations: + - Sick Kid + type: NotLocationGroup + - item: Cane of Byrna + locations: + - Spike Cave + type: NotLocationGroup + - item: Boss Heart Container + locations: + - Desert Palace - Boss + - Eastern Palace - Boss + - Tower of Hera - Boss + - Swamp Palace - Boss + - Thieves' Town - Boss + - Skull Woods - Boss + - Ice Palace - Boss + - Misery Mire - Boss + - Turtle Rock - Boss + - Palace of Darkness - Boss + - Sanctuary + type: NotLocationGroup + - item: Sanctuary Heart Container + locations: + - Desert Palace - Boss + - Eastern Palace - Boss + - Tower of Hera - Boss + - Swamp Palace - Boss + - Thieves' Town - Boss + - Skull Woods - Boss + - Ice Palace - Boss + - Misery Mire - Boss + - Turtle Rock - Boss + - Palace of Darkness - Boss + - Sanctuary + type: NotLocationGroup + - item: Piece of Heart + locations: + - Sunken Treasure + - Blind's Hideout - Top + - Zora's Ledge + - Aginah's Cave + - Maze Race + - Kakariko Well - Top + - Lost Woods Hideout + - Lumberjack Tree + - Cave 45 + - Graveyard Cave + - Checkerboard Cave + - Bonk Rock Cave + - Lake Hylia Island + - Desert Ledge + - Spectacle Rock + - Spectacle Rock Cave + - Pyramid + - Digging Game + - Peg Cave + - Chest Game + - Bumper Cave Ledge + - Mire Shed - Left + - Floating Island + - Mimic Cave + type: NotLocationGroup + - item: Rupee (1) + locations: + - Turtle Rock - Eye Bridge - Top Right + - Ganons Tower - Compass Room - Top Right + type: NotLocationGroup + - item: Rupees (5) + locations: + - Hyrule Castle - Zelda's Chest + - Turtle Rock - Eye Bridge - Top Left + - Palace of Darkness - Dark Maze - Bottom + - Ganons Tower - Validation Chest + type: NotLocationGroup + - item: Rupees (20) + locations: + - Blind's Hideout - Left + - Blind's Hideout - Right + - Blind's Hideout - Far Left + - Blind's Hideout - Far Right + - Kakariko Well - Left + - Kakariko Well - Middle + - Kakariko Well - Right + - Mini Moldorm Cave - Left + - Mini Moldorm Cave - Right + - Paradox Cave Lower - Far Left + - Paradox Cave Lower - Left + - Paradox Cave Lower - Right + - Paradox Cave Lower - Far Right + - Paradox Cave Lower - Middle + - Hype Cave - Top + - Hype Cave - Middle Right + - Hype Cave - Middle Left + - Hype Cave - Bottom + - Swamp Palace - West Chest + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Waterfall Room + - Swamp Palace - Flooded Room - Right + - Thieves' Town - Ambush Chest + - Turtle Rock - Eye Bridge - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Swamp Palace - Flooded Room - Right + - Thieves' Town - Ambush Chest + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + type: NotLocationGroup + - item: Rupees (50) + locations: + - Sahasrahla's Hut - Left + - Sahasrahla's Hut - Right + - Spiral Cave + - Superbunny Cave - Bottom + - Hookshot Cave - Top Right + - Hookshot Cave - Top Left + - Hookshot Cave - Bottom Right + - Hookshot Cave - Bottom Left + type: NotLocationGroup + - item: Rupees (100) + locations: + - Eastern Palace - Cannonball Chest + type: NotLocationGroup + - item: Rupees (300) + locations: + - Mini Moldorm Cave - Generous Guy + - Sewers - Secret Room - Middle + - Hype Cave - Generous Guy + - Brewery + - C-Shaped House + type: NotLocationGroup + - item: Magic Upgrade (1/2) + locations: + - Magic Bat + type: NotLocationGroup + - item: Big Key (Eastern Palace) + locations: + - Eastern Palace - Big Chest + - Eastern Palace - Boss + - Eastern Palace - Cannonball Chest + - Eastern Palace - Big Key Chest + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + type: NotLocationGroup + - item: Compass (Eastern Palace) + locations: + - Eastern Palace - Big Chest + - Eastern Palace - Boss + - Eastern Palace - Cannonball Chest + - Eastern Palace - Big Key Chest + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + type: NotLocationGroup + - item: Map (Eastern Palace) + locations: + - Eastern Palace - Big Chest + - Eastern Palace - Boss + - Eastern Palace - Cannonball Chest + - Eastern Palace - Big Key Chest + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + type: NotLocationGroup + - item: Small Key (Desert Palace) + locations: + - Desert Palace - Big Chest + - Desert Palace - Boss + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + type: NotLocationGroup + - item: Big Key (Desert Palace) + locations: + - Desert Palace - Big Chest + - Desert Palace - Boss + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + type: NotLocationGroup + - item: Compass (Desert Palace) + locations: + - Desert Palace - Big Chest + - Desert Palace - Boss + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + type: NotLocationGroup + - item: Map (Desert Palace) + locations: + - Desert Palace - Big Chest + - Desert Palace - Boss + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + type: NotLocationGroup + - item: Small Key (Tower of Hera) + locations: + - Tower of Hera - Big Chest + - Tower of Hera - Boss + - Tower of Hera - Big Key Chest + - Tower of Hera - Compass Chest + - Tower of Hera - Map Chest + - Tower of Hera - Basement Cage + type: NotLocationGroup + - item: Big Key (Tower of Hera) + locations: + - Tower of Hera - Big Chest + - Tower of Hera - Boss + - Tower of Hera - Big Key Chest + - Tower of Hera - Compass Chest + - Tower of Hera - Map Chest + - Tower of Hera - Basement Cage + type: NotLocationGroup + - item: Compass (Tower of Hera) + locations: + - Tower of Hera - Big Chest + - Tower of Hera - Boss + - Tower of Hera - Big Key Chest + - Tower of Hera - Compass Chest + - Tower of Hera - Map Chest + - Tower of Hera - Basement Cage + type: NotLocationGroup + - item: Map (Tower of Hera) + locations: + - Tower of Hera - Big Chest + - Tower of Hera - Boss + - Tower of Hera - Big Key Chest + - Tower of Hera - Compass Chest + - Tower of Hera - Map Chest + - Tower of Hera - Basement Cage + type: NotLocationGroup + - item: Small Key (Escape) + locations: + - Hyrule Castle - Map Chest + - Hyrule Castle - Boomerang Chest + - Hyrule Castle - Zelda's Chest + - Sewers - Dark Cross + - Sewers - Secret Room - Middle + - Sewers - Secret Room - Right + - Sewers - Secret Room - Left + - Sanctuary + type: NotLocationGroup + - item: Map (Escape) + locations: + - Hyrule Castle - Map Chest + - Hyrule Castle - Boomerang Chest + - Hyrule Castle - Zelda's Chest + - Sewers - Dark Cross + - Sewers - Secret Room - Middle + - Sewers - Secret Room - Right + - Sewers - Secret Room - Left + - Sanctuary + type: NotLocationGroup + - item: Small Key (Agahnims Tower) + locations: + - Castle Tower - Room 03 + - Castle Tower - Dark Maze + type: NotLocationGroup + - item: Small Key (Palace of Darkness) + locations: + - Palace of Darkness - Big Chest + - Palace of Darkness - Boss + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: NotLocationGroup + - item: Big Key (Palace of Darkness) + locations: + - Palace of Darkness - Big Chest + - Palace of Darkness - Boss + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: NotLocationGroup + - item: Compass (Palace of Darkness) + locations: + - Palace of Darkness - Big Chest + - Palace of Darkness - Boss + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: NotLocationGroup + - item: Map (Palace of Darkness) + locations: + - Palace of Darkness - Big Chest + - Palace of Darkness - Boss + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: NotLocationGroup + - item: Small Key (Thieves Town) + locations: + - Thieves' Town - Big Chest + - Thieves' Town - Boss + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Blind's Cell + - Thieves' Town - Ambush Chest + - Thieves' Town - Attic + type: NotLocationGroup + - item: Big Key (Thieves Town) + locations: + - Thieves' Town - Big Chest + - Thieves' Town - Boss + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Blind's Cell + - Thieves' Town - Ambush Chest + - Thieves' Town - Attic + type: NotLocationGroup + - item: Compass (Thieves Town) + locations: + - Thieves' Town - Big Chest + - Thieves' Town - Boss + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Blind's Cell + - Thieves' Town - Ambush Chest + - Thieves' Town - Attic + type: NotLocationGroup + - item: Map (Thieves Town) + locations: + - Thieves' Town - Big Chest + - Thieves' Town - Boss + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Blind's Cell + - Thieves' Town - Ambush Chest + - Thieves' Town - Attic + type: NotLocationGroup + - item: Small Key (Skull Woods) + locations: + - Skull Woods - Big Chest + - Skull Woods - Boss + - Skull Woods - Big Key Chest + - Skull Woods - Compass Chest + - Skull Woods - Map Chest + - Skull Woods - Bridge Room + - Skull Woods - Pinball Room + - Skull Woods - Pot Prison + type: NotLocationGroup + - item: Big Key (Skull Woods) + locations: + - Skull Woods - Big Chest + - Skull Woods - Boss + - Skull Woods - Big Key Chest + - Skull Woods - Compass Chest + - Skull Woods - Map Chest + - Skull Woods - Bridge Room + - Skull Woods - Pinball Room + - Skull Woods - Pot Prison + type: NotLocationGroup + - item: Compass (Skull Woods) + locations: + - Skull Woods - Big Chest + - Skull Woods - Boss + - Skull Woods - Big Key Chest + - Skull Woods - Compass Chest + - Skull Woods - Map Chest + - Skull Woods - Bridge Room + - Skull Woods - Pinball Room + - Skull Woods - Pot Prison + type: NotLocationGroup + - item: Map (Skull Woods) + locations: + - Skull Woods - Big Chest + - Skull Woods - Boss + - Skull Woods - Big Key Chest + - Skull Woods - Compass Chest + - Skull Woods - Map Chest + - Skull Woods - Bridge Room + - Skull Woods - Pinball Room + - Skull Woods - Pot Prison + type: NotLocationGroup + - item: Small Key (Swamp Palace) + locations: + - Swamp Palace - Entrance + type: NotLocationGroup + - item: Big Key (Swamp Palace) + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: NotLocationGroup + - item: Compass (Swamp Palace) + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: NotLocationGroup + - item: Map (Swamp Palace) + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: NotLocationGroup + - item: Small Key (Ice Palace) + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + type: NotLocationGroup + - item: Big Key (Ice Palace) + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + type: NotLocationGroup + - item: Compass (Ice Palace) + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + type: NotLocationGroup + - item: Map (Ice Palace) + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + type: NotLocationGroup + - item: Small Key (Misery Mire) + locations: + - Misery Mire - Big Chest + - Misery Mire - Boss + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: NotLocationGroup + - item: Big Key (Misery Mire) + locations: + - Misery Mire - Big Chest + - Misery Mire - Boss + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: NotLocationGroup + - item: Compass (Misery Mire) + locations: + - Misery Mire - Big Chest + - Misery Mire - Boss + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: NotLocationGroup + - item: Map (Misery Mire) + locations: + - Misery Mire - Big Chest + - Misery Mire - Boss + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: NotLocationGroup + - item: Small Key (Turtle Rock) + locations: + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + type: NotLocationGroup + - item: Big Key (Turtle Rock) + locations: + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + type: NotLocationGroup + - item: Compass (Turtle Rock) + locations: + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + type: NotLocationGroup + - item: Map (Turtle Rock) + locations: + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + type: NotLocationGroup + - item: Small Key (Ganons Tower) + locations: + - Ganons Tower - Big Chest + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: NotLocationGroup + - item: Big Key (Ganons Tower) + locations: + - Ganons Tower - Big Chest + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: NotLocationGroup + - item: Compass (Ganons Tower) + locations: + - Ganons Tower - Big Chest + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: NotLocationGroup + - item: Map (Ganons Tower) + locations: + - Ganons Tower - Big Chest + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: NotLocationGroup + diff --git a/docs/avianart/antivrosia.yaml b/docs/avianart/antivrosia.yaml new file mode 100644 index 00000000..3c213c83 --- /dev/null +++ b/docs/avianart/antivrosia.yaml @@ -0,0 +1,41 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + mode: inverted + mapshuffle: True + keyshuffle: wild +placements: + 1: + Link's Uncle: Progressive Sword + Blacksmith: Progressive Sword + Master Sword Pedestal: Progressive Sword + Pyramid Fairy - Left: Progressive Sword + Desert Palace - Boss: Compass (Desert Palace) + Eastern Palace - Boss: Compass (Eastern Palace) + Tower of Hera - Boss: Compass (Tower of Hera) + Swamp Palace - Boss: Compass (Swamp Palace) + Thieves' Town - Boss: Compass (Thieves Town) + Skull Woods - Boss: Compass (Skull Woods) + Ice Palace - Boss: Compass (Ice Palace) + Misery Mire - Boss: Compass (Misery Mire) + Turtle Rock - Boss: Compass (Turtle Rock) + Palace of Darkness - Boss: Compass (Palace of Darkness) + Eastern Palace - Big Key Chest: Big Key (Eastern Palace) + Desert Palace - Big Key Chest: Big Key (Desert Palace) + Tower of Hera - Big Key Chest: Big Key (Tower of Hera) + Palace of Darkness - Big Key Chest: Big Key (Palace of Darkness) + Thieves' Town - Big Key Chest: Big Key (Thieves Town) + Skull Woods - Big Key Chest: Big Key (Skull Woods) + Swamp Palace - Big Key Chest: Big Key (Swamp Palace) + Ice Palace - Big Key Chest: Big Key (Ice Palace) + Misery Mire - Big Key Chest: Big Key (Misery Mire) + Turtle Rock - Big Key Chest: Big Key (Turtle Rock) + Ganons Tower - Big Key Chest: Big Key (Ganons Tower) +start_inventory: + 1: + - Ocarina (Activated) + + + diff --git a/docs/avianart/invertacrismiser.yaml b/docs/avianart/invertacrismiser.yaml new file mode 100644 index 00000000..d7ff34ff --- /dev/null +++ b/docs/avianart/invertacrismiser.yaml @@ -0,0 +1,73 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + mode: inverted + goal: dungeons + shuffleenemies: shuffled + shufflebosses: full +item_pool: + 1: + Progressive Bow: 8 + Blue Boomerang: 4 + Red Boomerang: 4 + Hookshot: 4 + Magic Powder: 4 + Mushroom: 4 + Ice Rod: 4 + Fire Rod: 4 + Bombos: 4 + Ether: 4 + Quake: 4 + Lamp: 4 + Hammer: 4 + Ocarina: 4 + Shovel: 4 + Bug Catching Net: 4 + Book of Mudora: 4 + Bottle (Random): 16 + Cane of Byrna: 4 + Cane of Somaria: 4 + Cape: 4 + Magic Mirror: 4 + Flippers: 4 + Moon Pearl: 4 + Pegasus Boots: 4 + Progressive Glove: 8 + Progressive Armor: 8 + Progressive Shield: 12 + Progressive Sword: 16 + Magic Upgrade (1/2): 4 +start_inventory: + 1: + - Boss Heart Container + - Boss Heart Container + - Boss Heart Container + - Pegasus Boots + - Rupees (5) + - Rupees (5) + - Rupees (5) + - Rupee (1) + - Rupee (1) + - Rupee (1) + - Rupee (1) + - Compass (Desert Palace) + - Compass (Eastern Palace) + - Compass (Tower of Hera) + - Compass (Swamp Palace) + - Compass (Thieves Town) + - Compass (Skull Woods) + - Compass (Ice Palace) + - Compass (Misery Mire) + - Compass (Turtle Rock) + - Compass (Palace of Darkness) + - Compass (Ganons Tower) +drops: + 1: + Tree Pull Tier 1: Single Bomb + Tree Pull Tier 2: Bombs (4) + Tree Pull Tier 3: Bombs (8) + Crab Normal: Rupees (20) + Crab Special: Big Magic + Stun Prize: Rupees (20) diff --git a/docs/avianart/is_this_even_randomized.yaml b/docs/avianart/is_this_even_randomized.yaml new file mode 100644 index 00000000..8d863069 --- /dev/null +++ b/docs/avianart/is_this_even_randomized.yaml @@ -0,0 +1,443 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + mode: + open: 1 + standard: 1 + mapshuffle: True + compassshuffle: True + boots_hint: + True: 1 + False: 1 +advanced_placements: + 1: + - item: Green Pendant + locations: + - Eastern Palace - Prize + - Random + type: LocationGroup + - item: Crystal 5 + locations: + - Ice Palace - Prize + - Random + type: LocationGroup + - item: Crystal 6 + locations: + - Misery Mire - Prize + - Random + type: LocationGroup + - item: Progressive Bow + locations: + - Eastern Palace - Big Chest + - Random + type: LocationGroup + - item: Progressive Bow + locations: + - Pyramid Fairy - Right + - Random + type: LocationGroup + - item: Book of Mudora + locations: + - Library + - Random + type: LocationGroup + - item: Hammer + locations: + - Palace of Darkness - Big Chest + - Random + type: LocationGroup + - item: Hookshot + locations: + - Swamp Palace - Big Chest + - Random + type: LocationGroup + - item: Magic Mirror + locations: + - Old Man + - Random + type: LocationGroup + - item: Ocarina + locations: + - Flute Spot + - Random + type: LocationGroup + - item: Pegasus Boots + locations: + - Sahasrahla + - Random + type: LocationGroup + - item: Cape + locations: + - King's Tomb + - Random + type: LocationGroup + - item: Mushroom + locations: + - Mushroom + - Random + type: LocationGroup + - item: Shovel + locations: + - Stumpy + - Random + type: LocationGroup + - item: Lamp + locations: + Link's House: 1 + Secret Passage: 1 + Hyrule Castle - Zelda's Chest: 1 + Random: 3 + type: LocationGroup + - item: Magic Powder + locations: + - Potion Shop + - Random + type: LocationGroup + - item: Moon Pearl + locations: + - Tower of Hera - Big Chest + - Random + type: LocationGroup + - item: Cane of Somaria + locations: + - Misery Mire - Big Chest + - Random + type: LocationGroup + - item: Fire Rod + locations: + - Skull Woods - Big Chest + - Random + type: LocationGroup + - item: Flippers + locations: + - King Zora + - Random + type: LocationGroup + - item: Ice Rod + locations: + - Ice Rod Cave + - Random + type: LocationGroup + - item: Bombos + locations: + - Bombos Tablet + - Random + type: LocationGroup + - item: Ether + locations: + - Ether Tablet + - Random + type: LocationGroup + - item: Quake + locations: + - Catfish + - Random + type: LocationGroup + - item: Bottle + locations: + - Bottle Merchant + - Random + type: LocationGroup + - item: Bottle + locations: + - Kakariko Tavern + - Random + type: LocationGroup + - item: Bottle + locations: + - Purple Chest + - Random + type: LocationGroup + - item: Bottle + locations: + - Hobo + - Random + type: LocationGroup + - item: Progressive Sword + locations: + - Link's Uncle + - Random + type: LocationGroup + - item: Progressive Sword + locations: + - Blacksmith + - Random + type: LocationGroup + - item: Progressive Sword + locations: + - Master Sword Pedestal + - Random + type: LocationGroup + - item: Progressive Sword + locations: + - Pyramid Fairy - Left + - Random + type: LocationGroup + - item: Progressive Glove + locations: + - Desert Palace - Big Chest + - Random + type: LocationGroup + - item: Progressive Glove + locations: + - Thieves' Town - Big Chest + - Random + type: LocationGroup + - item: Progressive Armor + locations: + - Ice Palace - Big Chest + - Random + type: LocationGroup + - item: Progressive Armor + locations: + - Ganons Tower - Big Chest + - Random + type: LocationGroup + - item: Blue Boomerang + locations: + - Hyrule Castle - Boomerang Chest + - Random + type: LocationGroup + - item: Red Boomerang + locations: + - Waterfall Fairy - Left + - Random + type: LocationGroup + - item: Progressive Shield + locations: + - Secret Passage + - Random + type: LocationGroup + - item: Progressive Shield + locations: + - Waterfall Fairy - Right + - Random + type: LocationGroup + - item: Progressive Shield + locations: + - Turtle Rock - Big Chest + - Random + type: LocationGroup + - item: Bug Catching Net + locations: + - Sick Kid + - Random + type: LocationGroup + - item: Cane of Byrna + locations: + - Spike Cave + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Desert Palace - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Eastern Palace - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Tower of Hera - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Swamp Palace - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Thieves' Town - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Skull Woods - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Ice Palace - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Misery Mire - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Turtle Rock - Boss + - Random + type: LocationGroup + - item: Boss Heart Container + locations: + - Palace of Darkness - Boss + - Random + type: LocationGroup + - item: Sanctuary Heart Container + locations: + - Sanctuary + - Random + type: LocationGroup + - item: Rupees (300) + locations: + - Mini Moldorm Cave - Generous Guy + - Random + type: LocationGroup + - item: Rupees (300) + locations: + - Sewers - Secret Room - Middle + - Random + type: LocationGroup + - item: Rupees (300) + locations: + - Hype Cave - Generous Guy + - Random + type: LocationGroup + - item: Rupees (300) + locations: + - Brewery + - Random + type: LocationGroup + - item: Rupees (300) + locations: + - C-Shaped House + - Random + type: LocationGroup + - item: Magic Upgrade (1/2) + locations: + - Magic Bat + - Random + type: LocationGroup + - item: Compass (Eastern Palace) + locations: + - Eastern Palace - Compass Chest + - Random + type: LocationGroup + - item: Map (Eastern Palace) + locations: + - Eastern Palace - Map Chest + - Random + type: LocationGroup + - item: Compass (Desert Palace) + locations: + - Desert Palace - Compass Chest + - Random + type: LocationGroup + - item: Map (Desert Palace) + locations: + - Desert Palace - Map Chest + - Random + type: LocationGroup + - item: Compass (Tower of Hera) + locations: + - Tower of Hera - Compass Chest + - Random + type: LocationGroup + - item: Map (Tower of Hera) + locations: + - Tower of Hera - Map Chest + - Random + type: LocationGroup + - item: Map (Escape) + locations: + - Hyrule Castle - Map Chest + - Random + type: LocationGroup + - item: Compass (Palace of Darkness) + locations: + - Palace of Darkness - Compass Chest + - Random + type: LocationGroup + - item: Map (Palace of Darkness) + locations: + - Palace of Darkness - Map Chest + - Random + type: LocationGroup + - item: Compass (Thieves Town) + locations: + - Thieves' Town - Compass Chest + - Random + type: LocationGroup + - item: Map (Thieves Town) + locations: + - Thieves' Town - Map Chest + - Random + type: LocationGroup + - item: Compass (Skull Woods) + locations: + - Skull Woods - Compass Chest + - Random + type: LocationGroup + - item: Map (Skull Woods) + locations: + - Skull Woods - Map Chest + - Random + type: LocationGroup + - item: Compass (Swamp Palace) + locations: + - Swamp Palace - Compass Chest + - Random + type: LocationGroup + - item: Map (Swamp Palace) + locations: + - Swamp Palace - Map Chest + - Random + type: LocationGroup + - item: Compass (Ice Palace) + locations: + - Ice Palace - Compass Chest + - Random + type: LocationGroup + - item: Map (Ice Palace) + locations: + - Ice Palace - Map Chest + - Random + type: LocationGroup + - item: Compass (Misery Mire) + locations: + - Misery Mire - Compass Chest + - Random + type: LocationGroup + - item: Map (Misery Mire) + locations: + - Misery Mire - Map Chest + - Random + type: LocationGroup + - item: Compass (Turtle Rock) + locations: + - Turtle Rock - Compass Chest + - Random + type: LocationGroup + - item: Map (Turtle Rock) + locations: + - Turtle Rock - Roller Room - Left + - Random + type: LocationGroup + - item: Compass (Ganons Tower) + locations: + - Ganons Tower - Compass Room - Top Left + - Random + type: LocationGroup + - item: Map (Ganons Tower) + locations: + - Ganons Tower - Map Chest + - Random + type: LocationGroup +medallions: + 1: + Misery Mire: + Ether: 1 + Random: 1 + Turtle Rock: + Quake: 1 + Random: 1 + + + diff --git a/docs/avianart/true_pot_hunt.yaml b/docs/avianart/true_pot_hunt.yaml new file mode 100644 index 00000000..808a0c58 --- /dev/null +++ b/docs/avianart/true_pot_hunt.yaml @@ -0,0 +1,21 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + goal: triforcehunt + shuffle: crossed + keysanity: True + shopsanity: True + keydropshuffle: True + pottery: lottery + dungeon_counters: 'on' + triforce_goal: 420 + triforce_pool: 420 +start_inventory: + 1: + - Pegasus Boots + - Lamp + - Rupees (300) + - Rupees (100) + - Rupees (20) \ No newline at end of file diff --git a/docs/avianart/truest_pot_hunt.yaml b/docs/avianart/truest_pot_hunt.yaml new file mode 100644 index 00000000..bd6f8edc --- /dev/null +++ b/docs/avianart/truest_pot_hunt.yaml @@ -0,0 +1,21 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + goal: triforcehunt + shuffle: crossed + keysanity: True + shopsanity: True + keydropshuffle: True + pottery: lottery + dungeon_counters: 'on' + triforce_goal: 213 + triforce_pool: 420 +start_inventory: + 1: + - Pegasus Boots + - Lamp + - Rupees (300) + - Rupees (100) + - Rupees (20) \ No newline at end of file diff --git a/docs/avianart/why_is_that_there.yaml b/docs/avianart/why_is_that_there.yaml new file mode 100644 index 00000000..c69a5652 --- /dev/null +++ b/docs/avianart/why_is_that_there.yaml @@ -0,0 +1,259 @@ +meta: + algorithm: balanced + players: 1 +settings: + 1: + bigkeyshuffle: True +placements: + 1: + Potion Shop: Shovel + Flute Spot: Magic Powder +advanced_placements: + 1: + - item: Progressive Bow + locations: + - Palace of Darkness - Boss + - Palace of Darkness - Map Chest + - Palace of Darkness - The Arena - Ledge + - Eastern Palace - Boss + - Ganons Tower - Pre-Moldorm Chest + - Ganons Tower - Mini Helmasaur Room - Left + - Ganons Tower - Mini Helmasaur Room - Right + - Ganons Tower - Validation Chest + type: LocationGroup + - item: Fire Rod + locations: + - Ice Palace - Big Chest + - Ice Palace - Boss + - Ice Palace - Big Key Chest + - Ice Palace - Compass Chest + - Ice Palace - Map Chest + - Ice Palace - Spike Room + - Ice Palace - Iced T Room + - Ice Palace - Freezor Chest + - Desert Palace - Boss + - Tower of Hera - Big Key Chest + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + type: LocationGroup + - item: Pegasus Boots + locations: + - Hookshot Cave - Top Right + - Hookshot Cave - Top Left + - Hookshot Cave - Bottom Right + - Hookshot Cave - Bottom Left + - Mushroom Spot + - Zora Ledge + - Bombos Tablet + - Ether Tablet + - Floating Island + - Lake Hylia Island + - Maze Race + - Spectacle Rock + - Spectacle Rock Cave + - Pyramid + - Desert Ledge + - Bumper Cave Ledge + type: LocationGroup + - item: Progressive Sword + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: LocationGroup + - item: Titans Mitts + locations: + - Swamp Palace - Big Chest + - Swamp Palace - Boss + - Swamp Palace - Big Key Chest + - Swamp Palace - Compass Chest + - Swamp Palace - Map Chest + - Swamp Palace - Entrance + - Swamp Palace - Flooded Room - Left + - Swamp Palace - Flooded Room - Right + - Swamp Palace - Waterfall Room + - Swamp Palace - West Chest + type: LocationGroup + - item: Ice Rod + type: LocationGroup + locations: + - Turtle Rock - Big Chest + - Turtle Rock - Boss + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Crystaroller Room + - Turtle Rock - Roller Room - Right + - Turtle Rock - Eye Bridge - Bottom Left + - Turtle Rock - Eye Bridge - Bottom Right + - Turtle Rock - Eye Bridge - Top Left + - Turtle Rock - Eye Bridge - Top Right + - Mimic Cave + - Link's House + - Link's Uncle + - Secret Passage + - Hyrule Castle - Map Chest + - Sanctuary + - Mushroom Spot + - Lost Woods Hideout + - Blind's Hideout - Left + - Blind's Hideout - Right + - Blind's Hideout - Far Left + - Blind's Hideout - Far Right + - Blind's Hideout - Top + - Kakariko Well - Right + - Kakariko Well - Left + - Kakariko Well - Middle + - Kakariko Well - Top + - Kakariko Well - Bottom + - Chicken House + - Bottle Merchant + - Kakariko Tavern + - Maze Race + - Floodgate Chest + - Sunken Treasure + - Mini Moldorm Cave - Left + - Mini Moldorm Cave - Right + - Mini Moldorm Cave - Generous Guy + - Mini Moldorm Cave - Far Left + - Mini Moldorm Cave - Far Right + - Sahasrahla's Hut - Middle + - Sahasrahla's Hut - Right + - Sahasrahla's Hut - Left + - Ice Rod Cave + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + - Eastern Palace - Cannonball Chest + - Aginah's Cave + - item: Big Key (Eastern Palace) + locations: + - Eastern Palace - Cannonball Chest + - Eastern Palace - Big Key Chest + - Eastern Palace - Compass Chest + - Eastern Palace - Map Chest + type: LocationGroup + - item: Big Key (Desert Palace) + locations: + - Desert Palace - Big Key Chest + - Desert Palace - Compass Chest + - Desert Palace - Map Chest + - Desert Palace - Torch + type: LocationGroup + - item: Big Key (Palace of Darkness) + locations: + - Palace of Darkness - Big Key Chest + - Palace of Darkness - Compass Chest + - Palace of Darkness - Map Chest + - Palace of Darkness - Stalfos Basement + - Palace of Darkness - Dark Basement - Right + - Palace of Darkness - Harmless Hellway + - Palace of Darkness - Shooter Room + - Palace of Darkness - The Arena - Bridge + - Palace of Darkness - The Arena - Ledge + - Palace of Darkness - Dark Basement - Left + - Palace of Darkness - Dark Maze - Bottom + - Palace of Darkness - Dark Maze - Top + type: LocationGroup + - item: Big Key (Thieves Town) + locations: + - Thieves' Town - Big Key Chest + - Thieves' Town - Compass Chest + - Thieves' Town - Map Chest + - Thieves' Town - Ambush Chest + type: LocationGroup + - item: Big Key (Misery Mire) + locations: + - Misery Mire - Big Key Chest + - Misery Mire - Compass Chest + - Misery Mire - Map Chest + - Misery Mire - Spike Chest + - Misery Mire - Main Lobby + - Misery Mire - Bridge Chest + type: LocationGroup + - item: Big Key (Turtle Rock) + locations: + - Turtle Rock - Big Key Chest + - Turtle Rock - Compass Chest + - Turtle Rock - Roller Room - Left + - Turtle Rock - Chain Chomps + - Turtle Rock - Roller Room - Right + type: LocationGroup + - item: Big Key (Ganons Tower) + locations: + - Ganons Tower - Big Key Chest + - Ganons Tower - Compass Room - Top Left + - Ganons Tower - Map Chest + - Ganons Tower - Bob's Torch + - Ganons Tower - Tile Room + - Ganons Tower - Firesnake Room + - Ganons Tower - DMs Room - Top Right + - Ganons Tower - DMs Room - Top Left + - Ganons Tower - DMs Room - Bottom Left + - Ganons Tower - DMs Room - Bottom Right + - Ganons Tower - Compass Room - Top Right + - Ganons Tower - Compass Room - Bottom Right + - Ganons Tower - Compass Room - Bottom Left + - Ganons Tower - Hope Room - Left + - Ganons Tower - Hope Room - Right + - Ganons Tower - Randomizer Room - Top Left + - Ganons Tower - Randomizer Room - Top Right + - Ganons Tower - Randomizer Room - Bottom Right + - Ganons Tower - Randomizer Room - Bottom Left + - Ganons Tower - Bob's Chest + - Ganons Tower - Big Key Room - Left + - Ganons Tower - Big Key Room - Right + type: LocationGroup +item_pool: + 1: + Arrows (10): 12 + Blue Boomerang: 1 + Bombos: 1 + Bombs (10): 1 + Bombs (3): 16 + Book of Mudora: 1 + Boss Heart Container: 10 + Bottle (Random): 4 + Bug Catching Net: 1 + Cane of Byrna: 1 + Cane of Somaria: 1 + Cape: 1 + Ether: 1 + Fire Rod: 1 + Flippers: 1 + Hammer: 1 + Hookshot: 1 + Ice Rod: 1 + Lamp: 1 + Magic Mirror: 1 + Magic Powder: 1 + Magic Upgrade (1/2): 1 + Moon Pearl: 1 + Mushroom: 1 + Ocarina: 1 + Pegasus Boots: 1 + Piece of Heart: 24 + Progressive Armor: 2 + Progressive Bow: 2 + Progressive Glove: 2 + Progressive Shield: 3 + Progressive Sword: 4 + Titans Mitts: 1 + Quake: 1 + Red Boomerang: 1 + Rupee (1): 2 + Rupees (100): 1 + Rupees (20): 27 + Rupees (300): 5 + Rupees (5): 4 + Rupees (50): 7 + Sanctuary Heart Container: 1 + Shovel: 1 + Single Arrow: 1 diff --git a/resources/app/cli/args.json b/resources/app/cli/args.json index 0074143d..5758ca15 100644 --- a/resources/app/cli/args.json +++ b/resources/app/cli/args.json @@ -34,6 +34,10 @@ "retro" ] }, + "boots_hint": { + "action": "store_true", + "type": "bool" + }, "swords": { "choices": [ "random", diff --git a/source/classes/CustomSettings.py b/source/classes/CustomSettings.py index 08150a77..f8269b2a 100644 --- a/source/classes/CustomSettings.py +++ b/source/classes/CustomSettings.py @@ -24,15 +24,20 @@ class CustomSettings(object): head, filename = os.path.split(file) self.relative_dir = head - def determine_seed(self): - if 'meta' not in self.file_source: - return None - meta = defaultdict(lambda: None, self.file_source['meta']) - seed = meta['seed'] - if seed: - random.seed(seed) - return seed - return None + def determine_seed(self, default_seed): + if 'meta' in self.file_source: + meta = defaultdict(lambda: None, self.file_source['meta']) + seed = meta['seed'] + if seed: + random.seed(seed) + return seed + if default_seed is None: + random.seed(None) + seed = random.randint(0, 999999999) + else: + seed = default_seed + random.seed(seed) + return seed def determine_players(self): if 'meta' not in self.file_source: @@ -43,7 +48,10 @@ class CustomSettings(object): def adjust_args(self, args): def get_setting(value, default): if value: - return value + if isinstance(value, dict): + return random.choices(list(value.keys()), list(value.values()), k=1)[0] + else: + return value return default if 'meta' in self.file_source: meta = defaultdict(lambda: None, self.file_source['meta']) @@ -67,6 +75,7 @@ class CustomSettings(object): args.door_shuffle[p] = get_setting(settings['door_shuffle'], args.door_shuffle[p]) args.logic[p] = get_setting(settings['logic'], args.logic[p]) args.mode[p] = get_setting(settings['mode'], args.mode[p]) + args.boots_hint[p] = get_setting(settings['boots_hint'], args.boots_hint[p]) args.swords[p] = get_setting(settings['swords'], args.swords[p]) args.flute_mode[p] = get_setting(settings['flute_mode'], args.flute_mode[p]) args.bow_mode[p] = get_setting(settings['bow_mode'], args.bow_mode[p]) @@ -86,6 +95,14 @@ class CustomSettings(object): if args.pottery[p] == 'none': args.pottery[p] = 'keys' + if args.retro[p] or args.mode[p] == 'retro': + if args.bow_mode[p] == 'progressive': + args.bow_mode[p] = 'retro' + elif args.bow_mode[p] == 'silvers': + args.bow_mode[p] = 'retro_silvers' + args.take_any[p] = 'random' if args.take_any[p] == 'none' else args.take_any[p] + args.keyshuffle[p] = 'universal' + args.mixed_travel[p] = get_setting(settings['mixed_travel'], args.mixed_travel[p]) args.standardize_palettes[p] = get_setting(settings['standardize_palettes'], args.standardize_palettes[p]) @@ -104,7 +121,8 @@ class CustomSettings(object): if get_setting(settings['keysanity'], args.keysanity): args.bigkeyshuffle[p] = True - args.keyshuffle[p] = True + if args.keyshuffle[p] == 'none': + args.keyshuffle[p] = 'wild' args.mapshuffle[p] = True args.compassshuffle[p] = True @@ -149,6 +167,11 @@ class CustomSettings(object): return self.file_source['placements'] return None + def get_advanced_placements(self): + if 'advanced_placements' in self.file_source: + return self.file_source['advanced_placements'] + return None + def get_entrances(self): if 'entrances' in self.file_source: return self.file_source['entrances'] @@ -174,6 +197,11 @@ class CustomSettings(object): return self.file_source['medallions'] return None + def get_drops(self): + if 'drops' in self.file_source: + return self.file_source['drops'] + return None + def create_from_world(self, world): self.player_range = range(1, world.players + 1) settings_dict, meta_dict = {}, {} diff --git a/source/item/FillUtil.py b/source/item/FillUtil.py index 040497a2..6b242589 100644 --- a/source/item/FillUtil.py +++ b/source/item/FillUtil.py @@ -18,6 +18,8 @@ class ItemPoolConfig(object): self.item_pool = None self.placeholders = None self.reserved_locations = defaultdict(set) + self.restricted = {} + self.preferred = {} self.recorded_choices = [] @@ -380,8 +382,10 @@ def vanilla_fallback(item_to_place, locations, world): def filter_locations(item_to_place, locations, world, vanilla_skip=False, potion=False): + config = world.item_pool_config + item_name = 'Bottle' if item_to_place.name.startswith('Bottle') else item_to_place.name if world.algorithm == 'vanilla_fill': - config, filtered = world.item_pool_config, [] + filtered = [] item_name = 'Bottle' if item_to_place.name.startswith('Bottle') else item_to_place.name if item_name in config.static_placement[item_to_place.player]: restricted = config.static_placement[item_to_place.player][item_name] @@ -418,6 +422,12 @@ def filter_locations(item_to_place, locations, world, vanilla_skip=False, potion if len(filtered) == 0: raise RuntimeError('Can\'t sell potion of a certain type due to district restriction') return filtered + if (item_name, item_to_place.player) in config.restricted: + locs = config.restricted[(item_name, item_to_place.player)] + return sorted(locations, key=lambda l: 1 if l.name in locs else 0) + if (item_name, item_to_place.player) in config.preferred: + locs = config.preferred[(item_name, item_to_place.player)] + return sorted(locations, key=lambda l: 0 if l.name in locs else 1) return locations @@ -814,3 +824,26 @@ pot_items = { } valid_pot_items = {y: x for x, y in pot_items.items()} + + +if __name__ == '__main__': + import yaml + from yaml.representer import Representer + advanced_placements = {'advanced_placements': {}} + player_map = advanced_placements['advanced_placements'] + placement_list = [] + player_map[1] = placement_list + for item, location_list in vanilla_mapping.items(): + for location in location_list: + placement = {} + placement['type'] = 'LocationGroup' + placement['item'] = item + locations = placement['locations'] = [] + locations.append(location) + locations.append('Random') + placement_list.append(placement) + yaml.add_representer(defaultdict, Representer.represent_dict) + with open('fillgen.yaml', 'w') as file: + yaml.dump(advanced_placements, file) + +