diff --git a/code/__DEFINES/components.dm b/code/__DEFINES/components.dm
index 668d343a6f..56cf681a27 100644
--- a/code/__DEFINES/components.dm
+++ b/code/__DEFINES/components.dm
@@ -47,6 +47,10 @@
#define COMSIG_PARENT_PREQDELETED "parent_preqdeleted" //before a datum's Destroy() is called: (force), returning a nonzero value will cancel the qdel operation
#define COMSIG_PARENT_QDELETING "parent_qdeleting" //just before a datum's Destroy() is called: (force), at this point none of the other components chose to interrupt qdel and Destroy will be called
+/// Trait signals
+#define COMPONENT_ADD_TRAIT (1<<0)
+#define COMPONENT_REMOVE_TRAIT (1<<1)
+
// /atom signals
#define COMSIG_PARENT_ATTACKBY "atom_attackby" //from base of atom/attackby(): (/obj/item, /mob/living, params)
#define COMPONENT_NO_AFTERATTACK 1 //Return this in response if you don't want afterattack to be called
@@ -208,6 +212,16 @@
#define COMSIG_MOB_CLIENT_LOGIN "comsig_mob_client_login" //sent when a mob/login() finishes: (client)
#define COMSIG_LIVING_GUN_PROCESS_FIRE "living_gun_process_fire" //from base of /obj/item/gun/proc/process_fire(): (atom/target, params, zone_override)
+//ALL OF THESE DO NOT TAKE INTO ACCOUNT WHETHER AMOUNT IS 0 OR LOWER AND ARE SENT REGARDLESS!
+#define COMSIG_LIVING_STATUS_STUN "living_stun" //from base of mob/living/Stun() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_KNOCKDOWN "living_knockdown" //from base of mob/living/Knockdown() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_PARALYZE "living_paralyze" //from base of mob/living/Paralyze() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_IMMOBILIZE "living_immobilize" //from base of mob/living/Immobilize() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_UNCONSCIOUS "living_unconscious" //from base of mob/living/Unconscious() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_SLEEP "living_sleeping" //from base of mob/living/Sleeping() (amount, update, ignore)
+#define COMSIG_LIVING_STATUS_DAZE "living_daze" //from base of mob/living/Daze() (amount, update, ignore)
+ #define COMPONENT_NO_STUN 1 //For all of them
+
// /mob/living/carbon signals
#define COMSIG_CARBON_SOUNDBANG "carbon_soundbang" //from base of mob/living/carbon/soundbang_act(): (list(intensity))
diff --git a/code/__DEFINES/flags.dm b/code/__DEFINES/flags.dm
index 957f6edae4..396cf25be1 100644
--- a/code/__DEFINES/flags.dm
+++ b/code/__DEFINES/flags.dm
@@ -92,3 +92,30 @@ GLOBAL_LIST_INIT(bitflags, list(1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 204
// radiation
#define RAD_PROTECT_CONTENTS (1<<0)
#define RAD_NO_CONTAMINATE (1<<1)
+
+//Mob mobility var flags
+/// any flag
+#define CHECK_MOBILITY(target, flags) CHECK_BITFIELD(target.mobility_flags, flags)
+#define CHECK_ALL_MOBILITY(target, flags) CHECK_MULTIPLE_BITFIELDS(target.mobility_flags, flags)
+
+/// can move
+#define MOBILITY_MOVE (1<<0)
+/// can, and is, standing up.
+#define MOBILITY_STAND (1<<1)
+/// can pickup items
+#define MOBILITY_PICKUP (1<<2)
+/// can use items and interact with world objects like opening closets/etc
+#define MOBILITY_USE (1<<3)
+/// can use interfaces like consoles
+#define MOBILITY_UI (1<<4)
+/// can use storage item
+#define MOBILITY_STORAGE (1<<5)
+/// can pull things
+#define MOBILITY_PULL (1<<6)
+/// can hold non-nodropped items voluntarily
+#define MOBILITY_HOLD (1<<7)
+/// Can resist out of buckling, grabs, cuffs, etc, in the usual order (buckle --> cuffs --> grab)
+#define MOBILITY_RESIST (1<<8)
+
+#define MOBILITY_FLAGS_DEFAULT (MOBILITY_MOVE | MOBILITY_STAND | MOBILITY_PICKUP | MOBILITY_USE | MOBILITY_UI | MOBILITY_STORAGE | MOBILITY_PULL | MOBILITY_RESIST)
+#define MOBILITY_FLAGS_ANY_INTERACTION (MOBILITY_USE | MOBILITY_PICKUP | MOBILITY_UI | MOBILITY_STORAGE)
diff --git a/code/__DEFINES/status_effects.dm b/code/__DEFINES/status_effects.dm
index 40d3550d1b..9d09714cc0 100644
--- a/code/__DEFINES/status_effects.dm
+++ b/code/__DEFINES/status_effects.dm
@@ -37,10 +37,17 @@
/////////////
// DEBUFFS //
/////////////
+/// The affected is unable to move, or to use, hold, or pickup items.
+#define STATUS_EFFECT_STUN /datum/status_effect/incapacitating/stun
-#define STATUS_EFFECT_STUN /datum/status_effect/incapacitating/stun //the affected is stunned
+#define STATUS_EFFECT_KNOCKDOWN /datum/status_effect/incapacitating/knockdown //the affected is unable to stand up
-#define STATUS_EFFECT_KNOCKDOWN /datum/status_effect/incapacitating/knockdown //the affected is knocked down
+#define STATUS_EFFECT_IMMOBILIZED /datum/status_effect/incapacitating/immobilized //the affected is unable to move
+
+#define STATUS_EFFECT_PARALYZED /datum/status_effect/incapacitating/paralyzed //the affected is unable to move, use items, or stand up.
+
+/// The affected is unable to use or pickup items
+#define STATUS_EFFECT_DAZED /datum/status_effect/incapacitating/dazed
#define STATUS_EFFECT_UNCONSCIOUS /datum/status_effect/incapacitating/unconscious //the affected is unconscious
diff --git a/code/__DEFINES/traits.dm b/code/__DEFINES/traits.dm
index 91ba57456c..373945d951 100644
--- a/code/__DEFINES/traits.dm
+++ b/code/__DEFINES/traits.dm
@@ -1,3 +1,5 @@
+#define SIGNAL_TRAIT(trait_ref) "trait [trait_ref]"
+
// trait accessor defines
#define ADD_TRAIT(target, trait, source) \
do { \
@@ -6,12 +8,14 @@
target.status_traits = list(); \
_L = target.status_traits; \
_L[trait] = list(source); \
+ SEND_SIGNAL(target, SIGNAL_TRAIT(trait), COMPONENT_ADD_TRAIT); \
} else { \
_L = target.status_traits; \
if (_L[trait]) { \
_L[trait] |= list(source); \
} else { \
_L[trait] = list(source); \
+ SEND_SIGNAL(target, SIGNAL_TRAIT(trait), COMPONENT_ADD_TRAIT); \
} \
} \
} while (0)
@@ -31,7 +35,8 @@
} \
};\
if (!length(_L[trait])) { \
- _L -= trait \
+ _L -= trait; \
+ SEND_SIGNAL(target, SIGNAL_TRAIT(trait), COMPONENT_REMOVE_TRAIT); \
}; \
if (!length(_L)) { \
target.status_traits = null \
@@ -46,7 +51,8 @@
for (var/_T in _L) { \
_L[_T] &= _S;\
if (!length(_L[_T])) { \
- _L -= _T } \
+ _L -= _T ; \
+ SEND_SIGNAL(target, SIGNAL_TRAIT(_T), COMPONENT_REMOVE_TRAIT); } \
};\
if (!length(_L)) { \
target.status_traits = null\
@@ -137,6 +143,19 @@
#define TRAIT_NOMARROW "nomarrow" // You don't make blood, with chemicals or nanites.
#define TRAIT_NOPULSE "nopulse" // Your heart doesn't beat.
#define TRAIT_EXEMPT_HEALTH_EVENTS "exempt-health-events"
+
+// mobility flag traits
+// IN THE FUTURE, IT WOULD BE NICE TO DO SOMETHING SIMILAR TO https://github.com/tgstation/tgstation/pull/48923/files (ofcourse not nearly the same because I have my.. thoughts on it)
+// BUT FOR NOW, THESE ARE HOOKED TO DO update_mobility() VIA COMSIG IN living_mobility.dm
+// SO IF YOU ADD MORE, BESURE TO UPDATE IT THERE.
+
+/// Disallow movement
+#define TRAIT_MOBILITY_NOMOVE "mobility_nomove"
+/// Disallow pickup
+#define TRAIT_MOBILITY_NOPICKUP "mobility_nopickup"
+/// Disallow item use
+#define TRAIT_MOBILITY_NOUSE "mobility_nouse"
+
#define TRAIT_SWIMMING "swimming" //only applied by /datum/element/swimming, for checking
//non-mob traits
diff --git a/code/__HELPERS/mobs.dm b/code/__HELPERS/mobs.dm
index c61c706a85..2da96c7f8b 100644
--- a/code/__HELPERS/mobs.dm
+++ b/code/__HELPERS/mobs.dm
@@ -356,7 +356,7 @@ GLOBAL_LIST_EMPTY(species_list)
checked_health["health"] = health
return ..()
-/proc/do_after(mob/user, var/delay, needhand = 1, atom/target = null, progress = 1, datum/callback/extra_checks = null)
+/proc/do_after(mob/user, var/delay, needhand = 1, atom/target = null, progress = 1, datum/callback/extra_checks = null, required_mobility_flags = (MOBILITY_USE|MOBILITY_MOVE))
if(!user)
return 0
var/atom/Tloc = null
@@ -384,6 +384,7 @@ GLOBAL_LIST_EMPTY(species_list)
var/endtime = world.time + delay
var/starttime = world.time
. = 1
+ var/mob/living/L = isliving(user) && user //evals to last thing eval'd
while (world.time < endtime)
stoplag(1)
if (progress)
@@ -393,15 +394,13 @@ GLOBAL_LIST_EMPTY(species_list)
drifting = 0
Uloc = user.loc
- if(QDELETED(user) || user.stat || user.IsKnockdown() || user.IsStun() || (!drifting && user.loc != Uloc) || (extra_checks && !extra_checks.Invoke()))
+ if(L && !CHECK_ALL_MOBILITY(L, required_mobility_flags))
. = 0
break
- if(isliving(user))
- var/mob/living/L = user
- if(L.recoveringstam)
- . = 0
- break
+ if(QDELETED(user) || user.stat || (!drifting && user.loc != Uloc) || (extra_checks && !extra_checks.Invoke()))
+ . = 0
+ break
if(!QDELETED(Tloc) && (QDELETED(target) || Tloc != target.loc))
if((Uloc != Tloc || Tloc != user) && !drifting)
diff --git a/code/_globalvars/bitfields.dm b/code/_globalvars/bitfields.dm
index a0139dab83..b4cc682075 100644
--- a/code/_globalvars/bitfields.dm
+++ b/code/_globalvars/bitfields.dm
@@ -214,7 +214,7 @@ GLOBAL_LIST_INIT(bitfields, list(
"CAN_MASTURBATE_WITH" = CAN_MASTURBATE_WITH,
"MASTURBATE_LINKED_ORGAN" = MASTURBATE_LINKED_ORGAN,
"CAN_CLIMAX_WITH" = CAN_CLIMAX_WITH
-
+
),
"mob_biotypes" = list (
"MOB_ORGANIC" = MOB_ORGANIC,
@@ -227,5 +227,16 @@ GLOBAL_LIST_INIT(bitfields, list(
"MOB_EPIC" = MOB_EPIC,
"MOB_REPTILE" = MOB_REPTILE,
"MOB_SPIRIT" = MOB_SPIRIT
+ ),
+ "mobility_flags" = list(
+ "MOBILITY_MOVE" = MOBILITY_MOVE,
+ "MOBILITY_STAND" = MOBILITY_STAND,
+ "MOBILITY_PICKUP" = MOBILITY_PICKUP,
+ "MOBILITY_USE" = MOBILITY_USE,
+ "MOBILITY_UI" = MOBILITY_UI,
+ "MOBILITY_STORAGE" = MOBILITY_STORAGE,
+ "MOBILITY_PULL" = MOBILITY_PULL,
+ "MOBILITY_HOLD" = MOBILITY_HOLD,
+ "MOBILITY_RESIST" = MOBILITY_RESIST
)
))
diff --git a/code/_onclick/cyborg.dm b/code/_onclick/cyborg.dm
index 6e3cfea424..9fcccedf1a 100644
--- a/code/_onclick/cyborg.dm
+++ b/code/_onclick/cyborg.dm
@@ -14,7 +14,7 @@
if(check_click_intercept(params,A))
return
- if(stat || lockcharge || IsKnockdown() || IsStun() || IsUnconscious())
+ if(stat || locked_down || IsParalyzed() || IsStun() || IsUnconscious())
return
var/list/modifiers = params2list(params)
@@ -66,7 +66,7 @@
if(C.user_unbuckle_mob(C.buckled_mobs[1],src))
return
- if(!W && get_dist(src,A) <= interaction_range)
+ if(!W && (get_dist(src,A) <= interaction_range))
A.attack_robot(src)
return
diff --git a/code/_onclick/hud/alert.dm b/code/_onclick/hud/alert.dm
index c42956bbaa..bdc6ea2980 100644
--- a/code/_onclick/hud/alert.dm
+++ b/code/_onclick/hud/alert.dm
@@ -273,7 +273,7 @@ or shoot a gun to move around via Newton's 3rd Law of Motion."
if(!istype(L) || !L.can_resist())
return
L.changeNext_move(CLICK_CD_RESIST)
- if(L.canmove)
+ if(CHECK_MOBILITY(L, MOBILITY_MOVE))
return L.resist_fire() //I just want to start a flame in your hearrrrrrtttttt.
@@ -601,7 +601,7 @@ so as to remain in compliance with the most up-to-date laws."
if(!istype(L) || !L.can_resist())
return
L.changeNext_move(CLICK_CD_RESIST)
- if((L.canmove) && (L.last_special <= world.time))
+ if(CHECK_MOBILITY(L, MOBILITY_MOVE) && (L.last_special <= world.time))
return L.resist_restraints()
/obj/screen/alert/restrained/buckled/Click()
diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm
index 9ba51afc69..cba53eb4a5 100644
--- a/code/_onclick/item_attack.dm
+++ b/code/_onclick/item_attack.dm
@@ -113,7 +113,7 @@
var/mob/living/carbon/tempcarb = user
if(!tempcarb.combatmode)
totitemdamage *= 0.5
- if(user.resting)
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND))
totitemdamage *= 0.5
//CIT CHANGES END HERE
if(user != src && check_shields(I, totitemdamage, "the [I.name]", MELEE_ATTACK, I.armour_penetration))
diff --git a/code/datums/action.dm b/code/datums/action.dm
index 264b2a56e4..f1df2a80d8 100644
--- a/code/datums/action.dm
+++ b/code/datums/action.dm
@@ -8,6 +8,7 @@
var/desc = null
var/obj/target = null
var/check_flags = 0
+ var/required_mobility_flags = MOBILITY_USE
var/processing = FALSE
var/obj/screen/movable/action_button/button = null
var/buttontooltipstyle = ""
@@ -96,20 +97,23 @@
/datum/action/proc/IsAvailable()
if(!owner)
- return 0
+ return FALSE
+ var/mob/living/L = owner
+ if(istype(L) && !CHECK_ALL_MOBILITY(L, required_mobility_flags))
+ return FALSE
if(check_flags & AB_CHECK_RESTRAINED)
if(owner.restrained())
- return 0
+ return FALSE
if(check_flags & AB_CHECK_STUN)
- if(owner.IsKnockdown() || owner.IsStun())
- return 0
+ if(istype(L) && !CHECK_MOBILITY(L, MOBILITY_USE))
+ return FALSE
if(check_flags & AB_CHECK_LYING)
- if(owner.lying)
- return 0
+ if(istype(L) && !CHECK_MOBILITY(L, MOBILITY_STAND))
+ return FALSE
if(check_flags & AB_CHECK_CONSCIOUS)
if(owner.stat)
- return 0
- return 1
+ return FALSE
+ return TRUE
/datum/action/proc/UpdateButtonIcon(status_only = FALSE, force = FALSE)
if(button)
@@ -430,7 +434,8 @@
name = "Shift Nerves"
/datum/action/item_action/explosive_implant
- check_flags = 0
+ check_flags = NONE
+ required_mobility_flags = NONE
name = "Activate Explosive Implant"
/datum/action/item_action/toggle_research_scanner
diff --git a/code/datums/brain_damage/mild.dm b/code/datums/brain_damage/mild.dm
index d653671b5a..6d3eedee1d 100644
--- a/code/datums/brain_damage/mild.dm
+++ b/code/datums/brain_damage/mild.dm
@@ -136,7 +136,7 @@
fall_chance += 2
if(prob(fall_chance) && !owner.lying && !owner.buckled)
to_chat(owner, "Your leg gives out!")
- owner.Knockdown(35)
+ owner.DefaultCombatKnockdown(35)
else if(owner.get_active_held_item())
var/drop_chance = 1
diff --git a/code/datums/brain_damage/special.dm b/code/datums/brain_damage/special.dm
index b52c7d391c..bc1f566f23 100644
--- a/code/datums/brain_damage/special.dm
+++ b/code/datums/brain_damage/special.dm
@@ -13,7 +13,7 @@
/datum/brain_trauma/special/godwoken/on_life()
..()
if(prob(4))
- if(prob(33) && (owner.IsStun() || owner.IsKnockdown() || owner.IsUnconscious()))
+ if(prob(33) && owner.HighestImmobilityAmount())
speak("unstun", TRUE)
else if(prob(60) && owner.health <= owner.crit_threshold)
speak("heal", TRUE)
diff --git a/code/datums/components/caltrop.dm b/code/datums/components/caltrop.dm
index f0333072a8..863d55ccab 100644
--- a/code/datums/components/caltrop.dm
+++ b/code/datums/components/caltrop.dm
@@ -59,4 +59,4 @@
"You slide on [A]!")
cooldown = world.time
- H.Knockdown(60)
+ H.DefaultCombatKnockdown(60)
diff --git a/code/datums/components/chasm.dm b/code/datums/components/chasm.dm
index bc185994f6..c792cb4be9 100644
--- a/code/datums/components/chasm.dm
+++ b/code/datums/components/chasm.dm
@@ -100,7 +100,7 @@
AM.forceMove(T)
if(isliving(AM))
var/mob/living/L = AM
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
L.adjustBruteLoss(30)
falling_atoms -= AM
@@ -110,8 +110,7 @@
if (isliving(AM))
var/mob/living/L = AM
L.notransform = TRUE
- L.Stun(200)
- L.resting = TRUE
+ L.Paralyze(200)
var/oldtransform = AM.transform
var/oldcolor = AM.color
diff --git a/code/datums/components/footstep.dm b/code/datums/components/footstep.dm
index c4e65ea120..fbf559fe35 100644
--- a/code/datums/components/footstep.dm
+++ b/code/datums/components/footstep.dm
@@ -18,7 +18,7 @@
var/mob/living/LM = parent
var/v = volume
var/e = e_range
- if(!T.footstep || LM.buckled || LM.lying || !LM.canmove || LM.resting || LM.buckled || LM.throwing || LM.movement_type & (VENTCRAWLING | FLYING))
+ if(!T.footstep || LM.buckled || !CHECK_MOBILITY(LM, MOBILITY_STAND) || LM.buckled || LM.throwing || (LM.movement_type & (VENTCRAWLING | FLYING)))
if (LM.lying && !LM.buckled && !(!T.footstep || LM.movement_type & (VENTCRAWLING | FLYING))) //play crawling sound if we're lying
playsound(T, 'sound/effects/footstep/crawl1.ogg', 15 * v)
return
diff --git a/code/datums/components/jousting.dm b/code/datums/components/jousting.dm
index da2ff1b177..2a865d6658 100644
--- a/code/datums/components/jousting.dm
+++ b/code/datums/components/jousting.dm
@@ -54,7 +54,7 @@
msg += " and knocks [target] [target_buckled? "off of [target.buckled]" : "down"]"
if(target_buckled)
target.buckled.unbuckle_mob(target)
- target.Knockdown(knockdown_time)
+ target.DefaultCombatKnockdown(knockdown_time)
if(length(msg))
user.visible_message("[msg]!")
diff --git a/code/datums/components/riding.dm b/code/datums/components/riding.dm
index 0775a725b9..750120976f 100644
--- a/code/datums/components/riding.dm
+++ b/code/datums/components/riding.dm
@@ -240,7 +240,7 @@
/datum/component/riding/human/force_dismount(mob/living/user)
var/atom/movable/AM = parent
AM.unbuckle_mob(user)
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
user.visible_message("[AM] pushes [user] off of [AM.p_them()]!")
/datum/component/riding/cyborg
@@ -298,7 +298,7 @@
M.Move(targetm)
M.visible_message("[M] is thrown clear of [AM]!")
M.throw_at(target, 14, 5, AM)
- M.Knockdown(60)
+ M.DefaultCombatKnockdown(60)
/datum/component/riding/proc/equip_buckle_inhands(mob/living/carbon/human/user, amount_required = 1, mob/living/riding_target_override)
var/list/equipped
diff --git a/code/datums/components/spooky.dm b/code/datums/components/spooky.dm
index 1d5549d0fe..b74f71aaa5 100644
--- a/code/datums/components/spooky.dm
+++ b/code/datums/components/spooky.dm
@@ -22,7 +22,7 @@
return //undeads are unaffected by the spook-pocalypse.
if(istype(H.dna.species, /datum/species/zombie))
H.adjustStaminaLoss(25)
- H.Knockdown(15) //zombies can't resist the doot
+ H.DefaultCombatKnockdown(15) //zombies can't resist the doot
C.Jitter(35)
C.stuttering = 20
if((!istype(H.dna.species, /datum/species/skeleton)) && (!istype(H.dna.species, /datum/species/golem)) && (!istype(H.dna.species, /datum/species/android)) && (!istype(H.dna.species, /datum/species/jelly)))
@@ -36,7 +36,7 @@
/datum/component/spooky/proc/spectral_change(mob/living/carbon/human/H, mob/user)
if((H.getStaminaLoss() > 95) && (!istype(H.dna.species, /datum/species/skeleton)) && (!istype(H.dna.species, /datum/species/golem)) && (!istype(H.dna.species, /datum/species/android)) && (!istype(H.dna.species, /datum/species/jelly)))
- H.Knockdown(20)
+ H.DefaultCombatKnockdown(20)
H.set_species(/datum/species/skeleton)
H.visible_message("[H] has given up on life as a mortal.")
var/T = get_turf(H)
diff --git a/code/datums/components/storage/concrete/bag_of_holding.dm b/code/datums/components/storage/concrete/bag_of_holding.dm
index 8b9ecf5a4e..28b06b4867 100644
--- a/code/datums/components/storage/concrete/bag_of_holding.dm
+++ b/code/datums/components/storage/concrete/bag_of_holding.dm
@@ -11,7 +11,7 @@
var/turf/loccheck = get_turf(A)
if(is_reebe(loccheck.z))
user.visible_message("An unseen force knocks [user] to the ground!", "\"I think not!\"")
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
return
if(istype(loccheck.loc, /area/fabric_of_reality))
to_chat(user, "You can't do that here!")
@@ -25,7 +25,7 @@
for(var/mob/living/M in T)
if(M.movement_type & FLYING)
M.visible_message("The bluespace collapse crushes the air towards it, pulling [M] towards the ground...")
- M.Knockdown(5, TRUE, TRUE) //Overrides stun absorbs.
+ M.DefaultCombatKnockdown(5, TRUE, TRUE) //Overrides stun absorbs.
T.TerraformTurf(/turf/open/chasm/magic, /turf/open/chasm/magic)
for (var/obj/structure/ladder/unbreakable/binary/ladder in GLOB.ladders)
ladder.ActivateAlmonds()
diff --git a/code/datums/diseases/advance/symptoms/heal.dm b/code/datums/diseases/advance/symptoms/heal.dm
index c7b9758bcb..84d652b77d 100644
--- a/code/datums/diseases/advance/symptoms/heal.dm
+++ b/code/datums/diseases/advance/symptoms/heal.dm
@@ -279,7 +279,7 @@
M.emote("deathgasp")
M.fakedeath("regenerative_coma")
M.update_stat()
- M.update_canmove()
+ M.update_mobility()
addtimer(CALLBACK(src, .proc/uncoma, M), 300)
/datum/symptom/heal/coma/proc/uncoma(mob/living/M)
@@ -288,7 +288,7 @@
active_coma = FALSE
M.cure_fakedeath("regenerative_coma")
M.update_stat()
- M.update_canmove()
+ M.update_mobility()
/datum/symptom/heal/coma/Heal(mob/living/carbon/M, datum/disease/advance/A, actual_power)
var/heal_amt = 4 * actual_power
diff --git a/code/datums/diseases/heart_failure.dm b/code/datums/diseases/heart_failure.dm
index 196cd95f69..5eda0e928f 100644
--- a/code/datums/diseases/heart_failure.dm
+++ b/code/datums/diseases/heart_failure.dm
@@ -44,7 +44,7 @@
if(prob(25))
affected_mob.vomit(95)
H.emote("cough")
- H.Knockdown(40)
+ H.DefaultCombatKnockdown(40)
H.losebreath += 4
if(prob(3))
to_chat(H, "You feel very weak and dizzy...")
diff --git a/code/datums/emotes.dm b/code/datums/emotes.dm
index e653e3e36b..6660bafcaf 100644
--- a/code/datums/emotes.dm
+++ b/code/datums/emotes.dm
@@ -118,7 +118,8 @@
if(DEAD)
to_chat(user, "You cannot [key] while dead.")
return FALSE
- if(restraint_check && (user.IsStun() || user.IsKnockdown()))
+ var/mob/living/L = user
+ if(restraint_check && (istype(L) && !CHECK_MOBILITY(L, MOBILITY_USE)))
if(!intentional)
return FALSE
to_chat(user, "You cannot [key] while stunned.")
diff --git a/code/datums/martial/cqc.dm b/code/datums/martial/cqc.dm
index 4ec16ac18c..96f0caf82c 100644
--- a/code/datums/martial/cqc.dm
+++ b/code/datums/martial/cqc.dm
@@ -42,19 +42,19 @@
/datum/martial_art/cqc/proc/Slam(mob/living/carbon/human/A, mob/living/carbon/human/D)
if(!can_use(A))
return FALSE
- if(!D.stat || !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
D.visible_message("[A] slams [D] into the ground!", \
"[A] slams you into the ground!")
playsound(get_turf(A), 'sound/weapons/slam.ogg', 50, 1, -1)
D.apply_damage(10, BRUTE)
- D.Knockdown(120)
+ D.DefaultCombatKnockdown(120)
log_combat(A, D, "slammed (CQC)")
return TRUE
/datum/martial_art/cqc/proc/Kick(mob/living/carbon/human/A, mob/living/carbon/human/D)
if(!can_use(A))
return FALSE
- if(!D.stat || !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
D.visible_message("[A] kicks [D] back!", \
"[A] kicks you back!")
playsound(get_turf(A), 'sound/weapons/cqchit1.ogg', 50, 1, -1)
@@ -62,7 +62,7 @@
D.throw_at(throw_target, 1, 14, A)
D.apply_damage(10, BRUTE)
log_combat(A, D, "kicked (CQC)")
- if(D.IsKnockdown() && !D.stat)
+ if(!CHECK_MOBILITY(D, MOBILITY_STAND) && CHECK_MOBILITY(D, MOBILITY_USE))
log_combat(A, D, "knocked out (Head kick)(CQC)")
D.visible_message("[A] kicks [D]'s head, knocking [D.p_them()] out!", \
"[A] kicks your head, knocking you out!")
@@ -136,7 +136,7 @@
A.do_attack_animation(D)
var/picked_hit_type = pick("CQC'd", "Big Bossed")
var/bonus_damage = 13
- if(D.IsKnockdown() || D.resting || D.lying)
+ if(!CHECK_MOBILITY(D, MOBILITY_STAND))
bonus_damage += 5
picked_hit_type = "stomps on"
D.apply_damage(bonus_damage, BRUTE)
@@ -147,12 +147,12 @@
D.visible_message("[A] [picked_hit_type] [D]!", \
"[A] [picked_hit_type] you!")
log_combat(A, D, "[picked_hit_type] (CQC)")
- if(A.resting && !D.stat && !D.IsKnockdown())
+ if(!CHECK_MOBILITY(A, MOBILITY_STAND) && !D.stat && CHECK_MOBILITY(D, MOBILITY_STAND))
D.visible_message("[A] leg sweeps [D]!", \
"[A] leg sweeps you!")
playsound(get_turf(A), 'sound/effects/hit_kick.ogg', 50, 1, -1)
D.apply_damage(10, BRUTE)
- D.Knockdown(60)
+ D.DefaultCombatKnockdown(60)
log_combat(A, D, "sweeped (CQC)")
return TRUE
@@ -164,7 +164,7 @@
if(check_streak(A,D))
return TRUE
if(prob(65))
- if(!D.stat || !D.IsKnockdown() || !restraining)
+ if(CHECK_MOBILITY(D, MOBILITY_MOVE) || !restraining)
I = D.get_active_held_item()
D.visible_message("[A] strikes [D]'s jaw with their hand!", \
"[A] strikes your jaw, disorienting you!")
diff --git a/code/datums/martial/krav_maga.dm b/code/datums/martial/krav_maga.dm
index 4e8dacaef9..1a244f911e 100644
--- a/code/datums/martial/krav_maga.dm
+++ b/code/datums/martial/krav_maga.dm
@@ -96,13 +96,13 @@
return 0
/datum/martial_art/krav_maga/proc/leg_sweep(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(D.lying || D.IsKnockdown())
+ if(!CHECK_MOBILITY(D, MOBILITY_STAND))
return 0
D.visible_message("[A] leg sweeps [D]!", \
"[A] leg sweeps you!")
playsound(get_turf(A), 'sound/effects/hit_kick.ogg', 50, 1, -1)
D.apply_damage(5, BRUTE)
- D.Knockdown(40, override_hardstun = 0.01, override_stamdmg = 25)
+ D.DefaultCombatKnockdown(40, override_hardstun = 0.01, override_stamdmg = 25)
log_combat(A, D, "leg sweeped")
return 1
@@ -138,7 +138,7 @@
log_combat(A, D, "punched")
var/picked_hit_type = pick("punches", "kicks")
var/bonus_damage = 10
- if(D.IsKnockdown() || D.resting || D.lying)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
bonus_damage += 5
picked_hit_type = "stomps on"
D.apply_damage(bonus_damage, BRUTE)
diff --git a/code/datums/martial/mushpunch.dm b/code/datums/martial/mushpunch.dm
index 1ef7734771..fe9f0d77d6 100644
--- a/code/datums/martial/mushpunch.dm
+++ b/code/datums/martial/mushpunch.dm
@@ -16,7 +16,7 @@
playsound(D, 'sound/effects/meteorimpact.ogg', 25, 1, -1)
var/throwtarget = get_edge_target_turf(A, get_dir(A, get_step_away(D, A)))
D.throw_at(throwtarget, 4, 2, A)//So stuff gets tossed around at the same time.
- D.Knockdown(20)
+ D.DefaultCombatKnockdown(20)
if(atk_verb)
log_combat(A, D, "[atk_verb] (Mushroom Punch)")
return TRUE
diff --git a/code/datums/martial/psychotic_brawl.dm b/code/datums/martial/psychotic_brawl.dm
index f0ad7aedfd..7609157ae1 100644
--- a/code/datums/martial/psychotic_brawl.dm
+++ b/code/datums/martial/psychotic_brawl.dm
@@ -49,7 +49,7 @@
if(!istype(D.head,/obj/item/clothing/head/helmet/) && !istype(D.head,/obj/item/clothing/head/hardhat))
D.adjustOrganLoss(ORGAN_SLOT_BRAIN, 5)
A.Stun(rand(10,45))
- D.Knockdown(rand(5,30))//CIT CHANGE - makes stuns from martial arts always use Knockdown instead of Stun for the sake of consistency
+ D.DefaultCombatKnockdown(rand(5,30))//CIT CHANGE - makes stuns from martial arts always use Knockdown instead of Stun for the sake of consistency
if(5,6)
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
atk_verb = pick("punches", "kicks", "hits", "slams into")
@@ -59,7 +59,7 @@
playsound(get_turf(D), 'sound/effects/meteorimpact.ogg', 25, 1, -1)
var/throwtarget = get_edge_target_turf(A, get_dir(A, get_step_away(D, A)))
D.throw_at(throwtarget, 4, 2, A)//So stuff gets tossed around at the same time.
- D.Knockdown(60)
+ D.DefaultCombatKnockdown(60)
if(7,8)
basic_hit(A,D)
diff --git a/code/datums/martial/rising_bass.dm b/code/datums/martial/rising_bass.dm
index fd7b580470..22605e5624 100644
--- a/code/datums/martial/rising_bass.dm
+++ b/code/datums/martial/rising_bass.dm
@@ -79,7 +79,7 @@
return TRUE
/datum/martial_art/the_rising_bass/proc/sideKick(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.IsKnockdown() || D.lying == 0)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
var/dir = A.dir & (NORTH | SOUTH) ? pick(EAST, WEST) : pick(NORTH, SOUTH)
var/oppdir = dir == NORTH ? SOUTH : dir == SOUTH ? NORTH : dir == EAST ? WEST : EAST
var/turf/H = get_step(D, dir)
@@ -89,7 +89,7 @@
"[A] kicks you in the side, forcing you to step away!")
playsound(get_turf(A), 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
D.apply_damage(5, BRUTE, BODY_ZONE_CHEST)
- D.Knockdown(60)
+ D.DefaultCombatKnockdown(60)
var/L = !checkfordensity(H,D) ? (!checkfordensity(K,D) ? D.loc : K) : H
D.forceMove(L)
log_combat(A, D, "side kicked (Rising Bass)")
@@ -97,7 +97,7 @@
return basic_hit(A,D)
/datum/martial_art/the_rising_bass/proc/shoulderFlip(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.IsKnockdown() || !D.lying)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
var/turf/H = get_step(A, get_dir(D,A))
var/L = checkfordensity(H,D) ? H : A.loc
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
@@ -108,14 +108,14 @@
D.apply_damage(10, BRUTE, BODY_ZONE_CHEST)
D.apply_damage(30, BRUTE, BODY_ZONE_HEAD)
D.Sleeping(60)
- D.Knockdown(300)
+ D.DefaultCombatKnockdown(300)
D.forceMove(L)
log_combat(A, D, "shoulder flipped (Rising Bass)")
return TRUE
return basic_hit(A,D)
/datum/martial_art/the_rising_bass/proc/repulsePunch(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if((!D.IsKnockdown() || !D.lying) && repulsecool > world.time)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND) && repulsecool < world.time)
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
D.visible_message("[A] smashes [D] in the chest, throwing them away!", \
"[A] smashes you in the chest, repelling you away!")
@@ -123,14 +123,14 @@
var/atom/F = get_edge_target_turf(D, get_dir(A, get_step_away(D, A)))
D.throw_at(F, 10, 1)
D.apply_damage(10, BRUTE, BODY_ZONE_CHEST)
- D.Knockdown(90)
+ D.DefaultCombatKnockdown(90)
log_combat(A, D, "repulse punched (Rising Bass)")
repulsecool = world.time + 3 SECONDS
return TRUE
return basic_hit(A,D)
/datum/martial_art/the_rising_bass/proc/footSmash(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.IsKnockdown() || !D.lying)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
A.do_attack_animation(D, ATTACK_EFFECT_KICK)
D.visible_message("[A] smashes their foot down on [D]'s foot!", \
"[A] smashes your foot!")
@@ -142,7 +142,7 @@
return basic_hit(A,D)
/datum/martial_art/the_rising_bass/proc/deftSwitch(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.IsKnockdown() || !D.lying)
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
if (D.get_active_held_item())
var/obj/item/G = D.get_active_held_item()
if (G && !(G.item_flags & (ABSTRACT|DROPDEL)) && D.temporarilyRemoveItemFromInventory(G))
@@ -205,4 +205,4 @@
deftswitch.Remove(H)
sidekick.Remove(H)
REMOVE_TRAIT(H, TRAIT_NOGUNS, RISING_BASS_TRAIT)
- REMOVE_TRAIT(H, TRAIT_AUTO_CATCH_ITEM, RISING_BASS_TRAIT)
\ No newline at end of file
+ REMOVE_TRAIT(H, TRAIT_AUTO_CATCH_ITEM, RISING_BASS_TRAIT)
diff --git a/code/datums/martial/sleeping_carp.dm b/code/datums/martial/sleeping_carp.dm
index 85f8a4a101..9aab8b7c47 100644
--- a/code/datums/martial/sleeping_carp.dm
+++ b/code/datums/martial/sleeping_carp.dm
@@ -37,7 +37,7 @@
return FALSE
/datum/martial_art/the_sleeping_carp/proc/wristWrench(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.stat && !D.IsStun() && !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_USE))
log_combat(A, D, "wrist wrenched (Sleeping Carp)")
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
D.visible_message("[A] grabs [D]'s wrist and wrenches it sideways!", \
@@ -46,19 +46,19 @@
D.emote("scream")
D.dropItemToGround(D.get_active_held_item())
D.apply_damage(5, BRUTE, pick(BODY_ZONE_L_ARM, BODY_ZONE_R_ARM))
- D.Knockdown(60)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
+ D.DefaultCombatKnockdown(60)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
return TRUE
return basic_hit(A,D)
/datum/martial_art/the_sleeping_carp/proc/backKick(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.stat && !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
if(A.dir == D.dir)
log_combat(A, D, "back-kicked (Sleeping Carp)")
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
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)
- D.Knockdown(80)
+ D.DefaultCombatKnockdown(80)
playsound(get_turf(D), 'sound/weapons/punch1.ogg', 50, 1, -1)
return TRUE
else
@@ -68,20 +68,20 @@
return basic_hit(A,D)
/datum/martial_art/the_sleeping_carp/proc/kneeStomach(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.stat && !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
log_combat(A, D, "stomach kneed (Sleeping Carp)")
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!")
D.losebreath += 3
- D.Knockdown(40)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
+ D.DefaultCombatKnockdown(40)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
playsound(get_turf(D), 'sound/weapons/punch1.ogg', 50, 1, -1)
return TRUE
return basic_hit(A,D)
/datum/martial_art/the_sleeping_carp/proc/headKick(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(!D.stat && !D.IsKnockdown())
+ if(CHECK_MOBILITY(D, MOBILITY_STAND))
log_combat(A, D, "head kicked (Sleeping Carp)")
A.do_attack_animation(D, ATTACK_EFFECT_KICK)
D.visible_message("[A] kicks [D] in the head!", \
@@ -89,12 +89,12 @@
D.apply_damage(20, BRUTE, BODY_ZONE_HEAD)
D.drop_all_held_items()
playsound(get_turf(D), 'sound/weapons/punch1.ogg', 50, 1, -1)
- D.Knockdown(80)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
+ D.DefaultCombatKnockdown(80)//CIT CHANGE - makes sleepingcarp use knockdown() for its stuns instead of stun()
return TRUE
return basic_hit(A,D)
/datum/martial_art/the_sleeping_carp/proc/elbowDrop(mob/living/carbon/human/A, mob/living/carbon/human/D)
- if(D.IsKnockdown() || D.resting || D.stat)
+ if(!CHECK_MOBILITY(D, MOBILITY_STAND))
log_combat(A, D, "elbow dropped (Sleeping Carp)")
A.do_attack_animation(D, ATTACK_EFFECT_PUNCH)
D.visible_message("[A] elbow drops [D]!", \
@@ -134,7 +134,7 @@
playsound(get_turf(D), 'sound/weapons/punch1.ogg', 25, 1, -1)
if(prob(D.getBruteLoss()) && !D.lying)
D.visible_message("[D] stumbles and falls!", "The blow sends you to the ground!")
- D.Knockdown(80)
+ D.DefaultCombatKnockdown(80)
log_combat(A, D, "[atk_verb] (Sleeping Carp)")
return TRUE
@@ -192,7 +192,7 @@
add_fingerprint(user)
if((HAS_TRAIT(user, TRAIT_CLUMSY)) && prob(50))
to_chat(user, "You club yourself over the head with [src].")
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
if(ishuman(user))
var/mob/living/carbon/human/H = user
H.apply_damage(2*force, BRUTE, BODY_ZONE_HEAD)
@@ -226,7 +226,7 @@
if(prob(10))
H.visible_message("[H] collapses!", \
"Your legs give out!")
- H.Knockdown(80)
+ H.DefaultCombatKnockdown(80)
if(H.staminaloss && !H.IsSleeping())
var/total_health = (H.health - H.staminaloss)
if(total_health <= HEALTH_THRESHOLD_CRIT && !H.stat)
diff --git a/code/datums/martial/wrestling.dm b/code/datums/martial/wrestling.dm
index c967779d03..6ed2245dfd 100644
--- a/code/datums/martial/wrestling.dm
+++ b/code/datums/martial/wrestling.dm
@@ -207,7 +207,7 @@
if (T && isturf(T))
if (!D.stat)
D.emote("scream")
- D.throw_at(T, 10, 4, A, TRUE, TRUE, callback = CALLBACK(D, /mob/living/carbon/human.proc/Knockdown, 20))
+ D.throw_at(T, 10, 4, A, TRUE, TRUE, callback = CALLBACK(D, /mob/living/carbon/human.proc/DefaultCombatKnockdown, 20))
log_combat(A, D, "has thrown with wrestling")
return 0
@@ -303,7 +303,7 @@
playsound(A.loc, "swing_hit", 50, 1)
if (!D.stat)
D.emote("scream")
- D.Knockdown(40)
+ D.DefaultCombatKnockdown(40)
switch(rand(1,3))
if (2)
@@ -361,7 +361,7 @@
var/turf/T = get_edge_target_turf(A, get_dir(A, get_step_away(D, A)))
if (T && isturf(T))
- D.Knockdown(20)
+ D.DefaultCombatKnockdown(20)
D.throw_at(T, 3, 2)
log_combat(A, D, "roundhouse-kicked")
@@ -400,7 +400,7 @@
if (falling == 1)
A.visible_message("...and dives head-first into the ground, ouch!")
A.adjustBruteLoss(rand(10,20))
- A.Knockdown(60)
+ A.DefaultCombatKnockdown(60)
to_chat(A, "[D] is too far away!")
return 0
@@ -429,7 +429,7 @@
else
D.adjustBruteLoss(rand(20,30))
- D.Knockdown(40)
+ D.DefaultCombatKnockdown(40)
A.pixel_y = 0
diff --git a/code/datums/status_effects/buffs.dm b/code/datums/status_effects/buffs.dm
index 5dab98d5ca..43afcdd807 100644
--- a/code/datums/status_effects/buffs.dm
+++ b/code/datums/status_effects/buffs.dm
@@ -73,8 +73,7 @@
owner.log_message("gained Vanguard stun immunity", LOG_ATTACK)
owner.add_stun_absorption("vanguard", INFINITY, 1, "'s yellow aura momentarily intensifies!", "Your ward absorbs the stun!", " radiating with a soft yellow light!")
owner.visible_message("[owner] begins to faintly glow!", "You will absorb all stuns for the next twenty seconds.")
- owner.SetStun(0, FALSE)
- owner.SetKnockdown(0)
+ owner.SetAllImmobility(0, FALSE)
owner.setStaminaLoss(0, FALSE)
progbar = new(owner, duration, owner)
progbar.bar.color = list("#FAE48C", "#FAE48C", "#FAE48C", rgb(0,0,0))
@@ -97,7 +96,7 @@
if(owner.stun_absorption[i]["end_time"] > world.time && owner.stun_absorption[i]["priority"] > vanguard["priority"])
otheractiveabsorptions = TRUE
if(!GLOB.ratvar_awakens && stuns_blocked && !otheractiveabsorptions)
- owner.Knockdown(stuns_blocked)
+ owner.DefaultCombatKnockdown(stuns_blocked)
message_to_owner = "The weight of the Vanguard's protection crashes down upon you!"
if(stuns_blocked >= 300)
message_to_owner += "\nYou faint from the exertion!"
@@ -226,9 +225,8 @@
return ..()
/datum/status_effect/wish_granters_gift/on_remove()
- owner.revive(full_heal = 1, admin_revive = 1)
+ owner.revive(full_heal = TRUE, admin_revive = TRUE)
owner.visible_message("[owner] appears to wake from the dead, having healed all wounds!", "You have regenerated.")
- owner.update_canmove()
/obj/screen/alert/status_effect/wish_granters_gift
name = "Wish Granter's Immortality"
diff --git a/code/datums/status_effects/debuffs.dm b/code/datums/status_effects/debuffs.dm
index 5058dd0221..d04cf3939f 100644
--- a/code/datums/status_effects/debuffs.dm
+++ b/code/datums/status_effects/debuffs.dm
@@ -12,12 +12,12 @@
. = ..()
if(.)
if(updating_canmove)
- owner.update_canmove()
+ owner.update_mobility()
if(needs_update_stat || issilicon(owner))
owner.update_stat()
/datum/status_effect/incapacitating/on_remove()
- owner.update_canmove()
+ owner.update_mobility()
if(needs_update_stat || issilicon(owner)) //silicons need stat updates in addition to normal canmove updates
owner.update_stat()
@@ -29,10 +29,22 @@
/datum/status_effect/incapacitating/knockdown
id = "knockdown"
-/datum/status_effect/incapacitating/knockdown/tick()
+//IMMOBILIZED
+/datum/status_effect/incapacitating/immobilized
+ id = "immobilized"
+
+//PARALYZED
+/datum/status_effect/incapacitating/paralyzed
+ id = "paralyzed"
+
+/datum/status_effect/incapacitating/paralyzed/tick()
if(owner.getStaminaLoss())
owner.adjustStaminaLoss(-0.3) //reduce stamina loss by 0.3 per tick, 6 per 2 seconds
+//DAZED
+/datum/status_effect/incapacitating/dazed
+ id = "dazed"
+
//UNCONSCIOUS
/datum/status_effect/incapacitating/unconscious
id = "unconscious"
@@ -211,7 +223,7 @@
if(iscarbon(owner) && !is_servant_of_ratvar(owner) && !owner.anti_magic_check(chargecost = 0) && number_legs)
if(force_damage || owner.m_intent != MOVE_INTENT_WALK)
if(GLOB.ratvar_awakens)
- owner.Knockdown(20)
+ owner.DefaultCombatKnockdown(20)
if(iscultist(owner))
owner.apply_damage(cultist_damage_on_toggle * 0.5, BURN, BODY_ZONE_L_LEG)
owner.apply_damage(cultist_damage_on_toggle * 0.5, BURN, BODY_ZONE_R_LEG)
@@ -558,7 +570,7 @@
var/old_oxyloss
/datum/status_effect/kindle/tick()
- owner.Knockdown(15, TRUE, FALSE, 15)
+ owner.DefaultCombatKnockdown(15, TRUE, FALSE, 15)
if(iscarbon(owner))
var/mob/living/carbon/C = owner
C.silent = max(2, C.silent)
diff --git a/code/datums/status_effects/gas.dm b/code/datums/status_effects/gas.dm
index 0041799314..608dbb2d7a 100644
--- a/code/datums/status_effects/gas.dm
+++ b/code/datums/status_effects/gas.dm
@@ -17,11 +17,11 @@
to_chat(owner, "You become frozen in a cube!")
cube = icon('icons/effects/freeze.dmi', "ice_cube")
owner.add_overlay(cube)
- owner.update_canmove()
+ owner.update_mobility()
return ..()
/datum/status_effect/freon/tick()
- owner.update_canmove()
+ owner.update_mobility()
if(can_melt && owner.bodytemperature >= BODYTEMP_NORMAL)
qdel(src)
@@ -31,14 +31,14 @@
if(!QDELETED(src))
to_chat(owner, "You break out of the ice cube!")
owner.remove_status_effect(/datum/status_effect/freon)
- owner.update_canmove()
+ owner.update_mobility()
/datum/status_effect/freon/on_remove()
if(!owner.stat)
to_chat(owner, "The cube melts!")
owner.cut_overlay(cube)
owner.adjust_bodytemperature(100)
- owner.update_canmove()
+ owner.update_mobility()
UnregisterSignal(owner, COMSIG_LIVING_RESIST)
/datum/status_effect/freon/watcher
diff --git a/code/datums/wires/robot.dm b/code/datums/wires/robot.dm
index 5e0d0d77d0..aa7c3cc4c3 100644
--- a/code/datums/wires/robot.dm
+++ b/code/datums/wires/robot.dm
@@ -22,7 +22,7 @@
status += "The law sync module is [R.lawupdate ? "on" : "off"]."
status += "The intelligence link display shows [R.connected_ai ? R.connected_ai.name : "NULL"]."
status += "The camera light is [!isnull(R.builtInCamera) && R.builtInCamera.status ? "on" : "off"]."
- status += "The lockdown indicator is [R.lockcharge ? "on" : "off"]."
+ status += "The lockdown indicator is [R.locked_down ? "on" : "off"]."
status += "The reset module hardware light is [R.has_module() ? "on" : "off"]."
return status
@@ -54,7 +54,7 @@
R.lawsync()
R.show_laws()
if(WIRE_LOCKDOWN)
- R.SetLockdown(!R.lockcharge) // Toggle
+ R.SetLockdown(!R.locked_down) // Toggle
if(WIRE_RESET_MODULE)
if(R.has_module())
R.visible_message("[R]'s module servos twitch.", "Your module display flickers.")
diff --git a/code/datums/world_topic.dm b/code/datums/world_topic.dm
index 49fdd64a72..c2855250f4 100644
--- a/code/datums/world_topic.dm
+++ b/code/datums/world_topic.dm
@@ -172,7 +172,7 @@
.["security_level"] = get_security_level()
.["round_duration"] = SSticker ? round((world.time-SSticker.round_start_time)/10) : 0
// Amount of world's ticks in seconds, useful for calculating round duration
-
+
//Time dilation stats.
.["time_dilation_current"] = SStime_track.time_dilation_current
.["time_dilation_avg"] = SStime_track.time_dilation_avg
@@ -187,3 +187,4 @@
if(!key_valid)
GLOB.topic_status_cache = .
+
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index 6439fd1cfc..9da1b5efbb 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -28,7 +28,6 @@
var/list/managed_overlays
var/datum/proximity_monitor/proximity_monitor
- var/buckle_message_cooldown = 0
var/fingerprintslast
var/list/filter_data //For handling persistent filters
@@ -361,11 +360,12 @@
. = list()
SEND_SIGNAL(src, COMSIG_ATOM_UPDATE_OVERLAYS, .)
-/atom/proc/relaymove(mob/user)
- if(buckle_message_cooldown <= world.time)
- buckle_message_cooldown = world.time + 50
+/atom/proc/relaymove(mob/living/user)
+ if(!istype(user))
+ return //why are you buckling nonliving mobs to atoms?
+ if(user.buckle_message_cooldown <= world.time)
+ user.buckle_message_cooldown = world.time + 50
to_chat(user, "You can't move while buckled to [src]!")
- return
/atom/proc/contents_explosion(severity, target)
return //For handling the effects of explosions on contents that would not normally be effected
diff --git a/code/game/atoms_movable.dm b/code/game/atoms_movable.dm
index 42ccc4bbba..95b6d0c214 100644
--- a/code/game/atoms_movable.dm
+++ b/code/game/atoms_movable.dm
@@ -158,7 +158,7 @@
grab_state = 0
if(isliving(ex_pulled))
var/mob/living/L = ex_pulled
- L.update_canmove()// mob gets up if it was lyng down in a chokehold
+ L.update_mobility()// mob gets up if it was lyng down in a chokehold
/atom/movable/proc/Move_Pulled(atom/A)
if(!pulling)
@@ -194,160 +194,6 @@
stop_pulling()
return
-////////////////////////////////////////
-// Here's where we rewrite how byond handles movement except slightly different
-// To be removed on step_ conversion
-// All this work to prevent a second bump
-/atom/movable/Move(atom/newloc, direct=0)
- . = FALSE
- if(!newloc || newloc == loc)
- return
-
- if(!direct)
- direct = get_dir(src, newloc)
- setDir(direct)
-
- if(!loc.Exit(src, newloc))
- return
-
- if(!newloc.Enter(src, src.loc))
- return
-
- // Past this is the point of no return
- var/atom/oldloc = loc
- var/area/oldarea = get_area(oldloc)
- var/area/newarea = get_area(newloc)
- loc = newloc
- . = TRUE
- oldloc.Exited(src, newloc)
- if(oldarea != newarea)
- oldarea.Exited(src, newloc)
-
- for(var/i in oldloc)
- if(i == src) // Multi tile objects
- continue
- var/atom/movable/thing = i
- thing.Uncrossed(src)
-
- newloc.Entered(src, oldloc)
- if(oldarea != newarea)
- newarea.Entered(src, oldloc)
-
- for(var/i in loc)
- if(i == src) // Multi tile objects
- continue
- var/atom/movable/thing = i
- thing.Crossed(src)
-//
-////////////////////////////////////////
-
-/atom/movable/Move(atom/newloc, direct)
- var/atom/movable/pullee = pulling
- var/turf/T = loc
- if(pulling)
- if(pullee && get_dist(src, pullee) > 1)
- stop_pulling()
-
- if(pullee && pullee.loc != loc && !isturf(pullee.loc) ) //to be removed once all code that changes an object's loc uses forceMove().
- log_game("DEBUG:[src]'s pull on [pullee] wasn't broken despite [pullee] being in [pullee.loc]. Pull stopped manually.")
- stop_pulling()
- if(!loc || !newloc)
- return FALSE
- var/atom/oldloc = loc
-
- if(loc != newloc)
- if (!(direct & (direct - 1))) //Cardinal move
- . = ..()
- else //Diagonal move, split it into cardinal moves
- moving_diagonally = FIRST_DIAG_STEP
- var/first_step_dir
- // The `&& moving_diagonally` checks are so that a forceMove taking
- // place due to a Crossed, Bumped, etc. call will interrupt
- // the second half of the diagonal movement, or the second attempt
- // at a first half if step() fails because we hit something.
- if (direct & NORTH)
- if (direct & EAST)
- if (step(src, NORTH) && moving_diagonally)
- first_step_dir = NORTH
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, EAST)
- else if (moving_diagonally && step(src, EAST))
- first_step_dir = EAST
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, NORTH)
- else if (direct & WEST)
- if (step(src, NORTH) && moving_diagonally)
- first_step_dir = NORTH
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, WEST)
- else if (moving_diagonally && step(src, WEST))
- first_step_dir = WEST
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, NORTH)
- else if (direct & SOUTH)
- if (direct & EAST)
- if (step(src, SOUTH) && moving_diagonally)
- first_step_dir = SOUTH
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, EAST)
- else if (moving_diagonally && step(src, EAST))
- first_step_dir = EAST
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, SOUTH)
- else if (direct & WEST)
- if (step(src, SOUTH) && moving_diagonally)
- first_step_dir = SOUTH
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, WEST)
- else if (moving_diagonally && step(src, WEST))
- first_step_dir = WEST
- moving_diagonally = SECOND_DIAG_STEP
- . = step(src, SOUTH)
- if(moving_diagonally == SECOND_DIAG_STEP)
- if(!.)
- setDir(first_step_dir)
- else if (!inertia_moving)
- inertia_next_move = world.time + inertia_move_delay
- newtonian_move(direct)
- moving_diagonally = 0
- return
-
- if(!loc || (loc == oldloc && oldloc != newloc))
- last_move = 0
- return
-
- if(.)
- Moved(oldloc, direct)
- if(. && pulling && pulling == pullee) //we were pulling a thing and didn't lose it during our move.
- if(pulling.anchored)
- stop_pulling()
- else
- var/pull_dir = get_dir(src, pulling)
- //puller and pullee more than one tile away or in diagonal position
- if(get_dist(src, pulling) > 1 || (moving_diagonally != SECOND_DIAG_STEP && ((pull_dir - 1) & pull_dir)))
- pulling.Move(T, get_dir(pulling, T)) //the pullee tries to reach our previous position
- if(pulling && get_dist(src, pulling) > 1) //the pullee couldn't keep up
- stop_pulling()
- if(pulledby && moving_diagonally != FIRST_DIAG_STEP && get_dist(src, pulledby) > 1)//separated from our puller and not in the middle of a diagonal move.
- pulledby.stop_pulling()
-
-
- last_move = direct
- setDir(direct)
- if(. && has_buckled_mobs() && !handle_buckled_mob_movement(loc,direct)) //movement failed due to buckled mob(s)
- return FALSE
-
-//Called after a successful Move(). By this point, we've already moved
-/atom/movable/proc/Moved(atom/OldLoc, Dir, Forced = FALSE)
- SEND_SIGNAL(src, COMSIG_MOVABLE_MOVED, OldLoc, Dir, Forced)
- if (!inertia_moving)
- inertia_next_move = world.time + inertia_move_delay
- newtonian_move(Dir)
- if (length(client_mobs_in_contents))
- update_parallax_contents()
-
- return TRUE
-
/atom/movable/Destroy(force)
QDEL_NULL(proximity_monitor)
QDEL_NULL(language_holder)
@@ -372,143 +218,6 @@
orbiting.end_orbit(src)
orbiting = null
-// Make sure you know what you're doing if you call this, this is intended to only be called by byond directly.
-// You probably want CanPass()
-/atom/movable/Cross(atom/movable/AM)
- . = TRUE
- SEND_SIGNAL(src, COMSIG_MOVABLE_CROSS, AM)
- return CanPass(AM, AM.loc, TRUE)
-
-//oldloc = old location on atom, inserted when forceMove is called and ONLY when forceMove is called!
-/atom/movable/Crossed(atom/movable/AM, oldloc)
- SEND_SIGNAL(src, COMSIG_MOVABLE_CROSSED, AM)
-
-/atom/movable/Uncross(atom/movable/AM, atom/newloc)
- . = ..()
- if(SEND_SIGNAL(src, COMSIG_MOVABLE_UNCROSS, AM) & COMPONENT_MOVABLE_BLOCK_UNCROSS)
- return FALSE
- if(isturf(newloc) && !CheckExit(AM, newloc))
- return FALSE
-
-/atom/movable/Uncrossed(atom/movable/AM)
- SEND_SIGNAL(src, COMSIG_MOVABLE_UNCROSSED, AM)
-
-/atom/movable/Bump(atom/A)
- if(!A)
- CRASH("Bump was called with no argument.")
- SEND_SIGNAL(src, COMSIG_MOVABLE_BUMP, A)
- . = ..()
- if(!QDELETED(throwing))
- throwing.hit_atom(A)
- . = TRUE
- if(QDELETED(A))
- return
- A.Bumped(src)
-
-/atom/movable/proc/forceMove(atom/destination)
- . = FALSE
- if(destination)
- . = doMove(destination)
- else
- CRASH("No valid destination passed into forceMove")
-
-/atom/movable/proc/moveToNullspace()
- return doMove(null)
-
-/atom/movable/proc/doMove(atom/destination)
- . = FALSE
- if(destination)
- if(pulledby)
- pulledby.stop_pulling()
- var/atom/oldloc = loc
- var/same_loc = oldloc == destination
- var/area/old_area = get_area(oldloc)
- var/area/destarea = get_area(destination)
-
- loc = destination
- moving_diagonally = 0
-
- if(!same_loc)
- if(oldloc)
- oldloc.Exited(src, destination)
- if(old_area && old_area != destarea)
- old_area.Exited(src, destination)
- for(var/atom/movable/AM in oldloc)
- AM.Uncrossed(src)
- var/turf/oldturf = get_turf(oldloc)
- var/turf/destturf = get_turf(destination)
- var/old_z = (oldturf ? oldturf.z : null)
- var/dest_z = (destturf ? destturf.z : null)
- if (old_z != dest_z)
- onTransitZ(old_z, dest_z)
- destination.Entered(src, oldloc)
- if(destarea && old_area != destarea)
- destarea.Entered(src, oldloc)
-
- for(var/atom/movable/AM in destination)
- if(AM == src)
- continue
- AM.Crossed(src, oldloc)
-
- Moved(oldloc, NONE, TRUE)
- . = TRUE
-
- //If no destination, move the atom into nullspace (don't do this unless you know what you're doing)
- else
- . = TRUE
- if (loc)
- var/atom/oldloc = loc
- var/area/old_area = get_area(oldloc)
- oldloc.Exited(src, null)
- if(old_area)
- old_area.Exited(src, null)
- loc = null
-
-/atom/movable/proc/onTransitZ(old_z,new_z)
- SEND_SIGNAL(src, COMSIG_MOVABLE_Z_CHANGED, old_z, new_z)
- for (var/item in src) // Notify contents of Z-transition. This can be overridden IF we know the items contents do not care.
- var/atom/movable/AM = item
- AM.onTransitZ(old_z,new_z)
-
-/atom/movable/proc/setMovetype(newval)
- movement_type = newval
-
-//Called whenever an object moves and by mobs when they attempt to move themselves through space
-//And when an object or action applies a force on src, see newtonian_move() below
-//Return 0 to have src start/keep drifting in a no-grav area and 1 to stop/not start drifting
-//Mobs should return 1 if they should be able to move of their own volition, see client/Move() in mob_movement.dm
-//movement_dir == 0 when stopping or any dir when trying to move
-/atom/movable/proc/Process_Spacemove(movement_dir = 0)
- if(has_gravity(src))
- return 1
-
- if(pulledby)
- return 1
-
- if(throwing)
- return 1
-
- if(!isturf(loc))
- return 1
-
- if(locate(/obj/structure/lattice) in range(1, get_turf(src))) //Not realistic but makes pushing things in space easier
- return 1
-
- return 0
-
-
-/atom/movable/proc/newtonian_move(direction) //Only moves the object if it's under no gravity
- if(!loc || Process_Spacemove(0))
- inertia_dir = 0
- return 0
-
- inertia_dir = direction
- if(!direction)
- return 1
- inertia_last_loc = loc
- SSspacedrift.processing[src] = src
- return 1
-
/atom/movable/proc/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum)
set waitfor = 0
SEND_SIGNAL(src, COMSIG_MOVABLE_IMPACT, hit_atom, throwingdatum)
@@ -610,17 +319,6 @@
SSthrowing.currentrun[src] = TT
TT.tick()
-/atom/movable/proc/handle_buckled_mob_movement(newloc,direct)
- for(var/m in buckled_mobs)
- var/mob/living/buckled_mob = m
- if(!buckled_mob.Move(newloc, direct))
- forceMove(buckled_mob.loc)
- last_move = buckled_mob.last_move
- inertia_dir = last_move
- buckled_mob.inertia_dir = last_move
- return 0
- return 1
-
/atom/movable/proc/force_pushed(atom/movable/pusher, force = MOVE_FORCE_DEFAULT, direction)
return FALSE
@@ -639,7 +337,7 @@
/atom/movable/CanPass(atom/movable/mover, turf/target)
if(mover in buckled_mobs)
- return 1
+ return TRUE
return ..()
// called when this atom is removed from a storage item, which is passed on as S. The loc variable is already set to the new destination before this is called.
diff --git a/code/game/atoms_movement.dm b/code/game/atoms_movement.dm
new file mode 100644
index 0000000000..d418652cd8
--- /dev/null
+++ b/code/game/atoms_movement.dm
@@ -0,0 +1,307 @@
+// File for movement procs for atom/movable
+
+
+////////////////////////////////////////
+// Here's where we rewrite how byond handles movement except slightly different
+// To be removed on step_ conversion
+// All this work to prevent a second bump
+/atom/movable/Move(atom/newloc, direct=0)
+ . = FALSE
+ if(!newloc || newloc == loc)
+ return
+
+ if(!direct)
+ direct = get_dir(src, newloc)
+ setDir(direct)
+
+ if(!loc.Exit(src, newloc))
+ return
+
+ if(!newloc.Enter(src, src.loc))
+ return
+
+ // Past this is the point of no return
+ var/atom/oldloc = loc
+ var/area/oldarea = get_area(oldloc)
+ var/area/newarea = get_area(newloc)
+ loc = newloc
+ . = TRUE
+ oldloc.Exited(src, newloc)
+ if(oldarea != newarea)
+ oldarea.Exited(src, newloc)
+
+ for(var/i in oldloc)
+ if(i == src) // Multi tile objects
+ continue
+ var/atom/movable/thing = i
+ thing.Uncrossed(src)
+
+ newloc.Entered(src, oldloc)
+ if(oldarea != newarea)
+ newarea.Entered(src, oldloc)
+
+ for(var/i in loc)
+ if(i == src) // Multi tile objects
+ continue
+ var/atom/movable/thing = i
+ thing.Crossed(src)
+//
+////////////////////////////////////////
+
+/atom/movable/Move(atom/newloc, direct)
+ var/atom/movable/pullee = pulling
+ var/turf/T = loc
+ if(pulling)
+ if(pullee && get_dist(src, pullee) > 1)
+ stop_pulling()
+
+ if(pullee && pullee.loc != loc && !isturf(pullee.loc) ) //to be removed once all code that changes an object's loc uses forceMove().
+ log_game("DEBUG:[src]'s pull on [pullee] wasn't broken despite [pullee] being in [pullee.loc]. Pull stopped manually.")
+ stop_pulling()
+ if(!loc || !newloc)
+ return FALSE
+ var/atom/oldloc = loc
+
+ if(loc != newloc)
+ if (!(direct & (direct - 1))) //Cardinal move
+ . = ..()
+ else //Diagonal move, split it into cardinal moves
+ moving_diagonally = FIRST_DIAG_STEP
+ var/first_step_dir
+ // The `&& moving_diagonally` checks are so that a forceMove taking
+ // place due to a Crossed, Bumped, etc. call will interrupt
+ // the second half of the diagonal movement, or the second attempt
+ // at a first half if step() fails because we hit something.
+ if (direct & NORTH)
+ if (direct & EAST)
+ if (step(src, NORTH) && moving_diagonally)
+ first_step_dir = NORTH
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, EAST)
+ else if (moving_diagonally && step(src, EAST))
+ first_step_dir = EAST
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, NORTH)
+ else if (direct & WEST)
+ if (step(src, NORTH) && moving_diagonally)
+ first_step_dir = NORTH
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, WEST)
+ else if (moving_diagonally && step(src, WEST))
+ first_step_dir = WEST
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, NORTH)
+ else if (direct & SOUTH)
+ if (direct & EAST)
+ if (step(src, SOUTH) && moving_diagonally)
+ first_step_dir = SOUTH
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, EAST)
+ else if (moving_diagonally && step(src, EAST))
+ first_step_dir = EAST
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, SOUTH)
+ else if (direct & WEST)
+ if (step(src, SOUTH) && moving_diagonally)
+ first_step_dir = SOUTH
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, WEST)
+ else if (moving_diagonally && step(src, WEST))
+ first_step_dir = WEST
+ moving_diagonally = SECOND_DIAG_STEP
+ . = step(src, SOUTH)
+ if(moving_diagonally == SECOND_DIAG_STEP)
+ if(!.)
+ setDir(first_step_dir)
+ else if (!inertia_moving)
+ inertia_next_move = world.time + inertia_move_delay
+ newtonian_move(direct)
+ moving_diagonally = 0
+ return
+
+ if(!loc || (loc == oldloc && oldloc != newloc))
+ last_move = NONE
+ return
+
+ if(.)
+ last_move = direct
+ setDir(direct)
+
+ if(has_buckled_mobs() && !handle_buckled_mob_movement(loc,direct)) //movement failed due to buckled mob(s)
+ return FALSE
+
+ if(pulling && pulling == pullee) //we were pulling a thing and didn't lose it during our move.
+ if(pulling.anchored)
+ stop_pulling()
+ else
+ var/pull_dir = get_dir(src, pulling)
+ //puller and pullee more than one tile away or in diagonal position
+ if(get_dist(src, pulling) > 1 || (moving_diagonally != SECOND_DIAG_STEP && ((pull_dir - 1) & pull_dir)))
+ pulling.Move(T, get_dir(pulling, T)) //the pullee tries to reach our previous position
+ if(pulling && get_dist(src, pulling) > 1) //the pullee couldn't keep up
+ stop_pulling()
+ if(pulledby && moving_diagonally != FIRST_DIAG_STEP && get_dist(src, pulledby) > 1)//separated from our puller and not in the middle of a diagonal move.
+ pulledby.stop_pulling()
+
+ Moved(oldloc, direct)
+
+/atom/movable/proc/handle_buckled_mob_movement(newloc,direct)
+ for(var/m in buckled_mobs)
+ var/mob/living/buckled_mob = m
+ if(!buckled_mob.Move(newloc, direct))
+ forceMove(buckled_mob.loc)
+ last_move = buckled_mob.last_move
+ inertia_dir = last_move
+ buckled_mob.inertia_dir = last_move
+ return FALSE
+ return TRUE
+
+//Called after a successful Move(). By this point, we've already moved
+/atom/movable/proc/Moved(atom/OldLoc, Dir, Forced = FALSE)
+ SEND_SIGNAL(src, COMSIG_MOVABLE_MOVED, OldLoc, Dir, Forced)
+ if (!inertia_moving)
+ inertia_next_move = world.time + inertia_move_delay
+ newtonian_move(Dir)
+ if (length(client_mobs_in_contents))
+ update_parallax_contents()
+
+ return TRUE
+
+
+// Make sure you know what you're doing if you call this, this is intended to only be called by byond directly.
+// You probably want CanPass()
+/atom/movable/Cross(atom/movable/AM)
+ . = TRUE
+ SEND_SIGNAL(src, COMSIG_MOVABLE_CROSS, AM)
+ return CanPass(AM, AM.loc, TRUE)
+
+//oldloc = old location on atom, inserted when forceMove is called and ONLY when forceMove is called!
+/atom/movable/Crossed(atom/movable/AM, oldloc)
+ SEND_SIGNAL(src, COMSIG_MOVABLE_CROSSED, AM)
+
+/atom/movable/Uncross(atom/movable/AM, atom/newloc)
+ . = ..()
+ if(SEND_SIGNAL(src, COMSIG_MOVABLE_UNCROSS, AM) & COMPONENT_MOVABLE_BLOCK_UNCROSS)
+ return FALSE
+ if(isturf(newloc) && !CheckExit(AM, newloc))
+ return FALSE
+
+/atom/movable/Uncrossed(atom/movable/AM)
+ SEND_SIGNAL(src, COMSIG_MOVABLE_UNCROSSED, AM)
+
+/atom/movable/Bump(atom/A)
+ if(!A)
+ CRASH("Bump was called with no argument.")
+ SEND_SIGNAL(src, COMSIG_MOVABLE_BUMP, A)
+ . = ..()
+ if(!QDELETED(throwing))
+ throwing.hit_atom(A)
+ . = TRUE
+ if(QDELETED(A))
+ return
+ A.Bumped(src)
+
+/atom/movable/proc/onTransitZ(old_z,new_z)
+ SEND_SIGNAL(src, COMSIG_MOVABLE_Z_CHANGED, old_z, new_z)
+ for (var/item in src) // Notify contents of Z-transition. This can be overridden IF we know the items contents do not care.
+ var/atom/movable/AM = item
+ AM.onTransitZ(old_z,new_z)
+
+/atom/movable/proc/setMovetype(newval)
+ movement_type = newval
+
+///////////// FORCED MOVEMENT /////////////
+
+/atom/movable/proc/forceMove(atom/destination)
+ . = FALSE
+ if(destination)
+ . = doMove(destination)
+ else
+ CRASH("No valid destination passed into forceMove")
+
+/atom/movable/proc/moveToNullspace()
+ return doMove(null)
+
+/atom/movable/proc/doMove(atom/destination)
+ . = FALSE
+ if(destination)
+ if(pulledby)
+ pulledby.stop_pulling()
+ var/atom/oldloc = loc
+ var/same_loc = oldloc == destination
+ var/area/old_area = get_area(oldloc)
+ var/area/destarea = get_area(destination)
+
+ loc = destination
+ moving_diagonally = 0
+
+ if(!same_loc)
+ if(oldloc)
+ oldloc.Exited(src, destination)
+ if(old_area && old_area != destarea)
+ old_area.Exited(src, destination)
+ for(var/atom/movable/AM in oldloc)
+ AM.Uncrossed(src)
+ var/turf/oldturf = get_turf(oldloc)
+ var/turf/destturf = get_turf(destination)
+ var/old_z = (oldturf ? oldturf.z : null)
+ var/dest_z = (destturf ? destturf.z : null)
+ if (old_z != dest_z)
+ onTransitZ(old_z, dest_z)
+ destination.Entered(src, oldloc)
+ if(destarea && old_area != destarea)
+ destarea.Entered(src, oldloc)
+
+ for(var/atom/movable/AM in destination)
+ if(AM == src)
+ continue
+ AM.Crossed(src, oldloc)
+
+ Moved(oldloc, NONE, TRUE)
+ . = TRUE
+
+ //If no destination, move the atom into nullspace (don't do this unless you know what you're doing)
+ else
+ . = TRUE
+ if (loc)
+ var/atom/oldloc = loc
+ var/area/old_area = get_area(oldloc)
+ oldloc.Exited(src, null)
+ if(old_area)
+ old_area.Exited(src, null)
+ loc = null
+
+//Called whenever an object moves and by mobs when they attempt to move themselves through space
+//And when an object or action applies a force on src, see newtonian_move() below
+//Return 0 to have src start/keep drifting in a no-grav area and 1 to stop/not start drifting
+//Mobs should return 1 if they should be able to move of their own volition, see client/Move() in mob_movement.dm
+//movement_dir == 0 when stopping or any dir when trying to move
+/atom/movable/proc/Process_Spacemove(movement_dir = 0)
+ if(has_gravity(src))
+ return 1
+
+ if(pulledby)
+ return 1
+
+ if(throwing)
+ return 1
+
+ if(!isturf(loc))
+ return 1
+
+ if(locate(/obj/structure/lattice) in range(1, get_turf(src))) //Not realistic but makes pushing things in space easier
+ return 1
+
+ return 0
+
+/atom/movable/proc/newtonian_move(direction) //Only moves the object if it's under no gravity
+ if(!loc || Process_Spacemove(0))
+ inertia_dir = 0
+ return 0
+
+ inertia_dir = direction
+ if(!direction)
+ return 1
+ inertia_last_loc = loc
+ SSspacedrift.processing[src] = src
+ return 1
diff --git a/code/game/gamemodes/gangs/gang_pen.dm b/code/game/gamemodes/gangs/gang_pen.dm
index 0851f3b596..b7bd6cca5e 100644
--- a/code/game/gamemodes/gangs/gang_pen.dm
+++ b/code/game/gamemodes/gangs/gang_pen.dm
@@ -54,6 +54,6 @@
return
var/mob/living/carbon/human/H = gangster_mind.current // we are sure the dude's human cause it's checked in attack()
H.silent = max(H.silent, 5)
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
gangster_mind.add_antag_datum(/datum/antagonist/gang, gang)
return TRUE
\ No newline at end of file
diff --git a/code/game/machinery/_machinery.dm b/code/game/machinery/_machinery.dm
index 7132f046e6..995d11acb7 100644
--- a/code/game/machinery/_machinery.dm
+++ b/code/game/machinery/_machinery.dm
@@ -185,7 +185,7 @@ Class Procs:
A.forceMove(T)
if(isliving(A))
var/mob/living/L = A
- L.update_canmove()
+ L.update_mobility()
if(occupant)
SEND_SIGNAL(src, COMSIG_MACHINE_EJECT_OCCUPANT, occupant)
occupant = null
diff --git a/code/game/machinery/computer/arcade/orion_trail.dm b/code/game/machinery/computer/arcade/orion_trail.dm
index c8c7bc1319..2304312953 100644
--- a/code/game/machinery/computer/arcade/orion_trail.dm
+++ b/code/game/machinery/computer/arcade/orion_trail.dm
@@ -217,7 +217,7 @@
M.vomit(10, distance = 5)
if(ORION_TRAIL_FLUX)
if(prob(75))
- M.Knockdown(60)
+ M.DefaultCombatKnockdown(60)
say("A sudden gust of powerful wind slams [M] into the floor!")
M.take_bodypart_damage(25)
playsound(loc, 'sound/weapons/genhit.ogg', 100, 1)
diff --git a/code/game/machinery/computer/robot.dm b/code/game/machinery/computer/robot.dm
index 5573c56386..aad375a610 100644
--- a/code/game/machinery/computer/robot.dm
+++ b/code/game/machinery/computer/robot.dm
@@ -37,12 +37,11 @@
dat += "[R.name] |"
if(R.stat)
dat += " Not Responding |"
- else if (!R.canmove)
+ else if(R.locked_down)
dat += " Locked Down |"
else
dat += " Operating Normally |"
- if (!R.canmove)
- else if(R.cell)
+ if(R.cell)
dat += " Battery Installed ([R.cell.charge]/[R.cell.maxcharge]) |"
else
dat += " No Cell Installed |"
@@ -62,7 +61,7 @@
dat += "(Hack) "
else if(IsAdminGhost(user) && !R.emagged)
dat += "(Hack) "
- dat += "([R.canmove ? "Lockdown" : "Release"]) "
+ dat += "([R.locked_down? "Lockdown" : "Release"]) "
dat += "(Destroy)"
dat += "
"
@@ -116,14 +115,14 @@
if(src.allowed(usr))
var/mob/living/silicon/robot/R = locate(href_list["stopbot"]) in GLOB.silicon_mobs
if(can_control(usr, R))
- var/choice = input("Are you certain you wish to [R.canmove ? "lock down" : "release"] [R.name]?") in list("Confirm", "Abort")
+ var/choice = input("Are you certain you wish to [R.locked_down? "lock down" : "release"] [R.name]?") in list("Confirm", "Abort")
if(choice == "Confirm" && can_control(usr, R) && !..())
- message_admins("[ADMIN_LOOKUPFLW(usr)] [R.canmove ? "locked down" : "released"] [key_name(R, R.client)][ADMIN_LOOKUPFLW(R)]!")
- log_game("[key_name(usr)] [R.canmove ? "locked down" : "released"] [key_name(R)]!")
- R.SetLockdown(!R.lockcharge)
- to_chat(R, "[!R.lockcharge ? "Your lockdown has been lifted!" : "You have been locked down!"]")
+ message_admins("[ADMIN_LOOKUPFLW(usr)] [R.locked_down? "locked down" : "released"] [key_name(R, R.client)][ADMIN_LOOKUPFLW(R)]!")
+ log_game("[key_name(usr)] [R.locked_down? "locked down" : "released"] [key_name(R)]!")
+ R.SetLockdown(!R.locked_down)
+ to_chat(R, "[!R.locked_down ? "Your lockdown has been lifted!" : "You have been locked down!"]")
if(R.connected_ai)
- to_chat(R.connected_ai, "[!R.lockcharge ? "NOTICE - Cyborg lockdown lifted" : "ALERT - Cyborg lockdown detected"]: [R.name]
")
+ to_chat(R.connected_ai, "[!R.locked_down ? "NOTICE - Cyborg lockdown lifted" : "ALERT - Cyborg lockdown detected"]: [R.name]
")
else
to_chat(usr, "Access Denied.")
diff --git a/code/game/machinery/dance_machine.dm b/code/game/machinery/dance_machine.dm
index ea14031603..9ecc19e40f 100644
--- a/code/game/machinery/dance_machine.dm
+++ b/code/game/machinery/dance_machine.dm
@@ -433,5 +433,5 @@
. = ..()
if(active)
for(var/mob/living/M in rangers)
- if(prob(5+(allowed(M)*4)) && M.canmove)
+ if(prob(5+(allowed(M)*4)) && CHECK_MOBILITY(M, MOBILITY_MOVE))
dance(M)
diff --git a/code/game/machinery/doors/airlock.dm b/code/game/machinery/doors/airlock.dm
index d626c76aca..3bc8aff809 100644
--- a/code/game/machinery/doors/airlock.dm
+++ b/code/game/machinery/doors/airlock.dm
@@ -769,7 +769,7 @@
if(!istype(H.head, /obj/item/clothing/head/helmet))
H.visible_message("[user] headbutts the airlock.", \
"You headbutt the airlock!")
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
H.apply_damage(10, BRUTE, BODY_ZONE_HEAD)
else
visible_message("[user] headbutts the airlock. Good thing [user.p_theyre()] wearing a helmet.")
@@ -1033,7 +1033,7 @@
if(!I.use_tool(src, user, 150, volume=50))
to_chat(user, "You slip and [charge] detonates!")
charge.ex_act(EXPLODE_DEVASTATE)
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
return
user.visible_message("[user] removes [charge] from [src].", \
"You gently pry out [charge] from [src] and unhook its wires.")
diff --git a/code/game/machinery/doors/airlock_types.dm b/code/game/machinery/doors/airlock_types.dm
index 50ae7dab18..530a287134 100644
--- a/code/game/machinery/doors/airlock_types.dm
+++ b/code/game/machinery/doors/airlock_types.dm
@@ -508,7 +508,7 @@
throwtarget = get_edge_target_turf(src, get_dir(src, get_step_away(L, src)))
SEND_SOUND(L, sound(pick('sound/hallucinations/turn_around1.ogg','sound/hallucinations/turn_around2.ogg'),0,1,50))
flash_color(L, flash_color="#960000", flash_time=20)
- L.Knockdown(40)
+ L.DefaultCombatKnockdown(40)
L.throw_at(throwtarget, 5, 1)
return 0
diff --git a/code/game/machinery/doors/door.dm b/code/game/machinery/doors/door.dm
index d2f98a868b..c4c712ca25 100644
--- a/code/game/machinery/doors/door.dm
+++ b/code/game/machinery/doors/door.dm
@@ -319,10 +319,10 @@
else if(ishuman(L)) //For humans
L.adjustBruteLoss(DOOR_CRUSH_DAMAGE)
L.emote("scream")
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
else if(ismonkey(L)) //For monkeys
L.adjustBruteLoss(DOOR_CRUSH_DAMAGE)
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
else //for simple_animals & borgs
L.adjustBruteLoss(DOOR_CRUSH_DAMAGE)
var/turf/location = get_turf(src)
diff --git a/code/game/machinery/flasher.dm b/code/game/machinery/flasher.dm
index 9cc4fc43ac..7bef255aff 100644
--- a/code/game/machinery/flasher.dm
+++ b/code/game/machinery/flasher.dm
@@ -115,7 +115,7 @@
continue
if(L.flash_act(affect_silicon = 1))
- L.Knockdown(strength)
+ L.DefaultCombatKnockdown(strength)
flashed = TRUE
if(flashed)
diff --git a/code/game/machinery/pipe/construction.dm b/code/game/machinery/pipe/construction.dm
index 937e3909b0..8b6c2180d9 100644
--- a/code/game/machinery/pipe/construction.dm
+++ b/code/game/machinery/pipe/construction.dm
@@ -90,7 +90,8 @@ Buildable meters
set name = "Flip Pipe"
set src in view(1)
- if ( usr.stat || usr.restrained() || !usr.canmove )
+ var/mob/living/L = usr
+ if(!istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
return
do_a_flip()
diff --git a/code/game/machinery/pipe/pipe_dispenser.dm b/code/game/machinery/pipe/pipe_dispenser.dm
index 4cba24bac7..b0e26ce129 100644
--- a/code/game/machinery/pipe/pipe_dispenser.dm
+++ b/code/game/machinery/pipe/pipe_dispenser.dm
@@ -34,7 +34,8 @@
/obj/machinery/pipedispenser/Topic(href, href_list)
if(..())
return 1
- if(!anchored|| !usr.canmove || usr.stat || usr.restrained() || !in_range(loc, usr))
+ var/mob/living/L = usr
+ if(!anchored || !istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
usr << browse(null, "window=pipedispenser")
return 1
usr.set_machine(src)
@@ -93,14 +94,14 @@
//Allow you to drag-drop disposal pipes and transit tubes into it
-/obj/machinery/pipedispenser/disposal/MouseDrop_T(obj/structure/pipe, mob/usr)
- if(!usr.canmove || usr.stat || usr.restrained())
+/obj/machinery/pipedispenser/disposal/MouseDrop_T(obj/structure/pipe, mob/living/user)
+ if(!istype(user) || !CHECK_MOBILITY(user, MOBILITY_USE))
return
if (!istype(pipe, /obj/structure/disposalconstruct) && !istype(pipe, /obj/structure/c_transit_tube) && !istype(pipe, /obj/structure/c_transit_tube_pod))
return
- if (get_dist(usr, src) > 1 || get_dist(src,pipe) > 1 )
+ if (get_dist(user, src) > 1 || get_dist(src,pipe) > 1 )
return
if (pipe.anchored)
diff --git a/code/game/mecha/equipment/tools/medical_tools.dm b/code/game/mecha/equipment/tools/medical_tools.dm
index 5f6b709d1a..7d44e7611c 100644
--- a/code/game/mecha/equipment/tools/medical_tools.dm
+++ b/code/game/mecha/equipment/tools/medical_tools.dm
@@ -226,8 +226,7 @@
return
if(M.health > 0)
M.adjustOxyLoss(-1)
- M.AdjustStun(-80)
- M.AdjustKnockdown(-80)
+ M.AdjustAllImmobility(-80)
M.AdjustUnconscious(-80)
if(M.reagents.get_reagent_amount(/datum/reagent/medicine/epinephrine) < 5)
M.reagents.add_reagent(/datum/reagent/medicine/epinephrine, 5)
diff --git a/code/game/mecha/equipment/weapons/weapons.dm b/code/game/mecha/equipment/weapons/weapons.dm
index 978825c546..f1fa5ddd20 100644
--- a/code/game/mecha/equipment/weapons/weapons.dm
+++ b/code/game/mecha/equipment/weapons/weapons.dm
@@ -177,7 +177,7 @@
M.SetSleeping(0)
M.stuttering += 20
M.adjustEarDamage(0, 30)
- M.Knockdown(60)
+ M.DefaultCombatKnockdown(60)
if(prob(30))
M.Stun(200)
M.Unconscious(80)
diff --git a/code/game/mecha/mecha.dm b/code/game/mecha/mecha.dm
index 669bc89875..02115d3e30 100644
--- a/code/game/mecha/mecha.dm
+++ b/code/game/mecha/mecha.dm
@@ -755,7 +755,7 @@
AI.cancel_camera()
AI.controlled_mech = src
AI.remote_control = src
- AI.canmove = 1 //Much easier than adding AI checks! Be sure to set this back to 0 if you decide to allow an AI to leave a mech somehow.
+ AI.mobility_flags = MOBILITY_FLAGS_DEFAULT //Much easier than adding AI checks! Be sure to set this back to 0 if you decide to allow an AI to leave a mech somehow.
AI.can_shunt = 0 //ONE AI ENTERS. NO AI LEAVES.
to_chat(AI, AI.can_dominate_mechs ? "Takeover of [name] complete! You are now loaded onto the onboard computer. Do not attempt to leave the station sector!" :\
"You have been uploaded to a mech's onboard computer.")
@@ -927,7 +927,7 @@
brainmob.forceMove(src) //should allow relaymove
brainmob.reset_perspective(src)
brainmob.remote_control = src
- brainmob.update_canmove()
+ brainmob.update_mobility()
brainmob.update_mouse_pointer()
icon_state = initial(icon_state)
update_icon()
@@ -941,7 +941,6 @@
/obj/mecha/container_resist(mob/living/user)
go_out()
-
/obj/mecha/Exited(atom/movable/M, atom/newloc)
if(occupant && occupant == M) // The occupant exited the mech without calling go_out()
go_out(TRUE, newloc)
@@ -993,7 +992,7 @@
L.reset_perspective()
mmi.mecha = null
mmi.update_icon()
- L.canmove = 0
+ L.mobility_flags = NONE
icon_state = initial(icon_state)+"-open"
setDir(dir_in)
diff --git a/code/game/objects/buckling.dm b/code/game/objects/buckling.dm
index 416644cada..0e14af75a9 100644
--- a/code/game/objects/buckling.dm
+++ b/code/game/objects/buckling.dm
@@ -36,8 +36,7 @@
//procs that handle the actual buckling and unbuckling
/atom/movable/proc/buckle_mob(mob/living/M, force = FALSE, check_loc = TRUE)
- if(!buckled_mobs)
- buckled_mobs = list()
+ LAZYINITLIST(buckled_mobs)
if(!istype(M))
return FALSE
@@ -66,7 +65,7 @@
M.buckled = src
M.setDir(dir)
buckled_mobs |= M
- M.update_canmove()
+ M.update_mobility()
M.throw_alert("buckled", /obj/screen/alert/restrained/buckled)
post_buckle_mob(M)
@@ -85,7 +84,7 @@
. = buckled_mob
buckled_mob.buckled = null
buckled_mob.anchored = initial(buckled_mob.anchored)
- buckled_mob.update_canmove()
+ buckled_mob.update_mobility()
buckled_mob.clear_alert("buckled")
buckled_mobs -= buckled_mob
SEND_SIGNAL(src, COMSIG_MOVABLE_UNBUCKLE, buckled_mob, force)
diff --git a/code/game/objects/effects/anomalies.dm b/code/game/objects/effects/anomalies.dm
index fbe25c5d1b..8c3ffa3cfc 100644
--- a/code/game/objects/effects/anomalies.dm
+++ b/code/game/objects/effects/anomalies.dm
@@ -113,7 +113,7 @@
/obj/effect/anomaly/grav/proc/gravShock(mob/living/A)
if(boing && isliving(A) && !A.stat)
- A.Knockdown(40)
+ A.DefaultCombatKnockdown(40)
var/atom/target = get_edge_target_turf(A, get_dir(src, get_step_away(A, src)))
A.throw_at(target, 5, 1)
boing = 0
diff --git a/code/game/objects/effects/effect_system/effects_other.dm b/code/game/objects/effects/effect_system/effects_other.dm
index dbc9b35275..c62dddfdb2 100644
--- a/code/game/objects/effects/effect_system/effects_other.dm
+++ b/code/game/objects/effects/effect_system/effects_other.dm
@@ -104,4 +104,5 @@
if(explosion_message)
location.visible_message("The solution violently explodes!", \
"You hear an explosion!")
- dyn_explosion(location, amount, flashing_factor)
\ No newline at end of file
+ dyn_explosion(location, amount, flashing_factor)
+
diff --git a/code/game/objects/effects/mines.dm b/code/game/objects/effects/mines.dm
index 6b94c65f49..2fb068a29b 100644
--- a/code/game/objects/effects/mines.dm
+++ b/code/game/objects/effects/mines.dm
@@ -48,7 +48,7 @@
/obj/effect/mine/stun/mineEffect(mob/living/victim)
if(isliving(victim))
- victim.Knockdown(stun_time)
+ victim.DefaultCombatKnockdown(stun_time)
/obj/effect/mine/kickmine
name = "kick mine"
diff --git a/code/game/objects/effects/step_triggers.dm b/code/game/objects/effects/step_triggers.dm
index 8c3503367e..01edd82ccb 100644
--- a/code/game/objects/effects/step_triggers.dm
+++ b/code/game/objects/effects/step_triggers.dm
@@ -61,10 +61,11 @@
if(AM in T.affecting)
return
- if(ismob(AM))
- var/mob/M = AM
+ if(isliving(AM))
+ var/mob/living/M = AM
if(immobilize)
- M.canmove = 0
+ ADD_TRAIT(M, TRAIT_MOBILITY_NOMOVE, src)
+ M.update_mobility()
affecting.Add(AM)
while(AM && !stopthrow)
@@ -98,10 +99,11 @@
affecting.Remove(AM)
- if(ismob(AM))
- var/mob/M = AM
+ if(isliving(AM))
+ var/mob/living/M = AM
if(immobilize)
- M.canmove = 1
+ REMOVE_TRAIT(M, TRAIT_MOBILITY_NOMOVE, src)
+ M.update_mobility()
/* Stops things thrown by a thrower, doesn't do anything */
diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm
index 8dfb36ce8a..fd1d2fc43d 100644
--- a/code/game/objects/items.dm
+++ b/code/game/objects/items.dm
@@ -175,14 +175,13 @@ GLOBAL_VAR_INIT(rpg_loot_items, FALSE)
set category = "Object"
set src in oview(1)
- if(!isturf(loc) || usr.stat || usr.restrained() || !usr.canmove)
+ var/mob/living/L = usr
+ if(!istype(L) || !isturf(loc) || !CHECK_MOBILITY(L, MOBILITY_USE))
return
- var/turf/T = src.loc
-
- src.loc = null
-
- src.loc = T
+ var/turf/T = loc
+ loc = null
+ loc = T
/obj/item/examine(mob/user) //This might be spammy. Remove?
. = ..()
@@ -544,7 +543,7 @@ GLOBAL_VAR_INIT(rpg_loot_items, FALSE)
to_chat(M, "You drop what you're holding and clutch at your eyes!")
M.adjust_blurriness(10)
M.Unconscious(20)
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
if (prob(eyes.damage - 10 + 1))
M.become_blind(EYE_DAMAGE)
to_chat(M, "You go blind!")
diff --git a/code/game/objects/items/cigs_lighters.dm b/code/game/objects/items/cigs_lighters.dm
index ac666f04db..5b7c70b1b6 100644
--- a/code/game/objects/items/cigs_lighters.dm
+++ b/code/game/objects/items/cigs_lighters.dm
@@ -856,7 +856,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(prob(5))//small chance for the vape to break and deal damage if it's emagged
playsound(get_turf(src), 'sound/effects/pop_expl.ogg', 50, 0)
M.apply_damage(20, BURN, BODY_ZONE_HEAD)
- M.Knockdown(300, 1, 0)
+ M.DefaultCombatKnockdown(300, 1, 0)
var/datum/effect_system/spark_spread/sp = new /datum/effect_system/spark_spread
sp.set_up(5, 1, src)
sp.start()
diff --git a/code/game/objects/items/crayons.dm b/code/game/objects/items/crayons.dm
index f81268f1dc..f5b13d4e3e 100644
--- a/code/game/objects/items/crayons.dm
+++ b/code/game/objects/items/crayons.dm
@@ -694,7 +694,7 @@
C.blind_eyes(1)
if(C.get_eye_protection() <= 0) // no eye protection? ARGH IT BURNS.
C.confused = max(C.confused, 3)
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
if(ishuman(C) && actually_paints)
var/mob/living/carbon/human/H = C
H.lip_style = "spray_face"
diff --git a/code/game/objects/items/defib.dm b/code/game/objects/items/defib.dm
index b1e86d6643..3ac3347222 100644
--- a/code/game/objects/items/defib.dm
+++ b/code/game/objects/items/defib.dm
@@ -449,7 +449,7 @@
M.visible_message("[user] zaps [M] with [src]!", \
"[user] zaps [M] with [src]!")
M.adjustStaminaLoss(50)
- M.Knockdown(100)
+ M.DefaultCombatKnockdown(100)
M.updatehealth() //forces health update before next life tick
playsound(src, 'sound/machines/defib_zap.ogg', 50, 1, -1)
M.emote("gasp")
@@ -506,7 +506,7 @@
H.set_heartattack(TRUE)
H.apply_damage(50, BURN, BODY_ZONE_CHEST)
log_combat(user, H, "overloaded the heart of", defib)
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
H.Jitter(100)
if(req_defib)
defib.deductcharge(revivecost)
diff --git a/code/game/objects/items/devices/PDA/PDA.dm b/code/game/objects/items/devices/PDA/PDA.dm
index eed4f2ce80..9adc93a4da 100644
--- a/code/game/objects/items/devices/PDA/PDA.dm
+++ b/code/game/objects/items/devices/PDA/PDA.dm
@@ -469,7 +469,7 @@ GLOBAL_LIST_EMPTY(PDAs)
var/mob/living/U = usr
//Looking for master was kind of pointless since PDAs don't appear to have one.
- if(usr.canUseTopic(src, BE_CLOSE, FALSE, NO_TK) && !href_list["close"])
+ if(usr.canUseTopic(src, BE_CLOSE, FALSE, NO_TK, FALSE) && !href_list["close"])
add_fingerprint(U)
U.set_machine(src)
@@ -757,7 +757,7 @@ GLOBAL_LIST_EMPTY(PDAs)
var/t = stripped_input(U, "Please enter message", name)
if (!t || toff)
return
- if(!U.canUseTopic(src, BE_CLOSE))
+ if(!U.canUseTopic(src, BE_CLOSE, FALSE, NO_TK, FALSE))
return
if(emped)
t = Gibberish(t, 100)
diff --git a/code/game/objects/items/devices/laserpointer.dm b/code/game/objects/items/devices/laserpointer.dm
index 5b23f6f169..a3cfdb9177 100644
--- a/code/game/objects/items/devices/laserpointer.dm
+++ b/code/game/objects/items/devices/laserpointer.dm
@@ -116,7 +116,7 @@
//chance to actually hit the eyes depends on internal component
if(prob(effectchance * diode.rating))
S.flash_act(affect_silicon = 1)
- S.Knockdown(rand(100,200))
+ S.DefaultCombatKnockdown(rand(100,200))
to_chat(S, "Your sensors were overloaded by a laser!")
outmsg = "You overload [S] by shining [src] at [S.p_their()] sensors."
else
@@ -152,8 +152,7 @@
if(prob(50))
C.visible_message("[C] pounces on the light!","LIGHT!")
C.Move(targloc)
- C.resting = TRUE
- C.update_canmove()
+ C.set_resting(TRUE)
else
C.visible_message("[C] looks uninterested in your games.","You spot [user] shining [src] at you. How insulting!")
diff --git a/code/game/objects/items/devices/radio/electropack.dm b/code/game/objects/items/devices/radio/electropack.dm
index a173453f1c..914f2a149a 100644
--- a/code/game/objects/items/devices/radio/electropack.dm
+++ b/code/game/objects/items/devices/radio/electropack.dm
@@ -118,7 +118,7 @@
s.set_up(3, 1, L)
s.start()
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
if(master)
master.receive_signal()
@@ -192,7 +192,7 @@ Code:
s.set_up(3, 1, L)
s.start()
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
if(master)
master.receive_signal()
diff --git a/code/game/objects/items/devices/scanners.dm b/code/game/objects/items/devices/scanners.dm
index 1b8058e3d4..556080168f 100644
--- a/code/game/objects/items/devices/scanners.dm
+++ b/code/game/objects/items/devices/scanners.dm
@@ -484,7 +484,8 @@ SLIME SCANNER
set name = "Switch Verbosity"
set category = "Object"
- if(usr.stat || !usr.canmove || usr.restrained())
+ var/mob/living/L = usr
+ if(!istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
return
mode = !mode
diff --git a/code/game/objects/items/devices/traitordevices.dm b/code/game/objects/items/devices/traitordevices.dm
index 1d42198a23..4bab5a5bcd 100644
--- a/code/game/objects/items/devices/traitordevices.dm
+++ b/code/game/objects/items/devices/traitordevices.dm
@@ -44,7 +44,7 @@ effective or pretty fucking useless.
for(var/mob/living/carbon/human/M in urange(10, user, 1))
if(prob(50))
- M.Knockdown(rand(200,400))
+ M.DefaultCombatKnockdown(rand(200,400))
to_chat(M, "You feel a tremendous, paralyzing wave flood your mind.")
else
diff --git a/code/game/objects/items/granters.dm b/code/game/objects/items/granters.dm
index 24fc1043d8..0907a18fdd 100644
--- a/code/game/objects/items/granters.dm
+++ b/code/game/objects/items/granters.dm
@@ -294,7 +294,7 @@
/obj/item/book/granter/spell/knock/recoil(mob/living/user)
..()
to_chat(user,"You're knocked down!")
- user.Knockdown(40)
+ user.DefaultCombatKnockdown(40)
/obj/item/book/granter/spell/barnyard
spell = /obj/effect/proc_holder/spell/targeted/barnyardcurse
diff --git a/code/game/objects/items/grenades/flashbang.dm b/code/game/objects/items/grenades/flashbang.dm
index 67036bd604..6f79df28fe 100644
--- a/code/game/objects/items/grenades/flashbang.dm
+++ b/code/game/objects/items/grenades/flashbang.dm
@@ -31,7 +31,7 @@
M.show_message("BANG", MSG_AUDIBLE)
var/distance = get_dist(get_turf(M), source)
if(!distance || loc == M || loc == M.loc) //Stop allahu akbarring rooms with this.
- M.Knockdown(200)
+ M.DefaultCombatKnockdown(200)
M.soundbang_act(1, 200, 10, 15)
else
M.soundbang_act(1, max(200/max(1,distance), 60), rand(0, 5))
@@ -41,4 +41,4 @@
return
var/distance = get_dist(get_turf(M), source)
if(M.flash_act(affect_silicon = 1))
- M.Knockdown(max(200/max(1,distance), 60))
+ M.DefaultCombatKnockdown(max(200/max(1,distance), 60))
diff --git a/code/game/objects/items/handcuffs.dm b/code/game/objects/items/handcuffs.dm
index b4074737e5..ee25cbb985 100644
--- a/code/game/objects/items/handcuffs.dm
+++ b/code/game/objects/items/handcuffs.dm
@@ -349,7 +349,7 @@
C.update_inv_legcuffed()
SSblackbox.record_feedback("tally", "handcuffs", 1, type)
to_chat(C, "\The [src] ensnares you!")
- C.Knockdown(knockdown)
+ C.DefaultCombatKnockdown(knockdown)
/obj/item/restraints/legcuffs/bola/tactical//traitor variant
name = "reinforced bola"
diff --git a/code/game/objects/items/his_grace.dm b/code/game/objects/items/his_grace.dm
index da572d4d61..c961134244 100644
--- a/code/game/objects/items/his_grace.dm
+++ b/code/game/objects/items/his_grace.dm
@@ -92,7 +92,7 @@
master.emote("scream")
master.remove_status_effect(STATUS_EFFECT_HISGRACE)
REMOVE_TRAIT(src, TRAIT_NODROP, HIS_GRACE_TRAIT)
- master.Knockdown(60)
+ master.DefaultCombatKnockdown(60)
master.adjustBruteLoss(master.maxHealth)
playsound(master, 'sound/effects/splat.ogg', 100, 0)
else
diff --git a/code/game/objects/items/holy_weapons.dm b/code/game/objects/items/holy_weapons.dm
index 45abd4fb49..4d275e2034 100644
--- a/code/game/objects/items/holy_weapons.dm
+++ b/code/game/objects/items/holy_weapons.dm
@@ -64,16 +64,16 @@
else
playsound(src, 'sound/machines/buzz-sigh.ogg', 40, 1)
-/obj/item/holybeacon/proc/beacon_armor(mob/M)
+/obj/item/holybeacon/proc/beacon_armor(mob/living/L)
var/list/holy_armor_list = typesof(/obj/item/storage/box/holy)
var/list/display_names = list()
for(var/V in holy_armor_list)
var/atom/A = V
display_names += list(initial(A.name) = A)
- var/choice = input(M,"What holy armor kit would you like to order?","Holy Armor Theme") as null|anything in display_names
- var/turf/T = get_turf(M)
- if(!T || QDELETED(src) || !choice || M.stat || !in_range(M, src) || M.restrained() || !M.canmove || GLOB.holy_armor_type)
+ var/choice = input(L,"What holy armor kit would you like to order?","Holy Armor Theme") as null|anything in display_names
+ var/turf/T = get_turf(src)
+ if(!T || QDELETED(src) || !choice || !CHECK_MOBILITY(L, MOBILITY_USE) || !in_range(L, src) || GLOB.holy_armor_type)
return
var/index = display_names.Find(choice)
@@ -86,7 +86,7 @@
if(holy_armor_box)
qdel(src)
- M.put_in_hands(holy_armor_box)
+ L.put_in_hands(holy_armor_box)
/obj/item/storage/box/holy
name = "Templar Kit"
@@ -244,7 +244,7 @@
if(user.mind && (user.mind.isholy) && !reskinned)
reskin_holy_weapon(user)
-/obj/item/nullrod/proc/reskin_holy_weapon(mob/M)
+/obj/item/nullrod/proc/reskin_holy_weapon(mob/living/L)
if(GLOB.holy_weapon_type)
return
var/obj/item/holy_weapon
@@ -255,8 +255,8 @@
if (initial(rodtype.chaplain_spawnable))
display_names[initial(rodtype.name)] = rodtype
- var/choice = input(M,"What theme would you like for your holy weapon?","Holy Weapon Theme") as null|anything in display_names
- if(QDELETED(src) || !choice || M.stat || !in_range(M, src) || M.restrained() || !M.canmove || reskinned)
+ var/choice = input(L, "What theme would you like for your holy weapon?","Holy Weapon Theme") as null|anything in display_names
+ if(QDELETED(src) || !choice || !in_range(L, src) || !CHECK_MOBILITY(L, MOBILITY_USE) || reskinned)
return
var/A = display_names[choice] // This needs to be on a separate var as list member access is not allowed for new
@@ -269,7 +269,7 @@
if(holy_weapon)
holy_weapon.reskinned = TRUE
qdel(src)
- M.put_in_active_hand(holy_weapon)
+ L.put_in_active_hand(holy_weapon)
/obj/item/nullrod/proc/jedi_spin(mob/living/user)
for(var/i in list(NORTH,SOUTH,EAST,WEST,EAST,SOUTH,NORTH,SOUTH,EAST,WEST,EAST,SOUTH))
@@ -674,7 +674,7 @@
add_fingerprint(user)
if((HAS_TRAIT(user, TRAIT_CLUMSY)) && prob(50))
to_chat(user, "You club yourself over the head with [src].")
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
if(ishuman(user))
var/mob/living/carbon/human/H = user
H.apply_damage(2*force, BRUTE, BODY_ZONE_HEAD)
diff --git a/code/game/objects/items/hot_potato.dm b/code/game/objects/items/hot_potato.dm
index 8f1d968991..5f74830c99 100644
--- a/code/game/objects/items/hot_potato.dm
+++ b/code/game/objects/items/hot_potato.dm
@@ -71,8 +71,7 @@
if(stimulant)
if(isliving(loc))
var/mob/living/L = loc
- L.SetStun(0)
- L.SetKnockdown(0)
+ L.SetAllImmobility(0)
L.SetSleeping(0)
L.SetUnconscious(0)
L.reagents.add_reagent(/datum/reagent/medicine/muscle_stimulant, CLAMP(5 - L.reagents.get_reagent_amount(/datum/reagent/medicine/muscle_stimulant), 0, 5)) //If you don't have legs or get bola'd, tough luck!
diff --git a/code/game/objects/items/implants/implant_explosive.dm b/code/game/objects/items/implants/implant_explosive.dm
index bf8d215a11..370924063d 100644
--- a/code/game/objects/items/implants/implant_explosive.dm
+++ b/code/game/objects/items/implants/implant_explosive.dm
@@ -78,7 +78,7 @@
return
if(message && imp_in.stat == CONSCIOUS)
imp_in.visible_message("[imp_in] doubles over in pain!")
- imp_in.Knockdown(140)
+ imp_in.DefaultCombatKnockdown(140)
/obj/item/implant/explosive/proc/boom_goes_the_weasel()
explosion(get_turf(imp_in ? imp_in : src), heavy, medium, weak, weak, flame_range = weak)
diff --git a/code/game/objects/items/melee/misc.dm b/code/game/objects/items/melee/misc.dm
index bad140df9e..efe43d753b 100644
--- a/code/game/objects/items/melee/misc.dm
+++ b/code/game/objects/items/melee/misc.dm
@@ -200,7 +200,7 @@
add_fingerprint(user)
if((HAS_TRAIT(user, TRAIT_CLUMSY)) && prob(50))
to_chat(user, "You club yourself over the head.")
- user.Knockdown(60 * force)
+ user.DefaultCombatKnockdown(60 * force)
if(ishuman(user))
var/mob/living/carbon/human/H = user
H.apply_damage(2*force, BRUTE, BODY_ZONE_HEAD)
@@ -225,7 +225,7 @@
if(check_martial_counter(H, user))
return
playsound(get_turf(src), 'sound/effects/woodhit.ogg', 75, 1, -1)
- target.Knockdown(softstun_ds, TRUE, FALSE, hardstun_ds, stam_dmg)
+ target.DefaultCombatKnockdown(softstun_ds, TRUE, FALSE, hardstun_ds, stam_dmg)
log_combat(user, target, "stunned", src)
src.add_fingerprint(user)
target.visible_message("[user] has knocked down [target] with [src]!", \
diff --git a/code/game/objects/items/pneumaticCannon.dm b/code/game/objects/items/pneumaticCannon.dm
index dae4c9a137..342f756ffc 100644
--- a/code/game/objects/items/pneumaticCannon.dm
+++ b/code/game/objects/items/pneumaticCannon.dm
@@ -168,7 +168,7 @@
if(pressureSetting >= 3 && iscarbon(user))
var/mob/living/carbon/C = user
C.visible_message("[C] is thrown down by the force of the cannon!", "[src] slams into your shoulder, knocking you down!")
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
/obj/item/pneumatic_cannon/proc/fire_items(turf/target, mob/user)
if(fire_mode == PCANNON_FIREALL)
diff --git a/code/game/objects/items/religion.dm b/code/game/objects/items/religion.dm
index ac490b0122..cc466d73fc 100644
--- a/code/game/objects/items/religion.dm
+++ b/code/game/objects/items/religion.dm
@@ -64,8 +64,7 @@
/obj/item/banner/proc/inspiration(mob/living/carbon/human/H)
H.adjustBruteLoss(-15)
H.adjustFireLoss(-15)
- H.AdjustStun(-40)
- H.AdjustKnockdown(-40)
+ H.AdjustAllImmobility(-40)
H.AdjustUnconscious(-40)
playsound(H, 'sound/magic/staff_healing.ogg', 25, FALSE)
diff --git a/code/game/objects/items/robot/robot_items.dm b/code/game/objects/items/robot/robot_items.dm
index 48c16190d9..d3e966f2fa 100644
--- a/code/game/objects/items/robot/robot_items.dm
+++ b/code/game/objects/items/robot/robot_items.dm
@@ -20,7 +20,7 @@
return
user.do_attack_animation(M)
- M.Knockdown(100)
+ M.DefaultCombatKnockdown(100)
M.apply_effect(EFFECT_STUTTER, 5)
M.visible_message("[user] has prodded [M] with [src]!", \
@@ -81,8 +81,7 @@
user.visible_message("[user] hugs [M] to make [M.p_them()] feel better!", \
"You hug [M] to make [M.p_them()] feel better!")
if(M.resting && !M.recoveringstam)
- M.resting = FALSE
- M.update_canmove()
+ M.set_resting(FALSE, TRUE)
else
user.visible_message("[user] pets [M]!", \
"You pet [M]!")
@@ -100,9 +99,8 @@
else
user.visible_message("[user] hugs [M] in a firm bear-hug! [M] looks uncomfortable...", \
"You hug [M] firmly to make [M.p_them()] feel better! [M] looks uncomfortable...")
- if(M.resting && !M.recoveringstam)
- M.resting = FALSE
- M.update_canmove()
+ if(!CHECK_MOBILITY(M, MOBILITY_STAND) && !M.recoveringstam)
+ M.set_resting(FALSE, TRUE)
else
user.visible_message("[user] bops [M] on the head!", \
"You bop [M] on the head!")
@@ -114,7 +112,6 @@
M.electrocute_act(5, "[user]", safety = 1)
user.visible_message("[user] electrocutes [M] with [user.p_their()] touch!", \
"You electrocute [M] with your touch!")
- M.update_canmove()
else
if(!iscyborg(M))
M.adjustFireLoss(10)
@@ -326,7 +323,7 @@
C.stuttering += 10
C.Jitter(10)
if(2)
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
C.confused += 10
C.stuttering += 15
C.Jitter(25)
diff --git a/code/game/objects/items/robot/robot_parts.dm b/code/game/objects/items/robot/robot_parts.dm
index 54f0dc600d..6621095b72 100644
--- a/code/game/objects/items/robot/robot_parts.dm
+++ b/code/game/objects/items/robot/robot_parts.dm
@@ -317,8 +317,7 @@
O.robot_suit = src
if(!locomotion)
- O.lockcharge = 1
- O.update_canmove()
+ O.SetLockdown(TRUE)
to_chat(O, "Error: Servo motors unresponsive.")
else
@@ -356,8 +355,7 @@
forceMove(O)
O.robot_suit = src
if(!locomotion)
- O.lockcharge = TRUE
- O.update_canmove()
+ O.SetLockdown(TRUE)
else if(istype(W, /obj/item/pen))
to_chat(user, "You need to use a multitool to name [src]!")
diff --git a/code/game/objects/items/robot/robot_upgrades.dm b/code/game/objects/items/robot/robot_upgrades.dm
index 18568b3d0f..56af03139a 100644
--- a/code/game/objects/items/robot/robot_upgrades.dm
+++ b/code/game/objects/items/robot/robot_upgrades.dm
@@ -577,7 +577,7 @@
return FALSE
R.notransform = TRUE
- var/prev_lockcharge = R.lockcharge
+ var/prev_locked_down = R.locked_down
R.SetLockdown(1)
R.anchored = TRUE
var/datum/effect_system/smoke_spread/smoke = new
@@ -587,7 +587,7 @@
for(var/i in 1 to 4)
playsound(R, pick('sound/items/drill_use.ogg', 'sound/items/jaws_cut.ogg', 'sound/items/jaws_pry.ogg', 'sound/items/welder.ogg', 'sound/items/ratchet.ogg'), 80, 1, -1)
sleep(12)
- if(!prev_lockcharge)
+ if(!prev_locked_down)
R.SetLockdown(0)
R.anchored = FALSE
R.notransform = FALSE
diff --git a/code/game/objects/items/storage/bags.dm b/code/game/objects/items/storage/bags.dm
index b2fbbc8117..7a6e1e3db6 100644
--- a/code/game/objects/items/storage/bags.dm
+++ b/code/game/objects/items/storage/bags.dm
@@ -246,7 +246,8 @@
set name = "Activate Seed Extraction"
set category = "Object"
set desc = "Activate to convert your plants into plantable seeds."
- if(usr.stat || !usr.canmove || usr.restrained())
+ var/mob/living/L = usr
+ if(istype(L) && !CHECK_MOBILITY(L, MOBILITY_USE))
return
for(var/obj/item/O in contents)
seedify(O, 1)
@@ -353,7 +354,7 @@
if(ishuman(M) || ismonkey(M))
if(prob(10))
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
update_icon()
/obj/item/storage/bag/tray/update_overlays()
diff --git a/code/game/objects/items/stunbaton.dm b/code/game/objects/items/stunbaton.dm
index c48122fb0e..78ba6d4f5f 100644
--- a/code/game/objects/items/stunbaton.dm
+++ b/code/game/objects/items/stunbaton.dm
@@ -191,7 +191,7 @@
if(!disarming)
if(knockdown)
- L.Knockdown(50, override_stamdmg = 0) //knockdown
+ L.DefaultCombatKnockdown(50, override_stamdmg = 0) //knockdown
L.adjustStaminaLoss(stunpwr)
else
L.drop_all_held_items() //no knockdown/stamina damage, instead disarm.
@@ -218,7 +218,7 @@
user.visible_message("[user] accidentally hits [user.p_them()]self with [src]!", \
"You accidentally hit yourself with [src]!")
SEND_SIGNAL(user, COMSIG_LIVING_MINOR_SHOCK)
- user.Knockdown(stamforce*6)
+ user.DefaultCombatKnockdown(stamforce*6)
playsound(loc, 'sound/weapons/egloves.ogg', 50, 1, -1)
deductcharge(hitcost)
diff --git a/code/game/objects/items/teleprod.dm b/code/game/objects/items/teleprod.dm
index bab4d6a488..63bde36976 100644
--- a/code/game/objects/items/teleprod.dm
+++ b/code/game/objects/items/teleprod.dm
@@ -16,7 +16,7 @@
user.visible_message("[user] accidentally hits [user.p_them()]self with [src]!", \
"You accidentally hit yourself with [src]!")
SEND_SIGNAL(user, COMSIG_LIVING_MINOR_SHOCK)
- user.Knockdown(stamforce * 6)
+ user.DefaultCombatKnockdown(stamforce * 6)
playsound(loc, 'sound/weapons/egloves.ogg', 50, 1, -1)
if(do_teleport(user, get_turf(user), 50, channel = TELEPORT_CHANNEL_BLUESPACE))
deductcharge(hitcost)
diff --git a/code/game/objects/items/toys.dm b/code/game/objects/items/toys.dm
index 8f683b8c1c..ba51fa3d65 100644
--- a/code/game/objects/items/toys.dm
+++ b/code/game/objects/items/toys.dm
@@ -1078,8 +1078,13 @@
else
return ..()
-/obj/item/toy/cards/singlecard/attack_self(mob/user)
- if(usr.stat || !ishuman(usr) || !usr.canmove || usr.restrained())
+/obj/item/toy/cards/singlecard/attack_self(mob/living/user)
+ . = ..()
+ if(.)
+ return
+ if(!ishuman(user))
+ return
+ if(!CHECK_MOBILITY(user, MOBILITY_USE))
return
Flip()
diff --git a/code/game/objects/structures.dm b/code/game/objects/structures.dm
index 1d36b2b41b..e185defc0a 100644
--- a/code/game/objects/structures.dm
+++ b/code/game/objects/structures.dm
@@ -33,7 +33,7 @@
if(structureclimber && structureclimber != user)
user.changeNext_move(CLICK_CD_MELEE)
user.do_attack_animation(src)
- structureclimber.Knockdown(40)
+ structureclimber.DefaultCombatKnockdown(40)
structureclimber.visible_message("[structureclimber] has been knocked off [src].", "You're knocked off [src]!", "You see [structureclimber] get knocked off [src].")
/obj/structure/ui_act(action, params)
@@ -45,7 +45,8 @@
if(!climbable)
return
if(user == O && iscarbon(O))
- if(user.canmove)
+ var/mob/living/L = O
+ if(CHECK_MOBILITY(L, MOBILITY_MOVE))
climb_structure(user)
return
if(!istype(O, /obj/item) || user.get_active_held_item() != O)
diff --git a/code/game/objects/structures/beds_chairs/chair.dm b/code/game/objects/structures/beds_chairs/chair.dm
index 39fa7affa6..34b599c932 100644
--- a/code/game/objects/structures/beds_chairs/chair.dm
+++ b/code/game/objects/structures/beds_chairs/chair.dm
@@ -110,7 +110,7 @@
user.visible_message("[user] pulls [src] out from under [poordude].", "You pull [src] out from under [poordude].")
var/C = new item_chair(loc)
user.put_in_hands(C)
- poordude.Knockdown(20)//rip in peace
+ poordude.DefaultCombatKnockdown(20)//rip in peace
user.adjustStaminaLoss(5)
unbuckle_all_mobs(TRUE)
qdel(src)
@@ -377,7 +377,7 @@
if(iscarbon(target))
var/mob/living/carbon/C = target
if(C.health < C.maxHealth*0.5)
- C.Knockdown(20)
+ C.DefaultCombatKnockdown(20)
smash(user)
/obj/item/chair/greyscale
diff --git a/code/game/objects/structures/crates_lockers/closets.dm b/code/game/objects/structures/crates_lockers/closets.dm
index f95f900a48..c932dd96e8 100644
--- a/code/game/objects/structures/crates_lockers/closets.dm
+++ b/code/game/objects/structures/crates_lockers/closets.dm
@@ -431,7 +431,7 @@
"You hear a loud metal bang.")
var/mob/living/L = O
if(!issilicon(L))
- L.Knockdown(40)
+ L.DefaultCombatKnockdown(40)
O.forceMove(T)
close()
else
@@ -474,8 +474,9 @@
set category = "Object"
set name = "Toggle Open"
- if(!usr.canmove || usr.stat || usr.restrained())
- return
+ var/mob/living/L = usr
+ if(!istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
+ return FALSE
if(iscarbon(usr) || issilicon(usr) || isdrone(usr))
return attack_hand(usr)
@@ -510,7 +511,7 @@
user.visible_message("[src] begins to shake violently!", \
"You lean on the back of [src] and start pushing the door open... (this will take about [DisplayTimeText(breakout_time)].)", \
"You hear banging from [src].")
- if(do_after(user,(breakout_time), target = src))
+ if(do_after(user,(breakout_time), target = src, required_mobility_flags = MOBILITY_RESIST))
if(!user || user.stat != CONSCIOUS || user.loc != src || opened || (!locked && !welded) )
return
//we check after a while whether there is a point of resisting anymore and whether the user is capable of resisting
@@ -603,12 +604,12 @@
step_towards(user, T2)
T1 = get_turf(user)
if(T1 == T2)
- user.resting = TRUE //so people can jump into crates without slamming the lid on their head
+ user.set_resting(TRUE, TRUE)
if(!close(user))
to_chat(user, "You can't get [src] to close!")
- user.resting = FALSE
+ user.set_resting(FALSE, TRUE)
return
- user.resting = FALSE
+ user.set_resting(FALSE, TRUE)
togglelock(user)
T1.visible_message("[user] dives into [src]!")
diff --git a/code/game/objects/structures/crates_lockers/closets/cardboardbox.dm b/code/game/objects/structures/crates_lockers/closets/cardboardbox.dm
index 645d1e5d7a..ae2e1a070a 100644
--- a/code/game/objects/structures/crates_lockers/closets/cardboardbox.dm
+++ b/code/game/objects/structures/crates_lockers/closets/cardboardbox.dm
@@ -18,8 +18,8 @@
var/egged = 0
var/use_mob_movespeed = FALSE //Citadel adds snowflake box handling
-/obj/structure/closet/cardboard/relaymove(mob/user, direction)
- if(opened || move_delay || user.stat || user.IsStun() || user.IsKnockdown() || user.IsUnconscious() || !isturf(loc) || !has_gravity(loc))
+/obj/structure/closet/cardboard/relaymove(mob/living/user, direction)
+ if(opened || move_delay || !CHECK_MOBILITY(user, MOBILITY_MOVE) || !isturf(loc) || !has_gravity(loc))
return
move_delay = TRUE
var/oldloc = loc
diff --git a/code/game/objects/structures/kitchen_spike.dm b/code/game/objects/structures/kitchen_spike.dm
index ebac89579b..05a7e1c958 100644
--- a/code/game/objects/structures/kitchen_spike.dm
+++ b/code/game/objects/structures/kitchen_spike.dm
@@ -139,7 +139,7 @@
src.visible_message(text("[M] falls free of [src]!"))
unbuckle_mob(M,force=1)
M.emote("scream")
- M.AdjustKnockdown(20)
+ M.DefaultCombatKnockdown(20)
/obj/structure/kitchenspike/Destroy()
if(has_buckled_mobs())
diff --git a/code/game/objects/structures/musician.dm b/code/game/objects/structures/musician.dm
index 6ad420f57c..bdc7825feb 100644
--- a/code/game/objects/structures/musician.dm
+++ b/code/game/objects/structures/musician.dm
@@ -82,7 +82,7 @@
/datum/song/proc/shouldStopPlaying(mob/user)
if(instrumentObj)
- if(!user.canUseTopic(instrumentObj))
+ if(!user.canUseTopic(instrumentObj, TRUE, FALSE, FALSE, FALSE))
return TRUE
return !instrumentObj.anchored // add special cases to stop in subclasses
else
@@ -220,7 +220,7 @@
updateDialog(usr) // make sure updates when complete
/datum/song/Topic(href, href_list)
- if(!usr.canUseTopic(instrumentObj))
+ if(!usr.canUseTopic(instrumentObj, TRUE, FALSE, FALSE, FALSE))
usr << browse(null, "window=instrument")
usr.unset_machine()
return
diff --git a/code/game/objects/structures/petrified_statue.dm b/code/game/objects/structures/petrified_statue.dm
index 65ffb7e2e5..a8a5a577c2 100644
--- a/code/game/objects/structures/petrified_statue.dm
+++ b/code/game/objects/structures/petrified_statue.dm
@@ -49,7 +49,7 @@
if(S.mind)
if(petrified_mob)
S.mind.transfer_to(petrified_mob)
- petrified_mob.Knockdown(100)
+ petrified_mob.DefaultCombatKnockdown(100)
to_chat(petrified_mob, "You slowly come back to your senses. You are in control of yourself again!")
qdel(S)
diff --git a/code/game/objects/structures/tables_racks.dm b/code/game/objects/structures/tables_racks.dm
index 4eba21b8f9..02740ce858 100644
--- a/code/game/objects/structures/tables_racks.dm
+++ b/code/game/objects/structures/tables_racks.dm
@@ -109,8 +109,7 @@
/obj/structure/table/proc/tableplace(mob/living/user, mob/living/pushed_mob)
pushed_mob.forceMove(src.loc)
- pushed_mob.resting = TRUE
- pushed_mob.update_canmove()
+ pushed_mob.set_resting(TRUE, FALSE)
pushed_mob.visible_message("[user] places [pushed_mob] onto [src].", \
"[user] places [pushed_mob] onto [src].")
log_combat(user, pushed_mob, "placed")
@@ -128,7 +127,7 @@
pushed_mob.pass_flags &= ~PASSTABLE
if(pushed_mob.loc != loc) //Something prevented the tabling
return
- pushed_mob.Knockdown(40)
+ pushed_mob.DefaultCombatKnockdown(40)
pushed_mob.visible_message("[user] slams [pushed_mob] onto [src]!", \
"[user] slams you onto [src]!")
log_combat(user, pushed_mob, "tabled", null, "onto [src]")
@@ -138,11 +137,11 @@
SEND_SIGNAL(H, COMSIG_ADD_MOOD_EVENT, "table", /datum/mood_event/table)
/obj/structure/table/shove_act(mob/living/target, mob/living/user)
- if(!target.resting)
- target.Knockdown(SHOVE_KNOCKDOWN_TABLE)
+ if(CHECK_MOBILITY(target, MOBILITY_STAND))
+ target.DefaultCombatKnockdown(SHOVE_KNOCKDOWN_TABLE)
user.visible_message("[user.name] shoves [target.name] onto \the [src]!",
"You shove [target.name] onto \the [src]!", null, COMBAT_MESSAGE_RANGE)
- target.forceMove(src.loc)
+ target.forceMove(loc)
log_combat(user, target, "shoved", "onto [src] (table)")
return TRUE
@@ -270,7 +269,7 @@
debris -= AM
if(istype(AM, /obj/item/shard))
AM.throw_impact(L)
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
qdel(src)
/obj/structure/table/glass/deconstruct(disassembled = TRUE, wrench_disassembly = 0)
@@ -568,23 +567,20 @@
break
/obj/structure/table/optable/tablepush(mob/living/user, mob/living/pushed_mob)
- pushed_mob.forceMove(src.loc)
- pushed_mob.resting = 1
- pushed_mob.update_canmove()
+ pushed_mob.forceMove(loc)
+ pushed_mob.set_resting(TRUE, TRUE)
visible_message("[user] has laid [pushed_mob] on [src].")
check_patient()
/obj/structure/table/optable/proc/check_patient()
- var/mob/M = locate(/mob/living/carbon/human, loc)
- if(M)
- if(M.resting)
- patient = M
- return 1
+ var/mob/living/carbon/human/H = locate() in loc
+ if(H)
+ if(!CHECK_MOBILITY(H, MOBILITY_STAND))
+ patient = H
+ return TRUE
else
patient = null
- return 0
-
-
+ return FALSE
/*
* Racks
@@ -644,7 +640,7 @@
. = ..()
if(.)
return
- if(user.IsKnockdown() || user.resting || user.lying || user.get_num_legs() < 2)
+ if(CHECK_MULTIPLE_BITFIELDS(user.mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) || user.get_num_legs() < 2)
return
user.changeNext_move(CLICK_CD_MELEE)
user.do_attack_animation(src, ATTACK_EFFECT_KICK)
diff --git a/code/game/objects/structures/transit_tubes/station.dm b/code/game/objects/structures/transit_tubes/station.dm
index c386726f34..17ca178cd9 100644
--- a/code/game/objects/structures/transit_tubes/station.dm
+++ b/code/game/objects/structures/transit_tubes/station.dm
@@ -43,10 +43,10 @@
//pod insertion
-/obj/structure/transit_tube/station/MouseDrop_T(obj/structure/c_transit_tube_pod/R, mob/user)
- if(!user.canmove || user.stat || user.restrained())
+/obj/structure/transit_tube/station/MouseDrop_T(obj/structure/c_transit_tube_pod/R, mob/living/user)
+ if(!istype(user) || !CHECK_MOBILITY(user, MOBILITY_USE))
return
- if (!istype(R) || get_dist(user, src) > 1 || get_dist(src,R) > 1)
+ if(!istype(R) || get_dist(user, src) > 1 || get_dist(src,R) > 1)
return
for(var/obj/structure/transit_tube_pod/pod in loc)
return //no fun allowed
@@ -74,7 +74,7 @@
pod.visible_message("[user] starts putting [GM] into the [pod]!")
if(do_after(user, 15, target = src))
if(open_status == STATION_TUBE_OPEN && GM && user.grab_state >= GRAB_AGGRESSIVE && user.pulling == GM && !GM.buckled && !GM.has_buckled_mobs())
- GM.Knockdown(100)
+ GM.DefaultCombatKnockdown(100)
src.Bumped(GM)
break
else
diff --git a/code/game/objects/structures/traps.dm b/code/game/objects/structures/traps.dm
index 3f559382f0..fa9c052aa3 100644
--- a/code/game/objects/structures/traps.dm
+++ b/code/game/objects/structures/traps.dm
@@ -83,7 +83,7 @@
/obj/structure/trap/stun/trap_effect(mob/living/L)
L.electrocute_act(30, src, safety=1) // electrocute act does a message.
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
/obj/structure/trap/fire
name = "flame trap"
@@ -92,7 +92,7 @@
/obj/structure/trap/fire/trap_effect(mob/living/L)
to_chat(L, "Spontaneous combustion!")
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
/obj/structure/trap/fire/flare()
..()
@@ -106,7 +106,7 @@
/obj/structure/trap/chill/trap_effect(mob/living/L)
to_chat(L, "You're frozen solid!")
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
L.adjust_bodytemperature(-300)
L.apply_status_effect(/datum/status_effect/freon)
@@ -119,7 +119,7 @@
/obj/structure/trap/damage/trap_effect(mob/living/L)
to_chat(L, "The ground quakes beneath your feet!")
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
L.adjustBruteLoss(35)
/obj/structure/trap/damage/flare()
@@ -147,7 +147,7 @@
/obj/structure/trap/cult/trap_effect(mob/living/L)
to_chat(L, "With a crack, the hostile constructs come out of hiding, stunning you!")
L.electrocute_act(10, src, safety = TRUE) // electrocute act does a message.
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
new /mob/living/simple_animal/hostile/construct/proteon/hostile(loc)
new /mob/living/simple_animal/hostile/construct/proteon/hostile(loc)
- QDEL_IN(src, 30)
\ No newline at end of file
+ QDEL_IN(src, 30)
diff --git a/code/game/objects/structures/watercloset.dm b/code/game/objects/structures/watercloset.dm
index bd86255377..bdef4ab46d 100644
--- a/code/game/objects/structures/watercloset.dm
+++ b/code/game/objects/structures/watercloset.dm
@@ -529,7 +529,7 @@
if(B.cell.charge > 0 && B.status == 1)
flick("baton_active", src)
var/stunforce = B.stamforce
- user.Knockdown(stunforce * 2)
+ user.DefaultCombatKnockdown(stunforce * 2)
user.stuttering = stunforce/20
B.deductcharge(B.hitcost)
user.visible_message("[user] shocks [user.p_them()]self while attempting to wash the active [B.name]!", \
diff --git a/code/game/objects/structures/windoor_assembly.dm b/code/game/objects/structures/windoor_assembly.dm
index 7f039598cf..e824567b50 100644
--- a/code/game/objects/structures/windoor_assembly.dm
+++ b/code/game/objects/structures/windoor_assembly.dm
@@ -343,7 +343,8 @@
set name = "Flip Windoor Assembly"
set category = "Object"
set src in oview(1)
- if(usr.stat || !usr.canmove || usr.restrained())
+ var/mob/living/L = usr
+ if(!CHECK_MOBILITY(L, MOBILITY_PULL))
return
if(facing == "l")
@@ -354,4 +355,3 @@
to_chat(usr, "The windoor will now slide to the left.")
update_icon()
- return
diff --git a/code/game/turfs/open.dm b/code/game/turfs/open.dm
index c4c7ab2d7b..066249505d 100644
--- a/code/game/turfs/open.dm
+++ b/code/game/turfs/open.dm
@@ -272,7 +272,7 @@
var/olddir = C.dir
if(!(lube & SLIDE_ICE))
- C.Knockdown(knockdown_amount)
+ C.DefaultCombatKnockdown(knockdown_amount)
C.stop_pulling()
else
C.Stun(20)
diff --git a/code/modules/admin/verbs/bluespacearty.dm b/code/modules/admin/verbs/bluespacearty.dm
index 97248b572b..2910d6dd85 100644
--- a/code/modules/admin/verbs/bluespacearty.dm
+++ b/code/modules/admin/verbs/bluespacearty.dm
@@ -21,6 +21,6 @@
target.gib(1, 1)
else
target.adjustBruteLoss(min(99,(target.health - 1)))
- target.Knockdown(400)
+ target.DefaultCombatKnockdown(400)
target.stuttering = 20
diff --git a/code/modules/admin/verbs/borgpanel.dm b/code/modules/admin/verbs/borgpanel.dm
index c0445d588d..8cfd53b300 100644
--- a/code/modules/admin/verbs/borgpanel.dm
+++ b/code/modules/admin/verbs/borgpanel.dm
@@ -47,7 +47,7 @@
"emagged" = borg.emagged,
"active_module" = "[borg.module.type]",
"lawupdate" = borg.lawupdate,
- "lockdown" = borg.lockcharge,
+ "lockdown" = borg.locked_down,
"scrambledcodes" = borg.scrambledcodes
)
.["upgrades"] = list()
@@ -122,8 +122,8 @@
message_admins("[key_name_admin(user)] disabled lawsync on [ADMIN_LOOKUPFLW(borg)].")
log_admin("[key_name(user)] disabled lawsync on [key_name(borg)].")
if ("toggle_lockdown")
- borg.SetLockdown(!borg.lockcharge)
- if (borg.lockcharge)
+ borg.SetLockdown(!borg.locked_down)
+ if (borg.locked_down)
message_admins("[key_name_admin(user)] locked down [ADMIN_LOOKUPFLW(borg)].")
log_admin("[key_name(user)] locked down [key_name(borg)].")
else
diff --git a/code/modules/antagonists/abductor/equipment/abduction_gear.dm b/code/modules/antagonists/abductor/equipment/abduction_gear.dm
index 332329a221..c2a3f953f5 100644
--- a/code/modules/antagonists/abductor/equipment/abduction_gear.dm
+++ b/code/modules/antagonists/abductor/equipment/abduction_gear.dm
@@ -116,14 +116,13 @@
var/mob/living/carbon/human/M = loc
M.adjustStaminaLoss(-75)
M.SetUnconscious(0)
- M.SetStun(0)
- M.SetKnockdown(0)
+ M.SetAllImmobility(0)
combat_cooldown = 0
START_PROCESSING(SSobj, src)
/obj/item/clothing/suit/armor/abductor/vest/process()
combat_cooldown++
- if(combat_cooldown==initial(combat_cooldown))
+ if(combat_cooldown == initial(combat_cooldown))
STOP_PROCESSING(SSobj, src)
/obj/item/clothing/suit/armor/abductor/Destroy()
@@ -512,7 +511,7 @@
L.lastattackerckey = user.ckey
L.adjustStaminaLoss(35) //because previously it took 5-6 hits to actually "incapacitate" someone for the purposes of the sleep inducement
- L.Knockdown(140)
+ L.DefaultCombatKnockdown(140)
L.apply_effect(EFFECT_STUTTER, 7)
SEND_SIGNAL(L, COMSIG_LIVING_MINOR_SHOCK)
diff --git a/code/modules/antagonists/bloodsucker/bloodsucker_powers.dm b/code/modules/antagonists/bloodsucker/bloodsucker_powers.dm
index 626ad43b10..507e1f2739 100644
--- a/code/modules/antagonists/bloodsucker/bloodsucker_powers.dm
+++ b/code/modules/antagonists/bloodsucker/bloodsucker_powers.dm
@@ -96,7 +96,7 @@
// Incap?
if(must_be_capacitated)
var/mob/living/L = owner
- if (L.incapacitated(TRUE, TRUE) || L.resting && !can_be_immobilized)
+ if (L.incapacitated(TRUE, TRUE) || !CHECK_MOBILITY(L, MOBILITY_STAND) && !can_be_immobilized)
if(display_error)
to_chat(owner, "Not while you're incapacitated!")
return FALSE
diff --git a/code/modules/antagonists/bloodsucker/items/bloodsucker_stake.dm b/code/modules/antagonists/bloodsucker/items/bloodsucker_stake.dm
index b7c90523b6..b69b851990 100644
--- a/code/modules/antagonists/bloodsucker/items/bloodsucker_stake.dm
+++ b/code/modules/antagonists/bloodsucker/items/bloodsucker_stake.dm
@@ -1,9 +1,5 @@
-
-
// organ_internal.dm -- /obj/item/organ
-
-
// Do I have a stake in my heart?
/mob/living/AmStaked()
var/obj/item/bodypart/BP = get_bodypart("chest")
@@ -13,16 +9,14 @@
if (istype(I,/obj/item/stake/))
return TRUE
return FALSE
+
/mob/proc/AmStaked()
return FALSE
-
/mob/living/proc/StakeCanKillMe()
return IsSleeping() || stat >= UNCONSCIOUS || blood_volume <= 0 || HAS_TRAIT(src, TRAIT_DEATHCOMA) // NOTE: You can't go to sleep in a coffin with a stake in you.
-
-///obj/item/weapon/melee/stake
-/obj/item/stake/
+/obj/item/stake
name = "wooden stake"
desc = "A simple wooden stake carved to a sharp point."
icon = 'icons/obj/items_and_weapons.dmi'
@@ -112,8 +106,7 @@
// Can this target be staked? If someone stands up before this is complete, it fails. Best used on someone stationary.
/mob/living/carbon/proc/can_be_staked()
- //return resting || IsKnockdown() || IsUnconscious() || (stat && (stat != SOFT_CRIT || pulledby)) || (has_trait(TRAIT_FAKEDEATH)) || resting || IsStun() || IsFrozen() || (pulledby && pulledby.grab_state >= GRAB_NECK)
- return (resting || lying || IsUnconscious() || pulledby && pulledby.grab_state >= GRAB_NECK)
+ return !CHECK_MOBILITY(src, MOBILITY_STAND)
// ABOVE: Taken from update_mobility() in living.dm
/obj/item/stake/hardened
diff --git a/code/modules/antagonists/bloodsucker/objects/bloodsucker_crypt.dm b/code/modules/antagonists/bloodsucker/objects/bloodsucker_crypt.dm
index 9e46203483..db286dd6fe 100644
--- a/code/modules/antagonists/bloodsucker/objects/bloodsucker_crypt.dm
+++ b/code/modules/antagonists/bloodsucker/objects/bloodsucker_crypt.dm
@@ -205,7 +205,7 @@
buckled_mob.pixel_y = buckled_mob.get_standard_pixel_y_offset(180)
src.visible_message(text("[buckled_mob][buckled_mob.stat==DEAD?"'s corpse":""] slides off of the rack."))
density = FALSE
- buckled_mob.AdjustKnockdown(30)
+ buckled_mob.DefaultCombatKnockdown(30)
update_icon()
useLock = FALSE // Failsafe
diff --git a/code/modules/antagonists/bloodsucker/powers/brawn.dm b/code/modules/antagonists/bloodsucker/powers/brawn.dm
index 712a15dff9..cf0393ff3a 100644
--- a/code/modules/antagonists/bloodsucker/powers/brawn.dm
+++ b/code/modules/antagonists/bloodsucker/powers/brawn.dm
@@ -72,8 +72,7 @@
if(rand(5 + powerlevel) >= 5)
target.visible_message("[user] lands a vicious punch, sending [target] away!", \
"[user] has landed a horrifying punch on you, sending you flying!!", null, COMBAT_MESSAGE_RANGE)
- target.Knockdown(min(5, rand(10, 10 * powerlevel)) )
-
+ target.DefaultCombatKnockdown(min(5, rand(10, 10 * powerlevel)) )
// Attack!
playsound(get_turf(target), 'sound/weapons/punch4.ogg', 60, 1, -1)
user.do_attack_animation(target, ATTACK_EFFECT_SMASH)
@@ -145,7 +144,7 @@
// Knock Down (if Living)
if (isliving(M))
var/mob/living/L = M
- L.Knockdown(pull_power * 10 + 20)
+ L.DefaultCombatKnockdown(pull_power * 10 + 20)
// Knock Back (before Knockdown, which probably cancels pull)
var/send_dir = get_dir(owner, M)
var/turf/T = get_ranged_target_turf(M, send_dir, pull_power)
diff --git a/code/modules/antagonists/bloodsucker/powers/feed.dm b/code/modules/antagonists/bloodsucker/powers/feed.dm
index f9ff31d94a..bbce221d91 100644
--- a/code/modules/antagonists/bloodsucker/powers/feed.dm
+++ b/code/modules/antagonists/bloodsucker/powers/feed.dm
@@ -306,7 +306,7 @@
// Bloodsuckers not affected by "the Kiss" of another vampire
if(!target.mind || !target.mind.has_antag_datum(ANTAG_DATUM_BLOODSUCKER))
target.Unconscious(50,0)
- target.Knockdown(40 + 5 * level_current,1)
+ target.DefaultCombatKnockdown(40 + 5 * level_current,1)
// NOTE: THis is based on level of power!
if(ishuman(target))
target.adjustStaminaLoss(5, forced = TRUE)// Base Stamina Damage
@@ -321,4 +321,4 @@
// My mouth is no longer full
REMOVE_TRAIT(owner, TRAIT_MUTE, "bloodsucker_feed")
// Let me move immediately
- user.update_canmove()
+ user.update_mobility()
diff --git a/code/modules/antagonists/bloodsucker/powers/go_home.dm b/code/modules/antagonists/bloodsucker/powers/go_home.dm
index 3fa8a07299..4788d7639e 100644
--- a/code/modules/antagonists/bloodsucker/powers/go_home.dm
+++ b/code/modules/antagonists/bloodsucker/powers/go_home.dm
@@ -100,8 +100,8 @@
var/mob/living/simple_animal/SA = pick(/mob/living/simple_animal/mouse,/mob/living/simple_animal/mouse,/mob/living/simple_animal/mouse, /mob/living/simple_animal/hostile/retaliate/bat) //prob(300) /mob/living/simple_animal/mouse,
new SA (owner.loc)
// TELEPORT: Move to Coffin & Close it!
+ user.set_resting(TRUE, TRUE, FALSE)
do_teleport(owner, bloodsuckerdatum.coffin, no_effects = TRUE, forced = TRUE, channel = TELEPORT_CHANNEL_QUANTUM)
- user.resting = TRUE
user.Stun(30,1)
// CLOSE LID: If fail, force me in.
if(!bloodsuckerdatum.coffin.close(owner))
diff --git a/code/modules/antagonists/bloodsucker/powers/haste.dm b/code/modules/antagonists/bloodsucker/powers/haste.dm
index 47c93b794e..143950b32f 100644
--- a/code/modules/antagonists/bloodsucker/powers/haste.dm
+++ b/code/modules/antagonists/bloodsucker/powers/haste.dm
@@ -76,16 +76,17 @@
sleep(speed)
UnregisterSignal(owner, COMSIG_MOVABLE_MOVED)
hit = null
- user.update_canmove()
+ user.update_mobility()
/datum/action/bloodsucker/targeted/haste/DeactivatePower(mob/living/user = owner, mob/living/target)
..() // activate = FALSE
- user.update_canmove()
+ user.update_mobility()
/datum/action/bloodsucker/targeted/haste/proc/on_move()
for(var/mob/living/L in dview(1, get_turf(owner)))
if(!hit[L] && (L != owner))
hit[L] = TRUE
playsound(L, "sound/weapons/punch[rand(1,4)].ogg", 15, 1, -1)
- L.Knockdown(10 + level_current * 5, override_hardstun = 0.1)
+ L.DefaultCombatKnockdown(10 + level_current * 5)
+ L.Paralyze(0.1)
L.spin(10, 1)
diff --git a/code/modules/antagonists/bloodsucker/powers/lunge.dm b/code/modules/antagonists/bloodsucker/powers/lunge.dm
index 12fc51d300..cc9363bbaf 100644
--- a/code/modules/antagonists/bloodsucker/powers/lunge.dm
+++ b/code/modules/antagonists/bloodsucker/powers/lunge.dm
@@ -52,6 +52,7 @@
// set waitfor = FALSE <---- DONT DO THIS!We WANT this power to hold up ClickWithPower(), so that we can unlock the power when it's done.
var/mob/living/carbon/target = A
var/turf/T = get_turf(target)
+ var/mob/living/L = owner
// Clear Vars
owner.pulling = null
// Will we Knock them Down?
@@ -63,7 +64,7 @@
owner.playsound_local(owner, 'sound/bloodsucker/lunge_warn.ogg', 60, FALSE, pressure_affected = FALSE) // audio feedback to the user
if(do_mob(owner, owner, 7, TRUE, TRUE))
walk_towards(owner, T, 0.1, 10) // yes i know i shouldn't use this but i don't know how to work in anything better
- if(get_turf(owner) != T && !(isliving(target) && target.Adjacent(owner)) && owner.incapacitated() && owner.resting)
+ if(get_turf(owner) != T && !(isliving(target) && target.Adjacent(owner)) && owner.incapacitated() && !CHECK_MOBILITY(L, MOBILITY_STAND))
var/send_dir = get_dir(owner, T)
new /datum/forced_movement(owner, get_ranged_target_turf(owner, send_dir, 1), 1, FALSE)
owner.spin(10)
@@ -84,4 +85,4 @@
/datum/action/bloodsucker/targeted/lunge/DeactivatePower(mob/living/user = owner, mob/living/target)
..() // activate = FALSE
- user.update_canmove()
+ user.update_mobility()
diff --git a/code/modules/antagonists/bloodsucker/powers/mesmerize.dm b/code/modules/antagonists/bloodsucker/powers/mesmerize.dm
index 8699e43854..d5354c1af9 100644
--- a/code/modules/antagonists/bloodsucker/powers/mesmerize.dm
+++ b/code/modules/antagonists/bloodsucker/powers/mesmerize.dm
@@ -82,7 +82,7 @@
to_chat(owner, "You must be facing your victim.")
return FALSE
// Check: Target facing me?
- if(!target.resting && !is_A_facing_B(target,owner))
+ if (CHECK_MOBILITY(target, MOBILITY_STAND) && !is_A_facing_B(target,owner))
if(display_error)
to_chat(owner, "Your victim must be facing you to see into your eyes.")
return FALSE
diff --git a/code/modules/antagonists/changeling/powers/fakedeath.dm b/code/modules/antagonists/changeling/powers/fakedeath.dm
index 8ed5b5e39c..da626bcf1c 100644
--- a/code/modules/antagonists/changeling/powers/fakedeath.dm
+++ b/code/modules/antagonists/changeling/powers/fakedeath.dm
@@ -18,7 +18,6 @@
user.tod = STATION_TIME_TIMESTAMP("hh:mm:ss", world.time)
user.fakedeath("changeling") //play dead
user.update_stat()
- user.update_canmove()
addtimer(CALLBACK(src, .proc/ready_to_regenerate, user), LING_FAKEDEATH_TIME, TIMER_UNIQUE)
return TRUE
diff --git a/code/modules/antagonists/changeling/powers/headcrab.dm b/code/modules/antagonists/changeling/powers/headcrab.dm
index 4ef0d2f240..867f160081 100644
--- a/code/modules/antagonists/changeling/powers/headcrab.dm
+++ b/code/modules/antagonists/changeling/powers/headcrab.dm
@@ -30,7 +30,7 @@
H.confused += 3
for(var/mob/living/silicon/S in range(2,user))
to_chat(S, "Your sensors are disabled by a shower of blood!")
- S.Knockdown(60)
+ S.DefaultCombatKnockdown(60)
var/turf = get_turf(user)
user.gib()
. = TRUE
diff --git a/code/modules/antagonists/changeling/powers/shriek.dm b/code/modules/antagonists/changeling/powers/shriek.dm
index 65e58ae65b..3de220dbcb 100644
--- a/code/modules/antagonists/changeling/powers/shriek.dm
+++ b/code/modules/antagonists/changeling/powers/shriek.dm
@@ -24,7 +24,7 @@
if(issilicon(M))
SEND_SOUND(M, sound('sound/weapons/flash.ogg'))
- M.Knockdown(rand(100,200))
+ M.DefaultCombatKnockdown(rand(100,200))
for(var/obj/machinery/light/L in range(4, user))
L.on = 1
diff --git a/code/modules/antagonists/changeling/powers/strained_muscles.dm b/code/modules/antagonists/changeling/powers/strained_muscles.dm
index 1f25e06324..a98700683e 100644
--- a/code/modules/antagonists/changeling/powers/strained_muscles.dm
+++ b/code/modules/antagonists/changeling/powers/strained_muscles.dm
@@ -26,7 +26,7 @@
changeling.chem_recharge_slowdown -= 0.5
if(stacks >= 20)
to_chat(user, "We collapse in exhaustion.")
- user.Knockdown(60)
+ user.DefaultCombatKnockdown(60)
user.emote("gasp")
INVOKE_ASYNC(src, .proc/muscle_loop, user)
@@ -40,7 +40,7 @@
if(user.stat != CONSCIOUS || user.staminaloss >= 90)
active = !active
to_chat(user, "Our muscles relax without the energy to strengthen them.")
- user.Knockdown(40)
+ user.DefaultCombatKnockdown(40)
user.remove_movespeed_modifier(MOVESPEED_ID_CHANGELING_MUSCLES)
changeling.chem_recharge_slowdown -= 0.5
break
diff --git a/code/modules/antagonists/clockcult/clock_effects/clock_sigils.dm b/code/modules/antagonists/clockcult/clock_effects/clock_sigils.dm
index eb7f83735d..1b4d26ac86 100644
--- a/code/modules/antagonists/clockcult/clock_effects/clock_sigils.dm
+++ b/code/modules/antagonists/clockcult/clock_effects/clock_sigils.dm
@@ -80,7 +80,7 @@
if(iscultist(L)) //No longer stuns cultists, instead sets them on fire and burns them
to_chat(L, "\"Watch your step, wretch.\"")
L.adjustFireLoss(10)
- L.Knockdown(20, FALSE)
+ L.DefaultCombatKnockdown(20, FALSE)
L.adjust_fire_stacks(5) //Burn!
L.IgniteMob()
else
@@ -155,7 +155,7 @@
if(brutedamage || burndamage)
L.adjustBruteLoss(-(brutedamage * 0.25))
L.adjustFireLoss(-(burndamage * 0.25))
- L.Knockdown(50) //Completely defenseless for five seconds - mainly to give them time to read over the information they've just been presented with
+ L.DefaultCombatKnockdown(50) //Completely defenseless for five seconds - mainly to give them time to read over the information they've just been presented with
if(iscarbon(L))
var/mob/living/carbon/C = L
C.silent += 5
diff --git a/code/modules/antagonists/clockcult/clock_helpers/slab_abilities.dm b/code/modules/antagonists/clockcult/clock_helpers/slab_abilities.dm
index ee1a1233d2..c7c9c42ee9 100644
--- a/code/modules/antagonists/clockcult/clock_helpers/slab_abilities.dm
+++ b/code/modules/antagonists/clockcult/clock_helpers/slab_abilities.dm
@@ -196,7 +196,7 @@
if(!iscultist(L))
L.visible_message("[L]'s eyes blaze with brilliant light!", \
"Your vision suddenly screams with white-hot light!")
- L.Knockdown(15, TRUE, FALSE, 15)
+ L.DefaultCombatKnockdown(15, TRUE, FALSE, 15)
L.apply_status_effect(STATUS_EFFECT_KINDLE)
L.flash_act(1, 1)
if(issilicon(target))
diff --git a/code/modules/antagonists/clockcult/clock_items/clock_weapons/ratvarian_spear.dm b/code/modules/antagonists/clockcult/clock_items/clock_weapons/ratvarian_spear.dm
index 05516cc6a2..4a10862e28 100644
--- a/code/modules/antagonists/clockcult/clock_items/clock_weapons/ratvarian_spear.dm
+++ b/code/modules/antagonists/clockcult/clock_items/clock_weapons/ratvarian_spear.dm
@@ -57,15 +57,15 @@
else if(!..())
if(!L.anti_magic_check())
if(issilicon(L))
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
else if(iscultist(L))
L.confused += CLAMP(10 - L.confused, 0, 5) // Spearthrow now confuses enemy cultists + just deals extra damage / sets on fire instead of hardstunning + damage
to_chat(L, "[src] crashes into you with burning force, sending you reeling!")
L.adjust_fire_stacks(2)
- L.Knockdown(1)
+ L.DefaultCombatKnockdown(1)
L.IgniteMob()
else
- L.Knockdown(40)
+ L.DefaultCombatKnockdown(40)
GLOB.clockwork_vitality += L.adjustFireLoss(bonus_burn * 3) //normally a total of 40 damage, 70 with ratvar
break_spear(T)
else
diff --git a/code/modules/antagonists/clockcult/clock_items/judicial_visor.dm b/code/modules/antagonists/clockcult/clock_items/judicial_visor.dm
index 644d9eedd5..6a53097922 100644
--- a/code/modules/antagonists/clockcult/clock_items/judicial_visor.dm
+++ b/code/modules/antagonists/clockcult/clock_items/judicial_visor.dm
@@ -176,7 +176,7 @@
var/datum/status_effect/belligerent/B = C.apply_status_effect(STATUS_EFFECT_BELLIGERENT)
if(!QDELETED(B))
B.duration = world.time + 30
- C.Knockdown(5) //knocks down for half a second if affected
+ C.DefaultCombatKnockdown(5) //knocks down for half a second if affected
sleep(!GLOB.ratvar_approaches ? 16 : 10)
name = "judicial blast"
layer = ABOVE_ALL_MOB_LAYER
@@ -196,7 +196,7 @@
L.visible_message("Strange energy flows into [L]'s [I.name]!", \
"Your [I.name] shields you from [src]!")
continue
- L.Knockdown(15) //knocks down briefly when exploding
+ L.DefaultCombatKnockdown(15) //knocks down briefly when exploding
if(!iscultist(L))
L.visible_message("[L] is struck by a judicial explosion!", \
"[!issilicon(L) ? "An unseen force slams you into the ground!" : "ERROR: Motor servos disabled by external source!"]")
diff --git a/code/modules/antagonists/clockcult/clock_structures/taunting_trail.dm b/code/modules/antagonists/clockcult/clock_structures/taunting_trail.dm
index 1158b02a4c..98b3c32b0f 100644
--- a/code/modules/antagonists/clockcult/clock_structures/taunting_trail.dm
+++ b/code/modules/antagonists/clockcult/clock_structures/taunting_trail.dm
@@ -57,5 +57,5 @@
L.confused = min(L.confused + 15, 50)
L.dizziness = min(L.dizziness + 15, 50)
if(L.confused >= 25)
- L.Knockdown(FLOOR(L.confused * 0.8, 1))
+ L.DefaultCombatKnockdown(FLOOR(L.confused * 0.8, 1))
take_damage(max_integrity)
diff --git a/code/modules/antagonists/clockcult/clock_structures/traps/brass_skewer.dm b/code/modules/antagonists/clockcult/clock_structures/traps/brass_skewer.dm
index 2f0db73bfc..a4b19f2d40 100644
--- a/code/modules/antagonists/clockcult/clock_structures/traps/brass_skewer.dm
+++ b/code/modules/antagonists/clockcult/clock_structures/traps/brass_skewer.dm
@@ -22,7 +22,7 @@
if(buckled_mobs && LAZYLEN(buckled_mobs))
var/mob/living/L = buckled_mobs[1]
if(iscarbon(L))
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
L.visible_message("[L] is maimed as the skewer shatters while still in [L.p_their()] body!")
L.adjustBruteLoss(15)
unbuckle_mob(L)
@@ -117,6 +117,6 @@
return
skewee.visible_message("[skewee] comes free of [src] with a squelching pop!", \
"You come free of [src]!")
- skewee.Knockdown(30)
+ skewee.DefaultCombatKnockdown(30)
playsound(skewee, 'sound/misc/desceration-03.ogg', 50, TRUE)
unbuckle_mob(skewee)
diff --git a/code/modules/antagonists/cult/blood_magic.dm b/code/modules/antagonists/cult/blood_magic.dm
index 636061783e..9a086b75a2 100644
--- a/code/modules/antagonists/cult/blood_magic.dm
+++ b/code/modules/antagonists/cult/blood_magic.dm
@@ -446,7 +446,7 @@
var/atom/throw_target = get_edge_target_turf(L, user.dir)
L.throw_at(throw_target, 7, 1, user)
else if(!iscultist(L))
- L.Knockdown(160)
+ L.DefaultCombatKnockdown(160)
L.adjustStaminaLoss(140) //Ensures hard stamcrit
L.flash_act(1,1)
if(issilicon(target))
diff --git a/code/modules/antagonists/cult/cult_items.dm b/code/modules/antagonists/cult/cult_items.dm
index 743d3cfc9a..3dc199b56d 100644
--- a/code/modules/antagonists/cult/cult_items.dm
+++ b/code/modules/antagonists/cult/cult_items.dm
@@ -50,7 +50,7 @@
/obj/item/melee/cultblade/attack(mob/living/target, mob/living/carbon/human/user)
if(!iscultist(user))
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
user.dropItemToGround(src, TRUE)
user.visible_message("A powerful force shoves [user] away from [target]!", \
"\"You shouldn't play with sharp things. You'll poke someone's eye out.\"")
@@ -149,7 +149,7 @@
user.emote("scream")
user.apply_damage(30, BRUTE, pick(BODY_ZONE_L_ARM, BODY_ZONE_R_ARM))
user.dropItemToGround(src, TRUE)
- user.Knockdown(50)
+ user.DefaultCombatKnockdown(50)
return
force = initial(force)
jaunt.Grant(user, src)
@@ -406,7 +406,7 @@
to_chat(user, "An overwhelming sense of nausea overpowers you!")
user.dropItemToGround(src, TRUE)
user.Dizzy(30)
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
else
to_chat(user, "\"Trying to use things you don't own is bad, you know.\"")
to_chat(user, "The armor squeezes at your body!")
@@ -458,7 +458,7 @@
to_chat(user, "An overwhelming sense of nausea overpowers you!")
user.dropItemToGround(src, TRUE)
user.Dizzy(30)
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
else
to_chat(user, "\"Trying to use things you don't own is bad, you know.\"")
to_chat(user, "The robes squeeze at your body!")
@@ -479,7 +479,7 @@
to_chat(user, "\"You want to be blind, do you?\"")
user.dropItemToGround(src, TRUE)
user.Dizzy(30)
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
user.blind_eyes(30)
/obj/item/reagent_containers/glass/beaker/unholywater
@@ -500,7 +500,7 @@
/obj/item/shuttle_curse/attack_self(mob/living/user)
if(!iscultist(user))
user.dropItemToGround(src, TRUE)
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
to_chat(user, "A powerful force shoves you away from [src]!")
return
if(curselimit > 1)
@@ -706,10 +706,10 @@
if(is_servant_of_ratvar(L))
to_chat(L, "\"Kneel for me, scum\"")
L.confused += CLAMP(10 - L.confused, 0, 5) //confuses and lightly knockdowns + damages hostile cultists instead of hardstunning like before
- L.Knockdown(15)
+ L.DefaultCombatKnockdown(15)
L.adjustBruteLoss(10)
else
- L.Knockdown(50)
+ L.DefaultCombatKnockdown(50)
break_spear(T)
else
..()
@@ -844,7 +844,7 @@
INVOKE_ASYNC(src, .proc/pewpew, user, params)
var/obj/structure/emergency_shield/invoker/N = new(user.loc)
if(do_after(user, 90, target = user))
- user.Knockdown(40)
+ user.DefaultCombatKnockdown(40)
to_chat(user, "You have exhausted the power of this spell!")
firing = FALSE
if(N)
@@ -909,7 +909,7 @@
else
var/mob/living/L = target
if(L.density)
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
L.adjustBruteLoss(45)
playsound(L, 'sound/hallucinations/wail.ogg', 50, 1)
L.emote("scream")
@@ -945,7 +945,7 @@
T.visible_message("The sheer force from [P] shatters the mirror shield!")
new /obj/effect/temp_visual/cult/sparks(T)
playsound(T, 'sound/effects/glassbr3.ogg', 100)
- owner.Knockdown(25)
+ owner.DefaultCombatKnockdown(25)
qdel(src)
return FALSE
if(P.is_reflectable)
@@ -1002,9 +1002,9 @@
else if(!..())
if(!L.anti_magic_check())
if(is_servant_of_ratvar(L))
- L.Knockdown(60)
+ L.DefaultCombatKnockdown(60)
else
- L.Knockdown(30)
+ L.DefaultCombatKnockdown(30)
if(D.thrower)
for(var/mob/living/Next in orange(2, T))
if(!Next.density || iscultist(Next))
diff --git a/code/modules/antagonists/cult/runes.dm b/code/modules/antagonists/cult/runes.dm
index 0111334748..3d27fa942b 100644
--- a/code/modules/antagonists/cult/runes.dm
+++ b/code/modules/antagonists/cult/runes.dm
@@ -219,7 +219,7 @@ structure_check() searches for nearby cultist structures required for the invoca
L.visible_message("[L]'s eyes glow a defiant yellow!", \
"\"Stop resisting. You will be mi-\"\n\
\"Give up and you will feel pain unlike anything you've ever felt!\"")
- L.Knockdown(80)
+ L.DefaultCombatKnockdown(80)
else if(is_convertable)
do_convert(L, invokers)
else
@@ -908,7 +908,7 @@ structure_check() searches for nearby cultist structures required for the invoca
if(affecting.key)
affecting.visible_message("[affecting] slowly relaxes, the glow around [affecting.p_them()] dimming.", \
"You are re-united with your physical form. [src] releases its hold over you.")
- affecting.Knockdown(40)
+ affecting.DefaultCombatKnockdown(40)
break
if(affecting.health <= 10)
to_chat(G, "Your body can no longer sustain the connection!")
@@ -970,7 +970,7 @@ structure_check() searches for nearby cultist structures required for the invoca
playsound(T, 'sound/magic/enter_blood.ogg', 100, 1)
visible_message("A colossal shockwave of energy bursts from the rune, disintegrating it in the process!")
for(var/mob/living/L in range(src, 3))
- L.Knockdown(30)
+ L.DefaultCombatKnockdown(30)
empulse(T, 0.42*(intensity), 1)
var/list/images = list()
var/zmatch = T.z
diff --git a/code/modules/antagonists/devil/devil_helpers.dm b/code/modules/antagonists/devil/devil_helpers.dm
index 4d0a781570..d3445eac0f 100644
--- a/code/modules/antagonists/devil/devil_helpers.dm
+++ b/code/modules/antagonists/devil/devil_helpers.dm
@@ -32,7 +32,7 @@
if(BANE_HARVEST)
if(istype(weapon, /obj/item/reagent_containers/food/snacks/grown/))
visible_message("The spirits of the harvest aid in the exorcism.", "The harvest spirits are harming you.")
- Knockdown(40)
+ DefaultCombatKnockdown(40)
qdel(weapon)
return 2
return 1
\ No newline at end of file
diff --git a/code/modules/antagonists/swarmer/swarmer.dm b/code/modules/antagonists/swarmer/swarmer.dm
index 99d12972d8..b3cf7dbe41 100644
--- a/code/modules/antagonists/swarmer/swarmer.dm
+++ b/code/modules/antagonists/swarmer/swarmer.dm
@@ -586,7 +586,7 @@
playsound(loc,'sound/effects/snap.ogg',50, 1, -1)
L.electrocute_act(0, src, 1, 1, 1)
if(iscyborg(L))
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
qdel(src)
..()
diff --git a/code/modules/antagonists/wizard/equipment/artefact.dm b/code/modules/antagonists/wizard/equipment/artefact.dm
index 492da73e66..74cfc61d0f 100644
--- a/code/modules/antagonists/wizard/equipment/artefact.dm
+++ b/code/modules/antagonists/wizard/equipment/artefact.dm
@@ -261,7 +261,7 @@
GiveHint(target)
else if(is_pointed(I))
to_chat(target, "You feel a stabbing pain in [parse_zone(user.zone_selected)]!")
- target.Knockdown(40)
+ target.DefaultCombatKnockdown(40)
GiveHint(target)
else if(istype(I, /obj/item/bikehorn))
to_chat(target, "HONK")
@@ -377,7 +377,10 @@
/obj/item/warpwhistle/proc/end_effect(mob/living/carbon/user)
user.invisibility = initial(user.invisibility)
user.status_flags &= ~GODMODE
- user.canmove = TRUE
+ REMOVE_TRAIT(user, TRAIT_MOBILITY_NOMOVE, src)
+ REMOVE_TRAIT(user, TRAIT_MOBILITY_NOUSE, src)
+ REMOVE_TRAIT(user, TRAIT_MOBILITY_NOPICKUP, src)
+ user.update_mobility()
/obj/item/warpwhistle/attack_self(mob/living/carbon/user)
if(!istype(user) || on_cooldown)
@@ -390,7 +393,10 @@
on_cooldown = TRUE
last_user = user
playsound(T,'sound/magic/warpwhistle.ogg', 200, 1)
- user.canmove = FALSE
+ ADD_TRAIT(user, TRAIT_MOBILITY_NOMOVE, src)
+ ADD_TRAIT(user, TRAIT_MOBILITY_NOUSE, src)
+ ADD_TRAIT(user, TRAIT_MOBILITY_NOPICKUP, src)
+ user.update_mobility()
new /obj/effect/temp_visual/tornado(T)
sleep(20)
if(interrupted(user))
@@ -412,7 +418,6 @@
return
if(T.z != potential_T.z || abs(get_dist_euclidian(potential_T,T)) > 50 - breakout)
do_teleport(user, potential_T, channel = TELEPORT_CHANNEL_MAGIC)
- user.canmove = 0
T = potential_T
break
breakout += 1
diff --git a/code/modules/antagonists/wizard/equipment/soulstone.dm b/code/modules/antagonists/wizard/equipment/soulstone.dm
index 962c2b2da4..0f43dfaf3a 100644
--- a/code/modules/antagonists/wizard/equipment/soulstone.dm
+++ b/code/modules/antagonists/wizard/equipment/soulstone.dm
@@ -83,8 +83,8 @@
/obj/item/soulstone/proc/release_shades(mob/user)
for(var/mob/living/simple_animal/shade/A in src)
A.status_flags &= ~GODMODE
- A.canmove = TRUE
A.forceMove(get_turf(user))
+ A.mobility_flags = MOBILITY_FLAGS_DEFAULT
A.cancel_camera()
icon_state = "soulstone"
name = initial(name)
@@ -173,7 +173,7 @@
else
T.forceMove(src) //put shade in stone
T.status_flags |= GODMODE
- T.canmove = FALSE
+ T.mobility_flags = NONE
T.health = T.maxHealth
icon_state = "soulstone2"
name = "soulstone: Shade of [T.real_name]"
@@ -240,8 +240,8 @@
T.dust_animation()
QDEL_IN(T, 5)
var/mob/living/simple_animal/shade/S = new /mob/living/simple_animal/shade(src)
- S.status_flags |= GODMODE //So they won't die inside the stone somehow
- S.canmove = FALSE//Can't move out of the soul stone
+ S.status_flags |= GODMODE //So they won't die inside the stone somehow
+ S.mobility_flags = NONE //Can't move out of the soul stone
S.name = "Shade of [T.real_name]"
S.real_name = "Shade of [T.real_name]"
T.transfer_ckey(S)
diff --git a/code/modules/assembly/flash.dm b/code/modules/assembly/flash.dm
index b6afc3cc0b..13ea317b9b 100644
--- a/code/modules/assembly/flash.dm
+++ b/code/modules/assembly/flash.dm
@@ -150,7 +150,7 @@
var/mob/living/silicon/robot/R = M
log_combat(user, R, "flashed", src)
update_icon(1)
- R.Knockdown(rand(80,120))
+ R.DefaultCombatKnockdown(rand(80,120))
var/diff = 5 * CONFUSION_STACK_MAX_MULTIPLIER - M.confused
R.confused += min(5, diff)
R.flash_act(affect_silicon = 1)
@@ -197,14 +197,13 @@
else
to_chat(user, "This mind seems resistant to the flash!")
-
/obj/item/assembly/flash/cyborg
/obj/item/assembly/flash/cyborg/attack(mob/living/M, mob/user)
. = ..()
new /obj/effect/temp_visual/borgflash(get_turf(src))
- if(. && !CONFIG_GET(flag/disable_borg_flash_knockdown) && iscarbon(M) && !M.resting && !M.get_eye_protection())
- M.Knockdown(80)
+ if(. && !CONFIG_GET(flag/disable_borg_flash_knockdown) && iscarbon(M) && CHECK_MOBILITY(M, MOBILITY_STAND) && !M.get_eye_protection())
+ M.DefaultCombatKnockdown(80)
/obj/item/assembly/flash/cyborg/attack_self(mob/user)
..()
diff --git a/code/modules/assembly/mousetrap.dm b/code/modules/assembly/mousetrap.dm
index c701e13a26..90d4662c15 100644
--- a/code/modules/assembly/mousetrap.dm
+++ b/code/modules/assembly/mousetrap.dm
@@ -48,7 +48,7 @@
if("feet")
if(!H.shoes || !(H.shoes.body_parts_covered & FEET))
affecting = H.get_bodypart(pick(BODY_ZONE_L_LEG, BODY_ZONE_R_LEG))
- H.Knockdown(60)
+ H.DefaultCombatKnockdown(60)
if(BODY_ZONE_PRECISE_L_HAND, BODY_ZONE_PRECISE_R_HAND)
if(!H.gloves)
affecting = H.get_bodypart(type)
diff --git a/code/modules/atmospherics/machinery/atmosmachinery.dm b/code/modules/atmospherics/machinery/atmosmachinery.dm
index 0904808f51..864edfdbe6 100644
--- a/code/modules/atmospherics/machinery/atmosmachinery.dm
+++ b/code/modules/atmospherics/machinery/atmosmachinery.dm
@@ -314,10 +314,6 @@
user.forceMove(loc)
user.visible_message("You hear something squeezing through the ducts...", "You climb out the ventilation system.")
- user.canmove = FALSE
- addtimer(VARSET_CALLBACK(user, canmove, TRUE), 1)
-
-
/obj/machinery/atmospherics/AltClick(mob/living/L)
if(is_type_in_typecache(src, GLOB.ventcrawl_machinery))
return L.handle_ventcrawl(src)
diff --git a/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm b/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm
index 1e8cce32c0..e013a86fd2 100644
--- a/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm
+++ b/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm
@@ -244,7 +244,7 @@
M.forceMove(get_turf(src))
if(isliving(M))
var/mob/living/L = M
- L.update_canmove()
+ L.update_mobility()
occupant = null
update_icon()
@@ -277,10 +277,10 @@
else
. += "[src] seems empty."
-/obj/machinery/atmospherics/components/unary/cryo_cell/MouseDrop_T(mob/target, mob/user)
- if(user.stat || user.lying || !Adjacent(user) || !user.Adjacent(target) || !iscarbon(target) || !user.IsAdvancedToolUser())
+/obj/machinery/atmospherics/components/unary/cryo_cell/MouseDrop_T(mob/living/carbon/target, mob/user)
+ if(user.stat || user.lying || !Adjacent(user) || !user.Adjacent(target) || !istype(target) || !user.IsAdvancedToolUser())
return
- if (target.IsKnockdown() || target.IsStun() || target.IsSleeping() || target.IsUnconscious())
+ if(!CHECK_MOBILITY(target, MOBILITY_MOVE))
close_machine(target)
else
user.visible_message("[user] starts shoving [target] inside [src].", "You start shoving [target] inside [src].")
diff --git a/code/modules/client/verbs/suicide.dm b/code/modules/client/verbs/suicide.dm
index 255a5a2eec..cae9a54484 100644
--- a/code/modules/client/verbs/suicide.dm
+++ b/code/modules/client/verbs/suicide.dm
@@ -224,7 +224,7 @@
/mob/living/carbon/canSuicide()
if(!..())
return
- if(IsStun() || IsKnockdown()) //just while I finish up the new 'fun' suiciding verb. This is to prevent metagaming via suicide
+ if(!CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_MOVE|MOBILITY_USE)) //just while I finish up the new 'fun' suiciding verb. This is to prevent metagaming via suicide
to_chat(src, "You can't commit suicide while stunned! ((You can type Ghost instead however.))")
return
if(restrained())
diff --git a/code/modules/clothing/spacesuits/chronosuit.dm b/code/modules/clothing/spacesuits/chronosuit.dm
index a8387c5ccc..3d06fba285 100644
--- a/code/modules/clothing/spacesuits/chronosuit.dm
+++ b/code/modules/clothing/spacesuits/chronosuit.dm
@@ -221,7 +221,7 @@
if(user.wear_suit == src)
if(hard_landing)
user.electrocute_act(35, src, safety = 1)
- user.Knockdown(200)
+ user.DefaultCombatKnockdown(200)
if(!silent)
to_chat(user, "\nroot@ChronosuitMK4# chronowalk4 --stop\n")
if(camera)
diff --git a/code/modules/clothing/spacesuits/flightsuit.dm b/code/modules/clothing/spacesuits/flightsuit.dm
index 04aacfc3f5..2f9ded7848 100644
--- a/code/modules/clothing/spacesuits/flightsuit.dm
+++ b/code/modules/clothing/spacesuits/flightsuit.dm
@@ -481,7 +481,7 @@
adjust_momentum(0, 0, 10)
wearer.visible_message("[wearer]'s flight suit crashes into the ground!")
if(knockdown)
- wearer.Knockdown(80)
+ wearer.DefaultCombatKnockdown(80)
momentum_x = 0
momentum_y = 0
calculate_momentum_speed()
diff --git a/code/modules/clothing/suits/reactive_armour.dm b/code/modules/clothing/suits/reactive_armour.dm
index dff62dd2c3..87e7098ebd 100644
--- a/code/modules/clothing/suits/reactive_armour.dm
+++ b/code/modules/clothing/suits/reactive_armour.dm
@@ -252,7 +252,7 @@
return
owner.visible_message("The reactive teleport system flings [H] clear of [attack_text] and slams [H.p_them()] into a fabricated table!")
owner.visible_message("[H] GOES ON THE TABLE!!!")
- owner.Knockdown(40)
+ owner.DefaultCombatKnockdown(40)
var/list/turfs = new/list()
for(var/turf/T in orange(tele_range, H))
if(T.density)
diff --git a/code/modules/fields/peaceborg_dampener.dm b/code/modules/fields/peaceborg_dampener.dm
index 79bd866fca..13a2bc0135 100644
--- a/code/modules/fields/peaceborg_dampener.dm
+++ b/code/modules/fields/peaceborg_dampener.dm
@@ -42,7 +42,7 @@
if(R.has_buckled_mobs())
for(var/mob/living/L in R.buckled_mobs)
L.visible_message("[L] is knocked off of [R] by the charge in [R]'s chassis induced by [name]!") //I know it's bad.
- L.Knockdown(10)
+ L.DefaultCombatKnockdown(10)
R.unbuckle_mob(L)
do_sparks(5, 0, L)
..()
diff --git a/code/modules/flufftext/Hallucination.dm b/code/modules/flufftext/Hallucination.dm
index b0c3121c67..ea475b28d6 100644
--- a/code/modules/flufftext/Hallucination.dm
+++ b/code/modules/flufftext/Hallucination.dm
@@ -220,8 +220,8 @@ GLOBAL_LIST_INIT(hallucination_list, list(
/obj/effect/hallucination/simple/xeno/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum)
update_icon("alienh_pounce")
- if(hit_atom == target && target.stat!=DEAD)
- target.Knockdown(100)
+ if(hit_atom == target && target.stat != DEAD)
+ target.DefaultCombatKnockdown(100)
target.visible_message("[target] flails around wildly.","[name] pounces on you!")
/datum/hallucination/xeno_attack
@@ -308,7 +308,7 @@ GLOBAL_LIST_INIT(hallucination_list, list(
shake_camera(target, 2, 1)
if(bubblegum.Adjacent(target) && !charged)
charged = TRUE
- target.Knockdown(80)
+ target.DefaultCombatKnockdown(80)
target.adjustStaminaLoss(40)
step_away(target, bubblegum)
shake_camera(target, 4, 3)
@@ -1106,7 +1106,7 @@ GLOBAL_LIST_INIT(hallucination_list, list(
if(istype(target, /obj/effect/dummy/phased_mob))
return
to_chat(target, "You fall into the chasm!")
- target.Knockdown(40)
+ target.DefaultCombatKnockdown(40)
addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, target, "It's surprisingly shallow."), 15)
QDEL_IN(src, 30)
@@ -1245,7 +1245,7 @@ GLOBAL_LIST_INIT(hallucination_list, list(
/datum/hallucination/shock/proc/shock_drop()
target.jitteriness = max(target.jitteriness - 990, 10) //Still jittery, but vastly less
- target.Knockdown(60)
+ target.DefaultCombatKnockdown(60)
/datum/hallucination/husks
@@ -1318,7 +1318,7 @@ GLOBAL_LIST_INIT(hallucination_list, list(
"[G] grabs your wrist and violently wrenches it to the side!")
C.emote("scream")
C.dropItemToGround(C.get_active_held_item())
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
else
to_chat(C,"[G] violently grabs you!")
qdel(src)
diff --git a/code/modules/food_and_drinks/drinks/drinks/bottle.dm b/code/modules/food_and_drinks/drinks/drinks/bottle.dm
index 07026e79de..b38250e39d 100644
--- a/code/modules/food_and_drinks/drinks/drinks/bottle.dm
+++ b/code/modules/food_and_drinks/drinks/drinks/bottle.dm
@@ -51,7 +51,7 @@
head_attack_message = " on the head"
//Knockdown the target for the duration that we calculated and divide it by 5.
if(armor_duration)
- target.Knockdown(min(armor_duration, 200)) // Never knockdown more than a flash!
+ target.DefaultCombatKnockdown(min(armor_duration, 200)) // Never knockdown more than a flash!
//Display an attack message.
if(target != user)
diff --git a/code/modules/food_and_drinks/food/snacks_meat.dm b/code/modules/food_and_drinks/food/snacks_meat.dm
index 9bf95f65db..83a03ed2d9 100644
--- a/code/modules/food_and_drinks/food/snacks_meat.dm
+++ b/code/modules/food_and_drinks/food/snacks_meat.dm
@@ -225,7 +225,7 @@
if(iscarbon(M))
M.visible_message("[src] bursts out of [M]!")
M.emote("scream")
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
M.adjustBruteLoss(60)
Expand()
return ..()
diff --git a/code/modules/food_and_drinks/food/snacks_pie.dm b/code/modules/food_and_drinks/food/snacks_pie.dm
index 1533f067ab..b3ad6b5126 100644
--- a/code/modules/food_and_drinks/food/snacks_pie.dm
+++ b/code/modules/food_and_drinks/food/snacks_pie.dm
@@ -49,7 +49,7 @@
else
creamoverlay.icon_state = "creampie_human"
if(stunning)
- H.Knockdown(20) //splat!
+ H.DefaultCombatKnockdown(20) //splat!
H.adjust_blurriness(1)
H.visible_message("[H] is creamed by [src]!", "You've been creamed by [src]!")
playsound(H, "desceration", 50, TRUE)
@@ -83,7 +83,7 @@
A.throw_at(T, 1, 1)
M.visible_message("[src] bursts out of [M]!")
M.emote("scream")
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
M.adjustBruteLoss(60)
return ..()
diff --git a/code/modules/food_and_drinks/kitchen_machinery/deep_fryer.dm b/code/modules/food_and_drinks/kitchen_machinery/deep_fryer.dm
index f3b8e466f3..1215dd7ecb 100644
--- a/code/modules/food_and_drinks/kitchen_machinery/deep_fryer.dm
+++ b/code/modules/food_and_drinks/kitchen_machinery/deep_fryer.dm
@@ -152,6 +152,6 @@ God bless America.
reagents.reaction(C, TOUCH)
C.apply_damage(min(30, reagents.total_volume), BURN, BODY_ZONE_HEAD)
reagents.remove_any((reagents.total_volume/2))
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
user.changeNext_move(CLICK_CD_MELEE)
return ..()
diff --git a/code/modules/food_and_drinks/kitchen_machinery/processor.dm b/code/modules/food_and_drinks/kitchen_machinery/processor.dm
index b81c127523..3fa188fb94 100644
--- a/code/modules/food_and_drinks/kitchen_machinery/processor.dm
+++ b/code/modules/food_and_drinks/kitchen_machinery/processor.dm
@@ -132,7 +132,8 @@
set name = "Eject Contents"
set src in oview(1)
- if(usr.stat || !usr.canmove || usr.restrained())
+ var/mob/living/L = usr
+ if(!istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
return
empty()
add_fingerprint(usr)
diff --git a/code/modules/holiday/halloween/jacqueen.dm b/code/modules/holiday/halloween/jacqueen.dm
index 2b116bbfd3..638d1427bc 100644
--- a/code/modules/holiday/halloween/jacqueen.dm
+++ b/code/modules/holiday/halloween/jacqueen.dm
@@ -46,6 +46,8 @@
var/progression = list() //Keep track of where people are in the story.
var/active = TRUE //Turn this to false to keep normal mob behavour
var/cached_z
+ /// I'm busy chatting, don't move.
+ var/busy_chatting = FALSE
/mob/living/simple_animal/jacq/Initialize()
..()
@@ -76,9 +78,9 @@
say("Hello there [gender_check(M)]!")
return ..()
if(!ckey)
- canmove = FALSE
+ busy_chatting = FALSE
chit_chat(M)
- canmove = TRUE
+ busy_chatting = TRUE
..()
/mob/living/simple_animal/jacq/attack_paw(mob/living/carbon/monkey/M)
@@ -86,9 +88,9 @@
say("Hello there [gender_check(M)]!")
return ..()
if(!ckey)
- canmove = FALSE
+ busy_chatting = FALSE
chit_chat(M)
- canmove = TRUE
+ busy_chatting = TRUE
..()
/mob/living/simple_animal/jacq/proc/poof()
@@ -99,7 +101,7 @@
s.set_up(R, 0, loc)
s.start()
visible_message("[src] disappears in a puff of smoke!")
- canmove = TRUE
+ busy_chatting = TRUE
health = 25
//Try to go to populated areas
@@ -377,6 +379,12 @@
sleep(20)
poof()
+/mob/living/simple_animal/jacq/update_mobility()
+ . = ..()
+ if(busy_chatting)
+ DISABLE_BITFIELD(., MOBILITY_MOVE)
+ mobility_flags = .
+
/obj/item/clothing/head/hardhat/pumpkinhead/jaqc
name = "Jacq o' latern"
desc = "A jacqueline o' lantern! You can't seem to get rid of it."
diff --git a/code/modules/holodeck/items.dm b/code/modules/holodeck/items.dm
index 206a5c14a3..e6aed7a8ca 100644
--- a/code/modules/holodeck/items.dm
+++ b/code/modules/holodeck/items.dm
@@ -87,7 +87,7 @@
playsound(src, 'sound/items/dodgeball.ogg', 50, 1)
M.apply_damage(10, STAMINA)
if(prob(5))
- M.Knockdown(60)
+ M.DefaultCombatKnockdown(60)
visible_message("[M] is knocked right off [M.p_their()] feet!")
//
@@ -117,7 +117,7 @@
to_chat(user, "You need a better grip to do that!")
return
L.forceMove(loc)
- L.Knockdown(100)
+ L.DefaultCombatKnockdown(100)
visible_message("[user] dunks [L] into \the [src]!")
user.stop_pulling()
else
diff --git a/code/modules/hydroponics/grown/nettle.dm b/code/modules/hydroponics/grown/nettle.dm
index c3bd82c624..0979ea483f 100644
--- a/code/modules/hydroponics/grown/nettle.dm
+++ b/code/modules/hydroponics/grown/nettle.dm
@@ -98,7 +98,7 @@
/obj/item/reagent_containers/food/snacks/grown/nettle/death/pickup(mob/living/carbon/user)
if(..())
if(prob(50))
- user.Knockdown(100)
+ user.DefaultCombatKnockdown(100)
to_chat(user, "You are stunned by the Deathnettle as you try picking it up!")
/obj/item/reagent_containers/food/snacks/grown/nettle/death/attack(mob/living/carbon/M, mob/user)
@@ -111,5 +111,5 @@
M.adjust_blurriness(force/7)
if(prob(20))
M.Unconscious(force / 0.3)
- M.Knockdown(force / 0.75)
+ M.DefaultCombatKnockdown(force / 0.75)
M.drop_all_held_items()
diff --git a/code/modules/integrated_electronics/subtypes/weaponized.dm b/code/modules/integrated_electronics/subtypes/weaponized.dm
index 350f05914d..02340970af 100644
--- a/code/modules/integrated_electronics/subtypes/weaponized.dm
+++ b/code/modules/integrated_electronics/subtypes/weaponized.dm
@@ -336,7 +336,7 @@
if(!L || !isliving(L))
return 0
- L.Knockdown(stunforce)
+ L.DefaultCombatKnockdown(stunforce)
SEND_SIGNAL(L, COMSIG_LIVING_MINOR_SHOCK)
message_admins("stunned someone with an assembly. Last touches: Assembly: [assembly.fingerprintslast] Circuit: [fingerprintslast]")
diff --git a/code/modules/library/lib_items.dm b/code/modules/library/lib_items.dm
index 459212aad0..bfd0ae03cb 100644
--- a/code/modules/library/lib_items.dm
+++ b/code/modules/library/lib_items.dm
@@ -112,14 +112,14 @@
else
return ..()
-/obj/structure/bookcase/attack_hand(mob/user)
+/obj/structure/bookcase/attack_hand(mob/living/user)
. = ..()
- if(.)
+ if(. || !istype(user))
return
if(contents.len)
var/obj/item/book/choice = input("Which book would you like to remove from the shelf?") as null|obj in contents
if(choice)
- if(!usr.canmove || usr.stat || usr.restrained() || !in_range(loc, usr))
+ if(!CHECK_MOBILITY(user, MOBILITY_USE) || !in_range(loc, user))
return
if(ishuman(user))
if(!user.get_active_held_item())
diff --git a/code/modules/mining/equipment/wormhole_jaunter.dm b/code/modules/mining/equipment/wormhole_jaunter.dm
index 5e2e8bdd5a..c31008fa62 100644
--- a/code/modules/mining/equipment/wormhole_jaunter.dm
+++ b/code/modules/mining/equipment/wormhole_jaunter.dm
@@ -93,7 +93,7 @@
playsound(M,'sound/weapons/resonator_blast.ogg',50,1)
if(iscarbon(M))
var/mob/living/carbon/L = M
- L.Knockdown(60)
+ L.DefaultCombatKnockdown(60)
if(ishuman(L))
shake_camera(L, 20, 1)
addtimer(CALLBACK(L, /mob/living/carbon.proc/vomit), 20)
diff --git a/code/modules/mining/fulton.dm b/code/modules/mining/fulton.dm
index fd366670f0..5044a73c10 100644
--- a/code/modules/mining/fulton.dm
+++ b/code/modules/mining/fulton.dm
@@ -74,7 +74,7 @@ GLOBAL_LIST_EMPTY(total_extraction_beacons)
var/mutable_appearance/balloon3
if(isliving(A))
var/mob/living/M = A
- M.Knockdown(320) // Keep them from moving during the duration of the extraction
+ M.DefaultCombatKnockdown(320) // Keep them from moving during the duration of the extraction
M.buckled = 0 // Unbuckle them to prevent anchoring problems
else
A.anchored = TRUE
diff --git a/code/modules/mob/dead/new_player/new_player.dm b/code/modules/mob/dead/new_player/new_player.dm
index 0418b281e6..7658bd963d 100644
--- a/code/modules/mob/dead/new_player/new_player.dm
+++ b/code/modules/mob/dead/new_player/new_player.dm
@@ -10,7 +10,6 @@
density = FALSE
stat = DEAD
- canmove = FALSE
var/mob/living/new_character //for instant transfer once the round is set up
diff --git a/code/modules/mob/dead/observer/observer.dm b/code/modules/mob/dead/observer/observer.dm
index d2cf3608e6..b891525e42 100644
--- a/code/modules/mob/dead/observer/observer.dm
+++ b/code/modules/mob/dead/observer/observer.dm
@@ -11,7 +11,7 @@ GLOBAL_VAR_INIT(observer_default_invisibility, INVISIBILITY_OBSERVER)
layer = GHOST_LAYER
stat = DEAD
density = FALSE
- canmove = 0
+ move_resist = INFINITY
see_invisible = SEE_INVISIBLE_OBSERVER
see_in_dark = 100
invisibility = INVISIBILITY_OBSERVER
diff --git a/code/modules/mob/living/brain/brain.dm b/code/modules/mob/living/brain/brain.dm
index 37dd7b6a31..e7b8250494 100644
--- a/code/modules/mob/living/brain/brain.dm
+++ b/code/modules/mob/living/brain/brain.dm
@@ -39,12 +39,8 @@
container = null
return ..()
-/mob/living/brain/update_canmove()
- if(in_contents_of(/obj/mecha))
- canmove = 1
- else
- canmove = 0
- return canmove
+/mob/living/brain/update_mobility()
+ return ((mobility_flags = (in_contents_of(/obj/mecha)? MOBILITY_FLAGS_DEFAULT : NONE)))
/mob/living/brain/ex_act() //you cant blow up brainmobs because it makes transfer_to() freak out when borgs blow up.
return
diff --git a/code/modules/mob/living/carbon/alien/alien_defense.dm b/code/modules/mob/living/carbon/alien/alien_defense.dm
index 8de60cba2f..fda136df0b 100644
--- a/code/modules/mob/living/carbon/alien/alien_defense.dm
+++ b/code/modules/mob/living/carbon/alien/alien_defense.dm
@@ -22,11 +22,11 @@ In all, this is a lot like the monkey code. /N
switch(M.a_intent)
if (INTENT_HELP)
if(!recoveringstam)
- resting = 0
- AdjustStun(-60)
- AdjustKnockdown(-60)
- AdjustUnconscious(-60)
- AdjustSleeping(-100)
+ set_resting(FALSE, TRUE, FALSE)
+ AdjustAllImmobility(-60, FALSE)
+ AdjustUnconscious(-60, FALSE)
+ AdjustSleeping(-100, FALSE)
+ update_mobility()
visible_message("[M.name] nuzzles [src] trying to wake [p_them()] up!")
if(INTENT_DISARM, INTENT_HARM)
if(health > 0)
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 b20383301d..e0647159a5 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/caste/hunter.dm
@@ -31,7 +31,7 @@
#define MAX_ALIEN_LEAP_DIST 7
/mob/living/carbon/alien/humanoid/hunter/proc/leap_at(atom/A)
- if(!canmove || leaping)
+ if(!CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND | MOBILITY_MOVE) || leaping)
return
if(pounce_cooldown > world.time)
@@ -65,21 +65,21 @@
var/mob/living/L = hit_atom
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)
+ L.DefaultCombatKnockdown(100)
sleep(2)//Runtime prevention (infinite bump() calls on hulks)
step_towards(src,L)
else
- Knockdown(40, 1, 1)
+ DefaultCombatKnockdown(40, 1, 1)
toggle_leap(0)
else if(hit_atom.density && !hit_atom.CanPass(src))
visible_message("[src] smashes into [hit_atom]!", "[src] smashes into [hit_atom]!")
- Knockdown(40, 1, 1)
+ Paralyze(40, TRUE, TRUE)
if(leaping)
leaping = 0
update_icons()
- update_canmove()
+ update_mobility()
/mob/living/carbon/alien/humanoid/float(on)
diff --git a/code/modules/mob/living/carbon/alien/humanoid/death.dm b/code/modules/mob/living/carbon/alien/humanoid/death.dm
index 5625e98b75..cbbe8a3e0a 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/death.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/death.dm
@@ -4,7 +4,7 @@
. = ..()
- update_canmove()
+ update_mobility()
update_icons()
status_flags |= CANPUSH
diff --git a/code/modules/mob/living/carbon/alien/humanoid/humanoid.dm b/code/modules/mob/living/carbon/alien/humanoid/humanoid.dm
index 347106f6c1..048b5062ec 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/humanoid.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/humanoid.dm
@@ -69,11 +69,11 @@
playsound(src, 'sound/voice/hiss5.ogg', 40, 1, 1) //Alien roars when starting to break free
..(I, cuff_break = INSTANT_CUFFBREAK)
-/mob/living/carbon/alien/humanoid/resist_grab(moving_resist)
- if(pulledby.grab_state)
+/mob/living/carbon/alien/humanoid/do_resist_grab(moving_resist, forced, silent = FALSE)
+ if(pulledby.grab_state && !silent)
visible_message("[src] has broken free of [pulledby]'s grip!")
pulledby.stop_pulling()
- . = 0
+ return TRUE
/mob/living/carbon/alien/humanoid/get_standard_pixel_y_offset(lying = 0)
if(leaping)
diff --git a/code/modules/mob/living/carbon/alien/humanoid/update_icons.dm b/code/modules/mob/living/carbon/alien/humanoid/update_icons.dm
index a1ef522f1a..ca62df0b57 100644
--- a/code/modules/mob/living/carbon/alien/humanoid/update_icons.dm
+++ b/code/modules/mob/living/carbon/alien/humanoid/update_icons.dm
@@ -12,12 +12,12 @@
else
icon_state = "alien[caste]_dead"
- else if((stat == UNCONSCIOUS && !asleep) || stat == SOFT_CRIT || IsKnockdown())
+ else if((stat == UNCONSCIOUS && !asleep) || stat == SOFT_CRIT || IsParalyzed())
icon_state = "alien[caste]_unconscious"
else if(leap_on_click)
icon_state = "alien[caste]_pounce"
- else if(lying || resting || asleep)
+ else if(lying || !CHECK_MOBILITY(src, MOBILITY_STAND) || asleep)
icon_state = "alien[caste]_sleep"
else if(mob_size == MOB_SIZE_LARGE)
icon_state = "alien[caste]"
diff --git a/code/modules/mob/living/carbon/alien/larva/life.dm b/code/modules/mob/living/carbon/alien/larva/life.dm
index 01a52b3b80..81b76c1720 100644
--- a/code/modules/mob/living/carbon/alien/larva/life.dm
+++ b/code/modules/mob/living/carbon/alien/larva/life.dm
@@ -22,13 +22,13 @@
if(stat == CONSCIOUS)
stat = UNCONSCIOUS
blind_eyes(1)
- update_canmove()
+ update_mobility()
else
if(stat == UNCONSCIOUS)
stat = CONSCIOUS
if(!recoveringstam)
- resting = 0
+ set_resting(FALSE, TRUE)
adjust_blindness(-1)
- update_canmove()
+ update_mobility()
update_damage_hud()
update_health_hud()
diff --git a/code/modules/mob/living/carbon/alien/larva/update_icons.dm b/code/modules/mob/living/carbon/alien/larva/update_icons.dm
index 9b762d1728..e6e7e657e8 100644
--- a/code/modules/mob/living/carbon/alien/larva/update_icons.dm
+++ b/code/modules/mob/living/carbon/alien/larva/update_icons.dm
@@ -14,9 +14,9 @@
icon_state = "larva[state]_dead"
else if(handcuffed || legcuffed) //This should be an overlay. Who made this an icon_state?
icon_state = "larva[state]_cuff"
- else if(stat == UNCONSCIOUS || lying || resting)
+ else if(stat == UNCONSCIOUS || !CHECK_MOBILITY(src, MOBILITY_STAND))
icon_state = "larva[state]_sleep"
- else if(IsStun())
+ else if(IsStun() || IsParalyzed())
icon_state = "larva[state]_stun"
else
icon_state = "larva[state]"
diff --git a/code/modules/mob/living/carbon/alien/organs.dm b/code/modules/mob/living/carbon/alien/organs.dm
index febd0a024a..b57f9653a9 100644
--- a/code/modules/mob/living/carbon/alien/organs.dm
+++ b/code/modules/mob/living/carbon/alien/organs.dm
@@ -140,7 +140,7 @@
else if(ishuman(owner)) //Humans, being more fragile, are more overwhelmed by the mental backlash.
to_chat(owner, "You feel a splitting pain in your head, and are struck with a wave of nausea. You cannot hear the hivemind anymore!")
owner.emote("scream")
- owner.Knockdown(100)
+ owner.DefaultCombatKnockdown(100)
owner.jitteriness += 30
owner.confused += 30
diff --git a/code/modules/mob/living/carbon/alien/special/alien_embryo.dm b/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
index 0621d1400e..5352329f99 100644
--- a/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
+++ b/code/modules/mob/living/carbon/alien/special/alien_embryo.dm
@@ -89,8 +89,8 @@
var/mob/living/carbon/alien/larva/new_xeno = new(xeno_loc)
ghost.transfer_ckey(new_xeno, FALSE)
SEND_SOUND(new_xeno, sound('sound/voice/hiss5.ogg',0,0,0,100)) //To get the player's attention
- new_xeno.canmove = 0 //so we don't move during the bursting animation
- new_xeno.notransform = 1
+ new_xeno.Paralyze(6)
+ new_xeno.notransform = TRUE
new_xeno.invisibility = INVISIBILITY_MAXIMUM
sleep(6)
@@ -99,8 +99,8 @@
return
if(new_xeno)
- new_xeno.canmove = 1
- new_xeno.notransform = 0
+ new_xeno.SetParalyzed(0)
+ new_xeno.notransform = FALSE
new_xeno.invisibility = 0
var/mob/living/carbon/old_owner = owner
diff --git a/code/modules/mob/living/carbon/carbon.dm b/code/modules/mob/living/carbon/carbon.dm
index 574a5aedd2..5f9e838330 100644
--- a/code/modules/mob/living/carbon/carbon.dm
+++ b/code/modules/mob/living/carbon/carbon.dm
@@ -103,7 +103,7 @@
hurt = FALSE
if(hit_atom.density && isturf(hit_atom))
if(hurt)
- Knockdown(20)
+ DefaultCombatKnockdown(20)
take_bodypart_damage(10)
if(iscarbon(hit_atom) && hit_atom != src)
var/mob/living/carbon/victim = hit_atom
@@ -112,8 +112,8 @@
if(hurt)
victim.take_bodypart_damage(10)
take_bodypart_damage(10)
- victim.Knockdown(20)
- Knockdown(20)
+ victim.DefaultCombatKnockdown(20)
+ DefaultCombatKnockdown(20)
visible_message("[src] crashes into [victim], knocking them both over!",\
"You violently crash into [victim]!")
playsound(src,'sound/weapons/punch1.ogg',50,1)
@@ -281,19 +281,23 @@
return FALSE
/mob/living/carbon/resist_buckle()
+ . = FALSE
if(restrained())
- changeNext_move(CLICK_CD_BREAKOUT)
- last_special = world.time + CLICK_CD_BREAKOUT
+ // too soon.
+ if(last_special > world.time)
+ return
var/buckle_cd = 600
if(handcuffed)
var/obj/item/restraints/O = src.get_item_by_slot(SLOT_HANDCUFFED)
buckle_cd = O.breakouttime
+ changeNext_move(min(CLICK_CD_BREAKOUT, buckle_cd))
+ last_special = world.time + min(CLICK_CD_BREAKOUT, buckle_cd)
visible_message("[src] attempts to unbuckle [p_them()]self!", \
"You attempt to unbuckle yourself... (This will take around [round(buckle_cd/600,1)] minute\s, and you need to stay still.)")
- if(do_after(src, buckle_cd, 0, target = src))
+ if(do_after(src, buckle_cd, 0, target = src, required_mobility_flags = MOBILITY_RESIST))
if(!buckled)
return
- buckled.user_unbuckle_mob(src,src)
+ buckled.user_unbuckle_mob(src, src)
else
if(src && buckled)
to_chat(src, "You fail to unbuckle yourself!")
@@ -301,21 +305,26 @@
buckled.user_unbuckle_mob(src,src)
/mob/living/carbon/resist_fire()
+ if(last_special > world.time)
+ return
fire_stacks -= 5
- Knockdown(60, TRUE, TRUE)
+ DefaultCombatKnockdown(60, TRUE, TRUE)
spin(32,2)
visible_message("[src] rolls on the floor, trying to put [p_them()]self out!", \
"You stop, drop, and roll!")
+ last_special = world.time + 30
sleep(30)
if(fire_stacks <= 0)
visible_message("[src] has successfully extinguished [p_them()]self!", \
"You extinguish yourself.")
ExtinguishMob()
- return
-/mob/living/carbon/resist_restraints()
+/mob/living/carbon/resist_restraints(ignore_delay = FALSE)
var/obj/item/I = null
var/type = 0
+ if(!ignore_delay && (last_special > world.time))
+ to_chat(src, "You don't have the energy to resist your restraints that fast!")
+ return
if(handcuffed)
I = handcuffed
type = 1
@@ -324,14 +333,13 @@
type = 2
if(I)
if(type == 1)
- changeNext_move(CLICK_CD_BREAKOUT)
+ changeNext_move(min(CLICK_CD_BREAKOUT, I.breakouttime))
last_special = world.time + CLICK_CD_BREAKOUT
if(type == 2)
- changeNext_move(CLICK_CD_RANGE)
+ changeNext_move(min(CLICK_CD_RANGE, I.breakouttime))
last_special = world.time + CLICK_CD_RANGE
cuff_resist(I)
-
/mob/living/carbon/proc/cuff_resist(obj/item/I, breakouttime = 600, cuff_break = 0)
if(I.item_flags & BEING_REMOVED)
to_chat(src, "You're already attempting to remove [I]!")
@@ -341,7 +349,7 @@
if(!cuff_break)
visible_message("[src] attempts to remove [I]!")
to_chat(src, "You attempt to remove [I]... (This will take around [DisplayTimeText(breakouttime)] and you need to stand still.)")
- if(do_after(src, breakouttime, 0, target = src))
+ if(do_after(src, breakouttime, 0, target = src, required_mobility_flags = MOBILITY_RESIST))
clear_cuffs(I, cuff_break)
else
to_chat(src, "You fail to remove [I]!")
@@ -488,7 +496,7 @@
visible_message("[src] dry heaves!", \
"You try to throw up, but there's nothing in your stomach!")
if(stun)
- Knockdown(200)
+ DefaultCombatKnockdown(200)
return 1
if(is_mouth_covered()) //make this add a blood/vomit overlay later it'll be hilarious
@@ -572,9 +580,9 @@
if(stam > DAMAGE_PRECISION)
var/total_health = (health - stam)
if(total_health <= crit_threshold && !stat)
- if(!IsKnockdown())
+ if(CHECK_MOBILITY(src, MOBILITY_STAND))
to_chat(src, "You're too exhausted to keep going...")
- Knockdown(100)
+ KnockToFloor(TRUE)
update_health_hud()
/mob/living/carbon/update_sight()
@@ -814,7 +822,7 @@
else
stat = CONSCIOUS
adjust_blindness(-1)
- update_canmove()
+ update_mobility()
update_damage_hud()
update_health_hud()
med_hud_set_status()
diff --git a/code/modules/mob/living/carbon/carbon_defense.dm b/code/modules/mob/living/carbon/carbon_defense.dm
index 4d860ad4e2..5bbc6d6a64 100644
--- a/code/modules/mob/living/carbon/carbon_defense.dm
+++ b/code/modules/mob/living/carbon/carbon_defense.dm
@@ -82,7 +82,7 @@
var/mob/living/carbon/tempcarb = user
if(!tempcarb.combatmode)
totitemdamage *= 0.5
- if(user.resting)
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND))
totitemdamage *= 0.5
if(!combatmode)
totitemdamage *= 1.5
@@ -193,7 +193,7 @@
do_sparks(5, TRUE, src)
var/power = M.powerlevel + rand(0,3)
- Knockdown(power*20)
+ DefaultCombatKnockdown(power*20)
if(stuttering < power)
stuttering = power
if (prob(stunprob) && M.powerlevel >= 8)
@@ -267,7 +267,7 @@
spawn(20)
jitteriness = max(jitteriness - 990, 10) //Still jittery, but vastly less
if((!tesla_shock || (tesla_shock && siemens_coeff > 0.5)) && stun)
- Knockdown(60)
+ DefaultCombatKnockdown(60)
if(override)
return override
else
@@ -346,16 +346,14 @@
else if (mood.sanity >= SANITY_DISTURBED)
SEND_SIGNAL(src, COMSIG_ADD_MOOD_EVENT, "friendly_hug", /datum/mood_event/betterhug, M)
- AdjustStun(-60)
- AdjustKnockdown(-60)
- AdjustUnconscious(-60)
- AdjustSleeping(-100)
+ AdjustAllImmobility(-60, FALSE)
+ AdjustUnconscious(-60, FALSE)
+ AdjustSleeping(-100, FALSE)
if(recoveringstam)
adjustStaminaLoss(-15)
- else if(resting)
- resting = 0
- update_canmove()
-
+ else
+ set_resting(FALSE, FALSE)
+ update_mobility()
playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
@@ -419,7 +417,7 @@
var/effect_amount = intensity - ear_safety
if(effect_amount > 0)
if(stun_pwr)
- Knockdown(stun_pwr*effect_amount)
+ DefaultCombatKnockdown(stun_pwr*effect_amount)
if(istype(ears) && (deafen_pwr || damage_pwr))
var/ear_damage = damage_pwr * effect_amount
diff --git a/code/modules/mob/living/carbon/carbon_movement.dm b/code/modules/mob/living/carbon/carbon_movement.dm
index 7413e84196..26ac12b97a 100644
--- a/code/modules/mob/living/carbon/carbon_movement.dm
+++ b/code/modules/mob/living/carbon/carbon_movement.dm
@@ -41,3 +41,10 @@
nutrition -= HUNGER_FACTOR/10
if(m_intent == MOVE_INTENT_RUN)
nutrition -= HUNGER_FACTOR/10
+
+/mob/living/carbon/can_move_under_living(mob/living/other)
+ . = ..()
+ if(!.) //we failed earlier don't need to fail again
+ return
+ if(!other.lying && lying) //they're up, we're down.
+ return FALSE
diff --git a/code/modules/mob/living/carbon/examine.dm b/code/modules/mob/living/carbon/examine.dm
index 3f2a259df7..efd81c1744 100644
--- a/code/modules/mob/living/carbon/examine.dm
+++ b/code/modules/mob/living/carbon/examine.dm
@@ -91,7 +91,7 @@
. += "[t_He] [t_is] moving [t_his] body in an unnatural and blatantly unsimian manner."
if(combatmode)
- . += "[t_He] [t_is] visibly tense[resting ? "." : ", and [t_is] standing in combative stance."]"
+ . += "[t_He] [t_is] visibly tense[CHECK_MOBILITY(src, MOBILITY_STAND) ? "." : ", and [t_is] standing in combative stance."]"
var/trait_exam = common_trait_examine()
if (!isnull(trait_exam))
diff --git a/code/modules/mob/living/carbon/human/human.dm b/code/modules/mob/living/carbon/human/human.dm
index 423277863f..bd7cbb48f9 100644
--- a/code/modules/mob/living/carbon/human/human.dm
+++ b/code/modules/mob/living/carbon/human/human.dm
@@ -491,7 +491,7 @@
to_chat(usr, "Unable to locate a data core entry for this person.")
/mob/living/carbon/human/proc/canUseHUD()
- return !(src.stat || IsKnockdown() || IsStun() || src.restrained())
+ return CHECK_MOBILITY(src, MOBILITY_UI)
/mob/living/carbon/human/can_inject(mob/user, error_msg, target_zone, penetrate_thick = FALSE, bypass_immunity = FALSE)
. = 1 // Default to returning true.
@@ -724,8 +724,8 @@
remove_atom_colour(TEMPORARY_COLOUR_PRIORITY, "#000000")
cut_overlay(MA)
-/mob/living/carbon/human/canUseTopic(atom/movable/M, be_close=FALSE, no_dextery=FALSE, no_tk=FALSE)
- if(incapacitated() || lying )
+/mob/living/carbon/human/canUseTopic(atom/movable/M, be_close=FALSE, no_dextery=FALSE, no_tk=FALSE, check_resting = TRUE)
+ if(incapacitated() || (check_resting && !CHECK_MOBILITY(src, MOBILITY_STAND)))
to_chat(src, "You can't do that right now!")
return FALSE
if(!Adjacent(M) && (M.loc != src))
@@ -836,7 +836,7 @@
visible_message("[src] dry heaves!", \
"You try to throw up, but there's nothing in your stomach!")
if(stun)
- Knockdown(200)
+ DefaultCombatKnockdown(200)
return 1
..()
@@ -870,7 +870,7 @@
return (istype(target) && target.stat == CONSCIOUS)
/mob/living/carbon/human/proc/can_be_firemanned(mob/living/carbon/target)
- return (ishuman(target) && target.lying)
+ return (ishuman(target) && !CHECK_MOBILITY(target, MOBILITY_STAND))
/mob/living/carbon/human/proc/fireman_carry(mob/living/carbon/target)
if(can_be_firemanned(target))
@@ -879,7 +879,7 @@
if(do_after(src, 30, TRUE, target))
//Second check to make sure they're still valid to be carried
if(can_be_firemanned(target) && !incapacitated(FALSE, TRUE))
- target.resting = FALSE
+ target.set_resting(FALSE, TRUE)
buckle_mob(target, TRUE, TRUE, 90, 1, 0)
return
visible_message("[src] fails to fireman carry [target]!")
@@ -892,7 +892,7 @@
/mob/living/carbon/human/proc/piggyback(mob/living/carbon/target)
if(can_piggyback(target))
visible_message("[target] starts to climb onto [src]...")
- if(do_after(target, 15, target = src))
+ if(do_after(target, 15, target = src, required_mobility_flags = MOBILITY_STAND))
if(can_piggyback(target))
if(target.incapacitated(FALSE, TRUE) || incapacitated(FALSE, TRUE))
target.visible_message("[target] can't hang onto [src]!")
diff --git a/code/modules/mob/living/carbon/human/human_defense.dm b/code/modules/mob/living/carbon/human/human_defense.dm
index 78a38aa7fa..5bedce359b 100644
--- a/code/modules/mob/living/carbon/human/human_defense.dm
+++ b/code/modules/mob/living/carbon/human/human_defense.dm
@@ -179,7 +179,7 @@
"[M] disarmed [src]!")
else if(!M.client || prob(5)) // only natural monkeys get to stun reliably, (they only do it occasionaly)
playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
- Knockdown(100)
+ DefaultCombatKnockdown(100)
log_combat(M, src, "tackled")
visible_message("[M] has tackled down [src]!", \
"[M] has tackled down [src]!")
@@ -228,9 +228,9 @@
else
playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
if(!lying) //CITADEL EDIT
- Knockdown(100, TRUE, FALSE, 30, 25)
+ DefaultCombatKnockdown(100, TRUE, FALSE, 30, 25)
else
- Knockdown(100)
+ DefaultCombatKnockdown(100)
log_combat(M, src, "tackled")
visible_message("[M] has tackled down [src]!", \
"[M] has tackled down [src]!")
@@ -297,10 +297,10 @@
switch(M.damtype)
if("brute")
if(M.force > 35) // durand and other heavy mechas
- Knockdown(50)
+ DefaultCombatKnockdown(50)
src.throw_at(throw_target, rand(1,5), 7)
- else if(M.force >= 20 && !IsKnockdown()) // lightweight mechas like gygax
- Knockdown(30)
+ else if(M.force >= 20 && CHECK_MOBILITY(src, MOBILITY_STAND)) // lightweight mechas like gygax
+ DefaultCombatKnockdown(30)
src.throw_at(throw_target, rand(1,3), 7)
update |= temp.receive_damage(dmg, 0)
playsound(src, 'sound/weapons/punch4.ogg', 50, 1)
diff --git a/code/modules/mob/living/carbon/human/human_mobility.dm b/code/modules/mob/living/carbon/human/human_mobility.dm
new file mode 100644
index 0000000000..61ceb42336
--- /dev/null
+++ b/code/modules/mob/living/carbon/human/human_mobility.dm
@@ -0,0 +1,48 @@
+/mob/living/carbon/human/resist_a_rest(automatic = FALSE, ignoretimer = FALSE)
+ if(!resting || stat || attemptingstandup)
+ return FALSE
+ if(ignoretimer)
+ set_resting(FALSE, FALSE)
+ return TRUE
+ if(!lying) //if they're in a chair or something they don't need to force themselves off the ground.
+ set_resting(FALSE, FALSE)
+ return TRUE
+ else if(!CHECK_MOBILITY(src, MOBILITY_RESIST))
+ if(!automatic)
+ to_chat(src, "You are unable to stand up right now.")
+ return FALSE
+ else
+ var/totaldelay = 3 //A little bit less than half of a second as a baseline for getting up from a rest
+ if(getStaminaLoss() >= STAMINA_SOFTCRIT)
+ to_chat(src, "You're too exhausted to get up!")
+ return FALSE
+ attemptingstandup = TRUE
+ var/health_deficiency = max((maxHealth - (health - getStaminaLoss()))*0.5, 0)
+ if(!has_gravity())
+ health_deficiency = health_deficiency*0.2
+ totaldelay += health_deficiency
+ var/standupwarning = "[src] and everyone around them should probably yell at the dev team"
+ switch(health_deficiency)
+ if(-INFINITY to 10)
+ standupwarning = "[src] stands right up!"
+ if(10 to 35)
+ standupwarning = "[src] tries to stand up."
+ if(35 to 60)
+ standupwarning = "[src] slowly pushes [p_them()]self upright."
+ if(60 to 80)
+ standupwarning = "[src] weakly attempts to stand up."
+ if(80 to INFINITY)
+ standupwarning = "[src] struggles to stand up."
+ var/usernotice = automatic ? "You are now getting up. (Auto)" : "You are now getting up."
+ visible_message("[standupwarning]", usernotice, vision_distance = 5)
+ if(do_after(src, totaldelay, target = src, required_mobility_flags = MOBILITY_RESIST))
+ set_resting(FALSE, TRUE)
+ attemptingstandup = FALSE
+ return TRUE
+ else
+ attemptingstandup = FALSE
+ if(resting) //we didn't shove ourselves up or something
+ visible_message("[src] falls right back down.", "You fall right back down.")
+ if(has_gravity())
+ playsound(src, "bodyfall", 20, 1)
+ return FALSE
diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm
index b1bc47ea4a..b834de3302 100644
--- a/code/modules/mob/living/carbon/human/species.dm
+++ b/code/modules/mob/living/carbon/human/species.dm
@@ -1364,9 +1364,9 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
return TRUE
if(radiation > RAD_MOB_KNOCKDOWN && prob(RAD_MOB_KNOCKDOWN_PROB))
- if(!H.IsKnockdown())
+ if(CHECK_MOBILITY(H, MOBILITY_STAND))
H.emote("collapse")
- H.Knockdown(RAD_MOB_KNOCKDOWN_AMOUNT)
+ H.DefaultCombatKnockdown(RAD_MOB_KNOCKDOWN_AMOUNT)
to_chat(H, "You feel weak.")
if(radiation > RAD_MOB_VOMIT && prob(RAD_MOB_VOMIT_PROB))
@@ -1514,7 +1514,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
//CITADEL CHANGES - makes resting and disabled combat mode reduce punch damage, makes being out of combat mode result in you taking more damage
if(!target.combatmode && damage < user.dna.species.punchstunthreshold)
damage = user.dna.species.punchstunthreshold - 1
- if(user.resting)
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND))
damage *= 0.5
if(!user.combatmode)
damage *= 0.25
@@ -1632,7 +1632,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
return*/
if(!target.combatmode) // CITADEL CHANGE
randn += -10 //CITADEL CHANGE - being out of combat mode makes it easier for you to get disarmed
- if(user.resting) //CITADEL CHANGE
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND)) //CITADEL CHANGE
randn += 100 //CITADEL CHANGE - No kosher disarming if you're resting
if(!user.combatmode) //CITADEL CHANGE
randn += 25 //CITADEL CHANGE - Makes it harder to disarm outside of combat mode
@@ -1715,7 +1715,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
var/mob/living/carbon/tempcarb = user
if(!tempcarb.combatmode)
totitemdamage *= 0.5
- if(user.resting)
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND))
totitemdamage *= 0.5
if(istype(H))
if(!H.combatmode)
@@ -1831,12 +1831,14 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
if(user.getStaminaLoss() >= STAMINA_SOFTCRIT)
to_chat(user, "You're too exhausted for that.")
return
- if(!user.resting)
+ if(user.IsKnockdown() || user.IsParalyzed() || user.IsStun())
+ to_chat(user, "You can't seem to force yourself up right now!")
+ return
+ if(CHECK_MOBILITY(user, MOBILITY_STAND))
to_chat(user, "You can only force yourself up if you're on the ground.")
return
user.visible_message("[user] forces [p_them()]self up to [p_their()] feet!", "You force yourself up to your feet!")
- user.resting = 0
- user.update_canmove()
+ user.set_resting(FALSE, TRUE)
user.adjustStaminaLossBuffered(user.stambuffer) //Rewards good stamina management by making it easier to instantly get up from resting
playsound(user, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
@@ -1849,7 +1851,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
return FALSE
if(attacker_style && attacker_style.disarm_act(user,target))
return TRUE
- if(user.resting)
+ if(!CHECK_MOBILITY(user, MOBILITY_STAND))
return FALSE
else
if(user == target)
@@ -1862,7 +1864,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
target.w_uniform.add_fingerprint(user)
SEND_SIGNAL(target, COMSIG_HUMAN_DISARM_HIT, user, user.zone_selected)
- if(!target.resting)
+ if(CHECK_MOBILITY(target, MOBILITY_STAND))
target.adjustStaminaLoss(5)
if(target.is_shove_knockdown_blocked())
@@ -1876,7 +1878,7 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
//Thank you based whoneedsspace
target_collateral_human = locate(/mob/living/carbon/human) in target_shove_turf.contents
- if(target_collateral_human && !target_collateral_human.resting)
+ if(target_collateral_human && CHECK_MOBILITY(target_collateral_human, MOBILITY_STAND))
shove_blocked = TRUE
else
target_collateral_human = null
@@ -1887,15 +1889,15 @@ GLOBAL_LIST_EMPTY(roundstart_race_names)
var/append_message = ""
if(shove_blocked && !target.buckled)
var/directional_blocked = !target.Adjacent(target_shove_turf)
- var/targetatrest = target.resting
+ var/targetatrest = !CHECK_MOBILITY(target, MOBILITY_STAND)
if((directional_blocked || !(target_collateral_human || target_shove_turf.shove_act(target, user))) && !targetatrest)
- target.Knockdown(SHOVE_KNOCKDOWN_SOLID)
+ target.DefaultCombatKnockdown(SHOVE_KNOCKDOWN_SOLID)
user.visible_message("[user.name] shoves [target.name], knocking them down!",
"You shove [target.name], knocking them down!", null, COMBAT_MESSAGE_RANGE)
log_combat(user, target, "shoved", "knocking them down")
else if(target_collateral_human && !targetatrest)
- target.Knockdown(SHOVE_KNOCKDOWN_HUMAN)
- target_collateral_human.Knockdown(SHOVE_KNOCKDOWN_COLLATERAL)
+ target.DefaultCombatKnockdown(SHOVE_KNOCKDOWN_HUMAN)
+ target_collateral_human.DefaultCombatKnockdown(SHOVE_KNOCKDOWN_COLLATERAL)
user.visible_message("[user.name] shoves [target.name] into [target_collateral_human.name]!",
"You shove [target.name] into [target_collateral_human.name]!", null, COMBAT_MESSAGE_RANGE)
append_message += ", into [target_collateral_human.name]"
diff --git a/code/modules/mob/living/carbon/human/species_types/angel.dm b/code/modules/mob/living/carbon/human/species_types/angel.dm
index 18c6a7bab4..924f5f9c6a 100644
--- a/code/modules/mob/living/carbon/human/species_types/angel.dm
+++ b/code/modules/mob/living/carbon/human/species_types/angel.dm
@@ -52,21 +52,20 @@
return 0
/datum/species/angel/proc/CanFly(mob/living/carbon/human/H)
- if(H.stat || H.IsStun() || H.IsKnockdown())
- return 0
+ if(!CHECK_MOBILITY(H, MOBILITY_MOVE))
+ return FALSE
if(H.wear_suit && ((H.wear_suit.flags_inv & HIDEJUMPSUIT) && (!H.wear_suit.species_exception || !is_type_in_list(src, H.wear_suit.species_exception)))) //Jumpsuits have tail holes, so it makes sense they have wing holes too
to_chat(H, "Your suit blocks your wings from extending!")
- return 0
+ return FALSE
var/turf/T = get_turf(H)
if(!T)
- return 0
+ return FALSE
var/datum/gas_mixture/environment = T.return_air()
if(environment && !(environment.return_pressure() > 30))
to_chat(H, "The atmosphere is too thin for you to fly!")
- return 0
- else
- return 1
+ return FALSE
+ return TRUE
/datum/action/innate/flight
name = "Toggle Flight"
@@ -81,12 +80,12 @@
if(H.movement_type & FLYING)
to_chat(H, "You settle gently back onto the ground...")
A.ToggleFlight(H,0)
- H.update_canmove()
+ H.update_mobility()
else
to_chat(H, "You beat your wings and begin to hover gently above the ground...")
- H.resting = 0
+ H.set_resting(FALSE, TRUE)
A.ToggleFlight(H,1)
- H.update_canmove()
+ H.update_mobility()
/datum/species/angel/proc/flyslip(mob/living/carbon/human/H)
var/obj/buckled_obj
diff --git a/code/modules/mob/living/carbon/human/species_types/jellypeople.dm b/code/modules/mob/living/carbon/human/species_types/jellypeople.dm
index eb1e194c0f..cf2950ff6f 100644
--- a/code/modules/mob/living/carbon/human/species_types/jellypeople.dm
+++ b/code/modules/mob/living/carbon/human/species_types/jellypeople.dm
@@ -83,6 +83,7 @@
button_icon_state = "slimeheal"
icon_icon = 'icons/mob/actions/actions_slime.dmi'
background_icon_state = "bg_alien"
+ required_mobility_flags = NONE
/datum/action/innate/regenerate_limbs/IsAvailable()
if(..())
diff --git a/code/modules/mob/living/carbon/human/species_types/podpeople.dm b/code/modules/mob/living/carbon/human/species_types/podpeople.dm
index b29890a97d..d2d4c6c658 100644
--- a/code/modules/mob/living/carbon/human/species_types/podpeople.dm
+++ b/code/modules/mob/living/carbon/human/species_types/podpeople.dm
@@ -58,7 +58,7 @@
if(/obj/item/projectile/energy/floramut)
if(prob(15))
H.rad_act(rand(30,80))
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
H.visible_message("[H] writhes in pain as [H.p_their()] vacuoles boil.", "You writhe in pain as your vacuoles boil!", "You hear the crunching of leaves.")
if(prob(80))
H.randmutb()
diff --git a/code/modules/mob/living/carbon/human/status_procs.dm b/code/modules/mob/living/carbon/human/status_procs.dm
index 49121c9409..37bafdab67 100644
--- a/code/modules/mob/living/carbon/human/status_procs.dm
+++ b/code/modules/mob/living/carbon/human/status_procs.dm
@@ -3,7 +3,7 @@
amount = dna.species.spec_stun(src,amount)
return ..()
-/mob/living/carbon/human/Knockdown(amount, updating = TRUE, ignore_canknockdown = FALSE, override_hardstun, override_stamdmg)
+/mob/living/carbon/human/DefaultCombatKnockdown(amount, updating = TRUE, ignore_canknockdown = FALSE, override_hardstun, override_stamdmg)
amount = dna.species.spec_stun(src,amount)
return ..()
diff --git a/code/modules/mob/living/carbon/life.dm b/code/modules/mob/living/carbon/life.dm
index 0460819c4b..639cfc40e2 100644
--- a/code/modules/mob/living/carbon/life.dm
+++ b/code/modules/mob/living/carbon/life.dm
@@ -509,7 +509,7 @@ GLOBAL_LIST_INIT(ballmer_windows_me_msg, list("Yo man, what if, we like, uh, put
/mob/living/carbon/handle_status_effects()
..()
if(getStaminaLoss() && !combatmode)//CIT CHANGE - prevents stamina regen while combat mode is active
- adjustStaminaLoss(resting ? (recoveringstam ? -7.5 : -6) : -3)//CIT CHANGE - decreases adjuststaminaloss to stop stamina damage from being such a joke
+ adjustStaminaLoss(!CHECK_MOBILITY(src, MOBILITY_STAND) ? (recoveringstam ? -7.5 : -6) : -3)//CIT CHANGE - decreases adjuststaminaloss to stop stamina damage from being such a joke
if(!recoveringstam && incomingstammult != 1)
incomingstammult = max(0.01, incomingstammult)
@@ -521,7 +521,7 @@ GLOBAL_LIST_INIT(ballmer_windows_me_msg, list("Yo man, what if, we like, uh, put
bufferedstam = max(bufferedstam - drainrate, 0)
//END OF CIT CHANGES
- var/restingpwr = 1 + 4 * resting
+ var/restingpwr = 1 + 4 * !CHECK_MOBILITY(src, MOBILITY_STAND)
//Dizziness
if(dizziness)
diff --git a/code/modules/mob/living/carbon/monkey/combat.dm b/code/modules/mob/living/carbon/monkey/combat.dm
index 3277c57b75..a06d65ad4b 100644
--- a/code/modules/mob/living/carbon/monkey/combat.dm
+++ b/code/modules/mob/living/carbon/monkey/combat.dm
@@ -50,17 +50,11 @@
// taken from /mob/living/carbon/human/interactive/
/mob/living/carbon/monkey/proc/IsDeadOrIncap(checkDead = TRUE)
- if(!canmove)
- return 1
+ if(!CHECK_MOBILITY(src, MOBILITY_MOVE))
+ return TRUE
if(health <= 0 && checkDead)
- return 1
- if(IsUnconscious())
- return 1
- if(IsStun() || IsKnockdown())
- return 1
- if(stat)
- return 1
- return 0
+ return TRUE
+ return FALSE
/mob/living/carbon/monkey/proc/battle_screech()
if(next_battle_screech < world.time)
diff --git a/code/modules/mob/living/carbon/monkey/life.dm b/code/modules/mob/living/carbon/monkey/life.dm
index e83f67f796..31589f1cab 100644
--- a/code/modules/mob/living/carbon/monkey/life.dm
+++ b/code/modules/mob/living/carbon/monkey/life.dm
@@ -13,7 +13,7 @@
if(!client)
if(stat == CONSCIOUS)
- if(on_fire || buckled || restrained() || (resting && canmove)) //CIT CHANGE - makes it so monkeys attempt to resist if they're resting)
+ if(on_fire || buckled || restrained() || (!CHECK_MOBILITY(src, MOBILITY_STAND) && CHECK_MOBILITY(src, MOBILITY_MOVE))) //CIT CHANGE - makes it so monkeys attempt to resist if they're resting)
if(!resisting && prob(MONKEY_RESIST_PROB))
resisting = TRUE
walk_to(src,0)
@@ -21,7 +21,7 @@
else if(resisting)
resisting = FALSE
else if((mode == MONKEY_IDLE && !pickupTarget && !prob(MONKEY_SHENANIGAN_PROB)) || !handle_combat())
- if(prob(25) && canmove && isturf(loc) && !pulledby)
+ if(prob(25) && CHECK_MOBILITY(src, MOBILITY_MOVE) && isturf(loc) && !pulledby)
step(src, pick(GLOB.cardinals))
else if(prob(1))
emote(pick("scratch","jump","roll","tail"))
@@ -34,9 +34,9 @@
gorillize()
return
if(radiation > RAD_MOB_KNOCKDOWN && prob(RAD_MOB_KNOCKDOWN_PROB))
- if(!IsKnockdown())
+ if(!recoveringstam)
emote("collapse")
- Knockdown(RAD_MOB_KNOCKDOWN_AMOUNT)
+ DefaultCombatKnockdown(RAD_MOB_KNOCKDOWN_AMOUNT)
to_chat(src, "You feel weak.")
if(radiation > RAD_MOB_MUTATE)
if(prob(1))
diff --git a/code/modules/mob/living/carbon/monkey/monkey_defense.dm b/code/modules/mob/living/carbon/monkey/monkey_defense.dm
index 62550f4ccb..50793eb821 100644
--- a/code/modules/mob/living/carbon/monkey/monkey_defense.dm
+++ b/code/modules/mob/living/carbon/monkey/monkey_defense.dm
@@ -82,7 +82,7 @@
if(!IsUnconscious())
M.do_attack_animation(src, ATTACK_EFFECT_DISARM)
if (prob(25))
- Knockdown(40)
+ DefaultCombatKnockdown(40)
playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
log_combat(M, src, "pushed")
visible_message("[M] has pushed down [src]!", \
@@ -126,7 +126,7 @@
var/obj/item/I = null
playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
if(prob(95))
- Knockdown(20)
+ DefaultCombatKnockdown(20)
visible_message("[M] has tackled down [name]!", \
"[M] has tackled down [name]!", null, COMBAT_MESSAGE_RANGE)
else
diff --git a/code/modules/mob/living/damage_procs.dm b/code/modules/mob/living/damage_procs.dm
index abcb0589ae..d5e1fa6fc4 100644
--- a/code/modules/mob/living/damage_procs.dm
+++ b/code/modules/mob/living/damage_procs.dm
@@ -88,7 +88,7 @@
if(EFFECT_STUN)
Stun(effect * hit_percent)
if(EFFECT_KNOCKDOWN)
- Knockdown(effect * hit_percent, override_stamdmg = knockdown_stammax ? CLAMP(knockdown_stamoverride, 0, knockdown_stammax-getStaminaLoss()) : knockdown_stamoverride)
+ DefaultCombatKnockdown(effect * hit_percent, override_stamdmg = knockdown_stammax ? CLAMP(knockdown_stamoverride, 0, knockdown_stammax-getStaminaLoss()) : knockdown_stamoverride)
if(EFFECT_UNCONSCIOUS)
Unconscious(effect * hit_percent)
if(EFFECT_IRRADIATE)
diff --git a/code/modules/mob/living/death.dm b/code/modules/mob/living/death.dm
index a33eebf12a..ad1a3bc9b9 100644
--- a/code/modules/mob/living/death.dm
+++ b/code/modules/mob/living/death.dm
@@ -78,7 +78,7 @@
update_action_buttons_icon()
update_damage_hud()
update_health_hud()
- update_canmove()
+ update_mobility()
med_hud_set_health()
med_hud_set_status()
if(!gibbed && !QDELETED(src))
diff --git a/code/modules/mob/living/emote.dm b/code/modules/mob/living/emote.dm
index 3221981e78..a1efae5838 100644
--- a/code/modules/mob/living/emote.dm
+++ b/code/modules/mob/living/emote.dm
@@ -273,7 +273,7 @@
if(H.get_num_arms() == 0)
if(H.get_num_legs() != 0)
message_param = "tries to point at %t with a leg, falling down in the process!"
- H.Knockdown(20)
+ H.DefaultCombatKnockdown(20)
else
message_param = "bumps [user.p_their()] head on the ground trying to motion towards %t."
H.adjustOrganLoss(ORGAN_SLOT_BRAIN, 5)
@@ -377,7 +377,7 @@
. = ..()
if(. && isliving(user))
var/mob/living/L = user
- L.Knockdown(200)
+ L.DefaultCombatKnockdown(200)
/datum/emote/living/sway
key = "sway"
diff --git a/code/modules/mob/living/living.dm b/code/modules/mob/living/living.dm
index df6257e38b..d9a22674ae 100644
--- a/code/modules/mob/living/living.dm
+++ b/code/modules/mob/living/living.dm
@@ -48,7 +48,7 @@
/mob/living/proc/ZImpactDamage(turf/T, levels)
visible_message("[src] crashes into [T] with a sickening noise!")
adjustBruteLoss((levels * 5) ** 1.5)
- Knockdown(levels * 50)
+ DefaultCombatKnockdown(levels * 50)
/mob/living/proc/OpenCraftingMenu()
@@ -88,7 +88,7 @@
var/they_can_move = TRUE
if(isliving(M))
var/mob/living/L = M
- they_can_move = L.canmove //L.mobility_flags & MOBILITY_MOVE
+ they_can_move = CHECK_MOBILITY(L, MOBILITY_MOVE)
//Also spread diseases
for(var/thing in diseases)
var/datum/disease/D = thing
@@ -115,7 +115,7 @@
return 1
//CIT CHANGES START HERE - makes it so resting stops you from moving through standing folks without a short delay
- if(resting && !L.resting)
+ if(!CHECK_MOBILITY(src, MOBILITY_STAND) && CHECK_MOBILITY(L, MOBILITY_STAND))
var/origtargetloc = L.loc
if(!pulledby)
if(attemptingcrawl)
@@ -125,7 +125,7 @@
return TRUE
attemptingcrawl = TRUE
visible_message("[src] is attempting to crawl under [L].", "You are now attempting to crawl under [L].")
- if(!do_after(src, CRAWLUNDER_DELAY, target = src) || !resting)
+ if(!do_after(src, CRAWLUNDER_DELAY, target = src) || CHECK_MOBILITY(src, MOBILITY_STAND))
attemptingcrawl = FALSE
return TRUE
var/src_passmob = (pass_flags & PASSMOB)
@@ -369,8 +369,8 @@
death()
-/mob/living/incapacitated(ignore_restraints, ignore_grab)
- if(stat || IsUnconscious() || IsStun() || IsKnockdown() || recoveringstam || (!ignore_restraints && restrained(ignore_grab))) // CIT CHANGE - adds recoveringstam check here
+/mob/living/incapacitated(ignore_restraints = FALSE, ignore_grab = FALSE, check_immobilized = FALSE)
+ if(stat || IsUnconscious() || IsStun() || IsParalyzed() || recoveringstam || (check_immobilized && IsImmobilized()) || (!ignore_restraints && restrained(ignore_grab)))
return TRUE
/mob/living/canUseStorage()
@@ -428,7 +428,6 @@
else
if(alert(src, "You sure you want to sleep for a while?", "Sleep", "Yes", "No") == "Yes")
SetSleeping(400) //Short nap
- update_canmove()
/mob/proc/get_contents()
@@ -493,7 +492,7 @@
stat = UNCONSCIOUS //the mob starts unconscious,
blind_eyes(1)
updatehealth() //then we check if the mob should wake up.
- update_canmove()
+ update_mobility()
update_sight()
clear_alert("not_enough_oxy")
reload_fullscreen()
@@ -512,8 +511,7 @@
setStaminaLoss(0, 0)
SetUnconscious(0, FALSE)
set_disgust(0)
- SetStun(0, FALSE)
- SetKnockdown(0, FALSE)
+ SetAllImmobility(0, FALSE)
SetSleeping(0, FALSE)
radiation = 0
nutrition = NUTRITION_LEVEL_FED + 50
@@ -528,7 +526,7 @@
ExtinguishMob()
fire_stacks = 0
confused = 0
- update_canmove()
+ update_mobility()
//Heal all organs
if(iscarbon(src))
var/mob/living/carbon/C = src
@@ -552,30 +550,6 @@
var/obj/item/item = i
SEND_SIGNAL(item, COMSIG_ITEM_WEARERCROSSED, AM)
-/mob/living/Move(atom/newloc, direct)
- if (buckled && buckled.loc != newloc) //not updating position
- if (!buckled.anchored)
- return buckled.Move(newloc, direct)
- else
- return 0
-
- var/old_direction = dir
- var/turf/T = loc
-
- if(pulling)
- update_pull_movespeed()
-
- . = ..()
-
- if(pulledby && moving_diagonally != FIRST_DIAG_STEP && get_dist(src, pulledby) > 1)//separated from our puller and not in the middle of a diagonal move.
- pulledby.stop_pulling()
-
- if(active_storage && !(CanReach(active_storage.parent,view_only = TRUE)))
- active_storage.close(src)
-
- if(lying && !buckled && prob(getBruteLoss()*200/maxHealth))
- makeTrail(newloc, T, old_direction)
-
/mob/living/proc/makeTrail(turf/target_turf, turf/start, direction)
if(!has_gravity())
return
@@ -648,66 +622,97 @@
..(pressure_difference, direction, pressure_resistance_prob_delta)
/mob/living/can_resist()
- return !((next_move > world.time) || incapacitated(ignore_restraints = TRUE))
+ return !((next_move > world.time) || !CHECK_MOBILITY(src, MOBILITY_RESIST))
+/// Resist verb for attempting to get out of whatever is restraining your motion. Gives you resist clickdelay if do_resist() returns true.
/mob/living/verb/resist()
set name = "Resist"
set category = "IC"
if(!can_resist())
return
- changeNext_move(CLICK_CD_RESIST)
+ if(do_resist())
+ changeNext_move(CLICK_CD_RESIST)
+
+/// The actual proc for resisting. Return TRUE to give clickdelay.
+/mob/living/proc/do_resist()
SEND_SIGNAL(src, COMSIG_LIVING_RESIST, src)
//resisting grabs (as if it helps anyone...)
- if(!restrained(ignore_grab = 1) && pulledby)
- visible_message("[src] resists against [pulledby]'s grip!")
- log_combat(src, pulledby, "resisted grab")
- resist_grab()
- return
+ // only works if you're not cuffed.
+ if(!restrained(ignore_grab = TRUE) && pulledby)
+ var/old_gs = pulledby.grab_state
+ attempt_resist_grab(FALSE)
+ // Return as we should only resist one thing at a time. Give clickdelay if the grab wasn't passive.
+ return old_gs? TRUE : FALSE
- //unbuckling yourself
+ // unbuckling yourself. stops the chain if you try it.
if(buckled && last_special <= world.time)
- resist_buckle()
+ log_combat(src, buckled, "resisted buckle")
+ return resist_buckle()
- // CIT CHANGE - climbing out of a gut
- if(attempt_vr(src,"vore_process_resist",args)) return TRUE
+ // CIT CHANGE - climbing out of a gut.
+ if(attempt_vr(src,"vore_process_resist",args))
+ //Sure, give clickdelay for anti spam. shouldn't be combat voring anyways.
+ return TRUE
//Breaking out of a container (Locker, sleeper, cryo...)
- else if(isobj(loc))
+ if(isobj(loc))
var/obj/C = loc
C.container_resist(src)
+ // This shouldn't give clickdelays sometime (e.g. going out of a mech/unwelded and unlocked locker/disposals bin/etc) but there's so many overrides that I am not going to bother right now.
+ return TRUE
- else if(canmove)
+ if(CHECK_MOBILITY(src, MOBILITY_MOVE))
if(on_fire)
resist_fire() //stop, drop, and roll
- return
- if(resting) //cit change - allows resisting out of resting
- resist_a_rest() // ditto
- return
- if(resist_embedded()) //Citadel Change for embedded removal memes
- return
- if(last_special <= world.time)
- resist_restraints() //trying to remove cuffs.
- return
+ // Give clickdelay
+ return TRUE
+ if(resting) //cit change - allows resisting out of resting
+ resist_a_rest() // ditto
+ // DO NOT GIVE CLCIKDELAY - resist_a_rest() handles spam prevention. Somewhat.
+ return FALSE
+ if(last_special <= world.time)
+ resist_restraints() //trying to remove cuffs.
+ // DO NOT GIVE CLICKDELAY - last_special handles this.
+ return FALSE
+ if(CHECK_MOBILITY(src, MOBILITY_USE) && resist_embedded()) //Citadel Change for embedded removal memes - requires being able to use items.
+ // DO NOT GIVE DEFAULT CLICKDELAY - This is a combat action.
+ changeNext_move(CLICK_CD_MELEE)
+ return FALSE
+/// Proc to resist a grab. moving_resist is TRUE if this began by someone attempting to move. Return FALSE if still grabbed/failed to break out. Use this instead of resist_grab() directly.
+/mob/proc/attempt_resist_grab(moving_resist, forced, log = TRUE)
+ if(!pulledby) //not being grabbed
+ return TRUE
+ var/old_gs = pulledby.grab_state //how strong the grab is
+ var/old_pulled = pulledby
+ var/success = do_resist_grab(moving_resist, forced)
+ if(log)
+ log_combat(src, old_pulled, "[success? "successfully broke free of" : "failed to resist"] a grab of strength [old_gs][moving_resist? " (moving)":""][forced? " (forced)":""]")
+ return success
-/mob/proc/resist_grab(moving_resist)
- return 1 //returning 0 means we successfully broke free
+/*!
+ * Proc that actually does the grab resisting. Return TRUE if successful. Does not check that a grab exists! Use attempt_resist_grab() instead of this in general!
+ * Forced is if something other than the user mashing movement keys/pressing resist button did it, silent is if it makes messages (like "attempted to resist" and "broken free").
+ * Forced does NOT force success!
+ */
+/mob/proc/do_resist_grab(moving_resist, forced, silent = FALSE)
+ return FALSE
-/mob/living/resist_grab(moving_resist)
- . = 1
+/mob/living/do_resist_grab(moving_resist, forced, silent = FALSE)
+ . = ..()
if(pulledby.grab_state)
- if(!resting && prob(30/pulledby.grab_state))
+ if(CHECK_MOBILITY(src, MOBILITY_STAND) && prob(30/pulledby.grab_state))
visible_message("[src] has broken free of [pulledby]'s grip!")
- log_combat(pulledby, src, "broke grab")
pulledby.stop_pulling()
- return 0
- if(moving_resist && client) //we resisted by trying to move
+ return TRUE
+ else if(moving_resist && client) //we resisted by trying to move // this is a horrible system and whoever thought using client instead of mob is okay is not an okay person
client.move_delay = world.time + 20
+ visible_message("[src] resists against [pulledby]'s grip!")
else
pulledby.stop_pulling()
- return 0
+ return TRUE
/mob/living/proc/resist_buckle()
buckled.user_unbuckle_mob(src,src)
@@ -1048,7 +1053,7 @@
"[C] trips over [src] and falls!", \
"[C] topples over [src]!", \
"[C] leaps out of [src]'s way!")]")
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
/mob/living/ConveyorMove()
if((movement_type & FLYING) && !stat)
@@ -1058,61 +1063,6 @@
/mob/living/can_be_pulled()
return ..() && !(buckled && buckled.buckle_prevents_pull)
-//Updates canmove, lying and icons. Could perhaps do with a rename but I can't think of anything to describe it.
-//Robots, animals and brains have their own version so don't worry about them
-/mob/living/proc/update_canmove()
- var/ko = IsKnockdown() || IsUnconscious() || (stat && (stat != SOFT_CRIT || pulledby)) || (HAS_TRAIT(src, TRAIT_DEATHCOMA))
- var/move_and_fall = stat == SOFT_CRIT && !pulledby
- var/chokehold = pulledby && pulledby.grab_state >= GRAB_NECK
- var/buckle_lying = !(buckled && !buckled.buckle_lying)
- var/has_legs = get_num_legs()
- var/has_arms = get_num_arms()
- var/ignore_legs = get_leg_ignore()
- var/pinned = resting && pulledby && pulledby.grab_state >= GRAB_AGGRESSIVE // Cit change - adds pinning for aggressive-grabbing people on the ground
- if(ko || move_and_fall || IsStun() || chokehold) // Cit change - makes resting not force you to drop everything
- drop_all_held_items()
- unset_machine()
- if(pulling)
- stop_pulling()
- else if(resting) //CIT CHANGE - makes resting make you stop pulling and interacting with machines
- unset_machine() //CIT CHANGE - Ditto!
- if(pulling) //CIT CHANGE - Ditto.
- stop_pulling() //CIT CHANGE - Ditto...
- else if(has_legs || ignore_legs)
- lying = 0
- if (pulledby && isliving(pulledby))
- var/mob/living/L = pulledby
- L.update_pull_movespeed()
- if(buckled)
- lying = 90*buckle_lying
- else if(!lying)
- if(resting)
- lying = pick(90, 270) // Cit change - makes resting not force you to drop your held items
- if(has_gravity()) // Cit change - Ditto
- playsound(src, "bodyfall", 50, 1) // Cit change - Ditto!
- else if(ko || move_and_fall || (!has_legs && !ignore_legs) || chokehold)
- fall(forced = 1)
- canmove = !(ko || recoveringstam || pinned || IsStun() || IsFrozen() || chokehold || buckled || (!has_legs && !ignore_legs && !has_arms)) //Cit change - makes it plausible to move while resting, adds pinning and stamina crit
- density = !lying
- if(resting)
- ENABLE_BITFIELD(movement_type, CRAWLING)
- else
- DISABLE_BITFIELD(movement_type, CRAWLING)
- if(lying)
- if(layer == initial(layer)) //to avoid special cases like hiding larvas.
- layer = LYING_MOB_LAYER //so mob lying always appear behind standing mobs
- else
- if(layer == LYING_MOB_LAYER)
- layer = initial(layer)
- update_transform()
- if(!lying && lying_prev)
- if(client)
- client.move_delay = world.time + movement_delay()
- lying_prev = lying
- if(canmove && !intentionalresting && iscarbon(src) && client && client.prefs && client.prefs.autostand)//CIT CHANGE - adds autostanding as a preference
- addtimer(CALLBACK(src, .proc/resist_a_rest, TRUE), 0) //CIT CHANGE - ditto
- return canmove
-
/mob/living/proc/AddAbility(obj/effect/proc_holder/A)
abilities.Add(A)
A.on_gain(src)
@@ -1140,42 +1090,6 @@
return LINGHIVE_LINK
return LINGHIVE_NONE
-/mob/living/forceMove(atom/destination)
- stop_pulling()
- if(buckled)
- buckled.unbuckle_mob(src, force = TRUE)
- if(has_buckled_mobs())
- unbuckle_all_mobs(force = TRUE)
- . = ..()
- if(.)
- if(client)
- reset_perspective()
- update_canmove() //if the mob was asleep inside a container and then got forceMoved out we need to make them fall.
-
-/mob/living/proc/update_z(new_z) // 1+ to register, null to unregister
- if(isnull(new_z) && audiovisual_redirect)
- return
- if (registered_z != new_z)
- if (registered_z)
- SSmobs.clients_by_zlevel[registered_z] -= src
- if (client || audiovisual_redirect)
- if (new_z)
- SSmobs.clients_by_zlevel[new_z] += src
- for (var/I in length(SSidlenpcpool.idle_mobs_by_zlevel[new_z]) to 1 step -1) //Backwards loop because we're removing (guarantees optimal rather than worst-case performance), it's fine to use .len here but doesn't compile on 511
- var/mob/living/simple_animal/SA = SSidlenpcpool.idle_mobs_by_zlevel[new_z][I]
- if (SA)
- SA.toggle_ai(AI_ON) // Guarantees responsiveness for when appearing right next to mobs
- else
- SSidlenpcpool.idle_mobs_by_zlevel[new_z] -= SA
-
- registered_z = new_z
- else
- registered_z = null
-
-/mob/living/onTransitZ(old_z,new_z)
- ..()
- update_z(new_z)
-
/mob/living/MouseDrop(mob/over)
. = ..()
var/mob/living/user = usr
@@ -1222,14 +1136,6 @@
GLOB.dead_mob_list += src
. = ..()
switch(var_name)
- if("knockdown")
- SetKnockdown(var_value)
- if("stun")
- SetStun(var_value)
- if("unconscious")
- SetUnconscious(var_value)
- if("sleeping")
- SetSleeping(var_value)
if("eye_blind")
set_blindness(var_value)
if("eye_damage")
@@ -1261,21 +1167,20 @@
SetSleeping(clamp_unconscious_to)
if(AmountUnconscious() > clamp_unconscious_to)
SetUnconscious(clamp_unconscious_to)
- if(AmountStun() > clamp_immobility_to)
- SetStun(clamp_immobility_to)
- if(AmountKnockdown() > clamp_immobility_to)
- SetKnockdown(clamp_immobility_to)
+ HealAllImmobilityUpTo(clamp_immobility_to)
adjustStaminaLoss(min(0, -stamina_boost))
adjustStaminaLossBuffered(min(0, -stamina_buffer_boost))
if(scale_stamina_loss_recovery)
adjustStaminaLoss(min(-((getStaminaLoss() - stamina_loss_recovery_bypass) * scale_stamina_loss_recovery), 0))
if(put_on_feet)
- resting = FALSE
- lying = FALSE
+ set_resting(FALSE, TRUE, FALSE)
if(reset_misc)
stuttering = 0
updatehealth()
update_stamina()
- update_canmove()
+ update_mobility()
if(healing_chems)
reagents.add_reagent_list(healing_chems)
+
+/mob/living/canface()
+ return ..() && CHECK_MOBILITY(src, MOBILITY_MOVE)
diff --git a/code/modules/mob/living/living_defense.dm b/code/modules/mob/living/living_defense.dm
index 6a14cce4af..9c67498935 100644
--- a/code/modules/mob/living/living_defense.dm
+++ b/code/modules/mob/living/living_defense.dm
@@ -261,21 +261,21 @@
else
visible_message("[user] has grabbed [src] aggressively!", \
"[user] has grabbed you aggressively!")
- drop_all_held_items()
+ update_mobility()
stop_pulling()
log_combat(user, src, "grabbed", addition="aggressive grab[add_log]")
if(GRAB_NECK)
log_combat(user, src, "grabbed", addition="neck grab")
visible_message("[user] has grabbed [src] by the neck!",\
"[user] has grabbed you by the neck!")
- update_canmove() //we fall down
+ update_mobility() //we fall down
if(!buckled && !density)
Move(user.loc)
if(GRAB_KILL)
log_combat(user, src, "strangled", addition="kill grab")
visible_message("[user] is strangling [src]!", \
"[user] is strangling you!")
- update_canmove() //we fall down
+ update_mobility() //we fall down
if(!buckled && !density)
Move(user.loc)
return 1
diff --git a/code/modules/mob/living/living_defines.dm b/code/modules/mob/living/living_defines.dm
index 7106d003ee..ed46568489 100644
--- a/code/modules/mob/living/living_defines.dm
+++ b/code/modules/mob/living/living_defines.dm
@@ -22,6 +22,8 @@
var/staminaloss = 0 //Stamina damage, or exhaustion. You recover it slowly naturally, and are knocked down if it gets too high. Holodeck and hallucinations deal this.
var/crit_threshold = HEALTH_THRESHOLD_CRIT // when the mob goes from "normal" to crit
+ var/mobility_flags = MOBILITY_FLAGS_DEFAULT
+
var/confused = 0 //Makes the mob move in random directions.
var/hallucination = 0 //Directly affects how long a mob will hallucinate for
@@ -112,4 +114,7 @@
var/drag_slowdown = TRUE //Whether the mob is slowed down when dragging another prone mob
- var/rotate_on_lying = FALSE
\ No newline at end of file
+ var/rotate_on_lying = FALSE
+
+ /// Next world.time when we can get the "you can't move while buckled to [thing]" message.
+ var/buckle_message_cooldown = 0
diff --git a/code/modules/mob/living/living_mobility.dm b/code/modules/mob/living/living_mobility.dm
new file mode 100644
index 0000000000..4b2afd0448
--- /dev/null
+++ b/code/modules/mob/living/living_mobility.dm
@@ -0,0 +1,155 @@
+/// IN THE FUTURE, WE WILL PROBABLY REFACTOR TO LESSEN THE NEED FOR UPDATE_MOBILITY, BUT FOR NOW.. WE CAN START DOING THIS.
+/// FOR BLOCKING MOVEMENT, USE TRAIT_MOBILITY_NOMOVE AS MUCH AS POSSIBLE. IT WILL MAKE REFACTORS IN THE FUTURE EASIER.
+/mob/living/ComponentInitialize()
+ . = ..()
+ RegisterSignal(src, SIGNAL_TRAIT(TRAIT_MOBILITY_NOMOVE), .proc/update_mobility)
+ RegisterSignal(src, SIGNAL_TRAIT(TRAIT_MOBILITY_NOPICKUP), .proc/update_mobility)
+ RegisterSignal(src, SIGNAL_TRAIT(TRAIT_MOBILITY_NOUSE), .proc/update_mobility)
+
+//Stuff like mobility flag updates, resting updates, etc.
+
+//Force-set resting variable, without needing to resist/etc.
+/mob/living/proc/set_resting(new_resting, silent = FALSE, updating = TRUE)
+ if(new_resting != resting)
+ resting = new_resting
+ if(!silent)
+ to_chat(src, "You are now [resting? "resting" : "getting up"].")
+ update_resting(updating)
+
+/mob/living/proc/update_resting(update_mobility = TRUE)
+ if(update_mobility)
+ update_mobility()
+
+//Force mob to rest, does NOT do stamina damage.
+//It's really not recommended to use this proc to give feedback, hence why silent is defaulting to true.
+/mob/living/proc/KnockToFloor(disarm_items = FALSE, silent = TRUE, updating = TRUE)
+ if(!silent && !resting)
+ to_chat(src, "You are knocked to the floor!")
+ set_resting(TRUE, TRUE, updating)
+ if(disarm_items)
+ drop_all_held_items()
+
+/mob/living/proc/lay_down()
+ set name = "Rest"
+ set category = "IC"
+ if(client?.prefs?.autostand)
+ intentionalresting = !intentionalresting
+ to_chat(src, "You are now attempting to [intentionalresting ? "[!resting ? "lay down and ": ""]stay down" : "[resting ? "get up and ": ""]stay up"].")
+ if(intentionalresting && !resting)
+ set_resting(TRUE, FALSE)
+ else
+ resist_a_rest()
+ else
+ if(!resting)
+ set_resting(TRUE, FALSE)
+ to_chat(src, "You are now laying down.")
+ else
+ resist_a_rest()
+
+/mob/living/proc/resist_a_rest(automatic = FALSE, ignoretimer = FALSE) //Lets mobs resist out of resting. Major QOL change with combat reworks.
+ set_resting(FALSE, TRUE)
+ return TRUE
+
+//Updates canmove, lying and icons. Could perhaps do with a rename but I can't think of anything to describe it.
+//Robots, animals and brains have their own version so don't worry about them
+/mob/living/proc/update_mobility()
+ var/stat_softcrit = stat == SOFT_CRIT
+ var/stat_conscious = (stat == CONSCIOUS) || stat_softcrit
+
+ var/conscious = !IsUnconscious() && stat_conscious && !HAS_TRAIT(src, TRAIT_DEATHCOMA)
+
+ var/has_arms = get_num_arms()
+ var/has_legs = get_num_legs()
+ var/ignore_legs = get_leg_ignore()
+ var/stun = IsStun()
+ var/paralyze = IsParalyzed()
+ var/knockdown = IsKnockdown()
+ var/daze = IsDazed()
+ var/immobilize = IsImmobilized()
+
+ var/chokehold = pulledby && pulledby.grab_state >= GRAB_NECK
+ var/restrained = restrained()
+ var/pinned = resting && pulledby && pulledby.grab_state >= GRAB_AGGRESSIVE // Cit change - adds pinning for aggressive-grabbing people on the ground
+ var/has_limbs = has_arms || ignore_legs || has_legs
+ var/canmove = !immobilize && !stun && conscious && !paralyze && (!stat_softcrit || !pulledby) && !chokehold && !IsFrozen() && has_limbs && !pinned && !recoveringstam
+ var/canresist = !stun && conscious && !stat_softcrit && !paralyze && has_limbs && !recoveringstam
+
+ if(canmove)
+ mobility_flags |= MOBILITY_MOVE
+ else
+ mobility_flags &= ~MOBILITY_MOVE
+
+ if(canresist)
+ mobility_flags |= MOBILITY_RESIST
+ else
+ mobility_flags &= ~MOBILITY_RESIST
+
+ var/canstand_involuntary = conscious && !stat_softcrit && !knockdown && !chokehold && !paralyze && (ignore_legs || has_legs) && !(buckled && buckled.buckle_lying) && !recoveringstam
+ var/canstand = canstand_involuntary && !resting
+
+ var/should_be_lying = !canstand
+ if(buckled)
+ if(buckled.buckle_lying != -1)
+ should_be_lying = buckled.buckle_lying
+
+ if(should_be_lying)
+ mobility_flags &= ~MOBILITY_STAND
+ if(!lying) //force them on the ground
+ lying = pick(90, 270)
+ if(has_gravity() && !buckled)
+ playsound(src, "bodyfall", 20, 1)
+ else
+ mobility_flags |= MOBILITY_STAND
+ lying = 0
+
+ if(should_be_lying || restrained || incapacitated())
+ mobility_flags &= ~(MOBILITY_UI|MOBILITY_PULL)
+ else
+ mobility_flags |= MOBILITY_UI|MOBILITY_PULL
+
+ var/canitem_general = !paralyze && !stun && conscious && !(stat_softcrit) && !chokehold && !restrained && has_arms && !recoveringstam
+ if(canitem_general)
+ mobility_flags |= (MOBILITY_USE | MOBILITY_PICKUP | MOBILITY_STORAGE | MOBILITY_HOLD)
+ else
+ mobility_flags &= ~(MOBILITY_USE | MOBILITY_PICKUP | MOBILITY_STORAGE | MOBILITY_HOLD)
+
+ if(HAS_TRAIT(src, TRAIT_MOBILITY_NOMOVE))
+ DISABLE_BITFIELD(mobility_flags, MOBILITY_MOVE)
+ if(HAS_TRAIT(src, TRAIT_MOBILITY_NOPICKUP))
+ DISABLE_BITFIELD(mobility_flags, MOBILITY_PICKUP)
+ if(HAS_TRAIT(src, TRAIT_MOBILITY_NOUSE))
+ DISABLE_BITFIELD(mobility_flags, MOBILITY_USE)
+
+ if(daze)
+ DISABLE_BITFIELD(mobility_flags, MOBILITY_USE)
+
+ //Handle update-effects.
+ if(!CHECK_MOBILITY(src, MOBILITY_HOLD))
+ drop_all_held_items()
+ if(!CHECK_MOBILITY(src, MOBILITY_PULL))
+ if(pulling)
+ stop_pulling()
+ if(!CHECK_MOBILITY(src, MOBILITY_UI))
+ unset_machine()
+
+ if(isliving(pulledby))
+ var/mob/living/L = pulledby
+ L.update_pull_movespeed()
+
+ //Handle lying down, voluntary or involuntary
+ density = !lying
+ if(lying)
+ set_resting(TRUE, TRUE, FALSE)
+ if(layer == initial(layer)) //to avoid special cases like hiding larvas.
+ layer = LYING_MOB_LAYER //so mob lying always appear behind standing mobs
+ else
+ if(layer == LYING_MOB_LAYER)
+ layer = initial(layer)
+ update_transform()
+ lying_prev = lying
+
+ //Handle citadel autoresist
+ if(CHECK_MOBILITY(src, MOBILITY_MOVE) && !intentionalresting && canstand_involuntary && iscarbon(src) && client?.prefs?.autostand)//CIT CHANGE - adds autostanding as a preference
+ addtimer(CALLBACK(src, .proc/resist_a_rest, TRUE), 0) //CIT CHANGE - ditto
+
+ return mobility_flags
diff --git a/code/modules/mob/living/living_movement.dm b/code/modules/mob/living/living_movement.dm
index e0ea6350d7..f278d22891 100644
--- a/code/modules/mob/living/living_movement.dm
+++ b/code/modules/mob/living/living_movement.dm
@@ -12,10 +12,14 @@
return (!density || lying)
if(buckled == mover)
return TRUE
- if(ismob(mover))
- if (mover in buckled_mobs)
+ if(!ismob(mover))
+ if(mover.throwing?.thrower == src)
return TRUE
- return (!mover.density || !density || lying || (mover.throwing && mover.throwing.thrower == src && !ismob(mover)))
+ if(ismob(mover))
+ if(mover in buckled_mobs)
+ return TRUE
+ var/mob/living/L = mover //typecast first, check isliving and only check this if living using short circuit
+ return (!density || (isliving(mover)? L.can_move_under_living(src) : !mover.density))
/mob/living/toggle_move_intent()
. = ..()
@@ -25,6 +29,10 @@
update_move_intent_slowdown()
return ..()
+/// whether or not we can slide under another living mob. defaults to if we're not dense. CanPass should check "overriding circumstances" like buckled mobs/having PASSMOB flag, etc.
+/mob/living/proc/can_move_under_living(mob/living/other)
+ return !density
+
/mob/living/proc/update_move_intent_slowdown()
var/mod = 0
if(m_intent == MOVE_INTENT_WALK)
@@ -50,4 +58,69 @@
remove_movespeed_modifier(MOVESPEED_ID_PRONE_DRAGGING)
/mob/living/canZMove(dir, turf/target)
- return can_zTravel(target, dir) && (movement_type & FLYING)
\ No newline at end of file
+ return can_zTravel(target, dir) && (movement_type & FLYING)
+
+/mob/living/Move(atom/newloc, direct)
+ if (buckled && buckled.loc != newloc) //not updating position
+ if (!buckled.anchored)
+ return buckled.Move(newloc, direct)
+ else
+ return 0
+
+ var/old_direction = dir
+ var/turf/T = loc
+
+ if(pulling)
+ update_pull_movespeed()
+
+ . = ..()
+
+ if(pulledby && moving_diagonally != FIRST_DIAG_STEP && get_dist(src, pulledby) > 1)//separated from our puller and not in the middle of a diagonal move.
+ pulledby.stop_pulling()
+
+ if(active_storage && !(CanReach(active_storage.parent,view_only = TRUE)))
+ active_storage.close(src)
+
+ if(lying && !buckled && prob(getBruteLoss()*200/maxHealth))
+ makeTrail(newloc, T, old_direction)
+
+/mob/living/forceMove(atom/destination)
+ stop_pulling()
+ if(buckled)
+ buckled.unbuckle_mob(src, force = TRUE)
+ if(has_buckled_mobs())
+ unbuckle_all_mobs(force = TRUE)
+ . = ..()
+ if(.)
+ if(client)
+ reset_perspective()
+ update_mobility() //if the mob was asleep inside a container and then got forceMoved out we need to make them fall.
+
+/mob/living/proc/update_z(new_z) // 1+ to register, null to unregister
+ if(isnull(new_z) && audiovisual_redirect)
+ return
+ if (registered_z != new_z)
+ if (registered_z)
+ SSmobs.clients_by_zlevel[registered_z] -= src
+ if (client || audiovisual_redirect)
+ if (new_z)
+ SSmobs.clients_by_zlevel[new_z] += src
+ for (var/I in length(SSidlenpcpool.idle_mobs_by_zlevel[new_z]) to 1 step -1) //Backwards loop because we're removing (guarantees optimal rather than worst-case performance), it's fine to use .len here but doesn't compile on 511
+ var/mob/living/simple_animal/SA = SSidlenpcpool.idle_mobs_by_zlevel[new_z][I]
+ if (SA)
+ SA.toggle_ai(AI_ON) // Guarantees responsiveness for when appearing right next to mobs
+ else
+ SSidlenpcpool.idle_mobs_by_zlevel[new_z] -= SA
+
+ registered_z = new_z
+ else
+ registered_z = null
+
+/mob/living/onTransitZ(old_z,new_z)
+ ..()
+ update_z(new_z)
+
+/mob/living/canface()
+ if(!CHECK_MOBILITY(src, MOBILITY_MOVE))
+ return FALSE
+ return ..()
diff --git a/code/modules/mob/living/silicon/ai/ai.dm b/code/modules/mob/living/silicon/ai/ai.dm
index 3b15c47bcb..703e5cefac 100644
--- a/code/modules/mob/living/silicon/ai/ai.dm
+++ b/code/modules/mob/living/silicon/ai/ai.dm
@@ -18,7 +18,7 @@
icon_state = "ai"
move_resist = MOVE_FORCE_OVERPOWERING
density = TRUE
- canmove = FALSE
+ mobility_flags = ALL
status_flags = CANSTUN|CANPUSH
a_intent = INTENT_HARM //so we always get pushed instead of trying to swap
sight = SEE_TURFS | SEE_MOBS | SEE_OBJS
@@ -324,8 +324,10 @@
to_chat(src, "You are now [is_anchored ? "" : "un"]anchored.")
// the message in the [] will change depending whether or not the AI is anchored
-/mob/living/silicon/ai/update_canmove() //If the AI dies, mobs won't go through it anymore
- return 0
+// AIs are immobile
+/mob/living/silicon/ai/update_mobility()
+ mobility_flags = ALL
+ return ALL
/mob/living/silicon/ai/proc/ai_cancel_call()
set category = "Malfunction"
@@ -987,7 +989,7 @@
deployed_shell.undeploy()
diag_hud_set_deployed()
-/mob/living/silicon/ai/resist()
+/mob/living/silicon/ai/do_resist()
return
/mob/living/silicon/ai/spawned/Initialize(mapload, datum/ai_laws/L, mob/target_ai)
diff --git a/code/modules/mob/living/silicon/ai/death.dm b/code/modules/mob/living/silicon/ai/death.dm
index f978b7b697..afabafd929 100644
--- a/code/modules/mob/living/silicon/ai/death.dm
+++ b/code/modules/mob/living/silicon/ai/death.dm
@@ -15,7 +15,7 @@
cameraFollow = null
move_resist = MOVE_FORCE_NORMAL
- update_canmove()
+ update_mobility()
if(eyeobj)
eyeobj.setLoc(get_turf(src))
set_eyeobj_visible(FALSE)
diff --git a/code/modules/mob/living/silicon/pai/death.dm b/code/modules/mob/living/silicon/pai/death.dm
index 414ee2f3d7..c60d84438c 100644
--- a/code/modules/mob/living/silicon/pai/death.dm
+++ b/code/modules/mob/living/silicon/pai/death.dm
@@ -2,7 +2,7 @@
if(stat == DEAD)
return
stat = DEAD
- canmove = 0
+ update_mobility()
update_sight()
clear_fullscreens()
diff --git a/code/modules/mob/living/silicon/pai/pai.dm b/code/modules/mob/living/silicon/pai/pai.dm
index 074e637120..a65c1d24ac 100644
--- a/code/modules/mob/living/silicon/pai/pai.dm
+++ b/code/modules/mob/living/silicon/pai/pai.dm
@@ -80,7 +80,7 @@
var/radio_short_cooldown = 3 MINUTES
var/radio_short_timerid
- canmove = FALSE
+ mobility_flags = NONE
var/silent = FALSE
var/brightness_power = 5
@@ -101,7 +101,6 @@
START_PROCESSING(SSfastprocess, src)
GLOB.pai_list += src
make_laws()
- canmove = 0
if(!istype(P)) //when manually spawning a pai, we create a card to put it into.
var/newcardloc = P
P = new /obj/item/paicard(newcardloc)
diff --git a/code/modules/mob/living/silicon/pai/pai_defense.dm b/code/modules/mob/living/silicon/pai/pai_defense.dm
index 93cf10706a..0477492c0a 100644
--- a/code/modules/mob/living/silicon/pai/pai_defense.dm
+++ b/code/modules/mob/living/silicon/pai/pai_defense.dm
@@ -8,7 +8,7 @@
if(. & EMP_PROTECT_SELF)
return
take_holo_damage(50/severity)
- Knockdown(400/severity)
+ DefaultCombatKnockdown(400/severity)
silent = max(silent, (PAI_EMP_SILENCE_DURATION) / SSmobs.wait / severity)
if(holoform)
fold_in(force = TRUE)
@@ -23,10 +23,10 @@
qdel(src)
if(2)
fold_in(force = 1)
- Knockdown(400)
+ DefaultCombatKnockdown(400)
if(3)
fold_in(force = 1)
- Knockdown(200)
+ DefaultCombatKnockdown(200)
//ATTACK HAND IGNORING PARENT RETURN VALUE
/mob/living/silicon/pai/attack_hand(mob/living/carbon/human/user)
@@ -98,7 +98,7 @@
take_holo_damage(amount * 0.25)
/mob/living/silicon/pai/adjustOrganLoss(slot, amount, maximum = 500) //I kept this in, unlike tg
- Knockdown(amount * 0.2)
+ DefaultCombatKnockdown(amount * 0.2)
/mob/living/silicon/pai/getBruteLoss()
return emittermaxhealth - emitterhealth
diff --git a/code/modules/mob/living/silicon/pai/pai_shell.dm b/code/modules/mob/living/silicon/pai/pai_shell.dm
index 3734c7f1f2..7de983229e 100644
--- a/code/modules/mob/living/silicon/pai/pai_shell.dm
+++ b/code/modules/mob/living/silicon/pai/pai_shell.dm
@@ -17,7 +17,6 @@
return FALSE
emitter_next_use = world.time + emittercd
- canmove = TRUE
density = TRUE
if(istype(card.loc, /obj/item/pda))
var/obj/item/pda/P = card.loc
@@ -37,6 +36,7 @@
C.push_data()
forceMove(get_turf(card))
card.forceMove(src)
+ update_mobility()
if(client)
client.perspective = EYE_PERSPECTIVE
client.eye = src
@@ -63,12 +63,11 @@
var/turf/T = drop_location()
card.forceMove(T)
forceMove(card)
- canmove = FALSE
density = FALSE
set_light(0)
holoform = FALSE
- if(resting)
- lay_down()
+ set_resting(FALSE, TRUE, FALSE)
+ update_mobility()
/mob/living/silicon/pai/proc/choose_chassis()
if(!isturf(loc) && loc != card)
diff --git a/code/modules/mob/living/silicon/robot/death.dm b/code/modules/mob/living/silicon/robot/death.dm
index 23531e9f72..6a5338c1f5 100644
--- a/code/modules/mob/living/silicon/robot/death.dm
+++ b/code/modules/mob/living/silicon/robot/death.dm
@@ -21,7 +21,7 @@
locked = FALSE //unlock cover
- update_canmove()
+ update_mobility()
if(!QDELETED(builtInCamera) && builtInCamera.status)
builtInCamera.toggle_cam(src,0)
update_headlamp(1) //So borg lights are disabled when killed.
diff --git a/code/modules/mob/living/silicon/robot/life.dm b/code/modules/mob/living/silicon/robot/life.dm
index 26305eedb1..cf67517c52 100644
--- a/code/modules/mob/living/silicon/robot/life.dm
+++ b/code/modules/mob/living/silicon/robot/life.dm
@@ -91,12 +91,3 @@
add_overlay(fire_overlay)
else
cut_overlay(fire_overlay)
-
-/mob/living/silicon/robot/update_canmove()
- if(stat || buckled || lockcharge || resting) //CITADEL EDIT resting dogborg-os
- canmove = 0
- else
- canmove = 1
- update_transform()
- update_action_buttons_icon()
- return canmove
diff --git a/code/modules/mob/living/silicon/robot/robot.dm b/code/modules/mob/living/silicon/robot/robot.dm
index 86e3ccad24..d4f520a611 100644
--- a/code/modules/mob/living/silicon/robot/robot.dm
+++ b/code/modules/mob/living/silicon/robot/robot.dm
@@ -64,7 +64,7 @@
var/lawupdate = 1 //Cyborgs will sync their laws with their AI by default
var/scrambledcodes = 0 // Used to determine if a borg shows up on the robotics console. Setting to one hides them.
- var/lockcharge //Boolean of whether the borg is locked down or not
+ var/locked_down //Boolean of whether the borg is locked down or not
var/toner = 0
var/tonermax = 40
@@ -493,7 +493,7 @@
update_icons()
else if(istype(W, /obj/item/wrench) && opened && !cell) //Deconstruction. The flashes break from the fall, to prevent this from being a ghetto reset module.
- if(!lockcharge)
+ if(!locked_down)
to_chat(user, "[src]'s bolts spark! Maybe you should lock them down first!")
spark_system.start()
return
@@ -655,65 +655,6 @@
/mob/living/silicon/robot/regenerate_icons()
return update_icons()
-/mob/living/silicon/robot/update_icons()
- cut_overlays()
- icon_state = module.cyborg_base_icon
- //Citadel changes start here - Allows modules to use different icon files, and allows modules to specify a pixel offset
- icon = (module.cyborg_icon_override ? module.cyborg_icon_override : initial(icon))
- if(laser)
- add_overlay("laser")//Is this even used??? - Yes borg/inventory.dm
- if(disabler)
- add_overlay("disabler")//ditto
-
- if(sleeper_g && module.sleeper_overlay)
- add_overlay("[module.sleeper_overlay]_g[sleeper_nv ? "_nv" : ""]")
- if(sleeper_r && module.sleeper_overlay)
- add_overlay("[module.sleeper_overlay]_r[sleeper_nv ? "_nv" : ""]")
- if(stat == DEAD && module.has_snowflake_deadsprite)
- icon_state = "[module.cyborg_base_icon]-wreck"
-
- if(module.cyborg_pixel_offset)
- pixel_x = module.cyborg_pixel_offset
- //End of citadel changes
-
- if(module.cyborg_base_icon == "robot")
- icon = 'icons/mob/robots.dmi'
- pixel_x = initial(pixel_x)
- if(stat != DEAD && !(IsUnconscious() || IsStun() || IsKnockdown() || low_power_mode)) //Not dead, not stunned.
- if(!eye_lights)
- eye_lights = new()
- if(lamp_intensity > 2)
- eye_lights.icon_state = "[module.special_light_key ? "[module.special_light_key]":"[module.cyborg_base_icon]"]_l"
- else
- eye_lights.icon_state = "[module.special_light_key ? "[module.special_light_key]":"[module.cyborg_base_icon]"]_e[is_servant_of_ratvar(src) ? "_r" : ""]"
- eye_lights.icon = icon
- add_overlay(eye_lights)
-
- if(opened)
- if(wiresexposed)
- add_overlay("ov-opencover +w")
- else if(cell)
- add_overlay("ov-opencover +c")
- else
- add_overlay("ov-opencover -c")
- if(hat)
- var/mutable_appearance/head_overlay = hat.build_worn_icon(state = hat.icon_state, default_layer = 20, default_icon_file = 'icons/mob/head.dmi')
- head_overlay.pixel_y += hat_offset
- add_overlay(head_overlay)
- update_fire()
-
- if(client && stat != DEAD && module.dogborg == TRUE)
- if(resting)
- if(sitting)
- icon_state = "[module.cyborg_base_icon]-sit"
- if(bellyup)
- icon_state = "[module.cyborg_base_icon]-bellyup"
- else if(!sitting && !bellyup)
- icon_state = "[module.cyborg_base_icon]-rest"
- cut_overlays()
- else
- icon_state = "[module.cyborg_base_icon]"
-
/mob/living/silicon/robot/proc/self_destruct()
if(emagged)
if(mmi)
@@ -728,8 +669,6 @@
connected_ai.connected_robots -= src
src.connected_ai = null
lawupdate = 0
- lockcharge = 0
- canmove = 1
scrambledcodes = 1
//Disconnect it's camera so it's not so easily tracked.
if(!QDELETED(builtInCamera))
@@ -738,6 +677,7 @@
// Instead of being listed as "deactivated". The downside is that I'm going
// to have to check if every camera is null or not before doing anything, to prevent runtime errors.
// I could change the network to null but I don't know what would happen, and it seems too hacky for me.
+ update_mobility()
/mob/living/silicon/robot/mode()
set name = "Activate Held Object"
@@ -759,8 +699,8 @@
throw_alert("locked", /obj/screen/alert/locked)
else
clear_alert("locked")
- lockcharge = state
- update_canmove()
+ locked_down = state
+ update_mobility()
/mob/living/silicon/robot/proc/SetEmagged(new_state)
emagged = new_state
@@ -949,7 +889,7 @@
to_chat(connected_ai, "
NOTICE - Remote telemetry lost with [name].
")
/mob/living/silicon/robot/canUseTopic(atom/movable/M, be_close=FALSE, no_dextery=FALSE, no_tk=FALSE)
- if(stat || lockcharge || low_power_mode)
+ if(stat || locked_down || low_power_mode)
to_chat(src, "You can't do that right now!")
return FALSE
if(be_close && !in_range(M, src))
@@ -1025,17 +965,17 @@
if(health <= -maxHealth) //die only once
death()
return
- if(IsUnconscious() || IsStun() || IsKnockdown() || getOxyLoss() > maxHealth*0.5)
+ if(IsUnconscious() || IsStun() || IsParalyzed() || getOxyLoss() > maxHealth*0.5)
if(stat == CONSCIOUS)
stat = UNCONSCIOUS
blind_eyes(1)
- update_canmove()
+ update_mobility()
update_headlamp()
else
if(stat == UNCONSCIOUS)
stat = CONSCIOUS
adjust_blindness(-1)
- update_canmove()
+ update_mobility()
update_headlamp()
diag_hud_set_status()
diag_hud_set_health()
@@ -1269,20 +1209,6 @@
for(var/i in connected_ai.aicamera.stored)
aicamera.stored[i] = TRUE
-/mob/living/silicon/robot/lay_down()
- ..()
- update_canmove()
-
-/mob/living/silicon/robot/update_canmove()
- ..()
- if(client && stat != DEAD && dogborg == FALSE)
- if(resting)
- cut_overlays()
- icon_state = "[module.cyborg_base_icon]-rest"
- else
- icon_state = "[module.cyborg_base_icon]"
- update_icons()
-
/mob/living/silicon/robot/proc/rest_style()
set name = "Switch Rest Style"
set category = "Robot Commands"
diff --git a/code/modules/mob/living/silicon/robot/robot_defense.dm b/code/modules/mob/living/silicon/robot/robot_defense.dm
index e7b252a248..5750543a92 100644
--- a/code/modules/mob/living/silicon/robot/robot_defense.dm
+++ b/code/modules/mob/living/silicon/robot/robot_defense.dm
@@ -36,7 +36,7 @@
"[M] has disabled [src]'s active module!", null, COMBAT_MESSAGE_RANGE)
log_combat(M, src, "disarmed", "[I ? " removing \the [I]" : ""]")
else
- Stun(40)
+ Paralyze(40)
step(src,get_dir(M,src))
log_combat(M, src, "pushed")
visible_message("[M] has forced back [src]!", \
@@ -86,9 +86,9 @@
return
switch(severity)
if(1)
- Stun(160)
+ Paralyze(160)
if(2)
- Stun(60)
+ Paralyze(60)
/mob/living/silicon/robot/emag_act(mob/user)
diff --git a/code/modules/mob/living/silicon/robot/robot_mobility.dm b/code/modules/mob/living/silicon/robot/robot_mobility.dm
new file mode 100644
index 0000000000..c5863b523f
--- /dev/null
+++ b/code/modules/mob/living/silicon/robot/robot_mobility.dm
@@ -0,0 +1,15 @@
+/mob/living/silicon/robot/update_mobility()
+ var/newflags = NONE
+ if(!stat)
+ if(!resting)
+ newflags |= (MOBILITY_STAND | MOBILITY_RESIST)
+ if(!locked_down)
+ newflags |= MOBILITY_MOVE
+ newflags |= MOBILITY_PULL
+ if(!locked_down)
+ newflags |= MOBILITY_FLAGS_ANY_INTERACTION
+ mobility_flags = newflags
+ update_transform()
+ update_action_buttons_icon()
+ update_icons()
+ return mobility_flags
diff --git a/code/modules/mob/living/silicon/robot/robot_modules.dm b/code/modules/mob/living/silicon/robot/robot_modules.dm
index f3e0816b1b..d93f187bb2 100644
--- a/code/modules/mob/living/silicon/robot/robot_modules.dm
+++ b/code/modules/mob/living/silicon/robot/robot_modules.dm
@@ -257,7 +257,7 @@
/obj/item/robot_module/proc/do_transform_delay()
var/mob/living/silicon/robot/R = loc
- var/prev_lockcharge = R.lockcharge
+ var/prev_locked_down = R.locked_down
sleep(1)
flick("[cyborg_base_icon]_transform", R)
R.notransform = TRUE
@@ -267,7 +267,7 @@
for(var/i in 1 to 4)
playsound(R, pick('sound/items/drill_use.ogg', 'sound/items/jaws_cut.ogg', 'sound/items/jaws_pry.ogg', 'sound/items/welder.ogg', 'sound/items/ratchet.ogg'), 80, 1, -1)
sleep(7)
- if(!prev_lockcharge)
+ if(!prev_locked_down)
R.SetLockdown(0)
R.setDir(SOUTH)
R.anchored = FALSE
diff --git a/code/modules/mob/living/silicon/robot/update_icons.dm b/code/modules/mob/living/silicon/robot/update_icons.dm
new file mode 100644
index 0000000000..8d40e35706
--- /dev/null
+++ b/code/modules/mob/living/silicon/robot/update_icons.dm
@@ -0,0 +1,59 @@
+/// this is bad code
+/mob/living/silicon/robot/update_icons()
+ cut_overlays()
+ icon_state = module.cyborg_base_icon
+ //Citadel changes start here - Allows modules to use different icon files, and allows modules to specify a pixel offset
+ icon = (module.cyborg_icon_override ? module.cyborg_icon_override : initial(icon))
+ if(laser)
+ add_overlay("laser")//Is this even used??? - Yes borg/inventory.dm
+ if(disabler)
+ add_overlay("disabler")//ditto
+
+ if(sleeper_g && module.sleeper_overlay)
+ add_overlay("[module.sleeper_overlay]_g[sleeper_nv ? "_nv" : ""]")
+ if(sleeper_r && module.sleeper_overlay)
+ add_overlay("[module.sleeper_overlay]_r[sleeper_nv ? "_nv" : ""]")
+ if(stat == DEAD && module.has_snowflake_deadsprite)
+ icon_state = "[module.cyborg_base_icon]-wreck"
+
+ if(module.cyborg_pixel_offset)
+ pixel_x = module.cyborg_pixel_offset
+ //End of citadel changes
+
+ if(module.cyborg_base_icon == "robot")
+ icon = 'icons/mob/robots.dmi'
+ pixel_x = initial(pixel_x)
+ if(stat != DEAD && !(IsUnconscious() ||IsStun() || IsKnockdown() || IsParalyzed() || low_power_mode)) //Not dead, not stunned.
+ if(!eye_lights)
+ eye_lights = new()
+ if(lamp_intensity > 2)
+ eye_lights.icon_state = "[module.special_light_key ? "[module.special_light_key]":"[module.cyborg_base_icon]"]_l"
+ else
+ eye_lights.icon_state = "[module.special_light_key ? "[module.special_light_key]":"[module.cyborg_base_icon]"]_e[is_servant_of_ratvar(src) ? "_r" : ""]"
+ eye_lights.icon = icon
+ add_overlay(eye_lights)
+
+ if(opened)
+ if(wiresexposed)
+ add_overlay("ov-opencover +w")
+ else if(cell)
+ add_overlay("ov-opencover +c")
+ else
+ add_overlay("ov-opencover -c")
+ if(hat)
+ var/mutable_appearance/head_overlay = hat.build_worn_icon(state = hat.icon_state, default_layer = 20, default_icon_file = 'icons/mob/head.dmi')
+ head_overlay.pixel_y += hat_offset
+ add_overlay(head_overlay)
+ update_fire()
+
+ if(client && stat != DEAD && module.dogborg == TRUE)
+ if(resting)
+ if(sitting)
+ icon_state = "[module.cyborg_base_icon]-sit"
+ if(bellyup)
+ icon_state = "[module.cyborg_base_icon]-bellyup"
+ else if(!sitting && !bellyup)
+ icon_state = "[module.cyborg_base_icon]-rest"
+ cut_overlays()
+ else
+ icon_state = "[module.cyborg_base_icon]"
diff --git a/code/modules/mob/living/silicon/silicon_defense.dm b/code/modules/mob/living/silicon/silicon_defense.dm
index 4cd8dd47e4..5d1d2610b9 100644
--- a/code/modules/mob/living/silicon/silicon_defense.dm
+++ b/code/modules/mob/living/silicon/silicon_defense.dm
@@ -32,7 +32,7 @@
var/damage = rand(M.melee_damage_lower, M.melee_damage_upper)
if(prob(damage))
for(var/mob/living/N in buckled_mobs)
- N.Knockdown(20)
+ N.DefaultCombatKnockdown(20)
unbuckle_mob(N)
N.visible_message("[N] is knocked off of [src] by [M]!")
switch(M.melee_damage_type)
@@ -106,7 +106,7 @@
for(var/mob/living/M in buckled_mobs)
if(prob(severity*50))
unbuckle_mob(M)
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
M.visible_message("[M] is thrown off of [src]!")
flash_act(affect_silicon = 1)
@@ -123,7 +123,7 @@
for(var/mob/living/M in buckled_mobs)
M.visible_message("[M] is knocked off of [src]!")
unbuckle_mob(M)
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
if(P.stun || P.knockdown)
for(var/mob/living/M in buckled_mobs)
unbuckle_mob(M)
diff --git a/code/modules/mob/living/simple_animal/astral.dm b/code/modules/mob/living/simple_animal/astral.dm
index 6edf99981a..ebc89e2577 100644
--- a/code/modules/mob/living/simple_animal/astral.dm
+++ b/code/modules/mob/living/simple_animal/astral.dm
@@ -32,7 +32,6 @@
/mob/living/simple_animal/astral/death()
icon_state = "shade_dead"
Stun(1000)
- canmove = 0
friendly = "deads at"
pseudo_death = TRUE
incorporeal_move = 0
diff --git a/code/modules/mob/living/simple_animal/bot/bot.dm b/code/modules/mob/living/simple_animal/bot/bot.dm
index d5e6f687fb..75364b2845 100644
--- a/code/modules/mob/living/simple_animal/bot/bot.dm
+++ b/code/modules/mob/living/simple_animal/bot/bot.dm
@@ -115,7 +115,7 @@
if(stat)
return FALSE
on = TRUE
- canmove = TRUE
+ update_mobility()
set_light(initial(light_range))
update_icon()
diag_hud_set_botstat()
@@ -123,7 +123,7 @@
/mob/living/simple_animal/bot/proc/turn_off()
on = FALSE
- canmove = FALSE
+ update_mobility()
set_light(0)
bot_reset() //Resets an AI's call, should it exist.
update_icon()
@@ -160,11 +160,11 @@
path_hud.add_to_hud(src)
path_hud.add_hud_to(src)
-/mob/living/simple_animal/bot/update_canmove()
+/mob/living/simple_animal/bot/update_mobility()
. = ..()
if(!on)
- . = 0
- canmove = .
+ . = NONE
+ mobility_flags = .
/mob/living/simple_animal/bot/Destroy()
if(path_hud)
diff --git a/code/modules/mob/living/simple_animal/bot/ed209bot.dm b/code/modules/mob/living/simple_animal/bot/ed209bot.dm
index 6d304c6782..2ab0f1721c 100644
--- a/code/modules/mob/living/simple_animal/bot/ed209bot.dm
+++ b/code/modules/mob/living/simple_animal/bot/ed209bot.dm
@@ -525,7 +525,7 @@ Auto Patrol[]"},
return
if(iscarbon(A))
var/mob/living/carbon/C = A
- if(C.canmove || arrest_type) // CIT CHANGE - makes sentient ed209s check for canmove rather than !isstun.
+ if(CHECK_MOBILITY(C, MOBILITY_STAND|MOBILITY_MOVE|MOBILITY_USE) || arrest_type) // CIT CHANGE - makes sentient ed209s check for canmove rather than !isstun.
stun_attack(A)
else if(C.canBeHandcuffed() && !C.handcuffed)
cuff(A)
@@ -543,7 +543,7 @@ Auto Patrol[]"},
spawn(2)
icon_state = "[lasercolor]ed209[on]"
var/threat = 5
- C.Knockdown(100)
+ C.DefaultCombatKnockdown(100)
C.stuttering = 5
if(ishuman(C))
var/mob/living/carbon/human/H = C
diff --git a/code/modules/mob/living/simple_animal/bot/firebot.dm b/code/modules/mob/living/simple_animal/bot/firebot.dm
index 6ab4dc36db..a5ac2e8bca 100644
--- a/code/modules/mob/living/simple_animal/bot/firebot.dm
+++ b/code/modules/mob/living/simple_animal/bot/firebot.dm
@@ -170,7 +170,7 @@
if(!..())
return
- if(IsStun())
+ if(IsStun() || IsParalyzed())
old_target_fire = target_fire
target_fire = null
mode = BOT_IDLE
@@ -287,7 +287,7 @@
if(!on)
icon_state = "firebot0"
return
- if(IsStun())
+ if(IsStun() || IsParalyzed())
icon_state = "firebots1"
else if(stationary_mode) //Bot has yellow light to indicate stationary mode.
icon_state = "firebots1"
diff --git a/code/modules/mob/living/simple_animal/bot/honkbot.dm b/code/modules/mob/living/simple_animal/bot/honkbot.dm
index e491cff74a..c3c16d5976 100644
--- a/code/modules/mob/living/simple_animal/bot/honkbot.dm
+++ b/code/modules/mob/living/simple_animal/bot/honkbot.dm
@@ -196,7 +196,7 @@ Maintenance panel panel is [open ? "opened" : "closed"]"},
C.stuttering = 20
C.adjustEarDamage(0, 5) //far less damage than the H.O.N.K.
C.Jitter(50)
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
var/mob/living/carbon/human/H = C
if(client) //prevent spam from players..
spam_flag = TRUE
@@ -215,7 +215,7 @@ Maintenance panel panel is [open ? "opened" : "closed"]"},
"[src] has honked you!")
else
C.stuttering = 20
- C.Knockdown(80)
+ C.DefaultCombatKnockdown(80)
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntime)
@@ -358,7 +358,7 @@ Maintenance panel panel is [open ? "opened" : "closed"]"},
"[C] trips over [src] and falls!", \
"[C] topples over [src]!", \
"[C] leaps out of [src]'s way!")]")
- C.Knockdown(10)
+ C.DefaultCombatKnockdown(10)
playsound(loc, 'sound/misc/sadtrombone.ogg', 50, 1, -1)
if(!client)
speak("Honk!")
diff --git a/code/modules/mob/living/simple_animal/bot/medbot.dm b/code/modules/mob/living/simple_animal/bot/medbot.dm
index bb29cd3526..d3fb65c585 100644
--- a/code/modules/mob/living/simple_animal/bot/medbot.dm
+++ b/code/modules/mob/living/simple_animal/bot/medbot.dm
@@ -106,7 +106,7 @@
skin = new_skin
update_icon()
-/mob/living/simple_animal/bot/medbot/update_canmove()
+/mob/living/simple_animal/bot/medbot/update_mobility()
. = ..()
update_icon()
diff --git a/code/modules/mob/living/simple_animal/bot/mulebot.dm b/code/modules/mob/living/simple_animal/bot/mulebot.dm
index b5aa8b6967..ab7ce96336 100644
--- a/code/modules/mob/living/simple_animal/bot/mulebot.dm
+++ b/code/modules/mob/living/simple_animal/bot/mulebot.dm
@@ -662,7 +662,7 @@
if(!paicard)
log_combat(src, L, "knocked down")
visible_message("[src] knocks over [L]!")
- L.Knockdown(160)
+ L.DefaultCombatKnockdown(160)
return ..()
// called from mob/living/carbon/human/Crossed()
@@ -747,8 +747,8 @@
else
return null
-/mob/living/simple_animal/bot/mulebot/resist()
- ..()
+/mob/living/simple_animal/bot/mulebot/do_resist()
+ . = ..()
if(load)
unload()
diff --git a/code/modules/mob/living/simple_animal/bot/secbot.dm b/code/modules/mob/living/simple_animal/bot/secbot.dm
index 461fa9cf2a..3ff97f2cc0 100644
--- a/code/modules/mob/living/simple_animal/bot/secbot.dm
+++ b/code/modules/mob/living/simple_animal/bot/secbot.dm
@@ -213,7 +213,7 @@ Auto Patrol: []"},
return
if(iscarbon(A))
var/mob/living/carbon/C = A
- if(C.canmove || arrest_type) // CIT CHANGE - makes sentient secbots check for canmove rather than !isstun.
+ if(CHECK_MOBILITY(C, MOBILITY_MOVE|MOBILITY_USE|MOBILITY_STAND) || arrest_type) // CIT CHANGE - makes sentient secbots check for canmove rather than !isstun.
stun_attack(A)
else if(C.canBeHandcuffed() && !C.handcuffed)
cuff(A)
@@ -254,11 +254,11 @@ Auto Patrol: []"},
var/threat = 5
if(ishuman(C))
C.stuttering = 5
- C.Knockdown(100)
+ C.DefaultCombatKnockdown(100)
var/mob/living/carbon/human/H = C
threat = H.assess_threat(judgement_criteria, weaponcheck=CALLBACK(src, .proc/check_for_weapons))
else
- C.Knockdown(100)
+ C.DefaultCombatKnockdown(100)
C.stuttering = 5
threat = C.assess_threat(judgement_criteria, weaponcheck=CALLBACK(src, .proc/check_for_weapons))
diff --git a/code/modules/mob/living/simple_animal/constructs.dm b/code/modules/mob/living/simple_animal/constructs.dm
index 4c6bfc4c3e..64b783b692 100644
--- a/code/modules/mob/living/simple_animal/constructs.dm
+++ b/code/modules/mob/living/simple_animal/constructs.dm
@@ -353,7 +353,7 @@
if(!LAZYLEN(parts))
if(undismembermerable_limbs) //they have limbs we can't remove, and no parts we can, attack!
return ..()
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
visible_message("[src] knocks [C] down!")
to_chat(src, "\"Bring [C.p_them()] to me.\"")
return FALSE
diff --git a/code/modules/mob/living/simple_animal/friendly/bumbles.dm b/code/modules/mob/living/simple_animal/friendly/bumbles.dm
index 17e1490c3f..013bb31b63 100644
--- a/code/modules/mob/living/simple_animal/friendly/bumbles.dm
+++ b/code/modules/mob/living/simple_animal/friendly/bumbles.dm
@@ -33,7 +33,7 @@
. = ..()
AddElement(/datum/element/wuv, "bzzs!")
-/mob/living/simple_animal/pet/bumbles/update_canmove()
+/mob/living/simple_animal/pet/bumbles/update_mobility()
. = ..()
if(client && stat != DEAD)
if (resting)
diff --git a/code/modules/mob/living/simple_animal/friendly/cat.dm b/code/modules/mob/living/simple_animal/friendly/cat.dm
index 0f95096497..1297fddb69 100644
--- a/code/modules/mob/living/simple_animal/friendly/cat.dm
+++ b/code/modules/mob/living/simple_animal/friendly/cat.dm
@@ -43,10 +43,10 @@
AddElement(/datum/element/wuv, "purrs!", EMOTE_AUDIBLE, /datum/mood_event/pet_animal, "hisses!", EMOTE_AUDIBLE)
AddElement(/datum/element/mob_holder, held_icon)
-/mob/living/simple_animal/pet/cat/update_canmove()
- ..()
+/mob/living/simple_animal/pet/cat/update_mobility()
+ . = ..()
if(client && stat != DEAD)
- if (resting)
+ if(!CHECK_MOBILITY(src, MOBILITY_STAND))
icon_state = "[icon_living]_rest"
collar_type = "[initial(collar_type)]_rest"
else
@@ -180,27 +180,24 @@
emote("me", EMOTE_VISIBLE, pick("stretches out for a belly rub.", "wags its tail.", "lies down."))
icon_state = "[icon_living]_rest"
collar_type = "[initial(collar_type)]_rest"
- resting = 1
- update_canmove()
+ set_resting(TRUE)
else if (prob(1))
emote("me", EMOTE_VISIBLE, pick("sits down.", "crouches on its hind legs.", "looks alert."))
icon_state = "[icon_living]_sit"
collar_type = "[initial(collar_type)]_sit"
- resting = 1
- update_canmove()
+ set_resting(TRUE)
else if (prob(1))
if (resting)
emote("me", EMOTE_VISIBLE, pick("gets up and meows.", "walks around.", "stops resting."))
icon_state = "[icon_living]"
collar_type = "[initial(collar_type)]"
- resting = 0
- update_canmove()
+ set_resting(FALSE)
else
emote("me", EMOTE_VISIBLE, pick("grooms its fur.", "twitches its whiskers.", "shakes out its coat."))
//MICE!
if((src.loc) && isturf(src.loc))
- if(!stat && !resting && !buckled)
+ if(!stat && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled)
for(var/mob/living/simple_animal/mouse/M in view(1,src))
if(!M.stat && Adjacent(M))
emote("me", EMOTE_VISIBLE, "splats \the [M]!")
@@ -217,7 +214,7 @@
make_babies()
- if(!stat && !resting && !buckled)
+ if(!stat && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled)
turns_since_scan++
if(turns_since_scan > 5)
walk_to(src,0)
@@ -309,7 +306,6 @@
if (pseudo_death == TRUE) //secret cat chem
icon_state = "custom_cat_dead"
Stun(1000)
- canmove = 0
friendly = "deads at"
return
else
diff --git a/code/modules/mob/living/simple_animal/friendly/crab.dm b/code/modules/mob/living/simple_animal/friendly/crab.dm
index d906757ed5..9e1ae48bdd 100644
--- a/code/modules/mob/living/simple_animal/friendly/crab.dm
+++ b/code/modules/mob/living/simple_animal/friendly/crab.dm
@@ -26,7 +26,7 @@
..()
//CRAB movement
if(!ckey && !stat)
- if(isturf(src.loc) && !resting && !buckled) //This is so it only moves if it's not inside a closet, gentics machine, etc.
+ if(isturf(loc) && !resting && !buckled) //This is so it only moves if it's not inside a closet, gentics machine, etc.
turns_since_move++
if(turns_since_move >= turns_per_move)
var/east_vs_west = pick(4,8)
diff --git a/code/modules/mob/living/simple_animal/friendly/dog.dm b/code/modules/mob/living/simple_animal/friendly/dog.dm
index 37ef271226..46cdc755db 100644
--- a/code/modules/mob/living/simple_animal/friendly/dog.dm
+++ b/code/modules/mob/living/simple_animal/friendly/dog.dm
@@ -425,7 +425,7 @@
..()
//Feeding, chasing food, FOOOOODDDD
- if(!stat && !resting && !buckled)
+ if(!stat && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled)
turns_since_scan++
if(turns_since_scan > 5)
turns_since_scan = 0
@@ -625,7 +625,7 @@
make_babies()
- if(!stat && !resting && !buckled)
+ if(!stat && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled)
if(prob(1))
emote("me", EMOTE_VISIBLE, pick("dances around.","chases her tail."))
spawn(0)
@@ -635,8 +635,7 @@
/mob/living/simple_animal/pet/dog/pug/Life()
..()
-
- if(!stat && !resting && !buckled)
+ if(!stat && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled)
if(prob(1))
emote("me", EMOTE_VISIBLE, pick("chases its tail."))
spawn(0)
diff --git a/code/modules/mob/living/simple_animal/friendly/drone/extra_drone_types.dm b/code/modules/mob/living/simple_animal/friendly/drone/extra_drone_types.dm
index 6e1bf54000..da39fb71cf 100644
--- a/code/modules/mob/living/simple_animal/friendly/drone/extra_drone_types.dm
+++ b/code/modules/mob/living/simple_animal/friendly/drone/extra_drone_types.dm
@@ -204,37 +204,6 @@
else
icon_state = "[visualAppearence]_dead"
-/mob/living/simple_animal/drone/cogscarab/Stun(amount, updating = 1, ignore_canstun = 0)
+/mob/living/simple_animal/drone/cogscarab/update_mobility()
. = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/SetStun(amount, updating = 1, ignore_canstun = 0)
- . = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/AdjustStun(amount, updating = 1, ignore_canstun = 0)
- . = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/Knockdown(amount, updating = TRUE, ignore_canknockdown = FALSE, override_hardstun, override_stamdmg)
- . = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/SetKnockdown(amount, updating = 1, ignore_canknockdown = 0)
- . = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/AdjustKnockdown(amount, updating = 1, ignore_canknockdown = 0)
- . = ..()
- if(.)
- update_icons()
-
-/mob/living/simple_animal/drone/cogscarab/update_canmove()
- . = ..()
- if(.)
- update_icons()
+ update_icons()
diff --git a/code/modules/mob/living/simple_animal/friendly/farm_animals.dm b/code/modules/mob/living/simple_animal/friendly/farm_animals.dm
index fad519838a..e67e649ac6 100644
--- a/code/modules/mob/living/simple_animal/friendly/farm_animals.dm
+++ b/code/modules/mob/living/simple_animal/friendly/farm_animals.dm
@@ -160,7 +160,7 @@
M.visible_message("[M] tips over [src].",
"You tip over [src].")
to_chat(src, "You are tipped over by [M]!")
- Knockdown(60,ignore_canknockdown = TRUE)
+ DefaultCombatKnockdown(60,ignore_canknockdown = TRUE)
icon_state = icon_dead
spawn(rand(20,50))
if(!stat && M)
diff --git a/code/modules/mob/living/simple_animal/hostile/faithless.dm b/code/modules/mob/living/simple_animal/hostile/faithless.dm
index 479b102b36..69956c5d0d 100644
--- a/code/modules/mob/living/simple_animal/hostile/faithless.dm
+++ b/code/modules/mob/living/simple_animal/hostile/faithless.dm
@@ -41,6 +41,6 @@
. = ..()
if(. && prob(12) && iscarbon(target))
var/mob/living/carbon/C = target
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
C.visible_message("\The [src] knocks down \the [C]!", \
"\The [src] knocks you down!")
diff --git a/code/modules/mob/living/simple_animal/hostile/gorilla/gorilla.dm b/code/modules/mob/living/simple_animal/hostile/gorilla/gorilla.dm
index 6d864576a1..9b5b428f44 100644
--- a/code/modules/mob/living/simple_animal/hostile/gorilla/gorilla.dm
+++ b/code/modules/mob/living/simple_animal/hostile/gorilla/gorilla.dm
@@ -71,7 +71,7 @@
var/atom/throw_target = get_edge_target_turf(L, dir)
L.throw_at(throw_target, rand(1,2), 7, src)
else
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
visible_message("[src] knocks [L] down!")
/mob/living/simple_animal/hostile/gorilla/CanAttack(atom/the_target)
diff --git a/code/modules/mob/living/simple_animal/hostile/jungle/leaper.dm b/code/modules/mob/living/simple_animal/hostile/jungle/leaper.dm
index ea01e4b659..e558982fbb 100644
--- a/code/modules/mob/living/simple_animal/hostile/jungle/leaper.dm
+++ b/code/modules/mob/living/simple_animal/hostile/jungle/leaper.dm
@@ -93,7 +93,7 @@
var/mob/living/L = AM
if(!istype(L, /mob/living/simple_animal/hostile/jungle/leaper))
playsound(src,'sound/effects/snap.ogg',50, 1, -1)
- L.Knockdown(50)
+ L.DefaultCombatKnockdown(50)
if(iscarbon(L))
var/mob/living/carbon/C = L
C.reagents.add_reagent(/datum/reagent/toxin/leaper_venom, 5)
diff --git a/code/modules/mob/living/simple_animal/hostile/mimic.dm b/code/modules/mob/living/simple_animal/hostile/mimic.dm
index 16a55421b8..6ec8e0cfd2 100644
--- a/code/modules/mob/living/simple_animal/hostile/mimic.dm
+++ b/code/modules/mob/living/simple_animal/hostile/mimic.dm
@@ -69,7 +69,7 @@
icon_state = initial(icon_state)
if(prob(15) && iscarbon(target))
var/mob/living/carbon/C = target
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
C.visible_message("\The [src] knocks down \the [C]!", \
"\The [src] knocks you down!")
@@ -179,7 +179,7 @@ GLOBAL_LIST_INIT(protected_objects, list(/obj/structure/table, /obj/structure/ca
. = ..()
if(knockdown_people && . && prob(15) && iscarbon(target))
var/mob/living/carbon/C = target
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
C.visible_message("\The [src] knocks down \the [C]!", \
"\The [src] knocks you down!")
diff --git a/code/modules/mob/living/simple_animal/hostile/sharks.dm b/code/modules/mob/living/simple_animal/hostile/sharks.dm
index c94e49b286..4e16a1f7bd 100644
--- a/code/modules/mob/living/simple_animal/hostile/sharks.dm
+++ b/code/modules/mob/living/simple_animal/hostile/sharks.dm
@@ -44,7 +44,7 @@
var/mob/living/carbon/L = .
if(istype(L))
if(prob(25))
- L.Knockdown(20)
+ L.DefaultCombatKnockdown(20)
L.visible_message("\the [src] knocks down \the [L]!")
diff --git a/code/modules/mob/living/simple_animal/hostile/tree.dm b/code/modules/mob/living/simple_animal/hostile/tree.dm
index e7b2da1844..a915ede835 100644
--- a/code/modules/mob/living/simple_animal/hostile/tree.dm
+++ b/code/modules/mob/living/simple_animal/hostile/tree.dm
@@ -56,7 +56,7 @@
if(iscarbon(target))
var/mob/living/carbon/C = target
if(prob(15))
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
C.visible_message("\The [src] knocks down \the [C]!", \
"\The [src] knocks you down!")
diff --git a/code/modules/mob/living/simple_animal/hostile/venus_human_trap.dm b/code/modules/mob/living/simple_animal/hostile/venus_human_trap.dm
index 29bc2cbff0..976f8df229 100644
--- a/code/modules/mob/living/simple_animal/hostile/venus_human_trap.dm
+++ b/code/modules/mob/living/simple_animal/hostile/venus_human_trap.dm
@@ -94,7 +94,7 @@
if(prob(grasp_pull_chance))
setDir(get_dir(src,L) )//staaaare
step(L,get_dir(L,src)) //reel them in
- L.Knockdown(60) //you can't get away now~
+ L.DefaultCombatKnockdown(60) //you can't get away now~
if(grasping.len < max_grasps)
grasping:
diff --git a/code/modules/mob/living/simple_animal/parrot.dm b/code/modules/mob/living/simple_animal/parrot.dm
index e79e24b885..9ad9a121ca 100644
--- a/code/modules/mob/living/simple_animal/parrot.dm
+++ b/code/modules/mob/living/simple_animal/parrot.dm
@@ -381,7 +381,7 @@
/mob/living/simple_animal/parrot/handle_automated_movement()
- if(!isturf(src.loc) || !canmove || buckled)
+ if(!isturf(loc) || !CHECK_MOBILITY(src, MOBILITY_MOVE) || buckled)
return //If it can't move, dont let it move. (The buckled check probably isn't necessary thanks to canmove)
if(client && stat == CONSCIOUS && parrot_state != icon_living)
diff --git a/code/modules/mob/living/simple_animal/simple_animal.dm b/code/modules/mob/living/simple_animal/simple_animal.dm
index 1b1cab13bb..3feed2129b 100644
--- a/code/modules/mob/living/simple_animal/simple_animal.dm
+++ b/code/modules/mob/living/simple_animal/simple_animal.dm
@@ -153,7 +153,7 @@
/mob/living/simple_animal/proc/handle_automated_movement()
set waitfor = FALSE
if(!stop_automated_movement && wander)
- if((isturf(src.loc) || allow_movement_on_non_turfs) && !resting && !buckled && canmove) //This is so it only moves if it's not inside a closet, gentics machine, etc.
+ if((isturf(src.loc) || allow_movement_on_non_turfs) && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE) && !buckled) //This is so it only moves if it's not inside a closet, gentics machine, etc.
turns_since_move++
if(turns_since_move >= turns_per_move)
if(!(stop_automated_movement_when_pulled && pulledby)) //Some animals don't move when pulled
@@ -418,20 +418,19 @@
else
..()
-/mob/living/simple_animal/update_canmove(value_otherwise = TRUE)
- if(IsUnconscious() || IsStun() || IsKnockdown() || stat || resting)
+/mob/living/simple_animal/update_mobility(value_otherwise = MOBILITY_FLAGS_DEFAULT)
+ if(IsUnconscious() || IsStun() || IsParalyzed() || stat || resting)
drop_all_held_items()
- canmove = FALSE
+ mobility_flags = NONE
else if(buckled)
- canmove = FALSE
+ mobility_flags = ~MOBILITY_MOVE
else
- canmove = value_otherwise
- if(!canmove) // !(mobility_flags & MOBILITY_MOVE)
+ mobility_flags = MOBILITY_FLAGS_DEFAULT
+ if(!CHECK_MOBILITY(src, MOBILITY_MOVE)) // !(mobility_flags & MOBILITY_MOVE)
walk(src, 0) //stop mid walk
-
update_transform()
update_action_buttons_icon()
- return canmove
+ return mobility_flags
/mob/living/simple_animal/update_transform()
var/matrix/ntransform = matrix(transform) //aka transform.Copy()
diff --git a/code/modules/mob/living/simple_animal/slime/death.dm b/code/modules/mob/living/simple_animal/slime/death.dm
index 52c9210263..5cac0c630c 100644
--- a/code/modules/mob/living/simple_animal/slime/death.dm
+++ b/code/modules/mob/living/simple_animal/slime/death.dm
@@ -24,7 +24,7 @@
stat = DEAD
cut_overlays()
- update_canmove()
+ update_mobility()
if(SSticker.mode)
SSticker.mode.check_win()
diff --git a/code/modules/mob/living/simple_animal/slime/life.dm b/code/modules/mob/living/simple_animal/slime/life.dm
index fd6cecf926..a923da6ed6 100644
--- a/code/modules/mob/living/simple_animal/slime/life.dm
+++ b/code/modules/mob/living/simple_animal/slime/life.dm
@@ -41,7 +41,7 @@
AIproc = 1
while(AIproc && stat != DEAD && (attacked || hungry || rabid || buckled))
- if(!canmove) // !(mobility_flags & MOBILITY_MOVE) //also covers buckling. Not sure why buckled is in the while condition if we're going to immediately break, honestly
+ if(!CHECK_MOBILITY(src, MOBILITY_MOVE)) //also covers buckling. Not sure why buckled is in the while condition if we're going to immediately break, honestly
break
if(!Target || client)
@@ -140,12 +140,12 @@
stat = UNCONSCIOUS
powerlevel = 0
rabid = 0
- update_canmove()
+ update_mobility()
regenerate_icons()
else if(stat == UNCONSCIOUS && !stasis)
to_chat(src, "You wake up from the stasis.")
stat = CONSCIOUS
- update_canmove()
+ update_mobility()
regenerate_icons()
updatehealth()
@@ -272,15 +272,8 @@
if(prob(25-powerlevel*5))
powerlevel++
-
-
-
/mob/living/simple_animal/slime/proc/handle_targets()
- if(Tempstun)
- if(!buckled) // not while they're eating!
- canmove = 0
- else
- canmove = 1
+ update_mobility()
if(attacked > 50)
attacked = 50
@@ -298,7 +291,7 @@
Discipline--
if(!client)
- if(!canmove)
+ if(!CHECK_MOBILITY(src, MOBILITY_MOVE))
return
if(buckled)
@@ -383,13 +376,13 @@
if (Leader)
if(holding_still)
holding_still = max(holding_still - 1, 0)
- else if(canmove && isturf(loc))
+ else if(CHECK_MOBILITY(src, MOBILITY_MOVE) && isturf(loc))
step_to(src, Leader)
else if(hungry)
if (holding_still)
holding_still = max(holding_still - hungry, 0)
- else if(canmove && isturf(loc) && prob(50))
+ else if(CHECK_MOBILITY(src, MOBILITY_MOVE) && isturf(loc) && prob(50))
step(src, pick(GLOB.cardinals))
else
@@ -397,7 +390,7 @@
holding_still = max(holding_still - 1, 0)
else if (docile && pulledby)
holding_still = 10
- else if(canmove && isturf(loc) && prob(33))
+ else if(CHECK_MOBILITY(src, MOBILITY_MOVE) && isturf(loc) && prob(33))
step(src, pick(GLOB.cardinals))
else if(!AIproc)
INVOKE_ASYNC(src, .proc/AIprocess)
diff --git a/code/modules/mob/living/simple_animal/slime/slime.dm b/code/modules/mob/living/simple_animal/slime/slime.dm
index 2ea2a412f8..990e61974e 100644
--- a/code/modules/mob/living/simple_animal/slime/slime.dm
+++ b/code/modules/mob/living/simple_animal/slime/slime.dm
@@ -454,13 +454,13 @@
SStun = world.time + rand(20,60)
spawn(0)
- canmove = 0
+ DISABLE_BITFIELD(mobility_flags, MOBILITY_MOVE)
if(user)
step_away(src,user,15)
sleep(3)
if(user)
step_away(src,user,15)
- update_canmove()
+ update_mobility()
/mob/living/simple_animal/slime/pet
docile = 1
diff --git a/code/modules/mob/living/simple_animal/slime/slime_mobility.dm b/code/modules/mob/living/simple_animal/slime/slime_mobility.dm
new file mode 100644
index 0000000000..5be5ff4e36
--- /dev/null
+++ b/code/modules/mob/living/simple_animal/slime/slime_mobility.dm
@@ -0,0 +1,5 @@
+/mob/living/simple_animal/slime/update_mobility()
+ . = ..()
+ if(Tempstun && !buckled)
+ DISABLE_BITFIELD(., MOBILITY_MOVE)
+ mobility_flags = .
diff --git a/code/modules/mob/living/status_procs.dm b/code/modules/mob/living/status_procs.dm
index aa5b2256d2..40b4212aac 100644
--- a/code/modules/mob/living/status_procs.dm
+++ b/code/modules/mob/living/status_procs.dm
@@ -1,11 +1,24 @@
-//Here are the procs used to modify status effects of a mob.
-//The effects include: stun, knockdown, unconscious, sleeping, resting, jitteriness, dizziness,
-// eye damage, eye_blind, eye_blurry, druggy, TRAIT_BLIND trait, and TRAIT_NEARSIGHT trait.
-
+// YEEHAW GAMERS STAMINA REWORK PROC GETS TO BE FIRST
+// amount = strength
+// updating = update mobility etc etc
+// ignore_castun = same logic as Paralyze() in general
+// override_duration = If this is set, does Paralyze() for this duration.
+// override_stam = If this is set, does this amount of stamina damage.
+/mob/living/proc/DefaultCombatKnockdown(amount, updating = TRUE, ignore_canknockdown = FALSE, override_hardstun, override_stamdmg)
+ if(!iscarbon(src))
+ return Paralyze(amount, updating, ignore_canknockdown)
+ if(istype(buckled, /obj/vehicle/ridden))
+ buckled.unbuckle_mob(src)
+ var/drop_items = amount > 80 //80 is cutoff for old item dropping behavior
+ var/stamdmg = isnull(override_stamdmg)? (amount * 0.25) : override_stamdmg
+ KnockToFloor(drop_items, TRUE, updating)
+ adjustStaminaLoss(stamdmg)
+ if(!isnull(override_hardstun))
+ Paralyze(override_hardstun)
////////////////////////////// STUN ////////////////////////////////////
-/mob/living/IsStun() //If we're stunned
+/mob/living/proc/IsStun() //If we're stunned
return has_status_effect(STATUS_EFFECT_STUN)
/mob/living/proc/AmountStun() //How many deciseconds remain in our stun
@@ -15,6 +28,8 @@
return 0
/mob/living/proc/Stun(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_STUN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
if(((status_flags & CANSTUN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
if(absorb_stun(amount, ignore_canstun))
return
@@ -26,6 +41,8 @@
return S
/mob/living/proc/SetStun(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_STUN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
if(((status_flags & CANSTUN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
var/datum/status_effect/incapacitating/stun/S = IsStun()
if(amount <= 0)
@@ -41,6 +58,8 @@
return S
/mob/living/proc/AdjustStun(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_STUN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
if(((status_flags & CANSTUN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
if(absorb_stun(amount, ignore_canstun))
return
@@ -53,7 +72,7 @@
///////////////////////////////// KNOCKDOWN /////////////////////////////////////
-/mob/living/IsKnockdown() //If we're knocked down
+/mob/living/proc/IsKnockdown() //If we're knocked down
return has_status_effect(STATUS_EFFECT_KNOCKDOWN)
/mob/living/proc/AmountKnockdown() //How many deciseconds remain in our knockdown
@@ -62,25 +81,29 @@
return K.duration - world.time
return 0
-/mob/living/proc/Knockdown(amount, updating = TRUE, ignore_canknockdown = FALSE, override_hardstun, override_stamdmg) //Can't go below remaining duration
- if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canknockdown)
- if(absorb_stun(isnull(override_hardstun)? amount : override_hardstun, ignore_canknockdown))
+/mob/living/proc/Knockdown(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_KNOCKDOWN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
return
var/datum/status_effect/incapacitating/knockdown/K = IsKnockdown()
if(K)
- K.duration = max(world.time + (isnull(override_hardstun)? amount : override_hardstun), K.duration)
- else if((amount || override_hardstun) > 0)
- K = apply_status_effect(STATUS_EFFECT_KNOCKDOWN, amount, updating, override_hardstun, override_stamdmg)
+ K.duration = max(world.time + amount, K.duration)
+ else if(amount > 0)
+ K = apply_status_effect(STATUS_EFFECT_KNOCKDOWN, amount, updating)
return K
-/mob/living/proc/SetKnockdown(amount, updating = TRUE, ignore_canknockdown = FALSE) //Sets remaining duration
- if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canknockdown)
+/mob/living/proc/SetKnockdown(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_KNOCKDOWN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
var/datum/status_effect/incapacitating/knockdown/K = IsKnockdown()
if(amount <= 0)
if(K)
qdel(K)
else
- if(absorb_stun(amount, ignore_canknockdown))
+ if(absorb_stun(amount, ignore_canstun))
return
if(K)
K.duration = world.time + amount
@@ -88,9 +111,11 @@
K = apply_status_effect(STATUS_EFFECT_KNOCKDOWN, amount, updating)
return K
-/mob/living/proc/AdjustKnockdown(amount, updating = TRUE, ignore_canknockdown = FALSE) //Adds to remaining duration
- if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canknockdown)
- if(absorb_stun(amount, ignore_canknockdown))
+/mob/living/proc/AdjustKnockdown(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_KNOCKDOWN, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
return
var/datum/status_effect/incapacitating/knockdown/K = IsKnockdown()
if(K)
@@ -99,6 +124,304 @@
K = apply_status_effect(STATUS_EFFECT_KNOCKDOWN, amount, updating)
return K
+///////////////////////////////// IMMOBILIZED ////////////////////////////////////
+/mob/living/proc/IsImmobilized() //If we're immobilized
+ return has_status_effect(STATUS_EFFECT_IMMOBILIZED)
+
+/mob/living/proc/AmountImmobilized() //How many deciseconds remain in our Immobilized status effect
+ var/datum/status_effect/incapacitating/immobilized/I = IsImmobilized()
+ if(I)
+ return I.duration - world.time
+ return 0
+
+/mob/living/proc/Immobilize(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_IMMOBILIZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/immobilized/I = IsImmobilized()
+ if(I)
+ I.duration = max(world.time + amount, I.duration)
+ else if(amount > 0)
+ I = apply_status_effect(STATUS_EFFECT_IMMOBILIZED, amount, updating)
+ return I
+
+/mob/living/proc/SetImmobilized(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_IMMOBILIZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/immobilized/I = IsImmobilized()
+ if(amount <= 0)
+ if(I)
+ qdel(I)
+ else
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ if(I)
+ I.duration = world.time + amount
+ else
+ I = apply_status_effect(STATUS_EFFECT_IMMOBILIZED, amount, updating)
+ return I
+
+/mob/living/proc/AdjustImmobilized(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_IMMOBILIZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/immobilized/I = IsImmobilized()
+ if(I)
+ I.duration += amount
+ else if(amount > 0)
+ I = apply_status_effect(STATUS_EFFECT_IMMOBILIZED, amount, updating)
+ return I
+
+///////////////////////////////// PARALYZED //////////////////////////////////
+/mob/living/proc/IsParalyzed() //If we're immobilized
+ return has_status_effect(STATUS_EFFECT_PARALYZED)
+
+/mob/living/proc/AmountParalyzed() //How many deciseconds remain in our Paralyzed status effect
+ var/datum/status_effect/incapacitating/paralyzed/P = IsParalyzed(FALSE)
+ if(P)
+ return P.duration - world.time
+ return 0
+
+/mob/living/proc/Paralyze(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_PARALYZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/paralyzed/P = IsParalyzed(FALSE)
+ if(P)
+ P.duration = max(world.time + amount, P.duration)
+ else if(amount > 0)
+ P = apply_status_effect(STATUS_EFFECT_PARALYZED, amount, updating)
+ return P
+
+/mob/living/proc/SetParalyzed(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_PARALYZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/paralyzed/P = IsParalyzed(FALSE)
+ if(amount <= 0)
+ if(P)
+ qdel(P)
+ else
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ if(P)
+ P.duration = world.time + amount
+ else
+ P = apply_status_effect(STATUS_EFFECT_PARALYZED, amount, updating)
+ return P
+
+/mob/living/proc/AdjustParalyzed(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_PARALYZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/paralyzed/P = IsParalyzed(FALSE)
+ if(P)
+ P.duration += amount
+ else if(amount > 0)
+ P = apply_status_effect(STATUS_EFFECT_PARALYZED, amount, updating)
+ return P
+
+///////////////////////////////// DAZED ////////////////////////////////////
+/mob/living/proc/IsDazed() //If we're Dazed
+ return has_status_effect(STATUS_EFFECT_DAZED)
+
+/mob/living/proc/AmountDazed() //How many deciseconds remain in our Dazed status effect
+ var/datum/status_effect/incapacitating/dazed/I = IsDazed()
+ if(I)
+ return I.duration - world.time
+ return 0
+
+/mob/living/proc/Daze(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_DAZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/dazed/I = IsDazed()
+ if(I)
+ I.duration = max(world.time + amount, I.duration)
+ else if(amount > 0)
+ I = apply_status_effect(STATUS_EFFECT_DAZED, amount, updating)
+ return I
+
+/mob/living/proc/SetDazed(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_DAZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/dazed/I = IsDazed()
+ if(amount <= 0)
+ if(I)
+ qdel(I)
+ else
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ if(I)
+ I.duration = world.time + amount
+ else
+ I = apply_status_effect(STATUS_EFFECT_DAZED, amount, updating)
+ return I
+
+/mob/living/proc/AdjustDazed(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_DAZE, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANKNOCKDOWN) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ if(absorb_stun(amount, ignore_canstun))
+ return
+ var/datum/status_effect/incapacitating/dazed/I = IsDazed()
+ if(I)
+ I.duration += amount
+ else if(amount > 0)
+ I = apply_status_effect(STATUS_EFFECT_DAZED, amount, updating)
+ return I
+
+//Blanket
+/mob/living/proc/AllImmobility(amount, updating, ignore_canstun = FALSE)
+ Paralyze(amount, FALSE, ignore_canstun)
+ Knockdown(amount, FALSE, ignore_canstun)
+ Stun(amount, FALSE, ignore_canstun)
+ Immobilize(amount, FALSE, ignore_canstun)
+ Daze(amount, FALSE, ignore_canstun)
+ if(updating)
+ update_mobility()
+
+/mob/living/proc/SetAllImmobility(amount, updating, ignore_canstun = FALSE)
+ SetParalyzed(amount, FALSE, ignore_canstun)
+ SetKnockdown(amount, FALSE, ignore_canstun)
+ SetStun(amount, FALSE, ignore_canstun)
+ SetImmobilized(amount, FALSE, ignore_canstun)
+ SetDazed(amount, FALSE, ignore_canstun)
+ if(updating)
+ update_mobility()
+
+/mob/living/proc/AdjustAllImmobility(amount, updating, ignore_canstun = FALSE)
+ AdjustParalyzed(amount, FALSE, ignore_canstun)
+ AdjustKnockdown(amount, FALSE, ignore_canstun)
+ AdjustStun(amount, FALSE, ignore_canstun)
+ AdjustImmobilized(amount, FALSE, ignore_canstun)
+ AdjustDazed(amount, FALSE, ignore_canstun)
+ if(updating)
+ update_mobility()
+
+/// Makes sure all 5 of the non-knockout immobilizing status effects are lower or equal to amount.
+/mob/living/proc/HealAllImmobilityUpTo(amount, updating, ignore_canstun = FALSE)
+ if(AmountStun() > amount)
+ SetStun(amount, FALSE, ignore_canstun)
+ if(AmountKnockdown() > amount)
+ SetKnockdown(amount, FALSE, ignore_canstun)
+ if(AmountParalyzed() > amount)
+ SetParalyzed(amount, FALSE, ignore_canstun)
+ if(AmountImmobilized() > amount)
+ SetImmobilized(amount, FALSE, ignore_canstun)
+ if(AmountDazed() > amount)
+ SetImmobilized(amount, FALSE, ignore_canstun)
+ if(updating)
+ update_mobility()
+
+/mob/living/proc/HighestImmobilityAmount()
+ return max(max(max(max(AmountStun(), AmountKnockdown()), AmountParalyzed()), AmountImmobilized()), AmountDazed())
+
+//////////////////UNCONSCIOUS
+/mob/living/proc/IsUnconscious() //If we're unconscious
+ return has_status_effect(STATUS_EFFECT_UNCONSCIOUS)
+
+/mob/living/proc/AmountUnconscious() //How many deciseconds remain in our unconsciousness
+ var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
+ if(U)
+ return U.duration - world.time
+ return 0
+
+/mob/living/proc/Unconscious(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_UNCONSCIOUS, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
+ if(U)
+ U.duration = max(world.time + amount, U.duration)
+ else if(amount > 0)
+ U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
+ return U
+
+/mob/living/proc/SetUnconscious(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_UNCONSCIOUS, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
+ if(amount <= 0)
+ if(U)
+ qdel(U)
+ else if(U)
+ U.duration = world.time + amount
+ else
+ U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
+ return U
+
+/mob/living/proc/AdjustUnconscious(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_UNCONSCIOUS, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
+ if(U)
+ U.duration += amount
+ else if(amount > 0)
+ U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
+ return U
+
+/////////////////////////////////// SLEEPING ////////////////////////////////////
+
+/mob/living/proc/IsSleeping() //If we're asleep
+ return has_status_effect(STATUS_EFFECT_SLEEPING)
+
+/mob/living/proc/AmountSleeping() //How many deciseconds remain in our sleep
+ var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
+ if(S)
+ return S.duration - world.time
+ return 0
+
+/mob/living/proc/Sleeping(amount, updating = TRUE, ignore_canstun = FALSE) //Can't go below remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_SLEEP, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
+ if(S)
+ S.duration = max(world.time + amount, S.duration)
+ else if(amount > 0)
+ S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
+ return S
+
+/mob/living/proc/SetSleeping(amount, updating = TRUE, ignore_canstun = FALSE) //Sets remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_SLEEP, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
+ if(amount <= 0)
+ if(S)
+ qdel(S)
+ else if(S)
+ S.duration = world.time + amount
+ else
+ S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
+ return S
+
+/mob/living/proc/AdjustSleeping(amount, updating = TRUE, ignore_canstun = FALSE) //Adds to remaining duration
+ if(SEND_SIGNAL(src, COMSIG_LIVING_STATUS_SLEEP, amount, updating, ignore_canstun) & COMPONENT_NO_STUN)
+ return
+ if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_canstun)
+ var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
+ if(S)
+ S.duration += amount
+ else if(amount > 0)
+ S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
+ return S
+
///////////////////////////////// FROZEN /////////////////////////////////////
/mob/living/proc/IsFrozen()
@@ -119,8 +442,10 @@
"visible_message" = message, "self_message" = self_message, "examine_message" = examine_message)
/mob/living/proc/absorb_stun(amount, ignoring_flag_presence)
- if(!amount || amount <= 0 || stat || ignoring_flag_presence || !islist(stun_absorption))
+ if(amount < 0 || stat || ignoring_flag_presence || !islist(stun_absorption))
return FALSE
+ if(!amount)
+ amount = 0
var/priority_absorb_key
var/highest_priority
for(var/i in stun_absorption)
@@ -128,20 +453,20 @@
priority_absorb_key = stun_absorption[i]
highest_priority = priority_absorb_key["priority"]
if(priority_absorb_key)
- if(priority_absorb_key["visible_message"] || priority_absorb_key["self_message"])
- if(priority_absorb_key["visible_message"] && priority_absorb_key["self_message"])
- visible_message("[src][priority_absorb_key["visible_message"]]", "[priority_absorb_key["self_message"]]")
- else if(priority_absorb_key["visible_message"])
- visible_message("[src][priority_absorb_key["visible_message"]]")
- else if(priority_absorb_key["self_message"])
- to_chat(src, "[priority_absorb_key["self_message"]]")
- priority_absorb_key["stuns_absorbed"] += amount
+ if(amount) //don't spam up the chat for continuous stuns
+ if(priority_absorb_key["visible_message"] || priority_absorb_key["self_message"])
+ if(priority_absorb_key["visible_message"] && priority_absorb_key["self_message"])
+ visible_message("[src][priority_absorb_key["visible_message"]]", "[priority_absorb_key["self_message"]]")
+ else if(priority_absorb_key["visible_message"])
+ visible_message("[src][priority_absorb_key["visible_message"]]")
+ else if(priority_absorb_key["self_message"])
+ to_chat(src, "[priority_absorb_key["self_message"]]")
+ priority_absorb_key["stuns_absorbed"] += amount
return TRUE
/////////////////////////////////// DISABILITIES ////////////////////////////////////
-
/mob/living/proc/add_quirk(quirktype, spawn_effects) //separate proc due to the way these ones are handled
- if(has_quirk(quirktype))
+ if(HAS_TRAIT(src, quirktype))
return
var/datum/quirk/T = quirktype
var/qname = initial(T.name)
@@ -162,20 +487,23 @@
if(Q.type == quirktype)
return TRUE
return FALSE
+
/////////////////////////////////// TRAIT PROCS ////////////////////////////////////
-/mob/living/proc/cure_blind(list/sources)
- REMOVE_TRAIT(src, TRAIT_BLIND, sources)
+/mob/living/proc/cure_blind(source)
+ REMOVE_TRAIT(src, TRAIT_BLIND, source)
if(!HAS_TRAIT(src, TRAIT_BLIND))
- adjust_blindness(-1)
+ update_blindness()
/mob/living/proc/become_blind(source)
- if(!HAS_TRAIT(src, TRAIT_BLIND))
- blind_eyes(1)
- ADD_TRAIT(src, TRAIT_BLIND, source)
+ if(!HAS_TRAIT(src, TRAIT_BLIND)) // not blind already, add trait then overlay
+ ADD_TRAIT(src, TRAIT_BLIND, source)
+ update_blindness()
+ else
+ ADD_TRAIT(src, TRAIT_BLIND, source)
-/mob/living/proc/cure_nearsighted(list/sources)
- REMOVE_TRAIT(src, TRAIT_NEARSIGHT, sources)
+/mob/living/proc/cure_nearsighted(source)
+ REMOVE_TRAIT(src, TRAIT_NEARSIGHT, source)
if(!HAS_TRAIT(src, TRAIT_NEARSIGHT))
clear_fullscreen("nearsighted")
@@ -184,8 +512,8 @@
overlay_fullscreen("nearsighted", /obj/screen/fullscreen/impaired, 1)
ADD_TRAIT(src, TRAIT_NEARSIGHT, source)
-/mob/living/proc/cure_husk(list/sources)
- REMOVE_TRAIT(src, TRAIT_HUSK, sources)
+/mob/living/proc/cure_husk(source)
+ REMOVE_TRAIT(src, TRAIT_HUSK, source)
if(!HAS_TRAIT(src, TRAIT_HUSK))
REMOVE_TRAIT(src, TRAIT_DISFIGURED, "husk")
update_body()
@@ -193,14 +521,15 @@
/mob/living/proc/become_husk(source)
if(!HAS_TRAIT(src, TRAIT_HUSK))
+ ADD_TRAIT(src, TRAIT_HUSK, source)
ADD_TRAIT(src, TRAIT_DISFIGURED, "husk")
update_body()
- . = TRUE
- ADD_TRAIT(src, TRAIT_HUSK, source)
+ else
+ ADD_TRAIT(src, TRAIT_HUSK, source)
-/mob/living/proc/cure_fakedeath(list/sources)
- REMOVE_TRAIT(src, TRAIT_FAKEDEATH, sources)
- REMOVE_TRAIT(src, TRAIT_DEATHCOMA, sources)
+/mob/living/proc/cure_fakedeath(source)
+ REMOVE_TRAIT(src, TRAIT_FAKEDEATH, source)
+ REMOVE_TRAIT(src, TRAIT_DEATHCOMA, source)
if(stat != DEAD)
tod = null
update_stat()
@@ -215,10 +544,10 @@
tod = STATION_TIME_TIMESTAMP("hh:mm:ss", world.time)
update_stat()
-/mob/living/proc/unignore_slowdown(list/sources)
- REMOVE_TRAIT(src, TRAIT_IGNORESLOWDOWN, sources)
+/mob/living/proc/unignore_slowdown(source)
+ REMOVE_TRAIT(src, TRAIT_IGNORESLOWDOWN, source)
update_movespeed(FALSE)
/mob/living/proc/ignore_slowdown(source)
ADD_TRAIT(src, TRAIT_IGNORESLOWDOWN, source)
- update_movespeed(FALSE)
\ No newline at end of file
+ update_movespeed(FALSE)
diff --git a/code/modules/mob/living/ventcrawling.dm b/code/modules/mob/living/ventcrawling.dm
index 7f8513bfd9..36a596f42e 100644
--- a/code/modules/mob/living/ventcrawling.dm
+++ b/code/modules/mob/living/ventcrawling.dm
@@ -50,7 +50,7 @@ GLOBAL_LIST_INIT(ventcrawl_machinery, typecacheof(list(
if(vent_found_parent && (vent_found_parent.members.len || vent_found_parent.other_atmosmch))
visible_message("[src] begins climbing into the ventilation system..." ,"You begin climbing into the ventilation system...")
- if(!do_after(src, 25, target = vent_found))
+ if(!do_after(src, 25, target = vent_found, required_mobility_flags = MOBILITY_MOVE))
return
if(!client)
diff --git a/code/modules/mob/mob.dm b/code/modules/mob/mob.dm
index 1ca6299efb..a523c22d53 100644
--- a/code/modules/mob/mob.dm
+++ b/code/modules/mob/mob.dm
@@ -659,8 +659,6 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
// facing verbs
/mob/proc/canface()
- if(!canmove)
- return FALSE
if(world.time < client.last_turn)
return FALSE
if(stat == DEAD || stat == UNCONSCIOUS)
@@ -762,7 +760,7 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
//You can buckle on mobs if you're next to them since most are dense
/mob/buckle_mob(mob/living/M, force = FALSE, check_loc = TRUE)
if(M.buckled)
- return 0
+ return FALSE
var/turf/T = get_turf(src)
if(M.loc != T)
var/old_density = density
@@ -770,7 +768,7 @@ GLOBAL_VAR_INIT(exploit_warn_spam_prevention, 0)
var/can_step = step_towards(M, T)
density = old_density
if(!can_step)
- return 0
+ return FALSE
return ..()
//Default buckling shift visual for mobs
diff --git a/code/modules/mob/mob_defines.dm b/code/modules/mob/mob_defines.dm
index c45f6eec13..638a3aa0e2 100644
--- a/code/modules/mob/mob_defines.dm
+++ b/code/modules/mob/mob_defines.dm
@@ -38,7 +38,6 @@
var/resting = 0 //Carbon
var/lying = 0
var/lying_prev = 0
- var/canmove = 1
//MOVEMENT SPEED
var/list/movespeed_modification //Lazy list, see mob_movespeed.dm
diff --git a/code/modules/mob/mob_movement.dm b/code/modules/mob/mob_movement.dm
index b11d1632c8..071ef1f49e 100644
--- a/code/modules/mob/mob_movement.dm
+++ b/code/modules/mob/mob_movement.dm
@@ -62,7 +62,7 @@
if(mob.buckled) //if we're buckled to something, tell it we moved.
return mob.buckled.relaymove(mob, direction)
- if(!mob.canmove)
+ if(!CHECK_MOBILITY(L, MOBILITY_MOVE))
return FALSE
if(isobj(mob.loc) || ismob(mob.loc)) //Inside an object, tell it we moved
@@ -107,9 +107,7 @@
if(P && !ismob(P) && P.density)
mob.setDir(turn(mob.dir, 180))
-///Process_Grab()
-///Called by client/Move()
-///Checks to see if you are being grabbed and if so attemps to break it
+/// Process_Grab(): checks for grab, attempts to break if so. Return TRUE to prevent movement.
/client/proc/Process_Grab()
if(mob.pulledby)
if(mob.incapacitated(ignore_restraints = 1))
@@ -120,7 +118,7 @@
to_chat(src, "You're restrained! You can't move!")
return TRUE
else
- return mob.resist_grab(1)
+ return !mob.attempt_resist_grab(TRUE)
///Process_Incorpmove
///Called by client/Move()
diff --git a/code/modules/mob/status_procs.dm b/code/modules/mob/status_procs.dm
index 17311daec2..12379bce91 100644
--- a/code/modules/mob/status_procs.dm
+++ b/code/modules/mob/status_procs.dm
@@ -3,222 +3,81 @@
//The effects include: stun, knockdown, unconscious, sleeping, resting, jitteriness, dizziness, ear damage,
// eye damage, eye_blind, eye_blurry, druggy, TRAIT_BLIND trait, and TRAIT_NEARSIGHT trait.
-/////////////////////////////////// STUN ////////////////////////////////////
-
-/mob/proc/IsStun() //non-living mobs shouldn't be stunned
- return FALSE
-
-/////////////////////////////////// KNOCKDOWN ////////////////////////////////////
-
-/mob/proc/IsKnockdown() //non-living mobs shouldn't be knocked down
- return FALSE
-
-/////////////////////////////////// UNCONSCIOUS ////////////////////////////////////
-
-/mob/proc/IsUnconscious() //non-living mobs shouldn't be unconscious
- return FALSE
-
-/mob/living/IsUnconscious() //If we're unconscious
- return has_status_effect(STATUS_EFFECT_UNCONSCIOUS)
-
-/mob/living/proc/AmountUnconscious() //How many deciseconds remain in our unconsciousness
- var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
- if(U)
- return U.duration - world.time
- return 0
-
-/mob/living/proc/Unconscious(amount, updating = TRUE, ignore_canunconscious = FALSE) //Can't go below remaining duration
- if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canunconscious)
- var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
- if(U)
- U.duration = max(world.time + amount, U.duration)
- else if(amount > 0)
- U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
- return U
-
-/mob/living/proc/SetUnconscious(amount, updating = TRUE, ignore_canunconscious = FALSE) //Sets remaining duration
- if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canunconscious)
- var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
- if(amount <= 0)
- if(U)
- qdel(U)
- else if(U)
- U.duration = world.time + amount
- else
- U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
- return U
-
-/mob/living/proc/AdjustUnconscious(amount, updating = TRUE, ignore_canunconscious = FALSE) //Adds to remaining duration
- if(((status_flags & CANUNCONSCIOUS) && !HAS_TRAIT(src, TRAIT_STUNIMMUNE)) || ignore_canunconscious)
- var/datum/status_effect/incapacitating/unconscious/U = IsUnconscious()
- if(U)
- U.duration += amount
- else if(amount > 0)
- U = apply_status_effect(STATUS_EFFECT_UNCONSCIOUS, amount, updating)
- return U
-
-/////////////////////////////////// SLEEPING ////////////////////////////////////
-
-/mob/proc/IsSleeping() //non-living mobs shouldn't be sleeping either
- return FALSE
-
-/mob/living/IsSleeping() //If we're asleep
- return has_status_effect(STATUS_EFFECT_SLEEPING)
-
-/mob/living/proc/AmountSleeping() //How many deciseconds remain in our sleep
- var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
- if(S)
- return S.duration - world.time
- return 0
-
-/mob/living/proc/Sleeping(amount, updating = TRUE, ignore_sleepimmune = FALSE) //Can't go below remaining duration
- if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_sleepimmune)
- var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
- if(S)
- S.duration = max(world.time + amount, S.duration)
- else if(amount > 0)
- S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
- return S
-
-/mob/living/proc/SetSleeping(amount, updating = TRUE, ignore_sleepimmune = FALSE) //Sets remaining duration
- if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_sleepimmune)
- var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
- if(amount <= 0)
- if(S)
- qdel(S)
- else if(S)
- S.duration = world.time + amount
- else
- S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
- return S
-
-/mob/living/proc/AdjustSleeping(amount, updating = TRUE, ignore_sleepimmune = FALSE) //Adds to remaining duration
- if((!HAS_TRAIT(src, TRAIT_SLEEPIMMUNE)) || ignore_sleepimmune)
- var/datum/status_effect/incapacitating/sleeping/S = IsSleeping()
- if(S)
- S.duration += amount
- else if(amount > 0)
- S = apply_status_effect(STATUS_EFFECT_SLEEPING, amount, updating)
- return S
-
-/////////////////////////////////// RESTING ////////////////////////////////////
-
-/mob/proc/Resting(amount)
- resting = max(max(resting,amount),0)
-
-/mob/living/Resting(amount)
- ..()
- update_canmove()
-
-/mob/proc/SetResting(amount)
- resting = max(amount,0)
-
-/mob/living/SetResting(amount)
- ..()
- update_canmove()
-
-/mob/proc/AdjustResting(amount)
- resting = max(resting + amount,0)
-
-/mob/living/AdjustResting(amount)
- ..()
- update_canmove()
-
-/////////////////////////////////// JITTERINESS ////////////////////////////////////
-
+///Set the jitter of a mob
/mob/proc/Jitter(amount)
jitteriness = max(jitteriness,amount,0)
-/////////////////////////////////// DIZZINESS ////////////////////////////////////
-
+/**
+ * Set the dizzyness of a mob to a passed in amount
+ *
+ * Except if dizziness is already higher in which case it does nothing
+ */
/mob/proc/Dizzy(amount)
dizziness = max(dizziness,amount,0)
-/////////////////////////////////// EYE_BLIND ////////////////////////////////////
+///FOrce set the dizzyness of a mob
+/mob/proc/set_dizziness(amount)
+ dizziness = max(amount, 0)
+///Blind a mobs eyes by amount
/mob/proc/blind_eyes(amount)
- if(amount>0)
- var/old_eye_blind = eye_blind
- eye_blind = max(eye_blind, amount)
- if(!old_eye_blind)
- if(stat == CONSCIOUS || stat == SOFT_CRIT)
- throw_alert("blind", /obj/screen/alert/blind)
- overlay_fullscreen("blind", /obj/screen/fullscreen/blind)
+ adjust_blindness(amount)
+/**
+ * Adjust a mobs blindness by an amount
+ *
+ * Will apply the blind alerts if needed
+ */
/mob/proc/adjust_blindness(amount)
- if(amount>0)
- var/old_eye_blind = eye_blind
- eye_blind += amount
- if(!old_eye_blind)
- if(stat == CONSCIOUS || stat == SOFT_CRIT)
- throw_alert("blind", /obj/screen/alert/blind)
- overlay_fullscreen("blind", /obj/screen/fullscreen/blind)
- else if(eye_blind)
- var/blind_minimum = 0
- if((stat != CONSCIOUS && stat != SOFT_CRIT))
- blind_minimum = 1
- if(isliving(src))
- var/mob/living/L = src
- if(HAS_TRAIT(L, TRAIT_BLIND))
- blind_minimum = 1
- eye_blind = max(eye_blind+amount, blind_minimum)
- if(!eye_blind)
- clear_alert("blind")
- clear_fullscreen("blind")
-
+ var/old_eye_blind = eye_blind
+ eye_blind = max(0, eye_blind + amount)
+ if(!old_eye_blind || !eye_blind && !HAS_TRAIT(src, TRAIT_BLIND))
+ update_blindness()
+/**
+ * Force set the blindness of a mob to some level
+ */
/mob/proc/set_blindness(amount)
- if(amount>0)
- var/old_eye_blind = eye_blind
- eye_blind = amount
- if(client && !old_eye_blind)
- if(stat == CONSCIOUS || stat == SOFT_CRIT)
- throw_alert("blind", /obj/screen/alert/blind)
- overlay_fullscreen("blind", /obj/screen/fullscreen/blind)
- else if(eye_blind)
- var/blind_minimum = 0
- if(stat != CONSCIOUS && stat != SOFT_CRIT)
- blind_minimum = 1
- if(isliving(src))
- var/mob/living/L = src
- if(HAS_TRAIT(L, TRAIT_BLIND))
- blind_minimum = 1
- eye_blind = blind_minimum
- if(!eye_blind)
- clear_alert("blind")
- clear_fullscreen("blind")
-
-/////////////////////////////////// EYE_BLURRY ////////////////////////////////////
+ var/old_eye_blind = eye_blind
+ eye_blind = max(amount, 0)
+ if(!old_eye_blind || !eye_blind && !HAS_TRAIT(src, TRAIT_BLIND))
+ update_blindness()
+/// proc that adds and removes blindness overlays when necessary
+/mob/proc/update_blindness()
+ if(stat == UNCONSCIOUS || HAS_TRAIT(src, TRAIT_BLIND) || eye_blind) // UNCONSCIOUS or has blind trait, or has temporary blindness
+ if(stat == CONSCIOUS || stat == SOFT_CRIT)
+ throw_alert("blind", /obj/screen/alert/blind)
+ overlay_fullscreen("blind", /obj/screen/fullscreen/blind)
+ // You are blind why should you be able to make out details like color, only shapes near you
+ // add_client_colour(/datum/client_colour/monochrome/blind)
+ else // CONSCIOUS no blind trait, no blindness
+ clear_alert("blind")
+ clear_fullscreen("blind")
+ // remove_client_colour(/datum/client_colour/monochrome/blind)
+/**
+ * Make the mobs vision blurry
+ */
/mob/proc/blur_eyes(amount)
if(amount>0)
- var/old_eye_blurry = eye_blurry
eye_blurry = max(amount, eye_blurry)
- if(!old_eye_blurry)
- add_eyeblur() //Citadel edit blurry eye memes entailed. syncs beware
- else if(eye_blurry > 0)
- update_eyeblur()
+ update_eyeblur()
+/**
+ * Adjust the current blurriness of the mobs vision by amount
+ */
/mob/proc/adjust_blurriness(amount)
- var/old_eye_blurry = eye_blurry
eye_blurry = max(eye_blurry+amount, 0)
- if(amount>0)
- if(!old_eye_blurry)
- add_eyeblur()
- else if(eye_blurry > 0)
- update_eyeblur()
- else if(old_eye_blurry && !eye_blurry)
- remove_eyeblur()
+ update_eyeblur()
+///Set the mobs blurriness of vision to an amount
/mob/proc/set_blurriness(amount)
- var/old_eye_blurry = eye_blurry
eye_blurry = max(amount, 0)
- if(amount>0)
- if(!old_eye_blurry)
- add_eyeblur()
- else if(eye_blurry > 0)
- update_eyeblur()
- else if(old_eye_blurry)
- remove_eyeblur()
+ update_eyeblur()
+
+/mob/proc/update_eyeblur()
+ remove_eyeblur()
+ if(eye_blurry)
+ add_eyeblur()
/mob/proc/add_eyeblur()
if(!client)
@@ -228,10 +87,6 @@
GW.add_filter("blurry_eyes", 2, EYE_BLUR(CLAMP(eye_blurry*0.1,0.6,3)))
F.add_filter("blurry_eyes", 2, EYE_BLUR(CLAMP(eye_blurry*0.1,0.6,3)))
-/mob/proc/update_eyeblur()
- remove_eyeblur()
- add_eyeblur()
-
/mob/proc/remove_eyeblur()
if(!client)
return
@@ -240,24 +95,23 @@
GW.remove_filter("blurry_eyes")
F.remove_filter("blurry_eyes")
-/////////////////////////////////// DRUGGY ////////////////////////////////////
-
+///Adjust the drugginess of a mob
/mob/proc/adjust_drugginess(amount)
return
+///Set the drugginess of a mob
/mob/proc/set_drugginess(amount)
return
-/////////////////////////////////// GROSSED OUT ////////////////////////////////////
-
+///Adjust the disgust level of a mob
/mob/proc/adjust_disgust(amount)
return
+///Set the disgust level of a mob
/mob/proc/set_disgust(amount)
return
-/////////////////////////////////// TEMPERATURE ////////////////////////////////////
-
+///Adjust the body temperature of a mob, with min/max settings
/mob/proc/adjust_bodytemperature(amount,min_temp=0,max_temp=INFINITY)
if(bodytemperature >= min_temp && bodytemperature <= max_temp)
bodytemperature = CLAMP(bodytemperature + amount,min_temp,max_temp)
diff --git a/code/modules/mob/transform_procs.dm b/code/modules/mob/transform_procs.dm
index dfbc0f483e..4b360df8c7 100644
--- a/code/modules/mob/transform_procs.dm
+++ b/code/modules/mob/transform_procs.dm
@@ -29,9 +29,8 @@
dropItemToGround(W)
//Make mob invisible and spawn animation
- notransform = 1
- canmove = 0
- Stun(22, ignore_canstun = TRUE)
+ notransform = TRUE
+ Stun(INFINITY, ignore_canstun = TRUE)
icon = null
cut_overlays()
invisibility = INVISIBILITY_MAXIMUM
@@ -187,8 +186,7 @@
//Make mob invisible and spawn animation
- notransform = 1
- canmove = 0
+ notransform = TRUE
Stun(22, ignore_canstun = TRUE)
icon = null
cut_overlays()
@@ -316,13 +314,13 @@
return ..()
/mob/living/carbon/AIize()
- if (notransform)
+ if(notransform)
return
for(var/obj/item/W in src)
dropItemToGround(W)
regenerate_icons()
- notransform = 1
- canmove = 0
+ notransform = TRUE
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
return ..()
@@ -365,8 +363,8 @@
else
dropItemToGround(W)
regenerate_icons()
- notransform = 1
- canmove = 0
+ notransform = TRUE
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
for(var/t in bodyparts)
@@ -408,7 +406,7 @@
dropItemToGround(W)
regenerate_icons()
notransform = 1
- canmove = 0
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
for(var/t in bodyparts)
@@ -441,7 +439,7 @@
dropItemToGround(W)
regenerate_icons()
notransform = 1
- canmove = 0
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
for(var/t in bodyparts)
@@ -485,8 +483,8 @@
for(var/obj/item/W in src)
dropItemToGround(W)
regenerate_icons()
- notransform = 1
- canmove = 0
+ notransform = TRUE
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
for(var/t in bodyparts) //this really should not be necessary
@@ -516,7 +514,7 @@
regenerate_icons()
notransform = TRUE
- canmove = FALSE
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
var/mob/living/simple_animal/hostile/gorilla/new_gorilla = new (get_turf(src))
@@ -545,7 +543,7 @@
regenerate_icons()
notransform = TRUE
- canmove = FALSE
+ Paralyze(INFINITY)
icon = null
invisibility = INVISIBILITY_MAXIMUM
diff --git a/code/modules/ninja/suit/ninjaDrainAct.dm b/code/modules/ninja/suit/ninjaDrainAct.dm
index 10fce3d74e..6553211c07 100644
--- a/code/modules/ninja/suit/ninjaDrainAct.dm
+++ b/code/modules/ninja/suit/ninjaDrainAct.dm
@@ -263,7 +263,7 @@ They *could* go in their appropriate files, but this is supposed to be modular
visible_message("[H] electrocutes [src] with [H.p_their()] touch!", "[H] electrocutes you with [H.p_their()] touch!")
electrocute_act(15, H)
- Knockdown(G.stunforce)
+ DefaultCombatKnockdown(G.stunforce)
adjustStaminaLoss(G.stunforce*0.1, affected_zone = (istype(H) ? H.zone_selected : BODY_ZONE_CHEST))
apply_effect(EFFECT_STUTTER, G.stunforce)
SEND_SIGNAL(src, COMSIG_LIVING_MINOR_SHOCK)
diff --git a/code/modules/paperwork/paperplane.dm b/code/modules/paperwork/paperplane.dm
index 076d8b026a..06c16810b7 100644
--- a/code/modules/paperwork/paperplane.dm
+++ b/code/modules/paperwork/paperplane.dm
@@ -120,7 +120,7 @@
H.adjust_blurriness(6)
if(eyes)
eyes.applyOrganDamage(rand(6,8))
- H.Knockdown(40)
+ H.DefaultCombatKnockdown(40)
H.emote("scream")
/obj/item/paper/examine(mob/user)
diff --git a/code/modules/photography/photos/photo.dm b/code/modules/photography/photos/photo.dm
index d51f569738..d45a119553 100644
--- a/code/modules/photography/photos/photo.dm
+++ b/code/modules/photography/photos/photo.dm
@@ -84,8 +84,12 @@
set category = "Object"
set src in usr
+ var/mob/living/L = usr
+ if(!istype(L))
+ return
+
var/n_name = stripped_input(usr, "What would you like to label the photo?", "Photo Labelling", "", MAX_NAME_LEN)
//loc.loc check is for making possible renaming photos in clipboards
- if(n_name && (loc == usr || loc.loc && loc.loc == usr) && usr.stat == CONSCIOUS && usr.canmove && !usr.restrained())
+ if(n_name && (loc == usr || loc.loc && loc.loc == usr) && CHECK_MOBILITY(L, MOBILITY_USE))
name = "photo[(n_name ? text("- '[n_name]'") : null)]"
add_fingerprint(usr)
diff --git a/code/modules/pool/pool_controller.dm b/code/modules/pool/pool_controller.dm
index 681adb0ef3..52be51d1c1 100644
--- a/code/modules/pool/pool_controller.dm
+++ b/code/modules/pool/pool_controller.dm
@@ -109,9 +109,11 @@
to_chat(user, "The interface on [src] is already too damaged to short it again.")
return
-/obj/machinery/pool/controller/AltClick(mob/user)
+/obj/machinery/pool/controller/AltClick(mob/living/user)
. = ..()
- if(!isliving(user) || !user.Adjacent(src) || !user.CanReach(src) || user.IsStun() || user.IsKnockdown() || user.incapacitated())
+ if(!istype(user))
+ return FALSE
+ if(!user.Adjacent(src) || !user.CanReach(src) || !CHECK_MOBILITY(user, MOBILITY_USE))
return FALSE
visible_message("[user] starts to drain [src]!")
draining = TRUE
diff --git a/code/modules/pool/pool_main.dm b/code/modules/pool/pool_main.dm
index 2b260b5c0b..40aac0e88d 100644
--- a/code/modules/pool/pool_main.dm
+++ b/code/modules/pool/pool_main.dm
@@ -50,9 +50,11 @@
layer = BELOW_MOB_LAYER
// Mousedrop hook to normal turfs to get out of pools.
-/turf/open/MouseDrop_T(atom/from, mob/user)
+/turf/open/MouseDrop_T(atom/from, mob/living/user)
+ if(!istype(user))
+ return ..()
// I could make this /open/floor and not have the !istype but ehh - kev
- if(isliving(from) && HAS_TRAIT(from, TRAIT_SWIMMING) && isliving(user) && ((user == from) || user.CanReach(from)) && !user.IsStun() && !user.IsKnockdown() && !user.incapacitated() && !istype(src, /turf/open/pool))
+ if(HAS_TRAIT(from, TRAIT_SWIMMING) && isliving(user) && ((user == from) || user.CanReach(from)) && !CHECK_MOBILITY(user, MOBILITY_USE) && !istype(src, /turf/open/pool))
var/mob/living/L = from
//The element only exists if you're on water and a living mob, so let's skip those checks.
var/pre_msg
@@ -119,10 +121,10 @@
H.visible_message("[H] falls in the water!",
"You fall in the water!")
playsound(src, 'sound/effects/splash.ogg', 60, TRUE, 1)
- H.Knockdown(20)
+ H.DefaultCombatKnockdown(20)
return
else
- H.Knockdown(60)
+ H.DefaultCombatKnockdown(60)
H.adjustOxyLoss(5)
H.emote("cough")
H.visible_message("[H] falls in and takes a drink!",
@@ -133,19 +135,19 @@
H.visible_message("[H] falls in the drained pool!",
"You fall in the drained pool!")
H.adjustBruteLoss(7)
- H.Knockdown(80)
+ H.DefaultCombatKnockdown(80)
playsound(src, 'sound/effects/woodhit.ogg', 60, TRUE, 1)
else
H.visible_message("[H] falls in the drained pool, and cracks his skull!",
"You fall in the drained pool, and crack your skull!")
H.apply_damage(15, BRUTE, "head")
- H.Knockdown(200) // This should hurt. And it does.
+ H.DefaultCombatKnockdown(200) // This should hurt. And it does.
playsound(src, 'sound/effects/woodhit.ogg', 60, TRUE, 1)
playsound(src, 'sound/misc/crack.ogg', 100, TRUE)
else
H.visible_message("[H] falls in the drained pool, but had an helmet!",
"You fall in the drained pool, but you had an helmet!")
- H.Knockdown(40)
+ H.DefaultCombatKnockdown(40)
playsound(src, 'sound/effects/woodhit.ogg', 60, TRUE, 1)
else if(filled)
victim.adjustStaminaLoss(1)
diff --git a/code/modules/pool/pool_structures.dm b/code/modules/pool/pool_structures.dm
index 92350abf44..4cea485237 100644
--- a/code/modules/pool/pool_structures.dm
+++ b/code/modules/pool/pool_structures.dm
@@ -119,7 +119,7 @@
"You misstep!")
var/atom/throw_target = get_edge_target_turf(src, dir)
jumper.throw_at(throw_target, 0, 1, callback = CALLBACK(src, .proc/on_finish_jump, jumper))
- jumper.Knockdown(100)
+ jumper.DefaultCombatKnockdown(100)
jumper.adjustBruteLoss(10)
if(91 to 100)
@@ -156,4 +156,4 @@
to_chat(victim, "That was stupid of you..")
victim.visible_message("[victim] smashes into the ground!")
victim.apply_damage(50)
- victim.Knockdown(200)
+ victim.DefaultCombatKnockdown(200)
diff --git a/code/modules/power/singularity/containment_field.dm b/code/modules/power/singularity/containment_field.dm
index 31e0c479ed..89596eb82f 100644
--- a/code/modules/power/singularity/containment_field.dm
+++ b/code/modules/power/singularity/containment_field.dm
@@ -108,7 +108,7 @@
var/shock_damage = min(rand(30,40),rand(30,40))
if(iscarbon(user))
- user.Knockdown(300)
+ user.DefaultCombatKnockdown(300)
user.electrocute_act(shock_damage, src, 1)
else if(issilicon(user))
diff --git a/code/modules/projectiles/guns/ballistic/revolver.dm b/code/modules/projectiles/guns/ballistic/revolver.dm
index 611f8c57bd..17dd1341b9 100644
--- a/code/modules/projectiles/guns/ballistic/revolver.dm
+++ b/code/modules/projectiles/guns/ballistic/revolver.dm
@@ -363,4 +363,4 @@
user.visible_message("[user] somehow manages to shoot [user.p_them()]self in the face!", "You somehow shoot yourself in the face! How the hell?!")
user.emote("scream")
user.drop_all_held_items()
- user.Knockdown(80)
+ user.DefaultCombatKnockdown(80)
diff --git a/code/modules/projectiles/guns/energy/dueling.dm b/code/modules/projectiles/guns/energy/dueling.dm
index 615bb5d939..2f0aa00027 100644
--- a/code/modules/projectiles/guns/energy/dueling.dm
+++ b/code/modules/projectiles/guns/energy/dueling.dm
@@ -334,7 +334,7 @@
L.death() //Die, powergamers.
if(DUEL_HUGBOX_NONLETHAL)
L.adjustStaminaLoss(200, forced = TRUE) //Die, powergamers x 2
- L.Knockdown(100, override_hardstun = 100) //For good measure.
+ L.Paralyze(100) //For good measure.
//Storage case.
/obj/item/storage/lockbox/dueling
diff --git a/code/modules/projectiles/projectile/magic.dm b/code/modules/projectiles/projectile/magic.dm
index 7608e5f4a8..7695ef77be 100644
--- a/code/modules/projectiles/projectile/magic.dm
+++ b/code/modules/projectiles/projectile/magic.dm
@@ -124,8 +124,8 @@
if(!istype(M) || M.stat == DEAD || M.notransform || (GODMODE & M.status_flags))
return
- M.notransform = 1
- M.canmove = 0
+ M.notransform = TRUE
+ M.Paralyze(INFINITY)
M.icon = null
M.cut_overlays()
M.invisibility = INVISIBILITY_ABSTRACT
@@ -529,7 +529,7 @@
else
used = 1
victim.take_overall_damage(30,30)
- victim.Knockdown(60)
+ victim.DefaultCombatKnockdown(60)
explosion(src, -1, -1, -1, -1, FALSE, FALSE, 5)
return BULLET_ACT_HIT
diff --git a/code/modules/projectiles/projectile/special/hallucination.dm b/code/modules/projectiles/projectile/special/hallucination.dm
index a6da1f26bd..3aa85c085f 100644
--- a/code/modules/projectiles/projectile/special/hallucination.dm
+++ b/code/modules/projectiles/projectile/special/hallucination.dm
@@ -166,7 +166,7 @@
hal_impact_effect_wall = null
/obj/item/projectile/hallucination/taser/hal_apply_effect()
- hal_target.Knockdown(100)
+ hal_target.DefaultCombatKnockdown(100)
hal_target.stuttering += 20
if(hal_target.dna && hal_target.dna.check_mutation(HULK))
hal_target.say(pick(";RAAAAAAAARGH!", ";HNNNNNNNNNGGGGGGH!", ";GWAAAAAAAARRRHHH!", "NNNNNNNNGGGGGGGGHH!", ";AAAAAAARRRGH!" ), forced = "hulk")
@@ -199,7 +199,7 @@
hal_impact_effect_wall = null
/obj/item/projectile/hallucination/ebow/hal_apply_effect()
- hal_target.Knockdown(100)
+ hal_target.DefaultCombatKnockdown(100)
hal_target.stuttering += 5
hal_target.adjustStaminaLoss(8)
diff --git a/code/modules/projectiles/projectile/special/neurotoxin.dm b/code/modules/projectiles/projectile/special/neurotoxin.dm
index 12f502f9f0..a72d078384 100644
--- a/code/modules/projectiles/projectile/special/neurotoxin.dm
+++ b/code/modules/projectiles/projectile/special/neurotoxin.dm
@@ -10,5 +10,5 @@
nodamage = TRUE
else if(iscarbon(target))
var/mob/living/L = target
- L.Knockdown(100, TRUE, FALSE, 30, 25)
+ L.DefaultCombatKnockdown(100, TRUE, FALSE, 30, 25)
return ..()
diff --git a/code/modules/reagents/chemistry/holder.dm b/code/modules/reagents/chemistry/holder.dm
index d53e4dfcbe..eff1531e23 100644
--- a/code/modules/reagents/chemistry/holder.dm
+++ b/code/modules/reagents/chemistry/holder.dm
@@ -342,7 +342,7 @@
addiction_tick++
if(C && need_mob_update) //some of the metabolized reagents had effects on the mob that requires some updates.
C.updatehealth()
- C.update_canmove()
+ C.update_mobility()
C.update_stamina()
update_total()
diff --git a/code/modules/reagents/chemistry/reagents/drug_reagents.dm b/code/modules/reagents/chemistry/reagents/drug_reagents.dm
index a2e651d791..04e7c0a74e 100644
--- a/code/modules/reagents/chemistry/reagents/drug_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/drug_reagents.dm
@@ -20,7 +20,7 @@
/datum/reagent/drug/space_drugs/on_mob_life(mob/living/carbon/M)
M.set_drugginess(15)
if(isturf(M.loc) && !isspaceturf(M.loc))
- if(M.canmove)
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE))
if(prob(10))
step(M, pick(GLOB.cardinals))
if(prob(7))
@@ -52,8 +52,7 @@
var/smoke_message = pick("You feel relaxed.", "You feel calmed.","You feel alert.","You feel rugged.")
to_chat(M, "[smoke_message]")
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "smoked", /datum/mood_event/smoked, name)
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
+ M.AdjustAllImmobility(-20, 0)
M.AdjustUnconscious(-20, 0)
M.adjustStaminaLoss(-0.5*REM, 0)
..()
@@ -72,8 +71,7 @@
if(prob(5))
var/high_message = pick("You feel jittery.", "You feel like you gotta go fast.", "You feel like you need to step it up.")
to_chat(M, "[high_message]")
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
+ M.AdjustAllImmobility(-20, 0)
M.AdjustUnconscious(-20, 0)
..()
. = 1
@@ -182,8 +180,7 @@
var/high_message = pick("You feel hyper.", "You feel like you need to go faster.", "You feel like you can run the world.")
if(prob(5))
to_chat(M, "[high_message]")
- M.AdjustStun(-40, 0)
- M.AdjustKnockdown(-40, 0)
+ M.AdjustAllImmobility(-40, 0)
M.AdjustUnconscious(-40, 0)
M.adjustStaminaLoss(-7.5 * REM, 0)
if(jitter)
@@ -197,7 +194,7 @@
. = 1
/datum/reagent/drug/methamphetamine/overdose_process(mob/living/M)
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i in 1 to 4)
step(M, pick(GLOB.cardinals))
if(prob(20))
@@ -224,7 +221,7 @@
..()
/datum/reagent/drug/methamphetamine/addiction_act_stage3(mob/living/M)
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 4, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(15)
@@ -234,7 +231,7 @@
..()
/datum/reagent/drug/methamphetamine/addiction_act_stage4(mob/living/carbon/human/M)
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 8, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(20)
@@ -286,7 +283,7 @@
M.adjustStaminaLoss(-5, 0)
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, 4)
M.hallucination += 5
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
step(M, pick(GLOB.cardinals))
step(M, pick(GLOB.cardinals))
..()
@@ -294,7 +291,7 @@
/datum/reagent/drug/bath_salts/overdose_process(mob/living/M)
M.hallucination += 5
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i in 1 to 8)
step(M, pick(GLOB.cardinals))
if(prob(20))
@@ -305,7 +302,7 @@
/datum/reagent/drug/bath_salts/addiction_act_stage1(mob/living/M)
M.hallucination += 10
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 8, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(5)
@@ -316,7 +313,7 @@
/datum/reagent/drug/bath_salts/addiction_act_stage2(mob/living/M)
M.hallucination += 20
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 8, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(10)
@@ -328,7 +325,7 @@
/datum/reagent/drug/bath_salts/addiction_act_stage3(mob/living/M)
M.hallucination += 30
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 12, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(15)
@@ -340,7 +337,7 @@
/datum/reagent/drug/bath_salts/addiction_act_stage4(mob/living/carbon/human/M)
M.hallucination += 30
- if(M.canmove && !ismovableatom(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !ismovableatom(M.loc))
for(var/i = 0, i < 16, i++)
step(M, pick(GLOB.cardinals))
M.Jitter(50)
diff --git a/code/modules/reagents/chemistry/reagents/food_reagents.dm b/code/modules/reagents/chemistry/reagents/food_reagents.dm
index 52eee9f8ea..fa30609c54 100644
--- a/code/modules/reagents/chemistry/reagents/food_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/food_reagents.dm
@@ -323,7 +323,7 @@
victim.blind_eyes(2)
victim.confused = max(M.confused, 3)
victim.damageoverlaytemp = 60
- victim.Knockdown(80, override_hardstun = 0.1, override_stamdmg = min(reac_volume * 3, 15))
+ victim.DefaultCombatKnockdown(80, override_hardstun = 0.1, override_stamdmg = min(reac_volume * 3, 15))
return
else if ( eyes_covered ) // Eye cover is better than mouth cover
victim.blur_eyes(3)
@@ -336,7 +336,7 @@
victim.blind_eyes(3)
victim.confused = max(M.confused, 6)
victim.damageoverlaytemp = 75
- victim.Knockdown(80, override_hardstun = 0.1, override_stamdmg = min(reac_volume * 5, 25))
+ victim.DefaultCombatKnockdown(80, override_hardstun = 0.1, override_stamdmg = min(reac_volume * 5, 25))
victim.update_damage_hud()
/datum/reagent/consumable/condensedcapsaicin/on_mob_life(mob/living/carbon/M)
diff --git a/code/modules/reagents/chemistry/reagents/medicine_reagents.dm b/code/modules/reagents/chemistry/reagents/medicine_reagents.dm
index 91e84b8c47..4b2c1447c5 100644
--- a/code/modules/reagents/chemistry/reagents/medicine_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/medicine_reagents.dm
@@ -46,8 +46,7 @@
REMOVE_TRAITS_NOT_IN(M, list(SPECIES_TRAIT, ROUNDSTART_TRAIT, ORGAN_TRAIT))
M.set_blurriness(0)
M.set_blindness(0)
- M.SetKnockdown(0, 0)
- M.SetStun(0, 0)
+ M.SetAllImmobility(0, 0)
M.SetUnconscious(0, 0)
M.silent = FALSE
M.dizziness = 0
@@ -87,8 +86,7 @@
/datum/reagent/medicine/synaptizine/on_mob_life(mob/living/carbon/M)
M.drowsyness = max(M.drowsyness-5, 0)
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
+ M.AdjustAllImmobility(-20, 0)
M.AdjustUnconscious(-20, 0)
if(holder.has_reagent(/datum/reagent/toxin/mindbreaker))
holder.remove_reagent(/datum/reagent/toxin/mindbreaker, 5)
@@ -637,10 +635,9 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 12
/datum/reagent/medicine/ephedrine/on_mob_life(mob/living/carbon/M)
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
- M.AdjustUnconscious(-20, 0)
- M.adjustStaminaLoss(-4.5*REM, 0)
+ M.AdjustAllImmobility(-20, FALSE)
+ M.AdjustUnconscious(-20, FALSE)
+ M.adjustStaminaLoss(-4.5*REM, FALSE)
M.Jitter(10)
if(prob(50))
M.confused = max(M.confused, 1)
@@ -848,8 +845,7 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
M.adjustStaminaLoss(-0.5*REM, 0)
. = 1
if(prob(20))
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
+ M.AdjustAllImmobility(-20, 0)
M.AdjustUnconscious(-20, 0)
..()
@@ -1003,21 +999,20 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
/datum/reagent/medicine/stimulants/on_mob_life(mob/living/carbon/M)
if(M.health < 50 && M.health > 0)
- M.adjustOxyLoss(-1*REM, 0)
- M.adjustToxLoss(-1*REM, 0)
- M.adjustBruteLoss(-1*REM, 0)
- M.adjustFireLoss(-1*REM, 0)
- M.AdjustStun(-60, 0)
- M.AdjustKnockdown(-60, 0)
- M.AdjustUnconscious(-60, 0)
- M.adjustStaminaLoss(-20*REM, 0)
+ M.adjustOxyLoss(-1*REM, FALSE)
+ M.adjustToxLoss(-1*REM, FALSE)
+ M.adjustBruteLoss(-1*REM, FALSE)
+ M.adjustFireLoss(-1*REM, FALSE)
+ M.AdjustAllImmobility(-60, FALSE)
+ M.AdjustUnconscious(-60, FALSE)
+ M.adjustStaminaLoss(-20*REM, FALSE)
..()
. = 1
/datum/reagent/medicine/stimulants/overdose_process(mob/living/M)
if(prob(33))
- M.adjustStaminaLoss(2.5*REM, 0)
- M.adjustToxLoss(1*REM, 0)
+ M.adjustStaminaLoss(2.5*REM, FALSE)
+ M.adjustToxLoss(1*REM, FALSE)
M.losebreath++
. = 1
..()
@@ -1046,12 +1041,12 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 5
/datum/reagent/medicine/bicaridine/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-2*REM, 0)
+ M.adjustBruteLoss(-2*REM, FALSE)
..()
. = 1
/datum/reagent/medicine/bicaridine/overdose_process(mob/living/M)
- M.adjustBruteLoss(4*REM, 0)
+ M.adjustBruteLoss(4*REM, FALSE)
..()
. = 1
@@ -1064,12 +1059,12 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 9.7
/datum/reagent/medicine/dexalin/on_mob_life(mob/living/carbon/M)
- M.adjustOxyLoss(-2*REM, 0)
+ M.adjustOxyLoss(-2*REM, FALSE)
..()
. = 1
/datum/reagent/medicine/dexalin/overdose_process(mob/living/M)
- M.adjustOxyLoss(4*REM, 0)
+ M.adjustOxyLoss(4*REM, FALSE)
..()
. = 1
@@ -1082,12 +1077,12 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 9
/datum/reagent/medicine/kelotane/on_mob_life(mob/living/carbon/M)
- M.adjustFireLoss(-2*REM, 0)
+ M.adjustFireLoss(-2*REM, FALSE)
..()
. = 1
/datum/reagent/medicine/kelotane/overdose_process(mob/living/M)
- M.adjustFireLoss(4*REM, 0)
+ M.adjustFireLoss(4*REM, FALSE)
..()
. = 1
@@ -1101,14 +1096,14 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 10
/datum/reagent/medicine/antitoxin/on_mob_life(mob/living/carbon/M)
- M.adjustToxLoss(-2*REM, 0)
+ M.adjustToxLoss(-2*REM, FALSE)
for(var/datum/reagent/toxin/R in M.reagents.reagent_list)
M.reagents.remove_reagent(R.type,1)
..()
. = 1
/datum/reagent/medicine/antitoxin/overdose_process(mob/living/M)
- M.adjustToxLoss(4*REM, 0) // End result is 2 toxin loss taken, because it heals 2 and then removes 4.
+ M.adjustToxLoss(4*REM, FALSE) // End result is 2 toxin loss taken, because it heals 2 and then removes 4.
..()
. = 1
@@ -1134,18 +1129,18 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
/datum/reagent/medicine/tricordrazine/on_mob_life(mob/living/carbon/M)
if(prob(80))
- M.adjustBruteLoss(-1*REM, 0)
- M.adjustFireLoss(-1*REM, 0)
- M.adjustOxyLoss(-1*REM, 0)
- M.adjustToxLoss(-1*REM, 0)
+ M.adjustBruteLoss(-1*REM, FALSE)
+ M.adjustFireLoss(-1*REM, FALSE)
+ M.adjustOxyLoss(-1*REM, FALSE)
+ M.adjustToxLoss(-1*REM, FALSE)
. = 1
..()
/datum/reagent/medicine/tricordrazine/overdose_process(mob/living/M)
- M.adjustToxLoss(2*REM, 0)
- M.adjustOxyLoss(2*REM, 0)
- M.adjustBruteLoss(2*REM, 0)
- M.adjustFireLoss(2*REM, 0)
+ M.adjustToxLoss(2*REM, FALSE)
+ M.adjustOxyLoss(2*REM, FALSE)
+ M.adjustBruteLoss(2*REM, FALSE)
+ M.adjustFireLoss(2*REM, FALSE)
..()
. = 1
@@ -1157,9 +1152,9 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
taste_description = "jelly"
/datum/reagent/medicine/regen_jelly/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-1.5*REM, 0)
- M.adjustFireLoss(-1.5*REM, 0)
- M.adjustOxyLoss(-1.5*REM, 0)
+ M.adjustBruteLoss(-1.5*REM, FALSE)
+ M.adjustFireLoss(-1.5*REM, FALSE)
+ M.adjustOxyLoss(-1.5*REM, FALSE)
M.adjustToxLoss(-1.5*REM, 0, TRUE) //heals TOXINLOVERs
. = 1
..()
@@ -1172,13 +1167,13 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 11
/datum/reagent/medicine/syndicate_nanites/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-5*REM, 0) //A ton of healing - this is a 50 telecrystal investment.
- M.adjustFireLoss(-5*REM, 0)
- M.adjustOxyLoss(-15, 0)
- M.adjustToxLoss(-5*REM, 0)
+ M.adjustBruteLoss(-5*REM, FALSE) //A ton of healing - this is a 50 telecrystal investment.
+ M.adjustFireLoss(-5*REM, FALSE)
+ M.adjustOxyLoss(-15, FALSE)
+ M.adjustToxLoss(-5*REM, FALSE)
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, -15*REM)
- M.adjustCloneLoss(-3*REM, 0)
- M.adjustStaminaLoss(-25*REM,0)
+ M.adjustCloneLoss(-3*REM, FALSE)
+ M.adjustStaminaLoss(-25*REM,FALSE)
if(M.blood_volume < (BLOOD_VOLUME_NORMAL*M.blood_ratio))
M.blood_volume += 40 // blood fall out man bad
..()
@@ -1192,13 +1187,13 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 11
/datum/reagent/medicine/lesser_syndicate_nanites/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-3*REM, 0) // hidden gold shh
- M.adjustFireLoss(-3*REM, 0)
- M.adjustOxyLoss(-15, 0)
- M.adjustToxLoss(-3*REM, 0)
+ M.adjustBruteLoss(-3*REM, FALSE) // hidden gold shh
+ M.adjustFireLoss(-3*REM, FALSE)
+ M.adjustOxyLoss(-15, FALSE)
+ M.adjustToxLoss(-3*REM, FALSE)
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, -15*REM)
- M.adjustCloneLoss(-3*REM, 0)
- M.adjustStaminaLoss(-20*REM,0)
+ M.adjustCloneLoss(-3*REM, FALSE)
+ M.adjustStaminaLoss(-20*REM,FALSE)
if(M.blood_volume < (BLOOD_VOLUME_NORMAL*M.blood_ratio))
M.blood_volume += 20 // blood fall out man bad
..()
@@ -1215,17 +1210,17 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 11.8
/datum/reagent/medicine/neo_jelly/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-1.5*REM, 0)
- M.adjustFireLoss(-1.5*REM, 0)
- M.adjustOxyLoss(-1.5*REM, 0)
+ M.adjustBruteLoss(-1.5*REM, FALSE)
+ M.adjustFireLoss(-1.5*REM, FALSE)
+ M.adjustOxyLoss(-1.5*REM, FALSE)
M.adjustToxLoss(-1.5*REM, 0, TRUE) //heals TOXINLOVERs
. = 1
..()
/datum/reagent/medicine/neo_jelly/overdose_process(mob/living/M)
- M.adjustOxyLoss(2.6*REM, 0)
- M.adjustBruteLoss(3.5*REM, 0)
- M.adjustFireLoss(3.5*REM, 0)
+ M.adjustOxyLoss(2.6*REM, FALSE)
+ M.adjustBruteLoss(3.5*REM, FALSE)
+ M.adjustFireLoss(3.5*REM, FALSE)
..()
. = 1
@@ -1237,13 +1232,13 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
pH = 11
/datum/reagent/medicine/earthsblood/on_mob_life(mob/living/carbon/M)
- M.adjustBruteLoss(-3 * REM, 0)
- M.adjustFireLoss(-3 * REM, 0)
- M.adjustOxyLoss(-15 * REM, 0)
- M.adjustToxLoss(-3 * REM, 0, TRUE) //Heals TOXINLOVERS
+ M.adjustBruteLoss(-3 * REM, FALSE)
+ M.adjustFireLoss(-3 * REM, FALSE)
+ M.adjustOxyLoss(-15 * REM, FALSE)
+ M.adjustToxLoss(-3 * REM, FALSE, TRUE) //Heals TOXINLOVERS
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, 2 * REM, 150) //This does, after all, come from ambrosia, and the most powerful ambrosia in existence, at that!
- M.adjustCloneLoss(-1 * REM, 0)
- M.adjustStaminaLoss(-13 * REM, 0)
+ M.adjustCloneLoss(-1 * REM, FALSE)
+ M.adjustStaminaLoss(-13 * REM, FALSE)
M.jitteriness = min(max(0, M.jitteriness + 3), 30)
M.druggy = min(max(0, M.druggy + 10), 15) //See above
..()
@@ -1251,7 +1246,7 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
/datum/reagent/medicine/earthsblood/overdose_process(mob/living/M)
M.hallucination = min(max(0, M.hallucination + 5), 60)
- M.adjustToxLoss(8 * REM, 0, TRUE) //Hurts TOXINLOVERS
+ M.adjustToxLoss(8 * REM, FALSE, TRUE) //Hurts TOXINLOVERS
..()
. = 1
@@ -1306,8 +1301,7 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
/datum/reagent/medicine/changelingadrenaline/on_mob_life(mob/living/carbon/M as mob)
M.AdjustUnconscious(-20, 0)
- M.AdjustStun(-20, 0)
- M.AdjustKnockdown(-20, 0)
+ M.AdjustAllImmobility(-20, 0)
M.AdjustSleeping(-20, 0)
M.adjustStaminaLoss(-30, 0)
..()
@@ -1390,8 +1384,7 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
/datum/reagent/medicine/modafinil/on_mob_life(mob/living/carbon/M)
if(!overdosed) // We do not want any effects on OD
overdose_threshold = overdose_threshold + rand(-10,10)/10 // for extra fun
- M.AdjustStun(-5, 0)
- M.AdjustKnockdown(-5, 0)
+ M.AdjustAllImmobility(-5, 0)
M.AdjustUnconscious(-5, 0)
M.adjustStaminaLoss(-1*REM, 0)
M.Jitter(1)
@@ -1423,7 +1416,7 @@ datum/reagent/medicine/styptic_powder/overdose_start(mob/living/M)
if(prob(20))
to_chat(M, "You have a sudden fit!")
M.emote("moan")
- M.Knockdown(20, 1, 0) // you should be in a bad spot at this point unless epipen has been used
+ M.DefaultCombatKnockdown(20, 1, 0) // you should be in a bad spot at this point unless epipen has been used
if(81)
to_chat(M, "You feel too exhausted to continue!") // at this point you will eventually die unless you get charcoal
M.adjustOxyLoss(0.1*REM, 0)
diff --git a/code/modules/reagents/chemistry/reagents/other_reagents.dm b/code/modules/reagents/chemistry/reagents/other_reagents.dm
index 9794b58112..5038a4b68c 100644
--- a/code/modules/reagents/chemistry/reagents/other_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/other_reagents.dm
@@ -391,22 +391,21 @@
/datum/reagent/fuel/unholywater/on_mob_life(mob/living/carbon/M)
if(iscultist(M))
M.drowsyness = max(M.drowsyness-5, 0)
- M.AdjustUnconscious(-20, 0)
- M.AdjustStun(-40, 0)
- M.AdjustKnockdown(-40, 0)
- M.adjustStaminaLoss(-10, 0)
- M.adjustToxLoss(-2, 0, TRUE)
- M.adjustOxyLoss(-2, 0)
- M.adjustBruteLoss(-2, 0)
- M.adjustFireLoss(-2, 0)
+ M.AdjustUnconscious(-20, FALSE)
+ M.AdjustAllImmobility(-40, FALSE)
+ M.adjustStaminaLoss(-10, FALSE)
+ M.adjustToxLoss(-2, FALSE, TRUE)
+ M.adjustOxyLoss(-2, FALSE)
+ M.adjustBruteLoss(-2, FALSE)
+ M.adjustFireLoss(-2, FALSE)
if(ishuman(M) && M.blood_volume < (BLOOD_VOLUME_NORMAL*M.blood_ratio))
M.blood_volume += 3
else // Will deal about 90 damage when 50 units are thrown
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, 3, 150)
- M.adjustToxLoss(2, 0)
- M.adjustFireLoss(2, 0)
- M.adjustOxyLoss(2, 0)
- M.adjustBruteLoss(2, 0)
+ M.adjustToxLoss(2, FALSE)
+ M.adjustFireLoss(2, FALSE)
+ M.adjustOxyLoss(2, FALSE)
+ M.adjustBruteLoss(2, FALSE)
holder.remove_reagent(type, 1)
return TRUE
@@ -418,8 +417,8 @@
/datum/reagent/hellwater/on_mob_life(mob/living/carbon/M)
M.fire_stacks = min(5,M.fire_stacks + 3)
M.IgniteMob() //Only problem with igniting people is currently the commonly availible fire suits make you immune to being on fire
- M.adjustToxLoss(1, 0)
- M.adjustFireLoss(1, 0) //Hence the other damages... ain't I a bastard?
+ M.adjustToxLoss(1, FALSE)
+ M.adjustFireLoss(1, FALSE) //Hence the other damages... ain't I a bastard?
M.adjustOrganLoss(ORGAN_SLOT_BRAIN, 5, 150)
holder.remove_reagent(type, 1)
pH = 0.1
@@ -432,23 +431,23 @@
/datum/reagent/fuel/holyoil/on_mob_life(mob/living/carbon/M)
if(is_servant_of_ratvar(M))
M.drowsyness = max(M.drowsyness-5, 0)
- M.AdjustUnconscious(-60, 0)
- M.AdjustStun(-30, 0)
- M.AdjustKnockdown(-70, 0)
- M.adjustStaminaLoss(-15, 0)
- M.adjustToxLoss(-5, 0, TRUE)
- M.adjustOxyLoss(-3, 0)
- M.adjustBruteLoss(-3, 0)
- M.adjustFireLoss(-5, 0)
+ M.AdjustUnconscious(-60, FALSE)
+ M.AdjustAllImmobility(-30, FALSE)
+ M.AdjustKnockdown(-40, FALSE)
+ M.adjustStaminaLoss(-15, FALSE)
+ M.adjustToxLoss(-5, FALSE, TRUE)
+ M.adjustOxyLoss(-3, FALSE)
+ M.adjustBruteLoss(-3, FALSE)
+ M.adjustFireLoss(-5, FALSE)
if(iscultist(M))
- M.AdjustUnconscious(1, 0)
- M.AdjustStun(10, 0)
- M.AdjustKnockdown(20, 0)
- M.adjustStaminaLoss(15, 0)
+ M.AdjustUnconscious(1, FALSE)
+ M.AdjustAllImmobility(10, FALSE)
+ M.AdjustKnockdown(10, FALSE)
+ M.adjustStaminaLoss(15, FALSE)
else
- M.adjustToxLoss(3, 0)
- M.adjustOxyLoss(2, 0)
- M.adjustStaminaLoss(10, 0)
+ M.adjustToxLoss(3, FALSE)
+ M.adjustOxyLoss(2, FALSE)
+ M.adjustStaminaLoss(10, FALSE)
holder.remove_reagent(type, 1)
return TRUE
@@ -601,7 +600,7 @@
return
to_chat(H, "You crumple in agony as your flesh wildly morphs into new forms!")
H.visible_message("[H] falls to the ground and screams as [H.p_their()] skin bubbles and froths!") //'froths' sounds painful when used with SKIN.
- H.Knockdown(60)
+ H.DefaultCombatKnockdown(60)
addtimer(CALLBACK(src, .proc/mutate, H), 30)
return
@@ -907,7 +906,7 @@
taste_mult = 0 // apparently tasteless.
/datum/reagent/mercury/on_mob_life(mob/living/carbon/M)
- if(M.canmove && !isspaceturf(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !isspaceturf(M.loc))
step(M, pick(GLOB.cardinals))
if(prob(5))
M.emote(pick("twitch","drool","moan"))
@@ -987,7 +986,7 @@
pH = 11.3
/datum/reagent/lithium/on_mob_life(mob/living/carbon/M)
- if(M.canmove && !isspaceturf(M.loc))
+ if(CHECK_MOBILITY(M, MOBILITY_MOVE) && !isspaceturf(M.loc))
step(M, pick(GLOB.cardinals))
if(prob(5))
M.emote(pick("twitch","drool","moan"))
diff --git a/code/modules/reagents/chemistry/reagents/pyrotechnic_reagents.dm b/code/modules/reagents/chemistry/reagents/pyrotechnic_reagents.dm
index 9eb033824d..cd63fff0db 100644
--- a/code/modules/reagents/chemistry/reagents/pyrotechnic_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/pyrotechnic_reagents.dm
@@ -227,8 +227,7 @@
/datum/reagent/teslium/energized_jelly/on_mob_life(mob/living/carbon/M)
if(isjellyperson(M))
shock_timer = 0 //immune to shocks
- M.AdjustStun(-40, 0)
- M.AdjustKnockdown(-40, 0)
+ M.AdjustAllImmobility(-40, 0)
M.AdjustUnconscious(-40, 0)
M.adjustStaminaLoss(-2, 0)
if(isluminescent(M))
diff --git a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
index 946cb1307c..025587bc2a 100644
--- a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
@@ -539,7 +539,7 @@
var/picked_option = rand(1,3)
switch(picked_option)
if(1)
- C.Knockdown(60, 0)
+ C.DefaultCombatKnockdown(60, 0)
. = TRUE
if(2)
C.losebreath += 10
@@ -678,7 +678,7 @@
/datum/reagent/toxin/curare/on_mob_life(mob/living/carbon/M)
if(current_cycle >= 11)
- M.Knockdown(60, 0)
+ M.DefaultCombatKnockdown(60, 0)
M.adjustOxyLoss(1*REM, 0)
. = 1
..()
@@ -843,7 +843,7 @@
holder.remove_reagent(type, actual_metaboliztion_rate * M.metabolism_efficiency)
M.adjustToxLoss(actual_toxpwr*REM, 0)
if(prob(10))
- M.Knockdown(20, 0)
+ M.DefaultCombatKnockdown(20, 0)
. = 1
..()
diff --git a/code/modules/reagents/chemistry/recipes/pyrotechnics.dm b/code/modules/reagents/chemistry/recipes/pyrotechnics.dm
index 3930988380..2c8be10ace 100644
--- a/code/modules/reagents/chemistry/recipes/pyrotechnics.dm
+++ b/code/modules/reagents/chemistry/recipes/pyrotechnics.dm
@@ -76,7 +76,7 @@
for(var/mob/living/carbon/C in get_hearers_in_view(round(multiplier/48,1),get_turf(holder.my_atom)))
if(iscultist(C))
to_chat(C, "The divine explosion sears you!")
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
C.adjust_fire_stacks(5)
C.IgniteMob()
..(holder, multiplier, T)
@@ -252,7 +252,7 @@
for(var/mob/living/carbon/C in get_hearers_in_view(range, location))
if(C.flash_act())
if(get_dist(C, location) < 4)
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
else
C.Stun(100)
holder.remove_reagent(/datum/reagent/flash_powder, multiplier*3)
@@ -273,7 +273,7 @@
for(var/mob/living/carbon/C in get_hearers_in_view(range, location))
if(C.flash_act())
if(get_dist(C, location) < 4)
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
else
C.Stun(100)
diff --git a/code/modules/recycling/disposal/bin.dm b/code/modules/recycling/disposal/bin.dm
index d39d9f4b85..38b62546a8 100644
--- a/code/modules/recycling/disposal/bin.dm
+++ b/code/modules/recycling/disposal/bin.dm
@@ -372,7 +372,7 @@
/obj/machinery/disposal/bin/shove_act(mob/living/target, mob/living/user)
if(!can_stuff_mob_in(target, user, TRUE))
return FALSE
- target.Knockdown(SHOVE_KNOCKDOWN_SOLID)
+ target.DefaultCombatKnockdown(SHOVE_KNOCKDOWN_SOLID)
target.forceMove(src)
user.visible_message("[user.name] shoves [target.name] into \the [src]!",
"You shove [target.name] into \the [src]!", null, COMBAT_MESSAGE_RANGE)
diff --git a/code/modules/research/nanites/nanite_programs/rogue.dm b/code/modules/research/nanites/nanite_programs/rogue.dm
index 287aed36fe..cd9b30bee9 100644
--- a/code/modules/research/nanites/nanite_programs/rogue.dm
+++ b/code/modules/research/nanites/nanite_programs/rogue.dm
@@ -116,4 +116,4 @@
host_mob.drop_all_held_items()
else if(prob(4))
to_chat(host_mob, "You can't feel your legs!")
- host_mob.Knockdown(30)
+ host_mob.DefaultCombatKnockdown(30)
diff --git a/code/modules/research/nanites/nanite_programs/suppression.dm b/code/modules/research/nanites/nanite_programs/suppression.dm
index 56fd7fa044..1c882cead3 100644
--- a/code/modules/research/nanites/nanite_programs/suppression.dm
+++ b/code/modules/research/nanites/nanite_programs/suppression.dm
@@ -50,9 +50,11 @@
trigger_cooldown = 300
rogue_types = list(/datum/nanite_program/shocking, /datum/nanite_program/nerve_decay)
-/datum/nanite_program/stun/on_trigger(comm_message)
+/datum/nanite_program/triggered/stun/trigger(delayed)
+ if(!..())
+ return
+ host_mob.DefaultCombatKnockdown(80)
playsound(host_mob, "sparks", 75, TRUE, -1)
- host_mob.Knockdown(80)
/datum/nanite_program/pacifying
name = "Pacification"
diff --git a/code/modules/ruins/spaceruin_code/hilbertshotel.dm b/code/modules/ruins/spaceruin_code/hilbertshotel.dm
index 8648e46cb9..b6e39e98dc 100644
--- a/code/modules/ruins/spaceruin_code/hilbertshotel.dm
+++ b/code/modules/ruins/spaceruin_code/hilbertshotel.dm
@@ -249,7 +249,7 @@ GLOBAL_VAR_INIT(hhmysteryRoomNumber, 1337)
to_chat(user, "The door seems to be malfunctioning and refuses to operate!")
return
if(alert(user, "Hilbert's Hotel would like to remind you that while we will do everything we can to protect the belongings you leave behind, we make no guarantees of their safety while you're gone, especially that of the health of any living creatures. With that in mind, are you ready to leave?", "Exit", "Leave", "Stay") == "Leave")
- if(!user.canmove || (get_dist(get_turf(src), get_turf(user)) > 1)) //no teleporting around if they're dead or moved away during the prompt.
+ if(!CHECK_MOBILITY(user, MOBILITY_MOVE) || (get_dist(get_turf(src), get_turf(user)) > 1)) //no teleporting around if they're dead or moved away during the prompt.
return
user.forceMove(get_turf(parentSphere))
do_sparks(3, FALSE, get_turf(user))
diff --git a/code/modules/shuttle/on_move.dm b/code/modules/shuttle/on_move.dm
index beaaa51adb..701c153783 100644
--- a/code/modules/shuttle/on_move.dm
+++ b/code/modules/shuttle/on_move.dm
@@ -318,7 +318,7 @@ All ShuttleMove procs go here
var/knockdown = movement_force["KNOCKDOWN"]
if(knockdown)
- Knockdown(knockdown)
+ DefaultCombatKnockdown(knockdown)
/mob/living/simple_animal/hostile/megafauna/onShuttleMove(turf/newT, turf/oldT, list/movement_force, move_dir, obj/docking_port/stationary/old_dock, obj/docking_port/mobile/moving_dock)
diff --git a/code/modules/shuttle/special.dm b/code/modules/shuttle/special.dm
index 2d17a8e55a..f05adb9309 100644
--- a/code/modules/shuttle/special.dm
+++ b/code/modules/shuttle/special.dm
@@ -186,7 +186,7 @@
// No climbing on the bar please
var/mob/living/M = AM
var/throwtarget = get_edge_target_turf(src, boot_dir)
- M.Knockdown(40)
+ M.DefaultCombatKnockdown(40)
M.throw_at(throwtarget, 5, 1)
to_chat(M, "No climbing on the bar please.")
else
diff --git a/code/modules/spells/spell_types/devil.dm b/code/modules/spells/spell_types/devil.dm
index d97d466e4d..3952a347e0 100644
--- a/code/modules/spells/spell_types/devil.dm
+++ b/code/modules/spells/spell_types/devil.dm
@@ -198,7 +198,7 @@
if(H.anti_magic_check(FALSE, TRUE))
continue
H.mind.add_antag_datum(/datum/antagonist/sintouched)
- H.Knockdown(400)
+ H.DefaultCombatKnockdown(400)
/obj/effect/proc_holder/spell/targeted/summon_dancefloor
diff --git a/code/modules/spells/spell_types/ethereal_jaunt.dm b/code/modules/spells/spell_types/ethereal_jaunt.dm
index a9d5f21abc..424a3b7671 100644
--- a/code/modules/spells/spell_types/ethereal_jaunt.dm
+++ b/code/modules/spells/spell_types/ethereal_jaunt.dm
@@ -40,7 +40,8 @@
return
mobloc = get_turf(target.loc)
jaunt_steam(mobloc)
- target.canmove = 0
+ ADD_TRAIT(target, TRAIT_MOBILITY_NOMOVE, src)
+ target.update_mobility()
holder.reappearing = 1
playsound(get_turf(target), 'sound/magic/ethereal_exit.ogg', 50, 1, -1)
sleep(25 - jaunt_in_time)
@@ -55,7 +56,8 @@
if(T)
if(target.Move(T))
break
- target.canmove = 1
+ REMOVE_TRAIT(target, TRAIT_MOBILITY_NOMOVE, src)
+ target.update_mobility()
/obj/effect/proc_holder/spell/targeted/ethereal_jaunt/proc/jaunt_steam(mobloc)
var/datum/effect_system/steam_spread/steam = new /datum/effect_system/steam_spread()
diff --git a/code/modules/spells/spell_types/godhand.dm b/code/modules/spells/spell_types/godhand.dm
index c4a2b4aa7e..fe53fd37e4 100644
--- a/code/modules/spells/spell_types/godhand.dm
+++ b/code/modules/spells/spell_types/godhand.dm
@@ -123,9 +123,9 @@
M.SetSleeping(0)
M.stuttering += 20*mul
M.adjustEarDamage(0, 30*mul)
- M.Knockdown(60*mul)
+ M.DefaultCombatKnockdown(60*mul)
if(prob(40))
- M.Knockdown(200*mul)
+ M.DefaultCombatKnockdown(200*mul)
else
M.Jitter(500*mul)
diff --git a/code/modules/spells/spell_types/inflict_handler.dm b/code/modules/spells/spell_types/inflict_handler.dm
index 7bc5ce34d3..5837caba24 100644
--- a/code/modules/spells/spell_types/inflict_handler.dm
+++ b/code/modules/spells/spell_types/inflict_handler.dm
@@ -46,7 +46,7 @@
if(!amt_knockdown && amt_dam_stam)
target.adjustStaminaLoss(amt_dam_stam)
else
- target.Knockdown(amt_knockdown, override_hardstun = amt_hardstun, override_stamdmg = amt_dam_stam)
+ target.DefaultCombatKnockdown(amt_knockdown, override_hardstun = amt_hardstun, override_stamdmg = amt_dam_stam)
target.Unconscious(amt_unconscious)
target.Stun(amt_stun)
diff --git a/code/modules/spells/spell_types/lichdom.dm b/code/modules/spells/spell_types/lichdom.dm
index 86597d5d2e..207ccd8374 100644
--- a/code/modules/spells/spell_types/lichdom.dm
+++ b/code/modules/spells/spell_types/lichdom.dm
@@ -135,7 +135,7 @@
lich.hardset_dna(null,null,lich.real_name,null, new /datum/species/skeleton/space)
to_chat(lich, "Your bones clatter and shudder as you are pulled back into this world!")
var/turf/body_turf = get_turf(old_body)
- lich.Knockdown(200 + 200*resurrections)
+ lich.DefaultCombatKnockdown(200 + 200*resurrections)
resurrections++
if(old_body && old_body.loc)
if(iscarbon(old_body))
diff --git a/code/modules/spells/spell_types/shadow_walk.dm b/code/modules/spells/spell_types/shadow_walk.dm
index b32c8c16c6..0b492cc6b0 100644
--- a/code/modules/spells/spell_types/shadow_walk.dm
+++ b/code/modules/spells/spell_types/shadow_walk.dm
@@ -25,8 +25,7 @@
if(light_amount < SHADOW_SPECIES_LIGHT_THRESHOLD)
playsound(get_turf(user), 'sound/magic/ethereal_enter.ogg', 50, 1, -1)
visible_message("[user] melts into the shadows!")
- user.SetStun(0, FALSE)
- user.SetKnockdown(0, FALSE)
+ user.SetAllImmobility(0)
user.setStaminaLoss(0, 0)
var/obj/effect/dummy/phased_mob/shadow/S2 = new(get_turf(user.loc))
user.forceMove(S2)
diff --git a/code/modules/spells/spell_types/wizard.dm b/code/modules/spells/spell_types/wizard.dm
index 44fdd1eb55..124159e910 100644
--- a/code/modules/spells/spell_types/wizard.dm
+++ b/code/modules/spells/spell_types/wizard.dm
@@ -297,14 +297,14 @@
if(distfromcaster == 0)
if(isliving(AM))
var/mob/living/M = AM
- M.Knockdown(100, override_hardstun = 20)
+ M.DefaultCombatKnockdown(100, override_hardstun = 20)
M.adjustBruteLoss(5)
to_chat(M, "You're slammed into the floor by [user]!")
else
new sparkle_path(get_turf(AM), get_dir(user, AM)) //created sparkles will disappear on their own
if(isliving(AM))
var/mob/living/M = AM
- M.Knockdown(stun_amt, override_hardstun = stun_amt * 0.2)
+ M.DefaultCombatKnockdown(stun_amt, override_hardstun = stun_amt * 0.2)
to_chat(M, "You're thrown back by [user]!")
AM.throw_at(throwtarget, ((CLAMP((maxthrow - (CLAMP(distfromcaster - 2, 0, distfromcaster))), 3, maxthrow))), 1,user)//So stuff gets tossed around at the same time.
safety--
diff --git a/code/modules/surgery/bodyparts/bodyparts.dm b/code/modules/surgery/bodyparts/bodyparts.dm
index c9affe92f9..bdea05decd 100644
--- a/code/modules/surgery/bodyparts/bodyparts.dm
+++ b/code/modules/surgery/bodyparts/bodyparts.dm
@@ -256,7 +256,7 @@
disabled = new_disabled
owner.update_health_hud() //update the healthdoll
owner.update_body()
- owner.update_canmove()
+ owner.update_mobility()
if(!disabled)
incoming_stam_mult = 1
return TRUE
diff --git a/code/modules/surgery/bodyparts/dismemberment.dm b/code/modules/surgery/bodyparts/dismemberment.dm
index 61811cdafc..8e47d6dbde 100644
--- a/code/modules/surgery/bodyparts/dismemberment.dm
+++ b/code/modules/surgery/bodyparts/dismemberment.dm
@@ -124,7 +124,7 @@
C.update_health_hud() //update the healthdoll
C.update_body()
C.update_hair()
- C.update_canmove()
+ C.update_mobility()
if(!Tsec) // Tsec = null happens when a "dummy human" used for rendering icons on prefs screen gets its limbs replaced.
qdel(src)
@@ -298,7 +298,7 @@
C.update_body()
C.update_hair()
C.update_damage_overlays()
- C.update_canmove()
+ C.update_mobility()
/obj/item/bodypart/head/attach_limb(mob/living/carbon/C, special)
diff --git a/code/modules/surgery/organs/augments_internal.dm b/code/modules/surgery/organs/augments_internal.dm
index 01cd4acbed..a678482ef3 100644
--- a/code/modules/surgery/organs/augments_internal.dm
+++ b/code/modules/surgery/organs/augments_internal.dm
@@ -105,11 +105,8 @@
..()
if(crit_fail || !(organ_flags & ORGAN_FAILING))
return
- owner.adjustStaminaLoss(-3.5) //Citadel edit, makes it more useful in Stamina based combat
- if(owner.AmountStun() > STUN_SET_AMOUNT)
- owner.SetStun(STUN_SET_AMOUNT)
- if(owner.AmountKnockdown() > STUN_SET_AMOUNT)
- owner.SetKnockdown(STUN_SET_AMOUNT)
+ owner.adjustStaminaLoss(-3.5, FALSE) //Citadel edit, makes it more useful in Stamina based combat
+ owner.HealAllImmobilityUpTo(STUN_SET_AMOUNT)
/obj/item/organ/cyberimp/brain/anti_stun/emp_act(severity)
. = ..()
diff --git a/code/modules/surgery/organs/vocal_cords.dm b/code/modules/surgery/organs/vocal_cords.dm
index c9596e3754..7c849dbd68 100644
--- a/code/modules/surgery/organs/vocal_cords.dm
+++ b/code/modules/surgery/organs/vocal_cords.dm
@@ -272,7 +272,7 @@
cooldown = COOLDOWN_STUN
for(var/V in listeners)
var/mob/living/L = V
- L.Knockdown(60 * power_multiplier)
+ L.DefaultCombatKnockdown(60 * power_multiplier)
//SLEEP
else if((findtext(message, sleep_words)))
@@ -492,10 +492,10 @@
for(var/V in listeners)
var/mob/living/L = V
if(L.resting)
- L.lay_down() //aka get up
- L.SetStun(0)
- L.SetKnockdown(0)
- L.SetUnconscious(0) //i said get up i don't care if you're being tased
+ L.set_resting(FALSE, FALSE, FALSE)
+ L.SetAllImmobility(0, FALSE)
+ L.SetUnconscious(0, FALSE) //i said get up i don't care if you're being tased
+ L.update_mobility()
//SIT
else if((findtext(message, sit_words)))
@@ -1205,7 +1205,7 @@
var/datum/status_effect/chem/enthrall/E = L.has_status_effect(/datum/status_effect/chem/enthrall)
switch(E.phase)
if(2 to INFINITY)
- L.Knockdown(30 * power_multiplier * E.phase)
+ L.DefaultCombatKnockdown(30 * power_multiplier * E.phase)
E.cooldown += 8
addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "You suddenly drop to the ground!"), 5)
to_chat(user, "You encourage [L] to drop down to the ground.")
@@ -1422,10 +1422,8 @@
var/datum/status_effect/chem/enthrall/E = L.has_status_effect(/datum/status_effect/chem/enthrall)
switch(E.phase)
if(3 to INFINITY)//Tier 3 only
- if(L.resting)
- L.lay_down() //aka get up
- L.SetStun(0)
- L.SetKnockdown(0)
+ L.set_resting(FALSE, TRUE, FALSE)
+ L.SetAllImmobility(0)
L.SetUnconscious(0) //i said get up i don't care if you're being tased
E.cooldown += 10 //This could be really strong
addtimer(CALLBACK(GLOBAL_PROC, .proc/to_chat, L, "You jump to your feet from sheer willpower!"), 5)
diff --git a/code/modules/tgui/states.dm b/code/modules/tgui/states.dm
index 959f096d05..b0808cef5e 100644
--- a/code/modules/tgui/states.dm
+++ b/code/modules/tgui/states.dm
@@ -70,7 +70,7 @@
return ..()
/mob/living/silicon/robot/shared_ui_interaction(src_object)
- if(!cell || cell.charge <= 0 || lockcharge) // Disable UIs if the Borg is unpowered or locked.
+ if(!cell || cell.charge <= 0 || locked_down) // Disable UIs if the Borg is unpowered or locked.
return UI_DISABLED
return ..()
diff --git a/code/modules/vehicles/cars/car.dm b/code/modules/vehicles/cars/car.dm
index d4437e17d5..dc6cccb9a9 100644
--- a/code/modules/vehicles/cars/car.dm
+++ b/code/modules/vehicles/cars/car.dm
@@ -29,8 +29,8 @@
last_enginesound_time = world.time
playsound(src, engine_sound, 100, TRUE)
-/obj/vehicle/sealed/car/MouseDrop_T(atom/dropping, mob/M)
- if(!M.canmove || M.stat || M.restrained())
+/obj/vehicle/sealed/car/MouseDrop_T(atom/dropping, mob/living/M)
+ if(!istype(M) || !CHECK_MOBILITY(M, MOBILITY_USE))
return FALSE
if(isliving(dropping) && M != dropping)
var/mob/living/L = dropping
diff --git a/code/modules/vehicles/cars/clowncar.dm b/code/modules/vehicles/cars/clowncar.dm
index 73ba785ec2..2b9890b863 100644
--- a/code/modules/vehicles/cars/clowncar.dm
+++ b/code/modules/vehicles/cars/clowncar.dm
@@ -52,7 +52,7 @@
var/mob/living/L = M
if(iscarbon(L))
var/mob/living/carbon/C = L
- C.Knockdown(40) //I play to make sprites go horizontal
+ C.DefaultCombatKnockdown(40) //I play to make sprites go horizontal
L.visible_message("[src] rams into [L] and sucks him up!") //fuck off shezza this isn't ERP.
mob_forced_enter(L)
playsound(src, pick('sound/vehicles/clowncar_ram1.ogg', 'sound/vehicles/clowncar_ram2.ogg', 'sound/vehicles/clowncar_ram3.ogg'), 75)
diff --git a/code/modules/vehicles/scooter.dm b/code/modules/vehicles/scooter.dm
index 0dd7ff32a8..cb53574653 100644
--- a/code/modules/vehicles/scooter.dm
+++ b/code/modules/vehicles/scooter.dm
@@ -71,7 +71,7 @@
var/atom/throw_target = get_edge_target_turf(H, pick(GLOB.cardinals))
unbuckle_mob(H)
H.throw_at(throw_target, 4, 3)
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
H.adjustStaminaLoss(40)
var/head_slot = H.get_item_by_slot(SLOT_HEAD)
if(!head_slot || !(istype(head_slot,/obj/item/clothing/head/helmet) || istype(head_slot,/obj/item/clothing/head/hardhat)))
@@ -199,7 +199,7 @@
var/atom/throw_target = get_edge_target_turf(H, pick(GLOB.cardinals))
unbuckle_mob(H)
H.throw_at(throw_target, 4, 3)
- H.Knockdown(30)
+ H.DefaultCombatKnockdown(30)
H.adjustStaminaLoss(10)
var/head_slot = H.get_item_by_slot(SLOT_HEAD)
if(!head_slot || !(istype(head_slot,/obj/item/clothing/head/helmet) || istype(head_slot,/obj/item/clothing/head/hardhat)))
diff --git a/code/modules/vehicles/sealed.dm b/code/modules/vehicles/sealed.dm
index 30ae49ecd2..fc81e2ec00 100644
--- a/code/modules/vehicles/sealed.dm
+++ b/code/modules/vehicles/sealed.dm
@@ -93,7 +93,7 @@
mob_exit(i, null, randomstep)
if(iscarbon(i))
var/mob/living/carbon/Carbon = i
- Carbon.Knockdown(40)
+ Carbon.DefaultCombatKnockdown(40)
/obj/vehicle/sealed/proc/DumpSpecificMobs(flag, randomstep = TRUE)
for(var/i in occupants)
@@ -101,7 +101,7 @@
mob_exit(i, null, randomstep)
if(iscarbon(i))
var/mob/living/carbon/C = i
- C.Knockdown(40)
+ C.DefaultCombatKnockdown(40)
/obj/vehicle/sealed/AllowDrop()
diff --git a/code/modules/vehicles/speedbike.dm b/code/modules/vehicles/speedbike.dm
index 6526e6d89a..a560cbb8f3 100644
--- a/code/modules/vehicles/speedbike.dm
+++ b/code/modules/vehicles/speedbike.dm
@@ -76,7 +76,7 @@
playsound(src, 'sound/effects/bang.ogg', 50, 1)
if(ishuman(A))
var/mob/living/carbon/human/H = A
- H.Knockdown(100)
+ H.DefaultCombatKnockdown(100)
H.adjustStaminaLoss(30)
H.apply_damage(rand(20,35), BRUTE)
if(!crash_all)
diff --git a/modular_citadel/code/datums/status_effects/chems.dm b/modular_citadel/code/datums/status_effects/chems.dm
index 82f4fbf1d9..e32d226595 100644
--- a/modular_citadel/code/datums/status_effects/chems.dm
+++ b/modular_citadel/code/datums/status_effects/chems.dm
@@ -543,7 +543,7 @@
if (statusStrength < 0)
status = null
owner.remove_movespeed_modifier(MOVESPEED_ID_MKULTRA)
- owner.Knockdown(50)
+ owner.DefaultCombatKnockdown(50)
to_chat(owner, "Your body gives out as the adrenaline in your system runs out.")
else
statusStrength -= 1
@@ -638,7 +638,7 @@
H.adjust_arousal(5)
C.jitteriness += 100
C.stuttering += 25
- C.Knockdown(60)
+ C.DefaultCombatKnockdown(60)
C.Stun(60)
to_chat(owner, "Your muscles seize up, then start spasming wildy!")
diff --git a/modular_citadel/code/datums/status_effects/debuffs.dm b/modular_citadel/code/datums/status_effects/debuffs.dm
deleted file mode 100644
index 6dcfc84a87..0000000000
--- a/modular_citadel/code/datums/status_effects/debuffs.dm
+++ /dev/null
@@ -1,18 +0,0 @@
-/datum/status_effect/incapacitating/knockdown/on_creation(mob/living/new_owner, set_duration, updating_canmove, override_duration, override_stam)
- if(iscarbon(new_owner) && (isnum(set_duration) || isnum(override_duration)))
- if(istype(new_owner.buckled, /obj/vehicle/ridden))
- var/obj/buckl = new_owner.buckled
- buckl.unbuckle_mob(new_owner)
- new_owner.resting = TRUE
- new_owner.adjustStaminaLoss(isnull(override_stam)? set_duration*0.25 : override_stam)
- if(isnull(override_duration) && (set_duration > 80))
- set_duration = set_duration*0.01
- return ..()
- else if(!isnull(override_duration))
- set_duration = override_duration
- return ..()
- else if(updating_canmove)
- new_owner.update_canmove()
- qdel(src)
- else
- . = ..()
diff --git a/modular_citadel/code/game/objects/cit_screenshake.dm b/modular_citadel/code/game/objects/cit_screenshake.dm
index 5bb1f82c10..ddb417e06e 100644
--- a/modular_citadel/code/game/objects/cit_screenshake.dm
+++ b/modular_citadel/code/game/objects/cit_screenshake.dm
@@ -53,7 +53,7 @@
if (1)
shake_camera(M, ((force - 10) * 0.015 + 1), ((force - 10) * 0.015))
if (2)
- if (!M.canmove)
+ if(!CHECK_MOBILITY(M, MOBILITY_MOVE))
shake_camera(M, ((force - 10) * 0.015 + 1), ((force - 10) * 0.015))
/obj/item/attack_obj(obj/O, mob/living/user)
diff --git a/modular_citadel/code/game/objects/items/devices/radio/shockcollar.dm b/modular_citadel/code/game/objects/items/devices/radio/shockcollar.dm
new file mode 100644
index 0000000000..44b8067876
--- /dev/null
+++ b/modular_citadel/code/game/objects/items/devices/radio/shockcollar.dm
@@ -0,0 +1,83 @@
+/obj/item/electropack/shockcollar
+ name = "shock collar"
+ desc = "A reinforced metal collar. It seems to have some form of wiring near the front. Strange.."
+ icon = 'modular_citadel/icons/obj/clothing/cit_neck.dmi'
+ alternate_worn_icon = 'modular_citadel/icons/mob/citadel/neck.dmi'
+ icon_state = "shockcollar"
+ item_state = "shockcollar"
+ body_parts_covered = NECK
+ slot_flags = ITEM_SLOT_NECK | ITEM_SLOT_DENYPOCKET //no more pocket shockers
+ w_class = WEIGHT_CLASS_SMALL
+ strip_delay = 60
+ equip_delay_other = 60
+ materials = list(MAT_METAL=5000, MAT_GLASS=2000)
+ var/tagname = null
+
+/datum/design/electropack/shockcollar
+ name = "Shockcollar"
+ id = "shockcollar"
+ build_type = AUTOLATHE
+ build_path = /obj/item/electropack/shockcollar
+ materials = list(MAT_METAL=5000, MAT_GLASS=2000)
+ category = list("hacked", "Misc")
+
+/obj/item/electropack/shockcollar/attack_hand(mob/user)
+ if(loc == user && user.get_item_by_slot(SLOT_NECK))
+ to_chat(user, "The collar is fastened tight! You'll need help taking this off!")
+ return
+ ..()
+
+/obj/item/electropack/shockcollar/receive_signal(datum/signal/signal)
+ if(!signal || signal.data["code"] != code)
+ return
+
+ if(isliving(loc) && on)
+ if(shock_cooldown != 0)
+ return
+ shock_cooldown = 1
+ spawn(100)
+ shock_cooldown = 0
+ var/mob/living/L = loc
+ step(L, pick(GLOB.cardinals))
+
+ to_chat(L, "You feel a sharp shock from the collar!")
+ var/datum/effect_system/spark_spread/s = new /datum/effect_system/spark_spread
+ s.set_up(3, 1, L)
+ s.start()
+
+ L.DefaultCombatKnockdown(100)
+
+ if(master)
+ master.receive_signal()
+ return
+
+/obj/item/electropack/shockcollar/attack_self(mob/user) //Turns out can't fully source this from the parent item, spritepath gets confused if power toggled. Will come back to this when I know how to code better and readd powertoggle..
+ var/option = "Change Name"
+ option = input(user, "What do you want to do?", "[src]", option) as null|anything in list("Change Name", "Change Frequency")
+ switch(option)
+ if("Change Name")
+ var/t = input(user, "Would you like to change the name on the tag?", "Name your new pet", tagname ? tagname : "Spot") as null|text
+ if(t)
+ tagname = copytext(sanitize(t), 1, MAX_NAME_LEN)
+ name = "[initial(name)] - [tagname]"
+ if("Change Frequency")
+ if(!ishuman(user))
+ return
+ user.set_machine(src)
+ var/dat = {"
+ Frequency/Code for shock collar:
+ Frequency:
+ -
+ - [format_frequency(frequency)]
+ +
+ +
+ Code:
+ -
+ - [code]
+ +
+ +
+ "}
+
+ user << browse(dat, "window=radio")
+ onclose(user, "radio")
+ return
diff --git a/modular_citadel/code/game/objects/structures/beds_chairs/chair.dm b/modular_citadel/code/game/objects/structures/beds_chairs/chair.dm
new file mode 100644
index 0000000000..5b20fe048b
--- /dev/null
+++ b/modular_citadel/code/game/objects/structures/beds_chairs/chair.dm
@@ -0,0 +1,21 @@
+/obj/structure/chair/alt_attack_hand(mob/living/user)
+ if(Adjacent(user) && istype(user))
+ if(!item_chair || !user.can_hold_items() || !has_buckled_mobs() || buckled_mobs.len > 1 || dir != user.dir || flags_1 & NODECONSTRUCT_1)
+ return TRUE
+ if(!user.canUseTopic(src, BE_CLOSE, ismonkey(user)))
+ to_chat(user, "You can't do that right now!")
+ return TRUE
+ if(user.getStaminaLoss() >= STAMINA_SOFTCRIT)
+ to_chat(user, "You're too exhausted for that.")
+ return TRUE
+ var/mob/living/poordude = buckled_mobs[1]
+ if(!istype(poordude))
+ return TRUE
+ user.visible_message("[user] pulls [src] out from under [poordude].", "You pull [src] out from under [poordude].")
+ var/C = new item_chair(loc)
+ user.put_in_hands(C)
+ poordude.DefaultCombatKnockdown(20)//rip in peace
+ user.adjustStaminaLoss(5)
+ unbuckle_all_mobs(TRUE)
+ qdel(src)
+ return TRUE
diff --git a/modular_citadel/code/modules/clothing/under/trek_under.dm b/modular_citadel/code/modules/clothing/under/trek_under.dm
index 683167f325..6cacf5921b 100644
--- a/modular_citadel/code/modules/clothing/under/trek_under.dm
+++ b/modular_citadel/code/modules/clothing/under/trek_under.dm
@@ -168,8 +168,9 @@
set category = "Object"
set src in usr
- if(!usr.canmove || usr.stat || usr.restrained())
- return 0
+ var/mob/living/L = usr
+ if(!istype(L) || !CHECK_MOBILITY(L, MOBILITY_USE))
+ return FALSE
switch(unbuttoned)
if(0)
diff --git a/modular_citadel/code/modules/mob/living/carbon/carbon.dm b/modular_citadel/code/modules/mob/living/carbon/carbon.dm
index 34ea0e789f..44512ac0c7 100644
--- a/modular_citadel/code/modules/mob/living/carbon/carbon.dm
+++ b/modular_citadel/code/modules/mob/living/carbon/carbon.dm
@@ -8,16 +8,6 @@
//oh no vore time
var/voremode = FALSE
-/mob/living/carbon/CanPass(atom/movable/mover, turf/target)
- . = ..()
- if(.)
- var/mob/living/mobdude = mover
- if(istype(mobdude))
- if(!resting && mobdude.resting)
- if(!(mobdude.pass_flags & PASSMOB))
- return FALSE
- return .
-
/mob/living/carbon/proc/toggle_combat_mode(forced, silent)
if(!forced)
if(recoveringstam || stat != CONSCIOUS)
diff --git a/modular_citadel/code/modules/mob/living/carbon/human/human.dm b/modular_citadel/code/modules/mob/living/carbon/human/human.dm
index e5d386b56b..ee88fcb277 100644
--- a/modular_citadel/code/modules/mob/living/carbon/human/human.dm
+++ b/modular_citadel/code/modules/mob/living/carbon/human/human.dm
@@ -4,7 +4,7 @@
/mob/living/carbon/human/resist_embedded()
if(handcuffed || legcuffed || (wear_suit && wear_suit.breakouttime))
return
- if(canmove && !on_fire)
+ if(CHECK_MOBILITY(src, MOBILITY_MOVE) && !on_fire)
for(var/obj/item/bodypart/L in bodyparts)
if(istype(L) && L.embedded_objects.len)
for(var/obj/item/I in L.embedded_objects)
@@ -25,4 +25,3 @@
if(!has_embedded_objects())
clear_alert("embeddedobject")
SEND_SIGNAL(user, COMSIG_CLEAR_MOOD_EVENT, "embedded")
- return
diff --git a/modular_citadel/code/modules/mob/living/carbon/human/human_movement.dm b/modular_citadel/code/modules/mob/living/carbon/human/human_movement.dm
index bd43d96ba4..2223b0816a 100644
--- a/modular_citadel/code/modules/mob/living/carbon/human/human_movement.dm
+++ b/modular_citadel/code/modules/mob/living/carbon/human/human_movement.dm
@@ -1,18 +1,18 @@
/mob/living/carbon/human/Move(NewLoc, direct)
var/oldpseudoheight = pseudo_z_axis
. = ..()
- if(. && sprinting && !(movement_type & FLYING) && canmove && !resting && m_intent == MOVE_INTENT_RUN && has_gravity(loc) && !pulledby)
+ if(. && sprinting && !(movement_type & FLYING) && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_MOVE|MOBILITY_STAND) && m_intent == MOVE_INTENT_RUN && has_gravity(loc) && !pulledby)
if(!HAS_TRAIT(src, TRAIT_FREESPRINT))
doSprintLossTiles(1)
if((oldpseudoheight - pseudo_z_axis) >= 8)
to_chat(src, "You trip off of the elevated surface!")
for(var/obj/item/I in held_items)
accident(I)
- Knockdown(80)
+ DefaultCombatKnockdown(80)
/mob/living/carbon/human/movement_delay()
. = 0
- if(!resting && m_intent == MOVE_INTENT_RUN && sprinting)
+ if((mobility_flags & MOBILITY_STAND) && m_intent == MOVE_INTENT_RUN && sprinting)
var/static/datum/config_entry/number/movedelay/sprint_speed_increase/SSI
if(!SSI)
SSI = CONFIG_GET_ENTRY(number/movedelay/sprint_speed_increase)
@@ -23,7 +23,7 @@
/mob/living/carbon/human/proc/togglesprint() // If you call this proc outside of hotkeys or clicking the HUD button, I'll be disappointed in you.
sprinting = !sprinting
- if(!resting && m_intent == MOVE_INTENT_RUN && canmove)
+ if((m_intent == MOVE_INTENT_RUN) && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE))
if(sprinting)
playsound_local(src, 'sound/misc/sprintactivate.ogg', 50, FALSE, pressure_affected = FALSE)
else
diff --git a/modular_citadel/code/modules/mob/living/living.dm b/modular_citadel/code/modules/mob/living/living.dm
index 0caf548196..c0e045365f 100644
--- a/modular_citadel/code/modules/mob/living/living.dm
+++ b/modular_citadel/code/modules/mob/living/living.dm
@@ -25,7 +25,7 @@
/mob/living/movement_delay(ignorewalk = 0)
. = ..()
- if(resting)
+ if(!CHECK_MOBILITY(src, MOBILITY_STAND))
. += 6
/atom
@@ -53,85 +53,22 @@
pseudo_z_axis = newloc.get_fake_z()
pixel_z = pseudo_z_axis
-/mob/living/proc/lay_down()
- set name = "Rest"
- set category = "IC"
-
- if(client && client.prefs && client.prefs.autostand)
- intentionalresting = !intentionalresting
- to_chat(src, "You are now attempting to [intentionalresting ? "[!resting ? "lay down and ": ""]stay down" : "[resting ? "get up and ": ""]stay up"].")
- if(intentionalresting && !resting)
- resting = TRUE
- update_canmove()
- else
- resist_a_rest()
- else
- if(!resting)
- resting = TRUE
- to_chat(src, "You are now laying down.")
- update_canmove()
- else
- resist_a_rest()
-
-/mob/living/proc/resist_a_rest(automatic = FALSE, ignoretimer = FALSE) //Lets mobs resist out of resting. Major QOL change with combat reworks.
- if(!resting || stat || attemptingstandup)
- return FALSE
- if(ignoretimer)
- resting = FALSE
- update_canmove()
- return TRUE
- else
- var/totaldelay = 3 //A little bit less than half of a second as a baseline for getting up from a rest
- if(getStaminaLoss() >= STAMINA_SOFTCRIT)
- to_chat(src, "You're too exhausted to get up!")
- return FALSE
- attemptingstandup = TRUE
- var/health_deficiency = max((maxHealth - (health - getStaminaLoss()))*0.5, 0)
- if(!has_gravity())
- health_deficiency = health_deficiency*0.2
- totaldelay += health_deficiency
- var/standupwarning = "[src] and everyone around them should probably yell at the dev team"
- switch(health_deficiency)
- if(-INFINITY to 10)
- standupwarning = "[src] stands right up!"
- if(10 to 35)
- standupwarning = "[src] tries to stand up."
- if(35 to 60)
- standupwarning = "[src] slowly pushes [p_them()]self upright."
- if(60 to 80)
- standupwarning = "[src] weakly attempts to stand up."
- if(80 to INFINITY)
- standupwarning = "[src] struggles to stand up."
- var/usernotice = automatic ? "You are now getting up. (Auto)" : "You are now getting up."
- visible_message("[standupwarning]", usernotice, vision_distance = 5)
- if(do_after(src, totaldelay, target = src))
- resting = FALSE
- attemptingstandup = FALSE
- update_canmove()
- return TRUE
- else
- visible_message("[src] falls right back down.", "You fall right back down.")
- attemptingstandup = FALSE
- if(has_gravity())
- playsound(src, "bodyfall", 20, 1)
- return FALSE
-
/mob/living/carbon/update_stamina()
var/total_health = getStaminaLoss()
if(total_health)
if(!recoveringstam && total_health >= STAMINA_CRIT && !stat)
to_chat(src, "You're too exhausted to keep going...")
- resting = TRUE
+ set_resting(TRUE, FALSE, FALSE)
if(combatmode)
toggle_combat_mode(TRUE)
recoveringstam = TRUE
filters += CIT_FILTER_STAMINACRIT
- update_canmove()
+ update_mobility()
if(recoveringstam && total_health <= STAMINA_SOFTCRIT)
to_chat(src, "You don't feel nearly as exhausted anymore.")
recoveringstam = FALSE
filters -= CIT_FILTER_STAMINACRIT
- update_canmove()
+ update_mobility()
update_health_hud()
/mob/living/proc/update_hud_sprint_bar()
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 c2b8ff0868..6d080ee898 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
@@ -54,8 +54,8 @@ SLEEPER CODE IS IN game/objects/items/devices/dogborg_sleeper.dm !
var/mob/living/M = A
var/cachedstam = M.getStaminaLoss()
var/totalstuntime = cachedstam * stamtostunconversion * (M.lying ? 2 : 1)
- if(!M.resting)
- M.Knockdown(cachedstam*2) //BORK BORK. GET DOWN.
+ if(CHECK_MOBILITY(M, MOBILITY_STAND))
+ M.DefaultCombatKnockdown(cachedstam*2) //BORK BORK. GET DOWN.
M.Stun(totalstuntime)
user.do_attack_animation(A, ATTACK_EFFECT_BITE)
user.start_pulling(M, TRUE) //Yip yip. Come with.
@@ -284,7 +284,7 @@ SLEEPER CODE IS IN game/objects/items/devices/dogborg_sleeper.dm !
to_chat(R, "Insufficent Power!")
return
L.Stun(4) // normal stunbaton is force 7 gimme a break good sir!
- L.Knockdown(80)
+ L.DefaultCombatKnockdown(80)
L.apply_effect(EFFECT_STUTTER, 4)
L.visible_message("[R] has shocked [L] with its tongue!", \
"[R] has shocked you with its tongue!")
@@ -426,13 +426,13 @@ SLEEPER CODE IS IN game/objects/items/devices/dogborg_sleeper.dm !
var/mob/living/L = hit_atom
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.
+ L.DefaultCombatKnockdown(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)
sleep(2)//Runtime prevention (infinite bump() calls on hulks)
step_towards(src,L)
log_combat(src, L, "borg pounced")
else
- Knockdown(15, 1, 1)
+ DefaultCombatKnockdown(15, 1, 1)
pounce_cooldown = !pounce_cooldown
spawn(pounce_cooldown_time) //3s by default
@@ -440,10 +440,10 @@ SLEEPER CODE IS IN game/objects/items/devices/dogborg_sleeper.dm !
else if(hit_atom.density && !hit_atom.CanPass(src))
visible_message("[src] smashes into [hit_atom]!", "You smash into [hit_atom]!")
playsound(src, 'sound/items/trayhit1.ogg', 50, 1)
- Knockdown(15, 1, 1)
+ DefaultCombatKnockdown(15, 1, 1)
if(leaping)
leaping = 0
pixel_y = initial(pixel_y)
update_icons()
- update_canmove()
+ update_mobility()
diff --git a/modular_citadel/code/modules/mob/living/silicon/robot/robot_movement.dm b/modular_citadel/code/modules/mob/living/silicon/robot/robot_movement.dm
index 3f88513372..526ea497c4 100644
--- a/modular_citadel/code/modules/mob/living/silicon/robot/robot_movement.dm
+++ b/modular_citadel/code/modules/mob/living/silicon/robot/robot_movement.dm
@@ -1,6 +1,6 @@
/mob/living/silicon/robot/Move(NewLoc, direct)
. = ..()
- if(. && sprinting && !(movement_type & FLYING) && canmove && !resting)
+ if(. && sprinting && !(movement_type & FLYING) && CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND | MOBILITY_MOVE))
if(!(cell?.use(25)))
togglesprint(TRUE)
@@ -14,7 +14,7 @@
if(!shutdown && (!cell || cell.charge < 25) || !cansprint)
return FALSE
sprinting = shutdown ? FALSE : !sprinting
- if(!resting && canmove)
+ if(CHECK_MULTIPLE_BITFIELDS(mobility_flags, MOBILITY_STAND|MOBILITY_MOVE))
if(sprinting)
playsound_local(src, 'sound/misc/sprintactivate.ogg', 50, FALSE, pressure_affected = FALSE)
else
diff --git a/modular_citadel/code/modules/reagents/chemistry/reagents/eigentstasium.dm b/modular_citadel/code/modules/reagents/chemistry/reagents/eigentstasium.dm
index 6262dc1a28..1ea4b956f7 100644
--- a/modular_citadel/code/modules/reagents/chemistry/reagents/eigentstasium.dm
+++ b/modular_citadel/code/modules/reagents/chemistry/reagents/eigentstasium.dm
@@ -100,7 +100,7 @@
if(addiction_stage == 11)
to_chat(M, "You start to convlse violently as you feel your consciousness split and merge across realities as your possessions fly wildy off your body.")
M.Jitter(200)
- M.Knockdown(200)
+ M.DefaultCombatKnockdown(200)
M.Stun(80)
var/items = M.get_contents()
if(!LAZYLEN(items))
@@ -154,7 +154,7 @@
do_sparks(5,FALSE,M)
M.Sleeping(100, 0)
M.Jitter(50)
- M.Knockdown(100)
+ M.DefaultCombatKnockdown(100)
to_chat(M, "You feel your eigenstate settle, snapping an alternative version of yourself into reality. All your previous memories are lost and replaced with the alternative version of yourself. This version of you feels more [pick("affectionate", "happy", "lusty", "radical", "shy", "ambitious", "frank", "voracious", "sensible", "witty")] than your previous self, sent to god knows what universe.")
M.emote("me",1,"flashes into reality suddenly, gasping as they gaze around in a bewildered and highly confused fashion!",TRUE)
log_game("FERMICHEM: [M] ckey: [M.key] has become an alternative universe version of themselves.")
diff --git a/modular_citadel/code/modules/reagents/chemistry/reagents/enlargement.dm b/modular_citadel/code/modules/reagents/chemistry/reagents/enlargement.dm
index b6b9c0bf34..c173d3775b 100644
--- a/modular_citadel/code/modules/reagents/chemistry/reagents/enlargement.dm
+++ b/modular_citadel/code/modules/reagents/chemistry/reagents/enlargement.dm
@@ -40,7 +40,7 @@
M.visible_message("A pair of breasts suddenly fly out of the [M]!")
var/T2 = get_random_station_turf()
M.adjustBruteLoss(25)
- M.Knockdown(50)
+ M.DefaultCombatKnockdown(50)
M.Stun(50)
B.throw_at(T2, 8, 1)
M.reagents.del_reagent(type)
@@ -196,7 +196,7 @@
M.visible_message("A penis suddenly flies out of the [M]!")
var/T2 = get_random_station_turf()
M.adjustBruteLoss(25)
- M.Knockdown(50)
+ M.DefaultCombatKnockdown(50)
M.Stun(50)
P.throw_at(T2, 8, 1)
M.reagents.del_reagent(type)
diff --git a/modular_citadel/code/modules/reagents/chemistry/reagents/fermi_reagents.dm b/modular_citadel/code/modules/reagents/chemistry/reagents/fermi_reagents.dm
index fb5574855e..a7dbe8d799 100644
--- a/modular_citadel/code/modules/reagents/chemistry/reagents/fermi_reagents.dm
+++ b/modular_citadel/code/modules/reagents/chemistry/reagents/fermi_reagents.dm
@@ -93,7 +93,7 @@
if(method == INJECT)
var/turf/T = get_turf(M)
M.adjustOxyLoss(15)
- M.Knockdown(50)
+ M.DefaultCombatKnockdown(50)
M.Stun(50)
M.emote("cough")
var/obj/item/toy/plush/P = pick(subtypesof(/obj/item/toy/plush))
diff --git a/tgstation.dme b/tgstation.dme
index 7f139d2ae9..ef0c1dc06a 100755
--- a/tgstation.dme
+++ b/tgstation.dme
@@ -578,6 +578,7 @@
#include "code\game\alternate_appearance.dm"
#include "code\game\atoms.dm"
#include "code\game\atoms_movable.dm"
+#include "code\game\atoms_movement.dm"
#include "code\game\communications.dm"
#include "code\game\data_huds.dm"
#include "code\game\say.dm"
@@ -2156,6 +2157,7 @@
#include "code\modules\mob\living\living.dm"
#include "code\modules\mob\living\living_defense.dm"
#include "code\modules\mob\living\living_defines.dm"
+#include "code\modules\mob\living\living_mobility.dm"
#include "code\modules\mob\living\living_movement.dm"
#include "code\modules\mob\living\login.dm"
#include "code\modules\mob\living\logout.dm"
@@ -2229,6 +2231,7 @@
#include "code\modules\mob\living\carbon\human\human_defense.dm"
#include "code\modules\mob\living\carbon\human\human_defines.dm"
#include "code\modules\mob\living\carbon\human\human_helpers.dm"
+#include "code\modules\mob\living\carbon\human\human_mobility.dm"
#include "code\modules\mob\living\carbon\human\human_movement.dm"
#include "code\modules\mob\living\carbon\human\inventory.dm"
#include "code\modules\mob\living\carbon\human\life.dm"
@@ -2310,9 +2313,11 @@
#include "code\modules\mob\living\silicon\robot\login.dm"
#include "code\modules\mob\living\silicon\robot\robot.dm"
#include "code\modules\mob\living\silicon\robot\robot_defense.dm"
+#include "code\modules\mob\living\silicon\robot\robot_mobility.dm"
#include "code\modules\mob\living\silicon\robot\robot_modules.dm"
#include "code\modules\mob\living\silicon\robot\robot_movement.dm"
#include "code\modules\mob\living\silicon\robot\say.dm"
+#include "code\modules\mob\living\silicon\robot\update_icons.dm"
#include "code\modules\mob\living\simple_animal\animal_defense.dm"
#include "code\modules\mob\living\simple_animal\astral.dm"
#include "code\modules\mob\living\simple_animal\constructs.dm"
@@ -2447,6 +2452,7 @@
#include "code\modules\mob\living\simple_animal\slime\powers.dm"
#include "code\modules\mob\living\simple_animal\slime\say.dm"
#include "code\modules\mob\living\simple_animal\slime\slime.dm"
+#include "code\modules\mob\living\simple_animal\slime\slime_mobility.dm"
#include "code\modules\mob\living\simple_animal\slime\subtypes.dm"
#include "code\modules\modular_computers\laptop_vendor.dm"
#include "code\modules\modular_computers\computers\item\computer.dm"
@@ -3158,7 +3164,6 @@
#include "modular_citadel\code\_onclick\hud\stamina.dm"
#include "modular_citadel\code\datums\components\souldeath.dm"
#include "modular_citadel\code\datums\status_effects\chems.dm"
-#include "modular_citadel\code\datums\status_effects\debuffs.dm"
#include "modular_citadel\code\game\machinery\wishgranter.dm"
#include "modular_citadel\code\game\objects\cit_screenshake.dm"
#include "modular_citadel\code\game\objects\effects\temporary_visuals\souldeath.dm"