GOLDOBJ pickup handling (trunk only)

For GOLDOBJ configuration, relax the 52 object limit for inventory
when gold uses the special $ slot instead of a letter.  Takes care of an
old buglist entry from the beta testers.  [It will need to be revisited
if we ever implement multiple coin types that can't all fit in one slot.]

     Also for GOLDOBJ, prevents nymphs and monkeys from stealing coins,
since allowing that made their steal-item attack be a complete superset
of leprechaun's steal-gold attack.
This commit is contained in:
nethack.rankin
2007-06-16 02:22:01 +00:00
parent e753fb50f2
commit 2ad3afee05
10 changed files with 37 additions and 26 deletions
+2
View File
@@ -31,6 +31,8 @@ internals: use Is_box rather than explicitly checking what it checks
fix some unreachable messages (either make then reachable or remove them) fix some unreachable messages (either make then reachable or remove them)
can quiver coins when GOLDOBJ is defined can quiver coins when GOLDOBJ is defined
make #loot behave same for GOLDOBJ as for !GOLDOBJ make #loot behave same for GOLDOBJ as for !GOLDOBJ
for GOLDOBJ, can pick gold up into $ when all 52 letters are in use, and
can pick non-gold up into unused letter when gold uses one of 52 slots
grammar, spelling and other typos grammar, spelling and other typos
keep various delayed killers separate to avoid mixed up messages keep various delayed killers separate to avoid mixed up messages
don't place randomly-placed aquatic monsters in lava on special levels don't place randomly-placed aquatic monsters in lava on special levels
+1 -1
View File
@@ -798,7 +798,7 @@ E int NDECL(near_capacity);
E int FDECL(calc_capacity, (int)); E int FDECL(calc_capacity, (int));
E int NDECL(max_capacity); E int NDECL(max_capacity);
E boolean FDECL(check_capacity, (const char *)); E boolean FDECL(check_capacity, (const char *));
E int NDECL(inv_cnt); E int FDECL(inv_cnt, (BOOLEAN_P));
#ifdef GOLDOBJ #ifdef GOLDOBJ
E long FDECL(money_cnt, (struct obj *)); E long FDECL(money_cnt, (struct obj *));
#endif #endif
+1 -1
View File
@@ -341,7 +341,7 @@ register struct obj *otmp;
if (carried(otmp)) { if (carried(otmp)) {
freeinv(otmp); freeinv(otmp);
if (inv_cnt() >= 52) { if (inv_cnt(FALSE) >= 52) {
sellobj_state(SELL_DONTSELL); sellobj_state(SELL_DONTSELL);
dropy(otmp); dropy(otmp);
sellobj_state(SELL_NORMAL); sellobj_state(SELL_NORMAL);
+10 -9
View File
@@ -2479,13 +2479,14 @@ const char *str;
} }
int int
inv_cnt() inv_cnt(incl_gold)
boolean incl_gold; /* only meaningful for GOLDOBJ config */
{ {
register struct obj *otmp = invent; register struct obj *otmp = invent;
register int ct = 0; register int ct = 0;
while(otmp){ while(otmp){
ct++; if (incl_gold || otmp->invlet != GOLD_SYM) ct++;
otmp = otmp->nobj; otmp = otmp->nobj;
} }
return(ct); return(ct);
@@ -2500,13 +2501,13 @@ long
money_cnt(otmp) money_cnt(otmp)
struct obj *otmp; struct obj *otmp;
{ {
while(otmp) { while (otmp) {
/* Must change when silver & copper is implemented: */ /* Must change when silver & copper is implemented: */
if (otmp->oclass == COIN_CLASS) return otmp->quan; if (otmp->oclass == COIN_CLASS) return otmp->quan;
otmp = otmp->nobj; otmp = otmp->nobj;
} }
return 0; return 0L;
} }
#endif #endif /* GOLDOBJ */
/*hack.c*/ /*hack.c*/
+3 -3
View File
@@ -420,7 +420,7 @@ const char *drop_fmt, *drop_arg, *hold_msg;
if (drop_arg) drop_arg = strcpy(buf, drop_arg); if (drop_arg) drop_arg = strcpy(buf, drop_arg);
obj = addinv(obj); obj = addinv(obj);
if (inv_cnt() > 52 if (inv_cnt(FALSE) > 52
|| ((obj->otyp != LOADSTONE || !obj->cursed) || ((obj->otyp != LOADSTONE || !obj->cursed)
&& near_capacity() > prev_encumbr)) { && near_capacity() > prev_encumbr)) {
if (drop_fmt) pline(drop_fmt, drop_arg); if (drop_fmt) pline(drop_fmt, drop_arg);
@@ -2932,7 +2932,7 @@ doorganize() /* inventory organizer by Del Lamb */
for (let = 'A'; let <= 'Z'; ) alphabet[ix++] = let++; for (let = 'A'; let <= 'Z'; ) alphabet[ix++] = let++;
alphabet[ix] = '\0'; alphabet[ix] = '\0';
/* for floating inv letters, truncate list after the first open slot */ /* for floating inv letters, truncate list after the first open slot */
if (!flags.invlet_constant && (ix = inv_cnt()) < 52) if (!flags.invlet_constant && (ix = inv_cnt(FALSE)) < 52)
alphabet[ix + (splitting ? 0 : 1)] = '\0'; alphabet[ix + (splitting ? 0 : 1)] = '\0';
/* blank out all the letters currently in use in the inventory */ /* blank out all the letters currently in use in the inventory */
@@ -3025,7 +3025,7 @@ doorganize() /* inventory organizer by Del Lamb */
if (merged(&otmp, &obj)) { if (merged(&otmp, &obj)) {
obj = otmp; obj = otmp;
extract_nobj(obj, &invent); extract_nobj(obj, &invent);
} else if (inv_cnt() >= 52) { } else if (inv_cnt(FALSE) >= 52) {
(void) merged(&splitting, &obj); /* undo split */ (void) merged(&splitting, &obj); /* undo split */
/* "knapsack cannot accommodate any more items" */ /* "knapsack cannot accommodate any more items" */
Your("pack is too full."); Your("pack is too full.");
+7 -7
View File
@@ -1168,7 +1168,8 @@ boolean telekinesis;
availability of open inventory slot iff not already carrying one */ availability of open inventory slot iff not already carrying one */
if (obj->otyp == LOADSTONE || if (obj->otyp == LOADSTONE ||
(obj->otyp == BOULDER && throws_rocks(youmonst.data))) { (obj->otyp == BOULDER && throws_rocks(youmonst.data))) {
if (inv_cnt() < 52 || !carrying(obj->otyp) || merge_choice(invent, obj)) if (inv_cnt(FALSE) < 52 || !carrying(obj->otyp) ||
merge_choice(invent, obj))
return 1; /* lift regardless of current situation */ return 1; /* lift regardless of current situation */
/* if we reach here, we're out of slots and already have at least /* if we reach here, we're out of slots and already have at least
one of these, so treat this one more like a normal item */ one of these, so treat this one more like a normal item */
@@ -1180,11 +1181,10 @@ boolean telekinesis;
*cnt_p = carry_count(obj, container, *cnt_p, telekinesis, &old_wt, &new_wt); *cnt_p = carry_count(obj, container, *cnt_p, telekinesis, &old_wt, &new_wt);
if (*cnt_p < 1L) { if (*cnt_p < 1L) {
result = -1; /* nothing lifted */ result = -1; /* nothing lifted */
} else if ( } else if (obj->oclass != COIN_CLASS &&
#ifndef GOLDOBJ /* [exception for gold coins will have to change
obj->oclass != COIN_CLASS && if silver/copper ones ever get implemented] */
#endif inv_cnt(FALSE) >= 52 && !merge_choice(invent, obj)) {
inv_cnt() >= 52 && !merge_choice(invent, obj)) {
Your("knapsack cannot accommodate any more items."); Your("knapsack cannot accommodate any more items.");
result = -1; /* nothing lifted */ result = -1; /* nothing lifted */
} else { } else {
@@ -1625,7 +1625,7 @@ reverse_loot()
if (!rn2(3)) { if (!rn2(3)) {
/* n objects: 1/(n+1) chance per object plus 1/(n+1) to fall off end */ /* n objects: 1/(n+1) chance per object plus 1/(n+1) to fall off end */
for (n = inv_cnt(), otmp = invent; otmp; --n, otmp = otmp->nobj) for (n = inv_cnt(TRUE), otmp = invent; otmp; --n, otmp = otmp->nobj)
if (!rn2(n + 1)) { if (!rn2(n + 1)) {
prinv("You find old loot:", otmp, 0L); prinv("You find old loot:", otmp, 0L);
return TRUE; return TRUE;
+1 -1
View File
@@ -146,7 +146,7 @@ long amount;
if (mongold->quan > amount) mongold = splitobj(mongold, amount); if (mongold->quan > amount) mongold = splitobj(mongold, amount);
obj_extract_self(mongold); obj_extract_self(mongold);
if (!merge_choice(invent, mongold) && inv_cnt() >= 52) { if (!merge_choice(invent, mongold) && inv_cnt(FALSE) >= 52) {
You("have no room for the money!"); You("have no room for the money!");
dropy(mongold); dropy(mongold);
} else { } else {
+9 -2
View File
@@ -263,6 +263,7 @@ boolean unchain_ball; /* whether to unpunish or just unwield */
/* Returns 1 when something was stolen (or at least, when N should flee now) /* Returns 1 when something was stolen (or at least, when N should flee now)
* Returns -1 if the monster died in the attempt * Returns -1 if the monster died in the attempt
* Avoid stealing the object stealoid * Avoid stealing the object stealoid
* GOLDOBJ: nymphs and monkeys won't steal coins
*/ */
int int
steal(mtmp, objnambuf) steal(mtmp, objnambuf)
@@ -282,7 +283,7 @@ char *objnambuf;
so this will cause it to be removed now */ so this will cause it to be removed now */
if (occupation) (void) maybe_finished_meal(FALSE); if (occupation) (void) maybe_finished_meal(FALSE);
if (!invent || (inv_cnt() == 1 && uskin)) { if (!invent || (inv_cnt(FALSE) == 1 && uskin)) {
nothing_to_steal: nothing_to_steal:
/* Not even a thousand men in armor can strip a naked man. */ /* Not even a thousand men in armor can strip a naked man. */
if(Blind) if(Blind)
@@ -308,6 +309,9 @@ nothing_to_steal:
tmp = 0; tmp = 0;
for(otmp = invent; otmp; otmp = otmp->nobj) for(otmp = invent; otmp; otmp = otmp->nobj)
if ((!uarm || otmp != uarmc) && otmp != uskin if ((!uarm || otmp != uarmc) && otmp != uskin
#ifdef GOLDOBJ
&& otmp->oclass != COIN_CLASS
#endif
#ifdef INVISIBLE_OBJECTS #ifdef INVISIBLE_OBJECTS
&& (!otmp->oinvis || perceives(mtmp->data)) && (!otmp->oinvis || perceives(mtmp->data))
#endif #endif
@@ -318,6 +322,9 @@ nothing_to_steal:
tmp = rn2(tmp); tmp = rn2(tmp);
for(otmp = invent; otmp; otmp = otmp->nobj) for(otmp = invent; otmp; otmp = otmp->nobj)
if ((!uarm || otmp != uarmc) && otmp != uskin if ((!uarm || otmp != uarmc) && otmp != uskin
#ifdef GOLDOBJ
&& otmp->oclass != COIN_CLASS
#endif
#ifdef INVISIBLE_OBJECTS #ifdef INVISIBLE_OBJECTS
&& (!otmp->oinvis || perceives(mtmp->data)) && (!otmp->oinvis || perceives(mtmp->data))
#endif #endif
@@ -375,7 +382,7 @@ gotobj:
/* the fewer items you have, the less likely the thief /* the fewer items you have, the less likely the thief
is going to stick around to try again (0) instead of is going to stick around to try again (0) instead of
running away (1) */ running away (1) */
return !rn2(inv_cnt() / 5 + 2); return !rn2(inv_cnt(FALSE) / 5 + 2);
} }
} }
+1 -1
View File
@@ -3160,7 +3160,7 @@ STATIC_OVL boolean
emergency_disrobe(lostsome) emergency_disrobe(lostsome)
boolean *lostsome; boolean *lostsome;
{ {
int invc = inv_cnt(); int invc = inv_cnt(TRUE);
while (near_capacity() > (Punished ? UNENCUMBERED : SLT_ENCUMBER)) { while (near_capacity() > (Punished ? UNENCUMBERED : SLT_ENCUMBER)) {
register struct obj *obj, *otmp = (struct obj *)0; register struct obj *obj, *otmp = (struct obj *)0;
+2 -1
View File
@@ -1478,7 +1478,8 @@ register struct attack *mattk;
struct obj *mongold = findgold(mdef->minvent); struct obj *mongold = findgold(mdef->minvent);
if (mongold) { if (mongold) {
obj_extract_self(mongold); obj_extract_self(mongold);
if (merge_choice(invent, mongold) || inv_cnt() < 52) { if (merge_choice(invent, mongold) ||
inv_cnt(FALSE) < 52) {
addinv(mongold); addinv(mongold);
Your("purse feels heavier."); Your("purse feels heavier.");
} else { } else {