From 64376e2899cc0770376a84a7dbbf0ccd6d5349f8 Mon Sep 17 00:00:00 2001 From: SyncIt21 <110812394+SyncIt21@users.noreply.github.com> Date: Thu, 31 Jul 2025 23:34:07 +0530 Subject: [PATCH] Refactors reagent transfer operations (#92213) ## About The Pull Request - Fixes #92198 - Fixes #92298 **1) Replaces reagent `on_transfer()` with its corresponding `expose()` proc variants** This PR replaces all known implementations of `/datum/reagent/on_transfer()` with `/datum/reagent/expose_mob()`. We use `expose_mob()` & not the other `expose()` variants because all known implementations were targeting living beings so this was the correct replacement This has 2 benefits - `expose_mob()` gets called correctly when an impure reagent is converted to it's inverse variant like for Cryostylane & Cryogeldia. This isn't the case for `on_transfer()` so we get correct behaviour which fixes the above bug - Removing `on_transfer()` makes the proc `/datum/reagents/trans_to()` much faster performance wise because we aren't calling `update_total()` per reagent transfered now but only once at the end after all reagents are transferred Also there was little to no functional difference between the 2 procs, `expose()` works correctly in comparison & this won't confuse devs when deciding which proc to use. One proc to cover all scenarios **2) Removes unused expose signals** `COMSIG_ATOM_AFTER_EXPOSE_REAGENTS` & `COMSIG_REAGENTS_EXPOSE_ATOM` are not used anywhere in the codebase i.e. no listeners. They can be discarded as dead code **3) Fixes wrong transfer amount passed to `/datum/reagent/intercept_reagents_transfer()` & `/datum/reagents/expose()`** The wrong transfer `amount` was passed when it fact it should use `transfer_amount` which contains the multiplier & proportional multiplier applied. Also the reagent volumes exposed was computed incorrectly resulting in the 2nd issue listed above. Blood transferred to mobs now go to `blood_volume` directly instead of getting added to the mobs reagent holder as long as it's less than `BLOOD_VOLUME_MAXIMUM` level ## Changelog :cl: fix: reagent intercept operations use correct volumes e.g. ph buffers fix: impure cryostylane now has inverse cryogeldia effects when applied on mods fix: exposing reagents now uses correct volumes i.e. injecting blood into mobs don't increase it exponentially and stops when max levels are reached. Exposure affects of all reagents are lessened upon continuous exposure refactor: refactors how reagent affects are applied on mobs. Report bugs on github /:cl: --- code/__DEFINES/dcs/signals/signals_reagent.dm | 4 - code/game/atom/_atom.dm | 7 +- .../lavaland/basilisk/basilisk_overheat.dm | 2 +- code/modules/mob/living/carbon/life.dm | 6 +- code/modules/mod/modules/modules_maint.dm | 2 +- .../reagents/chemistry/holder/holder.dm | 75 +++++++++---------- code/modules/reagents/chemistry/reagents.dm | 4 - .../reagents/cat2_medicine_reagents.dm | 32 ++++---- .../reagents/drinks/alcohol_reagents.dm | 14 ++-- .../chemistry/reagents/drug_reagents.dm | 10 +-- .../chemistry/reagents/impure_reagents.dm | 11 +-- .../chemistry/reagents/other_reagents.dm | 16 ++-- .../chemistry/reagents/toxin_reagents.dm | 22 +++--- .../reagents/reagent_containers/syringes.dm | 8 +- 14 files changed, 96 insertions(+), 117 deletions(-) diff --git a/code/__DEFINES/dcs/signals/signals_reagent.dm b/code/__DEFINES/dcs/signals/signals_reagent.dm index 7e2954e7d22..157f7058a4c 100644 --- a/code/__DEFINES/dcs/signals/signals_reagent.dm +++ b/code/__DEFINES/dcs/signals/signals_reagent.dm @@ -6,8 +6,6 @@ #define COMSIG_ATOM_EXPOSE_REAGENTS "atom_expose_reagents" /// Prevents the atom from being exposed to reagents if returned on [COMSIG_ATOM_EXPOSE_REAGENTS] #define COMPONENT_NO_EXPOSE_REAGENTS (1<<0) -///from base of atom/expose_reagents(): (/list, /datum/reagents, methods, volume_modifier, show_message) -#define COMSIG_ATOM_AFTER_EXPOSE_REAGENTS "atom_after_expose_reagents" ///from base of [/datum/reagent/proc/expose_atom]: (/datum/reagent, reac_volume) #define COMSIG_ATOM_EXPOSE_REAGENT "atom_expose_reagent" ///from base of [/datum/reagent/proc/expose_atom]: (/atom, reac_volume) @@ -36,8 +34,6 @@ ///from base of [/datum/reagents/proc/process]: (num_reactions) #define COMSIG_REAGENTS_REACTION_STEP "reagents_time_step" -///from base of [/atom/proc/expose_reagents]: (/atom, /list, methods, volume_modifier, show_message) -#define COMSIG_REAGENTS_EXPOSE_ATOM "reagents_expose_atom" ///from base of [/obj/proc/expose_reagents]: (/obj, /list, methods, volume_modifier, show_message) #define COMSIG_REAGENTS_EXPOSE_OBJ "reagents_expose_obj" ///from base of [/mob/living/proc/expose_reagents]: (/mob/living, /list, methods, volume_modifier, show_message, touch_protection) diff --git a/code/game/atom/_atom.dm b/code/game/atom/_atom.dm index 8bc13e27087..10aa9c8345a 100644 --- a/code/game/atom/_atom.dm +++ b/code/game/atom/_atom.dm @@ -414,18 +414,15 @@ * - [reagents][/list]: The list of reagents the atom is being exposed to. * - [source][/datum/reagents]: The reagent holder the reagents are being sourced from. * - methods: How the atom is being exposed to the reagents. Bitflags. - * - volume_modifier: Volume multiplier. * - show_message: Whether to display anything to mobs when they are exposed. */ -/atom/proc/expose_reagents(list/reagents, datum/reagents/source, methods=TOUCH, volume_modifier=1, show_message=TRUE) - . = SEND_SIGNAL(src, COMSIG_ATOM_EXPOSE_REAGENTS, reagents, source, methods, volume_modifier, show_message) +/atom/proc/expose_reagents(list/reagents, datum/reagents/source, methods=TOUCH, show_message=TRUE) + . = SEND_SIGNAL(src, COMSIG_ATOM_EXPOSE_REAGENTS, reagents, source, methods, show_message) if(. & COMPONENT_NO_EXPOSE_REAGENTS) return - SEND_SIGNAL(source, COMSIG_REAGENTS_EXPOSE_ATOM, src, reagents, methods, volume_modifier, show_message) for(var/datum/reagent/current_reagent as anything in reagents) . |= current_reagent.expose_atom(src, reagents[current_reagent], methods) - SEND_SIGNAL(src, COMSIG_ATOM_AFTER_EXPOSE_REAGENTS, reagents, source, methods, volume_modifier, show_message) /// Are you allowed to drop this atom /atom/proc/AllowDrop() diff --git a/code/modules/mob/living/basic/lavaland/basilisk/basilisk_overheat.dm b/code/modules/mob/living/basic/lavaland/basilisk/basilisk_overheat.dm index 71e938c5164..04961f7b2b5 100644 --- a/code/modules/mob/living/basic/lavaland/basilisk/basilisk_overheat.dm +++ b/code/modules/mob/living/basic/lavaland/basilisk/basilisk_overheat.dm @@ -52,7 +52,7 @@ qdel(src) /// Cool down if splashed with water -/datum/status_effect/basilisk_overheat/proc/on_splashed(atom/source, list/reagents, datum/reagents/source_reagents, methods, volume_modifier, show_message) +/datum/status_effect/basilisk_overheat/proc/on_splashed(atom/source, list/reagents, datum/reagents/source_reagents, methods, show_message) SIGNAL_HANDLER if(!(methods & (TOUCH|VAPOR))) return diff --git a/code/modules/mob/living/carbon/life.dm b/code/modules/mob/living/carbon/life.dm index 672914f5c43..02e67d04d16 100644 --- a/code/modules/mob/living/carbon/life.dm +++ b/code/modules/mob/living/carbon/life.dm @@ -485,13 +485,17 @@ if(blood_type.reagent_type != chem.type) return + var/blood_stream_volume = min(round(reac_volume, CHEMICAL_VOLUME_ROUNDING), BLOOD_VOLUME_MAXIMUM - blood_volume) + if(blood_stream_volume > 0) //remove reagents from mob that has now entered the bloodstream + reagents.remove_reagent(chem.type, blood_stream_volume) + blood_volume += blood_stream_volume + if(chem.data?["blood_type"]) var/datum/blood_type/donor_type = chem.data["blood_type"] if(!(donor_type.type_key() in blood_type.compatible_types)) reagents.add_reagent(/datum/reagent/toxin, reac_volume * 0.5) return COMPONENT_NO_EXPOSE_REAGENTS - blood_volume = min(blood_volume + round(reac_volume, 0.1), BLOOD_VOLUME_MAXIMUM) return COMPONENT_NO_EXPOSE_REAGENTS /mob/living/carbon/proc/handle_bodyparts(seconds_per_tick, times_fired) diff --git a/code/modules/mod/modules/modules_maint.dm b/code/modules/mod/modules/modules_maint.dm index 3d4f17b7f7a..17804dcd406 100644 --- a/code/modules/mod/modules/modules_maint.dm +++ b/code/modules/mod/modules/modules_maint.dm @@ -54,7 +54,7 @@ set_off = TRUE ///Calls snap_signal() when exposed to a reagent via VAPOR, PATCH or TOUCH -/obj/item/mod/module/springlock/proc/on_wearer_exposed(atom/source, list/reagents, datum/reagents/source_reagents, methods, volume_modifier, show_message) +/obj/item/mod/module/springlock/proc/on_wearer_exposed(atom/source, list/reagents, datum/reagents/source_reagents, methods, show_message) SIGNAL_HANDLER if(!(methods & (VAPOR|PATCH|TOUCH))) diff --git a/code/modules/reagents/chemistry/holder/holder.dm b/code/modules/reagents/chemistry/holder/holder.dm index 526f4e43c4c..02eb45ad3fb 100644 --- a/code/modules/reagents/chemistry/holder/holder.dm +++ b/code/modules/reagents/chemistry/holder/holder.dm @@ -3,7 +3,7 @@ /// Holder for a bunch of [/datum/reagent] /datum/reagents /// The reagents being held - var/list/datum/reagent/reagent_list = new/list() + var/list/datum/reagent/reagent_list = list() /// Current volume of all the reagents var/total_volume = 0 /// Max volume of this holder @@ -80,7 +80,7 @@ * * added_purity - override to force a purity when added * * added_ph - override to force a pH when added * * override_base_ph - ingore the present pH of the reagent, and instead use the default (i.e. if buffers/reactions alter it) - * * list/reagent_added - If not null use this as an holder to store and retrive the reagent datum that was just added without having to locate it after this proc returns. Clear the list to erase old values + * * list/reagent_added - If not null will contain an map of [reagent datum->amount added] which holds the inverse chems added to mobs. Clear the list to erase old values * * creation_callback - Callback to invoke when the reagent is created */ /datum/reagents/proc/add_reagent( @@ -154,7 +154,7 @@ set_temperature(reagtemp) if(!isnull(reagent_added)) - reagent_added += iter_reagent + reagent_added[iter_reagent] = amount if(!no_react && !is_reacting) //To reduce the amount of calculations for a reaction the reaction list is only updated on a reagents addition. handle_reactions() return amount @@ -185,7 +185,7 @@ set_temperature(reagtemp) if(!isnull(reagent_added)) - reagent_added += new_reagent + reagent_added[new_reagent] = amount if(!no_react) handle_reactions() return amount @@ -463,14 +463,9 @@ if(amount <= 0) return FALSE - //Set up new reagents to inherit the old ongoing reactions - if(!no_react) - transfer_reactions(target_holder) - var/trans_data = null var/list/r_to_send = methods ? list() : null // Validated list of reagents to be exposed var/list/transfer_log = list() - var/list/reagents_to_remove = list() var/part = isnull(target_id) ? (amount / total_volume) : 1 var/transfer_amount @@ -490,34 +485,29 @@ continue else transfer_amount = reagent.volume * part + transfer_amount *= multiplier if(preserve_data) trans_data = copy_data(reagent) - if(reagent.intercept_reagents_transfer(target_holder, amount)) + if(reagent.intercept_reagents_transfer(target_holder, transfer_amount)) update_total() target_holder.update_total() continue - transfered_amount = target_holder.add_reagent(reagent.type, transfer_amount * multiplier, trans_data, chem_temp, reagent.purity, reagent.ph, no_react = TRUE, reagent_added = r_to_send, creation_callback = CALLBACK(src, PROC_REF(_on_transfer_creation), reagent, target_holder)) //we only handle reaction after every reagent has been transferred. + transfered_amount = target_holder.add_reagent(reagent.type, transfer_amount, trans_data, chem_temp, reagent.purity, reagent.ph, no_react = TRUE, reagent_added = r_to_send, creation_callback = CALLBACK(src, PROC_REF(_on_transfer_creation), reagent, target_holder)) //we only handle reaction after every reagent has been transferred. if(!transfered_amount) continue - reagents_to_remove[reagent] = transfer_amount + total_transfered_amount += transfered_amount + reagent.volume -= transfered_amount + transfer_log += "[reagent.type] ([transfered_amount]u, [reagent.purity] purity)" if(!isnull(target_id)) break + update_total() //expose target to reagent changes if(methods) - target_holder.expose(isorgan(target_atom) ? target : target_atom, methods, part, show_message, r_to_send) - - //remove chemicals that were added above - for(var/datum/reagent/reagent as anything in reagents_to_remove) - transfer_amount = reagents_to_remove[reagent] - if(methods) - reagent.on_transfer(target_atom, methods, transfer_amount) - reagent.volume -= transfer_amount - update_total() - transfer_log += "[reagent.type] ([transfer_amount]u, [reagent.purity] purity)" + target_holder.expose(isorgan(target_atom) ? target : target_atom, methods, 1, show_message, r_to_send) //combat log if(transferred_by && target_atom) @@ -532,8 +522,9 @@ log_combat(transferred_by, log_target, "transferred reagents to", my_atom, "which had [english_list(transfer_log)]") if(!no_react) - target_holder.handle_reactions() + transfer_reactions(target_holder) handle_reactions() + target_holder.handle_reactions() return total_transfered_amount @@ -559,7 +550,7 @@ multiplier = 1, preserve_data = TRUE, no_react = FALSE, - copy_methods + copy_methods = NONE, ) if(QDELETED(target) || !total_volume) return @@ -584,23 +575,21 @@ var/list/cached_reagents = reagent_list var/part = amount / total_volume var/transfer_amount - var/transfered_amount = 0 var/total_transfered_amount = 0 var/trans_data = null + var/list/r_to_send = copy_methods ? list() : null for(var/datum/reagent/reagent as anything in cached_reagents) transfer_amount = reagent.volume * part * multiplier if(preserve_data) trans_data = copy_data(reagent) - transfered_amount = target_holder.add_reagent(reagent.type, transfer_amount, trans_data, chem_temp, reagent.purity, reagent.ph, no_react = TRUE) - if(copy_methods && !no_react) - reagent.on_transfer(target, copy_methods, transfer_amount) - if(!transfered_amount) - continue - total_transfered_amount += transfered_amount + total_transfered_amount += target_holder.add_reagent(reagent.type, transfer_amount, trans_data, chem_temp, reagent.purity, reagent.ph, reagent_added = r_to_send, no_react = TRUE) + + //expose target to reagent changes + if(copy_methods) + target_holder.expose(target, copy_methods, 1, FALSE, r_to_send) if(!no_react) - // pass over previous ongoing reactions before handle_reactions is called transfer_reactions(target_holder) target_holder.handle_reactions() @@ -804,23 +793,27 @@ * Arguments * - Atom/target: What mob/turf/object is being exposed to reagents? This is your reaction target. * - Methods: What reaction type is the reagent itself going to call on the reaction target? Types are TOUCH, INGEST, VAPOR, PATCH, INJECT and INHALE. - * - Volume_modifier: What is the reagent volume multiplied by when exposed? Note that this is called on the volume of EVERY reagent in the base body, so factor in your Maximum_Volume if necessary! + * - Volume_modifier: reagent volume modifier applied to the reagents(passed to r_to_expose or this holder) before exposing. Must be between 0->1 * - Show_message: Whether to display anything to mobs when they are exposed. - * - list/datum/reagent/r_to_expose: list of reagents to expose. if null will expose the reagents present in this holder instead + * - list/datum/reagent/r_to_expose: map of[/datum/reagent -> amount] when you to want to expose specific reagents with precise amounts */ /datum/reagents/proc/expose(atom/target, methods = TOUCH, volume_modifier = 1, show_message = 1, list/datum/reagent/r_to_expose = null) if(isnull(target)) - return null + return - var/list/target_reagents = isnull(r_to_expose) ? reagent_list : r_to_expose - if(!target_reagents.len) - return null + if(volume_modifier <= 0) + stack_trace("Volume modifier [volume_modifier] must be +ve") + return var/list/datum/reagent/reagents = list() - for(var/datum/reagent/reagent as anything in target_reagents) - reagents[reagent] = reagent.volume * volume_modifier + if(isnull(r_to_expose)) + for(var/datum/reagent/reagent as anything in reagent_list) + reagents[reagent] = reagent.volume * volume_modifier + else + for(var/datum/reagent/reagent as anything in r_to_expose) + reagents[reagent] = r_to_expose[reagent] * volume_modifier - return target.expose_reagents(reagents, src, methods, volume_modifier, show_message) + return target.expose_reagents(reagents, src, methods, show_message) /** * Applies heat to this holder diff --git a/code/modules/reagents/chemistry/reagents.dm b/code/modules/reagents/chemistry/reagents.dm index 4e0544f6ba2..23998091b52 100644 --- a/code/modules/reagents/chemistry/reagents.dm +++ b/code/modules/reagents/chemistry/reagents.dm @@ -196,10 +196,6 @@ Primarily used in reagents/reaction_agents /datum/reagent/proc/intercept_reagents_transfer(datum/reagents/target, amount) return FALSE -///Called after a reagent is transferred -/datum/reagent/proc/on_transfer(atom/A, methods=TOUCH, trans_volume) - return - /// Called when this reagent is first added to a mob /datum/reagent/proc/on_mob_add(mob/living/affected_mob, amount) // Scale the overdose threshold of the chem by the difference between the default and creation purity. diff --git a/code/modules/reagents/chemistry/reagents/cat2_medicine_reagents.dm b/code/modules/reagents/chemistry/reagents/cat2_medicine_reagents.dm index 300840c5d69..3099051c106 100644 --- a/code/modules/reagents/chemistry/reagents/cat2_medicine_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/cat2_medicine_reagents.dm @@ -154,14 +154,14 @@ if(need_mob_update) return UPDATE_MOB_HEALTH -/datum/reagent/medicine/c2/probital/on_transfer(atom/A, methods=INGEST, trans_volume) - if(!(methods & INGEST) || (!iscarbon(A) && !istype(A, /obj/item/organ/stomach)) ) +/datum/reagent/medicine/c2/probital/expose_mob(mob/living/exposed_mob, methods, reac_volume, show_message, touch_protection) + . = ..() + if(!(methods & INGEST) || !iscarbon(exposed_mob)) return - A.reagents.remove_reagent(/datum/reagent/medicine/c2/probital, trans_volume * 0.05) - A.reagents.add_reagent(/datum/reagent/medicine/metafactor, trans_volume * 0.25) - - ..() + var/datum/reagents/mob_reagents = exposed_mob.reagents + mob_reagents.remove_reagent(/datum/reagent/medicine/c2/probital, reac_volume * 0.05) + mob_reagents.add_reagent(/datum/reagent/medicine/metafactor, reac_volume * 0.25) /******BURN******/ /*Suffix: -uri*/ @@ -406,19 +406,21 @@ var/conversion_amount chemical_flags = REAGENT_CAN_BE_SYNTHESIZED -/datum/reagent/medicine/c2/syriniver/on_transfer(atom/A, methods=INJECT, trans_volume) - if(!(methods & INJECT) || !iscarbon(A)) +/datum/reagent/medicine/c2/syriniver/expose_mob(mob/living/carbon/exposed_mob, methods, trans_volume, show_message, touch_protection) + . = ..() + if(!(methods & INJECT) || !iscarbon(exposed_mob)) return - var/mob/living/carbon/C = A + if(trans_volume >= 0.4) //prevents cheesing with ultralow doses. - C.adjustToxLoss((-3 * min(2, trans_volume) * REM) * normalise_creation_purity(), required_biotype = affected_biotype) //This is to promote iv pole use for that chemotherapy feel. - var/obj/item/organ/liver/L = C.organs_slot[ORGAN_SLOT_LIVER] + exposed_mob.adjustToxLoss((-3 * min(2, trans_volume) * REM) * normalise_creation_purity(), required_biotype = affected_biotype) //This is to promote iv pole use for that chemotherapy feel. + var/obj/item/organ/liver/L = exposed_mob.organs_slot[ORGAN_SLOT_LIVER] if(!L || L.organ_flags & ORGAN_FAILING) return - conversion_amount = (trans_volume * (min(100 -C.get_organ_loss(ORGAN_SLOT_LIVER), 80) / 100)*normalise_creation_purity()) //the more damaged the liver the worse we metabolize. - C.reagents.remove_reagent(/datum/reagent/medicine/c2/syriniver, conversion_amount) - C.reagents.add_reagent(/datum/reagent/medicine/c2/musiver, conversion_amount) - ..() + conversion_amount = (trans_volume * (min(100 -exposed_mob.get_organ_loss(ORGAN_SLOT_LIVER), 80) / 100)*normalise_creation_purity()) //the more damaged the liver the worse we metabolize. + + var/datum/reagents/mob_reagents = exposed_mob.reagents + mob_reagents.remove_reagent(/datum/reagent/medicine/c2/syriniver, conversion_amount) + mob_reagents.add_reagent(/datum/reagent/medicine/c2/musiver, conversion_amount) /datum/reagent/medicine/c2/syriniver/on_mob_life(mob/living/carbon/affected_mob, seconds_per_tick, times_fired) . = ..() diff --git a/code/modules/reagents/chemistry/reagents/drinks/alcohol_reagents.dm b/code/modules/reagents/chemistry/reagents/drinks/alcohol_reagents.dm index e66a542a4d6..b7cda4cd113 100644 --- a/code/modules/reagents/chemistry/reagents/drinks/alcohol_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/drinks/alcohol_reagents.dm @@ -501,14 +501,16 @@ return ..() -/datum/reagent/consumable/ethanol/goldschlager/on_transfer(atom/atom, methods = TOUCH, trans_volume) +/datum/reagent/consumable/ethanol/goldschlager/expose_mob(mob/living/exposed_mob, methods, reac_volume) + . = ..() if(!(methods & INGEST)) - return ..() + return - var/convert_amount = trans_volume * min(GOLDSCHLAGER_GOLD_RATIO, 1) - atom.reagents.remove_reagent(/datum/reagent/consumable/ethanol/goldschlager, convert_amount) - atom.reagents.add_reagent(/datum/reagent/gold, convert_amount) - return ..() + var/convert_amount = reac_volume * min(GOLDSCHLAGER_GOLD_RATIO, 1) + var/datum/reagents/mob_reagents = exposed_mob.reagents + + mob_reagents.remove_reagent(/datum/reagent/consumable/ethanol/goldschlager, convert_amount) + mob_reagents.add_reagent(/datum/reagent/gold, convert_amount) /datum/reagent/consumable/ethanol/patron name = "Patron" diff --git a/code/modules/reagents/chemistry/reagents/drug_reagents.dm b/code/modules/reagents/chemistry/reagents/drug_reagents.dm index 4f373c2cf9d..039e6a2898b 100644 --- a/code/modules/reagents/chemistry/reagents/drug_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/drug_reagents.dm @@ -816,11 +816,11 @@ If you have at over 25u in your body you restore more than 20 stamina per cycle, if(!kronkaine_fiend.stat) kronkaine_fiend.stop_sound_channel(CHANNEL_HEARTBEAT) -/datum/reagent/drug/kronkaine/on_transfer(atom/kronkaine_receptacle, methods, trans_volume) +/datum/reagent/drug/kronkaine/expose_mob(mob/living/carbon/druggo, methods, trans_volume, show_message, touch_protection) . = ..() - if(!iscarbon(kronkaine_receptacle)) + if(!iscarbon(druggo)) return - var/mob/living/carbon/druggo = kronkaine_receptacle + //The drug is more effective if smoked or injected, restoring more stamina per unit. var/stamina_heal_per_unit if(methods & (INJECT|INHALE)) @@ -833,9 +833,7 @@ If you have at over 25u in your body you restore more than 20 stamina per cycle, to_chat(druggo, span_nicegreen(pick("You feel the cowardice melt away...", "You feel unbothered by the judgements of others.", "My life feels lovely!", "You lower your snout... and suddenly feel more charitable!"))) else stamina_heal_per_unit = 6 - if(druggo.adjustStaminaLoss(-stamina_heal_per_unit * trans_volume)) - return UPDATE_MOB_HEALTH - + druggo.adjustStaminaLoss(-stamina_heal_per_unit * trans_volume) /datum/reagent/drug/kronkaine/on_mob_life(mob/living/carbon/kronkaine_fiend, seconds_per_tick, times_fired) . = ..() diff --git a/code/modules/reagents/chemistry/reagents/impure_reagents.dm b/code/modules/reagents/chemistry/reagents/impure_reagents.dm index 09da3851e22..e21c0eada33 100644 --- a/code/modules/reagents/chemistry/reagents/impure_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/impure_reagents.dm @@ -97,18 +97,13 @@ chemical_flags = REAGENT_DEAD_PROCESS | REAGENT_IGNORE_STASIS | REAGENT_UNAFFECTED_BY_METABOLISM metabolization_rate = 1 * REM -/datum/reagent/inverse/cryostylane/on_transfer(atom/transfered_thing, methods, trans_volume) +/datum/reagent/inverse/cryostylane/expose_mob(mob/living/carbon/human/human_thing, methods, reac_volume, show_message, touch_protection) . = ..() - if(methods & INGEST) + if((methods & INGEST) || !ishuman(human_thing)) return - if(!ishuman(transfered_thing)) - return - - var/mob/living/carbon/human/human_thing = transfered_thing - if(HAS_TRAIT(human_thing, TRAIT_RESISTCOLD)) - holder.remove_reagent(type, volume) + holder.del_reagent(type) return human_thing.apply_status_effect(/datum/status_effect/frozenstasis/irresistable) diff --git a/code/modules/reagents/chemistry/reagents/other_reagents.dm b/code/modules/reagents/chemistry/reagents/other_reagents.dm index 17ad295a1e8..1c6e2c15d15 100644 --- a/code/modules/reagents/chemistry/reagents/other_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/other_reagents.dm @@ -2697,15 +2697,15 @@ . = ..() yuck_cycle = 0 // reset vomiting -/datum/reagent/yuck/on_transfer(atom/A, methods=TOUCH, trans_volume) - if((methods & INGEST) || !iscarbon(A)) - return ..() +/datum/reagent/yuck/expose_mob(mob/living/carbon/exposed_mob, methods, expose_volume, show_message, touch_protection) + . = ..() + if(!(methods & INGEST) || !iscarbon(exposed_mob)) + return - A.reagents.remove_reagent(type, trans_volume) - A.reagents.add_reagent(/datum/reagent/fuel, trans_volume * 0.75) - A.reagents.add_reagent(/datum/reagent/water, trans_volume * 0.25) - - return ..() + var/datum/reagents/mob_reagents = exposed_mob.reagents + mob_reagents.remove_reagent(type, expose_volume) + mob_reagents.add_reagent(/datum/reagent/fuel, expose_volume * 0.75) + mob_reagents.add_reagent(/datum/reagent/water, expose_volume * 0.25) //monkey powder heehoo /datum/reagent/monkey_powder diff --git a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm index a2a050d5ca6..9c76c88a399 100644 --- a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm @@ -269,13 +269,15 @@ . = ..() affected_mob.cure_fakedeath(type) -/datum/reagent/toxin/zombiepowder/on_transfer(atom/target_atom, methods, trans_volume) +/datum/reagent/toxin/zombiepowder/expose_mob(mob/living/exposed_mob, methods, reac_volume, show_message, touch_protection) . = ..() - var/datum/reagent/zombiepowder = target_atom.reagents.has_reagent(/datum/reagent/toxin/zombiepowder) - if(!zombiepowder || !(methods & (INGEST|INHALE))) + if(!(methods & (INGEST|INHALE))) return - LAZYINITLIST(zombiepowder.data) - zombiepowder.data["method"] |= (INGEST|INHALE) + + var/datum/reagent/zombiepowder = exposed_mob.reagents.has_reagent(/datum/reagent/toxin/zombiepowder) + if(zombiepowder) + LAZYINITLIST(zombiepowder.data) + zombiepowder.data["method"] |= (INGEST|INHALE) /datum/reagent/toxin/zombiepowder/on_mob_life(mob/living/affected_mob, seconds_per_tick, times_fired) . = ..() @@ -450,25 +452,19 @@ taste_description = "spores" chemical_flags = REAGENT_CAN_BE_SYNTHESIZED|REAGENT_NO_RANDOM_RECIPE -/datum/reagent/toxin/spore/on_transfer(atom/A, methods, trans_volume) +/datum/reagent/toxin/spore/expose_mob(mob/living/spore_lung_victim, methods, reac_volume, show_message, touch_protection) . = ..() - if(!isliving(A)) - return if(!(methods & INHALE)) return - - var/mob/living/spore_lung_victim = A - if(!(spore_lung_victim.mob_biotypes & (MOB_HUMANOID | MOB_BEAST))) return - if(prob(min(trans_volume * 10, 80))) + if(prob(min(reac_volume * 10, 80))) to_chat(spore_lung_victim, span_danger("[pick("You have a coughing fit!", "You hack and cough!", "Your lungs burn!")]")) spore_lung_victim.Stun(1 SECONDS) spore_lung_victim.emote("cough") - /datum/reagent/toxin/spore/on_mob_life(mob/living/carbon/affected_mob, seconds_per_tick, times_fired) . = ..() affected_mob.damageoverlaytemp = 60 diff --git a/code/modules/reagents/reagent_containers/syringes.dm b/code/modules/reagents/reagent_containers/syringes.dm index 2fc011246f7..2454416062a 100644 --- a/code/modules/reagents/reagent_containers/syringes.dm +++ b/code/modules/reagents/reagent_containers/syringes.dm @@ -67,7 +67,7 @@ to_chat(user, span_warning("You cannot directly fill [target]!")) return ITEM_INTERACT_BLOCKING - if(target.reagents.total_volume >= target.reagents.maximum_volume) + if(target.reagents.holder_full()) to_chat(user, span_notice("[target] is full.")) return ITEM_INTERACT_BLOCKING @@ -82,7 +82,7 @@ return ITEM_INTERACT_BLOCKING if(!reagents.total_volume) return ITEM_INTERACT_BLOCKING - if(living_target.reagents.total_volume >= living_target.reagents.maximum_volume) + if(living_target.reagents.holder_full()) return ITEM_INTERACT_BLOCKING living_target.visible_message( span_danger("[user] injects [living_target] with the syringe!"), @@ -109,7 +109,7 @@ SEND_SIGNAL(target, COMSIG_LIVING_TRY_SYRINGE_WITHDRAW, user) - if(reagents.total_volume >= reagents.maximum_volume) + if(reagents.holder_full()) to_chat(user, span_notice("[src] is full.")) return ITEM_INTERACT_BLOCKING @@ -123,7 +123,7 @@ ) if(!do_after(user, CHEM_INTERACT_DELAY(3 SECONDS, user), target, extra_checks = CALLBACK(src, PROC_REF(try_syringe), living_target, user))) return ITEM_INTERACT_BLOCKING - if(reagents.total_volume >= reagents.maximum_volume) + if(reagents.holder_full()) return ITEM_INTERACT_BLOCKING if(living_target.transfer_blood_to(src, drawn_amount)) user.visible_message(span_notice("[user] takes a blood sample from [living_target]."))