yaze 0.2.2
Link to the Past ROM Editor
 
Loading...
Searching...
No Matches
editor_manager.cc
Go to the documentation of this file.
1#include "editor_manager.h"
2
3#include "absl/status/status.h"
4#include "absl/strings/match.h"
5#include "app/core/features.h"
7#include "app/core/project.h"
16#include "app/emu/emulator.h"
17#include "app/gui/icons.h"
18#include "app/gui/input.h"
19#include "app/gui/style.h"
20#include "app/rom.h"
21#include "editor/editor.h"
22#include "imgui/imgui.h"
23#include "imgui/misc/cpp/imgui_stdlib.h"
24#include "util/hex.h"
25#include "util/macro.h"
26
27namespace yaze {
28namespace editor {
29
30using namespace ImGui;
31using core::FileDialogWrapper;
32
33namespace {
34
35bool BeginCentered(const char *name) {
36 ImGuiIO const &io = GetIO();
37 ImVec2 pos(io.DisplaySize.x * 0.5f, io.DisplaySize.y * 0.5f);
38 SetNextWindowPos(pos, ImGuiCond_Always, ImVec2(0.5f, 0.5f));
39 ImGuiWindowFlags flags =
40 ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoDecoration |
41 ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings;
42 return Begin(name, nullptr, flags);
43}
44
45bool IsEditorActive(Editor *editor, std::vector<Editor *> &active_editors) {
46 return std::find(active_editors.begin(), active_editors.end(), editor) !=
47 active_editors.end();
48}
49
50std::string GetEditorName(EditorType type) {
51 return kEditorNames[static_cast<int>(type)];
52}
53
54} // namespace
55
56void EditorManager::Initialize(const std::string &filename) {
57 if (!filename.empty()) {
58 PRINT_IF_ERROR(rom()->LoadFromFile(filename));
59 }
60
61 std::vector<gui::MenuItem> recent_files;
62 static RecentFilesManager manager("recent_files.txt");
63 manager.Load();
64 if (manager.GetRecentFiles().empty()) {
65 recent_files.emplace_back("No Recent Files", "", nullptr);
66 } else {
67 for (const auto &filePath : manager.GetRecentFiles()) {
68 recent_files.emplace_back(filePath, "",
69 [&]() { OpenRomOrProject(filePath); });
70 }
71 }
72
73 std::vector<gui::MenuItem> options_subitems;
74 options_subitems.emplace_back(
75 "Backup ROM", "", [&]() { backup_rom_ |= backup_rom_; },
76 [&]() { return backup_rom_; });
77 options_subitems.emplace_back(
78 "Save New Auto", "", [&]() { save_new_auto_ |= save_new_auto_; },
79 [&]() { return save_new_auto_; });
80
81 std::vector<gui::MenuItem> project_menu_subitems;
82 project_menu_subitems.emplace_back("New Project", "",
83 [&]() { new_project_menu = true; });
84 project_menu_subitems.emplace_back("Open Project", "",
85 [&]() { status_ = OpenProject(); });
86 project_menu_subitems.emplace_back(
87 "Save Project", "", [&]() { SaveProject(); },
88 [&]() { return current_project_.project_opened_; });
89
90 context_.shortcut_manager.RegisterShortcut(
91 "Open", {ImGuiKey_O, ImGuiMod_Ctrl}, [&]() { LoadRom(); });
92 context_.shortcut_manager.RegisterShortcut(
93 "Save", {ImGuiKey_S, ImGuiMod_Ctrl}, [&]() { SaveRom(); });
94 context_.shortcut_manager.RegisterShortcut(
95 "Close", {ImGuiKey_W, ImGuiMod_Ctrl}, [&]() { rom()->Close(); });
96 context_.shortcut_manager.RegisterShortcut(
97 "Quit", {ImGuiKey_Q, ImGuiMod_Ctrl}, [&]() { quit_ = true; });
98
99 context_.shortcut_manager.RegisterShortcut(
100 "Undo", {ImGuiKey_Z, ImGuiMod_Ctrl},
101 [&]() { status_ = current_editor_->Undo(); });
102 context_.shortcut_manager.RegisterShortcut(
103 "Redo", {ImGuiKey_Y, ImGuiMod_Ctrl},
104 [&]() { status_ = current_editor_->Redo(); });
105 context_.shortcut_manager.RegisterShortcut(
106 "Cut", {ImGuiKey_X, ImGuiMod_Ctrl},
107 [&]() { status_ = current_editor_->Cut(); });
108 context_.shortcut_manager.RegisterShortcut(
109 "Copy", {ImGuiKey_C, ImGuiMod_Ctrl},
110 [&]() { status_ = current_editor_->Copy(); });
111 context_.shortcut_manager.RegisterShortcut(
112 "Paste", {ImGuiKey_V, ImGuiMod_Ctrl},
113 [&]() { status_ = current_editor_->Paste(); });
114 context_.shortcut_manager.RegisterShortcut(
115 "Find", {ImGuiKey_F, ImGuiMod_Ctrl},
116 [&]() { status_ = current_editor_->Find(); });
117
118 context_.shortcut_manager.RegisterShortcut(
119 "Load Last ROM", {ImGuiKey_R, ImGuiMod_Ctrl}, [&]() {
120 manager.Load();
121 if (!manager.GetRecentFiles().empty()) {
122 auto front = manager.GetRecentFiles().front();
123 OpenRomOrProject(front);
124 }
125 });
126
127 context_.shortcut_manager.RegisterShortcut("F1", ImGuiKey_F1,
128 [&]() { about_ = true; });
129
130 gui::kMainMenu = {
131 {"File",
132 {},
133 {},
134 {},
135 {
136 {absl::StrCat(ICON_MD_FILE_OPEN, " Open"),
137 context_.shortcut_manager.GetKeys("Open"),
138 context_.shortcut_manager.GetCallback("Open")},
139 {"Open Recent", "", [&]() {},
140 []() { return !manager.GetRecentFiles().empty(); }, recent_files},
141 {absl::StrCat(ICON_MD_FILE_DOWNLOAD, " Save"),
142 context_.shortcut_manager.GetKeys("Save"),
143 context_.shortcut_manager.GetCallback("Save")},
144 {absl::StrCat(ICON_MD_SAVE_AS, " Save As.."), "",
145 [&]() { save_as_menu_ = true; }},
146 {absl::StrCat(ICON_MD_BALLOT, " Project"), "", [&]() {},
147 []() { return true; }, project_menu_subitems},
148 {absl::StrCat(ICON_MD_CLOSE, " Close"), "",
149 [&]() { rom()->Close(); }},
150 {gui::kSeparator, "", nullptr, []() { return true; }},
151 {absl::StrCat(ICON_MD_MISCELLANEOUS_SERVICES, " Options"), "",
152 [&]() {}, []() { return true; }, options_subitems},
153 {absl::StrCat(ICON_MD_EXIT_TO_APP, " Quit"), "Ctrl+Q",
154 [&]() { quit_ = true; }},
155 }},
156 {"Edit",
157 {},
158 {},
159 {},
160 {
161 {absl::StrCat(ICON_MD_CONTENT_CUT, " Cut"),
162 context_.shortcut_manager.GetKeys("Cut"),
163 context_.shortcut_manager.GetCallback("Cut")},
164 {absl::StrCat(ICON_MD_CONTENT_COPY, " Copy"),
165 context_.shortcut_manager.GetKeys("Copy"),
166 context_.shortcut_manager.GetCallback("Copy")},
167 {absl::StrCat(ICON_MD_CONTENT_PASTE, " Paste"),
168 context_.shortcut_manager.GetKeys("Paste"),
169 context_.shortcut_manager.GetCallback("Paste")},
170 {gui::kSeparator, "", nullptr, []() { return true; }},
171 {absl::StrCat(ICON_MD_UNDO, " Undo"),
172 context_.shortcut_manager.GetKeys("Undo"),
173 context_.shortcut_manager.GetCallback("Undo")},
174 {absl::StrCat(ICON_MD_REDO, " Redo"),
175 context_.shortcut_manager.GetKeys("Redo"),
176 context_.shortcut_manager.GetCallback("Redo")},
177 {gui::kSeparator, "", nullptr, []() { return true; }},
178 {absl::StrCat(ICON_MD_SEARCH, " Find"),
179 context_.shortcut_manager.GetKeys("Find"),
180 context_.shortcut_manager.GetCallback("Find")},
181 }},
182 {"View",
183 {},
184 {},
185 {},
186 {
187 {absl::StrCat(ICON_MD_CODE, " Assembly Editor"), "",
188 [&]() { show_asm_editor_ = true; },
189 [&]() { return show_asm_editor_; }},
190 {absl::StrCat(ICON_MD_CASTLE, " Dungeon Editor"), "",
191 [&]() { dungeon_editor_.set_active(true); },
192 [&]() { return *dungeon_editor_.active(); }},
193 {absl::StrCat(ICON_MD_PHOTO, " Graphics Editor"), "",
194 [&]() { graphics_editor_.set_active(true); },
195 [&]() { return *graphics_editor_.active(); }},
196 {absl::StrCat(ICON_MD_MUSIC_NOTE, " Music Editor"), "",
197 [&]() { music_editor_.set_active(true); },
198 [&]() { return *music_editor_.active(); }},
199 {absl::StrCat(ICON_MD_LAYERS, " Overworld Editor"), "",
200 [&]() { overworld_editor_.set_active(true); },
201 [&]() { return *overworld_editor_.active(); }},
202 {absl::StrCat(ICON_MD_PALETTE, " Palette Editor"), "",
203 [&]() { palette_editor_.set_active(true); },
204 [&]() { return *palette_editor_.active(); }},
205 {absl::StrCat(ICON_MD_SCREENSHOT, " Screen Editor"), "",
206 [&]() { screen_editor_.set_active(true); },
207 [&]() { return *screen_editor_.active(); }},
208 {absl::StrCat(ICON_MD_SMART_TOY, " Sprite Editor"), "",
209 [&]() { sprite_editor_.set_active(true); },
210 [&]() { return *sprite_editor_.active(); }},
211 {absl::StrCat(ICON_MD_MESSAGE, " Message Editor"), "",
212 [&]() { message_editor_.set_active(true); },
213 [&]() { return *message_editor_.active(); }},
214 {absl::StrCat(ICON_MD_SETTINGS, " Settings Editor"), "",
215 [&]() { settings_editor_.set_active(true); },
216 [&]() { return *settings_editor_.active(); }},
217 {gui::kSeparator, "", nullptr, []() { return true; }},
218 {absl::StrCat(ICON_MD_GAMEPAD, " Emulator"), "",
219 [&]() { show_emulator_ = true; }},
220 {absl::StrCat(ICON_MD_MEMORY, " Memory Editor"), "",
221 [&]() { show_memory_editor_ = true; }},
222 {absl::StrCat(ICON_MD_SIM_CARD, " ROM Metadata"), "",
223 [&]() { rom_info_ = true; }},
224 {gui::kSeparator, "", nullptr, []() { return true; }},
225 {absl::StrCat(ICON_MD_HELP, " ImGui Demo"), "",
226 [&]() { show_imgui_demo_ = true; }},
227 {absl::StrCat(ICON_MD_HELP, " ImGui Metrics"), "",
228 [&]() { show_imgui_metrics_ = true; }},
229 }},
230 {"Workspace",
231 {},
232 {},
233 {},
234 {
235 {absl::StrCat(ICON_MD_SPACE_DASHBOARD, " Layout"), "",
236 [&]() { show_workspace_layout = true; }},
237 }},
238 {"Help",
239 {},
240 {},
241 {},
242 {
243 {absl::StrCat(ICON_MD_HELP, " How to open a ROM"), "",
244 [&]() { open_rom_help = true; }},
245 {absl::StrCat(ICON_MD_HELP, " Supported Features"), "",
246 [&]() { open_supported_features = true; }},
247 {absl::StrCat(ICON_MD_HELP, " How to manage a project"), "",
248 [&]() { open_manage_project = true; }},
249 {absl::StrCat(ICON_MD_HELP, " About"), "F1",
250 [&]() { about_ = true; }},
251 }}};
252
253 overworld_editor_.Initialize();
254}
255
256absl::Status EditorManager::Update() {
257 DrawPopups();
258 ExecuteShortcuts(context_.shortcut_manager);
259
260 for (auto editor : active_editors_) {
261 if (*editor->active()) {
262 if (ImGui::Begin(GetEditorName(editor->type()).c_str(),
263 editor->active())) {
265 status_ = editor->Update();
266 }
267 ImGui::End();
268 }
269 }
270
271 static bool show_home = true;
272 ImGui::Begin("Home", &show_home);
273 if (!current_rom_) {
274 DrawHomepage();
275 } else {
277 }
278 ImGui::End();
279 return absl::OkStatus();
280}
281
283 // Show popup pane to select an editor to add
284 static bool show_add_editor = false;
285 if (show_add_editor) OpenPopup("AddEditor");
286
287 if (BeginPopup("AddEditor", ImGuiWindowFlags_AlwaysAutoResize)) {
288 if (MenuItem("Overworld", nullptr, false,
289 !IsEditorActive(&overworld_editor_, active_editors_))) {
291 CloseCurrentPopup();
292 }
293 if (MenuItem("Dungeon", nullptr, false,
294 !IsEditorActive(&dungeon_editor_, active_editors_))) {
296 CloseCurrentPopup();
297 }
298 if (MenuItem("Graphics", nullptr, false,
299 !IsEditorActive(&graphics_editor_, active_editors_))) {
301 CloseCurrentPopup();
302 }
303 if (MenuItem("Music", nullptr, false,
304 !IsEditorActive(&music_editor_, active_editors_))) {
305 active_editors_.push_back(&music_editor_);
306 CloseCurrentPopup();
307 }
308 if (MenuItem("Palette", nullptr, false,
309 !IsEditorActive(&palette_editor_, active_editors_))) {
311 CloseCurrentPopup();
312 }
313 if (MenuItem("Screen", nullptr, false,
314 !IsEditorActive(&screen_editor_, active_editors_))) {
316 CloseCurrentPopup();
317 }
318 if (MenuItem("Sprite", nullptr, false,
319 !IsEditorActive(&sprite_editor_, active_editors_))) {
321 CloseCurrentPopup();
322 }
323 if (MenuItem("Code", nullptr, false,
324 !IsEditorActive(&assembly_editor_, active_editors_))) {
326 CloseCurrentPopup();
327 }
328 if (MenuItem("Message", nullptr, false,
329 !IsEditorActive(&message_editor_, active_editors_))) {
331 CloseCurrentPopup();
332 }
333 if (MenuItem("Settings", nullptr, false,
334 !IsEditorActive(&settings_editor_, active_editors_))) {
336 CloseCurrentPopup();
337 }
338 EndPopup();
339 }
340
341 if (!IsPopupOpen("AddEditor")) {
342 show_add_editor = false;
343 }
344
345 if (BeginTabBar("##TabBar", ImGuiTabBarFlags_Reorderable |
346 ImGuiTabBarFlags_AutoSelectNewTabs)) {
347 for (auto editor : active_editors_) {
348 bool open = true;
349 switch (editor->type()) {
351 if (overworld_editor_.jump_to_tab() == -1) {
352 if (BeginTabItem("Overworld", &open)) {
354 status_ = overworld_editor_.Update();
355 EndTabItem();
356 }
357 }
358 break;
360 if (BeginTabItem("Dungeon", &open)) {
362 status_ = dungeon_editor_.Update();
363 if (overworld_editor_.jump_to_tab() != -1) {
364 dungeon_editor_.add_room(overworld_editor_.jump_to_tab());
365 overworld_editor_.jump_to_tab_ = -1;
366 }
367 EndTabItem();
368 }
369 break;
371 if (BeginTabItem("Graphics", &open)) {
373 status_ = graphics_editor_.Update();
374 EndTabItem();
375 }
376 break;
378 if (BeginTabItem("Music", &open)) {
380
381 status_ = music_editor_.Update();
382 EndTabItem();
383 }
384 break;
386 if (BeginTabItem("Palette", &open)) {
388 status_ = palette_editor_.Update();
389 EndTabItem();
390 }
391 break;
393 if (BeginTabItem("Screen", &open)) {
395 status_ = screen_editor_.Update();
396 EndTabItem();
397 }
398 break;
400 if (BeginTabItem("Sprite", &open)) {
402 status_ = sprite_editor_.Update();
403 EndTabItem();
404 }
405 break;
407 if (BeginTabItem("Code", &open)) {
409 assembly_editor_.UpdateCodeView();
410 EndTabItem();
411 }
412 break;
414 if (BeginTabItem("Settings", &open)) {
416 status_ = settings_editor_.Update();
417 EndTabItem();
418 }
419 break;
421 if (BeginTabItem("Message", &open)) {
423 status_ = message_editor_.Update();
424 EndTabItem();
425 }
426 break;
427 default:
428 break;
429 }
430 if (!open) {
431 active_editors_.erase(
432 std::remove(active_editors_.begin(), active_editors_.end(), editor),
433 active_editors_.end());
434 }
435 }
436
437 if (TabItemButton(ICON_MD_ADD, ImGuiTabItemFlags_Trailing)) {
438 show_add_editor = true;
439 }
440
441 EndTabBar();
442 }
443}
444
446 TextWrapped("Welcome to the Yet Another Zelda3 Editor (yaze)!");
447 TextWrapped(
448 "This editor is designed to be a comprehensive tool for editing the "
449 "Legend of Zelda: A Link to the Past.");
450 TextWrapped(
451 "The editor is still in development, so please report any bugs or issues "
452 "you encounter.");
453
454 if (gui::ClickableText("Open a ROM")) {
455 LoadRom();
456 }
457}
458
460 static bool show_status_ = false;
461 static absl::Status prev_status;
462 if (!status_.ok()) {
463 show_status_ = true;
464 prev_status = status_;
465 }
466
467 if (show_status_ && (BeginCentered("StatusWindow"))) {
468 Text("%s", ICON_MD_ERROR);
469 Text("%s", prev_status.ToString().c_str());
470 Spacing();
471 NextColumn();
472 Columns(1);
473 Separator();
474 NewLine();
475 SameLine(128);
476 if (Button("OK", gui::kDefaultModalSize) || IsKeyPressed(ImGuiKey_Space)) {
477 show_status_ = false;
478 status_ = absl::OkStatus();
479 }
480 SameLine();
481 if (Button(ICON_MD_CONTENT_COPY, ImVec2(50, 0))) {
482 SetClipboardText(prev_status.ToString().c_str());
483 }
484 End();
485 }
486
487 if (about_) OpenPopup("About");
488 if (BeginPopupModal("About", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) {
489 Text("Yet Another Zelda3 Editor - v%s", version_.c_str());
490 Text("Written by: scawful");
491 Spacing();
492 Text("Special Thanks: Zarby89, JaredBrian");
493 Separator();
494
495 if (Button("Close", gui::kDefaultModalSize)) {
496 about_ = false;
497 CloseCurrentPopup();
498 }
499 EndPopup();
500 }
501
502 if (rom_info_) OpenPopup("ROM Information");
503 if (BeginPopupModal("ROM Information", nullptr,
504 ImGuiWindowFlags_AlwaysAutoResize)) {
505 Text("Title: %s", rom()->title().c_str());
506 Text("ROM Size: %s", util::HexLongLong(rom()->size()).c_str());
507
508 if (Button("Close", gui::kDefaultModalSize) ||
509 IsKeyPressed(ImGuiKey_Escape)) {
510 rom_info_ = false;
511 CloseCurrentPopup();
512 }
513 EndPopup();
514 }
515}
516
518 static bool show_display_settings = false;
519 static bool save_as_menu = false;
520
521 if (BeginMenuBar()) {
522 gui::DrawMenu(gui::kMainMenu);
523
524 SameLine(GetWindowWidth() - GetStyle().ItemSpacing.x -
525 CalcTextSize(ICON_MD_DISPLAY_SETTINGS).x - 110);
526 PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0));
527 if (Button(ICON_MD_DISPLAY_SETTINGS)) {
528 show_display_settings = !show_display_settings;
529 }
530 PopStyleColor();
531 Text("yaze v%s", version_.c_str());
532 EndMenuBar();
533 }
534
535 if (show_display_settings) {
536 Begin("Display Settings", &show_display_settings, ImGuiWindowFlags_None);
538 End();
539 }
540
541 if (show_imgui_demo_) ShowDemoWindow();
542 if (show_imgui_metrics_) ShowMetricsWindow(&show_imgui_metrics_);
545
546 if (show_emulator_) {
547 Begin("Emulator", &show_emulator_, ImGuiWindowFlags_MenuBar);
548 emulator_.Run();
549 End();
550 }
551
553 Begin("Palette Editor", &show_palette_editor_);
554 status_ = palette_editor_.Update();
555 End();
556 }
557
558 if (open_supported_features) OpenPopup("Supported Features");
559 if (BeginPopupModal("Supported Features", nullptr,
560 ImGuiWindowFlags_AlwaysAutoResize)) {
561 Text("Overworld");
562 BulletText("LW/DW/SW Tilemap Editing");
563 BulletText("LW/DW/SW Map Properties");
564 BulletText("Create/Delete/Update Entrances");
565 BulletText("Create/Delete/Update Exits");
566 BulletText("Create/Delete/Update Sprites");
567 BulletText("Create/Delete/Update Items");
568
569 Text("Dungeon");
570 BulletText("View Room Header Properties");
571 BulletText("View Entrance Properties");
572
573 Text("Graphics");
574 BulletText("View Decompressed Graphics Sheets");
575 BulletText("View/Update Graphics Groups");
576
577 Text("Palettes");
578 BulletText("View Palette Groups");
579
580 Text("Saveable");
581 BulletText("All Listed Overworld Features");
582 BulletText("Hex Editor Changes");
583
584 if (Button("Close", gui::kDefaultModalSize)) {
586 CloseCurrentPopup();
587 }
588 EndPopup();
589 }
590
591 if (open_rom_help) OpenPopup("Open a ROM");
592 if (BeginPopupModal("Open a ROM", nullptr,
593 ImGuiWindowFlags_AlwaysAutoResize)) {
594 Text("File -> Open");
595 Text("Select a ROM file to open");
596 Text("Supported ROMs (headered or unheadered):");
597 Text("The Legend of Zelda: A Link to the Past");
598 Text("US Version 1.0");
599 Text("JP Version 1.0");
600
601 if (Button("Close", gui::kDefaultModalSize)) {
602 open_rom_help = false;
603 CloseCurrentPopup();
604 }
605 EndPopup();
606 }
607
608 if (open_manage_project) OpenPopup("Manage Project");
609 if (BeginPopupModal("Manage Project", nullptr,
610 ImGuiWindowFlags_AlwaysAutoResize)) {
611 Text("Project Menu");
612 Text("Create a new project or open an existing one.");
613 Text("Save the project to save the current state of the project.");
614 TextWrapped(
615 "To save a project, you need to first open a ROM and initialize your "
616 "code path and labels file. Label resource manager can be found in "
617 "the View menu. Code path is set in the Code editor after opening a "
618 "folder.");
619
620 if (Button("Close", gui::kDefaultModalSize)) {
621 open_manage_project = false;
622 CloseCurrentPopup();
623 }
624 EndPopup();
625 }
626
628 rom()->resource_label()->DisplayLabels(&show_resource_label_manager);
629 if (current_project_.project_opened_ &&
630 !current_project_.labels_filename_.empty()) {
631 current_project_.labels_filename_ = rom()->resource_label()->filename_;
632 }
633 }
634
635 if (save_as_menu) {
636 static std::string save_as_filename = "";
637 Begin("Save As..", &save_as_menu, ImGuiWindowFlags_AlwaysAutoResize);
638 InputText("Filename", &save_as_filename);
639 if (Button("Save", gui::kDefaultModalSize)) {
640 SaveRom();
641 save_as_menu = false;
642 }
643 SameLine();
644 if (Button("Cancel", gui::kDefaultModalSize)) {
645 save_as_menu = false;
646 }
647 End();
648 }
649
650 if (new_project_menu) {
651 Begin("New Project", &new_project_menu, ImGuiWindowFlags_AlwaysAutoResize);
652 static std::string save_as_filename = "";
653 InputText("Project Name", &save_as_filename);
654 if (Button("Destination Filepath", gui::kDefaultModalSize)) {
656 }
657 SameLine();
658 Text("%s", current_project_.filepath.c_str());
659 if (Button("ROM File", gui::kDefaultModalSize)) {
661 }
662 SameLine();
663 Text("%s", current_project_.rom_filename_.c_str());
664 if (Button("Labels File", gui::kDefaultModalSize)) {
665 current_project_.labels_filename_ =
667 }
668 SameLine();
669 Text("%s", current_project_.labels_filename_.c_str());
670 if (Button("Code Folder", gui::kDefaultModalSize)) {
672 }
673 SameLine();
674 Text("%s", current_project_.code_folder_.c_str());
675
676 Separator();
677 if (Button("Create", gui::kDefaultModalSize)) {
678 new_project_menu = false;
679 status_ = current_project_.Create(save_as_filename);
680 if (status_.ok()) {
681 status_ = current_project_.Save();
682 }
683 }
684 SameLine();
685 if (Button("Cancel", gui::kDefaultModalSize)) {
686 new_project_menu = false;
687 }
688 End();
689 }
690}
691
693 auto file_name = FileDialogWrapper::ShowOpenFileDialog();
694 auto load_rom = rom()->LoadFromFile(file_name);
695 if (load_rom.ok()) {
696 current_rom_ = rom();
697 static RecentFilesManager manager("recent_files.txt");
698 manager.Load();
699 manager.AddFile(file_name);
700 manager.Save();
701 LoadAssets();
702 }
703}
704
706 auto load_rom_assets = [&]() -> absl::Status {
707 auto &sheet_manager = GraphicsSheetManager::GetInstance();
708 ASSIGN_OR_RETURN(*sheet_manager.mutable_gfx_sheets(),
711 return absl::OkStatus();
712 };
713 if (!load_rom_assets().ok()) {
714 status_ = load_rom_assets();
715 }
716}
717
719 if (core::FeatureFlags::get().kSaveDungeonMaps) {
720 status_ = screen_editor_.SaveDungeonMaps();
722 }
723
724 status_ = overworld_editor_.Save();
726
727 if (core::FeatureFlags::get().kSaveGraphicsSheet)
729 *rom(), GraphicsSheetManager::GetInstance().gfx_sheets()));
730
731 status_ = rom()->SaveToFile(backup_rom_, save_new_auto_);
732}
733
734void EditorManager::OpenRomOrProject(const std::string &filename) {
735 if (absl::StrContains(filename, ".yaze")) {
736 status_ = current_project_.Open(filename);
737 if (status_.ok()) {
739 }
740 } else {
741 status_ = rom()->LoadFromFile(filename);
742 current_rom_ = rom();
743 LoadAssets();
744 }
745}
746
748 RETURN_IF_ERROR(rom()->LoadFromFile(current_project_.rom_filename_));
749 current_rom_ = rom();
750
751 if (!rom()->resource_label()->LoadLabels(current_project_.labels_filename_)) {
752 return absl::InternalError(
753 "Could not load labels file, update your project file.");
754 }
755
756 static RecentFilesManager manager("recent_files.txt");
757 manager.Load();
758 manager.AddFile(current_project_.filepath + "/" + current_project_.name +
759 ".yaze");
760 manager.Save();
761 assembly_editor_.OpenFolder(current_project_.code_folder_);
762 current_project_.project_opened_ = true;
763 LoadAssets();
764 return absl::OkStatus();
765}
766
768 if (current_project_.project_opened_) {
769 status_ = current_project_.Save();
770 } else {
771 new_project_menu = true;
772 }
773}
774
775} // namespace editor
776} // namespace yaze
static GraphicsSheetManager & GetInstance()
Definition rom.h:270
const std::vector< std::string > & GetRecentFiles() const
Definition project.h:122
void AddFile(const std::string &file_path)
Definition project.h:88
auto rom()
Definition rom.h:382
static Flags & get()
Definition features.h:69
void OpenRomOrProject(const std::string &filename)
OverworldEditor overworld_editor_
MemoryEditorWithDiffChecker memory_editor_
std::vector< Editor * > active_editors_
void Initialize(const std::string &filename="")
Interface for editor classes.
Definition editor.h:53
static std::string ShowOpenFileDialog()
ShowOpenFileDialog opens a file dialog and returns the selected filepath.
static std::string ShowOpenFolderDialog()
ShowOpenFolderDialog opens a file dialog and returns the selected folder path.
#define ICON_MD_CONTENT_CUT
Definition icons.h:464
#define ICON_MD_SETTINGS
Definition icons.h:1697
#define ICON_MD_FILE_OPEN
Definition icons.h:745
#define ICON_MD_EXIT_TO_APP
Definition icons.h:697
#define ICON_MD_MEMORY
Definition icons.h:1193
#define ICON_MD_SEARCH
Definition icons.h:1671
#define ICON_MD_SIM_CARD
Definition icons.h:1762
#define ICON_MD_FILE_DOWNLOAD
Definition icons.h:742
#define ICON_MD_SAVE_AS
Definition icons.h:1644
#define ICON_MD_CODE
Definition icons.h:432
#define ICON_MD_REDO
Definition icons.h:1568
#define ICON_MD_MESSAGE
Definition icons.h:1199
#define ICON_MD_CASTLE
Definition icons.h:378
#define ICON_MD_SCREENSHOT
Definition icons.h:1664
#define ICON_MD_ERROR
Definition icons.h:684
#define ICON_MD_MUSIC_NOTE
Definition icons.h:1262
#define ICON_MD_CONTENT_PASTE
Definition icons.h:465
#define ICON_MD_LAYERS
Definition icons.h:1066
#define ICON_MD_DISPLAY_SETTINGS
Definition icons.h:585
#define ICON_MD_ADD
Definition icons.h:84
#define ICON_MD_BALLOT
Definition icons.h:235
#define ICON_MD_SPACE_DASHBOARD
Definition icons.h:1803
#define ICON_MD_PALETTE
Definition icons.h:1368
#define ICON_MD_CONTENT_COPY
Definition icons.h:463
#define ICON_MD_MISCELLANEOUS_SERVICES
Definition icons.h:1211
#define ICON_MD_PHOTO
Definition icons.h:1449
#define ICON_MD_CLOSE
Definition icons.h:416
#define ICON_MD_GAMEPAD
Definition icons.h:864
#define ICON_MD_HELP
Definition icons.h:931
#define ICON_MD_UNDO
Definition icons.h:2034
#define ICON_MD_SMART_TOY
Definition icons.h:1776
#define PRINT_IF_ERROR(expression)
Definition macro.h:25
#define RETURN_IF_ERROR(expression)
Definition macro.h:51
#define ASSIGN_OR_RETURN(type_variable_name, expression)
Definition macro.h:59
#define RETURN_VOID_IF_ERROR(expression)
Definition macro.h:42
bool IsEditorActive(Editor *editor, std::vector< Editor * > &active_editors)
Editors are the view controllers for the application.
constexpr std::array< const char *, 10 > kEditorNames
Definition editor.h:42
void ExecuteShortcuts(const ShortcutManager &shortcut_manager)
constexpr std::string kSeparator
Definition input.h:92
bool ClickableText(const std::string &text)
Definition input.cc:192
void DrawMenu(Menu &menu)
Definition input.cc:364
void DrawDisplaySettings(ImGuiStyle *ref)
Definition style.cc:396
constexpr ImVec2 kDefaultModalSize
Definition input.h:22
std::string HexLongLong(uint64_t qword, HexStringParams params)
Definition hex.cc:72
Main namespace for the application.
Definition controller.cc:18
absl::StatusOr< std::array< gfx::Bitmap, kNumGfxSheets > > LoadAllGraphicsData(Rom &rom, bool defer_render)
This function iterates over all graphics sheets in the Rom and loads them into memory....
Definition rom.cc:77
absl::Status SaveAllGraphicsData(Rom &rom, std::array< gfx::Bitmap, kNumGfxSheets > &gfx_sheets)
Definition rom.cc:136