Skip to content

Commit 84dc340

Browse files
authored
Add mechanism for alerting the user when they try to do something wrong (#693)
1 parent 607d073 commit 84dc340

File tree

4 files changed

+114
-11
lines changed

4 files changed

+114
-11
lines changed
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
package edu.wpi.grip.core.events;
2+
3+
import static com.google.common.base.Preconditions.checkNotNull;
4+
5+
/**
6+
* An event fired when the user should be warned they tried to do something unsupported, such as
7+
* trying to generate code with an operation that does not support code gen.
8+
*
9+
* <p>The event contains a short header text describing the warning and a detailed body text
10+
* that lets the user know why what they attempted was not allowed.</p>
11+
*/
12+
public class WarningEvent {
13+
14+
private final String header;
15+
private final String body;
16+
17+
/**
18+
* Creates a new warning event.
19+
*
20+
* @param header the header or title of the warning (e.g. "Cannot generate code").
21+
* This should be short and descriptive.
22+
* @param body the body of the warning.
23+
* This should go into detail about what the user did wrong.
24+
*/
25+
public WarningEvent(String header, String body) {
26+
checkNotNull(header, "Header text cannot be null");
27+
checkNotNull(body, "Body text cannot be null");
28+
this.header = header;
29+
this.body = body;
30+
}
31+
32+
/**
33+
* Gets the warning header.
34+
*/
35+
public String getHeader() {
36+
return header;
37+
}
38+
39+
/**
40+
* Gets the warning body.
41+
*/
42+
public String getBody() {
43+
return body;
44+
}
45+
46+
}

ui/src/main/java/edu/wpi/grip/ui/MainWindowController.java

Lines changed: 25 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
import edu.wpi.grip.core.events.ProjectSettingsChangedEvent;
99
import edu.wpi.grip.core.events.TimerEvent;
1010
import edu.wpi.grip.core.events.UnexpectedThrowableEvent;
11+
import edu.wpi.grip.core.events.WarningEvent;
1112
import edu.wpi.grip.core.serialization.Project;
1213
import edu.wpi.grip.core.settings.AppSettings;
1314
import edu.wpi.grip.core.settings.ProjectSettings;
@@ -31,7 +32,6 @@
3132
import java.util.logging.Logger;
3233

3334
import javafx.application.Platform;
34-
import javafx.event.ActionEvent;
3535
import javafx.fxml.FXML;
3636
import javafx.scene.Parent;
3737
import javafx.scene.Scene;
@@ -275,9 +275,9 @@ protected void quit() {
275275
/**
276276
* Controls the export button in the main menu. Opens a filechooser with language selection.
277277
* The user can select the language to export to, save location and file name.
278-
* @param actionEvent Unused event passed by the controller.
279278
*/
280-
public void generate(ActionEvent actionEvent) {
279+
@FXML
280+
public void generate() {
281281
final FileChooser fileChooser = new FileChooser();
282282
fileChooser.setTitle("Export to");
283283
fileChooser.getExtensionFilters().add(new ExtensionFilter(Language.JAVA.name, "*.java"));
@@ -290,13 +290,15 @@ public void generate(ActionEvent actionEvent) {
290290
}
291291
Language lang = Language.get(fileChooser.getSelectedExtensionFilter().getDescription());
292292
Exporter exporter = new Exporter(pipeline.getSteps(), lang, file);
293-
final Set<String> nonExportableSteps = exporter.getNonExportableSteps();
293+
final Set<String> nonExportableSteps = exporter.getNonExportableStepNames();
294294
if (!nonExportableSteps.isEmpty()) {
295-
StringBuilder b = new StringBuilder("The following steps cannot be exported:\n");
296-
nonExportableSteps.forEach(n -> b.append(" ").append(n).append('\n'));
297-
Alert alert = new Alert(Alert.AlertType.WARNING);
298-
alert.setContentText(b.toString());
299-
alert.showAndWait();
295+
StringBuilder b = new StringBuilder(
296+
"The following steps do not support code generation:\n\n"
297+
);
298+
nonExportableSteps.stream()
299+
.sorted()
300+
.forEach(n -> b.append(" - ").append(n).append("\n"));
301+
eventBus.post(new WarningEvent("Cannot generate code", b.toString()));
300302
return;
301303
}
302304
Thread exportRunner = new Thread(exporter);
@@ -325,7 +327,20 @@ protected void deploy() {
325327
}
326328

327329
@Subscribe
328-
@SuppressWarnings( {"PMD.UnusedPrivateMethod", "PMD.UnusedFormalParameter"})
330+
public void onWarningEvent(WarningEvent e) {
331+
if (Platform.isFxApplicationThread()) {
332+
showWarningAlert(e);
333+
} else {
334+
Platform.runLater(() -> showWarningAlert(e));
335+
}
336+
}
337+
338+
private void showWarningAlert(WarningEvent e) {
339+
Alert alert = new WarningAlert(e.getHeader(), e.getBody(), root.getScene().getWindow());
340+
alert.showAndWait();
341+
}
342+
343+
@SuppressWarnings({"PMD.UnusedPrivateMethod", "PMD.UnusedFormalParameter"})
329344
private void runStopped(TimerEvent event) {
330345
if (event.getTarget() instanceof PipelineRunner) {
331346
Platform.runLater(() -> updateElapsedTimeLabel(event.getElapsedTime()));
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
package edu.wpi.grip.ui;
2+
3+
import javafx.scene.control.Alert;
4+
import javafx.scene.layout.Region;
5+
import javafx.stage.StageStyle;
6+
import javafx.stage.Window;
7+
8+
import static com.google.common.base.Preconditions.checkNotNull;
9+
10+
/**
11+
* An alert that warns the user when they try to do something unsupported, such as trying to
12+
* generate code with an operation that does not support code gen.
13+
*/
14+
public class WarningAlert extends Alert {
15+
16+
/**
17+
* Creates a new warning alert.
18+
*
19+
* @param header the header text of the alert. This should be short and descriptive.
20+
* @param body the body text of the alert. This should go into detail about the warning
21+
* and what prompted it.
22+
* @param owner the owner window of this alert
23+
*
24+
* @throws NullPointerException if any of the parameters are null
25+
*/
26+
public WarningAlert(String header, String body, Window owner) {
27+
super(AlertType.WARNING);
28+
checkNotNull(header, "The header text cannot be null");
29+
checkNotNull(body, "The body text cannot be null");
30+
checkNotNull(owner, "The owner window cannot be null");
31+
32+
initStyle(StageStyle.UTILITY);
33+
initOwner(owner);
34+
getDialogPane().setMinHeight(Region.USE_PREF_SIZE); // expand to fit content
35+
getDialogPane().setMinWidth(Region.USE_PREF_SIZE);
36+
37+
setTitle("Warning | " + header);
38+
setHeaderText(header);
39+
setContentText(body);
40+
}
41+
42+
}

ui/src/main/java/edu/wpi/grip/ui/codegeneration/Exporter.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ public void run() {
9999
*
100100
* @return a set of the names of the non-exportable operations in the pipeline
101101
*/
102-
public Set<String> getNonExportableSteps() {
102+
public Set<String> getNonExportableStepNames() {
103103
return steps.stream()
104104
.filter(s -> {
105105
return s.getOperationDescription().category() != OperationDescription.Category.NETWORK;

0 commit comments

Comments
 (0)