diff --git a/src/app/editor/editor.h b/src/app/editor/editor.h index 8eebbb6c..81e87f7d 100644 --- a/src/app/editor/editor.h +++ b/src/app/editor/editor.h @@ -78,6 +78,8 @@ class Editor { virtual absl::Status Clear() { return absl::OkStatus(); } + virtual void CleanupUnusedTextures(uint64_t current_time, uint64_t timeout) { } + EditorType type() const { return type_; } void set_context(EditorContext* context) { context_ = context; } diff --git a/src/app/editor/editor_manager.cc b/src/app/editor/editor_manager.cc index 49a8aa23..ed01666a 100644 --- a/src/app/editor/editor_manager.cc +++ b/src/app/editor/editor_manager.cc @@ -300,6 +300,15 @@ absl::Status EditorManager::Update() { ImGui::End(); } } + + static uint64_t last_cleanup_time = 0; + uint64_t current_time = SDL_GetTicks64(); + + // Clean up unused textures every 5 seconds + if (current_time - last_cleanup_time > 5000) { + current_editor_set_->CleanupUnusedTextures(current_time, 5000); + last_cleanup_time = current_time; + } } if (show_homepage_) { @@ -481,6 +490,7 @@ absl::Status EditorManager::LoadAssets() { return absl::FailedPreconditionError("No ROM or editor set loaded"); } current_editor_set_->overworld_editor_.Initialize(); + current_editor_set_->message_editor_.Initialize(); auto &sheet_manager = GraphicsSheetManager::GetInstance(); ASSIGN_OR_RETURN(*sheet_manager.mutable_gfx_sheets(), diff --git a/src/app/editor/editor_manager.h b/src/app/editor/editor_manager.h index 3ca3304b..f746b600 100644 --- a/src/app/editor/editor_manager.h +++ b/src/app/editor/editor_manager.h @@ -51,17 +51,17 @@ class EditorManager { context_.popup_manager = popup_manager_.get(); } - void Initialize(const std::string &filename = ""); + void Initialize(const std::string& filename = ""); absl::Status Update(); void DrawMenuBar(); - auto emulator() -> emu::Emulator & { return emulator_; } + auto emulator() -> emu::Emulator& { return emulator_; } auto quit() const { return quit_; } auto version() const { return version_; } - absl::Status SetCurrentRom(Rom *rom); - auto GetRoms() -> std::vector> & { return roms_; } - auto GetCurrentRom() -> Rom * { return current_rom_; } + absl::Status SetCurrentRom(Rom* rom); + auto GetRoms() -> std::vector>& { return roms_; } + auto GetCurrentRom() -> Rom* { return current_rom_; } auto GetCurrentEditorSet() -> EditorSet* { return current_editor_set_; } private: @@ -71,7 +71,7 @@ class EditorManager { absl::Status LoadRom(); absl::Status LoadAssets(); absl::Status SaveRom(); - absl::Status OpenRomOrProject(const std::string &filename); + absl::Status OpenRomOrProject(const std::string& filename); absl::Status OpenProject(); absl::Status SaveProject(); @@ -110,38 +110,46 @@ class EditorManager { * @brief Contains a complete set of editors for a single ROM instance */ class EditorSet { -public: - explicit EditorSet(Rom* rom) - : assembly_editor_(rom), - dungeon_editor_(rom), - graphics_editor_(rom), - music_editor_(rom), - overworld_editor_(*rom), - palette_editor_(rom), - screen_editor_(rom), - sprite_editor_(rom), - settings_editor_(rom), - message_editor_(rom), - memory_editor_(rom) { - active_editors_ = {&overworld_editor_, &dungeon_editor_, &graphics_editor_, - &palette_editor_, &sprite_editor_, &message_editor_, - &music_editor_, &screen_editor_, &settings_editor_, - &assembly_editor_}; - } + public: + explicit EditorSet(Rom* rom = nullptr) + : assembly_editor_(rom), + dungeon_editor_(rom), + graphics_editor_(rom), + music_editor_(rom), + overworld_editor_(rom), + palette_editor_(rom), + screen_editor_(rom), + sprite_editor_(rom), + settings_editor_(rom), + message_editor_(rom), + memory_editor_(rom) { + active_editors_ = {&overworld_editor_, &dungeon_editor_, &graphics_editor_, + &palette_editor_, &sprite_editor_, &message_editor_, + &music_editor_, &screen_editor_, &settings_editor_, + &assembly_editor_}; + } - AssemblyEditor assembly_editor_; - DungeonEditor dungeon_editor_; - GraphicsEditor graphics_editor_; - MusicEditor music_editor_; - OverworldEditor overworld_editor_; - PaletteEditor palette_editor_; - ScreenEditor screen_editor_; - SpriteEditor sprite_editor_; - SettingsEditor settings_editor_; - MessageEditor message_editor_; - MemoryEditorWithDiffChecker memory_editor_; - - std::vector active_editors_; + AssemblyEditor assembly_editor_; + DungeonEditor dungeon_editor_; + GraphicsEditor graphics_editor_; + MusicEditor music_editor_; + OverworldEditor overworld_editor_; + PaletteEditor palette_editor_; + ScreenEditor screen_editor_; + SpriteEditor sprite_editor_; + SettingsEditor settings_editor_; + MessageEditor message_editor_; + MemoryEditorWithDiffChecker memory_editor_; + + std::vector active_editors_; + + void CleanupUnusedTextures(uint64_t current_time, uint64_t timeout) { + if (active_editors_.size() > 0) { + for (auto editor : active_editors_) { + editor->CleanupUnusedTextures(current_time, timeout); + } + } + } }; } // namespace editor diff --git a/src/app/editor/overworld/overworld_editor.cc b/src/app/editor/overworld/overworld_editor.cc index 1cdf330d..b47fa4bb 100644 --- a/src/app/editor/overworld/overworld_editor.cc +++ b/src/app/editor/overworld/overworld_editor.cc @@ -32,30 +32,7 @@ namespace yaze { namespace editor { using core::Renderer; -using ImGui::BeginChild; -using ImGui::BeginTabBar; -using ImGui::BeginTabItem; -using ImGui::BeginTable; -using ImGui::BeginTooltip; -using ImGui::Button; -using ImGui::Checkbox; -using ImGui::EndChild; -using ImGui::EndTabBar; -using ImGui::EndTabItem; -using ImGui::EndTable; -using ImGui::EndTooltip; -using ImGui::IsItemHovered; -using ImGui::NewLine; -using ImGui::PopStyleColor; -using ImGui::PushStyleColor; -using ImGui::SameLine; -using ImGui::Selectable; -using ImGui::Separator; -using ImGui::TableHeadersRow; -using ImGui::TableNextColumn; -using ImGui::TableNextRow; -using ImGui::TableSetupColumn; -using ImGui::Text; +using namespace ImGui; constexpr int kTile16Size = 0x10; @@ -70,19 +47,19 @@ void OverworldEditor::Initialize() { gui::zeml::Bind(&*layout_node_.GetNode("OverworldTileSelector"), [this]() { status_ = DrawTileSelector(); }); gui::zeml::Bind(&*layout_node_.GetNode("OwUsageStats"), [this]() { - if (rom_.is_loaded()) { + if (rom_->is_loaded()) { status_ = UpdateUsageStats(); } }); gui::zeml::Bind(&*layout_node_.GetNode("owToolset"), [this]() { DrawToolset(); }); gui::zeml::Bind(&*layout_node_.GetNode("OwTile16Editor"), [this]() { - if (rom_.is_loaded()) { + if (rom_->is_loaded()) { status_ = tile16_editor_.Update(); } }); gui::zeml::Bind(&*layout_node_.GetNode("OwGfxGroupEditor"), [this]() { - if (rom_.is_loaded()) { + if (rom_->is_loaded()) { status_ = gfx_group_editor_.Update(); } }); @@ -1072,7 +1049,7 @@ absl::Status OverworldEditor::LoadGraphics() { map_blockset_loaded_ = true; // Copy the tile16 data into individual tiles. - auto tile16_data = overworld_.tile16_blockset_data(); + auto tile16_blockset_data = overworld_.tile16_blockset_data(); util::logf("Loading overworld tile16 graphics."); // Loop through the tiles and copy their pixel data into separate vectors @@ -1084,9 +1061,9 @@ absl::Status OverworldEditor::LoadGraphics() { for (int ty = 0; ty < kTile16Size; ty++) { for (int tx = 0; tx < kTile16Size; tx++) { int position = tx + (ty * kTile16Size); - uint8_t value = - tile16_data[(i % 8 * kTile16Size) + (i / 8 * kTile16Size * 0x80) + - (ty * 0x80) + tx]; + uint8_t value = tile16_blockset_data[(i % 8 * kTile16Size) + + (i / 8 * kTile16Size * 0x80) + + (ty * 0x80) + tx]; tile16_individual_[i].mutable_data()[position] = value; } } @@ -1400,7 +1377,7 @@ absl::Status OverworldEditor::UpdateUsageStats() { if (BeginChild("UnusedSpritesetScroll", ImVec2(0, 0), true, ImGuiWindowFlags_HorizontalScrollbar)) { for (int i = 0; i < 0x81; i++) { - auto entrance_name = rom_.resource_label()->CreateOrGetLabel( + auto entrance_name = rom_->resource_label()->CreateOrGetLabel( "Dungeon Entrance Names", util::HexByte(i), zelda3::kEntranceNames[i].data()); std::string str = absl::StrFormat("%#x - %s", i, entrance_name); @@ -1516,5 +1493,34 @@ void OverworldEditor::DrawDebugWindow() { } } +absl::Status OverworldEditor::Clear() { + overworld_.Destroy(); + current_graphics_set_.clear(); + for (auto &bmp : tile16_individual_) { + bmp.Clear(); + } + for (auto &bmp : maps_bmp_) { + bmp.Clear(); + } + for (auto &bmp : sprite_previews_) { + bmp.Clear(); + } + tile16_blockset_bmp_.Clear(); + current_gfx_bmp_.Clear(); + all_gfx_loaded_ = false; + map_blockset_loaded_ = false; + return absl::OkStatus(); +} + +void OverworldEditor::CleanupUnusedTextures(uint64_t current_time, + uint64_t timeout) { + for (auto &bmp : tile16_individual_) { + bmp.CleanupUnusedTexture(current_time, timeout); + } + for (auto &bmp : maps_bmp_) { + bmp.CleanupUnusedTexture(current_time, timeout); + } +} + } // namespace editor } // namespace yaze diff --git a/src/app/editor/overworld/overworld_editor.h b/src/app/editor/overworld/overworld_editor.h index 5146f707..a73fa2c7 100644 --- a/src/app/editor/overworld/overworld_editor.h +++ b/src/app/editor/overworld/overworld_editor.h @@ -74,7 +74,7 @@ constexpr absl::string_view kOWMapTable = "#MapSettingsTable"; */ class OverworldEditor : public Editor, public gfx::GfxContext { public: - OverworldEditor(Rom& rom) : rom_(rom) { type_ = EditorType::kOverworld; } + explicit OverworldEditor(Rom* rom) : rom_(rom) { type_ = EditorType::kOverworld; } void Initialize() override; absl::Status Load() override; @@ -215,7 +215,7 @@ class OverworldEditor : public Editor, public gfx::GfxContext { std::vector> tile8_individual_data_; std::vector tile8_individual_; - Rom& rom_; + Rom* rom_; Tile16Editor tile16_editor_{tile16_individual_}; GfxGroupEditor gfx_group_editor_; diff --git a/src/app/zelda3/overworld/overworld.cc b/src/app/zelda3/overworld/overworld.cc index ee6ce10f..39ed48d1 100644 --- a/src/app/zelda3/overworld/overworld.cc +++ b/src/app/zelda3/overworld/overworld.cc @@ -17,8 +17,8 @@ namespace yaze { namespace zelda3 { -absl::Status Overworld::Load(Rom &rom) { - if (rom.size() == 0) { +absl::Status Overworld::Load(Rom *rom) { + if (rom->size() == 0) { return absl::InvalidArgumentError("ROM file not loaded"); } rom_ = rom; @@ -97,10 +97,10 @@ void Overworld::FetchLargeMaps() { absl::StatusOr Overworld::GetTile16ForTile32( int index, int quadrant, int dimension, const uint32_t *map32address) { - ASSIGN_OR_RETURN(auto arg1, - rom_.ReadByte(map32address[dimension] + quadrant + (index))); - ASSIGN_OR_RETURN(auto arg2, rom_.ReadWord(map32address[dimension] + (index) + - (quadrant <= 1 ? 4 : 5))); + ASSIGN_OR_RETURN( + auto arg1, rom()->ReadByte(map32address[dimension] + quadrant + (index))); + ASSIGN_OR_RETURN(auto arg2, rom()->ReadWord(map32address[dimension] + (index) + + (quadrant <= 1 ? 4 : 5))); return (uint16_t)(arg1 + (((arg2 >> (quadrant % 2 == 0 ? 4 : 0)) & 0x0F) * 256)); } @@ -108,13 +108,13 @@ absl::StatusOr Overworld::GetTile16ForTile32( absl::Status Overworld::AssembleMap32Tiles() { constexpr int kMap32TilesLength = 0x33F0; int num_tile32 = kMap32TilesLength; - uint32_t map32address[4] = {rom_.version_constants().kMap32TileTL, - rom_.version_constants().kMap32TileTR, - rom_.version_constants().kMap32TileBL, - rom_.version_constants().kMap32TileBR}; + uint32_t map32address[4] = {rom()->version_constants().kMap32TileTL, + rom()->version_constants().kMap32TileTR, + rom()->version_constants().kMap32TileBL, + rom()->version_constants().kMap32TileBR}; if (rom()->data()[kMap32ExpandedFlagPos] != 0x04 && core::FeatureFlags::get().overworld.kLoadCustomOverworld) { - map32address[0] = rom_.version_constants().kMap32TileTL; + map32address[0] = rom()->version_constants().kMap32TileTL; map32address[1] = kMap32TileTRExpanded; map32address[2] = kMap32TileBLExpanded; map32address[3] = kMap32TileBRExpanded; @@ -338,10 +338,8 @@ absl::Status Overworld::LoadEntrances() { absl::Status Overworld::LoadHoles() { constexpr int kNumHoles = 0x13; for (int i = 0; i < kNumHoles; i++) { - ASSIGN_OR_RETURN(auto map_id, - rom()->ReadWord(kOverworldHoleArea + (i * 2))); - ASSIGN_OR_RETURN(auto map_pos, - rom()->ReadWord(kOverworldHolePos + (i * 2))); + ASSIGN_OR_RETURN(auto map_id, rom()->ReadWord(kOverworldHoleArea + (i * 2))); + ASSIGN_OR_RETURN(auto map_pos, rom()->ReadWord(kOverworldHolePos + (i * 2))); ASSIGN_OR_RETURN(auto entrance_id, rom()->ReadByte(kOverworldHoleEntrance + i)); int p = (map_pos + 0x400) >> 1; @@ -412,8 +410,7 @@ absl::Status Overworld::LoadItems() { rom()->ReadLong(zelda3::kOverworldItemsAddress)); uint32_t pointer_pc = SnesToPc(pointer); // 1BC2F9 -> 0DC2F9 for (int i = 0; i < 128; i++) { - ASSIGN_OR_RETURN(uint16_t word_address, - rom()->ReadWord(pointer_pc + i * 2)); + ASSIGN_OR_RETURN(uint16_t word_address, rom()->ReadWord(pointer_pc + i * 2)); uint32_t addr = (pointer & 0xFF0000) | word_address; // 1B F9 3C addr = SnesToPc(addr); @@ -515,7 +512,7 @@ absl::Status Overworld::LoadSpritesFromMap(int sprites_per_gamestate_ptr, return absl::OkStatus(); } -absl::Status Overworld::Save(Rom &rom) { +absl::Status Overworld::Save(Rom *rom) { rom_ = rom; if (expanded_tile16_) RETURN_IF_ERROR(SaveMap16Expanded()) RETURN_IF_ERROR(SaveMap16Tiles()) @@ -676,8 +673,8 @@ absl::Status Overworld::SaveLargeMaps() { int parent_x_pos = overworld_maps_[i].parent() % 8; // Always write the map parent since it should not matter - RETURN_IF_ERROR(rom()->WriteByte(kOverworldMapParentId + i, - overworld_maps_[i].parent())) + RETURN_IF_ERROR( + rom()->WriteByte(kOverworldMapParentId + i, overworld_maps_[i].parent())) if (std::find(checked_map.begin(), checked_map.end(), i) != checked_map.end()) { @@ -700,72 +697,72 @@ absl::Status Overworld::SaveLargeMaps() { RETURN_IF_ERROR( rom()->WriteByte(kOverworldScreenSize + i + offset + 64, 0x00)); // Check 4 - RETURN_IF_ERROR(rom()->WriteByte( - kOverworldScreenSizeForLoading + i + offset, 0x04)); + RETURN_IF_ERROR( + rom()->WriteByte(kOverworldScreenSizeForLoading + i + offset, 0x04)); RETURN_IF_ERROR(rom()->WriteByte( kOverworldScreenSizeForLoading + i + offset + kDarkWorldMapIdStart, 0x04)); RETURN_IF_ERROR(rom()->WriteByte(kOverworldScreenSizeForLoading + i + - offset + kSpecialWorldMapIdStart, - 0x04)); + offset + kSpecialWorldMapIdStart, + 0x04)); } // Check 5 and 6 RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetNorth + (i * 2), - (uint16_t)((parent_y_pos * 0x200) - 0xE0))); + (uint16_t)((parent_y_pos * 0x200) - 0xE0))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetWest + (i * 2), - (uint16_t)((parent_x_pos * 0x200) - 0x100))); + (uint16_t)((parent_x_pos * 0x200) - 0x100))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetNorth + (i * 2) + 2, - (uint16_t)((parent_y_pos * 0x200) - 0xE0))); + (uint16_t)((parent_y_pos * 0x200) - 0xE0))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetWest + (i * 2) + 2, - (uint16_t)((parent_x_pos * 0x200) - 0x100))); + (uint16_t)((parent_x_pos * 0x200) - 0x100))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetNorth + (i * 2) + 16, - (uint16_t)((parent_y_pos * 0x200) - 0xE0))); + (uint16_t)((parent_y_pos * 0x200) - 0xE0))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetWest + (i * 2) + 16, - (uint16_t)((parent_x_pos * 0x200) - 0x100))); + (uint16_t)((parent_x_pos * 0x200) - 0x100))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetNorth + (i * 2) + 18, - (uint16_t)((parent_y_pos * 0x200) - 0xE0))); + (uint16_t)((parent_y_pos * 0x200) - 0xE0))); RETURN_IF_ERROR( rom()->WriteShort(kTransitionTargetWest + (i * 2) + 18, - (uint16_t)((parent_x_pos * 0x200) - 0x100))); + (uint16_t)((parent_x_pos * 0x200) - 0x100))); // Check 7 and 8 RETURN_IF_ERROR(rom()->WriteShort(kOverworldTransitionPositionX + (i * 2), - (parent_x_pos * 0x200))); + (parent_x_pos * 0x200))); RETURN_IF_ERROR(rom()->WriteShort(kOverworldTransitionPositionY + (i * 2), - (parent_y_pos * 0x200))); + (parent_y_pos * 0x200))); RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionX + (i * 2) + 02, - (parent_x_pos * 0x200))); + (parent_x_pos * 0x200))); RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionY + (i * 2) + 02, - (parent_y_pos * 0x200))); + (parent_y_pos * 0x200))); // problematic RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionX + (i * 2) + 16, - (parent_x_pos * 0x200))); + (parent_x_pos * 0x200))); RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionY + (i * 2) + 16, - (parent_y_pos * 0x200))); + (parent_y_pos * 0x200))); RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionX + (i * 2) + 18, - (parent_x_pos * 0x200))); + (parent_x_pos * 0x200))); RETURN_IF_ERROR( rom()->WriteShort(kOverworldTransitionPositionY + (i * 2) + 18, - (parent_y_pos * 0x200))); + (parent_y_pos * 0x200))); // Check 9 RETURN_IF_ERROR(rom()->WriteShort( @@ -958,14 +955,14 @@ absl::Status Overworld::SaveLargeMaps() { } RETURN_IF_ERROR(rom()->WriteShort(kTransitionTargetNorth + (i * 2), - (uint16_t)((y_pos * 0x200) - 0xE0))); + (uint16_t)((y_pos * 0x200) - 0xE0))); RETURN_IF_ERROR(rom()->WriteShort(kTransitionTargetWest + (i * 2), - (uint16_t)((x_pos * 0x200) - 0x100))); + (uint16_t)((x_pos * 0x200) - 0x100))); RETURN_IF_ERROR(rom()->WriteShort(kOverworldTransitionPositionX + (i * 2), - (x_pos * 0x200))); + (x_pos * 0x200))); RETURN_IF_ERROR(rom()->WriteShort(kOverworldTransitionPositionY + (i * 2), - (y_pos * 0x200))); + (y_pos * 0x200))); checked_map.emplace_back(i); } @@ -1352,17 +1349,13 @@ absl::Status Overworld::SaveMap16Tiles() { int tpos = kMap16Tiles; // 3760 for (int i = 0; i < NumberOfMap16; i += 1) { - RETURN_IF_ERROR( - rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile0_))) + RETURN_IF_ERROR(rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile0_))) tpos += 2; - RETURN_IF_ERROR( - rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile1_))) + RETURN_IF_ERROR(rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile1_))) tpos += 2; - RETURN_IF_ERROR( - rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile2_))) + RETURN_IF_ERROR(rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile2_))) tpos += 2; - RETURN_IF_ERROR( - rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile3_))) + RETURN_IF_ERROR(rom()->WriteShort(tpos, TileInfoToShort(tiles16_[i].tile3_))) tpos += 2; } return absl::OkStatus(); @@ -1383,11 +1376,11 @@ absl::Status Overworld::SaveEntrances() { for (int i = 0; i < kNumOverworldEntrances; i++) { RETURN_IF_ERROR(rom()->WriteShort(kOverworldEntranceMap + (i * 2), - all_entrances_[i].map_id_)) + all_entrances_[i].map_id_)) RETURN_IF_ERROR(rom()->WriteShort(kOverworldEntrancePos + (i * 2), - all_entrances_[i].map_pos_)) + all_entrances_[i].map_pos_)) RETURN_IF_ERROR(rom()->WriteByte(kOverworldEntranceEntranceId + i, - all_entrances_[i].entrance_id_)) + all_entrances_[i].entrance_id_)) } for (int i = 0; i < kNumOverworldHoles; i++) { @@ -1395,8 +1388,8 @@ absl::Status Overworld::SaveEntrances() { rom()->WriteShort(kOverworldHoleArea + (i * 2), all_holes_[i].map_id_)) RETURN_IF_ERROR( rom()->WriteShort(kOverworldHolePos + (i * 2), all_holes_[i].map_pos_)) - RETURN_IF_ERROR(rom()->WriteByte(kOverworldHoleEntrance + i, - all_holes_[i].entrance_id_)) + RETURN_IF_ERROR( + rom()->WriteByte(kOverworldHoleEntrance + i, all_holes_[i].entrance_id_)) } return absl::OkStatus(); @@ -1427,9 +1420,9 @@ absl::Status Overworld::SaveExits() { RETURN_IF_ERROR( rom()->WriteByte(OWExitUnk2 + i, all_exits_[i].scroll_mod_x_)); RETURN_IF_ERROR(rom()->WriteShort(OWExitDoorType1 + (i * 2), - all_exits_[i].door_type_1_)); + all_exits_[i].door_type_1_)); RETURN_IF_ERROR(rom()->WriteShort(OWExitDoorType2 + (i * 2), - all_exits_[i].door_type_2_)); + all_exits_[i].door_type_2_)); } return absl::OkStatus(); @@ -1545,49 +1538,49 @@ absl::Status Overworld::SaveItems() { absl::Status Overworld::SaveMapProperties() { util::logf("Saving Map Properties"); for (int i = 0; i < kDarkWorldMapIdStart; i++) { - RETURN_IF_ERROR(rom()->WriteByte(kAreaGfxIdPtr + i, - overworld_maps_[i].area_graphics())); + RETURN_IF_ERROR( + rom()->WriteByte(kAreaGfxIdPtr + i, overworld_maps_[i].area_graphics())); RETURN_IF_ERROR(rom()->WriteByte(kOverworldMapPaletteIds + i, - overworld_maps_[i].area_palette())); + overworld_maps_[i].area_palette())); RETURN_IF_ERROR(rom()->WriteByte(kOverworldSpriteset + i, - overworld_maps_[i].sprite_graphics(0))); + overworld_maps_[i].sprite_graphics(0))); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpriteset + kDarkWorldMapIdStart + i, - overworld_maps_[i].sprite_graphics(1))); + overworld_maps_[i].sprite_graphics(1))); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpriteset + kSpecialWorldMapIdStart + i, - overworld_maps_[i].sprite_graphics(2))); + overworld_maps_[i].sprite_graphics(2))); RETURN_IF_ERROR(rom()->WriteByte(kOverworldSpritePaletteIds + i, - overworld_maps_[i].sprite_palette(0))); + overworld_maps_[i].sprite_palette(0))); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpritePaletteIds + kDarkWorldMapIdStart + i, - overworld_maps_[i].sprite_palette(1))); + overworld_maps_[i].sprite_palette(1))); RETURN_IF_ERROR(rom()->WriteByte( kOverworldSpritePaletteIds + kSpecialWorldMapIdStart + i, overworld_maps_[i].sprite_palette(2))); } for (int i = kDarkWorldMapIdStart; i < kSpecialWorldMapIdStart; i++) { - RETURN_IF_ERROR(rom()->WriteByte(kAreaGfxIdPtr + i, - overworld_maps_[i].area_graphics())); + RETURN_IF_ERROR( + rom()->WriteByte(kAreaGfxIdPtr + i, overworld_maps_[i].area_graphics())); RETURN_IF_ERROR(rom()->WriteByte(kOverworldSpriteset + i, - overworld_maps_[i].sprite_graphics(0))); + overworld_maps_[i].sprite_graphics(0))); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpriteset + kDarkWorldMapIdStart + i, - overworld_maps_[i].sprite_graphics(1))); + overworld_maps_[i].sprite_graphics(1))); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpriteset + kSpecialWorldMapIdStart + i, - overworld_maps_[i].sprite_graphics(2))); + overworld_maps_[i].sprite_graphics(2))); RETURN_IF_ERROR(rom()->WriteByte(kOverworldMapPaletteIds + i, - overworld_maps_[i].area_palette())); + overworld_maps_[i].area_palette())); RETURN_IF_ERROR( rom()->WriteByte(kOverworldSpritePaletteIds + kDarkWorldMapIdStart + i, - overworld_maps_[i].sprite_palette(0))); + overworld_maps_[i].sprite_palette(0))); RETURN_IF_ERROR(rom()->WriteByte( kOverworldSpritePaletteIds + kSpecialWorldMapIdStart + i, overworld_maps_[i].sprite_palette(1))); RETURN_IF_ERROR(rom()->WriteByte(kOverworldSpritePaletteIds + 192 + i, - overworld_maps_[i].sprite_palette(2))); + overworld_maps_[i].sprite_palette(2))); } return absl::OkStatus(); diff --git a/src/app/zelda3/overworld/overworld.h b/src/app/zelda3/overworld/overworld.h index d212d466..07beafeb 100644 --- a/src/app/zelda3/overworld/overworld.h +++ b/src/app/zelda3/overworld/overworld.h @@ -109,11 +109,11 @@ constexpr int kNumMapsPerWorld = 0x40; * This class is responsible for loading and saving the overworld data, * as well as creating the tilesets and tilemaps for the overworld. */ -class Overworld : public SharedRom { +class Overworld { public: - Overworld(Rom &rom) : rom_(rom) {} + Overworld(Rom *rom) : rom_(rom) {} - absl::Status Load(Rom &rom); + absl::Status Load(Rom *rom); absl::Status LoadOverworldMaps(); void LoadTileTypes(); absl::Status LoadEntrances(); @@ -125,7 +125,7 @@ class Overworld : public SharedRom { absl::Status LoadSpritesFromMap(int sprite_start, int sprite_count, int sprite_index); - absl::Status Save(Rom &rom); + absl::Status Save(Rom *rom); absl::Status SaveOverworldMaps(); absl::Status SaveLargeMaps(); absl::Status SaveEntrances(); @@ -140,6 +140,9 @@ class Overworld : public SharedRom { absl::Status SaveMapProperties(); + auto rom() const { return rom_; } + auto mutable_rom() { return rom_; } + void Destroy() { for (auto &map : overworld_maps_) { map.Destroy(); @@ -151,6 +154,9 @@ class Overworld : public SharedRom { for (auto &sprites : all_sprites_) { sprites.clear(); } + tiles16_.clear(); + tiles32_.clear(); + tiles32_unique_.clear(); is_loaded_ = false; } @@ -234,7 +240,7 @@ class Overworld : public SharedRom { int &ttpos); void DecompressAllMapTiles(); - Rom &rom_; + Rom *rom_; bool is_loaded_ = false; bool expanded_tile16_ = false; diff --git a/src/app/zelda3/overworld/overworld_entrance.h b/src/app/zelda3/overworld/overworld_entrance.h index 5956b56b..b99f113a 100644 --- a/src/app/zelda3/overworld/overworld_entrance.h +++ b/src/app/zelda3/overworld/overworld_entrance.h @@ -97,13 +97,14 @@ struct OverworldEntranceTileTypes { }; inline absl::StatusOr LoadEntranceTileTypes( - Rom &rom) { + Rom *rom) { OverworldEntranceTileTypes tiletypes; for (int i = 0; i < kNumEntranceTileTypes; i++) { - ASSIGN_OR_RETURN(auto value_low, rom.ReadWord(kEntranceTileTypePtrLow + i)); + ASSIGN_OR_RETURN(auto value_low, + rom->ReadWord(kEntranceTileTypePtrLow + i)); tiletypes.low[i] = value_low; ASSIGN_OR_RETURN(auto value_high, - rom.ReadWord(kEntranceTileTypePtrHigh + i)); + rom->ReadWord(kEntranceTileTypePtrHigh + i)); tiletypes.high[i] = value_high; } return tiletypes; diff --git a/src/app/zelda3/overworld/overworld_map.cc b/src/app/zelda3/overworld/overworld_map.cc index 0e26d7e7..0134f686 100644 --- a/src/app/zelda3/overworld/overworld_map.cc +++ b/src/app/zelda3/overworld/overworld_map.cc @@ -15,14 +15,14 @@ namespace yaze { namespace zelda3 { -OverworldMap::OverworldMap(int index, Rom &rom) +OverworldMap::OverworldMap(int index, Rom *rom) : index_(index), parent_(index), rom_(rom) { LoadAreaInfo(); if (core::FeatureFlags::get().overworld.kLoadCustomOverworld) { // If the custom overworld ASM has NOT already been applied, manually set // the vanilla values. - uint8_t asm_version = rom_[OverworldCustomASMHasBeenApplied]; + uint8_t asm_version = (*rom_)[OverworldCustomASMHasBeenApplied]; if (asm_version == 0x00) { LoadCustomOverworldData(); } else { @@ -40,15 +40,15 @@ absl::Status OverworldMap::BuildMap(int count, int game_state, int world, if (parent_ != index_ && !initialized_) { if (index_ >= kSpecialWorldMapIdStart && index_ <= 0x8A && index_ != 0x88) { - area_graphics_ = rom_[kOverworldSpecialGfxGroup + + area_graphics_ = (*rom_)[kOverworldSpecialGfxGroup + (parent_ - kSpecialWorldMapIdStart)]; - area_palette_ = rom_[kOverworldSpecialPalGroup + 1]; + area_palette_ = (*rom_)[kOverworldSpecialPalGroup + 1]; } else if (index_ == 0x88) { area_graphics_ = 0x51; area_palette_ = 0x00; } else { - area_graphics_ = rom_[kAreaGfxIdPtr + parent_]; - area_palette_ = rom_[kOverworldMapPaletteIds + parent_]; + area_graphics_ = (*rom_)[kAreaGfxIdPtr + parent_]; + area_palette_ = (*rom_)[kOverworldMapPaletteIds + parent_]; } initialized_ = true; @@ -67,14 +67,14 @@ absl::Status OverworldMap::BuildMap(int count, int game_state, int world, void OverworldMap::LoadAreaInfo() { if (index_ != kSpecialWorldMapIdStart) { if (index_ <= 128) - large_map_ = (rom_[kOverworldMapSize + (index_ & 0x3F)] != 0); + large_map_ = ((*rom_)[kOverworldMapSize + (index_ & 0x3F)] != 0); else { large_map_ = index_ == 129 || index_ == 130 || index_ == 137 || index_ == 138; } } - auto message_id = rom_.ReadWord(kOverworldMessageIds + (parent_ * 2)); + auto message_id = rom_->ReadWord(kOverworldMessageIds + (parent_ * 2)); if (message_id.ok()) { message_id_ = message_id.value(); } else { @@ -83,43 +83,43 @@ void OverworldMap::LoadAreaInfo() { } if (index_ < kDarkWorldMapIdStart) { - area_graphics_ = rom_[kAreaGfxIdPtr + parent_]; - area_palette_ = rom_[kOverworldMapPaletteIds + parent_]; + area_graphics_ = (*rom_)[kAreaGfxIdPtr + parent_]; + area_palette_ = (*rom_)[kOverworldMapPaletteIds + parent_]; - area_music_[0] = rom_[kOverworldMusicBeginning + parent_]; - area_music_[1] = rom_[kOverworldMusicZelda + parent_]; - area_music_[2] = rom_[kOverworldMusicMasterSword + parent_]; - area_music_[3] = rom_[kOverworldMusicAgahnim + parent_]; + area_music_[0] = (*rom_)[kOverworldMusicBeginning + parent_]; + area_music_[1] = (*rom_)[kOverworldMusicZelda + parent_]; + area_music_[2] = (*rom_)[kOverworldMusicMasterSword + parent_]; + area_music_[3] = (*rom_)[kOverworldMusicAgahnim + parent_]; - sprite_graphics_[0] = rom_[kOverworldSpriteset + parent_]; + sprite_graphics_[0] = (*rom_)[kOverworldSpriteset + parent_]; sprite_graphics_[1] = - rom_[kOverworldSpriteset + parent_ + kDarkWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kDarkWorldMapIdStart]; sprite_graphics_[2] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; - sprite_palette_[0] = rom_[kOverworldSpritePaletteIds + parent_]; + sprite_palette_[0] = (*rom_)[kOverworldSpritePaletteIds + parent_]; sprite_palette_[1] = - rom_[kOverworldSpritePaletteIds + parent_ + kDarkWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kDarkWorldMapIdStart]; sprite_palette_[2] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; } else if (index_ < kSpecialWorldMapIdStart) { - area_graphics_ = rom_[kAreaGfxIdPtr + parent_]; - area_palette_ = rom_[kOverworldMapPaletteIds + parent_]; - area_music_[0] = rom_[kOverworldMusicDarkWorld + (parent_ - 64)]; + area_graphics_ = (*rom_)[kAreaGfxIdPtr + parent_]; + area_palette_ = (*rom_)[kOverworldMapPaletteIds + parent_]; + area_music_[0] = (*rom_)[kOverworldMusicDarkWorld + (parent_ - 64)]; sprite_graphics_[0] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_graphics_[1] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_graphics_[2] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[0] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[1] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[2] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; } else { if (index_ == 0x94) { parent_ = 0x80; @@ -145,35 +145,35 @@ void OverworldMap::LoadAreaInfo() { } area_palette_ = - rom_[kOverworldSpecialPalGroup + parent_ - kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpecialPalGroup + parent_ - kSpecialWorldMapIdStart]; if ((index_ >= kSpecialWorldMapIdStart && index_ <= 0x8A && index_ != 0x88) || index_ == 0x94) { area_graphics_ = - rom_[kOverworldSpecialGfxGroup + (parent_ - kSpecialWorldMapIdStart)]; - area_palette_ = rom_[kOverworldSpecialPalGroup + 1]; + (*rom_)[kOverworldSpecialGfxGroup + (parent_ - kSpecialWorldMapIdStart)]; + area_palette_ = (*rom_)[kOverworldSpecialPalGroup + 1]; } else if (index_ == 0x88) { area_graphics_ = 0x51; area_palette_ = 0x00; } else { // pyramid bg use 0x5B map - area_graphics_ = rom_[kAreaGfxIdPtr + parent_]; - area_palette_ = rom_[kOverworldMapPaletteIds + parent_]; + area_graphics_ = (*rom_)[kAreaGfxIdPtr + parent_]; + area_palette_ = (*rom_)[kOverworldMapPaletteIds + parent_]; } sprite_graphics_[0] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_graphics_[1] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_graphics_[2] = - rom_[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpriteset + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[0] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[1] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; sprite_palette_[2] = - rom_[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; + (*rom_)[kOverworldSpritePaletteIds + parent_ + kSpecialWorldMapIdStart]; } } @@ -213,38 +213,39 @@ void OverworldMap::LoadCustomOverworldData() { } const auto overworld_gfx_groups2 = - rom_.version_constants().kOverworldGfxGroups2; + rom_->version_constants().kOverworldGfxGroups2; // Main Blocksets for (int i = 0; i < 8; i++) { custom_gfx_ids_[i] = - (uint8_t)rom_[overworld_gfx_groups2 + (index_world * 8) + i]; + (uint8_t)(*rom_)[overworld_gfx_groups2 + (index_world * 8) + i]; } - const auto overworldgfxGroups = rom_.version_constants().kOverworldGfxGroups1; + const auto overworldgfxGroups = + rom_->version_constants().kOverworldGfxGroups1; // Replace the variable tiles with the variable ones. - uint8_t temp = rom_[overworldgfxGroups + (area_graphics_ * 4)]; + uint8_t temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4)]; if (temp != 0) { custom_gfx_ids_[3] = temp; } else { custom_gfx_ids_[3] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 1]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 1]; if (temp != 0) { custom_gfx_ids_[4] = temp; } else { custom_gfx_ids_[4] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 2]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 2]; if (temp != 0) { custom_gfx_ids_[5] = temp; } else { custom_gfx_ids_[5] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 3]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 3]; if (temp != 0) { custom_gfx_ids_[6] = temp; } else { @@ -290,18 +291,18 @@ void OverworldMap::LoadCustomOverworldData() { } void OverworldMap::SetupCustomTileset(uint8_t asm_version) { - area_palette_ = rom_[OverworldCustomMainPaletteArray + index_]; - mosaic_ = rom_[OverworldCustomMosaicArray + index_] != 0x00; + area_palette_ = (*rom_)[OverworldCustomMainPaletteArray + index_]; + mosaic_ = (*rom_)[OverworldCustomMosaicArray + index_] != 0x00; // This is just to load the GFX groups for ROMs that have an older version // of the Overworld ASM already applied. if (asm_version >= 0x01 && asm_version != 0xFF) { for (int i = 0; i < 8; i++) { custom_gfx_ids_[i] = - rom_[OverworldCustomTileGFXGroupArray + (index_ * 8) + i]; + (*rom_)[OverworldCustomTileGFXGroupArray + (index_ * 8) + i]; } - animated_gfx_ = rom_[OverworldCustomAnimatedGFXArray + index_]; + animated_gfx_ = (*rom_)[OverworldCustomAnimatedGFXArray + index_]; } else { int index_world = 0x20; @@ -317,38 +318,38 @@ void OverworldMap::SetupCustomTileset(uint8_t asm_version) { // Main Blocksets for (int i = 0; i < 8; i++) { custom_gfx_ids_[i] = - (uint8_t)rom_[rom_.version_constants().kOverworldGfxGroups2 + + (uint8_t)(*rom_)[rom_->version_constants().kOverworldGfxGroups2 + (index_world * 8) + i]; } const auto overworldgfxGroups = - rom_.version_constants().kOverworldGfxGroups1; + rom_->version_constants().kOverworldGfxGroups1; // Replace the variable tiles with the variable ones. // If the variable is 00 set it to 0xFF which is the new "don't load // anything" value. - uint8_t temp = rom_[overworldgfxGroups + (area_graphics_ * 4)]; + uint8_t temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4)]; if (temp != 0x00) { custom_gfx_ids_[3] = temp; } else { custom_gfx_ids_[3] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 1]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 1]; if (temp != 0x00) { custom_gfx_ids_[4] = temp; } else { custom_gfx_ids_[4] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 2]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 2]; if (temp != 0x00) { custom_gfx_ids_[5] = temp; } else { custom_gfx_ids_[5] = 0xFF; } - temp = rom_[overworldgfxGroups + (area_graphics_ * 4) + 3]; + temp = (*rom_)[overworldgfxGroups + (area_graphics_ * 4) + 3]; if (temp != 0x00) { custom_gfx_ids_[6] = temp; } else { @@ -365,7 +366,7 @@ void OverworldMap::SetupCustomTileset(uint8_t asm_version) { } subscreen_overlay_ = - rom_[OverworldCustomSubscreenOverlayArray + (index_ * 2)]; + (*rom_)[OverworldCustomSubscreenOverlayArray + (index_ * 2)]; } void OverworldMap::LoadMainBlocksetId() { @@ -388,7 +389,7 @@ void OverworldMap::LoadSpritesBlocksets() { for (int i = 0; i < 4; i++) { static_graphics_[12 + i] = - (rom_[rom_.version_constants().kSpriteBlocksetPointer + + ((*rom_)[rom_->version_constants().kSpriteBlocksetPointer + (sprite_graphics_[game_state_] * 4) + i] + static_graphics_base); } @@ -396,7 +397,7 @@ void OverworldMap::LoadSpritesBlocksets() { void OverworldMap::LoadMainBlocksets() { for (int i = 0; i < 8; i++) { - static_graphics_[i] = rom_[rom_.version_constants().kOverworldGfxGroups2 + + static_graphics_[i] = (*rom_)[rom_->version_constants().kOverworldGfxGroups2 + (main_gfx_id_ * 8) + i]; } } @@ -426,7 +427,7 @@ void OverworldMap::DrawAnimatedTiles() { void OverworldMap::LoadAreaGraphicsBlocksets() { for (int i = 0; i < 4; i++) { - uint8_t value = rom_[rom_.version_constants().kOverworldGfxGroups1 + + uint8_t value = (*rom_)[rom_->version_constants().kOverworldGfxGroups1 + (area_graphics_ * 4) + i]; if (value != 0) { static_graphics_[3 + i] = value; @@ -581,7 +582,7 @@ absl::StatusOr OverworldMap::GetPalette( const gfx::PaletteGroup &palette_group, int index, int previous_index, int limit) { if (index == 255) { - index = rom_[rom_.version_constants().kOverworldMapPaletteGroup + + index = (*rom_)[rom_->version_constants().kOverworldMapPaletteGroup + (previous_index * 4)]; } if (index >= limit) { @@ -592,28 +593,28 @@ absl::StatusOr OverworldMap::GetPalette( absl::Status OverworldMap::LoadPalette() { int previous_pal_id = - index_ > 0 ? rom_[kOverworldMapPaletteIds + parent_ - 1] : 0; + index_ > 0 ? (*rom_)[kOverworldMapPaletteIds + parent_ - 1] : 0; int previous_spr_pal_id = - index_ > 0 ? rom_[kOverworldSpritePaletteIds + parent_ - 1] : 0; + index_ > 0 ? (*rom_)[kOverworldSpritePaletteIds + parent_ - 1] : 0; area_palette_ = std::min((int)area_palette_, 0xA3); uint8_t pal0 = 0; - uint8_t pal1 = rom_[rom_.version_constants().kOverworldMapPaletteGroup + + uint8_t pal1 = (*rom_)[rom_->version_constants().kOverworldMapPaletteGroup + (area_palette_ * 4)]; - uint8_t pal2 = rom_[rom_.version_constants().kOverworldMapPaletteGroup + + uint8_t pal2 = (*rom_)[rom_->version_constants().kOverworldMapPaletteGroup + (area_palette_ * 4) + 1]; - uint8_t pal3 = rom_[rom_.version_constants().kOverworldMapPaletteGroup + + uint8_t pal3 = (*rom_)[rom_->version_constants().kOverworldMapPaletteGroup + (area_palette_ * 4) + 2]; uint8_t pal4 = - rom_[kOverworldSpritePaletteGroup + (sprite_palette_[game_state_] * 2)]; - uint8_t pal5 = rom_[kOverworldSpritePaletteGroup + + (*rom_)[kOverworldSpritePaletteGroup + (sprite_palette_[game_state_] * 2)]; + uint8_t pal5 = (*rom_)[kOverworldSpritePaletteGroup + (sprite_palette_[game_state_] * 2) + 1]; - auto grass_pal_group = rom_.palette_group().grass; + auto grass_pal_group = rom_->palette_group().grass; ASSIGN_OR_RETURN(gfx::SnesColor bgr, grass_pal_group[0].GetColor(0)); - auto ow_aux_pal_group = rom_.palette_group().overworld_aux; + auto ow_aux_pal_group = rom_->palette_group().overworld_aux; ASSIGN_OR_RETURN(gfx::SnesPalette aux1, GetPalette(ow_aux_pal_group, pal1, previous_pal_id, 20)); ASSIGN_OR_RETURN(gfx::SnesPalette aux2, @@ -621,7 +622,7 @@ absl::Status OverworldMap::LoadPalette() { // Additional handling of `pal3` and `parent_` if (pal3 == 255) { - pal3 = rom_[rom_.version_constants().kOverworldMapPaletteGroup + + pal3 = (*rom_)[rom_->version_constants().kOverworldMapPaletteGroup + (previous_pal_id * 4) + 2]; } @@ -641,26 +642,26 @@ absl::Status OverworldMap::LoadPalette() { pal0 = 4; } - auto ow_main_pal_group = rom_.palette_group().overworld_main; + auto ow_main_pal_group = rom_->palette_group().overworld_main; ASSIGN_OR_RETURN(gfx::SnesPalette main, GetPalette(ow_main_pal_group, pal0, previous_pal_id, 255)); - auto ow_animated_pal_group = rom_.palette_group().overworld_animated; + auto ow_animated_pal_group = rom_->palette_group().overworld_animated; ASSIGN_OR_RETURN(gfx::SnesPalette animated, GetPalette(ow_animated_pal_group, std::min((int)pal3, 13), previous_pal_id, 14)); - auto hud_pal_group = rom_.palette_group().hud; + auto hud_pal_group = rom_->palette_group().hud; gfx::SnesPalette hud = hud_pal_group[0]; ASSIGN_OR_RETURN(gfx::SnesPalette spr, - GetPalette(rom_.palette_group().sprites_aux3, pal4, + GetPalette(rom_->palette_group().sprites_aux3, pal4, previous_spr_pal_id, 24)); ASSIGN_OR_RETURN(gfx::SnesPalette spr2, - GetPalette(rom_.palette_group().sprites_aux3, pal5, + GetPalette(rom_->palette_group().sprites_aux3, pal5, previous_spr_pal_id, 24)); RETURN_IF_ERROR(palette_internal::SetColorsPalette( - rom_, parent_, current_palette_, main, animated, aux1, aux2, hud, bgr, + *rom_, parent_, current_palette_, main, animated, aux1, aux2, hud, bgr, spr, spr2)); if (palettesets_.count(area_palette_) == 0) { @@ -691,7 +692,7 @@ absl::Status OverworldMap::BuildTileset() { if (current_gfx_.size() == 0) current_gfx_.resize(0x10000, 0x00); for (int i = 0; i < 0x10; i++) { ProcessGraphicsBuffer(i, static_graphics_[i], 0x1000, - rom_.graphics_buffer().data()); + rom_->graphics_buffer().data()); } return absl::OkStatus(); } diff --git a/src/app/zelda3/overworld/overworld_map.h b/src/app/zelda3/overworld/overworld_map.h index 785c864d..415c1063 100644 --- a/src/app/zelda3/overworld/overworld_map.h +++ b/src/app/zelda3/overworld/overworld_map.h @@ -77,7 +77,7 @@ typedef struct OverworldMapTiles { class OverworldMap : public gfx::GfxContext { public: OverworldMap() = default; - OverworldMap(int index, Rom& rom); + OverworldMap(int index, Rom* rom); absl::Status BuildMap(int count, int game_state, int world, std::vector& tiles16, @@ -148,6 +148,24 @@ class OverworldMap : public gfx::GfxContext { current_blockset_.clear(); current_gfx_.clear(); bitmap_data_.clear(); + map_tiles_.light_world.clear(); + map_tiles_.dark_world.clear(); + map_tiles_.special_world.clear(); + built_ = false; + initialized_ = false; + large_map_ = false; + mosaic_ = false; + index_ = 0; + parent_ = 0; + large_index_ = 0; + world_ = 0; + game_state_ = 0; + main_gfx_id_ = 0; + message_id_ = 0; + area_graphics_ = 0; + area_palette_ = 0; + animated_gfx_ = 0; + subscreen_overlay_ = 0; } private: @@ -167,7 +185,7 @@ class OverworldMap : public gfx::GfxContext { int index, int previous_index, int limit); - Rom rom_; + Rom *rom_; bool built_ = false; bool large_map_ = false;