JavaFX ImageView - 图像清理

时间:2016-04-03 20:13:47

标签: java image javafx

我想问一下是否有人知道JavaFX ImageView如何处理图像清理。 当Image对象/内存空闲时。

这是导致我出现问题的情况: 我有两个"标签"在我的场景上的地方。这是我的标签:父窗格中的按钮和切换窗格。每个选项卡都有自己的ImageView。在我切换窗格之前,我在旧的ImageView上使用null,然后加载新的Image。我期待在切换标签之后旧的ImageView中的旧图像是免费的,但事实上并非如此。

要监视我使用Java VisualVM工具的行为,我正在从中触发GC。我还通过HeapDump验证对象列表,我可以在imageview上调用setImage(null)之后确认该事件,旧图像仍然保留在ImageView中,并且不能被GC收集。

我会非常感激如果有人可以建议我如何使用ImageView来清除旧图像以节省内存。

下面是显示此问题的代码:

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.image.Image;
import javafx.scene.image.ImageView;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;


public class IVTestApp extends Application {

    private String img1 = "http://formaciononline.co/wp-content/uploads/2014/05/aprender-a-programar-en-Java.jpg";
    private String img2 = "https://madushan1995.files.wordpress.com/2015/02/java-institute-new-final.png";

    @Override
    public void start(Stage primaryStage) throws Exception {
        BorderPane bp = new BorderPane();

        BorderPane p1 = new BorderPane();
        ImageView iv1 = new ImageView();
        iv1.setPreserveRatio(true);
        iv1.setFitHeight(200);
        iv1.setFitWidth(300);
        p1.setCenter(iv1);

        BorderPane p2 = new BorderPane();
        ImageView iv2 = new ImageView();
        iv2.setPreserveRatio(true);
        iv2.setFitHeight(200);
        iv2.setFitWidth(300);
        p2.setCenter(iv2);

        Button tab1 = new Button("tab1");
        Button tab2 = new Button("tab2");

        tab1.setOnAction(e -> {
            iv2.setImage(null);
            iv1.setImage(new Image(img1));
            bp.setCenter(p1);
        });

        tab2.setOnAction(e -> {
            iv1.setImage(null);
            iv2.setImage(new Image(img2));
            bp.setCenter(p2);
        });

        bp.setLeft(new VBox(tab1, tab2));

        Scene scen = new Scene(bp);
        primaryStage.setScene(scen);
        primaryStage.setWidth(600);
        primaryStage.setHeight(400);
        primaryStage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }

}

//注意: 我的环境由以下组成:Windows 7 x64bit和Java x86 jdk8u40

1 个答案:

答案 0 :(得分:0)

您可以尝试使用"空图像" (例如,具有所需大小的100%透明图像 - 易于使用alpha通道)保留空值。这应该替换存储器中保存的图像,从而使其可以收集垃圾。