by Rick McMullin
IN THIS CHAPTER
Over the past few years there has been a growing emphasis on application development
using visual programming. Visual programming is the name given to a way of creating
applications that allows the programmer to draw the user interface for the application
on the screen. Once the user interface has been defined, the tool being used generates
the code for all the user interface aspects of the application. Some of the best-known
such tools are Microsoft's Visual Basic and Visual C++, which are visual programming
environments for Microsoft Windows.
This chapter introduces a visual programming tool called ObjectBuilder and also introduces the Object Interface (OI) library that it uses. In this chapter you learn the following:
This chapter also discusses manipulating ObjectBuilder objects and creating applications in ObjectBuilder.
ObjectBuilder is a visual programming tool that was developed by ParcPlace Systems. It gives the programmer a simple way to create graphical user interfaces for X Window applications. ObjectBuilder builds these interfaces from pre-defined objects that are included in the Object Interface (OI) library. The OI library contains components such as menus, buttons, windows, and dialog boxes.
The OI library is a collection of user interface classes. Each element of the OI library is an instance of one of the classes contained in the library.
The OI class library contains many different kinds of user interface objects.
These objects are organized into a class hierarchy in which the classes that are
lower on the hierarchy inherit the behavior of the classes that are higher in the
hierarchy. Table 32.1 lists most of the concrete classes that are in the OI class
library. This table gives you an idea of what the OI class library and the ObjectBuilder
application provide for you.
Table 32.1. OI class library concrete classes.
Class Name | Description |
OI_app_window | The main window for an application. |
OI_box | A box that can contain other objects. |
OI_gauge | A horizontal progress indicator. |
OI_static_text | A text object that does not change. |
OI_menu_cell | An element of a menu. |
OI_scroll_menu | A box with scrollbars that contains menu items. |
OI_menu_box | A box that is used to contain menu items. |
OI_dialog_box | A box that contains controls that are used to interact with the user. |
OI_panned_box | A box that has separate, adjustable viewing panes. |
OI_scroll_box | A box that has scrollbars attached to it. |
OI_scroll_bar | A bar that can be moved up and down or left and right. It is usually attached to a box to make the contents of the box scrollable. |
OI_slider | A control that can be adjusted by moving it to the right or left. |
OI_entry_field | A field that is used to collect user input. |
OI_multi_text | A multiline text editor. |
OI_button_menu | A button that displays a menu when it is activated. |
There are many other user interface classes that are provided by the OI class library. Most of the classes that exist but are not listed in this table are specializations or subclasses of these classes and therefore have similar functions.
Although ObjectBuilder is on your Linux CD-ROM, the default install scripts do not install it onto your system. The ObjectBuilder distribution can be found in the devel directory on your Linux CD-ROM. To install ObjectBuilder on your system, follow the steps for installing software distributions that are outlined in Chapter 3, "Installing Linux."
To create an application using ObjectBuilder, you must first invoke ObjectBuilder. To do this, enter the following command into an Xterm window:
uib <options>
One of the options that can be specified when starting ObjectBuilder is which interaction model you want to use. Interaction models are the names given to the different styles of user interface objects that ObjectBuilder supports. The default is Motif, but if you want to use OPEN LOOK you would type the following command to invoke ObjectBuilder:
uib -openlook
Depending on which interaction model you choose, the mouse buttons act differently.
Table 32.2 defines the mouse buttons under each interaction model.
Table 32.2. Mouse button definitions.
Button | Name | Purpose |
left | Select | Motif--selects objects and menus, operates scrollbars, and activates pull-down menus |
|
|
OPEN LOOK--selects objects and menus and operates |
|
|
scrollbars |
middle | Adjust | Motif--resizes objects and acts as a go to pointer for |
|
|
scrollbars |
|
Drag | OPEN LOOK--resizes objects |
right | Menu | Motif--activates and selects from pop-up menus |
|
Custom | OPEN LOOK--activates and selects from pull-down and pop-up menus |
In addition to specifying the interaction model that you want to use on the command line, you can also specify the application that you want to load into ObjectBuilder. This is done by specifying the application name as an option on the command line. For example, the following command would start ObjectBuilder and load the sample application using the OPEN LOOK interaction model:
uib -openlook sample
After ObjectBuilder is started, its main window comes up on your screen. This window is illustrated in Figure 32.1.
The ObjectBuilder main window allows you to control all aspects of the ObjectBuilder session. There are nine options available from the window: five pull-down menus, three selection options, and one message area. Each of these options is described in detail next.
Figure 32.1. The ObjectBuilder main window.
The File menu contains the standard file-related options available in most visual tools. The File menu is shown in Figure 32.2.
Figure 32.2. The File menu.
Table 32.3
describes each of the options available in the File menu.
Table 32.3. File menu options.
Option | Description |
Clear | Clears the current application and initializes ObjectBuilder to begin a new application. |
Save | Saves the complete application using the current name. If a name has not been assigned to the application, you are prompted for one. |
Save As | Saves the application interface currently being edited via a dialog box. It also allows you to save only the configuration and help files of the application. |
Load | Loads the application specified in the Load dialog box. |
Append Subobject | Inserts the interface object specified in the Append dialog box into the current application. |
Revert to Disk | Discards all edits made during the current session and reloads the last saved version of the application from disk. |
Exit | Exits ObjectBuilder. |
This pull-down menu provides the basic editing features required to build an application. The options are shown in Figure 32.3.
Figure 32.3.The Edit menu.
A description of
each option can be found in Table 32.4.
Table 32.4. Edit menu options.
Option | Description |
Undo | Operates as either a stack of operations (you move backward through operations) or as a toggle (selecting negates the last operation performed and selecting the option again restores it) |
Subclass | Invokes the Subclass editor for any subclassed object in your application |
Help | Invokes the help editor |
Properties | Invokes the properties dialog box |
This menu gives you access to three functions that assist you in building and debugging the application. The View menu is shown in Figure 32.4.
Figure 32.4. The View menu.
The Hidden Objects function provides a menu of all of the hidden objects in your application. Objects are hidden if their initial state is either OI_ACTIVE_NOT_DISPLAYED (this is the case with pop-up or pull-right menus) or OI_NOT_DISPLAYED, meaning the object is not visible at that time. Additionally, the OI_abbr_menu object and all its derived classes are always treated as hidden objects.
When the Hidden Objects function is selected, the Hidden Objects dialog box is displayed, as in Figure 32.5.
Figure 32.5. The Hidden Objects dialog box.
When you click on an object name in the scroll menu, that object is displayed and can then be modified in the same manner as any other object. Clicking on the name a second time hides the object. The HIDE ALL and SHOW ALL buttons can be used to display and hide all objects in one step. If an object is not hidden when the CLOSE/DISMISS button is pressed, then it remains visible. But it is still a hidden object within the application at runtime.
The Status and Error Log function displays the Status Log window that is shown in Figure 32.6.
Figure 32.6. The Status Log window.
In this window you find all error messages and help messages that were issued since the ObjectBuilder session started. Pressing the CLEAR button removes all messages from the log. The CLOSE/DISMISS button closes the Status Log window.
The Simulation Trace function provides a running log of events, including interaction with all register callbacks, generated while ObjectBuilder is in RUN MODE. The Simulation Trace window is shown in Figure 32.7.
Figure 32.7. The Simulation Trace window.
The Filter menu allows you to determine which callback types are displayed. The Print menu allows you to determine which elements of the callback you want to display. You can display any or all of the following:
A palette contains objects that can be used in an application. These objects are a source of new instances of OI objects, user subclasses, and user-created objects. The Palette menu has two options: Palettes and Load. The Palettes option provides a pull-right menu that lists all available palettes. The Palettes menu is shown in Figure 32.8.
Figure 32.8. The Palettes menu.
Table 32.5 describes the purpose of each palette.
Table 32.5. The available palettes.
Palette | Description |
all_OI | Contains all displayable OI objects |
default | For users who can readily identify most objects |
dialog | Contains all dialog boxes |
editor | Contains objects for building custom attribute editors |
minfootprint | Positions all OI objects so the palette occupies the minimum amount of screen space |
novice | Contains icons and labels for all OI objects and is helpful until you are familiar with the objects and how to use them |
terse default | Lists all OI objects by the name found in the OI library |
terse dialog | A small palette listing all dialog box objects by name and icon |
user subclass | Contains user subclass objects |
The Load option of the Palette menu lets you load additional or custom palettes through a dialog box. The Load dialog box is shown in Figure 32.9.
Figure 32.9. The Load dialog box.
ObjectBuilder's Help menu provides a list of help topics that correspond to the chapters of the "Learning ObjectBuilder Guide" distributed by ParcPlace Systems. The Help menu is shown in Figure 32.10.
Figure 32.10. The Help menu.
The Builder Mode option is displayed in the main window as a selection option. You can choose which mode ObjectBuilder should be in. Figure 32.11 shows how the Builder Mode option appears in the main window.
Figure 32.11. The Builder Mode option.
At any time during development, you can change modes. In the Build mode you "build" the front end of the application under development. This is the mode that ObjectBuilder is initially in when it is invoked. In the Run mode, no editing can be done. This is used to test the objects in the application. All of the objects that were created function as they would in the completed application. ObjectBuilder also attaches callback stubs for all callbacks on objects for which callbacks were specified. The callbacks are logged in the Simulation Trace log discussed earlier.
A menu cell in ObjectBuilder is an option available in a menu after it is built. Therefore, menu cells reside within menu objects. When performing an action that could apply to either a menu or a menu cell, you need to tell ObjectBuilder which one you wish to apply the action to. This is done by selecting the appropriate option in the Menu Focus option. An example of when you would need this is if you want to delete a cell from a menu. To do this you would first have to select Cell from the Menu Focus option and then delete the cell. If Menu was selected from the Menu Focus option, the whole menu would be deleted and not just the cell that you wanted. Figure 32.12 shows how the Menu Focus option appears in the main window.
Figure 32.12. The Menu Focus option.
The model selection option allows you to choose which interaction model you want to work in, either OPEN LOOK, OPEN LOOK 3D, or Motif. The Model option is shown in Fig- ure 32.13.
Figure 32.13. The Model option.
When a new model is selected, everything associated to the application being built changes to the new model. The ObjectBuilder windows and menus remain in the model that was selected when ObjectBuilder was invoked. The default model is Motif.
The message area is a line at the bottom of the main window. ObjectBuilder uses the lower-left corner of the message area to display help messages and the lower-right corner to display status messages. The Message area is shown in Figure 32.14.
Figure 32.14. The Message area.
An application is built of three parts: the graphical user interface (GUI), the application code, and the link between the two. This section describes the basic object manipulation techniques required to build an application's GUI.
An object is said to be a child of another object if the child object resides within the parent object. Therefore, if your application has a button within a window then the button is a child of the window and the window is a parent of the button. In ObjectBuilder, objects are parented by dropping other objects into them.
Usually only container objects can be children of the root. These include windows, boxes, dialog boxes, scroll boxes, and paned boxes. Other objects are parented to or are children of the container objects. Most of these restrictions can be overridden using the Any Parent option in the Properties dialog box of the Edit Menu.
A child object can be reparented to another object by using the Object Modification pop-up menu shown in Figure 32.15.
Figure 32.15. The Object Modifi- cation menu.
This menu is displayed by placing the pointer over the object to be reparented and pressing the menu button. Once the Reparent option is selected, the object follows the pointer until you press a mouse button to release the object over the new parent object.
Creating an object is done by choosing an object from one of ObjectBuilder's palettes. To do this, you must first select a palette from the Palettes submenu of the Palette Menu. Now choose an object by clicking on it with the Select mouse button. Drag the mouse until the object is in the desired position in your application window. Release the mouse button to place the object in the window.
To delete an object, place the pointer over the object and press the Menu mouse button. The Object Modification menu, shown in Figure 32.15, is displayed.
In the pull-right menu of the Delete option, there are three suboptions from which
to choose. The function of each is described in Table 32.6.
Table 32.6. Object modification delete options.
Option | Description |
Clear | Removes all children from the selected object. |
Delete | Deletes the selected object and all children of that object. |
Eliminate | Deletes the selected object but not the children. The children are parented to the parent of the original object. |
If the object was just created, you can also remove it by selecting Undo from the Edit menu. To delete a menu cell, first make sure the Menu Focus option is set to Cell. If the last cell of an untitled menu is deleted, then the menu is deleted. With a titled menu, the menu remains if you delete all of the menu cells.
To move an object, simply place the pointer over the object and press the Select button of the mouse. Move the mouse and drag the object to the new location. Release the mouse button and the object is now located in a new position in the application window.
To move a menu cell, select Cell in the Menu Focus option, place the pointer over the cell to be moved, and press the Select mouse button. Now move the cell to the new location and release the mouse button. The cell is located directly below the cell over which it was dropped. To place a cell at the top of a menu, drop it on the menu title.
To resize an object, place the pointer over the object and press the Drag/Adjust mouse button. Drag the outline of the object until the desired size is achieved, then release the mouse button.
To copy an object, place the pointer over the object and press the Menu mouse button to display the Object Modification pop-up menu. Select Copy to create an exact duplicate, or clone, of the object with all its descendants. An outline of the object follows the pointer until you click a mouse button to release the clone and parent it to another object. It is possible to parent the clone to the original object.
An object can be converted to any other visible object derived within the same category. Object categories correspond to the OI class hierarchy discussed at the beginning of this chapter.
There are four categories of objects that are described in Table 32.7.
Table 32.7. Object categories.
Category | Description |
Container | OI_app_window and objects derived from OI_box |
Display and Controller | OI_panner and objects derived from OI_display_1d |
Text | OI_static_text and objects derived from OI_lang_server_input |
Menu | Objects derived from OI_menu |
The first step to creating an application is to invoke ObjectBuilder in a new or empty directory. Once the main window appears, move the window to a convenient area of the screen.
Next, open the Palette menu and select a palette from the Palettes pull-right menu shown in Figure 32.8. The palette window opens, displaying all possible objects for that palette. For beginners, the Novice palette is the simplest to use. The Novice palette window is shown in Figure 32.16.
Figure 32.16. The Novice palette window.
The application window is usually the top-level or root object of an application. Select the application window object and drag it to an empty location on your screen. This window can now be resized to what is appropriate for your application.
You can now select and drag each required object into the application window. Once all the objects needed have been created you can close the Palette window by selecting Close/Dismiss from the Palette window's File menu.
The Attribute Editor allows you to modify specific attributes or resources for each object. To invoke the editor, move the pointer to an object you want to modify and double-click the Select mouse button. An Attribute Editor similar to the one shown in Figure 32.17 is displayed.
Figure 32.17. The Attribute Editor.
The Attribute Editor appears with the name of the object being modified in the title bar. Depending on the object that is to be modified, the Attribute Editor displays different resources.
ObjectBuilder assigns an internal name to all of your objects. If you modify the Object Name resource (which is recommended because the names that ObjectBuilder assigns are not very intuitive) ObjectBuilder still maintains its internal name for the object. This name is displayed in the title bar of the Attribute Editor when you are editing the object.
The attributes that are common to all objects are Category, Object Name, Apply To, and Title. When the Editor appears, the Category is set to default. If the Category is not default, or you want another category, press the abbreviated menu button to display a list of categories from which to choose. The category tells you what the attributes or resources are for. Default is the object as viewed, and callback defines the action that occurs in response to an event for that object.
The Apply To resource lets you choose whether the modifications apply only to that object, to the object and its children, or siblings as well. There are numerous combinations to choose from in this menu.
The Title resource is the title for the window. Modifying this changes what is seen in the title bar of the window.
To ensure that the objects in an application window remain in the correct place relative to their siblings, you must set a layout method for that object. Select the Layout menu from the application window's Attribute Editor and view the layout options, as shown in Figure 32.18.
Figure 32.18. The Layout menu.
Select an appropriate layout, and the objects in the application are moved. After this the objects within the application window can still be moved but that movement is restricted to within the boundaries of their parents.
When modifying resources for menu objects or menu cells, you need to specify whether ObjectBuilder should perform the action on the menu or the menu cell by making a selection in the Menu Focus option of the main window.
The Label Resource is the text that appears in a menu cell. The cbCellAction resource assigns callback functions to the cell.
By selecting the Traverse pull-down menu from the menu bar at the top of the Attribute Editor, you can shift the focus of the editor to a parent, child, or sibling of the present object. This allows you to modify the resources of a child without affecting the resources of the parent. The Traverse menu is shown in Figure 32.19.
If the Attribute Editor is open and you wish to modify the attributes of a different object, place the pointer on the desired object and press the Select mouse button. This causes the editor to display the resources for the selected object.
Because each object has a unique set of resources available to it that are too numerous to mention here, they are explained in the Help function of ObjectBuilder.
Figure 32.19. The Traverse menu.
When you use ObjectBuilder to generate an application, it creates a number of files for you. It is important to understand what each of these files is and what they are used for. The files that are created and their purpose are listed here. Configuration File (appname.cf)--This file contains the hierarchical description of the graphical objects that make up the front end of the application. It also contains the resource definitions and callback information for the objects.
Help File (appname.hp)--This file contains the application's context-sensitive help.
Main Program (appname.C)--This file contains the code to handle the initialization, user interaction startup, and OI cleanup. This file can be edited after it is generated and ObjectBuilder will not overwrite any changes made to it.
Main Header File (appname.H)--This file is included in all ObjectBuilder-generated C++ source code files. It can be edited after it is generated and ObjectBuilder will not overwrite it.
External References Include File (appname_bd.H)--This file contains references to all objects for which you requested user variables.
Binding File (appname_bd.C)--This file contains the object variables, external declarations for all callback stubs, and a binding table that binds the name of the object listed in the configuration file to the object itself.
Callback Stubs File (appname_cb.C)--This file contains fully documented callback stubs generated by ObjectBuilder for all the callbacks according to the specifications you entered in the Attribute Editor. The top portion of the file is declarations and the bottom contains the callback stubs. There is a separator line between the two sections that must not be removed. If you delete a callback, the stub is deleted but you have to remove the declaration yourself. This file can be edited, and ObjectBuilder will not overwrite any changes made.
Makefile--This file provides instructions on how to build the application at runtime. It can be edited and ObjectBuilder will not overwrite the changes made.
Once the application is saved using the Save function from the File menu, the above files are generated and placed in the same directory that ObjectBuilder was originally started from. You can then use any text editor to edit those files that require changes.
Applications created using ObjectBuilder are event driven. This means that code is executed in response to an event. Here are examples of events:
For your application to work you have to create the back end. The back end is the code that tells your application what to do when an event, such as a selection from a menu, occurs. ObjectBuilder refers to this code as a callback.
ObjectBuilder generates the callback stubs file according to the specifications you give in the callback category of the Attribute Editor. Each callback has three parameter entry fields. These fields specify the callback object, function, and argument, going from left to right in the editor. Only the function is mandatory. The Attribute Editor for the callback category of a menu cell is shown in Figure 32.20.
Figure 32.20. The callback category.
The callback object is the object that is used when calling a member function for a specific class. It is good practice to allow runtime resolution of the object needed by a member function. The function can be a member function or a stand-alone function. The arguments can be strings, constants, or pointers to objects. Structures, floating point numbers, and pointers to member functions cannot be passed as arguments. These are the rules for entering arguments:
Each type of callback requires a different set of parameters. The parameters needed for each callback are documented in the "OI Programming Guide" available from ParcPlace Systems.
Once a callback function has been specified and the application is saved, ObjectBuilder updates the binding table in the binding file. This table tells the application which external functions to call when the button is pressed or menu item is selected at runtime. ObjectBuilder generates a function declaration and a callback stub in the callback stubs file. In the configuration file one statement is generated that states the specific callbacks for an object and a second that provides directions for satisfying those callbacks when the application runs.
You must add the C code for the functions to the callback stubs file (appname_cb.C) using any text editor.
Once the callback functions have been written you must compile and link the application to the OI_Library files. First make sure that the makefile can find any include files that are needed, as well as the OI_Library files, by editing the following statements in the makefile. You need to do this only if the include and OI files are not in the same directory as the application.
INC = $$OI_LIB/../../include OILIB = -L$$OI_LIB/../-1OI
The $$ ensures that the environment variable OI_LIB is used to find the libraries and the include files.
Compile and link the application by typing the following command in the directory where the application was saved:
make
When this finishes, you can run the application by typing the application name at the prompt.
If you want to make any changes, simply load the application into ObjectBuilder using the following command:
uib appname
The visual aspect of ObjectBuilder enables you to drag and drop objects and their resources into your application. ObjectBuilder does the rest of your user interface development by generating C code to produce the behavior and appearance of the objects that you put into your application. This saves you a great deal of time because a significant amount of the entire development of an application is spent on the user interface.
ObjectBuilder further helps you by defining the skeleton for the rest of the application. Although you still have to write the core of your application, using ObjectBuilder can save you vast amounts of time. Once you know the basic objects available in the OI library and their hierarchy, creating a GUI or front end for an X Window application using ObjectBuilder is simple.