Not logged in.  Login/Logout/Register | List snippets | | Create snippet | Upload image | Upload data

1165
LINES

< > BotCompany Repo | #1034148 // G22Utils

JavaX fragment (include) [tags: use-pretranspiled]

Transpiled version (69799L) is out of date.

1  
// Some of the functions are dependent on the concepts field,
2  
// others are global.
3  
4  
!include once #1035461 // Gazelle 22 Class synonyms Include
5  
6  
sclass G22Utils_Base {
7  
  // event that is triggered every time a file or directory inside the
8  
  // project changes. Starts the fileWatcher automatically when the
9  
  // first listener is added.
10  
  event projectFileChanged(File file);
11  
}
12  
13  
sclass G22Utils > G22Utils_Base is AutoCloseable, TransientObject {
14  
  delegate FunctionDef to GazelleV_LeftArrowScript.
15  
  
16  
  settable IBackgroundProcesses backgroundProcessesUI;
17  
  settable Enterable module;
18  
  settable G22MasterStuff masterStuff;
19  
  settable Concepts concepts;
20  
  settable G22ProjectActions projectActions;
21  
  gettable G22AutoStarter autoStarter = new(this);
22  
  settable new FunctionTimings<S> functionTimings;
23  
  gettable Map<S, FunctionDef> projectWideFunctionDefs = syncMap();
24  
  gettable Map<S, Class> projectWideClassDefs = syncMap();
25  
  
26  
  Timestamp recompileDate;
27  
  
28  
  gettable Set<AutoCloseable> autoClosingResources = syncLinkedHashSet();
29  
  
30  
  // TODO: set this to a few seconds if your variables are expensive to render
31  
  // settable Seconds variableUpdateIntervalInUI;
32  
  
33  
  FileWatchService fileWatcher; // general file watch service
34  
  bool projectFileListenerInitiated;
35  
36  
  gettable CombinedStringifier stringifier = new(
37  
    o -> o cast BufferedImage ? "Image (" + o.getWidth() + "*" + o.getHeight() + " px)" : null
38  
  );
39  
  
40  
  ILASClassLoader lasClassLoader() { ret masterStuff?.lasClassLoader(); }
41  
  
42  
  settable bool confirmProjectReplacements;
43  
  
44  
  // add fields here
45  
  
46  
  ImageSurface stdImageSurface_noToolTip(ImageSurface is default imageSurface()) {
47  
    imageSurface_pixelated(is);
48  
    is.setAutoZoomToDisplay(true).repaintInThread(false);
49  
    is.defaultImageDir = -> dbDir();
50  
    is.specialPurposed = true;
51  
    ret is;
52  
  }
53  
    
54  
  ImageSurface stdImageSurface(ImageSurface is default imageSurface()) {
55  
    stdImageSurface_noToolTip(is);
56  
    new ImageSurface_PositionToolTip(is);
57  
    ret is;
58  
  }
59  
  
60  
  L<ImageSurface> stdImageSurfaces(Cl images) {
61  
    ret map stdImageSurface(toBufferedImages(images));
62  
  }
63  
64  
  ImageSurface stdImageSurface(BufferedImage etc img) {
65  
    var is = stdImageSurface();
66  
    is.setImage(img);
67  
    ret is;
68  
  }
69  
  
70  
  ImageSurface stdImageSurface(File file) {
71  
    var is = stdImageSurface();
72  
    is.setImage(file);
73  
    ret is;
74  
  }
75  
  
76  
  ImageSurface stdImageSurface(G22GalleryImage img) {
77  
    ret stdImageSurface(img?.path);
78  
  }
79  
  
80  
  ImageSurface stdImageSurfaceWithSelection(BufferedImage etc img, Rect selection) {
81  
    var is = stdImageSurface(img);
82  
    is.setSelection(selection);
83  
    ret is;
84  
  }
85  
  
86  
  S stringify(O o) { ret stringifier.toString(o); }
87  
  
88  
  event bigVariableLoaded(G22Variable var);
89  
90  
  event settingUpParser(GazelleV_LeftArrowScriptParser parser);
91  
  event settingUpScriptIDE(JLeftArrowScriptIDE ide);
92  
  
93  
  GazelleV_LeftArrowScriptParser leftArrowParser() {
94  
    new GazelleV_LeftArrowScriptParser parser;
95  
    parser.classNameResolver(classNameResolver());
96  
    parser.lasClassLoader(lasClassLoader());
97  
    
98  
    settingUpParser(parser);
99  
    parser.addClassAlias("Bool", "Boolean");
100  
    parser.addClassAlias("BollingerBands", "LiveBollingerBands");
101  
    parser.addClassAlias("Freq", "Frequency");
102  
    parser.addClassAlias("PriceDigitizer", "PriceDigitizer2");
103  
    parser.addClassAlias("MRUAndAllTimeTop", "MRUAndAllTimeTop_optimized");
104  
    parser.findExternalObject2 = name -> {
105  
      try object projectWideClassDefs.get(name);
106  
      ret parser.findExternalObject2_base(name);
107  
    };
108  
    
109  
    parser.addFunctionDefs(projectWideFunctionDefs);
110  
    
111  
    ret parser;
112  
  }
113  
  
114  
  O leftArrow(S script) {
115  
    ret leftArrowParse(script)!;
116  
  }
117  
  
118  
  GazelleV_LeftArrowScript.Script leftArrowParse(S script) {
119  
    ret leftArrowParser().parse(script);
120  
  }
121  
  
122  
  O leftArrowWithVars(S script, O... vars) {
123  
    var parser = leftArrowParser();
124  
    for (int i = 0; i < l(vars); i += 2)
125  
      parser.addVar((S) vars[i], or(_getClass(vars[i+1]), O), true);
126  
      
127  
    var parsed = parser.parse(script);
128  
    FlexibleVarContext varContext = flexibleVarContextFromParams(vars);
129  
    ret parsed.get(varContext);
130  
  }
131  
  
132  
  void basicParserTest() {
133  
    var parser = leftArrowParser();
134  
    print(classContainerPrefixes := parser.classContainerPrefixes());
135  
    assertEquals(pair(1, 2), parser.parse("new Pair 1 2")!);
136  
  }
137  
138  
  ifclass JLeftArrowScriptIDE
139  
  JLeftArrowScriptIDE leftArrowIDE aka leftArrowScriptIDE() {
140  
    new JLeftArrowScriptIDE ide;
141  
    ide.g22utils(this);
142  
    ide.scriptTimeout(projectWideScriptTimeout());
143  
    settingUpScriptIDE(ide);
144  
    ret ide;
145  
  }
146  
  endif
147  
  
148  
  File byteCodePath() {
149  
    ret assertNotNull(getBytecodePathForClass(this));
150  
  }
151  
152  
  simplyCached ClassNameResolver classNameResolver() {
153  
    ret new ClassNameResolver().byteCodePath(byteCodePath()).init();
154  
  }
155  
  
156  
  File databasesMotherDir() {
157  
    ret masterStuff.databasesMotherDir();
158  
  }
159  
  
160  
  File dirOfProjectNamed(S name) {
161  
    assertNempty(name);
162  
    ret newFile(databasesMotherDir(), name);
163  
  }
164  
  
165  
  AutoCloseable enter() { ret module?.enter(); }
166  
  
167  
  S defaultDBName() { ret "Default"; }
168  
  
169  
  File lastOpenedDBsFile() {
170  
    ret newFile(databasesMotherDir(), "Last Opened");
171  
  }
172  
  
173  
  File recentlyOpenedDBsFile() {
174  
    ret newFile(databasesMotherDir(), "Recently Opened");
175  
  }
176  
  
177  
  File autoUpdateFile() {
178  
    ret newFile(databasesMotherDir(), "Auto-Update");
179  
  }
180  
  
181  
  bool autoUpdateEnabled() {
182  
    ret fileExists(autoUpdateFile());
183  
  }
184  
  
185  
  void setAutoUpdate(bool b) {
186  
    createOrRemoveFile(autoUpdateFile(), b);
187  
  }
188  
  
189  
  LS dbsToOpen() {
190  
    ret loadRecentProjectsFile(lastOpenedDBsFile());
191  
  }
192  
  
193  
  LS dbNamesRecentlyOpened() {
194  
    ret loadRecentProjectsFile(recentlyOpenedDBsFile());
195  
  }
196  
  
197  
  void addToRecentDBNames(S dbName, bool hidden) {
198  
    LS list = dbNamesRecentlyOpened();
199  
    LS list2 = cloneList(list);
200  
    removeAll(list2, dbName, "*" + dbName);
201  
    list2.add(0, hidden ? "*" + dbName : dbName);
202  
    truncateList(list2, 100);
203  
    if (!eq(list, list2))
204  
      saveTextFile(recentlyOpenedDBsFile(), lines(list2));
205  
  }
206  
  
207  
  // returns project names with optional "*" prefix for hidden projects
208  
  LS loadRecentProjectsFile(File file) {
209  
    new LS dbNames;
210  
    for (S name : tlft(loadTextFile(file))) {
211  
      S name2 = dropPrefix("*", name);
212  
      if (fileExists(newFile(databasesMotherDir(), name2)))
213  
        dbNames.add(name);
214  
    }
215  
        
216  
    if (empty(dbNames)) dbNames.add(defaultDBName());
217  
    ret dbNames;
218  
  }
219  
  
220  
  void setOpenDBs(Cl<? extends IG22LoadedDB> dbs) {
221  
    new LS dbNames;
222  
    for (db : dbs) {
223  
      var dbDir = conceptsDir(db.concepts());
224  
      if (sameFile(databasesMotherDir(), dirOfFile(dbDir)))
225  
        dbNames.add((db.hidden() ? "*" : "") + fileName(dbDir));
226  
    }
227  
      
228  
    saveTextFile(lastOpenedDBsFile(), lines(dbNames));
229  
  }
230  
  
231  
  ifclass SimpleCRUD_v2
232  
  <A extends G22LeftArrowScript> void setupScriptCRUD(SimpleCRUD_v2<A> crud, bool allowRunOnProjectOpen default false) {
233  
    crud.useNewChangeHandler(true);
234  
    crud.editableFieldsForItem = x -> llNonNulls("description",
235  
      allowRunOnProjectOpen ? "runOnProjectOpen" : null,
236  
      allowRunOnProjectOpen ? "runOrder" : null);
237  
    //G22LeftArrowScript.f_description().getName());
238  
    crud.multiLineField("text");
239  
    crud.multiLineField("editingText");
240  
    crud.makeTextArea = text -> jMinHeight(200, crud.makeTextArea_base(text));
241  
    crud.humanizeFieldNames = false;
242  
    crud.iconButtons(true);
243  
    crud.itemToMap_inner2 = c -> scriptToMap(c, allowRunOnProjectOpen);
244  
    crud.dontDuplicateFields = litset("runOnProjectOpen", /*"runOrder",*/ "runCount", "lastResultByMode");
245  
246  
  }
247  
  endif
248  
249  
  MapSO scriptToMap(G22LeftArrowScript c, bool allowRunOnProjectOpen default false) {  
250  
    ret litorderedmap(
251  
      "Description" := c.description(),
252  
      "Status" := renderScriptStatus(c),
253  
      "LoC" := renderScriptLoC(c),
254  
      "Import note" := c.importNote,
255  
      "Run on project open" := c.renderRunOnProjectOpenStatus());
256  
  }
257  
  
258  
  S renderScriptStatus(G22LeftArrowScript c) {
259  
    ret or2_rev("Empty", joinNemptiesWithSpacedPlus(
260  
      c.isClearForAutoRun() ? "Clear for auto-run" : null,
261  
      c.isSavedDistinctFromAutoRunVersion() ? "Saved" /*"Saved (not cleared)"*/ : null,
262  
      c.isEditing() ? "Editing" : null
263  
    ));
264  
  }
265  
  
266  
  S renderScriptLoC(G22LeftArrowScript c) {
267  
    ret n2(intMax(mapLL linesOfCode_javaTok(
268  
      c.editingText,
269  
      c.text,
270  
      c.codeForAutoRun())));
271  
  }
272  
  
273  
  // e.g. for an image file
274  
  L<G22Label> labelsForFile(File file) {
275  
    if (file == null) null;
276  
    File labelsFile = appendToFileName(file, ".labels");
277  
    LS labels = tlft(loadTextFile(labelsFile));
278  
    ret map getLabel(labels);
279  
  }
280  
281  
  File labelsFile(File file) {  
282  
    if (file == null) null;
283  
    ret appendToFileName(file, ".labels");
284  
  }
285  
  
286  
  void setLabelsForFile(File file, L<G22Label> labels) {
287  
    LS list = map(labels, label -> label.name);
288  
    File f = labelsFile(file);
289  
    saveTextFile(f, lines(list));
290  
    print("Saved " + nLabels(list) + " (" + joinWithComma(list) + ") to " + f);
291  
  }
292  
  
293  
  G22Label getLabel(S name) {
294  
    if (empty(name)) null;
295  
    if (containsNewLine(name)) fail("No newlines in label names allowed: " + name);
296  
    ret uniqCI(concepts, G22Label, +name);
297  
  }
298  
  
299  
  File dbDir aka projectDir() { ret conceptsDir(concepts); }
300  
  
301  
  File fileInDbDir aka projectFile aka projectDir(S name) { ret newFile(dbDir(), name); }
302  
  
303  
  record GazelleDB(S name, File dir) {
304  
    S name() { ret name; }
305  
    File dir() { ret dir; }
306  
    
307  
    bool loaded() {
308  
      ret loadedDB() != null;
309  
    }
310  
    
311  
    simplyCached IG22LoadedDB loadedDB() {
312  
      ret masterStuff.getLoadedDBForConceptDir(dir);
313  
    }
314  
    
315  
    File conceptsFile() { ret conceptsFileIn(dir); }
316  
  }
317  
  
318  
  L<GazelleDB> gazelleDBs() {
319  
    new L<GazelleDB> dbs;
320  
    for (File dir : listDirsContainingFileNamed(databasesMotherDir(),
321  
      "concepts.structure.gz"))
322  
      dbs.add(new GazelleDB(fileName(dir), dir));
323  
    ret dbs;
324  
  }
325  
  
326  
  ItIt<Concepts> peekAllProjectsConcepts() {
327  
    var classFinder = masterStuff.makeClassFinder();
328  
    ret mapI_pcall(gazelleDBs(), db -> {
329  
      var cc = newConceptsWithClassFinder(db.conceptsFile(), classFinder);
330  
      cc.loadFromDisk();
331  
      ret cc;
332  
    });
333  
  }
334  
  
335  
  ifclass RSyntaxTextAreaWithSearch
336  
    RSyntaxTextAreaWithSearch newSyntaxTextArea(IF1<JComponent> wrapStatusLabel default (IF1) null) {
337  
      RSyntaxTextAreaWithSearch ta = new(wrapStatusLabel);
338  
      ta.textArea().setHighlightCurrentLine(false);
339  
      ta.menuLessOperation();
340  
      ret ta;
341  
    }
342  
    
343  
    RSyntaxTextAreaWithSearch newSyntaxTextArea(S text) {
344  
      var ta = newSyntaxTextArea();
345  
      ta.setText(text);
346  
      ret ta;
347  
    }
348  
  endif
349  
  
350  
  File projectStoryTextFile() { ret newFile(dbDir(), "story.txt"); }
351  
  
352  
  S projectName() { ret fileName(dbDir()); }
353  
  
354  
  close {
355  
    autoStarter.close();
356  
    closeAndClear(autoClosingResources);
357  
    dispose fileWatcher;
358  
  }
359  
  
360  
  // solve shadowing problem in LAS
361  
  void close(AutoCloseable c) {
362  
    main close(c);
363  
  }
364  
  
365  
  // project vars
366  
  
367  
  G22Variable findProjectVar(S name) {
368  
    ret conceptWhereCI(concepts, G22Variable, +name);
369  
  }
370  
  
371  
  Cl<S> projectVarNames() {
372  
    ret collect name(list(concepts, G22Variable));
373  
  }
374  
  
375  
  O getProjectVar(S name) {
376  
    G22Variable var = findProjectVar(name);
377  
    ret var?.value();
378  
  }
379  
  
380  
  // If it's a big variable, load it just now and then forget
381  
  // it again
382  
  O getBigProjectVarOnce(S name) {
383  
    G22Variable var = findProjectVar(name);
384  
    ret var?.getOnce();
385  
  }
386  
  
387  
  // fail if var doesn't exist or value is null
388  
  O getMandatoryProjectVar(S name) {
389  
    ret assertNotNull(name, getProjectVar(name));
390  
  }
391  
  
392  
  O getOrSetTransientProjectVar(S name, IF0 f) {
393  
    try object getProjectVar(name);
394  
    ret setTransientProjectVarAndReturn(name, f!);
395  
  }
396  
  
397  
  O getProjectVarOrCallScript(S name, long scriptID) {
398  
    try object getProjectVar(name);
399  
    ret callScript(scriptID);
400  
  }
401  
  
402  
  O getProjectVarSetByScript(S name, long scriptID) {
403  
    try object getProjectVar(name);
404  
    callScript(scriptID);
405  
    ret getProjectVar(name);
406  
  }
407  
  
408  
  // gets first non-null value of project variable named "name"
409  
  // in any open project (order not defined)
410  
  O getProjectVarFromAnyProject(S name) {
411  
    for (project : masterStuff().openProjects())
412  
      try object project.g22utils().getProjectVar(name);
413  
    null;
414  
  }
415  
  
416  
  // gets all non-null values from project variable named "name"
417  
  // in any open project
418  
  L getProjectVarFromAllProjects aka getVarFromAnyProject(S name) {
419  
    ret nonNulls(masterStuff().openProjects(),
420  
      project -> project.g22utils().getProjectVar(name));
421  
  }
422  
  
423  
  // Creates the variable if it's not there, otherwise
424  
  // returns existing variable.
425  
  G22Variable projectVarConcept(S name) {
426  
    ret optimizedUniqCI(concepts, G22Variable, +name);
427  
  }
428  
  
429  
  O waitForProjectVar(double timeoutSeconds default infinity(), S name) {
430  
    G22Variable var = projectVarConcept(name);
431  
    ret waitForCalculatedValueUsingChangeListener(timeoutSeconds, -> var.value(), var);
432  
  }
433  
  
434  
  void setBigProjectVar(bool persistent, S name, O value) {
435  
    if (persistent)
436  
      setBigProjectVar(name, value);
437  
    else
438  
      setTransientProjectVar(name, value);
439  
  }
440  
  
441  
  G22Variable setProjectVar(bool persistent, S name, O value) {
442  
    G22Variable var = projectVarConcept(name);
443  
    
444  
    // defensive order
445  
    if (!persistent) var.persistent(persistent);
446  
    var.value(value);
447  
    if (persistent) var.persistent(persistent);
448  
    
449  
    ret var;
450  
  }
451  
  
452  
  // uncache a big project variable. Does not change the value
453  
  void unloadProjectVar(S name) {
454  
    var var = findProjectVar(name);
455  
    var?.unload();
456  
  }
457  
458  
  <A> A setBigProjectVar(S name, A value) {
459  
    setPersistentProjectVar(name, value);
460  
    G22Variable var = projectVarConcept(name);
461  
    var.makeBig();
462  
    ret value;
463  
  }
464  
  
465  
  O getCachedProjectVar(S name) {
466  
    var var = findProjectVar(name);
467  
    ret var?.cachedValue();
468  
  }
469  
  
470  
  bool isBigProjectVar(S name) {
471  
    var v = findProjectVar(name);
472  
    ret v != null && v.big();
473  
  }
474  
  
475  
  <A> A setPersistentProjectVar(S name, A value) {
476  
    setProjectVar(true, name, value);
477  
    ret value;
478  
  }
479  
  
480  
  G22Variable setTransientProjectVar(S name, O value) {
481  
    ret setProjectVar(false, name, value);
482  
  }
483  
  
484  
  <A> A setTransientProjectVarAndReturn(S name, A value) {
485  
    setProjectVar(false, name, value);
486  
    ret value;
487  
  }
488  
  
489  
  void setAutoClosingProjectVar(S name, O value) {
490  
    setTransientProjectVar(name, value).autoClose(true);
491  
  }
492  
  
493  
  void clearProjectVar(S name) {
494  
    var v = findProjectVar(name);
495  
    v?.clear();
496  
  }
497  
  
498  
  void deleteProjectVar(S name) {
499  
    deleteConcept(findProjectVar(name));
500  
  }
501  
  
502  
  // Note: unsynced. Wild west baby!
503  
  O getOrCreateProjectVar aka getOrCreateTransientProjectVar(S name, IF0 maker) {
504  
    ret getOrCreateProjectVar(projectVarConcept(name), maker);
505  
  }
506  
  
507  
  O getOrCreatePersistentProjectVar(S name, IF0 maker) {
508  
    var var = projectVarConcept(name);
509  
    O value = getOrCreateProjectVar(var, maker);
510  
    var.persistent(true);
511  
    ret value;
512  
  }
513  
  
514  
  O getOrCreateBigProjectVar(S name, IF0 maker) {
515  
    var var = projectVarConcept(name);
516  
    O value = getOrCreateProjectVar(var, maker);
517  
    var.makeBig();
518  
    ret value;
519  
  }
520  
  
521  
  O getOrCreateAutoClosingProjectVar(S name, IF0 maker) {
522  
    var var = projectVarConcept(name);
523  
    O value = getOrCreateProjectVar(var, maker);
524  
    var.autoClose(true);
525  
    ret value;
526  
  }
527  
  
528  
  G22Variable getOrCreateAutoClosingProjectVar_returnVar(S name, IF0 maker) {
529  
    var var = projectVarConcept(name);
530  
    getOrCreateProjectVar(var, maker);
531  
    ret var.autoClose(true);
532  
  }
533  
  
534  
  bool projectVarIsNotNull(S name) {
535  
    var var = findProjectVar(name);
536  
    ret var != null && var.has();
537  
  }
538  
  
539  
  O getOrCreateProjectVar(G22Variable var, IF0 maker) {
540  
    if (!var.has()) {
541  
      O value = maker!;
542  
      if (value != null)
543  
        var.setValueIfNull(value);
544  
    }
545  
    ret var!;
546  
  }
547  
  
548  
  // variable is made persistent
549  
  IVarWithNotify liveProjectVar(S name, O defaultValue default null) {
550  
    G22Variable var = projectVarConcept(name);
551  
    var.persistent(true);
552  
    var.setValueIfNull(defaultValue);
553  
    ret var.varValue();
554  
  }
555  
  
556  
  IVarWithNotify liveTransientProjectVar(S name, O defaultValue default null) {
557  
    G22Variable var = projectVarConcept(name);
558  
    var.persistent(false);
559  
    var.setValueIfNull(defaultValue);
560  
    ret var.varValue();
561  
  }
562  
  
563  
  void replaceCloseableProjectVar(S name, IF0<? extends AutoCloseable> calc) {
564  
    O value = getProjectVar(name);
565  
    if (value cast AutoCloseable) {
566  
      main close(value);
567  
      deleteProjectVar(name);
568  
    }
569  
    setTransientProjectVar(name, calc?!);
570  
  }
571  
  
572  
  // notify of internal changes in the variable
573  
  // even though the value pointer may have stayed the same.
574  
  void projectVarChanged aka saveProjectVar(S name) {
575  
    var var = findProjectVar(name);
576  
    var?.changeInsideOfValue();
577  
  }
578  
579  
  // search by value
580  
  Cl<G22Variable> projectVarChanged aka saveProjectVar(O value) {
581  
    var vars = conceptsWhere(concepts, G22Variable, +value);
582  
    for (var : vars)
583  
      var.change();
584  
    ret vars;
585  
  }
586  
  
587  
  // timeouts
588  
  
589  
  double defaultScriptTimeout() { ret 10.0; }
590  
  double projectWideScriptTimeout() {
591  
    ret or(toDoubleOrNull(getProjectVar("!Script Timeout")),
592  
      defaultScriptTimeout());
593  
  }
594  
  
595  
  // getting objects
596  
  
597  
  G22Analyzer getAnalyzer(long id) {
598  
    var a = getConcept(concepts, G22Analyzer, id);
599  
    if (a == null) fail("Analyzer not found: " + id);
600  
    ret a;
601  
  }
602  
603  
  G22LeftArrowScript getScript(long id) {
604  
    var a = getConcept(concepts, G22LeftArrowScript, id);
605  
    if (a == null) fail("Script not found: " + id);
606  
    ret a;
607  
  }
608  
  
609  
  S textOfScript(long id) {
610  
    ret getScript(id).latestText();
611  
  }
612  
613  
  // calling scripts
614  
  
615  
  // This is meant to be called from within another script.
616  
  // No timeout (timeout is handled by calling script)
617  
  // Uses "safest" version available (auto-run or saved)
618  
  O callScript(long id) {
619  
    var script = getScript(id);
620  
    ret script.evaluateWithoutTimeout();
621  
  }
622  
  
623  
  // Like callScript, but only uses auto-run version
624  
  O callAutoRunnableScript(long id) {
625  
    var script = getScript(id);
626  
    ret script.evaluateAutoRunWithoutTimeout();
627  
  }
628  
  
629  
  O callScriptWithParams(long id, O... params) {
630  
    ret callScriptWithParams(getScript(id), params);
631  
  }
632  
  
633  
  O callScriptWithParams(G22LeftArrowScript script, O... params) {
634  
    var compiledScript = script.compileSaved()!;
635  
    ret compiledScript.get(flexibleVarContextFromParams(params));
636  
  }
637  
  
638  
  // no timeout by default
639  
  double defaultTimeout() { ret infinity(); }
640  
  
641  
  // evaluate
642  
  // -with timeout
643  
  // -registered in background processes
644  
  // -with module entered
645  
  <A> A evalRegisteredCode(double timeoutSeconds default defaultTimeout(), S processName, IF0<A> code) {
646  
    if (code == null) null;
647  
    ret evalWithTimeoutOrTypedException(timeoutSeconds, ->
648  
      useThisThreadAsBackgroundProcess(processName, code)
649  
    );
650  
  }
651  
  
652  
  Thread startAsRegisteredThread(S processName default str_shorten(r), Runnable r) {
653  
    if (r == null) null;
654  
    ret startThread(processName, -> useThisThreadAsBackgroundProcess(processName, toIF0(r)));
655  
  }
656  
657  
  <A> A useThisThreadAsBackgroundProcess(S processName, IF0<A> code) {
658  
    temp enter();
659  
    temp var process = backgroundProcessesUI.tempAdd(processName);
660  
    Thread myThread = currentThread();
661  
    process.setInterruptAction(r { cancelThread(myThread) });
662  
    ret code!;
663  
  }
664  
  
665  
  virtual GazelleHost host() {
666  
    temp enter();
667  
    ret dm_os();
668  
  }
669  
  
670  
  <A> A timeFunction(S name, IF0<A> f) {
671  
    ret functionTimings.get(name, f);
672  
  }
673  
  
674  
  bool isConceptsDir(File dir) {
675  
    ret isSameFile(conceptsDir(concepts), dir);
676  
  }
677  
  
678  
  synchronized FileWatchService fileWatcher() {
679  
    ret fileWatcher if null = new FileWatchService;
680  
  }
681  
  
682  
  synchronized selfType onProjectFileChanged(IVF1<File> listener) {
683  
    super.onProjectFileChanged(listener);
684  
    if (!projectFileListenerInitiated) {
685  
      set projectFileListenerInitiated;
686  
      fileWatcher().addRecursiveListener(dbDir(), l1 projectFileChanged);
687  
    }
688  
    this;
689  
  }
690  
  
691  
  simplyCached G22ProjectInfo projectInfo() {
692  
    ret optimizedUniq(concepts, G22ProjectInfo);
693  
  }
694  
  
695  
  RunnablesReferenceQueue runnablesReferenceQueue() {
696  
    ret masterStuff.runnablesReferenceQueue();
697  
  }
698  
  
699  
  EphemeralObjectIDs ephemeralObjectIDs() {
700  
    ret masterStuff.ephemeralObjectIDs();
701  
  }
702  
  
703  
  // get a remember ephemeral object by ID
704  
  O eph(long id) { ret ephemeralObjectIDs().get(id); }
705  
  
706  
  void openInBrowser(S url) {
707  
    main openPlatformBrowser(url);
708  
    /*if (Desktop.getDesktop().isSupported(Desktop.Action.BROWSE))
709  
      main openInBrowser(url);
710  
    else {
711  
      S cmd;
712  
      if (projectInfo().useFirefox() && isOnPATH("firefox")) 
713  
        cmd = "firefox";
714  
      else {
715  
        cmd = chromeCmd();
716  
        if (isRoot())
717  
          cmd += " -no-sandbox";
718  
      }
719  
      cmd += " " + platformQuote(url);
720  
      nohup(cmd);
721  
    }*/
722  
  }
723  
  
724  
  S compilationDate() {
725  
    ret or2(compilationDateFromClassPath(this), "unknown");
726  
  }
727  
  
728  
  // Global ID for project
729  
  S projectID() {
730  
    ret projectInfo().projectID();
731  
  }
732  
  
733  
  IG22LoadedDB getLoadedDB() {
734  
    ret masterStuff.getLoadedDB(concepts);
735  
  }
736  
  
737  
  ConceptsComboBox<GalleryImage> galleryImagesComboBox() {
738  
    ret swing(->
739  
      new ConceptsComboBox<GalleryImage>(concepts, GalleryImage));
740  
  }
741  
  
742  
  IBackgroundProcess tempAddBackgroundProcess(S name) {
743  
    ret backgroundProcessesUI?.tempAdd(name);
744  
  }
745  
  
746  
  IF1<S, Class> classFinder() {
747  
    var master = masterStuff.makeClassFinder();
748  
    ret name -> {
749  
      try object projectWideClassDefs().get(dropPrefix("main$", name));
750  
      ret master.get(name);
751  
    };
752  
  }
753  
  
754  
  O restructure(O o) {
755  
    ret unstructure(structure(o), false, concepts.classFinder);
756  
  }
757  
  
758  
  G22ProjectActions project() { ret projectActions(); }
759  
  
760  
  bool openPathInProject(S path) {
761  
    ret projectActions().openPathInProject(path);
762  
  }
763  
  
764  
  void openUIURL aka showUIURL aka goToURIURL(S url) {
765  
    projectActions().openUIURL(url);
766  
  }
767  
  
768  
  BufferedImage loadProjectImage(S fileName) {
769  
    ret loadImage2(projectFile(fileName));
770  
  }
771  
  
772  
  IG22LoadedDB openDB(S name, bool hidden default false) {
773  
    ret masterStuff().openDB(name, hidden);
774  
  }
775  
  
776  
  // Hides project if it is opened by this call
777  
  G22Utils getProject(S name) {
778  
    ret openDB(name, true).g22utils();
779  
  }
780  
  
781  
  G22Utils getProjectIfExists(S name) {
782  
    ret !masterStuff().projectExists(name) ? null
783  
      : getProject(name);
784  
  }
785  
  
786  
  G22Utils getProjectIfOpen(S name) {
787  
    var db = first(openProjects(), p -> eqic(p.g22utils().projectName(), name));
788  
    ret db?.g22utils();
789  
  }
790  
  
791  
  G22JavaObjectVisualizer visualizeObject aka visualizeJavaObject(O o) {
792  
    ret new G22JavaObjectVisualizer(this, o);
793  
  }
794  
  
795  
  G22JavaObjectVisualizer visualizeObjectWithoutType aka visualizeJavaObjectWithoutType(O o) {
796  
    ret visualizeObject(o).withTypeAndTime(false);
797  
  }
798  
  
799  
  swappable G22VariablesPanel makeVariablesPanel() {
800  
    ret new G22VariablesPanel().g22utils(this);
801  
  }
802  
  
803  
  swappable JComponent jGazelleLogo() {
804  
    ret main jGazelleLogo();
805  
  }
806  
  
807  
  bool devMode() {
808  
    ret masterStuff().devMode();
809  
  }
810  
  
811  
  // specialize list() for our concepts
812  
  
813  
  <A extends Concept> L<A> nuLike list(Class<A> type, Concepts cc default concepts()) {
814  
    ret main list(cc, type);
815  
  }
816  
  
817  
  <A extends Concept> L<A> list(Concepts concepts, Class<A> type) {
818  
    ret main list(type, concepts);
819  
  }
820  
  
821  
  G22GalleryImage galleryImageForMD5(S md5) {
822  
    ret firstThat(list(concepts, G22GalleryImage),
823  
      img -> cic(fileName(img.path), md5));
824  
  }
825  
  
826  
  // add the right kind of scrollpane to an image surface
827  
  JComponent wrapImageSurface(ImageSurface is) {
828  
    ret is == null ?: jscroll_centered_borderless(is);
829  
  }
830  
  
831  
  JComponent wrap(O o) {
832  
    var c = main wrap(o);
833  
    if (c cast ImageSurface)
834  
      ret wrapImageSurface(c);
835  
    ret c;
836  
  }
837  
  
838  
  swappable S byUser() {
839  
    ret "";
840  
  }
841  
  
842  
  Cl<? extends IG22LoadedDB> getLoadedDBs aka openProjects() {
843  
    ret masterStuff().openProjects();
844  
  }
845  
  
846  
  <A extends Concept> L<A> nuLike listInOpenProjects(Class<A> type) {
847  
    ret concatMap(openProjects(), db -> db.g22utils().list(type));
848  
  }
849  
  
850  
  transient simplyCached PicturesByMD5 picturesByMD5() {
851  
    ret new PicturesByMD5(projectFile("Images"))
852  
      .extension(".qoi");
853  
  }
854  
  
855  
  JButton reloadButton(S toolTip, Runnable action) {
856  
    ret jimageButton(#1101440, toolTip, action);
857  
  }
858  
  
859  
  void registerConcept(Concept c) {
860  
    main registerConcept(concepts, c);
861  
  }
862  
  
863  
  void registerConcept(Concepts cc, Concept c) {
864  
    main registerConcept(cc, c);
865  
  }
866  
  
867  
  void addingAdditionalAutoCompletes(LeftArrowScriptAutoCompleter autoCompleter) {
868  
    // projectVar magic
869  
    S token = autoCompleter.prevToken();
870  
    if (isIdentifier(token) && cic(token, "ProjectVar"))
871  
      autoCompleter.addToSearcher(quoteAll(projectVarNames()));
872  
      
873  
    // project-wide class defs
874  
    autoCompleter.addToSearcher(keys(projectWideClassDefs()));
875  
  }
876  
  
877  
  meta-for Lib as S, File {  
878  
    bool addLibrary(Lib library) {
879  
      if (!main addLibrary(library)) false;
880  
      print("Loaded library: " + library);
881  
      masterStuff().newClassesDefined();
882  
      true;
883  
    }
884  
  }
885  
  
886  
  // add an auto-closing resource to the project
887  
  <A extends AutoCloseable> WrappedCloseable<A> addResource(A resource) {
888  
    if (resource == null) null; 
889  
    autoClosingResources.add(resource);
890  
    ret new WrappedCloseable<A>(resource) {
891  
      @Override void beforeClose {
892  
        autoClosingResources.remove(resource);
893  
      }
894  
    };
895  
  }
896  
897  
  // TODO: Improve LAS to not need this anymore  
898  
  O callFunctionFromScript(int scriptID, S functionName, O... args) {
899  
    ret callFunctionFromScript((long) scriptID, functionName, args);
900  
  }
901  
    
902  
  // This even returns the version being edited - very aggressive
903  
  O callLatestFunctionFromScript(int scriptID, S functionName, O... args) {
904  
    var function = getScript(scriptID).latestCompileResult().get().getFunction(functionName);
905  
    ret function.callFromOutside(args);
906  
  }
907  
  
908  
  // Uses "saved" version, not "cleared for auto-run"
909  
  O callSavedFunctionFromScript(int scriptID, S functionName, O... args) {
910  
    var function = getScript(scriptID).compileSaved().get().getFunction(functionName);
911  
    ret function.callFromOutside(args);
912  
  }
913  
  
914  
  O callFunctionFromScript(long scriptID, S functionName, O... args) {
915  
    var function = getScript(scriptID).safestCompileResult().get().getFunction(functionName);
916  
    ret function.callFromOutside(args);
917  
  }
918  
  
919  
  O callProjectFunction(S functionName, O... args) {
920  
    var function = projectWideFunctionDefs.get(functionName);
921  
    if (function == null) fail("Function " + functionName + " not found in project " + projectName());
922  
    ret function.callFromOutside(args);
923  
  }
924  
  
925  
  JComponent visualizeAutoRunnableScript(long scriptID) {
926  
    ret visualizeAutoRunnableScript(getScript(scriptID));
927  
  }
928  
  
929  
  JComponent visualizeAutoRunnableScript(G22LeftArrowScript script) {
930  
    if (script == null) null;
931  
932  
    if (!script.isClearForAutoRun())
933  
      ret jcenteredlabel("Script not clear for auto-run");
934  
      
935  
    try {
936  
      O result = script.evaluateAutoRunWithoutTimeout();
937  
      var objVisualizer = G22JavaObjectVisualizer(this, result).withType(false);
938  
      ret objVisualizer.visualize();
939  
    } catch print e {
940  
      ret jErrorView(e);
941  
    }
942  
  }
943  
  
944  
  JComponent visualizeSavedScript(long scriptID) {
945  
    ret visualizeSavedScript(getScript(scriptID));
946  
  }
947  
  
948  
  JComponent visualizeSavedScript(G22LeftArrowScript script) {
949  
    if (script == null) null;
950  
951  
    if (!script.isSaved())
952  
      ret jcenteredlabel("Script not saved");
953  
      
954  
    try {
955  
      O result = script.evaluateWithoutTimeout();
956  
      var objVisualizer = G22JavaObjectVisualizer(this, result).withType(false);
957  
      ret objVisualizer.visualize();
958  
    } catch print e {
959  
      ret jErrorView(e);
960  
    }
961  
  }
962  
  
963  
  // projectName must match base dir in zip
964  
  void importProjectFromZip(File zipFile, S baseDirInZip, S projectName) {
965  
    File dir = dirOfProjectNamed(projectName);
966  
    if (isConceptsDir(dir)) {
967  
      if (eqic(projectName(), "Default"))
968  
        ret with infoMessage("Sorry dude");
969  
970  
      IG22LoadedDB defaultDB = masterStuff().getLoadedDBForConceptDir(dirOfProjectNamed("Default"));
971  
      IG22LoadedDB preloadedDefaultDB = defaultDB;
972  
      if (defaultDB == null)
973  
        defaultDB = openDB("Default");
974  
        
975  
      project().closeProject();
976  
      defaultDB.g22utils().importProjectFromZip(zipFile, baseDirInZip, projectName);
977  
      
978  
      // Close default project again if only opened for this purpose
979  
      if (preloadedDefaultDB == null)
980  
        defaultDB.projectActions().closeProject();
981  
        
982  
      ret;
983  
    }
984  
    
985  
    if (!directoryIsEmpty(dir)) {
986  
      if (confirmProjectReplacements && !swingConfirm("Archive and overwrite existing project " + projectName + "?"))
987  
        ret;
988  
      
989  
      File archiveDir = javaxBackupDir("Gazelle/" + projectName + "-" + computerID() + "-" + ymdMinusHMS());
990  
      moveFile(dir, archiveDir);
991  
      infoMessage("Archived project to: " + archiveDir);
992  
    }
993  
      
994  
    zip2dir(zipFile, empty(baseDirInZip) ? dir : dir.getParentFile());
995  
    infoBox("Imported project " + projectName);
996  
    
997  
    masterStuff().openDB(projectName);
998  
  }
999  
  
1000  
  void importProjectFromZip(File zipFile) {
1001  
    S baseDir = baseDirInZip(zipFile);
1002  
    S projectName = takeFirst(baseDir, smartIndexOf(baseDir, '/'));
1003  
    if (empty(projectName)) {
1004  
      ret with inputText("Please enter name for imported project",
1005  
        name -> {
1006  
          if (!validFileName(name)) {
1007  
            infoBox("Invalid name, use simpler characters");
1008  
            importProjectFromZip(zipFile);
1009  
            ret;
1010  
          }
1011  
          importProjectFromZip(zipFile, "", name);
1012  
        });
1013  
    }
1014  
        
1015  
    assertValidFileName(projectName);
1016  
    importProjectFromZip(zipFile, baseDir, projectName);
1017  
  }
1018  
  
1019  
  Class export(Class c) {
1020  
    if (c != null) {
1021  
      projectWideClassDefs.put(dropHashFromClassName(shortClassName(c)), c);
1022  
      newFunctionsDefined();
1023  
    }
1024  
    ret c;
1025  
  }
1026  
  
1027  
  FunctionDef exportFunction aka export(FunctionDef def) {
1028  
    ret def == null ?: exportFunction(def.name, def);
1029  
  }
1030  
  
1031  
  FunctionDef exportFunction aka export(S name, FunctionDef def) {
1032  
    projectWideFunctionDefs.put(name, def);
1033  
    //print("Defined function " + name);
1034  
    
1035  
    // Make sure all compiled scripts are forgotten
1036  
    newFunctionsDefined();
1037  
    
1038  
    ret def;
1039  
  }
1040  
  
1041  
  // return previous definition
1042  
  FunctionDef unexportFunction aka unexport(S name) {
1043  
    FunctionDef f = projectWideFunctionDefs.remove(name);
1044  
    if (f != null) {
1045  
      print("Undefined function " + name);
1046  
      newFunctionsDefined();
1047  
    }
1048  
    ret f;
1049  
  }
1050  
  
1051  
  void newFunctionsDefined {
1052  
    masterStuff().newClassesDefined();
1053  
    recompileDate = tsNow();
1054  
  }
1055  
1056  
  bool shouldRecompile(LASCompileResult cr) {  
1057  
    ret recompileDate != null && cr.compilationStart() != null
1058  
      && cr.compilationStart().compareTo(recompileDate) < 0;
1059  
  }
1060  
  
1061  
  bool compileResultValid(LASCompileResult cr, S code) {
1062  
    ret cr != null && eq(cr.script, code) && !shouldRecompile(cr);
1063  
  }
1064  
  
1065  
  toString {
1066  
    ret "G22Utils(" + quote(projectName()) + ")";
1067  
  }
1068  
  
1069  
  void editScript(G22LeftArrowScript script) {
1070  
    projectActions().editScript(script);
1071  
  }
1072  
  
1073  
  JButton editButton(S toolTip, Runnable action) {
1074  
    ret jimageButtonScaledToWidth(16, #1103068, toolTip, action);
1075  
  }
1076  
  
1077  
  JButton editScriptButton(G22LeftArrowScript script) {
1078  
    ret editButton("Edit script",
1079  
      -> projectActions().editScript(script));
1080  
  }
1081  
  
1082  
  G22ScriptView savedScriptView(long scriptID) {
1083  
    ret new G22ScriptView(getScript(scriptID)).mustBeAutoRunnable(false);
1084  
  }
1085  
  
1086  
  G22ScriptView scriptView(long scriptID) {
1087  
    ret new G22ScriptView(getScript(scriptID));
1088  
  }
1089  
  
1090  
  File gazelleJar() {
1091  
    ret getBytecodePathForClass(this);
1092  
  }
1093  
  
1094  
  L<PersistableThrowable> projectErrors() {
1095  
    ret projectActions().projectErrors();
1096  
  }
1097  
  
1098  
  JComponent jErrorView(Throwable e) {
1099  
    var view = main jErrorView(e);
1100  
    var scriptErrors = instancesOf(GazelleV_LeftArrowScript.ScriptError.class, allCausesIncludingSelf(e));
1101  
    var sources = mapNotNulls(scriptErrors, -> .tokenRangeWithSrc());
1102  
    if (empty(sources)) ret view;
1103  
    sources = uniquifySources(sources);
1104  
    ret centerAndEastWithMargin(view,
1105  
      jline(map(sources, src ->
1106  
        jThreadedButton(
1107  
          str_shorten(src, 40),
1108  
          -> projectActions().goToSource(src)))));
1109  
  }
1110  
  
1111  
  L<TokenRangeWithSrc> uniquifySources(L<TokenRangeWithSrc> sources) {
1112  
    ret uniquifyWith(sources, src -> pair(src.sourceInfo, src.renderRange()));
1113  
  }
1114  
  
1115  
  structure_Data makeStructureData() {
1116  
    ret concepts().makeStructureData();
1117  
  }
1118  
  
1119  
  S g22struct(O o) {
1120  
    ret struct(o, makeStructureData());
1121  
  }
1122  
  
1123  
  O g22unstruct(S struct) {
1124  
    ret unstructure(struct, classFinder());
1125  
  }
1126  
  
1127  
  O stem() {
1128  
    ret dm_stem(module());
1129  
  }
1130  
  
1131  
  void reloadProject {
1132  
    masterStuff().reopenDB(getLoadedDB());
1133  
  }
1134  
1135  
  File downloadProjectFromGazAI(GazAICredentials credentials, S projectName) ctex {
1136  
    var cred = credentials.asParams();
1137  
    var params = cloneMap(cred);
1138  
    params.put("asZip", 1);
1139  
    
1140  
    var url = "https://" + gazAIHost() + "/dl-authed/gazelle/" + spaceToPercent20(projectName) + "/";
1141  
    var conn = urlConnection(url);
1142  
    
1143  
    var file = javaxBackupDir(concat(projectName + " Downloaded ", ymdMinusHMS(), ".zip"));
1144  
    doPostBinaryToFile(makePostData(params), conn, file);
1145  
1146  
    if (!isZip(file))
1147  
      fail("Download failed, not authenticated for " + gazAIHost() + "?");
1148  
1149  
    fileSavedInfoBox(file);
1150  
    ret file;
1151  
  }
1152  
  
1153  
  public void waitForAutoStart() {
1154  
    autoStarter().waitUntilDone();
1155  
  }
1156  
  
1157  
  void adaptTextEditor(JSyntaxTextFileEditor editor) {
1158  
    editor.adaptSyntaxTextArea = textArea ->
1159  
      g22_adaptSyntaxTextAreaForHashRefs(textArea, this);
1160  
  }
1161  
  
1162  
  Window projectWindow() {
1163  
    ret (Window) call(stem(), "window");
1164  
  }
1165  
} // end of G22Utils

download  show line numbers  debug dex  old transpilations   

Travelled to 4 computer(s): bhatertpkbcr, ekrmjmnbrukm, mowyntqkapby, mqqgnosmbjvj

No comments. add comment

Snippet ID: #1034148
Snippet name: G22Utils
Eternal ID of this version: #1034148/393
Text MD5: 974c4d889c207f200442450b507d81c2
Author: stefan
Category: javax / gazelle 22
Type: JavaX fragment (include)
Public (visible to everyone): Yes
Archived (hidden from active list): No
Created/modified: 2024-08-27 15:04:39
Source code size: 34895 bytes / 1165 lines
Pitched / IR pitched: No / No
Views / Downloads: 1094 / 3582
Version history: 392 change(s)
Referenced in: [show references]