Files
Bubberstation/code/game/objects/items/storage/backpack.dm
MrMelbert e85674d366 Unified CMO blues slightly, updates garment bags slightly, updates CMO locker contents slightly (#93321)
## About The Pull Request

### CMO palette update

Before - after

<img width="533" height="324" alt="image"
src="https://github.com/user-attachments/assets/c8a843a6-875d-4796-8c62-d24dd509147b"
/>

Logical follow up to #93313 and #91902

CMO now has a backpack which matches their teal palette rather than
re-using the medical doctor's blue backpack

CMO now starts with white sneakers instead of blue sneakers

### Garment bag update

Garment bags can hold backpacks, duffels, etc. 

However they CANNOT store backpacks which have ANY contents, so no risk
of storage nesting memes here.

### Misc

Removed the defib mount from the CMO's closet

Minor bugfix for being unable to swap storage positions of items which
were instantiated in a storage

## Why It's Good For The Game

- Much like the Paramedic, the CMO has had many cooks which have not
always been on the same page, so this makes their sprite a bit more
coherent.

- Heads with unique packs just tossed them in their closet which is
pretty spammy given we have four variants now. Putting them in the
garment back makes sense.

- Defib mount in CMO's locker hasn't been necessary for a while now that
all treatment centers spawn with defib mounts.

- Bugfix.

## Changelog

🆑 Melbert
image: CMO now has unique backpack/satchel/etc. sprites which matches
their teal palette.
image: CMO spawns with white sneakers instead of blue sneakers.
qol: Garment bags can hold empty backpacks/satchels/etc.
del: Defib mount removed from CMO's locker.
fix: Items stocked in a storage item by default can be
mouse-drag-swapped like any other item.
/🆑
2025-10-13 00:16:49 +02:00

500 lines
18 KiB
Plaintext

/* Backpacks
* Contains:
* Backpack
* Backpack Types
* Satchel Types
*/
/*
* Backpack
*/
/obj/item/storage/backpack
name = "backpack"
desc = "You wear this on your back and put items into it."
icon = 'icons/obj/storage/backpack.dmi'
worn_icon = 'icons/mob/clothing/back/backpack.dmi'
icon_state = "backpack"
inhand_icon_state = "backpack"
lefthand_file = 'icons/mob/inhands/equipment/backpack_lefthand.dmi'
righthand_file = 'icons/mob/inhands/equipment/backpack_righthand.dmi'
w_class = WEIGHT_CLASS_BULKY
slot_flags = ITEM_SLOT_BACK //ERROOOOO
resistance_flags = NONE
max_integrity = 300
storage_type = /datum/storage/backpack
pickup_sound = 'sound/items/handling/backpack/backpack_pickup1.ogg'
drop_sound = 'sound/items/handling/backpack/backpack_drop1.ogg'
equip_sound = 'sound/items/equip/backpack_equip.ogg'
sound_vary = TRUE
/obj/item/storage/backpack/Initialize(mapload)
. = ..()
AddElement(/datum/element/attack_equip)
/*
* Backpack Types
*/
/obj/item/bag_of_holding_inert
name = "inert bag of holding"
desc = "What is currently a just an unwieldy block of metal with a slot ready to accept a bluespace anomaly core."
icon = 'icons/obj/storage/backpack.dmi'
worn_icon = 'icons/mob/clothing/back/backpack.dmi'
icon_state = "bag_of_holding-inert"
inhand_icon_state = "brokenpack"
lefthand_file = 'icons/mob/inhands/equipment/backpack_lefthand.dmi'
righthand_file = 'icons/mob/inhands/equipment/backpack_righthand.dmi'
w_class = WEIGHT_CLASS_BULKY
resistance_flags = FIRE_PROOF
item_flags = NO_MAT_REDEMPTION
/obj/item/bag_of_holding_inert/Initialize(mapload)
. = ..()
var/static/list/recipes = list(/datum/crafting_recipe/boh)
AddElement(/datum/element/slapcrafting, recipes)
/obj/item/storage/backpack/holding
name = "bag of holding"
desc = "A backpack that opens into a localized pocket of bluespace."
icon_state = "bag_of_holding"
inhand_icon_state = "holdingpack"
resistance_flags = FIRE_PROOF
item_flags = NO_MAT_REDEMPTION
armor_type = /datum/armor/backpack_holding
storage_type = /datum/storage/bag_of_holding
pickup_sound = null
drop_sound = null
/datum/armor/backpack_holding
fire = 60
acid = 50
/obj/item/storage/backpack/holding/suicide_act(mob/living/user)
user.visible_message(span_suicide("[user] is jumping into [src]! It looks like [user.p_theyre()] trying to commit suicide."))
user.dropItemToGround(src, TRUE)
user.Stun(100, ignore_canstun = TRUE)
sleep(2 SECONDS)
playsound(src, SFX_RUSTLE, 50, TRUE, -5)
user.suicide_log()
qdel(user)
/obj/item/storage/backpack/santabag
name = "Santa's Gift Bag"
desc = "Space Santa uses this to deliver presents to all the nice children in space in Christmas! Wow, it's pretty big!"
icon_state = "giftbag0"
inhand_icon_state = "giftbag"
w_class = WEIGHT_CLASS_BULKY
storage_type = /datum/storage/backpack/santabag
/obj/item/storage/backpack/santabag/Initialize(mapload)
. = ..()
regenerate_presents()
/obj/item/storage/backpack/santabag/suicide_act(mob/living/user)
user.visible_message(span_suicide("[user] places [src] over [user.p_their()] head and pulls it tight! It looks like [user.p_they()] [user.p_are()]n't in the Christmas spirit..."))
return OXYLOSS
/obj/item/storage/backpack/santabag/proc/regenerate_presents()
addtimer(CALLBACK(src, PROC_REF(regenerate_presents)), 30 SECONDS)
var/mob/user = get(loc, /mob)
if(!istype(user))
return
if(HAS_MIND_TRAIT(user, TRAIT_CANNOT_OPEN_PRESENTS))
var/turf/floor = get_turf(src)
var/obj/item/thing = new /obj/item/gift/anything(floor)
if(!atom_storage.attempt_insert(thing, user, override = TRUE, force = STORAGE_SOFT_LOCKED))
qdel(thing)
/obj/item/storage/backpack/cultpack
name = "trophy rack"
desc = "It's useful for both carrying extra gear and proudly declaring your insanity."
icon_state = "backpack-cult"
inhand_icon_state = "backpack"
alternate_worn_layer = ABOVE_BODY_FRONT_HEAD_LAYER
/obj/item/storage/backpack/clown
name = "Giggles von Honkerton"
desc = "It's a backpack made by Honk! Co."
icon_state = "backpack-clown"
inhand_icon_state = "clownpack"
/obj/item/storage/backpack/explorer
name = "explorer bag"
desc = "A robust backpack for stashing your loot."
icon_state = "backpack-explorer"
inhand_icon_state = "explorerpack"
/obj/item/storage/backpack/mime
name = "Parcel Parceaux"
desc = "A silent backpack made for those silent workers. Silence Co."
icon_state = "backpack-mime"
inhand_icon_state = "mimepack"
/obj/item/storage/backpack/medic
name = "medical backpack"
desc = "It's a backpack especially designed for use in a sterile environment."
icon_state = "backpack-medical"
inhand_icon_state = "medicalpack"
/obj/item/storage/backpack/chief_medic
name = "chief medical officer's backpack"
desc = "A backpack with just enough pockets to carry the chief medical officer's equipment."
icon_state = "backpack-chiefmedical"
inhand_icon_state = "medicalpack"
/obj/item/storage/backpack/coroner
name = "coroner backpack"
desc = "It's a backpack especially designed for use in an undead environment."
icon_state = "backpack-coroner"
inhand_icon_state = "coronerpack"
/obj/item/storage/backpack/security
name = "security backpack"
desc = "It's a very robust backpack."
icon_state = "backpack-security"
inhand_icon_state = "securitypack"
/obj/item/storage/backpack/captain
name = "captain's backpack"
desc = "It's a special backpack made exclusively for Nanotrasen officers."
icon_state = "backpack-captain"
inhand_icon_state = "captainpack"
/obj/item/storage/backpack/industrial
name = "industrial backpack"
desc = "It's a tough backpack for the daily grind of station life."
icon_state = "backpack-engineering"
inhand_icon_state = "engiepack"
resistance_flags = FIRE_PROOF
/obj/item/storage/backpack/botany
name = "botany backpack"
desc = "It's a backpack made of all-natural fibers."
icon_state = "backpack-hydroponics"
inhand_icon_state = "botpack"
/obj/item/storage/backpack/chemistry
name = "chemistry backpack"
desc = "A backpack specially designed to repel stains and hazardous liquids."
icon_state = "backpack-chemistry"
inhand_icon_state = "chempack"
/obj/item/storage/backpack/genetics
name = "genetics backpack"
desc = "A bag designed to be super tough, just in case someone hulks out on you."
icon_state = "backpack-genetics"
inhand_icon_state = "genepack"
/obj/item/storage/backpack/science
name = "science backpack"
desc = "A specially designed backpack. It's fire resistant and smells vaguely of plasma."
icon_state = "backpack-science"
inhand_icon_state = "scipack"
/obj/item/storage/backpack/virology
name = "virology backpack"
desc = "A backpack made of hypo-allergenic fibers. It's designed to help prevent the spread of disease. Smells like monkey."
icon_state = "backpack-virology"
inhand_icon_state = "viropack"
/obj/item/storage/backpack/floortile
name = "floortile backpack"
desc = "It's a backpack especially designed for use in floortiles..."
icon_state = "floortile_backpack"
inhand_icon_state = "backpack"
/obj/item/storage/backpack/ert
name = "emergency response team commander backpack"
desc = "A spacious backpack with lots of pockets, worn by the Commander of an Emergency Response Team."
icon_state = "ert_commander"
inhand_icon_state = "securitypack"
resistance_flags = FIRE_PROOF
/obj/item/storage/backpack/ert/security
name = "emergency response team security backpack"
desc = "A spacious backpack with lots of pockets, worn by Security Officers of an Emergency Response Team."
icon_state = "ert_security"
/obj/item/storage/backpack/ert/medical
name = "emergency response team medical backpack"
desc = "A spacious backpack with lots of pockets, worn by Medical Officers of an Emergency Response Team."
icon_state = "ert_medical"
/obj/item/storage/backpack/ert/engineer
name = "emergency response team engineer backpack"
desc = "A spacious backpack with lots of pockets, worn by Engineers of an Emergency Response Team."
icon_state = "ert_engineering"
/obj/item/storage/backpack/ert/janitor
name = "emergency response team janitor backpack"
desc = "A spacious backpack with lots of pockets, worn by Janitors of an Emergency Response Team."
icon_state = "ert_janitor"
/obj/item/storage/backpack/ert/clown
name = "emergency response team clown backpack"
desc = "A spacious backpack with lots of pockets, worn by Clowns of an Emergency Response Team."
icon_state = "ert_clown"
/obj/item/storage/backpack/saddlepack
name = "saddlepack"
desc = "A backpack designed to be saddled on a mount or carried on your back, and switch between the two on the fly. It's quite spacious, at the cost of making you feel like a literal pack mule."
icon = 'icons/obj/storage/ethereal.dmi'
worn_icon = 'icons/mob/clothing/back/ethereal.dmi'
icon_state = "saddlepack"
storage_type = /datum/storage/backpack/saddle
// MEAT MEAT MEAT MEAT MEAT
///This nullifies the force malus from the meat material while not touching other stats.
#define INVERSE_MEAT_STRENTGH (1 / /datum/material/meat::strength_modifier)
/obj/item/storage/backpack/meat
name = "\improper MEAT"
desc = "MEAT MEAT MEAT MEAT MEAT MEAT"
icon_state = "meatmeatmeat"
inhand_icon_state = "meatmeatmeat"
force = 15 * INVERSE_MEAT_STRENTGH
throwforce = 15 * INVERSE_MEAT_STRENTGH
material_flags = MATERIAL_EFFECTS | MATERIAL_AFFECT_STATISTICS
attack_verb_continuous = list("MEATS", "MEAT MEATS")
attack_verb_simple = list("MEAT", "MEAT MEAT")
custom_materials = list(/datum/material/meat = SHEET_MATERIAL_AMOUNT * 15) // MEAT
///Sounds used in the squeak component
var/list/meat_sounds = list('sound/effects/blob/blobattack.ogg' = 1)
///Reagents added to the edible component on top of the meat material, ingested when you EAT the MEAT
var/list/meat_reagents = list(
/datum/reagent/consumable/nutriment/vitamin = 15,
)
///Eating verbs when consuming the MEAT
var/list/eatverbs = list("MEAT", "absorb", "gnaw", "consume")
/obj/item/storage/backpack/meat/Initialize(mapload)
. = ..()
AddComponentFrom(
SOURCE_EDIBLE_INNATE, \
/datum/component/edible,\
initial_reagents = meat_reagents,\
tastes = list("meat" = 1),\
eatverbs = eatverbs,\
)
AddComponent(/datum/component/squeak, meat_sounds)
#undef INVERSE_MEAT_STRENTGH
/*
* Satchel Types
*/
/obj/item/storage/backpack/satchel
name = "satchel"
desc = "A trendy looking satchel."
icon_state = "satchel-norm"
inhand_icon_state = "satchel-norm"
/obj/item/storage/backpack/satchel/leather
name = "leather satchel"
desc = "It's a very fancy satchel made with fine leather."
icon_state = "satchel-leather"
inhand_icon_state = "satchel"
/obj/item/storage/backpack/satchel/leather/withwallet/PopulateContents()
new /obj/item/storage/wallet/random(src)
/obj/item/storage/backpack/satchel/fireproof
resistance_flags = FIRE_PROOF
/obj/item/storage/backpack/satchel/eng
name = "industrial satchel"
desc = "A tough satchel with extra pockets."
icon_state = "satchel-engineering"
inhand_icon_state = "satchel-eng"
resistance_flags = FIRE_PROOF
/obj/item/storage/backpack/satchel/med
name = "medical satchel"
desc = "A sterile satchel used in medical departments."
icon_state = "satchel-medical"
inhand_icon_state = "satchel-med"
/obj/item/storage/backpack/satchel/chief_medic
name = "chief medical officer's satchel"
desc = "A satchel with barely enough pockets to carry the chief medical officer's equipment."
icon_state = "satchel-chiefmedical"
inhand_icon_state = "satchel-med"
/obj/item/storage/backpack/satchel/vir
name = "virologist satchel"
desc = "A sterile satchel with virologist colours."
icon_state = "satchel-virology"
inhand_icon_state = "satchel-vir"
/obj/item/storage/backpack/satchel/chem
name = "chemist satchel"
desc = "A sterile satchel with chemist colours."
icon_state = "satchel-chemistry"
inhand_icon_state = "satchel-chem"
/obj/item/storage/backpack/satchel/coroner
name = "coroner satchel"
desc = "A satchel used to carry whatever's left of human bodies."
icon_state = "satchel-coroner"
inhand_icon_state = "satchel-coroner"
/obj/item/storage/backpack/satchel/gen
name = "geneticist satchel"
desc = "A sterile satchel with geneticist colours."
icon_state = "satchel-genetics"
inhand_icon_state = "satchel-gen"
/obj/item/storage/backpack/satchel/science
name = "scientist satchel"
desc = "Useful for holding research materials."
icon_state = "satchel-science"
inhand_icon_state = "satchel-sci"
/obj/item/storage/backpack/satchel/hyd
name = "botanist satchel"
desc = "A satchel made of all natural fibers."
icon_state = "satchel-hydroponics"
inhand_icon_state = "satchel-hyd"
/obj/item/storage/backpack/satchel/sec
name = "security satchel"
desc = "A robust satchel for security related needs."
icon_state = "satchel-security"
inhand_icon_state = "satchel-sec"
/obj/item/storage/backpack/satchel/explorer
name = "explorer satchel"
desc = "A robust satchel for stashing your loot."
icon_state = "satchel-explorer"
inhand_icon_state = "satchel-explorer"
/obj/item/storage/backpack/satchel/cap
name = "captain's satchel"
desc = "An exclusive satchel for Nanotrasen officers."
icon_state = "satchel-captain"
inhand_icon_state = "satchel-cap"
/obj/item/storage/backpack/satchel/flat
name = "smuggler's satchel"
desc = "A very slim satchel that can easily fit into tight spaces. Its contents cannot be detected by contraband scanners."
icon_state = "satchel-flat"
inhand_icon_state = "satchel-flat"
w_class = WEIGHT_CLASS_NORMAL //Can fit in backpacks itself.
storage_type = /datum/storage/backpack/satchel_flat
/obj/item/storage/backpack/satchel/flat/Initialize(mapload)
. = ..()
AddElement(/datum/element/undertile, TRAIT_T_RAY_VISIBLE, INVISIBILITY_OBSERVER, use_anchor = TRUE)
ADD_TRAIT(src, TRAIT_CONTRABAND_BLOCKER, INNATE_TRAIT)
/obj/item/storage/backpack/satchel/flat/PopulateContents()
for(var/items in 1 to 4)
new /obj/effect/spawner/random/contraband(src)
/obj/item/storage/backpack/satchel/flat/with_tools/PopulateContents()
new /obj/item/stack/tile/iron/base(src)
new /obj/item/crowbar(src)
..()
/obj/item/storage/backpack/satchel/flat/empty/PopulateContents()
return
/// Messenger Bag Types
/obj/item/storage/backpack/messenger
name = "messenger bag"
desc = "A trendy looking messenger bag; sometimes known as a courier bag. Fashionable and portable."
icon_state = "messenger"
inhand_icon_state = "messenger"
icon = 'icons/obj/storage/backpack.dmi'
worn_icon = 'icons/mob/clothing/back/backpack.dmi'
lefthand_file = 'icons/mob/inhands/equipment/backpack_lefthand.dmi'
righthand_file = 'icons/mob/inhands/equipment/backpack_righthand.dmi'
/obj/item/storage/backpack/messenger/eng
name = "industrial messenger bag"
desc = "A tough messenger bag made of advanced treated leather for fireproofing. It also has more pockets than usual."
icon_state = "messenger_engineering"
inhand_icon_state = "messenger_engineering"
resistance_flags = FIRE_PROOF
/obj/item/storage/backpack/messenger/med
name = "medical messenger bag"
desc = "A sterile messenger bag well loved by medics for its portability and sleek profile."
icon_state = "messenger_medical"
inhand_icon_state = "messenger_medical"
/obj/item/storage/backpack/messenger/chief_medic
name = "chief medical officer's messenger bag"
desc = "A slim messenger bag appreciated by chief medical officers for staying out of their way while working - unlike their chemists."
icon_state = "messenger_chiefmedical"
inhand_icon_state = "messenger_medical"
/obj/item/storage/backpack/messenger/vir
name = "virologist messenger bag"
desc = "A sterile messenger bag with virologist colours, useful for deploying biohazards in record times."
icon_state = "messenger_virology"
inhand_icon_state = "messenger_virology"
/obj/item/storage/backpack/messenger/chem
name = "chemist messenger bag"
desc = "A sterile messenger bag with chemist colours, good for getting to your alleyway deals on time."
icon_state = "messenger_chemistry"
inhand_icon_state = "messenger_chemistry"
/obj/item/storage/backpack/messenger/coroner
name = "coroner messenger bag"
desc = "A messenger bag used to sneak your way out of graveyards at a good pace."
icon_state = "messenger_coroner"
inhand_icon_state = "messenger_coroner"
/obj/item/storage/backpack/messenger/gen
name = "geneticist messenger bag"
desc = "A sterile messenger bag with geneticist colours, making a remarkably cute accessory for hulks."
icon_state = "messenger_genetics"
inhand_icon_state = "messenger_genetics"
/obj/item/storage/backpack/messenger/science
name = "scientist messenger bag"
desc = "Useful for holding research materials, and for speeding your way to different scan objectives."
icon_state = "messenger_science"
inhand_icon_state = "messenger_science"
/obj/item/storage/backpack/messenger/hyd
name = "botanist messenger bag"
desc = "A messenger bag made of all natural fibers, great for getting to the sesh in time."
icon_state = "messenger_hydroponics"
inhand_icon_state = "messenger_hydroponics"
/obj/item/storage/backpack/messenger/sec
name = "security messenger bag"
desc = "A robust messenger bag for security related needs."
icon_state = "messenger_security"
inhand_icon_state = "messenger_security"
/obj/item/storage/backpack/messenger/explorer
name = "explorer messenger bag"
desc = "A robust messenger bag for stashing your loot, as well as making a remarkably cute accessory for your drakebone armor."
icon_state = "messenger_explorer"
inhand_icon_state = "messenger_explorer"
/obj/item/storage/backpack/messenger/cap
name = "captain's messenger bag"
desc = "An exclusive messenger bag for Nanotrasen officers, made of real whale leather."
icon_state = "messenger_captain"
inhand_icon_state = "messenger_captain"
/obj/item/storage/backpack/messenger/clown
name = "Giggles von Honkerton Jr."
desc = "The latest in storage 'technology' from Honk Co. Hey, how does this fit so much with such a small profile anyway? The wearer will definitely never tell you."
icon_state = "messenger_clown"
inhand_icon_state = "messenger_clown"