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