From d9281adc079c0965ad298babec15d5e168b78882 Mon Sep 17 00:00:00 2001 From: Bonta-kun <40473493+Bonta0@users.noreply.github.com> Date: Tue, 17 Dec 2019 12:14:29 +0100 Subject: [PATCH] Individual settings: accessibility --- BaseClasses.py | 2 +- EntranceRandomizer.py | 2 +- Fill.py | 12 +++++------- Main.py | 4 ++-- Rules.py | 24 ++++++++++++------------ 5 files changed, 21 insertions(+), 23 deletions(-) diff --git a/BaseClasses.py b/BaseClasses.py index 205aee99..5761c9fc 100644 --- a/BaseClasses.py +++ b/BaseClasses.py @@ -50,7 +50,7 @@ class World(object): self.lock_aga_door_in_escape = False self.fix_trock_doors = {player: self.shuffle[player] != 'vanilla' or self.mode[player] == 'inverted' for player in range(1, players + 1)} self.save_and_quit_from_boss = True - self.accessibility = accessibility + self.accessibility = accessibility.copy() self.fix_skullwoods_exit = {player: self.shuffle[player] not in ['vanilla', 'simple', 'restricted', 'dungeonssimple'] for player in range(1, players + 1)} self.fix_palaceofdarkness_exit = {player: self.shuffle[player] not in ['vanilla', 'simple', 'restricted', 'dungeonssimple'] for player in range(1, players + 1)} self.fix_trock_exit = {player: self.shuffle[player] not in ['vanilla', 'simple', 'restricted', 'dungeonssimple'] for player in range(1, players + 1)} diff --git a/EntranceRandomizer.py b/EntranceRandomizer.py index a423cae1..883a90cf 100755 --- a/EntranceRandomizer.py +++ b/EntranceRandomizer.py @@ -281,7 +281,7 @@ def parse_arguments(argv, no_defaults=False): for name in ['logic', 'mode', 'swords', 'goal', 'difficulty', 'item_functionality', 'shuffle', 'crystals_ganon', 'crystals_gt', 'openpyramid', 'mapshuffle', 'compassshuffle', 'keyshuffle', 'bigkeyshuffle', - 'retro']: + 'retro', 'accessibility']: value = getattr(defaults, name) if getattr(playerargs, name) is None else getattr(playerargs, name) if player == 1: setattr(ret, name, {1: value}) diff --git a/Fill.py b/Fill.py index 1ee3d859..a27aadc4 100644 --- a/Fill.py +++ b/Fill.py @@ -179,14 +179,12 @@ def fill_restrictive(world, base_state, locations, itempool, single_player_place items_to_place = [[itempool.remove(items[-1]), items.pop()][-1] for items in player_items.values() if items] maximum_exploration_state = sweep_from_pool() - - perform_access_check = True - if world.accessibility == 'none' and not single_player_placement: - perform_access_check = not world.has_beaten_game(maximum_exploration_state) + has_beaten_game = world.has_beaten_game(maximum_exploration_state) for item_to_place in items_to_place: - if single_player_placement and world.accessibility == 'none': - perform_access_check = not world.has_beaten_game(maximum_exploration_state, item_to_place.player) + perform_access_check = True + if world.accessibility[item_to_place.player] == 'none': + perform_access_check = not world.has_beaten_game(maximum_exploration_state, item_to_place.player) if single_player_placement else not has_beaten_game spot_to_fill = None for location in locations: @@ -199,7 +197,7 @@ def fill_restrictive(world, base_state, locations, itempool, single_player_place # we filled all reachable spots. Maybe the game can be beaten anyway? unplaced_items.insert(0, item_to_place) if world.can_beat_game(): - if world.accessibility != 'none': + if world.accessibility[item_to_place.player] != 'none': logging.getLogger('').warning('Not all items placed. Game beatable anyway. (Could not place %s)' % item_to_place) continue raise FillError('No more spots to place %s' % item_to_place) diff --git a/Main.py b/Main.py index 876f6912..8157c39c 100644 --- a/Main.py +++ b/Main.py @@ -330,7 +330,7 @@ def create_playthrough(world): world = copy_world(world) # if we only check for beatable, we can do this sanity check first before writing down spheres - if world.accessibility == 'none' and not world.can_beat_game(): + if not world.can_beat_game(): raise RuntimeError('Cannot beat game. Something went terribly wrong here!') # get locations containing progress items @@ -360,7 +360,7 @@ def create_playthrough(world): logging.getLogger('').debug('Calculated sphere %i, containing %i of %i progress items.', len(collection_spheres), len(sphere), len(prog_locations)) if not sphere: logging.getLogger('').debug('The following items could not be reached: %s', ['%s (Player %d) at %s (Player %d)' % (location.item.name, location.item.player, location.name, location.player) for location in sphere_candidates]) - if not world.accessibility == 'none': + if any([world.accessibility[location.item.player] != 'none' for location in sphere_candidates]): raise RuntimeError('Not all progression items reachable. Something went terribly wrong here.') else: break diff --git a/Rules.py b/Rules.py index a22a81c7..0950f393 100644 --- a/Rules.py +++ b/Rules.py @@ -173,7 +173,7 @@ def global_rules(world, player): set_rule(world.get_entrance('Tower of Hera Big Key Door', player), lambda state: state.has('Big Key (Tower of Hera)', player)) set_rule(world.get_location('Tower of Hera - Big Chest', player), lambda state: state.has('Big Key (Tower of Hera)', player)) set_rule(world.get_location('Tower of Hera - Big Key Chest', player), lambda state: state.has_fire_source(player)) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Tower of Hera - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Tower of Hera)' and item.player == player) set_defeat_dungeon_boss_rule(world.get_location('Tower of Hera - Boss', player)) set_defeat_dungeon_boss_rule(world.get_location('Tower of Hera - Prize', player)) @@ -186,7 +186,7 @@ def global_rules(world, player): set_rule(world.get_entrance('Swamp Palace Small Key Door', player), lambda state: state.has_key('Small Key (Swamp Palace)', player)) set_rule(world.get_entrance('Swamp Palace (Center)', player), lambda state: state.has('Hammer', player)) set_rule(world.get_location('Swamp Palace - Big Chest', player), lambda state: state.has('Big Key (Swamp Palace)', player) or item_name(state, 'Swamp Palace - Big Chest', player) == ('Big Key (Swamp Palace)', player)) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Swamp Palace - Big Chest', player), lambda state, item: item.name == 'Big Key (Swamp Palace)' and item.player == player) set_rule(world.get_entrance('Swamp Palace (North)', player), lambda state: state.has('Hookshot', player)) set_defeat_dungeon_boss_rule(world.get_location('Swamp Palace - Boss', player)) @@ -199,7 +199,7 @@ def global_rules(world, player): set_defeat_dungeon_boss_rule(world.get_location('Thieves\' Town - Boss', player)) set_defeat_dungeon_boss_rule(world.get_location('Thieves\' Town - Prize', player)) set_rule(world.get_location('Thieves\' Town - Big Chest', player), lambda state: (state.has_key('Small Key (Thieves Town)', player) or item_name(state, 'Thieves\' Town - Big Chest', player) == ('Small Key (Thieves Town)', player)) and state.has('Hammer', player)) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Thieves\' Town - Big Chest', player), lambda state, item: item.name == 'Small Key (Thieves Town)' and item.player == player and state.has('Hammer', player)) set_rule(world.get_location('Thieves\' Town - Attic', player), lambda state: state.has_key('Small Key (Thieves Town)', player)) for location in ['Thieves\' Town - Attic', 'Thieves\' Town - Big Chest', 'Thieves\' Town - Blind\'s Cell', 'Thieves\' Town - Boss']: @@ -212,7 +212,7 @@ def global_rules(world, player): set_rule(world.get_entrance('Skull Woods First Section West Door', player), lambda state: state.has_key('Small Key (Skull Woods)', player, 2)) # ideally would only be one key, but we may have spent thst key already on escaping the right section set_rule(world.get_entrance('Skull Woods First Section (Left) Door to Exit', player), lambda state: state.has_key('Small Key (Skull Woods)', player, 2)) set_rule(world.get_location('Skull Woods - Big Chest', player), lambda state: state.has('Big Key (Skull Woods)', player) or item_name(state, 'Skull Woods - Big Chest', player) == ('Big Key (Skull Woods)', player)) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Skull Woods - Big Chest', player), lambda state, item: item.name == 'Big Key (Skull Woods)' and item.player == player) set_rule(world.get_entrance('Skull Woods Torch Room', player), lambda state: state.has_key('Small Key (Skull Woods)', player, 3) and state.has('Fire Rod', player) and state.has_sword(player)) # sword required for curtain set_defeat_dungeon_boss_rule(world.get_location('Skull Woods - Boss', player)) @@ -277,13 +277,13 @@ def global_rules(world, player): set_rule(world.get_location('Palace of Darkness - Big Chest', player), lambda state: state.has('Big Key (Palace of Darkness)', player)) set_rule(world.get_entrance('Palace of Darkness Big Key Chest Staircase', player), lambda state: state.has_key('Small Key (Palace of Darkness)', player, 6) or (item_name(state, 'Palace of Darkness - Big Key Chest', player) in [('Small Key (Palace of Darkness)', player)] and state.has_key('Small Key (Palace of Darkness)', player, 3))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Palace of Darkness - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Palace of Darkness)' and item.player == player and state.has_key('Small Key (Palace of Darkness)', player, 5)) else: forbid_item(world.get_location('Palace of Darkness - Big Key Chest', player), 'Small Key (Palace of Darkness)', player) set_rule(world.get_entrance('Palace of Darkness Spike Statue Room Door', player), lambda state: state.has_key('Small Key (Palace of Darkness)', player, 6) or (item_name(state, 'Palace of Darkness - Harmless Hellway', player) in [('Small Key (Palace of Darkness)', player)] and state.has_key('Small Key (Palace of Darkness)', player, 4))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Palace of Darkness - Harmless Hellway', player), lambda state, item: item.name == 'Small Key (Palace of Darkness)' and item.player == player and state.has_key('Small Key (Palace of Darkness)', player, 5)) else: forbid_item(world.get_location('Palace of Darkness - Harmless Hellway', player), 'Small Key (Palace of Darkness)', player) @@ -301,7 +301,7 @@ def global_rules(world, player): set_rule(world.get_entrance('Ganons Tower (Hookshot Room)', player), lambda state: state.has('Hammer', player)) set_rule(world.get_entrance('Ganons Tower (Map Room)', player), lambda state: state.has_key('Small Key (Ganons Tower)', player, 4) or (item_name(state, 'Ganons Tower - Map Chest', player) in [('Big Key (Ganons Tower)', player), ('Small Key (Ganons Tower)', player)] and state.has_key('Small Key (Ganons Tower)', player, 3))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Ganons Tower - Map Chest', player), lambda state, item: item.name == 'Small Key (Ganons Tower)' and item.player == player and state.has_key('Small Key (Ganons Tower)', player, 3)) else: forbid_item(world.get_location('Ganons Tower - Map Chest', player), 'Small Key (Ganons Tower)', player) @@ -770,13 +770,13 @@ def set_trock_key_rules(world, player): # might open all the locked doors in any order so we need maximally restrictive rules. if can_reach_back: set_rule(world.get_location('Turtle Rock - Big Key Chest', player), lambda state: (state.has_key('Small Key (Turtle Rock)', player, 4) or item_name(state, 'Turtle Rock - Big Key Chest', player) == ('Small Key (Turtle Rock)', player))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Turtle Rock - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Turtle Rock)' and item.player == player) else: forbid_item(world.get_location('Turtle Rock - Big Key Chest', player), 'Small Key (Turtle Rock)', player) elif can_reach_front and can_reach_middle: set_rule(world.get_location('Turtle Rock - Big Key Chest', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, tr_big_key_chest_keys_needed(state))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Turtle Rock - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Turtle Rock)' and item.player == player) else: forbid_item(world.get_location('Turtle Rock - Big Key Chest', player), 'Small Key (Turtle Rock)', player) @@ -787,7 +787,7 @@ def set_trock_key_rules(world, player): set_rule(world.get_entrance('Turtle Rock (Chain Chomp Room) (North)', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, 2)) set_rule(world.get_entrance('Turtle Rock Pokey Room', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, 1)) set_rule(world.get_location('Turtle Rock - Big Key Chest', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, tr_big_key_chest_keys_needed(state))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Turtle Rock - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Turtle Rock)' and item.player == player and state.has_key('Small Key (Turtle Rock)', player, 2)) else: forbid_item(world.get_location('Turtle Rock - Big Key Chest', player), 'Small Key (Turtle Rock)', player) @@ -797,7 +797,7 @@ def set_trock_key_rules(world, player): elif can_reach_big_chest: set_rule(world.get_entrance('Turtle Rock (Chain Chomp Room) (South)', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, 2) if item_in_locations(state, 'Big Key (Turtle Rock)', player, [('Turtle Rock - Compass Chest', player), ('Turtle Rock - Roller Room - Left', player), ('Turtle Rock - Roller Room - Right', player)]) else state.has_key('Small Key (Turtle Rock)', player, 4)) set_rule(world.get_location('Turtle Rock - Big Key Chest', player), lambda state: (state.has_key('Small Key (Turtle Rock)', player, 4) or item_name(state, 'Turtle Rock - Big Key Chest', player) == ('Small Key (Turtle Rock)', player))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Turtle Rock - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Turtle Rock)' and item.player == player) else: forbid_item(world.get_location('Turtle Rock - Big Key Chest', player), 'Small Key (Turtle Rock)', player) @@ -809,7 +809,7 @@ def set_trock_key_rules(world, player): else: set_rule(world.get_entrance('Turtle Rock (Chain Chomp Room) (South)', player), lambda state: state.has_key('Small Key (Turtle Rock)', player, 2) if item_in_locations(state, 'Big Key (Turtle Rock)', player, [('Turtle Rock - Compass Chest', player), ('Turtle Rock - Roller Room - Left', player), ('Turtle Rock - Roller Room - Right', player)]) else state.has_key('Small Key (Turtle Rock)', player, 4)) set_rule(world.get_location('Turtle Rock - Big Key Chest', player), lambda state: (state.has_key('Small Key (Turtle Rock)', player, 4) or item_name(state, 'Turtle Rock - Big Key Chest', player) == ('Small Key (Turtle Rock)', player))) - if world.accessibility != 'locations': + if world.accessibility[player] != 'locations': set_always_allow(world.get_location('Turtle Rock - Big Key Chest', player), lambda state, item: item.name == 'Small Key (Turtle Rock)' and item.player == player) non_big_key_locations += ['Turtle Rock - Crystaroller Room', 'Turtle Rock - Eye Bridge - Bottom Left', 'Turtle Rock - Eye Bridge - Bottom Right', 'Turtle Rock - Eye Bridge - Top Left',