]> git.cameronkatri.com Git - bsdgames-darwin.git/blob - hack/hack.topl.c
remove sh warning when invoked with no args
[bsdgames-darwin.git] / hack / hack.topl.c
1 /* $NetBSD: hack.topl.c,v 1.4 1997/10/19 16:59:10 christos Exp $ */
2
3 /*
4 * Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985.
5 */
6
7 #include <sys/cdefs.h>
8 #ifndef lint
9 __RCSID("$NetBSD: hack.topl.c,v 1.4 1997/10/19 16:59:10 christos Exp $");
10 #endif /* not lint */
11
12 #include <stdlib.h>
13 #include "hack.h"
14 #include "extern.h"
15
16 char toplines[BUFSZ];
17 xchar tlx, tly; /* set by pline; used by addtopl */
18
19 struct topl {
20 struct topl *next_topl;
21 char *topl_text;
22 } *old_toplines, *last_redone_topl;
23 #define OTLMAX 20 /* max nr of old toplines remembered */
24
25 int
26 doredotopl()
27 {
28 if (last_redone_topl)
29 last_redone_topl = last_redone_topl->next_topl;
30 if (!last_redone_topl)
31 last_redone_topl = old_toplines;
32 if (last_redone_topl) {
33 (void) strcpy(toplines, last_redone_topl->topl_text);
34 }
35 redotoplin();
36 return (0);
37 }
38
39 void
40 redotoplin()
41 {
42 home();
43 if (strchr(toplines, '\n'))
44 cl_end();
45 putstr(toplines);
46 cl_end();
47 tlx = curx;
48 tly = cury;
49 flags.toplin = 1;
50 if (tly > 1)
51 more();
52 }
53
54 void
55 remember_topl()
56 {
57 struct topl *tl;
58 int cnt = OTLMAX;
59 if (last_redone_topl &&
60 !strcmp(toplines, last_redone_topl->topl_text))
61 return;
62 if (old_toplines &&
63 !strcmp(toplines, old_toplines->topl_text))
64 return;
65 last_redone_topl = 0;
66 tl = (struct topl *)
67 alloc((unsigned) (strlen(toplines) + sizeof(struct topl) + 1));
68 tl->next_topl = old_toplines;
69 tl->topl_text = (char *) (tl + 1);
70 (void) strcpy(tl->topl_text, toplines);
71 old_toplines = tl;
72 while (cnt && tl) {
73 cnt--;
74 tl = tl->next_topl;
75 }
76 if (tl && tl->next_topl) {
77 free((char *) tl->next_topl);
78 tl->next_topl = 0;
79 }
80 }
81
82 void
83 addtopl(s)
84 char *s;
85 {
86 curs(tlx, tly);
87 if (tlx + strlen(s) > CO)
88 putsym('\n');
89 putstr(s);
90 tlx = curx;
91 tly = cury;
92 flags.toplin = 1;
93 }
94
95 void
96 xmore(s)
97 char *s; /* allowed chars besides space/return */
98 {
99 if (flags.toplin) {
100 curs(tlx, tly);
101 if (tlx + 8 > CO)
102 putsym('\n'), tly++;
103 }
104 if (flags.standout)
105 standoutbeg();
106 putstr("--More--");
107 if (flags.standout)
108 standoutend();
109
110 xwaitforspace(s);
111 if (flags.toplin && tly > 1) {
112 home();
113 cl_end();
114 docorner(1, tly - 1);
115 }
116 flags.toplin = 0;
117 }
118
119 void
120 more()
121 {
122 xmore("");
123 }
124
125 void
126 cmore(s)
127 char *s;
128 {
129 xmore(s);
130 }
131
132 void
133 clrlin()
134 {
135 if (flags.toplin) {
136 home();
137 cl_end();
138 if (tly > 1)
139 docorner(1, tly - 1);
140 remember_topl();
141 }
142 flags.toplin = 0;
143 }
144
145 void
146 #ifdef __STDC__
147 pline(const char *fmt, ...)
148 #else
149 pline(va_alist)
150 va_dcl
151 #endif
152 {
153 va_list ap;
154 #ifndef __STDC__
155 const char *fmt;
156 va_start(ap);
157 fmt = va_arg(ap, const char *);
158 #else
159 va_start(ap, fmt);
160 #endif
161 vpline(fmt, ap);
162 va_end(ap);
163 }
164
165 void
166 vpline(line, ap)
167 const char *line;
168 va_list ap;
169 {
170 char pbuf[BUFSZ];
171 char *bp = pbuf, *tl;
172 int n, n0;
173
174 if (!line || !*line)
175 return;
176 if (!strchr(line, '%'))
177 (void) strcpy(pbuf, line);
178 else
179 (void) vsprintf(pbuf, line, ap);
180 if (flags.toplin == 1 && !strcmp(pbuf, toplines))
181 return;
182 nscr(); /* %% */
183
184 /* If there is room on the line, print message on same line */
185 /* But messages like "You die..." deserve their own line */
186 n0 = strlen(bp);
187 if (flags.toplin == 1 && tly == 1 &&
188 n0 + strlen(toplines) + 3 < CO - 8 && /* leave room for
189 * --More-- */
190 strncmp(bp, "You ", 4)) {
191 (void) strcat(toplines, " ");
192 (void) strcat(toplines, bp);
193 tlx += 2;
194 addtopl(bp);
195 return;
196 }
197 if (flags.toplin == 1)
198 more();
199 remember_topl();
200 toplines[0] = 0;
201 while (n0) {
202 if (n0 >= CO) {
203 /* look for appropriate cut point */
204 n0 = 0;
205 for (n = 0; n < CO; n++)
206 if (bp[n] == ' ')
207 n0 = n;
208 if (!n0)
209 for (n = 0; n < CO - 1; n++)
210 if (!letter(bp[n]))
211 n0 = n;
212 if (!n0)
213 n0 = CO - 2;
214 }
215 (void) strncpy((tl = eos(toplines)), bp, n0);
216 tl[n0] = 0;
217 bp += n0;
218
219 /* remove trailing spaces, but leave one */
220 while (n0 > 1 && tl[n0 - 1] == ' ' && tl[n0 - 2] == ' ')
221 tl[--n0] = 0;
222
223 n0 = strlen(bp);
224 if (n0 && tl[0])
225 (void) strcat(tl, "\n");
226 }
227 redotoplin();
228 }
229
230 void
231 putsym(c)
232 char c;
233 {
234 switch (c) {
235 case '\b':
236 backsp();
237 return;
238 case '\n':
239 curx = 1;
240 cury++;
241 if (cury > tly)
242 tly = cury;
243 break;
244 default:
245 if (curx == CO)
246 putsym('\n'); /* 1 <= curx <= CO; avoid CO */
247 else
248 curx++;
249 }
250 (void) putchar(c);
251 }
252
253 void
254 putstr(s)
255 char *s;
256 {
257 while (*s)
258 putsym(*s++);
259 }