Sync API with GLib GDir head
[gnome.introspection-doc-generator] / JSDOC / Template.js
1 //<script type="text/javscript">
2
3 Gio = imports.gi.Gio;
4 GLib = imports.gi.GLib;
5
6 imports['Object.js'].load(Object);
7
8
9
10 console = imports['console.js'].console;
11 xnew    = imports['xnew.js'].xnew;
12 Link    = imports['JSDOC/Template/Link.js'].Link;
13
14
15
16
17 Template = function(templateFile) {
18         if (templateFile) {
19         
20         this.template = Gio.simple_read(templateFile);
21         
22     }
23         
24         this.templateFile = templateFile;
25     this.templateName = GLib.path_get_basename(templateFile);
26         this.code = "";
27         this.parse();
28 }
29
30
31
32
33 Object.extend(Template.prototype , {
34     
35
36     parse : function() {
37         
38         console.log("Parsing template? " + this.templateName);
39         
40         this.template = this.template.replace(/\{#[\s\S]+?#\}/gi, "");
41         this.code = "var output=``"+this.template;
42
43         this.code = this.code.replace(
44             /<for +each="(.+?)" +in="(.+?)" *>/gi, 
45             function (match, eachName, inName) {
46                 return "``;\rvar $"+eachName+"_keys = keys("+inName+");\rfor(var $"+eachName+"_i = 0; $"+eachName+"_i < $"+eachName+"_keys.length; $"+eachName+"_i++) {\rvar $"+eachName+"_last = ($"+eachName+"_i == $"+eachName+"_keys.length-1);\rvar $"+eachName+"_key = $"+eachName+"_keys[$"+eachName+"_i];\rvar "+eachName+" = "+inName+"[$"+eachName+"_key];\routput+=``";
47             }
48         );      
49         this.code = this.code.replace(/<if test="(.+?)">/g, "``;\rif ($1) { \routput+=``");
50         this.code = this.code.replace(/<else\s*\/>/g, "``;} \relse\r{ \routput+=``");
51         
52         this.code = this.code.replace(/<\/(if|for)>/g, "``;\r};\routput+=``");
53         
54         //File.write("/tmp/jstookit_eval_"+this.templateName+".4.js", this.code);
55         
56         this.code = this.code.replace(
57             /\{\+\s*([\s\S]+?)\s*\+\}/gi,
58             function (match, code) {
59                 code = code.replace(/"/g, "``"); // prevent qoute-escaping of inline code
60                 code = code.replace(/(\r?\n)/g, " ");
61                 return "``+ \r("+code+") +\r``";
62             }
63         );
64         //File.write("/tmp/jstookit_eval_"+this.templateName+".6.js", this.code);
65         
66         this.code = this.code.replace(
67             /\{!\s*([\s\S]+?)\s*!\}/gi,
68             function (match, code) {
69                 code = code.replace(/"/g, "``"); // prevent qoute-escaping of inline code
70                 code = code.replace(/(\n)/g, " "); // remove quotes..
71                 return "``; "+code+";\routput+=``";
72             }
73         );
74        //File.write("/tmp/jstookit_eval_"+this.templateName+".7.js", this.code);
75         this.code = this.code+"``;";
76
77         
78         
79         this.code = this.code.replace(/(\r?\n)/g, "\\n");
80         this.code = this.code.replace(/"/g, "\\\"");
81         
82         this.code = this.code.replace(/``/g, "\"");
83         this.code = this.code.replace(/\\r/g, "\n");
84         //File.write("/tmp/jstookit_eval_"+this.templateName+".9.js", this.code);
85         this.code = this.code.replace(/\r/g, "\n\n");
86         
87
88     },
89
90     toCode : function() {
91         return this.code;
92     },
93
94     keys : function(obj) {
95         var keys = [];
96         if (obj && obj.constructor.toString().indexOf("Array") > -1) {
97             for (var i = 0; i < obj.length; i++) {
98                 keys.push(i);
99             }
100         }
101         else {
102             for (var i in obj) {
103                 keys.push(i);
104             }
105         }
106         return keys;
107     },
108
109     values : function(obj) {
110         var values = [];
111         if (obj.constructor.toString().indexOf("Array") > -1) {
112             for (var i = 0; i < obj.length; i++) {
113                 values.push(obj[i]);
114             }
115         }
116         else {
117             for (var i in obj) {
118                 values.push(obj[i]);
119             }
120         }
121         
122         
123         return values;
124     },
125
126     process : function(data) {
127         
128         //console.log("processing template");
129         var keys = this.keys;
130         var values = this.values;
131         
132         var makeSortby = this.makeSortby;
133         var makeSignature = this.makeSignature;
134         var summarize = this.summarize ;
135         var makeFuncSkel = this.makeFuncSkel;
136         var resolveLinks = this.resolveLinks;
137         var makeImage = this.makeImage;
138         // usefull for cross refing..
139         Template.data = data;
140         
141         
142         
143         try {
144              eval(this.code);
145            } catch (e) {
146              Gio.simple_write('/tmp/template.js', this.code);
147              Seed.print('in /tmp/template.js');
148             throw e;
149             Seed.quit();
150             }
151         
152         
153         //File.write("/tmp/jstookit_eval.js", this.code);
154         //try {
155         //eval('include     "/tmp/jstookit_eval.js";');
156         //includeJs("/tmp/jstookit_eval.js");
157             //eval(this.code);
158        // console.log("done eval of template");   
159         
160         return output;
161     },
162
163  
164     isdefined : function (typ) {
165         return typ != 'undefined';
166     },
167     
168     
169     summarize : function(desc) {
170         if (typeof desc != "undefined")
171             return desc.match(/([\w\W]+?\.)[^a-z0-9]/i)? RegExp.$1 : desc;
172     },
173
174     /** make a symbol sorter by some attribute */
175     makeSortby : function(attribute) {
176         return function(a, b) {
177             if (a[attribute] != undefined && b[attribute] != undefined) {
178                 a = a[attribute]; //.toLowerCase();
179                 b = b[attribute];//.toLowerCase();
180                 if (a < b) return -1;
181                 if (a > b) return 1;
182                 return 0;
183             }
184         }
185     },
186     makeImage : function(alias) {
187         ///  http://library.gnome.org/devel/gtk/stable/notebook.png
188         var ns = alias.split('.').shift();
189         var cls = alias.split('.').pop().toLowerCase();
190         if (ns != 'Gtk' ) {
191             return '';//ns;
192         }
193         return '<img class="class-picture" src="http://library.gnome.org/devel/gtk/stable/' + cls + '.png">';
194         
195         
196     },
197     
198     
199
200     makeSignature : function(params) {
201         if (!params) return "()";
202         var signature = "("     +
203             params.filter(
204                 function($) {
205                     return $.name.indexOf(".") == -1; // don't show config params in signature
206                 }
207             ).map(
208                 function($) {
209                     $.defaultValue = typeof($.defaultValue) == 'undefined' ? false : $.defaultValue;
210                     
211                     return "" +
212                         ($.isOptional ? "[" : "") +
213                         (($.type) ? 
214                             (new Link().toSymbol(
215                                 (typeof($.type) == 'object' ) ? 'Function' : $.type
216                             )) + " " :  ""
217                         )   + 
218                         "<B><i>" +$.name + "</i></B>" +
219                         ($.defaultValue ? "=" +item.defaultValue : "") +
220                         ($.isOptional ? "]" : "");
221                     
222                      
223                 }
224             ).join(", ")
225         +
226         ")";
227         return signature;
228     },
229
230     makeFuncSkel :  function(params) {
231         if (!params) return "function ()\n{\n\n}";
232         return "function ("     +
233             params.filter(
234                 function($) {
235                     return $.name.indexOf(".") == -1; // don't show config params in signature
236                 }
237             ).map( function($) { return $.name == 'this' ? '_self' : $.name; } ).join(", ")
238         +
239         ")\n{\n\n}";
240         
241     },
242
243     /** Find symbol {@link ...} strings in text and turn into html links */
244     resolveLinks : function (str, from) {
245         if (!str || typeof(str) == 'undefined') {
246             return '';
247         }
248         
249         // gtk specific. now..
250         // @ -> bold.. - they are arguments..
251         
252         str = str.replace(/@([a-z_]+)/gi,
253             function(match, symbolName) {
254                 return '<b>' + symbolName + '</b>';
255             }
256         );
257         // constants.
258         str = str.replace(/%([a-z_]+)/gi,
259             function(match, symbolName) {
260                 return '<b>' + symbolName + '</b>';
261             }
262         );
263         
264         str = str.replace(/#([a-z_]+)/gi,
265             function(match, symbolName) {
266                 return '<b>' + symbolName + '</b>';
267                 // this should do a lookup!!!!
268                 /// it could use data in the signature to find out..
269                 //return new Link().toSymbol(Template.data.ns + '.' + symbolName);
270             }
271         );
272         
273         str = str.replace(/\n/gi, '<br/>');
274         
275         /*
276         str = str.replace(/\{@link ([^} ]+) ?\}/gi,
277             function(match, symbolName) {
278                 return new Link().toSymbol(symbolName);
279             }
280         );
281         */
282         /*
283         str = str.replace(/\{([a-z\.\/]+)\}/gi,
284             function(match, symbolName) {
285                 //println("got match " + symbolName);
286                 bits = symbolName.split('/');
287                 var mret = '';
288                 for(var i = 0; i < bits.length; i++) {
289                     
290                     mret += (mret.length ? '&nbsp;|&nbsp;' : '') + new Link().toSymbol(bits[i]);
291                 }
292                 
293                 return mret; //new Link().toSymbol(symbolName);
294             }
295         );
296         */
297         // look for aaaa.\S+  ??? this might work???
298         /*
299         str = str.replace(/\([a-z]+\.\S+)/gi,
300             function(match, symbolName) {
301                 return new Link().toSymbol(symbolName);
302             }
303         );
304         */
305         
306         return str;
307     }
308     
309     
310 });