|
Comments
Did you read today's front page stories & breaking news?
SYS-CON.TV
|
General Java On JavaBeans Customization
On JavaBeans Customization
May. 1, 1999 12:00 AM
JavaBeans, now in its third year, is proving to be a powerful component model. Whether it's the Java e-commerce framework or the Java platform for the enterprise, JavaBeans is at the heart of many new and exciting technologies. The JavaBeans model provides a framework to build, customize, run and deploy Java software components. While there are numerous books and articles on JavaBeans, not many of them deal with the customization aspect of JavaBeans. An object that conforms to the JavaBeans specs is called a JavaBean or, more generally, a bean, which at runtime is like any other object. What distinguishes it from other Java objects is that it can be manipulated with visual builder tools. This process includes customization and connection, which means that you can visually customize beans and connect them to assemble an application. Let's discuss customization using the Pie Chart bean (part of the visualization bean suite developed for my book, The Awesome Power of JavaBeans) shown in Figure 1. If you want to use this bean, you'll probably customize it to suit your application, which may include changing the size and position of the pie as well as the location of the legends. You can customize the bean visually by using a bean builder tool. Once you customize it, you may want to save the configuration for future use by using the Java serialization feature. Sun's BeanBox, which comes with the BDK, is an example of a visual builder tool that allows you to customize, serialize and connect beans. Most of the Java IDEs provide similar tools.
Property Sheets
Introspection How does introspection work? The process first checks the BeanInfo class to obtain a bean's feature (property, method and event) descriptions. If the bean author doesn't provide any information about properties (or other features) in the BeanInfo class, the introspection process uses the low-level reflection API (java.lang.reflect and java.lang.Class) to obtain it. Using these APIs, it probes the bean class to obtain its fields and methods, then deduces a bean's feature descriptions by matching the method signatures with the naming conventions defined by the JavaBeans specs. The naming conventions for properties define the signatures for setter and getter methods. The former sets the property and the latter reads it. Here is a naming convention defined for a simple property:
public void set
public <Property Type> get<PropertyName) {} The following example shows the setter and getter methods for the Graph Color property: public void setGraphColor(Color color){//code } public Color getGraphColor(){// code} The other types of properties, which include indexed and boolean, have similar naming conventions.
Editing Properties To edit a property, each property type needs to be associated with a property editor. For simple properties, a property value can be expressed as a text string. The property editor converts the property value obtained from the bean to a text string so as to display it in the text field. When the user inputs a value in the text field, it converts the inputted text string to the corresponding primitive type. When you start writing real-world beans, you'll realize that Java primitive types aren't always adequate to represent different types of bean attributes. Take the background and foreground colors in the Pie Chart bean, for example. In this case the property type is Color, which is a class in the AWT. You can't enter a color name in the edit field because the text type property editor can't convert a color name to a Color object. What you need is a special property editor that does this conversion. Builder tools often provide custom-written property editors for commonly used properties such as Font and Color. If the property type is a class defined by the bean author, then she/he needs to write a property editor for that class.
Property Sheet Limitations
Customizers
Customizer Interface
1. setObject(Object bean): The builder tool calls this method to pass the target bean instance to the customizer. It is called only once, which is before the builder tool launches the customizer.
Builder Tool Interaction Before the builder tool launches a customizer, it calls the setObject(Object bean) method in the customizer object and passes the bean instance as the parameter. It also registers for the propertyChange events. The customizer has to fire these events whenever a property is modified. When the customizer fires the event, it sends the new property value encapsulated in the PropertyChangeEvent object.
Designing Customizers If you intend to provide a customizer for your bean, start the customizer design while you're designing the bean itself. Design your bean's properties to be compatible with the customizer GUI you have in mind. For example, I wanted to have "+" and "-" buttons to increment and decrement the pie size in the Pie Chart bean (see Figure 3). I originally intended to have just one property, Pie Diameter, to represent the pie size. In order to develop a more interactive customizer GUI, I created one more property, Pie Diameter Increment, to represent the increments or decrements relative to Pie Diameter. Thus, when you click the "+" button, the pie diameter is incremented by a certain amount. Likewise, when you click the "-" button, it is decremented by the same amount. With the Pie Position property, I added two more properties: Pie Position X Increment and Pie Position Y Increment to represent the increments (decrements) to the pie position in X direction and Y direction, respectively.Figure 3 shows the Pie Chart bean customizer, which provides a better graphical interface compared to its property sheet. You can adjust the size and position of the pie smoothly by clicking the "+" and "-" buttons. Similarly, you can adjust the position of the legend by clicking the appropriate "+" and "-" buttons.
Implementing a Customizer A customizer class has to meet the following requirements to enable builder tools to launch it:
1. It must implement the Customizer interface. This is to enable the builder tool to recognize the customizer and to obtain the bean instance, which can be passed on to the customizer. Using this bean instance, the customizer can fetch and modify a bean's properties. The customizer UI will have different types of GUI components depending on your design. The event-handling code for these components should fetch and set property values. Since the customizer object gets the bean instance, it can directly call any public methods in the bean. This means that the customizer can directly invoke the getter and setter method to get and set a property in the bean. While you can build a customizer easily this way, it's not a good solution for the following reasons:
An appropriate solution would be to use the reflection API to obtain the getter and setter methods of a property and fire the propertyChange events to set its value. The Pie Chart bean customizer uses this approach.
Pie Chart Customizer
CustomizerImpl Class
As the listing shows, the CustomizerImpl class has three instance variables: The instance variables, bean and pcs, are set in the setObject() method. The createGUI() method creates the GUI components and is called only after the target bean instance is received. It is an abstract method, which means that subclasses of CustomizerImpl provide the actual code.
CustomizerUtil Class As an example, see Listing 2, which shows the createJTextField() method. This method first constructs a JTextField component. It then obtains the actual property value from the bean by calling the getProperty() method (see Listing 3). Using the property name string, getProperty() method first constructs the Method object for the property's getter method. The Method object executes invoke() to invoke the getter method. The createJTextField() method also has the code to set the property. When the user types a value and hits Enter, the JTextField fires an action event. To handle this event, createJTextField() registers with the JTextField to receive action events. The event-handling code for the action event is in an anonymous class in which the actionPerformed() method first fetches the text entered by the user from the JTextField and converts the value to an appropriate object. It then calls the firePropertyChangeEvent() method in pcs. Listing 4 shows the code to create "+" and "-" buttons for incrementing and decrementing a property. This method uses a highly reusable class, IncrButtonAdapter, which is an adapter class for the action event (see Listing 5). An IncrButtonAdapter instance is constructed for each button. The property name and increment intervals are passed as arguments to this constructor. The actionPerformed() method, which is called whenever the increment button is clicked, first fetches the property value from the bean, then adds the increment to this value and calls the firePropertyChangeEvent() in pcs. The IncrButtonAdapter class is used by pie and legend properties in the Pie Chart bean customizer.
PieChartCustomizer Class
Registering the Customizer
The second constructor is used to register the customizer. If you use the first constructor, the builder tool assumes that the bean has no customizer. The code to register the customizer goes in the BeanInfo class. The example below shows how the Pie Chart bean customizer is registered. This code is taken from the PieChartBeanInfo class. public BeanDescriptor getBeanDescriptor(){ BeanDescriptor bd = new BeanDescriptor(PieChart.class, PieChartCustomizer.class); // Other stuff return bd; } A bean's own BeanInfo class is the only place where you can register a customizer. This means that building a BeanInfo class for that bean class is a must. This is because builder tools won't recognize the customizer even if the customizer is registered in a bean's superclass BeanInfo.
Customizer at Runtime To launch the customizer, you can use the button, pop-up menu or any suitable component depending on your bean and the application. The Graphics Viewport bean shown in Figure 4 provides a pop-up menu that can be triggered by right-clicking. (You can download this bean from my Web site at www.execpc.com/~larryhr/gvbean.html and use it to draw a variety of shapes and text.) This menu contains the items customize and serialize. The customizer class itself is a property in the Graphics Viewport bean. This means that the class can be set by the setter method and fetched by the getter method. The bean context or application that uses the Graphics Viewport bean can call these methods to register and launch the customizer. Listing 7 shows the event-handling code (which is in the Graphics Viewport bean itself) for the Customize menu item. As you can see, the actionPerformed() method first fetches the customizer class and passes it as a parameter to launchCustomizer() to launch the customizer.
Launching the Customizer In the event-handling method it retrieves the property values from the PropertyChangeEvent object and calls the setProperty() method (see Listing 9). This method uses the Method class to invoke the setter method.
Bean as a Standalone Application To make a bean run as a standalone application, you need to add the main() method. Starting with Java 2, a jar file can be made executable. This means that you can run a bean that has the main() method by executing its JAR file. For example, to run the Graphics Viewport bean, just type java -jar grbean.jar. To make a JAR executable, you need to include an attribute called Main-Class in the JAR manifest file. Following is the example from the grbean.jar manifest file.
Main-Class: com.vistech.viewport.GraphicsViewport
Name: com/vistech/viewport/GraphicsViewport.class
Java-Bean: True This brings up another issue: Should the runtime and design-time customizers be the same? There is nothing to prevent you from having two customizers - one for design time and one for runtime. You can use the same Customizer interface to implement these customizers.
Conclusion
References Reader Feedback: Page 1 of 1
Latest Cloud Developer Stories
Subscribe to the World's Most Powerful Newsletters
Subscribe to Our Rss Feeds & Get Your SYS-CON News Live!
|
SYS-CON Featured Whitepapers
Most Read This Week
Breaking Cloud Computing News
|
|||||||||||||||||||||||||||||||||||||||||||||||||