source: gaycko/trunk/src/dom/dom.c @ 4730

Last change on this file since 4730 was 4730, checked in by Jean-Yves Lamoureux, 10 years ago
  • Don't crash on unknow/weird/hippy tags
File size: 3.2 KB
Line 
1#include <stdio.h>
2#include <string.h>
3#include "dom.h"
4#include "helpers/str.h"
5
6gDOM *gaycko_convert_dom(htmlDocPtr doc) {
7
8        gDOM *dom = malloc(sizeof(gDOM));
9        dom->root = NULL; 
10        htmlNodePtr root = xmlDocGetRootElement(doc);
11        gElement **r = NULL;
12        gElement *ret = NULL;
13
14        if(root != NULL)
15        {
16                ret = explore(r, root, 0, NULL);
17        }
18
19        dom->root = ret;
20        pretty_print(ret);
21
22        return dom;
23}
24
25
26gElement *add_element(htmlNodePtr node) {
27
28        gElement *e;
29        e = malloc(sizeof(gElement));
30        e->children_count  = 0;
31        e->children        = NULL;
32        e->attribute_count = 0;
33        e->attributes      = NULL;
34
35        if(!node->name) {
36                e->name = strdup("UNKNOW");
37                e->type = ELEM_UNKNOW;
38                return e;       
39        }
40       
41        e->name = (char*)strdup((const char*)node->name);
42        if(!strncmp(e->name, "html", 4)) {
43                e->type = ELEM_HTML;
44        }else if(!strncmp(e->name, "head", 4)) {
45                e->type = ELEM_HEAD;
46        }else if(!strncmp(e->name, "title", 5)) {
47                e->type = ELEM_TITLE;
48        }else if(!strncmp(e->name, "meta", 4)) {
49                e->type = ELEM_META;
50        }else if(!strncmp(e->name, "body", 4)) {
51                e->type = ELEM_BODY;
52        }else if(!strncmp(e->name, "h1", 2)) {
53                e->type = ELEM_H1;
54        }else if(!strncmp(e->name, "br", 2) || !strncmp(e->name, "br ", 3)) {
55                e->type = ELEM_BR;
56        }else if(!strncmp(e->name, "p", 1)) {
57                e->type = ELEM_P;
58        }else if(!strncmp(e->name, "img", 3)) {
59                e->type = ELEM_IMG;
60        }else if(!strncmp(e->name, "text", 4)) {
61                e->type = ELEM_TEXT;
62                e->text = (char*)strdup((const char*)xmlNodeGetContent(node));
63                strip_eol(e->text);
64                strip_spaces(e->text);
65        }else {
66                e->type = ELEM_UNKNOW;
67                printf("Unknow tag '%s'\n", e->name);   
68        }
69
70        if(node->properties) {
71                for(xmlAttrPtr attr = node->properties; attr != NULL; attr = attr->next) {
72                        e->attributes = realloc(e->attributes, sizeof(gAttribute));
73                        e->attributes[e->attribute_count].name = strdup(attr->name);
74                        e->attributes[e->attribute_count].value = strdup(attr->children->content);
75                }
76        }
77
78        return e;
79}
80
81
82gElement* explore(gElement **elem, htmlNodePtr element, unsigned int level, gElement *parent)
83{
84        unsigned int c = 0;
85        for(htmlNodePtr node = element; node != NULL; node = node->next)
86        {
87                gElement *child = add_element(node);
88                child->level = level;
89
90                if(elem) elem  = realloc(elem, sizeof(gElement*)*(c+1));
91                else elem = malloc(sizeof(gElement*));
92
93
94                elem[c] = child;
95
96                c++;
97
98                if(node->type == XML_ELEMENT_NODE)
99                {
100                        if(node->children != NULL) {
101                                explore(child->children,
102                                                node->children,
103                                                level+1,
104                                                child);
105                        } else {
106                                free(child->children);
107                                child->children = NULL;
108                        }
109                }         
110                if(parent) {
111                        parent->children = realloc(parent->children, sizeof(gElement*)*(parent->children_count+1));
112                        parent->children[parent->children_count] = child;
113                        parent->children_count++;
114                }
115        }
116        return *elem;
117}
118
119
120#define LEVEL {unsigned int foo=0; for(foo=0; foo<elem->level; foo++) printf("    ");}
121
122void pretty_print(gElement *elem) {
123        if(!elem) {
124                printf("elem is %p\n", elem);
125                return;
126        }
127
128        if(elem->type == ELEM_TEXT) {
129                LEVEL printf("%s\n", elem->text);
130        } else {
131                LEVEL printf("<%s>\n", elem->name);
132        }
133
134        unsigned int i;
135        for(i=0; i < elem->children_count; i++) {
136                pretty_print(elem->children[i]);
137        }
138
139        if(elem->type == ELEM_TEXT) {
140
141        } else {
142                LEVEL printf("</%s>\n", elem->name);
143        }
144}
145
Note: See TracBrowser for help on using the repository browser.