Skip to content

Commit

Permalink
Redo penalties for amulets of regen and dismissal
Browse files Browse the repository at this point in the history
The old penalties gave strategic penalties for tactical costs, which
seemed disproportional and inappropriate.

The new swap deterrent for amulets of regeneration (courtesy of Haifisch
via archaeo, I believe) is that the amulet won't regenerate you at all
until it attunes to your physiology, which happens as soon as you hit
full health. This means that you cannot use it for emergency healing, but
there's no frustrating penalty for swapping it strategically.

The new swap deterrent for amulets of dismissal is a brief (3-6 turns)
spell of vertigo when you put it on. Vertigo affects your EV, combat
accuracy, and spell success chances. This makes it a bad thing to pop on
in the middle of a fight, but is not a meaningful penalty outside of
combat. The status lasts quite briefly, meaning that resting after
putting on the amulet isn't particularly necessary.
  • Loading branch information
cbuchananhowland committed Dec 5, 2015
1 parent bb51d4e commit eb0600f
Show file tree
Hide file tree
Showing 11 changed files with 73 additions and 39 deletions.
3 changes: 0 additions & 3 deletions crawl-ref/source/artefact.cc
Expand Up @@ -421,7 +421,6 @@ struct jewellery_fake_artp
static map<jewellery_type, vector<jewellery_fake_artp>> jewellery_artps = {
{ AMU_RAGE, { { ARTP_BERSERK, 1 } } },
{ AMU_REGENERATION, { { ARTP_REGENERATION, 1 } } },
{ AMU_DISMISSAL, { { ARTP_CONTAM, 1 } } },

{ RING_INVISIBILITY, { { ARTP_INVISIBLE, 1 } } },
{ RING_MAGICAL_POWER, { { ARTP_MAGICAL_POWER, 9 } } },
Expand Down Expand Up @@ -638,8 +637,6 @@ static bool _artp_can_go_on_item(artefact_prop_type prop, const item_def &item,
case ARTP_MAGICAL_POWER:
return item_class != OBJ_WEAPONS
|| get_weapon_brand(item) != SPWPN_ANTIMAGIC;
case ARTP_CONTAM:
return !item.is_type(OBJ_JEWELLERY, AMU_DISMISSAL);
// not quite as interesting on armour, since you swap it less
case ARTP_FRAGILE:
return item_class != OBJ_ARMOUR;
Expand Down
4 changes: 4 additions & 0 deletions crawl-ref/source/attack.cc
Expand Up @@ -214,6 +214,10 @@ int attack::calc_to_hit(bool random)
// armour penalty
mhit -= (attacker_armour_tohit_penalty + attacker_shield_tohit_penalty);

// vertigo penalty
if (you.duration[DUR_VERTIGO])
mhit -= 5;

// mutation
if (player_mutation_level(MUT_EYEBALLS))
mhit += 2 * player_mutation_level(MUT_EYEBALLS) + 1;
Expand Down
13 changes: 6 additions & 7 deletions crawl-ref/source/dat/descript/items.txt
Expand Up @@ -13,10 +13,10 @@ being berserked against one's will.
%%%%
amulet of dismissal

This amulet generates a field of translocational energy that will teleport away
creatures that harm you one tenth of the time. Removing it causes that
energy to latch onto the former wearer, causing an intense build-up of magical
contamination.
This amulet generates a field of translocational energy that will one in ten
times teleport away creatures that harm you. It takes a few moments to get used
to the translocational energy field, initially disorienting the wearer for a
few turns.
%%%%
amulet of faith

Expand Down Expand Up @@ -45,9 +45,8 @@ This amulet enables its wearer to attempt to enter a state of berserk rage.
%%%%
amulet of regeneration

This amulet bonds with its wearer to greatly increases their recuperative
powers. Removing the amulet violently severs this recuperative bond, causing
rot.
This amulet increases the wearer's natural regeneration rate. In order to
function, it must first attune itself to the wearer's body at full health.
%%%%
amulet of resist corrosion

Expand Down
2 changes: 2 additions & 0 deletions crawl-ref/source/duration-data.h
Expand Up @@ -370,6 +370,8 @@ static const duration_def duration_data[] =
RED, "Howl",
"doom howling", "howl",
"A terrible howling echoes in your mind.", D_DISPELLABLE },
{ DUR_VERTIGO, YELLOW, "Vertigo", "", "vertigo",
"Vertigo is making it harder to attack, cast, and dodge.", D_NO_FLAGS },

// The following are visible in wizmode only, or are handled
// specially in the status lights and/or the % or @ screens.
Expand Down
1 change: 1 addition & 0 deletions crawl-ref/source/enum.h
Expand Up @@ -1909,6 +1909,7 @@ enum duration_type
DUR_DEVICE_SURGE,
DUR_DOOM_HOWL,
DUR_DOOM_HOWL_IMMUNITY,
DUR_VERTIGO,
NUM_DURATIONS
};

