Committing FS#11345 by JdGordon. Theme editor parser now includes full tag informati...
[kugel-rb.git] / utils / themeeditor / parsetreenode.cpp
bloba93295f35771a33bb4209599fb7f207f21e2c2b3
1 /***************************************************************************
2 * __________ __ ___.
3 * Open \______ \ ____ ____ | | _\_ |__ _______ ___
4 * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
5 * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
6 * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
7 * \/ \/ \/ \/ \/
8 * $Id$
10 * Copyright (C) 2010 Robert Bieber
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.
17 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
18 * KIND, either express or implied.
20 ****************************************************************************/
22 extern "C"
24 #include "symbols.h"
25 #include "tag_table.h"
28 #include "parsetreenode.h"
30 /* Root element constructor */
31 ParseTreeNode::ParseTreeNode(struct skin_element* data)
32 : parent(0), element(0), param(0), children()
34 while(data)
36 children.append(new ParseTreeNode(data, this));
37 data = data->next;
41 /* Normal element constructor */
42 ParseTreeNode::ParseTreeNode(struct skin_element* data, ParseTreeNode* parent)
43 : parent(parent), element(data), param(0), children()
45 switch(element->type)
48 case TAG:
49 for(int i = 0; i < element->params_count; i++)
51 if(element->params[i].type == skin_tag_parameter::CODE)
52 children.append(new ParseTreeNode(element->params[i].data.code,
53 this));
54 else
55 children.append(new ParseTreeNode(&element->params[i], this));
57 break;
59 /* CONDITIONAL and SUBLINES fall through to the same code */
60 case CONDITIONAL:
61 case SUBLINES:
62 for(int i = 0; i < element->children_count; i++)
64 children.append(new ParseTreeNode(data->children[i], this));
66 break;
68 case VIEWPORT:
69 case LINE:
70 for(struct skin_element* current = data->children[0]; current;
71 current = current->next)
73 children.append(new ParseTreeNode(current, this));
75 break;
77 default:
78 break;
82 /* Parameter constructor */
83 ParseTreeNode::ParseTreeNode(skin_tag_parameter *data, ParseTreeNode *parent)
84 : parent(parent), element(0), param(data), children()
89 QString ParseTreeNode::genCode() const
91 QString buffer = "";
93 if(element)
95 switch(element->type)
98 case VIEWPORT:
99 buffer.append(children[0]->genCode());
101 case LINE:
102 for(int i = 0; i < children.count(); i++)
105 Adding a % in case of tag, because the tag rendering code
106 doesn't insert its own
108 if(children[i]->element->type == TAG)
109 buffer.append(TAGSYM);
110 buffer.append(children[i]->genCode());
112 break;
114 case SUBLINES:
115 for(int i = 0; i < children.count(); i++)
117 buffer.append(children[i]->genCode());
118 if(i != children.count() - 1)
119 buffer.append(MULTILINESYM);
121 break;
123 case CONDITIONAL:
124 /* Inserts a %?, the tag renderer doesn't deal with the TAGSYM */
125 buffer.append(TAGSYM);
126 buffer.append(CONDITIONSYM);
127 buffer.append(children[0]->genCode());
129 /* Inserting the sublines */
130 buffer.append(ENUMLISTOPENSYM);
131 for(int i = 1; i < children.count(); i++)
133 buffer.append(children[i]->genCode());
134 if(i != children.count() - 1)
135 buffer.append(ENUMLISTSEPERATESYM);
137 buffer.append(ENUMLISTCLOSESYM);
138 break;
140 case TAG:
141 /* When generating code, we DO NOT insert the leading TAGSYM, leave
142 * the calling functions to handle that
144 buffer.append(element->tag->name);
146 if(element->params_count > 0)
148 /* Rendering parameters if there are any */
149 buffer.append(ARGLISTOPENSYM);
150 for(int i = 0; i < children.count(); i++)
152 buffer.append(children[i]->genCode());
153 if(i != children.count() - 1)
154 buffer.append(ARGLISTSEPERATESYM);
156 buffer.append(ARGLISTCLOSESYM);
158 break;
160 case NEWLINE:
161 buffer.append('\n');
162 break;
164 case TEXT:
165 buffer.append(element->text);
166 break;
168 case COMMENT:
169 buffer.append(COMMENTSYM);
170 buffer.append(element->text);
171 break;
174 else if(param)
176 switch(param->type)
178 case skin_tag_parameter::STRING:
179 buffer.append(param->data.text);
180 break;
182 case skin_tag_parameter::NUMERIC:
183 buffer.append(QString::number(param->data.numeric, 10));
184 break;
186 case skin_tag_parameter::DEFAULT:
187 buffer.append(DEFAULTSYM);
188 break;
190 case skin_tag_parameter::CODE:
191 buffer.append(QObject::tr("This doesn't belong here"));
192 break;
196 else
198 for(int i = 0; i < children.count(); i++)
199 buffer.append(children[i]->genCode());
202 return buffer;
205 ParseTreeNode* ParseTreeNode::child(int row)
207 if(row < 0 || row >= children.count())
208 return 0;
210 return children[row];
213 int ParseTreeNode::numChildren() const
215 return children.count();
219 QVariant ParseTreeNode::data(int column) const
221 switch(column)
223 /* Column 0 is the element type */
224 case 0:
225 if(element)
227 switch(element->type)
229 case VIEWPORT:
230 return QObject::tr("Viewport");
232 case LINE:
233 return QObject::tr("Logical Line");
235 case SUBLINES:
236 return QObject::tr("Alternator");
238 case COMMENT:
239 return QObject::tr("Comment");
241 case CONDITIONAL:
242 return QObject::tr("Conditional Tag");
244 case TAG:
245 return QObject::tr("Tag");
247 case NEWLINE:
248 return QObject::tr("Newline");
250 case TEXT:
251 return QObject::tr("Plaintext");
254 else if(param)
256 switch(param->type)
258 case skin_tag_parameter::STRING:
259 return QObject::tr("String");
261 case skin_tag_parameter::NUMERIC:
262 return QObject::tr("Number");
264 case skin_tag_parameter::DEFAULT:
265 return QObject::tr("Default Argument");
267 case skin_tag_parameter::CODE:
268 return QObject::tr("This doesn't belong here");
271 else
273 return QObject::tr("Root");
276 break;
278 /* Column 1 is the value */
279 case 1:
280 if(element)
282 switch(element->type)
284 case VIEWPORT:
285 case LINE:
286 case SUBLINES:
287 case CONDITIONAL:
288 return QString();
290 case NEWLINE:
291 return QObject::tr("\\n");
293 case TEXT:
294 case COMMENT:
295 return QString(element->text);
297 case TAG:
298 return QString(element->tag->name);
301 else if(param)
303 switch(param->type)
305 case skin_tag_parameter::DEFAULT:
306 return QObject::tr("-");
308 case skin_tag_parameter::STRING:
309 return QString(param->data.text);
311 case skin_tag_parameter::NUMERIC:
312 return QString::number(param->data.numeric, 10);
314 case skin_tag_parameter::CODE:
315 return QObject::tr("Seriously, something's wrong here");
318 else
320 return QString();
322 break;
324 /* Column 2 is the line number */
325 case 2:
326 if(element)
327 return QString::number(element->line, 10);
328 else
329 return QString();
330 break;
333 return QVariant();
337 int ParseTreeNode::getRow() const
339 if(!parent)
340 return -1;
342 return parent->children.indexOf(const_cast<ParseTreeNode*>(this));
345 ParseTreeNode* ParseTreeNode::getParent() const
347 return parent;
350 ParseTreeNode::~ParseTreeNode()
352 for(int i = 0; i < children.count(); i++)
353 delete children[i];