Skip to content

Commit 2145db4

Browse files
committed
Usability improvements - External Viewer is the default, hints to configure Source Roots and Viewer command, viewer binary always inserted at the beginning of the command field
1 parent 062f753 commit 2145db4

File tree

3 files changed

+54
-30
lines changed

3 files changed

+54
-30
lines changed

plugins/sources/src/org/graalvm/visualvm/sources/VisualVMGoToSource.java

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,9 @@
2929
import org.graalvm.visualvm.lib.profiler.api.ProfilerDialogs;
3030
import org.graalvm.visualvm.lib.profiler.spi.java.GoToSourceProvider;
3131
import org.graalvm.visualvm.sources.impl.SourceHandles;
32+
import org.graalvm.visualvm.sources.impl.SourceRoots;
3233
import org.graalvm.visualvm.sources.impl.SourceViewers;
34+
import org.netbeans.api.options.OptionsDisplayer;
3335
import org.openide.filesystems.FileObject;
3436
import org.openide.util.Lookup;
3537
import org.openide.util.NbBundle;
@@ -40,6 +42,8 @@
4042
* @author Jiri Sedlacek
4143
*/
4244
@NbBundle.Messages({
45+
"VisualVMGoToSource_NoSourceRootsCaption=Go To Source", // NOI18N
46+
"VisualVMGoToSource_NoSourceRoots=<html><br><b>Source roots have not been defined yet.</b><br><br>Use Options | Sources | Definitions to define the directories or archives containing the sources.</html>", // NOI18N
4347
"VisualVMGoToSource_SourceNotFound=No source found for {0}", // NOI18N
4448
"VisualVMGoToSource_OpenSourceFailed=Failed to open source for {0}" // NOI18N
4549
})
@@ -69,12 +73,17 @@ public static final class Provider extends GoToSourceProvider {
6973

7074
@Override
7175
public boolean openSource(Lookup.Provider project, String className, String methodName, String signature, int line) {
72-
for (SourceHandleProvider provider : SourceHandles.registeredProviders()) {
73-
SourceHandle handle = provider.createHandle(className, methodName, signature, line);
74-
if (handle != null) return openSourceImpl(handle);
75-
}
76+
if (SourceRoots.getRoots().length == 0) {
77+
ProfilerDialogs.displayWarning(Bundle.VisualVMGoToSource_NoSourceRoots(), Bundle.VisualVMGoToSource_NoSourceRootsCaption(), null);
78+
OptionsDisplayer.getDefault().open("SourcesOptions"); // NOI18N
79+
} else {
80+
for (SourceHandleProvider provider : SourceHandles.registeredProviders()) {
81+
SourceHandle handle = provider.createHandle(className, methodName, signature, line);
82+
if (handle != null) return openSourceImpl(handle);
83+
}
7684

77-
ProfilerDialogs.displayError(Bundle.VisualVMGoToSource_SourceNotFound(className));
85+
ProfilerDialogs.displayError(Bundle.VisualVMGoToSource_SourceNotFound(className));
86+
}
7887

7988
return true;
8089
}

plugins/sources/src/org/graalvm/visualvm/sources/impl/SourceViewers.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ public final class SourceViewers {
3939

4040
private static final String PROP_SELECTED_VIEWER = "prop_SourceViewers_selected"; // NOI18N
4141

42+
private static final String DEFAULT_VIEWER_ID = ExternalSourcesViewer.ID;
43+
4244

4345
private static SourcesViewer FORCED_VIEWER;
4446

@@ -55,7 +57,7 @@ public static Collection<? extends SourcesViewer> getRegisteredViewers() {
5557
public static SourcesViewer getSelectedViewer() {
5658
if (isForcedViewer()) return FORCED_VIEWER;
5759

58-
String selectedID = NbPreferences.forModule(SourcesViewer.class).get(PROP_SELECTED_VIEWER, null);
60+
String selectedID = NbPreferences.forModule(SourcesViewer.class).get(PROP_SELECTED_VIEWER, DEFAULT_VIEWER_ID);
5961

6062
if (selectedID != null)
6163
for (SourcesViewer registered : getRegisteredViewers())

plugins/sources/src/org/graalvm/visualvm/sources/viewer/ExternalSourcesViewer.java

Lines changed: 37 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@
5050
import org.graalvm.visualvm.lib.ui.swing.PopupButton;
5151
import org.graalvm.visualvm.lib.ui.swing.SmallButton;
5252
import org.graalvm.visualvm.sources.SourceHandle;
53+
import org.netbeans.api.options.OptionsDisplayer;
5354
import org.openide.awt.Mnemonics;
5455
import org.openide.util.NbBundle;
5556
import org.openide.util.NbPreferences;
@@ -64,7 +65,8 @@
6465
"ExternalSourcesViewer_CommandHint=<select a predefined command or define a custom one>", // NOI18N
6566
"ExternalSourcesViewer_Name=External Viewer", // NOI18N
6667
"ExternalSourcesViewer_Description=custom command to launch an external viewer", // NOI18N
67-
"ExternalSourcesViewer_EmptyCommand=External viewer command is empty.", // NOI18N
68+
"ExternalSourcesViewer_NotConfiguredCaption=Go To Source", // NOI18N
69+
"ExternalSourcesViewer_NotConfigured=<html><br><b>Sources viewer has not been configured yet.</b><br><br>Use Options | Sources | Viewer to define the external IDE or editor to open the sources.<br><br>Customize a predefined template from the popup list or define a custom command using<br>the available parameters to launch the external sources viewer.<br><br>Alternatively choose to use a viewer registered in the OS (preselecting line not supported).</html>", // NOI18N
6870
"ExternalSourcesViewer_CommandFailed=Failed to open source in external viewer.\n\n{0}", // NOI18N
6971
"ExternalSourcesViewer_CommandLabel=&Command:", // NOI18N
7072
"ExternalSourcesViewer_RootsDialogCaption=Select File Or Directory", // NOI18N
@@ -77,7 +79,7 @@ public final class ExternalSourcesViewer extends SourcesViewer {
7779

7880
private static final Logger LOGGER = Logger.getLogger(ExternalSourcesViewer.class.getName());
7981

80-
private static final String ID = "ExternalSourcesViewer"; // NOI18N
82+
public static final String ID = "ExternalSourcesViewer"; // NOI18N
8183

8284
private static final String PROP_COMMAND = "prop_ExternalSourcesViewer_command"; // NOI18N
8385
private static final String DEFAULT_COMMAND = Bundle.ExternalSourcesViewer_CommandHint();
@@ -170,27 +172,11 @@ public ExternalSourcesViewer(String forcedCommand) {
170172

171173
@Override
172174
public boolean open(SourceHandle handle) {
173-
String expandedCommand = handle.expandFeatures(getCommand());
174-
if (expandedCommand.isEmpty()) {
175-
ProfilerDialogs.displayError(Bundle.ExternalSourcesViewer_EmptyCommand());
176-
} else {
177-
String commandS = getCommand();
178-
List<String> commandL = ExternalViewerLauncher.getCommandStrings(commandS);
179-
180-
for (int i = 0; i < commandL.size(); i++) {
181-
String command = commandL.get(i);
182-
command = handle.expandFeatures(command);
183-
commandL.set(i, command);
184-
}
185-
186-
new ExternalViewerLauncher(commandL) {
187-
@Override protected void failed(IOException e) {
188-
ProfilerDialogs.displayError(Bundle.ExternalSourcesViewer_CommandFailed(e.getMessage()));
189-
LOGGER.log(Level.INFO, "Opening external sources viewer failed", e); // NOI18N
190-
}
191-
}.run();
192-
}
175+
String command = getCommand();
193176

177+
if (command.isEmpty() || command.equals(DEFAULT_COMMAND)) configureCommand();
178+
else executeCommand(handle, command);
179+
194180
return true;
195181
}
196182

@@ -220,6 +206,29 @@ private String getCommand() {
220206
}
221207

222208

209+
private static void configureCommand() {
210+
ProfilerDialogs.displayWarning(Bundle.ExternalSourcesViewer_NotConfigured(), Bundle.ExternalSourcesViewer_NotConfiguredCaption(), null);
211+
OptionsDisplayer.getDefault().open("SourcesOptions"); // NOI18N
212+
}
213+
214+
private static void executeCommand(SourceHandle handle, String commandS) {
215+
List<String> commandL = ExternalViewerLauncher.getCommandStrings(commandS);
216+
217+
for (int i = 0; i < commandL.size(); i++) {
218+
String commandI = commandL.get(i);
219+
commandI = handle.expandFeatures(commandI);
220+
commandL.set(i, commandI);
221+
}
222+
223+
new ExternalViewerLauncher(commandL) {
224+
@Override protected void failed(IOException e) {
225+
ProfilerDialogs.displayError(Bundle.ExternalSourcesViewer_CommandFailed(e.getMessage()));
226+
LOGGER.log(Level.INFO, "Opening external sources viewer failed", e); // NOI18N
227+
}
228+
}.run();
229+
}
230+
231+
223232
@Override
224233
public JComponent getSettingsComponent() {
225234
if (settingsPanel == null) {
@@ -339,8 +348,12 @@ private static void insertFile(JTextField textField, File file) {
339348
String path = file.getAbsolutePath();
340349
if (path.contains(" ")) path = "\"" + path + "\""; // NOI18N
341350

342-
try { textField.getDocument().insertString(textField.getCaretPosition(), path, null); }
343-
catch (BadLocationException ex) {}
351+
// try { textField.getDocument().insertString(textField.getCaretPosition(), path, null); }
352+
try {
353+
textField.getDocument().insertString(0, path, null);
354+
textField.select(0, path.length());
355+
textField.requestFocusInWindow();
356+
} catch (BadLocationException ex) {}
344357
}
345358

346359
private static void insertParameter(JTextField textField, String parameter) {

0 commit comments

Comments
 (0)