Ah, so THAT'S how you trap a single keystroke in VMS C!
andersen at vaxr.llnl.gov
andersen at vaxr.llnl.gov
Sat Jul 28 03:53:58 AEST 1990
Hey, Gang --
I asked how to trap a single keystroke in VMS C earlier this week. I've since
been told that this is really not the proper forum for such a question, since
it is more a VMS question than a C one. But I've had a few e-mail messages
asking me to post whatever solutions I received, so at the risk of your
disapproval, here is a program that combines the two general types of
solutions that were sent to me.
The SMG way is dead-simple to code, and was sent to me by Robert J. Drabek from
Arizona. The QIO way was sent to me by Russ Evans and Phil Wild from the
British Geological Survery, and is less obvious; but once it works, it works
well.
The difference is that the QIO way will buffer up extra keystrokes (if,
for example, you hit an arrow key, it will trap the entire escape sequence
one character at a time). It also allows for timeouts (though the SMG way
might as well -- I didn't explore it.)
This program demonstrates both methods, but it is not crash-proofed or dolled
up very much, and if it's bad or wrong or ugly, it's because I screwed up
Robert's and Russ' and Phil's examples.
So, thanks to all of you who responded with you solutions and ideas. I'll
try to make my next question (if any) more C-specific.
-- Roger Andersen
LLNL
----------------- CUT HERE -------------------------
/* ====================================================================== */
/* File: keytraps.c */
/* Author: Roger W. Andersen */
/* Laser Controls Group L-572 2-2176 */
/* Abstract: */
/* This program demonstrates two methods of trapping a single */
/* keystroke in VMS C. The two solutions were suggested by many folks */
/* in USENETs alt.lang.c, and complete working examples came from: */
/* */
/* QIO type: Russ Evans and Phil Wild */
/* British Geological Survey - Seismology Reseach Group */
/* */
/* SMG type: Robert J. Drabek -- somewhere in Arizona */
/* */
/* */
/* Both methods still allow ^Y and ^C to kill the process. */
/* */
/* This is just a combiantion of their code, and if it is wrong or */
/* ugly it is simply because I mucked it up. */
/* */
/* So there. */
/* */
/* */
/* Modification History: */
/* ================================================================== */
/* Date Author Modification */
/* ================================================================== */
/* 07-27-90 RWA Initial key-in */
/* */
/* ====================================================================== */
#include <stdio.h>
#define then
/* ====================================================================== */
/* for the SMG method: */
static unsigned int kb;
/* ====================================================================== */
/* for the QIO method: */
#include <iodef>
#include <ssdef>
#include <descrip>
static int qioch_in = 0;
static int stat_in;
static int IO_function =
IO$_READVBLK | IO$M_NOECHO | IO$M_TRMNOECHO | IO$M_NOFILTR;
static int delay = 0;
$DESCRIPTOR (input_stream, "SYS$INPUT");
typedef struct {
short cond_code;
short count;
int info;
} io_status_block;
typedef struct {
int type;
int mask;
} io_mask;
/* ======================================================================= */
/* PREP_SMG_KEYTRAPPER */
/* ======================================================================= */
void prep_SMG_keytrapper( )
{
smg$create_virtual_keyboard(&kb);
}
/* ======================================================================= */
/* PREP_QIO_KEYTRAPPER */
/* ======================================================================= */
void prep_QIO_keytrapper( )
{
int answer;
if (qioch_in == 0) {
if ((stat_in = SYS$ASSIGN(&input_stream,
&qioch_in,
0,
0))
!= SS$_NORMAL) {
printf("Can't open connection\n");
LIB$STOP(stat_in);
}
}
printf("Enter (0) for normal trap, (1) for timeout : ");
scanf("%d", &answer );
if ( answer ) then
{
IO_function |= IO$M_TIMED;
printf("Enter timeout value in seconds: " );
scanf("%d", &delay );
}
}
/* ======================================================================= */
/* TRAP_KEYSTROKE_USING_SMG */
/* ======================================================================= */
static int trap_keystroke_using_SMG( )
{
short key;
smg$read_keystroke(&kb, &key);
return (int)key;
}
/* ======================================================================= */
/* TRAP_KEYSTROKE_USING_QIO */
/* Remove comments to make this wait 1 second, then return -1 if */
/* no keystroke detected. */
/* ======================================================================= */
int trap_keystroke_using_QIO( )
{
char c;
io_mask mask = {0, 0};
io_status_block iosb;
if ((stat_in = SYS$QIOW(0,
qioch_in,
IO_function,
&iosb,
0,
0,
&c,
1,
delay,
&mask,
0,
0))
!= SS$_NORMAL) {
LIB$SIGNAL(stat_in);
}
return ( (iosb.count == 0) ? -1 : (int)c);
}
/* ======================================================================= */
/* ======================================================================= */
main( )
{
int ch;
int which;
printf("Which method do you want to use? (0 = SMG, 1 = QIO) : ");
scanf("%d", &which );
if ( which )
then prep_QIO_keytrapper( );
else prep_SMG_keytrapper( );
while ( 1 )
{
printf("Hit key to be trapped : ");
if ( which )
then ch = trap_keystroke_using_QIO( );
else ch = trap_keystroke_using_SMG( );
printf("Key is <%c>; its ASCII value is <%d>\n", ch, ch);
}
}
More information about the Comp.lang.c
mailing list