1: /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
   2: /* hack.potion.c - version 1.0.3 */
   3: 
   4: #include "hack.h"
   5: extern int float_down();
   6: extern char *nomovemsg;
   7: extern struct monst youmonst;
   8: extern struct monst *makemon();
   9: 
  10: dodrink() {
  11:     register struct obj *otmp,*objs;
  12:     register struct monst *mtmp;
  13:     register int unkn = 0, nothing = 0;
  14: 
  15:     otmp = getobj("!", "drink");
  16:     if(!otmp) return(0);
  17:     if(!strcmp(objects[otmp->otyp].oc_descr, "smoky") && !rn2(13)) {
  18:         ghost_from_bottle();
  19:         goto use_it;
  20:     }
  21:     switch(otmp->otyp){
  22:     case POT_RESTORE_STRENGTH:
  23:         unkn++;
  24:         pline("Wow!  This makes you feel great!");
  25:         if(u.ustr < u.ustrmax) {
  26:             u.ustr = u.ustrmax;
  27:             flags.botl = 1;
  28:         }
  29:         break;
  30:     case POT_BOOZE:
  31:         unkn++;
  32:         pline("Ooph!  This tastes like liquid fire!");
  33:         Confusion += d(3,8);
  34:         /* the whiskey makes us feel better */
  35:         if(u.uhp < u.uhpmax) losehp(-1, "bottle of whiskey");
  36:         if(!rn2(4)) {
  37:             pline("You pass out.");
  38:             multi = -rnd(15);
  39:             nomovemsg = "You awake with a headache.";
  40:         }
  41:         break;
  42:     case POT_INVISIBILITY:
  43:         if(Invis || See_invisible)
  44:           nothing++;
  45:         else {
  46:           if(!Blind)
  47:             pline("Gee!  All of a sudden, you can't see yourself.");
  48:           else
  49:             pline("You feel rather airy."), unkn++;
  50:           newsym(u.ux,u.uy);
  51:         }
  52:         Invis += rn1(15,31);
  53:         break;
  54:     case POT_FRUIT_JUICE:
  55:         pline("This tastes like fruit juice.");
  56:         lesshungry(20);
  57:         break;
  58:     case POT_HEALING:
  59:         pline("You begin to feel better.");
  60:         flags.botl = 1;
  61:         u.uhp += rnd(10);
  62:         if(u.uhp > u.uhpmax)
  63:             u.uhp = ++u.uhpmax;
  64:         if(Blind) Blind = 1;    /* see on next move */
  65:         if(Sick) Sick = 0;
  66:         break;
  67:     case POT_PARALYSIS:
  68:         if(Levitation)
  69:             pline("You are motionlessly suspended.");
  70:         else
  71:             pline("Your feet are frozen to the floor!");
  72:         nomul(-(rn1(10,25)));
  73:         break;
  74:     case POT_MONSTER_DETECTION:
  75:         if(!fmon) {
  76:             strange_feeling(otmp, "You feel threatened.");
  77:             return(1);
  78:         } else {
  79:             cls();
  80:             for(mtmp = fmon; mtmp; mtmp = mtmp->nmon)
  81:                 if(mtmp->mx > 0)
  82:                 at(mtmp->mx,mtmp->my,mtmp->data->mlet);
  83:             prme();
  84:             pline("You sense the presence of monsters.");
  85:             more();
  86:             docrt();
  87:         }
  88:         break;
  89:     case POT_OBJECT_DETECTION:
  90:         if(!fobj) {
  91:             strange_feeling(otmp, "You feel a pull downward.");
  92:             return(1);
  93:         } else {
  94:             for(objs = fobj; objs; objs = objs->nobj)
  95:             if(objs->ox != u.ux || objs->oy != u.uy)
  96:                 goto outobjmap;
  97:             pline("You sense the presence of objects close nearby.");
  98:             break;
  99:         outobjmap:
 100:             cls();
 101:             for(objs = fobj; objs; objs = objs->nobj)
 102:                 at(objs->ox,objs->oy,objs->olet);
 103:             prme();
 104:             pline("You sense the presence of objects.");
 105:             more();
 106:             docrt();
 107:         }
 108:         break;
 109:     case POT_SICKNESS:
 110:         pline("Yech! This stuff tastes like poison.");
 111:         if(Poison_resistance)
 112:     pline("(But in fact it was biologically contaminated orange juice.)");
 113:         losestr(rn1(4,3));
 114:         losehp(rnd(10), "contaminated potion");
 115:         break;
 116:     case POT_CONFUSION:
 117:         if(!Confusion)
 118:             pline("Huh, What?  Where am I?");
 119:         else
 120:             nothing++;
 121:         Confusion += rn1(7,16);
 122:         break;
 123:     case POT_GAIN_STRENGTH:
 124:         pline("Wow do you feel strong!");
 125:         if(u.ustr >= 118) break;    /* > 118 is impossible */
 126:         if(u.ustr > 17) u.ustr += rnd(118-u.ustr);
 127:         else u.ustr++;
 128:         if(u.ustr > u.ustrmax) u.ustrmax = u.ustr;
 129:         flags.botl = 1;
 130:         break;
 131:     case POT_SPEED:
 132:         if(Wounded_legs) {
 133:             heal_legs();
 134:             unkn++;
 135:             break;
 136:         }
 137:         if(!(Fast & ~INTRINSIC))
 138:             pline("You are suddenly moving much faster.");
 139:         else
 140:             pline("Your legs get new energy."), unkn++;
 141:         Fast += rn1(10,100);
 142:         break;
 143:     case POT_BLINDNESS:
 144:         if(!Blind)
 145:             pline("A cloud of darkness falls upon you.");
 146:         else
 147:             nothing++;
 148:         Blind += rn1(100,250);
 149:         seeoff(0);
 150:         break;
 151:     case POT_GAIN_LEVEL:
 152:         pluslvl();
 153:         break;
 154:     case POT_EXTRA_HEALING:
 155:         pline("You feel much better.");
 156:         flags.botl = 1;
 157:         u.uhp += d(2,20)+1;
 158:         if(u.uhp > u.uhpmax)
 159:             u.uhp = (u.uhpmax += 2);
 160:         if(Blind) Blind = 1;
 161:         if(Sick) Sick = 0;
 162:         break;
 163:     case POT_LEVITATION:
 164:         if(!Levitation)
 165:             float_up();
 166:         else
 167:             nothing++;
 168:         Levitation += rnd(100);
 169:         u.uprops[PROP(RIN_LEVITATION)].p_tofn = float_down;
 170:         break;
 171:     default:
 172:         impossible("What a funny potion! (%u)", otmp->otyp);
 173:         return(0);
 174:     }
 175:     if(nothing) {
 176:         unkn++;
 177:         pline("You have a peculiar feeling for a moment, then it passes.");
 178:     }
 179:     if(otmp->dknown && !objects[otmp->otyp].oc_name_known) {
 180:         if(!unkn) {
 181:             objects[otmp->otyp].oc_name_known = 1;
 182:             more_experienced(0,10);
 183:         } else if(!objects[otmp->otyp].oc_uname)
 184:             docall(otmp);
 185:     }
 186: use_it:
 187:     useup(otmp);
 188:     return(1);
 189: }
 190: 
 191: pluslvl()
 192: {
 193:     register num;
 194: 
 195:     pline("You feel more experienced.");
 196:     num = rnd(10);
 197:     u.uhpmax += num;
 198:     u.uhp += num;
 199:     if(u.ulevel < 14) {
 200:         extern long newuexp();
 201: 
 202:         u.uexp = newuexp()+1;
 203:         pline("Welcome to experience level %u.", ++u.ulevel);
 204:     }
 205:     flags.botl = 1;
 206: }
 207: 
 208: strange_feeling(obj,txt)
 209: register struct obj *obj;
 210: register char *txt;
 211: {
 212:     if(flags.beginner)
 213:         pline("You have a strange feeling for a moment, then it passes.");
 214:     else
 215:         pline(txt);
 216:     if(!objects[obj->otyp].oc_name_known && !objects[obj->otyp].oc_uname)
 217:         docall(obj);
 218:     useup(obj);
 219: }
 220: 
 221: char *bottlenames[] = {
 222:     "bottle", "phial", "flagon", "carafe", "flask", "jar", "vial"
 223: };
 224: 
 225: potionhit(mon, obj)
 226: register struct monst *mon;
 227: register struct obj *obj;
 228: {
 229:     extern char *xname();
 230:     register char *botlnam = bottlenames[rn2(SIZE(bottlenames))];
 231:     boolean uclose, isyou = (mon == &youmonst);
 232: 
 233:     if(isyou) {
 234:         uclose = TRUE;
 235:         pline("The %s crashes on your head and breaks into shivers.",
 236:             botlnam);
 237:         losehp(rnd(2), "thrown potion");
 238:     } else {
 239:         uclose = (dist(mon->mx,mon->my) < 3);
 240:         /* perhaps 'E' and 'a' have no head? */
 241:         pline("The %s crashes on %s's head and breaks into shivers.",
 242:             botlnam, monnam(mon));
 243:         if(rn2(5) && mon->mhp > 1)
 244:             mon->mhp--;
 245:     }
 246:     pline("The %s evaporates.", xname(obj));
 247: 
 248:     if(!isyou && !rn2(3)) switch(obj->otyp) {
 249: 
 250:     case POT_RESTORE_STRENGTH:
 251:     case POT_GAIN_STRENGTH:
 252:     case POT_HEALING:
 253:     case POT_EXTRA_HEALING:
 254:         if(mon->mhp < mon->mhpmax) {
 255:             mon->mhp = mon->mhpmax;
 256:             pline("%s looks sound and hale again!", Monnam(mon));
 257:         }
 258:         break;
 259:     case POT_SICKNESS:
 260:         if(mon->mhpmax > 3)
 261:             mon->mhpmax /= 2;
 262:         if(mon->mhp > 2)
 263:             mon->mhp /= 2;
 264:         break;
 265:     case POT_CONFUSION:
 266:     case POT_BOOZE:
 267:         mon->mconf = 1;
 268:         break;
 269:     case POT_INVISIBILITY:
 270:         unpmon(mon);
 271:         mon->minvis = 1;
 272:         pmon(mon);
 273:         break;
 274:     case POT_PARALYSIS:
 275:         mon->mfroz = 1;
 276:         break;
 277:     case POT_SPEED:
 278:         mon->mspeed = MFAST;
 279:         break;
 280:     case POT_BLINDNESS:
 281:         mon->mblinded |= 64 + rn2(64);
 282:         break;
 283: /*
 284: 	case POT_GAIN_LEVEL:
 285: 	case POT_LEVITATION:
 286: 	case POT_FRUIT_JUICE:
 287: 	case POT_MONSTER_DETECTION:
 288: 	case POT_OBJECT_DETECTION:
 289: 		break;
 290: */
 291:     }
 292:     if(uclose && rn2(5))
 293:         potionbreathe(obj);
 294:     obfree(obj, Null(obj));
 295: }
 296: 
 297: potionbreathe(obj)
 298: register struct obj *obj;
 299: {
 300:     switch(obj->otyp) {
 301:     case POT_RESTORE_STRENGTH:
 302:     case POT_GAIN_STRENGTH:
 303:         if(u.ustr < u.ustrmax) u.ustr++, flags.botl = 1;
 304:         break;
 305:     case POT_HEALING:
 306:     case POT_EXTRA_HEALING:
 307:         if(u.uhp < u.uhpmax) u.uhp++, flags.botl = 1;
 308:         break;
 309:     case POT_SICKNESS:
 310:         if(u.uhp <= 5) u.uhp = 1; else u.uhp -= 5;
 311:         flags.botl = 1;
 312:         break;
 313:     case POT_CONFUSION:
 314:     case POT_BOOZE:
 315:         if(!Confusion)
 316:             pline("You feel somewhat dizzy.");
 317:         Confusion += rnd(5);
 318:         break;
 319:     case POT_INVISIBILITY:
 320:         pline("For an instant you couldn't see your right hand.");
 321:         break;
 322:     case POT_PARALYSIS:
 323:         pline("Something seems to be holding you.");
 324:         nomul(-rnd(5));
 325:         break;
 326:     case POT_SPEED:
 327:         Fast += rnd(5);
 328:         pline("Your knees seem more flexible now.");
 329:         break;
 330:     case POT_BLINDNESS:
 331:         if(!Blind) pline("It suddenly gets dark.");
 332:         Blind += rnd(5);
 333:         seeoff(0);
 334:         break;
 335: /*
 336: 	case POT_GAIN_LEVEL:
 337: 	case POT_LEVITATION:
 338: 	case POT_FRUIT_JUICE:
 339: 	case POT_MONSTER_DETECTION:
 340: 	case POT_OBJECT_DETECTION:
 341: 		break;
 342: */
 343:     }
 344:     /* note: no obfree() */
 345: }
 346: 
 347: /*
 348:  * -- rudimentary -- to do this correctly requires much more work
 349:  * -- all sharp weapons get one or more qualities derived from the potions
 350:  * -- texts on scrolls may be (partially) wiped out; do they become blank?
 351:  * --   or does their effect change, like under Confusion?
 352:  * -- all objects may be made invisible by POT_INVISIBILITY
 353:  * -- If the flask is small, can one dip a large object? Does it magically
 354:  * --   become a jug? Etc.
 355:  */
 356: dodip(){
 357:     register struct obj *potion, *obj;
 358: 
 359:     if(!(obj = getobj("#", "dip")))
 360:         return(0);
 361:     if(!(potion = getobj("!", "dip into")))
 362:         return(0);
 363:     pline("Interesting...");
 364:     if(obj->otyp == ARROW || obj->otyp == DART ||
 365:        obj->otyp == CROSSBOW_BOLT) {
 366:         if(potion->otyp == POT_SICKNESS) {
 367:             useup(potion);
 368:             if(obj->spe < 7) obj->spe++;    /* %% */
 369:         }
 370:     }
 371:     return(1);
 372: }
 373: 
 374: ghost_from_bottle(){
 375:     extern struct permonst pm_ghost;
 376:     register struct monst *mtmp;
 377: 
 378:     if(!(mtmp = makemon(PM_GHOST,u.ux,u.uy))){
 379:         pline("This bottle turns out to be empty.");
 380:         return;
 381:     }
 382:     mnexto(mtmp);
 383:     pline("As you open the bottle, an enormous ghost emerges!");
 384:     pline("You are frightened to death, and unable to move.");
 385:     nomul(-3);
 386: }

Defined functions

dodip defined in line 356; used 2 times
dodrink defined in line 10; used 2 times
ghost_from_bottle defined in line 374; used 1 times
  • in line 18
pluslvl defined in line 191; used 2 times
potionbreathe defined in line 297; used 2 times
potionhit defined in line 225; used 2 times
strange_feeling defined in line 208; used 9 times

Defined variables

bottlenames defined in line 221; used 2 times
  • in line 230(2)
Last modified: 1985-10-01
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 3349
Valid CSS Valid XHTML 1.0 Strict