Files
Aurora.3/code/datums/components/psionics/psiblock_drugs.dm
T
VMSolidusandGitHub cb981d44ce Mindblanker Tweaks (#22553)
This was kind of a harsh mechanic to surprise players with, and turns
out it doesn't feel that great to tell them "Surprise your skill points
don't matter here". So this PR tweaks the "Empathy Penalty" from
Mindblanker and PsiProtect pills to 'only' cut the morale modifier from
those skills in half, rather than fully negating it.
2026-06-04 09:43:58 +00:00

171 lines
6.9 KiB
Plaintext

/datum/component/timed_life/psiblock_drugs
/// Typecasted parent of this component.
var/mob/living/carbon/human/owner
/// The set of messages to choose from when this drug is first taken.
var/initial_effect_message_list = list("Everything feels dulled and distant.", "You feel like you can't focus on anything.", "Your thoughts feel sluggish.", "Why should you care about others?")
/// The set of messages to choose from when this drug wears off.
var/removal_message_list = list("You feel more sensitive to your surroundings.", "Your thoughts feel clearer.", "You feel more aware of others around you.", "You can focus better.")
/// How much this drug modifies the user's psi sensitivity.
var/psi_sensitivity_modifier = -1
/// The percent chance that this drug will cancel a psionic power when the user is targeted by one.
var/telepathy_cancel_probability = 95
/datum/component/timed_life/psiblock_drugs/Initialize(lifetime_seconds = 5 MINUTES)
. = ..()
if (!parent)
return
owner = ashuman(parent)
if (length(initial_effect_message_list))
to_chat(parent, SPAN_NOTICE(pick(initial_effect_message_list)))
RegisterSignal(parent, COMSIG_PSI_CHECK_SENSITIVITY, PROC_REF(modify_sensitivity), override = TRUE)
RegisterSignal(parent, COMSIG_PSI_MIND_POWER, PROC_REF(cancel_power), override = TRUE)
RegisterSignal(parent, COMSIG_GET_MINISTRY_MODIFIERS, PROC_REF(modify_ministry_empathy), override = TRUE)
RegisterSignal(parent, COMSIG_RECEIVE_MINISTRY_MODIFIERS, PROC_REF(modify_ministry_receiving), override = TRUE)
RegisterSignal(parent, COMSIG_GET_LEADERSHIP_MODIFIERS, PROC_REF(modify_leadership_empathy), override = TRUE)
/datum/component/timed_life/psiblock_drugs/Destroy()
owner = null
if (!parent)
return ..()
// This is here and not on the reagent because the reagent's duration is handled by this component rather than metabolism.
// If the parent is being deleted, then there's no need to send a message about the drug wearing off.
if (!QDELING(parent) && length(removal_message_list))
to_chat(parent, SPAN_NOTICE(pick(removal_message_list)))
UnregisterSignal(parent, COMSIG_PSI_CHECK_SENSITIVITY)
UnregisterSignal(parent, COMSIG_PSI_MIND_POWER)
UnregisterSignal(parent, COMSIG_GET_MINISTRY_MODIFIERS)
UnregisterSignal(parent, COMSIG_RECEIVE_MINISTRY_MODIFIERS)
UnregisterSignal(parent, COMSIG_GET_LEADERSHIP_MODIFIERS)
return ..()
/datum/component/timed_life/psiblock_drugs/proc/modify_sensitivity(parent, effective_sensitivity)
SIGNAL_HANDLER
*effective_sensitivity = *effective_sensitivity + psi_sensitivity_modifier
/datum/component/timed_life/psiblock_drugs/proc/cancel_power(parent, caster, cancelled, cancel_return, wide_field)
SIGNAL_HANDLER
if (prob(telepathy_cancel_probability))
*cancelled = TRUE
/datum/component/timed_life/psiblock_drugs/proc/modify_ministry_empathy(minister, ministree, moodlet_value)
SIGNAL_HANDLER
if (!(*moodlet_value))
return
to_chat(minister, SPAN_BAD("Why should you care how [ministree] feels?"))
*moodlet_value = *moodlet_value * 0.5
/datum/component/timed_life/psiblock_drugs/proc/modify_ministry_receiving(ministree, minister, moodlet_value)
SIGNAL_HANDLER
if (!(*moodlet_value))
return
to_chat(ministree, SPAN_BAD("You feel nothing from [minister]'s words."))
*moodlet_value = *moodlet_value * 0.5
/datum/component/timed_life/psiblock_drugs/proc/modify_leadership_empathy(leader, moodlet_value)
SIGNAL_HANDLER
if (!(*moodlet_value))
return
to_chat(leader, SPAN_BAD("Why should you care about how others feel?"))
*moodlet_value = *moodlet_value * 0.5
/datum/component/timed_life/psiblock_drugs/process(seconds_per_tick)
. = ..()
// Variants of psiblocking drugs
/datum/component/timed_life/psiblock_drugs/yomi_genetics
/// The next time (in real life seconds) that a hand tremor will occur.
var/next_tremor_time = 0
/// The minimum time between hand tremors, in real life seconds.
var/min_tremor_time = 1 MINUTE
/// The maximum time between hand tremors, in real life seconds.
var/max_tremor_time = 3 MINUTES
/// The next time (in real life seconds) that a seizure will occur.
var/next_seizure_time = 0
/// The minimum time between seizures, in real life seconds.
var/min_seizure_time = 9 MINUTES + 30 SECONDS
/// The maximum time between seizures, in real life seconds.
var/max_seizure_time = 2 HOURS // Intentionally far greater than the actual duration, seizures are meant to be rare.
/// The penalty to accuracy for gun attacks due to hand tremors.
var/accuracy_penalty = 0.25
/// The penalty to dispersion for gun attacks due to hand tremors.
var/dispersion_penalty = 5
/// The penalty to surgery success chance due to hand tremors.
var/surgery_success_penalty = -10
/datum/component/timed_life/psiblock_drugs/yomi_genetics/Initialize(lifetime_seconds = 5 MINUTES)
. = ..()
next_tremor_time = REALTIMEOFDAY + rand(min_tremor_time, max_tremor_time)
next_seizure_time = REALTIMEOFDAY + rand(min_seizure_time, max_seizure_time)
// Some skill check penalties related to hand tremors. Tremors give a small penalty to some skill checks.
RegisterSignal(parent, COMSIG_BEFORE_GUN_FIRE, PROC_REF(check_tremor_gun), override = TRUE)
RegisterSignal(parent, COMSIG_GET_SURGERY_SUCCESS_MODIFIERS, PROC_REF(check_tremor_surgery), override = TRUE)
/datum/component/timed_life/psiblock_drugs/yomi_genetics/Destroy()
UnregisterSignal(parent, COMSIG_BEFORE_GUN_FIRE)
UnregisterSignal(parent, COMSIG_GET_SURGERY_SUCCESS_MODIFIERS)
return ..()
/datum/component/timed_life/psiblock_drugs/yomi_genetics/proc/check_tremor_gun(mob/shooter, accuracy_decrease, dispersion_increase)
SIGNAL_HANDLER
*accuracy_decrease = *accuracy_decrease + accuracy_penalty
*dispersion_increase = *dispersion_increase + dispersion_penalty
/datum/component/timed_life/psiblock_drugs/yomi_genetics/proc/check_tremor_surgery(mob/living/user, success_rate)
SIGNAL_HANDLER
*success_rate = *success_rate + surgery_success_penalty
/datum/component/timed_life/psiblock_drugs/yomi_genetics/process(seconds_per_tick)
. = ..()
var/time_of_day = REALTIMEOFDAY
if (time_of_day >= next_tremor_time)
owner.visible_message(SPAN_NOTICE("[owner]'s hand shakes..."), SPAN_NOTICE("Your hand shakes..."))
next_tremor_time = time_of_day + rand(min_tremor_time, max_tremor_time)
if (time_of_day >= next_seizure_time)
owner.seizure()
next_seizure_time = time_of_day + rand(min_seizure_time, max_seizure_time)
/datum/component/timed_life/psiblock_drugs/yomi_genetics/cheap
min_tremor_time = 30 SECONDS
max_tremor_time = 2 MINUTES
min_seizure_time = 5 MINUTES
max_seizure_time = 30 MINUTES
telepathy_cancel_probability = 75
psi_sensitivity_modifier = -0.75
accuracy_penalty = 0.35
dispersion_penalty = 10
surgery_success_penalty = -20
/datum/component/timed_life/psiblock_drugs/yomi_genetics/expensive
min_tremor_time = 2 MINUTES
max_tremor_time = 5 MINUTES
min_seizure_time = 30 MINUTES // Will never induce a seizure.
telepathy_cancel_probability = 100
psi_sensitivity_modifier = -1.25
accuracy_penalty = 0.15
dispersion_penalty = 2
surgery_success_penalty = -5