changeset 5995:7a85b9cf6241

RT-34634: Mac: Memory leak when Menu.useSystemMenuBar(true) is used. Reviewed-by: leifs
author jgiles
date Wed, 18 Dec 2013 11:05:19 +1300
parents dabee4f56388
children 2d7e3f9f76ec
files modules/controls/src/main/java/com/sun/javafx/scene/control/skin/MenuBarSkin.java
diffstat 1 files changed, 16 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/modules/controls/src/main/java/com/sun/javafx/scene/control/skin/MenuBarSkin.java	Tue Dec 17 12:47:27 2013 +1300
+++ b/modules/controls/src/main/java/com/sun/javafx/scene/control/skin/MenuBarSkin.java	Wed Dec 18 11:05:19 2013 +1300
@@ -52,6 +52,9 @@
 import javafx.scene.input.MouseEvent;
 import javafx.scene.layout.HBox;
 import javafx.stage.Stage;
+
+import java.lang.ref.Reference;
+import java.lang.ref.WeakReference;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.List;
@@ -83,7 +86,7 @@
     private TraversalEngine engine;
     private Direction direction;
 
-    private static WeakHashMap<Stage, MenuBarSkin> systemMenuMap;
+    private static WeakHashMap<Stage, Reference<MenuBarSkin>> systemMenuMap;
     private static List<MenuBase> wrappedDefaultMenus = new ArrayList<MenuBase>();
     private static Stage currentMenuBarStage;
     private List<MenuBase> wrappedMenus;
@@ -105,10 +108,16 @@
         }
     }
 
+    private static MenuBarSkin getMenuBarSkin(Stage stage) {
+        if (systemMenuMap == null) return null;
+        Reference<MenuBarSkin> skinRef = systemMenuMap.get(stage);
+        return skinRef == null ? null : skinRef.get();
+    }
+
     private static void setSystemMenu(Stage stage) {
         if (stage != null && stage.isFocused()) {
             while (stage != null && stage.getOwner() instanceof Stage) {
-                MenuBarSkin skin = systemMenuMap.get(stage);
+                MenuBarSkin skin = getMenuBarSkin(stage);
                 if (skin != null && skin.wrappedMenus != null) {
                     break;
                 } else {
@@ -126,7 +135,7 @@
         if (stage != currentMenuBarStage) {
             List<MenuBase> menuList = null;
             if (stage != null) {
-                MenuBarSkin skin = systemMenuMap.get(stage);
+                MenuBarSkin skin = getMenuBarSkin(stage);
                 if (skin != null) {
                     menuList = skin.wrappedMenus;
                 }
@@ -140,7 +149,7 @@
     }
 
     private static void initSystemMenuBar() {
-        systemMenuMap = new WeakHashMap<Stage, MenuBarSkin>();
+        systemMenuMap = new WeakHashMap<>();
 
         final InvalidationListener focusedStageListener = new InvalidationListener() {
             @Override public void invalidated(Observable ov) {
@@ -531,7 +540,7 @@
             Scene scene = getSkinnable().getScene();
             if (scene.getWindow() instanceof Stage) {
                 Stage stage = (Stage)scene.getWindow();
-                MenuBarSkin curMBSkin = (systemMenuMap != null) ? systemMenuMap.get(stage) : null;
+                MenuBarSkin curMBSkin = getMenuBarSkin(stage);
                 if (getSkinnable().isUseSystemMenuBar() && !menusContainCustomMenuItem()) {
                     if (curMBSkin != null &&
                         (curMBSkin.getSkinnable().getScene() == null || curMBSkin.getSkinnable().getScene().getWindow() == null)) {
@@ -547,8 +556,8 @@
                             initSystemMenuBar();
                         }
                         if (wrappedMenus == null) {
-                            wrappedMenus = new ArrayList<MenuBase>();
-                            systemMenuMap.put(stage, this);
+                            wrappedMenus = new ArrayList<>();
+                            systemMenuMap.put(stage, new WeakReference<>(this));
                         } else {
                             wrappedMenus.clear();
                         }