[sxhkd] Add script to show current sxhkd mode

Script can be used in a statusbar or otherwise and will return the
currently active sxhkd mode. Look into the README for further
explanation.
This commit is contained in:
Marty Oehme 2020-05-26 11:46:53 +02:00
parent 42379b25eb
commit cb5f09c414
No known key found for this signature in database
GPG key ID: 0CCB0526EFB9611A
6 changed files with 244 additions and 1 deletions

View file

@ -50,7 +50,7 @@ Enjoy!
* [`polybar`](polybar/README.md) - Easy to customize statusbar
* [`qutebrowser`](https://github.com/qutebrowser/qutebrowser) - vim-key enabled web browser
* [`rofi`](https://github.com/davatorium/rofi) - Application launcher, dmenu replacement
* [`sxhkd`](https://github.com/baskerville/sxhkd) - X11 hotkey manager
* [`sxhkd`](sxhkd/README.md) - X11 hotkey manager
* [`tmux`](https://github.com/tmux/tmux/) - terminal multiplexer
* [`vifm`](https://github.com/vifm/vifm) - vim-like file-manager

View file

@ -0,0 +1,30 @@
#!/usr/bin/env sh
# Starting sxhkd without arguments automatically creates
# a fifo pipe in XDG_RUNTIME_DIR, to enable IPC for sxhkd.
# Mostly used for sxhkd-chain-labels script.
type sxhkd >/dev/null 2>&1 || {
return 1
}
# get the complete path to sxhkd to avoid
# recursion later on
PROG="$(type sxhkd)"
PROG="${PROG##* }"
FIFO="$XDG_RUNTIME_DIR"/sxhkd_fifo
# create a fifo and start sxhkd with it
sxhkd() {
exist "$PROG" critical
if [ -n "$1" ]; then
"$PROG" "$@"
else
[ -e "$FIFO" ] && rm "$FIFO"
mkfifo "$FIFO"
"$PROG" -s "$FIFO"
fi
}

View file

@ -0,0 +1,7 @@
# for sxhkd-chain-labels script
# media manipulation mode: playing, pausing, skipping,..
media:super + alt + m
# academia mode: opening bibtex readings, annotating,..
academia:super + alt + a

View file

@ -60,3 +60,7 @@ super + alt + m : shift + {j,k}
# pause/stop player
super + alt + m : {_,shift} + p
playerctl {play-pause,stop}
# academia mode
super + alt + a : d
echo noice

View file

@ -0,0 +1,156 @@
#!/usr/bin/env sh
# output is to stdout unless explicitly set through -o
OUTPUTF=""
# set fifo input file, according (somewhat) to xdg
[ -n "$SXHKD_FIFO" ] && FIFO="$SXHKD_FIFO"
[ ! -e "$FIFO" ] && FIFO="${XDG_RUNTIME_DIR}"/sxhkd_fifo
[ ! -e "$FIFO" ] && FIFO="${XDG_CACHE_HOME:-$HOME/.cache}"/sxhkd_fifo
[ ! -e "$FIFO" ] && FIFO="$HOME/.sxhkd_fifo"
# set label config file, according (somewhat) to xdg
[ -n "$SXHKD_LABELCONFIG" ] && LABELCONFIG="$SXHKD_LABELCONFIG"
[ ! -f "$LABELCONFIG" ] && LABELCONFIG="${XDG_CONFIG_HOME:-$HOME/.config}"/sxhkd/chain-labels.conf
[ ! -f "$LABELCONFIG" ] && LABELCONFIG="$HOME/.chain-labels.conf"
main() {
while read -r event; do
detect_event "$event"
done <"$FIFO"
}
detect_event() {
ev="$(echo "$1" | sed -e 's/^H.*$/hotkey/;s/^C.*$/command/;s/^BBegin chain.*$/chainstart/;s/^EEnd chain.*$/chainend/;')"
case $ev in
hotkey) ev_hotkey "$(echo "$1" | sed -e 's/^H//')" ;;
# command) ev_command "$(echo "$1" | sed -e 's/^C//')" ;;
chainstart) ev_chainstart "$(echo "$1" | sed -e 's/^B//')" ;;
chainend) ev_chainend "$(echo "$1" | sed -e 's/^E//')" ;;
*) ;;
esac
}
send_msg() {
if [ -n "$OUTPUTF" ]; then
echo "$1" >"$OUTPUTF"
else
echo "$1"
fi
}
ev_hotkey() {
LAST_HOTKEY="$1"
}
# compare labels to last hotkey, return mode name
ev_chainstart() {
[ -z "$LAST_HOTKEY" ] && return 1
found=$(echo "$LABELS" | sed -e "/$LAST_HOTKEY/!d;s/^\(.\+\):.*$/\1/")
send_msg "$found"
}
ev_chainend() {
send_msg ""
}
# TODO add option to also display last command done in chain
# ev_command() {
# send_msg "command: $1"
# }
# read config from file, remove comments (lines starting with #) and empty lines
read_config() {
[ -f "$1" ] && LABELS="$(sed -e '/^#/d;/^[[:blank:]]*$/d' <"$1")" || LABELS=""
}
get_help() {
printf \
"Usage: sxhkd-chain-labels [-c config file][-o output file][-s input pipe]
By default will take the input from the input pipe (at XDG_RUNTIME_DIR/sxhkd_fifo) and
print the current sxhkd chain mode to stdout. That means, sxhkd needs to be started
with a fifo pipe running, ideally to the XDG_RUNTIME_DIR:
mkfifo \$XDG_RUNTIME_DIR/sxhkd_fifo && sxhkd -s \$XDG_RUNTIME_DIR/sxhkd_fifo
When given a key combination which maps to a specific mode, it will print out the name
of the mode instead. These maps can be passed with -c flag, specifying an options file.
By default it will look in \$XDG_CONFIG_HOME/sxhkd/sxhkd-chain-labels.conf
When passed the -o flag it will replace the contents of the file passed in with the
current sxhkd chain mode, emptying the file when no mode is active.
Default lookup places for files, in descending order:
:input fifo
\$SXHKD_FIFO (env variable)
\$XDG_RUNTIME_DIR/sxhkd_fifo
\$XDG_CACHE_HOME/sxhkd_fifo
~/.cache/sxhkd_fifo
~/.sxhkd_fifo
:label configuration
\$SXHKD_LABELCONFIG (env variable)
\$XDG_CONFIG_HOME/sxhkd/chain-labels.conf
~/.config/sxhkd/chain-labels.conf
~/.chain-labels.conf
The label configuration file uses the following format:
mode-name:chain activation combination
Lines beginning with a # will be ignored. Whitespace is
important, sxhkd will, by default, put a single space
between any component of the key combination.
An example file:
media:super + alt + m
system:super + backspace
\n"
}
get_version() {
printf \
"%s: 0.1
fifo input pipe:
%s
label configuration file:
%s
output:
%s \n" \
"$0" \
"$FIFO" \
"$LABELCONFIG" \
"${OUTPUTF:-stdout}"
}
while getopts "vho:s:c:" opt; do
case "$opt" in
\?)
printf "Usage: sxhkd-chain-labels [-c config file][-o output file][-s input pipe]\n"
exit 0
;;
h)
get_help
exit 0
;;
v)
get_version
exit 0
;;
o) OUTPUTF="$OPTARG" ;;
s) FIFO="$OPTARG" ;;
c) LABELCONFIG="$OPTARG" ;;
esac
done
shift $((OPTIND - 1))
[ "${1:-}" = "--" ] && shift
# look for default label config
[ -z "$LABELS" ] && read_config "$LABELCONFIG"
main "$@"

