uifc.h 17.2 KB
Newer Older
1
/* uifc.h */
2
3
4

/* Rob Swindell's Text-mode User Interface Library */

5
6
7
8
9
10
/* $Id$ */

/****************************************************************************
 * @format.tab-size 4		(Plain Text/Source Code File Header)			*
 * @format.use-tabs true	(see http://www.synchro.net/ptsc_hdr.html)		*
 *																			*
rswindell's avatar
rswindell committed
11
 * Copyright 2003 Rob Swindell - http://www.synchro.net/copyright.html		*
12
 *																			*
rswindell's avatar
rswindell committed
13
14
 * This library is free software; you can redistribute it and/or			*
 * modify it under the terms of the GNU Lesser General Public License		*
15
16
 * as published by the Free Software Foundation; either version 2			*
 * of the License, or (at your option) any later version.					*
rswindell's avatar
rswindell committed
17
18
 * See the GNU Lesser General Public License for more details: lgpl.txt or	*
 * http://www.fsf.org/copyleft/lesser.html									*
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
 *																			*
 * Anonymous FTP access to the most recent released source is available at	*
 * ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net	*
 *																			*
 * Anonymous CVS access to the development source and modification history	*
 * is available at cvs.synchro.net:/cvsroot/sbbs, example:					*
 * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs login			*
 *     (just hit return, no password is necessary)							*
 * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs checkout src		*
 *																			*
 * For Synchronet coding style and modification guidelines, see				*
 * http://www.synchro.net/source.html										*
 *																			*
 * You are encouraged to submit any modifications (preferably in Unix diff	*
 * format) via e-mail to mods@synchro.net									*
 *																			*
 * Note: If this box doesn't appear square, then you need to fix your tabs.	*
 ****************************************************************************/
37
38
39
40
41
42
43
44

#include <time.h>
#include <fcntl.h>
#include <ctype.h>
#include <stdio.h>
#include <string.h>
#include <stdarg.h>
#include <stdlib.h>
rswindell's avatar
rswindell committed
45
/* OS Specific */
46
47
48
#if defined(_WIN32)
    #include <windows.h>
#endif
49
50
#if defined(__unix__)
	#include <sys/param.h>	/* PATH_MAX */
51
#endif
52
53
54
#if (defined(__unix__) || defined(_WIN32)) && !defined(__FLAT__)
    #define __FLAT__
#endif
55
56
57
58
59

#if defined(__FLAT__)
	#define far
#endif

60
#if !defined(__FLAT__)
61
62
63
    #include <bios.h>
#endif

rswindell's avatar
rswindell committed
64
65
#if defined(__unix__) && !defined(stricmp)
    #define stricmp strcasecmp
66
	#define strnicmp strncasecmp
rswindell's avatar
rswindell committed
67
#endif
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104

/****************************************************************************/
/* MALLOC/FREE Macros for various compilers and environments				*/
/* MALLOC is used for allocations of 64k or less							*/
/* FREE is used to free buffers allocated with MALLOC						*/
/* LMALLOC is used for allocations of possibly larger than 64k				*/
/* LFREE is used to free buffers allocated with LMALLOC 					*/
/* REALLOC is used to re-size a previously MALLOCed or LMALLOCed buffer 	*/
/****************************************************************************/
#if defined(__COMPACT__) || defined(__LARGE__) || defined(__HUGE__)
	#if defined(__TURBOC__)
		#define REALLOC(x,y) farrealloc(x,y)
		#define LMALLOC(x) farmalloc(x)
		#define MALLOC(x) farmalloc(x)
		#define LFREE(x) farfree(x)
		#define FREE(x) farfree(x)
	#elif defined(__WATCOMC__)
		#define REALLOC realloc
		#define LMALLOC(x) halloc(x,1)	/* far heap, but slow */
		#define MALLOC malloc			/* far heap, but 64k max */
		#define LFREE hfree
		#define FREE free
	#else	/* Other 16-bit Compiler */
		#define REALLOC realloc
		#define LMALLOC malloc
		#define MALLOC malloc
		#define LFREE free
		#define FREE free
	#endif
#else		/* 32-bit Compiler or Small Memory Model */
	#define REALLOC realloc
	#define LMALLOC malloc
	#define MALLOC malloc
	#define LFREE free
	#define FREE free
#endif

rswindell's avatar
rswindell committed
105
106
107
108
109
110
111
112
113
114
115
116
#if !defined(MAX_PATH)	/* maximum path length */
	#if defined MAXPATHLEN
		#define MAX_PATH MAXPATHLEN	/* clib.h */
	#elif defined PATH_MAX
		#define MAX_PATH PATH_MAX
	#elif defined _MAX_PATH
		#define MAX_PATH _MAX_PATH
	#else
		#define MAX_PATH 260		
	#endif
