1use crate::html_element::HtmlElement;
2use crate::markdown_writer::{HandleTag, MarkdownWriter, StartTagOutcome};
3
4pub struct ParagraphHandler;
5
6impl HandleTag for ParagraphHandler {
7 fn should_handle(&self, _tag: &str) -> bool {
8 true
9 }
10
11 fn handle_tag_start(
12 &mut self,
13 tag: &HtmlElement,
14 writer: &mut MarkdownWriter,
15 ) -> StartTagOutcome {
16 if tag.is_inline() && writer.is_inside("p") {
17 if let Some(parent) = writer.current_element_stack().iter().last() {
18 if !parent.is_inline() {
19 if !(writer.markdown.ends_with(' ') || writer.markdown.ends_with('\n')) {
20 writer.push_str(" ");
21 }
22 }
23 }
24 }
25
26 match tag.tag.as_str() {
27 "p" => writer.push_blank_line(),
28 _ => {}
29 }
30
31 StartTagOutcome::Continue
32 }
33}
34
35pub struct HeadingHandler;
36
37impl HandleTag for HeadingHandler {
38 fn should_handle(&self, tag: &str) -> bool {
39 match tag {
40 "h1" | "h2" | "h3" | "h4" | "h5" | "h6" => true,
41 _ => false,
42 }
43 }
44
45 fn handle_tag_start(
46 &mut self,
47 tag: &HtmlElement,
48 writer: &mut MarkdownWriter,
49 ) -> StartTagOutcome {
50 match tag.tag.as_str() {
51 "h1" => writer.push_str("\n\n# "),
52 "h2" => writer.push_str("\n\n## "),
53 "h3" => writer.push_str("\n\n### "),
54 "h4" => writer.push_str("\n\n#### "),
55 "h5" => writer.push_str("\n\n##### "),
56 "h6" => writer.push_str("\n\n###### "),
57 _ => {}
58 }
59
60 StartTagOutcome::Continue
61 }
62
63 fn handle_tag_end(&mut self, tag: &HtmlElement, writer: &mut MarkdownWriter) {
64 match tag.tag.as_str() {
65 "h1" | "h2" | "h3" | "h4" | "h5" | "h6" => writer.push_blank_line(),
66 _ => {}
67 }
68 }
69}
70
71pub struct ListHandler;
72
73impl HandleTag for ListHandler {
74 fn should_handle(&self, tag: &str) -> bool {
75 match tag {
76 "ul" | "ol" | "li" => true,
77 _ => false,
78 }
79 }
80
81 fn handle_tag_start(
82 &mut self,
83 tag: &HtmlElement,
84 writer: &mut MarkdownWriter,
85 ) -> StartTagOutcome {
86 match tag.tag.as_str() {
87 "ul" | "ol" => writer.push_newline(),
88 "li" => writer.push_str("- "),
89 _ => {}
90 }
91
92 StartTagOutcome::Continue
93 }
94
95 fn handle_tag_end(&mut self, tag: &HtmlElement, writer: &mut MarkdownWriter) {
96 match tag.tag.as_str() {
97 "ul" | "ol" => writer.push_newline(),
98 "li" => writer.push_newline(),
99 _ => {}
100 }
101 }
102}
103
104pub struct StyledTextHandler;
105
106impl HandleTag for StyledTextHandler {
107 fn should_handle(&self, tag: &str) -> bool {
108 match tag {
109 "strong" | "em" => true,
110 _ => false,
111 }
112 }
113
114 fn handle_tag_start(
115 &mut self,
116 tag: &HtmlElement,
117 writer: &mut MarkdownWriter,
118 ) -> StartTagOutcome {
119 match tag.tag.as_str() {
120 "strong" => writer.push_str("**"),
121 "em" => writer.push_str("_"),
122 _ => {}
123 }
124
125 StartTagOutcome::Continue
126 }
127
128 fn handle_tag_end(&mut self, tag: &HtmlElement, writer: &mut MarkdownWriter) {
129 match tag.tag.as_str() {
130 "strong" => writer.push_str("**"),
131 "em" => writer.push_str("_"),
132 _ => {}
133 }
134 }
135}