From 21ff02a69331fbcd53dc93a1af9a93618225b4bf Mon Sep 17 00:00:00 2001 From: Ethan Yonker Date: Wed, 18 Feb 2015 14:35:00 -0600 Subject: GUI: Support styles in xml to reduce xml file size Also allow sliders to have their own text label instead of requiring a whole separate text object for the label in the xml. Change-Id: I6e314efb4bb454d496555ff7e003d743063a1308 --- gui/pages.cpp | 90 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 87 insertions(+), 3 deletions(-) (limited to 'gui/pages.cpp') diff --git a/gui/pages.cpp b/gui/pages.cpp index 58e99e60c..50c60a695 100644 --- a/gui/pages.cpp +++ b/gui/pages.cpp @@ -103,6 +103,56 @@ int ConvertStrToColor(std::string str, COLOR* color) } // Helper APIs +xml_node<>* FindNode(xml_node<>* parent, const char* nodename, int depth /* = 0 */) +{ + xml_node<>* child = parent->first_node(nodename); + if (child) + return child; + + if (depth == 10) { + LOGERR("Too many style loops detected.\n"); + return NULL; + } + + xml_node<>* style = parent->first_node("style"); + if (style) { + while (style) { + if (!style->first_attribute("name")) { + LOGERR("No name given for style.\n"); + continue; + } else { + std::string name = style->first_attribute("name")->value(); + xml_node<>* node = PageManager::FindStyle(name); + + if (node) { + // We found the style that was named + xml_node<>* stylenode = FindNode(node, nodename, depth + 1); + if (stylenode) + return stylenode; + } + } + style = style->next_sibling("style"); + } + } else { + // Search for stylename in the parent node + xml_attribute<>* attr = parent->first_attribute("style"); + // If no style is found anywhere else and the node wasn't found in the object itself + // as a special case we will search for a style that uses the same style name as the + // object type, so would search for a style named "button" + if (!attr) + attr = parent->first_attribute("type"); + if (attr) { + xml_node<>* node = PageManager::FindStyle(attr->value()); + if (node) { + xml_node<>* stylenode = FindNode(node, nodename, depth + 1); + if (stylenode) + return stylenode; + } + } + } + return NULL; +} + std::string LoadAttrString(xml_node<>* element, const char* attrname, const char* defaultvalue) { if (!element) @@ -130,9 +180,10 @@ int LoadAttrIntScaleY(xml_node<>* element, const char* attrname, int defaultvalu return scale_theme_y(LoadAttrInt(element, attrname, defaultvalue)); } -COLOR LoadAttrColor(xml_node<>* element, const char* attrname, COLOR defaultvalue) +COLOR LoadAttrColor(xml_node<>* element, const char* attrname, bool* found_color, COLOR defaultvalue) { string value = LoadAttrString(element, attrname); + *found_color = !value.empty(); // resolve variables DataManager::GetValue(value, value); COLOR ret = defaultvalue; @@ -142,6 +193,12 @@ COLOR LoadAttrColor(xml_node<>* element, const char* attrname, COLOR defaultvalu return defaultvalue; } +COLOR LoadAttrColor(xml_node<>* element, const char* attrname, COLOR defaultvalue) +{ + bool found_color = false; + return LoadAttrColor(element, attrname, &found_color, defaultvalue); +} + FontResource* LoadAttrFont(xml_node<>* element, const char* attrname) { std::string name = LoadAttrString(element, attrname, ""); @@ -621,8 +678,7 @@ int PageSet::Load(ZipArchive* package) xml_node<>* parent; xml_node<>* child; xml_node<>* xmltemplate; - xml_node<>* blank_templates; - int pages_loaded = -1, ret; + xml_node<>* xmlstyle; parent = mDoc.first_node("recovery"); if (!parent) @@ -701,6 +757,11 @@ int PageSet::Load(ZipArchive* package) if (xmltemplate) templates.push_back(xmltemplate); + // Load styles if present + xmlstyle = parent->first_node("styles"); + if (xmlstyle) + styles.push_back(xmlstyle); + child = parent->first_node("pages"); if (child) { if (LoadPages(child)) { @@ -720,6 +781,7 @@ int PageSet::CheckInclude(ZipArchive* package, xml_document<> *parentDoc) xml_node<>* parent; xml_node<>* child; xml_node<>* xmltemplate; + xml_node<>* xmlstyle; long len; char* xmlFile = NULL; string filename; @@ -817,6 +879,11 @@ int PageSet::CheckInclude(ZipArchive* package, xml_document<> *parentDoc) if (xmltemplate) templates.push_back(xmltemplate); + // Load styles if present + xmlstyle = parent->first_node("styles"); + if (xmlstyle) + styles.push_back(xmlstyle); + child = parent->first_node("pages"); if (child && LoadPages(child)) { @@ -1288,6 +1355,23 @@ HardwareKeyboard *PageManager::GetHardwareKeyboard() return mHardwareKeyboard; } +xml_node<>* PageManager::FindStyle(std::string name) +{ + for (std::vector*>::iterator itr = mCurrentSet->styles.begin(); itr != mCurrentSet->styles.end(); itr++) { + xml_node<>* node = (*itr)->first_node("style"); + + while (node) { + if (!node->first_attribute("name")) + continue; + + if (name == node->first_attribute("name")->value()) + return node; + node = node->next_sibling("style"); + } + } + return NULL; +} + MouseCursor *PageManager::GetMouseCursor() { if(!mMouseCursor) -- cgit v1.2.3