mirror of
https://github.com/xpipe-io/xpipe.git
synced 2026-05-19 05:45:58 -04:00
Fixes
This commit is contained in:
@@ -14,7 +14,7 @@ XPipe fully integrates with your tools such as your favourite text/code editors,
|
||||
|
||||
It currently supports:
|
||||
- [SSH](https://www.ssh.com/academy/ssh/protocol) connections, config files, and tunnels
|
||||
- [Docker](https://www.docker.com/), [Podman](https://podman.io/), LXD](https://linuxcontainers.org/lxd/introduction/), and [incus](https://linuxcontainers.org/incus/) container instances located on any host
|
||||
- [Docker](https://www.docker.com/), [Podman](https://podman.io/), [LXD](https://linuxcontainers.org/lxd/introduction/), and [incus](https://linuxcontainers.org/incus/) container instances located on any host
|
||||
- [Proxmox PVE](https://www.proxmox.com/en/proxmox-virtual-environment/overview) virtual machines and containers
|
||||
- [Hyper-V](https://learn.microsoft.com/en-us/virtualization/hyper-v-on-windows/about/), [KVM/QEMU](https://linux-kvm.org/page/Main_Page), [VMware Player/Workstation/Fusion](https://www.vmware.com/products/desktop-hypervisor/workstation-and-fusion) virtual machines
|
||||
- [Kubernetes](https://kubernetes.io/) clusters, pods, and containers
|
||||
|
||||
@@ -134,6 +134,7 @@ public class BaseMode extends OperationMode {
|
||||
PlatformInit.init(true);
|
||||
AppImages.init();
|
||||
imagesLoaded.countDown();
|
||||
storageLoaded.await();
|
||||
SystemIconManager.init();
|
||||
},
|
||||
() -> {
|
||||
|
||||
@@ -4,6 +4,7 @@ import io.xpipe.app.core.AppProperties;
|
||||
import io.xpipe.app.issue.ErrorEvent;
|
||||
import io.xpipe.app.prefs.AppPrefs;
|
||||
import io.xpipe.app.resources.AppImages;
|
||||
import io.xpipe.app.storage.DataStorage;
|
||||
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
@@ -16,6 +17,19 @@ public class SystemIconManager {
|
||||
private static final Map<SystemIconSource, SystemIconSourceData> LOADED = new HashMap<>();
|
||||
private static final Set<SystemIcon> ICONS = new HashSet<>();
|
||||
|
||||
public static List<SystemIconSource> getEffectiveSources() {
|
||||
var prefs = AppPrefs.get().getIconSources().getValue();
|
||||
var all = new ArrayList<SystemIconSource>();
|
||||
all.add(SystemIconSource.Directory.builder().path(DataStorage.get().getIconsDir()).id("custom").build());
|
||||
all.add(SystemIconSource.GitRepository.builder().remote("https://github.com/selfhst/icons").id("selfhst").build());
|
||||
for (var pref : prefs) {
|
||||
if (!all.contains(pref)) {
|
||||
all.add(pref);
|
||||
}
|
||||
}
|
||||
return all;
|
||||
}
|
||||
|
||||
public static Map<SystemIconSource, SystemIconSourceData> getSources() {
|
||||
return LOADED;
|
||||
}
|
||||
@@ -38,7 +52,7 @@ public class SystemIconManager {
|
||||
Files.createDirectories(DIRECTORY);
|
||||
|
||||
LOADED.clear();
|
||||
for (var source : AppPrefs.get().getIconSources().getValue()) {
|
||||
for (var source : getEffectiveSources()) {
|
||||
LOADED.put(source,SystemIconSourceData.of(source));
|
||||
}
|
||||
|
||||
@@ -54,7 +68,7 @@ public class SystemIconManager {
|
||||
public static void reloadImages() {
|
||||
AppImages.remove(s -> s.startsWith("icons/"));
|
||||
try {
|
||||
for (var source : AppPrefs.get().getIconSources().getValue()) {
|
||||
for (var source : getEffectiveSources()) {
|
||||
AppImages.loadRasterImages(SystemIconCache.getDirectory(source), "icons/" + source.getId());
|
||||
}
|
||||
} catch (Exception e) {
|
||||
@@ -64,7 +78,7 @@ public class SystemIconManager {
|
||||
|
||||
public static synchronized void reload() throws Exception {
|
||||
Files.createDirectories(DIRECTORY);
|
||||
for (var source : AppPrefs.get().getIconSources().getValue()) {
|
||||
for (var source : getEffectiveSources()) {
|
||||
source.refresh();
|
||||
}
|
||||
reloadSources();
|
||||
|
||||
@@ -7,6 +7,7 @@ import io.xpipe.app.ext.ProcessControlProvider;
|
||||
import io.xpipe.app.util.DesktopHelper;
|
||||
import io.xpipe.app.util.Hyperlinks;
|
||||
import io.xpipe.core.process.CommandBuilder;
|
||||
import io.xpipe.core.store.FileNames;
|
||||
import lombok.Builder;
|
||||
import lombok.Value;
|
||||
import lombok.extern.jackson.Jacksonized;
|
||||
@@ -32,7 +33,9 @@ public interface SystemIconSource {
|
||||
String id;
|
||||
|
||||
@Override
|
||||
public void refresh() throws Exception {}
|
||||
public void refresh() throws Exception {
|
||||
Files.createDirectories(path);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Path getPath() {
|
||||
@@ -44,6 +47,11 @@ public interface SystemIconSource {
|
||||
return "mdi2f-folder";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDisplayName() {
|
||||
return path.getFileName().toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return path.toString();
|
||||
@@ -51,6 +59,7 @@ public interface SystemIconSource {
|
||||
|
||||
@Override
|
||||
public void open() throws Exception {
|
||||
Files.createDirectories(path);
|
||||
DesktopHelper.browsePathLocal(path);
|
||||
}
|
||||
}
|
||||
@@ -86,6 +95,11 @@ public interface SystemIconSource {
|
||||
return "mdi2g-git";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDisplayName() {
|
||||
return FileNames.getFileName(remote);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getDescription() {
|
||||
return "Git repository " + remote;
|
||||
@@ -105,6 +119,8 @@ public interface SystemIconSource {
|
||||
|
||||
String getIcon();
|
||||
|
||||
String getDisplayName();
|
||||
|
||||
String getDescription();
|
||||
|
||||
void open() throws Exception;
|
||||
|
||||
@@ -80,8 +80,7 @@ public class AppPrefs {
|
||||
final BooleanProperty clearTerminalOnInit =
|
||||
mapLocal(new SimpleBooleanProperty(true), "clearTerminalOnInit", Boolean.class, false);
|
||||
final Property<List<SystemIconSource>> iconSources = map(Mapping.builder()
|
||||
.property(new SimpleObjectProperty<>(new ArrayList<>(List.of(
|
||||
SystemIconSource.GitRepository.builder().remote("https://github.com/selfhst/icons").id("selfhst").build()))))
|
||||
.property(new SimpleObjectProperty<>(new ArrayList<>()))
|
||||
.key("iconSources")
|
||||
.valueType(TypeFactory.defaultInstance().constructType(new TypeReference<List<SystemIconSource>>() {}))
|
||||
.build());
|
||||
|
||||
@@ -24,6 +24,7 @@ import javafx.scene.control.TextField;
|
||||
import org.kordamp.ikonli.javafx.FontIcon;
|
||||
|
||||
import java.nio.file.Path;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
@@ -49,9 +50,9 @@ public class IconsCategory extends AppPrefsCategory {
|
||||
private Comp<?> createOverview() {
|
||||
var sources = FXCollections.<SystemIconSource>observableArrayList();
|
||||
AppPrefs.get().getIconSources().subscribe((newValue) -> {
|
||||
sources.setAll(newValue);
|
||||
sources.setAll(SystemIconManager.getEffectiveSources());
|
||||
});
|
||||
var box = new ListBoxViewComp<>(sources, sources, s -> createSourceEntry(s), true);
|
||||
var box = new ListBoxViewComp<>(sources, sources, s -> createSourceEntry(s, sources), true);
|
||||
|
||||
var busy = new SimpleBooleanProperty(false);
|
||||
var refreshButton = new TileButtonComp("refreshSources", "refreshSourcesDescription", "mdi2r-refresh", e -> {
|
||||
@@ -81,7 +82,12 @@ public class IconsCategory extends AppPrefsCategory {
|
||||
}
|
||||
|
||||
var source = SystemIconSource.GitRepository.builder().remote(remote.get()).id(UUID.randomUUID().toString()).build();
|
||||
sources.add(source);
|
||||
if (!sources.contains(source)) {
|
||||
sources.add(source);
|
||||
var nl = new ArrayList<>(AppPrefs.get().getIconSources().getValue());
|
||||
nl.add(source);
|
||||
AppPrefs.get().iconSources.setValue(nl);
|
||||
}
|
||||
});
|
||||
modal.show();
|
||||
e.consume();
|
||||
@@ -99,7 +105,12 @@ public class IconsCategory extends AppPrefsCategory {
|
||||
}
|
||||
|
||||
var source = SystemIconSource.Directory.builder().path(Path.of(dir.get())).id(UUID.randomUUID().toString()).build();
|
||||
sources.add(source);
|
||||
if (!sources.contains(source)) {
|
||||
sources.add(source);
|
||||
var nl = new ArrayList<>(AppPrefs.get().getIconSources().getValue());
|
||||
nl.add(source);
|
||||
AppPrefs.get().iconSources.setValue(nl);
|
||||
}
|
||||
});
|
||||
modal.show();
|
||||
e.consume();
|
||||
@@ -111,17 +122,25 @@ public class IconsCategory extends AppPrefsCategory {
|
||||
return vbox;
|
||||
}
|
||||
|
||||
private Comp<?> createSourceEntry(SystemIconSource source) {
|
||||
private Comp<?> createSourceEntry(SystemIconSource source, List<SystemIconSource> sources) {
|
||||
var delete = new IconButtonComp(new LabelGraphic.IconGraphic("mdal-delete_outline"), () -> {
|
||||
if (!AppDialog.confirm("iconSourceDeletion")) {
|
||||
return;
|
||||
}
|
||||
|
||||
var nl = new ArrayList<>(AppPrefs.get().getIconSources().getValue());
|
||||
nl.remove(source);
|
||||
AppPrefs.get().iconSources.setValue(nl);
|
||||
sources.remove(source);
|
||||
});
|
||||
var buttons = new HorizontalComp(List.of(delete));
|
||||
buttons.spacing(5);
|
||||
if (!AppPrefs.get().getIconSources().getValue().contains(source)) {
|
||||
buttons.disable(new SimpleBooleanProperty(true));
|
||||
}
|
||||
|
||||
var tile = new TileButtonComp(
|
||||
new SimpleStringProperty(source.getId()),
|
||||
new SimpleStringProperty(AppPrefs.get().getIconSources().getValue().contains(source) ? source.getDisplayName() : source.getId()),
|
||||
new SimpleStringProperty(source.getDescription()),
|
||||
new SimpleObjectProperty<>(source.getIcon()),
|
||||
actionEvent -> {
|
||||
|
||||
@@ -252,6 +252,10 @@ public abstract class DataStorage {
|
||||
return dir.resolve("data");
|
||||
}
|
||||
|
||||
public Path getIconsDir() {
|
||||
return dir.resolve("icons");
|
||||
}
|
||||
|
||||
protected Path getCategoriesDir() {
|
||||
return dir.resolve("categories");
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user