UI Markup Using BXML

The user interface of a Pivot application is often defined using an XML markup language called BXML ("Bean XML"). BXML is effectively a shorthand for instantiating and configuring Java class instances. Though it can be used to declaratively construct any type of Java object hierarchy, it is most often used to define the structure of an application's user interface - the hierarchical structure of an XML document closely parallels the structure of the application's component hierarchy, which makes it easy to visualize the resulting output.

In general, XML elements in BXML refer either to class instances or properties of class instances. Any element that begins with a capital letter represents a class instance, and elements beginning with lowercase letters represent properties. The exception is elements that use the "bxml" namespace prefix, which represent processing directives to the BXML serializer. Similarly, XML attributes generally represent properties, with the exception of attributes that begin with a "bxml" prefix, which contain processing information used by the serializer.


The following is a snippet of code taken from stock_tracker_window.bxml, the BXML file that defines the main window of the Stock Tracker application:

            <stocktracker:StockTrackerWindow title="%stockTracker" maximized="true"
                <TablePane styles="{padding:8, horizontalSpacing:6, verticalSpacing:6}">
                        <TablePane.Column width="1*" />

                    <TablePane.Row height="-1">
                        <Label text="%stockTracker"
                            styles="{font:{size:14, bold:true}, verticalAlignment:'center'}" />

                    <TablePane.Row height="1*">
                        <SplitPane splitRatio="0.4">

                                <Border styles="{padding:6, color:10}">
                                    <bxml:include bxml:id="detailPane" src="detail_pane.bxml"/>

                    <TablePane.Row height="-1">
                        <BoxPane styles="{horizontalAlignment:'left', verticalAlignment:'center'}">
                            <Label text="%symbol" styles="{font:{bold:true}}" />
                            <TextInput bxml:id="symbolTextInput" textSize="10"
                                maximumLength="8" />

The root node of stock_tracker_window.bxml is a stocktracker:StockTrackerWindow element. This element corresponds to an instance of org.apache.pivot.tutorials.stocktracker.StockTrackerWindow. In BXML, XML namespaces are used to associate a class element with a Java package. In this case, "stocktracker" is mapped to org.apache.pivot.tutorials.stocktracker, and "content" is mapped to org.apache.pivot.wtk.content; the default namespace is mapped to org.apache.pivot.wtk, the Java package that contains most of Pivot's common components. The file also declares the "bxml", which is specific to the serializer.

StockTrackerWindow is an application-specific class that extends the base org.apache.pivot.wtk.Window class. Windows are the primary entry point into a Pivot user interface. Windows are always direct descendants of the "display" (an instance of org.apache.pivot.wtk.Display that is created by the platform). An application can open any number of windows on the display, though many applications will use a single primary window and a number of secondary windows (for example, dialogs, sheets, menu popups, or tooltips).

The Bindable Interface

StockTrackerWindow implements the org.apache.pivot.beans.Bindable interface. This interface allows developers to easily map elements declared with a bxml:id attribute to Java member variables. For example, StockTrackerWindow declares the following member variables:

            @BXML private TableView stocksTableView = null;
            @BXML private TextInput symbolTextInput = null;
            @BXML private Button addSymbolButton = null;
            @BXML private Button removeSymbolsButton = null;
            @BXML private BoxPane detailPane = null;
            @BXML private Label lastUpdateLabel = null;
            @BXML private Button yahooFinanceButton = null;

Because StockTrackerWindow implements Bindable, these member variables are automatically populated with the corresponding values declared in the BXML file. For example, the object with ID "stocksTableView" in the BXML file will be assigned to the stocksTableView member variable, and so on.

Bindable defines a single method, initialize(), that is called when the root element has been fully loaded and the bound values have been processed. This allows the bound class to perform any required initialization (generally event registration, discussed in more detail in the Event Handling section).

Attribute Resolution and Includes

The BXML snippet above also illustrates a couple other important aspects of BXML markup: resource resolution and includes. Resource resolution allows a developer to insert "tags" in the markup that will be replaced at load time with a localized equivalent. This makes it very easy to build internationalized applications in Pivot. Any attribute value that begins with a "%" character is considered a resource key, and the value for the attribute is obtained from a resource bundle associated with the BXML file. This is discussed in more detail in the Localization section.

BXML also supports two other attribute resolution operators: "@" and "$". The "at" symbol is used to resolve URLs; any attribute value preceded by an "at" symbol is converted to an instance of java.net.URL relative to the current BXML file. This notation is very useful for loading images from a location relative to the current file.

The dollar sign is a "variable dereference" operator. Though it isn't shown in this example, it is possible to embed script code in a BXML file using the <bxml:script> tag. Any JVM-capable scripting language is supported, including JavaScript, Groovy, and Clojure, among others. Any attribute value preceded by a dollar sign is resolved to an instance of a script variable declared within the page. This allows developers to define variables in script and then easily use them as initialization parameters for class instances declared as elements. Script code can also refer to any page elements identified via a bxml:id attribute as globally scoped page level variables.

Includes allow a developer to embed content defined in an external BXML file as if it was defined in the source file itself. This is useful for partitioning content into manageable pieces (for example, when working on large applications or with multiple developers, or when defining reusable content templates). The detail pane in the Stock Tracker application is defined in an include, detail_pane.bxml. This file is included into the main window via the <bxml:include> tag.

Next: Event Handling