prompt-toolkit / python-prompt-toolkit

Library for building powerful interactive command line applications in Python
https://python-prompt-toolkit.readthedocs.io/
BSD 3-Clause "New" or "Revised" License
9.28k stars 715 forks source link

Replaying history #499

Open randy3k opened 7 years ago

randy3k commented 7 years ago

After using Control-R to search history and executing the result, it would be nice to have the down key mapped to the next item of the searched result in the history list. For example.

> a = 1
> b = 1
> c = 1
> # Control-R and search for "a = 1" and then hit enter
> a = 1
> # press down key here to load "b = 1" and then hit enter
> b = 1
> # press down key again to load "c = 1"

With such implementation, it is much easier to replay history commands.

randy3k commented 7 years ago

Similar feature C-o has been implemented at https://github.com/jonathanslenders/python-prompt-toolkit/issues/416 but I argue that the down arrow is more intuitive.

PS: I am not using the prompt_toolkit.shortcuts.prompt function but rather have my own classes, so history is persistent between prompts.

randy3k commented 7 years ago

For reference, I used the following keybinds to mimick this feature. I am wishing there will be some kind of official support.

last_working_index = [-1]
last_history = Condition(lambda cli: cli.current_buffer.working_index == len(cli.current_buffer._working_lines)-1)
is_empty = Condition(lambda cli: len(cli.current_buffer.text) == 0)

@registry.add_binding(Keys.ControlJ, filter=foo & bar)
def _(event):
    last_working_index[0] = event.cli.current_buffer.working_index
    # do your stuff

@registry.add_binding(Keys.Down, filter=is_empty & last_history)
def _(event):
    if last_working_index[0] >= 0:
        event.cli.current_buffer.go_to_history(last_working_index[0] + 1)
        last_working_index[0] = -1