comparison rogue5/io.c @ 33:f502bf60e6e4

Import Rogue 5.4 from the Roguelike Restoration Project (r1490)
author elwin
date Mon, 24 May 2010 20:10:59 +0000
parents
children
comparison
equal deleted inserted replaced
32:2dcd75e6a736 33:f502bf60e6e4
1 /*
2 * Various input/output functions
3 *
4 * @(#)io.c 4.32 (Berkeley) 02/05/99
5 */
6
7 #include <stdarg.h>
8 #include <curses.h>
9 #include <ctype.h>
10 #include <string.h>
11 #include "rogue.h"
12
13 /*
14 * msg:
15 * Display a message at the top of the screen.
16 */
17 #define MAXMSG (NUMCOLS - sizeof "--More--")
18
19 static char msgbuf[2*MAXMSG+1];
20 static int newpos = 0;
21
22 /* VARARGS1 */
23 int
24 msg(const char *fmt, ...)
25 {
26 va_list args;
27
28 /*
29 * if the string is "", just clear the line
30 */
31 if (*fmt == '\0')
32 {
33 move(0, 0);
34 clrtoeol();
35 mpos = 0;
36 return ~ESCAPE;
37 }
38 /*
39 * otherwise add to the message and flush it out
40 */
41 va_start(args, fmt);
42 doadd(fmt, args);
43 va_end(args);
44 return endmsg();
45 }
46
47 /*
48 * addmsg:
49 * Add things to the current message
50 */
51 /* VARARGS1 */
52 void
53 addmsg(const char *fmt, ...)
54 {
55 va_list args;
56
57 va_start(args, fmt);
58 doadd(fmt, args);
59 va_end(args);
60 }
61
62 /*
63 * endmsg:
64 * Display a new msg (giving him a chance to see the previous one
65 * if it is up there with the --More--)
66 */
67 int
68 endmsg(void)
69 {
70 int ch;
71
72 if (save_msg)
73 strcpy(huh, msgbuf);
74 if (mpos)
75 {
76 look(FALSE);
77 mvaddstr(0, mpos, "--More--");
78 refresh();
79 if (!msg_esc)
80 wait_for(stdscr, ' ');
81 else
82 {
83 while ((ch = readchar()) != ' ')
84 if (ch == ESCAPE)
85 {
86 msgbuf[0] = '\0';
87 mpos = 0;
88 newpos = 0;
89 msgbuf[0] = '\0';
90 return ESCAPE;
91 }
92 }
93 }
94 /*
95 * All messages should start with uppercase, except ones that
96 * start with a pack addressing character
97 */
98 if (islower((int)msgbuf[0]) && !lower_msg && msgbuf[1] != ')')
99 msgbuf[0] = (char) toupper(msgbuf[0]);
100 mvaddstr(0, 0, msgbuf);
101 clrtoeol();
102 mpos = newpos;
103 newpos = 0;
104 msgbuf[0] = '\0';
105 refresh();
106 return ~ESCAPE;
107 }
108
109 /*
110 * doadd:
111 * Perform an add onto the message buffer
112 */
113 void
114 doadd(const char *fmt, va_list args)
115 {
116 static char buf[MAXSTR];
117
118 /*
119 * Do the printf into buf
120 */
121 vsprintf(buf, fmt, args);
122 if (strlen(buf) + newpos >= MAXMSG)
123 endmsg();
124 strcat(msgbuf, buf);
125 newpos = (int) strlen(msgbuf);
126 }
127
128 /*
129 * step_ok:
130 * Returns true if it is ok to step on ch
131 */
132 int
133 step_ok(int ch)
134 {
135 switch (ch)
136 {
137 case ' ':
138 case '|':
139 case '-':
140 return FALSE;
141 default:
142 return (!isalpha(ch));
143 }
144 }
145
146 /*
147 * readchar:
148 * Reads and returns a character, checking for gross input errors
149 */
150
151 int
152 readchar(void)
153 {
154 int ch;
155
156 ch = md_readchar(stdscr);
157
158 if (ch == 3)
159 {
160 quit(0);
161 return(27);
162 }
163
164 return(ch);
165 }
166
167 int
168 wreadchar(WINDOW *win)
169 {
170 int ch;
171
172 ch = md_readchar(win);
173
174 if (ch == 3)
175 {
176 quit(0);
177 return(27);
178 }
179
180 return(ch);
181 }
182
183
184 /*
185 * status:
186 * Display the important stats line. Keep the cursor where it was.
187 */
188 void
189 status(void)
190 {
191 int oy, ox, temp;
192 static int hpwidth = 0;
193 static int s_hungry = 0;
194 static int s_lvl = 0;
195 static int s_pur = -1;
196 static int s_hp = 0;
197 static int s_arm = 0;
198 static int s_str = 0;
199 static int s_exp = 0;
200 static char *state_name[] =
201 {
202 "", "Hungry", "Weak", "Faint"
203 };
204
205 /*
206 * If nothing has changed since the last status, don't
207 * bother.
208 */
209 temp = (cur_armor != NULL ? cur_armor->o_arm : pstats.s_arm);
210 if (s_hp == pstats.s_hpt && s_exp == pstats.s_exp && s_pur == purse
211 && s_arm == temp && s_str == pstats.s_str && s_lvl == level
212 && s_hungry == hungry_state
213 && !stat_msg
214 )
215 return;
216
217 s_arm = temp;
218
219 getyx(stdscr, oy, ox);
220 if (s_hp != max_hp)
221 {
222 temp = max_hp;
223 s_hp = max_hp;
224 for (hpwidth = 0; temp; hpwidth++)
225 temp /= 10;
226 }
227
228 /*
229 * Save current status
230 */
231 s_lvl = level;
232 s_pur = purse;
233 s_hp = pstats.s_hpt;
234 s_str = pstats.s_str;
235 s_exp = pstats.s_exp;
236 s_hungry = hungry_state;
237
238 if (stat_msg)
239 {
240 move(0, 0);
241 msg("Level: %d Gold: %-5d Hp: %*d(%*d) Str: %2d(%d) Arm: %-2d Exp: %d/%d %s",
242 level, purse, hpwidth, pstats.s_hpt, hpwidth, max_hp, pstats.s_str,
243 max_stats.s_str, 10 - s_arm, pstats.s_lvl, pstats.s_exp,
244 state_name[hungry_state]);
245 }
246 else
247 {
248 move(STATLINE, 0);
249
250 printw("Level: %d Gold: %-5d Hp: %*d(%*d) Str: %2d(%d) Arm: %-2d Exp: %d/%d %s",
251 level, purse, hpwidth, pstats.s_hpt, hpwidth, max_hp, pstats.s_str,
252 max_stats.s_str, 10 - s_arm, pstats.s_lvl, pstats.s_exp,
253 state_name[hungry_state]);
254 }
255
256 clrtoeol();
257 move(oy, ox);
258 }
259
260 /*
261 * wait_for
262 * Sit around until the guy types the right key
263 */
264 void
265 wait_for(WINDOW *win, int ch)
266 {
267 int c;
268
269 if (ch == '\n')
270 while ((c = wreadchar(win)) != '\n' && c != '\r')
271 continue;
272 else
273 while (wreadchar(win) != ch)
274 continue;
275 }
276
277 /*
278 * show_win:
279 * Function used to display a window and wait before returning
280 */
281 void
282 show_win(const char *message)
283 {
284 WINDOW *win;
285
286 win = hw;
287 wmove(win, 0, 0);
288 waddstr(win, message);
289 touchwin(win);
290 wrefresh(win);
291 wait_for(win, ' ');
292 clearok(curscr, TRUE);
293 touchwin(stdscr);
294 }