File: object.h

package info (click to toggle)
crossfire 1.75.0-9
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 24,168 kB
  • sloc: ansic: 83,169; sh: 4,659; perl: 1,736; lex: 1,443; makefile: 1,199; python: 43
file content (614 lines) | stat: -rw-r--r-- 28,147 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
/**
 * @file
 * Object structure, the core of Crossfire.
 */

#include "dialog.h"

#ifndef OBJECT_H
#define OBJECT_H

/** Object tag, unique during the whole game. */
typedef uint32_t tag_t;
#define NUM_BODY_LOCATIONS      13  /**< Number of body locations. */
#define BODY_ARMS               1   /**< This should be the index of the arms. */

/**
 * One body location.
 * See common/item.c.
 */
typedef struct body_locations_struct {
    const char *save_name;      /**< Name used to load/save it to disk */
    const char *use_name;       /**< Name used when describing an item we can use */
    const char *nonuse_name;    /**< Name to describe objects we can't use */
} body_locations_struct;

extern body_locations_struct body_locations[NUM_BODY_LOCATIONS];

extern const char *const move_name[];

/**
 * Each object (this also means archetypes!) could have a few of these
 * "dangling" from it; this could also end up containing 'parse errors'.
 *
 * key and value are shared-strings.
 *
 * Please use object_get_value(), object_set_value() from object.c rather than
 * accessing the list directly.
 * Exception is if you want to walk this list for some reason.
 */
typedef struct _key_value {
    const char *key;          /**< Name of the key. */
    const char *value;        /**< Key's value. */
    struct _key_value *next;  /**< Next key in the list. */
} key_value;

/**
 * @defgroup WILL_APPLY_xxx What monsters apply
 * How monsters should handle some items they have or things on the ground.
 * Those flags correspond to the object::will_apply field.
 */
/*@{*/
#define WILL_APPLY_HANDLE       0x1   /**< Apply handles and triggers. */
#define WILL_APPLY_TREASURE     0x2   /**< Open chests. */
#define WILL_APPLY_EARTHWALL    0x4   /**< Destroy earthwalls. */
#define WILL_APPLY_DOOR         0x8   /**< Open non-locked doors. */
#define WILL_APPLY_FOOD         0x10  /**< Eat food (not drinks). */
/*@}*/

/**
 * Checks if an object still exists.
 * @param op
 * object to check
 * @param old_tag
 * old tag of the object.
 * @return
 * true if the object was destroyed, 0 otherwise
 */
#define object_was_destroyed(op, old_tag) \
    (op->count != old_tag || QUERY_FLAG(op, FLAG_FREED))


/**
 * Defines default size of the *spell_tags pointer.
 * The OB_SPELL_TAG_HASH is a simple mechanism to get/set the
 * spell tags based on a simple hash - it should change if the tag size
 * also changes.  Note that since count is used for this, this value
 * is effectively random or at least fairly evenly distributed, at
 * least in the low bits.  And a size of 16 lets us do a very
 * fast operation.
 */
#define SPELL_TAG_SIZE 16
/**
 * Get the hash on an object for a specified count.
 * @param op what to check.
 * @param count item to check the hash for.
 */
#define OB_SPELL_TAG_HASH(op, count)    (op->spell_tags[count&0xf])
/**
 * Check whether a tag matches in the tags.
 * @param op item to check against.
 * @param count tag to check.
 */
#define OB_SPELL_TAG_MATCH(op, count)   (op->spell_tags[count&0xf] == count)

/**
 * Only add new values to this list if somewhere in the program code, it is
 * actually needed.  Just because you add a new monster does not mean it has to
 * have a type defined here.  That only needs to happen if in some .c file, it
 * needs to do certain special actions based on the monster type, that can not
 * be handled by any of the numerous flags.  Also, if you add new entries, try
 * and fill up the holes in this list.  Additionally, when you add a new entry,
 * include it in the table in common/item.c
 *
 * type 0 is undefined and indicates non-valid type information.
 */
