php7 fixes
[Pman.Builder] / Pman.Builder.View.js
1 /**
2  * The code that renders the view  - used to be in the Builder.View etc...
3  *
4  * used to be inside the Interface, but has proved to be to difficult to manage.
5  *
6  * In principle, simple event handling code is put in the interface, and any hard
7  * lifting is done in nice files...
8  *
9  * It might be better to just extend 'tree', and use the extended class..
10  * 
11  */
12
13 Pman.Builder.View = {
14     
15     panel : false,
16     
17     panelroot : false,
18     dialogroot : false,
19     
20     
21     renderObj : false,
22     
23     doc : function() {
24         var iframe = this.container.el.select('iframe',true).first().dom;
25         
26         return iframe.contentDocument || iframe.contentWindow.document;
27     },
28     win : function() {
29         var iframe = this.container.el.select('iframe',true).first().dom;
30         return iframe.contentWindow;
31     },
32     
33     init : function (comp) {
34         if (this.panel || !comp.layout) {
35             return;
36         }
37         this.panel = comp.panel;
38         this.layout  = comp.panel.layout;
39         // see if we can render a iframe..
40         
41         var app = 'test';
42         
43         this.container = comp.layout.getRegion('center').getPanel(0);
44         this.container.setContent(
45                 '<iframe width="100%" height="100%" src="'+baseURL+'/Builder/App/' + app + '?no_parts=1"></iframe>'
46         );
47         var iframe = this.container.el.select('iframe',true).first();
48         
49         iframe.setSize( this.panel.el.getSize());
50         
51         //this.doc = iframe.contentDocument || iframe.contentWindow.document;
52         
53         
54     },
55     
56     clearAll : function(isAuto) {
57         try {
58             this.win().Pman.Builder.View.frameClearAll(isAuto);
59         } catch(e) {
60             //alert(e);
61         }
62         
63        
64     },
65     
66     frameToHTML : function()
67     {
68         return this.win().Pman.Builder.View.toHTML();  
69         
70         
71         
72     },
73     toHTML : function ()  {
74         var ret = '';
75         Roo.select('body > div',true).each(function(el) {
76             this.traverseDOMTree(function(s) { ret+=s; }, el.dom, 1);
77             ret+="\n";
78         }, this);
79         return ret;
80         
81     },
82     traverseDOMTree : function(cb, currentElement, depth) {
83         if (currentElement) {
84             
85             if (currentElement.className.match(/roo-dynamic/)) {
86                 return;
87             }
88             //Roo.log(currentElement);
89             var j;
90             var nodeName = currentElement.nodeName;
91             var tagName = currentElement.tagName;
92             
93             if  (nodeName == '#text') {
94                 cb(currentElement.nodeValue);
95                 return;
96             
97             }
98             if(nodeName == 'BR'){
99                 cb("<BR/>");
100                 return;
101             }
102             
103             var i = 0;
104           // Prints the node tagName, such as <A>, <IMG>, etc
105             if (tagName) {
106                 var attr = [];
107                 for(i = 0; i < currentElement.attributes.length;i++) {
108                     var aname = currentElement.attributes.item(i).name;
109                     if (aname=='id') {
110                         aname= 'xbuilderid';
111                     }
112                     attr.push(aname + '="' + currentElement.attributes.item(i).value + '"' );
113                 }
114                 
115                 
116                 cb("<"+currentElement.tagName+ ( attr.length ? (' ' + attr.join(' ') ) : '') + ">");
117             } 
118             else {
119               cb("[unknown tag]");
120             }
121             // Traverse the tree
122             i = 0;
123             var currentElementChild = currentElement.childNodes[i];
124             var allText = true;
125             while (currentElementChild) {
126                 // Formatting code (indent the tree so it looks nice on the screen)
127                 
128                 if  (currentElementChild.nodeName == '#text') {
129                     cb(currentElementChild.nodeValue);
130                     i++;
131                     currentElementChild=currentElement.childNodes[i];
132                     continue;
133                 }   
134                 allText = false;
135                 cb("\n");
136                 for (j = 0; j < depth; j++) {
137                   // &#166 is just a vertical line
138                   cb("  ");
139                 }               
140                 
141                     
142                 // Recursively traverse the tree structure of the child node
143                 this.traverseDOMTree(cb, currentElementChild, depth+1);
144                 i++;
145                 currentElementChild=currentElement.childNodes[i];
146             }
147             if (!allText) {
148                 // The remaining code is mostly for formatting the tree
149                 cb("\n");
150                 for (j = 0; j < depth - 1; j++) {
151                   cb("  ");
152                 }     
153             }
154             if (tagName) {
155                 cb("</"+tagName+">");
156             }
157         }
158     },
159
160      
161     
162     frameClearAll : function(isAuto) {
163 //        this.renderObj = { isBuilder : true };
164
165         
166         if (this.panelroot) {
167             this.scroll = this.panelroot.el.getScroll();
168             this.layout.remove('center', this.panelroot);
169             this.panelroot = false;
170         }
171         if (this.dialogroot) {
172             this.dialogroot.remove();
173             this.dialogroot = false;
174         }
175         Roo.select('body > div').remove();
176         
177     },
178     munge : function(cfg, keyname, add_xattr) {
179         keyname = keyname || false;
180         
181         this.renderObj = this.renderObj || {};
182         
183         var xitems = false;
184         if (cfg.items) {
185             xitems = cfg.items;
186             delete cfg.items;
187         }
188         
189         if (typeof(cfg.background) != 'undefined') {
190             cfg.background = false;
191         }
192         
193         
194         for(var p in cfg){
195             // key is not string?!?!?!!?
196             if (typeof(p) != 'string') {
197                 continue;
198             }
199             
200             if (typeof(cfg[p]) == 'object') { // listeners!!!
201                 this.munge(cfg[p], p, add_xattr);
202                 continue;
203             }
204             // SPECIAL - PIPE
205             if (p.charAt(0) == '|' || keyname=='listeners') {
206                 
207                 if (!cfg[p].length) {
208                     delete cfg[p];
209                     continue;
210                 }
211                 var str = cfg[p];
212                 if (str.match(/\s*function/)) {
213                     var btz = str.split('{');
214                     str = btz.shift()  +'{ try {' + btz.join('{') + 
215                         ' catch (e) { Roo.log(e) } }';
216                 }
217                 try {
218                     Roo.log("interpret? " + str);
219                     var _tmp = false;
220                     var _this = this.renderObj; /// fake '_this' object..
221                     // stupid IE can not return objects evaluated..
222                     /**
223                      eval:var:_this  
224                      eval:var:_tmp 
225                     **/
226                     
227                     
228                     eval('_tmp =(' + str + ')');
229                     cfg[p.replace(/^\|/, '')] = _tmp;
230                     if (typeof(_tmp) == 'undefined') {
231                         alert(cfg[p]);
232                     }
233                    
234                 } catch(e) {  console.log('Error evaluating: '  + str); };
235                 //if (p.charAt(0) == '|' ) {
236                 //    delete cfg[p];
237                 //}
238                     
239                 
240                 continue;
241             }
242             // skip '*'
243             if ((p.charAt(0) == '*') || (p.charAt(0) == '+')) {
244                 delete cfg[p];
245                 continue;
246             }
247             // normal..
248               
249         }
250         
251         // add xattr data?
252         if (add_xattr) {
253             
254             if(typeof(cfg.xattr) != 'undefined'){
255                 
256                 cfg.xattr.xtype = cfg['|xns'] + '.' + cfg.xtype;
257             }else{
258                 cfg.xattr = {
259                     xtype : cfg['|xns'] + '.' + cfg.xtype 
260                 };
261             }
262             
263         }
264         
265         
266         
267         // now for all the children.. (items)
268         if (xitems === false) {
269             return;
270         }
271         cfg.items = [];
272         for (var i = 0; i < xitems.length; i++) {
273             // if +builderhide set !!!! drop it!!
274             
275             
276             var xi = xitems[i];
277             if (typeof(xi['*prop']) != 'undefined') {
278                 var pr = xi['*prop'];
279                 this.munge(xi, false, add_xattr);
280                 // if prop is an array - then it's items are really the value..
281                 if (pr.match(/\[\]$/)) {
282                     pr = pr.replace(/\[\]$/, '');
283                     if (typeof(cfg[pr]) == 'undefined') {
284                         cfg[pr] = [];
285                     }
286                     cfg[pr].push(xi);
287                     continue;
288                 }
289                 if (xi.xtype && xi.xtype  == 'Array') {
290                     cfg[pr] = xi.items;
291                 } else {
292                     cfg[pr] = xi;
293                 }
294                 
295                 
296                 continue;
297             }
298             this.munge(xi, false, add_xattr);
299             cfg.items.push(xi);
300         }
301         
302         if (cfg.items.length == 0) {
303             delete cfg.items;
304         }
305         // remove listeners if there are none..
306         if (typeof(cfg['listeners']) != 'undefined') {
307             var n =0;
308             for (var i in cfg.listeners) { n++; }
309             if (!n) {
310                 delete cfg['listeners'];
311             }
312             
313         }
314         
315         if (typeof(cfg.id) != 'undefined') {
316             cfg.id = 'pman-dyn-' + cfg.id;
317         }
318             
319             
320     },
321     toJS : function(n)
322     {
323     
324         if (!n) {
325             return Pman.Builder.Tree.toJS(Pman.Tab.BuilderTree.tree.root);
326         }
327    
328         var _this = this;
329         var ret = Pman.Builder.Tree.cloneConfig(n.elConfig);
330         
331         // flag to prevent rendering..
332         if ((typeof(ret['+buildershow']) != 'undefined') && !ret['+buildershow']) {
333             return false;
334         }
335     
336         ret.id = typeof(ret.id) == 'undefined' ? 'builder-' + n.id : ret.id;
337     
338         if (n.childNodes.length) {
339             ret.items = [];
340             n.eachChild(function(cn) {
341                 var add = _this.toJS(cn);
342                 if (add === false) {
343                     return;
344                 }
345                 
346                 
347                 ret.items.push(add);
348             });
349                 
350         }
351         return ret;
352     },
353
354     redraw : function(isAuto)
355     {
356         this.container.el.select('iframe',true).first().setSize(this.panel.el.getSize());
357  
358        // return;
359         // top level is not relivant
360
361 //          var btop =  Pman.Tab.BuilderTop2;
362   //      if (isAuto && btop.redrawBtn  && !btop.redrawBtn.auto) {
363     //        return; /// auto redraw is turned off..
364       //  }
365         
366         this.clearAll(isAuto);
367         
368         var cfg =  this.toJS();
369         
370         this.win().Pman.Builder.View.draw( cfg );
371         
372     },
373     draw :function(cfg)
374     {
375         Roo.log(cfg);
376         
377         if (!cfg.items[0]) {
378             return;
379         }
380         
381         
382         this.munge(cfg.items[0],false , true );
383         
384         Roo.log(cfg);
385         //  return;
386         // we draw either a dialog or a tab..
387         
388         if (cfg.items[0].xtype == 'LayoutDialog') {
389             
390             cfg.items[0].modal = false;
391             var xy  = this.el.getXY();
392             cfg.items[0].x = xy[0];
393             cfg.items[0].y = xy[1];
394             cfg.items[0].constraintoviewport = false;
395             
396             this.dialogroot = Roo.get( this.doc).createChild();
397             try { 
398                 this.dialog = new Roo[cfg.items[0].xtype](this.dialogroot, cfg.items[0]);
399               //  this.dialog.el.on('click', this.panelClick, this);
400                 this.dialog.show();
401                 var dlg = this.dialog;
402                 (function () {
403                     dlg.moveTo(xy[0], xy[1]);
404                 }).defer(100);
405             } catch(e) {
406                 Roo.log("Error rendering dialog: " + e.toString());
407                 Roo.log(e);
408             }
409             return;
410             
411             
412         }
413         if (cfg.items[0]['|xns'] == 'Roo.bootstrap') {
414             
415             if (cfg.items[0].xtype =='Modal' ) {
416                 this.bootstrapModal = Roo.factory(cfg.items[0]);
417                 this.bootstrapModal.show();
418                 return;
419             }
420             Roo.log("bootstrap build!?");
421             var top = new Roo.bootstrap.Body({});
422             top.onRender(false,false);
423             
424             this.bootstrapModal = top.addxtype(cfg.items[0]);
425             
426             this.applyFlexy(top);
427             
428             
429             
430             return;
431         }
432         
433         
434         
435         // should we render this into a dialog???
436              // force center region..
437         cfg.items[0].region = 'center';
438         cfg.items[0].background = false;
439         
440         try {
441             
442             cfg.parent = '#';
443             
444             
445             this.panelroot = this.layout.addxtype(cfg.items[0]);
446         
447         } catch(e) {
448             Roo.log("Error rendering: " + e.toString());
449             Roo.log(e);
450         }
451         //this.highlightElement(Pman.Tab.BuilderTree.currentNode);
452         
453         if (this.panelroot && this.panelroot.el) {
454                 this.panelroot.el.scrollTo('top', 0);
455                 this.panelroot.el.scrollTo('left', 0);
456             
457         }
458     },
459     frameUpdateTheme: function(name)
460     {
461          return this.win().Pman.Builder.View.updateTheme(name);  
462     },
463     updateTheme : function(name)
464     {
465        Roo.select('head link[rel=stylesheet]').each(function(e) {
466             if (!e.dom.href.match(/bootstrap\.\min.css$/)) {
467                 return;
468             }
469             e.dom.setAttribute('href', rootURL +'/themes/' + name + '/bootstrap.min.css' );
470             
471         
472        });
473     },
474     
475     applyFlexy: function(tree)
476     {
477         if (typeof(tree['flexy:foreach']) != 'undefined') {
478             tree.el.attr('flexy:foreach', tree['flexy:foreach']);
479         }
480         if (typeof(tree['flexy:if']) != 'undefined') {
481             tree.el.attr('flexy:if', tree['flexy:if']);
482         }
483         if (typeof(tree['flexy:nameuses']) != 'undefined') {
484             (tree.inputEl() !== 'undefined') ? tree.inputEl().attr('flexy:nameuses', tree['flexy:nameuses']) : tree.el.attr('flexy:nameuses', tree['flexy:nameuses']);
485         }
486         if (!tree.items || !tree.items.length) { return; }
487         
488         for (var i = 0; i < tree.items.length; i++){
489             this.applyFlexy(tree.items[i]);
490         }
491     }
492     
493     
494     
495 }