Nerf unicorn horn

Unicorn horns are just too good. Nerf it in similar way several
other variants have done: don't let it restore attribute loss.

This makes potion of restore ability more valuable, and the
int loss from the (nerfed) mind flayers matter more.
This commit is contained in:
Pasi Kallinen
2020-04-15 22:40:11 +03:00
parent a768507ebd
commit 43d331c4eb
5 changed files with 30 additions and 77 deletions

View File

@@ -1931,14 +1931,13 @@ struct obj *obj;
}
void
use_unicorn_horn(obj)
struct obj *obj;
use_unicorn_horn(optr)
struct obj **optr;
{
#define PROP_COUNT 7 /* number of properties we're dealing with */
#define ATTR_COUNT (A_MAX * 3) /* number of attribute points we might fix */
int idx, val, val_limit, trouble_count, unfixable_trbl, did_prop,
did_attr;
int trouble_list[PROP_COUNT + ATTR_COUNT];
int idx, val, val_limit, trouble_count, unfixable_trbl, did_prop;
int trouble_list[PROP_COUNT];
struct obj *obj = (optr ? *optr : (struct obj *) 0);
if (obj && obj->cursed) {
long lcount = (long) rn1(90, 10);
@@ -1962,7 +1961,10 @@ struct obj *obj;
make_stunned((HStun & TIMEOUT) + lcount, TRUE);
break;
case 4:
(void) adjattrib(rn2(A_MAX), -1, FALSE);
if (Vomiting)
vomit();
else
make_vomiting(14L, FALSE);
break;
case 5:
(void) make_hallucinated((HHallucination & TIMEOUT) + lcount,
@@ -1980,13 +1982,10 @@ struct obj *obj;
/*
* Entries in the trouble list use a very simple encoding scheme.
*/
#define prop2trbl(X) ((X) + A_MAX)
#define attr2trbl(Y) (Y)
#define prop_trouble(X) trouble_list[trouble_count++] = prop2trbl(X)
#define attr_trouble(Y) trouble_list[trouble_count++] = attr2trbl(Y)
#define prop_trouble(X) trouble_list[trouble_count++] = (X)
#define TimedTrouble(P) (((P) && !((P) & ~TIMEOUT)) ? ((P) & TIMEOUT) : 0L)
trouble_count = unfixable_trbl = did_prop = did_attr = 0;
trouble_count = unfixable_trbl = did_prop = 0;
/* collect property troubles */
if (TimedTrouble(Sick))
@@ -2006,44 +2005,11 @@ struct obj *obj;
if (TimedTrouble(HDeaf))
prop_trouble(DEAF);
unfixable_trbl = unfixable_trouble_count(TRUE);
/* collect attribute troubles */
for (idx = 0; idx < A_MAX; idx++) {
if (ABASE(idx) >= AMAX(idx))
continue;
val_limit = AMAX(idx);
/* this used to adjust 'val_limit' for A_STR when u.uhs was
WEAK or worse, but that's handled via ATEMP(A_STR) now */
if (Fixed_abil) {
/* potion/spell of restore ability override sustain ability
intrinsic but unicorn horn usage doesn't */
unfixable_trbl += val_limit - ABASE(idx);
continue;
}
/* don't recover more than 3 points worth of any attribute */
if (val_limit > ABASE(idx) + 3)
val_limit = ABASE(idx) + 3;
for (val = ABASE(idx); val < val_limit; val++)
attr_trouble(idx);
/* keep track of unfixed trouble, for message adjustment below */
unfixable_trbl += (AMAX(idx) - val_limit);
}
if (trouble_count == 0) {
pline1(nothing_happens);
return;
} else if (trouble_count > 1) { /* shuffle */
int i, j, k;
for (i = trouble_count - 1; i > 0; i--)
if ((j = rn2(i + 1)) != i) {
k = trouble_list[j];
trouble_list[j] = trouble_list[i];
trouble_list[i] = k;
}
}
} else if (trouble_count > 1)
shuffle_int_array(trouble_list, trouble_count);
/*
* Chances for number of troubles to be fixed
@@ -2060,60 +2026,47 @@ struct obj *obj;
idx = trouble_list[val];
switch (idx) {
case prop2trbl(SICK):
case SICK:
make_sick(0L, (char *) 0, TRUE, SICK_ALL);
did_prop++;
break;
case prop2trbl(BLINDED):
case BLINDED:
make_blinded((long) u.ucreamed, TRUE);
did_prop++;
break;
case prop2trbl(HALLUC):
case HALLUC:
(void) make_hallucinated(0L, TRUE, 0L);
did_prop++;
break;
case prop2trbl(VOMITING):
case VOMITING:
make_vomiting(0L, TRUE);
did_prop++;
break;
case prop2trbl(CONFUSION):
case CONFUSION:
make_confused(0L, TRUE);
did_prop++;
break;
case prop2trbl(STUNNED):
case STUNNED:
make_stunned(0L, TRUE);
did_prop++;
break;
case prop2trbl(DEAF):
case DEAF:
make_deaf(0L, TRUE);
did_prop++;
break;
default:
if (idx >= 0 && idx < A_MAX) {
ABASE(idx) += 1;
did_attr++;
} else
panic("use_unicorn_horn: bad trouble? (%d)", idx);
impossible("use_unicorn_horn: bad trouble? (%d)", idx);
break;
}
}
if (did_attr || did_prop)
if (did_prop)
g.context.botl = TRUE;
if (did_attr)
pline("This makes you feel %s!",
(did_prop + did_attr) == (trouble_count + unfixable_trbl)
? "great"
: "better");
else if (!did_prop)
else
pline("Nothing seems to happen.");
#undef PROP_COUNT
#undef ATTR_COUNT
#undef prop2trbl
#undef attr2trbl
#undef prop_trouble
#undef attr_trouble
#undef TimedTrouble
}
@@ -3809,7 +3762,7 @@ doapply()
use_figurine(&obj);
break;
case UNICORN_HORN:
use_unicorn_horn(obj);
use_unicorn_horn(&obj);
break;
case WOODEN_FLUTE:
case MAGIC_FLUTE:

View File

@@ -721,7 +721,7 @@ domonability(VOID_ARGS)
} else
There("is no fountain here.");
} else if (is_unicorn(g.youmonst.data)) {
use_unicorn_horn((struct obj *) 0);
use_unicorn_horn((struct obj **) 0);
return 1;
} else if (g.youmonst.data->msound == MS_SHRIEK) {
You("shriek.");

View File

@@ -73,7 +73,7 @@
void strbuf_nl_to_crlf (strbuf_t *)
char * nonconst (const char *, char *)
int swapbits (int, int, int)
UNUSED void shuffle_int_array (int *, int)
void shuffle_int_array (int *, int)
=*/
#ifdef LINT
#define Static /* pacify lint */
@@ -1302,9 +1302,8 @@ int val, bita, bitb;
return (val ^ ((tmp << bita) | (tmp << bitb)));
}
#if 0
/* randomize the given list of numbers 0 <= i < count */
static void
void
shuffle_int_array(indices, count)
int *indices;
int count;
@@ -1319,6 +1318,5 @@ int count;
indices[iswap] = temp;
}
}
#endif
/*hacklib.c*/