mirror of
https://github.com/ItsDrike/dotfiles.git
synced 2025-01-23 15:44:33 +00:00
Compare commits
3 commits
9e946c7611
...
6c5c3fb36c
Author | SHA1 | Date | |
---|---|---|---|
ItsDrike | 6c5c3fb36c | ||
ItsDrike | db58721f45 | ||
ItsDrike | f871b7b427 |
|
@ -102,3 +102,4 @@
|
||||||
gpgsign = true
|
gpgsign = true
|
||||||
[init]
|
[init]
|
||||||
defaultBranch = main
|
defaultBranch = main
|
||||||
|
templatedir = ~/.config/git/templates
|
||||||
|
|
156
home/.config/git/templates/hooks/commit-msg
Executable file
156
home/.config/git/templates/hooks/commit-msg
Executable file
|
@ -0,0 +1,156 @@
|
||||||
|
#!/usr/bin/env bash
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
# A hook script to check the commit log message.
|
||||||
|
# Called by "git commit" with one argument, the name of the file
|
||||||
|
# that has the commit message. The hook should exit with non-zero
|
||||||
|
# status after issuing an appropriate message if it wants to stop the
|
||||||
|
# commit. The hook is allowed to edit the commit message file.
|
||||||
|
|
||||||
|
# This script focuses on enforcing semantic commit message specification.
|
||||||
|
#
|
||||||
|
# It primarily focuses on the commit title, however, it also enforces some
|
||||||
|
# the mandatory newline between the title and the body.
|
||||||
|
|
||||||
|
LIGHT_GRAY="\033[0;37m"
|
||||||
|
YELLOW="\033[33m"
|
||||||
|
CYAN="\033[36m"
|
||||||
|
RED="\033[31m"
|
||||||
|
UNDO_COLOR="\033[0m"
|
||||||
|
|
||||||
|
check_dependencies() {
|
||||||
|
if ! [ -x "$(command -v jq)" ]; then
|
||||||
|
echo "\`commit-msg\` hook failed. Please install jq."
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
load_config() {
|
||||||
|
config_file="$PWD/.commit-msg-config.json"
|
||||||
|
|
||||||
|
if [ ! -f "$config_file" ]; then
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
enabled=$(jq -r .enabled "$config_file")
|
||||||
|
|
||||||
|
if [ "$enabled" != "true" ]; then
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
title_semver_enabled=$(jq -r .semver_structure "$config_file")
|
||||||
|
mapfile -t special_types < <(jq -r '.special_types[]' "$config_file")
|
||||||
|
mapfile -t types < <(jq -r '.types[]' "$config_file")
|
||||||
|
mapfile -t scopes < <(jq -r '.scopes[]' "$config_file")
|
||||||
|
title_min_length=$(jq -r '.length.min' "$config_file")
|
||||||
|
title_max_length=$(jq -r '.length.max' "$config_file")
|
||||||
|
}
|
||||||
|
|
||||||
|
# Build a dynamic regex for the commit message
|
||||||
|
build_title_regex() {
|
||||||
|
regexp="^("
|
||||||
|
|
||||||
|
# Special types
|
||||||
|
if [ ${#special_types[@]} -eq 0 ]; then
|
||||||
|
for s_type in "${special_types[@]}"; do
|
||||||
|
regexp="${regexp}$s_type|"
|
||||||
|
done
|
||||||
|
regexp="${regexp%|})"
|
||||||
|
|
||||||
|
regexp="${regexp}(: .+)?"
|
||||||
|
|
||||||
|
regexp="${regexp}$|^("
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Types
|
||||||
|
if [ ${#types[@]} -eq 0 ]; then
|
||||||
|
regexp="${regexp}.+"
|
||||||
|
else
|
||||||
|
for type in "${types[@]}"; do
|
||||||
|
regexp="${regexp}$type|"
|
||||||
|
done
|
||||||
|
regexp="${regexp%|})"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Scope
|
||||||
|
regexp="${regexp}(\("
|
||||||
|
if [ ${#scopes[@]} -eq 0 ]; then
|
||||||
|
regexp="${regexp}.+"
|
||||||
|
else
|
||||||
|
for scope in "${scopes[@]}"; do
|
||||||
|
regexp="${regexp}$scope|"
|
||||||
|
done
|
||||||
|
regexp="${regexp%|}"
|
||||||
|
fi
|
||||||
|
regexp="${regexp}\))?"
|
||||||
|
|
||||||
|
# Breaking change indicator
|
||||||
|
regexp="${regexp}(!)?"
|
||||||
|
|
||||||
|
regexp="${regexp}: (.+)$"
|
||||||
|
}
|
||||||
|
|
||||||
|
error_header() {
|
||||||
|
echo -e "${RED}[Invalid Commit Message]${UNDO_COLOR}"
|
||||||
|
echo -e "------------------------"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ---------------------------------------------
|
||||||
|
|
||||||
|
INPUT_FILE="$1"
|
||||||
|
|
||||||
|
check_dependencies
|
||||||
|
load_config
|
||||||
|
|
||||||
|
# Get the actual commit message, excluding comments
|
||||||
|
commit_message=$(sed '/^#/d' <"$INPUT_FILE")
|
||||||
|
|
||||||
|
# Don't do any checking on empty commit messages.
|
||||||
|
# Git will abort empty commits by default anyways.
|
||||||
|
if [ -z "$commit_message" ]; then
|
||||||
|
exit 0
|
||||||
|
fi
|
||||||
|
|
||||||
|
commit_title=$(echo "$commit_message" | head -n1 "$INPUT_FILE")
|
||||||
|
|
||||||
|
# Check the semver commit title structure first
|
||||||
|
if [ "$title_semver_enabled" == "true" ]; then
|
||||||
|
build_title_regex
|
||||||
|
|
||||||
|
if [[ ! $commit_title =~ $regexp ]]; then
|
||||||
|
error_header
|
||||||
|
echo -e "${LIGHT_GRAY}Valid types: ${UNDO_COLOR}${CYAN}${types[*]}${UNDO_COLOR}"
|
||||||
|
echo -e "${LIGHT_GRAY}Valid special types: ${UNDO_COLOR}${CYAN}${special_types[*]}${UNDO_COLOR}"
|
||||||
|
if [ ${#scopes[@]} -eq 0 ]; then
|
||||||
|
echo -e "${LIGHT_GRAY}Valid scopes: any${UNDO_COLOR}"
|
||||||
|
else
|
||||||
|
echo -e "${LIGHT_GRAY}Valid scopes: ${UNDO_COLOR}${CYAN}${scopes[*]}${UNDO_COLOR}"
|
||||||
|
fi
|
||||||
|
|
||||||
|
#echo -e "${LIGHT_GRAY}Expected regex: ${UNDO_COLOR}${CYAN}${regexp}${UNDO_COLOR}"
|
||||||
|
|
||||||
|
echo -e "Actual commit title: ${YELLOW}${commit_title}${UNDO_COLOR}"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Then check the length of the commit title
|
||||||
|
commit_title_len=${#commit_title}
|
||||||
|
if { [ "$title_min_length" != "null" ] && [ "$commit_title_len" -lt "$title_min_length" ]; } ||
|
||||||
|
{ [ "$title_max_length" != "null" ] && [ "$commit_title_len" -gt "$title_max_length" ]; }; then
|
||||||
|
error_header
|
||||||
|
echo -e "${LIGHT_GRAY}Expected title (first line) length: Min=${CYAN}$title_min_length${UNDO_COLOR} Max=${CYAN}$title_max_length${UNDO_COLOR}"
|
||||||
|
echo -e "Actual length: ${YELLOW}${commit_title_len}${UNDO_COLOR}"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Check for a newline between the title and the body
|
||||||
|
if [ "$(echo "$commit_message" | wc -l)" -gt 1 ]; then
|
||||||
|
second_line=$(echo "$commit_message" | sed -n '2p')
|
||||||
|
third_line=$(echo "$commit_message" | sed -n '3p')
|
||||||
|
if [ "$second_line" != "" ] || [ "$third_line" == "" ]; then
|
||||||
|
error_header
|
||||||
|
echo -e "There must be exactly one blank line between the commit title and the body."
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
fi
|
|
@ -1,19 +1,18 @@
|
||||||
#!/bin/sh
|
#!/bin/bash
|
||||||
|
|
||||||
# Inspired by grimblast (https://github.com/hyprwm/contrib/blob/main/grimblast/grimblast)
|
# Inspired by grimblast (https://github.com/hyprwm/contrib/blob/main/grimblast/grimblast)
|
||||||
|
|
||||||
# Helper functions
|
# Helper functions
|
||||||
|
|
||||||
die() {
|
die() {
|
||||||
MSG="${1}"
|
MSG="${1}"
|
||||||
ERR_CODE="${2:-1}"
|
ERR_CODE="${2:-1}"
|
||||||
URGENCY="${3:-critical}"
|
URGENCY="${3:-critical}"
|
||||||
|
|
||||||
>&2 echo "$MSG"
|
if [ "$NOTIFY" = "yes" ]; then
|
||||||
if [ "$NOTIFY" = "yes" ]; then
|
notify-send -a screenshot -u "$URGENCY" "Error ($ERR_CODE)" "$MSG"
|
||||||
notify-send -a screenshot -u "$URGENCY" "Error ($ERR_CODE)" "$MSG"
|
fi
|
||||||
fi
|
exit "$ERR_CODE"
|
||||||
exit "$ERR_CODE"
|
|
||||||
}
|
}
|
||||||
|
|
||||||
# Argument parsing
|
# Argument parsing
|
||||||
|
@ -27,9 +26,9 @@ EDIT=no
|
||||||
DELAY=0
|
DELAY=0
|
||||||
|
|
||||||
while [ "${1-}" ]; do
|
while [ "${1-}" ]; do
|
||||||
case "$1" in
|
case "$1" in
|
||||||
-h | --help)
|
-h | --help)
|
||||||
>&2 cat <<EOF
|
>&2 cat <<EOF
|
||||||
screenshot taking utility script, allowing for easy all-in-one solution for
|
screenshot taking utility script, allowing for easy all-in-one solution for
|
||||||
controlling how a screenshot should be taken.
|
controlling how a screenshot should be taken.
|
||||||
|
|
||||||
|
@ -54,163 +53,163 @@ Variables:
|
||||||
- all: Everything (all visible monitors/outputs)
|
- all: Everything (all visible monitors/outputs)
|
||||||
- area: Manually select a region
|
- area: Manually select a region
|
||||||
EOF
|
EOF
|
||||||
exit 0
|
exit 0
|
||||||
;;
|
;;
|
||||||
--notify)
|
--notify)
|
||||||
NOTIFY=yes
|
NOTIFY=yes
|
||||||
shift
|
shift
|
||||||
;;
|
;;
|
||||||
--cursor)
|
--cursor)
|
||||||
CURSOR=yes
|
CURSOR=yes
|
||||||
shift
|
shift
|
||||||
;;
|
;;
|
||||||
--edit)
|
--edit)
|
||||||
EDIT=yes
|
EDIT=yes
|
||||||
shift
|
shift
|
||||||
;;
|
;;
|
||||||
--target)
|
--target)
|
||||||
if [ -z "$TARGET" ]; then
|
if [ -z "$TARGET" ]; then
|
||||||
case "$2" in
|
case "$2" in
|
||||||
activewin | window | activemon | monitor | all | area)
|
activewin | window | activemon | monitor | all | area)
|
||||||
TARGET="$2"
|
TARGET="$2"
|
||||||
shift 2
|
shift 2
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
die "Invalid target (see TARGET variable in --help)"
|
die "Invalid target (see TARGET variable in --help)"
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
else
|
else
|
||||||
die "Only one target can be passed."
|
die "Only one target can be passed."
|
||||||
fi
|
fi
|
||||||
;;
|
;;
|
||||||
--delay)
|
--delay)
|
||||||
case "$2" in
|
case "$2" in
|
||||||
'' | *[!0-9]*)
|
'' | *[!0-9]*)
|
||||||
die "Argument after --delay must be an amount of MILISECONDS"
|
die "Argument after --delay must be an amount of MILISECONDS"
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
DELAY="$2"
|
DELAY="$2"
|
||||||
shift 2
|
shift 2
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
;;
|
;;
|
||||||
|
|
||||||
--copy)
|
--copy)
|
||||||
if [ -z "$SAVE_METHOD" ]; then
|
if [ -z "$SAVE_METHOD" ]; then
|
||||||
SAVE_METHOD="copy"
|
SAVE_METHOD="copy"
|
||||||
shift
|
shift
|
||||||
else
|
else
|
||||||
die "Only one method can be passed."
|
die "Only one method can be passed."
|
||||||
fi
|
fi
|
||||||
;;
|
;;
|
||||||
--save)
|
--save)
|
||||||
if [ -z "$SAVE_METHOD" ]; then
|
if [ -z "$SAVE_METHOD" ]; then
|
||||||
SAVE_METHOD="save"
|
SAVE_METHOD="save"
|
||||||
SAVE_FILE="$2"
|
SAVE_FILE="$2"
|
||||||
shift 2
|
shift 2
|
||||||
else
|
else
|
||||||
die "Only one method can be passed."
|
die "Only one method can be passed."
|
||||||
fi
|
fi
|
||||||
;;
|
;;
|
||||||
--copysave)
|
--copysave)
|
||||||
if [ -z "$SAVE_METHOD" ]; then
|
if [ -z "$SAVE_METHOD" ]; then
|
||||||
SAVE_METHOD="copysave"
|
SAVE_METHOD="copysave"
|
||||||
SAVE_FILE="$2"
|
SAVE_FILE="$2"
|
||||||
shift 2
|
shift 2
|
||||||
else
|
else
|
||||||
die "Only one method can be passed."
|
die "Only one method can be passed."
|
||||||
fi
|
fi
|
||||||
;;
|
;;
|
||||||
*)
|
*)
|
||||||
die "Unrecognized argument: $1"
|
die "Unrecognized argument: $1"
|
||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
done
|
done
|
||||||
|
|
||||||
# Screenshot functions
|
# Screenshot functions
|
||||||
|
|
||||||
takeScreenshot() {
|
takeScreenshot() {
|
||||||
FILE="$1"
|
FILE="$1"
|
||||||
GEOM="$2"
|
GEOM="$2"
|
||||||
|
|
||||||
ARGS=()
|
ARGS=()
|
||||||
[ "$CURSOR" = "yes" ] && ARGS+=("-c")
|
[ "$CURSOR" = "yes" ] && ARGS+=("-c")
|
||||||
[ -n "$GEOM" ] && ARGS+=("-g" "$GEOM")
|
[ -n "$GEOM" ] && ARGS+=("-g" "$GEOM")
|
||||||
ARGS+=("$FILE")
|
ARGS+=("$FILE")
|
||||||
|
|
||||||
sleep "$DELAY"e-3
|
sleep "$DELAY"e-3
|
||||||
grim "${ARGS[@]}" || die "Unable to invoke grim"
|
grim "${ARGS[@]}" || die "Unable to invoke grim"
|
||||||
}
|
}
|
||||||
|
|
||||||
takeEditedScreenshot() {
|
takeEditedScreenshot() {
|
||||||
FILE="$1"
|
FILE="$1"
|
||||||
GEOM="$2"
|
GEOM="$2"
|
||||||
|
|
||||||
if [ "$EDIT" = "yes" ]; then
|
if [ "$EDIT" = "yes" ]; then
|
||||||
takeScreenshot - "$GEOM" | swappy -f - -o "$FILE" || die "Unable to invoke swappy"
|
takeScreenshot - "$GEOM" | swappy -f - -o "$FILE" || die "Unable to invoke swappy"
|
||||||
else
|
else
|
||||||
takeScreenshot "$FILE" "$GEOM"
|
takeScreenshot "$FILE" "$GEOM"
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
# Obtain the geometry for screenshot to be taken at
|
# Obtain the geometry for screenshot to be taken at
|
||||||
|
|
||||||
if [ "$TARGET" = "area" ]; then
|
if [ "$TARGET" = "area" ]; then
|
||||||
GEOM="$(slurp -d)"
|
GEOM="$(slurp -d)"
|
||||||
if [ -z "$GEOM" ]; then
|
if [ -z "$GEOM" ]; then
|
||||||
die "No area selected" 2 normal
|
die "No area selected" 2 normal
|
||||||
fi
|
fi
|
||||||
WHAT="Area"
|
WHAT="Area"
|
||||||
elif [ "$TARGET" = "all" ]; then
|
elif [ "$TARGET" = "all" ]; then
|
||||||
GEOM=""
|
GEOM=""
|
||||||
WHAT="Screen"
|
WHAT="Screen"
|
||||||
elif [ "$TARGET" = "activewin" ]; then
|
elif [ "$TARGET" = "activewin" ]; then
|
||||||
FOCUSED="$(hyprctl activewindow -j)"
|
FOCUSED="$(hyprctl activewindow -j)"
|
||||||
GEOM="$(echo "$FOCUSED" | jq -r '"\(.at[0]),\(.at[1]) \(.size[0])x\(.size[1])"')"
|
GEOM="$(echo "$FOCUSED" | jq -r '"\(.at[0]),\(.at[1]) \(.size[0])x\(.size[1])"')"
|
||||||
APP_ID="$(echo "$FOCUSED" | jq -r '.class')"
|
APP_ID="$(echo "$FOCUSED" | jq -r '.class')"
|
||||||
WHAT="$APP_ID window"
|
WHAT="$APP_ID window"
|
||||||
elif [ "$TARGET" = "window" ]; then
|
elif [ "$TARGET" = "window" ]; then
|
||||||
WORKSPACES="$(hyprctl monitors -j | jq -r 'map(.activeWorkspace.id)')"
|
WORKSPACES="$(hyprctl monitors -j | jq -r 'map(.activeWorkspace.id)')"
|
||||||
WINDOWS="$(hyprctl clients -j | jq -r --argjson workspaces "$WORKSPACES" 'map(select([.workspace.id] | inside($workspaces)))')"
|
WINDOWS="$(hyprctl clients -j | jq -r --argjson workspaces "$WORKSPACES" 'map(select([.workspace.id] | inside($workspaces)))')"
|
||||||
GEOM=$(echo "$WINDOWS" | jq -r '.[] | "\(.at[0]),\(.at[1]) \(.size[0])x\(.size[1])"' | slurp -r)
|
GEOM=$(echo "$WINDOWS" | jq -r '.[] | "\(.at[0]),\(.at[1]) \(.size[0])x\(.size[1])"' | slurp -r)
|
||||||
if [ -z "$GEOM" ]; then
|
if [ -z "$GEOM" ]; then
|
||||||
die "No window selected" 2 normal
|
die "No window selected" 2 normal
|
||||||
fi
|
fi
|
||||||
WHAT="Window"
|
WHAT="Window"
|
||||||
elif [ "$TARGET" = "activemon" ]; then
|
elif [ "$TARGET" = "activemon" ]; then
|
||||||
ACTIVEMON="$(hyprctl monitors -j | jq -r '.[] | select(.focused == true)')"
|
ACTIVEMON="$(hyprctl monitors -j | jq -r '.[] | select(.focused == true)')"
|
||||||
GEOM="$(echo "$ACTIVEMON" | jq -r '"\(.x),\(.y) \(.width)x\(.height)"')"
|
GEOM="$(echo "$ACTIVEMON" | jq -r '"\(.x),\(.y) \(.width)x\(.height)"')"
|
||||||
WHAT="$(echo "$ACTIVEMON" | jq -r '.name')"
|
WHAT="$(echo "$ACTIVEMON" | jq -r '.name')"
|
||||||
elif [ "$TARGET" = "monitor" ]; then
|
elif [ "$TARGET" = "monitor" ]; then
|
||||||
GEOM="$(slurp -o)"
|
GEOM="$(slurp -o)"
|
||||||
if [ -z "$GEOM" ]; then
|
if [ -z "$GEOM" ]; then
|
||||||
die "No monitor selected" 2 normal
|
die "No monitor selected" 2 normal
|
||||||
fi
|
fi
|
||||||
WHAT="Monitor"
|
WHAT="Monitor"
|
||||||
else
|
else
|
||||||
if [ -z "$TARGET" ]; then
|
if [ -z "$TARGET" ]; then
|
||||||
die "No target specified!"
|
die "No target specified!"
|
||||||
else
|
else
|
||||||
die "Unknown target: $SAVE_METHOD"
|
die "Unknown target: $SAVE_METHOD"
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# Invoke grim and capture the screenshot
|
# Invoke grim and capture the screenshot
|
||||||
|
|
||||||
if [ "$SAVE_METHOD" = "save" ]; then
|
if [ "$SAVE_METHOD" = "save" ]; then
|
||||||
takeEditedScreenshot "$SAVE_FILE" "$GEOM"
|
takeEditedScreenshot "$SAVE_FILE" "$GEOM"
|
||||||
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot saved" -i "$(realpath "$SAVE_FILE")"
|
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot saved" -i "$(realpath "$SAVE_FILE")"
|
||||||
elif [ "$SAVE_METHOD" = "copy" ]; then
|
elif [ "$SAVE_METHOD" = "copy" ]; then
|
||||||
TEMP_FILE="$(mktemp --suffix=.png)"
|
TEMP_FILE="$(mktemp --suffix=.png)"
|
||||||
takeEditedScreenshot "-" "$GEOM" | tee "$TEMP_FILE" | wl-copy --type image/png || die "Clipboard error"
|
takeEditedScreenshot "-" "$GEOM" | tee "$TEMP_FILE" | wl-copy --type image/png || die "Clipboard error"
|
||||||
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot copied" -i "$(realpath "$TEMP_FILE")" && rm "$TEMP_FILE"
|
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot copied" -i "$(realpath "$TEMP_FILE")" && rm "$TEMP_FILE"
|
||||||
elif [ "$SAVE_METHOD" = "copysave" ]; then
|
elif [ "$SAVE_METHOD" = "copysave" ]; then
|
||||||
takeEditedScreenshot "-" "$GEOM" | tee "$SAVE_FILE" | wl-copy --type image/png || die "Clipboard error"
|
takeEditedScreenshot "-" "$GEOM" | tee "$SAVE_FILE" | wl-copy --type image/png || die "Clipboard error"
|
||||||
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot copied and saved" -i "$(realpath "$SAVE_FILE")"
|
[ "$NOTIFY" = "yes" ] && notify-send -a screenshot "Success" "$WHAT screenshot copied and saved" -i "$(realpath "$SAVE_FILE")"
|
||||||
else
|
else
|
||||||
if [ -z "$SAVE_METHOD" ]; then
|
if [ -z "$SAVE_METHOD" ]; then
|
||||||
die "No save method specified!"
|
die "No save method specified!"
|
||||||
else
|
else
|
||||||
die "Unknown save method: $SAVE_METHOD"
|
die "Unknown save method: $SAVE_METHOD"
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
|
@ -107,7 +107,7 @@ paru -S --noconfirm --needed \
|
||||||
|
|
||||||
# Wayland Utilities
|
# Wayland Utilities
|
||||||
paru -S --noconfirm --needed \
|
paru -S --noconfirm --needed \
|
||||||
grim slurp wofi swappy-git wf-recorder wlogout clipman hyprpicker hyprpaper
|
grim slurp wofi swappy wf-recorder wlogout clipman hyprpicker hyprpaper
|
||||||
|
|
||||||
# Applications
|
# Applications
|
||||||
paru -S --noconfirm --needed \
|
paru -S --noconfirm --needed \
|
||||||
|
|
Loading…
Reference in a new issue