diff options
author | Nicholas Feinberg <pleasingfung@gmail.com> | 2014-04-11 08:29:44 -0700 |
---|---|---|
committer | Nicholas Feinberg <pleasingfung@gmail.com> | 2014-05-25 20:27:48 -0700 |
commit | 6f959b73ab6b07a742e45870b540a2038e405253 (patch) | |
tree | f2145783a10e15c457d8a9031eacdaee6991eed4 | |
parent | f6d44216f86f13f3ce9a7e7ee174ecb80f4248e5 (diff) | |
download | crawl-ref-6f959b73ab6b07a742e45870b540a2038e405253.tar.gz crawl-ref-6f959b73ab6b07a742e45870b540a2038e405253.zip |
Add the Majin-Bo, a new fixedart that offers power at
a terrible price. (It's not that terrible!)
-rw-r--r-- | crawl-ref/source/art-data.txt | 11 | ||||
-rw-r--r-- | crawl-ref/source/art-func.h | 17 | ||||
-rw-r--r-- | crawl-ref/source/dat/descript/unrand.txt | 8 | ||||
-rw-r--r-- | crawl-ref/source/hiscores.cc | 7 | ||||
-rw-r--r-- | crawl-ref/source/player.cc | 29 | ||||
-rw-r--r-- | crawl-ref/source/player.h | 3 | ||||
-rw-r--r-- | crawl-ref/source/rltiles/dc-player.txt | 1 | ||||
-rw-r--r-- | crawl-ref/source/rltiles/item/weapon/artefact/spwpn_majin.png | bin | 0 -> 1549 bytes | |||
-rw-r--r-- | crawl-ref/source/rltiles/player/hand1/artefact/majin.png | bin | 0 -> 1344 bytes | |||
-rw-r--r-- | crawl-ref/source/spl-cast.cc | 73 | ||||
-rw-r--r-- | crawl-ref/source/spl-util.cc | 17 |
11 files changed, 150 insertions, 16 deletions
diff --git a/crawl-ref/source/art-data.txt b/crawl-ref/source/art-data.txt index 062f754d80..6634c9d6aa 100644 --- a/crawl-ref/source/art-data.txt +++ b/crawl-ref/source/art-data.txt @@ -1163,6 +1163,17 @@ INT: 3 BRAND: SPARM_ARCHMAGI BOOL: clarity, sustab +ENUM: MAJIN +NAME: Majin-Bo +OBJ: OBJ_WEAPONS/WPN_QUARTERSTAFF +PLUS: +6/+6 +COLOUR: ETC_UNHOLY +TILE: spwpn_majin +TILE_EQ: majin +MP: 6 +INT: 6 +BRAND: SPWPN_VAMPIRICISM + # This is the first of two amulets used to test suppression aura. # Together, they confer every randart effect except for a few that are # determined explicitly by checking whether a certain amulet is worn diff --git a/crawl-ref/source/art-func.h b/crawl-ref/source/art-func.h index c636dcfcd9..2c5a0a1fef 100644 --- a/crawl-ref/source/art-func.h +++ b/crawl-ref/source/art-func.h @@ -1139,3 +1139,20 @@ static void _FLAMING_DEATH_melee_effects(item_def* weapon, actor* attacker, } } } + +/////////////////////////////////////////////////// + +static void _MAJIN_equip(item_def *item, bool *show_msgs, bool unmeld) +{ + if (you.max_magic_points) + _equip_mpr(show_msgs, "You feel a darkness envelop your magic."); +} + +static void _MAJIN_unequip(item_def *item, bool *show_msgs) +{ + if (you.max_magic_points) + { + _equip_mpr(show_msgs, + "The darkness slowly releases its grasp on your magic."); + } +} diff --git a/crawl-ref/source/dat/descript/unrand.txt b/crawl-ref/source/dat/descript/unrand.txt index edc3a73307..97f491b96e 100644 --- a/crawl-ref/source/dat/descript/unrand.txt +++ b/crawl-ref/source/dat/descript/unrand.txt @@ -570,6 +570,14 @@ Carved from transparent orange crystal, this armour provides remarkable protection for both mind and body. A skilled user can even channel psychic energies through the crystal itself. However, it's rather heavy... %%%% +Majin-Bo + +The Majin-Bo is actually a mighty demon, tricked and trapped in this form long +ago. To survive, she now offers tremendous arcane power at a small price: a +tiny portion of the caster’s life essence, taken alongside the magic used every +time its wielder casts a spell. Of course - the demon is more than happy to +suck the life from others, as well. +%%%% milk chocolate This item is a debugging aid, granting a vast array of mostly beneficial diff --git a/crawl-ref/source/hiscores.cc b/crawl-ref/source/hiscores.cc index 85dfde43f7..ca890c2237 100644 --- a/crawl-ref/source/hiscores.cc +++ b/crawl-ref/source/hiscores.cc @@ -1902,6 +1902,12 @@ static bool _species_is_undead(int sp) return sp == SP_MUMMY || sp == SP_GHOUL || sp == SP_VAMPIRE; } +/** + * Describes the cause of the player's death. + * + * @param verbosity The verbosity of the description. + * @return A description of the cause of death. + */ string scorefile_entry::death_description(death_desc_verbosity verbosity) const { bool needs_beam_cause_line = false; @@ -2430,6 +2436,7 @@ string scorefile_entry::death_description(death_desc_verbosity verbosity) const needs_damage = true; break; + default: desc += terse? "program bug" : "Nibbled to death by software bugs"; break; diff --git a/crawl-ref/source/player.cc b/crawl-ref/source/player.cc index 5d9c82cf06..2839607395 100644 --- a/crawl-ref/source/player.cc +++ b/crawl-ref/source/player.cc @@ -7175,6 +7175,35 @@ bool player::tengu_flight() const return species == SP_TENGU && flight_mode(); } +/** + * Returns the HP cost (per MP) of casting a spell. + * + * Checks to see if the player is wielding the Majin-Bo. + * + * @return The HP cost (per MP) of casting a spell. + **/ +int player::spell_hp_cost() const +{ + int cost = 0; + + if (player_equip_unrand(UNRAND_MAJIN)) + cost += 1; + + return cost; +} + +/** + * Returns true if player spellcasting is considered unholy. + * + * Checks to see if the player is wielding the Majin-Bo. + * + * @return Whether player spellcasting is an unholy act. + */ +bool player::spellcasting_unholy() const +{ + return player_equip_unrand(UNRAND_MAJIN); +} + bool player::nightvision() const { return is_undead diff --git a/crawl-ref/source/player.h b/crawl-ref/source/player.h index dd8c214065..2cbf7e02eb 100644 --- a/crawl-ref/source/player.h +++ b/crawl-ref/source/player.h @@ -444,6 +444,9 @@ public: bool tengu_flight() const; + int spell_hp_cost() const; + bool spellcasting_unholy() const; + // Dealing with beholders. Implemented in behold.cc. void add_beholder(const monster* mon, bool axe = false); bool beheld() const; diff --git a/crawl-ref/source/rltiles/dc-player.txt b/crawl-ref/source/rltiles/dc-player.txt index 7324e701f0..88aa2945ca 100644 --- a/crawl-ref/source/rltiles/dc-player.txt +++ b/crawl-ref/source/rltiles/dc-player.txt @@ -509,6 +509,7 @@ shillelagh SHILLELAGH dark_maul DARK_MAUL spellbinder SPELLBINDER firestarter FIRESTARTER +majin MAJIN ## polearms trident_octopus_king TRIDENT_OCTOPUS_KING glaive_of_prune GLAIVE_OF_PRUNE diff --git a/crawl-ref/source/rltiles/item/weapon/artefact/spwpn_majin.png b/crawl-ref/source/rltiles/item/weapon/artefact/spwpn_majin.png Binary files differnew file mode 100644 index 0000000000..fe5af2d473 --- /dev/null +++ b/crawl-ref/source/rltiles/item/weapon/artefact/spwpn_majin.png diff --git a/crawl-ref/source/rltiles/player/hand1/artefact/majin.png b/crawl-ref/source/rltiles/player/hand1/artefact/majin.png Binary files differnew file mode 100644 index 0000000000..d64b7ca602 --- /dev/null +++ b/crawl-ref/source/rltiles/player/hand1/artefact/majin.png diff --git a/crawl-ref/source/spl-cast.cc b/crawl-ref/source/spl-cast.cc index dfded666a2..05297cfb22 100644 --- a/crawl-ref/source/spl-cast.cc +++ b/crawl-ref/source/spl-cast.cc @@ -515,6 +515,7 @@ static int _spell_enhancement(unsigned int typeflags) enhanced -= 2; enhanced += you.archmagi(); + enhanced += player_equip_unrand(UNRAND_MAJIN); #if TAG_MAJOR_VERSION == 34 if (you.species == SP_LAVA_ORC && temperature_effect(LORC_LAVA_BOOST) @@ -607,7 +608,15 @@ void do_cast_spell_cmd(bool force) flush_input_buffer(FLUSH_ON_FAILURE); } -// Returns false if spell failed, and true otherwise. +/** + * Cast a spell. + * + * Handles general preconditions & costs. + * + * @param check_range If true, abort if no targets are in range. (z vs Z) + * @param spell The type of spell to be cast. + * @return Whether the spell was successfully cast. + **/ bool cast_a_spell(bool check_range, spell_type spell) { if (!_can_cast()) @@ -716,7 +725,8 @@ bool cast_a_spell(bool check_range, spell_type spell) return false; } - if (!enough_mp(spell_mana(spell), true)) + const int cost = spell_mana(spell); + if (!enough_mp(cost, true)) { mpr("You don't have enough magic to cast that spell."); crawl_state.zero_turns_taken(); @@ -774,8 +784,8 @@ bool cast_a_spell(bool check_range, spell_type spell) const bool staff_energy = player_energy(); you.last_cast_spell = spell; // Silently take MP before the spell. - const int cost = spell_mana(spell); dec_mp(cost, true); + const spret_type cast_result = your_spells(spell, 0, true, check_range); if (cast_result == SPRET_ABORT) { @@ -840,7 +850,7 @@ static void _spellcasting_god_conduct(spell_type spell) const int conduct_level = 10 + spell_difficulty(spell); - if (is_unholy_spell(spell)) + if (is_unholy_spell(spell) || you.spellcasting_unholy()) did_god_conduct(DID_UNHOLY, conduct_level); if (is_unclean_spell(spell)) @@ -1202,12 +1212,38 @@ static double _chance_miscast_prot() return min(1.0, miscast_prot); } -// Returns SPRET_SUCCESS if spell is successfully cast for purposes of -// exercising, SPRET_FAIL otherwise, or SPRET_ABORT if the player cancelled -// the casting. -// Not all of these are actually real spells; invocations, decks, rods or misc. -// effects might also land us here. -// Others are currently unused or unimplemented. +/** + * Handles damage from corrupted magic effects. + * + * Currently only from the Majin-Bo. + * + * @param spell The type of spell that was just cast. + **/ +static void _spellcasting_corruption(spell_type spell) +{ + // never kill the player (directly) + int hp_cost = min(you.spell_hp_cost() * spell_mana(spell), you.hp - 1); + const char * source = NULL; + if (player_equip_unrand(UNRAND_MAJIN)) + source = "the Majin-Bo"; // for debugging + ouch(hp_cost, NON_MONSTER, KILLED_BY_SOMETHING, source); +} + +/** + * Targets and fires player-cast spells & spell-like effects. + * + * Not all of these are actually real spells; invocations, decks, rods or misc. + * effects might also land us here. + * Others are currently unused or unimplemented. + * + * @param spell The type of spell being cast. + * @param powc Spellpower. + * @param allow_fail Whether spell-fail chance applies. + * @param check_range ...I'm not sure this actually does anything + * @return SPRET_SUCCESS if spell is successfully cast for purposes of + * exercising, SPRET_FAIL otherwise, or SPRET_ABORT if the player cancelled + * the casting. + **/ spret_type your_spells(spell_type spell, int powc, bool allow_fail, bool check_range) { @@ -1385,7 +1421,13 @@ spret_type your_spells(spell_type spell, int powc, const bool old_target = actor_at(beam.target); - switch (_do_cast(spell, powc, spd, beam, god, potion, check_range, fail)) + spret_type cast_result = _do_cast(spell, powc, spd, beam, god, + potion, check_range, fail); + + if (cast_result != SPRET_ABORT && you.spell_hp_cost() && allow_fail) + _spellcasting_corruption(spell); + + switch (cast_result) { case SPRET_SUCCESS: { @@ -1465,7 +1507,14 @@ spret_type your_spells(spell_type spell, int powc, return SPRET_SUCCESS; } -// Special-cased after-effects. +/** + * Handles special-cased aftereffects of spellcasting. + * + * Currently handles damage from casting Pain, since that occurs before the + * spellcast, whether or not it's successful, as long as it's not aborted. + * + * @param spell The type of spell that was just cast. + **/ static void _spell_zap_effect(spell_type spell) { // Casting pain costs 1 hp. diff --git a/crawl-ref/source/spl-util.cc b/crawl-ref/source/spl-util.cc index 3ff9ffb7fd..e812ef0533 100644 --- a/crawl-ref/source/spl-util.cc +++ b/crawl-ref/source/spl-util.cc @@ -1190,16 +1190,25 @@ bool spell_is_useless(spell_type spell, bool transient) return false; } -// This function takes a spell, and determines what color it should be -// highlighted with. You shouldn't have to touch this unless you want -// to add new highlighting options. +/** + * Determines what color a spell should be highlighted with. + * + * @param spell The type of spell to be colored. + * @param default_color Color to be used if the spell is unremarkable. + * @param transient If true, check if spell is temporarily useless. + * @param rod_spell If the spell being evoked from a rod. + * @return The color to highlight the spell. + */ int spell_highlight_by_utility(spell_type spell, int default_color, bool transient, bool rod_spell) { // If your god hates the spell, that // overrides all other concerns - if (god_hates_spell(spell, you.religion, rod_spell)) + if (god_hates_spell(spell, you.religion, rod_spell) + || is_good_god(you.religion) && you.spellcasting_unholy()) + { return COL_FORBIDDEN; + } if (_spell_is_empowered(spell) && !rod_spell) default_color = COL_EMPOWERED; |