overrode use of the name
some actions such as eating corpses off the floor didn't check whether hero
could reach the bottom of a pit
+usmellmon() instead of "It turns into it" during monster polymorph
Platform- and/or Interface-Specific Fixes
#endif
E void FDECL(bagotricks, (struct obj *));
E boolean FDECL(propagate, (int, BOOLEAN_P,BOOLEAN_P));
+E boolean FDECL(usmellmon, (struct permonst *));
/* ### mapglyph.c ### */
E const char *FDECL(stagger, (const struct permonst *,const char *));
E const char *FDECL(on_fire, (struct permonst *,struct attack *));
E const struct permonst *FDECL(raceptr, (struct monst *));
+E boolean FDECL(olfaction, (struct permonst *));
/* ### monmove.c ### */
STATIC_PTR int NDECL(wiz_level_change);
STATIC_PTR int NDECL(wiz_show_seenv);
STATIC_PTR int NDECL(wiz_show_vision);
+STATIC_PTR int NDECL(wiz_smell);
STATIC_PTR int NDECL(wiz_mon_polycontrol);
STATIC_PTR int NDECL(wiz_show_wmodes);
#if defined(__BORLANDC__) && !defined(_WIN32)
return 0;
}
+/* #wizsmell command - test usmellmon(). */
+STATIC_PTR int
+wiz_smell()
+{
+ char out_str[BUFSZ];
+ const char *firstmatch = 0;
+ struct permonst *pm = 0;
+ int ans = 0;
+ int mndx; /* monster index */
+ int found; /* count of matching mndxs found */
+ coord cc; /* screen pos of unknown glyph */
+ int glyph; /* glyph at selected position */
+
+ cc.x = u.ux;
+ cc.y = u.uy;
+ mndx = 0; /* gcc -Wall lint */
+ if (!olfaction(youmonst.data)) {
+ You("are incapable of detecting odors in your present form.");
+ return 0;
+ }
+
+ pline("You can move the cursor to a monster that you want to smell.");
+ do {
+ /* Reset some variables. */
+ pm = (struct permonst *)0;
+ found = 0;
+ out_str[0] = '\0';
+
+ pline("Pick a monster to smell.");
+ ans = getpos(&cc, TRUE, "a monster");
+ if (ans < 0 || cc.x < 0) {
+ return 0; /* done */
+ }
+ /* Convert the glyph at the selected position to a mndxbol. */
+ glyph = glyph_at(cc.x,cc.y);
+ if (glyph_is_monster(glyph))
+ mndx = glyph_to_mon(glyph);
+ else
+ mndx = 0;
+ /* Is it a monster? */
+ if (mndx) {
+ if (!usmellmon(&mons[mndx]))
+ pline("That monster seems to give off no smell.");
+ } else pline("That is not a monster.");
+ } while (TRUE);
+ return 0;
+}
#endif /* WIZARD */
{(char *)0, (char *)0, donull, TRUE},
{(char *)0, (char *)0, donull, TRUE},
{(char *)0, (char *)0, donull, TRUE},
+ {(char *)0, (char *)0, donull, TRUE},
#ifdef DEBUG
{(char *)0, (char *)0, donull, TRUE},
#endif
{"stats", "show memory statistics", wiz_show_stats, TRUE},
{"timeout", "look at timeout queue", wiz_timeout_queue, TRUE},
{"vision", "show vision array", wiz_show_vision, TRUE},
+ {"wizsmell", "smell monster", wiz_smell, TRUE},
#ifdef DEBUG
{"wizdebug", "wizard debug command", wiz_debug_cmd, TRUE},
#endif
int mhp, hpn, hpd;
int mndx, tryct;
struct permonst *olddata = mtmp->data;
- char oldname[BUFSZ];
+ char oldname[BUFSZ], newname[BUFSZ];
if (msg) {
/* like Monnam() but never mention saddle */
if (msg) {
uchar save_mnamelth = mtmp->mnamelth;
mtmp->mnamelth = 0;
- pline("%s turns into %s!", oldname,
- mdat == &mons[PM_GREEN_SLIME] ? "slime" :
- x_monnam(mtmp, ARTICLE_A, (char*)0, SUPPRESS_SADDLE, FALSE));
+ Strcpy(newname,
+ (mdat == &mons[PM_GREEN_SLIME]) ? "slime" :
+ x_monnam(mtmp, ARTICLE_A, (char *)0,SUPPRESS_SADDLE, FALSE));
+ if (!strcmpi(oldname,"it") && !strcmpi(newname,"it"))
+ (void) usmellmon(mdat);
+ else
+ pline("%s turns into %s!", oldname, newname);
mtmp->mnamelth = save_mnamelth;
}
}
}
+boolean
+usmellmon(mdat)
+struct permonst *mdat;
+{
+ int mndx;
+ boolean nonspecific = FALSE;
+ boolean msg_given = FALSE;
+
+ if (mdat) {
+ if (!olfaction(youmonst.data)) return FALSE;
+ mndx = monsndx(mdat);
+ switch (mndx) {
+ case PM_MINOTAUR:
+ You("notice a bovine smell.");
+ msg_given = TRUE;
+ break;
+ case PM_CAVEMAN:
+ case PM_CAVEWOMAN:
+ case PM_BARBARIAN:
+ case PM_NEANDERTHAL:
+ You("smell body odor.");
+ msg_given = TRUE;
+ break;
+/*
+ case PM_PESTILENCE:
+ case PM_FAMINE:
+ case PM_DEATH:
+ break;
+*/
+ case PM_HORNED_DEVIL:
+ case PM_BALROG:
+ case PM_ASMODEUS:
+ case PM_DISPATER:
+ case PM_YEENOGHU:
+ case PM_ORCUS:
+ break;
+ case PM_HUMAN_WEREJACKAL:
+ case PM_HUMAN_WERERAT:
+ case PM_HUMAN_WEREWOLF:
+ case PM_WEREJACKAL:
+ case PM_WERERAT:
+ case PM_WEREWOLF:
+ case PM_OWLBEAR:
+ You("detect an odor reminiscent of an animal's den.");
+ msg_given = TRUE;
+ break;
+/*
+ case PM_PURPLE_WORM:
+ break;
+*/
+ case PM_STEAM_VORTEX:
+ You("smell steam.");
+ msg_given = TRUE;
+ break;
+ case PM_GREEN_SLIME:
+ pline("%s stinks.", Something);
+ msg_given = TRUE;
+ break;
+ case PM_VIOLET_FUNGUS:
+ case PM_SHRIEKER:
+ You("smell mushrooms.");
+ msg_given = TRUE;
+ break;
+ /* These are here to avoid triggering the
+ nonspecific treatment through the default case below*/
+ case PM_WHITE_UNICORN:
+ case PM_GRAY_UNICORN:
+ case PM_BLACK_UNICORN:
+ case PM_JELLYFISH:
+ break;
+ default:
+ nonspecific = TRUE;
+ break;
+ }
+
+ if (nonspecific) switch(mdat->mlet) {
+ case S_DOG:
+ You("notice a dog smell.");
+ msg_given = TRUE;
+ break;
+ case S_DRAGON:
+ You("smell a dragon!");
+ msg_given = TRUE;
+ break;
+ case S_FUNGUS:
+ pline("%s smells moldy.", Something);
+ msg_given = TRUE;
+ break;
+ case S_UNICORN:
+ You("detect a%s odor reminiscent of a stable.",
+ (mndx == PM_PONY) ? "n" : " strong");
+ msg_given = TRUE;
+ break;
+ case S_ZOMBIE:
+ You("smell rotting flesh.");
+ msg_given = TRUE;
+ break;
+ case S_EEL:
+ You("smell fish.");
+ msg_given = TRUE;
+ break;
+ case S_ORC:
+ if (maybe_polyd(is_orc(youmonst.data), Race_if(PM_ORC)))
+ You("notice an attractive smell.");
+ else
+ pline(
+ "A foul stench makes you feel a little nauseated.");
+ msg_given = TRUE;
+ break;
+ default:
+ break;
+ }
+ }
+ return (msg_given) ? TRUE : FALSE;
+}
+
/*mon.c*/
return what;
}
+/*
+ * Returns:
+ * TRUE if monster is presumed to have a sense of smell.
+ * FALSE if monster definitely does not have a sense of smell.
+ *
+ * Do not base this on presence of a head or nose, since many
+ * creatures sense smells other ways (feelers, forked-tongues, etc.)
+ * We're assuming all insects can smell at a distance too.
+ */
+boolean
+olfaction(mdat)
+struct permonst *mdat;
+{
+ if (mdat && (is_golem(mdat) ||
+ mdat->mlet == S_EYE || /* spheres */
+ mdat->mlet == S_JELLY ||
+ mdat->mlet == S_PUDDING ||
+ mdat->mlet == S_BLOB ||
+ mdat->mlet == S_VORTEX ||
+ mdat->mlet == S_ELEMENTAL ||
+ mdat->mlet == S_FUNGUS || /* mushrooms and fungi */
+ mdat->mlet == S_LIGHT))
+ return FALSE;
+ return TRUE;
+}
+
/*mondata.c*/