feat(desktop): add screen recording (task 0029) #21
@@ -34,7 +34,9 @@ No audio capture and no full-screen recording variant.
|
|||||||
- **No waybar `window-rewrite` icon.**
|
- **No waybar `window-rewrite` icon.**
|
||||||
wf-recorder is headless and slurp is a transient selection overlay, so neither owns a workspace window and the per-application icon convention does not apply.
|
wf-recorder is headless and slurp is a transient selection overlay, so neither owns a workspace window and the per-application icon convention does not apply.
|
||||||
|
|
||||||
- **Recordings land in `~/Videos/Recordings`**, timestamped `recording-<date>.mp4`, with the directory created on first capture.
|
- **Output paths follow XDG user-dirs.**
|
||||||
|
A new `modules.desktop.userdirs` declares the XDG user directories (home-manager `xdg.userDirs`), and the recorder resolves its base with `xdg-user-dir VIDEOS`, writing timestamped `recording-<date>.mp4` under `<Videos>/Recordings` (created on first capture).
|
||||||
|
The screenshot module (task 0028) was aligned to the same convention (`xdg-user-dir PICTURES` → `<Pictures>/Screenshots`), so relocating a directory is a one-line change to `xdg.userDirs` rather than an edit in each tool.
|
||||||
|
|
||||||
- **Live capture is the irreducible manual step.**
|
- **Live capture is the irreducible manual step.**
|
||||||
The build is green, the config parses under `Hyprland --verify-config`, and the indicator's idle/recording transitions are verified against a stand-in process; exercising a real slurp selection and wf-recorder capture needs a running session.
|
The build is green, the config parses under `Hyprland --verify-config`, and the indicator's idle/recording transitions are verified against a stand-in process; exercising a real slurp selection and wf-recorder capture needs a running session.
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ in
|
|||||||
modules.desktop.rofi.enable = lib.mkDefault true;
|
modules.desktop.rofi.enable = lib.mkDefault true;
|
||||||
modules.desktop.screenshot.enable = lib.mkDefault true;
|
modules.desktop.screenshot.enable = lib.mkDefault true;
|
||||||
modules.desktop.terminal.enable = lib.mkDefault true;
|
modules.desktop.terminal.enable = lib.mkDefault true;
|
||||||
|
modules.desktop.userdirs.enable = lib.mkDefault true;
|
||||||
modules.desktop.theming.enable = lib.mkDefault true;
|
modules.desktop.theming.enable = lib.mkDefault true;
|
||||||
modules.desktop.waybar.enable = lib.mkDefault true;
|
modules.desktop.waybar.enable = lib.mkDefault true;
|
||||||
modules.desktop.audio.enable = lib.mkDefault true;
|
modules.desktop.audio.enable = lib.mkDefault true;
|
||||||
|
|||||||
@@ -16,8 +16,7 @@ let
|
|||||||
pkill = "${pkgs.procps}/bin/pkill";
|
pkill = "${pkgs.procps}/bin/pkill";
|
||||||
date = "${pkgs.coreutils}/bin/date";
|
date = "${pkgs.coreutils}/bin/date";
|
||||||
mkdir = "${pkgs.coreutils}/bin/mkdir";
|
mkdir = "${pkgs.coreutils}/bin/mkdir";
|
||||||
|
xdgUserDir = "${pkgs.xdg-user-dirs}/bin/xdg-user-dir";
|
||||||
recDir = "$HOME/Videos/Recordings";
|
|
||||||
|
|
||||||
# A single key both starts and stops.
|
# A single key both starts and stops.
|
||||||
# A running wf-recorder is stopped with SIGINT so it finalises the file.
|
# A running wf-recorder is stopped with SIGINT so it finalises the file.
|
||||||
@@ -32,8 +31,9 @@ let
|
|||||||
fi
|
fi
|
||||||
|
|
||||||
region=$(${slurp}) || exit 0
|
region=$(${slurp}) || exit 0
|
||||||
${mkdir} -p "${recDir}"
|
dir="$(${xdgUserDir} VIDEOS)/Recordings"
|
||||||
file="${recDir}/recording-$(${date} +%Y%m%d-%H%M%S).mp4"
|
${mkdir} -p "$dir"
|
||||||
|
file="$dir/recording-$(${date} +%Y%m%d-%H%M%S).mp4"
|
||||||
|
|
||||||
${notify-send} -a "Screen recording" "Recording started" "Region capture, no audio."
|
${notify-send} -a "Screen recording" "Recording started" "Region capture, no audio."
|
||||||
${wf-recorder} -g "$region" -f "$file"
|
${wf-recorder} -g "$region" -f "$file"
|
||||||
|
|||||||
@@ -13,8 +13,7 @@ let
|
|||||||
grimblast = "${pkgs.grimblast}/bin/grimblast";
|
grimblast = "${pkgs.grimblast}/bin/grimblast";
|
||||||
satty = "${pkgs.satty}/bin/satty";
|
satty = "${pkgs.satty}/bin/satty";
|
||||||
wl-copy = "${pkgs.wl-clipboard}/bin/wl-copy";
|
wl-copy = "${pkgs.wl-clipboard}/bin/wl-copy";
|
||||||
|
xdgUserDir = "${pkgs.xdg-user-dirs}/bin/xdg-user-dir";
|
||||||
shotDir = "$HOME/Pictures/Screenshots";
|
|
||||||
|
|
||||||
# satty is the annotation step, and its copy action is set to save as well,
|
# satty is the annotation step, and its copy action is set to save as well,
|
||||||
# so a single keystroke through it lands the shot in both the clipboard and a
|
# so a single keystroke through it lands the shot in both the clipboard and a
|
||||||
@@ -22,10 +21,11 @@ let
|
|||||||
capture =
|
capture =
|
||||||
target:
|
target:
|
||||||
pkgs.writeShellScript "screenshot-${target}" ''
|
pkgs.writeShellScript "screenshot-${target}" ''
|
||||||
mkdir -p ${shotDir}
|
dir="$(${xdgUserDir} PICTURES)/Screenshots"
|
||||||
|
mkdir -p "$dir"
|
||||||
${grimblast} save ${target} - \
|
${grimblast} save ${target} - \
|
||||||
| ${satty} --filename - \
|
| ${satty} --filename - \
|
||||||
--output-filename "${shotDir}/screenshot-%Y%m%d-%H%M%S.png" \
|
--output-filename "$dir/screenshot-%Y%m%d-%H%M%S.png" \
|
||||||
--copy-command ${wl-copy} \
|
--copy-command ${wl-copy} \
|
||||||
--save-after-copy \
|
--save-after-copy \
|
||||||
--early-exit \
|
--early-exit \
|
||||||
|
|||||||
16
modules/desktop/userdirs.nix
Normal file
16
modules/desktop/userdirs.nix
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
{ config, lib, ... }:
|
||||||
|
# Declares the XDG user directories, so a tool that queries them lands in a
|
||||||
|
# well-known folder a host can relocate from one place.
|
||||||
|
let
|
||||||
|
cfg = config.modules.desktop.userdirs;
|
||||||
|
user = config.user.name;
|
||||||
|
in
|
||||||
|
{
|
||||||
|
options.modules.desktop.userdirs.enable = lib.mkEnableOption "XDG user directories";
|
||||||
|
|
||||||
|
config = lib.mkIf cfg.enable {
|
||||||
|
# enable writes ~/.config/user-dirs.dirs from the option defaults, which
|
||||||
|
# xdg-user-dir then reads.
|
||||||
|
home-manager.users.${user}.xdg.userDirs.enable = true;
|
||||||
|
};
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user