JSDOC/Walker2.js
[gnome.introspection-doc-generator] / JSDOC / DocTag.js
index e69de29..e5449ab 100644 (file)
@@ -0,0 +1,209 @@
+//<script  type="text/javascript">
+XObject = imports.XObject.XObject;
+
+Options = imports.Options.Options;
+
+/**
+ * DocTag - represents a single A=b tag.
+ * @class DocTag
+ */
+DocTag = XObject.define(
+
+/**
+ * @constructor
+ * @arg {String} src
+ */
+
+    function(src) {
+        this.title        = "";
+        this.type         = "";
+        this.name         = "";
+        this.isOptional   = false;
+        this.defaultValue = "";
+        this.desc         = "";
+        if (typeof src != "undefined") {
+            this.parse(src);
+        }
+    }, 
+    Object,
+    {
+        
+        title: '',
+        type: '',
+        name : '',
+        isOptional : false,
+        defaultValue : '',
+        desc : '',
+        /* qdump needed for cahcing?
+        toQDump  :function(t)
+        {
+            return JSDOC.toQDump(t, 'JSDOC.DocTag.fromDump({', '})', new JSDOC.DocTag());
+        } ,
+        */
+
+
+        /**
+            Populate the properties of this from the given tag src.
+            @param {string} src
+         */
+        parse : function(src) {
+            if (typeof src != "string") throw "src must be a string not "+(typeof src);
+
+            try {
+                src = this.nibbleTitle(src);
+                //if (JSDOC.PluginManager) {
+                //    JSDOC.PluginManager.run("onDocTagSynonym", this);
+               // }
+                
+                src = this.nibbleType(src);
+                
+                // only some tags are allowed to have names.
+                if (this.title == "param" || this.title == "property" || this.title == "cfg") { // @config is deprecated
+                    src = this.nibbleName(src);
+                }
+            }
+            catch(e) {
+                if (Options.LOG) Options.LOG.warn(e);
+                else throw e;
+            }
+            this.desc = src; // whatever is left
+            
+            // example tags need to have whitespace preserved
+            if (this.title != "example") this.desc = this.desc.trim();
+            
+            //if (JSDOC.PluginManager) {
+            //    JSDOC.PluginManager.run("onDocTag", this);
+            //}
+        },
+
+        /**
+            Automatically called when this is stringified.
+         */
+        toString : function() {
+            return this.desc;
+        },
+         
+
+        /**
+            Find and shift off the title of a tag.
+            @param {string} src
+            @return src
+         */
+        nibbleTitle : function(src) {
+            if (typeof src != "string") throw "src must be a string not "+(typeof src);
+            
+            var parts = src.match(/^\s*(\S+)(?:\s([\s\S]*))?$/);
+
+            if (parts && parts[1]) this.title = parts[1];
+            if (parts && parts[2]) src = parts[2];
+            else src = "";
+            
+            return src;
+        },
+         
+        /**
+            Find and shift off the type of a tag.
+            @requires frame/String.js
+            @param {string} src
+            @return src
+         */
+        nibbleType : function(src) 
+        {
+            if (typeof src != "string") throw "src must be a string not "+(typeof src);
+            
+            if (src.match(/^\s*\{/)) {
+                var typeRange = this.balance(src,"{", "}");
+                if (typeRange[1] == -1) {
+                    throw "Malformed comment tag ignored. Tag type requires an opening { and a closing }: "+src;
+                }
+                this.type = src.substring(typeRange[0]+1, typeRange[1]).trim();
+                this.type = this.type.replace(/\s*,\s*/g, "|"); // multiples can be separated by , or |
+                src = src.substring(typeRange[1]+1);
+            }
+            
+            return src;
+        },
+         
+
+        /**
+            Find and shift off the name of a tag.
+            @requires frame/String.js
+            @param {string} src
+            @return src
+         */
+        nibbleName : function(src) {
+            if (typeof src != "string") throw "src must be a string not "+(typeof src);
+            
+            src = src.trim();
+            
+            // is optional?
+            if (src.charAt(0) == "[") {
+                var nameRange = this.balance(src,"[", "]");
+                if (nameRange[1] == -1) {
+                    throw "Malformed comment tag ignored. Tag optional name requires an opening [ and a closing ]: "+src;
+                }
+                this.name = src.substring(nameRange[0]+1, nameRange[1]).trim();
+                this.isOptional = true;
+                
+                src = src.substring(nameRange[1]+1);
+                
+                // has default value?
+                var nameAndValue = this.name.split("=");
+                if (nameAndValue.length) {
+                    this.name = nameAndValue.shift().trim();
+                    this.defaultValue = nameAndValue.join("=");
+                }
+            }
+            else {
+                var parts = src.match(/^(\S+)(?:\s([\s\S]*))?$/);
+                if (parts) {
+                    if (parts[1]) this.name = parts[1];
+                    if (parts[2]) src = parts[2].trim();
+                    else src = "";
+                }
+            }  
+
+            return src;
+        },
+        
+        balance : function(str, open, close) {
+            var i = 0;
+            while (str.charAt(i) != open) {
+                if (i == str.length) return [-1, -1];
+                i++;
+            }
+            
+            var j = i+1;
+            var balance = 1;
+            while (j < str.length) {
+                if (str.charAt(j) == open) balance++;
+                if (str.charAt(j) == close) balance--;
+                if (balance == 0) break;
+                j++;
+                if (j == str.length) return [-1, -1];
+            }
+            
+            return [i, j];
+}
+
+        
+        
+});
+
+// cached support?
+DocTag.fromDump = function(t)
+{
+    var ns = new DocTag();
+    for (var i in t) {
+        if (typeof(ns[i]) == "undefined") {
+            println("ERR:no default for DocTag:"+ i);
+        }
+       ns[i] = t[i];
+    }
+    return ns;
+}