mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2025-12-10 17:52:36 +00:00
* Let's you talk through action figures, plushies, and toy mechs with `.l` and `.r`. Also a big clean up of `say` because its support for non-mobs was lackluster. * Update code/game/objects/items/plushes.dm * a --------- Co-authored-by: MrMelbert <51863163+MrMelbert@users.noreply.github.com> Co-authored-by: Pinta <68373373+softcerv@users.noreply.github.com>
155 lines
6.3 KiB
Plaintext
155 lines
6.3 KiB
Plaintext
/**
|
|
* Common behaviour shared by things which are minions to a blob
|
|
*/
|
|
/datum/component/blob_minion
|
|
dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
|
|
/// Overmind who is our boss
|
|
var/mob/camera/blob/overmind
|
|
/// Callback to run if overmind strain changes
|
|
var/datum/callback/on_strain_changed
|
|
|
|
/datum/component/blob_minion/Initialize(mob/camera/blob/overmind, datum/callback/on_strain_changed)
|
|
. = ..()
|
|
if (!isliving(parent))
|
|
return COMPONENT_INCOMPATIBLE
|
|
src.on_strain_changed = on_strain_changed
|
|
register_overlord(overmind)
|
|
|
|
/datum/component/blob_minion/InheritComponent(datum/component/new_comp, i_am_original, mob/camera/blob/overmind, datum/callback/on_strain_changed)
|
|
if (!isnull(on_strain_changed))
|
|
src.on_strain_changed = on_strain_changed
|
|
register_overlord(overmind)
|
|
|
|
/datum/component/blob_minion/proc/register_overlord(mob/camera/blob/overmind)
|
|
if (isnull(overmind))
|
|
return
|
|
src.overmind = overmind
|
|
overmind.register_new_minion(parent)
|
|
RegisterSignal(overmind, COMSIG_QDELETING, PROC_REF(overmind_deleted))
|
|
RegisterSignal(overmind, COMSIG_BLOB_SELECTED_STRAIN, PROC_REF(overmind_properties_changed))
|
|
overmind_properties_changed(overmind, overmind.blobstrain)
|
|
|
|
/// Our overmind is gone, uh oh!
|
|
/datum/component/blob_minion/proc/overmind_deleted()
|
|
SIGNAL_HANDLER
|
|
overmind = null
|
|
overmind_properties_changed()
|
|
|
|
/// Our overmind has changed colour and properties
|
|
/datum/component/blob_minion/proc/overmind_properties_changed(mob/camera/blob/overmind, datum/blobstrain/new_strain)
|
|
SIGNAL_HANDLER
|
|
var/mob/living/living_parent = parent
|
|
living_parent.update_appearance(UPDATE_ICON)
|
|
on_strain_changed?.Invoke(overmind, new_strain)
|
|
|
|
/datum/component/blob_minion/RegisterWithParent()
|
|
var/mob/living/living_parent = parent
|
|
living_parent.pass_flags |= PASSBLOB
|
|
living_parent.faction |= ROLE_BLOB
|
|
ADD_TRAIT(parent, TRAIT_BLOB_ALLY, REF(src))
|
|
remove_verb(parent, /mob/living/verb/pulled) // No dragging people into the blob
|
|
RegisterSignal(parent, COMSIG_MOB_MIND_INITIALIZED, PROC_REF(on_mind_init))
|
|
RegisterSignal(parent, COMSIG_ATOM_UPDATE_ICON, PROC_REF(on_update_appearance))
|
|
RegisterSignal(parent, COMSIG_MOB_GET_STATUS_TAB_ITEMS, PROC_REF(on_update_status_tab))
|
|
RegisterSignal(parent, COMSIG_ATOM_BLOB_ACT, PROC_REF(on_blob_touched))
|
|
RegisterSignal(parent, COMSIG_ATOM_FIRE_ACT, PROC_REF(on_burned))
|
|
RegisterSignal(parent, COMSIG_ATOM_TRIED_PASS, PROC_REF(on_attempted_pass))
|
|
RegisterSignal(parent, COMSIG_MOVABLE_SPACEMOVE, PROC_REF(on_space_move))
|
|
RegisterSignal(parent, COMSIG_MOB_TRY_SPEECH, PROC_REF(on_try_speech))
|
|
RegisterSignal(parent, COMSIG_MOB_CHANGED_TYPE, PROC_REF(on_transformed))
|
|
living_parent.update_appearance(UPDATE_ICON)
|
|
GLOB.blob_telepathy_mobs |= parent
|
|
|
|
/datum/component/blob_minion/UnregisterFromParent()
|
|
if (!isnull(overmind))
|
|
overmind.blob_mobs -= parent
|
|
var/mob/living/living_parent = parent
|
|
living_parent.pass_flags &= ~PASSBLOB
|
|
living_parent.faction -= ROLE_BLOB
|
|
REMOVE_TRAIT(parent, TRAIT_BLOB_ALLY, REF(src))
|
|
add_verb(parent, /mob/living/verb/pulled)
|
|
UnregisterSignal(parent, list(
|
|
COMSIG_ATOM_BLOB_ACT,
|
|
COMSIG_ATOM_FIRE_ACT,
|
|
COMSIG_ATOM_TRIED_PASS,
|
|
COMSIG_ATOM_UPDATE_ICON,
|
|
COMSIG_MOB_TRY_SPEECH,
|
|
COMSIG_MOB_CHANGED_TYPE,
|
|
COMSIG_MOB_GET_STATUS_TAB_ITEMS,
|
|
COMSIG_MOB_MIND_INITIALIZED,
|
|
COMSIG_MOVABLE_SPACEMOVE,
|
|
))
|
|
GLOB.blob_telepathy_mobs -= parent
|
|
|
|
/// Become blobpilled when we gain a mind
|
|
/datum/component/blob_minion/proc/on_mind_init(mob/living/minion, datum/mind/new_mind)
|
|
SIGNAL_HANDLER
|
|
if (isnull(overmind))
|
|
return
|
|
var/datum/antagonist/blob_minion/minion_motive = new(overmind)
|
|
new_mind.add_antag_datum(minion_motive)
|
|
|
|
/// When our icon is updated, update our colour too
|
|
/datum/component/blob_minion/proc/on_update_appearance(mob/living/minion)
|
|
SIGNAL_HANDLER
|
|
if(isnull(overmind))
|
|
minion.remove_atom_colour(FIXED_COLOUR_PRIORITY)
|
|
return
|
|
minion.add_atom_colour(overmind.blobstrain.color, FIXED_COLOUR_PRIORITY)
|
|
|
|
/// When our icon is updated, update our colour too
|
|
/datum/component/blob_minion/proc/on_update_status_tab(mob/living/minion, list/status_items)
|
|
SIGNAL_HANDLER
|
|
if (isnull(overmind))
|
|
return
|
|
status_items += "Blobs to Win: [length(overmind.blobs_legit)]/[overmind.blobwincount]"
|
|
|
|
/// If we feel the gentle caress of a blob, we feel better
|
|
/datum/component/blob_minion/proc/on_blob_touched(mob/living/minion)
|
|
SIGNAL_HANDLER
|
|
if(minion.stat == DEAD || minion.health >= minion.maxHealth)
|
|
return COMPONENT_CANCEL_BLOB_ACT // Don't hurt us in order to heal us
|
|
for(var/i in 1 to 2)
|
|
var/obj/effect/temp_visual/heal/heal_effect = new /obj/effect/temp_visual/heal(get_turf(parent)) // hello yes you are being healed
|
|
heal_effect.color = isnull(overmind) ? COLOR_BLACK : overmind.blobstrain.complementary_color
|
|
minion.heal_overall_damage(minion.maxHealth * BLOBMOB_HEALING_MULTIPLIER)
|
|
return COMPONENT_CANCEL_BLOB_ACT
|
|
|
|
/// If we feel the fearsome bite of open flame, we feel worse
|
|
/datum/component/blob_minion/proc/on_burned(mob/living/minion, exposed_temperature, exposed_volume)
|
|
SIGNAL_HANDLER
|
|
if(isnull(exposed_temperature))
|
|
minion.adjustFireLoss(5)
|
|
return
|
|
minion.adjustFireLoss(clamp(0.01 * exposed_temperature, 1, 5))
|
|
|
|
/// Someone is attempting to move through us, allow it if it is a blob tile
|
|
/datum/component/blob_minion/proc/on_attempted_pass(mob/living/minion, atom/movable/incoming)
|
|
SIGNAL_HANDLER
|
|
if(istype(incoming, /obj/structure/blob))
|
|
return COMSIG_COMPONENT_PERMIT_PASSAGE
|
|
|
|
/// If we're near a blob, stop drifting
|
|
/datum/component/blob_minion/proc/on_space_move(mob/living/minion)
|
|
SIGNAL_HANDLER
|
|
var/obj/structure/blob/blob_handhold = locate() in range(1, parent)
|
|
if (!isnull(blob_handhold))
|
|
return COMSIG_MOVABLE_STOP_SPACEMOVE
|
|
|
|
/// We only speak telepathically to blobs
|
|
/datum/component/blob_minion/proc/on_try_speech(mob/living/minion, message, ignore_spam, forced)
|
|
SIGNAL_HANDLER
|
|
var/spanned_message = minion.say_quote(message)
|
|
var/rendered = span_blob("<b>\[Blob Telepathy\] [minion.real_name]</b> [spanned_message]")
|
|
relay_to_list_and_observers(rendered, GLOB.blob_telepathy_mobs, minion)
|
|
return COMPONENT_CANNOT_SPEAK
|
|
|
|
/// Called when a blob minion is transformed into something else, hopefully a spore into a zombie
|
|
/datum/component/blob_minion/proc/on_transformed(mob/living/minion, mob/living/replacement)
|
|
SIGNAL_HANDLER
|
|
overmind?.assume_direct_control(replacement)
|
|
|
|
/datum/component/blob_minion/PostTransfer()
|
|
if(!isliving(parent))
|
|
return COMPONENT_INCOMPATIBLE
|