I use a simple zle widget print-current-word
to illustrate how you can extract the current word on the command line in simple cases, i.e. assuming that blanks are always word separators. (So this fails when quoting or escaped blanks come into play):
print-current-word() {
CURRENTWORD="${LBUFFER/* /}${RBUFFER/ */}"
print; print "The current word is: $CURRENTWORD"
}
zle -N print-current-word
$LBUFFER
and $RBUFFER
contains the command line left and right from the cursor, respectively.
${name/pattern/repl}
return the variable name with pattern replaced with repl. So in that case this trims in $LBUFFER
everything up to the last blank, leaving the portion left of the cursor of the current word. Analog for $RBUFFER
.
A more complicated approach would be:
print-current-word () {
local words i beginword
i=0
beginword=0
words=("${(z)BUFFER}")
while (( beginword <= CURSOR )); do
(( i++ ))
(( beginword += ${#words[$i]}+1 ))
done
CURRENTWORD="$words[$i]"
print; print "The current word is: $CURRENTWORD"
}
However, this one is also not free of assumptions, as it is assumes that every word is separated by exactly one blank (addition of +1 to beginword
).
Just a few words about some special things:
words=("${(z)BUFFER}")
splits $BUFFER
, i.e. the complete command line, into shell words using shell parsing rules by Expansion Flag (z)
and puts it into an array
(( ... ))
activates zsh's math mode
${#name}
gives the length of the variable name