Using a user event

After you define a user event, you must write the script that PowerBuilder will execute when that user event is triggered. If it is an unmapped user event, you also write the code that will trigger the user event.

User events display in alphabetical order in the Event List view and the event list box in the Script view, along with the predefined events. As with predefined events, the script tells PowerBuilder what processing to perform when the user event occurs.

If the user event is not mapped to a Windows message (that is, if there is no event ID associated with it), you must trigger the event in a script. You can trigger the user event in an object using the EVENT syntax. For information about calling events, see the section called “About events” in PowerScript Reference.

Examples of user event scripts

This section includes two examples that use a mapped user event and one example that uses an unmapped user event. For more user event examples, see Communicating between a window and a user object.

Example 1: mapped user event for a control

Situation. You have several SingleLineEdit controls in a window and want the Enter key to behave like the Tab key (if users press Enter, you want them to tab to the next SingleLineEdit).

Solution. Define a user event for each SingleLineEdit. Give the event any name you want, such as ue_CheckKey. Map the event to the event ID pbm_keydown. Write a script for the user event that tests for the key that was pressed. If Enter was pressed, set the focus to the SingleLineEdit that you want the user to go to.

For example, in the script for the user event for sle_1, you could code:

// Script for user event ue_CheckKey
// which is mapped to pbm_keydown.
IF KeyDown(KeyEnter!) THEN   // Go to sle_2 if
   sle_2.SetFocus( )         // Enter pressed.
END IF

Similarly, in the script for the user event for sle_2, you could code:

// Script for user event ue_CheckKey,
// which is mapped to pbm_keydown.
IF KeyDown(KeyEnter!) THEN  // Go to sle_3 if
   sle_3.SetFocus( )        // Enter pressed. 
END IF

Example 2: mapped user event for an edit style

Situation. You have a DataWindow control with a column that uses the RadioButton edit style and you want to allow users to scroll through the RadioButtons when they press Down Arrow or Up Arrow (normally, pressing Down Arrow or Up Arrow scrolls to the next or preceding row).

Solution. Declare a user event for the DataWindow control that maps to the event ID pbm_dwnkey and write a script like the following for it. dwn stands for DataWindow notification.

// Script is in a user event for a DataWindow control.
// It is mapped to pbm_dwnkey. If user is in column 
// number 6, which uses the RadioButton edit style, and
// presses DownArrow, the cursor moves to the next item
// in the RadioButton list, instead of going to the next
// row in the DataWindow, which is the default behavior.
// Pressing UpArrow moves to preceding RadioButton.
//
// Note that the CHOOSE CASE below tests for data 
// values, not display values, for the RadioButtons.

int colnum = 6                     // Column number
long rownum
rownum = dw_2.GetRow( ) // Current row

IF KeyDown(KeydownArrow!) AND &
   This.GetColumn( ) = colnum THEN   
   CHOOSE CASE dw_2.GetItemString(rownum, colnum)      
      case "P"             // First value in RB
         This.SetItem(rownum, colnum,"L")  // Next 
      case "L"             // Second value in RB
         This.SetItem(rownum, colnum,"A")  // Next 
      case "A"             // Last value in RB
         This.SetItem(rownum, colnum,"P")  // First
   END CHOOSE   
   This.SetActionCode(1)   // Ignore key press
END IF

// The following code does same thing for UpArrow.
IF KeyDown(KeyupArrow!) AND &
   This.GetColumn( ) = colnum THEN

   CHOOSE CASE dw_2.GetItemString(rownum, colnum) 
      case "P"            // First value in RB   
         This.SetItem(rownum, colnum,"A")   // Last  
      case "L"            // Another value in RB  
         This.SetItem(rownum, colnum,"P")
      case "A"            // Last value in RB 
         This.SetItem(rownum, colnum,"L")   
   END CHOOSE
   This.SetActionCode(1)
END IF

Example 3: unmapped user event for menu options

Situation. Suppose you use the same menu in all your windows, but you want to enable or disable some menu items, in this case database update items, depending on which window the user is in.

Solution. In the window that will be the ancestor of all the sheet windows that do not have database update capability, define an unmapped user event called ue_ct_menu_enable. The event takes a boolean argument, ab_state, to set or clear the enabled property on various menus. This is the script for the ue_ct_menu_enable user event in the ancestor window:

// Enable / Disable Menu Options
            im_CurrMenu.m_maint.m_add.enabled = Not ab_state
            im_CurrMenu.m_maint.m_delete.enabled = Not ab_state
            im_CurrMenu.m_maint.m_undelete.enabled = Not ab_state
            im_CurrMenu.m_maint.m_update.enabled = Not ab_state
            im_CurrMenu.m_maint.m_close.enabled = ab_state

Then, in the script for the Activate event in the ancestor window, call the user event and pass the value "true" for the boolean variable ab_state.

this.EVENT ue_ct_menu_enable ( TRUE )

Write a similar script for the Deactivate event with the value "false" for ab_state.

You can use this window as the ancestor of any sheet window in your application that does not have database update capability. When the window is active, the Add, Delete, Undelete, and Update menu items are grayed out. When it is not active, the Close item is grayed out.

For windows that have database update capability, you can create a second ancestor window that inherits from the ancestor window in which you defined ue_ct_menu_enable. In the second ancestor window, you can override the ue_ct_menu_enable event script so that the appropriate menu options are enabled.