From 915e7dc416eb5d852f75b700b01e3e4fd3f237f1 Mon Sep 17 00:00:00 2001 From: aerinon Date: Tue, 26 Sep 2023 08:59:31 -0600 Subject: [PATCH] Ability to enemize fairies Fix for blue square in caves Lower limit for sprites on tiles that support it, to help with pot lifting Swamp waterway enemies fixed to not drop --- DoorShuffle.py | 1 + Doors.py | 2 + Dungeons.py | 9 +- EntranceShuffle.py | 8 ++ Regions.py | 17 ++-- Rom.py | 2 +- Rules.py | 4 +- data/base2current.bps | Bin 117403 -> 117439 bytes source/dungeon/EnemyList.py | 142 ++++++++++++++++----------- source/enemizer/Enemizer.py | 4 +- source/enemizer/EnemyLogic.py | 13 ++- source/enemizer/SpriteSheets.py | 3 +- source/enemizer/enemy_deny.yaml | 102 +++++++++++++------ source/enemizer/enemy_weight.yaml | 4 + source/enemizer/sheet_weight.yaml | 2 +- source/overworld/EntranceShuffle2.py | 8 ++ 16 files changed, 217 insertions(+), 104 deletions(-) diff --git a/DoorShuffle.py b/DoorShuffle.py index e64a3c19..022c5e5c 100644 --- a/DoorShuffle.py +++ b/DoorShuffle.py @@ -4351,6 +4351,7 @@ default_door_connections = [ ('PoD Arena Crystals E', 'PoD Sexy Statue W'), ('PoD Mimics 1 NW', 'PoD Conveyor SW'), ('PoD Map Balcony WS', 'PoD Arena Ledge ES'), + ('PoD Map Balcony ES', 'PoD Fairy Pool WS'), ('PoD Falling Bridge WN', 'PoD Dark Maze EN'), ('PoD Dark Maze E', 'PoD Big Chest Balcony W'), ('PoD Sexy Statue NW', 'PoD Mimics 2 SW'), diff --git a/Doors.py b/Doors.py index 309abbab..651f9bd4 100644 --- a/Doors.py +++ b/Doors.py @@ -410,6 +410,8 @@ def create_doors(world, player): create_door(player, 'PoD Map Balcony Drop Down', Lgcl), create_door(player, 'PoD Map Balcony to Ranged Crystal', Lgcl), create_door(player, 'PoD Map Balcony Ranged Crystal Exit', Lgcl), + create_door(player, 'PoD Map Balcony ES', Intr).dir(Ea, 0x2b, Bot, High).pos(0), + create_door(player, 'PoD Fairy Pool WS', Intr).dir(We, 0x2b, Bot, High).pos(0), create_door(player, 'PoD Map Balcony WS', Nrml).dir(We, 0x2b, Bot, High).pos(1), create_door(player, 'PoD Map Balcony South Stairs', StrS).dir(So, 0x2b, Left, High), create_door(player, 'PoD Conveyor North Stairs', StrS).dir(No, 0x3b, Left, High), diff --git a/Dungeons.py b/Dungeons.py index 6cf12837..3284617e 100644 --- a/Dungeons.py +++ b/Dungeons.py @@ -98,10 +98,11 @@ pod_regions = [ 'PoD Lobby', 'PoD Left Cage', 'PoD Middle Cage', 'PoD Shooter Room', 'PoD Pit Room', 'PoD Pit Room Blocked', 'PoD Arena Main', 'PoD Arena Main - Ranged Crystal', 'PoD Arena North', 'PoD Arena Bridge', 'PoD Arena Bridge - Ranged Crystal', 'PoD Arena Landing', 'PoD Arena Right', 'PoD Arena Right - Ranged Crystal', 'PoD Arena Ledge', 'PoD Arena Ledge - Ranged Crystal', 'PoD Sexy Statue', - 'PoD Map Balcony', 'PoD Map Balcony - Ranged Crystal', 'PoD Conveyor', 'PoD Mimics 1', 'PoD Jelly Hall', 'PoD Warp Hint', 'PoD Warp Room', - 'PoD Stalfos Basement', 'PoD Basement Ledge', 'PoD Big Key Landing', 'PoD Falling Bridge', 'PoD Falling Bridge Mid', - 'PoD Falling Bridge Ledge', 'PoD Dark Maze', 'PoD Big Chest Balcony', 'PoD Compass Room', 'PoD Dark Basement', - 'PoD Harmless Hellway', 'PoD Mimics 2', 'PoD Bow Statue Left', 'PoD Bow Statue Left - Crystal', 'PoD Bow Statue Right', 'PoD Bow Statue Right - Ranged Crystal', + 'PoD Map Balcony', 'PoD Map Balcony - Ranged Crystal', 'PoD Fairy Pool', 'PoD Conveyor', 'PoD Mimics 1', + 'PoD Jelly Hall', 'PoD Warp Hint', 'PoD Warp Room', 'PoD Stalfos Basement', 'PoD Basement Ledge', + 'PoD Big Key Landing', 'PoD Falling Bridge', 'PoD Falling Bridge Mid', 'PoD Falling Bridge Ledge', 'PoD Dark Maze', + 'PoD Big Chest Balcony', 'PoD Compass Room', 'PoD Dark Basement', 'PoD Harmless Hellway', 'PoD Mimics 2', + 'PoD Bow Statue Left', 'PoD Bow Statue Left - Crystal', 'PoD Bow Statue Right', 'PoD Bow Statue Right - Ranged Crystal', 'PoD Dark Pegs Landing', 'PoD Dark Pegs Right', 'PoD Dark Pegs Middle', 'PoD Dark Pegs Left', 'PoD Dark Pegs Landing - Ranged Crystal', 'PoD Dark Pegs Middle - Ranged Crystal', 'PoD Dark Pegs Left - Ranged Crystal', 'PoD Lonely Turtle', 'PoD Turtle Party', 'PoD Dark Alley', 'PoD Callback', 'PoD Boss', 'Palace of Darkness Portal' diff --git a/EntranceShuffle.py b/EntranceShuffle.py index cbc5cffb..a9907ce5 100644 --- a/EntranceShuffle.py +++ b/EntranceShuffle.py @@ -2093,11 +2093,19 @@ mandatory_connections = [('Links House S&Q', 'Links House'), ('Kakariko Well (top to back)', 'Kakariko Well (back)'), ('Blinds Hideout N', 'Blinds Hideout (Top)'), ('Bat Cave Door', 'Bat Cave (left)'), + ('Good Bee Cave Front to Back', 'Good Bee Cave (back)'), + ('Good Bee Cave Back to Front', 'Good Bee Cave'), + ('Capacity Upgrade East', 'Capacity Fairy Pool'), + ('Capacity Fairy Pool West', 'Capacity Upgrade'), + ('Bonk Fairy (Dark) Pool', 'Bonk Fairy Pool'), + ('Bonk Fairy (Light) Pool', 'Bonk Fairy Pool'), ('Hookshot Cave Front to Middle', 'Hookshot Cave (Middle)'), ('Hookshot Cave Middle to Front', 'Hookshot Cave (Front)'), ('Hookshot Cave Middle to Back', 'Hookshot Cave (Back)'), ('Hookshot Cave Back to Middle', 'Hookshot Cave (Middle)'), + ('Hookshot Cave Back to Fairy', 'Hookshot Cave (Fairy Pool)'), + ('Hookshot Cave Fairy to Back', 'Hookshot Cave (Back)'), ('Hookshot Cave Bonk Path', 'Hookshot Cave (Bonk Islands)'), ('Hookshot Cave Hook Path', 'Hookshot Cave (Hook Islands)'), ('Superbunny Cave Climb', 'Superbunny Cave (Top)'), diff --git a/Regions.py b/Regions.py index 509f11b7..9f986006 100644 --- a/Regions.py +++ b/Regions.py @@ -177,7 +177,8 @@ def create_regions(world, player): create_cave_region(player, 'Two Brothers House', 'a connector', None, ['Two Brothers House Exit (East)', 'Two Brothers House Exit (West)']), create_cave_region(player, 'Library', 'the library', ['Library']), create_cave_region(player, 'Kakariko Gamble Game', 'a game of chance'), - create_cave_region(player, 'Bonk Fairy (Light)', 'a fairy fountain'), + create_cave_region(player, 'Bonk Fairy (Light)', 'a fairy fountain', None, ['Bonk Fairy (Light) Pool']), + create_cave_region(player, 'Bonk Fairy Pool', 'a fairy fountain'), create_cave_region(player, 'Links House', 'your house', ['Link\'s House'], ['Links House Exit']), create_cave_region(player, 'Chris Houlihan Room', 'I AM ERROR', None, ['Chris Houlihan Room Exit']), create_cave_region(player, 'Lake Hylia Healer Fairy', 'a fairy fountain'), @@ -188,11 +189,13 @@ def create_regions(world, player): create_cave_region(player, 'Light Hype Fairy', 'a fairy fountain'), create_cave_region(player, 'Lake Hylia Fortune Teller', 'a fortune teller'), create_cave_region(player, 'Lake Hylia Shop', 'a common shop', ['Lake Hylia Shop - Left', 'Lake Hylia Shop - Middle', 'Lake Hylia Shop - Right']), - create_cave_region(player, 'Capacity Upgrade', 'the queen of fairies', ['Capacity Upgrade - Left', 'Capacity Upgrade - Right']), + create_cave_region(player, 'Capacity Upgrade', 'the queen of fairies', ['Capacity Upgrade - Left', 'Capacity Upgrade - Right'], ['Capacity Upgrade East']), + create_cave_region(player, 'Capacity Fairy Pool', 'near the queen of fairies', None, ['Capacity Fairy Pool West']), create_cave_region(player, 'Mini Moldorm Cave', 'a bounty of five items', ['Mini Moldorm Cave - Far Left', 'Mini Moldorm Cave - Left', 'Mini Moldorm Cave - Right', 'Mini Moldorm Cave - Far Right', 'Mini Moldorm Cave - Generous Guy']), create_cave_region(player, 'Ice Rod Cave', 'a cave with a chest', ['Ice Rod Cave']), - create_cave_region(player, 'Good Bee Cave', 'a cold bee'), + create_cave_region(player, 'Good Bee Cave', 'a cold bee', None, ['Good Bee Cave Front to Back']), + create_cave_region(player, 'Good Bee Cave (back)', 'a cold bee', None, ['Good Bee Cave Back to Front']), create_cave_region(player, '20 Rupee Cave', 'a cave with some cash'), create_cave_region(player, 'Desert Healer Fairy', 'a fairy fountain'), create_cave_region(player, '50 Rupee Cave', 'a cave with some cash'), @@ -206,7 +209,8 @@ def create_regions(world, player): create_cave_region(player, 'Hookshot Cave (Bonk Islands)', 'a connector', ['Hookshot Cave - Bottom Right']), create_cave_region(player, 'Hookshot Cave (Hook Islands)', 'a connector', ['Hookshot Cave - Top Right', 'Hookshot Cave - Top Left', 'Hookshot Cave - Bottom Left']), create_cave_region(player, 'Hookshot Cave (Middle)', 'a connector', None, ['Hookshot Cave Middle to Back', 'Hookshot Cave Middle to Front']), - create_cave_region(player, 'Hookshot Cave (Back)', 'a connector', None, ['Hookshot Cave Back to Middle', 'Hookshot Cave Back Exit']), + create_cave_region(player, 'Hookshot Cave (Back)', 'a connector', None, ['Hookshot Cave Back to Middle', 'Hookshot Cave Back to Fairy', 'Hookshot Cave Back Exit']), + create_cave_region(player, 'Hookshot Cave (Fairy Pool)', 'a connector', None, ['Hookshot Cave Fairy to Back']), create_cave_region(player, 'Superbunny Cave (Top)', 'a connector', ['Superbunny Cave - Top', 'Superbunny Cave - Bottom'], ['Superbunny Cave Exit (Top)']), create_cave_region(player, 'Superbunny Cave (Bottom)', 'a connector', None, ['Superbunny Cave Climb', 'Superbunny Cave Exit (Bottom)']), create_cave_region(player, 'Dark Death Mountain Shop', 'a common shop', ['Dark Death Mountain Shop - Left', 'Dark Death Mountain Shop - Middle', 'Dark Death Mountain Shop - Right']), @@ -226,7 +230,7 @@ def create_regions(world, player): create_cave_region(player, 'Palace of Darkness Hint', 'a storyteller'), create_cave_region(player, 'Hammer Peg Cave', 'a cave with an item', ['Peg Cave']), create_cave_region(player, 'Archery Game', 'a game of skill'), - create_cave_region(player, 'Bonk Fairy (Dark)', 'a fairy fountain'), + create_cave_region(player, 'Bonk Fairy (Dark)', 'a fairy fountain', None, ['Bonk Fairy (Dark) Pool']), create_cave_region(player, 'Big Bomb Shop', 'the bomb shop'), create_cave_region(player, 'Dark Lake Hylia Healer Fairy', 'a fairy fountain'), create_cave_region(player, 'East Dark World Hint', 'a storyteller'), @@ -447,8 +451,9 @@ def create_dungeon_regions(world, player): create_dungeon_region(player, 'PoD Arena Ledge', 'Palace of Darkness', ['Palace of Darkness - The Arena - Ledge'], ['PoD Arena Ledge ES', 'PoD Arena Ledge to Ranged Crystal']), create_dungeon_region(player, 'PoD Arena Ledge - Ranged Crystal', 'Palace of Darkness', None, ['PoD Arena Ledge Ranged Crystal Exit']), create_dungeon_region(player, 'PoD Sexy Statue', 'Palace of Darkness', None, ['PoD Sexy Statue W', 'PoD Sexy Statue NW']), - create_dungeon_region(player, 'PoD Map Balcony', 'Palace of Darkness', ['Palace of Darkness - Map Chest'], ['PoD Map Balcony to Ranged Crystal', 'PoD Map Balcony WS', 'PoD Map Balcony South Stairs', 'PoD Map Balcony Drop Down']), + create_dungeon_region(player, 'PoD Map Balcony', 'Palace of Darkness', ['Palace of Darkness - Map Chest'], ['PoD Map Balcony to Ranged Crystal', 'PoD Map Balcony WS', 'PoD Map Balcony South Stairs', 'PoD Map Balcony Drop Down', 'PoD Map Balcony ES']), create_dungeon_region(player, 'PoD Map Balcony - Ranged Crystal', 'Palace of Darkness', None, ['PoD Map Balcony Ranged Crystal Exit']), + create_dungeon_region(player, 'PoD Fairy Pool', 'Palace of Darkness', None, ['PoD Fairy Pool WS']), create_dungeon_region(player, 'PoD Conveyor', 'Palace of Darkness', None, ['PoD Conveyor North Stairs', 'PoD Conveyor SW']), create_dungeon_region(player, 'PoD Mimics 1', 'Palace of Darkness', None, ['PoD Mimics 1 NW', 'PoD Mimics 1 SW']), create_dungeon_region(player, 'PoD Jelly Hall', 'Palace of Darkness', None, ['PoD Jelly Hall NW', 'PoD Jelly Hall NE']), diff --git a/Rom.py b/Rom.py index 010e86d6..3933ac76 100644 --- a/Rom.py +++ b/Rom.py @@ -40,7 +40,7 @@ from source.enemizer.Enemizer import write_enemy_shuffle_settings JAP10HASH = '03a63945398191337e896e5771f77173' -RANDOMIZERBASEHASH = 'bc80079ef83a98f718be2a06c40546ce' +RANDOMIZERBASEHASH = '6fbf895bae14a0c74ec8dc782d3b9a95' class JsonRom(object): diff --git a/Rules.py b/Rules.py index 052698cd..d21f564b 100644 --- a/Rules.py +++ b/Rules.py @@ -716,7 +716,9 @@ def bomb_rules(world, player): bonkable_doors = ['Two Brothers House Exit (West)', 'Two Brothers House Exit (East)'] # Technically this is incorrectly defined, but functionally the same as what is intended. bombable_doors = ['Ice Rod Cave', 'Light World Bomb Hut', 'Paradox Shop', 'Mini Moldorm Cave', 'Hookshot Cave Back to Middle', 'Hookshot Cave Front to Middle', 'Hookshot Cave Middle to Front', - 'Hookshot Cave Middle to Back', 'Dark Lake Hylia Ledge Fairy', 'Hype Cave', 'Brewery', + 'Hookshot Cave Middle to Back', 'Hookshot Cave Back to Fairy', 'Hookshot Cave Fairy to Back', + 'Good Bee Cave Front to Back', 'Good Bee Cave Back to Front', 'Capacity Upgrade East', + 'Capacity Fairy Pool West', 'Dark Lake Hylia Ledge Fairy', 'Hype Cave', 'Brewery', 'Paradox Cave Chest Area NE', 'Blinds Hideout N', 'Kakariko Well (top to back)', 'Light Hype Fairy'] for entrance in bonkable_doors: diff --git a/data/base2current.bps b/data/base2current.bps index aa06d0481365467b1975891c1bf8e84364e12aa3..80984e899379618bfc446f1d737abbe1b45a38c3 100644 GIT binary patch delta 1002 zcmWlYYfMvj9ESUAX?xmo>7cb#!NF0SpmiVvZ4;;C4mx4L?jQt_mX$0HCSz0F{}iFC zTvm2cj!=*@7G^ubfSkc8Rwy*tNCVpn(k0767ERFDn5AZBGFaAi@2BU>o9F%VS}j7C zML2l};5%{-4nscUhg}fnJD2h$8OAd}6=USdcpzs61!jOpqzY4uW$Uz8;LjmUNz6s8 zm!l+e(X|4uH+FFs`=>! zu~#@A9_EP-aAT{h2ek37RW-SBI~mlZ(3ujZI7z(6WH_Y&$C$i3u>d7Z)tp`i73A`& z5{jA4)ddizya z#EHg^e(zJA{RBE_-OFA+3L$}v?MjEGI7np6OCTr;m&^MtqEWF&%AquD)jROLP@DqK zW^{4i?n9TUBQ@|jyv5Gfz!Ja{s-qSVS29gu7vQ59PmtpkTJzr=?rrC~4o+InRSZ+c z3($4uAwmQUQAyrie1yD-a>Ocj})Gu|gPrfqqRE8=vYaM!g*TVD@t z3cf07j!b8tASj3uG#B^Lj|^bb93Lp>Wh Qr3u4IM4aOp>V*gY0Xu1+tN;K2 delta 982 zcmWlTeM}Q~9Eb1Q*Q30&R60ap&_g@XvGF$4>f#G9Dlin7W-KxZZ!I3%L}eq}WWOr{ z0|ctKCsb zkx$+PxJ=K(%aF?l;02Hre=u#KC1NvF^4;P%G06EbnFU~l&cJslWPZ*k3lva2YW_HW zKmT+1v zizdAg1k#f^aU{X+!-te2^O6qHb#sL|vCV7GRn2RZA`+QLPnqwvnuqfCtR|wCl;H|g zdGa?(`WJcdt{%x$C?6ef{lk4SnqHaP06O~VTzdFZU0Wn|yQu=c%%uXT=8xW75AY%1 zHc!SS=IPy2d;I5H>KUsBBQPyifR$mMQ}qm;&i{L70Thy=`?sWO=Q`BP-@a$bkBq~g zQRGDV8)KtNp)MZGk%`Ls{ySpKo{L$;cC~2m*3R}CB~pr}wz39i8gwh8t4?$c`<|HW zucOVQdf|&~2v^7iYYr?WL5%R;K?p@eWod?)2&=-Y!q~$?+dJ@`Tp@wKou;I()6gNd zs1^pHRQRD5mH<}S@p?d_&<$4G03YFj3Yr;%t zu^o+I06qJCBV@oacC8W8Gz-orap;KtZWl?oXKY@vPhq&KWwVWt2d!+A5wgL^ju{~% zGAU}{_n@-)s|)vytltRlCoKw&n$({KqWbB@Odze%Ufj3!+6l2w%aSSVyC(Qly7QCX zo@w@h2@+n~RX5IWYh);mU>^3Q+E34-b;6l%!jv)FSK{cz=aGEmaK#jx(iBd6n|-qh zh!-0wH0azvp-^a_OH`>reSmljQL8R9^{3-OiO}B!9r4o2P4jfLprOE^l$CCO$jSBRv-a!h!|13ftYSYcvwllCwC2P71dAOHXW diff --git a/source/dungeon/EnemyList.py b/source/dungeon/EnemyList.py index b07c867e..2a8a2377 100644 --- a/source/dungeon/EnemyList.py +++ b/source/dungeon/EnemyList.py @@ -1,4 +1,4 @@ -from collections import defaultdict +from collections import defaultdict, deque import typing import yaml @@ -10,7 +10,8 @@ except ImportError: from enum import IntFlag as FastEnum import RaceRandom as random -from BaseClasses import Location, LocationType +from BaseClasses import Location, LocationType, RegionType +from EntranceShuffle import door_addresses from Items import ItemFactory from Utils import snes_to_pc, pc_to_snes, int16_as_bytes @@ -491,7 +492,7 @@ def init_enemy_stats(): EnemySprite.RedRupee: EnemyStats(EnemySprite.RedRupee, True, ignore=True, dmg=0), EnemySprite.BombRefill1: EnemyStats(EnemySprite.BombRefill1, True, ignore=True, dmg=0), EnemySprite.BombRefill4: EnemyStats(EnemySprite.BombRefill4, True, ignore=True, dmg=0), - EnemySprite.Faerie: EnemyStats(EnemySprite.Faerie, True, ignore=True, dmg=0, dmask=0x10), + EnemySprite.Faerie: EnemyStats(EnemySprite.Faerie, False, False, ignore=True, dmg=0, dmask=0x10), EnemySprite.SmallKey: EnemyStats(EnemySprite.SmallKey, True, ignore=True, dmg=0), EnemySprite.FakeMasterSword: EnemyStats(EnemySprite.FakeMasterSword, False, False, ignore=True, dmg=0), EnemySprite.MagicShopAssistant: EnemyStats(EnemySprite.MagicShopAssistant, True, ignore=True, dmg=0), @@ -545,6 +546,7 @@ class Sprite(object): sprite.static = self.static sprite.water = self.water sprite.embedded = self.embedded + sprite.never_drop = self.never_drop return sprite def sprite_data(self): @@ -748,10 +750,10 @@ def init_vanilla_sprites(): create_sprite(0x001c, EnemySprite.ArmosKnight, 0x00, 0, 0x07, 0x08) create_sprite(0x001c, EnemySprite.ArmosKnight, 0x00, 0, 0x04, 0x08) create_sprite(0x001c, 0x19, SpriteType.Overlord, 0, 0x07, 0x08) - create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x07, 0x07) - create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07) - create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x07, 0x08) - create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x08) + create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x07, 0x07, 'GT Fairy Abyss') + create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07, 'GT Fairy Abyss') + create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x07, 0x08, 'GT Fairy Abyss') + create_sprite(0x001c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x08, 'GT Fairy Abyss') create_sprite(0x001e, EnemySprite.CrystalSwitch, 0x00, 0, 0x1a, 0x09) create_sprite(0x001e, EnemySprite.RedBari, 0x00, 0, 0x16, 0x05, 'Ice Bomb Drop - Top') create_sprite(0x001e, EnemySprite.RedBari, 0x00, 0, 0x19, 0x05, 'Ice Bomb Drop - Top') @@ -835,15 +837,15 @@ def init_vanilla_sprites(): create_sprite(0x002b, EnemySprite.CrystalSwitch, 0x00, 0, 0x0a, 0x11) create_sprite(0x002b, EnemySprite.Statue, 0x00, 0, 0x0a, 0x0a, fix=True) create_sprite(0x002b, EnemySprite.RedBari, 0x00, 0, 0x07, 0x17, 'PoD Map Balcony') - create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x16, 0x17) - create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x18, 0x18) + create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x16, 0x17, 'PoD Fairy Pool') + create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x18, 0x18, 'PoD Fairy Pool') create_sprite(0x002b, EnemySprite.RedBari, 0x00, 0, 0x05, 0x1a, 'PoD Map Balcony') create_sprite(0x002b, EnemySprite.RedBari, 0x00, 0, 0x0a, 0x1a, 'PoD Map Balcony') - create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x17, 0x1a) + create_sprite(0x002b, EnemySprite.Faerie, 0x00, 0, 0x17, 0x1a, 'PoD Fairy Pool') create_sprite(0x002c, EnemySprite.BigFairy, 0x00, 0, 0x17, 0x05) - create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x09, 0x04) - create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x06, 0x05) - create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07) + create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x09, 0x04, 'Hookshot Cave (Fairy Pool)') + create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x06, 0x05, 'Hookshot Cave (Fairy Pool)') + create_sprite(0x002c, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07, 'Hookshot Cave (Fairy Pool)') create_sprite(0x002e, EnemySprite.Pengator, 0x00, 0, 0x14, 0x06, 'Ice Compass Room') create_sprite(0x002e, EnemySprite.Pengator, 0x00, 0, 0x1c, 0x06, 'Ice Compass Room') create_sprite(0x002e, EnemySprite.Pengator, 0x00, 0, 0x16, 0x08, 'Ice Compass Room') @@ -1051,9 +1053,9 @@ def init_vanilla_sprites(): create_sprite(0x004e, EnemySprite.Blob, 0x00, 0, 0x16, 0x08, 'Ice Narrow Corridor') create_sprite(0x004e, EnemySprite.Blob, 0x00, 0, 0x18, 0x08, 'Ice Narrow Corridor') create_sprite(0x004e, EnemySprite.FirebarCW, 0x00, 0, 0x07, 0x09, 'Ice Bomb Jump Catwalk') - create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x17, 0x06) - create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x14, 0x08) - create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x1a, 0x08) + create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x17, 0x06, 'Ice Fairy') + create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x14, 0x08, 'Ice Fairy') + create_sprite(0x004f, EnemySprite.Faerie, 0x00, 0, 0x1a, 0x08, 'Ice Fairy') create_sprite(0x0050, EnemySprite.GreenGuard, 0x00, 1, 0x17, 0x0e, 'Hyrule Castle West Hall') create_sprite(0x0050, EnemySprite.GreenKnifeGuard, 0x00, 1, 0x18, 0x10, 'Hyrule Castle West Hall') create_sprite(0x0050, EnemySprite.GreenKnifeGuard, 0x00, 1, 0x17, 0x12, 'Hyrule Castle West Hall') @@ -1150,8 +1152,8 @@ def init_vanilla_sprites(): create_sprite(0x005c, EnemySprite.WallCannonHorzTop, 0x00, 0, 0x0b, 0x02, embed=True) create_sprite(0x005c, EnemySprite.WallCannonHorzBottom, 0x00, 0, 0x05, 0x0e, embed=True) create_sprite(0x005c, EnemySprite.WallCannonHorzBottom, 0x00, 0, 0x0e, 0x0e, embed=True) - create_sprite(0x005c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x18) - create_sprite(0x005c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x18) + create_sprite(0x005c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x18, 'GT Refill') + create_sprite(0x005c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x18, 'GT Refill') create_sprite(0x005d, EnemySprite.Stalfos, 0x00, 0, 0x07, 0x05, 'GT Gauntlet 2') create_sprite(0x005d, EnemySprite.Beamos, 0x00, 0, 0x08, 0x06, 'GT Gauntlet 2') create_sprite(0x005d, EnemySprite.Stalfos, 0x00, 0, 0x03, 0x08, 'GT Gauntlet 2') @@ -1366,8 +1368,8 @@ def init_vanilla_sprites(): create_sprite(0x0083, EnemySprite.DebirandoPit, 0x00, 0, 0x1b, 0x08, 'Desert West Wing') create_sprite(0x0083, EnemySprite.DebirandoPit, 0x00, 0, 0x14, 0x10, 'Desert West Wing') create_sprite(0x0083, EnemySprite.Leever, 0x00, 0, 0x14, 0x05, 'Desert West Wing') - create_sprite(0x0083, EnemySprite.Faerie, 0x00, 0, 0x07, 0x06) - create_sprite(0x0083, EnemySprite.Faerie, 0x00, 0, 0x08, 0x08) + create_sprite(0x0083, EnemySprite.Faerie, 0x00, 0, 0x07, 0x06, 'Desert Fairy Fountain') + create_sprite(0x0083, EnemySprite.Faerie, 0x00, 0, 0x08, 0x08, 'Desert Fairy Fountain') create_sprite(0x0083, EnemySprite.Leever, 0x00, 0, 0x1b, 0x0b, 'Desert West Wing') create_sprite(0x0083, EnemySprite.Leever, 0x00, 0, 0x17, 0x10, 'Desert West Wing') create_sprite(0x0083, EnemySprite.Beamos, 0x00, 0, 0x08, 0x17, 'Desert West Lobby') @@ -1403,8 +1405,8 @@ def init_vanilla_sprites(): create_sprite(0x0087, EnemySprite.Stalfos, 0x00, 0, 0x04, 0x19, 'Hera Basement Cage') create_sprite(0x0087, EnemySprite.SmallKey, 0x00, 0, 0x08, 0x1a, 'Hera Basement Cage') create_sprite(0x0087, EnemySprite.Stalfos, 0x00, 0, 0x15, 0x1c, 'Hera Torches') - create_sprite(0x0089, EnemySprite.Faerie, 0x00, 0, 0x10, 0x0a) - create_sprite(0x0089, EnemySprite.Faerie, 0x00, 0, 0x0f, 0x0b) + create_sprite(0x0089, EnemySprite.Faerie, 0x00, 0, 0x10, 0x0a, 'Eastern Fairies') + create_sprite(0x0089, EnemySprite.Faerie, 0x00, 0, 0x0f, 0x0b, 'Eastern Fairies') create_sprite(0x008b, EnemySprite.Bumper, 0x00, 0, 0x15, 0x07, 'GT Conveyor Cross') create_sprite(0x008b, EnemySprite.CrystalSwitch, 0x00, 0, 0x04, 0x18, 'GT Hookshot South Platform') create_sprite(0x008b, EnemySprite.CrystalSwitch, 0x00, 0, 0x0b, 0x18, 'GT Hookshot South Platform') @@ -1573,8 +1575,8 @@ def init_vanilla_sprites(): create_sprite(0x00a5, EnemySprite.BlueGuard, 0x00, 0, 0x13, 0x18, 'GT Dashing Bridge') create_sprite(0x00a6, 0x15, SpriteType.Overlord, 0, 0x0f, 0x0f) create_sprite(0x00a6, EnemySprite.AntiFairy, 0x00, 0, 0x0c, 0x0e, 'GT Moldorm Pit') - create_sprite(0x00a7, EnemySprite.Faerie, 0x00, 0, 0x06, 0x08) - create_sprite(0x00a7, EnemySprite.Faerie, 0x00, 0, 0x06, 0x09) + create_sprite(0x00a7, EnemySprite.Faerie, 0x00, 0, 0x06, 0x08, 'Hera Fairies') + create_sprite(0x00a7, EnemySprite.Faerie, 0x00, 0, 0x06, 0x09, 'Hera Fairies') create_sprite(0x00a8, EnemySprite.Stalfos, 0x00, 0, 0x16, 0x0e, 'Eastern West Wing') create_sprite(0x00a8, EnemySprite.Stalfos, 0x00, 0, 0x1a, 0x0e, 'Eastern West Wing') create_sprite(0x00a8, EnemySprite.Stalfos, 0x00, 0, 0x16, 0x12, 'Eastern West Wing') @@ -1655,7 +1657,7 @@ def init_vanilla_sprites(): create_sprite(0x00b6, EnemySprite.Chainchomp, 0x00, 0, 0x0a, 0x07, 'TR Chain Chomps Top') create_sprite(0x00b6, EnemySprite.CrystalSwitch, 0x00, 0, 0x03, 0x04) create_sprite(0x00b6, EnemySprite.CrystalSwitch, 0x00, 0, 0x0c, 0x04) - create_sprite(0x00b6, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07) + create_sprite(0x00b6, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07, 'TR Refill') create_sprite(0x00b6, EnemySprite.Pokey, 0x00, 0, 0x07, 0x15, 'TR Pokey 1', True, 0xe4) create_sprite(0x00b6, 0x14, SpriteType.Overlord, 0, 0x17, 0x18) create_sprite(0x00b6, EnemySprite.Blob, 0x00, 0, 0x07, 0x1b, 'TR Pokey 1') @@ -1896,10 +1898,10 @@ def init_vanilla_sprites(): create_sprite(0x00e0, EnemySprite.BluesainBolt, 0x00, 0, 0x1a, 0x09, 'Tower Room 03') create_sprite(0x00e1, EnemySprite.HeartPiece, 0x00, 0, 0x17, 0x0d) create_sprite(0x00e1, EnemySprite.AdultNpc, 0x00, 1, 0x07, 0x12) - create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x07, 0x06) - create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x08, 0x06) - create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x07, 0x07) - create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07) + create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x07, 0x06, 'Lumberjack Tree (top)') + create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x08, 0x06, 'Lumberjack Tree (top)') + create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x07, 0x07, 'Lumberjack Tree (top)') + create_sprite(0x00e2, EnemySprite.Faerie, 0x00, 0, 0x08, 0x07, 'Lumberjack Tree (top)') create_sprite(0x00e2, EnemySprite.HeartPiece, 0x00, 0, 0x13, 0x10) create_sprite(0x00e3, EnemySprite.MagicBat, 0x00, 1, 0x17, 0x05) create_sprite(0x00e4, EnemySprite.Keese, 0x00, 0, 0x19, 0x07, 'Old Man House', embed=True) # partial @@ -1966,16 +1968,16 @@ def init_vanilla_sprites(): create_sprite(0x00f9, EnemySprite.MiniMoldorm, 0x00, 0, 0x15, 0x0f, 'Spectacle Rock Cave (Bottom)') create_sprite(0x00f9, EnemySprite.MiniMoldorm, 0x00, 0, 0x11, 0x13, 'Spectacle Rock Cave (Bottom)') create_sprite(0x00f9, EnemySprite.MiniMoldorm, 0x00, 0, 0x0c, 0x17, 'Spectacle Rock Cave (Bottom)') - create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x17, 0x0e) - create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x18, 0x10) - create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x15, 0x11) + create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x17, 0x0e, 'Spectacle Rock Cave (Bottom)') + create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x18, 0x10, 'Spectacle Rock Cave (Bottom)') + create_sprite(0x00fa, EnemySprite.Faerie, 0x00, 0, 0x15, 0x11, 'Spectacle Rock Cave (Bottom)') create_sprite(0x00fb, EnemySprite.Bumper, 0x00, 0, 0x17, 0x0d, 'Bumper Cave (bottom)') create_sprite(0x00fb, EnemySprite.HardhatBeetle, 0x00, 0, 0x19, 0x0a, 'Bumper Cave (bottom)') create_sprite(0x00fb, EnemySprite.HardhatBeetle, 0x00, 0, 0x15, 0x12, 'Bumper Cave (bottom)') create_sprite(0x00fd, EnemySprite.MiniMoldorm, 0x00, 0, 0x09, 0x0e, 'Fairy Ascension Cave (Bottom)') create_sprite(0x00fd, EnemySprite.BlueBari, 0x00, 0, 0x05, 0x08, 'Fairy Ascension Cave (Bottom)') - create_sprite(0x00fd, EnemySprite.Faerie, 0x00, 0, 0x16, 0x08) - create_sprite(0x00fd, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08) + create_sprite(0x00fd, EnemySprite.Faerie, 0x00, 0, 0x16, 0x08, 'Fairy Ascension Cave (Top)') + create_sprite(0x00fd, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08, 'Fairy Ascension Cave (Top)') create_sprite(0x00fd, EnemySprite.BlueBari, 0x00, 0, 0x0f, 0x11, 'Fairy Ascension Cave (Bottom)') create_sprite(0x00fe, EnemySprite.MiniMoldorm, 0x00, 0, 0x16, 0x12, 'Spiral Cave (Bottom)') create_sprite(0x00fe, EnemySprite.MiniMoldorm, 0x00, 0, 0x14, 0x16, 'Spiral Cave (Bottom)') @@ -2008,10 +2010,10 @@ def init_vanilla_sprites(): create_sprite(0x010b, 0x1a, SpriteType.Overlord, 0, 0x0f, 0x09) create_sprite(0x010b, EnemySprite.CorrectPullSwitch, 0x00, 0, 0x12, 0x03) create_sprite(0x010b, EnemySprite.AntiFairy, 0x00, 0, 0x0d, 0x07, 'Dam') - create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07) - create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x07) - create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x08) - create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08) + create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07, 'Hookshot Fairy') + create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x07, 'Hookshot Fairy') + create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x17, 0x08, 'Hookshot Fairy') + create_sprite(0x010c, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08, 'Hookshot Fairy') create_sprite(0x010c, EnemySprite.GreenEyegoreMimic, 0x00, 0, 0x07, 0x14, 'Mimic Cave') create_sprite(0x010c, EnemySprite.GreenEyegoreMimic, 0x00, 0, 0x08, 0x14, 'Mimic Cave') create_sprite(0x010c, EnemySprite.GreenEyegoreMimic, 0x00, 0, 0x0c, 0x14, 'Mimic Cave') @@ -2028,10 +2030,10 @@ def init_vanilla_sprites(): create_sprite(0x0114, EnemySprite.FairyPondTrigger, 0x00, 0, 0x07, 0x18) create_sprite(0x0114, EnemySprite.DarkWorldHintNpc, 0x00, 0, 0x19, 0x14) create_sprite(0x0115, EnemySprite.BigFairy, 0x00, 0, 0x17, 0x16) - create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07) - create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x18, 0x07) - create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x17, 0x08) - create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08) + create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x17, 0x07, 'Capacity Fairy Pool') + create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x18, 0x07, 'Capacity Fairy Pool') + create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x17, 0x08, 'Capacity Fairy Pool') + create_sprite(0x0115, EnemySprite.Faerie, 0x00, 0, 0x18, 0x08, 'Capacity Fairy Pool') create_sprite(0x0115, EnemySprite.FairyPondTrigger, 0x00, 0, 0x07, 0x09) create_sprite(0x0116, EnemySprite.FairyPondTrigger, 0x00, 0, 0x17, 0x18) create_sprite(0x0118, EnemySprite.Shopkeeper, 0x00, 0, 0x19, 0x1b) @@ -2040,15 +2042,15 @@ def init_vanilla_sprites(): create_sprite(0x011b, EnemySprite.HeartPiece, 0x00, 0, 0x18, 0x09) create_sprite(0x011b, EnemySprite.HeartPiece, 0x00, 1, 0x05, 0x16) create_sprite(0x011c, EnemySprite.BombShopGuy, 0x00, 0, 0x09, 0x19) - create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x05, 0x07) - create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x06, 0x07) - create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x05, 0x08) - create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x06, 0x08) + create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x05, 0x07, 'Long Fairy Cave') + create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x06, 0x07, 'Long Fairy Cave') + create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x05, 0x08, 'Long Fairy Cave') + create_sprite(0x011e, EnemySprite.Faerie, 0x00, 0, 0x06, 0x08, 'Long Fairy Cave') create_sprite(0x011e, EnemySprite.Shopkeeper, 0x00, 0, 0x18, 0x16) create_sprite(0x011f, EnemySprite.Shopkeeper, 0x00, 0, 0x17, 0x16) create_sprite(0x0120, EnemySprite.GoodBee, 0x00, 0, 0x17, 0x07) - create_sprite(0x0120, EnemySprite.Faerie, 0x00, 0, 0x1b, 0x08) - create_sprite(0x0120, EnemySprite.Faerie, 0x00, 0, 0x1a, 0x09) + create_sprite(0x0120, EnemySprite.Faerie, 0x00, 0, 0x1b, 0x08, 'Good Bee Cave (back)') + create_sprite(0x0120, EnemySprite.Faerie, 0x00, 0, 0x1a, 0x09, 'Good Bee Cave (back)') create_sprite(0x0121, EnemySprite.Smithy, 0x00, 0, 0x04, 0x17) create_sprite(0x0122, EnemySprite.FortuneTeller, 0x00, 0, 0x07, 0x18) create_sprite(0x0122, EnemySprite.FortuneTeller, 0x00, 0, 0x17, 0x18) @@ -2059,10 +2061,10 @@ def init_vanilla_sprites(): create_sprite(0x0123, EnemySprite.Shopkeeper, 0x00, 0, 0x08, 0x05) create_sprite(0x0124, EnemySprite.Shopkeeper, 0x00, 0, 0x08, 0x16) create_sprite(0x0125, EnemySprite.Shopkeeper, 0x00, 0, 0x08, 0x16) - create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x07, 0x15) - create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x08, 0x15) - create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x07, 0x16) - create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x08, 0x16) + create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x07, 0x15, 'Bonk Fairy Pool') + create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x08, 0x15, 'Bonk Fairy Pool') + create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x07, 0x16, 'Bonk Fairy Pool') + create_sprite(0x0126, EnemySprite.Faerie, 0x00, 0, 0x08, 0x16, 'Bonk Fairy Pool') create_sprite(0x0126, EnemySprite.HeartPiece, 0x00, 0, 0x1c, 0x14) create_sprite(0x0127, EnemySprite.HeartPiece, 0x00, 0, 0x07, 0x16) @@ -2157,8 +2159,7 @@ class EnemyTable: rom.write_byte(snes_to_pc(0x28AF00) + super_tile, pointer_index) is_even = len(dungeon_list) % 2 == 0 for dungeon, bitmask in dungeon_list.items(): - dungeon_id = dungeon * 2 - rom.write_bytes(snes_to_pc(0x28B028) + pointer, [dungeon_id] + int16_as_bytes(bitmask)) + rom.write_bytes(snes_to_pc(0x28B028) + pointer, [dungeon] + int16_as_bytes(bitmask)) pointer += 3 if is_even: rom.write_bytes(snes_to_pc(0x28B028) + pointer, [0xFF, 0xFF]) @@ -2177,7 +2178,10 @@ def setup_enemy_locations(world, player): # 1,1,1,1,2,1,2,2,1,2,3,2,2,2,2,2,2,1,2,1(2),1,1,1,1,2 splittable_supertiles = {0x9, 0x1a, 0x35, 0x36, 0x37, 0x2a, 0x57, 0x74, 0x75, 0x6a, 0x7b, 0x7c, 0x7d, 0x9d, 0x8c, - 0x9b, 0x87, 0x82, 0xa2, 0xb2, 0xb6, 0xa9, 0xaa, 0xbc, 0xdb, 0xd1} + 0x9b, 0x87, 0x82, 0xa2, 0xb2, 0xb6, 0xa9, 0xaa, 0xbc, 0xdb, 0xd1, + # fairy needs + 0x107, 0x10c, 0x115, 0x11e, 0x120, 0x126} + # minimum 159 bytes maybe reserve 256 (0x100) # tr pipes, mire left/right bridges, eastern cannonball, tr front entrance = have zero enemies so far but are splittable # 0x14, 0xa2, 0xb9, 0xd6 @@ -2190,6 +2194,7 @@ splittable_supertiles = {0x9, 0x1a, 0x35, 0x36, 0x37, 0x2a, 0x57, 0x74, 0x75, 0x def setup_enemy_dungeon_tables(world, player): enemy_table = world.data_tables[player].uw_enemy_table dungeon_map = defaultdict(lambda: defaultdict(list)) + super_tile_entrance_id_map = {} # for memoization, very minor optimization for super_tile, enemy_list in enemy_table.room_map.items(): if super_tile in splittable_supertiles: idx_adj = 0 @@ -2201,8 +2206,14 @@ def setup_enemy_dungeon_tables(world, player): continue # overlords can't have locations if loc: # possible to-do: caves really aren't supported yet - entrance ids? - dungeon = loc.parent_region.dungeon.dungeon_id if loc.parent_region.dungeon else 0xFF - dungeon_map[super_tile][dungeon].append((loc, index-idx_adj)) + if loc.parent_region.dungeon: + dungeon = loc.parent_region.dungeon.dungeon_id * 2 + dungeon_map[super_tile][dungeon].append((loc, index-idx_adj)) + else: + if super_tile not in super_tile_entrance_id_map: + super_tile_entrance_id_map[super_tile] = find_entrance_ids(loc.parent_region) + for entrance_id in super_tile_entrance_id_map[super_tile]: + dungeon_map[super_tile][entrance_id].append((loc, index-idx_adj)) special_bitmasks = defaultdict(lambda: defaultdict(int)) for super_tile, dungeon_list in dungeon_map.items(): for dungeon, data_list in dungeon_list.items(): @@ -2211,6 +2222,21 @@ def setup_enemy_dungeon_tables(world, player): enemy_table.special_bitmasks = special_bitmasks +def find_entrance_ids(region): + entrance_list = [] + queue = deque([region]) + visited = {region} + while len(queue) > 0: + current = queue.popleft() + for ent in current.entrances: + if ent.parent_region.type in [RegionType.LightWorld, RegionType.DarkWorld]: + entrance_list.append(door_addresses[ent.name][0] + 1) + elif ent.parent_region not in visited: + queue.append(ent.parent_region) + visited.add(ent.parent_region) + return entrance_list + + def valid_drop_location(sprite, index, world, player): if world.dropshuffle[player] == 'underworld': if sprite.drops_item and sprite.drop_item_kind in [0xe4, 0xe5]: @@ -2572,6 +2598,7 @@ sprite_translation = { 'Debirando': EnemySprite.Debirando, 'DebirandoPit': EnemySprite.DebirandoPit, 'FakeMasterSword': EnemySprite.FakeMasterSword, + 'Faerie': EnemySprite.Faerie, 'FireballZora': EnemySprite.FireballZora, 'Firesnake': EnemySprite.Firesnake, 'FloatingSkull': EnemySprite.FloatingSkull, @@ -2632,6 +2659,7 @@ sprite_translation = { 'Toppo': EnemySprite.Toppo, 'UsainBolt': EnemySprite.UsainBolt, 'Vulture': EnemySprite.Vulture, + 'YellowStalfos': EnemySprite.YellowStalfos, 'Wallmaster': EnemySprite.Wallmaster, 'Wizzrobe': EnemySprite.Wizzrobe, 'Zora': EnemySprite.Zora, diff --git a/source/enemizer/Enemizer.py b/source/enemizer/Enemizer.py index c7408e66..539591d1 100644 --- a/source/enemizer/Enemizer.py +++ b/source/enemizer/Enemizer.py @@ -273,7 +273,7 @@ sprite_limiter = { def exceeds_sprite_limit(limit, sprite): - return sprite_limiter[sprite.sprite]-1+limit > 16 if sprite.sprite in sprite_limiter else False + return sprite_limiter[sprite.sprite]-1+limit > 15 if sprite.sprite in sprite_limiter else False def randomize_underworld_rooms(data_tables, world, player, custom_uw): @@ -282,7 +282,7 @@ def randomize_underworld_rooms(data_tables, world, player, custom_uw): specific = setup_specific_requirements(data_tables) uw_candidates, uw_sheets, all_sheets = find_candidate_sprites(data_tables, range(65, 124)) for room_id in range(0, 0x128): - if room_id in {0, 1, 3, 6, 7, 0xd, 0x14, 0x1c, 0x20, 0x29, 0x30, 0x33, + if room_id in {0, 1, 3, 6, 7, 0xd, 0x14, 0x20, 0x29, 0x30, 0x33, 0x4d, 0x5a, 0x90, 0xa4, 0xac, 0xc8, 0xde}: continue current_sprites = data_tables.uw_enemy_table.room_map[room_id] diff --git a/source/enemizer/EnemyLogic.py b/source/enemizer/EnemyLogic.py index 4bb66d8f..67f6eb38 100644 --- a/source/enemizer/EnemyLogic.py +++ b/source/enemizer/EnemyLogic.py @@ -223,7 +223,7 @@ special_rules_check = { 'Swamp Waterway': None, 'Hera Back': [5, 6], 'GT Petting Zoo': [5, 8, 9, 11], - 'Mimic Cave': [3, 4], + 'Mimic Cave': [4, 5, 6, 7], 'Ice Hookshot Ledge': None, 'TR Hub Ledges': [3, 4, 5, 6, 7], 'TR Dark Ride': [1, 2, 3], @@ -233,7 +233,8 @@ special_rules_check = { 'Old Man House': [1, 3], 'Old Man House Back': [4, 5, 6], 'Death Mountain Return Cave (left)': None, - 'Death Mountain Return Cave (right)': [1, 2, 3, 6, 7] # 2, 5, 6 are considered embedded + 'Death Mountain Return Cave (right)': [1, 2, 3, 6, 7], # 2, 5, 6 are considered embedded + 'Hookshot Fairy': [0, 1, 2, 3] } @@ -244,6 +245,11 @@ def special_rules_for_region(world, player, region_name, location, original_rule medallion_rule(world, player, 'Bombos', 1)) elif region_name in ['Hera Back', 'GT Petting Zoo', 'Mimic Cave']: enemy_number = int(location.name.split('#')[1]) + if region_name == 'Mimic Cave': + if enemy_number in [4, 5]: # these are behind hammer blocks potentially + return and_rule(original_rule, has('Hammer', player)) + elif enemy_number in special_rules_check[region_name]: # these are behind rails + return and_rule(original_rule, has_boomerang(player)) if enemy_number in special_rules_check[region_name]: return and_rule(original_rule, has_boomerang(player)) else: @@ -255,7 +261,8 @@ def special_rules_for_region(world, player, region_name, location, original_rule else: return original_rule elif region_name in ['Old Man Cave (West)', 'Old Man Cave (East)', 'Old Man House Back', 'Old Man House', - 'Death Mountain Return Cave (left)', 'Death Mountain Return Cave (right)']: + 'Death Mountain Return Cave (left)', 'Death Mountain Return Cave (right)', + 'Hookshot Fairy']: enemy_number = int(location.name.split('#')[1]) if region_name == 'Death Mountain Return Cave (left)': if enemy_number in [1, 5]: diff --git a/source/enemizer/SpriteSheets.py b/source/enemizer/SpriteSheets.py index 50d12ff6..fa703e20 100644 --- a/source/enemizer/SpriteSheets.py +++ b/source/enemizer/SpriteSheets.py @@ -283,6 +283,7 @@ def init_sprite_requirements(): SpriteRequirement(EnemySprite.RedEyegoreMimic).sub_group(2, 0x2e), SpriteRequirement(EnemySprite.Kodongo).sub_group(2, 0x2a), + # SpriteRequirement(EnemySprite.YellowStalfos).sub_group(0, 0x1f), # doesn't spawn SpriteRequirement(EnemySprite.Mothula).exalt().sub_group(2, 0x38).sub_group(3, 0x52), SpriteRequirement(EnemySprite.SpikeBlock).immune().sub_group(3, [0x52, 0x53]).exclude(NoBeamosOrTrapRooms) .exclude({0x28}), # why exclude sp entrance? @@ -360,7 +361,7 @@ def init_sprite_requirements(): SpriteRequirement(EnemySprite.DiggingGameNPC).affix().sub_group(1, 0x2a), SpriteRequirement(EnemySprite.Ganon).exalt().sub_group(0, 0x21).sub_group(1, 0x41) .sub_group(2, 0x45).sub_group(3, 0x33), - SpriteRequirement(EnemySprite.Faerie).affix(), + SpriteRequirement(EnemySprite.Faerie).immune(), SpriteRequirement(EnemySprite.FakeMasterSword).immune().sub_group(3, 0x11), SpriteRequirement(EnemySprite.MagicShopAssistant).affix().sub_group(0, 0x4b).sub_group(3, 0x5a), SpriteRequirement(EnemySprite.SomariaPlatform).affix().sub_group(2, 0x27), diff --git a/source/enemizer/enemy_deny.yaml b/source/enemizer/enemy_deny.yaml index 4ff270f0..f4866764 100644 --- a/source/enemizer/enemy_deny.yaml +++ b/source/enemizer/enemy_deny.yaml @@ -33,7 +33,7 @@ UwGeneralDeny: - [ 0x0021, 3, [ "RollerVerticalDown", "RollerVerticalUp" ] ] #"Sewers - Dark U - Rat 2" - [ 0x0021, 4, [ "RollerVerticalDown", "RollerVerticalUp" ] ] #"Sewers - Dark U - Rat 3" - [ 0x0024, 6, [ "Wizzrobe" ] ] # Wizzrobes can't spawn on pots - - [ 0x0026, 1, [ "SparkCW", "SparkCCW", "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Bumper" ] ] #"Swamp Palace - Big Spoon - Red Bari 1" + - [ 0x0026, 1, [ "SparkCW", "SparkCCW", "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Bumper", "Statue" ] ] #"Swamp Palace - Big Spoon - Red Bari 1" - [ 0x0026, 8, [ "AntiFairyCircle", "Bumper", "Statue" ] ] #"Swamp Palace - Big Spoon - Red Bari 3" - [ 0x0026, 9, [ "RollerHorizontalRight", "Statue" ] ] #"Swamp Palace - Big Spoon - Kyameron" - [ 0x0026, 10, [ "Statue" ] ] # multiple push statues in this room can cause issues @@ -45,6 +45,7 @@ UwGeneralDeny: - [ 0x0028, 4, [ "RollerVerticalUp" ] ] #"Swamp Palace - Entrance Ledge - Spike Trap" - [ 0x002a, 2, [ "SparkCW", "SparkCCW", "RollerHorizontalRight", "RollerHorizontalLeft", "AntiFairyCircle", "BigSpike", "SpikeBlock" ] ] #"Palace of Darkness - Arena Main - Hardhat Beetle 1" - [ 0x002a, 3, [ "Statue", "SparkCW", "SparkCCW", "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "FirebarCW", "FirebarCCW", "SpikeBlock", "Bumper" ] ] #"Palace of Darkness - Arena Main - Hardhat Beetle 2" + - [ 0x002a, 4, [ "Statue", "Beamos", "AntiFairyCircle", "BigSpike", "Bumper" ]] - [ 0x002a, 6, [ "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Bumper" ] ] #"Palace of Darkness - Arena Main - Hardhat Beetle 5" - [ 0x002b, 5, [ "RollerHorizontalRight" ] ] #"Palace of Darkness - Fairies - Red Bari 2" - [ 0x002e, 0, [ "RollerVerticalUp", "RollerVerticalDown", "RollerHorizontalLeft", "RollerHorizontalRight", "BigSpike", "FirebarCW", "FirebarCCW" ] ] #"Ice Palace - Penguin Chest - Pengator 1" @@ -289,6 +290,10 @@ UwGeneralDeny: - [ 0x00ce, 0, [ "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "AntiFairyCircle", "Antifairy", "BigSpike", "FirebarCCW", "Bumper" ] ] #"Ice Palace - Over Boss - top - Red Bari 1" - [ 0x00ce, 1, [ "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "AntiFairyCircle", "Antifairy", "BigSpike", "FirebarCW", "Bumper" ] ] #"Ice Palace - Over Boss - top - Red Bari 2" - [ 0x00ce, 3, [ "SparkCW", "SparkCCW", "RollerVerticalDown", "RollerVerticalUp", "RollerHorizontalRight", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "Antifairy", "BigSpike", "FirebarCW", "FirebarCCW", "SpikeBlock", "Bumper" ] ] #"Ice Palace - Over Boss - top - Statue" + - [ 0x00ce, 4, [ "RollerVerticalDown", "RollerVerticalUp", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Beamos", "Bumper", "FirebarCW", "FirebarCCW"]] + - [ 0x00ce, 5, [ "RollerVerticalDown", "RollerVerticalUp", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Beamos", "Bumper", "FirebarCW", "FirebarCCW"]] + - [ 0x00ce, 6, [ "RollerVerticalDown", "RollerVerticalUp", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Beamos", "Bumper", "FirebarCW", "FirebarCCW"]] + - [ 0x00ce, 7, [ "RollerVerticalDown", "RollerVerticalUp", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Beamos", "Bumper", "FirebarCW", "FirebarCCW"]] - [ 0x00d0, 6, [ "Statue", "RollerVerticalUp", "RollerVerticalDown", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Bumper" ] ] # Agahnims Tower - Dark Maze - Blue Guard 2 - [ 0x00d2, 8, [ "RollerVerticalDown", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "SpikeBlock", "Bumper" ] ] #"Misery Mire - Mire 2 - Popo BL" - [ 0x00d5, 4, [ "Statue", "RollerVerticalUp", "RollerVerticalDown", "RollerHorizontalLeft", "Beamos", "AntiFairyCircle", "BigSpike", "FirebarCW", "FirebarCCW", "SpikeBlock", "Bumper" ] ] #"Turtle Rock - Eye Bridge - Hardhat Beetle" @@ -334,8 +339,14 @@ UwGeneralDeny: - [ 0x00f1, 4, [ "RollerVerticalUp", "RollerVerticalDown", "RollerHorizontalLeft", "RollerHorizontalRight" ] ] #"Old Man Maze - Keese 5" - [ 0x00f1, 5, [ "RollerVerticalUp", "RollerVerticalDown", "RollerHorizontalLeft", "RollerHorizontalRight" ] ] #"Old Man Maze - Keese 6" - [ 0x00fd, 0, [ "Bumper" ] ] + - [ 0x0107, 1, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] + - [ 0x0107, 2, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] OwGeneralDeny: - - [0x1e, 3, ["Beamos"]] # forbid a beamos here + - [0x1e, 3, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] # forbid a beamos here + - [0x40, 0, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] + - [0x40, 7, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] + - [0x40, 13, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] + - [0x40, 14, ["Beamos", "Bumper", "BigSpike", "AntiFairyCircle"]] - [0x5e, 4, ["RollerVerticalUp", "Gibo"]] # forbid that one roller for kiki pod, and the kiki eating Gibo - [0x5e, 5, ["Gibo"]] # kiki eating Gibo UwEnemyDrop: @@ -343,8 +354,8 @@ UwEnemyDrop: - [0x0085, 9, ["Babasu"]] # ran off the edge and didn't return - [0x00cc, 5, ["Babasu"]] # little hard to see and kill appropriately # the following are behind rails - - [0x0077, 4, ["StalfosKnight", "Geldman", "Blob", "Stal"]] # can't activate here - - [0x0077, 5, ["StalfosKnight", "Geldman", "Blob", "Stal"]] + - [0x0077, 4, ["StalfosKnight", "Geldman", "Blob", "Stal", "Wizzrobe"]] # can't activate here + - [0x0077, 5, ["StalfosKnight", "Geldman", "Blob", "Stal", "Wizzrobe"]] - [0x007D, 4, ["StalfosKnight", "Geldman", "Blob", "Stal"]] - [0x007D, 7, ["StalfosKnight", "Geldman", "Blob", "Stal"]] - [0x007D, 8, ["StalfosKnight", "Geldman", "Blob", "Stal"]] @@ -357,10 +368,10 @@ UwEnemyDrop: # because they despawned or clipped away or immediately fell, etc - [0x003d, 9, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x003d, 10, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x0044, 4, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] @@ -381,73 +392,108 @@ UwEnemyDrop: "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] - [0x007f, 0, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x007f, 1, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x007f, 2, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x007f, 3, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x0095, 0, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] - [0x0095, 1, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x0095, 2, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x0095, 3, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] - [0x00b5, 0, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00b5, 1, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00b5, 2, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00c6, 2, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00c6, 3, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00c6, 4, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00c6, 5, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Bumper", "Stal", "GreenMimic", "RedMimic"]] + "BombGuard", "GreenKnifeGuard", "Bumper", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] - [0x00c6, 6, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] - - [0x00e6, 6, [ "HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", - "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", - "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic"]] - # wizzrobe despawn issues - on pots/blocks + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] + - [0x00e6, 6, ["HardhatBeetle", "Wizzrobe", "MiniHelmasaur", "BlueGuard", "GreenGuard", "RedSpearGuard", + "BluesainBolt", "UsainBolt", "BlueArcher", "GreenBushGuard", "RedJavelinGuard", "RedBushGuard", + "BombGuard", "GreenKnifeGuard", "Stal", "GreenMimic", "RedMimic", "StalfosKnight", "Geldman", "Blob"]] + # wizzrobe despawn issues - on pots/blocks - too close to some object + - [0x0016, 0, ["Wizzrobe"]] + - [0x0016, 1, ["Wizzrobe"]] + - [0x0016, 2, ["Wizzrobe"]] + - [0x0016, 3, ["Wizzrobe"]] + - [0x0019, 2, ["Wizzrobe"]] + - [0x0019, 3, ["Wizzrobe"]] + - [0x002a, 3, ["Wizzrobe"]] + - [0x002a, 7, ["Wizzrobe"]] + - [0x0035, 5, ["Wizzrobe"]] + - [0x0036, 8, ["Wizzrobe"]] + - [0x003c, 1, ["Wizzrobe"]] + - [0x004b, 2, ["Wizzrobe"]] + - [0x004b, 6, ["Wizzrobe"]] + - [0x004b, 7, ["Wizzrobe"]] - [0x004e, 3, ["Wizzrobe", "Stal"]] + - [0x0054, 3, ["Wizzrobe", "Stal"]] + - [0x0055, 2, ["Wizzrobe"]] # slightly on wall - [0x005e, 4, ["Wizzrobe", "Stal"]] + - [0x0067, 5, ["Wizzrobe"]] + - [0x0067, 6, ["Wizzrobe"]] + - [0x0067, 7, ["Wizzrobe", "Stal"]] + - [0x0067, 8, ["Wizzrobe", "Stal"]] + - [0x0074, 5, ["Wizzrobe"]] - [0x007c, 1, ["Wizzrobe", "Stal"]] - [0x007c, 3, ["Wizzrobe", "Stal"]] - [0x007e, 1, ["Wizzrobe", "Stal"]] - [0x007e, 6, ["Wizzrobe", "Stal"]] + - [0x0083, 9, ["Wizzrobe"]] - [0x008b, 6, ["Wizzrobe", "Stal"]] - [0x008b, 7, ["Wizzrobe", "Stal"]] - [0x008d, 9, ["Wizzrobe", "Stal"]] - [0x009f, 5, ["Wizzrobe", "Stal"]] + - [0x00a1, 1, ["Wizzrobe"]] - [0x00af, 0, ["Wizzrobe", "Stal"]] + - [0x00b2, 4, ["Wizzrobe"]] - [0x00bf, 1, ["Wizzrobe"]] - - [0x00ce, 5, ["Wizzrobe"]] - - [0x00ce, 6, ["Wizzrobe"]] - - [0x00ce, 7, ["Wizzrobe"]] - - [0x00ce, 8, ["Wizzrobe"]] + - [0x00c1, 3, ["Wizzrobe", "Stal"]] + - [0x00c2, 0, ["Wizzrobe"]] + - [0x00c2, 3, ["Wizzrobe"]] + - [0x00c2, 7, ["Wizzrobe"]] + - [0x00ce, 5, ["Wizzrobe", "Leever", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", + "BlueArcher", "RedJavelinGuard", "GreenKnifeGuard", "GreenMimic", "RedMimic"]] + - [0x00ce, 6, ["Wizzrobe", "Leever", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", + "BlueArcher", "RedJavelinGuard", "GreenKnifeGuard", "GreenMimic", "RedMimic"]] + - [0x00ce, 7, ["Wizzrobe", "Leever", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", + "BlueArcher", "RedJavelinGuard", "GreenKnifeGuard", "GreenMimic", "RedMimic"]] + - [0x00ce, 8, ["Wizzrobe", "Leever", "BlueGuard", "GreenGuard", "RedSpearGuard", "BluesainBolt", "UsainBolt", + "BlueArcher", "RedJavelinGuard", "GreenKnifeGuard", "GreenMimic", "RedMimic"]] - [0x00d5, 4, ["Wizzrobe"]] + - [0x00df, 1, ["Wizzrobe"]] # slightly on wall + - [0x00e7, 4, ["Wizzrobe"]] # slightly on wall + - [0x00fd, 1, ["Wizzrobe"]] # slightly on rock - [0x010c, 4, ["Wizzrobe"]] - [0x010c, 5, ["Wizzrobe"]] # other mimic cave spots are in the rail section diff --git a/source/enemizer/enemy_weight.yaml b/source/enemizer/enemy_weight.yaml index 58126bf3..7cef3326 100644 --- a/source/enemizer/enemy_weight.yaml +++ b/source/enemizer/enemy_weight.yaml @@ -25,6 +25,7 @@ UW: # Total 94431 Deadrock: 186 # 0.53796% raw:508 4.49558% Debirando: 154 # 0.65127% raw:615 5.44248% DebirandoPit: 154 # 0.65127% raw:615 5.44248% + Faerie: 19 FakeMasterSword: 120 # 0.81223% raw:767 6.78761% FireballZora: 165 # 0.60679% raw:573 5.07080% FirebarCCW: 49 # 2.02688% raw:1914 16.93805% @@ -97,6 +98,7 @@ UW: # Total 94431 Vulture: 445 # 0.22450% raw:212 1.87611% Wallmaster: 247 # 0.40453% raw:382 3.38053% Wizzrobe: 306 # 0.32722% raw:309 2.73451% +# YellowStalfos: 49 Zora: 609 # 0.16414% raw:155 1.37168% Zoro: 80 # 1.15428% raw:1090 9.64602% OW: # Total 117724 @@ -126,6 +128,7 @@ OW: # Total 117724 Deadrock: 144 # 0.69570% raw:819 7.24779% Debirando: 164 # 0.60905% raw:717 6.34513% DebirandoPit: 164 # 0.60905% raw:717 6.34513% + Faerie: 19 FakeMasterSword: 120 # 1.15609% raw:1361 12.04425% FireballZora: 119 # 0.84350% raw:993 8.78761% FirebarCCW: 47 # 2.11767% raw:2493 22.06195% @@ -198,5 +201,6 @@ OW: # Total 117724 Vulture: 229 # 0.43746% raw:515 4.55752% Wallmaster: 643 # 0.15545% raw:183 1.61947% Wizzrobe: 345 # 0.28966% raw:341 3.01770% +# YellowStalfos: 47 Zora: 558 # 0.17923% raw:211 1.86726% Zoro: 100 # 0.84605% raw:996 8.81416% \ No newline at end of file diff --git a/source/enemizer/sheet_weight.yaml b/source/enemizer/sheet_weight.yaml index 03d151c5..07adea77 100644 --- a/source/enemizer/sheet_weight.yaml +++ b/source/enemizer/sheet_weight.yaml @@ -43,7 +43,7 @@ SheetChoices: - slots: [0] assignments: 0: 0x1f - weight: 7 # Sparks, Firebars, FloatingSkull, RedBari, BlueBari, Firesnake, Stalfos + weight: 7 # Sparks, Firebars, FloatingSkull, RedBari, BlueBari, Firesnake, Stalfos, ~~YellowStalfos~~ - slots: [0] assignments: 0: 0x2f diff --git a/source/overworld/EntranceShuffle2.py b/source/overworld/EntranceShuffle2.py index 23edc76c..60c56a19 100644 --- a/source/overworld/EntranceShuffle2.py +++ b/source/overworld/EntranceShuffle2.py @@ -1888,11 +1888,19 @@ mandatory_connections = [('Links House S&Q', 'Links House'), ('Kakariko Well (top to back)', 'Kakariko Well (back)'), ('Blinds Hideout N', 'Blinds Hideout (Top)'), ('Bat Cave Door', 'Bat Cave (left)'), + ('Good Bee Cave Front to Back', 'Good Bee Cave (back)'), + ('Good Bee Cave Back to Front', 'Good Bee Cave'), + ('Capacity Upgrade East', 'Capacity Fairy Pool'), + ('Capacity Fairy Pool West', 'Capacity Upgrade'), + ('Bonk Fairy (Dark) Pool', 'Bonk Fairy Pool'), + ('Bonk Fairy (Light) Pool', 'Bonk Fairy Pool'), ('Hookshot Cave Front to Middle', 'Hookshot Cave (Middle)'), ('Hookshot Cave Middle to Front', 'Hookshot Cave (Front)'), ('Hookshot Cave Middle to Back', 'Hookshot Cave (Back)'), ('Hookshot Cave Back to Middle', 'Hookshot Cave (Middle)'), + ('Hookshot Cave Back to Fairy', 'Hookshot Cave (Fairy Pool)'), + ('Hookshot Cave Fairy to Back', 'Hookshot Cave (Back)'), ('Hookshot Cave Bonk Path', 'Hookshot Cave (Bonk Islands)'), ('Hookshot Cave Hook Path', 'Hookshot Cave (Hook Islands)'), ('Superbunny Cave Climb', 'Superbunny Cave (Top)'),