zsh-users
 help / color / mirror / code / Atom feed
* incr. search: skip duplicates on the same history event
@ 2007-06-16 18:31 Frank Terbeck
  2007-06-16 19:03 ` Richard Hartmann
  0 siblings, 1 reply; 3+ messages in thread
From: Frank Terbeck @ 2007-06-16 18:31 UTC (permalink / raw)
  To: zsh users

Hey list,

Someone on IRC came up with the following question:

Say, you got a few history events that got the string 'make' in them:

  % make depend
  % make clean ; make all ; sudo make install

After a few more commands, you do a
'history-incremental-search-backward' for 'make' and get back the last
event with the three make calls on one line. Now you can reinvoke
'history-incremental-search-backward' again to jump back to earlier
occurrences of 'make' in the history:

  % make clean ; make all ; sudo make install
    ^            ^               ^
    |            |               |
    |            |               \-- ^Rmake
    |            |
    |            \-- 1st time you hit ^R after making
    |                your initial search.
    |
    \-- after hitting ^R for the 2nd time you end up here.

Now, the idea is to after searching backwards for the first time
(^Rmake), hitting ^R again, to go further backwards should ignore any
other occurrences of 'make' in the current history event and jump
directly to the next history event containing 'make' ('make depend')
in the example above.

I have been playing around to get this working and had a few rather
complex solutions, that all failed somehow. :-)

So, I took another approach and the closest I got (which works) is the
following. It exists the incremental search and re-enters it if you
continue typing. That is not an exceptionally nice solution and it
would require additional tweaking to become usable.

[snip]
self-insert () {
  if [[ $LASTWIDGET == incsearch ]] ; then
    zle history-incremental-search-backward $LASTSEARCH
  fi
  zle .self-insert
}
zle -N self-insert
incsearch () {
  if [[ $LASTWIDGET == incsearch ]] ; then
    zle history-search-backward
  else
    zle history-incremental-search-backward
  fi
}
zle -N incsearch
bindkey '^r' incsearch
[snap]

However, I hope that someone has got a better idea to solve this.

Regards, Frank

-- 
In protocol design, perfection has been reached not when there is
nothing left to add, but when there is nothing left to take away.
                                                  -- RFC 1925


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: incr. search: skip duplicates on the same history event
  2007-06-16 18:31 incr. search: skip duplicates on the same history event Frank Terbeck
@ 2007-06-16 19:03 ` Richard Hartmann
  2007-06-17  0:32   ` Bart Schaefer
  0 siblings, 1 reply; 3+ messages in thread
From: Richard Hartmann @ 2007-06-16 19:03 UTC (permalink / raw)
  To: zsh users

[-- Attachment #1: Type: text/plain, Size: 187 bytes --]

I would like to add that, ideally, the ^R should jump to make clean, not
make install (if possible).

Also, I would like to ft++ for biting into my problem as hard as he did :)


Richard

[-- Attachment #2: Type: text/html, Size: 206 bytes --]

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: incr. search: skip duplicates on the same history event
  2007-06-16 19:03 ` Richard Hartmann
@ 2007-06-17  0:32   ` Bart Schaefer
  0 siblings, 0 replies; 3+ messages in thread
From: Bart Schaefer @ 2007-06-17  0:32 UTC (permalink / raw)
  To: zsh users

On Jun 16,  8:31pm, Frank Terbeck wrote:
}
} Now, the idea is to after searching backwards for the first time
} (^Rmake), hitting ^R again, to go further backwards should ignore any
} other occurrences of 'make' in the current history event and jump
} directly to the next history event containing 'make' ('make depend')
} in the example above.

On Jun 16,  9:03pm, Richard Hartmann wrote:
} 
} I would like to add that, ideally, the ^R should jump to make clean, not
} make install (if possible).

This is very difficult.  There's no non-interactive history-search
operation that leaves the cursor at the word that was found, and the
incremental search won't let you "interrupt" it to force the cursor
farther towards the beginning of the line until the *next* character
is typed *after* it has stopped at the match near the end of the line.

On Jun 16,  8:31pm, Frank Terbeck wrote:
} 
} So, I took another approach and the closest I got (which works) is the
} following. It exists the incremental search and re-enters it if you
} continue typing. That is not an exceptionally nice solution and it
} would require additional tweaking to become usable.

Unfortunately that's probably the best approach to take without a lot
of work.  If history-incremental-search-* were implemented with real
widgets and a named keymap, you could copy the keymap, selectively
replace some widgets, and be on your way; but instead it's implemented
by hijacking specific widget names internally, so replacing them has no
effect within an incremental search in progress.

Another complication is that a wrapper for history-incremental-search-*
has to handle its own looping.  I'm not precisely sure what's going on,
but pressing the key that's bound to incsearch (which would, from the
top level, exit history-incremental-search-backward and execute your
widget) merely interrupts the search and returns control to the wrapper
*unless* the call to the wrapper *is* the first one (from the top level),
in which case one nested call is OK.  Maybe it has something to do with
whether an argument is passed to history-incremental-search-backward.

Then there are the strangenesses of up-line-* and beginning-of-line
behaving differently in multi-line buffers vs. single-line buffers, etc.
Perhaps the most annoying is that if the cursor is already on the first
character of a string matching the argument search pattern, you have
to invoke the search twice to move the cursor to the next occurrence
-- which means that in the wrapper function you *must* move the cursor
before trying another search -- which means moving up a history entry if
you're at the beginning of one -- so it's impossible to leave the buffer
unchanged when the search fails, though you can restore the old buffer
once the search is abandoned.

Having taken about 10 different stabs at this without really getting
any of them working any better than what Frank posted, I'm going to
leave this to someone with the patience to actually populate an entire
keymap.


^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2007-06-17  0:33 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2007-06-16 18:31 incr. search: skip duplicates on the same history event Frank Terbeck
2007-06-16 19:03 ` Richard Hartmann
2007-06-17  0:32   ` Bart Schaefer

Code repositories for project(s) associated with this public inbox

	https://git.vuxu.org/mirror/zsh/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).