diff --git a/code/__DEFINES/traits.dm b/code/__DEFINES/traits.dm
index b3c2b241f3..4f66482f51 100644
--- a/code/__DEFINES/traits.dm
+++ b/code/__DEFINES/traits.dm
@@ -169,6 +169,7 @@
#define TRAIT_EMPATH "empath"
#define TRAIT_FRIENDLY "friendly"
#define TRAIT_CULT_EYES "cult_eyes"
+#define TRAIT_AUTO_CATCH_ITEM "auto_catch_item"
#define TRAIT_CLOWN_MENTALITY "clown_mentality" // The future is now, clownman.
#define TRAIT_FREESPRINT "free_sprinting"
diff --git a/code/__HELPERS/unsorted.dm b/code/__HELPERS/unsorted.dm
index 29f5331fd3..74c32dd52f 100644
--- a/code/__HELPERS/unsorted.dm
+++ b/code/__HELPERS/unsorted.dm
@@ -758,16 +758,6 @@ GLOBAL_LIST_INIT(can_embed_types, typecacheof(list(
/obj/item/stack/rods,
/obj/item/pipe)))
-/proc/can_embed(obj/item/W)
- if(W.get_sharpness())
- return 1
- if(is_pointed(W))
- return 1
-
- if(is_type_in_typecache(W, GLOB.can_embed_types))
- return 1
-
-
/*
Checks if that loc and dir has an item on the wall
*/
diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm
index f082f2ad16..e6b2a63673 100644
--- a/code/_onclick/item_attack.dm
+++ b/code/_onclick/item_attack.dm
@@ -98,17 +98,19 @@
take_damage(I.force, I.damtype, "melee", 1)
/mob/living/attacked_by(obj/item/I, mob/living/user)
+ //CIT CHANGES START HERE - combatmode and resting checks
+ var/totitemdamage = I.force
+ if(iscarbon(user))
+ var/mob/living/carbon/tempcarb = user
+ if(!tempcarb.combatmode)
+ totitemdamage *= 0.5
+ if(user.resting)
+ totitemdamage *= 0.5
+ //CIT CHANGES END HERE
+ if(user != src && check_shields(I, totitemdamage, "the [I.name]", MELEE_ATTACK, I.armour_penetration))
+ return FALSE
send_item_attack_message(I, user)
if(I.force)
- //CIT CHANGES START HERE - combatmode and resting checks
- var/totitemdamage = I.force
- if(iscarbon(user))
- var/mob/living/carbon/tempcarb = user
- if(!tempcarb.combatmode)
- totitemdamage *= 0.5
- if(user.resting)
- totitemdamage *= 0.5
- //CIT CHANGES END HERE
apply_damage(totitemdamage, I.damtype) //CIT CHANGE - replaces I.force with totitemdamage
if(I.damtype == BRUTE && !HAS_TRAIT(src, TRAIT_NOMARROW))
if(prob(33))
diff --git a/code/datums/martial/rising_bass.dm b/code/datums/martial/rising_bass.dm
index a3b71c6784..9e00c90a92 100644
--- a/code/datums/martial/rising_bass.dm
+++ b/code/datums/martial/rising_bass.dm
@@ -150,7 +150,9 @@
if(!.)
return
ADD_TRAIT(H, TRAIT_NOGUNS, RISING_BASS_TRAIT)
+ ADD_TRAIT(H, TRAIT_AUTO_CATCH_ITEM, RISING_BASS_TRAIT)
/datum/martial_art/the_rising_bass/on_remove(mob/living/carbon/human/H)
. = ..()
- REMOVE_TRAIT(H, TRAIT_NOGUNS, RISING_BASS_TRAIT)
\ No newline at end of file
+ REMOVE_TRAIT(H, TRAIT_NOGUNS, RISING_BASS_TRAIT)
+ REMOVE_TRAIT(H, TRAIT_AUTO_CATCH_ITEM, RISING_BASS_TRAIT)
\ No newline at end of file
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index 66570205e3..773c12b6af 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -166,7 +166,7 @@
return FALSE
-/atom/proc/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/atom/proc/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
SEND_SIGNAL(src, COMSIG_ATOM_HULK_ATTACK, user)
if(does_attack_animation)
user.changeNext_move(CLICK_CD_MELEE)
diff --git a/code/game/objects/items/melee/misc.dm b/code/game/objects/items/melee/misc.dm
index d8abff70a6..4242fb6c4b 100644
--- a/code/game/objects/items/melee/misc.dm
+++ b/code/game/objects/items/melee/misc.dm
@@ -216,10 +216,11 @@
return
else
if(last_hit < world.time)
+ if(target.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK))
+ playsound(target, 'sound/weapons/genhit.ogg', 50, 1)
+ return
if(ishuman(target))
var/mob/living/carbon/human/H = target
- if (H.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK))
- return
if(check_martial_counter(H, user))
return
playsound(get_turf(src), 'sound/effects/woodhit.ogg', 75, 1, -1)
diff --git a/code/game/objects/items/robot/robot_items.dm b/code/game/objects/items/robot/robot_items.dm
index 77bc7ed810..c09f5b1b65 100644
--- a/code/game/objects/items/robot/robot_items.dm
+++ b/code/game/objects/items/robot/robot_items.dm
@@ -11,11 +11,9 @@
var/charge_cost = 30
/obj/item/borg/stun/attack(mob/living/M, mob/living/user)
- if(ishuman(M))
- var/mob/living/carbon/human/H = M
- if(H.check_shields(src, 0, "[M]'s [name]", MELEE_ATTACK))
- playsound(M, 'sound/weapons/genhit.ogg', 50, 1)
- return FALSE
+ if(M.check_shields(src, 0, "[M]'s [name]", MELEE_ATTACK))
+ playsound(M, 'sound/weapons/genhit.ogg', 50, 1)
+ return FALSE
if(iscyborg(user))
var/mob/living/silicon/robot/R = user
if(!R.cell.use(charge_cost))
diff --git a/code/game/objects/items/stunbaton.dm b/code/game/objects/items/stunbaton.dm
index 484b9862ff..b5c8f6b631 100644
--- a/code/game/objects/items/stunbaton.dm
+++ b/code/game/objects/items/stunbaton.dm
@@ -168,11 +168,9 @@
/obj/item/melee/baton/proc/baton_stun(mob/living/L, mob/user)
- if(ishuman(L))
- var/mob/living/carbon/human/H = L
- if(H.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK)) //No message; check_shields() handles that
- playsound(L, 'sound/weapons/genhit.ogg', 50, 1)
- return FALSE
+ if(L.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK)) //No message; check_shields() handles that
+ playsound(L, 'sound/weapons/genhit.ogg', 50, 1)
+ return FALSE
var/stunpwr = stunforce
var/obj/item/stock_parts/cell/our_cell = get_cell()
if(!our_cell)
diff --git a/code/modules/antagonists/abductor/equipment/abduction_gear.dm b/code/modules/antagonists/abductor/equipment/abduction_gear.dm
index 433f52306b..fce45810d1 100644
--- a/code/modules/antagonists/abductor/equipment/abduction_gear.dm
+++ b/code/modules/antagonists/abductor/equipment/abduction_gear.dm
@@ -484,11 +484,9 @@
user.do_attack_animation(L)
- if(ishuman(L))
- var/mob/living/carbon/human/H = L
- if(H.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK))
- playsound(H, 'sound/weapons/genhit.ogg', 50, TRUE)
- return FALSE
+ if(L.check_shields(src, 0, "[user]'s [name]", MELEE_ATTACK))
+ playsound(L, 'sound/weapons/genhit.ogg', 50, TRUE)
+ return FALSE
switch (mode)
if(BATON_STUN)
diff --git a/code/modules/mob/living/carbon/alien/alien_defense.dm b/code/modules/mob/living/carbon/alien/alien_defense.dm
index b9e27c0637..bdc691ce49 100644
--- a/code/modules/mob/living/carbon/alien/alien_defense.dm
+++ b/code/modules/mob/living/carbon/alien/alien_defense.dm
@@ -6,21 +6,21 @@
return 2 //no ears
/mob/living/carbon/alien/hitby(atom/movable/AM, skipcatch, hitpush)
- ..(AM, skipcatch = TRUE, hitpush = FALSE)
+ return ..(AM, skipcatch = TRUE, hitpush = FALSE)
+/mob/living/carbon/alien/can_embed(obj/item/I)
+ return FALSE
/*Code for aliens attacking aliens. Because aliens act on a hivemind, I don't see them as very aggressive with each other.
As such, they can either help or harm other aliens. Help works like the human help command while harm is a simple nibble.
In all, this is a lot like the monkey code. /N
*/
/mob/living/carbon/alien/attack_alien(mob/living/carbon/alien/M)
- if(isturf(loc) && istype(loc.loc, /area/start))
- to_chat(M, "No attacking people at spawn, you jackass.")
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
return
-
switch(M.a_intent)
-
- if ("help")
+ if (INTENT_HELP)
if(!recoveringstam)
resting = 0
AdjustStun(-60)
@@ -28,11 +28,7 @@ In all, this is a lot like the monkey code. /N
AdjustUnconscious(-60)
AdjustSleeping(-100)
visible_message("[M.name] nuzzles [src] trying to wake [p_them()] up!")
-
- if ("grab")
- grabbedby(M)
-
- else
+ if(INTENT_DISARM, INTENT_HARM)
if(health > 0)
M.do_attack_animation(src, ATTACK_EFFECT_BITE)
playsound(loc, 'sound/weapons/bite.ogg', 50, 1, -1)
@@ -50,28 +46,31 @@ In all, this is a lot like the monkey code. /N
/mob/living/carbon/alien/attack_hand(mob/living/carbon/human/M)
- if(..()) //to allow surgery to return properly.
- return 0
-
+ . = ..()
+ if(.) //To allow surgery to return properly.
+ return
switch(M.a_intent)
- if("help")
+ if(INTENT_HELP)
help_shake_act(M)
- if("grab")
+ if(INTENT_GRAB)
grabbedby(M)
- if ("harm")
+ if (INTENT_HARM)
+ if(HAS_TRAIT(M, TRAIT_PACIFISM))
+ to_chat(M, "You don't want to hurt [src]!")
+ return TRUE
M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
- return 1
- if("disarm")
+ if(INTENT_DISARM)
+ if(HAS_TRAIT(M, TRAIT_PACIFISM))
+ to_chat(M, "You don't want to hurt [src]!")
+ return TRUE
M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
- return 1
- return 0
/mob/living/carbon/alien/attack_paw(mob/living/carbon/monkey/M)
- if(..())
- if (stat != DEAD)
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
- apply_damage(rand(1, 3), BRUTE, affecting)
+ . = ..()
+ if(.) //successful monkey bite.
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
+ apply_damage(rand(1, 3), BRUTE, affecting)
/mob/living/carbon/alien/attack_animal(mob/living/simple_animal/M)
@@ -93,13 +92,15 @@ In all, this is a lot like the monkey code. /N
adjustStaminaLoss(damage)
/mob/living/carbon/alien/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
- var/damage = rand(5, 35)
- if(M.is_adult)
- damage = rand(10, 40)
- adjustBruteLoss(damage)
- log_combat(M, src, "attacked")
- updatehealth()
+ . = ..()
+ if(!.) //unsuccessful slime attack
+ return
+ var/damage = rand(5, 35)
+ if(M.is_adult)
+ damage = rand(10, 40)
+ adjustBruteLoss(damage)
+ log_combat(M, src, "attacked")
+ updatehealth()
/mob/living/carbon/alien/ex_act(severity, target, origin)
if(origin && istype(origin, /datum/spacevine_mutation) && isvineimmune(src))
diff --git a/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm b/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm
index fe682b5c99..d1ed09665b 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm
@@ -63,12 +63,7 @@
if(A)
if(isliving(A))
var/mob/living/L = A
- var/blocked = FALSE
- if(ishuman(A))
- var/mob/living/carbon/human/H = A
- if(H.check_shields(src, 0, "the [name]", attack_type = LEAP_ATTACK))
- blocked = TRUE
- if(!blocked)
+ if(!L.check_shields(src, 0, "the [name]", attack_type = LEAP_ATTACK))
L.visible_message("[src] pounces on [L]!", "[src] pounces on you!")
L.Knockdown(100)
sleep(2)//Runtime prevention (infinite bump() calls on hulks)
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 b3839a6033..1d613db07a 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/humanoid_defense.dm
@@ -5,9 +5,11 @@
else
..()
-/mob/living/carbon/alien/humanoid/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/mob/living/carbon/alien/humanoid/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
if(user.a_intent == INTENT_HARM)
- ..(user, 1)
+ . = ..(user, TRUE)
+ if(.)
+ return
adjustBruteLoss(15)
var/hitverb = "punched"
if(mob_size < MOB_SIZE_LARGE)
@@ -21,46 +23,46 @@
return 1
/mob/living/carbon/alien/humanoid/attack_hand(mob/living/carbon/human/M)
- if(..())
- switch(M.a_intent)
- if ("harm")
- var/damage = rand(1, 9)
- if (prob(90))
- playsound(loc, "punch", 25, 1, -1)
- visible_message("[M] has punched [src]!", \
- "[M] has punched [src]!", null, COMBAT_MESSAGE_RANGE)
- if ((stat != DEAD) && (damage > 9 || prob(5)))//Regular humans have a very small chance of knocking an alien down.
- Unconscious(40)
- visible_message("[M] has knocked [src] down!", \
- "[M] has knocked [src] down!")
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
- apply_damage(damage, BRUTE, affecting)
- log_combat(M, src, "attacked")
+ . = ..()
+ if(.) //To allow surgery to return properly.
+ return
+ switch(M.a_intent)
+ if (INTENT_HARM)
+ var/damage = rand(1, 9)
+ if (prob(90))
+ playsound(loc, "punch", 25, 1, -1)
+ visible_message("[M] has punched [src]!", \
+ "[M] has punched [src]!", null, COMBAT_MESSAGE_RANGE)
+ if ((stat != DEAD) && (damage > 9 || prob(5)))//Regular humans have a very small chance of knocking an alien down.
+ Unconscious(40)
+ visible_message("[M] has knocked [src] down!", \
+ "[M] has knocked [src] down!")
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
+ apply_damage(damage, BRUTE, affecting)
+ log_combat(M, src, "attacked")
+ else
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to punch [src]!", \
+ "[M] has attempted to punch [src]!", null, COMBAT_MESSAGE_RANGE)
+
+ if (INTENT_DISARM)
+ if (!lying)
+ if (prob(5))
+ Unconscious(40)
+ playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
+ log_combat(M, src, "pushed")
+ visible_message("[M] has pushed down [src]!", \
+ "[M] has pushed down [src]!")
else
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to punch [src]!", \
- "[M] has attempted to punch [src]!", null, COMBAT_MESSAGE_RANGE)
-
- if ("disarm")
- if (!lying)
- if (prob(5))
- Unconscious(40)
+ if (prob(50))
+ dropItemToGround(get_active_held_item())
playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
- log_combat(M, src, "pushed")
- visible_message("[M] has pushed down [src]!", \
- "[M] has pushed down [src]!")
+ visible_message("[M] has disarmed [src]!", \
+ "[M] has disarmed [src]!", null, COMBAT_MESSAGE_RANGE)
else
- if (prob(50))
- dropItemToGround(get_active_held_item())
- playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
- visible_message("[M] has disarmed [src]!", \
- "[M] has disarmed [src]!", null, COMBAT_MESSAGE_RANGE)
- else
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to disarm [src]!",\
- "[M] has attempted to disarm [src]!", null, COMBAT_MESSAGE_RANGE)
-
-
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to disarm [src]!",\
+ "[M] has attempted to disarm [src]!", null, COMBAT_MESSAGE_RANGE)
/mob/living/carbon/alien/humanoid/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect)
if(!no_effect && !visual_effect_icon)
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 69c1be707d..7dabcf5abf 100644
--- a/code/modules/mob/living/carbon/alien/larva/larva_defense.dm
+++ b/code/modules/mob/living/carbon/alien/larva/larva_defense.dm
@@ -1,26 +1,33 @@
/mob/living/carbon/alien/larva/attack_hand(mob/living/carbon/human/M)
- if(..())
- var/damage = rand(1, 9)
- if (prob(90))
- playsound(loc, "punch", 25, 1, -1)
- log_combat(M, src, "attacked")
- visible_message("[M] has kicked [src]!", \
- "[M] has kicked [src]!", null, COMBAT_MESSAGE_RANGE)
- if ((stat != DEAD) && (damage > 4.9))
- Unconscious(rand(100,200))
+ . = ..()
+ if(. || M.a_intent == INTENT_HELP || M.a_intent == INTENT_GRAB)
+ return
+ var/damage = rand(1, 9)
+ if (prob(90))
+ playsound(loc, "punch", 25, 1, -1)
+ log_combat(M, src, "attacked")
+ visible_message("[M] has kicked [src]!", \
+ "[M] has kicked [src]!", null, COMBAT_MESSAGE_RANGE)
+ if ((stat != DEAD) && (damage > 4.9))
+ Unconscious(rand(100,200))
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
- apply_damage(damage, BRUTE, affecting)
- else
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to kick [src]!", \
- "[M] has attempted to kick [src]!", null, COMBAT_MESSAGE_RANGE)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
+ apply_damage(damage, BRUTE, affecting)
+ else
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to kick [src]!", \
+ "[M] has attempted to kick [src]!", null, COMBAT_MESSAGE_RANGE)
-/mob/living/carbon/alien/larva/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/mob/living/carbon/alien/larva/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
if(user.a_intent == INTENT_HARM)
- ..(user, 1)
+ . = ..(user, TRUE)
+ if(.)
+ return
+ playsound(loc, "punch", 25, 1, -1)
+ visible_message("[user] has pummeled [src]!", \
+ "[user] has pummeled [src]!", null, COMBAT_MESSAGE_RANGE)
adjustBruteLoss(5 + rand(1,9))
new /datum/forced_movement(src, get_step_away(user,src, 30), 1)
return 1
diff --git a/code/modules/mob/living/carbon/carbon_defense.dm b/code/modules/mob/living/carbon/carbon_defense.dm
index 06575aa802..ba40ae8e5f 100644
--- a/code/modules/mob/living/carbon/carbon_defense.dm
+++ b/code/modules/mob/living/carbon/carbon_defense.dm
@@ -48,41 +48,42 @@
if(affecting && affecting.dismemberable && affecting.get_damage() >= (affecting.max_damage - P.dismemberment))
affecting.dismember(P.damtype)
-/mob/living/carbon/proc/can_catch_item(skip_throw_mode_check)
- . = FALSE
- if(mind)
- if(mind.martial_art && mind.martial_art.dodge_chance == 100)
- return TRUE
- if(!skip_throw_mode_check && !in_throw_mode)
+/mob/living/carbon/catch_item(obj/item/I, skip_throw_mode_check = FALSE)
+ . = ..()
+ if(!HAS_TRAIT(src, TRAIT_AUTO_CATCH_ITEM) && !skip_throw_mode_check && !in_throw_mode)
return
- if(get_active_held_item())
+ if(get_active_held_item() || restrained())
return
- if(restrained())
- return
- return TRUE
-
-/mob/living/carbon/hitby(atom/movable/AM, skipcatch, hitpush = TRUE, blocked = FALSE)
- if(!skipcatch) //ugly, but easy
- if(can_catch_item())
- if(istype(AM, /obj/item))
- var/obj/item/I = AM
- if (mind)
- if (mind.martial_art && mind.martial_art.dodge_chance == 100) //autocatch for rising bass
- if (get_active_held_item())
- visible_message("[I] falls to the ground as [src] chops it out of the air!")
- return 1
- if(!in_throw_mode)
- throw_mode_on()
- if(isturf(I.loc))
- I.attack_hand(src)
- if(get_active_held_item() == I) //if our attack_hand() picks up the item...
- visible_message("[src] catches [I]!") //catch that sucker!
- throw_mode_off()
- return 1
- ..()
+ I.attack_hand(src)
+ if(get_active_held_item() == I) //if our attack_hand() picks up the item...
+ visible_message("[src] catches [I]!") //catch that sucker!
+ throw_mode_off()
+ return TRUE
+/mob/living/carbon/embed_item(obj/item/I)
+ throw_alert("embeddedobject", /obj/screen/alert/embeddedobject)
+ var/obj/item/bodypart/L = pick(bodyparts)
+ L.embedded_objects |= I
+ I.add_mob_blood(src)//it embedded itself in you, of course it's bloody!
+ I.forceMove(src)
+ L.receive_damage(I.w_class*I.embedding.embedded_impact_pain_multiplier)
+ visible_message("[I] embeds itself in [src]'s [L.name]!","[I] embeds itself in your [L.name]!")
+ SEND_SIGNAL(src, COMSIG_ADD_MOOD_EVENT, "embedded", /datum/mood_event/embedded)
/mob/living/carbon/attacked_by(obj/item/I, mob/living/user)
+ //CIT CHANGES START HERE - combatmode and resting checks
+ var/totitemdamage = I.force
+ if(iscarbon(user))
+ var/mob/living/carbon/tempcarb = user
+ if(!tempcarb.combatmode)
+ totitemdamage *= 0.5
+ if(user.resting)
+ totitemdamage *= 0.5
+ if(!combatmode)
+ totitemdamage *= 1.5
+ //CIT CHANGES END HERE
+ if(user != src && check_shields(I, totitemdamage, "the [I.name]", MELEE_ATTACK, I.armour_penetration))
+ return FALSE
var/obj/item/bodypart/affecting
if(user == src)
affecting = get_bodypart(check_zone(user.zone_selected)) //we're self-mutilating! yay!
@@ -93,17 +94,6 @@
SEND_SIGNAL(I, COMSIG_ITEM_ATTACK_ZONE, src, user, affecting)
send_item_attack_message(I, user, affecting.name)
if(I.force)
- //CIT CHANGES START HERE - combatmode and resting checks
- var/totitemdamage = I.force
- if(iscarbon(user))
- var/mob/living/carbon/tempcarb = user
- if(!tempcarb.combatmode)
- totitemdamage *= 0.5
- if(user.resting)
- totitemdamage *= 0.5
- if(!combatmode)
- totitemdamage *= 1.5
- //CIT CHANGES END HERE
apply_damage(totitemdamage, I.damtype, affecting) //CIT CHANGE - replaces I.force with totitemdamage
if(I.damtype == BRUTE && affecting.status == BODYPART_ORGANIC)
var/basebloodychance = affecting.brute_dam + totitemdamage
@@ -137,7 +127,9 @@
//ATTACK HAND IGNORING PARENT RETURN VALUE
/mob/living/carbon/attack_hand(mob/living/carbon/human/user)
-
+ . = ..()
+ if(.) //was the attack blocked?
+ return
for(var/thing in diseases)
var/datum/disease/D = thing
if(D.spread_flags & DISEASE_SPREAD_CONTACT_SKIN)
@@ -152,8 +144,7 @@
if(user.a_intent == INTENT_HELP || user.a_intent == INTENT_DISARM)
for(var/datum/surgery/S in surgeries)
if(S.next_step(user, user.a_intent))
- return 1
- return 0
+ return TRUE
/mob/living/carbon/attack_paw(mob/living/carbon/monkey/M)
@@ -173,7 +164,8 @@
help_shake_act(M)
return 0
- if(..()) //successful monkey bite.
+ . = ..()
+ if(.) //successful monkey bite.
for(var/thing in M.diseases)
var/datum/disease/D = thing
ForceContractDisease(D)
@@ -181,26 +173,27 @@
/mob/living/carbon/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
- if(M.powerlevel > 0)
- var/stunprob = M.powerlevel * 7 + 10 // 17 at level 1, 80 at level 10
- if(prob(stunprob))
- M.powerlevel -= 3
- if(M.powerlevel < 0)
- M.powerlevel = 0
+ . = ..()
+ if(!.)
+ return
+ if(M.powerlevel > 0)
+ var/stunprob = M.powerlevel * 7 + 10 // 17 at level 1, 80 at level 10
+ if(prob(stunprob))
+ M.powerlevel -= 3
+ if(M.powerlevel < 0)
+ M.powerlevel = 0
- visible_message("The [M.name] has shocked [src]!", \
- "The [M.name] has shocked [src]!")
+ visible_message("The [M.name] has shocked [src]!", \
+ "The [M.name] has shocked [src]!")
- do_sparks(5, TRUE, src)
- var/power = M.powerlevel + rand(0,3)
- Knockdown(power*20)
- if(stuttering < power)
- stuttering = power
- if (prob(stunprob) && M.powerlevel >= 8)
- adjustFireLoss(M.powerlevel * rand(6,10))
- updatehealth()
- return 1
+ do_sparks(5, TRUE, src)
+ var/power = M.powerlevel + rand(0,3)
+ Knockdown(power*20)
+ if(stuttering < power)
+ stuttering = power
+ if (prob(stunprob) && M.powerlevel >= 8)
+ adjustFireLoss(M.powerlevel * rand(6,10))
+ updatehealth()
/mob/living/carbon/proc/dismembering_strike(mob/living/attacker, dam_zone)
if(!attacker.limb_destroyer)
@@ -332,12 +325,12 @@
else
return
-
+
else if(check_zone(M.zone_selected) == "r_arm" || check_zone(M.zone_selected) == "l_arm")
M.visible_message( \
"[M] shakes [src]'s hand.", \
"You shake [src]'s hand.", )
-
+
else
M.visible_message("[M] hugs [src] to make [p_them()] feel better!", \
"You hug [src] to make [p_them()] feel better!")
diff --git a/code/modules/mob/living/carbon/human/human_defense.dm b/code/modules/mob/living/carbon/human/human_defense.dm
index 165e1fdd31..2b1d6afc4f 100644
--- a/code/modules/mob/living/carbon/human/human_defense.dm
+++ b/code/modules/mob/living/carbon/human/human_defense.dm
@@ -67,66 +67,36 @@
P.setAngle(rand(0, 360))//SHING
return FALSE
- if(!(P.original == src && P.firer == src)) //can't block or reflect when shooting yourself
- if(P.is_reflectable)
- if(check_reflect(def_zone)) // Checks if you've passed a reflection% check
- visible_message("The [P.name] gets reflected by [src]!", \
- "The [P.name] gets reflected by [src]!")
- // Find a turf near or on the original location to bounce to
- if(P.starting)
- var/new_x = P.starting.x + pick(0, 0, 0, 0, 0, -1, 1, -2, 2)
- var/new_y = P.starting.y + pick(0, 0, 0, 0, 0, -1, 1, -2, 2)
- var/turf/curloc = get_turf(src)
+ return ..()
- // redirect the projectile
- P.original = locate(new_x, new_y, P.z)
- P.starting = curloc
- P.firer = src
- P.yo = new_y - curloc.y
- P.xo = new_x - curloc.x
- var/new_angle_s = P.Angle + rand(120,240)
- while(new_angle_s > 180) // Translate to regular projectile degrees
- new_angle_s -= 360
- P.setAngle(new_angle_s)
+/mob/living/carbon/human/check_reflect(def_zone)
+ if(wear_suit?.IsReflect(def_zone))
+ return TRUE
+ return ..()
- return -1 // complete projectile permutation
-
- if(check_shields(P, P.damage, "the [P.name]", PROJECTILE_ATTACK, P.armour_penetration))
- P.on_hit(src, 100, def_zone)
- return 2
-
- return (..(P , def_zone))
-
-/mob/living/carbon/human/proc/check_reflect(def_zone) //Reflection checks for anything in your l_hand, r_hand, or wear_suit based on the reflection chance of the object
- if(wear_suit)
- if(wear_suit.IsReflect(def_zone) == 1)
- return 1
- for(var/obj/item/I in held_items)
- if(I.IsReflect(def_zone) == 1)
- return 1
- return 0
-
-/mob/living/carbon/human/proc/check_shields(atom/AM, var/damage, attack_text = "the attack", attack_type = MELEE_ATTACK, armour_penetration = 0)
+/mob/living/carbon/human/check_shields(atom/AM, damage, attack_text = "the attack", attack_type = MELEE_ATTACK, armour_penetration = 0)
+ . = ..()
+ if(.)
+ return
var/block_chance_modifier = round(damage / -3)
-
- for(var/obj/item/I in held_items)
- if(!istype(I, /obj/item/clothing))
- var/final_block_chance = I.block_chance - (CLAMP((armour_penetration-I.armour_penetration)/2,0,100)) + block_chance_modifier //So armour piercing blades can still be parried by other blades, for example
- if(I.hit_reaction(src, AM, attack_text, final_block_chance, damage, attack_type))
- return 1
if(wear_suit)
var/final_block_chance = wear_suit.block_chance - (CLAMP((armour_penetration-wear_suit.armour_penetration)/2,0,100)) + block_chance_modifier
if(wear_suit.hit_reaction(src, AM, attack_text, final_block_chance, damage, attack_type))
- return 1
+ return TRUE
if(w_uniform)
var/final_block_chance = w_uniform.block_chance - (CLAMP((armour_penetration-w_uniform.armour_penetration)/2,0,100)) + block_chance_modifier
if(w_uniform.hit_reaction(src, AM, attack_text, final_block_chance, damage, attack_type))
- return 1
+ return TRUE
if(wear_neck)
var/final_block_chance = wear_neck.block_chance - (CLAMP((armour_penetration-wear_neck.armour_penetration)/2,0,100)) + block_chance_modifier
if(wear_neck.hit_reaction(src, AM, attack_text, final_block_chance, damage, attack_type))
- return 1
- return 0
+ return TRUE
+ return FALSE
+
+/mob/living/carbon/human/can_embed(obj/item/I)
+ if(I.get_sharpness() || is_pointed(I) || is_type_in_typecache(I, GLOB.can_embed_types))
+ return TRUE
+ return FALSE
/mob/living/carbon/human/proc/check_block()
if(mind)
@@ -135,39 +105,7 @@
return FALSE
/mob/living/carbon/human/hitby(atom/movable/AM, skipcatch = FALSE, hitpush = TRUE, blocked = FALSE)
- if(dna && dna.species)
- var/spec_return = dna.species.spec_hitby(AM, src)
- if(spec_return)
- return spec_return
- var/obj/item/I
- var/throwpower = 30
- if(istype(AM, /obj/item))
- I = AM
- throwpower = I.throwforce
- if(I.thrownby == src) //No throwing stuff at yourself to trigger hit reactions
- return ..()
- if(check_shields(AM, throwpower, "\the [AM.name]", THROWN_PROJECTILE_ATTACK))
- hitpush = FALSE
- skipcatch = TRUE
- blocked = TRUE
- else if(I)
- if(I.throw_speed >= EMBED_THROWSPEED_THRESHOLD && !(mind.martial_art && mind.martial_art.dodge_chance == 100))
- if(can_embed(I))
- if(prob(I.embedding.embed_chance) && !HAS_TRAIT(src, TRAIT_PIERCEIMMUNE))
- throw_alert("embeddedobject", /obj/screen/alert/embeddedobject)
- var/obj/item/bodypart/L = pick(bodyparts)
- L.embedded_objects |= I
- I.add_mob_blood(src)//it embedded itself in you, of course it's bloody!
- I.forceMove(src)
- L.receive_damage(I.w_class*I.embedding.embedded_impact_pain_multiplier)
- visible_message("[I] embeds itself in [src]'s [L.name]!","[I] embeds itself in your [L.name]!")
- SEND_SIGNAL(src, COMSIG_ADD_MOOD_EVENT, "embedded", /datum/mood_event/embedded)
- hitpush = FALSE
- skipcatch = TRUE //can't catch the now embedded item
- if (mind)
- if (mind.martial_art && mind.martial_art.dodge_chance == 100)
- skipcatch = FALSE
- return ..()
+ return dna?.species?.spec_hitby(AM, src) || ..()
/mob/living/carbon/human/grabbedby(mob/living/carbon/user, supress_message = 0)
if(user == src && pulling && !pulling.anchored && grab_state >= GRAB_AGGRESSIVE && (HAS_TRAIT(src, TRAIT_FAT)) && ismonkey(pulling))
@@ -201,12 +139,12 @@
return dna.species.spec_attacked_by(I, user, affecting, a_intent, src)
-/mob/living/carbon/human/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/mob/living/carbon/human/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
if(user.a_intent == INTENT_HARM)
- var/hulk_verb = pick("smash","pummel")
- if(check_shields(user, 15, "the [hulk_verb]ing"))
+ . = ..(user, TRUE)
+ if(.)
return
- ..(user, 1)
+ var/hulk_verb = pick("smash","pummel")
playsound(loc, user.dna.species.attack_sound, 25, 1, -1)
var/message = "[user] has [hulk_verb]ed [src]!"
visible_message("[message]", \
@@ -215,7 +153,8 @@
return 1
/mob/living/carbon/human/attack_hand(mob/user)
- if(..()) //to allow surgery to return properly.
+ . = ..()
+ if(.) //To allow surgery to return properly.
return
if(ishuman(user))
var/mob/living/carbon/human/H = user
@@ -227,8 +166,7 @@
if(!affecting)
affecting = get_bodypart(BODY_ZONE_CHEST)
if(M.a_intent == INTENT_HELP)
- ..() //shaking
- return 0
+ return ..() //shaking
if(M.a_intent == INTENT_DISARM) //Always drop item in hand, if no item, get stunned instead.
var/obj/item/I = get_active_held_item()
@@ -249,78 +187,69 @@
if(can_inject(M, 1, affecting))//Thick suits can stop monkey bites.
if(..()) //successful monkey bite, this handles disease contraction.
var/damage = rand(1, 3)
- if(check_shields(M, damage, "the [M.name]"))
- return 0
- if(stat != DEAD)
- apply_damage(damage, BRUTE, affecting, run_armor_check(affecting, "melee"))
+ apply_damage(damage, BRUTE, affecting, run_armor_check(affecting, "melee"))
return 1
/mob/living/carbon/human/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(check_shields(M, 0, "the M.name"))
- visible_message("[M] attempted to touch [src]!")
- return 0
+ . = ..()
+ if(!.)
+ return
+ if(M.a_intent == INTENT_HARM)
+ if (w_uniform)
+ w_uniform.add_fingerprint(M)
+ var/damage = prob(90) ? 20 : 0
+ if(!damage)
+ playsound(loc, 'sound/weapons/slashmiss.ogg', 50, 1, -1)
+ visible_message("[M] has lunged at [src]!", \
+ "[M] has lunged at [src]!")
+ return 0
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ var/armor_block = run_armor_check(affecting, "melee", null, null,10)
- if(..())
- if(M.a_intent == INTENT_HARM)
- if (w_uniform)
- w_uniform.add_fingerprint(M)
- var/damage = prob(90) ? 20 : 0
- if(!damage)
- playsound(loc, 'sound/weapons/slashmiss.ogg', 50, 1, -1)
- visible_message("[M] has lunged at [src]!", \
- "[M] has lunged at [src]!")
- return 0
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- var/armor_block = run_armor_check(affecting, "melee", null, null,10)
+ playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
+ visible_message("[M] has slashed at [src]!", \
+ "[M] has slashed at [src]!")
+ log_combat(M, src, "attacked")
+ if(!dismembering_strike(M, M.zone_selected)) //Dismemberment successful
+ return 1
+ apply_damage(damage, BRUTE, affecting, armor_block)
- playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
- visible_message("[M] has slashed at [src]!", \
- "[M] has slashed at [src]!")
- log_combat(M, src, "attacked")
- if(!dismembering_strike(M, M.zone_selected)) //Dismemberment successful
- return 1
- apply_damage(damage, BRUTE, affecting, armor_block)
-
- if(M.a_intent == INTENT_DISARM) //Always drop item in hand, if no item, get stun instead.
- var/obj/item/I = get_active_held_item()
- if(I && dropItemToGround(I))
- playsound(loc, 'sound/weapons/slash.ogg', 25, 1, -1)
- visible_message("[M] disarmed [src]!", \
- "[M] disarmed [src]!")
+ if(M.a_intent == INTENT_DISARM) //Always drop item in hand, if no item, get stun instead.
+ var/obj/item/I = get_active_held_item()
+ if(I && dropItemToGround(I))
+ playsound(loc, 'sound/weapons/slash.ogg', 25, 1, -1)
+ visible_message("[M] disarmed [src]!", \
+ "[M] disarmed [src]!")
+ else
+ playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
+ if(!lying) //CITADEL EDIT
+ Knockdown(100, TRUE, FALSE, 30, 25)
else
- playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
- if(!lying) //CITADEL EDIT
- Knockdown(100, TRUE, FALSE, 30, 25)
- else
- Knockdown(100)
- log_combat(M, src, "tackled")
- visible_message("[M] has tackled down [src]!", \
- "[M] has tackled down [src]!")
-
+ Knockdown(100)
+ log_combat(M, src, "tackled")
+ visible_message("[M] has tackled down [src]!", \
+ "[M] has tackled down [src]!")
/mob/living/carbon/human/attack_larva(mob/living/carbon/alien/larva/L)
-
- if(..()) //successful larva bite.
- var/damage = rand(1, 3)
- if(check_shields(L, damage, "the [L.name]"))
- return 0
- if(stat != DEAD)
- L.amount_grown = min(L.amount_grown + damage, L.max_grown)
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(L.zone_selected))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- var/armor_block = run_armor_check(affecting, "melee")
- apply_damage(damage, BRUTE, affecting, armor_block)
+ . = ..()
+ if(!.) //unsuccessful larva bite.
+ return
+ var/damage = rand(1, 3)
+ if(stat != DEAD)
+ L.amount_grown = min(L.amount_grown + damage, L.max_grown)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(L.zone_selected))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ var/armor_block = run_armor_check(affecting, "melee")
+ apply_damage(damage, BRUTE, affecting, armor_block)
/mob/living/carbon/human/attack_animal(mob/living/simple_animal/M)
. = ..()
if(.)
var/damage = rand(M.melee_damage_lower, M.melee_damage_upper)
- if(check_shields(M, damage, "the [M.name]", MELEE_ATTACK, M.armour_penetration))
- return FALSE
var/dam_zone = dismembering_strike(M, pick(BODY_ZONE_CHEST, BODY_ZONE_PRECISE_L_HAND, BODY_ZONE_PRECISE_R_HAND, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
if(!dam_zone) //Dismemberment successful
return TRUE
@@ -332,23 +261,22 @@
/mob/living/carbon/human/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
- var/damage = rand(5, 25)
- if(M.is_adult)
- damage = rand(10, 35)
+ . = ..()
+ if(!.) //unsuccessful slime attack
+ return
+ var/damage = rand(5, 25)
+ if(M.is_adult)
+ damage = rand(10, 35)
- if(check_shields(M, damage, "the [M.name]"))
- return 0
+ var/dam_zone = dismembering_strike(M, pick(BODY_ZONE_HEAD, BODY_ZONE_CHEST, BODY_ZONE_L_ARM, BODY_ZONE_R_ARM, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
+ if(!dam_zone) //Dismemberment successful
+ return 1
- var/dam_zone = dismembering_strike(M, pick(BODY_ZONE_HEAD, BODY_ZONE_CHEST, BODY_ZONE_L_ARM, BODY_ZONE_R_ARM, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
- if(!dam_zone) //Dismemberment successful
- return 1
-
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- var/armor_block = run_armor_check(affecting, "melee")
- apply_damage(damage, BRUTE, affecting, armor_block)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ var/armor_block = run_armor_check(affecting, "melee")
+ apply_damage(damage, BRUTE, affecting, armor_block)
/mob/living/carbon/human/mech_melee_attack(obj/mecha/M)
if(M.occupant.a_intent == INTENT_HARM)
diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm
index 50ca1d90e9..2e069297b3 100644
--- a/code/modules/mob/living/carbon/human/species.dm
+++ b/code/modules/mob/living/carbon/human/species.dm
@@ -1685,11 +1685,6 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
attacker_style = M.mind.martial_art
if(attacker_style?.pacifism_check && HAS_TRAIT(M, TRAIT_PACIFISM)) // most martial arts are quite harmful, alas.
attacker_style = null
- if((M != H) && M.a_intent != INTENT_HELP && H.check_shields(M, 0, M.name, attack_type = UNARMED_ATTACK))
- log_combat(M, H, "attempted to touch")
- H.visible_message("[M] attempted to touch [H]!")
- return 0
- SEND_SIGNAL(M, COMSIG_MOB_ATTACK_HAND, M, H, attacker_style)
switch(M.a_intent)
if("help")
help(M, H, attacker_style)
diff --git a/code/modules/mob/living/carbon/monkey/combat.dm b/code/modules/mob/living/carbon/monkey/combat.dm
index 92ad87f6b5..56ef4fe24a 100644
--- a/code/modules/mob/living/carbon/monkey/combat.dm
+++ b/code/modules/mob/living/carbon/monkey/combat.dm
@@ -369,6 +369,23 @@
retaliate(L)
return ..()
+/mob/living/carbon/monkey/attack_alien(mob/living/carbon/alien/humanoid/M)
+ if(M.a_intent == INTENT_HARM && prob(MONKEY_RETALIATE_HARM_PROB))
+ retaliate(M)
+ else if(M.a_intent == INTENT_DISARM && prob(MONKEY_RETALIATE_DISARM_PROB))
+ retaliate(M)
+ return ..()
+
+/mob/living/carbon/monkey/attack_larva(mob/living/carbon/alien/larva/L)
+ if(L.a_intent == INTENT_HARM && prob(MONKEY_RETALIATE_HARM_PROB))
+ retaliate(L)
+ return ..()
+
+/mob/living/carbon/monkey/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
+ if(user.a_intent == INTENT_HARM && prob(MONKEY_RETALIATE_HARM_PROB))
+ retaliate(user)
+ return ..()
+
/mob/living/carbon/monkey/attack_paw(mob/living/L)
if(L.a_intent == INTENT_HARM && prob(MONKEY_RETALIATE_HARM_PROB))
retaliate(L)
diff --git a/code/modules/mob/living/carbon/monkey/monkey_defense.dm b/code/modules/mob/living/carbon/monkey/monkey_defense.dm
index df90dd56fd..32e3d21ee2 100644
--- a/code/modules/mob/living/carbon/monkey/monkey_defense.dm
+++ b/code/modules/mob/living/carbon/monkey/monkey_defense.dm
@@ -6,37 +6,55 @@
..()
/mob/living/carbon/monkey/attack_paw(mob/living/M)
- if(..()) //successful monkey bite.
- var/dam_zone = pick(BODY_ZONE_CHEST, BODY_ZONE_PRECISE_L_HAND, BODY_ZONE_PRECISE_R_HAND, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG)
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- if(M.limb_destroyer)
- dismembering_strike(M, affecting.body_zone)
- if(stat != DEAD)
- var/dmg = rand(1, 5)
- apply_damage(dmg, BRUTE, affecting)
+ . = ..()
+ if(!.) //unsuccessful monkey bite.
+ return
+ var/dam_zone = pick(BODY_ZONE_CHEST, BODY_ZONE_PRECISE_L_HAND, BODY_ZONE_PRECISE_R_HAND, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ if(M.limb_destroyer)
+ dismembering_strike(M, affecting.body_zone)
+ var/dmg = rand(1, 5)
+ apply_damage(dmg, BRUTE, affecting)
/mob/living/carbon/monkey/attack_larva(mob/living/carbon/alien/larva/L)
- if(..()) //successful larva bite.
- var/damage = rand(1, 3)
- if(stat != DEAD)
- L.amount_grown = min(L.amount_grown + damage, L.max_grown)
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(L.zone_selected))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- apply_damage(damage, BRUTE, affecting)
+ . = ..()
+ if(!.) //unsuccessful larva bite
+ return
+ var/damage = rand(1, 3)
+ if(stat != DEAD)
+ L.amount_grown = min(L.amount_grown + damage, L.max_grown)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(L.zone_selected))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ apply_damage(damage, BRUTE, affecting)
+
+/mob/living/carbon/monkey/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
+ . = ..(user, TRUE)
+ if(.)
+ return
+ var/hulk_verb = pick("smash","pummel")
+ playsound(loc, user.dna.species.attack_sound, 25, 1, -1)
+ var/message = "[user] has [hulk_verb]ed [src]!"
+ visible_message("[message]", \
+ "[message]")
+ adjustBruteLoss(15)
+ return TRUE
/mob/living/carbon/monkey/attack_hand(mob/living/carbon/human/M)
- if(..()) //To allow surgery to return properly.
+ . = ..()
+ if(.) //To allow surgery to return properly.
return
-
switch(M.a_intent)
- if("help")
+ if(INTENT_HELP)
help_shake_act(M)
- if("grab")
+ if(INTENT_GRAB)
grabbedby(M)
- if("harm")
+ if(INTENT_HARM)
+ if(HAS_TRAIT(M, TRAIT_PACIFISM))
+ to_chat(M, "You don't want to hurt [src]!")
+ return
M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
if (prob(75))
visible_message("[M] has punched [name]!", \
@@ -60,7 +78,7 @@
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
visible_message("[M] has attempted to punch [name]!", \
"[M] has attempted to punch [name]!", null, COMBAT_MESSAGE_RANGE)
- if("disarm")
+ if(INTENT_DISARM)
if(!IsUnconscious())
M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
if (prob(25))
@@ -74,50 +92,51 @@
visible_message("[M] has disarmed [src]!", "[M] has disarmed [src]!", null, COMBAT_MESSAGE_RANGE)
/mob/living/carbon/monkey/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(..()) //if harm or disarm intent.
- if (M.a_intent == INTENT_HARM)
- if ((prob(95) && health > 0))
- playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
- var/damage = rand(15, 30)
- if (damage >= 25)
- damage = rand(20, 40)
- if(AmountUnconscious() < 300)
- Unconscious(rand(200, 300))
- visible_message("[M] has wounded [name]!", \
- "[M] has wounded [name]!", null, COMBAT_MESSAGE_RANGE)
- else
- visible_message("[M] has slashed [name]!", \
- "[M] has slashed [name]!", null, COMBAT_MESSAGE_RANGE)
-
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
- log_combat(M, src, "attacked")
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- if(!dismembering_strike(M, affecting.body_zone)) //Dismemberment successful
- return 1
- apply_damage(damage, BRUTE, affecting)
-
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
+ return
+ if (M.a_intent == INTENT_HARM)
+ if ((prob(95) && health > 0))
+ playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
+ var/damage = rand(15, 30)
+ if (damage >= 25)
+ damage = rand(20, 40)
+ if(AmountUnconscious() < 300)
+ Unconscious(rand(200, 300))
+ visible_message("[M] has wounded [name]!", \
+ "[M] has wounded [name]!", null, COMBAT_MESSAGE_RANGE)
else
- playsound(loc, 'sound/weapons/slashmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to lunge at [name]!", \
- "[M] has attempted to lunge at [name]!", null, COMBAT_MESSAGE_RANGE)
+ visible_message("[M] has slashed [name]!", \
+ "[M] has slashed [name]!", null, COMBAT_MESSAGE_RANGE)
- if (M.a_intent == INTENT_DISARM)
- var/obj/item/I = null
- playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
- if(prob(95))
- Knockdown(20)
- visible_message("[M] has tackled down [name]!", \
- "[M] has tackled down [name]!", null, COMBAT_MESSAGE_RANGE)
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(M.zone_selected))
+ log_combat(M, src, "attacked")
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ if(!dismembering_strike(M, affecting.body_zone)) //Dismemberment successful
+ return 1
+ apply_damage(damage, BRUTE, affecting)
+
+ else
+ playsound(loc, 'sound/weapons/slashmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to lunge at [name]!", \
+ "[M] has attempted to lunge at [name]!", null, COMBAT_MESSAGE_RANGE)
+
+ else
+ var/obj/item/I = null
+ playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
+ if(prob(95))
+ Knockdown(20)
+ visible_message("[M] has tackled down [name]!", \
+ "[M] has tackled down [name]!", null, COMBAT_MESSAGE_RANGE)
+ else
+ I = get_active_held_item()
+ if(dropItemToGround(I))
+ visible_message("[M] has disarmed [name]!", "[M] has disarmed [name]!", null, COMBAT_MESSAGE_RANGE)
else
- I = get_active_held_item()
- if(dropItemToGround(I))
- visible_message("[M] has disarmed [name]!", "[M] has disarmed [name]!", null, COMBAT_MESSAGE_RANGE)
- else
- I = null
- log_combat(M, src, "disarmed", "[I ? " removing \the [I]" : ""]")
- updatehealth()
-
+ I = null
+ log_combat(M, src, "disarmed", "[I ? " removing \the [I]" : ""]")
+ updatehealth()
/mob/living/carbon/monkey/attack_animal(mob/living/simple_animal/M)
. = ..()
@@ -132,17 +151,19 @@
apply_damage(damage, M.melee_damage_type, affecting)
/mob/living/carbon/monkey/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
- var/damage = rand(5, 35)
- if(M.is_adult)
- damage = rand(20, 40)
- var/dam_zone = dismembering_strike(M, pick(BODY_ZONE_HEAD, BODY_ZONE_CHEST, BODY_ZONE_L_ARM, BODY_ZONE_R_ARM, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
- if(!dam_zone) //Dismemberment successful
- return 1
- var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
- if(!affecting)
- affecting = get_bodypart(BODY_ZONE_CHEST)
- apply_damage(damage, BRUTE, affecting)
+ . = ..()
+ if(!.) //unsuccessful slime attack
+ return
+ var/damage = rand(5, 35)
+ if(M.is_adult)
+ damage = rand(20, 40)
+ var/dam_zone = dismembering_strike(M, pick(BODY_ZONE_HEAD, BODY_ZONE_CHEST, BODY_ZONE_L_ARM, BODY_ZONE_R_ARM, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
+ if(!dam_zone) //Dismemberment successful
+ return 1
+ var/obj/item/bodypart/affecting = get_bodypart(ran_zone(dam_zone))
+ if(!affecting)
+ affecting = get_bodypart(BODY_ZONE_CHEST)
+ apply_damage(damage, BRUTE, affecting)
/mob/living/carbon/monkey/acid_act(acidpwr, acid_volume, bodyzone_hit)
. = 1
diff --git a/code/modules/mob/living/living_defense.dm b/code/modules/mob/living/living_defense.dm
index 722c984309..3c5c5e3518 100644
--- a/code/modules/mob/living/living_defense.dm
+++ b/code/modules/mob/living/living_defense.dm
@@ -36,7 +36,50 @@
/mob/living/proc/on_hit(obj/item/projectile/P)
return
+/mob/living/proc/check_shields(atom/AM, damage, attack_text = "the attack", attack_type = MELEE_ATTACK, armour_penetration = 0)
+ var/block_chance_modifier = round(damage / -3)
+ for(var/obj/item/I in held_items)
+ if(!istype(I, /obj/item/clothing))
+ var/final_block_chance = I.block_chance - (CLAMP((armour_penetration-I.armour_penetration)/2,0,100)) + block_chance_modifier //So armour piercing blades can still be parried by other blades, for example
+ if(I.hit_reaction(src, AM, attack_text, final_block_chance, damage, attack_type))
+ return TRUE
+ return FALSE
+
+/mob/living/proc/check_reflect(def_zone) //Reflection checks for anything in your hands, based on the reflection chance of the object(s)
+ for(var/obj/item/I in held_items)
+ if(I.IsReflect(def_zone))
+ return TRUE
+ return FALSE
+
+/mob/living/proc/reflect_bullet_check(obj/item/projectile/P, def_zone)
+ if(P.is_reflectable && check_reflect(def_zone)) // Checks if you've passed a reflection% check
+ visible_message("The [P.name] gets reflected by [src]!", \
+ "The [P.name] gets reflected by [src]!")
+ // Find a turf near or on the original location to bounce to
+ if(P.starting)
+ var/new_x = P.starting.x + pick(0, 0, 0, 0, 0, -1, 1, -2, 2)
+ var/new_y = P.starting.y + pick(0, 0, 0, 0, 0, -1, 1, -2, 2)
+ var/turf/curloc = get_turf(src)
+ // redirect the projectile
+ P.original = locate(new_x, new_y, P.z)
+ P.starting = curloc
+ P.firer = src
+ P.yo = new_y - curloc.y
+ P.xo = new_x - curloc.x
+ var/new_angle_s = P.Angle + rand(120,240)
+ while(new_angle_s > 180) // Translate to regular projectile degrees
+ new_angle_s -= 360
+ P.setAngle(new_angle_s)
+ return TRUE
+ return FALSE
+
/mob/living/bullet_act(obj/item/projectile/P, def_zone)
+ if(P.original != src || P.firer != src) //try to block or reflect the bullet, can't do so when shooting oneself
+ if(reflect_bullet_check(P, def_zone))
+ return -1 // complete projectile permutation
+ if(check_shields(P, P.damage, "the [P.name]", PROJECTILE_ATTACK, P.armour_penetration))
+ P.on_hit(src, 100, def_zone)
+ return 2
var/armor = run_armor_check(def_zone, P.flag, null, null, P.armour_penetration, null)
if(!P.nodamage)
apply_damage(P.damage, P.damage_type, def_zone, armor)
@@ -55,9 +98,32 @@
else
return 0
+/mob/living/proc/catch_item(obj/item/I, skip_throw_mode_check = FALSE)
+ return FALSE
+
+/mob/living/proc/embed_item(obj/item/I)
+ return
+
+/mob/living/proc/can_embed(obj/item/I)
+ return FALSE
+
/mob/living/hitby(atom/movable/AM, skipcatch, hitpush = TRUE, blocked = FALSE)
- if(istype(AM, /obj/item))
- var/obj/item/I = AM
+ var/obj/item/I
+ var/throwpower = 30
+ if(isitem(AM))
+ I = AM
+ throwpower = I.throwforce
+ if(check_shields(AM, throwpower, "\the [AM.name]", THROWN_PROJECTILE_ATTACK))
+ hitpush = FALSE
+ skipcatch = TRUE
+ blocked = TRUE
+ else if(I && I.throw_speed >= EMBED_THROWSPEED_THRESHOLD && can_embed(I, src) && prob(I.embedding.embed_chance) && !HAS_TRAIT(src, TRAIT_PIERCEIMMUNE) && (!HAS_TRAIT(src, TRAIT_AUTO_CATCH_ITEM) || incapacitated() || get_active_held_item()))
+ embed_item(I)
+ hitpush = FALSE
+ skipcatch = TRUE //can't catch the now embedded item
+ if(I)
+ if(!skipcatch && isturf(I.loc) && catch_item(I))
+ return TRUE
var/zone = ran_zone(BODY_ZONE_CHEST, 65)//Hits a random part of the body, geared towards the chest
var/dtype = BRUTE
var/volume = I.get_volume_by_throwforce_and_or_w_class()
@@ -214,6 +280,24 @@
Move(user.loc)
return 1
+/mob/living/attack_hand(mob/user)
+ ..() //Ignoring parent return value here.
+ SEND_SIGNAL(src, COMSIG_MOB_ATTACK_HAND, user)
+ if((user != src) && user.a_intent != INTENT_HELP && check_shields(user, 0, user.name, attack_type = UNARMED_ATTACK))
+ log_combat(user, src, "attempted to touch")
+ visible_message("[user] attempted to touch [src]!")
+ return TRUE
+
+/mob/living/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
+ if(user.a_intent == INTENT_HARM)
+ if(HAS_TRAIT(user, TRAIT_PACIFISM))
+ to_chat(user, "You don't want to hurt [src]!")
+ return TRUE
+ var/hulk_verb = pick("smash","pummel")
+ if(user != src && check_shields(user, 15, "the [hulk_verb]ing"))
+ return TRUE
+ ..()
+ return FALSE
/mob/living/attack_slime(mob/living/simple_animal/slime/M)
if(!SSticker.HasRoundStarted())
@@ -229,6 +313,12 @@
to_chat(M, "You don't want to hurt anyone!")
return FALSE
+ var/damage = rand(5, 35)
+ if(M.is_adult)
+ damage = rand(20, 40)
+ if(check_shields(M, damage, "the [M.name]"))
+ return FALSE
+
if (stat != DEAD)
log_combat(M, src, "attacked")
M.do_attack_animation(src)
@@ -245,7 +335,8 @@
if(HAS_TRAIT(M, TRAIT_PACIFISM))
to_chat(M, "You don't want to hurt anyone!")
return FALSE
-
+ if(check_shields(M, rand(M.melee_damage_lower, M.melee_damage_upper), "the [M.name]", MELEE_ATTACK, M.armour_penetration))
+ return FALSE
if(M.attack_sound)
playsound(loc, M.attack_sound, 50, 1, 1)
M.do_attack_animation(src)
@@ -256,10 +347,6 @@
/mob/living/attack_paw(mob/living/carbon/monkey/M)
- if(isturf(loc) && istype(loc.loc, /area/start))
- to_chat(M, "No attacking people at spawn, you jackass.")
- return FALSE
-
if (M.a_intent == INTENT_HARM)
if(HAS_TRAIT(M, TRAIT_PACIFISM))
to_chat(M, "You don't want to hurt anyone!")
@@ -268,6 +355,8 @@
if(M.is_muzzled() || (M.wear_mask && M.wear_mask.flags_cover & MASKCOVERSMOUTH))
to_chat(M, "You can't bite with your mouth covered!")
return FALSE
+ if(check_shields(M, 0, "the [M.name]"))
+ return FALSE
M.do_attack_animation(src, ATTACK_EFFECT_BITE)
if (prob(75))
log_combat(M, src, "attacked")
@@ -282,15 +371,16 @@
/mob/living/attack_larva(mob/living/carbon/alien/larva/L)
switch(L.a_intent)
- if("help")
+ if(INTENT_HELP)
visible_message("[L.name] rubs its head against [src].")
return FALSE
else
if(HAS_TRAIT(L, TRAIT_PACIFISM))
to_chat(L, "You don't want to hurt anyone!")
- return
-
+ return FALSE
+ if(L != src && check_shields(L, rand(1, 3), "the [L.name]"))
+ return FALSE
L.do_attack_animation(src)
if(prob(90))
log_combat(L, src, "attacked")
@@ -301,24 +391,29 @@
else
visible_message("[L.name] has attempted to bite [src]!", \
"[L.name] has attempted to bite [src]!", null, COMBAT_MESSAGE_RANGE)
- return FALSE
/mob/living/attack_alien(mob/living/carbon/alien/humanoid/M)
+ if((M != src) && M.a_intent != INTENT_HELP && check_shields(M, 0, "the [M.name]"))
+ visible_message("[M] attempted to touch [src]!")
+ return FALSE
switch(M.a_intent)
- if ("help")
- visible_message("[M] caresses [src] with its scythe like arm.")
+ if (INTENT_HELP)
+ if(!isalien(src)) //I know it's ugly, but the alien vs alien attack_alien behaviour is a bit different.
+ visible_message("[M] caresses [src] with its scythe like arm.")
return FALSE
- if ("grab")
+ if (INTENT_GRAB)
grabbedby(M)
return FALSE
- if("harm")
+ if(INTENT_HARM)
if(HAS_TRAIT(M, TRAIT_PACIFISM))
to_chat(M, "You don't want to hurt anyone!")
return FALSE
- M.do_attack_animation(src)
+ if(!isalien(src))
+ M.do_attack_animation(src)
return TRUE
- if("disarm")
- M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
+ if(INTENT_DISARM)
+ if(!isalien(src))
+ M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
return TRUE
/mob/living/ex_act(severity, target, origin)
diff --git a/code/modules/mob/living/silicon/ai/ai_defense.dm b/code/modules/mob/living/silicon/ai/ai_defense.dm
index 7c59c2b791..97d26f672a 100644
--- a/code/modules/mob/living/silicon/ai/ai_defense.dm
+++ b/code/modules/mob/living/silicon/ai/ai_defense.dm
@@ -1,15 +1,9 @@
-
/mob/living/silicon/ai/attacked_by(obj/item/I, mob/living/user, def_zone)
+ . = ..()
+ if(!.)
+ return FALSE
if(I.force && I.damtype != STAMINA && stat != DEAD) //only sparks if real damage is dealt.
spark_system.start()
- return ..()
-
-
-/mob/living/silicon/ai/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(!SSticker.HasRoundStarted())
- to_chat(M, "You cannot attack people before the game has started.")
- return
- ..()
/mob/living/silicon/ai/attack_slime(mob/living/simple_animal/slime/user)
return //immune to slimes
diff --git a/code/modules/mob/living/silicon/pai/pai_defense.dm b/code/modules/mob/living/silicon/pai/pai_defense.dm
index dfc718f1ab..5ac841326b 100644
--- a/code/modules/mob/living/silicon/pai/pai_defense.dm
+++ b/code/modules/mob/living/silicon/pai/pai_defense.dm
@@ -26,13 +26,14 @@
fold_in(force = 1)
Knockdown(200)
+//ATTACK HAND IGNORING PARENT RETURN VALUE
/mob/living/silicon/pai/attack_hand(mob/living/carbon/human/user)
switch(user.a_intent)
- if("help")
+ if(INTENT_HELP)
visible_message("[user] gently pats [src] on the head, eliciting an off-putting buzzing from its holographic field.")
- if("disarm")
+ if(INTENT_DISARM)
visible_message("[user] boops [src] on the head!")
- if("harm")
+ if(INTENT_HARM)
user.do_attack_animation(src)
if (user.name == master)
visible_message("Responding to its master's touch, [src] disengages its holochassis emitter, rapidly losing coherence.")
@@ -41,14 +42,19 @@
if(user.put_in_hands(card))
user.visible_message("[user] promptly scoops up [user.p_their()] pAI's card.")
else
+ if(HAS_TRAIT(user, TRAIT_PACIFISM))
+ to_chat(user, "You don't want to hurt [src]!")
+ return
visible_message("[user] stomps on [src]!.")
take_holo_damage(2)
+ else
+ grabbedby(user)
-/mob/living/silicon/pai/bullet_act(obj/item/projectile/Proj)
- if(Proj.stun)
+/mob/living/silicon/pai/bullet_act(obj/item/projectile/P, def_zone)
+ if(P.stun)
fold_in(force = TRUE)
- src.visible_message("The electrically-charged projectile disrupts [src]'s holomatrix, forcing [src] to fold in!")
- . = ..(Proj)
+ visible_message("The electrically-charged projectile disrupts [src]'s holomatrix, forcing [src] to fold in!")
+ . = ..()
/mob/living/silicon/pai/stripPanelUnequip(obj/item/what, mob/who, where) //prevents stripping
to_chat(src, "Your holochassis stutters and warps intensely as you attempt to interact with the object, forcing you to cease lest the field fail.")
diff --git a/code/modules/mob/living/silicon/robot/robot_defense.dm b/code/modules/mob/living/silicon/robot/robot_defense.dm
index 0f09b6f62a..7e06c66eff 100644
--- a/code/modules/mob/living/silicon/robot/robot_defense.dm
+++ b/code/modules/mob/living/silicon/robot/robot_defense.dm
@@ -13,7 +13,19 @@
spark_system.start()
return ..()
+/mob/living/silicon/robot/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
+ . = ..()
+ if(.)
+ spark_system.start()
+ spawn(0)
+ step_away(src,user,15)
+ sleep(3)
+ step_away(src,user,15)
+
/mob/living/silicon/robot/attack_alien(mob/living/carbon/alien/humanoid/M)
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
+ return
if (M.a_intent == INTENT_DISARM)
if(!(lying))
M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
@@ -30,24 +42,19 @@
visible_message("[M] has forced back [src]!", \
"[M] has forced back [src]!", null, COMBAT_MESSAGE_RANGE)
playsound(loc, 'sound/weapons/pierce.ogg', 50, 1, -1)
- else
- ..()
- return
/mob/living/silicon/robot/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime shock
- flash_act()
- var/stunprob = M.powerlevel * 7 + 10
- if(prob(stunprob) && M.powerlevel >= 8)
- adjustBruteLoss(M.powerlevel * rand(6,10))
-
- var/damage = rand(1, 3)
-
+ . = ..()
+ if(!.) //unsuccessful slime shock
+ return
+ var/stunprob = M.powerlevel * 7 + 10
+ var/damage = M.powerlevel * rand(6,10)
+ if(prob(stunprob) && M.powerlevel >= 8)
+ flash_act(affect_silicon = TRUE) //my borg eyes!
if(M.is_adult)
- damage = rand(20, 40)
+ damage += rand(10, 20)
else
- damage = rand(5, 35)
- damage = round(damage / 2) // borgs receive half damage
+ damage += rand(2, 17)
adjustBruteLoss(damage)
updatehealth()
@@ -56,23 +63,17 @@
//ATTACK HAND IGNORING PARENT RETURN VALUE
/mob/living/silicon/robot/attack_hand(mob/living/carbon/human/user)
add_fingerprint(user)
- if(opened && !wiresexposed && !issilicon(user))
- if(cell)
- cell.update_icon()
- cell.add_fingerprint(user)
- user.put_in_active_hand(cell)
- to_chat(user, "You remove \the [cell].")
- cell = null
- update_icons()
- diag_hud_set_borgcell()
+ if(opened && !wiresexposed && cell && !issilicon(user))
+ cell.update_icon()
+ cell.add_fingerprint(user)
+ user.put_in_active_hand(cell)
+ to_chat(user, "You remove \the [cell].")
+ cell = null
+ update_icons()
+ diag_hud_set_borgcell()
if(!opened)
- if(..()) // hulk attack
- spark_system.start()
- spawn(0)
- step_away(src,user,15)
- sleep(3)
- step_away(src,user,15)
+ return ..()
/mob/living/silicon/robot/fire_act()
if(!on_fire) //Silicons don't gain stacks from hotspots, but hotspots can ignite them
@@ -182,9 +183,9 @@
if (stat != DEAD)
adjustBruteLoss(30)
-/mob/living/silicon/robot/bullet_act(var/obj/item/projectile/Proj)
- ..(Proj)
+/mob/living/silicon/robot/bullet_act(obj/item/projectile/P, def_zone)
+ ..()
updatehealth()
- if(prob(75) && Proj.damage > 0)
+ if(prob(75) && P.damage > 0)
spark_system.start()
return 2
diff --git a/code/modules/mob/living/silicon/silicon_defense.dm b/code/modules/mob/living/silicon/silicon_defense.dm
index 073a2eec2b..ca8ad25713 100644
--- a/code/modules/mob/living/silicon/silicon_defense.dm
+++ b/code/modules/mob/living/silicon/silicon_defense.dm
@@ -6,7 +6,10 @@
return 2
/mob/living/silicon/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(..()) //if harm or disarm intent
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
+ return
+ if(M.a_intent == INTENT_HARM)
var/damage = 20
if (prob(90))
log_combat(M, src, "attacked")
@@ -49,34 +52,33 @@
/mob/living/silicon/attack_paw(mob/living/user)
return attack_hand(user)
-/mob/living/silicon/attack_larva(mob/living/carbon/alien/larva/L)
- if(L.a_intent == INTENT_HELP)
- visible_message("[L.name] rubs its head against [src].")
-
-/mob/living/silicon/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/mob/living/silicon/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
if(user.a_intent == INTENT_HARM)
- ..(user, 1)
+ . = ..(user, TRUE)
+ if(.)
+ return
adjustBruteLoss(rand(10, 15))
playsound(loc, "punch", 25, 1, -1)
visible_message("[user] has punched [src]!", \
"[user] has punched [src]!")
- return 1
- return 0
+ return TRUE
+ return FALSE
-//ATTACK HAND IGNORING PARENT RETURN VALUE
/mob/living/silicon/attack_hand(mob/living/carbon/human/M)
+ . = ..()
+ if(.) //the attack was blocked
+ return
switch(M.a_intent)
- if ("help")
+ if (INTENT_HELP)
M.visible_message("[M] pets [src].", \
"You pet [src].")
- if("grab")
+ if(INTENT_GRAB)
grabbedby(M)
else
M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
playsound(src.loc, 'sound/effects/bang.ogg', 10, 1)
visible_message("[M] punches [src], but doesn't leave a dent.", \
"[M] punches [src], but doesn't leave a dent.", null, COMBAT_MESSAGE_RANGE)
- return 0
/mob/living/silicon/attack_drone(mob/living/simple_animal/drone/M)
if(M.a_intent == INTENT_HARM)
@@ -108,19 +110,25 @@
M.visible_message("[M] is thrown off of [src]!")
flash_act(affect_silicon = 1)
-/mob/living/silicon/bullet_act(obj/item/projectile/Proj)
- if((Proj.damage_type == BRUTE || Proj.damage_type == BURN))
- adjustBruteLoss(Proj.damage)
- if(prob(Proj.damage*1.5))
+/mob/living/silicon/bullet_act(obj/item/projectile/P, def_zone)
+ if(P.original != src || P.firer != src) //try to block or reflect the bullet, can't do so when shooting oneself
+ if(reflect_bullet_check(P, def_zone))
+ return -1 // complete projectile permutation
+ if(check_shields(P, P.damage, "the [P.name]", PROJECTILE_ATTACK, P.armour_penetration))
+ P.on_hit(src, 100, def_zone)
+ return 2
+ if((P.damage_type == BRUTE || P.damage_type == BURN))
+ adjustBruteLoss(P.damage)
+ if(prob(P.damage*1.5))
for(var/mob/living/M in buckled_mobs)
M.visible_message("[M] is knocked off of [src]!")
unbuckle_mob(M)
M.Knockdown(40)
- if(Proj.stun || Proj.knockdown)
+ if(P.stun || P.knockdown)
for(var/mob/living/M in buckled_mobs)
unbuckle_mob(M)
- M.visible_message("[M] is knocked off of [src] by the [Proj]!")
- Proj.on_hit(src)
+ M.visible_message("[M] is knocked off of [src] by the [P]!")
+ P.on_hit(src)
return 2
/mob/living/silicon/flash_act(intensity = 1, override_blindness_check = 0, affect_silicon = 0, visual = 0, type = /obj/screen/fullscreen/flash/static)
diff --git a/code/modules/mob/living/simple_animal/animal_defense.dm b/code/modules/mob/living/simple_animal/animal_defense.dm
index 793df63c87..0dfa126e79 100644
--- a/code/modules/mob/living/simple_animal/animal_defense.dm
+++ b/code/modules/mob/living/simple_animal/animal_defense.dm
@@ -1,20 +1,22 @@
/mob/living/simple_animal/attack_hand(mob/living/carbon/human/M)
- ..()
+ . = ..()
+ if(.) //the attack was blocked
+ return
switch(M.a_intent)
- if("help")
+ if(INTENT_HELP)
if (health > 0)
visible_message("[M] [response_help] [src].")
playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
- if("grab")
+ if(INTENT_GRAB)
if(grab_state >= GRAB_AGGRESSIVE && isliving(pulling))
vore_attack(M, pulling)
else
grabbedby(M)
- if("harm", "disarm")
+ if(INTENT_HARM, INTENT_DISARM)
if(HAS_TRAIT(M, TRAIT_PACIFISM))
to_chat(M, "You don't want to hurt [src]!")
return
@@ -27,12 +29,11 @@
updatehealth()
return TRUE
-/mob/living/simple_animal/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
+/mob/living/simple_animal/attack_hulk(mob/living/carbon/human/user, does_attack_animation = FALSE)
if(user.a_intent == INTENT_HARM)
- if(HAS_TRAIT(user, TRAIT_PACIFISM))
- to_chat(user, "You don't want to hurt [src]!")
- return FALSE
- ..(user, 1)
+ . = ..(user, TRUE)
+ if(.)
+ return
playsound(loc, "punch", 25, 1, -1)
visible_message("[user] has punched [src]!", \
"[user] has punched [src]!", null, COMBAT_MESSAGE_RANGE)
@@ -40,32 +41,32 @@
return TRUE
/mob/living/simple_animal/attack_paw(mob/living/carbon/monkey/M)
- if(..()) //successful monkey bite.
- if(stat != DEAD)
- var/damage = rand(1, 3)
- attack_threshold_check(damage)
- return 1
+ . = ..()
+ if(.) //successful larva bite
+ var/damage = rand(1, 3)
+ attack_threshold_check(damage)
+ return 1
if (M.a_intent == INTENT_HELP)
if (health > 0)
visible_message("[M.name] [response_help] [src].")
playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
-
/mob/living/simple_animal/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(..()) //if harm or disarm intent.
- if(M.a_intent == INTENT_DISARM)
- playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
- visible_message("[M] [response_disarm] [name]!", \
- "[M] [response_disarm] [name]!", null, COMBAT_MESSAGE_RANGE)
- log_combat(M, src, "disarmed")
- else
- var/damage = rand(15, 30)
- visible_message("[M] has slashed at [src]!", \
- "[M] has slashed at [src]!", null, COMBAT_MESSAGE_RANGE)
- playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
- attack_threshold_check(damage)
- log_combat(M, src, "attacked")
- return 1
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
+ return
+ if(M.a_intent == INTENT_DISARM)
+ playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
+ visible_message("[M] [response_disarm] [name]!", \
+ "[M] [response_disarm] [name]!", null, COMBAT_MESSAGE_RANGE)
+ log_combat(M, src, "disarmed")
+ else
+ var/damage = rand(15, 30)
+ visible_message("[M] has slashed at [src]!", \
+ "[M] has slashed at [src]!", null, COMBAT_MESSAGE_RANGE)
+ playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
+ attack_threshold_check(damage)
+ log_combat(M, src, "attacked")
/mob/living/simple_animal/attack_larva(mob/living/carbon/alien/larva/L)
. = ..()
@@ -82,7 +83,8 @@
return attack_threshold_check(damage, M.melee_damage_type)
/mob/living/simple_animal/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
+ . = ..()
+ if(.) //successful slime shock
var/damage = rand(15, 25)
if(M.is_adult)
damage = rand(20, 35)
diff --git a/code/modules/mob/living/simple_animal/bot/honkbot.dm b/code/modules/mob/living/simple_animal/bot/honkbot.dm
index 2de4ca39fd..109c7b4636 100644
--- a/code/modules/mob/living/simple_animal/bot/honkbot.dm
+++ b/code/modules/mob/living/simple_animal/bot/honkbot.dm
@@ -113,7 +113,7 @@ Maintenance panel panel is [open ? "opened" : "closed"]"},
mode = BOT_HUNT
/mob/living/simple_animal/bot/honkbot/attack_hand(mob/living/carbon/human/H)
- if(H.a_intent == "harm")
+ if(H.a_intent == INTENT_HARM)
retaliate(H)
addtimer(CALLBACK(src, .proc/react_buzz), 5)
return ..()
diff --git a/code/modules/mob/living/simple_animal/friendly/cat.dm b/code/modules/mob/living/simple_animal/friendly/cat.dm
index 02e171e4c4..bda309f7c7 100644
--- a/code/modules/mob/living/simple_animal/friendly/cat.dm
+++ b/code/modules/mob/living/simple_animal/friendly/cat.dm
@@ -232,9 +232,9 @@
/mob/living/simple_animal/pet/cat/attack_hand(mob/living/carbon/human/M)
. = ..()
switch(M.a_intent)
- if("help")
+ if(INTENT_HELP)
wuv(1, M)
- if("harm")
+ if(INTENT_HARM)
wuv(-1, M)
/mob/living/simple_animal/pet/cat/proc/wuv(change, mob/M)
@@ -290,7 +290,9 @@
D.decorate_donut()
/mob/living/simple_animal/pet/cat/cak/attack_hand(mob/living/L)
- ..()
+ . = ..()
+ if(.) //the attack was blocked
+ return
if(L.a_intent == INTENT_HARM && L.reagents && !stat)
L.reagents.add_reagent("nutriment", 0.4)
L.reagents.add_reagent("vitamin", 0.4)
diff --git a/code/modules/mob/living/simple_animal/friendly/dog.dm b/code/modules/mob/living/simple_animal/friendly/dog.dm
index 0d933d171b..986e5c9b4d 100644
--- a/code/modules/mob/living/simple_animal/friendly/dog.dm
+++ b/code/modules/mob/living/simple_animal/friendly/dog.dm
@@ -643,9 +643,9 @@
/mob/living/simple_animal/pet/dog/attack_hand(mob/living/carbon/human/M)
. = ..()
switch(M.a_intent)
- if("help")
+ if(INTENT_HELP)
wuv(1,M)
- if("harm")
+ if(INTENT_HARM)
wuv(-1,M)
/mob/living/simple_animal/pet/dog/proc/wuv(change, mob/M)
diff --git a/code/modules/mob/living/simple_animal/friendly/drone/interaction.dm b/code/modules/mob/living/simple_animal/friendly/drone/interaction.dm
index e40eb585e8..c9207fcf89 100644
--- a/code/modules/mob/living/simple_animal/friendly/drone/interaction.dm
+++ b/code/modules/mob/living/simple_animal/friendly/drone/interaction.dm
@@ -31,9 +31,9 @@
//picky up the drone c:
/mob/living/simple_animal/drone/attack_hand(mob/user)
- ..()
- if(user.a_intent == INTENT_HELP)
- mob_try_pickup(user)
+ if(user.a_intent != INTENT_HELP)
+ return ..() // TODO: convert picking up mobs into an element or component.
+ mob_try_pickup(user)
/mob/living/simple_animal/drone/proc/try_reactivate(mob/living/user)
var/mob/dead/observer/G = get_ghost()
diff --git a/code/modules/mob/living/simple_animal/guardian/types/charger.dm b/code/modules/mob/living/simple_animal/guardian/types/charger.dm
index 49514d0d12..914d38022f 100644
--- a/code/modules/mob/living/simple_animal/guardian/types/charger.dm
+++ b/code/modules/mob/living/simple_animal/guardian/types/charger.dm
@@ -54,10 +54,8 @@
var/blocked = FALSE
if(hasmatchingsummoner(A)) //if the summoner matches don't hurt them
blocked = TRUE
- if(ishuman(A))
- var/mob/living/carbon/human/H = A
- if(H.check_shields(src, 90, "[name]", attack_type = THROWN_PROJECTILE_ATTACK))
- blocked = TRUE
+ if(L.check_shields(src, 90, "[name]", attack_type = THROWN_PROJECTILE_ATTACK))
+ blocked = TRUE
if(!blocked)
L.drop_all_held_items()
L.visible_message("[src] slams into [L]!", "[src] slams into you!")
diff --git a/code/modules/mob/living/simple_animal/hostile/mushroom.dm b/code/modules/mob/living/simple_animal/hostile/mushroom.dm
index 514edf896b..a5e3cd8120 100644
--- a/code/modules/mob/living/simple_animal/hostile/mushroom.dm
+++ b/code/modules/mob/living/simple_animal/hostile/mushroom.dm
@@ -166,7 +166,9 @@
..()
/mob/living/simple_animal/hostile/mushroom/attack_hand(mob/living/carbon/human/M)
- ..()
+ . = ..()
+ if(.) // the attack was blocked
+ return
if(M.a_intent == INTENT_HARM)
Bruise()
diff --git a/code/modules/mob/living/simple_animal/slime/slime.dm b/code/modules/mob/living/simple_animal/slime/slime.dm
index d1e10ea693..439ea5b2bf 100644
--- a/code/modules/mob/living/simple_animal/slime/slime.dm
+++ b/code/modules/mob/living/simple_animal/slime/slime.dm
@@ -253,33 +253,34 @@
return
/mob/living/simple_animal/slime/attack_slime(mob/living/simple_animal/slime/M)
- if(..()) //successful slime attack
- if(M == src)
- return
- if(buckled)
- Feedstop(silent = TRUE)
- visible_message("[M] pulls [src] off!")
- return
- attacked += 5
- if(nutrition >= 100) //steal some nutrition. negval handled in life()
- nutrition -= (50 + (40 * M.is_adult))
- M.add_nutrition(50 + (40 * M.is_adult))
- if(health > 0)
- M.adjustBruteLoss(-10 + (-10 * M.is_adult))
- M.updatehealth()
+ . = ..()
+ if(!. || M == src) //unsuccessful slime shock
+ return
+ if(buckled)
+ Feedstop(silent = TRUE)
+ visible_message("[M] pulls [src] off!")
+ return
+ attacked += 5
+ if(nutrition >= 100) //steal some nutrition. negval handled in life()
+ nutrition -= (50 + (40 * M.is_adult))
+ M.add_nutrition(50 + (40 * M.is_adult))
+ if(health > 0)
+ M.adjustBruteLoss(-10 + (-10 * M.is_adult))
+ M.updatehealth()
/mob/living/simple_animal/slime/attack_animal(mob/living/simple_animal/M)
. = ..()
if(.)
attacked += 10
-
/mob/living/simple_animal/slime/attack_paw(mob/living/carbon/monkey/M)
- if(..()) //successful monkey bite.
+ . = ..()
+ if(.)//successful monkey bite.
attacked += 10
/mob/living/simple_animal/slime/attack_larva(mob/living/carbon/alien/larva/L)
- if(..()) //successful larva bite.
+ . = ..()
+ if(.) //successful larva bite.
attacked += 10
/mob/living/simple_animal/slime/attack_hulk(mob/living/carbon/human/user, does_attack_animation = 0)
@@ -321,9 +322,11 @@
attacked += 10
/mob/living/simple_animal/slime/attack_alien(mob/living/carbon/alien/humanoid/M)
- if(..()) //if harm or disarm intent.
- attacked += 10
- discipline_slime(M)
+ . = ..()
+ if(!.) // the attack was blocked or was help/grab intent
+ return
+ attacked += 10
+ discipline_slime(M)
/mob/living/simple_animal/slime/attackby(obj/item/W, mob/living/user, params)
diff --git a/code/modules/ninja/suit/n_suit_verbs/ninja_stealth.dm b/code/modules/ninja/suit/n_suit_verbs/ninja_stealth.dm
index 8c304d8a2b..56c50078c1 100644
--- a/code/modules/ninja/suit/n_suit_verbs/ninja_stealth.dm
+++ b/code/modules/ninja/suit/n_suit_verbs/ninja_stealth.dm
@@ -26,10 +26,9 @@ Contents:
/obj/item/clothing/suit/space/space_ninja/proc/enable_signals()
if(!affecting)
return
- RegisterSignal(affecting, list(COMSIG_MOB_ITEM_ATTACK, COMSIG_MOB_ATTACK_RANGED, COMSIG_MOB_ATTACK_HAND, COMSIG_MOB_THROW, COMSIG_PARENT_ATTACKBY, COMSIG_MOVABLE_TELEPORTED, COMSIG_LIVING_GUN_PROCESS_FIRE), .proc/reduce_stealth)
+ RegisterSignal(affecting, list(COMSIG_MOB_ITEM_ATTACK, COMSIG_MOB_ATTACK_RANGED, COMSIG_HUMAN_MELEE_UNARMED_ATTACK, COMSIG_MOB_ATTACK_HAND, COMSIG_MOB_THROW, COMSIG_PARENT_ATTACKBY, COMSIG_MOVABLE_TELEPORTED, COMSIG_LIVING_GUN_PROCESS_FIRE), .proc/reduce_stealth)
RegisterSignal(affecting, COMSIG_MOVABLE_BUMP, .proc/bumping_stealth)
-
/obj/item/clothing/suit/space/space_ninja/proc/reduce_stealth(datum/source)
affecting.alpha = min(affecting.alpha + 40, 100)
@@ -42,7 +41,7 @@ Contents:
return FALSE
stealth = !stealth
stealth_cooldown = world.time + 5 SECONDS
- UnregisterSignal(affecting, list(COMSIG_MOB_ITEM_ATTACK, COMSIG_MOB_ATTACK_RANGED, COMSIG_MOB_ATTACK_HAND, COMSIG_MOB_THROW, COMSIG_PARENT_ATTACKBY, COMSIG_MOVABLE_BUMP, COMSIG_MOVABLE_TELEPORTED, COMSIG_LIVING_GUN_PROCESS_FIRE))
+ UnregisterSignal(affecting, list(COMSIG_MOB_ITEM_ATTACK, COMSIG_MOB_ATTACK_RANGED, COMSIG_HUMAN_MELEE_UNARMED_ATTACK, COMSIG_MOB_ATTACK_HAND, COMSIG_MOB_THROW, COMSIG_PARENT_ATTACKBY, COMSIG_MOVABLE_BUMP, COMSIG_MOVABLE_TELEPORTED, COMSIG_LIVING_GUN_PROCESS_FIRE))
animate(affecting, alpha = 255, time = 3 SECONDS)
affecting.visible_message("[affecting.name] appears from thin air!", \
"You are now visible.")
diff --git a/code/modules/paperwork/paperplane.dm b/code/modules/paperwork/paperplane.dm
index 2ca6ce2611..f3f7e45378 100644
--- a/code/modules/paperwork/paperplane.dm
+++ b/code/modules/paperwork/paperplane.dm
@@ -102,7 +102,7 @@
/obj/item/paperplane/throw_impact(atom/hit_atom)
if(iscarbon(hit_atom))
var/mob/living/carbon/C = hit_atom
- if(C.can_catch_item(TRUE))
+ if(!C.get_active_held_item() && !C.restrained())
var/datum/action/innate/origami/origami_action = locate() in C.actions
if(origami_action?.active) //if they're a master of origami and have the ability turned on, force throwmode on so they'll automatically catch the plane.
C.throw_mode_on()
diff --git a/modular_citadel/code/modules/mob/living/silicon/robot/dogborg_equipment.dm b/modular_citadel/code/modules/mob/living/silicon/robot/dogborg_equipment.dm
index a1466f58d4..98de5eed14 100644
--- a/modular_citadel/code/modules/mob/living/silicon/robot/dogborg_equipment.dm
+++ b/modular_citadel/code/modules/mob/living/silicon/robot/dogborg_equipment.dm
@@ -424,12 +424,7 @@ SLEEPER CODE IS IN game/objects/items/devices/dogborg_sleeper.dm !
if(A)
if(isliving(A))
var/mob/living/L = A
- var/blocked = 0
- if(ishuman(A))
- var/mob/living/carbon/human/H = A
- if(H.check_shields(0, "the [name]", src, attack_type = LEAP_ATTACK))
- blocked = 1
- if(!blocked)
+ if(!L.check_shields(0, "the [name]", src, attack_type = LEAP_ATTACK))
L.visible_message("[src] pounces on [L]!", "[src] pounces on you!")
L.Knockdown(iscarbon(L) ? 60 : 45, override_stamdmg = CLAMP(pounce_stamloss, 0, pounce_stamloss_cap-L.getStaminaLoss())) // Temporary. If someone could rework how dogborg pounces work to accomodate for combat changes, that'd be nice.
playsound(src, 'sound/weapons/Egloves.ogg', 50, 1)