Fix #7991 - better updateing of error status and char position of errors
[roobuilder] / src / JsRender / JsRender.vala
1 //<Script type="text/javascript">
2
3 namespace JsRender {
4
5
6         public errordomain Error {
7                 INVALID_FORMAT,
8                 RENAME_FILE_EXISTS
9         }
10                 
11         public abstract class JsRender  : Object {
12                 /**
13                  * @cfg {Array} doubleStringProps list of properties that can be double quoted.
14                  */
15                 public Gee.ArrayList<string> doubleStringProps;
16                 
17                 public string id  = "";
18                 public string name { get; set; default = ""; }   // is the JS name of the file.
19                 public string fullname = "";
20                 public string path = "";  // is the full path to the file.
21                 
22                 public  string relpath {
23                         owned get { 
24                                 return  this.project.path  == this.path ? "" : this.path.substring(this.project.path.length+1);
25                         } 
26                         private set {}
27                 }
28                 public  string reldir {
29                         owned get { 
30                                 return  this.project.path == this.dir ? "" : this. dir.substring(this.project.path.length+1);
31                         } 
32                         private set {}
33                 }
34                 
35                 public  string  dir {
36                         owned get { 
37                                 return GLib.Path.get_dirname(this.path);
38                                  
39                         } 
40                         private set {}
41                 }
42                 
43                 public string file_namespace {
44                         public owned get {
45                                 if (!this.name.contains(".")) {
46                                         return "";
47                                 }
48                                 var bits = this.name.split(".");
49                                 return bits[0];
50                         }
51                         private set {}
52                 }
53                 public string file_without_namespace {
54                         public  owned get {
55                                 if (!this.name.contains(".")) {
56                                         return this.name;
57                                 }
58                                 var bits = this.name.split(".");
59                                 return this.name.substring(bits[0].length +1);
60                         }
61                         private set {}
62                 }
63                 
64                 public string file_ext {
65                         public owned get {
66                                 if (!this.path.contains(".")) {
67                                         return "";
68                                 }
69                                 var bits = this.name.split(".");
70                                 return bits[bits.length-1];
71                         }
72                         private set {}
73                 }
74                 public string parent = "";  // JS parent.
75                 public string region = "";  // RooJS - insert region.
76         
77                 public string title = "";  // a title.. ?? nickname.. ??? -
78
79                 private int _version = 1;   // should we increment this based on the node..?
80                 public int version {
81                         get {
82                                 if (this.tree != null) {
83                                         return this.tree.updated_count;
84                                 }
85                                 return ++this._version; // increased on every call? - bit of a kludge until we do real versioning
86                         }
87                         private set {
88                                 this._version = value;
89                         }
90                         
91                 }
92
93                 public string permname;
94                 public string language;
95                 public string content_type;
96                 public string modOrder;
97                 public string xtype;
98                 public uint64 webkit_page_id; // set by webkit view - used to extract extension/etc..
99                 public bool gen_extended  = false; // nodetovala??
100
101                 public Project.Project project;
102
103                 // GTK Specifc
104  
105                 public string build_module; // module to build if we compile (or are running tests...)      
106
107                 //Project : false, // link to container project!
108                 
109                 public Node tree; // the tree of nodes.
110                 
111                 //public GLib.List<JsRender> cn; // child files.. (used by project ... should move code here..)
112
113                 public bool hasParent; 
114                 
115                 public bool loaded;
116                 
117                 public Gee.HashMap<string,string> transStrings; // map of md5 -> string.
118                 public  Gee.HashMap<string,string> namedStrings;
119                 //public        Gee.HashMap<string, GLib.ListStore> errorsByType;
120                 private Gee.ArrayList<Lsp.Diagnostic> errors;
121                 public int error_counter {
122                         get; private set; default = 0;
123                 }
124
125                 public signal void changed (Node? node, string source); 
126                 
127                  
128                 public signal void compile_notice(string type, string file, int line, string message);
129                 
130                 private  GLib.Icon? _icon = null;
131                 
132                 public GLib.Icon? icon { 
133                         private set {}
134                         get {
135                                 if (this._icon !=  null) {
136                                         return this._icon;
137                                 }
138                                 
139                                 if (this.path == "") {
140                                         return null;
141                                 }
142                                 if (!GLib.FileUtils.test(this.path, GLib.FileTest.EXISTS)) {
143                                         return null;
144                                 }
145                                 this._icon = File.new_for_path(this.path).query_info("standard::icon",GLib.FileQueryInfoFlags.NONE).get_icon();
146                                 return this._icon;
147                         }
148                 }
149                 
150                 /**
151                  * UI componenets
152                  * 
153                  */
154                 //public Xcls_Editor editor;
155                 public GLib.ListStore childfiles; // used by directories..
156                 
157                 
158                 //abstract JsRender(Project.Project project, string path); 
159                 
160                 protected JsRender(Project.Project project, string path)
161                 {
162                     
163                         //this.cn = new GLib.List<JsRender>();
164                         GLib.debug("new jsrender %s", path);
165                         this.path = path;
166                         this.project = project;
167                         this.hasParent = false;
168                         this.parent = "";
169                         this.tree = null; 
170                         this.title = "";
171                         this.region = "";
172                         this.permname = "";
173                         this.modOrder = "";
174                         this.language = "";
175                         this.content_type = "";
176                         this.build_module = "";
177                         //this.loaded = false;
178                         //print("JsRender.cto() - reset transStrings\n");
179                         this.transStrings = new Gee.HashMap<string,string>();
180                         this.namedStrings = new Gee.HashMap<string,string>();
181                         // should use basename reallly...
182                         
183                         var ar = this.path.split("/");
184                         // name is in theory filename without .bjs (or .js eventually...)
185                         try {
186                                 Regex regex = new Regex ("\\.(bjs)$");
187
188                                 this.name = ar.length > 0 ? regex.replace(ar[ar.length-1],ar[ar.length-1].length, 0 , "") : "";
189                         } catch (GLib.Error e) {
190                                 this.name = "???";
191                         }
192                         this.fullname = (this.parent.length > 0 ? (this.parent + ".") : "" ) + this.name;
193
194                         this.doubleStringProps = new Gee.ArrayList<string>();
195                         this.childfiles = new GLib.ListStore(typeof(JsRender));
196                         //this.errorsByType  = new Gee.HashMap<string, GLib.ListStore>();
197                         this.errors = new Gee.ArrayList<Lsp.Diagnostic>((a,b) => { return a.equals(b); }); 
198                         
199
200
201                 }
202                 
203                 public void renameTo(string name) throws  Error
204                 {
205                         if (this.xtype == "PlainFile") {
206                                 return;
207                         }
208                         var bjs = GLib.Path.get_dirname(this.path) +"/" +  name + ".bjs";
209                         if (FileUtils.test(bjs, FileTest.EXISTS)) {
210                                 throw new Error.RENAME_FILE_EXISTS("File exists %s\n",name);
211                         }
212                         GLib.FileUtils.remove(this.path);
213                         this.removeFiles();
214                         // remove other files?
215                         
216                         this.name = name;
217                         this.path = bjs;
218                         
219                 }
220                 
221
222                 
223                 // not sure why xt is needed... -> project contains xtype..
224                 
225                 public static JsRender factory(string xt, Project.Project project, string path) throws Error
226                 {
227          
228                         switch (xt) {
229                                 case "Gtk":
230                                         return new Gtk(project, path);
231                                         
232                                 case "Roo":
233                                         return new Roo((Project.Roo) project, path);
234 //                      case "Flutter":
235 //                                      return new Flutter(project, path);
236                                 case "PlainFile":
237                                         return new PlainFile(project, path);
238                         }
239                         throw new Error.INVALID_FORMAT("JsRender Factory called with xtype=%s", xt);
240                         //return null;    
241                 }
242                 
243         
244         
245                 public string nickType()
246                 {
247                         var ar = this.name.split(".");
248                         string[] ret = {};
249                         for (var i =0; i < ar.length -1; i++) {
250                                 ret += ar[i];
251                         }
252                         return string.joinv(".", ret);
253                         
254                 }
255                 public string nickName()
256                 {
257                         var ar = this.name.split(".");
258                         return ar[ar.length-1];
259                         
260                 }
261                 
262                 public string nickNameSplit()
263                 {
264                         var n = this.nickName();
265                         var ret = "";
266                         var len = 0;
267                         for (var i = 0; i < n.length; i++) {
268                                 if (i!=0 && n.get(i).isupper() && len > 10) {
269                                         ret +="\n";
270                                         len= 0;
271                                 }
272                                 ret += n.get(i).to_string();
273                                 len++;
274                         }
275                         
276
277                         
278                         return ret;
279                 
280                 }
281                 
282                 Gdk.Pixbuf screenshot = null;
283                 Gdk.Pixbuf screenshot92 = null;
284                 Gdk.Pixbuf screenshot368 = null;
285                 
286                 public Gdk.Pixbuf? getIcon(int size = 0) {
287                     var fname = this.getIconFileName( );                
288                     if (!FileUtils.test(fname, FileTest.EXISTS)) {
289                 GLib.debug("PIXBUF %s:  %s does not exist?", this.name, fname);
290                                 return null;
291                         }
292                         
293                         switch (size) {
294                                 case 0:
295                                         if (this.screenshot == null) {
296                                                 try { 
297                                                         this.screenshot = new Gdk.Pixbuf.from_file(fname);
298                                                 } catch (GLib.Error e) {}
299                                         }
300                                         return this.screenshot;
301                                 
302                                 case 92:
303                                         
304                                         if (this.screenshot == null) {
305                                                 this.getIcon(0);
306                                                 if (this.screenshot == null) {
307                                                         return null;
308                                                 }
309                                         }
310                                         
311                                         this.screenshot92 = this.screenshot.scale_simple(92, (int) (this.screenshot.height * 92.0 /this.screenshot.width * 1.0 )
312                                                 , Gdk.InterpType.NEAREST) ;
313                                     return this.screenshot92;
314                             
315                             case 368:
316                                         if (this.screenshot == null) {
317                                                 this.getIcon(0);
318                                                 if (this.screenshot == null) {
319                                                         return null;
320                                                 }
321                                         }
322                                         
323                                         this.screenshot368 = this.screenshot.scale_simple(368, (int) (this.screenshot.height * 368.0 /this.screenshot.width * 1.0 )
324                                     , Gdk.InterpType.NEAREST) ;
325                                     return this.screenshot368;
326                     }
327                     return null;
328                 }
329                 
330                 public void writeIcon(Gdk.Pixbuf pixbuf) {
331                         
332                         this.screenshot92 = null;
333                         this.screenshot368 = null;
334                         this.screenshot = null;
335                         try {
336                                 GLib.debug("Wirte %s", this.getIconFileName( ));
337                                 pixbuf.save(this.getIconFileName( ),"png");
338                                 this.screenshot = pixbuf;
339                         
340                         } catch (GLib.Error e) {
341                                 GLib.debug("failed to write pixbuf?");
342                         
343                         }
344                                 
345                          
346                         
347                 
348                 }
349                 public void widgetToIcon(global::Gtk.Widget widget) {
350                         
351                         this.screenshot92 = null;
352                         this.screenshot368 = null;
353                         this.screenshot = null;
354                         
355                         try {
356                         
357
358                         var filename = this.getIconFileName();
359                                 
360
361                                  var p = new global::Gtk.WidgetPaintable(widget);
362                                  var s = new global::Gtk.Snapshot();
363                                  GLib.debug("Width %d, Height %d", widget.get_width(), widget.get_height()); 
364                                  p.snapshot(s, widget.get_width(), widget.get_height());
365                                  var n = s.free_to_node();
366                                  if (n == null) {
367                                         return;
368                                 }
369                                  var r = new  Gsk.CairoRenderer();
370                                  r.realize(null);
371                                  var t = r.render_texture(n,null);
372                                  GLib.debug("write to %s", filename);
373                                  t.save_to_png(filename);
374                                  r.unrealize();
375                                          
376                         
377                         } catch (GLib.Error e) {
378                                 GLib.debug("failed to write pixbuf?");
379                         
380                         }
381                                 
382                          
383                         
384                 
385                 }
386
387                 
388                 public string getIconFileName( )
389                 {
390                          
391                         var m5 = GLib.Checksum.compute_for_string(GLib.ChecksumType.MD5,this.path); 
392
393                         var dir = GLib.Environment.get_home_dir() + "/.Builder/icons";
394                         try {
395                                 if (!FileUtils.test(dir, FileTest.IS_DIR)) {
396                                          File.new_for_path(dir).make_directory();
397                                 }
398                         } catch (GLib.Error e) {
399                                 // eakk.. what to do here...
400                         }
401                         var fname = dir + "/" + m5 + ".png";
402                         
403                          
404                         return fname;
405                           
406                 }
407                 
408                 public string toJsonString()
409                 {
410                         if (this.xtype == "PlainFile") {
411                                 return "";
412                         }
413                         var node = new Json.Node(Json.NodeType.OBJECT);
414                         node.set_object(this.toJsonObject());                   
415                         var generator = new JsonGen(node);
416                     generator.indent = 1;
417                     generator.pretty = true;
418                     
419                         
420                         return generator.to_data();
421                 }
422                 
423                 public void saveBJS()
424                 {
425                    // if (!this.loaded) {
426                         ///     GLib.debug("saveBJS - skip - not loaded?");
427                 //          return;
428                     //}
429                     if (this.xtype == "PlainFile") {
430                             return;
431                     }
432                    
433                      
434                     
435                     GLib.debug("WRITE :%s\n " , this.path);// + "\n" + JSON.stringify(write));
436                     try {
437                                 this.writeFile(this.path, this.toJsonString());
438                          
439                     } catch(GLib.Error e) {
440                         print("Save failed");
441                     }
442                 }
443                  
444                  
445
446
447                  
448                  
449                  
450                   
451                 public string jsonHasOrEmpty(Json.Object obj, string key) {
452                         return obj.has_member(key) ? 
453                                                 obj.get_string_member(key) : "";
454                 }
455
456                 
457                 public Json.Object toJsonObject ()
458                 {
459                     
460                     
461                         var ret = new Json.Object();
462                         if (this.xtype == "PlainFile") {
463                                 return ret;
464                         }
465                         
466                         //ret.set_string_member("id", this.id); // not relivant..
467                         ret.set_string_member("name", this.name);
468                         
469                         if (this.project.xtype == "Roo") {
470                                 ret.set_string_member("parent", this.parent == null ? "" : this.parent);
471                                 ret.set_string_member("title", this.title == null ? "" : this.title);
472                                 //ret.set_string_member("path", this.path);
473                                 //ret.set_string_member("items", this.items);
474                                 ret.set_string_member("permname", this.permname  == null ? "" : this.permname);
475                                 ret.set_string_member("modOrder", this.modOrder  == null ? "" : this.modOrder);
476                         }
477                         if (this.project.xtype == "Gtk") {
478  
479                                 ret.set_string_member("build_module", this.build_module  );
480                         }
481                         ret.set_boolean_member("gen_extended", this.gen_extended);
482                         
483                         if (this.transStrings.size > 0) {
484                                 var tr =  new Json.Object();
485                                 var iter = this.transStrings.map_iterator();
486                                 while (iter.next()) {
487                                         tr.set_string_member(iter.get_value(), iter.get_key());
488                                 }
489                                 ret.set_object_member("strings", tr);
490             }
491
492             
493             
494                         if (this.namedStrings.size > 0) {
495                                 var tr =  new Json.Object();
496                                 var iter = this.namedStrings.map_iterator();
497                                 while (iter.next()) {
498                                         tr.set_string_member(iter.get_key(), iter.get_value());
499                                 }
500                                 ret.set_object_member("named_strings", tr);
501             }
502                         
503                         var ar = new Json.Array();
504                         // empty files do not have a tree.
505                         if (this.tree != null) {
506                                 ar.add_object_element(this.tree.toJsonObject());
507                         }
508                         ret.set_array_member("items", ar);
509                 
510                     return ret;
511                 }
512                 
513                 
514
515                 public string getTitle ()
516                 {
517                     if (this.title == null) { // not sure why this happens..
518                         return "";
519                 }
520                     if (this.title.length > 0) {
521                         return this.title;
522                     }
523                     var a = this.path.split("/");
524                     return a[a.length-1];
525                 }
526                 public string getTitleTip()
527                 {
528                     if (this.title.length > 0) {
529                         return "<b>" + this.title + "</b> " + this.path;
530                     }
531                     return this.path;
532                 }
533                 /*
534                     sortCn: function()
535                     {
536                         this.cn.sort(function(a,b) {
537                             return a.path > b.path;// ? 1 : -1;
538                         });
539                     },
540                 */
541                     // should be in palete provider really..
542
543
544                 public Palete.Palete palete()
545                 {
546                         // error on plainfile?
547                         return this.project.palete;
548
549                 }
550                 
551                 public string guessName(Node ar) // turns the object into full name.
552                 {
553                      // eg. xns: Roo, xtype: XXX -> Roo.xxx
554                     if (!ar.hasXnsType()) {
555                        return "";
556                     }
557                     
558                     return ar.get("xns") + "." + ar.get("xtype");
559                                       
560                                         
561                 }
562                 /**
563                  *  non-atomic write (replacement for put contents, as it creates temporary files.
564                  */
565                 public void writeFile(string path, string contents) throws GLib.IOError, GLib.Error
566                 {
567
568                                  
569                         var f = GLib.File.new_for_path(path);
570                         var data_out = new GLib.DataOutputStream(
571                                           f.replace(null, false, GLib.FileCreateFlags.NONE, null)
572                        );
573                         data_out.put_string(contents, null);
574                         data_out.close(null);
575                 }
576                  
577                 
578                 
579                 public  Node? lineToNode(int line)
580                 {
581                         if (this.tree == null) {
582                                 return null;
583                         }
584                         return this.tree.lineToNode(line);
585                         
586                         
587                 }
588                 
589                 public GLib.ListStore toListStore()
590                 {
591                         var ret = new GLib.ListStore(typeof(Node));
592                         ret.append(this.tree);
593                         return ret;
594                 }
595                  
596                 
597                 // used to handle list of files in project editor (really Gtk only)
598                 public bool compile_group_selected {
599                         get {
600                                 var gproj = (Project.Gtk) this.project;
601                                 
602                                 if (gproj.active_cg == null) {
603                                         return false;
604                                 }
605                                 if (this.xtype == "Dir") {
606                                         // show ticked if all ticked..
607                                         var ticked = true;
608                                         for(var i = 0; i < this.childfiles.n_items; i++ ) {
609                                                 var f = (JsRender) this.childfiles.get_item(i);
610                                                 if (!f.compile_group_selected) {
611                                                         ticked = false;
612                                                         break;
613                                                 }
614                                         }
615                                         return ticked;
616                                 
617                                 
618                                 }
619                                 if (gproj.active_cg.sources == null) {
620                                         GLib.debug("compile_group_selected - sources is null? ");
621                                         return false;
622                                 }
623
624                                 return gproj.active_cg.sources.contains(this.relpath);
625                                 
626                         }
627                         set {
628                                 
629                                 var gproj = (Project.Gtk) this.project;
630                                 
631                                 if (gproj.active_cg == null) {
632                                         return;
633                                 }
634                                 if (gproj.active_cg.loading_ui) {
635                                         return;
636                                 }
637                                 
638                                 if (this.xtype == "Dir") {
639                                         for(var i = 0; i < this.childfiles.n_items; i++ ) {
640                                                 var f = (JsRender) this.childfiles.get_item(i);
641                                                 f.compile_group_selected = value;
642  
643                                         }
644                                         return;
645                                  
646                                 }
647                                 
648                                 
649                                 
650                                 if (value == false) {
651                                         GLib.debug("REMOVE %s", this.relpath);
652                                         
653                                         gproj.active_cg.sources.remove(this.relpath);
654                                         return;
655                                 }
656                                 if (!gproj.active_cg.sources.contains(this.relpath)) { 
657                                         GLib.debug("ADD %s", this.relpath);
658                                         gproj.active_cg.sources.add(this.relpath);
659                                 }
660                         
661                         }
662                 }
663                 /*
664                 public bool compile_group_hidden {
665                         get {
666                                 var gproj = (Project.Gtk) this.project;
667                                 
668                                 
669                                 return gproj.hidden.contains(this.relpath);
670                                 
671                         }
672                         set {
673                                 
674                                 var gproj = (Project.Gtk) this.project;
675                                 
676                                 if (gproj.active_cg == null) {
677                                         return;
678                                 }
679                                 if (gproj.active_cg.loading_ui) {
680                                         return;
681                                 } 
682                                 if (value == false) {
683                                         GLib.debug("REMOVE %s", this.relpath);
684                                         
685                                         gproj.hidden.remove(this.relpath);
686                                         return;
687                                 }
688                                 if (!gproj.hidden.contains(this.relpath)) { 
689                                         gproj.hidden.add(this.relpath);
690                                         // hiding a project will auto clear it.
691                                         for(var i = 0; i < this.childfiles.n_items; i++ ) {
692                                                 var f = (JsRender) this.childfiles.get_item(i);
693                                                 f.compile_group_selected = false;
694                                         }
695                                         return;
696                                         
697                                 }
698                         
699                         }
700                 }
701                 */
702                 public void remove()
703                 {
704                         if (this.xtype == "Dir") {
705                                 return;
706                         }
707                         // cleans up build (should really be in children..
708                         this.removeFile(this.path);
709                         if (this.path.has_suffix(".bjs") && this.project.xtype == "Roo") {
710                                 this.removeFile(this.path.substring(0, this.path.length-4) + ".js");
711                                 return;
712                         }
713                         if (this.path.has_suffix(".bjs") && this.project.xtype == "Gtk") {
714                                 this.removeFile(this.path.substring(0, this.path.length-4) + ".vala");
715                                 this.removeFile(this.path.substring(0, this.path.length-4) + ".c");
716                                 this.removeFile(this.path.substring(0, this.path.length-4) + ".o");                             
717                         }
718                         if (this.path.has_suffix(".vala") && this.project.xtype == "Gtk") {
719                                 this.removeFile(this.path.substring(0, this.path.length-5) + ".c");
720                                 this.removeFile(this.path.substring(0, this.path.length-5) + ".o");                             
721                         }       
722                 
723                 
724                 }
725                 
726                 private void removeFile(string path)
727                 {
728
729                         if (GLib.FileUtils.test(path, GLib.FileTest.EXISTS)) {
730                                 GLib.FileUtils.unlink(path);
731                         }
732
733                 }
734                 public string relTargetName()
735                 {
736                         return this.targetName().substring(this.project.path.length +1);
737                 
738                 }
739                 
740                 public string to_url()
741                 {
742                         return File.new_for_path (this.targetName()).get_uri ();
743                 }
744                 public Palete.LanguageClient? getLanguageServer()
745                 {
746                         
747                         return this.project.getLanguageServer(this.language_id());
748                 
749                 }
750                  
751                 public void updateErrors(Gee.ArrayList<Lsp.Diagnostic> new_errors) 
752                 {
753                         var oc = this.error_counter;
754                         var skip = new Gee.ArrayList<Lsp.Diagnostic>((a,b) => { return a.equals(b); });
755                         var rem = new Gee.ArrayList<Lsp.Diagnostic>((a,b) => { return a.equals(b); });
756                         foreach(var old in this.errors) {
757                                 if (new_errors.contains(old)) {
758                                         skip.add(old);
759                                         continue;
760                                 }
761                                 rem.add(old);
762                                  
763                         }
764                         foreach(var old in  rem) {
765                                 this.removeError(old);
766                         }
767                         foreach(var err in new_errors) {
768                                 if (skip.contains(err)) {
769                                         continue;
770                                 }
771                                 this.addError(err);
772                         }
773                         if (oc != this.error_counter) {
774                                 BuilderApplication.updateCompileResults();
775                         }
776                         
777                 }
778                 
779                 
780                 
781                 public Gee.ArrayList<Lsp.Diagnostic> getErrors()
782                 {
783                         return this.errors;
784                 }
785                 
786                 private void addError(Lsp.Diagnostic diag)
787                 {
788                         
789                         GLib.debug("ADD Error %s", diag.to_string());
790                         this.errors.add(diag);
791                         this.project.addError(this, diag);
792                         
793                         this.error_counter++;
794                          
795                 }
796                  
797                 public void removeError(Lsp.Diagnostic diag) 
798                 {
799                         GLib.debug("REMOVE Error %s", diag.to_string());
800                         this.errors.remove(diag);
801                         this.project.removeError(this, diag);
802                         this.error_counter++;
803                 }
804                 public int getErrorsTotal(string category) 
805                 {
806                         var  ret = 0;
807                         foreach(var diag in this.errors) {
808                                 if (diag.category == category) {
809                                         ret++;
810                                 }
811                         }
812                         return ret;
813                         
814                 
815                 }
816                 
817                 
818                 public abstract string language_id();
819                 public abstract void save();
820                 public abstract void saveHTML(string html);
821                 public abstract string toSource() ;
822                 public abstract string toSourceCode() ; // used by commandline tester..
823                 public abstract void setSource(string str);
824                 public abstract string toSourcePreview() ;
825                 public abstract void removeFiles() ;
826                 public abstract void  findTransStrings(Node? node );
827                 public abstract string toGlade();
828                 public abstract string targetName();
829                 public abstract void loadItems() throws GLib.Error;
830         } 
831
832 }
833  
834