Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Weird window close behavior

0 views
Skip to first unread message

mrstephengross

unread,
Jun 26, 2008, 3:27:16 PM6/26/08
to
I have a short swing program (see below) that dislpays a HelloWorld
frame. It compiles fine, but runtime behavior is a bit awkward. To
wit:

(1) I run the program. It shows a nice 100x100 empty panel. I move the
mouse directly over the CLOSE button (the top-right "X") WITHOUT
moving over the content pane at all. I click the close button. The
window closes.

(2) I run the program. It shows a nice 100x100 empty panel. I move the
mouse first over the content pane, THEN over the CLOSE button and
click it. The window does NOT close.

This is indeed weird behavior. I wonder if it has anything to do with
my system configuration. I am running:
OS: Ubuntu 6
Javac: gcj-4.2 (GCC) 4.3.2 (Ubuntu 4.2.3-2ubuntu6)
java: "1.5.0" gij (GNU libgcj) version 4.2.3 (Ubuntu 4.2.3-2ubuntu6)

Any ideas?

=== CODE FOLLOWS ===
import javax.swing.JFrame;

public class HelloWorldFrame {

public static void main(String args[]) {
new HelloWorldFrame();
}
HelloWorldFrame() {
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(100, 100);
frame.setVisible(true);
}
}
=== EOF ===

mrstephengross

unread,
Jun 26, 2008, 3:32:21 PM6/26/08
to
Small correction: I have Ubuntu 8 (kernel version 2.6.24-19).

--Steve

Daniel Pitts

unread,
Jun 26, 2008, 4:01:01 PM6/26/08
to
It is possible that because you didn't create the JFrame instance in the
Event Dispatch Thread, you've cause some strange race condition.

Always make sure you are in the EDT. If you know you're not, or aren't
sure, use EventQueue.invokeLater(...) to ensure your code is in the EDT.

--
Daniel Pitts' Tech Blog: <http://virtualinfinity.net/wordpress/>

mrstephengross

unread,
Jun 26, 2008, 4:08:54 PM6/26/08
to
> It is possible that because you didn't create the JFrame instance in the
> Event Dispatch Thread, you've cause some strange race condition.
> Always make sure you are in the EDT. If you know you're not, or aren't
> sure, use EventQueue.invokeLater(...) to ensure your code is in the EDT.

Ok, I looked up stuff on EDT and amended my code to use it (see
below). However, the weird behavior still persists. Have I implemented
it incorrectly?

=== CODE FOLLOWS ===
import javax.swing.JFrame;

import javax.swing.JLabel;
import javax.swing.SwingUtilities;

public class HelloWorldFrame {

public static void main(String args[]) {
new HelloWorldFrame();
}

HelloWorldFrame() {
Runnable doWorkRunnable = new Runnable() {
public void run() {


JFrame frame = new JFrame();

frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(100, 100);

frame.getContentPane().add(new
JLabel("hi"));
frame.setVisible(true);
}
};
SwingUtilities.invokeLater(doWorkRunnable);
}
}

=== EOF ===

mrstephengross

unread,
Jun 26, 2008, 4:34:38 PM6/26/08
to
I tried running the program with /usr/local/jdk/jdk1.6.0_03/bin/java,
and it produced (helpfully) a lot of debugging info regarding a
"locking assertion failure" (see below). Does anyone know how to
diagnose such an error message?


=== ERROR MESSAGE FOLLOWS ===

