From 22899c252368abfdaa6ee3410b01e83b194f42f8 Mon Sep 17 00:00:00 2001 From: Krzosa Karol Date: Sat, 3 Aug 2024 10:47:12 +0200 Subject: [PATCH] Add kill selected lines --- src/text_editor/commands_window.cpp | 87 ++++++++++++++++++++--------- 1 file changed, 60 insertions(+), 27 deletions(-) diff --git a/src/text_editor/commands_window.cpp b/src/text_editor/commands_window.cpp index 6237b43..0b48a44 100644 --- a/src/text_editor/commands_window.cpp +++ b/src/text_editor/commands_window.cpp @@ -31,7 +31,31 @@ void Command_DuplicateLine(View *view, int direction) { For(view->carets) it = MakeCaret(MovePos(*buffer, it.range.min, direction, false)); } -Array GetSortedSelectedLines(Allocator allocator, View *view) { +Int FindRangeByPos(Array &ranges, Int pos) { + // binary search + Int low = 0; + Int high = ranges.len - 1; + Int result = -1; + + while (low <= high) { + Int mid = low + (high - low) / 2; + Range range = ranges[mid]; + if (pos >= range.min && pos < range.max) { + result = mid; + break; + } + + if (range.min < pos) { + low = mid + 1; + } else { + high = mid - 1; + } + } + + return result; +} + +Array GetSelectedLinesSorted(Allocator allocator, View *view) { Scratch scratch(allocator); Buffer *buffer = GetBuffer(view->active_buffer); Array caret_copy = TightCopy(scratch, view->carets); @@ -66,7 +90,7 @@ void Command_IndentSelectedLines(View *view, bool shift = false) { BeforeEdit(buffer, view->carets); MergeCarets(view); - Array line_ranges_to_indent = GetSortedSelectedLines(scratch, view); + Array line_ranges_to_indent = GetSelectedLinesSorted(scratch, view); Array edits = {scratch}; For(line_ranges_to_indent) { for (Int i = it.min; i < it.max; i += 1) { @@ -92,30 +116,6 @@ void Command_IndentSelectedLines(View *view, bool shift = false) { view->update_scroll = false; } -Int FindRangeByPos(Array &ranges, Int pos) { - // binary search - Int low = 0; - Int high = ranges.len - 1; - Int result = -1; - - while (low <= high) { - Int mid = low + (high - low) / 2; - Range range = ranges[mid]; - if (pos >= range.min && pos < range.max) { - result = mid; - break; - } - - if (range.min < pos) { - low = mid + 1; - } else { - high = mid - 1; - } - } - - return result; -} - void Command_TrimTrailingWhitespace(View *view, bool dont_trim_lines_with_cursor) { Scratch scratch; Buffer *buffer = GetBuffer(view->active_buffer); @@ -124,7 +124,7 @@ void Command_TrimTrailingWhitespace(View *view, bool dont_trim_lines_with_cursor MergeCarets(view); Array lines_to_skip_triming = {}; - if (dont_trim_lines_with_cursor) lines_to_skip_triming = GetSortedSelectedLines(scratch, view); + if (dont_trim_lines_with_cursor) lines_to_skip_triming = GetSelectedLinesSorted(scratch, view); Array edits = {scratch}; for (Int i = 0; i < buffer->line_starts.len; i += 1) { @@ -148,6 +148,35 @@ void Command_TrimTrailingWhitespace(View *view, bool dont_trim_lines_with_cursor view->update_scroll = false; } +void Command_KillSelectedLines(View *view) { + Scratch scratch; + Buffer *buffer = GetBuffer(view->active_buffer); + + BeforeEdit(buffer, view->carets); + MergeCarets(view); + + Array lines = GetSelectedLinesSorted(scratch, view); + Array edits = {scratch}; + For(lines) { + + Range add_range = GetLineRange(*buffer, it.min); + for (Int i = it.min + 1; i < it.max; i += 1) { + Range line_range = GetLineRange(*buffer, i); + add_range.max = Max(line_range.max, add_range.max); + } + AddEdit(&edits, add_range, L""); + } + + For(view->carets) { + Int line = PosToLine(*buffer, it.range.min); + Range range = GetLineRange(*buffer, line); + it.range.min = it.range.max = range.min; + } + + ApplyEdits(buffer, edits); + AfterEdit(buffer, &edits, &view->carets, KILL_SELECTION); +} + bool SHIFT_PRESSED = true; void Command_MoveCursorsByPageSize(Window *window, int direction, bool shift = false) { Assert(direction == DIR_UP || direction == DIR_DOWN); @@ -487,6 +516,10 @@ void WindowCommand(Event event, Window *window, View *view) { Command_TrimTrailingWhitespace(view, false); } + if (CtrlShift(SDLK_K)) { + Command_KillSelectedLines(view); + } + if (Ctrl(SDLK_BACKSPACE)) { Command_Delete(view, DIR_LEFT, CTRL_PRESSED); search = true;