diff options
author | Robert Bieber <robby@bieberphoto.com> | 2010-05-29 00:04:04 +0000 |
---|---|---|
committer | Robert Bieber <robby@bieberphoto.com> | 2010-05-29 00:04:04 +0000 |
commit | 6980c1e9988a7c959876ad77b760e042272a9ec2 (patch) | |
tree | 3b9ca757bfe83f8bef1ac9bcf544b1d47b542e8e /utils/themeeditor | |
parent | 1dcc21d8466a6279ff79c8b9ee02bc5cfc7f5167 (diff) | |
download | rockbox-6980c1e9988a7c959876ad77b760e042272a9ec2.tar.gz rockbox-6980c1e9988a7c959876ad77b760e042272a9ec2.zip |
Theme Editor: Got code generation tentatively working along with a solid C++ tree structure for WPS parse trees
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@26367 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'utils/themeeditor')
-rw-r--r-- | utils/themeeditor/main.cpp | 15 | ||||
-rw-r--r-- | utils/themeeditor/parsetreemodel.cpp | 11 | ||||
-rw-r--r-- | utils/themeeditor/parsetreemodel.h | 6 | ||||
-rw-r--r-- | utils/themeeditor/parsetreenode.cpp | 228 | ||||
-rw-r--r-- | utils/themeeditor/parsetreenode.h | 40 | ||||
-rw-r--r-- | utils/themeeditor/skin_parser.c | 26 | ||||
-rw-r--r-- | utils/themeeditor/skin_parser.h | 10 |
7 files changed, 245 insertions, 91 deletions
diff --git a/utils/themeeditor/main.cpp b/utils/themeeditor/main.cpp index 49e870c369..27ce2da23f 100644 --- a/utils/themeeditor/main.cpp +++ b/utils/themeeditor/main.cpp | |||
@@ -27,6 +27,7 @@ extern "C" | |||
27 | 27 | ||
28 | #include <cstdlib> | 28 | #include <cstdlib> |
29 | #include <cstdio> | 29 | #include <cstdio> |
30 | #include <iostream> | ||
30 | 31 | ||
31 | #include <QtGui/QApplication> | 32 | #include <QtGui/QApplication> |
32 | #include <QTreeView> | 33 | #include <QTreeView> |
@@ -36,15 +37,21 @@ extern "C" | |||
36 | int main(int argc, char* argv[]) | 37 | int main(int argc, char* argv[]) |
37 | { | 38 | { |
38 | 39 | ||
39 | char doc[] = "%Vd(U);Hey\n%?bl(test,3,5,2,1)<param2|param3>"; | 40 | char doc[] = "#Comment\n%Vd(U);Hey\n%?bl(test,3,5,2,1)<param2|param3>"; |
40 | 41 | ||
41 | struct skin_element* test = skin_parse(doc); | 42 | struct skin_element* test = skin_parse(doc); |
42 | 43 | ||
43 | skin_debug_tree(test); | 44 | ParseTreeNode tree(test); |
45 | std::cout << "----" << std::endl; | ||
46 | if(std::string(doc) == tree.genCode().toStdString()) | ||
47 | std::cout << "Code in/out matches" << std::endl; | ||
48 | else | ||
49 | std::cout << "Match error" << std::endl; | ||
44 | 50 | ||
45 | skin_free_tree(test); | ||
46 | 51 | ||
52 | skin_free_tree(test); | ||
47 | 53 | ||
54 | /* | ||
48 | QApplication app(argc, argv); | 55 | QApplication app(argc, argv); |
49 | 56 | ||
50 | QTreeView tree; | 57 | QTreeView tree; |
@@ -53,7 +60,7 @@ int main(int argc, char* argv[]) | |||
53 | tree.show(); | 60 | tree.show(); |
54 | 61 | ||
55 | return app.exec(); | 62 | return app.exec(); |
56 | 63 | */ | |
57 | return 0; | 64 | return 0; |
58 | } | 65 | } |
59 | 66 | ||
diff --git a/utils/themeeditor/parsetreemodel.cpp b/utils/themeeditor/parsetreemodel.cpp index aa5fb5cdb8..c99f166c41 100644 --- a/utils/themeeditor/parsetreemodel.cpp +++ b/utils/themeeditor/parsetreemodel.cpp | |||
@@ -26,8 +26,8 @@ | |||
26 | ParseTreeModel::ParseTreeModel(char* wps, QObject* parent): | 26 | ParseTreeModel::ParseTreeModel(char* wps, QObject* parent): |
27 | QAbstractItemModel(parent) | 27 | QAbstractItemModel(parent) |
28 | { | 28 | { |
29 | this->wps = skin_parse(wps); | 29 | this->tree = skin_parse(wps); |
30 | this->root = new ParseTreeNode(this->wps, 0, true); | 30 | this->root = new ParseTreeNode(tree, 0); |
31 | } | 31 | } |
32 | 32 | ||
33 | 33 | ||
@@ -36,6 +36,12 @@ ParseTreeModel::~ParseTreeModel() | |||
36 | delete root; | 36 | delete root; |
37 | } | 37 | } |
38 | 38 | ||
39 | QString genCode() | ||
40 | { | ||
41 | return QString(); | ||
42 | } | ||
43 | |||
44 | /* | ||
39 | QModelIndex ParseTreeModel::index(int row, int column, | 45 | QModelIndex ParseTreeModel::index(int row, int column, |
40 | const QModelIndex& parent) const | 46 | const QModelIndex& parent) const |
41 | { | 47 | { |
@@ -98,3 +104,4 @@ QVariant ParseTreeModel::data(const QModelIndex &index, int role) const | |||
98 | ParseTreeNode* item = static_cast<ParseTreeNode*>(index.internalPointer()); | 104 | ParseTreeNode* item = static_cast<ParseTreeNode*>(index.internalPointer()); |
99 | return item->data(index.column()); | 105 | return item->data(index.column()); |
100 | } | 106 | } |
107 | */ | ||
diff --git a/utils/themeeditor/parsetreemodel.h b/utils/themeeditor/parsetreemodel.h index 78484eb5f4..64365ed038 100644 --- a/utils/themeeditor/parsetreemodel.h +++ b/utils/themeeditor/parsetreemodel.h | |||
@@ -43,15 +43,19 @@ public: | |||
43 | ParseTreeModel(char* wps, QObject* parent = 0); | 43 | ParseTreeModel(char* wps, QObject* parent = 0); |
44 | virtual ~ParseTreeModel(); | 44 | virtual ~ParseTreeModel(); |
45 | 45 | ||
46 | QString genCode(); | ||
47 | |||
48 | /* | ||
46 | QModelIndex index(int row, int column, const QModelIndex& parent) const; | 49 | QModelIndex index(int row, int column, const QModelIndex& parent) const; |
47 | QModelIndex parent(const QModelIndex &child) const; | 50 | QModelIndex parent(const QModelIndex &child) const; |
48 | int rowCount(const QModelIndex &parent) const; | 51 | int rowCount(const QModelIndex &parent) const; |
49 | int columnCount(const QModelIndex &parent) const; | 52 | int columnCount(const QModelIndex &parent) const; |
50 | QVariant data(const QModelIndex &index, int role) const; | 53 | QVariant data(const QModelIndex &index, int role) const; |
54 | */ | ||
51 | 55 | ||
52 | private: | 56 | private: |
53 | ParseTreeNode* root; | 57 | ParseTreeNode* root; |
54 | struct skin_element* wps; | 58 | struct skin_element* tree; |
55 | }; | 59 | }; |
56 | 60 | ||
57 | 61 | ||
diff --git a/utils/themeeditor/parsetreenode.cpp b/utils/themeeditor/parsetreenode.cpp index 77ec897dd7..ccfac615be 100644 --- a/utils/themeeditor/parsetreenode.cpp +++ b/utils/themeeditor/parsetreenode.cpp | |||
@@ -1,74 +1,200 @@ | |||
1 | #include "parsetreenode.h" | 1 | /*************************************************************************** |
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2010 Robert Bieber | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
2 | 21 | ||
3 | ParseTreeNode::ParseTreeNode(struct skin_element* data, ParseTreeNode* parent, | 22 | extern "C" |
4 | bool tree) | ||
5 | { | 23 | { |
24 | #include "symbols.h" | ||
25 | } | ||
6 | 26 | ||
7 | if(tree) | 27 | #include "parsetreenode.h" |
8 | { | 28 | |
9 | while(data) | 29 | /* Root element constructor */ |
10 | { | 30 | ParseTreeNode::ParseTreeNode(struct skin_element* data) |
11 | appendChild(new ParseTreeNode(data, this, false)); | 31 | : parent(0), element(0), param(0), children() |
12 | data = data->next; | 32 | { |
13 | } | 33 | while(data) |
14 | parentLink = 0; | ||
15 | } | ||
16 | else | ||
17 | { | 34 | { |
18 | element = data; | 35 | children.append(new ParseTreeNode(data, this)); |
19 | parentLink = parent; | 36 | data = data->next; |
20 | } | 37 | } |
21 | |||
22 | } | 38 | } |
23 | 39 | ||
24 | ParseTreeNode::ParseTreeNode(struct skin_tag_parameter* param, | 40 | /* Normal element constructor */ |
25 | ParseTreeNode* parent) | 41 | ParseTreeNode::ParseTreeNode(struct skin_element* data, ParseTreeNode* parent) |
26 | :parentLink(parent), element(0), param(param) | 42 | : parent(parent), element(data), param(0), children() |
27 | { | 43 | { |
44 | switch(element->type) | ||
45 | { | ||
28 | 46 | ||
29 | } | 47 | case TAG: |
48 | for(int i = 0; i < element->params_count; i++) | ||
49 | { | ||
50 | if(element->params[i].type == skin_tag_parameter::CODE) | ||
51 | children.append(new ParseTreeNode(element->params[i].data.code, | ||
52 | this)); | ||
53 | else | ||
54 | children.append(new ParseTreeNode(&element->params[i], this)); | ||
55 | } | ||
56 | break; | ||
30 | 57 | ||
58 | /* CONDITIONAL and SUBLINES fall through to the same code */ | ||
59 | case CONDITIONAL: | ||
60 | case SUBLINES: | ||
61 | for(int i = 0; i < element->children_count; i++) | ||
62 | { | ||
63 | children.append(new ParseTreeNode(data->children[i], this)); | ||
64 | } | ||
65 | break; | ||
31 | 66 | ||
32 | ParseTreeNode::~ParseTreeNode() | 67 | case LINE: |
33 | { | 68 | for(struct skin_element* current = data->children[0]; current; |
34 | qDeleteAll(children); | 69 | current = current->next) |
35 | } | 70 | { |
71 | children.append(new ParseTreeNode(current, this)); | ||
72 | } | ||
73 | break; | ||
36 | 74 | ||
37 | void ParseTreeNode::appendChild(ParseTreeNode* child) | 75 | default: |
38 | { | 76 | break; |
39 | children.append(child); | 77 | } |
40 | } | 78 | } |
41 | 79 | ||
42 | ParseTreeNode* ParseTreeNode::child(int row) | 80 | /* Parameter constructor */ |
81 | ParseTreeNode::ParseTreeNode(skin_tag_parameter *data, ParseTreeNode *parent) | ||
82 | : parent(parent), element(0), param(data), children() | ||
43 | { | 83 | { |
44 | return children[row]; | ||
45 | } | ||
46 | 84 | ||
47 | int ParseTreeNode::childCount() const | ||
48 | { | ||
49 | return children.count(); | ||
50 | } | 85 | } |
51 | 86 | ||
52 | int ParseTreeNode::columnCount() const | 87 | QString ParseTreeNode::genCode() const |
53 | { | 88 | { |
54 | return 2; | 89 | QString buffer = ""; |
55 | } | ||
56 | 90 | ||
57 | QVariant ParseTreeNode::data(int column) const | 91 | if(element) |
58 | { | 92 | { |
59 | if(column == 0) | 93 | switch(element->type) |
60 | return element->type; | 94 | { |
95 | case LINE: | ||
96 | for(int i = 0; i < children.count(); i++) | ||
97 | { | ||
98 | /* | ||
99 | Adding a % in case of tag, because the tag rendering code | ||
100 | doesn't insert its own | ||
101 | */ | ||
102 | if(children[i]->element->type == TAG) | ||
103 | buffer.append(TAGSYM); | ||
104 | buffer.append(children[i]->genCode()); | ||
105 | } | ||
106 | break; | ||
107 | |||
108 | case SUBLINES: | ||
109 | for(int i = 0; i < children.count(); i++) | ||
110 | { | ||
111 | buffer.append(children[i]->genCode()); | ||
112 | if(i != children.count() - 1) | ||
113 | buffer.append(MULTILINESYM); | ||
114 | } | ||
115 | break; | ||
116 | |||
117 | case CONDITIONAL: | ||
118 | /* Inserts a %?, the tag renderer doesn't deal with the TAGSYM */ | ||
119 | buffer.append(TAGSYM); | ||
120 | buffer.append(CONDITIONSYM); | ||
121 | buffer.append(children[0]->genCode()); | ||
122 | |||
123 | /* Inserting the sublines */ | ||
124 | buffer.append(ENUMLISTOPENSYM); | ||
125 | for(int i = 1; i < children.count(); i++) | ||
126 | { | ||
127 | buffer.append(children[i]->genCode()); | ||
128 | if(i != children.count() - 1) | ||
129 | buffer.append(ENUMLISTSEPERATESYM); | ||
130 | } | ||
131 | buffer.append(ENUMLISTCLOSESYM); | ||
132 | break; | ||
133 | |||
134 | case TAG: | ||
135 | /* When generating code, we DO NOT insert the leading TAGSYM, leave | ||
136 | * the calling functions to handle that | ||
137 | */ | ||
138 | buffer.append(element->name); | ||
139 | |||
140 | if(element->params_count > 0) | ||
141 | { | ||
142 | /* Rendering parameters if there are any */ | ||
143 | buffer.append(ARGLISTOPENSYM); | ||
144 | for(int i = 0; i < children.count(); i++) | ||
145 | { | ||
146 | buffer.append(children[i]->genCode()); | ||
147 | if(i != children.count() - 1) | ||
148 | buffer.append(ARGLISTSEPERATESYM); | ||
149 | } | ||
150 | buffer.append(ARGLISTCLOSESYM); | ||
151 | } | ||
152 | break; | ||
153 | |||
154 | case NEWLINE: | ||
155 | buffer.append('\n'); | ||
156 | break; | ||
157 | |||
158 | case TEXT: | ||
159 | buffer.append(element->text); | ||
160 | break; | ||
161 | |||
162 | case COMMENT: | ||
163 | buffer.append(COMMENTSYM); | ||
164 | buffer.append(element->text); | ||
165 | break; | ||
166 | } | ||
167 | } | ||
168 | else if(param) | ||
169 | { | ||
170 | switch(param->type) | ||
171 | { | ||
172 | case skin_tag_parameter::STRING: | ||
173 | buffer.append(param->data.text); | ||
174 | break; | ||
175 | |||
176 | case skin_tag_parameter::NUMERIC: | ||
177 | buffer.append(QString::number(param->data.numeric, 10)); | ||
178 | break; | ||
179 | |||
180 | case skin_tag_parameter::DEFAULT: | ||
181 | buffer.append(DEFAULTSYM); | ||
182 | break; | ||
183 | |||
184 | } | ||
185 | } | ||
61 | else | 186 | else |
62 | return element->line; | 187 | { |
63 | } | 188 | for(int i = 0; i < children.count(); i++) |
64 | int ParseTreeNode::row() const | 189 | buffer.append(children[i]->genCode()); |
65 | { | 190 | } |
66 | if(parentLink) | ||
67 | return parentLink->children.indexOf(const_cast<ParseTreeNode*>(this)); | ||
68 | return 0; | ||
69 | } | ||
70 | 191 | ||
71 | ParseTreeNode* ParseTreeNode::parent() | 192 | return buffer; |
72 | { | ||
73 | return parentLink; | ||
74 | } | 193 | } |
194 | /* | ||
195 | ParseTreeNode* child(int row); | ||
196 | int numChildren() const; | ||
197 | QVariant data(int column) const; | ||
198 | int getRow() const; | ||
199 | ParseTreeNode* getParent(); | ||
200 | */ | ||
diff --git a/utils/themeeditor/parsetreenode.h b/utils/themeeditor/parsetreenode.h index c3372e0a20..4d8c4ebc14 100644 --- a/utils/themeeditor/parsetreenode.h +++ b/utils/themeeditor/parsetreenode.h | |||
@@ -1,3 +1,24 @@ | |||
1 | /*************************************************************************** | ||
2 | * __________ __ ___. | ||
3 | * Open \______ \ ____ ____ | | _\_ |__ _______ ___ | ||
4 | * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / | ||
5 | * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < | ||
6 | * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ | ||
7 | * \/ \/ \/ \/ \/ | ||
8 | * $Id$ | ||
9 | * | ||
10 | * Copyright (C) 2010 Robert Bieber | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 | ||
15 | * of the License, or (at your option) any later version. | ||
16 | * | ||
17 | * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY | ||
18 | * KIND, either express or implied. | ||
19 | * | ||
20 | ****************************************************************************/ | ||
21 | |||
1 | #ifndef PARSETREENODE_H | 22 | #ifndef PARSETREENODE_H |
2 | #define PARSETREENODE_H | 23 | #define PARSETREENODE_H |
3 | 24 | ||
@@ -13,24 +34,23 @@ extern "C" | |||
13 | class ParseTreeNode | 34 | class ParseTreeNode |
14 | { | 35 | { |
15 | public: | 36 | public: |
16 | ParseTreeNode(struct skin_element* data, ParseTreeNode* parent, bool tree); | 37 | ParseTreeNode(struct skin_element* data); |
17 | ParseTreeNode(struct skin_tag_parameter* param, ParseTreeNode* parent); | 38 | ParseTreeNode(struct skin_element* data, ParseTreeNode* parent); |
18 | virtual ~ParseTreeNode(); | 39 | ParseTreeNode(struct skin_tag_parameter* data, ParseTreeNode* parent); |
19 | 40 | ||
20 | void appendChild(ParseTreeNode* child); | 41 | QString genCode() const; |
21 | 42 | ||
22 | ParseTreeNode* child(int row); | 43 | ParseTreeNode* child(int row); |
23 | int childCount() const; | 44 | int numChildren() const; |
24 | int columnCount() const; | ||
25 | QVariant data(int column) const; | 45 | QVariant data(int column) const; |
26 | int row() const; | 46 | int getRow() const; |
27 | ParseTreeNode* parent(); | 47 | ParseTreeNode* getParent(); |
28 | 48 | ||
29 | private: | 49 | private: |
30 | ParseTreeNode* parentLink; | 50 | ParseTreeNode* parent; |
31 | QList<ParseTreeNode*> children; | ||
32 | struct skin_element* element; | 51 | struct skin_element* element; |
33 | struct skin_tag_parameter* param; | 52 | struct skin_tag_parameter* param; |
53 | QList<ParseTreeNode*> children; | ||
34 | 54 | ||
35 | }; | 55 | }; |
36 | 56 | ||
diff --git a/utils/themeeditor/skin_parser.c b/utils/themeeditor/skin_parser.c index a6c5ea41a2..2f68cdf1c8 100644 --- a/utils/themeeditor/skin_parser.c +++ b/utils/themeeditor/skin_parser.c | |||
@@ -103,7 +103,14 @@ struct skin_element* skin_parse(char* document) | |||
103 | else | 103 | else |
104 | to_write = &(last->next); | 104 | to_write = &(last->next); |
105 | 105 | ||
106 | if(sublines) | 106 | if(*cursor == '\n') |
107 | { | ||
108 | *to_write = skin_alloc_element(); | ||
109 | skin_parse_newline(*to_write, &cursor); | ||
110 | if(!last) | ||
111 | return NULL; | ||
112 | } | ||
113 | else if(sublines) | ||
107 | { | 114 | { |
108 | *to_write = skin_parse_sublines(&cursor); | 115 | *to_write = skin_parse_sublines(&cursor); |
109 | last = *to_write; | 116 | last = *to_write; |
@@ -202,23 +209,6 @@ struct skin_element* skin_parse_line_optional(char** document, int conditional) | |||
202 | } | 209 | } |
203 | } | 210 | } |
204 | 211 | ||
205 | if(*cursor == '\n') | ||
206 | { | ||
207 | /* Allocating memory if necessary */ | ||
208 | if(root) | ||
209 | { | ||
210 | current->next = skin_alloc_element(); | ||
211 | current = current->next; | ||
212 | } | ||
213 | else | ||
214 | { | ||
215 | current = skin_alloc_element(); | ||
216 | root = current; | ||
217 | } | ||
218 | if(!skin_parse_newline(current, &cursor)) | ||
219 | return NULL; | ||
220 | } | ||
221 | |||
222 | /* Moving up the calling function's pointer */ | 212 | /* Moving up the calling function's pointer */ |
223 | *document = cursor; | 213 | *document = cursor; |
224 | 214 | ||
diff --git a/utils/themeeditor/skin_parser.h b/utils/themeeditor/skin_parser.h index 7de726bbfc..7b3ab13ad0 100644 --- a/utils/themeeditor/skin_parser.h +++ b/utils/themeeditor/skin_parser.h | |||
@@ -36,13 +36,13 @@ extern char skin_parse_tree[]; | |||
36 | /* Possible types of element in a WPS file */ | 36 | /* Possible types of element in a WPS file */ |
37 | enum skin_element_type | 37 | enum skin_element_type |
38 | { | 38 | { |
39 | TEXT, | 39 | LINE, |
40 | SUBLINES, | ||
41 | CONDITIONAL, | ||
42 | TAG, | ||
40 | NEWLINE, | 43 | NEWLINE, |
44 | TEXT, | ||
41 | COMMENT, | 45 | COMMENT, |
42 | TAG, | ||
43 | CONDITIONAL, | ||
44 | SUBLINES, | ||
45 | LINE | ||
46 | }; | 46 | }; |
47 | 47 | ||
48 | enum skin_errorcode | 48 | enum skin_errorcode |