mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2026-08-26 22:50:26 +01:00
Mobility refactor: UI, pull and lying down edition (#54078)
This commit is contained in:
@@ -515,3 +515,6 @@ GLOBAL_LIST_INIT(pda_styles, sortList(list(MONO, VT, ORBITRON, SHARE)))
|
||||
#define ANON_DISABLED "" //so it's falsey
|
||||
#define ANON_RANDOMNAMES "Random Default"
|
||||
#define ANON_EMPLOYEENAMES "Employees"
|
||||
|
||||
/// Possible value of [/atom/movable/buckle_lying]. If set to a different (positive-or-zero) value than this, the buckling thing will force a lying angle on the buckled.
|
||||
#define NO_BUCKLE_LYING -1
|
||||
|
||||
@@ -209,6 +209,10 @@
|
||||
#define SENTIENCE_BOSS 5
|
||||
|
||||
//Mob AI Status
|
||||
#define POWER_RESTORATION_OFF 0
|
||||
#define POWER_RESTORATION_START 1
|
||||
#define POWER_RESTORATION_SEARCH_APC 2
|
||||
#define POWER_RESTORATION_APC_FOUND 3
|
||||
|
||||
//Hostile simple animals
|
||||
//If you add a new status, be sure to add a list for it to the simple_animals global in _globalvars/lists/mobs.dm
|
||||
|
||||
@@ -81,6 +81,10 @@ Remember to update _globalvars/traits.dm if you're adding/removing/renaming trai
|
||||
#define TRAIT_FLOORED "floored" //Prevents standing or staying up on its own.
|
||||
/// Prevents usage of manipulation appendages (picking, holding or using items, manipulating storage).
|
||||
#define TRAIT_HANDS_BLOCKED "handsblocked"
|
||||
/// Inability to access UI hud elements. Turned into a trait from [MOBILITY_UI] to be able to track sources.
|
||||
#define TRAIT_UI_BLOCKED "uiblocked"
|
||||
/// Inability to pull things. Turned into a trait from [MOBILITY_PULL] to be able to track sources.
|
||||
#define TRAIT_PULL_BLOCKED "pullblocked"
|
||||
/// Abstract condition that prevents movement if being pulled and might be resisted against. Handcuffs and straight jackets, basically.
|
||||
#define TRAIT_RESTRAINED "restrained"
|
||||
#define TRAIT_INCAPACITATED "incapacitated"
|
||||
@@ -292,6 +296,10 @@ Remember to update _globalvars/traits.dm if you're adding/removing/renaming trai
|
||||
#define MAPPING_HELPER_TRAIT "mapping-helper" //obtained from mapping helper
|
||||
/// Trait associated to wearing a suit
|
||||
#define SUIT_TRAIT "suit"
|
||||
/// Trait associated to lying down (having a [lying_angle] of a different value than zero).
|
||||
#define LYING_DOWN_TRAIT "lying-down"
|
||||
/// Trait associated to lacking electrical power.
|
||||
#define POWER_LACK_TRAIT "power-lack"
|
||||
|
||||
// unique trait sources, still defines
|
||||
#define CLONING_POD_TRAIT "cloning-pod"
|
||||
|
||||
@@ -230,6 +230,7 @@
|
||||
if(!.)
|
||||
return
|
||||
ADD_TRAIT(owner, TRAIT_IMMOBILIZED, TRAIT_STATUS_EFFECT(id))
|
||||
ADD_TRAIT(owner, TRAIT_HANDS_BLOCKED, TRAIT_STATUS_EFFECT(id))
|
||||
owner.update_mobility()
|
||||
|
||||
/datum/status_effect/grouped/stasis/tick()
|
||||
@@ -237,6 +238,7 @@
|
||||
|
||||
/datum/status_effect/grouped/stasis/on_remove()
|
||||
REMOVE_TRAIT(owner, TRAIT_IMMOBILIZED, TRAIT_STATUS_EFFECT(id))
|
||||
REMOVE_TRAIT(owner, TRAIT_HANDS_BLOCKED, TRAIT_STATUS_EFFECT(id))
|
||||
owner.update_mobility()
|
||||
update_time_of_death()
|
||||
return ..()
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
/atom/movable
|
||||
var/can_buckle = FALSE
|
||||
var/buckle_lying = -1 //bed-like behaviour, forces mob.lying = buckle_lying if != -1
|
||||
/// Bed-like behaviour, forces mob.lying = buckle_lying if not set to [NO_BUCKLE_LYING].
|
||||
var/buckle_lying = NO_BUCKLE_LYING
|
||||
var/buckle_requires_restraints = FALSE //require people to be handcuffed before being able to buckle. eg: pipes
|
||||
var/list/mob/living/buckled_mobs = null //list()
|
||||
var/max_buckled_mobs = 1
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
anchored = FALSE
|
||||
density = TRUE
|
||||
max_integrity = 100
|
||||
buckle_lying = FALSE
|
||||
buckle_lying = 0
|
||||
layer = ABOVE_MOB_LAYER
|
||||
var/view_range = 2.5
|
||||
var/cooldown = 0
|
||||
|
||||
@@ -552,7 +552,7 @@
|
||||
smoothing_groups = null
|
||||
canSmoothWith = null
|
||||
can_buckle = 1
|
||||
buckle_lying = -1
|
||||
buckle_lying = NO_BUCKLE_LYING
|
||||
buckle_requires_restraints = TRUE
|
||||
var/mob/living/carbon/human/patient = null
|
||||
var/obj/machinery/computer/operating/computer = null
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
flags_1 = CONDUCT_1
|
||||
can_buckle = TRUE
|
||||
max_buckled_mobs = 1
|
||||
buckle_lying = FALSE
|
||||
buckle_lying = 0
|
||||
var/obj/item/target/pinned_target
|
||||
|
||||
/obj/structure/target_stake/Destroy()
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
var/minimum_temperature_difference = 20
|
||||
var/thermal_conductivity = WINDOW_HEAT_TRANSFER_COEFFICIENT
|
||||
color = "#404040"
|
||||
buckle_lying = -1
|
||||
buckle_lying = NO_BUCKLE_LYING
|
||||
var/icon_temperature = T20C //stop small changes in temperature causing icon refresh
|
||||
resistance_flags = LAVA_PROOF | FIRE_PROOF
|
||||
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
//Buckling
|
||||
can_buckle = TRUE
|
||||
buckle_requires_restraints = TRUE
|
||||
buckle_lying = -1
|
||||
buckle_lying = NO_BUCKLE_LYING
|
||||
|
||||
/obj/machinery/atmospherics/pipe/New()
|
||||
add_atom_colour(pipe_color, FIXED_COLOUR_PRIORITY)
|
||||
|
||||
@@ -542,12 +542,17 @@
|
||||
if(dna)
|
||||
dna.real_name = real_name
|
||||
|
||||
/mob/living/carbon/update_mobility()
|
||||
|
||||
/mob/living/carbon/set_lying_angle(new_lying)
|
||||
. = ..()
|
||||
if(!(mobility_flags & MOBILITY_STAND))
|
||||
add_movespeed_modifier(/datum/movespeed_modifier/carbon_crawling)
|
||||
else
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/carbon_crawling)
|
||||
if(isnull(.))
|
||||
return
|
||||
switch(lying_angle)
|
||||
if(90, 270)
|
||||
add_movespeed_modifier(/datum/movespeed_modifier/carbon_crawling)
|
||||
else
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/carbon_crawling)
|
||||
|
||||
|
||||
//Updates the mob's health from bodyparts and mob damage variables
|
||||
/mob/living/carbon/updatehealth()
|
||||
@@ -1281,7 +1286,5 @@
|
||||
if(.)
|
||||
if(!handcuffed)
|
||||
REMOVE_TRAIT(src, TRAIT_RESTRAINED, HANDCUFFED_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_HANDS_BLOCKED, HANDCUFFED_TRAIT)
|
||||
else if(handcuffed)
|
||||
ADD_TRAIT(src, TRAIT_RESTRAINED, HANDCUFFED_TRAIT)
|
||||
ADD_TRAIT(src, TRAIT_HANDS_BLOCKED, HANDCUFFED_TRAIT)
|
||||
|
||||
@@ -64,11 +64,22 @@
|
||||
. = ..()
|
||||
if(isnull(.))
|
||||
return
|
||||
if(. & !(FLYING | FLOATING))
|
||||
if(!(. & (FLYING | FLOATING)))
|
||||
if(movement_type & (FLYING | FLOATING)) //From not flying to flying.
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/limbless)
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
else if(!(movement_type & (FLYING | FLOATING)) && !usable_legs) //From flying to no longer flying.
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
if(!usable_hands)
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
else if(!(movement_type & (FLYING | FLOATING))) //From flying to no longer flying.
|
||||
var/limbless_slowdown = 0
|
||||
if(usable_legs < default_num_legs)
|
||||
limbless_slowdown += (default_num_legs - usable_legs) * 3
|
||||
if(!usable_legs)
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
if(usable_hands < default_num_hands)
|
||||
limbless_slowdown += (default_num_hands - usable_hands) * 3
|
||||
if(!usable_hands)
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
if(limbless_slowdown)
|
||||
add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/limbless, multiplicative_slowdown = limbless_slowdown)
|
||||
else
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/limbless)
|
||||
|
||||
@@ -149,7 +149,6 @@
|
||||
update_inv_w_uniform()
|
||||
if(wear_suit.breakouttime) //when equipping a straightjacket
|
||||
ADD_TRAIT(src, TRAIT_RESTRAINED, SUIT_TRAIT)
|
||||
ADD_TRAIT(src, TRAIT_HANDS_BLOCKED, SUIT_TRAIT)
|
||||
stop_pulling() //can't pull if restrained
|
||||
update_action_buttons_icon() //certain action buttons will no longer be usable.
|
||||
update_inv_wear_suit()
|
||||
@@ -206,7 +205,6 @@
|
||||
dropItemToGround(s_store, TRUE) //It makes no sense for your suit storage to stay on you if you drop your suit.
|
||||
if(wear_suit.breakouttime) //when unequipping a straightjacket
|
||||
REMOVE_TRAIT(src, TRAIT_RESTRAINED, SUIT_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_HANDS_BLOCKED, SUIT_TRAIT)
|
||||
drop_all_held_items() //suit is restraining
|
||||
update_action_buttons_icon() //certain action buttons may be usable again.
|
||||
wear_suit = null
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
///Called on /mob/living/Initialize(), for the mob to register to relevant signals.
|
||||
/// Called on [/mob/living/Initialize()], for the mob to register to relevant signals.
|
||||
/mob/living/proc/register_init_signals()
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_KNOCKEDOUT), .proc/on_knockedout_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_KNOCKEDOUT), .proc/on_knockedout_trait_loss)
|
||||
@@ -9,9 +9,24 @@
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_IMMOBILIZED), .proc/on_immobilized_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_IMMOBILIZED), .proc/on_immobilized_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_FLOORED), .proc/on_floored_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_FLOORED), .proc/on_floored_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_HANDS_BLOCKED), .proc/on_handsblocked_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_HANDS_BLOCKED), .proc/on_handsblocked_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_UI_BLOCKED), .proc/on_ui_blocked_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_UI_BLOCKED), .proc/on_ui_blocked_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_PULL_BLOCKED), .proc/on_pull_blocked_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_PULL_BLOCKED), .proc/on_pull_blocked_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_INCAPACITATED), .proc/on_incapacitated_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_INCAPACITATED), .proc/on_incapacitated_trait_loss)
|
||||
|
||||
RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_RESTRAINED), .proc/on_restrained_trait_gain)
|
||||
RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_RESTRAINED), .proc/on_restrained_trait_loss)
|
||||
|
||||
RegisterSignal(src, list(
|
||||
SIGNAL_ADDTRAIT(TRAIT_CRITICAL_CONDITION),
|
||||
SIGNAL_REMOVETRAIT(TRAIT_CRITICAL_CONDITION),
|
||||
@@ -21,48 +36,132 @@
|
||||
), .proc/update_succumb_action)
|
||||
|
||||
|
||||
///Called when TRAIT_KNOCKEDOUT is added to the mob.
|
||||
/// Called when [TRAIT_KNOCKEDOUT] is added to the mob.
|
||||
/mob/living/proc/on_knockedout_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
if(stat < UNCONSCIOUS)
|
||||
set_stat(UNCONSCIOUS)
|
||||
|
||||
///Called when TRAIT_KNOCKEDOUT is removed from the mob.
|
||||
/// Called when [TRAIT_KNOCKEDOUT] is removed from the mob.
|
||||
/mob/living/proc/on_knockedout_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
if(stat <= UNCONSCIOUS)
|
||||
update_stat()
|
||||
|
||||
|
||||
///Called when TRAIT_DEATHCOMA is added to the mob.
|
||||
/// Called when [TRAIT_DEATHCOMA] is added to the mob.
|
||||
/mob/living/proc/on_deathcoma_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
ADD_TRAIT(src, TRAIT_KNOCKEDOUT, TRAIT_DEATHCOMA)
|
||||
|
||||
///Called when TRAIT_DEATHCOMA is removed from the mob.
|
||||
/// Called when [TRAIT_DEATHCOMA] is removed from the mob.
|
||||
/mob/living/proc/on_deathcoma_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
REMOVE_TRAIT(src, TRAIT_KNOCKEDOUT, TRAIT_DEATHCOMA)
|
||||
|
||||
|
||||
///Called when TRAIT_IMMOBILIZED is added to the mob.
|
||||
/// Called when [TRAIT_IMMOBILIZED] is added to the mob.
|
||||
/mob/living/proc/on_immobilized_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags &= ~MOBILITY_MOVE
|
||||
|
||||
///Called when TRAIT_IMMOBILIZED is removed from the mob.
|
||||
/// Called when [TRAIT_IMMOBILIZED] is removed from the mob.
|
||||
/mob/living/proc/on_immobilized_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags |= MOBILITY_MOVE
|
||||
|
||||
|
||||
///Called when TRAIT_HANDS_BLOCKED is added to the mob.
|
||||
/// Called when [TRAIT_FLOORED] is added to the mob.
|
||||
/mob/living/proc/on_floored_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
if(buckled && buckled.buckle_lying != NO_BUCKLE_LYING)
|
||||
return // Handled by the buckle.
|
||||
mobility_flags &= ~MOBILITY_STAND
|
||||
if(lying_angle == 0) //force them on the ground
|
||||
set_lying_angle(pick(90, 270))
|
||||
on_fall()
|
||||
|
||||
|
||||
/// Called when [TRAIT_FLOORED] is removed from the mob.
|
||||
/mob/living/proc/on_floored_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags |= MOBILITY_STAND
|
||||
if(!resting)
|
||||
get_up()
|
||||
|
||||
|
||||
/// Called when [TRAIT_HANDS_BLOCKED] is added to the mob.
|
||||
/mob/living/proc/on_handsblocked_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags &= ~(MOBILITY_USE | MOBILITY_PICKUP | MOBILITY_STORAGE)
|
||||
drop_all_held_items()
|
||||
ADD_TRAIT(src, TRAIT_UI_BLOCKED, TRAIT_HANDS_BLOCKED)
|
||||
ADD_TRAIT(src, TRAIT_PULL_BLOCKED, TRAIT_HANDS_BLOCKED)
|
||||
|
||||
///Called when TRAIT_HANDS_BLOCKED is removed from the mob.
|
||||
/// Called when [TRAIT_HANDS_BLOCKED] is removed from the mob.
|
||||
/mob/living/proc/on_handsblocked_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags |= (MOBILITY_USE | MOBILITY_PICKUP | MOBILITY_STORAGE)
|
||||
REMOVE_TRAIT(src, TRAIT_UI_BLOCKED, TRAIT_HANDS_BLOCKED)
|
||||
REMOVE_TRAIT(src, TRAIT_PULL_BLOCKED, TRAIT_HANDS_BLOCKED)
|
||||
|
||||
|
||||
/// Called when traits that alter succumbing are added/removed.
|
||||
/// Will show or hide the succumb alert prompt.
|
||||
/// Called when [TRAIT_UI_BLOCKED] is added to the mob.
|
||||
/mob/living/proc/on_ui_blocked_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags &= ~(MOBILITY_UI)
|
||||
unset_machine()
|
||||
|
||||
/// Called when [TRAIT_UI_BLOCKED] is removed from the mob.
|
||||
/mob/living/proc/on_ui_blocked_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags |= MOBILITY_UI
|
||||
|
||||
|
||||
/// Called when [TRAIT_PULL_BLOCKED] is added to the mob.
|
||||
/mob/living/proc/on_pull_blocked_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags &= ~(MOBILITY_PULL)
|
||||
if(pulling)
|
||||
stop_pulling()
|
||||
|
||||
/// Called when [TRAIT_PULL_BLOCKED] is removed from the mob.
|
||||
/mob/living/proc/on_pull_blocked_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
mobility_flags |= MOBILITY_PULL
|
||||
|
||||
|
||||
/// Called when [TRAIT_INCAPACITATED] is added to the mob.
|
||||
/mob/living/proc/on_incapacitated_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
ADD_TRAIT(src, TRAIT_UI_BLOCKED, TRAIT_INCAPACITATED)
|
||||
ADD_TRAIT(src, TRAIT_PULL_BLOCKED, TRAIT_INCAPACITATED)
|
||||
|
||||
/// Called when [TRAIT_INCAPACITATED] is removed from the mob.
|
||||
/mob/living/proc/on_incapacitated_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
REMOVE_TRAIT(src, TRAIT_UI_BLOCKED, TRAIT_INCAPACITATED)
|
||||
REMOVE_TRAIT(src, TRAIT_PULL_BLOCKED, TRAIT_INCAPACITATED)
|
||||
|
||||
|
||||
/// Called when [TRAIT_RESTRAINED] is added to the mob.
|
||||
/mob/living/proc/on_restrained_trait_gain(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
ADD_TRAIT(src, TRAIT_HANDS_BLOCKED, TRAIT_RESTRAINED)
|
||||
|
||||
/// Called when [TRAIT_RESTRAINED] is removed from the mob.
|
||||
/mob/living/proc/on_restrained_trait_loss(datum/source)
|
||||
SIGNAL_HANDLER
|
||||
REMOVE_TRAIT(src, TRAIT_HANDS_BLOCKED, TRAIT_RESTRAINED)
|
||||
|
||||
|
||||
/**
|
||||
* Called when traits that alter succumbing are added/removed.
|
||||
*
|
||||
* Will show or hide the succumb alert prompt.
|
||||
*/
|
||||
/mob/living/proc/update_succumb_action()
|
||||
SIGNAL_HANDLER
|
||||
if (CAN_SUCCUMB(src))
|
||||
throw_alert("succumb", /obj/screen/alert/succumb)
|
||||
else
|
||||
|
||||
@@ -385,7 +385,7 @@
|
||||
death()
|
||||
|
||||
/mob/living/incapacitated(ignore_restraints = FALSE, ignore_grab = FALSE, ignore_stasis = FALSE)
|
||||
if(stat || HAS_TRAIT(src, TRAIT_INCAPACITATED) || (!ignore_restraints && (HAS_TRAIT(src, TRAIT_RESTRAINED) || (!ignore_grab && pulledby && pulledby.grab_state >= GRAB_AGGRESSIVE))) || (!ignore_stasis && IS_IN_STASIS(src)))
|
||||
if(HAS_TRAIT(src, TRAIT_INCAPACITATED) || (!ignore_restraints && (HAS_TRAIT(src, TRAIT_RESTRAINED) || (!ignore_grab && pulledby && pulledby.grab_state >= GRAB_AGGRESSIVE))) || (!ignore_stasis && IS_IN_STASIS(src)))
|
||||
return TRUE
|
||||
|
||||
/mob/living/canUseStorage()
|
||||
@@ -427,30 +427,43 @@
|
||||
|
||||
/mob/proc/get_contents()
|
||||
|
||||
|
||||
/mob/living/proc/lay_down()
|
||||
set name = "Rest"
|
||||
set category = "IC"
|
||||
|
||||
if(!resting)
|
||||
set_resting(TRUE, FALSE)
|
||||
else
|
||||
if(do_after(src, 10, target = src))
|
||||
set_resting(FALSE, FALSE)
|
||||
else
|
||||
to_chat(src, "<span class='warning'>You fail to get up!</span>")
|
||||
set_resting(!resting, FALSE)
|
||||
|
||||
|
||||
///Proc to hook behavior to the change of value in the resting variable.
|
||||
/mob/living/proc/set_resting(rest, silent = TRUE)
|
||||
if(rest == resting)
|
||||
/mob/living/proc/set_resting(new_resting, silent = TRUE)
|
||||
if(new_resting == resting)
|
||||
return
|
||||
if(!silent)
|
||||
if(rest)
|
||||
to_chat(src, "<span class='notice'>You are now resting.</span>")
|
||||
. = resting
|
||||
resting = new_resting
|
||||
if(new_resting)
|
||||
if(lying_angle == 90 || lying_angle == 270)
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You will now try to stay lying down on the floor.</span>")
|
||||
else if(buckled && buckled.buckle_lying != NO_BUCKLE_LYING)
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You will now lay down as soon as you are able to.</span>")
|
||||
else
|
||||
to_chat(src, "<span class='notice'>You get up.</span>")
|
||||
. = rest
|
||||
resting = rest
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You lay down.</span>")
|
||||
set_lying_down()
|
||||
else
|
||||
if(lying_angle == 0)
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You will now try to remain standing up.</span>")
|
||||
else if(HAS_TRAIT(src, TRAIT_FLOORED) || (buckled && buckled.buckle_lying != NO_BUCKLE_LYING))
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You will now stand up as soon as you are able to.</span>")
|
||||
else
|
||||
if(!silent)
|
||||
to_chat(src, "<span class='notice'>You stand up.</span>")
|
||||
get_up()
|
||||
|
||||
update_resting()
|
||||
|
||||
|
||||
@@ -459,6 +472,31 @@
|
||||
update_mobility()
|
||||
|
||||
|
||||
/mob/living/proc/get_up()
|
||||
set waitfor = FALSE
|
||||
var/static/datum/callback/rest_checks = CALLBACK(src, .proc/rest_checks_callback)
|
||||
if(!do_mob(src, src, 2 SECONDS, uninterruptible = TRUE, extra_checks = rest_checks))
|
||||
return
|
||||
if(resting || lying_angle == 0 || HAS_TRAIT(src, TRAIT_FLOORED))
|
||||
return
|
||||
set_lying_angle(0)
|
||||
|
||||
|
||||
/mob/living/proc/rest_checks_callback()
|
||||
if(resting || lying_angle == 0 || HAS_TRAIT(src, TRAIT_FLOORED))
|
||||
return FALSE
|
||||
return TRUE
|
||||
|
||||
|
||||
/mob/living/proc/set_lying_down(new_lying_angle)
|
||||
if(buckled && buckled.buckle_lying == 0)
|
||||
return
|
||||
if(!new_lying_angle)
|
||||
set_lying_angle(pick(90, 270))
|
||||
else
|
||||
set_lying_angle(new_lying_angle)
|
||||
|
||||
|
||||
//Recursive function to find everything a mob is holding. Really shitty proc tbh.
|
||||
/mob/living/get_contents()
|
||||
var/list/ret = list()
|
||||
@@ -1177,53 +1215,9 @@
|
||||
return ..() && !(buckled && buckled.buckle_prevents_pull)
|
||||
|
||||
|
||||
//Updates 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
|
||||
//Updates lying and icons on robots, animals and brains. Needs to be refactored to use traits and update based on events.
|
||||
/mob/living/proc/update_mobility()
|
||||
var/canstand_involuntary = !HAS_TRAIT(src, TRAIT_FLOORED)
|
||||
var/canstand = canstand_involuntary && !resting
|
||||
|
||||
if(buckled && buckled.buckle_lying != -1)
|
||||
if(buckled.buckle_lying != 0)
|
||||
mobility_flags &= ~MOBILITY_STAND
|
||||
else
|
||||
mobility_flags |= MOBILITY_STAND
|
||||
set_lying_angle(buckled.buckle_lying)
|
||||
else if(!canstand)
|
||||
mobility_flags &= ~MOBILITY_STAND
|
||||
if(lying_angle == 0) //force them on the ground
|
||||
set_lying_angle(pick(90, 270))
|
||||
if(!canstand_involuntary)
|
||||
on_fall()
|
||||
else
|
||||
mobility_flags |= MOBILITY_STAND
|
||||
set_lying_angle(0)
|
||||
|
||||
if(lying_angle != 0 || HAS_TRAIT(src, TRAIT_HANDS_BLOCKED) || incapacitated())
|
||||
mobility_flags &= ~(MOBILITY_UI|MOBILITY_PULL)
|
||||
else
|
||||
mobility_flags |= MOBILITY_UI|MOBILITY_PULL
|
||||
|
||||
if(!(mobility_flags & MOBILITY_PULL))
|
||||
if(pulling)
|
||||
stop_pulling()
|
||||
if(!(mobility_flags & MOBILITY_UI))
|
||||
unset_machine()
|
||||
|
||||
// Movespeed mods based on arms/legs quantity
|
||||
if(movement_type & (FLYING | FLOATING))
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/limbless)
|
||||
else
|
||||
var/limbless_slowdown = 0
|
||||
// These checks for <2 should be swapped out for something else if we ever end up with a species with more than 2
|
||||
if(usable_legs < default_num_legs)
|
||||
limbless_slowdown += (default_num_legs * 3) - (usable_legs * 3)
|
||||
if(!usable_legs && usable_hands < default_num_hands)
|
||||
limbless_slowdown += (default_num_hands * 3) - (usable_hands * 3)
|
||||
if(limbless_slowdown)
|
||||
add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/limbless, multiplicative_slowdown = limbless_slowdown)
|
||||
else
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/limbless)
|
||||
return
|
||||
|
||||
|
||||
///Called when mob changes from a standing position into a prone while lacking the ability to stand up at the moment, through update_mobility()
|
||||
@@ -1437,13 +1431,19 @@
|
||||
if(lying_angle != 0) //We are not standing up.
|
||||
if(layer == initial(layer)) //to avoid things like hiding larvas.
|
||||
layer = LYING_MOB_LAYER //so mob lying always appear behind standing mobs
|
||||
if(. == 0) //We became prone and were not before. We lose density and stop bumping passable dense things.
|
||||
density = FALSE
|
||||
if(. == 0) // We became prone and were not before.
|
||||
ADD_TRAIT(src, TRAIT_UI_BLOCKED, LYING_DOWN_TRAIT)
|
||||
ADD_TRAIT(src, TRAIT_PULL_BLOCKED, LYING_DOWN_TRAIT)
|
||||
density = FALSE // We lose density and stop bumping passable dense things.
|
||||
if(HAS_TRAIT(src, TRAIT_FLOORED) && !(dir & (NORTH|SOUTH)))
|
||||
setDir(pick(NORTH, SOUTH)) // We are and look helpless.
|
||||
else //We are prone.
|
||||
if(layer == LYING_MOB_LAYER)
|
||||
layer = initial(layer)
|
||||
if(.) //We were prone before, so we become dense and things can bump into us again.
|
||||
density = initial(density)
|
||||
REMOVE_TRAIT(src, TRAIT_UI_BLOCKED, LYING_DOWN_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_PULL_BLOCKED, LYING_DOWN_TRAIT)
|
||||
|
||||
|
||||
/**
|
||||
@@ -1601,6 +1601,7 @@
|
||||
switch(.) //Previous stat.
|
||||
if(CONSCIOUS)
|
||||
if(stat >= UNCONSCIOUS)
|
||||
ADD_TRAIT(src, TRAIT_INCAPACITATED, TRAIT_KNOCKEDOUT)
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, TRAIT_KNOCKEDOUT)
|
||||
ADD_TRAIT(src, TRAIT_HANDS_BLOCKED, TRAIT_KNOCKEDOUT)
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, UNCONSCIOUS_TRAIT)
|
||||
@@ -1619,6 +1620,7 @@
|
||||
switch(stat) //Current stat.
|
||||
if(CONSCIOUS)
|
||||
if(. >= UNCONSCIOUS)
|
||||
REMOVE_TRAIT(src, TRAIT_INCAPACITATED, TRAIT_KNOCKEDOUT)
|
||||
REMOVE_TRAIT(src, TRAIT_IMMOBILIZED, TRAIT_KNOCKEDOUT)
|
||||
REMOVE_TRAIT(src, TRAIT_HANDS_BLOCKED, TRAIT_KNOCKEDOUT)
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, UNCONSCIOUS_TRAIT)
|
||||
@@ -1655,11 +1657,21 @@
|
||||
if(buckled)
|
||||
if(!.)
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, BUCKLED_TRAIT)
|
||||
if(buckled.buckle_lying)
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, BUCKLED_TRAIT)
|
||||
else if(.)
|
||||
switch(buckled.buckle_lying)
|
||||
if(NO_BUCKLE_LYING) // The buckle doesn't force a lying angle.
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, BUCKLED_TRAIT)
|
||||
return
|
||||
if(0) // Forcing to a standing position.
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, BUCKLED_TRAIT)
|
||||
else // Forcing to a lying position.
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, BUCKLED_TRAIT)
|
||||
set_lying_angle(buckled.buckle_lying)
|
||||
else if(.) // We unbuckled from something.
|
||||
REMOVE_TRAIT(src, TRAIT_IMMOBILIZED, BUCKLED_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, BUCKLED_TRAIT)
|
||||
var/atom/movable/old_buckled = .
|
||||
if(old_buckled.buckle_lying == 0 && resting) // The buckle forced us to stay up (like a chair) and our preference is set to resting...
|
||||
set_lying_down() // ...so let's drop on the ground.
|
||||
|
||||
|
||||
/mob/living/set_pulledby(new_pulledby)
|
||||
@@ -1707,6 +1719,23 @@
|
||||
. = usable_legs
|
||||
usable_legs = new_value
|
||||
|
||||
if(new_value > .) // Gained leg usage.
|
||||
REMOVE_TRAIT(src, TRAIT_FLOORED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
REMOVE_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
else if(!(movement_type & (FLYING | FLOATING))) //Lost leg usage, not flying.
|
||||
if(!usable_legs)
|
||||
ADD_TRAIT(src, TRAIT_FLOORED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
if(!usable_hands)
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
|
||||
if(usable_legs < default_num_legs)
|
||||
var/limbless_slowdown = (default_num_legs - usable_legs) * 3
|
||||
if(!usable_legs && usable_hands < default_num_hands)
|
||||
limbless_slowdown += (default_num_hands - usable_hands) * 3
|
||||
add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/limbless, multiplicative_slowdown = limbless_slowdown)
|
||||
else
|
||||
remove_movespeed_modifier(/datum/movespeed_modifier/limbless)
|
||||
|
||||
|
||||
///Proc to modify the value of num_hands and hook behavior associated to this event.
|
||||
/mob/living/proc/set_num_hands(new_value)
|
||||
@@ -1723,6 +1752,12 @@
|
||||
. = usable_hands
|
||||
usable_hands = new_value
|
||||
|
||||
if(new_value > .) // Gained hand usage.
|
||||
REMOVE_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
else if(!(movement_type & (FLYING | FLOATING)) && !usable_hands && !usable_legs) //Lost a hand, not flying, no hands left, no legs.
|
||||
ADD_TRAIT(src, TRAIT_IMMOBILIZED, LACKING_LOCOMOTION_APPENDAGES_TRAIT)
|
||||
|
||||
|
||||
/// Whether or not this mob will escape from storages while being picked up/held.
|
||||
/mob/living/proc/will_escape_storage()
|
||||
return FALSE
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
var/list/network = list("ss13")
|
||||
var/obj/machinery/camera/current
|
||||
var/list/connected_robots = list()
|
||||
var/aiRestorePowerRoutine = 0
|
||||
var/aiRestorePowerRoutine = POWER_RESTORATION_OFF
|
||||
var/requires_power = POWER_REQ_ALL
|
||||
var/can_be_carded = TRUE
|
||||
var/alarms = list("Motion"=list(), "Fire"=list(), "Atmosphere"=list(), "Power"=list(), "Camera"=list(), "Burglar"=list())
|
||||
@@ -170,6 +170,9 @@
|
||||
builtInCamera = new (src)
|
||||
builtInCamera.network = list("ss13")
|
||||
|
||||
ADD_TRAIT(src, TRAIT_PULL_BLOCKED, ROUNDSTART_TRAIT)
|
||||
|
||||
|
||||
/mob/living/silicon/ai/key_down(_key, client/user)
|
||||
if(findtext(_key, "numpad")) //if it's a numpad number, we can convert it to just the number
|
||||
_key = _key[7] //strings, lists, same thing really
|
||||
@@ -798,10 +801,6 @@
|
||||
/mob/living/silicon/ai/can_buckle()
|
||||
return FALSE
|
||||
|
||||
/mob/living/silicon/ai/incapacitated(ignore_restraints = FALSE, ignore_grab = FALSE, ignore_stasis = FALSE)
|
||||
if(aiRestorePowerRoutine)
|
||||
return TRUE
|
||||
return ..()
|
||||
|
||||
/mob/living/silicon/ai/canUseTopic(atom/movable/M, be_close=FALSE, no_dexterity=FALSE, no_tk=FALSE)
|
||||
if(control_disabled || incapacitated())
|
||||
@@ -1032,3 +1031,16 @@
|
||||
|
||||
/mob/living/silicon/ai/zMove(dir, feedback = FALSE)
|
||||
. = eyeobj.zMove(dir, feedback)
|
||||
|
||||
|
||||
/// Proc to hook behavior to the changes of the value of [aiRestorePowerRoutine].
|
||||
/mob/living/silicon/ai/proc/setAiRestorePowerRoutine(new_value)
|
||||
if(new_value == aiRestorePowerRoutine)
|
||||
return
|
||||
. = aiRestorePowerRoutine
|
||||
aiRestorePowerRoutine = new_value
|
||||
if(aiRestorePowerRoutine)
|
||||
if(!.)
|
||||
ADD_TRAIT(src, TRAIT_INCAPACITATED, POWER_LACK_TRAIT)
|
||||
else if(.)
|
||||
REMOVE_TRAIT(src, TRAIT_INCAPACITATED, POWER_LACK_TRAIT)
|
||||
|
||||
@@ -1,8 +1,3 @@
|
||||
#define POWER_RESTORATION_OFF 0
|
||||
#define POWER_RESTORATION_START 1
|
||||
#define POWER_RESTORATION_SEARCH_APC 2
|
||||
#define POWER_RESTORATION_APC_FOUND 3
|
||||
|
||||
/mob/living/silicon/ai/Life()
|
||||
if (stat == DEAD)
|
||||
return
|
||||
@@ -110,7 +105,7 @@
|
||||
T = get_turf(src)
|
||||
if(isspaceturf(T))
|
||||
to_chat(src, "<span class='alert'>Unable to verify! No power connection detected!</span>")
|
||||
aiRestorePowerRoutine = POWER_RESTORATION_SEARCH_APC
|
||||
setAiRestorePowerRoutine(POWER_RESTORATION_SEARCH_APC)
|
||||
return
|
||||
to_chat(src, "<span class='notice'>Connection verified. Searching for APC in power network.</span>")
|
||||
sleep(50)
|
||||
@@ -131,7 +126,7 @@
|
||||
to_chat(src, "<span class='alert'>Unable to locate APC!</span>")
|
||||
else
|
||||
to_chat(src, "<span class='alert'>Lost connection with the APC!</span>")
|
||||
aiRestorePowerRoutine = POWER_RESTORATION_SEARCH_APC
|
||||
setAiRestorePowerRoutine(POWER_RESTORATION_SEARCH_APC)
|
||||
return
|
||||
if(AIarea.power_equip)
|
||||
if(!isspaceturf(T))
|
||||
@@ -152,7 +147,7 @@
|
||||
apc_override = 1
|
||||
theAPC.ui_interact(src)
|
||||
apc_override = 0
|
||||
aiRestorePowerRoutine = POWER_RESTORATION_APC_FOUND
|
||||
setAiRestorePowerRoutine(POWER_RESTORATION_APC_FOUND)
|
||||
sleep(50)
|
||||
theAPC = null
|
||||
|
||||
@@ -162,19 +157,14 @@
|
||||
to_chat(src, "<span class='notice'>Alert cancelled. Power has been restored.</span>")
|
||||
else
|
||||
to_chat(src, "<span class='notice'>Alert cancelled. Power has been restored without our assistance.</span>")
|
||||
aiRestorePowerRoutine = POWER_RESTORATION_OFF
|
||||
setAiRestorePowerRoutine(POWER_RESTORATION_OFF)
|
||||
set_blindness(0)
|
||||
update_sight()
|
||||
|
||||
/mob/living/silicon/ai/proc/ai_lose_power()
|
||||
disconnect_shell()
|
||||
aiRestorePowerRoutine = POWER_RESTORATION_START
|
||||
setAiRestorePowerRoutine(POWER_RESTORATION_START)
|
||||
blind_eyes(1)
|
||||
update_sight()
|
||||
to_chat(src, "<span class='alert'>You've lost power!</span>")
|
||||
addtimer(CALLBACK(src, .proc/start_RestorePowerRoutine), 20)
|
||||
|
||||
#undef POWER_RESTORATION_OFF
|
||||
#undef POWER_RESTORATION_START
|
||||
#undef POWER_RESTORATION_SEARCH_APC
|
||||
#undef POWER_RESTORATION_APC_FOUND
|
||||
|
||||
@@ -375,7 +375,7 @@
|
||||
icon_state_on = "protoemitter_+a"
|
||||
icon_state_underpowered = "protoemitter_+u"
|
||||
can_buckle = TRUE
|
||||
buckle_lying = FALSE
|
||||
buckle_lying = 0
|
||||
var/view_range = 4.5
|
||||
var/datum/action/innate/protoemitter/firing/auto
|
||||
|
||||
|
||||
Reference in New Issue
Block a user