Programming Konfabulator Widgets

Balazs Fejes


Table of Contents

The downloads you'll need
How does it work?
Your own widget
Packaging and Publishing

Abstract

With the recent acquisition of the Konfabulator application, Yahoo! released its Yahoo Widgets package, which enables cross-platform (Mac OS X and Windows XP) development of dynamic, simple, and visually pleasing mini desktop applications. This tutorial will show you how to build these "widgets" with JavaScript and XML.

The downloads you'll need

Currently Konfabulator can be downloaded from konfabulator.com as well as widgets.yahoo.com. The Konfabulator site contains a developers' section called Workshop. Here you can find the reference guide, a simple tutorial, and a Photoshop template, as well as some other tools.

For the JavaScript language, it's a good idea to download a reference guide as well, the Mozilla project currently hosts an old Netscape reference, which is perfectly adequate for the JavaScript engine contained in Konfabulator.

Here is the current URL:

http://devedge-temp.mozilla.org/library/manuals/2000/javascript/1.5/reference/

There's no need for any compiler, or any other development tool, although it's useful to have an editor which can do syntax highlighting on both XML and JavaScript. I use the free SciTE editor, which fits the bill.

How does it work?

Here's what the Konfabulator web page says about the product:

Konfabulator is a JavaScript runtime engine for Windows and Mac OS X that lets you run little files called Widgets that can do pretty much whatever you want them to. Widgets can be alarm clocks, calculators, can tell you your WiFi signal strength, will fetch the latest stock quotes for your preferred symbols, and even give your current local weather.

When you install the product, you'll be able to run the widgets, either as part of your normal desktop (as opaque topmost windows, or normal application windows), or you can place them exclusively on a sort of second desktop (called Konsposé), which can be switched on and off with a hotkey. The "Konsposé" mode is my favourite, as I can get these widgets out of view when not needed, and I can quickly pull them to front when I want to use any of them. Each widget is actually a separate process, which runs its own interpreter instance.

Figure 1. Konsposé view

Konsposé view

Does it make sense to use this tool? The need for these mini applications is certainly questionable - after all, I am able to get the information displayed within them from various desktop applications or websites. In my opinion, the centralized access, and the attractive visuals alone are worth the memory footprint. We don't need plants in the office, and we don't need a personal coffee mug in the workplace - however having them makes our environment more bearable and colorful, and they add a personal touch to the otherwise gray environment we're spending too much time in.

Each widget is packaged separately. There's no executable file for the widget, the interpreter itself loads up the XML document describing the widget, and all the included JavaScript files and other resources. The widgets can be packaged in two ways - the Mac OS way is basically a directory with a .widget extension, which is treated as a single executable by the OS. Because there's no such concept in Windows, the widget directory must be packed in a zip file, and the .zip extension should be renamed to .widget. It's useful that during the development, even in Windows there's no need to pack the zip file, the actual widget description XML file can be run directly from within the folder.

Your own widget

What sort of functionality is best delivered as a widget? In my opinion, these are some of the key attibutes of a widget (as opposed to a fully functional desktop application or webpage):

  • The widgets should do one specific thing instead of having multiple functional modules hosted within the application - if the user needs to navigate within the application a lot, the whole quick on-and-off aspect of the widget and the hosting Konsposé view is lost

  • The user input should be minimal. The environment has rich presentation functionality, but there are no pre-built form based components to deal with radio buttons, dropdown lists, validated, complex user inputs. A normal desktop or web based application has a richer suite of existing input controls.

  • The widget should display a limited amount of information, especially textual information. The desktop space is limited, and a large widget looks out of place between the small, graphic-heavy widgets. A more useful approach is just to highlight the key elements of whatever information is available for the particular functionality within the widget, preferably with images, not just words, and to open up the full application or web page on demand when the user wants to dig in.

Once you decided the functionality of the widget, the actual implementation is straight forward, with a very simple programming model.

To have your own widget, first you need to create a new directory with the widget's name (for example, HelloWorld.widget). Below this root directory level, there should be a Contents directory.

Figure 2. Folder structure

Folder structure

The key resource in the widget's Contents directory is the actual widget definition file, which should have a .kon extension (example: HelloWorld.kon). This .kon file is an XML document, so it's a good idea to configure your editor to treat .kon files as XML documents.

Unfortunately there's no DTD or XSD for the XML format. There's a message on the support forum where the developers note that they do intend to deliver this later on. I guess the ownership of Yahoo! will also move the platform into this more strict direction, for example to reduce support problems for widget writers.

