feat(idle): suspend on battery only, cohering with power management
hypridle's suspend listener now runs `nomarchy-on-ac || systemctl suspend`, so a plugged-in machine no longer suspends itself mid-idle (long builds, media, presentations survive). It also fires sooner — 15 min, vs the old fixed 30 — since it now only applies unplugged. Lock and screen-off are unchanged on both power sources, and logind's lid handling stays at its sensible defaults (suspend on lid close, ignore when docked). Closes the idle-cohesion follow-up under the laptop-power roadmap item. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
13
README.md
13
README.md
@@ -454,10 +454,15 @@ close · `SUPER+1..9` workspaces · `Print` region screenshot.
|
|||||||
default; the installer scaffolds it commented-out on laptops.
|
default; the installer scaffolds it commented-out on laptops.
|
||||||
- ✓ **installer:** writes `power.laptop = true` (battery probe) and
|
- ✓ **installer:** writes `power.laptop = true` (battery probe) and
|
||||||
`power.thermal.enable` (Intel) into the generated `system.nix`.
|
`power.thermal.enable` (Intel) into the generated `system.nix`.
|
||||||
- Remaining: **cohere** with `modules/home/idle.nix` (AC-vs-battery idle
|
- ✓ **idle cohesion:** `modules/home/idle.nix` now suspends only on
|
||||||
timeouts / no auto-suspend on AC) and review logind lid handling, plus a
|
battery (and sooner — 15 min vs the old fixed 30), gating the hypridle
|
||||||
boot-only→event-driven charge-limit re-apply (udev) if a firmware resets
|
suspend listener on a `nomarchy-on-ac` probe so a plugged-in machine
|
||||||
the threshold on unplug.
|
stays up mid-idle; lock/screen-off are unchanged on both sources.
|
||||||
|
logind's lid handling is left at its defaults (suspend on lid close,
|
||||||
|
ignore when docked) — an explicit "I'm done" that coheres with the
|
||||||
|
idle behaviour.
|
||||||
|
- Remaining: a boot-only→event-driven charge-limit re-apply (udev) if a
|
||||||
|
firmware resets the threshold on unplug.
|
||||||
- **Opt-in services & integrations:** the counterpart to the opt-*out*
|
- **Opt-in services & integrations:** the counterpart to the opt-*out*
|
||||||
application suite above — heavier or more personal integrations shipped
|
application suite above — heavier or more personal integrations shipped
|
||||||
**off by default**, each a `nomarchy.services.<name>.enable` toggle a
|
**off by default**, each a `nomarchy.services.<name>.enable` toggle a
|
||||||
|
|||||||
@@ -2,13 +2,23 @@
|
|||||||
# theme-state.json. One concern, one file: hypridle drives WHEN (idle
|
# theme-state.json. One concern, one file: hypridle drives WHEN (idle
|
||||||
# lock, display off, suspend, lock-before-sleep), hyprlock is the
|
# lock, display off, suspend, lock-before-sleep), hyprlock is the
|
||||||
# themed lock screen itself (also behind the power menu's Lock entry).
|
# themed lock screen itself (also behind the power menu's Lock entry).
|
||||||
{ config, lib, ... }:
|
{ config, lib, pkgs, ... }:
|
||||||
|
|
||||||
let
|
let
|
||||||
cfg = config.nomarchy;
|
cfg = config.nomarchy;
|
||||||
t = cfg.theme;
|
t = cfg.theme;
|
||||||
c = t.colors;
|
c = t.colors;
|
||||||
inherit (config.nomarchy.lib) rgb;
|
inherit (config.nomarchy.lib) rgb;
|
||||||
|
|
||||||
|
# Exits 0 when running on AC: a mains adapter reports `online` 1 (battery
|
||||||
|
# supplies have no `online` node, so they never match). Used as
|
||||||
|
# `${onAc} || <action>` so the action is skipped while plugged in.
|
||||||
|
onAc = pkgs.writeShellScript "nomarchy-on-ac" ''
|
||||||
|
for f in /sys/class/power_supply/*/online; do
|
||||||
|
[ -r "$f" ] && [ "$(cat "$f")" = "1" ] && exit 0
|
||||||
|
done
|
||||||
|
exit 1
|
||||||
|
'';
|
||||||
in
|
in
|
||||||
{
|
{
|
||||||
config = lib.mkIf cfg.idle.enable {
|
config = lib.mkIf cfg.idle.enable {
|
||||||
@@ -62,13 +72,20 @@ in
|
|||||||
after_sleep_cmd = "hyprctl dispatch dpms on";
|
after_sleep_cmd = "hyprctl dispatch dpms on";
|
||||||
};
|
};
|
||||||
listener = [
|
listener = [
|
||||||
|
# Lock and screen-off are the same on either power source —
|
||||||
|
# they're about privacy and the panel, not battery.
|
||||||
{ timeout = 300; on-timeout = "loginctl lock-session"; }
|
{ timeout = 300; on-timeout = "loginctl lock-session"; }
|
||||||
{
|
{
|
||||||
timeout = 600;
|
timeout = 600;
|
||||||
on-timeout = "hyprctl dispatch dpms off";
|
on-timeout = "hyprctl dispatch dpms off";
|
||||||
on-resume = "hyprctl dispatch dpms on";
|
on-resume = "hyprctl dispatch dpms on";
|
||||||
}
|
}
|
||||||
{ timeout = 1800; on-timeout = "systemctl suspend"; }
|
# Suspend only on battery, and sooner than the old fixed 30 min
|
||||||
|
# (it now only fires unplugged). Plugged in, the machine stays
|
||||||
|
# up — long builds, media, presentations aren't killed mid-idle.
|
||||||
|
# Closing the lid still suspends on AC (logind's default): that's
|
||||||
|
# an explicit "I'm done", distinct from sitting idle.
|
||||||
|
{ timeout = 900; on-timeout = "${onAc} || systemctl suspend"; }
|
||||||
];
|
];
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user