1 #pragma once
2 
3 #include <vector>
4 
5 #include "artefact-prop-type.h"
6 #include "beam-type.h"
7 #include "conduct-type.h"
8 #include "energy-use-type.h"
9 #include "equipment-type.h"
10 #include "god-type.h"
11 #include "item-prop-enum.h"
12 #include "kill-method-type.h"
13 #include "mon-holy-type.h"
14 #include "random-var.h"
15 #include "ouch.h"
16 #include "pronoun-type.h"
17 #include "reach-type.h"
18 #include "size-part-type.h"
19 #include "size-type.h"
20 #include "stat-type.h"
21 
22 using std::vector;
23 
24 enum class ev_ignore
25 {
26     none       = 0,
27     helpless   = 1<<0,
28     unided     = 1<<1,
29 };
30 DEF_BITFIELD(ev_ignore_type, ev_ignore);
31 
32 struct bolt;
33 
34 class actor
35 {
36 public:
37     virtual ~actor();
38 
39     monster_type type;
40     mid_t        mid;
41     virtual int       mindex() const = 0;
42 
43     virtual bool is_player() const = 0;
is_monster()44     bool is_monster() const { return !is_player(); }
45     virtual monster* as_monster() = 0;
46     virtual player* as_player() = 0;
47     virtual const monster* as_monster() const = 0;
48     virtual const player* as_player() const = 0;
49 
50     virtual kill_category kill_alignment() const = 0;
51     virtual god_type  deity() const = 0;
52 
53     virtual bool      alive() const = 0;
54 
55     // Should return false for perma-summoned things.
56     virtual bool is_summoned(int* duration = nullptr,
57                              int* summon_type = nullptr) const = 0;
58 
59     virtual bool is_perm_summoned() const = 0;
60 
61     // [ds] Low-level moveto() - moves the actor without updating relevant
62     // grids, such as env.mgrid.
63     virtual void moveto(const coord_def &c, bool clear_net = true) = 0;
64 
65     // High-level actor movement. If in doubt, use this. Returns false if the
66     // actor cannot be moved to the target, possibly because it is already
67     // occupied.
68     virtual bool move_to_pos(const coord_def &c, bool clear_net = true,
69                              bool force = false) = 0;
70 
71     virtual void apply_location_effects(const coord_def &oldpos,
72                                         killer_type killer = KILL_NONE,
73                                         int killernum = -1) = 0;
74 
75     virtual void set_position(const coord_def &c);
pos()76     const coord_def& pos() const { return position; }
77 
self_destruct()78     virtual void self_destruct() { }
79 
80     // Blink the actor to the destination. c should be a
81     // valid target, though the method returns false
82     // if the blink fails.
83     virtual bool blink_to(const coord_def &c, bool quiet = false) = 0;
84 
85     virtual bool      swimming() const = 0;
86     virtual bool      submerged() const = 0;
87     virtual bool      floundering() const = 0;
88 
89     // Returns true if the actor is exceptionally well balanced.
90     virtual bool      extra_balanced() const = 0;
91 
92     virtual int       get_hit_dice() const = 0;
93     virtual int       get_experience_level() const = 0;
94 
95     virtual bool shove(const char* feat_name = "") = 0;
96     virtual bool can_pass_through_feat(dungeon_feature_type grid) const = 0;
97     virtual bool can_pass_through(int x, int y) const;
98     virtual bool can_pass_through(const coord_def &c) const;
99     virtual bool can_burrow() const = 0;
100 
101     virtual bool is_habitable_feat(dungeon_feature_type actual_grid) const = 0;
102             bool is_habitable(const coord_def &pos) const;
103 
104     virtual size_type body_size(size_part_type psize = PSIZE_TORSO,
105                                 bool base = false) const = 0;
106 
107     virtual brand_type damage_brand(int which_attack = -1) = 0;
108     virtual int       damage_type(int which_attack = -1) = 0;
109     virtual item_def *weapon(int which_attack = -1) const = 0;
primary_weapon()110     const item_def *primary_weapon() const
111     {
112         return weapon(0);
113     }
114     virtual random_var attack_delay(const item_def *projectile = nullptr,
115                                     bool rescale = true) const = 0;
116     virtual int has_claws(bool allow_tran = true) const = 0;
117     virtual item_def *shield() const = 0;
118     virtual item_def *slot_item(equipment_type eq,
119                                 bool include_melded=false) const = 0;
120     virtual int wearing(equipment_type slot, int sub_type,
121                         bool calc_unid = true) const = 0;
122     virtual int wearing_ego(equipment_type slot, int sub_type,
123                             bool calc_unid = true) const = 0;
124     virtual int scan_artefacts(artefact_prop_type which_property,
125                                bool calc_unid = true,
126                                vector<const item_def *> *matches = nullptr) const = 0;
127 
128     virtual hands_reqd_type hands_reqd(const item_def &item,
129                                        bool base = false) const;
130 
131             bool can_wield(const item_def* item,
132                            bool ignore_curse = false,
133                            bool ignore_brand = false,
134                            bool ignore_shield = false,
135                            bool ignore_transform = false) const;
136     virtual bool can_wield(const item_def &item,
137                            bool ignore_curse = false,
138                            bool ignore_brand = false,
139                            bool ignore_shield = false,
140                            bool ignore_transform = false) const = 0;
141     virtual bool could_wield(const item_def &item,
142                              bool ignore_brand = false,
143                              bool ignore_transform = false,
144                              bool quiet = true) const = 0;
145 
146     virtual void lose_energy(energy_use_type, int /*div*/ = 1, int /*mult*/ = 1)
147     {
148     }
149     virtual void gain_energy(energy_use_type, int /*div*/ = 1, int /*mult*/ = 1)
150     {
151     }
152 
153     virtual string name(description_level_type type,
154                         bool force_visible = false,
155                         bool force_article = false) const = 0;
156     virtual string pronoun(pronoun_type which_pronoun,
157                            bool force_visible = false) const = 0;
158     virtual string conj_verb(const string &verb) const = 0;
159     virtual string hand_name(bool plural, bool *can_plural = nullptr) const = 0;
160     virtual string foot_name(bool plural, bool *can_plural = nullptr) const = 0;
161     virtual string arm_name(bool plural, bool *can_plural = nullptr) const = 0;
162 
163     virtual bool fumbles_attack() = 0;
164 
fights_well_unarmed(int)165     virtual bool fights_well_unarmed(int /*heavy_armour_penalty*/)
166     {
167         return true;
168     }
169     virtual void attacking(actor *other, bool ranged = false) = 0;
170     virtual bool can_go_berserk() const = 0;
171     virtual bool go_berserk(bool intentional, bool potion = false) = 0;
172     virtual bool berserk() const = 0;
173     virtual bool can_see_invisible(bool calc_unid = true) const = 0;
174     virtual bool invisible() const = 0;
175     virtual bool nightvision() const = 0;
176     virtual reach_type reach_range() const = 0;
177 
178     // Would looker be able to see the actor when in LOS?
179     virtual bool visible_to(const actor *looker) const = 0;
180 
181     // Is the given cell within LOS of the actor?
182     virtual bool see_cell(const coord_def &c) const;
183     virtual bool see_cell_no_trans(const coord_def &c) const;
184 
185     // Can the actor actually see the target?
186     virtual bool can_see(const actor &target) const;
187 
188     // Visibility as required by messaging. In usual play:
189     //   Does the player know what's happening to the actor?
190     bool observable() const;
191 
192     virtual bool is_icy() const = 0;
193     virtual bool is_fiery() const = 0;
194     virtual bool is_skeletal() const = 0;
195     virtual bool can_mutate() const = 0;
196     virtual bool can_safely_mutate(bool temp = true) const = 0;
197     virtual bool can_polymorph() const = 0;
198     virtual bool can_bleed(bool temp = true) const = 0;
199     virtual bool is_stationary() const = 0;
200     virtual bool malmutate(const string &reason) = 0;
201     virtual bool polymorph(int pow, bool allow_immobile = true) = 0;
202     virtual bool drain(const actor *agent, bool quiet = false,
203                        int pow = 3) = 0;
204     virtual int  hurt(const actor *attacker, int amount,
205                       beam_type flavour = BEAM_MISSILE,
206                       kill_method_type kill_type = KILLED_BY_MONSTER,
207                       string source = "",
208                       string aux = "",
209                       bool cleanup_dead = true,
210                       bool attacker_effects = true) = 0;
211     virtual bool heal(int amount) = 0;
212     virtual void banish(const actor *agent, const string &who = "",
213                         const int power = 0, bool force = false) = 0;
214     virtual void blink() = 0;
215     virtual void teleport(bool right_now = false,
216                           bool wizard_tele = false) = 0;
217     virtual bool poison(actor *attacker, int amount = 1, bool force = false) = 0;
218     virtual bool sicken(int amount) = 0;
219     virtual void paralyse(const actor *attacker, int strength,
220                           string source = "") = 0;
221     virtual void petrify(const actor *attacker, bool force = false) = 0;
222     virtual bool fully_petrify(bool quiet = false) = 0;
223     virtual void slow_down(actor *attacker, int strength) = 0;
224     virtual void confuse(actor *attacker, int strength) = 0;
225     virtual void put_to_sleep(actor *attacker, int strength,
226                               bool hibernate = false) = 0;
227     virtual void weaken(actor *attacker, int pow) = 0;
228     virtual void expose_to_element(beam_type element, int strength = 0,
229                                    bool slow_cold_blood = true) = 0;
drain_stat(stat_type,int)230     virtual void drain_stat(stat_type /*stat*/, int /*amount*/) { }
231     virtual void splash_with_acid(const actor* evildoer, int acid_strength = -1,
232                                   bool allow_corrosion = true,
233                                   const char* hurt_msg = nullptr) = 0;
234     virtual bool corrode_equipment(const char* corrosion_source = "the acid",
235                                    int degree = 1) = 0;
236 
237     virtual bool can_hibernate(bool holi_only = false,
238                                bool intrinsic_only = false) const;
239     virtual bool can_sleep(bool holi_only = false) const;
240     virtual void check_awaken(int disturbance) = 0;
241     virtual int beam_resists(bolt &beam, int hurted, bool doEffects,
242                              string source = "") = 0;
243     virtual bool can_feel_fear(bool include_unknown) const = 0;
244 
245     virtual int  skill(skill_type sk, int scale = 1, bool real = false,
246                        bool temp = true) const = 0;
247     int  skill_rdiv(skill_type sk, int mult = 1, int div = 1) const;
248 
249 #define TORPOR_SLOWED_KEY "torpor_slowed"
250     bool torpor_slowed() const;
251 
252     virtual int heads() const = 0;
253 
254     virtual int stat_hp() const = 0;
255     virtual int stat_maxhp() const = 0;
256 
257     virtual int stealth () const = 0;
258 
259     virtual bool can_throw_large_rocks() const = 0;
260 
261     virtual int armour_class(bool calc_unid = true) const = 0;
262     virtual int gdr_perc() const = 0;
263     int apply_ac(int damage, int max_damage = 0,
264                  ac_type ac_rule = ac_type::normal,
265                  bool for_real = true) const;
266     virtual int evasion(ev_ignore_type ign = ev_ignore::none,
267                         const actor *attacker = nullptr) const = 0;
268     virtual bool shielded() const = 0;
269     virtual int shield_bonus() const = 0;
270     virtual int shield_block_penalty() const = 0;
271     virtual int shield_bypass_ability(int tohit) const = 0;
272     virtual void shield_block_succeeded();
273     virtual bool missile_repulsion() const = 0;
274 
275     // Combat-related virtual class methods
276     virtual int unadjusted_body_armour_penalty() const = 0;
277     virtual int adjusted_body_armour_penalty(int scale = 1) const = 0;
278     virtual int adjusted_shield_penalty(int scale) const = 0;
279     virtual int armour_tohit_penalty(bool random_factor, int scale = 1) const = 0;
280     virtual int shield_tohit_penalty(bool random_factor, int scale = 1) const = 0;
281 
282     virtual monster_type mons_species(bool zombie_base = false) const = 0;
283 
284     virtual mon_holy_type holiness(bool temp = true) const = 0;
285     virtual bool undead_or_demonic(bool temp = true) const = 0;
286     virtual bool holy_wrath_susceptible() const;
287     virtual bool is_holy() const = 0;
288     virtual bool is_nonliving(bool temp = true) const = 0;
289     bool evil() const;
290     virtual int  how_chaotic(bool check_spells_god = false) const = 0;
291     virtual bool is_unbreathing() const = 0;
292     virtual bool is_insubstantial() const = 0;
293     virtual int res_acid(bool calc_unid = true) const = 0;
294     virtual bool res_damnation() const = 0;
295     virtual int res_fire() const = 0;
296     virtual int res_steam() const = 0;
297     virtual int res_cold() const = 0;
298     virtual int res_elec() const = 0;
299     virtual int res_poison(bool temp = true) const = 0;
300     virtual bool res_miasma(bool temp = true) const = 0;
301     virtual int res_water_drowning() const = 0;
302     virtual bool res_sticky_flame() const = 0;
303     virtual int res_holy_energy() const = 0;
304     virtual int res_negative_energy(bool intrinsic_only = false) const = 0;
305     virtual bool res_torment() const = 0;
306     virtual bool res_polar_vortex() const = 0;
307     virtual bool res_petrify(bool temp = true) const = 0;
308     virtual int res_constrict() const = 0;
309     virtual int willpower(bool calc_unid = true) const = 0;
310     virtual int check_willpower(int power);
311     virtual bool no_tele(bool calc_unid = true, bool permit_id = true,
312                          bool blink = false) const = 0;
313     virtual int inaccuracy() const;
314     virtual bool antimagic_susceptible() const = 0;
315 
316     virtual bool res_corr(bool calc_unid = true, bool temp = true) const;
317     bool has_notele_item(bool calc_unid = true,
318                          vector<const item_def *> *matches = nullptr) const;
319     virtual bool stasis() const = 0;
320     virtual bool cloud_immune(bool calc_unid = true, bool items = true) const;
321     virtual bool angry(bool calc_unid = true, bool items = true) const;
322     virtual bool clarity(bool calc_unid = true, bool items = true) const;
323     virtual bool faith(bool calc_unid = true, bool items = true) const;
324     virtual int archmagi(bool calc_unid = true, bool items = true) const;
325     virtual int spec_evoke(bool calc_unid = true, bool items = true) const;
326     virtual bool no_cast(bool calc_unid = true, bool items = true) const;
327     virtual bool reflection(bool calc_unid = true, bool items = true) const;
328     virtual bool extra_harm(bool calc_unid = true, bool items = true) const;
329 
330     virtual bool rmut_from_item(bool calc_unid = true) const;
331     virtual bool evokable_berserk(bool calc_unid = true) const;
332     virtual bool evokable_invis(bool calc_unid = true) const;
333 
334     // Return an int so we know whether an item is the sole source.
335     virtual int equip_flight(bool calc_unid = true) const;
336     virtual int spirit_shield(bool calc_unid = true, bool items = true) const;
337     virtual bool rampaging(bool calc_unid = true, bool items = true) const;
338 
339     virtual bool is_banished() const = 0;
340     virtual bool is_web_immune() const = 0;
341     virtual bool airborne() const = 0;
342     virtual bool ground_level() const;
343 
344     virtual bool is_dragonkind() const;
345     virtual int  dragon_level() const;
346 
347     virtual bool paralysed() const = 0;
348     virtual bool cannot_move() const = 0;
349     virtual bool cannot_act() const = 0;
350     virtual bool confused() const = 0;
351     virtual bool caught() const = 0;
asleep()352     virtual bool asleep() const { return false; }
353 
354     // self_halo: include own halo (actually if self_halo = false
355     //            and has a halo, returns false; so if you have a
356     //            halo you're not affected by others' halos for this
357     //            purpose)
358     virtual bool backlit(bool self_halo = true) const = 0;
359     virtual bool umbra() const = 0;
360     // Within any actor's halo?
361     virtual bool haloed() const;
362     // Within an umbra?
363     virtual bool umbraed() const;
364     // Halo radius.
365     virtual int halo_radius() const = 0;
366     // Silence radius.
367     virtual int silence_radius() const = 0;
368     // Demonspawn silence radius
369     virtual int demon_silence_radius() const = 0;
370     // Liquefying radius.
371     virtual int liquefying_radius() const = 0;
372     virtual int umbra_radius() const = 0;
373 
374     virtual bool petrifying() const = 0;
375     virtual bool petrified() const = 0;
376 
377     virtual bool liquefied_ground() const = 0;
378 
379     virtual bool handle_trap();
380 
god_conduct(conduct_type,int)381     virtual void god_conduct(conduct_type /*thing_done*/, int /*level*/) { }
382 
incapacitated()383     virtual bool incapacitated() const
384     {
385         return cannot_move()
386             || asleep()
387             || confused()
388             || caught()
389             || petrifying();
390     }
391 
392     virtual bool wont_attack() const = 0;
393     virtual mon_attitude_type temp_attitude() const = 0;
394     virtual mon_attitude_type real_attitude() const = 0;
395 
396     virtual bool has_spell(spell_type spell) const = 0;
397 
398     virtual bool     will_trigger_shaft() const;
399     virtual level_id shaft_dest() const;
400     virtual bool     do_shaft() = 0;
401 
402     coord_def position;
403 
404     CrawlHashTable props;
405 
406     int shield_blocks;                 // Count of shield blocks this round.
407 
408     // Constriction stuff:
409 
410     mid_t constricted_by;
411     int escape_attempts;
412 
413     // Map from mid to duration.
414     typedef map<mid_t, int> constricting_t;
415     // Freed and set to nullptr when empty.
416     constricting_t *constricting;
417 
418     void start_constricting(actor &whom, int duration = 0);
419 
420     void stop_constricting(mid_t whom, bool intentional = false,
421                            bool quiet = false);
422     void stop_constricting_all(bool intentional = false, bool quiet = false);
423     void stop_directly_constricting_all(bool intentional = false,
424                                         bool quiet = false);
425     void stop_being_constricted(bool quiet = false);
426 
427     bool can_constrict(const actor* defender, bool direct,
428                        bool engulf = false) const;
429     bool has_invalid_constrictor(bool move = false) const;
430     void clear_invalid_constrictions(bool move = false);
431     void accum_has_constricted();
432     void handle_constriction();
433     bool is_constricted() const;
434     bool is_directly_constricted() const;
435     bool is_constricting() const;
436     int num_constricting() const;
437     virtual bool has_usable_tentacle() const = 0;
438     virtual int constriction_damage(bool direct) const = 0;
439     virtual bool constriction_does_damage(bool direct) const = 0;
440     virtual bool clear_far_engulf(bool force = false) = 0;
441 
442     // Be careful using this, as it doesn't keep the constrictor in sync.
443     void clear_constricted();
444 
445     string describe_props() const;
446 
447     string resist_margin_phrase(int margin) const;
448 
449     void collide(coord_def newpos, const actor *agent, int pow);
450 
451     static const actor *ensure_valid_actor(const actor *act);
452     static actor *ensure_valid_actor(actor *act);
453 
454 private:
455     void constriction_damage_defender(actor &defender, int duration);
456     void end_constriction(mid_t whom, bool intentional, bool quiet);
457 };
458 
459 bool actor_slime_wall_immune(const actor *actor);
460