summaryrefslogtreecommitdiff
path: root/utils/themeeditor/models/parsetreenode.cpp
diff options
context:
space:
mode:
authorRobert Bieber <robby@bieberphoto.com>2010-06-17 05:37:01 +0000
committerRobert Bieber <robby@bieberphoto.com>2010-06-17 05:37:01 +0000
commitca564287ee3f48945d45c7d92be7a83452f53745 (patch)
treed6e502bb604f925240a742b3bac2c813a98c447b /utils/themeeditor/models/parsetreenode.cpp
parentba07b2055c7eb8f2add96f55cb52b40b9ccb3d63 (diff)
downloadrockbox-ca564287ee3f48945d45c7d92be7a83452f53745.zip
rockbox-ca564287ee3f48945d45c7d92be7a83452f53745.tar.gz
rockbox-ca564287ee3f48945d45c7d92be7a83452f53745.tar.bz2
rockbox-ca564287ee3f48945d45c7d92be7a83452f53745.tar.xz
Theme Editor: Moved source files into subdirectories
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@26876 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'utils/themeeditor/models/parsetreenode.cpp')
-rw-r--r--utils/themeeditor/models/parsetreenode.cpp474
1 files changed, 474 insertions, 0 deletions
diff --git a/utils/themeeditor/models/parsetreenode.cpp b/utils/themeeditor/models/parsetreenode.cpp
new file mode 100644
index 0000000..397031a
--- /dev/null
+++ b/utils/themeeditor/models/parsetreenode.cpp
@@ -0,0 +1,474 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2010 Robert Bieber
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#include "symbols.h"
+#include "tag_table.h"
+
+#include "parsetreenode.h"
+#include "parsetreemodel.h"
+
+int ParseTreeNode::openConditionals = 0;
+
+/* Root element constructor */
+ParseTreeNode::ParseTreeNode(struct skin_element* data)
+ : parent(0), element(0), param(0), children()
+{
+ while(data)
+ {
+ children.append(new ParseTreeNode(data, this));
+ data = data->next;
+ }
+}
+
+/* Normal element constructor */
+ParseTreeNode::ParseTreeNode(struct skin_element* data, ParseTreeNode* parent)
+ : parent(parent), element(data), param(0), children()
+{
+ switch(element->type)
+ {
+
+ case TAG:
+ for(int i = 0; i < element->params_count; i++)
+ {
+ if(element->params[i].type == skin_tag_parameter::CODE)
+ children.append(new ParseTreeNode(element->params[i].data.code,
+ this));
+ else
+ children.append(new ParseTreeNode(&element->params[i], this));
+ }
+ break;
+
+ case CONDITIONAL:
+ for(int i = 0; i < element->params_count; i++)
+ children.append(new ParseTreeNode(&data->params[i], this));
+ for(int i = 0; i < element->children_count; i++)
+ children.append(new ParseTreeNode(data->children[i], this));
+ break;
+
+ case SUBLINES:
+ for(int i = 0; i < element->children_count; i++)
+ {
+ children.append(new ParseTreeNode(data->children[i], this));
+ }
+ break;
+
+case VIEWPORT:
+ for(int i = 0; i < element->params_count; i++)
+ children.append(new ParseTreeNode(&data->params[i], this));
+ /* Deliberate fall-through here */
+
+ case LINE:
+ for(int i = 0; i < data->children_count; i++)
+ {
+ for(struct skin_element* current = data->children[i]; current;
+ current = current->next)
+ {
+ children.append(new ParseTreeNode(current, this));
+ }
+ }
+ break;
+
+ default:
+ break;
+ }
+}
+
+/* Parameter constructor */
+ParseTreeNode::ParseTreeNode(skin_tag_parameter *data, ParseTreeNode *parent)
+ : parent(parent), element(0), param(data), children()
+{
+
+}
+
+QString ParseTreeNode::genCode() const
+{
+ QString buffer = "";
+
+ if(element)
+ {
+ switch(element->type)
+ {
+ case UNKNOWN:
+ break;
+ case VIEWPORT:
+ /* Generating the Viewport tag, if necessary */
+ if(element->tag)
+ {
+ buffer.append(TAGSYM);
+ buffer.append(element->tag->name);
+ buffer.append(ARGLISTOPENSYM);
+ for(int i = 0; i < element->params_count; i++)
+ {
+ buffer.append(children[i]->genCode());
+ if(i != element->params_count - 1)
+ buffer.append(ARGLISTSEPERATESYM);
+ }
+ buffer.append(ARGLISTCLOSESYM);
+ buffer.append('\n');
+ }
+
+ for(int i = element->params_count; i < children.count(); i++)
+ buffer.append(children[i]->genCode());
+ break;
+
+ case LINE:
+ for(int i = 0; i < children.count(); i++)
+ {
+ buffer.append(children[i]->genCode());
+ }
+ if(openConditionals == 0
+ && !(parent && parent->element->type == SUBLINES))
+ {
+ buffer.append('\n');
+ }
+ break;
+
+ case SUBLINES:
+ for(int i = 0; i < children.count(); i++)
+ {
+ buffer.append(children[i]->genCode());
+ if(i != children.count() - 1)
+ buffer.append(MULTILINESYM);
+ }
+ if(openConditionals == 0)
+ buffer.append('\n');
+ break;
+
+ case CONDITIONAL:
+ openConditionals++;
+
+ /* Inserting the tag part */
+ buffer.append(TAGSYM);
+ buffer.append(CONDITIONSYM);
+ buffer.append(element->tag->name);
+ if(element->params_count > 0)
+ {
+ buffer.append(ARGLISTOPENSYM);
+ for(int i = 0; i < element->params_count; i++)
+ {
+ buffer.append(children[i]->genCode());
+ if( i != element->params_count - 1)
+ buffer.append(ARGLISTSEPERATESYM);
+ buffer.append(ARGLISTCLOSESYM);
+ }
+ }
+
+ /* Inserting the sublines */
+ buffer.append(ENUMLISTOPENSYM);
+ for(int i = element->params_count; i < children.count(); i++)
+ {
+ buffer.append(children[i]->genCode());
+ if(i != children.count() - 1)
+ buffer.append(ENUMLISTSEPERATESYM);
+ }
+ buffer.append(ENUMLISTCLOSESYM);
+ openConditionals--;
+ break;
+
+ case TAG:
+ buffer.append(TAGSYM);
+ buffer.append(element->tag->name);
+
+ if(element->params_count > 0)
+ {
+ /* Rendering parameters if there are any */
+ buffer.append(ARGLISTOPENSYM);
+ for(int i = 0; i < children.count(); i++)
+ {
+ buffer.append(children[i]->genCode());
+ if(i != children.count() - 1)
+ buffer.append(ARGLISTSEPERATESYM);
+ }
+ buffer.append(ARGLISTCLOSESYM);
+ }
+ break;
+
+ case TEXT:
+ for(char* cursor = (char*)element->data; *cursor; cursor++)
+ {
+ if(find_escape_character(*cursor))
+ buffer.append(TAGSYM);
+ buffer.append(*cursor);
+ }
+ break;
+
+ case COMMENT:
+ buffer.append(COMMENTSYM);
+ buffer.append((char*)element->data);
+ buffer.append('\n');
+ break;
+ }
+ }
+ else if(param)
+ {
+ switch(param->type)
+ {
+ case skin_tag_parameter::STRING:
+ for(char* cursor = param->data.text; *cursor; cursor++)
+ {
+ if(find_escape_character(*cursor))
+ buffer.append(TAGSYM);
+ buffer.append(*cursor);
+ }
+ break;
+
+ case skin_tag_parameter::NUMERIC:
+ buffer.append(QString::number(param->data.numeric, 10));
+ break;
+
+ case skin_tag_parameter::DEFAULT:
+ buffer.append(DEFAULTSYM);
+ break;
+
+ case skin_tag_parameter::CODE:
+ buffer.append(QObject::tr("This doesn't belong here"));
+ break;
+
+ }
+ }
+ else
+ {
+ for(int i = 0; i < children.count(); i++)
+ buffer.append(children[i]->genCode());
+ }
+
+ return buffer;
+}
+
+/* A more or less random hashing algorithm */
+int ParseTreeNode::genHash() const
+{
+ int hash = 0;
+ char *text;
+
+ if(element)
+ {
+ hash += element->type;
+ switch(element->type)
+ {
+ case UNKNOWN:
+ break;
+ case VIEWPORT:
+ case LINE:
+ case SUBLINES:
+ case CONDITIONAL:
+ hash += element->children_count;
+ break;
+
+ case TAG:
+ for(unsigned int i = 0; i < strlen(element->tag->name); i++)
+ hash += element->tag->name[i];
+ break;
+
+ case COMMENT:
+ case TEXT:
+ text = (char*)element->data;
+ for(unsigned int i = 0; i < strlen(text); i++)
+ {
+ if(i % 2)
+ hash += text[i] % element->type;
+ else
+ hash += text[i] % element->type * 2;
+ }
+ break;
+ }
+
+ }
+
+ if(param)
+ {
+ hash += param->type;
+ switch(param->type)
+ {
+ case skin_tag_parameter::DEFAULT:
+ case skin_tag_parameter::CODE:
+ break;
+
+ case skin_tag_parameter::NUMERIC:
+ hash += param->data.numeric * (param->data.numeric / 4);
+ break;
+
+ case skin_tag_parameter::STRING:
+ for(unsigned int i = 0; i < strlen(param->data.text); i++)
+ {
+ if(i % 2)
+ hash += param->data.text[i] * 2;
+ else
+ hash += param->data.text[i];
+ }
+ break;
+ }
+ }
+
+ for(int i = 0; i < children.count(); i++)
+ {
+ hash += children[i]->genHash();
+ }
+
+ return hash;
+}
+
+ParseTreeNode* ParseTreeNode::child(int row)
+{
+ if(row < 0 || row >= children.count())
+ return 0;
+
+ return children[row];
+}
+
+int ParseTreeNode::numChildren() const
+{
+ return children.count();
+}
+
+
+QVariant ParseTreeNode::data(int column) const
+{
+ switch(column)
+ {
+ case ParseTreeModel::typeColumn:
+ if(element)
+ {
+ switch(element->type)
+ {
+ case UNKNOWN:
+ return QObject::tr("Unknown");
+ case VIEWPORT:
+ return QObject::tr("Viewport");
+
+ case LINE:
+ return QObject::tr("Logical Line");
+
+ case SUBLINES:
+ return QObject::tr("Alternator");
+
+ case COMMENT:
+ return QObject::tr("Comment");
+
+ case CONDITIONAL:
+ return QObject::tr("Conditional Tag");
+
+ case TAG:
+ return QObject::tr("Tag");
+
+ case TEXT:
+ return QObject::tr("Plaintext");
+ }
+ }
+ else if(param)
+ {
+ switch(param->type)
+ {
+ case skin_tag_parameter::STRING:
+ return QObject::tr("String");
+
+ case skin_tag_parameter::NUMERIC:
+ return QObject::tr("Number");
+
+ case skin_tag_parameter::DEFAULT:
+ return QObject::tr("Default Argument");
+
+ case skin_tag_parameter::CODE:
+ return QObject::tr("This doesn't belong here");
+ }
+ }
+ else
+ {
+ return QObject::tr("Root");
+ }
+
+ break;
+
+ case ParseTreeModel::valueColumn:
+ if(element)
+ {
+ switch(element->type)
+ {
+ case UNKNOWN:
+ case VIEWPORT:
+ case LINE:
+ case SUBLINES:
+ return QString();
+
+ case CONDITIONAL:
+ return QString(element->tag->name);
+
+ case TEXT:
+ case COMMENT:
+ return QString((char*)element->data);
+
+ case TAG:
+ return QString(element->tag->name);
+ }
+ }
+ else if(param)
+ {
+ switch(param->type)
+ {
+ case skin_tag_parameter::DEFAULT:
+ return QObject::tr("-");
+
+ case skin_tag_parameter::STRING:
+ return QString(param->data.text);
+
+ case skin_tag_parameter::NUMERIC:
+ return QString::number(param->data.numeric, 10);
+
+ case skin_tag_parameter::CODE:
+ return QObject::tr("Seriously, something's wrong here");
+ }
+ }
+ else
+ {
+ return QString();
+ }
+ break;
+
+ case ParseTreeModel::lineColumn:
+ if(element)
+ return QString::number(element->line, 10);
+ else
+ return QString();
+ break;
+ }
+
+ return QVariant();
+}
+
+
+int ParseTreeNode::getRow() const
+{
+ if(!parent)
+ return -1;
+
+ return parent->children.indexOf(const_cast<ParseTreeNode*>(this));
+}
+
+ParseTreeNode* ParseTreeNode::getParent() const
+{
+ return parent;
+}
+
+ParseTreeNode::~ParseTreeNode()
+{
+ for(int i = 0; i < children.count(); i++)
+ delete children[i];
+}