Keep software-composited cursors out of screenshots

Hyprland falls back to compositing the cursor into the frame on GPUs
without working hardware cursors, so grim would capture it. Force
hardware cursors for the duration of the capture and restore after.

Closes #6142

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
David Heinemeier Hansson
2026-07-18 15:42:01 -07:00
co-authored by Claude Fable 5
parent 96bb617a9c
commit fa2b997513
+17 -4
View File
@@ -40,11 +40,24 @@ PROCESSING="${2:-slurp}"
# The picker leaves the screen freeze running (PID on its first output line)
# so grim captures the frozen overlay rather than live content shifting
# during teardown.
cleanup_freeze() {
[[ -n $FREEZE_PID ]] && kill $FREEZE_PID 2>/dev/null
}
trap cleanup_freeze EXIT
#
# Software-composited cursors (Hyprland's fallback on GPUs without working
# hardware cursors) are baked into the frames grim captures, so force
# hardware cursors until after grim runs and restore the setting on exit.
NO_HW_CURSORS=$(hyprctl getoption cursor:no_hardware_cursors -j | jq '.int')
set_no_hw_cursors() {
hyprctl eval "hl.config({ cursor = { no_hardware_cursors = $1 } })" &>/dev/null ||
hyprctl keyword cursor:no_hardware_cursors "$1" &>/dev/null
}
cleanup() {
[[ -n $FREEZE_PID ]] && kill $FREEZE_PID 2>/dev/null
set_no_hw_cursors "$NO_HW_CURSORS"
}
trap cleanup EXIT
set_no_hw_cursors 0
{ read -r FREEZE_PID; read -r SELECTION; } < <(omarchy-capture-region "$MODE" --keep-freeze)
[[ -z $SELECTION ]] && exit 0