Each .kon file is somewhat like a HTML page. There's an empty canvas for your widget, but it's fully transparent unlike the white background of a browser page. Each file contains one widget. Each widget can contain windows drawn onto this transparent canvas.

Figure 3. Head of a .kon file

Head of a .kon file

The widget must be placed on the desktop using absolute positioning in pixels. In general this pixel-based positioning and sizing is true for all the components of the widget - I guess resizing could be implemented in Javascript, but it is not a feature of the Konfabulator environment. When the main Widget window has been defined, the various components can be laid out on top of the window using pixel positioning. By default, the window is transparent, and usually widget writers place background images (typically not just rectangular shapes) into these windows. You can use all the usual image formats, like JPG, PNG and GIF images. I tend to use XML comments to separate segments of these widgets, as a long flat list of components could be difficult to navigate.

The section above defines an input box (the Konfabulator type is textarea) in the window. The attributes of the component are defined using CSS-like attributes, but the engine itself does not support CSS-like separation of components and style attributes, you have to define colors, fonts and style for each element separately. It'd be great to have support for a separate CSS file, or at least reusable CSS class-like style definitions, as it'd make styling easier and cleaner. Currently it takes a lot of copy and paste to change the look of the widget.

For the actual layout and position mechanisms, I recommend to read the The Beginning Widget Writer's Guide.

Within each component instance description, and also globally for the widget itself, you can define event handlers. The Konfabulator widget itself is event-driven, you can trigger JavaScript functions based on user interface events, like mouse or keyboard events, or you can define timers to trigger functionality.

The general flow of a widget execution is the following:

Figure 4. Widget execution sequence diagram

Widget execution sequence diagram

The actual JavaScript functions can be either contained within the .kon file, or they can be referenced from external JavaScript files. I do prefer to use external files, as then my editor can syntax-highlight them properly, and at least there's a little separation between layout and code. The logic itself in a typical widget tends to fall into two main categories:

  • The widget retrieves and presents live data from a local system or a local application (CPU load, current iTunes playlist for example). In this case, the JavasScript code executes a system call, or executes a command through an application's API interface. A runCommandinBg() JavaScript method enables this to be executed in an asynchronous manner, not blocking the main widget thread. To enable more elaborate cross-platform widget implementations, there's a large set of Unix commands installed with the Windows version.

  • The widget retrieves live data from the Internet, using a HTTP request, parsing and displaying the response in a graphically rich form. As far as I was able to see, there's no XML parser within the Konfabulator JavaScript API, so typically the returned HTML pages or XML response is parsed using string mungling code. The stock ticker widget example widget uses a JavaScript library called xmldom.js, which is a good candidate for reuse for any XML HTTP based interaction, presenting a DOM-like object interface to the parsed XML document.

Figure 5. Last section of the .kon file

Last section of the .kon file

The last section of the widget definition file describes the various configurable properties of the application. The preferences panel is the available for each widget with some default attributes. Additional attributes can be added to the main preferences panel, or custom tabs can be added to contain more structured preferences. There's no extensive persistency framework included with Konfabulator, however these attributes are automatically persisted in the registry.

Packaging and Publishing

After completing your custom widget, you can package it (following the detailed instructions in the Konfabulator documentation), and publish it in the Widget Gallery hosted by Konfabulator/Yahoo. There's a widget available which prepares the zip archives, but I couldn't resist my "enterprise development" "repeatable automated build" tendencies, and I've created a batch build file, which uses an XML parser to check if the .kon file is well-formed, then zips it with the free InfoZip tool.

@ECHO OFF 
set WIDGET_NAME=FXHistory 
 
set INFOZIP_PATH=c:\work\zip 
set XERCES_PATH=c:\work\xerces 
 
%XERCES_PATH%\PParse .\%WIDGET_NAME%.widget\Contents\%WIDGET_NAME%.kon 
 
IF ERRORLEVEL 1 GOTO ValidationError 
%INFOZIP_PATH%\zip build\%WIDGET_NAME%.widget -r .\%WIDGET_NAME%.widget 
GOTO End 
 
:ValidationError 
@ECHO Validation Error 
 
:End 
@ECHO Build finished

With my predominantly programmer background, I have found Konfabulator development somewhat orthogonal to my way of development. I think the target audience is more on the side of JavaScript-capable Web Designers rather than code-oriented programmers. Nevertheless it's a nice and free application to make our boring Windows desktops more engaging and responsive, and widgets are a nice way to code quick and frequently used mini apps.