make mark commands typeable

pull/10905/head
Sam Vente 6 months ago
parent cfbc46cfa2
commit 89b63a23cb
No known key found for this signature in database

@ -570,8 +570,6 @@ impl MappableCommand {
command_palette, "Open command palette",
goto_word, "Jump to a two-character label",
extend_to_word, "Extend to a two-character label",
register_mark, "Register a bookmark",
goto_mark, "Goto a bookmark",
);
}
@ -6131,77 +6129,6 @@ fn read_from_register(editor: &Editor, reg: char) -> Option<RegisterValues> {
editor.registers.read(reg, &editor)
}
pub fn goto_mark(cx: &mut Context) {
let register_name = cx.register.unwrap_or('^').clone();
let registers_vals = read_from_register(cx.editor, register_name);
let blurb = registers_vals
.unwrap()
.into_iter()
.next()
.map(|c| c.into_owned());
match blurb {
Some(s) => {
let doc_id_parser = seq!(take_until(|c| c == ':'), ":");
let range_parser = seq!(
"(",
take_until(|c| c == ','),
",",
take_until(|c| c == ')'),
")"
);
let multiple_ranges_parser = sep(range_parser, ",");
let (tail, (doc_id_str, _)) = doc_id_parser.parse(&s).unwrap();
let (tail, v) = multiple_ranges_parser.parse(tail).unwrap();
let mut ranges = v
.iter()
.map(|tup| {
let (_, anchor_str, _, head_str, _) = tup;
let anchor: usize = <usize as FromStr>::from_str(anchor_str).unwrap();
let head: usize = <usize as FromStr>::from_str(head_str).unwrap();
Range {
anchor,
head,
old_visual_position: None,
}
})
.rev();
// reverse the iterators so the first range will end up as the primary when we push them
let doc_id: DocumentId = doc_id_str.try_into().unwrap();
cx.editor.switch(doc_id, Action::Replace);
let (view, doc) = current!(cx.editor);
let last_range = ranges.next().unwrap(); // there is always at least one range
let mut selection = Selection::from(last_range);
for r in ranges {
selection = selection.push(r);
}
doc.set_selection(view.id, selection);
}
None => (),
}
}
fn register_mark(cx: &mut Context) {
let register_name = cx.register.unwrap_or('^').clone();
let (view, doc) = current!(cx.editor);
let ranges = doc.selection(view.id).ranges();
let ranges_str = ranges
.iter()
.map(|r| r.to_string())
.collect::<Vec<String>>()
.join(",");
cx.editor
.registers
.write(
register_name,
vec![format!("{}:{}", doc.id(), ranges_str.to_string())],
)
.unwrap();
cx.editor
.set_status(format!("Saved selection bookmark to [{}]", register_name));
}
fn jump_to_label(cx: &mut Context, labels: Vec<Range>, behaviour: Movement) {
let doc = doc!(cx.editor);
let alphabet = &cx.editor.config().jump_label_alphabet;

@ -1,3 +1,4 @@
use std::borrow::Borrow;
use std::fmt::Write;
use std::io::BufReader;
use std::ops::Deref;
@ -446,6 +447,105 @@ fn new_file(
Ok(())
}
fn register_mark(
cx: &mut compositor::Context,
args: &[Cow<str>],
event: PromptEvent,
) -> anyhow::Result<()> {
if event != PromptEvent::Validate {
return Ok(());
};
let register_name: char = args
.first()
.map_or_else(
|| cx.editor.selected_register,
|s| s.as_ref().chars().next(),
)
.unwrap_or('^');
let (view, doc) = current!(cx.editor);
let ranges = doc.selection(view.id).ranges();
let ranges_str = ranges
.iter()
.map(|r| r.to_string())
.collect::<Vec<String>>()
.join(",");
cx.editor
.registers
.write(
register_name,
vec![format!("{}:{}", doc.id(), ranges_str.to_string())],
)
.unwrap();
cx.editor
.set_status(format!("Saved selection bookmark to [{}]", register_name));
Ok(())
}
fn goto_mark(
cx: &mut compositor::Context,
args: &[Cow<str>],
event: PromptEvent,
) -> anyhow::Result<()> {
if event != PromptEvent::Validate {
return Ok(());
};
let register_name: char = args
.first()
.map_or_else(
|| cx.editor.selected_register,
|s| s.as_ref().chars().next(),
)
.unwrap_or('^');
let registers_vals = read_from_register(cx.editor, register_name);
let blurb = registers_vals
.unwrap()
.into_iter()
.next()
.map(|c| c.into_owned());
match blurb {
Some(s) => {
let doc_id_parser = seq!(take_until(|c| c == ':'), ":");
let range_parser = seq!(
"(",
take_until(|c| c == ','),
",",
take_until(|c| c == ')'),
")"
);
let multiple_ranges_parser = sep(range_parser, ",");
let (tail, (doc_id_str, _)) = doc_id_parser.parse(&s).unwrap();
let (_tail, v) = multiple_ranges_parser.parse(tail).unwrap();
let mut ranges = v
.iter()
.map(|tup| {
let (_, anchor_str, _, head_str, _) = tup;
let anchor: usize = <usize as FromStr>::from_str(anchor_str).unwrap();
let head: usize = <usize as FromStr>::from_str(head_str).unwrap();
Range {
anchor,
head,
old_visual_position: None,
}
})
.rev();
// reverse the iterators so the first range will end up as the primary when we push them
let doc_id: DocumentId = doc_id_str.try_into().unwrap();
cx.editor.switch(doc_id, Action::Replace);
let (view, doc) = current!(cx.editor);
let last_range = ranges.next().unwrap(); // there is always at least one range
let mut selection = Selection::from(last_range);
for r in ranges {
selection = selection.push(r);
}
doc.set_selection(view.id, selection);
}
None => (),
};
Ok(())
}
fn format(
cx: &mut compositor::Context,
_args: &[Cow<str>],
@ -2633,6 +2733,20 @@ pub const TYPABLE_COMMAND_LIST: &[TypableCommand] = &[
fun: new_file,
signature: CommandSignature::none(),
},
TypableCommand {
name: "goto_mark",
aliases: &[],
doc: "Go to the selection saved in a register. Register can be provided as argument or selected register else ^ will be used",
fun: goto_mark,
signature: CommandSignature::positional(&[completers::register]),
},
TypableCommand {
name: "register_mark",
aliases: &[],
doc: "Save current selection into a register. Register can be provided as argument or selected register else ^ will be used",
fun: register_mark,
signature: CommandSignature::positional(&[completers::register]),
},
TypableCommand {
name: "format",
aliases: &["fmt"],

@ -333,8 +333,6 @@ pub fn default() -> HashMap<Mode, KeyTrie> {
"C-a" => increment,
"C-x" => decrement,
// just for debugging I'll find something better later
"1" => register_mark,
"2" => goto_mark,
});
let mut select = normal.clone();

Loading…
Cancel
Save