Locking assertion failure. Backtrace:
#0 /usr/lib/libxcb-xlib.so.0 [0xb5581767]
#1 /usr/lib/libxcb-xlib.so.0(xcb_xlib_unlock+0x31) [0xb55818b1]
#2 /usr/lib/libX11.so.6(_XReply+0xfd) [0xb55ce1bd]
#3 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56ce64e]
#4 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56acf97]
#5 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56ad248]
#6 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/
libmawt.so(Java_sun_awt_X11GraphicsEnvironment_initDisplay+0x2f)
[0xb56ad54f]
#7 [0xb5c6c66e]
#8 [0xb5c64edd]
#9 [0xb5c64edd]
#10 [0xb5c62243]
#11 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x620bc6d]
#12 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x630a828]
#13 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x620bb00]
#14 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/
libjvm.so(JVM_DoPrivileged+0x34b) [0x62619bb]
#15 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/
libjava.so(Java_java_security_AccessController_doPrivileged__Ljava_security_PrivilegedAction_2+0x3d)
[0xb7c7d96d]
#16 [0xb5c6c66e]
#17 [0xb5c64d77]
#18 [0xb5c62243]
#19 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x620bc6d]
Locking assertion failure. Backtrace:
#0 /usr/lib/libxcb-xlib.so.0 [0xb5581767]
#1 /usr/lib/libxcb-xlib.so.0(xcb_xlib_lock+0x2e) [0xb558181e]
#2 /usr/lib/libX11.so.6 [0xb55cd518]
#3 /usr/lib/libX11.so.6(XGetVisualInfo+0x26) [0xb55c40a6]
#4 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56ac249]
#5 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56ac495]
#6 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/libmawt.so
[0xb56ad2f9]
#7 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/xawt/
libmawt.so(Java_sun_awt_X11GraphicsEnvironment_initDisplay+0x2f)
[0xb56ad54f]
#8 [0xb5c6c66e]
#9 [0xb5c64edd]
#10 [0xb5c64edd]
#11 [0xb5c62243]
#12 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x620bc6d]
#13 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x630a828]
#14 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/libjvm.so
[0x620bb00]
#15 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/client/
libjvm.so(JVM_DoPrivileged+0x34b) [0x62619bb]
#16 /usr/local/jdk/jdk1.6.0_03/jre/lib/i386/
libjava.so(Java_java_security_AccessController_doPrivileged__Ljava_security_PrivilegedAction_2+0x3d)
[0xb7c7d96d]
#17 [0xb5c6c66e]
#18 [0xb5c64d77]
#19 [0xb5c62243]

mrstephengross

unread,
Jun 26, 2008, 5:04:25 PM6/26/08
to
One more followup. I found the following link:

http://daveshuck.instantspot.com/blog/2008/01/29/cxliblock-failed-error-on-Java-applications

which describes how you can "patch" the libmawt.so library to
eliminate the problem. It's kind of a hacky patch, however. It would
be nice if Sun/Ubuntu could sort out this mess so I don't have to tell
java users to apply an unsupported patch. Any ideas?

Lew

unread,
Apr 27, 2011, 11:46:32 AM4/27/11
to
To: comp.lang.java.gui

mrstephengross wrote:
> Javac: gcj-4.2 (GCC) 4.3.2 (Ubuntu 4.2.3-2ubuntu6)
> java: "1.5.0" gij (GNU libgcj) version 4.2.3 (Ubuntu 4.2.3-2ubuntu6)

I have Ubuntu 8, but I'm running real Java, not the pale imitation that GCJ
seems to be. I've never been able to get GCJ to work for me in the past.

So right away I suspect your problem is that you're using the wrong JVM.

> Ok, I looked up stuff on EDT and amended my code to use it (see
> below). However, the weird behavior still persists. Have I implemented
> it incorrectly?
>
> === CODE FOLLOWS ===
> import javax.swing.JFrame;
> import javax.swing.JLabel;
> import javax.swing.SwingUtilities;
>
> public class HelloWorldFrame {
>
> public static void main(String args[]) {
> new HelloWorldFrame();

Doing things this way causes code to be executed from the constructor. It
likely doesn't matter much in this particular case, but it might be wise to
break the habit so you aren't tempted when it really does matter.

> }
>
> HelloWorldFrame() {
> Runnable doWorkRunnable = new Runnable() {
> public void run() {
> JFrame frame = new JFrame();
>
> frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
> frame.setSize(100, 100);
> frame.getContentPane().add(new
> JLabel("hi"));
> frame.setVisible(true);
> }
> };
> SwingUtilities.invokeLater(doWorkRunnable);
> }
> }

Here's my recast to avoid doing anything besides construction in the constructor:

<sscce file="testit/HelloWorldFrame.java" >
package testit;

import java.awt.Dimension;


import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.SwingUtilities;

/** Investigate whether frame closes after mouse passes over the frame.
*/
public class HelloWorldFrame implements Runnable
{
private JFrame frame = new JFrame();

@Override
public void run()
{
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(new JLabel("hi"));

Dimension dim = new Dimension( 100, 100 );
frame.setPreferredSize( dim );

frame.pack();
frame.setVisible(true);
}

/** main.
* @param args the command line arguments
*/
public static void main( String[] args )
{
SwingUtilities.invokeLater( new HelloWorldFrame() );
}
}
</sscce>

