Zsh Mailing List Archive
Messages sorted by: Reverse Date, Date, Thread, Author

Re: history-incremental-search-backward and personnal zle widget

On Dec 29,  2:24am, antho.charles@xxxxxxxxx wrote:
} zle -N rationalise-dot
} bindkey . rationalise-dot
} but when I type a dot in a history-incremental-search-backward ( ^R ),
} it stops the search and insert a dot in the line instead of inserting
} a dot in the searched string.

history-incremental-search-* were added to the shell long before there
were user-defined widgets or multiple keymaps, so they are implemented
by hijacking existing widgets by name rather than by adding new widgets.
Consequently when the manual says "an undefined key" it really means a
key that is bound to anything outside the small number of widgets whose
names are recognized.

There are two possible approaches, then.  Casper has outlined one of
them:  Reset the key bindings around the search so that dot is bound
to a widget that the minibuffer knows about.  The other is to replace
a standard widget with a variation of your rationalise-dot function.

On Dec 29,  6:51pm, Casper Gripenberg wrote:
: function scrub-history-incremental-search-backward () {
:    bindkey -r "."
:    zle .history-incremental-search-backward
:    bindkey "." rationalise-dot
: }

This won't quite work.  You need to replace
   bindkey -r "."
   bindkey "." self-insert

Otherwise there is no binding for dot and it's truly an undefined key.
Further you need to replace both history-incremental-search-backward
and history-incremental-search-forward with similar functions.

That bindkey is a clue to how to implement the second option:

    rationalise-dot() {
       if [[ $KEYS = "." && $LBUFFER = *.. ]]; then
	  zle .self-insert "$@"
    zle -N self-insert rationalise-dot

Now your rationalise-dot widget is actually *named* self-insert, which
is a widget known to the minibuffer and therefore everything works.

The drawback to the latter solution is that there are other tricks that
rely on redefining self-insert, so you may have to choose which of the
various possibilities is most important to you.

So instead you could pick another widget that the minibuffer "knows
about" and redefine that.  A good choice is "magic-space" because (1)
it's already "magic" and (2) it's designed to be bound to a specific
key, unlike self-insert which is bound to almost everything.

    magic-space-rationalise-dot() {
       case "$KEYS" in
       (" ") zle .magic-space "$@" ;;
       ( . ) [[ $LBUFFER = *.. ]] && LBUFFER+=/. ;&
       ( * ) zle .self-insert "$@" ;;
    zle -N magic-space magic-space-rationalise-dot
    bindkey "." magic-space

Note that binding space to magic-space still works as it did before.

Messages sorted by: Reverse Date, Date, Thread, Author