Java MEallows us to write applications that are, generally speaking, portable across a wide range of small devices that support the platform. While the basic functionalities usually work well on all supported devices, the area that does pose problems for developers is the user interface. Native implementations of
javax.microedition.lcdui -- the primary API for UIs in Java ME -- differ so widely from one device to another that maintaining a device independent and uniform look and feel is virtually impossible.
Non-uniform look and feel is not the only reason why developers have been waiting for something better to turn up. The
javax.microedition.lcdui package does not support components and capabilities that can fully satisfy present-day user expectations.
It is in this context that the arrival of Lightweight User Interface Toolkit (LWUIT) is so exciting. LWUIT offers a wide range of widgets for building UIs. While some of these widgets are also available under
lcdui, there are a number of new ones that enable application developers to design UIs that can come very close to their desktop counterparts in terms of visual sophistication. Even the components that are also offered by
lcdui have been functionally enhanced. And LWUIT is not just about new components, either. The API supports a whole range of new functionalities, too -- theming, transitions, and more.
The designers of LWUIT have said that this API has been inspired by and modeled on Swing. This has a number of implications. A significant implication is that the widgets are rendered by the LWUIT code and are not derived from native equivalents. This ensures device independence and visual uniformity.
Adaptation of the Swing architecture also means that the code for drawing a component is well defined and is distinct from code that defines its behavior. So it is possible to replace the rendering code to implement a completely customized look.
In this article, we will look at some of the significant features and functionalities that we have mentioned above. Our overview of LWUIT will discuss the following aspects:
- "Infrastructural" items like
UIManager, and so on.
- Functionalities like themes and transitions.
A simplified version of the hierarchical structure of the widget classes in LWUIT is shown in the figure above, which is adapted from the "Developer's Guide" provided in the LWUIT bundle. As seen here, the base class of the widgets is
Component. We also see that while LWUIT supports familiar
lcdui widgets such as
Label, it also has a number of new ones like
TabbedPane, and so on.
Container and Form
Among the widgets, the
Container is the basic "holder" that can contain other components including other containers. This nesting ability of containers allows complex and elaborate UIs to be built up. The arrangement of components within a container is taken care of by a layout manager.
Form is a container with a Title Bar at the top on which the title of the form can be written and a Menu Bar at the bottom for commands and menu. The space between the two bars is for the content pane, which holds the components to be placed on the form.
TabbedPane lets a number of component groups share the same space. Each group of components has a tab associated with it and the user sees only the group corresponding to the tab that has been selected. The default placement of tabs is at the top of the pane. However, it is possible to position them at the left, right, or bottom of the pane. Figure 2 shows a tabbed pane with the tabs at the top and with the first tab selected.
Dialog is an "always-on-top" component. By default, a dialog is modal -- that is, it blocks the calling thread until it is disposed of. Dialogs can be of one of five types:
Dialogs can be used to convey information to the user at runtime and to collect user feedback. The type of the dialog would normally determine the sound to play when the dialog is displayed. It is possible to add icons to a dialog to graphically indicate the dialog type. Figure 3 shows a simple warning dialog with OKand Cancel commands.
Label and Button
Label is for displaying images and text that cannot be selected and does not interact with the user. A number of alignment possibilities are supported for positioning the label and for positioning the text with respect to the image on the label.
Button class extends
Label. A button has states and it generates an action eventwhen selected and clicked. Like a
Label (which is the superclass for buttons), a
Button can have descriptive text, an image, or both. The three states of a button are:
Rollover: This is normally equivalent to the button being selected or receiving focus.
Pressed: When the button has been clicked or pressed.
Default: When the button is neither selected nor clicked.
A button has two subclasses:
RadioButton has all the functionalities of a button. In addition, a radio button can be added to a
ButtonGroup, which allows it to maintain its selection state exclusively within the group. Within a button group, only one radio button can be in the pressed state at a time. If another radio button is clicked on, the one that was in the pressed state earlier will get deselected. Also note that once a radio button is in the pressed state, clicking on it does not change the state.
CheckBox is similar to a radio button in the sense that it can remember its state if it has been selected by being clicked. However, repetitive clicking on a check box will toggle its state between selected and deselected. Another difference is that a check box cannot be a part of button group.
A number of buttons, radio buttons, and check boxes are shown in Figure 4 below. The screenshot shows that the first two buttons are in the
default state while the third is in the
rollover state. Both the check boxes are shownselected, but only one radio button in each group isselected.
TextArea is a component that displays text that may be editable. The editing is performed using the native system editor, which often opens a new screen. A text area uses the concept of constraints just as the
lcdui does. Figure 5 shows a form with a text area.
List is a very widely used component that presents a number of information items to the user. The items are presented in a single column but each item may contain multiple lines of text and images. The model-view-controllerarchitecture adapted by LWUIT makes it possible to make a list look just the way we want it to. The data structure of a list is represented by the
ListModel interface. So a list is not tied to any specific data structure and can display information from any object that implements this interface. Similarly, the rendering of a list is performed by a class that implements the
ListCellRenderer, thus making it possible to create the kind of look the application developer wants. The library includes default implementations of the above interfaces that make it easy to instantiate a list.
Figure 6 shows a simple list with four items. Compare this with the list shown in Figure 7 and its significantly different appearance. The application behind the screenshot of Figure 7 implements its own renderer to achieve a very polished and attractive look.
ComboBox is a space-saving component that drops down a list when its button is clicked. The user can then select one of the items on the list. As
List, you can use custom models and renderers for combo boxes, too. Figure 8 shows a combo box with a four item drop-down list.
The Underlying Support Elements
LWUIT incorporates a number of "behind the scenes" support elements that make it possible for the functional features to operate. Here we take a look at these elements and see how they work.
Applications often require non-code items; for example, an image used as an icon for a
Label by an application. LWUIT allows such items to be packaged in bundles. A resource bundle is essentially a binary file that can be loaded into a device. An application can have more than one resource file and each such file can contain resource elements of the same or different types. The following types of resource elements are supported:
- Image resources
- Animation resources
- Bitmap fonts
- Localization bundles
Individual resource elements can be extracted by a set of appropriate methods of the
Resources class. The LWUIT bundle has a utility -- the Resource Editor -- for building a resource file. Resource files can also be created by a set of Ant tasks.
LWUIT brings the power of sophisticated layout managers to the design of UIs for small devices. The managers supported are:
These layout managers work just as they do in the context of AWT and Swing. Figure 9 shows an example of
LWUIT provides a very convenient way of defining the appearance of a component at a single point. Each component has a
Style object associated with it, and the attributes related to the look of the component can be set within this object. The attributes are:
When a component is generated, it constructs a default
Style object. The values of the attributes of this object can be changed at runtime to modify the appearance of a component. Setting a theme updates the contents of all
Style objects simultaneously so that all widgets take on the same appearance, as defined by the theme.
Painter interface allows you to draw on the background of a component. A painter can be used to draw a specific pattern on the background of one or a group of components. The LWUIT package provides two classes that implement this interface:
BackgroundPainter: Draws the background of a component based on its style.
PainterChain: Creates a "chain" of painters that can produce a layer effect, with each painter drawing just one element.
An interesting feature of LWUIT is that it manages the appearance of an entire application from a single point. The
UIManager is the class that coordinates the visual aspects of an application. This is a singleton to ensure that there is only one
UIManager object per application. The methods of this class enable it to impose the same look on all components and to localize the UI on the fly.
LookAndFeel is the interface that takes care of all rendering for an application. It is therefore possible to completely customize the appearance of an application by overriding the appropriate methods of this interface. The concrete implementation of
LookAndFeel that comes with the LWUIT package is
DefaultLookAndFeel, and this class controls the actual rendering of the default look. It is possible to plug in a custom implementation of
LookAndFeel by using the
setLookAndFeel method of
A really interesting aspect of LWUIT is that it goes beyond components and offers features that enable us to produce very sophisticated UIs. In this section we look at these features.
Animations and Transitions
The LWUIT library supports the implementation of different modes of transition from one
Form to the next one to be displayed. The basic implementation of such transitions is achieved through the mechanisms provided by the interface
Animation and the classes
Transition3D, which are contained in the
Animation interface defines objects that are animatable. All components are inherently animatable, as they all implement
Animation. However, a component must register itself into its parent form to get animation callbacks that perform the animation tasks and, to stop these callbacks, the component must explicitly deregister itself.
Transition is an abstract class that represents animation from one form into another. Its two concrete subclasses are:
CommonTransitions: Has methods to implement the two common types of transitions, which are
Transition3D: Performs transitions (
Cube, Fly in, and
Rotation) that require device support for 3D graphics and, therefore, do not work properly on all devices.
Motion is a class that implements motion equations. The types of motion that are built-in are
friction. It is possible to implement other varieties of motion by subclassing
A theme defines a uniform look for all visual components in an application. For example, if you want all buttons in your application to have a green background, you can do it by defining an appropriate key-value pair in your theme. A theme file is essentially a list of key-value pairs that define the relevant attributes. The following is a part of a theme file that comes with the LWUIT demo bundle:
Menu.bgColor= 555555 Menu.bgSelectionColor= 555555 Menu.fgColor= ffffff Menu.fgSelectionColor= 99cc00 Scroll.bgColor= 111111 Scroll.bgSelectionColor= 242627 Scroll.fgColor= AAAA00 Scroll.fgSelectionColor= ffffff SoftButton.bgColor= 000000 SoftButton.fgColor= ffffff TextField.bgColor= 242627 TextField.bgSelectionColor= 242627 TextField.fgColor= 99cc00 TextField.fgSelectionColor= ffffff
A theme can be packaged into a resource file. To apply a theme, it must be loaded using the
Resource class. The received hashtable must then be submitted to the
UIManager for necessary action.
As we have already seen, every component has a style associated with it. When a theme is set, the value of an attribute is read from the theme data and the style objects for all components of the corresponding type are updated accordingly. However, there is one exception to this rule: the modification affects only those attributes which have not been manually modified. This feature allows you to apply themes selectively.
Figure 10 shows an example of a theme. The fish at the right-hand bottom corner is animated.
In addition to themes and animations, LWUIT also supports:
- Logging: This is a debugging aid that allows you to log information at runtime. The
com.sun.lwuit.util.Logclass provides methods for logging information into a logfile (created in the root directory), and also for displaying logged information on a
Formand on the console. You can use information saved in the log file through the
- 3D graphics: Supports optional hardware acceleration on some mobile devices to deliver enhanced performance.
On the the Sun Java (TM) Wireless Toolkit, the performance of LWUIT is very slow. This is because of certain architectural issues and, as per the LWUIT "Developer's Guide," the performance problems do not appear on Sprint Wireless Toolkit version 3.2 and higher (which has a different architecture). I haven't tried the Sprint Toolkit, but I loaded the demo application into one of my handsets and it works quite well. This is the first release of LWUIT and with increasing use, it will surely evolve into a UI library to be reckoned with -- the promise is already apparent. It is also going to thrive on the increasingly powerful devices of the future. Java ME UI developers can now look forward to a highly satisfying product to work with for a long time to come.
Figures 2, 3, 4, 7, 9, and 10 are screenshots from the demo applications that are part of the LWUIT download bundle.
- Lightweight User Interface Toolkit (LWUIT) project home
- LWUIT download bundle
- Jonathan Knudsen's LWUIT tutorial