How can I use the arrow keys to move the cursor in the SpinBox text fields?
|
20-Jan-04 12:30 GMT
|
Question:
The left and right arrows in an XmSpinBox are mapped to the spinbox up
and down arrows. How can I change this so that they move the cursor left
and right in SpinBox text fields instead?
This can be done by overriding the translations and accelerators for the
SpinBox and SimpleSpinBox widgets.
This can most easily be achieved by including the following in the X
resources for your application:
*XmSpinBox.translations: \
<Btn1Down>: SpinBArm()\n\
<Btn1Up>: SpinBDisarm()\n\
<EnterWindow>: SpinBEnter()\n\
<LeaveWindow>: SpinBLeave()\n\
:<Key>osfUp: SpinBNext()\n\
:<Key>osfDown: SpinBPrior()\n\
:<KeyUp>osfUp: SpinBDisarm()\n\
:<KeyUp>osfDown: SpinBDisarm()\n\
:<KeyUp>osfLeft: SpinBDisarm()\n\
:<KeyUp>osfRight: SpinBDisarm()\n\
:<Key>osfBeginLine: SpinBFirst()\n\
:<Key>osfEndLine: SpinBLast()
*XmSpinBox.accelerators: \
#override\n\
<Key>osfUp: SpinBNext()\n\
<Key>osfDown: SpinBPrior()\n\
<KeyUp>osfUp: SpinBDisarm()\n\
<KeyUp>osfDown: SpinBDisarm()\n\
<KeyUp>osfLeft: SpinBDisarm()\n\
<KeyUp>osfRight: SpinBDisarm()\n\
<Key>osfBeginLine: SpinBFirst()\n\
<Key>osfEndLine: SpinBLast()
*XmSimpleSpinBox.translations: \
<Btn1Down>: SpinBArm()\n\
<Btn1Up>: SpinBDisarm()\n\
<EnterWindow>: SpinBEnter()\n\
<LeaveWindow>: SpinBLeave()\n\
:<Key>osfUp: SpinBNext()\n\
:<Key>osfDown: SpinBPrior()\n\
:<KeyUp>osfUp: SpinBDisarm()\n\
:<KeyUp>osfDown: SpinBDisarm()\n\
:<KeyUp>osfLeft: SpinBDisarm()\n\
:<KeyUp>osfRight: SpinBDisarm()\n\
:<Key>osfBeginLine: SpinBFirst()\n\
:<Key>osfEndLine: SpinBLast()
*XmSimpleSpinBox.accelerators: \
#override\n\
<Key>osfUp: SpinBNext()\n\
<Key>osfDown: SpinBPrior()\n\
<KeyUp>osfUp: SpinBDisarm()\n\
<KeyUp>osfDown: SpinBDisarm()\n\
<KeyUp>osfLeft: SpinBDisarm()\n\
<KeyUp>osfRight: SpinBDisarm()\n\
<Key>osfBeginLine: SpinBFirst()\n\
<Key>osfEndLine: SpinBLast()
Alternatively this can be done programmatically. First we need to construct
the translation and accelerator tables that will be applied to the SpinBox
or SimpleSpinBox widgets. The following routines (SpinBoxAccelerators and
SpinBoxTranslations) can be used to perform this task:
#include <stdlib.h>
#include <X11/Intrinsic.h>
#include <Xm/Xm.h>
static _XmConst char SpinBoxTranslationString[] = "\
<Btn1Down>: SpinBArm()\n\
<Btn1Up>: SpinBDisarm()\n\
<EnterWindow>: SpinBEnter()\n\
<LeaveWindow>: SpinBLeave()\n\
:<Key>osfUp: SpinBNext()\n\
:<Key>osfDown: SpinBPrior()\n\
:<KeyUp>osfUp: SpinBDisarm()\n\
:<KeyUp>osfDown: SpinBDisarm()\n\
:<Key>osfBeginLine: SpinBFirst()\n\
:<Key>osfEndLine: SpinBLast()";
static _XmConst char SpinBoxAcceleratorString[] = "\
#override\n\
<Key>osfUp: SpinBNext()\n\
<Key>osfDown: SpinBPrior()\n\
<KeyUp>osfUp: SpinBDisarm()\n\
<KeyUp>osfDown: SpinBDisarm()\n\
<Key>osfBeginLine: SpinBFirst()\n\
<Key>osfEndLine: SpinBLast()";
#ifndef _NO_PROTO
XtAccelerators SpinBoxAccelerators(void)
#else /* _NO_PROTO */
XtAccelerators SpinBoxAccelerators()
#endif /* _NO_PROTO */
{
static XtAccelerators accelerators = (XtAccelerators) 0 ;
if (accelerators == (XtAccelerators) 0) {
accelerators =
XtParseAcceleratorTable(SpinBoxAcceleratorString) ;
}
return accelerators ;
}
#ifndef _NO_PROTO
XtTranslations SpinBoxTranslations(void)
#else /* _NO_PROTO */
XtTranslations SpinBoxTranslations()
#endif /* _NO_PROTO */
{
static XtTranslations translations = (XtTranslations) 0 ;
if (translations == (XtTranslations) 0) {
translations =
XtParseTranslationTable(SpinBoxTranslationString) ;
}
return translations ;
}
Having created the tables we need to set the appropriate widget resources.
In terms of the SpinBox (as opposed to SimpleSpinBox) widget, it does not
matter if the accelerators and translations are applied before or after the
widget is created so either of the following code fragments could be used
to set these on the widget:
XtTranslations t = SpinBoxTranslations() ;
XtAccelerators a = SpinBoxAccelerators() ;
XtSetArg(al[ac], XmNaccelerators, a) ; ac++ ;
XtSetArg(al[ac], XmNtranslations, t) ; ac++ ;
spinBox = XmCreateSpinBox(parent, name, al, ac) ;
or
spinBox = XmCreateSpinBox(parent, name, NULL, 0) ;
XtVaSetValues(spinBox, XmNtranslations, t,
XmNaccelerators, a, NULL) ;
For the SimpleSpinBox widget the rules are a little different in that the
accelerators at least have to be applied at widget creation time:
XtAccelerators a = SpinBoxAccelerators() ;
XtSetArg(al[ac], XmNaccelerators, a) ; ac++ ;
simpleSpinBox = XmCreateSimpleSpinBox(parent, name, al, ac) ;
For safety we recommend applying both translations and accelerators in the
create method for SimpleSpinBox widgets.
Using the above methods you should find that the left and right arrow keys
will move the cursor through the text in the SpinBox TextField widgets
instead of triggering the SpinBox up and down arrows.
Note that the above example includes translations to correct a problem on
Solaris systems whereby the up and down SpinBox arrows are reversed. You
can read more about this Solaris Motif bug in an
earlier Motifdeveloper.com
technical tip. It is not necessary to include these
translations for other platforms.
To assist you in taking the above and incorporating it into your software we
have provided the whole of the above as a text file.
Right click here and 'Save As ...'.
Sponsored
by X-Designer - The Leading X/Motif GUI Builder
- Click to download a FREE evaluation
Goto top of page
|