⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 charget.c

📁 该程序是C语言编写的
💻 C
字号:
/****************************************************************/
/* Getch() routines of the PCcurses package			*/
/*								*/
/****************************************************************/
/* This version of curses is based on ncurses, a curses version	*/
/* originally written by Pavel Curtis at Cornell University.	*/
/* I have made substantial changes to make it run on IBM PC's,	*/
/* and therefore consider myself free to make it public domain.	*/
/*				Bjorn Larsson (bl@infovox.se)	*/
/****************************************************************/
/* 1.4:  Routines that ended in while-loops now end		*/
/*	 with return(ERR) to avoid compiler warnings.		*/
/*	 Use of short wherever possible. Portability		*/
/*	 improvements:					900114	*/
/* 1.3:	 MSC -W3, Turbo'C' -w -w-pro checkes:		881005	*/
/* 1.2:	 #undef:ine of getch now covers all the file, to	*/
/*	 make sure this module's getch() calls go to DOS,	*/
/*	 not to the PCCurses 'getch()' function. Fixed		*/
/*	 thanks to N.D. Pentcheff:			881002	*/
/* 1.1:	 Bug fixes: call to _curseskeytest() changed		*/
/*	 _curseskeytst(). Test of that routine also		*/
/*	 lacked () in one place:			870907	*/
/* 1.0:	 Release:					870515	*/
/****************************************************************/

#include <curses.h>
#include <curspriv.h>

#undef getch				/* We use MSC getch() below */
#undef ungetch

#include <conio.h>

static	short	rawgetch();		/* get raw char via BIOS */
static	short	sysgetch();		/* get char via system */
static	short	validchar();		/* keypad xlate and char check */

char _curses_charget_rcsid[] = "@(#)charget.c    v.1.4  - 900114";

static	short	buffer[_INBUFSIZ];	/* character buffer */
static	short	pindex = 0;		/* putter index */
static	short	gindex = 1;		/* getter index */
static	WINDOW *w;			/* to reduce stack usage */
static	short	ungind = 0;		/* wungetch() push index */
static	short	ungch[NUNGETCH];	/* array of ungotten chars */

/* Table for key code translation of function keys in keypad mode */
/* These values are for strict IBM keyboard compatibles only */

static	short	kptab[] =
  {
  0x3b,KEY_F(1),  0x3c,KEY_F(2),  0x3d,KEY_F(3),  0x3e,KEY_F(4),
  0x3f,KEY_F(5),  0x40,KEY_F(6),  0x41,KEY_F(7),  0x42,KEY_F(8),
  0x43,KEY_F(9),  0x44,KEY_F(10), 0x47,KEY_HOME,  0x48,KEY_UP,
  0x49,KEY_PPAGE, 0x4b,KEY_LEFT,  0x4d,KEY_RIGHT, 0x4f,KEY_LL,
  0x50,KEY_DOWN,  0x51,KEY_NPAGE, 0x52,KEY_IC,    0x53,KEY_DC,
  0x54,KEY_F(11), 0x55,KEY_F(12), 0x56,KEY_F(13), 0x57,KEY_F(14),
  0x58,KEY_F(15), 0x59,KEY_F(16), 0x5a,KEY_F(17), 0x5b,KEY_F(18),
  0x5c,KEY_F(19), 0x5d,KEY_F(20), 0x5e,KEY_F(21), 0x5f,KEY_F(22),
  0x60,KEY_F(23), 0x61,KEY_F(24), 0x62,KEY_F(25), 0x63,KEY_F(26),
  0x64,KEY_F(27), 0x65,KEY_F(28), 0x66,KEY_F(29), 0x67,KEY_F(30),
  0x73,KEY_LEFT,  0x74,KEY_RIGHT,  0x75,KEY_LL,   0x76,KEY_NPAGE,
  0x77,KEY_HOME,  0x84,KEY_PPAGE,  0x100,        -1
  };

/****************************************************************/
/* Wgetch(win) gets a character from the terminal, in normal,	*/
/* cbreak or raw mode, optionally echoing to window  'win'.	*/
/****************************************************************/

int wgetch(win)
  WINDOW	*win;
  {
  short	key;
  short	cbr;

  if (ungind)					/* if ungotten char exists */
    return(ungch[--ungind]);			/* remove and return it */

  if ((!_cursvar.raw) && (!_cursvar.cbreak))	/* if normal */
    if (gindex < pindex)			/* and data in buffer */
      return(buffer[gindex++]);

  w = win;					/* static for speed & stack */
  pindex = 0;					/* prepare to buffer data */
  gindex = 0;
  while(1)					/* loop for any buffering */
    {
    if (_cursvar.raw)				/* get a raw character */
      key = rawgetch();
    else					/* get a system character */
      {
      cbr = _cursesgcb();			/* get ^BREAK status */
      _cursesscb(_cursvar.orgcbr);		/* if break return proper */
      key = sysgetch();
      _cursesscb(cbr);				/* restore as it was */
      }
    if (w->_nodelay && (key == -1))		/* if nodelay and no char */
      return(-1);
    if ((key == '\r') && _cursvar.autocr && !_cursvar.raw) /* translate cr */
      key = '\n';
    if (_cursvar.echo && (key < 0x100))		/* check if echo */
      {
      waddch(w,key);
      wrefresh(w);
      }
    if (_cursvar.raw || _cursvar.cbreak)	/* if no buffering */
      return(key);
    if (pindex < _INBUFSIZ-2)			/* if no overflow, */
      buffer[pindex++] = key;			/* put data in buffer */
    if ((key == '\n') || (key == '\r'))		/* if we got a line */
      return(buffer[gindex++]);
    } /* while */
  return (ERR);					/* Can't happen */
  } /* wgetch */

