Handle leaving quote mode properly;

This commit is contained in:
Nathan Fisher 2023-06-02 11:09:39 -04:00
parent 5113775933
commit c36009db46

View file

@ -26,7 +26,7 @@ pub enum GemtextNode {
Heading3(String),
ListItem(String),
Quote(String),
Preformatted(String),
Preformatted(Option<String>, String),
Link(Link),
}
@ -42,7 +42,10 @@ impl fmt::Display for GemtextNode {
Self::Heading3(h) => writeln!(f, "### {h}"),
Self::ListItem(l) => writeln!(f, "* {l}"),
Self::Quote(q) => writeln!(f, "> {q}"),
Self::Preformatted(p) => writeln!(f, "```\n{p}\n```"),
Self::Preformatted(a, p) => match a {
None => writeln!(f, "```\n{}\n```", p),
Some(alt) => writeln!(f, "```{alt}\n{}\n```", p),
},
Self::Link(l) => writeln!(f, "=> {l}"),
}
}
@ -155,13 +158,25 @@ impl<'a> Parser<'a> {
self.lines.push(GemtextNode::parse_list_item(line));
}
fn quote(&mut self, line: &'a str) {
fn enter_quote(&mut self, line: &'a str) {
match line.split_once(char::is_whitespace) {
Some((prefix, suffix)) if prefix == ">" => self.state = State::Quote(vec![suffix]),
_ => self.lines.push(GemtextNode::Text(line.to_string())),
}
}
fn leave_quote(&mut self, line: &'a str) {
match &mut self.state {
State::Quote(q) => {
let quote = q.join("\n").to_string();
self.lines.push(GemtextNode::Quote(quote));
}
_ => panic!("Attempt to parse as quote when not in quote mode"),
}
self.state = State::Normal;
self.lines.push(GemtextNode::Text(line.to_string()));
}
fn enter_preformatted(&mut self, line: &'a str) {
let alt = if line.len() > 3 {
Some(line[3..].trim())
@ -196,7 +211,7 @@ impl<'a> Parser<'a> {
s if s.starts_with("=>") => self.link(s),
s if s.starts_with('#') => self.heading(s),
s if s.starts_with('*') => self.list_item(s),
s if s.starts_with('>') => self.quote(s),
s if s.starts_with('>') => self.enter_quote(s),
s if s.starts_with("```") => self.enter_preformatted(s),
s if s.starts_with('<') => self.senders(s),
s if s.starts_with(':') => self.recipients(s),
@ -217,6 +232,13 @@ impl<'a> Parser<'a> {
}
fn parse_quote(&mut self, line: &'a str) {
todo!()
if let Some(suffix) = line.strip_prefix('>') {
match &mut self.state {
State::Quote(q) => q.push(suffix.trim()),
_ => panic!("Attempt to parse as quote when not in quote mode"),
}
} else {
self.leave_quote(line);
}
}
}