diff options
author | monster <[email protected]> | 2022-07-07 14:41:37 +0300 |
---|---|---|
committer | monster <[email protected]> | 2022-07-07 14:41:37 +0300 |
commit | 06e5c21a835c0e923506c4ff27929f34e00761c2 (patch) | |
tree | 75efcbc6854ef9bd476eb8bf00cc5c900da436a2 /contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding | |
parent | 03f024c4412e3aa613bb543cf1660176320ba8f4 (diff) |
fix ya.make
Diffstat (limited to 'contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding')
15 files changed, 0 insertions, 6088 deletions
diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/__init__.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/__init__.py deleted file mode 100644 index baffc488252..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/__init__.py +++ /dev/null @@ -1 +0,0 @@ -from __future__ import unicode_literals diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/__init__.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/__init__.py deleted file mode 100644 index e69de29bb2d..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/__init__.py +++ /dev/null diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/basic.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/basic.py deleted file mode 100644 index 401135dec06..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/basic.py +++ /dev/null @@ -1,407 +0,0 @@ -# pylint: disable=function-redefined -from __future__ import unicode_literals - -from prompt_toolkit.enums import DEFAULT_BUFFER -from prompt_toolkit.filters import HasSelection, Condition, EmacsInsertMode, ViInsertMode -from prompt_toolkit.keys import Keys -from prompt_toolkit.layout.screen import Point -from prompt_toolkit.mouse_events import MouseEventType, MouseEvent -from prompt_toolkit.renderer import HeightIsUnknownError -from prompt_toolkit.utils import suspend_to_background_supported, is_windows - -from .named_commands import get_by_name -from ..registry import Registry - - -__all__ = ( - 'load_basic_bindings', - 'load_abort_and_exit_bindings', - 'load_basic_system_bindings', - 'load_auto_suggestion_bindings', -) - -def if_no_repeat(event): - """ Callable that returns True when the previous event was delivered to - another handler. """ - return not event.is_repeat - - -def load_basic_bindings(): - registry = Registry() - insert_mode = ViInsertMode() | EmacsInsertMode() - handle = registry.add_binding - has_selection = HasSelection() - - @handle(Keys.ControlA) - @handle(Keys.ControlB) - @handle(Keys.ControlC) - @handle(Keys.ControlD) - @handle(Keys.ControlE) - @handle(Keys.ControlF) - @handle(Keys.ControlG) - @handle(Keys.ControlH) - @handle(Keys.ControlI) - @handle(Keys.ControlJ) - @handle(Keys.ControlK) - @handle(Keys.ControlL) - @handle(Keys.ControlM) - @handle(Keys.ControlN) - @handle(Keys.ControlO) - @handle(Keys.ControlP) - @handle(Keys.ControlQ) - @handle(Keys.ControlR) - @handle(Keys.ControlS) - @handle(Keys.ControlT) - @handle(Keys.ControlU) - @handle(Keys.ControlV) - @handle(Keys.ControlW) - @handle(Keys.ControlX) - @handle(Keys.ControlY) - @handle(Keys.ControlZ) - @handle(Keys.F1) - @handle(Keys.F2) - @handle(Keys.F3) - @handle(Keys.F4) - @handle(Keys.F5) - @handle(Keys.F6) - @handle(Keys.F7) - @handle(Keys.F8) - @handle(Keys.F9) - @handle(Keys.F10) - @handle(Keys.F11) - @handle(Keys.F12) - @handle(Keys.F13) - @handle(Keys.F14) - @handle(Keys.F15) - @handle(Keys.F16) - @handle(Keys.F17) - @handle(Keys.F18) - @handle(Keys.F19) - @handle(Keys.F20) - @handle(Keys.ControlSpace) - @handle(Keys.ControlBackslash) - @handle(Keys.ControlSquareClose) - @handle(Keys.ControlCircumflex) - @handle(Keys.ControlUnderscore) - @handle(Keys.Backspace) - @handle(Keys.Up) - @handle(Keys.Down) - @handle(Keys.Right) - @handle(Keys.Left) - @handle(Keys.ShiftUp) - @handle(Keys.ShiftDown) - @handle(Keys.ShiftRight) - @handle(Keys.ShiftLeft) - @handle(Keys.Home) - @handle(Keys.End) - @handle(Keys.Delete) - @handle(Keys.ShiftDelete) - @handle(Keys.ControlDelete) - @handle(Keys.PageUp) - @handle(Keys.PageDown) - @handle(Keys.BackTab) - @handle(Keys.Tab) - @handle(Keys.ControlLeft) - @handle(Keys.ControlRight) - @handle(Keys.ControlUp) - @handle(Keys.ControlDown) - @handle(Keys.Insert) - @handle(Keys.Ignore) - def _(event): - """ - First, for any of these keys, Don't do anything by default. Also don't - catch them in the 'Any' handler which will insert them as data. - - If people want to insert these characters as a literal, they can always - do by doing a quoted insert. (ControlQ in emacs mode, ControlV in Vi - mode.) - """ - pass - - # Readline-style bindings. - handle(Keys.Home)(get_by_name('beginning-of-line')) - handle(Keys.End)(get_by_name('end-of-line')) - handle(Keys.Left)(get_by_name('backward-char')) - handle(Keys.Right)(get_by_name('forward-char')) - handle(Keys.ControlUp)(get_by_name('previous-history')) - handle(Keys.ControlDown)(get_by_name('next-history')) - handle(Keys.ControlL)(get_by_name('clear-screen')) - - handle(Keys.ControlK, filter=insert_mode)(get_by_name('kill-line')) - handle(Keys.ControlU, filter=insert_mode)(get_by_name('unix-line-discard')) - handle(Keys.ControlH, filter=insert_mode, save_before=if_no_repeat)( - get_by_name('backward-delete-char')) - handle(Keys.Backspace, filter=insert_mode, save_before=if_no_repeat)( - get_by_name('backward-delete-char')) - handle(Keys.Delete, filter=insert_mode, save_before=if_no_repeat)( - get_by_name('delete-char')) - handle(Keys.ShiftDelete, filter=insert_mode, save_before=if_no_repeat)( - get_by_name('delete-char')) - handle(Keys.Any, filter=insert_mode, save_before=if_no_repeat)( - get_by_name('self-insert')) - handle(Keys.ControlT, filter=insert_mode)(get_by_name('transpose-chars')) - handle(Keys.ControlW, filter=insert_mode)(get_by_name('unix-word-rubout')) - handle(Keys.ControlI, filter=insert_mode)(get_by_name('menu-complete')) - handle(Keys.BackTab, filter=insert_mode)(get_by_name('menu-complete-backward')) - - handle(Keys.PageUp, filter= ~has_selection)(get_by_name('previous-history')) - handle(Keys.PageDown, filter= ~has_selection)(get_by_name('next-history')) - - # CTRL keys. - - text_before_cursor = Condition(lambda cli: cli.current_buffer.text) - handle(Keys.ControlD, filter=text_before_cursor & insert_mode)(get_by_name('delete-char')) - - is_multiline = Condition(lambda cli: cli.current_buffer.is_multiline()) - is_returnable = Condition(lambda cli: cli.current_buffer.accept_action.is_returnable) - - @handle(Keys.ControlJ, filter=is_multiline & insert_mode) - def _(event): - " Newline (in case of multiline input. " - event.current_buffer.newline(copy_margin=not event.cli.in_paste_mode) - - @handle(Keys.ControlJ, filter=~is_multiline & is_returnable) - def _(event): - " Enter, accept input. " - buff = event.current_buffer - buff.accept_action.validate_and_handle(event.cli, buff) - - # Delete the word before the cursor. - - @handle(Keys.Up) - def _(event): - event.current_buffer.auto_up(count=event.arg) - - @handle(Keys.Down) - def _(event): - event.current_buffer.auto_down(count=event.arg) - - @handle(Keys.Delete, filter=has_selection) - def _(event): - data = event.current_buffer.cut_selection() - event.cli.clipboard.set_data(data) - - # Global bindings. - - @handle(Keys.ControlZ) - def _(event): - """ - By default, control-Z should literally insert Ctrl-Z. - (Ansi Ctrl-Z, code 26 in MSDOS means End-Of-File. - In a Python REPL for instance, it's possible to type - Control-Z followed by enter to quit.) - - When the system bindings are loaded and suspend-to-background is - supported, that will override this binding. - """ - event.current_buffer.insert_text(event.data) - - @handle(Keys.CPRResponse, save_before=lambda e: False) - def _(event): - """ - Handle incoming Cursor-Position-Request response. - """ - # The incoming data looks like u'\x1b[35;1R' - # Parse row/col information. - row, col = map(int, event.data[2:-1].split(';')) - - # Report absolute cursor position to the renderer. - event.cli.renderer.report_absolute_cursor_row(row) - - @handle(Keys.BracketedPaste) - def _(event): - " Pasting from clipboard. " - data = event.data - - # Be sure to use \n as line ending. - # Some terminals (Like iTerm2) seem to paste \r\n line endings in a - # bracketed paste. See: https://github.com/ipython/ipython/issues/9737 - data = data.replace('\r\n', '\n') - data = data.replace('\r', '\n') - - event.current_buffer.insert_text(data) - - @handle(Keys.Any, filter=Condition(lambda cli: cli.quoted_insert), eager=True) - def _(event): - """ - Handle quoted insert. - """ - event.current_buffer.insert_text(event.data, overwrite=False) - event.cli.quoted_insert = False - - return registry - - -def load_mouse_bindings(): - """ - Key bindings, required for mouse support. - (Mouse events enter through the key binding system.) - """ - registry = Registry() - - @registry.add_binding(Keys.Vt100MouseEvent) - def _(event): - """ - Handling of incoming mouse event. - """ - # Typical: "Esc[MaB*" - # Urxvt: "Esc[96;14;13M" - # Xterm SGR: "Esc[<64;85;12M" - - # Parse incoming packet. - if event.data[2] == 'M': - # Typical. - mouse_event, x, y = map(ord, event.data[3:]) - mouse_event = { - 32: MouseEventType.MOUSE_DOWN, - 35: MouseEventType.MOUSE_UP, - 96: MouseEventType.SCROLL_UP, - 97: MouseEventType.SCROLL_DOWN, - }.get(mouse_event) - - # Handle situations where `PosixStdinReader` used surrogateescapes. - if x >= 0xdc00: x-= 0xdc00 - if y >= 0xdc00: y-= 0xdc00 - - x -= 32 - y -= 32 - else: - # Urxvt and Xterm SGR. - # When the '<' is not present, we are not using the Xterm SGR mode, - # but Urxvt instead. - data = event.data[2:] - if data[:1] == '<': - sgr = True - data = data[1:] - else: - sgr = False - - # Extract coordinates. - mouse_event, x, y = map(int, data[:-1].split(';')) - m = data[-1] - - # Parse event type. - if sgr: - mouse_event = { - (0, 'M'): MouseEventType.MOUSE_DOWN, - (0, 'm'): MouseEventType.MOUSE_UP, - (64, 'M'): MouseEventType.SCROLL_UP, - (65, 'M'): MouseEventType.SCROLL_DOWN, - }.get((mouse_event, m)) - else: - mouse_event = { - 32: MouseEventType.MOUSE_DOWN, - 35: MouseEventType.MOUSE_UP, - 96: MouseEventType.SCROLL_UP, - 97: MouseEventType.SCROLL_DOWN, - }.get(mouse_event) - - x -= 1 - y -= 1 - - # Only handle mouse events when we know the window height. - if event.cli.renderer.height_is_known and mouse_event is not None: - # Take region above the layout into account. The reported - # coordinates are absolute to the visible part of the terminal. - try: - y -= event.cli.renderer.rows_above_layout - except HeightIsUnknownError: - return - - # Call the mouse handler from the renderer. - handler = event.cli.renderer.mouse_handlers.mouse_handlers[x,y] - handler(event.cli, MouseEvent(position=Point(x=x, y=y), - event_type=mouse_event)) - - @registry.add_binding(Keys.WindowsMouseEvent) - def _(event): - """ - Handling of mouse events for Windows. - """ - assert is_windows() # This key binding should only exist for Windows. - - # Parse data. - event_type, x, y = event.data.split(';') - x = int(x) - y = int(y) - - # Make coordinates absolute to the visible part of the terminal. - screen_buffer_info = event.cli.renderer.output.get_win32_screen_buffer_info() - rows_above_cursor = screen_buffer_info.dwCursorPosition.Y - event.cli.renderer._cursor_pos.y - y -= rows_above_cursor - - # Call the mouse event handler. - handler = event.cli.renderer.mouse_handlers.mouse_handlers[x,y] - handler(event.cli, MouseEvent(position=Point(x=x, y=y), - event_type=event_type)) - - return registry - - -def load_abort_and_exit_bindings(): - """ - Basic bindings for abort (Ctrl-C) and exit (Ctrl-D). - """ - registry = Registry() - handle = registry.add_binding - - @handle(Keys.ControlC) - def _(event): - " Abort when Control-C has been pressed. " - event.cli.abort() - - @Condition - def ctrl_d_condition(cli): - """ Ctrl-D binding is only active when the default buffer is selected - and empty. """ - return (cli.current_buffer_name == DEFAULT_BUFFER and - not cli.current_buffer.text) - - handle(Keys.ControlD, filter=ctrl_d_condition)(get_by_name('end-of-file')) - - return registry - - -def load_basic_system_bindings(): - """ - Basic system bindings (For both Emacs and Vi mode.) - """ - registry = Registry() - - suspend_supported = Condition( - lambda cli: suspend_to_background_supported()) - - @registry.add_binding(Keys.ControlZ, filter=suspend_supported) - def _(event): - """ - Suspend process to background. - """ - event.cli.suspend_to_background() - - return registry - - -def load_auto_suggestion_bindings(): - """ - Key bindings for accepting auto suggestion text. - """ - registry = Registry() - handle = registry.add_binding - - suggestion_available = Condition( - lambda cli: - cli.current_buffer.suggestion is not None and - cli.current_buffer.document.is_cursor_at_the_end) - - @handle(Keys.ControlF, filter=suggestion_available) - @handle(Keys.ControlE, filter=suggestion_available) - @handle(Keys.Right, filter=suggestion_available) - def _(event): - " Accept suggestion. " - b = event.current_buffer - suggestion = b.suggestion - - if suggestion: - b.insert_text(suggestion.text) - - return registry diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/completion.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/completion.py deleted file mode 100644 index 4903900bc6e..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/completion.py +++ /dev/null @@ -1,161 +0,0 @@ -""" -Key binding handlers for displaying completions. -""" -from __future__ import unicode_literals -from prompt_toolkit.completion import CompleteEvent, get_common_complete_suffix -from prompt_toolkit.utils import get_cwidth -from prompt_toolkit.keys import Keys -from prompt_toolkit.key_binding.registry import Registry - -import math - -__all__ = ( - 'generate_completions', - 'display_completions_like_readline', -) - -def generate_completions(event): - r""" - Tab-completion: where the first tab completes the common suffix and the - second tab lists all the completions. - """ - b = event.current_buffer - - # When already navigating through completions, select the next one. - if b.complete_state: - b.complete_next() - else: - event.cli.start_completion(insert_common_part=True, select_first=False) - - -def display_completions_like_readline(event): - """ - Key binding handler for readline-style tab completion. - This is meant to be as similar as possible to the way how readline displays - completions. - - Generate the completions immediately (blocking) and display them above the - prompt in columns. - - Usage:: - - # Call this handler when 'Tab' has been pressed. - registry.add_binding(Keys.ControlI)(display_completions_like_readline) - """ - # Request completions. - b = event.current_buffer - if b.completer is None: - return - complete_event = CompleteEvent(completion_requested=True) - completions = list(b.completer.get_completions(b.document, complete_event)) - - # Calculate the common suffix. - common_suffix = get_common_complete_suffix(b.document, completions) - - # One completion: insert it. - if len(completions) == 1: - b.delete_before_cursor(-completions[0].start_position) - b.insert_text(completions[0].text) - # Multiple completions with common part. - elif common_suffix: - b.insert_text(common_suffix) - # Otherwise: display all completions. - elif completions: - _display_completions_like_readline(event.cli, completions) - - -def _display_completions_like_readline(cli, completions): - """ - Display the list of completions in columns above the prompt. - This will ask for a confirmation if there are too many completions to fit - on a single page and provide a paginator to walk through them. - """ - from prompt_toolkit.shortcuts import create_confirm_application - assert isinstance(completions, list) - - # Get terminal dimensions. - term_size = cli.output.get_size() - term_width = term_size.columns - term_height = term_size.rows - - # Calculate amount of required columns/rows for displaying the - # completions. (Keep in mind that completions are displayed - # alphabetically column-wise.) - max_compl_width = min(term_width, - max(get_cwidth(c.text) for c in completions) + 1) - column_count = max(1, term_width // max_compl_width) - completions_per_page = column_count * (term_height - 1) - page_count = int(math.ceil(len(completions) / float(completions_per_page))) - # Note: math.ceil can return float on Python2. - - def display(page): - # Display completions. - page_completions = completions[page * completions_per_page: - (page+1) * completions_per_page] - - page_row_count = int(math.ceil(len(page_completions) / float(column_count))) - page_columns = [page_completions[i * page_row_count:(i+1) * page_row_count] - for i in range(column_count)] - - result = [] - for r in range(page_row_count): - for c in range(column_count): - try: - result.append(page_columns[c][r].text.ljust(max_compl_width)) - except IndexError: - pass - result.append('\n') - cli.output.write(''.join(result)) - cli.output.flush() - - # User interaction through an application generator function. - def run(): - if len(completions) > completions_per_page: - # Ask confirmation if it doesn't fit on the screen. - message = 'Display all {} possibilities? (y on n) '.format(len(completions)) - confirm = yield create_confirm_application(message) - - if confirm: - # Display pages. - for page in range(page_count): - display(page) - - if page != page_count - 1: - # Display --MORE-- and go to the next page. - show_more = yield _create_more_application() - if not show_more: - return - else: - cli.output.write('\n'); cli.output.flush() - else: - # Display all completions. - display(0) - - cli.run_application_generator(run, render_cli_done=True) - - -def _create_more_application(): - """ - Create an `Application` instance that displays the "--MORE--". - """ - from prompt_toolkit.shortcuts import create_prompt_application - registry = Registry() - - @registry.add_binding(' ') - @registry.add_binding('y') - @registry.add_binding('Y') - @registry.add_binding(Keys.ControlJ) - @registry.add_binding(Keys.ControlI) # Tab. - def _(event): - event.cli.set_return_value(True) - - @registry.add_binding('n') - @registry.add_binding('N') - @registry.add_binding('q') - @registry.add_binding('Q') - @registry.add_binding(Keys.ControlC) - def _(event): - event.cli.set_return_value(False) - - return create_prompt_application( - '--MORE--', key_bindings_registry=registry, erase_when_done=True) diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/emacs.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/emacs.py deleted file mode 100644 index bccdb04ff38..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/emacs.py +++ /dev/null @@ -1,452 +0,0 @@ -# pylint: disable=function-redefined -from __future__ import unicode_literals -from prompt_toolkit.buffer import SelectionType, indent, unindent -from prompt_toolkit.keys import Keys -from prompt_toolkit.enums import IncrementalSearchDirection, SEARCH_BUFFER, SYSTEM_BUFFER -from prompt_toolkit.filters import Condition, EmacsMode, HasSelection, EmacsInsertMode, HasFocus, HasArg -from prompt_toolkit.completion import CompleteEvent - -from .scroll import scroll_page_up, scroll_page_down -from .named_commands import get_by_name -from ..registry import Registry, ConditionalRegistry - -__all__ = ( - 'load_emacs_bindings', - 'load_emacs_search_bindings', - 'load_emacs_system_bindings', - 'load_extra_emacs_page_navigation_bindings', -) - - -def load_emacs_bindings(): - """ - Some e-macs extensions. - """ - # Overview of Readline emacs commands: - # http://www.catonmat.net/download/readline-emacs-editing-mode-cheat-sheet.pdf - registry = ConditionalRegistry(Registry(), EmacsMode()) - handle = registry.add_binding - - insert_mode = EmacsInsertMode() - has_selection = HasSelection() - - @handle(Keys.Escape) - def _(event): - """ - By default, ignore escape key. - - (If we don't put this here, and Esc is followed by a key which sequence - is not handled, we'll insert an Escape character in the input stream. - Something we don't want and happens to easily in emacs mode. - Further, people can always use ControlQ to do a quoted insert.) - """ - pass - - handle(Keys.ControlA)(get_by_name('beginning-of-line')) - handle(Keys.ControlB)(get_by_name('backward-char')) - handle(Keys.ControlDelete, filter=insert_mode)(get_by_name('kill-word')) - handle(Keys.ControlE)(get_by_name('end-of-line')) - handle(Keys.ControlF)(get_by_name('forward-char')) - handle(Keys.ControlLeft)(get_by_name('backward-word')) - handle(Keys.ControlRight)(get_by_name('forward-word')) - handle(Keys.ControlX, 'r', 'y', filter=insert_mode)(get_by_name('yank')) - handle(Keys.ControlY, filter=insert_mode)(get_by_name('yank')) - handle(Keys.Escape, 'b')(get_by_name('backward-word')) - handle(Keys.Escape, 'c', filter=insert_mode)(get_by_name('capitalize-word')) - handle(Keys.Escape, 'd', filter=insert_mode)(get_by_name('kill-word')) - handle(Keys.Escape, 'f')(get_by_name('forward-word')) - handle(Keys.Escape, 'l', filter=insert_mode)(get_by_name('downcase-word')) - handle(Keys.Escape, 'u', filter=insert_mode)(get_by_name('uppercase-word')) - handle(Keys.Escape, 'y', filter=insert_mode)(get_by_name('yank-pop')) - handle(Keys.Escape, Keys.ControlH, filter=insert_mode)(get_by_name('backward-kill-word')) - handle(Keys.Escape, Keys.Backspace, filter=insert_mode)(get_by_name('backward-kill-word')) - handle(Keys.Escape, '\\', filter=insert_mode)(get_by_name('delete-horizontal-space')) - - handle(Keys.ControlUnderscore, save_before=(lambda e: False), filter=insert_mode)( - get_by_name('undo')) - - handle(Keys.ControlX, Keys.ControlU, save_before=(lambda e: False), filter=insert_mode)( - get_by_name('undo')) - - - handle(Keys.Escape, '<', filter= ~has_selection)(get_by_name('beginning-of-history')) - handle(Keys.Escape, '>', filter= ~has_selection)(get_by_name('end-of-history')) - - handle(Keys.Escape, '.', filter=insert_mode)(get_by_name('yank-last-arg')) - handle(Keys.Escape, '_', filter=insert_mode)(get_by_name('yank-last-arg')) - handle(Keys.Escape, Keys.ControlY, filter=insert_mode)(get_by_name('yank-nth-arg')) - handle(Keys.Escape, '#', filter=insert_mode)(get_by_name('insert-comment')) - handle(Keys.ControlO)(get_by_name('operate-and-get-next')) - - # ControlQ does a quoted insert. Not that for vt100 terminals, you have to - # disable flow control by running ``stty -ixon``, otherwise Ctrl-Q and - # Ctrl-S are captured by the terminal. - handle(Keys.ControlQ, filter= ~has_selection)(get_by_name('quoted-insert')) - - handle(Keys.ControlX, '(')(get_by_name('start-kbd-macro')) - handle(Keys.ControlX, ')')(get_by_name('end-kbd-macro')) - handle(Keys.ControlX, 'e')(get_by_name('call-last-kbd-macro')) - - @handle(Keys.ControlN) - def _(event): - " Next line. " - event.current_buffer.auto_down() - - @handle(Keys.ControlP) - def _(event): - " Previous line. " - event.current_buffer.auto_up(count=event.arg) - - def handle_digit(c): - """ - Handle input of arguments. - The first number needs to be preceeded by escape. - """ - @handle(c, filter=HasArg()) - @handle(Keys.Escape, c) - def _(event): - event.append_to_arg_count(c) - - for c in '0123456789': - handle_digit(c) - - @handle(Keys.Escape, '-', filter=~HasArg()) - def _(event): - """ - """ - if event._arg is None: - event.append_to_arg_count('-') - - @handle('-', filter=Condition(lambda cli: cli.input_processor.arg == '-')) - def _(event): - """ - When '-' is typed again, after exactly '-' has been given as an - argument, ignore this. - """ - event.cli.input_processor.arg = '-' - - is_returnable = Condition( - lambda cli: cli.current_buffer.accept_action.is_returnable) - - # Meta + Newline: always accept input. - handle(Keys.Escape, Keys.ControlJ, filter=insert_mode & is_returnable)( - get_by_name('accept-line')) - - def character_search(buff, char, count): - if count < 0: - match = buff.document.find_backwards(char, in_current_line=True, count=-count) - else: - match = buff.document.find(char, in_current_line=True, count=count) - - if match is not None: - buff.cursor_position += match - - @handle(Keys.ControlSquareClose, Keys.Any) - def _(event): - " When Ctl-] + a character is pressed. go to that character. " - # Also named 'character-search' - character_search(event.current_buffer, event.data, event.arg) - - @handle(Keys.Escape, Keys.ControlSquareClose, Keys.Any) - def _(event): - " Like Ctl-], but backwards. " - # Also named 'character-search-backward' - character_search(event.current_buffer, event.data, -event.arg) - - @handle(Keys.Escape, 'a') - def _(event): - " Previous sentence. " - # TODO: - - @handle(Keys.Escape, 'e') - def _(event): - " Move to end of sentence. " - # TODO: - - @handle(Keys.Escape, 't', filter=insert_mode) - def _(event): - """ - Swap the last two words before the cursor. - """ - # TODO - - @handle(Keys.Escape, '*', filter=insert_mode) - def _(event): - """ - `meta-*`: Insert all possible completions of the preceding text. - """ - buff = event.current_buffer - - # List all completions. - complete_event = CompleteEvent(text_inserted=False, completion_requested=True) - completions = list(buff.completer.get_completions(buff.document, complete_event)) - - # Insert them. - text_to_insert = ' '.join(c.text for c in completions) - buff.insert_text(text_to_insert) - - @handle(Keys.ControlX, Keys.ControlX) - def _(event): - """ - Move cursor back and forth between the start and end of the current - line. - """ - buffer = event.current_buffer - - if buffer.document.is_cursor_at_the_end_of_line: - buffer.cursor_position += buffer.document.get_start_of_line_position(after_whitespace=False) - else: - buffer.cursor_position += buffer.document.get_end_of_line_position() - - @handle(Keys.ControlSpace) - def _(event): - """ - Start of the selection (if the current buffer is not empty). - """ - # Take the current cursor position as the start of this selection. - buff = event.current_buffer - if buff.text: - buff.start_selection(selection_type=SelectionType.CHARACTERS) - - @handle(Keys.ControlG, filter= ~has_selection) - def _(event): - """ - Control + G: Cancel completion menu and validation state. - """ - event.current_buffer.complete_state = None - event.current_buffer.validation_error = None - - @handle(Keys.ControlG, filter=has_selection) - def _(event): - """ - Cancel selection. - """ - event.current_buffer.exit_selection() - - @handle(Keys.ControlW, filter=has_selection) - @handle(Keys.ControlX, 'r', 'k', filter=has_selection) - def _(event): - """ - Cut selected text. - """ - data = event.current_buffer.cut_selection() - event.cli.clipboard.set_data(data) - - @handle(Keys.Escape, 'w', filter=has_selection) - def _(event): - """ - Copy selected text. - """ - data = event.current_buffer.copy_selection() - event.cli.clipboard.set_data(data) - - @handle(Keys.Escape, Keys.Left) - def _(event): - """ - Cursor to start of previous word. - """ - buffer = event.current_buffer - buffer.cursor_position += buffer.document.find_previous_word_beginning(count=event.arg) or 0 - - @handle(Keys.Escape, Keys.Right) - def _(event): - """ - Cursor to start of next word. - """ - buffer = event.current_buffer - buffer.cursor_position += buffer.document.find_next_word_beginning(count=event.arg) or \ - buffer.document.get_end_of_document_position() - - @handle(Keys.Escape, '/', filter=insert_mode) - def _(event): - """ - M-/: Complete. - """ - b = event.current_buffer - if b.complete_state: - b.complete_next() - else: - event.cli.start_completion(select_first=True) - - @handle(Keys.ControlC, '>', filter=has_selection) - def _(event): - """ - Indent selected text. - """ - buffer = event.current_buffer - - buffer.cursor_position += buffer.document.get_start_of_line_position(after_whitespace=True) - - from_, to = buffer.document.selection_range() - from_, _ = buffer.document.translate_index_to_position(from_) - to, _ = buffer.document.translate_index_to_position(to) - - indent(buffer, from_, to + 1, count=event.arg) - - @handle(Keys.ControlC, '<', filter=has_selection) - def _(event): - """ - Unindent selected text. - """ - buffer = event.current_buffer - - from_, to = buffer.document.selection_range() - from_, _ = buffer.document.translate_index_to_position(from_) - to, _ = buffer.document.translate_index_to_position(to) - - unindent(buffer, from_, to + 1, count=event.arg) - - return registry - - -def load_emacs_open_in_editor_bindings(): - """ - Pressing C-X C-E will open the buffer in an external editor. - """ - registry = Registry() - - registry.add_binding(Keys.ControlX, Keys.ControlE, - filter=EmacsMode() & ~HasSelection())( - get_by_name('edit-and-execute-command')) - - return registry - - -def load_emacs_system_bindings(): - registry = ConditionalRegistry(Registry(), EmacsMode()) - handle = registry.add_binding - - has_focus = HasFocus(SYSTEM_BUFFER) - - @handle(Keys.Escape, '!', filter= ~has_focus) - def _(event): - """ - M-'!' opens the system prompt. - """ - event.cli.push_focus(SYSTEM_BUFFER) - - @handle(Keys.Escape, filter=has_focus) - @handle(Keys.ControlG, filter=has_focus) - @handle(Keys.ControlC, filter=has_focus) - def _(event): - """ - Cancel system prompt. - """ - event.cli.buffers[SYSTEM_BUFFER].reset() - event.cli.pop_focus() - - @handle(Keys.ControlJ, filter=has_focus) - def _(event): - """ - Run system command. - """ - system_line = event.cli.buffers[SYSTEM_BUFFER] - event.cli.run_system_command(system_line.text) - system_line.reset(append_to_history=True) - - # Focus previous buffer again. - event.cli.pop_focus() - - return registry - - -def load_emacs_search_bindings(get_search_state=None): - registry = ConditionalRegistry(Registry(), EmacsMode()) - handle = registry.add_binding - - has_focus = HasFocus(SEARCH_BUFFER) - - assert get_search_state is None or callable(get_search_state) - - if not get_search_state: - def get_search_state(cli): return cli.search_state - - @handle(Keys.ControlG, filter=has_focus) - @handle(Keys.ControlC, filter=has_focus) - # NOTE: the reason for not also binding Escape to this one, is that we want - # Alt+Enter to accept input directly in incremental search mode. - def _(event): - """ - Abort an incremental search and restore the original line. - """ - search_buffer = event.cli.buffers[SEARCH_BUFFER] - - search_buffer.reset() - event.cli.pop_focus() - - @handle(Keys.ControlJ, filter=has_focus) - @handle(Keys.Escape, filter=has_focus, eager=True) - def _(event): - """ - When enter pressed in isearch, quit isearch mode. (Multiline - isearch would be too complicated.) - """ - input_buffer = event.cli.buffers.previous(event.cli) - search_buffer = event.cli.buffers[SEARCH_BUFFER] - - # Update search state. - if search_buffer.text: - get_search_state(event.cli).text = search_buffer.text - - # Apply search. - input_buffer.apply_search(get_search_state(event.cli), include_current_position=True) - - # Add query to history of search line. - search_buffer.append_to_history() - search_buffer.reset() - - # Focus previous document again. - event.cli.pop_focus() - - @handle(Keys.ControlR, filter= ~has_focus) - def _(event): - get_search_state(event.cli).direction = IncrementalSearchDirection.BACKWARD - event.cli.push_focus(SEARCH_BUFFER) - - @handle(Keys.ControlS, filter= ~has_focus) - def _(event): - get_search_state(event.cli).direction = IncrementalSearchDirection.FORWARD - event.cli.push_focus(SEARCH_BUFFER) - - def incremental_search(cli, direction, count=1): - " Apply search, but keep search buffer focussed. " - # Update search_state. - search_state = get_search_state(cli) - direction_changed = search_state.direction != direction - - search_state.text = cli.buffers[SEARCH_BUFFER].text - search_state.direction = direction - - # Apply search to current buffer. - if not direction_changed: - input_buffer = cli.buffers.previous(cli) - input_buffer.apply_search(search_state, - include_current_position=False, count=count) - - @handle(Keys.ControlR, filter=has_focus) - @handle(Keys.Up, filter=has_focus) - def _(event): - incremental_search(event.cli, IncrementalSearchDirection.BACKWARD, count=event.arg) - - @handle(Keys.ControlS, filter=has_focus) - @handle(Keys.Down, filter=has_focus) - def _(event): - incremental_search(event.cli, IncrementalSearchDirection.FORWARD, count=event.arg) - - return registry - - -def load_extra_emacs_page_navigation_bindings(): - """ - Key bindings, for scrolling up and down through pages. - This are separate bindings, because GNU readline doesn't have them. - """ - registry = ConditionalRegistry(Registry(), EmacsMode()) - handle = registry.add_binding - - handle(Keys.ControlV)(scroll_page_down) - handle(Keys.PageDown)(scroll_page_down) - handle(Keys.Escape, 'v')(scroll_page_up) - handle(Keys.PageUp)(scroll_page_up) - - return registry diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/named_commands.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/named_commands.py deleted file mode 100644 index f80c439fc6d..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/named_commands.py +++ /dev/null @@ -1,578 +0,0 @@ -""" -Key bindings which are also known by GNU readline by the given names. - -See: http://www.delorie.com/gnu/docs/readline/rlman_13.html -""" -from __future__ import unicode_literals -from prompt_toolkit.enums import IncrementalSearchDirection, SEARCH_BUFFER -from prompt_toolkit.selection import PasteMode -from six.moves import range -import six - -from .completion import generate_completions, display_completions_like_readline -from prompt_toolkit.document import Document -from prompt_toolkit.enums import EditingMode -from prompt_toolkit.key_binding.input_processor import KeyPress -from prompt_toolkit.keys import Keys - -__all__ = ( - 'get_by_name', -) - - -# Registry that maps the Readline command names to their handlers. -_readline_commands = {} - -def register(name): - """ - Store handler in the `_readline_commands` dictionary. - """ - assert isinstance(name, six.text_type) - def decorator(handler): - assert callable(handler) - - _readline_commands[name] = handler - return handler - return decorator - - -def get_by_name(name): - """ - Return the handler for the (Readline) command with the given name. - """ - try: - return _readline_commands[name] - except KeyError: - raise KeyError('Unknown readline command: %r' % name) - -# -# Commands for moving -# See: http://www.delorie.com/gnu/docs/readline/rlman_14.html -# - -@register('beginning-of-line') -def beginning_of_line(event): - " Move to the start of the current line. " - buff = event.current_buffer - buff.cursor_position += buff.document.get_start_of_line_position(after_whitespace=False) - - -@register('end-of-line') -def end_of_line(event): - " Move to the end of the line. " - buff = event.current_buffer - buff.cursor_position += buff.document.get_end_of_line_position() - - -@register('forward-char') -def forward_char(event): - " Move forward a character. " - buff = event.current_buffer - buff.cursor_position += buff.document.get_cursor_right_position(count=event.arg) - - -@register('backward-char') -def backward_char(event): - " Move back a character. " - buff = event.current_buffer - buff.cursor_position += buff.document.get_cursor_left_position(count=event.arg) - - -@register('forward-word') -def forward_word(event): - """ - Move forward to the end of the next word. Words are composed of letters and - digits. - """ - buff = event.current_buffer - pos = buff.document.find_next_word_ending(count=event.arg) - - if pos: - buff.cursor_position += pos - - -@register('backward-word') -def backward_word(event): - """ - Move back to the start of the current or previous word. Words are composed - of letters and digits. - """ - buff = event.current_buffer - pos = buff.document.find_previous_word_beginning(count=event.arg) - - if pos: - buff.cursor_position += pos - - -@register('clear-screen') -def clear_screen(event): - """ - Clear the screen and redraw everything at the top of the screen. - """ - event.cli.renderer.clear() - - -@register('redraw-current-line') -def redraw_current_line(event): - """ - Refresh the current line. - (Readline defines this command, but prompt-toolkit doesn't have it.) - """ - pass - -# -# Commands for manipulating the history. -# See: http://www.delorie.com/gnu/docs/readline/rlman_15.html -# - -@register('accept-line') -def accept_line(event): - " Accept the line regardless of where the cursor is. " - b = event.current_buffer - b.accept_action.validate_and_handle(event.cli, b) - - -@register('previous-history') -def previous_history(event): - " Move `back` through the history list, fetching the previous command. " - event.current_buffer.history_backward(count=event.arg) - - -@register('next-history') -def next_history(event): - " Move `forward` through the history list, fetching the next command. " - event.current_buffer.history_forward(count=event.arg) - - -@register('beginning-of-history') -def beginning_of_history(event): - " Move to the first line in the history. " - event.current_buffer.go_to_history(0) - - -@register('end-of-history') -def end_of_history(event): - """ - Move to the end of the input history, i.e., the line currently being entered. - """ - event.current_buffer.history_forward(count=10**100) - buff = event.current_buffer - buff.go_to_history(len(buff._working_lines) - 1) - - -@register('reverse-search-history') -def reverse_search_history(event): - """ - Search backward starting at the current line and moving `up` through - the history as necessary. This is an incremental search. - """ - event.cli.current_search_state.direction = IncrementalSearchDirection.BACKWARD - event.cli.push_focus(SEARCH_BUFFER) - - -# -# Commands for changing text -# - -@register('end-of-file') -def end_of_file(event): - """ - Exit. - """ - event.cli.exit() - - -@register('delete-char') -def delete_char(event): - " Delete character before the cursor. " - deleted = event.current_buffer.delete(count=event.arg) - if not deleted: - event.cli.output.bell() - - -@register('backward-delete-char') -def backward_delete_char(event): - " Delete the character behind the cursor. " - if event.arg < 0: - # When a negative argument has been given, this should delete in front - # of the cursor. - deleted = event.current_buffer.delete(count=-event.arg) - else: - deleted = event.current_buffer.delete_before_cursor(count=event.arg) - - if not deleted: - event.cli.output.bell() - - -@register('self-insert') -def self_insert(event): - " Insert yourself. " - event.current_buffer.insert_text(event.data * event.arg) - - -@register('transpose-chars') -def transpose_chars(event): - """ - Emulate Emacs transpose-char behavior: at the beginning of the buffer, - do nothing. At the end of a line or buffer, swap the characters before - the cursor. Otherwise, move the cursor right, and then swap the - characters before the cursor. - """ - b = event.current_buffer - p = b.cursor_position - if p == 0: - return - elif p == len(b.text) or b.text[p] == '\n': - b.swap_characters_before_cursor() - else: - b.cursor_position += b.document.get_cursor_right_position() - b.swap_characters_before_cursor() - - -@register('uppercase-word') -def uppercase_word(event): - """ - Uppercase the current (or following) word. - """ - buff = event.current_buffer - - for i in range(event.arg): - pos = buff.document.find_next_word_ending() - words = buff.document.text_after_cursor[:pos] - buff.insert_text(words.upper(), overwrite=True) - - -@register('downcase-word') -def downcase_word(event): - """ - Lowercase the current (or following) word. - """ - buff = event.current_buffer - - for i in range(event.arg): # XXX: not DRY: see meta_c and meta_u!! - pos = buff.document.find_next_word_ending() - words = buff.document.text_after_cursor[:pos] - buff.insert_text(words.lower(), overwrite=True) - - -@register('capitalize-word') -def capitalize_word(event): - """ - Capitalize the current (or following) word. - """ - buff = event.current_buffer - - for i in range(event.arg): - pos = buff.document.find_next_word_ending() - words = buff.document.text_after_cursor[:pos] - buff.insert_text(words.title(), overwrite=True) - - -@register('quoted-insert') -def quoted_insert(event): - """ - Add the next character typed to the line verbatim. This is how to insert - key sequences like C-q, for example. - """ - event.cli.quoted_insert = True - - -# -# Killing and yanking. -# - -@register('kill-line') -def kill_line(event): - """ - Kill the text from the cursor to the end of the line. - - If we are at the end of the line, this should remove the newline. - (That way, it is possible to delete multiple lines by executing this - command multiple times.) - """ - buff = event.current_buffer - if event.arg < 0: - deleted = buff.delete_before_cursor(count=-buff.document.get_start_of_line_position()) - else: - if buff.document.current_char == '\n': - deleted = buff.delete(1) - else: - deleted = buff.delete(count=buff.document.get_end_of_line_position()) - event.cli.clipboard.set_text(deleted) - - -@register('kill-word') -def kill_word(event): - """ - Kill from point to the end of the current word, or if between words, to the - end of the next word. Word boundaries are the same as forward-word. - """ - buff = event.current_buffer - pos = buff.document.find_next_word_ending(count=event.arg) - - if pos: - deleted = buff.delete(count=pos) - event.cli.clipboard.set_text(deleted) - - -@register('unix-word-rubout') -def unix_word_rubout(event, WORD=True): - """ - Kill the word behind point, using whitespace as a word boundary. - Usually bound to ControlW. - """ - buff = event.current_buffer - pos = buff.document.find_start_of_previous_word(count=event.arg, WORD=WORD) - - if pos is None: - # Nothing found? delete until the start of the document. (The - # input starts with whitespace and no words were found before the - # cursor.) - pos = - buff.cursor_position - - if pos: - deleted = buff.delete_before_cursor(count=-pos) - - # If the previous key press was also Control-W, concatenate deleted - # text. - if event.is_repeat: - deleted += event.cli.clipboard.get_data().text - - event.cli.clipboard.set_text(deleted) - else: - # Nothing to delete. Bell. - event.cli.output.bell() - - -@register('backward-kill-word') -def backward_kill_word(event): - """ - Kills the word before point, using "not a letter nor a digit" as a word boundary. - Usually bound to M-Del or M-Backspace. - """ - unix_word_rubout(event, WORD=False) - - -@register('delete-horizontal-space') -def delete_horizontal_space(event): - " Delete all spaces and tabs around point. " - buff = event.current_buffer - text_before_cursor = buff.document.text_before_cursor - text_after_cursor = buff.document.text_after_cursor - - delete_before = len(text_before_cursor) - len(text_before_cursor.rstrip('\t ')) - delete_after = len(text_after_cursor) - len(text_after_cursor.lstrip('\t ')) - - buff.delete_before_cursor(count=delete_before) - buff.delete(count=delete_after) - - -@register('unix-line-discard') -def unix_line_discard(event): - """ - Kill backward from the cursor to the beginning of the current line. - """ - buff = event.current_buffer - - if buff.document.cursor_position_col == 0 and buff.document.cursor_position > 0: - buff.delete_before_cursor(count=1) - else: - deleted = buff.delete_before_cursor(count=-buff.document.get_start_of_line_position()) - event.cli.clipboard.set_text(deleted) - - -@register('yank') -def yank(event): - """ - Paste before cursor. - """ - event.current_buffer.paste_clipboard_data( - event.cli.clipboard.get_data(), count=event.arg, paste_mode=PasteMode.EMACS) - -@register('yank-nth-arg') -def yank_nth_arg(event): - """ - Insert the first argument of the previous command. With an argument, insert - the nth word from the previous command (start counting at 0). - """ - n = (event.arg if event.arg_present else None) - event.current_buffer.yank_nth_arg(n) - - -@register('yank-last-arg') -def yank_last_arg(event): - """ - Like `yank_nth_arg`, but if no argument has been given, yank the last word - of each line. - """ - n = (event.arg if event.arg_present else None) - event.current_buffer.yank_last_arg(n) - -@register('yank-pop') -def yank_pop(event): - """ - Rotate the kill ring, and yank the new top. Only works following yank or - yank-pop. - """ - buff = event.current_buffer - doc_before_paste = buff.document_before_paste - clipboard = event.cli.clipboard - - if doc_before_paste is not None: - buff.document = doc_before_paste - clipboard.rotate() - buff.paste_clipboard_data( - clipboard.get_data(), paste_mode=PasteMode.EMACS) - -# -# Completion. -# - -@register('complete') -def complete(event): - " Attempt to perform completion. " - display_completions_like_readline(event) - - -@register('menu-complete') -def menu_complete(event): - """ - Generate completions, or go to the next completion. (This is the default - way of completing input in prompt_toolkit.) - """ - generate_completions(event) - - -@register('menu-complete-backward') -def menu_complete_backward(event): - " Move backward through the list of possible completions. " - event.current_buffer.complete_previous() - -# -# Keyboard macros. -# - -@register('start-kbd-macro') -def start_kbd_macro(event): - """ - Begin saving the characters typed into the current keyboard macro. - """ - event.cli.input_processor.start_macro() - - -@register('end-kbd-macro') -def start_kbd_macro(event): - """ - Stop saving the characters typed into the current keyboard macro and save - the definition. - """ - event.cli.input_processor.end_macro() - - -@register('call-last-kbd-macro') -def start_kbd_macro(event): - """ - Re-execute the last keyboard macro defined, by making the characters in the - macro appear as if typed at the keyboard. - """ - event.cli.input_processor.call_macro() - - -@register('print-last-kbd-macro') -def print_last_kbd_macro(event): - " Print the last keboard macro. " - # TODO: Make the format suitable for the inputrc file. - def print_macro(): - for k in event.cli.input_processor.macro: - print(k) - event.cli.run_in_terminal(print_macro) - -# -# Miscellaneous Commands. -# - -@register('undo') -def undo(event): - " Incremental undo. " - event.current_buffer.undo() - - -@register('insert-comment') -def insert_comment(event): - """ - Without numeric argument, comment all lines. - With numeric argument, uncomment all lines. - In any case accept the input. - """ - buff = event.current_buffer - - # Transform all lines. - if event.arg != 1: - def change(line): - return line[1:] if line.startswith('#') else line - else: - def change(line): - return '#' + line - - buff.document = Document( - text='\n'.join(map(change, buff.text.splitlines())), - cursor_position=0) - - # Accept input. - buff.accept_action.validate_and_handle(event.cli, buff) - - -@register('vi-editing-mode') -def vi_editing_mode(event): - " Switch to Vi editing mode. " - event.cli.editing_mode = EditingMode.VI - - -@register('emacs-editing-mode') -def emacs_editing_mode(event): - " Switch to Emacs editing mode. " - event.cli.editing_mode = EditingMode.EMACS - - -@register('prefix-meta') -def prefix_meta(event): - """ - Metafy the next character typed. This is for keyboards without a meta key. - - Sometimes people also want to bind other keys to Meta, e.g. 'jj':: - - registry.add_key_binding('j', 'j', filter=ViInsertMode())(prefix_meta) - """ - event.cli.input_processor.feed(KeyPress(Keys.Escape)) - - -@register('operate-and-get-next') -def operate_and_get_next(event): - """ - Accept the current line for execution and fetch the next line relative to - the current line from the history for editing. - """ - buff = event.current_buffer - new_index = buff.working_index + 1 - - # Accept the current input. (This will also redraw the interface in the - # 'done' state.) - buff.accept_action.validate_and_handle(event.cli, buff) - - # Set the new index at the start of the next run. - def set_working_index(): - if new_index < len(buff._working_lines): - buff.working_index = new_index - - event.cli.pre_run_callables.append(set_working_index) - - -@register('edit-and-execute-command') -def edit_and_execute(event): - """ - Invoke an editor on the current command line, and accept the result. - """ - buff = event.current_buffer - - buff.open_in_editor(event.cli) - buff.accept_action.validate_and_handle(event.cli, buff) diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/scroll.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/scroll.py deleted file mode 100644 index 2cc58129ffc..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/scroll.py +++ /dev/null @@ -1,185 +0,0 @@ -""" -Key bindings, for scrolling up and down through pages. - -This are separate bindings, because GNU readline doesn't have them, but -they are very useful for navigating through long multiline buffers, like in -Vi, Emacs, etc... -""" -from __future__ import unicode_literals - -from prompt_toolkit.layout.utils import find_window_for_buffer_name -from six.moves import range - -__all__ = ( - 'scroll_forward', - 'scroll_backward', - 'scroll_half_page_up', - 'scroll_half_page_down', - 'scroll_one_line_up', - 'scroll_one_line_down', -) - - -def _current_window_for_event(event): - """ - Return the `Window` for the currently focussed Buffer. - """ - return find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - - -def scroll_forward(event, half=False): - """ - Scroll window down. - """ - w = _current_window_for_event(event) - b = event.cli.current_buffer - - if w and w.render_info: - info = w.render_info - ui_content = info.ui_content - - # Height to scroll. - scroll_height = info.window_height - if half: - scroll_height //= 2 - - # Calculate how many lines is equivalent to that vertical space. - y = b.document.cursor_position_row + 1 - height = 0 - while y < ui_content.line_count: - line_height = info.get_height_for_line(y) - - if height + line_height < scroll_height: - height += line_height - y += 1 - else: - break - - b.cursor_position = b.document.translate_row_col_to_index(y, 0) - - -def scroll_backward(event, half=False): - """ - Scroll window up. - """ - w = _current_window_for_event(event) - b = event.cli.current_buffer - - if w and w.render_info: - info = w.render_info - - # Height to scroll. - scroll_height = info.window_height - if half: - scroll_height //= 2 - - # Calculate how many lines is equivalent to that vertical space. - y = max(0, b.document.cursor_position_row - 1) - height = 0 - while y > 0: - line_height = info.get_height_for_line(y) - - if height + line_height < scroll_height: - height += line_height - y -= 1 - else: - break - - b.cursor_position = b.document.translate_row_col_to_index(y, 0) - - -def scroll_half_page_down(event): - """ - Same as ControlF, but only scroll half a page. - """ - scroll_forward(event, half=True) - - -def scroll_half_page_up(event): - """ - Same as ControlB, but only scroll half a page. - """ - scroll_backward(event, half=True) - - -def scroll_one_line_down(event): - """ - scroll_offset += 1 - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.cli.current_buffer - - if w: - # When the cursor is at the top, move to the next line. (Otherwise, only scroll.) - if w.render_info: - info = w.render_info - - if w.vertical_scroll < info.content_height - info.window_height: - if info.cursor_position.y <= info.configured_scroll_offsets.top: - b.cursor_position += b.document.get_cursor_down_position() - - w.vertical_scroll += 1 - - -def scroll_one_line_up(event): - """ - scroll_offset -= 1 - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.cli.current_buffer - - if w: - # When the cursor is at the bottom, move to the previous line. (Otherwise, only scroll.) - if w.render_info: - info = w.render_info - - if w.vertical_scroll > 0: - first_line_height = info.get_height_for_line(info.first_visible_line()) - - cursor_up = info.cursor_position.y - (info.window_height - 1 - first_line_height - - info.configured_scroll_offsets.bottom) - - # Move cursor up, as many steps as the height of the first line. - # TODO: not entirely correct yet, in case of line wrapping and many long lines. - for _ in range(max(0, cursor_up)): - b.cursor_position += b.document.get_cursor_up_position() - - # Scroll window - w.vertical_scroll -= 1 - - -def scroll_page_down(event): - """ - Scroll page down. (Prefer the cursor at the top of the page, after scrolling.) - """ - w = _current_window_for_event(event) - b = event.cli.current_buffer - - if w and w.render_info: - # Scroll down one page. - line_index = max(w.render_info.last_visible_line(), w.vertical_scroll + 1) - w.vertical_scroll = line_index - - b.cursor_position = b.document.translate_row_col_to_index(line_index, 0) - b.cursor_position += b.document.get_start_of_line_position(after_whitespace=True) - - -def scroll_page_up(event): - """ - Scroll page up. (Prefer the cursor at the bottom of the page, after scrolling.) - """ - w = _current_window_for_event(event) - b = event.cli.current_buffer - - if w and w.render_info: - # Put cursor at the first visible line. (But make sure that the cursor - # moves at least one line up.) - line_index = max(0, min(w.render_info.first_visible_line(), - b.document.cursor_position_row - 1)) - - b.cursor_position = b.document.translate_row_col_to_index(line_index, 0) - b.cursor_position += b.document.get_start_of_line_position(after_whitespace=True) - - # Set the scroll offset. We can safely set it to zero; the Window will - # make sure that it scrolls at least until the cursor becomes visible. - w.vertical_scroll = 0 diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/utils.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/utils.py deleted file mode 100644 index caf08c5c1bd..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/utils.py +++ /dev/null @@ -1,25 +0,0 @@ -from __future__ import unicode_literals -from prompt_toolkit.filters import CLIFilter, Always - -__all__ = ( - 'create_handle_decorator', -) - -def create_handle_decorator(registry, filter=Always()): - """ - Create a key handle decorator, which is compatible with `Registry.handle`, - but will chain the given filter to every key binding. - - :param filter: `CLIFilter` - """ - assert isinstance(filter, CLIFilter) - - def handle(*keys, **kw): - # Chain the given filter to the filter of this specific binding. - if 'filter' in kw: - kw['filter'] = kw['filter'] & filter - else: - kw['filter'] = filter - - return registry.add_binding(*keys, **kw) - return handle diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/vi.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/vi.py deleted file mode 100644 index 72568ee273d..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/bindings/vi.py +++ /dev/null @@ -1,1903 +0,0 @@ -# pylint: disable=function-redefined -from __future__ import unicode_literals -from prompt_toolkit.buffer import ClipboardData, indent, unindent, reshape_text -from prompt_toolkit.document import Document -from prompt_toolkit.enums import IncrementalSearchDirection, SEARCH_BUFFER, SYSTEM_BUFFER -from prompt_toolkit.filters import Filter, Condition, HasArg, Always, IsReadOnly -from prompt_toolkit.filters.cli import ViNavigationMode, ViInsertMode, ViInsertMultipleMode, ViReplaceMode, ViSelectionMode, ViWaitingForTextObjectMode, ViDigraphMode, ViMode -from prompt_toolkit.key_binding.digraphs import DIGRAPHS -from prompt_toolkit.key_binding.vi_state import CharacterFind, InputMode -from prompt_toolkit.keys import Keys -from prompt_toolkit.layout.utils import find_window_for_buffer_name -from prompt_toolkit.selection import SelectionType, SelectionState, PasteMode - -from .scroll import scroll_forward, scroll_backward, scroll_half_page_up, scroll_half_page_down, scroll_one_line_up, scroll_one_line_down, scroll_page_up, scroll_page_down -from .named_commands import get_by_name -from ..registry import Registry, ConditionalRegistry, BaseRegistry - -import prompt_toolkit.filters as filters -from six.moves import range -import codecs -import six -import string - -try: - from itertools import accumulate -except ImportError: # < Python 3.2 - def accumulate(iterable): - " Super simpel 'accumulate' implementation. " - total = 0 - for item in iterable: - total += item - yield total - -__all__ = ( - 'load_vi_bindings', - 'load_vi_search_bindings', - 'load_vi_system_bindings', - 'load_extra_vi_page_navigation_bindings', -) - -if six.PY2: - ascii_lowercase = string.ascii_lowercase.decode('ascii') -else: - ascii_lowercase = string.ascii_lowercase - -vi_register_names = ascii_lowercase + '0123456789' - - -class TextObjectType(object): - EXCLUSIVE = 'EXCLUSIVE' - INCLUSIVE = 'INCLUSIVE' - LINEWISE = 'LINEWISE' - BLOCK = 'BLOCK' - - -class TextObject(object): - """ - Return struct for functions wrapped in ``text_object``. - Both `start` and `end` are relative to the current cursor position. - """ - def __init__(self, start, end=0, type=TextObjectType.EXCLUSIVE): - self.start = start - self.end = end - self.type = type - - @property - def selection_type(self): - if self.type == TextObjectType.LINEWISE: - return SelectionType.LINES - if self.type == TextObjectType.BLOCK: - return SelectionType.BLOCK - else: - return SelectionType.CHARACTERS - - def sorted(self): - """ - Return a (start, end) tuple where start <= end. - """ - if self.start < self.end: - return self.start, self.end - else: - return self.end, self.start - - def operator_range(self, document): - """ - Return a (start, end) tuple with start <= end that indicates the range - operators should operate on. - `buffer` is used to get start and end of line positions. - """ - start, end = self.sorted() - doc = document - - if (self.type == TextObjectType.EXCLUSIVE and - doc.translate_index_to_position(end + doc.cursor_position)[1] == 0): - # If the motion is exclusive and the end of motion is on the first - # column, the end position becomes end of previous line. - end -= 1 - if self.type == TextObjectType.INCLUSIVE: - end += 1 - if self.type == TextObjectType.LINEWISE: - # Select whole lines - row, col = doc.translate_index_to_position(start + doc.cursor_position) - start = doc.translate_row_col_to_index(row, 0) - doc.cursor_position - row, col = doc.translate_index_to_position(end + doc.cursor_position) - end = doc.translate_row_col_to_index(row, len(doc.lines[row])) - doc.cursor_position - return start, end - - def get_line_numbers(self, buffer): - """ - Return a (start_line, end_line) pair. - """ - # Get absolute cursor positions from the text object. - from_, to = self.operator_range(buffer.document) - from_ += buffer.cursor_position - to += buffer.cursor_position - - # Take the start of the lines. - from_, _ = buffer.document.translate_index_to_position(from_) - to, _ = buffer.document.translate_index_to_position(to) - - return from_, to - - def cut(self, buffer): - """ - Turn text object into `ClipboardData` instance. - """ - from_, to = self.operator_range(buffer.document) - - from_ += buffer.cursor_position - to += buffer.cursor_position - to -= 1 # SelectionState does not include the end position, `operator_range` does. - - document = Document(buffer.text, to, SelectionState( - original_cursor_position=from_, type=self.selection_type)) - - new_document, clipboard_data = document.cut_selection() - return new_document, clipboard_data - - -def create_text_object_decorator(registry): - """ - Create a decorator that can be used to register Vi text object implementations. - """ - assert isinstance(registry, BaseRegistry) - - operator_given = ViWaitingForTextObjectMode() - navigation_mode = ViNavigationMode() - selection_mode = ViSelectionMode() - - def text_object_decorator(*keys, **kw): - """ - Register a text object function. - - Usage:: - - @text_object('w', filter=..., no_move_handler=False) - def handler(event): - # Return a text object for this key. - return TextObject(...) - - :param no_move_handler: Disable the move handler in navigation mode. - (It's still active in selection mode.) - """ - filter = kw.pop('filter', Always()) - no_move_handler = kw.pop('no_move_handler', False) - no_selection_handler = kw.pop('no_selection_handler', False) - eager = kw.pop('eager', False) - assert not kw - - def decorator(text_object_func): - assert callable(text_object_func) - - @registry.add_binding(*keys, filter=operator_given & filter, eager=eager) - def _(event): - # Arguments are multiplied. - vi_state = event.cli.vi_state - event._arg = (vi_state.operator_arg or 1) * (event.arg or 1) - - # Call the text object handler. - text_obj = text_object_func(event) - if text_obj is not None: - assert isinstance(text_obj, TextObject) - - # Call the operator function with the text object. - vi_state.operator_func(event, text_obj) - - # Clear operator. - event.cli.vi_state.operator_func = None - event.cli.vi_state.operator_arg = None - - # Register a move operation. (Doesn't need an operator.) - if not no_move_handler: - @registry.add_binding(*keys, filter=~operator_given & filter & navigation_mode, eager=eager) - def _(event): - " Move handler for navigation mode. " - text_object = text_object_func(event) - event.current_buffer.cursor_position += text_object.start - - # Register a move selection operation. - if not no_selection_handler: - @registry.add_binding(*keys, filter=~operator_given & filter & selection_mode, eager=eager) - def _(event): - " Move handler for selection mode. " - text_object = text_object_func(event) - buff = event.current_buffer - - # When the text object has both a start and end position, like 'i(' or 'iw', - # Turn this into a selection, otherwise the cursor. - if text_object.end: - # Take selection positions from text object. - start, end = text_object.operator_range(buff.document) - start += buff.cursor_position - end += buff.cursor_position - - buff.selection_state.original_cursor_position = start - buff.cursor_position = end - - # Take selection type from text object. - if text_object.type == TextObjectType.LINEWISE: - buff.selection_state.type = SelectionType.LINES - else: - buff.selection_state.type = SelectionType.CHARACTERS - else: - event.current_buffer.cursor_position += text_object.start - - # Make it possible to chain @text_object decorators. - return text_object_func - - return decorator - return text_object_decorator - - -def create_operator_decorator(registry): - """ - Create a decorator that can be used for registering Vi operators. - """ - assert isinstance(registry, BaseRegistry) - - operator_given = ViWaitingForTextObjectMode() - navigation_mode = ViNavigationMode() - selection_mode = ViSelectionMode() - - def operator_decorator(*keys, **kw): - """ - Register a Vi operator. - - Usage:: - - @operator('d', filter=...) - def handler(cli, text_object): - # Do something with the text object here. - """ - filter = kw.pop('filter', Always()) - eager = kw.pop('eager', False) - assert not kw - - def decorator(operator_func): - @registry.add_binding(*keys, filter=~operator_given & filter & navigation_mode, eager=eager) - def _(event): - """ - Handle operator in navigation mode. - """ - # When this key binding is matched, only set the operator - # function in the ViState. We should execute it after a text - # object has been received. - event.cli.vi_state.operator_func = operator_func - event.cli.vi_state.operator_arg = event.arg - - @registry.add_binding(*keys, filter=~operator_given & filter & selection_mode, eager=eager) - def _(event): - """ - Handle operator in selection mode. - """ - buff = event.current_buffer - selection_state = buff.selection_state - - # Create text object from selection. - if selection_state.type == SelectionType.LINES: - text_obj_type = TextObjectType.LINEWISE - elif selection_state.type == SelectionType.BLOCK: - text_obj_type = TextObjectType.BLOCK - else: - text_obj_type = TextObjectType.INCLUSIVE - - text_object = TextObject( - selection_state.original_cursor_position - buff.cursor_position, - type=text_obj_type) - - # Execute operator. - operator_func(event, text_object) - - # Quit selection mode. - buff.selection_state = None - - return operator_func - return decorator - return operator_decorator - - -def load_vi_bindings(get_search_state=None): - """ - Vi extensions. - - # Overview of Readline Vi commands: - # http://www.catonmat.net/download/bash-vi-editing-mode-cheat-sheet.pdf - - :param get_search_state: None or a callable that takes a - CommandLineInterface and returns a SearchState. - """ - # Note: Some key bindings have the "~IsReadOnly()" filter added. This - # prevents the handler to be executed when the focus is on a - # read-only buffer. - # This is however only required for those that change the ViState to - # INSERT mode. The `Buffer` class itself throws the - # `EditReadOnlyBuffer` exception for any text operations which is - # handled correctly. There is no need to add "~IsReadOnly" to all key - # bindings that do text manipulation. - - registry = ConditionalRegistry(Registry(), ViMode()) - handle = registry.add_binding - - # Default get_search_state. - if get_search_state is None: - def get_search_state(cli): return cli.search_state - - # (Note: Always take the navigation bindings in read-only mode, even when - # ViState says different.) - navigation_mode = ViNavigationMode() - insert_mode = ViInsertMode() - insert_multiple_mode = ViInsertMultipleMode() - replace_mode = ViReplaceMode() - selection_mode = ViSelectionMode() - operator_given = ViWaitingForTextObjectMode() - digraph_mode = ViDigraphMode() - - vi_transform_functions = [ - # Rot 13 transformation - (('g', '?'), Always(), lambda string: codecs.encode(string, 'rot_13')), - - # To lowercase - (('g', 'u'), Always(), lambda string: string.lower()), - - # To uppercase. - (('g', 'U'), Always(), lambda string: string.upper()), - - # Swap case. - (('g', '~'), Always(), lambda string: string.swapcase()), - (('~', ), Condition(lambda cli: cli.vi_state.tilde_operator), lambda string: string.swapcase()), - ] - - # Insert a character literally (quoted insert). - handle(Keys.ControlV, filter=insert_mode)(get_by_name('quoted-insert')) - - @handle(Keys.Escape) - def _(event): - """ - Escape goes to vi navigation mode. - """ - buffer = event.current_buffer - vi_state = event.cli.vi_state - - if vi_state.input_mode in (InputMode.INSERT, InputMode.REPLACE): - buffer.cursor_position += buffer.document.get_cursor_left_position() - - vi_state.reset(InputMode.NAVIGATION) - - if bool(buffer.selection_state): - buffer.exit_selection() - - @handle('k', filter=selection_mode) - def _(event): - """ - Arrow up in selection mode. - """ - event.current_buffer.cursor_up(count=event.arg) - - @handle('j', filter=selection_mode) - def _(event): - """ - Arrow down in selection mode. - """ - event.current_buffer.cursor_down(count=event.arg) - - @handle(Keys.Up, filter=navigation_mode) - @handle(Keys.ControlP, filter=navigation_mode) - def _(event): - """ - Arrow up and ControlP in navigation mode go up. - """ - event.current_buffer.auto_up(count=event.arg) - - @handle('k', filter=navigation_mode) - def _(event): - """ - Go up, but if we enter a new history entry, move to the start of the - line. - """ - event.current_buffer.auto_up( - count=event.arg, go_to_start_of_line_if_history_changes=True) - - @handle(Keys.Down, filter=navigation_mode) - @handle(Keys.ControlN, filter=navigation_mode) - def _(event): - """ - Arrow down and Control-N in navigation mode. - """ - event.current_buffer.auto_down(count=event.arg) - - @handle('j', filter=navigation_mode) - def _(event): - """ - Go down, but if we enter a new history entry, go to the start of the line. - """ - event.current_buffer.auto_down( - count=event.arg, go_to_start_of_line_if_history_changes=True) - - @handle(Keys.ControlH, filter=navigation_mode) - @handle(Keys.Backspace, filter=navigation_mode) - def _(event): - """ - In navigation-mode, move cursor. - """ - event.current_buffer.cursor_position += \ - event.current_buffer.document.get_cursor_left_position(count=event.arg) - - @handle(Keys.ControlN, filter=insert_mode) - def _(event): - b = event.current_buffer - - if b.complete_state: - b.complete_next() - else: - event.cli.start_completion(select_first=True) - - @handle(Keys.ControlP, filter=insert_mode) - def _(event): - """ - Control-P: To previous completion. - """ - b = event.current_buffer - - if b.complete_state: - b.complete_previous() - else: - event.cli.start_completion(select_last=True) - - @handle(Keys.ControlY, filter=insert_mode) - def _(event): - """ - Accept current completion. - """ - event.current_buffer.complete_state = None - - @handle(Keys.ControlE, filter=insert_mode) - def _(event): - """ - Cancel completion. Go back to originally typed text. - """ - event.current_buffer.cancel_completion() - - @handle(Keys.ControlJ, filter=navigation_mode) # XXX: only if the selected buffer has a return handler. - def _(event): - """ - In navigation mode, pressing enter will always return the input. - """ - b = event.current_buffer - - if b.accept_action.is_returnable: - b.accept_action.validate_and_handle(event.cli, b) - - # ** In navigation mode ** - - # List of navigation commands: http://hea-www.harvard.edu/~fine/Tech/vi.html - - @handle(Keys.Insert, filter=navigation_mode) - def _(event): - " Presing the Insert key. " - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('a', filter=navigation_mode & ~IsReadOnly()) - # ~IsReadOnly, because we want to stay in navigation mode for - # read-only buffers. - def _(event): - event.current_buffer.cursor_position += event.current_buffer.document.get_cursor_right_position() - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('A', filter=navigation_mode & ~IsReadOnly()) - def _(event): - event.current_buffer.cursor_position += event.current_buffer.document.get_end_of_line_position() - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('C', filter=navigation_mode & ~IsReadOnly()) - def _(event): - """ - # Change to end of line. - # Same as 'c$' (which is implemented elsewhere.) - """ - buffer = event.current_buffer - - deleted = buffer.delete(count=buffer.document.get_end_of_line_position()) - event.cli.clipboard.set_text(deleted) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('c', 'c', filter=navigation_mode & ~IsReadOnly()) - @handle('S', filter=navigation_mode & ~IsReadOnly()) - def _(event): # TODO: implement 'arg' - """ - Change current line - """ - buffer = event.current_buffer - - # We copy the whole line. - data = ClipboardData(buffer.document.current_line, SelectionType.LINES) - event.cli.clipboard.set_data(data) - - # But we delete after the whitespace - buffer.cursor_position += buffer.document.get_start_of_line_position(after_whitespace=True) - buffer.delete(count=buffer.document.get_end_of_line_position()) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('D', filter=navigation_mode) - def _(event): - buffer = event.current_buffer - deleted = buffer.delete(count=buffer.document.get_end_of_line_position()) - event.cli.clipboard.set_text(deleted) - - @handle('d', 'd', filter=navigation_mode) - def _(event): - """ - Delete line. (Or the following 'n' lines.) - """ - buffer = event.current_buffer - - # Split string in before/deleted/after text. - lines = buffer.document.lines - - before = '\n'.join(lines[:buffer.document.cursor_position_row]) - deleted = '\n'.join(lines[buffer.document.cursor_position_row: - buffer.document.cursor_position_row + event.arg]) - after = '\n'.join(lines[buffer.document.cursor_position_row + event.arg:]) - - # Set new text. - if before and after: - before = before + '\n' - - # Set text and cursor position. - buffer.document = Document( - text=before + after, - # Cursor At the start of the first 'after' line, after the leading whitespace. - cursor_position = len(before) + len(after) - len(after.lstrip(' '))) - - # Set clipboard data - event.cli.clipboard.set_data(ClipboardData(deleted, SelectionType.LINES)) - - @handle('x', filter=selection_mode) - def _(event): - """ - Cut selection. - ('x' is not an operator.) - """ - clipboard_data = event.current_buffer.cut_selection() - event.cli.clipboard.set_data(clipboard_data) - - @handle('i', filter=navigation_mode & ~IsReadOnly()) - def _(event): - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('I', filter=navigation_mode & ~IsReadOnly()) - def _(event): - event.cli.vi_state.input_mode = InputMode.INSERT - event.current_buffer.cursor_position += \ - event.current_buffer.document.get_start_of_line_position(after_whitespace=True) - - @Condition - def in_block_selection(cli): - buff = cli.current_buffer - return buff.selection_state and buff.selection_state.type == SelectionType.BLOCK - - @handle('I', filter=in_block_selection & ~IsReadOnly()) - def go_to_block_selection(event, after=False): - " Insert in block selection mode. " - buff = event.current_buffer - - # Store all cursor positions. - positions = [] - - if after: - def get_pos(from_to): - return from_to[1] + 1 - else: - def get_pos(from_to): - return from_to[0] - - for i, from_to in enumerate(buff.document.selection_ranges()): - positions.append(get_pos(from_to)) - if i == 0: - buff.cursor_position = get_pos(from_to) - - buff.multiple_cursor_positions = positions - - # Go to 'INSERT_MULTIPLE' mode. - event.cli.vi_state.input_mode = InputMode.INSERT_MULTIPLE - buff.exit_selection() - - @handle('A', filter=in_block_selection & ~IsReadOnly()) - def _(event): - go_to_block_selection(event, after=True) - - @handle('J', filter=navigation_mode & ~IsReadOnly()) - def _(event): - " Join lines. " - for i in range(event.arg): - event.current_buffer.join_next_line() - - @handle('g', 'J', filter=navigation_mode & ~IsReadOnly()) - def _(event): - " Join lines without space. " - for i in range(event.arg): - event.current_buffer.join_next_line(separator='') - - @handle('J', filter=selection_mode & ~IsReadOnly()) - def _(event): - " Join selected lines. " - event.current_buffer.join_selected_lines() - - @handle('g', 'J', filter=selection_mode & ~IsReadOnly()) - def _(event): - " Join selected lines without space. " - event.current_buffer.join_selected_lines(separator='') - - @handle('p', filter=navigation_mode) - def _(event): - """ - Paste after - """ - event.current_buffer.paste_clipboard_data( - event.cli.clipboard.get_data(), - count=event.arg, - paste_mode=PasteMode.VI_AFTER) - - @handle('P', filter=navigation_mode) - def _(event): - """ - Paste before - """ - event.current_buffer.paste_clipboard_data( - event.cli.clipboard.get_data(), - count=event.arg, - paste_mode=PasteMode.VI_BEFORE) - - @handle('"', Keys.Any, 'p', filter=navigation_mode) - def _(event): - " Paste from named register. " - c = event.key_sequence[1].data - if c in vi_register_names: - data = event.cli.vi_state.named_registers.get(c) - if data: - event.current_buffer.paste_clipboard_data( - data, count=event.arg, paste_mode=PasteMode.VI_AFTER) - - @handle('"', Keys.Any, 'P', filter=navigation_mode) - def _(event): - " Paste (before) from named register. " - c = event.key_sequence[1].data - if c in vi_register_names: - data = event.cli.vi_state.named_registers.get(c) - if data: - event.current_buffer.paste_clipboard_data( - data, count=event.arg, paste_mode=PasteMode.VI_BEFORE) - - @handle('r', Keys.Any, filter=navigation_mode) - def _(event): - """ - Replace single character under cursor - """ - event.current_buffer.insert_text(event.data * event.arg, overwrite=True) - event.current_buffer.cursor_position -= 1 - - @handle('R', filter=navigation_mode) - def _(event): - """ - Go to 'replace'-mode. - """ - event.cli.vi_state.input_mode = InputMode.REPLACE - - @handle('s', filter=navigation_mode & ~IsReadOnly()) - def _(event): - """ - Substitute with new text - (Delete character(s) and go to insert mode.) - """ - text = event.current_buffer.delete(count=event.arg) - event.cli.clipboard.set_text(text) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('u', filter=navigation_mode, save_before=(lambda e: False)) - def _(event): - for i in range(event.arg): - event.current_buffer.undo() - - @handle('V', filter=navigation_mode) - def _(event): - """ - Start lines selection. - """ - event.current_buffer.start_selection(selection_type=SelectionType.LINES) - - @handle(Keys.ControlV, filter=navigation_mode) - def _(event): - " Enter block selection mode. " - event.current_buffer.start_selection(selection_type=SelectionType.BLOCK) - - @handle('V', filter=selection_mode) - def _(event): - """ - Exit line selection mode, or go from non line selection mode to line - selection mode. - """ - selection_state = event.current_buffer.selection_state - - if selection_state.type != SelectionType.LINES: - selection_state.type = SelectionType.LINES - else: - event.current_buffer.exit_selection() - - @handle('v', filter=navigation_mode) - def _(event): - " Enter character selection mode. " - event.current_buffer.start_selection(selection_type=SelectionType.CHARACTERS) - - @handle('v', filter=selection_mode) - def _(event): - """ - Exit character selection mode, or go from non-character-selection mode - to character selection mode. - """ - selection_state = event.current_buffer.selection_state - - if selection_state.type != SelectionType.CHARACTERS: - selection_state.type = SelectionType.CHARACTERS - else: - event.current_buffer.exit_selection() - - @handle(Keys.ControlV, filter=selection_mode) - def _(event): - """ - Exit block selection mode, or go from non block selection mode to block - selection mode. - """ - selection_state = event.current_buffer.selection_state - - if selection_state.type != SelectionType.BLOCK: - selection_state.type = SelectionType.BLOCK - else: - event.current_buffer.exit_selection() - - - @handle('a', 'w', filter=selection_mode) - @handle('a', 'W', filter=selection_mode) - def _(event): - """ - Switch from visual linewise mode to visual characterwise mode. - """ - buffer = event.current_buffer - - if buffer.selection_state and buffer.selection_state.type == SelectionType.LINES: - buffer.selection_state.type = SelectionType.CHARACTERS - - @handle('x', filter=navigation_mode) - def _(event): - """ - Delete character. - """ - text = event.current_buffer.delete(count=event.arg) - event.cli.clipboard.set_text(text) - - @handle('X', filter=navigation_mode) - def _(event): - text = event.current_buffer.delete_before_cursor() - event.cli.clipboard.set_text(text) - - @handle('y', 'y', filter=navigation_mode) - @handle('Y', filter=navigation_mode) - def _(event): - """ - Yank the whole line. - """ - text = '\n'.join(event.current_buffer.document.lines_from_current[:event.arg]) - event.cli.clipboard.set_data(ClipboardData(text, SelectionType.LINES)) - - @handle('+', filter=navigation_mode) - def _(event): - """ - Move to first non whitespace of next line - """ - buffer = event.current_buffer - buffer.cursor_position += buffer.document.get_cursor_down_position(count=event.arg) - buffer.cursor_position += buffer.document.get_start_of_line_position(after_whitespace=True) - - @handle('-', filter=navigation_mode) - def _(event): - """ - Move to first non whitespace of previous line - """ - buffer = event.current_buffer - buffer.cursor_position += buffer.document.get_cursor_up_position(count=event.arg) - buffer.cursor_position += buffer.document.get_start_of_line_position(after_whitespace=True) - - @handle('>', '>', filter=navigation_mode) - def _(event): - """ - Indent lines. - """ - buffer = event.current_buffer - current_row = buffer.document.cursor_position_row - indent(buffer, current_row, current_row + event.arg) - - @handle('<', '<', filter=navigation_mode) - def _(event): - """ - Unindent lines. - """ - current_row = event.current_buffer.document.cursor_position_row - unindent(event.current_buffer, current_row, current_row + event.arg) - - @handle('O', filter=navigation_mode & ~IsReadOnly()) - def _(event): - """ - Open line above and enter insertion mode - """ - event.current_buffer.insert_line_above( - copy_margin=not event.cli.in_paste_mode) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('o', filter=navigation_mode & ~IsReadOnly()) - def _(event): - """ - Open line below and enter insertion mode - """ - event.current_buffer.insert_line_below( - copy_margin=not event.cli.in_paste_mode) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle('~', filter=navigation_mode) - def _(event): - """ - Reverse case of current character and move cursor forward. - """ - buffer = event.current_buffer - c = buffer.document.current_char - - if c is not None and c != '\n': - buffer.insert_text(c.swapcase(), overwrite=True) - - @handle('g', 'u', 'u', filter=navigation_mode & ~IsReadOnly()) - def _(event): - " Lowercase current line. " - buff = event.current_buffer - buff.transform_current_line(lambda s: s.lower()) - - @handle('g', 'U', 'U', filter=navigation_mode & ~IsReadOnly()) - def _(event): - " Uppercase current line. " - buff = event.current_buffer - buff.transform_current_line(lambda s: s.upper()) - - @handle('g', '~', '~', filter=navigation_mode & ~IsReadOnly()) - def _(event): - " Swap case of the current line. " - buff = event.current_buffer - buff.transform_current_line(lambda s: s.swapcase()) - - @handle('#', filter=navigation_mode) - def _(event): - """ - Go to previous occurence of this word. - """ - b = event.cli.current_buffer - - search_state = get_search_state(event.cli) - search_state.text = b.document.get_word_under_cursor() - search_state.direction = IncrementalSearchDirection.BACKWARD - - b.apply_search(search_state, count=event.arg, - include_current_position=False) - - @handle('*', filter=navigation_mode) - def _(event): - """ - Go to next occurence of this word. - """ - b = event.cli.current_buffer - - search_state = get_search_state(event.cli) - search_state.text = b.document.get_word_under_cursor() - search_state.direction = IncrementalSearchDirection.FORWARD - - b.apply_search(search_state, count=event.arg, - include_current_position=False) - - @handle('(', filter=navigation_mode) - def _(event): - # TODO: go to begin of sentence. - # XXX: should become text_object. - pass - - @handle(')', filter=navigation_mode) - def _(event): - # TODO: go to end of sentence. - # XXX: should become text_object. - pass - - operator = create_operator_decorator(registry) - text_object = create_text_object_decorator(registry) - - @text_object(Keys.Any, filter=operator_given) - def _(event): - """ - Unknown key binding while waiting for a text object. - """ - event.cli.output.bell() - - # - # *** Operators *** - # - - def create_delete_and_change_operators(delete_only, with_register=False): - """ - Delete and change operators. - - :param delete_only: Create an operator that deletes, but doesn't go to insert mode. - :param with_register: Copy the deleted text to this named register instead of the clipboard. - """ - if with_register: - handler_keys = ('"', Keys.Any, 'cd'[delete_only]) - else: - handler_keys = 'cd'[delete_only] - - @operator(*handler_keys, filter=~IsReadOnly()) - def delete_or_change_operator(event, text_object): - clipboard_data = None - buff = event.current_buffer - - if text_object: - new_document, clipboard_data = text_object.cut(buff) - buff.document = new_document - - # Set deleted/changed text to clipboard or named register. - if clipboard_data and clipboard_data.text: - if with_register: - reg_name = event.key_sequence[1].data - if reg_name in vi_register_names: - event.cli.vi_state.named_registers[reg_name] = clipboard_data - else: - event.cli.clipboard.set_data(clipboard_data) - - # Only go back to insert mode in case of 'change'. - if not delete_only: - event.cli.vi_state.input_mode = InputMode.INSERT - - create_delete_and_change_operators(False, False) - create_delete_and_change_operators(False, True) - create_delete_and_change_operators(True, False) - create_delete_and_change_operators(True, True) - - def create_transform_handler(filter, transform_func, *a): - @operator(*a, filter=filter & ~IsReadOnly()) - def _(event, text_object): - """ - Apply transformation (uppercase, lowercase, rot13, swap case). - """ - buff = event.current_buffer - start, end = text_object.operator_range(buff.document) - - if start < end: - # Transform. - buff.transform_region( - buff.cursor_position + start, - buff.cursor_position + end, - transform_func) - - # Move cursor - buff.cursor_position += (text_object.end or text_object.start) - - for k, f, func in vi_transform_functions: - create_transform_handler(f, func, *k) - - @operator('y') - def yank_handler(event, text_object): - """ - Yank operator. (Copy text.) - """ - _, clipboard_data = text_object.cut(event.current_buffer) - if clipboard_data.text: - event.cli.clipboard.set_data(clipboard_data) - - @operator('"', Keys.Any, 'y') - def _(event, text_object): - " Yank selection to named register. " - c = event.key_sequence[1].data - if c in vi_register_names: - _, clipboard_data = text_object.cut(event.current_buffer) - event.cli.vi_state.named_registers[c] = clipboard_data - - @operator('>') - def _(event, text_object): - """ - Indent. - """ - buff = event.current_buffer - from_, to = text_object.get_line_numbers(buff) - indent(buff, from_, to + 1, count=event.arg) - - @operator('<') - def _(event, text_object): - """ - Unindent. - """ - buff = event.current_buffer - from_, to = text_object.get_line_numbers(buff) - unindent(buff, from_, to + 1, count=event.arg) - - @operator('g', 'q') - def _(event, text_object): - """ - Reshape text. - """ - buff = event.current_buffer - from_, to = text_object.get_line_numbers(buff) - reshape_text(buff, from_, to) - - # - # *** Text objects *** - # - - @text_object('b') - def _(event): - """ Move one word or token left. """ - return TextObject(event.current_buffer.document.find_start_of_previous_word(count=event.arg) or 0) - - @text_object('B') - def _(event): - """ Move one non-blank word left """ - return TextObject(event.current_buffer.document.find_start_of_previous_word(count=event.arg, WORD=True) or 0) - - @text_object('$') - def key_dollar(event): - """ 'c$', 'd$' and '$': Delete/change/move until end of line. """ - return TextObject(event.current_buffer.document.get_end_of_line_position()) - - @text_object('w') - def _(event): - """ 'word' forward. 'cw', 'dw', 'w': Delete/change/move one word. """ - return TextObject(event.current_buffer.document.find_next_word_beginning(count=event.arg) or - event.current_buffer.document.get_end_of_document_position()) - - @text_object('W') - def _(event): - """ 'WORD' forward. 'cW', 'dW', 'W': Delete/change/move one WORD. """ - return TextObject(event.current_buffer.document.find_next_word_beginning(count=event.arg, WORD=True) or - event.current_buffer.document.get_end_of_document_position()) - - @text_object('e') - def _(event): - """ End of 'word': 'ce', 'de', 'e' """ - end = event.current_buffer.document.find_next_word_ending(count=event.arg) - return TextObject(end - 1 if end else 0, type=TextObjectType.INCLUSIVE) - - @text_object('E') - def _(event): - """ End of 'WORD': 'cE', 'dE', 'E' """ - end = event.current_buffer.document.find_next_word_ending(count=event.arg, WORD=True) - return TextObject(end - 1 if end else 0, type=TextObjectType.INCLUSIVE) - - @text_object('i', 'w', no_move_handler=True) - def _(event): - """ Inner 'word': ciw and diw """ - start, end = event.current_buffer.document.find_boundaries_of_current_word() - return TextObject(start, end) - - @text_object('a', 'w', no_move_handler=True) - def _(event): - """ A 'word': caw and daw """ - start, end = event.current_buffer.document.find_boundaries_of_current_word(include_trailing_whitespace=True) - return TextObject(start, end) - - @text_object('i', 'W', no_move_handler=True) - def _(event): - """ Inner 'WORD': ciW and diW """ - start, end = event.current_buffer.document.find_boundaries_of_current_word(WORD=True) - return TextObject(start, end) - - @text_object('a', 'W', no_move_handler=True) - def _(event): - """ A 'WORD': caw and daw """ - start, end = event.current_buffer.document.find_boundaries_of_current_word(WORD=True, include_trailing_whitespace=True) - return TextObject(start, end) - - @text_object('a', 'p', no_move_handler=True) - def _(event): - """ - Auto paragraph. - """ - start = event.current_buffer.document.start_of_paragraph() - end = event.current_buffer.document.end_of_paragraph(count=event.arg) - return TextObject(start, end) - - @text_object('^') - def key_circumflex(event): - """ 'c^', 'd^' and '^': Soft start of line, after whitespace. """ - return TextObject(event.current_buffer.document.get_start_of_line_position(after_whitespace=True)) - - @text_object('0') - def key_zero(event): - """ - 'c0', 'd0': Hard start of line, before whitespace. - (The move '0' key is implemented elsewhere, because a '0' could also change the `arg`.) - """ - return TextObject(event.current_buffer.document.get_start_of_line_position(after_whitespace=False)) - - def create_ci_ca_handles(ci_start, ci_end, inner, key=None): - # TODO: 'dat', 'dit', (tags (like xml) - """ - Delete/Change string between this start and stop character. But keep these characters. - This implements all the ci", ci<, ci{, ci(, di", di<, ca", ca<, ... combinations. - """ - def handler(event): - if ci_start == ci_end: - # Quotes - start = event.current_buffer.document.find_backwards(ci_start, in_current_line=False) - end = event.current_buffer.document.find(ci_end, in_current_line=False) - else: - # Brackets - start = event.current_buffer.document.find_enclosing_bracket_left(ci_start, ci_end) - end = event.current_buffer.document.find_enclosing_bracket_right(ci_start, ci_end) - - if start is not None and end is not None: - offset = 0 if inner else 1 - return TextObject(start + 1 - offset, end + offset) - else: - # Nothing found. - return TextObject(0) - - if key is None: - text_object('ai'[inner], ci_start, no_move_handler=True)(handler) - text_object('ai'[inner], ci_end, no_move_handler=True)(handler) - else: - text_object('ai'[inner], key, no_move_handler=True)(handler) - - for inner in (False, True): - for ci_start, ci_end in [('"', '"'), ("'", "'"), ("`", "`"), - ('[', ']'), ('<', '>'), ('{', '}'), ('(', ')')]: - create_ci_ca_handles(ci_start, ci_end, inner) - - create_ci_ca_handles('(', ')', inner, 'b') # 'dab', 'dib' - create_ci_ca_handles('{', '}', inner, 'B') # 'daB', 'diB' - - @text_object('{') - def _(event): - """ - Move to previous blank-line separated section. - Implements '{', 'c{', 'd{', 'y{' - """ - index = event.current_buffer.document.start_of_paragraph( - count=event.arg, before=True) - return TextObject(index) - - @text_object('}') - def _(event): - """ - Move to next blank-line separated section. - Implements '}', 'c}', 'd}', 'y}' - """ - index = event.current_buffer.document.end_of_paragraph(count=event.arg, after=True) - return TextObject(index) - - @text_object('f', Keys.Any) - def _(event): - """ - Go to next occurance of character. Typing 'fx' will move the - cursor to the next occurance of character. 'x'. - """ - event.cli.vi_state.last_character_find = CharacterFind(event.data, False) - match = event.current_buffer.document.find( - event.data, in_current_line=True, count=event.arg) - if match: - return TextObject(match, type=TextObjectType.INCLUSIVE) - else: - return TextObject(0) - - @text_object('F', Keys.Any) - def _(event): - """ - Go to previous occurance of character. Typing 'Fx' will move the - cursor to the previous occurance of character. 'x'. - """ - event.cli.vi_state.last_character_find = CharacterFind(event.data, True) - return TextObject(event.current_buffer.document.find_backwards( - event.data, in_current_line=True, count=event.arg) or 0) - - @text_object('t', Keys.Any) - def _(event): - """ - Move right to the next occurance of c, then one char backward. - """ - event.cli.vi_state.last_character_find = CharacterFind(event.data, False) - match = event.current_buffer.document.find( - event.data, in_current_line=True, count=event.arg) - if match: - return TextObject(match - 1, type=TextObjectType.INCLUSIVE) - else: - return TextObject(0) - - @text_object('T', Keys.Any) - def _(event): - """ - Move left to the previous occurance of c, then one char forward. - """ - event.cli.vi_state.last_character_find = CharacterFind(event.data, True) - match = event.current_buffer.document.find_backwards( - event.data, in_current_line=True, count=event.arg) - return TextObject(match + 1 if match else 0) - - def repeat(reverse): - """ - Create ',' and ';' commands. - """ - @text_object(',' if reverse else ';') - def _(event): - # Repeat the last 'f'/'F'/'t'/'T' command. - pos = 0 - vi_state = event.cli.vi_state - - type = TextObjectType.EXCLUSIVE - - if vi_state.last_character_find: - char = vi_state.last_character_find.character - backwards = vi_state.last_character_find.backwards - - if reverse: - backwards = not backwards - - if backwards: - pos = event.current_buffer.document.find_backwards(char, in_current_line=True, count=event.arg) - else: - pos = event.current_buffer.document.find(char, in_current_line=True, count=event.arg) - type = TextObjectType.INCLUSIVE - if pos: - return TextObject(pos, type=type) - else: - return TextObject(0) - repeat(True) - repeat(False) - - @text_object('h') - @text_object(Keys.Left) - def _(event): - """ Implements 'ch', 'dh', 'h': Cursor left. """ - return TextObject(event.current_buffer.document.get_cursor_left_position(count=event.arg)) - - @text_object('j', no_move_handler=True, no_selection_handler=True) - # Note: We also need `no_selection_handler`, because we in - # selection mode, we prefer the other 'j' binding that keeps - # `buffer.preferred_column`. - def _(event): - """ Implements 'cj', 'dj', 'j', ... Cursor up. """ - return TextObject(event.current_buffer.document.get_cursor_down_position(count=event.arg), - type=TextObjectType.LINEWISE) - - @text_object('k', no_move_handler=True, no_selection_handler=True) - def _(event): - """ Implements 'ck', 'dk', 'k', ... Cursor up. """ - return TextObject(event.current_buffer.document.get_cursor_up_position(count=event.arg), - type=TextObjectType.LINEWISE) - - @text_object('l') - @text_object(' ') - @text_object(Keys.Right) - def _(event): - """ Implements 'cl', 'dl', 'l', 'c ', 'd ', ' '. Cursor right. """ - return TextObject(event.current_buffer.document.get_cursor_right_position(count=event.arg)) - - @text_object('H') - def _(event): - """ - Moves to the start of the visible region. (Below the scroll offset.) - Implements 'cH', 'dH', 'H'. - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.current_buffer - - if w and w.render_info: - # When we find a Window that has BufferControl showing this window, - # move to the start of the visible area. - pos = (b.document.translate_row_col_to_index( - w.render_info.first_visible_line(after_scroll_offset=True), 0) - - b.cursor_position) - - else: - # Otherwise, move to the start of the input. - pos = -len(b.document.text_before_cursor) - return TextObject(pos, type=TextObjectType.LINEWISE) - - @text_object('M') - def _(event): - """ - Moves cursor to the vertical center of the visible region. - Implements 'cM', 'dM', 'M'. - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.current_buffer - - if w and w.render_info: - # When we find a Window that has BufferControl showing this window, - # move to the center of the visible area. - pos = (b.document.translate_row_col_to_index( - w.render_info.center_visible_line(), 0) - - b.cursor_position) - - else: - # Otherwise, move to the start of the input. - pos = -len(b.document.text_before_cursor) - return TextObject(pos, type=TextObjectType.LINEWISE) - - @text_object('L') - def _(event): - """ - Moves to the end of the visible region. (Above the scroll offset.) - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.current_buffer - - if w and w.render_info: - # When we find a Window that has BufferControl showing this window, - # move to the end of the visible area. - pos = (b.document.translate_row_col_to_index( - w.render_info.last_visible_line(before_scroll_offset=True), 0) - - b.cursor_position) - - else: - # Otherwise, move to the end of the input. - pos = len(b.document.text_after_cursor) - return TextObject(pos, type=TextObjectType.LINEWISE) - - @text_object('n', no_move_handler=True) - def _(event): - " Search next. " - buff = event.current_buffer - cursor_position = buff.get_search_position( - get_search_state(event.cli), include_current_position=False, - count=event.arg) - return TextObject(cursor_position - buff.cursor_position) - - @handle('n', filter=navigation_mode) - def _(event): - " Search next in navigation mode. (This goes through the history.) " - event.current_buffer.apply_search( - get_search_state(event.cli), include_current_position=False, - count=event.arg) - - @text_object('N', no_move_handler=True) - def _(event): - " Search previous. " - buff = event.current_buffer - cursor_position = buff.get_search_position( - ~get_search_state(event.cli), include_current_position=False, - count=event.arg) - return TextObject(cursor_position - buff.cursor_position) - - @handle('N', filter=navigation_mode) - def _(event): - " Search previous in navigation mode. (This goes through the history.) " - event.current_buffer.apply_search( - ~get_search_state(event.cli), include_current_position=False, - count=event.arg) - - @handle('z', '+', filter=navigation_mode|selection_mode) - @handle('z', 't', filter=navigation_mode|selection_mode) - @handle('z', Keys.ControlJ, filter=navigation_mode|selection_mode) - def _(event): - """ - Scrolls the window to makes the current line the first line in the visible region. - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.cli.current_buffer - w.vertical_scroll = b.document.cursor_position_row - - @handle('z', '-', filter=navigation_mode|selection_mode) - @handle('z', 'b', filter=navigation_mode|selection_mode) - def _(event): - """ - Scrolls the window to makes the current line the last line in the visible region. - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - - # We can safely set the scroll offset to zero; the Window will meke - # sure that it scrolls at least enough to make the cursor visible - # again. - w.vertical_scroll = 0 - - @handle('z', 'z', filter=navigation_mode|selection_mode) - def _(event): - """ - Center Window vertically around cursor. - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - b = event.cli.current_buffer - - if w and w.render_info: - info = w.render_info - - # Calculate the offset that we need in order to position the row - # containing the cursor in the center. - scroll_height = info.window_height // 2 - - y = max(0, b.document.cursor_position_row - 1) - height = 0 - while y > 0: - line_height = info.get_height_for_line(y) - - if height + line_height < scroll_height: - height += line_height - y -= 1 - else: - break - - w.vertical_scroll = y - - @text_object('%') - def _(event): - """ - Implements 'c%', 'd%', '%, 'y%' (Move to corresponding bracket.) - If an 'arg' has been given, go this this % position in the file. - """ - buffer = event.current_buffer - - if event._arg: - # If 'arg' has been given, the meaning of % is to go to the 'x%' - # row in the file. - if 0 < event.arg <= 100: - absolute_index = buffer.document.translate_row_col_to_index( - int((event.arg * buffer.document.line_count - 1) / 100), 0) - return TextObject(absolute_index - buffer.document.cursor_position, type=TextObjectType.LINEWISE) - else: - return TextObject(0) # Do nothing. - - else: - # Move to the corresponding opening/closing bracket (()'s, []'s and {}'s). - match = buffer.document.find_matching_bracket_position() - if match: - return TextObject(match, type=TextObjectType.INCLUSIVE) - else: - return TextObject(0) - - @text_object('|') - def _(event): - # Move to the n-th column (you may specify the argument n by typing - # it on number keys, for example, 20|). - return TextObject(event.current_buffer.document.get_column_cursor_position(event.arg - 1)) - - @text_object('g', 'g') - def _(event): - """ - Implements 'gg', 'cgg', 'ygg' - """ - d = event.current_buffer.document - - if event._arg: - # Move to the given line. - return TextObject(d.translate_row_col_to_index(event.arg - 1, 0) - d.cursor_position, type=TextObjectType.LINEWISE) - else: - # Move to the top of the input. - return TextObject(d.get_start_of_document_position(), type=TextObjectType.LINEWISE) - - @text_object('g', '_') - def _(event): - """ - Go to last non-blank of line. - 'g_', 'cg_', 'yg_', etc.. - """ - return TextObject( - event.current_buffer.document.last_non_blank_of_current_line_position(), type=TextObjectType.INCLUSIVE) - - @text_object('g', 'e') - def _(event): - """ - Go to last character of previous word. - 'ge', 'cge', 'yge', etc.. - """ - prev_end = event.current_buffer.document.find_previous_word_ending(count=event.arg) - return TextObject(prev_end - 1 if prev_end is not None else 0, type=TextObjectType.INCLUSIVE) - - @text_object('g', 'E') - def _(event): - """ - Go to last character of previous WORD. - 'gE', 'cgE', 'ygE', etc.. - """ - prev_end = event.current_buffer.document.find_previous_word_ending(count=event.arg, WORD=True) - return TextObject(prev_end - 1 if prev_end is not None else 0, type=TextObjectType.INCLUSIVE) - - @text_object('g', 'm') - def _(event): - """ - Like g0, but half a screenwidth to the right. (Or as much as possible.) - """ - w = find_window_for_buffer_name(event.cli, event.cli.current_buffer_name) - buff = event.current_buffer - - if w and w.render_info: - width = w.render_info.window_width - start = buff.document.get_start_of_line_position(after_whitespace=False) - start += int(min(width / 2, len(buff.document.current_line))) - - return TextObject(start, type=TextObjectType.INCLUSIVE) - return TextObject(0) - - @text_object('G') - def _(event): - """ - Go to the end of the document. (If no arg has been given.) - """ - buf = event.current_buffer - return TextObject(buf.document.translate_row_col_to_index(buf.document.line_count - 1, 0) - - buf.cursor_position, type=TextObjectType.LINEWISE) - - # - # *** Other *** - # - - @handle('G', filter=HasArg()) - def _(event): - """ - If an argument is given, move to this line in the history. (for - example, 15G) - """ - event.current_buffer.go_to_history(event.arg - 1) - - for n in '123456789': - @handle(n, filter=navigation_mode|selection_mode|operator_given) - def _(event): - """ - Always handle numberics in navigation mode as arg. - """ - event.append_to_arg_count(event.data) - - @handle('0', filter=(navigation_mode|selection_mode|operator_given) & HasArg()) - def _(event): - " Zero when an argument was already give. " - event.append_to_arg_count(event.data) - - @handle(Keys.Any, filter=replace_mode) - def _(event): - """ - Insert data at cursor position. - """ - event.current_buffer.insert_text(event.data, overwrite=True) - - @handle(Keys.Any, filter=insert_multiple_mode, - save_before=(lambda e: not e.is_repeat)) - def _(event): - """ - Insert data at multiple cursor positions at once. - (Usually a result of pressing 'I' or 'A' in block-selection mode.) - """ - buff = event.current_buffer - original_text = buff.text - - # Construct new text. - text = [] - p = 0 - - for p2 in buff.multiple_cursor_positions: - text.append(original_text[p:p2]) - text.append(event.data) - p = p2 - - text.append(original_text[p:]) - - # Shift all cursor positions. - new_cursor_positions = [ - p + i + 1 for i, p in enumerate(buff.multiple_cursor_positions)] - - # Set result. - buff.text = ''.join(text) - buff.multiple_cursor_positions = new_cursor_positions - buff.cursor_position += 1 - - @handle(Keys.Backspace, filter=insert_multiple_mode) - def _(event): - " Backspace, using multiple cursors. " - buff = event.current_buffer - original_text = buff.text - - # Construct new text. - deleted_something = False - text = [] - p = 0 - - for p2 in buff.multiple_cursor_positions: - if p2 > 0 and original_text[p2 - 1] != '\n': # Don't delete across lines. - text.append(original_text[p:p2 - 1]) - deleted_something = True - else: - text.append(original_text[p:p2]) - p = p2 - - text.append(original_text[p:]) - - if deleted_something: - # Shift all cursor positions. - lengths = [len(part) for part in text[:-1]] - new_cursor_positions = list(accumulate(lengths)) - - # Set result. - buff.text = ''.join(text) - buff.multiple_cursor_positions = new_cursor_positions - buff.cursor_position -= 1 - else: - event.cli.output.bell() - - @handle(Keys.Delete, filter=insert_multiple_mode) - def _(event): - " Delete, using multiple cursors. " - buff = event.current_buffer - original_text = buff.text - - # Construct new text. - deleted_something = False - text = [] - new_cursor_positions = [] - p = 0 - - for p2 in buff.multiple_cursor_positions: - text.append(original_text[p:p2]) - if p2 >= len(original_text) or original_text[p2] == '\n': - # Don't delete across lines. - p = p2 - else: - p = p2 + 1 - deleted_something = True - - text.append(original_text[p:]) - - if deleted_something: - # Shift all cursor positions. - lengths = [len(part) for part in text[:-1]] - new_cursor_positions = list(accumulate(lengths)) - - # Set result. - buff.text = ''.join(text) - buff.multiple_cursor_positions = new_cursor_positions - else: - event.cli.output.bell() - - - @handle(Keys.ControlX, Keys.ControlL, filter=insert_mode) - def _(event): - """ - Pressing the ControlX - ControlL sequence in Vi mode does line - completion based on the other lines in the document and the history. - """ - event.current_buffer.start_history_lines_completion() - - @handle(Keys.ControlX, Keys.ControlF, filter=insert_mode) - def _(event): - """ - Complete file names. - """ - # TODO - pass - - @handle(Keys.ControlK, filter=insert_mode|replace_mode) - def _(event): - " Go into digraph mode. " - event.cli.vi_state.waiting_for_digraph = True - - @Condition - def digraph_symbol_1_given(cli): - return cli.vi_state.digraph_symbol1 is not None - - @handle(Keys.Any, filter=digraph_mode & ~digraph_symbol_1_given) - def _(event): - event.cli.vi_state.digraph_symbol1 = event.data - - @handle(Keys.Any, filter=digraph_mode & digraph_symbol_1_given) - def _(event): - " Insert digraph. " - try: - # Lookup. - code = (event.cli.vi_state.digraph_symbol1, event.data) - if code not in DIGRAPHS: - code = code[::-1] # Try reversing. - symbol = DIGRAPHS[code] - except KeyError: - # Unkown digraph. - event.cli.output.bell() - else: - # Insert digraph. - overwrite = event.cli.vi_state.input_mode == InputMode.REPLACE - event.current_buffer.insert_text( - six.unichr(symbol), overwrite=overwrite) - event.cli.vi_state.waiting_for_digraph = False - finally: - event.cli.vi_state.waiting_for_digraph = False - event.cli.vi_state.digraph_symbol1 = None - - return registry - - -def load_vi_open_in_editor_bindings(): - """ - Pressing 'v' in navigation mode will open the buffer in an external editor. - """ - registry = Registry() - navigation_mode = ViNavigationMode() - - registry.add_binding('v', filter=navigation_mode)( - get_by_name('edit-and-execute-command')) - return registry - - -def load_vi_system_bindings(): - registry = ConditionalRegistry(Registry(), ViMode()) - handle = registry.add_binding - - has_focus = filters.HasFocus(SYSTEM_BUFFER) - navigation_mode = ViNavigationMode() - - @handle('!', filter=~has_focus & navigation_mode) - def _(event): - """ - '!' opens the system prompt. - """ - event.cli.push_focus(SYSTEM_BUFFER) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle(Keys.Escape, filter=has_focus) - @handle(Keys.ControlC, filter=has_focus) - def _(event): - """ - Cancel system prompt. - """ - event.cli.vi_state.input_mode = InputMode.NAVIGATION - event.cli.buffers[SYSTEM_BUFFER].reset() - event.cli.pop_focus() - - @handle(Keys.ControlJ, filter=has_focus) - def _(event): - """ - Run system command. - """ - event.cli.vi_state.input_mode = InputMode.NAVIGATION - - system_buffer = event.cli.buffers[SYSTEM_BUFFER] - event.cli.run_system_command(system_buffer.text) - system_buffer.reset(append_to_history=True) - - # Focus previous buffer again. - event.cli.pop_focus() - - return registry - - -def load_vi_search_bindings(get_search_state=None, - search_buffer_name=SEARCH_BUFFER): - assert get_search_state is None or callable(get_search_state) - - if not get_search_state: - def get_search_state(cli): return cli.search_state - - registry = ConditionalRegistry(Registry(), ViMode()) - handle = registry.add_binding - - has_focus = filters.HasFocus(search_buffer_name) - navigation_mode = ViNavigationMode() - selection_mode = ViSelectionMode() - - reverse_vi_search_direction = Condition( - lambda cli: cli.application.reverse_vi_search_direction(cli)) - - @handle('/', filter=(navigation_mode|selection_mode)&~reverse_vi_search_direction) - @handle('?', filter=(navigation_mode|selection_mode)&reverse_vi_search_direction) - @handle(Keys.ControlS, filter=~has_focus) - def _(event): - """ - Vi-style forward search. - """ - # Set the ViState. - get_search_state(event.cli).direction = IncrementalSearchDirection.FORWARD - event.cli.vi_state.input_mode = InputMode.INSERT - - # Focus search buffer. - event.cli.push_focus(search_buffer_name) - - @handle('?', filter=(navigation_mode|selection_mode)&~reverse_vi_search_direction) - @handle('/', filter=(navigation_mode|selection_mode)&reverse_vi_search_direction) - @handle(Keys.ControlR, filter=~has_focus) - def _(event): - """ - Vi-style backward search. - """ - # Set the ViState. - get_search_state(event.cli).direction = IncrementalSearchDirection.BACKWARD - - # Focus search buffer. - event.cli.push_focus(search_buffer_name) - event.cli.vi_state.input_mode = InputMode.INSERT - - @handle(Keys.ControlJ, filter=has_focus) - @handle(Keys.Escape, filter=has_focus) - def _(event): - """ - Apply the search. (At the / or ? prompt.) - """ - input_buffer = event.cli.buffers.previous(event.cli) - search_buffer = event.cli.buffers[search_buffer_name] - - # Update search state. - if search_buffer.text: - get_search_state(event.cli).text = search_buffer.text - - # Apply search. - input_buffer.apply_search(get_search_state(event.cli)) - - # Add query to history of search line. - search_buffer.append_to_history() - search_buffer.reset() - - # Focus previous document again. - event.cli.vi_state.input_mode = InputMode.NAVIGATION - event.cli.pop_focus() - - def incremental_search(cli, direction, count=1): - " Apply search, but keep search buffer focussed. " - # Update search_state. - search_state = get_search_state(cli) - direction_changed = search_state.direction != direction - - search_state.text = cli.buffers[search_buffer_name].text - search_state.direction = direction - - # Apply search to current buffer. - if not direction_changed: - input_buffer = cli.buffers.previous(cli) - input_buffer.apply_search(search_state, - include_current_position=False, count=count) - - @handle(Keys.ControlR, filter=has_focus) - def _(event): - incremental_search(event.cli, IncrementalSearchDirection.BACKWARD, count=event.arg) - - @handle(Keys.ControlS, filter=has_focus) - def _(event): - incremental_search(event.cli, IncrementalSearchDirection.FORWARD, count=event.arg) - - def search_buffer_is_empty(cli): - """ Returns True when the search buffer is empty. """ - return cli.buffers[search_buffer_name].text == '' - - @handle(Keys.ControlC, filter=has_focus) - @handle(Keys.ControlH, filter=has_focus & Condition(search_buffer_is_empty)) - @handle(Keys.Backspace, filter=has_focus & Condition(search_buffer_is_empty)) - def _(event): - """ - Cancel search. - """ - event.cli.vi_state.input_mode = InputMode.NAVIGATION - - event.cli.pop_focus() - event.cli.buffers[search_buffer_name].reset() - - return registry - - -def load_extra_vi_page_navigation_bindings(): - """ - Key bindings, for scrolling up and down through pages. - This are separate bindings, because GNU readline doesn't have them. - """ - registry = ConditionalRegistry(Registry(), ViMode()) - handle = registry.add_binding - - handle(Keys.ControlF)(scroll_forward) - handle(Keys.ControlB)(scroll_backward) - handle(Keys.ControlD)(scroll_half_page_down) - handle(Keys.ControlU)(scroll_half_page_up) - handle(Keys.ControlE)(scroll_one_line_down) - handle(Keys.ControlY)(scroll_one_line_up) - handle(Keys.PageDown)(scroll_page_down) - handle(Keys.PageUp)(scroll_page_up) - - return registry - - -class ViStateFilter(Filter): - " Deprecated! " - def __init__(self, get_vi_state, mode): - self.get_vi_state = get_vi_state - self.mode = mode - - def __call__(self, cli): - return self.get_vi_state(cli).input_mode == self.mode diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/defaults.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/defaults.py deleted file mode 100644 index fb2c1070f79..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/defaults.py +++ /dev/null @@ -1,119 +0,0 @@ -""" -Default key bindings.:: - - registry = load_key_bindings() - app = Application(key_bindings_registry=registry) -""" -from __future__ import unicode_literals -from prompt_toolkit.key_binding.registry import ConditionalRegistry, MergedRegistry -from prompt_toolkit.key_binding.bindings.basic import load_basic_bindings, load_abort_and_exit_bindings, load_basic_system_bindings, load_auto_suggestion_bindings, load_mouse_bindings -from prompt_toolkit.key_binding.bindings.emacs import load_emacs_bindings, load_emacs_system_bindings, load_emacs_search_bindings, load_emacs_open_in_editor_bindings, load_extra_emacs_page_navigation_bindings -from prompt_toolkit.key_binding.bindings.vi import load_vi_bindings, load_vi_system_bindings, load_vi_search_bindings, load_vi_open_in_editor_bindings, load_extra_vi_page_navigation_bindings -from prompt_toolkit.filters import to_cli_filter - -__all__ = ( - 'load_key_bindings', - 'load_key_bindings_for_prompt', -) - - -def load_key_bindings( - get_search_state=None, - enable_abort_and_exit_bindings=False, - enable_system_bindings=False, - enable_search=False, - enable_open_in_editor=False, - enable_extra_page_navigation=False, - enable_auto_suggest_bindings=False): - """ - Create a Registry object that contains the default key bindings. - - :param enable_abort_and_exit_bindings: Filter to enable Ctrl-C and Ctrl-D. - :param enable_system_bindings: Filter to enable the system bindings (meta-! - prompt and Control-Z suspension.) - :param enable_search: Filter to enable the search bindings. - :param enable_open_in_editor: Filter to enable open-in-editor. - :param enable_open_in_editor: Filter to enable open-in-editor. - :param enable_extra_page_navigation: Filter for enabling extra page - navigation. (Bindings for up/down scrolling through long pages, like in - Emacs or Vi.) - :param enable_auto_suggest_bindings: Filter to enable fish-style suggestions. - """ - - assert get_search_state is None or callable(get_search_state) - - # Accept both Filters and booleans as input. - enable_abort_and_exit_bindings = to_cli_filter(enable_abort_and_exit_bindings) - enable_system_bindings = to_cli_filter(enable_system_bindings) - enable_search = to_cli_filter(enable_search) - enable_open_in_editor = to_cli_filter(enable_open_in_editor) - enable_extra_page_navigation = to_cli_filter(enable_extra_page_navigation) - enable_auto_suggest_bindings = to_cli_filter(enable_auto_suggest_bindings) - - registry = MergedRegistry([ - # Load basic bindings. - load_basic_bindings(), - load_mouse_bindings(), - - ConditionalRegistry(load_abort_and_exit_bindings(), - enable_abort_and_exit_bindings), - - ConditionalRegistry(load_basic_system_bindings(), - enable_system_bindings), - - # Load emacs bindings. - load_emacs_bindings(), - - ConditionalRegistry(load_emacs_open_in_editor_bindings(), - enable_open_in_editor), - - ConditionalRegistry(load_emacs_search_bindings(get_search_state=get_search_state), - enable_search), - - ConditionalRegistry(load_emacs_system_bindings(), - enable_system_bindings), - - ConditionalRegistry(load_extra_emacs_page_navigation_bindings(), - enable_extra_page_navigation), - - # Load Vi bindings. - load_vi_bindings(get_search_state=get_search_state), - - ConditionalRegistry(load_vi_open_in_editor_bindings(), - enable_open_in_editor), - - ConditionalRegistry(load_vi_search_bindings(get_search_state=get_search_state), - enable_search), - - ConditionalRegistry(load_vi_system_bindings(), - enable_system_bindings), - - ConditionalRegistry(load_extra_vi_page_navigation_bindings(), - enable_extra_page_navigation), - - # Suggestion bindings. - # (This has to come at the end, because the Vi bindings also have an - # implementation for the "right arrow", but we really want the - # suggestion binding when a suggestion is available.) - ConditionalRegistry(load_auto_suggestion_bindings(), - enable_auto_suggest_bindings), - ]) - - return registry - - -def load_key_bindings_for_prompt(**kw): - """ - Create a ``Registry`` object with the defaults key bindings for an input - prompt. - - This activates the key bindings for abort/exit (Ctrl-C/Ctrl-D), - incremental search and auto suggestions. - - (Not for full screen applications.) - """ - kw.setdefault('enable_abort_and_exit_bindings', True) - kw.setdefault('enable_search', True) - kw.setdefault('enable_auto_suggest_bindings', True) - - return load_key_bindings(**kw) diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/digraphs.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/digraphs.py deleted file mode 100644 index 36c6b15103a..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/digraphs.py +++ /dev/null @@ -1,1378 +0,0 @@ -# encoding: utf-8 -from __future__ import unicode_literals -""" -Vi Digraphs. -This is a list of special characters that can be inserted in Vi insert mode by -pressing Control-K followed by to normal characters. - -Taken from Neovim and translated to Python: -https://raw.githubusercontent.com/neovim/neovim/master/src/nvim/digraph.c -""" -__all__ = ('DIGRAPHS', ) - -# digraphs for Unicode from RFC1345 -# (also work for ISO-8859-1 aka latin1) -DIGRAPHS = { - ('N', 'U'): 0x00, - ('S', 'H'): 0x01, - ('S', 'X'): 0x02, - ('E', 'X'): 0x03, - ('E', 'T'): 0x04, - ('E', 'Q'): 0x05, - ('A', 'K'): 0x06, - ('B', 'L'): 0x07, - ('B', 'S'): 0x08, - ('H', 'T'): 0x09, - ('L', 'F'): 0x0a, - ('V', 'T'): 0x0b, - ('F', 'F'): 0x0c, - ('C', 'R'): 0x0d, - ('S', 'O'): 0x0e, - ('S', 'I'): 0x0f, - ('D', 'L'): 0x10, - ('D', '1'): 0x11, - ('D', '2'): 0x12, - ('D', '3'): 0x13, - ('D', '4'): 0x14, - ('N', 'K'): 0x15, - ('S', 'Y'): 0x16, - ('E', 'B'): 0x17, - ('C', 'N'): 0x18, - ('E', 'M'): 0x19, - ('S', 'B'): 0x1a, - ('E', 'C'): 0x1b, - ('F', 'S'): 0x1c, - ('G', 'S'): 0x1d, - ('R', 'S'): 0x1e, - ('U', 'S'): 0x1f, - ('S', 'P'): 0x20, - ('N', 'b'): 0x23, - ('D', 'O'): 0x24, - ('A', 't'): 0x40, - ('<', '('): 0x5b, - ('/', '/'): 0x5c, - (')', '>'): 0x5d, - ('\'', '>'): 0x5e, - ('\'', '!'): 0x60, - ('(', '!'): 0x7b, - ('!', '!'): 0x7c, - ('!', ')'): 0x7d, - ('\'', '?'): 0x7e, - ('D', 'T'): 0x7f, - ('P', 'A'): 0x80, - ('H', 'O'): 0x81, - ('B', 'H'): 0x82, - ('N', 'H'): 0x83, - ('I', 'N'): 0x84, - ('N', 'L'): 0x85, - ('S', 'A'): 0x86, - ('E', 'S'): 0x87, - ('H', 'S'): 0x88, - ('H', 'J'): 0x89, - ('V', 'S'): 0x8a, - ('P', 'D'): 0x8b, - ('P', 'U'): 0x8c, - ('R', 'I'): 0x8d, - ('S', '2'): 0x8e, - ('S', '3'): 0x8f, - ('D', 'C'): 0x90, - ('P', '1'): 0x91, - ('P', '2'): 0x92, - ('T', 'S'): 0x93, - ('C', 'C'): 0x94, - ('M', 'W'): 0x95, - ('S', 'G'): 0x96, - ('E', 'G'): 0x97, - ('S', 'S'): 0x98, - ('G', 'C'): 0x99, - ('S', 'C'): 0x9a, - ('C', 'I'): 0x9b, - ('S', 'T'): 0x9c, - ('O', 'C'): 0x9d, - ('P', 'M'): 0x9e, - ('A', 'C'): 0x9f, - ('N', 'S'): 0xa0, - ('!', 'I'): 0xa1, - ('C', 't'): 0xa2, - ('P', 'd'): 0xa3, - ('C', 'u'): 0xa4, - ('Y', 'e'): 0xa5, - ('B', 'B'): 0xa6, - ('S', 'E'): 0xa7, - ('\'', ':'): 0xa8, - ('C', 'o'): 0xa9, - ('-', 'a'): 0xaa, - ('<', '<'): 0xab, - ('N', 'O'): 0xac, - ('-', '-'): 0xad, - ('R', 'g'): 0xae, - ('\'', 'm'): 0xaf, - ('D', 'G'): 0xb0, - ('+', '-'): 0xb1, - ('2', 'S'): 0xb2, - ('3', 'S'): 0xb3, - ('\'', '\''): 0xb4, - ('M', 'y'): 0xb5, - ('P', 'I'): 0xb6, - ('.', 'M'): 0xb7, - ('\'', ','): 0xb8, - ('1', 'S'): 0xb9, - ('-', 'o'): 0xba, - ('>', '>'): 0xbb, - ('1', '4'): 0xbc, - ('1', '2'): 0xbd, - ('3', '4'): 0xbe, - ('?', 'I'): 0xbf, - ('A', '!'): 0xc0, - ('A', '\''): 0xc1, - ('A', '>'): 0xc2, - ('A', '?'): 0xc3, - ('A', ':'): 0xc4, - ('A', 'A'): 0xc5, - ('A', 'E'): 0xc6, - ('C', ','): 0xc7, - ('E', '!'): 0xc8, - ('E', '\''): 0xc9, - ('E', '>'): 0xca, - ('E', ':'): 0xcb, - ('I', '!'): 0xcc, - ('I', '\''): 0xcd, - ('I', '>'): 0xce, - ('I', ':'): 0xcf, - ('D', '-'): 0xd0, - ('N', '?'): 0xd1, - ('O', '!'): 0xd2, - ('O', '\''): 0xd3, - ('O', '>'): 0xd4, - ('O', '?'): 0xd5, - ('O', ':'): 0xd6, - ('*', 'X'): 0xd7, - ('O', '/'): 0xd8, - ('U', '!'): 0xd9, - ('U', '\''): 0xda, - ('U', '>'): 0xdb, - ('U', ':'): 0xdc, - ('Y', '\''): 0xdd, - ('T', 'H'): 0xde, - ('s', 's'): 0xdf, - ('a', '!'): 0xe0, - ('a', '\''): 0xe1, - ('a', '>'): 0xe2, - ('a', '?'): 0xe3, - ('a', ':'): 0xe4, - ('a', 'a'): 0xe5, - ('a', 'e'): 0xe6, - ('c', ','): 0xe7, - ('e', '!'): 0xe8, - ('e', '\''): 0xe9, - ('e', '>'): 0xea, - ('e', ':'): 0xeb, - ('i', '!'): 0xec, - ('i', '\''): 0xed, - ('i', '>'): 0xee, - ('i', ':'): 0xef, - ('d', '-'): 0xf0, - ('n', '?'): 0xf1, - ('o', '!'): 0xf2, - ('o', '\''): 0xf3, - ('o', '>'): 0xf4, - ('o', '?'): 0xf5, - ('o', ':'): 0xf6, - ('-', ':'): 0xf7, - ('o', '/'): 0xf8, - ('u', '!'): 0xf9, - ('u', '\''): 0xfa, - ('u', '>'): 0xfb, - ('u', ':'): 0xfc, - ('y', '\''): 0xfd, - ('t', 'h'): 0xfe, - ('y', ':'): 0xff, - - ('A', '-'): 0x0100, - ('a', '-'): 0x0101, - ('A', '('): 0x0102, - ('a', '('): 0x0103, - ('A', ';'): 0x0104, - ('a', ';'): 0x0105, - ('C', '\''): 0x0106, - ('c', '\''): 0x0107, - ('C', '>'): 0x0108, - ('c', '>'): 0x0109, - ('C', '.'): 0x010a, - ('c', '.'): 0x010b, - ('C', '<'): 0x010c, - ('c', '<'): 0x010d, - ('D', '<'): 0x010e, - ('d', '<'): 0x010f, - ('D', '/'): 0x0110, - ('d', '/'): 0x0111, - ('E', '-'): 0x0112, - ('e', '-'): 0x0113, - ('E', '('): 0x0114, - ('e', '('): 0x0115, - ('E', '.'): 0x0116, - ('e', '.'): 0x0117, - ('E', ';'): 0x0118, - ('e', ';'): 0x0119, - ('E', '<'): 0x011a, - ('e', '<'): 0x011b, - ('G', '>'): 0x011c, - ('g', '>'): 0x011d, - ('G', '('): 0x011e, - ('g', '('): 0x011f, - ('G', '.'): 0x0120, - ('g', '.'): 0x0121, - ('G', ','): 0x0122, - ('g', ','): 0x0123, - ('H', '>'): 0x0124, - ('h', '>'): 0x0125, - ('H', '/'): 0x0126, - ('h', '/'): 0x0127, - ('I', '?'): 0x0128, - ('i', '?'): 0x0129, - ('I', '-'): 0x012a, - ('i', '-'): 0x012b, - ('I', '('): 0x012c, - ('i', '('): 0x012d, - ('I', ';'): 0x012e, - ('i', ';'): 0x012f, - ('I', '.'): 0x0130, - ('i', '.'): 0x0131, - ('I', 'J'): 0x0132, - ('i', 'j'): 0x0133, - ('J', '>'): 0x0134, - ('j', '>'): 0x0135, - ('K', ','): 0x0136, - ('k', ','): 0x0137, - ('k', 'k'): 0x0138, - ('L', '\''): 0x0139, - ('l', '\''): 0x013a, - ('L', ','): 0x013b, - ('l', ','): 0x013c, - ('L', '<'): 0x013d, - ('l', '<'): 0x013e, - ('L', '.'): 0x013f, - ('l', '.'): 0x0140, - ('L', '/'): 0x0141, - ('l', '/'): 0x0142, - ('N', '\''): 0x0143, - ('n', '\''): 0x0144, - ('N', ','): 0x0145, - ('n', ','): 0x0146, - ('N', '<'): 0x0147, - ('n', '<'): 0x0148, - ('\'', 'n'): 0x0149, - ('N', 'G'): 0x014a, - ('n', 'g'): 0x014b, - ('O', '-'): 0x014c, - ('o', '-'): 0x014d, - ('O', '('): 0x014e, - ('o', '('): 0x014f, - ('O', '"'): 0x0150, - ('o', '"'): 0x0151, - ('O', 'E'): 0x0152, - ('o', 'e'): 0x0153, - ('R', '\''): 0x0154, - ('r', '\''): 0x0155, - ('R', ','): 0x0156, - ('r', ','): 0x0157, - ('R', '<'): 0x0158, - ('r', '<'): 0x0159, - ('S', '\''): 0x015a, - ('s', '\''): 0x015b, - ('S', '>'): 0x015c, - ('s', '>'): 0x015d, - ('S', ','): 0x015e, - ('s', ','): 0x015f, - ('S', '<'): 0x0160, - ('s', '<'): 0x0161, - ('T', ','): 0x0162, - ('t', ','): 0x0163, - ('T', '<'): 0x0164, - ('t', '<'): 0x0165, - ('T', '/'): 0x0166, - ('t', '/'): 0x0167, - ('U', '?'): 0x0168, - ('u', '?'): 0x0169, - ('U', '-'): 0x016a, - ('u', '-'): 0x016b, - ('U', '('): 0x016c, - ('u', '('): 0x016d, - ('U', '0'): 0x016e, - ('u', '0'): 0x016f, - ('U', '"'): 0x0170, - ('u', '"'): 0x0171, - ('U', ';'): 0x0172, - ('u', ';'): 0x0173, - ('W', '>'): 0x0174, - ('w', '>'): 0x0175, - ('Y', '>'): 0x0176, - ('y', '>'): 0x0177, - ('Y', ':'): 0x0178, - ('Z', '\''): 0x0179, - ('z', '\''): 0x017a, - ('Z', '.'): 0x017b, - ('z', '.'): 0x017c, - ('Z', '<'): 0x017d, - ('z', '<'): 0x017e, - ('O', '9'): 0x01a0, - ('o', '9'): 0x01a1, - ('O', 'I'): 0x01a2, - ('o', 'i'): 0x01a3, - ('y', 'r'): 0x01a6, - ('U', '9'): 0x01af, - ('u', '9'): 0x01b0, - ('Z', '/'): 0x01b5, - ('z', '/'): 0x01b6, - ('E', 'D'): 0x01b7, - ('A', '<'): 0x01cd, - ('a', '<'): 0x01ce, - ('I', '<'): 0x01cf, - ('i', '<'): 0x01d0, - ('O', '<'): 0x01d1, - ('o', '<'): 0x01d2, - ('U', '<'): 0x01d3, - ('u', '<'): 0x01d4, - ('A', '1'): 0x01de, - ('a', '1'): 0x01df, - ('A', '7'): 0x01e0, - ('a', '7'): 0x01e1, - ('A', '3'): 0x01e2, - ('a', '3'): 0x01e3, - ('G', '/'): 0x01e4, - ('g', '/'): 0x01e5, - ('G', '<'): 0x01e6, - ('g', '<'): 0x01e7, - ('K', '<'): 0x01e8, - ('k', '<'): 0x01e9, - ('O', ';'): 0x01ea, - ('o', ';'): 0x01eb, - ('O', '1'): 0x01ec, - ('o', '1'): 0x01ed, - ('E', 'Z'): 0x01ee, - ('e', 'z'): 0x01ef, - ('j', '<'): 0x01f0, - ('G', '\''): 0x01f4, - ('g', '\''): 0x01f5, - (';', 'S'): 0x02bf, - ('\'', '<'): 0x02c7, - ('\'', '('): 0x02d8, - ('\'', '.'): 0x02d9, - ('\'', '0'): 0x02da, - ('\'', ';'): 0x02db, - ('\'', '"'): 0x02dd, - ('A', '%'): 0x0386, - ('E', '%'): 0x0388, - ('Y', '%'): 0x0389, - ('I', '%'): 0x038a, - ('O', '%'): 0x038c, - ('U', '%'): 0x038e, - ('W', '%'): 0x038f, - ('i', '3'): 0x0390, - ('A', '*'): 0x0391, - ('B', '*'): 0x0392, - ('G', '*'): 0x0393, - ('D', '*'): 0x0394, - ('E', '*'): 0x0395, - ('Z', '*'): 0x0396, - ('Y', '*'): 0x0397, - ('H', '*'): 0x0398, - ('I', '*'): 0x0399, - ('K', '*'): 0x039a, - ('L', '*'): 0x039b, - ('M', '*'): 0x039c, - ('N', '*'): 0x039d, - ('C', '*'): 0x039e, - ('O', '*'): 0x039f, - ('P', '*'): 0x03a0, - ('R', '*'): 0x03a1, - ('S', '*'): 0x03a3, - ('T', '*'): 0x03a4, - ('U', '*'): 0x03a5, - ('F', '*'): 0x03a6, - ('X', '*'): 0x03a7, - ('Q', '*'): 0x03a8, - ('W', '*'): 0x03a9, - ('J', '*'): 0x03aa, - ('V', '*'): 0x03ab, - ('a', '%'): 0x03ac, - ('e', '%'): 0x03ad, - ('y', '%'): 0x03ae, - ('i', '%'): 0x03af, - ('u', '3'): 0x03b0, - ('a', '*'): 0x03b1, - ('b', '*'): 0x03b2, - ('g', '*'): 0x03b3, - ('d', '*'): 0x03b4, - ('e', '*'): 0x03b5, - ('z', '*'): 0x03b6, - ('y', '*'): 0x03b7, - ('h', '*'): 0x03b8, - ('i', '*'): 0x03b9, - ('k', '*'): 0x03ba, - ('l', '*'): 0x03bb, - ('m', '*'): 0x03bc, - ('n', '*'): 0x03bd, - ('c', '*'): 0x03be, - ('o', '*'): 0x03bf, - ('p', '*'): 0x03c0, - ('r', '*'): 0x03c1, - ('*', 's'): 0x03c2, - ('s', '*'): 0x03c3, - ('t', '*'): 0x03c4, - ('u', '*'): 0x03c5, - ('f', '*'): 0x03c6, - ('x', '*'): 0x03c7, - ('q', '*'): 0x03c8, - ('w', '*'): 0x03c9, - ('j', '*'): 0x03ca, - ('v', '*'): 0x03cb, - ('o', '%'): 0x03cc, - ('u', '%'): 0x03cd, - ('w', '%'): 0x03ce, - ('\'', 'G'): 0x03d8, - (',', 'G'): 0x03d9, - ('T', '3'): 0x03da, - ('t', '3'): 0x03db, - ('M', '3'): 0x03dc, - ('m', '3'): 0x03dd, - ('K', '3'): 0x03de, - ('k', '3'): 0x03df, - ('P', '3'): 0x03e0, - ('p', '3'): 0x03e1, - ('\'', '%'): 0x03f4, - ('j', '3'): 0x03f5, - ('I', 'O'): 0x0401, - ('D', '%'): 0x0402, - ('G', '%'): 0x0403, - ('I', 'E'): 0x0404, - ('D', 'S'): 0x0405, - ('I', 'I'): 0x0406, - ('Y', 'I'): 0x0407, - ('J', '%'): 0x0408, - ('L', 'J'): 0x0409, - ('N', 'J'): 0x040a, - ('T', 's'): 0x040b, - ('K', 'J'): 0x040c, - ('V', '%'): 0x040e, - ('D', 'Z'): 0x040f, - ('A', '='): 0x0410, - ('B', '='): 0x0411, - ('V', '='): 0x0412, - ('G', '='): 0x0413, - ('D', '='): 0x0414, - ('E', '='): 0x0415, - ('Z', '%'): 0x0416, - ('Z', '='): 0x0417, - ('I', '='): 0x0418, - ('J', '='): 0x0419, - ('K', '='): 0x041a, - ('L', '='): 0x041b, - ('M', '='): 0x041c, - ('N', '='): 0x041d, - ('O', '='): 0x041e, - ('P', '='): 0x041f, - ('R', '='): 0x0420, - ('S', '='): 0x0421, - ('T', '='): 0x0422, - ('U', '='): 0x0423, - ('F', '='): 0x0424, - ('H', '='): 0x0425, - ('C', '='): 0x0426, - ('C', '%'): 0x0427, - ('S', '%'): 0x0428, - ('S', 'c'): 0x0429, - ('=', '"'): 0x042a, - ('Y', '='): 0x042b, - ('%', '"'): 0x042c, - ('J', 'E'): 0x042d, - ('J', 'U'): 0x042e, - ('J', 'A'): 0x042f, - ('a', '='): 0x0430, - ('b', '='): 0x0431, - ('v', '='): 0x0432, - ('g', '='): 0x0433, - ('d', '='): 0x0434, - ('e', '='): 0x0435, - ('z', '%'): 0x0436, - ('z', '='): 0x0437, - ('i', '='): 0x0438, - ('j', '='): 0x0439, - ('k', '='): 0x043a, - ('l', '='): 0x043b, - ('m', '='): 0x043c, - ('n', '='): 0x043d, - ('o', '='): 0x043e, - ('p', '='): 0x043f, - ('r', '='): 0x0440, - ('s', '='): 0x0441, - ('t', '='): 0x0442, - ('u', '='): 0x0443, - ('f', '='): 0x0444, - ('h', '='): 0x0445, - ('c', '='): 0x0446, - ('c', '%'): 0x0447, - ('s', '%'): 0x0448, - ('s', 'c'): 0x0449, - ('=', '\''): 0x044a, - ('y', '='): 0x044b, - ('%', '\''): 0x044c, - ('j', 'e'): 0x044d, - ('j', 'u'): 0x044e, - ('j', 'a'): 0x044f, - ('i', 'o'): 0x0451, - ('d', '%'): 0x0452, - ('g', '%'): 0x0453, - ('i', 'e'): 0x0454, - ('d', 's'): 0x0455, - ('i', 'i'): 0x0456, - ('y', 'i'): 0x0457, - ('j', '%'): 0x0458, - ('l', 'j'): 0x0459, - ('n', 'j'): 0x045a, - ('t', 's'): 0x045b, - ('k', 'j'): 0x045c, - ('v', '%'): 0x045e, - ('d', 'z'): 0x045f, - ('Y', '3'): 0x0462, - ('y', '3'): 0x0463, - ('O', '3'): 0x046a, - ('o', '3'): 0x046b, - ('F', '3'): 0x0472, - ('f', '3'): 0x0473, - ('V', '3'): 0x0474, - ('v', '3'): 0x0475, - ('C', '3'): 0x0480, - ('c', '3'): 0x0481, - ('G', '3'): 0x0490, - ('g', '3'): 0x0491, - ('A', '+'): 0x05d0, - ('B', '+'): 0x05d1, - ('G', '+'): 0x05d2, - ('D', '+'): 0x05d3, - ('H', '+'): 0x05d4, - ('W', '+'): 0x05d5, - ('Z', '+'): 0x05d6, - ('X', '+'): 0x05d7, - ('T', 'j'): 0x05d8, - ('J', '+'): 0x05d9, - ('K', '%'): 0x05da, - ('K', '+'): 0x05db, - ('L', '+'): 0x05dc, - ('M', '%'): 0x05dd, - ('M', '+'): 0x05de, - ('N', '%'): 0x05df, - ('N', '+'): 0x05e0, - ('S', '+'): 0x05e1, - ('E', '+'): 0x05e2, - ('P', '%'): 0x05e3, - ('P', '+'): 0x05e4, - ('Z', 'j'): 0x05e5, - ('Z', 'J'): 0x05e6, - ('Q', '+'): 0x05e7, - ('R', '+'): 0x05e8, - ('S', 'h'): 0x05e9, - ('T', '+'): 0x05ea, - (',', '+'): 0x060c, - (';', '+'): 0x061b, - ('?', '+'): 0x061f, - ('H', '\''): 0x0621, - ('a', 'M'): 0x0622, - ('a', 'H'): 0x0623, - ('w', 'H'): 0x0624, - ('a', 'h'): 0x0625, - ('y', 'H'): 0x0626, - ('a', '+'): 0x0627, - ('b', '+'): 0x0628, - ('t', 'm'): 0x0629, - ('t', '+'): 0x062a, - ('t', 'k'): 0x062b, - ('g', '+'): 0x062c, - ('h', 'k'): 0x062d, - ('x', '+'): 0x062e, - ('d', '+'): 0x062f, - ('d', 'k'): 0x0630, - ('r', '+'): 0x0631, - ('z', '+'): 0x0632, - ('s', '+'): 0x0633, - ('s', 'n'): 0x0634, - ('c', '+'): 0x0635, - ('d', 'd'): 0x0636, - ('t', 'j'): 0x0637, - ('z', 'H'): 0x0638, - ('e', '+'): 0x0639, - ('i', '+'): 0x063a, - ('+', '+'): 0x0640, - ('f', '+'): 0x0641, - ('q', '+'): 0x0642, - ('k', '+'): 0x0643, - ('l', '+'): 0x0644, - ('m', '+'): 0x0645, - ('n', '+'): 0x0646, - ('h', '+'): 0x0647, - ('w', '+'): 0x0648, - ('j', '+'): 0x0649, - ('y', '+'): 0x064a, - (':', '+'): 0x064b, - ('"', '+'): 0x064c, - ('=', '+'): 0x064d, - ('/', '+'): 0x064e, - ('\'', '+'): 0x064f, - ('1', '+'): 0x0650, - ('3', '+'): 0x0651, - ('0', '+'): 0x0652, - ('a', 'S'): 0x0670, - ('p', '+'): 0x067e, - ('v', '+'): 0x06a4, - ('g', 'f'): 0x06af, - ('0', 'a'): 0x06f0, - ('1', 'a'): 0x06f1, - ('2', 'a'): 0x06f2, - ('3', 'a'): 0x06f3, - ('4', 'a'): 0x06f4, - ('5', 'a'): 0x06f5, - ('6', 'a'): 0x06f6, - ('7', 'a'): 0x06f7, - ('8', 'a'): 0x06f8, - ('9', 'a'): 0x06f9, - ('B', '.'): 0x1e02, - ('b', '.'): 0x1e03, - ('B', '_'): 0x1e06, - ('b', '_'): 0x1e07, - ('D', '.'): 0x1e0a, - ('d', '.'): 0x1e0b, - ('D', '_'): 0x1e0e, - ('d', '_'): 0x1e0f, - ('D', ','): 0x1e10, - ('d', ','): 0x1e11, - ('F', '.'): 0x1e1e, - ('f', '.'): 0x1e1f, - ('G', '-'): 0x1e20, - ('g', '-'): 0x1e21, - ('H', '.'): 0x1e22, - ('h', '.'): 0x1e23, - ('H', ':'): 0x1e26, - ('h', ':'): 0x1e27, - ('H', ','): 0x1e28, - ('h', ','): 0x1e29, - ('K', '\''): 0x1e30, - ('k', '\''): 0x1e31, - ('K', '_'): 0x1e34, - ('k', '_'): 0x1e35, - ('L', '_'): 0x1e3a, - ('l', '_'): 0x1e3b, - ('M', '\''): 0x1e3e, - ('m', '\''): 0x1e3f, - ('M', '.'): 0x1e40, - ('m', '.'): 0x1e41, - ('N', '.'): 0x1e44, - ('n', '.'): 0x1e45, - ('N', '_'): 0x1e48, - ('n', '_'): 0x1e49, - ('P', '\''): 0x1e54, - ('p', '\''): 0x1e55, - ('P', '.'): 0x1e56, - ('p', '.'): 0x1e57, - ('R', '.'): 0x1e58, - ('r', '.'): 0x1e59, - ('R', '_'): 0x1e5e, - ('r', '_'): 0x1e5f, - ('S', '.'): 0x1e60, - ('s', '.'): 0x1e61, - ('T', '.'): 0x1e6a, - ('t', '.'): 0x1e6b, - ('T', '_'): 0x1e6e, - ('t', '_'): 0x1e6f, - ('V', '?'): 0x1e7c, - ('v', '?'): 0x1e7d, - ('W', '!'): 0x1e80, - ('w', '!'): 0x1e81, - ('W', '\''): 0x1e82, - ('w', '\''): 0x1e83, - ('W', ':'): 0x1e84, - ('w', ':'): 0x1e85, - ('W', '.'): 0x1e86, - ('w', '.'): 0x1e87, - ('X', '.'): 0x1e8a, - ('x', '.'): 0x1e8b, - ('X', ':'): 0x1e8c, - ('x', ':'): 0x1e8d, - ('Y', '.'): 0x1e8e, - ('y', '.'): 0x1e8f, - ('Z', '>'): 0x1e90, - ('z', '>'): 0x1e91, - ('Z', '_'): 0x1e94, - ('z', '_'): 0x1e95, - ('h', '_'): 0x1e96, - ('t', ':'): 0x1e97, - ('w', '0'): 0x1e98, - ('y', '0'): 0x1e99, - ('A', '2'): 0x1ea2, - ('a', '2'): 0x1ea3, - ('E', '2'): 0x1eba, - ('e', '2'): 0x1ebb, - ('E', '?'): 0x1ebc, - ('e', '?'): 0x1ebd, - ('I', '2'): 0x1ec8, - ('i', '2'): 0x1ec9, - ('O', '2'): 0x1ece, - ('o', '2'): 0x1ecf, - ('U', '2'): 0x1ee6, - ('u', '2'): 0x1ee7, - ('Y', '!'): 0x1ef2, - ('y', '!'): 0x1ef3, - ('Y', '2'): 0x1ef6, - ('y', '2'): 0x1ef7, - ('Y', '?'): 0x1ef8, - ('y', '?'): 0x1ef9, - (';', '\''): 0x1f00, - (',', '\''): 0x1f01, - (';', '!'): 0x1f02, - (',', '!'): 0x1f03, - ('?', ';'): 0x1f04, - ('?', ','): 0x1f05, - ('!', ':'): 0x1f06, - ('?', ':'): 0x1f07, - ('1', 'N'): 0x2002, - ('1', 'M'): 0x2003, - ('3', 'M'): 0x2004, - ('4', 'M'): 0x2005, - ('6', 'M'): 0x2006, - ('1', 'T'): 0x2009, - ('1', 'H'): 0x200a, - ('-', '1'): 0x2010, - ('-', 'N'): 0x2013, - ('-', 'M'): 0x2014, - ('-', '3'): 0x2015, - ('!', '2'): 0x2016, - ('=', '2'): 0x2017, - ('\'', '6'): 0x2018, - ('\'', '9'): 0x2019, - ('.', '9'): 0x201a, - ('9', '\''): 0x201b, - ('"', '6'): 0x201c, - ('"', '9'): 0x201d, - (':', '9'): 0x201e, - ('9', '"'): 0x201f, - ('/', '-'): 0x2020, - ('/', '='): 0x2021, - ('.', '.'): 0x2025, - ('%', '0'): 0x2030, - ('1', '\''): 0x2032, - ('2', '\''): 0x2033, - ('3', '\''): 0x2034, - ('1', '"'): 0x2035, - ('2', '"'): 0x2036, - ('3', '"'): 0x2037, - ('C', 'a'): 0x2038, - ('<', '1'): 0x2039, - ('>', '1'): 0x203a, - (':', 'X'): 0x203b, - ('\'', '-'): 0x203e, - ('/', 'f'): 0x2044, - ('0', 'S'): 0x2070, - ('4', 'S'): 0x2074, - ('5', 'S'): 0x2075, - ('6', 'S'): 0x2076, - ('7', 'S'): 0x2077, - ('8', 'S'): 0x2078, - ('9', 'S'): 0x2079, - ('+', 'S'): 0x207a, - ('-', 'S'): 0x207b, - ('=', 'S'): 0x207c, - ('(', 'S'): 0x207d, - (')', 'S'): 0x207e, - ('n', 'S'): 0x207f, - ('0', 's'): 0x2080, - ('1', 's'): 0x2081, - ('2', 's'): 0x2082, - ('3', 's'): 0x2083, - ('4', 's'): 0x2084, - ('5', 's'): 0x2085, - ('6', 's'): 0x2086, - ('7', 's'): 0x2087, - ('8', 's'): 0x2088, - ('9', 's'): 0x2089, - ('+', 's'): 0x208a, - ('-', 's'): 0x208b, - ('=', 's'): 0x208c, - ('(', 's'): 0x208d, - (')', 's'): 0x208e, - ('L', 'i'): 0x20a4, - ('P', 't'): 0x20a7, - ('W', '='): 0x20a9, - ('=', 'e'): 0x20ac, # euro - ('E', 'u'): 0x20ac, # euro - ('=', 'R'): 0x20bd, # rouble - ('=', 'P'): 0x20bd, # rouble - ('o', 'C'): 0x2103, - ('c', 'o'): 0x2105, - ('o', 'F'): 0x2109, - ('N', '0'): 0x2116, - ('P', 'O'): 0x2117, - ('R', 'x'): 0x211e, - ('S', 'M'): 0x2120, - ('T', 'M'): 0x2122, - ('O', 'm'): 0x2126, - ('A', 'O'): 0x212b, - ('1', '3'): 0x2153, - ('2', '3'): 0x2154, - ('1', '5'): 0x2155, - ('2', '5'): 0x2156, - ('3', '5'): 0x2157, - ('4', '5'): 0x2158, - ('1', '6'): 0x2159, - ('5', '6'): 0x215a, - ('1', '8'): 0x215b, - ('3', '8'): 0x215c, - ('5', '8'): 0x215d, - ('7', '8'): 0x215e, - ('1', 'R'): 0x2160, - ('2', 'R'): 0x2161, - ('3', 'R'): 0x2162, - ('4', 'R'): 0x2163, - ('5', 'R'): 0x2164, - ('6', 'R'): 0x2165, - ('7', 'R'): 0x2166, - ('8', 'R'): 0x2167, - ('9', 'R'): 0x2168, - ('a', 'R'): 0x2169, - ('b', 'R'): 0x216a, - ('c', 'R'): 0x216b, - ('1', 'r'): 0x2170, - ('2', 'r'): 0x2171, - ('3', 'r'): 0x2172, - ('4', 'r'): 0x2173, - ('5', 'r'): 0x2174, - ('6', 'r'): 0x2175, - ('7', 'r'): 0x2176, - ('8', 'r'): 0x2177, - ('9', 'r'): 0x2178, - ('a', 'r'): 0x2179, - ('b', 'r'): 0x217a, - ('c', 'r'): 0x217b, - ('<', '-'): 0x2190, - ('-', '!'): 0x2191, - ('-', '>'): 0x2192, - ('-', 'v'): 0x2193, - ('<', '>'): 0x2194, - ('U', 'D'): 0x2195, - ('<', '='): 0x21d0, - ('=', '>'): 0x21d2, - ('=', '='): 0x21d4, - ('F', 'A'): 0x2200, - ('d', 'P'): 0x2202, - ('T', 'E'): 0x2203, - ('/', '0'): 0x2205, - ('D', 'E'): 0x2206, - ('N', 'B'): 0x2207, - ('(', '-'): 0x2208, - ('-', ')'): 0x220b, - ('*', 'P'): 0x220f, - ('+', 'Z'): 0x2211, - ('-', '2'): 0x2212, - ('-', '+'): 0x2213, - ('*', '-'): 0x2217, - ('O', 'b'): 0x2218, - ('S', 'b'): 0x2219, - ('R', 'T'): 0x221a, - ('0', '('): 0x221d, - ('0', '0'): 0x221e, - ('-', 'L'): 0x221f, - ('-', 'V'): 0x2220, - ('P', 'P'): 0x2225, - ('A', 'N'): 0x2227, - ('O', 'R'): 0x2228, - ('(', 'U'): 0x2229, - (')', 'U'): 0x222a, - ('I', 'n'): 0x222b, - ('D', 'I'): 0x222c, - ('I', 'o'): 0x222e, - ('.', ':'): 0x2234, - (':', '.'): 0x2235, - (':', 'R'): 0x2236, - (':', ':'): 0x2237, - ('?', '1'): 0x223c, - ('C', 'G'): 0x223e, - ('?', '-'): 0x2243, - ('?', '='): 0x2245, - ('?', '2'): 0x2248, - ('=', '?'): 0x224c, - ('H', 'I'): 0x2253, - ('!', '='): 0x2260, - ('=', '3'): 0x2261, - ('=', '<'): 0x2264, - ('>', '='): 0x2265, - ('<', '*'): 0x226a, - ('*', '>'): 0x226b, - ('!', '<'): 0x226e, - ('!', '>'): 0x226f, - ('(', 'C'): 0x2282, - (')', 'C'): 0x2283, - ('(', '_'): 0x2286, - (')', '_'): 0x2287, - ('0', '.'): 0x2299, - ('0', '2'): 0x229a, - ('-', 'T'): 0x22a5, - ('.', 'P'): 0x22c5, - (':', '3'): 0x22ee, - ('.', '3'): 0x22ef, - ('E', 'h'): 0x2302, - ('<', '7'): 0x2308, - ('>', '7'): 0x2309, - ('7', '<'): 0x230a, - ('7', '>'): 0x230b, - ('N', 'I'): 0x2310, - ('(', 'A'): 0x2312, - ('T', 'R'): 0x2315, - ('I', 'u'): 0x2320, - ('I', 'l'): 0x2321, - ('<', '/'): 0x2329, - ('/', '>'): 0x232a, - ('V', 's'): 0x2423, - ('1', 'h'): 0x2440, - ('3', 'h'): 0x2441, - ('2', 'h'): 0x2442, - ('4', 'h'): 0x2443, - ('1', 'j'): 0x2446, - ('2', 'j'): 0x2447, - ('3', 'j'): 0x2448, - ('4', 'j'): 0x2449, - ('1', '.'): 0x2488, - ('2', '.'): 0x2489, - ('3', '.'): 0x248a, - ('4', '.'): 0x248b, - ('5', '.'): 0x248c, - ('6', '.'): 0x248d, - ('7', '.'): 0x248e, - ('8', '.'): 0x248f, - ('9', '.'): 0x2490, - ('h', 'h'): 0x2500, - ('H', 'H'): 0x2501, - ('v', 'v'): 0x2502, - ('V', 'V'): 0x2503, - ('3', '-'): 0x2504, - ('3', '_'): 0x2505, - ('3', '!'): 0x2506, - ('3', '/'): 0x2507, - ('4', '-'): 0x2508, - ('4', '_'): 0x2509, - ('4', '!'): 0x250a, - ('4', '/'): 0x250b, - ('d', 'r'): 0x250c, - ('d', 'R'): 0x250d, - ('D', 'r'): 0x250e, - ('D', 'R'): 0x250f, - ('d', 'l'): 0x2510, - ('d', 'L'): 0x2511, - ('D', 'l'): 0x2512, - ('L', 'D'): 0x2513, - ('u', 'r'): 0x2514, - ('u', 'R'): 0x2515, - ('U', 'r'): 0x2516, - ('U', 'R'): 0x2517, - ('u', 'l'): 0x2518, - ('u', 'L'): 0x2519, - ('U', 'l'): 0x251a, - ('U', 'L'): 0x251b, - ('v', 'r'): 0x251c, - ('v', 'R'): 0x251d, - ('V', 'r'): 0x2520, - ('V', 'R'): 0x2523, - ('v', 'l'): 0x2524, - ('v', 'L'): 0x2525, - ('V', 'l'): 0x2528, - ('V', 'L'): 0x252b, - ('d', 'h'): 0x252c, - ('d', 'H'): 0x252f, - ('D', 'h'): 0x2530, - ('D', 'H'): 0x2533, - ('u', 'h'): 0x2534, - ('u', 'H'): 0x2537, - ('U', 'h'): 0x2538, - ('U', 'H'): 0x253b, - ('v', 'h'): 0x253c, - ('v', 'H'): 0x253f, - ('V', 'h'): 0x2542, - ('V', 'H'): 0x254b, - ('F', 'D'): 0x2571, - ('B', 'D'): 0x2572, - ('T', 'B'): 0x2580, - ('L', 'B'): 0x2584, - ('F', 'B'): 0x2588, - ('l', 'B'): 0x258c, - ('R', 'B'): 0x2590, - ('.', 'S'): 0x2591, - (':', 'S'): 0x2592, - ('?', 'S'): 0x2593, - ('f', 'S'): 0x25a0, - ('O', 'S'): 0x25a1, - ('R', 'O'): 0x25a2, - ('R', 'r'): 0x25a3, - ('R', 'F'): 0x25a4, - ('R', 'Y'): 0x25a5, - ('R', 'H'): 0x25a6, - ('R', 'Z'): 0x25a7, - ('R', 'K'): 0x25a8, - ('R', 'X'): 0x25a9, - ('s', 'B'): 0x25aa, - ('S', 'R'): 0x25ac, - ('O', 'r'): 0x25ad, - ('U', 'T'): 0x25b2, - ('u', 'T'): 0x25b3, - ('P', 'R'): 0x25b6, - ('T', 'r'): 0x25b7, - ('D', 't'): 0x25bc, - ('d', 'T'): 0x25bd, - ('P', 'L'): 0x25c0, - ('T', 'l'): 0x25c1, - ('D', 'b'): 0x25c6, - ('D', 'w'): 0x25c7, - ('L', 'Z'): 0x25ca, - ('0', 'm'): 0x25cb, - ('0', 'o'): 0x25ce, - ('0', 'M'): 0x25cf, - ('0', 'L'): 0x25d0, - ('0', 'R'): 0x25d1, - ('S', 'n'): 0x25d8, - ('I', 'c'): 0x25d9, - ('F', 'd'): 0x25e2, - ('B', 'd'): 0x25e3, - ('*', '2'): 0x2605, - ('*', '1'): 0x2606, - ('<', 'H'): 0x261c, - ('>', 'H'): 0x261e, - ('0', 'u'): 0x263a, - ('0', 'U'): 0x263b, - ('S', 'U'): 0x263c, - ('F', 'm'): 0x2640, - ('M', 'l'): 0x2642, - ('c', 'S'): 0x2660, - ('c', 'H'): 0x2661, - ('c', 'D'): 0x2662, - ('c', 'C'): 0x2663, - ('M', 'd'): 0x2669, - ('M', '8'): 0x266a, - ('M', '2'): 0x266b, - ('M', 'b'): 0x266d, - ('M', 'x'): 0x266e, - ('M', 'X'): 0x266f, - ('O', 'K'): 0x2713, - ('X', 'X'): 0x2717, - ('-', 'X'): 0x2720, - ('I', 'S'): 0x3000, - (',', '_'): 0x3001, - ('.', '_'): 0x3002, - ('+', '"'): 0x3003, - ('+', '_'): 0x3004, - ('*', '_'): 0x3005, - (';', '_'): 0x3006, - ('0', '_'): 0x3007, - ('<', '+'): 0x300a, - ('>', '+'): 0x300b, - ('<', '\''): 0x300c, - ('>', '\''): 0x300d, - ('<', '"'): 0x300e, - ('>', '"'): 0x300f, - ('(', '"'): 0x3010, - (')', '"'): 0x3011, - ('=', 'T'): 0x3012, - ('=', '_'): 0x3013, - ('(', '\''): 0x3014, - (')', '\''): 0x3015, - ('(', 'I'): 0x3016, - (')', 'I'): 0x3017, - ('-', '?'): 0x301c, - ('A', '5'): 0x3041, - ('a', '5'): 0x3042, - ('I', '5'): 0x3043, - ('i', '5'): 0x3044, - ('U', '5'): 0x3045, - ('u', '5'): 0x3046, - ('E', '5'): 0x3047, - ('e', '5'): 0x3048, - ('O', '5'): 0x3049, - ('o', '5'): 0x304a, - ('k', 'a'): 0x304b, - ('g', 'a'): 0x304c, - ('k', 'i'): 0x304d, - ('g', 'i'): 0x304e, - ('k', 'u'): 0x304f, - ('g', 'u'): 0x3050, - ('k', 'e'): 0x3051, - ('g', 'e'): 0x3052, - ('k', 'o'): 0x3053, - ('g', 'o'): 0x3054, - ('s', 'a'): 0x3055, - ('z', 'a'): 0x3056, - ('s', 'i'): 0x3057, - ('z', 'i'): 0x3058, - ('s', 'u'): 0x3059, - ('z', 'u'): 0x305a, - ('s', 'e'): 0x305b, - ('z', 'e'): 0x305c, - ('s', 'o'): 0x305d, - ('z', 'o'): 0x305e, - ('t', 'a'): 0x305f, - ('d', 'a'): 0x3060, - ('t', 'i'): 0x3061, - ('d', 'i'): 0x3062, - ('t', 'U'): 0x3063, - ('t', 'u'): 0x3064, - ('d', 'u'): 0x3065, - ('t', 'e'): 0x3066, - ('d', 'e'): 0x3067, - ('t', 'o'): 0x3068, - ('d', 'o'): 0x3069, - ('n', 'a'): 0x306a, - ('n', 'i'): 0x306b, - ('n', 'u'): 0x306c, - ('n', 'e'): 0x306d, - ('n', 'o'): 0x306e, - ('h', 'a'): 0x306f, - ('b', 'a'): 0x3070, - ('p', 'a'): 0x3071, - ('h', 'i'): 0x3072, - ('b', 'i'): 0x3073, - ('p', 'i'): 0x3074, - ('h', 'u'): 0x3075, - ('b', 'u'): 0x3076, - ('p', 'u'): 0x3077, - ('h', 'e'): 0x3078, - ('b', 'e'): 0x3079, - ('p', 'e'): 0x307a, - ('h', 'o'): 0x307b, - ('b', 'o'): 0x307c, - ('p', 'o'): 0x307d, - ('m', 'a'): 0x307e, - ('m', 'i'): 0x307f, - ('m', 'u'): 0x3080, - ('m', 'e'): 0x3081, - ('m', 'o'): 0x3082, - ('y', 'A'): 0x3083, - ('y', 'a'): 0x3084, - ('y', 'U'): 0x3085, - ('y', 'u'): 0x3086, - ('y', 'O'): 0x3087, - ('y', 'o'): 0x3088, - ('r', 'a'): 0x3089, - ('r', 'i'): 0x308a, - ('r', 'u'): 0x308b, - ('r', 'e'): 0x308c, - ('r', 'o'): 0x308d, - ('w', 'A'): 0x308e, - ('w', 'a'): 0x308f, - ('w', 'i'): 0x3090, - ('w', 'e'): 0x3091, - ('w', 'o'): 0x3092, - ('n', '5'): 0x3093, - ('v', 'u'): 0x3094, - ('"', '5'): 0x309b, - ('0', '5'): 0x309c, - ('*', '5'): 0x309d, - ('+', '5'): 0x309e, - ('a', '6'): 0x30a1, - ('A', '6'): 0x30a2, - ('i', '6'): 0x30a3, - ('I', '6'): 0x30a4, - ('u', '6'): 0x30a5, - ('U', '6'): 0x30a6, - ('e', '6'): 0x30a7, - ('E', '6'): 0x30a8, - ('o', '6'): 0x30a9, - ('O', '6'): 0x30aa, - ('K', 'a'): 0x30ab, - ('G', 'a'): 0x30ac, - ('K', 'i'): 0x30ad, - ('G', 'i'): 0x30ae, - ('K', 'u'): 0x30af, - ('G', 'u'): 0x30b0, - ('K', 'e'): 0x30b1, - ('G', 'e'): 0x30b2, - ('K', 'o'): 0x30b3, - ('G', 'o'): 0x30b4, - ('S', 'a'): 0x30b5, - ('Z', 'a'): 0x30b6, - ('S', 'i'): 0x30b7, - ('Z', 'i'): 0x30b8, - ('S', 'u'): 0x30b9, - ('Z', 'u'): 0x30ba, - ('S', 'e'): 0x30bb, - ('Z', 'e'): 0x30bc, - ('S', 'o'): 0x30bd, - ('Z', 'o'): 0x30be, - ('T', 'a'): 0x30bf, - ('D', 'a'): 0x30c0, - ('T', 'i'): 0x30c1, - ('D', 'i'): 0x30c2, - ('T', 'U'): 0x30c3, - ('T', 'u'): 0x30c4, - ('D', 'u'): 0x30c5, - ('T', 'e'): 0x30c6, - ('D', 'e'): 0x30c7, - ('T', 'o'): 0x30c8, - ('D', 'o'): 0x30c9, - ('N', 'a'): 0x30ca, - ('N', 'i'): 0x30cb, - ('N', 'u'): 0x30cc, - ('N', 'e'): 0x30cd, - ('N', 'o'): 0x30ce, - ('H', 'a'): 0x30cf, - ('B', 'a'): 0x30d0, - ('P', 'a'): 0x30d1, - ('H', 'i'): 0x30d2, - ('B', 'i'): 0x30d3, - ('P', 'i'): 0x30d4, - ('H', 'u'): 0x30d5, - ('B', 'u'): 0x30d6, - ('P', 'u'): 0x30d7, - ('H', 'e'): 0x30d8, - ('B', 'e'): 0x30d9, - ('P', 'e'): 0x30da, - ('H', 'o'): 0x30db, - ('B', 'o'): 0x30dc, - ('P', 'o'): 0x30dd, - ('M', 'a'): 0x30de, - ('M', 'i'): 0x30df, - ('M', 'u'): 0x30e0, - ('M', 'e'): 0x30e1, - ('M', 'o'): 0x30e2, - ('Y', 'A'): 0x30e3, - ('Y', 'a'): 0x30e4, - ('Y', 'U'): 0x30e5, - ('Y', 'u'): 0x30e6, - ('Y', 'O'): 0x30e7, - ('Y', 'o'): 0x30e8, - ('R', 'a'): 0x30e9, - ('R', 'i'): 0x30ea, - ('R', 'u'): 0x30eb, - ('R', 'e'): 0x30ec, - ('R', 'o'): 0x30ed, - ('W', 'A'): 0x30ee, - ('W', 'a'): 0x30ef, - ('W', 'i'): 0x30f0, - ('W', 'e'): 0x30f1, - ('W', 'o'): 0x30f2, - ('N', '6'): 0x30f3, - ('V', 'u'): 0x30f4, - ('K', 'A'): 0x30f5, - ('K', 'E'): 0x30f6, - ('V', 'a'): 0x30f7, - ('V', 'i'): 0x30f8, - ('V', 'e'): 0x30f9, - ('V', 'o'): 0x30fa, - ('.', '6'): 0x30fb, - ('-', '6'): 0x30fc, - ('*', '6'): 0x30fd, - ('+', '6'): 0x30fe, - ('b', '4'): 0x3105, - ('p', '4'): 0x3106, - ('m', '4'): 0x3107, - ('f', '4'): 0x3108, - ('d', '4'): 0x3109, - ('t', '4'): 0x310a, - ('n', '4'): 0x310b, - ('l', '4'): 0x310c, - ('g', '4'): 0x310d, - ('k', '4'): 0x310e, - ('h', '4'): 0x310f, - ('j', '4'): 0x3110, - ('q', '4'): 0x3111, - ('x', '4'): 0x3112, - ('z', 'h'): 0x3113, - ('c', 'h'): 0x3114, - ('s', 'h'): 0x3115, - ('r', '4'): 0x3116, - ('z', '4'): 0x3117, - ('c', '4'): 0x3118, - ('s', '4'): 0x3119, - ('a', '4'): 0x311a, - ('o', '4'): 0x311b, - ('e', '4'): 0x311c, - ('a', 'i'): 0x311e, - ('e', 'i'): 0x311f, - ('a', 'u'): 0x3120, - ('o', 'u'): 0x3121, - ('a', 'n'): 0x3122, - ('e', 'n'): 0x3123, - ('a', 'N'): 0x3124, - ('e', 'N'): 0x3125, - ('e', 'r'): 0x3126, - ('i', '4'): 0x3127, - ('u', '4'): 0x3128, - ('i', 'u'): 0x3129, - ('v', '4'): 0x312a, - ('n', 'G'): 0x312b, - ('g', 'n'): 0x312c, - ('1', 'c'): 0x3220, - ('2', 'c'): 0x3221, - ('3', 'c'): 0x3222, - ('4', 'c'): 0x3223, - ('5', 'c'): 0x3224, - ('6', 'c'): 0x3225, - ('7', 'c'): 0x3226, - ('8', 'c'): 0x3227, - ('9', 'c'): 0x3228, - - # code points 0xe000 - 0xefff excluded, they have no assigned - # characters, only used in proposals. - ('f', 'f'): 0xfb00, - ('f', 'i'): 0xfb01, - ('f', 'l'): 0xfb02, - ('f', 't'): 0xfb05, - ('s', 't'): 0xfb06, - - # Vim 5.x compatible digraphs that don't conflict with the above - ('~', '!'): 161, - ('c', '|'): 162, - ('$', '$'): 163, - ('o', 'x'): 164, # currency symbol in ISO 8859-1 - ('Y', '-'): 165, - ('|', '|'): 166, - ('c', 'O'): 169, - ('-', ','): 172, - ('-', '='): 175, - ('~', 'o'): 176, - ('2', '2'): 178, - ('3', '3'): 179, - ('p', 'p'): 182, - ('~', '.'): 183, - ('1', '1'): 185, - ('~', '?'): 191, - ('A', '`'): 192, - ('A', '^'): 194, - ('A', '~'): 195, - ('A', '"'): 196, - ('A', '@'): 197, - ('E', '`'): 200, - ('E', '^'): 202, - ('E', '"'): 203, - ('I', '`'): 204, - ('I', '^'): 206, - ('I', '"'): 207, - ('N', '~'): 209, - ('O', '`'): 210, - ('O', '^'): 212, - ('O', '~'): 213, - ('/', '\\'): 215, # multiplication symbol in ISO 8859-1 - ('U', '`'): 217, - ('U', '^'): 219, - ('I', 'p'): 222, - ('a', '`'): 224, - ('a', '^'): 226, - ('a', '~'): 227, - ('a', '"'): 228, - ('a', '@'): 229, - ('e', '`'): 232, - ('e', '^'): 234, - ('e', '"'): 235, - ('i', '`'): 236, - ('i', '^'): 238, - ('n', '~'): 241, - ('o', '`'): 242, - ('o', '^'): 244, - ('o', '~'): 245, - ('u', '`'): 249, - ('u', '^'): 251, - ('y', '"'): 255, -} diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/input_processor.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/input_processor.py deleted file mode 100644 index 51a3110827a..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/input_processor.py +++ /dev/null @@ -1,372 +0,0 @@ -# *** encoding: utf-8 *** -""" -An :class:`~.InputProcessor` receives callbacks for the keystrokes parsed from -the input in the :class:`~prompt_toolkit.inputstream.InputStream` instance. - -The `InputProcessor` will according to the implemented keybindings call the -correct callbacks when new key presses are feed through `feed`. -""" -from __future__ import unicode_literals -from prompt_toolkit.buffer import EditReadOnlyBuffer -from prompt_toolkit.filters.cli import ViNavigationMode -from prompt_toolkit.keys import Keys, Key -from prompt_toolkit.utils import Event - -from .registry import BaseRegistry - -from collections import deque -from six.moves import range -import weakref -import six - -__all__ = ( - 'InputProcessor', - 'KeyPress', -) - - -class KeyPress(object): - """ - :param key: A `Keys` instance or text (one character). - :param data: The received string on stdin. (Often vt100 escape codes.) - """ - def __init__(self, key, data=None): - assert isinstance(key, (six.text_type, Key)) - assert data is None or isinstance(data, six.text_type) - - if data is None: - data = key.name if isinstance(key, Key) else key - - self.key = key - self.data = data - - def __repr__(self): - return '%s(key=%r, data=%r)' % ( - self.__class__.__name__, self.key, self.data) - - def __eq__(self, other): - return self.key == other.key and self.data == other.data - - -class InputProcessor(object): - """ - Statemachine that receives :class:`KeyPress` instances and according to the - key bindings in the given :class:`Registry`, calls the matching handlers. - - :: - - p = InputProcessor(registry) - - # Send keys into the processor. - p.feed(KeyPress(Keys.ControlX, '\x18')) - p.feed(KeyPress(Keys.ControlC, '\x03') - - # Process all the keys in the queue. - p.process_keys() - - # Now the ControlX-ControlC callback will be called if this sequence is - # registered in the registry. - - :param registry: `BaseRegistry` instance. - :param cli_ref: weakref to `CommandLineInterface`. - """ - def __init__(self, registry, cli_ref): - assert isinstance(registry, BaseRegistry) - - self._registry = registry - self._cli_ref = cli_ref - - self.beforeKeyPress = Event(self) - self.afterKeyPress = Event(self) - - # The queue of keys not yet send to our _process generator/state machine. - self.input_queue = deque() - - # The key buffer that is matched in the generator state machine. - # (This is at at most the amount of keys that make up for one key binding.) - self.key_buffer = [] - - # Simple macro recording. (Like readline does.) - self.record_macro = False - self.macro = [] - - self.reset() - - def reset(self): - self._previous_key_sequence = [] - self._previous_handler = None - - self._process_coroutine = self._process() - self._process_coroutine.send(None) - - #: Readline argument (for repetition of commands.) - #: https://www.gnu.org/software/bash/manual/html_node/Readline-Arguments.html - self.arg = None - - def start_macro(self): - " Start recording macro. " - self.record_macro = True - self.macro = [] - - def end_macro(self): - " End recording macro. " - self.record_macro = False - - def call_macro(self): - for k in self.macro: - self.feed(k) - - def _get_matches(self, key_presses): - """ - For a list of :class:`KeyPress` instances. Give the matching handlers - that would handle this. - """ - keys = tuple(k.key for k in key_presses) - cli = self._cli_ref() - - # Try match, with mode flag - return [b for b in self._registry.get_bindings_for_keys(keys) if b.filter(cli)] - - def _is_prefix_of_longer_match(self, key_presses): - """ - For a list of :class:`KeyPress` instances. Return True if there is any - handler that is bound to a suffix of this keys. - """ - keys = tuple(k.key for k in key_presses) - cli = self._cli_ref() - - # Get the filters for all the key bindings that have a longer match. - # Note that we transform it into a `set`, because we don't care about - # the actual bindings and executing it more than once doesn't make - # sense. (Many key bindings share the same filter.) - filters = set(b.filter for b in self._registry.get_bindings_starting_with_keys(keys)) - - # When any key binding is active, return True. - return any(f(cli) for f in filters) - - def _process(self): - """ - Coroutine implementing the key match algorithm. Key strokes are sent - into this generator, and it calls the appropriate handlers. - """ - buffer = self.key_buffer - retry = False - - while True: - if retry: - retry = False - else: - buffer.append((yield)) - - # If we have some key presses, check for matches. - if buffer: - is_prefix_of_longer_match = self._is_prefix_of_longer_match(buffer) - matches = self._get_matches(buffer) - - # When eager matches were found, give priority to them and also - # ignore all the longer matches. - eager_matches = [m for m in matches if m.eager(self._cli_ref())] - - if eager_matches: - matches = eager_matches - is_prefix_of_longer_match = False - - # Exact matches found, call handler. - if not is_prefix_of_longer_match and matches: - self._call_handler(matches[-1], key_sequence=buffer[:]) - del buffer[:] # Keep reference. - - # No match found. - elif not is_prefix_of_longer_match and not matches: - retry = True - found = False - - # Loop over the input, try longest match first and shift. - for i in range(len(buffer), 0, -1): - matches = self._get_matches(buffer[:i]) - if matches: - self._call_handler(matches[-1], key_sequence=buffer[:i]) - del buffer[:i] - found = True - break - - if not found: - del buffer[:1] - - def feed(self, key_press): - """ - Add a new :class:`KeyPress` to the input queue. - (Don't forget to call `process_keys` in order to process the queue.) - """ - assert isinstance(key_press, KeyPress) - self.input_queue.append(key_press) - - def process_keys(self): - """ - Process all the keys in the `input_queue`. - (To be called after `feed`.) - - Note: because of the `feed`/`process_keys` separation, it is - possible to call `feed` from inside a key binding. - This function keeps looping until the queue is empty. - """ - while self.input_queue: - key_press = self.input_queue.popleft() - - if key_press.key != Keys.CPRResponse: - self.beforeKeyPress.fire() - - self._process_coroutine.send(key_press) - - if key_press.key != Keys.CPRResponse: - self.afterKeyPress.fire() - - # Invalidate user interface. - cli = self._cli_ref() - if cli: - cli.invalidate() - - def _call_handler(self, handler, key_sequence=None): - was_recording = self.record_macro - arg = self.arg - self.arg = None - - event = KeyPressEvent( - weakref.ref(self), arg=arg, key_sequence=key_sequence, - previous_key_sequence=self._previous_key_sequence, - is_repeat=(handler == self._previous_handler)) - - # Save the state of the current buffer. - cli = event.cli # Can be `None` (In unit-tests only.) - - if handler.save_before(event) and cli: - cli.current_buffer.save_to_undo_stack() - - # Call handler. - try: - handler.call(event) - self._fix_vi_cursor_position(event) - - except EditReadOnlyBuffer: - # When a key binding does an attempt to change a buffer which is - # read-only, we can just silently ignore that. - pass - - self._previous_key_sequence = key_sequence - self._previous_handler = handler - - # Record the key sequence in our macro. (Only if we're in macro mode - # before and after executing the key.) - if self.record_macro and was_recording: - self.macro.extend(key_sequence) - - def _fix_vi_cursor_position(self, event): - """ - After every command, make sure that if we are in Vi navigation mode, we - never put the cursor after the last character of a line. (Unless it's - an empty line.) - """ - cli = self._cli_ref() - if cli: - buff = cli.current_buffer - preferred_column = buff.preferred_column - - if (ViNavigationMode()(event.cli) and - buff.document.is_cursor_at_the_end_of_line and - len(buff.document.current_line) > 0): - buff.cursor_position -= 1 - - # Set the preferred_column for arrow up/down again. - # (This was cleared after changing the cursor position.) - buff.preferred_column = preferred_column - - - -class KeyPressEvent(object): - """ - Key press event, delivered to key bindings. - - :param input_processor_ref: Weak reference to the `InputProcessor`. - :param arg: Repetition argument. - :param key_sequence: List of `KeyPress` instances. - :param previouskey_sequence: Previous list of `KeyPress` instances. - :param is_repeat: True when the previous event was delivered to the same handler. - """ - def __init__(self, input_processor_ref, arg=None, key_sequence=None, - previous_key_sequence=None, is_repeat=False): - self._input_processor_ref = input_processor_ref - self.key_sequence = key_sequence - self.previous_key_sequence = previous_key_sequence - - #: True when the previous key sequence was handled by the same handler. - self.is_repeat = is_repeat - - self._arg = arg - - def __repr__(self): - return 'KeyPressEvent(arg=%r, key_sequence=%r, is_repeat=%r)' % ( - self.arg, self.key_sequence, self.is_repeat) - - @property - def data(self): - return self.key_sequence[-1].data - - @property - def input_processor(self): - return self._input_processor_ref() - - @property - def cli(self): - """ - Command line interface. - """ - return self.input_processor._cli_ref() - - @property - def current_buffer(self): - """ - The current buffer. - """ - return self.cli.current_buffer - - @property - def arg(self): - """ - Repetition argument. - """ - if self._arg == '-': - return -1 - - result = int(self._arg or 1) - - # Don't exceed a million. - if int(result) >= 1000000: - result = 1 - - return result - - @property - def arg_present(self): - """ - True if repetition argument was explicitly provided. - """ - return self._arg is not None - - def append_to_arg_count(self, data): - """ - Add digit to the input argument. - - :param data: the typed digit as string - """ - assert data in '-0123456789' - current = self._arg - - if data == '-': - assert current is None or current == '-' - result = data - elif current is None: - result = data - else: - result = "%s%s" % (current, data) - - self.input_processor.arg = result diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/manager.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/manager.py deleted file mode 100644 index 83612c2a5cc..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/manager.py +++ /dev/null @@ -1,96 +0,0 @@ -""" -DEPRECATED: -Use `prompt_toolkit.key_binding.defaults.load_key_bindings` instead. - -:class:`KeyBindingManager` is a utility (or shortcut) for loading all the key -bindings in a key binding registry, with a logic set of filters to quickly to -quickly change from Vi to Emacs key bindings at runtime. - -You don't have to use this, but it's practical. - -Usage:: - - manager = KeyBindingManager() - app = Application(key_bindings_registry=manager.registry) -""" -from __future__ import unicode_literals -from .defaults import load_key_bindings -from prompt_toolkit.filters import to_cli_filter -from prompt_toolkit.key_binding.registry import Registry, ConditionalRegistry, MergedRegistry - -__all__ = ( - 'KeyBindingManager', -) - - -class KeyBindingManager(object): - """ - Utility for loading all key bindings into memory. - - :param registry: Optional `Registry` instance. - :param enable_abort_and_exit_bindings: Filter to enable Ctrl-C and Ctrl-D. - :param enable_system_bindings: Filter to enable the system bindings - (meta-! prompt and Control-Z suspension.) - :param enable_search: Filter to enable the search bindings. - :param enable_open_in_editor: Filter to enable open-in-editor. - :param enable_open_in_editor: Filter to enable open-in-editor. - :param enable_extra_page_navigation: Filter for enabling extra page navigation. - (Bindings for up/down scrolling through long pages, like in Emacs or Vi.) - :param enable_auto_suggest_bindings: Filter to enable fish-style suggestions. - - :param enable_vi_mode: Deprecated! - """ - def __init__(self, - registry=None, # XXX: not used anymore. - enable_vi_mode=None, # (`enable_vi_mode` is deprecated.) - enable_all=True, # - get_search_state=None, - enable_abort_and_exit_bindings=False, - enable_system_bindings=False, - enable_search=False, - enable_open_in_editor=False, - enable_extra_page_navigation=False, - enable_auto_suggest_bindings=False): - - assert registry is None or isinstance(registry, Registry) - assert get_search_state is None or callable(get_search_state) - enable_all = to_cli_filter(enable_all) - - defaults = load_key_bindings( - get_search_state=get_search_state, - enable_abort_and_exit_bindings=enable_abort_and_exit_bindings, - enable_system_bindings=enable_system_bindings, - enable_search=enable_search, - enable_open_in_editor=enable_open_in_editor, - enable_extra_page_navigation=enable_extra_page_navigation, - enable_auto_suggest_bindings=enable_auto_suggest_bindings) - - # Note, we wrap this whole thing again in a MergedRegistry, because we - # don't want the `enable_all` settings to apply on items that were - # added to the registry as a whole. - self.registry = MergedRegistry([ - ConditionalRegistry(defaults, enable_all) - ]) - - @classmethod - def for_prompt(cls, **kw): - """ - Create a ``KeyBindingManager`` with the defaults for an input prompt. - This activates the key bindings for abort/exit (Ctrl-C/Ctrl-D), - incremental search and auto suggestions. - - (Not for full screen applications.) - """ - kw.setdefault('enable_abort_and_exit_bindings', True) - kw.setdefault('enable_search', True) - kw.setdefault('enable_auto_suggest_bindings', True) - - return cls(**kw) - - def reset(self, cli): - # For backwards compatibility. - pass - - def get_vi_state(self, cli): - # Deprecated! - return cli.vi_state diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/registry.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/registry.py deleted file mode 100644 index 24d0e729a1b..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/registry.py +++ /dev/null @@ -1,350 +0,0 @@ -""" -Key bindings registry. - -A `Registry` object is a container that holds a list of key bindings. It has a -very efficient internal data structure for checking which key bindings apply -for a pressed key. - -Typical usage:: - - r = Registry() - - @r.add_binding(Keys.ControlX, Keys.ControlC, filter=INSERT) - def handler(event): - # Handle ControlX-ControlC key sequence. - pass - - -It is also possible to combine multiple registries. We do this in the default -key bindings. There are some registries that contain Emacs bindings, while -others contain the Vi bindings. They are merged together using a -`MergedRegistry`. - -We also have a `ConditionalRegistry` object that can enable/disable a group of -key bindings at once. -""" -from __future__ import unicode_literals -from abc import ABCMeta, abstractmethod - -from prompt_toolkit.cache import SimpleCache -from prompt_toolkit.filters import CLIFilter, to_cli_filter, Never -from prompt_toolkit.keys import Key, Keys - -from six import text_type, with_metaclass - -__all__ = ( - 'BaseRegistry', - 'Registry', - 'ConditionalRegistry', - 'MergedRegistry', -) - - -class _Binding(object): - """ - (Immutable binding class.) - """ - def __init__(self, keys, handler, filter=None, eager=None, save_before=None): - assert isinstance(keys, tuple) - assert callable(handler) - assert isinstance(filter, CLIFilter) - assert isinstance(eager, CLIFilter) - assert callable(save_before) - - self.keys = keys - self.handler = handler - self.filter = filter - self.eager = eager - self.save_before = save_before - - def call(self, event): - return self.handler(event) - - def __repr__(self): - return '%s(keys=%r, handler=%r)' % ( - self.__class__.__name__, self.keys, self.handler) - - -class BaseRegistry(with_metaclass(ABCMeta, object)): - """ - Interface for a Registry. - """ - _version = 0 # For cache invalidation. - - @abstractmethod - def get_bindings_for_keys(self, keys): - pass - - @abstractmethod - def get_bindings_starting_with_keys(self, keys): - pass - - # `add_binding` and `remove_binding` don't have to be part of this - # interface. - - -class Registry(BaseRegistry): - """ - Key binding registry. - """ - def __init__(self): - self.key_bindings = [] - self._get_bindings_for_keys_cache = SimpleCache(maxsize=10000) - self._get_bindings_starting_with_keys_cache = SimpleCache(maxsize=1000) - self._version = 0 # For cache invalidation. - - def _clear_cache(self): - self._version += 1 - self._get_bindings_for_keys_cache.clear() - self._get_bindings_starting_with_keys_cache.clear() - - def add_binding(self, *keys, **kwargs): - """ - Decorator for annotating key bindings. - - :param filter: :class:`~prompt_toolkit.filters.CLIFilter` to determine - when this key binding is active. - :param eager: :class:`~prompt_toolkit.filters.CLIFilter` or `bool`. - When True, ignore potential longer matches when this key binding is - hit. E.g. when there is an active eager key binding for Ctrl-X, - execute the handler immediately and ignore the key binding for - Ctrl-X Ctrl-E of which it is a prefix. - :param save_before: Callable that takes an `Event` and returns True if - we should save the current buffer, before handling the event. - (That's the default.) - """ - filter = to_cli_filter(kwargs.pop('filter', True)) - eager = to_cli_filter(kwargs.pop('eager', False)) - save_before = kwargs.pop('save_before', lambda e: True) - to_cli_filter(kwargs.pop('invalidate_ui', True)) # Deprecated! (ignored.) - - assert not kwargs - assert keys - assert all(isinstance(k, (Key, text_type)) for k in keys), \ - 'Key bindings should consist of Key and string (unicode) instances.' - assert callable(save_before) - - if isinstance(filter, Never): - # When a filter is Never, it will always stay disabled, so in that case - # don't bother putting it in the registry. It will slow down every key - # press otherwise. - def decorator(func): - return func - else: - def decorator(func): - self.key_bindings.append( - _Binding(keys, func, filter=filter, eager=eager, - save_before=save_before)) - self._clear_cache() - - return func - return decorator - - def remove_binding(self, function): - """ - Remove a key binding. - - This expects a function that was given to `add_binding` method as - parameter. Raises `ValueError` when the given function was not - registered before. - """ - assert callable(function) - - for b in self.key_bindings: - if b.handler == function: - self.key_bindings.remove(b) - self._clear_cache() - return - - # No key binding found for this function. Raise ValueError. - raise ValueError('Binding not found: %r' % (function, )) - - def get_bindings_for_keys(self, keys): - """ - Return a list of key bindings that can handle this key. - (This return also inactive bindings, so the `filter` still has to be - called, for checking it.) - - :param keys: tuple of keys. - """ - def get(): - result = [] - for b in self.key_bindings: - if len(keys) == len(b.keys): - match = True - any_count = 0 - - for i, j in zip(b.keys, keys): - if i != j and i != Keys.Any: - match = False - break - - if i == Keys.Any: - any_count += 1 - - if match: - result.append((any_count, b)) - - # Place bindings that have more 'Any' occurences in them at the end. - result = sorted(result, key=lambda item: -item[0]) - - return [item[1] for item in result] - - return self._get_bindings_for_keys_cache.get(keys, get) - - def get_bindings_starting_with_keys(self, keys): - """ - Return a list of key bindings that handle a key sequence starting with - `keys`. (It does only return bindings for which the sequences are - longer than `keys`. And like `get_bindings_for_keys`, it also includes - inactive bindings.) - - :param keys: tuple of keys. - """ - def get(): - result = [] - for b in self.key_bindings: - if len(keys) < len(b.keys): - match = True - for i, j in zip(b.keys, keys): - if i != j and i != Keys.Any: - match = False - break - if match: - result.append(b) - return result - - return self._get_bindings_starting_with_keys_cache.get(keys, get) - - -class _AddRemoveMixin(BaseRegistry): - """ - Common part for ConditionalRegistry and MergedRegistry. - """ - def __init__(self): - # `Registry` to be synchronized with all the others. - self._registry2 = Registry() - self._last_version = None - - # The 'extra' registry. Mostly for backwards compatibility. - self._extra_registry = Registry() - - def _update_cache(self): - raise NotImplementedError - - # For backwards, compatibility, we allow adding bindings to both - # ConditionalRegistry and MergedRegistry. This is however not the - # recommended way. Better is to create a new registry and merge them - # together using MergedRegistry. - - def add_binding(self, *k, **kw): - return self._extra_registry.add_binding(*k, **kw) - - def remove_binding(self, *k, **kw): - return self._extra_registry.remove_binding(*k, **kw) - - # Proxy methods to self._registry2. - - @property - def key_bindings(self): - self._update_cache() - return self._registry2.key_bindings - - @property - def _version(self): - self._update_cache() - return self._last_version - - def get_bindings_for_keys(self, *a, **kw): - self._update_cache() - return self._registry2.get_bindings_for_keys(*a, **kw) - - def get_bindings_starting_with_keys(self, *a, **kw): - self._update_cache() - return self._registry2.get_bindings_starting_with_keys(*a, **kw) - - -class ConditionalRegistry(_AddRemoveMixin): - """ - Wraps around a `Registry`. Disable/enable all the key bindings according to - the given (additional) filter.:: - - @Condition - def setting_is_true(cli): - return True # or False - - registy = ConditionalRegistry(registry, setting_is_true) - - When new key bindings are added to this object. They are also - enable/disabled according to the given `filter`. - - :param registries: List of `Registry` objects. - :param filter: `CLIFilter` object. - """ - def __init__(self, registry=None, filter=True): - registry = registry or Registry() - assert isinstance(registry, BaseRegistry) - - _AddRemoveMixin.__init__(self) - - self.registry = registry - self.filter = to_cli_filter(filter) - - def _update_cache(self): - " If the original registry was changed. Update our copy version. " - expected_version = (self.registry._version, self._extra_registry._version) - - if self._last_version != expected_version: - registry2 = Registry() - - # Copy all bindings from `self.registry`, adding our condition. - for reg in (self.registry, self._extra_registry): - for b in reg.key_bindings: - registry2.key_bindings.append( - _Binding( - keys=b.keys, - handler=b.handler, - filter=self.filter & b.filter, - eager=b.eager, - save_before=b.save_before)) - - self._registry2 = registry2 - self._last_version = expected_version - - -class MergedRegistry(_AddRemoveMixin): - """ - Merge multiple registries of key bindings into one. - - This class acts as a proxy to multiple `Registry` objects, but behaves as - if this is just one bigger `Registry`. - - :param registries: List of `Registry` objects. - """ - def __init__(self, registries): - assert all(isinstance(r, BaseRegistry) for r in registries) - - _AddRemoveMixin.__init__(self) - - self.registries = registries - - def _update_cache(self): - """ - If one of the original registries was changed. Update our merged - version. - """ - expected_version = ( - tuple(r._version for r in self.registries) + - (self._extra_registry._version, )) - - if self._last_version != expected_version: - registry2 = Registry() - - for reg in self.registries: - registry2.key_bindings.extend(reg.key_bindings) - - # Copy all bindings from `self._extra_registry`. - registry2.key_bindings.extend(self._extra_registry.key_bindings) - - self._registry2 = registry2 - self._last_version = expected_version diff --git a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/vi_state.py b/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/vi_state.py deleted file mode 100644 index 92ce3cbd292..00000000000 --- a/contrib/python/prompt-toolkit/py2/prompt_toolkit/key_binding/vi_state.py +++ /dev/null @@ -1,61 +0,0 @@ -from __future__ import unicode_literals - -__all__ = ( - 'InputMode', - 'CharacterFind', - 'ViState', -) - - -class InputMode(object): - INSERT = 'vi-insert' - INSERT_MULTIPLE = 'vi-insert-multiple' - NAVIGATION = 'vi-navigation' - REPLACE = 'vi-replace' - - -class CharacterFind(object): - def __init__(self, character, backwards=False): - self.character = character - self.backwards = backwards - - -class ViState(object): - """ - Mutable class to hold the state of the Vi navigation. - """ - def __init__(self): - #: None or CharacterFind instance. (This is used to repeat the last - #: search in Vi mode, by pressing the 'n' or 'N' in navigation mode.) - self.last_character_find = None - - # When an operator is given and we are waiting for text object, - # -- e.g. in the case of 'dw', after the 'd' --, an operator callback - # is set here. - self.operator_func = None - self.operator_arg = None - - #: Named registers. Maps register name (e.g. 'a') to - #: :class:`ClipboardData` instances. - self.named_registers = {} - - #: The Vi mode we're currently in to. - self.input_mode = InputMode.INSERT - - #: Waiting for digraph. - self.waiting_for_digraph = False - self.digraph_symbol1 = None # (None or a symbol.) - - #: When true, make ~ act as an operator. - self.tilde_operator = False - - def reset(self, mode=InputMode.INSERT): - """ - Reset state, go back to the given mode. INSERT by default. - """ - # Go back to insert mode. - self.input_mode = mode - - self.waiting_for_digraph = False - self.operator_func = None - self.operator_arg = None |