1 /* NetHack 3.6 uhitm.c $NHDT-Date: 1573764936 2019/11/14 20:55:36 $ $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.215 $ */
2 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
3 /*-Copyright (c) Robert Patrick Rankin, 2012. */
4 /* NetHack may be freely redistributed. See license for details. */
6 /* JNetHack Copyright */
7 /* (c) Issei Numata, Naoki Hamada, Shigehiro Miyashita, 1994-2000 */
8 /* For 3.4-, Copyright (c) SHIRAKATA Kentaro, 2002-2019 */
9 /* JNetHack may be freely redistributed. See license for details. */
13 STATIC_DCL boolean FDECL(known_hitum, (struct monst *, struct obj *, int *,
14 int, int, struct attack *, int));
15 STATIC_DCL boolean FDECL(theft_petrifies, (struct obj *));
16 STATIC_DCL void FDECL(steal_it, (struct monst *, struct attack *));
17 STATIC_DCL boolean FDECL(hitum_cleave, (struct monst *, struct attack *));
18 STATIC_DCL boolean FDECL(hitum, (struct monst *, struct attack *));
19 STATIC_DCL boolean FDECL(hmon_hitmon, (struct monst *, struct obj *, int,
21 STATIC_DCL int FDECL(joust, (struct monst *, struct obj *));
22 STATIC_DCL void NDECL(demonpet);
23 STATIC_DCL boolean FDECL(m_slips_free, (struct monst *, struct attack *));
24 STATIC_DCL int FDECL(explum, (struct monst *, struct attack *));
25 STATIC_DCL void FDECL(start_engulf, (struct monst *));
26 STATIC_DCL void NDECL(end_engulf);
27 STATIC_DCL int FDECL(gulpum, (struct monst *, struct attack *));
28 STATIC_DCL boolean FDECL(hmonas, (struct monst *));
29 STATIC_DCL void FDECL(nohandglow, (struct monst *));
30 STATIC_DCL boolean FDECL(shade_aware, (struct obj *));
32 extern boolean notonhead; /* for long worms */
34 /* Used to flag attacks caused by Stormbringer's maliciousness. */
35 static boolean override_confirmation = FALSE;
37 #define PROJECTILE(obj) ((obj) && is_ammo(obj))
40 erode_armor(mdef, hurt)
46 /* What the following code does: it keeps looping until it
47 * finds a target for the rust monster.
48 * Head, feet, etc... not covered by metal, or covered by
49 * rusty metal, are not targets. However, your body always
50 * is, no matter what covers it.
55 target = which_armor(mdef, W_ARMH);
57 || erode_obj(target, xname(target), hurt, EF_GREASE)
62 target = which_armor(mdef, W_ARMC);
64 (void) erode_obj(target, xname(target), hurt,
65 EF_GREASE | EF_VERBOSE);
68 if ((target = which_armor(mdef, W_ARM)) != (struct obj *) 0) {
69 (void) erode_obj(target, xname(target), hurt,
70 EF_GREASE | EF_VERBOSE);
71 } else if ((target = which_armor(mdef, W_ARMU))
72 != (struct obj *) 0) {
73 (void) erode_obj(target, xname(target), hurt,
74 EF_GREASE | EF_VERBOSE);
78 target = which_armor(mdef, W_ARMS);
80 || erode_obj(target, xname(target), hurt, EF_GREASE)
85 target = which_armor(mdef, W_ARMG);
87 || erode_obj(target, xname(target), hurt, EF_GREASE)
92 target = which_armor(mdef, W_ARMF);
94 || erode_obj(target, xname(target), hurt, EF_GREASE)
99 break; /* Out of while loop */
103 /* FALSE means it's OK to attack */
105 attack_checks(mtmp, wep)
106 register struct monst *mtmp;
107 struct obj *wep; /* uwep for attack(), null for kick_monster() */
111 /* if you're close enough to attack, alert any waiting monster */
112 mtmp->mstrategy &= ~STRAT_WAITMASK;
114 if (u.uswallow && mtmp == u.ustuck)
117 if (context.forcefight) {
118 /* Do this in the caller, after we checked that the monster
119 * didn't die from the blow. Reason: putting the 'I' there
120 * causes the hero to forget the square's contents since
121 * both 'I' and remembered contents are stored in .glyph.
122 * If the monster dies immediately from the blow, the 'I' will
123 * not stay there, so the player will have suddenly forgotten
124 * the square's contents for no apparent reason.
125 if (!canspotmon(mtmp)
126 && !glyph_is_invisible(levl[bhitpos.x][bhitpos.y].glyph))
127 map_invisible(bhitpos.x, bhitpos.y);
132 /* cache the shown glyph;
133 cases which might change it (by placing or removing
134 'rembered, unseen monster' glyph or revealing a mimic)
135 always return without further reference to this */
136 glyph = glyph_at(bhitpos.x, bhitpos.y);
138 /* Put up an invisible monster marker, but with exceptions for
139 * monsters that hide and monsters you've been warned about.
140 * The former already prints a warning message and
141 * prevents you from hitting the monster just via the hidden monster
142 * code below; if we also did that here, similar behavior would be
143 * happening two turns in a row. The latter shows a glyph on
144 * the screen, so you know something is there.
146 if (!canspotmon(mtmp)
147 && !glyph_is_warning(glyph) && !glyph_is_invisible(glyph)
148 && !(!Blind && mtmp->mundetected && hides_under(mtmp->data))) {
150 pline("Wait! There's %s there you can't see!", something);
152 pline("
\82¿
\82å
\82Á
\82Æ
\91Ò
\82Á
\82½
\81I
\8ep
\82Ì
\8c©
\82¦
\82È
\82¢%s
\82ª
\82¢
\82é
\81I", something);
153 map_invisible(bhitpos.x, bhitpos.y);
154 /* if it was an invisible mimic, treat it as if we stumbled
155 * onto a visible mimic
157 if (M_AP_TYPE(mtmp) && !Protection_from_shape_changers
158 /* applied pole-arm attack is too far to get stuck */
159 && distu(mtmp->mx, mtmp->my) <= 2) {
160 if (!u.ustuck && !mtmp->mflee && dmgtype(mtmp->data, AD_STCK))
163 /* #H7329 - if hero is on engraved "Elbereth", this will end up
164 * assessing an alignment penalty and removing the engraving
165 * even though no attack actually occurs. Since it also angers
166 * peacefuls, we're operating as if an attack attempt did occur
167 * and the Elbereth behavior is consistent.
169 wakeup(mtmp, TRUE); /* always necessary; also un-mimics mimics */
173 if (M_AP_TYPE(mtmp) && !Protection_from_shape_changers && !sensemon(mtmp)
174 && !glyph_is_warning(glyph)) {
175 /* If a hidden mimic was in a square where a player remembers
176 * some (probably different) unseen monster, the player is in
177 * luck--he attacks it even though it's hidden.
179 if (glyph_is_invisible(glyph)) {
183 stumble_onto_mimic(mtmp);
187 if (mtmp->mundetected && !canseemon(mtmp)
188 && !glyph_is_warning(glyph)
189 && (hides_under(mtmp->data) || mtmp->data->mlet == S_EEL)) {
190 mtmp->mundetected = mtmp->msleeping = 0;
191 newsym(mtmp->mx, mtmp->my);
192 if (glyph_is_invisible(glyph)) {
196 if (!((Blind ? Blind_telepat : Unblind_telepat) || Detect_monsters)) {
199 if (!Blind && Hallucination)
201 pline("A %s %s appeared!",
202 mtmp->mtame ? "tame" : "wild", l_monnam(mtmp));
204 pline("%s%s
\82ª
\8c»
\82ê
\82½
\81I",
205 mtmp->mtame ? "
\8eè
\82È
\82Ã
\82¯
\82ç
\82ê
\82½" : "
\96ì
\90¶
\82Ì", l_monnam(mtmp));
207 else if (Blind || (is_pool(mtmp->mx, mtmp->my) && !Underwater))
209 pline("Wait! There's a hidden monster there!");
211 pline("
\91Ò
\82Ä
\81I
\89ö
\95¨
\82ª
\89B
\82ê
\82Ä
\82¢
\82é
\81I");
212 else if ((obj = level.objects[mtmp->mx][mtmp->my]) != 0)
214 pline("Wait! There's %s hiding under %s!",
215 an(l_monnam(mtmp)), doname(obj));
217 pline("
\91Ò
\82Ä
\81I%s
\82Ì
\89º
\82É%s
\82ª
\89B
\82ê
\82Ä
\82¢
\82é
\81I",
218 doname(obj), l_monnam(mtmp));
225 * make sure to wake up a monster from the above cases if the
226 * hero can sense that the monster is there.
228 if ((mtmp->mundetected || M_AP_TYPE(mtmp)) && sensemon(mtmp)) {
229 mtmp->mundetected = 0;
233 if (flags.confirm && mtmp->mpeaceful
234 && !Confusion && !Hallucination && !Stunned) {
235 /* Intelligent chaotic weapons (Stormbringer) want blood */
236 if (wep && wep->oartifact == ART_STORMBRINGER) {
237 override_confirmation = TRUE;
240 if (canspotmon(mtmp)) {
244 Sprintf(qbuf, "Really attack %s?", mon_nam(mtmp));
246 Sprintf(qbuf, "
\96{
\93\96\82É%s
\82ð
\8dU
\8c\82\82·
\82é
\82Ì
\81H", mon_nam(mtmp));
247 if (!paranoid_query(ParanoidHit, qbuf)) {
258 * It is unchivalrous for a knight to attack the defenseless or from behind.
264 if (u.ualign.record <= -10)
267 if (Role_if(PM_KNIGHT) && u.ualign.type == A_LAWFUL
268 && (!mtmp->mcanmove || mtmp->msleeping
269 || (mtmp->mflee && !mtmp->mavenge))) {
273 pline("
\82±
\82ê
\82Í
\94Ú
\8b¯
\82È
\8ds
\82¢
\82¾
\81I");
275 } else if (Role_if(PM_SAMURAI) && mtmp->mpeaceful) {
276 /* attacking peaceful creatures is bad for the samurai's giri */
278 You("dishonorably attack the innocent!");
280 pline("
\96³
\8eÀ
\82Ì
\8eÒ
\82ð
\8dU
\8c\82\82·
\82é
\82Ì
\82Í
\95s
\96¼
\97_
\82¾
\81I");
286 find_roll_to_hit(mtmp, aatyp, weapon, attk_count, role_roll_penalty)
287 register struct monst *mtmp;
288 uchar aatyp; /* usually AT_WEAP or AT_KICK */
289 struct obj *weapon; /* uwep or uswapwep or NULL */
290 int *attk_count, *role_roll_penalty;
294 *role_roll_penalty = 0; /* default is `none' */
296 tmp = 1 + Luck + abon() + find_mac(mtmp) + u.uhitinc
297 + maybe_polyd(youmonst.data->mlevel, u.ulevel);
299 /* some actions should occur only once during multiple attacks */
300 if (!(*attk_count)++) {
301 /* knight's chivalry or samurai's giri */
305 /* adjust vs. (and possibly modify) monster state */
311 if (mtmp->msleeping) {
315 if (!mtmp->mcanmove) {
323 /* role/race adjustments */
324 if (Role_if(PM_MONK) && !Upolyd) {
326 tmp -= (*role_roll_penalty = urole.spelarmr);
327 else if (!uwep && !uarms)
328 tmp += (u.ulevel / 3) + 2;
330 if (is_orc(mtmp->data)
331 && maybe_polyd(is_elf(youmonst.data), Race_if(PM_ELF)))
334 /* encumbrance: with a lot of luggage, your agility diminishes */
335 if ((tmp2 = near_capacity()) != 0)
336 tmp -= (tmp2 * 2) - 1;
341 * hitval applies if making a weapon attack while wielding a weapon;
342 * weapon_hit_bonus applies if doing a weapon attack even bare-handed
343 * or if kicking as martial artist
345 if (aatyp == AT_WEAP || aatyp == AT_CLAW) {
347 tmp += hitval(weapon, mtmp);
348 tmp += weapon_hit_bonus(weapon);
349 } else if (aatyp == AT_KICK && martial_bonus()) {
350 tmp += weapon_hit_bonus((struct obj *) 0);
356 /* try to attack; return False if monster evaded;
357 u.dx and u.dy must be set */
360 register struct monst *mtmp;
362 register struct permonst *mdat = mtmp->data;
364 /* This section of code provides protection against accidentally
365 * hitting peaceful (like '@') and tame (like 'd') monsters.
366 * Protection is provided as long as player is not: blind, confused,
367 * hallucinating or stunned.
368 * changes by wwp 5/16/85
369 * More changes 12/90, -dkh-. if its tame and safepet, (and protected
370 * 07/92) then we assume that you're not trying to attack. Instead,
371 * you'll usually just swap places if this is a movement command
373 /* Intelligent chaotic weapons (Stormbringer) want blood */
374 if (is_safepet(mtmp) && !context.forcefight) {
375 if (!uwep || uwep->oartifact != ART_STORMBRINGER) {
376 /* There are some additional considerations: this won't work
377 * if in a shop or Punished or you miss a random roll or
378 * if you can walk thru walls and your pet cannot (KAA) or
379 * if your pet is a long worm with a tail.
380 * There's also a chance of displacing a "frozen" monster:
381 * sleeping monsters might magically walk in their sleep.
383 boolean foo = (Punished || !rn2(7)
384 || (is_longworm(mtmp->data) && mtmp->wormno)),
388 /* only check for in-shop if don't already have reason to stop */
390 for (p = in_rooms(mtmp->mx, mtmp->my, SHOPBASE); *p; p++)
391 if (tended_shop(&rooms[*p - ROOMOFFSET])) {
396 if (inshop || foo || (IS_ROCK(levl[u.ux][u.uy].typ)
397 && !passes_walls(mtmp->data))) {
400 monflee(mtmp, rnd(6), FALSE, FALSE);
401 Strcpy(buf, y_monnam(mtmp));
402 buf[0] = highc(buf[0]);
404 You("stop. %s is in the way!", buf);
406 You("
\8e~
\82Ü
\82Á
\82½
\81D%s
\82ª
\93¹
\82É
\82¢
\82é
\81I", buf);
407 context.travel = context.travel1 = context.mv = context.run
410 } else if ((mtmp->mfrozen || (!mtmp->mcanmove)
411 || (mtmp->data->mmove == 0)) && rn2(6)) {
413 pline("%s doesn't seem to move!", Monnam(mtmp));
415 pline("%s
\82Í
\93®
\82¯
\82È
\82¢
\82æ
\82¤
\82¾
\81I", Monnam(mtmp));
416 context.travel = context.travel1 = context.mv = context.run
424 /* possibly set in attack_checks;
425 examined in known_hitum, called via hitum or hmonas below */
426 override_confirmation = FALSE;
427 /* attack_checks() used to use <u.ux+u.dx,u.uy+u.dy> directly, now
428 it uses bhitpos instead; it might map an invisible monster there */
429 bhitpos.x = u.ux + u.dx;
430 bhitpos.y = u.uy + u.dy;
431 notonhead = (bhitpos.x != mtmp->mx || bhitpos.y != mtmp->my);
432 if (attack_checks(mtmp, uwep))
435 if (Upolyd && noattacks(youmonst.data)) {
436 /* certain "pacifist" monsters don't attack */
438 You("have no way to attack monsters physically.");
440 You("
\95¨
\97\9d\93I
\82É
\89ö
\95¨
\82ð
\8dU
\8c\82\82·
\82é
\82·
\82×
\82ª
\82È
\82¢
\81D");
441 mtmp->mstrategy &= ~STRAT_WAITMASK;
446 if (check_capacity("You cannot fight while so heavily loaded.")
448 if (check_capacity("
\82 \82È
\82½
\82Í
\95¨
\82ð
\82½
\82
\82³
\82ñ
\8e\9d\82¿
\82·
\82¬
\82Ä
\90í
\82¦
\82È
\82¢
\81D")
449 /* consume extra nutrition during combat; maybe pass out */
453 if (u.twoweap && !can_twoweapon())
461 You("begin bashing monsters with %s.", yname(uwep));
463 You("%s
\82Å
\89ö
\95¨
\82ð
\82È
\82®
\82è
\82Â
\82¯
\82½
\81D", yname(uwep));
464 else if (!cantwield(youmonst.data))
466 You("begin %s monsters with your %s %s.",
467 ing_suffix(Role_if(PM_MONK) ? "strike" : "bash"),
468 uarmg ? "gloved" : "bare", /* Del Lamb */
469 makeplural(body_part(HAND)));
471 You("%s%s
\82Å
\89ö
\95¨
\82ð%s
\82Â
\82¯
\82½
\81D",
472 uarmg ? "
\83O
\83\8d\81[
\83u
\82ð
\95t
\82¯
\82½" : "
\91f",
474 Role_if(PM_MONK) ? "
\91Å
\82¿" : "
\82È
\82®
\82è");
478 exercise(A_STR, TRUE); /* you're exercising muscles */
479 /* andrew@orca: prevent unlimited pick-axe attacks */
482 /* Is the "it died" check actually correct? */
483 if (mdat->mlet == S_LEPRECHAUN && !mtmp->mfrozen && !mtmp->msleeping
484 && !mtmp->mconf && mtmp->mcansee && !rn2(7)
485 && (m_move(mtmp, 0) == 2 /* it died */
486 || mtmp->mx != u.ux + u.dx
487 || mtmp->my != u.uy + u.dy)) { /* it moved */
489 You("miss wildly and stumble forwards.");
491 You("
\91å
\82«
\82
\8aO
\82µ
\82Ä
\91O
\82É
\82Â
\82Ü
\82Ã
\82¢
\82½
\81D");
498 (void) hitum(mtmp, youmonst.data->mattk);
499 mtmp->mstrategy &= ~STRAT_WAITMASK;
502 /* see comment in attack_checks() */
503 /* we only need to check for this if we did an attack_checks()
504 * and it returned 0 (it's okay to attack), and the monster didn't
507 if (context.forcefight && !DEADMONSTER(mtmp) && !canspotmon(mtmp)
508 && !glyph_is_invisible(levl[u.ux + u.dx][u.uy + u.dy].glyph)
509 && !(u.uswallow && mtmp == u.ustuck))
510 map_invisible(u.ux + u.dx, u.uy + u.dy);
515 /* really hit target monster; returns TRUE if it still lives */
517 known_hitum(mon, weapon, mhit, rollneeded, armorpenalty, uattk, dieroll)
518 register struct monst *mon;
521 int rollneeded, armorpenalty; /* for monks */
522 struct attack *uattk;
525 boolean malive = TRUE,
526 /* hmon() might destroy weapon; remember aspect for cutworm */
527 slice_or_chop = (weapon && (is_blade(weapon) || is_axe(weapon)));
529 if (override_confirmation) {
530 /* this may need to be generalized if weapons other than
531 Stormbringer acquire similar anti-social behavior... */
534 Your("bloodthirsty blade attacks!");
536 Your("
\95\90\8aí
\82Í
\8c\8c\82É
\8bQ
\82¦
\82Ä
\82¢
\82é
\81I");
540 missum(mon, uattk, (rollneeded + armorpenalty > dieroll));
542 int oldhp = mon->mhp;
543 long oldweaphit = u.uconduct.weaphit;
546 if (weapon && (weapon->oclass == WEAPON_CLASS || is_weptool(weapon)))
547 u.uconduct.weaphit++;
549 /* we hit the monster; be careful: it might die or
550 be knocked into a different location */
551 notonhead = (mon->mx != bhitpos.x || mon->my != bhitpos.y);
552 malive = hmon(mon, weapon, HMON_MELEE, dieroll);
554 /* monster still alive */
555 if (!rn2(25) && mon->mhp < mon->mhpmax / 2
556 && !(u.uswallow && mon == u.ustuck)) {
557 /* maybe should regurgitate if swallowed? */
558 monflee(mon, !rn2(3) ? rnd(100) : 0, FALSE, TRUE);
560 if (u.ustuck == mon && !u.uswallow && !sticks(youmonst.data))
563 /* Vorpal Blade hit converted to miss */
564 /* could be headless monster or worm tail */
565 if (mon->mhp == oldhp) {
567 /* a miss does not break conduct */
568 u.uconduct.weaphit = oldweaphit;
570 if (mon->wormno && *mhit)
571 cutworm(mon, bhitpos.x, bhitpos.y, slice_or_chop);
577 /* hit the monster next to you and the monsters to the left and right of it;
578 return False if the primary target is killed, True otherwise */
580 hitum_cleave(target, uattk)
581 struct monst *target; /* non-Null; forcefight at nothing doesn't cleave... */
582 struct attack *uattk; /* ... but we don't enforce that here; Null works ok */
584 /* swings will be delivered in alternate directions; with consecutive
585 attacks it will simulate normal swing and backswing; when swings
586 are non-consecutive, hero will sometimes start a series of attacks
587 with a backswing--that doesn't impact actual play, just spoils the
588 simulation attempt a bit */
589 static boolean clockwise = FALSE;
592 int count, umort, x = u.ux, y = u.uy;
594 /* find the direction toward primary target */
595 for (i = 0; i < 8; ++i)
596 if (xdir[i] == u.dx && ydir[i] == u.dy)
599 impossible("hitum_cleave: unknown target direction [%d,%d,%d]?",
601 return TRUE; /* target hasn't been killed */
603 /* adjust direction by two so that loop's increment (for clockwise)
604 or decrement (for counter-clockwise) will point at the spot next
606 i = (i + (clockwise ? 6 : 2)) % 8;
607 umort = u.umortality; /* used to detect life-saving */
608 save_bhitpos = bhitpos;
611 * Three attacks: adjacent to primary, primary, adjacent on other
612 * side. Primary target must be present or we wouldn't have gotten
613 * here (forcefight at thin air won't 'cleave'). However, the
614 * first attack might kill it (gas spore explosion, weak long worm
615 * occupying both spots) so we don't assume that it's still present
616 * on the second attack.
618 for (count = 3; count > 0; --count) {
620 int tx, ty, tmp, dieroll, mhit, attknum, armorpenalty;
622 /* ++i, wrap 8 to i=0 /or/ --i, wrap -1 to i=7 */
623 i = (i + (clockwise ? 1 : 7)) % 8;
625 tx = x + xdir[i], ty = y + ydir[i]; /* current target location */
630 if (glyph_is_invisible(levl[tx][ty].glyph))
631 (void) unmap_invisible(tx, ty);
635 tmp = find_roll_to_hit(mtmp, uattk->aatyp, uwep,
636 &attknum, &armorpenalty);
638 mhit = (tmp > dieroll);
639 bhitpos.x = tx, bhitpos.y = ty; /* normally set up by attack() */
640 (void) known_hitum(mtmp, uwep, &mhit, tmp, armorpenalty,
642 (void) passive(mtmp, uwep, mhit, !DEADMONSTER(mtmp), AT_WEAP, !uwep);
644 /* stop attacking if weapon is gone or hero got killed and
645 life-saved after passive counter-attack */
646 if (!uwep || u.umortality > umort)
649 /* set up for next time */
650 clockwise = !clockwise; /* alternate */
651 bhitpos = save_bhitpos; /* in case somebody relies on bhitpos
652 * designating the primary target */
654 /* return False if primary target died, True otherwise; note: if 'target'
655 was nonNull upon entry then it's still nonNull even if *target died */
656 return (target && DEADMONSTER(target)) ? FALSE : TRUE;
659 /* hit target monster; returns TRUE if it still lives */
663 struct attack *uattk;
665 boolean malive, wep_was_destroyed = FALSE;
666 struct obj *wepbefore = uwep;
667 int armorpenalty, attknum = 0, x = u.ux + u.dx, y = u.uy + u.dy,
668 tmp = find_roll_to_hit(mon, uattk->aatyp, uwep,
669 &attknum, &armorpenalty);
670 int dieroll = rnd(20);
671 int mhit = (tmp > dieroll || u.uswallow);
673 /* Cleaver attacks three spots, 'mon' and one on either side of 'mon';
674 it can't be part of dual-wielding but we guard against that anyway;
675 cleave return value reflects status of primary target ('mon') */
676 if (uwep && uwep->oartifact == ART_CLEAVER && !u.twoweap
677 && !u.uswallow && !u.ustuck && !NODIAG(u.umonnum))
678 return hitum_cleave(mon, uattk);
681 exercise(A_DEX, TRUE);
682 /* bhitpos is set up by caller */
683 malive = known_hitum(mon, uwep, &mhit, tmp, armorpenalty, uattk, dieroll);
684 if (wepbefore && !uwep)
685 wep_was_destroyed = TRUE;
686 (void) passive(mon, uwep, mhit, malive, AT_WEAP, wep_was_destroyed);
688 /* second attack for two-weapon combat; won't occur if Stormbringer
689 overrode confirmation (assumes Stormbringer is primary weapon)
690 or if the monster was killed or knocked to different location */
691 if (u.twoweap && !override_confirmation && malive && m_at(x, y) == mon) {
692 tmp = find_roll_to_hit(mon, uattk->aatyp, uswapwep, &attknum,
695 mhit = (tmp > dieroll || u.uswallow);
696 malive = known_hitum(mon, uswapwep, &mhit, tmp, armorpenalty, uattk,
698 /* second passive counter-attack only occurs if second attack hits */
700 (void) passive(mon, uswapwep, mhit, malive, AT_WEAP, !uswapwep);
705 /* general "damage monster" routine; return True if mon still alive */
707 hmon(mon, obj, thrown, dieroll)
710 int thrown; /* HMON_xxx (0 => hand-to-hand, other => ranged) */
713 boolean result, anger_guards;
715 anger_guards = (mon->mpeaceful
716 && (mon->ispriest || mon->isshk || is_watch(mon->data)));
717 result = hmon_hitmon(mon, obj, thrown, dieroll);
718 if (mon->ispriest && !rn2(2))
721 (void) angry_guards(!!Deaf);
727 hmon_hitmon(mon, obj, thrown, dieroll)
730 int thrown; /* HMON_xxx (0 => hand-to-hand, other => ranged) */
734 struct permonst *mdat = mon->data;
735 int barehand_silver_rings = 0;
736 /* The basic reason we need all these booleans is that we don't want
737 * a "hit" message when a monster dies, so we have to know how much
738 * damage it did _before_ outputting a hit message, but any messages
739 * associated with the damage don't come out until _after_ outputting
742 boolean hittxt = FALSE, destroyed = FALSE, already_killed = FALSE;
743 boolean get_dmg_bonus = TRUE;
744 boolean ispoisoned = FALSE, needpoismsg = FALSE, poiskilled = FALSE,
746 boolean silvermsg = FALSE, silverobj = FALSE;
747 boolean lightobj = FALSE;
748 boolean valid_weapon_attack = FALSE;
749 boolean unarmed = !uwep && !uarm && !uarms;
750 boolean hand_to_hand = (thrown == HMON_MELEE
751 /* not grapnels; applied implies uwep */
752 || (thrown == HMON_APPLIED && is_pole(uwep)));
757 char saved_oname[BUFSZ];
759 saved_oname[0] = '\0';
762 if (!obj) { /* attack with bare hands */
763 if (mdat == &mons[PM_SHADE])
765 else if (martial_bonus())
766 tmp = rnd(4); /* bonus for martial arts */
769 valid_weapon_attack = (tmp > 1);
770 /* Blessed gloves give bonuses when fighting 'bare-handed'. So do
771 silver rings. Note: rings are worn under gloves, so you don't
772 get both bonuses, and two silver rings don't give double bonus. */
773 tmp += special_dmgval(&youmonst, mon, (W_ARMG | W_RINGL | W_RINGR),
775 barehand_silver_rings += (((silverhit & W_RINGL) ? 1 : 0)
776 + ((silverhit & W_RINGR) ? 1 : 0));
777 if (barehand_silver_rings > 0)
780 if (!(artifact_light(obj) && obj->lamplit))
781 Strcpy(saved_oname, cxname(obj));
783 Strcpy(saved_oname, bare_artifactname(obj));
784 if (obj->oclass == WEAPON_CLASS || is_weptool(obj)
785 || obj->oclass == GEM_CLASS) {
786 /* is it not a melee weapon? */
787 if (/* if you strike with a bow... */
789 /* or strike with a missile in your hand... */
790 || (!thrown && (is_missile(obj) || is_ammo(obj)))
791 /* or use a pole at short range and not mounted... */
792 || (!thrown && !u.usteed && is_pole(obj))
793 /* or throw a missile without the proper bow... */
794 || (is_ammo(obj) && (thrown != HMON_THROWN
795 || !ammo_and_launcher(obj, uwep)))) {
796 /* then do only 1-2 points of damage */
797 if (mdat == &mons[PM_SHADE] && !shade_glare(obj))
801 if (objects[obj->otyp].oc_material == SILVER
802 && mon_hates_silver(mon)) {
805 /* if it will already inflict dmg, make it worse */
806 tmp += rnd((tmp) ? 20 : 10);
808 if (!thrown && obj == uwep && obj->otyp == BOOMERANG
809 && rnl(4) == 4 - 1) {
810 boolean more_than_1 = (obj->quan > 1L);
813 pline("As you hit %s, %s%s breaks into splinters.",
814 mon_nam(mon), more_than_1 ? "one of " : "",
817 pline("%s
\82ð
\8dU
\8c\82\82·
\82é
\82Æ
\81C%s%s
\82Í
\82±
\82Á
\82Ï
\82Ý
\82¶
\82ñ
\82É
\82È
\82Á
\82½
\81D",
818 mon_nam(mon), yname(obj),
819 more_than_1 ? "
\82Ì
\82Ð
\82Æ
\82Â" : "");
822 uwepgone(); /* set unweapon */
825 obj = (struct obj *) 0;
827 if (mdat != &mons[PM_SHADE])
831 tmp = dmgval(obj, mon);
832 /* a minimal hit doesn't exercise proficiency */
833 valid_weapon_attack = (tmp > 1);
834 if (!valid_weapon_attack || mon == u.ustuck || u.twoweap
835 /* Cleaver can hit up to three targets at once so don't
836 let it also hit from behind or shatter foes' weapons */
837 || (hand_to_hand && obj->oartifact == ART_CLEAVER)) {
838 ; /* no special bonuses */
839 } else if (mon->mflee && Role_if(PM_ROGUE) && !Upolyd
840 /* multi-shot throwing is too powerful here */
843 You("strike %s from behind!", mon_nam(mon));
845 You("%s
\82ð
\94w
\8cã
\82©
\82ç
\8dU
\8c\82\82µ
\82½
\81I", mon_nam(mon));
846 tmp += rnd(u.ulevel);
848 } else if (dieroll == 2 && obj == uwep
849 && obj->oclass == WEAPON_CLASS
851 || (Role_if(PM_SAMURAI) && obj->otyp == KATANA
853 && ((wtype = uwep_skill_type()) != P_NONE
854 && P_SKILL(wtype) >= P_SKILLED)
855 && ((monwep = MON_WEP(mon)) != 0
856 && !is_flimsy(monwep)
857 && !obj_resists(monwep,
858 50 + 15 * (greatest_erosion(obj)
859 - greatest_erosion(monwep)),
862 * 2.5% chance of shattering defender's weapon when
863 * using a two-handed weapon; less if uwep is rusted.
864 * [dieroll == 2 is most successful non-beheading or
865 * -bisecting hit, in case of special artifact damage;
866 * the percentage chance is (1/20)*(50/100).]
867 * If attacker's weapon is rustier than defender's,
868 * the obj_resists chance is increased so the shatter
869 * chance is decreased; if less rusty, then vice versa.
871 setmnotwielded(mon, monwep);
872 mon->weapon_check = NEED_WEAPON;
874 pline("%s from the force of your blow!",
875 Yobjnam2(monwep, "shatter"));
877 pline("%s
\82Ì%s
\82Í
\82 \82È
\82½
\82Ì
\88ê
\8c\82\82Å
\95²
\81X
\82É
\82È
\82Á
\82½
\81I",
878 Monnam(mon), xname(monwep));
880 m_useupall(mon, monwep);
881 /* If someone just shattered MY weapon, I'd flee! */
883 monflee(mon, d(2, 3), TRUE, TRUE);
889 && artifact_hit(&youmonst, mon, obj, &tmp, dieroll)) {
890 if (DEADMONSTER(mon)) /* artifact killed monster */
896 if (objects[obj->otyp].oc_material == SILVER
897 && mon_hates_silver(mon)) {
901 if (artifact_light(obj) && obj->lamplit
902 && mon_hates_light(mon))
904 if (u.usteed && !thrown && tmp > 0
905 && weapon_type(obj) == P_LANCE && mon != u.ustuck) {
906 jousting = joust(mon, obj);
907 /* exercise skill even for minimal damage hits */
909 valid_weapon_attack = TRUE;
911 if (thrown == HMON_THROWN
912 && (is_ammo(obj) || is_missile(obj))) {
913 if (ammo_and_launcher(obj, uwep)) {
914 /* Elves and Samurai do extra damage using
915 * their bows&arrows; they're highly trained.
917 if (Role_if(PM_SAMURAI) && obj->otyp == YA
918 && uwep->otyp == YUMI)
920 else if (Race_if(PM_ELF) && obj->otyp == ELVEN_ARROW
921 && uwep->otyp == ELVEN_BOW)
924 if (obj->opoisoned && is_poisonable(obj))
928 } else if (obj->oclass == POTION_CLASS) {
930 obj = splitobj(obj, 1L);
932 setuwep((struct obj *) 0);
935 hand_to_hand ? POTHIT_HERO_BASH : POTHIT_HERO_THROW);
936 if (DEADMONSTER(mon))
937 return FALSE; /* killed */
939 /* in case potion effect causes transformation */
941 tmp = (mdat == &mons[PM_SHADE]) ? 0 : 1;
943 if (mdat == &mons[PM_SHADE] && !shade_aware(obj)) {
947 case BOULDER: /* 1d20 */
948 case HEAVY_IRON_BALL: /* 1d25 */
949 case IRON_CHAIN: /* 1d4+1 */
950 tmp = dmgval(obj, mon);
953 if (breaktest(obj)) {
955 You("break %s. That's bad luck!", ysimple_name(obj));
957 You("%s
\8b¾
\82ð
\89ó
\82µ
\82Ä
\82µ
\82Ü
\82Á
\82½
\81D
\82±
\82è
\82á
\82Ü
\82¢
\82Á
\82½
\81I", ysimple_name(obj));
960 obj = (struct obj *) 0;
961 unarmed = FALSE; /* avoid obj==0 confusion */
962 get_dmg_bonus = FALSE;
967 case EXPENSIVE_CAMERA:
969 You("succeed in destroying %s. Congratulations!",
971 You("%s
\83J
\83\81\83\89\82ð
\89ó
\82·
\82±
\82Æ
\82ª
\82Å
\82«
\82½
\81D
\82¨
\82ß
\82Å
\82Æ
\82¤
\81I",
973 release_camera_demon(obj, u.ux, u.uy);
976 case CORPSE: /* fixed by polder@cs.vu.nl */
977 if (touch_petrifies(&mons[obj->corpsenm])) {
981 You("hit %s with %s.", mon_nam(mon),
982 corpse_xname(obj, (const char *) 0,
983 obj->dknown ? CXN_PFX_THE
986 You("%s
\82ð%s
\82Å
\8dU
\8c\82\82µ
\82½
\81D", mon_nam(mon),
987 corpse_xname(obj, (const char *) 0,
988 obj->dknown ? CXN_PFX_THE
992 if (!munstone(mon, TRUE))
993 minstapetrify(mon, TRUE);
994 if (resists_ston(mon))
996 /* note: hp may be <= 0 even if munstoned==TRUE */
997 return (boolean) !DEADMONSTER(mon);
999 } else if (touch_petrifies(mdat)) {
1000 ; /* maybe turn the corpse into a statue? */
1003 tmp = (obj->corpsenm >= LOW_PM ? mons[obj->corpsenm].msize
1007 #define useup_eggs(o) \
1010 obfree(o, (struct obj *) 0); \
1013 o = (struct obj *) 0; \
1014 } while (0) /* now gone */
1016 long cnt = obj->quan;
1018 tmp = 1; /* nominal physical damage */
1019 get_dmg_bonus = FALSE;
1020 hittxt = TRUE; /* message always given */
1021 /* egg is always either used up or transformed, so next
1022 hand-to-hand attack should yield a "bashing" mesg */
1025 if (obj->spe && obj->corpsenm >= LOW_PM) {
1027 change_luck((schar) - (obj->quan));
1032 if (touch_petrifies(&mons[obj->corpsenm])) {
1033 /*learn_egg_type(obj->corpsenm);*/
1035 pline("Splat! You hit %s with %s %s egg%s!",
1037 obj->known ? "the" : cnt > 1L ? "some" : "a",
1038 obj->known ? mons[obj->corpsenm].mname
1042 pline("
\83r
\83`
\83\83\83b
\81I
\82 \82È
\82½
\82Í%s
\82É%s%s
\82Ì
\97\91\82ð
\93\8a\82°
\82Â
\82¯
\82½
\81I",
1044 cnt > 1L ? "
\82¢
\82
\82Â
\82©
\82Ì" : "",
1045 obj->known ? mons[obj->corpsenm].mname
1048 obj->known = 1; /* (not much point...) */
1050 if (!munstone(mon, TRUE))
1051 minstapetrify(mon, TRUE);
1052 if (resists_ston(mon))
1054 return (boolean) (!DEADMONSTER(mon));
1055 } else { /* ordinary egg(s) */
1057 const char *eggp = (obj->corpsenm != NON_PM
1059 ? the(mons[obj->corpsenm].mname)
1060 : (cnt > 1L) ? "some" : "an";
1062 You("hit %s with %s egg%s.", mon_nam(mon), eggp,
1065 const char *eggp = (obj->corpsenm != NON_PM
1067 ? mons[obj->corpsenm].mname
1069 You("%s
\82É%s%s
\97\91\82ð
\93\8a\82°
\82Â
\82¯
\82½
\81D",
1070 mon_nam(mon), eggp, *eggp ? "
\82Ì" : "");
1072 if (touch_petrifies(mdat) && !stale_egg(obj)) {
1074 pline_The("egg%s %s alive any more...", plur(cnt),
1075 (cnt == 1L) ? "isn't" : "aren't");
1077 pline("
\82à
\82¤
\97\91\82ª
\9bz
\89»
\82·
\82é
\82±
\82Æ
\82Í
\82È
\82¢
\82¾
\82ë
\82¤
\81D
\81D
\81D");
1080 obj_stop_timers(obj);
1082 obj->oclass = GEM_CLASS;
1085 obj->known = obj->dknown = obj->bknown = 0;
1086 obj->owt = weight(obj);
1088 place_object(obj, mon->mx, mon->my);
1093 pline("
\83r
\83`
\83\83\83b
\81I");
1095 exercise(A_WIS, FALSE);
1101 case CLOVE_OF_GARLIC: /* no effect against demons */
1102 if (is_undead(mdat) || is_vampshifter(mon)) {
1103 monflee(mon, d(2, 4), FALSE, TRUE);
1108 case BLINDING_VENOM:
1110 if (can_blnd(&youmonst, mon,
1111 (uchar) ((obj->otyp == BLINDING_VENOM)
1117 pline(obj->otyp == CREAM_PIE ? "Splat!"
1120 pline(obj->otyp == CREAM_PIE ? "
\83r
\83V
\83\83\83b
\81I"
1121 : "
\83s
\83`
\83\83\83b
\81I");
1123 } else if (obj->otyp == BLINDING_VENOM) {
1125 pline_The("venom blinds %s%s!", mon_nam(mon),
1126 mon->mcansee ? "" : " further");
1128 pline("
\93Å
\89t
\82Å%s
\82Í%s
\96Ú
\82ª
\8c©
\82¦
\82È
\82
\82È
\82Á
\82½
\81I", mon_nam(mon),
1129 mon->mcansee ? "" : "
\82³
\82ç
\82É");
1132 char *whom = mon_nam(mon);
1133 char *what = The(xname(obj));
1135 if (!thrown && obj->quan > 1L)
1136 what = An(singular(obj, xname));
1137 /* note: s_suffix returns a modifiable buffer */
1139 && mdat != &mons[PM_FLOATING_EYE])
1141 whom = strcat(strcat(s_suffix(whom), " "),
1142 mbodypart(mon, FACE));
1144 whom = strcat(s_suffix(whom),
1145 mbodypart(mon, FACE));
1148 pline("%s %s over %s!", what,
1149 vtense(what, "splash"), whom);
1151 pline("%s
\82Í%s
\82É
\82Ô
\82¿
\82Ü
\82¯
\82ç
\82ê
\82½
\81I",
1155 setmangry(mon, TRUE);
1158 if (((int) mon->mblinded + tmp) > 127)
1159 mon->mblinded = 127;
1161 mon->mblinded += tmp;
1164 pline(obj->otyp == CREAM_PIE ? "Splat!" : "Splash!");
1166 pline(obj->otyp==CREAM_PIE ? "
\83r
\83V
\83\83\83b
\81I" : "
\83s
\83`
\83\83\83b
\81I");
1167 setmangry(mon, TRUE);
1170 obfree(obj, (struct obj *) 0);
1174 get_dmg_bonus = FALSE;
1177 case ACID_VENOM: /* thrown (or spit) */
1178 if (resists_acid(mon)) {
1180 Your("venom hits %s harmlessly.", mon_nam(mon));
1182 pline("
\93Å
\89t
\82Í%s
\82É
\82Í
\8cø
\89Ê
\82ª
\82È
\82©
\82Á
\82½
\81D", mon_nam(mon));
1186 Your("venom burns %s!", mon_nam(mon));
1188 Your("
\93Å
\89t
\82Í%s
\82ð
\8fÄ
\82¢
\82½
\81I", mon_nam(mon));
1189 tmp = dmgval(obj, mon);
1192 obfree(obj, (struct obj *) 0);
1196 get_dmg_bonus = FALSE;
1199 /* non-weapons can damage because of their weight */
1200 /* (but not too much) */
1201 tmp = obj->owt / 100;
1202 if (is_wet_towel(obj)) {
1203 /* wielded wet towel should probably use whip skill
1204 (but not by setting objects[TOWEL].oc_skill==P_WHIP
1205 because that would turn towel into a weptool) */
1207 if (rn2(obj->spe + 1)) /* usually lose some wetness */
1208 dry_a_towel(obj, -1, TRUE);
1217 * Things like silver wands can arrive here so
1218 * so we need another silver check.
1220 if (objects[obj->otyp].oc_material == SILVER
1221 && mon_hates_silver(mon)) {
1231 /****** NOTE: perhaps obj is undefined!! (if !thrown && BOOMERANG)
1232 * *OR* if attacking bare-handed!! */
1234 if (get_dmg_bonus && tmp > 0) {
1236 /* If you throw using a propellor, you don't get a strength
1237 * bonus but you do get an increase-damage bonus.
1239 if (thrown != HMON_THROWN || !obj || !uwep
1240 || !ammo_and_launcher(obj, uwep))
1244 if (valid_weapon_attack) {
1247 /* to be valid a projectile must have had the correct projector */
1248 wep = PROJECTILE(obj) ? uwep : obj;
1249 tmp += weapon_dam_bonus(wep);
1250 /* [this assumes that `!thrown' implies wielded...] */
1251 wtype = thrown ? weapon_type(wep) : uwep_skill_type();
1252 use_skill(wtype, 1);
1256 int nopoison = (10 - (obj->owt / 10));
1260 if (Role_if(PM_SAMURAI)) {
1262 You("dishonorably use a poisoned weapon!");
1264 You("
\95s
\96¼
\97_
\82É
\82à
\93Å
\82Ì
\95\90\8aí
\82ð
\8eg
\97p
\82µ
\82½
\81I");
1265 adjalign(-sgn(u.ualign.type));
1266 } else if (u.ualign.type == A_LAWFUL && u.ualign.record > -10) {
1268 You_feel("like an evil coward for using a poisoned weapon.");
1270 You("
\93Å
\82Ì
\95\90\8aí
\82ð
\8eg
\97p
\82·
\82é
\82Ì
\82Í
\94Ú
\8b¯
\82¾
\82Æ
\8a´
\82¶
\82½
\81D");
1273 if (obj && !rn2(nopoison)) {
1274 /* remove poison now in case obj ends up in a bones file */
1275 obj->opoisoned = FALSE;
1276 /* defer "obj is no longer poisoned" until after hit message */
1279 if (resists_poison(mon))
1287 boolean mon_is_shade = (mon->data == &mons[PM_SHADE]);
1289 /* make sure that negative damage adjustment can't result
1290 in inadvertently boosting the victim's hit points */
1291 tmp = (get_dmg_bonus && !mon_is_shade) ? 1 : 0;
1292 if (mon_is_shade && !hittxt
1293 && thrown != HMON_THROWN && thrown != HMON_KICKED)
1294 hittxt = shade_miss(&youmonst, mon, obj, FALSE, TRUE);
1298 tmp += d(2, (obj == uwep) ? 10 : 2); /* [was in dmgval()] */
1300 You("joust %s%s", mon_nam(mon), canseemon(mon) ? exclam(tmp) : ".");
1302 You("%s
\82É
\93Ë
\8c\82\82µ
\82½%s", mon_nam(mon), canseemon(mon) ? exclam(tmp) : "
\81D");
1305 pline("%s shatters on impact!", Yname2(obj));
1307 Your("%s
\82Í
\8fÕ
\8c\82\82Å
\89ó
\82ê
\82½
\81I", xname(obj));
1308 /* (must be either primary or secondary weapon to get here) */
1309 u.twoweap = FALSE; /* untwoweapon() is too verbose here */
1311 uwepgone(); /* set unweapon */
1312 /* minor side-effect: broken lance won't split puddings */
1316 /* avoid migrating a dead monster */
1317 if (mon->mhp > tmp) {
1318 mhurtle(mon, u.dx, u.dy, 1);
1319 mdat = mon->data; /* in case of a polymorph trap */
1320 if (DEADMONSTER(mon))
1321 already_killed = TRUE;
1324 } else if (unarmed && tmp > 1 && !thrown && !obj && !Upolyd) {
1325 /* VERY small chance of stunning opponent if unarmed. */
1326 if (rnd(100) < P_SKILL(P_BARE_HANDED_COMBAT) && !bigmonst(mdat)
1327 && !thick_skinned(mdat)) {
1328 if (canspotmon(mon))
1330 pline("%s %s from your powerful strike!", Monnam(mon),
1331 makeplural(stagger(mon->data, "stagger")));
1333 pline("%s
\82Í
\82 \82È
\82½
\82Ì
\89ï
\90S
\82Ì
\88ê
\8c\82\82Å%s
\81I", Monnam(mon),
1334 jpast(stagger(mon->data, "
\82æ
\82ë
\82ß
\82")));
1336 /* avoid migrating a dead monster */
1337 if (mon->mhp > tmp) {
1338 mhurtle(mon, u.dx, u.dy, 1);
1339 mdat = mon->data; /* in case of a polymorph trap */
1340 if (DEADMONSTER(mon))
1341 already_killed = TRUE;
1347 if (!already_killed)
1349 /* adjustments might have made tmp become less than what
1350 a level draining artifact has already done to max HP */
1351 if (mon->mhp > mon->mhpmax)
1352 mon->mhp = mon->mhpmax;
1353 if (DEADMONSTER(mon))
1355 if (mon->mtame && tmp > 0) {
1356 /* do this even if the pet is being killed (affects revival) */
1357 abuse_dog(mon); /* reduces tameness */
1358 /* flee if still alive and still tame; if already suffering from
1359 untimed fleeing, no effect, otherwise increases timed fleeing */
1360 if (mon->mtame && !destroyed)
1361 monflee(mon, 10 * rnd(tmp), FALSE, FALSE);
1363 if ((mdat == &mons[PM_BLACK_PUDDING] || mdat == &mons[PM_BROWN_PUDDING])
1364 /* pudding is alive and healthy enough to split */
1365 && mon->mhp > 1 && !mon->mcan
1366 /* iron weapon using melee or polearm hit [3.6.1: metal weapon too;
1367 also allow either or both weapons to cause split when twoweap] */
1368 && obj && (obj == uwep || (u.twoweap && obj == uswapwep))
1369 && ((objects[obj->otyp].oc_material == IRON
1370 /* allow scalpel and tsurugi to split puddings */
1371 || objects[obj->otyp].oc_material == METAL)
1372 /* but not bashing with darts, arrows or ya */
1373 && !(is_ammo(obj) || is_missile(obj)))
1375 struct monst *mclone;
1376 if ((mclone = clone_mon(mon, 0, 0)) != 0) {
1377 char withwhat[BUFSZ];
1381 if (u.twoweap && flags.verbose)
1382 Sprintf(withwhat, " with %s", yname(obj));
1383 pline("%s divides as you hit it%s!", Monnam(mon), withwhat);
1385 if (u.twoweap && flags.verbose)
1386 Sprintf(withwhat, "%s
\82Å
\82Ì", yname(obj));
1387 pline("
\82 \82È
\82½
\82Ì%s
\8dU
\8c\82\82Å%s
\82Í
\95ª
\97ô
\82µ
\82½
\81I", withwhat, Monnam(mon));
1394 if (!hittxt /*( thrown => obj exists )*/
1396 || (thrown && m_shot.n > 1 && m_shot.o == obj->otyp))) {
1398 hit(mshot_xname(obj), mon, exclam(tmp));
1399 else if (!flags.verbose)
1403 pline("
\8dU
\8c\82\82Í
\96½
\92\86\82µ
\82½
\81D");
1405 #if 0 /*JP*//*
\89£
\82è
\95û
\82ð
\95ª
\82¯
\82é
\82Ü
\82Å
\82Í
\82â
\82ç
\82È
\82¢*/
1407 (obj && (is_shield(obj) || obj->otyp == HEAVY_IRON_BALL))
1408 ? "bash" : Role_if(PM_BARBARIAN) ? "smite" : "hit",
1409 mon_nam(mon), canseemon(mon) ? exclam(tmp) : ".");
1411 Your("%s
\82Ö
\82Ì
\8dU
\8c\82\82Í
\96½
\92\86\82µ
\82½%s",
1412 mon_nam(mon), canseemon(mon) ? exclam(tmp) : "
\81D");
1418 char *whom = mon_nam(mon);
1419 char silverobjbuf[BUFSZ];
1421 if (canspotmon(mon)) {
1422 if (barehand_silver_rings == 1)
1424 fmt = "Your silver ring sears %s!";
1426 fmt = "%s
\82Í
\8bâ
\82Ì
\8ew
\97Ö
\82Å
\8fÄ
\82©
\82ê
\82½
\81I";
1427 else if (barehand_silver_rings == 2)
1429 fmt = "Your silver rings sear %s!";
1431 fmt = "%s
\82Í
\8bâ
\82Ì
\8ew
\97Ö
\82Å
\8fÄ
\82©
\82ê
\82½
\81I";
1432 else if (silverobj && saved_oname[0]) {
1433 /* guard constructed format string against '%' in
1434 saved_oname[] from xname(via cxname()) */
1436 Sprintf(silverobjbuf, "Your %s%s %s",
1437 strstri(saved_oname, "silver") ? "" : "silver ",
1438 saved_oname, vtense(saved_oname, "sear"));
1439 (void) strNsubst(silverobjbuf, "%", "%%", 0);
1440 Strcat(silverobjbuf, " %s!");
1442 Sprintf(silverobjbuf, "%%s
\82Í%s%s
\82Å
\8fÄ
\82©
\82ê
\82½
\81I",
1443 strstri(saved_oname, "
\8bâ") ?
1446 (void) strNsubst(silverobjbuf, "%%", "%", 0);
1451 fmt = "The silver sears %s!";
1453 fmt = "%s
\82Í
\8bâ
\82Å
\8fÄ
\82©
\82ê
\82½
\81I";
1455 *whom = highc(*whom); /* "it" -> "It" */
1457 fmt = "%s is seared!";
1459 fmt = "%s
\82Í
\8fÄ
\82©
\82ê
\82½
\81I";
1461 /* note: s_suffix returns a modifiable buffer */
1462 if (!noncorporeal(mdat) && !amorphous(mdat))
1464 whom = strcat(s_suffix(whom), " flesh");
1466 whom = strcat(s_suffix(whom), "
\93÷");
1471 char *whom = mon_nam(mon);
1472 char emitlightobjbuf[BUFSZ];
1474 if (canspotmon(mon)) {
1475 if (saved_oname[0]) {
1477 Sprintf(emitlightobjbuf,
1478 "%s radiance penetrates deep into",
1479 s_suffix(saved_oname));
1480 Strcat(emitlightobjbuf, " %s!");
1482 Sprintf(emitlightobjbuf,
1483 "%s
\8cõ
\82ª%%s
\82É
\90[
\82
\8aÑ
\92Ê
\82µ
\82½
\81I",
1484 s_suffix(saved_oname));
1486 fmt = emitlightobjbuf;
1489 fmt = "The light sears %s!";
1491 fmt = "
\8cõ
\82Í%s
\82ð
\8fÄ
\82¢
\82½
\81I";
1494 *whom = highc(*whom); /* "it" -> "It" */
1497 fmt = "%s is seared!";
1499 fmt = "%s
\82Í
\8fÄ
\82©
\82ê
\82½
\81I";
1501 /* note: s_suffix returns a modifiable buffer */
1502 if (!noncorporeal(mdat) && !amorphous(mdat))
1504 whom = strcat(s_suffix(whom), " flesh");
1506 whom = strcat(s_suffix(whom), "
\93÷");
1509 /* if a "no longer poisoned" message is coming, it will be last;
1510 obj->opoisoned was cleared above and any message referring to
1511 "poisoned <obj>" has now been given; we want just "<obj>" for
1512 last message, so reformat while obj is still accessible */
1514 Strcpy(saved_oname, cxname(obj));
1516 /* [note: thrown obj might go away during killed()/xkilled() call
1517 (via 'thrownobj'; if swallowed, it gets added to engulfer's
1518 minvent and might merge with a stack that's already there)] */
1522 pline_The("poison doesn't seem to affect %s.", mon_nam(mon));
1524 pline("
\93Å
\82Í%s
\82É
\8cø
\82©
\82È
\82©
\82Á
\82½
\82æ
\82¤
\82¾
\81D", mon_nam(mon));
1527 pline_The("poison was deadly...");
1529 pline("
\93Å
\82Í
\92v
\8e\80\97Ê
\82¾
\82Á
\82½
\81D
\81D
\81D");
1530 if (!already_killed)
1531 xkilled(mon, XKILL_NOMSG);
1532 destroyed = TRUE; /* return FALSE; */
1533 } else if (destroyed) {
1534 if (!already_killed)
1535 killed(mon); /* takes care of most messages */
1536 } else if (u.umconf && hand_to_hand) {
1538 if (!mon->mconf && !resist(mon, SPBOOK_CLASS, 0, NOTELL)) {
1540 if (!mon->mstun && mon->mcanmove && !mon->msleeping
1543 pline("%s appears confused.", Monnam(mon));
1545 pline("%s
\82Í
\8d¬
\97\90\82µ
\82Ä
\82¢
\82é
\82æ
\82¤
\82¾
\81D", Monnam(mon));
1550 Your("%s %s no longer poisoned.", saved_oname,
1551 vtense(saved_oname, "are"));
1553 Your("%s
\82Í
\82à
\82¤
\93Å
\82ª
\93h
\82ç
\82ê
\82Ä
\82¢
\82È
\82¢
\81D", xname(obj));
1556 return destroyed ? FALSE : TRUE;
1566 * The things in this list either
1569 * 2) are dealt with properly by other routines
1570 * when it comes to shades.
1572 if (obj->otyp == BOULDER
1573 || obj->otyp == HEAVY_IRON_BALL
1574 || obj->otyp == IRON_CHAIN /* dmgval handles those first three */
1575 || obj->otyp == MIRROR /* silver in the reflective surface */
1576 || obj->otyp == CLOVE_OF_GARLIC /* causes shades to flee */
1577 || objects[obj->otyp].oc_material == SILVER)
1582 /* used for hero vs monster and monster vs monster; also handles
1583 monster vs hero but that won't happen because hero can't be a shade */
1585 shade_miss(magr, mdef, obj, thrown, verbose)
1586 struct monst *magr, *mdef;
1588 boolean thrown, verbose;
1590 const char *what, *whose, *target;
1591 boolean youagr = (magr == &youmonst), youdef = (mdef == &youmonst);
1593 /* we're using dmgval() for zero/not-zero, not for actual damage amount */
1594 if (mdef->data != &mons[PM_SHADE] || (obj && dmgval(obj, mdef)))
1598 && ((youdef || cansee(mdef->mx, mdef->my) || sensemon(mdef))
1599 || (magr == &youmonst && distu(mdef->mx, mdef->my) <= 2))) {
1600 static const char harmlessly_thru[] = " harmlessly through ";
1602 what = (!obj || shade_aware(obj)) ? "attack" : cxname(obj);
1603 target = youdef ? "you" : mon_nam(mdef);
1606 whose = youagr ? "Your" : s_suffix(Monnam(magr));
1608 whose = youagr ? "
\82 \82È
\82½
\82Ì" : s_suffix(Monnam(magr));
1610 pline("%s %s %s%s%s.", whose, what,
1611 vtense(what, "pass"), harmlessly_thru, target);
1613 pline("%s%s
\82Í%s
\82ð
\92Ê
\82è
\82Ê
\82¯
\82½
\81D", whose, what,
1617 pline("%s %s%s%s.", The(what), /* note: not pline_The() */
1618 vtense(what, "pass"), harmlessly_thru, target);
1620 if (!youdef && !canspotmon(mdef))
1621 map_invisible(mdef->mx, mdef->my);
1624 mdef->msleeping = 0;
1628 /* check whether slippery clothing protects from hug or wrap attack */
1629 /* [currently assumes that you are the attacker] */
1631 m_slips_free(mdef, mattk)
1633 struct attack *mattk;
1637 if (mattk->adtyp == AD_DRIN) {
1638 /* intelligence drain attacks the head */
1639 obj = which_armor(mdef, W_ARMH);
1641 /* grabbing attacks the body */
1642 obj = which_armor(mdef, W_ARMC); /* cloak */
1644 obj = which_armor(mdef, W_ARM); /* suit */
1646 obj = which_armor(mdef, W_ARMU); /* shirt */
1649 /* if monster's cloak/armor is greased, your grab slips off; this
1650 protection might fail (33% chance) when the armor is cursed */
1651 if (obj && (obj->greased || obj->otyp == OILSKIN_CLOAK)
1652 && (!obj->cursed || rn2(3))) {
1655 mattk->adtyp == AD_WRAP ? "slip off of"
1656 : "grab, but cannot hold onto",
1657 s_suffix(mon_nam(mdef)), obj->greased ? "greased" : "slippery",
1658 /* avoid "slippery slippery cloak"
1659 for undiscovered oilskin cloak */
1660 (obj->greased || objects[obj->otyp].oc_name_known)
1662 : cloak_simple_name(obj));
1664 You("%s
\82Ì%s%s%s
\81I",
1665 mon_nam(mdef), obj->greased ? "
\96û
\82Ì
\93h
\82ç
\82ê
\82½" : "
\8a\8a\82è
\82â
\82·
\82¢",
1666 (obj->greased || objects[obj->otyp].oc_name_known)
1668 : cloak_simple_name(obj),
1669 mattk->adtyp == AD_WRAP ? "
\82Å
\8a\8a\82Á
\82½"
1670 : "
\82ð
\82Â
\82©
\82Ü
\82æ
\82¤
\82Æ
\82µ
\82½
\82ª
\81C
\82Å
\82«
\82È
\82©
\82Á
\82½");
1673 if (obj->greased && !rn2(2)) {
1675 pline_The("grease wears off.");
1677 pline("
\96û
\82Í
\97\8e\82¿
\82Ä
\82µ
\82Ü
\82Á
\82½
\81D");
1685 /* used when hitting a monster with a lance while mounted;
1686 1: joust hit; 0: ordinary hit; -1: joust but break lance */
1689 struct monst *mon; /* target */
1690 struct obj *obj; /* weapon */
1692 int skill_rating, joust_dieroll;
1694 if (Fumbling || Stunned)
1696 /* sanity check; lance must be wielded in order to joust */
1697 if (obj != uwep && (obj != uswapwep || !u.twoweap))
1700 /* if using two weapons, use worse of lance and two-weapon skills */
1701 skill_rating = P_SKILL(weapon_type(obj)); /* lance skill */
1702 if (u.twoweap && P_SKILL(P_TWO_WEAPON_COMBAT) < skill_rating)
1703 skill_rating = P_SKILL(P_TWO_WEAPON_COMBAT);
1704 if (skill_rating == P_ISRESTRICTED)
1705 skill_rating = P_UNSKILLED; /* 0=>1 */
1707 /* odds to joust are expert:80%, skilled:60%, basic:40%, unskilled:20% */
1708 if ((joust_dieroll = rn2(5)) < skill_rating) {
1709 if (joust_dieroll == 0 && rnl(50) == (50 - 1) && !unsolid(mon->data)
1710 && !obj_resists(obj, 0, 100))
1711 return -1; /* hit that breaks lance */
1712 return 1; /* successful joust */
1714 return 0; /* no joust bonus; revert to ordinary attack */
1718 * Send in a demon pet for the hero. Exercise wisdom.
1720 * This function used to be inline to damageum(), but the Metrowerks compiler
1721 * (DR4 and DR4.5) screws up with an internal error 5 "Expression Too
1723 * Pulling it out makes it work.
1729 struct permonst *pm;
1733 pline("Some hell-p has arrived!");
1735 pline("
\92n
\8d\96\82Ì
\92\87\8aÔ
\82ª
\8c»
\82í
\82ê
\82½
\81I");
1736 i = !rn2(6) ? ndemon(u.ualign.type) : NON_PM;
1737 pm = i != NON_PM ? &mons[i] : youmonst.data;
1738 if ((dtmp = makemon(pm, u.ux, u.uy, NO_MM_FLAGS)) != 0)
1739 (void) tamedog(dtmp, (struct obj *) 0);
1740 exercise(A_WIS, TRUE);
1744 theft_petrifies(otmp)
1747 if (uarmg || otmp->otyp != CORPSE
1748 || !touch_petrifies(&mons[otmp->corpsenm]) || Stone_resistance)
1751 #if 0 /* no poly_when_stoned() critter has theft capability */
1752 if (poly_when_stoned(youmonst.data) && polymon(PM_STONE_GOLEM)) {
1753 display_nhwindow(WIN_MESSAGE, FALSE); /* --More-- */
1758 /* stealing this corpse is fatal... */
1760 instapetrify(corpse_xname(otmp, "stolen", CXN_ARTICLE));
1762 instapetrify(corpse_xname(otmp, "
\93\90\82Ü
\82ê
\82½", CXN_ARTICLE));
1763 /* apparently wasn't fatal after all... */
1768 * Player uses theft attack against monster.
1770 * If the target is wearing body armor, take all of its possessions;
1771 * otherwise, take one object. [Is this really the behavior we want?]
1774 steal_it(mdef, mattk)
1776 struct attack *mattk;
1778 struct obj *otmp, *gold = 0, *stealoid, **minvent_ptr;
1781 otmp = mdef->minvent;
1782 if (!otmp || (otmp->oclass == COIN_CLASS && !otmp->nobj))
1783 return; /* nothing to take */
1785 /* look for worn body armor */
1786 stealoid = (struct obj *) 0;
1787 if (could_seduce(&youmonst, mdef, mattk)) {
1788 /* find armor, and move it to end of inventory in the process */
1789 minvent_ptr = &mdef->minvent;
1790 while ((otmp = *minvent_ptr) != 0)
1791 if (otmp->owornmask & W_ARM) {
1793 panic("steal_it: multiple worn suits");
1794 *minvent_ptr = otmp->nobj; /* take armor out of minvent */
1796 stealoid->nobj = (struct obj *) 0;
1798 minvent_ptr = &otmp->nobj;
1800 *minvent_ptr = stealoid; /* put armor back into minvent */
1802 gold = findgold(mdef->minvent);
1804 if (stealoid) { /* we will be taking everything */
1805 if (gender(mdef) == (int) u.mfemale && youmonst.data->mlet == S_NYMPH)
1807 You("charm %s. She gladly hands over %sher possessions.",
1808 mon_nam(mdef), !gold ? "" : "most of ");
1810 You("%s
\82ð
\82¤
\82Á
\82Æ
\82è
\82³
\82¹
\82½
\81D
\94Þ
\8f\97\82Í
\82æ
\82ë
\82±
\82ñ
\82Å
\8e\9d\82¿
\95¨%s
\82ð
\82³
\82µ
\82¾
\82µ
\82½
\81D",
1811 mon_nam(mdef), !gold ? "" : "
\82Ì
\82Ù
\82Æ
\82ñ
\82Ç");
1815 You("seduce %s and %s starts to take off %s clothes.",
1816 mon_nam(mdef), mhe(mdef), mhis(mdef));
1818 You("%s
\82ð
\97U
\98f
\82µ
\82½
\81D%s
\82Í
\95\9e\82ð
\92E
\82¬
\82Í
\82¶
\82ß
\82½
\81D",
1819 mon_nam(mdef), mhe(mdef));
1823 /* prevent gold from being stolen so that steal-item isn't a superset
1824 of steal-gold; shuffling it out of minvent before selecting next
1825 item, and then back in case hero or monster dies (hero touching
1826 stolen c'trice corpse or monster wielding one and having gloves
1827 stolen) is less bookkeeping than skipping it within the loop or
1828 taking it out once and then trying to figure out how to put it back */
1830 obj_extract_self(gold);
1832 while ((otmp = mdef->minvent) != 0) {
1833 if (gold) /* put 'mdef's gold back after remembering mdef->minvent */
1834 mpickobj(mdef, gold), gold = 0;
1836 break; /* no longer have ability to steal */
1837 /* take the object away from the monster */
1838 obj_extract_self(otmp);
1839 if ((unwornmask = otmp->owornmask) != 0L) {
1840 mdef->misc_worn_check &= ~unwornmask;
1841 if (otmp->owornmask & W_WEP)
1842 setmnotwielded(mdef, otmp);
1843 otmp->owornmask = 0L;
1844 update_mon_intrinsics(mdef, otmp, FALSE, FALSE);
1845 /* give monster a chance to wear other equipment on its next
1846 move instead of waiting until it picks something up */
1847 mdef->misc_worn_check |= I_SPECIAL;
1849 if (otmp == stealoid) /* special message for final item */
1851 pline("%s finishes taking off %s suit.", Monnam(mdef),
1854 pline("%s
\82Í
\92E
\82¬
\8fI
\82¦
\82½
\81D", Monnam(mdef));
1857 /* give the object to the character */
1859 otmp = hold_another_object(otmp, "You snatched but dropped %s.",
1860 doname(otmp), "You steal: ");
1862 otmp = hold_another_object(otmp, "
\82 \82È
\82½
\82Í%s
\82ð
\93\90\82ñ
\82¾
\82ª
\97\8e\82Æ
\82µ
\82½
\81D",
1863 doname(otmp), "
\82ð
\93\90\82ñ
\82¾
\81D");
1865 /* might have dropped otmp, and it might have broken or left level */
1866 if (!otmp || otmp->where != OBJ_INVENT)
1868 if (theft_petrifies(otmp))
1869 break; /* stop thieving even though hero survived */
1870 /* more take-away handling, after theft message */
1871 if (unwornmask & W_WEP) { /* stole wielded weapon */
1872 possibly_unwield(mdef, FALSE);
1873 } else if (unwornmask & W_ARMG) { /* stole worn gloves */
1874 mselftouch(mdef, (const char *) 0, TRUE);
1875 if (DEADMONSTER(mdef)) /* it's now a statue */
1876 break; /* can't continue stealing */
1880 break; /* only taking one item */
1882 /* take gold out of minvent before making next selection; if it
1883 is the only thing left, the loop will terminate and it will be
1885 if ((gold = findgold(mdef->minvent)) != 0)
1886 obj_extract_self(gold);
1889 /* put gold back; won't happen if either hero or 'mdef' dies because
1890 gold will be back in monster's inventory at either of those times
1891 (so will be present in mdef's minvent for bones, or in its statue
1892 now if it has just been turned into one) */
1894 mpickobj(mdef, gold);
1898 damageum(mdef, mattk, specialdmg)
1899 register struct monst *mdef;
1900 register struct attack *mattk;
1901 int specialdmg; /* blessed and/or silver bonus against various things */
1903 register struct permonst *pd = mdef->data;
1904 int armpro, tmp = d((int) mattk->damn, (int) mattk->damd);
1906 struct obj *mongold;
1908 armpro = magic_negation(mdef);
1909 /* since hero can't be cancelled, only defender's armor applies */
1910 negated = !(rn2(10) >= 3 * armpro);
1912 if (is_demon(youmonst.data) && !rn2(13) && !uwep
1913 && u.umonnum != PM_SUCCUBUS && u.umonnum != PM_INCUBUS
1914 && u.umonnum != PM_BALROG) {
1918 switch (mattk->adtyp) {
1922 pline("%s %s for a moment.", Monnam(mdef),
1923 makeplural(stagger(pd, "stagger")));
1925 pline("%s
\82Í
\88ê
\8fu%s
\81D", Monnam(mdef),
1926 jpast(stagger(pd, "
\82æ
\82ë
\82ß
\82")));
1938 case AD_WERE: /* no special effect on monsters */
1939 case AD_HEAL: /* likewise */
1942 if (pd == &mons[PM_SHADE]) {
1945 impossible("bad shade attack function flow?");
1949 if (mattk->aatyp == AT_WEAP) {
1950 /* hmonas() uses known_hitum() to deal physical damage,
1951 then also damageum() for non-AD_PHYS; don't inflict
1952 extra physical damage for unusual damage types */
1954 } else if (mattk->aatyp == AT_KICK
1955 || mattk->aatyp == AT_CLAW
1956 || mattk->aatyp == AT_TUCH
1957 || mattk->aatyp == AT_HUGS) {
1958 if (thick_skinned(pd))
1959 tmp = (mattk->aatyp == AT_KICK) ? 0 : (tmp + 1) / 2;
1960 /* add ring(s) of increase damage */
1961 if (u.udaminc > 0) {
1962 /* applies even if damage was 0 */
1964 } else if (tmp > 0) {
1965 /* ring(s) might be negative; avoid converting
1966 0 to non-0 or positive to non-positive */
1980 pline("%s is %s!", Monnam(mdef), on_fire(pd, mattk));
1982 pline("%s
\82Í%s
\81I", Monnam(mdef), on_fire(mdef->data, mattk));
1983 if (completelyburns(pd)) { /* paper golem or straw golem */
1986 pline("%s burns completely!", Monnam(mdef));
1988 pline("%s
\82Í
\8a®
\91S
\82É
\94R
\82¦
\90s
\82«
\82½
\81I", Monnam(mdef));
1991 You("smell burning%s.",
1992 (pd == &mons[PM_PAPER_GOLEM]) ? " paper"
1993 : (pd == &mons[PM_STRAW_GOLEM]) ? " straw" : "");
1995 You("%s
\82ª
\94R
\82¦
\82é
\82É
\82¨
\82¢
\82ª
\82µ
\82½
\81D",
1996 (pd == &mons[PM_PAPER_GOLEM]) ? "
\8e\86"
1997 : (pd == &mons[PM_STRAW_GOLEM]) ? "
\82í
\82ç" : "
\89½
\82©");
1999 xkilled(mdef, XKILL_NOMSG | XKILL_NOCORPSE);
2002 /* Don't return yet; keep hp<1 and tmp=0 for pet msg */
2004 tmp += destroy_mitem(mdef, SCROLL_CLASS, AD_FIRE);
2005 tmp += destroy_mitem(mdef, SPBOOK_CLASS, AD_FIRE);
2006 if (resists_fire(mdef)) {
2009 pline_The("fire doesn't heat %s!", mon_nam(mdef));
2011 pline("
\89\8a\82Í%s
\82É
\89e
\8b¿
\82ª
\82È
\82¢
\81I", mon_nam(mdef));
2012 golemeffects(mdef, AD_FIRE, tmp);
2013 shieldeff(mdef->mx, mdef->my);
2016 /* only potions damage resistant players in destroy_item */
2017 tmp += destroy_mitem(mdef, POTION_CLASS, AD_FIRE);
2026 pline("%s is covered in frost!", Monnam(mdef));
2028 pline("%s
\82Í
\95X
\82Å
\95¢
\82í
\82ê
\82½
\81I", Monnam(mdef));
2029 if (resists_cold(mdef)) {
2030 shieldeff(mdef->mx, mdef->my);
2033 pline_The("frost doesn't chill %s!", mon_nam(mdef));
2035 pline("
\95X
\82Í%s
\82ð
\93\80\82ç
\82·
\82±
\82Æ
\82ª
\82Å
\82«
\82È
\82¢
\81I", mon_nam(mdef));
2036 golemeffects(mdef, AD_COLD, tmp);
2039 tmp += destroy_mitem(mdef, POTION_CLASS, AD_COLD);
2048 pline("%s is zapped!", Monnam(mdef));
2050 pline("%s
\82Í
\93d
\8c\82\82ð
\82
\82ç
\82Á
\82½
\81I", Monnam(mdef));
2051 tmp += destroy_mitem(mdef, WAND_CLASS, AD_ELEC);
2052 if (resists_elec(mdef)) {
2055 pline_The("zap doesn't shock %s!", mon_nam(mdef));
2057 pline("
\93d
\8c\82\82Í%s
\82É
\89e
\8b¿
\82ð
\97^
\82¦
\82È
\82¢
\81I", mon_nam(mdef));
2058 golemeffects(mdef, AD_ELEC, tmp);
2059 shieldeff(mdef->mx, mdef->my);
2062 /* only rings damage resistant players in destroy_item */
2063 tmp += destroy_mitem(mdef, RING_CLASS, AD_ELEC);
2066 if (resists_acid(mdef))
2070 if (!munstone(mdef, TRUE))
2071 minstapetrify(mdef, TRUE);
2077 steal_it(mdef, mattk);
2081 /* This you as a leprechaun, so steal
2082 real gold only, no lesser coins */
2083 mongold = findgold(mdef->minvent);
2085 obj_extract_self(mongold);
2086 if (merge_choice(invent, mongold) || inv_cnt(FALSE) < 52) {
2089 Your("purse feels heavier.");
2091 You("
\8dà
\95z
\82ª
\8fd
\82
\82È
\82Á
\82½
\82æ
\82¤
\82È
\8bC
\82ª
\82µ
\82½
\81D");
2094 You("grab %s's gold, but find no room in your knapsack.",
2096 You("%s
\82Ì
\82¨
\8bà
\82ð
\82Â
\82©
\82ñ
\82¾
\82ª
\81C
\8e\9d\82¿
\95¨
\91Ü
\82É
\93ü
\82ç
\82È
\82©
\82Á
\82½
\81D",
2101 exercise(A_DEX, TRUE);
2109 boolean u_saw_mon = (canseemon(mdef)
2110 || (u.uswallow && u.ustuck == mdef));
2112 /* record the name before losing sight of monster */
2113 Strcpy(nambuf, Monnam(mdef));
2114 if (u_teleport_mon(mdef, FALSE) && u_saw_mon
2115 && !(canseemon(mdef) || (u.uswallow && u.ustuck == mdef)))
2117 pline("%s suddenly disappears!", nambuf);
2119 pline("%s
\82Í
\93Ë
\91R
\8fÁ
\82¦
\82½
\81I", nambuf);
2120 if (tmp >= mdef->mhp) { /* see hitmu(mhitu.c) */
2123 tmp = mdef->mhp - 1;
2128 if (can_blnd(&youmonst, mdef, mattk->aatyp, (struct obj *) 0)) {
2129 if (!Blind && mdef->mcansee)
2131 pline("%s is blinded.", Monnam(mdef));
2133 pline("%s
\82Í
\96Ú
\82ª
\8c©
\82¦
\82È
\82
\82È
\82Á
\82½
\81D", Monnam(mdef));
2135 tmp += mdef->mblinded;
2138 mdef->mblinded = tmp;
2143 if (night() && !rn2(10) && !mdef->mcan) {
2144 if (pd == &mons[PM_CLAY_GOLEM]) {
2147 pline("Some writing vanishes from %s head!",
2148 s_suffix(mon_nam(mdef)));
2150 pline("%s
\82Ì
\93ª
\82É
\8f\91\82¢
\82Ä
\82 \82é
\95¶
\8e\9a\82Ì
\82¢
\82
\82Â
\82©
\82ª
\8fÁ
\82¦
\82½
\81I",
2153 xkilled(mdef, XKILL_NOMSG);
2154 /* Don't return yet; keep hp<1 and tmp=0 for pet msg */
2160 You("
\82
\82·
\82
\82·
\8fÎ
\82Á
\82½
\81D");
2166 if (!negated && !rn2(3) && !resists_drli(mdef)) {
2170 pline("%s suddenly seems weaker!", Monnam(mdef));
2172 pline("%s
\82Í
\93Ë
\91R
\8eã
\82
\82È
\82Á
\82½
\82æ
\82¤
\82É
\8c©
\82¦
\82½
\81I", Monnam(mdef));
2173 mdef->mhpmax -= xtmp;
2175 /* !m_lev: level 0 monster is killed regardless of hit points
2176 rather than drop to level -1 */
2177 if (DEADMONSTER(mdef) || !mdef->m_lev) {
2179 pline("%s dies!", Monnam(mdef));
2181 pline("%s
\82Í
\8e\80\82ñ
\82¾
\81I", Monnam(mdef));
2182 xkilled(mdef, XKILL_NOMSG);
2189 if (pd == &mons[PM_IRON_GOLEM]) {
2191 pline("%s falls to pieces!", Monnam(mdef));
2193 pline("%s
\82Í
\83o
\83\89\83o
\83\89\82É
\82È
\82Á
\82½
\81I", Monnam(mdef));
2194 xkilled(mdef, XKILL_NOMSG);
2196 erode_armor(mdef, ERODE_RUST);
2200 erode_armor(mdef, ERODE_CORRODE);
2204 if (pd == &mons[PM_WOOD_GOLEM] || pd == &mons[PM_LEATHER_GOLEM]) {
2206 pline("%s falls to pieces!", Monnam(mdef));
2208 pline("%s
\82Í
\83o
\83\89\83o
\83\89\82É
\82È
\82Á
\82½
\81I", Monnam(mdef));
2209 xkilled(mdef, XKILL_NOMSG);
2211 erode_armor(mdef, ERODE_ROT);
2215 if (!negated && !rn2(4))
2216 xdrainenergym(mdef, TRUE);
2222 if (!negated && !rn2(8)) {
2224 Your("%s was poisoned!", mpoisons_subj(&youmonst, mattk));
2226 Your("%s
\82Í
\93Å
\82³
\82ê
\82Ä
\82¢
\82é
\81I", mpoisons_subj(&youmonst, mattk));
2227 if (resists_poison(mdef)) {
2229 pline_The("poison doesn't seem to affect %s.", mon_nam(mdef));
2231 pline("
\93Å
\82Í%s
\82É
\89e
\8b¿
\82ð
\97^
\82¦
\82È
\82¢
\81D", mon_nam(mdef));
2235 Your("poison was deadly...");
2237 Your("
\97^
\82¦
\82½
\93Å
\82Í
\92v
\8e\80\97Ê
\82¾
\82Á
\82½
\81D
\81D
\81D");
2247 if (notonhead || !has_head(pd)) {
2249 pline("%s doesn't seem harmed.", Monnam(mdef));
2251 pline("%s
\82Í
\8f\9d\82Â
\82¢
\82½
\82æ
\82¤
\82É
\82Í
\8c©
\82¦
\82È
\82¢
\81D", Monnam(mdef));
2253 if (!Unchanging && pd == &mons[PM_GREEN_SLIME]) {
2256 You("suck in some slime and don't feel very well.");
2258 You("
\83X
\83\89\83C
\83\80\82ð
\8bz
\82¢
\8eæ
\82Á
\82Ä
\81C
\8bï
\8d\87\82ª
\88«
\82
\82È
\82Á
\82½
\81D");
2259 make_slimed(10L, (char *) 0);
2264 if (m_slips_free(mdef, mattk))
2267 if ((helmet = which_armor(mdef, W_ARMH)) != 0 && rn2(8)) {
2269 pline("%s %s blocks your attack to %s head.",
2270 s_suffix(Monnam(mdef)), helm_simple_name(helmet),
2273 pline("%s
\82Ì%s
\82ª
\93ª
\82Ö
\82Ì
\8dU
\8c\82\82ð
\96h
\82¢
\82¾
\81D",
2274 Monnam(mdef), helm_simple_name(helmet));
2279 (void) eat_brains(&youmonst, mdef, TRUE, &tmp);
2283 if (!negated && !sticks(pd))
2284 u.ustuck = mdef; /* it's now stuck to you */
2288 if (!u.ustuck && !rn2(10)) {
2289 if (m_slips_free(mdef, mattk)) {
2293 You("swing yourself around %s!", mon_nam(mdef));
2295 You("%s
\82É
\90g
\91Ì
\82ð
\97\8d\82Ý
\82Â
\82©
\82¹
\82½
\81I", mon_nam(mdef));
2298 } else if (u.ustuck == mdef) {
2299 /* Monsters don't wear amulets of magical breathing */
2300 if (is_pool(u.ux, u.uy) && !is_swimmer(pd)
2301 && !amphibious(pd)) {
2303 You("drown %s...", mon_nam(mdef));
2305 You("%s
\82ð
\93M
\82ê
\82³
\82¹
\82½
\81D
\81D
\81D", mon_nam(mdef));
2307 } else if (mattk->aatyp == AT_HUGS)
2309 pline("%s is being crushed.", Monnam(mdef));
2311 pline("%s
\82Í
\89\9f\82µ
\82Â
\82Ô
\82³
\82ê
\82Ä
\82¢
\82é
\81D", Monnam(mdef));
2316 You("brush against %s %s.", s_suffix(mon_nam(mdef)),
2317 mbodypart(mdef, LEG));
2319 You("%s
\82Ì%s
\82É
\90G
\82ê
\82½
\81D", mon_nam(mdef),
2320 mbodypart(mdef, LEG));
2327 if (!negated && mdef->mcanmove && !rn2(3) && tmp < mdef->mhp) {
2330 pline("%s is frozen by you!", Monnam(mdef));
2332 pline("%s
\82Í
\82 \82È
\82½
\82Ì
\82É
\82ç
\82Ý
\82Å
\93®
\82¯
\82È
\82
\82È
\82Á
\82½
\81I", Monnam(mdef));
2333 paralyze_monst(mdef, rnd(10));
2337 if (!negated && !mdef->msleeping && sleep_monst(mdef, rnd(10), -1)) {
2340 pline("%s is put to sleep by you!", Monnam(mdef));
2342 pline("%s
\82Í
\93Ë
\91R
\96°
\82è
\82É
\82¨
\82¿
\82½
\81I", Monnam(mdef));
2348 break; /* physical damage only */
2349 if (!rn2(4) && !slimeproof(pd)) {
2350 if (!munslime(mdef, TRUE) && !DEADMONSTER(mdef)) {
2351 /* this assumes newcham() won't fail; since hero has
2352 a slime attack, green slimes haven't been geno'd */
2354 You("turn %s into slime.", mon_nam(mdef));
2356 pline("%s
\82Í
\83X
\83\89\83C
\83\80\82É
\82È
\82Á
\82½
\81D", mon_nam(mdef));
2357 if (newcham(mdef, &mons[PM_GREEN_SLIME], FALSE, FALSE))
2360 /* munslime attempt could have been fatal */
2361 if (DEADMONSTER(mdef))
2362 return 2; /* skip death message */
2366 case AD_ENCH: /* KMH -- remove enchantment (disenchanter) */
2367 /* there's no msomearmor() function, so just do damage */
2368 /* if (negated) break; */
2371 if (!negated && mdef->mspeed != MSLOW) {
2372 unsigned int oldspeed = mdef->mspeed;
2374 mon_adjust_speed(mdef, -1, (struct obj *) 0);
2375 if (mdef->mspeed != oldspeed && canseemon(mdef))
2377 pline("%s slows down.", Monnam(mdef));
2379 pline("%s
\82Í
\82Ì
\82ë
\82
\82È
\82Á
\82½
\81D", Monnam(mdef));
2384 if (canseemon(mdef))
2386 pline("%s looks confused.", Monnam(mdef));
2388 pline("%s
\82Í
\8d¬
\97\90\82µ
\82½
\82æ
\82¤
\82¾
\81D", Monnam(mdef));
2397 mdef->mstrategy &= ~STRAT_WAITFORU; /* in case player is very fast */
2399 if (DEADMONSTER(mdef)) {
2400 if (mdef->mtame && !cansee(mdef->mx, mdef->my)) {
2402 You_feel("embarrassed for a moment.");
2404 You("
\82µ
\82Î
\82ç
\82
\8d¢
\98f
\82µ
\82½
\81D");
2406 xkilled(mdef, XKILL_NOMSG); /* !tmp but hp<1: already killed */
2407 } else if (!flags.verbose) {
2411 You("
\93|
\82µ
\82½
\81I");
2413 xkilled(mdef, XKILL_NOMSG);
2423 register struct monst *mdef;
2424 register struct attack *mattk;
2426 boolean resistance; /* only for cold/fire/elec */
2427 register int tmp = d((int) mattk->damn, (int) mattk->damd);
2432 You("
\94\9a\94
\82µ
\82½
\81I");
2433 switch (mattk->adtyp) {
2435 if (!resists_blnd(mdef)) {
2437 pline("%s is blinded by your flash of light!", Monnam(mdef));
2439 pline("%s
\82Í
\82Ü
\82Î
\82ä
\82¢
\8cõ
\82Å
\96Ú
\82ª
\82
\82ç
\82ñ
\82¾
\81I", Monnam(mdef));
2440 mdef->mblinded = min((int) mdef->mblinded + tmp, 127);
2445 if (haseyes(mdef->data) && mdef->mcansee) {
2447 pline("%s is affected by your flash of light!", Monnam(mdef));
2449 pline("%s
\82Í
\82Ü
\82Î
\82ä
\82¢
\8cõ
\82Å
\89e
\8b¿
\82ð
\8eó
\82¯
\82½
\81I", Monnam(mdef));
2454 resistance = resists_cold(mdef);
2457 resistance = resists_fire(mdef);
2460 resistance = resists_elec(mdef);
2464 pline("%s gets blasted!", Monnam(mdef));
2466 pline("%s
\82Í
\94\9a\94
\82ð
\97\81\82Ñ
\82½
\81I", Monnam(mdef));
2468 if (DEADMONSTER(mdef)) {
2473 shieldeff(mdef->mx, mdef->my);
2474 if (is_golem(mdef->data))
2475 golemeffects(mdef, (int) mattk->adtyp, tmp);
2478 pline_The("blast doesn't seem to affect %s.", mon_nam(mdef));
2480 pline("
\94\9a\94
\82Í%s
\82É
\89e
\8b¿
\82ð
\97^
\82¦
\82È
\82©
\82Á
\82½
\82æ
\82¤
\82¾
\81D", mon_nam(mdef));
2494 map_location(u.ux, u.uy, TRUE);
2495 tmp_at(DISP_ALWAYS, mon_to_glyph(&youmonst, rn2_on_display_rng));
2496 tmp_at(mdef->mx, mdef->my);
2499 You("engulf %s!", mon_nam(mdef));
2501 You("%s
\82ð
\88ù
\82Ý
\8d\9e\82ñ
\82¾
\81I", mon_nam(mdef));
2510 tmp_at(DISP_END, 0);
2517 register struct monst *mdef;
2518 register struct attack *mattk;
2520 #ifdef LINT /* static char msgbuf[BUFSZ]; */
2523 static char msgbuf[BUFSZ]; /* for nomovemsg */
2526 register int dam = d((int) mattk->damn, (int) mattk->damd);
2529 struct permonst *pd = mdef->data;
2531 /* Not totally the same as for real monsters. Specifically, these
2532 * don't take multiple moves. (It's just too hard, for too little
2533 * result, to program monsters which attack from inside you, which
2534 * would be necessary if done accurately.) Instead, we arbitrarily
2535 * kill the monster immediately for AD_DGST and we regurgitate them
2536 * after exactly 1 round of attack otherwise. -KAA
2539 if (!engulf_target(&youmonst, mdef))
2542 if (u.uhunger < 1500 && !u.uswallow) {
2543 for (otmp = mdef->minvent; otmp; otmp = otmp->nobj)
2544 (void) snuff_lit(otmp);
2546 /* force vampire in bat, cloud, or wolf form to revert back to
2547 vampire form now instead of dealing with that when it dies */
2548 if (is_vampshifter(mdef)
2549 && newcham(mdef, &mons[mdef->cham], FALSE, FALSE)) {
2551 You("engulf it, then expel it.");
2553 You("
\88ù
\82Ý
\8d\9e\82ñ
\82Å
\81C
\93f
\82«
\8fo
\82µ
\82½
\81D");
2554 if (canspotmon(mdef))
2556 pline("It turns into %s.", a_monnam(mdef));
2558 pline("
\82»
\82ê
\82Í%s
\82É
\82È
\82Á
\82½
\81D", a_monnam(mdef));
2560 map_invisible(mdef->mx, mdef->my);
2564 /* engulfing a cockatrice or digesting a Rider or Medusa */
2565 fatal_gulp = (touch_petrifies(pd) && !Stone_resistance)
2566 || (mattk->adtyp == AD_DGST
2567 && (is_rider(pd) || (pd == &mons[PM_MEDUSA]
2568 && !Stone_resistance)));
2570 if ((mattk->adtyp == AD_DGST && !Slow_digestion) || fatal_gulp)
2571 eating_conducts(pd);
2573 if (fatal_gulp && !is_rider(pd)) { /* petrification */
2575 const char *mname = pd->mname;
2577 if (!type_is_pname(pd))
2580 You("englut %s.", mon_nam(mdef));
2582 You("%s
\82ð
\88ù
\82Ý
\8d\9e\82ñ
\82¾
\81D", mon_nam(mdef));
2584 Sprintf(kbuf, "swallowing %s whole", mname);
2586 Sprintf(kbuf, "%s
\82ð
\88ù
\82Ý
\8d\9e\82ñ
\82Å", mname);
2590 switch (mattk->adtyp) {
2592 /* eating a Rider or its corpse is fatal */
2595 pline("Unfortunately, digesting any of it is fatal.");
2597 pline("
\8ec
\94O
\82È
\82ª
\82ç
\81C
\82»
\82ê
\82ð
\90H
\82×
\82é
\82Ì
\82Í
\92v
\96½
\93I
\82È
\8aÔ
\88á
\82¢
\82¾
\81D");
2600 Sprintf(killer.name, "unwisely tried to eat %s",
2602 killer.format = NO_KILLER_PREFIX;
2604 Sprintf(killer.name, "
\8bð
\82©
\82É
\82à%s
\82ð
\90H
\82×
\82æ
\82¤
\82Æ
\82µ
\82Ä",
2606 killer.format = KILLED_BY;
2609 return 0; /* lifesaved */
2612 if (Slow_digestion) {
2617 /* Use up amulet of life saving */
2618 if ((otmp = mlifesaver(mdef)) != 0)
2619 m_useup(mdef, otmp);
2622 /* start_engulf() issues "you engulf <mdef>" above; this
2623 used to specify XKILL_NOMSG but we need "you kill <mdef>"
2624 in case we're also going to get "welcome to level N+1";
2625 "you totally digest <mdef>" will be coming soon (after
2626 several turns) but the level-gain message seems out of
2627 order if the kill message is left implicit */
2628 xkilled(mdef, XKILL_GIVEMSG | XKILL_NOCORPSE);
2629 if (!DEADMONSTER(mdef)) { /* monster lifesaved */
2631 You("hurriedly regurgitate the sizzling in your %s.",
2633 You("%s
\82Ì
\92\86\82Å
\83V
\83\85\81[
\83V
\83\85\81[
\82Æ
\82¢
\82¤
\89¹
\82ð
\97§
\82Ä
\82Ä
\82¢
\82é
\82à
\82Ì
\82ð
\91å
\8b}
\82¬
\82Å
\93f
\82«
\96ß
\82µ
\82½
\81D",
2634 body_part(STOMACH));
2636 tmp = 1 + (pd->cwt >> 8);
2637 if (corpse_chance(mdef, &youmonst, TRUE)
2638 && !(mvitals[monsndx(pd)].mvflags & G_NOCORPSE)) {
2639 /* nutrition only if there can be a corpse */
2640 u.uhunger += (pd->cnutrit + 1) / 2;
2644 Sprintf(msgbuf, "You totally digest %s.", mon_nam(mdef));
2646 Sprintf(msgbuf, "
\82 \82È
\82½
\82Í%s
\82ð
\8a®
\91S
\82É
\8fÁ
\89»
\82µ
\82½
\81D", mon_nam(mdef));
2648 /* setting afternmv = end_engulf is tempting,
2649 * but will cause problems if the player is
2650 * attacked (which uses his real location) or
2651 * if his See_invisible wears off
2654 You("digest %s.", mon_nam(mdef));
2656 You("%s
\82ð
\8fÁ
\89»
\82µ
\82Ä
\82¢
\82é
\81D", mon_nam(mdef));
2661 multi_reason = "digesting something";
2663 multi_reason = "
\8fÁ
\89»
\92\86\82É";
2667 if (pd == &mons[PM_GREEN_SLIME]) {
2669 Sprintf(msgbuf, "%s isn't sitting well with you.",
2671 Sprintf(msgbuf, "%s
\82Í
\82 \82È
\82½
\82Æ
\82¤
\82Ü
\82
\90Ü
\82è
\8d\87\82¢
\82ð
\82Â
\82¯
\82ç
\82ê
\82È
\82¢
\82æ
\82¤
\82¾
\81D",
2674 make_slimed(5L, (char *) 0);
2677 exercise(A_CON, TRUE);
2682 if (youmonst.data == &mons[PM_FOG_CLOUD]) {
2684 pline("%s is laden with your moisture.", Monnam(mdef));
2686 pline("%s
\82Í
\82 \82È
\82½
\82Ì
\8e¼
\8bC
\82É
\8bê
\82µ
\82ß
\82ç
\82ê
\82Ä
\82¢
\82é
\81D", Monnam(mdef));
2687 if (amphibious(pd) && !flaming(pd)) {
2690 pline("%s seems unharmed.", Monnam(mdef));
2692 pline("%s
\82Í
\8f\9d\82Â
\82¢
\82Ä
\82¢
\82È
\82¢
\82æ
\82¤
\82¾
\81D", Monnam(mdef));
2696 pline("%s is pummeled with your debris!", Monnam(mdef));
2698 pline("%s
\82Í
\8a¢âI
\82Å
\92É
\82ß
\82Â
\82¯
\82ç
\82ê
\82½
\81I", Monnam(mdef));
2702 pline("%s is covered with your goo!", Monnam(mdef));
2704 pline("%s
\82Í
\82Ë
\82Î
\82Â
\82
\82à
\82Ì
\82Å
\95¢
\82í
\82ê
\82½
\81I", Monnam(mdef));
2705 if (resists_acid(mdef)) {
2707 pline("It seems harmless to %s.", mon_nam(mdef));
2709 pline("
\82µ
\82©
\82µ
\81C%s
\82Í
\82È
\82ñ
\82Æ
\82à
\82È
\82¢
\81D", mon_nam(mdef));
2714 if (can_blnd(&youmonst, mdef, mattk->aatyp,
2715 (struct obj *) 0)) {
2718 pline("%s can't see in there!", Monnam(mdef));
2720 pline("%s
\82Í
\96Ú
\82ª
\8c©
\82¦
\82È
\82
\82È
\82Á
\82½
\81I", mon_nam(mdef));
2722 dam += mdef->mblinded;
2725 mdef->mblinded = dam;
2732 pline_The("air around %s crackles with electricity.",
2734 pline("%s
\82Ì
\89ñ
\82è
\82Ì
\8bó
\8bC
\82Í
\93d
\8bC
\82Å
\83s
\83\8a\83s
\83\8a\82µ
\82Ä
\82¢
\82é
\81D",
2736 if (resists_elec(mdef)) {
2738 pline("%s seems unhurt.", Monnam(mdef));
2740 pline("
\82µ
\82©
\82µ
\81C%s
\82Í
\95½
\8bC
\82È
\82æ
\82¤
\82¾
\81D", Monnam(mdef));
2743 golemeffects(mdef, (int) mattk->adtyp, dam);
2749 if (resists_cold(mdef)) {
2751 pline("%s seems mildly chilly.", Monnam(mdef));
2753 pline("%s
\82Í
\97â
\82¦
\82½
\82æ
\82¤
\82¾
\81D", Monnam(mdef));
2757 pline("%s is freezing to death!", Monnam(mdef));
2759 pline("%s
\82Í
\93\80\8e\80\82µ
\82»
\82¤
\82¾
\81I", Monnam(mdef));
2760 golemeffects(mdef, (int) mattk->adtyp, dam);
2766 if (resists_fire(mdef)) {
2768 pline("%s seems mildly hot.", Monnam(mdef));
2770 pline("%s
\82Í
\92g
\82©
\82
\82È
\82Á
\82½
\82æ
\82¤
\82¾
\81D", Monnam(mdef));
2774 pline("%s is burning to a crisp!", Monnam(mdef));
2776 pline("%s
\82Í
\94R
\82¦
\82Ä
\83J
\83\89\83J
\83\89\82É
\82È
\82Á
\82½
\81I", Monnam(mdef));
2777 golemeffects(mdef, (int) mattk->adtyp, dam);
2783 xdrainenergym(mdef, TRUE);
2789 if (DEADMONSTER(mdef)) {
2791 if (DEADMONSTER(mdef)) /* not lifesaved */
2795 You("%s %s!", is_animal(youmonst.data) ? "regurgitate" : "expel",
2798 You("%s
\82ð%s
\82µ
\82½
\81I", mon_nam(mdef),
2799 is_animal(youmonst.data) ? "
\93f
\82«
\96ß" : "
\94r
\8fo");
2801 if (Slow_digestion || is_animal(youmonst.data)) {
2803 pline("Obviously, you didn't like %s taste.",
2804 s_suffix(mon_nam(mdef)));
2806 pline("
\82Ç
\82¤
\82à%s
\82Ì
\96¡
\82Í
\8dD
\82«
\82É
\82È
\82ê
\82È
\82¢
\81D",
2816 missum(mdef, mattk, wouldhavehit)
2817 register struct monst *mdef;
2818 register struct attack *mattk;
2819 boolean wouldhavehit;
2821 if (wouldhavehit) /* monk is missing due to penalty for wearing suit */
2823 Your("armor is rather cumbersome...");
2825 Your("
\96h
\8bï
\82Í
\8f
\82µ
\8e×
\96\82\82¾
\81D
\81D
\81D");
2827 if (could_seduce(&youmonst, mdef, mattk))
2829 You("pretend to be friendly to %s.", mon_nam(mdef));
2831 You("%s
\82É
\97F
\8dD
\93I
\82È
\82Ó
\82è
\82ð
\82µ
\82½
\81D", mon_nam(mdef));
2832 else if (canspotmon(mdef) && flags.verbose)
2834 You("miss %s.", mon_nam(mdef));
2836 Your("%s
\82Ö
\82Ì
\8dU
\8c\82\82Í
\8aO
\82ê
\82½
\81D", mon_nam(mdef));
2841 Your("
\89½
\8eÒ
\82©
\82Ö
\82Ì
\8dU
\8c\82\82Í
\8aO
\82ê
\82½
\81D");
2842 if (!mdef->msleeping && mdef->mcanmove)
2846 /* attack monster as a monster; returns True if mon survives */
2849 register struct monst *mon;
2851 struct attack *mattk, alt_attk;
2852 struct obj *weapon, **originalweapon;
2853 boolean altwep = FALSE, weapon_used = FALSE, odd_claw = TRUE;
2854 int i, tmp, armorpenalty, sum[NATTK], nsum = 0, dhit = 0, attknum = 0;
2855 int dieroll, multi_claw = 0;
2857 /* with just one touch/claw/weapon attack, both rings matter;
2858 with more than one, alternate right and left when checking
2859 whether silver ring causes successful hit */
2860 for (i = 0; i < NATTK; i++) {
2862 mattk = getmattk(&youmonst, mon, i, sum, &alt_attk);
2863 if (mattk->aatyp == AT_WEAP
2864 || mattk->aatyp == AT_CLAW || mattk->aatyp == AT_TUCH)
2867 multi_claw = (multi_claw > 1); /* switch from count to yes/no */
2869 for (i = 0; i < NATTK; i++) {
2870 /* sum[i] = 0; -- now done above */
2871 mattk = getmattk(&youmonst, mon, i, sum, &alt_attk);
2873 switch (mattk->aatyp) {
2875 /* if (!uwep) goto weaponless; */
2877 odd_claw = !odd_claw; /* see case AT_CLAW,AT_TUCH below */
2878 /* if we've already hit with a two-handed weapon, we don't
2879 get to make another weapon attack (note: monsters who
2880 use weapons do not have this restriction, but they also
2881 never have the opportunity to use two weapons) */
2882 if (weapon_used && sum[i - 1] && uwep && bimanual(uwep))
2884 /* Certain monsters don't use weapons when encountered as enemies,
2885 * but players who polymorph into them have hands or claws and
2886 * thus should be able to use weapons. This shouldn't prohibit
2887 * the use of most special abilities, either.
2888 * If monster has multiple claw attacks, only one can use weapon.
2891 /* Potential problem: if the monster gets multiple weapon attacks,
2892 * we currently allow the player to get each of these as a weapon
2893 * attack. Is this really desirable?
2895 /* approximate two-weapon mode; known_hitum() -> hmon() -> &c
2896 might destroy the weapon argument, but it might also already
2897 be Null, and we want to track that for passive() */
2898 originalweapon = (altwep && uswapwep) ? &uswapwep : &uwep;
2899 if (uswapwep /* set up 'altwep' flag for next iteration */
2900 /* only consider seconary when wielding one-handed primary */
2901 && uwep && (uwep->oclass == WEAPON_CLASS || is_weptool(uwep))
2903 /* only switch if not wearing shield and not at artifact;
2904 shield limitation is iffy since still get extra swings
2905 if polyform has them, but it matches twoweap behavior;
2906 twoweap also only allows primary to be an artifact, so
2907 if alternate weapon is one, don't use it */
2908 && !uarms && !uswapwep->oartifact
2909 /* only switch to uswapwep if it's a weapon */
2910 && (uswapwep->oclass == WEAPON_CLASS || is_weptool(uswapwep))
2911 /* only switch if uswapwep is not bow, arrows, or darts */
2912 && !(is_launcher(uswapwep) || is_ammo(uswapwep)
2913 || is_missile(uswapwep)) /* dart, shuriken, boomerang */
2914 /* and not two-handed and not incapable of being wielded */
2915 && !bimanual(uswapwep)
2916 && !(objects[uswapwep->otyp].oc_material == SILVER
2918 altwep = !altwep; /* toggle for next attack */
2919 weapon = *originalweapon;
2920 if (!weapon) /* no need to go beyond no-gloves to rings; not ...*/
2921 originalweapon = &uarmg; /*... subject to erosion damage */
2923 tmp = find_roll_to_hit(mon, AT_WEAP, weapon, &attknum,
2926 dhit = (tmp > dieroll || u.uswallow);
2927 /* caller must set bhitpos */
2928 if (!known_hitum(mon, weapon, &dhit, tmp,
2929 armorpenalty, mattk, dieroll)) {
2930 /* enemy dead, before any special abilities used */
2935 /* originalweapon points to an equipment slot which might
2936 now be empty if the weapon was destroyed during the hit;
2937 passive(,weapon,...) won't call passive_obj() in that case */
2938 weapon = *originalweapon; /* might receive passive erosion */
2939 /* might be a worm that gets cut in half; if so, early return */
2940 if (m_at(u.ux + u.dx, u.uy + u.dy) != mon) {
2941 i = NATTK; /* skip additional attacks */
2942 /* proceed with uswapwep->cursed check, then exit loop */
2945 /* Do not print "You hit" message; known_hitum already did it. */
2946 if (dhit && mattk->adtyp != AD_SPEL && mattk->adtyp != AD_PHYS)
2947 sum[i] = damageum(mon, mattk, 0);
2950 if (uwep && !cantwield(youmonst.data) && !weapon_used)
2954 if (uwep && youmonst.data->mlet == S_LICH && !weapon_used)
2963 tmp = find_roll_to_hit(mon, mattk->aatyp, (struct obj *) 0,
2964 &attknum, &armorpenalty);
2966 dhit = (tmp > dieroll || u.uswallow);
2968 int compat, specialdmg;
2969 long silverhit = 0L;
2970 #if 0 /*JP*//*
\82·
\82×
\82Ä
\81u
\8dU
\8c\82\82µ
\82½
\81v
\82É
\82·
\82é */
2971 const char *verb = 0; /* verb or body part */
2975 && (compat = could_seduce(&youmonst, mon, mattk)) != 0) {
2978 (mon->mcansee && haseyes(mon->data)) ? "smile at"
2981 (compat == 2) ? "engagingly" : "seductively");
2983 You("%s
\82Ö%s%s
\81D",
2985 compat == 2 ? "
\96£
\97Í
\93I
\82É" : "
\97U
\98f
\93I
\82É",
2986 mon->mcansee && haseyes(mon->data) ? "
\94÷
\8fÎ
\82Ý
\82©
\82¯
\82½"
2987 : "
\98b
\82µ
\82©
\82¯
\82½");
2989 /* doesn't anger it; no wakeup() */
2990 sum[i] = damageum(mon, mattk, 0);
2995 specialdmg = 0; /* blessed and/or silver bonus */
2996 switch (mattk->aatyp) {
2999 /* verb=="claws" may be overridden below */
3001 verb = (mattk->aatyp == AT_TUCH) ? "touch" : "claws";
3003 /* decide if silver-hater will be hit by silver ring(s);
3004 for 'multi_claw' where attacks alternate right/left,
3005 assume 'even' claw or touch attacks use right hand
3006 or paw, 'odd' ones use left for ring interaction;
3007 even vs odd is based on actual attacks rather
3008 than on index into mon->dat->mattk[] so that {bite,
3009 claw,claw} instead of {claw,claw,bite} doesn't
3010 make poly'd hero mysteriously become left-handed */
3011 odd_claw = !odd_claw;
3012 specialdmg = special_dmgval(&youmonst, mon,
3014 | ((odd_claw || !multi_claw)
3016 | ((!odd_claw || !multi_claw)
3021 /* assumes mind flayer's tentacles-on-head rather
3022 than sea monster's tentacle-as-arm */
3031 specialdmg = special_dmgval(&youmonst, mon, W_ARMF,
3036 verb = "head butt"; /* mbodypart(mon,HEAD)=="head" */
3037 /* hypothetical; if any form with a head-butt attack
3038 could wear a helmet, it would hit shades when
3039 wearing a blessed (or silver) one */
3041 specialdmg = special_dmgval(&youmonst, mon, W_ARMH,
3060 if (mon->data == &mons[PM_SHADE] && !specialdmg) {
3062 if (!strcmp(verb, "hit")
3063 || (mattk->aatyp == AT_CLAW && humanoid(mon->data)))
3067 Your("%s %s harmlessly through %s.",
3068 verb, vtense(verb, "pass"), mon_nam(mon));
3070 Your("
\8dU
\8c\82\82Í%s
\82ð
\92Ê
\82è
\82Ê
\82¯
\82½
\81D",
3074 if (mattk->aatyp == AT_TENT) {
3076 Your("tentacles suck %s.", mon_nam(mon));
3078 Your("
\90G
\8eè
\82ª%s
\82Ì
\91Ì
\89t
\82ð
\8bz
\82¢
\82Æ
\82Á
\82½
\81D", mon_nam(mon));
3081 if (mattk->aatyp == AT_CLAW)
3082 verb = "hit"; /* not "claws" */
3085 You("%s %s.", verb, mon_nam(mon));
3087 You("%s
\82ð
\8dU
\8c\82\82µ
\82½
\81D", mon_nam(mon));
3089 if (silverhit && flags.verbose)
3090 silver_sears(&youmonst, mon, silverhit);
3092 sum[i] = damageum(mon, mattk, specialdmg);
3094 } else { /* !dhit */
3095 missum(mon, mattk, (tmp + armorpenalty > dieroll));
3101 long silverhit = 0L;
3102 boolean byhand = hug_throttles(&mons[u.umonnum]), /* rope golem */
3103 unconcerned = (byhand && !can_be_strangled(mon));
3105 if (sticks(mon->data) || u.uswallow || notonhead
3106 || (byhand && (uwep || !has_head(mon->data)))) {
3107 /* can't hold a holder due to subsequent ambiguity over
3108 who is holding whom; can't hug engulfer from inside;
3109 can't hug a worm tail (would immobilize entire worm!);
3110 byhand: can't choke something that lacks a head;
3111 not allowed to make a choking hug if wielding a weapon
3112 (but might have grabbed w/o weapon, then wielded one,
3113 and may even be attacking a different monster now) */
3114 if (byhand && uwep && u.ustuck
3115 && !(sticks(u.ustuck->data) || u.uswallow))
3117 continue; /* not 'break'; bypass passive counter-attack */
3119 /* automatic if prev two attacks succeed, or if
3120 already grabbed in a previous attack */
3123 /* choking hug/throttling grab uses hands (gloves or rings);
3124 normal hug uses outermost of cloak/suit/shirt */
3125 specialdmg = special_dmgval(&youmonst, mon,
3126 byhand ? (W_ARMG | W_RINGL | W_RINGR)
3127 : (W_ARMC | W_ARM | W_ARMU),
3130 /* strangling something which can't be strangled */
3131 if (mattk != &alt_attk) {
3135 /* change damage to 1d1; not strangling but still
3136 doing [minimal] physical damage to victim's body */
3137 mattk->damn = mattk->damd = 1;
3138 /* don't give 'unconcerned' feedback if there is extra damage
3139 or if it is nearly destroyed or if creature doesn't have
3140 the mental ability to be concerned in the first place */
3141 if (specialdmg || mindless(mon->data)
3142 || mon->mhp <= 1 + max(u.udaminc, 1))
3143 unconcerned = FALSE;
3145 if (mon->data == &mons[PM_SHADE]) {
3147 const char *verb = byhand ? "grasp" : "hug";
3150 /* hugging a shade; successful if blessed outermost armor
3151 for normal hug, or blessed gloves or silver ring(s) for
3152 choking hug; deals damage but never grabs hold */
3155 You("%s %s%s", verb, mon_nam(mon), exclam(specialdmg));
3157 You("%s
\82ð
\82Â
\82©
\82ñ
\82¾%s", mon_nam(mon), exclam(specialdmg));
3159 if (silverhit && flags.verbose)
3160 silver_sears(&youmonst, mon, silverhit);
3161 sum[i] = damageum(mon, mattk, specialdmg);
3164 Your("%s passes harmlessly through %s.",
3165 verb, mon_nam(mon));
3167 You("%s
\82ð
\82Â
\82©
\82Ü
\82¦
\82æ
\82¤
\82Æ
\82µ
\82½
\82ª
\92Ê
\82è
\82Ê
\82¯
\82½
\81D",
3173 /* hug attack against ordinary foe */
3174 if (mon == u.ustuck) {
3176 pline("%s is being %s%s.", Monnam(mon),
3177 byhand ? "throttled" : "crushed",
3178 /* extra feedback for non-breather being choked */
3179 unconcerned ? " but doesn't seem concerned" : "");
3181 pline("%s
\82Í%s%s
\81D", Monnam(mon),
3182 byhand ? "
\8eñ
\82ð
\8di
\82ß
\82ç
\82ê
\82Ä
\82¢
\82é" : "
\89\9f\82µ
\82Â
\82Ô
\82³
\82ê
\82Ä
\82¢
\82é",
3183 /* extra feedback for non-breather being choked */
3184 unconcerned ? "
\82ª
\81C
\8bC
\82É
\82µ
\82Ä
\82¢
\82È
\82¢
\82æ
\82¤
\82¾" : "");
3186 if (silverhit && flags.verbose)
3187 silver_sears(&youmonst, mon, silverhit);
3188 sum[i] = damageum(mon, mattk, specialdmg);
3189 } else if (i >= 2 && sum[i - 1] && sum[i - 2]) {
3190 /* in case we're hugging a new target while already
3191 holding something else; yields feedback
3192 "<u.ustuck> is no longer in your clutches" */
3193 if (u.ustuck && u.ustuck != mon)
3196 You("grab %s!", mon_nam(mon));
3198 You("%s
\82ð
\82Â
\82©
\82Ü
\82¦
\82½
\81I", mon_nam(mon));
3200 if (silverhit && flags.verbose)
3201 silver_sears(&youmonst, mon, silverhit);
3202 sum[i] = damageum(mon, mattk, specialdmg);
3204 break; /* AT_HUGS */
3207 case AT_EXPL: /* automatic hit if next to */
3210 sum[i] = explum(mon, mattk);
3214 tmp = find_roll_to_hit(mon, mattk->aatyp, (struct obj *) 0,
3215 &attknum, &armorpenalty);
3216 if ((dhit = (tmp > rnd(20 + i)))) {
3218 if (mon->data == &mons[PM_SHADE])
3220 Your("attempt to surround %s is harmless.", mon_nam(mon));
3222 You("%s
\82ð
\88ù
\82Ý
\82±
\82à
\82¤
\82Æ
\82µ
\82½
\82ª
\8e¸
\94s
\82µ
\82½
\81D", mon_nam(mon));
3224 sum[i] = gulpum(mon, mattk);
3225 if (sum[i] == 2 && (mon->data->mlet == S_ZOMBIE
3226 || mon->data->mlet == S_MUMMY)
3227 && rn2(5) && !Sick_resistance) {
3229 You_feel("%ssick.", (Sick) ? "very " : "");
3231 You_feel("%s
\8bC
\95ª
\82ª
\88«
\82¢
\81D", (Sick) ? "
\82Æ
\82Ä
\82à" : "");
3232 mdamageu(mon, rnd(8));
3236 missum(mon, mattk, FALSE);
3241 /* No check for uwep; if wielding nothing we want to
3242 * do the normal 1-2 points bare hand damage...
3244 if ((youmonst.data->mlet == S_KOBOLD
3245 || youmonst.data->mlet == S_ORC
3246 || youmonst.data->mlet == S_GNOME) && !weapon_used)
3253 /* Not break--avoid passive attacks from enemy */
3257 case AT_GAZE: /* all done using #monster command */
3261 default: /* Strange... */
3262 impossible("strange attack of yours (%d)", mattk->aatyp);
3265 u.mh = -1; /* dead in the current form */
3270 (void) passive(mon, weapon, 1, 0, mattk->aatyp, FALSE);
3271 nsum = 0; /* return value below used to be 'nsum > 0' */
3273 (void) passive(mon, weapon, sum[i], 1, mattk->aatyp, FALSE);
3277 /* don't use sum[i] beyond this point;
3278 'i' will be out of bounds if we get here via 'goto' */
3280 /* when using dual weapons, cursed secondary weapon doesn't weld,
3281 it gets dropped; do the same when multiple AT_WEAP attacks
3283 if (uswapwep && weapon == uswapwep && weapon->cursed) {
3285 break; /* don't proceed with additional attacks */
3287 /* stop attacking if defender has died;
3288 needed to defer this until after uswapwep->cursed check */
3289 if (DEADMONSTER(mon))
3292 break; /* No extra attacks if no longer a monster */
3294 break; /* If paralyzed while attacking, i.e. floating eye */
3296 /* return value isn't used, but make it match hitum()'s */
3297 return !DEADMONSTER(mon);
3300 /* Special (passive) attacks on you by monsters done here.
3303 passive(mon, weapon, mhit, malive, aatyp, wep_was_destroyed)
3305 struct obj *weapon; /* uwep or uswapwep or uarmg or uarmf or Null */
3309 boolean wep_was_destroyed;
3311 register struct permonst *ptr = mon->data;
3312 register int i, tmp;
3316 return (malive | mhit); /* no passive attacks */
3317 if (ptr->mattk[i].aatyp == AT_NONE)
3318 break; /* try this one */
3320 /* Note: tmp not always used */
3321 if (ptr->mattk[i].damn)
3322 tmp = d((int) ptr->mattk[i].damn, (int) ptr->mattk[i].damd);
3323 else if (ptr->mattk[i].damd)
3324 tmp = d((int) mon->m_lev + 1, (int) ptr->mattk[i].damd);
3328 /* These affect you even if they just died.
3330 switch (ptr->mattk[i].adtyp) {
3332 if (mhit && !mon->mcan && weapon) {
3333 if (aatyp == AT_KICK) {
3334 if (uarmf && !rn2(6))
3335 (void) erode_obj(uarmf, xname(uarmf), ERODE_BURN,
3336 EF_GREASE | EF_VERBOSE);
3337 } else if (aatyp == AT_WEAP || aatyp == AT_CLAW
3338 || aatyp == AT_MAGC || aatyp == AT_TUCH)
3339 passive_obj(mon, weapon, &(ptr->mattk[i]));
3343 if (mhit && rn2(2)) {
3344 if (Blind || !flags.verbose)
3346 You("are splashed!");
3348 You("
\89½
\82©
\82ð
\97\81\82Ñ
\82¹
\82ç
\82ê
\82½
\81I");
3351 You("are splashed by %s %s!", s_suffix(mon_nam(mon)),
3354 You("%s
\82Ì%s
\82ð
\97\81\82Ñ
\82¹
\82ç
\82ê
\82½
\81I", mon_nam(mon),
3358 if (!Acid_resistance)
3361 erode_armor(&youmonst, ERODE_CORRODE);
3363 if (mhit && weapon) {
3364 if (aatyp == AT_KICK) {
3365 if (uarmf && !rn2(6))
3366 (void) erode_obj(uarmf, xname(uarmf), ERODE_CORRODE,
3367 EF_GREASE | EF_VERBOSE);
3368 } else if (aatyp == AT_WEAP || aatyp == AT_CLAW
3369 || aatyp == AT_MAGC || aatyp == AT_TUCH)
3370 passive_obj(mon, weapon, &(ptr->mattk[i]));
3372 exercise(A_STR, FALSE);
3375 if (mhit) { /* successful attack */
3376 long protector = attk_protection((int) aatyp);
3378 /* hero using monsters' AT_MAGC attack is hitting hand to
3379 hand rather than casting a spell */
3380 if (aatyp == AT_MAGC)
3383 if (protector == 0L /* no protection */
3384 || (protector == W_ARMG && !uarmg
3385 && !uwep && !wep_was_destroyed)
3386 || (protector == W_ARMF && !uarmf)
3387 || (protector == W_ARMH && !uarmh)
3388 || (protector == (W_ARMC | W_ARMG) && (!uarmc || !uarmg))) {
3389 if (!Stone_resistance
3390 && !(poly_when_stoned(youmonst.data)
3391 && polymon(PM_STONE_GOLEM))) {
3392 done_in_by(mon, STONING); /* "You turn to stone..." */
3399 if (mhit && !mon->mcan && weapon) {
3400 if (aatyp == AT_KICK) {
3402 (void) erode_obj(uarmf, xname(uarmf), ERODE_RUST,
3403 EF_GREASE | EF_VERBOSE);
3404 } else if (aatyp == AT_WEAP || aatyp == AT_CLAW
3405 || aatyp == AT_MAGC || aatyp == AT_TUCH)
3406 passive_obj(mon, weapon, &(ptr->mattk[i]));
3410 if (mhit && !mon->mcan && weapon) {
3411 if (aatyp == AT_KICK) {
3413 (void) erode_obj(uarmf, xname(uarmf), ERODE_CORRODE,
3414 EF_GREASE | EF_VERBOSE);
3415 } else if (aatyp == AT_WEAP || aatyp == AT_CLAW
3416 || aatyp == AT_MAGC || aatyp == AT_TUCH)
3417 passive_obj(mon, weapon, &(ptr->mattk[i]));
3421 /* wrath of gods for attacking Oracle */
3423 shieldeff(u.ux, u.uy);
3425 pline("A hail of magic missiles narrowly misses you!");
3427 pline("
\96\82\96@
\82Ì
\96î
\82Ì
\89J
\82ª
\82©
\82·
\82ß
\82Ä
\82¢
\82Á
\82½
\81I");
3430 You("are hit by magic missiles appearing from thin air!");
3432 pline("
\93Ë
\94@
\8bó
\92\86\82É
\8c»
\82í
\82ê
\82½
\96\82\96@
\82Ì
\96î
\82ª
\96½
\92\86\82µ
\82½
\81I");
3436 case AD_ENCH: /* KMH -- remove enchantment (disenchanter) */
3438 if (aatyp == AT_KICK) {
3441 } else if (aatyp == AT_BITE || aatyp == AT_BUTT
3442 || (aatyp >= AT_STNG && aatyp < AT_WEAP)) {
3443 break; /* no object involved */
3445 passive_obj(mon, weapon, &(ptr->mattk[i]));
3452 /* These only affect you if they still live.
3454 if (malive && !mon->mcan && rn2(3)) {
3455 switch (ptr->mattk[i].adtyp) {
3457 if (ptr == &mons[PM_FLOATING_EYE]) {
3458 if (!canseemon(mon)) {
3463 if (ureflects("%s gaze is reflected by your %s.",
3464 s_suffix(Monnam(mon)))) {
3466 if (ureflects("%s
\82Ì
\82É
\82ç
\82Ý
\82Í%s
\82É
\82æ
\82Á
\82Ä
\94½
\8eË
\82³
\82ê
\82½
\81D",
3470 } else if (Hallucination && rn2(4)) {
3471 /* [it's the hero who should be getting paralyzed
3472 and isn't; this message describes the monster's
3473 reaction rather than the hero's escape] */
3475 pline("%s looks %s%s.", Monnam(mon),
3476 !rn2(2) ? "" : "rather ",
3477 !rn2(2) ? "numb" : "stupefied");
3479 pline("%s
\82Í%s
\82Î
\82©
\82É
\82È
\82Á
\82½
\82æ
\82¤
\82¾
\81D", Monnam(mon),
3480 !rn2(2) ? "" : "
\8f
\82µ");
3482 } else if (Free_action) {
3484 You("momentarily stiffen under %s gaze!",
3485 s_suffix(mon_nam(mon)));
3487 You("%s
\82Ì
\82É
\82ç
\82Ý
\82Å
\88ê
\8fu
\8dd
\92¼
\82µ
\82½
\81I",
3492 You("are frozen by %s gaze!", s_suffix(mon_nam(mon)));
3494 You("%s
\82Ì
\82É
\82ç
\82Ý
\82Å
\93®
\82¯
\82È
\82
\82È
\82Á
\82½
\81I", mon_nam(mon));
3495 nomul((ACURR(A_WIS) > 12 || rn2(4)) ? -tmp : -127);
3497 multi_reason = "frozen by a monster's gaze";
3499 multi_reason = "
\89ö
\95¨
\82Ì
\82É
\82ç
\82Ý
\82Å
\8dd
\92¼
\82µ
\82Ä
\82¢
\82é
\8e\9e\82É";
3504 pline("%s cannot defend itself.",
3505 Adjmonnam(mon, "blind"));
3507 pline("%s
\82Í
\96h
\8cä
\82Å
\82«
\82È
\82¢
\81D",
3508 Adjmonnam(mon,"
\96Ú
\82Ì
\8c©
\82¦
\82È
\82¢"));
3513 } else if (Free_action) {
3515 You("momentarily stiffen.");
3517 You("
\88ê
\8fu
\8dd
\92¼
\82µ
\82½
\81D");
3518 } else { /* gelatinous cube */
3520 You("are frozen by %s!", mon_nam(mon));
3522 You("%s
\82É
\82æ
\82Á
\82Ä
\93®
\82¯
\82È
\82
\82È
\82Á
\82½
\81I", mon_nam(mon));
3523 nomovemsg = You_can_move_again;
3526 multi_reason = "frozen by a monster";
3528 multi_reason = "
\89ö
\95¨
\82É
\82æ
\82Á
\82Ä
\8dd
\92¼
\82µ
\82Ä
\82¢
\82é
\8e\9e\82É";
3529 exercise(A_DEX, FALSE);
3532 case AD_COLD: /* brown mold or blue jelly */
3533 if (monnear(mon, u.ux, u.uy)) {
3534 if (Cold_resistance) {
3535 shieldeff(u.ux, u.uy);
3537 You_feel("a mild chill.");
3539 You("
\8a¦
\82³
\82ð
\8a´
\82¶
\82½
\81D");
3540 ugolemeffects(AD_COLD, tmp);
3544 You("are suddenly very cold!");
3546 You("
\93Ë
\91R
\81C
\96Ò
\97ó
\82É
\8a¦
\82
\82È
\82Á
\82½
\81I");
3548 /* monster gets stronger with your heat! */
3549 mon->mhp += tmp / 2;
3550 if (mon->mhpmax < mon->mhp)
3551 mon->mhpmax = mon->mhp;
3552 /* at a certain point, the monster will reproduce! */
3553 if (mon->mhpmax > ((int) (mon->m_lev + 1) * 8))
3554 (void) split_mon(mon, &youmonst);
3557 case AD_STUN: /* specifically yellow mold */
3559 make_stunned((long) tmp, TRUE);
3562 if (monnear(mon, u.ux, u.uy)) {
3563 if (Fire_resistance) {
3564 shieldeff(u.ux, u.uy);
3566 You_feel("mildly warm.");
3568 You("
\92g
\82©
\82³
\82ð
\8a´
\82¶
\82½
\81D");
3569 ugolemeffects(AD_FIRE, tmp);
3573 You("are suddenly very hot!");
3575 You("
\93Ë
\91R
\81C
\96Ò
\97ó
\82É
\94M
\82
\82È
\82Á
\82½
\81I");
3576 mdamageu(mon, tmp); /* fire damage */
3580 if (Shock_resistance) {
3581 shieldeff(u.ux, u.uy);
3583 You_feel("a mild tingle.");
3585 You("
\83s
\83\8a\83s
\83\8a\82Æá
\83\82ê
\82ð
\8a´
\82¶
\82½
\81D");
3586 ugolemeffects(AD_ELEC, tmp);
3590 You("are jolted with electricity!");
3592 You("
\93d
\8bC
\83V
\83\87\83b
\83N
\82ð
\82¤
\82¯
\82½
\81I");
3599 return (malive | mhit);
3603 * Special (passive) attacks on an attacking object by monsters done here.
3604 * Assumes the attack was successful.
3607 passive_obj(mon, obj, mattk)
3609 struct obj *obj; /* null means pick uwep, uswapwep or uarmg */
3610 struct attack *mattk; /* null means we find one internally */
3612 struct permonst *ptr = mon->data;
3615 /* [this first bit is obsolete; we're not called with Null anymore] */
3616 /* if caller hasn't specified an object, use uwep, uswapwep or uarmg */
3618 obj = (u.twoweap && uswapwep && !rn2(2)) ? uswapwep : uwep;
3619 if (!obj && mattk->adtyp == AD_ENCH)
3620 obj = uarmg; /* no weapon? then must be gloves */
3622 return; /* no object to affect */
3625 /* if caller hasn't specified an attack, find one */
3629 return; /* no passive attacks */
3630 if (ptr->mattk[i].aatyp == AT_NONE)
3631 break; /* try this one */
3633 mattk = &(ptr->mattk[i]);
3636 switch (mattk->adtyp) {
3638 if (!rn2(6) && !mon->mcan
3639 /* steam vortex: fire resist applies, fire damage doesn't */
3640 && mon->data != &mons[PM_STEAM_VORTEX]) {
3641 (void) erode_obj(obj, NULL, ERODE_BURN, EF_NONE);
3646 (void) erode_obj(obj, NULL, ERODE_CORRODE, EF_GREASE);
3651 (void) erode_obj(obj, (char *) 0, ERODE_RUST, EF_GREASE);
3656 (void) erode_obj(obj, (char *) 0, ERODE_CORRODE, EF_GREASE);
3661 if (drain_item(obj, TRUE) && carried(obj)
3662 && (obj->known || obj->oclass == ARMOR_CLASS)) {
3664 pline("%s less effective.", Yobjnam2(obj, "seem"));
3666 Your("%s
\82©
\82ç
\96\82\97Í
\82ª
\8fÁ
\82¦
\82½
\82æ
\82¤
\82¾
\81D", xname(obj));
3678 /* Note: caller must ascertain mtmp is mimicking... */
3680 stumble_onto_mimic(mtmp)
3684 const char *fmt = "Wait! That's %s!", *generic = "a monster", *what = 0;
3686 const char *fmt = "
\82¿
\82å
\82Á
\82Æ
\82Ü
\82Á
\82½
\81I%s
\82¾
\81I", *generic = "
\89ö
\95¨", *what = 0;
3688 if (!u.ustuck && !mtmp->mflee && dmgtype(mtmp->data, AD_STCK))
3693 what = generic; /* with default fmt */
3694 else if (M_AP_TYPE(mtmp) == M_AP_MONSTER)
3695 what = a_monnam(mtmp); /* differs from what was sensed */
3697 int glyph = levl[u.ux + u.dx][u.uy + u.dy].glyph;
3699 if (glyph_is_cmap(glyph) && (glyph_to_cmap(glyph) == S_hcdoor
3700 || glyph_to_cmap(glyph) == S_vcdoor))
3702 fmt = "The door actually was %s!";
3704 fmt = "
\94à
\82Í
\8eÀ
\8dÛ
\82É
\82Í%s
\82¾
\82Á
\82½
\81I";
3705 else if (glyph_is_object(glyph) && glyph_to_obj(glyph) == GOLD_PIECE)
3707 fmt = "That gold was %s!";
3709 fmt = "
\8bà
\89Ý
\82Í%s
\82¾
\82Á
\82½
\81I";
3711 /* cloned Wiz starts out mimicking some other monster and
3712 might make himself invisible before being revealed */
3713 if (mtmp->minvis && !See_invisible)
3716 what = a_monnam(mtmp);
3721 wakeup(mtmp, FALSE); /* clears mimicking */
3722 /* if hero is blind, wakeup() won't display the monster even though
3723 it's no longer concealed */
3724 if (!canspotmon(mtmp)
3725 && !glyph_is_invisible(levl[mtmp->mx][mtmp->my].glyph))
3726 map_invisible(mtmp->mx, mtmp->my);
3733 char *hands = makeplural(body_part(HAND));
3735 if (!u.umconf || mon->mconf)
3737 if (u.umconf == 1) {
3740 Your("%s stop tingling.", hands);
3742 Your("%s
\82Ìá
\83\82ê
\82ª
\82Æ
\82ê
\82½
\81D", hands);
3745 Your("%s stop glowing %s.", hands, hcolor(NH_RED));
3747 Your("%s
\82Ì%s
\8bP
\82«
\82Í
\82È
\82
\82È
\82Á
\82½
\81D", hands, hcolor(NH_RED));
3751 pline_The("tingling in your %s lessens.", hands);
3753 pline("%s
\82Ìá
\83\82ê
\82ª
\82Æ
\82ê
\82Ä
\82«
\82½
\81D",hands);
3756 Your("%s no longer glow so brightly %s.", hands, hcolor(NH_RED));
3758 Your("%s
\82Ì%s
\8bP
\82«
\82ª
\82È
\82
\82È
\82Á
\82Ä
\82«
\82½
\81D",hands, hcolor(NH_RED));
3764 flash_hits_mon(mtmp, otmp)
3766 struct obj *otmp; /* source of flash */
3768 int tmp, amt, res = 0, useeit = canseemon(mtmp);
3770 if (mtmp->msleeping) {
3771 mtmp->msleeping = 0;
3774 pline_The("flash awakens %s.", mon_nam(mtmp));
3776 pline("
\91M
\8cõ
\82Å%s
\82ª
\96Ú
\82ð
\8ao
\82Ü
\82µ
\82½
\81D", mon_nam(mtmp));
3779 } else if (mtmp->data->mlet != S_LIGHT) {
3780 if (!resists_blnd(mtmp)) {
3781 tmp = dist2(otmp->ox, otmp->oy, mtmp->mx, mtmp->my);
3784 pline("%s is blinded by the flash!", Monnam(mtmp));
3786 pline("%s
\82Í
\91M
\8cõ
\82Å
\96Ú
\82ª
\8c©
\82¦
\82È
\82
\82È
\82Á
\82½
\81I", Monnam(mtmp));
3789 if (mtmp->data == &mons[PM_GREMLIN]) {
3790 /* Rule #1: Keep them out of the light. */
3791 amt = otmp->otyp == WAN_LIGHT ? d(1 + otmp->spe, 4)
3792 : rn2(min(mtmp->mhp, 4));
3793 light_hits_gremlin(mtmp, amt);
3795 if (!DEADMONSTER(mtmp)) {
3796 if (!context.mon_moving)
3797 setmangry(mtmp, TRUE);
3798 if (tmp < 9 && !mtmp->isshk && rn2(4))
3799 monflee(mtmp, rn2(4) ? rnd(100) : 0, FALSE, TRUE);
3801 mtmp->mblinded = (tmp < 3) ? 0 : rnd(1 + 50 / tmp);
3809 light_hits_gremlin(mon, dmg)
3814 pline("%s %s!", Monnam(mon),
3815 (dmg > mon->mhp / 2) ? "wails in agony" : "cries out in pain");
3817 pline("%s
\82Í%s
\81I", Monnam(mon),
3818 (dmg > mon->mhp / 2) ? "
\8bê
\92É
\82Ì
\90º
\82ð
\82 \82°
\82½" : "
\8c\83\92É
\82Å
\8b©
\82ñ
\82¾");
3821 wake_nearto(mon->mx, mon->my, 30);
3822 if (DEADMONSTER(mon)) {
3823 if (context.mon_moving)
3824 monkilled(mon, (char *) 0, AD_BLND);
3827 } else if (cansee(mon->mx, mon->my) && !canspotmon(mon)) {
3828 map_invisible(mon->mx, mon->my);