Tuesday, November 11, 2008

Why Swing UIs are so hard...

I'll tell you why - ok, well at least with issue I'm having now, which seems to be a common issue - LAYOUT.

How do you nicely lay out components? I've been reasonably happy with the layout tools NetBeans puts in for you. But I have a main window with 9 sub-panels, almost like portlets. Not all are the same size - and I want to have the user re-size them. Splitters? No, not the JSplitPane - too much overhead, can only split 2 sides. Enter the MultiSplitPane from SwingLabs - quite nice! An arbitrary grid layout even with custom split bars. BUT - how to specify a nice division. Well it provides "weight" - that's where the extra space goes. But what about the initial size? It uses each component's "preferred size" - seems like a good idea. But how do the components set their preferred size? This gets to the basic issue:

Layout - Bottom up or top down?
I attempted to have a component (tree control) set its preferred size based on the text and font it is assigned. Seems like a fine idea with good control, precision, etc. Nope! NullPointerException - the graphics aren't assigned at constructor time. Put in nice code:
String name = net.name;
FontRenderContext frc = ((Graphics2D)this.getGraphics()).getFontRenderContext();
TextLayout tl = new TextLayout(name, networkTree.getFont(), frc);
setPreferredSize(new Dimension((int)(tl.getBounds().getWidth()*1.5), 0));

NullPointerException at the line with getGraphics.

Top down...
Seems like Swing should learn from HTML/CSS - why can't a table support column widths in percentages? Seems like a simple enough thing - so I'm off to try banging that into MultiSplitPane.

Thursday, October 9, 2008

Better Swing through dynamic JVM languages...

The holy grail (?) - applying lessons learned in Web App development to Swing/desktop development. We have Python, Ruby, Groovy and now Scala on the JVM. Shouldn't they bring something to the party in terms of making my life easier to make Swing apps - which is still very tedious.

A couple good news items on this front-
Griffon for Groovy - This project shows some great promise! I hadn't been a big Groovy fan mostly because if it looks so much like Java, why not use Java? But then I realize a large impediment to starting up with Python or Ruby or Scala is the learning curve. On closer examination, it seems perhaps Groovy gets the benefits of a dynamic language while still in the overall "framework" of Java. That would be nice. One might say, 'but without the "buzz" it won't get the vast libraries of Python' - true, except for the extent to which it can just use the vast array of Java libraries. Is there an impedance mismatch? Don't know.

Monkeybars for JRuby - I just came across this project yesterday. (See http://groups.google.com/group/monkeybars) It seems to have a lot of the right objectives. The interesting thing is that there is no Ruby API for Swing components - you do the actual Swing components in a Java class and the Ruby code introspects the bytecode to manipulate stuff. Well, plausible I guess.

But interestingly, I've still not come across any Python-Swing or Scala-Swing toolkit/frameworks.

Singletons gone bad - again

I've been successful at using the swing framework, org.jdesktop.application classes in particular. I have a handful of applications sharing a rather large code base. Now however, of course we want to launch application B from application A. It actually works, but the problem is now that the Application singleton became B instead of A and when the objects in the A application go to use their resource map or action map, the get application B which of course isn't an A, so ClassCastException results. Ugh.

Option A: don't use ResourceMap and ActionMap.
I've already headed in this direction because of NetBeans' issues around keeping track of which class is the true application when it is generating code - so that wouldn't be all bad.

Option B: create one master application perhaps deriving from a new class MultipleFrameApplication extended from SingleFrameApplication. It would know how to create a new JFrame, etc. Arguments could be passed in to specify which "real" application to run - which in this case would mean which view to show first.

Option C: pass application A to the new view for application B. But somewhere we need a new JFrame, etc.

I have a related issue in that my model and helper (controller?) classes have common base classes and the models are singletons. So when application B launches, I'm not sure I want a whole new B model which would replicate the base classes of model A.

Hmm...

Tuesday, May 6, 2008

NetBeans (6.1) lost my code!

Things were going so well... I had created a Java Desktop application, got a desktop pane going, a dialog and an internal pane. It was now time to take a step back, refactor a little and etc.

I renamed my project, created a project group and BOOM! No more code. After a day or so reading about various frameworks, etc. and figuring out NetBeans 6.1 I got the program running in about an afternoon. Now I have nothing.
And now I have to Join Netbeans.org to post a message about this. Forget about it! My joining wiki.netbeans.org apparently wasn't good enough. My subscription to nbannounce was not good enough. FUGGET ABOUTIT!

The GUI builder was fairly good - but I'm going back to IntelliJ.