Annotation of Amaya/amaya/XHTMLbuilder.c, revision 1.28
1.1 cvs 1: /*
2: *
3: * (c) COPYRIGHT MIT and INRIA, 1996.
4: * Please first read the full copyright statement in file COPYRIGHT.
5: *
6: */
7:
8: /*
9: *
1.23 cvs 10: * Builds the corresponding abstract tree for a Thot document of type HTML.
1.1 cvs 11: *
1.20 cvs 12: * Authors: L. Carcone
13: * V. Quint
1.1 cvs 14: */
15:
16: #define THOT_EXPORT extern
17: #include "amaya.h"
18: #include "css.h"
1.2 cvs 19: #include "parser.h"
20: #include "HTML.h"
21:
1.13 cvs 22: #include "css_f.h"
23: #include "fetchXMLname_f.h"
1.22 cvs 24: #include "html2thot_f.h"
1.1 cvs 25: #include "HTMLactions_f.h"
26: #include "HTMLedit_f.h"
1.22 cvs 27: #include "HTMLform_f.h"
1.1 cvs 28: #include "HTMLimage_f.h"
29: #include "HTMLtable_f.h"
30: #include "HTMLimage_f.h"
31: #include "UIcss_f.h"
1.13 cvs 32: #include "styleparser_f.h"
1.2 cvs 33: #include "XHTMLbuilder_f.h"
1.13 cvs 34: #include "Xml2thot_f.h"
1.1 cvs 35:
36: /* maximum length of a Thot structure schema name */
37: #define MAX_SS_NAME_LENGTH 32
38:
1.14 cvs 39: /* Mapping table of HTML attribute values */
40: AttrValueMapping XhtmlAttrValueMappingTable[] =
1.1 cvs 41: {
42: {HTML_ATTR_dir, TEXT("ltr"), HTML_ATTR_dir_VAL_ltr},
43: {HTML_ATTR_dir, TEXT("rtl"), HTML_ATTR_dir_VAL_rtl},
44:
45: {HTML_ATTR_TextAlign, TEXT("left"), HTML_ATTR_TextAlign_VAL_left_},
46: {HTML_ATTR_TextAlign, TEXT("center"), HTML_ATTR_TextAlign_VAL_center_},
47: {HTML_ATTR_TextAlign, TEXT("right"), HTML_ATTR_TextAlign_VAL_right_},
48: {HTML_ATTR_TextAlign, TEXT("justify"), HTML_ATTR_TextAlign_VAL_justify_},
49:
50: {HTML_ATTR_Align, TEXT("left"), HTML_ATTR_Align_VAL_left_},
51: {HTML_ATTR_Align, TEXT("center"), HTML_ATTR_Align_VAL_center_},
52: {HTML_ATTR_Align, TEXT("right"), HTML_ATTR_Align_VAL_right_},
53:
54: {HTML_ATTR_LAlign, TEXT("top"), HTML_ATTR_LAlign_VAL_Top_},
55: {HTML_ATTR_LAlign, TEXT("bottom"), HTML_ATTR_LAlign_VAL_Bottom_},
56: {HTML_ATTR_LAlign, TEXT("left"), HTML_ATTR_LAlign_VAL_Left_},
57: {HTML_ATTR_LAlign, TEXT("right"), HTML_ATTR_LAlign_VAL_Right_},
58:
59: {HTML_ATTR_Clear, TEXT("left"), HTML_ATTR_Clear_VAL_Left_},
60: {HTML_ATTR_Clear, TEXT("right"), HTML_ATTR_Clear_VAL_Right_},
61: {HTML_ATTR_Clear, TEXT("all"), HTML_ATTR_Clear_VAL_All_},
62: {HTML_ATTR_Clear, TEXT("none"), HTML_ATTR_Clear_VAL_None_},
63:
64: {HTML_ATTR_NumberStyle, TEXT("1"), HTML_ATTR_NumberStyle_VAL_Arabic_},
65: {HTML_ATTR_NumberStyle, TEXT("a"), HTML_ATTR_NumberStyle_VAL_LowerAlpha},
66: {HTML_ATTR_NumberStyle, TEXT("A"), HTML_ATTR_NumberStyle_VAL_UpperAlpha},
67: {HTML_ATTR_NumberStyle, TEXT("i"), HTML_ATTR_NumberStyle_VAL_LowerRoman},
68: {HTML_ATTR_NumberStyle, TEXT("I"), HTML_ATTR_NumberStyle_VAL_UpperRoman},
69:
70: {HTML_ATTR_BulletStyle, TEXT("disc"), HTML_ATTR_BulletStyle_VAL_disc},
71: {HTML_ATTR_BulletStyle, TEXT("square"), HTML_ATTR_BulletStyle_VAL_square},
72: {HTML_ATTR_BulletStyle, TEXT("circle"), HTML_ATTR_BulletStyle_VAL_circle},
73:
74: {HTML_ATTR_ItemStyle, TEXT("1"), HTML_ATTR_ItemStyle_VAL_Arabic_},
75: {HTML_ATTR_ItemStyle, TEXT("a"), HTML_ATTR_ItemStyle_VAL_LowerAlpha},
76: {HTML_ATTR_ItemStyle, TEXT("A"), HTML_ATTR_ItemStyle_VAL_UpperAlpha},
77: {HTML_ATTR_ItemStyle, TEXT("i"), HTML_ATTR_ItemStyle_VAL_LowerRoman},
78: {HTML_ATTR_ItemStyle, TEXT("I"), HTML_ATTR_ItemStyle_VAL_UpperRoman},
79: {HTML_ATTR_ItemStyle, TEXT("disc"), HTML_ATTR_ItemStyle_VAL_disc},
80: {HTML_ATTR_ItemStyle, TEXT("square"), HTML_ATTR_ItemStyle_VAL_square},
81: {HTML_ATTR_ItemStyle, TEXT("circle"), HTML_ATTR_ItemStyle_VAL_circle},
82:
83: {HTML_ATTR_Button_type, TEXT("button"), HTML_ATTR_Button_type_VAL_button},
84: {HTML_ATTR_Button_type, TEXT("submit"), HTML_ATTR_Button_type_VAL_submit},
85: {HTML_ATTR_Button_type, TEXT("reset"), HTML_ATTR_Button_type_VAL_reset},
86:
87: {HTML_ATTR_frame, TEXT("void"), HTML_ATTR_frame_VAL_void},
88: {HTML_ATTR_frame, TEXT("above"), HTML_ATTR_frame_VAL_above},
89: {HTML_ATTR_frame, TEXT("below"), HTML_ATTR_frame_VAL_below},
90: {HTML_ATTR_frame, TEXT("hsides"), HTML_ATTR_frame_VAL_hsides},
91: {HTML_ATTR_frame, TEXT("lhs"), HTML_ATTR_frame_VAL_lhs},
92: {HTML_ATTR_frame, TEXT("rhs"), HTML_ATTR_frame_VAL_rhs},
93: {HTML_ATTR_frame, TEXT("vsides"), HTML_ATTR_frame_VAL_vsides},
94: {HTML_ATTR_frame, TEXT("box"), HTML_ATTR_frame_VAL_box},
95: {HTML_ATTR_frame, TEXT("border"), HTML_ATTR_frame_VAL_border},
96:
97: {HTML_ATTR_frameborder, TEXT("0"), HTML_ATTR_frameborder_VAL_Border0},
98: {HTML_ATTR_frameborder, TEXT("1"), HTML_ATTR_frameborder_VAL_Border1},
99:
100: {HTML_ATTR_scrolling, TEXT("yes"), HTML_ATTR_scrolling_VAL_Yes_},
101: {HTML_ATTR_scrolling, TEXT("no"), HTML_ATTR_scrolling_VAL_No_},
102: {HTML_ATTR_scrolling, TEXT("auto"), HTML_ATTR_scrolling_VAL_auto_},
103:
104: {HTML_ATTR_rules_, TEXT("none"), HTML_ATTR_rules__VAL_none_},
105: {HTML_ATTR_rules_, TEXT("groups"), HTML_ATTR_rules__VAL_groups},
106: {HTML_ATTR_rules_, TEXT("rows"), HTML_ATTR_rules__VAL_rows},
107: {HTML_ATTR_rules_, TEXT("cols"), HTML_ATTR_rules__VAL_cols},
108: {HTML_ATTR_rules_, TEXT("all"), HTML_ATTR_rules__VAL_all},
109:
110: {HTML_ATTR_Cell_align, TEXT("left"), HTML_ATTR_Cell_align_VAL_Cell_left},
111: {HTML_ATTR_Cell_align, TEXT("center"), HTML_ATTR_Cell_align_VAL_Cell_center},
112: {HTML_ATTR_Cell_align, TEXT("right"), HTML_ATTR_Cell_align_VAL_Cell_right},
113: {HTML_ATTR_Cell_align, TEXT("justify"), HTML_ATTR_Cell_align_VAL_Cell_justify},
114: {HTML_ATTR_Cell_align, TEXT("char"), HTML_ATTR_Cell_align_VAL_Cell_char},
115:
116: {HTML_ATTR_Alignment, TEXT("top"), HTML_ATTR_Alignment_VAL_Top_},
117: {HTML_ATTR_Alignment, TEXT("middle"), HTML_ATTR_Alignment_VAL_Middle_},
118: {HTML_ATTR_Alignment, TEXT("bottom"), HTML_ATTR_Alignment_VAL_Bottom_},
119: {HTML_ATTR_Alignment, TEXT("left"), HTML_ATTR_Alignment_VAL_Left_},
120: {HTML_ATTR_Alignment, TEXT("right"), HTML_ATTR_Alignment_VAL_Right_},
121:
122: {HTML_ATTR_METHOD, TEXT("get"), HTML_ATTR_METHOD_VAL_Get_},
123: {HTML_ATTR_METHOD, TEXT("post"), HTML_ATTR_METHOD_VAL_Post_},
124:
125: {HTML_ATTR_Position, TEXT("top"), HTML_ATTR_Position_VAL_Position_top},
126: {HTML_ATTR_Position, TEXT("bottom"), HTML_ATTR_Position_VAL_Position_bottom},
127: {HTML_ATTR_Position, TEXT("left"), HTML_ATTR_Position_VAL_Position_left},
128: {HTML_ATTR_Position, TEXT("right"), HTML_ATTR_Position_VAL_Position_right},
129:
130: {HTML_ATTR_Row_valign, TEXT("top"), HTML_ATTR_Row_valign_VAL_Row_top},
131: {HTML_ATTR_Row_valign, TEXT("middle"), HTML_ATTR_Row_valign_VAL_Row_middle},
132: {HTML_ATTR_Row_valign, TEXT("bottom"), HTML_ATTR_Row_valign_VAL_Row_bottom},
133: {HTML_ATTR_Row_valign, TEXT("baseline"), HTML_ATTR_Row_valign_VAL_Row_baseline},
134:
135: {HTML_ATTR_Cell_valign, TEXT("top"), HTML_ATTR_Cell_valign_VAL_Cell_top},
136: {HTML_ATTR_Cell_valign, TEXT("middle"), HTML_ATTR_Cell_valign_VAL_Cell_middle},
137: {HTML_ATTR_Cell_valign, TEXT("bottom"), HTML_ATTR_Cell_valign_VAL_Cell_bottom},
138: {HTML_ATTR_Cell_valign, TEXT("baseline"), HTML_ATTR_Cell_valign_VAL_Cell_baseline},
139:
140: {HTML_ATTR_shape, TEXT("rect"), HTML_ATTR_shape_VAL_rectangle},
141: {HTML_ATTR_shape, TEXT("circle"), HTML_ATTR_shape_VAL_circle},
142: {HTML_ATTR_shape, TEXT("poly"), HTML_ATTR_shape_VAL_polygon},
143:
144: {HTML_ATTR_valuetype, TEXT("data"), HTML_ATTR_valuetype_VAL_data_},
145: {HTML_ATTR_valuetype, TEXT("ref"), HTML_ATTR_valuetype_VAL_ref},
146: {HTML_ATTR_valuetype, TEXT("object"), HTML_ATTR_valuetype_VAL_object_},
147:
148: /* HTML attribute TYPE generates a Thot element */
149: {DummyAttribute, TEXT("button"), HTML_EL_Button_Input},
150: {DummyAttribute, TEXT("checkbox"), HTML_EL_Checkbox_Input},
151: {DummyAttribute, TEXT("file"), HTML_EL_File_Input},
152: {DummyAttribute, TEXT("hidden"), HTML_EL_Hidden_Input},
153: {DummyAttribute, TEXT("image"), HTML_EL_PICTURE_UNIT},
154: {DummyAttribute, TEXT("password"), HTML_EL_Password_Input},
155: {DummyAttribute, TEXT("radio"), HTML_EL_Radio_Input},
156: {DummyAttribute, TEXT("reset"), HTML_EL_Reset_Input},
157: {DummyAttribute, TEXT("submit"), HTML_EL_Submit_Input},
158: {DummyAttribute, TEXT("text"), HTML_EL_Text_Input},
159:
160: /* The following declarations allow the parser to accept boolean attributes */
161: /* written "checked=CHECKED"), for instance */
162: {HTML_ATTR_ISMAP, TEXT("ismap"), HTML_ATTR_ISMAP_VAL_Yes_},
163: {HTML_ATTR_nohref, TEXT("nohref"), HTML_ATTR_nohref_VAL_Yes_},
164: {HTML_ATTR_COMPACT, TEXT("compact"), HTML_ATTR_COMPACT_VAL_Yes_},
165: {HTML_ATTR_Multiple, TEXT("multiple"), HTML_ATTR_Multiple_VAL_Yes_},
166: {HTML_ATTR_Selected, TEXT("selected"), HTML_ATTR_Selected_VAL_Yes_},
167: {HTML_ATTR_Checked, TEXT("checked"), HTML_ATTR_Checked_VAL_Yes_},
168: {HTML_ATTR_No_wrap, TEXT("nowrap"), HTML_ATTR_No_wrap_VAL_no_wrap},
169: {HTML_ATTR_NoShade, TEXT("noshade"), HTML_ATTR_NoShade_VAL_NoShade_},
170: {HTML_ATTR_declare, TEXT("declare"), HTML_ATTR_declare_VAL_Yes_},
171: {HTML_ATTR_defer, TEXT("defer"), HTML_ATTR_defer_VAL_Yes_},
172: {HTML_ATTR_disabled, TEXT("disabled"), HTML_ATTR_disabled_VAL_Yes_},
173: {HTML_ATTR_readonly, TEXT("readonly"), HTML_ATTR_readonly_VAL_Yes_},
174: {HTML_ATTR_no_resize, TEXT("noresize"), HTML_ATTR_no_resize_VAL_Yes_},
1.21 cvs 175:
176: /* XML attribute xml:space */
177: {HTML_ATTR_xml_space, TEXT("default"), HTML_ATTR_xml_space_VAL_xml_space_default},
178: {HTML_ATTR_xml_space, TEXT("preserve"), HTML_ATTR_xml_space_VAL_xml_space_preserve},
179:
1.1 cvs 180: {0, TEXT(""), 0} /* Last entry. Mandatory */
181: };
1.6 cvs 182:
1.28 ! cvs 183: /* Define a pointer to let parser functions access the HTML entity table */
! 184: extern XmlEntity *pXhtmlEntityTable;
1.6 cvs 185:
186: /*----------------------------------------------------------------------
1.15 cvs 187: ParseCharset:
1.6 cvs 188: Parses the element HTTP-EQUIV and looks for the charset value.
189: ----------------------------------------------------------------------*/
190: #ifdef __STDC__
1.15 cvs 191: void ParseCharset (Element el, Document doc)
1.6 cvs 192: #else /* !__STDC__ */
1.15 cvs 193: void ParseCharset (el, doc)
1.6 cvs 194: Element el;
195: Document doc;
196: #endif /* !__STDC__ */
197: {
1.15 cvs 198: AttributeType attrType;
199: Attribute attr;
200: SSchema docSSchema;
201: CHARSET charset;
1.6 cvs 202: CHAR_T *text, *text2, *ptrText, *str;
203: CHAR_T charsetname[MAX_LENGTH];
1.15 cvs 204: int length;
1.6 cvs 205: int pos, index = 0;
206:
1.15 cvs 207: charset = TtaGetDocumentCharset (doc);
208: if (charset != UNDEFINED_CHARSET)
209: /* the charset was already defined by the http header */
210: return;
1.6 cvs 211:
212: docSSchema = TtaGetDocumentSSchema (doc);
213: attrType.AttrSSchema = docSSchema;
214: attrType.AttrTypeNum = HTML_ATTR_http_equiv;
215: attr = TtaGetAttribute (el, attrType);
216: if (attr != NULL)
217: {
218: /* There is a HTTP-EQUIV attribute */
219: length = TtaGetTextAttributeLength (attr);
220: if (length > 0)
221: {
222: text = TtaAllocString (length + 1);
223: TtaGiveTextAttributeValue (attr, text, &length);
224: if (!ustrcasecmp (text, TEXT("content-type")))
225: {
226: attrType.AttrTypeNum = HTML_ATTR_meta_content;
227: attr = TtaGetAttribute (el, attrType);
228: if (attr != NULL)
229: {
230: length = TtaGetTextAttributeLength (attr);
231: if (length > 0)
232: {
233: text2 = TtaAllocString (length + 1);
234: TtaGiveTextAttributeValue (attr, text2, &length);
235: ptrText = text2;
236: while (*ptrText)
237: {
238: *ptrText = utolower (*ptrText);
239: ptrText++;
240: }
241:
242: str = ustrstr (text2, TEXT("charset="));
243: if (str)
244: {
245: pos = str - text2 + 8;
246: while (text2[pos] != WC_SPACE &&
247: text2[pos] != WC_TAB && text2[pos] != WC_EOS)
248: charsetname[index++] = text2[pos++];
249: charsetname[index] = WC_EOS;
1.15 cvs 250: charset = TtaGetCharset (charsetname);
251: if (charset != UNDEFINED_CHARSET)
252: TtaSetDocumentCharset (doc, charset);
1.6 cvs 253: }
254: TtaFreeMemory (text2);
255: }
256: }
257: }
258: TtaFreeMemory (text);
259: }
260: }
261: }
262:
1.23 cvs 263: /*---------------------------------------------------------------------------
264: XhtmlMapEntity
265: Search that entity in the entity table and return the corresponding value.
266: ---------------------------------------------------------------------------*/
267: #ifdef __STDC__
1.25 cvs 268: void XhtmlMapEntity (STRING entityName, int *entityValue, STRING alphabet)
1.23 cvs 269: #else
270: void XhtmlMapEntity (entityName, entityValue, alphabet)
271: STRING entityName;
272: int *entityValue;
273: STRING alphabet;
274: #endif
275: {
276: int i;
277: ThotBool found;
278:
279: found = FALSE;
1.28 ! cvs 280: for (i = 0; pXhtmlEntityTable[i].charCode >= 0 && ! found; i++)
! 281: found = !ustrcmp (pXhtmlEntityTable[i].charName, entityName);
1.23 cvs 282:
283: if (found)
284: {
285: /* entity found */
286: i--;
1.28 ! cvs 287: *entityValue = pXhtmlEntityTable[i].charCode;
! 288: *alphabet = pXhtmlEntityTable[i].charAlphabet;
1.23 cvs 289: }
290: else
291: *alphabet = WC_EOS;
292: }
293:
294: /*----------------------------------------------------------------------
295: PutNonISOlatin1Char
296: Put a Unicode character in the input buffer.
297: ----------------------------------------------------------------------*/
298: #ifdef __STDC__
299: static void PutNonISOlatin1Char (int code,
300: STRING prefix,
301: STRING entityName,
302: ParserData *context)
303: #else
304: static void PutNonISOlatin1Char (code, prefix, entityName, context)
305: int code;
306: STRING prefix;
307: STRING entityName;
308: ParserData *context;
309: #endif
310: {
311: Language lang, l;
312: ElementType elType;
313: Element elText;
314: AttributeType attrType;
315: Attribute attr;
316: CHAR_T buffer[MaxEntityLength+10];
317:
318: /* create a new text leaf */
319: elType.ElSSchema = TtaGetDocumentSSchema (context->doc);
320: elType.ElTypeNum = HTML_EL_TEXT_UNIT;
321: elText = TtaNewElement (context->doc, elType);
322: XmlSetElemLineNumber (elText);
1.26 cvs 323: InsertXmlElement (&elText);
1.23 cvs 324: context->lastElement = elText;
325: context->lastElementClosed = TRUE;
326:
327: /* try to find a fallback character */
328: l = context->language;
329: GetFallbackCharacter (code, buffer, &lang);
330:
331: /* put that fallback character in the new text leaf */
332: TtaSetTextContent (elText, buffer, lang, context->doc);
333: context->language = l;
334:
335: /* make that text leaf read-only */
336: TtaSetAccessRight (elText, ReadOnly, context->doc);
337:
338: /* associate an attribute EntityName with the new text leaf */
339: attrType.AttrSSchema = TtaGetDocumentSSchema (context->doc);
340: attrType.AttrTypeNum = HTML_ATTR_EntityName;
341: attr = TtaNewAttribute (attrType);
342: TtaAttachAttribute (elText, attr, context->doc);
1.25 cvs 343: buffer[0] = '&';
344: ustrcpy (&buffer[1], prefix);
1.23 cvs 345: ustrcat (buffer, entityName);
1.25 cvs 346: ustrcat (buffer, TEXT(";"));
1.23 cvs 347: TtaSetAttributeText (attr, buffer, elText, context->doc);
348: context->mergeText = FALSE;
349: }
350:
351: /*----------------------------------------------------------------------
352: XhtmlEntityCreated
353: A XTHML entity has been created by the XML parser.
354: ----------------------------------------------------------------------*/
355: #ifdef __STDC__
356: void XhtmlEntityCreated (int entityValue, Language lang,
357: STRING entityName, ParserData *context)
358: #else
359: void XhtmlEntityCreated (entityValue, lang, entityName, context)
360: int entityValue;
361: Language lang;
362: STRING entityName;
363: ParserData *context;
364: #endif
365: {
366: CHAR_T buffer[2];
367:
368: if (lang < 0)
369: PutInXmlElement (entityName);
370: else
371: {
372: if (entityValue < 255)
373: {
374: buffer[0] = ((UCHAR_T) entityValue);
375: buffer[1] = WC_EOS;
376: PutInXmlElement (buffer);
377: }
378: else
379: PutNonISOlatin1Char (entityValue, TEXT(""), entityName, context);
380: }
381: }
382:
1.6 cvs 383: /*----------------------------------------------------------------------
384: XhtmlElementComplete
1.20 cvs 385: Complete Xhtml elements.
1.6 cvs 386: Check its attributes and its contents.
387: ----------------------------------------------------------------------*/
388: #ifdef __STDC__
1.15 cvs 389: void XhtmlElementComplete (Element el, Document doc, int *error)
1.6 cvs 390: #else
1.15 cvs 391: void XhtmlElementComplete (el, doc, error)
392: Element el;
393: Document doc;
394: int *error;
1.6 cvs 395: #endif
396: {
1.23 cvs 397: ElementType elType, newElType, childType;
398: Element constElem, child, desc, leaf, prev, next, last,
399: elFrames, lastFrame, lastChild;
400: Attribute attr;
401: AttributeType attrType;
402: Language lang;
403: STRING text;
404: CHAR_T lastChar[2];
405: STRING name1;
406: int length;
407: SSchema docSSchema;
1.6 cvs 408:
409: *error = 0;
410: docSSchema = TtaGetDocumentSSchema (doc);
411:
412: elType = TtaGetElementType (el);
413: /* is this a block-level element in a character-level element? */
1.27 cvs 414: if (!IsXMLElementInline (elType) &&
1.24 cvs 415: elType.ElTypeNum != HTML_EL_Comment_ &&
416: elType.ElTypeNum != HTML_EL_XMLPI)
1.6 cvs 417: BlockInCharLevelElem (el);
418:
419: newElType.ElSSchema = elType.ElSSchema;
420: switch (elType.ElTypeNum)
421: {
422: case HTML_EL_Object: /* it's an object */
423: /* create Object_Content */
424: child = TtaGetFirstChild (el);
425: if (child != NULL)
426: elType = TtaGetElementType (child);
427:
428: /* is it the PICTURE element ? */
429: if (child == NULL || elType.ElTypeNum != HTML_EL_PICTURE_UNIT)
430: {
431: desc = child;
432: /* create the PICTURE element */
433: elType.ElTypeNum = HTML_EL_PICTURE_UNIT;
434: child = TtaNewTree (doc, elType, "");
435: if (desc == NULL)
436: TtaInsertFirstChild (&child, el, doc);
437: else
438: TtaInsertSibling (child, desc, TRUE, doc);
439: }
440:
441: /* copy attribute data into SRC attribute of Object_Image */
442: attrType.AttrSSchema = docSSchema;
443: attrType.AttrTypeNum = HTML_ATTR_data;
444: attr = TtaGetAttribute (el, attrType);
445: if (attr != NULL)
446: {
447: length = TtaGetTextAttributeLength (attr);
448: if (length > 0)
449: {
450: name1 = TtaAllocString (length + 1);
451: TtaGiveTextAttributeValue (attr, name1, &length);
452: attrType.AttrTypeNum = HTML_ATTR_SRC;
453: attr = TtaGetAttribute (child, attrType);
454: if (attr == NULL)
455: {
456: attr = TtaNewAttribute (attrType);
457: TtaAttachAttribute (child, attr, doc);
458: }
459: TtaSetAttributeText (attr, name1, child, doc);
460: TtaFreeMemory (name1);
461: }
462: }
463:
464: /* is the Object_Content element already created ? */
465: desc = child;
466: TtaNextSibling(&desc);
467: if (desc != NULL)
468: elType = TtaGetElementType (desc);
469:
470: /* is it the Object_Content element ? */
471: if (desc == NULL || elType.ElTypeNum != HTML_EL_Object_Content)
472: {
473: /* create Object_Content */
474: elType.ElTypeNum = HTML_EL_Object_Content;
475: desc = TtaNewTree (doc, elType, "");
476: TtaInsertSibling (desc, child, FALSE, doc);
477: /* move previous existing children into Object_Content */
478: child = TtaGetLastChild(el);
479: while (child != desc)
480: {
481: TtaRemoveTree (child, doc);
482: TtaInsertFirstChild (&child, desc, doc);
483: child = TtaGetLastChild(el);
484: }
485: }
486: break;
487:
488: case HTML_EL_Unnumbered_List:
489: case HTML_EL_Numbered_List:
490: case HTML_EL_Menu:
491: case HTML_EL_Directory:
492: /* It's a List element. It should only have List_Item children.
493: If it has List element chidren, move these List elements
494: within their previous List_Item sibling. This is to fix
495: a bug in document generated by Mozilla. */
496: prev = NULL;
497: next = NULL;
498: child = TtaGetFirstChild (el);
499: while (child != NULL)
500: {
501: next = child;
502: TtaNextSibling (&next);
503: elType = TtaGetElementType (child);
504: if (elType.ElTypeNum == HTML_EL_Unnumbered_List ||
505: elType.ElTypeNum == HTML_EL_Numbered_List ||
506: elType.ElTypeNum == HTML_EL_Menu ||
507: elType.ElTypeNum == HTML_EL_Directory)
508: /* this list element is a child of another list element */
509: if (prev)
510: {
511: elType = TtaGetElementType (prev);
512: if (elType.ElTypeNum == HTML_EL_List_Item)
513: {
514: /* get the last child of the previous List_Item */
515: desc = TtaGetFirstChild (prev);
516: last = NULL;
517: while (desc)
518: {
519: last = desc;
520: TtaNextSibling (&desc);
521: }
522: /* move the list element after the last child of the
523: previous List_Item */
524: TtaRemoveTree (child, doc);
525: if (last)
526: TtaInsertSibling (child, last, FALSE, doc);
527: else
528: TtaInsertFirstChild (&child, prev, doc);
529: child = prev;
530: }
531: }
532: prev = child;
533: child = next;
534: }
535: break;
536:
537: case HTML_EL_FRAMESET:
538: /* The FRAMESET element is now complete. Gather all its FRAMESET
539: and FRAME children and wrap them up in a Frames element */
540: elFrames = NULL; lastFrame = NULL;
541: lastChild = NULL;
542: child = TtaGetFirstChild (el);
543: while (child != NULL)
544: {
545: next = child;
546: TtaNextSibling (&next);
547: elType = TtaGetElementType (child);
548: if (elType.ElTypeNum == HTML_EL_FRAMESET ||
549: elType.ElTypeNum == HTML_EL_FRAME ||
550: elType.ElTypeNum == HTML_EL_Comment_)
551: {
552: /* create the Frames element if it does not exist */
553: if (elFrames == NULL)
554: {
555: newElType.ElSSchema = docSSchema;
556: newElType.ElTypeNum = HTML_EL_Frames;
557: elFrames = TtaNewElement (doc, newElType);
558: XmlSetElemLineNumber (elFrames);
559: TtaInsertSibling (elFrames, child, TRUE, doc);
560: }
561: /* move the element as the last child of the Frames element */
562: TtaRemoveTree (child, doc);
563: if (lastFrame == NULL)
564: TtaInsertFirstChild (&child, elFrames, doc);
565: else
566: TtaInsertSibling (child, lastFrame, FALSE, doc);
567: lastFrame = child;
568: }
569: child = next;
570: }
571: break;
572:
573: case HTML_EL_Input: /* it's an INPUT without any TYPE attribute */
574: /* Create a child of type Text_Input */
575: elType.ElTypeNum = HTML_EL_Text_Input;
576: child = TtaNewTree (doc, elType, "");
577: XmlSetElemLineNumber (child);
578: TtaInsertFirstChild (&child, el, doc);
579: /* now, process it like a Text_Input element */
580:
581: case HTML_EL_Text_Input:
582: case HTML_EL_Password_Input:
583: case HTML_EL_File_Input:
584: /* get element Inserted_Text */
585: child = TtaGetFirstChild (el);
586: if (child != NULL)
587: {
588: attrType.AttrSSchema = docSSchema;
589: attrType.AttrTypeNum = HTML_ATTR_Value_;
590: attr = TtaGetAttribute (el, attrType);
591: if (attr != NULL)
592: {
593: /* copy the value of attribute "value" into the first text
594: leaf of element */
595: length = TtaGetTextAttributeLength (attr);
596: if (length > 0)
597: {
598: /* get the text leaf */
599: leaf = TtaGetFirstChild (child);
600: if (leaf != NULL)
601: {
602: childType = TtaGetElementType (leaf);
603: if (childType.ElTypeNum == HTML_EL_TEXT_UNIT)
604: {
605: /* copy attribute value into the text leaf */
606: text = TtaAllocString (length + 1);
607: TtaGiveTextAttributeValue (attr, text, &length);
608: TtaSetTextContent (leaf, text,
609: TtaGetDefaultLanguage (), doc);
610: TtaFreeMemory (text);
611: }
612: }
613: }
614: }
615: }
616: break;
617:
618: case HTML_EL_META:
1.15 cvs 619: ParseCharset (el, doc);
1.6 cvs 620: break;
621:
622: case HTML_EL_STYLE_: /* it's a STYLE element */
1.8 cvs 623: case HTML_EL_SCRIPT: /* it's a SCRIPT element */
1.6 cvs 624: case HTML_EL_Preformatted: /* it's a PRE */
625: /* if the last line of the Preformatted is empty, remove it */
626: leaf = XmlLastLeafInElement (el);
627: if (leaf != NULL)
628: {
629: elType = TtaGetElementType (leaf);
630: if (elType.ElTypeNum == HTML_EL_TEXT_UNIT)
631: /* the last leaf is a TEXT element */
632: {
633: length = TtaGetTextLength (leaf);
634: if (length > 0)
635: {
636: TtaGiveSubString (leaf, lastChar, length, 1);
637: if (lastChar[0] == EOL)
638: /* last character is new line, delete it */
639: {
640: if (length == 1)
641: /* empty TEXT element */
642: TtaDeleteTree (leaf, doc);
643: else
644: /* remove the last character */
645: TtaDeleteTextContent (leaf, length, 1, doc);
646: }
647: }
648: }
649: }
650: if (IsParsingCSS ())
651: {
652: text = GetStyleContents (el);
653: if (text)
654: {
655: ReadCSSRules (doc, NULL, text, FALSE);
656: TtaFreeMemory (text);
657: }
658: SetParsingCSS (FALSE);
659: }
660: /* and continue as if it were a Preformatted or a Script */
661: break;
662:
663: case HTML_EL_Text_Area: /* it's a Text_Area */
664: SetParsingTextArea (FALSE);
665: child = TtaGetFirstChild (el);
666: if (child == NULL)
667: /* it's an empty Text_Area */
668: /* insert a Inserted_Text element in the element */
669: {
670: newElType.ElTypeNum = HTML_EL_Inserted_Text;
671: child = TtaNewTree (doc, newElType, "");
672: TtaInsertFirstChild (&child, el, doc);
673: }
674: else
675: {
676: /* save the text into Default_Value attribute */
677: attrType.AttrSSchema = docSSchema;
678: attrType.AttrTypeNum = HTML_ATTR_Default_Value;
679: if (TtaGetAttribute (el, attrType) == NULL)
680: /* attribute Default_Value is missing */
681: {
682: attr = TtaNewAttribute (attrType);
683: TtaAttachAttribute (el, attr, doc);
684: desc = TtaGetFirstChild (child);
685: length = TtaGetTextLength (desc) + 1;
686: text = TtaAllocString (length);
687: TtaGiveTextContent (desc, text, &length, &lang);
688: TtaSetAttributeText (attr, text, el, doc);
689: TtaFreeMemory (text);
690: }
691: }
692: /* insert a Frame element */
693: newElType.ElTypeNum = HTML_EL_Frame;
694: constElem = TtaNewTree (doc, newElType, "");
695: TtaInsertSibling (constElem, child, FALSE, doc);
696: break;
697:
698: case HTML_EL_Radio_Input:
699: case HTML_EL_Checkbox_Input:
700: /* put an attribute Checked if it is missing */
701: attrType.AttrSSchema = docSSchema;
702: attrType.AttrTypeNum = HTML_ATTR_Checked;
703: if (TtaGetAttribute (el, attrType) == NULL)
704: /* attribute Checked is missing */
705: {
706: attr = TtaNewAttribute (attrType);
707: TtaAttachAttribute (el, attr, doc);
708: TtaSetAttributeValue (attr, HTML_ATTR_Checked_VAL_No_, el, doc);
709: }
710: break;
711:
712: case HTML_EL_Option_Menu:
713: /* Check that at least one option has a SELECTED attribute */
714: OnlyOneOptionSelected (el, doc, TRUE);
715: break;
716:
717: case HTML_EL_PICTURE_UNIT:
718: break;
719:
720: case HTML_EL_LINK:
721: CheckCSSLink (el, doc, docSSchema);
722: break;
723:
724: case HTML_EL_Data_cell:
725: case HTML_EL_Heading_cell:
726: /* insert a pseudo paragraph into empty cells */
727: child = TtaGetFirstChild (el);
728: if (child == NULL)
729: {
730: elType.ElTypeNum = HTML_EL_Pseudo_paragraph;
731: child = TtaNewTree (doc, elType, "");
732: if (child != NULL)
733: TtaInsertFirstChild (&child, el, doc);
734: }
735:
736: /* detect whether we're parsing a whole table or just a cell */
737: if (IsWithinTable ())
738: NewCell (el, doc, FALSE);
739: break;
740:
741: case HTML_EL_Table:
742: CheckTable (el, doc);
743: SubWithinTable ();
744: break;
745:
746: case HTML_EL_TITLE:
747: /* show the TITLE in the main window */
748: UpdateTitle (el, doc);
749: break;
750:
751: default:
752: break;
753: }
754: }
1.1 cvs 755:
756: /*----------------------------------------------------------------------
1.16 cvs 757: MapHTMLAttributeValue
1.2 cvs 758: Search in the Attribute Value Mapping Table the entry for the attribute
759: ThotAtt and its value AttrVal. Returns the corresponding Thot value.
1.1 cvs 760: ----------------------------------------------------------------------*/
761: #ifdef __STDC__
1.16 cvs 762: void MapHTMLAttributeValue (CHAR_T* AttrVal,
1.20 cvs 763: AttributeType attrType,
764: int* value)
1.1 cvs 765: #else
1.23 cvs 766: void MapHTMLAttributeValue (AttrVal, attrType, value)
1.11 cvs 767: CHAR_T* AttrVal;
768: AttributeType attrType;
769: int* value;
1.1 cvs 770: #endif
771: {
1.2 cvs 772: int i;
1.1 cvs 773:
1.2 cvs 774: *value = 0;
1.1 cvs 775: i = 0;
776:
1.2 cvs 777: while (XhtmlAttrValueMappingTable[i].ThotAttr != attrType.AttrTypeNum &&
778: XhtmlAttrValueMappingTable[i].ThotAttr != 0)
779: i++;
780:
781: if (XhtmlAttrValueMappingTable[i].ThotAttr == attrType.AttrTypeNum)
782: {
783: do
1.18 cvs 784: if (!ustrcmp (XhtmlAttrValueMappingTable[i].XMLattrValue, AttrVal))
1.2 cvs 785: *value = XhtmlAttrValueMappingTable[i].ThotAttrValue;
1.1 cvs 786: else
1.2 cvs 787: i++;
788: while (*value <= 0 &&
789: XhtmlAttrValueMappingTable[i].ThotAttr != 0);
1.1 cvs 790: }
791: }
Webmaster