aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDanilo M. <danix@danix.xyz>2026-09-15 12:29:42 +0200
committerDanilo M. <danix@danix.xyz>2026-09-15 12:29:42 +0200
commit661d477e7806d322d3499c19537541c5dd4e7d82 (patch)
treeb23199038db02f9bdbc9c4d91eb467b8d35b7e8f
parentfceeb5dc23c5e5a951f725e7682eab6814191c47 (diff)
downloadquickshell-661d477e7806d322d3499c19537541c5dd4e7d82.tar.gz
quickshell-661d477e7806d322d3499c19537541c5dd4e7d82.zip
fix(status): address final review findings
F1: after a click the shared Switch writes checked directly, dropping StatusRow's declarative binding, so an external mode change from waybar or statusctl no longer moved the switch. Resync via onValueChanged. F2: the spec claimed hyprctl clients counts idle inhibitors, which is false for a layer-surface inhibitor; replace with the behavioral hypridle marker check. F3: README said the check covers both watch states; it exercises the activated report and the absent-file down report. F4: give breakProc an onExited check so a failed breaktimer.sh verb is visible instead of silent. F5: drop StatusTile's unused required st property and its injection. F6: comment the startup-order limit on dndBeforePresentation.
-rw-r--r--desktop/modules/status/README.md2
-rw-r--r--desktop/modules/status/StatusModule.qml2
-rw-r--r--desktop/modules/status/StatusRow.qml5
-rw-r--r--desktop/modules/status/StatusTile.qml4
-rw-r--r--docs/superpowers/specs/2026-09-15-status-registry-design.md8
-rw-r--r--shared/Status.qml12
6 files changed, 23 insertions, 10 deletions
diff --git a/desktop/modules/status/README.md b/desktop/modules/status/README.md
index 0bb376f..84736d5 100644
--- a/desktop/modules/status/README.md
+++ b/desktop/modules/status/README.md
@@ -56,4 +56,4 @@ before the screen could lock.
Points `XDG_RUNTIME_DIR` at a temporary directory, so it never touches live
modes. Covers the file format, the atomic write, the toggle, the unknown-mode
-error and both watch states.
+error, both the activated report and the absent-file down report.
diff --git a/desktop/modules/status/StatusModule.qml b/desktop/modules/status/StatusModule.qml
index c36d9d0..30f8557 100644
--- a/desktop/modules/status/StatusModule.qml
+++ b/desktop/modules/status/StatusModule.qml
@@ -28,7 +28,7 @@ Module {
// The tile renders in its accent while any mode is on.
active: Status.activeCount > 0
- tileContent: Component { StatusTile { st: mod } }
+ tileContent: Component { StatusTile {} }
page: Component {
Page {
diff --git a/desktop/modules/status/StatusRow.qml b/desktop/modules/status/StatusRow.qml
index c342e2b..c9e78c0 100644
--- a/desktop/modules/status/StatusRow.qml
+++ b/desktop/modules/status/StatusRow.qml
@@ -53,4 +53,9 @@ Item {
checked: row.value
onToggled: Status.toggleMode(row.mode)
}
+
+ // The shared Switch's click handler writes `checked` directly, which drops
+ // the declarative binding above. Resync on any value change so an external
+ // write (statusctl, waybar) moves the switch back into agreement.
+ onValueChanged: sw.checked = row.value
}
diff --git a/desktop/modules/status/StatusTile.qml b/desktop/modules/status/StatusTile.qml
index 9bc6f04..c4b87d4 100644
--- a/desktop/modules/status/StatusTile.qml
+++ b/desktop/modules/status/StatusTile.qml
@@ -12,11 +12,7 @@
import QtQuick
import "../.."
-// Injected as st, never mod: a property named the same as the enclosing
-// object's id binds to itself and arrives undefined. See AGENTS.md.
Text {
- required property var st
-
width: parent ? parent.width : implicitWidth
elide: Text.ElideRight
font { family: Theme.fontFamily; pixelSize: Theme.fontSize - 4 }
diff --git a/docs/superpowers/specs/2026-09-15-status-registry-design.md b/docs/superpowers/specs/2026-09-15-status-registry-design.md
index 34e5945..db1e79c 100644
--- a/docs/superpowers/specs/2026-09-15-status-registry-design.md
+++ b/docs/superpowers/specs/2026-09-15-status-registry-design.md
@@ -222,8 +222,10 @@ That covers the parse, the write, the atomic rename and the watch together, and
it fails if any of them break.
The effects need the shell and are confirmed by hand, once, because each is
-observable: `hyprctl clients` counts inhibitors, `breaktimer.sh status` reports
-`paused`, and the notification daemon's own behaviour under DND is the second
-spec's verification.
+observable: a throwaway `hypridle -c` instance with a short timeout writes a
+marker on `on-timeout`, and the marker must not appear while presentation is on
+and must appear within a few seconds of it being turned off; `breaktimer.sh
+status` reports `paused`; and the notification daemon's own behaviour under DND
+is the second spec's verification.
Per AGENTS.md, anything visual is confirmed by the user rather than screenshotted.
diff --git a/shared/Status.qml b/shared/Status.qml
index 5df1847..8f80b9a 100644
--- a/shared/Status.qml
+++ b/shared/Status.qml
@@ -43,6 +43,10 @@ Singleton {
// presentation mode off restores it rather than clearing it. Held here
// rather than in a file: it is meaningful only while presentation mode is
// on, and presentation mode does not survive a reboot.
+ //
+ // Known limit: on a shell restart while presentation is already on,
+ // onPresentationChanged can run before the dnd FileView has loaded, so the
+ // recorded prior value depends on which file loads first.
property bool dndBeforePresentation: false
function setMode(name, on) {
@@ -80,7 +84,13 @@ Singleton {
// breaktimer owns its own state file; this only calls its verbs. Two
// writers on that file would race with its daemon loop, which rewrites it
// on every phase change.
- Process { id: breakProc }
+ Process {
+ id: breakProc
+ onExited: code => {
+ if (code !== 0)
+ console.warn("status: breaktimer.sh " + breakProc.command[1] + " exited " + code);
+ }
+ }
// Wayland idle inhibit. The compositor advertises
// zwp_idle_inhibit_manager_v1 and hypridle honours it, so no D-Bus path