Skip to content

Commit 7d1576f

Browse files
committed
Improve Syntaxes, preferences & prompts logic
- Support for Kotlin and Markdown syntaxes - Reset Layout when reseting preferences - Patches for RSyntaxArea 3.3.0 - Move all JOptionPane prompts to centralized methods. This simplifies code and would simplify migration to e.g., UIService, or hacking the Swing L&F to match that of the RSyntaxArea theme
1 parent b4d919a commit 7d1576f

File tree

6 files changed

+148
-132
lines changed

6 files changed

+148
-132
lines changed

pom.xml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -164,10 +164,12 @@
164164
<dependency>
165165
<groupId>com.fifesoft</groupId>
166166
<artifactId>rsyntaxtextarea</artifactId>
167+
<version>3.3.0</version>
167168
</dependency>
168169
<dependency>
169170
<groupId>com.fifesoft</groupId>
170171
<artifactId>languagesupport</artifactId>
172+
<version>3.3.0</version>
171173
</dependency>
172174
<dependency>
173175
<groupId>com.miglayout</groupId>
@@ -199,6 +201,10 @@
199201
<artifactId>scripting-groovy</artifactId>
200202
<scope>test</scope>
201203
</dependency>
204+
<dependency>
205+
<groupId>com.formdev</groupId>
206+
<artifactId>flatlaf</artifactId>
207+
</dependency>
202208
</dependencies>
203209

204210
<repositories>

src/main/java/org/scijava/ui/swing/script/EditorPane.java

