diff --git a/conf.d/key_bindings.fish b/conf.d/key_bindings.fish index 1f9793f..588e073 100644 --- a/conf.d/key_bindings.fish +++ b/conf.d/key_bindings.fish @@ -65,7 +65,6 @@ function fish_user_key_bindings bind ctrl-alt-u _replace_command_token type -q qalc && bind ctrl-alt-= _qalc_eval bind ctrl-enter _smart_execute - bind @@ __fzf_inline_picker bind ctrl-right nextd-or-forward-word bind \e\[1\;5C nextd-or-forward-word @@ -77,8 +76,17 @@ function fish_user_key_bindings bind --mode $mode ctrl-alt-u _replace_command_token type -q qalc && bind --mode $mode ctrl-alt-= _qalc_eval bind --mode $mode ctrl-enter _smart_execute - bind --mode $mode @@ __fzf_inline_picker bind --mode $mode ctrl-right nextd-or-forward-word bind --mode $mode \e\[1\;5C nextd-or-forward-word end + + # @ is Emacs/Vi-insert only. Emacs bindings and Vi's "default" (normal) + # mode share the same bind_mode name, so a mode-less `bind @` would also + # land in Vi normal mode, turning its current no-op @ into a self-insert. + # Register the mode-less form only when Vi bindings aren't the active + # base, and rely on the explicit insert-mode bind otherwise. + if test "$fish_key_bindings" != fish_vi_key_bindings + bind @ __fzf_inline_picker + end + bind --mode insert @ __fzf_inline_picker end diff --git a/docs/manual/03-key-bindings.md b/docs/manual/03-key-bindings.md index 7841c13..4df6c5f 100644 --- a/docs/manual/03-key-bindings.md +++ b/docs/manual/03-key-bindings.md @@ -42,9 +42,11 @@ are active in Insert, Normal, and Visual modes unless noted. pressing Enter a second time for certain fast-path commands (speedtest-fast, etc.). - @@ FZF inline picker. Type @@ anywhere on the command - line to open an fzf picker and insert a selection - at the cursor position. + @@ FZF inline picker. Type @ twice anywhere on the + command line to open an fzf picker and replace the + @@ with the selection. The @@ must be typed as its + own token: "test @@" triggers it, but "test@@" does + not. Ctrl+Right Accept autosuggestion one word/directory segment at a time. (Restores Fish 3.x behavior by binding diff --git a/functions/__fzf_inline_picker.fish b/functions/__fzf_inline_picker.fish index 7913d45..f9e05fb 100644 --- a/functions/__fzf_inline_picker.fish +++ b/functions/__fzf_inline_picker.fish @@ -5,23 +5,29 @@ # __fzf_inline_picker # # DESCRIPTION -# Opens an interactive fzf session and injects the selected item directly -# into the command line at the cursor position. Bound to @@ by default. +# Bound to the @ key. Self-inserts @ normally; on a second consecutive @ +# (detected by looking behind at the current token rather than making fish +# buffer ahead for a chord), opens an interactive fzf session and replaces +# the bare @ with the selected item. Cancelling leaves a literal @@ behind. # Repaints the prompt after selection or cancellation. # # EXIT STATUS -# 0 Always; no-op if fzf is cancelled +# 0 Always # # EXAMPLE -# # Press @@ at the command prompt to open fzf and insert the selected item. +# # Press @ twice at the command prompt to open fzf and insert the +# # selected item in place of the second @, then keep typing to extend it +# # (e.g. a trailing /subdir). function __fzf_inline_picker - # Open fzf and capture selection - set -l selection (fzf) - - if test -n "$selection" - # Injects text instantly at the cursor - commandline -i (string escape -- $selection) + if test (commandline -t) = @ + set -l selection (fzf) + if test -n "$selection" + commandline -t -- (string escape -- $selection) + else + commandline -t -- @@ + end + commandline -f repaint + else + commandline -i @ end - # Refresh the line display - commandline -f repaint end