Expand Down
3 changes: 2 additions & 1 deletion crawl-ref/source/invent.cc
Expand Up @@ -1644,7 +1644,8 @@ bool needs_handle_warning(const item_def &item, operation_types oper,
return true;
}
if (item.is_type(OBJ_JEWELLERY, AMU_REGENERATION)
&& player_mutation_level(MUT_SLOW_REGENERATION) < 3)
&& player_mutation_level(MUT_SLOW_REGENERATION) < 3
&& you.props[REGEN_AMULET_ACTIVE].get_int() == 1)
{
return true;
}
Expand Down
47 changes: 23 additions & 24 deletions crawl-ref/source/player-equip.cc
Expand Up @@ -24,6 +24,7 @@
#include "macro.h" // command_to_string
#include "message.h"
#include "misc.h"
#include "mutation.h"
#include "notes.h"
#include "options.h"
#include "player-stats.h"
Expand Down Expand Up @@ -1101,18 +1102,27 @@ static void _remove_amulet_of_faith(item_def &item)
}
}

static void _remove_amulet_of_dismissal(item_def &item)
static void _equip_amulet_of_dismissal()
{
mpr("The amulet's energy floods into your body!");
contaminate_player(7000, true);
mprf(MSGCH_DURATION, "The world spins around you as a field of "
"translocational energy flows through you!");
you.increase_duration(DUR_VERTIGO, random2(4) + 3);
}

static void _remove_amulet_of_regeneration(item_def &item)
static void _equip_amulet_of_regeneration()
{
if (player_mutation_level(MUT_SLOW_REGENERATION) < 3)
if (player_mutation_level(MUT_SLOW_REGENERATION) == 3)
mpr("The amulet feels cold and inert.");
else if (you.hp == you.hp_max)
{
mpr("Your flesh rots as the regenerative bond is broken!");
rot_hp(2 + random2(5));
you.props[REGEN_AMULET_ACTIVE] = 1;
mpr("The amulet throbs as it attunes itself to your healthy body.");
}
else
{
mpr("You sense that the amulet cannot attune itself to your injured"
" body.");
you.props[REGEN_AMULET_ACTIVE] = 0;
}
}

Expand Down Expand Up @@ -1198,16 +1208,13 @@ static void _equip_jewellery_effect(item_def &item, bool unmeld,
break;

case AMU_DISMISSAL:
mpr("You feel a field of translocational energy surge around you.");
if (!unmeld)
_equip_amulet_of_dismissal();
break;

case AMU_REGENERATION:
if (player_mutation_level(MUT_SLOW_REGENERATION) == 3)
mpr("The amulet feels cold and inert.");
else
mprf("The amulet begins to pulse %s.",
you.undead_state() ? "steadily"
: "in time with your heartbeat");
if (!unmeld)
_equip_amulet_of_regeneration();
break;

case AMU_GUARDIAN_SPIRIT:
Expand Down Expand Up @@ -1322,6 +1329,8 @@ static void _unequip_jewellery_effect(item_def &item, bool mesg, bool meld,
case RING_STEALTH:
case RING_TELEPORTATION:
case RING_WIZARDRY:
case AMU_DISMISSAL:
case AMU_REGENERATION:
break;

case RING_SEE_INVISIBLE:
Expand Down Expand Up @@ -1378,16 +1387,6 @@ static void _unequip_jewellery_effect(item_def &item, bool mesg, bool meld,
_remove_amulet_of_faith(item);
break;

case AMU_DISMISSAL:
if (!meld)
_remove_amulet_of_dismissal(item);
break;

case AMU_REGENERATION:
if (!meld)
_remove_amulet_of_regeneration(item);
break;

case AMU_GUARDIAN_SPIRIT:
if (you.species == SP_DEEP_DWARF)
mpr("Your magic begins regenerating once more.");
Expand Down
6 changes: 5 additions & 1 deletion crawl-ref/source/player-reacts.cc
Expand Up @@ -642,7 +642,9 @@ static void _decrement_durations()
if (_decrement_a_duration(DUR_PHASE_SHIFT, delay,
"You are firmly grounded in the material plane once more.",
coinflip(),
"You feel closer to the material plane."))
"You feel closer to the material plane.")
|| _decrement_a_duration(DUR_VERTIGO, delay,
"The world stops spinning."))
{
you.redraw_evasion = true;
}
Expand Down Expand Up @@ -1283,6 +1285,8 @@ static void _regenerate_hp_and_mp(int delay)
}

