Skip to content

Commit

Permalink
howmonseen - monster visibility (trunk only)
Browse files Browse the repository at this point in the history
     Pull some code out of lookat() so that it can be used elsewhere.
howmonseen(mon) returns a bitmask of the ways that hero can see mon.
  • Loading branch information
nethack.rankin committed May 12, 2007
1 parent b805ba7 commit 24f3e00
Show file tree
Hide file tree
Showing 4 changed files with 103 additions and 79 deletions.
1 change: 1 addition & 0 deletions include/extern.h
Expand Up @@ -2402,6 +2402,7 @@ E void FDECL(unblock_point, (int,int));
E boolean FDECL(clear_path, (int,int,int,int));
E void FDECL(do_clear_area, (int,int,int,
void (*)(int,int,genericptr_t),genericptr_t));
E unsigned FDECL(howmonseen, (struct monst *));

#ifdef VMS

Expand Down
11 changes: 10 additions & 1 deletion include/vision.h
@@ -1,4 +1,4 @@
/* SCCS Id: @(#)vision.h 3.5 1995/01/26 */
/* SCCS Id: @(#)vision.h 3.5 2007/05/11 */
/* Copyright (c) Dean Luick, with acknowledgements to Dave Cohrs, 1990. */
/* NetHack may be freely redistributed. See license for details. */

Expand Down Expand Up @@ -55,4 +55,13 @@ extern char *viz_rmax; /* max could see indices */
/* Use this macro to get a list of distances of the edges (see vision.c). */
#define circle_ptr(z) (&circle_data[(int)circle_start[z]])

/* howmonseen() bitmask values */
#define MONSEEN_NORMAL 0x0001 /* normal vision */
#define MONSEEN_SEEINVIS 0x0002 /* seeing invisible */
#define MONSEEN_INFRAVIS 0x0004 /* via infravision */
#define MONSEEN_TELEPAT 0x0008 /* via telepathy */
#define MONSEEN_XRAYVIS 0x0010 /* via Xray vision */
#define MONSEEN_DETECT 0x0020 /* via extended monster detection */
#define MONSEEN_WARNMON 0x0040 /* via type-specific warning */

#endif /* VISION_H */
130 changes: 53 additions & 77 deletions src/pager.c
@@ -1,4 +1,4 @@
/* SCCS Id: @(#)pager.c 3.5 2006/12/02 */
/* SCCS Id: @(#)pager.c 3.5 2007/05/11 */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/* NetHack may be freely redistributed. See license for details. */

Expand Down Expand Up @@ -123,8 +123,9 @@ lookat(x, y, buf, monbuf)
bhitpos.x = x;
bhitpos.y = y;
mtmp = m_at(x,y);
if (mtmp != (struct monst *) 0) {
if (mtmp) {
char *name, monnambuf[BUFSZ];
unsigned how_seen;
boolean accurate = !Hallucination;

if (mtmp->data == &mons[PM_COYOTE] && accurate)
Expand Down Expand Up @@ -157,83 +158,58 @@ lookat(x, y, buf, monbuf)
an(defsyms[trap_to_defsym(tt)].explanation));
}

