From 21bf516fc0e39f9c1cced4b39d6b7695c233469c Mon Sep 17 00:00:00 2001 From: SatinIsle Date: Sun, 22 Sep 2024 10:30:14 +0100 Subject: [PATCH] Replicant Species This PR makes the replicant outsider species a whitelist species after an application was made to play one as a crew member. Added the Gamma Replicant station species, accessible via whitelist only. This species has additional weaknesses (radiation and shock). They have a few unique organs: The crew version of the rage heart can only activate once every 60 minutes (rather than every minute) but lasts for 40 seconds. The mending lungs repair a few organs very very slowly, instead of extremely quickly. The plasma sac generates plasma a little faster without added phoron. Changed ventcrawl to specifically allow replicants to take underclothes and pocket sized items with them. I've balanced this for replicants only, but could remove the species check if wanted. Changed alien and resin structures so that they can also be destroyed by replicants (though more slowly than aliens). Added the user to the whitelist as approved here: https://forum.vore-station.net/viewtopic.php?f=45&t=2448&p=14179#p14179 --- code/__defines/mobs.dm | 1 + code/game/objects/structures/alien/alien.dm | 7 +++ .../materials/materials/organic/resin.dm | 20 ++++++-- .../human/species/station/replicant_crew.dm | 50 +++++++++++++++++++ code/modules/organs/subtypes/replicant.dm | 42 ++++++++++++++++ code/modules/ventcrawl/ventcrawl.dm | 7 +++ config/alienwhitelist.txt | 1 + vorestation.dme | 1 + 8 files changed, 124 insertions(+), 5 deletions(-) create mode 100644 code/modules/mob/living/carbon/human/species/station/replicant_crew.dm diff --git a/code/__defines/mobs.dm b/code/__defines/mobs.dm index 9478891464b..77e1e2d74ab 100644 --- a/code/__defines/mobs.dm +++ b/code/__defines/mobs.dm @@ -341,6 +341,7 @@ #define SPECIES_REPLICANT "Replicant" #define SPECIES_REPLICANT_ALPHA "Alpha Replicant" #define SPECIES_REPLICANT_BETA "Beta Replicant" +#define SPECIES_REPLICANT_CREW "Gamma Replicant" // Used to seperate simple animals by ""intelligence"". #define SA_PLANT 1 diff --git a/code/game/objects/structures/alien/alien.dm b/code/game/objects/structures/alien/alien.dm index cde036bc68f..9b192408fa8 100644 --- a/code/game/objects/structures/alien/alien.dm +++ b/code/game/objects/structures/alien/alien.dm @@ -81,6 +81,13 @@ health = 0 healthcheck() return + if(locate(/obj/item/organ/internal/xenos/resinspinner/replicant) in M.internal_organs) + if(!do_after(M, 3 SECONDS)) + return + visible_message ("[usr] strokes the [name] and it melts away!", 1) + health = 0 + healthcheck() + return visible_message("[usr] claws at the [name]!") health -= rand(5,10) healthcheck() diff --git a/code/modules/materials/materials/organic/resin.dm b/code/modules/materials/materials/organic/resin.dm index 5d46999c29c..4fe1d15cb9e 100644 --- a/code/modules/materials/materials/organic/resin.dm +++ b/code/modules/materials/materials/organic/resin.dm @@ -19,17 +19,27 @@ var/mob/living/carbon/M = user if(istype(M) && locate(/obj/item/organ/internal/xenos/hivenode) in M.internal_organs) return TRUE + if(istype(M) && locate(/obj/item/organ/internal/xenos/resinspinner/replicant) in M.internal_organs) + return TRUE return FALSE /datum/material/resin/wall_touch_special(var/turf/simulated/wall/W, var/mob/living/L) var/mob/living/carbon/M = L if(istype(M) && locate(/obj/item/organ/internal/xenos/hivenode) in M.internal_organs) - to_chat(M, "\The [W] shudders under your touch, starting to become porous.") + to_chat(M, "\The [W] shudders under your touch, starting to become porous.") playsound(W, 'sound/effects/attackblob.ogg', 50, 1) - if(do_after(L, 5 SECONDS)) - spawn(2) - playsound(W, 'sound/effects/attackblob.ogg', 100, 1) - W.dismantle_wall() + if(!do_after(L, 5 SECONDS)) + return FALSE + playsound(W, 'sound/effects/attackblob.ogg', 100, 1) + W.dismantle_wall() + return TRUE + if(istype(M) && locate(/obj/item/organ/internal/xenos/resinspinner/replicant) in M.internal_organs) + to_chat(M, "\The [W] shudders under your touch, starting to become porous.") + playsound(W, 'sound/effects/attackblob.ogg', 50, 1) + if(!do_after(L, 5 SECONDS)) + return FALSE + playsound(W, 'sound/effects/attackblob.ogg', 100, 1) + W.dismantle_wall() return TRUE return FALSE diff --git a/code/modules/mob/living/carbon/human/species/station/replicant_crew.dm b/code/modules/mob/living/carbon/human/species/station/replicant_crew.dm new file mode 100644 index 00000000000..d5d3ed3c040 --- /dev/null +++ b/code/modules/mob/living/carbon/human/species/station/replicant_crew.dm @@ -0,0 +1,50 @@ +/datum/species/shapeshifter/replicant/crew + name = SPECIES_REPLICANT_CREW + blurb = "Replicants are one of the few remaining living examples of precursor technology. \ + While their origins remain unknown, they are a facsimile of organic life held together by amalgamate, \ + rubbery flesh and anomalous organs. Whilst their original purpose is speculated to be used through cortical \ + mirrors as a way to 'wirelessly exist' in a different body via VR pods, this specific variant has had its \ + forking capabilities severed in exchange for a more stable, self-sufficient (albeit weaker) form." + + min_age = 18 + max_age = 200 + blood_color = "#C0C0C0" + + radiation_mod = 1.2 //Affected more by radiation + siemens_coefficient = 1.5 //Don't get electrocuted + + secondary_langs = list() // None by default + + has_organ = list( + O_HEART = /obj/item/organ/internal/heart/replicant/rage/crew, + O_LUNGS = /obj/item/organ/internal/lungs/replicant/mending/crew, + O_VOICE = /obj/item/organ/internal/voicebox/replicant, + O_LIVER = /obj/item/organ/internal/liver/replicant, + O_KIDNEYS = /obj/item/organ/internal/kidneys/replicant, + O_BRAIN = /obj/item/organ/internal/brain/replicant/torso, + O_EYES = /obj/item/organ/internal/eyes/replicant, + O_AREJECT = /obj/item/organ/internal/immunehub/replicant, + O_VENTC = /obj/item/organ/internal/metamorphgland/replicant, + O_PLASMA = /obj/item/organ/internal/xenos/plasmavessel/replicant/crew, + O_RESIN = /obj/item/organ/internal/xenos/resinspinner/replicant, + O_STOMACH = /obj/item/organ/internal/stomach, + O_INTESTINE = /obj/item/organ/internal/intestine + ) + + appearance_flags = HAS_SKIN_COLOR | HAS_EYE_COLOR | HAS_HAIR_COLOR | HAS_UNDERWEAR | HAS_LIPS + spawn_flags = SPECIES_CAN_JOIN | SPECIES_IS_WHITELISTED | SPECIES_WHITELIST_SELECTABLE + color_mult = 1 + valid_transform_species = list(SPECIES_HUMAN, SPECIES_HUMAN_VATBORN, SPECIES_UNATHI, SPECIES_TAJ, SPECIES_SKRELL, SPECIES_ALTEVIAN, SPECIES_TESHARI, SPECIES_MONKEY, SPECIES_LLEILL, SPECIES_VULPKANIN, SPECIES_ZORREN_HIGH, SPECIES_RAPALA, SPECIES_NEVREAN, SPECIES_VASILISSAN, SPECIES_AKULA) + + inherent_verbs = list( + /mob/living/carbon/human/proc/shapeshifter_select_shape, + /mob/living/carbon/human/proc/shapeshifter_select_colour, + /mob/living/carbon/human/proc/shapeshifter_select_hair, + /mob/living/carbon/human/proc/shapeshifter_select_hair_colors, + /mob/living/carbon/human/proc/shapeshifter_select_gender, + /mob/living/carbon/human/proc/shapeshifter_select_wings, + /mob/living/carbon/human/proc/shapeshifter_select_tail, + /mob/living/carbon/human/proc/shapeshifter_select_ears, + /mob/living/carbon/human/proc/shapeshifter_select_eye_colour, + /mob/living/proc/set_size + ) diff --git a/code/modules/organs/subtypes/replicant.dm b/code/modules/organs/subtypes/replicant.dm index 51605ab098d..2aaa4c6fd23 100644 --- a/code/modules/organs/subtypes/replicant.dm +++ b/code/modules/organs/subtypes/replicant.dm @@ -53,6 +53,20 @@ can_reject = FALSE icon_state = "plasma_grey" +/obj/item/organ/internal/xenos/plasmavessel/replicant/crew/handle_organ_proc_special() + if(!istype(owner)) + return + + var/modifier = 1 - 0.5 * is_bruised() + + if(owner.bloodstr.has_reagent("phoron")) + adjust_plasma(round(4 * modifier)) + + if(owner.ingested.has_reagent("phoron")) + adjust_plasma(round(2 * modifier)) + + adjust_plasma(2) //Make it a decent amount so people can actually build stuff without stealing all of medbays phoron + /obj/item/organ/internal/xenos/acidgland/replicant name = "replicant aerosol tubule" desc = "A long, rubbery tube that ends in a hard plastic-like bulb." @@ -152,6 +166,22 @@ owner.add_modifier(/datum/modifier/berserk, 20 SECONDS) take_damage(5) +/obj/item/organ/internal/heart/replicant/rage/crew/handle_organ_proc_special() + if(!owner) + return + + var/damage_tally = 0 + var/pain_tally = 0 + damage_tally += owner.getBruteLoss() + damage_tally += owner.getFireLoss() + pain_tally += owner.getHalLoss() + + if(((damage_tally >= 50 || prev_damage_tally >= 50) && prev_damage_tally - damage_tally < 0) || pain_tally >= 60) + if(world.time > last_activation_time + 60 MINUTES) //Can only be activated once every 60 minutes to prevent it being able to be spammed + last_activation_time = world.time + owner.add_modifier(/datum/modifier/berserk, 40 SECONDS) //Lasts a little longer so that it can actually get some use seeing as it activates so infrequently + take_damage(5) + /obj/item/organ/internal/lungs/replicant/mending name = "replicant hive lungs" desc = "A pair of rubbery sacs with large portions dedicated to honeycombed nanite filters." @@ -169,3 +199,15 @@ var/obj/item/organ/O = owner.internal_organs_by_name[o_tag] if(O) O.take_damage(-1 * modifier) + +/obj/item/organ/internal/lungs/replicant/mending/crew/handle_organ_proc_special() + if(!owner) + return + + var/modifier = 1 - (0.5 * is_bruised()) + + if(istype(owner)) + for(var/o_tag in repair_list) + var/obj/item/organ/O = owner.internal_organs_by_name[o_tag] + if(O) + O.take_damage(-0.01 * modifier) //Very very slow regen, but still cool flavour diff --git a/code/modules/ventcrawl/ventcrawl.dm b/code/modules/ventcrawl/ventcrawl.dm index 0acc4626b18..2ae067c4433 100644 --- a/code/modules/ventcrawl/ventcrawl.dm +++ b/code/modules/ventcrawl/ventcrawl.dm @@ -90,6 +90,13 @@ var/list/ventcrawl_machinery = list( /mob/living/carbon/human/is_allowed_vent_crawl_item(var/obj/item/carried_item) if(carried_item in organs) return 1 + if(species.name == SPECIES_REPLICANT_CREW) + if(istype(carried_item, /obj/item/clothing/under)) + return 1 //Allow them to not vent crawl naked + if(istype(carried_item, /obj/item)) + var/obj/item/I = carried_item + if(I.w_class <= 2) + return 1 //Allow them to carry items that fit in pockets return ..() /mob/living/proc/ventcrawl_carry() diff --git a/config/alienwhitelist.txt b/config/alienwhitelist.txt index 06a1d4e64fd..79be051a631 100644 --- a/config/alienwhitelist.txt +++ b/config/alienwhitelist.txt @@ -126,6 +126,7 @@ ontejbjoav - Black-Eyed Shadekin ontejbjoav - Diona oreganovulgaris - Xenochimera oscarholmes - Protean +oscarholmes - Gamma Replicant owwy - Black-Eyed Shadekin oxenfree - Protean ozyton - Black-Eyed Shadekin diff --git a/vorestation.dme b/vorestation.dme index 9f8a730d4f0..99abec6d811 100644 --- a/vorestation.dme +++ b/vorestation.dme @@ -3006,6 +3006,7 @@ #include "code\modules\mob\living\carbon\human\species\station\prometheans.dm" #include "code\modules\mob\living\carbon\human\species\station\prometheans_vr.dm" #include "code\modules\mob\living\carbon\human\species\station\prommie_blob.dm" +#include "code\modules\mob\living\carbon\human\species\station\replicant_crew.dm" #include "code\modules\mob\living\carbon\human\species\station\station.dm" #include "code\modules\mob\living\carbon\human\species\station\station_special_abilities_vr.dm" #include "code\modules\mob\living\carbon\human\species\station\station_special_vr.dm"