monster name formatting

While testing monster summoning by using a debugger to force the
outcome, I saw "the renegade Angel of <foo> appears in a cloud of
smoke" as if only one such creature existed.  Trying to change
that to "a renegate Angel" pointed out some problems:  type names
like Angel, Green-elf, and Uruk-hai fool an() into using "the"
because of their capital letter.  Fixing that was a bit of a hack
and worked for Green-elf and Uruk-hai but not for Angel because
it has the eminion extension so uses priestname() instead of the
guts of x_monnam().  Fixing that involved more hackery and now I
feel unclean, but it seems to be working.

It wasn't as noticeable as it might have been because most of the
time that "the Angel of <foo>" or "the priest of <bar>" was shown,
the caller is requesting "the" rather than "a/an".
This commit is contained in:
PatR
2021-06-21 17:44:35 -07:00
parent 3af1cc79e6
commit fa7980c585
4 changed files with 58 additions and 19 deletions

View File

@@ -1,4 +1,4 @@
NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.573 $ $NHDT-Date: 1624053070 2021/06/18 21:51:10 $
NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.575 $ $NHDT-Date: 1624322667 2021/06/22 00:44:27 $
General Fixes and Modified Features
-----------------------------------
@@ -547,6 +547,8 @@ using a bullwhip to snatch a wielded cockatrice corpse from a monster when not
panic during final cleanup
make fire-command autowield an appropriate launcher and add fireassist boolean
option to toggle the assistance off
Angels and priests were always described as "the {Angel,priest,high priest} of
<deity>" when first two should have been "{an Angel,a high priest}..."
Fixes to 3.7.0-x Problems that Were Exposed Via git Repository

View File

@@ -1,4 +1,4 @@
/* NetHack 3.7 extern.h $NHDT-Date: 1624232719 2021/06/20 23:45:19 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.983 $ */
/* NetHack 3.7 extern.h $NHDT-Date: 1624322668 2021/06/22 00:44:28 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.984 $ */
/* Copyright (c) Steve Creps, 1988. */
/* NetHack may be freely redistributed. See license for details. */
@@ -2054,7 +2054,7 @@ extern boolean inhistemple(struct monst *);
extern int pri_move(struct monst *);
extern void priestini(d_level *, struct mkroom *, int, int, boolean);
extern aligntyp mon_aligntyp(struct monst *);
extern char *priestname(struct monst *, char *);
extern char *priestname(struct monst *, int, char *);
extern boolean p_coaligned(struct monst *);
extern struct monst *findpriest(char);
extern void intemple(int);

View File

