yaze 0.3.2
Link to the Past ROM Editor
 
Loading...
Searching...
No Matches
overworld_map_metadata.cc
Go to the documentation of this file.
2
3#include <algorithm>
4#include <array>
5#include <string>
6#include <unordered_map>
7
8#include "absl/status/status.h"
9#include "absl/strings/str_format.h"
10#include "absl/strings/strip.h"
11#include "core/project.h"
15
16namespace yaze::editor {
17namespace {
18
19std::string TrimCopy(const std::string& value) {
20 return std::string(absl::StripAsciiWhitespace(value));
21}
22
23std::array<std::string, 9> ResourceLabelKeysForId(int id) {
24 const std::string hex_upper = absl::StrFormat("%X", id);
25 return {
26 std::to_string(id),
27 absl::StrFormat("0x%x", id),
28 absl::StrFormat("0x%s", hex_upper),
29 absl::StrFormat("0X%s", hex_upper),
30 absl::StrFormat("$%s", hex_upper),
31 absl::StrFormat("0x%02X", id),
32 absl::StrFormat("0x%03X", id),
33 absl::StrFormat("0x%04X", id),
34 absl::StrFormat("$%02X", id),
35 };
36}
37
39 const std::unordered_map<std::string, std::string>& labels, int id) {
40 for (const auto& key : ResourceLabelKeysForId(id)) {
41 const auto it = labels.find(key);
42 if (it != labels.end() && !it->second.empty()) {
43 return it->second;
44 }
45 }
46 return "";
47}
48
50 std::unordered_map<std::string, std::string>& labels, int id) {
51 for (const auto& key : ResourceLabelKeysForId(id)) {
52 labels.erase(key);
53 }
54}
55
56std::string LabelWithId(const char* prefix, int id, const std::string& label,
57 int width = 2) {
58 const std::string id_text = width <= 2 ? absl::StrFormat("0x%02X", id)
59 : absl::StrFormat("0x%04X", id);
60 if (label.empty()) {
61 return absl::StrFormat("%s %s", prefix, id_text);
62 }
63 return absl::StrFormat("%s %s %s", prefix, id_text, label);
64}
65
66std::string WorldLabelForMap(int map_id) {
67 if (map_id >= zelda3::kSpecialWorldMapIdStart) {
68 return "Special World";
69 }
70 if (map_id >= zelda3::kDarkWorldMapIdStart) {
71 return "Dark World";
72 }
73 return "Light World";
74}
75
76std::string VersionLabelForRom(const Rom* rom) {
77 if (!rom) {
78 return "Unknown OW";
79 }
82 return "Vanilla OW";
84 return "ZS OW v1";
86 return "ZS OW v2";
88 return "ZS OW v3";
89 default:
90 return "Unknown OW";
91 }
92}
93
94std::string AreaSizeLabel(zelda3::AreaSizeEnum area_size) {
95 switch (area_size) {
97 return "Large 2x2";
99 return "Wide 2x1";
101 return "Tall 1x2";
103 default:
104 return "Small 1x1";
105 }
106}
107
109 const project::YazeProject* project,
110 int game_state) {
111 const int clamped_state = std::clamp(game_state, 0, 2);
112 const int music_id = map.area_music(clamped_state);
113 if (std::string project_label =
114 GetProjectResourceLabel(project, "overworld_music", music_id);
115 !project_label.empty()) {
116 return LabelWithId("Music", music_id, project_label);
117 }
118 std::string label = zelda3::GetResourceLabels().GetLabel(
120 return LabelWithId("Music", music_id, label);
121}
122
124 const std::string& project_type,
125 zelda3::ResourceType provider_type, int id) {
126 if (std::string project_label =
127 GetProjectResourceLabel(project, project_type, id);
128 !project_label.empty()) {
129 return project_label;
130 }
131 return zelda3::GetResourceLabels().GetLabel(provider_type, id);
132}
133
134} // namespace
135
137 const std::string& type, int id) {
138 if (!project) {
139 return "";
140 }
141 const auto type_it = project->resource_labels.find(type);
142 if (type_it == project->resource_labels.end()) {
143 return "";
144 }
145 return LookupResourceLabel(type_it->second, id);
146}
147
149 const std::string& type, int id,
150 const std::string& label) {
151 if (!project) {
152 return absl::FailedPreconditionError("No project is open");
153 }
154
155 const std::string trimmed = TrimCopy(label);
156 auto& labels = project->resource_labels[type];
157 EraseResourceLabelKeys(labels, id);
158 if (!trimmed.empty()) {
159 labels[std::to_string(id)] = trimmed;
160 }
162
163 if (project->project_opened()) {
164 return project->Save();
165 }
166 return absl::OkStatus();
167}
168
170 const zelda3::Overworld& overworld, const Rom* rom,
171 const project::YazeProject* project, int map_id, int game_state) {
172 OverworldMapMetadata metadata;
173 metadata.map_id = std::clamp(map_id, 0, zelda3::kNumOverworldMaps - 1);
174 metadata.world = std::clamp(metadata.map_id / 0x40, 0, 2);
175 metadata.world_label = WorldLabelForMap(metadata.map_id);
176 metadata.map_id_label = absl::StrFormat("0x%02X", metadata.map_id);
177 metadata.version_label = VersionLabelForRom(rom);
178
181 if (std::string project_label =
182 GetProjectResourceLabel(project, "overworld_map", metadata.map_id);
183 !project_label.empty()) {
184 metadata.map_name = project_label;
185 }
186 metadata.map_title =
187 absl::StrFormat("%s | %s %s", metadata.world_label, metadata.map_id_label,
188 metadata.map_name);
189
190 const zelda3::OverworldMap* map = overworld.overworld_map(metadata.map_id);
191 if (!map) {
192 metadata.area_size_label = "Unknown size";
193 metadata.parent_label = "Parent --";
194 metadata.area_gfx_label = "GFX --";
195 metadata.area_palette_label = "Area Pal --";
196 metadata.main_palette_label = "Main Pal --";
197 metadata.sprite_gfx_label = "Sprite GFX --";
198 metadata.sprite_palette_label = "Sprite Pal --";
199 metadata.animated_gfx_label = "Anim GFX --";
200 metadata.message_label = "Msg ----";
201 metadata.music_label = "Music --";
202 return metadata;
203 }
204
205 metadata.area_size_label = AreaSizeLabel(map->area_size());
206 metadata.parent_label = absl::StrFormat("Parent 0x%02X", map->parent());
207
208 metadata.area_gfx_label =
209 LabelWithId("Area GFX", map->area_graphics(),
210 ProjectOrProviderLabel(project, "graphics",
212 map->area_graphics()));
213
214 metadata.area_palette_label =
215 LabelWithId("Area Pal", map->area_palette(),
216 GetProjectResourceLabel(project, "overworld_area_palette",
217 map->area_palette()));
218
219 metadata.main_palette_label =
220 LabelWithId("Main Pal", map->main_palette(),
221 GetProjectResourceLabel(project, "overworld_main_palette",
222 map->main_palette()));
223
224 metadata.sprite_gfx_label =
225 LabelWithId("Sprite GFX", map->sprite_graphics(0),
226 ProjectOrProviderLabel(project, "graphics",
228 map->sprite_graphics(0)));
229
230 metadata.sprite_palette_label =
231 LabelWithId("Sprite Pal", map->sprite_palette(0),
232 GetProjectResourceLabel(project, "overworld_sprite_palette",
233 map->sprite_palette(0)));
234
235 metadata.animated_gfx_label =
236 LabelWithId("Anim GFX", map->animated_gfx(),
237 ProjectOrProviderLabel(project, "graphics",
239 map->animated_gfx()));
240
241 metadata.message_label = LabelWithId(
242 "Msg", map->message_id(),
243 GetProjectResourceLabel(project, "message", map->message_id()), 4);
244 metadata.music_label = MusicLabelForState(*map, project, game_state);
245
246 return metadata;
247}
248
249} // namespace yaze::editor
The Rom class is used to load, save, and modify Rom data. This is a generic SNES ROM container and do...
Definition rom.h:28
Represents a single Overworld map screen.
auto sprite_graphics(int i) const
auto area_music(int i) const
auto sprite_palette(int i) const
static OverworldVersion GetVersion(const Rom &rom)
Detect ROM version from ASM marker byte.
Represents the full Overworld data, light and dark world.
Definition overworld.h:389
auto overworld_map(int i) const
Definition overworld.h:662
std::string GetLabel(ResourceType type, int id) const
Get a label for a resource by type and ID.
std::string MusicLabelForState(const zelda3::OverworldMap &map, const project::YazeProject *project, int game_state)
void EraseResourceLabelKeys(std::unordered_map< std::string, std::string > &labels, int id)
std::string LookupResourceLabel(const std::unordered_map< std::string, std::string > &labels, int id)
std::string ProjectOrProviderLabel(const project::YazeProject *project, const std::string &project_type, zelda3::ResourceType provider_type, int id)
std::string LabelWithId(const char *prefix, int id, const std::string &label, int width=2)
Editors are the view controllers for the application.
absl::Status RenameProjectResourceLabel(project::YazeProject *project, const std::string &type, int id, const std::string &label)
OverworldMapMetadata BuildOverworldMapMetadata(const zelda3::Overworld &overworld, const Rom *rom, const project::YazeProject *project, int map_id, int game_state)
std::string GetProjectResourceLabel(const project::YazeProject *project, const std::string &type, int id)
ResourceType
Enumeration of all supported resource types for labeling.
constexpr int kSpecialWorldMapIdStart
constexpr int kNumOverworldMaps
Definition common.h:85
AreaSizeEnum
Area size enumeration for v3+ ROMs.
@ kZSCustomV2
Parent system, BG colors, main palettes.
@ kZSCustomV1
Basic features, expanded pointers.
@ kVanilla
0xFF in ROM, no ZScream ASM applied
@ kZSCustomV3
Area enum, wide/tall areas, all features.
constexpr int kDarkWorldMapIdStart
ResourceLabelProvider & GetResourceLabels()
Get the global ResourceLabelProvider instance.
Modern project structure with comprehensive settings consolidation.
Definition project.h:172
bool project_opened() const
Definition project.h:348
void InitializeResourceLabelProvider()
Initialize the global ResourceLabelProvider with this project's labels.
Definition project.cc:2498
std::unordered_map< std::string, std::unordered_map< std::string, std::string > > resource_labels
Definition project.h:205