home *** CD-ROM | disk | FTP | other *** search
/ Simtel MSDOS - Coast to Coast / simteldosarchivecoasttocoast2.iso / ddjmag / ddj9105.zip / C_PROG.ASC < prev    next >
Text File  |  1991-03-15  |  29KB  |  971 lines

  1. _C PROGRAMMING COLUMN_
  2. by Al Stevens
  3.  
  4. [LISTING ONE]
  5.  
  6. /* ------------- dflat.h ----------- */
  7.  
  8. #ifndef WINDOW_H
  9. #define WINDOW_H
  10.  
  11. #define TRUE 1
  12. #define FALSE 0
  13.  
  14. #include "system.h"
  15. #include "config.h"
  16. #include "rect.h"
  17. #include "menu.h"
  18. #include "keys.h"
  19. #include "commands.h"
  20. #include "config.h"
  21. #include "dialbox.h"
  22.  
  23. /* ------ integer type for message parameters ----- */
  24. typedef long PARAM;
  25. typedef enum window_class    {
  26.     NORMAL,
  27.     APPLICATION,
  28.     TEXTBOX,
  29.     LISTBOX,
  30.     EDITBOX,
  31.     MENUBAR,
  32.     POPDOWNMENU,
  33.     BUTTON,
  34.     DIALOG,
  35.     ERRORBOX,
  36.     MESSAGEBOX,
  37.     HELPBOX,
  38.     TEXT,
  39.     RADIOBUTTON,
  40.     DUMMY
  41. } CLASS;
  42. typedef struct window {
  43.     CLASS class;           /* window class                  */
  44.     char *title;           /* window title                  */
  45.     struct window *parent; /* parent window                 */
  46.     int (*wndproc)
  47.         (struct window *, enum messages, PARAM, PARAM);
  48.     /* ---------------- window dimensions ----------------- */
  49.     RECT rc;               /* window coordinates
  50.                                             (0/0 to 79/24)  */
  51.     int ht, wd;            /* window height and width       */
  52.     RECT RestoredRC;       /* restored condition rect       */
  53.     /* -------------- linked list pointers ---------------- */
  54.     struct window *next;        /* next window on screen    */
  55.     struct window *prev;        /* previous window on screen*/
  56.     struct window *nextbuilt;   /* next window built        */
  57.     struct window *prevbuilt;   /* previous window built    */
  58.  
  59.     int attrib;                 /* Window attributes        */
  60.     char *videosave;            /* video save buffer        */
  61.     int condition;              /* Restored, Maximized,
  62.                                            Minimized        */
  63.     void *extension;            /* -> menus, dialog box, etc*/
  64.     struct window *PrevMouse;
  65.     struct window *PrevKeyboard;
  66.     /* ----------------- text box fields ------------------ */
  67.     int wlines;     /* number of lines of text              */
  68.     int wtop;       /* text line that is on the top display */
  69.     char *text;     /* window text                          */
  70.     int textlen;    /* text length                          */
  71.     int wleft;      /* left position in window viewport     */
  72.     int textwidth;  /* width of longest line in textbox     */
  73.     int BlkBegLine; /* beginning line of marked block       */
  74.     int BlkBegCol;  /* beginning column of marked block     */
  75.     int BlkEndLine; /* ending line of marked block          */
  76.     int BlkEndCol;  /* ending column of marked block        */
  77.     int HScrollBox; /* position of horizontal scroll box    */
  78.     int VScrollBox; /* position of vertical scroll box      */
  79.     /* ------------------ list box field ------------------ */
  80.     int selection;  /* current selection                    */
  81.     /* ----------------- edit box fields ------------------ */
  82.     int CurrCol;    /* Current column                       */
  83.     char *CurrLine; /* Current line                         */
  84.     int WndRow;     /* Current window row                   */
  85.     int TextChanged; /* TRUE if text has changed            */
  86.     char *DeletedText; /* for undo                          */
  87.     int DeletedLength; /*  "   "                            */
  88.     /* ---------------- dialog box fields ----------------- */
  89.     struct window *dFocus; /* control that has the focus    */
  90.     int ReturnCode;        /* return code from a dialog box */
  91. } * WINDOW;
  92.  
  93. #include "message.h"
  94. #include "classdef.h"
  95. #include "video.h"
  96.  
  97. enum Condition     {
  98.     ISRESTORED, ISMINIMIZED, ISMAXIMIZED
  99. };
  100. /* ------- window methods ----------- */
  101. #define WindowHeight(w)      ((w)->ht)
  102. #define WindowWidth(w)       ((w)->wd)
  103. #define BorderAdj(w,n)       (TestAttribute(w,HASBORDER)?n:0)
  104. #define ClientWidth(w)       (WindowWidth(w)-BorderAdj(w,2))
  105. #define ClientHeight(w)      (WindowHeight(w)-BorderAdj(w,2))
  106. #define WindowRect(w)        ((w)->rc)
  107. #define GetTop(w)            (RectTop(WindowRect(w)))
  108. #define GetBottom(w)         (RectBottom(WindowRect(w)))
  109. #define GetLeft(w)           (RectLeft(WindowRect(w)))
  110. #define GetRight(w)          (RectRight(WindowRect(w)))
  111. #define GetClientTop(w)      (GetTop(w)+BorderAdj(w,1))
  112. #define GetClientBottom(w)   (GetBottom(w)-BorderAdj(w,1))
  113. #define GetClientLeft(w)     (GetLeft(w)+BorderAdj(w,1))
  114. #define GetClientRight(w)    (GetRight(w)-BorderAdj(w,1))
  115. #define GetParent(w)         ((w)->parent)
  116. #define GetTitle(w)          ((w)->title)
  117. #define NextWindow(w)        ((w)->next)
  118. #define PrevWindow(w)        ((w)->prev)
  119. #define NextWindowBuilt(w)   ((w)->nextbuilt)
  120. #define PrevWindowBuilt(w)   ((w)->prevbuilt)
  121. #define GetClass(w)          ((w)->class)
  122. #define GetAttribute(w)      ((w)->attrib)
  123. #define AddAttribute(w,a)    (GetAttribute(w) |= a)
  124. #define ClearAttribute(w,a)  (GetAttribute(w) &= ~(a))
  125. #define TestAttribute(w,a)   (GetAttribute(w) & (a))
  126. #define isVisible(w)         (GetAttribute(w) & VISIBLE)
  127. #define SetVisible(w)        (GetAttribute(w) |= VISIBLE)
  128. #define ClearVisible(w)      (GetAttribute(w) &= ~VISIBLE)
  129. #define gotoxy(w,x,y) cursor(w->rc.lf+(x)+1,w->rc.tp+(y)+1)
  130. WINDOW CreateWindow(CLASS,char *,int,int,int,int,void*,WINDOW,
  131.         int (*)(struct window *,enum messages,PARAM,PARAM),int);
  132. void AddTitle(WINDOW, char *);
  133. void RepaintBorder(WINDOW, RECT *);
  134. void ClearWindow(WINDOW, RECT *, int);
  135. void clipline(WINDOW, int, char *);
  136. void writeline(WINDOW, char *, int, int, int);
  137. void writefull(WINDOW, char *, int);
  138. void SetNextFocus(WINDOW,int);
  139. void PutWindowChar(WINDOW, int, int, int);
  140. void GetVideoBuffer(WINDOW);
  141. void RestoreVideoBuffer(WINDOW);
  142. int LineLength(char *);
  143. #define DisplayBorder(wnd) RepaintBorder(wnd, NULL)
  144. #define DefaultWndProc(wnd,msg,p1,p2)    \
  145.     classdefs[FindClass(wnd->class)].wndproc(wnd,msg,p1,p2)
  146. #define BaseWndProc(class,wnd,msg,p1,p2)    \
  147.     classdefs[DerivedClass(class)].wndproc(wnd,msg,p1,p2)
  148. #define NULLWND ((WINDOW) 0)
  149. struct LinkedList    {
  150.     WINDOW FirstWindow;
  151.     WINDOW LastWindow;
  152. };
  153. extern struct LinkedList Focus;
  154. extern struct LinkedList Built;
  155. extern WINDOW inFocus;
  156. extern WINDOW CaptureMouse;
  157. extern WINDOW CaptureKeyboard;
  158. extern int foreground, background;
  159. extern int WindowMoving;
  160. extern int WindowSizing;
  161. extern int TextMarking;
  162. extern char *Clipboard;
  163. extern WINDOW SystemMenuWnd;
  164. /* --------------- border characters ------------- */
  165. #define FOCUS_NW       '\xc9'
  166. #define FOCUS_NE       '\xbb'
  167. #define FOCUS_SE       '\xbc'
  168. #define FOCUS_SW       '\xc8'
  169. #define FOCUS_SIDE     '\xba'
  170. #define FOCUS_LINE     '\xcd'
  171. #define NW             '\xda'
  172. #define NE             '\xbf'
  173. #define SE             '\xd9'
  174. #define SW             '\xc0'
  175. #define SIDE           '\xb3'
  176. #define LINE           '\xc4'
  177. #define LEDGE          '\xc3'
  178. #define REDGE          '\xb4'
  179. #define SHADOWFG       DARKGRAY
  180. /* ------------- scroll bar characters ------------ */
  181. #define UPSCROLLBOX    '\x1e'
  182. #define DOWNSCROLLBOX  '\x1f'
  183. #define LEFTSCROLLBOX  '\x11'
  184. #define RIGHTSCROLLBOX '\x10'
  185. #define SCROLLBARCHAR  176 
  186. #define SCROLLBOXCHAR  178
  187. #define CHECKMARK      251      /* menu item toggle         */
  188. /* ----------------- title bar characters ----------------- */
  189. #define CONTROLBOXCHAR '\xf0'
  190. #define MAXPOINTER     24      /* maximize token            */
  191. #define MINPOINTER     25      /* minimize token            */
  192. #define RESTOREPOINTER 18      /* restore token             */
  193. /* --------------- text control characters ---------------- */
  194. #define APPLCHAR     176    /* fills application window     */
  195. #define SHORTCUTCHAR '~'    /* prefix: shortcut key display */
  196. #define CHANGECOLOR  174    /* prefix to change colors      */
  197. #define RESETCOLOR   175    /* reset colors to default      */
  198. /* ---- standard window message processing prototypes ----- */
  199. int ApplicationProc(WINDOW, MESSAGE, PARAM, PARAM);
  200. int NormalProc(WINDOW, MESSAGE, PARAM, PARAM);
  201. int TextBoxProc(WINDOW, MESSAGE, PARAM, PARAM);
  202. int ListBoxProc(WINDOW, MESSAGE, PARAM, PARAM);
  203. int EditBoxProc(WINDOW, MESSAGE, PARAM, PARAM);
  204. int MenuBarProc(WINDOW, MESSAGE, PARAM, PARAM);
  205. int PopDownProc(WINDOW, MESSAGE, PARAM, PARAM);
  206. int ButtonProc(WINDOW, MESSAGE, PARAM, PARAM);
  207. int DialogProc(WINDOW, MESSAGE, PARAM, PARAM);
  208. int SystemMenuProc(WINDOW, MESSAGE, PARAM, PARAM);
  209. int HelpBoxProc(WINDOW, MESSAGE, PARAM, PARAM);
  210. int MessageBoxProc(WINDOW, MESSAGE, PARAM, PARAM);
  211. /* ------------- normal box prototypes ------------- */
  212. int isWindow(WINDOW);
  213. WINDOW inWindow(int, int);
  214. int WndForeground(WINDOW);
  215. int WndBackground(WINDOW);
  216. int FrameForeground(WINDOW);
  217. int FrameBackground(WINDOW);
  218. int SelectForeground(WINDOW);
  219. int SelectBackground(WINDOW);
  220. void SetStandardColor(WINDOW);
  221. void SetReverseColor(WINDOW);
  222. void SetClassColors(CLASS);
  223. WINDOW GetFirstChild(WINDOW);
  224. WINDOW GetNextChild(WINDOW);
  225. WINDOW GetLastChild(WINDOW);
  226. WINDOW GetPrevChild(WINDOW);
  227. #define HitControlBox(wnd, p1, p2)     \
  228.     (TestAttribute(wnd, TITLEBAR)   && \
  229.      TestAttribute(wnd, CONTROLBOX) && \
  230.      p1 == 2 && p2 == 0)
  231. /* -------- text box prototypes ---------- */
  232. char *TextLine(WINDOW, int);
  233. void WriteTextLine(WINDOW, RECT *, int, int);
  234. void SetTextBlock(WINDOW, int, int, int, int);
  235. #define BlockMarked(wnd) (  wnd->BlkBegLine ||    \
  236.                             wnd->BlkEndLine ||    \
  237.                             wnd->BlkBegCol  ||    \
  238.                             wnd->BlkEndCol)
  239. #define ClearBlock(wnd) wnd->BlkBegLine = wnd->BlkEndLine =  \
  240.                         wnd->BlkBegCol  = wnd->BlkEndCol = 0;
  241. #define GetText(w)        ((w)->text)
  242. /* --------- menu prototypes ---------- */
  243. int CopyCommand(char *, char *, int, int);
  244. void PrepOptionsMenu(void *, struct Menu *);
  245. void PrepEditMenu(void *, struct Menu *);
  246. void PrepWindowMenu(void *, struct Menu *);
  247. void BuildSystemMenu(WINDOW);
  248. /* ------------- edit box prototypes ----------- */
  249. #define isMultiLine(wnd)     TestAttribute(wnd, MULTILINE)
  250. /* --------- message box prototypes -------- */
  251. void MessageBox(char *, char *);
  252. void ErrorMessage(char *);
  253. int TestErrorMessage(char *);
  254. int YesNoBox(char *);
  255. int MsgHeight(char *);
  256. int MsgWidth(char *);
  257. /* ------------- dialog box prototypes -------------- */
  258. int DialogBox(DBOX *, int (*)(struct window *,
  259.                         enum messages, PARAM, PARAM));
  260. int DlgOpenFile(char *, char *);
  261. int DlgSaveAs(char *);
  262. void GetDlgListText(WINDOW, char *, enum commands);
  263. int DlgDirList(WINDOW, char *, enum commands,
  264.                             enum commands, unsigned);
  265. int RadioButtonSetting(DBOX *, enum commands);
  266. void PushRadioButton(DBOX *, enum commands);
  267. void PutItemText(WINDOW, enum commands, char *);
  268. void GetItemText(WINDOW, enum commands, char *, int);
  269. /* ------------- help box prototypes ------------- */
  270. void HelpFunction(void);
  271. void LoadHelpFile(void);
  272. #define swap(a,b){int x=a;a=b;b=x;}
  273.  
  274. #endif
  275.  
  276.  
  277. [LISTING TWO]
  278.  
  279. /* ----------- keys.h ------------ */
  280. #ifndef KEYS_H
  281. #define KEYS_H
  282. #define RUBOUT        8
  283. #define BELL          7
  284. #define ESC          27
  285. #define ALT_BS      197
  286. #define SHIFT_DEL   198
  287. #define CTRL_INS    186
  288. #define SHIFT_INS   185
  289. #define F1          187
  290. #define F2          188
  291. #define F3          189
  292. #define F4          190
  293. #define F5          191
  294. #define F6          192
  295. #define F7          193
  296. #define F8          194
  297. #define F9          195
  298. #define F10         196
  299. #define CTRL_F1     222
  300. #define CTRL_F2     223
  301. #define CTRL_F3     224
  302. #define CTRL_F4     225
  303. #define CTRL_F5     226
  304. #define CTRL_F6     227
  305. #define CTRL_F7     228
  306. #define CTRL_F8     229
  307. #define CTRL_F9     230
  308. #define CTRL_F10    231
  309. #define ALT_F1      232
  310. #define ALT_F2      233
  311. #define ALT_F3      234
  312. #define ALT_F4      235
  313. #define ALT_F5      236
  314. #define ALT_F6      237
  315. #define ALT_F7      238
  316. #define ALT_F8      239
  317. #define ALT_F9      240
  318. #define ALT_F10     241
  319. #define HOME        199
  320. #define UP          200
  321. #define PGUP        201
  322. #define BS          203
  323. #define FWD         205
  324. #define END         207
  325. #define DN          208
  326. #define PGDN        209
  327. #define INS         210
  328. #define DEL         211
  329. #define CTRL_HOME   247
  330. #define CTRL_PGUP   132
  331. #define CTRL_BS     243
  332. #define CTRL_FIVE   143
  333. #define CTRL_FWD    244
  334. #define CTRL_END    245
  335. #define CTRL_PGDN   246
  336. #define SHIFT_HT    143
  337. #define ALT_A       158
  338. #define ALT_B       176
  339. #define ALT_C       174
  340. #define ALT_D       160
  341. #define ALT_E       146
  342. #define ALT_F       161
  343. #define ALT_G       162
  344. #define ALT_H       163
  345. #define ALT_I       151
  346. #define ALT_J       164
  347. #define ALT_K       165
  348. #define ALT_L       166
  349. #define ALT_M       178
  350. #define ALT_N       177
  351. #define ALT_O       152
  352. #define ALT_P       153
  353. #define ALT_Q       144
  354. #define ALT_R       147
  355. #define ALT_S       159
  356. #define ALT_T       148
  357. #define ALT_U       150
  358. #define ALT_V       175
  359. #define ALT_W       145
  360. #define ALT_X       173
  361. #define ALT_Y       149
  362. #define ALT_Z       172
  363. #define ALT_1      0xf8
  364. #define ALT_2      0xf9
  365. #define ALT_3      0xfa
  366. #define ALT_4      0xfb
  367. #define ALT_5      0xfc
  368. #define ALT_6      0xfd
  369. #define ALT_7      0xfe
  370. #define ALT_8      0xff
  371. #define ALT_9      0x80
  372. #define ALT_0      0x81
  373. #define ALT_HYPHEN  130
  374.  
  375. #define RIGHTSHIFT 0x01
  376. #define LEFTSHIFT  0x02
  377. #define CTRLKEY    0x04
  378. #define ALTKEY     0x08
  379. #define SCROLLLOCK 0x10
  380. #define NUMLOCK    0x20
  381. #define CAPSLOCK   0x40
  382. #define INSERTKEY  0x80
  383.  
  384. struct keys {
  385.     int keycode;
  386.     char *keylabel;
  387. };
  388. int getkey(void);
  389. int getshift(void);
  390. int keyhit(void);
  391. void beep(void);
  392. extern struct keys keys[];
  393. extern char altconvert[];
  394.  
  395. #endif
  396.  
  397.  
  398.  
  399. [LISTING THREE]
  400.  
  401.  
  402. /* --------------- system.h -------------- */
  403. #ifndef SYSTEM_H
  404. #define SYSTEM_H
  405. /* ----- interrupt vectors ----- */
  406. #define TIMER  8
  407. #define VIDEO  0x10
  408. #define KEYBRD 0x16
  409. #define DOS    0x21
  410. #define CRIT   0x24
  411. #define MOUSE  0x33
  412. /* ------- platform-dependent values ------ */
  413. #define FREQUENCY 100
  414. #define COUNT (1193280L / FREQUENCY)
  415. #define ZEROFLAG 0x40
  416. #define MAXSAVES 50
  417. #define SCREENWIDTH  80
  418. #define SCREENHEIGHT 25
  419. /* ----- keyboard BIOS (0x16) functions -------- */
  420. #define READKB 0
  421. #define KBSTAT 1
  422. /* ------- video BIOS (0x10) functions --------- */
  423. #define SETCURSORTYPE 1
  424. #define SETCURSOR     2
  425. #define READCURSOR    3
  426. #define READATTRCHAR  8
  427. #define WRITEATTRCHAR 9
  428. #define HIDECURSOR 0x20
  429. /* ------- the interrupt function registers -------- */
  430. typedef struct {
  431.     int bp,di,si,ds,es,dx,cx,bx,ax,ip,cs,fl;
  432. } IREGS;
  433. /* ---------- cursor prototypes -------- */
  434. void curr_cursor(int *x, int *y);
  435. void cursor(int x, int y);
  436. void hidecursor(void);
  437. void unhidecursor(void);
  438. void savecursor(void);
  439. void restorecursor(void);
  440. void normalcursor(void);
  441. void set_cursor_type(unsigned t);
  442. void videomode(void);
  443. /* ---------- mouse prototypes ---------- */
  444. int mouse_installed(void);
  445. int mousebuttons(void);
  446. void get_mouseposition(int *x, int *y);
  447. void set_mouseposition(int x, int y);
  448. void show_mousecursor(void);
  449. void hide_mousecursor(void);
  450. int button_releases(void);
  451. void resetmouse(void);
  452. #define leftbutton()     (mousebuttons()&1)
  453. #define rightbutton()     (mousebuttons()&2)
  454. #define waitformouse()     while(mousebuttons());
  455. /* ------------ timer macros -------------- */
  456. #define timed_out(timer)         (timer==0)
  457. #define set_timer(timer, secs)     timer=(secs)*182/10+1
  458. #define disable_timer(timer)     timer = -1
  459. #define timer_running(timer)     (timer > 0)
  460. #define countdown(timer)         --timer
  461. #define timer_disabled(timer)     (timer == -1)
  462.  
  463. #ifdef MSC
  464. /* ============= MSC Compatibility Macros ============ */
  465. #define BLACK         0
  466. #define BLUE          1
  467. #define GREEN         2
  468. #define CYAN          3
  469. #define RED           4
  470. #define MAGENTA       5
  471. #define BROWN         6
  472. #define LIGHTGRAY     7
  473. #define DARKGRAY      8
  474. #define LIGHTBLUE     9
  475. #define LIGHTGREEN   10
  476. #define LIGHTCYAN    11
  477. #define LIGHTRED     12
  478. #define LIGHTMAGENTA 13
  479. #define YELLOW       14
  480. #define WHITE        15
  481.  
  482. #define getvect(v)   _dos_getvect(v)
  483. #define setvect(v,f) _dos_setvect(v,f)
  484. #define MK_FP(s,o)   ((void far *) \
  485.                (((unsigned long)(s) << 16) | (unsigned)(o)))
  486. #undef FP_OFF
  487. #undef FP_SEG
  488. #define FP_OFF(p)    ((unsigned)(p))
  489. #define FP_SEG(p)    ((unsigned)((unsigned long)(p) >> 16))
  490. #define poke(a,b,c)  (*((int  far*)MK_FP((a),(b))) = (int)(c))
  491. #define pokeb(a,b,c) (*((char far*)MK_FP((a),(b))) = (char)(c))
  492. #define peek(a,b)    (*((int  far*)MK_FP((a),(b))))
  493. #define peekb(a,b)   (*((char far*)MK_FP((a),(b))))
  494. #define findfirst(p,f,a) _dos_findfirst(p,a,f)
  495. #define findnext(f)      _dos_findnext(f)
  496. #define ffblk            find_t
  497. #define ff_name          name
  498. #define ff_fsize         size
  499. #define ff_attrib        attrib
  500. #define fnsplit          _splitpath
  501. #define fnmerge          _makepath
  502. #define EXTENSION         2
  503. #define FILENAME          4
  504. #define DIRECTORY         8
  505. #define DRIVE            16
  506. #define MAXPATH          80
  507. #define MAXDRIVE          3 
  508. #define MAXDIR           66
  509. #define MAXFILE           9
  510. #define MAXEXT            5
  511. #define setdisk(d)       _dos_setdrive((d)+1, NULL)
  512. #define bioskey          _bios_keybrd
  513. #define keyhit           kbhit
  514. #endif
  515. #endif
  516.  
  517.  
  518.  
  519. [LISTING FOUR]
  520.  
  521. /* ----------- rect.h ------------ */
  522. #ifndef RECT_H
  523. #define RECT_H
  524.  
  525. typedef struct    {
  526.     int lf,tp,rt,bt;
  527. } RECT;
  528. #define within(p,v1,v2)   ((p)>=(v1)&&(p)<=(v2))
  529. #define RectTop(r)        (r.tp)
  530. #define RectBottom(r)     (r.bt)
  531. #define RectLeft(r)       (r.lf)
  532. #define RectRight(r)      (r.rt)
  533. #define InsideRect(x,y,r) (within(x,RectLeft(r),RectRight(r)) \
  534.                                &&                             \
  535.                           within(y,RectTop(r),RectBottom(r)))
  536. #define ValidRect(r)      (RectRight(r) || RectLeft(r))
  537. #define RectWidth(r)      (RectRight(r)-RectLeft(r)+1)
  538. #define RectHeight(r)     (RectBottom(r)-RectTop(r)+1)
  539. RECT subRectangle(RECT, RECT);
  540. RECT RelativeRectangle(RECT, RECT);
  541. RECT ClientRect(void *);
  542. RECT SetRect(int,int,int,int);
  543. #endif
  544.  
  545.  
  546.  
  547. [LISTING FIVE]
  548.  
  549. /* ---------------- video.h ----------------- */
  550.  
  551. #ifndef VIDEO_H
  552. #define VIDEO_H
  553.  
  554. #include "rect.h"
  555.  
  556. void getvideo(RECT, void far *);
  557. void storevideo(RECT, void far *);
  558. extern unsigned video_mode;
  559. extern unsigned video_page;
  560. void wputch(WINDOW, int, int, int);
  561. int GetVideoChar(int, int);
  562. void PutVideoChar(int, int, int);
  563. void get_videomode(void);
  564. void wputs(WINDOW, void *, int, int);
  565.  
  566. #define clr(fg,bg) ((fg)|((bg)<<4))
  567. #define vad(x,y) ((y)*160+(x)*2)
  568. #define ismono() (video_mode == 7)
  569. #define istext() (video_mode < 4)
  570. #define videochar(x,y) (GetVideoChar(x,y) & 255)
  571.  
  572. #endif
  573.  
  574.  
  575.  
  576. [LISTING SIX]
  577.  
  578. /* --------------------- video.c -------------------- */
  579. #include <stdio.h>
  580. #include <dos.h>
  581. #include <string.h>
  582. #include <conio.h>
  583. #include "dflat.h"
  584.  
  585. static unsigned video_address;
  586. /* -- read a rectangle of video memory into a save buffer -- */
  587. void getvideo(RECT rc, void far *bf)
  588. {
  589.     int ht = RectBottom(rc)-RectTop(rc)+1;
  590.     int bytes_row = (RectRight(rc)-RectLeft(rc)+1) * 2;
  591.     unsigned vadr = vad(RectLeft(rc), RectTop(rc));
  592.     hide_mousecursor();
  593.     while (ht--)    {
  594.         movedata(video_address, vadr, FP_SEG(bf),
  595.                 FP_OFF(bf), bytes_row);
  596.         vadr += 160;
  597.         (char far *)bf += bytes_row;
  598.     }
  599.     show_mousecursor();
  600. }
  601.  
  602. /* -- write a rectangle of video memory from a save buffer -- */
  603. void storevideo(RECT rc, void far *bf)
  604. {
  605.     int ht = RectBottom(rc)-RectTop(rc)+1;
  606.     int bytes_row = (RectRight(rc)-RectLeft(rc)+1) * 2;
  607.     unsigned vadr = vad(RectLeft(rc), RectTop(rc));
  608.     hide_mousecursor();
  609.     while (ht--)    {
  610.         movedata(FP_SEG(bf), FP_OFF(bf), video_address,
  611.                 vadr, bytes_row);
  612.         vadr += 160;
  613.         (char far *)bf += bytes_row;
  614.     }
  615.     show_mousecursor();
  616. }
  617.  
  618. /* -------- read a character of video memory ------- */
  619. int GetVideoChar(int x, int y)
  620. {
  621.     int c;
  622.     hide_mousecursor();
  623.     c = peek(video_address, vad(x,y));
  624.     show_mousecursor();
  625.     return c;
  626. }
  627.  
  628. /* -------- write a character of video memory ------- */
  629. void PutVideoChar(int x, int y, int c)
  630. {
  631.     if (x < SCREENWIDTH && y < SCREENHEIGHT)    {
  632.         hide_mousecursor();
  633.         poke(video_address, vad(x,y), c);
  634.         show_mousecursor();
  635.     }
  636. }
  637.  
  638. /* -------- write a character to a window ------- */
  639. void wputch(WINDOW wnd, int c, int x, int y)
  640. {
  641.     int x1 = GetClientLeft(wnd)+x;
  642.     int y1 = GetClientTop(wnd)+y;
  643.     if (x1 < SCREENWIDTH && y1 < SCREENHEIGHT)    {
  644.         hide_mousecursor();
  645.         poke(video_address,
  646.             vad(x1,y1),(c & 255) |
  647.                 (clr(foreground, background) << 8));
  648.         show_mousecursor();
  649.     }
  650. }
  651.  
  652. /* ------- write a string to a window ---------- */
  653. void wputs(WINDOW wnd, void *s, int x, int y)
  654. {
  655.     int x1 = GetLeft(wnd)+x;
  656.     int y1 = GetTop(wnd)+y;
  657.     if (x1 < SCREENWIDTH && y1 < SCREENHEIGHT)    {
  658.         int fg = foreground;
  659.         int bg = background;
  660.         unsigned char *str = s;
  661.         char ss[200];
  662.         int ln[SCREENWIDTH];
  663.         int *cp1 = ln;
  664.         int len;
  665.         strncpy(ss, s, 199);
  666.         ss[199] = '\0';
  667.         clipline(wnd, x, ss);
  668.         str = (unsigned char *) ss;
  669.         hide_mousecursor();
  670.         while (*str)    {
  671.             if (*str == CHANGECOLOR)    {
  672.                 str++;
  673.                 foreground = (*str++) & 0x7f;
  674.                 background = (*str++) & 0x7f;
  675.                 continue;
  676.             }
  677.             if (*str == RESETCOLOR)    {
  678.                 foreground = fg;
  679.                 background = bg;
  680.                 str++;
  681.                 continue;
  682.             }
  683.             *cp1++ = (*str & 255) |
  684.                 (clr(foreground, background) << 8);
  685.             str++;
  686.         }
  687.         foreground = fg;
  688.         background = bg;
  689.         len = (int)(cp1-ln);
  690.         if (x1+len > SCREENWIDTH)
  691.             len = SCREENWIDTH-x1;
  692.         movedata(FP_SEG(ln), FP_OFF(ln), video_address,
  693.             vad(x1,y1), len*2);
  694.         show_mousecursor();
  695.     }
  696. }
  697.  
  698. /* --------- get the current video mode -------- */
  699. void get_videomode(void)
  700. {
  701.     videomode();
  702.     /* ---- Monochrome Display Adaptor or text mode ---- */
  703.     if (ismono())
  704.         video_address = 0xb000;
  705.     else
  706.         /* ------ Text mode -------- */
  707.         video_address = 0xb800 + video_page;
  708. }
  709.  
  710.  
  711.  
  712. [LISTING SEVEN]
  713.  
  714. /* ----------- console.c ---------- */
  715.  
  716. #include <conio.h>
  717. #include <bios.h>
  718. #include <dos.h>
  719. #include "system.h"
  720. #include "keys.h"
  721.  
  722. /* ----- table of alt keys for finding shortcut keys ----- */
  723. char altconvert[] = {
  724.     ALT_A,ALT_B,ALT_C,ALT_D,ALT_E,ALT_F,ALT_G,ALT_H,
  725.     ALT_I,ALT_J,ALT_K,ALT_L,ALT_M,ALT_N,ALT_O,ALT_P,
  726.     ALT_Q,ALT_R,ALT_S,ALT_T,ALT_U,ALT_V,ALT_W,ALT_X,
  727.     ALT_Y,ALT_Z,ALT_0,ALT_1,ALT_2,ALT_3,ALT_4,ALT_5,
  728.     ALT_6,ALT_7,ALT_8,ALT_9,0
  729. };
  730.  
  731. unsigned video_mode;
  732. unsigned video_page;
  733.  
  734. static int near cursorpos[MAXSAVES];
  735. static int near cursorshape[MAXSAVES];
  736. static int cs = 0;
  737.  
  738. static union REGS regs;
  739.  
  740. #ifndef MSC
  741. #define ZEROFLAG 0x40
  742. /* ---- Test for keystroke ---- */
  743. int keyhit(void)
  744. {
  745.     _AH = 1;
  746.     geninterrupt(KEYBRD);
  747.     return (_FLAGS & ZEROFLAG) == 0;
  748. }
  749. #endif
  750.  
  751. /* ---- Read a keystroke ---- */
  752. int getkey(void)
  753. {
  754.     int c;
  755.     while (keyhit() == 0)
  756.         ;
  757.     if (((c = bioskey(0)) & 0xff) == 0)
  758.         c = (c >> 8) | 0x80;
  759.     return c & 0xff;
  760. }
  761.  
  762. /* ---------- read the keyboard shift status --------- */
  763. int getshift(void)
  764. {
  765.     regs.h.ah = 2;
  766.     int86(KEYBRD, ®s, ®s);
  767.     return regs.h.al;
  768. }
  769.  
  770. /* ------- macro to wait one clock tick -------- */
  771. #define wait()                     \
  772. {                                  \
  773.     int now = peek(0x40,0x6c);     \
  774.     while (now == peek(0x40,0x6c)) \
  775.         ;                          \
  776. }
  777.  
  778. /* -------- sound a buzz tone ---------- */
  779. void beep(void)
  780. {
  781.     wait();
  782.     outp(0x43, 0xb6);               /* program the frequency */
  783.     outp(0x42, (int) (COUNT % 256));
  784.     outp(0x42, (int) (COUNT / 256));
  785.     outp(0x61, inp(0x61) | 3);      /* start the sound */
  786.     wait();
  787.     outp(0x61, inp(0x61) & ~3);     /* stop the sound  */
  788. }
  789.  
  790. /* -------- get the video mode and page from BIOS -------- */
  791. void videomode(void)
  792. {
  793.     regs.h.ah = 15;
  794.     int86(VIDEO, ®s, ®s);
  795.     video_mode = regs.h.al;
  796.     video_page = regs.x.bx;
  797.     video_page &= 0xff00;
  798.     video_mode &= 0x7f;
  799. }
  800.  
  801. /* ------ position the cursor ------ */
  802. void cursor(int x, int y)
  803. {
  804.     videomode();
  805.     regs.x.dx = ((y << 8) & 0xff00) + x;
  806.     regs.x.ax = 0x0200;
  807.     regs.x.bx = video_page;
  808.     int86(VIDEO, ®s, ®s);
  809. }
  810.  
  811. /* ------ get cursor shape and position ------ */
  812. static void near getcursor(void)
  813. {
  814.     videomode();
  815.     regs.h.ah = READCURSOR;
  816.     regs.x.bx = video_page;
  817.     int86(VIDEO, ®s, ®s);
  818. }
  819.  
  820. /* ------- get the current cursor position ------- */
  821. void curr_cursor(int *x, int *y)
  822. {
  823.     getcursor();
  824.     *x = regs.h.dl;
  825.     *y = regs.h.dh;
  826. }
  827.  
  828. /* ------ save the current cursor configuration ------ */
  829. void savecursor(void)
  830. {
  831.     if (cs < MAXSAVES)    {
  832.         getcursor();
  833.         cursorshape[cs] = regs.x.cx;
  834.         cursorpos[cs] = regs.x.dx;
  835.         cs++;
  836.     }
  837. }
  838.  
  839. /* ---- restore the saved cursor configuration ---- */
  840. void restorecursor(void)
  841. {
  842.     if (cs)    {
  843.         --cs;
  844.         videomode();
  845.         regs.x.dx = cursorpos[cs];
  846.         regs.h.ah = SETCURSOR;
  847.          regs.x.bx = video_page;
  848.         int86(VIDEO, ®s, ®s);
  849.         set_cursor_type(cursorshape[cs]);
  850.     }
  851. }
  852.  
  853. /* ------ make a normal cursor ------ */
  854. void normalcursor(void)
  855. {
  856.     set_cursor_type(0x0607);
  857. }
  858.  
  859. /* ------ hide the cursor ------ */
  860. void hidecursor(void)
  861. {
  862.     getcursor();
  863.     regs.h.ch |= HIDECURSOR;
  864.     regs.h.ah = SETCURSORTYPE;
  865.     int86(VIDEO, ®s, ®s);
  866. }
  867.  
  868. /* ------ unhide the cursor ------ */
  869. void unhidecursor(void)
  870. {
  871.     getcursor();
  872.     regs.h.ch &= ~HIDECURSOR;
  873.     regs.h.ah = SETCURSORTYPE;
  874.     int86(VIDEO, ®s, ®s);
  875. }
  876.  
  877. /* ---- use BIOS to set the cursor type ---- */
  878. void set_cursor_type(unsigned t)
  879. {
  880.     videomode();
  881.     regs.h.ah = SETCURSORTYPE;
  882.      regs.x.bx = video_page;
  883.     regs.x.cx = t;
  884.     int86(VIDEO, ®s, ®s);
  885. }
  886.  
  887.  
  888.  
  889.  
  890. [LISTING EIGHT]
  891.  
  892. /* ------------- mouse.c ------------- */
  893.  
  894. #include <stdio.h>
  895. #include <dos.h>
  896. #include <stdlib.h>
  897. #include <string.h>
  898. #include "system.h"
  899.  
  900. static union REGS regs;
  901.  
  902. static void near mouse(int m1,int m2,int m3,int m4)
  903. {
  904.     regs.x.dx = m4;
  905.     regs.x.cx = m3;
  906.     regs.x.bx = m2;
  907.     regs.x.ax = m1;
  908.     int86(MOUSE, ®s, ®s);
  909. }
  910.  
  911. /* ---------- reset the mouse ---------- */
  912. void resetmouse(void)
  913. {
  914.     mouse(0,0,0,0);
  915. }
  916.  
  917. /* ----- test to see if the mouse driver is installed ----- */
  918. int mouse_installed(void)
  919. {
  920.     unsigned char far *ms;
  921.     ms = MK_FP(peek(0, MOUSE*4+2), peek(0, MOUSE*4));
  922.     return (ms != NULL && *ms != 0xcf);
  923. }
  924.  
  925. /* ------ return true if mouse buttons are pressed ------- */
  926. int mousebuttons(void)
  927. {
  928.     if (mouse_installed())
  929.         mouse(3,0,0,0);
  930.     return regs.x.bx & 3;
  931. }
  932.  
  933. /* ---------- return mouse coordinates ---------- */
  934. void get_mouseposition(int *x, int *y)
  935. {
  936.     if (mouse_installed())    {
  937.         mouse(3,0,0,0);
  938.         *x = regs.x.cx/8;
  939.         *y = regs.x.dx/8;
  940.     }
  941. }
  942.  
  943. /* -------- position the mouse cursor -------- */
  944. void set_mouseposition(int x, int y)
  945. {
  946.     if(mouse_installed())
  947.         mouse(4,0,x*8,y*8);
  948. }
  949.  
  950. /* --------- display the mouse cursor -------- */
  951. void show_mousecursor(void)
  952. {
  953.     if(mouse_installed())
  954.         mouse(1,0,0,0);
  955. }
  956.  
  957. /* --------- hide the mouse cursor ------- */
  958. void hide_mousecursor(void)
  959. {
  960.     if(mouse_installed())
  961.         mouse(2,0,0,0);
  962. }
  963.  
  964. /* --- return true if a mouse button has been released --- */
  965. int button_releases(void)
  966. {
  967.     if(mouse_installed())
  968.         mouse(6,0,0,0);
  969.     return regs.x.bx;
  970. }
  971.