OSDN Git Service

Merge branch 'branch_0.12.0' into branch_0.13.0
[modchxj/mod_chxj.git] / src / chxj_jxhtml.c
1 /*
2  * Copyright (C) 2005-2009 Atsushi Konno All rights reserved.
3  * Copyright (C) 2005 QSDN,Inc. All rights reserved.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  *     http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 #include "chxj_jxhtml.h"
18 #include "chxj_hdml.h"
19 #include "chxj_dump.h"
20 #include "chxj_img_conv.h"
21 #include "chxj_qr_code.h"
22 #include "chxj_encoding.h"
23 #include "chxj_url_encode.h"
24 #include "chxj_str_util.h"
25 #include "chxj_header_inf.h"
26 #include "chxj_jreserved_tag.h"
27 #include "chxj_conv_z2h.h"
28
29
30 #define GET_JXHTML(X) ((jxhtml_t *)(X))
31 #undef W_L
32 #undef W_V
33 #define W_L(X)          do { jxhtml->out = BUFFERED_WRITE_LITERAL(jxhtml->out, &doc->buf, (X)); } while(0)
34 #define W_V(X)          do { jxhtml->out = (X) ? BUFFERED_WRITE_VALUE(jxhtml->out, &doc->buf, (X))  \
35                                                : BUFFERED_WRITE_LITERAL(jxhtml->out, &doc->buf, ""); } while(0)
36 #undef W_NLCODE
37 #define W_NLCODE()     do { char *nlcode = TO_NLCODE(jxhtml->conf); W_V(nlcode); } while (0)
38
39 static char *s_jxhtml_start_html_tag     (void *pdoc, Node *node);
40 static char *s_jxhtml_end_html_tag       (void *pdoc, Node *node);
41 static char *s_jxhtml_start_meta_tag     (void *pdoc, Node *node);
42 static char *s_jxhtml_end_meta_tag       (void *pdoc, Node *node);
43 static char *s_jxhtml_start_head_tag     (void *pdoc, Node *node);
44 static char *s_jxhtml_end_head_tag       (void *pdoc, Node *node);
45 static char *s_jxhtml_start_title_tag    (void *pdoc, Node *node);
46 static char *s_jxhtml_end_title_tag      (void *pdoc, Node *node);
47 static char *s_jxhtml_start_base_tag     (void *pdoc, Node *node);
48 static char *s_jxhtml_end_base_tag       (void *pdoc, Node *node);
49 static char *s_jxhtml_start_body_tag     (void *pdoc, Node *node);
50 static char *s_jxhtml_end_body_tag       (void *pdoc, Node *node);
51 static char *s_jxhtml_start_a_tag        (void *pdoc, Node *node);
52 static char *s_jxhtml_end_a_tag          (void *pdoc, Node *node);
53 static char *s_jxhtml_start_pre_tag      (void *pdoc, Node *node);
54 static char *s_jxhtml_end_pre_tag        (void *pdoc, Node *node);
55 static char *s_jxhtml_start_p_tag        (void *pdoc, Node *node);
56 static char *s_jxhtml_end_p_tag          (void *pdoc, Node *node);
57 static char *s_jxhtml_start_ul_tag       (void *pdoc, Node *node);
58 static char *s_jxhtml_end_ul_tag         (void *pdoc, Node *node);
59 static char *s_jxhtml_start_ol_tag       (void *pdoc, Node *node);
60 static char *s_jxhtml_end_ol_tag         (void *pdoc, Node *node);
61 static char *s_jxhtml_start_li_tag       (void *pdoc, Node *node);
62 static char *s_jxhtml_end_li_tag         (void *pdoc, Node *node);
63 static char *s_jxhtml_start_br_tag       (void *pdoc, Node *node);
64 static char *s_jxhtml_end_br_tag         (void *pdoc, Node *node);
65 static char *s_jxhtml_start_tr_tag       (void *pdoc, Node *node);
66 static char *s_jxhtml_end_tr_tag         (void *pdoc, Node *node);
67 static char *s_jxhtml_start_font_tag     (void *pdoc, Node *node);
68 static char *s_jxhtml_end_font_tag       (void *pdoc, Node *node);
69 static char *s_jxhtml_start_form_tag     (void *pdoc, Node *node);
70 static char *s_jxhtml_end_form_tag       (void *pdoc, Node *node);
71 static char *s_jxhtml_start_input_tag    (void *pdoc, Node *node);
72 static char *s_jxhtml_end_input_tag      (void *pdoc, Node *node);
73 static char *s_jxhtml_start_center_tag   (void *pdoc, Node *node);
74 static char *s_jxhtml_end_center_tag     (void *pdoc, Node *node);
75 static char *s_jxhtml_start_hr_tag       (void *pdoc, Node *node);
76 static char *s_jxhtml_end_hr_tag         (void *pdoc, Node *node);
77 static char *s_jxhtml_start_img_tag      (void *pdoc, Node *node);
78 static char *s_jxhtml_end_img_tag        (void *pdoc, Node *node);
79 static char *s_jxhtml_start_select_tag   (void *pdoc, Node *node);
80 static char *s_jxhtml_end_select_tag     (void *pdoc, Node *node);
81 static char *s_jxhtml_start_option_tag   (void *pdoc, Node *node);
82 static char *s_jxhtml_end_option_tag     (void *pdoc, Node *node);
83 static char *s_jxhtml_start_div_tag      (void *pdoc, Node *node);
84 static char *s_jxhtml_end_div_tag        (void *pdoc, Node *node);
85 static char *s_jxhtml_start_textarea_tag (void *pdoc, Node *node);
86 static char *s_jxhtml_end_textarea_tag   (void *pdoc, Node *node);
87 static char *s_jxhtml_start_b_tag        (void *pdoc, Node *node);
88 static char *s_jxhtml_end_b_tag          (void *pdoc, Node *node);
89 static char *s_jxhtml_chxjif_tag         (void *pdoc, Node *node); 
90 static char *s_jxhtml_text_tag           (void *pdoc, Node *node);
91 static char *s_jxhtml_start_blockquote_tag (void *pdoc, Node *node);
92 static char *s_jxhtml_end_blockquote_tag  (void *pdoc, Node *node);
93 static char *s_jxhtml_start_dir_tag      (void *pdoc, Node *node);
94 static char *s_jxhtml_end_dir_tag        (void *pdoc, Node *node);
95 static char *s_jxhtml_start_dl_tag       (void *pdoc, Node *node);
96 static char *s_jxhtml_end_dl_tag         (void *pdoc, Node *node);
97 static char *s_jxhtml_start_dt_tag       (void *pdoc, Node *node);
98 static char *s_jxhtml_end_dt_tag         (void *pdoc, Node *node);
99 static char *s_jxhtml_start_dd_tag       (void *pdoc, Node *node);
100 static char *s_jxhtml_end_dd_tag         (void *pdoc, Node *node);
101 static char *s_jxhtml_start_h1_tag       (void *pdoc, Node *node);
102 static char *s_jxhtml_end_h1_tag         (void *pdoc, Node *node);
103 static char *s_jxhtml_start_h2_tag       (void *pdoc, Node *node);
104 static char *s_jxhtml_end_h2_tag         (void *pdoc, Node *node);
105 static char *s_jxhtml_start_h3_tag       (void *pdoc, Node *node);
106 static char *s_jxhtml_end_h3_tag         (void *pdoc, Node *node);
107 static char *s_jxhtml_start_h4_tag       (void *pdoc, Node *node);
108 static char *s_jxhtml_end_h4_tag         (void *pdoc, Node *node);
109 static char *s_jxhtml_start_h5_tag       (void *pdoc, Node *node);
110 static char *s_jxhtml_end_h5_tag         (void *pdoc, Node *node);
111 static char *s_jxhtml_start_h6_tag       (void *pdoc, Node *node);
112 static char *s_jxhtml_end_h6_tag         (void *pdoc, Node *node);
113 static char *s_jxhtml_start_menu_tag     (void *pdoc, Node *node);
114 static char *s_jxhtml_end_menu_tag       (void *pdoc, Node *node);
115 static char *s_jxhtml_start_plaintext_tag       (void *pdoc, Node *node);
116 static char *s_jxhtml_start_plaintext_tag_inner (void *pdoc, Node *node);
117 static char *s_jxhtml_end_plaintext_tag         (void *pdoc, Node *node);
118 static char *s_jxhtml_start_blink_tag  (void *pdoc, Node *node);
119 static char *s_jxhtml_end_blink_tag    (void *pdoc, Node *node);
120 static char *s_jxhtml_start_marquee_tag (void *pdoc, Node *node);
121 static char *s_jxhtml_end_marquee_tag  (void *pdoc, Node *node);
122 static char *s_jxhtml_newline_mark       (void *pdoc, Node *node);
123 static char *s_jxhtml_link_tag           (void *pdoc, Node *node);
124 static char *s_jxhtml_start_span_tag     (void *pdoc, Node *node);
125 static char *s_jxhtml_end_span_tag       (void *pdoc, Node *node);
126 static char *s_jxhtml_style_tag       (void *pdoc, Node *node);
127
128 static void  s_init_jxhtml(jxhtml_t *jxhtml, Doc *doc, request_rec *r, device_table *spec);
129
130 static int   s_jxhtml_search_emoji(jxhtml_t *jxhtml, char *txt, char **rslt);
131
132 static css_prop_list_t *s_jxhtml_nopush_and_get_now_style(void *pdoc, Node *node, const char *style_attr_value);
133 static css_prop_list_t *s_jxhtml_push_and_get_now_style(void *pdoc, Node *node, const char *style_attr_value);
134
135
136
137 tag_handler jxhtml_handler[] = {
138   /* tagHTML */
139   {
140     s_jxhtml_start_html_tag,
141     s_jxhtml_end_html_tag,
142   },
143   /* tagMETA */
144   {
145     s_jxhtml_start_meta_tag,
146     s_jxhtml_end_meta_tag,
147   },
148   /* tagTEXTAREA */
149   {
150     s_jxhtml_start_textarea_tag,
151     s_jxhtml_end_textarea_tag,
152   },
153   /* tagP */
154   {
155     s_jxhtml_start_p_tag,
156     s_jxhtml_end_p_tag,
157   },
158   /* tagPRE */
159   {
160     s_jxhtml_start_pre_tag,
161     s_jxhtml_end_pre_tag,
162   },
163   /* tagUL */
164   {
165     s_jxhtml_start_ul_tag,
166     s_jxhtml_end_ul_tag,
167   },
168   /* tagLI */
169   {
170     s_jxhtml_start_li_tag,
171     s_jxhtml_end_li_tag,
172   },
173   /* tagOL */
174   {
175     s_jxhtml_start_ol_tag,
176     s_jxhtml_end_ol_tag,
177   },
178   /* tagH1 */
179   {
180     s_jxhtml_start_h1_tag,
181     s_jxhtml_end_h1_tag,
182   },
183   /* tagH2 */
184   {
185     s_jxhtml_start_h2_tag,
186     s_jxhtml_end_h2_tag,
187   },
188   /* tagH3 */
189   {
190     s_jxhtml_start_h3_tag,
191     s_jxhtml_end_h3_tag,
192   },
193   /* tagH4 */
194   {
195     s_jxhtml_start_h4_tag,
196     s_jxhtml_end_h4_tag,
197   },
198   /* tagH5 */
199   {
200     s_jxhtml_start_h5_tag,
201     s_jxhtml_end_h5_tag,
202   },
203   /* tagH6 */
204   {
205     s_jxhtml_start_h6_tag,
206     s_jxhtml_end_h6_tag,
207   },
208   /* tagHEAD */
209   {
210     s_jxhtml_start_head_tag,
211     s_jxhtml_end_head_tag,
212   },
213   /* tagTITLE */
214   {
215     s_jxhtml_start_title_tag,
216     s_jxhtml_end_title_tag,
217   },
218   /* tagBASE */
219   {
220     s_jxhtml_start_base_tag,
221     s_jxhtml_end_base_tag,
222   },
223   /* tagBODY */
224   {
225     s_jxhtml_start_body_tag,
226     s_jxhtml_end_body_tag,
227   },
228   /* tagA */
229   {
230     s_jxhtml_start_a_tag,
231     s_jxhtml_end_a_tag,
232   },
233   /* tagBR */
234   {
235     s_jxhtml_start_br_tag,
236     s_jxhtml_end_br_tag,
237   },
238   /* tagTABLE */
239   {
240     NULL,
241     NULL,
242   },
243   /* tagTR */
244   {
245     s_jxhtml_start_tr_tag,
246     s_jxhtml_end_tr_tag,
247   },
248   /* tagTD */
249   {
250     NULL,
251     NULL,
252   },
253   /* tagTBODY */
254   {
255     NULL,
256     NULL,
257   },
258   /* tagFONT */
259   {
260     s_jxhtml_start_font_tag,
261     s_jxhtml_end_font_tag,
262   },
263   /* tagFORM */
264   {
265     s_jxhtml_start_form_tag,
266     s_jxhtml_end_form_tag,
267   },
268   /* tagINPUT */
269   {
270     s_jxhtml_start_input_tag,
271     s_jxhtml_end_input_tag,
272   },
273   /* tagCENTER */
274   {
275     s_jxhtml_start_center_tag,
276     s_jxhtml_end_center_tag,
277   },
278   /* tagHR */
279   {
280     s_jxhtml_start_hr_tag,
281     s_jxhtml_end_hr_tag,
282   },
283   /* tagIMG */
284   {
285     s_jxhtml_start_img_tag,
286     s_jxhtml_end_img_tag,
287   },
288   /* tagSELECT */
289   {
290     s_jxhtml_start_select_tag,
291     s_jxhtml_end_select_tag,
292   },
293   /* tagOPTION */
294   {
295     s_jxhtml_start_option_tag,
296     s_jxhtml_end_option_tag,
297   },
298   /* tagDIV */
299   {
300     s_jxhtml_start_div_tag,
301     s_jxhtml_end_div_tag,
302   },
303   /* tagCHXJIF */
304   {
305     s_jxhtml_chxjif_tag,
306     NULL,
307   },
308   /* tagNOBR */
309   {
310     NULL,
311     NULL,
312   },
313   /* tagSMALL */
314   {
315     NULL,
316     NULL,
317   },
318   /* tagSTYLE */
319   {
320     s_jxhtml_style_tag,
321     NULL,
322   },
323   /* tagSPAN */
324   {
325     s_jxhtml_start_span_tag,
326     s_jxhtml_end_span_tag,
327   },
328   /* tagTEXT */
329   {
330     s_jxhtml_text_tag,
331     NULL,
332   },
333   /* tagTH */
334   {
335     NULL,
336     NULL,
337   },
338   /* tagB */
339   {
340     s_jxhtml_start_b_tag,
341     s_jxhtml_end_b_tag,
342   },
343   /* tagFIELDSET */
344   {
345     NULL,
346     NULL,
347   },
348   /* tagDT */
349   {
350     s_jxhtml_start_dt_tag,
351     s_jxhtml_end_dt_tag,
352   },
353   /* tagLEGEND */
354   {
355     NULL,
356     NULL,
357   },
358   /* tagLABEL */
359   {
360     NULL,
361     NULL,
362   },
363   /* tagBLOCKQUOTE */
364   {
365     s_jxhtml_start_blockquote_tag,
366     s_jxhtml_end_blockquote_tag,
367   },
368   /* tagDIR */
369   {
370     s_jxhtml_start_dir_tag,
371     s_jxhtml_end_dir_tag,
372   },
373   /* tagDL */
374   {
375     s_jxhtml_start_dl_tag,
376     s_jxhtml_end_dl_tag,
377   },
378   /* tagDD */
379   {
380     s_jxhtml_start_dd_tag,
381     s_jxhtml_end_dd_tag,
382   },
383   /* tagMENU */
384   {
385     s_jxhtml_start_menu_tag,
386     s_jxhtml_end_menu_tag,
387   },
388   /* tagPLAINTEXT */
389   {
390     s_jxhtml_start_plaintext_tag,
391     s_jxhtml_end_plaintext_tag,
392   },
393   /* tagBLINK */
394   {
395     s_jxhtml_start_blink_tag,
396     s_jxhtml_end_blink_tag,
397   },
398   /* tagMARQUEE */
399   {
400     s_jxhtml_start_marquee_tag,
401     s_jxhtml_end_marquee_tag,
402   },
403   /* tagLINK */
404   {
405     s_jxhtml_link_tag,
406     NULL,
407   },
408   /* tagNLMARK */
409   {
410     s_jxhtml_newline_mark,
411     NULL,
412   },
413 };
414
415
416 /**
417  * converts from CHTML5.0 to JXHTML.
418  *
419  * @param r     [i]   Requet_rec is appointed.
420  * @param spec  [i]   The result of the device specification processing which 
421  *                    was done in advance is appointed.
422  * @param src   [i]   The character string before the converting is appointed.
423  * @return The character string after the converting is returned.
424  */
425 char *
426 chxj_convert_jxhtml(
427   request_rec         *r,
428   device_table        *spec,
429   const char          *src,
430   apr_size_t          srclen,
431   apr_size_t          *dstlen,
432   chxjconvrule_entry  *entryp,
433   cookie_t            *cookie
434 )
435 {
436   char      *dst;
437   char      *ss;
438   jxhtml_t   jxhtml;
439   Doc       doc;
440
441   dst = NULL;
442
443   /*--------------------------------------------------------------------------*/
444   /* If qrcode xml                                                            */
445   /*--------------------------------------------------------------------------*/
446   *dstlen = srclen;
447   dst = chxj_qr_code_blob_handler(r, src, (size_t*)dstlen);
448   if (dst) {
449     DBG(r,"I found qrcode xml");
450     return dst;
451   }
452   DBG(r,"not found qrcode xml");
453
454   /*--------------------------------------------------------------------------*/
455   /* The CHTML structure is initialized.                                      */
456   /*--------------------------------------------------------------------------*/
457   s_init_jxhtml(&jxhtml, &doc, r, spec);
458
459   jxhtml.entryp = entryp;
460   jxhtml.cookie = cookie;
461
462   chxj_set_content_type(r, chxj_header_inf_set_content_type(r, "application/xhtml+xml; charset=Windows-31J"));
463
464   /*--------------------------------------------------------------------------*/
465   /* The character string of the input is analyzed.                           */
466   /*--------------------------------------------------------------------------*/
467   qs_init_malloc(&doc);
468   qs_init_root_node(&doc);
469
470   ss = apr_pcalloc(r->pool, srclen + 1);
471
472   memset(ss,   0, srclen + 1);
473   memcpy(ss, src, srclen);
474
475   if (IS_CSS_ON(jxhtml.entryp)) {
476     /* current property list */
477     jxhtml.css_prop_stack = chxj_new_prop_list_stack(&doc);
478   }
479 #ifdef DUMP_LOG
480   chxj_dump_out("[src] CHTML -> JXHTML", ss, srclen);
481 #endif
482
483   qs_parse_string(&doc,ss,strlen(ss));
484
485   chxj_buffered_write_init(r->pool, &doc.buf);
486   /*--------------------------------------------------------------------------*/
487   /* It converts it from CHTML to JXHTML.                                     */
488   /*--------------------------------------------------------------------------*/
489   chxj_node_convert(spec,r,(void*)&jxhtml, &doc, qs_get_root(&doc), 0);
490   jxhtml.out = chxj_buffered_write_flush(jxhtml.out, &doc.buf);
491   dst = apr_pstrdup(r->pool, jxhtml.out);
492   chxj_buffered_write_terminate(&doc.buf);
493
494
495   qs_all_free(&doc,QX_LOGMARK);
496
497   if (! dst) 
498     return apr_pstrdup(r->pool,ss);
499
500   if (! strlen(dst)) 
501     dst = apr_psprintf(r->pool, "\n");
502
503   *dstlen = strlen(dst);
504
505 #ifdef DUMP_LOG
506   chxj_dump_out("[dst] CHTML -> JXHTML", dst, *dstlen);
507 #endif
508
509   return dst;
510 }
511
512
513 /**
514  * The JXHTML structure is initialized.
515  *
516  * @param jxhtml [i/o] The pointer to the JXHTML structure that wants to be
517  *                   initialized is specified.
518  * @param doc   [i]   The Doc structure that should be set to the initialized
519  *                   JXHTML structure is specified.
520  * @param r     [i]   To use POOL, the pointer to request_rec is specified.
521  * @param spec  [i]   The pointer to the device_table
522  */
523 static void
524 s_init_jxhtml(jxhtml_t *jxhtml, Doc *doc, request_rec *r, device_table *spec)
525 {
526   memset(doc,   0, sizeof(Doc));
527   memset(jxhtml, 0, sizeof(jxhtml_t));
528
529   doc->r      = r;
530   jxhtml->doc  = doc;
531   jxhtml->spec = spec;
532   jxhtml->out  = qs_alloc_zero_byte_string(r->pool);
533   jxhtml->conf = chxj_get_module_config(r->per_dir_config, &chxj_module);
534   jxhtml->doc->parse_mode = PARSE_MODE_CHTML;
535 }
536
537
538 /**
539  * Corresponding EMOJI to a current character-code is retrieved. 
540  * The substitution character string is stored in the rslt pointer if agreeing.
541  *
542  * @param jxhtml   [i]   The pointer to the JXHTML structure is specified. 
543  * @param txt     [i]   The character string to want to examine whether it is 
544  *                      EMOJI is specified. 
545  * @param rslt    [o]   The pointer to the pointer that stores the result is 
546  *                      specified. 
547  * @return When corresponding EMOJI exists, it returns it excluding 0. 
548  */
549 static int
550 s_jxhtml_search_emoji(jxhtml_t *jxhtml, char *txt, char **rslt)
551 {
552   emoji_t       *ee;
553   request_rec   *r;
554   device_table  *spec;
555   int           len;
556
557   spec = jxhtml->spec;
558
559   len = strlen(txt);
560   r = jxhtml->doc->r;
561
562   if (! spec) DBG(r,"spec is NULL");
563
564   for (ee = jxhtml->conf->emoji;
565        ee;
566        ee = ee->next) {
567
568     unsigned char hex1byte;
569     unsigned char hex2byte;
570
571     if (! ee->imode) { 
572       DBG(r,"emoji->imode is NULL");
573       continue;
574     }
575
576     hex1byte = ee->imode->hex1byte & 0xff;
577     hex2byte = ee->imode->hex2byte & 0xff;
578
579     if (ee->imode->string
580     &&  strlen(ee->imode->string) > 0
581     &&  strncasecmp(ee->imode->string, txt, strlen(ee->imode->string)) == 0) {
582       if (spec == NULL || spec->emoji_type == NULL) {
583         *rslt = apr_psprintf(r->pool,"\e%s\ f", ee->jphone->string);
584         return strlen(ee->imode->string);
585       }
586
587       return 0;
588     }
589
590     if (len >= 2
591     && ((unsigned char)txt[0] & 0xff) == ((unsigned char)hex1byte)
592     && ((unsigned char)txt[1] & 0xff) == ((unsigned char)hex2byte)) {
593       if (spec == NULL || spec->emoji_type == NULL) {
594         *rslt = apr_psprintf(r->pool,"\e%s\ f", ee->jphone->string);
595         return 2;
596       }
597
598       return 0;
599     }
600   }
601
602   return 0;
603 }
604
605
606 char *
607 chxj_jxhtml_emoji_only_converter(request_rec *r, device_table *spec, const char *src, apr_size_t len)
608 {
609   apr_size_t ii;
610   Doc __doc;
611   Doc *doc;
612   jxhtml_t __jxhtml;
613   jxhtml_t *jxhtml;
614   char one_byte[2];
615   char two_byte[3];
616   apr_pool_t *pool;
617
618   jxhtml = &__jxhtml;
619   doc    = &__doc;
620
621   DBG(r, "REQ[%X] start chxj_jxhtml_emoji_eonly_converter()", (unsigned int)(apr_size_t)r);
622   memset(doc,    0, sizeof(Doc));
623   memset(jxhtml, 0, sizeof(jxhtml_t));
624
625   doc->r       = r;
626   jxhtml->doc  = doc;
627   jxhtml->spec = spec;
628   jxhtml->out  = qs_alloc_zero_byte_string(r->pool);
629   jxhtml->conf = chxj_get_module_config(r->per_dir_config, &chxj_module);
630   jxhtml->doc->parse_mode = PARSE_MODE_CHTML;
631
632   apr_pool_create(&pool, r->pool);
633
634   chxj_buffered_write_init(pool, &doc->buf);
635
636   for (ii=0; ii<len; ii++) {
637     char *out;
638     int   rtn;
639
640     rtn = s_jxhtml_search_emoji(jxhtml, (char *)&src[ii], &out);
641     if (rtn) {
642       W_V(out);
643       ii+=(rtn - 1);
644       continue;
645     }
646
647     if (is_sjis_kanji(src[ii])) {
648       two_byte[0] = src[ii+0];
649       two_byte[1] = src[ii+1];
650       two_byte[2] = 0;
651       W_V(two_byte);
652       ii++;
653     }
654     else {
655       one_byte[0] = src[ii+0];
656       one_byte[1] = 0;
657       W_V(one_byte);
658     }
659   }
660   jxhtml->out = chxj_buffered_write_flush(jxhtml->out, &doc->buf);
661
662   DBG(r, "REQ[%X] end chxj_jxhtml_emoji_eonly_converter()", (unsigned int)(apr_size_t)r);
663   return jxhtml->out;
664 }
665
666
667 /**
668  * It is a handler who processes the HTML tag.
669  *
670  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
671  *                     destination is specified.
672  * @param node   [i]   The HTML tag node is specified.
673  * @return The conversion result is returned.
674  */
675 static char *
676 s_jxhtml_start_html_tag(void *pdoc, Node *UNUSED(node)) 
677 {
678   jxhtml_t       *jxhtml;
679   Doc           *doc;
680   request_rec   *r;
681
682
683   jxhtml  = GET_JXHTML(pdoc);
684   doc    = jxhtml->doc;
685   r      = doc->r;
686   DBG(r, "REQ[%X] start s_jxhtml_start_html_tag()", TO_ADDR(r));
687
688   W_L("<?xml version=\"1.0\" encoding=\"Shift_JIS\" ?>");
689   W_NLCODE();
690   W_L("<!DOCTYPE html PUBLIC \"-//J-PHONE//DTD XHTML Basic 1.0 Plus//EN\" \"xhtml-basic10-plus.dtd\">");
691   W_NLCODE();
692
693   /*--------------------------------------------------------------------------*/
694   /* start HTML tag                                                           */
695   /*--------------------------------------------------------------------------*/
696   W_L("<html xmlns=\"http://www.w3.org/1999/xhtml\" lang=\"ja\" xml:lang=\"ja\">");
697
698   jxhtml->start_html_flag = 1;
699
700   DBG(r, "REQ[%X] end s_jxhtml_start_html_tag()", TO_ADDR(r));
701
702   return jxhtml->out;
703 }
704
705
706 /**
707  * It is a handler who processes the HTML tag.
708  *
709  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
710  *                     destination is specified.
711  * @param node   [i]   The HTML tag node is specified.
712  * @return The conversion result is returned.
713  */
714 static char *
715 s_jxhtml_end_html_tag(void *pdoc, Node *UNUSED(child)) 
716 {
717   jxhtml_t      *jxhtml = GET_JXHTML(pdoc);
718   Doc           *doc = jxhtml->doc;
719
720   W_L("</html>");
721
722   return jxhtml->out;
723 }
724
725
726 /**
727  * It is a handler who processes the META tag.
728  *
729  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
730  *                     destination is specified.
731  * @param node   [i]   The META tag node is specified.
732  * @return The conversion result is returned.
733  */
734 static char *
735 s_jxhtml_start_meta_tag(void *pdoc, Node *node) 
736 {
737   jxhtml_t     *jxhtml;
738   Doc          *doc;
739   request_rec  *r;
740   Attr         *attr;
741   int          content_type_flag;
742   int          refresh_flag;
743
744   jxhtml             = GET_JXHTML(pdoc);
745   doc               = jxhtml->doc;
746   r                 = doc->r;
747   refresh_flag      = 0;
748   content_type_flag = 0;
749
750   W_L("<meta");
751   /*--------------------------------------------------------------------------*/
752   /* Get Attributes                                                           */
753   /*--------------------------------------------------------------------------*/
754   for (attr = qs_get_attr(doc,node);
755        attr;
756        attr = qs_get_next_attr(doc,attr)) {
757     char *name   = qs_get_attr_name(doc,attr);
758     char *value  = qs_get_attr_value(doc,attr);
759     switch(*name) {
760     case 'h':
761     case 'H':
762       if (strcasecmp(name, "http-equiv") == 0 && value && *value) {
763         /*----------------------------------------------------------------------*/
764         /* CHTML 2.0                                                            */
765         /*----------------------------------------------------------------------*/
766         W_L(" http-equiv=\"");
767         W_V(value);
768         W_L("\"");
769         if (STRCASEEQ('c','C',"content-type",value)) {
770           content_type_flag = 1;
771         }
772         if (STRCASEEQ('r','R',"refresh",value)) {
773           refresh_flag = 1;
774         }
775       }
776       break;
777
778     case 'c':
779     case 'C':
780       if (strcasecmp(name, "content") == 0 && value && *value) {
781         /*----------------------------------------------------------------------*/
782         /* CHTML 2.0                                                            */
783         /*----------------------------------------------------------------------*/
784         if (content_type_flag)  {
785           W_L(" ");
786           W_V(name);
787           W_L("=\"");
788           W_V(chxj_header_inf_set_content_type(r, "application/xhtml+xml; charset=SHIFT_JIS"));
789           W_L("\"");
790         }
791         else
792         if (refresh_flag) {
793           char *buf;
794           char *sec;
795           char *url;
796   
797           buf = apr_pstrdup(r->pool, value);
798   
799           url = strchr(buf, ';');
800           if (url) {
801             sec = apr_pstrdup(r->pool, buf);
802             sec[url-buf] = 0;
803             url++;
804             url = chxj_encoding_parameter(r, url, 1);
805             W_L(" ");
806             W_V(name);
807             W_L("=\"");
808             W_V(sec);
809             W_L(";");
810             W_V(url);
811             W_L("\"");
812           }
813         }
814         else {
815           W_L(" ");
816           W_V(name);
817           W_L("=\"");
818           W_V(value);
819           W_L("\"");
820         }
821       }
822       break;
823     
824     default:
825       break;
826     }
827   }
828   W_L(" />");
829   return jxhtml->out;
830 }
831
832
833 /**
834  * It is a handler who processes the META tag.
835  *
836  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
837  *                     destination is specified.
838  * @param node   [i]   The META tag node is specified.
839  * @return The conversion result is returned.
840  */
841 static char *
842 s_jxhtml_end_meta_tag(void *pdoc, Node *UNUSED(child)) 
843 {
844   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
845
846   return jxhtml->out;
847 }
848
849
850 /**
851  * It is a handler who processes the HEAD tag.
852  *
853  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
854  *                     destination is specified.
855  * @param node   [i]   The HEAD tag node is specified.
856  * @return The conversion result is returned.
857  */
858 static char *
859 s_jxhtml_start_head_tag(void *pdoc, Node *UNUSED(node)) 
860 {
861   jxhtml_t      *jxhtml;
862   Doc           *doc;
863   request_rec   *r;
864
865   jxhtml = GET_JXHTML(pdoc);
866   doc   = jxhtml->doc;
867   r     = doc->r;
868
869   W_L("<head>");
870   return jxhtml->out;
871 }
872
873
874 /**
875  * It is a handler who processes the HEAD tag.
876  *
877  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
878  *                     destination is specified.
879  * @param node   [i]   The HEAD tag node is specified.
880  * @return The conversion result is returned.
881  */
882 static char *
883 s_jxhtml_end_head_tag(void *pdoc, Node *UNUSED(child)) 
884 {
885   jxhtml_t       *jxhtml;
886   Doc           *doc;
887   request_rec   *r;
888
889   jxhtml = GET_JXHTML(pdoc);
890   doc   = jxhtml->doc;
891   r     = doc->r;
892
893   W_L("</head>");
894   return jxhtml->out;
895 }
896
897
898 /**
899  * It is a handler who processes the TITLE tag.
900  *
901  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
902  *                     destination is specified.
903  * @param node   [i]   The TITLE tag node is specified.
904  * @return The conversion result is returned.
905  */
906 static char *
907 s_jxhtml_start_title_tag(void *pdoc, Node *UNUSED(node)) 
908 {
909   jxhtml_t      *jxhtml;
910   Doc          *doc;
911   request_rec  *r;
912
913   jxhtml = GET_JXHTML(pdoc);
914   doc   = jxhtml->doc;
915   r     = doc->r;
916
917   W_L("<title>");
918   return jxhtml->out;
919 }
920
921
922 /**
923  * It is a handler who processes the TITLE tag.
924  *
925  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
926  *                     destination is specified.
927  * @param node   [i]   The TITLE tag node is specified.
928  * @return The conversion result is returned.
929  */
930 static char *
931 s_jxhtml_end_title_tag(void *pdoc, Node *UNUSED(child)) 
932 {
933   jxhtml_t      *jxhtml;
934   Doc           *doc;
935   request_rec   *r;
936
937   jxhtml = GET_JXHTML(pdoc);
938   doc   = jxhtml->doc;
939   r     = doc->r;
940
941   W_L("</title>");
942   return jxhtml->out;
943 }
944
945
946 /**
947  * It is a handler who processes the BASE tag.
948  *
949  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
950  *                     destination is specified.
951  * @param node   [i]   The BASE tag node is specified.
952  * @return The conversion result is returned.
953  */
954 static char *
955 s_jxhtml_start_base_tag(void *pdoc, Node *node) 
956 {
957   jxhtml_t      *jxhtml;
958   Attr          *attr;
959   Doc           *doc;
960   request_rec   *r;
961
962   jxhtml = GET_JXHTML(pdoc);
963   doc   = jxhtml->doc;
964   r     = doc->r;
965
966   W_L("<base");
967   /*--------------------------------------------------------------------------*/
968   /* Get Attributes                                                           */
969   /*--------------------------------------------------------------------------*/
970   for (attr = qs_get_attr(doc,node);
971        attr;
972        attr = qs_get_next_attr(doc,attr)) {
973     char *name  = qs_get_attr_name(doc,attr);
974     char *value = qs_get_attr_value(doc,attr);
975     if (STRCASEEQ('h','H',"href",name)) {
976       W_L(" href=\"");
977       W_V(value);
978       W_L("\"");
979     }
980   }
981   W_L(" />");
982   return jxhtml->out;
983 }
984
985
986 /**
987  * It is a handler who processes the BASE tag.
988  *
989  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
990  *                     destination is specified.
991  * @param node   [i]   The BASE tag node is specified.
992  * @return The conversion result is returned.
993  */
994 static char *
995 s_jxhtml_end_base_tag(void *pdoc, Node *UNUSED(child)) 
996 {
997   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
998   return jxhtml->out;
999 }
1000
1001
1002 /**
1003  * It is a handler who processes the BODY tag.
1004  *
1005  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1006  *                     destination is specified.
1007  * @param node   [i]   The BODY tag node is specified.
1008  * @return The conversion result is returned.
1009  */
1010 static char *
1011 s_jxhtml_start_body_tag(void *pdoc, Node *node) 
1012 {
1013   jxhtml_t    *jxhtml;
1014   Doc         *doc;
1015   request_rec *r;
1016   Attr        *attr;
1017   char        *attr_bgcolor = NULL;
1018   char        *attr_text    = NULL;
1019   char        *attr_link    = NULL;
1020   char        *attr_style   = NULL;
1021
1022   jxhtml = GET_JXHTML(pdoc);
1023   doc   = jxhtml->doc;
1024   r     = doc->r;
1025
1026   /*--------------------------------------------------------------------------*/
1027   /* Get Attributes                                                           */
1028   /*--------------------------------------------------------------------------*/
1029   for (attr = qs_get_attr(doc,node);
1030        attr;
1031        attr = qs_get_next_attr(doc,attr)) {
1032     char *name   = qs_get_attr_name(doc,attr);
1033     char *value  = qs_get_attr_value(doc,attr);
1034     if (STRCASEEQ('b','B',"bgcolor",name) && value && *value) {
1035       /*----------------------------------------------------------------------*/
1036       /* CHTML 2.0                                                            */
1037       /*----------------------------------------------------------------------*/
1038       attr_bgcolor = value;
1039     }
1040     else if (STRCASEEQ('t','T',"text",name) && value && *value) {
1041       /*----------------------------------------------------------------------*/
1042       /* CHTML 2.0                                                            */
1043       /*----------------------------------------------------------------------*/
1044       attr_text = value;
1045     }
1046     else if (STRCASEEQ('l','L',"link",name) && value && *value) {
1047       /*----------------------------------------------------------------------*/
1048       /* CHTML 2.0                                                            */
1049       /*----------------------------------------------------------------------*/
1050       attr_link = value;
1051     }
1052     else if (STRCASEEQ('a','A',"alink",name)) {
1053       /*----------------------------------------------------------------------*/
1054       /* CHTML 4.0                                                            */
1055       /*----------------------------------------------------------------------*/
1056       /* ignore */
1057     }
1058     else if (STRCASEEQ('v','V',"vlink",name)) {
1059       /*----------------------------------------------------------------------*/
1060       /* CHTML 4.0                                                            */
1061       /*----------------------------------------------------------------------*/
1062       /* ignore */
1063     }
1064     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
1065       attr_style = value;
1066     }
1067   }
1068
1069   if (IS_CSS_ON(jxhtml->entryp)) {
1070     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
1071     if (style) {
1072       css_property_t *color_prop      = chxj_css_get_property_value(doc, style, "color");
1073       css_property_t *bgcolor_prop    = chxj_css_get_property_value(doc, style, "background-color");
1074       css_property_t *cur;
1075       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
1076         if (cur->value && *cur->value) {
1077           attr_text = apr_pstrdup(doc->pool, cur->value);
1078         }
1079       }
1080       for (cur = bgcolor_prop->next; cur != bgcolor_prop; cur = cur->next) {
1081         if (cur->value && *cur->value) {
1082           attr_bgcolor = apr_pstrdup(doc->pool, cur->value);
1083         }
1084       }
1085     }
1086     if (jxhtml->style) {
1087       css_stylesheet_t *pseudos = chxj_find_pseudo_selectors(doc, jxhtml->style);
1088       css_selector_t *cur_sel;
1089       for (cur_sel = pseudos->selector_head.next; cur_sel != &pseudos->selector_head; cur_sel = cur_sel->next) {
1090         if (cur_sel->name && strcasecmp(cur_sel->name, "a:link") == 0) {
1091           css_property_t *cur;
1092           for (cur = cur_sel->property_head.next; cur != &cur_sel->property_head; cur = cur->next) {
1093             if (cur->name && strcasecmp(cur->name, "color") == 0) {
1094               attr_link = apr_pstrdup(doc->pool, cur->value);
1095             }
1096           }
1097         }
1098       }
1099     }
1100   }
1101
1102
1103   W_L("<body");
1104   if (attr_bgcolor || attr_text) {
1105     W_L(" style=\"");
1106     if (attr_bgcolor) {
1107       attr_bgcolor = chxj_css_rgb_func_to_value(doc->pool, attr_bgcolor);
1108       W_L("background-color:");
1109       W_V(attr_bgcolor);
1110       W_L(";");
1111     }
1112     if (attr_text) {
1113       attr_text = chxj_css_rgb_func_to_value(doc->pool, attr_text);
1114       W_L("color:");
1115       W_V(attr_text);
1116       W_L(";");
1117     }
1118     W_L("\"");
1119   }
1120   if (attr_link) {
1121     attr_link = chxj_css_rgb_func_to_value(doc->pool, attr_link);
1122     W_L(" link=\"");
1123     W_V(attr_link);
1124     W_L("\"");
1125   }
1126   W_L("><div>");
1127   return jxhtml->out;
1128 }
1129
1130
1131 /**
1132  * It is a handler who processes the BODY tag.
1133  *
1134  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1135  *                     destination is specified.
1136  * @param node   [i]   The BODY tag node is specified.
1137  * @return The conversion result is returned.
1138  */
1139 static char *
1140 s_jxhtml_end_body_tag(void *pdoc, Node *UNUSED(child)) 
1141 {
1142   jxhtml_t       *jxhtml;
1143   Doc           *doc;
1144   request_rec   *r;
1145
1146   jxhtml = GET_JXHTML(pdoc);
1147   doc   = jxhtml->doc;
1148   r     = doc->r;
1149
1150   W_L("</div></body>");
1151   if (IS_CSS_ON(jxhtml->entryp)) {
1152     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
1153   }
1154   return jxhtml->out;
1155 }
1156
1157
1158 /**
1159  * It is a handler who processes the A tag.
1160  *
1161  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1162  *                     destination is specified.
1163  * @param node   [i]   The A tag node is specified.
1164  * @return The conversion result is returned.
1165  */
1166 static char *
1167 s_jxhtml_start_a_tag(void *pdoc, Node *node) 
1168 {
1169   jxhtml_t    *jxhtml;
1170   Doc         *doc;
1171   request_rec *r;
1172   Attr        *attr;
1173   char        *attr_style = NULL;
1174
1175   jxhtml = GET_JXHTML(pdoc);
1176   doc   = jxhtml->doc;
1177   r     = doc->r;
1178
1179   W_L("<a");
1180   /*--------------------------------------------------------------------------*/
1181   /* Get Attributes                                                           */
1182   /*--------------------------------------------------------------------------*/
1183   for (attr = qs_get_attr(doc,node);
1184        attr; 
1185        attr = qs_get_next_attr(doc,attr)) {
1186     char *name  = qs_get_attr_name(doc,attr);
1187     char *value = qs_get_attr_value(doc,attr);
1188     if (STRCASEEQ('n','N',"name",name)) {
1189       /*----------------------------------------------------------------------*/
1190       /* CHTML1.0                                                             */
1191       /*----------------------------------------------------------------------*/
1192       W_L(" name=\"");
1193       W_V(chxj_jreserved_to_safe_tag(r, value, jxhtml->entryp));
1194       W_L("\"");
1195     }
1196     else if (STRCASEEQ('h','H',"href",name)) {
1197       /*----------------------------------------------------------------------*/
1198       /* CHTML1.0                                                             */
1199       /*----------------------------------------------------------------------*/
1200       value = chxj_encoding_parameter(r, value, 1);
1201       if (! chxj_starts_with(value, "mailto:") && ! chxj_starts_with(value, "tel:")) {
1202         value = chxj_jreserved_tag_to_safe_for_query_string(r, value, jxhtml->entryp, 1);
1203       }
1204       W_L(" href=\"");
1205       W_V(value);
1206       W_L("\"");
1207     }
1208     else if (STRCASEEQ('a','A',"accesskey",name)) {
1209       /*----------------------------------------------------------------------*/
1210       /* CHTML1.0                                                             */
1211       /*----------------------------------------------------------------------*/
1212       W_L(" accesskey=\"");
1213       W_V(value);
1214       W_L("\"");
1215     }
1216     else if (STRCASEEQ('c','C',"cti",name)) {
1217       /*----------------------------------------------------------------------*/
1218       /* CHTML 2.0                                                            */
1219       /*----------------------------------------------------------------------*/
1220       W_L(" cti=\"");
1221       W_V(value);
1222       W_L("\"");
1223     }
1224     else if (STRCASEEQ('i','I',"ijam",name)) {
1225       /*----------------------------------------------------------------------*/
1226       /* CHTML 3.0                                                            */
1227       /*----------------------------------------------------------------------*/
1228       /* ignore */
1229     }
1230     else if (STRCASEEQ('u','U',"utn",name)) {
1231       /*----------------------------------------------------------------------*/
1232       /* CHTML 3.0                                                            */
1233       /* It is special only for CHTML.                                        */
1234       /*----------------------------------------------------------------------*/
1235       W_L(" utn ");
1236     }
1237     else if (STRCASEEQ('t','T',"telbook",name)) {
1238       /*----------------------------------------------------------------------*/
1239       /* CHTML 3.0                                                            */
1240       /*----------------------------------------------------------------------*/
1241       /* not support */
1242     }
1243     else if (STRCASEEQ('k','K',"kana",name)) {
1244       /*----------------------------------------------------------------------*/
1245       /* CHTML 3.0                                                            */
1246       /*----------------------------------------------------------------------*/
1247       /* not support */
1248     }
1249     else if (STRCASEEQ('e','E',"email",name)) {
1250       /*----------------------------------------------------------------------*/
1251       /* CHTML 3.0                                                            */
1252       /*----------------------------------------------------------------------*/
1253       /* not support */
1254     }
1255     else if (STRCASEEQ('i','I',"ista",name)) {
1256       /*----------------------------------------------------------------------*/
1257       /* CHTML 4.0                                                            */
1258       /*----------------------------------------------------------------------*/
1259       /* ignore */
1260     }
1261     else if (STRCASEEQ('i','I',"ilet",name)) {
1262       /*----------------------------------------------------------------------*/
1263       /* CHTML 5.0                                                            */
1264       /*----------------------------------------------------------------------*/
1265       /* ignore */
1266     }
1267     else if (STRCASEEQ('i','I',"iswf",name)) {
1268       /*----------------------------------------------------------------------*/
1269       /* CHTML 5.0                                                            */
1270       /*----------------------------------------------------------------------*/
1271       /* ignore */
1272     }
1273     else if (STRCASEEQ('i','I',"irst",name)) {
1274       /*----------------------------------------------------------------------*/
1275       /* CHTML 5.0                                                            */
1276       /*----------------------------------------------------------------------*/
1277       /* ignore */
1278     }
1279     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
1280       /*----------------------------------------------------------------------*/
1281       /* CHTML 5.0                                                            */
1282       /*----------------------------------------------------------------------*/
1283       attr_style = value;
1284     }
1285   }
1286   W_L(">");
1287
1288   if (IS_CSS_ON(jxhtml->entryp)) {
1289     s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
1290   }
1291
1292   return jxhtml->out;
1293 }
1294
1295
1296 /**
1297  * It is a handler who processes the A tag.
1298  *
1299  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1300  *                     destination is specified.
1301  * @param node   [i]   The A tag node is specified.
1302  * @return The conversion result is returned.
1303  */
1304 static char *
1305 s_jxhtml_end_a_tag(void *pdoc, Node *UNUSED(child)) 
1306 {
1307   jxhtml_t      *jxhtml;
1308   Doc          *doc;
1309   request_rec  *r;
1310
1311   jxhtml = GET_JXHTML(pdoc);
1312   doc   = jxhtml->doc;
1313   r     = doc->r;
1314
1315   W_L("</a>");
1316
1317   if (IS_CSS_ON(jxhtml->entryp)) {
1318     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
1319   }
1320
1321   return jxhtml->out;
1322 }
1323
1324
1325 /**
1326  * It is a handler who processes the BR tag.
1327  *
1328  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1329  *                     destination is specified.
1330  * @param node   [i]   The BR tag node is specified.
1331  * @return The conversion result is returned.
1332  */
1333 static char *
1334 s_jxhtml_start_br_tag(void *pdoc, Node *node)
1335 {
1336   jxhtml_t     *jxhtml;
1337   Doc          *doc;
1338   request_rec  *r;
1339   Attr         *attr;
1340
1341   jxhtml = GET_JXHTML(pdoc);
1342   doc   = jxhtml->doc;
1343   r     = doc->r;
1344
1345   W_L("<br");
1346   /*--------------------------------------------------------------------------*/
1347   /* Get Attributes                                                           */
1348   /*--------------------------------------------------------------------------*/
1349   for (attr = qs_get_attr(doc,node);
1350        attr;
1351        attr = qs_get_next_attr(doc,attr)) {
1352     char *name  = qs_get_attr_name(doc,attr);
1353     char *value = qs_get_attr_value(doc,attr);
1354     if (STRCASEEQ('c','C',"clear",name)) {
1355       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('a','A',"all",value))) {
1356         W_L(" clear=\"");
1357         W_V(value);
1358         W_L("\"");
1359       }
1360     }
1361   }
1362   W_L(" />");
1363   return jxhtml->out;
1364 }
1365
1366
1367 /**
1368  * It is a handler who processes the BR tag.
1369  *
1370  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1371  *                     destination is specified.
1372  * @param node   [i]   The BR tag node is specified.
1373  * @return The conversion result is returned.
1374  */
1375 static char *
1376 s_jxhtml_end_br_tag(void *pdoc, Node *UNUSED(child)) 
1377 {
1378   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
1379   return jxhtml->out;
1380 }
1381
1382
1383 /**
1384  * It is a handler who processes the TR tag.
1385  *
1386  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1387  *                     destination is specified.
1388  * @param node   [i]   The TR tag node is specified.
1389  * @return The conversion result is returned.
1390  */
1391 static char *
1392 s_jxhtml_start_tr_tag(void *pdoc, Node *UNUSED(node)) 
1393 {
1394   jxhtml_t      *jxhtml;
1395   Doc          *doc;
1396   request_rec  *r;
1397
1398   jxhtml = GET_JXHTML(pdoc);
1399   doc   = jxhtml->doc;
1400   r     = doc->r;
1401
1402   W_L("<br />");
1403   return jxhtml->out;
1404 }
1405
1406
1407 /**
1408  * It is a handler who processes the TR tag.
1409  *
1410  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1411  *                     destination is specified.
1412  * @param node   [i]   The TR tag node is specified.
1413  * @return The conversion result is returned.
1414  */
1415 static char *
1416 s_jxhtml_end_tr_tag(void *pdoc, Node *UNUSED(child)) 
1417 {
1418   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
1419   return jxhtml->out;
1420 }
1421
1422
1423 /**
1424  * It is a handler who processes the FONT tag.
1425  *
1426  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1427  *                     destination is specified.
1428  * @param node   [i]   The FONT tag node is specified.
1429  * @return The conversion result is returned.
1430  */
1431 static char *
1432 s_jxhtml_start_font_tag(void *pdoc, Node *node) 
1433 {
1434   jxhtml_t      *jxhtml;
1435   Doc           *doc;
1436   request_rec   *r;
1437   Attr          *attr;
1438   char          *attr_color = NULL;
1439   char          *attr_size  = NULL;
1440   char          *attr_style = NULL;
1441
1442   jxhtml = GET_JXHTML(pdoc);
1443   doc   = jxhtml->doc;
1444   r     = doc->r;
1445
1446   /*--------------------------------------------------------------------------*/
1447   /* Get Attributes                                                           */
1448   /*--------------------------------------------------------------------------*/
1449   for (attr = qs_get_attr(doc,node);
1450        attr; 
1451        attr = qs_get_next_attr(doc,attr)) {
1452     char *name  = qs_get_attr_name(doc,attr);
1453     char *value = qs_get_attr_value(doc,attr);
1454     if (STRCASEEQ('c','C',"color",name) && value && *value) {
1455       attr_color = apr_pstrdup(doc->buf.pool, value);
1456     }
1457     else if (STRCASEEQ('s','S',"size",name) && value && *value) {
1458       /*----------------------------------------------------------------------*/
1459       /* CHTML 5.0                                                            */
1460       /*----------------------------------------------------------------------*/
1461       attr_size = apr_pstrdup(doc->buf.pool, value);
1462     }
1463     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
1464       attr_style = apr_pstrdup(doc->buf.pool, value);
1465     }
1466   }
1467   if (IS_CSS_ON(jxhtml->entryp)) {
1468     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
1469     if (style) {
1470       css_property_t *color_prop = chxj_css_get_property_value(doc, style, "color");
1471       css_property_t *size_prop  = chxj_css_get_property_value(doc, style, "font-size");
1472       css_property_t *cur;
1473       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
1474         if (cur->value && *cur->value) {
1475           attr_color = apr_pstrdup(doc->pool, cur->value);
1476         }
1477       }
1478       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
1479         if (cur->value && *cur->value) {
1480           attr_size = apr_pstrdup(doc->pool, cur->value);
1481           if (STRCASEEQ('x','X',"xx-small",attr_size)) {
1482             attr_size = apr_pstrdup(doc->pool, "1");
1483           }
1484           else if (STRCASEEQ('x','X',"x-small",attr_size)) {
1485             attr_size = apr_pstrdup(doc->pool, "2");
1486           }
1487           else if (STRCASEEQ('s','S',"small",attr_size)) {
1488             attr_size = apr_pstrdup(doc->pool, "3");
1489           }
1490           else if (STRCASEEQ('m','M',"medium",attr_size)) {
1491             attr_size = apr_pstrdup(doc->pool, "4");
1492           }
1493           else if (STRCASEEQ('l','L',"large",attr_size)) {
1494             attr_size = apr_pstrdup(doc->pool, "5");
1495           }
1496           else if (STRCASEEQ('x','X',"x-large",attr_size)) {
1497             attr_size = apr_pstrdup(doc->pool, "6");
1498           }
1499           else if (STRCASEEQ('x','X',"xx-large",attr_size)) {
1500             attr_size = apr_pstrdup(doc->pool, "7");
1501           }
1502         }
1503       }
1504     }
1505   }
1506   jxhtml_flags_t *flg = (jxhtml_flags_t *)apr_palloc(doc->pool, sizeof(*flg));
1507   memset(flg, 0, sizeof(*flg));
1508   if (attr_color) {
1509     attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
1510     W_L("<font color=\"");
1511     W_V(attr_color);
1512     W_L("\">");
1513     flg->font_color_flag = 1;
1514   }
1515   if (attr_size) {
1516     flg->font_size_flag = 1;
1517     switch(*attr_size) {
1518     case '1': W_L("<span style=\"font-size: xx-small\">"); break;
1519     case '2': W_L("<span style=\"font-size: x-small\">");  break;
1520     case '3': W_L("<span style=\"font-size: small\">");    break;
1521     case '4': W_L("<span style=\"font-size: medium\">");   break;
1522     case '5': W_L("<span style=\"font-size: large\">");    break;
1523     case '6': W_L("<span style=\"font-size: x-large\">");  break;
1524     case '7': W_L("<span style=\"font-size: xx-large\">"); break;
1525     case '-':
1526       if (*(attr_size + 1) == '1') {
1527         W_L("<span style=\"font-size: small\">");
1528         break;
1529       }
1530       if (*(attr_size + 1) == '2') {
1531         W_L("<span style=\"font-size: x-small\">");
1532         break;
1533       }
1534       if (*(attr_size + 1) == '3') {
1535         W_L("<span style=\"font-size: xx-small\">");
1536         break;
1537       }
1538       flg->font_size_flag = 0;
1539       break;
1540
1541     case '+':
1542       if (*(attr_size + 1) == '1') {
1543         W_L("<span style=\"font-size: large\">");
1544         break;
1545       }
1546       if (*(attr_size + 1) == '2') {
1547         W_L("<span style=\"font-size: x-large\">");
1548         break;
1549       }
1550       if (*(attr_size + 1) == '3') {
1551         W_L("<span style=\"font-size: xx-large\">");
1552         break;
1553       }
1554       flg->font_size_flag = 0;
1555       break;
1556
1557     default:
1558       WRN(doc->r, "invlalid font size. [%s] != (1|2|3|4|5|6|7|+1|+2|+3|-1|-2|-3)", attr_size);
1559       flg->font_size_flag = 0;
1560     }
1561   }
1562   node->userData = flg;
1563   return jxhtml->out;
1564 }
1565
1566
1567 /**
1568  * It is a handler who processes the FONT tag.
1569  *
1570  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1571  *                     destination is specified.
1572  * @param node   [i]   The FONT tag node is specified.
1573  * @return The conversion result is returned.
1574  */
1575 static char *
1576 s_jxhtml_end_font_tag(void *pdoc, Node *node)
1577 {
1578   jxhtml_t      *jxhtml;
1579   request_rec  *r;
1580   Doc          *doc;
1581
1582   jxhtml = GET_JXHTML(pdoc);
1583   doc   = jxhtml->doc;
1584   r     = jxhtml->doc->r;
1585
1586   jxhtml_flags_t *flg = (jxhtml_flags_t *)node->userData;
1587   if (flg && flg->font_size_flag) {
1588     W_L("</span>");
1589   }
1590   if (flg && flg->font_color_flag) {
1591     W_L("</font>");
1592   }
1593   if (IS_CSS_ON(jxhtml->entryp)) {
1594     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
1595   }
1596
1597   return jxhtml->out;
1598 }
1599
1600
1601 /**
1602  * It is a handler who processes the FORM tag.
1603  *
1604  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1605  *                     destination is specified.
1606  * @param node   [i]   The FORM tag node is specified.
1607  * @return The conversion result is returned.
1608  */
1609 static char *
1610 s_jxhtml_start_form_tag(void *pdoc, Node *node) 
1611 {
1612   jxhtml_t    *jxhtml;
1613   Doc         *doc;
1614   request_rec *r;
1615   Attr        *attr;
1616   char        *attr_action = NULL;
1617   char        *attr_method = NULL;
1618   char        *attr_style  = NULL;
1619   char        *attr_color  = NULL;
1620   char        *attr_align  = NULL;
1621   char        *attr_name   = NULL;
1622   char        *new_hidden_tag = NULL;
1623
1624   jxhtml  = GET_JXHTML(pdoc);
1625   doc     = jxhtml->doc;
1626   r       = doc->r;
1627
1628   /*--------------------------------------------------------------------------*/
1629   /* Get Attributes                                                           */
1630   /*--------------------------------------------------------------------------*/
1631   for (attr = qs_get_attr(doc,node);
1632        attr;
1633        attr = qs_get_next_attr(doc,attr)) {
1634     char *name  = qs_get_attr_name(doc,attr);
1635     char *value = qs_get_attr_value(doc,attr);
1636     switch(*name) {
1637     case 'a':
1638     case 'A':
1639       if (strcasecmp(name, "action") == 0) {
1640         /*--------------------------------------------------------------------*/
1641         /* CHTML 1.0                                                          */
1642         /*--------------------------------------------------------------------*/
1643         attr_action = value;
1644       }
1645       break;
1646
1647     case 'm':
1648     case 'M':
1649       if (strcasecmp(name, "method") == 0) {
1650         /*--------------------------------------------------------------------*/
1651         /* CHTML 1.0                                                          */
1652         /*--------------------------------------------------------------------*/
1653         attr_method = value;
1654       }
1655       break;
1656
1657     case 'n':
1658     case 'N':
1659       if (strcasecmp(name, "name") == 0) {
1660         /*--------------------------------------------------------------------*/
1661         /* CHTML 1.0                                                          */
1662         /*--------------------------------------------------------------------*/
1663         attr_name = value;
1664       }
1665       break;
1666
1667     case 's':
1668     case 'S':
1669       if (strcasecmp(name, "style") == 0) {
1670         attr_style = value;
1671       }
1672       break;
1673
1674     default:
1675       break;
1676     }
1677   }
1678   if (IS_CSS_ON(jxhtml->entryp)) {
1679     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
1680     if (style) {
1681       css_property_t *text_align_prop = chxj_css_get_property_value(doc, style, "text-align");
1682       css_property_t *color_prop      = chxj_css_get_property_value(doc, style, "color");
1683       css_property_t *cur;
1684       for (cur = text_align_prop->next; cur != text_align_prop; cur = cur->next) {
1685         if (STRCASEEQ('l','L',"left", cur->value)) {
1686           attr_align = apr_pstrdup(doc->pool, "left");
1687         }
1688         else if (STRCASEEQ('c','C',"center",cur->value)) {
1689           attr_align = apr_pstrdup(doc->pool, "center");
1690         }
1691         else if (STRCASEEQ('r','R',"right",cur->value)) {
1692           attr_align = apr_pstrdup(doc->pool, "right");
1693         }
1694       }
1695       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
1696         attr_color = apr_pstrdup(doc->pool, cur->value);
1697       }
1698     }
1699   }
1700
1701   int post_flag = (attr_method && strcasecmp(attr_method, "post") == 0) ? 1 : 0;
1702
1703   W_L("<form");
1704   if (attr_action) {
1705     attr_action = chxj_encoding_parameter(r, attr_action, 1);
1706     attr_action = chxj_add_cookie_parameter(r, attr_action, jxhtml->cookie);
1707     char *q;
1708     char *old_qs = NULL;
1709     q = strchr(attr_action, '?');
1710     if (q) {
1711       new_hidden_tag = chxj_form_action_to_hidden_tag(r, doc->pool, attr_action, 1, post_flag, &old_qs, CHXJ_FALSE, CHXJ_TRUE, jxhtml->entryp);
1712       if (new_hidden_tag || old_qs) {
1713         *q = 0;
1714       }
1715     }
1716     W_L(" action=\"");
1717     W_V(attr_action);
1718     if (old_qs) {
1719       W_L("?");
1720       W_V(old_qs);
1721     }
1722     W_L("\"");
1723   }
1724   if (attr_method) {
1725     W_L(" method=\"");
1726     W_V(attr_method);
1727     W_L("\"");
1728   }
1729   if (attr_name) {
1730     W_L(" name=\"");
1731     W_V(attr_name);
1732     W_L("\"");
1733   }
1734   W_L(">");
1735
1736   jxhtml_flags_t *flg = (jxhtml_flags_t *)apr_palloc(doc->pool, sizeof(jxhtml_flags_t));
1737   memset(flg, 0, sizeof(*flg));
1738   if (attr_color) {
1739     attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
1740     W_L("<font color=\"");
1741     W_V(attr_color);
1742     W_L("\">");
1743     flg->with_font_flag = 1;
1744   }
1745   if (attr_align) {
1746     W_L("<div align=\"");
1747     W_V(attr_align);
1748     W_L("\">");
1749     flg->with_div_flag = 1;
1750   }
1751   node->userData = flg;
1752   if (new_hidden_tag) {
1753     W_V(new_hidden_tag);
1754   }
1755   return jxhtml->out;
1756 }
1757
1758
1759 /**
1760  * It is a handler who processes the FORM tag.
1761  *
1762  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1763  *                     destination is specified.
1764  * @param node   [i]   The FORM tag node is specified.
1765  * @return The conversion result is returned.
1766  */
1767 static char *
1768 s_jxhtml_end_form_tag(void *pdoc, Node *node)
1769 {
1770   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
1771   Doc      *doc    = jxhtml->doc;
1772
1773   jxhtml_flags_t *flg = (jxhtml_flags_t *)node->userData;
1774   if (flg && flg->with_div_flag) {
1775     W_L("</div>");
1776   }
1777   if (flg && flg->with_font_flag) {
1778     W_L("</font>");
1779   }
1780   W_L("</form>");
1781   if (IS_CSS_ON(jxhtml->entryp)) {
1782     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
1783   }
1784
1785   return jxhtml->out;
1786 }
1787
1788
1789 /**
1790  * It is a handler who processes the INPUT tag.
1791  *
1792  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
1793  *                     destination is specified.
1794  * @param node   [i]   The INPUT tag node is specified.
1795  * @return The conversion result is returned.
1796  */
1797 static char *
1798 s_jxhtml_start_input_tag(void *pdoc, Node *node) 
1799 {
1800   jxhtml_t    *jxhtml;
1801   Doc         *doc;
1802   request_rec *r;
1803   Attr        *attr;
1804   char        *attr_accesskey  = NULL;
1805   char        *attr_max_length = NULL;
1806   char        *attr_type       = NULL;
1807   char        *attr_name       = NULL;
1808   char        *attr_value      = NULL;
1809   char        *attr_istyle     = NULL;
1810   char        *attr_size       = NULL;
1811   char        *attr_checked    = NULL;
1812   char        *attr_style      = NULL;
1813
1814   jxhtml  = GET_JXHTML(pdoc);
1815   doc     = jxhtml->doc;
1816   r       = doc->r;
1817
1818   /*--------------------------------------------------------------------------*/
1819   /* Get Attributes                                                           */
1820   /*--------------------------------------------------------------------------*/
1821   for (attr = qs_get_attr(doc,node);
1822        attr;
1823        attr = qs_get_next_attr(doc,attr)) {
1824     char *name  = qs_get_attr_name(doc,attr);
1825     char *value = qs_get_attr_value(doc,attr);
1826     if (STRCASEEQ('t','T',"type",name) && value && *value) {
1827       char *tmp_type = qs_trim_string(doc->buf.pool, value);
1828       if (tmp_type && (STRCASEEQ('t','T',"text",    tmp_type) ||
1829                        STRCASEEQ('p','P',"password",tmp_type) ||
1830                        STRCASEEQ('c','C',"checkbox",tmp_type) ||
1831                        STRCASEEQ('r','R',"radio",   tmp_type) ||
1832                        STRCASEEQ('h','H',"hidden",  tmp_type) ||
1833                        STRCASEEQ('s','S',"submit",  tmp_type) ||
1834                        STRCASEEQ('r','R',"reset",   tmp_type))) {
1835         attr_type = tmp_type;
1836       }
1837     }
1838     else if (STRCASEEQ('n','N',"name",name) && value && *value) {
1839       attr_name = value;
1840     }
1841     else if (STRCASEEQ('v','V',"value",name) && value && *value) {
1842       attr_value = value;
1843     }
1844     else if (STRCASEEQ('i','I',"istyle",name) && value && *value) {
1845       attr_istyle = value;
1846     }
1847     else if (STRCASEEQ('m','M',"maxlength",name) && value && *value) {
1848       attr_max_length = value;
1849     }
1850     else if (STRCASEEQ('c','C',"checked", name)) {
1851       attr_checked = value;
1852     }
1853     else if (STRCASEEQ('a','A',"accesskey", name) && value && *value) {
1854       attr_accesskey = value;
1855     }
1856     else if (STRCASEEQ('s','S',"size", name) && value && *value) {
1857       attr_size = value;
1858     }
1859     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
1860       attr_style = value;
1861     }
1862   }
1863
1864   if (IS_CSS_ON(jxhtml->entryp)) {
1865     css_prop_list_t *style = s_jxhtml_nopush_and_get_now_style(pdoc, node, attr_style);
1866     if (style) {
1867       css_property_t *wap_input_format = chxj_css_get_property_value(doc, style, "-wap-input-format");
1868       css_property_t *cur;
1869       for (cur = wap_input_format->next; cur != wap_input_format; cur = cur->next) {
1870         if (strcasestr(cur->value, "<ja:n>")) {
1871           attr_istyle = "4";
1872         }
1873         else if (strcasestr(cur->value, "<ja:en>")) {
1874           attr_istyle = "3";
1875         }
1876         else if (strcasestr(cur->value, "<ja:hk>")) {
1877           attr_istyle = "2";
1878         }
1879         else if (strcasestr(cur->value, "<ja:h>")) {
1880           attr_istyle = "1";
1881         }
1882       }
1883     }
1884   }
1885
1886   W_L("<input");
1887   if (attr_type) {
1888     W_L(" type=\"");
1889     W_V(attr_type);
1890     W_L("\"");
1891   }
1892   if (attr_size) {
1893     W_L(" size=\"");
1894     W_V(attr_size);
1895     W_L("\"");
1896   }
1897   if (attr_name) {
1898     W_L(" name=\"");
1899     W_V(chxj_jreserved_to_safe_tag(r, attr_name, jxhtml->entryp));
1900     W_L("\"");
1901   }
1902   if (attr_value) {
1903     W_L(" value=\"");
1904     W_V(chxj_add_slash_to_doublequote(doc->pool, attr_value));
1905     W_L("\"");
1906   }
1907   if (attr_accesskey) {
1908     W_L(" accesskey=\"");
1909     W_V(attr_accesskey);
1910     W_L("\"");
1911   }
1912   if (attr_istyle && (*attr_istyle == '1' || *attr_istyle == '2' || *attr_istyle == '3' || *attr_istyle == '4')) {
1913     /*------------------------------------------------------------------------*/
1914     /* CHTML 2.0                                                              */
1915     /*------------------------------------------------------------------------*/
1916     if (attr_type && STRCASEEQ('p','P',"password", attr_type) && ! jxhtml->entryp->pc_flag ) {
1917       char *vv = qs_conv_istyle_to_format(doc->buf.pool, "4");
1918       W_L(" style=\"-wap-input-format:&quot;*");
1919       W_V(vv);
1920       W_L("&quot;;\"");
1921     }
1922     else {
1923       char *vv = qs_conv_istyle_to_format(doc->buf.pool, attr_istyle);
1924       W_L(" style=\"");
1925       W_L("-wap-input-format:&quot;*");
1926       W_V(vv);
1927       W_L("&quot;;");
1928       W_L("\"");
1929     }
1930   }
1931   else if (attr_type && STRCASEEQ('p','P',"password",attr_type)) {
1932     char *vv = qs_conv_istyle_to_format(doc->buf.pool, "4");
1933     W_L(" style=\"-wap-input-format:&quot;*");
1934     W_V(vv);
1935     W_L("&quot;;\"");
1936   }
1937   /*--------------------------------------------------------------------------*/
1938   /* The figure is default for the password.                                  */
1939   /*--------------------------------------------------------------------------*/
1940   if (attr_max_length && *attr_max_length) {
1941     if (chxj_chk_numeric(attr_max_length) == 0) {
1942       W_L(" maxlength=\"");
1943       W_V(attr_max_length);
1944       W_L("\"");
1945     }
1946   }
1947   if (attr_checked) {
1948     W_L(" checked=\"checked\"");
1949   }
1950   W_L(" />");
1951 #if 0
1952   jxhtml_t       *jxhtml;
1953   Doc           *doc;
1954   request_rec   *r;
1955   char          *max_length;
1956   char          *type;
1957   char          *name;
1958   char          *value;
1959   char          *istyle;
1960   char          *size;
1961   char          *checked;
1962   char          *accesskey;
1963
1964   jxhtml       = GET_JXHTML(pdoc);
1965   doc         = jxhtml->doc;
1966   r           = doc->r;
1967   max_length  = NULL;
1968   type        = NULL;
1969   name        = NULL;
1970   value       = NULL;
1971   istyle      = NULL;
1972   size        = NULL;
1973   checked     = NULL;
1974   accesskey   = NULL;
1975
1976   W_L("<input");
1977   /*--------------------------------------------------------------------------*/
1978   /* Get Attributes                                                           */
1979   /*--------------------------------------------------------------------------*/
1980   type       = qs_get_type_attr(doc, node, doc->buf.pool);
1981   name       = qs_get_name_attr(doc, node, doc->buf.pool);
1982   value      = qs_get_value_attr(doc,node, doc->buf.pool);
1983   istyle     = qs_get_istyle_attr(doc,node,doc->buf.pool);
1984   max_length = qs_get_maxlength_attr(doc,node,doc->buf.pool);
1985   checked    = qs_get_checked_attr(doc,node,doc->buf.pool);
1986   accesskey  = qs_get_accesskey_attr(doc, node, doc->buf.pool);
1987   size       = qs_get_size_attr(doc, node, doc->buf.pool);
1988
1989   if (type) {
1990     if (type && (STRCASEEQ('t','T',"text",    type) ||
1991                  STRCASEEQ('p','P',"password",type) ||
1992                  STRCASEEQ('c','C',"checkbox",type) ||
1993                  STRCASEEQ('r','R',"radio",   type) ||
1994                  STRCASEEQ('h','H',"hidden",  type) ||
1995                  STRCASEEQ('s','S',"submit",  type) ||
1996                  STRCASEEQ('r','R',"reset",   type))) {
1997       W_L(" type=\"");
1998       W_V(type);
1999       W_L("\"");
2000     }
2001   }
2002   if (size && *size) {
2003     W_L(" size=\"");
2004     W_V(size);
2005     W_L("\"");
2006   }
2007   if (name && *name) {
2008     W_L(" name=\"");
2009     W_V(chxj_jreserved_to_safe_tag(r, name, jxhtml->entryp));
2010     W_L("\"");
2011   }
2012   if (value && *value) {
2013     if (STRCASEEQ('s','S',"submit",type) || STRCASEEQ('r','R',"reset",type)) {
2014       apr_size_t value_len = strlen(value);
2015       value = chxj_conv_z2h(r, value, &value_len, jxhtml->entryp);
2016     }
2017
2018     W_L(" value=\"");
2019     W_V(chxj_add_slash_to_doublequote(doc->pool, value));
2020     W_L("\"");
2021   }
2022   if (accesskey && *accesskey) {
2023     W_L(" accesskey=\"");
2024     W_V(accesskey);
2025     W_L("\"");
2026   }
2027   if (istyle && (*istyle == '1' || *istyle == '2' || *istyle == '3' || *istyle == '4')) {
2028     /*------------------------------------------------------------------------*/
2029     /* CHTML 2.0                                                              */
2030     /*------------------------------------------------------------------------*/
2031     if (type && STRCASEEQ('p','P',"password", type) && ! jxhtml->entryp->pc_flag ) {
2032       W_L(" style=\"-wap-input-format: &quot;*&lt;ja:n&gt;&quot;;\"");
2033     }
2034     else {
2035       char *vv = qs_conv_istyle_to_format(doc->buf.pool, istyle);
2036       W_L(" style=\"");
2037       W_L("-wap-input-format:'*");
2038       W_V(vv);
2039       W_L("';");
2040       W_L("\"");
2041     }
2042   }
2043   else if (type && STRCASEEQ('p','P',"password",type)) {
2044     W_L(" style=\"-wap-input-format: &quot;*&lt;ja:n&gt;&quot;;\"");
2045   }
2046   /*--------------------------------------------------------------------------*/
2047   /* The figure is default for the password.                                  */
2048   /*--------------------------------------------------------------------------*/
2049   if (max_length && *max_length) {
2050     if (chxj_chk_numeric(max_length) == 0) {
2051       W_L(" maxlength=\"");
2052       W_V(max_length);
2053       W_L("\"");
2054     }
2055   }
2056
2057   if (checked) {
2058     W_L(" checked=\"checked\"");
2059   }
2060   W_L(" />");
2061 #endif
2062   return jxhtml->out;
2063 }
2064
2065
2066 /**
2067  * It is a handler who processes the INPUT tag.
2068  *
2069  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2070  *                     destination is specified.
2071  * @param node   [i]   The INPUT tag node is specified.
2072  * @return The conversion result is returned.
2073  */
2074 static char *
2075 s_jxhtml_end_input_tag(void *pdoc, Node *UNUSED(child)) 
2076 {
2077   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
2078   return jxhtml->out;
2079 }
2080
2081
2082 /**
2083  * It is a handler who processes the CENTER tag.
2084  *
2085  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2086  *                     destination is specified.
2087  * @param node   [i]   The CENTER tag node is specified.
2088  * @return The conversion result is returned.
2089  */
2090 static char *
2091 s_jxhtml_start_center_tag(void *pdoc, Node *node)
2092 {
2093   jxhtml_t *jxhtml;
2094   Doc       *doc;
2095   Attr      *attr;
2096   char      *attr_style = NULL;
2097   char      *attr_color = NULL;
2098   char      *attr_size  = NULL;
2099
2100   jxhtml = GET_JXHTML(pdoc);
2101   doc    = jxhtml->doc;
2102
2103   for (attr = qs_get_attr(doc,node);
2104        attr;
2105        attr = qs_get_next_attr(doc,attr)) {
2106     char *name  = qs_get_attr_name(doc,attr);
2107     char *value = qs_get_attr_value(doc,attr);
2108     if (STRCASEEQ('s','S',"style",name) && value && *value) {
2109       attr_style = value;
2110     }
2111   }
2112   if (IS_CSS_ON(jxhtml->entryp)) {
2113     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2114     if (style) {
2115       css_property_t *color_prop      = chxj_css_get_property_value(doc, style, "color");
2116       css_property_t *size_prop       = chxj_css_get_property_value(doc, style, "font-size");
2117       css_property_t *cur;
2118       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
2119         if (cur->value && *cur->value) {
2120           attr_color = apr_pstrdup(doc->pool, cur->value);
2121         }
2122       }
2123       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
2124         if (cur->value && *cur->value) {
2125           attr_size = apr_pstrdup(doc->pool, cur->value);
2126         }
2127       }
2128     }
2129   }
2130
2131   W_L("<center");
2132   if (attr_size || attr_color) {
2133     W_L(" style=\"");
2134     if (attr_size) {
2135       W_L("font-size:");
2136       W_V(attr_size);
2137       W_L(";");
2138     }
2139     if (attr_color) {
2140       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
2141       W_L("color:");
2142       W_V(attr_color);
2143       W_L(";");
2144     }
2145     W_L("\"");
2146   }
2147   W_L(">");
2148   
2149   return jxhtml->out;
2150 }
2151
2152
2153 /**
2154  * It is a handler who processes the CENTER tag.
2155  *
2156  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2157  *                     destination is specified.
2158  * @param node   [i]   The CENTER tag node is specified.
2159  * @return The conversion result is returned.
2160  */
2161 static char *
2162 s_jxhtml_end_center_tag(void *pdoc, Node *UNUSED(node))
2163 {
2164   jxhtml_t    *jxhtml;
2165   Doc         *doc;
2166   request_rec *r;
2167
2168   jxhtml = GET_JXHTML(pdoc);
2169   doc    = jxhtml->doc;
2170   r      = doc->r;
2171
2172   W_L("</center>");
2173   if (IS_CSS_ON(jxhtml->entryp)) {
2174     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2175   }
2176   return jxhtml->out;
2177 }
2178
2179
2180 /**
2181  * It is a handler who processes the li tag.
2182  *
2183  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2184  *                     destination is specified.
2185  * @param node   [i]   The li tag node is specified.
2186  * @return The conversion result is returned.
2187  */
2188 static char *
2189 s_jxhtml_start_li_tag(void *pdoc, Node *node)
2190 {
2191   jxhtml_t    *jxhtml;
2192   Doc         *doc;
2193   request_rec *r;
2194   Attr        *attr;
2195   char        *attr_type  = NULL;
2196   char        *attr_value = NULL;
2197   char        *attr_style = NULL;
2198
2199   jxhtml = GET_JXHTML(pdoc);
2200   doc   = jxhtml->doc;
2201   r     = doc->r;
2202
2203   for (attr = qs_get_attr(doc,node);
2204        attr;
2205        attr = qs_get_next_attr(doc,attr)) {
2206     char *name  = qs_get_attr_name(doc,attr);
2207     char *value = qs_get_attr_value(doc,attr);
2208     if (STRCASEEQ('t','T',"type",name)) {
2209       if (value && (*value == '1' || *value == 'a' || *value == 'A' || STRCASEEQ('d','D',"disc",value) || STRCASEEQ('s','S',"square",value) || STRCASEEQ('c','C',"circle",value))) {
2210         if (*value == '1') {
2211           attr_type = apr_pstrdup(doc->pool, "decimal");
2212         }
2213         else if (*value == 'a') {
2214           attr_type = apr_pstrdup(doc->pool, "lower-alpha");
2215         }
2216         else if (*value == 'A') {
2217           attr_type = apr_pstrdup(doc->pool, "upper-alpha");
2218         }
2219         else {
2220           attr_type = value;
2221         }
2222       }
2223     }
2224     else if (STRCASEEQ('v','V',"value", name) && value && *value) {
2225       attr_value = value;
2226     }
2227     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
2228       attr_style = value;
2229     }
2230   }
2231   if (IS_CSS_ON(jxhtml->entryp)) {
2232     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2233     if (style) {
2234       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "list-style-type");
2235       css_property_t *cur;
2236       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
2237         if (STRCASEEQ('d','D',"decimal", cur->value)) {
2238           attr_type = apr_pstrdup(doc->pool, "decimal");
2239         }
2240         else if (STRCASEEQ('u','U',"upper-alpha", cur->value)) {
2241           attr_type = apr_pstrdup(doc->pool, "upper-alpha");
2242         }
2243         else if (STRCASEEQ('l','L',"lower-alpha", cur->value)) {
2244           attr_type = apr_pstrdup(doc->pool, "lower-alpha");
2245         }
2246         else if (STRCASEEQ('d','D',"disc", cur->value)) {
2247           attr_type = apr_pstrdup(doc->pool, "disc");
2248         }
2249         else if (STRCASEEQ('s','S',"square", cur->value)) {
2250           attr_type = apr_pstrdup(doc->pool, "square");
2251         }
2252         else if (STRCASEEQ('c','C',"circle", cur->value)) {
2253           attr_type = apr_pstrdup(doc->pool, "circle");
2254         }
2255       }
2256     }
2257   }
2258
2259
2260   W_L("<li");
2261   if (attr_type) {
2262     W_L(" style=\"");
2263     W_L("list-style-type:");
2264     W_V(attr_type);
2265     W_L(";");
2266     W_L("\"");
2267   }
2268   if (attr_value) {
2269     W_L(" value=\"");
2270     W_V(attr_value);
2271     W_L("\"");
2272   }
2273   W_L(">");
2274   return jxhtml->out;
2275 }
2276
2277
2278 /**
2279  * It is a handler who processes the li tag.
2280  *
2281  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2282  *                     destination is specified.
2283  * @param node   [i]   The li tag node is specified.
2284  * @return The conversion result is returned.
2285  */
2286 static char *
2287 s_jxhtml_end_li_tag(void *pdoc, Node *UNUSED(child)) 
2288 {
2289   jxhtml_t     *jxhtml;
2290   Doc         *doc;
2291   request_rec *r;
2292
2293   jxhtml = GET_JXHTML(pdoc);
2294   doc   = jxhtml->doc;
2295   r     = doc->r;
2296
2297   if (IS_CSS_ON(jxhtml->entryp)) {
2298     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2299   }
2300   W_L("</li>");
2301   return jxhtml->out;
2302 }
2303
2304
2305 /**
2306  * It is a handler who processes the OL tag.
2307  *
2308  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2309  *                     destination is specified.
2310  * @param node   [i]   The OL tag node is specified.
2311  * @return The conversion result is returned.
2312  */
2313 static char *
2314 s_jxhtml_start_ol_tag(void *pdoc, Node *node)
2315 {
2316   jxhtml_t    *jxhtml;
2317   Doc         *doc;
2318   request_rec *r;
2319   Attr        *attr;
2320   char        *attr_style = NULL;
2321   char        *attr_start = NULL;
2322   char        *attr_type  = NULL;
2323
2324   jxhtml = GET_JXHTML(pdoc);
2325   doc   = jxhtml->doc;
2326   r     = doc->r;
2327
2328   /*--------------------------------------------------------------------------*/
2329   /* Get Attributes                                                           */
2330   /*--------------------------------------------------------------------------*/
2331   for (attr = qs_get_attr(doc,node);
2332        attr;
2333        attr = qs_get_next_attr(doc,attr)) {
2334     char *name = qs_get_attr_name(doc,attr);
2335     char *value = qs_get_attr_value(doc,attr);
2336     if (STRCASEEQ('t','T',"type",name) && value) {
2337       if (*value == '1') {
2338         attr_type = apr_pstrdup(doc->pool, "decimal");
2339       }
2340       else if (*value == 'a') {
2341         attr_type = apr_pstrdup(doc->pool, "lower-alpha");
2342       }
2343       else if (*value == 'A') {
2344         attr_type = apr_pstrdup(doc->pool, "upper-alpha");
2345       }
2346     }
2347     else if (STRCASEEQ('s','S',"start",name) && value && *value) {
2348       attr_start = value;
2349     }
2350     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
2351       attr_style = value;
2352     }
2353   }
2354   if (IS_CSS_ON(jxhtml->entryp)) {
2355     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2356     if (style) {
2357       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "list-style-type");
2358       css_property_t *cur;
2359       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
2360         if (STRCASEEQ('d','D',"decimal", cur->value)) {
2361           attr_type = apr_pstrdup(doc->pool, "decimal");
2362         }
2363         else if (STRCASEEQ('u','U',"upper-alpha", cur->value)) {
2364           attr_type = apr_pstrdup(doc->pool, "upper-alpha");
2365         }
2366         else if (STRCASEEQ('l','L',"lower-alpha", cur->value)) {
2367           attr_type = apr_pstrdup(doc->pool, "lower-alpha");
2368         }
2369       }
2370     }
2371   }
2372   W_L("<ol");
2373   if (attr_type) {
2374     W_L(" style=\"");
2375     W_L("list-style-type:");
2376     W_V(attr_type);
2377     W_L(";");
2378     W_L("\"");
2379   }
2380   if (attr_start) {
2381     W_L(" start=\"");
2382     W_V(attr_start);
2383     W_L("\"");
2384   }
2385   W_L(">");
2386
2387   return jxhtml->out;
2388 }
2389
2390
2391 /**
2392  * It is a handler who processes the OL tag.
2393  *
2394  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2395  *                     destination is specified.
2396  * @param node   [i]   The OL tag node is specified.
2397  * @return The conversion result is returned.
2398  */
2399 static char *
2400 s_jxhtml_end_ol_tag(void *pdoc, Node *UNUSED(child)) 
2401 {
2402   jxhtml_t     *jxhtml;
2403   Doc         *doc;
2404   request_rec *r;
2405
2406   jxhtml = GET_JXHTML(pdoc);
2407   doc   = jxhtml->doc;
2408   r     = doc->r;
2409
2410   W_L("</ol>");
2411   if (IS_CSS_ON(jxhtml->entryp)) {
2412     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2413   }
2414   return jxhtml->out;
2415 }
2416
2417
2418 /**
2419  * It is a handler who processes the P tag.
2420  *
2421  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2422  *                     destination is specified.
2423  * @param node   [i]   The P tag node is specified.
2424  * @return The conversion result is returned.
2425  */
2426 static char *
2427 s_jxhtml_start_p_tag(void *pdoc, Node *node)
2428 {
2429   jxhtml_t    *jxhtml;
2430   Doc         *doc;
2431   request_rec *r;
2432   Attr        *attr;
2433   char        *attr_align = NULL;
2434   char        *attr_style = NULL;
2435   char        *attr_color = NULL;
2436   char        *attr_blink = NULL;
2437
2438   jxhtml = GET_JXHTML(pdoc);
2439   doc   = jxhtml->doc;
2440   r     = doc->r;
2441
2442   for (attr = qs_get_attr(doc,node);
2443        attr;
2444        attr = qs_get_next_attr(doc,attr)) {
2445     char *nm  = qs_get_attr_name(doc,attr);
2446     char *val = qs_get_attr_value(doc,attr);
2447     if (STRCASEEQ('a','A',"align", nm)) {
2448       /*----------------------------------------------------------------------*/
2449       /* CHTML 1.0 (W3C version 3.2)                                          */
2450       /*----------------------------------------------------------------------*/
2451       if (val && (STRCASEEQ('l','L',"left",val) || STRCASEEQ('r','R',"right",val) || STRCASEEQ('c','C',"center",val))) {
2452         attr_align = apr_pstrdup(doc->buf.pool, val);
2453         break;
2454       }
2455     }
2456     else if (STRCASEEQ('s','S',"style", nm) && val && *val) {
2457       attr_style = apr_pstrdup(doc->buf.pool, val);
2458     }
2459   }
2460   if (IS_CSS_ON(jxhtml->entryp)) {
2461     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2462     if (style) {
2463       css_property_t *text_align_prop = chxj_css_get_property_value(doc, style, "text-align");
2464       css_property_t *color_prop      = chxj_css_get_property_value(doc, style, "color");
2465       css_property_t *text_deco_prop  = chxj_css_get_property_value(doc, style, "text-decoration");
2466       css_property_t *cur;
2467       for (cur = text_align_prop->next; cur != text_align_prop; cur = cur->next) {
2468         if (STRCASEEQ('l','L',"left",cur->value)) {
2469           attr_align = apr_pstrdup(doc->pool, "left");
2470         }
2471         else if (STRCASEEQ('c','C',"center",cur->value)) {
2472           attr_align = apr_pstrdup(doc->pool, "center");
2473         }
2474         else if (STRCASEEQ('r','R',"right",cur->value)) {
2475           attr_align = apr_pstrdup(doc->pool, "right");
2476         }
2477       }
2478       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
2479         if (cur->value && *cur->value) {
2480           attr_color = apr_pstrdup(doc->pool, cur->value);
2481         }
2482       }
2483       for (cur = text_deco_prop->next; cur != text_deco_prop; cur = cur->next) {
2484         if (cur->value && *cur->value && STRCASEEQ('b','B',"blink",cur->value)) {
2485           attr_blink = apr_pstrdup(doc->pool, cur->value);
2486         }
2487       }
2488     }
2489   }
2490   W_L("<p");
2491   if ((attr_align && *attr_align) || (attr_color && *attr_color) || (attr_blink && *attr_blink)) {
2492     W_L(" style=\"");
2493     if (attr_align) {
2494       W_L("text-align:");
2495       W_V(attr_align);
2496       W_L(";");
2497     }
2498     if (attr_color) {
2499       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
2500       W_L("color:");
2501       W_V(attr_color);
2502       W_L(";");
2503     }
2504     if (attr_blink) {
2505       W_L("text-decoration:");
2506       W_V(attr_blink);
2507       W_L(";");
2508     }
2509     W_L("\"");
2510   }
2511   W_L(">");
2512   return jxhtml->out;
2513 }
2514
2515
2516 /**
2517  * It is a handler who processes the P tag.
2518  *
2519  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2520  *                     destination is specified.
2521  * @param node   [i]   The P tag node is specified.
2522  * @return The conversion result is returned.
2523  */
2524 static char *
2525 s_jxhtml_end_p_tag(void *pdoc, Node *UNUSED(child)) 
2526 {
2527   jxhtml_t  *jxhtml = GET_JXHTML(pdoc);
2528   Doc       *doc    = jxhtml->doc;
2529
2530   W_L("</p>");
2531   if (IS_CSS_ON(jxhtml->entryp)) {
2532     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2533   }
2534   return jxhtml->out;
2535 }
2536
2537
2538 /**
2539  * It is a handler who processes the PRE tag.
2540  *
2541  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2542  *                     destination is specified.
2543  * @param node   [i]   The PRE tag node is specified.
2544  * @return The conversion result is returned.
2545  */
2546 static char *
2547 s_jxhtml_start_pre_tag(void *pdoc, Node *node)
2548 {
2549   jxhtml_t  *jxhtml = GET_JXHTML(pdoc);
2550   Doc       *doc   = jxhtml->doc;
2551   Attr      *attr;
2552   char      *attr_style = NULL;
2553
2554   for (attr = qs_get_attr(doc,node);
2555        attr;
2556        attr = qs_get_next_attr(doc,attr)) {
2557     char *nm  = qs_get_attr_name(doc,attr);
2558     char *val = qs_get_attr_value(doc,attr);
2559     if (val && STRCASEEQ('s','S',"style", nm)) {
2560       attr_style = val;
2561     }
2562   }
2563
2564   if (IS_CSS_ON(jxhtml->entryp)) {
2565     s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2566   }
2567
2568   jxhtml->pre_flag++;
2569   W_L("<pre>");
2570   return jxhtml->out;
2571 }
2572
2573
2574 /**
2575  * It is a handler who processes the PRE tag.
2576  *
2577  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2578  *                     destination is specified.
2579  * @param node   [i]   The PRE tag node is specified.
2580  * @return The conversion result is returned.
2581  */
2582 static char *
2583 s_jxhtml_end_pre_tag(void *pdoc, Node *UNUSED(child)) 
2584 {
2585   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
2586   Doc     *doc   = jxhtml->doc;
2587
2588   W_L("</pre>");
2589   jxhtml->pre_flag--;
2590   if (IS_CSS_ON(jxhtml->entryp)) {
2591     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2592   }
2593
2594   return jxhtml->out;
2595 }
2596
2597
2598 /**
2599  * It is a handler who processes the UL tag.
2600  *
2601  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2602  *                     destination is specified.
2603  * @param node   [i]   The UL tag node is specified.
2604  * @return The conversion result is returned.
2605  */
2606 static char *
2607 s_jxhtml_start_ul_tag(void *pdoc, Node *node)
2608 {
2609   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
2610   Doc      *doc    = jxhtml->doc;
2611   Attr     *attr;
2612   char     *attr_type = NULL;
2613   char     *attr_style = NULL;
2614   /*--------------------------------------------------------------------------*/
2615   /* Get Attributes                                                           */
2616   /*--------------------------------------------------------------------------*/
2617   for (attr = qs_get_attr(doc,node);
2618        attr;
2619        attr = qs_get_next_attr(doc,attr)) {
2620     char *name   = qs_get_attr_name(doc,attr);
2621     char *value  = qs_get_attr_value(doc,attr);
2622     if (STRCASEEQ('t','T',"type",name)) {
2623       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
2624         attr_type = value;
2625       }
2626     }
2627     else if (value && *value && STRCASEEQ('s','S',"style", name)) {
2628       attr_style = value;
2629     }
2630   }
2631   if (IS_CSS_ON(jxhtml->entryp)) {
2632     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
2633     if (style) {
2634       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "list-style-type");
2635       css_property_t *cur;
2636       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
2637         if (STRCASEEQ('d','D',"disc",cur->value)) {
2638           attr_type = apr_pstrdup(doc->pool, "disc");
2639         }
2640         else if (STRCASEEQ('c','C',"circle",cur->value)) {
2641           attr_type = apr_pstrdup(doc->pool, "circle");
2642         }
2643         else if (STRCASEEQ('s','S',"square",cur->value)) {
2644           attr_type = apr_pstrdup(doc->pool, "square");
2645         }
2646       }
2647     }
2648   }
2649   W_L("<ul");
2650   if (attr_type) {
2651     W_L(" style=\"");
2652     W_L("list-style-type:");
2653     W_V(attr_type);
2654     W_L(";");
2655     W_L("\"");
2656   }
2657   W_L(">");
2658   return jxhtml->out;
2659 }
2660
2661
2662 /**
2663  * It is a handler who processes the UL tag.
2664  *
2665  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2666  *                     destination is specified.
2667  * @param node   [i]   The UL tag node is specified.
2668  * @return The conversion result is returned.
2669  */
2670 static char *
2671 s_jxhtml_end_ul_tag(void *pdoc, Node *UNUSED(child)) 
2672 {
2673   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
2674   Doc     *doc   = jxhtml->doc;
2675
2676   W_L("</ul>");
2677   if (IS_CSS_ON(jxhtml->entryp)) {
2678     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
2679   }
2680   return jxhtml->out;
2681 }
2682
2683
2684 /**
2685  * It is a handler who processes the HR tag.
2686  *
2687  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2688  *                     destination is specified.
2689  * @param node   [i]   The HR tag node is specified.
2690  * @return The conversion result is returned.
2691  */
2692 static char *
2693 s_jxhtml_start_hr_tag(void *pdoc, Node *node) 
2694 {
2695   Attr        *attr;
2696   jxhtml_t     *jxhtml;
2697   Doc         *doc;
2698   request_rec *r;
2699   char        *attr_align   = NULL;
2700   char        *attr_size    = NULL;
2701   char        *attr_width   = NULL;
2702   char        *attr_noshade = NULL;
2703   char        *attr_style   = NULL;
2704   char        *attr_color   = NULL;
2705
2706   jxhtml   = GET_JXHTML(pdoc);
2707   doc     = jxhtml->doc;
2708   r       = doc->r;
2709
2710   for (attr = qs_get_attr(doc,node);
2711        attr; 
2712        attr = qs_get_next_attr(doc,attr)) {
2713     char *name  = qs_get_attr_name (doc,attr);
2714     char *value = qs_get_attr_value(doc,attr);
2715     switch(*name) {
2716     case 'a':
2717     case 'A':
2718       if (strcasecmp(name, "align") == 0) {
2719         /*--------------------------------------------------------------------*/
2720         /* CHTML 1.0                                                          */
2721         /*--------------------------------------------------------------------*/
2722         if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2723           attr_align = value;
2724         }
2725       }
2726       break;
2727
2728     case 's':
2729     case 'S':
2730       if (strcasecmp(name, "size") == 0) {
2731         /*--------------------------------------------------------------------*/
2732         /* CHTML 1.0                                                          */
2733         /*--------------------------------------------------------------------*/
2734         if (value && *value) {
2735           attr_size = value;
2736         }
2737       }
2738       else if (strcasecmp(name, "style") == 0) {
2739         if (value && *value) {
2740           attr_style = value;
2741         }
2742       }
2743       break;
2744
2745     case 'w':
2746     case 'W':
2747       if (strcasecmp(name, "width") == 0) {
2748         /*--------------------------------------------------------------------*/
2749         /* CHTML 1.0                                                          */
2750         /*--------------------------------------------------------------------*/
2751         if (value && *value) {
2752           attr_width = value;
2753         }
2754       }
2755       break;
2756
2757     case 'n':
2758     case 'N':
2759       if (strcasecmp(name, "noshade") == 0) {
2760         /*--------------------------------------------------------------------*/
2761         /* CHTML 1.0                                                          */
2762         /*--------------------------------------------------------------------*/
2763         attr_noshade = apr_pstrdup(doc->pool, "noshade");
2764       }
2765       break;
2766
2767     case 'c':
2768     case 'C':
2769       if (strcasecmp(name, "color") == 0 && value && *value) {
2770         /*--------------------------------------------------------------------*/
2771         /* CHTML 4.0                                                          */
2772         /*--------------------------------------------------------------------*/
2773         attr_color = value;
2774       }
2775       break;
2776
2777     default:
2778       break;
2779     }
2780   }
2781   if (IS_CSS_ON(jxhtml->entryp)) {
2782     css_prop_list_t *style = s_jxhtml_nopush_and_get_now_style(pdoc, node, attr_style);
2783     if (style) {
2784       css_property_t *border_style_prop = chxj_css_get_property_value(doc, style, "border-style");
2785       css_property_t *height_prop       = chxj_css_get_property_value(doc, style, "height");
2786       css_property_t *width_prop        = chxj_css_get_property_value(doc, style, "width");
2787       css_property_t *cur;
2788       for (cur = border_style_prop->next; cur != border_style_prop; cur = cur->next) {
2789         if (STRCASEEQ('s','S',"solid",cur->value)) {
2790           attr_noshade = "noshade";
2791         }
2792       }
2793       for (cur = height_prop->next; cur != height_prop; cur = cur->next) {
2794         char *tmp = apr_pstrdup(doc->pool, cur->value);
2795         char *tmpp = strstr(tmp, "px");
2796         if (tmpp) { 
2797           attr_size = apr_pstrdup(doc->pool, tmp);
2798         }
2799       }
2800       for (cur = width_prop->next; cur != width_prop; cur = cur->next) {
2801         char *tmp = apr_pstrdup(doc->pool, cur->value);
2802         char *tmpp = strstr(tmp, "px");
2803         if (tmpp) {
2804           attr_width = apr_pstrdup(doc->pool, tmp);
2805         }
2806         else {
2807           tmpp = strstr(tmp, "%");
2808           if (tmpp) {
2809             attr_width = apr_pstrdup(doc->pool, tmp);
2810           }
2811         }
2812       }
2813     }
2814   }
2815   W_L("<hr");
2816   if (attr_align) {
2817     W_L(" align=\"");
2818     W_V(attr_align);
2819     W_L("\"");
2820   }
2821   if (attr_size || attr_width || attr_noshade) {
2822     W_L(" style=\"");
2823     if (attr_size) {
2824       W_L("height:");
2825       W_V(attr_size);
2826       if (!strstr(attr_size, "px")) {
2827         W_L("px");
2828       }
2829       W_L(";");
2830     }
2831     if (attr_width) {
2832       W_L("width:");
2833       W_V(attr_width);
2834       if (!strstr(attr_width, "px") && !strstr(attr_width, "%")) {
2835         W_L("px");
2836       }
2837       W_L(";");
2838     }
2839     if (attr_noshade) {
2840       W_L("border-style:solid;");
2841     }
2842     W_L("\"");
2843   }
2844   if (attr_color) {
2845     W_L(" color=\"");
2846     W_V(attr_color);
2847     W_L("\"");
2848   }
2849   W_L(" />");
2850
2851   return jxhtml->out;
2852 }
2853
2854
2855 /**
2856  * It is a handler who processes the HR tag.
2857  *
2858  * @param jxhtml  [i/o] The pointer to the JXHTML structure at the output
2859  *                     destination is specified.
2860  * @param node   [i]   The HR tag node is specified.
2861  * @return The conversion result is returned.
2862  */
2863 static char *
2864 s_jxhtml_end_hr_tag(void *pdoc, Node *UNUSED(child)) 
2865 {
2866   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
2867   return jxhtml->out;
2868 }
2869
2870
2871 /**
2872  * It is a handler who processes the IMG tag.
2873  *
2874  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
2875  *                     destination is specified.
2876  * @param node   [i]   The IMG tag node is specified.
2877  * @return The conversion result is returned.
2878  */
2879 static char *
2880 s_jxhtml_start_img_tag(void *pdoc, Node *node) 
2881 {
2882   jxhtml_t    *jxhtml = GET_JXHTML(pdoc);
2883   Doc         *doc   = jxhtml->doc;
2884   request_rec *r     = doc->r;
2885   Attr        *attr;
2886   char        *attr_src    = NULL;
2887   char        *attr_height = NULL;
2888   char        *attr_width  = NULL;
2889   char        *attr_align  = NULL;
2890   char        *attr_alt    = NULL;
2891   char        *attr_style  = NULL;
2892 #ifndef IMG_NOT_CONVERT_FILENAME
2893   device_table  *spec = jxhtml->spec;
2894 #endif
2895
2896   /*--------------------------------------------------------------------------*/
2897   /* Get Attributes                                                           */
2898   /*--------------------------------------------------------------------------*/
2899   for (attr = qs_get_attr(doc,node);
2900        attr;
2901        attr = qs_get_next_attr(doc,attr)) {
2902     char *name  = qs_get_attr_name(doc,attr);
2903     char *value = qs_get_attr_value(doc,attr);
2904     if (STRCASEEQ('s','S',"src",name)) {
2905       /*----------------------------------------------------------------------*/
2906       /* CHTML 1.0                                                            */
2907       /*----------------------------------------------------------------------*/
2908 #ifdef IMG_NOT_CONVERT_FILENAME
2909       value = chxj_encoding_parameter(r, value, 1);
2910       value = chxj_jreserved_tag_to_safe_for_query_string(r, value, jxhtml->entryp, 1);
2911       value = chxj_add_cookie_no_update_parameter(r, value);
2912       attr_src = value;
2913 #else
2914       value = chxj_img_conv(r, spec, value);
2915       value = chxj_encoding_parameter(r, value, 1);
2916       value = chxj_jreserved_tag_to_safe_for_query_string(r, value, jxhtml->entryp, 1);
2917       value = chxj_add_cookie_no_update_parameter(r, value);
2918       attr_src = value;
2919 #endif
2920     }
2921     else if (STRCASEEQ('a','A',"align",name)) {
2922       /*----------------------------------------------------------------------*/
2923       /* CHTML 1.0                                                            */
2924       /*----------------------------------------------------------------------*/
2925       if (value) {
2926         if (STRCASEEQ('t','T',"top",   value) ||
2927             STRCASEEQ('m','M',"middle",value) ||
2928             STRCASEEQ('b','B',"bottom",value) ||
2929             STRCASEEQ('l','L',"left",  value) ||
2930             STRCASEEQ('r','R',"right", value)) {
2931           attr_align = value;
2932         }
2933         else if (STRCASEEQ('c','C',"center",value)) {
2934           attr_align = apr_pstrdup(doc->pool, "middle");
2935         }
2936       }
2937     }
2938     else if (STRCASEEQ('w','W',"width",name) && value && *value) {
2939       /*----------------------------------------------------------------------*/
2940       /* CHTML 1.0                                                            */
2941       /*----------------------------------------------------------------------*/
2942       attr_width = value;
2943     }
2944     else if (STRCASEEQ('h','H',"height",name) && value && *value) {
2945       /*----------------------------------------------------------------------*/
2946       /* CHTML 1.0                                                            */
2947       /*----------------------------------------------------------------------*/
2948       attr_height = value;
2949     }
2950     else if (STRCASEEQ('h','H',"hspace",name)) {
2951       /*----------------------------------------------------------------------*/
2952       /* CHTML 1.0                                                            */
2953       /*----------------------------------------------------------------------*/
2954       /* ignore */
2955     }
2956     else if (STRCASEEQ('v','V',"vspace",name)) {
2957       /*----------------------------------------------------------------------*/
2958       /* CHTML 1.0                                                            */
2959       /*----------------------------------------------------------------------*/
2960       /* ignore */
2961     }
2962     else if (STRCASEEQ('a','A',"alt",name) && value && *value) {
2963       /*----------------------------------------------------------------------*/
2964       /* CHTML 1.0                                                            */
2965       /*----------------------------------------------------------------------*/
2966       attr_alt = value;
2967     }
2968     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
2969       /*----------------------------------------------------------------------*/
2970       /* CHTML 1.0                                                            */
2971       /*----------------------------------------------------------------------*/
2972       attr_style = value;
2973     }
2974   }
2975
2976   if (IS_CSS_ON(jxhtml->entryp)) {
2977     css_prop_list_t *style = s_jxhtml_nopush_and_get_now_style(pdoc, node, attr_style);
2978     if (style) {
2979       css_property_t *height_prop = chxj_css_get_property_value(doc, style, "height");
2980       css_property_t *width_prop  = chxj_css_get_property_value(doc, style, "width");
2981       css_property_t *valign_prop = chxj_css_get_property_value(doc, style, "vertical-align");
2982       css_property_t *cur;
2983       for (cur = height_prop->next; cur != height_prop; cur = cur->next) {
2984         attr_height = apr_pstrdup(doc->pool, cur->value);
2985       }
2986       for (cur = width_prop->next; cur != width_prop; cur = cur->next) {
2987         attr_width = apr_pstrdup(doc->pool, cur->value);
2988       }
2989       for (cur = valign_prop->next; cur != valign_prop; cur = cur->next) {
2990         attr_align = apr_pstrdup(doc->pool, cur->value);
2991       }
2992     }
2993   }
2994
2995   W_L("<img");
2996   if (attr_src) {
2997     W_L(" src=\"");
2998     W_V(attr_src);
2999     W_L("\"");
3000   }
3001   if (attr_align) {
3002     W_L(" align=\"");
3003     W_V(attr_align); 
3004     W_L("\"");
3005   }
3006   if (attr_width) {
3007     W_L(" width=\"");
3008     W_V(attr_width);
3009     W_L("\"");
3010   }
3011   if (attr_height) {
3012     W_L(" height=\"");
3013     W_V(attr_height);
3014     W_L("\"");
3015   }
3016   if (attr_alt) {
3017     W_L(" alt=\"");
3018     W_V(attr_alt);
3019     W_L("\"");
3020   } 
3021   else {
3022     W_L(" alt=\"\"");
3023   }
3024   W_L(" />");
3025   return jxhtml->out;
3026 }
3027
3028
3029 /**
3030  * It is a handler who processes the IMG tag.
3031  *
3032  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3033  *                     destination is specified.
3034  * @param node   [i]   The IMG tag node is specified.
3035  * @return The conversion result is returned.
3036  */
3037 static char *
3038 s_jxhtml_end_img_tag(void *pdoc, Node *UNUSED(child)) 
3039 {
3040   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3041   return jxhtml->out;
3042 }
3043
3044
3045 /**
3046  * It is a handler who processes the SELECT tag.
3047  *
3048  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3049  *                     destination is specified.
3050  * @param node   [i]   The SELECT tag node is specified.
3051  * @return The conversion result is returned.
3052  */
3053 static char *
3054 s_jxhtml_start_select_tag(void *pdoc, Node *node)
3055 {
3056   jxhtml_t *jxhtml    = GET_JXHTML(pdoc);
3057   Doc     *doc      = jxhtml->doc;
3058   Attr    *attr;
3059   char    *size     = NULL;
3060   char    *name     = NULL;
3061   char    *multiple = NULL;
3062   char    *attr_style = NULL;
3063
3064   W_L("<select");
3065   for (attr = qs_get_attr(doc,node);
3066        attr;
3067        attr = qs_get_next_attr(doc,attr)) {
3068     char *nm  = qs_get_attr_name(doc,attr);
3069     char *val = qs_get_attr_value(doc,attr);
3070     if (STRCASEEQ('s','S',"size",nm)) {
3071       /*----------------------------------------------------------------------*/
3072       /* CHTML 1.0 version 2.0                                                */
3073       /*----------------------------------------------------------------------*/
3074       size = apr_pstrdup(doc->buf.pool, val);
3075     }
3076     else if (STRCASEEQ('s','S',"style",nm) && val && *val) {
3077       /*----------------------------------------------------------------------*/
3078       /* CHTML 1.0 version 2.0                                                */
3079       /*----------------------------------------------------------------------*/
3080       attr_style = apr_pstrdup(doc->buf.pool, val);
3081     }
3082     else if (STRCASEEQ('n','N',"name",nm)) {
3083       /*----------------------------------------------------------------------*/
3084       /* CHTML 1.0 version 2.0                                                */
3085       /*----------------------------------------------------------------------*/
3086       name = apr_pstrdup(doc->buf.pool, val);
3087     }
3088     else if (STRCASEEQ('m','M',"multiple", nm)) {
3089       /*----------------------------------------------------------------------*/
3090       /* CHTML 1.0 version 2.0                                                */
3091       /*----------------------------------------------------------------------*/
3092       multiple = apr_pstrdup(doc->buf.pool, val);
3093     }
3094   }
3095   if (size && *size) {
3096     W_L(" size=\"");
3097     W_V(size);
3098     W_L("\"");
3099   }
3100   if (name && *name) {
3101     W_L(" name=\"");
3102     W_V(name);
3103     W_L("\"");
3104   }
3105   if (multiple) {
3106     W_L(" multiple");
3107   }
3108   W_L(">");
3109
3110   if (IS_CSS_ON(jxhtml->entryp)) {
3111     s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
3112   }
3113
3114   return jxhtml->out;
3115 }
3116
3117
3118 /**
3119  * It is a handler who processes the SELECT tag.
3120  *
3121  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3122  *                     destination is specified.
3123  * @param node   [i]   The SELECT tag node is specified.
3124  * @return The conversion result is returned.
3125  */
3126 static char *
3127 s_jxhtml_end_select_tag(void *pdoc, Node *UNUSED(child))
3128 {
3129   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3130   Doc     *doc   = jxhtml->doc;
3131
3132   W_L("</select>");
3133   if (IS_CSS_ON(jxhtml->entryp)) {
3134     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
3135   }
3136
3137   return jxhtml->out;
3138 }
3139
3140 /**
3141  * It is a handler who processes the OPTION tag.
3142  *
3143  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3144  *                     destination is specified.
3145  * @param node   [i]   The OPTION tag node is specified.
3146  * @return The conversion result is returned.
3147  */
3148 static char *
3149 s_jxhtml_start_option_tag(void *pdoc, Node *node)
3150 {
3151   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3152   Doc     *doc   = jxhtml->doc;
3153   Attr    *attr;
3154
3155   char *selected   = NULL;
3156   char *value      = NULL;
3157   char *attr_style = NULL;
3158
3159   W_L("<option");
3160   for (attr = qs_get_attr(doc,node);
3161        attr;
3162        attr = qs_get_next_attr(doc,attr)) {
3163     char *nm  = qs_get_attr_name(doc,attr);
3164     char *val = qs_get_attr_value(doc,attr);
3165     if (STRCASEEQ('s','S',"selected",nm)) {
3166       /*----------------------------------------------------------------------*/
3167       /* CHTML 1.0 version 2.0                                                */
3168       /*----------------------------------------------------------------------*/
3169       selected = apr_pstrdup(doc->buf.pool, val);
3170     }
3171     else if (STRCASEEQ('s','S',"style",nm) && val && *val) {
3172       /*----------------------------------------------------------------------*/
3173       /* CHTML 1.0 version 2.0                                                */
3174       /*----------------------------------------------------------------------*/
3175       attr_style = apr_pstrdup(doc->buf.pool, val);
3176     }
3177     else if (STRCASEEQ('v','V',"value",nm)) {
3178       /*----------------------------------------------------------------------*/
3179       /* CHTML 1.0 version 2.0                                                */
3180       /*----------------------------------------------------------------------*/
3181       value = apr_pstrdup(doc->buf.pool, val);
3182     }
3183   }
3184   if (value) {
3185     W_L(" value=\"");
3186     W_V(value);
3187     W_L("\"");
3188   }
3189   if (selected) {
3190     W_L(" selected");
3191   }
3192   W_L(">");
3193
3194   if (IS_CSS_ON(jxhtml->entryp)) {
3195     s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
3196   }
3197
3198   return jxhtml->out;
3199 }
3200
3201
3202 /**
3203  * It is a handler who processes the OPTION tag.
3204  *
3205  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3206  *                     destination is specified.
3207  * @param node   [i]   The OPTION tag node is specified.
3208  * @return The conversion result is returned.
3209  */
3210 static char *
3211 s_jxhtml_end_option_tag(void *pdoc, Node *UNUSED(child))
3212 {
3213   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3214   Doc      *doc = jxhtml->doc;
3215
3216   W_L("</option>");
3217   if (IS_CSS_ON(jxhtml->entryp)) {
3218     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
3219   }
3220
3221   return jxhtml->out;
3222 }
3223
3224
3225 /**
3226  * It is a handler who processes the DIV tag.
3227  *
3228  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3229  *                     destination is specified.
3230  * @param node   [i]   The DIV tag node is specified.
3231  * @return The conversion result is returned.
3232  */
3233 static char *
3234 s_jxhtml_start_div_tag(void *pdoc, Node *node)
3235 {
3236   jxhtml_t    *jxhtml;
3237   Doc         *doc;
3238   request_rec *r;
3239   Attr        *attr;
3240   char        *attr_style             = NULL;
3241   char        *attr_align             = NULL;
3242   char        *attr_display           = NULL;
3243   char        *attr_decoration        = NULL;
3244   char        *attr_wap_marquee_style = NULL;
3245   char        *attr_wap_marquee_dir   = NULL;
3246   char        *attr_wap_marquee_loop  = NULL;
3247   char        *attr_color             = NULL;
3248   char        *attr_bgcolor           = NULL;
3249   char        *attr_font_size         = NULL;
3250
3251   jxhtml = GET_JXHTML(pdoc);
3252   doc   = jxhtml->doc;
3253   r     = doc->r;
3254
3255   for (attr = qs_get_attr(doc,node);
3256        attr;
3257        attr = qs_get_next_attr(doc,attr)) {
3258     char *nm  = qs_get_attr_name(doc,attr);
3259     char *val = qs_get_attr_value(doc,attr);
3260     if (STRCASEEQ('a','A',"align",nm)) {
3261       /*----------------------------------------------------------------------*/
3262       /* CHTML 1.0 (W3C version 3.2)                                          */
3263       /*----------------------------------------------------------------------*/
3264       if (val && (STRCASEEQ('l','L',"left",val) || STRCASEEQ('r','R',"right",val) || STRCASEEQ('c','C',"center",val))) {
3265         attr_align = apr_pstrdup(doc->buf.pool, val);
3266       }
3267     }
3268     else if (STRCASEEQ('s','S',"style",nm) && val && *val) {
3269       attr_style = apr_pstrdup(doc->buf.pool, val);
3270     }
3271   }
3272
3273   if (IS_CSS_ON(jxhtml->entryp)) {
3274     css_prop_list_t *style = s_jxhtml_nopush_and_get_now_style(pdoc, node, attr_style);
3275     if (style) {
3276       css_property_t *display_prop           = chxj_css_get_property_value(doc, style, "display");
3277       css_property_t *text_decoration_prop   = chxj_css_get_property_value(doc, style, "text-decoration");
3278       css_property_t *color_prop             = chxj_css_get_property_value(doc, style, "color");
3279       css_property_t *text_align_prop        = chxj_css_get_property_value(doc, style, "text-align");
3280       css_property_t *font_size_prop         = chxj_css_get_property_value(doc, style, "font-size");
3281       css_property_t *background_color_prop  = chxj_css_get_property_value(doc, style, "background-color");
3282       css_property_t *background_prop        = chxj_css_get_property_value(doc, style, "background");
3283
3284       css_property_t *cur;
3285       for (cur = display_prop->next; cur != display_prop; cur = cur->next) {
3286         if (strcasecmp("-wap-marquee", cur->value) == 0) {
3287           attr_display = apr_pstrdup(doc->pool, cur->value);
3288         }
3289       }
3290       for (cur = text_decoration_prop->next; cur != text_decoration_prop; cur = cur->next) {
3291         if (STRCASEEQ('b','B',"blink", cur->value)) {
3292           attr_decoration = apr_pstrdup(doc->pool, cur->value);
3293         }
3294       }
3295       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
3296         attr_color = apr_pstrdup(doc->pool, cur->value);
3297       }
3298       for (cur = background_color_prop->next; cur != background_color_prop; cur = cur->next) {
3299         attr_bgcolor = apr_pstrdup(doc->pool, cur->value);
3300         attr_bgcolor = chxj_css_rgb_func_to_value(doc->pool, attr_bgcolor);
3301       }
3302       for (cur = background_prop->next; cur != background_prop; cur = cur->next) {
3303         char *ss = strchr(cur->value, '#');
3304         if (!ss || !*ss) {
3305           ss = strstr(cur->value, "rgb");
3306         }
3307         if (ss && *ss) {
3308           attr_bgcolor = apr_pstrdup(doc->pool, cur->value);
3309           attr_bgcolor = chxj_css_rgb_func_to_value(doc->pool, attr_bgcolor);
3310         }
3311       }
3312       for (cur = text_align_prop->next; cur != text_align_prop; cur = cur->next) {
3313         attr_align = apr_pstrdup(doc->pool, cur->value);
3314       }
3315       for (cur = font_size_prop->next; cur != font_size_prop; cur = cur->next) {
3316         if (   STRCASEEQ('x','X',"xx-small",cur->value)
3317             || STRCASEEQ('x','X',"x-small",cur->value)
3318             || STRCASEEQ('s','S',"small",cur->value)
3319             || STRCASEEQ('m','M',"medium",cur->value)
3320             || STRCASEEQ('l','L',"large",cur->value)
3321             || STRCASEEQ('x','X',"x-large",cur->value)
3322             || STRCASEEQ('x','X',"xx-large",cur->value)) {
3323           attr_font_size = apr_pstrdup(doc->pool, cur->value);
3324         }
3325       }
3326       if (attr_display) {
3327         css_property_t *wap_marquee_style_prop = chxj_css_get_property_value(doc, style, "-wap-marquee-style");
3328         css_property_t *wap_marquee_dir_prop   = chxj_css_get_property_value(doc, style, "-wap-marquee-dir");
3329         css_property_t *wap_marquee_loop_prop  = chxj_css_get_property_value(doc, style, "-wap-marquee-loop");
3330         for (cur = wap_marquee_style_prop->next; cur != wap_marquee_style_prop; cur = cur->next) {
3331           if (STRCASEEQ('s','S',"scroll", cur->value) || STRCASEEQ('s','S',"slide",cur->value) || STRCASEEQ('a','A',"alternate",cur->value)) {
3332             attr_wap_marquee_style = apr_pstrdup(doc->pool, cur->value);
3333           }
3334         }
3335         for (cur = wap_marquee_dir_prop->next; cur != wap_marquee_dir_prop; cur = cur->next) {
3336           if (STRCASEEQ('l','L',"ltr",cur->value)) {
3337             attr_wap_marquee_dir = apr_pstrdup(doc->pool, cur->value);
3338           }
3339           else if (STRCASEEQ('r','R',"rtl",cur->value)) {
3340             attr_wap_marquee_dir = apr_pstrdup(doc->pool, cur->value);
3341           }
3342         }
3343         for (cur = wap_marquee_loop_prop->next; cur != wap_marquee_loop_prop; cur = cur->next) {
3344           attr_wap_marquee_loop = apr_pstrdup(doc->pool, cur->value);
3345         }
3346       }
3347     }
3348   }  
3349   W_L("<div");
3350   if (attr_align
3351       || attr_display
3352       || attr_decoration
3353       || attr_wap_marquee_style
3354       || attr_wap_marquee_dir
3355       || attr_wap_marquee_loop
3356       || attr_color
3357       || attr_bgcolor
3358       || attr_font_size) {
3359     W_L(" style=\"");
3360     if (attr_align) {
3361       W_L("text-align:");
3362       W_V(attr_align);
3363       W_L(";");
3364     }
3365     if (attr_display) {
3366       W_L("display:");
3367       W_V(attr_display);
3368       W_L(";");
3369     }
3370     if (attr_decoration) {
3371       W_L("text-decoration:");
3372       W_V(attr_decoration);
3373       W_L(";");
3374     }
3375     if (attr_wap_marquee_style) {
3376       W_L("-wap-marquee-style:");
3377       W_V(attr_wap_marquee_style);
3378       W_L(";");
3379     }
3380     if (attr_wap_marquee_dir) {
3381       W_L("-wap-marquee-dir:");
3382       W_V(attr_wap_marquee_dir);
3383       W_L(";");
3384     }
3385     if (attr_wap_marquee_loop) {
3386       W_L("-wap-marquee-loop:");
3387       W_V(attr_wap_marquee_loop);
3388       W_L(";");
3389     }
3390     if (attr_color) {
3391       W_L("color:");
3392       W_V(attr_color);
3393       W_L(";");
3394     }
3395     if (attr_bgcolor) {
3396       W_L("background-color:");
3397       W_V(attr_bgcolor);
3398       W_L(";");
3399     }
3400     if (attr_font_size) {
3401       W_L("font-size:");
3402       W_V(attr_font_size);
3403       W_L(";");
3404     }
3405     W_L("\"");
3406   }
3407   W_L(">");
3408   return jxhtml->out;
3409 }
3410
3411
3412 /**
3413  * It is a handler who processes the DIV tag.
3414  *
3415  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3416  *                     destination is specified.
3417  * @param node   [i]   The DIV tag node is specified.
3418  * @return The conversion result is returned.
3419  */
3420 static char *
3421 s_jxhtml_end_div_tag(void *pdoc, Node *UNUSED(child))
3422 {
3423   jxhtml_t      *jxhtml;
3424   Doc          *doc;
3425   request_rec  *r;
3426
3427   jxhtml = GET_JXHTML(pdoc);
3428   doc   = jxhtml->doc;
3429   r     = doc->r;
3430
3431   W_L("</div>");
3432   if (IS_CSS_ON(jxhtml->entryp)) {
3433     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
3434   }
3435   return jxhtml->out;
3436 }
3437
3438
3439 static char *
3440 s_jxhtml_chxjif_tag(void *pdoc, Node *node)
3441 {
3442   jxhtml_t *jxhtml;
3443   Doc     *doc;
3444   Node    *child;
3445   request_rec *r;
3446
3447   jxhtml = GET_JXHTML(pdoc);
3448   doc   = jxhtml->doc;
3449   r     = doc->r;
3450
3451   for (child = qs_get_child_node(doc, node);
3452        child;
3453        child = qs_get_next_node(doc, child)) {
3454     W_V(child->otext);
3455     s_jxhtml_chxjif_tag(jxhtml, child);
3456   }
3457   return NULL;
3458 }
3459
3460
3461 /**
3462  * It is a handler who processes the TEXTARE tag.
3463  *
3464  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3465  *                     destination is specified.
3466  * @param node   [i]   The TEXTAREA tag node is specified.
3467  * @return The conversion result is returned.
3468  */
3469 static char *
3470 s_jxhtml_start_textarea_tag(void *pdoc, Node *node) 
3471 {
3472   jxhtml_t      *jxhtml;
3473   Doc           *doc;
3474   request_rec   *r;
3475   Attr          *attr;
3476   char          *attr_accesskey = NULL;
3477   char          *attr_name      = NULL;
3478   char          *attr_rows      = NULL;
3479   char          *attr_cols      = NULL;
3480   char          *attr_istyle    = NULL;
3481   char          *attr_style     = NULL;
3482
3483
3484   jxhtml = GET_JXHTML(pdoc);
3485   doc   = jxhtml->doc;
3486   r     = doc->r;
3487
3488   jxhtml->textarea_flag++;
3489   for (attr = qs_get_attr(doc,node);
3490        attr;
3491        attr = qs_get_next_attr(doc,attr)) {
3492     char *name  = qs_get_attr_name(doc,attr);
3493     char *value = qs_get_attr_value(doc,attr);
3494     if (STRCASEEQ('a','A',"accesskey",name) && value && *value != 0) {
3495       attr_accesskey = value;
3496     }
3497     else if (STRCASEEQ('i','I',"istyle", name) && value && (*value == '1' || *value == '2' || *value == '3' || *value == '4')) {
3498       attr_istyle = value;
3499     }
3500     else if (STRCASEEQ('n','N',"name", name) && value && *value) {
3501       attr_name = value;
3502     }
3503     else if (STRCASEEQ('r','R',"rows", name) && value && *value) {
3504       attr_rows = value;
3505     }
3506     else if (STRCASEEQ('c','C',"cols", name) && value && *value) {
3507       attr_cols = value;
3508     }
3509     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
3510       attr_style = value;
3511     }
3512   }
3513   if (IS_CSS_ON(jxhtml->entryp)) {
3514     css_prop_list_t *style = s_jxhtml_nopush_and_get_now_style(pdoc, node, attr_style);
3515     if (style) {
3516       css_property_t *wap_input_format = chxj_css_get_property_value(doc, style, "-wap-input-format");
3517       css_property_t *cur;
3518       for (cur = wap_input_format->next; cur != wap_input_format; cur = cur->next) {
3519         if (strcasestr(cur->value, "<ja:n>")) {
3520           attr_istyle = "4";
3521         }
3522         else if (strcasestr(cur->value, "<ja:en>")) {
3523           attr_istyle = "3";
3524         }
3525         else if (strcasestr(cur->value, "<ja:hk>")) {
3526           attr_istyle = "2";
3527         }
3528         else if (strcasestr(cur->value, "<ja:h>")) {
3529           attr_istyle = "1";
3530         }
3531       }
3532     }
3533   }
3534   W_L("<textarea");
3535   if (attr_accesskey) {
3536     W_L(" accesskey=\"");
3537     W_V(attr_accesskey);
3538     W_L("\"");
3539   }
3540   if (attr_name) {
3541     W_L(" name=\"");
3542     W_V(attr_name);
3543     W_L("\"");
3544   }
3545   if (attr_rows) {
3546     W_L(" rows=\"");
3547     W_V(attr_rows);
3548     W_L("\"");
3549   }
3550   if (attr_cols) {
3551     W_L(" cols=\"");
3552     W_V(attr_cols);
3553     W_L("\"");
3554   }
3555   if (attr_istyle) {
3556     char *vv = qs_conv_istyle_to_format(doc->buf.pool, attr_istyle);
3557     W_L(" style=\"");
3558     W_L("-wap-input-format:&quot;*");
3559     W_V(vv);
3560     W_L("&quot;;");
3561     W_L("\"");
3562   }
3563   W_L(">");
3564   return jxhtml->out;
3565 }
3566
3567
3568 /**
3569  * It is a handler who processes the TEXTAREA tag.
3570  *
3571  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3572  *                     destination is specified.
3573  * @param node   [i]   The TEXTAREA tag node is specified.
3574  * @return The conversion result is returned.
3575  */
3576 static char *
3577 s_jxhtml_end_textarea_tag(void *pdoc, Node *UNUSED(child)) 
3578 {
3579   jxhtml_t       *jxhtml;
3580   Doc           *doc;
3581   request_rec   *r;
3582
3583   jxhtml = GET_JXHTML(pdoc);
3584   doc   = jxhtml->doc;
3585   r     = doc->r;
3586
3587   W_L("</textarea>");
3588   jxhtml->textarea_flag--;
3589
3590   return jxhtml->out;
3591 }
3592
3593
3594 /**
3595  * It is a handler who processes the B tag.
3596  *
3597  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3598  *                     destination is specified.
3599  * @param node   [i]   The B tag node is specified.
3600  * @return The conversion result is returned.
3601  */
3602 static char*
3603 s_jxhtml_start_b_tag(void* pdoc, Node* UNUSED(node)) 
3604 {
3605   jxhtml_t*      jxhtml;
3606   Doc*          doc;
3607   request_rec*  r;
3608
3609   jxhtml = GET_JXHTML(pdoc);
3610   doc   = jxhtml->doc;
3611   r     = doc->r;
3612
3613   W_L("<b>");
3614   return jxhtml->out;
3615 }
3616
3617
3618 /**
3619  * It is a handler who processes the B tag.
3620  *
3621  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3622  *                     destination is specified.
3623  * @param node   [i]   The B tag node is specified.
3624  * @return The conversion result is returned.
3625  */
3626 static char*
3627 s_jxhtml_end_b_tag(void* pdoc, Node* UNUSED(child)) 
3628 {
3629   jxhtml_t*      jxhtml = GET_JXHTML(pdoc);
3630   Doc*          doc   = jxhtml->doc;
3631
3632   W_L("</b>");
3633   return jxhtml->out;
3634 }
3635
3636 static char*
3637 s_jxhtml_text_tag(void* pdoc, Node* child)
3638 {
3639   jxhtml_t*     jxhtml;
3640   Doc*         doc;
3641   char*        textval;
3642   char*        tmp;
3643   char*        tdst;
3644   char         one_byte[2];
3645   int          ii;
3646   int          tdst_len;
3647   request_rec* r;
3648   apr_size_t   z2h_input_len;
3649
3650   jxhtml = GET_JXHTML(pdoc);
3651   doc   = jxhtml->doc;
3652   r     = doc->r;
3653
3654   textval = qs_get_node_value(doc,child);
3655   if (strlen(textval) == 0) {
3656     return jxhtml->out;
3657   }
3658
3659   tmp = apr_palloc(r->pool, qs_get_node_size(doc,child)+1);
3660   memset(tmp, 0, qs_get_node_size(doc,child)+1);
3661
3662   tdst     = qs_alloc_zero_byte_string(doc->buf.pool);
3663   memset(one_byte, 0, sizeof(one_byte));
3664   tdst_len = 0;
3665
3666   for (ii=0; ii<qs_get_node_size(doc,child); ii++) {
3667     char* out;
3668     int rtn = s_jxhtml_search_emoji(jxhtml, &textval[ii], &out);
3669     if (rtn) {
3670       tdst = qs_out_apr_pstrcat(r, tdst, out, &tdst_len);
3671       ii+=(rtn - 1);
3672       continue;
3673     }
3674
3675     if (is_sjis_kanji(textval[ii])) {
3676       one_byte[0] = textval[ii+0];
3677       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
3678       one_byte[0] = textval[ii+1];
3679       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
3680       ii++;
3681     }
3682     else 
3683     if (jxhtml->pre_flag) {
3684       one_byte[0] = textval[ii+0];
3685       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
3686     }
3687     else
3688     if (jxhtml->textarea_flag) {
3689       one_byte[0] = textval[ii+0];
3690       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
3691     }
3692     else {
3693       if (textval[ii] != '\r' && textval[ii] != '\n') {
3694         one_byte[0] = textval[ii+0];
3695         tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
3696       }
3697     }
3698   }
3699   z2h_input_len = strlen(tdst);
3700   tdst = chxj_conv_z2h(r, tdst, &z2h_input_len, jxhtml->entryp);
3701
3702   W_V(tdst);
3703   return jxhtml->out;
3704 }
3705
3706
3707 /**
3708  * It is a handler who processes the BLOCKQUOTE tag.
3709  *
3710  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3711  *                     destination is specified.
3712  * @param node   [i]   The BLOCKQUOTE tag node is specified.
3713  * @return The conversion result is returned.
3714  */
3715 static char *
3716 s_jxhtml_start_blockquote_tag(void *pdoc, Node *node)
3717 {
3718   jxhtml_t *jxhtml;
3719   Doc      *doc;
3720   Attr     *attr;
3721   char     *attr_style = NULL;
3722   char     *attr_color = NULL;
3723   char     *attr_size  = NULL;
3724
3725   jxhtml  = GET_JXHTML(pdoc);
3726   doc     = jxhtml->doc;
3727   for (attr = qs_get_attr(doc,node);
3728        attr;
3729        attr = qs_get_next_attr(doc,attr)) {
3730     char *nm  = qs_get_attr_name(doc,attr);
3731     char *val = qs_get_attr_value(doc,attr);
3732     if (val && STRCASEEQ('s','S',"style", nm)) {
3733       attr_style = val;
3734     }
3735   }
3736   if (IS_CSS_ON(jxhtml->entryp)) {
3737     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
3738     if (style) {
3739       css_property_t *color_prop = chxj_css_get_property_value(doc, style, "color");
3740       css_property_t *font_size_prop = chxj_css_get_property_value(doc, style, "font-size");
3741       css_property_t *cur;
3742       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
3743         if (cur->value && *cur->value) {
3744           attr_color = apr_pstrdup(doc->pool, cur->value);
3745         }
3746       }
3747       for (cur = font_size_prop->next; cur != font_size_prop; cur = cur->next) {
3748         if (cur->value && *cur->value) {
3749           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
3750             attr_size = apr_pstrdup(doc->pool, cur->value);
3751           }
3752           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
3753             attr_size = apr_pstrdup(doc->pool, cur->value);
3754           }
3755           else if (STRCASEEQ('s','S',"small",cur->value)) {
3756             attr_size = apr_pstrdup(doc->pool, cur->value);
3757           }
3758           else if (STRCASEEQ('m','M',"medium",cur->value)) {
3759             attr_size = apr_pstrdup(doc->pool, cur->value);
3760           }
3761           else if (STRCASEEQ('l','L',"large",cur->value)) {
3762             attr_size = apr_pstrdup(doc->pool, cur->value);
3763           }
3764           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
3765             attr_size = apr_pstrdup(doc->pool, cur->value);
3766           }
3767           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
3768             attr_size = apr_pstrdup(doc->pool, cur->value);
3769           }
3770         }
3771       }
3772     }
3773   }
3774   W_L("<blockquote");
3775   if (attr_color || attr_size) {
3776     W_L(" style=\"");
3777     if (attr_color) {
3778       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
3779       W_L("color:");
3780       W_V(attr_color);
3781       W_L(";");
3782     }
3783     if (attr_size) {
3784       W_L("font-size:");
3785       W_V(attr_size);
3786       W_L(";");
3787     }
3788     W_L("\"");
3789   }
3790   W_L(">");
3791   return jxhtml->out;
3792 }
3793
3794
3795 /**
3796  * It is a handler who processes the BLOCKQUOTE tag.
3797  *
3798  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3799  *                     destination is specified.
3800  * @param node   [i]   The BLOCKQUOTE tag node is specified.
3801  * @return The conversion result is returned.
3802  */
3803 static char *
3804 s_jxhtml_end_blockquote_tag(void *pdoc, Node *UNUSED(child))
3805 {
3806   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3807   Doc     *doc   = jxhtml->doc;
3808   W_L("</blockquote>");
3809   if (IS_CSS_ON(jxhtml->entryp)) {
3810     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
3811   }
3812   return jxhtml->out;
3813 }
3814
3815
3816 /**
3817  * It is a handler who processes the DIR tag.
3818  *
3819  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3820  *                     destination is specified.
3821  * @param node   [i]   The DIR tag node is specified.
3822  * @return The conversion result is returned.
3823  */
3824 static char *
3825 s_jxhtml_start_dir_tag(void *pdoc, Node *node)
3826 {
3827   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
3828   Doc       *doc        = jxhtml->doc;
3829   Attr      *attr;
3830   char      *attr_style = NULL;
3831   char      *attr_color = NULL;
3832   char      *attr_type  = NULL;
3833   char      *attr_size  = NULL;
3834   for (attr = qs_get_attr(doc,node);
3835        attr;
3836        attr = qs_get_next_attr(doc,attr)) {
3837     char *name   = qs_get_attr_name(doc,attr);
3838     char *value  = qs_get_attr_value(doc,attr);
3839     if (STRCASEEQ('t','T',"type",name)) {
3840       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
3841         attr_type = value;
3842       }
3843     }
3844     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
3845       attr_style = value;
3846     }
3847   }
3848   if (IS_CSS_ON(jxhtml->entryp)) {
3849     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
3850     if (style) {
3851       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
3852       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
3853       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "list-style-type");
3854       css_property_t *cur;
3855       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
3856         if (cur->value && *cur->value) {
3857           attr_color = apr_pstrdup(doc->pool, cur->value);
3858         }
3859       }
3860       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
3861         if (cur->value && *cur->value) {
3862           attr_type = apr_pstrdup(doc->pool, cur->value);
3863         }
3864       }
3865       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
3866         if (cur->value && *cur->value) {
3867           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
3868             attr_size = apr_pstrdup(doc->pool, cur->value);
3869           }
3870           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
3871             attr_size = apr_pstrdup(doc->pool, cur->value);
3872           }
3873           else if (STRCASEEQ('s','S',"small",cur->value)) {
3874             attr_size = apr_pstrdup(doc->pool, cur->value);
3875           }
3876           else if (STRCASEEQ('m','M',"medium",cur->value)) {
3877             attr_size = apr_pstrdup(doc->pool, cur->value);
3878           }
3879           else if (STRCASEEQ('l','L',"large",cur->value)) {
3880             attr_size = apr_pstrdup(doc->pool, cur->value);
3881           }
3882           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
3883             attr_size = apr_pstrdup(doc->pool, cur->value);
3884           }
3885           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
3886             attr_size = apr_pstrdup(doc->pool, cur->value);
3887           }
3888         }
3889       }
3890     }
3891   }
3892   W_L("<dir");
3893   if (attr_type || attr_color || attr_size) {
3894     W_L(" style=\"");
3895     if (attr_type) {
3896       W_L("list-style-type:");
3897       W_V(attr_type);
3898       W_L(";");
3899     }
3900     if (attr_color) {
3901       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
3902       W_L("color:");
3903       W_V(attr_color);
3904       W_L(";");
3905     }
3906     if (attr_size) {
3907       W_L("font-size:");
3908       W_V(attr_size);
3909       W_L(";");
3910     }
3911     W_L("\"");
3912   }
3913   W_L(">");
3914   return jxhtml->out;
3915 }
3916
3917
3918 /**
3919  * It is a handler who processes the DIR tag.
3920  *
3921  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3922  *                     destination is specified.
3923  * @param node   [i]   The DIR tag node is specified.
3924  * @return The conversion result is returned.
3925  */
3926 static char *
3927 s_jxhtml_end_dir_tag(void *pdoc, Node *UNUSED(child))
3928 {
3929   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
3930   Doc *doc = jxhtml->doc;
3931   W_L("</dir>");
3932   if (IS_CSS_ON(jxhtml->entryp)) {
3933     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
3934   }
3935   return jxhtml->out;
3936 }
3937
3938
3939 /**
3940  * It is a handler who processes the DL tag.
3941  *
3942  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
3943  *                     destination is specified.
3944  * @param node   [i]   The DL tag node is specified.
3945  * @return The conversion result is returned.
3946  */
3947 static char *
3948 s_jxhtml_start_dl_tag(void *pdoc, Node *node)
3949 {
3950   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
3951   Doc       *doc        = jxhtml->doc;
3952   Attr      *attr;
3953   char      *attr_style = NULL;
3954   char      *attr_color = NULL;
3955   char      *attr_size  = NULL;
3956   for (attr = qs_get_attr(doc,node);
3957        attr;
3958        attr = qs_get_next_attr(doc,attr)) {
3959     char *name   = qs_get_attr_name(doc,attr);
3960     char *value  = qs_get_attr_value(doc,attr);
3961     if (STRCASEEQ('s','S',"style", name) && value && *value) {
3962       attr_style = value;
3963     }
3964   }
3965   if (IS_CSS_ON(jxhtml->entryp)) {
3966     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
3967     if (style) {
3968       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
3969       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
3970       css_property_t *cur;
3971       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
3972         if (cur->value && *cur->value) {
3973           attr_color = apr_pstrdup(doc->pool, cur->value);
3974         }
3975       }
3976       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
3977         if (cur->value && *cur->value) {
3978           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
3979             attr_size = apr_pstrdup(doc->pool, cur->value);
3980           }
3981           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
3982             attr_size = apr_pstrdup(doc->pool, cur->value);
3983           }
3984           else if (STRCASEEQ('s','S',"small",cur->value)) {
3985             attr_size = apr_pstrdup(doc->pool, cur->value);
3986           }
3987           else if (STRCASEEQ('m','M',"medium",cur->value)) {
3988             attr_size = apr_pstrdup(doc->pool, cur->value);
3989           }
3990           else if (STRCASEEQ('l','L',"large",cur->value)) {
3991             attr_size = apr_pstrdup(doc->pool, cur->value);
3992           }
3993           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
3994             attr_size = apr_pstrdup(doc->pool, cur->value);
3995           }
3996           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
3997             attr_size = apr_pstrdup(doc->pool, cur->value);
3998           }
3999         }
4000       }
4001     }
4002   }
4003   W_L("<dl");
4004   if (attr_color || attr_size) {
4005     W_L(" style=\"");
4006     if (attr_color) {
4007       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
4008       W_L("color:");
4009       W_V(attr_color);
4010       W_L(";");
4011     }
4012     if (attr_size) {
4013       W_L("font-size:");
4014       W_V(attr_size);
4015       W_L(";");
4016     }
4017     W_L("\"");
4018   }
4019   W_L(">");
4020   return jxhtml->out;
4021 }
4022
4023
4024 /**
4025  * It is a handler who processes the DL tag.
4026  *
4027  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4028  *                     destination is specified.
4029  * @param node   [i]   The DL tag node is specified.
4030  * @return The conversion result is returned.
4031  */
4032 static char *
4033 s_jxhtml_end_dl_tag(void *pdoc, Node *UNUSED(child))
4034 {
4035   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
4036   Doc *doc = jxhtml->doc;
4037   W_L("</dl>");
4038   if (IS_CSS_ON(jxhtml->entryp)) {
4039     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4040   }
4041   return jxhtml->out;
4042 }
4043
4044
4045 /**
4046  * It is a handler who processes the DT tag.
4047  *
4048  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4049  *                     destination is specified.
4050  * @param node   [i]   The DT tag node is specified.
4051  * @return The conversion result is returned.
4052  */
4053 static char *
4054 s_jxhtml_start_dt_tag(void *pdoc, Node *node)
4055 {
4056   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
4057   Doc       *doc        = jxhtml->doc;
4058   Attr      *attr;
4059   char      *attr_style = NULL;
4060   char      *attr_color = NULL;
4061   char      *attr_size  = NULL;
4062   for (attr = qs_get_attr(doc,node);
4063        attr;
4064        attr = qs_get_next_attr(doc,attr)) {
4065     char *name   = qs_get_attr_name(doc,attr);
4066     char *value  = qs_get_attr_value(doc,attr);
4067     if (STRCASEEQ('s','S',"style", name) && value && *value) {
4068       attr_style = value;
4069     }
4070   }
4071   if (IS_CSS_ON(jxhtml->entryp)) {
4072     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4073     if (style) {
4074       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
4075       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
4076       css_property_t *cur;
4077       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
4078         if (cur->value && *cur->value) {
4079           attr_color = apr_pstrdup(doc->pool, cur->value);
4080         }
4081       }
4082       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
4083         if (cur->value && *cur->value) {
4084           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
4085             attr_size = apr_pstrdup(doc->pool, cur->value);
4086           }
4087           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
4088             attr_size = apr_pstrdup(doc->pool, cur->value);
4089           }
4090           else if (STRCASEEQ('s','S',"small",cur->value)) {
4091             attr_size = apr_pstrdup(doc->pool, cur->value);
4092           }
4093           else if (STRCASEEQ('m','M',"medium",cur->value)) {
4094             attr_size = apr_pstrdup(doc->pool, cur->value);
4095           }
4096           else if (STRCASEEQ('l','L',"large",cur->value)) {
4097             attr_size = apr_pstrdup(doc->pool, cur->value);
4098           }
4099           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
4100             attr_size = apr_pstrdup(doc->pool, cur->value);
4101           }
4102           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
4103             attr_size = apr_pstrdup(doc->pool, cur->value);
4104           }
4105         }
4106       }
4107     }
4108   }
4109   W_L("<dt");
4110   if (attr_color || attr_size) {
4111     W_L(" style=\"");
4112     if (attr_color) {
4113       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
4114       W_L("color:");
4115       W_V(attr_color);
4116       W_L(";");
4117     }
4118     if (attr_size) {
4119       W_L("font-size:");
4120       W_V(attr_size);
4121       W_L(";");
4122     }
4123     W_L("\"");
4124   }
4125   W_L(">");
4126   return jxhtml->out;
4127 }
4128
4129
4130 /**
4131  * It is a handler who processes the DT tag.
4132  *
4133  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4134  *                     destination is specified.
4135  * @param node   [i]   The DT tag node is specified.
4136  * @return The conversion result is returned.
4137  */
4138 static char *
4139 s_jxhtml_end_dt_tag(void *pdoc, Node *UNUSED(child))
4140 {
4141   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
4142   Doc      *doc    = jxhtml->doc;
4143   W_L("</dt>");
4144   if (IS_CSS_ON(jxhtml->entryp)) {
4145     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4146   }
4147   return jxhtml->out;
4148 }
4149
4150
4151 /**
4152  * It is a handler who processes the DD tag.
4153  *
4154  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4155  *                     destination is specified.
4156  * @param node   [i]   The DD tag node is specified.
4157  * @return The conversion result is returned.
4158  */
4159 static char *
4160 s_jxhtml_start_dd_tag(void *pdoc, Node *node)
4161 {
4162   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
4163   Doc       *doc        = jxhtml->doc;
4164   Attr      *attr;
4165   char      *attr_style = NULL;
4166   char      *attr_color = NULL;
4167   char      *attr_size  = NULL;
4168   for (attr = qs_get_attr(doc,node);
4169        attr;
4170        attr = qs_get_next_attr(doc,attr)) {
4171     char *name   = qs_get_attr_name(doc,attr);
4172     char *value  = qs_get_attr_value(doc,attr);
4173     if (STRCASEEQ('s','S',"style", name) && value && *value) {
4174       attr_style = value;
4175     }
4176   }
4177   if (IS_CSS_ON(jxhtml->entryp)) {
4178     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4179     if (style) {
4180       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
4181       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
4182       css_property_t *cur;
4183       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
4184         if (cur->value && *cur->value) {
4185           attr_color = apr_pstrdup(doc->pool, cur->value);
4186         }
4187       }
4188       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
4189         if (cur->value && *cur->value) {
4190           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
4191             attr_size = apr_pstrdup(doc->pool, cur->value);
4192           }
4193           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
4194             attr_size = apr_pstrdup(doc->pool, cur->value);
4195           }
4196           else if (STRCASEEQ('s','S',"small",cur->value)) {
4197             attr_size = apr_pstrdup(doc->pool, cur->value);
4198           }
4199           else if (STRCASEEQ('m','M',"medium",cur->value)) {
4200             attr_size = apr_pstrdup(doc->pool, cur->value);
4201           }
4202           else if (STRCASEEQ('l','L',"large",cur->value)) {
4203             attr_size = apr_pstrdup(doc->pool, cur->value);
4204           }
4205           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
4206             attr_size = apr_pstrdup(doc->pool, cur->value);
4207           }
4208           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
4209             attr_size = apr_pstrdup(doc->pool, cur->value);
4210           }
4211         }
4212       }
4213     }
4214   }
4215   W_L("<dd");
4216   if (attr_color || attr_size) {
4217     W_L(" style=\"");
4218     if (attr_color) {
4219       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
4220       W_L("color:");
4221       W_V(attr_color);
4222       W_L(";");
4223     }
4224     if (attr_size) {
4225       W_L("font-size:");
4226       W_V(attr_size);
4227       W_L(";");
4228     }
4229     W_L("\"");
4230   }
4231   W_L(">");
4232   return jxhtml->out;
4233 }
4234
4235
4236 /**
4237  * It is a handler who processes the DD tag.
4238  *
4239  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4240  *                     destination is specified.
4241  * @param node   [i]   The DD tag node is specified.
4242  * @return The conversion result is returned.
4243  */
4244 static char *
4245 s_jxhtml_end_dd_tag(void *pdoc, Node *UNUSED(child))
4246 {
4247   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
4248   Doc      *doc = jxhtml->doc;
4249   W_L("</dd>");
4250   if (IS_CSS_ON(jxhtml->entryp)) {
4251     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4252   }
4253   return jxhtml->out;
4254 }
4255
4256
4257 /**
4258  * It is a handler who processes the H1 tag.
4259  *
4260  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4261  *                     destination is specified.
4262  * @param node   [i]   The H1 tag node is specified.
4263  * @return The conversion result is returned.
4264  */
4265 static char *
4266 s_jxhtml_start_h1_tag(void *pdoc, Node *node)
4267 {
4268   jxhtml_t    *jxhtml;
4269   Doc         *doc;
4270   request_rec *r;
4271   Attr        *attr;
4272   char        *attr_style = NULL;
4273   char        *attr_align = NULL;
4274
4275   jxhtml = GET_JXHTML(pdoc);
4276   doc    = jxhtml->doc;
4277   r      = doc->r;
4278
4279   for (attr = qs_get_attr(doc,node);
4280        attr;
4281        attr = qs_get_next_attr(doc,attr)) {
4282     char *name  = qs_get_attr_name(doc,attr);
4283     char *value = qs_get_attr_value(doc,attr);
4284     if (STRCASEEQ('a','A',"align", name)) {
4285       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4286         attr_align = value;
4287       }
4288     }
4289     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4290       attr_style = value;
4291     }
4292   }
4293   if (IS_CSS_ON(jxhtml->entryp)) {
4294     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4295     if (style) {
4296       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4297       css_property_t *cur;
4298       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4299         if (STRCASEEQ('l','L',"left", cur->value)) {
4300           attr_align = apr_pstrdup(doc->pool, "left");
4301         }
4302         else if (STRCASEEQ('c','C',"center",cur->value)) {
4303           attr_align = apr_pstrdup(doc->pool, "center");
4304         }
4305         else if (STRCASEEQ('r','R',"right",cur->value)) {
4306           attr_align = apr_pstrdup(doc->pool, "right");
4307         }
4308       }
4309     }
4310   }
4311   W_L("<div");
4312   W_L(" style=\""); 
4313   W_L("font-size:xx-large;");
4314   if (attr_align) {
4315     W_L("text-align:");
4316     W_V(attr_align);
4317     W_L(";");
4318   }
4319   W_L("\">");
4320
4321   return jxhtml->out;
4322 }
4323
4324
4325 /**
4326  * It is a handler who processes the H1 tag.
4327  *
4328  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4329  *                     destination is specified.
4330  * @param node   [i]   The H1 tag node is specified.
4331  * @return The conversion result is returned.
4332  */
4333 static char *
4334 s_jxhtml_end_h1_tag(void *pdoc, Node *UNUSED(child)) 
4335 {
4336   jxhtml_t*    jxhtml;
4337   Doc*          doc;
4338   request_rec*  r;
4339
4340   jxhtml = GET_JXHTML(pdoc);
4341   doc     = jxhtml->doc;
4342   r       = doc->r;
4343   
4344   W_L("</div>");
4345   if (IS_CSS_ON(jxhtml->entryp)) {
4346     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4347   }
4348
4349   return jxhtml->out;
4350 }
4351
4352
4353 /**
4354  * It is a handler who processes the H2 tag.
4355  *
4356  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4357  *                     destination is specified.
4358  * @param node   [i]   The H1 tag node is specified.
4359  * @return The conversion result is returned.
4360  */
4361 static char *
4362 s_jxhtml_start_h2_tag(void *pdoc, Node *node)
4363 {
4364   jxhtml_t    *jxhtml;
4365   Doc         *doc;
4366   request_rec *r;
4367   Attr        *attr;
4368   char        *attr_style = NULL;
4369   char        *attr_align = NULL;
4370
4371   jxhtml   = GET_JXHTML(pdoc);
4372   doc     = jxhtml->doc;
4373   r       = doc->r;
4374
4375   for (attr = qs_get_attr(doc,node);
4376        attr;
4377        attr = qs_get_next_attr(doc,attr)) {
4378     char *name  = qs_get_attr_name(doc,attr);
4379     char *value = qs_get_attr_value(doc,attr);
4380     if (STRCASEEQ('a','A',"align", name)) {
4381       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4382         attr_align = value;
4383       }
4384     }
4385     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4386       attr_style = value;
4387     }
4388   }
4389   if (IS_CSS_ON(jxhtml->entryp)) {
4390     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4391     if (style) {
4392       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4393       css_property_t *cur;
4394       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4395         if (STRCASEEQ('l','L',"left", cur->value)) {
4396           attr_align = apr_pstrdup(doc->pool, "left");
4397         }
4398         else if (STRCASEEQ('c','C',"center",cur->value)) {
4399           attr_align = apr_pstrdup(doc->pool, "center");
4400         }
4401         else if (STRCASEEQ('r','R',"right",cur->value)) {
4402           attr_align = apr_pstrdup(doc->pool, "right");
4403         }
4404       }
4405     }
4406   }
4407   W_L("<div");
4408   W_L(" style=\""); 
4409   W_L("font-size:x-large;");
4410   if (attr_align) {
4411     W_L("text-align:");
4412     W_V(attr_align);
4413     W_L(";");
4414   }
4415   W_L("\">");
4416
4417   return jxhtml->out;
4418 }
4419
4420
4421 /**
4422  * It is a handler who processes the H2 tag.
4423  *
4424  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4425  *                     destination is specified.
4426  * @param node   [i]   The H1 tag node is specified.
4427  * @return The conversion result is returned.
4428  */
4429 static char *
4430 s_jxhtml_end_h2_tag(void *pdoc, Node *UNUSED(child)) 
4431 {
4432   jxhtml_t*    jxhtml;
4433   Doc*          doc;
4434   request_rec*  r;
4435
4436   jxhtml = GET_JXHTML(pdoc);
4437   doc     = jxhtml->doc;
4438   r       = doc->r;
4439   
4440   W_L("</div>");
4441   if (IS_CSS_ON(jxhtml->entryp)) {
4442     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4443   }
4444   return jxhtml->out;
4445 }
4446
4447
4448 /**
4449  * It is a handler who processes the H3 tag.
4450  *
4451  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4452  *                     destination is specified.
4453  * @param node   [i]   The H1 tag node is specified.
4454  * @return The conversion result is returned.
4455  */
4456 static char *
4457 s_jxhtml_start_h3_tag(void *pdoc, Node *node)
4458 {
4459   jxhtml_t    *jxhtml;
4460   Doc         *doc;
4461   request_rec *r;
4462   Attr        *attr;
4463   char        *attr_style = NULL;
4464   char        *attr_align = NULL;
4465
4466   jxhtml   = GET_JXHTML(pdoc);
4467   doc     = jxhtml->doc;
4468   r       = doc->r;
4469
4470   for (attr = qs_get_attr(doc,node);
4471        attr;
4472        attr = qs_get_next_attr(doc,attr)) {
4473     char *name  = qs_get_attr_name(doc,attr);
4474     char *value = qs_get_attr_value(doc,attr);
4475     if (STRCASEEQ('a','A',"align", name)) {
4476       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4477         attr_align = value;
4478       }
4479     }
4480     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4481       attr_style = value;
4482     }
4483   }
4484   if (IS_CSS_ON(jxhtml->entryp)) {
4485     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4486     if (style) {
4487       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4488       css_property_t *cur;
4489       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4490         if (STRCASEEQ('l','L',"left", cur->value)) {
4491           attr_align = apr_pstrdup(doc->pool, "left");
4492         }
4493         else if (STRCASEEQ('c','C',"center",cur->value)) {
4494           attr_align = apr_pstrdup(doc->pool, "center");
4495         }
4496         else if (STRCASEEQ('r','R',"right",cur->value)) {
4497           attr_align = apr_pstrdup(doc->pool, "right");
4498         }
4499       }
4500     }
4501   }
4502   W_L("<div");
4503   W_L(" style=\""); 
4504   W_L("font-size:large;");
4505   if (attr_align) {
4506     W_L("text-align:");
4507     W_V(attr_align);
4508     W_L(";");
4509   }
4510   W_L("\">");
4511
4512   return jxhtml->out;
4513 }
4514
4515
4516 /**
4517  * It is a handler who processes the H3 tag.
4518  *
4519  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4520  *                     destination is specified.
4521  * @param node   [i]   The H1 tag node is specified.
4522  * @return The conversion result is returned.
4523  */
4524 static char *
4525 s_jxhtml_end_h3_tag(void *pdoc, Node *UNUSED(child)) 
4526 {
4527   jxhtml_t*    jxhtml;
4528   Doc*          doc;
4529   request_rec*  r;
4530
4531   jxhtml = GET_JXHTML(pdoc);
4532   doc     = jxhtml->doc;
4533   r       = doc->r;
4534
4535   W_L("</div>");
4536   if (IS_CSS_ON(jxhtml->entryp)) {
4537     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4538   }
4539   return jxhtml->out;
4540 }
4541
4542
4543 /**
4544  * It is a handler who processes the H4 tag.
4545  *
4546  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4547  *                     destination is specified.
4548  * @param node   [i]   The H1 tag node is specified.
4549  * @return The conversion result is returned.
4550  */
4551 static char *
4552 s_jxhtml_start_h4_tag(void *pdoc, Node *node)
4553 {
4554   jxhtml_t    *jxhtml;
4555   Doc         *doc;
4556   request_rec *r;
4557   Attr        *attr;
4558   char        *attr_style = NULL;
4559   char        *attr_align = NULL;
4560
4561   jxhtml   = GET_JXHTML(pdoc);
4562   doc     = jxhtml->doc;
4563   r       = doc->r;
4564
4565   for (attr = qs_get_attr(doc,node);
4566        attr;
4567        attr = qs_get_next_attr(doc,attr)) {
4568     char *name  = qs_get_attr_name(doc,attr);
4569     char *value = qs_get_attr_value(doc,attr);
4570     if (STRCASEEQ('a','A',"align", name)) {
4571       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4572         attr_align = value;
4573       }
4574     }
4575     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4576       attr_style = value;
4577     }
4578   }
4579   if (IS_CSS_ON(jxhtml->entryp)) {
4580     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4581     if (style) {
4582       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4583       css_property_t *cur;
4584       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4585         if (STRCASEEQ('l','L',"left", cur->value)) {
4586           attr_align = apr_pstrdup(doc->pool, "left");
4587         }
4588         else if (STRCASEEQ('c','C',"center",cur->value)) {
4589           attr_align = apr_pstrdup(doc->pool, "center");
4590         }
4591         else if (STRCASEEQ('r','R',"right",cur->value)) {
4592           attr_align = apr_pstrdup(doc->pool, "right");
4593         }
4594       }
4595     }
4596   }
4597   W_L("<div");
4598   W_L(" style=\""); 
4599   W_L("font-size:small;");
4600   if (attr_align) {
4601     W_L("text-align:");
4602     W_V(attr_align);
4603     W_L(";");
4604   }
4605   W_L("\">");
4606
4607   return jxhtml->out;
4608 }
4609
4610
4611 /**
4612  * It is a handler who processes the H4 tag.
4613  *
4614  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4615  *                     destination is specified.
4616  * @param node   [i]   The H1 tag node is specified.
4617  * @return The conversion result is returned.
4618  */
4619 static char *
4620 s_jxhtml_end_h4_tag(void *pdoc, Node *UNUSED(child)) 
4621 {
4622   jxhtml_t      *jxhtml;
4623   Doc           *doc;
4624   request_rec   *r;
4625
4626   jxhtml = GET_JXHTML(pdoc);
4627   doc     = jxhtml->doc;
4628   r       = doc->r;
4629   
4630   W_L("</div>");
4631   if (IS_CSS_ON(jxhtml->entryp)) {
4632     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4633   }
4634
4635   return jxhtml->out;
4636 }
4637
4638
4639 /**
4640  * It is a handler who processes the H5 tag.
4641  *
4642  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4643  *                     destination is specified.
4644  * @param node   [i]   The H1 tag node is specified.
4645  * @return The conversion result is returned.
4646  */
4647 static char *
4648 s_jxhtml_start_h5_tag(void *pdoc, Node *node)
4649 {
4650   jxhtml_t    *jxhtml;
4651   Doc         *doc;
4652   request_rec *r;
4653   Attr        *attr;
4654   char        *attr_style = NULL;
4655   char        *attr_align = NULL;
4656
4657   jxhtml   = GET_JXHTML(pdoc);
4658   doc     = jxhtml->doc;
4659   r       = doc->r;
4660
4661   for (attr = qs_get_attr(doc,node);
4662        attr;
4663        attr = qs_get_next_attr(doc,attr)) {
4664     char *name  = qs_get_attr_name(doc,attr);
4665     char *value = qs_get_attr_value(doc,attr);
4666     if (STRCASEEQ('a','A',"align", name)) {
4667       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4668         attr_align = value;
4669       }
4670     }
4671     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4672       attr_style = value;
4673     }
4674   }
4675   if (IS_CSS_ON(jxhtml->entryp)) {
4676     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4677     if (style) {
4678       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4679       css_property_t *cur;
4680       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4681         if (STRCASEEQ('l','L',"left", cur->value)) {
4682           attr_align = apr_pstrdup(doc->pool, "left");
4683         }
4684         else if (STRCASEEQ('c','C',"center",cur->value)) {
4685           attr_align = apr_pstrdup(doc->pool, "center");
4686         }
4687         else if (STRCASEEQ('r','R',"right",cur->value)) {
4688           attr_align = apr_pstrdup(doc->pool, "right");
4689         }
4690       }
4691     }
4692   }
4693   W_L("<div");
4694   W_L(" style=\""); 
4695   W_L("font-size:x-small;");
4696   if (attr_align) {
4697     W_L("text-align:");
4698     W_V(attr_align);
4699     W_L(";");
4700   }
4701   W_L("\">");
4702
4703   return jxhtml->out;
4704 }
4705
4706
4707 /**
4708  * It is a handler who processes the H5 tag.
4709  *
4710  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4711  *                     destination is specified.
4712  * @param node   [i]   The H1 tag node is specified.
4713  * @return The conversion result is returned.
4714  */
4715 static char *
4716 s_jxhtml_end_h5_tag(void *pdoc, Node *UNUSED(child)) 
4717 {
4718   jxhtml_t    *jxhtml;
4719   Doc         *doc;
4720   request_rec *r;
4721
4722   jxhtml = GET_JXHTML(pdoc);
4723   doc     = jxhtml->doc;
4724   r       = doc->r;
4725   
4726   W_L("</div>");
4727   if (IS_CSS_ON(jxhtml->entryp)) {
4728     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4729   }
4730
4731   return jxhtml->out;
4732 }
4733
4734
4735 /**
4736  * It is a handler who processes the H6 tag.
4737  *
4738  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4739  *                     destination is specified.
4740  * @param node   [i]   The H1 tag node is specified.
4741  * @return The conversion result is returned.
4742  */
4743 static char *
4744 s_jxhtml_start_h6_tag(void *pdoc, Node *node)
4745 {
4746   jxhtml_t    *jxhtml;
4747   Doc         *doc;
4748   request_rec *r;
4749   Attr        *attr;
4750   char        *attr_style = NULL;
4751   char        *attr_align = NULL;
4752
4753   jxhtml   = GET_JXHTML(pdoc);
4754   doc     = jxhtml->doc;
4755   r       = doc->r;
4756
4757   for (attr = qs_get_attr(doc,node);
4758        attr;
4759        attr = qs_get_next_attr(doc,attr)) {
4760     char *name  = qs_get_attr_name(doc,attr);
4761     char *value = qs_get_attr_value(doc,attr);
4762     if (STRCASEEQ('a','A',"align", name)) {
4763       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
4764         attr_align = value;
4765       }
4766     }
4767     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
4768       attr_style = value;
4769     }
4770   }
4771   if (IS_CSS_ON(jxhtml->entryp)) {
4772     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4773     if (style) {
4774       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "text-align");
4775       css_property_t *cur;
4776       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4777         if (STRCASEEQ('l','L',"left", cur->value)) {
4778           attr_align = apr_pstrdup(doc->pool, "left");
4779         }
4780         else if (STRCASEEQ('c','C',"center",cur->value)) {
4781           attr_align = apr_pstrdup(doc->pool, "center");
4782         }
4783         else if (STRCASEEQ('r','R',"right",cur->value)) {
4784           attr_align = apr_pstrdup(doc->pool, "right");
4785         }
4786       }
4787     }
4788   }
4789   W_L("<div");
4790   W_L(" style=\""); 
4791   W_L("font-size:xx-small;");
4792   if (attr_align) {
4793     W_L("text-align:");
4794     W_V(attr_align);
4795     W_L(";");
4796   }
4797   W_L("\">");
4798
4799   return jxhtml->out;
4800 }
4801
4802
4803 /**
4804  * It is a handler who processes the H6 tag.
4805  *
4806  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4807  *                     destination is specified.
4808  * @param node   [i]   The H1 tag node is specified.
4809  * @return The conversion result is returned.
4810  */
4811 static char *
4812 s_jxhtml_end_h6_tag(void *pdoc, Node *UNUSED(child)) 
4813 {
4814   jxhtml_t    *jxhtml;
4815   Doc         *doc;
4816   request_rec *r;
4817
4818   jxhtml = GET_JXHTML(pdoc);
4819   doc     = jxhtml->doc;
4820   r       = doc->r;
4821   
4822   W_L("</div>");
4823   if (IS_CSS_ON(jxhtml->entryp)) {
4824     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4825   }
4826
4827   return jxhtml->out;
4828 }
4829
4830
4831 /**
4832  * It is a handler who processes the MENU tag.
4833  *
4834  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4835  *                     destination is specified.
4836  * @param node   [i]   The MENU tag node is specified.
4837  * @return The conversion result is returned.
4838  */
4839 static char *
4840 s_jxhtml_start_menu_tag(void *pdoc, Node *node)
4841 {
4842   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
4843   Doc       *doc        = jxhtml->doc;
4844   Attr      *attr;
4845   char      *attr_style = NULL;
4846   char      *attr_color = NULL;
4847   char      *attr_type  = NULL;
4848   char      *attr_size  = NULL;
4849   for (attr = qs_get_attr(doc,node);
4850        attr;
4851        attr = qs_get_next_attr(doc,attr)) {
4852     char *name   = qs_get_attr_name(doc,attr);
4853     char *value  = qs_get_attr_value(doc,attr);
4854     if (STRCASEEQ('t','T',"type",name)) {
4855       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
4856         attr_type = value;
4857       }
4858     }
4859     else if (STRCASEEQ('s','S',"style", name) && value && *value) {
4860       attr_style = value;
4861     }
4862   }
4863   if (IS_CSS_ON(jxhtml->entryp)) {
4864     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
4865     if (style) {
4866       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
4867       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
4868       css_property_t *list_style_type_prop = chxj_css_get_property_value(doc, style, "list-style-type");
4869       css_property_t *cur;
4870       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
4871         if (cur->value && *cur->value) {
4872           attr_color = apr_pstrdup(doc->pool, cur->value);
4873         }
4874       }
4875       for (cur = list_style_type_prop->next; cur != list_style_type_prop; cur = cur->next) {
4876         if (cur->value && *cur->value) {
4877           attr_type = apr_pstrdup(doc->pool, cur->value);
4878         }
4879       }
4880       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
4881         if (cur->value && *cur->value) {
4882           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
4883             attr_size = apr_pstrdup(doc->pool, cur->value);
4884           }
4885           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
4886             attr_size = apr_pstrdup(doc->pool, cur->value);
4887           }
4888           else if (STRCASEEQ('s','S',"small",cur->value)) {
4889             attr_size = apr_pstrdup(doc->pool, cur->value);
4890           }
4891           else if (STRCASEEQ('m','M',"medium",cur->value)) {
4892             attr_size = apr_pstrdup(doc->pool, cur->value);
4893           }
4894           else if (STRCASEEQ('l','L',"large",cur->value)) {
4895             attr_size = apr_pstrdup(doc->pool, cur->value);
4896           }
4897           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
4898             attr_size = apr_pstrdup(doc->pool, cur->value);
4899           }
4900           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
4901             attr_size = apr_pstrdup(doc->pool, cur->value);
4902           }
4903         }
4904       }
4905     }
4906   }
4907   W_L("<menu");
4908   if (attr_type || attr_color || attr_size) {
4909     W_L(" style=\"");
4910     if (attr_type) {
4911       W_L("list-style-type:");
4912       W_V(attr_type);
4913       W_L(";");
4914     }
4915     if (attr_color) {
4916       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
4917       W_L("color:");
4918       W_V(attr_color);
4919       W_L(";");
4920     }
4921     if (attr_size) {
4922       W_L("font-size:");
4923       W_V(attr_size);
4924       W_L(";");
4925     }
4926     W_L("\"");
4927   }
4928   W_L(">");
4929   return jxhtml->out;
4930 }
4931
4932
4933 /**
4934  * It is a handler who processes the MENU tag.
4935  *
4936  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4937  *                     destination is specified.
4938  * @param node   [i]   The MENU tag node is specified.
4939  * @return The conversion result is returned.
4940  */
4941 static char *
4942 s_jxhtml_end_menu_tag(void *pdoc, Node *UNUSED(child))
4943 {
4944   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
4945   Doc *doc = jxhtml->doc;
4946   W_L("</menu>");
4947   if (IS_CSS_ON(jxhtml->entryp)) {
4948     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
4949   }
4950   return jxhtml->out;
4951 }
4952
4953
4954 /**
4955  * It is a handler who processes the PLAINTEXT tag.
4956  *
4957  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4958  *                     destination is specified.
4959  * @param node   [i]   The PLAINTEXT tag node is specified.
4960  * @return The conversion result is returned.
4961  */
4962 static char *
4963 s_jxhtml_start_plaintext_tag(void *pdoc, Node *node)
4964 {
4965   jxhtml_t *jxhtml;
4966   Doc *doc;
4967
4968   jxhtml = GET_JXHTML(pdoc);
4969   doc     = jxhtml->doc;
4970   W_L("<plaintext>");
4971   s_jxhtml_start_plaintext_tag_inner(pdoc,node);
4972   return jxhtml->out;
4973 }
4974
4975 static char *
4976 s_jxhtml_start_plaintext_tag_inner(void *pdoc, Node *node)
4977 {
4978   jxhtml_t *jxhtml;
4979   Doc *doc;
4980   Node *child;
4981   jxhtml = GET_JXHTML(pdoc);
4982   doc     = jxhtml->doc;
4983   for (child = qs_get_child_node(doc, node);
4984        child;
4985        child = qs_get_next_node(doc, child)) {
4986     W_V(child->otext);
4987     s_jxhtml_start_plaintext_tag_inner(pdoc, child);
4988   }
4989   return jxhtml->out;
4990 }
4991
4992
4993 /**
4994  * It is a handler who processes the PLAINTEXT tag.
4995  *
4996  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
4997  *                     destination is specified.
4998  * @param node   [i]   The PLAINTEXT tag node is specified.
4999  * @return The conversion result is returned.
5000  */
5001 static char *
5002 s_jxhtml_end_plaintext_tag(void *pdoc, Node *UNUSED(child))
5003 {
5004   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5005   return jxhtml->out;
5006 }
5007
5008
5009 /**
5010  * It is a handler who processes the BLINK tag.
5011  *
5012  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
5013  *                     destination is specified.
5014  * @param node   [i]   The BLINK tag node is specified.
5015  * @return The conversion result is returned.
5016  */
5017 static char *
5018 s_jxhtml_start_blink_tag(void *pdoc, Node *node)
5019 {
5020   jxhtml_t *jxhtml      = GET_JXHTML(pdoc);
5021   Doc       *doc        = jxhtml->doc;
5022   Attr      *attr;
5023   char      *attr_style = NULL;
5024   char      *attr_color = NULL;
5025   char      *attr_size  = NULL;
5026   for (attr = qs_get_attr(doc,node);
5027        attr;
5028        attr = qs_get_next_attr(doc,attr)) {
5029     char *name   = qs_get_attr_name(doc,attr);
5030     char *value  = qs_get_attr_value(doc,attr);
5031     if (STRCASEEQ('s','S',"style", name) && value && *value) {
5032       attr_style = value;
5033     }
5034   }
5035   if (IS_CSS_ON(jxhtml->entryp)) {
5036     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
5037     if (style) {
5038       css_property_t *color_prop           = chxj_css_get_property_value(doc, style, "color");
5039       css_property_t *size_prop            = chxj_css_get_property_value(doc, style, "font-size");
5040       css_property_t *cur;
5041       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
5042         if (cur->value && *cur->value) {
5043           attr_color = apr_pstrdup(doc->pool, cur->value);
5044         }
5045       }
5046       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
5047         if (cur->value && *cur->value) {
5048           if (STRCASEEQ('x','X',"xx-small",cur->value)) {
5049             attr_size = apr_pstrdup(doc->pool, cur->value);
5050           }
5051           else if (STRCASEEQ('x','X',"x-small",cur->value)) {
5052             attr_size = apr_pstrdup(doc->pool, cur->value);
5053           }
5054           else if (STRCASEEQ('s','S',"small",cur->value)) {
5055             attr_size = apr_pstrdup(doc->pool, cur->value);
5056           }
5057           else if (STRCASEEQ('m','M',"medium",cur->value)) {
5058             attr_size = apr_pstrdup(doc->pool, cur->value);
5059           }
5060           else if (STRCASEEQ('l','L',"large",cur->value)) {
5061             attr_size = apr_pstrdup(doc->pool, cur->value);
5062           }
5063           else if (STRCASEEQ('x','X',"x-large",cur->value)) {
5064             attr_size = apr_pstrdup(doc->pool, cur->value);
5065           }
5066           else if (STRCASEEQ('x','X',"xx-large",cur->value)) {
5067             attr_size = apr_pstrdup(doc->pool, cur->value);
5068           }
5069         }
5070       }
5071     }
5072   }
5073   W_L("<blink");
5074   if (attr_color || attr_size) {
5075     W_L(" style=\"");
5076     if (attr_color) {
5077       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
5078       W_L("color:");
5079       W_V(attr_color);
5080       W_L(";");
5081     }
5082     if (attr_size) {
5083       W_L("font-size:");
5084       W_V(attr_size);
5085       W_L(";");
5086     }
5087     W_L("\"");
5088   }
5089   W_L(">");
5090   return jxhtml->out;
5091 }
5092
5093
5094 /**
5095  * It is a handler who processes the BLINK tag.
5096  *
5097  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
5098  *                     destination is specified.
5099  * @param node   [i]   The BLINK tag node is specified.
5100  * @return The conversion result is returned.
5101  */
5102 static char *
5103 s_jxhtml_end_blink_tag(void *pdoc, Node *UNUSED(child))
5104 {
5105   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5106   Doc      *doc = jxhtml->doc;
5107   W_L("</blink>");
5108   if (IS_CSS_ON(jxhtml->entryp)) {
5109     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
5110   }
5111   return jxhtml->out;
5112 }
5113
5114
5115 /**
5116  * It is a handler who processes the MARQUEE tag.
5117  *
5118  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
5119  *                     destination is specified.
5120  * @param node   [i]   The MARQUEE tag node is specified.
5121  * @return The conversion result is returned.
5122  */
5123 static char *
5124 s_jxhtml_start_marquee_tag(void *pdoc, Node *node)
5125 {
5126   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5127   Doc       *doc = jxhtml->doc;
5128   Attr      *attr;
5129   char      *attr_direction = NULL;
5130   char      *attr_style     = NULL;
5131   char      *attr_color     = NULL;
5132   char      *attr_size      = NULL;
5133   char      *attr_bgcolor   = NULL;
5134   /*--------------------------------------------------------------------------*/
5135   /* Get Attributes                                                           */
5136   /*--------------------------------------------------------------------------*/
5137   for (attr = qs_get_attr(doc,node);
5138        attr;
5139        attr = qs_get_next_attr(doc,attr)) {
5140     char *name   = qs_get_attr_name(doc,attr);
5141     char *value  = qs_get_attr_value(doc,attr);
5142     if (STRCASEEQ('d','D',"direction", name)) {
5143       if (value) {
5144         if (STRCASEEQ('l','L',"left",value)) {
5145           attr_direction = "rtl";
5146         }
5147         else if (STRCASEEQ('r','R',"right",value)) {
5148           attr_direction = "ltr";
5149         }
5150       }
5151     }
5152     else if (STRCASEEQ('b','B',"behavior",name)) {
5153       /* ignore */
5154     }
5155     else if (STRCASEEQ('l','L',"loop",name)) {
5156       /* ignore */
5157     }
5158     else if (STRCASEEQ('b','B',"bgcolor",name)) {
5159       if (value && *value) {
5160         attr_bgcolor = value;
5161       }
5162     }
5163     else if (STRCASEEQ('s','S',"style",name) && value && *value) {
5164       attr_style = value;
5165     }
5166   }
5167   if (IS_CSS_ON(jxhtml->entryp)) {
5168     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
5169     if (style) {
5170       css_property_t *color_prop = chxj_css_get_property_value(doc, style, "color");
5171       css_property_t *size_prop  = chxj_css_get_property_value(doc, style, "font-size");
5172       css_property_t *bgcolor_prop  = chxj_css_get_property_value(doc, style, "background-color");
5173       css_property_t *direction_prop  = chxj_css_get_property_value(doc, style, "-wap-marquee-dir");
5174       css_property_t *cur;
5175       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
5176         if (cur->value && *cur->value) {
5177           attr_color = apr_pstrdup(doc->pool, cur->value);
5178         }
5179       }
5180       for (cur = bgcolor_prop->next; cur != bgcolor_prop; cur = cur->next) {
5181         if (cur->value && *cur->value) {
5182           attr_bgcolor = apr_pstrdup(doc->pool, cur->value);
5183         }
5184       }
5185       for (cur = direction_prop->next; cur != direction_prop; cur = cur->next) {
5186         if (cur->value && *cur->value) {
5187           attr_direction = apr_pstrdup(doc->pool, cur->value);
5188         }
5189       }
5190       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
5191         if (cur->value && *cur->value) {
5192           if ( STRCASEEQ('x','X',"xx-small",cur->value)
5193             || STRCASEEQ('x','X',"x-small", cur->value)
5194             || STRCASEEQ('s','S',"small",   cur->value)
5195             || STRCASEEQ('m','M',"medium",  cur->value)
5196             || STRCASEEQ('l','L',"large",   cur->value)
5197             || STRCASEEQ('x','X',"x-large", cur->value)
5198             || STRCASEEQ('x','X',"xx-large",cur->value)) {
5199             attr_size = apr_pstrdup(doc->pool, cur->value);
5200           }
5201         }
5202       }
5203     }
5204   }
5205   W_L("<marquee");
5206   if (attr_color || attr_size || attr_direction || attr_bgcolor) {
5207     W_L(" style=\"");
5208     if (attr_direction) {
5209       W_L("-wap-marquee-dir:");
5210       W_V(attr_direction);
5211       W_L(";");
5212     }
5213     if (attr_bgcolor) {
5214       attr_bgcolor = chxj_css_rgb_func_to_value(doc->pool, attr_bgcolor);
5215       W_L("background-color:");
5216       W_V(attr_bgcolor);
5217       W_L(";");
5218     }
5219     if (attr_color) {
5220       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
5221       W_L("color:");
5222       W_V(attr_color);
5223       W_L(";");
5224     }
5225     if (attr_size) {
5226       W_L("font-size:");
5227       W_V(attr_size);
5228       W_L(";");
5229     }
5230     W_L("\"");
5231   }
5232   W_L(">");
5233
5234   return jxhtml->out;
5235 }
5236
5237
5238 /**
5239  * It is a handler who processes the MARQUEE tag.
5240  *
5241  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
5242  *                     destination is specified.
5243  * @param node   [i]   The MARQUEE tag node is specified.
5244  * @return The conversion result is returned.
5245  */
5246 static char *
5247 s_jxhtml_end_marquee_tag(void *pdoc, Node *UNUSED(node))
5248 {
5249   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5250   Doc      *doc     = jxhtml->doc;
5251   W_L("</marquee>");
5252   if (IS_CSS_ON(jxhtml->entryp)) {
5253     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
5254   }
5255   return jxhtml->out;
5256 }
5257
5258
5259 /**
5260  * It is handler who processes the New Line Code.
5261  */
5262 static char *
5263 s_jxhtml_newline_mark(void *pdoc, Node *UNUSED(node))
5264 {
5265   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5266   if (jxhtml->start_html_flag) {
5267     Doc *doc = jxhtml->doc;
5268     W_NLCODE();
5269   }
5270   return jxhtml->out;
5271 }
5272
5273
5274 /**
5275  * It is a handler who processes the LINK tag.
5276  *
5277  * @param pdoc  [i/o] The pointer to the JXHTML structure at the output
5278  *                     destination is specified.
5279  * @param node   [i]   The LINK tag node is specified.
5280  * @return The conversion result is returned.
5281  */
5282 static char *
5283 s_jxhtml_link_tag(void *pdoc, Node *node)
5284 {
5285   jxhtml_t      *jxhtml;
5286   Doc           *doc;
5287   Attr          *attr;
5288   char          *rel  = NULL;
5289   char          *href = NULL;
5290   char          *type = NULL;
5291
5292   jxhtml = GET_JXHTML(pdoc);
5293   doc    = jxhtml->doc;
5294
5295   if (! IS_CSS_ON(jxhtml->entryp)) {
5296     return jxhtml->out;
5297   }
5298
5299   for (attr = qs_get_attr(doc,node);
5300        attr;
5301        attr = qs_get_next_attr(doc,attr)) {
5302     char *name  = qs_get_attr_name(doc,attr);
5303     char *value = qs_get_attr_value(doc,attr);
5304     if (STRCASEEQ('r','R',"rel", name)) {
5305       if (value && *value && STRCASEEQ('s','S',"stylesheet", value)) {
5306         rel = value;
5307       }
5308     }
5309     else if (STRCASEEQ('h','H',"href", name)) {
5310       if (value && *value) {
5311         href = value;
5312       }
5313     }
5314     else if (STRCASEEQ('t','T',"type", name)) {
5315       if (value && *value && STRCASEEQ('t','T',"text/css",value)) {
5316         type = value;
5317       }
5318     }
5319   }
5320
5321   if (rel && href && type) {
5322     DBG(doc->r, "start load CSS. url:[%s]", href);
5323     jxhtml->style = chxj_css_parse_from_uri(doc->r, doc->pool, jxhtml->style, href);
5324     DBG(doc->r, "end load CSS. url:[%s]", href);
5325   }
5326
5327   return jxhtml->out;
5328 }
5329
5330
5331 static css_prop_list_t *
5332 s_jxhtml_push_and_get_now_style(void *pdoc, Node *node, const char *style_attr_value)
5333 {
5334   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5335   Doc *doc = jxhtml->doc;
5336   css_prop_list_t *last_css = NULL;
5337   if (IS_CSS_ON(jxhtml->entryp)) {
5338     css_prop_list_t *dup_css;
5339     css_selector_t  *selector;
5340
5341     last_css = chxj_css_get_last_prop_list(jxhtml->css_prop_stack);
5342     dup_css  = chxj_dup_css_prop_list(doc, last_css);
5343     selector = chxj_css_find_selector(doc, jxhtml->style, node);
5344     if (selector) {
5345       chxj_css_prop_list_merge_property(doc, dup_css, selector);
5346     }
5347     chxj_css_push_prop_list(jxhtml->css_prop_stack, dup_css);
5348     last_css = chxj_css_get_last_prop_list(jxhtml->css_prop_stack);
5349
5350     if (style_attr_value) {
5351       css_stylesheet_t *ssheet = chxj_css_parse_style_attr(doc, NULL, apr_pstrdup(doc->pool, node->name), NULL, NULL, apr_pstrdup(doc->pool, style_attr_value));
5352       if (ssheet) {
5353         chxj_css_prop_list_merge_property(doc, last_css, ssheet->selector_head.next);
5354       }
5355     }
5356   }
5357   return last_css;
5358 }
5359
5360
5361 static css_prop_list_t *
5362 s_jxhtml_nopush_and_get_now_style(void *pdoc, Node *node, const char *style_attr_value)
5363 {
5364   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5365   Doc *doc = jxhtml->doc;
5366   css_prop_list_t *last_css = NULL;
5367   if (IS_CSS_ON(jxhtml->entryp)) {
5368     css_prop_list_t *dup_css;
5369     css_selector_t  *selector;
5370
5371     last_css = chxj_css_get_last_prop_list(jxhtml->css_prop_stack);
5372     dup_css  = chxj_dup_css_prop_list(doc, last_css);
5373     selector = chxj_css_find_selector(doc, jxhtml->style, node);
5374     if (selector) {
5375       chxj_css_prop_list_merge_property(doc, dup_css, selector);
5376     }
5377     last_css = dup_css;
5378
5379     if (style_attr_value) {
5380       css_stylesheet_t *ssheet = chxj_css_parse_style_attr(doc, NULL, apr_pstrdup(doc->pool, node->name), NULL, NULL, apr_pstrdup(doc->pool, style_attr_value));
5381       if (ssheet) {
5382         chxj_css_prop_list_merge_property(doc, last_css, ssheet->selector_head.next);
5383       }
5384     }
5385   }
5386   return last_css;
5387 }
5388
5389
5390 /**
5391  * It is a handler who processes the SPAN tag.
5392  *
5393  * @param pdoc  [i/o] The pointer to the JHTML structure at the output
5394  *                     destination is specified.
5395  * @param node   [i]   The SPAN tag node is specified.
5396  * @return The conversion result is returned.
5397  */
5398 static char *
5399 s_jxhtml_start_span_tag(void *pdoc, Node *node)
5400 {
5401   jxhtml_t *jxhtml;
5402   Doc *doc;
5403   Attr *attr;
5404   char *attr_style = NULL;
5405   char *attr_color = NULL;
5406   char *attr_size = NULL;
5407   char *attr_align = NULL;
5408   char *attr_blink = NULL;
5409   char *attr_marquee = NULL;
5410   char *attr_marquee_dir = NULL;
5411   char *attr_marquee_style = NULL;
5412   char *attr_marquee_loop = NULL;
5413
5414   jxhtml = GET_JXHTML(pdoc);
5415   doc     = jxhtml->doc;
5416
5417   for (attr = qs_get_attr(doc,node);
5418        attr;
5419        attr = qs_get_next_attr(doc,attr)) {
5420     char *nm  = qs_get_attr_name(doc,attr);
5421     char *val = qs_get_attr_value(doc,attr);
5422     if (val && STRCASEEQ('s','S',"style", nm)) {
5423       attr_style = val;
5424     }
5425   }
5426   if (IS_CSS_ON(jxhtml->entryp)) {
5427     css_prop_list_t *style = s_jxhtml_push_and_get_now_style(pdoc, node, attr_style);
5428     if (style) {
5429       css_property_t *color_prop = chxj_css_get_property_value(doc, style, "color");
5430       css_property_t *size_prop = chxj_css_get_property_value(doc, style, "font-size");
5431       css_property_t *text_align_prop = chxj_css_get_property_value(doc, style, "text-align");
5432       css_property_t *decoration_prop = chxj_css_get_property_value(doc, style, "text-decoration");
5433       css_property_t *display_prop = chxj_css_get_property_value(doc, style, "display");
5434       css_property_t *marquee_dir_prop = chxj_css_get_property_value(doc, style, "-wap-marquee-dir");
5435       css_property_t *marquee_style_prop = chxj_css_get_property_value(doc, style, "-wap-marquee-style");
5436       css_property_t *marquee_loop_prop = chxj_css_get_property_value(doc, style, "-wap-marquee-loop");
5437       css_property_t *cur;
5438       for (cur = color_prop->next; cur != color_prop; cur = cur->next) {
5439         attr_color = apr_pstrdup(doc->pool, cur->value);
5440       }
5441       for (cur = size_prop->next; cur != size_prop; cur = cur->next) {
5442         if (cur->value && *cur->value) {
5443           if ( STRCASEEQ('x','X',"xx-small",cur->value)
5444             || STRCASEEQ('x','X',"x-small", cur->value)
5445             || STRCASEEQ('s','S',"small",   cur->value)
5446             || STRCASEEQ('m','M',"medium",  cur->value)
5447             || STRCASEEQ('l','L',"large",   cur->value)
5448             || STRCASEEQ('x','X',"x-large", cur->value)
5449             || STRCASEEQ('x','X',"xx-large",cur->value)) {
5450             attr_size = apr_pstrdup(doc->pool, cur->value);
5451           }
5452         }
5453       }
5454       for (cur = decoration_prop->next; cur != decoration_prop; cur = cur->next) {
5455         if (cur->value && STRCASEEQ('b','B',"blink",cur->value)) {
5456           attr_blink = apr_pstrdup(doc->pool, cur->value);
5457         }
5458       }
5459       for (cur = display_prop->next; cur != display_prop; cur = cur->next) {
5460         if (cur->value && strcasecmp("-wap-marquee",cur->value) == 0) {
5461           attr_marquee = apr_pstrdup(doc->pool, cur->value);
5462         }
5463       }
5464       for (cur = marquee_dir_prop->next; cur != marquee_dir_prop; cur = cur->next) {
5465         if (cur->value && *cur->value) {
5466           if ( STRCASEEQ('l','L',"ltr",cur->value)
5467             || STRCASEEQ('r','R',"rtl",cur->value)) {
5468             attr_marquee_dir = apr_pstrdup(doc->pool, cur->value);
5469           }
5470         }
5471       }
5472       for (cur = marquee_style_prop->next; cur != marquee_style_prop; cur = cur->next) {
5473         if (cur->value && *cur->value) {
5474           if ( STRCASEEQ('s','S',"scroll",cur->value)
5475             || STRCASEEQ('s','S',"slide",cur->value)
5476             || STRCASEEQ('a','A',"alternate",cur->value)) {
5477             attr_marquee_style = apr_pstrdup(doc->pool, cur->value);
5478           }
5479         }
5480       }
5481       for (cur = marquee_loop_prop->next; cur != marquee_loop_prop; cur = cur->next) {
5482         if (cur->value && *cur->value) {
5483           attr_marquee_loop = apr_pstrdup(doc->pool, cur->value);
5484         }
5485       }
5486       for (cur = text_align_prop->next; cur != text_align_prop; cur = cur->next) {
5487         if (STRCASEEQ('l','L',"left", cur->value)) {
5488           attr_align = apr_pstrdup(doc->pool, "left");
5489         }
5490         else if (STRCASEEQ('c','C',"center",cur->value)) {
5491           attr_align = apr_pstrdup(doc->pool, "center");
5492         }
5493         else if (STRCASEEQ('r','R',"right",cur->value)) {
5494           attr_align = apr_pstrdup(doc->pool, "right");
5495         }
5496       }
5497     }
5498   }
5499
5500   W_L("<span");
5501   if (attr_color || attr_size || attr_align || attr_blink || attr_marquee) {
5502     W_L(" style=\"");
5503     if (attr_color) {
5504       attr_color = chxj_css_rgb_func_to_value(doc->pool, attr_color);
5505       W_L("color:");
5506       W_V(attr_color);
5507       W_L(";");
5508     }
5509     if (attr_size) {
5510       W_L("font-size:");
5511       W_V(attr_size);
5512       W_L(";");
5513     }
5514     if (attr_align) {
5515       W_L("text-align:");
5516       W_V(attr_align);
5517       W_L(";");
5518     }
5519     if (attr_blink) {
5520       W_L("text-decoration:");
5521       W_V("blink");
5522       W_L(";");
5523     }
5524     if (attr_marquee) {
5525       W_L("display:-wap-marquee;");
5526       if (attr_marquee_dir) {
5527         W_L("-wap-marquee-dir:");
5528         W_V(attr_marquee_dir);
5529         W_L(";");
5530       }
5531       if (attr_marquee_style) {
5532         W_L("-wap-marquee-style:");
5533         W_V(attr_marquee_style);
5534         W_L(";");
5535       }
5536       if (attr_marquee_loop) {
5537         W_L("-wap-marquee-loop:");
5538         W_V(attr_marquee_loop);
5539         W_L(";");
5540       }
5541     }
5542     W_L("\"");
5543   }
5544   W_L(">");
5545   return jxhtml->out;
5546 }
5547
5548
5549 /**
5550  * It is a handler who processes the SPAN tag.
5551  *
5552  * @param pdoc  [i/o] The pointer to the JHTML structure at the output
5553  *                     destination is specified.
5554  * @param node   [i]   The SPAN tag node is specified.
5555  * @return The conversion result is returned.
5556  */
5557 static char *
5558 s_jxhtml_end_span_tag(void *pdoc, Node *UNUSED(node))
5559 {
5560   jxhtml_t *jxhtml = GET_JXHTML(pdoc);
5561   Doc *doc = jxhtml->doc;
5562
5563   W_L("</span>");
5564   if (IS_CSS_ON(jxhtml->entryp)) {
5565     chxj_css_pop_prop_list(jxhtml->css_prop_stack);
5566   }
5567   return jxhtml->out;
5568 }
5569
5570
5571 /**
5572  * It is a handler who processes the STYLE tag.
5573  *
5574  * @param pdoc  [i/o] The pointer to the SoftBank XHTML structure at the output
5575  *                     destination is specified.
5576  * @param node   [i]   The STYLE tag node is specified.
5577  * @return The conversion result is returned.
5578  */
5579 static char *
5580 s_jxhtml_style_tag(void *pdoc, Node *node)
5581 {
5582   jxhtml_t     *jxhtml;
5583   Doc           *doc;
5584   Attr          *attr;
5585   char          *type = NULL;
5586
5587   jxhtml = GET_JXHTML(pdoc);
5588   doc     = jxhtml->doc;
5589
5590   if (! IS_CSS_ON(jxhtml->entryp)) {
5591     return jxhtml->out;
5592   }
5593
5594   for (attr = qs_get_attr(doc,node);
5595        attr;
5596        attr = qs_get_next_attr(doc,attr)) {
5597     char *name  = qs_get_attr_name(doc,attr);
5598     char *value = qs_get_attr_value(doc,attr);
5599     if (STRCASEEQ('t','T',"type", name)) {
5600       if (value && *value && STRCASEEQ('t','T',"text/css",value)) {
5601         type = value;
5602       }
5603     }
5604   }
5605
5606   Node *child = qs_get_child_node(doc, node);
5607   if (type && child) {
5608     char *name  = qs_get_node_name(doc, child);
5609     if (STRCASEEQ('t','T',"text", name)) {
5610       char *value = qs_get_node_value(doc, child);
5611       DBG(doc->r, "start load CSS. buf:[%s]", value);
5612       jxhtml->style = chxj_css_parse_style_value(doc, jxhtml->style, value);
5613       DBG(doc->r, "end load CSS. value:[%s]", value);
5614     }
5615   }
5616   return jxhtml->out;
5617 }
5618 /*
5619  * vim:ts=2 et
5620  */