49 static void slow_living(
object *op,
object *hitter,
int dam);
54 static void poison_living(
object *op,
object *hitter,
int dam);
71 for (tmp = op->
inv; tmp != NULL; tmp = tmp->
below)
104 int i, roll, saves = 0,
attacks = 0, number;
144 if (op->
resist[number] == 100)
148 else if ((20-mt->
save[number])/3 > originator->
stats.
dam)
173 object *env = op->
env;
175 int x = op->
x, y = op->
y;
184 while (inv != NULL) {
298 tag_t op_tag, next_tag = 0;
336 if (!(type&~(AT_COUNTERSPELL|
AT_MAGIC))) {
339 type &= ~AT_COUNTERSPELL;
350 next_tag = next->
count;
369 next_tag = next->
count;
380 if (tmp->
map != map || tmp->
x != x || tmp->
y != y)
390 for (pl = tmp->
inv; pl; pl = pl->
below) {
444 if (dam == 9998 && op->
type ==
DOOR) {
445 sprintf(buf1,
"unlock %s", op->
name);
446 sprintf(buf2,
" unlocks");
450 sprintf(buf1,
"hit %s", op->
name);
451 sprintf(buf2,
" hits");
453 }
else if (dam == 0) {
454 sprintf(buf1,
"missed %s", op->
name);
455 sprintf(buf2,
" misses");
469 }
else if (op->
type ==
DOOR && !found) {
519 sprintf(buf1,
"hit");
599 sprintf(buf1,
"hit");
600 sprintf(buf2,
"hits");
617 sprintf(buf,
"%s's %s %s you.", hitter->
owner->
name, hitter->
name, buf2);
619 sprintf(buf,
"%s%s you.", hitter->
name, buf2);
636 sprintf(buf,
"You %s.", buf1);
670 }
else if (
rndm(0, 5) != 0)
692 int *simple_attack) {
694 LOG(
llevError,
"BUG: get_attack_mode(): freed object\n");
698 *target = (*target)->
head;
700 *hitter = (*hitter)->
head;
701 if ((*hitter)->env != NULL || (*target)->env != NULL) {
707 || (*hitter)->map == NULL
709 LOG(
llevError,
"BUG: hitter (arch %s, name %s) with no relation to target\n", (*hitter)->arch->name, (*hitter)->name);
729 static int abort_attack(
object *target,
object *hitter,
int simple_attack) {
732 if (hitter->
env == target || target->
env == hitter)
740 return new_mode != simple_attack;
762 int simple_attack, roll, dam = 0;
764 const char *op_name = NULL;
765 tag_t op_tag, hitter_tag;
788 hitter_tag = hitter->
count;
817 if (roll == 20 || op->
stats.
ac >= base_wc-roll) {
818 int hitdam = base_dam;
823 "You attacked and lost your spell!", NULL);
829 "You were hit and lost your spell!", NULL);
832 "%s was hit by %s and lost a spell.",
833 "%s was hit by %s and lost a spell.",
834 op_name, hitter->
name);
838 if (!simple_attack) {
856 "You were hit by a wild attack. You are no longer hidden!",
886 "You are splashed by acid!\n", NULL);
932 hitter = hitter->
head;
954 if (tmp->
head != NULL)
976 object *container, *hitter;
977 int hit_something = 0;
978 tag_t victim_tag, hitter_tag;
979 sint16 victim_x, victim_y;
981 const char *old_skill = NULL;
984 for (hitter = op->
inv; hitter; hitter = hitter->
below) {
1008 victim_x = victim->
x;
1009 victim_y = victim->
y;
1010 victim_map = victim->
map;
1011 victim_tag = victim->
count;
1012 hitter_tag = hitter->
count;
1025 if (container != NULL) {
1026 old_skill = hitter->
skill;
1044 if (container != NULL) {
1046 hitter->
skill = old_skill;
1052 if (hit_something && op->
speed <= 10.0) {
1054 if (container == NULL) {
1075 if (victim_x != hitter->
x || victim_y != hitter->
y) {
1077 hitter->
x = victim_x;
1078 hitter->
y = victim_y;
1087 if (hit_something && op->
speed >= 10.0)
1160 target->
enemy = owner;
1181 int doesnt_slay = 1;
1186 LOG(
llevError,
"hit_with_one_attacktype: Invalid attacknumber passed: %u\n", attacknum);
1191 LOG(
llevError,
"hit_with_one_attacktype called with negative damage: %d\n", dam);
1214 if (op->
resist[attacknum]) {
1217 dam *= (100-op->
resist[attacknum]);
1229 if ((op->
resist[attacknum] >= 100)
1236 switch (attacknum) {
1303 for (tmp = op->
inv; tmp != NULL; tmp = tmp->
below) {
1312 if (tmp->
magic < -4)
1331 "The %s's acid corrodes your %s!",
1332 "The %s's acid corrodes your %s!",
1333 name_hitter, name_op);
1386 if (owner && owner != hitter) {
1430 LOG(
llevError,
"%s was hit by %s with non-specific chaos.\n", name_op, name_hitter);
1437 LOG(
llevError,
"%s was hit by %s with counterspell attack.\n", name_op, name_hitter);
1486 new_hp = hitter->
stats.
hp+dam;
1489 if (new_hp > hitter->
stats.
hp)
1534 static int kill_object(
object *op,
int dam,
object *hitter,
int type) {
1540 object *owner = NULL;
1541 object *skop = NULL;
1587 LOG(
llevError,
"BUG: hit_player(): Encountered golem without owner.\n");
1616 name_hitter[0] =
'\0';
1623 time_t t = time(NULL);
1628 tmv = localtime(&t);
1629 strftime(buf, 256,
"%a %b %d %H:%M:%S %Y", tmv);
1640 if (owner != hitter) {
1646 "You killed %s with %s.",
1647 "You killed %s with %s.",
1671 if (op->
type ==
PLAYER && owner != op && !battleg)
1680 skill = hitter->
skill;
1687 LOG(
llevError,
"kill_object - unable to find skill that killed monster\n");
1692 if ((!skop || skop->
type !=
SKILL) && skill) {
1708 if (owner != hitter) {
1713 (void)sprintf(buf,
"%s killed %s with %s%s.", owner->
name, name_op, name_hitter, battleg ?
" (duel)" : (pk ?
" (pk)" :
""));
1715 (void)sprintf(buf,
"%s killed %s%s%s.", hitter->
name, op->
name,
1717 " in hand to hand combat" :
"", battleg ?
" (duel)" : (pk ?
" (pk)" :
""));
1723 skill = skop->
skill;
1739 "Your foe has fallen!\nVICTORY!!!", NULL);
1762 #ifdef PARTY_KILL_LOG
1767 add_kill_to_party(party, name,
query_name(op), exp);
1778 if (owner1 != NULL && owner1->
type ==
PLAYER) {
1782 "Your pet, the %s, is killed by %s.",
1783 "Your pet, the %s, is killed by %s.",
1823 hitter = hitter->
head;
1831 if ((owner =
get_owner(hitter)) != NULL) {
1842 return friendlyfire;
1869 int maxdam = 0, ndam = 0, attacktype = 1, magic = (type&
AT_MAGIC);
1870 int maxattacktype, attacknum;
1871 int body_attack = op && op->
head;
1873 tag_t op_tag, hitter_tag;
1885 hitter_tag = hitter->
count;
1904 if (!simple_attack && op->
type ==
DOOR) {
1907 for (tmp = op->
inv; tmp != NULL; tmp = tmp->
below)
1927 LOG(
llevDebug,
"hit player: attacktype %d, dam %d\n", type, dam);
1937 dam = (dam > (
rndm(0, 99))) ? 1 : 0;
1963 && god->
race != NULL
1968 maxattacktype = type;
1969 for (attacknum = 0; attacknum <
NROFATTACKS; attacknum++, attacktype = 1<<attacknum) {
1982 if (type&attacktype) {
1987 if (ndam >= maxdam) {
1989 maxattacktype = 1<<attacknum;
1993 if (attacktype ==
AT_DEATH && ndam > 0)
2004 if (friendlyfire && maxdam) {
2018 for (at = op->
arch; at != NULL; at = at->
more)
2024 remainder = 100*(maxdam%area)/area;
2026 if (RANDOM()%100 < remainder)
2031 LOG(
llevDebug,
"Attacktype %d did %d damage\n", type, maxdam);
2090 LOG(
llevError,
"SPLITTING without other_arch error.\n");
2178 "You suddenly feel very ill.", NULL);
2189 "Your %s poisons %s.",
2190 "Your %s poisons %s.",
2219 "The world suddenly moves very fast!", NULL);
2262 "You suddenly feel very confused!", NULL);
2277 object *tmp, *owner;
2305 "Your attack blinds %s!",
2306 "Your attack blinds %s!",
2380 int atk_lev, def_lev, kill_lev;
2390 def_lev = op->
level;
2398 if (atk_lev >= def_lev) {
2406 if (kill_lev >= def_lev) {
2412 *dam *= kill_lev/def_lev;
2436 switch (hitter->
type) {
2472 object *attacker = hitter;
2476 if (!target || !hitter || !hitter->
map || !target->
map || !
on_same_map(hitter, target)) {
2477 LOG(
llevError,
"BUG: adj_attackroll(): hitter and target not on same map\n");
2483 if ((attacker =
get_owner(hitter)) == NULL)
static void scare_creature(object *target, object *hitter)
void spring_trap(object *trap, object *victim)
static int abort_attack(object *target, object *hitter, int simple_attack)
int get_map_flags(mapstruct *oldmap, mapstruct **newmap, sint16 x, sint16 y, sint16 *nx, sint16 *ny)
const char * determine_god(object *op)
archetype * find_archetype(const char *name)
void share_exp(object *op, sint64 exp, const char *skill, int flag)
void drain_stat(object *op)
const char * get_ob_key_value(const object *op, const char *const key)
void change_exp(object *op, sint64 exp, const char *skill_name, int flag)
void leave(player *pl, int draw_exit)
materialtype_t * name_to_material(const char *name)
void set_owner(object *op, object *owner)
#define MSG_TYPE_ATTRIBUTE_BAD_EFFECT_START
static void attack_message(int dam, int type, object *op, object *hitter)
static void thrown_item_effect(object *, object *)
object * present_in_ob(uint8 type, const object *op)
sstring add_refcount(sstring str)
attackmess_t attack_mess[NROFATTACKMESS][MAXATTACKMESS]
EXTERN materialtype_t * materialt
void shuffle_attack(object *op, int change_face)
static int stick_arrow(object *op, object *tmp)
void free_string(sstring str)
void fix_stopped_item(object *op, mapstruct *map, object *originator)
#define SET_ANIMATION(ob, newanim)
void esrv_update_item(int flags, object *pl, object *op)
short freearr_x[SIZEOFFREE]
object * merge_ob(object *op, object *top)
#define MSG_TYPE_ADMIN_PLAYER
void draw_ext_info(int flags, int pri, const object *pl, uint8 type, uint8 subtype, const char *message, const char *oldmessage)
int free_no_drop(object *op)
static void tear_down_wall(object *op)
object * ranges[range_size]
void update_object(object *op, int action)
#define MSG_TYPE_VICTIM_WAS_HIT
void blind_living(object *op, object *hitter, int dam)
void change_luck(object *op, int value)
static int is_aimed_missile(object *op)
#define MSG_TYPE_ATTACK_FUMBLE
#define FLAG_IS_LIGHTABLE
object * stop_item(object *op)
void remove_friendly_object(object *op)
method_ret ob_apply(object *op, object *applier, int aflags)
static int did_make_save_item(object *op, int type, object *originator)
const object * find_god(const char *name)
void draw_ext_info_format(int flags, int pri, const object *pl, uint8 type, uint8 subtype, const char *new_format, const char *old_format,...)
struct archt * other_arch
static int kill_object(object *op, int dam, object *hitter, int type)
#define MSG_TYPE_ATTACK_PET_DIED
static int adj_attackroll(object *hitter, object *target)
short freearr_y[SIZEOFFREE]
#define FLAG_KNOWN_MAGICAL
int rndm(int min, int max)
struct obj * chosen_skill
int change_abil(object *op, object *tmp)
sint64 check_exp_loss(const object *op, sint64 exp)
void confuse_living(object *op, object *hitter, int dam)
void remove_ob(object *op)
#define ATNR_CANCELLATION
static int get_attack_mode(object **target, object **hitter, int *simple_attack)
object * create_archetype(const char *name)
EXTERN const char * undead_name
int is_wraith_pl(object *op)
EXTERN Chaos_Attacks ATTACKS[22]
const char * materialname
void update_all_los(const mapstruct *map, int x, int y)
#define FLAG_UNAGGRESSIVE
#define ATNR_LIFE_STEALING
void save_throw_object(object *op, uint32 type, object *originator)
int find_first_free_spot(const object *ob, mapstruct *m, int x, int y)
sint64 calc_skill_exp(object *who, object *op, object *skill)
int stand_in_light(object *op)
void add_friendly_object(object *op)
#define MSG_TYPE_ATTRIBUTE
object * get_owner(object *op)
int execute_global_event(int eventcode,...)
struct obj * current_weapon
object * present_in_ob_by_name(int type, const char *str, const object *op)
void paralyze_living(object *op, object *hitter, int dam)
void play_sound_map(sint8 sound_type, object *emitter, int dir, const char *action)
int op_on_battleground(object *op, int *x, int *y, archetype **trophy)
object * present_arch(const archetype *at, mapstruct *m, int x, int y)
static void deathstrike_living(object *op, object *hitter, int *dam)
int process_object(object *op)
int on_same_map(const object *op1, const object *op2)
#define QUERY_FLAG(xyz, p)
#define CLEAR_FLAG(xyz, p)
object * insert_ob_in_ob(object *op, object *where)
#define ATNR_COUNTERSPELL
object * insert_ob_in_map(object *op, mapstruct *m, object *originator, int flag)
#define MSG_TYPE_ATTACK_DID_KILL
void copy_owner(object *op, object *clone)
#define FLAG_READY_WEAPON
void npc_call_help(object *op)
const int turn_bonus[MAX_STAT+1]
sint16 resist[NROFATTACKS]
#define FLAG_KNOWN_CURSED
int snprintf(char *dest, int max, const char *format,...)
#define SOUND_TYPE_HIT_BY
static void cancellation(object *op)
#define NUM_ANIMATIONS(ob)
object * present_arch_in_ob(const archetype *at, const object *op)
object * decrease_ob_nr(object *op, uint32 i)
int hit_map(object *op, int dir, uint32 type, int full_hit)
static int hit_with_one_attacktype(object *op, object *hitter, int dam, uint32 attacknum)
void check_physically_infect(object *victim, object *hitter)
int out_of_map(mapstruct *m, int x, int y)
int execute_event(object *op, int eventcode, object *activator, object *third, const char *message, int fix)
void update_ob_speed(object *op)
sstring add_string(const char *str)
#define MSG_TYPE_ATTACK_DID_HIT
void play_sound_player_only(player *pl, sint8 sound_type, object *emitter, int dir, const char *action)
#define GET_MAP_OB(M, X, Y)
int can_see_enemy(object *op, object *enemy)
void counterspell(object *op, int dir)
static int attack_ob_simple(object *op, object *hitter, int base_dam, int base_wc)
void apply_anim_suffix(object *who, sstring suffix)
void LOG(LogLevel logLevel, const char *format,...)
int did_make_save(const object *op, int level, int bonus)
void make_visible(object *op)
#define was_destroyed(op, old_tag)
struct _materialtype * next
object * last_skill_ob[NUM_SKILLS]
void kill_player(object *op)
void query_name(const object *op, char *buf, size_t size)
void free_object(object *ob)
static void slow_living(object *op, object *hitter, int dam)
int hit_player(object *op, int dam, object *hitter, uint32 type, int full_hit)
int random_roll(int min, int max, const object *op, int goodbad)
#define USING_SKILL(op, skill)
int friendly_fire(object *op, object *hitter)
int pk_max_experience_percent
void replace_insert_ob_in_map(const char *arch_string, object *op)
void fix_object(object *op)
object * arch_to_object(archetype *at)
int attack_ob(object *op, object *hitter)
object * fix_stopped_arrow(object *op)
static void poison_living(object *op, object *hitter, int dam)
object * hit_with_arrow(object *op, object *victim)
const char *const attacks[NROFATTACKS]
#define MSG_TYPE_ATTACK_PET_HIT