Improve _get_comp_words_by_ref to return words' and
cword'
Usage: _get_comp_words_by_ref [OPTIONS] [VARNAMES] Available VARNAMES: cur Return cur within varname "cur" prev Return prev within varname "prev" words Return words within varname "words" cword Return cword within varname "cword" Available OPTIONS: -n EXCLUDE Characters out of $COMP_WORDBREAKS which should NOT be considered word breaks. This is useful for things like scp where we want to return host:path and not only path, so we would pass the colon (:) as -n option in this case. Bash-3 doesn't do word splitting, so this ensures we get the same word on both bash-3 and bash-4. -c VARNAME Return cur within specified VARNAME -p VARNAME Return prev within specified VARNAME -w VARNAME Return words within specified VARNAME -i VARNAME Return words within specified VARNAME Example usage: $ _get_comp_words_by_ref -n : cur prev
This commit is contained in:
parent
f8bafe285e
commit
bdca37a7bf
@ -330,53 +330,83 @@ ___get_cword_at_cursor_by_ref() {
|
|||||||
# (For example, if the line is "ls foobar",
|
# (For example, if the line is "ls foobar",
|
||||||
# and the cursor is here --------> ^
|
# and the cursor is here --------> ^
|
||||||
# Also one is able to cross over possible wordbreak characters.
|
# Also one is able to cross over possible wordbreak characters.
|
||||||
# Usage: _get_comp_words_by_ref [OPTIONS] VAR1 [VAR2 [VAR3]]
|
# Usage: _get_comp_words_by_ref [OPTIONS] [VARNAMES]
|
||||||
|
# Available VARNAMES:
|
||||||
|
# cur Return cur within varname "cur"
|
||||||
|
# prev Return prev within varname "prev"
|
||||||
|
# words Return words within varname "words"
|
||||||
|
# cword Return cword within varname "cword"
|
||||||
|
#
|
||||||
|
# Available OPTIONS:
|
||||||
|
# -n EXCLUDE Characters out of $COMP_WORDBREAKS which should NOT be
|
||||||
|
# considered word breaks. This is useful for things like scp
|
||||||
|
# where we want to return host:path and not only path, so we
|
||||||
|
# would pass the colon (:) as -n option in this case. Bash-3
|
||||||
|
# doesn't do word splitting, so this ensures we get the same
|
||||||
|
# word on both bash-3 and bash-4.
|
||||||
|
# -c VARNAME Return cur within specified VARNAME
|
||||||
|
# -p VARNAME Return prev within specified VARNAME
|
||||||
|
# -w VARNAME Return words within specified VARNAME
|
||||||
|
# -i VARNAME Return words within specified VARNAME
|
||||||
|
#
|
||||||
# Example usage:
|
# Example usage:
|
||||||
#
|
#
|
||||||
# $ _get_comp_words_by_ref -n : cur prev
|
# $ _get_comp_words_by_ref -n : cur prev
|
||||||
#
|
#
|
||||||
# Options: -n EXCLUDE Characters out of $COMP_WORDBREAKS which should NOT
|
|
||||||
# be considered word breaks. This is useful for things like scp where
|
|
||||||
# we want to return host:path and not only path, so we would pass the
|
|
||||||
# colon (:) as -n option in this case. Bash-3 doesn't do word splitting,
|
|
||||||
# so this ensures we get the same word on both bash-3 and bash-4.
|
|
||||||
# @see __get_comp_words_by_ref
|
# @see __get_comp_words_by_ref
|
||||||
_get_comp_words_by_ref() {
|
_get_comp_words_by_ref() {
|
||||||
# NOTE: The call to the main function __get_comp_words_by_ref() is wrapped
|
# NOTE: The call to the main function __get_comp_words_by_ref() is wrapped
|
||||||
# to make collisions with local variable name less likely.
|
# to make collisions with local variable names less likely.
|
||||||
local __words __cword __cur __var __vars
|
local __words __cword __cur
|
||||||
__get_comp_words_by_ref __words __cword __cur __vars "$@"
|
local __var_cur __var_prev __var_words __var_cword
|
||||||
set -- "${__vars[@]}"
|
|
||||||
eval $1=\$__cur
|
__get_comp_words_by_ref \
|
||||||
shift
|
__words __cword __cur \
|
||||||
for __var; do
|
__var_cur __var_prev __var_words __var_cword "$@"
|
||||||
((__cword--))
|
|
||||||
[[ ${__words[__cword]} ]] && eval $__var=\${__words[__cword]}
|
[[ $__var_cur ]] && eval $__var_cur=\$__cur
|
||||||
done
|
[[ $__var_prev ]] && ((__cword)) && eval $__var_prev=\${__words[__cword - 1]}
|
||||||
|
[[ $__var_words ]] && eval $__var_words=\${__words[@]}
|
||||||
|
[[ $__var_cword ]] && eval $__var_cword=\$__cword
|
||||||
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
# @param $1 words Name of variable to return words to
|
# @param $1 words Name of variable to return words to
|
||||||
# @param $2 cword Name of variable to return cword to
|
# @param $2 cword Name of variable to return cword to
|
||||||
# @param $3 cur Name of variable to return current word to complete to
|
# @param $3 cur Name of variable to return current word to complete to
|
||||||
# @param $4 varnames Name of variable to return array of variable names to
|
# @param $4 var_cur Name of variable to return current word to complete to
|
||||||
|
# @param $5 var_prev Name of variable to return previous word to complete to
|
||||||
|
# @param $6 var_words Name of variable to return words to complete to
|
||||||
|
# @param $7 var_cword Name of variable to return index of words to complete to
|
||||||
# @param $@ Arguments to _get_comp_words_by_ref()
|
# @param $@ Arguments to _get_comp_words_by_ref()
|
||||||
# @note Do not call this function directly but call `_get_comp_words_by_ref()'
|
# @note Do not call this function directly but call `_get_comp_words_by_ref()'
|
||||||
# instead to make variable name collisions less likely
|
# instead to make variable name collisions less likely
|
||||||
|
#
|
||||||
# @see _get_comp_words_by_ref()
|
# @see _get_comp_words_by_ref()
|
||||||
__get_comp_words_by_ref()
|
__get_comp_words_by_ref()
|
||||||
{
|
{
|
||||||
local exclude flag i OPTIND=5 # Skip first four arguments
|
local exclude flag i OPTIND=8 # Skip first seven arguments
|
||||||
local cword words cur varnames=()
|
local cword words cur
|
||||||
while getopts "n:" flag "$@"; do
|
local var_cur var_cword var_prev var_words
|
||||||
|
|
||||||
|
while getopts "c:i:n:p:w:" flag "$@"; do
|
||||||
case $flag in
|
case $flag in
|
||||||
|
c) var_cur=$OPTARG ;;
|
||||||
|
i) var_cword=$OPTARG ;;
|
||||||
n) exclude=$OPTARG ;;
|
n) exclude=$OPTARG ;;
|
||||||
|
p) var_prev=$OPTARG ;;
|
||||||
|
w) var_words=$OPTARG ;;
|
||||||
esac
|
esac
|
||||||
done
|
done
|
||||||
varnames=( ${!OPTIND} )
|
|
||||||
let "OPTIND += 1"
|
|
||||||
while [[ $# -ge $OPTIND ]]; do
|
while [[ $# -ge $OPTIND ]]; do
|
||||||
varnames+=( ${!OPTIND} )
|
case ${!OPTIND} in
|
||||||
|
cur) var_cur=cur ;;
|
||||||
|
prev) var_prev=prev ;;
|
||||||
|
cword) var_cword=cword ;;
|
||||||
|
words) var_words=words ;;
|
||||||
|
*) echo "error: $FUNCNAME(): unknown argument: ${!OPTIND}"
|
||||||
|
esac
|
||||||
let "OPTIND += 1"
|
let "OPTIND += 1"
|
||||||
done
|
done
|
||||||
|
|
||||||
@ -385,7 +415,10 @@ __get_comp_words_by_ref()
|
|||||||
eval $1=\( \"\${words[@]}\" \)
|
eval $1=\( \"\${words[@]}\" \)
|
||||||
eval $2=\$cword
|
eval $2=\$cword
|
||||||
eval $3=\$cur
|
eval $3=\$cur
|
||||||
eval $4=\( \"\${varnames[@]}\" \)
|
eval $4=\$var_cur
|
||||||
|
eval $5=\$var_prev
|
||||||
|
eval $6=\${var_words[@]}
|
||||||
|
eval $7=\$var_cword
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -5,7 +5,10 @@ proc setup {} {
|
|||||||
|
|
||||||
|
|
||||||
proc teardown {} {
|
proc teardown {} {
|
||||||
assert_bash_exec {unset COMP_CWORD COMP_LINE COMP_POINT COMP_WORDS cur prev prev2}
|
assert_bash_exec { \
|
||||||
|
unset COMP_CWORD COMP_LINE COMP_POINT COMP_WORDS cur prev words cword \
|
||||||
|
cur2 prev2 words2 cword2 \
|
||||||
|
}
|
||||||
# Delete 'COMP_WORDBREAKS' occupying two lines
|
# Delete 'COMP_WORDBREAKS' occupying two lines
|
||||||
assert_env_unmodified {
|
assert_env_unmodified {
|
||||||
/COMP_WORDBREAKS=/{N
|
/COMP_WORDBREAKS=/{N
|
||||||
@ -46,8 +49,8 @@ sync_after_int
|
|||||||
|
|
||||||
|
|
||||||
set test "a b |"; # | = cursor position
|
set test "a b |"; # | = cursor position
|
||||||
set cmd {COMP_WORDS=(a b ''); COMP_CWORD=2; COMP_LINE='a b '; COMP_POINT=4; _get_comp_words_by_ref cur prev prev2; echo "$cur $prev $prev2"}
|
set cmd {COMP_WORDS=(a b ''); COMP_CWORD=2; COMP_LINE='a b '; COMP_POINT=4; _get_comp_words_by_ref cur prev; echo "$cur $prev"}
|
||||||
assert_bash_list {" b a"} $cmd $test
|
assert_bash_list {" b"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
sync_after_int
|
sync_after_int
|
||||||
@ -192,8 +195,8 @@ if {[lindex $::BASH_VERSINFO 0] <= 3} {
|
|||||||
}; # if
|
}; # if
|
||||||
append cmd {; COMP_LINE='a b c:'; COMP_POINT=6}
|
append cmd {; COMP_LINE='a b c:'; COMP_POINT=6}
|
||||||
assert_bash_exec $cmd $test
|
assert_bash_exec $cmd $test
|
||||||
set cmd {_get_comp_words_by_ref -n : cur prev; echo "$cur $prev $prev2"}
|
set cmd {_get_comp_words_by_ref -n : cur prev; echo "$cur $prev"}
|
||||||
assert_bash_list {"c: b a"} $cmd $test
|
assert_bash_list {"c: b"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
sync_after_int
|
sync_after_int
|
||||||
@ -336,4 +339,48 @@ expect {
|
|||||||
sync_after_int
|
sync_after_int
|
||||||
|
|
||||||
|
|
||||||
|
set test {unknown argument should raise error}
|
||||||
|
set cmd {_get_comp_words_by_ref dummy}
|
||||||
|
assert_bash_list {"error: __get_comp_words_by_ref(): unknown argument: dummy"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
|
sync_after_int
|
||||||
|
|
||||||
|
|
||||||
|
set test "a b| to all vars"; # | = cursor position
|
||||||
|
set cmd {COMP_WORDS=(a b); COMP_CWORD=1; COMP_LINE='a b'; COMP_POINT=3}
|
||||||
|
assert_bash_exec $cmd
|
||||||
|
set cmd { \
|
||||||
|
_get_comp_words_by_ref words cword prev cur; echo "${words[@]} $cword $cur $prev" \
|
||||||
|
}
|
||||||
|
assert_bash_list {"a b 1 b a"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
|
sync_after_int
|
||||||
|
|
||||||
|
|
||||||
|
set test "a b| to alternate vars"; # | = cursor position
|
||||||
|
set cmd {COMP_WORDS=(a b); COMP_CWORD=1; COMP_LINE='a b'; COMP_POINT=3;}
|
||||||
|
assert_bash_exec $cmd
|
||||||
|
set cmd {_get_comp_words_by_ref -c cur2 -p prev2 -w words2 -i cword2}
|
||||||
|
assert_bash_exec $cmd
|
||||||
|
set cmd {echo "$cur2 $prev2 ${words2[@]} $cword2"}
|
||||||
|
assert_bash_list {"b a a b 1"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
|
sync_after_int
|
||||||
|
|
||||||
|
|
||||||
|
set test "a b| to alternate vars"; # | = cursor position
|
||||||
|
set cmd {COMP_WORDS=(a b); COMP_CWORD=1; COMP_LINE='a b'; COMP_POINT=3;}
|
||||||
|
assert_bash_exec $cmd
|
||||||
|
set cmd {_get_comp_words_by_ref -c cur2 -p prev2 -w words2 -i cword2}
|
||||||
|
assert_bash_exec $cmd
|
||||||
|
set cmd {echo "$cur2 $prev2 ${words2[@]} $cword2"}
|
||||||
|
assert_bash_list {"b a a b 1"} $cmd $test
|
||||||
|
|
||||||
|
|
||||||
|
sync_after_int
|
||||||
|
|
||||||
|
|
||||||
teardown
|
teardown
|
||||||
|
Loading…
x
Reference in New Issue
Block a user