Problem
In our stand-alone Swing application, a modal JDialog is displayed for certain events (button press, etc.). The dialog contains some other Swing components (JLabels, JButtons, ...). Instead, I explicitly set its size through the JDialog.setBounds(...)
method, which we call JDialog.pack()
(or the JOptionPane
showDialog(...)
methods, invokes it implicitly). The size calculated by the pack()
method is always constant (for example, 300x100 px.) Unfortunately, sometimes the real dimension of the visible dialog is 1x1 px ( JDialog.getSize().equals(new Dimension(1, 1))
).
Initializing JDialog
There are two ways to initialize JDialog
in our application. We verified that both initialization methods are always called from EventDispatchThread.
First method
We simply create an instance of ADialog
, which is a subclass of JDialog
. Here is a snippet of our initialization procedure:
ADialog dialog = new ADialog(); dialog.setContentPane(content); dialog.setVisible(true);
Here is our implementation of ADialog
:
public class ADialog extends JDialog implements ComponentListener { public JfosDialog(Frame owner) { super(owner); init(); } private void init() { super.addComponentListener(this); } @Override public void componentShown(ComponentEvent e) {
Second method
public JOptionPane showDialog(...) { JOptionPane jop = new JOptionPane(message, msgType, option, null, textMessages); JDialog dialog = jop.createDialog(owner, titleMsg); setDialogTraversal(dialog); dialog.setVisible(true); dialog.dispose(); return jop; }
Reproducibility
Environment
- Ubuntu 12.04., JRE 1.6 / JRE 1.7 / OpenJDK 1.6
- Windows XP, JRE 1.6.u16
Reproducing a problem using the first initialization method
We just show and then hide the dialog N times (0 <N <1000), and once by the size of the time dialog box - 1x1 (sign of a problem with the stream, race condition). Since the nature of this problem is very stochastic, we wrote a simple java.awt.Robot script that shows and hides the dialog in a loop. It is simply more convenient than doing it manually.
Reproducing a problem with the second initialization method
The steps are the same as in the first method: just show and then hide the dialog N times. Unfortunately, we cannot reproduce it in our development environment, but it can be easily reproduced on a production PC (in our development environment there is another processor, some kind of antivirus that constantly creates a system boot, etc.)
So far, we cannot reproduce the problem in some test / sample project. This may mean that something is wrong with our application. However, it seems that the problem may be somewhere in the native Swing code (see the Tracing section).
Tracing
We traced the cause of our problem in the 64-bit OpenJDK 1.6.0_24. We found that the dimension of JDialog
changes to XConfigureEvent
released by XToolkit
. The event is built in the event loop of the XToolkit.run(boolean)
method after returning from the built-in method call.
To simplify things, I am only XToolkit
code snippet here illustrating the XToolkit
event loop mechanism with our trace results. You can also see the full source code here .
public class XToolkit ... { ... public void run(boolean loop) { XEvent ev = new XEvent(); while(true) { awtLock(); try { if (loop == SECONDARY_LOOP) { ... } else { ...
Do you have ideas on how to fix this error / track it deeper / reproduce it more confidently ...?
I appreciate any ideas, as this mistake is a real pain.