Swing memory leak caused by JFrame.setLocation? (original) (raw)
Nick Miyake nmiyake at palantir.com
Thu Jan 30 17:55:54 UTC 2014
- Previous message: [9] Review request: 8033233 [JLightweightFrame] support default JViewport BLIT_SCROLL_MODE
- Next message: Swing memory leak caused by JFrame.setLocation?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]
Hello,
I believe I have found an issue that causes a memory leak in the Java process when using "JFrame.setLocation".
If you launch the application in the sample program below (which simply calls "setLocation" on a JFrame repeatedly) in MacOS using JDK 1.7.0_06 or later and observe the memory usage of the application using Activity Monitor and click the "setLocation x 1000" button, the memory usage of the program nearly triples (on my machine, it goes from 50MB to 150MB) and never decreases after that. The issue seems to be with the Java process itself, as the heap/memory usage reported by JConsole does not change. Repeating the same steps using JDK 1.7.0_05 or earlier shows that this leak does not seem to happen.
Sample code:
public final class MemoryLeakRepro { private static final int NUM_SET_LOCATIONS = 1000; public static void main(String[] args) { javax.swing.SwingUtilities.invokeLater(new Runnable() { public void run() { final JFrame frame = new JFrame("Test"); JPanel content = new JPanel(new GridLayout(1, 1));
JButton button = new JButton("setLocation x " + NUM_SET_LOCATIONS);
content.add(button);
button.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
for (int i = 0; i < NUM_SET_LOCATIONS; i++) {
int delta = (i % 2 == 0 ? 1 : -1);
frame.setLocation(frame.getX() + delta, frame.getY() +
delta);
}
}
});
frame.setContentPane(content);
frame.pack();
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
});
}
}
A similar issue seems to reproduce on Windows as well (although not using the same "setLocation" button method). If you use the other sample program below, increase the window size and then drag the JPanel all over the screen repeatedly, the memory usage goes from around 28MB to 34MB or so and never comes back down. Repeating the process can cause it to take up more and more memory, which never seems to be released. The same behavior is not observed when dragging the native title bar. This behavior occurs in both JDK 1.6.0_45 and in all versions of JDK 7 I tested.
Sample code:
public final class MemoryLeakRepro { private static final int NUM_SET_LOCATIONS = 1000; public static void main(String[] args) { javax.swing.SwingUtilities.invokeLater(new Runnable() { public void run() { final JFrame frame = new JFrame("Test"); JPanel content = new JPanel(new GridLayout(1, 1));
JPanel dragPanel = new JPanel();
dragPanel.setPreferredSize(new Dimension(100, 100));
FrameDragger frameDragger = new FrameDragger(frame);
dragPanel.addMouseListener(frameDragger);
dragPanel.addMouseMotionListener(frameDragger); content.add(dragPanel); frame.setContentPane(content);
frame.pack();
frame.setVisible(true);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
});
} private static final class FrameDragger extends MouseAdapter { private final JFrame frame; private int prevMouseX; private int prevMouseY; public FrameDragger(JFrame frame) { this.frame = frame; } @Override public void mousePressed(MouseEvent e) { prevMouseX = e.getX(); prevMouseY = e.getY(); } @Override public void mouseDragged(MouseEvent e) { int currMouseX = e.getX(); int currMouseY = e.getY(); int currWindowX = frame.getX(); int currWindowY = frame.getY();
int moveX = currMouseX - prevMouseX;
int moveY = currMouseY - prevMouseY;
if (moveX == 0 && moveY == 0) return;
int newFrameX = currWindowX + moveX;
int newFrameY = currWindowY + moveY;
frame.setLocation(newFrameX, newFrameY);
} } }
Has anyone here seen this issue in the past or have any ideas about what we could do to fix it?
Thanks, -Nick
-------------- next part -------------- An HTML attachment was scrubbed... URL: <http://mail.openjdk.java.net/pipermail/swing-dev/attachments/20140130/d8c8b1e3/attachment.html> -------------- next part -------------- A non-text attachment was scrubbed... Name: smime.p7s Type: application/pkcs7-signature Size: 5034 bytes Desc: not available URL: <http://mail.openjdk.java.net/pipermail/swing-dev/attachments/20140130/d8c8b1e3/smime.p7s>
- Previous message: [9] Review request: 8033233 [JLightweightFrame] support default JViewport BLIT_SCROLL_MODE
- Next message: Swing memory leak caused by JFrame.setLocation?
- Messages sorted by: [ date ] [ thread ] [ subject ] [ author ]