The Java Look-and-Feel Debate

Java Swing comes with “pluggable look-and-feel technology”, which essentially boils down to the fact that interfaces can be “skinned” (although this is simplifying a tad) and is therefore, extremely flexible. By default, Java ships with a cross-platform look-and-feel (LAF), which means your apps can look consistent across all platforms, or LAFs that mimic the look of a specific platform, say Windows, for example. However, one of the chief complaints of Java desktop applications is its “look”. It basically stems from two issues:

  1. The default cross-platform LAF is “ugly”.
  2. The platform specific LAFs lack fidelity, i.e., they’re not convincingly native.

To be honest, they have a point! That’s not to say that there aren’t many devs (and users) out there who are happy with the LAFs Java ships, but there is work to be done. However, this isn’t the end of the story. Java GUIs can be made to look great. Also, is the issue of platform fidelity really as big an issue as many developers think?

Native look and feels

There are many Java developers who program with only the Windows platform in mind. They often feel disappointed that the Windows LAF bundled with Java doesn’t do an adequate job of looking like a Windows application. However, does this really matter? Let’s look at Microsoft software for example. Take Microsoft Office, Microsoft Media Player and Microsoft Messenger. Three extremely popular pieces of software for Windows, written by Microsoft. Yet, the irony here is that MS themselves have taken great effort to deviate away from the normal Windows look (and from a intra-MS perspective, their own products also deviate from each other, where Office looks different to Media Player, which looks different to Messenger, and so on). And they aren’t the only ones.

Screenshot showing MS Office, Media Player and Messenger. All of which deviate from the Windows look and feel.

I queried Romain Guy about this issue. He’s an experienced developer and commentator on UI design, and recently started an internship at Sun working on LAFs, (NB all views expressed here are his own, and not of his employer!):

“These LAFs should have helped delivering a better desktop experience. Unfortunately they completely failed, mainly on Windows. Since Swing does not rely on any native widgets, LAF developers need to recreate them all by themselves. And it is very hard to duplicate the look and behaviour of a widget when you don’t have access to its source code. Windows LAFs have always been awkward: they almost look and feel like Windows, but not exactly. A lot of people protested against that. Funnily, they are mainly Windows developers/users. Linux and Solaris users, for instance, are used to seeing mixed toolkits on the screen. You can launch The GIMP and its GTK UI, Mozilla and its very own look and feel, KMail and its QT UI, etc. on the same desktop and nobody will ever complain about it. The Aqua look and feel for MacOS X is quite good so there aren’t so many complaints (the LAF has its quirks and there is a project, Quaqua, which addresses these issues).

“Now, Windows folks are just manic about this problem. I sure like to see the efforts of the WinLAF guys who address the Windows LAF issues, but I have a lukewarm opinion about this. See, I never liked Java’s Windows LAF precisely because it looks awkward. What’s the big deal? I used other look and feels instead. Now, a lot of people will tell you that it is a bad idea because your application would then not look like a native one. So what? I won’t use the well-debated argument of Winamp and iTunes for Windows, but I will rather use most common examples. Microsoft keeps changing the look of Office, does anyone complain? WinForms.NET widgets don’t look exactly like the widget we’re used to see, does anyone care? Delphi has brought us a lot of odd-looking components (like the ugly green-ticked Ok button) for years and nobody cares. Even Firefox and Thunderbird don’t look totally native. Oh, and what about Photoshop? The list goes on. I’m staring at my Windows taskbar right now and out of 7 launched applications, there are 6 not looking totally (or not at all) native. And Winamp isn’t even started (neither is iTunes).

“Tell me why this should be different for Java?! Worse, it is the developers who are actually complaining about that. Not the users. Don’t misunderstand, I would love having a perfect or close-to-perfect Windows look and feel, but as far as I’m concerned, it’s not that a big deal.”

