Implement DECCKM
This commit is contained in:
parent
bf3f6f6014
commit
142c883b0c
@ -282,7 +282,7 @@ class Boss(Thread):
|
|||||||
if window.screen.auto_repeat_enabled or action == GLFW_PRESS:
|
if window.screen.auto_repeat_enabled or action == GLFW_PRESS:
|
||||||
if window.char_grid.scrolled_by and key not in MODIFIER_KEYS:
|
if window.char_grid.scrolled_by and key not in MODIFIER_KEYS:
|
||||||
window.scroll_end()
|
window.scroll_end()
|
||||||
data = interpret_key_event(key, scancode, mods)
|
data = interpret_key_event(key, scancode, mods, window)
|
||||||
if data:
|
if data:
|
||||||
window.write_to_child(data)
|
window.write_to_child(data)
|
||||||
|
|
||||||
|
|||||||
@ -244,7 +244,7 @@ PyTypeObject ChangeTracker_Type;
|
|||||||
|
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
bool mLNM, mIRM, mDECTCEM, mDECSCNM, mDECOM, mDECAWM, mDECCOLM, mDECARM,
|
bool mLNM, mIRM, mDECTCEM, mDECSCNM, mDECOM, mDECAWM, mDECCOLM, mDECARM, mDECCKM,
|
||||||
mBRACKETED_PASTE, mFOCUS_TRACKING;
|
mBRACKETED_PASTE, mFOCUS_TRACKING;
|
||||||
unsigned long mouse_tracking_mode, mouse_tracking_protocol;
|
unsigned long mouse_tracking_mode, mouse_tracking_protocol;
|
||||||
} ScreenModes;
|
} ScreenModes;
|
||||||
|
|||||||
@ -5,7 +5,7 @@
|
|||||||
import kitty.fast_data_types as defines
|
import kitty.fast_data_types as defines
|
||||||
from .terminfo import key_as_bytes
|
from .terminfo import key_as_bytes
|
||||||
|
|
||||||
key_map = {
|
smkx_key_map = {
|
||||||
defines.GLFW_KEY_UP: 'kcuu1',
|
defines.GLFW_KEY_UP: 'kcuu1',
|
||||||
defines.GLFW_KEY_DOWN: 'kcud1',
|
defines.GLFW_KEY_DOWN: 'kcud1',
|
||||||
defines.GLFW_KEY_LEFT: 'kcub1',
|
defines.GLFW_KEY_LEFT: 'kcub1',
|
||||||
@ -17,16 +17,16 @@ key_map = {
|
|||||||
defines.GLFW_KEY_PAGE_UP: 'kpp',
|
defines.GLFW_KEY_PAGE_UP: 'kpp',
|
||||||
defines.GLFW_KEY_PAGE_DOWN: 'knp',
|
defines.GLFW_KEY_PAGE_DOWN: 'knp',
|
||||||
}
|
}
|
||||||
key_map = {k: key_as_bytes(v) for k, v in key_map.items()}
|
smkx_key_map = {k: key_as_bytes(v) for k, v in smkx_key_map.items()}
|
||||||
for f in range(1, 13):
|
for f in range(1, 13):
|
||||||
key_map[getattr(defines, 'GLFW_KEY_F{}'.format(f))] = key_as_bytes('kf{}'.format(f))
|
smkx_key_map[getattr(defines, 'GLFW_KEY_F{}'.format(f))] = key_as_bytes('kf{}'.format(f))
|
||||||
del f
|
del f
|
||||||
|
|
||||||
key_map[defines.GLFW_KEY_ESCAPE] = b'\033'
|
smkx_key_map[defines.GLFW_KEY_ESCAPE] = b'\033'
|
||||||
key_map[defines.GLFW_KEY_ENTER] = b'\r'
|
smkx_key_map[defines.GLFW_KEY_ENTER] = b'\r'
|
||||||
key_map[defines.GLFW_KEY_KP_ENTER] = b'\r'
|
smkx_key_map[defines.GLFW_KEY_KP_ENTER] = b'\r'
|
||||||
key_map[defines.GLFW_KEY_BACKSPACE] = key_as_bytes('kbs')
|
smkx_key_map[defines.GLFW_KEY_BACKSPACE] = key_as_bytes('kbs')
|
||||||
key_map[defines.GLFW_KEY_TAB] = b'\t'
|
smkx_key_map[defines.GLFW_KEY_TAB] = b'\t'
|
||||||
|
|
||||||
SHIFTED_KEYS = {
|
SHIFTED_KEYS = {
|
||||||
defines.GLFW_KEY_TAB: key_as_bytes('kcbt'),
|
defines.GLFW_KEY_TAB: key_as_bytes('kcbt'),
|
||||||
@ -49,6 +49,22 @@ control_codes[defines.GLFW_KEY_DELETE] = bytearray(key_as_bytes('kdch1').replace
|
|||||||
alt_codes = {k: (0x1b, k) for i, k in enumerate(range(defines.GLFW_KEY_SPACE, defines.GLFW_KEY_RIGHT_BRACKET + 1))}
|
alt_codes = {k: (0x1b, k) for i, k in enumerate(range(defines.GLFW_KEY_SPACE, defines.GLFW_KEY_RIGHT_BRACKET + 1))}
|
||||||
|
|
||||||
|
|
||||||
|
rmkx_key_map = smkx_key_map.copy()
|
||||||
|
rmkx_key_map.update({
|
||||||
|
defines.GLFW_KEY_UP: b'\033[A',
|
||||||
|
defines.GLFW_KEY_DOWN: b'\033[B',
|
||||||
|
defines.GLFW_KEY_LEFT: b'\033[D',
|
||||||
|
defines.GLFW_KEY_RIGHT: b'\033[C',
|
||||||
|
defines.GLFW_KEY_HOME: b'\033[H',
|
||||||
|
defines.GLFW_KEY_END: b'\033[F',
|
||||||
|
})
|
||||||
|
cursor_key_mode_map = {True: smkx_key_map, False: rmkx_key_map}
|
||||||
|
|
||||||
|
|
||||||
|
def get_key_map(screen):
|
||||||
|
return cursor_key_mode_map[screen.cursor_key_mode]
|
||||||
|
|
||||||
|
|
||||||
valid_localized_key_names = {
|
valid_localized_key_names = {
|
||||||
k: getattr(defines, 'GLFW_KEY_' + k) for k in 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'
|
k: getattr(defines, 'GLFW_KEY_' + k) for k in 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789'
|
||||||
}
|
}
|
||||||
@ -64,7 +80,7 @@ def get_localized_key(key, scancode):
|
|||||||
return valid_localized_key_names.get((name or '').upper(), key)
|
return valid_localized_key_names.get((name or '').upper(), key)
|
||||||
|
|
||||||
|
|
||||||
def interpret_key_event(key, scancode, mods):
|
def interpret_key_event(key, scancode, mods, window):
|
||||||
data = bytearray()
|
data = bytearray()
|
||||||
key = get_localized_key(key, scancode)
|
key = get_localized_key(key, scancode)
|
||||||
if mods == defines.GLFW_MOD_CONTROL and key in control_codes:
|
if mods == defines.GLFW_MOD_CONTROL and key in control_codes:
|
||||||
@ -74,6 +90,7 @@ def interpret_key_event(key, scancode, mods):
|
|||||||
# Map Alt+key to Esc-key
|
# Map Alt+key to Esc-key
|
||||||
data.extend(alt_codes[key])
|
data.extend(alt_codes[key])
|
||||||
else:
|
else:
|
||||||
|
key_map = get_key_map(window.screen)
|
||||||
x = key_map.get(key)
|
x = key_map.get(key)
|
||||||
if x is not None:
|
if x is not None:
|
||||||
if mods == defines.GLFW_MOD_SHIFT:
|
if mods == defines.GLFW_MOD_SHIFT:
|
||||||
|
|||||||
@ -12,7 +12,7 @@
|
|||||||
#include "modes.h"
|
#include "modes.h"
|
||||||
#include "wcwidth9.h"
|
#include "wcwidth9.h"
|
||||||
|
|
||||||
static const ScreenModes empty_modes = {0, .mDECAWM=true, .mDECTCEM=true, .mDECARM=true};
|
static const ScreenModes empty_modes = {0, .mDECAWM=true, .mDECTCEM=true, .mDECARM=true, .mDECCKM=true};
|
||||||
|
|
||||||
// Constructor/destructor {{{
|
// Constructor/destructor {{{
|
||||||
|
|
||||||
@ -404,10 +404,12 @@ set_mode_from_const(Screen *self, unsigned int mode, bool val) {
|
|||||||
MOUSE_MODE(MOUSE_SGR_MODE, mouse_tracking_protocol, SGR_PROTOCOL)
|
MOUSE_MODE(MOUSE_SGR_MODE, mouse_tracking_protocol, SGR_PROTOCOL)
|
||||||
MOUSE_MODE(MOUSE_URXVT_MODE, mouse_tracking_protocol, URXVT_PROTOCOL)
|
MOUSE_MODE(MOUSE_URXVT_MODE, mouse_tracking_protocol, URXVT_PROTOCOL)
|
||||||
|
|
||||||
case DECCKM:
|
|
||||||
case DECSCLM:
|
case DECSCLM:
|
||||||
case DECNRCM:
|
case DECNRCM:
|
||||||
break; // we ignore these modes
|
break; // we ignore these modes
|
||||||
|
case DECCKM:
|
||||||
|
self->modes.mDECCKM = val;
|
||||||
|
break;
|
||||||
case DECTCEM:
|
case DECTCEM:
|
||||||
self->modes.mDECTCEM = val;
|
self->modes.mDECTCEM = val;
|
||||||
tracker_cursor_changed(self->change_tracker);
|
tracker_cursor_changed(self->change_tracker);
|
||||||
@ -1047,6 +1049,7 @@ MODE_GETSET(in_bracketed_paste_mode, BRACKETED_PASTE)
|
|||||||
MODE_GETSET(focus_tracking_enabled, FOCUS_TRACKING)
|
MODE_GETSET(focus_tracking_enabled, FOCUS_TRACKING)
|
||||||
MODE_GETSET(auto_repeat_enabled, DECARM)
|
MODE_GETSET(auto_repeat_enabled, DECARM)
|
||||||
MODE_GETSET(cursor_visible, DECTCEM)
|
MODE_GETSET(cursor_visible, DECTCEM)
|
||||||
|
MODE_GETSET(cursor_key_mode, DECCKM)
|
||||||
|
|
||||||
static PyObject*
|
static PyObject*
|
||||||
mouse_tracking_mode(Screen *self) {
|
mouse_tracking_mode(Screen *self) {
|
||||||
@ -1250,6 +1253,7 @@ static PyGetSetDef getsetters[] = {
|
|||||||
GETSET(auto_repeat_enabled)
|
GETSET(auto_repeat_enabled)
|
||||||
GETSET(focus_tracking_enabled)
|
GETSET(focus_tracking_enabled)
|
||||||
GETSET(cursor_visible)
|
GETSET(cursor_visible)
|
||||||
|
GETSET(cursor_key_mode)
|
||||||
{NULL} /* Sentinel */
|
{NULL} /* Sentinel */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@ -92,15 +92,15 @@ string_capabilities = {
|
|||||||
# Make cursor appear normal
|
# Make cursor appear normal
|
||||||
'cnorm': r'\E[?12l\E[?25h',
|
'cnorm': r'\E[?12l\E[?25h',
|
||||||
# Carriage return
|
# Carriage return
|
||||||
'cr': r'^M',
|
'cr': r'^M', # CR (carriage return \r)
|
||||||
# Change scroll region
|
# Change scroll region
|
||||||
'csr': r'\E[%i%p1%d;%p2%dr',
|
'csr': r'\E[%i%p1%d;%p2%dr',
|
||||||
# Move cursor to the left by the specified amount
|
# Move cursor to the left by the specified amount
|
||||||
'cub': r'\E[%p1%dD',
|
'cub': r'\E[%p1%dD',
|
||||||
'cub1': r'^H',
|
'cub1': r'^H', # BS (backspace)
|
||||||
# Move cursor down specified number of lines
|
# Move cursor down specified number of lines
|
||||||
'cud': r'\E[%p1%dB',
|
'cud': r'\E[%p1%dB',
|
||||||
'cud1': r'^J',
|
'cud1': r'^J', # LF (line-feed \n)
|
||||||
# Move cursor to the right by the specified amount
|
# Move cursor to the right by the specified amount
|
||||||
'cuf': r'\E[%p1%dC',
|
'cuf': r'\E[%p1%dC',
|
||||||
'cuf1': r'\E[C',
|
'cuf1': r'\E[C',
|
||||||
@ -203,6 +203,8 @@ string_capabilities = {
|
|||||||
'rmcup': r'\E[?1049l',
|
'rmcup': r'\E[?1049l',
|
||||||
# Exit insert mode
|
# Exit insert mode
|
||||||
'rmir': r'\E[4l',
|
'rmir': r'\E[4l',
|
||||||
|
# Exit application keypad mode
|
||||||
|
'rmkx': r'\E[?1l',
|
||||||
# Exit standout mode
|
# Exit standout mode
|
||||||
'rmso': r'\E[27m',
|
'rmso': r'\E[27m',
|
||||||
# Exit underline mode
|
# Exit underline mode
|
||||||
@ -227,6 +229,8 @@ string_capabilities = {
|
|||||||
'smcup': r'\E[?1049h',
|
'smcup': r'\E[?1049h',
|
||||||
# Enster insert mode
|
# Enster insert mode
|
||||||
'smir': r'\E[4h',
|
'smir': r'\E[4h',
|
||||||
|
# Enter application keymap mode
|
||||||
|
'smkx': r'\E[?1h',
|
||||||
# Enter standout mode
|
# Enter standout mode
|
||||||
'smso': r'\E[7m',
|
'smso': r'\E[7m',
|
||||||
# Enter underline mode
|
# Enter underline mode
|
||||||
@ -373,6 +377,8 @@ termcap_aliases.update({
|
|||||||
'ZR': 'ritm',
|
'ZR': 'ritm',
|
||||||
'as': 'smacs',
|
'as': 'smacs',
|
||||||
'ae': 'rmacs',
|
'ae': 'rmacs',
|
||||||
|
'ks': 'smkx',
|
||||||
|
'ke': 'rmkx',
|
||||||
'#2': 'kHOM',
|
'#2': 'kHOM',
|
||||||
'#4': 'kLFT',
|
'#4': 'kLFT',
|
||||||
'*7': 'kEND',
|
'*7': 'kEND',
|
||||||
|
|||||||
@ -17,7 +17,7 @@ from .fast_data_types import (
|
|||||||
GLFW_MOUSE_BUTTON_5, ANY_MODE, MOTION_MODE, GLFW_KEY_LEFT_SHIFT,
|
GLFW_MOUSE_BUTTON_5, ANY_MODE, MOTION_MODE, GLFW_KEY_LEFT_SHIFT,
|
||||||
GLFW_KEY_RIGHT_SHIFT, GLFW_KEY_UP, GLFW_KEY_DOWN, GLFW_MOUSE_BUTTON_4
|
GLFW_KEY_RIGHT_SHIFT, GLFW_KEY_UP, GLFW_KEY_DOWN, GLFW_MOUSE_BUTTON_4
|
||||||
)
|
)
|
||||||
from .keys import key_map
|
from .keys import get_key_map
|
||||||
from .mouse import encode_mouse_event, PRESS, RELEASE, MOVE, DRAG
|
from .mouse import encode_mouse_event, PRESS, RELEASE, MOVE, DRAG
|
||||||
from .terminfo import get_capabilities
|
from .terminfo import get_capabilities
|
||||||
from .utils import sanitize_title, get_primary_selection, parse_color_set, safe_print
|
from .utils import sanitize_title, get_primary_selection, parse_color_set, safe_print
|
||||||
@ -254,7 +254,7 @@ class Window:
|
|||||||
if ev:
|
if ev:
|
||||||
self.write_to_child(ev)
|
self.write_to_child(ev)
|
||||||
else:
|
else:
|
||||||
k = key_map[GLFW_KEY_UP if upwards else GLFW_KEY_DOWN]
|
k = get_key_map(self.screen)[GLFW_KEY_UP if upwards else GLFW_KEY_DOWN]
|
||||||
self.write_to_child(k * abs(s))
|
self.write_to_child(k * abs(s))
|
||||||
|
|
||||||
def buf_toggled(self, is_main_linebuf):
|
def buf_toggled(self, is_main_linebuf):
|
||||||
|
|||||||
Binary file not shown.
@ -101,6 +101,7 @@ xterm-kitty|KovIdTTY,
|
|||||||
rmam=\E[?7l,
|
rmam=\E[?7l,
|
||||||
rmcup=\E[?1049l,
|
rmcup=\E[?1049l,
|
||||||
rmir=\E[4l,
|
rmir=\E[4l,
|
||||||
|
rmkx=\E[?1l,
|
||||||
rmso=\E[27m,
|
rmso=\E[27m,
|
||||||
rmul=\E[24m,
|
rmul=\E[24m,
|
||||||
rs1=\Ec,
|
rs1=\Ec,
|
||||||
@ -114,6 +115,7 @@ xterm-kitty|KovIdTTY,
|
|||||||
smam=\E[?7h,
|
smam=\E[?7h,
|
||||||
smcup=\E[?1049h,
|
smcup=\E[?1049h,
|
||||||
smir=\E[4h,
|
smir=\E[4h,
|
||||||
|
smkx=\E[?1h,
|
||||||
smso=\E[7m,
|
smso=\E[7m,
|
||||||
smul=\E[4m,
|
smul=\E[4m,
|
||||||
tbc=\E[3g,
|
tbc=\E[3g,
|
||||||
|
|||||||
Binary file not shown.
Loading…
x
Reference in New Issue
Block a user