如何在关闭舞台后清除Javafx Webview的内存使用

4

我尝试使用JavaFX中的Webview制作用户界面,但是出现了一个问题:当使用弹出窗口打开大型图片时,内存使用量非常大,并且在关闭弹出窗口后,内存使用量并没有下降。我通过Windows任务管理器查看了内存使用情况。

当使用Webview打开大小约为8MB的图片时,内存使用量达到了300MB。我不明白为什么会这么大。

我已经尝试过:

stage.setOnCloseRequest(new EventHandler<WindowEvent>() {

        @Override
        public void handle(WindowEvent event) { 
            webengine.load(null);   

        }
    });

但是,仍然不要释放内存。
3个回答

7

可能,您正在看到 RT-33729 WebView 泄漏 WCImgDecoderImpl 实例 的一个实例,目前的目标是在Java 8u20中进行修复。在RT-33729中,开发者(Leonid Popov)写道:

Webkit拥有用于网页的资源缓存,包括图片。即使不再被引用,它仍然保留未使用(“死亡”)资源,以防用户按下“后退”键来避免重新加载已加载的资源,而它们不会占用太多堆空间。请参见Webkit源代码中的注释中的详细信息: http://trac.webkit.org/browser/trunk/Source/WebCore/loader/cache/MemoryCache.h WCImgDecoderImpl的实例通过JNI由ImageSource引用,由BitmapImage引用,在MemoryCache中存储的CachedImage引用。我测试了一下,修改缓存使其完全清除其缓存的资源,并观察到所有WCImgDecoderImpl都已经消失。虽然WCImgDecoderImpl的实例可以从WebKit本地代码访问,但它并不是无用的。关键是它是由WebKit通过JNI控制WCImgDecoderImpl的生命周期。如何强制刷新此缓存以在删除WebView时清除,仍在调查中。
谈论描述中的测试应用程序。当您从场景中删除WebView时,它不会立即被删除(因此它不会释放任何资源)。相反,它在处理器线程上注册了一个处理器(类似于AWT使用的处理器),在一定时间内应该回调它并导致WebEngine使用的本机资源释放。
此外,我建议在删除WebView之前导航到“about:blank”,这将使其立即释放一些资源。

但是,也许你看到的完全是另一回事,我不能确定告诉你,比如 RT-35262 JVM崩溃由于WebView/Webkit中的内存泄漏,也将在Java 8u20中得到解决或RT-34630当JavaScript回调被分配时,WebView存在内存泄漏,将在Java 9中得到解决。


1

我的代码(适用于我),灵感来自jewelsea的答案。

// Delete cache for navigate back
webEngine.load("about:blank");
// Delete cookies 
java.net.CookieHandler.setDefault(new java.net.CookieManager());

0

我在互联网上进行了广泛的搜索,并找到了各种解决方案,但不幸的是,它们都对我无效。看起来,无论做什么,JFXPanel都会缓存场景。对我有效的是以下方法:

Scene scene = getScene();
jfxPanel.removeAll();
jfxPanel.setScene(scene);
WebView webView = (WebView) scene.getRoot();
webView.getWebEngine().load(url);

在编写程序时,getScene() 方法会重复使用之前创建的场景(包括其中的 Webview 和 WebEngine),当创建新场景时,JFXPanel 会变为不可见。因此,解决方法是移除并重新设置现有的场景,然后加载 URL。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接