Some interesting points here. Why is there so much fear from developers that Windows users won’t cope with Java LAFs, when companies like Microsoft itself disprove this? As mentioned, Linux users are less concerned by this issue because they typically use a myriad of applications which may use different UI toolkits. Some may argue that Linux users tend to be more computer savvy, and thus are less worried about differences in aesthetics. It’s the less experienced users who are thrown on seeing alternative looks (regardless if it’s an improvement or not) as unfamiliar and therefore a Bad Thing.

For Windows at least, there is the WinLAF project which provides the most consistent LAF to the Windows platform as a library that can be easily employed by Java applications. Then there’s always SWT, which uses native widgets of a given platform, but that’s a different kettle of fish to Swing and beyond the scope of this article.

Ugly look and feels

I think this is the crux of Java’s reputation on the desktop. I personally do not think that the lack of fidelity is that important. I simply think that people feel Swing is ugly – at least relatively speaking. Romain (candidly) sums up his feelings here:

“… Let’s be clear, Java’s default look and feels suck. Really. I never used the native ones because I always found them worse that the known-to-be-ugly-Metal one. Things have become a little better with the introduction of the Windows XP look and feel. It doesn’t suck, it is just awful :)”

But does this really matter? Don’t forget, good UI is much more than aesthetics, it’s about making the user able to perform a task efficiently. Romain elucidates,

“To be honest I’m very sensitive to GUI aesthetics. I could even prefer an application over another because it looks better, even though it is worse feature-wise. In fact, aesthetics are not that important in a GUI. Ergonomics are. A nice-looking GUI can help you appeal to potential users but it otherwise it doesn’t really matter. Now, it greatly depends on what kind of application you are referring to. Applications used 8 hours a day by people who need to input kilometres of data don’t need to be eye-candy, they need to drive the user efficiently. That means an eye-candy GUI can be as bad as an ugly one. Just imagine using a word processor with any Winamp skin, would you be able to use it all day long? I don’t think so.”

Now, I agree in many respects with Romain here because I too like a good looking application – it simply has greater appeal; it gives a good first impression and makes you feel comfortable. In today’s IT world, I think users’ expectations are higher in this respect, and so expect something easy on the eye. So, will we ever have good looking Java applications? Well, yes, we already do!

The solution here is quite simple, use a different LAF! Because of the pluggable LAF facilities in Swing, it is possible to use third-party LAFs instead. Of course, some are commercial offerings, others are free. Possibly the best known freely available LAFs are those released by Karsten Lentzsch called JGoodies Looks. Let’s look at a sample Swing application using the old Metal and the new Ocean cross-platform LAFs.

Screenshot of a Swing application using Java's old Metal look-and-feel.
Screenshot of a Swing application using Java's Ocean look-and-feel, which should be an improvement over Metal to most viewers.

Ocean is an improvement, that’s for sure. Now, let’s see what happens when we use the Plastic LAF:

Screenshot of a Swing application using Platic look-and-feel, which should be more appealing to most viewers.

Now we have a perfectly pleasing LAF for any platform. JLooks also provides a themes mechanism that allows you to specify different colour schemes. By default, it tried to match the desktop colours. Also, it doesn’t take very much effort to get your Java application to look like this. LAFs can be set in the program code directly with a couple of lines of code. Alternatively, you can actually specify as a command-line option, although it does require you having the appropriate LAF classes that you want to use (if third party).


Truthfully, the lack of anti-aliased fonts in Swing mean that it still stands out like a sore thumb. Yet, there is support – it’s just not enabled by default! This is a funny issue because the underlying graphics framework, Java2D, which actually draws the Swing components has supported anti-aliased fonts for years, although work is in progress to enhance this for better sub-pixel support to improve text display on LCDs. As far as I can tell, the reason why it’s not enabled for Swing components by default is mainly for legacy reasons, as Romain pointed out to me:

“Anti-aliased text does not have the same size as non-AA text and that can break layouts and legacy apps.”

