Files
yaze/src/app/editor/dungeon_editor.cc
scawful 299770922c Add Debugger interface, RoomObject class
- Log instructions to debugger using experiment flag
- Use BitmapManager for more functionality
- Draw framebuffer and integrated debugger
2023-11-13 14:51:01 -05:00

229 lines
7.1 KiB
C++

#include "dungeon_editor.h"
#include <imgui/imgui.h>
#include "app/core/common.h"
#include "app/gui/canvas.h"
#include "app/gui/icons.h"
#include "app/gui/input.h"
#include "app/rom.h"
#include "app/zelda3/dungeon/room_names.h"
#include "zelda3/dungeon/room.h"
namespace yaze {
namespace app {
namespace editor {
void DungeonEditor::Update() {
if (!is_loaded_) {
for (int i = 0; i < 0x100; i++) {
rooms_.emplace_back(zelda3::dungeon::Room(i));
rooms_[i].LoadHeader();
// rooms_[i].LoadRoomGraphics(rooms_[i].blockset);
}
is_loaded_ = true;
}
DrawToolset();
ImGui::Separator();
if (ImGui::BeginTable("#DungeonEditTable", 3, toolset_table_flags_,
ImVec2(0, 0))) {
ImGui::TableSetupColumn("Room Selector");
ImGui::TableSetupColumn("Canvas", ImGuiTableColumnFlags_WidthStretch,
ImGui::GetContentRegionAvail().x);
ImGui::TableSetupColumn("Object Selector");
ImGui::TableHeadersRow();
ImGui::TableNextRow();
ImGui::TableNextColumn();
if (rom()->isLoaded()) {
if (ImGuiID child_id = ImGui::GetID((void*)(intptr_t)9);
ImGui::BeginChild(child_id, ImGui::GetContentRegionAvail(), true,
ImGuiWindowFlags_AlwaysVerticalScrollbar)) {
int i = 0;
for (const auto each_room_name : zelda3::dungeon::kRoomNames) {
ImGui::Button(each_room_name.data());
if (ImGui::IsItemClicked()) {
active_rooms_.push_back(i);
}
i += 1;
}
}
ImGui::EndChild();
}
ImGui::TableNextColumn();
DrawDungeonTabView();
ImGui::TableNextColumn();
if (ImGui::Button("dungeon object renderer")) {
object_renderer_.RenderObjectsAsBitmaps();
}
DrawTileSelector();
ImGui::EndTable();
}
}
// Using ImGui Custom Tabs show each individual room the user selects from the
// Buttons above to open a canvas for each individual room.
void DungeonEditor::DrawDungeonTabView() {
static int next_tab_id = 0;
// TabItemButton() and Leading/Trailing flags are distinct features which we
// will demo together. (It is possible to submit regular tabs with
// Leading/Trailing flags, or TabItemButton tabs without Leading/Trailing
// flags... but they tend to make more sense together)
static bool show_trailing_button = true;
ImGui::Checkbox("Show Trailing TabItemButton()", &show_trailing_button);
// Expose some other flags which are useful to showcase how they interact with
// Leading/Trailing tabs
static ImGuiTabBarFlags tab_bar_flags =
ImGuiTabBarFlags_AutoSelectNewTabs | ImGuiTabBarFlags_Reorderable |
ImGuiTabBarFlags_FittingPolicyResizeDown |
ImGuiTabBarFlags_TabListPopupButton;
if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyResizeDown",
&tab_bar_flags,
ImGuiTabBarFlags_FittingPolicyResizeDown))
tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^
ImGuiTabBarFlags_FittingPolicyResizeDown);
if (ImGui::CheckboxFlags("ImGuiTabBarFlags_FittingPolicyScroll",
&tab_bar_flags,
ImGuiTabBarFlags_FittingPolicyScroll))
tab_bar_flags &= ~(ImGuiTabBarFlags_FittingPolicyMask_ ^
ImGuiTabBarFlags_FittingPolicyScroll);
if (ImGui::BeginTabBar("MyTabBar", tab_bar_flags)) {
// Demo Trailing Tabs: click the "+" button to add a new tab (in your app
// you may want to use a font icon instead of the "+") Note that we submit
// it before the regular tabs, but because of the ImGuiTabItemFlags_Trailing
// flag it will always appear at the end.
if (show_trailing_button)
if (ImGui::TabItemButton(
"+", ImGuiTabItemFlags_Trailing | ImGuiTabItemFlags_NoTooltip))
active_rooms_.push_back(next_tab_id++); // Add new tab
// Submit our regular tabs
for (int n = 0; n < active_rooms_.Size;) {
bool open = true;
if (ImGui::BeginTabItem(
zelda3::dungeon::kRoomNames[active_rooms_[n]].data(), &open,
ImGuiTabItemFlags_None)) {
DrawDungeonCanvas(active_rooms_[n]);
ImGui::EndTabItem();
}
if (!open)
active_rooms_.erase(active_rooms_.Data + n);
else
n++;
}
ImGui::EndTabBar();
}
ImGui::Separator();
}
void DungeonEditor::DrawDungeonCanvas(int room_id) {
ImGui::BeginGroup();
gui::InputHexByte("Layout", &rooms_[room_id].layout);
ImGui::SameLine();
gui::InputHexByte("Blockset", &rooms_[room_id].blockset);
ImGui::SameLine();
gui::InputHexByte("Spriteset", &rooms_[room_id].spriteset);
ImGui::SameLine();
gui::InputHexByte("Palette", &rooms_[room_id].palette);
gui::InputHexByte("Floor1", &rooms_[room_id].floor1);
ImGui::SameLine();
gui::InputHexByte("Floor2", &rooms_[room_id].floor2);
ImGui::SameLine();
gui::InputHexWord("Message ID", &rooms_[room_id].message_id_);
ImGui::SameLine();
ImGui::EndGroup();
canvas_.DrawBackground();
canvas_.DrawContextMenu();
canvas_.DrawGrid();
canvas_.DrawOverlay();
}
void DungeonEditor::DrawToolset() {
if (ImGui::BeginTable("DWToolset", 9, ImGuiTableFlags_SizingFixedFit,
ImVec2(0, 0))) {
ImGui::TableSetupColumn("#undoTool");
ImGui::TableSetupColumn("#redoTool");
ImGui::TableSetupColumn("#history");
ImGui::TableSetupColumn("#separator");
ImGui::TableSetupColumn("#bg1Tool");
ImGui::TableSetupColumn("#bg2Tool");
ImGui::TableSetupColumn("#bg3Tool");
ImGui::TableSetupColumn("#itemTool");
ImGui::TableSetupColumn("#spriteTool");
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_UNDO);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_REDO);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_MANAGE_HISTORY);
ImGui::TableNextColumn();
ImGui::Text(ICON_MD_MORE_VERT);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_FILTER_1);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_FILTER_2);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_FILTER_3);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_GRASS);
ImGui::TableNextColumn();
ImGui::Button(ICON_MD_PEST_CONTROL_RODENT);
ImGui::EndTable();
}
}
void DungeonEditor::DrawRoomGraphics() {
room_gfx_canvas_.DrawBackground(ImVec2(256 + 1, 0x10 * 0x40 + 1));
room_gfx_canvas_.DrawContextMenu();
room_gfx_canvas_.DrawTileSelector(32);
room_gfx_canvas_.DrawBitmap(room_gfx_bmp_, 2, is_loaded_);
room_gfx_canvas_.DrawGrid(32.0f);
room_gfx_canvas_.DrawOverlay();
}
void DungeonEditor::DrawTileSelector() {
if (ImGui::BeginTabBar("##TabBar", ImGuiTabBarFlags_FittingPolicyScroll)) {
if (ImGui::BeginTabItem("Room Graphics")) {
if (ImGuiID child_id = ImGui::GetID((void*)(intptr_t)3);
ImGui::BeginChild(child_id, ImGui::GetContentRegionAvail(), true,
ImGuiWindowFlags_AlwaysVerticalScrollbar)) {
DrawRoomGraphics();
}
ImGui::EndChild();
ImGui::EndTabItem();
}
ImGui::EndTabBar();
}
}
} // namespace editor
} // namespace app
} // namespace yaze