on master help sign in
Support m in surround delete and replace
76175dbGokul Soumya
helix-core/src/surround.rs+8−3
@@ -212,17 +212,22 @@ fn find_nth_close_pair(
212/// Find position of surround characters around every cursor. Returns None
212/// Find position of surround characters around every cursor. Returns None
213/// if any positions overlap. Note that the positions are in a flat Vec.
213/// if any positions overlap. Note that the positions are in a flat Vec.
214/// Use get_surround_pos().chunks(2) to get matching pairs of surround positions.
214/// Use get_surround_pos().chunks(2) to get matching pairs of surround positions.
215−/// `ch` can be either closing or opening pair.
215+/// `ch` can be either closing or opening pair. If `ch` is None, surround pairs
216+/// are automatically detected around each cursor (note that this may result
217+/// in them selecting different surround characters for each selection).
216pub fn get_surround_pos(
218pub fn get_surround_pos(
217 text: RopeSlice,
219 text: RopeSlice,
218 selection: &Selection,
220 selection: &Selection,
219− ch: char,
221+ ch: Option<char>,
220 skip: usize,
222 skip: usize,
221) -> Result<Vec<usize>> {
223) -> Result<Vec<usize>> {
222 let mut change_pos = Vec::new();
224 let mut change_pos = Vec::new();
223
225
224 for &range in selection {
226 for &range in selection {
227+ let (open_pos, close_pos) = match ch {
225− let (open_pos, close_pos) = find_nth_pairs_pos(text, ch, range, skip)?;
228+ Some(ch) => find_nth_pairs_pos(text, ch, range, skip)?,
229+ None => find_nth_closest_pairs_pos(text, range, skip)?,
230+ };
226 if change_pos.contains(&open_pos) || change_pos.contains(&close_pos) {
231 if change_pos.contains(&open_pos) || change_pos.contains(&close_pos) {
227 return Err(Error::CursorOverlap);
232 return Err(Error::CursorOverlap);
228 }
233 }
helix-term/src/commands.rs+8−6
@@ -4111,15 +4111,16 @@ fn surround_add(cx: &mut Context) {
4111fn surround_replace(cx: &mut Context) {
4111fn surround_replace(cx: &mut Context) {
4112 let count = cx.count();
4112 let count = cx.count();
4113 cx.on_next_key(move |cx, event| {
4113 cx.on_next_key(move |cx, event| {
4114− let from = match event.char() {
4114+ let surround_ch = match event.char() {
4115− Some(from) => from,
4115+ Some('m') => None, // m selects the closest surround pair
4116+ Some(ch) => Some(ch),
4116 None => return,
4117 None => return,
4117 };
4118 };
4118 let (view, doc) = current!(cx.editor);
4119 let (view, doc) = current!(cx.editor);
4119 let text = doc.text().slice(..);
4120 let text = doc.text().slice(..);
4120 let selection = doc.selection(view.id);
4121 let selection = doc.selection(view.id);
4121
4122
4122− let change_pos = match surround::get_surround_pos(text, selection, from, count) {
4123+ let change_pos = match surround::get_surround_pos(text, selection, surround_ch, count) {
4123 Ok(c) => c,
4124 Ok(c) => c,
4124 Err(err) => {
4125 Err(err) => {
4125 cx.editor.set_error(err.to_string());
4126 cx.editor.set_error(err.to_string());
@@ -4150,15 +4151,16 @@ fn surround_replace(cx: &mut Context) {
4150fn surround_delete(cx: &mut Context) {
4151fn surround_delete(cx: &mut Context) {
4151 let count = cx.count();
4152 let count = cx.count();
4152 cx.on_next_key(move |cx, event| {
4153 cx.on_next_key(move |cx, event| {
4153− let ch = match event.char() {
4154+ let surround_ch = match event.char() {
4155+ Some('m') => None, // m selects the closest surround pair
4154− Some(ch) => ch,
4156+ Some(ch) => Some(ch),
4155 None => return,
4157 None => return,
4156 };
4158 };
4157 let (view, doc) = current!(cx.editor);
4159 let (view, doc) = current!(cx.editor);
4158 let text = doc.text().slice(..);
4160 let text = doc.text().slice(..);
4159 let selection = doc.selection(view.id);
4161 let selection = doc.selection(view.id);
4160
4162
4161− let change_pos = match surround::get_surround_pos(text, selection, ch, count) {
4163+ let change_pos = match surround::get_surround_pos(text, selection, surround_ch, count) {
4162 Ok(c) => c,
4164 Ok(c) => c,
4163 Err(err) => {
4165 Err(err) => {
4164 cx.editor.set_error(err.to_string());
4166 cx.editor.set_error(err.to_string());