93 lines
2.5 KiB
Nix
93 lines
2.5 KiB
Nix
{
|
|
config,
|
|
lib,
|
|
pkgs,
|
|
...
|
|
}:
|
|
with lib; let
|
|
cfg = config.custom.services.systemd-lock-handler;
|
|
|
|
gtklock = getExe pkgs.gtklock;
|
|
hyprlock = getExe config.programs.hyprlock.package;
|
|
niri = getExe config.programs.niri.package;
|
|
pgrep = getExe' pkgs.procps "pgrep";
|
|
sleep = getExe' pkgs.coreutils "sleep";
|
|
in {
|
|
options.custom.services.systemd-lock-handler = {
|
|
enable = mkOption {default = false;};
|
|
delay = mkOption {default = 1;}; # Seconds
|
|
|
|
lock = mkOption {
|
|
default =
|
|
if config.custom.lockscreen == "gtklock"
|
|
then gtklock
|
|
else if config.custom.lockscreen == "hyprlock"
|
|
then hyprlock
|
|
else "";
|
|
};
|
|
|
|
transition = mkOption {default = true;};
|
|
};
|
|
|
|
config = mkIf cfg.enable {
|
|
# https://sr.ht/~whynothugo/systemd-lock-handler/
|
|
services.systemd-lock-handler.enable = true;
|
|
|
|
# https://sr.ht/~whynothugo/systemd-lock-handler/#usage
|
|
# https://github.com/hyprwm/hypridle/issues/49
|
|
systemd.user.services = {
|
|
handle-lock = let
|
|
delay-ms = toString (cfg.delay * 1000); # Milliseconds
|
|
in {
|
|
unitConfig = {
|
|
Description = "Lockscreen";
|
|
|
|
# Use Before, not After lock.target
|
|
# https://todo.sr.ht/~whynothugo/systemd-lock-handler/4
|
|
Before = ["lock.target"];
|
|
};
|
|
|
|
serviceConfig = {
|
|
Type = "exec";
|
|
|
|
ExecCondition = pkgs.writeShellScript "lock-condition" ''
|
|
if ${pgrep} ${config.custom.lockscreen}; then
|
|
exit 1 # Lockscreen process already running
|
|
else
|
|
exit 0 # Lockscreen process not found
|
|
fi
|
|
'';
|
|
|
|
# HACK: Default red background immediately shows while lockscreen starts, so use transition
|
|
# https://github.com/YaLTeR/niri/issues/808
|
|
ExecStartPre = mkIf cfg.transition (
|
|
if config.custom.desktop == "niri"
|
|
then "${niri} msg action do-screen-transition --delay-ms ${delay-ms}"
|
|
else ""
|
|
);
|
|
|
|
ExecStart = cfg.lock;
|
|
};
|
|
|
|
requiredBy = ["lock.target" "sleep.target"];
|
|
};
|
|
|
|
handle-sleep = let
|
|
# Transition time is about 1 second
|
|
delay = toString (cfg.delay + 1); # Seconds
|
|
in {
|
|
unitConfig = {
|
|
Description = "Delay sleep for ${delay}s";
|
|
Before = ["sleep.target"];
|
|
};
|
|
|
|
serviceConfig = {
|
|
Type = "oneshot";
|
|
ExecStart = "${sleep} ${delay}s";
|
|
};
|
|
|
|
requiredBy = ["sleep.target"];
|
|
};
|
|
};
|
|
};
|
|
}
|