first pass for new make
[unix-history] / usr / src / games / hack / hack.mhitu.c
CommitLineData
93721f3e
KB
1/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
2/* hack.mhitu.c - version 1.0.3 */
3
4#include "hack.h"
5extern struct monst *makemon();
6
7/*
8 * mhitu: monster hits you
9 * returns 1 if monster dies (e.g. 'y', 'F'), 0 otherwise
10 */
11mhitu(mtmp)
12register struct monst *mtmp;
13{
14 register struct permonst *mdat = mtmp->data;
15 register int tmp, ctmp;
16
17 nomul(0);
18
19 /* If swallowed, can only be affected by hissers and by u.ustuck */
20 if(u.uswallow) {
21 if(mtmp != u.ustuck) {
22 if(mdat->mlet == 'c' && !rn2(13)) {
23 pline("Outside, you hear %s's hissing!",
24 monnam(mtmp));
25 pline("%s gets turned to stone!",
26 Monnam(u.ustuck));
27 pline("And the same fate befalls you.");
28 done_in_by(mtmp);
29 /* "notreached": not return(1); */
30 }
31 return(0);
32 }
33 switch(mdat->mlet) { /* now mtmp == u.ustuck */
34 case ',':
35 youswld(mtmp, (u.uac > 0) ? u.uac+4 : 4,
36 5, "The trapper");
37 break;
38 case '\'':
39 youswld(mtmp,rnd(6),7,"The lurker above");
40 break;
41 case 'P':
42 youswld(mtmp,d(2,4),12,"The purple worm");
43 break;
44 default:
45 /* This is not impossible! */
46 pline("The mysterious monster totally digests you.");
47 u.uhp = 0;
48 }
49 if(u.uhp < 1) done_in_by(mtmp);
50 return(0);
51 }
52
53 if(mdat->mlet == 'c' && Stoned)
54 return(0);
55
56 /* make eels visible the moment they hit/miss us */
57 if(mdat->mlet == ';' && mtmp->minvis && cansee(mtmp->mx,mtmp->my)){
58 mtmp->minvis = 0;
59 pmon(mtmp);
60 }
61 if(!index("1&DuxynNF",mdat->mlet))
62 tmp = hitu(mtmp,d(mdat->damn,mdat->damd));
63 else
64 tmp = 0;
65 if(index(UNDEAD, mdat->mlet) && midnight())
66 tmp += hitu(mtmp,d(mdat->damn,mdat->damd));
67
68 ctmp = tmp && !mtmp->mcan &&
69 (!uarm || objects[uarm->otyp].a_can < rnd(3) || !rn2(50));
70 switch(mdat->mlet) {
71 case '1':
72 if(wiz_hit(mtmp)) return(1); /* he disappeared */
73 break;
74 case '&':
75 if(!mtmp->cham && !mtmp->mcan && !rn2(13)) {
76 (void) makemon(PM_DEMON,u.ux,u.uy);
77 } else {
78 (void) hitu(mtmp,d(2,6));
79 (void) hitu(mtmp,d(2,6));
80 (void) hitu(mtmp,rnd(3));
81 (void) hitu(mtmp,rnd(3));
82 (void) hitu(mtmp,rn1(4,2));
83 }
84 break;
85 case ',':
86 if(tmp) justswld(mtmp,"The trapper");
87 break;
88 case '\'':
89 if(tmp) justswld(mtmp, "The lurker above");
90 break;
91 case ';':
92 if(ctmp) {
93 if(!u.ustuck && !rn2(10)) {
94 pline("%s swings itself around you!",
95 Monnam(mtmp));
96 u.ustuck = mtmp;
97 } else if(u.ustuck == mtmp &&
98 levl[mtmp->mx][mtmp->my].typ == POOL) {
99 pline("%s drowns you ...", Monnam(mtmp));
100 done("drowned");
101 }
102 }
103 break;
104 case 'A':
105 if(ctmp && rn2(2)) {
106 if(Poison_resistance)
107 pline("The sting doesn't seem to affect you.");
108 else {
109 pline("You feel weaker!");
110 losestr(1);
111 }
112 }
113 break;
114 case 'C':
115 (void) hitu(mtmp,rnd(6));
116 break;
117 case 'c':
118 if(!rn2(5)) {
119 pline("You hear %s's hissing!", monnam(mtmp));
120 if(ctmp || !rn2(20) || (flags.moonphase == NEW_MOON
121 && !carrying(DEAD_LIZARD))) {
122 Stoned = 5;
123 /* pline("You get turned to stone!"); */
124 /* done_in_by(mtmp); */
125 }
126 }
127 break;
128 case 'D':
129 if(rn2(6) || mtmp->mcan) {
130 (void) hitu(mtmp,d(3,10));
131 (void) hitu(mtmp,rnd(8));
132 (void) hitu(mtmp,rnd(8));
133 break;
134 }
135 kludge("%s breathes fire!","The dragon");
136 buzz(-1,mtmp->mx,mtmp->my,u.ux-mtmp->mx,u.uy-mtmp->my);
137 break;
138 case 'd':
139 (void) hitu(mtmp,d(2, (flags.moonphase == FULL_MOON) ? 3 : 4));
140 break;
141 case 'e':
142 (void) hitu(mtmp,d(3,6));
143 break;
144 case 'F':
145 if(mtmp->mcan) break;
146 kludge("%s explodes!","The freezing sphere");
147 if(Cold_resistance) pline("You don't seem affected by it.");
148 else {
149 xchar dn;
150 if(17-(u.ulevel/2) > rnd(20)) {
151 pline("You get blasted!");
152 dn = 6;
153 } else {
154 pline("You duck the blast...");
155 dn = 3;
156 }
157 losehp_m(d(dn,6), mtmp);
158 }
159 mondead(mtmp);
160 return(1);
161 case 'g':
162 if(ctmp && multi >= 0 && !rn2(3)) {
163 kludge("You are frozen by %ss juices","the cube'");
164 nomul(-rnd(10));
165 }
166 break;
167 case 'h':
168 if(ctmp && multi >= 0 && !rn2(5)) {
169 nomul(-rnd(10));
170 kludge("You are put to sleep by %ss bite!",
171 "the homunculus'");
172 }
173 break;
174 case 'j':
175 tmp = hitu(mtmp,rnd(3));
176 tmp &= hitu(mtmp,rnd(3));
177 if(tmp){
178 (void) hitu(mtmp,rnd(4));
179 (void) hitu(mtmp,rnd(4));
180 }
181 break;
182 case 'k':
183 if((hitu(mtmp,rnd(4)) || !rn2(3)) && ctmp){
184 poisoned("bee's sting",mdat->mname);
185 }
186 break;
187 case 'L':
188 if(tmp) stealgold(mtmp);
189 break;
190 case 'N':
191 if(mtmp->mcan && !Blind) {
192 pline("%s tries to seduce you, but you seem not interested.",
193 Amonnam(mtmp, "plain"));
194 if(rn2(3)) rloc(mtmp);
195 } else if(steal(mtmp)) {
196 rloc(mtmp);
197 mtmp->mflee = 1;
198 }
199 break;
200 case 'n':
201 if(!uwep && !uarm && !uarmh && !uarms && !uarmg) {
202 pline("%s hits! (I hope you don't mind)",
203 Monnam(mtmp));
204 u.uhp += rnd(7);
205 if(!rn2(7)) u.uhpmax++;
206 if(u.uhp > u.uhpmax) u.uhp = u.uhpmax;
207 flags.botl = 1;
208 if(!rn2(50)) rloc(mtmp);
209 } else {
210 (void) hitu(mtmp,d(2,6));
211 (void) hitu(mtmp,d(2,6));
212 }
213 break;
214 case 'o':
215 tmp = hitu(mtmp,rnd(6));
216 if(hitu(mtmp,rnd(6)) && tmp && /* hits with both paws */
217 !u.ustuck && rn2(2)) {
218 u.ustuck = mtmp;
219 kludge("%s has grabbed you!","The owlbear");
220 u.uhp -= d(2,8);
221 } else if(u.ustuck == mtmp) {
222 u.uhp -= d(2,8);
223 pline("You are being crushed.");
224 }
225 break;
226 case 'P':
227 if(ctmp && !rn2(4))
228 justswld(mtmp,"The purple worm");
229 else
230 (void) hitu(mtmp,d(2,4));
231 break;
232 case 'Q':
233 (void) hitu(mtmp,rnd(2));
234 (void) hitu(mtmp,rnd(2));
235 break;
236 case 'R':
237 if(tmp && uarmh && !uarmh->rustfree &&
238 (int) uarmh->spe >= -1) {
239 pline("Your helmet rusts!");
240 uarmh->spe--;
241 } else
242 if(ctmp && uarm && !uarm->rustfree && /* Mike Newton */
243 uarm->otyp < STUDDED_LEATHER_ARMOR &&
244 (int) uarm->spe >= -1) {
245 pline("Your armor rusts!");
246 uarm->spe--;
247 }
248 break;
249 case 'S':
250 if(ctmp && !rn2(8)) {
251 poisoned("snake's bite",mdat->mname);
252 }
253 break;
254 case 's':
255 if(tmp && !rn2(8)) {
256 poisoned("scorpion's sting",mdat->mname);
257 }
258 (void) hitu(mtmp,rnd(8));
259 (void) hitu(mtmp,rnd(8));
260 break;
261 case 'T':
262 (void) hitu(mtmp,rnd(6));
263 (void) hitu(mtmp,rnd(6));
264 break;
265 case 't':
266 if(!rn2(5)) rloc(mtmp);
267 break;
268 case 'u':
269 mtmp->mflee = 1;
270 break;
271 case 'U':
272 (void) hitu(mtmp,d(3,4));
273 (void) hitu(mtmp,d(3,4));
274 break;
275 case 'v':
276 if(ctmp && !u.ustuck) u.ustuck = mtmp;
277 break;
278 case 'V':
279 if(tmp) u.uhp -= 4;
280 if(ctmp) losexp();
281 break;
282 case 'W':
283 if(ctmp) losexp();
284 break;
285#ifndef NOWORM
286 case 'w':
287 if(tmp) wormhit(mtmp);
288#endif NOWORM
289 break;
290 case 'X':
291 (void) hitu(mtmp,rnd(5));
292 (void) hitu(mtmp,rnd(5));
293 (void) hitu(mtmp,rnd(5));
294 break;
295 case 'x':
296 { register long side = rn2(2) ? RIGHT_SIDE : LEFT_SIDE;
297 pline("%s pricks in your %s leg!",
298 Monnam(mtmp), (side == RIGHT_SIDE) ? "right" : "left");
299 set_wounded_legs(side, rnd(50));
300 losehp_m(2, mtmp);
301 break;
302 }
303 case 'y':
304 if(mtmp->mcan) break;
305 mondead(mtmp);
306 if(!Blind) {
307 pline("You are blinded by a blast of light!");
308 Blind = d(4,12);
309 seeoff(0);
310 }
311 return(1);
312 case 'Y':
313 (void) hitu(mtmp,rnd(6));
314 break;
315 }
316 if(u.uhp < 1) done_in_by(mtmp);
317 return(0);
318}
319
320hitu(mtmp,dam)
321register struct monst *mtmp;
322register dam;
323{
324 register tmp, res;
325
326 nomul(0);
327 if(u.uswallow) return(0);
328
329 if(mtmp->mhide && mtmp->mundetected) {
330 mtmp->mundetected = 0;
331 if(!Blind) {
332 register struct obj *obj;
333 extern char * Xmonnam();
334 if(obj = o_at(mtmp->mx,mtmp->my))
335 pline("%s was hidden under %s!",
336 Xmonnam(mtmp), doname(obj));
337 }
338 }
339
340 tmp = u.uac;
341 /* give people with Ac = -10 at least some vulnerability */
342 if(tmp < 0) {
343 dam += tmp; /* decrease damage */
344 if(dam <= 0) dam = 1;
345 tmp = -rn2(-tmp);
346 }
347 tmp += mtmp->data->mlevel;
348 if(multi < 0) tmp += 4;
349 if((Invis && mtmp->data->mlet != 'I') || !mtmp->mcansee) tmp -= 2;
350 if(mtmp->mtrapped) tmp -= 2;
351 if(tmp <= rnd(20)) {
352 if(Blind) pline("It misses.");
353 else pline("%s misses.",Monnam(mtmp));
354 res = 0;
355 } else {
356 if(Blind) pline("It hits!");
357 else pline("%s hits!",Monnam(mtmp));
358 losehp_m(dam, mtmp);
359 res = 1;
360 }
361 stop_occupation();
362 return(res);
363}