From 731b38c975e2fa2503898e31fee840e87488dfc4 Mon Sep 17 00:00:00 2001 From: kevinz000 <2003111+kevinz000@users.noreply.github.com> Date: Thu, 14 Nov 2019 15:52:11 -0700 Subject: [PATCH] Merge pull request #9683 from Ghommie/Ghommie-cit303 Dullahans fixes and QoL. --- code/__DEFINES/components.dm | 6 ++ code/__DEFINES/is_helpers.dm | 2 + code/__HELPERS/game.dm | 1 + .../datums/weather/weather_types/ash_storm.dm | 2 +- code/game/machinery/recycler.dm | 2 +- .../components/unary_devices/cryo.dm | 2 +- code/modules/mob/living/carbon/human/life.dm | 92 +++++++++---------- .../mob/living/carbon/human/species.dm | 6 +- .../carbon/human/species_types/dullahan.dm | 63 ++++++++----- code/modules/mob/living/living.dm | 1 + code/modules/mob/mob.dm | 7 +- .../surgery/bodyparts/dismemberment.dm | 9 +- code/modules/surgery/bodyparts/head.dm | 2 + code/modules/surgery/bodyparts/helpers.dm | 18 +++- 14 files changed, 128 insertions(+), 85 deletions(-) diff --git a/code/__DEFINES/components.dm b/code/__DEFINES/components.dm index 91cc89ce..676733b6 100644 --- a/code/__DEFINES/components.dm +++ b/code/__DEFINES/components.dm @@ -103,3 +103,9 @@ */ #define ELEMENT_BESPOKE (1 << 1) #define COMSIG_MOVABLE_UPDATE_GLIDE_SIZE "movable_glide_size" //Called when the movable's glide size is updated: (new_glide_size) + +#define COMPONENT_ALLOW_EXAMINE 1 + +#define COMSIG_LIVING_FULLY_HEAL "living_fully_healed" //from base of /mob/living/fully_heal(): (admin_revive) +#define COMSIG_LIVING_REGENERATE_LIMBS "living_regenerate_limbs" //from base of /mob/living/regenerate_limbs(): (noheal, excluded_limbs) + diff --git a/code/__DEFINES/is_helpers.dm b/code/__DEFINES/is_helpers.dm index 7d4dc1ca..2dbc63aa 100644 --- a/code/__DEFINES/is_helpers.dm +++ b/code/__DEFINES/is_helpers.dm @@ -76,6 +76,8 @@ GLOBAL_LIST_INIT(turfs_without_ground, typecacheof(list( #define ishumanbasic(A) (is_species(A, /datum/species/human)) #define iscatperson(A) (ishumanbasic(A) && istype(A.dna.species, /datum/species/human/felinid) ) #define isvampire(A) (is_species(A,/datum/species/vampire)) +#define isdwarf(A) (is_species(A, /datum/species/dwarf)) +#define isdullahan(A) (is_species(A, /datum/species/dullahan)) // Citadel specific species #define isipcperson(A) (is_species(A, /datum/species/ipc)) diff --git a/code/__HELPERS/game.dm b/code/__HELPERS/game.dm index 8ef1c3f3..7e0e9136 100644 --- a/code/__HELPERS/game.dm +++ b/code/__HELPERS/game.dm @@ -156,6 +156,7 @@ var/atom/A = processing_list[1] if(A.flags_1 & HEAR_1) . += A + SEND_SIGNAL(A, COMSIG_ATOM_HEARER_IN_VIEW, processing_list, .) processing_list.Cut(1, 2) processing_list += A.contents diff --git a/code/datums/weather/weather_types/ash_storm.dm b/code/datums/weather/weather_types/ash_storm.dm index 345212cc..3247b890 100644 --- a/code/datums/weather/weather_types/ash_storm.dm +++ b/code/datums/weather/weather_types/ash_storm.dm @@ -80,7 +80,7 @@ return TRUE if(ishuman(L)) //Are you immune? var/mob/living/carbon/human/H = L - var/thermal_protection = H.get_thermal_protection() + var/thermal_protection = H.easy_thermal_protection() if(thermal_protection >= FIRE_IMMUNITY_MAX_TEMP_PROTECT) return TRUE if(isliving(L))// if we're a non immune mob inside an immune mob we have to reconsider if that mob is immune to protect ourselves diff --git a/code/game/machinery/recycler.dm b/code/game/machinery/recycler.dm index d6c73ce5..845e7da0 100644 --- a/code/game/machinery/recycler.dm +++ b/code/game/machinery/recycler.dm @@ -107,7 +107,7 @@ var/atom/movable/AM = i var/obj/item/bodypart/head/as_head = AM var/obj/item/mmi/as_mmi = AM - var/brain_holder = istype(AM, /obj/item/organ/brain) || (istype(as_head) && as_head.brain) || (istype(as_mmi) && as_mmi.brain) || isbrain(AM) + var/brain_holder = istype(AM, /obj/item/organ/brain) || (istype(as_head) && as_head.brain) || (istype(as_mmi) && as_mmi.brain) || isbrain(AM) || istype(AM, /obj/item/dullahan_relay) if(brain_holder) emergency_stop(AM) else if(isliving(AM)) diff --git a/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm b/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm index 2ec683e9..78f1af4e 100644 --- a/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm +++ b/code/modules/atmospherics/machinery/components/unary_devices/cryo.dm @@ -209,7 +209,7 @@ if(ishuman(occupant)) var/mob/living/carbon/human/H = occupant - cold_protection = H.get_cold_protection(air1.temperature) + cold_protection = H.get_thermal_protection(air1.temperature, TRUE) if(abs(temperature_delta) > 1) var/air_heat_capacity = air1.heat_capacity() diff --git a/code/modules/mob/living/carbon/human/life.dm b/code/modules/mob/living/carbon/human/life.dm index 5a0dce99..139ab861 100644 --- a/code/modules/mob/living/carbon/human/life.dm +++ b/code/modules/mob/living/carbon/human/life.dm @@ -3,7 +3,7 @@ //NOTE: Breathing happens once per FOUR TICKS, unless the last breath fails. In which case it happens once per ONE TICK! So oxyloss healing is done once per 4 ticks while oxyloss damage is applied once per tick! // bitflags for the percentual amount of protection a piece of clothing which covers the body part offers. -// Used with human/proc/get_heat_protection() and human/proc/get_cold_protection() +// Used with human/proc/get_thermal_protection() // The values here should add up to 1. // Hands and feet have 2.5%, arms and legs 7.5%, each of the torso parts has 15% and the head has 30% #define THERMAL_PROTECTION_HEAD 0.3 @@ -50,16 +50,17 @@ /mob/living/carbon/human/calculate_affecting_pressure(pressure) - if (wear_suit && head && istype(wear_suit, /obj/item/clothing) && istype(head, /obj/item/clothing)) + var/headless = !get_bodypart(BODY_ZONE_HEAD) //should the mob be perennially headless (see dullahans), we only take the suit into account, so they can into space. + if (wear_suit && istype(wear_suit, /obj/item/clothing) && (headless || (head && istype(head, /obj/item/clothing)))) var/obj/item/clothing/CS = wear_suit var/obj/item/clothing/CH = head - if (CS.clothing_flags & CH.clothing_flags & STOPSPRESSUREDAMAGE) + if (CS.clothing_flags & STOPSPRESSUREDAMAGE && (headless || (CH.clothing_flags & STOPSPRESSUREDAMAGE))) return ONE_ATMOSPHERE if(istype(loc, /obj/belly)) //START OF CIT CHANGES - Makes it so you don't suffocate while inside vore organs. Remind me to modularize this some time - Bhijn return ONE_ATMOSPHERE if(istype(loc, /obj/item/dogborg/sleeper)) return ONE_ATMOSPHERE //END OF CIT CHANGES - return pressure + return ..() /mob/living/carbon/human/handle_traits() @@ -133,7 +134,7 @@ if(dna) dna.species.handle_fire(src) -/mob/living/carbon/human/proc/get_thermal_protection() +/mob/living/carbon/human/proc/easy_thermal_protection() var/thermal_protection = 0 //Simple check to estimate how protected we are against multiple temperatures //CITADEL EDIT Vore code required overrides if(istype(loc, /obj/item/dogborg/sleeper)) @@ -165,7 +166,6 @@ ..() //END FIRE CODE - //This proc returns a number made up of the flags for body parts which you are protected on. (such as HEAD, CHEST, GROIN, etc. See setup.dm for the full list) /mob/living/carbon/human/proc/get_heat_protection_flags(temperature) //Temperature is the temperature you're being exposed to. var/thermal_protection_flags = 0 @@ -191,37 +191,6 @@ return thermal_protection_flags -/mob/living/carbon/human/proc/get_heat_protection(temperature) //Temperature is the temperature you're being exposed to. - var/thermal_protection_flags = get_heat_protection_flags(temperature) - - var/thermal_protection = 0 - if(thermal_protection_flags) - if(thermal_protection_flags & HEAD) - thermal_protection += THERMAL_PROTECTION_HEAD - if(thermal_protection_flags & CHEST) - thermal_protection += THERMAL_PROTECTION_CHEST - if(thermal_protection_flags & GROIN) - thermal_protection += THERMAL_PROTECTION_GROIN - if(thermal_protection_flags & LEG_LEFT) - thermal_protection += THERMAL_PROTECTION_LEG_LEFT - if(thermal_protection_flags & LEG_RIGHT) - thermal_protection += THERMAL_PROTECTION_LEG_RIGHT - if(thermal_protection_flags & FOOT_LEFT) - thermal_protection += THERMAL_PROTECTION_FOOT_LEFT - if(thermal_protection_flags & FOOT_RIGHT) - thermal_protection += THERMAL_PROTECTION_FOOT_RIGHT - if(thermal_protection_flags & ARM_LEFT) - thermal_protection += THERMAL_PROTECTION_ARM_LEFT - if(thermal_protection_flags & ARM_RIGHT) - thermal_protection += THERMAL_PROTECTION_ARM_RIGHT - if(thermal_protection_flags & HAND_LEFT) - thermal_protection += THERMAL_PROTECTION_HAND_LEFT - if(thermal_protection_flags & HAND_RIGHT) - thermal_protection += THERMAL_PROTECTION_HAND_RIGHT - - - return min(1,thermal_protection) - //See proc/get_heat_protection_flags(temperature) for the description of this proc. /mob/living/carbon/human/proc/get_cold_protection_flags(temperature) var/thermal_protection_flags = 0 @@ -248,17 +217,42 @@ return thermal_protection_flags -/mob/living/carbon/human/proc/get_cold_protection(temperature) -//CITADEL EDIT Mandatory for vore code. - if(istype(loc, /obj/item/dogborg/sleeper)) - return TRUE //freezing to death in sleepers ruins fun. - if(isbelly(loc)) - return TRUE - if(ismob(loc)) - return TRUE //because lazy and being inside somemone insulates you from space -//END EDIT - temperature = max(temperature, 2.7) //There is an occasional bug where the temperature is miscalculated in ares with a small amount of gas on them, so this is necessary to ensure that that bug does not affect this calculation. Space's temperature is 2.7K and most suits that are intended to protect against any cold, protect down to 2.0K. - var/thermal_protection_flags = get_cold_protection_flags(temperature) +/mob/living/carbon/human/proc/get_thermal_protection(temperature, cold = FALSE) + if(cold) + //CITADEL EDIT Mandatory for vore code. + if(istype(loc, /obj/item/dogborg/sleeper) || isbelly(loc) || ismob(loc)) + return 1 //freezing to death in sleepers ruins fun. + //END EDIT + temperature = max(temperature, 2.7) //There is an occasional bug where the temperature is miscalculated in ares with a small amount of gas on them, so this is necessary to ensure that that bug does not affect this calculation. Space's temperature is 2.7K and most suits that are intended to protect against any cold, protect down to 2.0K. + var/thermal_protection_flags = cold ? get_cold_protection_flags(temperature) : get_heat_protection_flags(temperature) + var/missing_body_parts_flags = ~get_body_parts_flags() + var/max_protection = 1 + if(missing_body_parts_flags) //I don't like copypasta as much as proc overhead. Do you want me to make these into a macro? + DISABLE_BITFIELD(thermal_protection_flags, missing_body_parts_flags) + if(missing_body_parts_flags & HEAD) + max_protection -= THERMAL_PROTECTION_HEAD + if(missing_body_parts_flags & CHEST) + max_protection -= THERMAL_PROTECTION_CHEST + if(missing_body_parts_flags & GROIN) + max_protection -= THERMAL_PROTECTION_GROIN + if(missing_body_parts_flags & LEG_LEFT) + max_protection -= THERMAL_PROTECTION_LEG_LEFT + if(missing_body_parts_flags & LEG_RIGHT) + max_protection -= THERMAL_PROTECTION_LEG_RIGHT + if(missing_body_parts_flags & FOOT_LEFT) + max_protection -= THERMAL_PROTECTION_FOOT_LEFT + if(missing_body_parts_flags & FOOT_RIGHT) + max_protection -= THERMAL_PROTECTION_FOOT_RIGHT + if(missing_body_parts_flags & ARM_LEFT) + max_protection -= THERMAL_PROTECTION_ARM_LEFT + if(missing_body_parts_flags & ARM_RIGHT) + max_protection -= THERMAL_PROTECTION_ARM_RIGHT + if(missing_body_parts_flags & HAND_LEFT) + max_protection -= THERMAL_PROTECTION_HAND_LEFT + if(missing_body_parts_flags & HAND_RIGHT) + max_protection -= THERMAL_PROTECTION_HAND_RIGHT + if(max_protection == 0) //Is it even a man if it doesn't have a body at all? Early return to avoid division by zero. + return 1 var/thermal_protection = 0 if(thermal_protection_flags) @@ -285,7 +279,7 @@ if(thermal_protection_flags & HAND_RIGHT) thermal_protection += THERMAL_PROTECTION_HAND_RIGHT - return min(1,thermal_protection) + return round(thermal_protection/max_protection, 0.001) /mob/living/carbon/human/handle_random_events() //Puke if toxloss is too high diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm index fef4c127..dc25b4e5 100644 --- a/code/modules/mob/living/carbon/human/species.dm +++ b/code/modules/mob/living/carbon/human/species.dm @@ -1877,13 +1877,13 @@ GLOBAL_LIST_EMPTY(roundstart_races) natural = H.natural_bodytemperature_stabilization() var/thermal_protection = 1 if(loc_temp < H.bodytemperature) //Place is colder than we are - thermal_protection -= H.get_cold_protection(loc_temp) //This returns a 0 - 1 value, which corresponds to the percentage of protection based on what you're wearing and what you're exposed to. + thermal_protection -= H.get_thermal_protection(loc_temp, TRUE) //This returns a 0 - 1 value, which corresponds to the percentage of protection based on what you're wearing and what you're exposed to. if(H.bodytemperature < BODYTEMP_NORMAL) //we're cold, insulation helps us retain body heat and will reduce the heat we lose to the environment H.adjust_bodytemperature((thermal_protection+1)*natural + max(thermal_protection * (loc_temp - H.bodytemperature) / BODYTEMP_COLD_DIVISOR, BODYTEMP_COOLING_MAX)) else //we're sweating, insulation hinders our ability to reduce heat - and it will reduce the amount of cooling you get from the environment H.adjust_bodytemperature(natural*(1/(thermal_protection+1)) + max((thermal_protection * (loc_temp - H.bodytemperature) + BODYTEMP_NORMAL - H.bodytemperature) / BODYTEMP_COLD_DIVISOR , BODYTEMP_COOLING_MAX)) //Extra calculation for hardsuits to bleed off heat else //Place is hotter than we are - thermal_protection -= H.get_heat_protection(loc_temp) //This returns a 0 - 1 value, which corresponds to the percentage of protection based on what you're wearing and what you're exposed to. + thermal_protection -= H.get_thermal_protection(loc_temp) //This returns a 0 - 1 value, which corresponds to the percentage of protection based on what you're wearing and what you're exposed to. if(H.bodytemperature < BODYTEMP_NORMAL) //and we're cold, insulation enhances our ability to retain body heat but reduces the heat we get from the environment H.adjust_bodytemperature((thermal_protection+1)*natural + min(thermal_protection * (loc_temp - H.bodytemperature) / BODYTEMP_HEAT_DIVISOR, BODYTEMP_HEATING_MAX)) else //we're sweating, insulation hinders out ability to reduce heat - but will reduce the amount of heat we get from the environment @@ -2022,7 +2022,7 @@ GLOBAL_LIST_EMPTY(roundstart_races) if(!(I.resistance_flags & FIRE_PROOF)) I.take_damage(H.fire_stacks, BURN, "fire", 0) - var/thermal_protection = H.get_thermal_protection() + var/thermal_protection = H.easy_thermal_protection() if(thermal_protection >= FIRE_IMMUNITY_MAX_TEMP_PROTECT && !no_protection) return diff --git a/code/modules/mob/living/carbon/human/species_types/dullahan.dm b/code/modules/mob/living/carbon/human/species_types/dullahan.dm index 0e7633f3..2c7272e2 100644 --- a/code/modules/mob/living/carbon/human/species_types/dullahan.dm +++ b/code/modules/mob/living/carbon/human/species_types/dullahan.dm @@ -18,6 +18,8 @@ var/obj/item/dullahan_relay/myhead /datum/species/dullahan/pumpkin + name = "Pumpkin Head Dullahan" + id = "pumpkindullahan" pumpkin = TRUE /datum/species/dullahan/check_roundstart_eligible() @@ -27,7 +29,7 @@ /datum/species/dullahan/on_species_gain(mob/living/carbon/human/H, datum/species/old_species) . = ..() - H.flags_1 &= ~HEAR_1 + DISABLE_BITFIELD(H.flags_1, HEAR_1) var/obj/item/bodypart/head/head = H.get_bodypart(BODY_ZONE_HEAD) if(head) if(pumpkin)//Pumpkinhead! @@ -36,16 +38,16 @@ head.icon_state = "hardhat1_pumpkin_j" head.custom_head = TRUE head.drop_limb() - head.flags_1 = HEAR_1 - head.throwforce = 25 - myhead = new /obj/item/dullahan_relay (head, H) - H.put_in_hands(head) - var/obj/item/organ/eyes/E = H.getorganslot(ORGAN_SLOT_EYES) - for(var/datum/action/item_action/organ_action/OA in E.actions) - OA.Trigger() + if(!QDELETED(head)) //drop_limb() deletes the limb if it's no drop location and dummy humans used for rendering icons are located in nullspace. Do the math. + head.throwforce = 25 + myhead = new /obj/item/dullahan_relay (head, H) + H.put_in_hands(head) + var/obj/item/organ/eyes/E = H.getorganslot(ORGAN_SLOT_EYES) + for(var/datum/action/item_action/organ_action/OA in E.actions) + OA.Trigger() /datum/species/dullahan/on_species_loss(mob/living/carbon/human/H) - H.flags_1 |= ~HEAR_1 + ENABLE_BITFIELD(H.flags_1, HEAR_1) H.reset_perspective(H) if(myhead) var/obj/item/dullahan_relay/DR = myhead @@ -84,7 +86,7 @@ /obj/item/organ/tongue/dullahan/handle_speech(datum/source, list/speech_args) if(ishuman(owner)) var/mob/living/carbon/human/H = owner - if(H.dna.species.id == "dullahan") + if(isdullahan(H)) var/datum/species/dullahan/D = H.dna.species if(isobj(D.myhead.loc)) var/obj/O = D.myhead.loc @@ -99,6 +101,7 @@ desc = "An abstraction." actions_types = list(/datum/action/item_action/organ_action/dullahan) zone = "abstract" + tint = INFINITY // used to switch the vision perspective to the head on species_gain(). /datum/action/item_action/organ_action/dullahan name = "Toggle Perspective" @@ -114,37 +117,53 @@ if(ishuman(owner)) var/mob/living/carbon/human/H = owner - if(H.dna.species.id == "dullahan") + if(isdullahan(H)) var/datum/species/dullahan/D = H.dna.species D.update_vision_perspective(H) /obj/item/dullahan_relay + name = "dullahan relay" var/mob/living/owner flags_1 = HEAR_1 -/obj/item/dullahan_relay/Initialize(mapload,new_owner) +/obj/item/dullahan_relay/Initialize(mapload, mob/living/carbon/human/new_owner) . = ..() + if(!new_owner) + return INITIALIZE_HINT_QDEL owner = new_owner START_PROCESSING(SSobj, src) + RegisterSignal(owner, COMSIG_MOB_EXAMINATE, .proc/examinate_check) + RegisterSignal(src, COMSIG_ATOM_HEARER_IN_VIEW, .proc/include_owner) + RegisterSignal(owner, COMSIG_LIVING_REGENERATE_LIMBS, .proc/unlist_head) + RegisterSignal(owner, COMSIG_LIVING_FULLY_HEAL, .proc/retrieve_head) + +/obj/item/dullahan_relay/proc/examinate_check(mob/source, atom/A) + if(source.client.eye == src && ((A in view(source.client.view, src)) || (isturf(A) && source.sight & SEE_TURFS) || (ismob(A) && source.sight & SEE_MOBS) || (isobj(A) && source.sight & SEE_OBJS))) + return COMPONENT_ALLOW_EXAMINE + +/obj/item/dullahan_relay/proc/include_owner(datum/source, list/processing_list, list/hearers) + if(!QDELETED(owner)) + hearers += owner + +/obj/item/dullahan_relay/proc/unlist_head(datum/source, noheal = FALSE, list/excluded_limbs) + excluded_limbs |= BODY_ZONE_HEAD // So we don't gib when regenerating limbs. + +/obj/item/dullahan_relay/proc/retrieve_head(datum/source, admin_revive = FALSE) + if(admin_revive) //retrieving the owner's head for ahealing purposes. + var/obj/item/bodypart/head/H = loc + var/turf/T = get_turf(owner) + if(H && istype(H) && T && !(H in owner.GetAllContents())) + H.forceMove(T) /obj/item/dullahan_relay/process() if(!istype(loc, /obj/item/bodypart/head) || QDELETED(owner)) . = PROCESS_KILL qdel(src) -/obj/item/dullahan_relay/Hear(message, atom/movable/speaker, message_language, raw_message, radio_freq, list/spans, message_mode) - . = ..() - if(!QDELETED(owner)) - message = compose_message(speaker, message_language, raw_message, radio_freq, spans, message_mode) - to_chat(owner,message) - else - qdel(src) - - /obj/item/dullahan_relay/Destroy() if(!QDELETED(owner)) var/mob/living/carbon/human/H = owner - if(H.dna.species.id == "dullahan") + if(isdullahan(H)) var/datum/species/dullahan/D = H.dna.species D.myhead = null owner.gib() diff --git a/code/modules/mob/living/living.dm b/code/modules/mob/living/living.dm index 26015c60..2d448c76 100644 --- a/code/modules/mob/living/living.dm +++ b/code/modules/mob/living/living.dm @@ -536,6 +536,7 @@ for(var/organ in C.internal_organs) var/obj/item/organ/O = organ O.setOrganDamage(0) + SEND_SIGNAL(src, COMSIG_LIVING_FULLY_HEAL, admin_revive) //proc called by revive(), to check if we can actually ressuscitate the mob (we don't want to revive him and have him instantly die again) diff --git a/code/modules/mob/mob.dm b/code/modules/mob/mob.dm index c7ce6577..62ba672c 100644 --- a/code/modules/mob/mob.dm +++ b/code/modules/mob/mob.dm @@ -309,8 +309,11 @@ set name = "Examine" set category = "IC" - if(isturf(A) && !(sight & SEE_TURFS) && !(A in view(client ? client.view : world.view, src))) - // shift-click catcher may issue examinate() calls for out-of-sight turfs + if(!client) + return + + if(!(SEND_SIGNAL(src, COMSIG_MOB_EXAMINATE, A) & COMPONENT_ALLOW_EXAMINE) && ((client.eye != src && client.eye != loc) || (isturf(A) && !(sight & SEE_TURFS) && !(A in view(client ? client.view : world.view, src))))) + //cameras & co don't allow users to examine far away things, also shift-click catcher may issue examinate() calls for out-of-sight turfs return if(is_blind(src)) diff --git a/code/modules/surgery/bodyparts/dismemberment.dm b/code/modules/surgery/bodyparts/dismemberment.dm index 32d790d8..4d681c59 100644 --- a/code/modules/surgery/bodyparts/dismemberment.dm +++ b/code/modules/surgery/bodyparts/dismemberment.dm @@ -334,12 +334,13 @@ //Regenerates all limbs. Returns amount of limbs regenerated -/mob/living/proc/regenerate_limbs(noheal, excluded_limbs) - return 0 +/mob/living/proc/regenerate_limbs(noheal = FALSE, list/excluded_limbs = list()) + SEND_SIGNAL(src, COMSIG_LIVING_REGENERATE_LIMBS, noheal, excluded_limbs) -/mob/living/carbon/regenerate_limbs(noheal, list/excluded_limbs) +/mob/living/carbon/regenerate_limbs(noheal = FALSE, list/excluded_limbs = list()) + . = ..() var/list/limb_list = list(BODY_ZONE_HEAD, BODY_ZONE_CHEST, BODY_ZONE_R_ARM, BODY_ZONE_L_ARM, BODY_ZONE_R_LEG, BODY_ZONE_L_LEG) - if(excluded_limbs) + if(excluded_limbs.len) limb_list -= excluded_limbs for(var/Z in limb_list) . += regenerate_limb(Z, noheal) diff --git a/code/modules/surgery/bodyparts/head.dm b/code/modules/surgery/bodyparts/head.dm index 90a5ab11..da9ec462 100644 --- a/code/modules/surgery/bodyparts/head.dm +++ b/code/modules/surgery/bodyparts/head.dm @@ -120,6 +120,8 @@ ..() /obj/item/bodypart/head/update_icon_dropped() + if(custom_head) + return var/list/standing = get_limb_icon(1) if(!standing.len) icon_state = initial(icon_state)//no overlays found, we default back to initial icon. diff --git a/code/modules/surgery/bodyparts/helpers.dm b/code/modules/surgery/bodyparts/helpers.dm index d33d0167..37b6ecc1 100644 --- a/code/modules/surgery/bodyparts/helpers.dm +++ b/code/modules/surgery/bodyparts/helpers.dm @@ -18,8 +18,6 @@ return FALSE - - /mob/proc/has_left_hand(check_disabled = TRUE) return TRUE @@ -335,3 +333,19 @@ else S.adjusted = ALT_STYLE H.update_inv_wear_suit() + +/mob/living/carbon/proc/get_body_parts_flags() + for(var/X in bodyparts) + var/obj/item/bodypart/L = X + switch(L.body_part) + if(CHEST) + . |= GROIN + if(LEG_LEFT) + . |= FOOT_LEFT + if(LEG_RIGHT) + . |= FOOT_RIGHT + if(ARM_LEFT) + . |= HAND_LEFT + if(ARM_RIGHT) + . |= HAND_RIGHT + . |= L.body_part \ No newline at end of file