From 6c19d2c1c4f6e0665ceb44e75e5e5315b87d3b4b Mon Sep 17 00:00:00 2001 From: Nikita Revenco <154856872+NikitaRevenco@users.noreply.github.com> Date: Sun, 12 Jan 2025 20:31:49 +0000 Subject: [PATCH] feat: implement double click and single click selection --- helix-core/src/textobject.rs | 7 ++++++- helix-term/src/ui/editor.rs | 24 ++++++++++++++++++++++-- 2 files changed, 28 insertions(+), 3 deletions(-) diff --git a/helix-core/src/textobject.rs b/helix-core/src/textobject.rs index 7576b3a78..1225b70a7 100644 --- a/helix-core/src/textobject.rs +++ b/helix-core/src/textobject.rs @@ -11,7 +11,12 @@ use crate::syntax::LanguageConfiguration; use crate::Range; use crate::{surround, Syntax}; -fn find_word_boundary(slice: RopeSlice, mut pos: usize, direction: Direction, long: bool) -> usize { +pub fn find_word_boundary( + slice: RopeSlice, + mut pos: usize, + direction: Direction, + long: bool, +) -> usize { use CharCategory::{Eol, Whitespace}; let iter = match direction { diff --git a/helix-term/src/ui/editor.rs b/helix-term/src/ui/editor.rs index f86de5b81..03f5ba97f 100644 --- a/helix-term/src/ui/editor.rs +++ b/helix-term/src/ui/editor.rs @@ -14,11 +14,13 @@ use crate::{ }; use helix_core::{ + chars::CharCategory, diagnostic::NumberOrString, graphemes::{next_grapheme_boundary, prev_grapheme_boundary}, movement::Direction, syntax::{self, HighlightEvent}, text_annotations::TextAnnotations, + textobject::find_word_boundary, unicode::width::UnicodeWidthStr, visual_offset_from_block, Change, Position, Range, Selection, Transaction, }; @@ -1176,10 +1178,9 @@ impl EditorView { if let Some((pos, view_id)) = pos_and_view(editor, row, column, true) { let prev_view_id = view!(editor).id; let doc = doc_mut!(editor, &view!(editor, view_id).doc); + let text = doc.text().slice(..); match editor.mouse_clicks.register_click(pos) { - MouseClick::Triple => {} - MouseClick::Double => {} MouseClick::Single => { if modifiers == KeyModifiers::ALT { let selection = doc.selection(view_id).clone(); @@ -1200,6 +1201,25 @@ impl EditorView { doc.set_selection(view_id, Selection::point(pos)); } } + MouseClick::Double => { + let word_start = + find_word_boundary(text, pos, Direction::Backward, false); + let word_end = match text + .get_char(pos) + .map(helix_core::chars::categorize_char) + { + None | Some(CharCategory::Whitespace | CharCategory::Eol) => pos, + _ => find_word_boundary(text, pos + 1, Direction::Forward, false), + }; + + doc.set_selection(view_id, Selection::single(word_start, word_end)); + } + MouseClick::Triple => { + let current_line = text.char_to_line(pos); + let from = text.line_to_char(current_line); + let to = text.line_to_char(current_line + 1); + doc.set_selection(view_id, Selection::single(from, to)); + } } if view_id != prev_view_id {