From 1e2caab0b3ee9562b484d2c3d019670118a92db1 Mon Sep 17 00:00:00 2001 From: Kara Alexandra Date: Tue, 5 Sep 2023 19:46:02 -0500 Subject: [PATCH] Added bug net mode --- BaseClasses.py | 65 ++++++++++++++++++++++++++++++++++--- InitialSram.py | 13 +++++--- ItemList.py | 33 ++++++++----------- Items.py | 1 + Rom.py | 52 ++++++++++++++++++++++++----- Rules.py | 9 ++--- resources/app/cli/args.json | 3 +- 7 files changed, 133 insertions(+), 43 deletions(-) diff --git a/BaseClasses.py b/BaseClasses.py index 7a850d00..dd5e32b2 100644 --- a/BaseClasses.py +++ b/BaseClasses.py @@ -435,6 +435,19 @@ class World(object): ret.prog_items['L2 Cane', item.player] += 1 else: ret.prog_items['L1 Cane', item.player] += 1 + elif 'Net' in item.name: + if ret.has('L5 Net', item.player): + pass + elif ret.has('L4 Net', item.player): + ret.prog_items['L5 Net', item.player] += 1 + elif ret.has('L3 Net', item.player): + ret.prog_items['L4 Net', item.player] += 1 + elif ret.has('L2 Net', item.player): + ret.prog_items['L3 Net', item.player] += 1 + elif ret.has('L1 Net', item.player): + ret.prog_items['L2 Net', item.player] += 1 + else: + ret.prog_items['L1 Net', item.player] += 1 elif 'Glove' in item.name: if ret.has('Titans Mitts', item.player): pass @@ -1048,6 +1061,7 @@ class CollectionState(object): 'Blue Pendant', 'Red Pendant', 'Crystal 1', 'Crystal 2', 'Crystal 3', 'Crystal 4', 'Crystal 5', 'Crystal 6', 'Crystal 7', 'Blue Boomerang', 'Red Boomerang', 'Blue Shield', 'Red Shield', 'Mirror Shield', 'Progressive Shield', 'Bug Catching Net', 'Cane of Byrna', 'Ocarina (Activated)', + 'Progressive Bombs', 'Progressive Cane', 'Progressive Net', 'Boss Heart Container', 'Sanctuary Heart Container', 'Piece of Heart', 'Magic Upgrade (1/2)', 'Magic Upgrade (1/4)'] or item_name.startswith(('Bottle', 'Small Key', 'Big Key')) @@ -1272,8 +1286,6 @@ class CollectionState(object): return (not self.world.bombbag[player] or self.has('Bomb Upgrade (+10)', player) or self.has('Bomb Upgrade (+5)', player, 2)) and (self.world.override_bomb_check or self.can_farm_bombs(player)) def can_kill_with_bombs(self, player): - if self.world.swords[player] in ['cane', 'somaria', 'byrna']: - return False return self.can_use_bombs(player) def can_hit_crystal(self, player): @@ -1363,11 +1375,23 @@ class CollectionState(object): elif level == 1: return self.has('L5 Cane', player) or self.has('L4 Cane', player) or self.has('L3 Cane', player) or self.has('L2 Cane', player) or self.has('L1 Cane', player) return True + elif self.world.swords[player] in ['bugnet']: + if level == 5: + return self.has('L5 Net', player) + elif level == 4: + return self.has('L5 Net', player) or self.has('L4 Net', player) + elif level == 3: + return self.has('L5 Net', player) or self.has('L4 Net', player) or self.has('L3 Net', player) + elif level == 2: + return self.has('L5 Net', player) or self.has('L4 Net', player) or self.has('L3 Net', player) or self.has('L2 Net', player) + elif level == 1: + return self.has('L5 Net', player) or self.has('L4 Net', player) or self.has('L3 Net', player) or self.has('L2 Net', player) or self.has('L1 Net', player) + return True else: return False def special_weapon_check(self, player, level): - if self.world.swords[player] in ['bombs', 'byrna', 'somaria', 'cane']: + if self.world.swords[player] in ['bombs']: return self.has_special_weapon_level(player, level) else: return True @@ -1413,7 +1437,7 @@ class CollectionState(object): return False def can_use_medallions(self, player): - return self.has_sword(player) or self.world.swords[player] in ['bombs', 'byrna', 'somaria', 'cane'] + return self.has_sword(player) or self.world.swords[player] in ['bombs', 'byrna', 'somaria', 'cane', 'bugnet'] def has_blunt_weapon(self, player): return self.has_real_sword(player) or self.has('Hammer', player) @@ -1545,6 +1569,24 @@ class CollectionState(object): else: self.prog_items['L1 Cane', item.player] += 1 changed = True + elif 'Net' in item.name: + if self.has('L5 Net', item.player): + pass + elif self.has('L4 Net', item.player): + self.prog_items['L5 Net', item.player] += 1 + changed = True + elif self.has('L3 Net', item.player): + self.prog_items['L4 Net', item.player] += 1 + changed = True + elif self.has('L2 Net', item.player): + self.prog_items['L3 Net', item.player] += 1 + changed = True + elif self.has('L1 Net', item.player): + self.prog_items['L2 Net', item.player] += 1 + changed = True + else: + self.prog_items['L1 Net', item.player] += 1 + changed = True elif 'Glove' in item.name: if self.has('Titans Mitts', item.player): pass @@ -1650,6 +1692,19 @@ class CollectionState(object): to_remove = 'L1 Cane' else: to_remove = None + elif 'Net' in to_remove: + if self.has('L5 Net', item.player): + to_remove = 'L5 Net' + elif self.has('L4 Net', item.player): + to_remove = 'L4 Net' + elif self.has('L3 Net', item.player): + to_remove = 'L3 Net' + elif self.has('L2 Net', item.player): + to_remove = 'L2 Net' + elif self.has('L1 Net', item.player): + to_remove = 'L1 Net' + else: + to_remove = None elif 'Glove' in item.name: if self.has('Titans Mitts', item.player): to_remove = 'Titans Mitts' @@ -3619,7 +3674,7 @@ er_mode = {"vanilla": 0, "simple": 1, "restricted": 2, "full": 3, "crossed": 4, # byte 1: LLLW WSSS (logic, mode, sword) logic_mode = {"noglitches": 0, "minorglitches": 1, "nologic": 2, "owglitches": 3, "majorglitches": 4} world_mode = {"open": 0, "standard": 1, "inverted": 2} -sword_mode = {"random": 0, "assured": 1, "swordless": 2, "swordless_hammer": 2, "vanilla": 3, "bombs": 4, "pseudo": 5, "assured_pseudo": 5, "byrna": 6, "somaria": 6, "cane": 6, "bees": 7} +sword_mode = {"random": 0, "assured": 1, "swordless": 2, "swordless_b": 2, "vanilla": 3, "bombs": 4, "pseudo": 5, "assured_pseudo": 5, "byrna": 6, "somaria": 6, "cane": 6, "bees": 7, "bugnet": 7} # byte 2: GGGD DFFH (goal, diff, item_func, hints) goal_mode = {'ganon': 0, 'pedestal': 1, 'dungeons': 2, 'triforcehunt': 3, 'crystals': 4, 'trinity': 5, 'z1': 6, diff --git a/InitialSram.py b/InitialSram.py index e23f08e0..69ab270f 100644 --- a/InitialSram.py +++ b/InitialSram.py @@ -95,21 +95,23 @@ class InitialSram: elif startingstate.has('Fighter Sword', player): equip[0x359] = 1 - if startingstate.has('L5 Bombs', player) or startingstate.has('L5 Cane', player): + if startingstate.has('L5 Bombs', player) or startingstate.has('L5 Cane', player) or startingstate.has('L5 Net', player): equip[0x38F] = 5 - elif startingstate.has('L4 Bombs', player) or startingstate.has('L4 Cane', player): + elif startingstate.has('L4 Bombs', player) or startingstate.has('L4 Cane', player) or startingstate.has('L4 Net', player): equip[0x38F] = 4 - elif startingstate.has('L3 Bombs', player) or startingstate.has('L3 Cane', player): + elif startingstate.has('L3 Bombs', player) or startingstate.has('L3 Cane', player) or startingstate.has('L3 Net', player): equip[0x38F] = 3 - elif startingstate.has('L2 Bombs', player) or startingstate.has('L2 Cane', player): + elif startingstate.has('L2 Bombs', player) or startingstate.has('L2 Cane', player) or startingstate.has('L2 Net', player): equip[0x38F] = 2 - elif startingstate.has('L1 Bombs', player) or startingstate.has('L1 Cane', player) or world.swords[player] == 'cane': + elif startingstate.has('L1 Bombs', player) or startingstate.has('L1 Cane', player) or world.swords[player] == 'cane' or startingstate.has('L1 Net', player): equip[0x38F] = 1 if startingstate.has('L1 Cane', player) or startingstate.has('L2 Cane', player) or startingstate.has('L3 Cane', player) or startingstate.has('L4 Cane', player) or startingstate.has('L5 Cane', player): if world.swords[player] == 'byrna': equip[0x351] = 1 elif world.swords[player] == 'somaria': equip[0x350] = 1 + if startingstate.has('L1 Net', player) or startingstate.has('L2 Net', player) or startingstate.has('L3 Net', player) or startingstate.has('L4 Net', player) or startingstate.has('L5 Net', player): + equip[0x34D] = 1 if startingstate.has('Mirror Shield', player): equip[0x35A] = 3 @@ -139,6 +141,7 @@ class InitialSram: 'Golden Sword', 'Tempered Sword', 'Master Sword', 'Fighter Sword', 'Progressive Sword', 'L5 Bombs', 'L4 Bombs', 'L3 Bombs', 'L2 Bombs', 'L1 Bombs', 'Progressive Bombs', 'L5 Cane', 'L4 Cane', 'L3 Cane', 'L2 Cane', 'L1 Cane', 'Progressive Cane', + 'L5 Net', 'L4 Net', 'L3 Net', 'L2 Net', 'L1 Net', 'Progressive Net', 'Mirror Shield', 'Red Shield', 'Blue Shield', 'Progressive Shield', 'Red Mail', 'Blue Mail', 'Progressive Armor', 'Magic Upgrade (1/4)', 'Magic Upgrade (1/2)']: diff --git a/ItemList.py b/ItemList.py index e8e1b3bc..88148392 100644 --- a/ItemList.py +++ b/ItemList.py @@ -37,7 +37,7 @@ normalfinal25extra = ['Rupees (20)'] * 23 + ['Rupees (5)'] * 2 Difficulty = namedtuple('Difficulty', ['baseitems', 'bottles', 'bottle_count', 'same_bottle', 'progressiveshield', - 'basicshield', 'progressivearmor', 'basicarmor', 'swordless', 'bombs_only', 'cane_only', + 'basicshield', 'progressivearmor', 'basicarmor', 'swordless', 'bombs_only', 'cane_only', 'bugnet_mode', 'progressivesword', 'basicsword', 'basicbow', 'timedohko', 'timedother', 'retro', 'bombbag', 'extras', 'progressive_sword_limit', 'progressive_shield_limit', @@ -60,6 +60,7 @@ difficulties = { swordless = ['Rupees (20)'] * 4, bombs_only = ['Progressive Bombs'] * 4, cane_only = ['Progressive Cane'] * 3 + ['Rupees (20)'], + bugnet_mode = ['Progressive Net'] * 4, progressivesword = ['Progressive Sword'] * 4, basicsword = ['Fighter Sword', 'Master Sword', 'Tempered Sword', 'Golden Sword'], basicbow = ['Bow', 'Silver Arrows'], @@ -88,6 +89,7 @@ difficulties = { swordless = ['Rupees (20)'] * 4, bombs_only = ['Progressive Bombs'] * 4, cane_only = ['Progressive Cane'] * 3 + ['Rupees (20)'], + bugnet_mode = ['Progressive Net'] * 4, progressivesword = ['Progressive Sword'] * 4, basicsword = ['Fighter Sword', 'Master Sword', 'Master Sword', 'Tempered Sword'], basicbow = ['Bow'] * 2, @@ -116,6 +118,7 @@ difficulties = { swordless = ['Rupees (20)'] * 4, bombs_only = ['Progressive Bombs'] * 4, cane_only = ['Progressive Cane'] * 3 + ['Rupees (20)'], + bugnet_mode = ['Progressive Net'] * 4, progressivesword = ['Progressive Sword'] * 4, basicsword = ['Fighter Sword', 'Fighter Sword', 'Master Sword', 'Master Sword'], basicbow = ['Bow'] * 2, @@ -339,27 +342,11 @@ def generate_itempool(world, player): for item in precollected_items: world.push_precollected(ItemFactory(item, player)) - if world.mode[player] == 'standard' and not (world.state.has_special_weapon_level(player, 1) if world.swords[player] in ['bombs', 'byrna', 'somaria', 'cane'] else world.state.has_blunt_weapon(player)): + if world.mode[player] == 'standard' and not (world.state.has_special_weapon_level(player, 1) if world.swords[player] in ['bombs'] else world.state.has_blunt_weapon(player) or world.state.has_special_weapon_level(player, 1)): if world.swords[player] == 'bombs' and "Link's Uncle" not in placed_items: possible_weapons = [] for item in pool: - if item in ['Progressive Bombs', 'L1 Bombs', 'L2 Bombs', 'L3 Bombs', 'L4 Bombs', 'L5 Bombs']: - possible_weapons.append(item) - starting_weapon = random.choice(possible_weapons) - placed_items["Link's Uncle"] = starting_weapon - pool.remove(starting_weapon) - elif world.swords[player] in ['byrna', 'somaria'] and "Link's Uncle" not in placed_items: - possible_weapons = [] - for item in pool: - if item in ['Progressive Cane', 'L1 Cane', 'L2 Cane', 'L3 Cane', 'L4 Cane', 'L5 Cane']: - possible_weapons.append(item) - starting_weapon = random.choice(possible_weapons) - placed_items["Link's Uncle"] = starting_weapon - pool.remove(starting_weapon) - elif world.swords[player] in ['cane'] and "Link's Uncle" not in placed_items: - possible_weapons = [] - for item in pool: - if item in ['Cane of Byrna', 'Cane of Somaria']: + if item in ['Progressive Bombs']: possible_weapons.append(item) starting_weapon = random.choice(possible_weapons) placed_items["Link's Uncle"] = starting_weapon @@ -373,6 +360,9 @@ def generate_itempool(world, player): if not found_sword and world.swords[player] != 'swordless': found_sword = True possible_weapons.append(item) + if item in ['Progressive Cane', 'Progressive Net']: + if world.swords[player] != 'cane': + possible_weapons.append(item) if (item in ['Progressive Bow', 'Bow'] and not found_bow and not world.bow_mode[player].startswith('retro')): found_bow = True @@ -1167,7 +1157,7 @@ def get_pool_core(world, player, progressive, shuffle, difficulty, treasure_hunt if 'silvers' not in world.bow_mode[player]: pool.extend(['Progressive Bow'] * 2) - elif swords not in ['swordless', 'pseudo', 'assured_pseudo', 'swordless_hammer']: + elif swords not in ['swordless', 'pseudo', 'assured_pseudo', 'swordless_b']: pool.extend(diff.basicbow) else: pool.extend(['Bow', 'Silver Arrows']) @@ -1184,6 +1174,9 @@ def get_pool_core(world, player, progressive, shuffle, difficulty, treasure_hunt pool.extend(diff.cane_only) elif swords == 'cane': pool.extend(diff.cane_only) + elif swords == 'bugnet': + pool = [item.replace('Bug Catching Net', 'Progressive Net') for item in pool] + pool.extend(diff.bugnet_mode) elif swords == 'vanilla': swords_to_use = diff.progressivesword.copy() if want_progressives() else diff.basicsword.copy() random.shuffle(swords_to_use) diff --git a/Items.py b/Items.py index f11b7c6b..d4dd519a 100644 --- a/Items.py +++ b/Items.py @@ -173,6 +173,7 @@ item_table = {'Bow': (True, False, None, 0x0B, 200, 'You have\nchosen the\narche 'Bee Trap': (False, False, None, 0xB0, 50, 'We will sting your face a whole lot!', 'and the sting buddies', 'the beekeeper kid', 'insects for sale', 'shroom pollenation', 'bottle boy has mad bees again', 'friendship'), 'Progressive Bombs': (True, False, 'SwordBomb', 0xC0, 200, 'throw more\npowerful\nexplosives', 'the unknown grenades', 'the bomb-holding kid', 'better booms for sale', 'blend fungus into bombs', '\'splosion boy explodes again', 'fancy bombs'), 'Progressive Cane': (True, False, 'SwordCane', 0xC1, 200, 'a better\nstick\nrests here!', 'the unknown stick', 'the stick-holding kid', 'better stick for sale', 'fungus into stick', 'cane boy improves again', 'fancy cane'), + 'Progressive Net': (True, False, 'SwordNet', 0xC2, 200, 'a better\nnet\nrests here!', 'the unknown net', 'the net-holding kid', 'better net for sale', 'fungus into net', 'net boy improves again', 'fancy net'), 'Red Potion': (False, False, None, 0x2E, 150, 'Hearty red goop!', 'and the red goo', 'the liquid kid', 'potion for sale', 'free samples', 'bottle boy has red goo again', 'a red potion'), 'Green Potion': (False, False, None, 0x2F, 60, 'Refreshing green goop!', 'and the green goo', 'the liquid kid', 'potion for sale', 'free samples', 'bottle boy has green goo again', 'a green potion'), 'Blue Potion': (False, False, None, 0x30, 160, 'Delicious blue goop!', 'and the blue goo', 'the liquid kid', 'potion for sale', 'free samples', 'bottle boy has blue goo again', 'a blue potion'), diff --git a/Rom.py b/Rom.py index a0729156..e29b23b0 100644 --- a/Rom.py +++ b/Rom.py @@ -1240,7 +1240,7 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): #Set overflow items for progressive equipment rom.write_bytes(0x180090, - [difficulty.progressive_sword_limit if world.swords[player] not in ['swordless', 'swordless_hammer', 'bees'] else 0, overflow_replacement, + [difficulty.progressive_sword_limit if world.swords[player] not in ['swordless', 'swordless_b', 'bees'] else 0, overflow_replacement, difficulty.progressive_shield_limit, overflow_replacement, difficulty.progressive_armor_limit, overflow_replacement, difficulty.progressive_bottle_limit, overflow_replacement]) @@ -1248,7 +1248,7 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): #Work around for json patch ordering issues - write bow limit separately so that it is replaced in the patch rom.write_bytes(0x180098, [difficulty.progressive_bow_limit, overflow_replacement]) - if difficulty.progressive_bow_limit < 2 and world.swords[player] in ['swordless', 'swordless_hammer', 'bees', 'pseudo', 'assured_pseudo']: + if difficulty.progressive_bow_limit < 2 and world.swords[player] in ['swordless', 'swordless_b', 'bees', 'pseudo', 'assured_pseudo']: rom.write_bytes(0x180098, [2, overflow_replacement]) # set up game internal RNG seed @@ -1318,14 +1318,14 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): rom.write_byte(0x180029, 0x01) # Smithy quick item give # set swordless mode settings - if world.swords[player] in ['swordless', 'swordless_hammer']: + if world.swords[player] in ['swordless', 'swordless_b']: rom.write_byte(0x18003F, 0x01) # hammer can harm ganon rom.initial_sram.set_swordless_curtains() # open curtains rom.write_byte(0x180041, 0x01) # swordless medallions (on pads) rom.write_byte(0x180043, 0xFF) # starting sword for link rom.write_byte(0x180044, 0x01) # hammer activates tablets - if world.swords[player] == 'swordless_hammer': - rom.write_byte(0x18002F, 0x07) # hammer on B + if world.swords[player] == 'swordless_b': + rom.write_byte(0x18002C, 0xFF) # items on B elif world.swords[player] in ['pseudo', 'assured_pseudo']: rom.write_byte(0x18002F, 0x02) # pseudo-swords rom.write_byte(0x18003F, 0x01) # hammer can harm ganon @@ -1396,6 +1396,7 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): elif world.swords[player] in ['byrna', 'somaria', 'cane']: rom.initial_sram.set_swordless_curtains() # open curtains rom.write_byte(0x180041, 0x02) # swordless medallions (always) + rom.write_byte(0x18002C, 0xFF) # any item on B # remove magic cost of cane(s) if world.swords[player] in ['byrna', 'cane']: @@ -1412,13 +1413,13 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): rom.write_byte(0x03B0AE, 0x81) if world.swords[player] == 'byrna': - rom.write_byte(0x18002F, 0x83) + rom.write_byte(0x18002F, 0x03) colr = 0x2C elif world.swords[player] == 'somaria': - rom.write_byte(0x18002F, 0x84) + rom.write_byte(0x18002F, 0x04) colr = 0x24 elif world.swords[player] == 'cane': - rom.write_byte(0x18002F, 0x85) + rom.write_byte(0x18002F, 0x05) colr = 0x28 spritedata = [ @@ -1450,6 +1451,41 @@ def patch_rom(world, rom, player, team, enemized, is_mystery=False): rom.write_bytes(0x118188, credits_string_bot("TEMPERED CANE ")) rom.write_bytes(0x1181A6, credits_string_top("GOLD CANE ")) rom.write_bytes(0x1181C4, credits_string_bot("GOLD CANE ")) + elif world.swords[player] in ['bugnet']: + rom.initial_sram.set_swordless_curtains() # open curtains + rom.write_byte(0x180041, 0x02) # swordless medallions (always) + rom.write_byte(0x18002C, 0x0E) # bug net on B + rom.write_byte(0x18002F, 0x08) # bug net mode + + spritedata = [ + 0xF5, 0x20, 0xF5, 0x20, 0xF5, 0x20, 0xF5, 0x20, + 0x40, 0x3C, 0x41, 0x3C, 0x42, 0x3C, 0x17, 0x3C, + 0x40, 0x2C, 0x41, 0x2C, 0x42, 0x2C, 0x18, 0x2C, + 0x40, 0x24, 0x41, 0x24, 0x42, 0x24, 0x19, 0x24, + 0x40, 0x28, 0x41, 0x28, 0x42, 0x28, 0x1A, 0x28, + 0x40, 0x28, 0x41, 0x28, 0x42, 0x28, 0x1B, 0x28, + 0xF5, 0x20, 0xF5, 0x20, 0xF5, 0x20, 0xF5, 0x20, + 0x40, 0x3C, 0x41, 0x3C, 0x42, 0x3C, 0x43, 0x3C, + 0x40, 0x2C, 0x41, 0x2C, 0x42, 0x2C, 0x43, 0x2C, + 0x40, 0x24, 0x41, 0x24, 0x42, 0x24, 0x43, 0x24, + 0x40, 0x28, 0x41, 0x28, 0x42, 0x28, 0x43, 0x28, + 0x40, 0x28, 0x41, 0x28, 0x42, 0x28, 0x43, 0x28, + ]; + rom.write_bytes(0x06FC51, spritedata) + + # update sword references in credits to cane + rom.write_bytes(0x11807A, credits_string_top("FIRST NET ")) + rom.write_bytes(0x118098, credits_string_bot("FIRST NET ")) + rom.write_bytes(0x1180B6, credits_string_top("NETLESS ")) + rom.write_bytes(0x1180D4, credits_string_bot("NETLESS ")) + rom.write_bytes(0x1180F2, credits_string_top("FIGHTER'S NET ")) + rom.write_bytes(0x118110, credits_string_bot("FIGHTER'S NET ")) + rom.write_bytes(0x11812E, credits_string_top("MASTER NET ")) + rom.write_bytes(0x11814C, credits_string_bot("MASTER NET ")) + rom.write_bytes(0x11816A, credits_string_top("TEMPERED NET ")) + rom.write_bytes(0x118188, credits_string_bot("TEMPERED NET ")) + rom.write_bytes(0x1181A6, credits_string_top("GOLD NET ")) + rom.write_bytes(0x1181C4, credits_string_bot("GOLD NET ")) # set up clocks for timed modes if world.shuffle[player] == 'vanilla': diff --git a/Rules.py b/Rules.py index 484266a6..e593d14f 100644 --- a/Rules.py +++ b/Rules.py @@ -23,12 +23,12 @@ def set_rules(world, player): global_rules(world, player) ow_inverted_rules(world, player) - if world.swords[player] in ['swordless', 'swordless_hammer', 'bees']: + if world.swords[player] in ['swordless', 'swordless_b', 'bees']: swordless_rules(world, player) if world.swords[player] == 'bombs': bomb_mode_rules(world, player) - if world.swords[player] in ['byrna', 'somaria', 'cane']: - cane_mode_rules(world, player) + if world.swords[player] in ['byrna', 'somaria', 'cane', 'bugnet']: + cane_or_net_mode_rules(world, player) if world.swords[player] in ['pseudo', 'assured_pseudo']: pseudo_sword_mode_rules(world, player) @@ -870,6 +870,7 @@ def global_rules(world, player): and state.has_fire_source(player) and (state.has_crystals(world.crystals_needed_for_ganon[player], player) or world.goal[player] == 'z1') and (state.has_real_sword(player, 3) or + state.has_special_weapon_level(player, 3) or state.can_hit_stunned_ganon(player) or state.has_real_sword(player, 2) and (state.has('Lamp', player) or state.can_extend_magic(player, 12)))) @@ -1510,7 +1511,7 @@ def bomb_mode_rules(world, player): add_bunny_rule(world.get_entrance('Turtle Rock', player), player) add_bunny_rule(world.get_entrance('Misery Mire', player), player) -def cane_mode_rules(world, player): +def cane_or_net_mode_rules(world, player): set_rule(world.get_entrance('Tower Altar NW', player), lambda state: True) set_rule(world.get_entrance('Skull Vines NW', player), lambda state: True) diff --git a/resources/app/cli/args.json b/resources/app/cli/args.json index 7c338824..bc740e98 100644 --- a/resources/app/cli/args.json +++ b/resources/app/cli/args.json @@ -51,7 +51,8 @@ "cane", "vanilla", "bees", - "swordless_hammer" + "swordless_b", + "bugnet" ] }, "flute_mode": {