X-Git-Url: http://git.osdn.net/view?a=blobdiff_plain;f=src%2Fpotion.c;h=66111f479fb9888f4bef4da37576f5aedf21544c;hb=b38b2d9f907996eba5e88ed244717985d3e89f0d;hp=c05cecab9ff65f67d8d349f44d422c0c40887109;hpb=054ea5c83de985535d46dcda3537b2c9adbc54b6;p=jnethack%2Fsource.git diff --git a/src/potion.c b/src/potion.c index c05ceca..66111f4 100644 --- a/src/potion.c +++ b/src/potion.c @@ -1,11 +1,11 @@ -/* NetHack 3.6 potion.c $NHDT-Date: 1520797133 2018/03/11 19:38:53 $ $NHDT-Branch: NetHack-3.6.0 $:$NHDT-Revision: 1.144 $ */ +/* NetHack 3.6 potion.c $NHDT-Date: 1573848199 2019/11/15 20:03:19 $ $NHDT-Branch: NetHack-3.6 $:$NHDT-Revision: 1.167 $ */ /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */ /*-Copyright (c) Robert Patrick Rankin, 2013. */ /* NetHack may be freely redistributed. See license for details. */ /* JNetHack Copyright */ /* (c) Issei Numata, Naoki Hamada, Shigehiro Miyashita, 1994-2000 */ -/* For 3.4-, Copyright (c) SHIRAKATA Kentaro, 2002-2019 */ +/* For 3.4-, Copyright (c) SHIRAKATA Kentaro, 2002-2020 */ /* JNetHack may be freely redistributed. See license for details. */ #include "hack.h" @@ -97,7 +97,7 @@ boolean talk; if (!xtime && old) { if (talk) -#if 0 /*JP*/ +#if 0 /*JP:T*/ You_feel("%s now.", Hallucination ? "less wobbly" : "a bit steadier"); #else @@ -125,6 +125,9 @@ boolean talk; set_itimeout(&HStun, xtime); } +/* Sick is overloaded with both fatal illness and food poisoning (via + u.usick_type bit mask), but delayed killer can only support one or + the other at a time. They should become separate intrinsics.... */ void make_sick(xtime, cause, talk, type) long xtime; @@ -132,9 +135,10 @@ const char *cause; /* sickness cause */ boolean talk; int type; { + struct kinfo *kptr; long old = Sick; -#if 0 +#if 0 /* tell player even if hero is unconscious */ if (Unaware) talk = FALSE; #endif @@ -179,11 +183,20 @@ int type; context.botl = TRUE; } + kptr = find_delayed_killer(SICK); if (Sick) { exercise(A_CON, FALSE); - delayed_killer(SICK, KILLED_BY_AN, cause); + /* setting delayed_killer used to be unconditional, but that's + not right when make_sick(0) is called to cure food poisoning + if hero was also fatally ill; this is only approximate */ + if (xtime || !old || !kptr) { + int kpfx = ((cause && !strcmp(cause, "#wizintrinsic")) + ? KILLED_BY : KILLED_BY_AN); + + delayed_killer(SICK, kpfx, cause); + } } else - dealloc_killer(find_delayed_killer(SICK)); + dealloc_killer(kptr); } void @@ -193,7 +206,7 @@ const char *msg; { long old = Slimed; -#if 0 +#if 0 /* tell player even if hero is unconscious */ if (Unaware) msg = 0; #endif @@ -201,10 +214,17 @@ const char *msg; if ((xtime != 0L) ^ (old != 0L)) { context.botl = TRUE; if (msg) - pline1(msg); + pline("%s", msg); } - if (!Slimed) + if (!Slimed) { dealloc_killer(find_delayed_killer(SLIMED)); + /* fake appearance is set late in turn-to-slime countdown */ + if (U_AP_TYPE == M_AP_MONSTER + && youmonst.mappearance == PM_GREEN_SLIME) { + youmonst.m_ap_type = M_AP_NOTHING; + youmonst.mappearance = 0; + } + } } /* start or stop petrification */ @@ -217,7 +237,7 @@ const char *killername; { long old = Stoned; -#if 0 +#if 0 /* tell player even if hero is unconscious */ if (Unaware) msg = 0; #endif @@ -225,7 +245,7 @@ const char *killername; if ((xtime != 0L) ^ (old != 0L)) { context.botl = TRUE; if (msg) - pline1(msg); + pline("%s", msg); } if (!Stoned) dealloc_killer(find_delayed_killer(STONED)); @@ -361,32 +381,43 @@ boolean talk; set_itimeout(&Blinded, xtime); if (u_could_see ^ can_see_now) { /* one or the other but not both */ - context.botl = TRUE; - vision_full_recalc = 1; /* blindness just got toggled */ - /* this vision recalculation used to be deferred until - moveloop(), but that made it possible for vision - irregularities to occur (cited case was force bolt - hitting adjacent potion of blindness and then a - secret door; hero was blinded by vapors but then - got the message "a door appears in the wall") */ - vision_recalc(0); - if (Blind_telepat || Infravision) - see_monsters(); - - /* avoid either of the sequences - "Sting starts glowing", [become blind], "Sting stops quivering" or - "Sting starts quivering", [regain sight], "Sting stops glowing" - by giving "Sting is quivering" when becoming blind or - "Sting is glowing" when regaining sight so that the eventual - "stops" message matches */ - if (warn_obj_cnt && uwep && (EWarn_of_mon & W_WEP) != 0L) - Sting_effects(-1); - /* update dknown flag for inventory picked up while blind */ - if (can_see_now) - learn_unseen_invent(); + toggle_blindness(); } } +/* blindness has just started or just ended--caller enforces that; + called by Blindf_on(), Blindf_off(), and make_blinded() */ +void +toggle_blindness() +{ + boolean Stinging = (uwep && (EWarn_of_mon & W_WEP) != 0L); + + /* blindness has just been toggled */ + context.botl = TRUE; /* status conditions need update */ + vision_full_recalc = 1; /* vision has changed */ + /* this vision recalculation used to be deferred until moveloop(), + but that made it possible for vision irregularities to occur + (cited case was force bolt hitting an adjacent potion of blindness + and then a secret door; hero was blinded by vapors but then got the + message "a door appears in the wall" because wall spot was IN_SIGHT) */ + vision_recalc(0); + if (Blind_telepat || Infravision || Stinging) + see_monsters(); /* also counts EWarn_of_mon monsters */ + /* + * Avoid either of the sequences + * "Sting starts glowing", [become blind], "Sting stops quivering" or + * "Sting starts quivering", [regain sight], "Sting stops glowing" + * by giving "Sting is quivering" when becoming blind or + * "Sting is glowing" when regaining sight so that the eventual + * "stops" message matches the most recent "Sting is ..." one. + */ + if (Stinging) + Sting_effects(-1); + /* update dknown flag for inventory picked up while blind */ + if (!Blind) + learn_unseen_invent(); +} + boolean make_hallucinated(xtime, talk, mask) long xtime; /* nonzero if this is an attempt to turn on hallucination */ @@ -400,7 +431,7 @@ long mask; /* nonzero if resistance status should change by mask */ if (Unaware) talk = FALSE; -#if 0 /*JP*/ +#if 0 /*JP:T*/ message = (!xtime) ? "Everything %s SO boring now." : "Oh wow! Everything %s so cosmic!"; #else @@ -430,7 +461,7 @@ long mask; /* nonzero if resistance status should change by mask */ if (!haseyes(youmonst.data)) { strange_feeling((struct obj *) 0, (char *) 0); } else if (Blind) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ const char *eyes = body_part(EYE); if (eyecount(youmonst.data) != 1) @@ -495,10 +526,21 @@ boolean talk; } } +/* set or clear "slippery fingers" */ +void +make_glib(xtime) +int xtime; +{ + set_itimeout(&Glib, xtime); + /* may change "(being worn)" to "(being worn; slippery)" or vice versa */ + if (uarmg) + update_inventory(); +} + void self_invis_message() { -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s %s.", Hallucination ? "Far out, man! You" : "Gee! All of a sudden, you", @@ -531,7 +573,7 @@ ghost_from_bottle() pline("•r‚ðŠJ‚¯‚é‚ƁC‰½‚©‚ªo‚Ä‚«‚½D"); return; } -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("As you open the bottle, an enormous %s emerges!", Hallucination ? rndmonnam(NULL) : (const char *) "ghost"); #else @@ -664,7 +706,7 @@ register struct obj *otmp; if (nothing) { unkn++; -#if 0 /*JP*/ +#if 0 /*JP:T*/ You("have a %s feeling for a moment, then it passes.", Hallucination ? "normal" : "peculiar"); #else @@ -701,7 +743,7 @@ register struct obj *otmp; break; } else { /* unlike unicorn horn, overrides Fixed_abil */ -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("Wow! This makes you feel %s!", (otmp->blessed) ? (unfixable_trouble_count(FALSE) ? "better" : "great") @@ -733,8 +775,7 @@ register struct obj *otmp; the spell or with a unihorn; this is better than full healing in that it can restore all of them, not just half, and a blessed potion restores them all at once */ - if (otmp->otyp == POT_RESTORE_ABILITY && - u.ulevel < u.ulevelmax) { + if (otmp->otyp == POT_RESTORE_ABILITY && u.ulevel < u.ulevelmax) { do { pluslvl(FALSE); } while (u.ulevel < u.ulevelmax && otmp->blessed); @@ -744,9 +785,9 @@ register struct obj *otmp; case POT_HALLUCINATION: if (Hallucination || Halluc_resistance) nothing++; - (void) make_hallucinated( - itimeout_incr(HHallucination, rn1(200, 600 - 300 * bcsign(otmp))), - TRUE, 0L); + (void) make_hallucinated(itimeout_incr(HHallucination, + rn1(200, 600 - 300 * bcsign(otmp))), + TRUE, 0L); break; case POT_WATER: if (!otmp->blessed && !otmp->cursed) { @@ -828,14 +869,14 @@ register struct obj *otmp; break; case POT_BOOZE: unkn++; -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("Ooph! This tastes like %s%s!", otmp->odiluted ? "watered down " : "", Hallucination ? "dandelion wine" : "liquid fire"); #else pline("‚¤‚¥‚Á‚ՁI‚±‚ê‚Í%s%s‚̂悤‚È–¡‚ª‚·‚éI", otmp->odiluted ? "…‚Å”–‚ß‚½" : "", - Hallucination ? "ƒ^ƒ“ƒ|ƒ|ƒƒCƒ“" : "”R—¿ƒIƒCƒ‹"); + Hallucination ? "‚½‚ñ‚Û‚Û‚Ì‚¨Žð" : "”R—¿ƒIƒCƒ‹"); #endif if (!otmp->blessed) make_confused(itimeout_incr(HConfusion, d(3, 8)), FALSE); @@ -918,7 +959,7 @@ register struct obj *otmp; unkn++; if (otmp->cursed) -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("Yecch! This tastes %s.", Hallucination ? "overripe" : "rotten"); #else @@ -926,7 +967,7 @@ register struct obj *otmp; Hallucination ? "n‚µ‚·‚¬‚½" : "•…‚Á‚½"); #endif else -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline( Hallucination ? "This tastes like 10%% real %s%s all-natural beverage." @@ -984,7 +1025,7 @@ register struct obj *otmp; */ You("‚»‚̏ê‚Å“®‚¯‚È‚­‚È‚Á‚½I"); else -#if 0 /*JP*/ +#if 0 /*JP:T*/ Your("%s are frozen to the %s!", makeplural(body_part(FOOT)), surface(u.ux, u.uy)); #else @@ -1088,7 +1129,7 @@ register struct obj *otmp; char contaminant[BUFSZ]; int typ = rn2(A_MAX); -#if 0 /*JP*/ +#if 0 /*JP:T*/ Sprintf(contaminant, "%s%s", (Poison_resistance) ? "mildly " : "", (otmp->fromsink) ? "contaminated tap water" @@ -1170,9 +1211,9 @@ register struct obj *otmp; } break; case POT_SPEED: + /* skip when mounted; heal_legs() would heal steed's legs */ if (Wounded_legs && !otmp->cursed && !u.usteed) { - /* heal_legs() would heal steeds legs */ - heal_legs(); + heal_legs(0); unkn++; break; } @@ -1325,9 +1366,9 @@ register struct obj *otmp; ceiling(u.ux,u.uy)); #endif /*JP - losehp(Maybe_Half_Phys(dmg), "colliding with the ceiling", + losehp(Maybe_Half_Phys(dmg), "colliding with the ceiling", */ - losehp(Maybe_Half_Phys(dmg), "“Vˆä‚É“ª‚ð‚Ԃ‚¯‚Ä", + losehp(Maybe_Half_Phys(dmg), "“Vˆä‚É“ª‚ð‚Ԃ‚¯‚Ä", KILLED_BY); nothing = 0; /* not nothing after all */ } @@ -1428,7 +1469,7 @@ register struct obj *otmp; } else { int dmg; -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("This burns%s!", otmp->blessed ? " a little" : otmp->cursed ? " a lot" : " like acid"); @@ -1502,6 +1543,8 @@ register boolean curesick, cureblind; mundane 'dirt', but if it doesn't, blindness isn't cured */ u.ucreamed = 0; make_blinded(0L, TRUE); + /* heal deafness too */ + make_deaf(0L, TRUE); } if (curesick) { make_vomiting(0L, TRUE); @@ -1517,7 +1560,7 @@ struct obj *obj; const char *txt; { if (flags.beginner || !txt) -#if 0 /*JP*/ +#if 0 /*JP:T*/ You("have a %s feeling for a moment, then it passes.", Hallucination ? "normal" : "strange"); #else @@ -1537,7 +1580,7 @@ const char *txt; useup(obj); } -#if 0 /*JP*/ +#if 0 /*JP:T*/ const char *bottlenames[] = { "bottle", "phial", "flagon", "carafe", "flask", "jar", "vial" }; #else @@ -1609,19 +1652,28 @@ const char *objphrase; /* "Your widget glows" or "Steed's saddle glows" */ glowcolor = hcolor(glowcolor); /*JP:3.6.0Žž“_‚Å‚Í“®ŽŒ‚Í"glow"‚¾‚¯‚È‚Ì‚ÅŒˆ‚ߌ‚‚¿*/ if (altfmt) -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s with %s aura.", objphrase, an(glowcolor)); #else pline("%s‚Í%sƒI[ƒ‰‚ɂ‚‚܂ꂽD", objphrase, glowcolor); #endif else -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s %s.", objphrase, glowcolor); #else pline("%s‚Í%s‹P‚¢‚½D", objphrase, jconj_adj(glowcolor)); #endif iflags.last_msg = PLNMSG_OBJ_GLOWS; targobj->bknown = !Hallucination; + } else { + /* didn't see what happened: forget the BUC state if that was + known unless the bless/curse state of the water is known; + without this, hero would know the new state even without + seeing the glow; priest[ess] will immediately relearn it */ + if (!potion->bknown || !potion->dknown) + targobj->bknown = 0; + /* [should the bknown+dknown exception require that water + be discovered or at least named?] */ } /* potions of water are the only shop goods whose price depends on their curse/bless state */ @@ -1694,7 +1746,7 @@ int how; char buf[BUFSZ]; if (hit_saddle && saddle) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ Sprintf(buf, "%s saddle", s_suffix(x_monnam(mon, ARTICLE_THE, (char *) 0, (SUPPRESS_IT | SUPPRESS_SADDLE), @@ -1706,7 +1758,7 @@ int how; FALSE)); #endif } else if (has_head(mon->data)) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ Sprintf(buf, "%s %s", s_suffix(mnam), (notonhead ? "body" : "head")); #else @@ -1716,7 +1768,7 @@ int how; } else { Strcpy(buf, mnam); } -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline_The("%s crashes on %s and breaks into shards.", botlnam, buf); #else @@ -1815,7 +1867,7 @@ int how; /*FALLTHRU*/ case POT_RESTORE_ABILITY: case POT_GAIN_ABILITY: - do_healing: + do_healing: angermon = FALSE; if (mon->mhp < mon->mhpmax) { mon->mhp = mon->mhpmax; @@ -1837,14 +1889,14 @@ int how; /* most common case */ || resists_poison(mon)) { if (canseemon(mon)) -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s looks unharmed.", Monnam(mon)); #else pline("%s‚Í‚È‚ñ‚Æ‚à‚È‚¢‚悤‚¾D", Monnam(mon)); #endif break; } - do_illness: + do_illness: if ((mon->mhpmax > 3) && !resist(mon, POTION_CLASS, 0, NOTELL)) mon->mhpmax /= 2; if ((mon->mhp > 2) && !resist(mon, POTION_CLASS, 0, NOTELL)) @@ -1907,7 +1959,7 @@ int how; if (is_undead(mon->data) || is_demon(mon->data) || is_were(mon->data) || is_vampshifter(mon)) { if (obj->blessed) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s %s in pain!", Monnam(mon), is_silent(mon->data) ? "writhes" : "shrieks"); #else @@ -1918,7 +1970,7 @@ int how; wake_nearto(tx, ty, mon->data->mlevel * 10); mon->mhp -= d(2, 6); /* should only be by you */ - if (mon->mhp < 1) + if (DEADMONSTER(mon)) killed(mon); else if (is_were(mon->data) && !is_human(mon->data)) new_were(mon); /* revert to human */ @@ -1947,7 +1999,7 @@ int how; pline("%s‚ÍŽK‚Ñ‚½D", Monnam(mon)); mon->mhp -= d(1, 6); /* should only be by you */ - if (mon->mhp < 1) + if (DEADMONSTER(mon)) killed(mon); } break; @@ -1957,7 +2009,7 @@ int how; break; case POT_ACID: if (!resists_acid(mon) && !resist(mon, POTION_CLASS, 0, NOTELL)) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("%s %s in pain!", Monnam(mon), is_silent(mon->data) ? "writhes" : "shrieks"); #else @@ -1967,7 +2019,7 @@ int how; if (!is_silent(mon->data)) wake_nearto(tx, ty, mon->data->mlevel * 10); mon->mhp -= d(obj->cursed ? 2 : 1, obj->blessed ? 4 : 8); - if (mon->mhp < 1) { + if (DEADMONSTER(mon)) { if (your_fault) killed(mon); else @@ -1988,7 +2040,7 @@ int how; */ } /* target might have been killed */ - if (mon->mhp > 0) { + if (!DEADMONSTER(mon)) { if (angermon) wakeup(mon, TRUE); else @@ -2044,7 +2096,7 @@ register struct obj *obj; */ pline("ƒEƒQƒFI–ò‚Í‚à‚Ì‚·‚²‚¢“õ‚¢‚ª‚·‚éI"); else if (haseyes(youmonst.data)) { -#if 0 /*JP*/ +#if 0 /*JP:T*/ const char *eyes = body_part(EYE); if (eyecount(youmonst.data) != 1) @@ -2091,8 +2143,10 @@ register struct obj *obj; u.uhp++, context.botl = 1; if (obj->blessed) cureblind = TRUE; - if (cureblind) + if (cureblind) { make_blinded(0L, !u.ucreamed); + make_deaf(0L, TRUE); + } exercise(A_CON, TRUE); break; case POT_SICKNESS: @@ -2130,7 +2184,7 @@ register struct obj *obj; case POT_INVISIBILITY: if (!Blind && !Invis) { kn++; -#if 0 /*JP*/ +#if 0 /*JP:T*/ pline("For an instant you %s!", See_invisible ? "could see right through yourself" : "couldn't see yourself"); @@ -2243,41 +2297,33 @@ STATIC_OVL short mixtype(o1, o2) register struct obj *o1, *o2; { + int o1typ = o1->otyp, o2typ = o2->otyp; + /* cut down on the number of cases below */ if (o1->oclass == POTION_CLASS - && (o2->otyp == POT_GAIN_LEVEL || o2->otyp == POT_GAIN_ENERGY - || o2->otyp == POT_HEALING || o2->otyp == POT_EXTRA_HEALING - || o2->otyp == POT_FULL_HEALING || o2->otyp == POT_ENLIGHTENMENT - || o2->otyp == POT_FRUIT_JUICE)) { - struct obj *swp; - - swp = o1; - o1 = o2; - o2 = swp; + && (o2typ == POT_GAIN_LEVEL || o2typ == POT_GAIN_ENERGY + || o2typ == POT_HEALING || o2typ == POT_EXTRA_HEALING + || o2typ == POT_FULL_HEALING || o2typ == POT_ENLIGHTENMENT + || o2typ == POT_FRUIT_JUICE)) { + /* swap o1 and o2 */ + o1typ = o2->otyp; + o2typ = o1->otyp; } - switch (o1->otyp) { + switch (o1typ) { case POT_HEALING: - switch (o2->otyp) { - case POT_SPEED: - case POT_GAIN_LEVEL: - case POT_GAIN_ENERGY: + if (o2typ == POT_SPEED) return POT_EXTRA_HEALING; - } + /*FALLTHRU*/ case POT_EXTRA_HEALING: - switch (o2->otyp) { - case POT_GAIN_LEVEL: - case POT_GAIN_ENERGY: - return POT_FULL_HEALING; - } case POT_FULL_HEALING: - switch (o2->otyp) { - case POT_GAIN_LEVEL: - case POT_GAIN_ENERGY: - return POT_GAIN_ABILITY; - } + if (o2typ == POT_GAIN_LEVEL || o2typ == POT_GAIN_ENERGY) + return (o1typ == POT_HEALING) ? POT_EXTRA_HEALING + : (o1typ == POT_EXTRA_HEALING) ? POT_FULL_HEALING + : POT_GAIN_ABILITY; + /*FALLTHRU*/ case UNICORN_HORN: - switch (o2->otyp) { + switch (o2typ) { case POT_SICKNESS: return POT_FRUIT_JUICE; case POT_HALLUCINATION: @@ -2287,12 +2333,12 @@ register struct obj *o1, *o2; } break; case AMETHYST: /* "a-methyst" == "not intoxicated" */ - if (o2->otyp == POT_BOOZE) + if (o2typ == POT_BOOZE) return POT_FRUIT_JUICE; break; case POT_GAIN_LEVEL: case POT_GAIN_ENERGY: - switch (o2->otyp) { + switch (o2typ) { case POT_CONFUSION: return (rn2(3) ? POT_BOOZE : POT_ENLIGHTENMENT); case POT_HEALING: @@ -2308,7 +2354,7 @@ register struct obj *o1, *o2; } break; case POT_FRUIT_JUICE: - switch (o2->otyp) { + switch (o2typ) { case POT_SICKNESS: return POT_SICKNESS; case POT_ENLIGHTENMENT: @@ -2320,7 +2366,7 @@ register struct obj *o1, *o2; } break; case POT_ENLIGHTENMENT: - switch (o2->otyp) { + switch (o2typ) { case POT_LEVITATION: if (rn2(3)) return POT_GAIN_LEVEL; @@ -2458,26 +2504,22 @@ dodip() 5, 95)) { pline1(nothing_happens); } else { - boolean was_wep, was_swapwep, was_quiver; short save_otyp = obj->otyp; /* KMH, conduct */ u.uconduct.polypiles++; - was_wep = (obj == uwep); - was_swapwep = (obj == uswapwep); - was_quiver = (obj == uquiver); - obj = poly_obj(obj, STRANGE_OBJECT); - if (was_wep) - setuwep(obj); - else if (was_swapwep) - setuswapwep(obj); - else if (was_quiver) - setuqwep(obj); - - if (obj->otyp != save_otyp) { + /* + * obj might be gone: + * poly_obj() -> set_wear() -> Amulet_on() -> useup() + * if obj->otyp is worn amulet and becomes AMULET_OF_CHANGE. + */ + if (!obj) { + makeknown(POT_POLYMORPH); + return 1; + } else if (obj->otyp != save_otyp) { makeknown(POT_POLYMORPH); useup(potion); prinv((char *) 0, obj, 0L); @@ -2516,11 +2558,10 @@ dodip() if ((long) amt < obj->quan) { obj = splitobj(obj, (long) amt); -#if 0 /*JP*/ +/*JP Sprintf(qbuf, "%ld of the", obj->quan); -#else +*/ Sprintf(qbuf, "%ld–{‚Ì", obj->quan); -#endif } } /* [N of] the {obj(s)} mix(es) with [one of] {the potion}... */ @@ -2533,6 +2574,8 @@ dodip() thesimpleoname(potion), (potion->quan > 1L) ? "‚̈ê‚Â" : ""); #endif + /* get rid of 'dippee' before potential perm_invent updates */ + useup(potion); /* now gone */ /* Mixing potions is dangerous... KMH, balance patch -- acid is particularly unstable */ if (obj->cursed || obj->otyp == POT_ACID || !rn2(10)) { @@ -2542,15 +2585,14 @@ dodip() to 'amt' because that's not implemented] */ obj->in_use = 1; /*JP - pline("BOOM! They explode!"); + pline("%sThey explode!", !Deaf ? "BOOM! " : ""); */ - pline("ƒo[ƒ“I”š”­‚µ‚½I"); + pline("%s”š”­‚µ‚½I", !Deaf ? "ƒo[ƒ“I" : ""); wake_nearto(u.ux, u.uy, (BOLT_LIM + 1) * (BOLT_LIM + 1)); exercise(A_STR, FALSE); if (!breathless(youmonst.data) || haseyes(youmonst.data)) potionbreathe(obj); useupall(obj); - useup(potion); losehp(amt + rnd(9), /* not physical damage */ /*JP "alchemic blast", KILLED_BY_AN); @@ -2566,6 +2608,8 @@ dodip() if (mixture != STRANGE_OBJECT) { obj->otyp = mixture; } else { + struct obj *otmp; + switch (obj->odiluted ? 1 : rnd(8)) { case 1: obj->otyp = POT_WATER; @@ -2574,21 +2618,20 @@ dodip() case 3: obj->otyp = POT_SICKNESS; break; - case 4: { - struct obj *otmp = mkobj(POTION_CLASS, FALSE); - + case 4: + otmp = mkobj(POTION_CLASS, FALSE); obj->otyp = otmp->otyp; obfree(otmp, (struct obj *) 0); break; - } default: useupall(obj); - useup(potion); - if (!Blind) -/*JP - pline_The("mixture glows brightly and evaporates."); -*/ - pline("¬‚º‚é‚Æ–ò‚Í–¾‚é‚­‹P‚«Cö”­‚µ‚½D"); +#if 0 /*JP:T*/ + pline_The("mixture %sevaporates.", + !Blind ? "glows brightly and " : ""); +#else + pline_The("¬‚º‚é‚Æ–ò‚Í%sö”­‚µ‚½D", + !Blind ? "–¾‚é‚­‹P‚«C" : ""); +#endif return 1; } } @@ -2607,7 +2650,6 @@ dodip() hcolor(OBJ_DESCR(objects[obj->otyp]))); } - useup(potion); /* this is required when 'obj' was split off from a bigger stack, so that 'obj' will now be assigned its own inventory slot; it has a side-effect of merging 'obj' into another compatible @@ -2615,7 +2657,7 @@ dodip() been made in order to get the merge result for both cases; as a consequence, mixing while Fumbling drops the mixture */ freeinv(obj); -#if 0 /*JP*/ +#if 0 /*JP:T*/ (void) hold_another_object(obj, "You drop %s!", doname(obj), (const char *) 0); #else @@ -2626,16 +2668,23 @@ dodip() } if (potion->otyp == POT_ACID && obj->otyp == CORPSE - && obj->corpsenm == PM_LICHEN && !Blind) { -#if 0 /*JP*/ + && obj->corpsenm == PM_LICHEN) { +#if 0 /*JP:T*/ pline("%s %s %s around the edges.", The(cxname(obj)), - otense(obj, "turn"), - potion->odiluted ? hcolor(NH_ORANGE) : hcolor(NH_RED)); + otense(obj, "turn"), Blind ? "wrinkled" + : potion->odiluted ? hcolor(NH_ORANGE) + : hcolor(NH_RED)); #else pline("%s‚Í‚Ó‚¿‚ª%s‚È‚Á‚½D", The(cxname(obj)), - jconj_adj(potion->odiluted ? hcolor(NH_ORANGE) : hcolor(NH_RED))); + Blind ? "‚µ‚킵‚í‚É" + : jconj_adj(potion->odiluted ? hcolor(NH_ORANGE) + : hcolor(NH_RED))); #endif potion->in_use = FALSE; /* didn't go poof */ + if (potion->dknown + && !objects[potion->otyp].oc_name_known + && !objects[potion->otyp].oc_uname) + docall(potion); return 1; } @@ -2692,8 +2741,8 @@ dodip() pline_The("potion spills and covers your %s with oil.", */ pline("–û‚Í”ò‚ÑŽU‚è‚ ‚È‚½‚Ì%s‚É‚©‚©‚Á‚½D", - makeplural(body_part(FINGER))); - incr_itimeout(&Glib, d(2, 10)); + fingers_or_gloves(TRUE)); + make_glib((int) (Glib & TIMEOUT) + d(2, 10)); } else if (obj->oclass != WEAPON_CLASS && !is_weptool(obj)) { /* the following cases apply only to weapons */ goto more_dips; @@ -2704,23 +2753,31 @@ dodip() } else if ((!is_rustprone(obj) && !is_corrodeable(obj)) || is_ammo(obj) || (!obj->oeroded && !obj->oeroded2)) { /* uses up potion, doesn't set obj->greased */ -#if 0 /*JP*/ - pline("%s %s with an oily sheen.", Yname2(obj), - otense(obj, "gleam")); + if (!Blind) +#if 0 /*JP:T*/ + pline("%s %s with an oily sheen.", Yname2(obj), + otense(obj, "gleam")); #else pline("%s‚Í–û‚ÌŒõ‘ò‚Å‚«‚ç‚è‚ÆŒõ‚Á‚½D", Yname2(obj)); #endif + else /*if (!uarmg)*/ +/*JP + pline("%s %s oily.", Yname2(obj), otense(obj, "feel")); +*/ + pline("%s‚Í–û‚Á‚Û‚¢D", Yname2(obj)); } else { -#if 0 /*JP*/ - pline("%s %s less %s.", Yname2(obj), otense(obj, "are"), +#if 0 /*JP:T*/ + pline("%s %s less %s.", Yname2(obj), + otense(obj, !Blind ? "are" : "feel"), (obj->oeroded && obj->oeroded2) ? "corroded and rusty" : obj->oeroded ? "rusty" : "corroded"); #else - pline("%s‚Ì%s‚ªŽæ‚ꂽD", Yname2(obj), + pline("%s‚Ì%s‚ªŽæ‚ꂽ%sD", Yname2(obj), (obj->oeroded && obj->oeroded2) ? "•…H‚ÆŽK" - : obj->oeroded ? "ŽK" : "•…H"); + : obj->oeroded ? "ŽK" : "•…H", + !Blind ? "" : "‚悤‚¾"); #endif if (obj->oeroded > 0) obj->oeroded--; @@ -2729,11 +2786,12 @@ dodip() wisx = TRUE; } exercise(A_WIS, wisx); - makeknown(potion->otyp); + if (potion->dknown) + makeknown(potion->otyp); useup(potion); return 1; } -more_dips: + more_dips: /* Allow filling of MAGIC_LAMPs to prevent identification by player */ if ((obj->otyp == OIL_LAMP || obj->otyp == MAGIC_LAMP) @@ -2762,13 +2820,17 @@ more_dips: */ You("%s‚É–û‚ð“ü‚ꂽD", yname(obj)); check_unpaid(potion); /* Yendorian Fuel Tax */ - obj->age += 2 * potion->age; /* burns more efficiently */ + /* burns more efficiently in a lamp than in a bottle; + diluted potion provides less benefit but we don't attempt + to track that the lamp now also has some non-oil in it */ + obj->age += (!potion->odiluted ? 4L : 3L) * potion->age / 2L; if (obj->age > 1500L) obj->age = 1500L; useup(potion); exercise(A_WIS, TRUE); } - makeknown(POT_OIL); + if (potion->dknown) + makeknown(POT_OIL); obj->spe = 1; update_inventory(); return 1; @@ -2809,26 +2871,41 @@ more_dips: singlepotion->dknown = FALSE; } else { singlepotion->dknown = !Hallucination; -#if 0 /*JP*/ + *newbuf = '\0'; if (mixture == POT_WATER && singlepotion->dknown) +/*JP Sprintf(newbuf, "clears"); - else +*/ + Sprintf(newbuf, "“§–¾"); + else if (!Blind) +#if 0 /*JP*/ Sprintf(newbuf, "turns %s", hcolor(OBJ_DESCR(objects[mixture]))); - pline_The("%spotion%s %s.", oldbuf, - more_than_one ? " that you dipped into" : "", newbuf); #else - if (mixture == POT_WATER && singlepotion->dknown) - Sprintf(newbuf, "“§–¾"); - else Sprintf(newbuf, "%s–ò", hcolor(OBJ_DESCR(objects[mixture]))); - pline_The("%s%s–ò‚Í%s‚É‚È‚Á‚½D.", more_than_one ? "Z‚µ‚½" : "", - oldbuf, newbuf); #endif - if (!objects[old_otyp].oc_uname - && !objects[old_otyp].oc_name_known && old_dknown) { + if (*newbuf) +#if 0 /*JP:T*/ + pline_The("%spotion%s %s.", oldbuf, + more_than_one ? " that you dipped into" : "", + newbuf); +#else + pline_The("%s%s–ò‚Í%s‚É‚È‚Á‚½D.", + more_than_one ? "Z‚µ‚½" : "", + oldbuf, newbuf); +#endif + else +/*JP + pline("Something happens."); +*/ + pline("‰½‚©‚ª‹N‚«‚½D"); + + if (old_dknown + && !objects[old_otyp].oc_name_known + && !objects[old_otyp].oc_uname) { struct obj fakeobj; + fakeobj = zeroobj; fakeobj.dknown = 1; fakeobj.otyp = old_otyp; @@ -2837,12 +2914,14 @@ more_dips: } } obj_extract_self(singlepotion); - singlepotion = + singlepotion = hold_another_object(singlepotion, /*JP - hold_another_object(singlepotion, "You juggle and drop %s!", + "You juggle and drop %s!", */ - hold_another_object(singlepotion, "‚¨Žè‹Ê‚µ‚Ä%s‚ð—Ž‚Æ‚µ‚Ä‚µ‚Ü‚Á‚½I", - doname(singlepotion), (const char *) 0); + "‚¨Žè‹Ê‚µ‚Ä%s‚ð—Ž‚Æ‚µ‚Ä‚µ‚Ü‚Á‚½I", + doname(singlepotion), + (const char *) 0); + nhUse(singlepotion); update_inventory(); return 1; } @@ -2853,8 +2932,9 @@ more_dips: pline("–Ê”’‚¢DDD"); return 1; -poof: - if (!objects[potion->otyp].oc_name_known + poof: + if (potion->dknown + && !objects[potion->otyp].oc_name_known && !objects[potion->otyp].oc_uname) docall(potion); useup(potion); @@ -2988,7 +3068,7 @@ struct monst *mon, /* monster being split */ reason[0] = '\0'; if (mtmp) -#if 0 /*JP*/ +#if 0 /*JP:T*/ Sprintf(reason, " from %s heat", (mtmp == &youmonst) ? the_your[1] : (const char *) s_suffix(mon_nam(mtmp)));