1332 lines
37 KiB
C
1332 lines
37 KiB
C
//
|
|
// Copyright (C) 2001, 2000, 1999, Rildo Pragana, Jim Noeth,
|
|
// Andrew Cameron, David Essex.
|
|
// Copyright (C) 1993, 1991 Rildo Pragana.
|
|
//
|
|
// This library is free software; you can redistribute it and/or
|
|
// modify it under the terms of the GNU Lesser General Public License
|
|
// as published by the Free Software Foundation; either version 2.1,
|
|
// or (at your option) any later version.
|
|
//
|
|
// This library is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
// GNU Lesser General Public License for more details.
|
|
//
|
|
// You should have received a copy of the GNU Lesser General Public
|
|
// License along with this library; see the file COPYING.LIB. If
|
|
// not, write to the Free Software Foundation, Inc., 59 Temple Place,
|
|
// Suite 330, Boston, MA 02111-1307 USA
|
|
|
|
|
|
//
|
|
// Cobol Compiler Run Time Library -- Screen I/O functions
|
|
//
|
|
//
|
|
|
|
#include "htcoblib.h"
|
|
#include "mwindows.h"
|
|
|
|
#if defined(SunOS)
|
|
# include <curses.h>
|
|
#else
|
|
# if defined(__CYGWIN__)
|
|
# include <ncurses/ncurses.h>
|
|
# else
|
|
# if defined(__MINGW32__)
|
|
# include <curses.h> //# include <pdcurses.h>
|
|
# else
|
|
# include <curses.h>
|
|
# endif
|
|
# endif
|
|
#endif
|
|
|
|
#include "screenio.h"
|
|
#include "rterrors.h"
|
|
|
|
extern char *screen_status; // pointer to the screen status field
|
|
extern char *screen_cursor; // pointer to the cursor field
|
|
// walter
|
|
extern char *last_screen_status;
|
|
|
|
extern int bDecimalComma;
|
|
|
|
static int bScrIOInit = 0;
|
|
static char cDecimalChar = '.';
|
|
static struct ScrFld *_Fields_ = (struct ScrFld *)0;
|
|
|
|
#define get_first_field() (_Fields_)
|
|
#define set_first_field(f) (_Fields_=f)
|
|
|
|
static void set_cursor_yx(int,int);
|
|
|
|
void tcob_scr_process(int iAttr, int iLine, int line_sign, int iColumn,
|
|
int column_sign, int iFgColor, int iBgColor,int size,
|
|
struct fld_desc *fldScr, char *caScr, void *pInfo, ...);
|
|
|
|
static void free_scr_fields();
|
|
void cob_init_screen();
|
|
int tcob_isAlpha(char *p);
|
|
int tcob_isNumeric(char *p);
|
|
int tcob_picCharLen(unsigned char *p);
|
|
char tcob_classifyPic(char *p);
|
|
unsigned int tcob_picDecimalPointPosition(struct fld_desc *f);
|
|
unsigned int tcob_picTotalLen(char *p);
|
|
unsigned int tcob_picSignPosition(struct fld_desc *f);
|
|
int tcob_scr_scrl(void);
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
tcob_accept_curses
|
|
|
|
Similar to tcob_accept_std (basicio.c) but only called when position
|
|
options or on exception are given or with screenio initialized.
|
|
|
|
Simulates an accept of an screen section item, first calls
|
|
tcob_scr_process and the tcob_accept_screen
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
// walter acrescentei cor
|
|
int tcob_accept_curses( char *buffer, struct fld_desc *f, int flags, int cor ) {
|
|
int r,y;
|
|
struct fld_desc *f_tmp=NULL;
|
|
char *buffer_tmp=NULL;
|
|
// walter
|
|
int fg = -1, bg = -1; // walter
|
|
if(cor) {
|
|
fg = cor % 8;
|
|
bg = cor / 8;
|
|
}
|
|
// Nilo - 2007, May 28 - an ACCEPT with AT clause must use same previous foreground and background color on screen at first accepted character's position
|
|
#if defined(__MINGW32__)
|
|
else
|
|
{
|
|
short f, b;
|
|
chtype k = mvinch(tcob_scr_gety(),tcob_scr_getx());
|
|
pair_content(PAIR_NUMBER( k ), &f, &b );
|
|
fg = f;
|
|
bg = b;
|
|
}
|
|
#endif
|
|
// End Nilo
|
|
// fim walter
|
|
|
|
f_tmp = (struct fld_desc *)malloc(sizeof(struct fld_desc));
|
|
buffer_tmp = (char *)malloc(f->len);
|
|
|
|
if((!f_tmp)||(!buffer_tmp)) {
|
|
tcob_rt_error("screenio: tcob_accept_curses",TCERR_NO_MEM);
|
|
}
|
|
|
|
memcpy(f_tmp,f,sizeof(struct fld_desc));
|
|
|
|
if (flags & SCR_JUST_RIGHT) {
|
|
f_tmp->just_r = 1;
|
|
}
|
|
|
|
if (!(flags & SCR_UPDATE)) {
|
|
if ((f_tmp->type == DTYPE_ALPHANUMERIC) || (f_tmp->type == DTYPE_ALPHA) || (f_tmp->type == DTYPE_GROUP))
|
|
memset(buffer_tmp,' ',f_tmp->len);
|
|
else
|
|
memset(buffer_tmp,'0',f_tmp->len);
|
|
} else {
|
|
memcpy(buffer_tmp,buffer,f_tmp->len);
|
|
}
|
|
|
|
tcob_scr_process(flags, 0, 0, 0, 0, fg, bg, -1, f_tmp, buffer_tmp, f_tmp, buffer_tmp, f_tmp, buffer_tmp);
|
|
|
|
r = tcob_accept_screen();
|
|
|
|
/*tcob_move(f_tmp,buffer_tmp,f,buffer);*/
|
|
memcpy(buffer, buffer_tmp, f->len);
|
|
|
|
if ( f_tmp != NULL ) {
|
|
free(f_tmp);
|
|
f_tmp = NULL;
|
|
}
|
|
|
|
if ( buffer_tmp != NULL ) {
|
|
free(buffer_tmp);
|
|
buffer_tmp = NULL ;
|
|
}
|
|
|
|
y=tcob_scr_gety();
|
|
|
|
if (!(flags & SCR_NO_ADVANCING)) { // no advancing?
|
|
if (!tcob_scr_scrl()) {
|
|
set_cursor_yx(y + 1 , 0);
|
|
}
|
|
//set_cursor_yx(y + 1 , 1);
|
|
}
|
|
|
|
if ( r == TCOBKEY_RETURN || r == TCOBKEY_ENTER)
|
|
r=0;
|
|
|
|
return r;
|
|
}
|
|
/*int accept_curses_old( char *buffer, struct fld_desc *f, int flags ) {
|
|
int i, r, x, y, x0, y0, bEndLoop, first=1;
|
|
int action;
|
|
static char *szBuf = NULL;
|
|
int tmp, len = f->len;
|
|
int ib; // szBuf offset
|
|
unsigned int picLen;
|
|
struct fld_desc f1 = {0,DTYPE_ALPHANUMERIC,0,0,0,0,0,0,0,0,NULL};
|
|
|
|
cob_init_screen();
|
|
// we alloc the line buffer only at the first time
|
|
if (!szBuf)
|
|
szBuf=malloc(RLBUF_SIZE);
|
|
// check if UPDATE was given (copy input field to szBuf and show it)
|
|
getyx(stdscr,y0,x0);
|
|
if (flags & SCR_UPDATE) {
|
|
strncpy(szBuf,buffer,len);
|
|
getyx(stdscr,y,x);
|
|
for (i=0; i<len; i++)
|
|
addch(buffer[i]);
|
|
set_cursor_yx(y,x);
|
|
} else {
|
|
if ((f->type == DTYPE_ALPHANUMERIC)||
|
|
(f->type == DTYPE_ALPHA)||
|
|
(f->type == DTYPE_GROUP))
|
|
memset(szBuf,' ',len);
|
|
else
|
|
memset(szBuf,'0',len);
|
|
}
|
|
|
|
// do the accept
|
|
szBuf[len] = '\0';
|
|
ib=0;
|
|
for (bEndLoop=0; !bEndLoop; ) {
|
|
r=getch();
|
|
action = _get_action_for_key(r);
|
|
switch (action) {
|
|
case EDIT_BACKSPACE:
|
|
if (ib > 0) {
|
|
ib--;
|
|
if (ib < len)
|
|
memmove(szBuf+ib,szBuf+ib+1,len-ib);
|
|
szBuf[len-1]=' ';
|
|
getyx(stdscr,y,x);
|
|
x--;
|
|
set_cursor_yx(y,x);
|
|
for (tmp=ib;tmp<len;tmp++)
|
|
addch(szBuf[tmp]);
|
|
set_cursor_yx(y,x);
|
|
}
|
|
break;
|
|
case EDIT_RIGHT:
|
|
if (ib < len) {
|
|
ib++;
|
|
getyx(stdscr,y,x);
|
|
x++;
|
|
set_cursor_yx(y,x);
|
|
}
|
|
break;
|
|
case EDIT_DOWN_FIELD:
|
|
case EDIT_NEXT_FIELD:
|
|
if(ib < len) {
|
|
memset(szBuf+ib, ' ', len-ib);
|
|
addch_set(' ', len-ib);
|
|
ib = len;
|
|
}
|
|
r = 0x0d; // simulate a <Return> key
|
|
bEndLoop++;
|
|
break;
|
|
case TCOBKEY_HOMECLR:
|
|
//getyx(stdscr,y,x);
|
|
//x -= ib;
|
|
ib = 0;
|
|
if ((f->type == DTYPE_ALPHANUMERIC)||
|
|
(f->type == DTYPE_ALPHA)||
|
|
(f->type == DTYPE_GROUP))
|
|
memset(szBuf,' ',len);
|
|
else
|
|
memset(szBuf,'0',len);
|
|
set_cursor_yx(y0,x0);
|
|
for (i=0; i<len; i++)
|
|
addch(szBuf[i]);
|
|
set_cursor_yx(y0,x0);
|
|
break;
|
|
default:
|
|
// allow accented (portuguese, french, ...) chars as well
|
|
if (r < ' ' || r > 0xff || r == 0x7f) {
|
|
if (first)
|
|
ib = len;
|
|
bEndLoop++;
|
|
} else {
|
|
first=0;
|
|
if (ib < len) {
|
|
szBuf[ib++] = r;
|
|
addch(r);
|
|
}
|
|
if ((ib >= len) && (flags & SCR_AUTO)) {
|
|
bEndLoop++;
|
|
r = 0x0d; // simulate a <Return> key
|
|
}
|
|
}
|
|
}
|
|
}
|
|
if (r == 0x0d || r == 0x0a) {
|
|
r = 0;
|
|
}
|
|
if (flags & SCR_JUST_RIGHT) {
|
|
// trim right blanks
|
|
for (ib=len-1; (szBuf[ib] == ' ') && (ib > 0); ib--) ;
|
|
ib++;
|
|
memmove(szBuf+len-ib, szBuf, ib);
|
|
if ((f->type == DTYPE_ALPHANUMERIC)||
|
|
(f->type == DTYPE_ALPHA)||
|
|
(f->type == DTYPE_GROUP))
|
|
memset(szBuf,' ',len-ib);
|
|
else
|
|
memset(szBuf,'0',len-ib);
|
|
// update screen with the field justified right
|
|
set_cursor_yx(y0,x0);
|
|
for (i=0; i<len; i++)
|
|
addch(szBuf[i]);
|
|
}
|
|
f1.len = strlen(szBuf);
|
|
picLen = tcob_picReqLen(1);
|
|
f1.pic = (char *)malloc(picLen);
|
|
tcob_picCreate (f1.pic, picLen, 'X', f1.len, NULL);
|
|
tcob_move( &f1,szBuf,f,buffer );
|
|
free(f1.pic);
|
|
return r;
|
|
}*/
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
tcob_display_curses
|
|
|
|
Similar to tcob_display_std (basicio.c) but only called when position
|
|
options are given or with screenio initialized.
|
|
|
|
Simulates a display of an screen section item, first calls
|
|
tcob_scr_process and the tcob_display_screen
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
// walter acrescentei cor
|
|
void tcob_display_curses( struct fld_desc *f, char *s, int dspflags, int cor ) {
|
|
int y;
|
|
// walter
|
|
int fg = -1, bg = -1; // walter
|
|
if(cor) {
|
|
fg = cor % 8;
|
|
bg = cor / 8;
|
|
}
|
|
// Nilo - 2007, May 28 - a DISPLAY with AT clause must use same previous foreground and background color on screen at first displayed character's position
|
|
#if defined(__MINGW32__)
|
|
else
|
|
{
|
|
short f, b;
|
|
chtype k = mvinch(tcob_scr_gety(),tcob_scr_getx());
|
|
pair_content(PAIR_NUMBER( k ), &f, &b );
|
|
fg = f;
|
|
bg = b;
|
|
}
|
|
#endif
|
|
// End Nilo
|
|
// fim walter
|
|
|
|
tcob_scr_process(dspflags, 0, 0, 0,0,fg,bg,-1,f,s,NULL);
|
|
|
|
tcob_display_screen();
|
|
|
|
y=tcob_scr_gety();
|
|
|
|
if (!(dspflags & SCR_NO_ADVANCING)) // no advancing?
|
|
if (!tcob_scr_scrl()) {
|
|
set_cursor_yx(y + 1 , 0);
|
|
}
|
|
//set_cursor_yx(y + 1 , 1);
|
|
refresh();
|
|
}
|
|
/*
|
|
void display_curses_old( struct fld_desc *f, char *s, int dspflags ) {
|
|
char *buffer;
|
|
unsigned int i;
|
|
struct fld_desc ftmp;
|
|
unsigned int picLen;
|
|
int domove=0;
|
|
int x,y;
|
|
unsigned int len;
|
|
|
|
cob_init_screen();
|
|
if (dspflags & 2) { // erase?
|
|
getyx(stdscr,y,x);
|
|
erase();
|
|
set_cursor_yx(y,x);
|
|
}
|
|
if (dspflags & 4) { // erase to end of line?
|
|
getyx(stdscr,y,x);
|
|
clrtoeol();
|
|
set_cursor_yx(y,x);
|
|
}
|
|
if ((f->type == DTYPE_DISPLAY)
|
|
|| (f->type == DTYPE_PACKED)
|
|
|| (f->type == DTYPE_BININT)
|
|
|| (f->type == DTYPE_FLOAT)) {
|
|
domove++;
|
|
memmove(&ftmp,f,sizeof(ftmp));
|
|
len = tcob_picCompLength(f) + tc_abs((char)f->pscale);
|
|
//printf("display: type=%c, len=%d, decimals=%d\n",
|
|
// f->type, f->len, f->decimals);
|
|
|
|
picLen = tcob_picReqLen(4);
|
|
ftmp.pic = (char *)malloc(picLen);
|
|
tcob_picCreate (ftmp.pic, picLen, NULL);
|
|
if(tcob_picElemVal(f->pic,0) == 'S')
|
|
tcob_picAppend (ftmp.pic, picLen, '-', 1, NULL);
|
|
if (ftmp.decimals <= 0) {
|
|
tcob_picAppend (ftmp.pic, picLen, '9', len, NULL);
|
|
} else if (tcob_picElemVal(f->pic,0) == 'P' || // unsigned scaled
|
|
tcob_picElemVal(f->pic,1) == 'P') { // signed scaled
|
|
tcob_picAppend (ftmp.pic, picLen,
|
|
cDecimalChar, 1,
|
|
'9', ftmp.decimals, NULL);
|
|
} else {
|
|
tcob_picAppend (ftmp.pic, picLen,
|
|
'9', len - ftmp.decimals,
|
|
cDecimalChar, 1,
|
|
'9', ftmp.decimals, NULL);
|
|
}
|
|
ftmp.type = DTYPE_EDITED;
|
|
if(tcob_picElemVal(f->pic,0) == 'S') // account for the sign
|
|
len++;
|
|
if (ftmp.decimals > 0) // account for the decimal point
|
|
len++;
|
|
ftmp.len = len;
|
|
buffer = malloc(len);
|
|
tcob_move(f,s,&ftmp,buffer);
|
|
free(ftmp.pic);
|
|
} else {
|
|
len = f->len;
|
|
buffer = s;
|
|
}
|
|
|
|
for (i=0; i<len; i++)
|
|
addch(buffer[i]);
|
|
if ((dspflags & 1)==0) // no advancing?
|
|
addch('\n');
|
|
refresh();
|
|
if (domove)
|
|
free(buffer);
|
|
}*/
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
tcob_goxy_expr
|
|
|
|
Position cursor at the screen with screen plugin.
|
|
Called only if DISPLAY or ACCEPT statements generated with
|
|
position-spec is found.
|
|
Uses double coords because allow any arbitrary expressions.
|
|
|
|
tcob_goxy
|
|
tcob_go_y
|
|
tcob_go_x
|
|
|
|
The same functionality but using intgers.
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
void tcob_goxy_expr ( double x, double y ) {
|
|
tcob_init_screen();
|
|
set_cursor_yx((int)y-1,(int)x-1);
|
|
}
|
|
|
|
void tcob_gox_expr ( double x) {
|
|
tcob_init_screen();
|
|
set_cursor_yx(tcob_scr_gety(),(int)x-1);
|
|
}
|
|
|
|
void tcob_goy_expr ( double y) {
|
|
tcob_init_screen();
|
|
set_cursor_yx((int)y-1,tcob_scr_getx());
|
|
}
|
|
|
|
void tcob_goxy ( int x, int y ) {
|
|
tcob_init_screen();
|
|
set_cursor_yx(y-1,x-1);
|
|
}
|
|
|
|
void tcob_goxy_variable ( char *var, int len ) {
|
|
int x,y,pos;
|
|
char tmp[7];
|
|
|
|
tcob_init_screen();
|
|
|
|
/* len should be 4 or 6 */
|
|
if ((len != 4) && (len != 6))
|
|
tcob_rt_error("screenio: tcob_goxy_variable",TCERR_EMPTY,"bad arguments");
|
|
strncpy(tmp,var,len);
|
|
pos=atoi(tmp);
|
|
if (len == 6) {
|
|
y = pos / 1000;
|
|
x = pos - (1000 * y);
|
|
} else {
|
|
y = pos / 100;
|
|
x = pos - (100 * y);
|
|
}
|
|
|
|
set_cursor_yx(y-1,x-1);
|
|
}
|
|
|
|
void tcob_go_x ( int x,int sign) {
|
|
tcob_init_screen();
|
|
|
|
if(x==0)
|
|
return;
|
|
|
|
if (sign != 0) {
|
|
x = tcob_scr_getx() + (sign * x);
|
|
} else {
|
|
x--;
|
|
}
|
|
|
|
set_cursor_yx(tcob_scr_gety(),x );
|
|
}
|
|
|
|
void tcob_go_y ( int y,int sign ) {
|
|
tcob_init_screen();
|
|
|
|
if(y==0)
|
|
return;
|
|
|
|
if (sign != 0) {
|
|
y=tcob_scr_gety() + (sign * y);
|
|
} else {
|
|
y--;
|
|
}
|
|
|
|
set_cursor_yx(y,tcob_scr_getx());
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
get_next_input_field
|
|
get_prev_input_field
|
|
|
|
This are helper functions for tcob_accept_screen to help
|
|
moving between fields.
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
struct ScrFld *get_next_input_field(struct ScrFld *p) {
|
|
struct ScrFld *pFld;
|
|
/* find next input field in chain */
|
|
for (pFld=p->pNext; pFld; pFld=pFld->pNext) {
|
|
if(pFld->fldTo)
|
|
return pFld;
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
struct ScrFld *get_prev_input_field(struct ScrFld *p) {
|
|
struct ScrFld *pFldAux, *pNext;
|
|
|
|
/* find prev input field in chain */
|
|
pFldAux = get_first_field();
|
|
|
|
if (pFldAux->fldTo == NULL)
|
|
pFldAux = get_next_input_field(pFldAux);
|
|
|
|
for(; pFldAux; pFldAux=pNext) {
|
|
pNext = get_next_input_field(pFldAux);
|
|
if (p == pNext)
|
|
return pFldAux;
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
prepare_field - Prepare the string to be accepted or moved
|
|
|
|
prepare_dest_field - Prepare the destination field for make a move to
|
|
'to' field
|
|
prepare_input_field - Prepare the input field to make it easy to accept
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
static void prepare_field(char *ca,int len) {
|
|
int j=0;
|
|
int i=0;
|
|
int spaces_after_data=0;
|
|
int data_found=0;
|
|
|
|
// Numeric or edited field
|
|
// Only accepted 0123456789+-., and spaces before and after input
|
|
|
|
for(i=0;i < len;i++) {
|
|
if((ca[i]=='+')||
|
|
(ca[i]=='-')||
|
|
(ca[i]=='.')||
|
|
(ca[i]==',')||
|
|
((ca[i] >= '0') && (ca[i] <='9'))) { // accepted chars
|
|
if (!spaces_after_data) {
|
|
data_found++;
|
|
ca[j]=ca[i];
|
|
j++;
|
|
}
|
|
// spaces or incorrect char
|
|
} else if((ca[i] == ' ') && (data_found)) {
|
|
spaces_after_data++;
|
|
}
|
|
} //for
|
|
memset(ca+j, ' ', len-j);
|
|
}
|
|
void prepare_dest_field(struct ScrFld *pFld) {
|
|
if(pFld->fldScr.type != DTYPE_ALPHANUMERIC &&
|
|
pFld->fldScr.type != DTYPE_ACCEPT_DISPLAY)
|
|
prepare_field(pFld->caScr,pFld->fldScr.len);
|
|
return;
|
|
}
|
|
void prepare_input_field(struct ScrFld *pFld) {
|
|
if(pFld->fldScr.type != DTYPE_ALPHANUMERIC)
|
|
prepare_field(pFld->caWk,pFld->fldScr.len);
|
|
return;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| tcob_accept_screen |
|
|
| Calls to this routine are generated by the compiler when an ACCEPT |
|
|
| verb with an assocated screeen section name is encountered. The |
|
|
| routine takes no arguments, but assumes that the routine |
|
|
| tcob_scr_process has been called once for each field in the referenced |
|
|
| screen. The tcob_scr_process builds a linked list of ScrFld structures |
|
|
| with one structure per field in the screen. This linked list is |
|
|
| referenced to by the external variable _Fields_. Upon exit from this |
|
|
| routine, all memory associated with these structures is freed. |
|
|
| |
|
|
| Input is accepted from any field that has a destination or "To" |
|
|
| field associated with it. The routine accepts keyboard input and that |
|
|
| input is edited to insure that it is valid for the type of field |
|
|
| that was described in the screen section. |
|
|
| |
|
|
| Control stays in this routine until a carrage return is received, |
|
|
| then, corresponding data is moved to all receiving fields, memory |
|
|
| is freed, the screen mode is reset and the routine exits back to the |
|
|
| calling mainline program. |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
int tcob_accept_screen() {
|
|
int key_status;
|
|
struct ScrFld *pFld;
|
|
char tmp[5];
|
|
|
|
tcob_init_screen();
|
|
//
|
|
// Accept all the fields
|
|
//
|
|
pFld=get_first_field();
|
|
key_status = tcob_scr_accept(pFld);
|
|
// If exists the SCREEN STATUS field move the value to it .
|
|
// The SCREEN STATUS field is a PIC X(4) or 9(4) display
|
|
//
|
|
if (!(screen_status==NULL)) {
|
|
tmp[4]='\0';
|
|
snprintf(tmp,5,"%4.4u",key_status);
|
|
memcpy(screen_status,tmp,4);
|
|
}
|
|
// walter
|
|
if(last_screen_status == NULL)
|
|
last_screen_status = malloc(sizeof(char) * 5);
|
|
|
|
tmp[4]='\0';
|
|
snprintf(tmp, 5, "%4.4u", key_status);
|
|
memcpy(last_screen_status, tmp, 4);
|
|
// fim_walter
|
|
|
|
// Move data to 'to' fields
|
|
for(pFld=get_first_field(); pFld; pFld=pFld->pNext) {
|
|
if (pFld->fldTo) {
|
|
if (pFld->caWk != pFld->caScr) {
|
|
if (pFld->caScrCopy != NULL) {
|
|
free(pFld->fldScr.pic);
|
|
free(pFld->caScr);
|
|
pFld->caScr = pFld->caScrCopy;
|
|
memcpy(&(pFld->fldScr), &(pFld->fldScrCopy), sizeof(struct fld_desc));
|
|
}
|
|
tcob_move(&pFld->fldWk, pFld->caWk, &pFld->fldScr, pFld->caScr);
|
|
}
|
|
if (pFld->caScr != pFld->caTo) {
|
|
prepare_dest_field(pFld);
|
|
tcob_move(&pFld->fldScr, pFld->caScr, pFld->fldTo, pFld->caTo);
|
|
}
|
|
}
|
|
}
|
|
|
|
free_scr_fields(); // free Fields
|
|
return key_status;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
tcob_display_screen
|
|
Calls to this routine are generated by the compiler when an DISPLAY
|
|
verb with an assocated screeen section name is encountered. The
|
|
routine takes no arguments, but assumes that the routine
|
|
tcob_scr_process has been called once for each field in the referenced
|
|
screen. The tcob_scr_process builds a linked list of ScrFld structures
|
|
with one structure per field in the screen. This linked list is
|
|
referenced to by the external variable Fields. Upon exit from this
|
|
routine, all memory associated with these structures is freed.
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
void tcob_display_screen() {
|
|
tcob_init_screen();
|
|
tcob_scr_display(get_first_field());
|
|
free_scr_fields();
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
|
|
tcob_scr_process
|
|
|
|
\*-------------------------------------------------------------------------*/
|
|
void tcob_scr_process(int iAttr, int iLine, int line_sign, int iColumn,
|
|
int column_sign, int iFgColor, int iBgColor, int size,
|
|
struct fld_desc *fldScr, char *caScr, void *pInfo, ...) {
|
|
va_list ap;
|
|
|
|
int bIsAlpha;
|
|
int bIsDisplay;
|
|
int bIsEdited;
|
|
int bDecPoint;
|
|
unsigned int iCharCnt,caSize;
|
|
unsigned int iDecCnt;
|
|
struct ScrFld *pFld;
|
|
void *pWk;
|
|
struct fld_desc *pfldTmp;
|
|
|
|
|
|
tcob_init_screen();
|
|
|
|
pFld = get_first_field();
|
|
|
|
if (pFld == NULL) {
|
|
pFld = (struct ScrFld *)malloc(sizeof(struct ScrFld));
|
|
if(!pFld) {
|
|
tcob_rt_error("screenio: tcob_scr_process",TCERR_NO_MEM);
|
|
return;
|
|
}
|
|
set_first_field(pFld);
|
|
} else {
|
|
while(pFld->pNext) {
|
|
pFld = pFld->pNext;
|
|
}
|
|
pFld->pNext = (struct ScrFld *)malloc(sizeof(struct ScrFld));
|
|
if(!pFld->pNext) {
|
|
tcob_rt_error("screenio: tcob_scr_process",TCERR_NO_MEM);
|
|
return;
|
|
}
|
|
pFld = pFld->pNext;
|
|
}
|
|
pFld->pNext = (struct ScrFld *)0;
|
|
|
|
va_start(ap, pInfo);
|
|
pWk = pInfo;
|
|
pFld->fldFrom = (struct fld_desc *)pWk;
|
|
if(pWk) {
|
|
pWk = va_arg(ap, void *);
|
|
pFld->caFrom = (char *)pWk;
|
|
} else {
|
|
pFld->caFrom = (char *)0;
|
|
}
|
|
pWk = va_arg(ap, void *);
|
|
pFld->fldTo = (struct fld_desc *)pWk;
|
|
if(pWk) {
|
|
pWk = va_arg(ap, void *);
|
|
pFld->caTo = (char *)pWk;
|
|
} else
|
|
pFld->caTo = (char *)0;
|
|
|
|
pFld->iAttributes = iAttr;
|
|
|
|
if (iLine)
|
|
switch(line_sign) {
|
|
case 1:
|
|
pFld->iLine = tcob_scr_gety() + iLine;
|
|
break;
|
|
case -1:
|
|
pFld->iLine = tcob_scr_gety() - iLine;
|
|
break;
|
|
default:
|
|
pFld->iLine = iLine - 1;
|
|
break;
|
|
}
|
|
else {
|
|
pFld->iLine = tcob_scr_gety();
|
|
}
|
|
|
|
if (tcob_scr_gety() != pFld->iLine)
|
|
tcob_scr_setx(0);
|
|
|
|
tcob_scr_sety(pFld->iLine);
|
|
|
|
if(iColumn)
|
|
switch(column_sign) {
|
|
case 1:
|
|
pFld->iCol = tcob_scr_getx() + iColumn;
|
|
break;
|
|
case -1:
|
|
pFld->iCol = tcob_scr_getx() - iColumn;
|
|
break;
|
|
default:
|
|
pFld->iCol = iColumn - 1;
|
|
break;
|
|
}
|
|
else {
|
|
pFld->iCol = tcob_scr_getx();
|
|
}
|
|
tcob_scr_setx(pFld->iCol);
|
|
pFld->iFgColor = iFgColor;
|
|
if ((iFgColor > 0 ) && (iFgColor & 0x00000008)) {
|
|
pFld->iAttributes |= SCR_HIGHLIGHT ;
|
|
}
|
|
pFld->iBgColor = iBgColor;
|
|
|
|
memcpy(&(pFld->fldScr), fldScr, sizeof(struct fld_desc));
|
|
memcpy(&(pFld->fldScrCopy), fldScr, sizeof(struct fld_desc));
|
|
pFld->caScr = caScr;
|
|
pFld->caScrCopy = NULL;
|
|
bDecPoint = 0;
|
|
bIsAlpha = 0;
|
|
bIsDisplay = 0;
|
|
bIsEdited = 0;
|
|
iCharCnt = 0;
|
|
iDecCnt = 0;
|
|
if ((pFld->fldScr.type==DTYPE_GROUP) || (pFld->fldScr.pic==NULL)) {
|
|
int picLen;
|
|
picLen = tcob_picReqLen(1);
|
|
pFld->fldScr.pic = (char *)malloc(picLen);
|
|
tcob_picCreate (pFld->fldScr.pic, picLen, 'X', pFld->fldScr.len, NULL);
|
|
}
|
|
|
|
if (EDITEDFIELD(pFld->fldScr.type)) {
|
|
bIsEdited = 1;
|
|
iCharCnt = pFld->len = tcob_picEditedCompLength(&pFld->fldScr);
|
|
iDecCnt = pFld->decimals = tcob_picEditedCompDecimals(&pFld->fldScr);
|
|
}
|
|
else if (DISPLAYFIELD(pFld->fldScr.type) ||
|
|
!((pFld->iAttributes & SCR_IS_REFMOD) ||
|
|
tcob_isAlpha(pFld->fldScr.pic))) {
|
|
if (tcob_isNumeric(pFld->fldScr.pic)) { // walter acrescentei o S 13-12-05
|
|
int signP = tcob_picSignPosition(&pFld->fldScr);
|
|
int picLen;
|
|
int t;
|
|
iCharCnt = pFld->len = tcob_picCompLength(&pFld->fldScr);
|
|
iDecCnt = pFld->decimals = pFld->fldScr.decimals;
|
|
pFld->caScrCopy = pFld->caScr; /* save the original area */
|
|
picLen = strlen(pFld->fldScr.pic) + 3;
|
|
pFld->fldScr.pic = (char *)malloc(picLen);
|
|
t = iCharCnt-iDecCnt;
|
|
tcob_picCreate (pFld->fldScr.pic, picLen, NULL);
|
|
if (pFld->fldScr.type == 'D') {
|
|
if (t) {
|
|
tcob_picAppend (pFld->fldScr.pic, picLen, '9', t, NULL);
|
|
}
|
|
} else {
|
|
if (t > 1)
|
|
tcob_picAppend (pFld->fldScr.pic, picLen, 'Z', t - 1, NULL);
|
|
if (t > 0)
|
|
tcob_picAppend (pFld->fldScr.pic, picLen, '9', 1, NULL);
|
|
}
|
|
if (iDecCnt > 0) {
|
|
tcob_picAppend (pFld->fldScr.pic, picLen, CDECIMALPOINT, 1,
|
|
'9', iDecCnt, NULL);
|
|
iCharCnt++; /* count the decimal point */
|
|
}
|
|
if (signP >= 0) {
|
|
tcob_picAppend (pFld->fldScr.pic, picLen, '+', 1, NULL);
|
|
iCharCnt++; /* count the sign */
|
|
}
|
|
pFld->fldScr.type = DTYPE_EDITED;
|
|
pFld->fldScrCopy.type = '9';
|
|
bIsEdited = 1;
|
|
bIsDisplay = 0;
|
|
pFld->fldScr.len = iCharCnt;
|
|
pFld->len = tcob_picEditedCompLength(&pFld->fldScr);
|
|
caSize = tcob_picTotalLen(pFld->fldScr.pic);
|
|
pFld->caScr = (char*)malloc(caSize);
|
|
tcob_move(&pFld->fldScrCopy, pFld->caScrCopy,
|
|
&pFld->fldScr, pFld->caScr);
|
|
} else {
|
|
/* numeric-edited with a separate picture,
|
|
must have the picture required at the screen section */
|
|
iCharCnt = pFld->len = tcob_picEditedCompLength(&pFld->fldScr);
|
|
caSize = tcob_picTotalLen(pFld->fldScr.pic);
|
|
pFld->caScr = (char*)malloc(caSize);
|
|
pFld->fldScr.type = 'E';
|
|
}
|
|
} else {
|
|
bIsAlpha = 1;
|
|
iCharCnt = pFld->len = pFld->fldScr.len;
|
|
iDecCnt = pFld->decimals = 0;
|
|
}
|
|
if (pFld->iAttributes & SCR_IS_REFMOD) {
|
|
pFld->decimalPointPosition = pFld->len;
|
|
pFld->signPosition = -1;
|
|
} else {
|
|
pFld->decimalPointPosition =
|
|
tcob_picDecimalPointPosition(&pFld->fldScr);
|
|
pFld->signPosition =
|
|
tcob_picSignPosition(&pFld->fldScr);
|
|
}
|
|
|
|
//if(pFld->fldTo) { /* if we have a destination field */
|
|
|
|
if ((size > 1) && ((unsigned int)size < iCharCnt)) { /* size clause */
|
|
iCharCnt = (unsigned int)size;
|
|
}
|
|
pFld->fldWk.len = iCharCnt;
|
|
pFld->fldWk.decimals = iDecCnt;
|
|
pFld->fldScr.decimals = iDecCnt;
|
|
/*if(bIsEdited)
|
|
pFld->fldWk.type = DTYPE_DISPLAY;
|
|
else if(!bIsAlpha)
|
|
pFld->fldWk.type = DTYPE_DISPLAY;
|
|
else
|
|
pFld->fldWk.type = DTYPE_ALPHANUMERIC;*/
|
|
pFld->fldWk.just_r=0;
|
|
pFld->fldWk.all = 0;
|
|
pFld->fldWk.pscale = 0;
|
|
pFld->fldWk.pic = pFld->caPicWk;
|
|
|
|
/* RP -- classify our work field */
|
|
if (pFld->fldScrCopy.type == 'D') {
|
|
pFld->fldWk.type = tcob_classifyPic(pFld->fldScrCopy.pic);
|
|
if (pFld->fldWk.type == 'E') {
|
|
if (tcob_isNumEdit(pFld->fldScrCopy.pic))
|
|
pFld->fldWk.type = '9';
|
|
}
|
|
if (pFld->fldFrom != NULL) {
|
|
pfldTmp=pFld->fldFrom;
|
|
} else if (pFld->fldTo != NULL) {
|
|
pfldTmp=pFld->fldTo;
|
|
} else {
|
|
pfldTmp = NULL;
|
|
}
|
|
/*if (pfldTmp) {
|
|
pFld->fldWk.len = pfldTmp->len;
|
|
pFld->fldWk.decimals = pfldTmp->decimals;
|
|
pFld->fldWk.pic = pfldTmp->pic;
|
|
}*/
|
|
/* get all other info from the picture */
|
|
//pfld->fldWk.len = tcob_picCharLen(pFld->fldScrCopy.pic);
|
|
pFld->fldWk.decimals = tcob_picEditedCompDecimals(&pFld->fldScr);
|
|
pFld->fldWk.separate_sign=0;
|
|
pFld->fldWk.leading_sign=0;
|
|
} else if (DISPLAYFIELD(pFld->fldScr.type) ||
|
|
(EDITEDFIELD(pFld->fldScr.type) &&
|
|
tcob_isNumEdit(pFld->fldScr.pic))) {
|
|
pFld->fldWk.type = DTYPE_DISPLAY;
|
|
tcob_picCreate (pFld->caPicWk, 20, NULL);
|
|
if (pFld->signPosition >= 0) {
|
|
tcob_picAppend (pFld->caPicWk, 20, 'S', 1, NULL);
|
|
pFld->fldWk.len++;
|
|
pFld->fldWk.separate_sign=1;
|
|
pFld->fldWk.leading_sign=1;
|
|
}
|
|
tcob_picAppend (pFld->caPicWk, 20, '9', iCharCnt-iDecCnt, NULL);
|
|
if(HASDECIMALPOINT)
|
|
tcob_picAppend (pFld->caPicWk, 20, 'V', 1,
|
|
'9', iDecCnt, NULL);
|
|
} else {
|
|
pFld->fldWk.type = DTYPE_ALPHANUMERIC;
|
|
tcob_picCreate (pFld->caPicWk, 20, 'X', pFld->fldScr.len,NULL);
|
|
if (pFld->iAttributes & SCR_IS_REFMOD) {
|
|
pFld->fldWk.len = pFld->fldScr.len;
|
|
} else {
|
|
pFld->fldWk.len = (unsigned long int)tcob_picCharLen((unsigned char *)pFld->fldScr.pic);
|
|
}
|
|
}
|
|
/* if((pFld->fldWk.type == DTYPE_DISPLAY)
|
|
|| (pFld->fldWk.type == DTYPE_EDITED)) {
|
|
tcob_picCreate (pFld->caPicWk, 20, NULL);
|
|
if (pFld->signPosition >= 0)
|
|
tcob_picAppend (pFld->caPicWk, 20, 'S', 1, NULL);
|
|
tcob_picAppend (pFld->caPicWk, 20, '9', iCharCnt-iDecCnt, NULL);
|
|
if(HASDECIMALPOINT)
|
|
tcob_picAppend (pFld->caPicWk, 20, 'V', 1,
|
|
'9', iDecCnt, NULL);
|
|
} else
|
|
tcob_picCreate (pFld->caPicWk, 20, 'X', pFld->fldScr.len,NULL);
|
|
*/
|
|
pFld->caWk = (char *)malloc(pFld->fldWk.len+2);
|
|
|
|
if ((pFld->fldFrom) && (pFld->caFrom != pFld->caScr )) {
|
|
tcob_move(pFld->fldFrom, pFld->caFrom, &pFld->fldScr, pFld->caScr);
|
|
}
|
|
|
|
tcob_move(&pFld->fldScr, pFld->caScr, &pFld->fldWk, pFld->caWk);
|
|
|
|
/*} else
|
|
pFld->caWk = (char *)0;*/
|
|
|
|
pFld->iFldPos = 0;
|
|
pFld->iScrPos = 0;
|
|
tcob_scr_setx(tcob_scr_getx()+ pFld->fldScr.len);
|
|
|
|
refresh();
|
|
return;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| free_scr_fields |
|
|
| Frees memory used by the fields prepared by tcob_scr_process |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
static void free_scr_fields() {
|
|
struct ScrFld *pFld, *next;
|
|
|
|
for (pFld=_Fields_; pFld; pFld=next) {
|
|
next = pFld->pNext;
|
|
if (pFld->caWk) free (pFld->caWk);
|
|
if (pFld) free (pFld);
|
|
}
|
|
_Fields_ = (struct ScrFld *)NULL;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| set_cursor_yx |
|
|
| Move the cursor to the X Y position. It a layer for the curses |
|
|
| move function. |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
static void set_cursor_yx(int y,int x) {
|
|
|
|
tcob_scr_setyx(y,x);
|
|
/*
|
|
* If exists the CURSOR field move the value to it .
|
|
* The CURSOR field is a PIC X(6) or 9(6) display
|
|
*/
|
|
if (!(screen_cursor==NULL)) {
|
|
char tmp[6];
|
|
sprintf(tmp,"%3.3u%3.3u",tcob_scr_gety(),tcob_scr_getx());
|
|
memcpy(screen_cursor,tmp,6);
|
|
}
|
|
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| tcob_accept_inkey |
|
|
| Move 1 to field if there is a typed key in the buffer, 0 if not. |
|
|
| This version uses curses. |
|
|
\*-------------------------------------------------------------------------*/
|
|
int tcob_accept_inkey(struct fld_desc *f, char *buffer ) {
|
|
struct fld_desc ftmp = {1,DTYPE_ALPHANUMERIC,0,0,0,0,0,0,0,0,NULL};
|
|
char ctmp[1];
|
|
if (tcob_scr_kbdstatus()) {
|
|
ctmp[0]='1';
|
|
} else {
|
|
ctmp[0]='0';
|
|
}
|
|
tcob_move(&ftmp,ctmp,f,buffer);
|
|
return 0;
|
|
}
|
|
|
|
// walter
|
|
// put last escape character in cobol variable
|
|
int tcob_accept_escapekey(char *buffer ) {
|
|
memcpy(buffer, last_screen_status, 4);
|
|
return 0;
|
|
}
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| do_putch_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
/*
|
|
void do_putch_terminal(char c) {
|
|
int x,y;
|
|
int mx, my;
|
|
|
|
getyx(stdscr, y, x);
|
|
getmaxyx(stdscr, my, mx);
|
|
|
|
if(c>31)
|
|
addch(c);
|
|
else if(c=='\t') {
|
|
do {
|
|
addch(' ');
|
|
x++;
|
|
if(x==mx) {
|
|
x=0;
|
|
if(y<my)
|
|
y++;
|
|
set_cursor_yx(y,x);
|
|
return;
|
|
}
|
|
} while(x%8);
|
|
} else if(c=='\n') {
|
|
if(y<my)
|
|
set_cursor_yx(y+1, x);
|
|
} else if(c=='\r') {
|
|
set_cursor_yx(y,0);
|
|
}
|
|
}
|
|
|
|
*/
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| tcob_init_screen |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
void tcob_init_screen(void) {
|
|
|
|
if (bScrIOInit) // No need to initilize more than once
|
|
return;
|
|
if (bDecimalComma)
|
|
cDecimalChar = ',';
|
|
|
|
tcob_scr_init();
|
|
|
|
bScrIOInit++;
|
|
}
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| display_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void display_terminal(char *buf, int len) {
|
|
int i;
|
|
// char *tbuf=buf;
|
|
|
|
// while(*buf)
|
|
for(i=0; i<len; i++)
|
|
do_putch_terminal(buf[i]);
|
|
refresh();
|
|
}
|
|
|
|
*/
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| newline_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void newline_terminal(void) {
|
|
do_putch_terminal('\n');
|
|
}
|
|
|
|
*/
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| display_erase_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void display_erase_terminal(void) {
|
|
clear();
|
|
refresh();
|
|
}*/
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| tcob_do_scrio_finish |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
void tcob_do_scrio_finish(void) {
|
|
if (bScrIOInit) {
|
|
tcob_scr_finish();
|
|
}
|
|
}
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| outit_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void outit_terminal(void) {
|
|
write(2, "BRK",3);
|
|
}*/
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| outeek_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void outeek_terminal(void) {
|
|
write(2, "CNT",3);
|
|
}*/
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| ep_debug_terminal |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*void ep_debug_terminal(void *addr, void *low, void *high, void *ret) {
|
|
printf("ADDR=%p LOW=%p HIGH=%p RET=%p\n", addr, low, high, ret);
|
|
fflush(stdout);
|
|
}*/
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| backspace |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
|
|
/*static void backspace(void) {
|
|
int y,x;
|
|
getyx(stdscr, y,x);
|
|
if(x) x--;
|
|
set_cursor_yx(y,x);
|
|
}*/
|
|
|
|
|
|
/*-------------------------------------------------------------------------*\
|
|
| |
|
|
| cob_accept |
|
|
| |
|
|
\*-------------------------------------------------------------------------*/
|
|
/*
|
|
int cob_accept(char *buffer, struct fld_desc *f, int echo ) {
|
|
int y,x;
|
|
unsigned int i, ib;
|
|
int cnt, digcnt;
|
|
// cnt = how many chars need be entered
|
|
// digcnt = how many already entered
|
|
//
|
|
int c, sign=0;
|
|
int decimal_flg=0;
|
|
|
|
getyx(stdscr, y,x);
|
|
//
|
|
// echo & 4 --> DARK,
|
|
// echo == 0 --> NO ECHO
|
|
//
|
|
if (echo & 2) { // WITH FILLER (this isn't standard,
|
|
// I've invented it, but...)
|
|
addch_set('_', f->len);
|
|
if (f->decimals) addch(cDecimalChar);
|
|
refresh();
|
|
}
|
|
if (echo & 8) { // WITH UPDATE
|
|
for (i=0;i<f->len;i++)
|
|
addch(buffer[i]);
|
|
set_cursor_yx(y,x);
|
|
refresh();
|
|
}
|
|
digcnt=0;
|
|
cnt=f->len;
|
|
ib = 0;
|
|
while (1) {
|
|
c=getch();
|
|
if (c=='\n') // curses return '\n' as the return key
|
|
break;
|
|
if (c=='-' && ib==0) {
|
|
sign=1;
|
|
if (echo & 3) addch('-');
|
|
else if (echo & 4) addch('*');
|
|
continue;
|
|
}
|
|
if (c==KEY_BACKSPACE) {
|
|
for (i=0; i<ib; i++) {
|
|
backspace();
|
|
if (echo & 2) addch('_');
|
|
else if (echo & 8) addch(buffer[i]);
|
|
else if (echo) addch(' ');
|
|
}
|
|
if (decimal_flg) {
|
|
if (echo & 2) addch(cDecimalChar);
|
|
else if (echo & 8) { } // nothing to be done
|
|
else if (echo) addch(' ');
|
|
}
|
|
refresh();
|
|
decimal_flg=0;
|
|
cnt=f->len;
|
|
digcnt=0;
|
|
ib=0;
|
|
continue;
|
|
}
|
|
if (c==8) {
|
|
if (ib>0) {
|
|
ib--;
|
|
if (echo) backspace();
|
|
if (cnt==f->decimals) {
|
|
decimal_flg=0;
|
|
if (echo) backspace();
|
|
}
|
|
else if (digcnt==1 && sign) {
|
|
sign=0;
|
|
if (echo) backspace();
|
|
}
|
|
cnt++;
|
|
digcnt--;
|
|
}
|
|
continue;
|
|
}
|
|
if ( ((f->type==DTYPE_ALPHA) && (isalpha(c) || c==' ')) ||
|
|
((f->type==DTYPE_ALPHANUMERIC || f->type==DTYPE_GROUP)
|
|
&& (isprint(c) || c==' ')) ||
|
|
((f->type==DTYPE_DISPLAY) && isdigit(c) )) {
|
|
buffer[ib++] = c;
|
|
if (echo & 4) addch('*');
|
|
else if (echo) addch(c);
|
|
if (cnt) {
|
|
cnt--;
|
|
digcnt++;
|
|
}
|
|
if (cnt==f->decimals && cnt) {
|
|
if (echo & 4) addch('*');
|
|
else if (echo) addch(cDecimalChar);
|
|
decimal_flg++;
|
|
}
|
|
continue;
|
|
}
|
|
if (c==cDecimalChar && f->type==DTYPE_DISPLAY && !decimal_flg) {
|
|
decimal_flg++;
|
|
cnt=f->decimals;
|
|
if (echo & 4) addch('*');
|
|
else if (echo) addch(cDecimalChar);
|
|
continue;
|
|
}
|
|
}
|
|
|
|
if (f->type==DTYPE_DISPLAY) {
|
|
if (!decimal_flg) {
|
|
// align field (integer part) at the right
|
|
if (f->len-cnt)
|
|
memmove(buffer+cnt-f->decimals,
|
|
buffer,digcnt);
|
|
// fill rest of field at the left with zeros
|
|
if (cnt>f->decimals)
|
|
memset(buffer,'0',cnt-f->decimals);
|
|
// fill decimal digits with zeros at the right
|
|
memset(buffer+f->len-f->decimals,
|
|
'0',f->decimals);
|
|
} else {
|
|
memset(buffer+ib, '0', cnt);
|
|
digcnt += cnt;
|
|
ib += cnt;
|
|
memmove(buffer+f->len-digcnt,buffer,digcnt);
|
|
memset(buffer,'0',f->len-digcnt);
|
|
}
|
|
} else
|
|
memset(buffer+ib,' ',cnt);
|
|
if (f->type==DTYPE_DISPLAY)
|
|
put_sign(f,buffer,sign);
|
|
printw("\n");
|
|
return (int)ib;
|
|
}
|
|
|
|
*/
|
|
/* screenio.c */
|