diff --git a/code/__DEFINES/combat.dm b/code/__DEFINES/combat.dm
index 8b7f4830c13..4c2708bf9dd 100644
--- a/code/__DEFINES/combat.dm
+++ b/code/__DEFINES/combat.dm
@@ -64,6 +64,17 @@
#define THROWN_PROJECTILE_ATTACK 4
#define LEAP_ATTACK 5
+//attack visual effects
+#define ATTACK_EFFECT_PUNCH "punch"
+#define ATTACK_EFFECT_KICK "kick"
+#define ATTACK_EFFECT_SMASH "smash"
+#define ATTACK_EFFECT_CLAW "claw"
+#define ATTACK_EFFECT_DISARM "disarm"
+#define ATTACK_EFFECT_BITE "bite"
+#define ATTACK_EFFECT_MECHFIRE "mech_fire"
+#define ATTACK_EFFECT_MECHTOXIN "mech_toxin"
+#define ATTACK_EFFECT_BOOP "boop" //Honk
+
//Embedded objects
#define EMBEDDED_PAIN_CHANCE 15 //Chance for embedded objects to cause pain (damage user)
#define EMBEDDED_ITEM_FALLOUT 5 //Chance for embedded object to fall out (causing pain but removing the object)
diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm
index 6a658886f83..bf01bca6e3c 100644
--- a/code/_onclick/item_attack.dm
+++ b/code/_onclick/item_attack.dm
@@ -62,8 +62,7 @@
user.lastattacked = M
M.lastattacker = user
- if(user != M)
- user.do_attack_animation(M)
+ user.do_attack_animation(M)
M.attacked_by(src, user, def_zone)
add_attack_logs(user, M, "Attacked with [name] (INTENT: [uppertext(user.a_intent)]) (DAMTYPE: [uppertext(damtype)])", admin_notify = (force > 0 && damtype != STAMINA))
diff --git a/code/game/atoms_movable.dm b/code/game/atoms_movable.dm
index c7e6401e204..7ab561f0814 100644
--- a/code/game/atoms_movable.dm
+++ b/code/game/atoms_movable.dm
@@ -363,3 +363,70 @@
target.fingerprints += fingerprints
target.fingerprintshidden += fingerprintshidden
target.fingerprintslast = fingerprintslast
+
+/atom/movable/proc/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
+ if(!no_effect && (visual_effect_icon || used_item))
+ do_item_attack_animation(A, visual_effect_icon, used_item)
+
+ if(A == src)
+ return //don't do an animation if attacking self
+ var/pixel_x_diff = 0
+ var/pixel_y_diff = 0
+ var/final_pixel_y = initial(pixel_y)
+ if(end_pixel_y)
+ final_pixel_y = end_pixel_y
+
+ var/direction = get_dir(src, A)
+ if(direction & NORTH)
+ pixel_y_diff = 8
+ else if(direction & SOUTH)
+ pixel_y_diff = -8
+
+ if(direction & EAST)
+ pixel_x_diff = 8
+ else if(direction & WEST)
+ pixel_x_diff = -8
+
+ animate(src, pixel_x = pixel_x + pixel_x_diff, pixel_y = pixel_y + pixel_y_diff, time = 2)
+ animate(pixel_x = initial(pixel_x), pixel_y = final_pixel_y, time = 2)
+
+/atom/movable/proc/do_item_attack_animation(atom/A, visual_effect_icon, obj/item/used_item)
+ var/image/I
+ if(visual_effect_icon)
+ I = image('icons/effects/effects.dmi', A, visual_effect_icon, A.layer + 0.1)
+ else if(used_item)
+ I = image(used_item.icon, A, used_item.icon_state, A.layer + 0.1)
+
+ // Scale the icon.
+ I.transform *= 0.75
+ // The icon should not rotate.
+ I.appearance_flags = APPEARANCE_UI_IGNORE_ALPHA
+
+ // Set the direction of the icon animation.
+ var/direction = get_dir(src, A)
+ if(direction & NORTH)
+ I.pixel_y = -16
+ else if(direction & SOUTH)
+ I.pixel_y = 16
+
+ if(direction & EAST)
+ I.pixel_x = -16
+ else if(direction & WEST)
+ I.pixel_x = 16
+
+ if(!direction) // Attacked self?!
+ I.pixel_z = 16
+
+ if(!I)
+ return
+
+ // Who can see the attack?
+ var/list/viewing = list()
+ for(var/mob/M in viewers(A))
+ if(M.client && M.client.prefs.show_ghostitem_attack)
+ viewing |= M.client
+
+ flick_overlay(I, viewing, 5) // 5 ticks/half a second
+
+ // And animate the attack!
+ animate(I, alpha = 175, pixel_x = 0, pixel_y = 0, pixel_z = 0, time = 3)
\ No newline at end of file
diff --git a/code/game/gamemodes/changeling/powers/mutations.dm b/code/game/gamemodes/changeling/powers/mutations.dm
index 4e084e8b720..8f0aa4d210f 100644
--- a/code/game/gamemodes/changeling/powers/mutations.dm
+++ b/code/game/gamemodes/changeling/powers/mutations.dm
@@ -278,7 +278,7 @@
C.visible_message("[src] impales [C] with [I]!", "[src] impales you with [I]!")
C.apply_damage(I.force, BRUTE, "chest")
- do_attack_animation(C)
+ do_item_attack_animation(C, used_item = I)
add_blood(C)
playsound(get_turf(src), I.hitsound, 75, 1)
diff --git a/code/game/mecha/mecha.dm b/code/game/mecha/mecha.dm
index bb666a63da1..23134bc3144 100644
--- a/code/game/mecha/mecha.dm
+++ b/code/game/mecha/mecha.dm
@@ -469,15 +469,17 @@
/obj/mecha/attack_hand(mob/living/user)
user.changeNext_move(CLICK_CD_MELEE)
- user.do_attack_animation(src)
log_message("Attack by hand/paw. Attacker - [user].",1)
if((HULK in user.mutations) && !prob(deflect_chance))
+ do_attack_animation(src, ATTACK_EFFECT_SMASH)
take_damage(15)
check_for_internal_damage(list(MECHA_INT_TEMP_CONTROL,MECHA_INT_TANK_BREACH,MECHA_INT_CONTROL_LOST))
user.visible_message("[user] hits [name], doing some damage.",
"You hit [name] with all your might. The metal creaks and bends.")
else
+ user.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
+ playsound(loc, 'sound/weapons/tap.ogg', 40, 1, -1)
user.visible_message("[user] hits [name]. Nothing happens","You hit [name] with no visible effect.")
log_append_to_last("Armor saved.")
return
@@ -1478,3 +1480,15 @@
if(occupant_sight_flags)
if(user == occupant)
user.sight |= occupant_sight_flags
+
+/obj/mecha/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
+ if(!no_effect)
+ if(selected)
+ used_item = selected
+ else if(!visual_effect_icon)
+ visual_effect_icon = ATTACK_EFFECT_SMASH
+ if(damtype == BURN)
+ visual_effect_icon = ATTACK_EFFECT_MECHFIRE
+ else if(damtype == TOX)
+ visual_effect_icon = ATTACK_EFFECT_MECHTOXIN
+ ..()
\ No newline at end of file
diff --git a/code/game/objects/effects/effect_system/effects_foam.dm b/code/game/objects/effects/effect_system/effects_foam.dm
index 17723adcde7..93763c464e7 100644
--- a/code/game/objects/effects/effect_system/effects_foam.dm
+++ b/code/game/objects/effects/effect_system/effects_foam.dm
@@ -204,7 +204,7 @@
/obj/structure/foamedmetal/attack_hand(mob/user)
user.changeNext_move(CLICK_CD_MELEE)
- user.do_attack_animation(src)
+ user.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
if((HULK in user.mutations) || (prob(75 - metal*25)))
user.visible_message("[user] smashes through \the [src].", "You smash through \the [src].")
qdel(src)
diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm
index b2d0d6720c7..21bc0453500 100644
--- a/code/game/objects/items.dm
+++ b/code/game/objects/items.dm
@@ -443,10 +443,11 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
playsound(loc, src.hitsound, 30, 1, -1)
+ user.do_attack_animation(M)
+
if(M != user)
M.visible_message("[user] has stabbed [M] in the eye with [src]!", \
"[user] stabs you in the eye with [src]!")
- user.do_attack_animation(M)
else
user.visible_message( \
"[user] has stabbed themself in the eyes with [src]!", \
diff --git a/code/game/objects/structures/displaycase.dm b/code/game/objects/structures/displaycase.dm
index f888ee6cc94..0156cac96cc 100644
--- a/code/game/objects/structures/displaycase.dm
+++ b/code/game/objects/structures/displaycase.dm
@@ -295,7 +295,7 @@ var/global/list/captain_display_cases = list()
else
if(user.a_intent == INTENT_HARM)
user.changeNext_move(CLICK_CD_MELEE)
- user.do_attack_animation(src)
+ user.do_attack_animation(src, ATTACK_EFFECT_KICK)
user.visible_message("[user.name] kicks \the [src]!", \
"You kick \the [src]!", \
"You hear glass crack.")
diff --git a/code/game/objects/structures/grille.dm b/code/game/objects/structures/grille.dm
index d5dccaf0d03..0c0c3c1aa0c 100644
--- a/code/game/objects/structures/grille.dm
+++ b/code/game/objects/structures/grille.dm
@@ -71,7 +71,7 @@
/obj/structure/grille/attack_hand(mob/living/user)
user.changeNext_move(CLICK_CD_MELEE)
- user.do_attack_animation(src)
+ user.do_attack_animation(src, ATTACK_EFFECT_KICK)
user.visible_message("[user] kicks [src].", \
"You kick [src].", \
"You hear twisting metal.")
diff --git a/code/game/objects/structures/tables_racks.dm b/code/game/objects/structures/tables_racks.dm
index 367be27b6dc..4fedc99f0c5 100644
--- a/code/game/objects/structures/tables_racks.dm
+++ b/code/game/objects/structures/tables_racks.dm
@@ -616,7 +616,7 @@
if(user.weakened || user.resting || user.lying)
return
user.changeNext_move(CLICK_CD_MELEE)
- user.do_attack_animation(src)
+ user.do_attack_animation(src, ATTACK_EFFECT_KICK)
user.visible_message("[user] kicks [src].", \
"You kick [src].")
take_damage(rand(4,8), BRUTE, "melee", 1)
diff --git a/code/modules/flufftext/Hallucination.dm b/code/modules/flufftext/Hallucination.dm
index 021db59f8a4..d8a1f4f1526 100644
--- a/code/modules/flufftext/Hallucination.dm
+++ b/code/modules/flufftext/Hallucination.dm
@@ -641,6 +641,7 @@ Gunshots/explosions/opening doors/less rare audio (done)
updateimage()
else
if(prob(15))
+ do_attack_animation(my_target, ATTACK_EFFECT_PUNCH)
if(weapon_name)
my_target.playsound_local(my_target, weap.hitsound, 1)
my_target.show_message("[src.name] has attacked [my_target] with [weapon_name]!", 1)
diff --git a/code/modules/martial_arts/brawling.dm b/code/modules/martial_arts/brawling.dm
index 9f9fa5236b2..a40a52b86be 100644
--- a/code/modules/martial_arts/brawling.dm
+++ b/code/modules/martial_arts/brawling.dm
@@ -11,7 +11,7 @@
/datum/martial_art/boxing/harm_act(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
var/atk_verb = pick("left hook","right hook","straight punch")
@@ -62,7 +62,7 @@
/datum/martial_art/drunk_brawling/harm_act(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
add_attack_logs(A, D, "Melee attacked with [src]")
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
var/atk_verb = pick("jab","uppercut","overhand punch","drunken right hook","drunken left hook")
diff --git a/code/modules/martial_arts/krav_maga.dm b/code/modules/martial_arts/krav_maga.dm
index d17d1b30495..9e889bdce7a 100644
--- a/code/modules/martial_arts/krav_maga.dm
+++ b/code/modules/martial_arts/krav_maga.dm
@@ -109,7 +109,6 @@ datum/martial_art/krav_maga/grab_act(var/mob/living/carbon/human/A, var/mob/livi
if(check_streak(A,D))
return 1
add_attack_logs(A, D, "Melee attacked with [src]")
- A.do_attack_animation(D)
var/picked_hit_type = pick("punches", "kicks")
var/bonus_damage = 10
if(D.weakened || D.resting || D.lying)
@@ -117,8 +116,10 @@ datum/martial_art/krav_maga/grab_act(var/mob/living/carbon/human/A, var/mob/livi
picked_hit_type = "stomps on"
D.apply_damage(bonus_damage, BRUTE)
if(picked_hit_type == "kicks" || picked_hit_type == "stomps")
+ A.do_attack_animation(D, ATTACK_EFFECT_KICK)
playsound(get_turf(D), 'sound/effects/hit_kick.ogg', 50, 1, -1)
else
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
playsound(get_turf(D), 'sound/effects/hit_punch.ogg', 50, 1, -1)
D.visible_message("[A] [picked_hit_type] [D]!", \
"[A] [picked_hit_type] you!")
diff --git a/code/modules/martial_arts/martial.dm b/code/modules/martial_arts/martial.dm
index 3e1be19b0de..df1753e1dd7 100644
--- a/code/modules/martial_arts/martial.dm
+++ b/code/modules/martial_arts/martial.dm
@@ -33,7 +33,6 @@
/datum/martial_art/proc/basic_hit(var/mob/living/carbon/human/A,var/mob/living/carbon/human/D)
- A.do_attack_animation(D)
var/damage = rand(A.species.punchdamagelow, A.species.punchdamagehigh)
var/datum/unarmed_attack/attack = A.species.unarmed
@@ -41,6 +40,12 @@
if(D.lying)
atk_verb = "kick"
+ switch(atk_verb)
+ if("kick")
+ A.do_attack_animation(D, ATTACK_EFFECT_KICK)
+ else
+ A.do_attack_animation(D, attack.animation_type)
+
if(!damage)
playsound(D.loc, attack.miss_sound, 25, 1, -1)
D.visible_message("[A] has attempted to [atk_verb] [D]!")
diff --git a/code/modules/martial_arts/plasma_fist.dm b/code/modules/martial_arts/plasma_fist.dm
index d2e047dc08d..5aed9b8e9e1 100644
--- a/code/modules/martial_arts/plasma_fist.dm
+++ b/code/modules/martial_arts/plasma_fist.dm
@@ -46,7 +46,7 @@
return
/datum/martial_art/plasma_fist/proc/Plasma(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
playsound(D.loc, 'sound/weapons/punch1.ogg', 50, 1, -1)
A.say("PLASMA FIST!")
D.visible_message("[A] has hit [D] with THE PLASMA FIST TECHNIQUE!", \
diff --git a/code/modules/martial_arts/sleeping_carp.dm b/code/modules/martial_arts/sleeping_carp.dm
index 45f4948bc14..1cd29ac2511 100644
--- a/code/modules/martial_arts/sleeping_carp.dm
+++ b/code/modules/martial_arts/sleeping_carp.dm
@@ -36,7 +36,7 @@
/datum/martial_art/the_sleeping_carp/proc/wristWrench(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
if(!D.stat && !D.stunned && !D.weakened)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
D.visible_message("[A] grabs [D]'s wrist and wrenches it sideways!", \
"[A] grabs your wrist and violently wrenches it to the side!")
playsound(get_turf(A), 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
@@ -51,7 +51,7 @@
/datum/martial_art/the_sleeping_carp/proc/backKick(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
if(A.dir == D.dir && !D.stat && !D.weakened)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_KICK)
D.visible_message("[A] kicks [D] in the back!", \
"[A] kicks you in the back, making you stumble and fall!")
step_to(D,get_step(D,D.dir),1)
@@ -64,7 +64,7 @@
/datum/martial_art/the_sleeping_carp/proc/kneeStomach(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
if(!D.stat && !D.weakened)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_KICK)
D.visible_message("[A] knees [D] in the stomach!", \
"[A] winds you with a knee in the stomach!")
D.audible_message("[D] gags!")
@@ -78,7 +78,7 @@
/datum/martial_art/the_sleeping_carp/proc/headKick(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
if(!D.stat && !D.weakened)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_KICK)
D.visible_message("[A] kicks [D] in the head!", \
"[A] kicks you in the jaw!")
D.apply_damage(20, BRUTE, "head")
@@ -92,7 +92,7 @@
/datum/martial_art/the_sleeping_carp/proc/elbowDrop(var/mob/living/carbon/human/A, var/mob/living/carbon/human/D)
if(D.weakened || D.resting || D.stat)
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
D.visible_message("[A] elbow drops [D]!", \
"[A] piledrives you with their elbow!")
if(D.stat)
@@ -117,7 +117,7 @@
add_to_streak("H",D)
if(check_streak(A,D))
return 1
- A.do_attack_animation(D)
+ A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
var/atk_verb = pick("punches", "kicks", "chops", "hits", "slams")
D.visible_message("[A] [atk_verb] [D]!", \
"[A] [atk_verb] you!")
diff --git a/code/modules/mob/living/carbon/alien/alien_defense.dm b/code/modules/mob/living/carbon/alien/alien_defense.dm
index 22954451834..0d9c50ba5cc 100644
--- a/code/modules/mob/living/carbon/alien/alien_defense.dm
+++ b/code/modules/mob/living/carbon/alien/alien_defense.dm
@@ -29,7 +29,7 @@ In all, this is a lot like the monkey code. /N
else
if(health > 0)
- M.do_attack_animation(src)
+ M.do_attack_animation(src, ATTACK_EFFECT_BITE)
playsound(loc, 'sound/weapons/bite.ogg', 50, 1, -1)
var/damage = 1
visible_message("[M.name] bites [src]!", \
@@ -52,8 +52,10 @@ In all, this is a lot like the monkey code. /N
help_shake_act(M)
if(INTENT_GRAB)
grabbedby(M)
- if(INTENT_HARM, INTENT_DISARM)
- M.do_attack_animation(src)
+ if(INTENT_HARM)
+ M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
+ if(INTENT_DISARM)
+ M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
return 1
return 0
diff --git a/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm b/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm
index 0056bb709a5..41ebc8d8247 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm
@@ -43,3 +43,8 @@
else
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
visible_message("[M] has attempted to disarm [src]!")
+
+/mob/living/carbon/alien/humanoid/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
+ if(!no_effect && !visual_effect_icon)
+ visual_effect_icon = ATTACK_EFFECT_CLAW
+ ..()
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/alien/larva/larva_defense.dm b/code/modules/mob/living/carbon/alien/larva/larva_defense.dm
index fc7fa22510b..ef38327b5ee 100644
--- a/code/modules/mob/living/carbon/alien/larva/larva_defense.dm
+++ b/code/modules/mob/living/carbon/alien/larva/larva_defense.dm
@@ -22,3 +22,8 @@
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
visible_message("[M] has attempted to kick [src]!", \
"[M] has attempted to kick [src]!")
+
+/mob/living/carbon/alien/larva/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
+ if(!no_effect && !visual_effect_icon)
+ visual_effect_icon = ATTACK_EFFECT_BITE
+ ..()
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/human/human_damage.dm b/code/modules/mob/living/carbon/human/human_damage.dm
index c216badda93..5ed14b3a18e 100644
--- a/code/modules/mob/living/carbon/human/human_damage.dm
+++ b/code/modules/mob/living/carbon/human/human_damage.dm
@@ -372,7 +372,6 @@ This function restores all organs.
dmgIcon.pixel_y = (!lying) ? rand(-11,9) : rand(-10,1)
flick_overlay(dmgIcon, attack_bubble_recipients, 9)
- receiving_damage()
if(BURN)
damageoverlaytemp = 20
diff --git a/code/modules/mob/living/carbon/human/species/abductor.dm b/code/modules/mob/living/carbon/human/species/abductor.dm
index 3e1bb968c81..8aeb6f88a3d 100644
--- a/code/modules/mob/living/carbon/human/species/abductor.dm
+++ b/code/modules/mob/living/carbon/human/species/abductor.dm
@@ -6,7 +6,6 @@
path = /mob/living/carbon/human/abductor
language = "Abductor Mindlink"
default_language = "Abductor Mindlink"
- unarmed_type = /datum/unarmed_attack/punch
eyes = "blank_eyes"
has_organ = list(
"heart" = /obj/item/organ/internal/heart,
diff --git a/code/modules/mob/living/carbon/human/species/apollo.dm b/code/modules/mob/living/carbon/human/species/apollo.dm
index 6c37da34395..5a3e1d4cde9 100644
--- a/code/modules/mob/living/carbon/human/species/apollo.dm
+++ b/code/modules/mob/living/carbon/human/species/apollo.dm
@@ -5,7 +5,6 @@
deform = 'icons/mob/human_races/r_wryn.dmi'
language = "Wryn Hivemind"
tail = "wryntail"
- unarmed_type = /datum/unarmed_attack/punch/weak
punchdamagelow = 0
punchdamagehigh = 1
//primitive = /mob/living/carbon/monkey/wryn
@@ -82,7 +81,6 @@
name = "Nucleation"
name_plural = "Nucleations"
icobase = 'icons/mob/human_races/r_nucleation.dmi'
- unarmed_type = /datum/unarmed_attack/punch
blurb = "A sub-race of unfortunates who have been exposed to too much supermatter radiation. As a result, \
supermatter crystal clusters have begun to grow across their bodies. Research to find a cure for this ailment \
has been slow, and so this is a common fate for veteran engineers. The supermatter crystals produce oxygen, \
diff --git a/code/modules/mob/living/carbon/human/species/golem.dm b/code/modules/mob/living/carbon/human/species/golem.dm
index c289ba3a19e..74f3e97d879 100644
--- a/code/modules/mob/living/carbon/human/species/golem.dm
+++ b/code/modules/mob/living/carbon/human/species/golem.dm
@@ -13,7 +13,6 @@
dietflags = DIET_OMNI //golems can eat anything because they are magic or something
reagent_tag = PROCESS_ORG
- unarmed_type = /datum/unarmed_attack/punch
punchdamagelow = 5
punchdamagehigh = 14
punchstunthreshold = 11 //about 40% chance to stun
diff --git a/code/modules/mob/living/carbon/human/species/monkey.dm b/code/modules/mob/living/carbon/human/species/monkey.dm
index 07d3215126e..c5003b21330 100644
--- a/code/modules/mob/living/carbon/human/species/monkey.dm
+++ b/code/modules/mob/living/carbon/human/species/monkey.dm
@@ -28,8 +28,7 @@
reagent_tag = PROCESS_ORG
//Has standard darksight of 2.
- //unarmed_types = list(/datum/unarmed_attack/bite, /datum/unarmed_attack/claws)
- //inherent_verbs = list(/mob/living/proc/ventcrawl)
+ unarmed_type = /datum/unarmed_attack/bite
total_health = 75
brute_mod = 1.5
diff --git a/code/modules/mob/living/carbon/human/species/plasmaman.dm b/code/modules/mob/living/carbon/human/species/plasmaman.dm
index 620d49254f3..692a23c470a 100644
--- a/code/modules/mob/living/carbon/human/species/plasmaman.dm
+++ b/code/modules/mob/living/carbon/human/species/plasmaman.dm
@@ -4,7 +4,6 @@
icobase = 'icons/mob/human_races/r_plasmaman_sb.dmi'
deform = 'icons/mob/human_races/r_plasmaman_pb.dmi' // TODO: Need deform.
//language = "Clatter"
- unarmed_type = /datum/unarmed_attack/punch
species_traits = list(IS_WHITELISTED, NO_BLOOD, NOTRANSSTING)
dietflags = DIET_OMNI
diff --git a/code/modules/mob/living/carbon/human/species/skeleton.dm b/code/modules/mob/living/carbon/human/species/skeleton.dm
index d207dc20703..9da4d1222f6 100644
--- a/code/modules/mob/living/carbon/human/species/skeleton.dm
+++ b/code/modules/mob/living/carbon/human/species/skeleton.dm
@@ -8,7 +8,6 @@
deform = 'icons/mob/human_races/r_skeleton.dmi'
path = /mob/living/carbon/human/skeleton
default_language = "Galactic Common"
- unarmed_type = /datum/unarmed_attack/punch
blood_color = "#FFFFFF"
flesh_color = "#E6E6C6"
diff --git a/code/modules/mob/living/carbon/human/species/species.dm b/code/modules/mob/living/carbon/human/species/species.dm
index 50f969cae45..25d3fd342c5 100644
--- a/code/modules/mob/living/carbon/human/species/species.dm
+++ b/code/modules/mob/living/carbon/human/species/species.dm
@@ -356,7 +356,7 @@
else
var/datum/unarmed_attack/attack = user.species.unarmed
- user.do_attack_animation(target)
+ user.do_attack_animation(target, attack.animation_type)
add_attack_logs(user, target, "Melee attacked with fists", admin_notify = target.ckey ? TRUE : FALSE)
if(!iscarbon(user))
@@ -396,7 +396,7 @@
return 1
else
add_attack_logs(user, target, "Disarmed", admin_notify = FALSE)
- user.do_attack_animation(target)
+ user.do_attack_animation(target, ATTACK_EFFECT_DISARM)
if(target.w_uniform)
target.w_uniform.add_fingerprint(user)
var/obj/item/organ/external/affecting = target.get_organ(ran_zone(user.zone_sel.selecting))
@@ -500,17 +500,12 @@
//Species unarmed attacks
/datum/unarmed_attack
- var/attack_verb = list("attack") // Empty hand hurt intent verb.
+ var/attack_verb = list("punch") // Empty hand hurt intent verb.
var/damage = 0 // How much flat bonus damage an attack will do. This is a *bonus* guaranteed damage amount on top of the random damage attacks do.
var/attack_sound = "punch"
var/miss_sound = 'sound/weapons/punchmiss.ogg'
- var/sharp = 0
-
-/datum/unarmed_attack/punch
- attack_verb = list("punch")
-
-/datum/unarmed_attack/punch/weak
- attack_verb = list("flail")
+ var/sharp = FALSE
+ var/animation_type = ATTACK_EFFECT_PUNCH
/datum/unarmed_attack/diona
attack_verb = list("lash", "bludgeon")
@@ -519,7 +514,14 @@
attack_verb = list("scratch", "claw")
attack_sound = 'sound/weapons/slice.ogg'
miss_sound = 'sound/weapons/slashmiss.ogg'
- sharp = 1
+ sharp = TRUE
+ animation_type = ATTACK_EFFECT_CLAW
+
+/datum/unarmed_attack/bite
+ attack_verb = list("chomp")
+ attack_sound = 'sound/weapons/bite.ogg'
+ sharp = TRUE
+ animation_type = ATTACK_EFFECT_BITE
/datum/unarmed_attack/claws/armalis
attack_verb = list("slash", "claw")
diff --git a/code/modules/mob/living/carbon/human/species/station.dm b/code/modules/mob/living/carbon/human/species/station.dm
index 05e989afa50..015f1515683 100644
--- a/code/modules/mob/living/carbon/human/species/station.dm
+++ b/code/modules/mob/living/carbon/human/species/station.dm
@@ -10,7 +10,6 @@
clothing_flags = HAS_UNDERWEAR | HAS_UNDERSHIRT | HAS_SOCKS
bodyflags = HAS_SKIN_TONE | HAS_BODY_MARKINGS
dietflags = DIET_OMNI
- unarmed_type = /datum/unarmed_attack/punch
blurb = "Humanity originated in the Sol system, and over the last five centuries has spread \
colonies across a wide swathe of space. They hold a wide range of forms and creeds.
\
While the central Sol government maintains control of its far-flung people, powerful corporate \
@@ -237,7 +236,6 @@
default_language = "Galactic Common"
language = "Skrellian"
primitive_form = "Neara"
- unarmed_type = /datum/unarmed_attack/punch
blurb = "An amphibious species, Skrell come from the star system known as Qerr'Vallis, which translates to 'Star of \
the royals' or 'Light of the Crown'.
Skrell are a highly advanced and logical race who live under the rule \
@@ -546,7 +544,6 @@
icobase = 'icons/mob/human_races/r_slime.dmi'
deform = 'icons/mob/human_races/r_slime.dmi'
path = /mob/living/carbon/human/slime
- unarmed_type = /datum/unarmed_attack/punch
remains_type = /obj/effect/decal/remains/slime
// More sensitive to the cold
@@ -749,7 +746,6 @@
deform = 'icons/mob/human_races/r_def_grey.dmi'
default_language = "Galactic Common"
language = "Psionic Communication"
- unarmed_type = /datum/unarmed_attack/punch
eyes = "grey_eyes_s"
butt_sprite = "grey"
@@ -931,7 +927,6 @@
path = /mob/living/carbon/human/machine
default_language = "Galactic Common"
language = "Trinary"
- unarmed_type = /datum/unarmed_attack/punch
remains_type = /obj/effect/decal/remains/robot
eyes = "blank_eyes"
@@ -1015,7 +1010,6 @@
path = /mob/living/carbon/human/drask
default_language = "Galactic Common"
language = "Orluum"
- unarmed_type = /datum/unarmed_attack/punch
eyes = "drask_eyes_s"
speech_sounds = list('sound/voice/DraskTalk.ogg')
diff --git a/code/modules/mob/living/carbon/slime/slime.dm b/code/modules/mob/living/carbon/slime/slime.dm
index ecb233a2ebf..79bcd54775b 100644
--- a/code/modules/mob/living/carbon/slime/slime.dm
+++ b/code/modules/mob/living/carbon/slime/slime.dm
@@ -236,6 +236,7 @@
/mob/living/carbon/slime/attack_hand(mob/living/carbon/human/M)
if(Victim)
+ M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
if(Victim == M)
if(prob(60))
visible_message("[M] attempts to wrestle \the [name] off!")
@@ -259,7 +260,6 @@
return
else
- M.do_attack_animation(src)
if(prob(30))
visible_message("[M] attempts to wrestle \the [name] off of [Victim]!")
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
@@ -297,7 +297,7 @@
grabbedby(M)
else
- M.do_attack_animation(src)
+ M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
var/damage = rand(1, 9)
attacked += 10
if(prob(90))
diff --git a/code/modules/mob/living/living.dm b/code/modules/mob/living/living.dm
index 4f3265fc619..2f0d341f697 100644
--- a/code/modules/mob/living/living.dm
+++ b/code/modules/mob/living/living.dm
@@ -852,81 +852,11 @@
makeNewConstruct(/mob/living/simple_animal/hostile/construct/harvester, src, null, 1)
spawn_dust()
gib()
- return
-/atom/movable/proc/do_attack_animation(atom/A, end_pixel_y)
- var/pixel_x_diff = 0
- var/pixel_y_diff = 0
- var/final_pixel_y = initial(pixel_y)
- if(end_pixel_y)
- final_pixel_y = end_pixel_y
-
- var/direction = get_dir(src, A)
- if(direction & NORTH)
- pixel_y_diff = 8
- else if(direction & SOUTH)
- pixel_y_diff = -8
-
- if(direction & EAST)
- pixel_x_diff = 8
- else if(direction & WEST)
- pixel_x_diff = -8
-
- animate(src, pixel_x = pixel_x + pixel_x_diff, pixel_y = pixel_y + pixel_y_diff, time = 2)
- animate(pixel_x = initial(pixel_x), pixel_y = final_pixel_y, time = 2)
-
-
-/mob/living/do_attack_animation(atom/A)
- var/final_pixel_y = get_standard_pixel_y_offset(lying)
- ..(A, final_pixel_y)
- floating = 0 // If we were without gravity, the bouncing animation got stopped, so we make sure we restart the bouncing after the next movement.
-
- // What icon do we use for the attack?
- var/image/I
- if(hand && l_hand) // Attacked with item in left hand.
- I = image(l_hand.icon, A, l_hand.icon_state, A.layer + 1)
- else if(!hand && r_hand) // Attacked with item in right hand.
- I = image(r_hand.icon, A, r_hand.icon_state, A.layer + 1)
- else // Attacked with a fist?
- return
-
- // Who can see the attack?
- var/list/viewing = list()
- for(var/mob/M in viewers(A))
- if(M.client && M.client.prefs.show_ghostitem_attack)
- viewing |= M.client
- flick_overlay(I, viewing, 5) // 5 ticks/half a second
-
- // Scale the icon.
- I.transform *= 0.75
- // The icon should not rotate.
- I.appearance_flags = APPEARANCE_UI_IGNORE_ALPHA
-
- // Set the direction of the icon animation.
- var/direction = get_dir(src, A)
- if(direction & NORTH)
- I.pixel_y = -16
- else if(direction & SOUTH)
- I.pixel_y = 16
-
- if(direction & EAST)
- I.pixel_x = -16
- else if(direction & WEST)
- I.pixel_x = 16
-
- if(!direction) // Attacked self?!
- I.pixel_z = 16
-
- // And animate the attack!
- animate(I, alpha = 175, pixel_x = 0, pixel_y = 0, pixel_z = 0, time = 3)
-
-/atom/movable/proc/receiving_damage(atom/A)
- var/pixel_x_diff = rand(-3,3)
- var/pixel_y_diff = rand(-3,3)
- animate(src, pixel_x = pixel_x + pixel_x_diff, pixel_y = pixel_y + pixel_y_diff, time = 2)
- animate(pixel_x = initial(pixel_x), pixel_y = initial(pixel_y), time = 2)
-
-/mob/living/receiving_damage(atom/A)
+/mob/living/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
+ end_pixel_y = get_standard_pixel_y_offset(lying)
+ if(!used_item)
+ used_item = get_active_hand()
..()
floating = 0 // If we were without gravity, the bouncing animation got stopped, so we make sure we restart the bouncing after the next movement.
diff --git a/code/modules/mob/living/living_defense.dm b/code/modules/mob/living/living_defense.dm
index 38065ac1f2c..d734272e905 100644
--- a/code/modules/mob/living/living_defense.dm
+++ b/code/modules/mob/living/living_defense.dm
@@ -333,6 +333,9 @@
if(INTENT_GRAB)
grabbedby(M)
return FALSE
- else
+ if(INTENT_HARM)
M.do_attack_animation(src)
return TRUE
+ if(INTENT_DISARM)
+ M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
+ return TRUE
diff --git a/code/modules/mob/living/silicon/robot/robot_defense.dm b/code/modules/mob/living/silicon/robot/robot_defense.dm
index 712154bf146..e18ca8d6a17 100644
--- a/code/modules/mob/living/silicon/robot/robot_defense.dm
+++ b/code/modules/mob/living/silicon/robot/robot_defense.dm
@@ -1,7 +1,7 @@
/mob/living/silicon/robot/attack_alien(mob/living/carbon/alien/humanoid/M)
if(M.a_intent == INTENT_DISARM)
if(!lying)
- M.do_attack_animation(src)
+ M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
if(prob(85))
Stun(7)
step(src, get_dir(M,src))
diff --git a/code/modules/mob/living/silicon/silicon_defense.dm b/code/modules/mob/living/silicon/silicon_defense.dm
index 480c9442bd7..070ed327163 100644
--- a/code/modules/mob/living/silicon/silicon_defense.dm
+++ b/code/modules/mob/living/silicon/silicon_defense.dm
@@ -49,7 +49,7 @@
if("grab")
grabbedby(M)
else
- M.do_attack_animation(src)
+ M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
playsound(loc, 'sound/effects/bang.ogg', 10, 1)
if(HULK in M.mutations)
var/damage = rand(10,15)
diff --git a/code/modules/mob/living/simple_animal/animal_defense.dm b/code/modules/mob/living/simple_animal/animal_defense.dm
index b122decd322..972759812b4 100644
--- a/code/modules/mob/living/simple_animal/animal_defense.dm
+++ b/code/modules/mob/living/simple_animal/animal_defense.dm
@@ -11,7 +11,7 @@
grabbedby(M)
if(INTENT_HARM, INTENT_DISARM)
- M.do_attack_animation(src)
+ M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
visible_message("[M] [response_harm] [src]!")
playsound(loc, "punch", 25, 1, -1)
attack_threshold_check(harm_intent_damage)
@@ -58,3 +58,11 @@
visible_message("[src] looks unharmed.")
else
apply_damage(damage, damagetype)
+
+/mob/living/simple_animal/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
+ if(!no_effect && !visual_effect_icon && melee_damage_upper)
+ if(melee_damage_upper < 10)
+ visual_effect_icon = ATTACK_EFFECT_PUNCH
+ else
+ visual_effect_icon = ATTACK_EFFECT_SMASH
+ ..()
\ No newline at end of file
diff --git a/code/modules/mob/living/simple_animal/hostile/megafauna/bubblegum.dm b/code/modules/mob/living/simple_animal/hostile/megafauna/bubblegum.dm
index 971adc431cc..3c72042efce 100644
--- a/code/modules/mob/living/simple_animal/hostile/megafauna/bubblegum.dm
+++ b/code/modules/mob/living/simple_animal/hostile/megafauna/bubblegum.dm
@@ -117,7 +117,7 @@ Difficulty: Hard
bloodspell.phased = 1
internal_gps = new/obj/item/gps/internal/bubblegum(src)
-/mob/living/simple_animal/hostile/megafauna/bubblegum/do_attack_animation(atom/A, visual_effect_icon)
+/mob/living/simple_animal/hostile/megafauna/bubblegum/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
if(!charging)
..()
diff --git a/code/modules/mob/living/simple_animal/hostile/spaceworms.dm b/code/modules/mob/living/simple_animal/hostile/spaceworms.dm
index d63d43b4919..cdbc64eea1e 100644
--- a/code/modules/mob/living/simple_animal/hostile/spaceworms.dm
+++ b/code/modules/mob/living/simple_animal/hostile/spaceworms.dm
@@ -328,7 +328,7 @@
//Jiggle the whole worm forwards towards the next segment
-/mob/living/simple_animal/hostile/spaceWorm/do_attack_animation(atom/A)
+/mob/living/simple_animal/hostile/spaceWorm/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
..()
if(previousWorm)
previousWorm.do_attack_animation(src)
\ No newline at end of file
diff --git a/code/modules/mob/living/simple_animal/posessed_object.dm b/code/modules/mob/living/simple_animal/posessed_object.dm
index 9ba666ce96a..22901f4d29a 100644
--- a/code/modules/mob/living/simple_animal/posessed_object.dm
+++ b/code/modules/mob/living/simple_animal/posessed_object.dm
@@ -26,7 +26,7 @@
to_chat(usr, "[src] appears to be having trouble staying afloat!")
-/mob/living/simple_animal/possessed_object/do_attack_animation(atom/A)
+/mob/living/simple_animal/possessed_object/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
..()
animate_ghostly_presence(src, -1, 20, 1) // Restart the floating animation after the attack animation, as it will be cancelled.
diff --git a/icons/effects/effects.dmi b/icons/effects/effects.dmi
index ee05d5f450e..36ebff9a01e 100644
Binary files a/icons/effects/effects.dmi and b/icons/effects/effects.dmi differ