Graphical interfaces are best described by resources
Last week an interesting discussion popped up at Javalobby. (Yes, really.) The post was rhetorically asking why we don’t have a resourced-based GUI framework in Java.
Almost every platform has a visual designer that serializes the GUI to resources (some XML, some proprietary binaries) and then attaches it to the controller at runtime. Apple has had this for years with Interface Builder…
Poor NeXT. Their greatest innovations have been understandably muddled with those of Apple Computer in the public memory. It’s a complicated story but one fact is worth absorbing: Mac OS X is NeXTstep. Those of us using Macs in the late ’90s will remember this for the rest of our lives, as we watched for several grueling years while Apple made it so.
NeXTstep’s AppKit library (now Apple’s Cocoa) was the biggest innovation in GUI programming since the GUI itself. Using Interface Builder you lay out an interface, which is stored in binary resource files that will stay with the application from conception through deployment. Interface Builder connects interface elements to code “outlets,” and is capable of some skeletal code generation (as a convenience).
Anyone who’s used this tool knows it is the best method available to design a GUI. It doesn’t matter if it’s a simple interface you don’t care about or a complicated one that must be perfect: Interface Builder will give you better results in less time.
So I was a little surprised to see some usually-right folks championing the current Swing approach, talking about “flexibility” and chasing XML red herrings. What? Imagine the world of desktop applications with Mac (Cocoa) apps at one pole and Swing apps at the other. Need it be said which pole has the best interfaces and which has the worst?
It’s easy to be distracted by all the kludgy interface generators some platforms may have had, but a tool that tries to output Java code which arranges a Swing interface is not a resource-based API—it’s an example of why we need resource based APIs. They aren’t about cheating, or being too dumb to write UI code; they’re about being smart and putting reams of interface data into a resource file instead of program code.
Not that I have anything against plain-coded Swing layouts. For programming students, they’re straightforward and easy to throw together, an small step up from System.out.println. But for better application interfaces, it’s time to wake up and smell the Cocoa.
Wicket templates are interface resources
There’s a healthy parallel between resource-mapped GUIs and Web component templating systems like Wicket. That’s only natural, since Wicket is inspired by Tapestry, which is inspired by NeXT’s WebObjects. (We love WebObjects like a grandfather around here.) They all go back to AppKit.
In traditional Web programing the graphical interface is determined by program code that’s interspersed with the layout. It’s an inside-out draw function, which isn’t half bad except your application has no state outside of a few global variables (session objects) and strings you can manually pass and respond to in its event loop (request parameters). It’s not that this method fails to use resources with its graphical API; it’s that it has no graphical API in the first place.
But in Wicket the HTML template only determines the layout for components that live in the program code, just as resource files denote at what pixel a button should draw itself in Cocoa. It’s simple, elegant, and precise once you’re used to it, and you’d no more want to go back to the old way than a Cocoa programmer would switch to Swing. The only downside is its appetite for memory, a familial trait going back to NeXTstep’s outrageous (at the time) 16MB minimum.
Descendant graphical APIs of NeXTstep’s AppKit like Cocoa, .NET’s, and GTK# have slowly grown to dominate good desktop application programming. The same shift will eventually happen on the Web: session-stored components bound to HTML templates will overtake request-structured programming. In letting go of WebObjects Apple has given up on “their” idea too soon. Or perhaps the company is writing a WebObjects do-over with their new BFF Ruby.
And if that happens, well guys, it’s been fun!