Skip to content

Commit

Permalink
make Inline variants into structs
Browse files Browse the repository at this point in the history
- extract the inlined struct variants into actual structs
- make `Inline` be non-selectable

With this change, everything is now officially nice and tidy. Everything
that's selectable is a top-level variant in `MdElemRef`, and everything
that's not selectable is within the `NonSelectable` variant.

This (finally!) resolves #53
  • Loading branch information
yshavit authored Jun 23, 2024
1 parent 7b2eac8 commit 78ae814
Show file tree
Hide file tree
Showing 6 changed files with 253 additions and 232 deletions.
116 changes: 58 additions & 58 deletions src/fmt_md.rs
Original file line number Diff line number Diff line change
Expand Up @@ -163,9 +163,6 @@ impl<'a> MdWriterState<'a> {
MdElemRef::ListItem(ListItemRef(idx, item)) => {
self.write_list_item(out, &idx, item);
}
MdElemRef::Inline(inline) => {
self.write_inline_element(out, inline);
}
MdElemRef::NonSelectable(node) => match node {
NonSelectable::ThematicBreak => {
out.with_block(Block::Plain, |out| out.write_str("***"));
Expand All @@ -177,6 +174,9 @@ impl<'a> MdWriterState<'a> {
NonSelectable::BlockQuote(block) => self.write_block_quote(out, block),
NonSelectable::List(list) => self.write_list(out, list),
NonSelectable::Table(table) => self.write_table(out, table),
NonSelectable::Inline(inline) => {
self.write_inline_element(out, inline);
}
},
}
}
Expand Down Expand Up @@ -395,17 +395,17 @@ impl<'a> MdWriterState<'a> {
W: SimpleWrite,
{
match elem {
Inline::Span { variant, children } => {
Inline::Formatting(Formatting { variant, children }) => {
let surround = match variant {
SpanVariant::Delete => "~~",
SpanVariant::Emphasis => "_",
SpanVariant::Strong => "**",
FormattingVariant::Delete => "~~",
FormattingVariant::Emphasis => "_",
FormattingVariant::Strong => "**",
};
out.write_str(surround);
self.write_line(out, children);
out.write_str(surround);
}
Inline::Text { variant, value } => {
Inline::Text(Text { variant, value }) => {
let surround = match variant {
TextVariant::Plain => "",
TextVariant::Code => "`",
Expand All @@ -416,12 +416,12 @@ impl<'a> MdWriterState<'a> {
out.write_str(value);
out.write_str(surround);
}
Inline::Link { text, link_definition } => {
Inline::Link(Link { text, link_definition }) => {
self.write_link_inline(out, ReifiedLabel::Inline(text), link_definition, |me, out| {
me.write_line(out, text)
});
}
Inline::Image { alt, link } => {
Inline::Image(Image { alt, link }) => {
out.write_char('!');
self.write_link_inline(out, ReifiedLabel::Identifier(alt), link, |_, out| out.write_str(alt));
}
Expand Down Expand Up @@ -614,34 +614,34 @@ pub mod tests {
Section(_),
ListItem(..),

Inline(Inline::Span{variant: SpanVariant::Delete, ..}),
Inline(Inline::Span{variant: SpanVariant::Emphasis, ..}),
Inline(Inline::Span{variant: SpanVariant::Strong, ..}),

Inline(Inline::Text{variant: TextVariant::Plain, ..}),
Inline(Inline::Text{variant: TextVariant::Code, ..}),
Inline(Inline::Text{variant: TextVariant::Math, ..}),
Inline(Inline::Text{variant: TextVariant::Html, ..}),

Inline(Inline::Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Inline, ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Full(_), ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Collapsed, ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Shortcut, ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Inline, ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Full(_), ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Collapsed, ..}, ..}),
Inline(Inline::Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Shortcut, ..}, ..}),

Inline(Inline::Image{link: LinkDefinition{title: None, reference: LinkReference::Inline, ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: None, reference: LinkReference::Full(_), ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: None, reference: LinkReference::Collapsed, ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: None, reference: LinkReference::Shortcut, ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Inline, ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Full(_), ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Collapsed, ..}, ..}),
Inline(Inline::Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Shortcut, ..}, ..}),

Inline(Inline::Footnote{..}),
NonSelectable(NonSelectable::Inline(Inline::Formatting(Formatting{variant: FormattingVariant::Delete, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Formatting(Formatting{variant: FormattingVariant::Emphasis, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Formatting(Formatting{variant: FormattingVariant::Strong, ..}))),

NonSelectable(NonSelectable::Inline(Inline::Text(Text{variant: TextVariant::Plain, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Text(Text{variant: TextVariant::Code, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Text(Text{variant: TextVariant::Math, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Text(Text{variant: TextVariant::Html, ..}))),

NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Inline, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Full(_), ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Collapsed, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: None, reference: LinkReference::Shortcut, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Inline, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Full(_), ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Collapsed, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Link(Link{link_definition: LinkDefinition{title: Some(_), reference: LinkReference::Shortcut, ..}, ..}))),

NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: None, reference: LinkReference::Inline, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: None, reference: LinkReference::Full(_), ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: None, reference: LinkReference::Collapsed, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: None, reference: LinkReference::Shortcut, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Inline, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Full(_), ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Collapsed, ..}, ..}))),
NonSelectable(NonSelectable::Inline(Inline::Image(Image{link: LinkDefinition{title: Some(_), reference: LinkReference::Shortcut, ..}, ..}))),

NonSelectable(NonSelectable::Inline(Inline::Footnote{..})),

NonSelectable(NonSelectable::ThematicBreak),
NonSelectable(NonSelectable::CodeBlock(CodeBlock{variant: CodeVariant::Code(None), ..})),
Expand Down Expand Up @@ -1313,43 +1313,43 @@ pub mod tests {
#[test]
fn text() {
check_render(
vec![MdElem::Inline(Inline::Text {
vec![MdElem::Inline(Inline::Text(Text {
variant: TextVariant::Plain,
value: "hello world".to_string(),
})],
}))],
indoc! {"hello world"},
);
}

#[test]
fn code() {
check_render(
vec![MdElem::Inline(Inline::Text {
vec![MdElem::Inline(Inline::Text(Text {
variant: TextVariant::Code,
value: "hello world".to_string(),
})],
}))],
indoc! {"`hello world`"},
);
}

#[test]
fn math() {
check_render(
vec![MdElem::Inline(Inline::Text {
vec![MdElem::Inline(Inline::Text(Text {
variant: TextVariant::Math,
value: "hello world".to_string(),
})],
}))],
indoc! {"$hello world$"},
);
}

#[test]
fn html() {
check_render(
vec![MdElem::Inline(Inline::Text {
vec![MdElem::Inline(Inline::Text(Text {
variant: TextVariant::Html,
value: "<a hello />".to_string(),
})],
}))],
indoc! {"<a hello />"},
);
}
Expand Down Expand Up @@ -1494,14 +1494,14 @@ pub mod tests {

fn check_link(link: LinkDefinition, expect: &str) {
let nodes = vec![
MdElem::Inline(Inline::Link {
MdElem::Inline(Inline::Link(Link {
text: vec![
mdq_inline!("hello "),
mdq_inline!(span Emphasis [mdq_inline!("world")]),
mdq_inline!("!"),
],
link_definition: link,
}),
})),
m_node!(MdElem::Block::LeafBlock::ThematicBreak),
];
check_render(nodes, expect);
Expand Down Expand Up @@ -1647,10 +1647,10 @@ pub mod tests {

fn check_image(link: LinkDefinition, expect: &str) {
let nodes = vec![
MdElem::Inline(Inline::Image {
MdElem::Inline(Inline::Image(Image {
alt: "hello _world_!".to_string(),
link,
}),
})),
m_node!(MdElem::Block::LeafBlock::ThematicBreak),
];
check_render(nodes, expect);
Expand Down Expand Up @@ -1711,14 +1711,14 @@ pub mod tests {
md_elems![Block::LeafBlock::Paragraph {
body: vec![
mdq_inline!("Hello, "),
Inline::Link {
m_node!(Inline::Link {
text: vec![mdq_inline!("world"),],
link_definition: LinkDefinition {
url: "https://example.com".to_string(),
title: None,
reference: LinkReference::Full("1".to_string()),
}
},
}),
mdq_inline!("! This is interesting"),
Inline::Footnote(Footnote {
label: "a".to_string(),
Expand Down Expand Up @@ -1843,22 +1843,22 @@ pub mod tests {
label: "c".to_string(),
text: md_elems!["footnote 2"]
}),
Inline::Link {
m_node!(Inline::Link {
text: vec![mdq_inline!("b-text")],
link_definition: LinkDefinition {
url: "https://example.com/b".to_string(),
title: None,
reference: LinkReference::Full("b".to_string()),
},
},
Inline::Link {
}),
m_node!(Inline::Link {
text: vec![mdq_inline!("a-text")],
link_definition: LinkDefinition {
url: "https://example.com/a".to_string(),
title: None,
reference: LinkReference::Full("a".to_string()),
},
},
}),
]
}],
indoc! {r#"
Expand All @@ -1878,14 +1878,14 @@ pub mod tests {
title: vec![mdq_inline!("First section")],
body: md_elems![Block::LeafBlock::Paragraph {
body: vec![
Inline::Link {
m_node!(Inline::Link {
text: vec![mdq_inline!("link description")],
link_definition: LinkDefinition {
url: "https://exampl.com".to_string(),
title: None,
reference: LinkReference::Full("1".to_string()),
},
},
}),
mdq_inline!(" and then a thought"),
Inline::Footnote(Footnote {
label: "a".to_string(),
Expand Down
26 changes: 13 additions & 13 deletions src/fmt_str.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use crate::tree::{Inline, TextVariant};
use crate::tree::{Formatting, Image, Inline, Link, Text, TextVariant};
use std::borrow::Borrow;

pub fn inlines_to_plain_string<N: Borrow<Inline>>(inlines: &[N]) -> String {
Expand All @@ -15,14 +15,14 @@ fn build_inlines<N: Borrow<Inline>>(out: &mut String, inlines: &[N]) {

fn build_inline(out: &mut String, elem: &Inline) {
match elem {
Inline::Span { children, .. } => build_inlines(out, children),
Inline::Text { variant, value, .. } => {
Inline::Formatting(Formatting { children, .. }) => build_inlines(out, children),
Inline::Text(Text { variant, value, .. }) => {
if !matches!(variant, TextVariant::Html) {
out.push_str(value)
}
}
Inline::Link { text, .. } => build_inlines(out, text),
Inline::Image { alt, .. } => out.push_str(alt),
Inline::Link(Link { text, .. }) => build_inlines(out, text),
Inline::Image(Image { alt, .. }) => out.push_str(alt),
Inline::Footnote(footnote) => {
out.push_str("[^");
out.push_str(&footnote.label);
Expand All @@ -36,18 +36,18 @@ mod tests {
use super::*;
use indoc::indoc;

use crate::tree::{Block, Inline, LeafBlock, MdElem, ReadOptions, SpanVariant, TextVariant};
use crate::tree::{Block, FormattingVariant, Inline, LeafBlock, MdElem, ReadOptions, TextVariant};
use crate::unwrap;
use markdown::ParseOptions;

crate::variants_checker!(VARIANTS_CHECKER = Inline {
Span { variant: SpanVariant::Delete, .. },
Span { variant: SpanVariant::Emphasis, .. },
Span { variant: SpanVariant::Strong, .. },
Text { variant: TextVariant::Plain, .. },
Text { variant: TextVariant::Code, .. },
Text { variant: TextVariant::Math, .. },
Text { variant: TextVariant::Html, .. },
Formatting(Formatting{ variant: FormattingVariant::Delete, .. }),
Formatting(Formatting{ variant: FormattingVariant::Emphasis, .. }),
Formatting(Formatting{ variant: FormattingVariant::Strong, .. }),
Text(Text { variant: TextVariant::Plain, .. }),
Text(Text { variant: TextVariant::Code, .. }),
Text(Text { variant: TextVariant::Math, .. }),
Text(Text { variant: TextVariant::Html, .. }),
Link { .. },
Image { .. },
Footnote(_),
Expand Down
27 changes: 14 additions & 13 deletions src/select/selector.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,8 @@ use crate::select::base::Selector;
use crate::select::interface::{ParseError, ParseErrorReason, ParseResult, SelectResult};
use crate::select::list_item::{ListItemSelector, ListItemType};
use crate::select::section::SectionSelector;
use crate::tree::Inline;
use crate::tree::{Formatting, Image, Inline, Link, Text};
use crate::tree_ref::{ListItemRef, MdElemRef, NonSelectable};
use crate::wrap_mdq_refs;

#[derive(Debug, PartialEq)]
pub enum MdqRefSelector {
Expand Down Expand Up @@ -91,17 +90,8 @@ impl MdqRefSelector {
match node {
MdElemRef::Section(s) => MdElemRef::wrap_vec(&s.body),
MdElemRef::ListItem(ListItemRef(_, item)) => MdElemRef::wrap_vec(&item.item),
MdElemRef::Inline(inline) => match inline {
Inline::Span { children, .. } => children.iter().map(|child| MdElemRef::Inline(child)).collect(),
Inline::Footnote(footnote) => MdElemRef::wrap_vec(&footnote.text),
Inline::Link { .. } => {
// TODO need to return an MdqNodeRef::Link
Vec::new()
}
Inline::Text { .. } | Inline::Image { .. } => Vec::new(),
},
MdElemRef::NonSelectable(elem) => match elem {
NonSelectable::Paragraph(p) => wrap_mdq_refs!(Inline: &p.body),
NonSelectable::Paragraph(p) => p.body.iter().map(|child| child.into()).collect(),
NonSelectable::BlockQuote(b) => MdElemRef::wrap_vec(&b.body),
NonSelectable::List(list) => {
let mut idx = list.starting_index;
Expand All @@ -120,13 +110,24 @@ impl MdqRefSelector {
for row in &table.rows {
for col in row {
for cell in col {
result.push(MdElemRef::Inline(cell));
result.push(MdElemRef::NonSelectable(NonSelectable::Inline(cell)));
}
}
}
result
}
NonSelectable::ThematicBreak | NonSelectable::CodeBlock(_) => Vec::new(),
NonSelectable::Inline(inline) => match inline {
Inline::Formatting(Formatting { children, .. }) => {
children.iter().map(|child| child.into()).collect()
}
Inline::Footnote(footnote) => MdElemRef::wrap_vec(&footnote.text),
Inline::Link(Link { .. }) => {
// TODO need to return an MdqNodeRef::Link
Vec::new()
}
Inline::Text(Text { .. }) | Inline::Image(Image { .. }) => Vec::new(),
},
},
}
}
Expand Down
Loading

0 comments on commit 78ae814

Please sign in to comment.