1use crate::read_ebml::Process;
9use crate::read_ebml::Section;
10use crate::read_ebml::SubStep;
11use crate::read_ebml::Action;
12use crate::read_ebml::Requirement;
13use crate::read_ebml::Table;
14
15use std::fs::File;
16use std::fs::OpenOptions;
17use std::io::Write;
18
19pub fn generate_complete_html(filename:&String, p:&Process) {
24
25 let mut html_file = OpenOptions::new()
27 .read(true)
28 .write(true)
29 .create(true)
30 .open(filename)
31 .expect("cannot open file");
32
33 compose_top_of_html_file(&mut html_file);
35
36 compose_html_head(&mut html_file, &p);
38
39 compose_html_body(&mut html_file,&p,p.get_all_sections());
41
42 compose_bottom_of_html_file(&mut html_file);
44}
45
46fn compose_top_of_html_file(f:&mut File) {
48 f.write(b"<!DOCTYPE html>\n").expect("write failed");
49 f.write(b"<html lang=\"en-US\">\n\n").expect("write failed");
50}
51
52fn compose_bottom_of_html_file(f:&mut File) {
54 f.write(b"</html>").expect("write failed");
55}
56
57fn compose_html_head(f:&mut File,p:&Process) {
59 f.write(b"\t<head>\n").expect("write failed");
60
61 let temp_str = String::from("\t\t<title>") + p.get_number() + " \"" + p.get_title() + "\"</title>\n";
62 f.write(temp_str.as_bytes()).expect("write failed");
63 f.write(b"\t\t<meta charset=\"utf-8\" />\n").expect("write failed");
64 let temp_str = String::from("\t\t<meta name = \"keywords\" content = \"") + p.get_subject() + ", " + p.get_product() + "\" />\n";
65 f.write(temp_str.as_bytes()).expect("write failed");
66 let temp_str = String::from("\t\t<meta name = \"description\" content = \"") + p.get_number() + " " + p.get_title() + "\" />\n";
67 f.write(temp_str.as_bytes()).expect("write failed");
68 let temp_str = String::from("\t\t<meta name = \"author\" content = \"") + p.get_author() + "\" />\n";
69 f.write(temp_str.as_bytes()).expect("write failed");
70 f.write(b"\t\t<meta http-equiv = \"Content-Type\" content = \"text/html; charset = UTF-8\" />\n").expect("write failed");
71 f.write(b"\t\t<link rel=\"shortcut icon\" sizes=\"16x16 32x32 48x48\" type=\"image/png\" href=\"../assets/favicon.png\" />\n").expect("write failed");
72 f.write(b"\t\t<link rel=\"apple-touch-icon\" sizes=\"180x180\" href=\"../assets/favicon.png\" />\n").expect("write failed");
73 f.write(b"\t\t<link rel=\"mask-icon\" href=\"../assets/favicon.svg\" color=\"#000000\" />\n\n").expect("write failed");
74
75 f.write(b"\t\t<!-- The stanhope.css applies to every process, regardless of program -->\n").expect("write failed");
76 f.write(b"\t\t<link rel=\"stylesheet\" href=\"../assets/stanhope.css\"/>\n").expect("write failed");
77 for template in p.get_all_templates() {
80 let temp_str = String::from("\t\t<link rel=\"stylesheet\" href=\"../assets/") + &template + "\"/>\n";
81 f.write(temp_str.as_bytes()).expect("write failed");
82 }
83 f.write(b"\t</head>\n\n").expect("write failed");
84}
85
86fn compose_html_body(f:&mut File,p:&Process,s:&Vec<Section>) {
97 f.write(b"\t<body>\n\n").expect("write failed");
98 f.write(b"\t\t<div id=\"classification-header\" class=\"classification\"><p></p></div>\n").expect("write failed");
99
100 compose_html_body_title_page(f,p);
102 compose_html_body_rev_req_page(f,p);
103 compose_html_body_toc(f,p,s);
104
105 compose_html_body_section(f,p,s);
107 compose_html_body_end_of_sections_and_banners(f,p);
108
109 f.write(b"\t\t<div id=\"classification-footer\" class=\"classification\"><p></p></div>\n\n").expect("write failed");
110 f.write(b"\t</body>\n\n").expect("write failed");
111}
112
113fn compose_html_body_title_page(f:&mut File, p:&Process) {
117 f.write(b"\t\t<table>\n\n").expect("write failed");
119 f.write(b"\t\t\t<thead><tr><td>\n").expect("write failed");
120 f.write(b"\t\t\t\t<div class=\"header-space\"> </div>\n").expect("write failed");
121 f.write(b"\t\t\t</td></tr></thead>\n\n").expect("write failed");
122 f.write(b"\t\t<tbody>\n\n").expect("write failed");
123 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
124 f.write(b"\t\t\t\t<section class=\"hide-on-screen\">\n").expect("write failed");
125 f.write(b"\t\t\t\t\t<div id=\"title-page\">\n").expect("write failed");
126
127 let temp_str = String::from("\t\t\t\t\t\t<div id=\"title-page-title\">") + p.get_title() + "</div>\n";
129 f.write(temp_str.as_bytes()).expect("write failed");
130
131 let proxi = Process::new();
133 let mut process_type = "".to_string();
134 if !(p.get_process_type() == proxi.get_process_type()) { process_type = "<br/>".to_owned() + p.get_process_type(); }
135 let temp_str = String::from("\t\t\t\t\t\t<div id=\"title-page-docno\">") + p.get_number() + &process_type + "<br/>Revision " + p.get_revision() + "</div>\n";
136 f.write(temp_str.as_bytes()).expect("write failed");
137
138 f.write(b"\t\t\t\t\t\t<div id=\"title-page-authors\">\n").expect("write failed");
140 f.write(b"\t\t\t\t\t\t\t<table>\n").expect("write failed");
141 f.write(b"\t\t\t\t\t\t\t\t<thead>\n").expect("write failed");
142 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
143 let temp_str = String::from("\t\t\t\t\t\t\t\t\t\t<td>Written by:<br/>") + p.get_author() + "</td>\n";
144 f.write(temp_str.as_bytes()).expect("write failed");
145 let temp_str = String::from("\t\t\t\t\t\t\t\t\t\t<td>Reviewed by:<br/>") + p.get_reviewer() + "</td>\n";
146 f.write(temp_str.as_bytes()).expect("write failed");
147 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
148 f.write(b"\t\t\t\t\t\t\t\t</thead>\n").expect("write failed");
149 f.write(b"\t\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
150 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
151 f.write(b"\t\t\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
152 f.write(b"\t\t\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
153 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
154 f.write(b"\t\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
155 f.write(b"\t\t\t\t\t\t\t</table>\n").expect("write failed");
156 f.write(b"\t\t\t\t\t\t</div>\n").expect("write failed");
157
158 f.write(b"\t\t\t\t\t\t<div id=\"title-page-fine-print\"></div>\n").expect("write failed");
160
161 f.write(b"\t\t\t\t\t\t<div id=\"title-page-no-ai\"></div>\n").expect("write failed");
163
164 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
166 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
167 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
168}
169
170fn compose_html_body_rev_req_page(f:&mut File, p:&Process) {
172 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
174 f.write(b"\t\t\t\t<section class=\"\">\n").expect("write failed");
175 f.write(b"\t\t\t\t\t<div id=\"revision-page\">\n").expect("write failed");
176 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">Revision Table for ").to_string() + p.get_number() + " \"" + p.get_title() + "\"</span>\n";
177 f.write(temp_str.as_bytes()).expect("write failed");
178
179 f.write(b"\t\t\t\t\t\t<div class=\"revision-table-container\">\n").expect("write failed");
181 f.write(b"\t\t\t\t\t\t\t<table>\n").expect("write failed");
182 f.write(b"\t\t\t\t\t\t\t\t<thead>\n").expect("write failed");
183 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
184 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"revision-table-rev\">Rev</td>\n").expect("write failed");
185 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"revision-table-change\">Description of Change</td>\n").expect("write failed");
186 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
187 f.write(b"\t\t\t\t\t\t\t\t</thead>\n").expect("write failed");
188 f.write(b"\t\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
189
190 let mut rev_counter = 0;
193 let len_revs = p.get_all_revisions().len();
194 for rev in p.get_all_revisions().iter().rev() {
195 rev_counter += 1;
196 if rev_counter==len_revs {
198 f.write(b"\t\t\t\t\t\t\t\t\t<tr class=\"current-rev\">\n").expect("write failed");
199 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"revision-table-rev\"><span class=\"current-rev\">".to_string() + &rev.0 + "</span></td>\n";
200 f.write(temp_str.as_bytes()).expect("write failed");
201 } else {
202 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
203 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"revision-table-rev\">".to_string() + &rev.0 + "</td>\n";
204 f.write(temp_str.as_bytes()).expect("write failed");
205 }
206 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"revision-table-change\">".to_string() + &rev.1 + "</td>\n";
207 f.write(temp_str.as_bytes()).expect("write failed");
208 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
209 }
210 f.write(b"\t\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
212 f.write(b"\t\t\t\t\t\t\t</table>\n").expect("write failed");
213 f.write(b"\t\t\t\t\t\t</div>\n").expect("write failed");
214 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
215 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
216 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
217
218 if p.get_all_verifications().len()==0 { return };
220
221 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
223 f.write(b"\t\t\t\t<section class=\"\">\n").expect("write failed");
224 f.write(b"\t\t\t\t\t<div id=\"requirements-page\">\n").expect("write failed");
225 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">Requirements Table for ").to_string() + p.get_number() + " \"" + p.get_title() + "\"</span>\n";
226 f.write(temp_str.as_bytes()).expect("write failed");
227 let temp_str = "\t\t\t\t\t\t<div class=\"requirement\">Successful execution of this procedure produces evidence of verification for the requirements listed in the table below. Therefore, this procedure's execution is particularly important for us to achieve our goal. When you see procedure call-outs in this style of box, that step is what produces this critical evidence. Take the time to understand how these requirements will be verified prior to starting this procedure, and consult this procedure's author (".to_string() + p.get_author() + ") if necessary.</div>\n";
229 f.write(temp_str.as_bytes()).expect("write failed");
230 f.write(b"\t\t\t\t\t\t<div class=\"requirements-table-container\">\n").expect("write failed");
232 f.write(b"\t\t\t\t\t\t\t<table>\n").expect("write failed");
233 f.write(b"\t\t\t\t\t\t\t\t<thead>\n").expect("write failed");
234 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
235 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-rid\">RID</td>\n").expect("write failed");
237 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-text\">Text of Requirement</td>\n").expect("write failed");
238 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-method\">Verif. Method</td>\n").expect("write failed");
239 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-step\">Step</td>\n").expect("write failed");
240 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
241 f.write(b"\t\t\t\t\t\t\t\t</thead>\n").expect("write failed");
242 f.write(b"\t\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
243 for req in p.get_all_verifications().iter() {
245 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
246 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-rid\">".to_string() + &req.0.get_id() + "</td>\n";
247 f.write(temp_str.as_bytes()).expect("write failed");
248 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-text\">".to_string() + &req.0.get_text() + "</td>\n";
249 f.write(temp_str.as_bytes()).expect("write failed");
250 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-method\">".to_string() + &req.0.get_method() + "</td>\n";
251 f.write(temp_str.as_bytes()).expect("write failed");
252 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"requirements-table-step\">".to_string() + &req.1 + "</td>\n";
253 f.write(temp_str.as_bytes()).expect("write failed");
254 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
255 }
256 f.write(b"\t\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
258 f.write(b"\t\t\t\t\t\t\t</table>\n").expect("write failed");
259 f.write(b"\t\t\t\t\t\t</div>\n").expect("write failed");
260 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
261 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
262 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
263}
264
265fn compose_html_body_toc(f:&mut File,p:&Process,s:&Vec<Section>) {
271
272 fn pick_color(index:usize) -> String {
274 match index % 3 {
276 2 => String::from("border: 0; background-color: #FFFFFF; color: #5566AA;"),
277 1 => String::from("border: 0; background-color: #FFFFFF; color: #5566AA;"),
278 0 => String::from("border: 0; background-color: #FFFFFF; color: #5566AA;"),
279 _ => String::from("border: 0; background-color: #AA99DD; color: #5566AA;"),
280 }
281 }
290
291 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
293 f.write(b"\t\t\t\t<section class=\"\">\n").expect("write failed");
294 f.write(b"\t\t\t\t\t<div id=\"toc\">\n").expect("write failed");
295 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">").to_string() + p.get_number() + ", Rev " + p.get_revision() + " \"" + p.get_title() + "\"</span>\n";
296 f.write(temp_str.as_bytes()).expect("write failed");
297 f.write(b"\t\t\t\t\t\t<ul style=\"toc-section\">\n").expect("write failed");
299 for (ii,sec) in s.iter().enumerate() {
300 let temp_str = String::from("\t\t\t\t\t\t\t<li><a class=\"pageref\" href=\"#Section") + &(ii+1).to_string() + "\">Section " + &(ii+1).to_string() + "</a>: " + sec.get_title() + "</a></li>\n";
301 f.write(temp_str.as_bytes()).expect("write failed");
302 f.write(b"\t\t\t\t\t\t\t\t<ul style=\"toc-step\">\n").expect("write failed");
303 for (jj,stp) in sec.get_all_steps().iter().enumerate() {
304 let temp_str = String::from("\t\t\t\t\t\t\t\t\t<li><a class=\"pageref\" href=\"#Step") + &(ii+1).to_string() + "." + &(jj+1).to_string() + "\">Step " + &(ii+1).to_string() + "." + &(jj+1).to_string() + "</a>: " + stp.get_text() + "</a></li>\n";
305 f.write(temp_str.as_bytes()).expect("write failed");
306 }
307 f.write(b"\t\t\t\t\t\t\t\t</ul>\n").expect("write failed");
308 }
309 f.write(b"\t\t\t\t\t\t</ul>\n\n").expect("write failed");
310 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
311
312 f.write(b"\t\t\t\t\t<div id=\"roles\">\n").expect("write failed");
314 f.write(b"\t\t\t\t\t\t<span class=\"toc-title\">Personnel Performing this Process, by Named Role:</span>\n").expect("write failed");
315 f.write(b"\t\t\t\t\t\t<table id=\"roles-table\">\n").expect("write failed");
316 f.write(b"\t\t\t\t\t\t\t<thead id=\"roles-header\">\n").expect("write failed");
317 f.write(b"\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
318 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-title\">Role in this Process</td>\n").expect("write failed");
319 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-name\">Name of Person</td>\n").expect("write failed");
320 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-initials\">Initials</td>\n").expect("write failed");
321 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-contact\">Contact Information</td>\n").expect("write failed");
322 f.write(b"\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
323 f.write(b"\t\t\t\t\t\t\t</thead>\n").expect("write failed");
324 f.write(b"\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
325 let num_roles:usize = 10;
326 for ii in 1..(num_roles+1) {
327 let temp_str = String::from("\t\t\t\t\t\t\t\t<tr id=\"role-".to_string() + &format!("{:0>2}",ii) + "\">\n");
328 f.write(temp_str.as_bytes()).expect("write failed");
329 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-title\"></td>\n").expect("write failed");
330 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-name\"></td>\n").expect("write failed");
331 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-initials\"></td>\n").expect("write failed");
332 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"role-contact\"></td>\n").expect("write failed");
333 f.write(b"\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
334 }
335 f.write(b"\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
336 f.write(b"\t\t\t\t\t\t</table>\n").expect("write failed");
337 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
338
339 f.write(b"\t\t\t\t\t<div class=\"power-on\"><img/><span class=\"power-on-text\"></span></div>\n").expect("write failed");
342 f.write(b"\t\t\t\t\t<div class=\"rf-emission\"><img/><span class=\"rf-emission-text\"></span></div>\n").expect("write failed");
343 f.write(b"\t\t\t\t\t<div class=\"hazardous-ops\"><img/><span class=\"hazardous-ops-text\"></span></div>\n").expect("write failed");
344 f.write(b"\t\t\t\t\t<div class=\"esd\"><img/><span class=\"esd-text\"></span></div>\n").expect("write failed");
345 f.write(b"\t\t\t\t\t<div class=\"fod\"><img/><span class=\"fod-text\"></span></div>\n").expect("write failed");
346 f.write(b"\t\t\t\t\t<div class=\"welding\"><img/><span class=\"welding-text\"></span></div>\n").expect("write failed");
347 f.write(b"\t\t\t\t\t<div class=\"comsec\"><img/><span class=\"comsec-text\"></span></div>\n").expect("write failed");
348 f.write(b"\t\t\t\t\t<div class=\"cleanroom\"><img/><span class=\"cleanroom-text\"></span></div>\n").expect("write failed");
349 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
350 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
351
352 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
354 f.write(b"\t\t\t\t<section class=\"\">\n").expect("write failed");
355
356 let all_objectives = p.get_all_objectives();
357 if all_objectives.len() > 0 {
358 f.write(b"\t\t\t\t\t<div id=\"all-objectives\">\n").expect("write failed");
360 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">This process has ") + &all_objectives.len().to_string() + " stated objective" + match all_objectives.len() {1=>"",_=>"s"} + ":</span>\n";
361 f.write(temp_str.as_bytes()).expect("write failed");
362 f.write(b"\t\t\t\t\t\t<ol class=\"objective-list\">\n").expect("write failed");
363 for (_jj,(obj,snum)) in all_objectives.iter().enumerate() {
364 let temp_str = String::from("\t\t\t\t\t\t\t<li>") + &obj + " (" + &snum + ")</li>\n";
365 f.write(temp_str.as_bytes()).expect("write failed");
366 }
367 f.write(b"\t\t\t\t\t\t</ol>\n").expect("write failed");
368 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
369 };
370
371 let all_out_of_scopes = p.get_all_out_of_scopes();
372 if all_out_of_scopes.len() > 0 {
373 f.write(b"\t\t\t\t\t<div id=\"all-out-of-scopes\">\n").expect("write failed");
375 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">This process has ") + &all_out_of_scopes.len().to_string() + " <em>Out Of Scope</em> declaration" + match all_out_of_scopes.len() {1=>"",_=>"s"} + ":</span>\n";
376 f.write(temp_str.as_bytes()).expect("write failed");
377 f.write(b"\t\t\t\t\t\t<ol class=\"out-of-scope-list\">\n").expect("write failed");
378 for (_jj,(oos,snum)) in all_out_of_scopes.iter().enumerate() {
379 let temp_str = String::from("\t\t\t\t\t\t\t<li>") + &oos + " (" + &snum + ")</li>\n";
380 f.write(temp_str.as_bytes()).expect("write failed");
381 }
382 f.write(b"\t\t\t\t\t\t</ol>\n").expect("write failed");
383 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
384 };
385
386 f.write(b"\t\t\t\t\t<div id=\"subject-product\">\n").expect("write failed");
388
389 match p.get_product().as_str() {
390 ""|"N/A" => {
391 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">\"") + p.get_title() + "\" applies to <em>" + p.get_subject() + "</em></span><br/>\n";
392 f.write(temp_str.as_bytes()).expect("write failed");
393 let temp_str = String::from("\t\t\t\t\t\t<div class=\"subject-product-image-container\"><img src=\"") + p.get_subject_image() + "\"/></div>\n";
394 f.write(temp_str.as_bytes()).expect("write failed");
395 },
396 _ => {
397 let temp_str = String::from("\t\t\t\t\t\t<span class=\"toc-title\">\"") + p.get_title() + "\" applies to <em>" + p.get_subject() + "</em> to produce <em>" + p.get_product() +"</em></span><br/>\n";
398 f.write(temp_str.as_bytes()).expect("write failed");
399 let temp_str = String::from("\t\t\t\t\t\t<div class=\"subject-product-image-container\"><img src=\"") + p.get_subject_image() + "\"/><span class=\"arrow\">→</span><img src=\"" + p.get_product_image() + "\"/></div>\n";
400 f.write(temp_str.as_bytes()).expect("write failed");
401 },
402 };
403 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
404
405 if p.get_all_resources().len() > 0 {
407 f.write(b"\t\t\t\t\t\t<div class=\"resources-container\">\n").expect("write failed");
408 let temp_str = "\t\t\t\t\t\t<span class=\"resources-text\">".to_string() + &p.get_all_resources().len().to_string() + " named resources are identified to perform this process:</span><br/>\n";
409 f.write(temp_str.as_bytes()).expect("write failed");
410
411 let mut step_num = "";
413 let mut index:usize = 0;
414 for (resource,resource_step) in p.get_all_resources() {
415 if !(step_num==resource_step) { index += 1; };
416 step_num = resource_step;
417 let temp_str = "\t\t\t\t\t\t\t<div class=\"resource-bubble\" style=\"".to_string() + &pick_color(index) + ";\"><span class=\"resource-bubble-step\">" + &resource_step + "</span><br/>" + &resource.get_name() + "</div>\n";
418 f.write(temp_str.as_bytes()).expect("write failed");
419 }
420 f.write(b"\t\t\t\t\t\t</div><div style=\"clear:both;\"></div>\n").expect("write failed");
421
422 if p.get_all_calibrated_resources().len() > 0 {
424 f.write(b"\t\t\t\t\t<div id=\"calibration\">\n").expect("write failed");
425 f.write(b"\t\t\t\t\t\t<span class=\"toc-title\">Equipment Calibration Status</span>\n").expect("write failed");
426 f.write(b"\t\t\t\t\t\t<table id=\"calibration-table\">\n").expect("write failed");
427 f.write(b"\t\t\t\t\t\t\t<thead id=\"calibration-header\">\n").expect("write failed");
428 f.write(b"\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
430 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-resource\">Equipment</td>\n").expect("write failed");
431 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-num\">Model Number</td>\n").expect("write failed");
432 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-serial\">Serial</td>\n").expect("write failed");
433 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-date\">Last Cal Date</td>\n").expect("write failed");
434 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-due\">Valid Until</td>\n").expect("write failed");
435 f.write(b"\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
436 f.write(b"\t\t\t\t\t\t\t</thead>\n").expect("write failed");
437 f.write(b"\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
438 for resource in p.get_all_calibrated_resources() {
439 let temp_str = String::from("\t\t\t\t\t\t\t\t<tr>\n");
440 f.write(temp_str.as_bytes()).expect("write failed");
441 let temp_str = "\t\t\t\t\t\t\t\t\t<td class=\"calibration-resource\">".to_string() + &resource.get_name() + "</td>\n";
443 f.write(temp_str.as_bytes()).expect("write failed");
444 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-num\"></td>\n").expect("write failed");
445 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-serial\"></td>\n").expect("write failed");
446 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-date\"></td>\n").expect("write failed");
447 f.write(b"\t\t\t\t\t\t\t\t\t<td class=\"calibration-due\"></td>\n").expect("write failed");
448 f.write(b"\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
449 }
450 f.write(b"\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
451 f.write(b"\t\t\t\t\t\t\t<tfoot>\n").expect("write failed");
452 f.write(b"\t\t\t\t\t\t\t\t<tr><td colspan=\"3\">If any equipment is within 30 days of needing recalibration, notify your QA rep. <strong>Today's Date:</strong></td></tr>\n").expect("write failed");
453 f.write(b"\t\t\t\t\t\t\t</tfoot>\n").expect("write failed");
454 f.write(b"\t\t\t\t\t\t</table>\n").expect("write failed");
455 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
456 }
457
458
459 }
460 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
461 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
462 f.write(b"\t\t\t<tr id=\"non-conformances\"><td>\n\n").expect("write failed");
466 f.write(b"\t\t\t\t<section class=\"\">\n").expect("write failed");
467 f.write(b"\t\t\t\t\t<span class=\"toc-title\">Log of Non-Conformances during this execution:</span>\n").expect("write failed");
468 f.write(b"\t\t\t\t\t<table>\n").expect("write failed");
469 f.write(b"\t\t\t\t\t\t<thead>\n").expect("write failed");
470 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
471 f.write(b"\t\t\t\t\t\t\t\t<td class=\"text-rotated\">Time</td>\n").expect("write failed");
472 f.write(b"\t\t\t\t\t\t\t\t<td class=\"text-rotated\">Step</td>\n").expect("write failed");
473 f.write(b"\t\t\t\t\t\t\t\t<td class=\"text-rotated\">Record</td>\n").expect("write failed");
474 f.write(b"\t\t\t\t\t\t\t\t<td>Brief Summary of Observation(s) that Deviated from Documented Expectations</td>\n").expect("write failed");
475 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
476 f.write(b"\t\t\t\t\t\t</thead>\n").expect("write failed");
477 f.write(b"\t\t\t\t\t\t<tbody>\n").expect("write failed");
478 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
479 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
480 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
481 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
482 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
483 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
484 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
485 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
486 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
487 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
488 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
489 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
490 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
491 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
492 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
493 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
494 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
495 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
496 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
497 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
498 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
499 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
500 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
501 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
502 f.write(b"\t\t\t\t\t\t\t<tr>\n").expect("write failed");
503 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
504 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
505 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
506 f.write(b"\t\t\t\t\t\t\t\t<td></td>\n").expect("write failed");
507 f.write(b"\t\t\t\t\t\t\t</tr>\n").expect("write failed");
508 f.write(b"\t\t\t\t\t\t</tbody>\n").expect("write failed");
509 f.write(b"\t\t\t\t\t</table>\n").expect("write failed");
510 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
511 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
512
513
514}
515
516fn compose_html_body_section(f:&mut File, p:&Process, all_sections:&Vec<Section>) {
518
519 let mut counter = 0;
521 for section in all_sections {
522 f.write(b"\t\t\t<tr><td>\n\n").expect("write failed");
524 f.write(b"\t\t\t\t<section>\n").expect("write failed");
525
526 counter += 1;
529
530 let temp_str = "\t\t\t\t\t<div class=\"section-title\"><a name=\"Section".to_string() + &counter.to_string() + "\"></a>Section " + &counter.to_string() + ": " + §ion.get_title() + "</div>\n";
532 f.write(temp_str.as_bytes()).expect("write failed");
533
534 for (ii,step) in section.get_all_steps().iter().enumerate() {
536
537 let temp_str = "\t\t\t\t\t<div class=\"step\"><span class=\"step-text\"><a name=\"Step".to_string() + &counter.to_string() + "." + &{ii+1}.to_string() + "\"></a>Step " + &counter.to_string() + "." + &{ii+1}.to_string() + ": " + &step.get_text() + "</span><br/>\n";
539 f.write(temp_str.as_bytes()).expect("write failed");
540
541 if step.get_resources().len() > 0 {
543 f.write(b"\t\t\t\t\t\t\t<div class=\"resources-container\">\n").expect("write failed");
544 let temp_str = "\t\t\t\t\t\t\t\t<span class=\"resources-text\">".to_string() + &step.get_resources().len().to_string() + " named resources are identified to perform this step:</span><br/>\n";
545 f.write(temp_str.as_bytes()).expect("write failed");
546 for resource in step.get_resources() {
547 let temp_str = "\t\t\t\t\t\t\t\t<div class=\"resource-bubble\">".to_string() + &resource.get_name() + "</div>\n";
548 f.write(temp_str.as_bytes()).expect("write failed");
549 }
550 f.write(b"\t\t\t\t\t\t\t</div><div style=\"clear:both;\"></div>\n").expect("write failed");
551 }
552 for (_jj,sub_step) in step.get_all_sub_steps().iter().enumerate() {
556 match sub_step {
557 SubStep::ActionSequence(action_sequence) => compose_html_body_section_step_action_sequence(f,&action_sequence),
558 SubStep::Command(command_text) => compose_html_body_section_step_command(f,&command_text),
559 SubStep::Image(image_file,image_text) => compose_html_body_section_step_image(f,&image_file,&image_text),
560 SubStep::Warning(warning_text) => compose_html_body_section_step_warning(f,&warning_text),
561 SubStep::Verification(requirement) => compose_html_body_section_step_verification(f,&p.get_author(),&requirement),
562 SubStep::Resource(_resource) => (),
565 SubStep::Context(text) => compose_html_body_section_step_context(f,&text),
566 SubStep::Objective(objective_text) => compose_html_body_section_step_objective(f,&objective_text),
567 SubStep::OutOfScope(out_of_scope_text) => compose_html_body_section_step_out_of_scope(f,&out_of_scope_text),
568 SubStep::Table(table) => compose_html_body_section_step_table(f,&table),
569 }
570 }
571 f.write(b"\t\t\t\t\t</div>\n").expect("write failed");
573 }
574 f.write(b"\t\t\t\t</section>\n\n").expect("write failed");
576 f.write(b"\t\t\t</td></tr>\n\n").expect("write failed");
577 }
578}
579
580fn compose_html_body_section_step_action_sequence(f:&mut File, act_seq:&Vec<Action>) {
582 f.write(b"\t\t\t\t\t\t<div class=\"action-sequence\">\n").expect("write failed");
584 f.write(b"\t\t\t\t\t\t\t<table>\n").expect("write failed");
585 f.write(b"\t\t\t\t\t\t\t\t<thead>\n").expect("write failed");
586 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
587 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-action\">Action to perform</td>\n").expect("write failed");
589 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-expected\">Expected</td>\n").expect("write failed");
590 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-result\">Result</td>\n").expect("write failed");
591 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-tpv\">Done</td>\n").expect("write failed");
592 f.write(b"\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-tpv\">TPV</td>\n").expect("write failed");
593 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
594 f.write(b"\t\t\t\t\t\t\t\t</thead>\n").expect("write failed");
595 f.write(b"\t\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
596
597 for act in act_seq {
599 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
600 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-action\">".to_string() + act.get_perform() + "</td>\n";
601 f.write(temp_str.as_bytes()).expect("write failed");
602 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-expected\">".to_string() + act.get_expect() + "</td>\n";
603 f.write(temp_str.as_bytes()).expect("write failed");
604 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-result\">".to_string() + "</td>\n";
605 f.write(temp_str.as_bytes()).expect("write failed");
606 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-tpv\">".to_string() + "<span class=\"action-checkbox\">▢</span>" + "</td>\n";
607 f.write(temp_str.as_bytes()).expect("write failed");
608 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td class=\"action-sequence-tpv\">".to_string() + { if !act.get_tpv() { "N/A" } else { "<span class=\"action-checkbox\">▢</span>" }} + "</td>\n";
609 f.write(temp_str.as_bytes()).expect("write failed");
610 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
611 }
612
613 f.write(b"\t\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
615 f.write(b"\t\t\t\t\t\t\t</table>\n").expect("write failed");
616 f.write(b"\t\t\t\t\t\t</div>\n").expect("write failed");
617}
618
619fn compose_html_body_section_step_command(f:&mut File, c:&String) {
621 let temp_str = "\t\t\t\t\t\t<div class=\"command\"><span class=\"command-text\">".to_string() + &c.to_string() + "</span></div>\n";
623 f.write(temp_str.as_bytes()).expect("write failed");
624}
625
626fn compose_html_body_section_step_image(f:&mut File, img:&String, txt:&String) {
628 let temp_str = "\t\t\t\t\t\t<div class=\"image\"><div class=\"image-container\"><img src=\"".to_string() + &img.to_string() + "\" onerror=\"this.onerror=null; this.src='../assets/placeholderImage-small.png'\"/><br/><span class=\"image-text\">" + &txt.to_string() + "</span></div></div>\n";
632 f.write(temp_str.as_bytes()).expect("write failed");
633}
634
635fn compose_html_body_section_step_warning(f:&mut File, w:&String) {
637 let temp_str = "\t\t\t\t\t\t<div class=\"warning\"><span class=\"warning-text\">".to_string() + &w.to_string() + "</span></div>\n";
639 f.write(temp_str.as_bytes()).expect("write failed");
640}
641
642fn compose_html_body_section_step_verification(f:&mut File, author:&String, r:&Requirement) {
644 let temp_str = "\t\t\t\t\t\t<div class=\"requirement\">This step produces the evidence of verification for this requirement:<br/><span class=\"requirement-rid\">".to_string() + &r.get_id() + ": \"" + &r.get_text() + "\" (Verify by " + &r.get_method() + ")</span><br/>Please ensure the evidence produced passes the requirement before proceding. This might require consulting this procedure's author, " + author + ".</div>\n";
646 f.write(temp_str.as_bytes()).expect("write failed");
647}
648
649fn compose_html_body_section_step_context(f:&mut File, text:&String) {
651 let temp_str = "\t\t\t\t\t\t<div class=\"context\"><span class=\"context-text\">".to_string() + &text.to_string() + "</span></div>\n";
653 f.write(temp_str.as_bytes()).expect("write failed");
654}
655
656fn compose_html_body_section_step_objective(f:&mut File, objective_text:&String) {
658 let temp_str = "\t\t\t\t\t\t<div class=\"objective\">".to_string() + objective_text + "</div>\n";
660 f.write(temp_str.as_bytes()).expect("write failed");
661}
662
663fn compose_html_body_section_step_out_of_scope(f:&mut File, out_of_scope_text:&String) {
665 let temp_str = "\t\t\t\t\t\t<div class=\"out-of-scope\">".to_string() + out_of_scope_text + "</div>\n";
667 f.write(temp_str.as_bytes()).expect("write failed");
668}
669
670fn compose_html_body_section_step_table(f:&mut File, table:&Table) {
672
673 let (rows,cols) = table.get_size();
674
675 if rows > 0 {
677
678 f.write(b"\t\t\t\t\t\t<div class=\"csv-table-container\">\n").expect("write failed");
679 f.write(b"\t\t\t\t\t\t\t<table>\n").expect("write failed");
680
681 let temp_str = "\t\t\t\t\t\t\t\t<caption>".to_string() + table.get_caption() + "</caption>\n";
682 f.write(temp_str.as_bytes()).expect("write failed");
683
684 f.write(b"\t\t\t\t\t\t\t\t<thead>\n").expect("write failed");
685 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
686 let first_row = table.get_row(0);
687 for jj in 0..cols {
688
689 let temp_str = "\t\t\t\t\t\t\t\t\t\t<th>".to_string() + &first_row[jj] + "</th>\n";
690 f.write(temp_str.as_bytes()).expect("write failed");
691 }
692 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
693 f.write(b"\t\t\t\t\t\t\t\t</thead>\n").expect("write failed");
694 f.write(b"\t\t\t\t\t\t\t\t<tbody>\n").expect("write failed");
695
696 for ii in 1..rows {
697 let this_row = table.get_row(ii);
698 f.write(b"\t\t\t\t\t\t\t\t\t<tr>\n").expect("write failed");
699 for jj in 0..cols {
700 let temp_str = "\t\t\t\t\t\t\t\t\t\t<td>".to_string() + &this_row[jj] + "</td>\n";
701 f.write(temp_str.as_bytes()).expect("write failed");
702 }
703 f.write(b"\t\t\t\t\t\t\t\t\t</tr>\n").expect("write failed");
704 }
705
706 f.write(b"\t\t\t\t\t\t\t\t</tbody>\n").expect("write failed");
707 f.write(b"\t\t\t\t\t\t\t</table>\n").expect("write failed");
708 f.write(b"\t\t\t\t\t\t</div>\n").expect("write failed");
709 }
710}
711
712fn compose_html_body_end_of_sections_and_banners(f:&mut File, p:&Process) {
714 f.write(b"\t\t</tbody>\n\n").expect("write failed");
715 f.write(b"\t\t\t<tfoot><tr><td>\n").expect("write failed");
716 f.write(b"\t\t\t\t<div class=\"footer-space\"> </div>\n").expect("write failed");
717 f.write(b"\t\t\t</td></tr></tfoot>\n").expect("write failed");
718 f.write(b"\t\t</table>\n\n").expect("write failed");
719
720 f.write(b"\t\t<div class=\"header\">\n").expect("write failed");
722 f.write(b"\t\t\t<table style=\"margin:0; padding:0; width:100%;\">\n").expect("write failed");
723 f.write(b"\t\t\t\t<tbody style=\"margin:0; padding:0;\">\n").expect("write failed");
724 f.write(b"\t\t\t\t\t<tr style=\"vertical-align: top; margin:0;\">\n").expect("write failed");
725
726 let temp_str = "\t\t\t\t\t\t<td id=\"header-left\"><p class=\"header-p\"><img/><span style=\"font-size:1.3em; font-weight:bold;\">".to_string() + p.get_number() + ", Rev " + p.get_revision() + "</span><br/>Written by: " + p.get_author() + "<br/>Reviewed by: " + p.get_reviewer() + "</p></td>\n";
730 f.write(temp_str.as_bytes()).expect("write failed");
731 let temp_str = "\t\t\t\t\t\t<td id=\"header-right\"><p class=\"header-p\"><span style=\"font-size:1.3em; font-weight:bold;\">".to_string() + p.get_title() + "</span><br/>Applies to " + p.get_subject() + " to produce " + p.get_product() + "<br/>" + &p.get_all_resources().len().to_string() + " named resources are identified to perform this process</p></td>\n";
733 f.write(temp_str.as_bytes()).expect("write failed");
734 f.write(b"\t\t\t\t\t</tr>\n").expect("write failed");
736 f.write(b"\t\t\t\t</tbody>\n").expect("write failed");
737 f.write(b"\t\t\t</table>\n").expect("write failed");
738 f.write(b"\t\t</div>\n").expect("write failed");
739
740 f.write(b"\t\t<div class=\"footer\">\n").expect("write failed");
742 f.write(b"\t\t\t<table style=\"margin:0; padding:0; width:100%;\">\n").expect("write failed");
743 f.write(b"\t\t\t\t<tbody style=\"margin:0; padding:0; width:100%\">\n").expect("write failed");
744 f.write(b"\t\t\t\t\t<tr style=\"vertical-align: top; margin:0;\">\n").expect("write failed");
745 let temp_str = "\t\t\t\t\t\t<td width=\"100%\" style=\"margin:0; padding:0;\"><p class=\"header-p\"><!--<a href=\"https://strativusgroup.com\">--><img/>Produced efficiently with stanhope. See this document's first page for restrictions and distribution statements.<!--</a>--><span>".to_string() + "</p></td>\n";
747 f.write(temp_str.as_bytes()).expect("write failed");
748 let temp_str = "\t\t\t\t\t\t<td><p class=\"header-p\"><span>".to_string() + "</span><br/></p></td>\n";
750 f.write(temp_str.as_bytes()).expect("write failed");
751 f.write(b"\t\t\t\t\t</tr>\n").expect("write failed");
759 f.write(b"\t\t\t\t</tbody>\n").expect("write failed");
760 f.write(b"\t\t\t</table>\n").expect("write failed");
761 f.write(b"\t\t</div>\n").expect("write failed");
762}