]> granicus.if.org Git - nethack/commitdiff
mon_pmname(), obj_pmname()
authorPatR <rankin@nethack.org>
Sat, 12 Jun 2021 10:07:30 +0000 (03:07 -0700)
committerPatR <rankin@nethack.org>
Sat, 12 Jun 2021 10:07:30 +0000 (03:07 -0700)
Revive some code from 5 or so years ago that's been sitting in a
defunct local git branch.  There are a couple of references to
figurines having gender; the old, unfinished code did already have
support for that, the current code doesn't.  It probably won't take
much effort to add it in but I want to get this first part out of
the way.

Replace some of the
pmname(mon->data, Mgender[mon]) calls with simpler
mon_pmname(mon) and some
pmname(&mons[statue->corpsenm],
   (statue->spe & CORPSTAT_GENDER) == ... ? ... : ...) with simpler
obj_pmname(obj).  There are other instances of them which haven't
been changed but could be.

include/extern.h
src/do_name.c
src/objnam.c
src/trap.c
src/zap.c

index 59b14e6491755e42c061ff73eb020249859ce497..66bcccaaa90ef58fa86c25baf2e28907e9d5fbb1 100644 (file)
@@ -451,6 +451,8 @@ extern const char *lookup_novel(const char *, int *);
 extern int Mgender(struct monst *);
 extern const char *pmname(struct permonst *, int);
 #endif
+extern const char *mon_pmname(struct monst *);
+extern const char *obj_pmname(struct obj *);
 
 /* ### do_wear.c ### */
 
index 64049cde6ae6ebde700809b23a069726de09d96f..9c17550ae12af42303a4d55719337c5ae3709a4e 100644 (file)
@@ -1672,12 +1672,12 @@ rndghostname(void)
  * options works, since those are special cases.
  */
 char *
-x_monnam(register struct monst *mtmp, int article,
+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 = pmname(mdat, Mgender(mtmp));
+    const char *pm_name = mon_pmname(mtmp);
     boolean do_hallu, do_invis, do_it, do_saddle, do_name;
     boolean name_at_start, has_adjectives;
     char *bp;
@@ -2054,7 +2054,7 @@ minimal_monnam(struct monst *mon, boolean ckloc)
     } else {
         Sprintf(outbuf, "%s%s <%d,%d>",
                 mon->mtame ? "tame " : mon->mpeaceful ? "peaceful " : "",
-                pmname(mon->data, Mgender(mon)), mon->mx, mon->my);
+                mon_pmname(mon), mon->mx, mon->my);
         if (mon->cham != NON_PM)
             Sprintf(eos(outbuf), "{%s}",
                     pmname(&mons[mon->cham], Mgender(mon)));
@@ -2080,13 +2080,39 @@ Mgender(struct monst *mtmp)
 const char *
 pmname(struct permonst *pm, int mgender)
 {
-    if ((mgender >= MALE && mgender < NUM_MGENDERS) && pm->pmnames[mgender])
-        return pm->pmnames[mgender];
-    else
-        return pm->pmnames[NEUTRAL];
+    if (mgender < MALE || mgender >= NUM_MGENDERS || !pm->pmnames[mgender])
+        mgender = NEUTRAL;
+    return pm->pmnames[mgender];
 }
 #endif /* PMNAME_MACROS */
 
+/* mons[]->pmname for a monster */
+const char *
+mon_pmname(struct monst *mon)
+{
+    /* for neuter, mon->data->pmnames[MALE] will be Null and use [NEUTRAL] */
+    return pmname(mon->data, mon->female ? FEMALE : MALE);
+}
+
+/* mons[]->pmname for a corpse or statue or figurine */
+const char *
+obj_pmname(struct obj *obj)
+{
+    if (has_omonst(obj))
+        return mon_pmname(OMONST(obj));
+
+    if ((obj->otyp == CORPSE || obj->otyp == STATUE || obj->otyp == FIGURINE)
+        && obj->corpsenm >= LOW_PM) {
+        int cgend = (obj->spe & CORPSTAT_GENDER),
+            mgend = ((cgend == CORPSTAT_MALE) ? MALE
+                     : (cgend == CORPSTAT_FEMALE) ? FEMALE
+                       : NEUTRAL);
+
+        return pmname(&mons[obj->corpsenm], mgend);
+    }
+    return "";
+}
+
 /* fake monsters used to be in a hard-coded array, now in a data file */
 char *
 bogusmon(char *buf, char *code)
