diff options
Diffstat (limited to 'code/src/markdown/mod.rs')
-rw-r--r-- | code/src/markdown/mod.rs | 50 |
1 files changed, 43 insertions, 7 deletions
diff --git a/code/src/markdown/mod.rs b/code/src/markdown/mod.rs index dee923c..7ee18a2 100644 --- a/code/src/markdown/mod.rs +++ b/code/src/markdown/mod.rs @@ -7,7 +7,7 @@ use pest_derive::Parser; use crate::{html::escape, syntax_highlight::syntax_highlight}; #[derive(Parser)] -#[grammar = "grammar/markdown.pest"] +#[grammar = "src/markdown/parser.pest"] struct Grammar; pub fn render(s: &str) -> String { @@ -27,16 +27,28 @@ pub fn render_pairs(p: Pairs<Rule>) -> String { pub fn render_ast(p: Pair<Rule>) -> String { match p.as_rule() { Rule::block => render_pairs(p.into_inner()), - Rule::header => format!("<h1>{}</h1>", render_pairs(p.into_inner())), + Rule::header => { + let mut level = 0; + while p.as_str()[level..].starts_with("#") { + level += 1 + } + format!("<h{level}>{}</h{level}>", render_pairs(p.into_inner())) + } Rule::paragraph => format!("<p>{}</p>", render_pairs(p.into_inner())), + Rule::style_italic => format!("<i>{}</i>", render_pairs(p.into_inner())), + Rule::style_bold => format!("<b>{}</b>", render_pairs(p.into_inner())), + Rule::style_code => format!("<code>{}</code>", p.into_inner().next().unwrap().as_str()), Rule::unordered_list => format!("<ul>{}</ul>", render_pairs(p.into_inner())), Rule::ordered_list => format!("<ol>{}</ol>", render_pairs(p.into_inner())), Rule::unordered_list_item | Rule::ordered_list_item => { format!("<li>{}</li>", render_pairs(p.into_inner())) } - Rule::style_italic => format!("<i>{}</i>", render_pairs(p.into_inner())), - Rule::style_bold => format!("<b>{}</b>", render_pairs(p.into_inner())), - Rule::style_code => format!("<code>{}</code>", p.into_inner().next().unwrap().as_str()), + Rule::hyperlink => { + let k = p.into_inner().collect::<Vec<_>>(); + let label = k[0].as_str(); + let target = k[1].as_str(); + format!("<a href=\"{}\">{}</a>", escape(target), escape(label)) + } Rule::span => render_pairs(p.into_inner()), Rule::EOI => "".to_string(), Rule::code_block => { @@ -48,11 +60,35 @@ pub fn render_ast(p: Pair<Rule>) -> String { syntax_highlight(lang, &inner).unwrap_or_else(|| escape(&inner)) ) } - Rule::inline_latex => format!("<span>TODO: Inline latex</span>"), - Rule::latex_block => format!("<p>TODO: Latex block</p>"), + Rule::inline_latex => fix_katex( + &katex::render_with_opts( + &p.into_inner().as_str(), + &katex::OptsBuilder::default().build().unwrap(), + ) + .unwrap(), + ), + Rule::latex_block => fix_katex( + &katex::render_with_opts( + &p.into_inner().as_str(), + &katex::OptsBuilder::default() + .display_mode(true) + .build() + .unwrap(), + ) + .unwrap(), + ), Rule::text => escape(p.as_str()), _ => todo!("{:?}", p.as_rule()), } } + +// TODO this is *really* bad fix +fn fix_katex<'a>(s: &str) -> String { + let e = s.find("<span class=\"katex-html\"").unwrap(); + s[0..e].replace( + "<mspace linebreak=\"newline\"></mspace>", + "</mrow></semantics></math><math xmlns=\"http://www.w3.org/1998/Math/MathML\" display=\"block\"><semantics><mrow>", + ) +} |