From 5316b954323a4d7bee492a3997bae35dd107e44a Mon Sep 17 00:00:00 2001 From: metamuffin Date: Mon, 26 Sep 2022 17:08:20 +0200 Subject: hyperlinks --- code/grammar/markdown.pest | 27 ----------------------- code/src/markdown/mod.rs | 50 +++++++++++++++++++++++++++++++++++++------ code/src/markdown/parser.pest | 29 +++++++++++++++++++++++++ code/src/markdown/parser.rs | 26 ---------------------- 4 files changed, 72 insertions(+), 60 deletions(-) delete mode 100644 code/grammar/markdown.pest create mode 100644 code/src/markdown/parser.pest delete mode 100644 code/src/markdown/parser.rs diff --git a/code/grammar/markdown.pest b/code/grammar/markdown.pest deleted file mode 100644 index e387182..0000000 --- a/code/grammar/markdown.pest +++ /dev/null @@ -1,27 +0,0 @@ -// WHITESPACE = _{ " " | "\t" | NEWLINE } - -file = _{ SOI ~ NEWLINE* ~ (block ~ NEWLINE*)* ~ EOI } - -block = { code_block | latex_block | header | unordered_list | ordered_list | paragraph } - header = { "#"+ ~ span } - unordered_list = { unordered_list_item+ } - unordered_list_item = { "-" ~ span ~ NEWLINE } - ordered_list = { ordered_list_item+ } - ordered_list_item = { ASCII_DIGIT+ ~ "." ~ span ~ NEWLINE } - paragraph = { span } - code_block = { "```" ~ code_block_lang ~ NEWLINE ~ code_block_inner ~ "```" } - code_block_lang = { ASCII_ALPHANUMERIC* } - code_block_inner = { (!"```" ~ ANY)* } - latex_block = { "$$" ~ latex_block_inner ~ "$$" } - latex_block_inner = { (!"$$" ~ ANY)* } - -span = { (style_bold | style_italic | style_code | inline_latex | text)+ } - style_bold = { "**" ~ text ~ "**" } - style_italic = { "_" ~ text ~ "_" } - style_code = { "`" ~ code_inner ~ "`" } - code_inner = { (!"`" ~ ANY)+ } - inline_latex = { "$" ~ latex_inner ~ "$" } - latex_inner = { (!"$" ~ ANY)+ } - - text = { (!("\n" ~ forbidden_span_wrap | "*" | "_" | "`" | "$") ~ ANY)+ } - forbidden_span_wrap = _{ "\n" | "-" | ASCII_DIGIT+ ~ "." } 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) -> String { pub fn render_ast(p: Pair) -> String { match p.as_rule() { Rule::block => render_pairs(p.into_inner()), - Rule::header => format!("

{}

", render_pairs(p.into_inner())), + Rule::header => { + let mut level = 0; + while p.as_str()[level..].starts_with("#") { + level += 1 + } + format!("{}", render_pairs(p.into_inner())) + } Rule::paragraph => format!("

{}

", render_pairs(p.into_inner())), + Rule::style_italic => format!("{}", render_pairs(p.into_inner())), + Rule::style_bold => format!("{}", render_pairs(p.into_inner())), + Rule::style_code => format!("{}", p.into_inner().next().unwrap().as_str()), Rule::unordered_list => format!("
    {}
", render_pairs(p.into_inner())), Rule::ordered_list => format!("
    {}
", render_pairs(p.into_inner())), Rule::unordered_list_item | Rule::ordered_list_item => { format!("
  • {}
  • ", render_pairs(p.into_inner())) } - Rule::style_italic => format!("{}", render_pairs(p.into_inner())), - Rule::style_bold => format!("{}", render_pairs(p.into_inner())), - Rule::style_code => format!("{}", p.into_inner().next().unwrap().as_str()), + Rule::hyperlink => { + let k = p.into_inner().collect::>(); + let label = k[0].as_str(); + let target = k[1].as_str(); + format!("{}", 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) -> String { syntax_highlight(lang, &inner).unwrap_or_else(|| escape(&inner)) ) } - Rule::inline_latex => format!("TODO: Inline latex"), - Rule::latex_block => format!("

    TODO: Latex block

    "), + 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("", + "", + ) +} diff --git a/code/src/markdown/parser.pest b/code/src/markdown/parser.pest new file mode 100644 index 0000000..22563d4 --- /dev/null +++ b/code/src/markdown/parser.pest @@ -0,0 +1,29 @@ +file = _{ SOI ~ NEWLINE* ~ (block ~ NEWLINE*)* ~ EOI } + +block = { code_block | latex_block | header | unordered_list | ordered_list | paragraph } + header = { "#"{1,6} ~ span } + unordered_list = { unordered_list_item+ } + unordered_list_item = { "-" ~ span ~ NEWLINE } + ordered_list = { ordered_list_item+ } + ordered_list_item = { ASCII_DIGIT+ ~ "." ~ span ~ NEWLINE } + paragraph = { span } + code_block = { "```" ~ code_block_lang ~ NEWLINE ~ code_block_inner ~ "```" } + code_block_lang = { ASCII_ALPHANUMERIC* } + code_block_inner = { (!"```" ~ ANY)* } + latex_block = { "$$" ~ latex_block_inner ~ "$$" } + latex_block_inner = { (!"$$" ~ ANY)* } + + +span = { (style_bold | style_italic | style_code | inline_latex | hyperlink | text)+ } + style_bold = { "**" ~ span ~ "**" } + style_italic = { "_" ~ span ~ "_" } + style_code = { "`" ~ code_inner ~ "`" } + code_inner = { (!"`" ~ ANY)+ } + inline_latex = { "$" ~ latex_inner ~ "$" } + latex_inner = { (!"$" ~ ANY)+ } + hyperlink = { "[" ~ hyperlink_label ~ "](" ~ hyperlink_location ~ ")" } + hyperlink_label = { span } + hyperlink_location = { (!")" ~ANY)+ } + + text = { (!("[" | "]" | "*" | "_" | "`" | "$" | ("\n" ~ forbidden_span_wrap)) ~ ANY)+ } + forbidden_span_wrap = _{ "\n" | "-" | ASCII_DIGIT+ ~ "." } diff --git a/code/src/markdown/parser.rs b/code/src/markdown/parser.rs deleted file mode 100644 index 8876335..0000000 --- a/code/src/markdown/parser.rs +++ /dev/null @@ -1,26 +0,0 @@ -use pest::Parser; -use pest_derive::Parser; - -#[derive(Debug, Clone)] -pub enum Block { - Header(usize, Vec), - Paragraph(Vec), - Blockquote(Vec), - CodeBlock(Option, String), - LatexBlock(String), - OrderedList(Vec>), - UnorderedList(Vec>), - Raw(String), - Hr, -} -#[derive(Debug, Clone)] -pub enum Span { - Break, - Text(String), - Code(String), - Link(String, String), - Image(String, String), - Emphasis(Vec), - Strong(Vec), - Latex(String), -} -- cgit v1.2.3-70-g09d2