From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.
We appreciate your patience as we improve our online experience.
From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.
We appreciate your patience as we improve our online experience.
09-14-2017 09:21 AM
Hello,
I use 4 string Controls to input 4 serial number of 4 boards individually,but it must press Tab key to next input box. I need to press an enter key to move to next input box only. I don't know how to do. Please see the attached file for my question specification
Thank.
Solved! Go to Solution.
09-14-2017 12:53 PM
I'd suggest making those input boxes "Hot" and in the callback function for the controls (on EVENT_COMMIT) you could use SetActiveCtrl() to move focus to the next control. The last one could send the focus on the button.
09-15-2017 07:32 AM
09-18-2017 04:07 PM - edited 09-18-2017 04:37 PM
Another option is to use a table control. The table automatically moves to edit the next cell when the user hits the enter key.
I've attached a UIR with an example table. Note that the ATTR_AUTO_EDIT is enabled and
ATTR_ENABLE_COLUMN_SIZING is disabled.
Also, if you use the SetActiveCtrl() on the EVENT_COMMIT, you might get some unintended behavior. For instance,
- you only get a commit event if you make some change in the string control before hitting <enter>.
- you'll get a commit event if you make some change in the string control and then use the mouse to click on a different control. This case would probably be a weird user experience since the user might click on a previous control, but then your callback would make the next control be the active one.
- if the user does hit <tab> then you'll get a commit event, and that might interfere with your intended behavior.
09-19-2017 10:23 AM
Good point about those potentially unwanted behaviors, Jared.
However in the past I have always found that input to a table has its own quirks that confuses some users. The ATTR_AUTO_EDIT attribute is helpful, but even then users might try to place the cursor within the text of a selected cell to make a correction. Unless they double-click first that second (slow) click won't work, and to them the cell seems uneditable. (In Excel the formula bar accepts that cursor-placing click, but in a CVI table we do not have the equivalent of the formula bar.)
That said, the table may still be a better choice, especially if one does not catch other events beyond EVENT_COMMIT and refine the textbox behavior accordingly.
09-19-2017 03:43 PM
Yeah, I agree that getting the table into edit mode could be a little quirky for the user. In this case, it would be nice if the table were always in edit mode. Having a table callback like this would help....
static void ActivateNextTabOrderCtrl(int panel, int control) { int nextCtrl; GetCtrlAttribute(panel, control, ATTR_NEXT_CTRL, &nextCtrl); if (nextCtrl == 0) GetPanelAttribute(panel, ATTR_PANEL_FIRST_CTRL, &nextCtrl); SetActiveCtrl(panel, nextCtrl); } static void ActivateNextTabOrderCtrlIfNecessary(int panel, int control) { Point activeCell; int numRows; GetActiveTableCell(panel, control, &activeCell); GetNumTableRows(panel, control, &numRows); if (activeCell.y == numRows) { ActivateNextTabOrderCtrl(panel, control); } } static void ActivatePrevTabOrderCtrl(int panel, int control) { int numCtrls, currentCtrl, tabPosition, targetTabPosition; GetCtrlAttribute(panel, control, ATTR_CTRL_TAB_POSITION, &targetTabPosition); GetPanelAttribute(panel, ATTR_NUM_CTRLS, &numCtrls); if (targetTabPosition == 0) targetTabPosition = numCtrls-1; else targetTabPosition--; GetPanelAttribute(panel, ATTR_PANEL_FIRST_CTRL, ¤tCtrl); for (int i=0; i<numCtrls; i++) { GetCtrlAttribute(panel, currentCtrl, ATTR_CTRL_TAB_POSITION, &tabPosition); if (tabPosition == targetTabPosition) break; GetCtrlAttribute(panel, currentCtrl, ATTR_NEXT_CTRL, ¤tCtrl); } SetActiveCtrl(panel, currentCtrl); } static void ActivatePrevTabOrderCtrlIfNecessary(int panel, int control) { Point activeCell; GetActiveTableCell(panel, control, &activeCell); if (activeCell.y == 1) { ActivatePrevTabOrderCtrl(panel, control); } } int CVICALLBACK TableCB (int panel, int control, int event, void *callbackData, int eventData1, int eventData2) { int runState; switch (event) { case EVENT_ACTIVE_CELL_CHANGE: case EVENT_GOT_FOCUS: GetCtrlAttribute(panel, control, ATTR_TABLE_RUN_STATE, &runState); if (runState != VAL_EDIT_STATE) { SetCtrlAttribute(panel, control, ATTR_TABLE_RUN_STATE, VAL_EDIT_STATE); } break; case EVENT_KEYPRESS: if (eventData1 == VAL_ENTER_VKEY || eventData1 == VAL_TAB_VKEY) { ActivateNextTabOrderCtrlIfNecessary(panel, control); } else if (eventData1 == (VAL_SHIFT_MODIFIER | VAL_TAB_VKEY)) { ActivatePrevTabOrderCtrlIfNecessary(panel, control); } break; } return 0; }
09-20-2017 04:20 PM
Thanks, Jared! Next time I need table input I'm going to try this out.
Ian