#endif

117
118
119
120
121
122
123
#ifdef __DPMI32__
	#define INT_86(i,j,k) int386(i,j,k)
#else
	#define INT_86(i,j,k) int86(i,j,k)
#endif

#ifdef __FLAT__
124
	#define MAX_OPTS	10000
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
	#define MSK_ON		0xf0000000
	#define MSK_OFF 	0x0fffffff
	#define MSK_INS 	0x10000000
	#define MSK_DEL 	0x20000000
	#define MSK_GET 	0x30000000
	#define MSK_PUT 	0x40000000
#else
	#define MAX_OPTS	500 	/* Maximum number of options per menu call */
	#define MSK_ON		0xf000
	#define MSK_OFF 	0x0fff
	#define MSK_INS 	0x1000
	#define MSK_DEL 	0x2000
	#define MSK_GET 	0x3000
	#define MSK_PUT 	0x4000
#endif
#define MAX_OPLN	75		/* Maximum length of each option per menu call */
#define MAX_BUFS	7		/* Maximum number of screen buffers to save */
142
143
144
#define MIN_LINES   20      /* Minimum number of screen lines supported */
#define MAX_LINES   60      /* Maximum number of screen rows supported */ 
#define MAX_BFLN	80*MAX_LINES*2	/* Maximum size of screen buffers */
145
146
147
148
149

#ifndef uint
#define uint unsigned int
#endif

150
                            /* Bits in uifcapi_t.mode */
151
152
153
154
#define UIFC_INMSG	(1<<0)	/* Currently in Message Routine non-recursive */
#define UIFC_MOUSE	(1<<1)	/* Mouse installed and available */
#define UIFC_MONO	(1<<2)	/* Force monochrome mode */
#define UIFC_COLOR	(1<<3)	/* Force color mode */
155
#define UIFC_IBM	(1<<4)	/* Force use of IBM charset	*/
156

157
                            /* Bits in uifcapi_t.list mode */
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
#define WIN_ORG 	(1<<0)	/* Original menu - destroy valid screen area */
#define WIN_SAV 	(1<<1)	/* Save existing text and replace when finished */
#define WIN_ACT 	(1<<2)	/* Menu remains active after a selection */
#define WIN_L2R 	(1<<3)	/* Center the window based on 'width'   */
#define WIN_T2B 	(1<<4)	/* Center the window based on 'height'  */
#define WIN_INS 	(1<<5)	/* Allows user to user insert key */
#define WIN_INSACT	(1<<6)	/* Remains active after insert key */
#define WIN_DEL 	(1<<7)	/* Allows user to use delete key */
#define WIN_DELACT	(1<<8)	/* Remains active after delete key */
#define WIN_ESC 	(1<<9)	/* Screen is active when escape is hit			 */
#define WIN_RHT 	(1<<10) /* Place window against right side of screen */
#define WIN_BOT 	(1<<11) /* Place window against botton of screen */
#define WIN_GET 	(1<<12) /* Allows F5 to Get a menu item */
#define WIN_PUT 	(1<<13) /* Allows F6 to Put a menu item */
#define WIN_CHE 	(1<<14) /* Stay active after escape if changes */
#define WIN_XTR 	(1<<15) /* Add extra line at end for inserting at end */
174
175
176
#define WIN_DYN 	(1<<16) /* Dynamic window - return at least every second */
#define WIN_HLP 	(1<<17) /* Parse 'Help codes' */
#define WIN_PACK 	(1<<18) /* Pack text in window (No padding) */
177
178
#define WIN_IMM 	(1<<19) /* Draw window and return immediately */
#define WIN_FAT		(1<<20)	/* Do not pad outside borders */
179
180
#define WIN_REDRAW	(1<<21) /* Force redraw on dynamic window */
#define WIN_NODRAW	(1<<22) /* Force not to redraw on dynamic window */
deuce's avatar
deuce committed
181
182
183
#define WIN_EXTKEYS	(1<<23) /* Return on any keypress... if it's not handled internally
							 * Return value is -2 - keyvalue
							 */
184
185
186
187
188

#define WIN_MID WIN_L2R|WIN_T2B  /* Place window in middle of screen */

#define SCRN_TOP	3
#define SCRN_LEFT	5
189
#define SCRN_RIGHT 	((int)api->scrn_width-4)
190
191
192
193
194
195
196
197
198
199
200
201
202

								/* Bits in 'mode' for getkey and getstr     */
