From 1ed9af8300c037174dba4fc83fffeea9e6291ab8 Mon Sep 17 00:00:00 2001 From: "Kartik K. Agaram" Date: Fri, 4 Sep 2015 11:07:08 -0700 Subject: 2141 - attempt to deal with slow networks On slow networks sometimes escape sequences were being partially consumed, causing junk to be added to the editor when you pressed arrow keys and so on. Now we have a way to wait. Empirically seems to work if I page-up and then scroll back up using up-arrow. Before I'd consistently get junk even on my local machine. Now I no longer do. If we still see problems I'll increase the wait time and see if the increase helps. Then we'll know more about this approach. --- cannot_write_tests_for | 4 ++++ termbox/input.inl | 43 +++++++++++++++++++++++++++---------------- 2 files changed, 31 insertions(+), 16 deletions(-) diff --git a/cannot_write_tests_for b/cannot_write_tests_for index a77ef91b..8a678b37 100644 --- a/cannot_write_tests_for +++ b/cannot_write_tests_for @@ -3,3 +3,7 @@ 3. hide/show screen 4. more touch event types 5. sandbox isolation + +termbox issues are implementation-specific and not worth testing: + whether we clear junk from other processes + latency in interpreting low-level escape characters diff --git a/termbox/input.inl b/termbox/input.inl index 97ea1190..0088cd91 100644 --- a/termbox/input.inl +++ b/termbox/input.inl @@ -21,6 +21,9 @@ static bool starts_with(const char *s1, int len, const char *s2) // convert escape sequence to event, and return consumed bytes on success (failure == 0) static int parse_escape_seq(struct tb_event *event, const char *buf, int len) { + static int parse_attempts = 0; + static const int MAX_PARSE_ATTEMPTS = 2; + //? int x = 0; //? FOO("-- %d\n", len); //? for (x = 0; x < len; ++x) { @@ -48,6 +51,7 @@ static int parse_escape_seq(struct tb_event *event, const char *buf, int len) event->key = TB_KEY_MOUSE_RELEASE; break; default: + parse_attempts = 0; return -6; } event->type = TB_EVENT_MOUSE; // TB_EVENT_KEY by default @@ -56,6 +60,7 @@ static int parse_escape_seq(struct tb_event *event, const char *buf, int len) event->x = (uint8_t)buf[4] - 1 - 32; event->y = (uint8_t)buf[5] - 1 - 32; + parse_attempts = 0; return 6; } @@ -66,6 +71,7 @@ static int parse_escape_seq(struct tb_event *event, const char *buf, int len) if (starts_with(buf, len, keys[i])) { event->ch = 0; event->key = 0xFFFF-i; + parse_attempts = 0; return strlen(keys[i]); } } @@ -73,35 +79,48 @@ static int parse_escape_seq(struct tb_event *event, const char *buf, int len) if (starts_with(buf, len, "\033[200~")) { event->ch = 0; event->key = TB_KEY_START_PASTE; + parse_attempts = 0; return strlen("\033[200~"); } if (starts_with(buf, len, "\033[201~")) { event->ch = 0; event->key = TB_KEY_END_PASTE; + parse_attempts = 0; return strlen("\033[201~"); } if (starts_with(buf, len, "\033[1;5A")) { event->ch = 0; event->key = TB_KEY_CTRL_ARROW_UP; + parse_attempts = 0; return strlen("\033[1;5A"); } if (starts_with(buf, len, "\033[1;5B")) { event->ch = 0; event->key = TB_KEY_CTRL_ARROW_DOWN; + parse_attempts = 0; return strlen("\033[1;5B"); } if (starts_with(buf, len, "\033[1;5C")) { event->ch = 0; event->key = TB_KEY_CTRL_ARROW_RIGHT; + parse_attempts = 0; return strlen("\033[1;5C"); } if (starts_with(buf, len, "\033[1;5D")) { event->ch = 0; event->key = TB_KEY_CTRL_ARROW_LEFT; + parse_attempts = 0; return strlen("\033[1;5D"); } - return 0; + // no escape sequence recognized? wait a bit in case our buffer is incomplete + ++parse_attempts; + if (parse_attempts < MAX_PARSE_ATTEMPTS) return 0; + // still nothing? give up and consume just the esc + event->ch = 0; + event->key = TB_KEY_ESC; + parse_attempts = 0; + return 1; } static bool extract_event(struct tb_event *event, struct bytebuffer *inbuf) @@ -118,23 +137,15 @@ static bool extract_event(struct tb_event *event, struct bytebuffer *inbuf) //? } if (buf[0] == '\033') { int n = parse_escape_seq(event, buf, len); + if (n == 0) return false; //? FOO("parsed: %u %u %u %u\n", n, (unsigned int)event->type, (unsigned int)event->key, event->ch); - if (n != 0) { - bool success = true; - if (n < 0) { - success = false; - n = -n; - } - bytebuffer_truncate(inbuf, n); - return success; - } else { -//? FOO("escape sequence\n"); - // it's not escape sequence; assume it's esc - event->ch = 0; - event->key = TB_KEY_ESC; - bytebuffer_truncate(inbuf, 1); - return true; + bool success = true; + if (n < 0) { + success = false; + n = -n; } + bytebuffer_truncate(inbuf, n); + return success; } // if we're here, this is not an escape sequence and not an alt sequence -- cgit 1.4.1-2-gfad0