summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorj-p-e-g <j-p-e-g@c06c8d41-db1a-0410-9941-cceddc491573>2008-04-28 19:08:03 +0000
committerj-p-e-g <j-p-e-g@c06c8d41-db1a-0410-9941-cceddc491573>2008-04-28 19:08:03 +0000
commit1e14066ec4bae72628883a11e60460b6794645d0 (patch)
treec8cc530cc264af07d8c73510634da75c8f0886d4
parentb578218b05ae153f3425278bedbb8efca48e259e (diff)
downloadcrawl-ref-1e14066ec4bae72628883a11e60460b6794645d0.tar.gz
crawl-ref-1e14066ec4bae72628883a11e60460b6794645d0.zip
Fix 1951264: Buggy uniques' wielding messages.
Fix named orcs getting no descriptions. The descriptions will have to be tweaked, probably using lua, to allow for friendly orcs. The descriptions for orc priests look particularly out of place with Beogh. Viewing friendlies now also lists their quiver and alternate weapon. Dualwielders now never will pick up shields, and single wielders will drop their shield if they wield a two-handed weapon. git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@4755 c06c8d41-db1a-0410-9941-cceddc491573
-rw-r--r--crawl-ref/source/describe.cc2
-rw-r--r--crawl-ref/source/directn.cc53
-rw-r--r--crawl-ref/source/mon-util.cc69
-rw-r--r--crawl-ref/source/religion.cc30
4 files changed, 111 insertions, 43 deletions
diff --git a/crawl-ref/source/describe.cc b/crawl-ref/source/describe.cc
index 754f1b6d1a..45832e5d35 100644
--- a/crawl-ref/source/describe.cc
+++ b/crawl-ref/source/describe.cc
@@ -2094,7 +2094,7 @@ void describe_monsters(monsters& mons)
if (mons_is_mimic(mons.type) && mons.type != MONS_GOLD_MIMIC)
description << getLongDescription("mimic");
else
- description << getLongDescription(mons.name(DESC_PLAIN));
+ description << getLongDescription(mons.name(DESC_PLAIN, false));
std::string symbol = "";
symbol += get_monster_data(mons.type)->showchar;
diff --git a/crawl-ref/source/directn.cc b/crawl-ref/source/directn.cc
index 9c70996b98..e1ef6b8547 100644
--- a/crawl-ref/source/directn.cc
+++ b/crawl-ref/source/directn.cc
@@ -2165,10 +2165,10 @@ static void describe_monster(const monsters *mon)
std::string get_monster_desc(const monsters *mon, bool full_desc,
description_level_type mondtype)
{
- std::string desc = mon->name(mondtype);
+ std::string desc = "";
+ if (mondtype != DESC_NONE)
+ desc = mon->name(mondtype);
- const int mon_arm = mon->inv[MSLOT_ARMOUR];
- const int mon_shd = mon->inv[MSLOT_SHIELD];
std::string weap = "";
if (mon->type != MONS_DANCING_WEAPON)
@@ -2183,22 +2183,65 @@ std::string get_monster_desc(const monsters *mon, bool full_desc,
if (full_desc)
{
+ const int mon_arm = mon->inv[MSLOT_ARMOUR];
+ const int mon_shd = mon->inv[MSLOT_SHIELD];
+ const int mon_qvr = mon->inv[MSLOT_MISSILE];
+ const int mon_alt = mon->inv[MSLOT_ALT_WEAPON];
+
+ const bool need_quiver = (mon_qvr != NON_ITEM && mons_friendly(mon));
+ const bool need_alt_wpn = (mon_alt != NON_ITEM && mons_friendly(mon)
+ && !mons_wields_two_weapons(mon));
+ bool found_sth = !weap.empty();
+
+
if (mon_arm != NON_ITEM)
{
desc += ", ";
- if (!weap.empty() && mon_shd == NON_ITEM)
+ if (found_sth && mon_shd == NON_ITEM && !need_quiver
+ && !need_alt_wpn)
+ {
desc += "and ";
+ }
desc += "wearing ";
desc += mitm[mon_arm].name(DESC_NOCAP_A);
+ if (!found_sth)
+ found_sth = true;
}
if (mon_shd != NON_ITEM)
{
desc += ", ";
- if (!weap.empty() || mon_arm != NON_ITEM)
+ if (found_sth && !need_quiver && !need_alt_wpn)
desc += "and ";
desc += "wearing ";
desc += mitm[mon_shd].name(DESC_NOCAP_A);
+ if (!found_sth)
+ found_sth = true;
+ }
+
+ // For friendly monsters, also list quivered missiles
+ // and alternate weapon.
+ if (mons_friendly(mon))
+ {
+ if (mon_qvr != NON_ITEM)
+ {
+ desc += ", ";
+ if (found_sth && !need_alt_wpn)
+ desc += "and ";
+ desc += "quivering ";
+ desc += mitm[mon_qvr].name(DESC_NOCAP_A);
+ if (!found_sth)
+ found_sth = true;
+ }
+
+ if (need_alt_wpn)
+ {
+ desc += ", ";
+ if (found_sth)
+ desc += "and ";
+ desc += "carrying ";
+ desc += mitm[mon_alt].name(DESC_NOCAP_A);
+ }
}
}
diff --git a/crawl-ref/source/mon-util.cc b/crawl-ref/source/mon-util.cc
index 076a9390ed..d9b3235069 100644
--- a/crawl-ref/source/mon-util.cc
+++ b/crawl-ref/source/mon-util.cc
@@ -180,11 +180,11 @@ void init_mon_name_cache()
// except looking up "rakshasa" and getting _FAKE breaks ?/M rakshasa.
if (Mon_Name_Cache.find(name) != Mon_Name_Cache.end())
{
- if (mon == MONS_RAKSHASA_FAKE ||
- mon == MONS_ARMOUR_MIMIC ||
- mon == MONS_SCROLL_MIMIC ||
- mon == MONS_POTION_MIMIC ||
- mon == MONS_ABOMINATION_LARGE)
+ if (mon == MONS_RAKSHASA_FAKE
+ || mon == MONS_ARMOUR_MIMIC
+ || mon == MONS_SCROLL_MIMIC
+ || mon == MONS_POTION_MIMIC
+ || mon == MONS_ABOMINATION_LARGE)
{
// keep previous entry
continue;
@@ -3194,6 +3194,16 @@ void monsters::pickup_message(const item_def &item, int near)
bool monsters::pickup(item_def &item, int slot, int near, bool force_merge)
{
+ // If a monster chooses a two-handed weapon as main weapon, it will
+ // first have to drop any shield it might wear.
+ // (Monsters will always favour damage over protection.)
+ if (slot == MSLOT_WEAPON && inv[MSLOT_SHIELD] != NON_ITEM
+ && hands_reqd(item, body_size(PSIZE_BODY)) == HANDS_TWO)
+ {
+ if (!drop_item(MSLOT_SHIELD, near))
+ return false;
+ }
+
if (inv[slot] != NON_ITEM)
{
if (items_stack(item, mitm[inv[slot]], force_merge))
@@ -3319,12 +3329,20 @@ static bool _is_signature_weapon(monsters *monster, const item_def &weapon)
bool monsters::pickup_melee_weapon(item_def &item, int near)
{
+ const bool is_2handed =
+ (hands_reqd(item, body_size(PSIZE_BODY)) == HANDS_TWO);
+ size_type size = body_size(PSIZE_BODY);
+
if (mons_wields_two_weapons(this))
{
+ const item_def *wpn = mslot_item(MSLOT_WEAPON);
+ const item_def *alt = mslot_item(MSLOT_ALT_WEAPON);
+
// If we have either weapon slot free, pick up the weapon.
- if (inv[MSLOT_WEAPON] == NON_ITEM)
+ if (!wpn && (!alt || hands_reqd(*alt, size) < HANDS_TWO && !is_2handed))
return pickup(item, MSLOT_WEAPON, near);
- else if (inv[MSLOT_ALT_WEAPON] == NON_ITEM)
+
+ if (!alt && (!wpn || hands_reqd(*wpn, size) < HANDS_TWO && !is_2handed))
return pickup(item, MSLOT_ALT_WEAPON, near);
}
@@ -3389,6 +3407,7 @@ bool monsters::pickup_throwable_weapon(item_def &item, int near)
bool monsters::wants_weapon(const item_def &weap) const
{
+ // monsters can't use fixed artefacts
if (is_fixed_artefact( weap ))
return (false);
@@ -3400,26 +3419,26 @@ bool monsters::wants_weapon(const item_def &weap) const
return (false);
}
- // XXX: Make this check dependent on creature size.
- // wimpy monsters (Kob, gob) shouldn't pick up halberds etc
- // of course, this also block knives {dlb}:
- if ((::mons_species(type) == MONS_KOBOLD
- || ::mons_species(type) == MONS_GOBLIN)
- && property( weap, PWPN_HIT ) <= 0)
- {
+ // Wimpy monsters (e.g. kobold, goblin) shouldn't pick up halberds etc.
+ if (!check_weapon_wieldable_size( weap, body_size(PSIZE_BODY) ))
return (false);
- }
- // Nobody picks up giant clubs:
+ // Nobody picks up giant clubs.
+ // Starting equipment is okay, of course.
if (weap.sub_type == WPN_GIANT_CLUB
|| weap.sub_type == WPN_GIANT_SPIKED_CLUB)
{
return (false);
}
+ // Demonid/undead monsters won't pick up holy wrath.
if (get_weapon_brand(weap) == SPWPN_HOLY_WRATH && mons_is_unholy(this))
return (false);
+ // Holy monsters won't pick up demonic weapons.
+ if (mons_holiness(this) == MH_HOLY && is_evil_item(weap))
+ return (false);
+
return (true);
}
@@ -3490,12 +3509,13 @@ bool monsters::pickup_armour(item_def &item, int near, bool force)
if (mslot == NUM_MONSTER_SLOTS)
return (false);
- // Don't pick up a shield if you're already wielding a two-hander, or
- // two weapons as a double-wielding monster.
- if (mslot == MSLOT_SHIELD && mslot_item(MSLOT_WEAPON)
- && (hands_reqd(*mslot_item(MSLOT_WEAPON), body_size(PSIZE_BODY))
- == HANDS_TWO
- || mslot_item(MSLOT_ALT_WEAPON) && mons_wields_two_weapons(this)))
+ // Monsters that are capable of dual wielding won't pick up shields.
+ // Neither will monsters that are already wielding a two-hander.
+ if (mslot == MSLOT_SHIELD
+ && (mons_wields_two_weapons(this)
+ || mslot_item(MSLOT_WEAPON)
+ && hands_reqd(*mslot_item(MSLOT_WEAPON), body_size(PSIZE_BODY))
+ == HANDS_TWO))
{
return (false);
}
@@ -3620,6 +3640,11 @@ bool monsters::pickup_wand(item_def &item, int near)
if (hit_dice >= 14)
return (false);
+ // This is the only type based restriction I can think of:
+ // Holy monsters won't pick up draining items.
+ if (mons_holiness(this) == MH_HOLY && item.sub_type == WAND_DRAINING)
+ return (false);
+
// If you already have a charged wand, don't bother.
// Otherwise, replace with a charged one.
if (item_def *wand = mslot_item(MSLOT_WAND))
diff --git a/crawl-ref/source/religion.cc b/crawl-ref/source/religion.cc
index 88b37366ab..3ad061bdfb 100644
--- a/crawl-ref/source/religion.cc
+++ b/crawl-ref/source/religion.cc
@@ -2551,15 +2551,15 @@ bool is_evil_item(const item_def& item)
int item_eff = item_special_wield_effect(item);
retval = (is_demonic(item)
- || item.special == SPWPN_SCEPTRE_OF_ASMODEUS
- || item.special == SPWPN_STAFF_OF_DISPATER
- || item.special == SPWPN_SWORD_OF_CEREBOV
- || item_eff == SPWLD_CURSE
- || item_eff == SPWLD_TORMENT
- || item_eff == SPWLD_ZONGULDROK
- || item_brand == SPWPN_DRAINING
- || item_brand == SPWPN_PAIN
- || item_brand == SPWPN_VAMPIRICISM);
+ || item.special == SPWPN_SCEPTRE_OF_ASMODEUS
+ || item.special == SPWPN_STAFF_OF_DISPATER
+ || item.special == SPWPN_SWORD_OF_CEREBOV
+ || item_eff == SPWLD_CURSE
+ || item_eff == SPWLD_TORMENT
+ || item_eff == SPWLD_ZONGULDROK
+ || item_brand == SPWPN_DRAINING
+ || item_brand == SPWPN_PAIN
+ || item_brand == SPWPN_VAMPIRICISM);
}
break;
case OBJ_WANDS:
@@ -2570,18 +2570,18 @@ bool is_evil_item(const item_def& item)
break;
case OBJ_POTIONS:
retval = (item.sub_type == POT_BLOOD
- || item.sub_type == POT_BLOOD_COAGULATED);
+ || item.sub_type == POT_BLOOD_COAGULATED);
break;
case OBJ_BOOKS:
retval = (item.sub_type == BOOK_NECROMANCY
- || item.sub_type == BOOK_DEATH
- || item.sub_type == BOOK_UNLIFE
- || item.sub_type == BOOK_NECRONOMICON
- || item.sub_type == BOOK_DEMONOLOGY);
+ || item.sub_type == BOOK_DEATH
+ || item.sub_type == BOOK_UNLIFE
+ || item.sub_type == BOOK_NECRONOMICON
+ || item.sub_type == BOOK_DEMONOLOGY);
break;
case OBJ_STAVES:
retval = (item.sub_type == STAFF_DEATH
- || item.sub_type == STAFF_DEMONOLOGY);
+ || item.sub_type == STAFF_DEMONOLOGY);
break;
case OBJ_MISCELLANY:
retval = (item.sub_type == MISC_LANTERN_OF_SHADOWS);