Skip to content

Commit 80fd9dd

Browse files
committed
Create new menu item "Source or javadoc for class or package..." which
fixes or replaces the "Open Help" menu item, by using ClassUtils and showing a UI that lists all matching classes with buttons to open their source code in github or gitlab and the javadoc when available (will guess the URL, load it, and not show a link to it when 404). Can match partial text (the list of possible classes may be longer) and can also match package names or partial package names. Any substring of a fully qualified class name will be matched, which is fabulous. (Compare with current implementatio nof "Open Help..." which requires a fully qualified class name to work, which is not useful as often one does not know it or not have it handy in a script.)
1 parent 0a1b443 commit 80fd9dd

File tree

1 file changed

+79
-1
lines changed

1 file changed

+79
-1
lines changed

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

Lines changed: 79 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
package org.scijava.ui.swing.script;
3131

3232
import java.awt.Color;
33+
import java.awt.Cursor;
3334
import java.awt.Dimension;
3435
import java.awt.Font;
3536
import java.awt.GridBagConstraints;
@@ -108,6 +109,7 @@
108109
import javax.swing.JCheckBoxMenuItem;
109110
import javax.swing.JFileChooser;
110111
import javax.swing.JFrame;
112+
import javax.swing.JLabel;
111113
import javax.swing.JMenu;
112114
import javax.swing.JMenuBar;
113115
import javax.swing.JMenuItem;
@@ -214,7 +216,7 @@ public class TextEditor extends JFrame implements ActionListener,
214216
openMacroFunctions, decreaseFontSize, increaseFontSize, chooseFontSize,
215217
chooseTabSize, gitGrep, openInGitweb, replaceTabsWithSpaces,
216218
replaceSpacesWithTabs, toggleWhiteSpaceLabeling, zapGremlins,
217-
savePreferences, toggleAutoCompletionMenu;
219+
savePreferences, toggleAutoCompletionMenu, openClassOrPackageHelp;
218220
private RecentFilesMenuItem openRecent;
219221
private JMenu gitMenu, tabsMenu, fontSizeMenu, tabSizeMenu, toolsMenu,
220222
runMenu, whiteSpaceMenu;
@@ -483,6 +485,8 @@ public TextEditor(final Context context) {
483485
openHelp =
484486
addToMenu(toolsMenu, "Open Help for Class (with frames)...", 0, 0);
485487
openHelp.setMnemonic(KeyEvent.VK_P);
488+
openClassOrPackageHelp = addToMenu(toolsMenu, "Source or javadoc for class or package...", 0, 0);
489+
openClassOrPackageHelp.setMnemonic(KeyEvent.VK_S);
486490
openMacroFunctions =
487491
addToMenu(toolsMenu, "Open Help on Macro Functions...", 0, 0);
488492
openMacroFunctions.setMnemonic(KeyEvent.VK_H);
@@ -1400,6 +1404,7 @@ else if (source == savePreferences) {
14001404
}
14011405
else if (source == openHelp) openHelp(null);
14021406
else if (source == openHelpWithoutFrames) openHelp(null, false);
1407+
else if (source == openClassOrPackageHelp) openClassOrPackageHelp(null);
14031408
else if (source == openMacroFunctions) try {
14041409
new MacroFunctions(this).openHelp(getTextArea().getSelectedText());
14051410
}
@@ -2664,6 +2669,79 @@ public void openHelp(String className, final boolean withFrames) {
26642669
handleException(e);
26652670
}
26662671
}
2672+
2673+
/**
2674+
* @param text Either a classname, or a partial class name, or package name or any part of the fully qualified class name.
2675+
*/
2676+
public void openClassOrPackageHelp(String text) {
2677+
if (text == null)
2678+
text = getSelectedClassNameOrAsk();
2679+
if (null == text) return;
2680+
new Thread(new FindClassSourceAndJavadoc(text)).start(); // fork away from event dispatch thread
2681+
}
2682+
2683+
public class FindClassSourceAndJavadoc implements Runnable {
2684+
private final String text;
2685+
public FindClassSourceAndJavadoc(final String text) {
2686+
this.text = text;
2687+
}
2688+
@Override
2689+
public void run() {
2690+
setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
2691+
final HashMap<String, ArrayList<String>> matches;
2692+
try {
2693+
matches = ClassUtil.findDocumentationForClass(text);
2694+
} finally {
2695+
setCursor(Cursor.getPredefinedCursor(Cursor.DEFAULT_CURSOR));
2696+
}
2697+
if (matches.isEmpty()) {
2698+
JOptionPane.showMessageDialog(getEditorPane(), "No info found for:\n'" + text +'"');
2699+
return;
2700+
}
2701+
final JPanel panel = new JPanel();
2702+
final GridBagLayout gridbag = new GridBagLayout();
2703+
final GridBagConstraints c = new GridBagConstraints();
2704+
panel.setLayout(gridbag);
2705+
panel.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));
2706+
final List<String> keys = new ArrayList<String>(matches.keySet());
2707+
Collections.sort(keys);
2708+
c.gridy = 0;
2709+
for (final String classname: keys) {
2710+
c.gridx = 0;
2711+
c.anchor = GridBagConstraints.EAST;
2712+
final JLabel class_label = new JLabel(classname);
2713+
gridbag.setConstraints(class_label, c);
2714+
panel.add(class_label);
2715+
for (final String url: matches.get(classname)) {
2716+
c.gridx += 1;
2717+
c.anchor = GridBagConstraints.WEST;
2718+
final JButton link = new JButton(url.endsWith("java") ? "Source" : "JavaDoc");
2719+
gridbag.setConstraints(link, c);
2720+
panel.add(link);
2721+
link.addActionListener(new ActionListener() {
2722+
public void actionPerformed(final ActionEvent event) {
2723+
try {
2724+
platformService.open(new URL(url));
2725+
} catch (Exception e) {
2726+
e.printStackTrace();
2727+
}
2728+
}
2729+
});
2730+
}
2731+
c.gridy += 1;
2732+
}
2733+
final JScrollPane jsp = new JScrollPane(panel);
2734+
//jsp.setPreferredSize(new Dimension(800, 500));
2735+
SwingUtilities.invokeLater(new Runnable() {
2736+
public void run() {
2737+
final JFrame frame = new JFrame(text);
2738+
frame.getContentPane().add(jsp);
2739+
frame.pack();
2740+
frame.setVisible(true);
2741+
}
2742+
});
2743+
}
2744+
}
26672745

26682746
public void extractSourceJar() {
26692747
final File file = openWithDialog(null);

0 commit comments

Comments
 (0)