mirror of
https://github.com/cryptomator/cryptomator.git
synced 2026-05-19 03:01:27 +00:00
implemented volume type selection in 'vault options mount'
This commit is contained in:
@@ -1,18 +1,26 @@
|
||||
package org.cryptomator.ui.vaultoptions;
|
||||
|
||||
import com.google.common.base.Strings;
|
||||
import dagger.Lazy;
|
||||
import org.cryptomator.common.ObservableUtil;
|
||||
import org.cryptomator.common.mount.ActualMountService;
|
||||
import org.cryptomator.common.mount.MountModule;
|
||||
import org.cryptomator.common.mount.WindowsDriveLetters;
|
||||
import org.cryptomator.common.settings.Settings;
|
||||
import org.cryptomator.common.settings.VaultSettings;
|
||||
import org.cryptomator.common.vaults.Vault;
|
||||
import org.cryptomator.integrations.mount.MountCapability;
|
||||
import org.cryptomator.integrations.mount.MountService;
|
||||
import org.cryptomator.ui.common.FxController;
|
||||
import org.cryptomator.ui.fxapp.FxApplicationWindows;
|
||||
import org.cryptomator.ui.preferences.SelectedPreferencesTab;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import javafx.application.Application;
|
||||
import javafx.beans.binding.Bindings;
|
||||
import javafx.beans.binding.BooleanExpression;
|
||||
import javafx.beans.value.ObservableValue;
|
||||
import javafx.fxml.FXML;
|
||||
import javafx.scene.control.Button;
|
||||
import javafx.scene.control.CheckBox;
|
||||
import javafx.scene.control.ChoiceBox;
|
||||
import javafx.scene.control.RadioButton;
|
||||
@@ -26,16 +34,25 @@ import java.io.File;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.InvalidPathException;
|
||||
import java.nio.file.Path;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.ResourceBundle;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.atomic.AtomicReference;
|
||||
|
||||
@VaultOptionsScoped
|
||||
public class MountOptionsController implements FxController {
|
||||
|
||||
private static final String DOCS_MOUNTING_URL = "https://docs.cryptomator.org/en/1.7/desktop/volume-type/";
|
||||
private static final int MIN_PORT = 1024;
|
||||
private static final int MAX_PORT = 65535;
|
||||
|
||||
private final Stage window;
|
||||
private final VaultSettings vaultSettings;
|
||||
private final WindowsDriveLetters windowsDriveLetters;
|
||||
private final ResourceBundle resourceBundle;
|
||||
private final Lazy<Application> application;
|
||||
private final Settings settings;
|
||||
|
||||
private final ObservableValue<String> defaultMountFlags;
|
||||
private final ObservableValue<Boolean> mountpointDirSupported;
|
||||
@@ -43,7 +60,10 @@ public class MountOptionsController implements FxController {
|
||||
private final ObservableValue<Boolean> readOnlySupported;
|
||||
private final ObservableValue<Boolean> mountFlagsSupported;
|
||||
private final ObservableValue<String> directoryPath;
|
||||
private final FxApplicationWindows applicationWindows;
|
||||
private final List<MountService> mountProviders;
|
||||
private final ObservableValue<MountService> selectedMountService;
|
||||
private final ObservableValue<Boolean> fuseRestartRequired;
|
||||
private final BooleanExpression loopbackPortSupported;
|
||||
|
||||
|
||||
//-- FXML objects --
|
||||
@@ -56,9 +76,21 @@ public class MountOptionsController implements FxController {
|
||||
public RadioButton mountPointDirBtn;
|
||||
public TextField directoryPathField;
|
||||
public ChoiceBox<Path> driveLetterSelection;
|
||||
public ChoiceBox<MountService> volumeTypeChoiceBox;
|
||||
public TextField loopbackPortField;
|
||||
public Button loopbackPortApplyButton;
|
||||
|
||||
|
||||
@Inject
|
||||
MountOptionsController(@VaultOptionsWindow Stage window, @VaultOptionsWindow Vault vault, ObservableValue<ActualMountService> mountService, WindowsDriveLetters windowsDriveLetters, ResourceBundle resourceBundle, FxApplicationWindows applicationWindows) {
|
||||
MountOptionsController(@VaultOptionsWindow Stage window, //
|
||||
@VaultOptionsWindow Vault vault, //
|
||||
ObservableValue<ActualMountService> mountService, //
|
||||
WindowsDriveLetters windowsDriveLetters, //
|
||||
ResourceBundle resourceBundle, //
|
||||
Lazy<Application> application,
|
||||
Settings settings, //
|
||||
List<MountService> mountProviders, //
|
||||
@Named("FUPFMS") AtomicReference<MountService> firstUsedProblematicFuseMountService) {
|
||||
this.window = window;
|
||||
this.vaultSettings = vault.getVaultSettings();
|
||||
this.windowsDriveLetters = windowsDriveLetters;
|
||||
@@ -75,7 +107,17 @@ public class MountOptionsController implements FxController {
|
||||
this.mountFlagsSupported = mountService.map(as -> as.service().hasCapability(MountCapability.MOUNT_FLAGS));
|
||||
this.readOnlySupported = mountService.map(as -> as.service().hasCapability(MountCapability.READ_ONLY));
|
||||
this.directoryPath = vault.getVaultSettings().mountPoint.map(p -> isDriveLetter(p) ? null : p.toString());
|
||||
this.applicationWindows = applicationWindows;
|
||||
this.application = application;
|
||||
this.settings = settings;
|
||||
this.mountProviders = mountProviders;
|
||||
var fallbackProvider = mountProviders.stream().findFirst().orElse(null);
|
||||
this.selectedMountService = ObservableUtil.mapWithDefault(settings.mountService, serviceName -> mountProviders.stream().filter(s -> s.getClass().getName().equals(serviceName)).findFirst().orElse(fallbackProvider), fallbackProvider);
|
||||
this.fuseRestartRequired = selectedMountService.map(s -> {//
|
||||
return firstUsedProblematicFuseMountService.get() != null //
|
||||
&& MountModule.isProblematicFuseService(s) //
|
||||
&& !firstUsedProblematicFuseMountService.get().equals(s);
|
||||
});
|
||||
this.loopbackPortSupported = BooleanExpression.booleanExpression(selectedMountService.map(s -> s.hasCapability(MountCapability.LOOPBACK_PORT)));
|
||||
}
|
||||
|
||||
@FXML
|
||||
@@ -106,11 +148,21 @@ public class MountOptionsController implements FxController {
|
||||
mountPointToggleGroup.selectToggle(mountPointDirBtn);
|
||||
}
|
||||
mountPointToggleGroup.selectedToggleProperty().addListener(this::selectedToggleChanged);
|
||||
}
|
||||
|
||||
@FXML
|
||||
public void openVolumePreferences() {
|
||||
applicationWindows.showPreferencesWindow(SelectedPreferencesTab.VOLUME);
|
||||
volumeTypeChoiceBox.getItems().add(null);
|
||||
volumeTypeChoiceBox.getItems().addAll(mountProviders);
|
||||
volumeTypeChoiceBox.setConverter(new MountServiceConverter());
|
||||
boolean autoSelected = settings.mountService.get() == null;
|
||||
volumeTypeChoiceBox.getSelectionModel().select(autoSelected ? null : selectedMountService.getValue());
|
||||
volumeTypeChoiceBox.valueProperty().addListener((observableValue, oldProvider, newProvider) -> {
|
||||
var toSet = Optional.ofNullable(newProvider).map(nP -> nP.getClass().getName()).orElse(null);
|
||||
settings.mountService.set(toSet);
|
||||
});
|
||||
|
||||
loopbackPortField.setText(String.valueOf(settings.port.get()));
|
||||
loopbackPortApplyButton.visibleProperty().bind(settings.port.asString().isNotEqualTo(loopbackPortField.textProperty()));
|
||||
loopbackPortApplyButton.disableProperty().bind(Bindings.createBooleanBinding(this::validateLoopbackPort, loopbackPortField.textProperty()).not());
|
||||
|
||||
}
|
||||
|
||||
@FXML
|
||||
@@ -229,6 +281,26 @@ public class MountOptionsController implements FxController {
|
||||
|
||||
}
|
||||
|
||||
public void openDocs() {
|
||||
application.get().getHostServices().showDocument(DOCS_MOUNTING_URL);
|
||||
}
|
||||
|
||||
private boolean validateLoopbackPort() {
|
||||
try {
|
||||
int port = Integer.parseInt(loopbackPortField.getText());
|
||||
return port == 0 // choose port automatically
|
||||
|| port >= MIN_PORT && port <= MAX_PORT; // port within range
|
||||
} catch (NumberFormatException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public void doChangeLoopbackPort() {
|
||||
if (validateLoopbackPort()) {
|
||||
settings.port.set(Integer.parseInt(loopbackPortField.getText()));
|
||||
}
|
||||
}
|
||||
|
||||
//@formatter:off
|
||||
private static class NoDirSelectedException extends Exception {}
|
||||
//@formatter:on
|
||||
@@ -274,4 +346,40 @@ public class MountOptionsController implements FxController {
|
||||
public String getDirectoryPath() {
|
||||
return directoryPath.getValue();
|
||||
}
|
||||
|
||||
public ObservableValue<Boolean> fuseRestartRequiredProperty() {
|
||||
return fuseRestartRequired;
|
||||
}
|
||||
|
||||
public boolean getFuseRestartRequired() {
|
||||
return fuseRestartRequired.getValue();
|
||||
}
|
||||
|
||||
public BooleanExpression loopbackPortSupportedProperty() {
|
||||
return loopbackPortSupported;
|
||||
}
|
||||
|
||||
public boolean isLoopbackPortSupported() {
|
||||
return loopbackPortSupported.get();
|
||||
}
|
||||
|
||||
//Helpers
|
||||
/* Helpers */
|
||||
|
||||
private class MountServiceConverter extends StringConverter<MountService> {
|
||||
|
||||
@Override
|
||||
public String toString(MountService provider) {
|
||||
if (provider == null) {
|
||||
return resourceBundle.getString("preferences.volume.type.automatic");
|
||||
} else {
|
||||
return provider.displayName();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public MountService fromString(String string) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user