mirror of
https://github.com/stenzek/duckstation.git
synced 2025-06-28 14:20:30 +00:00
FullscreenUI: Polish dialogs
This commit is contained in:
parent
77457a3b1d
commit
06da45b3f2
@ -84,6 +84,7 @@ public:
|
|||||||
using ImGuiFullscreen::ChoiceDialogOptions;
|
using ImGuiFullscreen::ChoiceDialogOptions;
|
||||||
using ImGuiFullscreen::FocusResetType;
|
using ImGuiFullscreen::FocusResetType;
|
||||||
|
|
||||||
|
using ImGuiFullscreen::LAYOUT_CENTER_ALIGN_TEXT;
|
||||||
using ImGuiFullscreen::LAYOUT_FOOTER_HEIGHT;
|
using ImGuiFullscreen::LAYOUT_FOOTER_HEIGHT;
|
||||||
using ImGuiFullscreen::LAYOUT_HORIZONTAL_MENU_ITEM_IMAGE_SIZE;
|
using ImGuiFullscreen::LAYOUT_HORIZONTAL_MENU_ITEM_IMAGE_SIZE;
|
||||||
using ImGuiFullscreen::LAYOUT_LARGE_FONT_SIZE;
|
using ImGuiFullscreen::LAYOUT_LARGE_FONT_SIZE;
|
||||||
@ -2961,7 +2962,7 @@ void FullscreenUI::DrawIntRangeSetting(SettingsInterface* bsi, std::string_view
|
|||||||
ImGui::PopStyleVar(2);
|
ImGui::PopStyleVar(2);
|
||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
}
|
}
|
||||||
@ -3016,7 +3017,7 @@ void FullscreenUI::DrawFloatRangeSetting(SettingsInterface* bsi, std::string_vie
|
|||||||
ImGui::PopStyleVar(2);
|
ImGui::PopStyleVar(2);
|
||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
|
||||||
@ -3136,7 +3137,7 @@ void FullscreenUI::DrawFloatSpinBoxSetting(SettingsInterface* bsi, std::string_v
|
|||||||
SetSettingsChanged(bsi);
|
SetSettingsChanged(bsi);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
|
||||||
@ -3249,7 +3250,7 @@ bool FullscreenUI::DrawIntRectSetting(SettingsInterface* bsi, std::string_view t
|
|||||||
|
|
||||||
ImGui::PopStyleVar(2);
|
ImGui::PopStyleVar(2);
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
|
||||||
@ -3368,7 +3369,7 @@ void FullscreenUI::DrawIntSpinBoxSetting(SettingsInterface* bsi, std::string_vie
|
|||||||
SetSettingsChanged(bsi);
|
SetSettingsChanged(bsi);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
|
||||||
@ -5106,7 +5107,8 @@ void FullscreenUI::DrawControllerSettingsPage()
|
|||||||
}
|
}
|
||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
|
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
@ -5983,7 +5985,7 @@ void FullscreenUI::DrawPostProcessingSettingsPage()
|
|||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
ImVec2(0.5f, 0.0f)))
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
}
|
}
|
||||||
@ -6052,7 +6054,7 @@ void FullscreenUI::DrawPostProcessingSettingsPage()
|
|||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
ImVec2(0.5f, 0.0f)))
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
}
|
}
|
||||||
@ -6466,7 +6468,8 @@ void FullscreenUI::DrawAchievementsLoginWindow()
|
|||||||
|
|
||||||
const bool login_enabled = (std::strlen(username) > 0 && std::strlen(password) > 0 && !is_logging_in);
|
const bool login_enabled = (std::strlen(username) > 0 && std::strlen(password) > 0 && !is_logging_in);
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_KEY, "Login"), login_enabled))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_KEY, "Login"), login_enabled, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
ImGuiFullscreen::OpenBackgroundProgressDialog(LOGIN_PROGRESS_NAME, FSUI_STR("Logging in to RetroAchievements..."),
|
ImGuiFullscreen::OpenBackgroundProgressDialog(LOGIN_PROGRESS_NAME, FSUI_STR("Logging in to RetroAchievements..."),
|
||||||
0, 0, 0);
|
0, 0, 0);
|
||||||
@ -6490,8 +6493,11 @@ void FullscreenUI::DrawAchievementsLoginWindow()
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_TIMES, "Cancel"), !is_logging_in))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_TIMES, "Cancel"), !is_logging_in,
|
||||||
|
LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
|
}
|
||||||
|
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
|
||||||
@ -6740,7 +6746,8 @@ void FullscreenUI::DrawPatchesOrCheatsSettingsPage(bool cheats)
|
|||||||
SetSettingsChanged(bsi);
|
SetSettingsChanged(bsi);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(FSUI_VSTR("OK"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
|
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
@ -7557,21 +7564,23 @@ bool FullscreenUI::OpenLoadStateSelectorForGameResume(const GameList::Entry* ent
|
|||||||
|
|
||||||
void FullscreenUI::DrawResumeStateSelector()
|
void FullscreenUI::DrawResumeStateSelector()
|
||||||
{
|
{
|
||||||
if (!BeginFixedPopupDialog(LayoutScale(30.0f), LayoutScale(40.0f), LayoutScale(820.0f, 645.0f)))
|
if (!BeginFixedPopupDialog(LayoutScale(30.0f), LayoutScale(40.0f), ImVec2(LayoutScale(550.0f), 0.0f)))
|
||||||
{
|
{
|
||||||
ClearSaveStateEntryList();
|
ClearSaveStateEntryList();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
SaveStateListEntry& entry = s_state.save_state_selector_slots.front();
|
SaveStateListEntry& entry = s_state.save_state_selector_slots.front();
|
||||||
SmallString time;
|
|
||||||
TimeToPrintableString(&time, entry.timestamp);
|
SmallString sick;
|
||||||
ImGui::TextWrapped(
|
sick.format(FSUI_FSTR("Do you want to continue from the automatic save created at {:%c}?"),
|
||||||
FSUI_CSTR("A resume save state created at %s was found.\n\nDo you want to load this save and continue?"),
|
fmt::localtime(entry.timestamp));
|
||||||
time.c_str());
|
ImGui::PushFontWeight(UIStyle.BoldFontWeight);
|
||||||
|
ImGuiFullscreen::TextAlignedMultiLine(0.5f, IMSTR_START_END(sick));
|
||||||
|
ImGui::PopFontWeight();
|
||||||
|
|
||||||
const GPUTexture* image = entry.preview_texture ? entry.preview_texture.get() : GetPlaceholderTexture().get();
|
const GPUTexture* image = entry.preview_texture ? entry.preview_texture.get() : GetPlaceholderTexture().get();
|
||||||
const float image_height = LayoutScale(250.0f);
|
const float image_height = LayoutScale(280.0f);
|
||||||
const float image_width =
|
const float image_width =
|
||||||
image_height * (static_cast<float>(image->GetWidth()) / static_cast<float>(image->GetHeight()));
|
image_height * (static_cast<float>(image->GetWidth()) / static_cast<float>(image->GetHeight()));
|
||||||
const ImVec2 pos(ImGui::GetCursorScreenPos() +
|
const ImVec2 pos(ImGui::GetCursorScreenPos() +
|
||||||
@ -7587,7 +7596,8 @@ void FullscreenUI::DrawResumeStateSelector()
|
|||||||
ResetFocusHere();
|
ResetFocusHere();
|
||||||
BeginMenuButtons();
|
BeginMenuButtons();
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_PLAY, "Load State")))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_PLAY, "Load State"), true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
std::string game_path = std::move(entry.game_path);
|
std::string game_path = std::move(entry.game_path);
|
||||||
std::string state_path = std::move(entry.state_path);
|
std::string state_path = std::move(entry.state_path);
|
||||||
@ -7596,7 +7606,8 @@ void FullscreenUI::DrawResumeStateSelector()
|
|||||||
DoStartPath(std::move(game_path), std::move(state_path));
|
DoStartPath(std::move(game_path), std::move(state_path));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_LIGHTBULB, "Clean Boot")))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_LIGHTBULB, "Clean Boot"), true,
|
||||||
|
LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
std::string game_path = std::move(entry.game_path);
|
std::string game_path = std::move(entry.game_path);
|
||||||
ClearSaveStateEntryList();
|
ClearSaveStateEntryList();
|
||||||
@ -7604,7 +7615,8 @@ void FullscreenUI::DrawResumeStateSelector()
|
|||||||
DoStartPath(std::move(game_path));
|
DoStartPath(std::move(game_path));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_FOLDER_MINUS, "Delete State")))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_FOLDER_MINUS, "Delete State"), true,
|
||||||
|
LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
if (FileSystem::DeleteFile(entry.state_path.c_str()))
|
if (FileSystem::DeleteFile(entry.state_path.c_str()))
|
||||||
{
|
{
|
||||||
@ -7619,10 +7631,13 @@ void FullscreenUI::DrawResumeStateSelector()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_WINDOW_CLOSE, "Cancel")))
|
if (MenuButtonWithoutSummary(FSUI_ICONVSTR(ICON_FA_WINDOW_CLOSE, "Cancel"), true,
|
||||||
|
LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
|
}
|
||||||
|
|
||||||
EndMenuButtons();
|
ImGuiFullscreen::EndHorizontalMenuButtons();
|
||||||
|
|
||||||
SetStandardSelectionFooterText(false);
|
SetStandardSelectionFooterText(false);
|
||||||
|
|
||||||
@ -8309,12 +8324,14 @@ void FullscreenUI::DrawGameGrid(const ImVec2& heading_size)
|
|||||||
// ellipise title, remove one character to make room
|
// ellipise title, remove one character to make room
|
||||||
draw_title.format("{}...", std::string_view(entry->title).substr(0, unclipped_size - 1));
|
draw_title.format("{}...", std::string_view(entry->title).substr(0, unclipped_size - 1));
|
||||||
RenderShadowedTextClipped(UIStyle.Font, UIStyle.MediumFontSize, UIStyle.NormalFontWeight, title_bb.Min,
|
RenderShadowedTextClipped(UIStyle.Font, UIStyle.MediumFontSize, UIStyle.NormalFontWeight, title_bb.Min,
|
||||||
title_bb.Max, text_color, draw_title, nullptr, ImVec2(0.5f, 0.0f), 0.0f, &title_bb);
|
title_bb.Max, text_color, draw_title, nullptr, LAYOUT_CENTER_ALIGN_TEXT, 0.0f,
|
||||||
|
&title_bb);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
RenderShadowedTextClipped(UIStyle.Font, UIStyle.MediumFontSize, UIStyle.NormalFontWeight, title_bb.Min,
|
RenderShadowedTextClipped(UIStyle.Font, UIStyle.MediumFontSize, UIStyle.NormalFontWeight, title_bb.Min,
|
||||||
title_bb.Max, text_color, entry->title, nullptr, ImVec2(0.5f, 0.0f), 0.0f, &title_bb);
|
title_bb.Max, text_color, entry->title, nullptr, LAYOUT_CENTER_ALIGN_TEXT, 0.0f,
|
||||||
|
&title_bb);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pressed)
|
if (pressed)
|
||||||
@ -9190,7 +9207,6 @@ TRANSLATE_NOOP("FullscreenUI", "9x");
|
|||||||
TRANSLATE_NOOP("FullscreenUI", "9x (18x Speed)");
|
TRANSLATE_NOOP("FullscreenUI", "9x (18x Speed)");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "9x (for 4K)");
|
TRANSLATE_NOOP("FullscreenUI", "9x (for 4K)");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "A cover already exists for this game. Are you sure that you want to overwrite it?");
|
TRANSLATE_NOOP("FullscreenUI", "A cover already exists for this game. Are you sure that you want to overwrite it?");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "A resume save state created at %s was found.\n\nDo you want to load this save and continue?");
|
|
||||||
TRANSLATE_NOOP("FullscreenUI", "AMOLED");
|
TRANSLATE_NOOP("FullscreenUI", "AMOLED");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "About");
|
TRANSLATE_NOOP("FullscreenUI", "About");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Account");
|
TRANSLATE_NOOP("FullscreenUI", "Account");
|
||||||
@ -9364,6 +9380,7 @@ TRANSLATE_NOOP("FullscreenUI", "Displays DualShock/DualSense button icons in the
|
|||||||
TRANSLATE_NOOP("FullscreenUI", "Displays popup messages on events such as achievement unlocks and leaderboard submissions.");
|
TRANSLATE_NOOP("FullscreenUI", "Displays popup messages on events such as achievement unlocks and leaderboard submissions.");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Displays popup messages when starting, submitting, or failing a leaderboard challenge.");
|
TRANSLATE_NOOP("FullscreenUI", "Displays popup messages when starting, submitting, or failing a leaderboard challenge.");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Dithering");
|
TRANSLATE_NOOP("FullscreenUI", "Dithering");
|
||||||
|
TRANSLATE_NOOP("FullscreenUI", "Do you want to continue from the automatic save created at {:%c}?");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Double-Click Toggles Fullscreen");
|
TRANSLATE_NOOP("FullscreenUI", "Double-Click Toggles Fullscreen");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Download Covers");
|
TRANSLATE_NOOP("FullscreenUI", "Download Covers");
|
||||||
TRANSLATE_NOOP("FullscreenUI", "Downloads covers from a user-specified URL template.");
|
TRANSLATE_NOOP("FullscreenUI", "Downloads covers from a user-specified URL template.");
|
||||||
|
@ -207,12 +207,14 @@ struct ALIGN_TO_CACHE_LINE UIState
|
|||||||
{
|
{
|
||||||
std::recursive_mutex shared_state_mutex;
|
std::recursive_mutex shared_state_mutex;
|
||||||
|
|
||||||
u32 menu_button_index = 0;
|
|
||||||
CloseButtonState close_button_state = CloseButtonState::None;
|
CloseButtonState close_button_state = CloseButtonState::None;
|
||||||
ImGuiDir has_pending_nav_move = ImGuiDir_None;
|
ImGuiDir has_pending_nav_move = ImGuiDir_None;
|
||||||
FocusResetType focus_reset_queued = FocusResetType::None;
|
FocusResetType focus_reset_queued = FocusResetType::None;
|
||||||
bool initialized = false;
|
bool initialized = false;
|
||||||
|
|
||||||
|
u32 menu_button_index = 0;
|
||||||
|
ImVec2 horizontal_menu_button_size = {};
|
||||||
|
|
||||||
LRUCache<std::string, std::shared_ptr<GPUTexture>> texture_cache{128, true};
|
LRUCache<std::string, std::shared_ptr<GPUTexture>> texture_cache{128, true};
|
||||||
std::shared_ptr<GPUTexture> placeholder_texture;
|
std::shared_ptr<GPUTexture> placeholder_texture;
|
||||||
std::deque<std::pair<std::string, Image>> texture_upload_queue;
|
std::deque<std::pair<std::string, Image>> texture_upload_queue;
|
||||||
@ -1554,6 +1556,101 @@ void ImGuiFullscreen::RenderShadowedTextClipped(ImFont* font, float font_size, f
|
|||||||
text_size_if_known, align, wrap_width, clip_rect);
|
text_size_if_known, align, wrap_width, clip_rect);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ImGuiFullscreen::TextAlignedMultiLine(float align_x, const char* text, const char* text_end, float wrap_width)
|
||||||
|
{
|
||||||
|
ImGuiWindow* window = ImGui::GetCurrentWindow();
|
||||||
|
if (window->SkipItems)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ImGuiContext& g = *GImGui;
|
||||||
|
IM_ASSERT(text != NULL);
|
||||||
|
|
||||||
|
if (text_end == NULL)
|
||||||
|
text_end = text + strlen(text);
|
||||||
|
|
||||||
|
const ImVec2 text_pos = window->DC.CursorPos;
|
||||||
|
const ImRect clip_rect = window->ClipRect;
|
||||||
|
wrap_width = (wrap_width < 0.0f) ? ImGui::GetContentRegionAvail().x : wrap_width;
|
||||||
|
|
||||||
|
ImVec2 pos = text_pos;
|
||||||
|
const char* text_remaining = text;
|
||||||
|
|
||||||
|
while (text_remaining < text_end)
|
||||||
|
{
|
||||||
|
// Find the end of the current wrapped line
|
||||||
|
const char* line_end = text_remaining;
|
||||||
|
float line_width = 0.0f;
|
||||||
|
|
||||||
|
// Process text word by word to find natural line breaks
|
||||||
|
while (line_end < text_end)
|
||||||
|
{
|
||||||
|
const char* word_start = line_end;
|
||||||
|
const char* word_end = word_start;
|
||||||
|
|
||||||
|
// Handle explicit newlines
|
||||||
|
if (*line_end == '\n')
|
||||||
|
{
|
||||||
|
line_end++;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find end of current word (including spaces)
|
||||||
|
while (word_end < text_end && *word_end != ' ' && *word_end != '\n')
|
||||||
|
word_end++;
|
||||||
|
|
||||||
|
// Include trailing space if present
|
||||||
|
if (word_end < text_end && *word_end == ' ')
|
||||||
|
word_end++;
|
||||||
|
|
||||||
|
// Calculate width if we add this word
|
||||||
|
ImVec2 word_size = ImGui::CalcTextSize(text_remaining, word_end, false, -1.0f);
|
||||||
|
|
||||||
|
// If adding this word would exceed wrap width, break here
|
||||||
|
if (word_size.x > wrap_width && line_end > text_remaining)
|
||||||
|
break;
|
||||||
|
|
||||||
|
line_end = word_end;
|
||||||
|
line_width = word_size.x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If we didn't advance at all, force at least one character to prevent infinite loop
|
||||||
|
if (line_end == text_remaining && line_end < text_end)
|
||||||
|
line_end++;
|
||||||
|
|
||||||
|
// Calculate actual line size for the determined line segment
|
||||||
|
ImVec2 line_size = ImGui::CalcTextSize(text_remaining, line_end, false, -1.0f);
|
||||||
|
|
||||||
|
// Calculate aligned position for this line
|
||||||
|
ImVec2 line_pos = pos;
|
||||||
|
if (align_x > 0.0f)
|
||||||
|
{
|
||||||
|
float offset_x = (wrap_width - line_size.x) * align_x;
|
||||||
|
line_pos.x += offset_x;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Render the line
|
||||||
|
if (line_size.x > 0.0f)
|
||||||
|
{
|
||||||
|
ImGui::RenderTextClipped(line_pos, ImVec2(line_pos.x + line_size.x, line_pos.y + line_size.y), text_remaining,
|
||||||
|
line_end, &line_size, ImVec2(0.0f, 0.0f), &clip_rect);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Move to next line
|
||||||
|
pos.y += g.FontSize + g.Style.ItemSpacing.y;
|
||||||
|
text_remaining = line_end;
|
||||||
|
|
||||||
|
// Skip trailing spaces at the beginning of the next line
|
||||||
|
while (text_remaining < text_end && *text_remaining == ' ')
|
||||||
|
text_remaining++;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Update cursor position to account for the rendered text
|
||||||
|
ImVec2 text_size = ImVec2(wrap_width, pos.y - text_pos.y);
|
||||||
|
ImRect bb(text_pos, text_pos + text_size);
|
||||||
|
ImGui::ItemSize(text_size);
|
||||||
|
ImGui::ItemAdd(bb, 0);
|
||||||
|
}
|
||||||
|
|
||||||
void ImGuiFullscreen::MenuHeading(std::string_view title, bool draw_line /*= true*/)
|
void ImGuiFullscreen::MenuHeading(std::string_view title, bool draw_line /*= true*/)
|
||||||
{
|
{
|
||||||
const float line_thickness = draw_line ? LayoutScale(1.0f) : 0.0f;
|
const float line_thickness = draw_line ? LayoutScale(1.0f) : 0.0f;
|
||||||
@ -1970,7 +2067,7 @@ bool ImGuiFullscreen::RangeButton(std::string_view title, std::string_view summa
|
|||||||
ImGui::PopStyleVar(2);
|
ImGui::PopStyleVar(2);
|
||||||
|
|
||||||
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
ImGui::SetCursorPosY(ImGui::GetCursorPosY() + LayoutScale(10.0f));
|
||||||
if (MenuButtonWithoutSummary(ok_text, true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(ok_text, true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
}
|
}
|
||||||
@ -2035,7 +2132,7 @@ bool ImGuiFullscreen::RangeButton(std::string_view title, std::string_view summa
|
|||||||
|
|
||||||
ImGui::PopStyleVar(2);
|
ImGui::PopStyleVar(2);
|
||||||
|
|
||||||
if (MenuButtonWithoutSummary(ok_text, true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, ImVec2(0.5f, 0.0f)))
|
if (MenuButtonWithoutSummary(ok_text, true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
{
|
{
|
||||||
CloseFixedPopupDialog();
|
CloseFixedPopupDialog();
|
||||||
}
|
}
|
||||||
@ -2122,6 +2219,125 @@ bool ImGuiFullscreen::EnumChoiceButtonImpl(std::string_view title, std::string_v
|
|||||||
return changed;
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ImGuiFullscreen::BeginHorizontalMenuButtons(u32 num_items, float max_item_width /* = 0.0f */,
|
||||||
|
float x_padding /* = LAYOUT_MENU_BUTTON_Y_PADDING */,
|
||||||
|
float y_padding /* = LAYOUT_MENU_BUTTON_Y_PADDING */,
|
||||||
|
float item_height /* = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY */,
|
||||||
|
float x_spacing /* = LAYOUT_MENU_BUTTON_X_PADDING */,
|
||||||
|
float x_margin /* = LAYOUT_MENU_WINDOW_X_PADDING */)
|
||||||
|
{
|
||||||
|
s_state.menu_button_index = 0;
|
||||||
|
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, LayoutScale(x_padding, y_padding));
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 0.0f);
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_FrameBorderSize, LayoutScale(UIStyle.MenuBorders ? 1.0f : 0.0f));
|
||||||
|
ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, LayoutScale(x_spacing, 0.0f));
|
||||||
|
|
||||||
|
ImGuiWindow* const window = ImGui::GetCurrentWindow();
|
||||||
|
const ImGuiStyle& style = ImGui::GetStyle();
|
||||||
|
window->DC.LayoutType = ImGuiLayoutType_Horizontal;
|
||||||
|
|
||||||
|
const float available_width = ImGui::GetContentRegionAvail().x;
|
||||||
|
const float space_per_item = ImFloor(
|
||||||
|
std::max((available_width - LayoutScale(x_margin) - (style.ItemSpacing.x * static_cast<float>(num_items - 1))) /
|
||||||
|
static_cast<float>(num_items),
|
||||||
|
0.0f));
|
||||||
|
s_state.horizontal_menu_button_size =
|
||||||
|
ImVec2(space_per_item, LayoutScale(item_height) + (style.FramePadding.y * 2.0f));
|
||||||
|
s_state.horizontal_menu_button_size.x =
|
||||||
|
(max_item_width > 0.0f) ?
|
||||||
|
std::min(s_state.horizontal_menu_button_size.x, LayoutScale(max_item_width) + (style.FramePadding.x * 2.0f)) :
|
||||||
|
s_state.horizontal_menu_button_size.x;
|
||||||
|
|
||||||
|
const float left_padding =
|
||||||
|
ImFloor((available_width -
|
||||||
|
(((s_state.horizontal_menu_button_size.x + style.ItemSpacing.x) * static_cast<float>(num_items)) -
|
||||||
|
style.ItemSpacing.x)) *
|
||||||
|
0.5f);
|
||||||
|
ImGui::SetCursorPosX(ImGui::GetCursorPosX() + left_padding);
|
||||||
|
|
||||||
|
// need to prerender the backgrounds for all inactive items, otherwise the animation overlaps it
|
||||||
|
const ImU32 frame_background = ImGui::GetColorU32(
|
||||||
|
DarkerColor((window->Flags & ImGuiWindowFlags_Popup) ? UIStyle.PopupBackgroundColor : UIStyle.BackgroundColor));
|
||||||
|
ImVec2 current_pos = ImGui::GetCursorScreenPos();
|
||||||
|
for (u32 i = 0; i < num_items; i++)
|
||||||
|
{
|
||||||
|
ImGui::RenderFrame(current_pos, current_pos + s_state.horizontal_menu_button_size, frame_background, false,
|
||||||
|
LayoutScale(MENU_ITEM_BORDER_ROUNDING));
|
||||||
|
|
||||||
|
current_pos.x += s_state.horizontal_menu_button_size.x + style.ItemSpacing.x;
|
||||||
|
}
|
||||||
|
|
||||||
|
PrerenderMenuButtonBorder();
|
||||||
|
}
|
||||||
|
|
||||||
|
void ImGuiFullscreen::EndHorizontalMenuButtons()
|
||||||
|
{
|
||||||
|
ImGui::PopStyleVar(4);
|
||||||
|
ImGui::GetCurrentWindow()->DC.LayoutType = ImGuiLayoutType_Vertical;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ImGuiFullscreen::HorizontalMenuButton(std::string_view title, bool enabled /* = true */,
|
||||||
|
const ImVec2& text_align /* = LAYOUT_CENTER_ALIGN_TEXT */)
|
||||||
|
{
|
||||||
|
ImGuiWindow* window = ImGui::GetCurrentWindow();
|
||||||
|
if (window->SkipItems)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
const ImVec2 pos = window->DC.CursorPos;
|
||||||
|
const ImVec2& size = s_state.horizontal_menu_button_size;
|
||||||
|
|
||||||
|
ImRect bb(pos, pos + size);
|
||||||
|
|
||||||
|
const ImGuiID id = window->GetID(IMSTR_START_END(title));
|
||||||
|
ImGui::ItemSize(size);
|
||||||
|
if (enabled)
|
||||||
|
{
|
||||||
|
if (!ImGui::ItemAdd(bb, id))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (ImGui::IsClippedEx(bb, id))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool hovered;
|
||||||
|
bool held;
|
||||||
|
bool pressed;
|
||||||
|
if (enabled)
|
||||||
|
{
|
||||||
|
pressed = ImGui::ButtonBehavior(bb, id, &hovered, &held, 0);
|
||||||
|
if (hovered)
|
||||||
|
{
|
||||||
|
const ImU32 col = ImGui::GetColorU32(held ? ImGuiCol_ButtonActive : ImGuiCol_ButtonHovered);
|
||||||
|
|
||||||
|
const float t = static_cast<float>(std::min(std::abs(std::sin(ImGui::GetTime() * 0.75) * 1.1), 1.0));
|
||||||
|
ImGui::PushStyleColor(ImGuiCol_Border, ImGui::GetColorU32(ImGuiCol_Border, t));
|
||||||
|
|
||||||
|
DrawMenuButtonFrame(bb.Min, bb.Max, col, true);
|
||||||
|
|
||||||
|
ImGui::PopStyleColor();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
pressed = false;
|
||||||
|
held = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ImGuiStyle& style = ImGui::GetStyle();
|
||||||
|
bb.Min += style.FramePadding;
|
||||||
|
bb.Max -= style.FramePadding;
|
||||||
|
|
||||||
|
const ImVec4& color = ImGui::GetStyle().Colors[enabled ? ImGuiCol_Text : ImGuiCol_TextDisabled];
|
||||||
|
RenderShadowedTextClipped(UIStyle.Font, UIStyle.LargeFontSize, UIStyle.BoldFontWeight, bb.Min, bb.Max,
|
||||||
|
ImGui::GetColorU32(color), title, nullptr, text_align, 0.0f, &bb);
|
||||||
|
|
||||||
|
s_state.menu_button_index++;
|
||||||
|
return pressed;
|
||||||
|
}
|
||||||
|
|
||||||
void ImGuiFullscreen::BeginNavBar(float x_padding /*= LAYOUT_MENU_BUTTON_X_PADDING*/,
|
void ImGuiFullscreen::BeginNavBar(float x_padding /*= LAYOUT_MENU_BUTTON_X_PADDING*/,
|
||||||
float y_padding /*= LAYOUT_MENU_BUTTON_Y_PADDING*/)
|
float y_padding /*= LAYOUT_MENU_BUTTON_Y_PADDING*/)
|
||||||
{
|
{
|
||||||
@ -3117,8 +3333,12 @@ void ImGuiFullscreen::MessageDialog::Draw()
|
|||||||
|
|
||||||
for (s32 button_index = 0; button_index < static_cast<s32>(m_buttons.size()); button_index++)
|
for (s32 button_index = 0; button_index < static_cast<s32>(m_buttons.size()); button_index++)
|
||||||
{
|
{
|
||||||
if (!m_buttons[button_index].empty() && MenuButtonWithoutSummary(m_buttons[button_index]))
|
if (!m_buttons[button_index].empty() &&
|
||||||
|
MenuButtonWithoutSummary(m_buttons[button_index], true, LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
LAYOUT_CENTER_ALIGN_TEXT))
|
||||||
|
{
|
||||||
result = button_index;
|
result = button_index;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
EndMenuButtons();
|
EndMenuButtons();
|
||||||
|
@ -54,6 +54,7 @@ static constexpr float LAYOUT_SMALL_POPUP_PADDING = 20.0f;
|
|||||||
static constexpr float LAYOUT_LARGE_POPUP_PADDING = 30.0f;
|
static constexpr float LAYOUT_LARGE_POPUP_PADDING = 30.0f;
|
||||||
static constexpr float LAYOUT_LARGE_POPUP_ROUNDING = 40.0f;
|
static constexpr float LAYOUT_LARGE_POPUP_ROUNDING = 40.0f;
|
||||||
static constexpr float LAYOUT_WIDGET_FRAME_ROUNDING = 20.0f;
|
static constexpr float LAYOUT_WIDGET_FRAME_ROUNDING = 20.0f;
|
||||||
|
static constexpr ImVec2 LAYOUT_CENTER_ALIGN_TEXT = ImVec2(0.5f, 0.0f);
|
||||||
|
|
||||||
struct ALIGN_TO_CACHE_LINE UIStyles
|
struct ALIGN_TO_CACHE_LINE UIStyles
|
||||||
{
|
{
|
||||||
@ -282,24 +283,26 @@ bool MenuButtonFrame(std::string_view str_id, bool enabled, float height, bool*
|
|||||||
ImVec2* max, ImGuiButtonFlags flags = 0, float hover_alpha = 1.0f);
|
ImVec2* max, ImGuiButtonFlags flags = 0, float hover_alpha = 1.0f);
|
||||||
void DrawMenuButtonFrame(const ImVec2& p_min, const ImVec2& p_max, ImU32 fill_col, bool border = true);
|
void DrawMenuButtonFrame(const ImVec2& p_min, const ImVec2& p_max, ImU32 fill_col, bool border = true);
|
||||||
void ResetMenuButtonFrame();
|
void ResetMenuButtonFrame();
|
||||||
void RenderShadowedTextClipped(ImFont* font, float font_size, float font_weight, const ImVec2& pos_min, const ImVec2& pos_max, u32 color,
|
void RenderShadowedTextClipped(ImFont* font, float font_size, float font_weight, const ImVec2& pos_min,
|
||||||
std::string_view text, const ImVec2* text_size_if_known = nullptr,
|
|
||||||
const ImVec2& align = ImVec2(0, 0), float wrap_width = 0.0f,
|
|
||||||
const ImRect* clip_rect = nullptr);
|
|
||||||
void RenderShadowedTextClipped(ImDrawList* draw_list, ImFont* font, float font_size, float font_weight, const ImVec2& pos_min,
|
|
||||||
const ImVec2& pos_max, u32 color, std::string_view text,
|
const ImVec2& pos_max, u32 color, std::string_view text,
|
||||||
const ImVec2* text_size_if_known = nullptr, const ImVec2& align = ImVec2(0, 0),
|
const ImVec2* text_size_if_known = nullptr, const ImVec2& align = ImVec2(0, 0),
|
||||||
float wrap_width = 0.0f, const ImRect* clip_rect = nullptr);
|
float wrap_width = 0.0f, const ImRect* clip_rect = nullptr);
|
||||||
void RenderShadowedTextClipped(ImDrawList* draw_list, ImFont* font, float font_size, float font_weight, const ImVec2& pos_min,
|
void RenderShadowedTextClipped(ImDrawList* draw_list, ImFont* font, float font_size, float font_weight,
|
||||||
const ImVec2& pos_max, u32 color, std::string_view text,
|
const ImVec2& pos_min, const ImVec2& pos_max, u32 color, std::string_view text,
|
||||||
|
const ImVec2* text_size_if_known = nullptr, const ImVec2& align = ImVec2(0, 0),
|
||||||
|
float wrap_width = 0.0f, const ImRect* clip_rect = nullptr);
|
||||||
|
void RenderShadowedTextClipped(ImDrawList* draw_list, ImFont* font, float font_size, float font_weight,
|
||||||
|
const ImVec2& pos_min, const ImVec2& pos_max, u32 color, std::string_view text,
|
||||||
const ImVec2* text_size_if_known, const ImVec2& align, float wrap_width,
|
const ImVec2* text_size_if_known, const ImVec2& align, float wrap_width,
|
||||||
const ImRect* clip_rect, float shadow_offset);
|
const ImRect* clip_rect, float shadow_offset);
|
||||||
|
void TextAlignedMultiLine(float align_x, const char* text, const char* text_end = nullptr, float wrap_width = -1.0f);
|
||||||
void MenuHeading(std::string_view title, bool draw_line = true);
|
void MenuHeading(std::string_view title, bool draw_line = true);
|
||||||
bool MenuHeadingButton(std::string_view title, std::string_view value = {}, bool enabled = true, bool draw_line = true);
|
bool MenuHeadingButton(std::string_view title, std::string_view value = {}, bool enabled = true, bool draw_line = true);
|
||||||
bool MenuButton(std::string_view title, std::string_view summary, bool enabled = true,
|
bool MenuButton(std::string_view title, std::string_view summary, bool enabled = true,
|
||||||
float height = LAYOUT_MENU_BUTTON_HEIGHT, const ImVec2& text_align = ImVec2(0.0f, 0.0f));
|
float height = LAYOUT_MENU_BUTTON_HEIGHT, const ImVec2& text_align = ImVec2(0.0f, 0.0f));
|
||||||
bool MenuButtonWithoutSummary(std::string_view title, bool enabled = true,
|
bool MenuButtonWithoutSummary(std::string_view title, bool enabled = true,
|
||||||
float height = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY, const ImVec2& text_align = ImVec2(0.0f, 0.0f));
|
float height = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
const ImVec2& text_align = ImVec2(0.0f, 0.0f));
|
||||||
bool MenuButtonWithValue(std::string_view title, std::string_view summary, std::string_view value, bool enabled = true,
|
bool MenuButtonWithValue(std::string_view title, std::string_view summary, std::string_view value, bool enabled = true,
|
||||||
float height = LAYOUT_MENU_BUTTON_HEIGHT);
|
float height = LAYOUT_MENU_BUTTON_HEIGHT);
|
||||||
bool MenuImageButton(std::string_view title, std::string_view summary, ImTextureID user_texture_id,
|
bool MenuImageButton(std::string_view title, std::string_view summary, ImTextureID user_texture_id,
|
||||||
@ -344,6 +347,16 @@ ALWAYS_INLINE static bool EnumChoiceButton(std::string_view title, std::string_v
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void BeginHorizontalMenuButtons(u32 num_items, float max_item_width = 0.0f,
|
||||||
|
float x_padding = LAYOUT_MENU_BUTTON_Y_PADDING,
|
||||||
|
float y_padding = LAYOUT_MENU_BUTTON_Y_PADDING,
|
||||||
|
float item_height = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY,
|
||||||
|
float x_spacing = LAYOUT_MENU_BUTTON_X_PADDING,
|
||||||
|
float x_margin = LAYOUT_MENU_WINDOW_X_PADDING);
|
||||||
|
void EndHorizontalMenuButtons();
|
||||||
|
bool HorizontalMenuButton(std::string_view title, bool enabled = true,
|
||||||
|
const ImVec2& text_align = LAYOUT_CENTER_ALIGN_TEXT);
|
||||||
|
|
||||||
void BeginNavBar(float x_padding = LAYOUT_MENU_BUTTON_X_PADDING, float y_padding = LAYOUT_MENU_BUTTON_Y_PADDING);
|
void BeginNavBar(float x_padding = LAYOUT_MENU_BUTTON_X_PADDING, float y_padding = LAYOUT_MENU_BUTTON_Y_PADDING);
|
||||||
void EndNavBar();
|
void EndNavBar();
|
||||||
void NavTitle(std::string_view title, float height = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY);
|
void NavTitle(std::string_view title, float height = LAYOUT_MENU_BUTTON_HEIGHT_NO_SUMMARY);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user