void angry_priest(void) { struct monst *priest; struct rm *loc; if ((priest = findpriest(temple_occupied(u.urooms))) != 0) { wakeup(priest, FALSE); /* * If the altar has been destroyed or converted, let the * priest run loose. * (When it's just a conversion and there happens to be * a fresh corpse nearby, the priest ought to have an * opportunity to try converting it back; maybe someday...) */ loc = &level->locations [CONST_EPRI(priest)->shrpos.x][CONST_EPRI(priest)->shrpos.y]; if (!IS_ALTAR(loc->typ) || ((aligntyp) Amask2align(loc->altarmask & AM_MASK) != CONST_EPRI(priest)->shralign)) { priest->ispriest = 0; /* now a roamer */ priest->isminion = 1; /* but still aligned */ /* this overloads the `shroom' field, which is now clobbered */ EPRI(priest)->renegade = 0; } } }
static void describe_bg(int x, int y, int bg, char *buf) { if (!bg) return; switch(bg) { case S_altar: if (!In_endgame(&u.uz)) sprintf(buf, "%s altar", align_str(Amask2align(level->locations[x][y].altarmask & ~AM_SHRINE))); else sprintf(buf, "aligned altar"); break; case S_ndoor: if (is_drawbridge_wall(x, y) >= 0) strcpy(buf,"open drawbridge portcullis"); else if ((level->locations[x][y].doormask & ~D_TRAPPED) == D_BROKEN) strcpy(buf,"broken door"); else strcpy(buf,"doorway"); break; case S_cloud: strcpy(buf, Is_airlevel(&u.uz) ? "cloudy area" : "fog/vapor cloud"); break; default: strcpy(buf, defexplain[bg]); break; } }
static xchar has_shrine(const struct monst *pri) { struct rm *loc; if (!pri) return FALSE; loc = &level->locations [CONST_EPRI(pri)->shrpos.x][CONST_EPRI(pri)->shrpos.y]; if (!IS_ALTAR(loc->typ)) return FALSE; return (CONST_EPRI(pri)->shralign == Amask2align(loc->altarmask & AM_MASK)) ? loc->altarmask & (AM_SHRINE | AM_SANCTUM) : 0; }
/* exclusively for mktemple(); uses level creation RNG */ void priestini(struct level *lev, struct mkroom *sroom, int sx, int sy, boolean sanctum) { /* is it the seat of the high priest? */ struct monst *priest = NULL; struct obj *otmp; int cnt; coord *priest_pos, pos_array[] = { { sx + 1, sy }, { sx - 1, sy }, { sx, sy + 1 }, { sx, sy - 1 }, { sx, sy }, { COLNO, ROWNO }, }; /* Search for a good position for the priest. The -1 in the array bound is * to ensure that we stop on the { COLNO, ROWNO } entry which is not ok. Do * not pass a monster to goodpos(), because we will move any monster later. */ for (priest_pos = pos_array; !goodpos(lev, priest_pos->x, priest_pos->y, NULL, 0) && (priest_pos < pos_array + ARRAY_SIZE(pos_array) - 1); ++priest_pos) {} if (!isok(priest_pos->x, priest_pos->y)) { impossible("Unable to find location for priest in shrine"); } else { if (MON_AT(lev, priest_pos->x, priest_pos->y)) rloc(m_at(lev, priest_pos->x, priest_pos->y), FALSE); priest = makemon(&mons[sanctum ? PM_HIGH_PRIEST : PM_ALIGNED_PRIEST], lev, priest_pos->x, priest_pos->y, MM_ALLLEVRNG); } if (priest) { EPRI(priest)->shroom = (sroom - lev->rooms) + ROOMOFFSET; EPRI(priest)->shralign = Amask2align(lev->locations[sx][sy].altarmask); EPRI(priest)->shrpos.x = sx; EPRI(priest)->shrpos.y = sy; assign_level(&(EPRI(priest)->shrlevel), &lev->z); priest->mtrapseen = ~0; /* traps are known */ priest->mpeaceful = 1; priest->ispriest = 1; priest->msleeping = 0; set_malign(priest); /* mpeaceful may have changed */ /* now his/her goodies... */ if (sanctum && CONST_EPRI(priest)->shralign == A_NONE && on_level(&sanctum_level, &lev->z)) { mongets(priest, AMULET_OF_YENDOR, rng_for_level(&lev->z)); } /* 2 to 4 spellbooks */ for (cnt = rn1(3, 2); cnt > 0; --cnt) { mpickobj(priest, mkobj(level, SPBOOK_CLASS, FALSE, rng_for_level(&lev->z))); } /* robe [via makemon()] */ if (mklev_rn2(2, lev) && (otmp = which_armor(priest, os_armc)) != 0) { if (p_coaligned(priest)) uncurse(otmp); else curse(otmp); } } }