Commit 5abd65b
Libbirdxml documentation and examples
Changed files (5)
modifiedlibbirdfont/Font.valamodifiedlibbirdxml/Attribute.valamodifiedlibbirdxml/Attributes.valamodifiedlibbirdxml/Tag.valamodifiedlibbirdxml/Xml.vala
Diff
@@ -391,28 +391,24 @@ public class Font : GLib.Object { return; } - // FIXME: move unassinged- if (glyph_collection.get_unicode () != "" || glyph_collection.is_unassigned ()) {+ if (glyph_collection.get_name () != "") { glyph_name.insert (glyph_collection.get_name (), glyph_collection); } - glyph_cache.insert (glyph_collection.get_unicode (), glyph_collection);+ if (glyph_collection.get_unicode () != "") {+ glyph_cache.insert ((!) glyph_collection.get_unicode (), glyph_collection);+ } else {+ glyph_cache.insert ((!) glyph_collection.get_name (), glyph_collection);+ }+ + if (glyph_collection.is_unassigned ()) {+ ligature.insert (glyph_collection.get_name (), glyph_collection);+ } } public string get_name_for_character (unichar c) { StringBuilder sb; - // FIXME: this is too slow- /*- while ((gl = get_glyph_indice (i++)) != null) {- g = (!) gl;- - if (g.unichar_code == c) {- return g.name;- }- }- */- if (c == 0) { return ".null".dup (); }@@ -13,7 +13,9 @@ */ namespace Bird { -/** Representation of one XML attribute. */+/** + * Representation of one XML attribute.+ */ public class Attribute : GLib.Object { public string ns;@@ -32,17 +34,23 @@ public class Attribute : GLib.Object { this.content = ""; } - /** @return name space part for this attribute. */+ /** + * @return name space part for this attribute.+ */ public string get_namespace () { return ns; } - /** @return the name of this attribute. */+ /**+ * @return the name of this attribute. + */ public string get_name () { return name; } - /** @return the value of this attribute. */+ /** + * @return the value of this attribute.+ */ public string get_content () { return content; }@@ -13,7 +13,9 @@ */ namespace Bird { -/** Iterator for XML attributes. */+/** + * Iterator for XML attributes. + */ public class Attributes : GLib.Object { Tag tag;@@ -14,6 +14,9 @@ namespace Bird { +/**+ * Representation of one XML tag.+ */ public class Tag : GLib.Object { int tag_index; @@ -29,6 +32,8 @@ public class Tag : GLib.Object { Tag? next_tag = null; Attribute? next_attribute = null; + bool error = false;+ internal Tag (string name, string attributes, string content) { this.name = name; this.data = content;@@ -42,18 +47,25 @@ public class Tag : GLib.Object { attributes = ""; name = ""; }-- /** Get tag attributes for this tag. */+ + /** + * Get tag attributes for this tag. + * @return a container with all the attributes+ */ public Attributes get_attributes () { return new Attributes (this); } - /** Iterate over all tags inside of this tag. */+ /** + * Iterate over all tags inside of this tag.+ */ public Iterator iterator () { return new Iterator(this); } - /** Reset the parser and start from the beginning XML tag. */+ /** + * Reset the parser and start from the beginning XML tag.+ */ public void reparse () { tag_index = 0; next_tag = obtain_next_tag ();@@ -64,17 +76,25 @@ public class Tag : GLib.Object { next_attribute = obtain_next_attribute (); } - /** @return the name of this tag. */+ /** + * Obtain the name of the tag.+ * @return the name of this tag. + */ public string get_name () { return name; } - /** @return data between the starty and end tag. */+ /** + * Obtain tag content.+ * @return data between the start and end tags.+ */ public string get_content () { return data; } - /** @return true if there is one more tags left */+ /** + * @return true if there is one more tags left+ */ internal bool has_more_tags () { return has_tags; }@@ -98,6 +118,10 @@ public class Tag : GLib.Object { return r; } + internal bool has_failed () {+ return error;+ }+ Tag obtain_next_tag () { int end_tag_index; Tag tag;@@ -132,7 +156,8 @@ public class Tag : GLib.Object { separator = find_next_separator (index); if (separator < 0) {- warning ("Expecting a separator after index %d.", index);+ error = true;+ warning ("Expecting a separator."); return new Tag.empty (); } @@ -215,6 +240,7 @@ public class Tag : GLib.Object { } } + error = true; warning (@"No closing tag for $(name)."); return -1; }@@ -275,6 +301,7 @@ public class Tag : GLib.Object { while (true) { previous_index = index; if (!attributes.get_next_char (ref index, out c)) {+ error = true; warning (@"Unexpected end of attributes in tag $(this.name)"); has_attributes = false; return new Attribute.empty ();@@ -301,6 +328,7 @@ public class Tag : GLib.Object { break; } else { has_attributes = false;+ error = true; warning (@"Expecting equal sign for attribute $(attribute_name)."); return new Attribute.empty (); }@@ -313,6 +341,7 @@ public class Tag : GLib.Object { break; } else { has_attributes = false;+ error = true; warning (@"Expecting quote for attribute $(attribute_name)."); return new Attribute.empty (); }@@ -325,6 +354,7 @@ public class Tag : GLib.Object { while (true) { if (!attributes.get_next_char (ref index, out c)) { has_attributes = false;+ error = true; warning (@"Expecting end quote for attribute $(attribute_name)."); return new Attribute.empty (); }@@ -11,34 +11,135 @@ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. */++/** + * Tools originally written for the BirdFont project.+ */ namespace Bird { -/** A small xml parser originally written for the BirdFont project. */+/** + * XML parser+ * + * A tiny XML parser written in Vala.+ * + * Example:+ * {{{+ * + * /* Print all tags and attributes in an XML document. + * *+ * * Expected output:+ * * tag1+ * * tag2+ * * attribute1+ * */+ * public static int main (string[] arg) {+ * Tag root;+ * XmlParser parser;+ * + * parser = new XmlParser ("""<tag1><tag2 attribute1=""/></tag1>""); + * + * if (parser.validate ()) {+ * root = parser.get_root_tag ();+ * print_tags (root);+ * }+ * }+ * + * + * void print_tags (Tag tag) {+ * print (tag.get_name ());+ * print ("\n");+ * print_attributes (tag);+ * + * foreach (Tag t in tag) {+ * print_tags (t);+ * }+ * }+ * + * void print_attributes (Tag tag) {+ * foreach (Attribute attribute in tag.get_attributes ()) {+ * print (attribute.get_name ()");+ * print ("\n");+ * }+ * }+ * + * }}}+ * + */ public class XmlParser : GLib.Object { Tag root; string data;+ bool error; - /** Create a new xml parser. */+ /** + * Create a new xml parser. + * @param data valid xml data+ */ public XmlParser (string data) { this.data = data; reparse (); } - /** @return the root tag. */+ /** + * Determine if the document can be parsed.+ * @return true if the xml document is valid xml.+ */+ public bool validate () {+ reparse ();+ Tag root = get_root_tag ();+ + if (error) {+ return false;+ }+ + validate_tags (root);+ + reparse ();+ return !error;+ }+ + void validate_tags (Tag tag) {+ Attributes attributes = tag.get_attributes ();+ + foreach (Attribute a in attributes) {+ if (tag.has_failed ()) {+ error = true;+ return;+ }+ }+ + foreach (Tag t in tag) {+ if (tag.has_failed ()) {+ error = true;+ return;+ }+ + validate_tags (t);+ } + }+ + /** + * Obtain the root tag.+ * @return the root tag. + */ public Tag get_root_tag () { reparse (); return root; } - /** Reset the parser and start from the beginning of the XML document. */+ /** + * Reset the parser and start from the beginning of the XML document. + */ internal void reparse () { int root_index; Tag container; + error = false;+ root_index = find_root_tag (); if (root_index == -1) { warning ("No root tag found.");+ error = true; root = new Tag.empty (); } else { container = new Tag ("", "", data.substring (root_index));@@ -46,16 +147,6 @@ public class XmlParser : GLib.Object { } } - /** @return the root tag. **/- internal Tag get_next_tag () {- return root.get_next_tag ();- }- - /** @return true if there is one more tags left */- internal bool has_more_tags () {- return root.has_more_tags ();- }- int find_root_tag () { int index = 0; int prev_index = 0;