diff --git a/apps/toys/Hello/src/main/java/hello/HelloPopup.java b/apps/toys/Hello/src/main/java/hello/HelloPopup.java --- a/apps/toys/Hello/src/main/java/hello/HelloPopup.java +++ b/apps/toys/Hello/src/main/java/hello/HelloPopup.java @@ -128,11 +128,10 @@ } nextPopup.show(popupParent, popupX, popupY); - - Iterator windows = Window.impl_getWindows(); - while (windows.hasNext()) { - System.out.println("W: " + windows.next().getClass().getName()); - } + + Window.getWindows().stream().forEach(window -> { + System.out.println("W: " + window.getClass().getName()); + }); } } diff --git a/modules/graphics/src/main/java/com/sun/javafx/tk/Toolkit.java b/modules/graphics/src/main/java/com/sun/javafx/tk/Toolkit.java --- a/modules/graphics/src/main/java/com/sun/javafx/tk/Toolkit.java +++ b/modules/graphics/src/main/java/com/sun/javafx/tk/Toolkit.java @@ -855,14 +855,12 @@ */ public void pauseScenes() { pauseScenesLatch = new CountDownLatch(1); - Iterator i = Window.impl_getWindows(); - while (i.hasNext()) { - final Window w = i.next(); - final Scene scene = w.getScene(); + Window.getWindows().stream().forEach(window -> { + final Scene scene = window.getScene(); if (scene != null) { this.removeSceneTkPulseListener(scene.impl_getScenePulseListener()); } - } + }); this.getMasterTimer().pause(); SceneHelper.setPaused(true); } @@ -874,14 +872,12 @@ public void resumeScenes() { SceneHelper.setPaused(false); this.getMasterTimer().resume(); - Iterator i = Window.impl_getWindows(); - while (i.hasNext()) { - final Window w = i.next(); - final Scene scene = w.getScene(); + Window.getWindows().stream().forEach(window -> { + final Scene scene = window.getScene(); if (scene != null) { this.addSceneTkPulseListener(scene.impl_getScenePulseListener()); } - } + }); pauseScenesLatch.countDown(); pauseScenesLatch = null; } diff --git a/modules/graphics/src/main/java/javafx/stage/Window.java b/modules/graphics/src/main/java/javafx/stage/Window.java --- a/modules/graphics/src/main/java/javafx/stage/Window.java +++ b/modules/graphics/src/main/java/javafx/stage/Window.java @@ -28,9 +28,12 @@ import java.security.AllPermission; import java.security.AccessControlContext; import java.security.AccessController; +import java.util.ArrayList; import java.util.HashMap; import java.util.Iterator; +import java.util.List; +import com.sun.javafx.collections.annotations.ReturnsUnmodifiableCollection; import javafx.beans.property.DoubleProperty; import javafx.beans.property.DoublePropertyBase; import javafx.beans.property.ObjectProperty; @@ -43,6 +46,7 @@ import javafx.beans.property.ReadOnlyDoubleWrapper; import javafx.beans.property.SimpleObjectProperty; import javafx.collections.FXCollections; +import javafx.collections.ObservableList; import javafx.collections.ObservableMap; import javafx.event.Event; import javafx.event.EventDispatchChain; @@ -77,9 +81,10 @@ public class Window implements EventTarget { /** - * A list of all the currently existing windows. This is only used by SQE for testing. + * A list of all the currently _showing_ windows. This is publicly accessible via the unmodifiableWindows wrapper. */ - private static WeakReferenceQueuewindowQueue = new WeakReferenceQueue(); + private static ObservableList windows = FXCollections.observableArrayList(); + private static ObservableList unmodifiableWindows = FXCollections.unmodifiableObservableList(windows); static { WindowHelper.setWindowAccessor( @@ -134,20 +139,23 @@ } /** - * Return all Windows + * Returns a list containing a reference to the currently showing JavaFX windows. The list is unmodifiable - + * attempting to modify this list will result in an {@link UnsupportedOperationException} being thrown at runtime. * - * @return Iterator of all Windows - * @treatAsPrivate implementation detail - * @deprecated This is an internal API that is not intended for use and will be removed in the next version + *

It is strongly encouraged that developers do not retain references to the Window instances referenced in this + * list, as doing so can lead to memory leaks.

+ * + * @return A list containing all windows currently showing. + * @since 9 */ - @Deprecated - public static Iterator impl_getWindows() { + @ReturnsUnmodifiableCollection + public static ObservableList getWindows() { final SecurityManager securityManager = System.getSecurityManager(); if (securityManager != null) { securityManager.checkPermission(new AllPermission()); } - return (Iterator) windowQueue.iterator(); + return unmodifiableWindows; } final AccessControlContext acc = AccessController.getContext(); @@ -824,9 +832,9 @@ impl_visibleChanging(newVisible); if (newVisible) { hasBeenVisible = true; - windowQueue.add(Window.this); + windows.add(Window.this); } else { - windowQueue.remove(Window.this); + windows.remove(Window.this); } Toolkit tk = Toolkit.getToolkit(); if (impl_peer != null) { diff --git a/modules/jmx/src/main/java/com/oracle/javafx/jmx/SGMXBeanImpl.java b/modules/jmx/src/main/java/com/oracle/javafx/jmx/SGMXBeanImpl.java --- a/modules/jmx/src/main/java/com/oracle/javafx/jmx/SGMXBeanImpl.java +++ b/modules/jmx/src/main/java/com/oracle/javafx/jmx/SGMXBeanImpl.java @@ -362,12 +362,10 @@ private void importWindows() { int windowCount = 0; - final Iterator it = Window.impl_getWindows(); + final List windows = Window.getWindows(); jwindows = JSONDocument.createArray(); - while (it.hasNext()) { - final Window window = it.next(); - + for (Window window : windows) { windowMap.put(windowCount, window); final JSONDocument jwindow = JSONDocument.createObject(); diff --git a/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_sceneGraph_Test.java b/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_sceneGraph_Test.java --- a/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_sceneGraph_Test.java +++ b/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_sceneGraph_Test.java @@ -43,6 +43,7 @@ import java.util.HashSet; import java.util.Iterator; +import java.util.List; import java.util.Set; public class SGMXBean_sceneGraph_Test { @@ -74,12 +75,10 @@ stage2.setScene(scene2); stage2.show(); - final Iterator it = Window.impl_getWindows(); + final List windows = Window.getWindows(); nodesCount = 0; - while (it.hasNext()) { - final Window w = it.next(); + for (Window w : windows) { nodesCount += countNodes(w.getScene().getRoot()); - } } diff --git a/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_windows_Test.java b/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_windows_Test.java --- a/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_windows_Test.java +++ b/modules/jmx/src/test/java/com/oracle/javafx/jmx/SGMXBean_windows_Test.java @@ -42,6 +42,7 @@ import java.util.HashSet; import java.util.Iterator; import java.util.Set; +import java.util.List; public class SGMXBean_windows_Test { @@ -66,12 +67,8 @@ stage2.setScene(scene2); stage2.show(); - final Iterator it = Window.impl_getWindows(); - windowsCount = 0; - while (it.hasNext()) { - windowsCount++; - it.next(); - } + final List windows = Window.getWindows(); + windowsCount = windows.size(); } private static JSONDocument getJSONDocument(String source) {