From 18db172f87913e44e30e1980e24283d144b43c42 Mon Sep 17 00:00:00 2001 From: Cameron Lennox Date: Fri, 25 Jul 2025 06:07:16 -0400 Subject: [PATCH] Signals and God (#18031) * Begin godmode * Adds signals to a LOT of things Also makes godmode signal based. * Delete life_signals.dm * better like this tbh * this toooo * logic is hard sometime * Info and moving that detach * Unreg these * Organs * yeh * BESPOKE * emp * robutt * YEEE HAAA * Instant Damage * these should be updated as well * Update human_damage.dm * eh lets move this as well --- code/ZAS/Airflow.dm | 2 +- code/ZAS/ConnectionGroup.dm | 7 +- code/__defines/dcs/signals.dm | 77 ++++++++++- code/__defines/mobs.dm | 22 +-- code/__defines/vv.dm | 2 +- code/datums/elements/godmode.dm | 128 ++++++++++++++++++ code/game/gamemodes/cult/narsie.dm | 16 +-- code/game/gamemodes/cult/runes.dm | 2 +- code/game/gamemodes/cult/soulstone.dm | 6 +- code/modules/admin/verbs/randomverbs.dm | 16 ++- code/modules/mob/freelook/eye.dm | 5 +- code/modules/mob/living/bot/bot.dm | 5 +- code/modules/mob/living/carbon/alien/life.dm | 3 +- code/modules/mob/living/carbon/brain/life.dm | 3 +- code/modules/mob/living/carbon/carbon.dm | 3 +- code/modules/mob/living/carbon/human/human.dm | 7 +- .../mob/living/carbon/human/human_damage.dm | 20 ++- .../mob/living/carbon/human/human_species.dm | 3 +- code/modules/mob/living/carbon/human/life.dm | 29 ++-- code/modules/mob/living/damage_procs.dm | 2 + code/modules/mob/living/living.dm | 43 ++++-- code/modules/mob/living/living_defense.dm | 2 - code/modules/mob/living/silicon/ai/life.dm | 9 +- code/modules/mob/living/silicon/decoy/life.dm | 9 +- code/modules/mob/living/silicon/pai/life.dm | 9 +- .../silicon/robot/dogborg/dog_sleeper.dm | 4 +- .../mob/living/silicon/robot/robot_damage.dm | 10 +- code/modules/mob/living/silicon/silicon.dm | 2 + code/modules/mob/living/simple_mob/life.dm | 5 + .../mob/living/simple_mob/simple_mob.dm | 4 - code/modules/organs/organ.dm | 6 +- code/modules/organs/organ_external.dm | 8 +- code/modules/power/singularity/singularity.dm | 8 +- code/modules/power/tesla/energy_ball.dm | 4 +- vorestation.dme | 1 + 35 files changed, 376 insertions(+), 106 deletions(-) create mode 100644 code/datums/elements/godmode.dm diff --git a/code/ZAS/Airflow.dm b/code/ZAS/Airflow.dm index 70e32d57b1b..1e75ed49098 100644 --- a/code/ZAS/Airflow.dm +++ b/code/ZAS/Airflow.dm @@ -73,7 +73,7 @@ Contains helper procs for airflow, handled in /connection_group. return 1 /mob/AirflowCanMove(n) - if(status_flags & GODMODE) + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) return 0 if(buckled) return 0 diff --git a/code/ZAS/ConnectionGroup.dm b/code/ZAS/ConnectionGroup.dm index e2a5e7505b6..f021f2e1db0 100644 --- a/code/ZAS/ConnectionGroup.dm +++ b/code/ZAS/ConnectionGroup.dm @@ -99,9 +99,10 @@ Class Procs: //Check for knocking people over if(ismob(M) && differential > vsc.airflow_stun_pressure) - if(M:status_flags & GODMODE) continue - M:airflow_stun() - + var/mob/target = M + if(SEND_SIGNAL(target, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + continue + target.airflow_stun() if(M.check_airflow_movable(differential)) //Check for things that are in range of the midpoint turfs. var/list/close_turfs = list() diff --git a/code/__defines/dcs/signals.dm b/code/__defines/dcs/signals.dm index 24a1c7aa5e5..2a843025788 100644 --- a/code/__defines/dcs/signals.dm +++ b/code/__defines/dcs/signals.dm @@ -337,9 +337,6 @@ #define COMSIG_LIVING_IGNITED "living_ignite" ///from base of mob/living/ExtinguishMob() (/mob/living) #define COMSIG_LIVING_EXTINGUISHED "living_extinguished" -///from base of mob/living/electrocute_act(): (shock_damage, source, siemens_coeff, flags) -#define COMSIG_LIVING_ELECTROCUTE_ACT "living_electrocute_act" -///sent when items with siemen coeff. of 0 block a shock: (power_source, source, siemens_coeff, dist_check) #define COMSIG_LIVING_SHOCK_PREVENTED "living_shock_prevented" ///sent by stuff like stunbatons and tasers: () #define COMSIG_LIVING_MINOR_SHOCK "living_minor_shock" @@ -360,6 +357,48 @@ #define COMSIG_LIVING_LIFE "living_life" ///From /living/handle_disabilities(). #define COMSIG_HANDLE_DISABILITIES "handle_disabilities" +///From /mob/living/proc/updatehealth(). +#define COMSIG_UPDATE_HEALTH "update_health" + #define COMSIG_UPDATE_HEALTH_GOD_MODE (1<<0) //If this will set health to 100 and stat to conscious. + +// Damage specific signals for /mob/living +///from /mob/living/proc/adjustBrainLoss(amount) and /mob/living/proc/setBrainLoss(amount) +#define COMSIG_TAKING_BRAIN_DAMAGE "taking_brain_damage" +///Return this in response if you don't want brain damage to be dealt via the normal proc. + #define COMSIG_CANCEL_BRAIN_DAMAGE (1<<0) +///from /mob/living/proc/adjustOxyLoss(amount) and /mob/living/proc/setOxyLoss(amount) +#define COMSIG_TAKING_OXY_DAMAGE "taking_oxy_damage" +///Return this in response if you don't want brain damage to be dealt via the normal proc. + #define COMSIG_CANCEL_OXY_DAMAGE (1<<0) +///from /mob/living/proc/adjustToxLoss(amount) and /mob/living/proc/setToxLoss(amount) +#define COMSIG_TAKING_TOX_DAMAGE "taking_tox_damage" +///Return this in response if you don't want tox damage to be dealt via the normal proc. + #define COMSIG_CANCEL_TOX_DAMAGE (1<<0) +///from /mob/living/proc/adjustCloneLoss(amount) and /mob/living/proc/setCloneLoss(amount) +#define COMSIG_TAKING_CLONE_DAMAGE "taking_clone_damage" +///Return this in response if you don't want clone damage to be dealt via the normal proc. + #define COMSIG_CANCEL_CLONE_DAMAGE (1<<0) +///from /mob/living/proc/adjustFireLoss(amount, include_robo) +#define COMSIG_TAKING_FIRE_DAMAGE "taking_fire_damage" +///Return this in response if you don't want fire damage to be dealt via the normal proc. + #define COMSIG_CANCEL_FIRE_DAMAGE (1<<0) +///from /mob/living/proc/adjustBruteLoss(amount, include_robo) and /mob/living/carbon/human/adjustBruteLoss(amount, include_robo) +#define COMSIG_TAKING_BRUTE_DAMAGE "taking_brute_damage" +///Return this in response if you don't want brute damage to be dealt via the normal proc. + #define COMSIG_CANCEL_BRUTE_DAMAGE (1<<0) +///from /mob/living/proc/adjustHalLoss(amount) +#define COMSIG_TAKING_HALO_DAMAGE "taking_halo_damage" +///Return this in response if you don't want halo damage to be dealt via the normal proc. + #define COMSIG_CANCEL_HALO_DAMAGE (1<<0) +///from /mob/living/proc/apply_effect(effect, effecttype, blocked, check_protection) +#define COMSIG_TAKING_APPLY_EFFECT "applying_effect" +///Return this in response if you don't want the effect to be applied + #define COMSIG_CANCEL_EFFECT (1<<0) + +///Misc signal for checking for godmode. Used by /datum/element/godmode +#define COMSIG_CHECK_FOR_GODMODE "check_for_godmode" +///Returned by /datum/element/godmode if the target is in godmode and whatever we're checking we want to cancel + #define COMSIG_GODMODE_CANCEL (1<<0) //ALL OF THESE DO NOT TAKE INTO ACCOUNT WHETHER AMOUNT IS 0 OR LOWER AND ARE SENT REGARDLESS! @@ -396,8 +435,19 @@ #define COMSIG_CARBON_EMBED_RIP "item_embed_start_rip" ///called when removing a given item from a mob, from mob/living/carbon/remove_embedded_object(mob/living/carbon/target, /obj/item) #define COMSIG_CARBON_EMBED_REMOVAL "item_embed_remove_safe" +///called when being electrocuted, from /mob/living/carbon/electrocute_act(shock_damage, source, siemens_coeff, def_zone, stun) +#define COMSIG_BEING_ELECTROCUTED "being_electrocuted" + #define COMPONENT_CARBON_CANCEL_ELECTROCUTE (1<<0) //If this is set, the carbon will be not be electrocuted. -// /obj signals + +// /mob/living/silicon signals +///called when a silicon is emp'd. from /mob/living/silicon/emp_act(severity) +#define COMSIG_SILICON_EMP_ACT "silicon_emp_act" + #define COMPONENT_BLOCK_EMP (1<<0) //If this is set, the EMP will not go through. Used by other EMP acts as well. + +// /mob/living/silicon/robot signals +///called when a robot is emp'd. from /mob/living/silicon/robot/emp_act(severity) +#define COMSIG_ROBOT_EMP_ACT "robot_emp_act" ///from base of obj/deconstruct(): (disassembled) #define COMSIG_OBJ_DECONSTRUCT "obj_deconstruct" @@ -582,6 +632,25 @@ ///When the mob's dna and species have been fully applied #define COMSIG_HUMAN_DNA_FINALIZED "human_dna_finished" +// Organ specific signals + +///from /obj/item/organ/external/take_damage(brute, burn, sharp, edge, used_weapon, forbidden_limbs, permutation, projectile) +#define COMSIG_EXTERNAL_ORGAN_PRE_DAMAGE_APPLICATION "external_organ_pre_damage_application" +///Return this in response if you don't want external organ damage to be dealt via the normal proc. + #define COMPONENT_CANCEL_EXTERNAL_ORGAN_DAMAGE (1<<0) +///from /obj/item/organ/external/take_damage(brute, burn, sharp, edge, used_weapon, forbidden_limbs, permutation, projectile) +#define COMSIG_EXTERNAL_ORGAN_POST_DAMAGE_APPLICATION "external_organ_post_damage_application" +///from /obj/item/organ/take_damage(amount, silent) +#define COMSIG_INTERNAL_ORGAN_PRE_DAMAGE_APPLICATION "internal_organ_pre_damage_application" +///Return this in response if you don't want internal organ damage to be dealt via the normal proc. + #define COMPONENT_CANCEL_INTERNAL_ORGAN_DAMAGE (1<<0) +///from /obj/item/organ/take_damage(amount, silent) +#define COMSIG_INTERNAL_ORGAN_POST_DAMAGE_APPLICATION "internal_organ_post_damage_application" +///From /obj/item/organ/external/proc/embed(W, silent) +#define COMSIG_EMBED_OBJECT "embed_object" +///Return this in response if you don't want the embed to go through. + #define COMSIG_CANCEL_EMBED (1<<0) + // /datum/species signals ///from datum/species/on_species_gain(): (datum/species/new_species, datum/species/old_species) diff --git a/code/__defines/mobs.dm b/code/__defines/mobs.dm index 3a7a666b9b8..32552b0e62d 100644 --- a/code/__defines/mobs.dm +++ b/code/__defines/mobs.dm @@ -4,17 +4,17 @@ #define DEAD 2 // Bitflags defining which status effects could be or are inflicted on a mob. -#define CANSTUN 0x1 -#define CANWEAKEN 0x2 -#define CANPARALYSE 0x4 -#define CANPUSH 0x8 -#define LEAPING 0x10 -#define HIDING 0x20 -#define PASSEMOTES 0x40 // Mob has a cortical borer or holders inside of it that need to see emotes. -#define GODMODE 0x1000 -#define FAKEDEATH 0x2000 // Replaces stuff like changeling.changeling_fakedeath. -#define DISFIGURED 0x4000 // Set but never checked. Remove this sometime and replace occurences with the appropriate organ code -#define DOING_TASK 0x8000 // Performing a do_after or do_mob that's exclusive +#define CANSTUN 0x1 +#define CANWEAKEN 0x2 +#define CANPARALYSE 0x4 +#define CANPUSH 0x8 +#define LEAPING 0x10 +#define HIDING 0x20 +#define PASSEMOTES 0x40 // Mob has a cortical borer or holders inside of it that need to see emotes. +#define FAKEDEATH 0x1000 // Replaces stuff like changeling.changeling_fakedeath. +#define DISFIGURED 0x2000 // Set but never checked. Remove this sometime and replace occurences with the appropriate organ code +#define DOING_TASK 0x4000 // Performing a do_after or do_mob that's exclusive +#define GODMODE 0x8000 // If we have godmode enabled or not. // Grab levels. #define GRAB_PASSIVE 1 diff --git a/code/__defines/vv.dm b/code/__defines/vv.dm index ec2cb77b0b6..307056f8cdb 100644 --- a/code/__defines/vv.dm +++ b/code/__defines/vv.dm @@ -124,7 +124,7 @@ #define VV_HK_GIVE_SPELL "give_spell" #define VV_HK_REMOVE_SPELL "remove_spell" #define VV_HK_GIVE_DISEASE "give_disease" -#define VV_HK_GODMODE "godmode" +#define VV_HK_GODMODE "toggle_godmode" #define VV_HK_DROP_ALL "dropall" #define VV_HK_REGEN_ICONS "regen_icons" #define VV_HK_REGEN_ICONS_FULL "regen_icons_full" diff --git a/code/datums/elements/godmode.dm b/code/datums/elements/godmode.dm new file mode 100644 index 00000000000..b83297b4b2a --- /dev/null +++ b/code/datums/elements/godmode.dm @@ -0,0 +1,128 @@ +/** + * Attached to mobs. Gives them godmode by stopping damage, effects, embeds, among all other negative effects. + */ +/datum/element/godmode + element_flags = ELEMENT_DETACH_ON_HOST_DESTROY|ELEMENT_BESPOKE + argument_hash_start_idx = 2 + +/datum/element/godmode/Attach(datum/target) + . = ..() + //Must be appliied to mobs. + if(!ismob(target)) + return ELEMENT_INCOMPATIBLE + var/mob/our_target = target + if(our_target.status_flags & GODMODE) //Already have it. + return ELEMENT_INCOMPATIBLE + our_target.status_flags |= GODMODE + + if(ishuman(target)) + RegisterSignal(target, COMSIG_EXTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, PROC_REF(on_external_damaged)) + RegisterSignal(target, COMSIG_INTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, PROC_REF(on_internal_damaged)) + + if(issilicon(target)) + RegisterSignal(target, COMSIG_SILICON_EMP_ACT, PROC_REF(on_emp)) + + if(isrobot(target)) + RegisterSignal(target, COMSIG_ROBOT_EMP_ACT, PROC_REF(on_emp)) + + //Four main damage types: Brute, Burn, Oxy, Tox + RegisterSignal(target, COMSIG_TAKING_OXY_DAMAGE, PROC_REF(on_oxygen_damage)) + RegisterSignal(target, COMSIG_TAKING_TOX_DAMAGE, PROC_REF(on_tox_damage)) + RegisterSignal(target, COMSIG_TAKING_FIRE_DAMAGE, PROC_REF(on_fire_damage)) + RegisterSignal(target, COMSIG_TAKING_BRUTE_DAMAGE, PROC_REF(on_brute_damage)) + + //Rarer types, such as Brain, Clone, Halloss + RegisterSignal(target, COMSIG_TAKING_BRAIN_DAMAGE, PROC_REF(on_brain_damage)) + RegisterSignal(target, COMSIG_TAKING_CLONE_DAMAGE, PROC_REF(on_clone_damage)) + RegisterSignal(target, COMSIG_TAKING_HALO_DAMAGE, PROC_REF(on_halo_damage)) + + //Things such as update health. + RegisterSignal(target, COMSIG_UPDATE_HEALTH, PROC_REF(on_update_health)) + RegisterSignal(target, COMSIG_TAKING_APPLY_EFFECT, PROC_REF(on_apply_effect)) + + //For things that don't fall into a single bucket + RegisterSignal(target, COMSIG_CHECK_FOR_GODMODE, PROC_REF(godmode_check)) + RegisterSignal(target, COMSIG_BEING_ELECTROCUTED, PROC_REF(on_electrocute)) + RegisterSignal(target, COMSIG_EMBED_OBJECT, PROC_REF(embed_check)) + + +/datum/element/godmode/Detach(atom/movable/target) + //Human specific comsigs: + if(ishuman(target)) + UnregisterSignal(target, list(COMSIG_EXTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, COMSIG_INTERNAL_ORGAN_PRE_DAMAGE_APPLICATION)) + + if(issilicon(target)) + UnregisterSignal(target, list(COMSIG_SILICON_EMP_ACT)) + + if(isrobot(target)) + UnregisterSignal(target, list(COMSIG_ROBOT_EMP_ACT)) + + //All the general comsigs. + UnregisterSignal(target, list(COMSIG_TAKING_OXY_DAMAGE, COMSIG_TAKING_TOX_DAMAGE, COMSIG_TAKING_FIRE_DAMAGE, \ + COMSIG_TAKING_BRUTE_DAMAGE, COMSIG_TAKING_BRAIN_DAMAGE, COMSIG_TAKING_CLONE_DAMAGE, COMSIG_TAKING_HALO_DAMAGE, \ + COMSIG_UPDATE_HEALTH, COMSIG_TAKING_APPLY_EFFECT, COMSIG_CHECK_FOR_GODMODE, COMSIG_BEING_ELECTROCUTED, COMSIG_EMBED_OBJECT)) + var/mob/our_target = target + + //And finally, remove the fact we're in godmode. + our_target.status_flags &= ~GODMODE + return ..() + +/datum/element/godmode/proc/on_external_damaged() + SIGNAL_HANDLER + return COMPONENT_CANCEL_EXTERNAL_ORGAN_DAMAGE + +/datum/element/godmode/proc/on_internal_damaged() + SIGNAL_HANDLER + return COMPONENT_CANCEL_INTERNAL_ORGAN_DAMAGE + +/datum/element/godmode/proc/on_brain_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_BRAIN_DAMAGE + +/datum/element/godmode/proc/on_oxygen_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_OXY_DAMAGE + +/datum/element/godmode/proc/on_tox_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_TOX_DAMAGE + +/datum/element/godmode/proc/on_clone_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_CLONE_DAMAGE + +/datum/element/godmode/proc/on_fire_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_FIRE_DAMAGE + +/datum/element/godmode/proc/on_brute_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_BRUTE_DAMAGE + +/datum/element/godmode/proc/on_halo_damage() + SIGNAL_HANDLER + return COMSIG_CANCEL_HALO_DAMAGE + +/datum/element/godmode/proc/on_update_health() + SIGNAL_HANDLER + return COMSIG_UPDATE_HEALTH_GOD_MODE + +/datum/element/godmode/proc/on_apply_effect() + SIGNAL_HANDLER + return COMSIG_CANCEL_EFFECT + +/datum/element/godmode/proc/on_electrocute() + SIGNAL_HANDLER + return COMPONENT_CARBON_CANCEL_ELECTROCUTE + +/datum/element/godmode/proc/embed_check() + SIGNAL_HANDLER + return COMSIG_CANCEL_EMBED + +/datum/element/godmode/proc/on_emp() + SIGNAL_HANDLER + return COMPONENT_BLOCK_EMP + +/datum/element/godmode/proc/godmode_check() + SIGNAL_HANDLER + return COMSIG_GODMODE_CANCEL diff --git a/code/game/gamemodes/cult/narsie.dm b/code/game/gamemodes/cult/narsie.dm index f303b806e83..d245ecaeced 100644 --- a/code/game/gamemodes/cult/narsie.dm +++ b/code/game/gamemodes/cult/narsie.dm @@ -75,8 +75,8 @@ var/global/narsie_cometh = 0 /obj/singularity/narsie/mezzer() for(var/mob/living/carbon/M in oviewers(8, src)) if(M.stat == CONSCIOUS) - if(M.status_flags & GODMODE) - continue + if(SEND_SIGNAL(M, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component if(!iscultist(M)) to_chat(M, span_danger("You feel your sanity crumble away in an instant as you gaze upon [src.name]...")) M.apply_effect(3, STUN) @@ -169,8 +169,8 @@ var/global/narsie_cometh = 0 if (istype(A, /mob/) && (get_dist(A, src) <= 7)) var/mob/M = A - if(M.status_flags & GODMODE) - return 0 + if(SEND_SIGNAL(M, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component M.cultify() @@ -201,8 +201,8 @@ var/global/narsie_cometh = 0 if (istype(A, /mob/living/)) var/mob/living/C2 = A - if(C2.status_flags & GODMODE) - return 0 + if(SEND_SIGNAL(C2, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component C2.dust() // Changed from gib(), just for less lag. @@ -233,8 +233,8 @@ var/global/narsie_cometh = 0 if (istype(A, /mob/living/)) var/mob/living/C2 = A - if(C2.status_flags & GODMODE) - return 0 + if(SEND_SIGNAL(C2, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component C2.dust() // Changed from gib(), just for less lag. diff --git a/code/game/gamemodes/cult/runes.dm b/code/game/gamemodes/cult/runes.dm index 8586aae1f0b..60c8c4d7d7f 100644 --- a/code/game/gamemodes/cult/runes.dm +++ b/code/game/gamemodes/cult/runes.dm @@ -475,7 +475,7 @@ var/list/sacrificed = list() chose_name = 1 break D.universal_speak = 1 - D.status_flags &= ~GODMODE + D.RemoveElement(/datum/element/godmode) D.b_eyes = 200 D.r_eyes = 200 D.g_eyes = 200 diff --git a/code/game/gamemodes/cult/soulstone.dm b/code/game/gamemodes/cult/soulstone.dm index c02a754ba86..c314b22f0d0 100644 --- a/code/game/gamemodes/cult/soulstone.dm +++ b/code/game/gamemodes/cult/soulstone.dm @@ -74,7 +74,7 @@ if ("Summon") for(var/mob/living/simple_mob/construct/shade/A in src) - A.status_flags &= ~GODMODE + A.RemoveElement(/datum/element/godmode) A.canmove = 1 to_chat(A, span_infoplain(span_bold("You have been released from your prison, but you are still bound to [U.name]'s will. Help them suceed in their goals at all costs."))) A.forceMove(U.loc) @@ -134,7 +134,7 @@ var/mob/living/simple_mob/construct/shade/S = new /mob/living/simple_mob/construct/shade( T.loc ) S.forceMove(src) //put shade in stone - S.status_flags |= GODMODE //So they won't die inside the stone somehow + S.AddElement(/datum/element/godmode) S.canmove = 0//Can't move out of the soul stone S.name = "Shade of [T.real_name]" S.real_name = "Shade of [T.real_name]" @@ -170,7 +170,7 @@ return T.forceMove(src) //put shade in stone - T.status_flags |= GODMODE + T.AddElement(/datum/element/godmode) T.canmove = 0 T.health = T.getMaxHealth() src.icon_state = "soulstone2" diff --git a/code/modules/admin/verbs/randomverbs.dm b/code/modules/admin/verbs/randomverbs.dm index 9987f10ebc8..17223821621 100644 --- a/code/modules/admin/verbs/randomverbs.dm +++ b/code/modules/admin/verbs/randomverbs.dm @@ -158,20 +158,24 @@ ADMIN_VERB(drop_everything, R_ADMIN, "Drop Everything", ADMIN_VERB_NO_DESCRIPTIO /client/proc/cmd_admin_godmode(mob/M as mob in GLOB.mob_list) set category = "Admin.Game" - set name = "Godmode" + set name = "Toggle Godmode" if(!check_rights_for(src, R_HOLDER)) return - M.status_flags ^= GODMODE + if(M.status_flags & GODMODE) + M.RemoveElement(/datum/element/godmode) + + else if(!(M.status_flags & GODMODE)) + M.AddElement(/datum/element/godmode) + to_chat(usr, span_blue("Toggled [(M.status_flags & GODMODE) ? "ON" : "OFF"]")) - log_admin("[key_name(usr)] has toggled [key_name(M)]'s nodamage to [(M.status_flags & GODMODE) ? "On" : "Off"]") - var/msg = "[key_name_admin(usr)] has toggled [ADMIN_LOOKUPFLW(M)]'s nodamage to [(M.status_flags & GODMODE) ? "On" : "Off"]" + log_admin("[key_name(usr)] has toggled [key_name(M)]'s godmode to [(M.status_flags & GODMODE) ? "On" : "Off"]") + var/msg = "[key_name_admin(usr)] has toggled [ADMIN_LOOKUPFLW(M)]'s godmode to [(M.status_flags & GODMODE) ? "On" : "Off"]" message_admins(msg) admin_ticket_log(M, msg) - feedback_add_details("admin_verb","GOD") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc! - + feedback_add_details("admin_verb","GOD_ENABLE") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc! /proc/cmd_admin_mute(mob/M as mob, mute_type, automute = 0) if(automute) diff --git a/code/modules/mob/freelook/eye.dm b/code/modules/mob/freelook/eye.dm index 1cf279ddba2..fc46c6a678c 100644 --- a/code/modules/mob/freelook/eye.dm +++ b/code/modules/mob/freelook/eye.dm @@ -15,7 +15,6 @@ var/owner_follows_eye = 0 see_in_dark = 7 - status_flags = GODMODE plane = PLANE_AI_EYE invisibility = INVISIBILITY_EYE @@ -27,6 +26,10 @@ var/use_static = TRUE var/static_visibility_range = 16 +/mob/observer/eye/Initialize(mapload) + . = ..() + AddElement(/datum/element/godmode) + /mob/observer/eye/Destroy() if(owner) if(owner.eyeobj == src) diff --git a/code/modules/mob/living/bot/bot.dm b/code/modules/mob/living/bot/bot.dm index b6f507d7a64..a8c14c69d5a 100644 --- a/code/modules/mob/living/bot/bot.dm +++ b/code/modules/mob/living/bot/bot.dm @@ -95,7 +95,7 @@ . += span_info("You can use a crowbar to remove it.") */ /mob/living/bot/updatehealth() - if(status_flags & GODMODE) + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) health = getMaxHealth() set_stat(CONSCIOUS) else @@ -104,6 +104,9 @@ toxloss = 0 cloneloss = 0 halloss = 0 + if(health <= -getMaxHealth()) //die only once + death() + return /mob/living/bot/death() explode() diff --git a/code/modules/mob/living/carbon/alien/life.dm b/code/modules/mob/living/carbon/alien/life.dm index b8fb2c550fd..6003efd2c22 100644 --- a/code/modules/mob/living/carbon/alien/life.dm +++ b/code/modules/mob/living/carbon/alien/life.dm @@ -35,7 +35,8 @@ /mob/living/carbon/alien/handle_regular_status_updates() - if(status_flags & GODMODE) return 0 + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) //I don't want to go in and do HUD stuff imediately, so... no. + return 0 // Cancelled by a component if(stat == DEAD) blinded = 1 diff --git a/code/modules/mob/living/carbon/brain/life.dm b/code/modules/mob/living/carbon/brain/life.dm index 48ff3d6268e..0f01ac3e826 100644 --- a/code/modules/mob/living/carbon/brain/life.dm +++ b/code/modules/mob/living/carbon/brain/life.dm @@ -55,7 +55,8 @@ return //TODO: DEFERRED /mob/living/carbon/brain/proc/handle_temperature_damage(body_part, exposed_temperature, exposed_intensity) - if(status_flags & GODMODE) return + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component if(exposed_temperature > bodytemperature) var/discomfort = min( abs(exposed_temperature - bodytemperature)*(exposed_intensity)/2000000, 1.0) diff --git a/code/modules/mob/living/carbon/carbon.dm b/code/modules/mob/living/carbon/carbon.dm index d92fb8f2c07..22fe0c7a240 100644 --- a/code/modules/mob/living/carbon/carbon.dm +++ b/code/modules/mob/living/carbon/carbon.dm @@ -120,7 +120,8 @@ ..() /mob/living/carbon/electrocute_act(var/shock_damage, var/obj/source, var/siemens_coeff = 1.0, var/def_zone = null, var/stun = 1) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_BEING_ELECTROCUTED, shock_damage, source, siemens_coeff, def_zone, stun) & COMPONENT_CARBON_CANCEL_ELECTROCUTE) + return 0 // Cancelled by a component if(def_zone == BP_L_HAND || def_zone == BP_R_HAND) //Diona (And any other potential plant people) hands don't get shocked. if(species.flags & IS_PLANT) return 0 diff --git a/code/modules/mob/living/carbon/human/human.dm b/code/modules/mob/living/carbon/human/human.dm index d5565ec657d..90ff247ea5e 100644 --- a/code/modules/mob/living/carbon/human/human.dm +++ b/code/modules/mob/living/carbon/human/human.dm @@ -373,9 +373,10 @@ //Removed the horrible safety parameter. It was only being used by ninja code anyways. //Now checks siemens_coefficient of the affected area by default -/mob/living/carbon/human/electrocute_act(var/shock_damage, var/obj/source, var/base_siemens_coeff = 1.0, var/def_zone = null) +/mob/living/carbon/human/electrocute_act(var/shock_damage, var/obj/source, var/siemens_coeff = 1.0, var/def_zone = null, var/stun) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_BEING_ELECTROCUTED, shock_damage, source, siemens_coeff, def_zone, stun) & COMPONENT_CARBON_CANCEL_ELECTROCUTE) + return 0 // Cancelled by a component if (!def_zone) def_zone = pick(BP_L_HAND, BP_R_HAND) @@ -388,7 +389,7 @@ return var/obj/item/organ/external/affected_organ = get_organ(check_zone(def_zone)) - var/siemens_coeff = base_siemens_coeff * get_siemens_coefficient_organ(affected_organ) + siemens_coeff = siemens_coeff * get_siemens_coefficient_organ(affected_organ) if(fire_stacks < 0) // Water makes you more conductive. siemens_coeff *= 1.5 diff --git a/code/modules/mob/living/carbon/human/human_damage.dm b/code/modules/mob/living/carbon/human/human_damage.dm index 3433c456ec8..7c1c357a75e 100644 --- a/code/modules/mob/living/carbon/human/human_damage.dm +++ b/code/modules/mob/living/carbon/human/human_damage.dm @@ -2,7 +2,7 @@ /mob/living/carbon/human/updatehealth() var/huskmodifier = 2.5 // With 1.5, you need 250 burn instead of 200 to husk a human. - if(status_flags & GODMODE) + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) health = getMaxHealth() set_stat(CONSCIOUS) return @@ -16,15 +16,20 @@ total_burn += O.burn_dam health = getMaxHealth() - getOxyLoss() - getToxLoss() - getCloneLoss() - total_burn - total_brute - //TODO: fix husking if( ((getMaxHealth() - total_burn) < (-getMaxHealth()) * huskmodifier) && stat == DEAD) ChangeToHusk() + if(health <= -getMaxHealth()) //die only once + death() + return + handle_shock() + handle_pain() return /mob/living/carbon/human/adjustBrainLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_BRAIN_DAMAGE, amount) & COMSIG_CANCEL_BRAIN_DAMAGE) + return 0 // Cancelled by a component if(should_have_organ(O_BRAIN)) var/obj/item/organ/internal/brain/sponge = internal_organs_by_name[O_BRAIN] @@ -38,7 +43,8 @@ /mob/living/carbon/human/setBrainLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_BRAIN_DAMAGE, amount) & COMSIG_CANCEL_BRAIN_DAMAGE) + return 0 // Cancelled by a component if(should_have_organ(O_BRAIN)) var/obj/item/organ/internal/brain/sponge = internal_organs_by_name[O_BRAIN] @@ -52,7 +58,8 @@ /mob/living/carbon/human/getBrainLoss() - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) //I don't want to go in and do HUD stuff imediately, so... no. + return 0 // Cancelled by a component if(should_have_organ(O_BRAIN)) var/obj/item/organ/internal/brain/sponge = internal_organs_by_name[O_BRAIN] @@ -111,6 +118,8 @@ //'include_robo' only applies to healing, for legacy purposes, as all damage typically hurts both types of organs /mob/living/carbon/human/adjustBruteLoss(var/amount,var/include_robo) + if(SEND_SIGNAL(src, COMSIG_TAKING_BRUTE_DAMAGE, amount) & COMSIG_CANCEL_BRUTE_DAMAGE) + return 0 // Cancelled by a component amount = amount*species.brute_mod if(amount > 0) for(var/datum/modifier/M in modifiers) @@ -419,7 +428,6 @@ In most cases it makes more sense to use apply_damage() instead! And make sure t // damage MANY external organs, in random order /mob/living/carbon/human/take_overall_damage(var/brute, var/burn, var/sharp = FALSE, var/edge = FALSE, var/used_weapon = null) - if(status_flags & GODMODE) return //godmode var/list/obj/item/organ/external/parts = get_damageable_organs() var/update = 0 while(parts.len && (brute>0 || burn>0) ) diff --git a/code/modules/mob/living/carbon/human/human_species.dm b/code/modules/mob/living/carbon/human/human_species.dm index b09d7b1a46d..c2f7f2daa09 100644 --- a/code/modules/mob/living/carbon/human/human_species.dm +++ b/code/modules/mob/living/carbon/human/human_species.dm @@ -1,12 +1,13 @@ /mob/living/carbon/human/dummy real_name = "Test Dummy" - status_flags = GODMODE|CANPUSH + status_flags = CANPUSH has_huds = FALSE blocks_emissive = FALSE no_vore = TRUE //Dummies don't need bellies. /mob/living/carbon/human/dummy/Initialize(mapload) . = ..() + AddElement(/datum/element/godmode) GLOB.mob_list -= src GLOB.living_mob_list -= src GLOB.dead_mob_list -= src diff --git a/code/modules/mob/living/carbon/human/life.dm b/code/modules/mob/living/carbon/human/life.dm index 5d1a24ac638..ae78bee05d5 100644 --- a/code/modules/mob/living/carbon/human/life.dm +++ b/code/modules/mob/living/carbon/human/life.dm @@ -523,8 +523,8 @@ /mob/living/carbon/human/handle_breath(datum/gas_mixture/breath) - if(status_flags & GODMODE) - return + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component if(mNobreath in mutations) return @@ -910,8 +910,8 @@ // +/- 50 degrees from 310.15K is the 'safe' zone, where no damage is dealt. if(bodytemperature >= species.heat_level_1) //Body temperature is too hot. - if(status_flags & GODMODE) - return 1 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 1 // Cancelled by a component var/burn_dam = 0 @@ -933,8 +933,8 @@ else if(bodytemperature <= species.cold_level_1) //Body temperature is too cold. - if(status_flags & GODMODE) - return 1 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 1 // Cancelled by a component if(!istype(loc, /obj/machinery/atmospherics/unary/cryo_cell)) @@ -954,8 +954,8 @@ // Account for massive pressure differences. Done by Polymorph // Made it possible to actually have something that can protect against high pressure... Done by Errorage. Polymorph now has an axe sticking from his head for his previous hardcoded nonsense! - if(status_flags & GODMODE) - return 1 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 1 // Cancelled by a component if(adjusted_pressure >= species.hazard_high_pressure) var/pressure_damage = min( ( (adjusted_pressure / species.hazard_high_pressure) -1 )*PRESSURE_DAMAGE_COEFFICIENT , MAX_HIGH_PRESSURE_DAMAGE) @@ -1151,11 +1151,10 @@ r_hand_blocked = 1-(100-getarmor(BP_R_HAND, "bio"))/100 //This should get a number between 0 and 1 total_phoronloss += vsc.plc.CONTAMINATION_LOSS * r_hand_blocked if(total_phoronloss) - if(!(status_flags & GODMODE)) - adjustToxLoss(total_phoronloss) + adjustToxLoss(total_phoronloss) - if(status_flags & GODMODE) - return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component // nutrition decrease // Species controls hunger rate for humans, otherwise use defaults @@ -1201,7 +1200,8 @@ if(skip_some_updates()) return 0 - if(status_flags & GODMODE) return 0 + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component //SSD check, if a logged player is awake put them back to sleep! if(species.get_ssd(src) && !client && !teleop) @@ -1842,7 +1842,8 @@ /mob/living/carbon/human/handle_shock() ..() - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component if(traumatic_shock >= 80 && can_feel_pain()) shock_stage += 1 else diff --git a/code/modules/mob/living/damage_procs.dm b/code/modules/mob/living/damage_procs.dm index d4dfd1c483b..3dc4dc9f64c 100644 --- a/code/modules/mob/living/damage_procs.dm +++ b/code/modules/mob/living/damage_procs.dm @@ -178,6 +178,8 @@ /mob/living/proc/apply_effects(var/stun = 0, var/weaken = 0, var/paralyze = 0, var/irradiate = 0, var/stutter = 0, var/eyeblur = 0, var/drowsy = 0, var/agony = 0, var/blocked = 0, var/ignite = 0, var/flammable = 0) + if(SEND_SIGNAL(src, COMSIG_TAKING_APPLY_EFFECT) & COMSIG_CANCEL_EFFECT) + return 0 // Cancelled by a component if(blocked >= 100) return 0 if(stun) apply_effect(stun, STUN, blocked) diff --git a/code/modules/mob/living/living.dm b/code/modules/mob/living/living.dm index 724179cd855..a901fe24a77 100644 --- a/code/modules/mob/living/living.dm +++ b/code/modules/mob/living/living.dm @@ -170,8 +170,8 @@ manual_afk = TRUE /mob/living/proc/updatehealth() - if(status_flags & GODMODE) - health = 100 + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) + health = getMaxHealth() set_stat(CONSCIOUS) else // Pain/etc calculations, but more efficient:tm: - this should work for literally anything that applies to health. Far better than slapping emote("pain") everywhere like scream does. @@ -196,6 +196,9 @@ if(51 to INFINITY) if(prob(pain_noise * 3) && !isbelly(loc)) // More likely, most severe damage. No pain noises inside bellies. emote("pain") + if(health <= -getMaxHealth()) //die only once + death() + return //This proc is used for mobs which are affected by pressure to calculate the amount of pressure that actually //affects them once clothing is factored in. ~Errorage @@ -259,7 +262,8 @@ //'include_robo' only applies to healing, for legacy purposes, as all damage typically hurts both types of organs /mob/living/proc/adjustBruteLoss(var/amount,var/include_robo) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_BRUTE_DAMAGE, amount) & COMSIG_CANCEL_BRUTE_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) @@ -288,7 +292,8 @@ return oxyloss /mob/living/proc/adjustOxyLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_OXY_DAMAGE, amount) & COMSIG_CANCEL_OXY_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) @@ -309,14 +314,16 @@ updatehealth() /mob/living/proc/setOxyLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_OXY_DAMAGE, amount) & COMSIG_CANCEL_OXY_DAMAGE) + return 0 // Cancelled by a component oxyloss = amount /mob/living/proc/getToxLoss() return toxloss /mob/living/proc/adjustToxLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_TOX_DAMAGE, amount) & COMSIG_CANCEL_TOX_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) @@ -337,7 +344,8 @@ updatehealth() /mob/living/proc/setToxLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_TOX_DAMAGE, amount) & COMSIG_CANCEL_TOX_DAMAGE) + return 0 // Cancelled by a component toxloss = amount /mob/living/proc/getFireLoss() @@ -351,7 +359,8 @@ //'include_robo' only applies to healing, for legacy purposes, as all damage typically hurts both types of organs /mob/living/proc/adjustFireLoss(var/amount,var/include_robo) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_FIRE_DAMAGE, amount) & COMSIG_CANCEL_FIRE_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) if(!isnull(M.incoming_damage_percent)) @@ -377,7 +386,8 @@ return cloneloss /mob/living/proc/adjustCloneLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_CLONE_DAMAGE, amount) & COMSIG_CANCEL_CLONE_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) @@ -398,25 +408,29 @@ updatehealth() /mob/living/proc/setCloneLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_CLONE_DAMAGE, amount) & COMSIG_CANCEL_CLONE_DAMAGE) + return 0 // Cancelled by a component cloneloss = amount /mob/living/proc/getBrainLoss() return brainloss /mob/living/proc/adjustBrainLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_BRAIN_DAMAGE, amount) & COMSIG_CANCEL_BRAIN_DAMAGE) + return 0 // Cancelled by a component brainloss = min(max(brainloss + amount, 0),(getMaxHealth()*2)) /mob/living/proc/setBrainLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_BRAIN_DAMAGE, amount) & COMSIG_CANCEL_BRAIN_DAMAGE) + return 0 // Cancelled by a component brainloss = amount /mob/living/proc/getHalLoss() return halloss /mob/living/proc/adjustHalLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_HALO_DAMAGE, amount) & COMSIG_CANCEL_HALO_DAMAGE) + return 0 // Cancelled by a component if(amount > 0) for(var/datum/modifier/M in modifiers) if(M.energy_based && (!isnull(M.incoming_hal_damage_percent) || !isnull(M.disable_duration_percent))) @@ -436,7 +450,8 @@ updatehealth() /mob/living/proc/setHalLoss(var/amount) - if(status_flags & GODMODE) return 0 //godmode + if(SEND_SIGNAL(src, COMSIG_TAKING_HALO_DAMAGE, amount) & COMSIG_CANCEL_HALO_DAMAGE) + return 0 // Cancelled by a component halloss = amount // Use this to get a mob's max health whenever possible. Reading maxHealth directly will give inaccurate results if any modifiers exist. diff --git a/code/modules/mob/living/living_defense.dm b/code/modules/mob/living/living_defense.dm index 54c6a2429b5..9192157009a 100644 --- a/code/modules/mob/living/living_defense.dm +++ b/code/modules/mob/living/living_defense.dm @@ -596,7 +596,6 @@ // damage ONE external organ, organ gets randomly selected from damaged ones. /mob/living/proc/take_organ_damage(var/brute, var/burn, var/emp=0) - if(status_flags & GODMODE) return 0 //godmode adjustBruteLoss(brute) adjustFireLoss(burn) src.updatehealth() @@ -609,7 +608,6 @@ // damage MANY external organs, in random order /mob/living/proc/take_overall_damage(var/brute, var/burn, var/used_weapon = null) - if(status_flags & GODMODE) return 0 //godmode adjustBruteLoss(brute) adjustFireLoss(burn) src.updatehealth() diff --git a/code/modules/mob/living/silicon/ai/life.dm b/code/modules/mob/living/silicon/ai/life.dm index 349579a7fda..708f659ea22 100644 --- a/code/modules/mob/living/silicon/ai/life.dm +++ b/code/modules/mob/living/silicon/ai/life.dm @@ -168,12 +168,15 @@ return ((!A.power_equip) && A.requires_power == 1 || istype(T, /turf/space)) && !istype(src.loc,/obj/item) /mob/living/silicon/ai/updatehealth() - if(status_flags & GODMODE) - health = 100 + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) + health = getMaxHealth() set_stat(CONSCIOUS) setOxyLoss(0) else - health = 100 - getFireLoss() - getBruteLoss() // Oxyloss is not part of health as it represents AIs backup power. AI is immune against ToxLoss as it is machine. + health = getMaxHealth() - getFireLoss() - getBruteLoss() // Oxyloss is not part of health as it represents AIs backup power. AI is immune against ToxLoss as it is machine. + if(health <= -getMaxHealth()) //die only once + death() + return /mob/living/silicon/ai/rejuvenate() ..() diff --git a/code/modules/mob/living/silicon/decoy/life.dm b/code/modules/mob/living/silicon/decoy/life.dm index de818ef473d..a61eea9c3b6 100644 --- a/code/modules/mob/living/silicon/decoy/life.dm +++ b/code/modules/mob/living/silicon/decoy/life.dm @@ -8,8 +8,11 @@ /mob/living/silicon/decoy/updatehealth() - if(status_flags & GODMODE) - health = 100 + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) + health = getMaxHealth() set_stat(CONSCIOUS) else - health = 100 - getOxyLoss() - getToxLoss() - getFireLoss() - getBruteLoss() + health = getMaxHealth() - getOxyLoss() - getToxLoss() - getFireLoss() - getBruteLoss() + if(health <= -getMaxHealth()) //die only once + death() + return diff --git a/code/modules/mob/living/silicon/pai/life.dm b/code/modules/mob/living/silicon/pai/life.dm index 683c1ffac8e..c396eb8ea6f 100644 --- a/code/modules/mob/living/silicon/pai/life.dm +++ b/code/modules/mob/living/silicon/pai/life.dm @@ -44,8 +44,11 @@ adjustFireLoss(-0.5) /mob/living/silicon/pai/updatehealth() - if(status_flags & GODMODE) - health = 100 + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) + health = getMaxHealth() set_stat(CONSCIOUS) else - health = 100 - getBruteLoss() - getFireLoss() + health = getMaxHealth() - getBruteLoss() - getFireLoss() + if(health <= -getMaxHealth()) //die only once + death() + return diff --git a/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper.dm b/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper.dm index 765bdb6045d..1f5dbcac069 100644 --- a/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper.dm +++ b/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper.dm @@ -584,7 +584,9 @@ //Burn all the mobs or add them to the exclusion list for(var/mob/living/T in (touchable_items)) touchable_items -= T //Exclude mobs from loose item picking. - if((T.status_flags & GODMODE) || !T.digestable) + if(SEND_SIGNAL(T, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + items_preserved |= T + else if(!T.digestable) items_preserved |= T else var/old_brute = T.getBruteLoss() diff --git a/code/modules/mob/living/silicon/robot/robot_damage.dm b/code/modules/mob/living/silicon/robot/robot_damage.dm index 2ecfe99f1c3..4085d4b5353 100644 --- a/code/modules/mob/living/silicon/robot/robot_damage.dm +++ b/code/modules/mob/living/silicon/robot/robot_damage.dm @@ -1,9 +1,12 @@ /mob/living/silicon/robot/updatehealth() - if(status_flags & GODMODE) + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) health = getMaxHealth() set_stat(CONSCIOUS) return health = getMaxHealth() - (getBruteLoss() + getFireLoss()) + if(health <= -getMaxHealth()) //die only once + death() + return return /mob/living/silicon/robot/getMaxHealth() @@ -115,7 +118,8 @@ parts -= picked /mob/living/silicon/robot/take_overall_damage(var/brute = 0, var/burn = 0, var/sharp = FALSE, var/used_weapon = null) - if(status_flags & GODMODE) return //godmode + if(SEND_SIGNAL(src, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) //Normally we'd let this proc continue on, but it's much less time consumptive to just do a godmode check here. + return 0 // Cancelled by a component var/list/datum/robot_component/parts = get_damageable_components() //Combat shielding absorbs a percentage of damage directly into the cell. @@ -153,5 +157,7 @@ parts -= picked /mob/living/silicon/robot/emp_act(severity) + if(SEND_SIGNAL(src, COMSIG_ROBOT_EMP_ACT, severity) & COMPONENT_BLOCK_EMP) + return // Cancelled by a component uneq_all() ..() //Damage is handled at /silicon/ level. diff --git a/code/modules/mob/living/silicon/silicon.dm b/code/modules/mob/living/silicon/silicon.dm index a874af809e4..d1343f0d574 100644 --- a/code/modules/mob/living/silicon/silicon.dm +++ b/code/modules/mob/living/silicon/silicon.dm @@ -63,6 +63,8 @@ return /mob/living/silicon/emp_act(severity) + if(SEND_SIGNAL(src, COMSIG_SILICON_EMP_ACT, severity) & COMPONENT_BLOCK_EMP) + return switch(severity) if(1) src.take_organ_damage(0,20,emp=1) diff --git a/code/modules/mob/living/simple_mob/life.dm b/code/modules/mob/living/simple_mob/life.dm index f20f55e7803..0046f723f39 100644 --- a/code/modules/mob/living/simple_mob/life.dm +++ b/code/modules/mob/living/simple_mob/life.dm @@ -23,6 +23,11 @@ //Should we be dead? /mob/living/simple_mob/updatehealth() + if(SEND_SIGNAL(src, COMSIG_UPDATE_HEALTH) & COMSIG_UPDATE_HEALTH_GOD_MODE) + health = getMaxHealth() + set_stat(CONSCIOUS) + return + get_injury_level() health = getMaxHealth() - getFireLoss() - getBruteLoss() - getToxLoss() - getOxyLoss() - getCloneLoss() //Alive, becoming dead diff --git a/code/modules/mob/living/simple_mob/simple_mob.dm b/code/modules/mob/living/simple_mob/simple_mob.dm index 95532497a40..f360c5c7ea3 100644 --- a/code/modules/mob/living/simple_mob/simple_mob.dm +++ b/code/modules/mob/living/simple_mob/simple_mob.dm @@ -370,10 +370,6 @@ var/totaldelay = round(rand(1,3) * damage_fatigue_mult * clamp(((rand(2,5) * (h / getMaxHealth())) - rand(0,2)), 1, 5)) // totaldelay is how much delay we're going to feed into attacks and movement. Do NOT change this formula unless you know how to math. injury_level = totaldelay // Adds our returned slowdown to the mob's injury level -/mob/living/simple_mob/updatehealth() // We don't want to fully override the check, just hook our own code in - get_injury_level() // We check how injured we are, then actually update the mob on how hurt we are. - . = ..() // Calling parent here, actually updating our mob on how hurt we are. - /mob/living/simple_mob/proc/ColorMate() set name = "Recolour" set category = "Abilities.Settings" diff --git a/code/modules/organs/organ.dm b/code/modules/organs/organ.dm index 21213e5f1e8..6715c71e610 100644 --- a/code/modules/organs/organ.dm +++ b/code/modules/organs/organ.dm @@ -336,6 +336,9 @@ var/list/organ_cache = list() //Note: external organs have their own version of this proc /obj/item/organ/take_damage(amount, var/silent=0) + if(owner) + if(SEND_SIGNAL(owner, COMSIG_INTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, amount, silent) & COMPONENT_CANCEL_INTERNAL_ORGAN_DAMAGE) + return 0 if(src.robotic >= ORGAN_ROBOT) src.damage = between(0, src.damage + (amount * 0.8), max_damage) else @@ -346,7 +349,8 @@ var/list/organ_cache = list() var/obj/item/organ/external/parent = owner?.get_organ(parent_organ) if(parent && !silent) owner.custom_pain("Something inside your [parent.name] hurts a lot.", amount) - + if(owner) + SEND_SIGNAL(owner, COMSIG_INTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, amount, silent) /obj/item/organ/proc/bruise() damage = max(damage, min_bruised_damage) diff --git a/code/modules/organs/organ_external.dm b/code/modules/organs/organ_external.dm index aa937775066..b5c6eb29f31 100644 --- a/code/modules/organs/organ_external.dm +++ b/code/modules/organs/organ_external.dm @@ -296,6 +296,9 @@ return TRUE /obj/item/organ/external/take_damage(brute, burn, sharp, edge, used_weapon = null, list/forbidden_limbs = list(), permutation = FALSE, projectile) + if(owner) + if(SEND_SIGNAL(owner, COMSIG_EXTERNAL_ORGAN_PRE_DAMAGE_APPLICATION, brute, burn, sharp, edge, used_weapon, forbidden_limbs, permutation, projectile) & COMPONENT_CANCEL_EXTERNAL_ORGAN_DAMAGE) + return 0 // If the signal returns, we don't apply damage, it's done its own special thing. brute = round(brute * brute_mod, 0.1) burn = round(burn * burn_mod, 0.1) @@ -463,7 +466,8 @@ if(!C.is_stump()) C.take_damage(brute_on_children, burn_on_children, FALSE, FALSE, null, forbidden_limbs, 1) //Splits the damage to each individual 'child', incase multiple exist. parent.take_damage(brute_third, burn_third, FALSE, FALSE, null, forbidden_limbs, 1) - + if(owner) + SEND_SIGNAL(owner, COMSIG_EXTERNAL_ORGAN_POST_DAMAGE_APPLICATION, brute, burn, sharp, edge, used_weapon, forbidden_limbs, permutation, projectile) return update_icon() /obj/item/organ/external/proc/heal_damage(brute, burn, internal = FALSE, robo_repair = FALSE) @@ -1287,6 +1291,8 @@ Note that amputating the affected organ does in fact remove the infection from t /obj/item/organ/external/proc/embed(var/obj/item/W, var/silent = 0) if(!owner || loc != owner) return + if(SEND_SIGNAL(owner, COMSIG_EMBED_OBJECT) & COMSIG_CANCEL_EMBED) //Normally we'd let this proc continue on, but it's much less time consumptive to just do a godmode check here. + return 0 // Cancelled by a component if(!silent) owner.visible_message(span_danger("\The [W] sticks in the wound!")) implants += W diff --git a/code/modules/power/singularity/singularity.dm b/code/modules/power/singularity/singularity.dm index 4c7f5ddd129..5e5c6ed80fb 100644 --- a/code/modules/power/singularity/singularity.dm +++ b/code/modules/power/singularity/singularity.dm @@ -409,8 +409,8 @@ GLOBAL_LIST_BOILERPLATE(all_singularities, /obj/singularity) radiation = round(((src.energy-150)/50)*5,1) SSradiation.radiate(src, radiation) //Always radiate at max, so a decent dose of radiation is applied for(var/mob/living/M in view(toxrange, src.loc)) - if(M.status_flags & GODMODE) - continue + if(SEND_SIGNAL(M, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component toxdamage = (toxdamage - (toxdamage*M.getarmor(null, "rad"))) M.apply_effect(toxdamage, TOX) return @@ -420,8 +420,8 @@ GLOBAL_LIST_BOILERPLATE(all_singularities, /obj/singularity) for(var/mob/living/carbon/M in oviewers(8, src)) if(istype(M, /mob/living/carbon/brain)) //Ignore brains continue - if(M.status_flags & GODMODE) - continue + if(SEND_SIGNAL(M, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + return 0 // Cancelled by a component if(M.stat == CONSCIOUS) if (ishuman(M)) var/mob/living/carbon/human/H = M diff --git a/code/modules/power/tesla/energy_ball.dm b/code/modules/power/tesla/energy_ball.dm index 98b6b8587da..e2f97f93e51 100644 --- a/code/modules/power/tesla/energy_ball.dm +++ b/code/modules/power/tesla/energy_ball.dm @@ -224,7 +224,9 @@ else if(isliving(A)) var/dist = get_dist(source, A) var/mob/living/L = A - if(dist <= zap_range && (dist < closest_dist || !closest_mob) && L.stat != DEAD && !(L.status_flags & GODMODE)) + if(SEND_SIGNAL(L, COMSIG_CHECK_FOR_GODMODE) & COMSIG_GODMODE_CANCEL) + continue + if(dist <= zap_range && (dist < closest_dist || !closest_mob) && L.stat != DEAD) closest_mob = L closest_atom = A closest_dist = dist diff --git a/vorestation.dme b/vorestation.dme index e3ee9a3e879..6d3db0ca093 100644 --- a/vorestation.dme +++ b/vorestation.dme @@ -661,6 +661,7 @@ #include "code\datums\elements\conflict_checking.dm" #include "code\datums\elements\footstep.dm" #include "code\datums\elements\footstep_override.dm" +#include "code\datums\elements\godmode.dm" #include "code\datums\elements\light_blocking.dm" #include "code\datums\elements\slosh.dm" #include "code\datums\elements\turf_transparency.dm"