From 44c5fc22b42b8bbb5276daaa4645658e917d2139 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Henrik=20Rydg=C3=A5rd?= Date: Fri, 1 May 2026 20:04:22 +0200 Subject: [PATCH] Add a symbols page to the soft keyboard. Fixes #21624 --- Common/UI/PopupScreens.cpp | 38 +++++++++++++++++++++++--------------- Common/UI/PopupScreens.h | 11 +++++++++-- 2 files changed, 32 insertions(+), 17 deletions(-) diff --git a/Common/UI/PopupScreens.cpp b/Common/UI/PopupScreens.cpp index bb8b97d033..2535899b62 100644 --- a/Common/UI/PopupScreens.cpp +++ b/Common/UI/PopupScreens.cpp @@ -833,7 +833,7 @@ std::string PopupTextInputChoice::ValueText(bool *shadow) const { } } -ViewGroup *CreateSoftKeyboard(TextEdit *edit, bool *upperCase) { +ViewGroup *CreateSoftKeyboard(TextEdit *edit, SoftKeyboardState *state) { ScrollView *scrollView = new ScrollView(ORIENT_HORIZONTAL, new LinearLayoutParams(FILL_PARENT, WRAP_CONTENT)); LinearLayout *keyboard = scrollView->Add(new LinearLayout(ORIENT_VERTICAL, new LinearLayoutParams(WRAP_CONTENT, WRAP_CONTENT))); @@ -841,17 +841,20 @@ ViewGroup *CreateSoftKeyboard(TextEdit *edit, bool *upperCase) { static struct { std::string_view v; const char *tag; } kbRows[] = { - {"1234567890-=", "A"}, - {"qwertyuiop'[]", "L"}, - {"asdfghjkl()", "L"}, + {"1234567890-_", "A"}, + {"qwertyuiop", "L"}, + {"asdfghjkl", "L"}, {"zxcvbnm,.", "L"}, - {"QWERTYUIOP'[]", "U"}, - {"ASDFGHJKL()", "U"}, + {"QWERTYUIOP", "U"}, + {"ASDFGHJKL", "U"}, {"ZXCVBNM,.", "U"}, + {"@#$_&()/-+_", "S"}, + {"*\"':;!?[]", "S"}, + {"={}~<>|", "S"}, {"", "A"}, }; static const float space[] = { - 0.0f, 10.0f, 20.0f, 30.0f, 10.0f, 20.0f, 30.0f, 30.0f, + 0.0f, 10.0f, 20.0f, 30.0f, 10.0f, 20.0f, 30.0f, 10.0f, 20.0f, 30.0f, 30.0f, }; static_assert(ARRAY_SIZE(kbRows) == ARRAY_SIZE(space)); @@ -871,8 +874,9 @@ ViewGroup *CreateSoftKeyboard(TextEdit *edit, bool *upperCase) { bool visible = false; switch (kbRows[i].tag[0]) { - case 'L': visible = !(*upperCase); break; - case 'U': visible = *upperCase; break; + case 'L': visible = (*state == SoftKeyboardState::Lower); break; + case 'U': visible = (*state == SoftKeyboardState::Upper); break; + case 'S': visible = (*state == SoftKeyboardState::Symbols); break; case 'A': visible = true; break; default: visible = false; break; } @@ -885,16 +889,20 @@ ViewGroup *CreateSoftKeyboard(TextEdit *edit, bool *upperCase) { edit->Backspace(); }); break; - case 7: + case 10: // Special keys. - row->Add(new Button("Aa", new LinearLayoutParams(80.0f, 50.0f)))->OnClick.Add([keyboard, upperCase](EventParams &) { - *upperCase = !(*upperCase); + row->Add(new Button("Aa", new LinearLayoutParams(80.0f, 50.0f)))->OnClick.Add([keyboard, state](EventParams &) { + *state = (SoftKeyboardState)((int)*state + 1); + if (*state == SoftKeyboardState::MAX) { + *state = SoftKeyboardState::Upper; + } // Work through visibility. for (int i = 0; i < keyboard->GetNumSubviews(); i++) { LinearLayout *row = (LinearLayout *)keyboard->GetViewByIndex(i); switch (row->Tag()[0]) { - case 'L': row->SetVisibility(*upperCase ? V_GONE : V_VISIBLE); break; - case 'U': row->SetVisibility(*upperCase ? V_VISIBLE : V_GONE); break; + case 'L': row->SetVisibility((*state == SoftKeyboardState::Lower) ? V_VISIBLE : V_GONE); break; + case 'U': row->SetVisibility((*state == SoftKeyboardState::Upper) ? V_VISIBLE : V_GONE); break; + case 'S': row->SetVisibility((*state == SoftKeyboardState::Symbols) ? V_VISIBLE : V_GONE); break; case 'A': row->SetVisibility(V_VISIBLE); break; default: row->SetVisibility(V_GONE); break; } @@ -930,7 +938,7 @@ void TextEditPopupScreen::CreatePopupContents(UI::ViewGroup *parent) { parent->Add(new Spacer(8.0f)); - keyboard_ = parent->Add(CreateSoftKeyboard(edit_, &upperCase_)); + keyboard_ = parent->Add(CreateSoftKeyboard(edit_, &kbState_)); if (System_GetPropertyBool(SYSPROP_HAS_KEYBOARD)) { keyboard_->SetVisibility(V_GONE); lin->Add(new Spacer(5.0f)); diff --git a/Common/UI/PopupScreens.h b/Common/UI/PopupScreens.h index 739f0bc573..2491417c78 100644 --- a/Common/UI/PopupScreens.h +++ b/Common/UI/PopupScreens.h @@ -222,7 +222,14 @@ private: bool liveUpdate_; }; -ViewGroup *CreateSoftKeyboard(TextEdit *edit, bool *upperCase); +enum class SoftKeyboardState { + Upper = 0, + Lower, + Symbols, + MAX, +}; + +ViewGroup *CreateSoftKeyboard(TextEdit *edit, SoftKeyboardState *state); class TextEditPopupScreen : public PopupScreen { public: @@ -249,7 +256,7 @@ private: std::string textEditValue_; std::string placeholder_; int maxLen_; - bool upperCase_ = false; + SoftKeyboardState kbState_{}; bool passwordMasking_ = false; };