/****************************************************************/
/* Flushinp() kills any pending input characters.		*/
/****************************************************************/

void flushinp()
  {
  while(_curseskeytst())		/* empty keyboard buffer */
    _curseskey();
  while(kbhit())			/* empty system's buffers */
    (void) getch();
  gindex = 1;				/* set indices to kill buffer */
  pindex = 0;
  ungind = 0;				/* clear ungch array */
  } /* flushinp */

/****************************************************************/
/* Wungetch() pushes back it's argument on the input stream. If	*/
/* OK, returns 1, otherwise returns 0.				*/
/****************************************************************/

int	wungetch(ch)
  int 	ch;
  {
  if (ungind >= NUNGETCH)		/* pushback stack full */
    return(0);
  ungch[ungind++] = ch;
  return(1);
  } /* wungetch() */

/****************************************************************/
/* Mvgetch() first moves the stdscr cursor to a new location,	*/
/* then does a wgetch() on stdscr.				*/
/****************************************************************/

int	mvgetch(y,x)
  int y;
  int x;
  {
  wmove(stdscr,y,x);
  return(wgetch(stdscr));
  } /* mvgetch */

/****************************************************************/
/* Mvwgetch() first moves the cursor of window 'win' to a new	*/
/* location, then does a wgetch() in 'win'.			*/
/****************************************************************/

int mvwgetch(win,y,x)
  WINDOW *win;
  int y;
  int x;
  {
  wmove(win,y,x);
  return(wgetch(win));
  } /* mvwgetch */

/****************************************************************/
/* rawgetch() gets a character without any interpretation at	*/
/* all and returns it. If keypad mode is active for the desig-	*/
/* nated window, function key translation will be performed.	*/
/* Otherwise, function keys are ignored.If nodelay mode is	*/
/* active in the window, then rawgetch() returns -1 if no cha-	*/
/* racter is available.						*/
/****************************************************************/

static short rawgetch()
  {
  short	c;

  if (w->_nodelay && !_curseskeytst())
    return(-1);
  while(1)  					/* loop to get valid char */
    {
    if ((c = validchar(_curseskey())) >= 0)
      return(c);
    } /* while */
  return (ERR);					/* Can't happen */
  } /* rawgetch */

/****************************************************************/
/* Sysgetch() gets a character with normal ^S, ^Q, ^P and ^C	*/
/* interpretation and returns it. If keypad mode is active for	*/
/* the designated window, function key translation will be per-	*/
/* formed. Otherwise, function keys are ignored. If nodelay	*/
/* mode is active in the window, then sysgetch() returns -1 if	*/
/* no character is available.					*/
/****************************************************************/

static short sysgetch()
  {
  short	c;

  if (w->_nodelay && !kbhit())
    return(-1);
  while(1)
    {
    c = getch();
    if (c)					/* if not a function key */
      return(c & 0xff);				/* avoids sign-extending */
    c = getch();
    if ((c = validchar(c << 8)) >= 0)		/* get & check next char */
      return(c);
    } /* while */
  return (ERR);					/* Can't happen */
  } /* sysgetch */

/****************************************************************/
/* Validchar(c) chacks that 'c' is a valid character, and	*/
/* if so returns it, with function key translation applied if	*/
/* 'w' has keypad mode set. If char is invalid, returns -1.	*/
/****************************************************************/

static short validchar(c)
  int	c;
  {
  short *scanp;

  if (c == 0x0300)			/* special case, ^@ = NULL */
    return(0);
  if (!(c & 0xff00))			/* normal character */
    return(c);
  if (!(w->_keypad))			/* skip f keys if not keypad mode */
    return(-1);
  c = (c >> 8) & 0xff;
  scanp = kptab;
  while(*scanp <= c)			/* search for value */
    {					/* (stops on table entry 0x100) */
    if (*scanp++ == c)
      return(*scanp);			/* found, return it */
    scanp++;
    }
  return(-1);				/* not found, invalid */
  } /* validchar */

/****************************************************************/
/* _cursespendch() returns 1 if there is any character avai-	*/
/* lable, and 0 if there is none. This is not for programmer	*/
/* usage, but for the updatew routines.				*/
/****************************************************************/

bool	_cursespendch()
  {
  if (ungind)				/* ungotten char */
    return(TRUE);
  if (pindex > gindex)			/* buffered char */
    return(TRUE);
  if (_cursvar.raw)			/* raw mode test */
    return(_curseskeytst());
  return((bool)kbhit());		/* normal mode test */
  } /* _cursespendch */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -