How to suppress output of SetVariableControl?

I am building a control panel that includes a SetVariable control. Changing the value of this control triggers a procedure that moves the current selection in a table to the row indicated by the variable's new value:

Function moveCurrRow(sva) : setVariableControl
    STRUCT WMSetVariableAction &sva

    NVar gCurrEventRow
    wave eventName
    variable tableRows = numpnts(eventName)

    if (gCurrEventRow >= tableRows)
        gCurrEventRow -= 1
    elseIf (gCurrEventRow < 0)
        gCurrEventRow = 0
    else
        modifyTable /W=eventTable selection=(gCurrEventRow, 0, gCurrEventRow, 0, gCurrEventRow, 0)
    endIf


End //MoveCurrRow

Every time I click on the control to increment or decrement the variable's value, I get the output below on the history window. How can I suppress this output?

STRUCT WMSetVariableAction
 ctrlName[256]: currRowDisp
 win[401]: eventMarking
 winRect: STRUCT Rect
  top: 0
  left: 0
  bottom: 800
  right: 400
 ctrlRect: STRUCT Rect
  top: 140
  left: 20
  bottom: 154
  right: 110
 mouseLoc: STRUCT Point
  v: 145
  h: 108
 eventCode: 9
 eventMod: 1
 userdata:
 blockReentry: 0
 isStr: 0
 dval: 14
 sval[2500]: 14
 vName[1298]: gCurrEventRow
 svWave: <null>
 rowIndex: 0
 rowLabel[256]:
 colIndex: 0
 colLabel[256]:
 layerIndex: 0
 layerLabel[256]:
 chunkIndex: 0
 chunkLabel[256]:
 mousePart: 1
  in fcn moveCurrRow: sva=  

 

This is not the normal behavior of the SetVariable control, so I suppose the problematic behavior happens somewhere else in your code. Can you post a MWE (minimal working example), which compiles and shows the problematic behavior? Also, I see a few other issues with your setVariableControl function. For example, the function executes on all kinds of events such as just moving the mouse. I would restrict that to the relevant events (such as changing the value). Also, it is probably not a good idea in general to use global variables.

"in fcn moveCurrRow: sva=  "

You must have a function called "moveCurrRow" that is triggered when that code executes. Do you have a window hook on the table in question?

I guess gCurrEventRow is the global attached to the SetVariable that holds the value. That used to be the only way to use a SetVariable control, before the internal storage of the value was introduced, so it's natural that folks still use a global. These days, it is preferred to use the internal value rather than a global. 

Your GUI control procedure moveCurrRow should only execute the modifyTable code on a specific event. As it is right now the code is always executed  even when moving the mouse over the control.

Thank you everyone for your explanations. I now understand how to use the setvariablecontrol, i.e. using a switch...case statement based on the eventCode property. The control now works exactly as I had intended it to:

Function moveCurrRow(sva) : setVariableControl
    STRUCT WMSetVariableAction &sva

    NVar gCurrEventRow
    wave eventName
    variable tableRows = numpnts(eventName)


    switch (sva.eventCode)
        case 1:                             // Mouse up

            if (gCurrEventRow >= tableRows)
                gCurrEventRow -= 1
                beep
            elseIf (gCurrEventRow < 0)
                gCurrEventRow = 0
                beep
            else
                modifyTable /W=eventTable selection=(gCurrEventRow, 0, gCurrEventRow, 0, gCurrEventRow, 0)
            endIf
        case 2:                         // Enter key
        case 3:                             // Live update
            Variable dval = sva.dval
            String sval = sva.sval
            break
        case -1:                            // Control being killed
            break
    endswitch

    return 0


End //MoveCurrRow

Regarding the suggested use of the internal value instead of a global, where can I find more information? Is it by any chance a new feature in Igor 9? I am still using Igor 8.

No problem. The feature of internal variables already exists for quite some years. Here is an excerpt of the manual:

value=varOrWaveName    Sets the numeric or string variable or wave element to be controlled. You can have the control store the value internally rather than in a global variable. In place of varName, use _STR:str or _NUM:num. For example: NewPanel;SetVariable sv1,value=_NUM:123

I would also suggest to impose the limits of your table onto the SetVariable control itself instead of checking the limits in the control function (or does the size of the table change? You can of course also update the limits in this case):

wave eventName
SetVariable myTableCtrl ,value=_NUM:0 ,limits={0,numpnts(eventName),1}

Then your control function could be vastly simplified:

Function moveCurrRow(STRUCT WMSetVariableAction &sva) : setVariableControl
    if (sva.eventCode == 1 || sva.eventCode == 2)   // mouse up or enter
        modifyTable/W=eventTable selection=(sva.dval, 0, sva.dval, 0, sva.dval, 0)
    endif
    return 0
End