summaryrefslogtreecommitdiffstats
path: root/crawl-ref/source
diff options
context:
space:
mode:
Diffstat (limited to 'crawl-ref/source')
-rw-r--r--crawl-ref/source/enum.h1
-rw-r--r--crawl-ref/source/invent.cc21
-rw-r--r--crawl-ref/source/mon-util.cc4
-rw-r--r--crawl-ref/source/monplace.cc147
-rw-r--r--crawl-ref/source/religion.cc93
-rw-r--r--crawl-ref/source/spells4.cc9
-rw-r--r--crawl-ref/source/view.cc2
7 files changed, 166 insertions, 111 deletions
diff --git a/crawl-ref/source/enum.h b/crawl-ref/source/enum.h
index 970b0c7fe7..38dae10512 100644
--- a/crawl-ref/source/enum.h
+++ b/crawl-ref/source/enum.h
@@ -2180,6 +2180,7 @@ enum operation_types
OPER_FIRE = 'f',
OPER_PRAY = 'p',
OPER_EVOKE = 'E',
+ OPER_DESTROY = 'D',
OPER_ANY = 0
};
diff --git a/crawl-ref/source/invent.cc b/crawl-ref/source/invent.cc
index 90b915c74b..466352587e 100644
--- a/crawl-ref/source/invent.cc
+++ b/crawl-ref/source/invent.cc
@@ -1066,7 +1066,7 @@ static int _digit_to_index( char digit, operation_types oper )
if (is_valid_item(you.inv[i]))
{
const std::string& r(you.inv[i].inscription);
- /* note that r.size() is unsigned */
+ // Note that r.size() is unsigned.
for ( unsigned int j = 0; j + 2 < r.size(); ++j )
{
if ( r[j] == '@'
@@ -1092,13 +1092,13 @@ bool has_warning_inscription(const item_def& item,
if (r[i] == '!')
{
if (r[i+1] == iletter || r[i+1] == '*')
- return true;
+ return (true);
else if (oper == OPER_ZAP && r[i+1] == 'z') // for the 0.3.4. keys
- return true;
+ return (true);
}
}
- return false;
+ return (false);
}
// checks if current item (to be removed) has a warning inscription
@@ -1183,24 +1183,31 @@ static std::string _operation_verb(operation_types oper)
case OPER_FIRE: return "fire";
case OPER_PRAY: return "sacrifice";
case OPER_EVOKE: return "evoke";
+ case OPER_DESTROY: return "destroy";
case OPER_ANY:
default:
return "choose";
}
}
-/* return true if user OK'd it (or no warning), false otherwise */
+// Return true if user OK'd it (or no warning), false otherwise.
bool check_warning_inscriptions( const item_def& item,
operation_types oper )
{
if (is_valid_item( item ) && has_warning_inscription(item, oper) )
{
+ // When it's about destroying an item, don't even ask.
+ // If the player really wants to do that, they'll have
+ // to remove the inscription.
+ if (oper == OPER_DESTROY)
+ return (false);
+
if (oper == OPER_WEAR)
{
if (item.base_type != OBJ_ARMOUR)
return (true);
- // don't ask if item already worn
+ // Don't ask if item already worn.
int equip = you.equip[get_armour_slot(item)];
if (equip != -1 && item.link == equip)
return (_check_old_item_warning(item, oper));
@@ -1210,7 +1217,7 @@ bool check_warning_inscriptions( const item_def& item,
if (item.base_type != OBJ_JEWELLERY)
return (true);
- // don't ask if item already worn
+ // Don't ask if item already worn.
int equip = -1;
if (jewellery_is_amulet(item))
equip = you.equip[EQ_AMULET];
diff --git a/crawl-ref/source/mon-util.cc b/crawl-ref/source/mon-util.cc
index 104c77d3b3..bccde8e679 100644
--- a/crawl-ref/source/mon-util.cc
+++ b/crawl-ref/source/mon-util.cc
@@ -1209,7 +1209,9 @@ flight_type mons_flies(const monsters *mon)
return (mon->ghost->fly);
}
- const int type = mons_is_zombified(mon)? mons_zombie_base(mon) : mon->type;
+ const int type = mons_is_zombified(mon) ? mons_zombie_base(mon)
+ : mon->type;
+
const flight_type ret = mons_class_flies( type );
return (ret ? ret
: (_scan_mon_inv_randarts(mon, RAP_LEVITATE) > 0) ? FL_LEVITATE
diff --git a/crawl-ref/source/monplace.cc b/crawl-ref/source/monplace.cc
index 55b7e1eee2..83db1833da 100644
--- a/crawl-ref/source/monplace.cc
+++ b/crawl-ref/source/monplace.cc
@@ -45,9 +45,9 @@
#define BIG_BAND 20
static void _define_zombie( int mid, monster_type ztype,
- monster_type cs, int power );
+ monster_type cs, int power, coord_def pos );
static monster_type _band_member(band_type band, int power);
-static band_type choose_band(int mon_type, int power, int &band_size );
+static band_type _choose_band(int mon_type, int power, int &band_size );
// static int _place_monster_aux(int mon_type, beh_type behaviour, int target,
// int px, int py, int power, int extra,
// bool first_band_member, int dur = 0);
@@ -76,10 +76,12 @@ bool grid_compatible(dungeon_feature_type grid_wanted,
&& actual_grid <= DNGN_CLEAR_PERMAROCK_WALL);
}
+ // Restricted fountains during generation, so we don't monsters
+ // "trapped" in fountains for easy killing.
return (grid_wanted == actual_grid
|| (grid_wanted == DNGN_DEEP_WATER
&& (actual_grid == DNGN_SHALLOW_WATER
- || actual_grid == DNGN_FOUNTAIN_BLUE)));
+ || !generation && actual_grid == DNGN_FOUNTAIN_BLUE)));
}
// Can this monster survive on actual_grid?
@@ -90,13 +92,14 @@ bool monster_habitable_grid(const monsters *m,
dungeon_feature_type actual_grid)
{
// Zombified monsters enjoy the same habitat as their original.
- const int type = mons_is_zombified(m) ? mons_zombie_base(m) : m->type;
+ const int type = mons_is_zombified(m) ? mons_zombie_base(m)
+ : m->type;
return (monster_habitable_grid(type, actual_grid, mons_flies(m),
m->paralysed()));
}
-inline static bool mons_airborne(int mcls, int flies, bool paralysed)
+inline static bool _mons_airborne(int mcls, int flies, bool paralysed)
{
if (flies == -1)
flies = mons_class_flies(mcls);
@@ -124,7 +127,7 @@ bool monster_habitable_grid(int monster_class,
// [dshaligram] Flying creatures are all DNGN_FLOOR, so we
// only have to check for the additional valid grids of deep
// water and lava.
- if (mons_airborne(monster_class, flies, paralysed)
+ if (_mons_airborne(monster_class, flies, paralysed)
&& (actual_grid == DNGN_LAVA || actual_grid == DNGN_DEEP_WATER))
{
return (true);
@@ -151,9 +154,10 @@ bool monster_habitable_grid(int monster_class,
return (false);
}
-// Returns true if the monster can submerge in the given grid
+// Returns true if the monster can submerge in the given grid.
bool monster_can_submerge(const monsters *mons, dungeon_feature_type grid)
{
+ // Zombies of watery critters can not submerge.
switch (mons_habitat(mons))
{
case HT_WATER:
@@ -164,7 +168,7 @@ bool monster_can_submerge(const monsters *mons, dungeon_feature_type grid)
return (grid == DNGN_LAVA);
default:
- return false;
+ return (false);
}
}
@@ -189,7 +193,7 @@ static int _fuzz_mons_level(int level)
return (level);
}
-static void hell_spawn_random_monsters()
+static void _hell_spawn_random_monsters()
{
// Monster generation in the Vestibule drops off quickly.
const int taper_off_turn = 500;
@@ -214,7 +218,7 @@ void spawn_random_monsters()
{
if (player_in_branch(BRANCH_VESTIBULE_OF_HELL))
{
- hell_spawn_random_monsters();
+ _hell_spawn_random_monsters();
return;
}
@@ -354,7 +358,7 @@ monster_type pick_random_monster(const level_id &place,
return (mon_type);
}
-static bool can_place_on_trap(int mon_type, trap_type trap)
+static bool _can_place_on_trap(int mon_type, trap_type trap)
{
if (trap == TRAP_TELEPORT)
return (false);
@@ -377,13 +381,13 @@ bool drac_colour_incompatible(int drac, int colour)
return (drac == MONS_DRACONIAN_SCORCHER && colour == MONS_WHITE_DRACONIAN);
}
-static monster_type resolve_monster_type(monster_type mon_type,
- proximity_type proximity,
- monster_type base_type,
- coord_def &pos,
- unsigned mmask,
- dungeon_char_type *stair_type,
- int *lev_mons)
+static monster_type _resolve_monster_type(monster_type mon_type,
+ proximity_type proximity,
+ monster_type base_type,
+ coord_def &pos,
+ unsigned mmask,
+ dungeon_char_type *stair_type,
+ int *lev_mons)
{
if (mon_type == RANDOM_DRACONIAN)
{
@@ -437,7 +441,7 @@ static monster_type resolve_monster_type(monster_type mon_type,
int trap = trap_at_xy(pos.x, pos.y);
if (trap >= 0)
{
- if (!can_place_on_trap(mon_type, env.trap[trap].type))
+ if (!_can_place_on_trap(mon_type, env.trap[trap].type))
continue;
}
@@ -531,9 +535,9 @@ int place_monster(mgen_data mg, bool force_pos)
if (mg.use_position() && mgrd(mg.pos) != NON_MONSTER)
return (false);
- mg.cls = resolve_monster_type(mg.cls, mg.proximity, mg.base_type,
- mg.pos, mg.map_mask,
- &stair_type, &mg.power);
+ mg.cls = _resolve_monster_type(mg.cls, mg.proximity, mg.base_type,
+ mg.pos, mg.map_mask,
+ &stair_type, &mg.power);
if (mg.cls == MONS_PROGRAM_BUG)
return (false);
@@ -544,7 +548,7 @@ int place_monster(mgen_data mg, bool force_pos)
if (mg.permit_bands())
{
- const band_type band = choose_band(mg.cls, mg.power, band_size);
+ const band_type band = _choose_band(mg.cls, mg.power, band_size);
band_size ++;
for (int i = 1; i < band_size; i++)
band_monsters[i] = _band_member( band, mg.power );
@@ -579,8 +583,11 @@ int place_monster(mgen_data mg, bool force_pos)
// a) not occupied
// b) compatible
// c) in the 'correct' proximity to the player
+
+ const int htype = (mons_class_is_zombified(mg.cls) ? mg.base_type
+ : mg.cls);
dungeon_feature_type grid_wanted =
- habitat2grid( mons_habitat_by_type(mg.cls) );
+ habitat2grid( mons_habitat_by_type(htype) );
while (true)
{
@@ -589,11 +596,12 @@ int place_monster(mgen_data mg, bool force_pos)
return (false);
// Placement already decided for PROX_NEAR_STAIRS.
+ // Else choose a random point on the map.
if (mg.proximity != PROX_NEAR_STAIRS)
mg.pos = random_in_bounds();
- // Let's recheck these even for PROX_NEAR_STAIRS, just in case
- // occupied?
+ // Let's recheck these even for PROX_NEAR_STAIRS, just in case.
+ // Occupied?
if (mgrd(mg.pos) != NON_MONSTER || mg.pos == you.pos())
continue;
@@ -610,7 +618,7 @@ int place_monster(mgen_data mg, bool force_pos)
int trap = trap_at_xy(mg.pos.x, mg.pos.y);
if (trap >= 0)
{
- if (!can_place_on_trap(mg.cls, env.trap[trap].type))
+ if (!_can_place_on_trap(mg.cls, env.trap[trap].type))
continue;
}
@@ -629,9 +637,8 @@ int place_monster(mgen_data mg, bool force_pos)
case PROX_CLOSE_TO_PLAYER:
case PROX_AWAY_FROM_PLAYER:
- close_to_player =
- (distance(you.x_pos, you.y_pos,
- mg.pos.x, mg.pos.y) < 64);
+ close_to_player = (distance(you.x_pos, you.y_pos,
+ mg.pos.x, mg.pos.y) < 64);
if (mg.proximity == PROX_CLOSE_TO_PLAYER && !close_to_player
|| mg.proximity == PROX_AWAY_FROM_PLAYER && close_to_player)
@@ -659,7 +666,7 @@ int place_monster(mgen_data mg, bool force_pos)
}
shoved = true;
coord_def mpos = mg.pos;
- mg.pos = you.pos();
+ mg.pos = you.pos();
you.moveto(mpos);
}
proxOK = (pval > 0);
@@ -669,9 +676,9 @@ int place_monster(mgen_data mg, bool force_pos)
if (!proxOK)
continue;
- // cool.. passes all tests
+ // Cool.. passes all tests.
break;
- } // end while.. place first monster
+ } // end while... place first monster
}
id = _place_monster_aux(mg, true, force_pos);
@@ -680,7 +687,7 @@ int place_monster(mgen_data mg, bool force_pos)
if (id == -1)
return (id);
- // Message to player from stairwell/gate appearance?
+ // Message to player from stairwell/gate appearance.
if (see_grid(mg.pos) && mg.proximity == PROX_NEAR_STAIRS)
{
std::string msg;
@@ -748,11 +755,12 @@ static int _place_monster_aux( const mgen_data &mg,
dungeon_feature_type grid_wanted = DNGN_UNSEEN;
coord_def fpos;
- // gotta be able to pick an ID
+ // Gotta be able to pick an ID.
for (id = 0; id < MAX_MONSTERS; id++)
if (menv[id].type == -1)
break;
+ // Too many monsters on level?
if (id == MAX_MONSTERS)
return (-1);
@@ -793,14 +801,14 @@ static int _place_monster_aux( const mgen_data &mg,
// Don't generate monsters on top of teleport traps.
// (How do they get there?)
int trap = trap_at_xy(fpos.x, fpos.y);
- if (trap >= 0 && !can_place_on_trap(mg.cls, env.trap[trap].type))
+ if (trap >= 0 && !_can_place_on_trap(mg.cls, env.trap[trap].type))
continue;
- // cool.. passes all tests
+ // Cool.. passes all tests.
break;
}
- // did we really try 1000 times?
+ // Did we really try 1000 times?
if (i == 1000)
return (-1);
}
@@ -808,7 +816,7 @@ static int _place_monster_aux( const mgen_data &mg,
// Now, actually create the monster. (Wheeee!)
menv[id].type = mg.cls;
menv[id].base_monster = mg.base_type;
- menv[id].number = mg.number;
+ menv[id].number = mg.number;
menv[id].x = fpos.x;
menv[id].y = fpos.y;
@@ -818,7 +826,7 @@ static int _place_monster_aux( const mgen_data &mg,
// Generate a brand shiny new monster, or zombie.
if (mons_class_is_zombified(mg.cls))
- _define_zombie( id, mg.base_type, mg.cls, mg.power );
+ _define_zombie( id, mg.base_type, mg.cls, mg.power, fpos );
else
define_monster(id);
@@ -877,11 +885,11 @@ static int _place_monster_aux( const mgen_data &mg,
menv[id].wield_melee_weapon(false);
}
- // give manticores 8 to 16 spike volleys.
+ // Give manticores 8 to 16 spike volleys.
if (mg.cls == MONS_MANTICORE)
menv[id].number = 8 + random2(9);
- // set attitude, behaviour and target
+ // Set attitude, behaviour and target.
menv[id].attitude = ATT_HOSTILE;
menv[id].behaviour = mg.behaviour;
@@ -890,9 +898,8 @@ static int _place_monster_aux( const mgen_data &mg,
menv[id].foe_memory = 0;
- // setting attitude will always make the
- // monster wander.. if you want sleeping
- // hostiles, use BEH_SLEEP since the default
+ // Setting attitude will always make the monster wander...
+ // If you want sleeping hostiles, use BEH_SLEEP since the default
// attitude is hostile.
if (mg.behaviour > NUM_BEHAVIOURS)
{
@@ -949,12 +956,12 @@ static monster_type _pick_random_zombie()
}
static void _define_zombie( int mid, monster_type ztype,
- monster_type cs, int power )
+ monster_type cs, int power, coord_def pos )
{
+ monster_type cls = MONS_PROGRAM_BUG;
monster_type mons_sec2 = MONS_PROGRAM_BUG;
- int zombie_size = 0;
+ int zombie_size = 0;
bool ignore_rarity = false;
- monster_type cls = MONS_PROGRAM_BUG;
if (power > 27)
power = 27;
@@ -998,6 +1005,11 @@ static void _define_zombie( int mid, monster_type ztype,
{
cls = _pick_random_zombie();
+ // Actually pick a monster that is happy where we want to put it.
+ // Fish zombies on land are helpless and uncool.
+ if (!monster_habitable_grid(cls, grd(pos)))
+ continue;
+
// On certain branches, zombie creation will fail if we use
// the mons_rarity() functions, because (for example) there
// are NO zombifiable "native" abyss creatures. Other branches
@@ -1032,7 +1044,7 @@ static void _define_zombie( int mid, monster_type ztype,
// Size must match, but you can make a spectral thing out
// of anything.
- if (mons_zombie_size(cls) != zombie_size && zombie_size != -1)
+ if (zombie_size != -1 && mons_zombie_size(cls) != zombie_size)
continue;
// Skeletal or icy draconians shouldn't be coloured.
@@ -1052,8 +1064,8 @@ static void _define_zombie( int mid, monster_type ztype,
// Check for rarity.. and OOD - identical to mons_place()
int level, diff, chance;
- level = mons_level( cls ) - 4;
- diff = level - power;
+ level = mons_level( cls ) - 4;
+ diff = level - power;
chance = (ignore_rarity) ? 100
: mons_rarity(cls) - (diff * diff) / 2;
@@ -1071,21 +1083,22 @@ static void _define_zombie( int mid, monster_type ztype,
relax++;
}
- // set type and secondary appropriately
+ // Set type and secondary appropriately.
menv[mid].base_monster = cls;
mons_sec2 = cls;
}
else
{
menv[mid].base_monster = mons_species(ztype);
- mons_sec2 = menv[mid].base_monster;
+ mons_sec2 = menv[mid].base_monster;
}
+ // Set type to the base type to calculate appropriate stats.
menv[mid].type = menv[mid].base_monster;
define_monster(mid);
- menv[mid].hit_points = hit_points( menv[mid].hit_dice, 6, 5 );
+ menv[mid].hit_points = hit_points( menv[mid].hit_dice, 6, 5 );
menv[mid].max_hit_points = menv[mid].hit_points;
menv[mid].ac -= 2;
@@ -1105,6 +1118,7 @@ static void _define_zombie( int mid, monster_type ztype,
menv[mid].speed_increment = 70;
+ // Now override type with the required type.
if (cs == MONS_ZOMBIE_SMALL || cs == MONS_ZOMBIE_LARGE)
{
menv[mid].type = ((mons_zombie_size(menv[mid].base_monster) == Z_BIG)
@@ -1112,7 +1126,7 @@ static void _define_zombie( int mid, monster_type ztype,
}
else if (cs == MONS_SKELETON_SMALL || cs == MONS_SKELETON_LARGE)
{
- menv[mid].hit_points = hit_points( menv[mid].hit_dice, 5, 4 );
+ menv[mid].hit_points = hit_points( menv[mid].hit_dice, 5, 4 );
menv[mid].max_hit_points = menv[mid].hit_points;
menv[mid].ac -= 4;
@@ -1131,24 +1145,24 @@ static void _define_zombie( int mid, monster_type ztype,
else if (cs == MONS_SIMULACRUM_SMALL || cs == MONS_SIMULACRUM_LARGE)
{
// Simulacrum aren't tough, but you can create piles of them. -- bwr
- menv[mid].hit_points = hit_points( menv[mid].hit_dice, 1, 4 );
+ menv[mid].hit_points = hit_points( menv[mid].hit_dice, 1, 4 );
menv[mid].max_hit_points = menv[mid].hit_points;
menv[mid].type = ((mons_zombie_size( menv[mid].base_monster ) == Z_BIG)
? MONS_SIMULACRUM_LARGE : MONS_SIMULACRUM_SMALL);
}
else if (cs == MONS_SPECTRAL_THING)
{
- menv[mid].hit_points = hit_points( menv[mid].hit_dice, 4, 4 );
+ menv[mid].hit_points = hit_points( menv[mid].hit_dice, 4, 4 );
menv[mid].max_hit_points = menv[mid].hit_points;
- menv[mid].ac += 4;
- menv[mid].type = MONS_SPECTRAL_THING;
+ menv[mid].ac += 4;
+ menv[mid].type = MONS_SPECTRAL_THING;
}
menv[mid].base_monster = mons_sec2;
- menv[mid].colour = mons_class_colour(cs);
+ menv[mid].colour = mons_class_colour(cs);
}
-static band_type choose_band( int mon_type, int power, int &band_size )
+static band_type _choose_band( int mon_type, int power, int &band_size )
{
// init
band_size = 0;
@@ -1723,7 +1737,7 @@ static monster_type _band_member(band_type band, int power)
return (mon_type);
}
-static int ood_limit()
+static int _ood_limit()
{
return Options.ood_interesting;
}
@@ -1753,7 +1767,7 @@ void mark_interesting_monst(struct monsters* monster, beh_type behaviour)
}
else if (you.where_are_you == BRANCH_MAIN_DUNGEON
&& you.level_type == LEVEL_DUNGEON
- && mons_level(monster->type) >= you.your_level + ood_limit()
+ && mons_level(monster->type) >= you.your_level + _ood_limit()
&& mons_level(monster->type) < 99
&& !(monster->type >= MONS_EARTH_ELEMENTAL
&& monster->type <= MONS_AIR_ELEMENTAL)
@@ -1768,7 +1782,7 @@ void mark_interesting_monst(struct monsters* monster, beh_type behaviour)
// PUBLIC FUNCTION -- mons_place().
-static monster_type pick_zot_exit_defender()
+static monster_type _pick_zot_exit_defender()
{
if (one_chance_in(11))
return (MONS_PANDEMONIUM_DEMON);
@@ -1813,7 +1827,7 @@ int mons_place( mgen_data mg )
if (you.char_direction == GDT_ASCENDING && mg.cls == RANDOM_MONSTER
&& you.level_type == LEVEL_DUNGEON && !mg.summoned())
{
- mg.cls = pick_zot_exit_defender();
+ mg.cls = _pick_zot_exit_defender();
mg.flags |= MG_PERMIT_BANDS;
}
@@ -2080,8 +2094,7 @@ bool empty_surrounds(int emx, int emy, dungeon_feature_type spc_wanted,
if (mgrd[tx][ty] != NON_MONSTER)
continue;
- // players won't summon out of LOS, or past transparent
- // walls.
+ // Players won't summon out of LOS, or past transparent walls.
if (!see_grid_no_trans(tx, ty) && playerSummon)
continue;
diff --git a/crawl-ref/source/religion.cc b/crawl-ref/source/religion.cc
index 6ce4951b70..05511e8693 100644
--- a/crawl-ref/source/religion.cc
+++ b/crawl-ref/source/religion.cc
@@ -2756,6 +2756,13 @@ bool ely_destroy_weapons()
continue;
}
+ if (!check_warning_inscriptions(mitm[i], OPER_DESTROY))
+ {
+ mpr("Won't destroy {!D} inscribed item.");
+ i = next;
+ continue;
+ }
+
const int value = item_value( mitm[i], true );
#ifdef DEBUG_DIAGNOSTICS
mprf(MSGCH_DIAGNOSTICS, "Destroyed weapon value: %d", value);
@@ -2775,6 +2782,7 @@ bool ely_destroy_weapons()
_print_sacrifice_message(GOD_ELYVILON, mitm[i], pgain);
if (is_evil_weapon)
{
+ // Print this is addition to the above!
simple_god_message(" welcomes the destruction of this evil weapon.",
GOD_ELYVILON);
}
@@ -2817,41 +2825,48 @@ bool trog_burn_books()
for (int xpos = you.x_pos - 8; xpos < you.x_pos + 8; xpos++)
for (int ypos = you.y_pos - 8; ypos < you.y_pos + 8; ypos++)
{
- // checked above
- if (xpos == you.x_pos && ypos == you.y_pos)
- continue;
-
- // burn only squares in sight
- if (!see_grid(xpos, ypos))
- continue;
-
- // if a grid is blocked, books lying there will be ignored
- // allow bombing of monsters
- const int cloud = env.cgrid[xpos][ypos];
- if (grid_is_solid(grd[ xpos ][ ypos ]) ||
-// mgrd[ xpos ][ ypos ] != NON_MONSTER ||
- (cloud != EMPTY_CLOUD && env.cloud[cloud].type != CLOUD_FIRE))
- {
- continue;
- }
+ // Checked above.
+ if (xpos == you.x_pos && ypos == you.y_pos)
+ continue;
- int count = 0;
- int rarity = 0;
- i = igrd[xpos][ypos];
- while (i != NON_ITEM)
- {
- const int next = mitm[i].link; // in case we can't get it later.
+ // Burn only squares in sight.
+ if (!see_grid(xpos, ypos))
+ continue;
- if (mitm[i].base_type != OBJ_BOOKS
- || mitm[i].sub_type == BOOK_MANUAL
- || mitm[i].sub_type == BOOK_DESTRUCTION)
- {
- i = next;
- continue;
- }
+ // If a grid is blocked, books lying there will be ignored.
+ // Allow bombing of monsters.
+ const int cloud = env.cgrid[xpos][ypos];
+ if (grid_is_solid(grd[ xpos ][ ypos ])
+ || cloud != EMPTY_CLOUD && env.cloud[cloud].type != CLOUD_FIRE)
+ {
+ continue;
+ }
+
+ int count = 0;
+ int rarity = 0;
+ i = igrd[xpos][ypos];
+ while (i != NON_ITEM)
+ {
+ const int next = mitm[i].link; // in case we can't get it later
+
+ if (mitm[i].base_type != OBJ_BOOKS
+ || mitm[i].sub_type == BOOK_MANUAL
+ || mitm[i].sub_type == BOOK_DESTRUCTION)
+ {
+ i = next;
+ continue;
+ }
+
+ // Ignore {!D} inscribed books.
+ if (!check_warning_inscriptions(mitm[i], OPER_DESTROY))
+ {
+ mpr("Won't ignite {!D} inscribed book.");
+ i = next;
+ continue;
+ }
rarity += book_rarity(mitm[i].sub_type);
- // piety increases by 2 for books never picked up, else by 1
+ // Piety increases by 2 for books never picked up, else by 1.
if (mitm[i].flags & ISFLAG_DROPPED
|| mitm[i].flags & ISFLAG_THROWN)
{
@@ -4854,8 +4869,16 @@ void offer_items()
continue;
}
- if ( _is_risky_sacrifice(item)
- || item.inscription.find("=p") != std::string::npos)
+ // Ignore {!D} inscribed items.
+ if (!check_warning_inscriptions(item, OPER_DESTROY))
+ {
+ mpr("Won't sacrifice {!D} inscribed item.");
+ i = next;
+ continue;
+ }
+
+ if (_is_risky_sacrifice(item)
+ || item.inscription.find("=p") != std::string::npos)
{
const std::string msg =
"Really sacrifice " + item.name(DESC_NOCAP_A) + "?";
@@ -4884,8 +4907,8 @@ void offer_items()
you.attribute[ATTR_CARD_COUNTDOWN]);
#endif
}
- if ((item.base_type == OBJ_CORPSES &&
- one_chance_in(2+you.piety/50))
+ if (item.base_type == OBJ_CORPSES
+ && one_chance_in(2+you.piety/50)
// Nemelex piety gain is fairly fast...at least
// when you have low piety.
|| value/2 >= random2(30 + you.piety/2))
diff --git a/crawl-ref/source/spells4.cc b/crawl-ref/source/spells4.cc
index 22def56e72..5d3962aed9 100644
--- a/crawl-ref/source/spells4.cc
+++ b/crawl-ref/source/spells4.cc
@@ -482,6 +482,15 @@ void cast_sticks_to_snakes(int pow)
return;
}
+ // Don't enchant sticks marked with {!D}.
+ if (!check_warning_inscriptions(you.inv[ weapon ], OPER_DESTROY))
+ {
+ mprf("%s feel%s slithery for a moment!",
+ you.inv[weapon].name(DESC_CAP_YOUR).c_str(),
+ you.inv[weapon].quantity > 1 ? "s" : "");
+ return;
+ }
+
const beh_type beha = item_cursed(you.inv[ weapon ]) ? BEH_HOSTILE
: BEH_FRIENDLY;
const unsigned short hitting = (beha == BEH_HOSTILE) ? MHITYOU
diff --git a/crawl-ref/source/view.cc b/crawl-ref/source/view.cc
index e0d7150883..cf62ba37e1 100644
--- a/crawl-ref/source/view.cc
+++ b/crawl-ref/source/view.cc
@@ -1023,7 +1023,7 @@ void handle_monster_shouts(monsters* monster, bool force)
{
; // No "visual shout" defined for silent monster, do nothing.
}
- else if (msg == "") // S_SILENT handled above
+ else if (msg == "") // Still nothing found?
{
msg::streams(MSGCH_DIAGNOSTICS)
<< "No shout entry for default shout type '"