From e012046302beaa7bc3de74fd60b15fe652e1f227 Mon Sep 17 00:00:00 2001 From: nick black Date: Tue, 5 Oct 2021 08:27:42 -0400 Subject: [PATCH] [readline] handle left arrow in ncdirect_readline #2214 --- src/lib/direct.c | 30 +++++++++++++++++++++++++++--- src/lib/termdesc.c | 4 ++-- 2 files changed, 29 insertions(+), 5 deletions(-) diff --git a/src/lib/direct.c b/src/lib/direct.c index 1e84120b9..0f09efd3a 100644 --- a/src/lib/direct.c +++ b/src/lib/direct.c @@ -971,6 +971,7 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ if(fprintf(n->ttyfp, "%s", prompt) < 0){ return NULL; } + int dimx = ncdirect_dim_x(n); // FIXME what if we're reading from redirected input, not a terminal? int y, xstart; if(cursor_yx_get(n, u7, &y, &xstart)){ @@ -983,6 +984,7 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ if((str = malloc(wspace * sizeof(*str))) == NULL){ return NULL; } + int wpos = 0; // cursor location (single-dimensional) int wused = 0; // number used str[wused++] = L'\0'; ncinput ni; @@ -1007,6 +1009,11 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ str[wused - 2] = L'\0'; --wused; } + --wpos; + }else if(id == NCKEY_LEFT){ + if(wpos){ + --wpos; + } }else{ if(wspace - 1 < wused){ wspace += BUFSIZ; @@ -1017,9 +1024,17 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ } str = tmp; } - str[wused - 1] = id; - ++wused; - str[wused - 1] = L'\0'; + if(wpos < wused - 1){ + memmove(str + wpos + 1, str + wpos, (wused - wpos) * sizeof(*str)); + str[wpos] = id; + ++wused; + ++wpos; + }else{ + str[wused - 1] = id; + ++wused; + ++wpos; + str[wused - 1] = L'\0'; + } // FIXME check modifiers int x; if(cursor_yx_get(n, u7, &y, &x)){ @@ -1035,6 +1050,7 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ bline = y; } } + // clear to end of line(s) const char* el = get_escape(&n->tcache, ESCAPE_EL); for(int i = bline ; i >= tline ; --i){ if(ncdirect_cursor_move_yx(n, i, i > tline ? 0 : xstart)){ @@ -1047,6 +1063,14 @@ char* ncdirect_readline(ncdirect* n, const char* prompt){ if(fprintf(n->ttyfp, "%ls", str) < 0){ break; } + if(wpos != wused){ + int linear = xstart + wpos; + int ylin = linear / dimx; + int xlin = linear % dimx; + if(ncdirect_cursor_move_yx(n, tline + ylin, xlin)){ + break; + } + } if(fflush(n->ttyfp)){ break; } diff --git a/src/lib/termdesc.c b/src/lib/termdesc.c index ce36ab41c..58c08386f 100644 --- a/src/lib/termdesc.c +++ b/src/lib/termdesc.c @@ -318,10 +318,10 @@ init_terminfo_esc(tinfo* ti, const char* name, escape_e idx, // which can be identified directly, sans queries. #define KITTYQUERY "\x1b_Gi=1,a=q;\x1b\\" -// request kitty keyboard protocol through level 3, first pushing current. +// request kitty keyboard protocol through level 1, first pushing current. // see https://sw.kovidgoyal.net/kitty/keyboard-protocol/#progressive-enhancement // FIXME go to level 11, but need handle all functional keys -#define KBDSUPPORT "\x1b[>u\x1b[=3u" +#define KBDSUPPORT "\x1b[>u\x1b[=1u" // the kitty keyboard protocol allows unambiguous, complete identification of // input events. this queries for the level of support. we want to do this