From 8b85b40b2fd77128da2503e90ed358605e3e2656 Mon Sep 17 00:00:00 2001 From: Philip Langdale Date: Wed, 8 Jan 2020 19:09:14 -0800 Subject: bash completion: add initial implementation of bash completion While we've had a zsh completion script for a while, we haven't had one for bash. This one is reasonably comprehensive, although there are improvements one could imagine for certain options. --- etc/mpv.bash-completion | 112 ++++++++++++++++++++++++++++++++++++++++++++++++ wscript | 1 + wscript_build.py | 3 ++ 3 files changed, 116 insertions(+) create mode 100644 etc/mpv.bash-completion diff --git a/etc/mpv.bash-completion b/etc/mpv.bash-completion new file mode 100644 index 0000000000..b49ae423ef --- /dev/null +++ b/etc/mpv.bash-completion @@ -0,0 +1,112 @@ +#!/bin/bash + +# +# This file is part of mpv. +# +# mpv is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public +# License as published by the Free Software Foundation; either +# version 2.1 of the License, or (at your option) any later version. +# +# mpv is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with mpv. If not, see . +# + +_mpv_get_args() +{ + local doc=$(mpv --list-options | grep -E "^\\s*$1\\s") + local partial="$2" + local type=$(echo "$doc" | awk '{print $2;}') + + if [ "$1" = "--show-profile" ]; then + # This is a special case + type="Profile" + fi + + declare -a candidates + case $type in + String) + echo "$doc" | grep -q '\[file\]' + if [ $? -eq 0 ]; then + if [ "$cur" = '=' ]; then + # Without this, _filedir will try and complete files starting with '=' + cur="" + fi + _filedir + return 0 + else + candidates=($(mpv $1=help | grep -v ':' | awk '{print $1;}')) + candidates+=("help") + fi + ;; + Flag) + candidates=("yes" "no" "help") + ;; + Choices:) + candidates=($(mpv $1=help | grep -v ':' | awk '{print $1;}')) + candidates+=("help") + ;; + Image) + candidates=($(mpv $1=help)) + candidates=("${candidates[@]:2}") + candidates+=("help") + ;; + Profile) + candidates=($(mpv $1= | grep -v ':' | awk '{print $1;}')) + ;; + *) + # There are other categories; some of which we could do something smarter + # about, with enough work. + ;; + esac + COMPREPLY=($(compgen -W "${candidates[*]}" -- "${partial}")) + if [ ${#COMPREPLY[@]} -gt 1 ]; then + compopt -o nospace mpv + fi +} + +_mpv() +{ + compopt +o nospace mpv + + # This regex detects special options where we don't want an '=' appended + local special_regex='Flag.*\[not in config files\]|Print' + local options=($(mpv --list-options | grep -v -E "$special_regex" |awk '{print "\\"$1;}' | grep '\--')) + local specials=($(mpv --list-options | grep -E "$special_regex" |awk '{print "\\"$1;}' | grep '\--')) + + # _filedir requires the current candidate be in $cur + local cur=${COMP_WORDS[COMP_CWORD]} + local prev=${COMP_WORDS[((COMP_CWORD - 1))]} + + if [ "$cur" = '=' ]; then + # If the current word is '=' then we are looking for an argument for the + # option specified by the previous word. + _mpv_get_args "$prev" + elif [ "$prev" = '=' ]; then + # If the previous word is '=' then we are completing an argument for the + # option specified by the word before the '='. + local prevprev=${COMP_WORDS[((COMP_CWORD - 2))]} + _mpv_get_args "$prevprev" "$cur" + else + case $cur in + -*) + COMPREPLY=($(compgen -W "${options[*]}" -S '=' -- "${cur}")) + local normal_count=${#COMPREPLY[@]} + COMPREPLY+=($(compgen -W "${specials[*]}" -- "${cur}")) + if [ $normal_count -gt 0 -o ${#COMPREPLY[@]} -gt 1 ]; then + compopt -o nospace mpv + fi + ;; + *) + _filedir + ;; + esac + fi +} + +complete -F _mpv mpv diff --git a/wscript b/wscript index c9724e8d02..d47133e6a6 100644 --- a/wscript +++ b/wscript @@ -950,6 +950,7 @@ _INSTALL_DIRS_LIST = [ ('confdir', '${SYSCONFDIR}/mpv', 'configuration files'), ('zshdir', '${DATADIR}/zsh/site-functions', 'zsh completion functions'), ('confloaddir', '${CONFDIR}', 'configuration files load directory'), + ('bashdir', '${DATADIR}/bash-completion/completions', 'bash completion functions'), ] def options(opt): diff --git a/wscript_build.py b/wscript_build.py index 3d901df3fb..bbce31dfea 100644 --- a/wscript_build.py +++ b/wscript_build.py @@ -737,6 +737,9 @@ def build(ctx): if ctx.env.ZSHDIR: ctx.install_as(ctx.env.ZSHDIR + '/_mpv', 'etc/_mpv.zsh') + if ctx.env.BASHDIR: + ctx.install_as(ctx.env.BASHDIR + '/mpv', 'etc/mpv.bash-completion') + ctx.install_files( ctx.env.DATADIR + '/applications', ['etc/mpv.desktop'] ) -- cgit v1.2.3