#define K_UPPER 	(1L<<0) 	/* Converts all letters to upper case		*/
#define K_UPRLWR	(1L<<1) 	/* Upper/Lower case automatically			*/
#define K_NUMBER	(1L<<2) 	/* Allow numbers only						*/
#define K_WRAP		(1L<<3) 	/* Allows word wrap 						*/
#define K_MSG		(1L<<4) 	/* Allows ANSI, ^N ^A ^G					*/
#define K_SPIN		(1L<<5) 	/* Spinning cursor (same as SPIN)			*/
#define K_LINE		(1L<<6) 	/* Input line (inverse color)				*/
#define K_EDIT		(1L<<7) 	/* Edit string passed						*/
#define K_CHAT		(1L<<8) 	/* In chat multi-chat						*/
#define K_NOCRLF	(1L<<9) 	/* Don't print CRLF after string input      */
#define K_ALPHA 	(1L<<10)	/* Only allow alphabetic characters 		*/
203
204
#define K_SCANNING	(1L<<11)	/* UPC Scanner is active... return on '%'	*/
#define K_TABEXIT	(1L<<12)	/* Return on TAB					    	*/
205
#define K_DECIMAL	(1L<<13)	/* Allow floating point numbers only		*/
206
207
#define K_DEUCEEXIT	(1L<<13)	/* Return whenever Deuce wants to exit		*/
								/* Define this behaviour better - ToDo		*/
208
209
210
211
212
213
214

#define HELPBUF_SIZE 4000

#ifndef TAB
									/* Control characters */
#define STX 	0x02				/* Start of text			^B	*/
#define ETX 	0x03				/* End of text				^C	*/
215
216
217
#define BS		'\b'				/* Back space				^H	*/
#define TAB 	'\t'				/* Horizontal tabulation	^I	*/
#define LF		'\n'				/* Line feed				^J	*/
218
#define FF		0x0c				/* Form feed				^L	*/
219
#define CR		'\r'				/* Carriage return			^M	*/
220
#define ESC 	0x1b				/* Escape					^[	*/
221
#define DEL     0x7f                /* Delete                   ^BS */
222
223
224
225
226
227
228
229
230
231
232
233
234
235
#endif

#define CLREOL 256

#ifndef uchar				/* Short-hand for unsigned data types */
#define uchar unsigned char
#endif
#ifndef uint
#define uint unsigned int
#endif
#ifndef ulong
#define ulong unsigned long
#endif

236
237
#ifndef BOOL
#define BOOL    int
deuce's avatar
deuce committed
238
#ifndef TRUE
239
#define TRUE    1
deuce's avatar
deuce committed
240
241
#endif
#ifndef FALSE
242
243
#define FALSE   0
#endif
deuce's avatar
deuce committed
244
#endif
245
246

typedef struct {
247
248
249
	uint    left,top,right,bot;
    uchar   *buf;
} win_t;
250

251
252
253
254
255
256
257
258
259
260
#if !defined(__FLAT__)
    /* LCLOLL.ASM */
    int lclini(int);
    void lclxy(int,int);
    int lclwx(void);
    int lclwy(void);
    int lclatr(int);
    void lputc(int);
    long lputs(char far *);
#endif    
261
262
263
264
265
266

#if defined(__OS2__) || !defined(__FLAT__)
void mswait(int msecs);
extern mswtyp;
#endif