enum object_type {
    PLAYER = 1,
    TRANSPORT = 2, /**< see doc/Developers/objects */
    ROD = 3,
    TREASURE = 4,
    POTION = 5,
    FOOD = 6,
    POISON = 7,
    BOOK = 8,
    CLOCK = 9,
    DRAGON_FOCUS = 10, /**< Used during character creation */
    ARROW = 13,
    BOW = 14,
    WEAPON = 15,
    ARMOUR = 16,
    PEDESTAL = 17,
    ALTAR = 18,
    LOCKED_DOOR = 20,
    SPECIAL_KEY = 21,
    MAP = 22,
    DOOR = 23,
    KEY = 24,
    TIMED_GATE = 26,
    TRIGGER = 27,
    GRIMREAPER = 28,
    MAGIC_EAR = 29,
    TRIGGER_BUTTON = 30,
    TRIGGER_ALTAR = 31,
    TRIGGER_PEDESTAL = 32,
    SHIELD = 33,
    HELMET = 34,
    MONEY = 36,
    CLASS = 37, /**< Object for applying character class modifications to someone */
    AMULET = 39,
    PLAYERMOVER = 40,
    TELEPORTER = 41,
    CREATOR = 42,
    SKILL = 43, /**< Also see ::SKILL_TOOL (74) below */
    EARTHWALL = 45,
    GOLEM = 46,
    THROWN_OBJ = 48,
    BLINDNESS = 49,
    GOD = 50,
    DETECTOR = 51,       /**< peterm:  detector is an object
                                       * which notices the presense of
                                       * another object and is triggered
                                       * like buttons. */
    TRIGGER_MARKER = 52, /**< inserts an invisible, weightless
                                   * force into a player with a
                                   * specified string WHEN TRIGGERED. */
    DEAD_OBJECT = 53,
    DRINK = 54,
    MARKER = 55, /**< inserts an invisible, weightless
                                   * force into a player with a
                                   * specified string. */
    HOLY_ALTAR = 56,
    PLAYER_CHANGER = 57,
    BATTLEGROUND = 58, /**< battleground, by Andreas Vogl */
    PEACEMAKER = 59,   /**< Object owned by a player which can
                                     * convert a monster into a peaceful
                                     * being incapable of attack.  */
    GEM = 60,
    FIREWALL = 62,
    CHECK_INV = 64,  /**< b.t. thomas@nomad.astro.psu.edu */
    MOOD_FLOOR = 65, /**< b.t. thomas@nomad.astro.psu.edu
                                   * values of last_sp set how to
                                   * change:
                                   * 0 = furious, all monsters become
                                   *     aggressive
                                   * 1 = angry, all but friendly become
                                   *     aggressive
                                   * 2 = calm, all aggressive monsters
                                   *     calm down
                                   * 3 = sleep, all monsters fall asleep
                                   * 4 = charm, monsters become pets */
    EXIT = 66,
    ENCOUNTER = 67,
    SHOP_FLOOR = 68,
    SHOP_MAT = 69,
    RING = 70,
    FLOOR = 71,      /**< Floor tile -> native layer 0 */
    FLESH = 72,      /**< animal 'body parts' -b.t. */
    INORGANIC = 73,  /**< metals, minerals, dragon scales */
    SKILL_TOOL = 74, /**< Allows the use of a skill */
    LIGHTER = 75,
    WALL = 77,        /**< Wall. Put it always in layer 1 if
                                        * not set is_floor */
    MISC_OBJECT = 79, /**< misc. objects are for objects
                                    * without a function in the engine.
                                    * Like statues, clocks, chairs...
                                    *  If perhaps we create a function
                                    * where we can sit on chairs, we
                                    * create a new type and remove all
                                    * chairs from here. */
    MONSTER = 80,     /**< A real, living creature */
    LAMP = 82,        /**< Lamp */
    DUPLICATOR = 83,  /**< Duplicator/multiplier object */
    SPELLBOOK = 85,
    CLOAK = 87,
    SPINNER = 90,
    GATE = 91,
    BUTTON = 92,
    CF_HANDLE = 93,
    HOLE = 94, /* When open, objects fall through */
    TRAPDOOR = 95,
    SIGN = 98,
    BOOTS = 99,
    GLOVES = 100,
    SPELL = 101,
    SPELL_EFFECT = 102,
    CONVERTER = 103,
    BRACERS = 104,
    POISONING = 105,
    SAVEBED = 106,
    WAND = 109,
    SCROLL = 111,
    DIRECTOR = 112,
    GIRDLE = 113,
    FORCE = 114,
    POTION_RESIST_EFFECT = 115, /**< A force, holding the effect of a
                                  * resistance potion */
    EVENT_CONNECTOR = 116,      /**< Lauwenmark: an invisible object
                                          * holding a plugin event hook */
    CLOSE_CON = 121,            /**< Eneq((at)csd.uu.se): Id for
                                              * close_container archetype. */
    CONTAINER = 122,
    ARMOUR_IMPROVER = 123,
    WEAPON_IMPROVER = 124,
    SKILLSCROLL = 130, /**< can add a skill to player's
                                     * inventory -bt.*/
    DEEP_SWAMP = 138,
    IDENTIFY_ALTAR = 139,
    SHOP_INVENTORY = 150, /**< Mark Wedel (mark@pyramid.com) Shop
                                    * inventories */
    RUNE = 154,
    TRAP = 155,
    POWER_CRYSTAL = 156,
    CORPSE = 157,
    DISEASE = 158,
    SYMPTOM = 159,
    BUILDER = 160,  /**< Generic item builder, see subtypes
                                      * below */
    MATERIAL = 161, /**< Material for building */
    MIMIC = 162,
    OBJECT_TYPE_MAX = 163, /**< Update if you add new types */
};

