Merge pull request #125 from zsh-users/features/execute_widget

Add a widget to accept and execute the current suggestion.
This commit is contained in:
Eric Freese 2016-03-04 18:57:43 -07:00
commit 9df362f783
6 changed files with 95 additions and 4 deletions

View file

@ -70,6 +70,7 @@ This plugin works by triggering custom behavior when certain [zle widgets](http:
- `ZSH_AUTOSUGGEST_CLEAR_WIDGETS`: Widgets in this array will clear the suggestion when invoked. - `ZSH_AUTOSUGGEST_CLEAR_WIDGETS`: Widgets in this array will clear the suggestion when invoked.
- `ZSH_AUTOSUGGEST_ACCEPT_WIDGETS`: Widgets in this array will accept the suggestion when invoked. - `ZSH_AUTOSUGGEST_ACCEPT_WIDGETS`: Widgets in this array will accept the suggestion when invoked.
- `ZSH_AUTOSUGGEST_EXECUTE_WIDGETS`: Widgets in this array will execute the suggestion when invoked.
- `ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS`: Widgets in this array will partially accept the suggestion when invoked. - `ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS`: Widgets in this array will partially accept the suggestion when invoked.
Widgets not in any of these lists will update the suggestion when invoked. Widgets not in any of these lists will update the suggestion when invoked.
@ -79,10 +80,11 @@ Widgets not in any of these lists will update the suggestion when invoked.
### Key Bindings ### Key Bindings
This plugin provides two widgets that you can use with `bindkey`: This plugin provides three widgets that you can use with `bindkey`:
1. `autosuggest-accept`: Accepts the current suggestion. 1. `autosuggest-accept`: Accepts the current suggestion.
2. `autosuggest-clear`: Clears the current suggestion. 2. `autosuggest-execute`: Accepts and executes the current suggestion.
3. `autosuggest-clear`: Clears the current suggestion.
For example, this would bind <kbd>ctrl</kbd> + <kbd>space</kbd> to accept the current suggestion. For example, this would bind <kbd>ctrl</kbd> + <kbd>space</kbd> to accept the current suggestion.

View file

@ -177,6 +177,29 @@ testWidgetFunctionAcceptCursorNotAtEnd() {
"$POSTDISPLAY" "$POSTDISPLAY"
} }
testWidgetFunctionExecute() {
BUFFER="ec"
POSTDISPLAY="ho hello"
stub _zsh_autosuggest_invoke_original_widget
_zsh_autosuggest_execute
assertTrue \
"accept-line not invoked" \
"stub_called_with _zsh_autosuggest_invoke_original_widget 'accept-line'"
assertEquals \
"BUFFER was not modified" \
"echo hello" \
"$BUFFER"
assertEquals \
"POSTDISPLAY was not cleared" \
"" \
"$POSTDISPLAY"
}
testWidgetFunctionPartialAcceptCursorMovesOutOfBuffer() { testWidgetFunctionPartialAcceptCursorMovesOutOfBuffer() {
BUFFER="ec" BUFFER="ec"
POSTDISPLAY="ho hello" POSTDISPLAY="ho hello"
@ -281,6 +304,32 @@ testWidgetClear() {
"stub_called _zsh_autosuggest_highlight_apply" "stub_called _zsh_autosuggest_highlight_apply"
} }
testWidgetExecute() {
stub _zsh_autosuggest_highlight_reset
stub _zsh_autosuggest_execute
stub _zsh_autosuggest_highlight_apply
# Call the function pointed to by the widget since we can't call
# the widget itself when zle is not active
${widgets[autosuggest-execute]#*:} "original-widget"
assertTrue \
"autosuggest-execute widget does not exist" \
"zle -l autosuggest-execute"
assertTrue \
"highlight_reset was not called" \
"stub_called _zsh_autosuggest_highlight_reset"
assertTrue \
"widget function was not called" \
"stub_called _zsh_autosuggest_execute"
assertTrue \
"highlight_apply was not called" \
"stub_called _zsh_autosuggest_highlight_apply"
}
testEscapeCommandPrefix() { testEscapeCommandPrefix() {
assertEquals \ assertEquals \
"Did not escape single backslash" \ "Did not escape single backslash" \

View file

@ -55,6 +55,8 @@ _zsh_autosuggest_bind_widgets() {
_zsh_autosuggest_bind_widget $widget clear _zsh_autosuggest_bind_widget $widget clear
elif [ ${ZSH_AUTOSUGGEST_ACCEPT_WIDGETS[(r)$widget]} ]; then elif [ ${ZSH_AUTOSUGGEST_ACCEPT_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget accept _zsh_autosuggest_bind_widget $widget accept
elif [ ${ZSH_AUTOSUGGEST_EXECUTE_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget execute
elif [ ${ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS[(r)$widget]} ]; then elif [ ${ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget partial_accept _zsh_autosuggest_bind_widget $widget partial_accept
else else

View file

@ -32,6 +32,10 @@ ZSH_AUTOSUGGEST_ACCEPT_WIDGETS=(
vi-end-of-line vi-end-of-line
) )
# Widgets that accept the entire suggestion and execute it
ZSH_AUTOSUGGEST_EXECUTE_WIDGETS=(
)
# Widgets that accept the suggestion as far as the cursor moves # Widgets that accept the suggestion as far as the cursor moves
ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS=( ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS=(
forward-word forward-word

View file

@ -47,6 +47,19 @@ _zsh_autosuggest_accept() {
_zsh_autosuggest_invoke_original_widget $@ _zsh_autosuggest_invoke_original_widget $@
} }
# Accept the entire suggestion and execute it
_zsh_autosuggest_execute() {
# Add the suggestion to the buffer
BUFFER="$BUFFER$POSTDISPLAY"
# Remove the suggestion
unset POSTDISPLAY
# Call the original `accept-line` to handle syntax highlighting or
# other potential custom behavior
_zsh_autosuggest_invoke_original_widget "accept-line"
}
# Partially accept the suggestion # Partially accept the suggestion
_zsh_autosuggest_partial_accept() { _zsh_autosuggest_partial_accept() {
# Save the contents of the buffer so we can restore later if needed # Save the contents of the buffer so we can restore later if needed
@ -71,7 +84,7 @@ _zsh_autosuggest_partial_accept() {
fi fi
} }
for action in clear modify accept partial_accept; do for action in clear modify accept partial_accept execute; do
eval "_zsh_autosuggest_widget_$action() { eval "_zsh_autosuggest_widget_$action() {
_zsh_autosuggest_highlight_reset _zsh_autosuggest_highlight_reset
_zsh_autosuggest_$action \$@ _zsh_autosuggest_$action \$@
@ -81,3 +94,4 @@ done
zle -N autosuggest-accept _zsh_autosuggest_widget_accept zle -N autosuggest-accept _zsh_autosuggest_widget_accept
zle -N autosuggest-clear _zsh_autosuggest_widget_clear zle -N autosuggest-clear _zsh_autosuggest_widget_clear
zle -N autosuggest-execute _zsh_autosuggest_widget_execute

View file

@ -58,6 +58,10 @@ ZSH_AUTOSUGGEST_ACCEPT_WIDGETS=(
vi-end-of-line vi-end-of-line
) )
# Widgets that accept the entire suggestion and execute it
ZSH_AUTOSUGGEST_EXECUTE_WIDGETS=(
)
# Widgets that accept the suggestion as far as the cursor moves # Widgets that accept the suggestion as far as the cursor moves
ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS=( ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS=(
forward-word forward-word
@ -159,6 +163,8 @@ _zsh_autosuggest_bind_widgets() {
_zsh_autosuggest_bind_widget $widget clear _zsh_autosuggest_bind_widget $widget clear
elif [ ${ZSH_AUTOSUGGEST_ACCEPT_WIDGETS[(r)$widget]} ]; then elif [ ${ZSH_AUTOSUGGEST_ACCEPT_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget accept _zsh_autosuggest_bind_widget $widget accept
elif [ ${ZSH_AUTOSUGGEST_EXECUTE_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget execute
elif [ ${ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS[(r)$widget]} ]; then elif [ ${ZSH_AUTOSUGGEST_PARTIAL_ACCEPT_WIDGETS[(r)$widget]} ]; then
_zsh_autosuggest_bind_widget $widget partial_accept _zsh_autosuggest_bind_widget $widget partial_accept
else else
@ -252,6 +258,19 @@ _zsh_autosuggest_accept() {
_zsh_autosuggest_invoke_original_widget $@ _zsh_autosuggest_invoke_original_widget $@
} }
# Accept the entire suggestion and execute it
_zsh_autosuggest_execute() {
# Add the suggestion to the buffer
BUFFER="$BUFFER$POSTDISPLAY"
# Remove the suggestion
unset POSTDISPLAY
# Call the original `accept-line` to handle syntax highlighting or
# other potential custom behavior
_zsh_autosuggest_invoke_original_widget "accept-line"
}
# Partially accept the suggestion # Partially accept the suggestion
_zsh_autosuggest_partial_accept() { _zsh_autosuggest_partial_accept() {
# Save the contents of the buffer so we can restore later if needed # Save the contents of the buffer so we can restore later if needed
@ -276,7 +295,7 @@ _zsh_autosuggest_partial_accept() {
fi fi
} }
for action in clear modify accept partial_accept; do for action in clear modify accept partial_accept execute; do
eval "_zsh_autosuggest_widget_$action() { eval "_zsh_autosuggest_widget_$action() {
_zsh_autosuggest_highlight_reset _zsh_autosuggest_highlight_reset
_zsh_autosuggest_$action \$@ _zsh_autosuggest_$action \$@
@ -286,6 +305,7 @@ done
zle -N autosuggest-accept _zsh_autosuggest_widget_accept zle -N autosuggest-accept _zsh_autosuggest_widget_accept
zle -N autosuggest-clear _zsh_autosuggest_widget_clear zle -N autosuggest-clear _zsh_autosuggest_widget_clear
zle -N autosuggest-execute _zsh_autosuggest_widget_execute
#--------------------------------------------------------------------# #--------------------------------------------------------------------#
# Suggestion # # Suggestion #