{
int ways_seen = 0, normal = 0, xraydist;
boolean useemon = (boolean) canseemon(mtmp);

xraydist = (u.xray_range<0) ? -1 : u.xray_range * u.xray_range;
/* normal vision
* cansee is true for both normal and astral vision,
* but couldsee it not true for astral vision */
if ((mtmp->wormno ? worm_known(mtmp) :
(cansee(mtmp->mx, mtmp->my) && couldsee(mtmp->mx, mtmp->my))) &&
mon_visible(mtmp) && !mtmp->minvis) {
ways_seen++;
normal++;
how_seen = howmonseen(mtmp);
if (how_seen && how_seen != MONSEEN_NORMAL) {
if (how_seen & MONSEEN_NORMAL) {
Strcat(monbuf, "normal vision");
how_seen &= ~MONSEEN_NORMAL;
/* how_seen can't be 0 yet... */
if (how_seen) Strcat(monbuf, ", ");
}
/* see invisible */
if (useemon && mtmp->minvis)
ways_seen++;
/* infravision */
if ((!mtmp->minvis || See_invisible) && see_with_infrared(mtmp))
ways_seen++;
/* telepathy */
if (tp_sensemon(mtmp))
ways_seen++;
/* xray */
if (useemon && xraydist > 0 &&
distu(mtmp->mx, mtmp->my) <= xraydist)
ways_seen++;
if (Detect_monsters)
ways_seen++;
if (MATCH_WARN_OF_MON(mtmp))
ways_seen++;

if (ways_seen > 1 || !normal) {
if (normal) {
Strcat(monbuf, "normal vision");
/* can't actually be 1 yet here */
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (useemon && mtmp->minvis) {
Strcat(monbuf, "see invisible");
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if ((!mtmp->minvis || See_invisible) &&
see_with_infrared(mtmp)) {
Strcat(monbuf, "infravision");
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (tp_sensemon(mtmp)) {
Strcat(monbuf, "telepathy");
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (useemon && xraydist > 0 &&
distu(mtmp->mx, mtmp->my) <= xraydist) {
/* Eyes of the Overworld */
Strcat(monbuf, "astral vision");
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (Detect_monsters) {
Strcat(monbuf, "monster detection");
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (MATCH_WARN_OF_MON(mtmp)) {
char wbuf[BUFSZ];
if (Hallucination)
Strcat(monbuf, "paranoid delusion");
else {
Sprintf(wbuf, "warned of %s",
makeplural(mtmp->data->mname));
Strcat(monbuf, wbuf);
}
if (ways_seen-- > 1) Strcat(monbuf, ", ");
}
if (how_seen & MONSEEN_SEEINVIS) {
Strcat(monbuf, "see invisible");
how_seen &= ~MONSEEN_SEEINVIS;
if (how_seen) Strcat(monbuf, ", ");
}
}
}
}
else if (glyph_is_object(glyph)) {
if (how_seen & MONSEEN_INFRAVIS) {
Strcat(monbuf, "infravision");
how_seen &= ~MONSEEN_INFRAVIS;
if (how_seen) Strcat(monbuf, ", ");
}
if (how_seen & MONSEEN_TELEPAT) {
Strcat(monbuf, "telepathy");
how_seen &= ~MONSEEN_TELEPAT;
if (how_seen) Strcat(monbuf, ", ");
}
if (how_seen & MONSEEN_XRAYVIS) {
/* Eyes of the Overworld */
Strcat(monbuf, "astral vision");
how_seen &= ~MONSEEN_XRAYVIS;
if (how_seen) Strcat(monbuf, ", ");
}
if (how_seen & MONSEEN_DETECT) {
Strcat(monbuf, "monster detection");
how_seen &= ~MONSEEN_DETECT;
if (how_seen) Strcat(monbuf, ", ");
}
if (how_seen & MONSEEN_WARNMON) {
if (Hallucination)
Strcat(monbuf, "paranoid delusion");
else
Sprintf(eos(monbuf), "warned of %s",
makeplural(mtmp->data->mname));
how_seen &= ~MONSEEN_WARNMON;
if (how_seen) Strcat(monbuf, ", ");
}
/* should have used up all the how_seen bits by now */
if (how_seen) {
impossible("lookat: unknown method of seeing monster");
Sprintf(eos(monbuf), "(%u)", how_seen);
}
} /* seen by something other than normal vision */
} /* mtmp */

} else if (glyph_is_object(glyph)) {
struct obj *otmp = vobj_at(x,y);

if (!otmp || otmp->otyp != glyph_to_obj(glyph)) {
Expand Down
40 changes: 39 additions & 1 deletion src/vision.c
@@ -1,4 +1,4 @@
/* SCCS Id: @(#)vision.c 3.5 2005/06/15 */
/* SCCS Id: @(#)vision.c 3.5 2007/05/11 */
/* Copyright (c) Dean Luick, with acknowledgements to Dave Cohrs, 1990. */
/* NetHack may be freely redistributed. See license for details. */

Expand Down Expand Up @@ -2625,4 +2625,42 @@ do_clear_area(scol,srow,range,func,arg)
}
}

/* bitmask indicating ways mon is seen; extracted from lookat(pager.c) */
unsigned
howmonseen(mon)
struct monst *mon;
{
boolean useemon = (boolean)canseemon(mon);
int xraydist = (u.xray_range < 0) ? -1 : (u.xray_range * u.xray_range);
unsigned how_seen = 0; /* result */

/* normal vision;
cansee is true for both normal and astral vision,
but couldsee it not true for astral vision */
if ((mon->wormno ? worm_known(mon) :
(cansee(mon->mx, mon->my) && couldsee(mon->mx, mon->my))) &&
mon_visible(mon) && !mon->minvis)
how_seen |= MONSEEN_NORMAL;
/* see invisible */
if (useemon && mon->minvis)
how_seen |= MONSEEN_SEEINVIS;
/* infravision */
if ((!mon->minvis || See_invisible) && see_with_infrared(mon))
how_seen |= MONSEEN_INFRAVIS;
/* telepathy */
if (tp_sensemon(mon))
how_seen |= MONSEEN_TELEPAT;
/* xray */
if (useemon && xraydist > 0 && distu(mon->mx, mon->my) <= xraydist)
how_seen |= MONSEEN_XRAYVIS;
/* extended detection */
if (Detect_monsters)
how_seen |= MONSEEN_DETECT;
/* class-/type-specific warning */
if (MATCH_WARN_OF_MON(mon))
how_seen |= MONSEEN_WARNMON;

return how_seen;
}

/*vision.c*/

0 comments on commit 24f3e00

Please sign in to comment.