/**
 * Main Crossfire structure, one ingame object.
 *
 * Note that the ordering of this structure is sort of relevent -
 * object_copy() copies everything over beyond 'name' using memcpy.
 * Thus, values that need to be copied need to be located beyond that
 * point.
 *
 * However, if you're keeping a pointer of some sort, you probably
 * don't just want it copied, so you'll need to add to common/object.c,
 * e.g. copy-object
 *
 * I've tried to clean up this structure a bit (in terms of formatting)
 * by making it more consistent.  I've also tried to locate some of the fields
 * more logically together (put the item related ones together, the monster
 * related ones, etc.
 * This structure is best viewed with about a 100 width screen.
 * MSW 2002-07-05
 *
 * See the @ref page_object "documentation page" for more details.
 */
typedef struct obj {
    /* These variables are not changed by object_copy() */
    struct pl   *contr;         /**< Pointer to the player which control this object */
    struct obj  *next;          /**< Pointer to the next object in the free/used list */
    struct obj  *prev;          /**< Pointer to the previous object in the free/used list*/
    struct obj  *active_next;   /**< Next object in the 'active' list
                                 * This is used in process_events
                                 * so that the entire object list does not
                                 * need to be gone through.*/
    struct obj  *active_prev;   /**< Previous object in the 'active list
                                 * This is used in process_events
                                 * so that the entire object list does not
                                 * need to be gone through. */
    struct obj  *below;         /**< Pointer to the object stacked below this one */
    struct obj  *above;         /**< Pointer to the object stacked above this one */
                                /* Note: stacked in the *same *environment*/
    struct obj  *inv;           /**< Pointer to the first object in the inventory */
    struct obj  *container;     /**< Current container being used.  I think this
                                 * is only used by the player right now. */
    struct obj  *env;           /**< Pointer to the object which is the environment.
                                 * This is typically the container that the object is in. */
    struct obj  *more;          /**< Pointer to the rest of a large body of objects */
    struct obj  *head;          /**< Points to the main object of a large body */
    struct mapdef *map;         /**< Pointer to the map in which this object is present */

    tag_t       count;          /**< Unique object number for this object */
    struct struct_dialog_information *dialog_information; /**< Parsed dialog information for this object.
                                                           * Valid if FLAG_DIALOG_PARSED is set (but can be NULL). */

    /* These get an extra add_refcount(), after having been copied by memcpy().
     *
     * Fields below name (included) are copied by memcpy in object_copy().
     *
     * If adding something that needs a refcount updated, make sure you modify
     * object_copy() to do so.  
     * Everything below here also gets cleared by object_clear().
     */
    const char  *name;          /**< The name of the object, obviously... */
    /* Place new attributes that should get copied and cleared below name */

    sstring     artifact;       /**< If set, the item is the artifact with this name and the matching type. */
    const char  *name_pl;       /**< The plural name of the object */
    const char  *anim_suffix;   /**< Used to determine combined animations */
    const char  *title;         /**< Of foo, etc */
    const char  *race;          /**< Human, goblin, dragon, etc */
    const char  *slaying;       /**< Which race to do double damage to.
                                 * If this is an exit, this is the filename */
    const char  *skill;         /**< Name of the skill this object uses/grants */
    const char* msg;            /**< If this is a book/sign/magic mouth/etc. Modify with
                                     object_set_msg() to preserve invariants. */
    const char  *lore;          /**< Obscure information about this object,
                                 * to get put into books and the like. */

    int16_t      x, y;           /**< Position in the map for this object */
    int16_t      ox, oy;         /**< For debugging: Where it was last inserted */
    float       speed;          /**< Frequency of object 'moves' relative to server tick rate */
    float       speed_left;     /**< How much speed is left to spend this round */
    float       weapon_speed;   /**< The overall speed of this object */
    float       weapon_speed_left; /**< How much speed is left to spend this round */
    const Face    *face;    /**< Face with colors */
    uint32_t      nrof;          /**< Number of objects. Consider accessing
                                      with NROF() macro. */
    int8_t       direction;      /**< Means the object is moving that way. */
    int8_t       facing;         /**< Object is oriented/facing that way. */

    /* This next big block are basically used for monsters and equipment */
    uint8_t       type;           /**< PLAYER, BULLET, etc.  See define.h */
    uint8_t       subtype;        /**< Subtype of object */
    uint16_t      client_type;    /**< Public type information.  see doc/Developers/objects */
    int16_t      resist[NROFATTACKS]; /**< Resistance adjustments for attacks */
    uint32_t      attacktype;     /**< Bitmask of attacks this object does */
    uint32_t      path_attuned;   /**< Paths the object is attuned to */
    uint32_t      path_repelled;  /**< Paths the object is repelled from */
    uint32_t      path_denied;    /**< Paths the object is denied access to */
    const char  *materialname;  /**< Specific material name */
    uint16_t      material;       /**< What materials this object consist of */
    int8_t       magic;          /**< Any magical bonuses to this item */
    uint8_t       state;          /**< How the object was last drawn (animation) */
    int32_t      value;          /**< How much money it is worth (or contains) */
    int16_t      level;          /**< Level of creature or object */

    /* Note that the last_.. values are sometimes used for non obvious
     * meanings by some objects, eg, sp penalty, permanent exp.
     */
    int32_t      last_eat;       /**< How long since we last ate */
    int32_t      last_heal;      /**< Last healed. Depends on constitution */
    int32_t      last_sp;        /**< As last_heal, but for spell points */
    int16_t      last_grace;     /**< As last_sp, except for grace */
    int16_t      invisible;      /**< How much longer the object will be invis */
    uint8_t       pick_up;        /**< See crossfire.doc */
    int8_t       item_power;     /**< Power rating of the object */
    int8_t       gen_sp_armour;  /**< Sp regen penalty this object has (was last_heal)*/
    int8_t       glow_radius;    /**< indicates the glow radius of the object */
    int32_t      weight;         /**< Attributes of the object */
    int32_t      weight_limit;   /**< Weight-limit of object */
    int32_t      carrying;       /**< How much weight this object contains */
    living       stats;          /**< Str, Con, Dex, etc */
  //int64_t      perm_exp;       /**< Permanent exp */
    int64_t      total_exp;      /**< All exp ever earned (used to calc perm_exp) */
    struct obj  *current_weapon; /**< Pointer to the weapon currently used */
    uint32_t      weapontype;     /**< Type of weapon */
    int8_t       body_info[NUM_BODY_LOCATIONS];  /**< Body info as loaded from the file */
    int8_t       body_used[NUM_BODY_LOCATIONS];  /**< Calculated value based on items equipped */
                                /* See the doc/Developers/objects for more info about body locations */

    /* Following mostly refers to fields only used for monsters */
    struct obj  *owner;         /**< Pointer to the object which controls this one.
                                 * Owner should not be referred to directly -
                                 * object_get_owner() should be used instead. */
    tag_t       ownercount;     /**< What count the owner had (in case owner has been freed) */
    struct obj  *enemy;         /**< Monster/player to follow even if not closest */
    struct obj  *attacked_by;   /**< This object start to attack us! only player & monster */
    tag_t       attacked_by_count; /**< The tag of attacker, so we can be sure */
    uint8_t       run_away;          /**< Monster runs away if it's hp goes below this percentage. */
    struct treasureliststruct *randomitems; /**< Items to be generated */
    struct obj  *chosen_skill;  /**< The skill chosen to use */
    uint8_t      hide;           /**< The object is hidden, not invisible */
    /* changes made by kholland@sunlab.cit.cornell.edu */
    /* allows different movement patterns for attackers */
    int32_t      move_status;    /**< What stage in attack mode */
    uint16_t      attack_movement;/**< What kind of attack movement */
    uint8_t       will_apply;     /**< See crossfire.doc and @ref WILL_APPLY_xxx */
    uint8_t       sound_chance;   /**< Ignored. Probability, 0 to 100, of the object emitting a sound. */
    struct obj  *spellitem;     /**< Spell ability monster is choosing to use */
    double      expmul;         /**< needed experience = (calc_exp*expmul) - means some
                                 * races/classes can need less/more exp to gain levels */

    /* Spell related information, may be useful elsewhere
     * Note that other fields are used - these files are basically
     * only used in spells.
     */
    int16_t      casting_time;   /**< Time left before spell goes off */
    int16_t      duration;       /**< Number of moves (see 'speed') spell lasts */
    uint8_t       duration_modifier; /**< how level modifies duration */
    int8_t       range;          /**< Range of the spell */
    uint8_t       range_modifier; /**< How going up in level affects range  */
    uint8_t       dam_modifier;   /**< How going up in level affects damage */
    struct obj  *spell;         /**< Spell that was being cast */
    char        *spellarg;      /**< Optional argument when casting obj::spell. */

    /* Following are values used by any object */
    struct archt *arch;         /**< Pointer to archetype */
    struct archt *other_arch;   /**< Pointer used for various things - mostly used for what
                                 * this objects turns into or what this object creates */
    uint32_t      flags[4];       /**< Various flags */
    const Animations *animation;   /**< Animation of this item, NULL if not animated. */
    uint8_t       anim_speed;     /**< Ticks between animation-frames */
    uint8_t       last_anim;      /**< Last sequence used to draw face */
    const Animations *temp_animation; /**< A temporary animation. */
    uint8_t       temp_anim_speed; /**< Ticks between temporary animation-frames */
    uint8_t       smoothlevel;    /**< how to smooth this square around*/
    uint8_t       map_layer;      /**< What level to draw this on the map */

    MoveType    move_type;      /**< Type of movement this object uses */
    MoveType    move_block;     /**< What movement types this blocks */
    MoveType    move_allow;     /**< What movement types explicitly allowed */
    MoveType    move_on;        /**< Move types affected moving on to this space */
    MoveType    move_off;       /**< Move types affected moving off this space */
    MoveType    move_slow;      /**< Movement types this slows down */
    float       move_slow_penalty; /**< How much this slows down the object */

    const char  *custom_name;   /**< Custom name assigned by player */
    key_value   *key_values;    /**< Fields not explictly known by the loader. */

    tag_t       *spell_tags;      /**< Tags used for spell effect merging. */
} object;

