Neale Pickett
·
2011-10-13
handle.c
1#include <curses.h>
2#include "netprot.h"
3
4#define TREAS_ROOM 20 /* one chance in TREAS_ROOM for a treasure room */
5#define MAXTREAS 10 /* maximum number of treasures in a treasure room */
6#define MINTREAS 2 /* minimum number of treasures in a treasure room */
7
8/*
9 * new_level:
10 * Dig and draw a new level
11 *
12 * @(#)handle.c 4.38 (Berkeley) 02/05/99
13 */
14void
15new_level(void)
16{
17 THING *tp;
18 PLACE *pp;
19 char *sp;
20 int i;
21
22 Player.t_flags &= ~ISHELD; /* unhold when you go down just in case */
23 if (Level > Max_level)
24 Max_level = Level;
25 /*
26 * Clean things off from last level
27 */
28 for (pp = Places; pp < &Places[MAXCOLS*MAXLINES]; pp++)
29 {
30 pp->p_ch = ' ';
31 pp->p_flags = F_REAL;
32 pp->p_monst = NULL;
33 }
34 clear();
35 /*
36 * Free up the monsters on the last level
37 */
38 for (tp = Mlist; tp != NULL; tp = next(tp))
39 free_list(tp->t_pack);
40 free_list(Mlist);
41 /*
42 * Throw away stuff left on the previous level (if anything)
43 */
44 free_list(Lvl_obj);
45 do_rooms(); /* Draw rooms */
46 do_passages(); /* Draw passages */
47 No_food++;
48 put_things(); /* Place objects (if any) */
49 /*
50 * Place the traps
51 */
52 if (rnd(10) < Level)
53 {
54 Ntraps = rnd(Level / 4) + 1;
55 if (Ntraps > MAXTRAPS)
56 Ntraps = MAXTRAPS;
57 i = Ntraps;
58 while (i--)
59 {
60 /*
61 * not only wouldn't it be NICE to have traps in mazes
62 * (not that we care about being nice), since the trap
63 * number is stored where the passage number is, we
64 * can't actually do it.
65 */
66 do
67 {
68 find_floor((struct room *) NULL, &Stairs, FALSE, FALSE);
69 } while (chat(Stairs.y, Stairs.x) != FLOOR);
70 sp = &flat(Stairs.y, Stairs.x);
71 *sp &= ~F_REAL;
72 *sp |= rnd(NTRAPS);
73 }
74 }
75 /*
76 * Place the staircase down.
77 */
78 find_floor((struct room *) NULL, &Stairs, FALSE, FALSE);
79 chat(Stairs.y, Stairs.x) = STAIRS;
80 Seenstairs = FALSE;
81
82 for (tp = Mlist; tp != NULL; tp = next(tp))
83 tp->t_room = roomin(&tp->t_pos);
84
85 find_floor((struct room *) NULL, &Hero, FALSE, TRUE);
86 enter_room(&Hero);
87 mvaddch(Hero.y, Hero.x, PLAYER);
88 if (on(Player, SEEMONST))
89 turn_see(FALSE);
90 if (on(Player, ISHALU))
91 visuals();
92}
93
94/*
95 * rnd_room:
96 * Pick a room that is really there
97 */
98int
99rnd_room(void)
100{
101 int rm;
102
103 do
104 {
105 rm = rnd(MAXROOMS);
106 } while (Rooms[rm].r_flags & ISGONE);
107 return rm;
108}
109
110/*
111 * put_things:
112 * Put potions and scrolls on this level
113 */
114void
115put_things(void)
116{
117 int i;
118 THING *obj;
119
120 /*
121 * Once you have found the amulet, the only way to get new stuff is
122 * go down into the dungeon.
123 */
124 if (Amulet && Level < Max_level)
125 return;
126 /*
127 * check for treasure rooms, and if so, put it in.
128 */
129 if (rnd(TREAS_ROOM) == 0)
130 treas_room();
131 /*
132 * Do MAXOBJ attempts to put things on a level
133 */
134 for (i = 0; i < MAXOBJ; i++)
135 if (rnd(100) < 36)
136 {
137 /*
138 * Pick a new object and link it in the list
139 */
140 obj = new_thing();
141 attach(Lvl_obj, obj);
142 /*
143 * Put it somewhere
144 */
145 find_floor((struct room *) NULL, &obj->o_pos, FALSE, FALSE);
146 chat(obj->o_pos.y, obj->o_pos.x) = obj->o_type;
147 }
148 /*
149 * If he is really deep in the dungeon and he hasn't found the
150 * amulet yet, put it somewhere on the ground
151 */
152 if (Level >= AMULETLEVEL && !Amulet)
153 {
154 obj = new_item();
155 attach(Lvl_obj, obj);
156 obj->o_hplus = 0;
157 obj->o_dplus = 0;
158 obj->o_damage = obj->o_hurldmg = "0x0";
159 obj->o_arm = 11;
160 obj->o_type = AMULET;
161 /*
162 * Put it somewhere
163 */
164 find_floor((struct room *) NULL, &obj->o_pos, FALSE, FALSE);
165 chat(obj->o_pos.y, obj->o_pos.x) = AMULET;
166 }
167}
168
169/*
170 * treas_room:
171 * Add a treasure room
172 */
173#define MAXTRIES 10 /* max number of tries to put down a monster */
174
175void
176treas_room(void)
177{
178 int nm;
179 THING *tp;
180 struct room *rp;
181 int spots, num_monst;
182 static coord mp;
183
184 rp = &Rooms[rnd_room()];
185 spots = (rp->r_max.y - 2) * (rp->r_max.x - 2) - MINTREAS;
186 if (spots > (MAXTREAS - MINTREAS))
187 spots = (MAXTREAS - MINTREAS);
188 num_monst = nm = rnd(spots) + MINTREAS;
189 while (nm--)
190 {
191 find_floor(rp, &mp, 2 * MAXTRIES, FALSE);
192 tp = new_thing();
193 tp->o_pos = mp;
194 attach(Lvl_obj, tp);
195 chat(mp.y, mp.x) = tp->o_type;
196 }
197
198 /*
199 * fill up room with monsters from the next level down
200 */
201
202 if ((nm = rnd(spots) + MINTREAS) < num_monst + 2)
203 nm = num_monst + 2;
204 spots = (rp->r_max.y - 2) * (rp->r_max.x - 2);
205 if (nm > spots)
206 nm = spots;
207 Level++;
208 while (nm--)
209 {
210 spots = 0;
211 if (find_floor(rp, &mp, MAXTRIES, TRUE))
212 {
213 tp = new_item();
214 new_monster(tp, randmonster(FALSE), &mp);
215 tp->t_flags |= ISMEAN; /* no sloughers in THIS room */
216 give_pack(tp);
217 }
218 }
219 Level--;
220}