267
typedef struct {
268
269
270
/****************************************************************************/
/* Size of the structure (for version compatibility verification).			*/
/****************************************************************************/
271
    size_t  size;
272
273
274
/****************************************************************************/
/* Controls general UIFC library behavior.									*/
/****************************************************************************/
275
    long    mode;
276
277
278
/****************************************************************************/
/* Set to TRUE when changes to data have been made by input function.		*/ 
/****************************************************************************/
279
    BOOL    changes;
280
281
282
/****************************************************************************/
/* The overlapped-window save buffer number.								*/
/****************************************************************************/
283
    uint    savnum;
284
285
286
287
288
289
290
/****************************************************************************/
/* The current overlapped-window save buffer depth.							*/
/****************************************************************************/
    uint    savdepth;
/****************************************************************************/
/* Screen length															*/
/****************************************************************************/
291
    uint    scrn_len;
292
/****************************************************************************/
293
294
295
296
/* Screen Width 															*/
/****************************************************************************/
    uint    scrn_width;
/****************************************************************************/
297
298
299
300
/* ESC key delay for curses													*/
/****************************************************************************/
    uint    esc_delay;
/****************************************************************************/
301
302
/* Alternative method of setting current help text.							*/
/****************************************************************************/
303
    char*   helpbuf;
304
305
306
/****************************************************************************/
/* Location of the help data and index files.								*/
/****************************************************************************/
307
308
    char    helpdatfile[MAX_PATH+1];
    char    helpixbfile[MAX_PATH+1];
309
/****************************************************************************/
310
311
312
313
314
315
316
317
/* Help and exit button locations for current/last window					*/
/****************************************************************************/
	int		buttony;
	int		exitstart;
	int		exitend;
	int		helpstart;
	int		helpend;
/****************************************************************************/
318
319
/* Exit/uninitialize function.												*/
/****************************************************************************/
320
    void    (*bail) (void);
321
322
323
324
325
/****************************************************************************/
/* Fill the screen with the appropriate background attribute.				*/
/* str is the title for the application banner.								*/
/* Returns 0 on success, non-zero on failure.								*/
/****************************************************************************/
326
    int     (*scrn) (char* str);
327
328
329
/****************************************************************************/
/* Popup a message, maybe wait for the user to hit a key or click button.	*/
/****************************************************************************/
330
    void    (*msg)  (char* str);
331
332
333
334
335
/****************************************************************************/
/* Popup/down a status message.												*/
/* str is the message to display on popup.									*/
/* if str==NULL, then the the status is to be cleared (popdown).			*/
/****************************************************************************/
336
    void    (*pop)  (char* str);
337
338
339
340
341
342
343
344
/****************************************************************************/
/* General menu function.													*/
/* mode contains WIN_* flags to control display and functionality.			*/
/* left, top and width specify desired screen locations and window size.	*/
/* cur is a pointer to the current (default) option.						*/
/* bar is a pointer to the current location of the lightbar (which used).	*/
/* title is the caption for the menu.										*/
/* Menus can centered left to right and top to bottom automatically.		*/
345
/* mode bits are set with macros WIN_*.										*/
346
347
348
349
350
/* option is an array of char arrays, first element of last char array		*/
/* must be NULL.															*/
/* Returns the 0-based selected option number, -1 for ESC, or the selected	*/
/* option number OR'd with MSK_INS, MSK_DEL, MSK_GET, or MSK_PUT.			*/
/****************************************************************************/
351
    int     (*list) (int mode, int left, int top, int width, int* dflt
352
                        ,int* bar, char *title, char** option);
353
354
355
356
357
358
/****************************************************************************/
/* Windowed string input routine.											*/
/* mode contains WIN_* flags to control display and functionality.			*/
/* left and top specify desired screen location.							*/
/* prompt is displayed before the input is requested.						*/
/* str is the string to input or edit.										*/
359
360
361
/* len is the maximum length of the string.									*/
/* kmode contains flags that control the string input (K_* macros).			*/
/* This function sets uifcapi_t.changes to TRUE if the string is modified.	*/
362
363
/* Returns the length of the string or -1 on escape/abort.					*/
/****************************************************************************/
364
365
    int     (*input)(int mode, int left, int top, char* prompt, char* str
            	        ,int len, int kmode);
366
367
368
/****************************************************************************/
/* Sets the current help index by source code file and line number.			*/
/****************************************************************************/
369
    void    (*sethelp)(int line, char* file);
370
371
372
373
374

/****************************************************************************/
/* Shows the current help text												*/
/****************************************************************************/
    void    (*showhelp)(void);
375
376
	
/****************************************************************************/
377
/* Shows a scrollable text buffer - optionally parsing "help markup codes"	*/
378
/****************************************************************************/
379
	void (*showbuf)(int mode, int left, int top, int width, int height, char *title, char *hbuf, int *curp, int *barp);
380

381
382
383
384
385
386
/****************************************************************************/
/* Updates time in upper left corner of screen with current time in ASCII/  */
/* Unix format																*/
/****************************************************************************/
	void (*timedisplay)(void);

387
388
389
/****************************************************************************/
/* String input/exit box at a specified position							*/
/****************************************************************************/
390
	int (*getstrxy)(int left, int top, int width, char *outstr, int max, long mode, int *lastkey);
391
392
} uifcapi_t;

393
394
395
396
397
398
/****************************************************************************/
/* Initialization routines for each UIFC implementation.					*/
/* Returns 0 on success, non-zero on failure.								*/
/****************************************************************************/
int uifcini(uifcapi_t*);	/* Original implementation based on conio		*/
int uifcinix(uifcapi_t*);	/* Standard I/O implementation					*/
rswindell's avatar
rswindell committed
399
int uifcinic(uifcapi_t*);	/* Unix curses implementation (by Deuce)		*/
400
int uifcinid(uifcapi_t*);	/* Unix libdialog implementation (by Deuce)		*/
deuce's avatar
deuce committed
401
int uifcini32(uifcapi_t*);	/* conio/curses implementation					*/
402
403
404
405
#ifdef __cplusplus
extern "C"
#endif
int uifcinifltk(uifcapi_t*);	/* FLTK implementation (by Deuce)			*/
406
/****************************************************************************/