Merging in autopickup exception rework

This commit is contained in:
HMM
2019-09-24 19:12:54 -04:00
5 changed files with 60 additions and 76 deletions
+1 -1
View File
@@ -1893,7 +1893,7 @@ E boolean NDECL(u_handsy);
E int FDECL(use_container, (struct obj **, int, BOOLEAN_P)); E int FDECL(use_container, (struct obj **, int, BOOLEAN_P));
E int FDECL(loot_mon, (struct monst *, int *, boolean *)); E int FDECL(loot_mon, (struct monst *, int *, boolean *));
E int NDECL(dotip); E int NDECL(dotip);
E boolean FDECL(is_autopickup_exception, (struct obj *, BOOLEAN_P)); E struct autopickup_exception *FDECL(check_autopickup_exceptions, (struct obj *));
E boolean FDECL(autopick_testobj, (struct obj *, BOOLEAN_P)); E boolean FDECL(autopick_testobj, (struct obj *, BOOLEAN_P));
/* ### pline.c ### */ /* ### pline.c ### */
+4 -1
View File
@@ -423,9 +423,12 @@ struct instance_flags {
int wc2_statuslines; /* default = 2, curses can handle 3 */ int wc2_statuslines; /* default = 2, curses can handle 3 */
int wc2_windowborders; /* display borders on NetHack windows */ int wc2_windowborders; /* display borders on NetHack windows */
int wc2_petattr; /* text attributes for pet */ int wc2_petattr; /* text attributes for pet */
struct autopickup_exception *autopickup_exceptions[2]; /* VE edit: APE overhaul */
struct autopickup_exception *autopickup_exceptions;
/*
#define AP_LEAVE 0 #define AP_LEAVE 0
#define AP_GRAB 1 #define AP_GRAB 1
*/
#ifdef WIN32 #ifdef WIN32
#define MAX_ALTKEYHANDLER 25 #define MAX_ALTKEYHANDLER 25
char altkeyhandler[MAX_ALTKEYHANDLER]; char altkeyhandler[MAX_ALTKEYHANDLER];
+1 -2
View File
@@ -2139,8 +2139,7 @@ int final;
*ocl ? "'" : "", *ocl ? ocl : "all types", *ocl ? "'" : ""); *ocl ? "'" : "", *ocl ? ocl : "all types", *ocl ? "'" : "");
if (flags.pickup_thrown && *ocl) /* *ocl: don't show if 'all types' */ if (flags.pickup_thrown && *ocl) /* *ocl: don't show if 'all types' */
Strcat(buf, " plus thrown"); Strcat(buf, " plus thrown");
if (iflags.autopickup_exceptions[AP_GRAB] if (iflags.autopickup_exceptions)
|| iflags.autopickup_exceptions[AP_LEAVE])
Strcat(buf, ", with exceptions"); Strcat(buf, ", with exceptions");
} else } else
Strcpy(buf, "off"); Strcpy(buf, "off");
+42 -53
View File
@@ -573,7 +573,7 @@ STATIC_DCL boolean FDECL(special_handling, (const char *,
STATIC_DCL const char *FDECL(get_compopt_value, (const char *, char *)); STATIC_DCL const char *FDECL(get_compopt_value, (const char *, char *));
STATIC_DCL void FDECL(remove_autopickup_exception, STATIC_DCL void FDECL(remove_autopickup_exception,
(struct autopickup_exception *)); (struct autopickup_exception *));
STATIC_DCL int FDECL(count_ape_maps, (int *, int *)); STATIC_DCL int NDECL(count_ape_maps); /* VE edit: APE overhaul */
STATIC_DCL boolean FDECL(is_wc_option, (const char *)); STATIC_DCL boolean FDECL(is_wc_option, (const char *));
STATIC_DCL boolean FDECL(wc_supported, (const char *)); STATIC_DCL boolean FDECL(wc_supported, (const char *));
@@ -4411,10 +4411,11 @@ int nset;
add_menu(win, NO_GLYPH, &any, 0, 0, ATR_NONE, buf, MENU_UNSELECTED); add_menu(win, NO_GLYPH, &any, 0, 0, ATR_NONE, buf, MENU_UNSELECTED);
} }
/* VE edit: APE overhaul */
int int
count_apes(VOID_ARGS) count_apes(VOID_ARGS)
{ {
return count_ape_maps((int *) 0, (int *) 0); return count_ape_maps();
} }
enum opt_other_enums { enum opt_other_enums {
@@ -5285,13 +5286,13 @@ boolean setinitial, setfromfile;
goto menucolors_again; goto menucolors_again;
} }
} else if (!strcmp("autopickup_exception", optname)) { } else if (!strcmp("autopickup_exception", optname)) {
int opt_idx, pass, totalapes = 0, numapes[2] = { 0, 0 }; int opt_idx, pass, numapes = 0;
char apebuf[1 + BUFSZ]; /* so &apebuf[1] is BUFSZ long for getlin() */ char apebuf[2 + BUFSZ]; /* so &apebuf[1] is BUFSZ long for getlin() */
struct autopickup_exception *ape; struct autopickup_exception *ape;
ape_again: ape_again:
totalapes = count_ape_maps(&numapes[AP_LEAVE], &numapes[AP_GRAB]); numapes = count_ape_maps();
opt_idx = handle_add_list_remove("autopickup exception", totalapes); opt_idx = handle_add_list_remove("autopickup exception", numapes);
if (opt_idx == 3) { /* done */ if (opt_idx == 3) { /* done */
return TRUE; return TRUE;
} else if (opt_idx == 0) { /* add new */ } else if (opt_idx == 0) { /* add new */
@@ -5307,7 +5308,7 @@ boolean setinitial, setfromfile;
/* guarantee room for \" prefix and \"\0 suffix; /* guarantee room for \" prefix and \"\0 suffix;
-2 is good enough for apebuf[] but -3 makes -2 is good enough for apebuf[] but -3 makes
sure the whole thing fits within normal BUFSZ */ sure the whole thing fits within normal BUFSZ */
apebuf[sizeof apebuf - 3] = '\0'; apebuf[sizeof apebuf - 2] = '\0';
Strcat(apebuf, "\""); Strcat(apebuf, "\"");
add_autopickup_exception(apebuf); add_autopickup_exception(apebuf);
} }
@@ -5318,18 +5319,19 @@ boolean setinitial, setfromfile;
tmpwin = create_nhwindow(NHW_MENU); tmpwin = create_nhwindow(NHW_MENU);
start_menu(tmpwin); start_menu(tmpwin);
for (pass = AP_LEAVE; pass <= AP_GRAB; ++pass) { if (numapes) {
if (numapes[pass] == 0) ape = (struct autopickup_exception *)
continue; iflags.autopickup_exceptions;
ape = iflags.autopickup_exceptions[pass];
any = zeroany; any = zeroany;
add_menu(tmpwin, NO_GLYPH, &any, 0, 0, iflags.menu_headings, add_menu(tmpwin, NO_GLYPH, &any, 0, 0, iflags.menu_headings,
(pass == 0) ? "Never pickup" : "Always pickup", "Always pickup '<'; never pickup '>'",
MENU_UNSELECTED); MENU_UNSELECTED);
for (i = 0; i < numapes[pass] && ape; i++) { for (i = 0; i < numapes && ape; i++) {
any.a_void = (opt_idx == 1) ? 0 : ape; any.a_void = (opt_idx == 1) ? 0 : ape;
/* length of pattern plus quotes is less than BUFSZ */ /* length of pattern plus quotes (plus '<'/'>') is less than
Sprintf(apebuf, "\"%s\"", ape->pattern); BUFSZ */
Sprintf(apebuf, "\"%c%s\"", ape->grab ? '<' : '>',
ape->pattern);
add_menu(tmpwin, NO_GLYPH, &any, 0, 0, ATR_NONE, apebuf, add_menu(tmpwin, NO_GLYPH, &any, 0, 0, ATR_NONE, apebuf,
MENU_UNSELECTED); MENU_UNSELECTED);
ape = ape->next; ape = ape->next;
@@ -5889,9 +5891,8 @@ dotogglepickup()
if (flags.pickup) { if (flags.pickup) {
oc_to_str(flags.pickup_types, ocl); oc_to_str(flags.pickup_types, ocl);
Sprintf(buf, "ON, for %s objects%s", ocl[0] ? ocl : "all", Sprintf(buf, "ON, for %s objects%s", ocl[0] ? ocl : "all",
(iflags.autopickup_exceptions[AP_LEAVE] (iflags.autopickup_exceptions)
|| iflags.autopickup_exceptions[AP_GRAB]) ? ((count_ape_maps() == 1)
? ((count_ape_maps((int *) 0, (int *) 0) == 1)
? ", with one exception" ? ", with one exception"
: ", with some exceptions") : ", with some exceptions")
: ""); : "");
@@ -5902,6 +5903,7 @@ dotogglepickup()
return 0; return 0;
} }
/* VE edit: APE overhaul */
int int
add_autopickup_exception(mapping) add_autopickup_exception(mapping)
const char *mapping; const char *mapping;
@@ -5910,7 +5912,7 @@ const char *mapping;
APE_regex_error[] = "regex error in AUTOPICKUP_EXCEPTION", APE_regex_error[] = "regex error in AUTOPICKUP_EXCEPTION",
APE_syntax_error[] = "syntax error in AUTOPICKUP_EXCEPTION"; APE_syntax_error[] = "syntax error in AUTOPICKUP_EXCEPTION";
struct autopickup_exception *ape, **apehead; struct autopickup_exception *ape;
char text[256], end; char text[256], end;
int n; int n;
boolean grab = FALSE; boolean grab = FALSE;
@@ -5942,31 +5944,29 @@ const char *mapping;
free((genericptr_t) ape); free((genericptr_t) ape);
return 0; return 0;
} }
apehead = (grab) ? &iflags.autopickup_exceptions[AP_GRAB]
: &iflags.autopickup_exceptions[AP_LEAVE];
ape->pattern = dupstr(text); ape->pattern = dupstr(text);
ape->grab = grab; ape->grab = grab;
ape->next = *apehead; ape->next = (struct autopickup_exception *) iflags.autopickup_exceptions;
*apehead = ape; iflags.autopickup_exceptions = (struct autopickup_exception *) ape;
return 1; return 1;
} }
/* VE edit: APE overhaul */
STATIC_OVL void STATIC_OVL void
remove_autopickup_exception(whichape) remove_autopickup_exception(whichape)
struct autopickup_exception *whichape; struct autopickup_exception *whichape;
{ {
struct autopickup_exception *ape, *freeape, *prev = 0; struct autopickup_exception *ape, *freeape, *prev = 0;
int chain = whichape->grab ? AP_GRAB : AP_LEAVE;
for (ape = iflags.autopickup_exceptions[chain]; ape;) { for (ape = iflags.autopickup_exceptions; ape;) {
if (ape == whichape) { if (ape == whichape) {
freeape = ape; freeape = ape;
ape = ape->next; ape = ape->next;
if (prev) if (prev)
prev->next = ape; prev->next = ape;
else else
iflags.autopickup_exceptions[chain] = ape; iflags.autopickup_exceptions = ape;
regex_free(freeape->regex); regex_free(freeape->regex);
free((genericptr_t) freeape->pattern); free((genericptr_t) freeape->pattern);
free((genericptr_t) freeape); free((genericptr_t) freeape);
@@ -5977,42 +5977,31 @@ struct autopickup_exception *whichape;
} }
} }
/* VE edit: APE overhaul */
STATIC_OVL int STATIC_OVL int
count_ape_maps(leave, grab) count_ape_maps()
int *leave, *grab;
{ {
struct autopickup_exception *ape; int numapes = 0;
int pass, totalapes, numapes[2]; struct autopickup_exception *ape = iflags.autopickup_exceptions;
numapes[0] = numapes[1] = 0; while (ape) {
for (pass = AP_LEAVE; pass <= AP_GRAB; ++pass) { numapes++;
ape = iflags.autopickup_exceptions[pass]; ape = ape->next;
while (ape) {
ape = ape->next;
numapes[pass]++;
}
} }
totalapes = numapes[AP_LEAVE] + numapes[AP_GRAB];
if (leave) return numapes;
*leave = numapes[AP_LEAVE];
if (grab)
*grab = numapes[AP_GRAB];
return totalapes;
} }
/* VE edit: APE overhaul */
void void
free_autopickup_exceptions() free_autopickup_exceptions()
{ {
struct autopickup_exception *ape; struct autopickup_exception *ape = iflags.autopickup_exceptions;
int pass; while ((ape = iflags.autopickup_exceptions) != 0) {
regex_free(ape->regex);
for (pass = AP_LEAVE; pass <= AP_GRAB; ++pass) { free((genericptr_t) ape->pattern);
while ((ape = iflags.autopickup_exceptions[pass]) != 0) { iflags.autopickup_exceptions = ape->next;
regex_free(ape->regex); free((genericptr_t) ape);
free((genericptr_t) ape->pattern);
iflags.autopickup_exceptions[pass] = ape->next;
free((genericptr_t) ape);
}
} }
} }
+12 -19
View File
@@ -711,28 +711,20 @@ int what; /* should be a long */
return (n_tried > 0); return (n_tried > 0);
} }
boolean struct autopickup_exception *
is_autopickup_exception(obj, grab) check_autopickup_exceptions(obj)
struct obj *obj; struct obj *obj;
boolean grab; /* forced pickup, rather than forced leave behind? */
{ {
/* /*
* Does the text description of this match an exception? * Does the text description of this match an exception?
*/ */
struct autopickup_exception struct autopickup_exception
*ape = (grab) ? iflags.autopickup_exceptions[AP_GRAB] *ape = iflags.autopickup_exceptions;
: iflags.autopickup_exceptions[AP_LEAVE];
if (ape) { if (ape) {
char *objdesc = makesingular(doname(obj)); char *objdesc = makesingular(doname(obj));
do if (regex_match(objdesc, ape->regex)) return ape;
while (ape) { while (ape = ape->next);
if (regex_match(objdesc, ape->regex))
return TRUE;
ape = ape->next;
}
} }
return FALSE;
} }
boolean boolean
@@ -755,12 +747,13 @@ boolean calc_costly;
/* check for pickup_types */ /* check for pickup_types */
pickit = (!*otypes || index(otypes, otmp->oclass)); pickit = (!*otypes || index(otypes, otmp->oclass));
/* check for "always pick up */
if (!pickit) /* check for autopickup excpetions */
pickit = is_autopickup_exception(otmp, TRUE); struct autopickup_exception
/* then for "never pick up */ *ape = check_autopickup_exceptions(otmp);
if (pickit) if (ape)
pickit = !is_autopickup_exception(otmp, FALSE); pickit = ape->grab;
/* pickup_thrown overrides pickup_types and exceptions */ /* pickup_thrown overrides pickup_types and exceptions */
if (!pickit) if (!pickit)
pickit = (flags.pickup_thrown && otmp->was_thrown); pickit = (flags.pickup_thrown && otmp->was_thrown);