/**
 * Used to link together several objects
 */
typedef struct oblnk {
    object *ob;         /**< Item to link to. */
    struct oblnk *next; /**< Next item to link to. */
    tag_t id;           /**< ob's tag, in case it is removed. */
} objectlink;

/**
 * Used to link together several object links
 */
typedef struct oblinkpt {
    struct oblnk *link;   /**< Items for this value. */
    long value;           /**< Used as connected value in buttons/gates */
    struct oblinkpt *next;/**< Next value in the list. */
} oblinkpt;

/**
 * The archetype structure is a set of rules on how to generate and manipulate
 * objects which point to archetypes.
 * This probably belongs in arch.h, but there really doesn't appear to
 * be much left in the archetype - all it really is is a holder for the
 * object and pointers.  This structure should get removed, and just replaced
 * by the object structure
 */
typedef struct archt {
    const char *name;       /**< More definite name, like "generate_kobold" */
    struct archt *next;     /**< Next archetype in a linked list */
    struct archt *head;     /**< The main part of a linked object */
    struct archt *more;     /**< Next part of a linked object */
    object clone;           /**< An object from which to do object_copy() */
    int8_t tail_x, tail_y;   /**< Where the lower right most portion of the object is
                             * in comparison to the head. */
    int reference_count;    /**< How many times this temporary archetype is used. If 0, "permanent" archetype. */
} archetype;

extern object *objects;
extern object *active_objects;

extern int nrofallocobjects;
extern int nroffreeobjects;

static inline int compare_flags(const object *p, const object *q) {
    return ((p)->flags[0] == (q)->flags[0]) &&
        ((p)->flags[1] == (q)->flags[1]) &&
        ((p)->flags[2] == (q)->flags[2]) &&
        ((p)->flags[3] == (q)->flags[3]);
}

static inline int query_flag(const object *op, int flag) {
    return op->flags[flag / 32] & (1U << (flag % 32));
}

static inline void clear_flag(object *op, int flag) {
    op->flags[flag / 32] &= ~(1U << (flag % 32));
}

static inline void set_flag(object *op, int flag) {
    op->flags[flag / 32] |= (1U << (flag % 32));
}

/**
 * This returns TRUE if the object is something that
 * should be displayed in the look window
 */
#define LOOK_OBJ(ob) (!ob->invisible && ob->type != PLAYER && ob->type != EVENT_CONNECTOR)

/**
 * @defgroup UP_OBJ_xxx Object update flags
 *
 * Used by object_update() to know if the object being passed is
 * being added or removed.
 */
/*@{*/
#define UP_OBJ_INSERT   1   /**< Object was inserted. */
#define UP_OBJ_REMOVE   2   /**< Object was removed. */
#define UP_OBJ_CHANGE   3   /**< Object changed. */
#define UP_OBJ_FACE     4   /**< Only thing that changed was the face. In this case,
                             * we always update everything as that is easier than trying
                             * to look at what may have changed. */
/*@}*/

/**
 * @defgroup FREE_OBJ_xxx Object free flags
 *
 * Used by object_free() to specify options.
 */
/*@{*/
#define FREE_OBJ_FREE_INVENTORY      1 /**< Free inventory objects; if not set, drop inventory. */
#define FREE_OBJ_NO_DESTROY_CALLBACK 2 /**< Do not run the destroy callback. */
#define FREE_OBJ_DROP_ABOVE_FLOOR    4 /**< If FREE_OBJ_FREE_INVENTORY is not set, drop inventory just above ground instead on top. */
/*@}*/

/**
 * @defgroup INS_xxx Object insertion flags.
 *
 * These are flags passed to object_insert_in_map() and
 * object_insert_in_ob().  Note that all flags may not be meaningful
 * for both functions.
 * Most are fairly explanatory:
 * - INS_NO_MERGE: don't try to merge inserted object with ones alrady
 *    on space.
 * - INS_ABOVE_FLOOR_ONLY: Put object immediatly above the floor.
 * - INS_NO_WALK_ON: Don't call check_walk_on against the
 *    originator - saves cpu time if you know the inserted object
 *    is not meaningful in terms of having an effect.
 * - INS_ON_TOP: Always put object on top.  Generally only needed when loading
 *     files from disk and ordering needs to be preserved.
 * - INS_BELOW_ORIGINATOR: Insert new object immediately below originator -
 *     Use for treasure chests so the new object is the highest thing
 *     beneath the player, but not actually above it.  Note - the
 *     map and x,y coordinates for the object to be inserted must
 *     match the originator.
 * - INS_MAP_LOAD: disable lots of checkings done at insertion to
 *     speed up map loading process, as we assume the ordering in
 *     loaded map is correct.
 *
 * Note that INS_BELOW_ORIGINATOR, INS_ON_TOP, INS_ABOVE_FLOOR_ONLY
 * are mutually exclusive.  The behaviour for passing more than one
 * should be considered undefined - while you may notice what happens
 * right now if you pass more than one, that could very well change
 * in future revisions of the code.
 */
