// Note: The caller must 'free_me(obj)' after potionbreathe returns. // this is called only here and by do_throw. void potionbreathe(obj_t *obj) { switch(obj->otype) { case POT_RESTORE_STRENGTH: case POT_GAIN_STRENGTH: if (you.ustr < you.ustrmax) { you.ustr++; flags.botl |= BOTL_STR; } break; case POT_HEALING: case POT_EXTRA_HEALING: if (you.uhp < you.uhpmax) { you.uhp++; flags.botl |= BOTL_HP; } break; case POT_SICKNESS: if (you.uhp <= 5) you.uhp = 1; else you.uhp -= 5; flags.botl |= BOTL_HP; break; case POT_CONFUSION: case POT_BOOZE: if (!Confusion) message("You feel somewhat dizzy."); Confusion += rnd(5); break; case POT_INVISIBILITY: message("For an instant you couldn't see your right hand."); break; case POT_PARALYSIS: message("Something seems to be holding you."); nomul(-rnd(5)); break; case POT_SPEED: Fast += rnd(5); message("Your knees seem more flexible now."); break; case POT_BLINDNESS: if (!Blind) message("It suddenly gets dark."); Blind += rnd(5); seeoff(false); break; /* case POT_GAIN_LEVEL: case POT_LEVITATION: case POT_FRUIT_JUICE: case POT_MONSTER_DETECTION: case POT_OBJECT_DETECTION: break; */ default: break; } /* note: no obfree() */ }
void justswld(struct monst *mtmp, char *name) { mtmp->mx = u.ux; mtmp->my = u.uy; u.ustuck = mtmp; pmon(mtmp); kludge("%s swallows you!", name); more(); seeoff(1); u.uswallow = 1; swallowed(); }
int doeat(void) { struct obj *otmp; int tmp; // Is there some food (probably a heavy corpse) here on the ground? if (!Levitation) for (otmp = _level->objects; otmp; otmp = otmp->nobj) { if (otmp->ox == _u.ux && otmp->oy == _u.uy && otmp->olet == FOOD_SYM) { pline("There %s %s here; eat %s? [ny] ", (otmp->quan == 1) ? "is" : "are", doname(otmp), (otmp->quan == 1) ? "it" : "one"); if (readchar() == 'y') { if (otmp->quan != 1) (void) splitobj(otmp, 1); freeobj(otmp); otmp = addinv(otmp); addtobill(otmp); goto gotit; } } } otmp = getobj("%", "eat"); if (!otmp) return 0; gotit: if (otmp->otyp == TIN) { if (uwep) { switch (uwep->otyp) { case CAN_OPENER: tmp = 1; break; case DAGGER: tmp = 3; break; case PICK_AXE: case AXE: tmp = 6; break; default: goto no_opener; } pline("Using your %s you try to open the tin.", aobjnam(uwep, NULL)); } else { no_opener: pline("It is not so easy to open this tin."); if (Glib) { pline("The tin slips out of your hands."); if (otmp->quan > 1) { struct obj *obj; obj = splitobj(otmp, 1); if (otmp == uwep) setuwep(obj); } dropx(otmp); return 1; } tmp = 10 + rn2(1 + 500 / ((int) (_u.ulevel + _u.ustr))); } tin.reqtime = tmp; tin.usedtime = 0; tin.tin = otmp; occupation = opentin; occtxt = "opening the tin"; return 1; } const struct objclass* ftmp = &c_Objects[otmp->otyp]; multi = -ftmp->oc_delay; if (otmp->otyp >= CORPSE && eatcorpse(otmp)) goto eatx; if (!rn2(7) && otmp->otyp != FORTUNE_COOKIE) { pline("Blecch! Rotten food!"); if (!rn2(4)) { pline("You feel rather light headed."); Confusion += d(2, 4); } else if (!rn2(4) && !Blind) { pline("Everything suddenly goes dark."); Blind = d(2, 10); seeoff(0); } else if (!rn2(3)) { if (Blind) pline("The world spins and you slap against the floor."); else pline("The world spins and goes dark."); nomul(-rnd(10)); nomovemsg = "You are conscious again."; } lesshungry(ftmp->nutrition / 4); } else { if (_u.uhunger >= 1500) { pline("You choke over your food."); pline("You die..."); killer = ftmp->oc_name; done("choked"); } switch (otmp->otyp) { case FOOD_RATION: if (_u.uhunger <= 200) pline("That food really hit the spot!"); else if (_u.uhunger <= 700) pline("That satiated your stomach!"); else { pline("You're having a hard time getting all that food down."); multi -= 2; } lesshungry(ftmp->nutrition); if (multi < 0) nomovemsg = "You finished your meal."; break; case TRIPE_RATION: pline("Yak - dog food!"); more_experienced(1, 0); _wflags.botl = 1; if (rn2(2)) { pline("You vomit."); morehungry(20); if (Sick) { Sick = 0; // David Neves pline("What a relief!"); } } else lesshungry(ftmp->nutrition); break; default: if (otmp->otyp >= CORPSE) pline("That %s tasted terrible!", ftmp->oc_name); else pline("That %s was delicious!", ftmp->oc_name); lesshungry(ftmp->nutrition); if (otmp->otyp == DEAD_LIZARD && (Confusion > 2)) Confusion = 2; else if (otmp->otyp == FORTUNE_COOKIE) { if (Blind) { pline("This cookie has a scrap of paper inside!"); pline("What a pity, that you cannot read it!"); } else print_rumor(); } else if (otmp->otyp == LUMP_OF_ROYAL_JELLY) { // This stuff seems to be VERY healthy! if (_u.ustrmax < 118) ++_u.ustrmax; if (_u.ustr < _u.ustrmax) ++_u.ustr; _u.uhp += rnd(20); if (_u.uhp > _u.uhpmax) { if (!rn2(17)) ++_u.uhpmax; _u.uhp = _u.uhpmax; } heal_legs(); } break; } } eatx: if (multi < 0 && !nomovemsg) { static char msgbuf[BUFSZ]; sprintf(msgbuf, "You finished eating the %s.", ftmp->oc_name); nomovemsg = msgbuf; } useup(otmp); return 1; }
int dodrink() { struct obj *otmp,*objs; struct monst *mtmp; int unkn = 0, nothing = 0; otmp = getobj("!", "drink"); if(!otmp) return(0); if(!strcmp(objects[otmp->otyp].oc_descr, "smoky") && !rn2(13)) { ghost_from_bottle(); goto use_it; } switch(otmp->otyp){ case POT_RESTORE_STRENGTH: unkn++; pline("Wow! This makes you feel great!"); if(u.ustr < u.ustrmax) { u.ustr = u.ustrmax; flags.botl = 1; } break; case POT_BOOZE: unkn++; pline("Ooph! This tastes like liquid fire!"); Confusion += d(3,8); /* the whiskey makes us feel better */ if(u.uhp < u.uhpmax) losehp(-1, "bottle of whiskey"); if(!rn2(4)) { pline("You pass out."); multi = -rnd(15); nomovemsg = "You awake with a headache."; } break; case POT_INVISIBILITY: if(Invis || See_invisible) nothing++; else { if(!Blind) pline("Gee! All of a sudden, you can't see yourself."); else pline("You feel rather airy."), unkn++; newsym(u.ux,u.uy); } Invis += rn1(15,31); break; case POT_FRUIT_JUICE: pline("This tastes like fruit juice."); lesshungry(20); break; case POT_HEALING: pline("You begin to feel better."); flags.botl = 1; u.uhp += rnd(10); if(u.uhp > u.uhpmax) u.uhp = ++u.uhpmax; if(Blind) Blind = 1; /* see on next move */ if(Sick) Sick = 0; break; case POT_PARALYSIS: if(Levitation) pline("You are motionlessly suspended."); else pline("Your feet are frozen to the floor!"); nomul(-(rn1(10,25))); break; case POT_MONSTER_DETECTION: if(!fmon) { strange_feeling(otmp, "You feel threatened."); return(1); } else { cls(); for(mtmp = fmon; mtmp; mtmp = mtmp->nmon) if(mtmp->mx > 0) at(mtmp->mx,mtmp->my,mtmp->data->mlet); prme(); pline("You sense the presence of monsters."); more(); docrt(); } break; case POT_OBJECT_DETECTION: if(!fobj) { strange_feeling(otmp, "You feel a pull downward."); return(1); } else { for(objs = fobj; objs; objs = objs->nobj) if(objs->ox != u.ux || objs->oy != u.uy) goto outobjmap; pline("You sense the presence of objects close nearby."); break; outobjmap: cls(); for(objs = fobj; objs; objs = objs->nobj) at(objs->ox,objs->oy,objs->olet); prme(); pline("You sense the presence of objects."); more(); docrt(); } break; case POT_SICKNESS: pline("Yech! This stuff tastes like poison."); if(Poison_resistance) pline("(But in fact it was biologically contaminated orange juice.)"); losestr(rn1(4,3)); losehp(rnd(10), "contaminated potion"); break; case POT_CONFUSION: if(!Confusion) pline("Huh, What? Where am I?"); else nothing++; Confusion += rn1(7,16); break; case POT_GAIN_STRENGTH: pline("Wow do you feel strong!"); if(u.ustr >= 118) break; /* > 118 is impossible */ if(u.ustr > 17) u.ustr += rnd(118-u.ustr); else u.ustr++; if(u.ustr > u.ustrmax) u.ustrmax = u.ustr; flags.botl = 1; break; case POT_SPEED: if(Wounded_legs) { heal_legs(); unkn++; break; } if(!(Fast & ~INTRINSIC)) pline("You are suddenly moving much faster."); else pline("Your legs get new energy."), unkn++; Fast += rn1(10,100); break; case POT_BLINDNESS: if(!Blind) pline("A cloud of darkness falls upon you."); else nothing++; Blind += rn1(100,250); seeoff(0); break; case POT_GAIN_LEVEL: pluslvl(); break; case POT_EXTRA_HEALING: pline("You feel much better."); flags.botl = 1; u.uhp += d(2,20)+1; if(u.uhp > u.uhpmax) u.uhp = (u.uhpmax += 2); if(Blind) Blind = 1; if(Sick) Sick = 0; break; case POT_LEVITATION: if(!Levitation) float_up(); else nothing++; Levitation += rnd(100); u.uprops[PROP(RIN_LEVITATION)].p_tofn = float_down; break; default: impossible("What a funny potion! (%u)", otmp->otyp); return(0); } if(nothing) { unkn++; pline("You have a peculiar feeling for a moment, then it passes."); } if(otmp->dknown && !objects[otmp->otyp].oc_name_known) { if(!unkn) { objects[otmp->otyp].oc_name_known = 1; more_experienced(0,10); } else if(!objects[otmp->otyp].oc_uname) docall(otmp); } use_it: useup(otmp); return(1); }
void goto_level(int newlevel, boolean at_stairs) { int fd; boolean up = (newlevel < dlevel); if(newlevel <= 0) done("escaped"); /* in fact < 0 is impossible */ if(newlevel > MAXLEVEL) newlevel = MAXLEVEL; /* strange ... */ if(newlevel == dlevel) return; /* this can happen */ glo(dlevel); fd = creat(lock, FMASK); if(fd < 0) { /* * This is not quite impossible: e.g., we may have * exceeded our quota. If that is the case then we * cannot leave this level, and cannot save either. * Another possibility is that the directory was not * writable. */ pline("A mysterious force prevents you from going %s.", up ? "up" : "down"); return; } if(Punished) unplacebc(); u.utrap = 0; /* needed in level_tele */ u.ustuck = 0; /* idem */ keepdogs(); seeoff(1); if(u.uswallow) /* idem */ u.uswldtim = u.uswallow = 0; flags.nscrinh = 1; u.ux = FAR; /* hack */ (void) inshop(); /* probably was a trapdoor */ savelev(fd,dlevel); (void) close(fd); dlevel = newlevel; if(maxdlevel < dlevel) maxdlevel = dlevel; glo(dlevel); if(!level_exists[(int)dlevel]) mklev(); else { extern int hackpid; if((fd = open(lock, O_RDONLY)) < 0) { pline("Cannot open %s .", lock); pline("Probably someone removed it."); done("tricked"); } getlev(fd, hackpid, dlevel); (void) close(fd); } if(at_stairs) { if(up) { u.ux = xdnstair; u.uy = ydnstair; if(!u.ux) { /* entering a maze from below? */ u.ux = xupstair; /* this will confuse the player! */ u.uy = yupstair; } if(Punished && !Levitation){ pline("With great effort you climb the stairs."); placebc(1); } } else { u.ux = xupstair; u.uy = yupstair; if(inv_weight() + 5 > 0 || Punished){ pline("You fall down the stairs."); /* %% */ losehp(rnd(3), "fall"); if(Punished) { if(uwep != uball && rn2(3)){ pline("... and are hit by the iron ball."); losehp(rnd(20), "iron ball"); } placebc(1); } selftouch("Falling, you"); } } { struct monst *mtmp = m_at(u.ux, u.uy); if(mtmp) mnexto(mtmp); } } else { /* trapdoor or level_tele */ do { u.ux = rnd(COLNO-1); u.uy = rn2(ROWNO); } while(levl[(int)u.ux][(int)u.uy].typ != ROOM || m_at(u.ux,u.uy)); if(Punished){ if(uwep != uball && !up /* %% */ && rn2(5)){ pline("The iron ball falls on your head."); losehp(rnd(25), "iron ball"); } placebc(1); } selftouch("Falling, you"); } (void) inshop(); initrack(); losedogs(); { struct monst *mtmp; if ((mtmp = m_at(u.ux, u.uy))) mnexto(mtmp); /* riv05!a3 */ } flags.nscrinh = 0; setsee(); seeobjs(); /* make old cadavers disappear - riv05!a3 */ docrt(); pickup(1); read_engr_at(u.ux,u.uy); }
// Note: this is a litte different, it will return true // iff the action is COMPLETE, and false if there was no action OR // the action is needing to finish up (after leaving SenseForm). // So if (do_drink) the caller should exit invform _and_ tick, // otherwise the caller should just exit invform. // (exiting the invform occurs _before_ calling do_drink..) // .. Ok, I've modified this again so that it lets the caller distinguish // between "it worked" and "it worked and I popped up EngraveForm". tri_val_t do_drink(obj_t *otmp) { obj_t *objs; // monst_t *mtmp; Boolean unkn = false, nothing = false, b; Short tmp; if (!otmp) return NO_OP; tmp = oc_descr_offset[otmp->otype]; if (tmp >= 0 && (0 == StrNCompare("smoky", oc_descrs+tmp, 5)) && !rund(13)) { ghost_from_bottle(); useup(otmp); return DONE; } switch(otmp->otype) { case POT_RESTORE_STRENGTH: unkn = true; message("Wow! This makes you feel great!"); if (you.ustr < you.ustrmax) { you.ustr = you.ustrmax; flags.botl |= BOTL_STR; } break; case POT_BOOZE: unkn = true; message("Ooph! This tastes like liquid fire!"); Confusion += dice(3,8); /* the whiskey makes us feel better */ if (you.uhp < you.uhpmax) losehp(-1, "bottle of whiskey"); if (!rund(4)) { tri_val_t t; // Short coma; message("You pass out."); multi = -rnd(15); spin_multi("You awake with a headache."); // coma = rnd(15); // // do { tick(); } while (--coma > 0); // message("You awake with a headache."); // // nomovemsg = "You awake with a headache."; t = finish_do_drink(otmp, nothing, unkn); //.... I guess.... return (t==DONE ? NO_OP : t); // so that we don't take any _more_ turns } break; case POT_INVISIBILITY: if (Invis || See_invisible) nothing = true; else { if (!Blind) message("Gee! All of a sudden, you can't see yourself."); else { message("You feel rather airy."); unkn = true; } newsym(you.ux,you.uy); } Invis += rund(15)+31; break; case POT_FRUIT_JUICE: message("This tastes like fruit juice."); lesshungry(20); break; case POT_HEALING: message("You begin to feel better."); you.uhp += rnd(10); if (you.uhp > you.uhpmax) you.uhp = ++you.uhpmax; if (Blind) Blind = 1; /* you'll see again on the next move */ if (Sick) Sick = 0; flags.botl |= BOTL_HP; break; case POT_PARALYSIS: if (Levitation) message("You are motionlessly suspended."); else message("Your feet are frozen to the floor!"); nomul(-(rund(10)+25)); break; case POT_MONSTER_DETECTION: if (!fmon) { b = strange_feeling(otmp, "You feel threatened."); return ((b) ? GO_ON : DONE); } else { sense_what = SENSE_MONSTERS; sense_by_what = otmp; sense_init_screen(); FrmPopupForm(SenseForm); return GO_ON; // to postpone the tick! } break; case POT_OBJECT_DETECTION: if (!fobj) { b = strange_feeling(otmp, "You feel a pull downward."); return ((b) ? GO_ON : DONE); } else { for (objs = fobj; objs; objs = objs->nobj) if (objs->ox != you.ux || objs->oy != you.uy) { sense_what = SENSE_OBJECTS; sense_by_what = otmp; sense_init_screen(); FrmPopupForm(SenseForm); return GO_ON; // to postpone the tick! } message("You sense the presence of objects close nearby."); break; } break; case POT_SICKNESS: message("Yech! This stuff tastes like poison."); if (Poison_resistance) message("(But in fact it was biologically contaminated orange juice.)"); losestr(rund(4)+3); losehp(rnd(10), "contaminated potion"); flags.botl |= BOTL_STR; break; case POT_CONFUSION: if (!Confusion) message("Huh, What? Where am I?"); else nothing = true; Confusion += rund(7)+16; break; case POT_GAIN_STRENGTH: message("Wow do you feel strong!"); if (you.ustr >= 118) break; /* > 118 is impossible */ if (you.ustr > 17) you.ustr += rnd(118-you.ustr); else you.ustr++; if (you.ustr > you.ustrmax) you.ustrmax = you.ustr; flags.botl |= BOTL_STR; break; case POT_SPEED: if (Wounded_legs) { heal_legs(); unkn = true; break; } if (!(Fast & ~INTRINSIC)) message("You are suddenly moving much faster."); else { message("Your legs get new energy."); unkn = true; } Fast += rund(10)+100; break; case POT_BLINDNESS: if (!Blind) message("A cloud of darkness falls upon you."); else nothing = true; Blind += rund(100)+250; seeoff(false); break; case POT_GAIN_LEVEL: pluslvl(); break; case POT_EXTRA_HEALING: message("You feel much better."); you.uhp += dice(2,20)+1; if (you.uhp > you.uhpmax) you.uhp = (you.uhpmax += 2); if (Blind) Blind = 1; if (Sick) Sick = 0; flags.botl |= BOTL_HP; break; case POT_LEVITATION: if (!Levitation) float_up(); else nothing = true; Levitation += rnd(100); // you.uprops[PROP(RIN_LEVITATION)].p_tofn = float_down; // UNNEEDED, // it has been replaced by tweaking timeout.c to call float_down directly! break; default: StrPrintF(ScratchBuffer, "What a funny potion! (%u)", otmp->otype); message(ScratchBuffer); return NO_OP; } return finish_do_drink(otmp, nothing, unkn); }
/* * mhitu: monster hits you * returns 1 if monster dies (e.g. 'y', 'F'), 0 otherwise */ bool mhitu(struct monst *mtmp) { struct permonst *mdat = mtmp->data; int tmp, ctmp; nomul(0); /* If swallowed, can only be affected by hissers and by u.ustuck */ if (u.uswallow) { if (mtmp != u.ustuck) { if (mdat->mlet == 'c' && !rn2(13)) { pline("Outside, you hear %s's hissing!", monnam(mtmp)); pline("%s gets turned to stone!", Monnam(u.ustuck)); pline("And the same fate befalls you."); done_in_by(mtmp); /* "notreached": not return(1); */ } return (0); } switch (mdat->mlet) { /* now mtmp == u.ustuck */ case ',': youswld(mtmp, (u.uac > 0) ? u.uac + 4 : 4, 5, "The trapper"); break; case '\'': youswld(mtmp, rnd(6), 7, "The lurker above"); break; case 'P': youswld(mtmp, d(2, 4), 12, "The purple worm"); break; default: /* This is not impossible! */ pline("The mysterious monster totally digests you."); u.uhp = 0; } if (u.uhp < 1) done_in_by(mtmp); return (0); } if (mdat->mlet == 'c' && Stoned) return (0); /* make eels visible the moment they hit/miss us */ if (mdat->mlet == ';' && mtmp->minvis && cansee(mtmp->mx, mtmp->my)) { mtmp->minvis = 0; pmon(mtmp); } if (!strchr("1&DuxynNF", mdat->mlet)) tmp = hitu(mtmp, d(mdat->damn, mdat->damd)); else tmp = 0; if (strchr(UNDEAD, mdat->mlet) && midnight()) tmp += hitu(mtmp, d(mdat->damn, mdat->damd)); ctmp = tmp && !mtmp->mcan && (!uarm || objects[uarm->otyp].a_can < rnd(3) || !rn2(50)); switch (mdat->mlet) { case '1': if (wiz_hit(mtmp)) /* he disappeared */ return (1); break; case '&': if (!mtmp->cham && !mtmp->mcan && !rn2(13)) { makemon(PM_DEMON, u.ux, u.uy); } else { hitu(mtmp, d(2, 6)); hitu(mtmp, d(2, 6)); hitu(mtmp, rnd(3)); hitu(mtmp, rnd(3)); hitu(mtmp, rn1(4, 2)); } break; case ',': if (tmp) justswld(mtmp, "The trapper"); break; case '\'': if (tmp) justswld(mtmp, "The lurker above"); break; case ';': if (ctmp) { if (!u.ustuck && !rn2(10)) { pline("%s swings itself around you!", Monnam(mtmp)); u.ustuck = mtmp; } else if (u.ustuck == mtmp && levl[mtmp->mx][mtmp->my].typ == POOL) { pline("%s drowns you ...", Monnam(mtmp)); done("drowned"); } } break; case 'A': if (ctmp && rn2(2)) { if (Poison_resistance) pline("The sting doesn't seem to affect you."); else { pline("You feel weaker!"); losestr(1); } } break; case 'C': hitu(mtmp, rnd(6)); break; case 'c': if (!rn2(5)) { pline("You hear %s's hissing!", monnam(mtmp)); if (ctmp || !rn2(20) || (flags.moonphase == NEW_MOON && !carrying(DEAD_LIZARD))) Stoned = 5; } break; case 'D': if (rn2(6) || mtmp->mcan) { hitu(mtmp, d(3, 10)); hitu(mtmp, rnd(8)); hitu(mtmp, rnd(8)); break; } kludge("%s breathes fire!", "The dragon"); buzz(-1, mtmp->mx, mtmp->my, u.ux - mtmp->mx, u.uy - mtmp->my); break; case 'd': hitu(mtmp, d(2, (flags.moonphase == FULL_MOON) ? 3 : 4)); break; case 'e': hitu(mtmp, d(3, 6)); break; case 'F': if (mtmp->mcan) break; kludge("%s explodes!", "The freezing sphere"); if (Cold_resistance) pline("You don't seem affected by it."); else { xchar dn; if (17 - (u.ulevel / 2) > rnd(20)) { pline("You get blasted!"); dn = 6; } else { pline("You duck the blast..."); dn = 3; } losehp_m(d(dn, 6), mtmp); } mondead(mtmp); return (1); case 'g': if (ctmp && multi >= 0 && !rn2(3)) { kludge("You are frozen by %ss juices", "the cube'"); nomul(-rnd(10)); } break; case 'h': if (ctmp && multi >= 0 && !rn2(5)) { nomul(-rnd(10)); kludge("You are put to sleep by %ss bite!", "the homunculus'"); } break; case 'j': tmp = hitu(mtmp, rnd(3)); tmp &= hitu(mtmp, rnd(3)); if (tmp) { hitu(mtmp, rnd(4)); hitu(mtmp, rnd(4)); } break; case 'k': if ((hitu(mtmp, rnd(4)) || !rn2(3)) && ctmp) poisoned("bee's sting", mdat->mname); break; case 'L': if (tmp) stealgold(mtmp); break; case 'N': if (mtmp->mcan && !Blind) { pline("%s tries to seduce you, but you seem not interested.", Amonnam(mtmp, "plain")); if (rn2(3)) rloc(mtmp); } else if (steal(mtmp)) { rloc(mtmp); mtmp->mflee = 1; } break; case 'n': if (!uwep && !uarm && !uarmh && !uarms && !uarmg) { pline("%s hits! (I hope you don't mind)", Monnam(mtmp)); u.uhp += rnd(7); if (!rn2(7)) u.uhpmax++; if (u.uhp > u.uhpmax) u.uhp = u.uhpmax; flags.botl = 1; if (!rn2(50)) rloc(mtmp); } else { hitu(mtmp, d(2, 6)); hitu(mtmp, d(2, 6)); } break; case 'o': tmp = hitu(mtmp, rnd(6)); if (hitu(mtmp, rnd(6)) && tmp && /* hits with both paws */ !u.ustuck && rn2(2)) { u.ustuck = mtmp; kludge("%s has grabbed you!", "The owlbear"); u.uhp -= d(2, 8); } else if (u.ustuck == mtmp) { u.uhp -= d(2, 8); pline("You are being crushed."); } break; case 'P': if (ctmp && !rn2(4)) justswld(mtmp, "The purple worm"); else hitu(mtmp, d(2, 4)); break; case 'Q': hitu(mtmp, rnd(2)); hitu(mtmp, rnd(2)); break; case 'R': if (tmp && uarmh && !uarmh->rustfree && (int)uarmh->spe >= -1) { pline("Your helmet rusts!"); uarmh->spe--; } else if (ctmp && uarm && !uarm->rustfree && /* Mike Newton */ uarm->otyp < STUDDED_LEATHER_ARMOR && (int)uarm->spe >= -1) { pline("Your armor rusts!"); uarm->spe--; } break; case 'S': if (ctmp && !rn2(8)) poisoned("snake's bite", mdat->mname); break; case 's': if (tmp && !rn2(8)) poisoned("scorpion's sting", mdat->mname); hitu(mtmp, rnd(8)); hitu(mtmp, rnd(8)); break; case 'T': hitu(mtmp, rnd(6)); hitu(mtmp, rnd(6)); break; case 't': if (!rn2(5)) rloc(mtmp); break; case 'u': mtmp->mflee = 1; break; case 'U': hitu(mtmp, d(3, 4)); hitu(mtmp, d(3, 4)); break; case 'v': if (ctmp && !u.ustuck) u.ustuck = mtmp; break; case 'V': if (tmp) u.uhp -= 4; if (ctmp) losexp(); break; case 'W': if (ctmp) losexp(); break; #ifndef NOWORM case 'w': if (tmp) wormhit(mtmp); #endif /* NOWORM */ break; case 'X': hitu(mtmp, rnd(5)); hitu(mtmp, rnd(5)); hitu(mtmp, rnd(5)); break; case 'x': { long side = rn2(2) ? RIGHT_SIDE : LEFT_SIDE; pline("%s pricks in your %s leg!", Monnam(mtmp), (side == RIGHT_SIDE) ? "right" : "left"); set_wounded_legs(side, rnd(50)); losehp_m(2, mtmp); break; } case 'y': if (mtmp->mcan) break; mondead(mtmp); if (!Blind) { pline("You are blinded by a blast of light!"); Blind = d(4, 12); seeoff(0); } return (1); case 'Y': hitu(mtmp, rnd(6)); break; } if (u.uhp < 1) done_in_by(mtmp); return (0); }