]> git.pond.sub.org Git - empserver/blob - src/lib/commands/surv.c
Indented with src/scripts/indent-emp.
[empserver] / src / lib / commands / surv.c
1 /*
2  *  Empire - A multi-player, client/server Internet based war game.
3  *  Copyright (C) 1986-2000, Dave Pare, Jeff Bailey, Thomas Ruschak,
4  *                           Ken Stevens, Steve McClure
5  *
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 2 of the License, or
9  *  (at your option) any later version.
10  *
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *
16  *  You should have received a copy of the GNU General Public License
17  *  along with this program; if not, write to the Free Software
18  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  *
20  *  ---
21  *
22  *  See the "LEGAL", "LICENSE", "CREDITS" and "README" files for all the
23  *  related information and legal notices. It is expected that any future
24  *  projects/authors will amend these files as needed.
25  *
26  *  ---
27  *
28  *  surv.c: Show sector survey
29  * 
30  *  Known contributors to this file:
31  *     Dave Pare, 1986
32  */
33
34 #include "misc.h"
35 #include "player.h"
36 #include "var.h"
37 #include "sect.h"
38 #include "xy.h"
39 #include "nsc.h"
40 #include "deity.h"
41 #include "file.h"
42 #include "nat.h"
43 #include "map.h"
44 #include "commands.h"
45 #include "optlist.h"
46
47 static s_char code_char(long int coding, struct sctstr *sp);
48
49 /*
50  * survey type <sarg> ?cond
51  *
52  */
53 int
54 surv(void)
55 {
56     int nsect;
57     struct nstr_sect nstr;
58     int y;
59     long coding;
60     struct natstr *np;
61     struct sctstr sect;
62     struct range range;
63     s_char *ptr;
64     struct nscstr cond[NS_NCOND];
65     int ncond;
66     int i;
67     s_char what[64];
68     s_char buf[1024];
69     s_char *str;
70     /* Note this is not re-entrant anyway, so we keep the buffers
71        around */
72     static s_char *mapbuf = (s_char *)0;
73     static s_char **map = (s_char **)0;
74
75     nsect = 0;
76     if ((ptr =
77          getstarg(player->argp[1], "commodity or variable? ", buf)) == 0)
78         return RET_SYN;
79     if (encode(ptr, &coding, EF_SECTOR) < 0)
80         return RET_SYN;
81     if (player->argp[2] == (s_char *)0) {
82         if ((str = getstring("(sects)? ", buf)) == 0)
83             return RET_SYN;
84     } else {
85         str = player->argp[2];
86     }
87     if (*str == '*') {
88         sprintf(what, "%d:%d,%d:%d",
89                 -WORLD_X / 2, WORLD_X / 2 - 1,
90                 -WORLD_Y / 2, WORLD_Y / 2 - 1);
91         if (!snxtsct(&nstr, what))
92             return RET_FAIL;
93     } else if (!snxtsct(&nstr, str))
94         return RET_SYN;
95     if (!mapbuf)
96         mapbuf =
97             (s_char *)malloc((WORLD_Y * MAPWIDTH(1)) * sizeof(s_char));
98     if (!map) {
99         map = (s_char **)malloc(WORLD_Y * sizeof(s_char *));
100         if (map && mapbuf) {
101             for (i = 0; i < WORLD_Y; i++)
102                 map[i] = &mapbuf[MAPWIDTH(1) * i];
103         } else if (map) {
104             free((s_char *)map);
105             map = (s_char **)0;
106         }
107     }
108     if (!mapbuf || !map) {
109         pr("Memory error, tell the deity.\n");
110         logerror("malloc failed in sect\n");
111         return RET_FAIL;
112     }
113     ncond = nstr.ncond;
114     bcopy((s_char *)nstr.cond, (s_char *)cond,
115           sizeof(struct nscstr) * ncond);
116     nstr.ncond = 0;
117     np = getnatp(player->cnum);
118     xyrelrange(np, &nstr.range, &range);
119     border(&range, "     ", "");
120     blankfill((s_char *)mapbuf, &nstr.range, 1);
121     while (nxtsct(&nstr, &sect)) {
122         if (!player->owner)
123             continue;
124         ptr = &map[nstr.dy][nstr.dx];
125         if (nstr_exec(cond, ncond, (s_char *)&sect, EF_SECTOR)) {
126             ++nsect;
127             *ptr = 0x80 | code_char(coding, &sect);
128         } else {
129             *ptr = dchr[sect.sct_type].d_mnem;
130         }
131     }
132     for (y = nstr.range.ly, i = 0; i < nstr.range.height; y++, i++) {
133         int yval;
134
135         yval = yrel(np, y);
136         pr("%4d %s %4d\n", yval, map[i], yval);
137         if (y >= WORLD_Y)
138             y -= WORLD_Y;
139     }
140     border(&range, "     ", "");
141     if (nsect > 0)
142         pr("\n%d sector%s.\n", nsect, splur(nsect));
143     return RET_OK;
144 }
145
146 static
147     s_char
148 code_char(long int coding, struct sctstr *sp)
149 {
150     int amt;
151     int n;
152
153     if (!(coding & NSC_VAR))
154         coding |= NSC_OFF;
155     amt = decode(player->cnum, coding, (s_char *)sp, EF_SECTOR);
156     n = 0;
157     if ((coding & NSC_CMASK) == NSC_VAR) {
158         if (amt != 0)
159             n = (amt / 100) + 1;
160     } else if (amt != 0)
161         n = (amt / 10) + 1;
162     if (n > 11)
163         n = 11;
164     if (n < 0)
165         n = 0;
166     return " 0123456789$"[n];
167 }