index a74786d13ec684f3e9cea96c9ae39b50aae9e3fd..933219ba384651c104d4239282b19755148a84bd 100644 (file)
@@ -11,8 +11,7 @@
 #define NUMOBUF 12
 
 struct _readobjnam_data {
-    char globbuf[BUFSZ];
-    char fruitbuf[BUFSZ];
+    struct obj *otmp;
     char *bp;
     char *origbp;
     char oclass;
@@ -28,7 +27,8 @@ struct _readobjnam_data {
     int tmp, tinv, tvariety, mgend;
     int wetness, gsize;
     int ftype;
-    struct obj *otmp;
+    char globbuf[BUFSZ];
+    char fruitbuf[BUFSZ];
 };
 
 static char *strprepend(char *, const char *);
@@ -515,10 +515,9 @@ xname_flags(
 
         if (typ == FIGURINE && omndx != NON_PM) {
             char anbuf[10]; /* [4] would be enough: 'a','n',' ','\0' */
+            const char *pm_name = mons[omndx].pmnames[NEUTRAL];
 
-            Sprintf(eos(buf), " of %s%s",
-                    just_an(anbuf, mons[omndx].pmnames[NEUTRAL]),
-                    mons[omndx].pmnames[NEUTRAL]);
+            Sprintf(eos(buf), " of %s%s", just_an(anbuf, pm_name), pm_name);
         } else if (is_wet_towel(obj)) {
             if (wizard)
                 Sprintf(eos(buf), " (%d)", obj->spe);
@@ -606,8 +605,7 @@ xname_flags(
     case ROCK_CLASS:
         if (typ == STATUE && omndx != NON_PM) {
             char anbuf[10];
-            int mgend = (((obj->spe & CORPSTAT_GENDER) == CORPSTAT_FEMALE)
-                         ? FEMALE : MALE);
+            const char *statue_pmname = obj_pmname(obj);
 
             Sprintf(buf, "%s%s of %s%s",
                     (Role_if(PM_ARCHEOLOGIST)
@@ -615,8 +613,8 @@ xname_flags(
                     actualn,
                     type_is_pname(&mons[omndx]) ? ""
                       : the_unique_pm(&mons[omndx]) ? "the "
-                        : just_an(anbuf, pmname(&mons[omndx], mgend)),
-                    pmname(&mons[omndx], mgend));
+                        : just_an(anbuf, statue_pmname),
+                    statue_pmname);
         } else
             Strcpy(buf, actualn);
         break;
@@ -1421,12 +1419,7 @@ corpse_xname(
         /* avoid "aligned priest"; it just exposes internal details */
         mnam = "priest";
     } else {
-        int cgend = (otmp->spe & CORPSTAT_GENDER),
-            mgend = (cgend == CORPSTAT_FEMALE) ? FEMALE
-                    : (cgend == CORPSTAT_MALE) ? MALE
-                      : NEUTRAL;
-
-        mnam = pmname(&mons[omndx], mgend);
+        mnam = obj_pmname(otmp);
         if (the_unique_pm(&mons[omndx]) || type_is_pname(&mons[omndx])) {
             mnam = s_suffix(mnam);
             possessive = TRUE;
@@ -3254,8 +3247,9 @@ wizterrainwish(struct _readobjnam_data *d)
 #define SPINACH 2
 
 static void
-readobjnam_init(char* bp, struct _readobjnam_data* d)
+readobjnam_init(char *bp, struct _readobjnam_data *d)
 {
+    d->otmp = (struct obj *) 0;
     d->cnt = d->spe = d->spesgn = d->typ = 0;
     d->very = d->rechrg = d->blessed = d->uncursed = d->iscursed
         = d->ispoisoned = d->isgreased = d->eroded = d->eroded2
@@ -3277,12 +3271,13 @@ readobjnam_init(char* bp, struct _readobjnam_data* d)
     d->bp = d->origbp = bp;
     d->p = (char *) 0;
     d->name = (const char *) 0;
-    d->otmp = (struct obj *) 0;
     d->ftype = g.context.current_fruit;
+    (void) memset(d->globbuf, '\0', sizeof d->globbuf);
+    (void) memset(d->fruitbuf, '\0', sizeof d->globbuf);
 }
 
 static int
-readobjnam_preparse(struct _readobjnam_datad)
+readobjnam_preparse(struct _readobjnam_data *d)
 {
     for (;;) {
         register int l;
@@ -3443,7 +3438,7 @@ readobjnam_preparse(struct _readobjnam_data* d)
 }
 
 static void
-readobjnam_parse_charges(struct _readobjnam_datad)
+readobjnam_parse_charges(struct _readobjnam_data *d)
 {
     if (strlen(d->bp) > 1 && (d->p = rindex(d->bp, '(')) != 0) {
         boolean keeptrailingchars = TRUE;
@@ -3505,7 +3500,7 @@ readobjnam_parse_charges(struct _readobjnam_data* d)
 }
 
 static int
-readobjnam_postparse1(struct _readobjnam_datad)
+readobjnam_postparse1(struct _readobjnam_data *d)
 {
     int i;
 
@@ -3879,7 +3874,7 @@ readobjnam_postparse1(struct _readobjnam_data* d)
 }
 
 static int
-readobjnam_postparse2(struct _readobjnam_datad)
+readobjnam_postparse2(struct _readobjnam_data *d)
 {
     int i;
 
@@ -3940,7 +3935,7 @@ readobjnam_postparse2(struct _readobjnam_data* d)
 }
 
 static int
-readobjnam_postparse3(struct _readobjnam_datad)
+readobjnam_postparse3(struct _readobjnam_data *d)
 {
     int i;
 
@@ -4108,7 +4103,7 @@ readobjnam_postparse3(struct _readobjnam_data* d)
  * return null.
  */
 struct obj *
-readobjnam(char* bp, struct obj* no_wish)
+readobjnam(char *bp, struct obj *no_wish)
 {
     struct _readobjnam_data d;
 
@@ -4281,15 +4276,15 @@ readobjnam(char* bp, struct obj* no_wish)
     if (d.spesgn == -1)
         d.spe = -d.spe;
 
-    /* set otmp->spe.  This may, or may not, use spe... */
+    /* set otmp->spe.  This may, or may not, use d.spe... */
     switch (d.typ) {
     case TIN:
+        d.otmp->spe = 0; /* default: not spinach */
         if (d.contents == EMPTY) {
             d.otmp->corpsenm = NON_PM;
-            d.otmp->spe = 0;
         } else if (d.contents == SPINACH) {
             d.otmp->corpsenm = NON_PM;
-            d.otmp->spe = 1;
+            d.otmp->spe = 1; /* spinach after all */
         }
         break;
     case TOWEL:
@@ -4317,6 +4312,12 @@ readobjnam(char* bp, struct obj* no_wish)
                           : (d.mgend == MALE && !is_female(P)) ? CORPSTAT_MALE
                             /* unspecified or wish conflicts */
                             : CORPSTAT_RANDOM;
+        if (P && d.otmp->spe == CORPSTAT_RANDOM)
+            d.otmp->spe = is_male(P) ? CORPSTAT_MALE
+                          : is_female(P) ? CORPSTAT_FEMALE
+                            : rn2(2) ? CORPSTAT_MALE : CORPSTAT_FEMALE;
+        if (d.ishistoric && d.typ == STATUE)
+            d.otmp->spe |= CORPSTAT_HISTORIC;
         break;
     };
 #ifdef MAIL_STRUCTURES
@@ -4356,7 +4357,6 @@ readobjnam(char* bp, struct obj* no_wish)
 
         switch (d.typ) {
         case TIN:
-            d.otmp->spe = 0; /* No spinach */
             if (dead_species(d.mntmp, FALSE)) {
                 d.otmp->corpsenm = NON_PM; /* it's empty */
             } else if ((!(mons[d.mntmp].geno & G_UNIQ) || wizard)
@@ -4391,7 +4391,6 @@ readobjnam(char* bp, struct obj* no_wish)
             d.otmp->corpsenm = d.mntmp;
             if (Has_contents(d.otmp) && verysmall(&mons[d.mntmp]))
                 delete_contents(d.otmp); /* no spellbook */
-            d.otmp->spe |= d.ishistoric ? CORPSTAT_HISTORIC : 0;
             break;
         case SCALE_MAIL:
             /* Dragon mail - depends on the order of objects & dragons. */
@@ -4582,7 +4581,7 @@ Japanese_item_name(int i)
 }
 
 const char *
-suit_simple_name(struct objsuit)
+suit_simple_name(struct obj *suit)
 {
     const char *suitnm, *esuitp;
 
@@ -4603,7 +4602,7 @@ suit_simple_name(struct obj* suit)
 }
 
 const char *
-cloak_simple_name(struct objcloak)
+cloak_simple_name(struct obj *cloak)
 {
     if (cloak) {
         switch (cloak->otyp) {
@@ -4624,7 +4623,7 @@ cloak_simple_name(struct obj* cloak)
 
 /* helm vs hat for messages */
 const char *
-helm_simple_name(struct objhelmet)
+helm_simple_name(struct obj *helmet)
 {
     /*
      *  There is some wiggle room here; the result has been chosen
@@ -4643,7 +4642,7 @@ helm_simple_name(struct obj* helmet)
 
 /* gloves vs gauntlets; depends upon discovery state */
 const char *
-gloves_simple_name(struct objgloves)
+gloves_simple_name(struct obj *gloves)
 {
     static const char gauntlets[] = "gauntlets";
 
@@ -4662,7 +4661,7 @@ gloves_simple_name(struct obj* gloves)
 
 /* boots vs shoes; depends upon discovery state */
 const char *
-boots_simple_name(struct objboots)
+boots_simple_name(struct obj *boots)
 {
     static const char shoes[] = "shoes";
 
@@ -4681,7 +4680,7 @@ boots_simple_name(struct obj* boots)
 
 /* simplified shield for messages */
 const char *
-shield_simple_name(struct objshield)
+shield_simple_name(struct obj *shield)
 {
     if (shield) {
         /* xname() describes unknown (unseen) reflection as smooth */
@@ -4711,13 +4710,13 @@ shield_simple_name(struct obj* shield)
 
 /* for completness */
 const char *
-shirt_simple_name(struct objshirt UNUSED)
+shirt_simple_name(struct obj *shirt UNUSED)
 {
     return "shirt";
 }
 
 const char *
-mimic_obj_name(struct monstmtmp)
+mimic_obj_name(struct monst *mtmp)
 {
     if (M_AP_TYPE(mtmp) == M_AP_OBJECT) {
         if (mtmp->mappearance == GOLD_PIECE)
index a859fef2e35fcea78dc62eba4e9f864a67ae5d3f..c4e56225df4584d26d2cb35c6859bd497a9c4cd9 100644 (file)
@@ -3162,13 +3162,13 @@ void
 selftouch(const char *arg)
 {
     char kbuf[BUFSZ];
+    const char *corpse_pmname;
 
     if (uwep && uwep->otyp == CORPSE && touch_petrifies(&mons[uwep->corpsenm])
         && !Stone_resistance) {
-        pline("%s touch the %s corpse.", arg,
-              mons[uwep->corpsenm].pmnames[NEUTRAL]);
-        Sprintf(kbuf, "%s corpse",
-              an(mons[uwep->corpsenm].pmnames[NEUTRAL]));
+        corpse_pmname = obj_pmname(uwep);
+        pline("%s touch the %s corpse.", arg, corpse_pmname);
+        Sprintf(kbuf, "%s corpse", an(corpse_pmname));
         instapetrify(kbuf);
         /* life-saved; unwield the corpse if we can't handle it */
         if (!uarmg && !Stone_resistance)
@@ -3178,10 +3178,9 @@ selftouch(const char *arg)
        allow two-weapon combat when either weapon is a corpse] */
     if (u.twoweap && uswapwep && uswapwep->otyp == CORPSE
         && touch_petrifies(&mons[uswapwep->corpsenm]) && !Stone_resistance) {
-        pline("%s touch the %s corpse.", arg,
-              mons[uswapwep->corpsenm].pmnames[NEUTRAL]);
-        Sprintf(kbuf, "%s corpse",
-                an(mons[uswapwep->corpsenm].pmnames[NEUTRAL]));
+        corpse_pmname = obj_pmname(uswapwep);
+        pline("%s touch the %s corpse.", arg, corpse_pmname);
+        Sprintf(kbuf, "%s corpse", an(corpse_pmname));
         instapetrify(kbuf);
         /* life-saved; unwield the corpse */
         if (!uarmg && !Stone_resistance)
@@ -4715,17 +4714,17 @@ help_monster_out(
 
     /* is it a cockatrice?... */
     if (touch_petrifies(mtmp->data) && !uarmg && !Stone_resistance) {
+        const char *mtmp_pmname = mon_pmname(mtmp);
+
         You("grab the trapped %s using your bare %s.",
-            pmname(mtmp->data, Mgender(mtmp)),
-            makeplural(body_part(HAND)));
+            mtmp_pmname, makeplural(body_part(HAND)));
 
         if (poly_when_stoned(g.youmonst.data) && polymon(PM_STONE_GOLEM)) {
             display_nhwindow(WIN_MESSAGE, FALSE);
         } else {
             char kbuf[BUFSZ];
 
-            Sprintf(kbuf, "trying to help %s out of a pit",
-                    an(pmname(mtmp->data, Mgender(mtmp))));
+            Sprintf(kbuf, "trying to help %s out of a pit", an(mtmp_pmname));
             instapetrify(kbuf);
             return 1;
         }
index e78cb529fcee2ff3f05f462fb5cf0bf875d37611..0a0114de12409b4afdb2e3a0024231843266040e 100644 (file)
--- a/src/zap.c
+++ b/src/zap.c
@@ -1052,8 +1052,7 @@ unturn_dead(struct monst *mon)
                 pline("%s%s suddenly %s%s%s!", owner, corpse,
                       nonliving(mtmp2->data) ? "reanimates" : "comes alive",
                       different_type ? " as " : "",
-                      different_type ? an(pmname(mtmp2->data, Mgender(mtmp2)))
-                                     : "");
+                      different_type ? an(mon_pmname(mtmp2)) : "");
             else if (canseemon(mtmp2))
                 pline("%s suddenly appears!", Amonnam(mtmp2));
         } else {