6#include "absl/strings/str_format.h"
10#include "imgui/imgui.h"
11#include "imgui/imgui_internal.h"
46 return ImGui::GetStyle().Colors[idx];
81 return ImVec4(1.0f, 0.9f, 0.0f, 0.85f);
86 return ImVec4(0.9f, 1.0f, 1.0f, 0.85f);
91 return ImVec4(1.0f, 0.2f, 0.2f, 0.85f);
96 return ImVec4(1.0f, 0.3f, 1.0f, 0.85f);
105 return ImVec4(1.0f, 0.5f, 0.0f, 1.0f);
127 ImGui::PushStyleColor(ImGuiCol_Text, color);
128 ImGui::TextUnformatted(text);
129 ImGui::PopStyleColor();
133 ImGui::PushStyleColor(ImGuiCol_Text, color);
136 ImGui::TextV(fmt, args);
138 ImGui::PopStyleColor();
149 ImGui::TextV(fmt, args);
151 ImGui::PopStyleColor();
163 ImVec4(base.x * 1.2f, base.y * 1.2f, base.z * 1.2f, base.w),
164 ImVec4(base.x * 0.8f, base.y * 0.8f, base.z * 0.8f, base.w),
173 ImVec4(base.x * 1.2f, base.y * 1.2f, base.z * 1.2f, base.w),
174 ImVec4(base.x * 0.8f, base.y * 0.8f, base.z * 0.8f, base.w),
183 ImVec4(base.x * 1.2f, base.y * 1.2f, base.z * 1.2f, base.w),
184 ImVec4(base.x * 0.8f, base.y * 0.8f, base.z * 0.8f, base.w),
193 ImVec4(base.x * 1.2f, base.y * 1.2f, base.z * 1.2f, base.w),
194 ImVec4(base.x * 0.8f, base.y * 0.8f, base.z * 0.8f, base.w),
206 ImGui::PopStyleColor();
215 if (label_width > 0.0f) {
216 ImGui::Text(
"%s:", label);
217 ImGui::SameLine(label_width);
219 ImGui::TextUnformatted(label);
222 ImGui::PushItemWidth(ImGui::GetContentRegionAvail().x * 0.6f);
226 ImGui::PopItemWidth();
231 ImGuiTableFlags extra_flags) {
232 ImGuiTableFlags flags =
233 ImGuiTableFlags_Borders | ImGuiTableFlags_SizingFixedFit | extra_flags;
234 if (ImGui::BeginTable(
id, columns, flags)) {
235 ImGui::TableSetupColumn(
"Property", ImGuiTableColumnFlags_WidthFixed, 150);
236 ImGui::TableSetupColumn(
"Value", ImGuiTableColumnFlags_WidthStretch);
247 ImGui::TableNextColumn();
248 ImGui::Text(
"%s", label);
249 ImGui::TableNextColumn();
250 ImGui::TextWrapped(
"%s", value);
254 ImGui::TableNextColumn();
255 ImGui::Text(
"%s", label);
256 ImGui::TableNextColumn();
257 ImGui::Text(
"%d", value);
261 ImGui::TableNextColumn();
262 ImGui::Text(
"%s", label);
263 ImGui::TableNextColumn();
264 ImGui::Text(tr(
"0x%02X"), value);
268 ImGui::TableNextColumn();
269 ImGui::Text(
"%s", label);
270 ImGui::TableNextColumn();
271 ImGui::Text(tr(
"0x%04X"), value);
274void SectionHeader(
const char* icon,
const char* label,
const ImVec4& color) {
275 ImGui::TextColored(color,
"%s %s", icon, label);
283bool IconButton(
const char* icon,
const char* label,
const ImVec2& size) {
284 std::string button_text = std::string(icon) +
" " + std::string(label);
285 return ImGui::Button(button_text.c_str(), size);
289 ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0));
290 bool clicked = ImGui::Button(icon);
291 ImGui::PopStyleColor();
293 if (tooltip && ImGui::IsItemHovered()) {
294 ImGui::SetTooltip(
"%s", tooltip);
319 ImGui::PushStyleColor(ImGuiCol_Button, color);
320 ImGui::PushStyleColor(
321 ImGuiCol_ButtonHovered,
322 ImVec4(color.x * 1.2f, color.y * 1.2f, color.z * 1.2f, color.w));
323 ImGui::PushStyleColor(
324 ImGuiCol_ButtonActive,
325 ImVec4(color.x * 0.8f, color.y * 0.8f, color.z * 0.8f, color.w));
327 bool result = ImGui::Button(label, size);
329 ImGui::PopStyleColor(3);
333bool StyledButton(
const char* label,
const ImVec4& color,
const ImVec2& size) {
334 ImGui::PushStyleColor(ImGuiCol_Button, color);
335 ImGui::PushStyleColor(
336 ImGuiCol_ButtonHovered,
337 ImVec4(color.x * 1.2f, color.y * 1.2f, color.z * 1.2f, color.w));
338 ImGui::PushStyleColor(
339 ImGuiCol_ButtonActive,
340 ImVec4(color.x * 0.8f, color.y * 0.8f, color.z * 0.8f, color.w));
342 bool result = ImGui::Button(label, size);
344 ImGui::PopStyleColor(3);
349 const char* tooltip) {
350 const char* icon = *state ? icon_on : icon_off;
353 ImGui::PushStyleColor(ImGuiCol_Button, color);
354 bool result = ImGui::SmallButton(icon);
355 ImGui::PopStyleColor();
360 if (tooltip && ImGui::IsItemHovered()) {
361 ImGui::SetTooltip(
"%s", tooltip);
374 bool result = ImGui::Button(label, size);
377 ImGui::PopStyleColor(3);
385 if (ImGui::IsItemHovered()) {
386 ImGui::BeginTooltip();
387 ImGui::PushTextWrapPos(ImGui::GetFontSize() * 35.0f);
388 ImGui::TextUnformatted(desc);
389 ImGui::PopTextWrapPos();
395 ImGui::SeparatorText(label);
418 ImGui::PushStyleColor(ImGuiCol_Button, color);
419 ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 10.0f);
420 ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(8, 3));
421 ImGui::SmallButton(text);
422 ImGui::PopStyleVar(2);
423 ImGui::PopStyleColor();
431 ImGuiWindowFlags flags = scrollable ? ImGuiWindowFlags_AlwaysVerticalScrollbar
432 : ImGuiWindowFlags_None;
433 ImGui::BeginChild(
id, ImVec2(0, 0),
true, flags);
442 snprintf(tab_label,
sizeof(tab_label),
"%s %s", icon, label);
443 return ImGui::BeginTabItem(tab_label, p_open);
447 const char* confirm_text,
const char* cancel_text) {
448 bool confirmed =
false;
450 if (ImGui::BeginPopupModal(
id,
nullptr, ImGuiWindowFlags_AlwaysAutoResize)) {
451 ImGui::Text(
"%s", title);
453 ImGui::TextWrapped(
"%s", message);
458 ImGui::CloseCurrentPopup();
462 if (ImGui::Button(cancel_text, ImVec2(120, 0))) {
463 ImGui::CloseCurrentPopup();
480 ImDrawList* draw_list = ImGui::GetWindowDrawList();
481 ImVec2 pos = ImGui::GetCursorScreenPos();
485 pos.y += ImGui::GetTextLineHeight() * 0.5f;
487 draw_list->AddCircleFilled(pos, radius, ImGui::GetColorU32(color));
489 ImGui::SetCursorPosX(ImGui::GetCursorPosX() + radius * 2 + 8);
490 ImGui::Text(
"%s", label);
492 if (tooltip && ImGui::IsItemHovered()) {
493 ImGui::SetTooltip(
"%s", tooltip);
501 if (strcmp(provider,
"ollama") == 0) {
503 }
else if (strcmp(provider,
"gemini") == 0) {
505 }
else if (strcmp(provider,
"anthropic") == 0) {
507 }
else if (strcmp(provider,
"openai") == 0) {
511 ImGui::PushStyleColor(ImGuiCol_Text, color);
512 ImGui::Text(
"[%s]", provider);
513 ImGui::PopStyleColor();
520 ImGui::PushStyleColor(ImGuiCol_Text, color);
521 ImGui::Text(
"%s %s", icon, version);
522 ImGui::PopStyleColor();
538 ImGui::Dummy(ImVec2(0, pixels));
542 ImGui::Dummy(ImVec2(pixels, 0));
547 float text_width = ImGui::CalcTextSize(text).x;
548 ImGui::SetCursorPosX((ImGui::GetContentRegionAvail().x - text_width) * 0.5f);
549 ImGui::Text(
"%s", text);
553 ImGui::SetCursorPosX(ImGui::GetCursorPosX() +
554 ImGui::GetContentRegionAvail().x - width);
563 0.5f * sinf(
static_cast<float>(ImGui::GetTime()) * speed * 2.0f);
567 static double start_time = 0.0;
568 double current_time = ImGui::GetTime();
570 if (start_time == 0.0) {
571 start_time = current_time;
574 float elapsed =
static_cast<float>(current_time - start_time);
575 float alpha = ImClamp(elapsed / duration, 0.0f, 1.0f);
586 ImGui::PushStyleVar(ImGuiStyleVar_Alpha,
591 ImGui::PopStyleVar();
595 ImDrawList* draw_list = ImGui::GetWindowDrawList();
596 ImVec2 pos = ImGui::GetCursorScreenPos();
600 const float rotation =
static_cast<float>(ImGui::GetTime()) * 3.0f;
601 const int segments = 16;
602 const float thickness = 3.0f;
604 const float start_angle = rotation;
605 const float end_angle = rotation +
IM_PI * 1.5f;
607 draw_list->PathArcTo(pos, radius, start_angle, end_angle, segments);
608 draw_list->PathStroke(ImGui::GetColorU32(
GetAccentColor()), thickness);
611 ImGui::SetCursorPosX(ImGui::GetCursorPosX() + radius * 2 + 8);
612 ImGui::Text(
"%s", label);
614 ImGui::Dummy(ImVec2(radius * 2 + 8, radius * 2 + 8));
623 float available = ImGui::GetContentRegionAvail().x;
624 float target = available * ratio;
626 if (target < min_width)
628 if (target > max_width)
634 float available = ImGui::GetContentRegionAvail().x;
635 float col_width = available / count;
637 if (col_width < min_col_width) {
638 col_width = min_col_width;
641 for (
int i = 0; i < count; ++i) {
642 ImGui::TableSetupColumn(
"##col", ImGuiTableColumnFlags_WidthFixed,
647static int g_two_col_table_active = 0;
650 ImGuiTableFlags flags = ImGuiTableFlags_Resizable |
651 ImGuiTableFlags_BordersInnerV |
652 ImGuiTableFlags_SizingStretchProp;
654 if (ImGui::BeginTable(
id, 2, flags)) {
655 float available = ImGui::GetContentRegionAvail().x;
656 ImGui::TableSetupColumn(
"##left", ImGuiTableColumnFlags_None,
657 available * split_ratio);
658 ImGui::TableSetupColumn(
"##right", ImGuiTableColumnFlags_None,
659 available * (1.0f - split_ratio));
660 ImGui::TableNextRow();
661 ImGui::TableNextColumn();
662 g_two_col_table_active++;
667 ImGui::TableNextColumn();
672 g_two_col_table_active--;
681 ImGui::PushItemWidth(60);
683 ImGui::InputScalar(
"##hex", ImGuiDataType_U8, value,
nullptr,
nullptr,
684 "%02X", ImGuiInputTextFlags_CharsHexadecimal);
685 ImGui::PopItemWidth();
692 ImGui::PushItemWidth(80);
694 ImGui::InputScalar(
"##hex", ImGuiDataType_U16, value,
nullptr,
nullptr,
695 "%04X", ImGuiInputTextFlags_CharsHexadecimal);
696 ImGui::PopItemWidth();
701bool IconCombo(
const char* icon,
const char* label,
int* current,
702 const char*
const items[],
int count) {
703 ImGui::Text(
"%s", icon);
705 return ImGui::Combo(label, current, items, count);
const Theme & GetCurrentTheme() const
static ThemeManager & Get()
#define ICON_MD_LOCK_OPEN
#define ICON_MD_CHECK_CIRCLE
#define ICON_MD_HELP_OUTLINE
void RightAlign(float width)
void VerticalSpacing(float pixels)
void EndCanvasContainer()
ImVec4 ConvertColorToImVec4(const Color &color)
std::string MakePanelTitle(const std::string &title)
ImVec4 GetVanillaRomColor()
void PropertyRow(const char *label, const char *value)
void ColoredText(const char *text, const ImVec4 &color)
ButtonColorSet GetWarningButtonColors()
ButtonColorSet GetDangerButtonColors()
bool ToggleIconButton(const char *icon_on, const char *icon_off, bool *state, const char *tooltip)
void BeginField(const char *label, float label_width)
void SeparatorText(const char *label)
void StatusIndicator(const char *label, bool active, const char *tooltip)
ImVec4 GetSelectedColor()
void BeginTwoColumns(const char *id, float split_ratio)
void RomVersionBadge(const char *version, bool is_vanilla)
bool EditorTabItem(const char *icon, const char *label, bool *p_open)
ImVec4 GetEntranceColor()
void CenterText(const char *text)
bool LabeledInputHex(const char *label, uint8_t *value)
void SectionHeader(const char *icon, const char *label, const ImVec4 &color)
void LockIndicator(bool locked, const char *label)
bool IconButton(const char *icon, const char *label, const ImVec2 &size)
void PropertyRowHex(const char *label, uint8_t value)
bool ToggleButton(const char *label, bool active, const ImVec2 &size)
float GetResponsiveWidth(float min_width, float max_width, float ratio)
void SetupResponsiveColumns(int count, float min_col_width)
ButtonColorSet GetSuccessButtonColors()
bool ColoredButton(const char *label, ButtonType type, const ImVec2 &size)
bool BeginPropertyTable(const char *id, int columns, ImGuiTableFlags extra_flags)
void BeginCanvasContainer(const char *id, bool scrollable)
bool IconCombo(const char *icon, const char *label, int *current, const char *const items[], int count)
void LoadingSpinner(const char *label, float radius)
ImVec4 GetDisabledColor()
void ColoredTextF(const ImVec4 &color, const char *fmt,...)
bool ConfirmationDialog(const char *id, const char *title, const char *message, const char *confirm_text, const char *cancel_text)
ImVec4 GetModifiedColor()
bool StyledButton(const char *label, const ImVec4 &color, const ImVec2 &size)
float GetFadeIn(float duration)
float GetPulseAlpha(float speed)
void PushPulseEffect(float speed)
void HelpMarker(const char *desc)
Color GetThemeColor(const std::string &color_name)
void RenderProviderBadge(const char *provider)
void StatusBadge(const char *text, ButtonType type)
void ThemedText(const char *text, SemanticColor color)
void HorizontalSpacing(float pixels)
void ThemedTextF(SemanticColor color, const char *fmt,...)
ImVec4 GetCustomRomColor()
ButtonColorSet GetPrimaryButtonColors()
ImVec4 ResolveSemanticColor(SemanticColor color)