yaze 0.3.2
Link to the Past ROM Editor
 
Loading...
Searching...
No Matches
window_sidebar.cc
Go to the documentation of this file.
2#include "util/i18n/tr.h"
3
4#include <algorithm>
5#include <cctype>
6#include <string>
7
8#include "absl/strings/str_format.h"
10#include "app/gui/core/icons.h"
17#include "core/color.h"
18#include "imgui/imgui.h"
19
20namespace yaze {
21namespace editor {
22
23namespace {
24
25std::string LowercaseCopy(std::string value) {
26 std::transform(
27 value.begin(), value.end(), value.begin(),
28 [](unsigned char c) { return static_cast<char>(::tolower(c)); });
29 return value;
30}
31
32bool MatchesWindowSearch(const std::string& query,
33 const WindowDescriptor& window) {
35 query, window.display_name, window.card_id, window.shortcut_hint);
36}
37
38bool IsDungeonPanelModeWindow(const std::string& window_id) {
40}
41
42} // namespace
43
45 WorkspaceWindowManager& window_manager,
46 std::function<bool()> is_dungeon_workbench_mode,
47 std::function<void(bool)> set_dungeon_workflow_mode,
48 std::function<float()> get_bottom_reserved_height)
49 : window_manager_(window_manager),
50 is_dungeon_workbench_mode_(std::move(is_dungeon_workbench_mode)),
51 set_dungeon_workflow_mode_(std::move(set_dungeon_workflow_mode)),
52 get_bottom_reserved_height_(std::move(get_bottom_reserved_height)) {}
53
54bool WindowSidebar::MatchesWindowSearch(const std::string& query,
55 const std::string& display_name,
56 const std::string& window_id,
57 const std::string& shortcut_hint) {
58 if (query.empty()) {
59 return true;
60 }
61
62 const std::string search_str = LowercaseCopy(query);
63 return LowercaseCopy(display_name).find(search_str) != std::string::npos ||
64 LowercaseCopy(window_id).find(search_str) != std::string::npos ||
65 LowercaseCopy(shortcut_hint).find(search_str) != std::string::npos;
66}
67
68bool WindowSidebar::IsDungeonWindowModeTarget(const std::string& window_id) {
69 const bool is_room_window = window_id.rfind("dungeon.room_", 0) == 0;
70 return window_id == "dungeon.room_selector" ||
71 window_id == "dungeon.room_matrix" || is_room_window;
72}
73
74void WindowSidebar::Draw(size_t session_id, const std::string& category,
75 std::function<bool()> has_rom) {
76 const auto& theme = gui::ThemeManager::Get().GetCurrentTheme();
77 const ImGuiViewport* viewport = ImGui::GetMainViewport();
78 const float bar_width = WorkspaceWindowManager::GetSidebarWidth();
79 const float panel_width =
80 window_manager_.GetActiveSidePanelWidth(viewport->WorkSize.x);
81
82 const float top_inset = gui::LayoutHelpers::GetTopInset();
83 const auto safe_area = gui::LayoutHelpers::GetSafeAreaInsets();
84 const float bottom_reserved =
86 ? std::max(0.0f, get_bottom_reserved_height_())
87 : 0.0f;
88 const float panel_height =
89 std::max(0.0f, viewport->WorkSize.y - top_inset - safe_area.bottom -
90 bottom_reserved);
91
92 gui::FixedPanel panel(
93 "##SidePanel",
94 ImVec2(viewport->WorkPos.x + bar_width, viewport->WorkPos.y + top_inset),
95 ImVec2(panel_width, panel_height),
96 {.bg = gui::ConvertColorToImVec4(theme.surface),
97 .padding = {8.0f, 8.0f},
98 .border_size = 1.0f,
99 .rounding = 0.0f},
100 ImGuiWindowFlags_NoFocusOnAppearing);
101
102 if (!panel) {
103 return;
104 }
105
106 ImGui::PushFont(ImGui::GetIO().Fonts->Fonts[0]);
107 ImGui::Text("%s", category.c_str());
108 ImGui::PopFont();
109
110 float avail_width = ImGui::GetContentRegionAvail().x;
111 const ImVec2 chrome_icon_size = gui::IconSize::Small();
112 ImGui::SameLine(ImGui::GetCursorPosX() + avail_width - chrome_icon_size.x);
114 "Collapse Sidebar", false, ImVec4(0, 0, 0, 0),
115 "window_sidebar", "collapse_side_panel")) {
117 }
118
119 ImGui::Separator();
120 ImGui::Spacing();
121
122 const ImVec2 search_button_size = gui::IconSize::Small();
123 const float standard_spacing =
124 std::clamp(gui::LayoutHelpers::GetStandardSpacing(), 4.0f, 8.0f);
125 const float compact_spacing = std::max(4.0f, standard_spacing * 0.75f);
126 const float search_spacing = compact_spacing;
127 const float search_width =
128 std::max(140.0f, ImGui::GetContentRegionAvail().x - search_button_size.x -
129 search_spacing);
130 ImGui::SetNextItemWidth(search_width);
131 ImGui::InputTextWithHint("##SidebarSearch", ICON_MD_SEARCH " Filter...",
133 ImGui::SameLine(0.0f, search_spacing);
134 const bool filter_empty = sidebar_search_[0] == '\0';
135 if (filter_empty) {
136 ImGui::BeginDisabled();
137 }
138 if (gui::TransparentIconButton(ICON_MD_CLEAR, search_button_size,
139 "Clear filter", false,
140 gui::GetTextSecondaryVec4(), "window_sidebar",
141 "clear_sidebar_filter")) {
142 sidebar_search_[0] = '\0';
143 }
144 if (filter_empty) {
145 ImGui::EndDisabled();
146 }
147
148 auto read_dungeon_workbench_mode = [&]() -> bool {
149 if (category != "Dungeon") {
150 return false;
151 }
154 }
155 return window_manager_.IsWindowOpen(session_id, "dungeon.workbench");
156 };
157 bool dungeon_workbench_mode = read_dungeon_workbench_mode();
158
159 auto switch_to_dungeon_workbench_mode = [&]() -> bool {
160 if (category != "Dungeon" || dungeon_workbench_mode) {
161 return false;
162 }
165 dungeon_workbench_mode = true;
166 return true;
167 }
168 window_manager_.OpenWindow(session_id, "dungeon.workbench");
169 // Workbench-local tool windows (Object/Door/Sprite/Item Selector, Palette,
170 // Room Graphics/Tags, Custom Collision, Water Fill, Minecart) are NOT
171 // auto-closed here. Users can keep a standalone copy open alongside the
172 // Workbench drawer's embedded copy if they prefer that layout.
173 for (const auto& descriptor :
174 window_manager_.GetWindowsInCategory(session_id, "Dungeon")) {
175 const std::string& window_id = descriptor.card_id;
176 if (window_id == "dungeon.workbench") {
177 continue;
178 }
179 if (window_manager_.IsWindowPinned(session_id, window_id)) {
180 continue;
181 }
182 if (IsDungeonPanelModeWindow(window_id)) {
183 window_manager_.CloseWindow(session_id, window_id);
184 }
185 }
186 dungeon_workbench_mode = read_dungeon_workbench_mode();
187 return dungeon_workbench_mode;
188 };
189
190 auto switch_to_dungeon_window_mode = [&]() -> bool {
191 if (category != "Dungeon" || !dungeon_workbench_mode) {
192 return false;
193 }
196 dungeon_workbench_mode = false;
197 return true;
198 }
199 window_manager_.CloseWindow(session_id, "dungeon.workbench");
200 window_manager_.OpenWindow(session_id, "dungeon.room_selector");
201 window_manager_.OpenWindow(session_id, "dungeon.room_matrix");
202 dungeon_workbench_mode = read_dungeon_workbench_mode();
203 return !dungeon_workbench_mode;
204 };
205
206 auto ensure_dungeon_window_mode_for_window =
207 [&](const std::string& window_id) -> bool {
208 if (category != "Dungeon" || !dungeon_workbench_mode ||
209 !IsDungeonPanelModeWindow(window_id)) {
210 return false;
211 }
212 return switch_to_dungeon_window_mode();
213 };
214
215 if (category == "Dungeon") {
216 ImGui::Spacing();
217 ImGui::TextDisabled(ICON_MD_WORKSPACES " Workflow");
218 ImGui::Spacing();
219
220 const float workflow_gap = compact_spacing;
221 const float workflow_min_button_width = 96.0f;
222 const float workflow_available_width =
223 std::max(1.0f, ImGui::GetContentRegionAvail().x);
224 const bool stack_workflow_buttons =
225 workflow_available_width <=
226 (workflow_min_button_width * 2.0f + workflow_gap);
227 const float workflow_button_width =
228 stack_workflow_buttons
229 ? workflow_available_width
230 : std::max(workflow_min_button_width,
231 (workflow_available_width - workflow_gap) * 0.5f);
232 const float workflow_button_height =
234 auto draw_workflow_button =
235 [&](const char* id, const char* icon, const char* label, bool active,
236 const char* tooltip, const ImVec2& button_size) -> bool {
237 const ImVec4 active_bg = gui::GetPrimaryVec4();
238 const ImVec4 inactive_bg = gui::GetSurfaceContainerHighVec4();
239 const ImVec4 inactive_hover = gui::GetSurfaceContainerHighestVec4();
241 {{ImGuiCol_Button, active ? active_bg : inactive_bg},
242 {ImGuiCol_ButtonHovered, active ? active_bg : inactive_hover},
243 {ImGuiCol_ButtonActive, active ? active_bg : inactive_hover}});
244 const std::string button_label =
245 absl::StrFormat("%s %s##%s", icon, label, id);
246 const bool clicked = ImGui::Button(button_label.c_str(), button_size);
247 if (ImGui::IsItemHovered() && tooltip && *tooltip) {
248 ImGui::SetTooltip("%s", tooltip);
249 }
250 return clicked;
251 };
252 const ImVec2 workflow_button_size(workflow_button_width,
253 workflow_button_height);
254
255 if (draw_workflow_button(
256 "workflow_workbench", ICON_MD_WORKSPACES, "Workbench",
257 dungeon_workbench_mode,
258 "Workbench mode: integrated room browser + inspector",
259 workflow_button_size)) {
260 switch_to_dungeon_workbench_mode();
261 }
262 if (!stack_workflow_buttons) {
263 ImGui::SameLine(0.0f, workflow_gap);
264 }
265 if (draw_workflow_button(
266 "workflow_windows", ICON_MD_VIEW_QUILT, "Windows",
267 !dungeon_workbench_mode,
268 "Window mode: standalone Room List + Room Matrix + room windows",
269 workflow_button_size)) {
270 switch_to_dungeon_window_mode();
271 }
272 ImGui::Spacing();
273 ImGui::Separator();
274 ImGui::Spacing();
275 }
276
277 ImGui::Spacing();
278
279 const bool rom_loaded = has_rom ? has_rom() : true;
280 const bool disable_windows = !rom_loaded && category != "Emulator";
281
282 const auto category_windows =
283 window_manager_.GetWindowsInCategory(session_id, category);
284 int visible_windows_in_category = 0;
285 int total_windows_in_category = 0;
286 for (const auto& category_window : category_windows) {
287 ++total_windows_in_category;
288 if (category_window.visibility_flag && *category_window.visibility_flag) {
289 ++visible_windows_in_category;
290 }
291 }
292
293 ImGui::TextDisabled(tr("%d / %d visible"), visible_windows_in_category,
294 total_windows_in_category);
295 ImGui::Spacing();
296
297 const float action_gap = compact_spacing;
298 const float action_min_button_width = 84.0f;
299 const float action_available_width =
300 std::max(1.0f, ImGui::GetContentRegionAvail().x);
301 const bool stack_action_buttons =
302 action_available_width <=
303 (action_min_button_width * 3.0f + (action_gap * 2.0f));
304 const float action_button_width =
305 stack_action_buttons
306 ? action_available_width
307 : std::max(action_min_button_width,
308 (action_available_width - (action_gap * 2.0f)) / 3.0f);
309 const float action_button_height =
311 auto draw_action_button = [&](const char* id, const char* icon,
312 const char* label, const char* tooltip,
313 const ImVec2& button_size) -> bool {
314 const std::string button_label =
315 absl::StrFormat("%s %s##%s", icon, label, id);
316 const bool clicked = ImGui::Button(button_label.c_str(), button_size);
317 if (ImGui::IsItemHovered() && tooltip && *tooltip) {
318 ImGui::SetTooltip("%s", tooltip);
319 }
320 return clicked;
321 };
322 const ImVec2 action_button_size(action_button_width, action_button_height);
323
324 if (draw_action_button("open_window_browser", ICON_MD_APPS, "Browser",
325 "Open Window Browser", action_button_size)) {
327 }
328 if (!stack_action_buttons) {
329 ImGui::SameLine(0.0f, action_gap);
330 }
331
332 const bool bulk_actions_enabled =
333 !disable_windows && !(category == "Dungeon" && dungeon_workbench_mode);
334 bool bulk_action_hovered = false;
335 if (!bulk_actions_enabled) {
336 ImGui::BeginDisabled();
337 }
338 if (draw_action_button("show_category_windows", ICON_MD_VISIBILITY, "Show",
339 "Show all windows in this category",
340 action_button_size)) {
341 window_manager_.ShowAllWindowsInCategory(session_id, category);
342 }
343 if (!stack_action_buttons) {
344 ImGui::SameLine(0.0f, action_gap);
345 }
346 if (!bulk_actions_enabled &&
347 ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenDisabled)) {
348 bulk_action_hovered = true;
349 }
350 if (draw_action_button("hide_category_windows", ICON_MD_VISIBILITY_OFF,
351 "Hide", "Hide all windows in this category",
352 action_button_size)) {
353 window_manager_.HideAllWindowsInCategory(session_id, category);
354 }
355 if (!bulk_actions_enabled) {
356 if (ImGui::IsItemHovered(ImGuiHoveredFlags_AllowWhenDisabled)) {
357 bulk_action_hovered = true;
358 }
359 if (bulk_action_hovered && category == "Dungeon" &&
360 dungeon_workbench_mode) {
361 ImGui::SetTooltip(
362 tr("Switch to Window workflow to bulk-manage room windows."));
363 }
364 ImGui::EndDisabled();
365 }
366
367 ImGui::Spacing();
368
369 if (disable_windows) {
370 ImGui::TextUnformatted(ICON_MD_FOLDER_OPEN
371 " Open a ROM to enable this category");
372 ImGui::Spacing();
373 }
374
375 if (disable_windows) {
376 ImGui::BeginDisabled();
377 }
378
379 const auto pinned_windows = window_manager_.GetPinnedWindows();
380 const ImVec4 disabled_text = ImGui::GetStyleColorVec4(ImGuiCol_TextDisabled);
381 auto window_text_color = [&](bool visible) -> ImVec4 {
382 if (disable_windows) {
383 return disabled_text;
384 }
386 };
387 const float pin_button_side =
389 const ImVec2 pin_button_size(pin_button_side, pin_button_side);
390 auto draw_pin_toggle_button = [&](const std::string& widget_id,
391 bool pinned) -> bool {
392 ImGui::PushID(widget_id.c_str());
393 const ImVec4 pin_col = pinned ? gui::ConvertColorToImVec4(theme.primary)
395 const bool clicked = gui::TransparentIconButton(
396 pinned ? ICON_MD_PUSH_PIN : ICON_MD_PIN, pin_button_size,
397 pinned ? "Unpin window" : "Pin window", pinned, pin_col,
398 "window_sidebar", widget_id.c_str());
399 ImGui::PopID();
400 return clicked;
401 };
402
403 bool pinned_section_open = false;
404 if (sidebar_search_[0] == '\0' && !pinned_windows.empty()) {
405 bool has_pinned_in_category = false;
406 for (const auto& window_id : pinned_windows) {
407 const auto* window =
408 window_manager_.GetWindowDescriptor(session_id, window_id);
409 if (window && window->category == category) {
410 has_pinned_in_category = true;
411 break;
412 }
413 }
414
415 if (has_pinned_in_category) {
416 pinned_section_open = ImGui::CollapsingHeader(
417 ICON_MD_PUSH_PIN " Pinned Windows", ImGuiTreeNodeFlags_DefaultOpen);
418 if (pinned_section_open) {
419 for (const auto& window_id : pinned_windows) {
420 const auto* window =
421 window_manager_.GetWindowDescriptor(session_id, window_id);
422 if (!window || window->category != category) {
423 continue;
424 }
425
426 const bool visible =
427 window->visibility_flag ? *window->visibility_flag : false;
428
429 if (draw_pin_toggle_button("pin_" + window->card_id, true)) {
430 window_manager_.SetWindowPinned(session_id, window->card_id, false);
431 }
432
433 ImGui::SameLine(0.0f, compact_spacing);
434
435 std::string label = absl::StrFormat("%s %s", window->icon.c_str(),
436 window->display_name.c_str());
437 ImGui::PushID(
438 (std::string("pinned_select_") + window->card_id).c_str());
439 {
440 gui::StyleColorGuard text_color(ImGuiCol_Text,
441 window_text_color(visible));
442 ImVec2 item_size(ImGui::GetContentRegionAvail().x,
443 pin_button_size.y);
444 if (ImGui::Selectable(label.c_str(), visible,
445 ImGuiSelectableFlags_None, item_size)) {
446 const bool switched_mode =
447 ensure_dungeon_window_mode_for_window(window->card_id);
448 if (switched_mode) {
449 window_manager_.OpenWindow(session_id, window->card_id);
450 } else {
451 window_manager_.ToggleWindow(session_id, window->card_id);
452 }
453
454 const bool new_visible =
455 window->visibility_flag ? *window->visibility_flag : false;
456 if (new_visible) {
457 window_manager_.TriggerWindowClicked(window->category);
458 const std::string window_name =
460 if (!window_name.empty()) {
461 ImGui::SetWindowFocus(window_name.c_str());
462 }
463 }
464 }
465 }
466 ImGui::PopID();
467 }
468 ImGui::Spacing();
469 ImGui::Separator();
470 ImGui::Spacing();
471 }
472 }
473 }
474
475 auto windows = window_manager_.GetWindowsSortedByMRU(session_id, category);
476 const bool window_content_open = gui::LayoutHelpers::BeginContentChild(
477 "##WindowContent", ImVec2(0.0f, gui::UIConfig::kContentMinHeightList));
478 if (window_content_open) {
479 for (const auto& window : windows) {
480 if (!MatchesWindowSearch(sidebar_search_, window.display_name,
481 window.card_id, window.shortcut_hint)) {
482 continue;
483 }
484
485 const bool is_pinned = window_manager_.IsWindowPinned(window.card_id);
486 if (pinned_section_open && is_pinned) {
487 continue;
488 }
489
490 const bool visible =
491 window.visibility_flag ? *window.visibility_flag : false;
492
493 if (draw_pin_toggle_button("pin_" + window.card_id, is_pinned)) {
494 window_manager_.SetWindowPinned(session_id, window.card_id, !is_pinned);
495 }
496 ImGui::SameLine(0.0f, compact_spacing);
497
498 std::string label = absl::StrFormat("%s %s", window.icon.c_str(),
499 window.display_name.c_str());
500 ImGui::PushID((std::string("window_select_") + window.card_id).c_str());
501 {
502 gui::StyleColorGuard text_color(ImGuiCol_Text,
503 window_text_color(visible));
504 ImVec2 item_size(ImGui::GetContentRegionAvail().x, pin_button_size.y);
505 if (ImGui::Selectable(label.c_str(), visible, ImGuiSelectableFlags_None,
506 item_size)) {
507 const bool switched_mode =
508 ensure_dungeon_window_mode_for_window(window.card_id);
509 if (switched_mode) {
510 window_manager_.OpenWindow(session_id, window.card_id);
511 } else {
512 window_manager_.ToggleWindow(session_id, window.card_id);
513 }
514
515 const bool new_visible =
516 window.visibility_flag ? *window.visibility_flag : false;
517 if (new_visible) {
519 window_manager_.TriggerWindowClicked(window.category);
520 const std::string window_name =
522 if (!window_name.empty()) {
523 ImGui::SetWindowFocus(window_name.c_str());
524 }
525 }
526 }
527 }
528 ImGui::PopID();
529
530 if (ImGui::IsItemHovered() && !window.shortcut_hint.empty()) {
531 ImGui::SetTooltip("%s", window.shortcut_hint.c_str());
532 }
533 }
534 }
536
537 if (disable_windows) {
538 ImGui::EndDisabled();
539 }
540
541 const float handle_width = 6.0f;
542 const ImVec2 panel_pos = ImGui::GetWindowPos();
543 const float panel_draw_height = ImGui::GetWindowHeight();
544 ImGui::SetCursorScreenPos(
545 ImVec2(panel_pos.x + panel_width - handle_width * 0.5f, panel_pos.y));
546 ImGui::InvisibleButton("##SidePanelResizeHandle",
547 ImVec2(handle_width, panel_draw_height));
548 const bool handle_hovered = ImGui::IsItemHovered();
549 const bool handle_active = ImGui::IsItemActive();
550 if (handle_hovered || handle_active) {
551 ImGui::SetMouseCursor(ImGuiMouseCursor_ResizeEW);
552 }
553 if (handle_hovered && ImGui::IsMouseDoubleClicked(ImGuiMouseButton_Left)) {
555 }
556 if (handle_active) {
557 const float new_width = panel_width + ImGui::GetIO().MouseDelta.x;
558 window_manager_.SetActiveSidePanelWidth(new_width, viewport->WorkSize.x);
559 ImGui::SetTooltip(
560 tr("Width: %.0f px"),
561 window_manager_.GetActiveSidePanelWidth(viewport->WorkSize.x));
562 }
563
564 ImVec4 handle_color = gui::GetOutlineVec4();
565 handle_color.w = handle_active ? 0.95f : (handle_hovered ? 0.72f : 0.35f);
566 ImGui::GetWindowDrawList()->AddLine(
567 ImVec2(panel_pos.x + panel_width - 1.0f, panel_pos.y),
568 ImVec2(panel_pos.x + panel_width - 1.0f, panel_pos.y + panel_draw_height),
569 ImGui::GetColorU32(handle_color), handle_active ? 2.0f : 1.0f);
570}
571
572} // namespace editor
573} // namespace yaze
void Draw(size_t session_id, const std::string &category, std::function< bool()> has_rom)
std::function< void(bool)> set_dungeon_workflow_mode_
WindowSidebar(WorkspaceWindowManager &window_manager, std::function< bool()> is_dungeon_workbench_mode={}, std::function< void(bool)> set_dungeon_workflow_mode={}, std::function< float()> get_bottom_reserved_height={})
std::function< bool()> is_dungeon_workbench_mode_
static bool IsDungeonWindowModeTarget(const std::string &window_id)
WorkspaceWindowManager & window_manager_
std::function< float()> get_bottom_reserved_height_
static bool MatchesWindowSearch(const std::string &query, const std::string &display_name, const std::string &window_id, const std::string &shortcut_hint)
Central registry for all editor cards with session awareness and dependency injection.
void SetActiveSidePanelWidth(float width, float viewport_width=0.0f, bool notify=true)
void HideAllWindowsInCategory(size_t session_id, const std::string &category)
std::string GetWorkspaceWindowName(size_t session_id, const std::string &base_window_id) const
Resolve the exact ImGui window name for a panel by base ID.
std::vector< WindowDescriptor > GetWindowsInCategory(size_t session_id, const std::string &category) const
const WindowDescriptor * GetWindowDescriptor(size_t session_id, const std::string &base_window_id) const
void SetWindowPinned(size_t session_id, const std::string &base_window_id, bool pinned)
bool CloseWindow(size_t session_id, const std::string &base_window_id)
void TriggerWindowClicked(const std::string &category)
std::vector< std::string > GetPinnedWindows(size_t session_id) const
bool IsWindowOpen(size_t session_id, const std::string &base_window_id) const
float GetActiveSidePanelWidth(float viewport_width) const
bool OpenWindow(size_t session_id, const std::string &base_window_id)
std::vector< WindowDescriptor > GetWindowsSortedByMRU(size_t session_id, const std::string &category) const
bool IsWindowPinned(size_t session_id, const std::string &base_window_id) const
bool ToggleWindow(size_t session_id, const std::string &base_window_id)
void SetSidebarExpanded(bool expanded, bool notify=true)
void ShowAllWindowsInCategory(size_t session_id, const std::string &category)
void MarkWindowRecentlyUsed(const std::string &window_id)
RAII for fixed-position panels (activity bar, side panel, status bar).
static bool BeginContentChild(const char *id, const ImVec2 &min_size, bool border=false, ImGuiWindowFlags flags=0)
static void EndContentChild()
static SafeAreaInsets GetSafeAreaInsets()
static float GetStandardWidgetHeight()
static float GetStandardSpacing()
RAII guard for ImGui style colors.
Definition style_guard.h:27
const Theme & GetCurrentTheme() const
static ThemeManager & Get()
#define ICON_MD_FOLDER_OPEN
Definition icons.h:813
#define ICON_MD_VIEW_QUILT
Definition icons.h:2094
#define ICON_MD_APPS
Definition icons.h:168
#define ICON_MD_SEARCH
Definition icons.h:1673
#define ICON_MD_VISIBILITY
Definition icons.h:2101
#define ICON_MD_VISIBILITY_OFF
Definition icons.h:2102
#define ICON_MD_CHEVRON_LEFT
Definition icons.h:405
#define ICON_MD_PIN
Definition icons.h:1470
#define ICON_MD_CLEAR
Definition icons.h:416
#define ICON_MD_PUSH_PIN
Definition icons.h:1529
#define ICON_MD_WORKSPACES
Definition icons.h:2186
bool IsDungeonPanelModeWindow(const std::string &window_id)
bool TransparentIconButton(const char *icon, const ImVec2 &size, const char *tooltip, bool is_active, const ImVec4 &active_color, const char *panel_id, const char *anim_id)
Draw a transparent icon button (hover effect only).
ImVec4 ConvertColorToImVec4(const Color &color)
Definition color.h:134
ImVec4 GetSurfaceContainerHighestVec4()
ImVec4 GetPrimaryVec4()
ImVec4 GetTextSecondaryVec4()
ImVec4 GetSurfaceContainerHighVec4()
ImVec4 GetOutlineVec4()
ImVec4 GetOnSurfaceVec4()
Metadata for a dockable editor window (formerly PanelInfo)
static constexpr float kContentMinHeightList
Definition ui_config.h:54