File browser performance improvements

This commit is contained in:
crschnick 2023-04-19 05:40:35 +00:00
parent 3029bd54f6
commit d464118d83
5 changed files with 51 additions and 7 deletions

View file

@ -3,11 +3,13 @@ package io.xpipe.app.browser;
import atlantafx.base.controls.RingProgressIndicator;
import atlantafx.base.controls.Spacer;
import atlantafx.base.theme.Styles;
import io.xpipe.app.browser.icon.FileIconManager;
import io.xpipe.app.fxcomps.SimpleComp;
import io.xpipe.app.fxcomps.impl.PrettyImageComp;
import io.xpipe.app.fxcomps.util.PlatformThread;
import io.xpipe.app.storage.DataStorage;
import io.xpipe.app.util.BusyProperty;
import io.xpipe.app.util.ThreadHelper;
import io.xpipe.core.store.FileSystem;
import javafx.beans.binding.Bindings;
import javafx.beans.property.SimpleBooleanProperty;
@ -37,6 +39,10 @@ public class FileBrowserComp extends SimpleComp {
@Override
protected Region createSimple() {
ThreadHelper.runAsync( () -> {
FileIconManager.loadIfNecessary();
});
var bookmarksList = new BookmarkList(model).createRegion();
VBox.setVgrow(bookmarksList, Priority.ALWAYS);
var localDownloadStage = new LocalFileTransferComp(model.getLocalTransfersStage()).hide(Bindings.createBooleanBinding(() -> {

View file

@ -250,7 +250,12 @@ final class FileListComp extends AnchorPane {
var currentDirectory = fileList.getFileSystemModel().getCurrentDirectory();
if (!Objects.equals(lastDir.get(), currentDirectory)) {
table.scrollTo(0);
TableViewSkin<?> skin = (TableViewSkin<?>) table.getSkin();
VirtualFlow<?> flow = (VirtualFlow<?>) skin.getChildren().get(1);
ScrollBar vbar = (ScrollBar) flow.getChildrenUnmodifiable().get(2);
if (vbar.getValue() != 0.0) {
table.scrollTo(0);
}
}
lastDir.setValue(currentDirectory);
});
@ -310,7 +315,9 @@ final class FileListComp extends AnchorPane {
text.setValue(fullPath);
if (empty || getTableRow() == null || getTableRow().getItem() == null) {
img.set(null);
// Don't set image as that would trigger image comp update
// and cells are emptied on each change, leading to unnecessary changes
// img.set(null);
setGraphic(null);
} else {
var isDirectory = getTableRow().getItem().isDirectory();

View file

@ -2,23 +2,24 @@ package io.xpipe.app.browser.icon;
import io.xpipe.app.core.AppImages;
import io.xpipe.app.core.AppResources;
import io.xpipe.app.fxcomps.impl.SvgCache;
import io.xpipe.core.store.FileSystem;
import javafx.scene.image.Image;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.*;
public class FileIconManager {
private static final List<FileIconFactory> factories = new ArrayList<>();
private static final List<FolderIconFactory> folderFactories = new ArrayList<>();
private static SvgCache svgCache;
private static boolean loaded;
static {
private static void loadDefinitions() {
AppResources.with(AppResources.XPIPE_MODULE, "browser_icons/file_list.txt", path -> {
try (var reader =
new BufferedReader(new InputStreamReader(Files.newInputStream(path), StandardCharsets.UTF_8))) {
@ -87,8 +88,27 @@ public class FileIconManager {
});
}
private static void loadIfNecessary() {
private static void createCache() {
svgCache = new SvgCache() {
private final Map<String, Integer> hits = new HashMap<>();
private final Map<String, Image> images = new HashMap<>();
@Override
public Optional<Image> getCached(String image) {
var hitCount = hits.computeIfAbsent(image, s -> 1);
if (hitCount > 5) {
//images.computeIfAbsent(image, s -> AppImages.image())
}
return Optional.empty();
}
};
}
public static synchronized void loadIfNecessary() {
if (!loaded) {
loadDefinitions();
AppImages.loadDirectory(AppResources.XPIPE_MODULE, "browser_icons");
loaded = true;
}

View file

@ -0,0 +1,10 @@
package io.xpipe.app.fxcomps.impl;
import javafx.scene.image.Image;
import java.util.Optional;
public interface SvgCache {
Optional<Image> getCached(String image);
}

View file

@ -96,6 +96,7 @@ public class SvgComp {
var wv = new WebView();
wv.setPageFill(Color.TRANSPARENT);
wv.setDisable(true);
wv.getEngine().setJavaScriptEnabled(false);
wv.getEngine().loadContent(getHtml(svgContent.getValue()));
svgContent.addListener((c, o, n) -> {