From 76175dbd6da4f57118eb52477f3336c6dcab5692 Mon Sep 17 00:00:00 2001 From: Gokul Soumya Date: Sun, 3 Apr 2022 22:00:26 +0530 Subject: [PATCH] Support m in surround delete and replace --- helix-core/src/surround.rs | 11 ++++++++--- helix-term/src/commands.rs | 14 ++++++++------ 2 files changed, 16 insertions(+), 9 deletions(-) diff --git a/helix-core/src/surround.rs b/helix-core/src/surround.rs index 4cba81bff..6f1fdb95d 100644 --- a/helix-core/src/surround.rs +++ b/helix-core/src/surround.rs @@ -212,17 +212,22 @@ fn find_nth_close_pair( /// Find position of surround characters around every cursor. Returns None /// if any positions overlap. Note that the positions are in a flat Vec. /// Use get_surround_pos().chunks(2) to get matching pairs of surround positions. -/// `ch` can be either closing or opening pair. +/// `ch` can be either closing or opening pair. If `ch` is None, surround pairs +/// are automatically detected around each cursor (note that this may result +/// in them selecting different surround characters for each selection). pub fn get_surround_pos( text: RopeSlice, selection: &Selection, - ch: char, + ch: Option, skip: usize, ) -> Result> { let mut change_pos = Vec::new(); for &range in selection { - let (open_pos, close_pos) = find_nth_pairs_pos(text, ch, range, skip)?; + let (open_pos, close_pos) = match ch { + Some(ch) => find_nth_pairs_pos(text, ch, range, skip)?, + None => find_nth_closest_pairs_pos(text, range, skip)?, + }; if change_pos.contains(&open_pos) || change_pos.contains(&close_pos) { return Err(Error::CursorOverlap); } diff --git a/helix-term/src/commands.rs b/helix-term/src/commands.rs index 75c84b748..54dcc98fc 100644 --- a/helix-term/src/commands.rs +++ b/helix-term/src/commands.rs @@ -4111,15 +4111,16 @@ fn surround_add(cx: &mut Context) { fn surround_replace(cx: &mut Context) { let count = cx.count(); cx.on_next_key(move |cx, event| { - let from = match event.char() { - Some(from) => from, + let surround_ch = match event.char() { + Some('m') => None, // m selects the closest surround pair + Some(ch) => Some(ch), None => return, }; let (view, doc) = current!(cx.editor); let text = doc.text().slice(..); let selection = doc.selection(view.id); - let change_pos = match surround::get_surround_pos(text, selection, from, count) { + let change_pos = match surround::get_surround_pos(text, selection, surround_ch, count) { Ok(c) => c, Err(err) => { cx.editor.set_error(err.to_string()); @@ -4150,15 +4151,16 @@ fn surround_replace(cx: &mut Context) { fn surround_delete(cx: &mut Context) { let count = cx.count(); cx.on_next_key(move |cx, event| { - let ch = match event.char() { - Some(ch) => ch, + let surround_ch = match event.char() { + Some('m') => None, // m selects the closest surround pair + Some(ch) => Some(ch), None => return, }; let (view, doc) = current!(cx.editor); let text = doc.text().slice(..); let selection = doc.selection(view.id); - let change_pos = match surround::get_surround_pos(text, selection, ch, count) { + let change_pos = match surround::get_surround_pos(text, selection, surround_ch, count) { Ok(c) => c, Err(err) => { cx.editor.set_error(err.to_string());