Files
GS13NG/code/modules/reagents/chemistry/reagents.dm
T
2019-08-29 00:13:24 +01:00

197 lines
7.8 KiB
Plaintext

#define REM REAGENTS_EFFECT_MULTIPLIER
//Various reagents
//Toxin & acid reagents
//Hydroponics stuff
/datum/reagent
var/name = "Reagent"
var/id = "reagent"
var/description = ""
var/specific_heat = SPECIFIC_HEAT_DEFAULT //J/(K*mol)
var/taste_description = "metaphorical salt"
var/taste_mult = 1 //how this taste compares to others. Higher values means it is more noticable
var/glass_name = "glass of ...what?" // use for specialty drinks.
var/glass_desc = "You can't really tell what this is."
var/glass_icon_state = null // Otherwise just sets the icon to a normal glass with the mixture of the reagents in the glass.
var/shot_glass_icon_state = null
var/datum/reagents/holder = null
var/reagent_state = LIQUID
var/list/data
var/current_cycle = 0
var/volume = 0 //pretend this is moles
var/color = "#000000" // rgb: 0, 0, 0
var/can_synth = TRUE // can this reagent be synthesized? (for example: odysseus syringe gun)
var/metabolization_rate = REAGENTS_METABOLISM //how fast the reagent is metabolized by the mob
var/overrides_metab = 0
var/overdose_threshold = 0
var/addiction_threshold = 0
var/addiction_stage = 0
var/addiction_stage1_end = 10
var/addiction_stage2_end = 20
var/addiction_stage3_end = 30
var/addiction_stage4_end = 40
var/overdosed = 0 // You fucked up and this is now triggering its overdose effects, purge that shit quick.
var/self_consuming = FALSE
var/metabolizing = FALSE
var/invisible = FALSE //Set to true if it doesn't appear on handheld health analyzers.
//Fermichem vars:
var/purity = 1 //How pure a chemical is from 0 - 1.
var/addProc = FALSE //If the chemical should force an on_new() call
var/turf/loc = null //Should be the creation location!
var/pH = 7 //pH of the specific reagent, used for calculating the sum pH of a holder.
var/SplitChem = FALSE //If the chem splits on metabolism
var/ImpureChem = "fermiTox"// What chemical is metabolised with an inpure reaction
var/InverseChemVal = 0.25 // If the impurity is below 0.5, replace ALL of the chem with InverseChem upon metabolising
var/InverseChem = "fermiTox"// What chem is metabolised when purity is below InverseChemVal, this shouldn't be made, but if it does, well, I guess I'll know about it.
var/DoNotSplit = FALSE // If impurity is handled within the main chem itself
var/OnMobMergeCheck = FALSE //Call on_mob_life proc when reagents are merging.
/datum/reagent/Destroy() // This should only be called by the holder, so it's already handled clearing its references
. = ..()
holder = null
/datum/reagent/proc/reaction_mob(mob/living/M, method=TOUCH, reac_volume, show_message = 1, touch_protection = 0)
if(!istype(M))
return 0
if(method == VAPOR) //smoke, foam, spray
if(M.reagents)
var/modifier = CLAMP((1 - touch_protection), 0, 1)
var/amount = round(reac_volume*modifier, 0.1)
if(amount >= 0.5)
M.reagents.add_reagent(id, amount)
return 1
/datum/reagent/proc/reaction_obj(obj/O, volume)
return
/datum/reagent/proc/reaction_turf(turf/T, volume)
return
/datum/reagent/proc/on_mob_life(mob/living/carbon/M)
current_cycle++
if(holder)
holder.remove_reagent(src.id, metabolization_rate * M.metabolism_efficiency) //By default it slowly disappears.
return
// Called when this reagent is first added to a mob
/datum/reagent/proc/on_mob_add(mob/living/L, amount)
if(SplitChem)
var/mob/living/carbon/M = L
if(!M)
return
if(purity < 0)
CRASH("Purity below 0 for chem: [id], Please let Fermis Know!")
if (purity == 1 || DoNotSplit == TRUE)
log_game("FERMICHEM: [M] ckey: [M.key] has ingested [volume]u of [id]")
return
else if (InverseChemVal > purity)//Turns all of a added reagent into the inverse chem
M.reagents.remove_reagent(id, amount, FALSE)
M.reagents.add_reagent(InverseChem, amount, FALSE, other_purity = 1)
log_game("FERMICHEM: [M] ckey: [M.key] has ingested [volume]u of [InverseChem]")
return
else
var/impureVol = amount * (1 - purity) //turns impure ratio into impure chem
M.reagents.remove_reagent(id, (impureVol), FALSE)
M.reagents.add_reagent(ImpureChem, impureVol, FALSE, other_purity = 1)
log_game("FERMICHEM: [M] ckey: [M.key] has ingested [volume - impureVol]u of [id]")
log_game("FERMICHEM: [M] ckey: [M.key] has ingested [volume]u of [ImpureChem]")
return
// Called when this reagent is removed while inside a mob
/datum/reagent/proc/on_mob_delete(mob/living/L)
return
// Called when this reagent first starts being metabolized by a liver
/datum/reagent/proc/on_mob_metabolize(mob/living/L)
return
// Called when this reagent stops being metabolized by a liver
/datum/reagent/proc/on_mob_end_metabolize(mob/living/L)
return
/datum/reagent/proc/on_move(mob/M)
return
// Called after add_reagents creates a new reagent.
/datum/reagent/proc/on_new(data)
return
// Called when two reagents of the same are mixing.
/datum/reagent/proc/on_merge(data, amount, mob/living/carbon/M, purity)
if(SplitChem)
if(!ishuman(M))
return
if (purity < 0)
CRASH("Purity below 0 for chem: [id], Please let Fermis Know!")
if (purity == 1 || DoNotSplit == TRUE)
log_game("FERMICHEM: [M] ckey: [M.key] has merged [volume]u of [id] in themselves")
return
else if (InverseChemVal > purity)
M.reagents.remove_reagent(id, amount, FALSE)
M.reagents.add_reagent(InverseChem, amount, FALSE, other_purity = 1)
for(var/datum/reagent/fermi/R in M.reagents.reagent_list)
if(R.name == "")
R.name = name//Negative effects are hidden
log_game("FERMICHEM: [M] ckey: [M.key] has merged [volume]u of [InverseChem]")
return
else
var/impureVol = amount * (1 - purity)
M.reagents.remove_reagent(id, impureVol, FALSE)
M.reagents.add_reagent(ImpureChem, impureVol, FALSE, other_purity = 1)
for(var/datum/reagent/fermi/R in M.reagents.reagent_list)
if(R.name == "")
R.name = name//Negative effects are hidden
log_game("FERMICHEM: [M] ckey: [M.key] has merged [volume - impureVol]u of [id]")
log_game("FERMICHEM: [M] ckey: [M.key] has merged [volume]u of [ImpureChem]")
return
/datum/reagent/proc/on_update(atom/A)
return
// Called when the reagent container is hit by an explosion
/datum/reagent/proc/on_ex_act(severity)
return
// Called if the reagent has passed the overdose threshold and is set to be triggering overdose effects
/datum/reagent/proc/overdose_process(mob/living/M)
return
/datum/reagent/proc/overdose_start(mob/living/M)
to_chat(M, "<span class='userdanger'>You feel like you took too much of [name]!</span>")
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "[id]_overdose", /datum/mood_event/overdose, name)
return
/datum/reagent/proc/addiction_act_stage1(mob/living/M)
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "[id]_overdose", /datum/mood_event/withdrawal_light, name)
if(prob(30))
to_chat(M, "<span class='notice'>You feel like having some [name] right about now.</span>")
return
/datum/reagent/proc/addiction_act_stage2(mob/living/M)
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "[id]_overdose", /datum/mood_event/withdrawal_medium, name)
if(prob(30))
to_chat(M, "<span class='notice'>You feel like you need [name]. You just can't get enough.</span>")
return
/datum/reagent/proc/addiction_act_stage3(mob/living/M)
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "[id]_overdose", /datum/mood_event/withdrawal_severe, name)
if(prob(30))
to_chat(M, "<span class='danger'>You have an intense craving for [name].</span>")
return
/datum/reagent/proc/addiction_act_stage4(mob/living/M)
SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "[id]_overdose", /datum/mood_event/withdrawal_critical, name)
if(prob(30))
to_chat(M, "<span class='boldannounce'>You're not feeling good at all! You really need some [name].</span>")
return
/proc/pretty_string_from_reagent_list(list/reagent_list)
//Convert reagent list to a printable string for logging etc
var/list/rs = list()
for (var/datum/reagent/R in reagent_list)
rs += "[R.name], [R.volume]"
return rs.Join(" | ")