This repository has been archived by the owner on Nov 14, 2021. It is now read-only.
forked from dobkeratops/rustfind
-
Notifications
You must be signed in to change notification settings - Fork 0
/
htmlwriter.rs
138 lines (132 loc) · 4.33 KB
/
htmlwriter.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
use rf_common::*;
use std::iter::range_inclusive;
pub struct HtmlWriter {
pub doc:~str,
pub tag_stack:~[~str],
pub xlat:HashMap<char, ~str>,
}
/// convert u8 into html char.
fn mk_xlat_table()-> HashMap<char,~str>
{
let mut xlat= HashMap::new();
// let mut i=0u8;
for i in range_inclusive(0u8, 255) {
xlat.insert(i as char,
match i as char{
' ' =>~" ",
'<' =>~"<",
'>' =>~">",
'&' =>~"&",
'\t' =>~" ",
c => str::from_char(c)//x.slice(0,1)
});
}
xlat
}
/// helper object for building html docs, puts tags in a stack for convinient close
impl<'a> HtmlWriter {
pub fn new()->HtmlWriter { HtmlWriter { doc:~"", tag_stack:~[], xlat:mk_xlat_table()}}
pub fn write_quoted_str(&'a mut self, a:&str)->&'a mut HtmlWriter {
self.doc.push_str("\"");
self.doc.push_str(a);
self.doc.push_str("\"");
self
}
pub fn begin_tag_ext(&'a mut self, tag_name:&str, key_values:&[(~str,~str)])->&'a mut HtmlWriter {
self.write_tag_sub(tag_name,key_values,false);
self.tag_stack.push(tag_name.to_str());
self
}
pub fn begin_tag(&'a mut self, tag_name:&str)->&'a mut HtmlWriter {
self.begin_tag_ext(tag_name,&[])
}
pub fn begin_tag_check(&'a mut self, tag_name:&str)->int {
self.begin_tag_ext(tag_name,&[]);
self.depth()
}
pub fn write_tag_ext(&'a mut self, tag_name:&str, key_values:&[(~str,~str)])->&'a mut HtmlWriter {
self.write_tag_sub(tag_name,key_values,true)
}
pub fn write_tag(&'a mut self, tag_name:&str)->&'a mut HtmlWriter {
self.write_tag_sub(tag_name,&[],true);
self
}
fn write_tag_sub(&'a mut self, tag_name:&str, key_values:&[(~str,~str)], closed:bool)->&'a mut HtmlWriter {
self.doc.push_str("<"+tag_name);
for &(ref k,ref v) in key_values.iter() {
self.doc.push_str(" ");
self.doc.push_str(*k);
self.doc.push_str(&"=");
self.write_quoted_str(*v);
}
if closed { self.doc.push_str("/"); }
self.doc.push_str(">");
self
}
pub fn end_tag(&'a mut self)->&'a mut HtmlWriter {
match self.tag_stack.pop() {
Some(tag_name) => {
self.doc.push_str("</");
self.doc.push_str(tag_name);
self.doc.push_str(">");
},
None => ()
};
self
}
pub fn depth(&self)->int { self.tag_stack.len() as int }
pub fn end_tag_check(&'a mut self,depth:int) {
self.check_depth(depth);
self.end_tag();
}
#[allow(dead_code)]
pub fn end_all_tags(&'a mut self)->&'a mut HtmlWriter {
while self.tag_stack.len()>0 {
self.end_tag();
}
self
}
pub fn write(&'a mut self,t:&str)->&'a mut HtmlWriter {
for x in t.chars() {
self.doc.push_str(self.xlat.get(&x).clone());
};
self
}
// todo rename "write_raw?"
#[allow(dead_code)]
pub fn write_html(&'a mut self,t:&str)->&'a mut HtmlWriter {
self.doc.push_str(t);
self
}
pub fn write_tagged(&'a mut self, tagname:&str, text:&str)->&'a mut HtmlWriter {
self.begin_tag(tagname).write(text).end_tag()
}
pub fn writeln_tagged(&'a mut self, tagname:&str, text:&str)->&'a mut HtmlWriter {
self.begin_tag(tagname).write(text).end_tag().write_tag("br")
}
pub fn writeln(&'a mut self, text:&str)->&'a mut HtmlWriter {
self.write(text).write_tag("br")
}
pub fn write_u8_(&'a mut self, x:u8)->&'a mut HtmlWriter {
self.doc.push_str(self.xlat.get(&(x as char)).to_owned());
self
}
pub fn begin_tag_anchor(&'a mut self, anchor:&str)->int {
self.begin_tag_ext("a",[(~"id",anchor.to_owned())]);
self.depth()
}
pub fn begin_tag_link(&'a mut self, link:&str)->int {
self.begin_tag_ext("a",[(~"href",link.to_owned())]);
self.depth()
}
#[allow(dead_code)]
pub fn write_space(&'a mut self)->&'a mut HtmlWriter {
self.doc.push_str(" ");
self
}
pub fn check_depth(&self,depth:int) {
if self.depth() !=depth {
fail!(format!("check_depth should be {} it is {}", depth, self.depth()))
}
}
}