mirror of
https://github.com/neovim/neovim.git
synced 2026-04-01 05:12:02 +00:00
fix(tui): use 0x7f as Backspace on Windows with VT input (#37679)
Problem: 0x08 is treated as Backspace instead of Ctrl-H on Windows.
Solution: Treat 0x7f as Backspace if VT input is enabled, so that 0x08
is treated as Ctrl-H.
Ref: https://github.com/microsoft/terminal/issues/4949
This commit is contained in:
@@ -132,6 +132,9 @@ void tinput_init(TermInput *input, Loop *loop, TerminfoEntry *ti)
|
||||
input->ttimeout = (bool)p_ttimeout;
|
||||
input->ttimeoutlen = p_ttm;
|
||||
|
||||
// setup input handle
|
||||
rstream_init_fd(loop, &input->read_stream, input->in_fd);
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(kitty_key_map_entry); i++) {
|
||||
pmap_put(int)(&kitty_key_map, kitty_key_map_entry[i].key, (ptr_t)kitty_key_map_entry[i].name);
|
||||
}
|
||||
@@ -145,9 +148,6 @@ void tinput_init(TermInput *input, Loop *loop, TerminfoEntry *ti)
|
||||
int curflags = termkey_get_canonflags(input->tk);
|
||||
termkey_set_canonflags(input->tk, curflags | TERMKEY_CANON_DELBS);
|
||||
|
||||
// setup input handle
|
||||
rstream_init_fd(loop, &input->read_stream, input->in_fd);
|
||||
|
||||
// initialize a timer handle for handling ESC with libtermkey
|
||||
uv_timer_init(&loop->uv, &input->timer_handle);
|
||||
input->timer_handle.data = input;
|
||||
|
||||
@@ -2515,19 +2515,29 @@ static void flush_buf(TUIData *tui)
|
||||
|
||||
/// Try to get "kbs" code from stty because "the terminfo kbs entry is extremely
|
||||
/// unreliable." (Vim, Bash, and tmux also do this.)
|
||||
/// On Windows, use 0x7f as Backspace if VT input has been enabled by stream_init().
|
||||
///
|
||||
/// @see tmux/tty-keys.c fe4e9470bb504357d073320f5d305b22663ee3fd
|
||||
/// @see https://bugzilla.redhat.com/show_bug.cgi?id=142659
|
||||
static const char *tui_get_stty_erase(int fd)
|
||||
/// @see https://github.com/microsoft/terminal/issues/4949
|
||||
static const char *tui_get_stty_erase(TermInput *input)
|
||||
{
|
||||
static char stty_erase[2] = { 0 };
|
||||
#if defined(HAVE_TERMIOS_H)
|
||||
struct termios t;
|
||||
if (tcgetattr(fd, &t) != -1) {
|
||||
if (tcgetattr(input->in_fd, &t) != -1) {
|
||||
stty_erase[0] = (char)t.c_cc[VERASE];
|
||||
stty_erase[1] = NUL;
|
||||
DLOG("stty/termios:erase=%s", stty_erase);
|
||||
}
|
||||
#elif defined(MSWIN)
|
||||
DWORD dwMode;
|
||||
if (((uv_handle_t *)&input->read_stream.s.uv)->type == UV_TTY
|
||||
&& GetConsoleMode(input->read_stream.s.uv.tty.handle, &dwMode)
|
||||
&& (dwMode & ENABLE_VIRTUAL_TERMINAL_INPUT)) {
|
||||
stty_erase[0] = '\x7f';
|
||||
stty_erase[1] = NUL;
|
||||
}
|
||||
#endif
|
||||
return stty_erase;
|
||||
}
|
||||
@@ -2539,7 +2549,7 @@ static const char *tui_tk_ti_getstr(const char *name, const char *value, void *d
|
||||
TermInput *input = data;
|
||||
static const char *stty_erase = NULL;
|
||||
if (stty_erase == NULL) {
|
||||
stty_erase = tui_get_stty_erase(input->in_fd);
|
||||
stty_erase = tui_get_stty_erase(input);
|
||||
}
|
||||
|
||||
if (strequal(name, "key_backspace")) {
|
||||
|
||||
@@ -2830,7 +2830,6 @@ describe('TUI', function()
|
||||
end)
|
||||
|
||||
it('<C-h> #10134', function()
|
||||
t.skip(is_os('win'), 'FIXME: does not work on Windows #36660')
|
||||
local screen = tt.setup_child_nvim({
|
||||
'--clean',
|
||||
'--cmd',
|
||||
|
||||
Reference in New Issue
Block a user