diff --git a/worlds/crystal_project/constants/ap_regions.py b/worlds/crystal_project/constants/ap_regions.py index 4176a4dca14e..18e1be1c30d9 100644 --- a/worlds/crystal_project/constants/ap_regions.py +++ b/worlds/crystal_project/constants/ap_regions.py @@ -180,9 +180,18 @@ SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION = "Gold Near Ganymede" SKY_ARENA_AP_REGION = "Sky Arena" SHOUDU_WATERWAYS_AP_REGION = "Shoudu Waterways" +HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION = "Hole near the Prize Counter connection to Undercity" +BALANCE_BEAM_NEAR_WHITE_HUT_UNDERCITY_CONNECTOR_AP_REGION = "Balance beam above western Undercity in building next to white room" #Shoudu Province end -THE_UNDERCITY_AP_REGION = "The Undercity" -THE_UNDERCITY_AP_REGION_TELEPORT_LOCATION = "732,97,-197" +THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION = "Undercity Home Point and Blade Master" +THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION_TELEPORT_LOCATION = "732,97,-197" +EAST_UNDERCITY_WAREHOUSE_AP_REGION = "East Undercity Warehouse" +EAST_UNDERCITY_WALL_CLIMB_AP_REGION = "East Undercity wall climb to the Prize Counter" +DUEL_MASTER_AP_REGION = "Undercity Duel Master" +SHADOW_MASTER_ENTRANCE_AP_REGION = "The Shadow Master Entrance" +SHADOW_MASTER_AP_REGION = "The Shadow Master" +PAH_SUMMON_AP_REGION = "Pah Summon Cave" +UNDERCITY_WATERWAYS_AP_REGION = "Undercity Waterways" #Ganymede Shrine start GANYMEDE_SHRINE_AP_REGION = "Ganymede Shrine" GANYMEDE_SHRINE_AP_REGION_TELEPORT_LOCATION = "689,158,-240" diff --git a/worlds/crystal_project/constants/display_regions.py b/worlds/crystal_project/constants/display_regions.py index ab676653f26c..8c8c45b3f236 100644 --- a/worlds/crystal_project/constants/display_regions.py +++ b/worlds/crystal_project/constants/display_regions.py @@ -69,9 +69,9 @@ THE_OPEN_SEA_DISPLAY_NAME = "The Open Sea" THE_OPEN_SEA_DISPLAY_SUBREGIONS = [THE_OPEN_SEA_AP_REGION, JIDAMBA_ATOLLS_AP_REGION, BAZAAR_COAST_AP_REGION] SHOUDU_PROVINCE_DISPLAY_NAME = "Shoudu Province" -SHOUDU_PROVINCE_DISPLAY_SUBREGIONS = [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, NORTHEAST_MIDPOINT_SCAFFOLDING_AP_REGION, NORTHEAST_UPPER_SCAFFOLDING_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION, SKY_ARENA_AP_REGION, SHOUDU_WATERWAYS_AP_REGION] +SHOUDU_PROVINCE_DISPLAY_SUBREGIONS = [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, NORTHEAST_MIDPOINT_SCAFFOLDING_AP_REGION, NORTHEAST_UPPER_SCAFFOLDING_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION, SKY_ARENA_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION, BALANCE_BEAM_NEAR_WHITE_HUT_UNDERCITY_CONNECTOR_AP_REGION] THE_UNDERCITY_DISPLAY_NAME = "The Undercity" -THE_UNDERCITY_DISPLAY_SUBREGIONS = [THE_UNDERCITY_AP_REGION] +THE_UNDERCITY_DISPLAY_SUBREGIONS = [THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, EAST_UNDERCITY_WAREHOUSE_AP_REGION, EAST_UNDERCITY_WALL_CLIMB_AP_REGION, DUEL_MASTER_AP_REGION, SHADOW_MASTER_ENTRANCE_AP_REGION, SHADOW_MASTER_AP_REGION, PAH_SUMMON_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION] GANYMEDE_SHRINE_DISPLAY_NAME = "Ganymede Shrine" GANYMEDE_SHRINE_DISPLAY_SUBREGIONS = [GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION] BEAURIOR_VOLCANO_DISPLAY_NAME = "Beaurior Volcano" diff --git a/worlds/crystal_project/constants/home_points.py b/worlds/crystal_project/constants/home_points.py index 60cfe36941a9..ed328082375a 100644 --- a/worlds/crystal_project/constants/home_points.py +++ b/worlds/crystal_project/constants/home_points.py @@ -132,7 +132,7 @@ HOMEPOINT_SKY_ARENA_AP_REGION = SKY_ARENA_AP_REGION #The Undercity HOMEPOINT_THE_UNDERCITY_NAME = "HomePoint - The Undercity" -HOMEPOINT_THE_UNDERCITY_AP_REGION = THE_UNDERCITY_AP_REGION +HOMEPOINT_THE_UNDERCITY_AP_REGION = THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION #Ganymede Shrine HOMEPOINT_GANYMEDE_SHRINE_NAME = "HomePoint - Ganymede Shrine" HOMEPOINT_GANYMEDE_SHRINE_AP_REGION = GANYMEDE_SHRINE_AP_REGION diff --git a/worlds/crystal_project/locations.py b/worlds/crystal_project/locations.py index b560c8a975be..5bde42ea4a79 100644 --- a/worlds/crystal_project/locations.py +++ b/worlds/crystal_project/locations.py @@ -887,37 +887,34 @@ def get_treasure_and_npc_locations(player: int, options: CrystalProjectOptions | LocationData(SKY_ARENA_AP_REGION, SHOUDU_PROVINCE_DISPLAY_NAME + " NPC - Diamond through a hole in the 10 Sky Arena Wins room floor", 2832 + npc_index_offset, lambda state: logic.is_area_in_level_range(state, ARACHLEA_FIGHT_LEVEL)), #(753, 130, -264) Ore #The Undercity - #Treasures # can get without mounts from Shoudu - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 1", 2988 + treasure_index_offset), # Fenix Juice chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 2", 2987 + treasure_index_offset), # Ether chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 3", 1147 + treasure_index_offset), # Potion chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 4", 3517 + treasure_index_offset), # (778, 94, -254) Elevator Part chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 1", 2988 + treasure_index_offset), # Fenix Juice chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 2", 2987 + treasure_index_offset), # Ether chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 3", 1147 + treasure_index_offset), # Potion chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Gated-off room 4", 3517 + treasure_index_offset), # (778, 94, -254) Elevator Part chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gold hiding from the bats under the awning", 2835 + npc_index_offset), # Dust + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gated-off room Gold", 2825 + npc_index_offset), # Ore #except these up high - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Climb up lampposts and run across the fence", 1925 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or logic.has_glide(state)), # Cursegiver chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - North wall climb (or fall through broken grate by Sky Arena Prize Counter)", 3516 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or logic.has_glide(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Elevator Part chest + LocationData(EAST_UNDERCITY_WAREHOUSE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Climb up lampposts and run across the fence", 1925 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or logic.has_glide(state)), # Cursegiver chest + LocationData(EAST_UNDERCITY_WALL_CLIMB_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - North wall climb (or fall through broken grate by Sky Arena Prize Counter)", 3516 + treasure_index_offset), # Elevator Part chest #Home Point Stone area - can walk from Ganymede Shrine -> Undercity entrance next to white hut -> fall off rafter; can also swim from the sea - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hiding in the rafters", 2989 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Potion Pouch chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Atop awning east of the waterfall", 3518 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Elevator Part chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hidden in a nook in the wall", 2793 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or logic.has_glide(state)), # Knights Plate chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hiding in the rafters", 2989 + treasure_index_offset), # Potion Pouch chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Atop awning east of the waterfall", 3518 + treasure_index_offset), # Elevator Part chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hidden in a nook in the wall", 2793 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or (logic.has_glide(state) and logic.is_hop_to_it_at_least_fancy_footwork())), # Knights Plate chest #ibek from Home Point Stone area - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Up the rafters against a pillar", 2990 + treasure_index_offset, lambda state: logic.has_vertical_movement(state)), # Ether chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Even further up the rafters", 2991 + treasure_index_offset, lambda state: logic.has_vertical_movement(state)), # Ether Pouch chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Up the rafters against a pillar", 2990 + treasure_index_offset, lambda state: logic.has_vertical_movement(state) or logic.has_golden_quintar(state)), # Ether chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Even further up the rafters", 2991 + treasure_index_offset, lambda state: logic.has_vertical_movement(state)), # Ether Pouch chest #Undercity Inn area - can walk from Home Point Stone area if you hop up on guy who wants you to defeat the Undercity masters, go north, and hop west across lamps - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hiding in a building in the north area", 2826 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Potion chest - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Undercity Inn", 3519 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Elevator Part - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - South of the Undercity Inn", 1695 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), # Brigandine chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Hiding in a building in the north area", 2826 + treasure_index_offset), # Potion chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - Undercity Inn", 3519 + treasure_index_offset), # Elevator Part + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Chest - South of the Undercity Inn", 1695 + treasure_index_offset), # Brigandine chest + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Storage room Gold of the Undercity Inns", 1694 + npc_index_offset), #Ingot + #First north swimmable option when heading to shadw master + LocationData(SHADOW_MASTER_ENTRANCE_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gold in the sewer offshoot", 1696 + npc_index_offset), # Dust + #swimmy swimmy - LocationData(THE_UNDERCITY_AP_REGION, "Underpass Chest - Lovely bounce tree W of The Undercity", 3673 + treasure_index_offset, lambda state: logic.has_swimming(state) or logic.has_glide(state)), #(608, 91, -215) (Summon Pah) Underpass Scrap chest - - #NPCs - #can get without mounts from Shoudu - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gold hiding from the bats under the awning", 2835 + npc_index_offset), #Dust - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gated-off room Gold", 2825 + npc_index_offset), #Ore - #other side of canal from Home Point Stone area - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Gold in the sewer offshoot", 1696 + npc_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), #Dust - #Undercity Inn area - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " NPC - Storage room Gold of the Undercity Inns", 1694 + npc_index_offset, lambda state: logic.has_swimming(state) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state) or state.can_reach(GANYMEDE_SHRINE_AP_REGION, player=player) or state.can_reach(QUINTAR_RESERVE_AP_REGION, player=player)), #Ingot + LocationData(PAH_SUMMON_AP_REGION, "Underpass Chest - Lovely bounce tree W of The Undercity", 3673 + treasure_index_offset), #(608, 91, -215) (Summon Pah) Underpass Scrap chest + #Ganymede Shrine #Treasure chests @@ -1435,7 +1432,7 @@ def get_crystal_locations(player: int, options: CrystalProjectOptions | None) -> # Zones (Expert) LocationData(SKY_ARENA_AP_REGION, SHOUDU_PROVINCE_DISPLAY_NAME + SAMURAI_JOB_CRYSTAL_LOCATION, 1206 + crystal_index_offset, lambda state: logic.is_area_in_level_range(state, THIRD_SKY_ARENA_FIGHT_LEVEL)), # Can just swim or defeat the Undercity Masters; Blade Master: Ibek or Owl, Shadow Master: Horizontal or Fish, Duel Master: Ibek or Owl; to defeat all masters, you either need both ibek + quintar, owl, or fish - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + ASSASSIN_JOB_CRYSTAL_LOCATION, 1204 + crystal_index_offset, lambda state: (logic.has_horizontal_movement(state) and logic.has_vertical_movement(state)) or logic.has_glide(state) or logic.has_swimming(state)), + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + ASSASSIN_JOB_CRYSTAL_LOCATION, 1204 + crystal_index_offset, lambda state: (logic.has_horizontal_movement(state) and logic.has_vertical_movement(state)) or logic.has_glide(state) or logic.has_swimming(state)), LocationData(BEAURIOR_ROCK_AP_REGION, BEAURIOR_VOLCANO_DISPLAY_NAME + VALKYRIE_JOB_CRYSTAL_LOCATION, 1086 + crystal_index_offset, lambda state: logic.has_key(state, SMALL_KEY, 4) and logic.has_key(state, BEAURIOR_BOSS_KEY)), LocationData(SLIP_GLIDE_RIDE_AP_REGION, SLIP_GLIDE_RIDE_DISPLAY_NAME + SUMMONER_JOB_CRYSTAL_LOCATION, 1714 + crystal_index_offset, lambda state: logic.has_key(state, RED_DOOR_KEY, 3)), # (404, 243, -386) @@ -1455,7 +1452,7 @@ def get_boss_locations(player: int, options: CrystalProjectOptions | None) -> Li LocationData(SPAWNING_MEADOWS_AP_REGION, SPAWNING_MEADOWS_DISPLAY_NAME + " Boss - Shaku Summon", 477 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, SHAKU_FIGHT_LEVEL)), #(118, 109, 10) Monster ID: 102 LocationData(CAPITAL_SEQUOIA_AP_REGION, CAPITAL_SEQUOIA_DISPLAY_NAME + " Boss - Niltsi Summon", 1109 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, NILTSI_FIGHT_LEVEL)), #376, 178, -345 (Capital Sequoia (Maze) map) Monster ID: 93 LocationData(SALMON_BAY_AP_REGION, SALMON_BAY_DISPLAY_NAME + " Boss - Guaba Summon", 1138 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, GUABA_FIGHT_LEVEL)), #-50, 91, -330 Monster ID: 94 - LocationData(THE_UNDERCITY_AP_REGION, "Underpass Boss - Pah Summon", 1130 + boss_index_offset, lambda state: (logic.has_swimming(state) or logic.has_glide(state)) and state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, PAH_FIGHT_LEVEL)), #614, 91, -213 Monster ID: 97 + LocationData(PAH_SUMMON_AP_REGION, "Underpass Boss - Pah Summon", 1130 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, PAH_FIGHT_LEVEL)), #614, 91, -213 Monster ID: 97 LocationData(SHOUDU_ELEVATOR_BASE_AP_REGION, SHOUDU_PROVINCE_DISPLAY_NAME + " Boss - Tira Summon", 1132 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, TIRA_FIGHT_LEVEL)), #(720, 138, -278) Monster ID: 98 LocationData(LAKE_DELENDE_AP_REGION, LAKE_DELENDE_DISPLAY_NAME + " Boss - Ioske Summon", 1111 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, IOSKE_FIGHT_LEVEL)), #97, 126, -211 Monster ID: 92 LocationData(PAMOA_TREE_AP_REGION, TALL_TALL_HEIGHTS_DISPLAY_NAME + " Boss - Pamoa Summon", 1136 + boss_index_offset, lambda state: state.has(SUMMONER_JOB, player) and logic.is_area_in_level_range(state, PAMOA_FIGHT_LEVEL)), #498, 218, -412 Monster ID: 91 @@ -1482,9 +1479,9 @@ def get_boss_locations(player: int, options: CrystalProjectOptions | None) -> Li LocationData(OKIMOTO_NS_AP_REGION, OKIMOTO_NS_DISPLAY_NAME + " Boss - Kuromanto", 698 + boss_index_offset, lambda state: logic.is_area_in_level_range(state, KUROMANTO_FIGHT_LEVEL)), #Monster ID: 63 LocationData(IBEK_CAVE_AP_REGION, ANCIENT_RESERVOIR_DISPLAY_NAME + " Boss - Possessor", 1674 + boss_index_offset, lambda state: logic.is_area_in_level_range(state, POSSESSOR_FIGHT_LEVEL)), #Monster ID: 221 LocationData(SKY_ARENA_AP_REGION, SHOUDU_PROVINCE_DISPLAY_NAME + " Boss - Final Sky Arena Fight: Arachlea", 1366 + boss_index_offset, lambda state: logic.is_area_in_level_range(state, ARACHLEA_FIGHT_LEVEL)), #Monster ID: 252 (SkyArenaRegistrar) - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Blade Master", 1939 + boss_index_offset, lambda state: (logic.has_vertical_movement(state) or logic.has_glide(state)) and logic.is_area_in_level_range(state, BLADE_MASTER_FIGHT_LEVEL)), #Monster ID: 145 - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Shadow Master", 1940 + boss_index_offset, lambda state: (logic.has_swimming(state) or logic.has_horizontal_movement(state)) and logic.is_area_in_level_range(state, SHADOW_MASTER_FIGHT_LEVEL)), #Monster ID: 144 - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Duel Master", 1941 + boss_index_offset, lambda state: (logic.has_vertical_movement(state) or logic.has_glide(state)) and logic.is_area_in_level_range(state, DUEL_MASTER_FIGHT_LEVEL)), #Monster ID: 146 + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Blade Master", 1939 + boss_index_offset, lambda state: (logic.has_vertical_movement(state) or logic.has_glide(state)) and logic.is_area_in_level_range(state, BLADE_MASTER_FIGHT_LEVEL)), #Monster ID: 145 + LocationData(SHADOW_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Shadow Master", 1940 + boss_index_offset, lambda state: (logic.has_swimming(state) or logic.has_horizontal_movement(state)) and logic.is_area_in_level_range(state, SHADOW_MASTER_FIGHT_LEVEL)), #Monster ID: 144 + LocationData(DUEL_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Boss - Duel Master", 1941 + boss_index_offset, lambda state: (logic.has_vertical_movement(state) or logic.has_glide(state)) and logic.is_area_in_level_range(state, DUEL_MASTER_FIGHT_LEVEL)), #Monster ID: 146 LocationData(BEAURIOR_ROCK_AP_REGION, BEAURIOR_ROCK_DISPLAY_NAME + " Boss - Ancient Sword", 821 + boss_index_offset, lambda state: logic.has_key(state, SMALL_KEY, 2) and logic.is_area_in_level_range(state, ANCIENT_SWORD_FIGHT_LEVEL)), #Monster ID: 59 LocationData(BEAURIOR_ROCK_AP_REGION, BEAURIOR_ROCK_DISPLAY_NAME + " Boss - Iguanadon & Iguanadin", 862 + boss_index_offset, lambda state: logic.has_key(state, SMALL_KEY, 4) and logic.has_key(state, BEAURIOR_BOSS_KEY) and logic.is_area_in_level_range(state, IGUANADON_AND_DIN_FIGHT_LEVEL)), #Monster ID: 78 and 100 LocationData(EASTERN_CHASM_AP_REGION, EASTERN_CHASM_DISPLAY_NAME + " Boss - Undergrowth", 3476 + boss_index_offset, lambda state: logic.is_area_in_level_range(state, UNDERGROWTH_FIGHT_LEVEL)), #Monster ID: 293 @@ -1985,7 +1982,7 @@ def get_region_completion_locations() -> List[LocationData]: LocationData(THE_OPEN_SEA_AP_REGION, THE_OPEN_SEA_DISPLAY_NAME + " Region Completion", 6031 + regionsanity_index_offset, regionsanity=True), LocationData(SHOUDU_WATERFRONT_AP_REGION, SHOUDU_WATERFRONT_DISPLAY_NAME + " Region Completion", 6032 + regionsanity_index_offset, regionsanity=True), LocationData(SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_DISPLAY_NAME + " Region Completion", 6033 + regionsanity_index_offset, regionsanity=True), - LocationData(THE_UNDERCITY_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Region Completion", 6034 + regionsanity_index_offset, regionsanity=True), + LocationData(THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, THE_UNDERCITY_DISPLAY_NAME + " Region Completion", 6034 + regionsanity_index_offset, regionsanity=True), LocationData(GANYMEDE_SHRINE_AP_REGION, GANYMEDE_SHRINE_DISPLAY_NAME + " Region Completion", 6035 + regionsanity_index_offset, regionsanity=True), LocationData(BEAURIOR_VOLCANO_AP_REGION, BEAURIOR_VOLCANO_DISPLAY_NAME + " Region Completion", 6036 + regionsanity_index_offset, regionsanity=True), LocationData(BEAURIOR_ROCK_AP_REGION, BEAURIOR_ROCK_DISPLAY_NAME + " Region Completion", 6037 + regionsanity_index_offset, regionsanity=True), diff --git a/worlds/crystal_project/regions.py b/worlds/crystal_project/regions.py index 3b1eef049909..778c462d3fc7 100644 --- a/worlds/crystal_project/regions.py +++ b/worlds/crystal_project/regions.py @@ -459,13 +459,11 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti QUINTAR_RESERVE_AP_REGION: lambda state: logic.has_vertical_movement(state)}) fancy_add_exits(world, HUNTERS_TOWER_AP_REGION, [ROLLING_QUINTAR_FIELDS_AP_REGION, ROLLING_TREETOP_HIGHWAY_AP_REGION, SANCTUM_ENTRANCE_AP_REGION, SANCTUM_EXIT_CLIFFTOP_AP_REGION, RAMPART_ATOP_PORTCULLIS_AP_REGION], {SANCTUM_EXIT_CLIFFTOP_AP_REGION: lambda state: logic.has_horizontal_movement(state) or logic.has_vertical_movement(state)}) - fancy_add_exits(world, AEGIS_OUTPOST_AP_REGION, [ROLLING_QUINTAR_FIELDS_AP_REGION, WEST_COBBLESTONE_CRAG_AP_REGION, EAST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, THE_UNDERCITY_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], + fancy_add_exits(world, AEGIS_OUTPOST_AP_REGION, [ROLLING_QUINTAR_FIELDS_AP_REGION, WEST_COBBLESTONE_CRAG_AP_REGION, EAST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, PAH_SUMMON_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], #Note: Aegis Master is inside this region and requires rental quintar(obscure) or horizontal or vertical {OKIMOTO_NS_AP_REGION: lambda state: (logic.has_rental_quintar(state, ROLLING_QUINTAR_FIELDS_DISPLAY_NAME) and logic.obscure_routes_on()) or logic.has_horizontal_movement(state) or logic.has_vertical_movement(state), SHOUDU_WATERFRONT_AP_REGION: lambda state: logic.obscure_routes_on() and (logic.has_rental_quintar(state, ROLLING_QUINTAR_FIELDS_DISPLAY_NAME) or logic.has_vertical_movement(state)), - SHOUDU_DOCKSIDE_AP_REGION: lambda state: logic.obscure_routes_on() and (logic.has_vertical_movement(state) or logic.has_glide(state)), - #TODO: this Undercity connection is to the Pah Summon cave specifically - THE_UNDERCITY_AP_REGION: lambda state: logic.obscure_routes_on() and (logic.has_glide(state) or logic.has_swimming(state)), + PAH_SUMMON_AP_REGION: lambda state: logic.obscure_routes_on() and (logic.has_glide(state) or logic.has_swimming(state)), FLYERS_CRAG_LOWER_AP_REGION: lambda state: logic.obscure_routes_on() and (logic.has_vertical_movement(state) or logic.has_glide(state))}) #Rolling Quintar Fields end #Quintar Nest start @@ -516,19 +514,16 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti ROLLING_QUINTAR_FIELDS_AP_REGION: lambda state: logic.has_vertical_movement(state), AEGIS_OUTPOST_AP_REGION: lambda state: logic.has_vertical_movement(state), THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state)}) - fancy_add_exits(world, EAST_COBBLESTONE_CRAG_AP_REGION, [WEST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, THE_UNDERCITY_AP_REGION, THE_OPEN_SEA_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], + fancy_add_exits(world, EAST_COBBLESTONE_CRAG_AP_REGION, [WEST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, PAH_SUMMON_AP_REGION, THE_OPEN_SEA_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], {SHOUDU_WATERFRONT_AP_REGION: lambda state: logic.has_horizontal_movement(state) or (logic.has_vertical_movement(state) and logic.is_hop_to_it_at_least_fancy_footwork()), - SHOUDU_DOCKSIDE_AP_REGION: lambda state: (logic.is_hop_to_it_at_least_fancy_footwork() or logic.has_horizontal_movement(state)) and logic.has_vertical_movement(state), - #TODO: this Undercity connection is to the Pah Summon cave specifically - THE_UNDERCITY_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), + PAH_SUMMON_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state), FLYERS_CRAG_LOWER_AP_REGION: lambda state: (logic.is_hop_to_it_at_least_fancy_footwork() or logic.has_horizontal_movement(state)) and logic.has_vertical_movement(state)}) #Cobblestone Crag end - fancy_add_exits(world, OKIMOTO_NS_AP_REGION, [EAST_COBBLESTONE_CRAG_AP_REGION, THE_OPEN_SEA_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, THE_UNDERCITY_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, QUINTAR_RESERVE_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION, FLYERS_CRAG_UPPER_AP_REGION], + fancy_add_exits(world, OKIMOTO_NS_AP_REGION, [EAST_COBBLESTONE_CRAG_AP_REGION, THE_OPEN_SEA_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, PAH_SUMMON_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, QUINTAR_RESERVE_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION, FLYERS_CRAG_UPPER_AP_REGION], {THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state), SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), - #TODO: this Undercity connection is to the Pah Summon cave specifically - THE_UNDERCITY_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), + PAH_SUMMON_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), GANYMEDE_SHRINE_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), GANYMEDE_STEEPLE_AP_REGION: lambda state: (logic.has_horizontal_movement(state) and logic.has_swimming(state) and logic.obscure_routes_on()) or logic.has_glide(state), QUINTAR_RESERVE_AP_REGION: lambda state: (logic.obscure_routes_on() and logic.has_vertical_movement(state)) or logic.has_glide(state) or logic.has_swimming(state), @@ -667,14 +662,13 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti TOWER_OF_ZOT_AP_REGION: lambda state: logic.has_glide(state)}) #Salmon Bay end #The Open Sea start - fancy_add_exits(world, THE_OPEN_SEA_AP_REGION, [SEASIDE_CLIFFS_AP_REGION, PROVING_MEADOWS_AP_REGION, CAPITAL_MOAT_AP_REGION, WEST_COBBLESTONE_CRAG_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, BAZAAR_COAST_AP_REGION, SARA_SARA_BEACH_EAST_AP_REGION, RENTAL_QUINTAR_BEACH_EP_AP_REGION, RUINS_CRUMBLING_ON_SHORE_AP_REGION, SALMON_BAY_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, THE_UNDERCITY_AP_REGION, JIDAMBA_ATOLLS_AP_REGION, JIDAMBA_WATERWAYS_AP_REGION, THE_DEEP_SEA_AP_REGION], + fancy_add_exits(world, THE_OPEN_SEA_AP_REGION, [SEASIDE_CLIFFS_AP_REGION, PROVING_MEADOWS_AP_REGION, CAPITAL_MOAT_AP_REGION, WEST_COBBLESTONE_CRAG_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, BAZAAR_COAST_AP_REGION, SARA_SARA_BEACH_EAST_AP_REGION, RENTAL_QUINTAR_BEACH_EP_AP_REGION, RUINS_CRUMBLING_ON_SHORE_AP_REGION, SALMON_BAY_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION, JIDAMBA_ATOLLS_AP_REGION, JIDAMBA_WATERWAYS_AP_REGION, THE_DEEP_SEA_AP_REGION], {SEASIDE_CLIFFS_AP_REGION: lambda state: logic.has_swimming(state), PROVING_MEADOWS_AP_REGION: lambda state: logic.has_swimming(state), CAPITAL_MOAT_AP_REGION: lambda state: logic.has_swimming(state), WEST_COBBLESTONE_CRAG_AP_REGION: lambda state: logic.has_swimming(state), SHOUDU_WATERFRONT_AP_REGION: lambda state: logic.has_swimming(state), - #TODO: this Undercity connection is to the Pah Summon cave specifically, though there may be more connections - THE_UNDERCITY_AP_REGION: lambda state: logic.has_swimming(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), BAZAAR_COAST_AP_REGION: lambda state: logic.has_swimming(state), SARA_SARA_BEACH_EAST_AP_REGION: lambda state: logic.has_swimming(state), RENTAL_QUINTAR_BEACH_EP_AP_REGION: lambda state: logic.has_swimming(state), @@ -693,17 +687,16 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti CONTINENTAL_TRAM_AP_REGION: lambda state: logic.has_swimming(state)}) #The Open Sea end #Shoudu Province start (though the Waterfront is a separate display region) - fancy_add_exits(world, SHOUDU_WATERFRONT_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, EAST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, THE_UNDERCITY_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], + fancy_add_exits(world, SHOUDU_WATERFRONT_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, EAST_COBBLESTONE_CRAG_AP_REGION, OKIMOTO_NS_AP_REGION, PAH_SUMMON_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], {SHOUDU_DOCKSIDE_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state) or logic.has_swimming(state), SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), - #TODO: this Undercity connection is to the Pah Summon cave specifically - THE_UNDERCITY_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), + PAH_SUMMON_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), FLYERS_CRAG_LOWER_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state)}) - fancy_add_exits(world, SHOUDU_DOCKSIDE_AP_REGION, [SHOUDU_WATERFRONT_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, EAST_COBBLESTONE_CRAG_AP_REGION, SARA_SARA_BAZAAR_AP_REGION, THE_UNDERCITY_AP_REGION], + fancy_add_exits(world, SHOUDU_DOCKSIDE_AP_REGION, [SHOUDU_WATERFRONT_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, SARA_SARA_BAZAAR_AP_REGION, EAST_UNDERCITY_WAREHOUSE_AP_REGION], {SHOUDU_PROVINCE_PROPER_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state), SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), SARA_SARA_BAZAAR_AP_REGION: lambda state: (state.has(THE_OPEN_SEA_PASS, player) or not logic.is_regionsanity_extreme()) and state.has(FERRY_PASS, player)}) - fancy_add_exits(world, SHOUDU_PROVINCE_PROPER_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, NORTHEAST_MIDPOINT_SCAFFOLDING_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_WATERWAYS_AP_REGION], + fancy_add_exits(world, SHOUDU_PROVINCE_PROPER_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, NORTHEAST_MIDPOINT_SCAFFOLDING_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION, BALANCE_BEAM_NEAR_WHITE_HUT_UNDERCITY_CONNECTOR_AP_REGION], {SHOUDU_ELEVATOR_BASE_AP_REGION: lambda state: logic.has_glide(state), NORTHEAST_MIDPOINT_SCAFFOLDING_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state), SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state), @@ -728,23 +721,43 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti fancy_add_exits(world, SKY_ARENA_AP_REGION, [SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, NORTHEAST_UPPER_SCAFFOLDING_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION, SHOUDU_WATERWAYS_AP_REGION], {SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION: lambda state: logic.has_glide(state), SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) - fancy_add_exits(world, SHOUDU_WATERWAYS_AP_REGION, [SHOUDU_WATERFRONT_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, OKIMOTO_NS_AP_REGION, THE_OPEN_SEA_AP_REGION, THE_UNDERCITY_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, QUINTAR_RESERVE_AP_REGION, RESERVE_BLUFFS_AP_REGION], + fancy_add_exits(world, BALANCE_BEAM_NEAR_WHITE_HUT_UNDERCITY_CONNECTOR_AP_REGION, [SHOUDU_PROVINCE_PROPER_AP_REGION, THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, SHADOW_MASTER_ENTRANCE_AP_REGION]) + fancy_add_exits(world, HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION, [SHOUDU_PROVINCE_PROPER_AP_REGION, THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, EAST_UNDERCITY_WALL_CLIMB_AP_REGION]) + fancy_add_exits(world, SHOUDU_WATERWAYS_AP_REGION, [SHOUDU_WATERFRONT_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, OKIMOTO_NS_AP_REGION, THE_OPEN_SEA_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, QUINTAR_RESERVE_AP_REGION, RESERVE_BLUFFS_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION], {SHOUDU_WATERFRONT_AP_REGION: lambda state: logic.has_swimming(state), SHOUDU_DOCKSIDE_AP_REGION: lambda state: logic.has_swimming(state), SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION: lambda state: logic.has_swimming(state), OKIMOTO_NS_AP_REGION: lambda state: logic.has_swimming(state), THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state), - #TODO: multiple entrances from Shoudu Waterways into the Undercity, including the Pah Summon cave - THE_UNDERCITY_AP_REGION: lambda state: logic.has_swimming(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), GANYMEDE_SHRINE_AP_REGION: lambda state: logic.has_swimming(state), GANYMEDE_STEEPLE_AP_REGION: lambda state: logic.has_horizontal_movement(state) and logic.has_swimming(state) and logic.obscure_routes_on(), QUINTAR_RESERVE_AP_REGION: lambda state: logic.has_swimming(state), RESERVE_BLUFFS_AP_REGION: lambda state: logic.has_swimming(state)}) #Shoudu Province end - fancy_add_exits(world, THE_UNDERCITY_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, THE_OPEN_SEA_AP_REGION], - {SHOUDU_PROVINCE_PROPER_AP_REGION: lambda state: logic.has_vertical_movement(state), - SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), - THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state)}) + #The Undercity start + fancy_add_exits(world, THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, EAST_UNDERCITY_WAREHOUSE_AP_REGION, DUEL_MASTER_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION, SHADOW_MASTER_ENTRANCE_AP_REGION], + {SHADOW_MASTER_ENTRANCE_AP_REGION: lambda state: logic.has_horizontal_movement(state) or logic.has_vertical_movement(state), + DUEL_MASTER_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_glide(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) + fancy_add_exits(world, EAST_UNDERCITY_WAREHOUSE_AP_REGION, [SHOUDU_DOCKSIDE_AP_REGION, EAST_UNDERCITY_WALL_CLIMB_AP_REGION, THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, SHADOW_MASTER_ENTRANCE_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION], + {EAST_UNDERCITY_WALL_CLIMB_AP_REGION: lambda state: logic.has_vertical_movement(state) and logic.is_hop_to_it_at_least_fancy_footwork(), + THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION: lambda state: logic.has_vertical_movement(state) or logic.has_horizontal_movement(state), + SHADOW_MASTER_ENTRANCE_AP_REGION: lambda state: logic.has_vertical_movement(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) + fancy_add_exits(world, EAST_UNDERCITY_WALL_CLIMB_AP_REGION, [EAST_UNDERCITY_WAREHOUSE_AP_REGION, HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION], + {HOLE_NEAR_PRIZE_COUNTER_UNDERCITY_CONNECTOR_AP_REGION: lambda state: logic.has_vertical_movement(state)}) + fancy_add_exits(world, DUEL_MASTER_AP_REGION, [THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION]) + fancy_add_exits(world, SHADOW_MASTER_ENTRANCE_AP_REGION, [THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, SHADOW_MASTER_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION], + {SHADOW_MASTER_AP_REGION: lambda state: logic.has_horizontal_movement(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) + fancy_add_exits(world, SHADOW_MASTER_AP_REGION, [SHADOW_MASTER_ENTRANCE_AP_REGION, UNDERCITY_WATERWAYS_AP_REGION], + {SHADOW_MASTER_ENTRANCE_AP_REGION: lambda state: logic.has_horizontal_movement(state), + UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) + fancy_add_exits(world, PAH_SUMMON_AP_REGION, [UNDERCITY_WATERWAYS_AP_REGION], + {UNDERCITY_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) + fancy_add_exits(world, UNDERCITY_WATERWAYS_AP_REGION, [THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, EAST_UNDERCITY_WAREHOUSE_AP_REGION, DUEL_MASTER_AP_REGION, SHADOW_MASTER_AP_REGION, SHADOW_MASTER_ENTRANCE_AP_REGION, PAH_SUMMON_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, THE_OPEN_SEA_AP_REGION]) + #The Undercity end #Ganymede Shrine start fancy_add_exits(world, GANYMEDE_SHRINE_AP_REGION, [OKIMOTO_NS_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SHOUDU_GOLD_NEAR_GANYMEDE_AP_REGION, SHOUDU_WATERWAYS_AP_REGION, QUINTAR_RESERVE_AP_REGION, FLYERS_CRAG_LOWER_AP_REGION], {OKIMOTO_NS_AP_REGION: lambda state: logic.has_swimming(state), @@ -941,8 +954,9 @@ def init_areas(world: "CrystalProjectWorld", locations: List[LocationData], opti {SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state), GANYMEDE_STEEPLE_AP_REGION: lambda state: (logic.has_horizontal_movement(state) and logic.obscure_routes_on()) or logic.has_glide(state), JIDAMBA_SUMMIT_AP_REGION: lambda state: (state.has(THE_OPEN_SEA_PASS, player) or not logic.is_regionsanity_extreme()) and logic.has_glide(state)}) - fancy_add_exits(world, FLYERS_CRAG_LOWER_AP_REGION, [THE_OPEN_SEA_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_WATERWAYS_AP_REGION], + fancy_add_exits(world, FLYERS_CRAG_LOWER_AP_REGION, [THE_OPEN_SEA_AP_REGION, PAH_SUMMON_AP_REGION, SHOUDU_WATERFRONT_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_WATERWAYS_AP_REGION], {THE_OPEN_SEA_AP_REGION: lambda state: logic.has_swimming(state), + PAH_SUMMON_AP_REGION: lambda state: logic.has_glide(state) or logic.has_swimming(state), SHOUDU_WATERWAYS_AP_REGION: lambda state: logic.has_swimming(state)}) #Flyer's Crag end #Jidamba Tangle start @@ -1166,7 +1180,7 @@ def connect_menu_region(world: "CrystalProjectWorld", options: CrystalProjectOpt logic = CrystalProjectLogic(world.player, options) player = world.player - fancy_add_exits(world, MENU_AP_REGION, [SPAWNING_MEADOWS_AP_REGION, DELENDE_PLAINS_AP_REGION, DELENDE_HIGH_BRIDGES_AP_REGION, DELENDE_PEAK_AP_REGION, MERCURY_SHRINE_AP_REGION, THE_PALE_GROTTO_AP_REGION, SEASIDE_CLIFFS_AP_REGION, YAMAGAWA_MA_AP_REGION, PROVING_MEADOWS_AP_REGION, SKUMPARADISE_AP_REGION, CAPITAL_SEQUOIA_AP_REGION, CAPITAL_JAIL_AP_REGION, JAIL_DARK_WING_AP_REGION, ROLLING_QUINTAR_FIELDS_AP_REGION, SANCTUM_ENTRANCE_AP_REGION, QUINTAR_SANCTUM_AP_REGION, BOOMER_SOCIETY_AP_REGION, OKIMOTO_NS_AP_REGION, SALMON_PASS_EAST_AP_REGION, SALMON_RIVER_AP_REGION, CASTLE_SEQUOIA_AP_REGION, TOWER_OF_ZOT_AP_REGION, POKO_POKO_DESERT_AP_REGION, SARA_SARA_BAZAAR_AP_REGION, IBEK_CAVE_MOUTH_AP_REGION, BEACH_BIRDS_NEST_AP_REGION, BEAURIOR_VOLCANO_AP_REGION, BEAURIOR_ROCK_AP_REGION, ANCIENT_RESERVOIR_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SKY_ARENA_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, THE_UNDERCITY_AP_REGION, PIPELINE_NORTH_AP_REGION, PIPELINE_SOUTH_AP_REGION, SEQUOIA_ATHENAEUM_ENTRANCE_AP_REGION, LOWER_ICE_LAKES_AP_REGION, SOUVENIR_SHOP_AP_REGION, SLIP_GLIDE_RIDE_EXIT_AP_REGION, UPPER_ICE_LAKES_AP_REGION, TALL_TALL_SAVE_POINT_AP_REGION, PEAK_RAMPARTS_AP_REGION, SLIP_GLIDE_RIDE_ENTRANCE_AP_REGION, LANDS_END_AP_REGION, OWL_TREE_AP_REGION, QUINTAR_RESERVE_AP_REGION, EUROPA_SHRINE_AP_REGION, EACLANEYA_ENTRANCE_AP_REGION, SALMON_ROOM_AP_REGION, LABYRINTH_CORE_AP_REGION, DIONE_SHRINE_AP_REGION, DIONE_ROOF_AP_REGION, THE_SEQUOIA_AP_REGION, CHALICE_FOOT_AP_REGION, THE_OPEN_SEA_AP_REGION, CONTINENTAL_TRAM_AP_REGION, POSEIDON_SHRINE_ROOF_AP_REGION, NEPTUNE_SHRINE_AP_REGION, THE_OLD_WORLD_AP_REGION, THE_NEW_WORLD_AP_REGION, DISCIPLINE_HOLLOW_AP_REGION, MODDED_ZONE_AP_REGION], + fancy_add_exits(world, MENU_AP_REGION, [SPAWNING_MEADOWS_AP_REGION, DELENDE_PLAINS_AP_REGION, DELENDE_HIGH_BRIDGES_AP_REGION, DELENDE_PEAK_AP_REGION, MERCURY_SHRINE_AP_REGION, THE_PALE_GROTTO_AP_REGION, SEASIDE_CLIFFS_AP_REGION, YAMAGAWA_MA_AP_REGION, PROVING_MEADOWS_AP_REGION, SKUMPARADISE_AP_REGION, CAPITAL_SEQUOIA_AP_REGION, CAPITAL_JAIL_AP_REGION, JAIL_DARK_WING_AP_REGION, ROLLING_QUINTAR_FIELDS_AP_REGION, SANCTUM_ENTRANCE_AP_REGION, QUINTAR_SANCTUM_AP_REGION, BOOMER_SOCIETY_AP_REGION, OKIMOTO_NS_AP_REGION, SALMON_PASS_EAST_AP_REGION, SALMON_RIVER_AP_REGION, CASTLE_SEQUOIA_AP_REGION, TOWER_OF_ZOT_AP_REGION, POKO_POKO_DESERT_AP_REGION, SARA_SARA_BAZAAR_AP_REGION, IBEK_CAVE_MOUTH_AP_REGION, BEACH_BIRDS_NEST_AP_REGION, BEAURIOR_VOLCANO_AP_REGION, BEAURIOR_ROCK_AP_REGION, ANCIENT_RESERVOIR_AP_REGION, SHOUDU_DOCKSIDE_AP_REGION, SHOUDU_PROVINCE_PROPER_AP_REGION, SHOUDU_ELEVATOR_BASE_AP_REGION, SHOUDU_FIELDS_WEST_SCAFFOLDING_AP_REGION, SKY_ARENA_AP_REGION, GANYMEDE_SHRINE_AP_REGION, GANYMEDE_STEEPLE_AP_REGION, THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION, PIPELINE_NORTH_AP_REGION, PIPELINE_SOUTH_AP_REGION, SEQUOIA_ATHENAEUM_ENTRANCE_AP_REGION, LOWER_ICE_LAKES_AP_REGION, SOUVENIR_SHOP_AP_REGION, SLIP_GLIDE_RIDE_EXIT_AP_REGION, UPPER_ICE_LAKES_AP_REGION, TALL_TALL_SAVE_POINT_AP_REGION, PEAK_RAMPARTS_AP_REGION, SLIP_GLIDE_RIDE_ENTRANCE_AP_REGION, LANDS_END_AP_REGION, OWL_TREE_AP_REGION, QUINTAR_RESERVE_AP_REGION, EUROPA_SHRINE_AP_REGION, EACLANEYA_ENTRANCE_AP_REGION, SALMON_ROOM_AP_REGION, LABYRINTH_CORE_AP_REGION, DIONE_SHRINE_AP_REGION, DIONE_ROOF_AP_REGION, THE_SEQUOIA_AP_REGION, CHALICE_FOOT_AP_REGION, THE_OPEN_SEA_AP_REGION, CONTINENTAL_TRAM_AP_REGION, POSEIDON_SHRINE_ROOF_AP_REGION, NEPTUNE_SHRINE_AP_REGION, THE_OLD_WORLD_AP_REGION, THE_NEW_WORLD_AP_REGION, DISCIPLINE_HOLLOW_AP_REGION, MODDED_ZONE_AP_REGION], {SPAWNING_MEADOWS_AP_REGION: lambda state: state.has(HOMEPOINT_AP_SPAWN_NAME, player) or state.has(HOMEPOINT_OLD_NANS_WATERING_HOLE_NAME, player), DELENDE_PLAINS_AP_REGION: lambda state: (state.has(HOMEPOINT_THE_PALE_GROTTO_ENTRANCE_NAME, player) or state.has(HOMEPOINT_SOILED_DEN_NAME, player) or state.has(HOMEPOINT_FISH_HATCHERY_NAME, player)), DELENDE_HIGH_BRIDGES_AP_REGION: lambda state: (state.has(HOMEPOINT_CABIN_ON_THE_CLIFF_NAME, player) or state.has(HOMEPOINT_DELENDE_FALLS_NAME, player)), @@ -1203,7 +1217,7 @@ def connect_menu_region(world: "CrystalProjectWorld", options: CrystalProjectOpt SKY_ARENA_AP_REGION: lambda state: state.has(HOMEPOINT_SKY_ARENA_NAME, player), GANYMEDE_SHRINE_AP_REGION: lambda state: state.has(HOMEPOINT_GANYMEDE_SHRINE_NAME, player), GANYMEDE_STEEPLE_AP_REGION: lambda state: state.has(GANYMEDE_STONE, player), - THE_UNDERCITY_AP_REGION: lambda state: state.has(HOMEPOINT_THE_UNDERCITY_NAME, player), + THE_UNDERCITY_HOMEPOINT_AND_BLADE_MASTER_AP_REGION: lambda state: state.has(HOMEPOINT_THE_UNDERCITY_NAME, player), PIPELINE_NORTH_AP_REGION: lambda state: state.has(HOMEPOINT_CAPITAL_PIPELINE_NAME, player), PIPELINE_SOUTH_AP_REGION: lambda state: state.has(HOMEPOINT_EAST_CAPITAL_PIPELINE_NAME, player), SEQUOIA_ATHENAEUM_ENTRANCE_AP_REGION: lambda state: state.has(HOMEPOINT_SEQUOIA_ATHENAEUM_NAME, player),