> I move the mouse first over the content pane,
> THEN over the CLOSE button and click it.
> The window does NOT close.

Running this code against Sun's Java 6u10, the window closes even after I
mouse over the pane.

Maybe I'm right about GCJ being the problem. Have you tried using Java?

--
Lew

---
* Synchronet * The Whitehouse BBS --- whitehouse.hulds.com --- check it out free usenet!
--- Synchronet 3.15a-Win32 NewsLink 1.92
Time Warp of the Future BBS - telnet://time.synchro.net:24

Knute Johnson

unread,
Jun 26, 2008, 10:50:02 PM6/26/08
to

I'm curious, you have no constructor here. Why would you do that? I've
never seen anyone do this to create a basic Swing GUI before.

--

Knute Johnson
email s/nospam/knute2008/

--
Posted via NewsDemon.com - Premium Uncensored Newsgroup Service
------->>>>>>http://www.NewsDemon.com<<<<<<------
Unlimited Access, Anonymous Accounts, Uncensored Broadband Access

Andrew Thompson

unread,
Jun 26, 2008, 11:52:45 PM6/26/08
to
On Jun 27, 12:24 pm, Lew <l...@lewscanon.com> wrote:
...
>          frame.getContentPane().add(new JLabel("hi"));

Huhh?!? Lew, writing one *iota* of code to
support Java <1.5* JREs?

Is this..
- an oversite?**
- an(other) imposter?
- an alternate universe?

* See the new features for Swing in 1.5.
<http://java.sun.com/j2se/1.5.0/docs/relnotes/features.html#swing>

** I am constantly having to recheck my 1.5+
code for calls to getContentPane()!

--
Andrew Thompson
http://pscode.org/

Lew

unread,
Jun 27, 2008, 12:12:39 AM6/27/08
to

Knute Johnson wrote:
> I'm curious, you have no constructor here. Why would you do that? I've
> never seen anyone do this to create a basic Swing GUI before.

Not true, there is a constructor. Every object has a constructor.

The whole point of the SSCCE was to show how one can avoid putting anything
other than construction in a constructor. I even said,

> Here's my recast to avoid doing anything
> besides construction in the constructor:

in order to explain why I was doing what I did.

Why wouldn't I do it that way? Haven't you read that it's a best practice to
limit constructors to construction?

Y'know, people always complain that Java is verbose, but the minute you get
elegant with your code, ...

--
Lew

Lew

unread,
Jun 27, 2008, 12:15:04 AM6/27/08
to
Andrew Thompson wrote:

> Lew wrote:
> ...
>> frame.getContentPane().add(new JLabel("hi"));
>
> Huhh?!? Lew, writing one *iota* of code to
> support Java <1.5* JREs?
>
> Is this..
> - an oversite?**
> - an(other) imposter?
> - an alternate universe?
>
> * See the new features for Swing in 1.5.
> <http://java.sun.com/j2se/1.5.0/docs/relnotes/features.html#swing>
>
> ** I am constantly having to recheck my 1.5+
> code for calls to getContentPane()!

Well, there are two factors at work. One, I was quoting the OP's code, so it
really wasn't my fault. Two, I am not nearly as adept with Swing as you are.

I wouldn't normally label a label "hi", either.

What should actually amaze you is that I had anything useful to say about
Swing programming at all.

--
Lew

Knute Johnson

unread,
Jun 27, 2008, 12:25:48 AM6/27/08
to

I didn't say it was elegant, it is. I've just never seen anything like
it that's all.

So why wouldn't you construct a GUI in a GUI's constructor?

Lew

unread,
Jun 27, 2008, 12:35:15 AM6/27/08
to
Knute Johnson wrote:
> So why wouldn't you construct a GUI in a GUI's constructor?

That depends on your definition of "construction". The OP's code follows the
idiom you're probably used to seeing, where the GUI is assembled, but that is
not the same thing as object construction in the Java, or O-O sense. So let's
be precise in our terminology, shall we, and ask why one wouldn't assemble the
_GUI_ in the _object_'s constructor?

