1 /**
2  * @file
3  * @brief Monsters' starting equipment.
4 **/
5 
6 #include "AppHdr.h"
7 
8 #include "mon-gear.h"
9 
10 #include <algorithm>
11 
12 #include "artefact.h"
13 #include "art-enum.h"
14 #include "dungeon.h"
15 #include "item-name.h"
16 #include "item-prop.h"
17 #include "item-status-flag-type.h"
18 #include "items.h"
19 #include "libutil.h" // map_find
20 #include "mon-place.h"
21 #include "mpr.h"
22 #include "randbook.h" // roxanne, roxanne...
23 #include "religion.h" // upgrade_hepliaklqana_weapon
24 #include "state.h"
25 #include "tag-version.h"
26 #include "tilepick.h"
27 #include "unwind.h"
28 
_strip_item_ego(item_def & item)29 static void _strip_item_ego(item_def &item)
30 {
31     item.brand = 0; // SP{WPN,ARM,MSL}_NORMAL
32 
33     // Remove glow, since that might be because of the ego...
34     set_equip_desc(item, ISFLAG_NO_DESC);
35     // ...but give it back if it came from curses or plusses.
36     item_set_appearance(item);
37 }
38 
give_specific_item(monster * mon,int thing)39 void give_specific_item(monster* mon, int thing)
40 {
41     if (thing == NON_ITEM || thing == -1)
42         return;
43 
44     item_def &mthing = env.item[thing];
45     ASSERT(mthing.defined());
46 
47     dprf(DIAG_MONPLACE, "Giving %s to %s...", mthing.name(DESC_PLAIN).c_str(),
48          mon->name(DESC_PLAIN, true).c_str());
49 
50     mthing.pos.reset();
51     mthing.link = NON_ITEM;
52 
53     if (mon->undead_or_demonic() || mon->god == GOD_YREDELEMNUL)
54     {
55         convert2bad(mthing);
56         if (get_weapon_brand(mthing) == SPWPN_HOLY_WRATH)
57             _strip_item_ego(mthing);
58     }
59 
60     if (!is_artefact(mthing)
61         && (mthing.base_type == OBJ_WEAPONS
62          || mthing.base_type == OBJ_ARMOUR
63          || mthing.base_type == OBJ_MISSILES))
64     {
65         bool enchanted = mthing.plus;
66         // The item could either lose or gain brand after being generated,
67         // adjust the glowing flag.
68         if (!mthing.brand && !enchanted)
69             set_equip_desc(mthing, 0);
70         else if (mthing.brand && !get_equip_desc(mthing))
71             set_equip_desc(mthing, ISFLAG_GLOWING);
72     }
73 
74     unwind_var<int> save_speedinc(mon->speed_increment);
75     if (!mon->pickup_item(mthing, false, true))
76     {
77         dprf(DIAG_MONPLACE, "Destroying %s because %s doesn't want it!",
78              mthing.name(DESC_PLAIN, false, true).c_str(),
79              mon->name(DESC_PLAIN, true).c_str());
80         destroy_item(thing, true);
81         return;
82     }
83     if (!mthing.defined()) // missiles merged into an existing stack
84         return;
85     ASSERT(mthing.holding_monster() == mon);
86 
87     if (!mthing.appearance_initialized())
88         item_colour(mthing);
89 }
90 
give_specific_item(monster * mon,const item_def & tpl)91 void give_specific_item(monster* mon, const item_def& tpl)
92 {
93     int thing = get_mitm_slot();
94     if (thing == NON_ITEM)
95         return;
96 
97     env.item[thing] = tpl;
98     give_specific_item(mon, thing);
99 }
100 
_should_give_unique_item(monster * mon)101 static bool _should_give_unique_item(monster* mon)
102 {
103     // Don't give Natasha an item for dying.
104     return mon->type != MONS_NATASHA || !mon->props.exists("felid_revives");
105 }
106 
_give_book(monster * mon,int level)107 static void _give_book(monster* mon, int level)
108 {
109     if (mon->type == MONS_ROXANNE)
110     {
111         // Statue form books, heh.
112         const int which_book = (one_chance_in(3) ? BOOK_SLOTH
113                                                  : BOOK_STONE);
114 
115         const int thing_created = items(false, OBJ_BOOKS, which_book, level);
116 
117         if (thing_created == NON_ITEM)
118             return;
119 
120         // Maybe give Roxanne a random book containing Statue Form instead.
121         if (coinflip())
122             make_book_roxanne_special(&env.item[thing_created]);
123 
124         give_specific_item(mon, thing_created);
125     }
126 }
127 
_give_wand(monster * mon,int level)128 static void _give_wand(monster* mon, int level)
129 {
130     bool wand_allowed = mons_is_unique(mon->type)
131                         && !mons_class_flag(mon->type, M_NO_WAND)
132                         && _should_give_unique_item(mon);
133 
134     if (!wand_allowed)
135         return;
136 
137     bool give_wand = mons_class_flag(mon->type, M_ALWAYS_WAND)
138                      || one_chance_in(5);
139 
140     if (!give_wand)
141         return;
142 
143     // Don't give top-tier wands before 5 HD, except to Ijyb and not in sprint.
144     const bool no_high_tier =
145             (mon->get_experience_level() < 5
146                 || mons_class_flag(mon->type, M_NO_HT_WAND))
147             && (mon->type != MONS_IJYB || crawl_state.game_is_sprint());
148 
149     const int idx = items(false, OBJ_WANDS, OBJ_RANDOM, level);
150 
151     if (idx == NON_ITEM)
152         return;
153 
154     item_def& wand = env.item[idx];
155 
156     const char* rejection_reason =
157         (no_high_tier && is_high_tier_wand(wand.sub_type)) ? "high tier" :
158                                     !mon->likes_wand(wand) ?      "weak" :
159                                                                   nullptr;
160 
161     if (rejection_reason)
162     {
163         dprf(DIAG_MONPLACE,
164              "Destroying %s because %s doesn't want a %s wand.",
165              wand.name(DESC_A).c_str(),
166              mon->name(DESC_THE).c_str(),
167              rejection_reason);
168         destroy_item(idx, true);
169         return;
170     }
171 
172     wand.flags = 0;
173     give_specific_item(mon, idx);
174 }
175 
_give_potion(monster * mon,int level)176 static void _give_potion(monster* mon, int level)
177 {
178     if (mons_is_unique(mon->type) && one_chance_in(4)
179                 && _should_give_unique_item(mon))
180     {
181         const int thing_created = items(false, OBJ_POTIONS, OBJ_RANDOM,
182                                         level);
183 
184         if (thing_created == NON_ITEM)
185             return;
186 
187         env.item[thing_created].flags = 0;
188         give_specific_item(mon, thing_created);
189     }
190 }
191 
192 static item_def* make_item_for_monster(
193     monster* mons,
194     object_class_type base,
195     int subtype,
196     int level,
197     int allow_uniques = 0,
198     iflags_t flags = 0);
199 
200 typedef vector<pair<weapon_type, int>> weapon_list;
201 struct plus_range
202 {
203     int odds; ///<1/x chance of getting +[min,max] to weapon plus
204     int min, max;
205     int nrolls; ///< min 1
206 };
207 
208 struct mon_weapon_spec
209 {
210     /// weighted list of weapon types; NUM_WEAPONS -> no weapon
211     weapon_list types;
212     /// range of possible weapon enchant plusses; if nonzero, sets force_item
213     plus_range plusses;
214     /// weighted brand list; NUM_BRANDS -> no forced brand
215     vector<pair<brand_type, int>> brands;
216     /// extra 1/x chance to generate as ISPEC_GOOD_ITEM
217     int good_chance;
218 };
219 
220 /**
221  * Try to apply the given weapon spec to the given base item & generation
222  * parameters; randomly choose a weapon type and, possibly, change other fields.
223  *
224  * @param spec              How to choose weapon type, plusses, brands, etc.
225  * @param item[out]         An item to be populated with subtype and other
226  *                          fields, before or instead of a call to items().
227  * @param force_item[out]   Have we set something (plus, brand) that requires
228  *                          us to skip items()?
229  * @param level[out]        The item's quality level, if we want to override it.
230  * @return                  Did we choose a weapon type?
231  */
_apply_weapon_spec(const mon_weapon_spec & spec,item_def & item,bool & force_item,int & level)232 static bool _apply_weapon_spec(const mon_weapon_spec &spec, item_def &item,
233                                bool &force_item, int &level)
234 {
235 
236     const weapon_type *wpn_type
237         = random_choose_weighted(spec.types);
238     ASSERT(wpn_type);
239     if (*wpn_type == NUM_WEAPONS)
240         return false;
241 
242     item.base_type = OBJ_WEAPONS;
243     item.sub_type = *wpn_type;
244 
245     if (spec.plusses.odds)
246     {
247         if (one_chance_in(spec.plusses.odds))
248         {
249             const int rolls = max(1, spec.plusses.nrolls);
250             item.plus += random_range(spec.plusses.min, spec.plusses.max,
251                                       rolls);
252             force_item = true;
253         }
254     }
255     else // normal plusses (ignored if brand isn't set)
256         item.plus = determine_nice_weapon_plusses(level);
257 
258     if (spec.good_chance && one_chance_in(spec.good_chance))
259         level = ISPEC_GOOD_ITEM;
260 
261     const brand_type *brand = random_choose_weighted(spec.brands);
262     if (brand)
263     {
264         if (*brand != NUM_SPECIAL_WEAPONS)
265         {
266             set_item_ego_type(item, OBJ_WEAPONS, *brand);
267             force_item = true;
268         }
269     }
270     else if (force_item) // normal brand
271     {
272         set_item_ego_type(item, OBJ_WEAPONS,
273                           determine_weapon_brand(item, level));
274     }
275 
276     return true;
277 }
278 
279 /**
280  * Make a weapon for the given monster.
281  *
282  * @param mtyp          The type of monster; e.g. MONS_ORC_WARRIOR.
283  * @param level         The quality of the weapon to make, usually absdepth.
284  * @param melee_only    If this monster can be given both melee and ranged
285  *                      weapons, whether to restrict this to melee weapons.
286  * @return              The index of the newly-created weapon, or NON_ITEM if
287  *                      none was made.
288  */
make_mons_weapon(monster_type type,int level,bool melee_only)289 int make_mons_weapon(monster_type type, int level, bool melee_only)
290 {
291     rng::subgenerator item_rng;
292 
293     static const weapon_list GOBLIN_WEAPONS =
294     {   { WPN_DAGGER,           1 },
295         { WPN_CLUB,             1 }};
296     static const weapon_list GNOLL_WEAPONS = // total 30
297     {   { WPN_SPEAR,            8 },
298         { WPN_HALBERD,          4 },
299         { WPN_CLUB,             6 },
300         { WPN_WHIP,             6 },
301         { WPN_FLAIL,            6 } };
302     static const weapon_list ORC_WEAPONS = // total 525 (!)
303     {   { WPN_CLUB,            100 },
304         { WPN_DAGGER,           80 },
305         { WPN_FLAIL,            60 },
306         { WPN_SHORT_SWORD,      60 },
307         { WPN_HAND_AXE,         80 },
308         { WPN_WHIP,             45 },
309         { WPN_MACE,             40 },
310         { WPN_TRIDENT,          20 },
311         { WPN_FALCHION,         20 },
312         { WPN_WAR_AXE,          14 },
313         { WPN_MORNINGSTAR,      6 } };
314     static const weapon_list DE_KNIGHT_WEAPONS = // total 83 (?)
315     {   { WPN_LONG_SWORD,       22 },
316         { WPN_SHORT_SWORD,      22 },
317         { WPN_SCIMITAR,         17 },
318         { WPN_SHORTBOW,         17 },
319         { WPN_LONGBOW,          5 }, };
320     static const weapon_list DE_MAGE_WEAPONS =
321     {   { WPN_LONG_SWORD,       2 },
322         { WPN_SHORT_SWORD,      1 },
323         { WPN_RAPIER,           1 },
324         { WPN_DAGGER,           1 }, };
325     static const weapon_list DRAC_MAGE_WEAPONS = // XXX: merge with DE? ^
326     {   { WPN_LONG_SWORD,       2 },
327         { WPN_SHORT_SWORD,      1 },
328         { WPN_RAPIER,           1 },
329         { WPN_DAGGER,           1 },
330         { WPN_WHIP,             1 }, };
331     static const weapon_list NAGA_WEAPONS = // total 120
332     {   { WPN_LONG_SWORD,       10 },
333         { WPN_SHORT_SWORD,      10 },
334         { WPN_SCIMITAR,         10 },
335         { WPN_BATTLEAXE,        10 },
336         { WPN_HAND_AXE,         10 },
337         { WPN_HALBERD,          10 },
338         { WPN_GLAIVE,           10 },
339         { WPN_MACE,             10 },
340         { WPN_DIRE_FLAIL,       10 },
341         { WPN_TRIDENT,          10 },
342         { WPN_WAR_AXE,          9 },
343         { WPN_FLAIL,            9 },
344         { WPN_BROAD_AXE,        1 },
345         { WPN_MORNINGSTAR,      1 }, };
346     static const weapon_list ORC_KNIGHT_WEAPONS =
347     {   { WPN_GREAT_SWORD,      4 },
348         { WPN_LONG_SWORD,       4 },
349         { WPN_BATTLEAXE,        4 },
350         { WPN_WAR_AXE,          4 },
351         { WPN_GREAT_MACE,       3 },
352         { WPN_DIRE_FLAIL,       2 },
353         { WPN_BARDICHE,         1 },
354         { WPN_GLAIVE,           1 },
355         { WPN_BROAD_AXE,        1 },
356         { WPN_HALBERD,          1 }, };
357     static const mon_weapon_spec ORC_KNIGHT_WSPEC =
358         { ORC_KNIGHT_WEAPONS, {4, 1, 3} };
359     static const mon_weapon_spec ORC_WARLORD_WSPEC =
360         { ORC_KNIGHT_WEAPONS, {4, 1, 3}, {}, 3 };
361     static const weapon_list IRON_WEAPONS =
362     {   { WPN_GREAT_MACE,       3 },
363         { WPN_DIRE_FLAIL,       2 },
364         { WPN_FLAIL,            2 },
365         { WPN_MORNINGSTAR,      2 },
366         { WPN_MACE,             1 }, };
367     static const weapon_list OGRE_WEAPONS =
368     {   { WPN_GIANT_CLUB,        2 },
369         { WPN_GIANT_SPIKED_CLUB, 1 }, };
370     static const weapon_list DOUBLE_OGRE_WEAPONS = // total 100
371     {   { WPN_GIANT_CLUB,        60 },
372         { WPN_GIANT_SPIKED_CLUB, 30 },
373         { WPN_DIRE_FLAIL,        9 },
374         { WPN_GREAT_MACE,        1 }, };
375     static const weapon_list FAUN_WEAPONS =
376     {   { WPN_SPEAR,            2 },
377         { WPN_CLUB,             1 },
378         { WPN_QUARTERSTAFF,     1 }, };
379     static const mon_weapon_spec EFREET_WSPEC =
380     { { { WPN_SCIMITAR,         1 } },
381       { 1, 0, 4 },
382       { { SPWPN_FLAMING, 1 } } };
383     static const mon_weapon_spec DAEVA_WSPEC =
384     { { { WPN_EUDEMON_BLADE,    1 },
385         { WPN_SCIMITAR,         2 },
386         { WPN_LONG_SWORD,       1 } },
387       { 1, 2, 5 },
388       { { SPWPN_HOLY_WRATH,     1 } } };
389     static const vector<pair<brand_type, int>> HELL_KNIGHT_BRANDS = // sum 45
390     {   { SPWPN_FLAMING,        13 },
391         { SPWPN_DRAINING,       4 },
392         { SPWPN_VORPAL,         4 },
393         { SPWPN_DISTORTION,     2 },
394         { SPWPN_PAIN,           2 },
395         { NUM_SPECIAL_WEAPONS,  20 }, // 5/9 chance of brand
396     };
397     static const weapon_list URUG_WEAPONS =
398     {   { WPN_HALBERD,          5 },
399         { WPN_GLAIVE,           5 },
400         { WPN_WAR_AXE,          6 },
401         { WPN_GREAT_MACE,       6 },
402         { WPN_BATTLEAXE,        7 },
403         { WPN_LONG_SWORD,       8 },
404         { WPN_SCIMITAR,         8 },
405         { WPN_GREAT_SWORD,      8 },
406         { WPN_BROAD_AXE,        9 },
407         { WPN_DOUBLE_SWORD,     10 },
408         { WPN_EVENINGSTAR,      13 },
409         { WPN_DEMON_TRIDENT,    14 }, };
410     static const weapon_list SP_DEFENDER_WEAPONS =
411     {   { WPN_LAJATANG,         1 },
412         { WPN_QUICK_BLADE,      1 },
413         { WPN_RAPIER,           1 },
414         { WPN_DEMON_WHIP,       1 },
415         { WPN_FLAIL,            1 } };
416     // Demonspawn probably want to use weapons close to the "natural"
417     // demon weapons - demon blades, demon whips, and demon tridents.
418     // So pick from a selection of good weapons from those classes
419     // with a 2/5 chance in each category of having the demon weapon.
420     // XXX: this is so ridiculously overengineered
421     static const weapon_list DS_WEAPONS =
422     {   { WPN_LONG_SWORD,       10 },
423         { WPN_SCIMITAR,         10 },
424         { WPN_GREAT_SWORD,      10 },
425         { WPN_DEMON_BLADE,      20 },
426         { WPN_MACE,             10 },
427         { WPN_MORNINGSTAR,      8 },
428         { WPN_EVENINGSTAR,      2 },
429         { WPN_DIRE_FLAIL,       10 },
430         { WPN_DEMON_WHIP,       20 },
431         { WPN_TRIDENT,          10 },
432         { WPN_HALBERD,          10 },
433         { WPN_GLAIVE,           10 },
434         { WPN_DEMON_TRIDENT,    20 } };
435     static const weapon_list GARGOYLE_WEAPONS =
436     {   { WPN_MACE,             15 },
437         { WPN_FLAIL,            10 },
438         { WPN_MORNINGSTAR,      5 },
439         { WPN_DIRE_FLAIL,       2 }, };
440 
441     static const map<monster_type, mon_weapon_spec> primary_weapon_specs = {
442         { MONS_ROBIN,
443             { { { WPN_CLUB,             35 },
444                 { WPN_DAGGER,           30 },
445                 { WPN_SPEAR,            30 },
446                 { WPN_SHORT_SWORD,      20 },
447                 { WPN_MACE,             20 },
448                 { WPN_WHIP,             15 },
449                 { WPN_TRIDENT,          10 },
450                 { WPN_FALCHION,         10 },
451         } } },
452         { MONS_GOBLIN,                  { GOBLIN_WEAPONS } },
453         { MONS_JESSICA,                 { GOBLIN_WEAPONS } },
454         { MONS_IJYB,                    { GOBLIN_WEAPONS } },
455         { MONS_WIGHT,
456             { { { WPN_MORNINGSTAR,      4 },
457                 { WPN_DIRE_FLAIL,       4 },
458                 { WPN_WAR_AXE,          4 },
459                 { WPN_TRIDENT,          4 },
460                 { WPN_MACE,             7 },
461                 { WPN_FLAIL,            7 },
462                 { WPN_FALCHION,         7 },
463                 { WPN_DAGGER,           7 },
464                 { WPN_SHORT_SWORD,      7 },
465                 { WPN_LONG_SWORD,       7 },
466                 { WPN_SCIMITAR,         7 },
467                 { WPN_GREAT_SWORD,      7 },
468                 { WPN_HAND_AXE,         7 },
469                 { WPN_BATTLEAXE,        7 },
470                 { WPN_SPEAR,            7 },
471                 { WPN_HALBERD,          7 },
472             } } },
473         { MONS_EDMUND,
474             { { { WPN_DIRE_FLAIL,       1 },
475                 { WPN_FLAIL,            2 },
476         }, {}, {}, 1 } },
477         { MONS_DEATH_KNIGHT,
478             { { { WPN_MORNINGSTAR,      5 },
479                 { WPN_GREAT_MACE,       5 },
480                 { WPN_HALBERD,          5 },
481                 { WPN_GREAT_SWORD,      5 },
482                 { WPN_GLAIVE,           8 },
483                 { WPN_BROAD_AXE,        10 },
484                 { WPN_BATTLEAXE,        15 },
485         }, {2, 1, 4} } },
486         { MONS_GNOLL,                   { GNOLL_WEAPONS } },
487         { MONS_OGRE_MAGE,               { GNOLL_WEAPONS } },
488         { MONS_NAGA_MAGE,               { GNOLL_WEAPONS } },
489         { MONS_NAGARAJA,            { GNOLL_WEAPONS } },
490         { MONS_GNOLL_SHAMAN,
491             { { { WPN_CLUB,             1 },
492                 { WPN_WHIP,             1 },
493         } } },
494         { MONS_GNOLL_SERGEANT,
495             { { { WPN_SPEAR,            2 },
496                 { WPN_TRIDENT,          1 },
497         }, {}, {}, 3 } },
498         { MONS_PIKEL, { { { WPN_WHIP, 1 } }, { 1, 0, 2 }, {
499             { SPWPN_FLAMING, 2 },
500             { SPWPN_FREEZING, 2 },
501             { SPWPN_ELECTROCUTION, 1 },
502         } } },
503         { MONS_GRUM,
504             { { { WPN_SPEAR,            3 },
505                 { WPN_HALBERD,          1 },
506                 { WPN_GLAIVE,           1 },
507         }, { 1, -2, 1 } } },
508         { MONS_CRAZY_YIUF,
509             { { { WPN_QUARTERSTAFF, 1 } },
510             { 1, 2, 4 },
511             { { SPWPN_CHAOS, 1 } } } },
512         { MONS_JOSEPH, { { { WPN_QUARTERSTAFF, 1 } } } },
513         { MONS_SPRIGGAN_DRUID, { { { WPN_QUARTERSTAFF, 1 } } } },
514         { MONS_BAI_SUZHEN, { { { WPN_QUARTERSTAFF, 1 } } } },
515         { MONS_ORC,                     { ORC_WEAPONS } },
516         { MONS_ORC_PRIEST,              { ORC_WEAPONS } },
517         { MONS_DRACONIAN,               { ORC_WEAPONS } },
518         { MONS_TERENCE,
519             { { { WPN_FLAIL,            30 },
520                 { WPN_HAND_AXE,         20 },
521                 { WPN_SHORT_SWORD,      20 },
522                 { WPN_MACE,             20 },
523                 { WPN_TRIDENT,          10 },
524                 { WPN_FALCHION,         10 },
525                 { WPN_MORNINGSTAR,      3 },
526         } } },
527         { MONS_DUVESSA,
528             { { { WPN_SHORT_SWORD,      3 },
529                 { WPN_RAPIER,           1 },
530         } } },
531         { MONS_ASTERION, {
532             { { WPN_DEMON_WHIP,         1 },
533               { WPN_DEMON_BLADE,        1 },
534               { WPN_DEMON_TRIDENT,      1 },
535               { WPN_MORNINGSTAR,        1 },
536               { WPN_BROAD_AXE,          1 }, },
537             {}, {}, 1,
538         } },
539         { MONS_MARA,
540             { { { WPN_DEMON_WHIP,       1 },
541                 { WPN_DEMON_TRIDENT,    1 },
542                 { WPN_DEMON_BLADE,      1 },
543         }, {}, {}, 1 } },
544         { MONS_RAKSHASA,
545             { { { WPN_WHIP,             1 },
546                 { WPN_TRIDENT,          1 },
547                 { WPN_LONG_SWORD,       1 },
548         } } },
549         { MONS_DEEP_ELF_KNIGHT,         { DE_KNIGHT_WEAPONS } },
550         { MONS_DEEP_ELF_HIGH_PRIEST,    { DE_KNIGHT_WEAPONS } },
551         { MONS_DEEP_ELF_BLADEMASTER,
552             { { { WPN_RAPIER,           20 },
553                 { WPN_SHORT_SWORD,      5 },
554                 { WPN_QUICK_BLADE,      1 },
555         } } },
556         { MONS_DEEP_ELF_ARCHER,
557             { { { WPN_SHORT_SWORD,      1 },
558                 { WPN_DAGGER,           1 },
559         } } },
560         { MONS_DEEP_ELF_MASTER_ARCHER, { { { WPN_LONGBOW, 1 } } } },
561         { MONS_DEEP_ELF_AIR_MAGE,       { DE_MAGE_WEAPONS } },
562         { MONS_DEEP_ELF_FIRE_MAGE,      { DE_MAGE_WEAPONS } },
563         { MONS_DEEP_ELF_ANNIHILATOR,    { DE_MAGE_WEAPONS } },
564         { MONS_DEEP_ELF_DEATH_MAGE,     { DE_MAGE_WEAPONS } },
565         { MONS_DEEP_ELF_DEMONOLOGIST,   { DE_MAGE_WEAPONS } },
566         { MONS_DEEP_ELF_SORCERER,       { DE_MAGE_WEAPONS } },
567         { MONS_DEEP_ELF_ELEMENTALIST,   { DE_MAGE_WEAPONS } },
568         { MONS_DRACONIAN_SHIFTER,       { DRAC_MAGE_WEAPONS } },
569         { MONS_DRACONIAN_SCORCHER,      { DRAC_MAGE_WEAPONS } },
570         { MONS_DRACONIAN_ANNIHILATOR,   { DRAC_MAGE_WEAPONS } },
571         { MONS_DRACONIAN_STORMCALLER,   { DRAC_MAGE_WEAPONS } },
572         { MONS_RAGGED_HIEROPHANT,       { DRAC_MAGE_WEAPONS } },
573         { MONS_VASHNIA,                 { NAGA_WEAPONS, {}, {}, 1 } },
574         { MONS_NAGA_SHARPSHOOTER,       { NAGA_WEAPONS } },
575         { MONS_NAGA,                    { NAGA_WEAPONS } },
576         { MONS_NAGA_WARRIOR,            { NAGA_WEAPONS } },
577         { MONS_ORC_WARRIOR,             { NAGA_WEAPONS } },
578         { MONS_ORC_HIGH_PRIEST,         { NAGA_WEAPONS } },
579         { MONS_BLORK_THE_ORC,           { NAGA_WEAPONS } },
580         { MONS_DANCING_WEAPON,          { NAGA_WEAPONS, {}, {}, 1 } },
581         { MONS_SPECTRAL_WEAPON,         { NAGA_WEAPONS } }, // for mspec placement
582         { MONS_FRANCES,                 { NAGA_WEAPONS } },
583         { MONS_HAROLD,                  { NAGA_WEAPONS } },
584         { MONS_SKELETAL_WARRIOR,        { NAGA_WEAPONS } },
585         { MONS_PALE_DRACONIAN,          { NAGA_WEAPONS } },
586         { MONS_RED_DRACONIAN,           { NAGA_WEAPONS } },
587         { MONS_WHITE_DRACONIAN,         { NAGA_WEAPONS } },
588         { MONS_GREEN_DRACONIAN,         { NAGA_WEAPONS } },
589         { MONS_BLACK_DRACONIAN,         { NAGA_WEAPONS } },
590         { MONS_YELLOW_DRACONIAN,        { NAGA_WEAPONS } },
591         { MONS_PURPLE_DRACONIAN,        { NAGA_WEAPONS } },
592         { MONS_GREY_DRACONIAN,          { NAGA_WEAPONS } },
593         { MONS_TENGU,                   { NAGA_WEAPONS } },
594         { MONS_NAGA_RITUALIST,          { NAGA_WEAPONS } },
595         { MONS_TIAMAT,
596             { { { WPN_BARDICHE,         1 },
597                 { WPN_DEMON_TRIDENT,    1 },
598                 { WPN_GLAIVE,           1 },
599         }, {}, {}, 1 } },
600         { MONS_RUPERT,
601             // Rupert favours big two-handers with visceral up-close
602             // effects, i.e. no polearms.
603             { { { WPN_GREAT_MACE,       10 },
604                 { WPN_GREAT_SWORD,      6 },
605                 { WPN_TRIPLE_SWORD,     2 },
606                 { WPN_BATTLEAXE,        8 },
607                 { WPN_EXECUTIONERS_AXE, 2 },
608         }, {}, {}, 1 } },
609         { MONS_TENGU_REAVER,            ORC_WARLORD_WSPEC },
610         { MONS_VAULT_WARDEN,            ORC_WARLORD_WSPEC },
611         { MONS_ORC_WARLORD,             ORC_WARLORD_WSPEC },
612         { MONS_SAINT_ROKA,              ORC_WARLORD_WSPEC },
613         { MONS_DRACONIAN_KNIGHT,        ORC_WARLORD_WSPEC },
614         { MONS_ORC_KNIGHT,              ORC_KNIGHT_WSPEC },
615         { MONS_TENGU_WARRIOR,           ORC_KNIGHT_WSPEC },
616         { MONS_VAULT_GUARD,             ORC_KNIGHT_WSPEC },
617         { MONS_VAMPIRE_KNIGHT,          ORC_KNIGHT_WSPEC },
618         { MONS_LOUISE,
619             { { { WPN_MORNINGSTAR, 1 },
620                 { WPN_EVENINGSTAR, 1 },
621                 { WPN_TRIDENT, 1 },
622                 { WPN_DEMON_TRIDENT, 1 },
623         }, {}, {}, 1 } },
624         { MONS_JORY,
625             { { { WPN_GREAT_SWORD,      3 },
626                 { WPN_GLAIVE,           1 },
627                 { WPN_BATTLEAXE,        1 },
628         }, {}, {}, 1 } },
629         { MONS_VAULT_SENTINEL,
630             { { { WPN_LONG_SWORD,       5 },
631                 { WPN_FALCHION,         4 },
632                 { WPN_WAR_AXE,          3 },
633                 { WPN_MORNINGSTAR,      3 },
634         } } },
635         { MONS_IRONBOUND_CONVOKER,      { IRON_WEAPONS } },
636         { MONS_IRONBOUND_PRESERVER,     { IRON_WEAPONS } },
637         { MONS_SIGMUND, { { { WPN_SCYTHE, 1 } } } },
638         { MONS_REAPER, { { { WPN_SCYTHE, 1 } }, {}, {}, 1 } },
639         { MONS_BALRUG, { { { WPN_DEMON_WHIP, 1 } } } },
640         { MONS_RED_DEVIL,
641             { { { WPN_TRIDENT,          4 },
642                 { WPN_DEMON_TRIDENT,    1 },
643         } } },
644         { MONS_TWO_HEADED_OGRE,         { DOUBLE_OGRE_WEAPONS } },
645         { MONS_IRON_GIANT,              { DOUBLE_OGRE_WEAPONS } },
646         { MONS_IRONBOUND_BEASTMASTER,
647             { { { WPN_WHIP,             5 },
648                 { WPN_QUARTERSTAFF,     4 },
649                 { WPN_DEMON_WHIP,       1 },
650         } } },
651         { MONS_IRONBOUND_THUNDERHULK,
652             { { { WPN_DIRE_FLAIL,       9 },
653                 { WPN_GREAT_MACE,       1 },
654         } } },
655         { MONS_ETTIN,
656             { { { WPN_DIRE_FLAIL,       9 },
657                 { WPN_GREAT_MACE,       1 },
658         } } },
659         { MONS_OGRE,                    { OGRE_WEAPONS } },
660         { MONS_EROLCHA,                 { OGRE_WEAPONS } },
661         { MONS_ILSUIW, {
662             { { WPN_TRIDENT,            1 } },
663             { 1, -1, 6, 2 },
664             { { SPWPN_FREEZING, 1 } }
665         } },
666         { MONS_MERFOLK_IMPALER,
667             { { { WPN_TRIDENT,          20 },
668                 { WPN_DEMON_TRIDENT,    3 },
669         } } },
670         { MONS_MERFOLK_AQUAMANCER, { { { WPN_RAPIER, 1 } }, {}, {}, 2 } },
671         { MONS_MERFOLK_JAVELINEER, { { { WPN_SPEAR, 1 } } } },
672         { MONS_SPRIGGAN_RIDER, { { { WPN_SPEAR, 1 } } } },
673         { MONS_MERFOLK, { { { WPN_TRIDENT, 1 } } } },
674         { MONS_MERFOLK_SIREN,
675             { { { WPN_TRIDENT,          1 },
676                 { WPN_SPEAR,            2 },
677         } } },
678         { MONS_CENTAUR, { { { WPN_SHORTBOW, 1 } } } },
679         { MONS_CENTAUR_WARRIOR,
680             { { { WPN_SHORTBOW,         2 },
681                 { WPN_LONGBOW,          1 },
682         } } },
683         { MONS_FAUN,                    { FAUN_WEAPONS } },
684         { MONS_SATYR,                   { FAUN_WEAPONS } },
685         { MONS_SERVANT_OF_WHISPERS,     { FAUN_WEAPONS } },
686         { MONS_NESSOS, {
687             { { WPN_LONGBOW,            1 } },
688             { 1, 1, 3 },
689             { { SPWPN_FLAMING, 1 } }
690         } },
691         { MONS_YAKTAUR, { { { WPN_ARBALEST, 1 } } } },
692         { MONS_YAKTAUR_CAPTAIN, { { { WPN_ARBALEST, 1 } } } },
693         { MONS_EFREET,                  EFREET_WSPEC },
694         { MONS_ERICA,                   EFREET_WSPEC },
695         { MONS_AZRAEL,                  EFREET_WSPEC },
696         { MONS_ANGEL, {
697             { { WPN_WHIP,               3 },
698               { WPN_SACRED_SCOURGE,     1 }, },
699             { 1, 1, 3 },
700             { { SPWPN_HOLY_WRATH, 1 } },
701         } },
702         { MONS_CHERUB,
703             { { { WPN_FLAIL,            1 },
704                 { WPN_LONG_SWORD,       1 },
705                 { WPN_SCIMITAR,         1 },
706                 { WPN_FALCHION,         1 }, },
707             { 1, 0, 4 },
708             { { SPWPN_FLAMING, 1 } },
709         } },
710         { MONS_SERAPH, {
711             { { WPN_GREAT_SWORD,        1 } },
712             { 1, 3, 8 }, // highly enchanted, we're top rank
713             { { SPWPN_FLAMING, 1 } },
714         } },
715         { MONS_DAEVA,                   DAEVA_WSPEC },
716         { MONS_PROFANE_SERVITOR,
717             { { { WPN_DEMON_WHIP,       1 },
718                 { WPN_WHIP,             3 }, },
719             { 1, 1, 3 },
720         } },
721         { MONS_MENNAS, {
722             { { WPN_TRISHULA,       1},
723               { WPN_SACRED_SCOURGE, 1},
724               { WPN_EUDEMON_BLADE,  1}, },
725             { 1, 0, 5},
726             { { SPWPN_HOLY_WRATH, 1}}
727         } },
728         { MONS_DONALD,
729             { { { WPN_SCIMITAR,         12 },
730                 { WPN_LONG_SWORD,       10 },
731                 { WPN_BROAD_AXE,        9 },
732                 { WPN_EVENINGSTAR,      7 },
733                 { WPN_DOUBLE_SWORD,     7 },
734                 { WPN_DEMON_TRIDENT,    7 },
735                 { WPN_WAR_AXE,          3 },
736         } } },
737         { MONS_HELL_KNIGHT,
738             { { { WPN_DEMON_WHIP,       1 },
739                 { WPN_DEMON_BLADE,      1 },
740                 { WPN_DEMON_TRIDENT,    1 },
741                 { WPN_HALBERD,          1 },
742                 { WPN_GLAIVE,           1 },
743                 { WPN_WAR_AXE,          1 },
744                 { WPN_GREAT_MACE,       1 },
745                 { WPN_BATTLEAXE,        1 },
746                 { WPN_LONG_SWORD,       1 },
747                 { WPN_SCIMITAR,         1 },
748                 { WPN_GREAT_SWORD,      1 },
749                 { WPN_BROAD_AXE,        1 }, },
750               { 1, 0, 5 },
751               HELL_KNIGHT_BRANDS
752         } },
753         { MONS_MAGGIE,
754             { { { WPN_HALBERD,          1 },
755                 { WPN_GLAIVE,           1 },
756                 { WPN_WAR_AXE,          1 },
757                 { WPN_MORNINGSTAR,       1 },
758                 { WPN_LONG_SWORD,       1 },
759                 { WPN_SCIMITAR,         1 },
760                 { WPN_BROAD_AXE,        1 }, },
761               { },
762               HELL_KNIGHT_BRANDS
763         } },
764         { MONS_MARGERY,
765             { { { WPN_DEMON_WHIP,       2 },
766                 { WPN_DEMON_BLADE,      2 },
767                 { WPN_DEMON_TRIDENT,    2 },
768                 { WPN_HALBERD,          1 },
769                 { WPN_GLAIVE,           1 },
770                 { WPN_WAR_AXE,          1 },
771                 { WPN_GREAT_MACE,       1 },
772                 { WPN_BATTLEAXE,        1 },
773                 { WPN_LONG_SWORD,       1 },
774                 { WPN_SCIMITAR,         1 },
775                 { WPN_GREAT_SWORD,      1 },
776                 { WPN_BROAD_AXE,        1 }, },
777               { 1, 0, 5 },
778               HELL_KNIGHT_BRANDS
779         } },
780         { MONS_URUG,                    { URUG_WEAPONS } },
781         { MONS_FREDERICK,               { URUG_WEAPONS } },
782         { MONS_FIRE_GIANT, {
783             { { WPN_GREAT_SWORD,        1 } }, {},
784             { { SPWPN_FLAMING, 1 } },
785         } },
786         { MONS_FROST_GIANT, {
787             { { WPN_BATTLEAXE,          1 } }, {},
788             { { SPWPN_FREEZING, 1 } },
789         } },
790         { MONS_ORC_WIZARD,      { { { WPN_DAGGER, 1 } } } },
791         { MONS_ORC_SORCERER,    { { { WPN_DAGGER, 1 } } } },
792         { MONS_NERGALLE,        { { { WPN_DAGGER, 1 } } } },
793         { MONS_DOWAN,           { { { WPN_DAGGER, 1 } } } },
794         { MONS_KOBOLD_DEMONOLOGIST, { { { WPN_DAGGER, 1 } } } },
795         { MONS_NECROMANCER,      { { { WPN_DAGGER, 1 } } } },
796         { MONS_WIZARD,          { { { WPN_DAGGER, 1 } } } },
797         { MONS_JOSEPHINE,       { { { WPN_DAGGER, 1 } } } },
798         { MONS_PSYCHE, {
799             { { WPN_DAGGER,             1 }, },
800             { 1, 0, 4 },
801             { { SPWPN_CHAOS, 3 },
802               { SPWPN_DISTORTION, 1 } },
803         } },
804         { MONS_AGNES,       { { { WPN_LAJATANG, 1 } } } },
805         { MONS_SONJA, {
806             { { WPN_DAGGER,             1 },
807               { WPN_SHORT_SWORD,        1 }, }, {},
808             { { SPWPN_DISTORTION,       3 },
809               { SPWPN_VENOM,            2 },
810               { SPWPN_DRAINING,         1 } },
811         } },
812         { MONS_MAURICE,
813             { { { WPN_DAGGER,           1 },
814                 { WPN_SHORT_SWORD,      1 },
815         } } },
816         { MONS_EUSTACHIO,
817             { { { WPN_FALCHION,         1 },
818                 { WPN_RAPIER,           2 },
819         } } },
820         { MONS_NIKOLA, {
821             { { WPN_RAPIER,             1 } },
822             { 1, 0, 4 },
823             { { SPWPN_ELECTROCUTION, 1 } },
824         } },
825         { MONS_SALAMANDER_MYSTIC,
826             { { { WPN_QUARTERSTAFF,     10 },
827                 { WPN_DAGGER,           5 },
828                 { WPN_SCIMITAR,         2 },
829         } } },
830         { MONS_SPRIGGAN,
831             { { { WPN_DAGGER,           1 },
832                 { WPN_SHORT_SWORD,      1 },
833                 { WPN_RAPIER,           1 },
834         } } },
835         { MONS_SPRIGGAN_BERSERKER, {
836             { { WPN_QUARTERSTAFF,       10 },
837               { WPN_HAND_AXE,           9 },
838               { WPN_WAR_AXE,            12 },
839               { WPN_BROAD_AXE,          5 },
840               { WPN_FLAIL,              5 },
841               { WPN_RAPIER,             10 }, }, {},
842             { { SPWPN_ANTIMAGIC, 1 },
843               { NUM_SPECIAL_WEAPONS, 3 } },
844         } },
845         { MONS_SPRIGGAN_DEFENDER, { SP_DEFENDER_WEAPONS, {}, {}, 1 } },
846         { MONS_THE_ENCHANTRESS, { SP_DEFENDER_WEAPONS, {}, {}, 1 } },
847         { MONS_HELLBINDER, { { { WPN_DEMON_BLADE, 1 } } } },
848         { MONS_IGNACIO, {
849             { { WPN_EXECUTIONERS_AXE, 1 } },
850             { 1, 2, 8 },
851             { { SPWPN_PAIN, 1 } },
852         } },
853         { MONS_ANCIENT_CHAMPION, {
854             { { WPN_GREAT_MACE,         1 },
855               { WPN_BATTLEAXE,          1 },
856               { WPN_GREAT_SWORD,        1 }, },
857             { 1, 0, 3 },
858             { { SPWPN_DRAINING,      13 }, // total 45
859               { SPWPN_VORPAL,        7 },
860               { SPWPN_FREEZING,      4 },
861               { SPWPN_FLAMING,       4 },
862               { SPWPN_PAIN,          2 },
863               { NUM_SPECIAL_WEAPONS, 15 } }, // 2/3 chance of brand
864         } },
865         { MONS_SOJOBO, {
866             { { WPN_TRIPLE_SWORD,       1 },
867               { WPN_GREAT_SWORD,        5 } }, {},
868             { { SPWPN_ELECTROCUTION, 2 },
869               { NUM_SPECIAL_WEAPONS, 1 } },
870             1,
871         } },
872         { MONS_INFERNAL_DEMONSPAWN,     { DS_WEAPONS } },
873         { MONS_GELID_DEMONSPAWN,        { DS_WEAPONS } },
874         { MONS_TORTUROUS_DEMONSPAWN,    { DS_WEAPONS } },
875         { MONS_CORRUPTER,               { DS_WEAPONS } },
876         { MONS_BLACK_SUN,               { DS_WEAPONS } },
877         { MONS_BLOOD_SAINT, {
878             { { WPN_DAGGER,             4 },
879               { WPN_QUARTERSTAFF,       1 } },
880         } },
881         { MONS_WARMONGER, {
882             { { WPN_DEMON_BLADE,        10 },
883               { WPN_DEMON_WHIP,         10 },
884               { WPN_DEMON_TRIDENT,      10 },
885               { WPN_BATTLEAXE,          7 },
886               { WPN_GREAT_SWORD,        5 },
887               { WPN_DOUBLE_SWORD,       2 },
888               { WPN_DIRE_FLAIL,         5 },
889               { WPN_GREAT_MACE,         2 },
890               { WPN_GLAIVE,             5 },
891               { WPN_BARDICHE,           2 },
892               { WPN_LAJATANG,           1 }, },
893            {}, {}, 1,
894         } },
895         { MONS_GARGOYLE,                { GARGOYLE_WEAPONS } },
896         { MONS_MOLTEN_GARGOYLE,         { GARGOYLE_WEAPONS } },
897         { MONS_WAR_GARGOYLE, {
898             { { WPN_MORNINGSTAR,        10 },
899               { WPN_FLAIL,              10 },
900               { WPN_DIRE_FLAIL,         5 },
901               { WPN_GREAT_MACE,         5 },
902               { WPN_LAJATANG,           1 } },
903             {}, {}, 4,
904         } },
905         { MONS_MELIAI, { // labrys
906             { { WPN_HAND_AXE,           12 },
907               { WPN_WAR_AXE,            7 },
908               { WPN_BROAD_AXE,          1 }, },
909         } },
910         { MONS_IMPERIAL_MYRMIDON, {
911             { { WPN_SCIMITAR,           20 },
912               { WPN_DEMON_BLADE,        4 },
913               { WPN_DOUBLE_SWORD,       1 }, },
914         } },
915         { MONS_KILLER_KLOWN, {
916             { { WPN_CLUB,             10 }, },
917             { 1, 8, 12 },
918             { { SPWPN_NORMAL,         20 },
919               { SPWPN_FLAMING,        20 },
920               { SPWPN_FREEZING,       10 },
921               { SPWPN_VORPAL  ,       10 },
922               { SPWPN_ELECTROCUTION,  10 },
923               { SPWPN_VENOM,          10 },
924               { SPWPN_VAMPIRISM,       5 },
925               { SPWPN_ANTIMAGIC,       5 },
926               { SPWPN_PAIN,            4 },
927               { SPWPN_HOLY_WRATH,      3 },
928               { SPWPN_DISTORTION,      2 },
929               { SPWPN_CHAOS,           1 }, },
930         } },
931     };
932 
933     static const weapon_list ORC_KNIGHT_BOWS =
934     {   { WPN_ARBALEST,                 1 },
935         { NUM_WEAPONS,                  8 }, }; // 1/9 chance of ranged weapon
936 
937     static const map<monster_type, mon_weapon_spec> secondary_weapon_specs = {
938         { MONS_JOSEPH, { { { WPN_HUNTING_SLING, 1 } } } },
939         { MONS_DEEP_ELF_ARCHER, // XXX: merge w/centaur warrior primary?
940             { { { WPN_SHORTBOW,         2 },
941                 { WPN_LONGBOW,          1 },
942         } } },
943         { MONS_VASHNIA,
944             { { { WPN_LONGBOW,          1 },
945                 { WPN_ARBALEST,         1 },
946         } } },
947         { MONS_NAGA_SHARPSHOOTER,
948             { { { WPN_ARBALEST,         3 },
949                 { WPN_SHORTBOW,         2 },
950                 { WPN_LONGBOW,          1 }
951         } } },
952         { MONS_VAULT_WARDEN,            { ORC_KNIGHT_BOWS } },
953         { MONS_ORC_WARLORD,             { ORC_KNIGHT_BOWS } },
954         { MONS_SAINT_ROKA,              { ORC_KNIGHT_BOWS } },
955         { MONS_ORC_KNIGHT,              { ORC_KNIGHT_BOWS } },
956         { MONS_TENGU_WARRIOR,
957             { { { WPN_LONGBOW,                  1 },
958                 { WPN_ARBALEST,                 1 },
959                 { NUM_WEAPONS,                  16 }, // 1/9 chance of weap
960         } } },
961         { MONS_VAULT_SENTINEL,
962             { { { WPN_ARBALEST,                 1 },
963                 { NUM_WEAPONS,                  2 },
964         } } },
965         { MONS_FAUN, { { { WPN_HUNTING_SLING, 1 } } } },
966         { MONS_SATYR,
967             { { { WPN_FUSTIBALUS,               1 },
968                 { WPN_LONGBOW,                  2 },
969         } } },
970         { MONS_CHERUB,
971             { { { WPN_HUNTING_SLING,            1 },
972                 { WPN_FUSTIBALUS,               1 },
973                 { WPN_SHORTBOW,                 1 },
974                 { WPN_LONGBOW,                  1 },
975         } } },
976         // salamanders only have secondary weapons; melee or bow, not both
977         { MONS_SALAMANDER, {
978             { { WPN_HALBERD,                    5 },
979               { WPN_TRIDENT,                    5 },
980               { WPN_SPEAR,                      3 },
981               { WPN_GLAIVE,                     2 },
982               { WPN_SHORTBOW,                   5 }, },
983             { 4, 0, 4 },
984         } },
985         { MONS_WARMONGER, {
986             { { WPN_LONGBOW,                    10 }, // total 60
987               { WPN_ARBALEST,                   9 },
988               { WPN_TRIPLE_CROSSBOW,            1 },
989               { NUM_WEAPONS,                    40 }, }, // 1/3 odds of weap
990             {}, {}, 1,
991         } },
992     };
993 
994     bool force_item = false;
995 
996     string floor_tile = "";
997     string equip_tile = "";
998 
999     item_def item;
1000     item.base_type = OBJ_UNASSIGNED;
1001     item.quantity = 1;
1002 
1003     // do we have a secondary weapon to give the monster? (usually ranged)
1004     const mon_weapon_spec *secondary_spec = map_find(secondary_weapon_specs,
1005                                                      type);
1006     if (!secondary_spec || melee_only ||
1007         !_apply_weapon_spec(*secondary_spec, item, force_item, level))
1008     {
1009         // either we're just giving only giving out primary weapons in this
1010         // call, or we didn't find a secondary weapon to give. either way,
1011         // try to give the monster a primary weapon. (may be its second!)
1012         const mon_weapon_spec *primary_spec = map_find(primary_weapon_specs,
1013                                                        type);
1014         if (primary_spec)
1015             _apply_weapon_spec(*primary_spec, item, force_item, level);
1016     }
1017 
1018     // special cases.
1019     switch (type)
1020     {
1021     case MONS_KOBOLD:
1022     case MONS_KOBOLD_BRIGAND:
1023         if (one_chance_in(30) && level > 2)
1024         {
1025             item.base_type = OBJ_WEAPONS;
1026             item.sub_type  = WPN_HAND_CROSSBOW;
1027             break;
1028         }
1029         else     // give hand weapon
1030         {
1031             item.base_type = OBJ_WEAPONS;
1032             item.sub_type  = random_choose(WPN_DAGGER,      WPN_DAGGER,
1033                                            WPN_SHORT_SWORD, WPN_SHORT_SWORD,
1034                                            WPN_CLUB,        WPN_WHIP);
1035         }
1036         break;
1037 
1038     case MONS_GOBLIN:
1039         if (!melee_only && one_chance_in(12) && level)
1040         {
1041             item.base_type = OBJ_WEAPONS;
1042             item.sub_type  = WPN_HUNTING_SLING;
1043             break;
1044         }
1045         break;
1046 
1047     case MONS_GNOLL:
1048         if (!level && item.is_type(OBJ_WEAPONS, WPN_HALBERD))
1049             item.sub_type = WPN_CLUB;
1050         break;
1051 
1052     case MONS_WIGHT:
1053         if (coinflip())
1054         {
1055             force_item = true;
1056             item.plus += 1 + random2(3);
1057 
1058             if (one_chance_in(5))
1059                 set_item_ego_type(item, OBJ_WEAPONS, SPWPN_FREEZING);
1060         }
1061         break;
1062 
1063     case MONS_JORGRUN:
1064         force_item = true;
1065         if (one_chance_in(3))
1066         {
1067             item.base_type = OBJ_STAVES;
1068             item.sub_type = STAFF_EARTH;
1069         }
1070         else
1071         {
1072             item.base_type = OBJ_WEAPONS;
1073             item.sub_type = WPN_QUARTERSTAFF;
1074             set_item_ego_type(item, OBJ_WEAPONS, SPWPN_VORPAL);
1075         }
1076         item.flags |= ISFLAG_KNOW_TYPE;
1077         break;
1078 
1079     case MONS_CYCLOPS:
1080     case MONS_STONE_GIANT:
1081         item.base_type = OBJ_MISSILES;
1082         item.sub_type  = MI_LARGE_ROCK;
1083         break;
1084 
1085     case MONS_MERFOLK_IMPALER:
1086     case MONS_MERFOLK_JAVELINEER:
1087     case MONS_AGNES:
1088         if (!one_chance_in(3))
1089             level = ISPEC_GOOD_ITEM;
1090         break;
1091 
1092     case MONS_MERFOLK:
1093         if (active_monster_band == BAND_MERFOLK_IMPALER)
1094         {
1095             item.base_type = OBJ_WEAPONS;
1096             item.sub_type  = random_choose_weighted(10, WPN_SPEAR,
1097                                                     10, WPN_TRIDENT,
1098                                                     5, WPN_HALBERD,
1099                                                     5, WPN_GLAIVE);
1100         }
1101         break;
1102 
1103     case MONS_ANGEL:
1104     case MONS_DAEVA:
1105     case MONS_PROFANE_SERVITOR:
1106         set_equip_desc(item, ISFLAG_GLOWING); // will never come up...
1107         break;
1108 
1109     case MONS_DONALD:
1110     case MONS_FREDERICK:
1111     case MONS_URUG:
1112         if (x_chance_in_y(5, 9))
1113             level = ISPEC_GOOD_ITEM;
1114         else if (type != MONS_DONALD)
1115         {
1116             item.plus += random2(6);
1117             force_item = true;
1118         }
1119         break;
1120 
1121     case MONS_FANNAR:
1122         force_item = true;
1123         if (one_chance_in(3))
1124         {
1125             item.base_type = OBJ_STAVES;
1126             item.sub_type = STAFF_COLD;
1127         }
1128         else
1129         {
1130             item.base_type = OBJ_WEAPONS;
1131             item.sub_type = WPN_QUARTERSTAFF;
1132             set_item_ego_type(item, OBJ_WEAPONS, SPWPN_FREEZING);
1133         }
1134         item.flags |= ISFLAG_KNOW_TYPE;
1135         break;
1136 
1137     case MONS_NIKOLA:
1138         if (one_chance_in(100) && !get_unique_item_status(UNRAND_ARC_BLADE))
1139             make_item_unrandart(item, UNRAND_ARC_BLADE);
1140         break;
1141 
1142     case MONS_ARACHNE:
1143         force_item = true;
1144         item.base_type = OBJ_STAVES;
1145         item.sub_type = STAFF_POISON;
1146         item.flags    |= ISFLAG_KNOW_TYPE;
1147         if (one_chance_in(100) && !get_unique_item_status(UNRAND_OLGREB))
1148             make_item_unrandart(item, UNRAND_OLGREB);
1149         break;
1150 
1151     case MONS_CEREBOV:
1152         if (you.props.exists(CEREBOV_DISARMED_KEY))
1153             break;
1154         force_item = true;
1155         make_item_unrandart(item, UNRAND_CEREBOV);
1156         break;
1157 
1158     case MONS_DISPATER:
1159         force_item = true;
1160         make_item_unrandart(item, UNRAND_DISPATER);
1161         break;
1162 
1163     case MONS_ASMODEUS:
1164         force_item = true;
1165         make_item_unrandart(item, UNRAND_ASMODEUS);
1166         break;
1167 
1168     case MONS_GERYON:
1169         // mv: Probably should be moved out of this switch, but it's not
1170         // worth it, unless we have more monsters with misc. items.
1171         item.base_type = OBJ_MISCELLANY;
1172         item.sub_type  = MISC_HORN_OF_GERYON;
1173         break;
1174 
1175     case MONS_SALAMANDER:
1176         if (is_range_weapon(item))
1177         {
1178             set_item_ego_type(item, OBJ_WEAPONS, SPWPN_FLAMING);
1179             force_item = true;
1180         }
1181         break;
1182 
1183     case MONS_THE_ENCHANTRESS:
1184         if (one_chance_in(6))
1185         {
1186             force_item = true;
1187             set_item_ego_type(item, OBJ_WEAPONS, SPWPN_DISTORTION);
1188             item.plus  = random2(5);
1189         }
1190         break;
1191 
1192     case MONS_MAGGIE:
1193         if (one_chance_in(100) && !get_unique_item_status(UNRAND_WYRMBANE))
1194         {
1195             make_item_unrandart(item, UNRAND_WYRMBANE);
1196             item.plus = 9; // Since she's wearing a dragon armour
1197             force_item = true;
1198         }
1199         break;
1200 
1201     case MONS_MARGERY:
1202         if (one_chance_in(100) && !get_unique_item_status(UNRAND_WYRMBANE))
1203         {
1204             make_item_unrandart(item, UNRAND_WYRMBANE);
1205             item.plus = 10 + random2(2); // Now she's killed at least 2 dragons
1206             force_item = true;
1207         }
1208         break;
1209 
1210     case MONS_ANCESTOR_HEXER:
1211     case MONS_ANCESTOR_BATTLEMAGE:
1212     case MONS_ANCESTOR_KNIGHT:
1213         force_item = true;
1214         upgrade_hepliaklqana_weapon(type, item);
1215         break;
1216 
1217     default:
1218         break;
1219     }
1220 
1221     // Only happens if something in above switch doesn't set it. {dlb}
1222     if (item.base_type == OBJ_UNASSIGNED)
1223         return NON_ITEM;
1224 
1225     if (!force_item && mons_is_unique(type))
1226     {
1227         if (x_chance_in_y(10 + mons_class_hit_dice(type), 100))
1228             level = ISPEC_GOOD_ITEM;
1229         else if (level != ISPEC_GOOD_ITEM)
1230             level += 5;
1231     }
1232 
1233     const object_class_type xitc = item.base_type;
1234     const int xitt = item.sub_type;
1235 
1236     // Note this mess, all the work above doesn't mean much unless
1237     // force_item is set... otherwise we're just going to take the base
1238     // and subtype and create a new item. - bwr
1239     const int thing_created =
1240         ((force_item) ? get_mitm_slot() : items(false, xitc, xitt, level,
1241                                                 item.brand));
1242 
1243     if (thing_created == NON_ITEM)
1244         return NON_ITEM;
1245 
1246     // Copy temporary item into the item array if were forcing it, since
1247     // items() won't have done it for us.
1248     if (force_item)
1249         env.item[thing_created] = item;
1250     else
1251         env.item[thing_created].flags |= item.flags;
1252 
1253     item_def &i = env.item[thing_created];
1254     if (melee_only && (i.base_type != OBJ_WEAPONS || is_range_weapon(i)))
1255     {
1256         destroy_item(thing_created);
1257         return NON_ITEM;
1258     }
1259 
1260     if (force_item)
1261         item_set_appearance(i);
1262 
1263     if (!is_artefact(env.item[thing_created]) && !floor_tile.empty())
1264     {
1265         ASSERT(!equip_tile.empty());
1266         env.item[thing_created].props["item_tile_name"] = floor_tile;
1267         env.item[thing_created].props["worn_tile_name"] = equip_tile;
1268         bind_item_tile(env.item[thing_created]);
1269     }
1270 
1271     return thing_created;
1272 }
1273 
1274 /**
1275  * If you give a monster a weapon, he's going to ask for a glass of milk.
1276  *
1277  * @param mon               The monster to give a weapon to.
1278  * @param level             Item level, which might be absdepth.
1279  * @param second_weapon     Whether this is a recursive call to the function
1280  *                          to give the monster a melee weapon, after we've
1281  *                          already given them something else.
1282  */
_give_weapon(monster * mon,int level,bool second_weapon=false)1283 static void _give_weapon(monster *mon, int level, bool second_weapon = false)
1284 {
1285     ASSERT(mon); // TODO: change to monster &mon
1286 
1287     if (mon->type == MONS_DEEP_ELF_BLADEMASTER && mon->weapon())
1288     {
1289         const item_def &first_sword = *mon->weapon();
1290         ASSERT(first_sword.base_type == OBJ_WEAPONS);
1291         item_def twin_sword = first_sword; // copy
1292         give_specific_item(mon, twin_sword);
1293         return;
1294     }
1295 
1296     const int thing_created = make_mons_weapon(mon->type, level, second_weapon);
1297     if (thing_created == NON_ITEM)
1298         return;
1299 
1300     give_specific_item(mon, thing_created);
1301     if (second_weapon)
1302         return;
1303 
1304     const item_def &i = env.item[thing_created];
1305 
1306     if ((i.base_type != OBJ_WEAPONS
1307                 && i.base_type != OBJ_STAVES
1308                 && i.base_type != OBJ_MISCELLANY) // don't double-gift geryon horn
1309                || is_range_weapon(i))
1310     {
1311         _give_weapon(mon, level, true);
1312     }
1313 
1314     if (mon->type == MONS_FANNAR && i.is_type(OBJ_WEAPONS, WPN_QUARTERSTAFF))
1315     {
1316         make_item_for_monster(mon, OBJ_JEWELLERY, RING_ICE,
1317                               0, 1, ISFLAG_KNOW_TYPE);
1318     }
1319 }
1320 
1321 // Hands out ammunition fitting the monster's launcher (if any), or else any
1322 // throwable missiles depending on the monster type.
_give_ammo(monster * mon,int level,bool mons_summoned)1323 static void _give_ammo(monster* mon, int level, bool mons_summoned)
1324 {
1325     if (const item_def *launcher = mon->launcher())
1326     {
1327         const object_class_type xitc = OBJ_MISSILES;
1328         int xitt = fires_ammo_type(*launcher);
1329 
1330         if (xitt == MI_STONE
1331             && (mon->type == MONS_JOSEPH
1332                 || mon->type == MONS_SATYR
1333                 || (mon->type == MONS_FAUN && one_chance_in(3))
1334                 || one_chance_in(15)))
1335         {
1336             xitt = MI_SLING_BULLET;
1337         }
1338 
1339         const int thing_created = items(false, xitc, xitt, level);
1340 
1341         if (thing_created == NON_ITEM)
1342             return;
1343         else
1344         {
1345             // Sanity check to avoid useless brands.
1346             const int bow_brand  = get_weapon_brand(*launcher);
1347             const int ammo_brand = get_ammo_brand(env.item[thing_created]);
1348             if (ammo_brand != SPMSL_NORMAL
1349                 && (bow_brand == SPWPN_FLAMING || bow_brand == SPWPN_FREEZING))
1350             {
1351                 env.item[thing_created].brand = SPMSL_NORMAL;
1352             }
1353         }
1354 
1355         give_specific_item(mon, thing_created);
1356     }
1357     else
1358     {
1359         // Give some monsters throwables.
1360         int weap_type = -1;
1361         int qty = 0;
1362         int brand = SPMSL_NORMAL;
1363 
1364         switch (mon->type)
1365         {
1366         case MONS_KOBOLD:
1367             if (one_chance_in(10) && level > 1)
1368             {
1369                 weap_type  = MI_DART;
1370                 qty = random_range(2, 8);
1371                 brand = SPMSL_POISONED;
1372                 break;
1373             }
1374             if (x_chance_in_y(2, 5))
1375             {
1376                 weap_type  = MI_STONE;
1377                 qty = 1 + random2(5);
1378             }
1379             break;
1380         case MONS_KOBOLD_BRIGAND:
1381             weap_type  = MI_DART;
1382             if (one_chance_in(3))
1383             {
1384                 // Avoid increasing total amount of generated curare
1385                 // too much.
1386                 brand = SPMSL_CURARE;
1387                 qty = 1;
1388             }
1389             else
1390             {
1391                 qty = random_range(2, 8);
1392                 brand = SPMSL_POISONED;
1393             }
1394             break;
1395 
1396         case MONS_SONJA:
1397             weap_type = MI_DART;
1398             brand = SPMSL_CURARE;
1399             qty = random_range(2, 5);
1400             break;
1401 
1402         case MONS_SPRIGGAN_RIDER:
1403             if (one_chance_in(15))
1404             {
1405                 weap_type = MI_DART;
1406                 brand = SPMSL_CURARE;
1407                 qty = random_range(1, 4);
1408             }
1409             break;
1410 
1411         case MONS_ORC_WARRIOR:
1412             if (one_chance_in(
1413                     player_in_branch(BRANCH_ORC)? 9 : 20))
1414             {
1415                 weap_type = MI_BOOMERANG;
1416                 qty       = random_range(4, 8);
1417             }
1418             break;
1419 
1420         case MONS_ORC:
1421             if (one_chance_in(20))
1422             {
1423                 weap_type = MI_BOOMERANG;
1424                 qty       = random_range(2, 5);
1425             }
1426             break;
1427 
1428         case MONS_URUG:
1429             weap_type  = MI_JAVELIN;
1430             qty = random_range(4, 7);
1431             break;
1432 
1433         // Sprint-only.
1434         case MONS_CHUCK:
1435             weap_type  = MI_LARGE_ROCK;
1436             brand = SPMSL_CHAOS;
1437             qty = random_range(2, 4);
1438             break;
1439 
1440         case MONS_POLYPHEMUS:
1441             weap_type  = MI_LARGE_ROCK;
1442             qty        = random_range(8, 12);
1443             break;
1444 
1445         case MONS_MERFOLK_JAVELINEER:
1446         case MONS_MINOTAUR:
1447             weap_type  = MI_JAVELIN;
1448             qty        = random_range(5, 12);
1449             if (one_chance_in(3))
1450                 level = ISPEC_GOOD_ITEM;
1451             break;
1452 
1453         case MONS_MERFOLK:
1454             if (one_chance_in(3)
1455                 || active_monster_band == BAND_MERFOLK_JAVELINEER)
1456             {
1457                 weap_type  = MI_BOOMERANG;
1458                 qty        = random_range(4, 8);
1459                 if (active_monster_band == BAND_MERFOLK_JAVELINEER)
1460                     break;
1461             }
1462             if (one_chance_in(4) && !mons_summoned)
1463             {
1464                 weap_type  = MI_THROWING_NET;
1465                 qty        = 1;
1466                 if (one_chance_in(4))
1467                     qty += random2(3); // up to three nets
1468             }
1469             break;
1470 
1471         case MONS_DRACONIAN_KNIGHT:
1472         case MONS_GNOLL:
1473             if (!level || coinflip())
1474                 break;
1475             // deliberate fall-through
1476         case MONS_IRONBOUND_BEASTMASTER:
1477             if (!one_chance_in(10))
1478                 break;
1479             // deliberate fall-through to harold
1480 
1481         case MONS_HAROLD: // bounty hunter, up to 5 nets
1482             if (mons_summoned)
1483                 break;
1484 
1485             weap_type  = MI_THROWING_NET;
1486             qty        = 1;
1487             if (one_chance_in(3))
1488                 qty++;
1489             if (mon->type == MONS_HAROLD)
1490                 qty += random2(4);
1491 
1492             break;
1493 
1494         default:
1495             break;
1496         }
1497 
1498         if (weap_type == -1)
1499             return;
1500 
1501         const int thing_created = items(false, OBJ_MISSILES, weap_type, level);
1502 
1503         if (thing_created != NON_ITEM)
1504         {
1505             item_def& w(env.item[thing_created]);
1506 
1507             if (brand != SPMSL_NORMAL)
1508                 set_item_ego_type(w, OBJ_MISSILES, brand);
1509 
1510             w.quantity = qty;
1511             give_specific_item(mon, thing_created);
1512         }
1513     }
1514 }
1515 
make_item_for_monster(monster * mons,object_class_type base,int subtype,int level,int allow_uniques,iflags_t flags)1516 static item_def* make_item_for_monster(
1517     monster* mons,
1518     object_class_type base,
1519     int subtype,
1520     int level,
1521     int allow_uniques,
1522     iflags_t flags)
1523 {
1524     const int bp = get_mitm_slot();
1525     if (bp == NON_ITEM)
1526         return 0;
1527 
1528     const int thing_created = items(allow_uniques, base, subtype, level);
1529     if (thing_created == NON_ITEM)
1530         return 0;
1531 
1532     env.item[thing_created].flags |= flags;
1533 
1534     give_specific_item(mons, thing_created);
1535     return &env.item[thing_created];
1536 }
1537 
_give_shield(monster * mon,int level)1538 static void _give_shield(monster* mon, int level)
1539 {
1540     const item_def *main_weap = mon->mslot_item(MSLOT_WEAPON);
1541     const item_def *alt_weap  = mon->mslot_item(MSLOT_ALT_WEAPON);
1542     item_def *shield;
1543 
1544     // If the monster is already wielding/carrying a two-handed weapon,
1545     // it doesn't get a shield. (Monsters always prefer raw damage to
1546     // protection!)
1547     if (main_weap && mon->hands_reqd(*main_weap) == HANDS_TWO
1548         || alt_weap && mon->hands_reqd(*alt_weap) == HANDS_TWO)
1549     {
1550         return;
1551     }
1552 
1553     switch (mon->type)
1554     {
1555     case MONS_ASTERION:
1556         make_item_for_monster(mon, OBJ_ARMOUR, ARM_KITE_SHIELD,
1557                               level * 2 + 1, 1);
1558         break;
1559     case MONS_DAEVA:
1560     case MONS_MENNAS:
1561         make_item_for_monster(mon, OBJ_ARMOUR, ARM_TOWER_SHIELD,
1562                               level * 2 + 1, 1);
1563         break;
1564 
1565     case MONS_CHERUB:
1566         // Big shields interfere with ranged combat, at least theme-wise.
1567         make_item_for_monster(mon, OBJ_ARMOUR, ARM_BUCKLER, level, 1);
1568         break;
1569 
1570     case MONS_NAGA_WARRIOR:
1571     case MONS_VAULT_GUARD:
1572     case MONS_VAULT_WARDEN:
1573     case MONS_ORC_WARLORD:
1574         if (one_chance_in(3))
1575         {
1576             make_item_for_monster(mon, OBJ_ARMOUR,
1577                                   one_chance_in(3) ? ARM_TOWER_SHIELD
1578                                                    : ARM_KITE_SHIELD,
1579                                   level);
1580         }
1581         break;
1582 
1583     case MONS_DRACONIAN_KNIGHT:
1584         if (coinflip())
1585         {
1586             make_item_for_monster(mon, OBJ_ARMOUR,
1587                                   random_choose(ARM_TOWER_SHIELD, ARM_KITE_SHIELD),
1588                                   level);
1589         }
1590         break;
1591     case MONS_TENGU_WARRIOR:
1592         if (one_chance_in(3))
1593             level = ISPEC_GOOD_ITEM;
1594         // deliberate fall-through
1595     case MONS_TENGU:
1596     case MONS_GNOLL_SERGEANT:
1597         if (mon->type != MONS_TENGU_WARRIOR && !one_chance_in(3))
1598             break;
1599         make_item_for_monster(mon, OBJ_ARMOUR,
1600                               random_choose(ARM_BUCKLER, ARM_KITE_SHIELD),
1601                               level);
1602         break;
1603 
1604     case MONS_TENGU_REAVER:
1605         if (one_chance_in(3))
1606             level = ISPEC_GOOD_ITEM;
1607         make_item_for_monster(mon, OBJ_ARMOUR, ARM_BUCKLER, level);
1608         break;
1609 
1610     case MONS_TENGU_CONJURER:
1611     case MONS_DEEP_ELF_KNIGHT:
1612         if (one_chance_in(3))
1613             make_item_for_monster(mon, OBJ_ARMOUR, ARM_BUCKLER, level);
1614         break;
1615 
1616     case MONS_SPRIGGAN:
1617     case MONS_SPRIGGAN_RIDER:
1618         if (!one_chance_in(4))
1619             break;
1620     // else fall-through
1621     case MONS_SPRIGGAN_DEFENDER:
1622     case MONS_THE_ENCHANTRESS:
1623         shield = make_item_for_monster(mon, OBJ_ARMOUR, ARM_BUCKLER,
1624                       mon->type == MONS_THE_ENCHANTRESS ? ISPEC_GOOD_ITEM :
1625                       mon->type == MONS_SPRIGGAN_DEFENDER ? level * 2 + 1 :
1626                       level);
1627         if (shield && !is_artefact(*shield)) // ineligible...
1628         {
1629             shield->props["item_tile_name"] = "buckler_spriggan";
1630             shield->props["worn_tile_name"] = "buckler_spriggan";
1631             bind_item_tile(*shield);
1632         }
1633         break;
1634 
1635     case MONS_LOUISE:
1636         shield = make_item_for_monster(mon, OBJ_ARMOUR, ARM_TOWER_SHIELD,
1637                                        level * 2 + 1, 1);
1638         if (shield && !is_artefact(*shield))
1639         {
1640             shield->props["item_tile_name"] = "tower shield_louise";
1641             shield->props["worn_tile_name"] = "tower shield_louise";
1642             bind_item_tile(*shield);
1643         }
1644         break;
1645 
1646     case MONS_DONALD:
1647         shield = make_item_for_monster(mon, OBJ_ARMOUR, ARM_KITE_SHIELD,
1648                                        level * 2 + 1, 1);
1649 
1650         if (shield)
1651         {
1652             if (coinflip())
1653             {
1654                 set_item_ego_type(*shield, OBJ_ARMOUR, SPARM_REFLECTION);
1655                 set_equip_desc(*shield, ISFLAG_GLOWING);
1656             }
1657             if (!is_artefact(*shield))
1658             {
1659                 shield->props["item_tile_name"] = "kite_shield_donald";
1660                 shield->props["worn_tile_name"] = "kite_shield_donald";
1661                 bind_item_tile(*shield);
1662             }
1663         }
1664 
1665         break;
1666 
1667     case MONS_NIKOLA:
1668         shield = make_item_for_monster(mon, OBJ_ARMOUR, ARM_GLOVES,
1669                                        level * 2 + 1, 1);
1670         // Gloves.
1671         if (shield && get_armour_ego_type(*shield) == SPARM_ARCHERY)
1672             _strip_item_ego(*shield);
1673         break;
1674 
1675     case MONS_ROBIN:
1676         // The Nikola Hack
1677         make_item_for_monster(mon, OBJ_ARMOUR, ARM_HELMET,
1678                               level * 2 + 1, 1);
1679         break;
1680 
1681     case MONS_CORRUPTER:
1682     case MONS_BLACK_SUN:
1683         if (one_chance_in(3))
1684         {
1685             armour_type shield_type = random_choose(ARM_BUCKLER, ARM_KITE_SHIELD);
1686             make_item_for_monster(mon, OBJ_ARMOUR, shield_type, level);
1687         }
1688         break;
1689 
1690     case MONS_WARMONGER:
1691         make_item_for_monster(mon, OBJ_ARMOUR,
1692                               random_choose(ARM_TOWER_SHIELD, ARM_KITE_SHIELD),
1693                               ISPEC_GOOD_ITEM);
1694         break;
1695 
1696     case MONS_ANCESTOR_KNIGHT:
1697     {
1698         item_def shld;
1699         upgrade_hepliaklqana_shield(*mon, shld);
1700         if (!shld.defined())
1701             break;
1702 
1703         item_set_appearance(shld);
1704 
1705         const int thing_created = get_mitm_slot();
1706         if (thing_created == NON_ITEM)
1707             break;
1708 
1709         env.item[thing_created] = shld;
1710         give_specific_item(mon, thing_created);
1711     }
1712         break;
1713 
1714     default:
1715         break;
1716     }
1717 }
1718 
make_mons_armour(monster_type type,int level)1719 int make_mons_armour(monster_type type, int level)
1720 {
1721     item_def               item;
1722 
1723     item.base_type = OBJ_UNASSIGNED;
1724     item.quantity  = 1;
1725 
1726     bool force_item = false;
1727 
1728     switch (type)
1729     {
1730     case MONS_DEEP_ELF_ARCHER:
1731     case MONS_DEEP_ELF_BLADEMASTER:
1732     case MONS_DEEP_ELF_MASTER_ARCHER:
1733         item.base_type = OBJ_ARMOUR;
1734         item.sub_type  = ARM_LEATHER_ARMOUR;
1735         break;
1736 
1737     case MONS_DEEP_ELF_ANNIHILATOR:
1738     case MONS_DEEP_ELF_DEATH_MAGE:
1739     case MONS_DEEP_ELF_DEMONOLOGIST:
1740     case MONS_DEEP_ELF_HIGH_PRIEST:
1741     case MONS_DEEP_ELF_KNIGHT:
1742     case MONS_DEEP_ELF_AIR_MAGE:
1743     case MONS_DEEP_ELF_FIRE_MAGE:
1744     case MONS_DEEP_ELF_SORCERER:
1745     case MONS_DEEP_ELF_ELEMENTALIST:
1746     case MONS_ORC:
1747     case MONS_ORC_HIGH_PRIEST:
1748     case MONS_ORC_PRIEST:
1749         if (x_chance_in_y(2, 5))
1750         {
1751     case MONS_DUVESSA:
1752     case MONS_IJYB:
1753             item.base_type = OBJ_ARMOUR;
1754             item.sub_type  = random_choose_weighted(4, ARM_LEATHER_ARMOUR,
1755                                                     2, ARM_RING_MAIL,
1756                                                     1, ARM_SCALE_MAIL,
1757                                                     1, ARM_CHAIN_MAIL);
1758         }
1759         else
1760             return NON_ITEM; // er...
1761         break;
1762 
1763     case MONS_ERICA:
1764     case MONS_JOSEPHINE:
1765     case MONS_PSYCHE:
1766         if (one_chance_in(5))
1767             level = ISPEC_GOOD_ITEM;
1768         item.base_type = OBJ_ARMOUR;
1769         item.sub_type  = ARM_ROBE;
1770         break;
1771 
1772     case MONS_GNOLL_SHAMAN:
1773     case MONS_MELIAI:
1774         item.base_type = OBJ_ARMOUR;
1775         item.sub_type  = random_choose(ARM_ROBE, ARM_LEATHER_ARMOUR);
1776         break;
1777 
1778     case MONS_SOJOBO:
1779         level = ISPEC_GOOD_ITEM;
1780         // deliberate fall-through
1781     case MONS_GNOLL_SERGEANT:
1782     case MONS_TENGU_REAVER:
1783         item.base_type = OBJ_ARMOUR;
1784         item.sub_type  = random_choose(ARM_RING_MAIL, ARM_SCALE_MAIL);
1785         if (type == MONS_TENGU_REAVER && one_chance_in(3))
1786             level = ISPEC_GOOD_ITEM;
1787         break;
1788 
1789     case MONS_JOSEPH:
1790     case MONS_IMPERIAL_MYRMIDON:
1791         item.base_type = OBJ_ARMOUR;
1792         item.sub_type  = random_choose_weighted(3, ARM_LEATHER_ARMOUR,
1793                                                 2, ARM_RING_MAIL);
1794         break;
1795 
1796     case MONS_TERENCE:
1797     case MONS_URUG:
1798     case MONS_HAROLD:
1799         item.base_type = OBJ_ARMOUR;
1800         item.sub_type  = random_choose_weighted(1, ARM_RING_MAIL,
1801                                                 3, ARM_SCALE_MAIL,
1802                                                 2, ARM_CHAIN_MAIL);
1803         break;
1804 
1805     case MONS_GRUM:
1806     case MONS_SPRIGGAN_BERSERKER:
1807     case MONS_IRONBOUND_BEASTMASTER:
1808         item.base_type = OBJ_ARMOUR;
1809         item.sub_type  = ARM_ANIMAL_SKIN;
1810         break;
1811 
1812     case MONS_ASTERION:
1813     case MONS_EDMUND:
1814     case MONS_FRANCES:
1815     case MONS_RUPERT:
1816     {
1817         item.base_type = OBJ_ARMOUR;
1818         item.sub_type  = random_choose(ARM_LEATHER_ARMOUR, ARM_RING_MAIL,
1819                                        ARM_SCALE_MAIL,     ARM_CHAIN_MAIL);
1820         break;
1821     }
1822 
1823     case MONS_DONALD:
1824         if (one_chance_in(3))
1825             level = ISPEC_GOOD_ITEM;
1826         item.base_type = OBJ_ARMOUR;
1827         item.sub_type = random_choose_weighted(10, ARM_CHAIN_MAIL,
1828                                                9, ARM_PLATE_ARMOUR,
1829                                                1, ARM_CRYSTAL_PLATE_ARMOUR);
1830         break;
1831 
1832     case MONS_JORGRUN:
1833         if (one_chance_in(3))
1834             level = ISPEC_GOOD_ITEM;
1835         item.base_type = OBJ_ARMOUR;
1836         item.sub_type  = ARM_ROBE;
1837         break;
1838 
1839     case MONS_ORC_WARLORD:
1840     case MONS_SAINT_ROKA:
1841         // Being at the top has its privileges. :)
1842         if (one_chance_in(3))
1843             level = ISPEC_GOOD_ITEM;
1844         // deliberate fall through
1845 
1846     case MONS_ORC_KNIGHT:
1847     case MONS_ORC_WARRIOR:
1848     case MONS_HELL_KNIGHT:
1849     case MONS_LOUISE:
1850     case MONS_VAMPIRE_KNIGHT:
1851     case MONS_JORY:
1852     case MONS_FREDERICK:
1853     case MONS_VAULT_GUARD:
1854     case MONS_VAULT_WARDEN:
1855     case MONS_ANCIENT_CHAMPION:
1856     case MONS_MINOTAUR:
1857         item.base_type = OBJ_ARMOUR;
1858         item.sub_type  = random_choose(ARM_CHAIN_MAIL, ARM_PLATE_ARMOUR);
1859         break;
1860 
1861     case MONS_IRONBOUND_THUNDERHULK:
1862     case MONS_VAULT_SENTINEL:
1863     case MONS_IRONBOUND_CONVOKER:
1864     case MONS_IRONBOUND_FROSTHEART:
1865         item.base_type = OBJ_ARMOUR;
1866         item.sub_type  = random_choose(ARM_RING_MAIL,   ARM_SCALE_MAIL);
1867         break;
1868 
1869     case MONS_MAGGIE:
1870         item.base_type = OBJ_ARMOUR;
1871         item.sub_type = random_choose_weighted(3, ARM_ACID_DRAGON_ARMOUR,
1872                                                3, ARM_SWAMP_DRAGON_ARMOUR,
1873                                                6, ARM_STEAM_DRAGON_ARMOUR);
1874         break;
1875 
1876     case MONS_MARGERY:
1877         item.base_type = OBJ_ARMOUR;
1878         item.sub_type = random_choose_weighted(3, ARM_STORM_DRAGON_ARMOUR,
1879                                                3, ARM_SHADOW_DRAGON_ARMOUR,
1880                                                6, ARM_FIRE_DRAGON_ARMOUR);
1881         break;
1882 
1883     case MONS_HELLBINDER:
1884     case MONS_SALAMANDER_MYSTIC:
1885     case MONS_SERVANT_OF_WHISPERS:
1886     case MONS_RAGGED_HIEROPHANT:
1887     case MONS_FENSTRIDER_WITCH:
1888         item.base_type = OBJ_ARMOUR;
1889         item.sub_type  = ARM_ROBE;
1890         break;
1891 
1892     case MONS_DEATH_KNIGHT:
1893         item.base_type = OBJ_ARMOUR;
1894         item.sub_type  = random_choose_weighted(7, ARM_CHAIN_MAIL,
1895                                                 1, ARM_PLATE_ARMOUR);
1896         break;
1897 
1898     case MONS_MERFOLK_IMPALER:
1899         item.base_type = OBJ_ARMOUR;
1900         item.sub_type = random_choose_weighted(6, ARM_ROBE,
1901                                                4, ARM_LEATHER_ARMOUR);
1902         if (one_chance_in(16))
1903             level = ISPEC_GOOD_ITEM;
1904         break;
1905 
1906     case MONS_MERFOLK_JAVELINEER:
1907         item.base_type = OBJ_ARMOUR;
1908         item.sub_type  = ARM_LEATHER_ARMOUR;
1909         break;
1910 
1911     case MONS_ANGEL:
1912     case MONS_CHERUB:
1913     case MONS_SIGMUND:
1914     case MONS_WIGHT:
1915         item.base_type = OBJ_ARMOUR;
1916         item.sub_type  = ARM_ROBE;
1917         break;
1918 
1919     case MONS_SERAPH:
1920         level          = ISPEC_GOOD_ITEM;
1921         item.base_type = OBJ_ARMOUR;
1922         // obscenely good, don't ever place them randomly
1923         item.sub_type  = coinflip() ? ARM_PEARL_DRAGON_ARMOUR
1924                                     : ARM_FIRE_DRAGON_ARMOUR;
1925         break;
1926 
1927     // Centaurs sometimes wear barding.
1928     case MONS_CENTAUR:
1929     case MONS_CENTAUR_WARRIOR:
1930     case MONS_YAKTAUR:
1931     case MONS_YAKTAUR_CAPTAIN:
1932         if (one_chance_in(type == MONS_CENTAUR              ? 1000 :
1933                           type == MONS_CENTAUR_WARRIOR      ?  500 :
1934                           type == MONS_YAKTAUR              ?  300
1935                        /* type == MONS_YAKTAUR_CAPTAIN ? */ :  200))
1936         {
1937             item.base_type = OBJ_ARMOUR;
1938             item.sub_type  = ARM_BARDING;
1939         }
1940         else
1941             return NON_ITEM; // ???
1942         break;
1943 
1944     case MONS_NAGA:
1945     case MONS_NAGA_MAGE:
1946     case MONS_NAGA_RITUALIST:
1947     case MONS_NAGA_SHARPSHOOTER:
1948     case MONS_NAGA_WARRIOR:
1949     case MONS_NAGARAJA:
1950         if (one_chance_in(type == MONS_NAGA         ?  800 :
1951                           type == MONS_NAGA_WARRIOR ?  300 :
1952                           type == MONS_NAGARAJA     ?  100
1953                                                     :  200))
1954         {
1955             item.base_type = OBJ_ARMOUR;
1956             item.sub_type  = ARM_BARDING;
1957         }
1958         else if (type == MONS_NAGARAJA
1959                  || type == MONS_NAGA_RITUALIST
1960                  || one_chance_in(3))
1961         {
1962             item.base_type = OBJ_ARMOUR;
1963             item.sub_type  = ARM_ROBE;
1964         }
1965         else
1966             return NON_ITEM; // ???
1967         break;
1968 
1969     case MONS_VASHNIA:
1970         item.base_type = OBJ_ARMOUR;
1971         item.sub_type  = ARM_BARDING;
1972         level = ISPEC_GOOD_ITEM;
1973         break;
1974 
1975     case MONS_TENGU_WARRIOR:
1976     case MONS_IRONBOUND_PRESERVER:
1977         item.base_type = OBJ_ARMOUR;
1978         item.sub_type  = random_choose(ARM_LEATHER_ARMOUR, ARM_RING_MAIL);
1979         break;
1980 
1981     case MONS_GASTRONOK:
1982         if (one_chance_in(10) && !get_unique_item_status(UNRAND_PONDERING))
1983         {
1984             force_item = true;
1985             make_item_unrandart(item, UNRAND_PONDERING);
1986         }
1987         else
1988         {
1989             item.base_type = OBJ_ARMOUR;
1990             item.sub_type  = ARM_HAT;
1991 
1992             // Not as good as it sounds. Still just +0 a lot of the time.
1993             level          = ISPEC_GOOD_ITEM;
1994         }
1995         break;
1996 
1997     case MONS_MAURICE:
1998     case MONS_CRAZY_YIUF:
1999         item.base_type = OBJ_ARMOUR;
2000         item.sub_type  = ARM_CLOAK;
2001         break;
2002 
2003     case MONS_FANNAR:
2004     {
2005         force_item = true;
2006         item.base_type = OBJ_ARMOUR;
2007         item.sub_type  = ARM_ROBE;
2008         item.plus = 1 + coinflip();
2009         set_item_ego_type(item, OBJ_ARMOUR, SPARM_COLD_RESISTANCE);
2010         item.flags |= ISFLAG_KNOW_TYPE;
2011         break;
2012     }
2013 
2014     case MONS_DOWAN:
2015     case MONS_JESSICA:
2016     case MONS_KOBOLD_DEMONOLOGIST:
2017     case MONS_OGRE_MAGE:
2018     case MONS_EROLCHA:
2019     case MONS_WIZARD:
2020     case MONS_ILSUIW:
2021     case MONS_MARA:
2022     case MONS_RAKSHASA:
2023     case MONS_MERFOLK_AQUAMANCER:
2024     case MONS_SPRIGGAN:
2025     case MONS_SPRIGGAN_AIR_MAGE:
2026     case MONS_SPRIGGAN_DEFENDER:
2027         item.base_type = OBJ_ARMOUR;
2028         item.sub_type  = ARM_ROBE;
2029         break;
2030 
2031     case MONS_ROBIN:
2032         item.base_type = OBJ_ARMOUR;
2033         item.sub_type  = ARM_ANIMAL_SKIN;
2034         break;
2035 
2036     case MONS_DRACONIAN_SHIFTER:
2037     case MONS_DRACONIAN_SCORCHER:
2038     case MONS_DRACONIAN_ANNIHILATOR:
2039     case MONS_DRACONIAN_STORMCALLER:
2040     case MONS_DRACONIAN_MONK:
2041     case MONS_DRACONIAN_KNIGHT:
2042     case MONS_BAI_SUZHEN:
2043         item.base_type = OBJ_ARMOUR;
2044         item.sub_type  = ARM_CLOAK;
2045         break;
2046 
2047     case MONS_SPRIGGAN_DRUID:
2048         item.base_type = OBJ_ARMOUR;
2049         item.sub_type  = ARM_ROBE;
2050         break;
2051 
2052     case MONS_THE_ENCHANTRESS:
2053         force_item = true;
2054         make_item_unrandart(item, UNRAND_FAERIE);
2055         break;
2056 
2057     case MONS_TIAMAT:
2058         force_item = true;
2059         make_item_unrandart(item, UNRAND_DRAGONSKIN);
2060         break;
2061 
2062     case MONS_ORC_SORCERER:
2063         if (one_chance_in(3))
2064             level = ISPEC_GOOD_ITEM;
2065     case MONS_ORC_WIZARD:
2066     case MONS_BLORK_THE_ORC:
2067     case MONS_NERGALLE:
2068         item.base_type = OBJ_ARMOUR;
2069         item.sub_type  = ARM_ROBE;
2070         break;
2071 
2072     case MONS_BORIS:
2073         level = ISPEC_GOOD_ITEM;
2074         // fall-through
2075     case MONS_AGNES:
2076     case MONS_NECROMANCER:
2077     case MONS_VAMPIRE_MAGE:
2078     case MONS_PIKEL:
2079         item.base_type = OBJ_ARMOUR;
2080         item.sub_type  = ARM_ROBE;
2081         break;
2082 
2083     case MONS_EUSTACHIO:
2084         item.base_type = OBJ_ARMOUR;
2085         item.sub_type  = ARM_LEATHER_ARMOUR;
2086         break;
2087 
2088     case MONS_NESSOS:
2089         item.base_type = OBJ_ARMOUR;
2090         item.sub_type  = ARM_BARDING;
2091         break;
2092 
2093     case MONS_NIKOLA:
2094         item.base_type = OBJ_ARMOUR;
2095         item.sub_type  = ARM_CLOAK;
2096         break;
2097 
2098     case MONS_MONSTROUS_DEMONSPAWN:
2099     case MONS_GELID_DEMONSPAWN:
2100     case MONS_INFERNAL_DEMONSPAWN:
2101     case MONS_TORTUROUS_DEMONSPAWN:
2102     case MONS_CORRUPTER:
2103     case MONS_BLACK_SUN:
2104         item.base_type = OBJ_ARMOUR;
2105         item.sub_type  = random_choose_weighted(2, ARM_LEATHER_ARMOUR,
2106                                                 3, ARM_RING_MAIL,
2107                                                 5, ARM_SCALE_MAIL,
2108                                                 3, ARM_CHAIN_MAIL,
2109                                                 2, ARM_PLATE_ARMOUR);
2110         break;
2111 
2112     case MONS_BLOOD_SAINT:
2113         if (one_chance_in(3))
2114             level = ISPEC_GOOD_ITEM;
2115         item.base_type = OBJ_ARMOUR;
2116         item.sub_type  = ARM_ROBE;
2117         break;
2118 
2119     case MONS_WARMONGER:
2120         if (coinflip())
2121             level = ISPEC_GOOD_ITEM;
2122         item.base_type = OBJ_ARMOUR;
2123         item.sub_type  = random_choose_weighted( 50, ARM_CHAIN_MAIL,
2124                                                 100, ARM_PLATE_ARMOUR,
2125                                                   5, ARM_FIRE_DRAGON_ARMOUR,
2126                                                   5, ARM_ICE_DRAGON_ARMOUR,
2127                                                   5, ARM_ACID_DRAGON_ARMOUR);
2128         break;
2129 
2130     case MONS_HALAZID_WARLOCK:
2131         item.base_type = OBJ_ARMOUR;
2132         item.sub_type  = random_choose(ARM_LEATHER_ARMOUR, ARM_ROBE);
2133         break;
2134 
2135     default:
2136         return NON_ITEM;
2137     }
2138 
2139     // Only happens if something in above switch doesn't set it. {dlb}
2140     if (item.base_type == OBJ_UNASSIGNED)
2141         return NON_ITEM;
2142 
2143     const object_class_type xitc = item.base_type;
2144     const int xitt = item.sub_type;
2145 
2146     if (!force_item && mons_is_unique(type) && level != ISPEC_GOOD_ITEM)
2147     {
2148         if (x_chance_in_y(9 + mons_class_hit_dice(type), 100))
2149             level = ISPEC_GOOD_ITEM;
2150         else
2151             level = level * 2 + 5;
2152     }
2153 
2154     // Note this mess, all the work above doesn't mean much unless
2155     // force_item is set... otherwise we're just going to take the base
2156     // and subtype and create a new item. - bwr
2157     const int thing_created =
2158         ((force_item) ? get_mitm_slot() : items(false, xitc, xitt, level));
2159 
2160     if (thing_created == NON_ITEM)
2161         return NON_ITEM;
2162 
2163     // Copy temporary item into the item array if were forcing it, since
2164     // items() won't have done it for us.
2165     if (force_item)
2166         env.item[thing_created] = item;
2167 
2168     item_def &i = env.item[thing_created];
2169 
2170     if (force_item)
2171         item_set_appearance(i);
2172 
2173     return thing_created;
2174 }
2175 
_give_armour(monster * mon,int level)2176 static void _give_armour(monster* mon, int level)
2177 {
2178     ASSERT(mon); // TODO: make monster &mon
2179     give_specific_item(mon, make_mons_armour(mon->type, level));
2180 }
2181 
_give_gold(monster * mon,int level)2182 static void _give_gold(monster* mon, int level)
2183 {
2184     const int it = items(false, OBJ_GOLD, 0, level);
2185     give_specific_item(mon, it);
2186 }
2187 
give_weapon(monster * mons,int level_number)2188 void give_weapon(monster *mons, int level_number)
2189 {
2190     _give_weapon(mons, level_number);
2191 }
2192 
give_armour(monster * mons,int level_number)2193 void give_armour(monster *mons, int level_number)
2194 {
2195     _give_armour(mons, 1 + level_number/2);
2196 }
2197 
give_shield(monster * mons)2198 void give_shield(monster *mons)
2199 {
2200     _give_shield(mons, -1);
2201 }
2202 
give_item(monster * mons,int level_number,bool mons_summoned)2203 void give_item(monster *mons, int level_number, bool mons_summoned)
2204 {
2205     ASSERT(level_number > -1); // debugging absdepth0 changes
2206 
2207     if (mons->type == MONS_MAURICE)
2208         _give_gold(mons, level_number);
2209 
2210     _give_book(mons, level_number);
2211     _give_wand(mons, level_number);
2212     _give_potion(mons, level_number);
2213     _give_weapon(mons, level_number);
2214     _give_ammo(mons, level_number, mons_summoned);
2215     _give_armour(mons, 1 + level_number / 2);
2216     _give_shield(mons, 1 + level_number / 2);
2217 }
2218 
view_monster_equipment(monster * mon)2219 void view_monster_equipment(monster* mon)
2220 {
2221     for (unsigned int i = 0; i <= MSLOT_LAST_VISIBLE_SLOT; ++i)
2222     {
2223         if (mon->inv[i] == NON_ITEM)
2224             continue;
2225 
2226         item_def &item = env.item[mon->inv[i]];
2227         set_ident_flags(item, ISFLAG_IDENT_MASK);
2228         item.flags |= ISFLAG_SEEN;
2229         if (item.base_type == OBJ_WANDS)
2230             set_ident_type(item, true);
2231     }
2232 }
2233