use writedown::{ast, Render};
#[derive(Debug)]
pub enum Node {
Section(Section),
Paragraph(Paragraph),
Block(Block),
Unknown,
}
impl Render for Node {
fn render(&self) -> String {
match &self {
Node::Section(s) => s.render(),
Node::Paragraph(p) => p.render(),
Node::Block(b) => b.render(),
_ => unimplemented!(),
}
}
}
impl From<ast::Node> for Node {
fn from(node: ast::Node) -> Self {
match node {
ast::Node::Section(v) => Node::Section(v.into()),
ast::Node::Paragraph(v) => Node::Paragraph(v.into()),
ast::Node::Block(v) => Node::Block(v.into()),
_ => unimplemented!(),
}
}
}
#[derive(Debug)]
pub struct Section {
pub level: usize,
pub title: String,
pub child: Vec<Node>,
}
#[derive(Debug)]
pub struct Paragraph {
pub child: Vec<ParagraphChild>,
}
#[derive(Debug)]
pub enum ParagraphChild {
Sentence(String),
Func(ast::Func),
}
#[derive(Debug)]
pub enum Block {
Code(String),
}
impl From<ast::Section> for Section {
fn from(v: ast::Section) -> Section {
let mut child: Vec<Node> = Vec::new();
for c in v.child {
child.push(c.into());
}
Section {
level: v.level,
title: v.title,
child,
}
}
}
impl From<ast::Paragraph> for Paragraph {
fn from(v: ast::Paragraph) -> Paragraph {
let mut child = Vec::new();
for c in v.child {
child.push(c.into());
}
Paragraph { child }
}
}
impl From<ast::ParagraphChild> for ParagraphChild {
fn from(v: ast::ParagraphChild) -> ParagraphChild {
match v {
ast::ParagraphChild::Sentence(s) => ParagraphChild::Sentence(s),
ast::ParagraphChild::Func(f) => ParagraphChild::Func(f),
}
}
}
impl From<ast::Block> for Block {
fn from(v: ast::Block) -> Block {
match v {
ast::Block::Code(b) => Block::Code(b),
_ => unimplemented!(),
}
}
}
impl Render for Section {
fn render(&self) -> String {
let l = format!("{}", self.level + 1);
let mut cs = String::new();
for c in &self.child {
cs += &c.render();
}
format!("<h{}>{}</h{}>\n{}", l, self.title, l, cs)
}
}
impl Render for Paragraph {
fn render(&self) -> String {
let mut cs = String::new();
for c in &self.child {
cs += &c.render();
}
format!("<p>{}</p>\n", cs)
}
}
impl Render for ParagraphChild {
fn render(&self) -> String {
match &self {
ParagraphChild::Sentence(s) => s.to_string(),
ParagraphChild::Func(_f) => unimplemented!(),
}
}
}
impl Render for Block {
fn render(&self) -> String {
match &self {
Block::Code(code) => format!("\n<pre><code>{}</code></pre>", str2html(code)),
}
}
}
pub fn str2html(s: &str) -> String {
s.replace("<", "<").replace(">", ">")
}