From 7b2c8e58ffb8f50eb3dda68b987a7def56cf188f Mon Sep 17 00:00:00 2001 From: Fermi <> Date: Mon, 14 Oct 2019 13:23:39 +0100 Subject: [PATCH] Fixes freezing and ghost rider --- code/__DEFINES/misc.dm | 2 +- code/__DEFINES/obj_flags.dm | 2 +- .../structures/crates_lockers/crates.dm | 19 +++++ code/modules/mob/living/brain/brain_item.dm | 5 +- .../modules/mob/living/carbon/alien/organs.dm | 1 + code/modules/mob/living/taste.dm | 2 - code/modules/surgery/organs/autosurgeon.dm | 5 +- code/modules/surgery/organs/organ_internal.dm | 83 ++++++++++++++++--- code/modules/surgery/organs/tongue.dm | 2 + 9 files changed, 103 insertions(+), 18 deletions(-) diff --git a/code/__DEFINES/misc.dm b/code/__DEFINES/misc.dm index ba5e105041..4beff367c5 100644 --- a/code/__DEFINES/misc.dm +++ b/code/__DEFINES/misc.dm @@ -314,7 +314,7 @@ GLOBAL_LIST_INIT(pda_reskins, list(PDA_SKIN_CLASSIC = 'icons/obj/pda.dmi', PDA_S #define MAP_MAXZ 6 // Defib stats -#define DEFIB_TIME_LIMIT 960 +#define DEFIB_TIME_LIMIT 1500 #define DEFIB_TIME_LOSS 60 // Diagonal movement diff --git a/code/__DEFINES/obj_flags.dm b/code/__DEFINES/obj_flags.dm index ba8d229f12..1917d73a1b 100644 --- a/code/__DEFINES/obj_flags.dm +++ b/code/__DEFINES/obj_flags.dm @@ -47,4 +47,4 @@ #define ORGAN_FAILING (1<<2) //Failing organs perform damaging effects until replaced or fixed #define ORGAN_EXTERNAL (1<<3) //Was this organ implanted/inserted/etc, if true will not be removed during species change. #define ORGAN_VITAL (1<<4) //Currently only the brain -#define ORGAN_NO_SPOIL (1<<5) //Currently only the brain +#define ORGAN_NO_SPOIL (1<<5) //Do not spoil under any circumstances diff --git a/code/game/objects/structures/crates_lockers/crates.dm b/code/game/objects/structures/crates_lockers/crates.dm index 6caa7d834b..23703c7891 100644 --- a/code/game/objects/structures/crates_lockers/crates.dm +++ b/code/game/objects/structures/crates_lockers/crates.dm @@ -99,6 +99,25 @@ name = "freezer" icon_state = "freezer" +//Snowflake organ freezer code +//Order is important, since we check source, we need to do the check whenever we have all the organs in the crate + +/obj/structure/closet/crate/freezer/open() + recursive_organ_check(src) + ..() + +/obj/structure/closet/crate/freezer/close() + ..() + recursive_organ_check(src) + +/obj/structure/closet/crate/freezer/Destroy() + recursive_organ_check(src) + ..() + +/obj/structure/closet/crate/freezer/Initialize() + . = ..() + recursive_organ_check(src) + /obj/structure/closet/crate/freezer/blood name = "blood freezer" desc = "A freezer containing packs of blood." diff --git a/code/modules/mob/living/brain/brain_item.dm b/code/modules/mob/living/brain/brain_item.dm index 41a8944015..4192c2235b 100644 --- a/code/modules/mob/living/brain/brain_item.dm +++ b/code/modules/mob/living/brain/brain_item.dm @@ -11,6 +11,7 @@ attack_verb = list("attacked", "slapped", "whacked") ///The brain's organ variables are significantly more different than the other organs, with half the decay rate for balance reasons, and twice the maxHealth decay_factor = STANDARD_ORGAN_DECAY / 4 //30 minutes of decaying to result in a fully damaged brain, since a fast decay rate would be unfun gameplay-wise + healing_factor = STANDARD_ORGAN_HEALING / 2 maxHealth = BRAIN_DAMAGE_DEATH low_threshold = 45 @@ -247,11 +248,13 @@ to_chat(owner, "The last spark of life in your brain fizzles out...") owner.death() brain_death = TRUE + return + ..() /obj/item/organ/brain/on_death() if(damage <= BRAIN_DAMAGE_DEATH) //rip brain_death = FALSE - applyOrganDamage(maxHealth * decay_factor) + ..() /obj/item/organ/brain/applyOrganDamage(var/d, var/maximum = maxHealth) diff --git a/code/modules/mob/living/carbon/alien/organs.dm b/code/modules/mob/living/carbon/alien/organs.dm index 155f203708..df1be454ee 100644 --- a/code/modules/mob/living/carbon/alien/organs.dm +++ b/code/modules/mob/living/carbon/alien/organs.dm @@ -1,6 +1,7 @@ /obj/item/organ/alien icon_state = "xgibmid2" var/list/alien_powers = list() + organ_flags = ORGAN_NO_SPOIL /obj/item/organ/alien/Initialize() . = ..() diff --git a/code/modules/mob/living/taste.dm b/code/modules/mob/living/taste.dm index 8b0c54653c..e4d1aa94a5 100644 --- a/code/modules/mob/living/taste.dm +++ b/code/modules/mob/living/taste.dm @@ -52,13 +52,11 @@ switch(from.pH) if(11.5 to INFINITY) to_chat(src, "You taste a strong alkaline flavour!") - T.applyOrganDamage(1) if(8.5 to 11.5) to_chat(src, "You taste a sort of soapy tone in the mixture.") if(2.5 to 5.5) to_chat(src, "You taste a sort of acid tone in the mixture.") if(-INFINITY to 2.5) to_chat(src, "You taste a strong acidic flavour!") - T.applyOrganDamage(1) #undef DEFAULT_TASTE_SENSITIVITY diff --git a/code/modules/surgery/organs/autosurgeon.dm b/code/modules/surgery/organs/autosurgeon.dm index 2cc5c554c6..27bf575627 100644 --- a/code/modules/surgery/organs/autosurgeon.dm +++ b/code/modules/surgery/organs/autosurgeon.dm @@ -17,9 +17,10 @@ if(starting_organ) insert_organ(new starting_organ(src)) -/obj/item/autosurgeon/proc/insert_organ(var/obj/item/I) +/obj/item/autosurgeon/proc/insert_organ(var/obj/item/organ/I) storedorgan = I I.forceMove(src) + I.organ_flags |= ORGAN_FROZEN //Stops decay name = "[initial(name)] ([storedorgan.name])" /obj/item/autosurgeon/attack_self(mob/user)//when the object it used... @@ -125,4 +126,4 @@ /obj/item/autosurgeon/womb desc = "A single use autosurgeon that contains a womb. A screwdriver can be used to remove it, but implants can't be placed back in." uses = 1 - starting_organ = /obj/item/organ/genital/womb \ No newline at end of file + starting_organ = /obj/item/organ/genital/womb diff --git a/code/modules/surgery/organs/organ_internal.dm b/code/modules/surgery/organs/organ_internal.dm index 4ff22c35d8..a32616c711 100644 --- a/code/modules/surgery/organs/organ_internal.dm +++ b/code/modules/surgery/organs/organ_internal.dm @@ -41,6 +41,9 @@ else qdel(replaced) + //Hopefully this doesn't cause problems + organ_flags &= ~ORGAN_FROZEN + owner = M M.internal_organs |= src M.internal_organs_slot[slot] = src @@ -64,26 +67,82 @@ A.Remove(M) START_PROCESSING(SSobj, src) - /obj/item/organ/proc/on_find(mob/living/finder) return -/obj/item/organ/process() +/obj/item/organ/process() //runs decay when outside of a person AND ONLY WHEN OUTSIDE (i.e. long obj). on_death() //Kinda hate doing it like this, but I really don't want to call process directly. -/obj/item/organ/proc/on_death() //runs decay when outside of a person - if(CHECK_MULTIPLE_BITFIELDS(organ_flags, ORGAN_SYNTHETIC|ORGAN_FROZEN|ORGAN_NO_SPOIL)) +//Sources; life.dm process_organs +/obj/item/organ/proc/on_death() //Runs when outside AND inside. + decay() + +//Applys the slow damage over time decay +/obj/item/organ/proc/decay() + if(!can_decay()) + STOP_PROCESSING(SSobj, src) + return + is_cold() + if(organ_flags & ORGAN_FROZEN) return applyOrganDamage(maxHealth * decay_factor) +/obj/item/organ/proc/can_decay() + if(organ_flags & ORGAN_NO_SPOIL) + return FALSE + if(organ_flags & ORGAN_SYNTHETIC) + return FALSE + if((organ_flags & ORGAN_FAILING) || damage >= maxHealth) + return FALSE + return TRUE + +//Checks to see if the organ is frozen from temperature +/obj/item/organ/proc/is_cold() + if(istype(loc, /obj/))//Freezer of some kind, I hope. + if(istype(loc, /obj/structure/closet/crate/freezer) || istype(loc, /obj/structure/closet/secure_closet/freezer) || istype(loc, /obj/structure/bodycontainer)) + if(!(organ_flags & ORGAN_FROZEN))//Incase someone puts them in when cold, but they warm up inside of the thing. (i.e. they have the flag, the thing turns it off, this rights it.) + organ_flags |= ORGAN_FROZEN + return + + var/local_temp + if(istype(loc, /turf/))//Only concern is adding an organ to a freezer when the area around it is cold. + var/turf/T = loc + var/datum/gas_mixture/enviro = T.return_air() + local_temp = enviro.temperature + + if(istype(loc, /mob/)) + var/mob/M = loc + var/turf/T = M.loc + var/datum/gas_mixture/enviro = T.return_air() + local_temp = enviro.temperature + + else if(owner) + //Don't interfere with bodies frozen by structures. + if(istype(owner.loc, /obj/structure/closet/crate/freezer) || istype(owner.loc, /obj/structure/closet/secure_closet/freezer) || istype(owner.loc, /obj/structure/bodycontainer)) + if(!(organ_flags & ORGAN_FROZEN))//Incase someone puts them in when cold, but they warm up inside of the thing. (i.e. they have the flag, the thing turns it off, this rights it.) + organ_flags |= ORGAN_FROZEN + return TRUE + local_temp = owner.bodytemperature + + if(!local_temp)//Shouldn't happen but in case + return + if(local_temp < 154)//I have a pretty shaky citation that states -120 allows indefinite cyrostorage + organ_flags |= ORGAN_FROZEN + return TRUE + organ_flags &= ~ORGAN_FROZEN + return FALSE + /obj/item/organ/proc/on_life() //repair organ damage if the organ is not failing - if(!(organ_flags & ORGAN_FAILING)) - ///Damage decrements by a percent of its maxhealth - var/healing_amount = -(maxHealth * healing_factor) - ///Damage decrements again by a percent of its maxhealth, up to a total of 4 extra times depending on the owner's health - healing_amount -= owner.satiety > 0 ? 4 * healing_factor * owner.satiety / MAX_SATIETY : 0 - applyOrganDamage(healing_amount) //to FERMI_TWEAK - //Make it so each threshold is stuck. + if(organ_flags & ORGAN_FAILING) + return + if(is_cold()) + return + ///Damage decrements by a percent of its maxhealth + var/healing_amount = -(maxHealth * healing_factor) + ///Damage decrements again by a percent of its maxhealth, up to a total of 4 extra times depending on the owner's health + healing_amount -= owner.satiety > 0 ? 4 * healing_factor * owner.satiety / MAX_SATIETY : 0 + applyOrganDamage(healing_amount) //to FERMI_TWEAK + //Make it so each threshold is stuck. /obj/item/organ/examine(mob/user) . = ..() @@ -177,6 +236,8 @@ return low_threshold_passed else organ_flags &= ~ORGAN_FAILING + if(!owner)//Processing is stopped when the organ is dead and outside of someone. This hopefully should restart it if a removed organ is repaired outside of a body. + START_PROCESSING(SSobj, src) if(prev_damage > low_threshold && damage <= low_threshold) return low_threshold_cleared if(prev_damage > high_threshold && damage <= high_threshold) diff --git a/code/modules/surgery/organs/tongue.dm b/code/modules/surgery/organs/tongue.dm index fa6f3ce93b..cee20dddee 100644 --- a/code/modules/surgery/organs/tongue.dm +++ b/code/modules/surgery/organs/tongue.dm @@ -211,6 +211,8 @@ phomeme_type = pick(phomeme_types) /obj/item/organ/tongue/bone/applyOrganDamage(var/d, var/maximum = maxHealth) + if(d < 0) + return if(!owner) return var/target = owner.get_bodypart(BODY_ZONE_HEAD)