mirror of
https://github.com/AppleCommander/AppleCommander.git
synced 2026-10-24 23:02:27 +00:00
Adding About box. Updated FXControls to allow horizontal or vertical components.
This commit is contained in:
1 parent
65ba57449a
commit
f95b7e37fa
9 files changed
+153
-23
No files matched your search
@@ -7,6 +7,7 @@ module org.applecommander.javafx {
|
||||
requires org.applecommander.api;
|
||||
requires org.applecommander.applesingle;
|
||||
requires org.applecommander.bastools;
|
||||
requires org.applecommander.shrinkit;
|
||||
|
||||
opens org.applecommander.javafx to javafx.graphics;
|
||||
opens org.applecommander.javafx.settings to javafx.graphics;
|
||||
|
||||
@@ -30,9 +30,12 @@ import java.io.PrintWriter;
|
||||
import java.io.StringWriter;
|
||||
|
||||
public class AppleCommanderFX extends Application {
|
||||
private static AppleCommanderFX application;
|
||||
|
||||
@Override
|
||||
public void start(Stage stage) throws Exception {
|
||||
// This is really stupid the hoops just to launch the browser.
|
||||
application = this;
|
||||
// Based on user selection, use that theme.
|
||||
Settings.getThemeSelection().orElse(ThemeSelection.MODENA).apply();
|
||||
Platform.getPreferences().colorSchemeProperty().addListener((_, _, _) -> {
|
||||
@@ -46,6 +49,10 @@ public class AppleCommanderFX extends Application {
|
||||
launch(args);
|
||||
}
|
||||
|
||||
public static AppleCommanderFX getApplication() {
|
||||
return application;
|
||||
}
|
||||
|
||||
public static String buildTitle(String... args) {
|
||||
StringWriter sw = new StringWriter();
|
||||
PrintWriter pw = new PrintWriter(sw);
|
||||
|
||||
@@ -23,11 +23,13 @@ import javafx.beans.property.BooleanProperty;
|
||||
import javafx.beans.property.ObjectProperty;
|
||||
import javafx.event.ActionEvent;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.geometry.Orientation;
|
||||
import javafx.geometry.Pos;
|
||||
import javafx.scene.Node;
|
||||
import javafx.scene.control.CheckBox;
|
||||
import javafx.scene.control.Label;
|
||||
import javafx.scene.control.RadioButton;
|
||||
import javafx.scene.control.ToggleGroup;
|
||||
import javafx.scene.control.*;
|
||||
import javafx.scene.layout.GridPane;
|
||||
import javafx.scene.layout.HBox;
|
||||
import javafx.scene.layout.Pane;
|
||||
import javafx.scene.layout.VBox;
|
||||
|
||||
import java.util.function.Function;
|
||||
@@ -35,26 +37,82 @@ import java.util.function.Function;
|
||||
/// This is a simple control builder for JavaFX components. It is intended to include bindings
|
||||
/// that reflect the given property.
|
||||
public class FXControls {
|
||||
public static FXControls builder() {
|
||||
return new FXControls();
|
||||
public static FXControls vertical() {
|
||||
return new FXControls(new VBox());
|
||||
}
|
||||
public static FXControls horizontal() {
|
||||
return new FXControls(new HBox());
|
||||
}
|
||||
|
||||
private final VBox vbox;
|
||||
private final Pane pane;
|
||||
|
||||
private FXControls() {
|
||||
vbox = new VBox();
|
||||
vbox.setSpacing(10);
|
||||
vbox.setPadding(new Insets(10));
|
||||
private FXControls(Pane pane) {
|
||||
this.pane = pane;
|
||||
spacing(10);
|
||||
pane.setPadding(new Insets(10));
|
||||
}
|
||||
|
||||
public Node get() {
|
||||
return vbox;
|
||||
return pane;
|
||||
}
|
||||
|
||||
public FXControls alignment(Pos value) {
|
||||
if (pane instanceof VBox vbox) {
|
||||
vbox.setAlignment(value);
|
||||
}
|
||||
else if (pane instanceof HBox hbox) {
|
||||
hbox.setAlignment(value);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls spacing(double value) {
|
||||
if (pane instanceof VBox vbox) {
|
||||
vbox.setSpacing(value);
|
||||
}
|
||||
else if (pane instanceof HBox hbox) {
|
||||
hbox.setSpacing(value);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls node(Node node) {
|
||||
pane.getChildren().add(node);
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls label(String fmt, Object... args) {
|
||||
Label label = new Label(String.format(fmt, args));
|
||||
label.setWrapText(true);
|
||||
vbox.getChildren().add(label);
|
||||
pane.getChildren().add(label);
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls link(String text, String url) {
|
||||
Hyperlink hyperlink = new Hyperlink(url);
|
||||
hyperlink.setText(text);
|
||||
hyperlink.setOnAction(event -> {
|
||||
AppleCommanderFX.getApplication().getHostServices().showDocument(url);
|
||||
});
|
||||
pane.getChildren().add(hyperlink);
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls largeBold(String fmt, Object... args) {
|
||||
Label label = new Label(String.format(fmt, args));
|
||||
label.setWrapText(true);
|
||||
label.setStyle("-fx-font-weight: bold; -fx-font-size: 150%");
|
||||
pane.getChildren().add(label);
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls separator() {
|
||||
if (pane instanceof VBox vbox) {
|
||||
vbox.getChildren().add(new Separator(Orientation.HORIZONTAL));
|
||||
}
|
||||
else if (pane instanceof HBox hbox) {
|
||||
hbox.getChildren().add(new Separator(Orientation.VERTICAL));
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@@ -69,7 +127,7 @@ public class FXControls {
|
||||
});
|
||||
radioButton.addEventHandler(ActionEvent.ACTION, _ -> property.set(value));
|
||||
property.addListener((_, _, newValue) -> radioButton.setSelected(newValue.equals(value)));
|
||||
vbox.getChildren().add(radioButton);
|
||||
pane.getChildren().add(radioButton);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
@@ -80,7 +138,30 @@ public class FXControls {
|
||||
// We cannot bind this property, need to add listeners in BOTH directions.
|
||||
checkBox.addEventHandler(ActionEvent.ACTION, _ -> property.set(checkBox.isSelected()));
|
||||
property.addListener((_, _, newValue) -> checkBox.setSelected(newValue));
|
||||
vbox.getChildren().add(checkBox);
|
||||
pane.getChildren().add(checkBox);
|
||||
return this;
|
||||
}
|
||||
|
||||
public FXControls table(int columnCount, String... values) {
|
||||
assert values.length % columnCount == 0;
|
||||
GridPane grid = new GridPane();
|
||||
grid.setAlignment(Pos.CENTER);
|
||||
grid.setHgap(5);
|
||||
grid.setVgap(5);
|
||||
int col = 0;
|
||||
int row = 0;
|
||||
for (String value : values) {
|
||||
Label label = new Label(value);
|
||||
if (col == 0) label.setStyle("-fx-font-weight: bold;");
|
||||
else label.setWrapText(true);
|
||||
grid.add(label, col, row);
|
||||
col++;
|
||||
if (col >= columnCount) {
|
||||
col = 0;
|
||||
row++;
|
||||
}
|
||||
}
|
||||
pane.getChildren().add(grid);
|
||||
return this;
|
||||
}
|
||||
}
|
||||
@@ -19,6 +19,7 @@
|
||||
*/
|
||||
package org.applecommander.javafx;
|
||||
|
||||
import com.webcodepro.applecommander.ui.AppleCommander;
|
||||
import javafx.beans.property.*;
|
||||
import javafx.geometry.Insets;
|
||||
import javafx.geometry.Orientation;
|
||||
@@ -37,12 +38,15 @@ import javafx.scene.shape.Rectangle;
|
||||
import javafx.stage.FileChooser;
|
||||
import javafx.stage.FileChooser.ExtensionFilter;
|
||||
import javafx.stage.Stage;
|
||||
import org.applecommander.applesingle.AppleSingle;
|
||||
import org.applecommander.bastools.api.BasTools;
|
||||
import org.applecommander.capability.Capability;
|
||||
import org.applecommander.filestore.FileStore;
|
||||
import org.applecommander.filestore.FileStores;
|
||||
import org.applecommander.javafx.settings.Settings;
|
||||
import org.applecommander.javafx.settings.SettingsDialog;
|
||||
import org.applecommander.javafx.wizard.CreateFileStoreWizard;
|
||||
import org.applecommander.shrinkit.NuFileArchive;
|
||||
import org.applecommander.source.Source;
|
||||
import org.applecommander.source.Sources;
|
||||
import org.applecommander.usage.DiskUsage;
|
||||
@@ -50,6 +54,7 @@ import org.applecommander.util.FileExtensions;
|
||||
import org.applecommander.util.FileExtensions.FileExtension;
|
||||
|
||||
import java.io.File;
|
||||
import java.net.URL;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.StandardOpenOption;
|
||||
import java.util.Objects;
|
||||
@@ -66,6 +71,7 @@ public class FileStoreWindow {
|
||||
private final Button saveFileButton;
|
||||
private final Button saveFileAsButton;
|
||||
private final Button settingsButton;
|
||||
private final Button aboutButton;
|
||||
private final ToggleButton filesViewButton;
|
||||
private final ToggleButton diskUsageViewButton;
|
||||
private final ToggleButton informationViewButton;
|
||||
@@ -146,6 +152,7 @@ public class FileStoreWindow {
|
||||
saveFileButton = createButton("save-file.png", "Save", _ -> saveFile());
|
||||
saveFileAsButton = createButton("save-as-file.png", "Save As...", _ -> saveFileAs());
|
||||
settingsButton = createButton("settings.png", "Settings", _ -> settings());
|
||||
aboutButton = createButton("about.png", "About", _ -> about());
|
||||
|
||||
ToggleGroup viewModeGroup = new ToggleGroup();
|
||||
filesViewButton = createToggleButton("image-file-view.png", "Files", viewModeGroup, _ -> selectFilesContent());
|
||||
@@ -154,7 +161,7 @@ public class FileStoreWindow {
|
||||
HBox viewModeBox = new HBox(filesViewButton, diskUsageViewButton, informationViewButton);
|
||||
|
||||
ToolBar toolBar = new ToolBar(
|
||||
openFileButton, createFileButton, saveFileButton, saveFileAsButton, settingsButton,
|
||||
openFileButton, createFileButton, saveFileButton, saveFileAsButton, settingsButton, aboutButton,
|
||||
new Separator(Orientation.VERTICAL),
|
||||
viewModeBox,
|
||||
new Separator(Orientation.VERTICAL)
|
||||
@@ -162,7 +169,7 @@ public class FileStoreWindow {
|
||||
|
||||
saveFileButton.disableProperty().bind(changeCount.isEqualTo(0).or(canSave.not()));
|
||||
|
||||
ImageView logo = new ImageView(imageUrl("AppleCommanderLogo.png"));
|
||||
ImageView logo = new ImageView(imageUrl("AppleCommanderLogoLarge.png"));
|
||||
Label label = new Label("No disk image open. Use open to browse for a disk image.");
|
||||
label.setTextFill(Color.BLACK);
|
||||
Rectangle border = new Rectangle();
|
||||
@@ -372,6 +379,40 @@ public class FileStoreWindow {
|
||||
dialog.showAndWait(primaryStage);
|
||||
}
|
||||
|
||||
public void about() {
|
||||
Dialog<ButtonBar.ButtonData> dialog = new Dialog<>();
|
||||
dialog.setTitle("About AppleCommanderFX");
|
||||
|
||||
URL imageURL = getClass().getResource("/images/AppleCommanderLogoSmall.png");
|
||||
Objects.requireNonNull(imageURL);
|
||||
ImageView imageView = new ImageView(imageURL.toExternalForm());
|
||||
VBox imagePane = new VBox(imageView);
|
||||
imagePane.setPadding(new Insets(0, 0, 10, 0));
|
||||
imagePane.setStyle("-fx-background-color: white;");
|
||||
imagePane.setAlignment(Pos.CENTER);
|
||||
|
||||
dialog.getDialogPane().setHeader(imagePane);
|
||||
dialog.getDialogPane().setContent(FXControls.vertical()
|
||||
.alignment(Pos.CENTER)
|
||||
.spacing(5)
|
||||
.largeBold("AppleCommanderFX")
|
||||
.label("Version %s", AppleCommander.VERSION)
|
||||
.node(FXControls.horizontal()
|
||||
.alignment(Pos.CENTER)
|
||||
.spacing(5)
|
||||
.label("Visit:")
|
||||
.link("website", "https://applecommander.github.io/")
|
||||
.link("github", "https://github.com/AppleCommander/AppleCommander")
|
||||
.get())
|
||||
.table(2,
|
||||
"AppleSingle:", AppleSingle.VERSION,
|
||||
"ShrinkIt:", NuFileArchive.VERSION,
|
||||
"BASIC Tools:", BasTools.VERSION)
|
||||
.get());
|
||||
dialog.getDialogPane().getButtonTypes().addAll(ButtonType.OK);
|
||||
dialog.showAndWait();
|
||||
}
|
||||
|
||||
private void switchDisk() {
|
||||
if (fileStoreSelection.getSelectedIndex()+1 < fileStoreSelection.getItemCount()) {
|
||||
fileStoreSelection.selectNext();
|
||||
|
||||
@@ -47,21 +47,21 @@ public class SettingsDialog {
|
||||
public SettingsDialog() {
|
||||
Tab themeTab = new Tab("Theme");
|
||||
themeTab.setClosable(false);
|
||||
themeTab.setContent(FXControls.builder()
|
||||
themeTab.setContent(FXControls.vertical()
|
||||
.label("Please choose a theme:")
|
||||
.radioButton(ThemeSelection.values(), ThemeSelection::getDescription, themeSelection)
|
||||
.get());
|
||||
|
||||
Tab exportTab = new Tab("Export");
|
||||
exportTab.setClosable(false);
|
||||
exportTab.setContent(FXControls.builder()
|
||||
exportTab.setContent(FXControls.vertical()
|
||||
.label("Please select the export type:")
|
||||
.radioButton(ExportOption.values(), ExportOption::getDescription, exportOption)
|
||||
.get());
|
||||
|
||||
Tab importTab = new Tab("Import");
|
||||
importTab.setClosable(false);
|
||||
importTab.setContent(FXControls.builder()
|
||||
importTab.setContent(FXControls.vertical()
|
||||
.checkBox("Do you want to decode AppleSingle files on import?", importDecodeAppleSingle)
|
||||
.checkBox("Do you want to automatically tokenize .bas files as Applesoft?", importTokenizeApplesoft)
|
||||
.get());
|
||||
|
||||
+3
-3
@@ -69,15 +69,15 @@ public class CreateFileStoreWizard extends WizardDialog<CreateFileStoreWizard.Wi
|
||||
@Override
|
||||
public Map<WizardPage, Node> createWizardPages() {
|
||||
return Map.of(
|
||||
WizardPage.FILESTORE, FXControls.builder()
|
||||
WizardPage.FILESTORE, FXControls.vertical()
|
||||
.label("Choose an image type to create:")
|
||||
.radioButton(FileStoreSelection.values(), FileStoreSelection::getText, fileStoreSelectionProperty)
|
||||
.get(),
|
||||
WizardPage.SIZE, FXControls.builder()
|
||||
WizardPage.SIZE, FXControls.vertical()
|
||||
.label("Choose an image size to create:")
|
||||
.radioButton(ImageSizeSelection.values(), ImageSizeSelection::getText, imageSizeSelectionProperty)
|
||||
.get(),
|
||||
WizardPage.SECTOR, FXControls.builder()
|
||||
WizardPage.SECTOR, FXControls.vertical()
|
||||
.label("Choose a sector ordering for this image:")
|
||||
.radioButton(SectorOrderSelection.values(), SectorOrderSelection::getText, sectorOrderSelectionProperty)
|
||||
.get(),
|
||||
|
||||
File renamed without changes.
Binary file not shown.
|
After Width: | Height: | Size: 46 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 822 B |
Reference in new issue
Block a user