Lines changed: 5 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,6 @@
5656
import javax.swing.ButtonGroup;
5757
import javax.swing.JMenu;
5858
import javax.swing.JMenuItem;
59-
import javax.swing.JOptionPane;
6059
import javax.swing.JPopupMenu;
6160
import javax.swing.JRadioButtonMenuItem;
6261
import javax.swing.JScrollPane;
@@ -314,7 +313,9 @@ private JMenu geSyntaxForNoneLang() {
314313
menu.add(getSyntaxItem(bg, "Dockerfile", SYNTAX_STYLE_DOCKERFILE));
315314
menu.add(getSyntaxItem(bg, "HTML", SYNTAX_STYLE_HTML));
316315
menu.add(getSyntaxItem(bg, "JSON", SYNTAX_STYLE_JSON));
316+
menu.add(getSyntaxItem(bg, "Kotlin", SYNTAX_STYLE_KOTLIN));
317317
menu.add(getSyntaxItem(bg, "Makefile", SYNTAX_STYLE_MAKEFILE));
318+
menu.add(getSyntaxItem(bg, "Markdown", SYNTAX_STYLE_MARKDOWN));
318319
menu.add(getSyntaxItem(bg, "SH", SYNTAX_STYLE_UNIX_SHELL));
319320
menu.add(getSyntaxItem(bg, "XML", SYNTAX_STYLE_XML));
320321
menu.add(getSyntaxItem(bg, "YAML", SYNTAX_STYLE_YAML));
@@ -337,7 +338,7 @@ private JMenuItem getSyntaxItem(final ButtonGroup bg, final String label, final
337338
}
338339

339340
void error(final String message) {
340-
JOptionPane.showMessageDialog(this, message, "Error", JOptionPane.ERROR_MESSAGE);
341+
TextEditor.GuiUtils.error(this, message);
341342
}
342343

343344
private void updateNoneLangSyntaxMenu(final ScriptLanguage language) {
@@ -948,8 +949,7 @@ public void toggleBookmark(final int line) {
948949
}
949950
catch (final BadLocationException e) {
950951
/* ignore */
951-
JOptionPane.showMessageDialog(this, "Cannot toggle bookmark at this location.", "Error",
952-
JOptionPane.ERROR_MESSAGE);
952+
error("Cannot toggle bookmark at this location.");
953953
}
954954
}
955955
}
@@ -1099,7 +1099,7 @@ public void loadPreferences() {
10991099
*/
11001100
public void applyTheme(final String theme) throws IllegalArgumentException {
11011101
try {
1102-
applyTheme(getTheme(theme));
1102+
applyTheme(TextEditor.getTheme(theme));
11031103
} catch (final Exception ex) {
11041104
throw new IllegalArgumentException(ex);
11051105
}
@@ -1117,15 +1117,6 @@ private void applyTheme(final Theme th) throws IllegalArgumentException {
11171117
GutterUtils.updateIcons(gutter);
11181118
}
11191119

1120-
private static Theme getTheme(final String theme) throws IllegalArgumentException {
1121-
try {
1122-
return Theme
1123-
.load(TextEditor.class.getResourceAsStream("/org/fife/ui/rsyntaxtextarea/themes/" + theme + ".xml"));
1124-
} catch (final Exception ex) {
1125-
throw new IllegalArgumentException(ex);
1126-
}
1127-
}
1128-
11291120
public String loadFolders() {
11301121
return prefService.get(getClass(), FOLDERS_PREFS, System.getProperty("user.home"));
11311122
}

src/main/java/org/scijava/ui/swing/script/FileSystemTreePanel.java

Lines changed: 11 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,6 @@
5454
import javax.swing.JCheckBoxMenuItem;
5555
import javax.swing.JFileChooser;
5656
import javax.swing.JMenuItem;
57-
import javax.swing.JOptionPane;
5857
import javax.swing.JPanel;
5958
import javax.swing.JPopupMenu;
6059
import javax.swing.JScrollPane;
@@ -119,14 +118,11 @@ class FileSystemTreePanel extends JPanel {
119118
final List<File> dirs = Arrays.asList(files).stream().filter(f -> f.isDirectory())
120119
.collect(Collectors.toList());
121120
if (dirs.isEmpty()) {
122-
JOptionPane.showMessageDialog(this, "Only folders can be dropped into the file tree.",
123-
"Invalid Drop", JOptionPane.WARNING_MESSAGE);
121+
TextEditor.GuiUtils.warn(this, "Only folders can be dropped into the file tree.");
124122
return;
125123
}
126-
final boolean confirm = dirs.size() < 4 || (JOptionPane.showConfirmDialog(this,
127-
"Confirm loading of " + dirs.size() + " folders?", "Confirm?",
128-
JOptionPane.OK_CANCEL_OPTION) == JOptionPane.OK_OPTION);
129-
if (confirm) {
124+
if (TextEditor.GuiUtils.confirm(this, "Confirm loading of " + dirs.size() + " folders?", "Confirm?",
125+
"Confirm")) {
130126
dirs.forEach(dir -> tree.addRootDirectory(dir.getAbsolutePath(), true));
131127
}
132128
});
@@ -256,17 +252,15 @@ private JButton removeDirectoryButton() {
256252
remove_directory.addActionListener(e -> {
257253
final TreePath p = tree.getSelectionPath();
258254
if (null == p) {
259-
JOptionPane.showMessageDialog(this, "Select a top-level folder first.", "Invalid Folder",
260-
JOptionPane.ERROR_MESSAGE);
255+
TextEditor.GuiUtils.error(this, "Select a top-level folder first.");
261256
return;
262257
}
263258
if (2 == p.getPathCount()) {
264259
// Is a child of the root, so it's a top-level folder
265260
tree.getModel().removeNodeFromParent(//
266261
(FileSystemTree.Node) p.getLastPathComponent());
267262
} else {
268-
JOptionPane.showMessageDialog(this, "Can only remove top-level folders.", "Invalid Folder",
269-
JOptionPane.ERROR_MESSAGE);
263+
TextEditor.GuiUtils.error(this, "Can only remove top-level folders.");
270264
}
271265
});
272266
return remove_directory;
@@ -326,34 +320,30 @@ private void addContextualMenuToTree() {
326320
jmi.addActionListener(e -> {
327321
final TreePath path = tree.getSelectionPath();
328322
if (path == null) {
329-
JOptionPane.showMessageDialog(this, "No items are currently selected.", "Invalid Selection",
330-
JOptionPane.INFORMATION_MESSAGE);
323+
TextEditor.GuiUtils.info(this, "No items are currently selected.", "Invalid Selection");
331324
return;
332325
}
333326
try {
334327
final String filepath = (String) ((FileSystemTree.Node) path.getLastPathComponent()).getUserObject();
335328
final File f = new File(filepath);
336329
Desktop.getDesktop().open((f.isDirectory()) ? f : f.getParentFile());
337330
} catch (final Exception | Error ignored) {
338-
JOptionPane.showMessageDialog(this, "Folder of selected item does not seem to be accessible.", "Error",
339-
JOptionPane.ERROR_MESSAGE);
331+
TextEditor.GuiUtils.error(this, "Folder of selected item does not seem to be accessible.");
340332
}
341333
});
342334
popup.add(jmi);
343335
jmi = new JMenuItem("Open in Terminal");
344336
jmi.addActionListener(e -> {
345337
final TreePath path = tree.getSelectionPath();
346338
if (path == null) {
347-
JOptionPane.showMessageDialog(this, "No items are currently selected.", "Invalid Selection",
348-
JOptionPane.INFORMATION_MESSAGE);
339+
TextEditor.GuiUtils.info(this, "No items are currently selected.", "Invalid Selection");
349340
return;
350341
}
351342
try {
352343
final String filepath = (String) ((FileSystemTree.Node) path.getLastPathComponent()).getUserObject();
353344
TextEditor.GuiUtils.openTerminal(new File(filepath));
354345
} catch (final Exception ignored) {
355-
JOptionPane.showMessageDialog(this, "Could not open path in Terminal.", "Error",
356-
JOptionPane.ERROR_MESSAGE);
346+
TextEditor.GuiUtils.error(this, "Could not open path in Terminal.");
357347
}
358348
});
359349
popup.add(jmi);
@@ -381,7 +371,7 @@ private void expandImmediateNodes() {
381371
}
382372

383373
private void showHelpMsg() {
384-
final String msg = "<HTML><div WIDTH=500>" //
374+
final String msg = "<HTML>" //
385375
+ "<p><b>Overview</b></p>" //
386376
+ "<p>The File Explorer pane provides a direct view of selected folders. Changes in " //
387377
+ "the native file system are synchronized in real time.</p>" //
@@ -410,7 +400,7 @@ private void showHelpMsg() {
410400
+ " <td>Display filenames starting with <i>Demo</i></td>" //
411401
+ " </tr>" //
412402
+ "</table>";
413-
JOptionPane.showMessageDialog(this, msg, "File Explorer Pane", JOptionPane.PLAIN_MESSAGE);
403+
TextEditor.GuiUtils.showHTMLDialog(this.getRootPane(), "File Explorer Pane", msg);
414404
}
415405

416406
private boolean isCaseSensitive() {

src/main/java/org/scijava/ui/swing/script/GutterUtils.java

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,9 +49,12 @@ public class GutterUtils {
4949
GutterUtils(final Gutter gutter) {
5050
this.gutter = gutter;
5151
gutter.setSpacingBetweenLineNumbersAndFoldIndicator(0);
52+
//gutter.setFoldIndicatorStyle(org.fife.ui.rtextarea.FoldIndicatorStyle.MODERN); // DEFAULT
53+
gutter.setShowCollapsedRegionToolTips(true);
5254
}
5355

54-
private void updateFoldIcons() {
56+
@SuppressWarnings("unused")
57+
private void updateFoldIcons() { // no longer needed since v3.3.0
5558
int size;
5659
try {
5760
size = (int) new FoldIndicator(null).getPreferredSize().getWidth();
@@ -63,7 +66,7 @@ private void updateFoldIcons() {
6366
final int fontSize = gutter.getLineNumberFont().getSize();
6467
if (size > fontSize)
6568
size = fontSize;
66-
gutter.setFoldIcons(new FoldIcon(true, size), new FoldIcon(false, size));
69+
//gutter.setFoldIcons(new FoldIcon(true, size), new FoldIcon(false, size));
6770
}
6871

6972
private ImageIcon getBookmarkIcon() {
@@ -94,10 +97,11 @@ private void updateBookmarkIcon() {
9497

9598
public static void updateIcons(final Gutter gutter) {
9699
final GutterUtils utils = new GutterUtils(gutter);
97-
utils.updateFoldIcons();
100+
//utils.updateFoldIcons();
98101
utils.updateBookmarkIcon();
99102
}
100103

104+
@SuppressWarnings("unused")
101105
private class FoldIcon implements Icon {
102106

103107
private final boolean collapsed;

src/main/java/org/scijava/ui/swing/script/Main.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,9 @@
3838
import org.scijava.script.ScriptLanguage;
3939
import org.scijava.script.ScriptService;
4040

41+
import com.formdev.flatlaf.FlatDarkLaf;
42+
import com.formdev.flatlaf.FlatLightLaf;
43+
4144
/**
4245
* Main entry point for launching the script editor standalone.
4346
*
@@ -65,6 +68,7 @@ public void windowClosed(final WindowEvent e) {
6568
editor.setVisible(true);
6669
}
6770
public static void main(String[] args) throws Exception {
71+
FlatDarkLaf.setup();
6872
String lang = args.length == 0 ? "Java" : args[0];
6973
launch(lang);
7074
}

0 commit comments

Comments
 (0)