builder.html.js
[app.Builder.js] / builder.html.js
1 //<script type="text/javascript">
2  
3
4 var MODULE = { isBuilder : true };
5 // BC
6 var _this = MODULE;
7
8 // the apprenderer.
9 Builder  = {
10     
11     scriptTag : false,
12     
13     id : 1,
14     
15     render : function(data, clsname)
16     {
17         // for debugging 
18         // console.log(data);        return; 
19         //Roo.log(data);
20         //Roo.log(data);
21         // This would be alot simpler if we just use the XComponent code...
22         // data should now be dialog or xcomponent..
23         // only snag here is that we do not know the name currently..
24          Roo.log(clsname);
25         var  ix = '_src_' + this.id++;
26         // should replace module name with Builder._src_{id}
27         data =  data.replace(clsname, 'Builder.' + ix);
28         // next.. we need to ensure that parent is set correctly..
29         // done by sender... otherwise building becomes difficult..
30         //data  += "\n" + 'Builder.' + ix + ".parent = '#renderel';\n";
31         
32         //Roo.log(data);return;
33          Roo.log(data);
34         if (this.scriptTag) { 
35             document.body.removeChild(this.scriptTag);
36             this.scriptTag = false;
37         }
38         
39         this.scriptTag = document.body.appendChild(document.createElement('script'));
40         this.scriptTag.setAttribute('type','text/javascript');
41          
42         this.id++;
43         this.scriptTag.appendChild(
44                     document.createTextNode(
45                             data 
46         ));
47          
48         
49         //Roo.log(this.tree);
50         MODULE = { isBuilder : true }; 
51         _this = MODULE;
52         if (!Builder.click) {
53             Builder.click= Roo.get(document.body).on('click', this.onclick, this);
54         }
55         
56         return;
57         
58         return;
59         var  wait_for_tree = function() {
60             
61             Builder.tree = Builder[ix];
62             if (!Builder.tree) {
63                 Roo.log("Wating for tree : " + ix);
64                 wait_for_tree.defer(100);
65                 return;
66             }
67              Builder.redraw(false);
68         }
69         wait_for_tree.defer(100);
70     },
71     
72     
73     
74     tree : {}, 
75     renderObj :  { isBuilder : true },
76     dialogroot : false,
77     
78     redrawClear : function(isAuto)
79     {
80         this.renderObj = { isBuilder : true };
81         
82         this.scroll = {
83             top:0,
84             left:0
85         };
86         
87          
88         
89         //if (this.panelroot) {
90         //    this.scroll = this.panelroot.el.getScroll();
91         //    this.layout.remove('center', this.panelroot);
92         //    this.panelroot = false;
93         //}
94         if (this.dialogroot) {
95             this.dialogroot.remove();
96             this.dialogroot = false;
97         }
98         if (this.layoutbase) {
99             //console.log(Builder.dump(this.layoutbase.el));
100             
101             
102             try {
103                 var pan = this.layoutbase.getRegion('center').getPanel(0);
104                 if (pan) {
105                     this.layoutbase.remove('center', pan);
106                 }
107                 
108                 
109             } catch( e) {
110                 console.log(e);
111                 console.log(JSON.stringify(e));
112                 // reload!!?
113             }
114             
115             
116             
117             //this.layoutbase= false;
118         }
119          
120         
121     },
122     
123     
124     redraw: function(isAuto)
125     {
126         
127         // top level is not relivant
128         this.redrawClear(isAuto);
129         
130         
131         var cfg =  this.tree;
132         //console.log(this.dump(cfg));
133         if (!cfg) {
134             return;
135         }
136         
137         
138         this.munge(cfg);
139         this.cfg = cfg;
140         //console.log(this.dump(cfg)); 
141         // we draw either a dialog or a tab..
142         
143         if (cfg.xtype == 'LayoutDialog') {
144             
145             cfg.modal = false;
146             //var xy  = Pman.Tab.BuilderPanel.panel.el.getXY();
147             //cfg.items[0].x = xy[0];
148             //cfg.items[0].y = xy[1];
149             //cfg.items[0].constraintoviewport = false;
150         
151             this.dialogroot = Roo.get( document.body).createChild({
152                 id : cfg.id
153             });
154             
155             
156             MODULE.dialog = new Roo[cfg.xtype](this.dialogroot, cfg);
157             //this.dialog.el.on('click', this.panelClick, this);
158             MODULE.dialog.show();
159             return;
160             
161         }
162         
163         // otherwise we are creating a layout area on the document..
164         
165          
166         // handles 
167         // contentpanel, nestedlayoutpanel, contentpanel.. etc. 
168         // force center region..
169         cfg.region = 'center';
170         cfg.background = false;
171         if (!this.layoutbase) {
172                 
173             this.layoutbase = new Ext.BorderLayout(document.body, {
174               
175                  center: {
176                     titlebar: false,
177                     autoScroll:false,
178                     closeOnTab: true,
179                     tabPosition: 'top',
180                     //resizeTabs: true,
181                     alwaysShowTabs: true,
182                     minTabWidth: 140
183                 }
184             });
185         }
186         try {
187             console.log("ADDING CFG");    
188             console.log(cfg)
189             this.layoutbase.addxtype(  cfg ); 
190         } catch (e) {
191             console.log("GOT ERROR? - saved in Builder.lastError");
192             Builder.lastError = e;
193             console.log(e);
194             console.log(typeof(e));
195             
196             console.log(this.dump(e));
197             console.trace();
198         }
199         
200         
201     },
202   
203     
204     munge :function (cfg, isListener)
205     {
206         var xitems = false;
207         //cfg.cls = cfg.cls || '';
208         //cfg.cls += ' ' + cfg.id;
209         if (!cfg.id) {
210             this.dump(cfg);
211         }
212         
213         //console.log(cfg.xtype + ': ' + cfg.id);
214         
215         if (cfg.items) {
216             xitems = cfg.items;
217             delete cfg.items;
218         }
219         if (typeof(cfg.background) != 'undefined') {
220             cfg.background = false;
221         }
222         
223         var xtype = (cfg['|xns'] || '')  + '.' + (cfg.xtype || '');
224         
225         for(var p in cfg){
226             // key is not string?!?!?!!?
227           
228             if (typeof(p) != 'string') {
229                 continue;
230             }
231             
232             if (typeof(cfg[p]) == 'object') { // listeners!!!
233                 this.munge(cfg[p], p == 'listeners');
234                 continue;
235             }
236             // SPECIAL - PIPE
237             if (p.charAt(0) == '|' || isListener) {
238                 
239                 if (!cfg[p].length) {
240                     delete cfg[p];
241                     continue;
242                 }
243                 var pp = p.charAt(0) == '|'  ? p.substring(1) : p;
244                 try {
245                     
246                     
247                     var _tmp = false;
248                     
249                     /** eval:var:MOUDULE **/
250                     /** eval:var:_this **/
251                     /** eval:var:_tmp **/
252                     // stupid IE can not return objects evaluated..
253                    // console.log('_tmp =(' + cfg[p] + ')');
254                     eval('_tmp =(' + cfg[p] + ')');
255                     cfg[pp] = _tmp;
256                     
257                     //if (typeof(_tmp) == 'undefined') {
258                     //    alert(cfg[p]);
259                    // }
260                    
261                 } catch(e) {  
262                     console.log('Error evaluating: '  + cfg[p] + "\r\n" + JSON.stringify(e)); 
263                 };
264                 if (pp != p) {
265                     delete cfg[p];
266                 }
267                 
268                     
269                 
270                 continue;
271             }
272             // skip '*'
273             if ((p.charAt(0) == '*') || (p.charAt(0) == '+')) {
274                 delete cfg[p];
275                 continue;
276             }
277             // normal..
278               
279         }
280         
281         if (cfg.xtype && cfg.xtype.match(/^Roo\./) && !cfg.xns) {
282             // xtype contains full path..
283             var bits = cfg.xtype.split('.');
284             bits.shift(); // remove roo..
285             cfg.xtype = bits.pop(); // get the last bit..
286             cfg.xns = Roo;
287             while (bits.length) {
288                 cfg.xns = cfg.xns[bits.shift()]; 
289             }
290              
291         }
292         if (cfg.xtype) {
293             if (!cfg.xns || typeof(cfg.xns[cfg.xtype]) == 'undefined') {
294                 throw "Invalid Xtype " + cfg.xtype + ' on ' + cfg.xtreepath;
295             }
296         }
297         if (!isListener) {
298             cfg.listeners = cfg.listeners || {};
299         }
300         // we can overlay some event handlers here..
301         
302        
303         //console.log('xtype'  + xtype)
304         switch(xtype) {
305             case 'Roo.LayoutDialog':
306                 cfg.listeners.resize = function(dlg, w,h)
307                 {
308                     console.log('{ "id" : "' + dlg.id + '", "set" : "width", "value": ' + w + '}');
309                     console.log('{ "id" : "' + dlg.id + '", "set" : "height", "value": ' + h + '}');
310                 }
311                 break;
312         }
313         
314         
315         
316         
317         
318         // now for all the children.. (items)
319         if (xitems === false) {
320             
321             return;
322         }
323         cfg.items = [];
324         for (var i = 0; i < xitems.length; i++) {
325             // if +builderhide set !!!! drop it!!
326             
327             
328             var xi = xitems[i];
329             if (typeof(xi['*prop']) != 'undefined') {
330                 //console.log('adding prop:' + xi['*prop']);
331                 
332                 var pr = xi['*prop'];
333                 this.munge(xi);
334                 // if prop is an array - then it's items are really the value..
335                 if (pr.match(/\[\]$/)) {
336                     //console.log('adding array?:' + pr);
337                     pr = pr.replace(/\[\]$/, '');
338                     cfg[pr] = cfg[pr]  || [];
339                     cfg[pr].push(xi);
340                     continue;
341                 }
342                 
343                 
344                 if (xi.xtype && xi.xtype  == 'Array') {
345                     cfg[pr] = xi.items;
346                 } else {
347                     //console.log('setting property:' + pr);
348                     cfg[pr] = xi;
349                 }
350                 
351                 
352                 continue;
353             }
354             this.munge(xi);
355             cfg.items.push(xi);
356         }
357         
358         if (cfg.items.length == 0) {
359             delete cfg.items;
360         }
361         console.log(cfg);
362         
363         
364     },
365     
366     
367     
368     cloneConfig : function(config) {
369                 if (!config) { return null; }
370                 var newConfig = {};
371                 for (var i in config) {
372                         if (typeof config[i] == 'object') {
373                                 newConfig[i] = this.cloneConfig(config[i]);
374                         } else if (typeof config[i] != 'function') {
375                                 newConfig[i] = config[i];
376                         }
377                 }
378                 return newConfig;
379         },
380     dump : function (arr,level) {
381         var dumped_text = "";
382         if(!level) level = 0;
383         if (level >  3) {
384             return '... TO DEEP ...';
385         }
386         //The padding given at the beginning of the line.
387         var level_padding = "";
388         for(var j=0;j<level+1;j++) level_padding += "    ";
389         
390         if(typeof(arr) == 'object') { //Array/Hashes/Objects 
391             for(var item in arr) {
392                 
393                 var value = arr[item];
394                 if (item == 'xns') {
395                     continue;
396                 }
397                 if(typeof(value) == 'function') { //If it is an array,
398                     // fake dump...
399                     dumped_text += level_padding + "'" + item + "' : function() { ... },\n";
400                     continue;
401                 }
402                 if(typeof(value) == 'object') { //If it is an array,
403                     dumped_text += level_padding + "'" + item + "': {\n";
404                     dumped_text += this.dump(value,level+1);
405                     dumped_text += level_padding + "}\n";
406                     continue;
407                 }
408                 dumped_text += level_padding + "'" + item + "' : \"" + value + "\"\n";
409                 
410             }
411         } else { //Stings/Chars/Numbers etc.
412             dumped_text = "===>"+arr+"<===("+typeof(arr)+")";
413         }
414         return dumped_text;
415     },
416     findNode : function(ftg , method) {
417         if (!ftg) {
418             return; false
419         }
420       // console.log(ftg.id);
421         if (ftg.id && typeof(ftg.id) == 'string' && ftg.id.match(/builder-/)) {
422             var nid = ftg.id.replace('builder-', '').replace('x-form-el-', '');
423             this[method]( nid );
424             return true;
425         }
426         // needs fixing..
427         if (ftg.dom.className.match(/[0-9]+/)) {
428             //console.log(ftg.dom.className);
429             var cmat = ftg.dom.className.match(/x-grid-hd-builder-(form-gen-[0-9:]+)/);
430             if (cmat) {
431                 this[method]( cmat[1] );
432                 return true;
433             }
434         }
435         
436         
437         
438         
439         return false;
440     },
441     
442     overPos: function(x,y) 
443     {
444         
445         var el = document.elementFromPoint(x,y);
446        // //console.log(el.id);
447        // console.log(document.body.innerHTML);
448         this.hover( {
449             getTarget : function () {
450                 return el;
451             },
452             stopEvent : function() {
453                 
454             }
455         });
456         
457         
458     },
459     onclick: function(e) {
460         var tg = Roo.get(e.getTarget());
461         if (!tg) {
462             //console.log('no target');
463             return;
464            }
465          
466         if (this.findNode(tg,'logClick')) {
467             return;
468         }
469         var dp = Roo.get(tg.up(''));
470         if (dp && this.findNode(dp,'logClick')) {
471             return;
472         }
473         
474         var ns = Roo.get(tg.getNextSibling());
475         if (ns && this.findNode(ns,'logClick')) {
476           
477             return;
478         }
479         if (ns && ns.down('') && this.findNode(Roo.get(ns.down('')) ,'logClick') ) {
480             return;
481         }
482         
483         for(var i =0; i < 5; i++) {
484             tg = Roo.get(tg.up(''));
485             if (!tg) {
486                 //console.log('no parent' + i);
487                 return;
488             }
489             if (tg && this.findNode(tg,'logClick')) {
490                 return;
491             }
492         }
493         //console.log('no target in parents');
494         
495     },
496     logClick : function(id) 
497     {
498          var bid = id.length ? 'builder-' + id : '';
499          console.log('{ "id" :  "' + bid + '"}');
500     },
501     
502     
503     hover : function(e) {
504         
505        
506         var tg = Roo.get(e.getTarget());
507         if (!tg) {
508             //console.log('no target');
509             this.logMove('');
510             return;
511            }
512          
513         if (this.findNode(tg,'logMove')) {
514             e.stopEvent();
515             return;
516         }
517         var dp = Roo.get(tg.up(''));
518         if (dp && this.findNode(dp,'logMove')) {
519             e.stopEvent();
520             return;
521         }
522         
523         var ns = Roo.get(tg.getNextSibling());
524         if (ns && this.findNode(ns,'logMove')) {
525             e.stopEvent();
526             return;
527         }
528         if (ns && ns.down('') && this.findNode(Roo.get(ns.down('')) ,'logMove' )) {
529             e.stopEvent();
530             return;
531         }
532         
533         for(var i =0; i < 5; i++) {
534             tg = Roo.get(tg.up(''));
535             if (!tg) {
536                 //console.log('no parent' + i);
537                 this.logMove('');
538                 return;
539             }
540             if (tg && this.findNode(tg,'logMove')) {
541                 e.stopEvent();
542                 return;
543             }
544         }
545         //console.log('no target in parents');
546         this.logMove('');
547     },
548     logMove : function (id) {
549         //console.log("LOGMOVE: " + id);
550         
551         if (this.lastID === id) {
552             return;
553        }
554        id = ''+ id;
555        var bid = id.length ? 'builder-' + id : '';
556        console.log('{ "hover-node" :  "' + bid + '"}');
557        this.lastID = id;
558     }
559             
560     
561 };
562