oracle and rumor regarding priestly donations
keep various delayed killers separate to avoid mixed up messages
don't place randomly-placed aquatic monsters in lava on special levels
+hiding monsters don't hide under cockatrice/chickatrice corpses
Platform- and/or Interface-Specific Fixes
E void NDECL(rescham);
E void NDECL(restartcham);
E void FDECL(restore_cham, (struct monst *));
+E boolean FDECL(hideunder, (struct monst*));
E void FDECL(mon_animal_list, (BOOLEAN_P));
E int FDECL(newcham, (struct monst *,struct permonst *,BOOLEAN_P,BOOLEAN_P));
E int FDECL(can_be_hatched, (int));
nomul(0);
}
- if (hides_under(youmonst.data))
- u.uundetected = OBJ_AT(u.ux, u.uy);
- else if (youmonst.data->mlet == S_EEL)
- u.uundetected = is_pool(u.ux, u.uy) && !Is_waterlevel(&u.uz);
- else if (u.dx || u.dy)
- u.uundetected = 0;
+ if (hides_under(youmonst.data) || (youmonst.data->mlet == S_EEL) ||
+ u.dx || u.dy)
+ (void) hideunder(&youmonst);
/*
* Mimics (or whatever) become noticeable if they move and are
}
delobj(otmp);
if (at_u && u.uundetected && hides_under(youmonst.data))
- u.uundetected = OBJ_AT(u.ux, u.uy);
+ (void) hideunder(&youmonst);
}
/*
if(in_mklev)
if(x && y)
(void) mkobj_at(0, x, y, TRUE);
- if(hides_under(ptr) && OBJ_AT(x, y))
- mtmp->mundetected = TRUE;
+ (void) hideunder(mtmp);
break;
case S_LIGHT:
case S_ELEMENTAL:
}
break;
case S_EEL:
- if (is_pool(x, y))
- mtmp->mundetected = TRUE;
+ (void) hideunder(mtmp);
break;
case S_LEPRECHAUN:
mtmp->msleeping = 1;
return(FALSE);
}
+/* monster/hero tries to hide under something at the current location */
+boolean
+hideunder(mtmp)
+struct monst *mtmp;
+{
+ boolean undetected = FALSE;
+ xchar x = (mtmp == &youmonst) ? u.ux : mtmp->mx;
+ xchar y = (mtmp == &youmonst) ? u.uy : mtmp->my;
+
+ if (mtmp->data->mlet == S_EEL) {
+ undetected = (is_pool(x, y) && !Is_waterlevel(&u.uz));
+ } else if (hides_under(mtmp->data) && OBJ_AT(x, y)) {
+ struct obj *otmp = level.objects[x][y];
+
+ /* most monsters won't hide under cockatrice corpse */
+ if (otmp->nexthere || otmp->otyp != CORPSE ||
+ (mtmp == &youmonst ? Stone_resistance : resists_ston(mtmp)) ||
+ !touch_petrifies(&mons[otmp->corpsenm]))
+ undetected = TRUE;
+ }
+
+ if (mtmp == &youmonst) u.uundetected = undetected;
+ else mtmp->mundetected = undetected;
+ return undetected;
+}
+
short *animal_list = 0; /* list of PM values for animal monsters */
int animal_list_count;
if (!mtmp->perminvis || pm_invisible(olddata))
mtmp->perminvis = pm_invisible(mdat);
mtmp->minvis = mtmp->invis_blkd ? 0 : mtmp->perminvis;
- if (!(hides_under(mdat) && OBJ_AT(mtmp->mx, mtmp->my)) &&
- !(mdat->mlet == S_EEL && is_pool(mtmp->mx, mtmp->my)))
- mtmp->mundetected = 0;
+ if (mtmp->mundetected) (void) hideunder(mtmp);
if (u.ustuck == mtmp) {
if(u.uswallow) {
if(!attacktype(mdat,AT_ENGL)) {
usually set mundetected unless monster can't move. */
if (mtmp->mundetected ||
(mtmp->mcanmove && !mtmp->msleeping && rn2(5)))
- mtmp->mundetected = (ptr->mlet != S_EEL) ?
- OBJ_AT(mtmp->mx, mtmp->my) :
- (is_pool(mtmp->mx, mtmp->my) && !Is_waterlevel(&u.uz));
+ (void) hideunder(mtmp);
newsym(mtmp->mx, mtmp->my);
}
if (mtmp->isshk) {
}
if (!u.uswallow) {
- if (!OBJ_AT(u.ux,u.uy)) u.uundetected = 0;
+ if (hides_under(youmonst.data)) (void) hideunder(&youmonst);
- /* position may need updating (invisible hero) */
- if (n_picked) newsym(u.ux,u.uy);
+ /* position may need updating (invisible hero) */
+ if (n_picked) newsym(u.ux,u.uy);
- /* see whether there's anything else here, after auto-pickup is done */
- if (autopickup) check_here(n_picked > 0);
+ /* check if there's anything else here after auto-pickup is done */
+ if (autopickup) check_here(n_picked > 0);
}
return (n_tried > 0);
}
skinback(FALSE);
break_armor();
drop_weapon(1);
- if (hides_under(youmonst.data))
- u.uundetected = OBJ_AT(u.ux, u.uy);
- else if (youmonst.data->mlet == S_EEL)
- u.uundetected = is_pool(u.ux, u.uy);
- else
- u.uundetected = 0;
+ (void) hideunder(&youmonst);
if (u.utraptype == TT_PIT) {
if (could_pass_walls && !Passes_walls) {
u.ux0 = u.ux;
u.uy0 = u.uy;
- if (hides_under(youmonst.data))
- u.uundetected = OBJ_AT(nux, nuy);
- else if (youmonst.data->mlet == S_EEL)
- u.uundetected = is_pool(nux, nuy);
- else {
- u.uundetected = 0;
- /* mimics stop being unnoticed */
- if (youmonst.data->mlet == S_MIMIC)
- youmonst.m_ap_type = M_AP_NOTHING;
+ if (!hideunder(&youmonst) && youmonst.data->mlet == S_MIMIC) {
+ /* mimics stop being unnoticed */
+ youmonst.m_ap_type = M_AP_NOTHING;
}
if (u.uswallow) {