/*delete one character in front of cursor */ static void handle_delete(void) { int cur_tmp = cmd_cursor; /*when cursour at the end of string */ if (cmd_cursor >= cmd_strlen) return; /*delete one character from string */ strcpy(cmd_strp + cur_tmp, cmd_strp + cur_tmp + 1); cmd_strlen--; /*clear characters after cursor */ printf("\033[J"); /*re-print from delete position */ while (cmd_cursor < cmd_strlen) term_echo(); /*move cursor back to delete position */ cur_tmp = cmd_cursor - cur_tmp; while (cur_tmp--) cursor_backward(); }
/*deal with normal character*/ static void handle_normal(char *out_cmd, char c) { int tmp_cursor = cmd_cursor; /*buffer full */ if (++cmd_strlen > (MATCH_BUF_MAX - 2)) return; /*append operation */ if (cmd_cursor == (cmd_strlen - 1)) { *(out_cmd + cmd_cursor) = c; *(out_cmd + cmd_cursor + 1) = 0; term_echo(); } else { /* Insert operation */ /*give position to new char */ memmove(out_cmd + tmp_cursor + 1, out_cmd + tmp_cursor, cmd_strlen - tmp_cursor); *(out_cmd + tmp_cursor) = c; /* re-print from cursor */ while (cmd_cursor < cmd_strlen) term_echo(); /* restore curor to insert position */ tmp_cursor = cmd_cursor - tmp_cursor - 1; while (tmp_cursor--) cursor_backward(); } }
/* move backward one characters. */ static void handle_backward(void) { if (cmd_cursor > 0) { cursor_backward(); handle_delete(); } }
void backspace(char **str, int *pos, UNUSED t_head *history, UNUSED int *i_history) { if (*pos > 0) { edit_str(str, pos, 0); --*pos; cursor_save(); cursor_forward(strlen(*str) - *pos); cursor_backward(1); cursor_erase(1); cursor_restore(); cursor_backward(1); cursor_erase(1); cursor_save(); fflush(stdout); write(1, "\r", 1); write(1, history->prompt, strlen(history->prompt)); write(1, *str, strlen(*str)); cursor_restore(); fflush(stdout); } }
void del(char **str, int *pos, UNUSED t_head *history, UNUSED int *i_history) { if ((*str) && *pos < (int)strlen(*str)) { edit_str(str, pos, 1); cursor_save(); cursor_forward(strlen(*str) - *pos); cursor_backward(1); cursor_erase(strlen(*str) + 1); cursor_restore(); cursor_save(); fflush(stdout); write(1, "\r", 1); write(1, history->prompt, strlen(history->prompt)); write(1, *str, strlen(*str)); cursor_restore(); fflush(stdout); } }
static void handle_ansi(uint8_t byte) { if (atomic_test_and_clear_bit(&esc_state, ESC_ANSI_FIRST)) { if (!isdigit(byte)) { ansi_val = 1; goto ansi_cmd; } atomic_set_bit(&esc_state, ESC_ANSI_VAL); ansi_val = byte - '0'; ansi_val_2 = 0; return; } if (atomic_test_bit(&esc_state, ESC_ANSI_VAL)) { if (isdigit(byte)) { if (atomic_test_bit(&esc_state, ESC_ANSI_VAL_2)) { ansi_val_2 *= 10; ansi_val_2 += byte - '0'; } else { ansi_val *= 10; ansi_val += byte - '0'; } return; } /* Multi value sequence, e.g. Esc[Line;ColumnH */ if (byte == ';' && !atomic_test_and_set_bit(&esc_state, ESC_ANSI_VAL_2)) { return; } atomic_clear_bit(&esc_state, ESC_ANSI_VAL); atomic_clear_bit(&esc_state, ESC_ANSI_VAL_2); } ansi_cmd: switch (byte) { case ANSI_BACKWARD: if (ansi_val > cur) { break; } end += ansi_val; cur -= ansi_val; cursor_backward(ansi_val); break; case ANSI_FORWARD: if (ansi_val > end) { break; } end -= ansi_val; cur += ansi_val; cursor_forward(ansi_val); break; default: break; } atomic_clear_bit(&esc_state, ESC_ANSI); }
/* deal with left arrow*/ static void handle_left(void) { cursor_backward(); }
static void handle_ansi(u8_t byte, char *line) { if (atomic_test_and_clear_bit(&esc_state, ESC_ANSI_FIRST)) { if (!isdigit(byte)) { ansi_val = 1U; goto ansi_cmd; } atomic_set_bit(&esc_state, ESC_ANSI_VAL); ansi_val = byte - '0'; ansi_val_2 = 0U; return; } if (atomic_test_bit(&esc_state, ESC_ANSI_VAL)) { if (isdigit(byte)) { if (atomic_test_bit(&esc_state, ESC_ANSI_VAL_2)) { ansi_val_2 *= 10; ansi_val_2 += byte - '0'; } else { ansi_val *= 10; ansi_val += byte - '0'; } return; } /* Multi value sequence, e.g. Esc[Line;ColumnH */ if (byte == ';' && !atomic_test_and_set_bit(&esc_state, ESC_ANSI_VAL_2)) { return; } atomic_clear_bit(&esc_state, ESC_ANSI_VAL); atomic_clear_bit(&esc_state, ESC_ANSI_VAL_2); } ansi_cmd: switch (byte) { case ANSI_BACKWARD: if (ansi_val > cur) { break; } end += ansi_val; cur -= ansi_val; cursor_backward(ansi_val); break; case ANSI_FORWARD: if (ansi_val > end) { break; } end -= ansi_val; cur += ansi_val; cursor_forward(ansi_val); break; case ANSI_HOME: if (!cur) { break; } cursor_backward(cur); end += cur; cur = 0U; break; case ANSI_END: if (!end) { break; } cursor_forward(end); cur += end; end = 0U; break; case ANSI_DEL: if (!end) { break; } cursor_forward(1); del_char(&line[cur], --end); break; default: break; } atomic_clear_bit(&esc_state, ESC_ANSI); }