Fix #8000 - left tree and file open
[roobuilder] / src / Builder4 / WindowLeftTree.vala
1 static Xcls_WindowLeftTree  _WindowLeftTree;
2
3 public class Xcls_WindowLeftTree : Object
4 {
5         public Gtk.Box el;
6         private Xcls_WindowLeftTree  _this;
7
8         public static Xcls_WindowLeftTree singleton()
9         {
10                 if (_WindowLeftTree == null) {
11                     _WindowLeftTree= new Xcls_WindowLeftTree();
12                 }
13                 return _WindowLeftTree;
14         }
15         public Xcls_viewwin viewwin;
16         public Xcls_view view;
17         public Xcls_keystate keystate;
18         public Xcls_drop drop;
19         public Xcls_selmodel selmodel;
20         public Xcls_model model;
21         public Xcls_maincol maincol;
22         public Xcls_LeftTreeMenu LeftTreeMenu;
23
24                 // my vars (def)
25         public signal bool before_node_change ();
26         public Xcls_MainWindow? main_window;
27         public int last_error_counter;
28         public signal void changed ();
29         public signal void node_selected (JsRender.Node? node);
30
31         // ctor
32         public Xcls_WindowLeftTree()
33         {
34                 _this = this;
35                 this.el = new Gtk.Box( Gtk.Orientation.VERTICAL, 0 );
36
37                 // my vars (dec)
38                 this.main_window = null;
39                 this.last_error_counter = -1;
40
41                 // set gobject values
42                 this.el.hexpand = true;
43                 this.el.vexpand = true;
44                 var child_1 = new Xcls_ListView2( _this );
45                 child_1.ref();
46                 this.el.append( child_1.el );
47                 new Xcls_viewwin( _this );
48                 this.el.append( _this.viewwin.el );
49         }
50
51         // user defined functions
52         public void updateErrors () {
53                 var file = this.getActiveFile();
54                 var ar = file.getErrors();
55                         if (ar.size < 1) {
56                         if (this.last_error_counter != file.error_counter) {
57                                 this.removeErrors();
58                         }
59                 
60                         this.last_error_counter = file.error_counter ;
61         
62                         return;
63                 }
64                 if (this.last_error_counter == file.error_counter) {
65                         return;
66                 }
67                 this.removeErrors();
68                 
69                 foreach(var diag in ar) { 
70                 
71                          
72         //        print("get inter\n");
73                     var node= file.lineToNode( (int)diag.range.start.line) ;
74                     if (node == null) {
75                         continue;
76                 }
77                 var row = _this.model.nodeToRow(node);
78                 if (row < 0) {
79                         continue;
80                         }
81                 var w = this.view.getWidgetAtRow(row);
82                 if (w == null) {
83                         return;
84                         }
85                         // always show errors.
86                         var ed = diag.category.down();
87                         if (ed != "err" && w.has_css_class("node-err")) {
88                                 continue;
89                         }
90                         if (ed == "err" && w.has_css_class("node-warn")) {
91                                 w.remove_css_class("node-warn");
92                         }
93                         if (ed == "err" && w.has_css_class("node-depr")) {
94                                 w.remove_css_class("node-depr");
95                         }
96                         if (!w.has_css_class("node-"+ ed)) {
97                                 w.add_css_class("node-" + ed);
98                         }
99                         
100                 }
101                 
102         }
103         public void onresize () {
104          
105                  
106                 //GLib.debug("Got allocation width of scrolled view %d", allocation.width );
107         //      _this.maincol.el.set_max_width( _this.viewwin.el.get_width()  - 32 );
108         }
109         public void removeErrors () {
110                 var  child = this.view.el.get_first_child(); 
111          
112                 var reading_header = true;
113          
114                 while (child != null) {
115                         //GLib.debug("Got %s", child.get_type().name());
116                    
117                    if (reading_header) {
118                                 
119         
120                                 if (child.get_type().name() != "GtkColumnListView") {
121                                    
122                                         child = child.get_next_sibling();
123                                         continue;
124                                 }
125                                 // should be columnlistview
126                                 child = child.get_first_child(); 
127                          
128                          
129                                 
130                                 reading_header = false;
131                                  
132                     }
133                     
134                         if (child.has_css_class("node-err")) {
135                                 child.remove_css_class("node-err");
136                         }
137                         if (child.has_css_class("node-warn")) {
138                                 child.remove_css_class("node-warn");
139                         }
140                         
141                         if (child.has_css_class("node-depr")) {
142                                 child.remove_css_class("node-depr");
143                         }
144                         
145                 child = child.get_next_sibling(); 
146                 }
147                 //GLib.debug("Rturning null");
148              
149         }
150         public JsRender.Node? getActiveElement () { // return path to actie node.
151         
152              
153                 return _this.selmodel.getSelectedNode();
154             
155             
156         }
157         public JsRender.JsRender getActiveFile () {
158             return this.main_window.windowstate.file;
159         }
160         public class Xcls_ListView2 : Object
161         {
162                 public Gtk.ListView el;
163                 private Xcls_WindowLeftTree  _this;
164
165
166                         // my vars (def)
167
168                 // ctor
169                 public Xcls_ListView2(Xcls_WindowLeftTree _owner )
170                 {
171                         _this = _owner;
172                         var child_1 = new Xcls_SignalListItemFactory3( _this );
173                         child_1.ref();
174                         this.el = new Gtk.ListView( null, child_1.el );
175
176                         // my vars (dec)
177
178                         // set gobject values
179                 }
180
181                 // user defined functions
182         }
183         public class Xcls_SignalListItemFactory3 : Object
184         {
185                 public Gtk.SignalListItemFactory el;
186                 private Xcls_WindowLeftTree  _this;
187
188
189                         // my vars (def)
190
191                 // ctor
192                 public Xcls_SignalListItemFactory3(Xcls_WindowLeftTree _owner )
193                 {
194                         _this = _owner;
195                         this.el = new Gtk.SignalListItemFactory();
196
197                         // my vars (dec)
198
199                         // set gobject values
200                 }
201
202                 // user defined functions
203         }
204
205
206         public class Xcls_viewwin : Object
207         {
208                 public Gtk.ScrolledWindow el;
209                 private Xcls_WindowLeftTree  _this;
210
211
212                         // my vars (def)
213
214                 // ctor
215                 public Xcls_viewwin(Xcls_WindowLeftTree _owner )
216                 {
217                         _this = _owner;
218                         _this.viewwin = this;
219                         this.el = new Gtk.ScrolledWindow();
220
221                         // my vars (dec)
222
223                         // set gobject values
224                         this.el.vscrollbar_policy = Gtk.PolicyType.AUTOMATIC;
225                         this.el.has_frame = true;
226                         this.el.hexpand = true;
227                         this.el.vexpand = true;
228                         this.el.hscrollbar_policy = Gtk.PolicyType.AUTOMATIC;
229                         new Xcls_view( _this );
230                         this.el.child = _this.view.el;
231                         new Xcls_LeftTreeMenu( _this );
232                 }
233
234                 // user defined functions
235         }
236         public class Xcls_view : Object
237         {
238                 public Gtk.ColumnView el;
239                 private Xcls_WindowLeftTree  _this;
240
241
242                         // my vars (def)
243                 public bool blockChanges;
244                 public bool headers_visible;
245                 public string lastEventSource;
246                 public bool button_is_pressed;
247                 public Gtk.CssProvider css;
248                 public JsRender.Node? dragNode;
249
250                 // ctor
251                 public Xcls_view(Xcls_WindowLeftTree _owner )
252                 {
253                         _this = _owner;
254                         _this.view = this;
255                         new Xcls_selmodel( _this );
256                         this.el = new Gtk.ColumnView( _this.selmodel.el );
257
258                         // my vars (dec)
259                         this.blockChanges = false;
260                         this.headers_visible = false;
261                         this.lastEventSource = "";
262                         this.button_is_pressed = false;
263                         this.dragNode = null;
264
265                         // set gobject values
266                         this.el.name = "left-tree-view";
267                         this.el.hexpand = false;
268                         this.el.vexpand = true;
269                         var child_2 = new Xcls_GestureClick6( _this );
270                         child_2.ref();
271                         this.el.add_controller(  child_2.el );
272                         var child_3 = new Xcls_GestureClick7( _this );
273                         child_3.ref();
274                         this.el.add_controller(  child_3.el );
275                         var child_4 = new Xcls_DragSource8( _this );
276                         child_4.ref();
277                         this.el.add_controller(  child_4.el );
278                         var child_5 = new Xcls_EventControllerKey9( _this );
279                         child_5.ref();
280                         this.el.add_controller(  child_5.el );
281                         new Xcls_keystate( _this );
282                         this.el.add_controller(  _this.keystate.el );
283                         new Xcls_drop( _this );
284                         this.el.add_controller(  _this.drop.el );
285                         new Xcls_maincol( _this );
286                         this.el.append_column ( _this.maincol.el  );
287                         var child_9 = new Xcls_ColumnViewColumn16( _this );
288                         child_9.ref();
289                         this.el.append_column ( child_9.el  );
290
291                         // init method
292
293                         {
294                          
295                           this.css = new Gtk.CssProvider();
296                         //      try {
297                                         this.css.load_from_string("
298                         #left-tree-view { font-size: 12px;}     
299                         .drag-over  { background-color:#88a3bc; }
300                         .drag-below  {   
301                          border-bottom-width: 5px; 
302                          border-bottom-style: solid;
303                          border-bottom-color: #88a3bc;
304                         }
305                         .drag-above  {
306                          border-top-width: 5px;
307                          border-top-style: solid;
308                          border-top-color: #88a3bc;
309                         }
310                         .node-err  {
311                          border-top-width: 5px;
312                          border-top-style: solid;
313                          border-top-color: red;
314                          border-bottom-width: 5px; 
315                          border-bottom-style: solid;
316                          border-bottom-color: red;
317                         }
318                         .node-warn  {
319                          border-top-width: 5px;
320                          border-top-style: solid;
321                          border-top-color: #ABF4EB;
322                          border-bottom-width: 5px; 
323                          border-bottom-style: solid;
324                          border-bottom-color: #ABF4EB;
325                         }
326                         .node-depr  {
327                          border-top-width: 5px;
328                          border-top-style: solid;
329                          border-top-color: #EEA9FF;
330                          border-bottom-width: 5px; 
331                          border-bottom-style: solid;
332                          border-bottom-color: #EEA9FF;
333                         }
334                         
335                         #left-tree-view indent {
336                         -gtk-icon-size : 2px;
337                         }
338                         #left-tree-view indent:nth-last-child(2)  {
339                         min-width: 24px;
340                         }
341                         ");
342                         
343                                 Gtk.StyleContext.add_provider_for_display(
344                                         this.el.get_display(),
345                                         this.css,
346                                         Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION
347                                 );
348                                 
349                                   
350                         }
351                 }
352
353                 // user defined functions
354                 public Gtk.Widget? getWidgetAtRow (uint row) {
355                 /*
356                         
357                 from            https://discourse.gnome.org/t/gtk4-finding-a-row-data-on-gtkcolumnview/8465
358                         var colview = gesture.widget;
359                         var line_no = check_list_widget(colview, x,y);
360                          if (line_no > -1) {
361                                 var item = colview.model.get_item(line_no);
362                                  
363                         }
364                         */
365                                 //GLib.debug("Get Widget At Row %d", (int)row);
366                         var  child = this.el.get_first_child(); 
367                         var line_no = -1; 
368                         var reading_header = true;
369                          
370                         while (child != null) {
371                                         GLib.debug("Got %s", child.get_type().name());
372                            
373                            if (reading_header) {
374                                                 
375                 
376                                                 if (child.get_type().name() != "GtkColumnListView") {
377                                                    
378                                                         child = child.get_next_sibling();
379                                                         continue;
380                                                 }
381                                                 // should be columnlistview
382                                                 child = child.get_first_child(); 
383                                          
384                                          
385                                                 
386                                                 reading_header = false;
387                                                 continue;
388                                     }
389                                     
390                                   
391                             
392                                     line_no++;
393                                         if (line_no == row) {
394                                                 //GLib.debug("Returning widget %s", child.get_type().name());
395                                             return (Gtk.Widget)child;
396                                     }
397                                 child = child.get_next_sibling(); 
398                         }
399                                 //GLib.debug("Rturning null");
400                         return null;
401                 
402                  }
403                 public int getColAt (double x,  double y) {
404                 /*
405                         
406                 from            https://discourse.gnome.org/t/gtk4-finding-a-row-data-on-gtkcolumnview/8465
407                           
408                         */
409                                 //Gtk.Allocation alloc = { 0, 0, 0, 0 };
410                                 //GLib.debug("Cehck %d, %d", x,y);
411                         var  child = this.el.get_first_child(); 
412                          
413                         var col = 0;
414                         var offx = 0;
415                         while (child != null) {
416                                         
417                                         if (child.get_type().name() == "GtkColumnViewRowWidget") {
418                                                 child = child.get_first_child();
419                                                 continue;
420                                         }
421                                         
422                                         //child.get_allocation(out alloc);
423                                         if (x <  (child.get_width() + offx)) {
424                                                 return col;
425                                         }
426                                         return 1;
427                                         //offx += child.get_width();
428                                         //col++;
429                                         //child = child.get_next_sibling();
430                                 }
431                              
432                                           
433                         return -1;
434                 
435                  }
436                 public int getRowAt (double x,  double in_y, out string pos) {
437                 
438                 
439                          
440                 
441                 /*
442                         
443                 from            https://discourse.gnome.org/t/gtk4-finding-a-row-data-on-gtkcolumnview/8465
444                         var colview = gesture.widget;
445                         var line_no = check_list_widget(colview, x,y);
446                          if (line_no > -1) {
447                                 var item = colview.model.get_item(line_no);
448                                  
449                         }
450                         */
451                                  
452                                 
453                                 //GLib.debug("offset = %d  y = %d", (int) voff, (int) in_y);
454                         var y = in_y + _this.viewwin.el.vadjustment.value; 
455                         var  child = this.el.get_first_child(); 
456                         //Gtk.Allocation alloc = { 0, 0, 0, 0 };
457                         var line_no = -1; 
458                         var reading_header = true;
459                         var real_y = 0;
460                         var header_height  = 0;
461                         pos = "none";
462                         var h = 0;
463                         while (child != null) {
464                                         //GLib.debug("Got %s", child.get_type().name());
465                             if (reading_header) {
466                                                 
467                 
468                                                 if (child.get_type().name() != "GtkColumnListView") {
469                                                 h += child.get_height();
470                                                         child = child.get_next_sibling();
471                                                         continue;
472                                                 }
473                                                 // should be columnlistview
474                                                 child = child.get_first_child(); 
475                                             //GLib.debug("header height=%d", h);
476                                                 header_height =  h;
477                                                 
478                                                 reading_header = false;
479                                                 continue;
480                                                 
481                                 }
482                                 
483                                     if (child.get_type().name() != "GtkColumnViewRowWidget") {
484                                     child = child.get_next_sibling();
485                                     continue;
486                                     }
487                                     
488                                         if (y < header_height) {
489                                         return -1;
490                                 }
491                                     
492                                     line_no++;
493                                         var hh = child.get_height();
494                                         
495                                         if (child.has_css_class("node-err") || 
496                                                 child.has_css_class("node-warn") || 
497                                                 child.has_css_class("node-depr")) {
498                                                 hh += 10;
499                                         
500                                         }
501                                         //child.get_allocation(out alloc);
502                                         //GLib.debug("got cell xy = %d,%d  w,h= %d,%d", alloc.x, alloc.y, alloc.width, alloc.height);
503                                         //GLib.debug("row %d y= %d %s", line_no, (int) (header_height + alloc.y),
504                                         
505                                         //      child.visible ? "VIS" : "hidden");
506                 
507                                     if (y >  (header_height + real_y) && y <= (header_height +  real_y + hh) ) {
508                                         if (y > ( header_height + real_y + (hh * 0.8))) {
509                                                 pos = "below";
510                                         } else if (y > ( header_height + real_y + (hh * 0.2))) {
511                                                 pos = "over";
512                                         } else {
513                                                 pos = "above";
514                                                 }
515                                          GLib.debug("getRowAt return : %d, %s", line_no, pos);
516                                             return line_no;
517                                     }
518                  
519                 
520                                     if (real_y + hh > y) {
521                                         return -1;
522                                 }
523                                 real_y += hh;
524                                 child = child.get_next_sibling(); 
525                         }
526                         return -1;
527                 
528                  }
529                 public Gtk.Widget? getWidgetAt (double x,  double in_y) {
530                 /*
531                         
532                 from            https://discourse.gnome.org/t/gtk4-finding-a-row-data-on-gtkcolumnview/8465
533                         var colview = gesture.widget;
534                         var line_no = check_list_widget(colview, x,y);
535                          if (line_no > -1) {
536                                 var item = colview.model.get_item(line_no);
537                                  
538                         }
539                         */
540                         var y = in_y + _this.viewwin.el.vadjustment.value; 
541                         var  child = this.el.get_first_child(); 
542                         //Gtk.Allocation alloc = { 0, 0, 0, 0 };
543                         var line_no = -1; 
544                         var reading_header = true;
545                         var curr_y = 0;
546                         var header_height  = 0;
547                         var h = 0;
548                         while (child != null) {
549                                         //GLib.debug("Got %s", child.get_type().name());
550                                 if (reading_header) {
551                                                 
552                 
553                                                 if (child.get_type().name() != "GtkColumnListView") {
554                                                 h += child.get_height();
555                                                         child = child.get_next_sibling();
556                                                         continue;
557                                                 }
558                                                 // should be columnlistview
559                                                 child = child.get_first_child(); 
560                                             GLib.debug("header height=%d", h);
561                                                 header_height =  h;
562                                                 
563                                                 reading_header = false;
564                                                 continue;
565                                 }
566                                     line_no++;
567                 
568                                         if (y < header_height) {
569                                         return null;
570                                 }
571                 
572                                         var hh = child.get_height();
573                                         //GLib.debug("got cell xy = %d,%d  w,h= %d,%d", alloc.x, alloc.y, alloc.width, alloc.height);
574                                         if (child.has_css_class("node-err") || 
575                                                 child.has_css_class("node-warn") || 
576                                                 child.has_css_class("node-depr")) {
577                                                 hh += 10;
578                                         
579                                         }       
580                                     if (y > curr_y && y <= header_height + hh + curr_y ) {
581                                             return (Gtk.Widget)child;
582                                     }
583                                     curr_y +=  hh ;
584                 
585                                     if (curr_y > y) {
586                                         return null;
587                                 }
588                                 child = child.get_next_sibling(); 
589                         }
590                         return null;
591                 
592                  }
593         }
594         public class Xcls_GestureClick6 : Object
595         {
596                 public Gtk.GestureClick el;
597                 private Xcls_WindowLeftTree  _this;
598
599
600                         // my vars (def)
601
602                 // ctor
603                 public Xcls_GestureClick6(Xcls_WindowLeftTree _owner )
604                 {
605                         _this = _owner;
606                         this.el = new Gtk.GestureClick();
607
608                         // my vars (dec)
609
610                         // set gobject values
611
612                         //listeners
613                         this.el.released.connect( (n_press, x, y) => {
614                          
615                             _this.view.button_is_pressed = false;
616                         
617                         
618                         });
619                         this.el.pressed.connect( (n_press, x, y) => {
620                          
621                             //console.log("button press?");
622                             
623                             //this.el.set_state(Gtk.EventSequenceState.CLAIMED);
624                         
625                         
626                             
627                             _this.view.button_is_pressed = true;
628                               
629                             _this.view.lastEventSource = "tree";
630                             if (! _this.before_node_change() ) {
631                                 GLib.debug("before_node_change return false");
632                                return ;
633                             }
634                             
635                                  // nothing there -show dialog
636                             if (_this.model.el.get_n_items() < 1) {
637                                     _this.main_window.windowstate.showAddObject(_this.view.el, null);
638                                 GLib.debug("no items");
639                                     return ;
640                             }
641                             string pos;
642                             var row = _this.view.getRowAt(x,y, out pos );
643                             if (row < 0) {
644                                     GLib.debug("no row selected items");
645                                     return;
646                             }
647                             
648                             var node =   _this.selmodel.getNodeAt(row);
649                             if (node == null) {
650                                 GLib.warning("No node found at row %d", row);
651                                 return;
652                                 }
653                         
654                              
655                              
656                             if (_this.view.getColAt(x,y) > 0 ) {
657                                     GLib.debug("add colum clicked.");
658                                 var fqn = node.fqn();
659                                 var cn = _this.main_window.windowstate.project.palete.getChildList(fqn, false);
660                                         if (cn.size < 1) {
661                                                 return ;
662                                         }
663                         
664                                         _this.main_window.windowstate.leftTreeBeforeChange();
665                                         //_this.view.el.get_selection().select_path(res);
666                                         GLib.debug("Button Pressed - start show window");
667                                         _this.main_window.windowstate.showAddObject(_this.view.el, node);
668                                         GLib.debug("Button Pressed - finsihed show window");
669                                 return ;
670                                 }
671                             
672                                  
673                              
674                         });
675                 }
676
677                 // user defined functions
678         }
679
680         public class Xcls_GestureClick7 : Object
681         {
682                 public Gtk.GestureClick el;
683                 private Xcls_WindowLeftTree  _this;
684
685
686                         // my vars (def)
687
688                 // ctor
689                 public Xcls_GestureClick7(Xcls_WindowLeftTree _owner )
690                 {
691                         _this = _owner;
692                         this.el = new Gtk.GestureClick();
693
694                         // my vars (dec)
695
696                         // set gobject values
697                         this.el.button = 3;
698
699                         //listeners
700                         this.el.pressed.connect( (n_press, x, y) => {
701                         
702                                 
703                                   
704                                  
705                             if (_this.model.el.get_n_items() < 1) {
706                          
707                                 GLib.debug("no items");
708                                     return ;
709                             }
710                             string pos;
711                             var row = _this.view.getRowAt(x,y, out pos );
712                             if (row < 0) {
713                                     GLib.debug("no row selected items");
714                                     return;
715                             }
716                             
717                             var node =   _this.selmodel.getNodeAt(row);
718                             if (node == null) {
719                                 GLib.warning("No node found at row %d", row);
720                                 return;
721                                 }
722                                 
723                                 
724                                 _this.model.selectNode(node);
725                              
726                              
727                              
728                                 GLib.debug("Prssed %d", (int)  this.el.get_current_button());
729                                 //_this.deletemenu.el.set_parent(_this.view.el);
730                                 _this.LeftTreeMenu.el.set_parent(_this.view.el);
731                                 
732                                 
733                                 //Gtk.Allocation rect;
734                                 //_this.view.el.get_allocation(out rect);
735                                 //_this.deletemenu.el.set_has_arrow(false);
736                                 _this.LeftTreeMenu.el.set_position(Gtk.PositionType.BOTTOM); 
737                                 
738                                         
739                                 _this.LeftTreeMenu.el.set_offset( 
740                                                 (int)x  ,
741                                                 (int)y - (int)_this.view.el.get_height());
742                         
743                             _this.LeftTreeMenu.el.popup();
744                               
745                         });
746                 }
747
748                 // user defined functions
749         }
750
751         public class Xcls_DragSource8 : Object
752         {
753                 public Gtk.DragSource el;
754                 private Xcls_WindowLeftTree  _this;
755
756
757                         // my vars (def)
758
759                 // ctor
760                 public Xcls_DragSource8(Xcls_WindowLeftTree _owner )
761                 {
762                         _this = _owner;
763                         this.el = new Gtk.DragSource();
764
765                         // my vars (dec)
766
767                         // set gobject values
768                         this.el.actions = Gdk.DragAction.COPY   | Gdk.DragAction.MOVE   ;
769
770                         //listeners
771                         this.el.drag_cancel.connect( (drag, reason) => {
772                         
773                                 _this.view.dragNode = null;
774                                 return true;
775                         });
776                         this.el.prepare.connect( (x, y) => {
777                         
778                                 
779                                 
780                         ///     ( drag_context, data, info, time) => {
781                                     
782                         
783                                 //print("drag-data-get");
784                                 var ndata = _this.selmodel.getSelectedNode();
785                                 if (ndata == null) {
786                                         GLib.debug("return empty string - no selection..");
787                                         return null;
788                                  
789                                 }
790                         
791                           
792                                 //data.set_text(tp,tp.length);   
793                         
794                                 var     str = ndata.toJsonString();
795                                 GLib.debug("prepare  store: %s", str);
796                                 GLib.Value ov = GLib.Value(typeof(string));
797                                 ov.set_string(str);
798                                 var cont = new Gdk.ContentProvider.for_value(ov);
799                             /*
800                                 GLib.Value v = GLib.Value(typeof(string));
801                                 //var str = drop.read_text( [ "text/plain" ] 0);
802                                  
803                                         cont.get_value(ref v);
804                                  
805                                 }
806                                 GLib.debug("set %s", v.get_string());
807                               */  
808                                 return cont;
809                                  
810                                  
811                         });
812                         this.el.drag_begin.connect( ( drag )  => {
813                                 GLib.debug("SOURCE: drag-begin");
814                                  
815                             // find what is selected in our tree...
816                             var data = _this.selmodel.getSelectedNode();
817                                 if (data == null) {
818                                         return  ;
819                                 }
820                                 _this.view.dragNode = data;
821                             var xname = data.fqn();
822                             GLib.debug ("XNAME  IS %s", xname);
823                         
824                                 var widget = _this.view.getWidgetAtRow(_this.selmodel.el.selected);
825                                 
826                                 
827                             var paintable = new Gtk.WidgetPaintable(widget);
828                             this.el.set_icon(paintable, 0,0);
829                                     
830                          
831                         });
832                         this.el.drag_end.connect( (drag, delete_data) => {
833                         
834                         _this.view.dragNode = null;
835                         });
836                 }
837
838                 // user defined functions
839         }
840
841         public class Xcls_EventControllerKey9 : Object
842         {
843                 public Gtk.EventControllerKey el;
844                 private Xcls_WindowLeftTree  _this;
845
846
847                         // my vars (def)
848
849                 // ctor
850                 public Xcls_EventControllerKey9(Xcls_WindowLeftTree _owner )
851                 {
852                         _this = _owner;
853                         this.el = new Gtk.EventControllerKey();
854
855                         // my vars (dec)
856
857                         // set gobject values
858
859                         //listeners
860                         this.el.key_pressed.connect( (keyval, keycode, state) => {
861                         
862                          
863                         
864                                 if (keyval != Gdk.Key.Delete && keyval != Gdk.Key.BackSpace)  {
865                                         return true;
866                                 }
867                         
868                                 _this.model.deleteSelected();
869                                 return true;
870                         
871                         });
872                 }
873
874                 // user defined functions
875         }
876
877         public class Xcls_keystate : Object
878         {
879                 public Gtk.EventControllerKey el;
880                 private Xcls_WindowLeftTree  _this;
881
882
883                         // my vars (def)
884                 public int is_shift;
885
886                 // ctor
887                 public Xcls_keystate(Xcls_WindowLeftTree _owner )
888                 {
889                         _this = _owner;
890                         _this.keystate = this;
891                         this.el = new Gtk.EventControllerKey();
892
893                         // my vars (dec)
894                         this.is_shift = 0;
895
896                         // set gobject values
897
898                         //listeners
899                         this.el.key_released.connect( (keyval, keycode, state) => {
900                                 GLib.debug("key release %d, %d, %d" , (int) keyval, (int)  keycode, state);
901                                 if (keyval == Gdk.Key.Shift_L || keyval == Gdk.Key.Shift_R) {
902                                         this.is_shift = 0;
903                                 }
904                                 //GLib.debug("set state %d , shift = %d", (int)this.el.get_current_event_state(), Gdk.ModifierType.SHIFT_MASK);
905                         
906                         
907                          
908                         });
909                         this.el.key_pressed.connect( (keyval, keycode, state) => {
910                         
911                                 if (keyval == Gdk.Key.Shift_L || keyval == Gdk.Key.Shift_R) {
912                                         this.is_shift = 1;
913                                 }
914                                 return true;
915                         });
916                 }
917
918                 // user defined functions
919         }
920
921         public class Xcls_drop : Object
922         {
923                 public Gtk.DropTarget el;
924                 private Xcls_WindowLeftTree  _this;
925
926
927                         // my vars (def)
928                 public Gtk.Widget? highlightWidget;
929                 public JsRender.Node? lastDragNode;
930                 public string lastDragString;
931
932                 // ctor
933                 public Xcls_drop(Xcls_WindowLeftTree _owner )
934                 {
935                         _this = _owner;
936                         _this.drop = this;
937                         this.el = new Gtk.DropTarget ( typeof(string) ,
938                 Gdk.DragAction.COPY   | Gdk.DragAction.MOVE   );
939
940                         // my vars (dec)
941                         this.highlightWidget = null;
942                         this.lastDragNode = null;
943                         this.lastDragString = "";
944
945                         // set gobject values
946
947                         //listeners
948                         this.el.accept.connect( (drop) => {
949                         
950                                 GLib.debug("got DropTarget:accept");
951                          
952                         // NOT REALLY NEEDED? = put stuff in drop?
953                         
954                         
955                         /* (  ctx, x, y, time)  => {
956                               //Seed.print("TARGET: drag-drop");
957                            
958                            
959                             var src = Gtk.drag_get_source_widget(ctx);
960                              
961                            if (src != this.el) {
962                            
963                             
964                                
965                                this.drag_in_motion = false;   
966                                     // request data that will be recieved by the recieve...              
967                                 Gtk.drag_get_data
968                                 (
969                                         this.el,         // will receive 'drag-data-received' signal 
970                                         ctx,        // represents the current state of the DnD 
971                                         Gdk.Atom.intern("application/json",true),    // the target type we want 
972                                         time            // time stamp 
973                                 );
974                         
975                                  
976                                 // No target offered by source => error
977                            
978                         
979                                  return  false;
980                              }
981                              
982                              // handle drop around self..
983                              
984                                           
985                                     
986                             //print("GETTING POS");
987                             var  targetData = "";
988                             
989                             Gtk.TreePath path;
990                             Gtk.TreeViewDropPosition pos;
991                             var isOver = _this.view.el.get_dest_row_at_pos(this.drag_x,this.drag_y, out path, out pos);
992                             
993                             // if there are not items in the tree.. the we have to set isOver to true for anything..
994                             var isEmpty = false;
995                             if (_this.model.el.iter_n_children(null) < 1) {
996                                 print("got NO children?\n");
997                                 isOver = true; //??? 
998                                 isEmpty = true;
999                                 pos = Gtk.TreeViewDropPosition.INTO_OR_AFTER;
1000                             }
1001                             
1002                              
1003                              
1004                             //var action = Gdk.DragAction.COPY;
1005                                 // unless we are copying!!! ctl button..
1006                             
1007                             var action = (ctx.get_actions() & Gdk.DragAction.MOVE) > 0 ?
1008                                          Gdk.DragAction.COPY  : Gdk.DragAction.MOVE ;
1009                                         // Gdk.DragAction.MOVE : Gdk.DragAction.COPY ;
1010                         
1011                               
1012                             if (_this.model.el.iter_n_children(null) < 1) {
1013                                 // no children.. -- asume it's ok..
1014                                 
1015                                 targetData = "|%d|".printf((int)Gtk.TreeViewDropPosition.INTO_OR_AFTER);
1016                                  
1017                                 // continue through to allow drop...
1018                         
1019                             } else {
1020                                         
1021                                         
1022                             
1023                                         
1024                                         
1025                                         //print("ISOVER? " + isOver);
1026                                 if (!isOver) {
1027                                     
1028                                     Gtk.drag_finish (ctx, false, false, time);        // drop failed..
1029                                     return true; // not over apoint!?! - no action on drop or motion..
1030                                 }
1031                                         
1032                                 // drag node is parent of child..
1033                                 //console.log("SRC TREEPATH: " + src.treepath);
1034                                 //console.log("TARGET TREEPATH: " + data.path.to_string());
1035                                 
1036                                 // nned to check a  few here..
1037                                 //Gtk.TreeViewDropPosition.INTO_OR_AFTER
1038                                 //Gtk.TreeViewDropPosition.INTO_OR_BEFORE
1039                                 //Gtk.TreeViewDropPosition.AFTER
1040                                 //Gtk.TreeViewDropPosition.BEFORE
1041                                 
1042                                 // locally dragged items to not really use the 
1043                                 var selection_text = this.dragData;
1044                                 
1045                                 
1046                                 
1047                                 if (selection_text == null || selection_text.length < 1) {
1048                                     //print("Error  - drag selection text returned NULL");
1049                                   
1050                                      Gtk.drag_finish (ctx, false, false, time);        // drop failed..
1051                                      return true; /// -- fixme -- this is not really correct..
1052                                 }                
1053                                         
1054                                         // see if we are dragging into ourself?
1055                                         print ("got selection text of  " + selection_text);
1056                                 
1057                                 var target_path = path.to_string();
1058                                 //print("target_path="+target_path);
1059                         
1060                                 // 
1061                                 if (selection_text  == target_path) {
1062                                     print("self drag ?? == we should perhaps allow copy onto self..\n");
1063                                     
1064                                      Gtk.drag_finish (ctx, false, false, time);        // drop failed..
1065                         
1066                                      return true; /// -- fixme -- this is not really correct..
1067                         
1068                                 }
1069                                         
1070                                 // check that 
1071                                 //print("DUMPING DATA");
1072                                 //console.dump(data);
1073                                 // path, pos
1074                                 
1075                                 //print(data.path.to_string() +' => '+  data.pos);
1076                                 
1077                                 // dropList is a list of xtypes that this node could be dropped on.
1078                                 // it is set up when we start to drag..
1079                                 
1080                                 
1081                                 targetData = _this.model.findDropNodeByPath( path.to_string(), this.dropList, pos);
1082                                     
1083                                 print("targetDAta: " + targetData +"\n");
1084                                 
1085                                 if (targetData.length < 1) {
1086                                     //print("Can not find drop node path");
1087                                      
1088                                     Gtk.drag_finish (ctx, false, false, time);        // drop failed..
1089                                     return true;
1090                                 }
1091                                             
1092                                         
1093                                         
1094                                         // continue on to allow drop..
1095                           }
1096                                 // at this point, drag is not in motion... -- as checked above... - so it's a real drop event..
1097                         
1098                         
1099                              var delete_selection_data = false;
1100                                 
1101                             if (action == Gdk.DragAction.ASK)  {
1102                                 // Ask the user to move or copy, then set the ctx action. 
1103                             }
1104                         
1105                             if (action == Gdk.DragAction.MOVE) {
1106                                 delete_selection_data = true;
1107                             }
1108                               
1109                                         // drag around.. - reorder..
1110                             _this.model.moveNode(targetData, action);
1111                                 
1112                                
1113                                 
1114                                 
1115                                 
1116                                 // we can send stuff to souce here...
1117                         
1118                         
1119                         // do we always say failure, so we handle the reall drop?
1120                             Gtk.drag_finish (ctx, false, false,time); //delete_selection_data, time);
1121                         
1122                             return true;
1123                          
1124                          
1125                          
1126                          
1127                          
1128                          
1129                         }
1130                         */
1131                                 return true;
1132                         });
1133                         this.el.motion.connect( (  x, y) => {
1134                          
1135                                 var is_shift = _this.keystate.is_shift > 0;
1136                                 
1137                                 GLib.debug("shift is    %s", _this.keystate.is_shift > 0 ? "SHIFT" : "-");
1138                                 string pos; // over / before / after..
1139                         
1140                             //GLib.debug("got drag motion");
1141                         
1142                             GLib.Value v = GLib.Value(typeof(string));
1143                                 //var str = drop.read_text( [ "text/plain" ] 0);
1144                                 var cont = this.el.current_drop.get_drag().content ;
1145                                 try {
1146                                         cont.get_value(ref v);
1147                                 } catch (GLib.Error e) {
1148                                     GLib.debug("failed to get drag value");
1149                                         return Gdk.DragAction.COPY;      
1150                                 
1151                                 }
1152                          
1153                                 //GLib.debug("got %s", v.get_string());
1154                                   
1155                                 if (this.lastDragString != v.get_string() || this.lastDragNode == null) {
1156                                         // still dragging same node
1157                          
1158                                         this.lastDragNode = new JsRender.Node(); 
1159                                         this.lastDragNode.loadFromJsonString(v.get_string(), 1);
1160                                 }
1161                             
1162                         
1163                                 var drop_on_to = _this.main_window.windowstate.file.palete().getDropList(
1164                                                         this.lastDragNode.fqn());
1165                              
1166                              string[] str = {};
1167                              foreach(var dp in drop_on_to) {
1168                                 str += dp;
1169                                 }
1170                                 GLib.debug("droplist: %s", string.joinv(", ", str));
1171                              
1172                              
1173                             // if there are not items in the tree.. the we have to set isOver to true for anything..
1174                          
1175                             if (_this.model.el.n_items < 1) {
1176                                 // FIXME check valid drop types?
1177                                 if (drop_on_to.contains("*top")) {
1178                                                 this.addHighlight(_this.view.el, "over");
1179                                         } else {
1180                                                 this.addHighlight(null, "");            
1181                                         }
1182                         
1183                                         return Gdk.DragAction.COPY; // no need to highlight?
1184                              
1185                             }
1186                             
1187                             
1188                                 GLib.debug("check is over");
1189                                  
1190                             // if path of source and dest are inside each other..
1191                             // need to add source info to drag?
1192                             // the fail();
1193                                 var row = _this.view.getRowAt(x,y, out pos);
1194                                 
1195                                 if (row < 0) {
1196                                         this.addHighlight(null, "");    
1197                                         return Gdk.DragAction.COPY;
1198                                 }
1199                                 var tr = (Gtk.TreeListRow)_this.view.el.model.get_object(row);
1200                                 
1201                                 var node =  (JsRender.Node)tr.get_item();
1202                                 
1203                                 GLib.debug("Drop over node: %s", node.fqn());
1204                                 
1205                         
1206                                 if (pos == "above" || pos == "below") {
1207                                         if (node.parent == null) {
1208                                                 GLib.debug("no parent try center");
1209                                                 pos = "over";
1210                                         } else {
1211                                                  
1212                                                 if (!drop_on_to.contains(node.parent.fqn())) {
1213                                                         GLib.debug("drop on does not contain %s - try center" , node.parent.fqn());
1214                                                         pos = "over";
1215                                                 } else {
1216                                                         GLib.debug("drop  contains %s - using %s" , node.parent.fqn(), pos);
1217                                                         if (_this.view.dragNode  != null && is_shift) {
1218                                                                 if (node.parent.oid == _this.view.dragNode.oid || node.parent.has_parent(_this.view.dragNode)) {
1219                                                                         GLib.debug("shift drop not self not allowed");
1220                                                                         this.addHighlight(null, "");
1221                                                                         return Gdk.DragAction.COPY;     
1222                                                                 }
1223                                                                 
1224                                                         }
1225                                                         
1226                                                 }
1227                                                 
1228                                                 
1229                                                 
1230                                         }
1231                                         
1232                                         
1233                                 }
1234                                 if (pos == "over") {
1235                                         if (!drop_on_to.contains(node.fqn())) {
1236                                                 GLib.debug("drop on does not contain %s - try center" , node.fqn());
1237                                                 this.addHighlight(null, ""); 
1238                                                 return is_shift ?  Gdk.DragAction.MOVE :  Gdk.DragAction.COPY;          
1239                                         }
1240                                         if (_this.view.dragNode  != null && is_shift) {
1241                                                 if (node.oid == _this.view.dragNode.oid || node.has_parent(_this.view.dragNode)) {
1242                                                         GLib.debug("shift drop not self not allowed");
1243                                                         this.addHighlight(null, "");
1244                                                         return Gdk.DragAction.COPY;     
1245                                                 }
1246                                         }
1247                                                 
1248                                 }
1249                                 
1250                                 
1251                                     // _this.view.highlightDropPath("", (Gtk.TreeViewDropPosition)0);
1252                                 var w = _this.view.getWidgetAt(x,y);
1253                                 this.addHighlight(w, pos); 
1254                                 return is_shift ?  Gdk.DragAction.MOVE :  Gdk.DragAction.COPY;          
1255                         });
1256                         this.el.leave.connect( ( ) => {
1257                                 this.addHighlight(null,"");
1258                         
1259                         });
1260                         this.el.drop.connect( (v, x, y) => {
1261                                 
1262                                 this.addHighlight(null,"");
1263                          
1264                                 var is_shift = _this.keystate.is_shift > 0;
1265                          
1266                                 var pos = "";
1267                                 // -- get position..
1268                                 if (this.lastDragString != v.get_string() || this.lastDragNode == null) {
1269                                         // still dragging same node
1270                          
1271                                         this.lastDragNode = new JsRender.Node(); 
1272                                         this.lastDragNode.loadFromJsonString(v.get_string(), 1);
1273                                 }
1274                             
1275                                      
1276                                
1277                             var dropNode = new JsRender.Node(); 
1278                                 dropNode.loadFromJsonString(v.get_string(), 1);
1279                                 var drop_on_to = _this.main_window.windowstate.file.palete().getDropList(dropNode.fqn());
1280                            
1281                             // if there are not items in the tree.. the we have to set isOver to true for anything..
1282                          
1283                             if (_this.model.el.n_items < 1) {
1284                                 // FIXME check valid drop types?
1285                                 if (!drop_on_to.contains("*top")) {
1286                                                 GLib.debug("drop on to list does not contain top?");
1287                                                 return false;   
1288                                         }
1289                                         // add new node to top..
1290                                         
1291                                         
1292                                          var m = (GLib.ListStore) _this.model.el.model;
1293                                 _this.main_window.windowstate.file.tree = dropNode;  
1294                             
1295                            
1296                                         m.append(dropNode);
1297                                         _this.model.selectNode(dropNode);       
1298                                         _this.changed();
1299                                         return true; // no need to highlight?
1300                              
1301                             }
1302                         
1303                         
1304                         
1305                                 var row = _this.view.getRowAt(x,y, out pos);
1306                                 if (row < 0) {
1307                                         return   false; //Gdk.DragAction.COPY;
1308                                 }
1309                                 var tr = (Gtk.TreeListRow)_this.view.el.model.get_object(row);
1310                                 
1311                                 var node =  (JsRender.Node)tr.get_item();
1312                         
1313                                 if (pos == "above" || pos == "below") {
1314                                         if (node.parent == null) {
1315                                                 pos = "over";
1316                                         } else {
1317                                                 if (!drop_on_to.contains(node.parent.fqn())) {
1318                                                         pos = "over";
1319                                                 } else {
1320                                                         GLib.debug("drop  contains %s - using %s" , node.parent.fqn(), pos);
1321                                                         if (_this.view.dragNode  != null && is_shift) {
1322                                                                 if (node.parent.oid == _this.view.dragNode.oid || node.parent.has_parent(_this.view.dragNode)) {
1323                                                                         GLib.debug("shift drop not self not allowed");
1324                                                                         return false;   
1325                                                                 }
1326                                                                 
1327                                                         }
1328                                                         
1329                                                         
1330                                                 }
1331                                         }
1332                                         
1333                                 }
1334                                 if (pos == "over") {
1335                                         if (!drop_on_to.contains(node.fqn())) {
1336                                                 GLib.debug("drop on does not contain %s - try center" , node.fqn());
1337                                                 return false;
1338                         
1339                                         }
1340                                         if (node.oid == _this.view.dragNode.oid || node.has_parent(_this.view.dragNode)) {
1341                                                 GLib.debug("shift drop not self not allowed");
1342                                                 return false;   
1343                                         }
1344                                 }
1345                                 
1346                                 switch(pos) {
1347                                         case "over":
1348                                                 node.appendChild(dropNode);
1349                                                 if (is_shift && _this.view.dragNode != null) {
1350                                                         _this.model.selectNode(null); 
1351                                                         _this.view.dragNode.remove();
1352                                                 }
1353                                                         
1354                                                 
1355                                                 _this.model.selectNode(dropNode); 
1356                                                 
1357                                                 _this.changed();                                                
1358                                                 return true;
1359                                                 
1360                                         case "above":
1361                                                 GLib.debug("Above - insertBefore");
1362                                         
1363                                                 node.parent.insertBefore(dropNode, node);
1364                                                 if (is_shift && _this.view.dragNode != null) {
1365                                                         _this.model.selectNode(null);                   
1366                                                         _this.view.dragNode.remove();
1367                                                 }
1368                                 
1369                                                 _this.model.selectNode(dropNode);                       
1370                                                 _this.changed();
1371                                                 return true;
1372                                                 
1373                                         case "below":
1374                                                 GLib.debug("Below - insertAfter");              
1375                                                 if (is_shift && _this.view.dragNode != null) {
1376                                                         _this.model.selectNode(null);                   
1377                                                         _this.view.dragNode.remove();
1378                                                 }
1379                                 
1380                                                 
1381                                                 node.parent.insertAfter(dropNode, node);
1382                                                 _this.model.selectNode(dropNode);       
1383                                                 _this.changed();
1384                                                 // select it
1385                                                 return true;
1386                                                 
1387                                         default:
1388                                                 // should not happen
1389                                                 return false;
1390                                 }
1391                                 
1392                                 
1393                              
1394                                         
1395                                         
1396                         
1397                         });
1398                 }
1399
1400                 // user defined functions
1401                 public void addHighlight (Gtk.Widget? w, string hl) {
1402                         if (this.highlightWidget != null) {
1403                                 var ww  = this.highlightWidget;
1404                                 GLib.debug("clear drag from previous highlight");
1405                                 if (ww.has_css_class("drag-below")) {
1406                                          ww.remove_css_class("drag-below");
1407                                 }
1408                                 if (ww.has_css_class("drag-above")) {
1409                                          ww.remove_css_class("drag-above");
1410                                 }
1411                                 if (ww.has_css_class("drag-over")) {
1412                                          ww.remove_css_class("drag-over");
1413                                 }
1414                         }
1415                         if (w != null) {
1416                                 GLib.debug("add drag=%s to widget", hl);        
1417                                 if (!w.has_css_class("drag-" + hl)) {
1418                                         w.add_css_class("drag-" + hl);
1419                                 }
1420                         }
1421                         this.highlightWidget = w;
1422                 }
1423         }
1424
1425         public class Xcls_selmodel : Object
1426         {
1427                 public Gtk.SingleSelection el;
1428                 private Xcls_WindowLeftTree  _this;
1429
1430
1431                         // my vars (def)
1432
1433                 // ctor
1434                 public Xcls_selmodel(Xcls_WindowLeftTree _owner )
1435                 {
1436                         _this = _owner;
1437                         _this.selmodel = this;
1438                         new Xcls_model( _this );
1439                         this.el = new Gtk.SingleSelection( _this.model.el );
1440
1441                         // my vars (dec)
1442
1443                         // set gobject values
1444
1445                         //listeners
1446                         this.el.selection_changed.connect( (position, n_items) => {
1447                         
1448                                 
1449                                         
1450                                         //if (!this.button_is_pressed && !this.key_is_pressed) {
1451                                                 // then event was started by some other action
1452                                                 // which should manually trigger all the events..
1453                                         //      print("SKIPPING select - no button or key pressed\n");
1454                                         //      return;
1455                                         //}
1456                         
1457                         
1458                                          if (_this.view.blockChanges) { // probably not needed.. 
1459                                                 GLib.debug("SKIPPING select - blockchanges set..");     
1460                                            return  ;
1461                                          }
1462                         
1463                                           if (!_this.before_node_change( ) ) {
1464                                                  _this.view.blockChanges = true;
1465                                                  _this.selmodel.el.unselect_all();
1466                                                  _this.view.blockChanges = false;
1467                                                  
1468                                                  return;
1469                                          }
1470                                          if (_this.main_window.windowstate.file == null) {
1471                                                 GLib.debug("SKIPPING select windowstate file is not set...");     
1472                                                 return;
1473                                          } 
1474                                          
1475                                          //var render = this.get('/LeftTree').getRenderer();                
1476                                         GLib.debug("LEFT TREE -> view -> selection changed called");
1477                                         
1478                                         
1479                                         // -- it appears that the selection is not updated.
1480                                          // select the node...
1481                                          //_this.selmodel.el.set_selected(row);
1482                          
1483                                          GLib.debug("LEFT TREE -> view -> selection changed TIMEOUT CALLED");
1484                         
1485                                     var snode = _this.selmodel.getSelectedNode();
1486                                     if (snode == null) {
1487                         
1488                                          GLib.debug("selected rows < 1");
1489                                         //??this.model.load( false);
1490                                         _this.node_selected(null);
1491                                         
1492                                         return   ;
1493                                     }
1494                                  
1495                                     // why dup_?
1496                                     
1497                         
1498                                     GLib.debug ("calling left_tree.node_selected");
1499                                     _this.node_selected(snode);
1500                                    
1501                                      
1502                                     
1503                                      
1504                                     // no need to scroll. it's in the view as we clicked on it.
1505                                    // _this.view.el.scroll_to_cell(new Gtk.TreePath.from_string(_this.model.activePath), null, true, 0.1f,0.0f);
1506                                     
1507                                     return  ;
1508                         });
1509                 }
1510
1511                 // user defined functions
1512                 public JsRender.Node? getSelectedNode () {
1513                   if (this.el.selected_item == null) {
1514                                 return null;
1515                   }                             
1516                    var tr = (Gtk.TreeListRow)this.el.selected_item;
1517                    return (JsRender.Node)tr.get_item();
1518                          
1519                 }
1520                 public JsRender.Node getNodeAt (uint row) {
1521                 
1522                    var tr = (Gtk.TreeListRow)this.el.get_item(row);
1523                    
1524                    var a = tr.get_item();;   
1525                    GLib.debug("get_item (2) = %s", a.get_type().name());
1526                         
1527                    
1528                    return (JsRender.Node)tr.get_item();
1529                          
1530                 }
1531         }
1532         public class Xcls_model : Object
1533         {
1534                 public Gtk.TreeListModel el;
1535                 private Xcls_WindowLeftTree  _this;
1536
1537
1538                         // my vars (def)
1539
1540                 // ctor
1541                 public Xcls_model(Xcls_WindowLeftTree _owner )
1542                 {
1543                         _this = _owner;
1544                         _this.model = this;
1545                         this.el = this.updateModel(null);
1546
1547                         // my vars (dec)
1548
1549                         // set gobject values
1550                 }
1551
1552                 // user defined functions
1553                 public void loadFile (JsRender.JsRender f) {
1554                     //console.dump(f);
1555                     
1556                     _this.drop.highlightWidget = null;
1557                     
1558                     var m = (GLib.ListStore) this.el.model;
1559                         m.remove_all();
1560                     _this.main_window.windowstate.leftTreeNodeSelected(null);
1561                     // needed???
1562                     _this.main_window.windowstate.file = f;
1563                     _this.last_error_counter = -1;
1564                    
1565                     if (f.tree == null) {
1566                             try {
1567                                 f.loadItems( );
1568                         } catch (Error e) {
1569                                 return;
1570                         }
1571                     }
1572                     // if it's still null?
1573                     if (f.tree == null) {
1574                                 _this.main_window.windowstate.showAddObject(_this.view.el, null);
1575                         _this.updateErrors();
1576                         return;
1577                     }
1578                         m.append(f.tree);
1579                         _this.updateErrors();
1580                  
1581                     _this.selmodel.el.set_selected(Gtk.INVALID_LIST_POSITION);
1582                    
1583                     return;
1584                  
1585                             
1586                 }
1587                 public int nodeToRow (JsRender.Node node) 
1588                 {
1589                         var row = -1;
1590                         var s = _this.view.el.model as Gtk.SingleSelection;
1591                         for (var i = 0; i < s.n_items; i++) {
1592                                 //GLib.debug("check node %s", s.get_item(i).get_type().name());
1593                                 var lr = s.get_item(i) as Gtk.TreeListRow;
1594                                 GLib.debug("check node %s", lr.get_item().get_type().name());
1595                                 if ((lr.get_item() as JsRender.Node).oid == node.oid) {
1596                                         return i;
1597                                         
1598                                 }
1599                         }
1600                         return -1;                      
1601                         
1602                 
1603                 }
1604                 public void deleteSelected () {
1605                 
1606                 
1607                         
1608                         var node = _this.selmodel.getSelectedNode();
1609                         
1610                 
1611                      if (node == null) {
1612                         GLib.debug("delete Selected - no node slected?");
1613                              return;
1614                      }
1615                     _this.selmodel.el.unselect_all();
1616                     
1617                     node.remove();
1618                         GLib.debug("delete Selected - done");
1619                     _this.changed();
1620                 /*    
1621                     print("DELETE SELECTED?");
1622                     //_this.view.blockChanges = true;
1623                     print("GET SELECTION?");
1624                 
1625                     var s = _this.view.el.get_selection();
1626                     
1627                     print("GET  SELECTED?");
1628                    Gtk.TreeIter iter;
1629                     Gtk.TreeModel mod;
1630                 
1631                     
1632                     if (!s.get_selected(out mod, out iter)) {
1633                         return; // nothing seleted..
1634                     }
1635                       
1636                 
1637                 
1638                     this.activePath= "";      
1639                     print("GET  vnode value?");
1640                 
1641                     GLib.Value value;
1642                     this.el.get_value(iter, 2, out value);
1643                     var data = (JsRender.Node)(value.get_object());
1644                     print("removing node from Render\n");
1645                     if (data.parent == null) {
1646                        _this.main_window.windowstate.file.tree = null;
1647                     } else {
1648                         data.remove();
1649                     }
1650                     print("removing node from Tree\n");    
1651                     s.unselect_all();
1652                     this.el.remove(ref iter);
1653                 
1654                     
1655                     
1656                     
1657                     // 
1658                     
1659                     
1660                 
1661                 
1662                     this.activePath= ""; // again!?!?      
1663                     //this.changed(null,true);
1664                     
1665                     _this.changed();
1666                     
1667                     _this.view.blockChanges = false;
1668                     */
1669                 }
1670                 public Gtk.TreeListModel updateModel (GLib.ListStore? m) {
1671                         this.el = new Gtk.TreeListModel(
1672                                 m != null ? m : new GLib.ListStore(typeof(JsRender.Node)), //..... << that's our store..
1673                                 false, // passthru
1674                                 true, // autexpand
1675                                 (item) => {
1676                                         return ((JsRender.Node)item).childstore;
1677                                 
1678                                 }
1679                         );
1680                         if (_this.selmodel.el == null) {
1681                                 return this.el;
1682                         }
1683                         _this.selmodel.el.set_model(this.el);
1684                         return this.el;
1685                 }
1686                 public void selectNode (JsRender.Node node) 
1687                 {
1688                         var row = this.nodeToRow(node);
1689                         var s = _this.view.el.model as Gtk.SingleSelection;
1690                          
1691                         if (row < 0) {
1692                                 // select none?
1693                                 GLib.debug("Could not find node");
1694                                 return;
1695                         }
1696                         GLib.debug("Select %d", row);
1697                         s.set_selected(row);
1698                         _this.view.el.scroll_to(row, null, Gtk.ListScrollFlags.SELECT, null);
1699                         //_this.node_selected(node);                    
1700                         
1701                 
1702                 }
1703         }
1704
1705
1706         public class Xcls_maincol : Object
1707         {
1708                 public Gtk.ColumnViewColumn el;
1709                 private Xcls_WindowLeftTree  _this;
1710
1711
1712                         // my vars (def)
1713
1714                 // ctor
1715                 public Xcls_maincol(Xcls_WindowLeftTree _owner )
1716                 {
1717                         _this = _owner;
1718                         _this.maincol = this;
1719                         var child_1 = new Xcls_SignalListItemFactory15( _this );
1720                         child_1.ref();
1721                         this.el = new Gtk.ColumnViewColumn( "Property", child_1.el );
1722
1723                         // my vars (dec)
1724
1725                         // set gobject values
1726                         this.el.id = "maincol";
1727                         this.el.expand = true;
1728                         this.el.resizable = true;
1729                 }
1730
1731                 // user defined functions
1732         }
1733         public class Xcls_SignalListItemFactory15 : Object
1734         {
1735                 public Gtk.SignalListItemFactory el;
1736                 private Xcls_WindowLeftTree  _this;
1737
1738
1739                         // my vars (def)
1740
1741                 // ctor
1742                 public Xcls_SignalListItemFactory15(Xcls_WindowLeftTree _owner )
1743                 {
1744                         _this = _owner;
1745                         this.el = new Gtk.SignalListItemFactory();
1746
1747                         // my vars (dec)
1748
1749                         // set gobject values
1750
1751                         //listeners
1752                         this.el.setup.connect( (listitem) => {
1753                                 
1754                                 var expand = new Gtk.TreeExpander();
1755                                  
1756                                 expand.set_indent_for_depth(true);
1757                                 expand.set_indent_for_icon(true);
1758                                 var hbox = new Gtk.Box(Gtk.Orientation.HORIZONTAL,0);
1759                                 var icon = new Gtk.Image();
1760                                 var lbl = new Gtk.Label("");
1761                                 lbl.use_markup = true;
1762                                 lbl.ellipsize = Pango.EllipsizeMode.END;
1763                                 
1764                                 icon.margin_end = 4;
1765                                 lbl.justify = Gtk.Justification.LEFT;
1766                                 lbl.xalign = 0;
1767                         
1768                         //      listitem.activatable = true; ??
1769                                 
1770                                 hbox.append(icon);
1771                                 hbox.append(lbl);
1772                                 expand.set_child(hbox);
1773                                 ((Gtk.ListItem)listitem).set_child(expand);
1774                                 
1775                         });
1776                         this.el.bind.connect( (listitem) => {
1777                                  GLib.debug("listitme is is %s", ((Gtk.ListItem)listitem).get_type().name());
1778                                 
1779                                 //var expand = (Gtk.TreeExpander) ((Gtk.ListItem)listitem).get_child();
1780                                 var expand = (Gtk.TreeExpander)  ((Gtk.ListItem)listitem).get_child();
1781                                  
1782                                  
1783                                 var hbox = (Gtk.Box) expand.child;
1784                          
1785                                 
1786                                 var img = (Gtk.Image) hbox.get_first_child();
1787                                 var lbl = (Gtk.Label) img.get_next_sibling();
1788                                 
1789                                 var lr = (Gtk.TreeListRow)((Gtk.ListItem)listitem).get_item();
1790                                 var node = (JsRender.Node) lr.get_item();
1791                                 
1792                            GLib.debug("node is %s", node.get_type().name());
1793                         // was item (1) in old layout
1794                         
1795                                 
1796                          
1797                                  /* 
1798                                 var ic = Gtk.IconTheme.get_for_display(_this.el.get_display());
1799                             var clsname = node.fqn();
1800                             
1801                             var clsb = clsname.split(".");
1802                             var sub = clsb.length > 1 ? clsb[1].down()  : "";
1803                              
1804                             var fn = "/usr/share/glade/pixmaps/hicolor/16x16/actions/widget-gtk-" + sub + ".png";
1805                             try { 
1806                                  
1807                                          
1808                                         if (FileUtils.test (fn, FileTest.IS_REGULAR)) {
1809                                             img.set_from_file(fn);
1810                                                  
1811                                         } else {
1812                                                 img.set_from_paintable(
1813                                                         ic.lookup_icon (
1814                                                                 "media-playback-stop", null,  16,1, 
1815                                                          Gtk.TextDirection.NONE, 0
1816                                                 )
1817                                                  );
1818                                         }
1819                                 } catch (GLib.Error e) {}
1820                             */
1821                             expand.set_hide_expander( !node.hasChildren() );
1822                                 expand.set_list_row(lr);
1823                                 
1824                                 node.bind_property("iconFilename",
1825                                             img, "file",
1826                                            GLib.BindingFlags.SYNC_CREATE);
1827                                 
1828                                 node.bind_property("nodeTitleProp",
1829                                             lbl, "label",
1830                                            GLib.BindingFlags.SYNC_CREATE);
1831                                 node.bind_property("nodeTipProp",
1832                                             lbl, "tooltip_markup",
1833                                            GLib.BindingFlags.SYNC_CREATE);
1834                                 // bind image...
1835                                 
1836                         });
1837                 }
1838
1839                 // user defined functions
1840         }
1841
1842
1843         public class Xcls_ColumnViewColumn16 : Object
1844         {
1845                 public Gtk.ColumnViewColumn el;
1846                 private Xcls_WindowLeftTree  _this;
1847
1848
1849                         // my vars (def)
1850
1851                 // ctor
1852                 public Xcls_ColumnViewColumn16(Xcls_WindowLeftTree _owner )
1853                 {
1854                         _this = _owner;
1855                         var child_1 = new Xcls_SignalListItemFactory17( _this );
1856                         child_1.ref();
1857                         this.el = new Gtk.ColumnViewColumn( "Add", child_1.el );
1858
1859                         // my vars (dec)
1860
1861                         // set gobject values
1862                         this.el.fixed_width = 25;
1863                 }
1864
1865                 // user defined functions
1866         }
1867         public class Xcls_SignalListItemFactory17 : Object
1868         {
1869                 public Gtk.SignalListItemFactory el;
1870                 private Xcls_WindowLeftTree  _this;
1871
1872
1873                         // my vars (def)
1874
1875                 // ctor
1876                 public Xcls_SignalListItemFactory17(Xcls_WindowLeftTree _owner )
1877                 {
1878                         _this = _owner;
1879                         this.el = new Gtk.SignalListItemFactory();
1880
1881                         // my vars (dec)
1882
1883                         // set gobject values
1884
1885                         //listeners
1886                         this.el.setup.connect( (listitem) => {
1887                         
1888                                  
1889                                 var icon = new Gtk.Image();
1890                                  
1891                                 ((Gtk.ListItem)listitem).set_child(icon);
1892                         });
1893                         this.el.bind.connect( (listitem) => {
1894                         
1895                                 var img = (Gtk.Image) ((Gtk.ListItem)listitem).get_child(); 
1896                                 var lr = (Gtk.TreeListRow)((Gtk.ListItem)listitem).get_item();
1897                                 var node = (JsRender.Node) lr.get_item();
1898                                 
1899                           
1900                             var ic = Gtk.IconTheme.get_for_display(_this.el.get_display());
1901                                 img.set_from_paintable(
1902                                         ic.lookup_icon (
1903                                                 "list-add", null,  16,1, 
1904                                                  Gtk.TextDirection.NONE, 0
1905                                         )
1906                                  );
1907                                  
1908                                 var fqn = node.fqn();
1909                             var cn = _this.main_window.windowstate.project.palete.getChildList(fqn, false);
1910                         
1911                                 img.set_visible(cn.size > 0 ? true : false);
1912                                  
1913                         });
1914                 }
1915
1916                 // user defined functions
1917         }
1918
1919
1920
1921         public class Xcls_LeftTreeMenu : Object
1922         {
1923                 public Gtk.Popover el;
1924                 private Xcls_WindowLeftTree  _this;
1925
1926
1927                         // my vars (def)
1928
1929                 // ctor
1930                 public Xcls_LeftTreeMenu(Xcls_WindowLeftTree _owner )
1931                 {
1932                         _this = _owner;
1933                         _this.LeftTreeMenu = this;
1934                         this.el = new Gtk.Popover();
1935
1936                         // my vars (dec)
1937
1938                         // set gobject values
1939                         var child_1 = new Xcls_Box19( _this );
1940                         this.el.child = child_1.el;
1941                 }
1942
1943                 // user defined functions
1944         }
1945         public class Xcls_Box19 : Object
1946         {
1947                 public Gtk.Box el;
1948                 private Xcls_WindowLeftTree  _this;
1949
1950
1951                         // my vars (def)
1952
1953                 // ctor
1954                 public Xcls_Box19(Xcls_WindowLeftTree _owner )
1955                 {
1956                         _this = _owner;
1957                         this.el = new Gtk.Box( Gtk.Orientation.VERTICAL, 0 );
1958
1959                         // my vars (dec)
1960
1961                         // set gobject values
1962                         var child_1 = new Xcls_Button20( _this );
1963                         child_1.ref();
1964                         this.el.append( child_1.el );
1965                         var child_2 = new Xcls_Button21( _this );
1966                         child_2.ref();
1967                         this.el.append( child_2.el );
1968                         var child_3 = new Xcls_Button22( _this );
1969                         child_3.ref();
1970                         this.el.append( child_3.el );
1971                 }
1972
1973                 // user defined functions
1974         }
1975         public class Xcls_Button20 : Object
1976         {
1977                 public Gtk.Button el;
1978                 private Xcls_WindowLeftTree  _this;
1979
1980
1981                         // my vars (def)
1982
1983                 // ctor
1984                 public Xcls_Button20(Xcls_WindowLeftTree _owner )
1985                 {
1986                         _this = _owner;
1987                         this.el = new Gtk.Button();
1988
1989                         // my vars (dec)
1990
1991                         // set gobject values
1992                         this.el.label = "Delete Element";
1993
1994                         //listeners
1995                         this.el.clicked.connect( ( ) => {
1996                         _this.LeftTreeMenu.el.hide();
1997                          _this.model.deleteSelected();
1998                         _this.changed();
1999                         });
2000                 }
2001
2002                 // user defined functions
2003         }
2004
2005         public class Xcls_Button21 : Object
2006         {
2007                 public Gtk.Button el;
2008                 private Xcls_WindowLeftTree  _this;
2009
2010
2011                         // my vars (def)
2012
2013                 // ctor
2014                 public Xcls_Button21(Xcls_WindowLeftTree _owner )
2015                 {
2016                         _this = _owner;
2017                         this.el = new Gtk.Button();
2018
2019                         // my vars (dec)
2020
2021                         // set gobject values
2022                         this.el.label = "Save as Template";
2023
2024                         //listeners
2025                         this.el.clicked.connect( () => {
2026                         _this.LeftTreeMenu.el.hide();
2027                              DialogSaveTemplate.singleton().showIt(
2028                                     (Gtk.Window) _this.el.get_root (), 
2029                                     _this.main_window.windowstate.file.palete(), 
2030                                     _this.getActiveElement()
2031                             );
2032                              
2033                             
2034                         });
2035                 }
2036
2037                 // user defined functions
2038         }
2039
2040         public class Xcls_Button22 : Object
2041         {
2042                 public Gtk.Button el;
2043                 private Xcls_WindowLeftTree  _this;
2044
2045
2046                         // my vars (def)
2047
2048                 // ctor
2049                 public Xcls_Button22(Xcls_WindowLeftTree _owner )
2050                 {
2051                         _this = _owner;
2052                         this.el = new Gtk.Button();
2053
2054                         // my vars (dec)
2055
2056                         // set gobject values
2057                         this.el.label = "Save as Module";
2058
2059                         //listeners
2060                         this.el.clicked.connect( () => {
2061                             
2062                             _this.LeftTreeMenu.el.hide();
2063                             var node = _this.getActiveElement();
2064                               
2065                              
2066                              var sm = DialogSaveModule.singleton();
2067                              
2068                              
2069                             sm.showIt(
2070                                     (Gtk.Window) _this.el.get_root (), 
2071                                     _this.main_window.windowstate.project, 
2072                                     node
2073                              );
2074                              /*
2075                              gtk4 migration - disabled this part.. probably not used muchanyway
2076                              
2077                              
2078                              if (name.length < 1) {
2079                                     return;
2080                           
2081                              }
2082                              node.set_prop( new JsRender.NodeProp.special("xinclude", name));
2083                              node.items.clear();
2084                         
2085                         
2086                             var s = _this.view.el.get_selection();
2087                             
2088                             print("GET  SELECTED?");
2089                             Gtk.TreeIter iter;
2090                             Gtk.TreeModel mod;
2091                         
2092                             
2093                             if (!s.get_selected(out mod, out iter)) {
2094                                 return; // nothing seleted..
2095                             }
2096                             Gtk.TreeIter citer;
2097                             var n_cn = mod.iter_n_children(iter) -1;
2098                             for (var i = n_cn; i > -1; i--) {
2099                                 mod.iter_nth_child(out citer, iter, i);
2100                                 
2101                         
2102                                 print("removing node from Tree\n");    
2103                             
2104                                 _this.model.el.remove(ref citer);
2105                             }
2106                             _this.changed();
2107                             _this.node_selected(node, "tree");
2108                              */
2109                             
2110                         });
2111                 }
2112
2113                 // user defined functions
2114         }
2115
2116
2117
2118
2119 }