From 389f03e90e1e58e78d5ab2f6df7def7274bd3111 Mon Sep 17 00:00:00 2001 From: PatR Date: Fri, 17 Nov 2023 17:36:04 -0800 Subject: [PATCH] farlook of engravings Report headstone engraving when using farlook to examine a grave: | a grave (grave whose headstone reads: "foo") or | a grave (grave whose headstone you haven't read) Make the farlook of ordinary engravings operate more like farlook of other things: | a boulder or a statue or an engraving (engraving with text: "bar") rather than | a boulder or a statue or an engraving with text: "bar" The "or a statue" phrase will now be suppressed because statues aren't shown as backtick anymore, so the parenthesized form isn't quite as long as it would otherwise have been. If OPTIONS=boulder:symbol is in use, the "a boulder" part will be gone too. | an engraving (engraving with text: "bar") or | an engraving (engraving that you haven't read) Make quicklook include engraving text. It's quick because it doesn't ask the player to pick additional spots or whether to look up relevant data.base quote, not because it skimps on useful information. Autodescribe still does not include engraving text. --- doc/fixes3-7-0.txt | 1 + src/pager.c | 112 ++++++++++++++++++++++++++------------------- 2 files changed, 65 insertions(+), 48 deletions(-) diff --git a/doc/fixes3-7-0.txt b/doc/fixes3-7-0.txt index 5a5198b5a..c3bece5cb 100644 --- a/doc/fixes3-7-0.txt +++ b/doc/fixes3-7-0.txt @@ -2337,6 +2337,7 @@ allow #dip potions into a sink to get a hint about what they are, similar to dropping rings into a sink; dipping other stuff causes water damage so could be used to blank out scrolls and books when restoring, show current level's player-applied annotation if there is one +have farlook of a grave report the engraving on the headstone if it's known Platform- and/or Interface-Specific New Features diff --git a/src/pager.c b/src/pager.c index d9164f668..03412c6a6 100644 --- a/src/pager.c +++ b/src/pager.c @@ -1122,6 +1122,9 @@ add_cmap_descr( /* thawing ice ("solid ice", "thin ice", &c) */ || ((p = strchr(x_str, ' ')) != 0 && !strcmpi(p, " ice")) ); + } else if (idx == S_engroom || idx == S_engrcorr) { + x_str = "engraving"; + article = 1; } if (!found) { @@ -1265,22 +1268,46 @@ do_screen_description( /* Now check for objects */ if (!iflags.terrainmode || (iflags.terrainmode & TER_OBJ) != 0) { + /* need a static buffer in case it gets returned as *firstmatch */ + static char oc_buf[40]; /* does not need to be in 'struct g' */ + nhsym bouldersym; + + j = SYM_BOULDER + SYM_OFF_X; + bouldersym = Is_rogue_level(&u.uz) ? go.ov_rogue_syms[j] + : go.ov_primary_syms[j]; + if (!bouldersym) + bouldersym = def_oc_syms[ROCK_CLASS].sym; + for (i = 1; i < MAXOCLASSES; i++) { if (sym == (looked ? gs.showsyms[i + SYM_OFF_O] : def_oc_syms[i].sym) - || (looked && i == ROCK_CLASS && glyph_is_statue(glyph))) { + || (i == ROCK_CLASS && (glyph_is_statue(glyph) + || sym == bouldersym))) { + Strcpy(oc_buf, def_oc_syms[i].explain); + /* ROCK_CLASS is complicated; statues are displayed as the + monster they depict rather than as S_rock; boulders might + be displayed as a custom symbol rather than as S_rock; + for added fun, engravings are shown with the same symbol + as S_rock which is why we want to shorten this */ + if (i == ROCK_CLASS && !strcmp(oc_buf, "boulder or statue")) { + if (sym == bouldersym) + Strcpy(oc_buf, "boulder"); /* discard "or statue" */ + else if (glyph_is_statue(glyph)) + Strcpy(oc_buf, "statue"); /* discard "boulder or" */ + else if (looked) + continue; /* discard both */ + } need_to_look = TRUE; if (looked && i == VENOM_CLASS) { skipped_venom++; continue; } if (!found) { - Sprintf(out_str, "%s%s", - prefix, an(def_oc_syms[i].explain)); - *firstmatch = def_oc_syms[i].explain; + Sprintf(out_str, "%s%s", prefix, an(oc_buf)); + *firstmatch = oc_buf; found++; } else { - found += append_str(out_str, an(def_oc_syms[i].explain)); + found += append_str(out_str, an(oc_buf)); } } } @@ -1336,10 +1363,13 @@ do_screen_description( * places were swapped. */ alt_i = ((i != S_water && i != S_lava) ? i /* as-is */ - : (S_water + S_lava) - i); /* swap water and lava */ + : (S_water + S_lava - i)); /* swap water and lava */ x_str = defsyms[alt_i].explanation; - if (!*x_str) /* cmap includes beams, shield effects, swallow +*/ - continue; /*+ boundaries, and explosions; skip all of those */ + /* cmap includes beams, shield effects, swallow boundaries, and + explosions; skip all of those */ + if (!*x_str) + continue; + if (sym == (looked ? gs.showsyms[alt_i] : defsyms[alt_i].sym)) { int article; /* article==2 => "the", 1 => "an", 0 => (none) */ @@ -1354,11 +1384,6 @@ do_screen_description( || strcmp(x_str, "air") == 0 || strcmp(x_str, "land") == 0); - if (alt_i == S_engroom || alt_i == S_engrcorr) { - article = 1; - x_str = "engraving"; - need_to_look = TRUE; - } found = add_cmap_descr(found, alt_i, glyph, article, cc, x_str, prefix, &hit_trap, firstmatch, out_str); @@ -1375,7 +1400,9 @@ do_screen_description( if (alt_i == S_altar || is_cmap_trap(alt_i) || (hallucinate && (alt_i == S_water /* S_pool already done */ - || alt_i == S_lava || alt_i == S_ice))) + || alt_i == S_lava || alt_i == S_ice)) + || alt_i == S_engroom || alt_i == S_engrcorr + || alt_i == S_grave) /* 'need_to_look' to report engraving */ need_to_look = TRUE; } } @@ -1413,12 +1440,13 @@ do_screen_description( /* Finally, handle some optional overriding symbols */ for (j = SYM_OFF_X; j < SYM_MAX; ++j) { - if (j == (SYM_INVISIBLE + SYM_OFF_X)) + if (j == SYM_INVISIBLE + SYM_OFF_X || j == SYM_BOULDER + SYM_OFF_X) continue; /* already handled above */ tmpsym = Is_rogue_level(&u.uz) ? go.ov_rogue_syms[j] : go.ov_primary_syms[j]; if (tmpsym && sym == tmpsym) { switch (j) { +#if 0 case SYM_BOULDER + SYM_OFF_X: { static const char boulder[] = "boulder"; @@ -1431,6 +1459,7 @@ do_screen_description( } break; } +#endif case SYM_PET_OVERRIDE + SYM_OFF_X: if (looked) { /* convert to symbol without override in effect */ @@ -1446,19 +1475,6 @@ do_screen_description( } } } -#if 0 - /* handle optional boulder symbol as a special case */ - if (o_syms[SYM_BOULDER + SYM_OFF_X] - && sym == o_syms[SYM_BOULDER + SYM_OFF_X]) { - if (!found) { - *firstmatch = "boulder"; - Sprintf(out_str, "%s%s", prefix, an(*firstmatch)); - found++; - } else { - found += append_str(out_str, "boulder"); - } - } -#endif /* * If we are looking at the screen, follow multiple possibilities or @@ -1488,11 +1504,11 @@ do_screen_description( if (look_buf[0] != '\0') *firstmatch = look_buf; if (*(*firstmatch)) { - if (strncmp(look_buf, "engraving", 9) != 0) { - Snprintf(temp_buf, sizeof temp_buf, " (%s)", *firstmatch); - (void) strncat(out_str, temp_buf, - BUFSZ - strlen(out_str) - 1); - } + Sprintf(temp_buf, " (%s", *firstmatch); + (void) add_quoted_engraving(cc.x, cc.y, temp_buf); + Strcat(temp_buf, ")"); + (void) strncat(out_str, temp_buf, + BUFSZ - strlen(out_str) - 1); found = 1; /* we have something to look up */ } if (monbuf[0]) { @@ -1513,14 +1529,26 @@ add_quoted_engraving(coordxy x, coordxy y, char *buf) struct engr *ep = engr_at(x, y); if (ep) { +#define GRAVESTONE "(grave" + /* is a grave's headstone if buf ends with "(grave"; + caller will add closing ")" after we return; + -1: sizeof for a literal string includes the terminating '\0' */ + boolean is_headstone = (IS_GRAVE(levl[x][y].typ) + && strlen(buf) >= (sizeof GRAVESTONE - 1) + && !strcmp(eos(buf) - (sizeof GRAVESTONE - 1), + GRAVESTONE)); + if (ep->eread) - Snprintf(temp_buf, sizeof temp_buf, - " with remembered text: \"%s\"", + Snprintf(temp_buf, sizeof temp_buf, " with %s: \"%s\"", + is_headstone ? "headstone reading" : "remembered text", ep->engr_txt[remembered_text]); else - Snprintf(temp_buf, sizeof temp_buf, " that you've never read"); + Snprintf(temp_buf, sizeof temp_buf, " %s you haven't read", + is_headstone ? "whose headstone" : "that"); + (void) strncat(buf, temp_buf, BUFSZ - strlen(buf) - 1); return TRUE; +#undef ENGRVG } return FALSE; } @@ -1733,18 +1761,6 @@ do_look(int mode, coord *click_cc) /* Finally, print out our explanation. */ if (found) { - if (ans != LOOK_QUICK && ans != LOOK_ONCE - && (ans == LOOK_VERBOSE || (flags.help && !quick)) - && !clicklook - && !strncmp(firstmatch, "engraving", 9)) { - char engbuf[BUFSZ]; - - engbuf[0] = '\0'; - if (add_quoted_engraving(cc.x, cc.y, engbuf)) { - Snprintf(eos(out_str), BUFSZ - strlen(out_str) - 1, - "%s", engbuf); - } - } /* use putmixed() because there may be an encoded glyph present */ putmixed(WIN_MESSAGE, 0, out_str); #ifdef DUMPLOG