swayfx/contrib/grimshot

158 lines
4.4 KiB
Plaintext
Raw Normal View History

#!/bin/sh
## Grimshot: a helper for screenshots within sway
## Requirements:
## - `grim`: screenshot utility for wayland
## - `slurp`: to select an area
## - `swaymsg`: to read properties of current window
## - `wl-copy`: clipboard utility
2020-01-31 22:35:40 +11:00
## - `jq`: json utility to parse swaymsg output
## - `notify-send`: to show notifications
## - `mktemp`: to create a temporary file
## Those are needed to be installed, if unsure, run `grimshot check`
##
## Examples:
## `grimshot copy win` - to copy current window
## `grimshot save area` - to select area and save it to default file (Pictures/Grimshot-$datetime.png)
## `grimshot save screen ~/screenshot.png` - to save screenshot under ~/screenshot.png
2020-01-28 10:09:18 +11:00
## `grimshot save output ~/screenshot.png` - to save screenshot under ~/screenshot.png
## `grimshot` - usage
## `grimshot check` - verify if tools are installed
getTargetDirectory() {
test -f ${XDG_CONFIG_HOME:-~/.config}/user-dirs.dirs && \
source ${XDG_CONFIG_HOME:-~/.config}/user-dirs.dirs
echo ${XDG_SCREENSHOTS_DIR:-${XDG_PICTURES_DIR:-$HOME}}
}
if [ $1 == "--notify" ]; then
NOTIFY=yes
shift 1
else
NOTIFY=no
fi
ACTION=${1:-usage}
SUBJECT=${2:-screen}
FILE=${3:-$(getTargetDirectory)/$(date -Ins).png}
if [ "$ACTION" != "save" ] && [ "$ACTION" != "copy" ] && [ "$ACTION" != "check" ]; then
echo "Usage:"
echo " grimshot [--notify] (copy|save) [active|screen|output|area|window] [FILE]"
echo " grimshot check"
echo " grimshot usage"
echo ""
echo "Commands:"
echo " copy: Copy the screenshot data into the clipboard."
echo " save: Save the screenshot to a regular file."
echo " check: Verify if required tools are installed and exit."
echo " usage: Show this message and exit."
echo ""
echo "Targets:"
echo " active: Currently active window."
echo " screen: All visible outputs."
echo " output: Currently active output."
echo " region: Manually select a region."
echo " window: Manually select a window."
exit
fi
notify() {
notify-send -t 3000 -a grimshot "$@"
}
notifyOk() {
[ $NOTIFY = "no" ] && return
TITLE=${2:-"Screenshot"}
MESSAGE=${1:-"OK"}
notify "$TITLE" "$MESSAGE"
}
notifyError() {
if [ $NOTIFY = "yes" ]; then
TITLE=${2:-"Screenshot"}
MESSAGE=${1:-"Error taking screenshot with grim"}
notify -u critical "$TITLE" "$MESSAGE"
else
echo $1
fi
}
die() {
MSG=${1:-Bye}
notifyError "Error: $MSG"
exit 2
}
check() {
COMMAND=$1
if command -v "$COMMAND" > /dev/null 2>&1; then
RESULT="OK"
else
RESULT="NOT FOUND"
fi
echo " $COMMAND: $RESULT"
}
takeScreenshot() {
FILE=$1
GEOM=$2
2020-01-28 10:09:18 +11:00
OUTPUT=$3
if [ ! -z "$OUTPUT" ]; then
grim -o "$OUTPUT" "$FILE" || die "Unable to invoke grim"
elif [ -z "$GEOM" ]; then
grim "$FILE" || die "Unable to invoke grim"
else
grim -g "$GEOM" "$FILE" || die "Unable to invoke grim"
fi
}
if [ "$ACTION" = "check" ] ; then
echo "Checking if required tools are installed. If something is missing, install it to your system and make it available in PATH..."
check grim
check slurp
check swaymsg
check wl-copy
check jq
check notify-send
check mktemp
exit
elif [ "$SUBJECT" = "area" ] ; then
GEOM=$(slurp -d)
WHAT="Area"
elif [ "$SUBJECT" = "active" ] ; then
FOCUSED=$(swaymsg -t get_tree | jq -r 'recurse(.nodes[]?, .floating_nodes[]?) | select(.focused)')
GEOM=$(echo "$FOCUSED" | jq -r '.rect | "\(.x),\(.y) \(.width)x\(.height)"')
APP_ID=$(echo "$FOCUSED" | jq -r '.app_id')
WHAT="$APP_ID window"
elif [ "$SUBJECT" = "screen" ] ; then
GEOM=""
WHAT="Screen"
2020-01-28 10:09:18 +11:00
elif [ "$SUBJECT" = "output" ] ; then
GEOM=""
2020-01-28 10:09:18 +11:00
OUTPUT=$(swaymsg -t get_outputs | jq -r '.[] | select(.focused)' | jq -r '.name')
WHAT="$OUTPUT"
elif [ "$SUBJECT" = "window" ] ; then
GEOM=$(swaymsg -t get_tree | jq -r '.. | select(.pid? and .visible?) | .rect | "\(.x),\(.y) \(.width)x\(.height)"' | slurp)
WHAT="Window"
else
die "Unknown subject to take a screen shot from" "$SUBJECT"
fi
if [ "$ACTION" = "copy" ] ; then
TMP=$(mktemp) || die "Unable to create temp file: is mktemp installed?"
2020-01-28 10:09:18 +11:00
takeScreenshot "$TMP" "$GEOM" "$OUTPUT"
wl-copy --type image/png < "$TMP" || die "Clipboard error"
rm "$TMP"
notifyOk "$WHAT copied to buffer"
else
2020-01-28 10:09:18 +11:00
if takeScreenshot "$FILE" "$GEOM" "$OUTPUT"; then
TITLE="Screenshot of $SUBJECT"
MESSAGE=$(basename "$FILE")
notifyOk "$MESSAGE" "$TITLE"
echo $FILE
else
notifyError "Error taking screenshot with grim"
fi
fi