Cleanup as part of Sergeev merge.
[super-star-trek.git] / io.c
1 #ifdef SERGEEV
2 #define _GNU_SOURCE
3 #endif /* SERGEEV */
4 #include <stdio.h>
5 #ifdef SERGEEV
6 #include <unistd.h>
7 #endif /* SERGEEV */
8 #include <termios.h>
9 #include <curses.h>
10 #include <signal.h>
11 #include <ctype.h>
12 #include <stdarg.h>
13 #ifdef SERGEEV
14 #include <conio.h>
15 #endif /* SERGEEV */
16 #ifdef MSDOS
17 #include <dos.h>
18 #endif
19 #include <time.h>
20
21 #ifdef SERGEEV
22 #include "sstlinux.h"
23 #endif /* SERGEEV */
24 #include "sst.h"
25
26 #ifndef SERGEEV
27 static int linecount;   /* for paging */
28 #endif /* SERGEEV */
29 static int screenheight = 24, screenwidth = 80;
30 #ifndef SERGEEV
31 static int curses = FALSE;
32 #else /* SERGEEV */
33 static int curses = TRUE;
34 #endif /* SERGEEV */
35
36 static void outro(int sig) {
37 /* wrap up, either normally or due to signal */
38     if (curses) {
39         clear();
40         (void)refresh();
41         (void)resetterm();
42         //(void)echo();
43         (void)endwin();
44     }
45 }
46
47 static void fastexit(int sig) {
48     outro(sig);
49     putchar('\n');
50     exit(0);
51 }
52
53 void iostart(int usecurses) {
54         (void) signal(SIGINT, fastexit);
55         (void) signal(SIGINT, fastexit);
56 #ifdef SIGIOT
57         (void) signal(SIGIOT,fastexit);         /* for assert(3) */
58 #endif /* SIGIOT */
59         if(signal(SIGQUIT,SIG_IGN) != SIG_IGN)
60             (void)signal(SIGQUIT,fastexit);
61
62         if ((curses = usecurses)) {
63                 (void)initscr();
64 #ifdef KEY_MIN
65                 keypad(stdscr, TRUE);
66 #endif /* KEY_MIN */
67                 (void)saveterm();
68                 (void)nonl();
69                 (void)cbreak();
70                 //(void)noecho();
71                 scrollok(stdscr, TRUE);
72                 getmaxyx(stdscr, screenheight, screenwidth);
73         } else {
74                 char *LINES = getenv("LINES");
75                 if (LINES)
76                     screenheight = atoi(LINES);
77         }
78 }
79
80 void ioend(void) {
81     outro(0);
82 }
83
84 void clearscreen(void) {
85         /* Somehow we need to clear the screen */
86 #ifdef __BORLANDC__
87         extern void clrscr(void);
88         clrscr();
89 #else
90         if (curses) {
91             wclear(stdscr);
92             wrefresh(stdscr);
93         } else {
94                 // proutn("\033[2J"); /* Hope for an ANSI display */
95                 /* much more in that old-TTY spirit to just throw linefeeds */
96                 int i;
97                 for (i = 0; i < screenheight; i++)
98                     putchar('\n');
99         }
100 #endif
101 }
102
103 void pause_game(int i) {
104 #ifndef SERGEEV
105     char buf[BUFSIZ], *prompt;
106 #else /* SERGEEV */
107         char *prompt;
108         drawmaps(0);
109         setwnd(5);
110 #endif /* SERGEEV */
111         if (i==1) {
112                 if (skill > 2)
113                         prompt = "[ANOUNCEMENT ARRIVING...]";
114                 else
115                         prompt = "[IMPORTANT ANNOUNCEMENT ARRIVING -- PRESS ENTER TO CONTINUE]";
116         }
117         else {
118                 if (skill > 2)
119                         prompt = "[CONTINUE?]";
120                 else
121                         prompt = "[PRESS ENTER TO CONTINUE]";
122
123         }
124 #ifndef SERGEEV
125         if (curses) {
126             waddch(stdscr, '\n');
127                 waddstr(stdscr, prompt);
128                 wgetnstr(stdscr, buf, sizeof(buf));
129                 wclear(stdscr);
130                 wrefresh(stdscr);
131         } else {
132                 putchar('\n');
133                 prout(prompt);
134                 fgets(buf, sizeof(buf), stdin);
135                 if (i != 0) {
136                         clearscreen();
137                 }
138                 linecount = 0;
139         }
140 #else /* SERGEEV */
141         proutn(prompt);
142         getche();
143         clrscr();
144         setwnd(4);
145         clrscr();
146 #endif /* SERGEEV */
147 }
148
149
150 void skip(int i) {
151 #ifndef SERGEEV
152     while (i-- > 0) {
153         if (curses) {
154             int y, x;
155             getyx(stdscr, y, x);
156             if (y == screenheight-1)
157                 pause_game(0);
158             else
159                 waddch(stdscr, '\n');
160         } else {
161             linecount++;
162             if (linecount >= screenheight)
163                 pause_game(0);
164             else
165                 putchar('\n');
166         }
167 #else /* SERGEEV */
168         while (i-- > 0) proutn("\n\r");
169 }
170
171 static void vproutn(char *fmt, va_list ap) {
172     char *strbuf, *p, *s;
173     vasprintf(&strbuf, fmt, ap);
174     p=s=strbuf;
175     if ((curwnd==4)&&(wherey()==wnds[curwnd].wndbottom-wnds[curwnd].wndtop)){
176        if (strchr(strbuf,'\n')){
177           p=strchr(strbuf,'\n');
178           p[0]=0;
179           cprintf("%s",strbuf);
180           p++;
181           pause_game(0);
182        }
183 #endif /* SERGEEV */
184     }
185 #ifdef SERGEEV
186     if ((curwnd==4)&&(wherey()>wnds[curwnd].wndbottom-wnds[curwnd].wndtop+1))
187        cprintf("\r");
188 //        setwnd(curwnd);
189     if (strchr(s,'\n') || strchr(s,'\r')) clreol();
190     cprintf("%s",p);
191     free(strbuf);
192 #endif /* SERGEEV */
193 }
194
195 void proutn(char *fmt, ...) {
196     va_list ap;
197     va_start(ap, fmt);
198 #ifndef SERGEEV
199     if (curses) {
200         vw_printw(stdscr, fmt, ap);
201         wrefresh(stdscr);
202     } else
203         vprintf(fmt, ap);
204 #else /* SERGEEV */
205     vproutn(fmt, ap);
206 #endif /* SERGEEV */
207     va_end(ap);
208 }
209
210 void prout(char *fmt, ...) {
211     va_list ap;
212     va_start(ap, fmt);
213 #ifndef SERGEEV
214     if (curses) {
215         vw_printw(stdscr, fmt, ap);
216         wrefresh(stdscr);
217     } else
218         vprintf(fmt, ap);
219 #else /* SERGEEV */
220     vproutn(fmt, ap);
221 #endif /* SERGEEV */
222     va_end(ap);
223     skip(1);
224 }
225
226 void proutc(char *line) {
227     line[strlen(line)-1] = '\0';
228 #ifndef SERGEEV
229     if (curses)
230         waddstr(stdscr, line);
231     else
232         fputs(line, stdout);
233 #else /* SERGEEV */
234     cputs(line);
235 #endif /* SERGEEV */
236     skip(1);
237 }
238
239 #ifdef SERGEEV
240 static void prchr(char *s){
241      char str[2];
242      strncpy(str,s,1);
243      str[1]=0;
244      proutn(str);
245 }
246
247 static void vprouts(char *fmt, va_list ap) {
248     char *s;
249     vasprintf(&s, fmt, ap);
250     while (*s) {
251         prchr(s++);
252         delay(30);
253     }
254     free(s);
255 }
256
257 #endif /* SERGEEV */
258 void prouts(char *fmt, ...) {
259 #ifndef SERGEEV
260         clock_t endTime;
261         char *s, buf[BUFSIZ];
262         /* print slowly! */
263         va_list ap;
264         va_start(ap, fmt);
265         vsprintf(buf, fmt, ap);
266         va_end(ap);
267         skip(1);
268         for (s = buf; *s; s++) {
269                 endTime = clock() + CLOCKS_PER_SEC*0.05;
270                 while (clock() < endTime) continue;
271                 if (curses) {
272                     waddch(stdscr, *s);
273                     wrefresh(stdscr);
274                 }
275                 else {
276                     putchar(*s);
277                     fflush(stdout);
278                 }
279         }
280 #else /* SERGEEV */
281     va_list ap;
282     va_start(ap, fmt);
283     vprouts(fmt, ap);
284     va_end(ap);
285 #endif /* SERGEEV */
286 }
287
288 #ifndef SERGEEV
289 void getline(char *line, int max) {
290 #else /* SERGEEV */
291 void cgetline(char *line, int max) {
292 #endif /* SERGEEV */
293     if (curses) {
294 #ifndef SERGEEV
295         wgetnstr(stdscr, line, max);
296         wrefresh(stdscr);
297 #else /* SERGEEV */
298         line[0]=max-1;
299         cgets(line);
300         memmove(line,&line[2],max-3);
301 #endif /* SERGEEV */
302     } else {
303         fgets(line, max, stdin);
304         line[strlen(line)-1] = '\0';
305     }
306 }
307
308 void commandhook(char *cmd, int before) {
309 }