There are many, including Karsten and Romain, who believe that because the fonts used in GUIs are typically small, e.g., ~8-10pt, anti-aliasing can actually make text more difficult to read, and therefore only support the idea of anti-aliasing for larger sizes. There is some truth to this, but I think there is a certain amount of subjectivity too, and so I personally think it better to make it simple to enable/disable anti-aliased text as necessary.

Unfortunately, this hasn’t been simple. The old way required you to sub-class each component you wished to be anti-aliased and override the paint() method. This is clearly an inconvenient approach, although, the SmoothMetal project did just this and extended Java’s Metal LAF. There is another approach used by the Wrap LAF project that allows you to achieve global anti-aliased text by adding a wrapper around the bundled LAFs. As of Java 1.5, an undocumented class contained a way of setting each component to enable anti-aliased text. Better, but still required doing for each component you used, i.e., not global. The only global way (without external libraries) is also in Java 1.5 and that is an undocumented Swing property called “swing.aatext”. Set this to equal ‘true’ (and this can be done from the command-line when you launch an app) and all Swing components will be anti-aliased. It’s worth noting that Swing lead Scott Violet has said, “swing.aatext is not a documented or supported property. It’s meant for internal testing and may go away at any point.” Of course, he said in another post, “While it may go away it’ll be
replaced by something better :)”

In the meantime, it’ll do just fine! Here’s our sample app again, with anti-aliased fonts enabled.

Screenshot of a Swing application using Platic look-and-feel and with anti-aliased text.

Synth: the future of LAFs?

Creating your own LAFs requires a lot of knowledge about Swing, and is very programming intensive. Synth is a new look-and-feel that shipped with Java 1.5. It’s still pretty new and documentation is not comprehensive on this yet. Here’s Romain on Synth:

“The Synth look and feel is a generic look and feel, a kind of skins-engine. Its purpose is to let you create a whole look and feel only with an XML files and pictures. It is much simpler than creating a “real” look and feel which is a very complex and tedious task. And it actually allows you to create real look and feels. In Java 1.5, the GTK look and feel is Synth based. Unfortunately, Synth lacks documentation and examples but this issue will eventually be addressed in the future. Also, Synth might unfortunately require some programming work. Due to the nature of the Synth resources, XML files, you’re not free to do everything you want. When something’s missing, you have to crank out some code.”

This approach does look interesting, as it reduces considerably the burden required to get a LAF up-and-running, and is more analogous to skinnable applications like Winamp. There are of course performance issues to think about: a GUI consisting of images could well require additional resources, memory wise, although, with the improved graphics pipeline in the forthcoming Java release, this may not be an issue. A good example of a Synth-based LAF is Synthetica.

Screenshot of the Synthetica look-and-feel demonstrating Synth.


In conclusion, I think it’s fair to say that the bundled LAFs in Java are getting better, but still not pleasing to the majority. I have no doubt that the Java team is working hard on this. However, whilst there is room for improvement, I think this is a good time for many developers to reflect think about whether they really need true platform fidelity, when there are other perfectly decent third-party LAFs available. They will look different, but, so do many applications!

The “ugly” Java is something of a myth nowadays. Whilst Swing doesn’t exactly shine aesthetically by default, there’s not a lot of effort required to plug in a good looking LAF, and with Synth we can expect more LAFs to appear (and hopefully some will be decent!) There are plenty of Java applications that demonstrate how great Swing can look, Xerto’s Imagery is possibly my favourite example at the moment, although the JIDE products are pretty impressive. Also, Javootoo maintains a list of free and commercial LAFs.

About the author:
Andrew Roberts is a computer science graduate from the University of Leeds, UK. He remained at Leeds to study further towards a PhD in Natural Language Processing. He has been using Linux for almost 8 years, and Java has been his language of choice for advanced language processing and machine learning during the last three years.

