Some monsters can eat through iron bars

Any monster with rusting or corrosion attack can eat through
the bars. This includes rust monsters, grey oozes, and black puddings.

Original patch by Malcolm Ryan
This commit is contained in:
Pasi Kallinen
2015-04-13 19:36:49 +03:00
parent 6209d458f9
commit 1c970b171e
5 changed files with 34 additions and 6 deletions

View File

@@ -899,6 +899,7 @@ pudding corpses behave somewhat differently than before
mithril armor should have silver color
lichen corpse is an acid indicator
camera may contain a picture-painting demon
some monsters can eat through iron bars
Platform- and/or Interface-Specific Fixes

View File

@@ -1367,6 +1367,7 @@ E boolean FDECL(onscary, (int,int,struct monst *));
E void FDECL(monflee, (struct monst *, int, BOOLEAN_P, BOOLEAN_P));
E int FDECL(dochug, (struct monst *));
E int FDECL(m_move, (struct monst *,int));
E void FDECL(dissolve_bars, (int,int));
E boolean FDECL(closed_door, (int,int));
E boolean FDECL(accessible, (int,int));
E void FDECL(set_apparxy, (struct monst *));

View File

@@ -347,7 +347,7 @@ still_chewing(x,y)
if (!boulder && IS_ROCK(lev->typ) && !may_dig(x,y)) {
You("hurt your teeth on the %s.",
IS_TREE(lev->typ) ? "tree" : "hard stone");
lev->typ == IRONBARS ? "bars" : (IS_TREE(lev->typ) ? "tree" : "hard stone"));
nomul(0);
return 1;
} else if (context.digging.pos.x != x || context.digging.pos.y != y ||
@@ -362,9 +362,10 @@ still_chewing(x,y)
context.digging.effort =
(IS_ROCK(lev->typ) && !IS_TREE(lev->typ) ? 30 : 60) + u.udaminc;
You("start chewing %s %s.",
(boulder || IS_TREE(lev->typ)) ? "on a" : "a hole in the",
(boulder || IS_TREE(lev->typ) || lev->typ == IRONBARS) ? "on a" : "a hole in the",
boulder ? "boulder" :
IS_TREE(lev->typ) ? "tree" : IS_ROCK(lev->typ) ? "rock" : "door");
IS_TREE(lev->typ) ? "tree" : IS_ROCK(lev->typ) ? "rock" :
lev->typ == IRONBARS ? "bar" : "door");
watch_dig((struct monst *)0, x, y, FALSE);
return 1;
} else if ((context.digging.effort += (30 + u.udaminc)) <= 100) {
@@ -373,7 +374,8 @@ still_chewing(x,y)
context.digging.chew ? "continue" : "begin",
boulder ? "boulder" :
IS_TREE(lev->typ) ? "tree" :
IS_ROCK(lev->typ) ? "rock" : "door");
IS_ROCK(lev->typ) ? "rock" :
lev->typ == IRONBARS ? "bars" : "door");
context.digging.chew = TRUE;
watch_dig((struct monst *)0, x, y, FALSE);
return 1;
@@ -418,6 +420,9 @@ still_chewing(x,y)
} else if (IS_TREE(lev->typ)) {
digtxt = "chew through the tree.";
lev->typ = ROOM;
} else if (lev->typ == IRONBARS) {
digtxt = "eat through the bars.";
dissolve_bars(x,y);
} else if (lev->typ == SDOOR) {
if (lev->doormask & D_TRAPPED) {
lev->doormask = D_NODOOR;
@@ -630,10 +635,15 @@ int mode;
if (Passes_walls && may_passwall(x,y)) {
; /* do nothing */
} else if (tmpr->typ == IRONBARS) {
if ((dmgtype(youmonst.data, AD_RUST) ||
dmgtype(youmonst.data, AD_CORR)) &&
mode == DO_MOVE && still_chewing(x,y)) {
return FALSE;
}
if (!(Passes_walls || passes_bars(youmonst.data))) {
if (iflags.mention_walls)
You("cannot pass through the bars.");
return FALSE;
return FALSE;
}
} else if (tunnels(youmonst.data) && !needspick(youmonst.data)) {
/* Eat the rock. */

View File

@@ -285,6 +285,7 @@ struct permonst *mptr;
{
return (boolean) (passes_walls(mptr) || amorphous(mptr) ||
unsolid(mptr) || is_whirly(mptr) || verysmall(mptr) ||
dmgtype(mptr, AD_CORR) || dmgtype(mptr, AD_RUST) ||
(slithy(mptr) && !bigmonst(mptr)));
}

View File

@@ -1180,7 +1180,14 @@ postmov:
add_damage(mtmp->mx, mtmp->my, 0L);
}
} else if (levl[mtmp->mx][mtmp->my].typ == IRONBARS) {
if (flags.verbose && canseemon(mtmp))
if (may_dig(mtmp->mx,mtmp->my) &&
(dmgtype(ptr, AD_RUST) || dmgtype(ptr, AD_CORR))) {
if (canseemon(mtmp))
pline("%s eats through the iron bars.",
Monnam(mtmp));
dissolve_bars(mtmp->mx, mtmp->my);
return(3);
} else if (flags.verbose && canseemon(mtmp))
Norep("%s %s %s the iron bars.", Monnam(mtmp),
/* pluralization fakes verb conjugation */
makeplural(locomotion(ptr, "pass")),
@@ -1266,6 +1273,14 @@ postmov:
return(mmoved);
}
void
dissolve_bars(x, y)
register int x, y;
{
levl[x][y].typ = (Is_special(&u.uz) || *in_rooms(x,y,0)) ? ROOM : CORR;
newsym(x, y);
}
boolean
closed_door(x, y)
register int x, y;