From 2cc089b41f2d2251a029f81c5761fc8039d37aba Mon Sep 17 00:00:00 2001 From: 28allday Date: Sat, 20 Jun 2026 06:34:08 +0100 Subject: [PATCH] =?UTF-8?q?fix(nosignal):=20hardware-test=20round=203=20?= =?UTF-8?q?=E2=80=94=20notif=20Clear=20+=20Game=20Mode=20=E2=86=92=20DeckS?= =?UTF-8?q?hift?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit F2: NsNotifications.qml "Clear" mirrors the service (Notifs.list.slice() → n.close()) instead of n.notification?.dismiss() — cards now actually leave the list, and it works for disk-restored notifications (whose notification is null). C2: Toggles.qml gameMode delegate launches the guarded switch-to-gaming via Quickshell.execDetached (debounced + disabled + 5s timer so a double-click can't fire two SDDM restarts), and the tile is hidden entirely when DeckShift isn't installed (Process probe for the gamescope session file). Co-Authored-By: Claude Opus 4.8 (1M context) --- modules/nsbar/panels/NsNotifications.qml | 12 +++++- modules/utilities/cards/Toggles.qml | 47 +++++++++++++++++++++++- 2 files changed, 55 insertions(+), 4 deletions(-) diff --git a/modules/nsbar/panels/NsNotifications.qml b/modules/nsbar/panels/NsNotifications.qml index 9764dd5a..ebbc434b 100644 --- a/modules/nsbar/panels/NsNotifications.qml +++ b/modules/nsbar/panels/NsNotifications.qml @@ -71,8 +71,16 @@ NsPanel { hoverEnabled: true cursorShape: Qt.PointingHandCursor onClicked: { - for (const n of Notifs.notClosed) - n.notification?.dismiss(); + // Mirror the service's own clear() / clearNotifs shortcut: + // NotifData.close() sets `closed` (drops it from notClosed so the + // card disappears), removes it from Notifs.list, dismisses the + // server notification and destroys it. Calling + // `notification?.dismiss()` directly cleared nothing — it never + // touched the list, and is a no-op for notifications restored from + // disk (their `notification` is null). Iterate a slice() copy so + // mutating the list mid-loop is safe. + for (const n of Notifs.list.slice()) + n.close(); } } } diff --git a/modules/utilities/cards/Toggles.qml b/modules/utilities/cards/Toggles.qml index d145700a..f90c8c7b 100644 --- a/modules/utilities/cards/Toggles.qml +++ b/modules/utilities/cards/Toggles.qml @@ -2,6 +2,8 @@ pragma ComponentBehavior: Bound import QtQuick import QtQuick.Layouts +import Quickshell +import Quickshell.Io import Quickshell.Bluetooth import Caelestia.Components import Caelestia.Config @@ -17,6 +19,18 @@ StyledRect { required property DrawerVisibilities visibilities required property BarPopouts.Wrapper popouts + // NoSignal: the gamepad "Game Mode" toggle launches DeckShift gaming. Hide it + // entirely when DeckShift isn't installed (no gamescope session file) — checked + // once at load by deckshiftProbe below. + property bool deckshiftInstalled: false + + Process { + id: deckshiftProbe + running: true + command: ["test", "-f", "/usr/share/wayland-sessions/gamescope-session-steam-nm.desktop"] + onExited: (exitCode, exitStatus) => root.deckshiftInstalled = exitCode === 0 + } + readonly property var quickToggles: { const seenIds = new Set(); @@ -32,6 +46,11 @@ StyledRect { return GlobalConfig.utilities.vpn.provider.some(p => typeof p === "object" ? (p.enabled === true) : false); } + // NoSignal: drop the Game Mode tile unless DeckShift is installed. + if (item.id === "gameMode") { + return root.deckshiftInstalled; + } + seenIds.add(item.id); return true; }); @@ -126,9 +145,33 @@ StyledRect { DelegateChoice { roleValue: "gameMode" delegate: Toggle { + id: gmTog + // NoSignal: launch the DeckShift gaming session if installed; + // otherwise do nothing. (Was caelestia's cosmetic Game Mode.) + // Kept styled as an off-toggle (muted, outline icon) — the + // gamepad is a momentary LAUNCHER, not a stateful toggle. + // DEBOUNCED: a fast double-click must not fire two + // `switch-to-gaming` runs — two SDDM restarts race the + // one-shot autologin and drop you at the password greeter. + // Guard mirrors the Super+Shift+S bind + the deckshift-login + // install-check, so it no-ops if DeckShift is absent. + property bool launching: false icon: "gamepad" - checked: GameMode.enabled - onClicked: GameMode.enabled = !GameMode.enabled + disabled: launching + onClicked: { + if (gmTog.launching) + return; + gmTog.launching = true; + gmTog.internalChecked = false; // don't latch "on" + relockTimer.start(); + Quickshell.execDetached(["sh", "-c", "[ -x /usr/local/bin/switch-to-gaming ] && [ -f /usr/share/wayland-sessions/gamescope-session-steam-nm.desktop ] && exec /usr/local/bin/switch-to-gaming"]); + } + + Timer { + id: relockTimer + interval: 5000 + onTriggered: gmTog.launching = false + } } } DelegateChoice {