From 25068bcfdd0c39ee92a1675752fcff2c7eee2cc7 Mon Sep 17 00:00:00 2001 From: Bonta-kun <40473493+Bonta0@users.noreply.github.com> Date: Thu, 12 Dec 2019 09:20:32 +0100 Subject: [PATCH] Added an option to pre-open the pyramid hole (aka "fast ganon") --- BaseClasses.py | 1 + EntranceRandomizer.py | 4 +++- Gui.py | 4 ++++ Main.py | 1 + Rom.py | 4 ++-- Rules.py | 4 ++-- 6 files changed, 13 insertions(+), 5 deletions(-) diff --git a/BaseClasses.py b/BaseClasses.py index ff266bab..fc1dd304 100644 --- a/BaseClasses.py +++ b/BaseClasses.py @@ -76,6 +76,7 @@ class World(object): self.hints = hints self.crystals_needed_for_ganon = 7 self.crystals_needed_for_gt = 7 + self.open_pyramid = False self.dynamic_regions = [] self.dynamic_locations = [] self.spoiler = Spoiler(self) diff --git a/EntranceRandomizer.py b/EntranceRandomizer.py index 6e8af120..13155bd0 100755 --- a/EntranceRandomizer.py +++ b/EntranceRandomizer.py @@ -178,7 +178,9 @@ def start(): Random: Picks a random value between 0 and 7 (inclusive). 0-7: Number of crystals needed ''') - + parser.add_argument('--openpyramid', help='''\ + Pre-opens the pyramid hole, this removes the Agahnim 2 requirement for it + ''', action='store_true') parser.add_argument('--rom', default='Zelda no Densetsu - Kamigami no Triforce (Japan).sfc', help='Path to an ALttP JAP(1.0) rom to use as a base.') parser.add_argument('--loglevel', default='info', const='info', nargs='?', choices=['error', 'info', 'warning', 'debug'], help='Select level of logging for output.') parser.add_argument('--seed', help='Define seed number to generate.', type=int) diff --git a/Gui.py b/Gui.py index 8f7ec87f..f03d8377 100755 --- a/Gui.py +++ b/Gui.py @@ -61,6 +61,8 @@ def guiMain(args=None): suppressRomCheckbutton = Checkbutton(checkBoxFrame, text="Do not create patched Rom", variable=suppressRomVar) quickSwapVar = IntVar() quickSwapCheckbutton = Checkbutton(checkBoxFrame, text="Enabled L/R Item quickswapping", variable=quickSwapVar) + openpyramidVar = IntVar() + openpyramidCheckbutton = Checkbutton(checkBoxFrame, text="Pre-open Pyramid Hole", variable=openpyramidVar) keysanityVar = IntVar() keysanityCheckbutton = Checkbutton(checkBoxFrame, text="Keysanity (keys anywhere)", variable=keysanityVar) retroVar = IntVar() @@ -81,6 +83,7 @@ def guiMain(args=None): createSpoilerCheckbutton.pack(expand=True, anchor=W) suppressRomCheckbutton.pack(expand=True, anchor=W) quickSwapCheckbutton.pack(expand=True, anchor=W) + openpyramidCheckbutton.pack(expand=True, anchor=W) keysanityCheckbutton.pack(expand=True, anchor=W) retroCheckbutton.pack(expand=True, anchor=W) dungeonItemsCheckbutton.pack(expand=True, anchor=W) @@ -381,6 +384,7 @@ def guiMain(args=None): guiargs.fastmenu = fastMenuVar.get() guiargs.create_spoiler = bool(createSpoilerVar.get()) guiargs.suppress_rom = bool(suppressRomVar.get()) + guiargs.openpyramid = bool(openpyramidVar.get()) guiargs.keysanity = bool(keysanityVar.get()) guiargs.retro = bool(retroVar.get()) guiargs.nodungeonitems = bool(dungeonItemsVar.get()) diff --git a/Main.py b/Main.py index 851a8cfc..2c8c4ef0 100644 --- a/Main.py +++ b/Main.py @@ -36,6 +36,7 @@ def main(args, seed=None): world.crystals_needed_for_ganon = random.randint(0, 7) if args.crystals_ganon == 'random' else int(args.crystals_ganon) world.crystals_needed_for_gt = random.randint(0, 7) if args.crystals_gt == 'random' else int(args.crystals_gt) + world.open_pyramid = args.openpyramid world.rom_seeds = {player: random.randint(0, 999999999) for player in range(1, world.players + 1)} diff --git a/Rom.py b/Rom.py index c8dcec01..73ce31d7 100644 --- a/Rom.py +++ b/Rom.py @@ -870,8 +870,8 @@ def patch_rom(world, player, rom): rom.write_bytes(0x50563, [0x3F, 0x14]) # disable below ganon chest rom.write_byte(0x50599, 0x00) # disable below ganon chest rom.write_bytes(0xE9A5, [0x7E, 0x00, 0x24]) # disable below ganon chest - rom.write_byte(0x18008B, 0x00) # Pyramid Hole not pre-opened - rom.write_byte(0x18008C, 0x01 if world.crystals_needed_for_gt == 0 else 0x00) # Pyramid Hole pre-opened if crystal requirement is 0 + rom.write_byte(0x18008B, 0x01 if world.open_pyramid else 0x00) # pre-open Pyramid Hole + rom.write_byte(0x18008C, 0x01 if world.crystals_needed_for_gt == 0 else 0x00) # GT pre-opened if crystal requirement is 0 rom.write_byte(0xF5D73, 0xF0) # bees are catchable rom.write_byte(0xF5F10, 0xF0) # bees are catchable rom.write_byte(0x180086, 0x00 if world.aga_randomness else 0x01) # set blue ball and ganon warp randomness diff --git a/Rules.py b/Rules.py index 3c2bc18c..cfd43c63 100644 --- a/Rules.py +++ b/Rules.py @@ -455,7 +455,7 @@ def default_rules(world, player): set_rule(world.get_entrance('Floating Island Mirror Spot', player), lambda state: state.has_Mirror(player)) set_rule(world.get_entrance('Turtle Rock', player), lambda state: state.has_Pearl(player) and state.has_sword(player) and state.has_turtle_rock_medallion(player) and state.can_reach('Turtle Rock (Top)', 'Region', player)) # sword required to cast magic (!) - set_rule(world.get_entrance('Pyramid Hole', player), lambda state: state.has('Beat Agahnim 2', player)) + set_rule(world.get_entrance('Pyramid Hole', player), lambda state: state.has('Beat Agahnim 2', player) or world.open_pyramid) set_rule(world.get_entrance('Ganons Tower', player), lambda state: False) # This is a safety for the TR function below to not require GT entrance in its key logic. if world.swords == 'swordless': @@ -610,7 +610,7 @@ def inverted_rules(world, player): set_rule(world.get_entrance('Dark Grassy Lawn Flute', player), lambda state: state.can_flute(player)) set_rule(world.get_entrance('Hammer Peg Area Flute', player), lambda state: state.can_flute(player)) - set_rule(world.get_entrance('Inverted Pyramid Hole', player), lambda state: state.has('Beat Agahnim 2', player)) + set_rule(world.get_entrance('Inverted Pyramid Hole', player), lambda state: state.has('Beat Agahnim 2', player) or world.open_pyramid) set_rule(world.get_entrance('Inverted Ganons Tower', player), lambda state: False) # This is a safety for the TR function below to not require GT entrance in its key logic. if world.swords == 'swordless':