Various UI fixes

This commit is contained in:
crschnick
2026-09-15 18:02:19 +00:00
parent d95818f8ca
commit 2a16911dac
12 changed files with 77 additions and 41 deletions
+1 -1
View File
@@ -77,7 +77,7 @@ dependencies {
api "org.slf4j:slf4j-jdk-platform-logging:2.0.18"
api 'io.xpipe:modulefs:0.1.9'
api 'net.synedra:validatorfx:0.4.2'
api 'io.xpipe:atlantafx-base:2.1.1'
api 'io.xpipe:atlantafx-base:2.1.2'
api ("io.xpipe:atlantafx-themes:1.9.1") {
exclude group: "io.github.mkpaz", module: "atlantafx-base"
}
@@ -1,5 +1,6 @@
package io.xpipe.app.comp;
import javafx.beans.value.ObservableDoubleValue;
import javafx.geometry.Orientation;
import javafx.scene.control.Separator;
import javafx.scene.layout.Region;
@@ -26,6 +27,10 @@ public abstract class RegionBuilder<T extends Region> extends BaseRegionBuilder<
return of(() -> new Spacer(size));
}
public static RegionBuilder<Spacer> hspacer(ObservableDoubleValue size) {
return of(() -> new Spacer(size, Orientation.HORIZONTAL));
}
public static RegionBuilder<Spacer> vspacer() {
return of(() -> new Spacer(Orientation.VERTICAL));
}
@@ -47,4 +47,6 @@ public abstract class AuthModuleProvider {
public abstract void setWindowsCredential(
String target, int type, int persist, String userName, SecretValue password);
public abstract void deleteWindowsCredential(String target, int type);
}
@@ -76,6 +76,9 @@ public class CloneHubLeafProvider implements HubLeafProvider<DataStore> {
entry.setPinToTop(ref.get().isPinToTop());
entry.setOrderIndex(DataStorage.get().getNextOrderIndex());
entry.setNotes(ref.get().getNotes());
for (String tag : ref.get().getTags()) {
entry.addTag(tag);
}
var instant = ref.get().getLastAccess().plus(Duration.ofSeconds(1));
entry.setLastModified(instant);
@@ -90,7 +90,7 @@ public class StoreCategoryChoiceComp extends SimpleRegionBuilder {
setGraphic(PrettyImageHelper.ofFixedSizeSquare(w.getIconFile().getValue(), 16)
.build());
setText(w.getShownName().getValue());
setPadding(new Insets(6, 6, 6, 8 + (indent ? w.getDepth() * 8 : 0)));
setPadding(new Insets(6, 6, 6, 8 + (indent ? w.getDepth().getValue() * 8 : 0)));
} else {
setGraphic(null);
setText("None");
@@ -158,8 +158,11 @@ public class StoreCategoryComp extends SimpleRegionBuilder {
var showStatus = hover.or(new SimpleBooleanProperty(DataStorage.get().syncEnabled()))
.or(showing)
.or(focus);
var indentSpacer = RegionBuilder.hspacer(Bindings.createDoubleBinding(() -> {
return category.getDepth().getValue() * 8.0;
}, category.getDepth()));
var h = new HorizontalComp(List.of(
RegionBuilder.hspacer((category.getDepth() * 8)),
indentSpacer,
expandButton,
RegionBuilder.hspacer(3),
iconButton,
@@ -454,20 +457,27 @@ public class StoreCategoryComp extends SimpleRegionBuilder {
if (AppPrefs.get().enableHttpApi().get()) {
var copyId = new MenuItem(AppI18n.get("copyId"), new FontIcon("mdi2c-content-copy"));
copyId.setOnAction(event ->
ClipboardHelper.copyText(category.getCategory().getUuid().toString()));
{
ClipboardHelper.copyText(category.getCategory().getUuid().toString());
event.consume();
});
contextMenu.getItems().add(copyId);
}
if (AppPrefs.get().developerMode().getValue()) {
var browse = new MenuItem(AppI18n.get("browseInternalStorage"), new FontIcon("mdi2f-folder-open-outline"));
browse.setOnAction(
event -> DesktopHelper.browseFile(category.getCategory().getDirectory()));
event -> {
DesktopHelper.browseFile(category.getCategory().getDirectory());
event.consume();
});
contextMenu.getItems().add(browse);
}
var newCategory = new MenuItem(AppI18n.get("createNewCategory"), new FontIcon("mdi2p-plus-thick"));
newCategory.setOnAction(event -> {
StoreViewState.get().createNewCategory(category);
event.consume();
});
newCategory.setDisable(!DataStorage.get().canCreateStoreCategoryWithin(category.getCategory()));
contextMenu.getItems().add(newCategory);
@@ -477,10 +487,16 @@ public class StoreCategoryComp extends SimpleRegionBuilder {
var configure = new MenuItem(AppI18n.get("configure"), new FontIcon("mdi2w-wrench-outline"));
configure.setOnAction(event -> {
StoreCategoryConfigComp.show(category);
event.consume();
});
contextMenu.getItems().add(configure);
var rename = new MenuItem(AppI18n.get("rename"), new FontIcon("mdal-edit"));
rename.setAccelerator(switch (OsType.ofLocal()) {
case OsType.Linux ignored -> new KeyCodeCombination(KeyCode.F2);
case OsType.MacOs ignored -> new KeyCodeCombination(KeyCode.ENTER);
case OsType.Windows ignored -> new KeyCodeCombination(KeyCode.F2);
});
rename.setOnAction(event -> {
category.getRenameTrigger().fire(null);
event.consume();
@@ -511,8 +527,10 @@ public class StoreCategoryComp extends SimpleRegionBuilder {
contextMenu.getItems().add(new SeparatorMenuItem());
var del = new MenuItem(AppI18n.get("remove"), new FontIcon("mdal-delete_outline"));
del.setAccelerator(new KeyCodeCombination(KeyCode.DELETE));
del.setOnAction(event -> {
category.delete();
event.consume();
});
del.setDisable(!DataStorage.get().canDeleteStoreCategory(category.getCategory()));
contextMenu.getItems().add(del);
@@ -32,11 +32,11 @@ import java.util.Optional;
public class StoreCategoryWrapper {
private final DataStoreCategory root;
private final int depth;
private final Property<String> name;
private final IntegerProperty depth = new SimpleIntegerProperty();
private final Property<String> name = new SimpleObjectProperty<>();
private final DataStoreCategory category;
private final Property<Instant> lastAccess;
private final BooleanProperty sync;
private final Property<Instant> lastAccess = new SimpleObjectProperty<>();
private final BooleanProperty sync = new SimpleBooleanProperty();
private final DerivedObservableList<StoreCategoryWrapper> children;
private final DerivedObservableList<StoreCategoryWrapper> shownChildren;
private final DerivedObservableList<StoreEntryWrapper> directContainedEntries;
@@ -50,29 +50,11 @@ public class StoreCategoryWrapper {
private StoreCategoryWrapper cachedParent;
public StoreCategoryWrapper(DataStoreCategory category) {
var d = 0;
DataStoreCategory last = category;
DataStoreCategory p = category;
while ((p = DataStorage.get()
.getStoreCategoryIfPresent(p.getParentCategory())
.orElse(null))
!= null) {
d++;
last = p;
}
depth = d;
this.root = last;
this.root = DataStorage.get().getRootCategory(category);
this.category = category;
this.name = new SimpleStringProperty(category.getName());
this.lastAccess = new SimpleObjectProperty<>(category.getLastAccess());
this.sync = new SimpleBooleanProperty(Boolean.TRUE.equals(
DataStorage.get().getEffectiveCategoryConfig(category).getSync()));
this.children = DerivedObservableList.arrayList(true);
this.shownChildren = DerivedObservableList.arrayList(true);
this.directContainedEntries = DerivedObservableList.arrayList(true);
this.color.setValue(
DataStorage.get().getEffectiveCategoryConfig(category).getColor());
setupListeners();
}
@@ -192,6 +174,18 @@ public class StoreCategoryWrapper {
name.setValue(catName);
}
var d = 0;
DataStoreCategory last = category;
DataStoreCategory p = category;
while ((p = DataStorage.get()
.getStoreCategoryIfPresent(p.getParentCategory())
.orElse(null))
!= null) {
d++;
last = p;
}
depth.setValue(d);
orderIndex.set(category.getOrderIndex());
lastAccess.setValue(category.getLastAccess().minus(Duration.ofMillis(500)));
sync.setValue(Boolean.TRUE.equals(
@@ -464,8 +464,14 @@ public abstract class StoreEntryComp extends SimpleRegionBuilder {
if (cat == StoreActionCategory.CONFIGURATION
&& getWrapper().getEntry().getValidity() != DataStoreEntry.Validity.LOAD_FAILED) {
var rename = new MenuItem(AppI18n.get("rename"), new FontIcon("mdal-edit"));
rename.setAccelerator(switch (OsType.ofLocal()) {
case OsType.Linux ignored -> new KeyCodeCombination(KeyCode.F2);
case OsType.MacOs ignored -> new KeyCodeCombination(KeyCode.ENTER);
case OsType.Windows ignored -> new KeyCodeCombination(KeyCode.F2);
});
rename.setOnAction(event -> {
name.requestFocus();
event.consume();
});
items.add(items.size(), rename);
@@ -613,7 +619,11 @@ public abstract class StoreEntryComp extends SimpleRegionBuilder {
return !getWrapper().getDeletable().get();
},
getWrapper().getDeletable()));
del.setOnAction(event -> getWrapper().delete());
del.setOnAction(event -> {
getWrapper().delete();
event.consume();
});
del.setAccelerator(new KeyCodeCombination(KeyCode.DELETE));
contextMenu.getItems().add(del);
}
@@ -37,7 +37,7 @@ public class StoreEntryBatchSelectComp extends SimpleRegionBuilder {
return;
}
StoreViewState.get().unselectBatchMode(section);
StoreViewState.get().unselectBatchMode(section, false);
}
});
});
@@ -59,8 +59,14 @@ public class StoreEntryBatchSelectComp extends SimpleRegionBuilder {
}
BooleanScope.executeExclusive(selfUpdate, () -> {
if (cb.isSelected()) {
StoreViewState.get().selectBatchMode(section);
while (c.next()) {
if (c.wasRemoved()) {
for (StoreSection r : c.getRemoved()) {
Platform.runLater(() -> {
StoreViewState.get().unselectBatchMode(r, true);
});
}
}
}
});
});
@@ -75,7 +81,7 @@ public class StoreEntryBatchSelectComp extends SimpleRegionBuilder {
if (cb.isSelected()) {
StoreViewState.get().selectBatchMode(section);
} else {
StoreViewState.get().unselectBatchMode(section);
StoreViewState.get().unselectBatchMode(section, false);
}
}
@@ -284,7 +284,7 @@ public class StoreViewState {
}
}
public void unselectBatchMode(StoreSection section) {
public void unselectBatchMode(StoreSection section, boolean recursive) {
var wrapper = section.getWrapper();
if (wrapper != null && wrapper.getEntry().getValidity() == DataStoreEntry.Validity.LOAD_FAILED) {
return;
@@ -292,8 +292,8 @@ public class StoreViewState {
if (wrapper != null) {
batchModeSelection.getList().remove(wrapper);
}
if (wrapper == null || wrapper.getEntry().getProvider().getUsageCategory() == DataStoreUsageCategory.GROUP) {
section.getShownChildren().getList().forEach(c -> unselectBatchMode(c));
if (wrapper == null || wrapper.getEntry().getProvider().getUsageCategory() == DataStoreUsageCategory.GROUP || recursive) {
section.getAllChildren().getList().forEach(c -> unselectBatchMode(c, recursive));
}
}
@@ -717,7 +717,7 @@ public class StoreViewState {
return 1;
}
if (o1.getDepth() > o2.getDepth()) {
if (o1.getDepth().getValue() > o2.getDepth().getValue()) {
if (p1 == o2) {
return 1;
}
@@ -725,7 +725,7 @@ public class StoreViewState {
return compare(p1, o2);
}
if (o1.getDepth() < o2.getDepth()) {
if (o1.getDepth().getValue() < o2.getDepth().getValue()) {
if (p2 == o1) {
return -1;
}
@@ -689,8 +689,6 @@ public abstract class DataStorage {
}
cat.setParentCategory(newParent.getUuid());
listeners.forEach(storageListener -> storageListener.onCategoryRemove(cat));
listeners.forEach(storageListener -> storageListener.onCategoryAdd(cat));
listeners.forEach(storageListener -> storageListener.onCategoryListUpdate());
listeners.forEach(storageListener -> storageListener.onStoreListUpdate());
saveAsync();
+1 -1
View File
@@ -43,7 +43,7 @@ configurations {
dependencies {
compileOnly "tools.jackson.core:jackson-databind:3.2.0"
compileOnly project(':app')
compileOnly 'io.xpipe:atlantafx-base:2.1.0'
compileOnly 'io.xpipe:atlantafx-base:2.1.2'
compileOnly 'commons-io:commons-io:2.22.0'
compileOnly "org.kordamp.ikonli:ikonli-javafx:12.4.0"