Files
Bubberstation/code/datums/components/squeak.dm
T
LemonInTheDark 0504c0a2b4 Improper forced qdel cleanup, some expanded del all verbs (#66595)
* Removes all supurfolus uses of QDEL_HINT_LETMELIVE

This define exists to allow abstract, sturucturally important things to
opt out of being qdeleted.
It does not exist to be a "Immune to everything" get out of jail free
card.
We have systems for this, and it's not appropriate here.

This change is inherently breaking, because things might be improperly
qdeling these things. Those issues will need to be resolved in future,
as they pop up

* Changes all needless uses of COMSIG_PARENT_PREQDELETED

It exists for things that want to block the qdel. If that's not you,
don't use it

* Adds force and hard del verbs, for chip and break glass cases
respectively

The harddel verb comes with two options before it's run, to let you
tailor it to your level of fucked

* Damn you nova

Adds proper parent returns instead of . = ..()

Co-authored-by: Seth Scherer <supernovaa41@gmx.com>

* Ensures immortality talismans cannot delete their human if something goes fuckey. Thanks ath/oro for pointing this out

Co-authored-by: Seth Scherer <supernovaa41@gmx.com>
2022-05-06 17:52:45 -07:00

150 lines
5.6 KiB
Plaintext

/datum/component/squeak
var/static/list/default_squeak_sounds = list('sound/items/toysqueak1.ogg'=1, 'sound/items/toysqueak2.ogg'=1, 'sound/items/toysqueak3.ogg'=1)
var/list/override_squeak_sounds
var/mob/holder
var/squeak_chance = 100
var/volume = 30
// This is so shoes don't squeak every step
var/steps = 0
var/step_delay = 1
// This is to stop squeak spam from inhand usage
var/last_use = 0
var/use_delay = 20
///extra-range for this component's sound
var/sound_extra_range = -1
///when sounds start falling off for the squeak
var/sound_falloff_distance = SOUND_DEFAULT_FALLOFF_DISTANCE
///sound exponent for squeak. Defaults to 10 as squeaking is loud and annoying enough.
var/sound_falloff_exponent = 10
///what we set connect_loc to if parent is an item
var/static/list/item_connections = list(
COMSIG_ATOM_ENTERED = .proc/play_squeak_crossed,
)
/datum/component/squeak/Initialize(custom_sounds, volume_override, chance_override, step_delay_override, use_delay_override, extrarange, falloff_exponent, fallof_distance)
if(!isatom(parent))
return COMPONENT_INCOMPATIBLE
RegisterSignal(parent, list(COMSIG_ATOM_ENTERED, COMSIG_ATOM_BLOB_ACT, COMSIG_ATOM_HULK_ATTACK, COMSIG_PARENT_ATTACKBY), .proc/play_squeak)
if(ismovable(parent))
RegisterSignal(parent, list(COMSIG_MOVABLE_BUMP, COMSIG_MOVABLE_IMPACT, COMSIG_PROJECTILE_BEFORE_FIRE), .proc/play_squeak)
AddComponent(/datum/component/connect_loc_behalf, parent, item_connections)
RegisterSignal(parent, COMSIG_MOVABLE_DISPOSING, .proc/disposing_react)
if(isitem(parent))
RegisterSignal(parent, list(COMSIG_ITEM_ATTACK, COMSIG_ITEM_ATTACK_OBJ, COMSIG_ITEM_HIT_REACT), .proc/play_squeak)
RegisterSignal(parent, COMSIG_ITEM_ATTACK_SELF, .proc/use_squeak)
RegisterSignal(parent, COMSIG_ITEM_EQUIPPED, .proc/on_equip)
RegisterSignal(parent, COMSIG_ITEM_DROPPED, .proc/on_drop)
if(istype(parent, /obj/item/clothing/shoes))
RegisterSignal(parent, COMSIG_SHOES_STEP_ACTION, .proc/step_squeak)
else if(isstructure(parent))
RegisterSignal(parent, COMSIG_ATOM_ATTACK_HAND, .proc/use_squeak)
if(istype(parent, /obj/item/organ/liver))
// Liver squeaking is depending on them functioning like a clown's liver
RegisterSignal(parent, SIGNAL_REMOVETRAIT(TRAIT_COMEDY_METABOLISM), .proc/on_comedy_metabolism_removal)
override_squeak_sounds = custom_sounds
if(chance_override)
squeak_chance = chance_override
if(volume_override)
volume = volume_override
if(isnum(step_delay_override))
step_delay = step_delay_override
if(isnum(use_delay_override))
use_delay = use_delay_override
if(isnum(extrarange))
sound_extra_range = extrarange
if(isnum(falloff_exponent))
sound_falloff_exponent = falloff_exponent
if(isnum(fallof_distance))
sound_falloff_distance = fallof_distance
/datum/component/squeak/UnregisterFromParent()
. = ..()
qdel(GetComponent(/datum/component/connect_loc_behalf))
/datum/component/squeak/proc/play_squeak()
SIGNAL_HANDLER
if(prob(squeak_chance))
if(!override_squeak_sounds)
playsound(parent, pick_weight(default_squeak_sounds), volume, TRUE, sound_extra_range, sound_falloff_exponent, falloff_distance = sound_falloff_distance)
else
playsound(parent, pick_weight(override_squeak_sounds), volume, TRUE, sound_extra_range, sound_falloff_exponent, falloff_distance = sound_falloff_distance)
/datum/component/squeak/proc/step_squeak()
SIGNAL_HANDLER
if(steps > step_delay)
play_squeak()
steps = 0
else
steps++
/datum/component/squeak/proc/play_squeak_crossed(datum/source, atom/movable/arrived, atom/old_loc, list/atom/old_locs)
SIGNAL_HANDLER
if(isitem(arrived))
var/obj/item/I = arrived
if(I.item_flags & ABSTRACT)
return
if(arrived.movement_type & (FLYING|FLOATING) || !arrived.has_gravity())
return
var/atom/current_parent = parent
if(isturf(current_parent?.loc))
play_squeak()
/datum/component/squeak/proc/use_squeak()
SIGNAL_HANDLER
if(last_use + use_delay < world.time)
last_use = world.time
play_squeak()
/datum/component/squeak/proc/on_equip(datum/source, mob/equipper, slot)
SIGNAL_HANDLER
holder = equipper
RegisterSignal(holder, COMSIG_MOVABLE_DISPOSING, .proc/disposing_react, override=TRUE)
RegisterSignal(holder, COMSIG_PARENT_QDELETING, .proc/holder_deleted, override=TRUE)
//override for the preqdeleted is necessary because putting parent in hands sends the signal that this proc is registered towards,
//so putting an object in hands and then equipping the item on a clothing slot (without dropping it first)
//will always runtime without override = TRUE
/datum/component/squeak/proc/on_drop(datum/source, mob/user)
SIGNAL_HANDLER
UnregisterSignal(user, COMSIG_MOVABLE_DISPOSING)
UnregisterSignal(user, COMSIG_PARENT_QDELETING)
holder = null
///just gets rid of the reference to holder in the case that theyre qdeleted
/datum/component/squeak/proc/holder_deleted(datum/source, datum/possible_holder)
SIGNAL_HANDLER
if(possible_holder == holder)
holder = null
// Disposal pipes related shits
/datum/component/squeak/proc/disposing_react(datum/source, obj/structure/disposalholder/holder, obj/machinery/disposal/source)
SIGNAL_HANDLER
//We don't need to worry about unregistering this signal as it will happen for us automaticaly when the holder is qdeleted
RegisterSignal(holder, COMSIG_ATOM_DIR_CHANGE, .proc/holder_dir_change)
/datum/component/squeak/proc/holder_dir_change(datum/source, old_dir, new_dir)
SIGNAL_HANDLER
//If the dir changes it means we're going through a bend in the pipes, let's pretend we bumped the wall
if(old_dir != new_dir)
play_squeak()
/datum/component/squeak/proc/on_comedy_metabolism_removal(datum/source, trait)
SIGNAL_HANDLER
qdel(src)