Adding Custom Swing Components to the Data Control Palette for Oracle ADF JClient

An Oracle JDeveloper How To Document
Written by Frank Nimphius, Oracle Corporation
August, 2004

Content

      Introduction to Custom Swing Component Subclasses
      Details of the JNumberTextField Subclass g
      Adding JNumberTextField to the ADF JClient List of Components
      Using JNumberTextField in Your ADF JClient Swing Application
      Conclusion

Introduction to Custom Swing Component Subclasses

Many Oracle ADF JClient customers don't use standard Java Swing UI components to build their application user interfaces. Instead, they use custom subclassed versions of the standard Swing components, and they implement additional services like logging facilities, extra validation or security awareness with those subclasses. This document explains how to integrate a custom Swing class with the list of UI components displayed in the Data Control Palette of Oracle JDeveloper 10g to either replace an existing component on the palette or to insert an additional component onto the palette.

The Swing component example used in this document is a subclass of javax.swing.JTextfield that will only accept number inputs. The new component, JNumberTextField, is added as an additional choice to the list of UI components shown in the Data Control Palette that you can use with ADF JClient panels and frames. A modified text field icon  is used as a visual representation on the Data Control Palette.

Details of the JNumberTextField Subclass

JNumberTextField is a subclass of JTextField. As the following code shows, our subclass will block all keystrokes except those which are digits (1, 2, 3 and so on), dots ('.'), and commas (','). Optionally, calling setBeepOnError(true) acknowledges each nondigit keystroke with a beep alert. To disable the beep alert, call setBeepOnError(false);.

package oracle.samples.custom.swing.view;
import java.awt.Toolkit;
import javax.swing.JTextField;


/**
 * JTextField subclass that accepts number inputs and '.' and ','. Call
 * setBeepOnError() to enable system beep on wrong keyboard entry
 */


public class JNumberTextField extends JTextField 
{
  private boolean beep_on_error = false;
  
  public JNumberTextField()
  {
    super();
    initializeForNumbers();
  }
  
  private void initializeForNumbers()
  {
    setDocument(new javax.swing.text.PlainDocument()
    {
      public void insertString(int offs, String str, javax.swing.text.AttributeSet a) throws    javax.swing.text.BadLocationException 
      {
        StringBuffer buf = new StringBuffer(str);
        int size = buf.length();
        char c;
        for (int i = 0; i < size; i++)
        {
          c = buf.charAt(i);
          
          // allow digits and '.' as well as ',' for delimiting
          if (!Character.isDigit(c) && c != '.' && c != ',')
          {
              // beep on error
              
              if (beep_on_error){
                 Toolkit.getDefaultToolkit().beep(); 
              }
                 buf.deleteCharAt(i);
          }
        }
        super.insertString(offs, buf.toString(), a);
      }

    });
  }
  
  public void setBeepOnError(boolean beep)
  {
    beep_on_error = beep;
  }
}

Adding JNumberTextField to the ADF JClient List of Components

To make the JNumberTextField component available on the JDeveloper list of controls and allow it to be databinding-aware for ADF JClient, the following needs to be done:

  1. Create a Java Archive file (JAR) for the custom Swing component.
  2. Create a custom library in Oracle JDeveloper.
  3. Edit adfjclient_binding.xml to include the new component in the Data Control Palette

Create a Java Archive for the Custom Swing Component

To create a Java archive in JDeveloper:

  1. Select the project node that contains the JNumberTextField component you created and choose New from the right-click menu.
  2. In the New Gallery, open the General node and select the Deployment Profile node.
  3. Choose JAR File from the list of profiles and click OK. Specify a name for the new deployment profile and again click OK.

A new profile with the specified name is created in the project tree and can be further edited by double-clicking it. By maintaining the default settings of the deployment descriptor, you will create a JAR file with the specified name and the extension .jar in the project's deploy subdirectory.

