Skip to content

Commit 12e6e08

Browse files
console: add Delete key support
- Windows: VK_DELETE detection - Linux: ESC[3~ sequence parsing - Forward character deletion with UTF-8 support
1 parent a8beb3a commit 12e6e08

File tree

1 file changed

+41
-7
lines changed

1 file changed

+41
-7
lines changed

common/console.cpp

Lines changed: 41 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ namespace console {
5151
static constexpr char32_t KEY_END = 0xE005;
5252
static constexpr char32_t KEY_CTRL_ARROW_LEFT = 0xE006;
5353
static constexpr char32_t KEY_CTRL_ARROW_RIGHT = 0xE007;
54+
static constexpr char32_t KEY_DELETE = 0xE008;
5455
}
5556

5657
//
@@ -199,13 +200,14 @@ namespace console {
199200
const DWORD ctrl_mask = LEFT_CTRL_PRESSED | RIGHT_CTRL_PRESSED;
200201
const bool ctrl_pressed = (record.Event.KeyEvent.dwControlKeyState & ctrl_mask) != 0;
201202
switch (record.Event.KeyEvent.wVirtualKeyCode) {
202-
case VK_LEFT: return ctrl_pressed ? KEY_CTRL_ARROW_LEFT : KEY_ARROW_LEFT;
203-
case VK_RIGHT: return ctrl_pressed ? KEY_CTRL_ARROW_RIGHT : KEY_ARROW_RIGHT;
204-
case VK_UP: return KEY_ARROW_UP;
205-
case VK_DOWN: return KEY_ARROW_DOWN;
206-
case VK_HOME: return KEY_HOME;
207-
case VK_END: return KEY_END;
208-
default: continue;
203+
case VK_LEFT: return ctrl_pressed ? KEY_CTRL_ARROW_LEFT : KEY_ARROW_LEFT;
204+
case VK_RIGHT: return ctrl_pressed ? KEY_CTRL_ARROW_RIGHT : KEY_ARROW_RIGHT;
205+
case VK_UP: return KEY_ARROW_UP;
206+
case VK_DOWN: return KEY_ARROW_DOWN;
207+
case VK_HOME: return KEY_HOME;
208+
case VK_END: return KEY_END;
209+
case VK_DELETE: return KEY_DELETE;
210+
default: continue;
209211
}
210212
}
211213

@@ -418,6 +420,34 @@ namespace console {
418420
static void move_to_line_start(size_t & char_pos, size_t & byte_pos, const std::vector<int> & widths);
419421
static void move_to_line_end(size_t & char_pos, size_t & byte_pos, const std::vector<int> & widths, const std::string & line);
420422

423+
static void delete_at_cursor(std::string & line, std::vector<int> & widths, size_t & char_pos, size_t & byte_pos) {
424+
if (char_pos >= widths.size()) {
425+
return;
426+
}
427+
428+
size_t next_pos = next_utf8_char_pos(line, byte_pos);
429+
int w = widths[char_pos];
430+
size_t char_len = next_pos - byte_pos;
431+
432+
line.erase(byte_pos, char_len);
433+
widths.erase(widths.begin() + char_pos);
434+
435+
size_t p = byte_pos;
436+
int tail_width = 0;
437+
for (size_t i = char_pos; i < widths.size(); ++i) {
438+
size_t following = next_utf8_char_pos(line, p);
439+
put_codepoint(line.c_str() + p, following - p, widths[i]);
440+
tail_width += widths[i];
441+
p = following;
442+
}
443+
444+
for (int i = 0; i < w; ++i) {
445+
fputc(' ', out);
446+
}
447+
448+
move_cursor(-(tail_width + w));
449+
}
450+
421451
static void clear_current_line(const std::vector<int> & widths) {
422452
int total_width = 0;
423453
for (int w : widths) {
@@ -733,6 +763,8 @@ namespace console {
733763
move_to_line_start(char_pos, byte_pos, widths);
734764
} else if (digits == "4" || digits == "8") {
735765
move_to_line_end(char_pos, byte_pos, widths, line);
766+
} else if (digits == "3") {
767+
delete_at_cursor(line, widths, char_pos, byte_pos);
736768
}
737769
}
738770
}
@@ -767,6 +799,8 @@ namespace console {
767799
move_to_line_start(char_pos, byte_pos, widths);
768800
} else if (input_char == KEY_END) {
769801
move_to_line_end(char_pos, byte_pos, widths, line);
802+
} else if (input_char == KEY_DELETE) {
803+
delete_at_cursor(line, widths, char_pos, byte_pos);
770804
} else if (input_char == KEY_ARROW_UP || input_char == KEY_ARROW_DOWN) {
771805
if (!history.empty()) {
772806
if (input_char == KEY_ARROW_UP && history_index > 0) {

0 commit comments

Comments
 (0)