mirror of https://github.com/mirror/busybox.git
lineedit: change how cmdedit_set_out_char works
Rename two badly names functions, use "clear to end of screen" to eliminate annoying problems with clearing wide/combining chars, and such. Run tested. function old new delta put_cur_glyph_and_inc_cursor - 124 +124 put_till_end_and_adv_cursor - 24 +24 input_delete 125 130 +5 Ceos 5 4 -1 Ceol 5 4 -1 input_end 24 - -24 cmdedit_set_out_char 122 - -122 ------------------------------------------------------------------------------ (add/remove: 2/2 grow/shrink: 1/2 up/down: 153/-148) Total: 5 bytes Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>1_17_stable
parent
da1382410b
commit
94043e8ad2
|
@ -65,8 +65,8 @@ static const char SOn[] ALIGN1 = "\033[0m";
|
||||||
/* terminal bell sequence */
|
/* terminal bell sequence */
|
||||||
static const char bell[] ALIGN1 = "\007";
|
static const char bell[] ALIGN1 = "\007";
|
||||||
/* Clear-end-of-line and Clear-end-of-screen ESC sequence */
|
/* Clear-end-of-line and Clear-end-of-screen ESC sequence */
|
||||||
static const char Ceol[] ALIGN1 = "\033[0K";
|
static const char Ceol[] ALIGN1 = "\033[K";
|
||||||
static const char Ceos[] ALIGN1 = "\033[0J";
|
static const char Ceos[] ALIGN1 = "\033[J";
|
||||||
/* Cursor motion arbitrary destination ESC sequence */
|
/* Cursor motion arbitrary destination ESC sequence */
|
||||||
static const char CMrc[] ALIGN1 = "\033[%d;%dH";
|
static const char CMrc[] ALIGN1 = "\033[%d;%dH";
|
||||||
/* Cursor motion up and down ESC sequence */
|
/* Cursor motion up and down ESC sequence */
|
||||||
|
|
|
@ -66,6 +66,10 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#define SEQ_CLEAR_TILL_END_OF_SCREEN "\033[J"
|
||||||
|
//#define SEQ_CLEAR_TILL_END_OF_LINE "\033[K"
|
||||||
|
|
||||||
|
|
||||||
#undef CHAR_T
|
#undef CHAR_T
|
||||||
#if ENABLE_UNICODE_SUPPORT
|
#if ENABLE_UNICODE_SUPPORT
|
||||||
# define BB_NUL ((wchar_t)0)
|
# define BB_NUL ((wchar_t)0)
|
||||||
|
@ -221,13 +225,13 @@ static size_t load_string(const char *src, int maxsize)
|
||||||
}
|
}
|
||||||
static unsigned save_string(char *dst, unsigned maxsize)
|
static unsigned save_string(char *dst, unsigned maxsize)
|
||||||
{
|
{
|
||||||
#if !ENABLE_UNICODE_PRESERVE_BROKEN
|
# if !ENABLE_UNICODE_PRESERVE_BROKEN
|
||||||
ssize_t len = wcstombs(dst, command_ps, maxsize - 1);
|
ssize_t len = wcstombs(dst, command_ps, maxsize - 1);
|
||||||
if (len < 0)
|
if (len < 0)
|
||||||
len = 0;
|
len = 0;
|
||||||
dst[len] = '\0';
|
dst[len] = '\0';
|
||||||
return len;
|
return len;
|
||||||
#else
|
# else
|
||||||
unsigned dstpos = 0;
|
unsigned dstpos = 0;
|
||||||
unsigned srcpos = 0;
|
unsigned srcpos = 0;
|
||||||
|
|
||||||
|
@ -256,7 +260,7 @@ static unsigned save_string(char *dst, unsigned maxsize)
|
||||||
}
|
}
|
||||||
dst[dstpos] = '\0';
|
dst[dstpos] = '\0';
|
||||||
return dstpos;
|
return dstpos;
|
||||||
#endif
|
# endif
|
||||||
}
|
}
|
||||||
/* I thought just fputwc(c, stdout) would work. But no... */
|
/* I thought just fputwc(c, stdout) would work. But no... */
|
||||||
static void BB_PUTCHAR(wchar_t c)
|
static void BB_PUTCHAR(wchar_t c)
|
||||||
|
@ -293,19 +297,19 @@ static void save_string(char *dst, unsigned maxsize)
|
||||||
* Advance cursor on screen. If we reached right margin, scroll text up
|
* Advance cursor on screen. If we reached right margin, scroll text up
|
||||||
* and remove terminal margin effect by printing 'next_char' */
|
* and remove terminal margin effect by printing 'next_char' */
|
||||||
#define HACK_FOR_WRONG_WIDTH 1
|
#define HACK_FOR_WRONG_WIDTH 1
|
||||||
#if HACK_FOR_WRONG_WIDTH
|
static void put_cur_glyph_and_inc_cursor(void)
|
||||||
static void cmdedit_set_out_char(void)
|
|
||||||
#define cmdedit_set_out_char(next_char) cmdedit_set_out_char()
|
|
||||||
#else
|
|
||||||
static void cmdedit_set_out_char(int next_char)
|
|
||||||
#endif
|
|
||||||
{
|
{
|
||||||
CHAR_T c = command_ps[cursor];
|
CHAR_T c = command_ps[cursor];
|
||||||
|
|
||||||
if (c == BB_NUL) {
|
if (c == BB_NUL) {
|
||||||
/* erase character after end of input string */
|
/* erase character after end of input string */
|
||||||
c = ' ';
|
c = ' ';
|
||||||
|
} else {
|
||||||
|
/* advance cursor only if we aren't at the end yet */
|
||||||
|
cursor++;
|
||||||
|
cmdedit_x++;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if ENABLE_FEATURE_NONPRINTABLE_INVERSE_PUT
|
#if ENABLE_FEATURE_NONPRINTABLE_INVERSE_PUT
|
||||||
/* Display non-printable characters in reverse */
|
/* Display non-printable characters in reverse */
|
||||||
if (!BB_isprint(c)) {
|
if (!BB_isprint(c)) {
|
||||||
|
@ -321,7 +325,7 @@ static void cmdedit_set_out_char(int next_char)
|
||||||
{
|
{
|
||||||
BB_PUTCHAR(c);
|
BB_PUTCHAR(c);
|
||||||
}
|
}
|
||||||
if (++cmdedit_x >= cmdedit_termw) {
|
if (cmdedit_x >= cmdedit_termw) {
|
||||||
/* terminal is scrolled down */
|
/* terminal is scrolled down */
|
||||||
cmdedit_y++;
|
cmdedit_y++;
|
||||||
cmdedit_x = 0;
|
cmdedit_x = 0;
|
||||||
|
@ -335,27 +339,32 @@ static void cmdedit_set_out_char(int next_char)
|
||||||
* this will break things: there will be one extra empty line */
|
* this will break things: there will be one extra empty line */
|
||||||
puts("\r"); /* + implicit '\n' */
|
puts("\r"); /* + implicit '\n' */
|
||||||
#else
|
#else
|
||||||
/* Works ok only if cmdedit_termw is correct */
|
/* VT-10x terminals don't wrap cursor to next line when last char
|
||||||
/* destroy "(auto)margin" */
|
* on the line is printed - cursor stays "over" this char.
|
||||||
bb_putchar(next_char);
|
* Need to print _next_ char too (first one to appear on next line)
|
||||||
|
* to make cursor move down to next line.
|
||||||
|
*/
|
||||||
|
/* Works ok only if cmdedit_termw is correct. */
|
||||||
|
c = command_ps[cursor];
|
||||||
|
if (c == BB_NUL)
|
||||||
|
c = ' ';
|
||||||
|
BB_PUTCHAR(c);
|
||||||
bb_putchar('\b');
|
bb_putchar('\b');
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
// Huh? What if command_ps[cursor] == BB_NUL (we are at the end already?)
|
|
||||||
cursor++;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Move to end of line (by printing all chars till the end) */
|
/* Move to end of line (by printing all chars till the end) */
|
||||||
static void input_end(void)
|
static void put_till_end_and_adv_cursor(void)
|
||||||
{
|
{
|
||||||
while (cursor < command_len)
|
while (cursor < command_len)
|
||||||
cmdedit_set_out_char(' ');
|
put_cur_glyph_and_inc_cursor();
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Go to the next line */
|
/* Go to the next line */
|
||||||
static void goto_new_line(void)
|
static void goto_new_line(void)
|
||||||
{
|
{
|
||||||
input_end();
|
put_till_end_and_adv_cursor();
|
||||||
if (cmdedit_x)
|
if (cmdedit_x)
|
||||||
bb_putchar('\n');
|
bb_putchar('\n');
|
||||||
}
|
}
|
||||||
|
@ -433,8 +442,8 @@ static void redraw(int y, int back_cursor)
|
||||||
printf("\033[%uA", y);
|
printf("\033[%uA", y);
|
||||||
bb_putchar('\r');
|
bb_putchar('\r');
|
||||||
put_prompt();
|
put_prompt();
|
||||||
input_end(); /* rewrite */
|
put_till_end_and_adv_cursor();
|
||||||
printf("\033[J"); /* erase after cursor */
|
printf(SEQ_CLEAR_TILL_END_OF_SCREEN);
|
||||||
input_backward(back_cursor);
|
input_backward(back_cursor);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -468,8 +477,9 @@ static void input_delete(int save)
|
||||||
* simplified into (command_len - j) */
|
* simplified into (command_len - j) */
|
||||||
(command_len - j) * sizeof(command_ps[0]));
|
(command_len - j) * sizeof(command_ps[0]));
|
||||||
command_len--;
|
command_len--;
|
||||||
input_end(); /* rewrite new line */
|
put_till_end_and_adv_cursor();
|
||||||
cmdedit_set_out_char(' '); /* erase char */
|
/* Last char is still visible, erase it (and more) */
|
||||||
|
printf(SEQ_CLEAR_TILL_END_OF_SCREEN);
|
||||||
input_backward(cursor - j); /* back to old pos cursor */
|
input_backward(cursor - j); /* back to old pos cursor */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -487,7 +497,7 @@ static void put(void)
|
||||||
(command_len - cursor + 1) * sizeof(command_ps[0]));
|
(command_len - cursor + 1) * sizeof(command_ps[0]));
|
||||||
memcpy(command_ps + cursor, delbuf, j * sizeof(command_ps[0]));
|
memcpy(command_ps + cursor, delbuf, j * sizeof(command_ps[0]));
|
||||||
command_len += j;
|
command_len += j;
|
||||||
input_end(); /* rewrite new line */
|
put_till_end_and_adv_cursor();
|
||||||
input_backward(cursor - ocursor - j + 1); /* at end of new text */
|
input_backward(cursor - ocursor - j + 1); /* at end of new text */
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
@ -505,7 +515,7 @@ static void input_backspace(void)
|
||||||
static void input_forward(void)
|
static void input_forward(void)
|
||||||
{
|
{
|
||||||
if (cursor < command_len)
|
if (cursor < command_len)
|
||||||
cmdedit_set_out_char(command_ps[cursor + 1]);
|
put_cur_glyph_and_inc_cursor();
|
||||||
}
|
}
|
||||||
|
|
||||||
#if ENABLE_FEATURE_TAB_COMPLETION
|
#if ENABLE_FEATURE_TAB_COMPLETION
|
||||||
|
@ -1955,7 +1965,7 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
case CTRL('E'):
|
case CTRL('E'):
|
||||||
vi_case('$'|VI_CMDMODE_BIT:)
|
vi_case('$'|VI_CMDMODE_BIT:)
|
||||||
/* Control-e -- End of line */
|
/* Control-e -- End of line */
|
||||||
input_end();
|
put_till_end_and_adv_cursor();
|
||||||
break;
|
break;
|
||||||
case CTRL('F'):
|
case CTRL('F'):
|
||||||
vi_case('l'|VI_CMDMODE_BIT:)
|
vi_case('l'|VI_CMDMODE_BIT:)
|
||||||
|
@ -1984,12 +1994,12 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
/* Control-k -- clear to end of line */
|
/* Control-k -- clear to end of line */
|
||||||
command_ps[cursor] = BB_NUL;
|
command_ps[cursor] = BB_NUL;
|
||||||
command_len = cursor;
|
command_len = cursor;
|
||||||
printf("\033[J");
|
printf(SEQ_CLEAR_TILL_END_OF_SCREEN);
|
||||||
break;
|
break;
|
||||||
case CTRL('L'):
|
case CTRL('L'):
|
||||||
vi_case(CTRL('L')|VI_CMDMODE_BIT:)
|
vi_case(CTRL('L')|VI_CMDMODE_BIT:)
|
||||||
/* Control-l -- clear screen */
|
/* Control-l -- clear screen */
|
||||||
printf("\033[H");
|
printf("\033[H"); /* cursor to top,left */
|
||||||
redraw(0, command_len - cursor);
|
redraw(0, command_len - cursor);
|
||||||
break;
|
break;
|
||||||
#if MAX_HISTORY > 0
|
#if MAX_HISTORY > 0
|
||||||
|
@ -2040,7 +2050,7 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
vi_cmdmode = 0;
|
vi_cmdmode = 0;
|
||||||
break;
|
break;
|
||||||
case 'A'|VI_CMDMODE_BIT:
|
case 'A'|VI_CMDMODE_BIT:
|
||||||
input_end();
|
put_till_end_and_adv_cursor();
|
||||||
vi_cmdmode = 0;
|
vi_cmdmode = 0;
|
||||||
break;
|
break;
|
||||||
case 'x'|VI_CMDMODE_BIT:
|
case 'x'|VI_CMDMODE_BIT:
|
||||||
|
@ -2200,7 +2210,7 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
input_backward(cursor);
|
input_backward(cursor);
|
||||||
break;
|
break;
|
||||||
case KEYCODE_END:
|
case KEYCODE_END:
|
||||||
input_end();
|
put_till_end_and_adv_cursor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
@ -2260,7 +2270,7 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
/* We are at the end, append */
|
/* We are at the end, append */
|
||||||
command_ps[cursor] = ic;
|
command_ps[cursor] = ic;
|
||||||
command_ps[cursor + 1] = BB_NUL;
|
command_ps[cursor + 1] = BB_NUL;
|
||||||
cmdedit_set_out_char(' ');
|
put_cur_glyph_and_inc_cursor();
|
||||||
if (unicode_bidi_isrtl(ic))
|
if (unicode_bidi_isrtl(ic))
|
||||||
input_backward(1);
|
input_backward(1);
|
||||||
} else {
|
} else {
|
||||||
|
@ -2273,8 +2283,7 @@ int FAST_FUNC read_line_input(const char *prompt, char *command, int maxsize, li
|
||||||
/* is right-to-left char, or neutral one (e.g. comma) was just added to rtl text? */
|
/* is right-to-left char, or neutral one (e.g. comma) was just added to rtl text? */
|
||||||
if (!isrtl_str())
|
if (!isrtl_str())
|
||||||
sc++; /* no */
|
sc++; /* no */
|
||||||
/* rewrite from cursor */
|
put_till_end_and_adv_cursor();
|
||||||
input_end();
|
|
||||||
/* to prev x pos + 1 */
|
/* to prev x pos + 1 */
|
||||||
input_backward(cursor - sc);
|
input_backward(cursor - sc);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue