Tuesday 28 March 2017

Handling Events by Extending AWT Components - Java Tutorials

Before concluding our look at the AWT, one more topic needs to be discussed: handling events by extending AWT components. The delegation event model was introduced, and all of the programs in this book so far have used that design. But Java also allows you to handle events by subclassing AWT components. Doing so allows you to handle events in much the same way as they were handled under the original 1.0 version of Java. Of course, this technique is discouraged, because it has the same disadvantages of the Java 1.0 event model, the main one being inefficiency. Handling events by extending AWT components is described in this section for completeness. However, this technique is not used in any other sections of this book.

To extend an AWT component, you must call the enableEvents( ) method of Component. Its general form is shown here:

      protected final void enableEvents(long eventMask)

The eventMask argument is a bit mask that defines the events to be delivered to this component. The AWTEvent class defines int constants for making this mask. Several are shown here:

      ACTION_EVENT_MASK 
      KEY_EVENT_MASK
      ADJUSTMENT_EVENT_MASK 
      MOUSE_EVENT_MASK
      COMPONENT_EVENT_MASK 
      MOUSE_MOTION_EVENT_MASK
      CONTAINER_EVENT_MASK 
      MOUSE_WHEEL_EVENT_MASK
      FOCUS_EVENT_MASK 
      TEXT_EVENT_MASK
      INPUT_METHOD_EVENT_MASK 
      WINDOW_EVENT_MASK
      ITEM_EVENT_MASK

You must also override the appropriate method from one of your superclasses in order to process the event. lists the methods most commonly used and the classes that provide them. The following sections provide simple programs that show how to extend several AWT components.


Event Processing Methods

Button:  processActionEvent( )

Checkbox:  processItemEvent( )

CheckboxMenuItem:  processItemEvent( )

Choice:  processItemEvent( )

Component:  processComponentEvent( ), processFocusEvent( ), processKeyEvent( ), processMouseEvent( ), processMouseMotionEvent( ), processMouseWheelEvent ( )

List:  processActionEvent( ), processItemEvent( )

MenuItem:  processActionEvent( )

Scrollbar:  processAdjustmentEvent( )

TextComponent:  processTextEvent( )


Extending Button

The following program creates an applet that displays a button labeled “Test Button”. When the button is pressed, the string “action event: ” is displayed on the status line of the applet viewer or browser, followed by a count of the number of button presses.

The program has one top-level class named ButtonDemo2 that extends Applet. A static integer variable named i is defined and initialized to zero. This records the number of button pushes. The init( ) method instantiates MyButton and adds it to the applet.

MyButton is an inner class that extends Button. Its constructor uses super to pass the label of the button to the superclass constructor. It calls enableEvents( ) so that action events may be received by this object. When an action event is generated, processActionEvent( ) is called. That method displays a string on the status line and calls processActionEvent( ) for the superclass. Because MyButton is an inner class, it has direct access to the showStatus( ) method of ButtonDemo2.

  /*
  * <applet code=ButtonDemo2 width=200 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class ButtonDemo2 extends Applet {
    MyButton myButton;
    static int i = 0;
    public void init() {
      myButton = new MyButton("Test Button");
      add(myButton);
    }
    class MyButton extends Button {
      public MyButton(String label) {
        super(label);
        enableEvents(AWTEvent.ACTION_EVENT_MASK);
      }
      protected void processActionEvent(ActionEvent ae) {
        showStatus("action event: " + i++);
        super.processActionEvent(ae);
      }
    }
  }


Extending Checkbox

The following program creates an applet that displays three check boxes labeled “Item 1”, “Item 2”, and “Item 3”. When a check box is selected or deselected, a string containing the name and state of that check box is displayed on the status line of the applet viewer or browser.

The program has one top-level class named CheckboxDemo2 that extends Applet. Its init( ) method creates three instances of MyCheckbox and adds these to the applet. MyCheckbox is an inner class that extends Checkbox. Its constructor uses super to pass the label of the check box to the superclass constructor. It calls enableEvents( ) so that item events may be received by this object. When an item event is generated, processItemEvent( ) is called. That method displays a string on the status line and calls processItemEvent( ) for the superclass.

  /*
  * <applet code=CheckboxDemo2 width=300 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class CheckboxDemo2 extends Applet {
    MyCheckbox myCheckbox1, myCheckbox2, myCheckbox3;
    public void init() {
      myCheckbox1 = new MyCheckbox("Item 1");
      add(myCheckbox1);
      myCheckbox2 = new MyCheckbox("Item 2");
      add(myCheckbox2);
      myCheckbox3 = new MyCheckbox("Item 3");
      add(myCheckbox3);
    }
    class MyCheckbox extends Checkbox {
      public MyCheckbox(String label) {
        super(label);
        enableEvents(AWTEvent.ITEM_EVENT_MASK);
      }
      protected void processItemEvent(ItemEvent ie) {
        showStatus("Checkbox name/state: " + getLabel() +
                   "/" + getState());
        super.processItemEvent(ie);
      }
    }
  }


Extending a Check Box Group

The following program reworks the preceding check box example so that the check boxes form a check box group. Thus, only one of the check boxes may be selected at any time.

  /*
  * <applet code=CheckboxGroupDemo2 width=300 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class CheckboxGroupDemo2 extends Applet {
    CheckboxGroup cbg;
    MyCheckbox myCheckbox1, myCheckbox2, myCheckbox3;
    public void init() {
      cbg = new CheckboxGroup();
      myCheckbox1 = new MyCheckbox("Item 1", cbg, true);
      add(myCheckbox1);
      myCheckbox2 = new MyCheckbox("Item 2", cbg, false);
      add(myCheckbox2);
      myCheckbox3 = new MyCheckbox("Item 3", cbg, false);
      add(myCheckbox3);
    }
    class MyCheckbox extends Checkbox {
      public MyCheckbox(String label, CheckboxGroup cbg,
                        boolean flag) {
        super(label, cbg, flag);
        enableEvents(AWTEvent.ITEM_EVENT_MASK);
      }
      protected void processItemEvent(ItemEvent ie) {
        showStatus("Checkbox name/state: " + getLabel() +
                   "/" + getState());
        super.processItemEvent(ie);
      }
    }
  }


Extending Choice

The following program creates an applet that displays a choice list with items labeled “Red”, “Green”, and “Blue”. When an entry is selected, a string that contains the name of the color is displayed on the status line of the applet viewer or browser.

There is one top-level class named ChoiceDemo2 that extends Applet. Its init( ) method creates a choice element and adds it to the applet. MyChoice is an inner class that extends Choice. It calls enableEvents( ) so that item events may be received by this object. When an item event is generated, processItemEvent( ) is called. That method displays a string on the status line and calls processItemEvent( ) for the superclass.

  /*
  * <applet code=ChoiceDemo2 width=300 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class ChoiceDemo2 extends Applet {
    MyChoice choice;
    public void init() {
      choice = new MyChoice();
      choice.add("Red");
      choice.add("Green");
      choice.add("Blue");
      add(choice);
    }
    class MyChoice extends Choice {
      public MyChoice() {
        enableEvents(AWTEvent.ITEM_EVENT_MASK);
      }
      protected void processItemEvent(ItemEvent ie) {
        showStatus("Choice selection: " + getSelectedItem());
        super.processItemEvent(ie);
      }
    }
  }


Extending List

The following program modifies the preceding example so that it uses a list instead of a choice menu. There is one top-level class named ListDemo2 that extends Applet. Its init( ) method creates a list element and adds it to the applet. MyList is an inner class that extends List. It calls enableEvents( ) so that both action and item events may be received by this object. When an entry is selected or deselected, processItemEvent( ) is called. When an entry is double-clicked, processActionEvent( ) is also called. Both methods display a string and then hand control to the superclass.

  /*
  * <applet code=ListDemo2 width=300 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class ListDemo2 extends Applet {
    MyList list;
    public void init() {
      list = new MyList();
      list.add("Red");
      list.add("Green");
      list.add("Blue");
      add(list);
    }
    class MyList extends List {
      public MyList() {
        enableEvents(AWTEvent.ITEM_EVENT_MASK |
                     AWTEvent.ACTION_EVENT_MASK);
      }
      protected void processActionEvent(ActionEvent ae) {
        showStatus("Action event: " + ae.getActionCommand());
        super.processActionEvent(ae);
      }
      protected void processItemEvent(ItemEvent ie) {
        showStatus("Item event: " + getSelectedItem());
        super.processItemEvent(ie);
      }
    }
  }


Extending Scrollbar

The following program creates an applet that displays a scroll bar. When this control is manipulated, a string is displayed on the status line of the applet viewer or browser. That string includes the value represented by the scroll bar.

There is one top-level class named ScrollbarDemo2 that extends Applet. Its init( ) method creates a scroll bar element and adds it to the applet. MyScrollbar is an inner class that extends Scrollbar. It calls enableEvents( ) so that adjustment events may be received by this object. When the scroll bar is manipulated, processAdjustmentEvent( ) is called. When an entry is selected, processAdjustmentEvent( ) is called. It displays a string and then hands control to the superclass.

  /*
  * <applet code=ScrollbarDemo2 width=300 height=100>
  * </applet>
  */
  import java.awt.*;
  import java.awt.event.*;
  import java.applet.*;

  public class ScrollbarDemo2 extends Applet {
    MyScrollbar myScrollbar;
    public void init() {
      myScrollbar = new MyScrollbar(Scrollbar.HORIZONTAL,
                                    0, 1, 0, 100);
      add(myScrollbar);
    }
    class MyScrollbar extends Scrollbar {
      public MyScrollbar(int style, int initial, int thumb,
                         int min, int max) {
        super(style, initial, thumb, min, max);
        enableEvents(AWTEvent.ADJUSTMENT_EVENT_MASK);
      }
      protected void processAdjustmentEvent(AdjustmentEvent ae) {
        showStatus("Adjustment event: " + ae.getValue());
        setValue(getValue());
        super.processAdjustmentEvent(ae);
      }
    }
  }


Exploring the Controls, Menus, and Layout Managers

This chapter has discussed the classes that comprise the AWT controls, menus, and layout managers. However, the AWT provides a rich programming environment that you will want to continue exploring on your own. Here are some suggestions:
  • Try nesting a canvas inside an applet panel.
  • Explore the FileDialog component.
  • Experiment with manual positioning of components by using setBounds( ).
  • Try nesting controls within panels to gain more control over layouts.
  • Create your own layout manager by implementing the LayoutManager interface.
  • Explore PopupMenu.

The more you know about the AWT components, the more control you will have over the look, feel, and performance of your applets and applications. In the next chapter, we will examine one more of the AWT’s classes: Image. This class is used to support imaging and animation.

No comments:

Post a Comment