fix #6187 - attempting to eat inedible artifact

Rearrange the tests for edibility of non-food so that touching an
artifact won't happen unless the object could be eaten.

Add a bit of bulletproofing for rust monsters trying to eat a
rustproofed item and spitting it out.  Wishing for rustproof iron
ring, cursing it, wearing it, and attempting to eat it as a rust
monster would remove the rustproofing and spit it onto the floor,
ignoring the cursed state as far as taking it off goes.  That was
an issue in 3.4.3 and probably in 3.6.0, but in current code the
'rustproof' part of the wish would be ignored for an item which
isn't subject to erosion damage, so hero-as-rust monster will
successfully eat the ring instead of spitting it out.
This commit is contained in:
PatR
2017-10-14 02:09:43 -07:00
parent 8723742015
commit 1e3c00d760
+23 -10
View File
@@ -2443,10 +2443,7 @@ doeat()
* mails, players who polymorph back to human in the middle of their * mails, players who polymorph back to human in the middle of their
* metallic meal, etc.... * metallic meal, etc....
*/ */
if (!(carried(otmp) ? retouch_object(&otmp, FALSE) if (!is_edible(otmp)) {
: touch_artifact(otmp, &youmonst))) {
return 1;
} else if (!is_edible(otmp)) {
You("cannot eat that!"); You("cannot eat that!");
return 0; return 0;
} else if ((otmp->owornmask & (W_ARMOR | W_TOOL | W_AMUL | W_SADDLE)) } else if ((otmp->owornmask & (W_ARMOR | W_TOOL | W_AMUL | W_SADDLE))
@@ -2454,6 +2451,9 @@ doeat()
/* let them eat rings */ /* let them eat rings */
You_cant("eat %s you're wearing.", something); You_cant("eat %s you're wearing.", something);
return 0; return 0;
} else if (!(carried(otmp) ? retouch_object(&otmp, FALSE)
: touch_artifact(otmp, &youmonst))) {
return 1; /* got blasted so use a turn */
} }
if (is_metallic(otmp) && u.umonnum == PM_RUST_MONSTER if (is_metallic(otmp) && u.umonnum == PM_RUST_MONSTER
&& otmp->oerodeproof) { && otmp->oerodeproof) {
@@ -2468,13 +2468,26 @@ doeat()
/* The regurgitated object's rustproofing is gone now */ /* The regurgitated object's rustproofing is gone now */
otmp->oerodeproof = 0; otmp->oerodeproof = 0;
make_stunned((HStun & TIMEOUT) + (long) rn2(10), TRUE); make_stunned((HStun & TIMEOUT) + (long) rn2(10), TRUE);
You("spit %s out onto the %s.", the(xname(otmp)), /*
surface(u.ux, u.uy)); * We don't expect rust monsters to be wielding welded weapons
if (carried(otmp)) { * or wearing cursed rings which were rustproofed, but guard
freeinv(otmp); * against the possibility just in case.
dropy(otmp); */
if (welded(otmp) || (otmp->cursed && (otmp->owornmask & W_RING))) {
otmp->bknown = 1; /* for ring; welded() does this for weapon */
You("spit out %s.", the(xname(otmp)));
} else {
You("spit %s out onto the %s.", the(xname(otmp)),
surface(u.ux, u.uy));
if (carried(otmp)) {
/* no need to check for leash in use; it's not metallic */
if (otmp->owornmask)
remove_worn_item(otmp, FALSE);
freeinv(otmp);
dropy(otmp);
}
stackobj(otmp);
} }
stackobj(otmp);
return 1; return 1;
} }
/* KMH -- Slow digestion is... indigestible */ /* KMH -- Slow digestion is... indigestible */