The answer is what I said up front - it's a best practice not to do anything
but construction (that's *object* construction, please avoid sophistry) in the
object constructor. Properly speaking, the assembly of the GUI in an object,
like the frame holder portrayed by both the OP's and my examples, should occur
only after the object, the frame holder, is fully constructed.

It was to show how one can translate that lip-service principle into practice
that I presented the example.

--
Lew

Daniele Futtorovic

unread,
Jun 27, 2008, 10:00:40 AM6/27/08
to
On 2008-06-27 05:52 +0100, Andrew Thompson allegedly wrote:
> ** I am constantly having to recheck my 1.5+
> code for calls to getContentPane()!

Why is that?


Public code examples should keep using the getContentPane() form, IMHO.


--
DF.
to reply privately, change the top-level domain
in the FROM address from "invalid" to "net"

mrstephengross

unread,
Jun 27, 2008, 10:26:39 AM6/27/08
to
Hi folks. I did finally figure out that, at the very least, using
Sun's distro of java fixes the problem. It appears that Ubuntu has a
GNU-based default distro of Java that is a bit buggy. My solution, for
now anyway, is to recommend to my users that they use the Sun distro
instead. It's not a great solution, but it works.

Thanks for the help,
--Steve

Knute Johnson

unread,
Jun 27, 2008, 11:30:14 AM6/27/08
to
Lew wrote:
> Knute Johnson wrote:
>> So why wouldn't you construct a GUI in a GUI's constructor?
>
> That depends on your definition of "construction". The OP's code
> follows the idiom you're probably used to seeing, where the GUI is
> assembled, but that is not the same thing as object construction in the
> Java, or O-O sense. So let's be precise in our terminology, shall we,
> and ask why one wouldn't assemble the _GUI_ in the _object_'s constructor?
>
> The answer is what I said up front - it's a best practice not to do
> anything but construction (that's *object* construction, please avoid
> sophistry) in the object constructor. Properly speaking, the assembly
> of the GUI in an object, like the frame holder portrayed by both the
> OP's and my examples, should occur only after the object, the frame
> holder, is fully constructed.

This is the part that I am curious about. What makes it better practice
to 'build' the GUI someplace other than the constructor? And to take
that a step further, if you are building a GUI in a frame, why would it
not be even better to build it totally in the main() method and avoid
distributing the code out to the run()?

> It was to show how one can translate that lip-service principle into
> practice that I presented the example.

Honestly, I'm just curious and want to understand the thinking behind
your method. Are these best practices written down somewhere?

Thanks,

Lew

unread,
Jun 27, 2008, 7:02:32 PM6/27/08
to
Knute Johnson wrote:
> This is the part that I am curious about. What makes it better practice
> to 'build' the GUI someplace other than the constructor?

For that I recommend further reading. I was doing it as an exercise to follow
the advice I've read all over the place, is all.

> And to take that a step further, if you are building a GUI in a frame, why would it
> not be even better to build it totally in the main() method and avoid
> distributing the code out to the run()?

What's to avoid? The run() seems to me to be the natural place to do that,
given that SwingUtilities.invokeLater() wants a Runnable, and we want to do
the build of the GUI on the EDT.

>> It was to show how one can translate that lip-service principle into
>> practice that I presented the example.
>
> Honestly, I'm just curious and want to understand the thinking behind
> your method. Are these best practices written down somewhere?

The thinking is that I should see how to follow the advice of these pundits,
which indeed is written down in many places, none of which I can quote off the
top of my hand. The thinking is that I keep reading how dangerous it is to
use partially constructed objects, how there can be uninitialized variables or
thread dangers, how state of even final variables can appear to change, and
how one should be in the habit of limiting constructors to construction.
Apparently this is a new concept for you, but I must have seen it in a dozen
places.

So what the heck, if this is such a good idea, let's see how hard it is to
implement. After all, if it's difficult, maybe one should consider not
following this advice. Turns out, it's not only easy but makes for quite
clean and elegant code. Thus the cost is nil, and the benefits, well, you
just have to believe the pundits. I don't have enough authority.

Sorry I don't have the links, but you can google them as easily as I. If you
go even further, as in Joshua Bloch's /Effective Java/, Item 1, you won't use
constructors at all but static factory methods.

--
Lew

Lew

unread,
Jun 27, 2008, 7:04:04 PM6/27/08
to

How is that "not a great solution"? What better? What's wrong with it?

--
Lew

RedGrittyBrick

unread,
Jun 28, 2008, 5:09:57 PM6/28/08
to
Lew wrote:
> Knute Johnson wrote:
>> This is the part that I am curious about. What makes it better
>> practice to 'build' the GUI someplace other than the constructor?

I must admit I find it very natural to "construct" the GUI elements in a
GUI object's constructor. For example: to instantiate JTextFields in the
constructor of a subclass of JPanel.

>>
>> Honestly, I'm just curious and want to understand the thinking behind
>> your method. Are these best practices written down somewhere?
>
> The thinking is that I should see how to follow the advice of these
> pundits, which indeed is written down in many places, none of which I
> can quote off the top of my hand. The thinking is that I keep reading
> how dangerous it is to use partially constructed objects, how there can
> be uninitialized variables or thread dangers, how state of even final
> variables can appear to change, and how one should be in the habit of
> limiting constructors to construction. Apparently this is a new concept
> for you, but I must have seen it in a dozen places.
>

Doesn't the issue with partially constructed objects only arise if your
constructor passes a reference to itself to other methods?

E.g. http://nat.truemesh.com/archives/000222.html

Or

class ExamplePanel extends JPanel {
ExamplePanel() {
setLayout(new BoxLayout(this, BoxLayout.PAGE_AXIS));
// ^^^^ partially constructed!
add(new JLabel("One"));
add(new JLabel("Two"));
add(new JLabel("Three"));
}
}

Since the ancestral JComponent() constructor will have been completed
before BoxLayout() gets to make use of it - isn't it a fully constructed
JComponent so far as BoxLayout is concerned?

--
RGB

Lew

unread,
Jun 28, 2008, 5:23:18 PM6/28/08
to
RedGrittyBrick wrote:
> Doesn't the issue with partially constructed objects only arise if your
> constructor passes a reference to itself to other methods?
>
...

> Since the ancestral JComponent() constructor will have been completed
> before BoxLayout() gets to make use of it - isn't it a fully constructed
> JComponent so far as BoxLayout is concerned?

The questions you and Knute ask are valid and valuable.

I agree that there aren't dangers visible in the idiom of assembly in the
constructor in the cases we usually see, where the constructing object sort of
goes away after starting things off.

If I express a preference in the simple case it is that the notion of a run()
on an argument to invokeLater() seems more "natural" than to run things from a
constructor. Indeed the recast does eliminate the need for an extra anonymous
Runnable, making for cleaner code.

This I had not predicted, thinking /a priori/ that forcing code out of the
constructor would increase complexity. Instead, it simplified.

The second difference is one of planning. Since the class is not written to
prevent extension, it risks having subclasses. Safety in the visible
constructor might not convey to the inheritors.

Another danger is one of habit. If one gets used to putting a lot of action
in the constructor, one could trip on a corner case before realizing it. If
one habitually only lets fully-constructed objects participate, then safety is
built in from the get-go.

Finally, it comes down to judgment and style. When one knows that it is
harmless, then of course there's no harm done.

Before reaching a decision on the style questions,

- should I rigorously push non-construction out of the constructor?
- how rigorously?

I wanted to explore how one could even do such a thing. GUI assembly, so
often and publicly done in constructors, seemed like a perfect candidate for
the exploration.

I conclude that the rule to limit constructors to (object) construction is
valuable, and can lead to lean code that expresses its algorithms as "literate
code" quite naturally through method names and such. It simplifies reasoning
about thread boundaries in the cited example, and whether GUI assembly
correctly resides on the EDT. I found no disadvantages to the rule. So far.

YMMV.

The group has responded intelligently with excellent and probing questions
about the topic. Your participation has immeasurably increased the value of
the investigation, not least for forcing me to think more deeply about the
issues involved.

--
Lew

Roedy Green

unread,
Jun 30, 2008, 1:35:21 PM6/30/08
to
On Thu, 26 Jun 2008 12:27:16 -0700 (PDT), mrstephengross
<mrstev...@gmail.com> wrote, quoted or indirectly quoted someone
who said :

>import javax.swing.JFrame;
>
>public class HelloWorldFrame {
>
> public static void main(String args[]) {
> new HelloWorldFrame();
> }
> HelloWorldFrame() {
> JFrame frame = new JFrame();
> frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
> frame.setSize(100, 100);
> frame.setVisible(true);
> }
>}

When I run your program under Vista I don't see this behaviour. Sounds
like a bug in your JVM. Try submitting your sscce to whomever wrote
it.
--

Roedy Green Canadian Mind Products
The Java Glossary
http://mindprod.com

0 new messages