]>
git.cameronkatri.com Git - bsdgames-darwin.git/blob - cgram/cgram.c
1 /* $NetBSD: cgram.c,v 1.9 2021/02/21 17:16:00 rillig Exp $ */
4 * Copyright (c) 2013 The NetBSD Foundation, Inc.
7 * This code is derived from software contributed to The NetBSD Foundation
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
42 #include "pathnames.h"
44 ////////////////////////////////////////////////////////////
47 xstrdup(const char *s
)
51 ret
= malloc(strlen(s
) + 1);
53 errx(1, "Out of memory");
62 return (char)toupper((unsigned char)ch
);
68 return (char)tolower((unsigned char)ch
);
74 return isalpha((unsigned char)ch
);
80 return islower((unsigned char)ch
);
86 return isupper((unsigned char)ch
);
89 ////////////////////////////////////////////////////////////
97 stringarray_init(struct stringarray
*a
)
104 stringarray_cleanup(struct stringarray
*a
)
110 stringarray_add(struct stringarray
*a
, const char *s
)
112 a
->v
= realloc(a
->v
, (a
->num
+ 1) * sizeof(a
->v
[0]));
114 errx(1, "Out of memory");
116 a
->v
[a
->num
] = xstrdup(s
);
120 ////////////////////////////////////////////////////////////
122 static struct stringarray lines
;
123 static struct stringarray sollines
;
125 static int scrolldown
;
132 FILE *f
= popen(_PATH_FORTUNE
, "r");
134 err(1, "%s", _PATH_FORTUNE
);
137 char buf
[128], buf2
[8 * sizeof(buf
)];
138 while (fgets(buf
, sizeof buf
, f
) != NULL
) {
139 char *s
= strrchr(buf
, '\n');
141 assert(strlen(s
) == 1);
145 for (i
= j
= 0; buf
[i
] != '\0'; i
++) {
146 if (buf
[i
] == '\t') {
150 } else if (buf
[i
] == '\b') {
159 stringarray_add(&lines
, buf2
);
160 stringarray_add(&sollines
, buf2
);
171 for (int i
= 0; i
< 26; i
++)
174 for (int i
= 26; i
> 1; i
--) {
175 int c
= (int)(random() % i
);
181 for (int y
= 0; y
< (int)lines
.num
; y
++) {
182 for (char *p
= lines
.v
[y
]; *p
!= '\0'; p
++) {
184 *p
= (char)('a' + key
[*p
- 'a']);
186 *p
= (char)('A' + key
[*p
- 'A']);
194 assert(cury
>= 0 && cury
< (int)lines
.num
);
195 if (curx
>= (int)strlen(lines
.v
[cury
])) {
200 char och
= lines
.v
[cury
][curx
];
201 if (!ch_isalpha(och
)) {
206 char loch
= ch_tolower(och
);
207 char uoch
= ch_toupper(och
);
208 char lch
= ch_tolower(ch
);
209 char uch
= ch_toupper(ch
);
211 for (int y
= 0; y
< (int)lines
.num
; y
++) {
212 for (char *p
= lines
.v
[y
]; *p
!= '\0'; p
++) {
226 ////////////////////////////////////////////////////////////
233 for (int i
= 0; i
< LINES
- 1; i
++) {
235 int ln
= i
+ scrolldown
;
236 if (ln
< (int)lines
.num
) {
237 for (unsigned j
= 0; lines
.v
[i
][j
] != '\0'; j
++) {
238 char ch
= lines
.v
[i
][j
];
239 if (ch
!= sollines
.v
[i
][j
] && ch_isalpha(ch
)) {
243 if (hinting
&& ch
== sollines
.v
[i
][j
] &&
248 addch(lines
.v
[i
][j
]);
261 addstr("~ to quit, * to cheat, ^pnfb to move");
265 move(cury
- scrolldown
, curx
);
284 ////////////////////////////////////////////////////////////
302 } else if (cury
> 0) {
304 curx
= (int)strlen(lines
.v
[cury
]);
309 curx
= (int)strlen(lines
.v
[cury
]);
313 if (curx
< (int)strlen(lines
.v
[cury
])) {
315 } else if (cury
< (int)lines
.num
- 1) {
325 if (cury
< (int)lines
.num
- 1) {
328 if (curx
> (int)strlen(lines
.v
[cury
])) {
329 curx
= (int)strlen(lines
.v
[cury
]);
331 if (scrolldown
< cury
- (LINES
- 2)) {
332 scrolldown
= cury
- (LINES
- 2);
340 if (curx
> (int)strlen(lines
.v
[cury
])) {
341 curx
= (int)strlen(lines
.v
[cury
]);
343 if (scrolldown
> cury
) {
354 if (isascii(ch
) && ch_isalpha((char)ch
)) {
355 if (substitute((char)ch
)) {
356 if (curx
< (int)strlen(lines
.v
[cury
])) {
359 if (curx
== (int)strlen(lines
.v
[cury
]) &&
360 cury
< (int)lines
.num
- 1) {
365 } else if (curx
< (int)strlen(lines
.v
[cury
]) &&
366 ch
== lines
.v
[cury
][curx
]) {
368 if (curx
== (int)strlen(lines
.v
[cury
]) &&
369 cury
< (int)lines
.num
- 1) {
381 ////////////////////////////////////////////////////////////
387 stringarray_init(&lines
);
388 stringarray_init(&sollines
);
389 srandom((unsigned int)time(NULL
));
394 keypad(stdscr
, true);
398 stringarray_cleanup(&sollines
);
399 stringarray_cleanup(&lines
);