JDK-8094438 : OutOfMemory error due to GrowableDataBuffer in Canvas when window is not shown
  • Type: Bug
  • Component: javafx
  • Sub-Component: graphics
  • Affected Version: 7u40
  • Priority: P4
  • Status: Closed
  • Resolution: Duplicate
  • Submitted: 2014-03-20
  • Updated: 2015-06-12
  • Resolved: 2014-03-20
Related Reports
Duplicate :  
Description
Our application is drawing incoming images from a high speed camera to a JavaFX canvas using canvas.getGraphicsContext2D().drawImage(...). This is working fine as long as the JavaFX window is shown (for example the screen is not locked or the window is not minimized). When the window is not shown, the GrowableDataBuffer in the Canvas keeps growing with the new images, which after a while (depends on the size of the images and the speed to load them) leads to an out of memory error due to Java heap space.

The problem does not occur if you are drawing the same Image objects over and over, it needs to be new Image objects that are drawn.

The problem exists in at least JavaFX runtime versions 2.2.40-b43 and 8.0.0-b132.
Comments
This is a duplicate of a known issue, RT-24903.
20-03-2014

The following is a test application you can use for testing the issue. Place some png-images in the directory C:\temp\images\ (or change in the code to something else) and run. -------------------------------- import java.io.File; import java.io.FileInputStream; import java.io.FilenameFilter; import java.io.IOException; import java.util.Random; import javafx.animation.AnimationTimer; import javafx.application.Application; import javafx.scene.Group; import javafx.scene.Scene; import javafx.scene.canvas.Canvas; import javafx.scene.image.Image; import javafx.stage.Stage; public class TestMemory extends Application { private final static Random random = new Random(); private Canvas canvas; public static void main(String[] args) { launch(args); } @Override public void start(Stage primaryStage) throws Exception { System.out.println(com.sun.javafx.runtime.VersionInfo .getRuntimeVersion()); primaryStage.setTitle("Test memory"); Group root = new Group(); canvas = new Canvas(); canvas.setWidth(640); canvas.setHeight(480); root.getChildren().add(canvas); primaryStage.setScene(new Scene(root)); primaryStage.show(); AnimationTimer animationTimer = new AnimationTimer() { int i = 1; @Override public void handle(final long elapsedNanos) { System.out.println("displaying " + i++); canvas.getGraphicsContext2D().drawImage(getImage(), 0, 0); } }; animationTimer.start(); } private Image getImage() { try { File dir = new File("C:\\temp\\images"); File[] files = dir.listFiles(new FilenameFilter() { @Override public boolean accept(File dir, String name) { return name.endsWith(".png"); } }); File file = files[random.nextInt(files.length)]; FileInputStream is = new FileInputStream(file); Image image = new Image(is); is.close(); return image; } catch (IOException e) { e.printStackTrace(); return null; } } } ------------ end ----------------
20-03-2014