Fix initialisation of wide char support in FILE. Problem reported
[dragonfly/netmp.git] / games / hack / hack.termcap.c
blobbf6690d91e59eec95d63d1533f38f279c9d05853
1 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
2 /* hack.termcap.c - version 1.0.3 */
3 /* $FreeBSD: src/games/hack/hack.termcap.c,v 1.10 1999/11/16 10:26:38 marcel Exp $ */
4 /* $DragonFly: src/games/hack/hack.termcap.c,v 1.4 2005/05/22 03:37:05 y0netan1 Exp $ */
6 #include <stdio.h>
7 #include <termcap.h>
8 #include <stdlib.h>
9 #include <unistd.h>
10 #include "config.h" /* for ROWNO and COLNO */
11 #include "def.flag.h" /* for flags.nonull */
12 extern long *alloc();
14 static char tbuf[512];
15 static char *HO, *CL, *CE, *tcUP, *CM, *ND, *XD, *tcBC, *SO, *SE, *TI, *TE;
16 static char *VS, *VE;
17 static int SG;
18 static char tcPC = '\0';
19 char *CD; /* tested in pri.c: docorner() */
20 int CO, LI; /* used in pri.c and whatis.c */
22 startup()
24 char *term;
25 char *tptr;
26 char *tbufptr, *pc;
28 tptr = (char *) alloc(1024);
30 tbufptr = tbuf;
31 if(!(term = getenv("TERM")))
32 error("Can't get TERM.");
33 if(tgetent(tptr, term) < 1)
34 error("Unknown terminal type: %s.", term);
35 if (tgetflag(__DECONST(char *, "NP")) ||
36 tgetflag(__DECONST(char *, "nx")))
37 flags.nonull = 1;
38 if(pc = tgetstr(__DECONST(char *, "pc"), &tbufptr))
39 tcPC = *pc;
40 if(!(tcBC = tgetstr(__DECONST(char *, "bc"), &tbufptr))) {
41 if(!tgetflag(__DECONST(char *, "bs")))
42 error("Terminal must backspace.");
43 tcBC = tbufptr;
44 tbufptr += 2;
45 *tcBC = '\b';
47 HO = tgetstr(__DECONST(char *, "ho"), &tbufptr);
48 CO = tgetnum(__DECONST(char *, "co"));
49 LI = tgetnum(__DECONST(char *, "li"));
50 if(CO < COLNO || LI < ROWNO+2)
51 setclipped();
52 if(!(CL = tgetstr(__DECONST(char *, "cl"), &tbufptr)))
53 error("Hack needs CL.");
54 ND = tgetstr(__DECONST(char *, "nd"), &tbufptr);
55 if(tgetflag(__DECONST(char *, "os")))
56 error("Hack can't have OS.");
57 CE = tgetstr(__DECONST(char *, "ce"), &tbufptr);
58 tcUP = tgetstr(__DECONST(char *, "up"), &tbufptr);
59 /* It seems that xd is no longer supported, and we should use
60 a linefeed instead; unfortunately this requires resetting
61 CRMOD, and many output routines will have to be modified
62 slightly. Let's leave that till the next release. */
63 XD = tgetstr(__DECONST(char *, "xd"), &tbufptr);
64 /* not: XD = tgetstr("do", &tbufptr); */
65 if(!(CM = tgetstr(__DECONST(char *, "cm"), &tbufptr))) {
66 if(!tcUP && !HO)
67 error("Hack needs CM or UP or HO.");
68 printf("Playing hack on terminals without cm is suspect...\n");
69 getret();
71 SO = tgetstr(__DECONST(char *, "so"), &tbufptr);
72 SE = tgetstr(__DECONST(char *, "se"), &tbufptr);
73 SG = tgetnum(__DECONST(char *, "sg"));
74 if(!SO || !SE || (SG > 0)) SO = SE = 0;
75 CD = tgetstr(__DECONST(char *, "cd"), &tbufptr);
76 set_whole_screen(); /* uses LI and CD */
77 if(tbufptr-tbuf > sizeof(tbuf)) error("TERMCAP entry too big...\n");
78 free(tptr);
81 start_screen()
83 xputs(TI);
84 xputs(VS);
87 end_screen()
89 xputs(VE);
90 xputs(TE);
93 /* Cursor movements */
94 extern xchar curx, cury;
96 curs(x, y)
97 int x, y; /* not xchar: perhaps xchar is unsigned and
98 curx-x would be unsigned as well */
101 if (y == cury && x == curx)
102 return;
103 if(!ND && (curx != x || x <= 3)) { /* Extremely primitive */
104 cmov(x, y); /* bunker!wtm */
105 return;
107 if(abs(cury-y) <= 3 && abs(curx-x) <= 3)
108 nocmov(x, y);
109 else if((x <= 3 && abs(cury-y)<= 3) || (!CM && x<abs(curx-x))) {
110 (void) putchar('\r');
111 curx = 1;
112 nocmov(x, y);
113 } else if(!CM) {
114 nocmov(x, y);
115 } else
116 cmov(x, y);
119 nocmov(x, y)
121 if (cury > y) {
122 if(tcUP) {
123 while (cury > y) { /* Go up. */
124 xputs(tcUP);
125 cury--;
127 } else if(CM) {
128 cmov(x, y);
129 } else if(HO) {
130 home();
131 curs(x, y);
132 } /* else impossible("..."); */
133 } else if (cury < y) {
134 if(XD) {
135 while(cury < y) {
136 xputs(XD);
137 cury++;
139 } else if(CM) {
140 cmov(x, y);
141 } else {
142 while(cury < y) {
143 xputc('\n');
144 curx = 1;
145 cury++;
149 if (curx < x) { /* Go to the right. */
150 if(!ND) cmov(x, y); else /* bah */
151 /* should instead print what is there already */
152 while (curx < x) {
153 xputs(ND);
154 curx++;
156 } else if (curx > x) {
157 while (curx > x) { /* Go to the left. */
158 xputs(tcBC);
159 curx--;
164 cmov(x, y)
165 int x, y;
167 xputs(tgoto(CM, x-1, y-1));
168 cury = y;
169 curx = x;
172 xputc(c) char c; {
173 (void) fputc(c, stdout);
176 xputs(s) char *s; {
177 tputs(s, 1, xputc);
180 cl_end() {
181 if(CE)
182 xputs(CE);
183 else { /* no-CE fix - free after Harold Rynes */
184 /* this looks terrible, especially on a slow terminal
185 but is better than nothing */
186 int cx = curx, cy = cury;
188 while(curx < COLNO) {
189 xputc(' ');
190 curx++;
192 curs(cx, cy);
196 clear_screen() {
197 xputs(CL);
198 curx = cury = 1;
201 home()
203 if(HO)
204 xputs(HO);
205 else if(CM)
206 xputs(tgoto(CM, 0, 0));
207 else
208 curs(1, 1); /* using tcUP ... */
209 curx = cury = 1;
212 standoutbeg()
214 if(SO) xputs(SO);
217 standoutend()
219 if(SE) xputs(SE);
222 backsp()
224 xputs(tcBC);
225 curx--;
228 bell()
230 (void) putchar('\007'); /* curx does not change */
231 (void) fflush(stdout);
234 static short tmspc10[] = { /* from termcap */
235 0, 2000, 1333, 909, 743, 666, 500, 333, 166, 83, 55, 41, 20, 10, 5, 3, 2, 1
238 #if 0
239 delay_output() {
240 /* delay 50 ms - could also use a 'nap'-system call */
241 /* BUG: if the padding character is visible, as it is on the 5620
242 then this looks terrible. */
243 if(!flags.nonull)
244 tputs("50", 1, xputc);
246 /* cbosgd!cbcephus!pds for SYS V R2 */
247 /* is this terminfo, or what? */
248 /* tputs("$<50>", 1, xputc); */
249 else {
250 (void) fflush(stdout);
251 usleep(50*1000);
253 else if(ospeed > 0 || ospeed < SIZE(tmspc10)) if(CM) {
254 /* delay by sending cm(here) an appropriate number of times */
255 int cmlen = strlen(tgoto(CM, curx-1, cury-1));
256 int i = 500 + tmspc10[ospeed]/2;
258 while(i > 0) {
259 cmov(curx, cury);
260 i -= cmlen*tmspc10[ospeed];
264 #endif /* 0 */
266 cl_eos() /* free after Robert Viduya */
267 { /* must only be called with curx = 1 */
269 if(CD)
270 xputs(CD);
271 else {
272 int cx = curx, cy = cury;
273 while(cury <= LI-2) {
274 cl_end();
275 xputc('\n');
276 curx = 1;
277 cury++;
279 cl_end();
280 curs(cx, cy);