/*@{*/
#define INS_NO_MERGE            0x0001  /**< Don't try to merge with other items. */
#define INS_ABOVE_FLOOR_ONLY    0x0002  /**< Put object immediatly above the floor. */
#define INS_NO_WALK_ON          0x0004  /**< Don't call check_walk_on against the originator. */
#define INS_ON_TOP              0x0008  /**< Always put object on top. */
#define INS_BELOW_ORIGINATOR    0x0010  /**< Insert new object immediately below originator. */
#define INS_MAP_LOAD            0x0020  /**< Disable lots of checkings. */
/*@}*/

#define ARCH_SINGULARITY        "singularity"   /**< Archetype for singularity. */
#define ARCH_SINGULARITY_LEN    11              /**< Length of ::ARCH_SINGULARITY. */
#define ARCH_DETECT_MAGIC       "detect_magic"  /**< Archetype for detect magic spell. */
#define ARCH_DEPLETION          "depletion"     /**< Archetype for depletion. */
#define ARCH_SYMPTOM            "symptom"       /**< Archetype for disease symptom. */
#define ARCH_PORTAL_FAILED      "town_portal_failed"    /**< Archetype for town portal failure. */
#define ARCH_SPELL_BLOCKED      "spell_blocked" /**< Archetype when a spell is blocked (unholy ground or non magic). */
#define ARCH_SPELL_BUNGLE       "spell_bungle"  /**< Archetype when player bungles a spell. */

/**
 * Returns the head part of an object. For single-tile objects returns the
 * object itself.
 *
 * @param op
 * the object
 * @return
 * the head object
 */
#define HEAD(op) ((op)->head != NULL ? (op)->head : (op))

static inline bool IS_PLAYER(object *op) {
    return op->type == PLAYER;
}

/**
 * Determine whether the given object can have an HP bar.
 */
static inline bool CAN_PROBE(const object *ob) {
    return QUERY_FLAG(ob, FLAG_ALIVE) &&
        (ob->type == PLAYER || QUERY_FLAG(ob, FLAG_MONSTER));
}

/**
 * Returns ob->nrof, unless it is 0, in which case return 1. Most of the code
 * assumes that nrof=0 is the same as nrof=1.
 */
static inline uint32_t NROF(const object * const ob) {
    return ob->nrof ? ob->nrof : 1;
}

#endif /* OBJECT_H */