1 | /* |
|
|
2 | gen_html.c - Part of psiconv, a PSION 5 file formats converter |
1 | /* gen_html.c - Part of psiconv, a PSION 5 file formats converter |
3 | Copyright (c) 1999 Frodo Looijaard <frodol@dds.nl> |
2 | Copyright (c) 1999-2004 Frodo Looijaard <frodol@dds.nl> |
4 | |
3 | |
5 | This program is free software; you can redistribute it and/or modify |
4 | This program is free software; you can redistribute it and/or modify |
6 | it under the terms of the GNU General Public License as published by |
5 | it under the terms of the GNU General Public License as published by |
7 | the Free Software Foundation; either version 2 of the License, or |
6 | the Free Software Foundation; either version 2 of the License, or |
8 | (at your option) any later version. |
7 | (at your option) any later version. |
9 | |
8 | |
10 | This program is distributed in the hope that it will be useful, |
9 | This program is distributed in the hope that it will be useful, |
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
10 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
11 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
13 | GNU General Public License for more details. |
12 | GNU General Public License for more details. |
14 | |
13 | |
15 | You should have received a copy of the GNU General Public License |
14 | You should have received a copy of the GNU General Public License |
16 | along with this program; if not, write to the Free Software |
15 | along with this program; if not, write to the Free Software |
17 | Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
16 | Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
18 | */ |
17 | */ |
19 | |
18 | |
20 | #include "config.h" |
19 | #include "config.h" |
21 | #include <stdio.h> |
20 | |
|
|
21 | #include <psiconv/configuration.h> |
|
|
22 | #include <psiconv/data.h> |
|
|
23 | #include "general.h" |
|
|
24 | |
22 | #include <string.h> |
25 | #include <string.h> |
23 | #include <stdlib.h> |
26 | #include <stdlib.h> |
|
|
27 | |
|
|
28 | #ifdef DMALLOC |
24 | #include "data.h" |
29 | #include "dmalloc.h" |
25 | #include "list.h" |
30 | #endif |
26 | #include "gen.h" |
|
|
27 | #include "psiconv.h" |
|
|
28 | |
31 | |
29 | /* This determines for each character how it is displayed */ |
32 | #define TEMPSTR_LEN 100 |
30 | static const char *char_table[0x100] = |
|
|
31 | { |
|
|
32 | /* 0x00 */ "" ,"" ,"" ,"" ,"" ,"" ,"<P> ","<BR>" , |
|
|
33 | /* 0x08 */ "<P>" ," " ,"" ,"" ,"" ,"" ,"" ,"" , |
|
|
34 | /* 0x10 */ " " ,"" ,"" ,"" ,"" ,"" ,"" ,"" , |
|
|
35 | /* 0x18 */ "" ,"" ,"" ,"" ,"" ,"" ,"" ,"" , |
|
|
36 | /* 0x20 */ " " ,"!" ,""","#" ,"$" ,"%" ,"&","'" , |
|
|
37 | /* 0x28 */ "(" ,")" ,"*" ,"+" ,"," ,"-" ,"." ,"/" , |
|
|
38 | /* 0x30 */ "0" ,"1" ,"2" ,"3" ,"4" ,"5" ,"6" ,"7" , |
|
|
39 | /* 0x38 */ "8" ,"9" ,":" ,";" ,"<" ,"=" ,">" ,"?" , |
|
|
40 | /* 0x40 */ "@" ,"A" ,"B" ,"C" ,"D" ,"E" ,"F" ,"G" , |
|
|
41 | /* 0x48 */ "H" ,"I" ,"J" ,"K" ,"L" ,"M" ,"N" ,"O" , |
|
|
42 | /* 0x50 */ "P" ,"Q" ,"R" ,"S" ,"T" ,"U" ,"V" ,"W" , |
|
|
43 | /* 0x58 */ "X" ,"Y" ,"Z" ,"[" ,"\\" ,"]" ,"^" ,"_" , |
|
|
44 | /* 0x60 */ "`" ,"a" ,"b" ,"c" ,"d" ,"e" ,"f" ,"g" , |
|
|
45 | /* 0x68 */ "h" ,"i" ,"j" ,"k" ,"l" ,"m" ,"n" ,"o" , |
|
|
46 | /* 0x70 */ "p" ,"q" ,"r" ,"s" ,"t" ,"u" ,"v" ,"w" , |
|
|
47 | /* 0x78 */ "x" ,"y" ,"z" ,"{" ,"|" ,"}" ,"~" ,"" , |
|
|
48 | /* 0x80 */ "" ,"","&sbquot;","ƒ","„","…", |
|
|
49 | "†","‡", |
|
|
50 | /* 0x88 */ "^","‰","Š","⟨","Œ","" ,"" ,"" , |
|
|
51 | /* 0x90 */ "","‘","’","“","”", |
|
|
52 | "·","&ndash","&mdash", |
|
|
53 | /* 0x98 */ "˜","™","š","⟩","œ","","","Ÿ", |
|
|
54 | /* 0xa0 */ "","¡","¢","£", |
|
|
55 | "¤","¥","¦","§", |
|
|
56 | /* 0xa8 */ ""","©","a","«","¬","-","®","¯on;", |
|
|
57 | /* 0xb0 */ "°","±","²","³", |
|
|
58 | "&rsquot;","µn;","¶","·", |
|
|
59 | /* 0xb8 */ ",","¹","°","»", |
|
|
60 | "¼","½","¾","¿", |
|
|
61 | /* 0xc0 */ "À","Á","Â","Ã", |
|
|
62 | "Ä","Å","Æ","Ç", |
|
|
63 | /* 0xc8 */ "È","É","Ê","Ë", |
|
|
64 | "Ì","Í","Î","Ï", |
|
|
65 | /* 0xd0 */ "Ð","Ñ","Ò","Ó", |
|
|
66 | "Ô","Õ","Ö","×", |
|
|
67 | /* 0xd8 */ "Ø","Ù","Ú","Û", |
|
|
68 | "Ü","Ý","Þ","ß", |
|
|
69 | /* 0xe0 */ "à","á","â","ã", |
|
|
70 | "ä","å","æ","ç", |
|
|
71 | /* 0xe8 */ "è","é","ê","ë", |
|
|
72 | "ì","í","î","ï", |
|
|
73 | /* 0xf0 */ "ð","ñ","ò","ó", |
|
|
74 | "ô","õ","ö","÷", |
|
|
75 | /* 0xf8 */ "ø","ù","ú","û", |
|
|
76 | "ü","ý","þ","ÿ" |
|
|
77 | }; |
|
|
78 | |
33 | |
79 | static psiconv_character_layout gen_base_char(const psiconv_font font, |
34 | typedef enum output_type_e { output_html, output_xhtml } output_type; |
80 | const psiconv_color color, |
|
|
81 | const psiconv_color back_color); |
|
|
82 | static void diff_char(FILE *of, const psiconv_character_layout old, |
|
|
83 | const psiconv_character_layout new, int *flags); |
|
|
84 | static void gen_para(FILE *of, const psiconv_paragraph para, |
|
|
85 | const psiconv_character_layout base_char); |
|
|
86 | |
35 | |
87 | static void psiconv_gen_html_word(FILE *of,psiconv_word_f wf); |
36 | void character_layout_diffs(const psiconv_config config, psiconv_list list, |
88 | static void psiconv_gen_html_texted(FILE *of,psiconv_texted_f tf); |
|
|
89 | |
|
|
90 | /* This is not necessarily the same as returned by basic_character_layout_status |
|
|
91 | This one is specific for the base point of HTML */ |
|
|
92 | psiconv_character_layout gen_base_char(const psiconv_font font, |
|
|
93 | const psiconv_color color, |
|
|
94 | const psiconv_color back_color) |
|
|
95 | { |
|
|
96 | struct psiconv_character_layout base_char_struct = |
|
|
97 | { |
|
|
98 | NULL, /* color */ |
|
|
99 | NULL, /* back_color */ |
|
|
100 | 13.0, /* font_size */ |
|
|
101 | psiconv_bool_false, /* italic */ |
|
|
102 | psiconv_bool_false, /* bold */ |
|
|
103 | psiconv_normalscript, /* super_sub */ |
|
|
104 | psiconv_bool_false, /* underline */ |
|
|
105 | psiconv_bool_false, /* strike_out */ |
|
|
106 | NULL, /* font */ |
|
|
107 | }; |
|
|
108 | base_char_struct.color = color; |
|
|
109 | base_char_struct.back_color = back_color; |
|
|
110 | base_char_struct.font = font; |
|
|
111 | return psiconv_clone_character_layout(&base_char_struct); |
|
|
112 | } |
|
|
113 | |
|
|
114 | /* flags & 1: 0 if no <FONT> was yet generated. |
|
|
115 | flags & 2: 1 if at end-of-paragraph |
|
|
116 | */ |
|
|
117 | void diff_char(FILE *of, const psiconv_character_layout old, |
|
|
118 | const psiconv_character_layout new, |
37 | const psiconv_character_layout new, |
119 | int *flags) |
38 | const psiconv_character_layout base, |
|
|
39 | const encoding enc) |
120 | { |
40 | { |
121 | int font_set = 0; |
41 | if (new->italic != base->italic) { |
|
|
42 | output_simple_chars(config,list,"font-style:",enc); |
|
|
43 | output_simple_chars(config,list,new->italic?"italic":"normal",enc); |
|
|
44 | output_simple_chars(config,list,";",enc); |
|
|
45 | } |
|
|
46 | if ((new->underline != base->underline) || |
|
|
47 | (new->strikethrough != base->strikethrough)) { |
|
|
48 | output_simple_chars(config,list,"text-decoration:",enc); |
|
|
49 | output_simple_chars(config,list,new->underline?"underline": |
|
|
50 | new->strikethrough?"line-through": |
|
|
51 | "none",enc); |
|
|
52 | output_simple_chars(config,list,";",enc); |
|
|
53 | } |
|
|
54 | if (new->bold != base->bold) { |
|
|
55 | output_simple_chars(config,list,"font-weight:",enc); |
|
|
56 | output_simple_chars(config,list,new->bold?"bold":"normal",enc); |
|
|
57 | output_simple_chars(config,list,";",enc); |
|
|
58 | } |
|
|
59 | if (new->super_sub != base->super_sub) { |
|
|
60 | output_simple_chars(config,list,"font-style:",enc); |
|
|
61 | output_simple_chars(config,list, |
|
|
62 | new->super_sub==psiconv_superscript?"super": |
|
|
63 | new->super_sub==psiconv_subscript?"sub": |
|
|
64 | "normal",enc); |
|
|
65 | output_simple_chars(config,list,";",enc); |
|
|
66 | } |
|
|
67 | } |
122 | |
68 | |
123 | if ((old->font_size != new->font_size) || |
69 | void paragraph_layout_diffs(const psiconv_config config, psiconv_list list, |
124 | (old->color->red != new->color->red) || |
70 | const psiconv_paragraph_layout new, |
125 | (old->color->green != new->color->green) || |
71 | const psiconv_paragraph_layout base) |
126 | (old->color->blue != new->color->blue) || |
72 | { |
127 | (strcmp(old->font->name,new->font->name)) || |
73 | } |
128 | (old->font->screenfont != new->font->screenfont) || |
74 | |
129 | ((*flags & 0x03) == 3)) { |
75 | void header(const psiconv_config config, psiconv_list list, |
|
|
76 | output_type type, const encoding enc) |
|
|
77 | { |
|
|
78 | if (type == output_xhtml) |
|
|
79 | output_simple_chars(config,list, |
|
|
80 | "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n",enc); |
|
|
81 | output_simple_chars(config,list,"<!DOCTYPE html PUBLIC ",enc); |
|
|
82 | output_simple_chars(config,list,type == output_xhtml? |
|
|
83 | "\"-//W3C//DTD XHTML 1.0 Strict//EN\" ": |
|
|
84 | "\"-//W3C//DTD HTML 4.01//EN\" ",enc); |
|
|
85 | output_simple_chars(config,list,type == output_xhtml? |
|
|
86 | "\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">": |
|
|
87 | "\"http://www.w3.org/TR/html4/strict.dtd\">",enc); |
|
|
88 | output_simple_chars(config,list,"\n<html",enc); |
|
|
89 | if (type == output_xhtml) |
|
|
90 | output_simple_chars(config,list, |
|
|
91 | " xmlns=\"http://www.w3.org/1999/xhtml\"",enc); |
|
|
92 | output_simple_chars(config,list,">\n",enc); |
|
|
93 | output_simple_chars(config,list,"<head>\n",enc); |
|
|
94 | output_simple_chars(config,list,"<meta http-equiv=\"Content-Type\" " |
|
|
95 | "content=\"text/html; charset=",enc); |
|
|
96 | output_simple_chars(config,list,enc==ENCODING_UTF8?"UTF-8": |
|
|
97 | enc==ENCODING_UCS2?"UTF-16BE": |
|
|
98 | enc==ENCODING_ASCII?"US-ASCII": |
|
|
99 | "",enc); |
|
|
100 | output_simple_chars(config,list,"\">\n",enc); |
|
|
101 | output_simple_chars(config,list,"<meta http-equiv=\"Content-Style-Type\" " |
|
|
102 | "content=\"text/css\">\n",enc); |
|
|
103 | output_simple_chars(config,list,"<title>EPOC32 file " |
|
|
104 | "converted by psiconv</title>\n",enc); |
|
|
105 | output_simple_chars(config,list,"</head>\n",enc); |
|
|
106 | output_simple_chars(config,list,"<body>\n",enc); |
|
|
107 | } |
|
|
108 | |
|
|
109 | void footer(const psiconv_config config, psiconv_list list, |
|
|
110 | output_type type, const encoding enc) |
|
|
111 | { |
|
|
112 | output_simple_chars(config,list,"</body>\n",enc); |
|
|
113 | output_simple_chars(config,list,"</html>\n",enc); |
|
|
114 | } |
|
|
115 | |
|
|
116 | void color(const psiconv_config config, psiconv_list list, |
|
|
117 | psiconv_color color, output_type type, const encoding enc) |
|
|
118 | { |
|
|
119 | char tempstr[TEMPSTR_LEN]; |
|
|
120 | if ((color->red == 0xff) && |
|
|
121 | (color->blue == 0xff) && |
|
|
122 | (color->green == 0xff)) |
|
|
123 | output_simple_chars(config,list,"transparant",enc); |
|
|
124 | else { |
|
|
125 | snprintf(tempstr,TEMPSTR_LEN,"rgb(%d,%d,%d)", |
|
|
126 | color->red, |
|
|
127 | color->green, |
|
|
128 | color->blue); |
|
|
129 | output_simple_chars(config,list,tempstr,enc); |
|
|
130 | } |
|
|
131 | } |
|
|
132 | |
|
|
133 | void charlayout(const psiconv_config config, psiconv_list list, |
|
|
134 | psiconv_string_t text,psiconv_character_layout layout, |
|
|
135 | output_type type, const encoding enc) |
|
|
136 | { |
|
|
137 | char tempstr[TEMPSTR_LEN]; |
130 | if (old->italic) |
138 | if (layout->italic) |
131 | fputs("</I>",of); |
139 | output_simple_chars(config,list,"<i>",enc); |
132 | if (old->bold) |
140 | if (layout->bold) |
133 | fputs("</B>",of); |
141 | output_simple_chars(config,list,"<b>",enc); |
134 | if (old->underline) |
|
|
135 | fputs("</U>",of); |
|
|
136 | if (old->strike_out) |
|
|
137 | fputs("</STRIKE>",of); |
|
|
138 | if (old->super_sub == psiconv_superscript) |
142 | if (layout->super_sub != psiconv_normalscript) |
139 | fputs("</SUP>",of); |
143 | output_simple_chars(config,list, |
|
|
144 | layout->super_sub == psiconv_superscript?"<sup>": |
|
|
145 | layout->super_sub == psiconv_subscript?"<sub>": |
|
|
146 | "",enc); |
|
|
147 | |
|
|
148 | output_simple_chars(config,list,"<span style=\"",enc); |
|
|
149 | |
|
|
150 | if (layout->underline || layout->strikethrough) { |
|
|
151 | output_simple_chars(config,list,"text-decoration:",enc); |
|
|
152 | output_simple_chars(config,list,layout->underline?"underline": |
|
|
153 | layout->strikethrough?"line-through": |
|
|
154 | "",enc); |
|
|
155 | output_simple_chars(config,list,";",enc); |
|
|
156 | } |
|
|
157 | |
|
|
158 | output_simple_chars(config,list,"color:",enc); |
|
|
159 | color(config,list,layout->color,type,enc); |
|
|
160 | output_simple_chars(config,list,";",enc); |
|
|
161 | |
|
|
162 | output_simple_chars(config,list,"background-color:",enc); |
|
|
163 | color(config,list,layout->back_color,type,enc); |
|
|
164 | output_simple_chars(config,list,";",enc); |
|
|
165 | |
|
|
166 | output_simple_chars(config,list,"font-size:",enc); |
|
|
167 | snprintf(tempstr,TEMPSTR_LEN,"%f",layout->font_size); |
|
|
168 | output_simple_chars(config,list,tempstr,enc); |
|
|
169 | output_simple_chars(config,list,"pt;",enc); |
|
|
170 | |
|
|
171 | output_simple_chars(config,list,"\">",enc); |
|
|
172 | |
|
|
173 | output_string(config,list,text,enc); |
|
|
174 | |
|
|
175 | output_simple_chars(config,list,"</span>",enc); |
140 | if (old->super_sub == psiconv_subscript) |
176 | if (layout->super_sub != psiconv_normalscript) |
141 | fputs("</SUB>",of); |
177 | output_simple_chars(config,list, |
142 | if ((*flags & 1) == 1) |
178 | layout->super_sub == psiconv_superscript?"</sup>": |
143 | fputs("</FONT>",of); |
179 | layout->super_sub == psiconv_subscript?"</sub>": |
144 | if ((*flags & 2) == 0) { |
180 | "",enc); |
145 | *flags |= 1; |
181 | if (layout->bold) |
146 | fputs("<FONT SIZE=",of); |
182 | output_simple_chars(config,list,"</b>",enc); |
147 | if (new->font_size <= 8.0) |
183 | if (layout->italic) |
148 | fputs("1",of); |
184 | output_simple_chars(config,list,"</i>",enc); |
149 | else if (new->font_size <= 10.0) |
185 | } |
150 | fputs("2",of); |
186 | |
151 | else if (new->font_size <= 12.0) |
187 | void paragraph(const psiconv_config config, psiconv_list list, |
152 | fputs("3",of); |
188 | psiconv_paragraph para,output_type type, |
153 | else if (new->font_size <= 14.0) |
189 | const encoding enc) |
154 | fputs("4",of); |
190 | { |
155 | else if (new->font_size <= 18.0) |
191 | char tempstr[TEMPSTR_LEN]; |
156 | fputs("5",of); |
192 | int i,charnr; |
157 | else if (new->font_size <= 24.0) |
193 | psiconv_string_t text; |
158 | fputs("6",of); |
194 | psiconv_in_line_layout layout; |
|
|
195 | |
|
|
196 | output_simple_chars(config,list,"<p style=\"",enc); |
|
|
197 | |
|
|
198 | output_simple_chars(config,list,"background-color:",enc); |
|
|
199 | color(config,list,para->base_paragraph->back_color,type,enc); |
|
|
200 | output_simple_chars(config,list,";",enc); |
|
|
201 | |
|
|
202 | output_simple_chars(config,list,"padding-left:",enc); |
|
|
203 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->indent_left); |
|
|
204 | output_simple_chars(config,list,tempstr,enc); |
|
|
205 | output_simple_chars(config,list,"cm;",enc); |
|
|
206 | |
|
|
207 | output_simple_chars(config,list,"padding-right:",enc); |
|
|
208 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->indent_right); |
|
|
209 | output_simple_chars(config,list,tempstr,enc); |
|
|
210 | output_simple_chars(config,list,"cm;",enc); |
|
|
211 | |
|
|
212 | output_simple_chars(config,list,"text-indent:",enc); |
|
|
213 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->indent_left - para->base_paragraph->indent_first); |
|
|
214 | output_simple_chars(config,list,tempstr,enc); |
|
|
215 | output_simple_chars(config,list,"cm;",enc); |
|
|
216 | |
|
|
217 | output_simple_chars(config,list,"text-align:",enc); |
|
|
218 | output_simple_chars(config,list,para->base_paragraph->justify_hor==psiconv_justify_left?"left": |
|
|
219 | para->base_paragraph->justify_hor==psiconv_justify_centre?"center": |
|
|
220 | para->base_paragraph->justify_hor==psiconv_justify_right?"right": |
|
|
221 | para->base_paragraph->justify_hor==psiconv_justify_full?"justify": |
|
|
222 | "",enc); |
|
|
223 | output_simple_chars(config,list,";",enc); |
|
|
224 | |
|
|
225 | |
|
|
226 | output_simple_chars(config,list,"line-height:",enc); |
|
|
227 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->linespacing); |
|
|
228 | output_simple_chars(config,list,tempstr,enc); |
|
|
229 | output_simple_chars(config,list,"pt;",enc); |
|
|
230 | |
|
|
231 | output_simple_chars(config,list,"padding-top:",enc); |
|
|
232 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->space_above); |
|
|
233 | output_simple_chars(config,list,tempstr,enc); |
|
|
234 | output_simple_chars(config,list,"pt;",enc); |
|
|
235 | |
|
|
236 | output_simple_chars(config,list,"padding-bottom:",enc); |
|
|
237 | snprintf(tempstr,TEMPSTR_LEN,"%f",para->base_paragraph->space_below); |
|
|
238 | output_simple_chars(config,list,tempstr,enc); |
|
|
239 | output_simple_chars(config,list,"pt;",enc); |
|
|
240 | |
|
|
241 | output_simple_chars(config,list,"\">",enc); |
|
|
242 | |
|
|
243 | if (psiconv_list_length(para->in_lines) == 0) { |
|
|
244 | charlayout(config,list,para->text,para->base_character,type,enc); |
159 | else |
245 | } else { |
160 | fputs("7",of); |
246 | charnr = 0; |
161 | fprintf(of," COLOR=#%02x%02x%02x",new->color->red,new->color->green, |
247 | for (i = 0; i < psiconv_list_length(para->in_lines); i++) { |
162 | new->color->blue); |
248 | if (!(layout = psiconv_list_get(para->in_lines,i))) { |
163 | if (new->font->screenfont == 1) |
249 | fputs("Internal data structures corruption\n",stderr); |
164 | fprintf(of," FACE=\"%s, Sans-Serif\">",new->font->name); |
250 | exit(1); |
165 | else if (new->font->screenfont == 2) |
251 | } |
166 | fprintf(of," FACE=\"%s, Monospace\">",new->font-> name); |
252 | if (!(text = malloc(sizeof (*text) * (layout->length + 1)))) { |
167 | else if (new->font->screenfont == 3) |
253 | fputs("Out of memory error\n",stderr); |
168 | fprintf(of," FACE=\"%s, Serif\">",new->font-> name); |
254 | exit(1); |
169 | else |
255 | } |
170 | fprintf(of," FACE=\"%s, Serif\">",new->font-> name); |
256 | memcpy(text,para->text+charnr,layout->length * sizeof(*text)); |
|
|
257 | text[layout->length] = 0; |
|
|
258 | charlayout(config,list,text,layout->layout,type,enc); |
|
|
259 | free(text); |
|
|
260 | charnr += layout->length; |
171 | } |
261 | } |
172 | if (new->italic) |
|
|
173 | fputs("<I>",of); |
|
|
174 | if (new->bold) |
|
|
175 | fputs("<B>",of); |
|
|
176 | if (new->underline) |
|
|
177 | fputs("<U>",of); |
|
|
178 | if (new->strike_out) |
|
|
179 | fputs("<STRIKE>",of); |
|
|
180 | if (new->super_sub == psiconv_superscript) |
|
|
181 | fputs("<SUP>",of); |
|
|
182 | if (new->super_sub == psiconv_subscript) |
|
|
183 | fputs("<SUB>",of); |
|
|
184 | } else { |
|
|
185 | if (font_set || (old->italic != new->italic)) { |
|
|
186 | if (old->italic) |
|
|
187 | fputs("</I>",of); |
|
|
188 | else |
|
|
189 | fputs("<I>",of); |
|
|
190 | } |
262 | } |
191 | if (old->bold != new->bold) { |
263 | output_simple_chars(config,list,"</p>\n",enc); |
192 | if (old->bold) |
|
|
193 | fputs("</B>",of); |
|
|
194 | else |
|
|
195 | fputs("<B>",of); |
|
|
196 | } |
|
|
197 | if (old->underline != new->underline) { |
|
|
198 | if (old->underline) |
|
|
199 | fputs("</U>",of); |
|
|
200 | else |
|
|
201 | fputs("<U>",of); |
|
|
202 | } |
|
|
203 | if (old->strike_out != new->strike_out) { |
|
|
204 | if (old->strike_out) |
|
|
205 | fputs("</STRIKE>",of); |
|
|
206 | else |
|
|
207 | fputs("<STRIKE>",of); |
|
|
208 | } |
|
|
209 | if (old->super_sub != new->super_sub) { |
|
|
210 | if (old->super_sub == psiconv_superscript) |
|
|
211 | fputs("</SUP>",of); |
|
|
212 | else if (old->super_sub == psiconv_subscript) |
|
|
213 | fputs("</SUB>",of); |
|
|
214 | if (new->super_sub == psiconv_superscript) |
|
|
215 | fputs("<SUP>",of); |
|
|
216 | else if (new->super_sub == psiconv_subscript) |
|
|
217 | fputs("<SUB>",of); |
|
|
218 | } |
|
|
219 | } |
|
|
220 | } |
264 | } |
221 | |
265 | |
222 | void gen_para(FILE *of, const psiconv_paragraph para, |
266 | void paragraphs(const psiconv_config config, psiconv_list list, |
223 | const psiconv_character_layout base_char) |
267 | psiconv_text_and_layout paragraphs,output_type type, |
224 | { |
268 | const encoding enc) |
225 | int i,j,loc; |
|
|
226 | psiconv_character_layout cur_char; |
|
|
227 | psiconv_in_line_layout inl; |
|
|
228 | int flags = 0; |
|
|
229 | |
|
|
230 | |
|
|
231 | fputs("<P",of); |
|
|
232 | if (para->base_paragraph->justify_hor == psiconv_justify_left) |
|
|
233 | fputs(" ALIGN=left",of); |
|
|
234 | else if (para->base_paragraph->justify_hor == psiconv_justify_right) |
|
|
235 | fputs(" ALIGN=right",of); |
|
|
236 | else if (para->base_paragraph->justify_hor == psiconv_justify_centre) |
|
|
237 | fputs(" ALIGN=center",of); |
|
|
238 | else if (para->base_paragraph->justify_hor == psiconv_justify_full) |
|
|
239 | fputs(" ALIGN=left",of); |
|
|
240 | fputs(">",of); |
|
|
241 | if (para->base_paragraph->bullet->on) |
|
|
242 | fputs("<UL><LI>",of); |
|
|
243 | |
|
|
244 | cur_char = base_char; |
|
|
245 | |
|
|
246 | if (psiconv_list_length(para->in_lines) == 0) { |
|
|
247 | diff_char(of,cur_char,para->base_character,&flags); |
|
|
248 | cur_char = para->base_character; |
|
|
249 | } |
|
|
250 | loc = 0; |
|
|
251 | |
|
|
252 | for (i = 0; i < psiconv_list_length(para->in_lines); i++) { |
|
|
253 | inl = psiconv_list_get(para->in_lines,i); |
|
|
254 | diff_char(of,cur_char,inl->layout,&flags); |
|
|
255 | cur_char = inl->layout; |
|
|
256 | for (j = loc; j < inl->length + loc; j ++) { |
|
|
257 | fputs(char_table[(unsigned char) (para->text[j])],of); |
|
|
258 | } |
|
|
259 | loc = j; |
|
|
260 | } |
|
|
261 | |
|
|
262 | if (loc < strlen(para->text)) { |
|
|
263 | diff_char(of,cur_char,para->base_character,&flags); |
|
|
264 | cur_char = para->base_character; |
|
|
265 | for (j = loc; j < strlen(para->text); j ++) { |
|
|
266 | fputs(char_table[(unsigned char) (para->text[j])],of); |
|
|
267 | } |
|
|
268 | } |
|
|
269 | |
|
|
270 | if (strlen(para->text) == 0) |
|
|
271 | fputs("<BR>",of); |
|
|
272 | |
|
|
273 | flags |= 2; |
|
|
274 | diff_char(of,cur_char,base_char,&flags); |
|
|
275 | |
|
|
276 | if (para->base_paragraph->bullet->on) |
|
|
277 | fputs("</UL>",of); |
|
|
278 | |
|
|
279 | fputs("</P>\n",of); |
|
|
280 | } |
|
|
281 | |
|
|
282 | int psiconv_gen_html(const char * filename,const psiconv_file file, |
|
|
283 | const char *dest) |
|
|
284 | { |
|
|
285 | FILE *of = fopen(filename,"w"); |
|
|
286 | if (! of) |
|
|
287 | return -1; |
|
|
288 | |
|
|
289 | if (file->type == psiconv_word_file) { |
|
|
290 | psiconv_gen_html_word(of,(psiconv_word_f) file->file); |
|
|
291 | } else if (file->type == psiconv_texted_file) { |
|
|
292 | psiconv_gen_html_texted(of,(psiconv_texted_f) file->file); |
|
|
293 | } else { |
|
|
294 | fclose(of); |
|
|
295 | return -1; |
|
|
296 | } |
|
|
297 | return fclose(of); |
|
|
298 | } |
|
|
299 | |
|
|
300 | void psiconv_gen_html_texted(FILE *of,psiconv_texted_f tf) |
|
|
301 | { |
|
|
302 | psiconv_character_layout base_char; |
|
|
303 | psiconv_paragraph para; |
|
|
304 | int i; |
|
|
305 | |
|
|
306 | /* We have nothing better */ |
|
|
307 | base_char = psiconv_basic_character_layout(); |
|
|
308 | |
|
|
309 | fputs("<!doctype html public \"-//W3C//DTD HTML 3.2 Final//EN\">", of); |
|
|
310 | fputs("\n<HTML>\n<HEAD>\n <META NAME=\"GENERATOR\"", of); |
|
|
311 | fputs(" CONTENT=\"psiconv-" VERSION "\">\n", of); |
|
|
312 | fputs("<BODY>\n",of); |
|
|
313 | for (i = 0; i < psiconv_list_length(tf->texted_sec->paragraphs); i++) { |
|
|
314 | para = psiconv_list_get(tf->texted_sec->paragraphs,i); |
|
|
315 | gen_para(of,para,base_char); |
|
|
316 | } |
|
|
317 | fputs("</BODY>\n</HTML>\n",of); |
|
|
318 | psiconv_free_character_layout(base_char); |
|
|
319 | } |
|
|
320 | |
|
|
321 | |
|
|
322 | void psiconv_gen_html_word(FILE *of,psiconv_word_f wf) |
|
|
323 | { |
269 | { |
324 | int i; |
270 | int i; |
325 | psiconv_paragraph para; |
271 | psiconv_paragraph para; |
326 | psiconv_color white,black; |
|
|
327 | psiconv_character_layout base_char; |
|
|
328 | |
|
|
329 | white = malloc(sizeof(*white)); |
|
|
330 | black = malloc(sizeof(*black)); |
|
|
331 | white->red = 0x00; |
|
|
332 | white->green = 0x00; |
|
|
333 | white->blue = 0x00; |
|
|
334 | black->red = 0xff; |
|
|
335 | black->green = 0xff; |
|
|
336 | black->blue = 0xff; |
|
|
337 | |
|
|
338 | /* To keep from generating a font desc for each line */ |
|
|
339 | base_char = gen_base_char(wf->styles_sec->normal->character->font, |
|
|
340 | black,white); |
|
|
341 | |
|
|
342 | psiconv_free_color(black); |
|
|
343 | psiconv_free_color(white); |
|
|
344 | |
|
|
345 | fputs("<!doctype html public \"-//W3C//DTD HTML 3.2 Final//EN\">", of); |
|
|
346 | fputs("\n<HTML>\n<HEAD>\n <META NAME=\"GENERATOR\"", of); |
|
|
347 | fputs(" CONTENT=\"psiconv-" VERSION "\">\n", of); |
|
|
348 | fputs("<BODY>\n",of); |
|
|
349 | |
|
|
350 | for (i = 0; i < psiconv_list_length(wf->paragraphs); i++) { |
272 | for (i = 0; i < psiconv_list_length(paragraphs); i++) { |
351 | para = psiconv_list_get(wf->paragraphs,i); |
273 | if (!(para = psiconv_list_get(paragraphs,i))) { |
352 | gen_para(of,para,base_char); |
274 | fputs("Internal datastructure corruption\n",stderr); |
|
|
275 | exit(1); |
353 | } |
276 | } |
354 | fputs("</BODY>\n</HTML>\n",of); |
277 | paragraph(config,list,para,type,enc); |
355 | psiconv_free_character_layout(base_char); |
278 | } |
356 | } |
279 | } |
357 | |
280 | |
|
|
281 | void gen_html_word(const psiconv_config config, psiconv_list list, |
|
|
282 | const psiconv_word_f file, output_type type, |
|
|
283 | const encoding enc) |
|
|
284 | { |
|
|
285 | if (!file) |
|
|
286 | return; |
|
|
287 | |
|
|
288 | header(config,list,type,enc); |
|
|
289 | paragraphs(config,list,file->paragraphs,type,enc); |
|
|
290 | footer(config,list,type,enc); |
|
|
291 | } |
|
|
292 | |
|
|
293 | |
|
|
294 | void gen_html_texted(const psiconv_config config, psiconv_list list, |
|
|
295 | const psiconv_texted_f file, output_type type, |
|
|
296 | const encoding enc) |
|
|
297 | { |
|
|
298 | header(config,list,type,enc); |
|
|
299 | paragraphs(config,list,file->texted_sec->paragraphs,type,enc); |
|
|
300 | footer(config,list,type,enc); |
|
|
301 | } |
|
|
302 | |
|
|
303 | int gen_html(const psiconv_config config, psiconv_list list, |
|
|
304 | const psiconv_file file, const char *dest, |
|
|
305 | const encoding enc) |
|
|
306 | { |
|
|
307 | output_type type; |
|
|
308 | |
|
|
309 | if (!strcmp("HTML4",dest)) |
|
|
310 | type = output_html; |
|
|
311 | else if (!strcmp("XHTML",dest)) |
|
|
312 | type = output_xhtml; |
|
|
313 | else |
|
|
314 | return -1; |
|
|
315 | |
|
|
316 | if (enc == ENCODING_PSION) { |
|
|
317 | fputs("Unsupported encoding\n",stderr); |
|
|
318 | return -1; |
|
|
319 | } |
|
|
320 | |
|
|
321 | if (file->type == psiconv_word_file) { |
|
|
322 | gen_html_word(config,list,(psiconv_word_f) file->file,type,enc); |
|
|
323 | return 0; |
|
|
324 | } else if (file->type == psiconv_texted_file) { |
|
|
325 | gen_html_texted(config,list,(psiconv_texted_f) file->file,type, enc); |
|
|
326 | return 0; |
|
|
327 | } else |
|
|
328 | return -1; |
|
|
329 | } |
|
|
330 | |
|
|
331 | |
358 | static struct psiconv_fileformat ff = |
332 | static struct fileformat_s ffs[] = |
359 | { |
333 | { |
|
|
334 | { |
360 | "HTML3", |
335 | "XHTML", |
361 | "HTML 3.2, not verified so probably not completely compliant", |
336 | "XHTML 1.0 Strict, using CSS for formatting", |
362 | &psiconv_gen_html |
337 | gen_html |
|
|
338 | }, |
|
|
339 | { |
|
|
340 | "HTML4", |
|
|
341 | "HTML 4.01 Strict, using CSS for formatting", |
|
|
342 | gen_html |
|
|
343 | }, |
|
|
344 | { |
|
|
345 | NULL, |
|
|
346 | NULL, |
|
|
347 | NULL |
|
|
348 | } |
363 | }; |
349 | }; |
364 | |
350 | |
|
|
351 | |
365 | void init_html(void) |
352 | void init_html(void) |
366 | { |
353 | { |
|
|
354 | int i; |
|
|
355 | for (i = 0; ffs[i].name; i++) |
367 | psiconv_list_add(fileformat_list,&ff); |
356 | psiconv_list_add(fileformat_list,ffs+i); |
368 | } |
357 | } |