home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: Science
/
Science.zip
/
OS2SCALC.ZIP
/
CURS.C
< prev
next >
Wrap
C/C++ Source or Header
|
1990-07-20
|
13KB
|
701 lines
/**********************************************************************
*
* Tiny pseudo "curses" package (runs on U__X, VMS, OS2, or MCH_AMIGA)
*
* v1.0 870117 DBW - D. Wecker, initial hack
* OS/2 Modifications by Brady Flowers, 7/19/90
*
**********************************************************************/
/* ----------------------------------------------------------------------- */
#ifdef VMS
#include <stsdef.h>
#include <ssdef.h>
#include <descrip.h>
#include <iodef.h>
#include <ttdef.h>
#define NIBUF 128 /* Input buffer size */
#define NOBUF 1024 /* MM says bug buffers win! */
#define EFN 0 /* Event flag */
char obuf[NOBUF]; /* Output buffer */
int nobuf; /* # of bytes in above */
char ibuf[NIBUF]; /* Input buffer */
int nibuf; /* # of bytes in above */
int ibufi; /* Read index */
int oldmode[2]; /* Old TTY mode bits */
int newmode[2]; /* New TTY mode bits */
short iochan; /* TTY I/O channel */
struct dsc$descriptor idsc;
struct dsc$descriptor odsc;
char oname[40];
int iosb[2];
int term[2];
int status;
#endif
/* ----------------------------------------------------------------------- */
#ifdef MCH_AMIGA
extern char *Open();
extern long Read(),Write();
extern void Close();
#define NEW 1006L
#define AMG_MAXBUF 1024
static char *terminal = 0L;
static char scrn_tmp[AMG_MAXBUF+1];
static long scrn_tmp_p = 0L;
#endif
/* ----------------------------------------------------------------------- */
#ifdef U__X
#include <sys/ioctl.h>
#include <sgtty.h>
#include <stdio.h>
struct sgttyb old_tty,new_tty;
#endif
/* ----------------------------------------------------------------------- */
#ifdef OS2
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <conio.h>
#define INCL_KBD
#define INCL_VIO
#include <os2.h>
#define CURS_C
#include "curs.h"
#endif
/* ----------------------------------------------------------------------- */
#define NORMAL 0x00
#define BOLD 0x80
#ifndef OS2
char nscrn[ROWS][COLS],
cscrn[ROWS][COLS],
row,
col,
mode;
#else
typedef char SCRN[COLS];
SCRN *nscrn;
SCRN *cscrn;
char row, col, mode;
USHORT usRow = 0, usCol = 0;
BYTE bNormAttr = 0x07;
BYTE bBoldAttr = 0x70;
BYTE cell[2];
#endif
char str[256];
/* ----------------------------------------------------------------------- */
#ifdef OS2
/* OS/2 version, discover screen size, set raw keyboard mode,
* move the cursor, clear the screen, and get keystrokes
*/
static void SetOS2Scr(void);
static void AdvanceCurs(void);
static void GetOS2Curs(void);
static void SetOS2Curs(int r, int c);
static void ClsOS2(void);
static void SetOS2Kbd(void);
static int GetOS2Key(void);
static int curmode(void);
static void SetOS2Scr()
{
VIOMODEINFO viomi;
if (!fRemote)
{
VioGetMode(&viomi, 0);
PCrows = viomi.row - 1;
}
}
static void AdvanceCurs()
{
if (++usCol == COLS)
{
usCol = 0;
if (++usRow == ROWS)
{
--usRow;
cell[0] = ' ';
cell[1] = mode == BOLD ? bBoldAttr : bNormAttr;
VioScrollUp(0, 0, 0xffff, 0xffff, 1, cell, 0);
}
}
VioSetCurPos(usRow, usCol, 0);
}
static void GetOS2Curs()
{
VioGetCurPos(&usRow, &usCol, 0);
}
static void SetOS2Curs(int r, int c)
{
if (fRemote)
{
sprintf(str,"\033[%d;%dH", r+1, c+1);
fputs(str, stdout);
}
else
VioSetCurPos(usRow = r, usCol = c, 0);
}
static void ClsOS2(void)
{
if (fRemote)
fputs("\033[2J", stdout);
else
{
cell[0] = ' ';
cell[1] = mode == BOLD ? bBoldAttr : bNormAttr;
VioScrollUp(0, 0, 0xffff, 0xffff, 0xffff, cell, 0);
VioSetCurPos(usRow = 0, usCol = 0, 0);
}
}
static void SetOS2Kbd()
{
KBDINFO kbstInfo;
if (!fRemote)
{
kbstInfo.cb = sizeof(kbstInfo);
KbdGetStatus(&kbstInfo, 0); /* gets current status */
kbstInfo.fsMask =
(kbstInfo.fsMask & 0x00F7) /* masks out ASCII mode */
| 0x0004; /* OR into binary mode */
KbdSetStatus(&kbstInfo, 0); /* sets new status */
}
}
#define EXT_KEY 224
#define STDIN 0
static int GetOS2Key()
{
static USHORT pending = 0;
static KBDKEYINFO kbdi;
if (fRemote)
{
DosRead(STDIN, &(kbdi.chChar), 1, &pending);
return kbdi.chChar;
}
// Else, local keyboard
if (pending)
{
pending = 0;
return kbdi.chScan;
}
KbdCharIn(&kbdi, IO_WAIT, 0);
if (kbdi.chChar == 0 || kbdi.chChar == EXT_KEY)
{
pending = 1;
return 0;
}
return kbdi.chChar;
}
#else
#define VOID
#endif
VOID move(y,x)
int y,x;
{
row = (char)y;
col = (char)x;
}
VOID clrtoeol()
{
int i;
for (i = col; i < COLS; i++) nscrn[row][i] = (char)' ' | mode;
}
#ifdef OS2
VOID printw(char *fmt, ... )
{
va_list args;
va_start(args, fmt);
vprintw(fmt, args);
}
VOID vprintw(char *fmt, void *args)
{
int i,j;
vsprintf(str, fmt, (va_list)args);
j = 0;
for (i = col; i < COLS && str[j] != '\000'; i++)
nscrn[row][i] = str[j++] | mode;
col = (char)i;
}
#else
VOID printw(fmt,a1,a2,a3,a4,a5)
char *fmt,*a1,*a2,*a3,*a4,*a5;
{
int i,j;
sprintf(str,fmt,a1,a2,a3,a4,a5);
j = 0;
for (i = col; i < COLS && str[j] != '\000'; i++)
nscrn[row][i] = str[j++] | mode;
col = i;
}
#endif
VOID clrtobot()
{
int i,j;
clrtoeol();
for (i = row+1; i < ROWS; i++)
for (j = 0; j < COLS; j++)
nscrn[i][j] = (char)' ' | mode;
}
VOID standout()
{
mode = BOLD;
}
VOID standend()
{
mode = NORMAL;
}
static int curmode()
{
return mode;
}
VOID addstr(s)
char *s;
{
printw("%s",s);
}
VOID initscr()
{
int i,j;
#ifdef MCH_AMIGA
terminal = Open("RAW:1/1/639/199/DBW_VC (v1.0 870117)",(long)NEW);
#endif
#ifdef VMS
odsc.dsc$a_pointer = "TT";
odsc.dsc$w_length = strlen(odsc.dsc$a_pointer);
odsc.dsc$b_dtype = DSC$K_DTYPE_T;
odsc.dsc$b_class = DSC$K_CLASS_S;
idsc.dsc$b_dtype = DSC$K_DTYPE_T;
idsc.dsc$b_class = DSC$K_CLASS_S;
do {
idsc.dsc$a_pointer = odsc.dsc$a_pointer;
idsc.dsc$w_length = odsc.dsc$w_length;
odsc.dsc$a_pointer = &oname[0];
odsc.dsc$w_length = sizeof(oname);
status = LIB$SYS_TRNLOG(&idsc, &odsc.dsc$w_length, &odsc);
if (status!=SS$_NORMAL && status!=SS$_NOTRAN) exit(status);
if (oname[0] == 0x1B) {
odsc.dsc$a_pointer += 4;
odsc.dsc$w_length -= 4;
}
}
while (status == SS$_NORMAL);
status = SYS$ASSIGN(&odsc, &iochan, 0, 0);
if (status != SS$_NORMAL) exit(status);
status = SYS$QIOW(EFN, iochan, IO$_SENSEMODE, iosb, 0, 0,
oldmode, sizeof(oldmode), 0, 0, 0, 0);
if (status!=SS$_NORMAL || (iosb[0]&0xFFFF)!=SS$_NORMAL) exit(status);
newmode[0] = oldmode[0];
newmode[1] = oldmode[1] | TT$M_PASSALL | TT$M_NOECHO;
status = SYS$QIOW(EFN, iochan, IO$_SETMODE, iosb, 0, 0,
newmode, sizeof(newmode), 0, 0, 0, 0);
if (status!=SS$_NORMAL || (iosb[0]&0xFFFF)!=SS$_NORMAL) exit(status);
#endif
#ifdef U__X
ioctl(0,TIOCGETP,&old_tty);
ioctl(0,TIOCGETP,&new_tty);
new_tty.sg_flags |= RAW;
new_tty.sg_flags &= ~ECHO;
ioctl(0,TIOCSETP,&new_tty);
#endif
#ifdef OS2
SetOS2Kbd();
SetOS2Scr();
nscrn = malloc(sizeof(char) * COLS * ROWS);
cscrn = malloc(sizeof(char) * COLS * ROWS);
#endif
row = 0;
col = 0;
mode = NORMAL;
for (i = 0; i < ROWS; i++)
for (j = 0; j < COLS; j++)
nscrn[i][j] = cscrn[i][j] = ' ';
#ifdef OS2
ClsOS2();
#else
ttputs("\033[2J");
#endif
}
VOID clear()
{
row = 0;
col = 0;
clrtobot();
}
VOID endwin()
{
move(ROWS-1,0);
refresh();
#ifdef MCH_AMIGA
amg_flush();
Close(terminal);
#endif
#ifdef VMS
status = SYS$QIOW(EFN, iochan, IO$_SETMODE, iosb, 0, 0,
oldmode, sizeof(oldmode), 0, 0, 0, 0);
if (status!=SS$_NORMAL || (iosb[0]&0xFFFF)!=SS$_NORMAL) exit(status);
status = SYS$DASSGN(iochan);
if (status != SS$_NORMAL) exit(status);
#endif
#ifdef U__X
ioctl(0,TIOCSETP,&old_tty);
#endif
}
char inch()
{
return(nscrn[row][col] & 0x7F);
}
VOID touchwin()
{
int i,j;
for (i=0; i<ROWS; i++)
for (j=0; j<COLS; j++)
cscrn[i][j] = ' ';
#ifdef OS2
ClsOS2();
#else
ttputs("\033[2J");
#endif
}
VOID refresh()
{
int i,j,mode,savemode,curpos;
mode = NORMAL;
#ifdef OS2
if ((savemode = curmode()) == BOLD) standend();
GetOS2Curs();
#endif
for (i=0; i < ROWS; i++)
{
curpos = -1;
for (j = 0; j < COLS; j++)
{
if (nscrn[i][j] != cscrn[i][j])
{
if (curpos == -1)
{
#ifdef OS2
SetOS2Curs(i, j);
#else
sprintf(str,"\033[%d;%dH",i+1,j+1);
ttputs(str);
#endif
curpos = j;
}
else
{
#ifdef OS2
if (fRemote)
{
sprintf(str,"\033[%dC",j-curpos);
fputs(str, stdout);
}
else
SetOS2Curs(i, j);
#else
sprintf(str,"\033[%dC",j-curpos);
ttputs(str);
#endif
curpos = j;
}
while (nscrn[i][j] != cscrn[i][j])
{
if (mode == NORMAL && (nscrn[i][j] & BOLD) == BOLD)
{
#ifdef OS2
if (fRemote)
ttputs("\033[7m");
else
standout();
mode = BOLD;
#else
ttputs("\033[7m");
mode = BOLD;
#endif
}
else if (mode == BOLD && (nscrn[i][j] & BOLD) == NORMAL)
{
#ifdef OS2
if (fRemote)
ttputs("\033[0m");
else
standend();
mode = NORMAL;
#else
ttputs("\033[0m");
mode = NORMAL;
#endif
}
cscrn[i][j] = nscrn[i][j];
ttputc(nscrn[i][j] & 0x7F);
curpos++;
j++;
}
}
}
}
#ifdef OS2
SetOS2Curs(row, col);
if (mode && fRemote) fputs("\033[0m", stdout);
if (mode != savemode)
{
if (savemode == NORMAL)
standend();
else
standout();
}
#else
sprintf(str,"\033[%d;%dH",row+1,col+1);
ttputs(str);
if (mode) ttputs("\033[0m");
#endif
ttflush();
}
int ttgetc()
{
#ifdef MCH_AMIGA
unsigned char ch[2];
Read(terminal, ch, 1L);
return (ch[0] & 0xFF);
#endif
#ifdef VMS
while (ibufi >= nibuf) {
ibufi = 0;
term[0] = 0;
term[1] = 0;
status = SYS$QIOW(EFN, iochan, IO$_READLBLK|IO$M_TIMED,
iosb, 0, 0, ibuf, NIBUF, 0, term, 0, 0);
if (status != SS$_NORMAL) exit(status);
status = iosb[0] & 0xFFFF;
if (status!=SS$_NORMAL && status!=SS$_TIMEOUT) exit(status);
nibuf = (iosb[0]>>16) + (iosb[1]>>16);
if (nibuf == 0) {
status = SYS$QIOW(EFN, iochan, IO$_READLBLK,
iosb, 0, 0, ibuf, 1, 0, term, 0, 0);
if (status != SS$_NORMAL || (status = (iosb[0]&0xFFFF)) != SS$_NORMAL)
exit(status);
nibuf = (iosb[0]>>16) + (iosb[1]>>16);
}
}
return (ibuf[ibufi++] & 0x7F);
#endif
#ifdef U__X
return(getchar() & 0x7F);
#endif
#ifdef OS2
return (GetOS2Key() & 0x7f);
#endif
}
VOID ttputc(c)
#ifdef MCH_AMIGA
char c;
#endif
{
#ifdef MCH_AMIGA
scrn_tmp[scrn_tmp_p++] = c;
if(scrn_tmp_p>=AMG_MAXBUF) amg_flush();
#endif
#ifdef VMS
if (nobuf >= NOBUF) ttflush();
obuf[nobuf++] = c;
#endif
#ifdef U__X
fputc(c, stdout);
#endif
#ifdef OS2
if (fRemote)
fputc(c, stdout);
else
{
cell[0] = (BYTE)c;
cell[1] = mode != NORMAL ? bBoldAttr : bNormAttr;
VioWrtNCell(cell, 1, usRow, usCol, 0);
AdvanceCurs();
}
#endif
}
#ifdef MCH_AMIGA
amg_flush()
{
if(scrn_tmp_p) Write(terminal,scrn_tmp,(long)scrn_tmp_p);
scrn_tmp_p = 0;
}
#endif
VOID ttputs(s)
char *s;
{
while (*s) ttputc(*s++);
}
#ifdef VMS
int ttflush()
#else
VOID ttflush()
#endif
{
#ifdef MCH_AMIGA
amg_flush();
#endif
#ifdef VMS
status = SS$_NORMAL;
if (nobuf != 0)
{
status = SYS$QIOW(EFN, iochan, IO$_WRITELBLK|IO$M_NOFORMAT,
iosb, 0, 0, obuf, nobuf, 0, 0, 0, 0);
if (status == SS$_NORMAL) status = iosb[0] & 0xFFFF;
nobuf = 0;
}
return (status);
#endif
#ifdef U__X
fflush(stdout);
#endif
#ifdef OS2
if (fRemote)
fflush(stdout);
#endif
}