2. Create Custom Library in Oracle JDeveloper

To make the JAR file available to the ADF JClient project:

  1. Select the project node in Oracle JDeveloper and choose Project Properties from the right-click menu.
  2. Select the Libraries node and click New to create a new library.
  3. In the Create Library dialog, provide a name for the new library and point the classpath to the created JAR file.
  4. Confirm all dialogs with OK.

The new library automatically gets added to the JClient project.

3. Edit adfjclient_binding.xml to Include the New Component in the Data Control Palette

The ADF JClient components that appear in the Data Control Palette in Oracle JDeveloper are configured in the adfjclient_binding.xml configuration file. The file is located in the <JDeveloper installation Home>\jdev\system9.0.5.x.xxx directory. Open this file with a text editor and navigate to the JTextField entry.

Because JNumberTextField is a subclass of JTextField, copy the following JTextField configuration and paste it as a new configuration section below the JTextField configuration:

<controlDefinition name="TextField"
                className="javax.swing.JTextField"
                classPath=""
                shortLabel="JTextField"
                longLabel="javax.swing.JTextField"
                tooltipText="javax.swing.JTextField"
                bindingType="DCTextField" 
                icon="/oracle/ideimpl/resource/images/palette/JTextField.gif">
       <useTemplate>
          <![CDATA[${FieldName}.setDocument((Document)panelBinding.bindUIControl("${BindingName}",${FieldName}))]]>
       </useTemplate>
       <imports>
          <![CDATA[javax.swing.JTextField;javax.swing.text.Document]]>
       </imports>
 </controlDefinition>

Add the changes highlighted in bold below to the new configuration section to configure the JNumberTextField component.

<controlDefinition name=
                              
"JNumberTextField"
                className=
                              
"oracle.samples.custom.swing.view.JNumberTextField"
                classPath=""
                shortLabel="JTextField"
                longLabel=
                              
"oracle.samples.custom.swing.view.JNumberTextField"
                tooltipText=
                              
"oracle.samples.custom.swing.view.JNumberTextField"
                bindingType="DCTextField" 
                icon=
                              
"/oracle/ide/resource/images/JNumberTextField.gif">
       <useTemplate>
          <![CDATA[${FieldName}.setDocument((Document)panelBinding.bindUIControl("${BindingName}",${FieldName}))]]>
       </useTemplate>
       <imports>
          <![CDATA[
                              
oracle.samples.custom.swing.view.JNumberTextField;javax.swing.text.Document]]>
       </imports>
 </controlDefinition>
                            

In this example , the image icon is located in a JAR file with the directory structure of /oracle/ide/resource/images/. Note that the directory structure for the image is arbitrary and can be any custom structure. If you don't use JDeveloper to create the images archive file, you can also use the command line, assuming you have a Java SDK configured in the system path:

jar -cvf myComponnetIcons.jar /oracle/ide/resources/images/JNumberTextField.gif

This assumes the JAR file is to be created from the parent directory of the /oracle directory. Again, the directory structure is arbitrary and can differ, as long as it is configured correctly in the icon attribute of the controlDefinition element. The icon, in case you want to create your own, must have a size of 16x16 pixel.

Close and restart Oracle JDeveloper 10g so that the new settings get loaded.

Using JNumberTextField in Your ADF JClient Swing Application

Having completed the above configuration steps, JNumberTextField now shows in the Dr ag and Drop As selection list when displayed for an ADF JClient application.

Dropping the Salary attribute as a JNumberTextField into a JClient panel will automatically create the data binding for this component, as you would normally expect.

Don't forget to try the setBeepOnError(true) method on the JNumberTextField instance.

Conclusion

Oracle JDeveloper 10g can be customized to include custom Swing components in the list of available UI components that display in the Data Control Palette for ADF JClient. All the ADF data binding is automatically performed when dragging a customized component to a JClient panel.

false ,,,,,,,,,,,,,,,