completions: Rewrite zsh

- Fix some completions that never really worked correctly, e.g `riverctl
  input` didn't take the input name into account. Same with rule that
  didn't take into account glob.

- Add a lot of documentation to help people adding new commands.

- Add new rule-[add|del] order.

- `riverctl input` now autocomplete input name from `riverctl
  list-inputs`
This commit is contained in:
Hugo Machet 2023-10-17 16:51:22 +02:00 committed by Isaac Freund
parent f364e1b81b
commit de5f21cbb4
No known key found for this signature in database
GPG Key ID: 86DED400DDFD7A11

View File

@ -2,11 +2,15 @@
#
# Completion script for riverctl, part of river <https://github.com/riverwm/river>
_riverctl_subcommands()
# This is the list of all riverctl first argument, i.e `riverctl <first_arg>`.
# If a command doesn't need completion for subcommands then you just need
# to add a line to this list.
# Format is '<command-name>:<description>'
_riverctl_commands()
{
local -a riverctl_subcommands
local -a riverctl_commands
riverctl_subcommands=(
riverctl_commands=(
# Actions
'close:Close the focused view'
'exit:Exit the compositor, terminating the Wayland session'
@ -69,13 +73,39 @@ _riverctl_subcommands()
'list-input-configs:List all input configurations'
)
_describe -t command 'command' riverctl_subcommands
_describe -t command 'command' riverctl_commands
}
_riverctl_input_subcommands()
# This is the function called for the completion. Commands added in the
# riverctl_commands above are generated in the `commands` case, there is
# nothing more to do for this. If a command has a subcommand then a new case
# need to be added in `args`.
# If this is a simple subcommand with simple multi choice, the easier way to
# do it is:
# <command-name>) _alternative 'arguments:args:(<choice1 choice2)' ;;
# If the subcommand also has subcommands then, good luck...
# This is really complex, the easiest example to look at is the `hide-cursor` one.
_riverctl()
{
local -a input_subcommands
local state line
_arguments -C \
'1: :->commands' \
'*:: :->args'
case "$state" in
commands) _alternative 'common-commands:common:_riverctl_commands' ;;
args)
case "$line[1]" in
focus-output) _alternative 'arguments:args:(next previous)' ;;
focus-view) _alternative 'arguments:args:(next previous up down left right)' ;;
input)
_arguments '1: :->name' '2: :->commands' ':: :->args'
case "$state" in
name) _values 'inputs' $(riverctl list-inputs | grep -e '^[^[:space:]]') ;;
commands)
local -a input_subcommands
input_subcommands=(
'events:Configure whether the input devices events will be used by river'
'accel-profile:Set the pointer acceleration profile'
@ -94,20 +124,9 @@ _riverctl_input_subcommands()
)
_describe -t command 'command' input_subcommands
}
_riverctl_input()
{
local state
_arguments \
'1: :->commands' \
'*:: :->args'
case $state in
commands) _alternative 'common-commands:common:_riverctl_input_subcommands' ;;
;;
args)
case "$words[1]" in
case "$line[2]" in
events) _alternative 'input-cmds:args:(enabled disabled disabled-on-external-mouse)' ;;
accel-profile) _alternative 'input-cmds:args:(none flat adaptive)' ;;
click-method) _alternative 'input-cmds:args:(none button-area clickfinger)' ;;
@ -124,54 +143,7 @@ _riverctl_input()
esac
;;
esac
}
_riverctl_hide_cursor_subcommands()
{
local -a hide_cursor_subcommands
hide_cursor_subcommands=(
"timeout:Hide cursor if it wasn\'t moved in the last X millisecond, until it is moved again"
'when-typing:Enable or disable whether the cursor should be hidden when pressing any non-modifier key'
)
_describe -t command 'command' hide_cursor_subcommands
}
_riverctl_hide_cursor()
{
local state
_arguments \
'1: :->commands' \
'*:: :->args'
case $state in
commands) _alternative 'common-commands:common:_riverctl_hide_cursor_subcommands' ;;
args)
case "$words[1]" in
when-typing) _alternative 'hide-cursor-cmds:args:(enabled disabled)' ;;
*) return 0 ;;
esac
;;
esac
}
_riverctl()
{
local state
_arguments \
'1: :->commands' \
'*:: :->args'
case $state in
commands) _alternative 'common-commands:common:_riverctl_subcommands' ;;
args)
case "$words[1]" in
focus-output) _alternative 'arguments:args:(next previous)' ;;
focus-view) _alternative 'arguments:args:(next previous up down left right)' ;;
input) _riverctl_input ;;
move) _alternative 'arguments:args:(up down left right)' ;;
resize) _alternative 'arguments:args:(horizontal vertical)' ;;
snap) _alternative 'arguments:args:(up down left right)' ;;
@ -182,9 +154,37 @@ _riverctl()
attach-mode) _alternative 'arguments:args:(top bottom)' ;;
focus-follows-cursor) _alternative 'arguments:args:(disabled normal always)' ;;
set-cursor-warp) _alternative 'arguments:args:(disabled on-output-change on-focus-change)' ;;
hide-cursor) _riverctl_hide_cursor ;;
rule-add) _alternative 'arguments:args:(float no-float ssd csd tag)' ;;
rule-del) _alternative 'arguments:args:(float no-float ssd csd tag)' ;;
hide-cursor)
_arguments '1: :->commands' ':: :->args'
case "$state" in
commands)
local -a hide_cursor_subcommands
hide_cursor_subcommands=(
"timeout:Hide cursor if it wasn\'t moved in the last X millisecond, until it is moved again"
'when-typing:Enable or disable whether the cursor should be hidden when pressing any non-modifier key'
)
_describe -t command 'command' hide_cursor_subcommands
;;
args)
case "$line[1]" in
when-typing) _alternative 'hide-cursor-cmds:args:(enabled disabled)' ;;
*) return 0 ;;
esac
;;
esac
;;
rule-add | rule-del)
# This is not perfect as it only complete if there is
# either '-app-id' or '-title'.
# The empty action(2) mean that we need an argument
# but we don't generate anything for it.
# In case of a new rule added in river, we just need
# to add it to the third option between '()',
# i.e (float no-float <new-option>)
_arguments '1: :(-app-id -title)' '2: : ' ':: :(float no-float ssd csd tag)'
;;
list-rules) _alternative 'arguments:args:(float ssd tag)' ;;
*) return 0 ;;
esac