@@ -1,4 +1,4 @@
/* NetHack 3.7 do_name.c $NHDT-Date: 1623878512 2021/06/16 21:21:52 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.207 $ */
/* NetHack 3.7 do_name.c $NHDT-Date: 1624322669 2021/06/22 00:44:29 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.208 $ */
/* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
/*-Copyright (c) Pasi Kallinen, 2018. */
/* NetHack may be freely redistributed. See license for details. */
@@ -1672,14 +1672,19 @@ rndghostname(void)
* options works, since those are special cases.
*/
char *
x_monnam(struct monst *mtmp, int article,
const char *adjective, int suppress, boolean called)
x_monnam(
struct monst *mtmp,
int article,
const char *adjective,
int suppress,
boolean called)
{
char *buf = nextmbuf();
struct permonst *mdat = mtmp->data;
const char *pm_name = mon_pmname(mtmp);
boolean do_hallu, do_invis, do_it, do_saddle, do_name;
boolean name_at_start, has_adjectives;
boolean name_at_start, has_adjectives,
falseCap = (*pm_name != lowc(*pm_name));
char *bp;
if (g.program_state.gameover)
@@ -1715,7 +1720,7 @@ x_monnam(struct monst *mtmp, int article,
EHalluc_resistance = 1L;
if (!do_invis)
mtmp->minvis = 0;
name = priestname(mtmp, priestnambuf);
name = priestname(mtmp, article, priestnambuf);
EHalluc_resistance = save_prop;
mtmp->minvis = save_invis;
if (article == ARTICLE_NONE && !strncmp(name, "the ", 4))
@@ -1815,11 +1820,21 @@ x_monnam(struct monst *mtmp, int article,
article = ARTICLE_THE;
else
article = ARTICLE_NONE;
} else if ((mdat->geno & G_UNIQ) && article == ARTICLE_A) {
} else if ((mdat->geno & G_UNIQ) != 0 && article == ARTICLE_A) {
article = ARTICLE_THE;
}
{
if (article == ARTICLE_A && falseCap && !name_at_start) {
char buf2[BUFSZ], buf3[BUFSZ];
/* some type names like "Archon", "Green-elf", and "Uruk-hai" fool
an() because of the capitalization and would result in "the " */
Strcpy(buf3, buf);
*buf3 = lowc(*buf3);
(void) just_an(buf2, buf3);
Strcat(buf2, buf);
return strcpy(buf, buf2);
} else {
char buf2[BUFSZ];
switch (article) {

View File

@@ -1,4 +1,4 @@
/* NetHack 3.7 priest.c $NHDT-Date: 1597931337 2020/08/20 13:48:57 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.63 $ */
/* NetHack 3.7 priest.c $NHDT-Date: 1624322670 2021/06/22 00:44:30 $ $NHDT-Branch: NetHack-3.7 $:$NHDT-Revision: 1.70 $ */
/* Copyright (c) Izchak Miller, Steve Linhart, 1989. */
/* NetHack may be freely redistributed. See license for details. */
@@ -291,26 +291,48 @@ mon_aligntyp(struct monst *mon)
* the true name even when under that influence
*/
char *
priestname(struct monst *mon,
char *pname) /* caller-supplied output buffer */
priestname(
struct monst *mon,
int article,
char *pname) /* caller-supplied output buffer */
{
boolean do_hallu = Hallucination,
aligned_priest = mon->data == &mons[PM_ALIGNED_CLERIC],
high_priest = mon->data == &mons[PM_HIGH_CLERIC];
char whatcode = '\0';
const char *what = do_hallu ? rndmonnam(&whatcode)
: pmname(mon->data, Mgender(mon));
const char *what = do_hallu ? rndmonnam(&whatcode) : mon_pmname(mon);
if (!mon->ispriest && !mon->isminion) /* should never happen... */
return strcpy(pname, what); /* caller must be confused */
*pname = '\0';
if (!do_hallu || !bogon_is_pname(whatcode))
Strcat(pname, "the ");
if (mon->minvis)
if (article != ARTICLE_NONE && (!do_hallu || !bogon_is_pname(whatcode))) {
if (article == ARTICLE_YOUR || (article == ARTICLE_A && high_priest))
article = ARTICLE_THE;
if (article == ARTICLE_THE) {
Strcat(pname, "the ");
} else {
char buf2[BUFSZ];
/* don't let "Angel of <foo>" fool an() into using "the " */
Strcpy(buf2, pname);
*buf2 = lowc(*buf2);
(void) just_an(pname, buf2);
}
}
/* pname[] contains "" or {"a ","an ","the "} */
if (mon->minvis) {
/* avoid "a invisible priest" */
if (!strcmp(pname, "a "))
Strcpy(pname, "an ");
Strcat(pname, "invisible ");
if (mon->isminion && EMIN(mon)->renegade)
}
if (mon->isminion && EMIN(mon)->renegade) {
/* avoid "an renegade Angel" */
if (!strcmp(pname, "an ")) /* will fail for "an invisible " */
Strcpy(pname, "a ");
Strcat(pname, "renegade ");
}
if (mon->ispriest || aligned_priest) { /* high_priest implies ispriest */
if (!aligned_priest && !high_priest) {