From 18f15d80f94ae8e81b4ab70d31b68be372a3eebd Mon Sep 17 00:00:00 2001 From: CaitSith2 Date: Wed, 22 Jan 2020 09:27:25 -0800 Subject: [PATCH] MSU-1 (#13) * Add Extended MSU as an option --- EntranceRandomizer.py | 3 ++- Main.py | 8 +++++--- Mystery.py | 1 + Rom.py | 19 ++++++++++--------- 4 files changed, 18 insertions(+), 13 deletions(-) diff --git a/EntranceRandomizer.py b/EntranceRandomizer.py index c1eb9e8a..724d0d4b 100755 --- a/EntranceRandomizer.py +++ b/EntranceRandomizer.py @@ -208,6 +208,7 @@ def parse_arguments(argv, no_defaults=False): ''') parser.add_argument('--quickswap', help='Enable quick item swapping with L and R.', action='store_true') parser.add_argument('--disablemusic', help='Disables game music.', action='store_true') + parser.add_argument('--extendedmsu', help='Use v31 Extended msu', action='store_true') parser.add_argument('--mapshuffle', default=defval(False), help='Maps are no longer restricted to their dungeons, but can be anywhere', action='store_true') parser.add_argument('--compassshuffle', default=defval(False), help='Compasses are no longer restricted to their dungeons, but can be anywhere', action='store_true') parser.add_argument('--keyshuffle', default=defval(False), help='Small Keys are no longer restricted to their dungeons, but can be anywhere', action='store_true') @@ -294,7 +295,7 @@ def parse_arguments(argv, no_defaults=False): 'shufflebosses', 'shuffleenemies', 'enemy_health', 'enemy_damage', 'shufflepots', 'ow_palettes', 'uw_palettes', 'sprite', 'disablemusic', 'quickswap', 'fastmenu', 'heartcolor', 'heartbeep', - 'remote_items', 'progressive']: + 'remote_items', 'progressive', 'extendedmsu']: 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/Main.py b/Main.py index 1335d908..37bb4e4e 100644 --- a/Main.py +++ b/Main.py @@ -56,6 +56,7 @@ def main(args, seed=None): world.beemizer = args.beemizer.copy() world.shufflepots = args.shufflepots.copy() world.progressive = args.progressive.copy() + world.extendedmsu = args.extendedmsu.copy() world.rom_seeds = {player: random.randint(0, 999999999) for player in range(1, world.players + 1)} @@ -159,14 +160,14 @@ def main(args, seed=None): or world.enemy_health[player] != 'default' or world.enemy_damage[player] != 'default' or args.shufflepots[player] or sprite_random_on_hit) - rom = JsonRom() if args.jsonout or use_enemizer else LocalRom(args.rom) + rom = JsonRom() if args.jsonout or use_enemizer else LocalRom(args.rom, extendedmsu=args.extendedmsu[player]) patch_rom(world, rom, player, team, use_enemizer) if use_enemizer and (args.enemizercli or not args.jsonout): - patch_enemizer(world, player, rom, args.rom, args.enemizercli, args.shufflepots[player], sprite_random_on_hit) + patch_enemizer(world, player, rom, args.rom, args.enemizercli, args.shufflepots[player], sprite_random_on_hit, extendedmsu=args.extendedmsu[player]) if not args.jsonout: - rom = LocalRom.fromJsonRom(rom, args.rom, 0x400000) + rom = LocalRom.fromJsonRom(rom, args.rom, 0x400000, args.extendedmsu[player]) if args.race: patch_race_rom(rom) @@ -273,6 +274,7 @@ def copy_world(world): ret.enemy_damage = world.enemy_damage.copy() ret.beemizer = world.beemizer.copy() ret.shufflepots = world.shufflepots.copy() + ret.extendedmsu = world.extendedmsu.copy() for player in range(1, world.players + 1): if world.mode[player] != 'inverted': diff --git a/Mystery.py b/Mystery.py index fb2cc84e..71e61672 100644 --- a/Mystery.py +++ b/Mystery.py @@ -226,6 +226,7 @@ def roll_settings(weights): romweights = weights['rom'] ret.sprite = get_choice('sprite', romweights) ret.disablemusic = get_choice('disablemusic', romweights) + ret.extendedmsu = get_choice('extendedmsu', romweights) ret.quickswap = get_choice('quickswap', romweights) ret.fastmenu = get_choice('menuspeed', romweights) ret.heartcolor = get_choice('heartcolor', romweights) diff --git a/Rom.py b/Rom.py index 514eebb9..9bb65dfb 100644 --- a/Rom.py +++ b/Rom.py @@ -72,14 +72,15 @@ class JsonRom(object): class LocalRom(object): - def __init__(self, file, patch=True, name=None, hash=None): + def __init__(self, file, extendedmsu=False, patch=True, name=None, hash=None): self.name = name self.hash = hash self.orig_buffer = None + self.extendedmsu = extendedmsu with open(file, 'rb') as stream: self.buffer = read_rom(stream) if patch: - self.patch_base_rom() + self.patch_base_rom(extendedmsu) self.orig_buffer = self.buffer.copy() def write_byte(self, address, value): @@ -94,25 +95,25 @@ class LocalRom(object): outfile.write(self.buffer) @staticmethod - def fromJsonRom(rom, file, rom_size = 0x200000): - ret = LocalRom(file, True, rom.name, rom.hash) + def fromJsonRom(rom, file, rom_size = 0x200000, extendedmsu=False): + ret = LocalRom(file, extendedmsu, True, rom.name, rom.hash) ret.buffer.extend(bytearray([0x00]) * (rom_size - len(ret.buffer))) for address, values in rom.patches.items(): ret.write_bytes(int(address), values) return ret - def patch_base_rom(self): + def patch_base_rom(self, extendedmsu): # verify correct checksum of baserom basemd5 = hashlib.md5() basemd5.update(self.buffer) if JAP10HASH != basemd5.hexdigest(): logging.getLogger('').warning('Supplied Base Rom does not match known MD5 for JAP(1.0) release. Will try to patch anyway.') - + # extend to 2MB self.buffer.extend(bytearray([0x00]) * (0x200000 - len(self.buffer))) # load randomizer patches - with open(local_path('data/base2current.json'), 'r') as stream: + with open(local_path('data/base2current.json') if not extendedmsu else local_path('data/base2current_extendedmsu.json'), 'r') as stream: patches = json.load(stream) for patch in patches: if isinstance(patch, dict): @@ -156,9 +157,9 @@ def read_rom(stream): buffer = buffer[0x200:] return buffer -def patch_enemizer(world, player, rom, baserom_path, enemizercli, shufflepots, random_sprite_on_hit): +def patch_enemizer(world, player, rom, baserom_path, enemizercli, shufflepots, random_sprite_on_hit, extendedmsu): baserom_path = os.path.abspath(baserom_path) - basepatch_path = os.path.abspath(local_path('data/base2current.json')) + basepatch_path = os.path.abspath(local_path('data/base2current.json') if not extendedmsu else local_path('data/base2current_extendedmsu.json')) enemizer_basepatch_path = os.path.join(os.path.dirname(enemizercli), "enemizerBasePatch.json") randopatch_path = os.path.abspath(output_path('enemizer_randopatch.json')) options_path = os.path.abspath(output_path('enemizer_options.json'))