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