Callback Functions - slider_callback, num_callback

Cogent Tools Demo and Tutorials: Version 4.0
Prev | Chapter 8. Photon Functions (in `phsimple.g`) | Next

# 8.4. Callback Functions - `slider_callback`, `num_callback`

Although this section is named "Callback Functions," the functions here do one or two things in addition to attaching callbacks. The first function works specifically with `PtSlider` widgets; the second with `PtNumeric` widgets.

       /*--------------------------------------------------------------------
        * Function:    slider_callback
        * Returns:     t or nil
        * Description: Attaches a callback and adds an exception function to
        *              a slider widget.  The callback writes a value to the
        *              datahub point specified, and the exception function
        *              assigns the value of the datahub point to the slider
        *              widget whenever the value of the point changes in the
        *              datahub.
        *------------------------------------------------------------------*/
       function slider_callback(sld, !pnt)
       {
         PtAttachCallback(sld, Pt_CB_SLIDER_MOVE,
                          `write_point(@pnt, ((@sld).gauge_value)));
         add_exception_function(eval(pnt),
                                `(@sld).gauge_value = (@eval(pnt)));
       }

In both of these functions, the callbacks are created using the Gamma function `PtAttachCallback`, while the exception function is added with the Gamma function `add_exception_function`.

In these functions the `pnt` parameter has an exclamation point (`!`) in front of it, indicating that it is passed in as a protected argument (as explained in the Function Arguments section of the Gamma manual), and thus is not evaluated. We do this because normally a function evaluates its arguments, but in the callback the Gamma `write_point` function uses the unevaluated name of the point as a parameter. However, the rest of the function has to refer to the point itself, and its value, so we use the Gamma `eval` function to evaluate it once to get the point name, and again to get its value.

Here also are more examples of the use of Gamma's quote operators. It is useful to know that the `@` operator applies to the whole expression it precedes. For example, the expression `@sld.gauge_value` would allow for the evaluation of the current value of the slider at the time that this code is read. The expression `(@sld).gauge_value` evaluates the slider immediately, but the slider's `gauge_value` is not evaluated until an exception is received.

This explains an apparent inconsistency in the last expression of the `add_exception_function`s. In the `slider_callback` function you see the expression `(@eval(pnt))`, while in the `num_callback` function you see `eval(@pnt)`. In both functions the `pnt` parameter passed in is protected from evaluation. This means it must be evaluated once to get the name of the point, and another time to get its value. In the `slider_callback` function, the expression `(@eval(pnt))` allows both of these evaluations to occur, once by the `@` symbol, and once by the `eval` function. In the `num_callback` function, there is an extra line of code that evaluates the `pnt` variable, and assigns it the resulting name of the datahub point. We use that name when we set up the function (hence the use of `pnt` and `@pnt`), and we protect the point from evaluation until a datahub exception is received by not using the `@` symbol in front of the `eval` function.

| This function is an adaptation of the abstracted function `anyver_numeric_callback` explained in Tutorial Two.

       /*--------------------------------------------------------------------
        * Function:    num_callback
        * Returns:     t or nil
        * Description: Sets up a callback and an exception function for PtNumeric
        *              widgets to deal with sending changed values to and from
        *              the datahub.  Assigns initial values to the widgets.
        *------------------------------------------------------------------*/
       function num_callback(num, !pnt)
       {
         if(_os_ == "QNX4")
           {
             PtAttachCallback(num, Pt_CB_NUMERIC_CHANGED,
                              `write_point(@pnt, ((@eval(num)).numeric_value)));
             pnt = eval(pnt);
             num.numeric_value = eval(pnt);
             add_exception_function(pnt, `(@num).numeric_value = eval(@pnt));
           }
         else
           {

             /* Handle an annoying characteristic in Photon 2 (OS is QNX 6) whose
                PtNumericFloat widget does not work properly in Gamma. Thus we need
                to use a PtNumericInteger widget, and convert back and forth to write
                points and receive exceptions. The widget that corresponds to FREQ_001
                is a PtNumericInteger, which is already an integer.*/

             if (eval(pnt) != #FREQ_001)
               {
                 PtAttachCallback(num, Pt_CB_NUMERIC_CHANGED,
                                  `write_point(@pnt, ((@eval(num)).numeric_value) / 100.0));
                 pnt = eval(pnt);
                 num.numeric_value = round(eval(pnt) * 100);
                 add_exception_function(pnt, `((@num).numeric_value = round(eval(@pnt) * 100)));
               }
             else
               {
                 PtAttachCallback(num, Pt_CB_NUMERIC_CHANGED,
                                  `write_point(@pnt, ((@eval(num)).numeric_value)));
                 pnt = eval(pnt);
                 num.numeric_value = eval(pnt);
                 add_exception_function(pnt, `(@num).numeric_value = eval(@pnt));
               }
           }
       }

Prev | Home | Next
Button Functions - `toggle_sym`, `change_settings` | Up | Trend Functions - `accumulate_trends`, `update_trends`

Copyright 1995-2002 by Cogent Real-Time Systems, Inc.