From 3d68d467f746832185dfed16be50d2ef0884ee59 Mon Sep 17 00:00:00 2001 From: Damocles Date: Fri, 17 Apr 2026 14:31:37 +0200 Subject: [PATCH] lock: use TextInput for keyboard input instead of Keys on plain Item --- modules/lock/LockAuth.qml | 21 +++------------------ modules/lock/LockSurface.qml | 34 +++++++++++++++++++++++++++------- 2 files changed, 30 insertions(+), 25 deletions(-) diff --git a/modules/lock/LockAuth.qml b/modules/lock/LockAuth.qml index bd9cee7..1bfcb98 100644 --- a/modules/lock/LockAuth.qml +++ b/modules/lock/LockAuth.qml @@ -15,26 +15,11 @@ QtObject { signal authFailed - function handleKey(event) { + function submit() { if (_passwd.active || state === "max") return; - - if (event.key === Qt.Key_Enter || event.key === Qt.Key_Return) { - if (buffer.length > 0) - _passwd.start(); - } else if (event.key === Qt.Key_Backspace) { - if (event.modifiers & Qt.ControlModifier) - buffer = ""; - else - buffer = buffer.slice(0, -1); - } else if (event.key === Qt.Key_Escape) { - buffer = ""; - } else if (event.text && event.text.length === 1) { - const c = event.text; - // Accept printable ASCII - if (c.charCodeAt(0) >= 32 && c.charCodeAt(0) < 127) - buffer += c; - } + if (buffer.length > 0) + _passwd.start(); } property PamContext _passwd: PamContext { diff --git a/modules/lock/LockSurface.qml b/modules/lock/LockSurface.qml index a7c67b9..81b577e 100644 --- a/modules/lock/LockSurface.qml +++ b/modules/lock/LockSurface.qml @@ -139,17 +139,27 @@ WlSessionLockSurface { } } - // Keyboard input - focus lives on an Item since WlSessionLockSurface is a window. - // Aggressively reclaim focus: Component.onCompleted may fire before the surface - // is configured, and other items can steal activeFocus during layout. - Item { + // Keyboard input via TextInput - engages Qt's full input pipeline including + // text-input protocol, which is more reliable than Keys on a plain Item in + // layer-shell/lock surfaces where raw wl_keyboard delivery can be flaky. + TextInput { id: _keyInput anchors.fill: parent focus: true - Keys.onPressed: event => { - if (!root._unlocking) - root.auth.handleKey(event); + color: "transparent" + selectionColor: "transparent" + selectedTextColor: "transparent" + cursorVisible: false + enabled: !root._unlocking && root.auth.state !== "max" && root.auth.state !== "busy" + + onTextChanged: root.auth.buffer = text + + Keys.onReturnPressed: root.auth.submit() + Keys.onEnterPressed: root.auth.submit() + Keys.onEscapePressed: { + text = ""; } + onActiveFocusChanged: { if (!activeFocus) forceActiveFocus(); @@ -161,6 +171,16 @@ WlSessionLockSurface { _keyInput.forceActiveFocus(); } + // Sync TextInput when auth clears buffer externally (PAM submit, lock reset) + Connections { + target: root.auth + + function onBufferChanged() { + if (_keyInput.text !== root.auth.buffer) + _keyInput.text = root.auth.buffer; + } + } + // Unlock animation property bool _unlocking: false