播放过渡动画时缓存节点至位图 (#4815)

This commit is contained in:
Glavo
2025-11-18 16:35:02 +08:00
committed by GitHub
parent 5c726913e4
commit da5bbd2b22
5 changed files with 32 additions and 4 deletions

View File

@@ -20,6 +20,7 @@ package org.jackhuang.hmcl.ui.animation;
import javafx.animation.Animation;
import javafx.animation.Interpolator;
import javafx.application.Platform;
import javafx.scene.CacheHint;
import javafx.scene.Node;
import javafx.scene.layout.Pane;
import javafx.scene.layout.StackPane;
@@ -74,6 +75,15 @@ public class TransitionPane extends StackPane {
setMouseTransparent(true);
transition.init(this, previousNode, newView);
CacheHint cacheHint = newView instanceof Cacheable cacheable
? cacheable.getCacheHint(transition)
: null;
if (cacheHint != null) {
newView.setCache(true);
newView.setCacheHint(cacheHint);
}
// runLater or "init" will not work
Platform.runLater(() -> {
Animation newAnimation = transition.animate(
@@ -84,6 +94,10 @@ public class TransitionPane extends StackPane {
newAnimation.setOnFinished(e -> {
setMouseTransparent(false);
getChildren().remove(previousNode);
if (cacheHint != null) {
newView.setCache(false);
}
});
FXUtils.playAnimation(this, "transition_pane", newAnimation);
});
@@ -103,4 +117,14 @@ public class TransitionPane extends StackPane {
return null;
}
}
/// Marks a node as cacheable as a bitmap during animation.
public interface Cacheable {
/// @return the [cache hint][CacheHint] to use when caching this node during the given animation,
/// or `null` to not cache it.
default @Nullable CacheHint getCacheHint(AnimationProducer animationProducer) {
// https://github.com/HMCL-dev/HMCL/issues/4789
return animationProducer == ContainerAnimations.SLIDE_UP_FADE_IN ? CacheHint.SPEED : null;
}
}
}

View File

@@ -29,6 +29,7 @@ import org.jackhuang.hmcl.task.Task;
import org.jackhuang.hmcl.task.TaskExecutor;
import org.jackhuang.hmcl.task.TaskListener;
import org.jackhuang.hmcl.ui.*;
import org.jackhuang.hmcl.ui.animation.TransitionPane;
import org.jackhuang.hmcl.ui.download.UpdateInstallerWizardProvider;
import org.jackhuang.hmcl.util.TaskCancellationAction;
import org.jackhuang.hmcl.util.io.FileUtils;
@@ -42,7 +43,7 @@ import java.util.concurrent.CompletableFuture;
import static org.jackhuang.hmcl.ui.FXUtils.runInFX;
import static org.jackhuang.hmcl.util.i18n.I18n.i18n;
public class InstallerListPage extends ListPageBase<InstallerItem> implements VersionPage.VersionLoadable {
public class InstallerListPage extends ListPageBase<InstallerItem> implements VersionPage.VersionLoadable, TransitionPane.Cacheable {
private Profile profile;
private String versionId;
private Version version;

View File

@@ -34,6 +34,7 @@ import org.jackhuang.hmcl.task.Task;
import org.jackhuang.hmcl.ui.Controllers;
import org.jackhuang.hmcl.ui.FXUtils;
import org.jackhuang.hmcl.ui.ListPageBase;
import org.jackhuang.hmcl.ui.animation.TransitionPane;
import org.jackhuang.hmcl.ui.construct.MessageDialogPane;
import org.jackhuang.hmcl.ui.construct.PageAware;
import org.jackhuang.hmcl.util.TaskCancellationAction;
@@ -49,7 +50,7 @@ import java.util.concurrent.locks.ReentrantLock;
import static org.jackhuang.hmcl.util.logging.Logger.LOG;
import static org.jackhuang.hmcl.util.i18n.I18n.i18n;
public final class ModListPage extends ListPageBase<ModListPageSkin.ModInfoObject> implements VersionPage.VersionLoadable, PageAware {
public final class ModListPage extends ListPageBase<ModListPageSkin.ModInfoObject> implements VersionPage.VersionLoadable, PageAware, TransitionPane.Cacheable {
private final BooleanProperty modded = new SimpleBooleanProperty(this, "modded", false);
private final ReentrantLock lock = new ReentrantLock();

View File

@@ -37,6 +37,7 @@ import org.jackhuang.hmcl.setting.Theme;
import org.jackhuang.hmcl.task.Schedulers;
import org.jackhuang.hmcl.task.Task;
import org.jackhuang.hmcl.ui.*;
import org.jackhuang.hmcl.ui.animation.TransitionPane;
import org.jackhuang.hmcl.ui.construct.*;
import org.jackhuang.hmcl.util.Lang;
import org.jackhuang.hmcl.util.StringUtils;
@@ -60,7 +61,7 @@ import static org.jackhuang.hmcl.util.logging.Logger.LOG;
/**
* @author Glavo
*/
public final class SchematicsPage extends ListPageBase<SchematicsPage.Item> implements VersionPage.VersionLoadable {
public final class SchematicsPage extends ListPageBase<SchematicsPage.Item> implements VersionPage.VersionLoadable, TransitionPane.Cacheable {
private static String translateAuthorName(String author) {
if (I18n.isUseChinese() && "hsds".equals(author)) {

View File

@@ -27,6 +27,7 @@ import org.jackhuang.hmcl.setting.Profile;
import org.jackhuang.hmcl.task.Schedulers;
import org.jackhuang.hmcl.task.Task;
import org.jackhuang.hmcl.ui.*;
import org.jackhuang.hmcl.ui.animation.TransitionPane;
import org.jackhuang.hmcl.util.io.FileUtils;
import java.io.IOException;
@@ -41,7 +42,7 @@ import java.util.stream.Stream;
import static org.jackhuang.hmcl.util.i18n.I18n.i18n;
import static org.jackhuang.hmcl.util.logging.Logger.LOG;
public final class WorldListPage extends ListPageBase<WorldListItem> implements VersionPage.VersionLoadable {
public final class WorldListPage extends ListPageBase<WorldListItem> implements VersionPage.VersionLoadable, TransitionPane.Cacheable {
private final BooleanProperty showAll = new SimpleBooleanProperty(this, "showAll", false);
private Path savesDir;