46
sxhkd/README.md Normal file
View file

@ -0,0 +1,46 @@
# sxhkd
[sxhkd](https://github.com/baskerville/sxhkd) -- simple X hotkey daemon
sxhkd is set up to manage most of the key bindings in this dotfile configuraition. It is primarily used for three things: system control, to invoke rofi, and to switch between different desktop operating modes.
## system control
* super+x: lock the system, i.e. put a lockscreen in front of it, unlocked with your password
* media keys: control the Brightness, Volume, Mute of the system
* super+return: open a terminal
## rofi invocations
* super+backspace: system management (shutdown,reboot,logout,..)
* super+space: app launching
* super+r: extended run menu
* super+p: password/secret autofill menu
* super+F8: theme setting menu
* super+q: quick access to bookmarks and search bangs
## modal desktop
The modal setup of this desktop allows to first invoke an operating mode and then open the possibility for additional keybindings.
For example, `alt + m` will invoke the `media` mode and then media playback can be controlled through the hjkl keys.
Think of it like invoking the insert mode, or visual mode in a modal editor like vim.
The idea behind the modal system is to not overload normal system operation with key binds that are only needed every now and again, and mostly as a coherent package.
If I want to control my media playback, by seeking forward or backward, having quick access to controlling the volume seems logical.
But I may not want to open a scholarly pdf, or programming project at the same time, so these actions don't need to be included in a coherent 'media' mode.
The modes currently are:
* media, for controlling playback and volume
* academia, for opening pdf, seeing upcoming readings, and editing references
They are still in flux and may change every now and again as I put this modal setup to the test. To get a closer look at the actual key binds, look into `.config/sxhkd/sxhkdrc` for now.
## modal notifications
To know which mode is currently active on the desktop, this module includes a script which will print sxhkd's current mode to stdout, or a file.
This script can be used to show the active mode in a status bar, for example (as the polybar module in these dotfiles does).
The script lives in `.local/bin/sxhkd-chain-labels` and can be invoked from the path by default. To see available options and the configuration file format use `sxhkd-chain-labels -h`, or take look at the script itself.
This module overwrites the usual sxhkd program invocation using an alias, which makes sxhkd always (if no options are passed) create and use a named pipe in the XDG_RUNTIME_DIR directory. This is the default location the script will pick it up in.