If you would like to see your thoughts or experiences with technology published, please consider writing an article for OSNews.


  1. 2005-05-19 8:02 pm
  2. 2005-05-19 8:07 pm
  3. 2005-05-19 8:09 pm
  4. 2005-05-19 8:11 pm
  5. 2005-05-19 8:12 pm
  6. 2005-05-19 8:13 pm
  7. 2005-05-19 8:24 pm
  8. 2005-05-19 8:24 pm
  9. 2005-05-19 8:30 pm
  10. 2005-05-19 8:33 pm
  11. 2005-05-19 8:35 pm
  12. 2005-05-19 8:36 pm
  13. 2005-05-19 8:40 pm
  14. 2005-05-19 8:44 pm
  15. 2005-05-19 8:57 pm
  16. 2005-05-19 8:59 pm
  17. 2005-05-19 9:00 pm
  18. 2005-05-19 9:12 pm
  19. 2005-05-19 9:16 pm
  20. 2005-05-19 9:18 pm
  21. 2005-05-19 9:23 pm
  22. 2005-05-19 9:30 pm
  23. 2005-05-19 9:33 pm
  24. 2005-05-19 9:38 pm
  25. 2005-05-19 9:39 pm
  26. 2005-05-19 9:42 pm
  27. 2005-05-19 9:44 pm
  28. 2005-05-19 10:13 pm
  29. 2005-05-19 10:37 pm
  30. 2005-05-19 10:52 pm
  31. 2005-05-19 11:00 pm
  32. 2005-05-19 11:51 pm
  33. 2005-05-19 11:51 pm
  34. 2005-05-20 12:02 am
  35. 2005-05-20 1:03 am
  36. 2005-05-20 1:45 am
  37. 2005-05-20 2:12 am
  38. 2005-05-20 2:50 am
  39. 2005-05-20 4:24 am
  40. 2005-05-20 4:27 am
  41. 2005-05-20 4:30 am
  42. 2005-05-20 5:18 am
  43. 2005-05-20 5:40 am
  44. 2005-05-20 5:47 am
  45. 2005-05-20 5:58 am
  46. 2005-05-20 9:23 am
  47. 2005-05-20 9:23 am
  48. 2005-05-20 9:33 am
  49. 2005-05-20 10:12 am
  50. 2005-05-20 10:51 am
  51. 2005-05-20 11:08 am
  52. 2005-05-20 11:14 am
  53. 2005-05-20 11:21 am
  54. 2005-05-20 11:41 am
  55. 2005-05-20 12:16 pm
  56. 2005-05-20 12:19 pm
  57. 2005-05-20 12:41 pm
  58. 2005-05-20 1:02 pm
  59. 2005-05-20 1:08 pm
  60. 2005-05-20 1:34 pm
  61. 2005-05-20 2:26 pm
  62. 2005-05-20 2:32 pm
  63. 2005-05-20 2:32 pm
  64. 2005-05-20 2:36 pm
  65. 2005-05-20 2:48 pm
  66. 2005-05-20 4:49 pm
  67. 2005-05-20 10:53 pm
  68. 2005-05-20 11:11 pm
  69. 2005-05-20 11:25 pm
  70. 2005-05-20 11:50 pm
  71. 2005-05-20 11:52 pm
  72. 2005-05-21 12:10 am
  73. 2005-05-21 12:17 am
  74. 2005-05-21 2:04 am
  75. 2005-05-21 7:21 am
  76. 2005-05-21 8:55 am
  77. 2005-05-21 3:07 pm
  78. 2005-05-21 4:31 pm
  79. 2005-05-21 4:34 pm
  80. 2005-05-21 6:03 pm
  81. 2005-05-21 8:32 pm
  82. 2005-05-21 9:03 pm
  83. 2005-05-22 7:05 am
  84. 2005-05-22 8:05 am
  85. 2005-05-22 8:21 am
  86. 2005-05-22 8:35 am
  87. 2005-05-22 11:02 am
  88. 2005-05-22 2:54 pm