diff --git a/code/__DEFINES/dcs/signals.dm b/code/__DEFINES/dcs/signals.dm index a8a34a3ea07..a9054e3f578 100644 --- a/code/__DEFINES/dcs/signals.dm +++ b/code/__DEFINES/dcs/signals.dm @@ -560,6 +560,7 @@ ///Mob is trying to open the wires of a target [/atom], from /datum/wires/interactable(): (atom/target) #define COMSIG_TRY_WIRES_INTERACT "try_wires_interact" #define COMPONENT_CANT_INTERACT_WIRES (1<<0) +#define COMSIG_MOB_EMOTED(emote_key) "mob_emoted_[emote_key]" ///from /obj/structure/door/crush(): (mob/living/crushed, /obj/machinery/door/crushing_door) #define COMSIG_LIVING_DOORCRUSHED "living_doorcrush" diff --git a/code/__DEFINES/misc.dm b/code/__DEFINES/misc.dm index a1afc70785a..b152ed71267 100644 --- a/code/__DEFINES/misc.dm +++ b/code/__DEFINES/misc.dm @@ -542,6 +542,8 @@ GLOBAL_LIST_INIT(pda_styles, sortList(list(MONO, VT, ORBITRON, SHARE))) #define IGNORE_TARGET_LOC_CHANGE (1<<1) #define IGNORE_HELD_ITEM (1<<2) #define IGNORE_INCAPACITATED (1<<3) +///Used to prevent important slowdowns from being abused by drugs like kronkaine +#define IGNORE_SLOWDOWNS (1<<4) // Skillchip categories //Various skillchip categories. Use these when setting which categories a skillchip restricts being paired with diff --git a/code/__DEFINES/reagents.dm b/code/__DEFINES/reagents.dm index 2570442ba07..69bb4680f76 100644 --- a/code/__DEFINES/reagents.dm +++ b/code/__DEFINES/reagents.dm @@ -176,3 +176,6 @@ #define GOLDSCHLAGER_GOLD (1) #define GOLDSCHLAGER_GOLD_RATIO (GOLDSCHLAGER_GOLD/(GOLDSCHLAGER_VODKA+GOLDSCHLAGER_GOLD)) + +#define BLASTOFF_DANCE_MOVE_CHANCE_PER_UNIT 3 +#define BLASTOFF_DANCE_MOVES_PER_SUPER_MOVE 3 diff --git a/code/__DEFINES/sound.dm b/code/__DEFINES/sound.dm index 9c6ad94a791..0850e238bdb 100644 --- a/code/__DEFINES/sound.dm +++ b/code/__DEFINES/sound.dm @@ -87,6 +87,7 @@ #define SOUND_ENVIRONMENT_DIZZY 24 #define SOUND_ENVIRONMENT_PSYCHOTIC 25 //If we ever make custom ones add them here +#define SOUND_ENVIROMENT_PHASED list(1.8, 0.5, -1000, -4000, 0, 5, 0.1, 1, -15500, 0.007, 2000, 0.05, 0.25, 1, 1.18, 0.348, -5, 2000, 250, 0, 3, 100, 63) //"sound areas": easy way of keeping different types of areas consistent. #define SOUND_AREA_STANDARD_STATION SOUND_ENVIRONMENT_PARKING_LOT diff --git a/code/__DEFINES/traits.dm b/code/__DEFINES/traits.dm index 4dada5fe523..54526b60f4c 100644 --- a/code/__DEFINES/traits.dm +++ b/code/__DEFINES/traits.dm @@ -329,7 +329,8 @@ Remember to update _globalvars/traits.dm if you're adding/removing/renaming trai #define TRAIT_NOBLEED "nobleed" //This carbon doesn't bleed /// This atom can ignore the "is on a turf" check for simple AI datum attacks, allowing them to attack from bags or lockers as long as any other conditions are met #define TRAIT_AI_BAGATTACK "bagattack" - +/// This mobs bodyparts are invisible but still clickable. +#define TRAIT_INVISIBLE_MAN "invisible_man" // You can stare into the abyss, but it does not stare back. // You're immune to the hallucination effect of the supermatter, either // through force of will, or equipment. Present on /mob or /datum/mind diff --git a/code/__HELPERS/mobs.dm b/code/__HELPERS/mobs.dm index 3361793979c..d1436a0d781 100644 --- a/code/__HELPERS/mobs.dm +++ b/code/__HELPERS/mobs.dm @@ -204,6 +204,9 @@ GLOBAL_LIST_EMPTY(species_list) if(target.pixel_x != 0) //shifts the progress bar if target has an offset sprite progbar.bar.pixel_x -= target.pixel_x + if(!(timed_action_flags & IGNORE_SLOWDOWNS)) + time *= user.cached_multiplicative_actions_slowdown + var/endtime = world.time+time var/starttime = world.time . = TRUE @@ -281,7 +284,8 @@ GLOBAL_LIST_EMPTY(species_list) var/holding = user.get_active_held_item() - delay *= user.cached_multiplicative_actions_slowdown + if(!(timed_action_flags & IGNORE_SLOWDOWNS)) + delay *= user.cached_multiplicative_actions_slowdown var/datum/progressbar/progbar if(progress) @@ -337,7 +341,8 @@ GLOBAL_LIST_EMPTY(species_list) return FALSE var/user_loc = user.loc - time *= user.cached_multiplicative_actions_slowdown + if(!(timed_action_flags & IGNORE_SLOWDOWNS)) + time *= user.cached_multiplicative_actions_slowdown var/drifting = FALSE if(!user.Process_Spacemove(0) && user.inertia_dir) diff --git a/code/_globalvars/lists/maintenance_loot.dm b/code/_globalvars/lists/maintenance_loot.dm index c8bd256d783..d47bc5d9739 100644 --- a/code/_globalvars/lists/maintenance_loot.dm +++ b/code/_globalvars/lists/maintenance_loot.dm @@ -118,12 +118,12 @@ GLOBAL_LIST_INIT(common_loot, list( //common: basic items /obj/item/assembly/timer = 1, /obj/item/assembly/igniter = 1, /obj/item/assembly/health = 1, - /obj/item/stack/package_wrap = 1, /obj/item/stack/wrapping_paper = 1, ) = 1, list(//medical and chemicals + /obj/item/stock_parts/cell/lead = 1, /obj/item/storage/fancy/cigarettes/dromedaryco = 1, /obj/item/grenade/chem_grenade/cleaner = 1, /obj/item/storage/box/matches = 1, @@ -132,6 +132,7 @@ GLOBAL_LIST_INIT(common_loot, list( //common: basic items /obj/item/reagent_containers/glass/rag = 1, /obj/item/reagent_containers/hypospray/medipen/pumpup = 2, /obj/item/reagent_containers/glass/bottle/random_buffer = 2, + /obj/item/lead_pipe = 1, ) = 1, list(//food @@ -198,6 +199,7 @@ GLOBAL_LIST_INIT(uncommon_loot, list(//uncommon: useful items /obj/item/paper/fluff/stations/soap = 1, //recipes count as crafting. /obj/item/plaque = 1, /obj/item/storage/box/clown = 1, + /obj/item/seeds/kronkus = 1, ) = 8, list(//medical and chemicals diff --git a/code/_globalvars/traits.dm b/code/_globalvars/traits.dm index 0f94736dd58..c842effb3f9 100644 --- a/code/_globalvars/traits.dm +++ b/code/_globalvars/traits.dm @@ -162,6 +162,8 @@ GLOBAL_LIST_INIT(traits_by_type, list( "TRAIT_KISS_OF_DEATH" = TRAIT_KISS_OF_DEATH, "TRAIT_ANXIOUS" = TRAIT_ANXIOUS, "TRAIT_WEAK_SOUL" = TRAIT_WEAK_SOUL, + "TRAIT_INVISIBLE_MAN" = TRAIT_INVISIBLE_MAN + ), /obj/item/bodypart = list( "TRAIT_PARALYSIS" = TRAIT_PARALYSIS, diff --git a/code/datums/diseases/adrenal_crisis.dm b/code/datums/diseases/adrenal_crisis.dm new file mode 100644 index 00000000000..44eeec8b36b --- /dev/null +++ b/code/datums/diseases/adrenal_crisis.dm @@ -0,0 +1,38 @@ +/datum/disease/adrenal_crisis + form = "Condition" + name = "Adrenal Crisis" + max_stages = 2 + cure_text = "Trauma" + cures = list(/datum/reagent/determination) + cure_chance = 10 + agent = "Shitty Adrenal Glands" + viable_mobtypes = list(/mob/living/carbon/human) + permeability_mod = 1 + desc = "If left untreated the subject will suffer from lethargy, dizziness and periodic loss of conciousness." + severity = DISEASE_SEVERITY_MEDIUM + disease_flags = CAN_CARRY|CAN_RESIST + spread_flags = DISEASE_SPREAD_NON_CONTAGIOUS + visibility_flags = HIDDEN_PANDEMIC + bypasses_immunity = TRUE + +/datum/disease/adrenal_crisis/stage_act(delta_time, times_fired) + . = ..() + if(!.) + return + + switch(stage) + if(1) + if(DT_PROB(2.5, delta_time)) + to_chat(affected_mob, span_warning(pick("You feel lightheaded.", "You feel lethargic."))) + if(2) + if(DT_PROB(5, delta_time)) + affected_mob.Unconscious(40) + + if(DT_PROB(10, delta_time)) + affected_mob.slurring += 7 + + if(DT_PROB(7, delta_time)) + affected_mob.Dizzy(10) + + if(DT_PROB(2.5, delta_time)) + to_chat(affected_mob, span_warning(pick("You feel pain shoot down your legs!", "You feel like you are going to pass out at any moment.", "You feel really dizzy."))) diff --git a/code/datums/emotes.dm b/code/datums/emotes.dm index 91850cacbfd..077a8f81e72 100644 --- a/code/datums/emotes.dm +++ b/code/datums/emotes.dm @@ -145,6 +145,8 @@ else user.visible_message(msg, blind_message = "You hear how [user] [msg]", visible_message_flags = EMOTE_MESSAGE) + SEND_SIGNAL(user, COMSIG_MOB_EMOTED(key)) + /** * For handling emote cooldown, return true to allow the emote to happen. * diff --git a/code/datums/quirks/negative.dm b/code/datums/quirks/negative.dm index 335901bd364..972e16dcd53 100644 --- a/code/datums/quirks/negative.dm +++ b/code/datums/quirks/negative.dm @@ -593,7 +593,7 @@ medical_record_text = "Patient has a history of hard drugs." hardcore_value = 4 processing_quirk = TRUE - var/drug_list = list(/datum/reagent/drug/crank, /datum/reagent/drug/krokodil, /datum/reagent/medicine/morphine, /datum/reagent/drug/happiness, /datum/reagent/drug/methamphetamine) //List of possible IDs + var/drug_list = list(/datum/reagent/drug/blastoff, /datum/reagent/drug/krokodil, /datum/reagent/medicine/morphine, /datum/reagent/drug/happiness, /datum/reagent/drug/methamphetamine) //List of possible IDs var/datum/reagent/reagent_type //!If this is defined, reagent_id will be unused and the defined reagent type will be instead. var/datum/reagent/reagent_instance //! actual instanced version of the reagent var/where_drug //! Where the drug spawned diff --git a/code/game/objects/effects/spawners/lootdrop.dm b/code/game/objects/effects/spawners/lootdrop.dm index 9bf1f1ed282..af2d7b93348 100644 --- a/code/game/objects/effects/spawners/lootdrop.dm +++ b/code/game/objects/effects/spawners/lootdrop.dm @@ -111,7 +111,7 @@ /obj/item/storage/box/matches = 3, /obj/item/reagent_containers/syringe/contraband/space_drugs = 1, /obj/item/reagent_containers/syringe/contraband/krokodil = 1, - /obj/item/reagent_containers/syringe/contraband/crank = 1, + /obj/item/reagent_containers/syringe/contraband/saturnx = 1, /obj/item/reagent_containers/syringe/contraband/methamphetamine = 1, /obj/item/reagent_containers/syringe/contraband/bath_salts = 1, /obj/item/reagent_containers/syringe/contraband/fentanyl = 1, diff --git a/code/game/objects/items/drug_items.dm b/code/game/objects/items/drug_items.dm new file mode 100644 index 00000000000..4faa873b0bd --- /dev/null +++ b/code/game/objects/items/drug_items.dm @@ -0,0 +1,71 @@ +/obj/item/food/drug + name = "generic drug" + desc = "I am error" + icon = 'icons/obj/drugs.dmi' + foodtypes = GROSS + food_flags = FOOD_FINGER_FOOD + max_volume = 50 + eat_time = 1 SECONDS + tastes = list("drugs" = 2, "chemicals" = 1) + eatverbs = list("gnaws" = 1) + bite_consumption = 10 + w_class = WEIGHT_CLASS_TINY + preserved_food = TRUE + +/obj/item/food/drug/saturnx + name = "saturnX glob" + desc = "A congealed glob of pure saturnX.\nThis compound was first discovered during the infancy of cloaking technology and at the time thought to be a promising candidate agent. It was withdrawn for consideration after the researchers discovered a slew of associated safety issues including thought disorders and hepatoxicity.\nIt has since attained some limited popularity as a street drug." + icon_state = "saturnx_glob" //tell kryson to sprite two more variants in the future. + food_reagents = list(/datum/reagent/drug/saturnx = 10) + +/obj/item/food/drug/moon_rock + name = "moon rock" + desc = "A small hard lump of kronkaine freebase.\nIt is said the average kronkaine addict causes as much criminal damage as four cat burglars, two arsonists and one rabid pit bull terrier combined." + icon_state = "moon_rock1" + food_reagents = list(/datum/reagent/drug/kronkaine = 10) + +/obj/item/food/drug/moon_rock/Initialize() + . = ..() + icon_state = pick("moon_rock1", "moon_rock2", "moon_rock3") + +/obj/item/reagent_containers/glass/blastoff_ampoule + name = "bLaSToFF ampoule" //stylized name + desc = "A small ampoule. The liquid inside appears to be boiling violently.\nYou suspect it contains bLasSToFF; the drug thought to be the cause of the infamous Luna nightclub mass casualty incident." + icon = 'icons/obj/drugs.dmi' + icon_state = "blastoff_ampoule" + base_icon_state = "blastoff_ampoule" + volume = 20 + reagent_flags = TRANSPARENT + spillable = FALSE + list_reagents = list(/datum/reagent/drug/blastoff = 10) + +/obj/item/reagent_containers/glass/blastoff_ampoule/update_icon_state() + . = ..() + if(!reagents.total_volume) + icon_state = "[base_icon_state]_empty" + else if(spillable) + icon_state = "[base_icon_state]_open" + else + icon_state = base_icon_state + +/obj/item/reagent_containers/glass/blastoff_ampoule/attack_self(mob/user) + if(!user.canUseTopic(src, BE_CLOSE, NO_DEXTERITY) || spillable) + return ..() + reagent_flags |= OPENCONTAINER + spillable = TRUE + playsound(src, 'sound/items/ampoule_snap.ogg', 40) + update_appearance() + +/obj/item/reagent_containers/glass/blastoff_ampoule/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum) + . = ..() + if(.) + return + if(QDELING(src) || !hit_atom) //Invalid loc + return + var/obj/item/shard/ampoule_shard = new(drop_location()) + playsound(src, "shatter", 40, TRUE) + transfer_fingerprints_to(ampoule_shard) + spillable = TRUE + SplashReagents(hit_atom, TRUE) + qdel(src) + hit_atom.Bumped(ampoule_shard) diff --git a/code/game/objects/items/handcuffs.dm b/code/game/objects/items/handcuffs.dm index e8d653eb428..a0e3467ceb4 100644 --- a/code/game/objects/items/handcuffs.dm +++ b/code/game/objects/items/handcuffs.dm @@ -64,7 +64,7 @@ playsound(loc, cuffsound, 30, TRUE, -2) log_combat(user, C, "attempted to handcuff") - if(do_mob(user, C, 30) && C.canBeHandcuffed()) + if(do_mob(user, C, 30, timed_action_flags = IGNORE_SLOWDOWNS) && C.canBeHandcuffed()) if(iscyborg(user)) apply_cuffs(C, user, TRUE) else diff --git a/code/game/objects/items/maintenance_loot.dm b/code/game/objects/items/maintenance_loot.dm new file mode 100644 index 00000000000..5666f1422be --- /dev/null +++ b/code/game/objects/items/maintenance_loot.dm @@ -0,0 +1,41 @@ +//The items defined in this file are intended be scarce maintenance loot items some of these items are used as a non-renewable resource in crafting or ghetto chem. +//Exercise good judgement and don't add these to a lathe willy nilly. + +//Saw-tier bulky & blunt weapon. A decent bone breaker. Source of lead reagent. +//Add lead material to this once implemented. +/obj/item/lead_pipe + name = "lead pipe" + icon = 'icons/obj/maintenance_loot.dmi' + icon_state = "lead_pipe" + inhand_icon_state = "lead_pipe" + lefthand_file = 'icons/mob/inhands/weapons/melee_lefthand.dmi' + righthand_file = 'icons/mob/inhands/weapons/melee_righthand.dmi' + //wow, lore + desc = "A hefty lead pipe.\nLead in an uncommon sight in this sector after being phased out due to employee health concerns. \ + \nThose of a more cynical disposition assume that the NT lead ban is a scheme to prevent divertion to Syndicate ammunition factories." + force = 15 + throwforce = 12 + throw_range = 4 + w_class = WEIGHT_CLASS_BULKY + wound_bonus = 20 + grind_results = list(/datum/reagent/lead = 20) + +//A good battery early in the shift. Source of lead & sulphuric acid reagents. +//Add lead material to this once implemented. +/obj/item/stock_parts/cell/lead + name = "lead-acid battery" + desc = "A type of primitive battery. It is quite large feels unexpectedly heavy." + icon = 'icons/obj/maintenance_loot.dmi' + icon_state = "lead_battery" + throwforce = 10 + maxcharge = 20000 //decent max charge + chargerate = 1400 //charging is about 30% less efficient compared lithium batteries. + rating = 2 //Kind of a mid-tier battery + w_class = WEIGHT_CLASS_NORMAL + grind_results = list(/datum/reagent/lead = 15, /datum/reagent/toxin/acid = 15, /datum/reagent/water = 20) + +//starts partially discharged +/obj/item/stock_parts/cell/lead/Initialize() + AddElement(/datum/element/update_icon_blocker) + . = ..() + charge = rand(0.2,0.8) * maxcharge diff --git a/code/modules/actionspeed/modifiers/drugs.dm b/code/modules/actionspeed/modifiers/drugs.dm new file mode 100644 index 00000000000..8309f7fb30f --- /dev/null +++ b/code/modules/actionspeed/modifiers/drugs.dm @@ -0,0 +1,3 @@ +/datum/actionspeed_modifier/kronkaine + multiplicative_slowdown = -0.5 + id = ACTIONSPEED_ID_STIMULANTS diff --git a/code/modules/antagonists/cult/ritual.dm b/code/modules/antagonists/cult/ritual.dm index 5696440b8f3..f1fa3553bc6 100644 --- a/code/modules/antagonists/cult/ritual.dm +++ b/code/modules/antagonists/cult/ritual.dm @@ -131,7 +131,7 @@ This file contains the cult dagger and rune list code var/scribe_mod = initial(rune_to_scribe.scribe_delay) if(istype(get_turf(user), /turf/open/floor/engine/cult) && !(ispath(rune_to_scribe, /obj/effect/rune/narsie))) scribe_mod *= 0.5 - if(!do_after(user, scribe_mod, target = get_turf(user))) + if(!do_after(user, scribe_mod, target = get_turf(user), timed_action_flags = IGNORE_SLOWDOWNS)) for(var/V in shields) var/obj/structure/emergency_shield/cult/narsie/S = V if(S && !QDELETED(S)) diff --git a/code/modules/cargo/bounties/reagent.dm b/code/modules/cargo/bounties/reagent.dm index 7d03a8aabe6..1d3b02262a0 100644 --- a/code/modules/cargo/bounties/reagent.dm +++ b/code/modules/cargo/bounties/reagent.dm @@ -126,7 +126,7 @@ /datum/reagent/medicine/ephedrine,\ /datum/reagent/medicine/diphenhydramine,\ /datum/reagent/drug/space_drugs,\ - /datum/reagent/drug/crank,\ + /datum/reagent/drug/blastoff,\ /datum/reagent/gunpowder,\ /datum/reagent/napalm,\ /datum/reagent/firefighting_foam,\ @@ -223,7 +223,6 @@ /datum/reagent/medicine/c2/hercuri,\ /datum/reagent/medicine/c2/probital,\ /datum/reagent/drug/methamphetamine,\ - /datum/reagent/drug/crank,\ /datum/reagent/nitrous_oxide,\ /datum/reagent/barbers_aid,\ /datum/reagent/pax,\ diff --git a/code/modules/hydroponics/grown/cannabis.dm b/code/modules/hydroponics/grown/cannabis.dm index bab62cdc69a..025b1a6621b 100644 --- a/code/modules/hydroponics/grown/cannabis.dm +++ b/code/modules/hydroponics/grown/cannabis.dm @@ -72,7 +72,6 @@ /datum/reagent/medicine/atropine = 0.15, /datum/reagent/drug/methamphetamine = 0.15, /datum/reagent/drug/bath_salts = 0.15, - /datum/reagent/drug/crank = 0.15, /datum/reagent/drug/krokodil = 0.15, /datum/reagent/toxin/lipolicide = 0.15, /datum/reagent/drug/nicotine = 0.1) diff --git a/code/modules/hydroponics/grown/kronkus.dm b/code/modules/hydroponics/grown/kronkus.dm new file mode 100644 index 00000000000..b1e7ee39f3c --- /dev/null +++ b/code/modules/hydroponics/grown/kronkus.dm @@ -0,0 +1,25 @@ +/obj/item/seeds/kronkus + name = "pack of kronkus seeds" + desc = "A pack of highly illegal kronkus seeds.\nPossession of these seeds carries the death penalty in 7 sectors." + icon_state = "seed-kronkus" + species = "kronkus" + plantname = "Kronkus Vine" + product = /obj/item/food/grown/kronkus + //shitty stats, because botany is easy + lifespan = 60 + endurance = 10 + maturation = 8 + production = 4 + yield = 3 + growthstages = 3 + growing_icon = 'icons/obj/hydroponics/growing.dmi' + reagents_add = list(/datum/reagent/consumable/nutriment = 0.05) + +/obj/item/food/grown/kronkus + seed = /obj/item/seeds/kronkus + name = "kronkus vine segment" + desc = "A piece of mature kronkus vine. It exudes a sharp and noxious odor." + icon_state = "kronkus" + filling_color = "#37946e" + foodtypes = VEGETABLES | TOXIC + distill_reagent = /datum/reagent/kronkus_extract diff --git a/code/modules/mob/emote.dm b/code/modules/mob/emote.dm index 778487a547e..5062b49ea8b 100644 --- a/code/modules/mob/emote.dm +++ b/code/modules/mob/emote.dm @@ -27,6 +27,7 @@ continue if(P.run_emote(src, param, m_type, intentional)) SEND_SIGNAL(src, COMSIG_MOB_EMOTE, P, act, m_type, message, intentional) + SEND_SIGNAL(src, COMSIG_MOB_EMOTED(P.key)) return TRUE if(intentional && !silenced && !force_silence) to_chat(src, span_notice("Unusable emote '[act]'. Say *help for a list.")) diff --git a/code/modules/mob/living/carbon/human/examine.dm b/code/modules/mob/living/carbon/human/examine.dm index 30edc36c1df..a3e49a694aa 100644 --- a/code/modules/mob/living/carbon/human/examine.dm +++ b/code/modules/mob/living/carbon/human/examine.dm @@ -11,7 +11,7 @@ if(isliving(user)) var/mob/living/L = user - if(HAS_TRAIT(L, TRAIT_PROSOPAGNOSIA)) + if(HAS_TRAIT(L, TRAIT_PROSOPAGNOSIA) || HAS_TRAIT(L, TRAIT_INVISIBLE_MAN)) obscure_name = TRUE //SKYRAT EDIT CHANGE BEGIN - CUSTOMIZATION diff --git a/code/modules/mob/living/carbon/human/human_helpers.dm b/code/modules/mob/living/carbon/human/human_helpers.dm index 374f4538679..0a9347ab3b1 100644 --- a/code/modules/mob/living/carbon/human/human_helpers.dm +++ b/code/modules/mob/living/carbon/human/human_helpers.dm @@ -52,7 +52,7 @@ if( head && (head.flags_inv&HIDEFACE) ) return if_no_face //Likewise for hats var/obj/item/bodypart/O = get_bodypart(BODY_ZONE_HEAD) - if( !O || (HAS_TRAIT(src, TRAIT_DISFIGURED)) || (O.brutestate+O.burnstate)>2 || cloneloss>50 || !real_name ) //disfigured. use id-name if possible + if( !O || (HAS_TRAIT(src, TRAIT_DISFIGURED)) || (O.brutestate+O.burnstate)>2 || cloneloss>50 || !real_name || HAS_TRAIT(src, TRAIT_INVISIBLE_MAN)) //disfigured. use id-name if possible return if_no_face return real_name diff --git a/code/modules/mob/living/carbon/human/human_update_icons.dm b/code/modules/mob/living/carbon/human/human_update_icons.dm index 0ffe2935c67..e86978381c5 100644 --- a/code/modules/mob/living/carbon/human/human_update_icons.dm +++ b/code/modules/mob/living/carbon/human/human_update_icons.dm @@ -642,6 +642,9 @@ generate/load female uniform sprites matching all previously decided variables if(HAS_TRAIT(src, TRAIT_HUSK)) . += "-husk" + if(HAS_TRAIT(src, TRAIT_INVISIBLE_MAN)) + . += "-invisible" + /mob/living/carbon/human/load_limb_from_cache() ..() update_hair() diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm index 69f48f9ec6a..50662cb8342 100644 --- a/code/modules/mob/living/carbon/human/species.dm +++ b/code/modules/mob/living/carbon/human/species.dm @@ -505,7 +505,7 @@ GLOBAL_LIST_EMPTY(roundstart_races) if(!noggin) //Decapitated return - if(HAS_TRAIT(H, TRAIT_HUSK)) + if(HAS_TRAIT(H, TRAIT_HUSK) || HAS_TRAIT(H, TRAIT_INVISIBLE_MAN)) return var/datum/sprite_accessory/S var/list/standing = list() @@ -681,7 +681,8 @@ GLOBAL_LIST_EMPTY(roundstart_races) /* /datum/species/proc/handle_body(mob/living/carbon/human/species_human) species_human.remove_overlay(BODY_LAYER) - + if(HAS_TRAIT(species_human, TRAIT_INVISIBLE_MAN)) + return handle_mutant_bodyparts(species_human) var/list/standing = list() var/obj/item/bodypart/head/noggin = species_human.get_bodypart(BODY_ZONE_HEAD) @@ -826,7 +827,7 @@ GLOBAL_LIST_EMPTY(roundstart_races) source.remove_overlay(BODY_ADJ_LAYER) source.remove_overlay(BODY_FRONT_LAYER) - if(!mutant_bodyparts) + if(!mutant_bodyparts || HAS_TRAIT(source, TRAIT_INVISIBLE_MAN)) return var/obj/item/bodypart/head/noggin = source.get_bodypart(BODY_ZONE_HEAD) diff --git a/code/modules/movespeed/modifiers/status_effects.dm b/code/modules/movespeed/modifiers/status_effects.dm index 506a4672ef1..40339ed26f1 100644 --- a/code/modules/movespeed/modifiers/status_effects.dm +++ b/code/modules/movespeed/modifiers/status_effects.dm @@ -15,3 +15,4 @@ /datum/movespeed_modifier/status_effect/sepia variable = TRUE blacklisted_movetypes = (FLYING|FLOATING) + diff --git a/code/modules/reagents/chemistry/reagents/drug_reagents.dm b/code/modules/reagents/chemistry/reagents/drug_reagents.dm index 361cf8cdce3..df02b951277 100644 --- a/code/modules/reagents/chemistry/reagents/drug_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/drug_reagents.dm @@ -99,36 +99,6 @@ ..() . = TRUE -/datum/reagent/drug/crank - name = "Crank" - description = "Reduces stun times by about 200%. If overdosed it will deal significant Toxin, Brute and Brain damage." - reagent_state = LIQUID - color = "#FA00C8" - overdose_threshold = 20 - ph = 10 - chemical_flags = REAGENT_CAN_BE_SYNTHESIZED - addiction_types = list(/datum/addiction/stimulants = 14) //5.6 per 2 seconds - -/datum/reagent/drug/crank/on_mob_life(mob/living/carbon/M, delta_time, times_fired) - if(DT_PROB(2.5, delta_time)) - var/high_message = pick("You feel jittery.", "You feel like you gotta go fast.", "You feel like you need to step it up.") - to_chat(M, span_notice("[high_message]")) - SEND_SIGNAL(M, COMSIG_ADD_MOOD_EVENT, "tweaking", /datum/mood_event/stimulant_medium, name) - M.AdjustStun(-20 * REM * delta_time) - M.AdjustKnockdown(-20 * REM * delta_time) - M.AdjustUnconscious(-20 * REM * delta_time) - M.AdjustImmobilized(-20 * REM * delta_time) - M.AdjustParalyzed(-20 * REM * delta_time) - ..() - . = TRUE - -/datum/reagent/drug/crank/overdose_process(mob/living/M, delta_time, times_fired) - M.adjustOrganLoss(ORGAN_SLOT_BRAIN, 2 * REM * delta_time) - M.adjustToxLoss(2 * REM * delta_time, 0) - M.adjustBruteLoss(2 * REM * delta_time, FALSE, FALSE, BODYPART_ORGANIC) - ..() - . = TRUE - /datum/reagent/drug/krokodil name = "Krokodil" description = "Cools and calms you down. If overdosed it will deal significant Brain and Toxin damage." @@ -464,3 +434,337 @@ M.adjustToxLoss(5 * REM * delta_time) M.adjustOrganLoss(ORGAN_SLOT_LIVER, 3 * REM * delta_time) + +/datum/reagent/drug/mushroomhallucinogen + name = "Mushroom Hallucinogen" + description = "A strong hallucinogenic drug derived from certain species of mushroom." + color = "#E700E7" // rgb: 231, 0, 231 + metabolization_rate = 0.2 * REAGENTS_METABOLISM + taste_description = "mushroom" + ph = 11 + chemical_flags = REAGENT_CAN_BE_SYNTHESIZED + addiction_types = list(/datum/addiction/hallucinogens = 12) + +/datum/reagent/drug/mushroomhallucinogen/on_mob_life(mob/living/carbon/psychonaut, delta_time, times_fired) + if(!psychonaut.slurring) + psychonaut.slurring = 1 * REM * delta_time + SEND_SIGNAL(psychonaut, COMSIG_ADD_MOOD_EVENT, "tripping", /datum/mood_event/high, name) + switch(current_cycle) + if(1 to 5) + if(DT_PROB(5, delta_time)) + psychonaut.emote(pick("twitch","giggle")) + if(5 to 10) + psychonaut.Jitter(10 * REM * delta_time) + if(DT_PROB(10, delta_time)) + psychonaut.emote(pick("twitch","giggle")) + if (10 to INFINITY) + psychonaut.Jitter(20 * REM * delta_time) + if(DT_PROB(16, delta_time)) + psychonaut.emote(pick("twitch","giggle")) + ..() + +/datum/reagent/drug/mushroomhallucinogen/on_mob_metabolize(mob/living/psychonaut) + . = ..() + + if(!psychonaut.hud_used) + return + + var/atom/movable/plane_master_controller/game_plane_master_controller = psychonaut.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + + var/list/col_filter_identity = list(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.000,0,0,0) + var/list/col_filter_green = list(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.333,0,0,0) + var/list/col_filter_blue = list(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.666,0,0,0) + var/list/col_filter_red = list(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 1.000,0,0,0) //visually this is identical to the identity + + game_plane_master_controller.add_filter("rainbow", 10, color_matrix_filter(col_filter_red, FILTER_COLOR_HSL)) + + for(var/filter in game_plane_master_controller.get_filters("rainbow")) + animate(filter, color = col_filter_identity, time = 0 SECONDS, loop = -1, flags = ANIMATION_PARALLEL) + animate(color = col_filter_green, time = 4 SECONDS) + animate(color = col_filter_blue, time = 4 SECONDS) + animate(color = col_filter_red, time = 4 SECONDS) + + game_plane_master_controller.add_filter("psilocybin_wave", 1, list("type" = "wave", "size" = 2, "x" = 32, "y" = 32)) + + for(var/filter in game_plane_master_controller.get_filters("psilocybin_wave")) + animate(filter, time = 64 SECONDS, loop = -1, easing = LINEAR_EASING, offset = 32, flags = ANIMATION_PARALLEL) + +/datum/reagent/drug/mushroomhallucinogen/on_mob_end_metabolize(mob/living/psychonaut) + . = ..() + if(!psychonaut.hud_used) + return + var/atom/movable/plane_master_controller/game_plane_master_controller = psychonaut.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + game_plane_master_controller.remove_filter("rainbow") + game_plane_master_controller.remove_filter("psilocybin_wave") + +/datum/reagent/drug/blastoff + name = "bLaSToFF" + description = "A drug for the hardcore party crowd said to enhance ones abilities on the dance floor.\nMost old heads refuse to touch this stuff, perhaps because memories of the luna discoteque incident are seared into their brains." + reagent_state = LIQUID + color = "#9015a9" + taste_description = "holodisk cleaner" + ph = 5 + overdose_threshold = 30 + chemical_flags = REAGENT_CAN_BE_SYNTHESIZED + addiction_types = list(/datum/addiction/hallucinogens = 15) + ///How many flips have we done so far? + var/flip_count = 0 + ///How many spin have we done so far? + var/spin_count = 0 + ///How many flips for a super flip? + var/super_flip_requirement = 3 + +/datum/reagent/drug/blastoff/on_mob_metabolize(mob/living/dancer) + . = ..() + + RegisterSignal(dancer, COMSIG_MOB_EMOTED("flip"), .proc/on_flip) + RegisterSignal(dancer, COMSIG_MOB_EMOTED("spin"), .proc/on_spin) + + if(!dancer.hud_used) + return + + var/atom/movable/plane_master_controller/game_plane_master_controller = dancer.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + + var/list/col_filter_blue = list(0,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.764,0,0,0) //most blue color + var/list/col_filter_mid = list(0,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.832,0,0,0) //red/blue mix midpoint + var/list/col_filter_red = list(0,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1, 0.900,0,0,0) //most red color + + game_plane_master_controller.add_filter("blastoff_filter", 10, color_matrix_filter(col_filter_mid, FILTER_COLOR_HCY)) + game_plane_master_controller.add_filter("blastoff_wave", 1, list("type" = "wave", "x" = 32, "y" = 32)) + + + for(var/filter in game_plane_master_controller.get_filters("blastoff_filter")) + animate(filter, color = col_filter_blue, time = 3 SECONDS, loop = -1, flags = ANIMATION_PARALLEL) + animate(color = col_filter_mid, time = 3 SECONDS) + animate(color = col_filter_red, time = 3 SECONDS) + animate(color = col_filter_mid, time = 3 SECONDS) + + for(var/filter in game_plane_master_controller.get_filters("blastoff_wave")) + animate(filter, time = 32 SECONDS, loop = -1, easing = LINEAR_EASING, offset = 32, flags = ANIMATION_PARALLEL) + + dancer.sound_environment_override = SOUND_ENVIRONMENT_PSYCHOTIC + +/datum/reagent/drug/blastoff/on_mob_end_metabolize(mob/living/dancer) + . = ..() + + UnregisterSignal(dancer, COMSIG_MOB_EMOTED("flip")) + UnregisterSignal(dancer, COMSIG_MOB_EMOTED("spin")) + + if(!dancer.hud_used) + return + + var/atom/movable/plane_master_controller/game_plane_master_controller = dancer.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + + game_plane_master_controller.remove_filter("blastoff_filter") + game_plane_master_controller.remove_filter("blastoff_wave") + dancer.sound_environment_override = NONE + +/datum/reagent/drug/blastoff/on_mob_life(mob/living/carbon/dancer, delta_time, times_fired) + . = ..() + + dancer.adjustOrganLoss(ORGAN_SLOT_LUNGS, 0.3 * REM * delta_time) + dancer.AdjustKnockdown(-20) + SEND_SIGNAL(dancer, COMSIG_ADD_MOOD_EVENT, "vibing", /datum/mood_event/high, name) + + if(DT_PROB(BLASTOFF_DANCE_MOVE_CHANCE_PER_UNIT * volume, delta_time)) + dancer.emote("flip") + +/datum/reagent/drug/blastoff/overdose_process(mob/living/dancer, delta_time, times_fired) + . = ..() + dancer.adjustOrganLoss(ORGAN_SLOT_LUNGS, 0.3 * REM * delta_time) + + if(DT_PROB(BLASTOFF_DANCE_MOVE_CHANCE_PER_UNIT * volume, delta_time)) + dancer.emote("spin") + +///This proc listens to the flip signal and throws the mob every third flip +/datum/reagent/drug/blastoff/proc/on_flip() + SIGNAL_HANDLER + + if(!iscarbon(holder.my_atom)) + return + var/mob/living/carbon/dancer = holder.my_atom + + flip_count++ + if(flip_count < BLASTOFF_DANCE_MOVES_PER_SUPER_MOVE) + return + flip_count = 0 + var/atom/throw_target = get_edge_target_turf(dancer, dancer.dir) //Do a super flip + dancer.SpinAnimation(speed = 3, loops = 3) + dancer.visible_message(span_notice("[dancer] does an extravagant flip!"), span_nicegreen("You do an extravagant flip!")) + dancer.throw_at(throw_target, range = 6, speed = overdosed ? 4 : 1) + +///This proc listens to the spin signal and throws the mob every third spin +/datum/reagent/drug/blastoff/proc/on_spin() + SIGNAL_HANDLER + + if(!iscarbon(holder.my_atom)) + return + var/mob/living/carbon/dancer = holder.my_atom + + spin_count++ + if(spin_count < BLASTOFF_DANCE_MOVES_PER_SUPER_MOVE) + return + spin_count = 0 //Do a super spin. + dancer.visible_message(span_danger("[dancer] spins around violently!"), span_danger("You spin around violently!")) + dancer.spin(30, 2) + if(dancer.disgust < 40) + dancer.adjust_disgust(10) + if(!dancer.pulledby) + return + var/dancer_turf = get_turf(dancer) + var/atom/movable/dance_partner = dancer.pulledby + dance_partner.visible_message(span_danger("[dance_partner] tries to hold onto [dancer], but is thrown back!"), span_danger("You try to hold onto [dancer], but you are thrown back!"), null, COMBAT_MESSAGE_RANGE) + var/throwtarget = get_edge_target_turf(dancer_turf, get_dir(dancer_turf, get_step_away(dance_partner, dancer_turf))) + if(overdosed) + dance_partner.throw_at(target = throwtarget, range = 7, speed = 4) + else + dance_partner.throw_at(target = throwtarget, range = 4, speed = 1) //superspeed + +/datum/reagent/drug/saturnx + name = "SaturnX" + description = "This compound was first discovered during the infancy of cloaking technology and at the time thought to be a promising candidate agent. It was withdrawn for consideration after the researchers discovered a slew of associated safety issues including thought disorders and hepatoxicity." + reagent_state = SOLID + taste_description = "metallic bitterness" + color = "#638b9b" + overdose_threshold = 25 + metabolization_rate = 0.5 * REAGENTS_METABOLISM + ph = 10 + chemical_flags = REAGENT_CAN_BE_SYNTHESIZED + addiction_types = list(/datum/addiction/maintenance_drugs = 20) + +/datum/reagent/drug/saturnx/on_mob_life(mob/living/carbon/invisible_man, delta_time, times_fired) + . = ..() + invisible_man.adjustOrganLoss(ORGAN_SLOT_LIVER, 0.3 * REM * delta_time) + +/datum/reagent/drug/saturnx/on_mob_metabolize(mob/living/invisible_man) + . = ..() + playsound(invisible_man, 'sound/chemistry/saturnx_fade.ogg', 40) + to_chat(invisible_man, span_nicegreen("You feel pins and needles all over your skin as your body suddenly becomes transparent!")) + addtimer(CALLBACK(src, .proc/turn_man_invisible, invisible_man), 10) //just a quick delay to synch up the sound. + if(!invisible_man.hud_used) + return + + var/atom/movable/plane_master_controller/game_plane_master_controller = invisible_man.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + + var/list/col_filter_full = list(1,0,0,0, 0,1.00,0,0, 0,0,1,0, 0,0,0,1, 0,0,0,0) + var/list/col_filter_twothird = list(1,0,0,0, 0,0.68,0,0, 0,0,1,0, 0,0,0,1, 0,0,0,0) + var/list/col_filter_half = list(1,0,0,0, 0,0.42,0,0, 0,0,1,0, 0,0,0,1, 0,0,0,0) + var/list/col_filter_empty = list(1,0,0,0, 0,0,0,0, 0,0,1,0, 0,0,0,1, 0,0,0,0) + + game_plane_master_controller.add_filter("saturnx_filter", 10, color_matrix_filter(col_filter_twothird, FILTER_COLOR_HCY)) + + for(var/filter in game_plane_master_controller.get_filters("saturnx_filter")) + animate(filter, loop = -1, color = col_filter_full, time = 4 SECONDS, easing = CIRCULAR_EASING|EASE_IN, flags = ANIMATION_PARALLEL) + //uneven so we spend slightly less time with bright colors + animate(color = col_filter_twothird, time = 6 SECONDS, easing = LINEAR_EASING) + animate(color = col_filter_half, time = 3 SECONDS, easing = LINEAR_EASING) + animate(color = col_filter_empty, time = 2 SECONDS, easing = CIRCULAR_EASING|EASE_OUT) + animate(color = col_filter_half, time = 24 SECONDS, easing = CIRCULAR_EASING|EASE_IN) + animate(color = col_filter_twothird, time = 12 SECONDS, easing = LINEAR_EASING) + + game_plane_master_controller.add_filter("saturnx_blur", 1, list("type" = "radial_blur", "size" = 0)) + + for(var/filter in game_plane_master_controller.get_filters("saturnx_blur")) + animate(filter, loop = -1, size = 0.04, time = 2 SECONDS, easing = ELASTIC_EASING|EASE_OUT, flags = ANIMATION_PARALLEL) + animate(size = 0, time = 6 SECONDS, easing = CIRCULAR_EASING|EASE_IN) + +///This proc turns the living mob passed as the arg "invisible_man"s invisible by giving him the invisible man trait and updating his body, this changes the sprite of all his organic limbs to a 1 alpha version. +/datum/reagent/drug/saturnx/proc/turn_man_invisible(mob/living/carbon/invisible_man) + if(!invisible_man.getorganslot(ORGAN_SLOT_LIVER)) + return + if(invisible_man.undergoing_liver_failure()) + return + if(HAS_TRAIT(invisible_man, TRAIT_NOMETABOLISM)) + return + + ADD_TRAIT(invisible_man, TRAIT_INVISIBLE_MAN, name) + + var/datum/dna/druggy_dna = invisible_man.has_dna() + if(druggy_dna?.species) + druggy_dna.species.species_traits += NOBLOODOVERLAY + + invisible_man.update_body() + invisible_man.update_hair() + invisible_man.remove_from_all_data_huds() + invisible_man.sound_environment_override = SOUND_ENVIROMENT_PHASED + +/datum/reagent/drug/saturnx/on_mob_end_metabolize(mob/living/invisible_man) + . = ..() + if(HAS_TRAIT(invisible_man, TRAIT_INVISIBLE_MAN)) + invisible_man.add_to_all_human_data_huds() //Is this safe, what do you think, Floyd? + REMOVE_TRAIT(invisible_man, TRAIT_INVISIBLE_MAN, name) + to_chat(invisible_man, span_notice("As you sober up, opacity once again returns to your body meats.")) + + var/datum/dna/druggy_dna = invisible_man.has_dna() + if(druggy_dna?.species) + druggy_dna.species.species_traits -= NOBLOODOVERLAY + + invisible_man.update_body() + invisible_man.update_hair() + invisible_man.sound_environment_override = NONE + + if(!invisible_man.hud_used) + return + + var/atom/movable/plane_master_controller/game_plane_master_controller = invisible_man.hud_used.plane_master_controllers[PLANE_MASTERS_GAME] + game_plane_master_controller.remove_filter("saturnx_filter") + game_plane_master_controller.remove_filter("saturnx_blur") + +/datum/reagent/drug/saturnx/overdose_process(mob/living/invisible_man, delta_time, times_fired) + . = ..() + if(DT_PROB(7.5, delta_time)) + invisible_man.emote("giggle") + if(DT_PROB(5, delta_time)) + invisible_man.emote("laugh") + invisible_man.adjustOrganLoss(ORGAN_SLOT_LIVER, 0.4 * REM * delta_time) + +/datum/reagent/drug/kronkaine + name = "kronkaine" + description = "A highly illegal stimulant from the edge of the galaxy.\nIt is said the average kronkaine addict causes as much criminal damage as five stick up men, two rascals and one proferssional cambringo hustler combined." + reagent_state = SOLID + color = "#FAFAFA" + taste_description = "numbing bitterness" + ph = 8 + overdose_threshold = 20 + metabolization_rate = 0.75 * REAGENTS_METABOLISM + chemical_flags = REAGENT_CAN_BE_SYNTHESIZED + addiction_types = list(/datum/addiction/stimulants = 20) + +/datum/reagent/drug/kronkaine/on_mob_metabolize(mob/living/kronkaine_fiend) + ..() + kronkaine_fiend.add_actionspeed_modifier(/datum/actionspeed_modifier/kronkaine) + kronkaine_fiend.sound_environment_override = SOUND_ENVIRONMENT_HANGAR + +/datum/reagent/drug/kronkaine/on_mob_end_metabolize(mob/living/kronkaine_fiend) + kronkaine_fiend.remove_actionspeed_modifier(/datum/actionspeed_modifier/kronkaine) + kronkaine_fiend.sound_environment_override = NONE + . = ..() + +/datum/reagent/drug/kronkaine/on_transfer(atom/kronkaine_receptacle, methods, trans_volume) + . = ..() + if(!iscarbon(kronkaine_receptacle)) + return + var/mob/living/carbon/druggo = kronkaine_receptacle + druggo.adjustStaminaLoss(-4 * trans_volume, 0) + //I wish i could give it some kind of bonus when smoked, but we don't have an INHALE method. + +/datum/reagent/drug/kronkaine/on_mob_life(mob/living/carbon/kronkaine_fiend, delta_time, times_fired) + . = ..() + SEND_SIGNAL(kronkaine_fiend, COMSIG_ADD_MOOD_EVENT, "tweaking", /datum/mood_event/stimulant_medium, name) + kronkaine_fiend.adjustOrganLoss(ORGAN_SLOT_HEART, 0.4 * REM * delta_time) + kronkaine_fiend.Jitter(10 * REM * delta_time) + kronkaine_fiend.AdjustSleeping(-20 * REM * delta_time) + kronkaine_fiend.drowsyness = max(kronkaine_fiend.drowsyness - (5 * REM * delta_time), 0) + if(volume < 10) + return + for(var/possible_purger in kronkaine_fiend.reagents.reagent_list) + if(istype(possible_purger, /datum/reagent/medicine/c2/multiver) || istype(possible_purger, /datum/reagent/medicine/haloperidol)) + kronkaine_fiend.ForceContractDisease(new /datum/disease/adrenal_crisis(), FALSE, TRUE) //We punish players for purging, since unchecked purging would allow players to reap the stamina healing benefits without any drawbacks. This also has the benefit of making haloperidol a counter, like it is supposed to be. + break + +/datum/reagent/drug/kronkaine/overdose_process(mob/living/kronkaine_fiend, delta_time, times_fired) + . = ..() + kronkaine_fiend.adjustOrganLoss(ORGAN_SLOT_HEART, 1 * REM * delta_time) + kronkaine_fiend.Jitter(10 * REM * delta_time) + if(DT_PROB(10, delta_time)) + to_chat(kronkaine_fiend, span_danger(pick("You feel like your heart is going to explode!", "Your ears are ringing!", "You sweat like a pig!", "You clench your jaw and grind your teeth.", "You feel prickles of pain in your chest."))) diff --git a/code/modules/reagents/chemistry/reagents/food_reagents.dm b/code/modules/reagents/chemistry/reagents/food_reagents.dm index 441a1f629c9..103daeb114d 100644 --- a/code/modules/reagents/chemistry/reagents/food_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/food_reagents.dm @@ -412,39 +412,6 @@ taste_description = "bitterness" chemical_flags = REAGENT_CAN_BE_SYNTHESIZED -/datum/reagent/drug/mushroomhallucinogen - name = "Mushroom Hallucinogen" - description = "A strong hallucinogenic drug derived from certain species of mushroom." - color = "#E700E7" // rgb: 231, 0, 231 - metabolization_rate = 0.2 * REAGENTS_METABOLISM - taste_description = "mushroom" - ph = 11 - chemical_flags = REAGENT_CAN_BE_SYNTHESIZED - addiction_types = list(/datum/addiction/hallucinogens = 12) - -/datum/reagent/drug/mushroomhallucinogen/on_mob_life(mob/living/carbon/M, delta_time, times_fired) - if(!M.slurring) - M.slurring = 1 * REM * delta_time - switch(current_cycle) - if(1 to 5) - M.Dizzy(5 * REM * delta_time) - M.set_drugginess(30 * REM * delta_time) - if(DT_PROB(5, delta_time)) - M.emote(pick("twitch","giggle")) - if(5 to 10) - M.Jitter(10 * REM * delta_time) - M.Dizzy(10 * REM * delta_time) - M.set_drugginess(35 * REM * delta_time) - if(DT_PROB(10, delta_time)) - M.emote(pick("twitch","giggle")) - if (10 to INFINITY) - M.Jitter(20 * REM * delta_time) - M.Dizzy(20 * REM * delta_time) - M.set_drugginess(40 * REM * delta_time) - if(DT_PROB(16, delta_time)) - M.emote(pick("twitch","giggle")) - ..() - /datum/reagent/consumable/garlic //NOTE: having garlic in your blood stops vampires from biting you. name = "Garlic Juice" description = "Crushed garlic. Chefs love it, but it can make you smell bad." diff --git a/code/modules/reagents/chemistry/reagents/other_reagents.dm b/code/modules/reagents/chemistry/reagents/other_reagents.dm index 7228222deeb..6cd5e61120c 100644 --- a/code/modules/reagents/chemistry/reagents/other_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/other_reagents.dm @@ -2767,3 +2767,31 @@ if(methods & (PATCH|TOUCH|VAPOR)) amount_left = round(reac_volume,0.1) exposed_mob.apply_status_effect(STATUS_EFFECT_ANTS, amount_left) + +//This is intended to a be a scarce reagent to gate certain drugs and toxins with. Do not put in a synthesizer. Renewable sources of this reagent should be inefficient. +/datum/reagent/lead + name = "lead" + description = "A dull metalltic element with a low melting point." + taste_description = "metal" + reagent_state = SOLID + color = "#80919d" + metabolization_rate = 0.4 * REAGENTS_METABOLISM + +/datum/reagent/lead/on_mob_life(mob/living/carbon/victim) + . = ..() + victim.adjustOrganLoss(ORGAN_SLOT_BRAIN, 0.5) + +//The main feedstock for kronkaine production, also a shitty stamina healer. +/datum/reagent/kronkus_extract + name = "kronkus extract" + description = "A frothy extract made from fermented kronkus vine pulp.\nHighly bitter due to the presence of a variety of kronkamines." + taste_description = "bitterness" + color = "#228f63" + chemical_flags = REAGENT_CAN_BE_SYNTHESIZED + addiction_types = list(/datum/addiction/stimulants = 5) + +/datum/reagent/kronkus_extract/on_mob_life(mob/living/carbon/kronkus_enjoyer) + . = ..() + kronkus_enjoyer.adjustOrganLoss(ORGAN_SLOT_HEART, 0.1) + kronkus_enjoyer.adjustStaminaLoss(-2, FALSE) + diff --git a/code/modules/reagents/chemistry/recipes/drugs.dm b/code/modules/reagents/chemistry/recipes/drugs.dm index 212209c282d..d973f853424 100644 --- a/code/modules/reagents/chemistry/recipes/drugs.dm +++ b/code/modules/reagents/chemistry/recipes/drugs.dm @@ -3,13 +3,6 @@ required_reagents = list(/datum/reagent/mercury = 1, /datum/reagent/consumable/sugar = 1, /datum/reagent/lithium = 1) reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG -/datum/chemical_reaction/crank - results = list(/datum/reagent/drug/crank = 5) - required_reagents = list(/datum/reagent/medicine/diphenhydramine = 1, /datum/reagent/ammonia = 1, /datum/reagent/lithium = 1, /datum/reagent/toxin/acid = 1, /datum/reagent/fuel = 1) - mix_message = "The mixture violently reacts, leaving behind a few crystalline shards." - required_temp = 390 - reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG - /datum/chemical_reaction/krokodil results = list(/datum/reagent/drug/krokodil = 6) required_reagents = list(/datum/reagent/medicine/diphenhydramine = 1, /datum/reagent/medicine/morphine = 1, /datum/reagent/space_cleaner = 1, /datum/reagent/potassium = 1, /datum/reagent/phosphorus = 1, /datum/reagent/fuel = 1) @@ -126,3 +119,40 @@ required_reagents = list(/datum/reagent/drug/maint/sludge = 6 , /datum/reagent/toxin/acid/nitracid = 1 , /datum/reagent/consumable/enzyme = 1) required_catalysts = list(/datum/reagent/acetone_oxide = 5) reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG | REACTION_TAG_ORGAN | REACTION_TAG_DAMAGING + +//These drug item reactions should probably be converted to fermichem in the future. +/datum/chemical_reaction/moon_rock //botany is real easy so it requires a lot of kronkus_extract, make it cheaper if it doesnt get amde. + required_reagents = list(/datum/reagent/kronkus_extract = 15, /datum/reagent/fuel = 10, /datum/reagent/ammonia = 5) + mob_react = FALSE + reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG | REACTION_TAG_ORGAN | REACTION_TAG_DAMAGING + +/datum/chemical_reaction/moon_rock/on_reaction(datum/reagents/holder, datum/equilibrium/reaction, created_volume) + var/location = get_turf(holder.my_atom) + for(var/i = 1, i <= created_volume, i++) + var/obj/item/food/drug/moon_rock/new_rock = new(location) + new_rock.pixel_x = rand(-6, 6) + new_rock.pixel_y = rand(-6, 6) + +/datum/chemical_reaction/blastoff_ampoule + required_reagents = list(/datum/reagent/silver = 10, /datum/reagent/toxin/cyanide = 10, /datum/reagent/lye = 5) + mob_react = FALSE + reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG | REACTION_TAG_ORGAN | REACTION_TAG_DAMAGING + +/datum/chemical_reaction/blastoff_ampoule/on_reaction(datum/reagents/holder, datum/equilibrium/reaction, created_volume) + var/location = get_turf(holder.my_atom) + for(var/iteration = 1, iteration <= created_volume, iteration++) + var/obj/item/reagent_containers/glass/blastoff_ampoule/new_ampoule = new(location) + new_ampoule.pixel_x = rand(-6, 6) + new_ampoule.pixel_y = rand(-6, 6) + +/datum/chemical_reaction/saturnx_glob + required_reagents = list(/datum/reagent/lead = 5, /datum/reagent/consumable/nothing = 5, /datum/reagent/drug/maint/tar = 10) + mob_react = FALSE + reaction_tags = REACTION_TAG_EASY | REACTION_TAG_DRUG | REACTION_TAG_ORGAN | REACTION_TAG_DAMAGING + +/datum/chemical_reaction/saturnx_glob/on_reaction(datum/reagents/holder, datum/equilibrium/reaction, created_volume) + var/location = get_turf(holder.my_atom) + for(var/iteration = 1, iteration <= created_volume, iteration++) + var/obj/item/food/drug/saturnx/new_glob = new(location) + new_glob.pixel_x = rand(-6, 6) + new_glob.pixel_y = rand(-6, 6) diff --git a/code/modules/reagents/reagent_containers/syringes.dm b/code/modules/reagents/reagent_containers/syringes.dm index 40660ed8074..f754541433b 100644 --- a/code/modules/reagents/reagent_containers/syringes.dm +++ b/code/modules/reagents/reagent_containers/syringes.dm @@ -271,9 +271,9 @@ /obj/item/reagent_containers/syringe/contraband/krokodil list_reagents = list(/datum/reagent/drug/krokodil = 15) -/obj/item/reagent_containers/syringe/contraband/crank - list_reagents = list(/datum/reagent/drug/crank = 15) - +/obj/item/reagent_containers/syringe/contraband/saturnx + list_reagents = list(/datum/reagent/drug/saturnx = 15) + /obj/item/reagent_containers/syringe/contraband/methamphetamine list_reagents = list(/datum/reagent/drug/methamphetamine = 15) diff --git a/code/modules/surgery/bodyparts/_bodyparts.dm b/code/modules/surgery/bodyparts/_bodyparts.dm index 411758be8e6..4d8b4645c96 100644 --- a/code/modules/surgery/bodyparts/_bodyparts.dm +++ b/code/modules/surgery/bodyparts/_bodyparts.dm @@ -803,6 +803,13 @@ should_draw_greyscale = FALSE no_update = TRUE + if(HAS_TRAIT(limb_owner, TRAIT_INVISIBLE_MAN) && is_organic_limb()) + species_id = "invisible" //overrides species_id + dmg_overlay_type = "" //no damage overlay shown when invisible since the wounds themselves are invisible. + should_draw_gender = FALSE + should_draw_greyscale = FALSE + no_update = TRUE + if(no_update) return diff --git a/code/modules/surgery/organs/external/_external_organs.dm b/code/modules/surgery/organs/external/_external_organs.dm new file mode 100644 index 00000000000..2734edb4e4e --- /dev/null +++ b/code/modules/surgery/organs/external/_external_organs.dm @@ -0,0 +1,260 @@ +/** +* System for drawing organs with overlays. These overlays are drawn directly on the bodypart, attached to a person or not +* Works in tandem with the /datum/sprite_accessory datum to generate sprites +* Unlike normal organs, we're actually inside a persons limbs at all times +*/ +/obj/item/organ/external + name = "external organ" + desc = "An external organ that is too external." + + ///Unremovable is until the features are completely finished + organ_flags = ORGAN_UNREMOVABLE | ORGAN_EDIBLE + + ///Sometimes we need multiple layers, for like the back, middle and front of the person + var/layers + ///Convert the bitflag define into the actual layer define + var/static/list/all_layers = list(EXTERNAL_FRONT, EXTERNAL_ADJACENT, EXTERNAL_BEHIND) + + ///Defines what kind of 'organ' we're looking at. Sprites have names like 'm_firemoth_mothwings'. 'mothwings' would then be preference + var/preference = "" + ///Sprite datum we use to draw on the bodypart + var/datum/sprite_accessory/sprite_datum + ///Key of the icon states of all the sprite_datums for easy caching + var/cache_key = "" + + ///With what DNA block do we mutate in mutate_feature() ? For genetics + var/dna_block + + ///Reference to the limb we're inside of + var/obj/item/bodypart/ownerlimb + +/**mob_sprite is optional if you havent set sprite_datums for the object, and is used mostly to generate sprite_datums from a persons DNA +* For _mob_sprite we make a distinction between "Round Snout" and "round". Round Snout is the name of the sprite datum, while "round" would be part of the sprite +* I'm sorry +*/ +/obj/item/organ/external/Initialize(mapload, mob_sprite) + . = ..() + + if(mob_sprite) + set_sprite(mob_sprite) + + cache_key = generate_icon_cache() + +/obj/item/organ/external/Insert(mob/living/carbon/reciever, special, drop_if_replaced) + var/obj/item/bodypart/limb = reciever.get_bodypart(zone) + + if(!limb) + return FALSE + + limb.external_organs.Add(src) + ownerlimb = limb + + . = ..() + + limb.contents.Add(src) + + reciever.update_body_parts() + +/obj/item/organ/external/Remove(mob/living/carbon/organ_owner, special) + . = ..() + + if(ownerlimb) + ownerlimb.external_organs.Remove(src) + ownerlimb.contents.Remove(src) + ownerlimb = null + + organ_owner.update_body_parts() + +/obj/item/organ/external/transfer_to_limb(obj/item/bodypart/bodypart, mob/living/carbon/bodypart_owner) + . = ..() + + bodypart.external_organs.Add(src) + bodypart.contents.Add(src) + +///Add the overlays we need to draw on a person. Called from _bodyparts.dm +/obj/item/organ/external/proc/get_overlays(list/overlay_list, image_dir, image_layer, body_type, image_color) + if(!sprite_datum) + return + if(HAS_TRAIT(owner, TRAIT_INVISIBLE_MAN)) + return + var/gender = (body_type == FEMALE) ? "f" : "m" + var/finished_icon_state = (sprite_datum.gender_specific ? gender : "m") + "_" + preference + "_" + sprite_datum.icon_state + mutant_bodyparts_layertext(image_layer) + var/mutable_appearance/appearance = mutable_appearance(sprite_datum.icon, finished_icon_state, layer = -image_layer) + appearance.dir = image_dir + + if(sprite_datum.color_src) //There are multiple flags, but only one is ever used so meh :/ + appearance.color = image_color + + if(sprite_datum.center) + center_image(appearance, sprite_datum.dimension_x, sprite_datum.dimension_y) + + overlay_list += appearance + +/obj/item/organ/external/proc/set_sprite(sprite_name) + sprite_datum = get_sprite_datum(sprite_name) + cache_key = generate_icon_cache() + +///Generate a unique key based on our sprites. So that if we've aleady drawn these sprites, they can be found in the cache and wont have to be drawn again (blessing and curse) +/obj/item/organ/external/proc/generate_icon_cache() + return "[sprite_datum.icon_state]_[preference]" + +/**This exists so sprite accessories can still be per-layer without having to include that layer's +* number in their sprite name, which causes issues when those numbers change. +*/ +/obj/item/organ/external/proc/mutant_bodyparts_layertext(layer) + switch(layer) + if(BODY_BEHIND_LAYER) + return "_BEHIND" + if(BODY_ADJ_LAYER) + return "_ADJ" + if(BODY_FRONT_LAYER) + return "_FRONT" + +///Converts a bitflag to the right layer. I'd love to make this a static index list, but byond made an attempt on my life when i did +/obj/item/organ/external/proc/bitflag_to_layer(layer) + switch(layer) + if(EXTERNAL_BEHIND) + return BODY_BEHIND_LAYER + if(EXTERNAL_ADJACENT) + return BODY_ADJ_LAYER + if(EXTERNAL_FRONT) + return BODY_FRONT_LAYER + +///Because all the preferences have names like "Beautiful Sharp Snout" we need to get the sprite datum with the actual important info +/obj/item/organ/external/proc/get_sprite_datum(sprite) + var/list/feature_list = get_global_feature_list() + return feature_list[sprite] + +///Return a dumb glob list for this specific feature (called from parse_sprite) +/obj/item/organ/external/proc/get_global_feature_list() + return null + +///Check whether we can draw the overlays. You generally don't want lizard snouts to draw over an EVA suit +/obj/item/organ/external/proc/can_draw_on_bodypart(mob/living/carbon/human/human) + return TRUE + +///Update our features after something changed our appearance +/obj/item/organ/external/proc/mutate_feature(features, mob/living/carbon/human/human) + if(!dna_block || !get_global_feature_list()) + return + + var/list/feature_list = get_global_feature_list() + + set_sprite(feature_list[deconstruct_block(getblock(features, dna_block), feature_list.len)]) + +///The horns of a lizard! +/obj/item/organ/external/horns + zone = BODY_ZONE_HEAD + slot = ORGAN_SLOT_EXTERNAL_HORNS + layers = EXTERNAL_ADJACENT + + preference = "horns" + + dna_block = DNA_HORNS_BLOCK + +/obj/item/organ/external/horns/can_draw_on_bodypart(mob/living/carbon/human/human) + if(!(human.head?.flags_inv & HIDEHAIR) || (human.wear_mask?.flags_inv & HIDEHAIR)) + return TRUE + return FALSE + +/obj/item/organ/external/horns/get_global_feature_list() + return GLOB.horns_list + +///The frills of a lizard (like weird fin ears) +/obj/item/organ/external/frills + zone = BODY_ZONE_HEAD + slot = ORGAN_SLOT_EXTERNAL_FRILLS + layers = EXTERNAL_ADJACENT + + preference = "frills" + + dna_block = DNA_FRILLS_BLOCK + +/obj/item/organ/external/frills/can_draw_on_bodypart(mob/living/carbon/human/human) + if(!(human.head?.flags_inv & HIDEEARS)) + return TRUE + return FALSE + + +/obj/item/organ/external/frills/get_global_feature_list() + return GLOB.frills_list + +///Guess what part of the lizard this is? +/obj/item/organ/external/snout + zone = BODY_ZONE_HEAD + slot = ORGAN_SLOT_EXTERNAL_SNOUT + layers = EXTERNAL_ADJACENT + + preference = "snout" + + dna_block = DNA_SNOUT_BLOCK + +/obj/item/organ/external/snout/can_draw_on_bodypart(mob/living/carbon/human/human) + if(!(human.wear_mask?.flags_inv & HIDESNOUT) && !(human.head?.flags_inv & HIDESNOUT)) + return TRUE + return FALSE + +/obj/item/organ/external/snout/get_global_feature_list() + return GLOB.snouts_list + +///A moth's antennae +/obj/item/organ/external/antennae + zone = BODY_ZONE_HEAD + slot = ORGAN_SLOT_EXTERNAL_ANTENNAE + layers = EXTERNAL_FRONT | EXTERNAL_BEHIND + + preference = "moth_antennae" + + dna_block = DNA_MOTH_ANTENNAE_BLOCK + + ///Are we burned? + var/burnt = FALSE + ///Store our old sprite here for if our antennae wings are healed + var/original_sprite = "" + +/obj/item/organ/external/antennae/Insert(mob/living/carbon/reciever, special, drop_if_replaced) + . = ..() + + RegisterSignal(reciever, COMSIG_HUMAN_BURNING, .proc/try_burn_antennae) + RegisterSignal(reciever, COMSIG_LIVING_POST_FULLY_HEAL, .proc/heal_antennae) + +/obj/item/organ/external/antennae/Remove(mob/living/carbon/organ_owner, special) + . = ..() + + UnregisterSignal(organ_owner, list(COMSIG_HUMAN_BURNING, COMSIG_LIVING_POST_FULLY_HEAL)) + +/obj/item/organ/external/antennae/get_global_feature_list() + return GLOB.moth_antennae_list + +/obj/item/organ/external/antennae/can_draw_on_bodypart(mob/living/carbon/human/human) + return TRUE + +///For moth antennae and wings we make an exception. If their features are burnt, we only update our original sprite +/obj/item/organ/external/antennae/set_sprite(sprite) + if(!burnt) + return ..() //no one listens to the return value, I just need to call the parent proc and end the code + + original_sprite = sprite + +///check if our antennae can burn off ;_; +/obj/item/organ/external/antennae/proc/try_burn_antennae(mob/living/carbon/human/human) + SIGNAL_HANDLER + + if(!burnt && human.bodytemperature >= 800 && human.fire_stacks > 0) //do not go into the extremely hot light. you will not survive + to_chat(human, span_danger("Your precious antennae burn to a crisp!")) + + burn_antennae() + human.update_body_parts() + +/obj/item/organ/external/antennae/proc/burn_antennae() + burnt = TRUE + original_sprite = sprite_datum.name + set_sprite("Burnt Off") + +///heal our antennae back up!! +/obj/item/organ/external/antennae/proc/heal_antennae() + SIGNAL_HANDLER + + if(burnt) + burnt = FALSE + set_sprite(original_sprite) diff --git a/icons/mob/human_parts.dmi b/icons/mob/human_parts.dmi index 8a9c1e204da..c9ec0084b19 100644 Binary files a/icons/mob/human_parts.dmi and b/icons/mob/human_parts.dmi differ diff --git a/icons/mob/inhands/weapons/melee_lefthand.dmi b/icons/mob/inhands/weapons/melee_lefthand.dmi index 8b1a6388e31..36b3abfeddc 100644 Binary files a/icons/mob/inhands/weapons/melee_lefthand.dmi and b/icons/mob/inhands/weapons/melee_lefthand.dmi differ diff --git a/icons/mob/inhands/weapons/melee_righthand.dmi b/icons/mob/inhands/weapons/melee_righthand.dmi index c93352235ba..be564b93f9e 100644 Binary files a/icons/mob/inhands/weapons/melee_righthand.dmi and b/icons/mob/inhands/weapons/melee_righthand.dmi differ diff --git a/icons/obj/drugs.dmi b/icons/obj/drugs.dmi new file mode 100644 index 00000000000..21c52523ed1 Binary files /dev/null and b/icons/obj/drugs.dmi differ diff --git a/icons/obj/hydroponics/growing.dmi b/icons/obj/hydroponics/growing.dmi index 9ef27f934d9..9cf8169eee4 100644 Binary files a/icons/obj/hydroponics/growing.dmi and b/icons/obj/hydroponics/growing.dmi differ diff --git a/icons/obj/hydroponics/harvest.dmi b/icons/obj/hydroponics/harvest.dmi index f72e0387a69..43a03f96068 100644 Binary files a/icons/obj/hydroponics/harvest.dmi and b/icons/obj/hydroponics/harvest.dmi differ diff --git a/icons/obj/hydroponics/seeds.dmi b/icons/obj/hydroponics/seeds.dmi index 69969f576ef..602b10c90fa 100644 Binary files a/icons/obj/hydroponics/seeds.dmi and b/icons/obj/hydroponics/seeds.dmi differ diff --git a/icons/obj/maintenance_loot.dmi b/icons/obj/maintenance_loot.dmi new file mode 100644 index 00000000000..01c7f5682a9 Binary files /dev/null and b/icons/obj/maintenance_loot.dmi differ diff --git a/modular_skyrat/master_files/code/_globalvars/maint_loot_trash.dm b/modular_skyrat/master_files/code/_globalvars/maint_loot_trash.dm index c1b5a3b9437..aae7393e783 100644 --- a/modular_skyrat/master_files/code/_globalvars/maint_loot_trash.dm +++ b/modular_skyrat/master_files/code/_globalvars/maint_loot_trash.dm @@ -164,7 +164,6 @@ GLOBAL_LIST_INIT(trash_loot, list(//junk: useless, very easy to get, or ghetto c /obj/item/reagent_containers/spray/cleaner = 100, /obj/item/reagent_containers/spray/spraytan = 50, /obj/item/reagent_containers/syringe/contraband/bath_salts = 25, - /obj/item/reagent_containers/syringe/contraband/crank = 25, /obj/item/reagent_containers/syringe/contraband/fentanyl = 25, /obj/item/reagent_containers/syringe/contraband/krokodil = 25, /obj/item/reagent_containers/syringe/contraband/methamphetamine = 25, diff --git a/sound/chemistry/saturnx_fade.ogg b/sound/chemistry/saturnx_fade.ogg new file mode 100644 index 00000000000..aada84c4da8 Binary files /dev/null and b/sound/chemistry/saturnx_fade.ogg differ diff --git a/sound/items/ampoule_snap.ogg b/sound/items/ampoule_snap.ogg new file mode 100644 index 00000000000..eece6ff896c Binary files /dev/null and b/sound/items/ampoule_snap.ogg differ diff --git a/tgstation.dme b/tgstation.dme index 74976480e2f..3761577950d 100644 --- a/tgstation.dme +++ b/tgstation.dme @@ -677,6 +677,7 @@ #include "code\datums\components\storage\concrete\wallet.dm" #include "code\datums\diseases\_disease.dm" #include "code\datums\diseases\_MobProcs.dm" +#include "code\datums\diseases\adrenal_crisis.dm" #include "code\datums\diseases\anxiety.dm" #include "code\datums\diseases\beesease.dm" #include "code\datums\diseases\brainrot.dm" @@ -1218,6 +1219,7 @@ #include "code\game\objects\items\dice.dm" #include "code\game\objects\items\dna_injector.dm" #include "code\game\objects\items\door_seal.dm" +#include "code\game\objects\items\drug_items.dm" #include "code\game\objects\items\dualsaber.dm" #include "code\game\objects\items\dyekit.dm" #include "code\game\objects\items\eightball.dm" @@ -1241,6 +1243,7 @@ #include "code\game\objects\items\kitchen.dm" #include "code\game\objects\items\latexballoon.dm" #include "code\game\objects\items\mail.dm" +#include "code\game\objects\items\maintenance_loot.dm" #include "code\game\objects\items\manuals.dm" #include "code\game\objects\items\mop.dm" #include "code\game\objects\items\paint.dm" @@ -1591,6 +1594,7 @@ #include "code\modules\actionspeed\_actionspeed_modifier.dm" #include "code\modules\actionspeed\modifiers\addiction.dm" #include "code\modules\actionspeed\modifiers\base.dm" +#include "code\modules\actionspeed\modifiers\drugs.dm" #include "code\modules\actionspeed\modifiers\mood.dm" #include "code\modules\actionspeed\modifiers\status_effects.dm" #include "code\modules\admin\admin.dm" @@ -2434,6 +2438,7 @@ #include "code\modules\hydroponics\grown\grass_carpet.dm" #include "code\modules\hydroponics\grown\hedges.dm" #include "code\modules\hydroponics\grown\korta_nut.dm" +#include "code\modules\hydroponics\grown\kronkus.dm" #include "code\modules\hydroponics\grown\melon.dm" #include "code\modules\hydroponics\grown\mushrooms.dm" #include "code\modules\hydroponics\grown\onion.dm"