Keep the window alive on close; add a system toggle to VisibilityController

- Main.qml: ignore close requests (Alt+F4, task manager), so the window
  can't be hidden without VisibilityController knowing.
- main.cpp: don't quit when the last window closes; KWin only restarts
  the input method after a crash.
- VisibilityController::setEnabled(): when false, the keyboard is hidden
  regardless of other state; changing it clears show()/hide() overrides.
  Not wired to KWin's tray toggle yet.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-11-03 19:58:59 +01:00
co-authored by Claude Opus 5.5
parent 032fbd8ba4
commit 5e4d4051f3
5 changed files with 31 additions and 1 deletions
+3
View File
@@ -36,6 +36,9 @@ Window {
visible: false
color: "transparent"
// Alt+F4 or the task manager would hide it behind the visibility
// controller's back; the dismiss key and the tray toggle hide it instead.
onClosing: close => close.accepted = false
onInputRegionChanged: placement?.setInputRegion(inputRegion)
onBlurRegionChanged: placement?.setBlurRegion(blurRegion, Theme.windowRadius)
// For CollapseController.
+2
View File
@@ -157,6 +157,8 @@ int main(int argc, char *argv[])
// libwayland unsets it once connected.
const bool launchedByKWin = qEnvironmentVariableIsSet("WAYLAND_SOCKET");
QGuiApplication app(argc, argv);
// KWin relaunches it only after a crash: a closed window mustn't quit it.
QGuiApplication::setQuitOnLastWindowClosed(false);
quitOnSignal();
QGuiApplication::setApplicationName(QStringLiteral("sloposk"));
QGuiApplication::setOrganizationName(QStringLiteral("sloposk")); // ~/.config/sloposk/sloposk.conf
+9 -1
View File
@@ -26,6 +26,13 @@ void VisibilityController::setAlwaysVisible(bool always)
update();
}
void VisibilityController::setEnabled(bool enabled)
{
m_enabled = enabled;
m_override.reset();
update();
}
void VisibilityController::show()
{
m_override = true;
@@ -46,7 +53,8 @@ void VisibilityController::toggle()
void VisibilityController::update()
{
const bool visible = m_override.value_or(m_alwaysVisible || m_standalone || (m_fieldActive && m_showOnField));
const bool visible =
m_enabled && m_override.value_or(m_alwaysVisible || m_standalone || (m_fieldActive && m_showOnField));
if (visible == m_visible)
return;
m_visible = visible;
+4
View File
@@ -9,6 +9,7 @@
// standalone (no input-method connection)
// - show()/hide()/toggle() override that until the focus changes, also
// from one field straight to another
// - never while the system's virtual keyboard toggle is off
class VisibilityController : public QObject
{
Q_OBJECT
@@ -24,6 +25,8 @@ public:
void setShowOnField(bool show);
void setStandalone(bool standalone);
void setAlwaysVisible(bool always);
// The system toggle (KWin's tray icon); off hides it whatever else says.
void setEnabled(bool enabled);
void show();
void hide();
@@ -39,6 +42,7 @@ private:
bool m_showOnField = true;
bool m_standalone = false;
bool m_alwaysVisible = false;
bool m_enabled = true;
std::optional<bool> m_override;
bool m_visible = false;
};
+13
View File
@@ -70,6 +70,19 @@ private Q_SLOTS:
QVERIFY(!v.isVisible());
}
void systemToggleGatesEverything()
{
VisibilityController v;
v.setAlwaysVisible(true);
v.setEnabled(false);
QVERIFY(!v.isVisible());
v.show();
QVERIFY(!v.isVisible());
v.hide();
v.setEnabled(true); // turning it back on forgets the dismiss
QVERIFY(v.isVisible());
}
void standaloneAlwaysVisible()
{
VisibilityController v;