WARNING: This blog contains random thoughts on technology, software engineering, and general all-round nerdery. Read at your own risk. Nerd is contagious.

Friday, April 06, 2007

Respecting your OS Look & Feel

I've always said that any self-respecting UI presentation runtime should *always* be able to honor the host operating system's look & feel. I think it was Java's horrible "cross platform look & feel" that really burned this opinion into my soul.

Eventually, even Java relented and there is now a getSystemLookAndFeel() function to support looking like your favorite operating system. Still, this support lacks in many ways, not taking advantage of XP / Vista's "themeing" engine.

XUL has largely succeeded in getting Firefox, Thunderbird et. al. to look like they are native applications, but XUL isn't without it's own issues. Rather than rely on straight-up win32 or .NET libraries, how can you make your UI platform support the operating system?

I've set out to enable Boxely to leverage its operating system look & feel and deliver a new theme for all the base gadgets. Ok, so Boxely isn't cross-plaform (yet ;)), but given all the flavors of windows themes, we can't just fake the look.

So here's what Boxely currently supports from the operating system:

It can use the GetSysColor() call in win32, to get the reported "theme" colors from Windows. This is a good way to at least keep from leaving the OS's color palette. But that can't draw complex shapes and gradients. How about drawing my checkbox for me?

For that we have support for a "OSTheme(element, part, state)" type of fill. This leverages the DrawThemeBackground() function available in XP. To support Window 98 and when Windows is using the classic theme (the theme manager is no longer available in this situation, just like 98/Me), our code will fall back on DrawFrameControl() from back in the day, and even resorting to hardcore manual drawing to recreate the old-skool Windows look.

Starting off, I noticed that text fields are ignored in Classic theme because they're not supported by DrawFrameControl, so I went ahead and added support to fall back on my manually drawn text fields.

We haven't implemented everything possible in DrawThemeBackground(), so I set out to finish up the list. As I added some new parts and states, some of them worked, some of them didn't. I thought it was my code, but then I found the useful ThemeExplorer application, and found out that even though Microsoft has this API, the default Luna theme doesn't even implement all that it says it will! Column header drop down arrows don't even show up (Interestingly, they show in Vista, but even Vista's theme is not fully rounded out).

I'm not sure what to do at this point. Sure, I could hack together something that kinda-sorta looks like a Windows UI element using only GetSysColor(), but I wish Microsoft would have come through here. How can you blame them I suppose; they still haven't figured out UI for themselves yet.


Post a Comment

<< Home