ASSERT_RANGE(you.magic_points_regeneration, 0, 100);

update_regen_amulet_attunement();
}

void player_reacts()
Expand Down
29 changes: 26 additions & 3 deletions crawl-ref/source/player.cc
Expand Up @@ -1100,7 +1100,8 @@ static int _player_bonus_regen()
}

// Jewellery.
rr += REGEN_PIP * you.wearing(EQ_AMULET, AMU_REGENERATION);
if (you.props[REGEN_AMULET_ACTIVE].get_int() == 1)
rr += REGEN_PIP * you.wearing(EQ_AMULET, AMU_REGENERATION);

// Artefacts
rr += REGEN_PIP * you.scan_artefacts(ARTP_REGENERATION);
Expand Down Expand Up @@ -1201,6 +1202,25 @@ int player_regen()
return rr;
}

// Amulet of regeneration needs to be worn while at full health before it begins
// to function.
void update_regen_amulet_attunement()
{
if (you.wearing(EQ_AMULET, AMU_REGENERATION)
&& player_mutation_level(MUT_SLOW_REGENERATION) < 3)
{
if (you.hp == you.hp_max
&& you.props[REGEN_AMULET_ACTIVE].get_int() == 0)
{
you.props[REGEN_AMULET_ACTIVE] = 1;
mpr("Your amulet attunes itself to your body and you begin to "
"regenerate more quickly.");
}
}
else
you.props[REGEN_AMULET_ACTIVE] = 0;
}

int player_hunger_rate(bool temp)
{
int hunger = 3;
Expand Down Expand Up @@ -2184,7 +2204,7 @@ static int _player_adjusted_evasion_penalty(const int scale)
}

return piece_armour_evasion_penalty * scale / 10 +
you.adjusted_body_armour_penalty(scale) ;
you.adjusted_body_armour_penalty(scale);
}

// EV bonuses that work even when helpless.
Expand Down Expand Up @@ -2316,11 +2336,14 @@ static int _player_evasion(ev_ignore_type evit)
const int scale = 100;
const int size_base_ev = (10 + size_factor) * scale;

const int vertigo_penalty = you.duration[DUR_VERTIGO] ? 5 * scale : 0;

const int prestepdown_evasion =
size_base_ev
+ _player_armour_adjusted_dodge_bonus(scale)
- _player_adjusted_evasion_penalty(scale)
- you.adjusted_shield_penalty(scale);
- you.adjusted_shield_penalty(scale)
- vertigo_penalty;

const int poststepdown_evasion =
stepdown_value(prestepdown_evasion, 20*scale, 30*scale, 60*scale, -1);
Expand Down
2 changes: 2 additions & 0 deletions crawl-ref/source/player.h
Expand Up @@ -32,6 +32,7 @@
#define POWERED_BY_DEATH_KEY "powered_by_death_strength"
#define SONG_OF_SLAYING_KEY "song_of_slaying_bonus"
#define FORCE_MAPPABLE_KEY "force_mappable"
#define REGEN_AMULET_ACTIVE "regen_amulet_active"

// display/messaging breakpoints for penalties from Ru's MUT_HORROR
#define HORROR_LVL_EXTREME 3
Expand Down Expand Up @@ -913,6 +914,7 @@ int player_prot_life(bool calc_unid = true, bool temp = true,
bool items = true);

int player_regen();
void update_regen_amulet_attunement();

int player_res_cold(bool calc_unid = true, bool temp = true,
bool items = true);
Expand Down
2 changes: 2 additions & 0 deletions crawl-ref/source/spl-cast.cc
Expand Up @@ -384,6 +384,8 @@ int raw_spell_fail(spell_type spell)

chance2 += you.duration[DUR_MAGIC_SAPPED] / BASELINE_DELAY;

chance2 += you.duration[DUR_VERTIGO] ? 7 : 0;

// Apply the effects of Vehumet and items of wizardry.
chance2 = _apply_spellcasting_success_boosts(spell, chance2);

Expand Down

0 comments on commit eb0600f

Please sign in to comment.