1#ifndef YAZE_APP_ZELDA3_DUNGEON_ROOM_H
2#define YAZE_APP_ZELDA3_DUNGEON_ROOM_H
13#include "absl/types/span.h"
31class RoomLayerManager;
59const static LayerMergeType LayerMerge00{0x00,
"Off",
true,
false,
false};
60const static LayerMergeType LayerMerge01{0x01,
"Parallax",
true,
false,
false};
61const static LayerMergeType LayerMerge02{0x02,
"Dark",
true,
true,
true};
62const static LayerMergeType LayerMerge03{0x03,
"On top",
false,
true,
false};
63const static LayerMergeType LayerMerge04{0x04,
"Translucent",
true,
true,
true};
64const static LayerMergeType LayerMerge05{0x05,
"Addition",
true,
true,
true};
65const static LayerMergeType LayerMerge06{0x06,
"Normal",
true,
false,
false};
66const static LayerMergeType LayerMerge07{0x07,
"Transparent",
true,
true,
true};
67const static LayerMergeType LayerMerge08{0x08,
"Dark room",
true,
true,
true};
69const static LayerMergeType kLayerMergeTypeList[] = {
70 LayerMerge00, LayerMerge01, LayerMerge02, LayerMerge03, LayerMerge04,
71 LayerMerge05, LayerMerge06, LayerMerge07, LayerMerge08};
179 std::array<uint8_t, 64 * 64>
tiles{};
301 if (index <
doors_.size()) {
330 absl::StatusOr<size_t>
FindObjectAt(
int x,
int y,
int layer)
const;
395 if (x < 0 || x >= 64 || y < 0 || y >= 64)
return 0;
400 if (x < 0 || x >= 64 || y < 0 || y >= 64)
return;
416 if (x < 0 || x >= 64 || y < 0 || y >= 64)
return false;
421 if (x < 0 || x >= 64 || y < 0 || y >= 64)
return;
422 const uint8_t val = filled ? 1 : 0;
423 const size_t idx =
static_cast<size_t>(y * 64 + x);
425 if (prev == val)
return;
512 if (index >= 0 && index < 4)
517 if (index >= 0 && index < 4)
602 int& nbr_of_staircase);
623 : zelda3_version::US);
780 const std::vector<uint8_t>& encoded_bytes);
793 "Hyrule Castle (North Corridor)",
794 "Behind Sanctuary (Switch)",
796 "Turtle Rock (Crysta-Roller)",
798 "Swamp Palace (Arrghus[Boss])",
799 "Tower of Hera (Moldorm[Boss])",
800 "Cave (Healing Fairy)",
801 "Palace of Darkness",
802 "Palace of Darkness (Stalfos Trap)",
803 "Palace of Darkness (Turtle)",
804 "Ganon's Tower (Entrance)",
805 "Ganon's Tower (Agahnim2[Boss])",
806 "Ice Palace (Entrance )",
808 "Ganon Evacuation Route",
809 "Hyrule Castle (Bombable Stock )",
811 "Turtle Rock (Hokku-Bokku Key 2)",
812 "Turtle Rock (Big Key )",
814 "Swamp Palace (Swimming Treadmill)",
815 "Tower of Hera (Moldorm Fall )",
817 "Palace of Darkness (Dark Maze)",
818 "Palace of Darkness (Big Chest )",
819 "Palace of Darkness (Mimics / Moving Wall )",
820 "Ganon's Tower (Ice Armos)",
821 "Ganon's Tower (Final Hallway)",
822 "Ice Palace (Bomb Floor / Bari )",
823 "Ice Palace (Pengator / Big Key )",
824 "Agahnim's Tower (Agahnim[Boss])",
825 "Hyrule Castle (Key-rat )",
826 "Hyrule Castle (Sewer Text Trigger )",
827 "Turtle Rock (West Exit to Balcony)",
828 "Turtle Rock (Double Hokku-Bokku / Big chest )",
830 "Swamp Palace (Statue )",
831 "Tower of Hera (Big Chest)",
832 "Swamp Palace (Entrance )",
833 "Skull Woods (Mothula[Boss])",
834 "Palace of Darkness (Big Hub )",
835 "Palace of Darkness (Map Chest / Fairy )",
838 "Ice Palace (Compass )",
839 "Cave (Kakariko Well HP)",
840 "Agahnim's Tower (Maiden Sacrifice Chamber)",
841 "Tower of Hera (Hardhat Beetles )",
842 "Hyrule Castle (Sewer Key Chest )",
843 "Desert Palace (Lanmolas[Boss])",
844 "Swamp Palace (Push Block Puzzle / Pre-Big Key )",
845 "Swamp Palace (Big Key / BS )",
846 "Swamp Palace (Big Chest )",
847 "Swamp Palace (Map Chest / Water Fill )",
848 "Swamp Palace (Key Pot )",
849 "Skull Woods (Gibdo Key / Mothula Hole )",
850 "Palace of Darkness (Bombable Floor )",
851 "Palace of Darkness (Spike Block / Conveyor )",
853 "Ganon's Tower (Torch 2)",
854 "Ice Palace (Stalfos Knights / Conveyor Hellway)",
855 "Ice Palace (Map Chest )",
856 "Agahnim's Tower (Final Bridge )",
857 "Hyrule Castle (First Dark )",
858 "Hyrule Castle (6 Ropes )",
859 "Desert Palace (Torch Puzzle / Moving Wall )",
860 "Thieves Town (Big Chest )",
861 "Thieves Town (Jail Cells )",
862 "Swamp Palace (Compass Chest )",
865 "Skull Woods (Gibdo Torch Puzzle )",
866 "Palace of Darkness (Entrance )",
867 "Palace of Darkness (Warps / South Mimics )",
868 "Ganon's Tower (Mini-Helmasaur Conveyor )",
869 "Ganon's Tower (Moldorm )",
870 "Ice Palace (Bomb-Jump )",
871 "Ice Palace Clone (Fairy )",
872 "Hyrule Castle (West Corridor)",
873 "Hyrule Castle (Throne )",
874 "Hyrule Castle (East Corridor)",
875 "Desert Palace (Popos 2 / Beamos Hellway )",
876 "Swamp Palace (Upstairs Pits )",
877 "Castle Secret Entrance / Uncle Death ",
878 "Skull Woods (Key Pot / Trap )",
879 "Skull Woods (Big Key )",
880 "Skull Woods (Big Chest )",
881 "Skull Woods (Final Section Entrance )",
882 "Palace of Darkness (Helmasaur King[Boss])",
883 "Ganon's Tower (Spike Pit )",
884 "Ganon's Tower (Ganon-Ball Z)",
885 "Ganon's Tower (Gauntlet 1/2/3)",
886 "Ice Palace (Lonely Firebar)",
887 "Ice Palace (Hidden Chest / Spike Floor )",
888 "Hyrule Castle (West Entrance )",
889 "Hyrule Castle (Main Entrance )",
890 "Hyrule Castle (East Entrance )",
891 "Desert Palace (Final Section Entrance )",
892 "Thieves Town (West Attic )",
893 "Thieves Town (East Attic )",
894 "Swamp Palace (Hidden Chest / Hidden Door )",
895 "Skull Woods (Compass Chest )",
896 "Skull Woods (Key Chest / Trap )",
898 "Palace of Darkness (Rupee )",
899 "Ganon's Tower (Mimics s)",
900 "Ganon's Tower (Lanmolas )",
901 "Ganon's Tower (Gauntlet 4/5)",
902 "Ice Palace (Pengators )",
904 "Hyrule Castle (Small Corridor to Jail Cells)",
905 "Hyrule Castle (Boomerang Chest )",
906 "Hyrule Castle (Map Chest )",
907 "Desert Palace (Big Chest )",
908 "Desert Palace (Map Chest )",
909 "Desert Palace (Big Key Chest )",
910 "Swamp Palace (Water Drain )",
911 "Tower of Hera (Entrance )",
916 "Ganon's Tower (East Side Collapsing Bridge / Exploding Wall )",
917 "Ganon's Tower (Winder / Warp Maze )",
918 "Ice Palace (Hidden Chest / Bombable Floor )",
919 "Ice Palace ( Big Spike Traps )",
920 "Hyrule Castle (Jail Cell )",
922 "Hyrule Castle (Basement Chasm )",
923 "Desert Palace (West Entrance )",
924 "Desert Palace (Main Entrance )",
925 "Desert Palace (East Entrance )",
927 "Tower of Hera (Tile )",
929 "Eastern Palace (Fairy )",
931 "Ganon's Tower (Block Puzzle / Spike Skip / Map Chest )",
932 "Ganon's Tower (East and West Downstairs / Big Chest )",
933 "Ganon's Tower (Tile / Torch Puzzle )",
936 "Misery Mire (Vitreous[Boss])",
937 "Misery Mire (Final Switch )",
938 "Misery Mire (Dark Bomb Wall / Switches )",
939 "Misery Mire (Dark Cane Floor Switch Puzzle )",
941 "Ganon's Tower (Final Collapsing Bridge )",
942 "Ganon's Tower (Torches 1 )",
943 "Misery Mire (Torch Puzzle / Moving Wall )",
944 "Misery Mire (Entrance )",
945 "Eastern Palace (Eyegore Key )",
947 "Ganon's Tower (Many Spikes / Warp Maze )",
948 "Ganon's Tower (Invisible Floor Maze )",
949 "Ganon's Tower (Compass Chest / Invisible Floor )",
950 "Ice Palace (Big Chest )",
952 "Misery Mire (Pre-Vitreous )",
953 "Misery Mire (Fish )",
954 "Misery Mire (Bridge Key Chest )",
956 "Turtle Rock (Trinexx[Boss])",
957 "Ganon's Tower (Wizzrobes s)",
958 "Ganon's Tower (Moldorm Fall )",
959 "Tower of Hera (Fairy )",
960 "Eastern Palace (Stalfos Spawn )",
961 "Eastern Palace (Big Chest )",
962 "Eastern Palace (Map Chest )",
963 "Thieves Town (Moving Spikes / Key Pot )",
964 "Thieves Town (Blind The Thief[Boss])",
967 "Ice Palace (Ice Bridge )",
968 "Agahnim's Tower (Circle of Pots)",
969 "Misery Mire (Hourglass )",
970 "Misery Mire (Slug )",
971 "Misery Mire (Spike Key Chest )",
972 "Turtle Rock (Pre-Trinexx )",
973 "Turtle Rock (Dark Maze)",
974 "Turtle Rock (Chain Chomps )",
975 "Turtle Rock (Map Chest / Key Chest / Roller )",
976 "Eastern Palace (Big Key )",
977 "Eastern Palace (Lobby Cannonballs )",
978 "Eastern Palace (Dark Antifairy / Key Pot )",
979 "Thieves Town (Hellway)",
980 "Thieves Town (Conveyor Toilet)",
982 "Ice Palace (Block Puzzle )",
983 "Ice Palace Clone (Switch )",
984 "Agahnim's Tower (Dark Bridge )",
985 "Misery Mire (Compass Chest / Tile )",
986 "Misery Mire (Big Hub )",
987 "Misery Mire (Big Chest )",
988 "Turtle Rock (Final Crystal Switch Puzzle )",
989 "Turtle Rock (Laser Bridge)",
991 "Turtle Rock (Torch Puzzle)",
992 "Eastern Palace (Armos Knights[Boss])",
993 "Eastern Palace (Entrance )",
995 "Thieves Town (North West Entrance )",
996 "Thieves Town (North East Entrance )",
998 "Ice Palace (Hole to Kholdstare )",
1000 "Agahnim's Tower (Dark Maze)",
1001 "Misery Mire (Conveyor Slug / Big Key )",
1002 "Misery Mire (Mire02 / Wizzrobes )",
1005 "Turtle Rock (Laser Key )",
1006 "Turtle Rock (Entrance )",
1008 "Eastern Palace (Zeldagamer / Pre-Armos Knights )",
1009 "Eastern Palace (Canonball ",
1011 "Thieves Town (Main (South West) Entrance )",
1012 "Thieves Town (South East Entrance )",
1014 "Ice Palace (Kholdstare[Boss])",
1016 "Agahnim's Tower (Entrance )",
1017 "Cave (Lost Woods HP)",
1018 "Cave (Lumberjack's Tree HP)",
1020 "Cave (Lost Old Man Final Cave)",
1021 "Cave (Lost Old Man Final Cave)",
1026 "Cave (Spectacle Rock HP)",
1030 "Cave (Spiral Cave)",
1031 "Cave (Crystal Switch / 5 Chests )",
1032 "Cave (Lost Old Man Starting Cave)",
1033 "Cave (Lost Old Man Starting Cave)",
1035 "House (Old Woman (Sahasrahla's Wife?))",
1036 "House (Angry Brothers)",
1037 "House (Angry Brothers)",
1076 "Circle of bush Cave",
1077 "Big Bomb Shop, C-House",
1092extern const std::string
RoomTag[65];
The Rom class is used to load, save, and modify Rom data. This is a generic SNES ROM container and do...
Represents a bitmap image optimized for SNES ROM hacking.
static std::pair< uint8_t, uint8_t > EncodeDoorBytes(uint8_t position, DoorType type, DoorDirection direction)
Encode door data for ROM storage.
static std::pair< int, int > PositionToPixelCoords(uint8_t position, DoorDirection direction)
Convert encoded position to pixel coordinates.
static std::tuple< int, int, int, int > GetDoorBounds(uint8_t position, DoorDirection direction)
Get the bounding rectangle for a door.
static std::pair< int, int > PositionToTileCoords(uint8_t position, DoorDirection direction)
Convert encoded position to tile coordinates.
Interface for accessing dungeon game state.
RoomLayerManager - Manages layer visibility and compositing.
bool ValidateObject(const RoomObject &object) const
const std::array< uint8_t, 0x10000 > & get_gfx_buffer() const
std::vector< RoomObject > tile_objects_
gfx::BackgroundBuffer object_bg1_buffer_
void SetTag2Direct(TagKey tag2)
bool HasExceededLimits() const
Check if any object limits are exceeded.
const CustomCollisionMap & custom_collision() const
uint8_t staircase_plane_[4]
absl::Status UpdateObject(size_t index, const RoomObject &object)
WaterFillZoneMap & water_fill_zone()
void AddTileObject(const RoomObject &object)
void SetStair4Target(uint8_t target)
void SetPitsTarget(uint8_t target)
void SetIsLight(bool is_light)
gfx::BackgroundBuffer bg2_buffer_
const std::vector< chest_data > & GetChests() const
uint8_t cached_floor2_graphics_
std::vector< zelda3::Sprite > sprites_
CustomCollisionMap custom_collision_
void SetLoaded(bool loaded)
uint8_t GetCollisionTile(int x, int y) const
void ClearCustomCollisionDirty()
void CopyRoomGraphicsToBuffer()
void set_water_fill_sram_bit_mask(uint8_t mask)
uint16_t message_id() const
bool custom_collision_dirty() const
std::vector< staircase > & GetStairs()
zelda3_version_pointers version_constants() const
void LoadRoomGraphics(uint8_t entrance_blockset=0xFF)
void set_floor2(uint8_t value)
const WaterFillZoneMap & water_fill_zone() const
std::vector< Door > doors_
void SetStaircaseRoom(int index, uint8_t room)
const gfx::Bitmap & composite_bitmap() const
int WaterFillTileCount() const
absl::Status RemoveObject(size_t index)
void SetStair1TargetLayer(uint8_t layer)
void set_floor1(uint8_t value)
void SetLayer2Mode(uint8_t mode)
void LoadLayoutTilesToBuffer()
uint8_t staircase_room(int index) const
void SetTag2(TagKey tag2)
const std::vector< Door > & GetDoors() const
std::vector< DungeonLimitInfo > GetExceededLimitDetails() const
Get list of exceeded limits with details.
auto & object_bg2_buffer()
void ParseObjectsFromLocation(int objects_location)
uint8_t cached_floor1_graphics_
bool custom_collision_dirty_
void set_has_custom_collision(bool has)
void ClearWaterFillZone()
const auto & object_bg1_buffer() const
void ReloadGraphics(uint8_t entrance_blockset=0xFF)
std::vector< zelda3::Sprite > & GetSprites()
void SetTag1Direct(TagKey tag1)
bool IsCompositeDirty() const
void SetLayoutId(uint8_t id)
void SetHolewarp(uint8_t hw)
std::vector< Door > & GetDoors()
void SetStair2Target(uint8_t target)
size_t GetTileObjectCount() const
const auto & object_bg2_buffer() const
CustomCollisionMap & custom_collision()
void SetCollision(CollisionKey collision)
const std::vector< staircase > & GetStairs() const
gfx::BackgroundBuffer bg1_buffer_
absl::Status SaveObjects()
bool has_water_fill_zone() const
RoomObject & GetTileObject(size_t index)
void SetStaircasePlane(int index, uint8_t plane)
void SetIsDark(bool is_dark)
WaterFillZoneMap water_fill_zone_
std::map< DungeonLimit, int > GetLimitedObjectCounts() const
Count limited objects in this room.
void RenderRoomGraphics()
absl::Status SaveRoomHeader()
gfx::Bitmap composite_bitmap_
Room & operator=(Room &&)
std::vector< RoomObject > & GetTileObjects()
std::vector< PotItem > & GetPotItems()
CollisionKey collision() const
const RoomLayout & GetLayout() const
void SetMessageIdDirect(uint16_t mid)
void AddDoor(const Door &door)
uint8_t staircase_rooms_[4]
const auto & bg1_buffer() const
gfx::Bitmap & GetCompositeBitmap(RoomLayerManager &layer_mgr)
Get a composite bitmap of all layers merged.
std::vector< uint8_t > EncodeObjects() const
void SetEffect(EffectKey effect)
gfx::BackgroundBuffer object_bg2_buffer_
uint8_t spriteset() const
void ClearWaterFillDirty()
Room & operator=(const Room &)=delete
std::array< uint8_t, 16 > blocks_
void SetTag1(TagKey tag1)
void SetBackgroundTileset(uint8_t tileset)
void SetStair3TargetLayer(uint8_t layer)
const std::vector< zelda3::Sprite > & GetSprites() const
std::array< chest, 16 > chest_list_
const std::vector< RoomObject > & GetTileObjects() const
DungeonState * GetDungeonState()
const LayerMergeType & layer_merging() const
absl::Status SaveSprites()
void MarkWaterFillDirty()
void SetLayerMerging(LayerMergeType merging)
void SetPitsTargetLayer(uint8_t layer)
bool GetWaterFillTile(int x, int y) const
void SetSpriteTileset(uint8_t tileset)
void SetStair1Target(uint8_t target)
void SetBg2(background2 bg2)
std::vector< chest_data > & GetChests()
void SetSpriteset(uint8_t ss)
void SetTileObjects(const std::vector< RoomObject > &objects)
void MarkCompositeDirty()
Mark composite bitmap as needing regeneration.
std::unique_ptr< DungeonState > dungeon_state_
void LoadAnimatedGraphics()
std::vector< uint8_t > EncodeSprites() const
void SetCollisionTile(int x, int y, uint8_t tile)
std::vector< chest_data > chests_in_room_
void SetBlockset(uint8_t bs)
LayerMergeType layer_merging_
bool water_fill_dirty() const
uint8_t staircase_plane(int index) const
void MarkCustomCollisionDirty()
const RoomObject & GetTileObject(size_t index) const
uint8_t cached_spriteset_
std::array< uint8_t, 0x10000 > current_gfx16_
std::vector< staircase > z3_staircases_
std::vector< PotItem > pot_items_
int water_fill_tile_count_
uint8_t background_tileset_
void SetStair3Target(uint8_t target)
void HandleSpecialObjects(short oid, uint8_t posX, uint8_t posY, int &nbr_of_staircase)
void SetStair4TargetLayer(uint8_t layer)
absl::Status AddObject(const RoomObject &object)
absl::StatusOr< size_t > FindObjectAt(int x, int y, int layer) const
void RemoveTileObject(size_t index)
void SetPalette(uint8_t pal)
uint8_t layout_id() const
bool has_custom_collision() const
const std::vector< PotItem > & GetPotItems() const
uint8_t water_fill_sram_bit_mask() const
void RemoveDoor(size_t index)
void SetStair2TargetLayer(uint8_t layer)
Room(const Room &)=delete
const auto & bg2_buffer() const
void RenderObjectsToBackground()
void SetGameData(GameData *data)
auto & object_bg1_buffer()
void SetLayer2Behavior(uint8_t behavior)
void SetWaterFillTile(int x, int y, bool filled)
void SetMessageId(uint16_t mid)
zelda3_bg2_effect
Background layer 2 effects.
absl::Status SaveAllChests(Rom *rom, absl::Span< const Room > rooms)
constexpr DoorDirection DoorDirectionFromRaw(uint8_t raw_dir)
Convert raw direction byte to DoorDirection enum.
const std::string RoomTag[65]
constexpr DoorDimensions GetDoorDimensions(DoorDirection dir)
Get door dimensions based on direction.
DoorType
Door types from ALTTP.
Room LoadRoomHeaderFromRom(Rom *rom, int room_id)
int FindMaxUsedSpriteAddress(Rom *rom)
absl::Status RelocateSpriteData(Rom *rom, int room_id, const std::vector< uint8_t > &encoded_bytes)
absl::Status SaveAllPotItems(Rom *rom, absl::Span< const Room > rooms)
RoomSize CalculateRoomSize(Rom *rom, int room_id)
@ Kill_Enemy_to_clear_level
@ Trigger_activated_Chest
@ SW_Kill_Enemy_for_Chest
@ SE_Kill_Enemy_for_Chest
@ Pull_lever_to_Bomb_Wall
@ Pull_Switch_to_bomb_Wall
@ SE_Kill_Enemy_to_Move_Block
@ NE_Kill_Enemy_for_Chest
@ Kill_to_open_Ganon_Door
@ Open_Chest_Activate_Holes_0
@ Switch_Open_Door_Toggle
@ Clear_Quadrant_for_Chest
@ NW_Kill_Enemy_for_Chest
@ Light_Torches_to_get_Chest
absl::Status SaveAllTorches(Rom *rom, absl::Span< const Room > rooms)
constexpr std::string_view GetDoorDirectionName(DoorDirection dir)
Get human-readable name for door direction.
absl::Status SaveAllPits(Rom *rom)
absl::Status SaveAllBlocks(Rom *rom)
Room LoadRoomFromRom(Rom *rom, int room_id)
constexpr DoorType DoorTypeFromRaw(uint8_t raw_type)
Convert raw type byte to DoorType enum.
constexpr std::array< std::string_view, 297 > kRoomNames
constexpr std::string_view GetDoorTypeName(DoorType type)
Get human-readable name for door type.
const std::string RoomEffect[8]
DoorDirection
Door direction on room walls.
absl::Status SaveAllCollision(Rom *rom, absl::Span< Room > rooms)
Room transition destination.
std::array< uint8_t, 64 *64 > tiles
Door dimensions in tiles (8x8 pixel tiles)
LayerMergeType(uint8_t id, std::string name, bool see, bool top, bool trans)
int64_t room_size_pointer
Represents a door in a dungeon room.
std::tuple< int, int, int, int > GetBounds() const
Get bounding rectangle (x, y, width, height in pixels)
std::string_view GetTypeName() const
Get human-readable type name.
uint8_t byte1
Original ROM byte 1 (position data)
DoorDimensions GetDimensions() const
Get door dimensions in tiles.
DoorType type
Door type (determines appearance/behavior)
static Door FromRomBytes(uint8_t b1, uint8_t b2)
std::pair< uint8_t, uint8_t > EncodeBytes() const
Encode door data for ROM storage.
DoorDirection direction
Which wall the door is on.
uint8_t position
Encoded position (5-bit, 0-31)
std::string_view GetDirectionName() const
Get human-readable direction name.
std::pair< int, int > GetPixelCoords() const
Get pixel coordinates for this door.
uint8_t byte2
Original ROM byte 2 (type + direction)
std::pair< int, int > GetTileCoords() const
Get tile coordinates for this door.
std::array< uint8_t, 64 *64 > tiles
ROM data pointers for different game versions.
Public YAZE API umbrella header.