ai-station/.venv/lib/python3.12/site-packages/textual/_ansi_sequences.py

438 lines
18 KiB
Python
Raw Permalink Normal View History

2025-12-25 14:54:33 +00:00
from __future__ import annotations
from typing import Mapping, Tuple
from typing_extensions import Final
from textual.keys import Keys
class IgnoredSequence:
"""Class used to mark that a sequence should be ignored."""
IGNORE_SEQUENCE: Final[IgnoredSequence] = IgnoredSequence()
"""Constant to indicate that a sequence should be ignored."""
# Mapping of vt100 escape codes to Keys.
ANSI_SEQUENCES_KEYS: Mapping[str, Tuple[Keys, ...] | str | IgnoredSequence] = {
# Control keys.
" ": (Keys.Space,),
"\r": (Keys.Enter,),
"\x00": (Keys.ControlAt,), # Control-At (Also for Ctrl-Space)
"\x01": (Keys.ControlA,), # Control-A (home)
"\x02": (Keys.ControlB,), # Control-B (emacs cursor left)
"\x03": (Keys.ControlC,), # Control-C (interrupt)
"\x04": (Keys.ControlD,), # Control-D (exit)
"\x05": (Keys.ControlE,), # Control-E (end)
"\x06": (Keys.ControlF,), # Control-F (cursor forward)
"\x07": (Keys.ControlG,), # Control-G
"\x08": (Keys.Backspace,), # Control-H (8) (Identical to '\b')
"\x09": (Keys.Tab,), # Control-I (9) (Identical to '\t')
"\x0a": (Keys.ControlJ,), # Control-J (10) (Identical to '\n')
"\x0b": (Keys.ControlK,), # Control-K (delete until end of line; vertical tab)
"\x0c": (Keys.ControlL,), # Control-L (clear; form feed)
# "\x0d": (Keys.ControlM,), # Control-M (13) (Identical to '\r')
"\x0e": (Keys.ControlN,), # Control-N (14) (history forward)
"\x0f": (Keys.ControlO,), # Control-O (15)
"\x10": (Keys.ControlP,), # Control-P (16) (history back)
"\x11": (Keys.ControlQ,), # Control-Q
"\x12": (Keys.ControlR,), # Control-R (18) (reverse search)
"\x13": (Keys.ControlS,), # Control-S (19) (forward search)
"\x14": (Keys.ControlT,), # Control-T
"\x15": (Keys.ControlU,), # Control-U
"\x16": (Keys.ControlV,), # Control-V
"\x17": (Keys.ControlW,), # Control-W
"\x18": (Keys.ControlX,), # Control-X
"\x19": (Keys.ControlY,), # Control-Y (25)
"\x1a": (Keys.ControlZ,), # Control-Z
"\x1b": (Keys.Escape,), # Also Control-[
"\x1b\x1b": (
Keys.Escape,
), # Windows issues esc esc for a single press of escape key
"\x9b": (Keys.ShiftEscape,),
"\x1c": (Keys.ControlBackslash,), # Both Control-\ (also Ctrl-| )
"\x1d": (Keys.ControlSquareClose,), # Control-]
"\x1e": (Keys.ControlCircumflex,), # Control-^
"\x1f": (Keys.ControlUnderscore,), # Control-underscore (Also for Ctrl-hyphen.)
# ASCII Delete (0x7f)
# Vt220 (and Linux terminal) send this when pressing backspace. We map this
# to ControlH, because that will make it easier to create key bindings that
# work everywhere, with the trade-off that it's no longer possible to
# handle backspace and control-h individually for the few terminals that
# support it. (Most terminals send ControlH when backspace is pressed.)
# See: http://www.ibb.net/~anne/keyboard.html
"\x7f": (Keys.Backspace,),
"\x1b\x7f": (Keys.ControlW,),
# Various
"\x1b[1~": (Keys.Home,), # tmux
"\x1b[2~": (Keys.Insert,),
"\x1b[3~": (Keys.Delete,),
"\x1b[4~": (Keys.End,), # tmux
"\x1b[5~": (Keys.PageUp,),
"\x1b[6~": (Keys.PageDown,),
"\x1b[7~": (Keys.Home,), # xrvt
"\x1b[8~": (Keys.End,), # xrvt
"\x1b[Z": (Keys.BackTab,), # shift + tab
"\x1b\x09": (Keys.BackTab,), # Linux console
"\x1b[~": (Keys.BackTab,), # Windows console
# --
# Function keys.
"\x1bOP": (Keys.F1,),
"\x1bOQ": (Keys.F2,),
"\x1bOR": (Keys.F3,),
"\x1bOS": (Keys.F4,),
"\x1b[[A": (Keys.F1,), # Linux console.
"\x1b[[B": (Keys.F2,), # Linux console.
"\x1b[[C": (Keys.F3,), # Linux console.
"\x1b[[D": (Keys.F4,), # Linux console.
"\x1b[[E": (Keys.F5,), # Linux console.
"\x1b[11~": (Keys.F1,), # rxvt-unicode
"\x1b[12~": (Keys.F2,), # rxvt-unicode
"\x1b[13~": (Keys.F3,), # rxvt-unicode
"\x1b[14~": (Keys.F4,), # rxvt-unicode
"\x1b[15~": (Keys.F5,),
"\x1b[17~": (Keys.F6,),
"\x1b[18~": (Keys.F7,),
"\x1b[19~": (Keys.F8,),
"\x1b[20~": (Keys.F9,),
"\x1b[21~": (Keys.F10,),
"\x1b[23~": (Keys.F11,),
"\x1b[24~": (Keys.F12,),
"\x1b[25~": (Keys.F13,),
"\x1b[26~": (Keys.F14,),
"\x1b[28~": (Keys.F15,),
"\x1b[29~": (Keys.F16,),
"\x1b[31~": (Keys.F17,),
"\x1b[32~": (Keys.F18,),
"\x1b[33~": (Keys.F19,),
"\x1b[34~": (Keys.F20,),
# Xterm
"\x1b[1;2P": (Keys.F13,),
"\x1b[1;2Q": (Keys.F14,),
"\x1b[1;2R": (
Keys.F15,
), # Conflicts with CPR response; enabled after https://github.com/Textualize/textual/issues/3440.
"\x1b[1;2S": (Keys.F16,),
"\x1b[15;2~": (Keys.F17,),
"\x1b[17;2~": (Keys.F18,),
"\x1b[18;2~": (Keys.F19,),
"\x1b[19;2~": (Keys.F20,),
"\x1b[20;2~": (Keys.F21,),
"\x1b[21;2~": (Keys.F22,),
"\x1b[23;2~": (Keys.F23,),
"\x1b[24;2~": (Keys.F24,),
"\x1b[23$": (Keys.F23,), # rxvt
"\x1b[24$": (Keys.F24,), # rxvt
# --
# Control + function keys.
"\x1b[1;5P": (Keys.ControlF1,),
"\x1b[1;5Q": (Keys.ControlF2,),
"\x1b[1;5R": (
Keys.ControlF3,
), # Conflicts with CPR response; enabled after https://github.com/Textualize/textual/issues/3440.
"\x1b[1;5S": (Keys.ControlF4,),
"\x1b[15;5~": (Keys.ControlF5,),
"\x1b[17;5~": (Keys.ControlF6,),
"\x1b[18;5~": (Keys.ControlF7,),
"\x1b[19;5~": (Keys.ControlF8,),
"\x1b[20;5~": (Keys.ControlF9,),
"\x1b[21;5~": (Keys.ControlF10,),
"\x1b[23;5~": (Keys.ControlF11,),
"\x1b[24;5~": (Keys.ControlF12,),
"\x1b[1;6P": (Keys.ControlF13,),
"\x1b[1;6Q": (Keys.ControlF14,),
"\x1b[1;6R": (
Keys.ControlF15,
), # Conflicts with CPR response; enabled after https://github.com/Textualize/textual/issues/3440.
"\x1b[1;6S": (Keys.ControlF16,),
"\x1b[15;6~": (Keys.ControlF17,),
"\x1b[17;6~": (Keys.ControlF18,),
"\x1b[18;6~": (Keys.ControlF19,),
"\x1b[19;6~": (Keys.ControlF20,),
"\x1b[20;6~": (Keys.ControlF21,),
"\x1b[21;6~": (Keys.ControlF22,),
"\x1b[23;6~": (Keys.ControlF23,),
"\x1b[24;6~": (Keys.ControlF24,),
# rxvt-unicode control function keys:
"\x1b[11^": (Keys.ControlF1,),
"\x1b[12^": (Keys.ControlF2,),
"\x1b[13^": (Keys.ControlF3,),
"\x1b[14^": (Keys.ControlF4,),
"\x1b[15^": (Keys.ControlF5,),
"\x1b[17^": (Keys.ControlF6,),
"\x1b[18^": (Keys.ControlF7,),
"\x1b[19^": (Keys.ControlF8,),
"\x1b[20^": (Keys.ControlF9,),
"\x1b[21^": (Keys.ControlF10,),
"\x1b[23^": (Keys.ControlF11,),
"\x1b[24^": (Keys.ControlF12,),
# rxvt-unicode control+shift function keys:
"\x1b[25^": (Keys.ControlF13,),
"\x1b[26^": (Keys.ControlF14,),
"\x1b[28^": (Keys.ControlF15,),
"\x1b[29^": (Keys.ControlF16,),
"\x1b[31^": (Keys.ControlF17,),
"\x1b[32^": (Keys.ControlF18,),
"\x1b[33^": (Keys.ControlF19,),
"\x1b[34^": (Keys.ControlF20,),
"\x1b[23@": (Keys.ControlF21,),
"\x1b[24@": (Keys.ControlF22,),
# --
# Tmux (Win32 subsystem) sends the following scroll events.
"\x1b[62~": (Keys.ScrollUp,),
"\x1b[63~": (Keys.ScrollDown,),
# Meta/control/escape + pageup/pagedown/insert/delete.
"\x1b[3;2~": (Keys.ShiftDelete,), # xterm, gnome-terminal.
"\x1b[3$": (Keys.ShiftDelete,), # rxvt
"\x1b[5;2~": (Keys.ShiftPageUp,),
"\x1b[6;2~": (Keys.ShiftPageDown,),
"\x1b[2;3~": (Keys.Escape, Keys.Insert),
"\x1b[3;3~": (Keys.Escape, Keys.Delete),
"\x1b[5;3~": (Keys.Escape, Keys.PageUp),
"\x1b[6;3~": (Keys.Escape, Keys.PageDown),
"\x1b[2;4~": (Keys.Escape, Keys.ShiftInsert),
"\x1b[3;4~": (Keys.Escape, Keys.ShiftDelete),
"\x1b[5;4~": (Keys.Escape, Keys.ShiftPageUp),
"\x1b[6;4~": (Keys.Escape, Keys.ShiftPageDown),
"\x1b[3;5~": (Keys.ControlDelete,), # xterm, gnome-terminal.
"\x1b[3^": (Keys.ControlDelete,), # rxvt
"\x1b[5;5~": (Keys.ControlPageUp,),
"\x1b[6;5~": (Keys.ControlPageDown,),
"\x1b[5^": (Keys.ControlPageUp,), # rxvt
"\x1b[6^": (Keys.ControlPageDown,), # rxvt
"\x1b[3;6~": (Keys.ControlShiftDelete,),
"\x1b[5;6~": (Keys.ControlShiftPageUp,),
"\x1b[6;6~": (Keys.ControlShiftPageDown,),
"\x1b[2;7~": (Keys.Escape, Keys.ControlInsert),
"\x1b[5;7~": (Keys.Escape, Keys.ControlPageDown),
"\x1b[6;7~": (Keys.Escape, Keys.ControlPageDown),
"\x1b[2;8~": (Keys.Escape, Keys.ControlShiftInsert),
"\x1b[5;8~": (Keys.Escape, Keys.ControlShiftPageDown),
"\x1b[6;8~": (Keys.Escape, Keys.ControlShiftPageDown),
# --
# Arrows.
# (Normal cursor mode).
"\x1b[A": (Keys.Up,),
"\x1b[B": (Keys.Down,),
"\x1b[C": (Keys.Right,),
"\x1b[D": (Keys.Left,),
"\x1b[H": (Keys.Home,),
"\x1b[F": (Keys.End,),
# Tmux sends following keystrokes when control+arrow is pressed, but for
# Emacs ansi-term sends the same sequences for normal arrow keys. Consider
# it a normal arrow press, because that's more important.
# (Application cursor mode).
"\x1bOA": (Keys.Up,),
"\x1bOB": (Keys.Down,),
"\x1bOC": (Keys.Right,),
"\x1bOD": (Keys.Left,),
"\x1bOF": (Keys.End,),
"\x1bOH": (Keys.Home,),
# Shift + arrows.
"\x1b[1;2A": (Keys.ShiftUp,),
"\x1b[1;2B": (Keys.ShiftDown,),
"\x1b[1;2C": (Keys.ShiftRight,),
"\x1b[1;2D": (Keys.ShiftLeft,),
"\x1b[1;2F": (Keys.ShiftEnd,),
"\x1b[1;2H": (Keys.ShiftHome,),
# Shift+navigation in rxvt
"\x1b[a": (Keys.ShiftUp,),
"\x1b[b": (Keys.ShiftDown,),
"\x1b[c": (Keys.ShiftRight,),
"\x1b[d": (Keys.ShiftLeft,),
"\x1b[7$": (Keys.ShiftHome,),
"\x1b[8$": (Keys.ShiftEnd,),
# Meta + arrow keys. Several terminals handle this differently.
# The following sequences are for xterm and gnome-terminal.
# (Iterm sends ESC followed by the normal arrow_up/down/left/right
# sequences, and the OSX Terminal sends ESCb and ESCf for "alt
# arrow_left" and "alt arrow_right." We don't handle these
# explicitly, in here, because would could not distinguish between
# pressing ESC (to go to Vi navigation mode), followed by just the
# 'b' or 'f' key. These combinations are handled in
# the input processor.)
"\x1b[1;3A": (Keys.Escape, Keys.Up),
"\x1b[1;3B": (Keys.Escape, Keys.Down),
"\x1b[1;3C": (Keys.Escape, Keys.Right),
"\x1b[1;3D": (Keys.Escape, Keys.Left),
"\x1b[1;3F": (Keys.Escape, Keys.End),
"\x1b[1;3H": (Keys.Escape, Keys.Home),
# Alt+shift+number.
"\x1b[1;4A": (Keys.Escape, Keys.ShiftUp),
"\x1b[1;4B": (Keys.Escape, Keys.ShiftDown),
"\x1b[1;4C": (Keys.Escape, Keys.ShiftRight),
"\x1b[1;4D": (Keys.Escape, Keys.ShiftLeft),
"\x1b[1;4F": (Keys.Escape, Keys.ShiftEnd),
"\x1b[1;4H": (Keys.Escape, Keys.ShiftHome),
# Control + arrows.
"\x1b[1;5A": (Keys.ControlUp,), # Cursor Mode
"\x1b[1;5B": (Keys.ControlDown,), # Cursor Mode
"\x1b[1;5C": (Keys.ControlRight,), # Cursor Mode
"\x1b[1;5D": (Keys.ControlLeft,), # Cursor Mode
"\x1bf": (Keys.ControlRight,), # iTerm natural editing keys
"\x1bb": (Keys.ControlLeft,), # iTerm natural editing keys
"\x1b[1;5F": (Keys.ControlEnd,),
"\x1b[1;5H": (Keys.ControlHome,),
# rxvt
"\x1b[7^": (Keys.ControlEnd,),
"\x1b[8^": (Keys.ControlHome,),
# Tmux sends following keystrokes when control+arrow is pressed, but for
# Emacs ansi-term sends the same sequences for normal arrow keys. Consider
# it a normal arrow press, because that's more important.
"\x1b[5A": (Keys.ControlUp,),
"\x1b[5B": (Keys.ControlDown,),
"\x1b[5C": (Keys.ControlRight,),
"\x1b[5D": (Keys.ControlLeft,),
# Control arrow keys in rxvt
"\x1bOa": (Keys.ControlUp,),
"\x1bOb": (Keys.ControlUp,),
"\x1bOc": (Keys.ControlRight,),
"\x1bOd": (Keys.ControlLeft,),
# Control + shift + arrows.
"\x1b[1;6A": (Keys.ControlShiftUp,),
"\x1b[1;6B": (Keys.ControlShiftDown,),
"\x1b[1;6C": (Keys.ControlShiftRight,),
"\x1b[1;6D": (Keys.ControlShiftLeft,),
"\x1b[1;6F": (Keys.ControlShiftEnd,),
"\x1b[1;6H": (Keys.ControlShiftHome,),
# Control + Meta + arrows.
"\x1b[1;7A": (Keys.Escape, Keys.ControlUp),
"\x1b[1;7B": (Keys.Escape, Keys.ControlDown),
"\x1b[1;7C": (Keys.Escape, Keys.ControlRight),
"\x1b[1;7D": (Keys.Escape, Keys.ControlLeft),
"\x1b[1;7F": (Keys.Escape, Keys.ControlEnd),
"\x1b[1;7H": (Keys.Escape, Keys.ControlHome),
# Meta + Shift + arrows.
"\x1b[1;8A": (Keys.Escape, Keys.ControlShiftUp),
"\x1b[1;8B": (Keys.Escape, Keys.ControlShiftDown),
"\x1b[1;8C": (Keys.Escape, Keys.ControlShiftRight),
"\x1b[1;8D": (Keys.Escape, Keys.ControlShiftLeft),
"\x1b[1;8F": (Keys.Escape, Keys.ControlShiftEnd),
"\x1b[1;8H": (Keys.Escape, Keys.ControlShiftHome),
# Meta + arrow on (some?) Macs when using iTerm defaults (see issue #483).
"\x1b[1;9A": (Keys.Escape, Keys.Up),
"\x1b[1;9B": (Keys.Escape, Keys.Down),
"\x1b[1;9C": (Keys.Escape, Keys.Right),
"\x1b[1;9D": (Keys.Escape, Keys.Left),
# --
# Control/shift/meta + number in mintty.
# (c-2 will actually send c-@ and c-6 will send c-^.)
"\x1b[1;5p": (Keys.Control0,),
"\x1b[1;5q": (Keys.Control1,),
"\x1b[1;5r": (Keys.Control2,),
"\x1b[1;5s": (Keys.Control3,),
"\x1b[1;5t": (Keys.Control4,),
"\x1b[1;5u": (Keys.Control5,),
"\x1b[1;5v": (Keys.Control6,),
"\x1b[1;5w": (Keys.Control7,),
"\x1b[1;5x": (Keys.Control8,),
"\x1b[1;5y": (Keys.Control9,),
"\x1b[1;6p": (Keys.ControlShift0,),
"\x1b[1;6q": (Keys.ControlShift1,),
"\x1b[1;6r": (Keys.ControlShift2,),
"\x1b[1;6s": (Keys.ControlShift3,),
"\x1b[1;6t": (Keys.ControlShift4,),
"\x1b[1;6u": (Keys.ControlShift5,),
"\x1b[1;6v": (Keys.ControlShift6,),
"\x1b[1;6w": (Keys.ControlShift7,),
"\x1b[1;6x": (Keys.ControlShift8,),
"\x1b[1;6y": (Keys.ControlShift9,),
"\x1b[1;7p": (Keys.Escape, Keys.Control0),
"\x1b[1;7q": (Keys.Escape, Keys.Control1),
"\x1b[1;7r": (Keys.Escape, Keys.Control2),
"\x1b[1;7s": (Keys.Escape, Keys.Control3),
"\x1b[1;7t": (Keys.Escape, Keys.Control4),
"\x1b[1;7u": (Keys.Escape, Keys.Control5),
"\x1b[1;7v": (Keys.Escape, Keys.Control6),
"\x1b[1;7w": (Keys.Escape, Keys.Control7),
"\x1b[1;7x": (Keys.Escape, Keys.Control8),
"\x1b[1;7y": (Keys.Escape, Keys.Control9),
"\x1b[1;8p": (Keys.Escape, Keys.ControlShift0),
"\x1b[1;8q": (Keys.Escape, Keys.ControlShift1),
"\x1b[1;8r": (Keys.Escape, Keys.ControlShift2),
"\x1b[1;8s": (Keys.Escape, Keys.ControlShift3),
"\x1b[1;8t": (Keys.Escape, Keys.ControlShift4),
"\x1b[1;8u": (Keys.Escape, Keys.ControlShift5),
"\x1b[1;8v": (Keys.Escape, Keys.ControlShift6),
"\x1b[1;8w": (Keys.Escape, Keys.ControlShift7),
"\x1b[1;8x": (Keys.Escape, Keys.ControlShift8),
"\x1b[1;8y": (Keys.Escape, Keys.ControlShift9),
# Simplify some sequences that appear to be unique to rxvt; see
# https://github.com/Textualize/textual/issues/3741 for context.
"\x1bOj": "*",
"\x1bOk": "+",
"\x1bOm": "-",
"\x1bOn": ".",
"\x1bOo": "/",
"\x1bOp": "0",
"\x1bOq": "1",
"\x1bOr": "2",
"\x1bOs": "3",
"\x1bOt": "4",
"\x1bOu": "5",
"\x1bOv": "6",
"\x1bOw": "7",
"\x1bOx": "8",
"\x1bOy": "9",
"\x1bOM": (Keys.Enter,),
# WezTerm on macOS emits sequences for Opt and keys on the top numeric
# row; whereas other terminals provide various characters. The following
# swallow up those sequences and turns them into characters the same as
# the other terminals.
"\x1b§": "§",
"\x1b1": "¡",
"\x1b2": "",
"\x1b3": "£",
"\x1b4": "¢",
"\x1b5": "",
"\x1b6": "§",
"\x1b7": "",
"\x1b8": "",
"\x1b9": "ª",
"\x1b0": "º",
"\x1b-": "",
"\x1b=": "",
# Ctrl+§ on kitty is different from most other terminals on macOS.
"\x1b[167;5u": "0",
############################################################################
# The ignore section. Only add sequences here if they are going to be
# ignored. Also, when adding a sequence here, please include a note as
# to why it is being ignored; ideally citing sources if possible.
############################################################################
# The following 2 are inherited from prompt toolkit. They relate to a
# press of 5 on the numeric keypad, when *not* in number mode.
"\x1b[E": IGNORE_SEQUENCE, # Xterm.
"\x1b[G": IGNORE_SEQUENCE, # Linux console.
# Various ctrl+cmd+ keys under Kitty on macOS.
"\x1b[3;13~": IGNORE_SEQUENCE, # ctrl-cmd-del
"\x1b[1;13H": IGNORE_SEQUENCE, # ctrl-cmd-home
"\x1b[1;13F": IGNORE_SEQUENCE, # ctrl-cmd-end
"\x1b[5;13~": IGNORE_SEQUENCE, # ctrl-cmd-pgup
"\x1b[6;13~": IGNORE_SEQUENCE, # ctrl-cmd-pgdn
"\x1b[49;13u": IGNORE_SEQUENCE, # ctrl-cmd-1
"\x1b[50;13u": IGNORE_SEQUENCE, # ctrl-cmd-2
"\x1b[51;13u": IGNORE_SEQUENCE, # ctrl-cmd-3
"\x1b[52;13u": IGNORE_SEQUENCE, # ctrl-cmd-4
"\x1b[53;13u": IGNORE_SEQUENCE, # ctrl-cmd-5
"\x1b[54;13u": IGNORE_SEQUENCE, # ctrl-cmd-6
"\x1b[55;13u": IGNORE_SEQUENCE, # ctrl-cmd-7
"\x1b[56;13u": IGNORE_SEQUENCE, # ctrl-cmd-8
"\x1b[57;13u": IGNORE_SEQUENCE, # ctrl-cmd-9
"\x1b[48;13u": IGNORE_SEQUENCE, # ctrl-cmd-0
"\x1b[45;13u": IGNORE_SEQUENCE, # ctrl-cmd--
"\x1b[61;13u": IGNORE_SEQUENCE, # ctrl-cmd-+
"\x1b[91;13u": IGNORE_SEQUENCE, # ctrl-cmd-[
"\x1b[93;13u": IGNORE_SEQUENCE, # ctrl-cmd-]
"\x1b[92;13u": IGNORE_SEQUENCE, # ctrl-cmd-\
"\x1b[39;13u": IGNORE_SEQUENCE, # ctrl-cmd-'
"\x1b[59;13u": IGNORE_SEQUENCE, # ctrl-cmd-;
"\x1b[47;13u": IGNORE_SEQUENCE, # ctrl-cmd-/
"\x1b[46;13u": IGNORE_SEQUENCE, # ctrl-cmd-.
}
# https://gist.github.com/christianparpart/d8a62cc1ab659194337d73e399004036
SYNC_START = "\x1b[?2026h"
SYNC_END = "\x1b[?2026l"