From 22e375d42eabd760283d4e0d8ea42c65e66108af Mon Sep 17 00:00:00 2001 From: j-p-e-g Date: Tue, 10 Jun 2008 10:28:10 +0000 Subject: Modify Evaporate and Stinking Cloud to prompt when firing through allies. Note: This does still not handle the actual clouds, just the basic beam. git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@5701 c06c8d41-db1a-0410-9941-cceddc491573 --- crawl-ref/source/beam.cc | 112 +++++++++++++++++++++--------------------- crawl-ref/source/itemname.cc | 113 +++++++++++++++++++++++-------------------- crawl-ref/source/itemname.h | 4 +- crawl-ref/source/misc.cc | 7 ++- crawl-ref/source/spells1.cc | 50 +++++++++++++------ crawl-ref/source/spells1.h | 2 +- crawl-ref/source/spells3.cc | 2 +- crawl-ref/source/spells4.cc | 64 +++++++++++++++--------- crawl-ref/source/spl-cast.cc | 10 ++-- 9 files changed, 207 insertions(+), 157 deletions(-) (limited to 'crawl-ref') diff --git a/crawl-ref/source/beam.cc b/crawl-ref/source/beam.cc index d886ec06c9..77f3c7dffa 100644 --- a/crawl-ref/source/beam.cc +++ b/crawl-ref/source/beam.cc @@ -200,7 +200,7 @@ void zap_animation( int colour, const monsters *mon, bool force ) } } -// special front function for zap_animation to interpret enchantment flavours +// Special front function for zap_animation to interpret enchantment flavours. static void _ench_animation( int flavour, const monsters *mon, bool force ) { const int elem = (flavour == BEAM_HEALING) ? EC_HEAL : @@ -1675,7 +1675,7 @@ static void _zappy( zap_type z_type, int power, bolt &pbolt ) * Now handles all beamed/thrown items and spells, tracers, and their effects. * item is used for items actually thrown/launched * - * if item is NULL, there is no physical object being thrown that could + * If item is NULL, there is no physical object being thrown that could * land on the ground. */ @@ -1891,9 +1891,7 @@ void fire_beam( bolt &pbolt, item_def *item, bool drop_item ) // monsters have no chance to dodge or block such // a beam, and we want to avoid silly messages. if (tx == pbolt.target_x && ty == pbolt.target_y) - { beamTerminate = _beam_term_on_target(pbolt, tx, ty); - } // Affect the cell, except in the special case noted // above -- affect() will early out if something gets @@ -1910,9 +1908,7 @@ void fire_beam( bolt &pbolt, item_def *item, bool drop_item ) } if (!pbolt.affects_nothing) - { rangeRemaining -= affect(pbolt, tx, ty, item); - } if (random_beam) { @@ -2186,7 +2182,7 @@ int mons_adjust_flavoured( monsters *monster, bolt &pbolt, } else { - // early out for tracer/no side effects + // Early out for tracer/no side effects. if (!doFlavouredEffects) return (hurted); @@ -2360,8 +2356,9 @@ static bool _monster_resists_mass_enchantment(monsters *monster, if (check_mons_resist_magic( monster, pow )) { - simple_monster_message(monster, mons_immune_magic(monster) ? - " is unaffected." : " resists."); + simple_monster_message(monster, + mons_immune_magic(monster)? " is unaffected." + : " resists."); return (true); } } @@ -2376,8 +2373,9 @@ static bool _monster_resists_mass_enchantment(monsters *monster, if (check_mons_resist_magic( monster, pow )) { - simple_monster_message(monster, mons_immune_magic(monster) ? - " is unaffected." : " resists."); + simple_monster_message(monster, + mons_immune_magic(monster)? " is unaffected." + : " resists."); return (true); } } @@ -2476,9 +2474,9 @@ bool mass_enchantment( enchant_type wh_enchant, int pow, int origin, // * Returns MON_AFFECTED in all other cases (already enchanted, etc). int mons_ench_f2(monsters *monster, bolt &pbolt) { - switch (pbolt.flavour) /* put in magic resistance */ + switch (pbolt.flavour) // put in magic resistance { - case BEAM_SLOW: /* 0 = slow monster */ + case BEAM_SLOW: // try to remove haste, if monster is hasted if (monster->del_ench(ENCH_HASTE)) { @@ -2504,7 +2502,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) } return (MON_AFFECTED); - case BEAM_HASTE: // 1 = haste + case BEAM_HASTE: if (monster->del_ench(ENCH_SLOW)) { if (simple_monster_message(monster, " is no longer moving slowly.")) @@ -2513,7 +2511,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) return (MON_AFFECTED); } - // not slowed, haste it + // Not slowed, haste it. if (!monster->has_ench(ENCH_HASTE) && !mons_is_stationary(monster) && monster->add_ench(ENCH_HASTE)) @@ -2526,7 +2524,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) } return (MON_AFFECTED); - case BEAM_HEALING: /* 2 = healing */ + case BEAM_HEALING: if (YOU_KILL(pbolt.thrower)) { if (cast_healing(5 + roll_dice( pbolt.damage ), @@ -2551,11 +2549,11 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) } return (MON_AFFECTED); - case BEAM_PARALYSIS: /* 3 = paralysis */ + case BEAM_PARALYSIS: _beam_paralyses_monster(pbolt, monster); return (MON_AFFECTED); - case BEAM_CONFUSION: /* 4 = confusion */ + case BEAM_CONFUSION: if (!mons_class_is_confusable(monster->type)) return (MON_UNAFFECTED); @@ -2569,7 +2567,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) } return (MON_AFFECTED); - case BEAM_INVISIBILITY: /* 5 = invisibility */ + case BEAM_INVISIBILITY: { // Store the monster name before it becomes an "it" -- bwr const std::string monster_name = monster->name(DESC_CAP_THE); @@ -2602,7 +2600,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) } return (MON_AFFECTED); } - case BEAM_CHARM: /* 9 = charm */ + case BEAM_CHARM: if (player_will_anger_monster(monster)) { simple_monster_message(monster, " is repulsed!"); @@ -2620,7 +2618,7 @@ int mons_ench_f2(monsters *monster, bolt &pbolt) default: break; - } /* end of switch (beam_colour) */ + } return (MON_AFFECTED); } // end mons_ench_f2() @@ -2736,20 +2734,19 @@ void _sticky_flame_monster( int mn, kill_category who, int levels ) } } -/* - * Used by monsters in "planning" which spell to cast. Fires off a "tracer" - * which tells the monster what it'll hit if it breathes/casts etc. - * - * The output from this tracer function is four variables in the beam struct: - * fr_count, foe_count: a count of how many friends and foes will (probably) - * be hit by this beam - * fr_power, foe_power: a measure of how many 'friendly' hit dice it will - * affect, and how many 'unfriendly' hit dice. - * - * Note that beam properties must be set, as the tracer will take them - * into account, as well as the monster's intelligence. - * - */ +// +// Used by monsters in "planning" which spell to cast. Fires off a "tracer" +// which tells the monster what it'll hit if it breathes/casts etc. +// +// The output from this tracer function is four variables in the beam struct: +// fr_count, foe_count: a count of how many friends and foes will (probably) +// be hit by this beam +// fr_power, foe_power: a measure of how many 'friendly' hit dice it will +// affect, and how many 'unfriendly' hit dice. +// +// Note that beam properties must be set, as the tracer will take them +// into account, as well as the monster's intelligence. +// void fire_tracer(const monsters *monster, bolt &pbolt) { // Don't fiddle with any input parameters other than tracer stuff! @@ -3044,13 +3041,13 @@ int affect(bolt &beam, int x, int y, item_def *item) if (grid_is_solid(grd[x][y])) { - if (beam.is_tracer) // tracers always stop on walls. + if (beam.is_tracer) // Tracers always stop on walls. return (BEAM_STOP); if (_affects_wall(beam, grd[x][y])) rangeUsed += _affect_wall(beam, x, y); - // if it's still a wall, quit - we can't do anything else to a + // If it's still a wall, quit - we can't do anything else to a // wall (but we still might be able to do something to any // monster inside the wall). Otherwise effects (like clouds, // etc.) are still possible. @@ -3375,7 +3372,7 @@ static void _affect_place_explosion_clouds(bolt &beam, int x, int y) cloud_type cl_type; int duration; - // first check: FIRE/COLD over water/lava + // First check: FIRE/COLD over water/lava. if (grd[x][y] == DNGN_LAVA && beam.flavour == BEAM_COLD || grid_is_watery(grd[x][y]) && _is_fiery(beam)) { @@ -4041,7 +4038,7 @@ static int _affect_player( bolt &beam, item_def *item ) } } - // sticky flame + // Sticky flame. if (beam.name == "sticky flame" && (you.species != SP_MOTTLED_DRACONIAN || you.experience_level < 6)) @@ -4053,22 +4050,22 @@ static int _affect_player( bolt &beam, item_def *item ) } } - // simple cases for scroll burns + // Simple cases for scroll burns. if (beam.flavour == BEAM_LAVA || beam.name == "hellfire") expose_player_to_element(BEAM_LAVA, burn_power); - // more complex (geez..) + // More complex (geez..) if (beam.flavour == BEAM_FIRE && beam.name != "ball of steam") expose_player_to_element(BEAM_FIRE, burn_power); - // potions exploding + // Potions exploding. if (beam.flavour == BEAM_COLD) expose_player_to_element(BEAM_COLD, burn_power); if (beam.flavour == BEAM_ACID) splash_with_acid(5); - // spore pops + // Spore pops. if (beam.in_explosion_phase && beam.flavour == BEAM_SPORE) expose_player_to_element(BEAM_SPORE, burn_power); @@ -4197,7 +4194,7 @@ static bool _beam_is_harmless(bolt &beam, monsters *mon) } } -// return amount of range used up by affectation of this monster +// Returns amount of range used up by affectation of this monster. static int _affect_monster(bolt &beam, monsters *mon, item_def *item) { const int tid = mgrd[mon->x][mon->y]; @@ -4261,15 +4258,16 @@ static int _affect_monster(bolt &beam, monsters *mon, item_def *item) { if (beam.is_tracer) { - if (beam.thrower == KILL_YOU_MISSILE) + if (beam.thrower == KILL_YOU_MISSILE || beam.thrower == KILL_YOU) { - if (!_beam_is_harmless(beam, mon)) + if (!beam.fr_count && !_beam_is_harmless(beam, mon)) { const bool target = (beam.target_x == mon->x && beam.target_y == mon->y); if (stop_attack_prompt(mon, true, target)) { + mpr("Test2"); beam.fr_count = 1; return (BEAM_STOP); } @@ -4428,9 +4426,9 @@ static int _affect_monster(bolt &beam, monsters *mon, item_def *item) // hurt by this beam. if (beam.is_tracer) { - if (beam.thrower == KILL_YOU_MISSILE) + if (beam.thrower == KILL_YOU_MISSILE || beam.thrower == KILL_YOU) { - if (!_beam_is_harmless(beam, mon)) + if (!beam.fr_count && !_beam_is_harmless(beam, mon)) { const bool target = (beam.target_x == mon->x && beam.target_y == mon->y); @@ -4812,7 +4810,7 @@ static int _affect_monster_enchantment(bolt &beam, monsters *mon) simple_monster_message(mon, " is enslaved."); - // wow, permanent enslaving + // Wow, permanent enslaving! mon->attitude = ATT_FRIENDLY; return (MON_AFFECTED); } @@ -4831,7 +4829,7 @@ static int _affect_monster_enchantment(bolt &beam, monsters *mon) return (MON_RESIST); } - // already friendly + // Already friendly. if (mons_friendly(mon)) return (MON_UNAFFECTED); @@ -4940,7 +4938,7 @@ static int _affect_monster_enchantment(bolt &beam, monsters *mon) return (MON_UNAFFECTED); } - // everything else? + // Everything else? if (!death_check) return (mons_ench_f2(mon, beam)); @@ -4958,7 +4956,7 @@ static int _affect_monster_enchantment(bolt &beam, monsters *mon) } -// extra range used on hit +// Extra range used on hit. static int _range_used_on_hit(bolt &beam) { // Non-beams can only affect one thing (player/monster). @@ -5000,11 +4998,11 @@ static int _range_used_on_hit(bolt &beam) if (beam.name == "hellfire") return (0); - // generic explosion + // Generic explosion. if (beam.is_explosion || beam.is_big_cloud) return (BEAM_STOP); - // plant spit + // Plant spit. if (beam.flavour == BEAM_ACID) return (BEAM_STOP); @@ -5376,7 +5374,7 @@ static void _explosion_cell(bolt &beam, int x, int y, bool drawOnly) beam.flavour = BEAM_RANDOM; } - // early out for tracer + // Early out for tracer. if (beam.is_tracer) return; @@ -5457,11 +5455,11 @@ static void _explosion_map( bolt &beam, int x, int y, // straightforward. static bool _nasty_beam(monsters *mon, bolt &beam) { - // take care of non-enchantments + // Take care of non-enchantments. if (beam.name[0] != '0') return (true); - // now for some non-hurtful enchantments + // Now for some non-hurtful enchantments. // No charming holy beings! if (beam.flavour == BEAM_CHARM) diff --git a/crawl-ref/source/itemname.cc b/crawl-ref/source/itemname.cc index 82bddb848e..7e7a897242 100644 --- a/crawl-ref/source/itemname.cc +++ b/crawl-ref/source/itemname.cc @@ -2209,9 +2209,6 @@ bool is_good_item(const item_def &item) if (is_emergency_item(item)) return (true); - if (is_useless_item(item) || is_dangerous_item(item)) - return (false); - switch (item.base_type) { case OBJ_SCROLLS: @@ -2238,7 +2235,7 @@ bool is_good_item(const item_def &item) } // Returns true if using an item only has harmful effects. -bool is_bad_item(const item_def &item) +bool is_bad_item(const item_def &item, bool temp) { if (!item_type_known(item)) return (false); @@ -2251,6 +2248,11 @@ bool is_bad_item(const item_def &item) case SCR_CURSE_ARMOUR: case SCR_CURSE_WEAPON: return (true); + case SCR_SUMMONING: + // Summoning will always produce hostile monsters if you worship + // a good god. (Use temp to allow autopickup to prevent monsters + // from reading it.) + return (temp && is_good_god(you.religion)); default: return (false); } @@ -2266,13 +2268,15 @@ bool is_bad_item(const item_def &item) case POT_DEGENERATION: case POT_DECAY: case POT_PARALYSIS: - // Well, strictly poison is not that bad if you're poison resistant... + return (true); case POT_POISON: case POT_STRONG_POISON: - return (true); + // Poison is not that bad if you're poison resistant. + return (!player_res_poison() + || !temp && you.species == SP_VAMPIRE); case POT_MUTATION: return (you.is_undead - && (you.species != SP_VAMPIRE + && (temp || you.species != SP_VAMPIRE || you.hunger_state < HS_SATIATED)); default: return (false); @@ -2297,7 +2301,7 @@ bool is_bad_item(const item_def &item) } // Returns true if using an item is risky but may occasionally be worthwhile. -bool is_dangerous_item(const item_def &item) +bool is_dangerous_item(const item_def &item, bool temp) { if (!item_type_known(item)) { @@ -2318,8 +2322,10 @@ bool is_dangerous_item(const item_def &item) switch (item.sub_type) { case SCR_IMMOLATION: - case SCR_TORMENT: return (true); + case SCR_TORMENT: + return (!player_mutation_level(MUT_TORMENT_RESISTANCE) + || !temp && you.species == SP_VAMPIRE); default: return (false); } @@ -2329,11 +2335,14 @@ bool is_dangerous_item(const item_def &item) case POT_MUTATION: // Only living characters can mutate. return (!you.is_undead - || you.species == SP_VAMPIRE + || temp && you.species == SP_VAMPIRE && you.hunger_state >= HS_SATIATED); default: return (false); } + case OBJ_BOOKS: + // The Tome of Destruction is certainly risky. + return (item.sub_type == BOOK_DESTRUCTION); default: return (false); } @@ -2355,7 +2364,7 @@ bool is_useless_item(const item_def &item, bool temp) return (false); // A bad item is always useless. - if (is_bad_item(item)) + if (is_bad_item(item, temp)) return (true); switch (item.sub_type) @@ -2364,6 +2373,9 @@ bool is_useless_item(const item_def &item, bool temp) case SCR_RANDOM_USELESSNESS: case SCR_NOISE: return (true); + case SCR_TORMENT: + return (player_mutation_level(MUT_TORMENT_RESISTANCE) + || !temp && you.species == SP_VAMPIRE); default: return (false); } @@ -2375,23 +2387,14 @@ bool is_useless_item(const item_def &item, bool temp) if (!item_type_known(item)) return (false); - switch (item.sub_type) - { - case POT_CONFUSION: - case POT_SLOWING: - case POT_DEGENERATION: - case POT_DECAY: - case POT_PARALYSIS: - case POT_POISON: - case POT_STRONG_POISON: - case POT_MUTATION: - // Certainly not useless if it can be used for attacking. - return (!player_knows_spell(SPELL_EVAPORATE)); - } + // No potion is useless if it can be used for Evaporate. + if (player_knows_spell(SPELL_EVAPORATE)) + return (false); + + // Apart from Evaporate, mummies can't use potions. if (you.species == SP_MUMMY) return (true); - // Do a second switch for the other potions. switch (item.sub_type) { case POT_BERSERK_RAGE: @@ -2401,7 +2404,7 @@ bool is_useless_item(const item_def &item, bool temp) case POT_GAIN_DEXTERITY: return (you.species == SP_GHOUL || temp && you.species == SP_VAMPIRE - && you.hunger_state >= HS_SATIATED); + && you.hunger_state < HS_SATIATED); case POT_LEVITATION: return (you.permanent_levitation() || you.permanent_flight()); @@ -2412,6 +2415,10 @@ bool is_useless_item(const item_def &item, bool temp) case POT_BLOOD_COAGULATED: return (!can_ingest(item.base_type, item.sub_type, true, true, false)); + case POT_POISON: + case POT_STRONG_POISON: + // If you're poison resistant, poison is only useless. + return player_res_poison(); } return (false); @@ -2420,43 +2427,45 @@ bool is_useless_item(const item_def &item, bool temp) if (!item_type_known(item)) return (false); - if (is_bad_item(item)) + if (is_bad_item(item, temp)) return (true); - if (you.species == SP_MUMMY || you.species == SP_GHOUL) + switch (item.sub_type) { - switch (item.sub_type) - { - case AMU_RAGE: - case RING_REGENERATION: - case RING_SUSTENANCE: - case RING_HUNGER: - case RING_LIFE_PROTECTION: - return (true); - } - } + case AMU_RAGE: + return (you.is_undead + && (!temp || you.species == SP_VAMPIRE + && you.hunger_state <= HS_SATIATED) + || you.religion == GOD_TROG); + + case RING_LIFE_PROTECTION: + case RING_HUNGER: + case RING_REGENERATION: + case RING_SUSTENANCE: + return (you.is_undead + && (!temp || you.species == SP_VAMPIRE + && you.hunger_state == HS_STARVING)); - if (item.sub_type == RING_SEE_INVISIBLE) + case RING_SEE_INVISIBLE: return (player_mutation_level(MUT_ACUTE_VISION)); - if (item.sub_type == RING_POISON_RESISTANCE) - { - return (you.species != SP_VAMPIRE - && player_mutation_level(MUT_POISON_RESISTANCE)); - } + case RING_POISON_RESISTANCE: + return (player_res_poison() + && (temp || you.species != SP_VAMPIRE)); - if (item.sub_type == AMU_CONTROLLED_FLIGHT) + case AMU_CONTROLLED_FLIGHT: return (player_genus(GENPC_DRACONIAN) || you.permanent_flight()); - if (you.religion == GOD_TROG) - { - return (item.sub_type == RING_WIZARDRY - || item.sub_type == AMU_RAGE); + case RING_WIZARDRY: + return (you.religion == GOD_TROG); + + default: + return (false); } - return (false); case OBJ_STAVES: if (you.religion == GOD_TROG && !item_is_rod(item)) return (true); + default: return (false); } @@ -2504,9 +2513,9 @@ const std::string menu_colour_item_prefix(const item_def &item, bool temp) prefixes.push_back("emergency_item"); if (is_good_item(item)) prefixes.push_back("good_item"); - if (is_dangerous_item(item)) + if (is_dangerous_item(item, temp)) prefixes.push_back("dangerous_item"); - if (is_bad_item(item)) + if (is_bad_item(item, temp)) prefixes.push_back("bad_item"); if (is_useless_item(item, temp)) prefixes.push_back("useless_item"); diff --git a/crawl-ref/source/itemname.h b/crawl-ref/source/itemname.h index 2bafdf2e59..3b4a674044 100644 --- a/crawl-ref/source/itemname.h +++ b/crawl-ref/source/itemname.h @@ -111,8 +111,8 @@ bool item_type_tried( const item_def &item ); bool is_interesting_item( const item_def& item ); bool is_emergency_item( const item_def& item ); bool is_good_item(const item_def &item); -bool is_bad_item(const item_def &item); -bool is_dangerous_item( const item_def& item ); +bool is_bad_item(const item_def &item, bool temp = false); +bool is_dangerous_item( const item_def& item, bool temp = false); bool is_useless_item(const item_def &item, bool temp = false); std::string make_name( unsigned long seed, bool all_caps ); diff --git a/crawl-ref/source/misc.cc b/crawl-ref/source/misc.cc index 90879d3d75..fadc4b16b3 100644 --- a/crawl-ref/source/misc.cc +++ b/crawl-ref/source/misc.cc @@ -2721,6 +2721,9 @@ std::string your_hand(bool plural) bool stop_attack_prompt(const monsters *mon, bool beam_attack, bool beam_target) { + if (you.confused()) + return (false); + bool retval = false; bool prompt = false; @@ -2734,7 +2737,7 @@ bool stop_attack_prompt(const monsters *mon, bool beam_attack, if (isFriendly) { - // listed in the form: "your rat", "Blork the orc" + // Listed in the form: "your rat", "Blork the orc". snprintf(info, INFO_SIZE, "Really %s %s%s?", (beam_attack) ? (beam_target) ? "fire at" : "fire through" @@ -2769,7 +2772,7 @@ bool stop_attack_prompt(const monsters *mon, bool beam_attack, prompt = true; } - if (!you.confused() && prompt) + if (prompt) retval = !yesno(info, false, 'n'); return (retval); diff --git a/crawl-ref/source/spells1.cc b/crawl-ref/source/spells1.cc index e151ef26bd..d4b474bd17 100644 --- a/crawl-ref/source/spells1.cc +++ b/crawl-ref/source/spells1.cc @@ -552,27 +552,45 @@ bool conjure_flame(int pow) return true; } -int stinking_cloud( int pow, bolt &beem ) +bool stinking_cloud( int pow, bolt &beem ) { - beem.name = "ball of vapour"; - beem.colour = GREEN; - beem.range = 6; - beem.rangeMax = 6; - beem.damage = dice_def( 1, 0 ); - beem.hit = 20; - beem.type = dchar_glyph(DCHAR_FIRED_ZAP); - beem.flavour = BEAM_MMISSILE; - beem.ench_power = pow; + beem.name = "ball of vapour"; + beem.colour = GREEN; + beem.range = 6; + beem.rangeMax = 6; + beem.damage = dice_def( 1, 0 ); + beem.hit = 20; + beem.type = dchar_glyph(DCHAR_FIRED_ZAP); + beem.flavour = BEAM_MMISSILE; + beem.ench_power = pow; beem.beam_source = MHITYOU; - beem.thrower = KILL_YOU; + beem.thrower = KILL_YOU; + beem.is_beam = false; beem.aux_source.clear(); - beem.is_beam = false; - beem.is_tracer = false; + // Fire tracer. + beem.source_x = you.x_pos; + beem.source_y = you.y_pos; + beem.can_see_invis = player_see_invis(); + beem.smart_monster = true; + beem.attitude = ATT_FRIENDLY; + beem.fr_count = 0; + beem.is_tracer = true; fire_beam(beem); - return (1); -} // end stinking_cloud() + if (beem.fr_count > 0) + { + // We don't want to fire through friendlies. + canned_msg(MSG_OK); + return (false); + } + + // Really fire. + beem.is_tracer = false; + fire_beam(beem); + + return (true); +} int cast_big_c(int pow, cloud_type cty, kill_category whose, bolt &beam) { @@ -590,7 +608,7 @@ void big_cloud(cloud_type cl_type, kill_category whose, static bool _mons_hostile(const monsters *mon) { - // needs to be done this way because of friendly/neutral enchantments + // Needs to be done this way because of friendly/neutral enchantments. return (!mons_friendly(mon) && !mons_neutral(mon)); } diff --git a/crawl-ref/source/spells1.h b/crawl-ref/source/spells1.h index 0a14e106b1..0e1ea589db 100644 --- a/crawl-ref/source/spells1.h +++ b/crawl-ref/source/spells1.h @@ -92,7 +92,7 @@ void cast_ring_of_flames(int power); bool conjure_flame(int pow); void extension(int pow); bool fireball(int power, bolt &beam); -int stinking_cloud(int pow, bolt &beam); +bool stinking_cloud(int pow, bolt &beam); void abjuration(int pow); // last updated 24may2000 {dlb} diff --git a/crawl-ref/source/spells3.cc b/crawl-ref/source/spells3.cc index bc8ed70904..f3974c099c 100644 --- a/crawl-ref/source/spells3.cc +++ b/crawl-ref/source/spells3.cc @@ -265,7 +265,7 @@ int airstrike(int power, dist &beam) behaviour_event(monster, ME_ANNOY, MHITYOU); if (mons_is_mimic( monster->type )) mimic_alert(monster); - } + } conduct.enabled = true; diff --git a/crawl-ref/source/spells4.cc b/crawl-ref/source/spells4.cc index 9ef2376bd2..bd58066c2c 100644 --- a/crawl-ref/source/spells4.cc +++ b/crawl-ref/source/spells4.cc @@ -1305,8 +1305,6 @@ bool backlight_monsters(int x, int y, int pow, int garbage) bool cast_evaporate(int pow, bolt& beem, int potion) { - struct dist spelld; - if (potion == -1) return (false); else if (you.inv[potion].base_type != OBJ_POTIONS) @@ -1316,22 +1314,21 @@ bool cast_evaporate(int pow, bolt& beem, int potion) return (false); } - beem.name = "potion"; - beem.colour = you.inv[potion].colour; - beem.range = 9; - beem.rangeMax = 9; - beem.type = dchar_glyph(DCHAR_FIRED_FLASK); + beem.name = "potion"; + beem.colour = you.inv[potion].colour; + beem.range = 9; + beem.rangeMax = 9; + beem.type = dchar_glyph(DCHAR_FIRED_FLASK); beem.beam_source = MHITYOU; - beem.thrower = KILL_YOU_MISSILE; + beem.thrower = KILL_YOU_MISSILE; + beem.is_beam = false; beem.aux_source.clear(); - beem.is_beam = false; - beem.is_tracer = false; - beem.hit = you.dex / 2 + roll_dice( 2, you.skills[SK_THROWING] / 2 + 1 ); - beem.damage = dice_def( 1, 0 ); // no damage, just producing clouds - beem.ench_power = pow; // used for duration only? + beem.hit = you.dex / 2 + roll_dice( 2, you.skills[SK_THROWING] / 2 + 1 ); + beem.damage = dice_def( 1, 0 ); // no damage, just producing clouds + beem.ench_power = pow; // used for duration only? - beem.flavour = BEAM_POTION_STINKING_CLOUD; + beem.flavour = BEAM_POTION_STINKING_CLOUD; switch (you.inv[potion].sub_type) { @@ -1341,6 +1338,7 @@ bool cast_evaporate(int pow, bolt& beem, int potion) break; case POT_DEGENERATION: + beem.effect_known = false; beem.flavour = (coinflip() ? BEAM_POTION_POISON : BEAM_POTION_MIASMA); beem.ench_power *= 2; break; @@ -1373,6 +1371,7 @@ bool cast_evaporate(int pow, bolt& beem, int potion) break; // stinking cloud // deliberate fall through case POT_BERSERK_RAGE: + beem.effect_known = false; beem.flavour = (coinflip() ? BEAM_POTION_FIRE : BEAM_POTION_STEAM); break; @@ -1382,17 +1381,19 @@ bool cast_evaporate(int pow, bolt& beem, int potion) case POT_GAIN_INTELLIGENCE: case POT_EXPERIENCE: case POT_MAGIC: + beem.effect_known = false; switch (random2(5)) { - case 0: beem.flavour = BEAM_POTION_FIRE; break; - case 1: beem.flavour = BEAM_POTION_COLD; break; - case 2: beem.flavour = BEAM_POTION_POISON; break; - case 3: beem.flavour = BEAM_POTION_MIASMA; break; - default: beem.flavour = BEAM_POTION_RANDOM; break; + case 0: beem.flavour = BEAM_POTION_FIRE; break; + case 1: beem.flavour = BEAM_POTION_COLD; break; + case 2: beem.flavour = BEAM_POTION_POISON; break; + case 3: beem.flavour = BEAM_POTION_MIASMA; break; + default: beem.flavour = BEAM_POTION_RANDOM; break; } break; default: + beem.effect_known = false; switch (random2(12)) { case 0: beem.flavour = BEAM_POTION_FIRE; break; @@ -1408,12 +1409,31 @@ bool cast_evaporate(int pow, bolt& beem, int potion) break; } + // Fire tracer. + beem.source_x = you.x_pos; + beem.source_y = you.y_pos; + beem.can_see_invis = player_see_invis(); + beem.smart_monster = true; + beem.attitude = ATT_FRIENDLY; + beem.fr_count = 0; + beem.is_tracer = true; + fire_beam(beem); + + if (beem.fr_count > 0) + { + // We don't want to fire through friendlies. + canned_msg(MSG_OK); + return (false); + } + if (coinflip()) exercise( SK_THROWING, 1 ); + // Really fire. + beem.is_tracer = false; fire_beam(beem); - // both old and new code use up a potion: + // Use up a potion. if (is_blood_potion(you.inv[potion])) remove_oldest_blood_potion(you.inv[potion]); @@ -1464,9 +1484,9 @@ void cast_fulsome_distillation( int powc ) return; } - const bool rotten = food_is_rotten(mitm[corpse]); + const bool rotten = food_is_rotten(mitm[corpse]); const bool big_monster = (mons_type_hit_dice( mitm[corpse].plus ) >= 5); - const bool power_up = (rotten && big_monster); + const bool power_up = (rotten && big_monster); potion_type pot_type = POT_WATER; diff --git a/crawl-ref/source/spl-cast.cc b/crawl-ref/source/spl-cast.cc index f202254d83..065c549315 100644 --- a/crawl-ref/source/spl-cast.cc +++ b/crawl-ref/source/spl-cast.cc @@ -938,9 +938,10 @@ spret_type your_spells(spell_type spell, int powc, bool allow_fail) (testbits(flags, SPFLAG_HELPFUL) ? TARG_FRIEND : TARG_ENEMY); targeting_type dir = - (testbits( flags, SPFLAG_TARGET ) ? DIR_TARGET : - testbits( flags, SPFLAG_GRID ) ? DIR_TARGET : - testbits( flags, SPFLAG_DIR ) ? DIR_DIR : DIR_NONE); + (testbits( flags, SPFLAG_TARGET ) ? DIR_TARGET : + testbits( flags, SPFLAG_GRID ) ? DIR_TARGET : + testbits( flags, SPFLAG_DIR ) ? DIR_DIR + : DIR_NONE); const char *prompt = get_spell_target_prompt(spell); if (spell == SPELL_EVAPORATE) @@ -1235,7 +1236,8 @@ spret_type your_spells(spell_type spell, int powc, bool allow_fail) break; case SPELL_MEPHITIC_CLOUD: - stinking_cloud(powc, beam); + if (!stinking_cloud(powc, beam)) + return (SPRET_ABORT); break; case SPELL_RING_OF_FLAMES: -- cgit v1.2.3-54-g00ecf