diff --git a/citadel.dme b/citadel.dme index 68b16e09f4f1..d9fff80cfd1f 100644 --- a/citadel.dme +++ b/citadel.dme @@ -22,6 +22,7 @@ #include "code\__DEFINES\_bitfields.dm" #include "code\__DEFINES\_cooldowns.dm" #include "code\__DEFINES\_core.dm" +#include "code\__DEFINES\_enums.dm" #include "code\__DEFINES\_globals.dm" #include "code\__DEFINES\_lists.dm" #include "code\__DEFINES\_planes+layers.dm" @@ -201,6 +202,7 @@ #include "code\__DEFINES\fishing\fishing.dm" #include "code\__DEFINES\inventory\accessories.dm" #include "code\__DEFINES\inventory\bodytypes.dm" +#include "code\__DEFINES\inventory\carry_weight.dm" #include "code\__DEFINES\inventory\icons.dm" #include "code\__DEFINES\inventory\misc.dm" #include "code\__DEFINES\inventory\procs.dm" @@ -3422,6 +3424,7 @@ #include "code\modules\mob\living\carbon\human\human_resist.dm" #include "code\modules\mob\living\carbon\human\human_species.dm" #include "code\modules\mob\living\carbon\human\inventory.dm" +#include "code\modules\mob\living\carbon\human\inventory_legacy.dm" #include "code\modules\mob\living\carbon\human\life.dm" #include "code\modules\mob\living\carbon\human\login.dm" #include "code\modules\mob\living\carbon\human\logout.dm" @@ -4402,6 +4405,7 @@ #include "code\modules\shuttles\web_datums.dm" #include "code\modules\species\abilites.dm" #include "code\modules\species\character_species.dm" +#include "code\modules\species\physiology.dm" #include "code\modules\species\species.dm" #include "code\modules\species\species_attack.dm" #include "code\modules\species\species_getters.dm" @@ -4641,16 +4645,17 @@ #include "code\modules\tgchat\to_chat.dm" #include "code\modules\tgs\includes.dm" #include "code\modules\tgui\external.dm" -#include "code\modules\tgui\modal_vr.dm" +#include "code\modules\tgui\modal_vr_legacy.dm" #include "code\modules\tgui\module.dm" #include "code\modules\tgui\states.dm" #include "code\modules\tgui\status_composers.dm" #include "code\modules\tgui\tgui.dm" -#include "code\modules\tgui\tgui_alert.dm" -#include "code\modules\tgui\tgui_input_list.dm" -#include "code\modules\tgui\tgui_input_number.dm" -#include "code\modules\tgui\tgui_input_text.dm" #include "code\modules\tgui\tgui_window.dm" +#include "code\modules\tgui\modals\tgui_alert.dm" +#include "code\modules\tgui\modals\tgui_dynamic_input.dm" +#include "code\modules\tgui\modals\tgui_input_list.dm" +#include "code\modules\tgui\modals\tgui_input_number.dm" +#include "code\modules\tgui\modals\tgui_input_text.dm" #include "code\modules\tgui\modules\_base.dm" #include "code\modules\tgui\modules\alarm.dm" #include "code\modules\tgui\modules\atmos_control.dm" diff --git a/code/__DEFINES/_enums.dm b/code/__DEFINES/_enums.dm new file mode 100644 index 000000000000..d085dffa3793 --- /dev/null +++ b/code/__DEFINES/_enums.dm @@ -0,0 +1,8 @@ +// todo: enum system like bitfields +/// KEY: must be unique, may be arbitrary; not a string, as it's used in typepath generation +/// CONSTRAINTS: list(/type = list(varname, ...), ...) +/// ENUMS: list of ENUM(). +#define DEFINE_ENUM(KEY, CONSTRAINTS, ENUMS) +/// NAME: must be a string +/// VALUE: the actual enum value, whatever it is +#define ENUM(NAME, VALUE) ##NAME = ##VALUE diff --git a/code/__DEFINES/_flags/item_flags.dm b/code/__DEFINES/_flags/item_flags.dm index 29e39d3fa157..9feebe4d2d4f 100644 --- a/code/__DEFINES/_flags/item_flags.dm +++ b/code/__DEFINES/_flags/item_flags.dm @@ -23,6 +23,11 @@ #define ITEM_NO_LATHE_DECONSTRUCT (1<<10) /// stack-like handling for ingredients #define ITEM_MASS_INGREDIENT (1<<11) +/// encumbers while in hand +#define ITEM_ENCUMBERS_WHILE_HELD (1<<12) +/// doesn't encumber while not in hand +#define ITEM_ENCUMBERS_ONLY_HELD (1<<13) +// todo: ITEM_SLOWS_WHILE_HELD for slowdown DEFINE_BITFIELD(item_flags, list( BITFIELD(ITEM_IN_INVENTORY), @@ -37,6 +42,8 @@ DEFINE_BITFIELD(item_flags, list( BITFIELD(ITEM_EASY_LATHE_DECONSTRUCT), BITFIELD(ITEM_NO_LATHE_DECONSTRUCT), BITFIELD(ITEM_MASS_INGREDIENT), + BITFIELD(ITEM_ENCUMBERS_WHILE_HELD), + BITFIELD(ITEM_ENCUMBERS_ONLY_HELD), )) //! Flags for the clothing_flags var on /obj/item @@ -47,7 +54,7 @@ DEFINE_BITFIELD(item_flags, list( #define CLOTHING_IGNORE_BELTLINK (1<<2) /// for plural limbs, wearable with just one #define CLOTHING_ALLOW_SINGLE_LIMB (1<<3) -/// Prevents syringes, parapens and hyposprays if equipped to slot_suit or SLOT_ID_HEAD. +/// Prevents syringes, parapens and hyposprays. #define CLOTHING_THICK_MATERIAL (1<<4) /// Syringes / hyposprays / etc can get through, but need to pass through an injection port. #define CLOTHING_INJECTION_PORT (1<<5) diff --git a/code/__DEFINES/inventory/carry_weight.dm b/code/__DEFINES/inventory/carry_weight.dm new file mode 100644 index 000000000000..3858f6880a9f --- /dev/null +++ b/code/__DEFINES/inventory/carry_weight.dm @@ -0,0 +1,286 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + +//? Despite this being carry_weight.dm, this contains defines for: +//? carry strength - how much someone can carry or move +//? weight - how much stuff weighs, recursive +//? encumberence - how hard it is to move with an item, non-recursive + +//* CHECK https://www.desmos.com/calculator/o44o3naob2 FOR INFORMATION *// +//* DO nOT CHANGE ANY CONSTANTS WItHOUT GRAPHING IT OUT FIRST. *// + +//? Carry strength - flat strength. you can carry up to this with no penalty. + +#define CARRY_STRENGTH_BASELINE 20 + +#define CARRY_STRENGTH_ADD_HUMAN 1.25 +#define CARRY_STRENGTH_ADD_UNATHI 2.5 +#define CARRY_STRENGTH_ADD_PROTEAN 2.5 +#define CARRY_STRENGTH_ADD_MOTH_LIGHT 1.25 +#define CARRY_STRENGTH_ADD_MOTH_DARK 0 +#define CARRY_STRENGTH_ADD_TAJARAN 0 +#define CARRY_STRENGTH_ADD_TESHARI 0 +#define CARRY_STRENGTH_ADD_XENOCHIMERA 2.5 +#define CARRY_STRENGTH_ADD_XENOHYBRID 2.5 + +//? Carry factor - multiplier for penalizing over-limit weight; higher is worse. + +#define CARRY_FACTOR_BASELINE 1 + +#define CARRY_FACTOR_MOD_HUMAN 0.92 +#define CARRY_FACTOR_MOD_UNATHI 0.92 +#define CARRY_FACTOR_MOD_MOTH_LIGHT 0.96 +#define CARRY_FACTOR_MOD_MOTH_DARK 1.08 +#define CARRY_FACTOR_MOD_TAJARAN 1.08 +#define CARRY_FACTOR_MOD_TESHARI 1.12 +#define CARRY_FACTOR_MOD_PROTEAN 1.12 +#define CARRY_FACTOR_MOD_XENOCHIMERA 0.88 +#define CARRY_FACTOR_MOD_XENOHYBRID 0.88 + +//? Carry equation constants + +/// How penalizing the default penalty curve is; lower is weaker slowdowns from overweight. +#define CARRY_WEIGHT_SCALING 2 +/// For now, constant - bias factor; higher = skip more of the curve as soon as weight goes above strength +#define CARRY_WEIGHT_BIAS 1.2 +/// % from 0 to 1 of the curve that is automatically given ; 0.1 = the asymptote is 10%, as opposed to 0% movespeed +#define CARRY_WEIGHT_ASYMPTOTE 0.1 + +//? Item Encumbrance defines + +#define ITEM_ENCUMBRANCE_BASELINE 0 + +//* Armor + +#define ITEM_ENCUMBRANCE_ARMOR_ULTRALIGHT 7.5 +#define ITEM_ENCUMBRANCE_ARMOR_LIGHT 10 +#define ITEM_ENCUMBRANCE_ARMOR_MEDIUM 15 +#define ITEM_ENCUMBRANCE_ARMOR_HEAVY 20 +#define ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY 30 +#define ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED 15 + +#define ITEM_ENCUMBRANCE_ARMOR_ULTRALIGHT_HELMET 1 +#define ITEM_ENCUMBRANCE_ARMOR_LIGHT_HELMET 1.5 +#define ITEM_ENCUMBRANCE_ARMOR_MEDIUM_HELMET 2 +#define ITEM_ENCUMBRANCE_ARMOR_HEAVY_HELMET 2.5 +#define ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_HELMET 3 +#define ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED_HELMET 2 + +#define ITEM_ENCUMBRANCE_ARMOR_ULTRALIGHT_GLOVES 1 +#define ITEM_ENCUMBRANCE_ARMOR_LIGHT_GLOVES 2 +#define ITEM_ENCUMBRANCE_ARMOR_MEDIUM_GLOVES 3 +#define ITEM_ENCUMBRANCE_ARMOR_HEAVY_GLOVES 4 +#define ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_GLOVES 5 +#define ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED_GLOVES 3 + +#define ITEM_ENCUMBRANCE_ARMOR_ULTRALIGHT_BOOTS 2.5 +#define ITEM_ENCUMBRANCE_ARMOR_LIGHT_BOOTS 3.5 +#define ITEM_ENCUMBRANCE_ARMOR_MEDIUM_BOOTS 5 +#define ITEM_ENCUMBRANCE_ARMOR_HEAVY_BOOTS 7.5 +#define ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_BOOTS 10 +#define ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED_BOOTS 5 + +#define ITEM_ENCUMBRANCE_ARMOR_BIORAD_SUIT 30 +#define ITEM_ENCUMBRANCE_ARMOR_BIORAD_HELMET 0 +#define ITEM_ENCUMBRANCE_ARMOR_BOMB_SUIT 30 +#define ITEM_ENCUMBRANCE_ARMOR_BOMB_HELMET 0 +#define ITEM_ENCUMBRANCE_ARMOR_FIRE_SUIT 30 +#define ITEM_ENCUMBRANCE_ARMOR_FIRE_HELMET 0 + +#define ITEM_ENCUMBRANCE_ARMOR_MEDIEVAL_PLATE 30 +#define ITEM_ENCUMBRANCE_ARMOR_MEDIEVAL_CHAIN 25 + +#define ITEM_ENCUMBRANCE_ARMOR_ANOMALY 30 +#define ITEM_ENCUMBRANCE_ARMOR_ANOMALY_HELMET 0 + +//* Clothing + +/// shoecuffs +#define ITEM_ENCUMBRANCE_SHOES_CUFFED 50 +/// magboots off +#define ITEM_ENCUMBRANCE_SHOES_MAGBOOTS 5 +/// normal magboots on +#define ITEM_ENCUMBRANCE_SHOES_MAGBOOTS_PULSE 20 +/// ce magboots on +#define ITEM_ENCUMBRANCE_SHOES_MAGBOOTS_PULSE_ADVANCED 7.5 +#define ITEM_ENCUMBRANCE_SHOES_CLOWN 5 +#define ITEM_ENCUMBRANCE_SHOES_FINS 5 +#define ITEM_ENCUMBRANCE_SHOES_GALOSHES 5 + +//* Factions + +#define ITEM_ENCUMBRANCE_CHANGELING_MAGBOOTS 5 +#define ITEM_ENCUMBRANCE_CHANGELING_MAGBOOTS_PULSE 7.5 +#define ITEM_ENCUMBRANCE_CULT_VOIDSUIT 35 +#define ITEM_ENCUMBRANCE_CULT_VOIDSUIT_HELMET 2.5 + +//* Spacesuits + +#define ITEM_ENCUMBRANCE_SOFTSUIT 30 +#define ITEM_ENCUMBRANCE_SOFTSUIT_HELMET 2.5 + +#define ITEM_ENCUMBRANCE_VOIDSUIT 30 +#define ITEM_ENCUMBRANCE_VOIDSUIT_HELMET 0 +#define ITEM_ENCUMBRANCE_VOIDSUIT_LIGHT 25 +#define ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_LIGHT 0 +#define ITEM_ENCUMBRANCE_VOIDSUIT_HEAVY 35 +#define ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_HEAVY 0 +#define ITEM_ENCUMBRANCE_VOIDSUIT_ULTRALIGHT 20 +#define ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_ULTRALIGHT 0 + +#define ITEM_ENCUMBRANCE_VOIDSUIT_ANOMALY 30 +#define ITEM_ENCUMBRANCE_VOIDSUIT_ANOMALY_HELMET 2.5 + +#define ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT 25 +#define ITEM_ENCUMBRANCE_LEGACY_RIG 30 +#define ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY 35 + +#define ITEM_ENCUMBRANCE_EMERGENCY_SOFTSUIT 30 +#define ITEM_ENCUMBRANCE_EMERGENCY_SOFTSUIT_HELMET 0 + +//* Storage + +#define ITEM_ENCUMBRANCE_STORAGE_BACKPACK 5 +#define ITEM_ENCUMBRANCE_STORAGE_DUFFLEBAG 5 +#define ITEM_ENCUMBRANCE_STORAGE_POUCH_LARGE 5 + +//* Species + +#define ITEM_ENCUMBRANCE_PHORONOID_SUIT 20 +#define ITEM_ENCUMBRANCE_PHORONOID_HELMET 0 +#define ITEM_ENCUMBRANCE_TAJARAN_SWORDSMAN_ARMOR 20 + +//* Weapons + +#define ITEM_ENCUMBRANCE_GUN_LIGHT 2.5 +#define ITEM_ENCUMBRANCE_GUN_NORMAL 5 +#define ITEM_ENCUMBRANCE_GUN_LARGE 7.5 +#define ITEM_ENCUMBRANCE_GUN_BULKY 12.5 +#define ITEM_ENCUMBRANCE_GUN_UNREASONABLE 17.5 +#define ITEM_ENCUMBRANCE_GUN_RIDICULOUS 30 +#define ITEM_ENCUMBRANCE_GUN_VEHICLE 60 + +#define ITEM_ENCUMBRANCE_MELEE_SPEAR 15 +#define ITEM_ENCUMBRANCE_MELEE_SLEDGEHAMMER 20 + +#define ITEM_ENCUMBRANCE_SHIELD_TOWER 30 + +//? Item Flat Encumbrance defines + +#define ITEM_FLAT_ENCUMBRANCE_DUFFLEBAG 30 +#define ITEM_FLAT_ENCUMBRANCE_GALOSHES 30 +#define ITEM_FLAT_ENCUMBRANCE_SHOES_CLOWN 30 +#define ITEM_FLAT_ENCUMBRANCE_SHOES_FINS 30 + +//? Item Weight defines + +#define ITEM_WEIGHT_BASELINE 0 + +//* Armor + +#define ITEM_WEIGHT_ARMOR_ULTRALIGHT 0 +#define ITEM_WEIGHT_ARMOR_LIGHT 0 +#define ITEM_WEIGHT_ARMOR_MEDIUM 0 +#define ITEM_WEIGHT_ARMOR_HEAVY 0 +#define ITEM_WEIGHT_ARMOR_SUPERHEAVY 0 +#define ITEM_WEIGHT_ARMOR_SPECIALIZED 0 + +#define ITEM_WEIGHT_ARMOR_ULTRALIGHT_HELMET 0 +#define ITEM_WEIGHT_ARMOR_LIGHT_HELMET 0 +#define ITEM_WEIGHT_ARMOR_MEDIUM_HELMET 0 +#define ITEM_WEIGHT_ARMOR_HEAVY_HELMET 0 +#define ITEM_WEIGHT_ARMOR_SUPERHEAVY_HELMET 0 +#define ITEM_WEIGHT_ARMOR_SPECIALIZED_HELMET 0 + +#define ITEM_WEIGHT_ARMOR_ULTRALIGHT_GLOVES 0 +#define ITEM_WEIGHT_ARMOR_LIGHT_GLOVES 0 +#define ITEM_WEIGHT_ARMOR_MEDIUM_GLOVES 0 +#define ITEM_WEIGHT_ARMOR_HEAVY_GLOVES 0 +#define ITEM_WEIGHT_ARMOR_SUPERHEAVY_GLOVES 0 +#define ITEM_WEIGHT_ARMOR_SPECIALIZED_GLOVES 0 + +#define ITEM_WEIGHT_ARMOR_ULTRALIGHT_BOOTS 0 +#define ITEM_WEIGHT_ARMOR_LIGHT_BOOTS 0 +#define ITEM_WEIGHT_ARMOR_MEDIUM_BOOTS 0 +#define ITEM_WEIGHT_ARMOR_HEAVY_BOOTS 0 +#define ITEM_WEIGHT_ARMOR_SUPERHEAVY_BOOTS 0 +#define ITEM_WEIGHT_ARMOR_SPECIALIZED_BOOTS 0 + +#define ITEM_WEIGHT_ARMOR_BIORAD_SUIT 0 +#define ITEM_WEIGHT_ARMOR_BIORAD_SUIT_HELMET 0 +#define ITEM_WEIGHT_ARMOR_BOMB_SUIT 0 +#define ITEM_WEIGHT_ARMOR_BOMB_HELMET 0 +#define ITEM_WEIGHT_ARMOR_FIRE_SUIT 0 +#define ITEM_WEIGHT_ARMOR_FIRE_SUIT_HELMET 0 + +#define ITEM_WEIGHT_ARMOR_MEDIEVAL_PLATE 0 +#define ITEM_WEIGHT_ARMOR_MEDIEVAL_CHAIN 0 + +#define ITEM_WEIGHT_ARMOR_ANOMALY 0 +#define ITEM_WEIGHT_ARMOR_ANOMALY_HELMET 0 + +//* Clothing + +//* Items + +#define ITEM_WEIGHT_GAS_TANK 0 +#define ITEM_WEIGHT_VEHICLE_FRAME 0 + +//* Spacesuits / RIGs + +#define ITEM_WEIGHT_SOFTSUIT 0 +#define ITEM_WEIGHT_SOFTSUIT_HELMET 0 + +#define ITEM_WEIGHT_VOIDSUIT 0 +#define ITEM_WEIGHT_VOIDSUIT_HELMET 0 +#define ITEM_WEIGHT_VOIDSUIT_LIGHT 0 +#define ITEM_WEIGHT_VOIDSUIT_HELMET_LIGHT 0 +#define ITEM_WEIGHT_VOIDSUIT_HEAVY 0 +#define ITEM_WEIGHT_VOIDSUIT_HELMET_HEAVY 0 +#define ITEM_WEIGHT_VOIDSUIT_ULTRALIGHT 0 +#define ITEM_WEIGHT_VOIDSUIT_HELMET_ULTRALIGHT 0 + +#define ITEM_WEIGHT_VOIDSUIT_ANOMALY 0 +#define ITEM_WEIGHT_VOIDSUIT_ANOMALY_HELMET 0 + +#define ITEM_WEIGHT_LEGACY_RIG_LIGHT 0 +#define ITEM_WEIGHT_LEGACY_RIG 0 +#define ITEM_WEIGHT_LEGACY_RIG_HEAVY 0 + +#define ITEM_WEIGHT_EMERGENCY_SOFTSUIT 0 +#define ITEM_WEIGHT_EMERGENCY_SOFTSUIT_HELMET 0 + +//* Species + +#define ITEM_WEIGHT_TAJARAN_SWORDSMAN_ARMOR 0 +#define ITEM_WEIGHT_PHORONOID_SUIT 0 +#define ITEM_WEIGHT_PHORONOID_HELMET 0 + +//* Storage + +#define ITEM_WEIGHT_STORAGE_DUFFLEBAG 0 +#define ITEM_WEIGHT_STORAGE_BACKPACK 0 +#define ITEM_WEIGHT_STORAGE_POUCH_LARGE 0 + +//* Tools + +#define ITEM_WEIGHT_HYBRID_TOOLS 0 + +//* Weapons + +#define ITEM_WEIGHT_GUN_LIGHT 0 +#define ITEM_WEIGHT_GUN_NORMAL 0 +#define ITEM_WEIGHT_GUN_LARGE 0 +#define ITEM_WEIGHT_GUN_BULKY 0 +#define ITEM_WEIGHT_GUN_UNREASONABLE 0 +#define ITEM_WEIGHT_GUN_RIDICULOUS 0 +#define ITEM_WEIGHT_GUN_VEHICLE 0 + +#define ITEM_WEIGHT_MELEE_SPEAR 0 + +//* Antags + +#define ITEM_WEIGHT_CHANGELING_ARMOR 0 +#define ITEM_WEIGHT_CULT_VOIDSUIT_HELMET 0 +#define ITEM_WEIGHT_CULT_VOIDSUIT 0 +#define ITEM_WEIGHT_TECHNOMANCER_BULKY_CORE 0 diff --git a/code/__DEFINES/items_clothing.dm b/code/__DEFINES/items_clothing.dm index 4053ccf656bb..6c463461f061 100644 --- a/code/__DEFINES/items_clothing.dm +++ b/code/__DEFINES/items_clothing.dm @@ -1,6 +1,4 @@ -/// How much shoes slow you down by default. Negative values speed you up. -#define SHOES_SLOWDOWN 0 /// For how bright candles are. #define CANDLE_LUM 3 diff --git a/code/__DEFINES/movespeed_modification.dm b/code/__DEFINES/movespeed_modification.dm index 452b9fc97855..4a16ca58bfaf 100644 --- a/code/__DEFINES/movespeed_modification.dm +++ b/code/__DEFINES/movespeed_modification.dm @@ -1,8 +1,52 @@ -//! movespeed_modifier_flags +//* movespeed_modifier_flags // None yet -//! Conflicts IDs +//* calculation_type + +/// just use multiplicative_slowdown +#define MOVESPEED_CALCULATION_HYPERBOLIC "hyperbolic" +/// use multiplicative_slowdown and TILE_BOOST calculations +#define MOVESPEED_CALCULATION_HYPERBOLIC_BOOST "hyperbolic_boost" +/// use % change and TILE_BOOST calculations +#define MOVESPEED_CALCULATION_MULTIPLY "multiply" +/// legacy multiply +//! TODO: REMOVE THIS SHIT +#define MOVESPEED_CALCULATION_LEGACY_MULTIPLY "legacy_multiply" + +DEFINE_ENUM(movespeed_modifier_calculation_type, list( + /datum/movespeed_modifier = list( + "calculation_type", + ), +), list( + ENUM("Hyperbolic", MOVESPEED_CALCULATION_HYPERBOLIC), + ENUM("Hyperbolic w/ Limit", MOVESPEED_CALCULATION_HYPERBOLIC_BOOST), + ENUM("Multiply", MOVESPEED_CALCULATION_MULTIPLY), + ENUM("Legacy Multiply", MOVESPEED_CALCULATION_LEGACY_MULTIPLY), +)) + +//* params for add_or_update_variable_movespeed_modifier + +/// multiplicative_slowdown +#define MOVESPEED_PARAM_DELAY_MOD "delay" +/// multiply_speed +#define MOVESPEED_PARAM_MULTIPLY_SPEED "multiply" +/// absolute_max_tiles_per_second +#define MOVESPEED_PARAM_MAX_TILE_ABSOLUTE "absolute_tiles" +/// max_tiles_per_second_boost +#define MOVESPEED_PARAM_MAX_TILE_BOOST "max_tlies" + +//* Constants + +/// minimum movespeed +#define MOVESPEED_ABSOLUTE_MINIMUM_TILES_PER_SECOND 0.25 + +//* Priorities - Lower is applied first + +#define MOVESPEED_PRIORITY_DEFAULT 0 +#define MOVESPEED_PRIORITY_CARRY_WEIGHT 10 + +//* Conflicts IDs // None yet -//! IDs +//* IDs // None yet diff --git a/code/__DEFINES/tgui.dm b/code/__DEFINES/tgui.dm index bdc4055e5556..a3eaf187df97 100644 --- a/code/__DEFINES/tgui.dm +++ b/code/__DEFINES/tgui.dm @@ -1,4 +1,4 @@ -// ui_status +//* ui_status /// Green eye; fully interactive #define UI_INTERACTIVE 2 /// Orange eye; updates but is not interactive @@ -8,7 +8,7 @@ /// UI Should close #define UI_CLOSE -1 -// refreshing var +//* refreshing var /// no refresh queued #define UI_NOT_REFRESHING 0 /// soft refreshing - can show a status, won't block viewport @@ -46,6 +46,7 @@ "%7b%22type%22%3a%22[type]%22%2c%22payload%22%3a[url_encode(json_encode(payload))]%7d" \ ) +//* Legacy Modal Stuff /// Max length for Modal Input #define UI_MODAL_INPUT_MAX_LENGTH 1024 @@ -56,3 +57,21 @@ #define UI_MODAL_DELEGATE 2 #define UI_MODAL_ANSWER 3 #define UI_MODAL_CLOSE 4 + +//* tgui dynamic input +//* all constraints must be specified if it is included. + +#define TGUI_INPUT_DATA_TYPE "type" +#define TGUI_INPUT_DATA_DESC "desc" +#define TGUI_INPUT_DATA_NAME "name" +#define TGUI_INPUT_DATA_CONSTRAINTS "constraints" +#define TGUI_INPUT_DATA_DEFAULT "default" + +/// constraints: [maxlength] +#define TGUI_INPUT_DATATYPE_TEXT "text" +/// constraints: [min, max, round] +#define TGUI_INPUT_DATATYPE_NUM "num" +/// constraints (required): [str1, str2, ...] +#define TGUI_INPUT_DATATYPE_LIST_PICK "list_single" +/// constraints: nothing +#define TGUI_INPUT_DATATYPE_TOGGLE "bool" diff --git a/code/__DEFINES/vv.dm b/code/__DEFINES/vv.dm index c911c5e2b3ed..74f97ebc4be1 100644 --- a/code/__DEFINES/vv.dm +++ b/code/__DEFINES/vv.dm @@ -96,6 +96,10 @@ #define VV_HK_EDIT_COLOR_MATRIX "edit_color_matrix" #define VV_HK_EDIT_ARMOR "edit_armor" +// /mob +#define VV_HK_ADD_PHYSIOLOGY_MODIFIER "add_physiology_mod" +#define VV_HK_REMOVE_PHYSIOLOGY_MODIFIER "remove_physiology_mod" + /* // /obj #define VV_HK_OSAY "osay" diff --git a/code/datums/status_effects/grouped/staggered.dm b/code/datums/status_effects/grouped/staggered.dm index 88e17df556ea..0d082c8b393f 100644 --- a/code/datums/status_effects/grouped/staggered.dm +++ b/code/datums/status_effects/grouped/staggered.dm @@ -15,7 +15,9 @@ if(applied_highest == highest) return applied_highest = highest - owner.add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/mob_staggered, multiplicative_slowdown = highest) + owner.add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/mob_staggered, params = list( + MOVESPEED_PARAM_DELAY_MOD = highest + )) /datum/status_effect/grouped/staggered/on_remove() . = ..() diff --git a/code/game/gamemodes/changeling/powers/armor.dm b/code/game/gamemodes/changeling/powers/armor.dm index 4d3753a5f2b0..fec2083c9f33 100644 --- a/code/game/gamemodes/changeling/powers/armor.dm +++ b/code/game/gamemodes/changeling/powers/armor.dm @@ -64,11 +64,8 @@ action_button_name = "Toggle Grippers" clothing_flags = NONE item_flags = ITEM_DROPDEL - -/obj/item/clothing/shoes/magboots/changeling/set_slowdown() - slowdown = worn_over? max(SHOES_SLOWDOWN, worn_over.slowdown): SHOES_SLOWDOWN //So you can't put on magboots to make you walk faster. - if (magpulse) - slowdown += 1 //It's already tied to a slowdown suit, 6 slowdown is huge. + encumbrance = ITEM_ENCUMBRANCE_CHANGELING_MAGBOOTS + encumbrance_on = ITEM_ENCUMBRANCE_CHANGELING_MAGBOOTS_PULSE /obj/item/clothing/shoes/magboots/changeling/attack_self(mob/user) . = ..() @@ -97,7 +94,7 @@ armor_type = /datum/armor/changeling/chitin siemens_coefficient = 0.3 max_heat_protection_temperature = FIRESUIT_MAX_HEAT_PROTECTION_TEMPERATURE - slowdown = 3 + weight = ITEM_WEIGHT_CHANGELING_ARMOR /obj/item/clothing/suit/space/changeling/armored/Initialize(mapload) . = ..() diff --git a/code/game/gamemodes/cult/cult_items.dm b/code/game/gamemodes/cult/cult_items.dm index 7910cef20798..ef9ea2a2578e 100644 --- a/code/game/gamemodes/cult/cult_items.dm +++ b/code/game/gamemodes/cult/cult_items.dm @@ -118,6 +118,8 @@ icon_state = "culthelm" origin_tech = list(TECH_MATERIAL = 3, TECH_ARCANE = 1) armor_type = /datum/armor/cult/space + encumbrance = ITEM_ENCUMBRANCE_CULT_VOIDSUIT_HELMET + weight = ITEM_WEIGHT_CULT_VOIDSUIT_HELMET siemens_coefficient = 0 worn_render_flags = WORN_RENDER_SLOT_ONE_FOR_ALL @@ -132,7 +134,8 @@ desc = "A bulky suit of armour, bristling with spikes. It looks space-worthy." w_class = ITEMSIZE_NORMAL allowed = list(/obj/item/book/tome,/obj/item/melee/cultblade,/obj/item/tank/emergency/oxygen,/obj/item/suit_cooling_unit) - slowdown = 1 + weight = ITEM_WEIGHT_CULT_VOIDSUIT + encumbrance = ITEM_ENCUMBRANCE_CULT_VOIDSUIT armor_type = /datum/armor/cult/space siemens_coefficient = 0 inv_hide_flags = HIDEGLOVES|HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER diff --git a/code/game/gamemodes/technomancer/core_obj.dm b/code/game/gamemodes/technomancer/core_obj.dm index 3fae544560f0..969012419559 100644 --- a/code/game/gamemodes/technomancer/core_obj.dm +++ b/code/game/gamemodes/technomancer/core_obj.dm @@ -262,7 +262,7 @@ energy = 20000 max_energy = 20000 regen_rate = 25 //800 seconds to full - slowdown = 1 + weight = ITEM_WEIGHT_TECHNOMANCER_BULKY_CORE instability_modifier = 1.0 spell_power_modifier = 1.4 diff --git a/code/game/gamemodes/technomancer/devices/shield_armor.dm b/code/game/gamemodes/technomancer/devices/shield_armor.dm index 273428c41735..9317fb7f230f 100644 --- a/code/game/gamemodes/technomancer/devices/shield_armor.dm +++ b/code/game/gamemodes/technomancer/devices/shield_armor.dm @@ -16,7 +16,7 @@ require a very potent supply of an energy of some kind in order to function." icon_state = "shield_armor_0" blood_overlay_type = "armor" - slowdown = 0 + weight = ITEM_WEIGHT_BASELINE armor_type = /datum/armor/none action_button_name = "Toggle Shield Projector" var/active = 0 diff --git a/code/game/gamemodes/technomancer/devices/tesla_armor.dm b/code/game/gamemodes/technomancer/devices/tesla_armor.dm index 03668e4990e0..534079ef42b2 100644 --- a/code/game/gamemodes/technomancer/devices/tesla_armor.dm +++ b/code/game/gamemodes/technomancer/devices/tesla_armor.dm @@ -12,7 +12,7 @@ desc = "This rather dangerous looking armor will hopefully shock your enemies, and not you in the process." icon_state = "tesla_armor_1" //wip blood_overlay_type = "armor" - slowdown = 1 + weight = ITEM_WEIGHT_BASELINE armor_type = /datum/armor/none action_button_name = "Toggle Tesla Armor" var/active = 1 //Determines if the armor will zap or block diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm index ecf0da767c20..e232a0c21a10 100644 --- a/code/game/objects/items.dm +++ b/code/game/objects/items.dm @@ -11,7 +11,7 @@ //? Flags /// Item flags. /// These flags are listed in [code/__DEFINES/inventory/item_flags.dm]. - var/item_flags = NONE + var/item_flags = ITEM_ENCUMBERS_WHILE_HELD /// Miscellaneous flags pertaining to equippable objects. /// These flags are listed in [code/__DEFINES/inventory/item_flags.dm]. var/clothing_flags = NONE @@ -36,6 +36,25 @@ /// economic category for items var/economic_category_item = ECONOMIC_CATEGORY_ITEM_DEFAULT + //? Carry Weight + /// encumberance. + /// calculated as max() of all encumbrance + /// result is calculated into slowdown value + /// and then max()'d with carry weight for the final slowdown used. + var/encumbrance = ITEM_ENCUMBRANCE_BASELINE + /// registered encumbrance - null if not in inventory + var/encumbrance_registered + /// carry weight in kgs. this might be generalized later so KEEP IT REALISTIC. + var/weight = ITEM_WEIGHT_BASELINE + /// registered carry weight - null if not in inventory. + var/weight_registered + /// flat encumbrance - while worn, you are treated as at **least** this encumbered + /// e.g. if someone is wearing a flat 50 encumbrance item, but their regular encumbrance tally is only 45, they still have 50 total. + var/flat_encumbrance = 0 + /// Hard slowdown. Applied before carry weight. + /// This affects multiplicative movespeed. + var/slowdown = 0 + //? Combat /// Amount of damage we do on melee. var/damage_force = 0 @@ -99,8 +118,6 @@ var/permeability_coefficient = 1 /// For electrical admittance/conductance (electrocution checks and shit) var/siemens_coefficient = 1 - /// How much clothing is slowing you down. Negative values speeds you up - var/slowdown = 0 /// Suit storage stuff. var/list/allowed = null /// All items can have an uplink hidden inside, just remember to add the triggers. @@ -239,6 +256,40 @@ /obj/item/examine(mob/user, dist) . = ..() . += "[gender == PLURAL ? "They are" : "It is"] a [weightclass2text(w_class)] item." + switch(get_encumbrance()) + if(-INFINITY to 0.1) + . += "It looks effortless to carry around and wear." + if(0.1 to 0.75) + . += "It looks very easy to carry around and wear." + if(0.75 to 2) + . += "It looks decently able to be carried around and worn." + if(2 to 5) + . += "It looks somewhat unwieldly." + if(5 to 10) + . += "It looks quite unwieldly." + if(10 to 20) + . += "It looks very unwieldly. It would take a good effort to run around with it." + if(20 to 40) + . += "It looks extremely unwieldly. You probably will have a hard time running with it." + if(40 to INFINITY) + . += "It's so unwieldly that it's a surprise you can hold it at all. You really won't be doing much running with it." + switch(get_weight()) + if(-INFINITY to 0.1) + . += "It looks like it weighs practically nothing." + if(0.1 to 0.75) + . += "It looks like it weighs very little." + if(0.75 to 2) + . += "It looks like it's decently lightweight." + if(2 to 5) + . += "It looks like it weighs a bit." + if(5 to 10) + . += "It looks like it weighs a good amount." + if(10 to 20) + . += "It looks like it is heavy. It would take a good effort to run around with it." + if(20 to 40) + . += "It looks like it weighs a lot. You probably will have a hard time running with it." + if(40 to INFINITY) + . += "It looks like it weighs a ton. You really won't be doing much running with it." // if(resistance_flags & INDESTRUCTIBLE) // . += "[src] seems extremely robust! It'll probably withstand anything that could happen to it!" @@ -753,6 +804,81 @@ modules/mob/living/carbon/human/life.dm if you die, you will be zoomed out. // . = ..() // update_action_buttons() +//? Carry Weight + +/obj/item/proc/get_weight() + return weight + +/obj/item/proc/get_encumbrance() + return encumbrance + +/obj/item/proc/get_flat_encumbrance() + return flat_encumbrance + +/obj/item/proc/update_weight() + if(isnull(weight_registered)) + return null + . = get_weight() + if(. == weight_registered) + return 0 + . -= weight_registered + var/mob/living/wearer = worn_mob() + if(istype(wearer)) + wearer.adjust_current_carry_weight(.) + +/obj/item/proc/update_encumbrance() + if(isnull(encumbrance_registered)) + return null + . = get_encumbrance() + if(. == encumbrance_registered) + return 0 + . -= encumbrance_registered + encumbrance_registered += . + var/mob/living/wearer = worn_mob() + if(istype(wearer)) + wearer.adjust_current_carry_encumbrance(.) + +/obj/item/proc/update_flat_encumbrance() + var/mob/living/wearer = worn_mob() + if(istype(wearer)) + wearer.recalculate_carry() + +/obj/item/proc/set_weight(amount) + if(amount == weight) + return + var/old = weight + weight = amount + update_weight() + propagate_weight(old, weight) + +/obj/item/proc/set_encumbrance(amount) + if(amount == encumbrance) + return + encumbrance = amount + update_encumbrance() + +/obj/item/proc/set_flat_encumbrance(amount) + if(amount == flat_encumbrance) + return + flat_encumbrance = amount + update_flat_encumbrance() + +/obj/item/proc/set_slowdown(amount) + if(amount == slowdown) + return + slowdown = amount + worn_mob()?.update_item_slowdown() + +/obj/item/proc/propagate_weight(old_weight, new_weight) + if(!(item_flags & ITEM_IN_STORAGE)) + return + var/obj/item/storage/S = loc + if(!istype(S)) + return + S.stored_weight_changed(src, old_weight, new_weight) + +//? Attack Verbs + /** * grabs an attack verb to use * @@ -829,3 +955,34 @@ modules/mob/living/carbon/human/life.dm if you die, you will be zoomed out. /obj/item/proc/running_mob_armor(damage, tier, flag, mode, attack_type, datum/weapon, target_zone) damage = fetch_armor().resultant_damage(damage, tier, flag) return args.Copy() + +//? VV + +/obj/item/vv_edit_var(var_name, var_value, mass_edit, raw_edit) + switch(var_name) + if(NAMEOF(src, item_flags)) + var/requires_update = (item_flags & (ITEM_ENCUMBERS_WHILE_HELD | ITEM_ENCUMBERS_ONLY_HELD)) != (var_value & (ITEM_ENCUMBERS_WHILE_HELD | ITEM_ENCUMBERS_ONLY_HELD)) + . = ..() + if(. && requires_update) + var/mob/living/L = worn_mob() + // check, as worn_mob() returns /mob, not /living + if(istype(L)) + L.recalculate_carry() + L.update_carry() + if(NAMEOF(src, weight), NAMEOF(src, encumbrance), NAMEOF(src, flat_encumbrance)) + // todo: introspection system update - this should be 'handled', as opposed to hooked. + . = ..() + if(. ) + var/mob/living/L = worn_mob() + // check, as worn_mob() returns /mob, not /living + if(istype(L)) + L.update_carry_slowdown() + if(NAMEOF(src, slowdown)) + . = ..() + if(. ) + var/mob/living/L = worn_mob() + // check, as worn_mob() returns /mob, not /living + if(istype(L)) + L.update_item_slowdown() + else + return ..() diff --git a/code/game/objects/items/bodybag.dm b/code/game/objects/items/bodybag.dm index 049c28f77898..a1c7f27e5480 100644 --- a/code/game/objects/items/bodybag.dm +++ b/code/game/objects/items/bodybag.dm @@ -7,14 +7,20 @@ icon_state = "bodybag_folded" w_class = ITEMSIZE_SMALL + var/bag_type = /obj/structure/closet/body_bag + /obj/item/bodybag/attack_self(mob/user) . = ..() if(.) return - var/obj/structure/closet/body_bag/R = new /obj/structure/closet/body_bag(user.loc) - R.add_fingerprint(user) + add_fingerprint(user) + create_bag(user.drop_location()) qdel(src) +/obj/item/bodybag/proc/create_bag(atom/where) + var/obj/structure/closet/body_bag/bag = new bag_type(where) + transfer_fingerprints_to(bag) + return bag /obj/item/storage/box/bodybags name = "body bags" @@ -31,7 +37,6 @@ new /obj/item/bodybag(src) new /obj/item/bodybag(src) - /obj/structure/closet/body_bag name = "body bag" desc = "A plastic bag designed for the storage and transportation of cadavers." @@ -127,18 +132,17 @@ icon_state = "bodybag_folded" item_state = "bodybag_cryo_folded" origin_tech = list(TECH_BIO = 4) + var/obj/item/reagent_containers/syringe/syringe -/obj/item/bodybag/cryobag/attack_self(mob/user) - . = ..() - if(.) +/obj/item/bodybag/cryobag/create_bag(atom/where) + var/obj/structure/closet/body_bag/cryobag/bag = ..() + if(!istype(bag)) return - var/obj/structure/closet/body_bag/cryobag/R = new /obj/structure/closet/body_bag/cryobag(user.loc) - R.add_fingerprint(user) - if(syringe) - R.syringe = syringe + if(!isnull(syringe)) + bag.syringe = syringe syringe = null - qdel(src) + return bag /obj/structure/closet/body_bag/cryobag name = "stasis bag" @@ -148,7 +152,6 @@ item_path = /obj/item/bodybag/cryobag store_misc = 0 store_items = 0 - var/used = 0 var/obj/item/tank/tank = null var/tank_type = /obj/item/tank/stasis/oxygen var/stasis_level = 3 //Every 'this' life ticks are applied to the mob (when life_ticks%stasis_level == 1) @@ -163,24 +166,6 @@ QDEL_NULL(tank) return ..() -/obj/structure/closet/body_bag/cryobag/attack_hand(mob/user, list/params) - if(used) - var/confirm = tgui_alert(user, "Are you sure you want to open \the [src]? \The [src] will expire upon opening it.", "Confirm Opening", list("No", "Yes")) - if(confirm == "Yes") - ..() // Will call `toggle()` and open the bag. - else - ..() - -/obj/structure/closet/body_bag/cryobag/open() - . = ..() - if(used) - var/obj/item/O = new/obj/item(src.loc) - O.name = "used [name]" - O.icon = src.icon - O.icon_state = "bodybag_used" - O.desc = "Pretty useless now..." - qdel(src) - /obj/structure/closet/body_bag/cryobag/OnMouseDropLegacy(over_object, src_location, over_location) . = ..() if(. && syringe) @@ -192,7 +177,6 @@ if(ishuman(AM)) var/mob/living/carbon/human/H = AM H.Stasis(stasis_level) - src.used = 1 inject_occupant(H) if(istype(AM, /obj/item/organ)) @@ -256,12 +240,9 @@ else if(W.is_screwdriver()) if(syringe) - if(used) - to_chat(user,"The injector cannot be removed now that the stasis bag has been used!") - else - syringe.forceMove(src.loc) - to_chat(user,"You pry \the [syringe] out of \the [src].") - syringe = null + syringe.forceMove(src.loc) + to_chat(user,"You pry \the [syringe] out of \the [src].") + syringe = null else ..() diff --git a/code/game/objects/items/devices/body_snatcher_vr.dm b/code/game/objects/items/devices/body_snatcher_vr.dm index a89be30cd710..1d90d5dea57b 100644 --- a/code/game/objects/items/devices/body_snatcher_vr.dm +++ b/code/game/objects/items/devices/body_snatcher_vr.dm @@ -5,7 +5,7 @@ icon = 'icons/obj/device_alt.dmi' icon_state = "sleevemate" //Give this a fancier sprite later. item_state = "healthanalyzer" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_BELT w_class = ITEMSIZE_SMALL materials = list(MAT_STEEL = 200) diff --git a/code/game/objects/items/devices/communicator/communicator.dm b/code/game/objects/items/devices/communicator/communicator.dm index f1a4ea328e8e..fe74a7a448a4 100644 --- a/code/game/objects/items/devices/communicator/communicator.dm +++ b/code/game/objects/items/devices/communicator/communicator.dm @@ -351,7 +351,7 @@ var/global/list/obj/item/communicator/all_communicators = list() communications across different stations, planets, or even star systems. You can wear this one on your wrist!" icon = 'icons/obj/device.dmi' icon_state = "commwatch" - item_flags = CLOTHING_ALLOW_SINGLE_LIMB + item_flags = CLOTHING_ALLOW_SINGLE_LIMB | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_GLOVES /obj/item/communicator/watch/update_icon_state() diff --git a/code/game/objects/items/devices/holowarrant.dm b/code/game/objects/items/devices/holowarrant.dm index d4caf4057537..3713cbfcc7fc 100644 --- a/code/game/objects/items/devices/holowarrant.dm +++ b/code/game/objects/items/devices/holowarrant.dm @@ -4,7 +4,7 @@ desc = "The practical paperwork replacement for the officer on the go." icon_state = "holowarrant" item_state = "flashtool" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD throw_force = 5 w_class = ITEMSIZE_SMALL throw_speed = 4 diff --git a/code/game/objects/items/glassjar.dm b/code/game/objects/items/glassjar.dm index 5b5e9ca52c11..7b2eb3d858a3 100644 --- a/code/game/objects/items/glassjar.dm +++ b/code/game/objects/items/glassjar.dm @@ -5,7 +5,7 @@ icon_state = "jar" w_class = ITEMSIZE_SMALL materials = list(MAT_GLASS = 200) - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/list/accept_mobs = list(/mob/living/simple_mob/animal/passive/lizard, /mob/living/simple_mob/animal/passive/mouse, /mob/living/simple_mob/animal/sif/leech, /mob/living/simple_mob/animal/sif/frostfly, /mob/living/simple_mob/animal/sif/glitterfly) var/contains = 0 // 0 = nothing, 1 = money, 2 = animal, 3 = spiderling drop_sound = 'sound/items/drop/glass.ogg' diff --git a/code/game/objects/items/holosign_creator.dm b/code/game/objects/items/holosign_creator.dm index 12c53c4f2d8a..74fb53fece44 100644 --- a/code/game/objects/items/holosign_creator.dm +++ b/code/game/objects/items/holosign_creator.dm @@ -9,7 +9,7 @@ throw_force = 0 throw_speed = 3 throw_range = 7 - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/list/signs = list() var/max_signs = 10 var/creation_time = 0 //time to create a holosign in deciseconds. diff --git a/code/game/objects/items/offhand.dm b/code/game/objects/items/offhand.dm index 2cd8c8eec887..e19c0fa67f0a 100644 --- a/code/game/objects/items/offhand.dm +++ b/code/game/objects/items/offhand.dm @@ -6,7 +6,7 @@ /obj/item/offhand name = "broken offhand" desc = "fire coderbus" - item_flags = ITEM_DROPDEL | ITEM_ABSTRACT | ITEM_NOBLUDGEON + item_flags = ITEM_DROPDEL | ITEM_ABSTRACT | ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD icon = 'icons/obj/item/abstract.dmi' icon_state = "offhand" drop_sound = null diff --git a/code/game/objects/items/robobag.dm b/code/game/objects/items/robobag.dm index 6b67f589540e..c6de643dd277 100644 --- a/code/game/objects/items/robobag.dm +++ b/code/game/objects/items/robobag.dm @@ -7,17 +7,7 @@ icon_state = "bodybag_folded" item_state = "bodybag_cryo_folded" origin_tech = list(TECH_ENGINEERING = 3) - -/obj/item/bodybag/cryobag/robobag/attack_self(mob/user) - . = ..() - if(.) - return - var/obj/structure/closet/body_bag/cryobag/robobag/R = new /obj/structure/closet/body_bag/cryobag/robobag(user.loc) - R.add_fingerprint(user) - if(syringe) - R.syringe = syringe - syringe = null - qdel(src) + bag_type = /obj/structure/closet/body_bag/cryobag/robobag /obj/structure/closet/body_bag/cryobag/robobag name = "synthmorph bag" @@ -76,10 +66,7 @@ if(ishuman(AM)) var/mob/living/carbon/human/H = AM if(H.isSynthetic()) - if(H.getToxLoss() == 0) // We don't exactly care about the bag being 'used' when containing a synth, unless it's got work. - used = FALSE - else - H.add_modifier(/datum/modifier/fbp_debug/robobag) + H.add_modifier(/datum/modifier/fbp_debug/robobag) /obj/structure/closet/body_bag/cryobag/robobag/attackby(obj/item/W, mob/user) if(opened) diff --git a/code/game/objects/items/robot/gripper.dm b/code/game/objects/items/robot/gripper.dm index e3a3e6c5e392..804f19880000 100644 --- a/code/game/objects/items/robot/gripper.dm +++ b/code/game/objects/items/robot/gripper.dm @@ -7,7 +7,7 @@ Using an object on the gripper will interact with the item inside it, if it exists, instead." icon = 'icons/obj/device.dmi' icon_state = "gripper" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD //Has a list of items that it can hold. var/list/can_hold = list( diff --git a/code/game/objects/items/stacks/sheets/leather.dm b/code/game/objects/items/stacks/sheets/leather.dm index 4622ff7543b0..61d6a5f4077c 100644 --- a/code/game/objects/items/stacks/sheets/leather.dm +++ b/code/game/objects/items/stacks/sheets/leather.dm @@ -140,7 +140,6 @@ desc = "Pieces of a goliath's rocky hide, these might be able to make your suit a bit more durable to attack from the local fauna." icon_state = "sheet-goliath_hide" singular_name = "hide plate" - item_flags = ITEM_NOBLUDGEON w_class = WEIGHT_CLASS_NORMAL layer = MOB_LAYER @@ -164,7 +163,6 @@ icon_state = "sheet-dragon_hide" singular_name = "drake plate" max_amount = 10 - item_flags = ITEM_NOBLUDGEON w_class = WEIGHT_CLASS_NORMAL layer = MOB_LAYER diff --git a/code/game/objects/items/stock_parts/_stock_parts.dm b/code/game/objects/items/stock_parts/_stock_parts.dm index 5a275cdef4de..f09075921157 100644 --- a/code/game/objects/items/stock_parts/_stock_parts.dm +++ b/code/game/objects/items/stock_parts/_stock_parts.dm @@ -4,7 +4,7 @@ gender = PLURAL icon = 'icons/obj/stock_parts.dmi' w_class = ITEMSIZE_SMALL - item_flags = ITEM_EASY_LATHE_DECONSTRUCT + item_flags = ITEM_EASY_LATHE_DECONSTRUCT | ITEM_ENCUMBERS_WHILE_HELD var/rating = 1 /obj/item/stock_parts/Initialize(mapload) diff --git a/code/game/objects/items/storage/_storage.dm b/code/game/objects/items/storage/_storage.dm index 811c90be8cb8..2dbda152e487 100644 --- a/code/game/objects/items/storage/_storage.dm +++ b/code/game/objects/items/storage/_storage.dm @@ -38,6 +38,73 @@ var/last_message = 0 + /// carry weight in us + var/weight_cached = 0 + /// carry weight mitigation, static. applied after multiplicative + var/weight_mitigation = 0 + /// carry weight mitigation, multiplicative. + var/weight_multiply = 1 + +/obj/item/storage/Initialize(mapload) + . = ..() + + if(allow_quick_empty) + add_obj_verb(src, /obj/item/storage/verb/quick_empty) + else + remove_obj_verb(src, /obj/item/storage/verb/quick_empty) + + if(allow_quick_gather) + add_obj_verb(src, /obj/item/storage/verb/toggle_gathering_mode) + else + remove_obj_verb(src, /obj/item/storage/verb/toggle_gathering_mode) + + src.boxes = new /atom/movable/screen/storage( ) + src.boxes.name = "storage" + src.boxes.master = src + src.boxes.icon_state = "block" + src.boxes.screen_loc = storage_ui_default + + src.storage_start = new /atom/movable/screen/storage( ) + src.storage_start.name = "storage" + src.storage_start.master = src + src.storage_start.icon_state = "storage_start" + src.storage_start.screen_loc = storage_ui_default + + src.storage_continue = new /atom/movable/screen/storage( ) + src.storage_continue.name = "storage" + src.storage_continue.master = src + src.storage_continue.icon_state = "storage_continue" + src.storage_continue.screen_loc = storage_ui_default + + src.storage_end = new /atom/movable/screen/storage( ) + src.storage_end.name = "storage" + src.storage_end.master = src + src.storage_end.icon_state = "storage_end" + src.storage_end.screen_loc = storage_ui_default + + src.stored_start = new /atom/movable //we just need these to hold the icon + src.stored_start.icon_state = "stored_start" + + src.stored_continue = new /atom/movable + src.stored_continue.icon_state = "stored_continue" + + src.stored_end = new /atom/movable + src.stored_end.icon_state = "stored_end" + + src.closer = new /atom/movable/screen/close( ) + src.closer.master = src + src.closer.icon_state = "storage_close" + src.closer.hud_layerise() + orient2hud() + + populate_contents_legacy() + + PopulateContents() + + //calibrate_size() //Let's not! + + reset_weight() + /obj/item/storage/Destroy() close_all() QDEL_NULL(boxes) @@ -50,7 +117,34 @@ QDEL_NULL(closer) return ..() +/obj/item/storage/get_weight() + . = ..() + . += max(0, (weight_cached * weight_multiply) - weight_mitigation) +/obj/item/storage/proc/reset_weight() + var/old_weight_cached = weight_cached + weight_cached = 0 + for(var/obj/item/I in contents) + weight_cached += I.get_weight() + propagate_weight(old_weight_cached, weight_cached) + update_weight() + +/obj/item/storage/proc/stored_weight_changed(obj/item/I, old_weight, new_weight) + var/diff = new_weight - old_weight + var/old = weight_cached + weight_cached += diff + propagate_weight(old, weight_cached) + update_weight() + +/obj/item/storage/proc/reset_weight_recursive() + do_reset_weight_recursive(200) + +/obj/item/storage/proc/do_reset_weight_recursive(safety) + if(!(safety - 1)) + CRASH("out of safety") + for(var/obj/item/storage/S in contents) + S.do_reset_weight_recursive(safety - 1) + reset_weight() /obj/item/storage/AltClick(mob/user) if(user in is_seeing) @@ -359,6 +453,9 @@ W.forceMove(src) W.on_enter_storage(src) W.item_flags |= ITEM_IN_STORAGE + var/old_weight = weight_cached + weight_cached += W.get_weight() + propagate_weight(old_weight, weight_cached) if(user) if(!prevent_warning) for(var/mob/M in viewers(user)) @@ -407,6 +504,9 @@ W.maptext = "" W.on_exit_storage(src) W.item_flags &= ~ITEM_IN_STORAGE + var/old_weight = weight_cached + weight_cached -= W.get_weight() + propagate_weight(old_weight, weight_cached) update_icon() return 1 @@ -518,64 +618,6 @@ for(var/obj/item/I in contents) remove_from_storage(I, T) -/obj/item/storage/Initialize(mapload) - . = ..() - - if(allow_quick_empty) - add_obj_verb(src, /obj/item/storage/verb/quick_empty) - else - remove_obj_verb(src, /obj/item/storage/verb/quick_empty) - - if(allow_quick_gather) - add_obj_verb(src, /obj/item/storage/verb/toggle_gathering_mode) - else - remove_obj_verb(src, /obj/item/storage/verb/toggle_gathering_mode) - - src.boxes = new /atom/movable/screen/storage( ) - src.boxes.name = "storage" - src.boxes.master = src - src.boxes.icon_state = "block" - src.boxes.screen_loc = storage_ui_default - - src.storage_start = new /atom/movable/screen/storage( ) - src.storage_start.name = "storage" - src.storage_start.master = src - src.storage_start.icon_state = "storage_start" - src.storage_start.screen_loc = storage_ui_default - - src.storage_continue = new /atom/movable/screen/storage( ) - src.storage_continue.name = "storage" - src.storage_continue.master = src - src.storage_continue.icon_state = "storage_continue" - src.storage_continue.screen_loc = storage_ui_default - - src.storage_end = new /atom/movable/screen/storage( ) - src.storage_end.name = "storage" - src.storage_end.master = src - src.storage_end.icon_state = "storage_end" - src.storage_end.screen_loc = storage_ui_default - - src.stored_start = new /atom/movable //we just need these to hold the icon - src.stored_start.icon_state = "stored_start" - - src.stored_continue = new /atom/movable - src.stored_continue.icon_state = "stored_continue" - - src.stored_end = new /atom/movable - src.stored_end.icon_state = "stored_end" - - src.closer = new /atom/movable/screen/close( ) - src.closer.master = src - src.closer.icon_state = "storage_close" - src.closer.hud_layerise() - orient2hud() - - populate_contents_legacy() - - PopulateContents() - - //calibrate_size() //Let's not! - /obj/item/storage/proc/populate_contents_legacy() if(LAZYLEN(starts_with) && !empty) for(var/newtype in starts_with) diff --git a/code/game/objects/items/storage/backpack.dm b/code/game/objects/items/storage/backpack.dm index 6501a2467937..41956980ca93 100644 --- a/code/game/objects/items/storage/backpack.dm +++ b/code/game/objects/items/storage/backpack.dm @@ -10,6 +10,8 @@ w_class = ITEMSIZE_LARGE slot_flags = SLOT_BACK max_w_class = ITEMSIZE_LARGE + weight = ITEM_WEIGHT_STORAGE_BACKPACK + encumbrance = ITEM_ENCUMBRANCE_STORAGE_BACKPACK max_storage_space = INVENTORY_STANDARD_SPACE var/flippable = 0 var/side = 0 //0 = right, 1 = left @@ -49,6 +51,8 @@ /obj/item/storage/backpack/holding/duffle name = "dufflebag of holding" icon_state = "holdingduffle" + encumbrance = ITEM_ENCUMBRANCE_STORAGE_DUFFLEBAG + weight = ITEM_WEIGHT_STORAGE_DUFFLEBAG /obj/item/storage/backpack/holding/attackby(obj/item/W as obj, mob/user as mob) if(istype(W, /obj/item/storage/backpack/holding)) @@ -163,7 +167,11 @@ desc = "A large dufflebag for holding extra things." icon_state = "duffle" item_state_slots = list(SLOT_ID_RIGHT_HAND = "duffle", SLOT_ID_LEFT_HAND = "duffle") - slowdown = 1 + weight = ITEM_WEIGHT_STORAGE_DUFFLEBAG + encumbrance = ITEM_ENCUMBRANCE_STORAGE_DUFFLEBAG + flat_encumbrance = ITEM_FLAT_ENCUMBRANCE_DUFFLEBAG + // todo: remove when weight system is used + slowdown = 0.25 max_storage_space = INVENTORY_DUFFLEBAG_SPACE /obj/item/storage/backpack/dufflebag/syndie @@ -171,7 +179,7 @@ desc = "A large dufflebag for holding extra tactical supplies. This one appears to be made out of lighter material than usual." icon_state = "duffle-syndie" item_state_slots = list(SLOT_ID_RIGHT_HAND = "duffle_syndie", SLOT_ID_LEFT_HAND = "duffle_syndie") - slowdown = 0 + weight = ITEM_WEIGHT_BASELINE /obj/item/storage/backpack/dufflebag/syndie/med name = "medical dufflebag" @@ -588,8 +596,8 @@ item_state = "saddlebag" icon_state = "saddlebag" var/icon_base = "saddlebag" + encumbrance = ITEM_ENCUMBRANCE_STORAGE_DUFFLEBAG max_storage_space = INVENTORY_DUFFLEBAG_SPACE //Saddlebags can hold more, like dufflebags - slowdown = 1 //And are slower, too...Unless you're a macro, that is. var/no_message = "You aren't the appropriate taur type to wear this!" /obj/item/storage/backpack/saddlebag_common/can_equip(mob/M, slot, mob/user, flags) @@ -600,59 +608,27 @@ var/datum/sprite_accessory/tail/taur/TT = H.tail_style if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/horse)) item_state = "[icon_base]_horse" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/wolf)) item_state = "[icon_base]_wolf" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/cow)) item_state = "[icon_base]_cow" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/lizard)) item_state = "[icon_base]_lizard" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/feline)) item_state = "[icon_base]_feline" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/drake)) item_state = "[icon_base]_drake" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/otie)) item_state = "[icon_base]_otie" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 if(istype(H) && istype(TT, /datum/sprite_accessory/tail/taur/deer)) item_state = "[icon_base]_deer" - if(H.size_multiplier >= RESIZE_BIG) //Are they a macro? - slowdown = 0 - else - slowdown = initial(slowdown) return 1 else to_chat(H, "[no_message]") @@ -676,7 +652,7 @@ icon_state = "taurvest" icon_base = "taurvest" max_storage_space = INVENTORY_STANDARD_SPACE - slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_STORAGE_BACKPACK /obj/item/storage/backpack/dufflebag/fluff //Black dufflebag without syndie buffs. name = "plain black dufflebag" diff --git a/code/game/objects/items/storage/bags.dm b/code/game/objects/items/storage/bags.dm index 0a86bd3e4385..da126f8105bd 100644 --- a/code/game/objects/items/storage/bags.dm +++ b/code/game/objects/items/storage/bags.dm @@ -386,7 +386,6 @@ desc = "A bag for storing pills, patches, bottles, and hypovials." max_storage_space = 200 w_class = ITEMSIZE_LARGE - slowdown = 1 can_hold = list( /obj/item/reagent_containers/pill, /obj/item/reagent_containers/glass/beaker, @@ -404,7 +403,6 @@ desc = "A bag for storing slime extracts, slime potions, monkey cubes, and beakers." max_storage_space = 200 w_class = ITEMSIZE_LARGE - slowdown = 1 can_hold = list( /obj/item/reagent_containers/glass/beaker, /obj/item/reagent_containers/food/snacks/monkeycube, diff --git a/code/game/objects/items/tools/screwdriver.dm b/code/game/objects/items/tools/screwdriver.dm index 2ab66c31d2d8..23677846cb63 100644 --- a/code/game/objects/items/tools/screwdriver.dm +++ b/code/game/objects/items/tools/screwdriver.dm @@ -113,15 +113,13 @@ icon_state = "hybscrewdriver" item_state = "screwdriver_black" origin_tech = list(TECH_MATERIAL = 3, TECH_ENGINEERING = 3) - slowdown = 0.1 + weight = ITEM_WEIGHT_HYBRID_TOOLS w_class = ITEMSIZE_NORMAL tool_sound = 'sound/effects/uncloak.ogg' tool_speed = 0.4 random_color = FALSE reach = 2 - - /obj/item/tool/screwdriver/cyborg name = "powered screwdriver" desc = "An electrical screwdriver, designed to be both precise and quick." diff --git a/code/game/objects/items/tools/weldingtool.dm b/code/game/objects/items/tools/weldingtool.dm index 56273803514e..d38cc6803c39 100644 --- a/code/game/objects/items/tools/weldingtool.dm +++ b/code/game/objects/items/tools/weldingtool.dm @@ -453,7 +453,7 @@ icon_state = "hybwelder" max_fuel = 80 eye_safety_modifier = -2 // Brighter than the sun. Literally, you can look at the sun with a welding mask of proper grade, this will burn through that. - slowdown = 0.1 + weight = ITEM_WEIGHT_HYBRID_TOOLS tool_speed = 0.25 w_class = ITEMSIZE_LARGE flame_intensity = 5 diff --git a/code/game/objects/items/tools/wirecutters.dm b/code/game/objects/items/tools/wirecutters.dm index f2c4f501d63a..aad6ae7ee72b 100644 --- a/code/game/objects/items/tools/wirecutters.dm +++ b/code/game/objects/items/tools/wirecutters.dm @@ -107,7 +107,7 @@ catalogue_data = list(/datum/category_item/catalogue/anomalous/precursor_a/alien_wirecutters) icon_state = "hybcutters" w_class = ITEMSIZE_NORMAL - slowdown = 0.1 + weight = ITEM_WEIGHT_HYBRID_TOOLS origin_tech = list(TECH_MATERIAL = 3, TECH_ENGINEERING = 3, TECH_PHORON = 2) attack_verb = list("pinched", "nipped", "warped", "blasted") tool_sound = 'sound/effects/stealthoff.ogg' diff --git a/code/game/objects/items/tools/wrench.dm b/code/game/objects/items/tools/wrench.dm index acabc9ac3d7b..c05c30db45d8 100644 --- a/code/game/objects/items/tools/wrench.dm +++ b/code/game/objects/items/tools/wrench.dm @@ -81,7 +81,7 @@ damage_force = 8 throw_force = 10 w_class = ITEMSIZE_NORMAL - slowdown = 0.1 + weight = ITEM_WEIGHT_HYBRID_TOOLS origin_tech = list(TECH_MATERIAL = 3, TECH_ENGINEERING = 3, TECH_PHORON = 2) attack_verb = list("bashed", "battered", "bludgeoned", "whacked", "warped", "blasted") tool_sound = 'sound/effects/stealthoff.ogg' diff --git a/code/game/objects/items/weapons/RCD.dm b/code/game/objects/items/weapons/RCD.dm index da304f685f5e..3b1a72e99cd6 100644 --- a/code/game/objects/items/weapons/RCD.dm +++ b/code/game/objects/items/weapons/RCD.dm @@ -11,7 +11,7 @@ SLOT_ID_LEFT_HAND = 'icons/mob/items/lefthand.dmi', SLOT_ID_RIGHT_HAND = 'icons/mob/items/righthand.dmi', ) - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD damage_force = 10 throw_force = 10 throw_speed = 1 diff --git a/code/game/objects/items/weapons/RPD.dm b/code/game/objects/items/weapons/RPD.dm index c8fc53f016af..43bdfd5dfc0b 100644 --- a/code/game/objects/items/weapons/RPD.dm +++ b/code/game/objects/items/weapons/RPD.dm @@ -17,7 +17,7 @@ SLOT_ID_LEFT_HAND = 'icons/mob/items/lefthand.dmi', SLOT_ID_RIGHT_HAND = 'icons/mob/items/righthand.dmi', ) - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD damage_force = 10 throw_force = 10 throw_speed = 1 diff --git a/code/game/objects/items/weapons/duct_tape.dm b/code/game/objects/items/weapons/duct_tape.dm index d4e320a954ee..b39b7533f664 100644 --- a/code/game/objects/items/weapons/duct_tape.dm +++ b/code/game/objects/items/weapons/duct_tape.dm @@ -162,7 +162,7 @@ icon_state = "tape" w_class = ITEMSIZE_TINY plane = MOB_PLANE - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD anchored = FALSE var/obj/item/stuck = null diff --git a/code/game/objects/items/weapons/explosives.dm b/code/game/objects/items/weapons/explosives.dm index 754dc9468d0b..7ece8ebc95e2 100644 --- a/code/game/objects/items/weapons/explosives.dm +++ b/code/game/objects/items/weapons/explosives.dm @@ -5,7 +5,7 @@ icon = 'icons/obj/assemblies.dmi' icon_state = "plastic-explosive0" item_state = "plasticx" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD w_class = ITEMSIZE_SMALL origin_tech = list(TECH_ILLEGAL = 2) var/datum/wires/explosive/c4/wires = null diff --git a/code/game/objects/items/weapons/material/material_armor.dm b/code/game/objects/items/weapons/material/material_armor.dm index 6418facb2ca7..69a74661fba2 100644 --- a/code/game/objects/items/weapons/material/material_armor.dm +++ b/code/game/objects/items/weapons/material/material_armor.dm @@ -192,7 +192,9 @@ Protectiveness | Armor % if(!isnull(material.conductivity)) siemens_coefficient = clamp( material.conductivity / 10, 0, 10) - slowdown = clamp(0, round(material.weight / 10, 0.1) * material_weight_factor, 6) + var/legacy_whatever = clamp(0, round(material.weight / 10, 0.1) * material_weight_factor, 6) * 10 + set_weight(legacy_whatever * 2) + set_encumbrance(legacy_whatever * 4) /obj/item/clothing/suit/armor/material name = "armor" diff --git a/code/game/objects/items/weapons/material/twohanded.dm b/code/game/objects/items/weapons/material/twohanded.dm index 7237c7e83ede..2c85cc4bfa21 100644 --- a/code/game/objects/items/weapons/material/twohanded.dm +++ b/code/game/objects/items/weapons/material/twohanded.dm @@ -219,7 +219,7 @@ fragile = 1 //It's a haphazard thing of glass, wire, and steel reach = 2 // Spears are long. attackspeed = 20 - slowdown = 1.05 + weight = ITEM_WEIGHT_MELEE_SPEAR var/obj/item/grenade/explosive = null var/war_cry = "AAAAARGH!!!" @@ -302,7 +302,7 @@ force_divisor = 0.6 // 9/36 with hardness 60 (steel) and 0.25 unwielded divisor hitsound = 'sound/weapons/heavysmash.ogg' w_class = ITEMSIZE_HUGE - slowdown = 1.5 + encumbrance = ITEM_ENCUMBRANCE_MELEE_SLEDGEHAMMER dulled_divisor = 0.95 //Still metal on a stick sharp = 0 edge = 1 diff --git a/code/game/objects/items/weapons/melee/misc.dm b/code/game/objects/items/weapons/melee/misc.dm index 0d3690d06861..1b88198c6a26 100644 --- a/code/game/objects/items/weapons/melee/misc.dm +++ b/code/game/objects/items/weapons/melee/misc.dm @@ -387,7 +387,7 @@ edge = 1 attack_verb = list("attacked", "smashed", "crushed", "wacked", "pounded") armor_penetration = 50 - slowdown = 0 + weight = ITEM_WEIGHT_BASELINE //This currently just kills the user. lol /* diff --git a/code/game/objects/items/weapons/nullrod.dm b/code/game/objects/items/weapons/nullrod.dm index fdaf09c32e86..7775babacd52 100644 --- a/code/game/objects/items/weapons/nullrod.dm +++ b/code/game/objects/items/weapons/nullrod.dm @@ -412,8 +412,9 @@ hitsound = 'sound/weapons/bladeslice.ogg' attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut") -/obj/item/nullrod/tribal_knife/process(delta_time) - slowdown = rand(-2, 2) +// no this is hrp +// /obj/item/nullrod/tribal_knife/process(delta_time) +// slowdown = rand(-2, 2) /obj/item/nullrod/pitchfork icon_state = "pitchfork0" diff --git a/code/game/objects/items/weapons/shields.dm b/code/game/objects/items/weapons/shields.dm index 3262bc35c412..fd46d2d26634 100644 --- a/code/game/objects/items/weapons/shields.dm +++ b/code/game/objects/items/weapons/shields.dm @@ -191,7 +191,7 @@ item_state = "metal" icon_state = "metal" damage_force = 16 - slowdown = 2 + encumbrance = ITEM_ENCUMBRANCE_SHIELD_TOWER throw_force = 15 //Massive piece of metal w_class = ITEMSIZE_HUGE diff --git a/code/game/objects/items/weapons/surgery_tools.dm b/code/game/objects/items/weapons/surgery_tools.dm index 7b57ee6337de..59e1a1a7fff3 100644 --- a/code/game/objects/items/weapons/surgery_tools.dm +++ b/code/game/objects/items/weapons/surgery_tools.dm @@ -13,7 +13,7 @@ desc = "This shouldn't be here, ahelp it." icon = 'icons/obj/surgery.dmi' w_class = ITEMSIZE_SMALL - item_flags = ITEM_CAREFUL_BLUDGEON + item_flags = ITEM_CAREFUL_BLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/helpforce = 0 //For help intent things drop_sound = 'sound/items/drop/weldingtool.ogg' pickup_sound = 'sound/items/pickup/weldingtool.ogg' diff --git a/code/game/objects/items/weapons/tanks/tanks.dm b/code/game/objects/items/weapons/tanks/tanks.dm index 7b8e2af04dbd..40bf736e4c34 100644 --- a/code/game/objects/items/weapons/tanks/tanks.dm +++ b/code/game/objects/items/weapons/tanks/tanks.dm @@ -25,6 +25,8 @@ var/list/global/tank_gauge_cache = list() throw_speed = 1 throw_range = 4 + weight = ITEM_WEIGHT_GAS_TANK + var/datum/gas_mixture/air_contents = null var/distribute_pressure = ONE_ATMOSPHERE integrity = 20 diff --git a/code/game/objects/structures/inflatable.dm b/code/game/objects/structures/inflatable.dm index ce3ecc965f61..9cab554c8085 100644 --- a/code/game/objects/structures/inflatable.dm +++ b/code/game/objects/structures/inflatable.dm @@ -252,10 +252,7 @@ icon = 'icons/obj/inflatable.dmi' icon_state = "folded_wall_torn" -/obj/item/inflatable/torn/attack_self(mob/user) - . = ..() - if(.) - return +/obj/item/inflatable/torn/inflate(user,location) to_chat(user, "The inflatable wall is too torn to be inflated!") add_fingerprint(user) @@ -265,10 +262,7 @@ icon = 'icons/obj/inflatable.dmi' icon_state = "folded_door_torn" -/obj/item/inflatable/door/torn/attack_self(mob/user) - . = ..() - if(.) - return +/obj/item/inflatable/door/torn/inflate(user,location) to_chat(user, "The inflatable door is too torn to be inflated!") add_fingerprint(user) diff --git a/code/game/rendering/legacy/alert.dm b/code/game/rendering/legacy/alert.dm index 70753c7d6293..f5a70ffeac90 100644 --- a/code/game/rendering/legacy/alert.dm +++ b/code/game/rendering/legacy/alert.dm @@ -1,6 +1,23 @@ //A system to manage and display alerts on screen without needing you to do it yourself -//PUBLIC - call these wherever you want +/mob/var/list/alerts = list() // contains /atom/movable/screen/alert only // On /mob so clientless mobs will throw alerts properly + +/atom/movable/screen/alert/Click(location, control, params) + if(!usr || !usr.client) + return + var/paramslist = params2list(params) + if(paramslist["shift"]) // screen objects don't do the normal Click() stuff so we'll cheat + to_chat(usr,"[name] - [desc]") + return + if(master) + return usr.client.Click(master, location, control, params) + +/atom/movable/screen/alert/Destroy() + ..() + severity = 0 + master = null + screen_loc = "" + return QDEL_HINT_QUEUE /mob/proc/throw_alert(category, type, severity, obj/new_master) @@ -80,6 +97,10 @@ name = "Alert" desc = "Something seems to have gone wrong with this alert, so report this bug please" mouse_opacity = 1 + /// background to render + var/icon/background_icon = 'icons/screen/alerts/backgrounds.dmi' + /// background state to render; null to not render + var/background_state var/timeout = 0 //If set to a number, this alert will clear itself after that many deciseconds var/severity = 0 var/alerttooltipstyle = "" @@ -87,6 +108,16 @@ /// mob that owns us var/mob/owner +/atom/movable/screen/alert/Initialize(mapload) + . = ..() + update_icon() + +/atom/movable/screen/alert/update_icon(updates) + . = ..() + underlays.len = 0 + if(background_icon && background_state) + underlays += image(background_icon, background_state) + /atom/movable/screen/alert/Destroy() owner = null return ..() @@ -446,6 +477,8 @@ so as to remain in compliance with the most up-to-date laws." // Re-render all alerts - also called in /datum/hud/show_hud() because it's needed there /datum/hud/proc/reorganize_alerts() + if(!mymob) + return var/list/alerts = mymob.alerts if(!hud_shown) for(var/i = 1, i <= alerts.len, i++) @@ -480,21 +513,36 @@ so as to remain in compliance with the most up-to-date laws." mymob?.client?.screen |= alert return 1 -/mob/var/list/alerts = list() // contains /atom/movable/screen/alert only // On /mob so clientless mobs will throw alerts properly +//? Encumbrance -/atom/movable/screen/alert/Click(location, control, params) - if(!usr || !usr.client) - return - var/paramslist = params2list(params) - if(paramslist["shift"]) // screen objects don't do the normal Click() stuff so we'll cheat - to_chat(usr,"[name] - [desc]") - return - if(master) - return usr.client.Click(master, location, control, params) +/atom/movable/screen/alert/encumbered + abstract_type = /atom/movable/screen/alert/encumbered + icon = 'icons/screen/alerts/encumbered.dmi' + background_state = "default" + desc = "Carrying more than you can comfortably bear. Movement slowed." -/atom/movable/screen/alert/Destroy() - ..() - severity = 0 - master = null - screen_loc = "" - return QDEL_HINT_QUEUE +/atom/movable/screen/alert/encumbered/Click(location, control, params) + if(!isliving(owner)) + return + var/mob/living/L = owner + to_chat(usr, jointext(list( + "[usr == L? "You are" : "[L] is"] [lowertext(name)].", + "Encumbrance: [L.cached_carry_encumbrance] / [L.physiology.carry_strength]", + "Weight: [L.cached_carry_weight] / [L.physiology.carry_strength]", + ), "
")) + +/atom/movable/screen/alert/encumbered/minor + name = "Lightly Encumbered" + icon_state = "1" + +/atom/movable/screen/alert/encumbered/moderate + name = "Moderately Encumbered" + icon_state = "2" + +/atom/movable/screen/alert/encumbered/severe + name = "Severely Encumbered" + icon_state = "3" + +/atom/movable/screen/alert/encumbered/extreme + name = "Extremely Encumbered" + icon_state = "4" diff --git a/code/game/rendering/mob.dm b/code/game/rendering/mob.dm index 0be56c97185f..70a30824f565 100644 --- a/code/game/rendering/mob.dm +++ b/code/game/rendering/mob.dm @@ -23,6 +23,7 @@ client.using_perspective?.reload(client, TRUE) INVOKE_ASYNC(client, TYPE_PROC_REF(/client, init_viewport_blocking)) reload_fullscreen() + hud_used?.reorganize_alerts() /** * reloads rendering after screen viewport size change diff --git a/code/modules/artifice/telecube.dm b/code/modules/artifice/telecube.dm index 21056a7ed4fa..795dff6b7337 100644 --- a/code/modules/artifice/telecube.dm +++ b/code/modules/artifice/telecube.dm @@ -28,8 +28,6 @@ catalogue_data = list(/datum/category_item/catalogue/anomalous/precursor_a/telecube) - slowdown = 5 - throw_range = 2 var/obj/item/telecube/mate = null diff --git a/code/modules/clothing/clothing.dm b/code/modules/clothing/clothing.dm index 874236bbc727..cb6019645952 100644 --- a/code/modules/clothing/clothing.dm +++ b/code/modules/clothing/clothing.dm @@ -5,6 +5,7 @@ // todo: this is an awful way to do it but it works unequip_sound = 'sound/items/drop/clothing.ogg' pickup_sound = 'sound/items/pickup/cloth.ogg' + item_flags = NONE //? equip /// Inventory slot IDs where this is active for any effects. Used by subtypes, to be potentially refactored in the future. @@ -61,6 +62,12 @@ /// full list of accessories, everything inside must be an /obj/item. *not* /obj/item/clothing. var/list/accessories + //* Carry Weight + /// encumbrance compensation for accessories - flat. + var/accessory_encumbrance_mitigation = 0 + /// encumbrance multiplier for accessories. + var/accessory_encumbrance_multiply = 1 + /obj/item/clothing/Initialize(mapload) . = ..() if(islist(active_slots)) diff --git a/code/modules/clothing/clothing_accessories.dm b/code/modules/clothing/clothing_accessories.dm index 783372887a7c..ceca5912638d 100644 --- a/code/modules/clothing/clothing_accessories.dm +++ b/code/modules/clothing/clothing_accessories.dm @@ -15,6 +15,25 @@ return accessory_host.update_worn_icon() return ..() +/obj/item/clothing/get_encumbrance() + . = ..() + if(!isnull(accessory_host)) + . = max(0, . * accessory_host.accessory_encumbrance_multiply - accessory_host.accessory_encumbrance_mitigation) + +/obj/item/clothing/proc/set_accessory_encumbrance_mitigation(val, update) + accessory_encumbrance_mitigation = val + if(update) + update_accessory_encumbrance() + +/obj/item/clothing/proc/set_accessory_encumbrance_multiply(val, update) + accessory_encumbrance_multiply = val + if(update) + update_accessory_encumbrance() + +/obj/item/clothing/proc/update_accessory_encumbrance() + for(var/obj/item/I as anything in accessories) + I.update_encumbrance() + /obj/item/clothing/equipped(mob/user, slot, flags) . = ..() // propagate through accessories @@ -210,22 +229,16 @@ LAZYADD(accessories,A) A.on_attached(src, user) add_obj_verb(src, /obj/item/clothing/proc/removetie_verb) - update_accessory_slowdown() update_worn_icon() + update_encumbrance() /obj/item/clothing/proc/remove_accessory(mob/user, obj/item/clothing/accessory/A) if(!LAZYLEN(accessories) || !(A in accessories)) return - A.on_removed(user) accessories -= A - update_accessory_slowdown() update_worn_icon() - -/obj/item/clothing/proc/update_accessory_slowdown() - slowdown = initial(slowdown) - for(var/obj/item/clothing/accessory/A in accessories) - slowdown += A.slowdown + update_encumbrance() /obj/item/clothing/proc/removetie_verb() set name = "Remove Accessory" diff --git a/code/modules/clothing/head/helmet.dm b/code/modules/clothing/head/helmet.dm index ec7773a18b4d..dc3b49e743b2 100644 --- a/code/modules/clothing/head/helmet.dm +++ b/code/modules/clothing/head/helmet.dm @@ -16,6 +16,8 @@ ear_protection = 1 drop_sound = 'sound/items/drop/helm.ogg' pickup_sound = 'sound/items/pickup/helm.ogg' + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIUM_HELMET + weight = ITEM_WEIGHT_ARMOR_MEDIUM_HELMET /obj/item/clothing/head/helmet/ntsec name = "corpsec helmet" @@ -130,6 +132,8 @@ cold_protection = HEAD min_cold_protection_temperature = SPACE_HELMET_MIN_COLD_PROTECTION_TEMPERATURE siemens_coefficient = 0.5 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_HEAVY_HELMET + weight = ITEM_WEIGHT_ARMOR_HEAVY_HELMET /obj/item/clothing/head/helmet/alien name = "alien helmet" diff --git a/code/modules/clothing/shoes/_shoes.dm b/code/modules/clothing/shoes/_shoes.dm index 212ed0ce8e11..a86df9ffd1ea 100644 --- a/code/modules/clothing/shoes/_shoes.dm +++ b/code/modules/clothing/shoes/_shoes.dm @@ -25,7 +25,6 @@ var/step_volume_mod = 1 //How quiet or loud footsteps in this shoe are permeability_coefficient = 0.50 - slowdown = SHOES_SLOWDOWN damage_force = 2 var/overshoes = 0 species_restricted = list("exclude",SPECIES_TESHARI, SPECIES_VOX) diff --git a/code/modules/clothing/shoes/colour.dm b/code/modules/clothing/shoes/colour.dm index 2ae6d1db50b9..664c2e9c60ad 100644 --- a/code/modules/clothing/shoes/colour.dm +++ b/code/modules/clothing/shoes/colour.dm @@ -97,7 +97,8 @@ if(!user.attempt_insert_item_for_installation(cuffs, src)) return chained = cuffs - slowdown = 15 + // todo: refactor + set_encumbrance(ITEM_ENCUMBRANCE_SHOES_CUFFED) icon_state = "orange1" /obj/item/clothing/shoes/orange/proc/remove_cuffs(mob/user as mob) @@ -107,7 +108,8 @@ user.put_in_hands_or_drop(chained) chained.add_fingerprint(user) - slowdown = initial(slowdown) + // todo: refactor + set_encumbrance(initial(encumbrance)) icon_state = "orange" chained = null diff --git a/code/modules/clothing/shoes/leg_guards.dm b/code/modules/clothing/shoes/leg_guards.dm index fdef4c976a0d..6bdb4650acf0 100644 --- a/code/modules/clothing/shoes/leg_guards.dm +++ b/code/modules/clothing/shoes/leg_guards.dm @@ -2,7 +2,8 @@ name = "leg guards" desc = "These will protect your legs and feet." body_cover_flags = LEGS|FEET - slowdown = SHOES_SLOWDOWN+0.5 + weight = ITEM_WEIGHT_ARMOR_MEDIUM_BOOTS + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIUM_BOOTS species_restricted = null //Unathi and Taj can wear leg armor now w_class = ITEMSIZE_NORMAL step_volume_mod = 1.3 @@ -68,7 +69,8 @@ icon_state = "leg_guards_flexitac" item_state_slots = list(SLOT_ID_RIGHT_HAND = "jackboots", SLOT_ID_LEFT_HAND = "jackboots") siemens_coefficient = 0.6 - slowdown = SHOES_SLOWDOWN+0.2 + weight = ITEM_WEIGHT_ARMOR_LIGHT_BOOTS + encumbrance = ITEM_ENCUMBRANCE_ARMOR_LIGHT_BOOTS armor_type = /datum/armor/station/tactical min_cold_protection_temperature = T0C - 20 cold_protection = LEGS diff --git a/code/modules/clothing/shoes/magboots.dm b/code/modules/clothing/shoes/magboots.dm index 52b8110e09ad..6590ad1ad239 100644 --- a/code/modules/clothing/shoes/magboots.dm +++ b/code/modules/clothing/shoes/magboots.dm @@ -9,18 +9,18 @@ overshoes = 1 shoes_under_pants = -1 //These things are huge preserve_item = 1 + encumbrance = ITEM_ENCUMBRANCE_SHOES_MAGBOOTS var/magpulse = 0 - var/slowdown_on = 3 var/icon_base = "magboots" action_button_name = "Toggle Magboots" step_volume_mod = 1.3 drop_sound = 'sound/items/drop/metalboots.ogg' pickup_sound = 'sound/items/pickup/toolbox.ogg' -/obj/item/clothing/shoes/magboots/proc/set_slowdown() - slowdown = worn_over? max(SHOES_SLOWDOWN, worn_over.slowdown): SHOES_SLOWDOWN //So you can't put on magboots to make you walk faster. - if (magpulse) - slowdown += slowdown_on + var/encumbrance_on = ITEM_ENCUMBRANCE_SHOES_MAGBOOTS_PULSE + +/obj/item/clothing/shoes/magboots/proc/update_magboot_encumbrance() + set_encumbrance(initial(encumbrance) + (magpulse? encumbrance_on : 0)) /obj/item/clothing/shoes/magboots/attack_self(mob/user) . = ..() @@ -29,14 +29,14 @@ if(magpulse) clothing_flags &= ~NOSLIP magpulse = 0 - set_slowdown() + update_magboot_encumbrance() damage_force = 3 if(icon_base) icon_state = "[icon_base]0" to_chat(user, "You disable the mag-pulse traction system.") else clothing_flags |= NOSLIP magpulse = 1 - set_slowdown() + update_magboot_encumbrance() damage_force = 5 if(icon_base) icon_state = "[icon_base]1" to_chat(user, "You enable the mag-pulse traction system.") @@ -56,11 +56,11 @@ /obj/item/clothing/shoes/magboots/equipped(mob/user, slot, flags) . = ..() - set_slowdown() + update_magboot_encumbrance() /obj/item/clothing/shoes/magboots/unequipped(mob/user, slot, flags) . = ..() - set_slowdown() + update_magboot_encumbrance() /obj/item/clothing/shoes/magboots/examine(mob/user, dist) . = ..() @@ -118,7 +118,7 @@ /obj/item/clothing/shoes/magboots/advanced name = "advanced magboots" icon_state = "advmag0" - slowdown_on = 0 + encumbrance_on = 0 icon_base = "advmag" /obj/item/clothing/shoes/magboots/syndicate @@ -126,4 +126,4 @@ desc = "Prior to its dissolution, many Syndicate agents were tasked with stealing NanoTrasen's prototype advanced magboots. Reverse engineering these rare tactical boots was achieved shortly before the end of the conflict." icon_state = "syndiemag0" icon_base = "syndiemag" - slowdown_on = 0 + encumbrance_on = 0 diff --git a/code/modules/clothing/shoes/miscellaneous.dm b/code/modules/clothing/shoes/miscellaneous.dm index 25e7d88650a6..247bb9b1c57b 100644 --- a/code/modules/clothing/shoes/miscellaneous.dm +++ b/code/modules/clothing/shoes/miscellaneous.dm @@ -24,12 +24,12 @@ permeability_coefficient = 0.05 siemens_coefficient = 0 //They're thick rubber boots! Of course they won't conduct electricity! clothing_flags = NOSLIP - slowdown = SHOES_SLOWDOWN+1 + encumbrance = ITEM_ENCUMBRANCE_SHOES_GALOSHES + flat_encumbrance = ITEM_FLAT_ENCUMBRANCE_GALOSHES species_restricted = null drop_sound = 'sound/items/drop/rubber.ogg' pickup_sound = 'sound/items/pickup/rubber.ogg' - /obj/item/clothing/shoes/dress name = "dress shoes" desc = "Sharp looking low quarters, perfect for a formal uniform." @@ -65,7 +65,8 @@ desc = "The prankster's standard-issue clowning shoes. Damn they're huge!" name = "clown shoes" icon_state = "clown" - slowdown = SHOES_SLOWDOWN+1 + encumbrance = ITEM_ENCUMBRANCE_SHOES_CLOWN + flat_encumbrance = ITEM_FLAT_ENCUMBRANCE_SHOES_CLOWN damage_force = 0 var/footstep = 1 //used for squeeks whilst walking species_restricted = null @@ -137,7 +138,8 @@ icon_state = "flippers" item_state_slots = list(SLOT_ID_RIGHT_HAND = "galoshes", SLOT_ID_LEFT_HAND = "galoshes") clothing_flags = NOSLIP - slowdown = SHOES_SLOWDOWN+1 + encumbrance = ITEM_ENCUMBRANCE_SHOES_FINS + flat_encumbrance = ITEM_FLAT_ENCUMBRANCE_SHOES_FINS species_restricted = null /obj/item/clothing/shoes/flipflop @@ -271,6 +273,7 @@ name = "Antediluvian exposed heels alt" desc = "A pair of a set of heels recovered with an odd design. This version has toes exposed, granting the wearer elegance, or unsightliness. This one has extra gold trimming." icon_state = "aziru_heels_alt" + // The things folks do for fashion... /obj/item/clothing/shoes/galoshes/black name = "black galoshes" @@ -281,7 +284,7 @@ name = "dark-purple semi-galoshes" desc = "A dark-purple rubber boots. They obviously don't smell like a cotton candy, roses and fresh roasted peanuts." icon_state = "galoshes_sc" - slowdown = SHOES_SLOWDOWN + encumbrance = ITEM_ENCUMBRANCE_BASELINE //More Warhammer Fun /obj/item/clothing/shoes/utilitarian diff --git a/code/modules/clothing/spacesuits/miscellaneous.dm b/code/modules/clothing/spacesuits/miscellaneous.dm index 1825aea103b2..bb7a0a035882 100644 --- a/code/modules/clothing/spacesuits/miscellaneous.dm +++ b/code/modules/clothing/spacesuits/miscellaneous.dm @@ -11,6 +11,8 @@ min_cold_protection_temperature = SPACE_SUIT_MIN_COLD_PROTECTION_TEMPERATURE min_pressure_protection = 0 * ONE_ATMOSPHERE max_pressure_protection = 10 * ONE_ATMOSPHERE + weight = ITEM_WEIGHT_VOIDSUIT_HELMET + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET //Captain's space suit This is not the proper path but I don't currently know enough about how this all works to mess with it. /obj/item/clothing/suit/armor/captain @@ -23,7 +25,8 @@ clothing_flags = 0 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS allowed = list(/obj/item/tank/emergency/oxygen, /obj/item/flashlight,/obj/item/gun/energy, /obj/item/gun/ballistic, /obj/item/ammo_magazine, /obj/item/ammo_casing, /obj/item/melee/baton,/obj/item/handcuffs) - slowdown = 1.5 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT + weight = ITEM_WEIGHT_VOIDSUIT armor_type = /datum/armor/station/tactical inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETAIL cold_protection = UPPER_TORSO | LOWER_TORSO | LEGS | FEET | ARMS | HANDS @@ -66,8 +69,9 @@ name = "Santa's suit" desc = "Festive!" icon_state = "santa" - slowdown = 0 - clothing_flags = 0 + weight = ITEM_WEIGHT_BASELINE + encumbrance = ITEM_ENCUMBRANCE_BASELINE + clothing_flags = NONE allowed = list(/obj/item) //for stuffing exta special presents //Space pirate outfit @@ -76,9 +80,11 @@ desc = "Yarr." icon_state = "pirate" armor_type = /datum/armor/pirate/medium - clothing_flags = 0 + weight = ITEM_WEIGHT_BASELINE + encumbrance = ITEM_ENCUMBRANCE_BASELINE + clothing_flags = NONE inv_hide_flags = BLOCKHAIR - body_cover_flags = 0 + body_cover_flags = NONE siemens_coefficient = 0.9 /obj/item/clothing/suit/space/pirate //Whhhhyyyyyyy??? @@ -87,7 +93,8 @@ icon_state = "pirate" w_class = ITEMSIZE_NORMAL allowed = list(/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/handcuffs,/obj/item/tank/emergency/oxygen) - slowdown = 0 + weight = ITEM_WEIGHT_BASELINE + encumbrance = ITEM_ENCUMBRANCE_BASELINE armor_type = /datum/armor/pirate/medium siemens_coefficient = 0.9 inv_hide_flags = HIDETAIL|HIDEHOLSTER @@ -99,12 +106,15 @@ icon_state = "syndicate-helm-orange" desc = "A simple helmet with a built in light, smells like mothballs." flash_protection = FLASH_PROTECTION_NONE + encumbrance = ITEM_ENCUMBRANCE_EMERGENCY_SOFTSUIT_HELMET + weight = ITEM_WEIGHT_EMERGENCY_SOFTSUIT_HELMET /obj/item/clothing/suit/space/emergency name = "Emergency Softsuit" icon_state = "syndicate-orange" desc = "A thin, ungainly softsuit colored in blaze orange for rescuers to easily locate, looks pretty fragile." - slowdown = 4 + encumbrance = ITEM_ENCUMBRANCE_EMERGENCY_SOFTSUIT + weight = ITEM_WEIGHT_EMERGENCY_SOFTSUIT //Russian Emergency Suit /obj/item/clothing/head/helmet/space/emergency/russian @@ -117,4 +127,3 @@ name = "Sovjet Emergency Softsuit" icon_state = "russian" desc = "A chunky antique softsuit distributed to members of the Indo-Russian Diaspora. After all this time, it looks pretty fragile." - slowdown = 4 diff --git a/code/modules/clothing/spacesuits/plasman.dm b/code/modules/clothing/spacesuits/plasman.dm index 1f4723332f84..c1e84360c7e8 100644 --- a/code/modules/clothing/spacesuits/plasman.dm +++ b/code/modules/clothing/spacesuits/plasman.dm @@ -6,7 +6,8 @@ icon_state = "plasmaman_suit" icon_override = 'icons/mob/plasmeme/suits.dmi' desc = "A suit designed by NT to keep phoronoids from coming into contact with incompatible atmosphere. Seems like it doesn't protect from much else." - slowdown = 1 + weight = ITEM_WEIGHT_PHORONOID_SUIT + encumbrance = ITEM_ENCUMBRANCE_PHORONOID_SUIT clothing_flags = ALLOWINTERNALS armor_type = /datum/armor/phoronoid allowed = list(/obj/item/tank) @@ -35,6 +36,8 @@ clothing_flags = ALLOWINTERNALS | FLEXIBLEMATERIAL armor_type = /datum/armor/phoronoid light_overlay = "plasmaman_overlay" + weight = ITEM_WEIGHT_PHORONOID_HELMET + encumbrance = ITEM_ENCUMBRANCE_PHORONOID_HELMET // // SEC diff --git a/code/modules/clothing/spacesuits/spacesuits.dm b/code/modules/clothing/spacesuits/spacesuits.dm index 78dc09161d17..45de5eee2684 100644 --- a/code/modules/clothing/spacesuits/spacesuits.dm +++ b/code/modules/clothing/spacesuits/spacesuits.dm @@ -21,7 +21,9 @@ preserve_item = 1 flash_protection = FLASH_PROTECTION_MAJOR valid_accessory_slots = null - + weight = ITEM_WEIGHT_SOFTSUIT_HELMET + encumbrance = ITEM_ENCUMBRANCE_SOFTSUIT_HELMET + var/obj/machinery/camera/camera var/list/camera_networks @@ -73,7 +75,6 @@ clothing_flags = CLOTHING_THICK_MATERIAL | CLOTHING_INJECTION_PORT body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS allowed = list(/obj/item/flashlight,/obj/item/tank/emergency/oxygen,/obj/item/suit_cooling_unit) - slowdown = 1 armor_type = /datum/armor/general/space inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER cold_protection = UPPER_TORSO | LOWER_TORSO | LEGS | FEET | ARMS | HANDS @@ -84,6 +85,8 @@ species_restricted = list("exclude",SPECIES_DIONA) preserve_item = 1 valid_accessory_slots = (ACCESSORY_SLOT_OVER | ACCESSORY_SLOT_ARMBAND | ACCESSORY_SLOT_DECOR) + weight = ITEM_WEIGHT_SOFTSUIT + encumbrance = ITEM_ENCUMBRANCE_SOFTSUIT var/list/supporting_limbs //If not-null, automatically splints breaks. Checked when removing the suit. /obj/item/clothing/suit/space/equipped(mob/M, slot, accessory, silent, creation) diff --git a/code/modules/clothing/spacesuits/syndi.dm b/code/modules/clothing/spacesuits/syndi.dm index 2f1a9d056053..aa7a625237fa 100644 --- a/code/modules/clothing/spacesuits/syndi.dm +++ b/code/modules/clothing/spacesuits/syndi.dm @@ -12,7 +12,6 @@ desc = "A crimson spacesuit sporting clean lines and durable plating. Robust, reliable, and slightly suspicious." w_class = ITEMSIZE_NORMAL allowed = list(/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs,/obj/item/tank/emergency/oxygen) - slowdown = 1 armor_type = /datum/armor/agent/space siemens_coefficient = 0.6 diff --git a/code/modules/clothing/spacesuits/void/event.dm b/code/modules/clothing/spacesuits/void/event.dm index 7524e74fa5fd..7dfd4866dd8a 100644 --- a/code/modules/clothing/spacesuits/void/event.dm +++ b/code/modules/clothing/spacesuits/void/event.dm @@ -11,13 +11,16 @@ item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndicate-helm-black", SLOT_ID_LEFT_HAND = "syndicate-helm-black") armor_type = /datum/armor/vintage/space light_overlay = "helmet_light" + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_LIGHT + weight = ITEM_WEIGHT_VOIDSUIT_HELMET_LIGHT /obj/item/clothing/suit/space/void/refurb name = "vintage crewman's voidsuit" desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer spacers swear by these old things, even if new powered hardsuits have more features and better armor. This one is devoid of any identifying markings or rank indicators." icon_state = "rig-vintagecrew" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 0.5 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_LIGHT + weight = ITEM_WEIGHT_VOIDSUIT_LIGHT armor_type = /datum/armor/vintage/space allowed = list(/obj/item/flashlight, /obj/item/tank, @@ -47,7 +50,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. This one in particular seems to be an ode to the Ship of Theseus, but the insulation and radiation proofing are top-notch. The chestplate bears the logo of an old shipyard - though you don't recognize the name." icon_state = "rig-vintageengi" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 1 armor_type = /datum/armor/vintage/space/engi min_pressure_protection = 0 * ONE_ATMOSPHERE max_pressure_protection = 15 * ONE_ATMOSPHERE @@ -93,7 +95,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer spacers swear by these old things, even if new powered hardsuits have more features and better armor. The green and white markings indicate this as a medic's suit." icon_state = "rig-vintagemedic" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 0.5 armor_type = /datum/armor/vintage/space/med allowed = list(/obj/item/flashlight, /obj/item/tank, @@ -124,7 +125,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer marines swear by these old things, even if new powered hardsuits have more features and better armor. The blue markings indicate this as the marine/guard variant, likely from a merchant ship." icon_state = "rig-vintagemarine" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 1 armor_type = /datum/armor/vintage/space/marine siemens_coefficient = 0.8 allowed = list(/obj/item/gun, @@ -160,7 +160,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer spacers swear by these old things, even if new powered hardsuits have more features and better armor. This variant appears to be an officer's, and has the best protection of all the old models." icon_state = "rig-vintageofficer" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 1 armor_type = /datum/armor/vintage/space/officer siemens_coefficient = 0.7 allowed = list(/obj/item/gun, @@ -201,7 +200,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer spacers swear by these old things, even if new powered hardsuits have more features and better armor. The royal blue markings indicate this is the pilot's variant; low protection but ultra-lightweight." icon_state = "rig-vintagepilot" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 0.25 armor_type = /datum/armor/vintage/space/pilot siemens_coefficient = 0.9 allowed = list(/obj/item/flashlight, @@ -232,7 +230,6 @@ desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer spacers swear by these old things, even if new powered hardsuits have more features and better armor. The purple markings indicate this as a scientist's suit. Keep your eyes open for ropes." icon_state = "rig-vintagescientist" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 0.5 armor_type = /datum/armor/vintage/space/science siemens_coefficient = 0.8 allowed = list(/obj/item/flashlight, @@ -267,13 +264,16 @@ item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndicate-helm-black", SLOT_ID_LEFT_HAND = "syndicate-helm-black") armor_type = /datum/armor/vintage/space/merc siemens_coefficient = 0.6 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_HEAVY + weight = ITEM_WEIGHT_VOIDSUIT_HELMET_HEAVY /obj/item/clothing/suit/space/void/refurb/mercenary name = "vintage mercenary voidsuit" desc = "A refurbished early contact era voidsuit of human design. These things aren't especially good against modern weapons but they're sturdy, incredibly easy to come by, and there are lots of spare parts for repairs. Many old-timer mercs swear by these old things, even if new powered hardsuits have more features and better armor. The red markings indicate this as the mercenary variant. The company ID has been scratched off." icon_state = "rig-vintagemerc" item_state_slots = list(SLOT_ID_RIGHT_HAND = "sec_voidsuitTG", SLOT_ID_LEFT_HAND = "sec_voidsuitTG") - slowdown = 1.5 //the tradeoff for being hot shit almost on par with a crimson suit is that it slows you down even more + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HEAVY + weight = ITEM_WEIGHT_VOIDSUIT_HEAVY armor_type = /datum/armor/vintage/space/merc siemens_coefficient = 0.6 allowed = list(/obj/item/gun, diff --git a/code/modules/clothing/spacesuits/void/merc.dm b/code/modules/clothing/spacesuits/void/merc.dm index ce0633dcfaa4..c9fb92ef5ed2 100644 --- a/code/modules/clothing/spacesuits/void/merc.dm +++ b/code/modules/clothing/spacesuits/void/merc.dm @@ -6,6 +6,8 @@ item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndie_helm", SLOT_ID_LEFT_HAND = "syndie_helm") armor_type = /datum/armor/merc/space siemens_coefficient = 0.6 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET + weight = ITEM_WEIGHT_VOIDSUIT_HELMET camera_networks = list(NETWORK_MERCENARY) light_overlay = "helmet_light_green" //todo: species-specific light overlays @@ -14,7 +16,8 @@ name = "blood-red voidsuit" desc = "An advanced suit that protects against injuries during special operations. Property of Gorlex Marauders." item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndie_voidsuit", SLOT_ID_LEFT_HAND = "syndie_voidsuit") - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT + weight = ITEM_WEIGHT_VOIDSUIT w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/merc/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -86,7 +89,6 @@ name = "clown commando voidsuit" desc = "An advanced suit that protects against injuries during special operations. An intricate bananium wafer in the shape of a banana bears the crest of Columbina." item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndie_voidsuit", SLOT_ID_LEFT_HAND = "syndie_voidsuit") - slowdown = 1 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/merc/space/clown allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -107,7 +109,6 @@ icon_state = "odst" name = "hephaestus icarus suit" desc = "One of the few combat-grade suits avalible in the frontier, and the poster-child of Hephaestus Industries. Comes equipped with a wrist-bound oxygen timer." - slowdown = 1 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/station/secsuit allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -127,7 +128,6 @@ icon_state = "odst_corps" name = "hephaestus icarus medic suit" desc = "A standard Icarus line suit that has been repourposed to protect from heavier biohazards." - slowdown = 1 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/exploration/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -147,7 +147,6 @@ icon_state = "odst_orange" name = "hephaestus icarus engineer suit" desc = "Favoured suit of deep-space engineers, comfortable and comparable to suits avalible to NanoTrasen Engineers. Comes equipped with a wrist-bound oxygen timer." - slowdown = 1 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/engineering/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -167,7 +166,6 @@ icon_state = "odst_purple" name = "hephaestus icarus frontier suit" desc = "Cheaper version of the main Icarus line, often marketed to Frontier settlements. Perfect for Expeditions." - slowdown = 1 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/exploration/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -191,7 +189,6 @@ name = "necropolis operations suit" desc = "The main suit used by Necropolis Industries security division, a heavily modified Hephaestus Icarus suit emblazoned with the Necropolis logo on the left shoulder. Equipped with direct connections to the user's implants and prosthetics, making it function as a second skin." item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndie_voidsuit", SLOT_ID_LEFT_HAND = "syndie_voidsuit") - slowdown = 0.4 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/merc/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) @@ -203,9 +200,8 @@ name = "necropolis field medic suit" desc = "The main suit used by Necropolis Industries security division, a heavily modified Hephaestheus Icarus suit emblazoned with the Necropolis logo on the left shoulder and a blue cross on the right arm. Equipped with direct connections to the user's implants and prosthetics, making it function as a second skin." item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndie_voidsuit", SLOT_ID_LEFT_HAND = "syndie_voidsuit") - slowdown = 0.4 w_class = ITEMSIZE_NORMAL armor_type = /datum/armor/merc/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/melee/energy/sword,/obj/item/handcuffs) siemens_coefficient = 0.6 - species_restricted = null + species_restricted = null diff --git a/code/modules/clothing/spacesuits/void/station.dm b/code/modules/clothing/spacesuits/void/station.dm index 007848b460a4..2f43860e0a64 100644 --- a/code/modules/clothing/spacesuits/void/station.dm +++ b/code/modules/clothing/spacesuits/void/station.dm @@ -14,7 +14,6 @@ desc = "A special suit that protects against hazardous, low pressure environments. Has radiation shielding." icon_state = "rig-engineering" item_state_slots = list(SLOT_ID_RIGHT_HAND = "eng_voidsuit", SLOT_ID_LEFT_HAND = "eng_voidsuit") - slowdown = 1 armor_type = /datum/armor/engineering/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/storage/bag/ore,/obj/item/t_scanner,/obj/item/pickaxe, /obj/item/rcd) min_pressure_protection = 0 * ONE_ATMOSPHERE @@ -162,6 +161,8 @@ icon_state = "rig0-medicalalt" armor_type = /datum/armor/medical/space light_overlay = "helmet_light_dual_blue" + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_ULTRALIGHT + weight = ITEM_WEIGHT_VOIDSUIT_HELMET_ULTRALIGHT /obj/item/clothing/head/helmet/space/void/medical/alt_plated name = "streamlined medical voidsuit helmet" @@ -169,19 +170,23 @@ icon_state = "rig0-medicalalt2" armor_type = /datum/armor/medical/space/upgraded light_overlay = "helmet_light_dual_blue" + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_ULTRALIGHT + weight = ITEM_WEIGHT_VOIDSUIT_HELMET_ULTRALIGHT /obj/item/clothing/suit/space/void/medical/alt icon_state = "rig-medicalalt" name = "streamlined medical voidsuit" desc = "A more recent model of Vey-Med voidsuit, exchanging physical protection for fully unencumbered movement and a complete range of motion." - slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_ULTRALIGHT + weight = ITEM_WEIGHT_VOIDSUIT_ULTRALIGHT armor_type = /datum/armor/medical/space /obj/item/clothing/suit/space/void/medical/alt_plated icon_state = "rig-medicalalt2" name = "plated medical voidsuit" desc = "An iteration of an existing Vey-Med voidsuit, allowing full biohazard, radiation and increased close-quarters protection, at the expense of projectile and ranged layers." - slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_ULTRALIGHT + weight = ITEM_WEIGHT_VOIDSUIT_ULTRALIGHT armor_type = /datum/armor/medical/space/upgraded //Security @@ -373,7 +378,6 @@ icon_state = "capsuit_void" armor_type = /datum/armor/station/tactical allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun) - slowdown = 1.5 //Head of Security - update to the snowflake suit /obj/item/clothing/head/helmet/space/void/headofsecurity @@ -382,6 +386,8 @@ icon_state = "hosproto" armor_type = /datum/armor/security/hos/space camera_networks = list(NETWORK_SEC_HELMETS) + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET_HEAVY + weight = ITEM_WEIGHT_VOIDSUIT_HELMET_HEAVY /obj/item/clothing/suit/space/void/headofsecurity desc = "A customized security voidsuit. Has additional composite armor." @@ -389,7 +395,8 @@ icon_state = "hosproto_void" armor_type = /datum/armor/security/hos/space allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/gun) - slowdown = 1.5 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HEAVY + weight = ITEM_WEIGHT_VOIDSUIT_HEAVY //PARA /obj/item/clothing/head/helmet/space/void/para diff --git a/code/modules/clothing/spacesuits/void/void.dm b/code/modules/clothing/spacesuits/void/void.dm index 1931d2d7e215..63edea0cc322 100644 --- a/code/modules/clothing/spacesuits/void/void.dm +++ b/code/modules/clothing/spacesuits/void/void.dm @@ -9,6 +9,9 @@ max_heat_protection_temperature = SPACE_SUIT_MAX_HEAT_PROTECTION_TEMPERATURE min_pressure_protection = 0 * ONE_ATMOSPHERE max_pressure_protection = 10 * ONE_ATMOSPHERE + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_HELMET + weight = ITEM_WEIGHT_VOIDSUIT_HELMET + // inv_hide_flags = HIDEEARS|BLOCKHAIR @@ -37,7 +40,8 @@ icon_state = "void" item_state_slots = list(SLOT_ID_RIGHT_HAND = "space_suit_syndicate", SLOT_ID_LEFT_HAND = "space_suit_syndicate") desc = "A high-tech dark red space suit. Used for AI satellite maintenance." - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT + weight = ITEM_WEIGHT_VOIDSUIT armor_type = /datum/armor/general/space/armored allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit) heat_protection = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS @@ -81,6 +85,17 @@ action_button_name = "Toggle Helmet" +/obj/item/clothing/suit/space/void/get_weight() + . = ..() + if(boots?.loc == src) + . += boots.get_weight() + if(helmet?.loc == src) + . += helmet.get_weight() + if(tank?.loc == src) + . += tank.get_weight() + if(cooler?.loc == src) + . += cooler.get_weight() + /obj/item/clothing/suit/space/void/examine(mob/user, dist) . = ..() var/list/part_list = new diff --git a/code/modules/clothing/spacesuits/void/void_vr.dm b/code/modules/clothing/spacesuits/void/void_vr.dm index fa35d972d674..756207f9efc4 100644 --- a/code/modules/clothing/spacesuits/void/void_vr.dm +++ b/code/modules/clothing/spacesuits/void/void_vr.dm @@ -115,7 +115,8 @@ icon_state = "autoloksuit" item_state = "autoloksuit" armor_type = /datum/armor/autolok/space - slowdown = 0.5 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_LIGHT + weight = ITEM_WEIGHT_VOIDSUIT_LIGHT siemens_coefficient = 1 species_restricted = list("exclude",SPECIES_DIONA,SPECIES_VOX) //this thing can autoadapt breach_threshold = 6 //this thing is basically tissue paper diff --git a/code/modules/clothing/spacesuits/void/wizard.dm b/code/modules/clothing/spacesuits/void/wizard.dm index 5072351338bf..14c307259942 100644 --- a/code/modules/clothing/spacesuits/void/wizard.dm +++ b/code/modules/clothing/spacesuits/void/wizard.dm @@ -16,7 +16,8 @@ name = "gem-encrusted voidsuit" desc = "A bizarre gem-encrusted suit that radiates magical energies." item_state_slots = list(SLOT_ID_RIGHT_HAND = "wiz_voidsuit", SLOT_ID_LEFT_HAND = "wiz_voidsuit") - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_LIGHT + weight = ITEM_WEIGHT_VOIDSUIT_LIGHT w_class = ITEMSIZE_NORMAL unacidable = 1 armor_type = /datum/armor/wizard diff --git a/code/modules/clothing/spacesuits/void/zaddat.dm b/code/modules/clothing/spacesuits/void/zaddat.dm index 61456871d7a8..3502ce939f7d 100644 --- a/code/modules/clothing/spacesuits/void/zaddat.dm +++ b/code/modules/clothing/spacesuits/void/zaddat.dm @@ -5,7 +5,6 @@ item_state_slots = list(SLOT_ID_RIGHT_HAND = "syndicate", SLOT_ID_LEFT_HAND = "syndicate") heat_protection = HEAD body_cover_flags = HEAD|FACE|EYES - slowdown = 0.5 armor_type = /datum/armor/zaddat siemens_coefficient = 1 @@ -14,7 +13,6 @@ /obj/item/clothing/suit/space/void/zaddat name = "\improper Hegemony Shroud" desc = "A Hegemony environment suit, still favored by the Spacer Zaddat because of its durability and ease of manufacture." - slowdown = 1 armor_type = /datum/armor/zaddat siemens_coefficient = 1 allowed = list(/obj/item/flashlight,/obj/item/tank) diff --git a/code/modules/clothing/suits/aliens/tajara.dm b/code/modules/clothing/suits/aliens/tajara.dm index e86caf3513be..cf87201c829d 100644 --- a/code/modules/clothing/suits/aliens/tajara.dm +++ b/code/modules/clothing/suits/aliens/tajara.dm @@ -30,7 +30,8 @@ inv_hide_flags = HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER species_restricted = list(SPECIES_TAJ) armor_type = /datum/armor/general/medieval - slowdown = 0.5 + weight = ITEM_WEIGHT_TAJARAN_SWORDSMAN_ARMOR + encumbrance = ITEM_ENCUMBRANCE_TAJARAN_SWORDSMAN_ARMOR siemens_coefficient = 0.35 //Coats no hoods diff --git a/code/modules/clothing/suits/armor.dm b/code/modules/clothing/suits/armor.dm index e6574f0ac896..bdbf8e89f213 100644 --- a/code/modules/clothing/suits/armor.dm +++ b/code/modules/clothing/suits/armor.dm @@ -69,7 +69,8 @@ icon_state = "bulletproof" item_state_slots = list(SLOT_ID_RIGHT_HAND = "armor", SLOT_ID_LEFT_HAND = "armor") blood_overlay_type = "armor" - slowdown = 0.5 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED + weight = ITEM_WEIGHT_ARMOR_SPECIALIZED armor_type = /datum/armor/station/ballistic siemens_coefficient = 0.7 @@ -83,7 +84,6 @@ desc = "A vest that excels in protecting the wearer against energy projectiles." icon_state = "armor_reflec" blood_overlay_type = "armor" - slowdown = 0.5 armor_type = /datum/armor/station/ablative siemens_coefficient = 0.1 @@ -116,7 +116,8 @@ desc = "A vest that protects the wearer from several common types of ranged weaponry." icon_state = "combat" blood_overlay_type = "armor" - slowdown = 0.5 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIUM + weight = ITEM_WEIGHT_ARMOR_MEDIUM armor_type = /datum/armor/station/combat siemens_coefficient = 0.6 @@ -127,7 +128,8 @@ item_state_slots = list(SLOT_ID_RIGHT_HAND = "swat", SLOT_ID_LEFT_HAND = "swat") body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS inv_hide_flags = HIDETIE|HIDEHOLSTER - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_LIGHT + weight = ITEM_WEIGHT_ARMOR_LIGHT armor_type = /datum/armor/station/tactical siemens_coefficient = 0.7 @@ -141,7 +143,8 @@ clothing_flags = CLOTHING_THICK_MATERIAL body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS allowed = list(/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/handcuffs,/obj/item/tank/emergency/oxygen,/obj/item/clothing/head/helmet) - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_HEAVY + ITEM_ENCUMBRANCE_ARMOR_HEAVY_BOOTS + ITEM_ENCUMBRANCE_ARMOR_HEAVY_GLOVES + weight = ITEM_WEIGHT_ARMOR_HEAVY + ITEM_WEIGHT_ARMOR_HEAVY_BOOTS + ITEM_WEIGHT_ARMOR_HEAVY_GLOVES w_class = ITEMSIZE_HUGE armor_type = /datum/armor/centcom/deathsquad inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETIE|HIDEHOLSTER @@ -160,6 +163,8 @@ blood_overlay_type = "coat" inv_hide_flags = 0 body_cover_flags = UPPER_TORSO|ARMS + encumbrance = ITEM_ENCUMBRANCE_ARMOR_HEAVY + weight = ITEM_WEIGHT_ARMOR_HEAVY /obj/item/clothing/suit/armor/det_suit name = "armor" @@ -430,7 +435,8 @@ item_state = "flexitac" cold_protection = UPPER_TORSO|LOWER_TORSO min_cold_protection_temperature = T0C - 20 - slowdown = 0.3 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIUM + weight = ITEM_WEIGHT_ARMOR_MEDIUM /obj/item/clothing/suit/storage/vest/detective name = "detective armor vest" @@ -453,7 +459,8 @@ icon_state = "webvest" item_state_slots = list(SLOT_ID_RIGHT_HAND = "swat", SLOT_ID_LEFT_HAND = "swat") armor_type = /datum/armor/station/heavy - slowdown = 0.5 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_HEAVY + weight = ITEM_WEIGHT_ARMOR_HEAVY /obj/item/clothing/suit/storage/vest/heavy/officer name = "officer heavy armor vest" @@ -494,7 +501,8 @@ icon_state = "mercwebvest" item_state_slots = list(SLOT_ID_RIGHT_HAND = "swat", SLOT_ID_LEFT_HAND = "swat") armor_type = /datum/armor/station/combat - slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIUM + weight = ITEM_WEIGHT_ARMOR_MEDIUM /obj/item/clothing/suit/storage/vest/capcarapace name = "captain's carapace" @@ -566,9 +574,10 @@ w_class = ITEMSIZE_HUGE // Very bulky, very heavy. gas_transfer_coefficient = 0.90 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS - slowdown = 5 // If you're a tank you're gonna move like a tank. inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETIE|HIDEHOLSTER siemens_coefficient = 0 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY + ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_GLOVES + ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_BOOTS + weight = ITEM_WEIGHT_ARMOR_SUPERHEAVY + ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_GLOVES + ITEM_ENCUMBRANCE_ARMOR_SUPERHEAVY_BOOTS /obj/item/clothing/suit/armor/tdome body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS diff --git a/code/modules/clothing/suits/bio.dm b/code/modules/clothing/suits/bio.dm index 58777abcd83a..da3851ca62af 100644 --- a/code/modules/clothing/suits/bio.dm +++ b/code/modules/clothing/suits/bio.dm @@ -10,6 +10,7 @@ siemens_coefficient = 0.9 atom_flags = PHORONGUARD clothing_flags = CLOTHING_THICK_MATERIAL | ALLOW_SURVIVALFOOD + encumbrance /obj/item/clothing/suit/bio_suit name = "bio suit" @@ -19,7 +20,7 @@ gas_transfer_coefficient = 0.01 permeability_coefficient = 0.01 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS|HANDS|FEET - slowdown = 1.0 + weight = ITEM_WEIGHT_ARMOR_BIORAD_SUIT allowed = list(/obj/item/tank/emergency/oxygen,/obj/item/pen,/obj/item/flashlight/pen) armor_type = /datum/armor/general/biosuit inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER @@ -113,7 +114,7 @@ gas_transfer_coefficient = 0.01 permeability_coefficient = 0.01 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS|HANDS|FEET - slowdown = 1.0 + weight = ITEM_WEIGHT_ARMOR_BIORAD_SUIT allowed = list(/obj/item/tank/emergency/oxygen,/obj/item/pen,/obj/item/flashlight/pen) armor_type = /datum/armor/general/beekeeper inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER diff --git a/code/modules/clothing/suits/medieval_armor.dm b/code/modules/clothing/suits/medieval_armor.dm index 87e188ceb33c..19235b21c59c 100644 --- a/code/modules/clothing/suits/medieval_armor.dm +++ b/code/modules/clothing/suits/medieval_armor.dm @@ -50,7 +50,8 @@ armor_type = /datum/armor/general/medieval icon = 'icons/clothing/suit/armor/medieval/knight.dmi' icon_state = "knight" - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIEVAL_PLATE + weight = ITEM_WEIGHT_ARMOR_MEDIEVAL_PLATE inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETIE|HIDEHOLSTER body_cover_flags = UPPER_TORSO|LOWER_TORSO|ARMS|HANDS|LEGS|FEET worn_render_flags = WORN_RENDER_SLOT_ONE_FOR_ALL @@ -79,7 +80,8 @@ armor_type = /datum/armor/general/medieval/light icon = 'icons/clothing/suit/armor/medieval/bastard.dmi' icon_state = "bastard" - slowdown = 0 + weight = ITEM_WEIGHT_ARMOR_MEDIEVAL_CHAIN + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIEVAL_CHAIN /obj/item/clothing/suit/armor/medieval/paladin name = "elite paladin plate" @@ -87,7 +89,8 @@ armor_type = /datum/armor/general/medieval/mesh icon = 'icons/clothing/suit/armor/medieval/paladin.dmi' icon_state = "paladin" - slowdown = 0 + weight = ITEM_WEIGHT_ARMOR_MEDIEVAL_CHAIN + encumbrance = ITEM_ENCUMBRANCE_ARMOR_MEDIEVAL_CHAIN //Crusader stuff //Helmets diff --git a/code/modules/clothing/suits/utility.dm b/code/modules/clothing/suits/utility.dm index fe85ebfac383..41a5e2265d88 100644 --- a/code/modules/clothing/suits/utility.dm +++ b/code/modules/clothing/suits/utility.dm @@ -18,7 +18,8 @@ permeability_coefficient = 0.50 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS allowed = list(/obj/item/flashlight,/obj/item/tank/emergency/oxygen,/obj/item/extinguisher) - slowdown = 1.0 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_FIRE_SUIT + weight = ITEM_WEIGHT_ARMOR_FIRE_SUIT inv_hide_flags = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER clothing_flags = 0 heat_protection = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS @@ -31,14 +32,6 @@ /obj/item/clothing/suit/fire/firefighter icon_state = "firesuit" -/obj/item/clothing/suit/fire/heavy //Is this even used?? -S2- - name = "firesuit" - desc = "A suit that protects against extreme fire and heat." - //icon_state = "thermal" - item_state_slots = list(SLOT_ID_RIGHT_HAND = "black_suit", SLOT_ID_LEFT_HAND = "black_suit") - w_class = ITEMSIZE_LARGE//bulky item - slowdown = 1.5 - /* * Bomb protection */ @@ -50,6 +43,8 @@ inv_hide_flags = HIDEMASK|HIDEEARS|HIDEEYES|BLOCKHAIR body_cover_flags = HEAD|FACE|EYES siemens_coefficient = 0 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_BOMB_HELMET + weight = ITEM_WEIGHT_ARMOR_BOMB_HELMET /obj/item/clothing/suit/bomb_suit name = "bomb suit" @@ -58,7 +53,8 @@ w_class = ITEMSIZE_LARGE//bulky item gas_transfer_coefficient = 0.01 permeability_coefficient = 0.01 - slowdown = 2 + encumbrance = ITEM_ENCUMBRANCE_ARMOR_BOMB_SUIT + weight = ITEM_WEIGHT_ARMOR_BOMB_SUIT armor_type = /datum/armor/station/bomb inv_hide_flags = HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER heat_protection = UPPER_TORSO|LOWER_TORSO @@ -85,6 +81,8 @@ clothing_flags = CLOTHING_THICK_MATERIAL body_cover_flags = HEAD|FACE|EYES armor_type = /datum/armor/general/radsuit + weight = ITEM_WEIGHT_ARMOR_BIORAD_SUIT_HELMET + encumbrance = ITEM_ENCUMBRANCE_ARMOR_BIORAD_HELMET /obj/item/clothing/suit/radiation name = "Radiation suit" @@ -95,7 +93,8 @@ permeability_coefficient = 0.50 body_cover_flags = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS|HANDS|FEET allowed = list(/obj/item/flashlight,/obj/item/tank/emergency/oxygen,/obj/item/clothing/head/radiation,/obj/item/clothing/mask/gas) - slowdown = 1.5 + weight = ITEM_WEIGHT_ARMOR_BIORAD_SUIT armor_type = /datum/armor/general/radsuit inv_hide_flags = HIDEJUMPSUIT|HIDETAIL|HIDETIE|HIDEHOLSTER clothing_flags = CLOTHING_THICK_MATERIAL + encumbrance = ITEM_ENCUMBRANCE_ARMOR_BIORAD_SUIT diff --git a/code/modules/clothing/under/accessories/armor.dm b/code/modules/clothing/under/accessories/armor.dm index dbdadcb1fbd7..c0c12bc5cdbd 100644 --- a/code/modules/clothing/under/accessories/armor.dm +++ b/code/modules/clothing/under/accessories/armor.dm @@ -63,7 +63,8 @@ desc = "A collection of black pouches that can be attached to a plate carrier. Carries up to four items." icon_state = "lpouches" slots = 4 - slowdown = 0.25 + weight = ITEM_WEIGHT_STORAGE_POUCH_LARGE + encumbrance = ITEM_ENCUMBRANCE_STORAGE_POUCH_LARGE /obj/item/clothing/accessory/storage/pouches/large/blue desc = "A collection of blue pouches that can be attached to a plate carrier. Carries up to four items." @@ -162,14 +163,16 @@ name = "ballistic armor plate" desc = "A hefty silicon carbide armor plate with a layer of heavy tungsten, followed by a second coating of a polyurethane elastomeric to mitigate spalling from lower calibers as they're deflected. It's design is state of of the art when it comes to ballistics, and as a concequence the material is rather heavy, and is not as capable of dispersing laser fire as other armor varients. Fits within a plate carrier." icon_state = "armor_ballistic" - slowdown = 0.65 + weight = ITEM_WEIGHT_ARMOR_SPECIALIZED + encumbrance = ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED armor_type = /datum/armor/station/ballistic /obj/item/clothing/accessory/armor/armorplate/riot name = "riot armor plate" desc = "A synthetic mesh armor insert made of densely woven aromatic polyamide fibers, coated in malleable ballistic gelatin, and finally tight-jacketed with woven steel-polyethylene filaments. This provides excellent protection against low-velocity trauma, but most modern projectiles could tear through it with ease. Fits within a plate carrier." icon_state = "armor_riot" - slowdown = 0.65 + weight = ITEM_WEIGHT_ARMOR_SPECIALIZED + encumbrance = ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED armor_type = /datum/armor/station/riot siemens_coefficient = 0.5 @@ -177,7 +180,8 @@ name = "ablative armor plate" desc = "A highly reflective cobalt-chromium-tungsten alloy forms the seemingly jagged surface of the armor plate, which is adorned in perfectly cut and fitted glass prisms that form a smooth low-poly surface. When the ablative armor plate is working as designed, the glass prisms reflect laser fire inwards towards the innermost vertex for subsequent 'ablation', and sometimes reflection. There is a warning label on the back that warns you. It reads: Attempting to use this ablative armor plate to deflect ballistics and/or non-standard energy beams could result in 'rapid deconstruction' of the armor plate and its user. Fits within a plate carrier." icon_state = "armor_ablative" - slowdown = 0.65 + weight = ITEM_WEIGHT_ARMOR_SPECIALIZED + encumbrance = ITEM_ENCUMBRANCE_ARMOR_SPECIALIZED armor_type = /datum/armor/station/ablative siemens_coefficient = 0.2 diff --git a/code/modules/clothing/under/nanotrasen_vr.dm b/code/modules/clothing/under/nanotrasen_vr.dm index fa8d2a9217aa..273643cd59e0 100644 --- a/code/modules/clothing/under/nanotrasen_vr.dm +++ b/code/modules/clothing/under/nanotrasen_vr.dm @@ -52,4 +52,4 @@ icon_state = "webvest" item_state_slots = list(SLOT_ID_RIGHT_HAND = "swat", SLOT_ID_LEFT_HAND = "swat") armor_type = /datum/armor/station/tactical - slowdown = 0.5 + weight = ITEM_WEIGHT_ARMOR_LIGHT diff --git a/code/modules/detectivework/tools/rag.dm b/code/modules/detectivework/tools/rag.dm index dcb7dc037677..a6556eb4522d 100644 --- a/code/modules/detectivework/tools/rag.dm +++ b/code/modules/detectivework/tools/rag.dm @@ -23,7 +23,7 @@ possible_transfer_amounts = list(3) volume = 4 can_be_placed_into = null - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD atom_flags = OPENCONTAINER unacidable = 0 drop_sound = 'sound/items/drop/cloth.ogg' diff --git a/code/modules/detectivework/tools/scanner.dm b/code/modules/detectivework/tools/scanner.dm index d0f67ac5b7fa..dfe4070a7fb3 100644 --- a/code/modules/detectivework/tools/scanner.dm +++ b/code/modules/detectivework/tools/scanner.dm @@ -6,7 +6,7 @@ var/list/stored = list() w_class = ITEMSIZE_SMALL item_state = "electronic" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_BELT var/reveal_fingerprints = TRUE diff --git a/code/modules/economy/items/retail_scanner.dm b/code/modules/economy/items/retail_scanner.dm index d6729be41c36..511b95c6d559 100644 --- a/code/modules/economy/items/retail_scanner.dm +++ b/code/modules/economy/items/retail_scanner.dm @@ -3,7 +3,7 @@ desc = "Swipe your ID card to make purchases electronically." icon = 'icons/obj/device.dmi' icon_state = "retail_idle" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_BELT req_access = list(ACCESS_COMMAND_BRIDGE) w_class = ITEMSIZE_SMALL diff --git a/code/modules/fishing/fish.dm b/code/modules/fishing/fish.dm index 8d4a4068424a..8f96c42bf57f 100644 --- a/code/modules/fishing/fish.dm +++ b/code/modules/fishing/fish.dm @@ -14,8 +14,8 @@ /// Average size for this fish type in centimeters. Will be used as gaussian distribution with 20% deviation for fishing, bought fish are always standard size var/average_size = 50 /// Weight in grams - var/weight = 1000 - /// Average weight for this fish type in grams + var/fish_weight = 1000 + /// Average fish_weight for this fish type in grams var/average_weight = 1000 //? icon @@ -114,13 +114,13 @@ START_PROCESSING(SSobj, src) size = average_size - weight = average_weight + fish_weight = average_weight /obj/item/fish/examine(mob/user, dist) . = ..() - // All spacemen have magic eyes of fish weight perception until fish scale (get it?) is implemented. + // All spacemen have magic eyes of fish fish_weight perception until fish scale (get it?) is implemented. . += SPAN_NOTICE("It's [size] cm long.") - . += SPAN_NOTICE("It weighs [weight] g.") + . += SPAN_NOTICE("It weighs [fish_weight] g.") /obj/item/fish/proc/randomize_weight_and_size(modifier = 0) var/size_deviation = 0.2 * average_size @@ -129,7 +129,7 @@ var/weight_deviation = 0.2 * average_weight var/weight_mod = modifier * average_weight - weight = max(1,gaussian(average_weight + weight_mod, weight_deviation)) + fish_weight = max(1,gaussian(average_weight + weight_mod, weight_deviation)) /obj/item/fish/Moved(atom/old_loc, movement_dir, forced, list/old_locs, momentum_change) . = ..() diff --git a/code/modules/hardsuits/_rig.dm b/code/modules/hardsuits/_rig.dm index e7535c476e5f..4f2dc6574899 100644 --- a/code/modules/hardsuits/_rig.dm +++ b/code/modules/hardsuits/_rig.dm @@ -32,6 +32,11 @@ unacidable = 1 preserve_item = 1 + weight = ITEM_WEIGHT_BASELINE + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG + var/online_encumbrance + var/offline_encumbrance = ITEM_WEIGHT_LEGACY_RIG * 2 + // Activation /// activation state var/activation_state = RIG_ACTIVATION_OFF @@ -93,7 +98,6 @@ var/locked_down = 0 var/seal_delay = SEAL_DELAY - var/offline_slowdown = 3 // If the suit is deployed and unpowered, it sets slowdown to this. var/vision_restriction var/offline_vision_restriction = 1 // 0 - none, 1 - welder vision, 2 - blind. Maybe move this to helmets. var/airtight = 1 //If set, will adjust ALLOWINTERNALS flag and pressure protections on components. Otherwise it should leave them untouched. @@ -562,13 +566,10 @@ last_online = FALSE for(var/obj/item/hardsuit_module/module in installed_modules) module.deactivate() - slowdown = offline_slowdown + set_encumbrance(offline_encumbrance) if(istype(wearer)) if(is_activated()) - if (offline_slowdown < 3) - to_chat(wearer, "Your suit beeps stridently, and suddenly goes dead.") - else - to_chat(wearer, "Your suit beeps stridently, and suddenly you're wearing a leaden mass of metal and plastic composites instead of a powered suit.") + to_chat(wearer, "Your suit beeps stridently, and suddenly you're wearing a leaden mass of metal and plastic composites instead of a powered suit.") if(offline_vision_restriction == 1) to_chat(wearer, "The suit optics flicker and die, leaving you with restricted vision.") else if(offline_vision_restriction == 2) @@ -581,7 +582,8 @@ last_online = TRUE if(istype(wearer) && !wearer.wearing_rig) wearer.wearing_rig = src - slowdown = initial(slowdown) + sprint_slowdown_modifier + set_encumbrance(isnull(online_encumbrance)? initial(encumbrance) : online_encumbrance) + set_slowdown(initial(slowdown) + sprint_slowdown_modifier) if(cell && cell.charge > 0 && electrified > 0) electrified-- diff --git a/code/modules/hardsuits/modules/utility.dm b/code/modules/hardsuits/modules/utility.dm index 86d1f9d36926..107fa2e5c84b 100644 --- a/code/modules/hardsuits/modules/utility.dm +++ b/code/modules/hardsuits/modules/utility.dm @@ -647,7 +647,7 @@ to_chat(H, "You activate the suit's sprint mode.") - holder.slowdown -= sprint_speed + holder.set_slowdown(holder.slowdown - sprint_speed) holder.sprint_slowdown_modifier = -sprint_speed /obj/item/hardsuit_module/sprinter/deactivate() @@ -659,7 +659,7 @@ to_chat(H, "Your hardsuit returns to normal speed.") - holder.slowdown += sprint_speed + holder.set_slowdown(holder.slowdown + sprint_speed) holder.sprint_slowdown_modifier = 0 /obj/item/hardsuit_module/device/hand_defib diff --git a/code/modules/hardsuits/rig_pieces.dm b/code/modules/hardsuits/rig_pieces.dm index f06fd025829c..c4070fef4f73 100644 --- a/code/modules/hardsuits/rig_pieces.dm +++ b/code/modules/hardsuits/rig_pieces.dm @@ -16,6 +16,9 @@ min_pressure_protection = null damage_force = 3 // if you're headbutting someone with something meant to protect you from space... + weight = 0 + encumbrance = 0 + species_restricted = list( SPECIES_AKULA, SPECIES_ALRAUNE, @@ -50,6 +53,9 @@ heat_protection = HANDS cold_protection = HANDS + weight = 0 + encumbrance = 0 + species_restricted = list( SPECIES_AKULA, SPECIES_ALRAUNE, @@ -87,6 +93,9 @@ icon_base = null damage_force = 5 // if you're kicking someone with something meant to keep you locked on a hunk of metal... + weight = 0 + encumbrance = 0 + species_restricted = list( SPECIES_AKULA, SPECIES_ALRAUNE, @@ -125,7 +134,8 @@ inv_hide_flags = HIDEJUMPSUIT|HIDETAIL heat_protection = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS - slowdown = NONE + weight = 0 + encumbrance = 0 // Will reach 10 breach damage after 25 laser carbine blasts, 3 revolver hits, or ~1 PTR hit. // Completely immune to smg or sts hits. diff --git a/code/modules/hardsuits/suits/combat.dm b/code/modules/hardsuits/suits/combat.dm index 6f0dcf4db3fc..ae94a2f3f158 100644 --- a/code/modules/hardsuits/suits/combat.dm +++ b/code/modules/hardsuits/suits/combat.dm @@ -16,8 +16,8 @@ icon_state = "security_rig" suit_type = "combat hardsuit" armor_type = /datum/armor/hardsuit/combat - slowdown = 1 - offline_slowdown = 3 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY * 2 offline_vision_restriction = 1 helm_type = /obj/item/clothing/head/helmet/space/hardsuit/combat @@ -65,8 +65,8 @@ icon_state = "military_rig" suit_type = "military hardsuit" armor_type = /datum/armor/hardsuit/military - slowdown = 1 - offline_slowdown = 3 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY * 2 offline_vision_restriction = 1 allowed = list( /obj/item/flashlight, diff --git a/code/modules/hardsuits/suits/light.dm b/code/modules/hardsuits/suits/light.dm index da0613ba8262..59c745e9e3f4 100644 --- a/code/modules/hardsuits/suits/light.dm +++ b/code/modules/hardsuits/suits/light.dm @@ -14,9 +14,9 @@ allowed = list(/obj/item/gun,/obj/item/ammo_magazine,/obj/item/ammo_casing,/obj/item/melee/baton,/obj/item/handcuffs,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/cell) armor_type = /datum/armor/hardsuit/light emp_protection = 10 - slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 clothing_flags = CLOTHING_THICK_MATERIAL - offline_slowdown = 0 offline_vision_restriction = 0 chest_type = /obj/item/clothing/suit/space/hardsuit/light @@ -88,7 +88,6 @@ desc = "A unique suit of nano-enhanced armor designed for covert operations." icon_state = "ninja_rig" emp_protection = 40 //change this to 30 if too high. - slowdown = 0 chest_type = /obj/item/clothing/suit/space/hardsuit/light/ninja glove_type = /obj/item/clothing/gloves/gauntlets/hardsuit/light/ninja diff --git a/code/modules/hardsuits/suits/merc.dm b/code/modules/hardsuits/suits/merc.dm index 5dd2f90d1e99..72e78c098c70 100644 --- a/code/modules/hardsuits/suits/merc.dm +++ b/code/modules/hardsuits/suits/merc.dm @@ -17,8 +17,8 @@ icon_state = "merc_rig" suit_type = "crimson hardsuit" armor_type = /datum/armor/hardsuit/merc - slowdown = 1 - offline_slowdown = 3 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY * 2 offline_vision_restriction = 1 siemens_coefficient = 0.3 glove_type = /obj/item/clothing/gloves/gauntlets/hardsuit/eva diff --git a/code/modules/hardsuits/suits/species/protean.dm b/code/modules/hardsuits/suits/species/protean.dm index 4b3f412ec232..15e5eb356bfb 100644 --- a/code/modules/hardsuits/suits/species/protean.dm +++ b/code/modules/hardsuits/suits/species/protean.dm @@ -4,8 +4,8 @@ icon_state = "nanomachine_rig" armor_type = /datum/armor/hardsuit/protean siemens_coefficient = 0.5 - slowdown = 0 - offline_slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 seal_delay = 1 var/mob/living/carbon/human/myprotean initial_modules = list( diff --git a/code/modules/hardsuits/suits/species/unathi.dm b/code/modules/hardsuits/suits/species/unathi.dm index 90e804e7212d..6d0ca3859b96 100644 --- a/code/modules/hardsuits/suits/species/unathi.dm +++ b/code/modules/hardsuits/suits/species/unathi.dm @@ -5,8 +5,8 @@ icon_state = "breacher_hardsuit_cheap" armor_type = /datum/armor/hardsuit/breacher emp_protection = -20 - slowdown = 6 - offline_slowdown = 10 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY * 2 + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_HEAVY * 4 vision_restriction = 1 offline_vision_restriction = 2 siemens_coefficient = 0.75 diff --git a/code/modules/hardsuits/suits/species/vox.dm b/code/modules/hardsuits/suits/species/vox.dm index 900e92d94fec..ce02abf6e3e8 100644 --- a/code/modules/hardsuits/suits/species/vox.dm +++ b/code/modules/hardsuits/suits/species/vox.dm @@ -7,7 +7,6 @@ atom_flags = PHORONGUARD clothing_flags = CLOTHING_THICK_MATERIAL siemens_coefficient = 0.2 - offline_slowdown = 5 allowed = list( /obj/item/gun, /obj/item/flashlight, diff --git a/code/modules/hardsuits/suits/station/cargo.dm b/code/modules/hardsuits/suits/station/cargo.dm index df54f98bd0df..0ec49ab57534 100644 --- a/code/modules/hardsuits/suits/station/cargo.dm +++ b/code/modules/hardsuits/suits/station/cargo.dm @@ -4,8 +4,6 @@ desc = "A heavy, powerful hardsuit used by construction crews and mining corporations." icon_state = "engineering_rig" armor_type = /datum/armor/hardsuit/industrial - slowdown = 1 - offline_slowdown = 10 offline_vision_restriction = 2 emp_protection = -20 siemens_coefficient= 0.75 diff --git a/code/modules/hardsuits/suits/station/engineering.dm b/code/modules/hardsuits/suits/station/engineering.dm index 6b5424544aa2..7f9a19eb7c53 100644 --- a/code/modules/hardsuits/suits/station/engineering.dm +++ b/code/modules/hardsuits/suits/station/engineering.dm @@ -4,8 +4,8 @@ desc = "A light hardsuit for repairs and maintenance to the outside of habitats and vessels." icon_state = "eva_rig" armor_type = /datum/armor/hardsuit/eva - slowdown = 0 - offline_slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 offline_vision_restriction = 1 siemens_coefficient= 0.75 seal_delay = 24 //Should be slightly faster than other hardsuits, giving Engineering faster response time for emergencies. @@ -57,8 +57,8 @@ desc = "An advanced voidsuit that protects against hazardous, low pressure environments. Shines with a high polish." icon_state = "ce_rig" armor_type = /datum/armor/hardsuit/ce - slowdown = 0 - offline_slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 offline_vision_restriction = 0 siemens_coefficient= 0.75 rigsuit_max_pressure = 20 * ONE_ATMOSPHERE // Max pressure the hardsuit protects against when sealed @@ -97,7 +97,7 @@ siemens_coefficient = 0 /obj/item/clothing/shoes/magboots/hardsuit/ce - slowdown_on = 0 + encumbrance_on = ITEM_ENCUMBRANCE_SHOES_MAGBOOTS_PULSE_ADVANCED /obj/item/hardsuit/ce/equipped initial_modules = list( diff --git a/code/modules/hardsuits/suits/station/medical.dm b/code/modules/hardsuits/suits/station/medical.dm index c5e8403af5c7..95e83f2eeb4d 100644 --- a/code/modules/hardsuits/suits/station/medical.dm +++ b/code/modules/hardsuits/suits/station/medical.dm @@ -4,8 +4,8 @@ desc = "A durable suit designed for medical rescue in high risk areas." icon_state = "medical_rig" armor_type = /datum/armor/hardsuit/medical - slowdown = 1 - offline_vision_restriction = 1 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 siemens_coefficient= 0.75 helm_type = /obj/item/clothing/head/helmet/space/hardsuit/medical diff --git a/code/modules/hardsuits/suits/station/misc.dm b/code/modules/hardsuits/suits/station/misc.dm index 83dca958b893..904a6bb22508 100644 --- a/code/modules/hardsuits/suits/station/misc.dm +++ b/code/modules/hardsuits/suits/station/misc.dm @@ -5,8 +5,8 @@ icon_state = "internalaffairs_rig" armor_type = /datum/armor/none siemens_coefficient = 0.9 - slowdown = 0 - offline_slowdown = 0 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 offline_vision_restriction = 0 allowed = list( diff --git a/code/modules/hardsuits/suits/station/science.dm b/code/modules/hardsuits/suits/station/science.dm index 55446554860c..f4320fc9592d 100644 --- a/code/modules/hardsuits/suits/station/science.dm +++ b/code/modules/hardsuits/suits/station/science.dm @@ -4,8 +4,8 @@ desc = "An Anomalous Material Interaction hardsuit that protects against the strangest energies the universe can throw at it." icon_state = "science_rig" armor_type = /datum/armor/hardsuit/ami - slowdown = 1 - offline_vision_restriction = 1 + encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT + offline_encumbrance = ITEM_ENCUMBRANCE_LEGACY_RIG_LIGHT * 2 siemens_coefficient= 0.75 helm_type = /obj/item/clothing/head/helmet/space/hardsuit/hazmat diff --git a/code/modules/hardsuits/suits/station/security.dm b/code/modules/hardsuits/suits/station/security.dm index 1f1b17fe1133..019155c5fd2e 100644 --- a/code/modules/hardsuits/suits/station/security.dm +++ b/code/modules/hardsuits/suits/station/security.dm @@ -4,8 +4,6 @@ desc = "A Security hardsuit designed for prolonged EVA in dangerous environments." icon_state = "hazard_rig" armor_type = /datum/armor/hardsuit/hazard - slowdown = 1 - offline_slowdown = 3 offline_vision_restriction = 1 siemens_coefficient= 0.7 diff --git a/code/modules/hydroponics/trays/tray_reagents.dm b/code/modules/hydroponics/trays/tray_reagents.dm index 851842f309fd..751d40acbfd5 100644 --- a/code/modules/hydroponics/trays/tray_reagents.dm +++ b/code/modules/hydroponics/trays/tray_reagents.dm @@ -1,7 +1,7 @@ /obj/item/plantspray icon = 'icons/obj/hydroponics_machines.dmi' item_state = "spraycan" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_BELT throw_force = 4 w_class = ITEMSIZE_SMALL diff --git a/code/modules/integrated_electronics/core/assemblies.dm b/code/modules/integrated_electronics/core/assemblies.dm index 2f4f13d4d817..143735a609e6 100644 --- a/code/modules/integrated_electronics/core/assemblies.dm +++ b/code/modules/integrated_electronics/core/assemblies.dm @@ -7,7 +7,7 @@ w_class = ITEMSIZE_SMALL icon = 'icons/obj/integrated_electronics/electronic_setups.dmi' icon_state = "setup_small" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD show_messages = TRUE datum_flags = DF_USE_TAG var/list/assembly_components = list() diff --git a/code/modules/integrated_electronics/core/detailer.dm b/code/modules/integrated_electronics/core/detailer.dm index e61b6cf9620d..85046f6c44d1 100644 --- a/code/modules/integrated_electronics/core/detailer.dm +++ b/code/modules/integrated_electronics/core/detailer.dm @@ -3,7 +3,7 @@ desc = "A combination autopainter and flash anodizer designed to give electronic assemblies a colorful, wear-resistant finish." icon = 'icons/obj/integrated_electronics/electronic_tools.dmi' icon_state = "detailer" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD w_class = ITEMSIZE_SMALL var/detail_color = COLOR_ASSEMBLY_WHITE var/list/color_list = list( diff --git a/code/modules/materials/material_sheets.dm b/code/modules/materials/material_sheets.dm index 7ce1eaede2bc..11508f4bdbab 100644 --- a/code/modules/materials/material_sheets.dm +++ b/code/modules/materials/material_sheets.dm @@ -287,7 +287,6 @@ apply_colour = TRUE /obj/item/stack/material/supermatter/proc/update_mass() // Due to how dangerous they can be, the item will get heavier and larger the more are in the stack. - slowdown = amount / 10 w_class = min(5, round(amount / 10) + 1) throw_range = round(amount / 7) + 1 diff --git a/code/modules/mining/vertibore.dm b/code/modules/mining/vertibore.dm index bfc0b32e6fc9..ab7e20091ed5 100644 --- a/code/modules/mining/vertibore.dm +++ b/code/modules/mining/vertibore.dm @@ -3,9 +3,7 @@ name = "portable shaft excavation device" desc = "A heavily modified shaft bore utilizing phorogenic blasts to tunnel vertically through rock. Much faster than a large industrial drill unit, but is very resource- and power-intensive." description_fluff = "A phoron bore used for rapidly digging through rock that has been modified to allow it to fire straight down at a much higher power. However, this has resulted in a loss of power and resource efficiency, compactness, and modularity as the proprietary capacitor and manipulator cannot be swapped." - w_class = ITEMSIZE_NO_CONTAINER //haha harold can't powergame itemsize with BoHs if it doesn't even fit in a BoH - //he's just going to locker it isn't he - slowdown = 1 //chonker bore is heavy boy + w_class = ITEMSIZE_NO_CONTAINER icon = 'icons/obj/mining.dmi' icon_state = "vertibore" item_state = "vertibore" diff --git a/code/modules/mob/grab.dm b/code/modules/mob/grab.dm index 341b22107842..52c8362f2245 100644 --- a/code/modules/mob/grab.dm +++ b/code/modules/mob/grab.dm @@ -78,7 +78,7 @@ name = "grab" icon = 'icons/mob/screen1.dmi' icon_state = "reinforce" - item_flags = ITEM_ABSTRACT | ITEM_DROPDEL + item_flags = ITEM_ABSTRACT | ITEM_DROPDEL | ITEM_ENCUMBERS_WHILE_HELD atom_flags = ATOM_ABSTRACT drop_sound = null pickup_sound = null diff --git a/code/modules/mob/inventory.dm b/code/modules/mob/inventory.dm index 866f9c3df63a..42fce6a6208e 100644 --- a/code/modules/mob/inventory.dm +++ b/code/modules/mob/inventory.dm @@ -57,3 +57,11 @@ // todo: actual flag like BUCKLING_IS_CONSIDERED_RESTRICTING or something if(buckled?.buckle_flags & (BUCKLING_NO_DEFAULT_RESIST | BUCKLING_NO_DEFAULT_UNBUCKLE)) unbuckle(BUCKLE_OP_FORCE) + +//* Carry Weight + +/mob/proc/update_carry_slowdown() + return + +/mob/proc/update_item_slowdown() + return diff --git a/code/modules/mob/inventory/items.dm b/code/modules/mob/inventory/items.dm index 2abb30e06e34..25c23a27d510 100644 --- a/code/modules/mob/inventory/items.dm +++ b/code/modules/mob/inventory/items.dm @@ -47,6 +47,16 @@ playsound(src, equip_sound, 30, ignore_walls = FALSE) user.update_inv_hands() + // register carry + if(isliving(user)) + var/mob/living/L = user + if((slot == SLOT_ID_HANDS)? (item_flags & ITEM_ENCUMBERS_WHILE_HELD) : !(item_flags & ITEM_ENCUMBERS_ONLY_HELD)) + if(flat_encumbrance) + L.recalculate_carry() + else + encumbrance_registered = get_encumbrance() + L.adjust_current_carry_encumbrance(encumbrance_registered) + /** * called when an item is unequipped from inventory or moved around in inventory * @@ -69,6 +79,15 @@ if(!(flags & INV_OP_DIRECTLY_DROPPING) && (slot != SLOT_ID_HANDS) && unequip_sound) playsound(src, unequip_sound, 30, ignore_walls = FALSE) + // clear carry + if(isliving(user)) + var/mob/living/L = user + if(flat_encumbrance) + L.recalculate_carry() + else if(!isnull(encumbrance_registered)) + L.adjust_current_carry_encumbrance(-encumbrance_registered) + encumbrance_registered = null + /** * called when a mob drops an item * @@ -101,6 +120,12 @@ if(zoom) zoom() //binoculars, scope, etc + // clear carry + if(isliving(user)) + var/mob/living/L = user + L.adjust_current_carry_weight(-weight_registered) + weight_registered = null + // close context menus context_close() @@ -123,11 +148,11 @@ if(isturf(oldLoc) && !(flags & (INV_OP_SILENT | INV_OP_DIRECTLY_EQUIPPING))) playsound(src, pickup_sound, 20, ignore_walls = FALSE) -/** - * get the slowdown we incur when we're worn - */ -/obj/item/proc/get_equipment_speed_mod() - return slowdown + // register carry + weight_registered = get_weight() + if(isliving(user)) + var/mob/living/L = user + L.adjust_current_carry_weight(weight_registered) /** * update our worn icon if we can @@ -320,11 +345,20 @@ /** * checks if we're in inventory. if so, returns mob we're in + * * **hands count** */ /obj/item/proc/is_in_inventory(include_hands) return (worn_slot && ((worn_slot != SLOT_ID_HANDS) || include_hands)) && worn_mob() +/** + * checks if we're held in hand + * + * if so, returns mob we're in + */ +/obj/item/proc/is_held() + return (worn_slot == SLOT_ID_HANDS)? worn_mob() : null + /** * checks if we're worn. if so, return mob we're in * diff --git a/code/modules/mob/living/carbon/cpr.dm b/code/modules/mob/living/carbon/cpr.dm index 644f68539fe1..3aedb9610009 100644 --- a/code/modules/mob/living/carbon/cpr.dm +++ b/code/modules/mob/living/carbon/cpr.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + // someday, we'll combine /carbon and /human to /complex // let me believe....... diff --git a/code/modules/mob/living/carbon/human/inventory.dm b/code/modules/mob/living/carbon/human/inventory.dm index 2b73b38b1804..32d7e8a521be 100644 --- a/code/modules/mob/living/carbon/human/inventory.dm +++ b/code/modules/mob/living/carbon/human/inventory.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + /mob/living/carbon/human/_slot_by_item(obj/item/I) if(wear_suit == I) return SLOT_ID_SUIT @@ -267,79 +270,3 @@ if(!slot_meta) return FALSE return !(slot_meta.inventory_slot_flags & INV_SLOT_IS_INVENTORY) || !species || (id in species.hud.gear) - -//! old stuff below - -/mob/living/carbon/human/verb/quick_equip() - set name = "quick-equip" - set hidden = 1 - - attempt_smart_equip() - -//! old behaviors that i can't be assed to rewrite for now - -/mob/living/carbon/human/proc/smart_equipbag() // take most recent item out of bag or place held item in bag - if(incapacitated()) - return - var/obj/item/thing = get_active_held_item() - var/obj/item/equipped_back = item_by_slot(SLOT_ID_BACK) - if(!equipped_back) // We also let you equip a backpack like this - if(!thing) - to_chat(src, "You have no backpack to take something out of!") - return - if(equip_to_slot_if_possible(thing, SLOT_ID_BACK)) - update_inv_hands() - return - if(!istype(equipped_back, /obj/item/storage)) // not a storage item - if(!thing) - equipped_back.attack_hand(src) - else - to_chat(src, "You can't fit anything in!") - return - if(thing) // put thing in backpack - var/obj/item/storage/S = equipped_back - if(!S.can_be_inserted(thing)) - to_chat(src, "You can't fit anything in!") - return - S.handle_item_insertion(thing, src) - return - if(!equipped_back.contents.len) // nothing to take out - to_chat(src, "There's nothing in your backpack to take out!") - return - var/obj/item/stored = equipped_back.contents[equipped_back.contents.len] - if(!stored || stored.on_found(src)) - return - stored.attack_hand(src) // take out thing from backpack - -/mob/living/carbon/human/proc/smart_equipbelt() // put held thing in belt or take most recent item out of belt - if(incapacitated()) - return - var/obj/item/thing = get_active_held_item() - var/obj/item/equipped_belt = item_by_slot(SLOT_ID_BELT) - if(!equipped_belt) // We also let you equip a belt like this - if(!thing) - to_chat(src, "You have no belt to take something out of!") - return - if(equip_to_slot_if_possible(thing, SLOT_ID_BELT)) - update_inv_hands() - return - if(!istype(equipped_belt, /obj/item/storage)) // not a storage item - if(!thing) - equipped_belt.attack_hand(src) - else - to_chat(src, "You can't fit anything in!") - return - if(thing) // put thing in belt - var/obj/item/storage/S = equipped_belt - if(!S.can_be_inserted(thing)) - to_chat(src, "You can't fit anything in!") - return - S.handle_item_insertion(thing, src) - return - if(!equipped_belt.contents.len) // nothing to take out - to_chat(src, "There's nothing in your belt to take out!") - return - var/obj/item/stored = equipped_belt.contents[equipped_belt.contents.len] - if(!stored || stored.on_found(src)) - return - stored.attack_hand(src) // take out thing from belt diff --git a/code/modules/mob/living/carbon/human/inventory_legacy.dm b/code/modules/mob/living/carbon/human/inventory_legacy.dm new file mode 100644 index 000000000000..60294ffee85f --- /dev/null +++ b/code/modules/mob/living/carbon/human/inventory_legacy.dm @@ -0,0 +1,75 @@ +//! old stuff below + +/mob/living/carbon/human/verb/quick_equip() + set name = "quick-equip" + set hidden = 1 + + attempt_smart_equip() + +//! old behaviors that i can't be assed to rewrite for now + +/mob/living/carbon/human/proc/smart_equipbag() // take most recent item out of bag or place held item in bag + if(incapacitated()) + return + var/obj/item/thing = get_active_held_item() + var/obj/item/equipped_back = item_by_slot(SLOT_ID_BACK) + if(!equipped_back) // We also let you equip a backpack like this + if(!thing) + to_chat(src, "You have no backpack to take something out of!") + return + if(equip_to_slot_if_possible(thing, SLOT_ID_BACK)) + update_inv_hands() + return + if(!istype(equipped_back, /obj/item/storage)) // not a storage item + if(!thing) + equipped_back.attack_hand(src) + else + to_chat(src, "You can't fit anything in!") + return + if(thing) // put thing in backpack + var/obj/item/storage/S = equipped_back + if(!S.can_be_inserted(thing)) + to_chat(src, "You can't fit anything in!") + return + S.handle_item_insertion(thing, src) + return + if(!equipped_back.contents.len) // nothing to take out + to_chat(src, "There's nothing in your backpack to take out!") + return + var/obj/item/stored = equipped_back.contents[equipped_back.contents.len] + if(!stored || stored.on_found(src)) + return + stored.attack_hand(src) // take out thing from backpack + +/mob/living/carbon/human/proc/smart_equipbelt() // put held thing in belt or take most recent item out of belt + if(incapacitated()) + return + var/obj/item/thing = get_active_held_item() + var/obj/item/equipped_belt = item_by_slot(SLOT_ID_BELT) + if(!equipped_belt) // We also let you equip a belt like this + if(!thing) + to_chat(src, "You have no belt to take something out of!") + return + if(equip_to_slot_if_possible(thing, SLOT_ID_BELT)) + update_inv_hands() + return + if(!istype(equipped_belt, /obj/item/storage)) // not a storage item + if(!thing) + equipped_belt.attack_hand(src) + else + to_chat(src, "You can't fit anything in!") + return + if(thing) // put thing in belt + var/obj/item/storage/S = equipped_belt + if(!S.can_be_inserted(thing)) + to_chat(src, "You can't fit anything in!") + return + S.handle_item_insertion(thing, src) + return + if(!equipped_belt.contents.len) // nothing to take out + to_chat(src, "There's nothing in your belt to take out!") + return + var/obj/item/stored = equipped_belt.contents[equipped_belt.contents.len] + if(!stored || stored.on_found(src)) + return + stored.attack_hand(src) // take out thing from belt diff --git a/code/modules/mob/living/carbon/human/movement.dm b/code/modules/mob/living/carbon/human/movement.dm index 55ba626e7235..33450774b5a8 100644 --- a/code/modules/mob/living/carbon/human/movement.dm +++ b/code/modules/mob/living/carbon/human/movement.dm @@ -84,38 +84,15 @@ var/turf/T = get_turf(src) tally += calculate_turf_slowdown(T, direct) - // Item related slowdown. - var/item_tally = calculate_item_encumbrance() - if(item_tally > 0) // is it greater than 0? run the wacky shit - item_tally *= species.item_slowdown_mod // your item slowdown kicks in, but - if(!(CE_SPEEDBOOST in chem_effects)) // hyperzine users ignore item slow - tally += item_tally // no hyperzine? slowed down by things - else - tally += item_tally // if it's less than 0 that means it speeds you up, theoretically, so, hit it + if(CE_SPEEDBOOST in chem_effects) + tally -= 0.5 if(CE_SLOWDOWN in chem_effects) if (tally >= 0 ) tally = (tally + tally/4) //Add a quarter of penalties on top. tally += chem_effects[CE_SLOWDOWN] - return max(HUMAN_LOWEST_SLOWDOWN, tally + . + config_legacy.human_delay) // Minimum return should be the same as force_max_speed - -// This calculates the amount of slowdown to receive from items worn. This does NOT include species modifiers. -// It is in a seperate place to avoid an infinite loop situation with dragging mobs dragging each other. -// Also its nice to have these things seperated. -/mob/living/carbon/human/proc/calculate_item_encumbrance() - if(!buckled && shoes) // Shoes can make you go faster. - . += shoes.slowdown - - // Loop through some slots, and add up their slowdowns. - // Includes slots which can provide armor, the back slot, and suit storage. - for(var/obj/item/I in list(wear_suit, w_uniform, back, gloves, head, s_store)) - . += I.slowdown - - // Hands are also included, to make the 'take off your armor instantly and carry it with you to go faster' trick no longer viable. - // This is done seperately to disallow negative numbers (so you can't hold shoes in your hands to go faster). - for(var/obj/item/I in list(r_hand, l_hand)) - . += max(I.slowdown, 0) + . = max(HUMAN_LOWEST_SLOWDOWN, tally + . + config_legacy.human_delay) // Minimum return should be the same as force_max_speed // Similar to above, but for turf slowdown. /mob/living/carbon/human/proc/calculate_turf_slowdown(turf/T, direct) diff --git a/code/modules/mob/living/carbon/human/traits/negative.dm b/code/modules/mob/living/carbon/human/traits/negative.dm index 03536c3aa4d6..393a3718085d 100644 --- a/code/modules/mob/living/carbon/human/traits/negative.dm +++ b/code/modules/mob/living/carbon/human/traits/negative.dm @@ -10,18 +10,6 @@ cost = -3 var_changes = list("slowdown" = 1.0) -/datum/trait/negative/weakling - name = "Weakling" - desc = "Causes heavy equipment to slow you down more when carried." - cost = -1 - var_changes = list("item_slowdown_mod" = 1.5) - -/datum/trait/negative/weakling_plus - name = "Major Weakling" - desc = "Allows you to carry heavy equipment with much more slowdown." - cost = -2 - var_changes = list("item_slowdown_mod" = 2.0) - /datum/trait/negative/endurance_low name = "Low Endurance" desc = "Reduces your maximum total hitpoints to 75." diff --git a/code/modules/mob/living/carbon/human/traits/positive.dm b/code/modules/mob/living/carbon/human/traits/positive.dm index be9956f3b67e..5a1e05670cda 100644 --- a/code/modules/mob/living/carbon/human/traits/positive.dm +++ b/code/modules/mob/living/carbon/human/traits/positive.dm @@ -3,19 +3,6 @@ desc = "Allows you to move faster on average than baseline." cost = 2 var_changes = list("slowdown" = -0.2) - excludes = list(/datum/trait/positive/hardy, /datum/trait/positive/hardy_plus) - -/datum/trait/positive/hardy - name = "Hardy" - desc = "Allows you to carry heavy equipment with less slowdown." - cost = 1 - var_changes = list("item_slowdown_mod" = 0.5) - -/datum/trait/positive/hardy_plus - name = "Major Hardy" - desc = "Allows you to carry heavy equipment with almost no slowdown." - cost = 2 - var_changes = list("item_slowdown_mod" = 0.25) /datum/trait/positive/endurance_plus name = "Better Endurance" diff --git a/code/modules/mob/living/carbon/inventory.dm b/code/modules/mob/living/carbon/inventory.dm index 063704e5b4f8..1e404c1f17d0 100644 --- a/code/modules/mob/living/carbon/inventory.dm +++ b/code/modules/mob/living/carbon/inventory.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + /mob/living/carbon/_slot_by_item(obj/item/I) if(handcuffed == I) return SLOT_ID_HANDCUFFED @@ -44,3 +47,26 @@ SLOT_ID_HANDCUFFED, SLOT_ID_LEGCUFFED ) + +//* carry weight + +/mob/living/carbon/carry_weight_to_penalty(amount) + // https://www.desmos.com/calculator/5o2cx7grbo + var/carry_strength = physiology.carry_strength + physiology.carry_weight_add + if(amount < carry_strength) + return 1 + var/carry_factor = physiology.carry_factor * physiology.carry_weight_factor + return (1 / (1 + NUM_E ** (carry_factor * (CARRY_WEIGHT_SCALING / carry_strength) * (amount - carry_strength + CARRY_WEIGHT_BIAS * carry_strength) - 5))) * CARRY_WEIGHT_ASYMPTOTE + CARRY_WEIGHT_ASYMPTOTE + +/mob/living/carbon/carry_encumbrance_to_penalty(amount) + // https://www.desmos.com/calculator/5o2cx7grbo + var/carry_strength = physiology.carry_strength + if(amount < carry_strength) + return 1 + var/carry_factor = physiology.carry_factor + return (1 / (1 + NUM_E ** (carry_factor * (CARRY_WEIGHT_SCALING / carry_strength) * (amount - carry_strength + CARRY_WEIGHT_BIAS * carry_strength) - 5))) * (1 - CARRY_WEIGHT_ASYMPTOTE) + CARRY_WEIGHT_ASYMPTOTE + +/mob/living/carbon/get_item_slowdown() + . = ..() + if(!isnull(species)) + . *= species.item_slowdown_mod diff --git a/code/modules/mob/living/carbon/perspective.dm b/code/modules/mob/living/carbon/perspective.dm index d010e0257585..df90da7aebec 100644 --- a/code/modules/mob/living/carbon/perspective.dm +++ b/code/modules/mob/living/carbon/perspective.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + //? Darksight /mob/living/carbon/innate_vision() diff --git a/code/modules/mob/living/inventory.dm b/code/modules/mob/living/inventory.dm index 7369dc3608c3..9402e61f59ff 100644 --- a/code/modules/mob/living/inventory.dm +++ b/code/modules/mob/living/inventory.dm @@ -255,3 +255,94 @@ /mob/living/has_free_hand() return !l_hand || !r_hand + +//* carry weight + +// don't call this you shouldn't need to +/mob/living/update_carry_slowdown() + recalculate_carry() + +/mob/living/proc/recalculate_carry(update = TRUE) + var/tally_weight = 0 + var/tally_encumbrance = 0 + var/flat_encumbrance = 0 + for(var/obj/item/I as anything in get_equipped_items()) + tally_weight += (I.weight_registered = I.get_weight()) + if(I.is_held()) + if(!(I.item_flags & ITEM_ENCUMBERS_WHILE_HELD)) + I.encumbrance_registered = null + continue + else + if(I.item_flags & ITEM_ENCUMBERS_ONLY_HELD) + I.encumbrance_registered = null + continue + var/encumbrance = I.get_encumbrance() + tally_encumbrance += encumbrance + I.encumbrance_registered = encumbrance + flat_encumbrance = max(flat_encumbrance, I.get_flat_encumbrance()) + cached_carry_weight = tally_weight + cached_carry_encumbrance = tally_encumbrance + cached_carry_flat_encumbrance = flat_encumbrance + if(update) + update_carry() + +/mob/living/proc/adjust_current_carry_weight(amount) + if(!amount) + return + cached_carry_weight += amount + update_carry() + +/mob/living/proc/adjust_current_carry_encumbrance(amount) + if(!amount) + return + cached_carry_encumbrance += amount + update_carry() + +/** + * @return penalty as speed multiplier from 0 to 1 + */ +/mob/living/proc/carry_weight_to_penalty(amount) + return 1 + +/** + * @return penalty as speed multiplier from 0 to 1 + */ +/mob/living/proc/carry_encumbrance_to_penalty(amount) + return 1 + +/mob/living/proc/update_carry() + var/weight_penalty = carry_weight_to_penalty(cached_carry_weight) + var/encumbrance_penalty = carry_encumbrance_to_penalty(cached_carry_encumbrance) + var/flat_encumbrance_penalty = carry_encumbrance_to_penalty(cached_carry_flat_encumbrance) + var/penalty = min(weight_penalty, encumbrance_penalty, flat_encumbrance_penalty) + switch(round(min(weight_penalty, encumbrance_penalty) * 100)) + if(85 to 99) + throw_alert("encumbered", /atom/movable/screen/alert/encumbered/minor) + if(65 to 84) + throw_alert("encumbered", /atom/movable/screen/alert/encumbered/moderate) + if(36 to 64) + throw_alert("encumbered", /atom/movable/screen/alert/encumbered/severe) + if(0 to 35) + throw_alert("encumbered", /atom/movable/screen/alert/encumbered/extreme) + else + clear_alert("encumbered") + /// do not slow down below 10% of base + penalty = max(penalty, 0.1) + if(penalty) + add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/mob_inventory_carry, params = list(MOVESPEED_PARAM_MULTIPLY_SPEED = penalty)) + else + remove_movespeed_modifier(/datum/movespeed_modifier/mob_inventory_carry) + +//* hard movespeed slowdown + +/mob/living/update_item_slowdown() + var/tally = get_item_slowdown() + if(tally) + add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/mob_item_slowdown, params = list(MOVESPEED_PARAM_DELAY_MOD = tally)) + else + remove_movespeed_modifier(/datum/movespeed_modifier/mob_item_slowdown) + +/mob/living/proc/get_item_slowdown() + . = 0 + for(var/obj/item/I as anything in get_equipped_items()) + . += I.slowdown diff --git a/code/modules/mob/living/living_defines.dm b/code/modules/mob/living/living_defines.dm index e4a55f48a387..9281567fb6f7 100644 --- a/code/modules/mob/living/living_defines.dm +++ b/code/modules/mob/living/living_defines.dm @@ -1,9 +1,8 @@ /** - * # /mob/living + * living mobs * - * mob/living is the base type of mobs that have health - * there's probably a better explanation we can type someday but for that, uh - * yeah. + * living mobs are the subtype of mobs that are semantically what you'd think of as a true mob + * health, inventory carry weight simulations, etc. */ /mob/living see_invisible = SEE_INVISIBLE_LIVING @@ -127,6 +126,15 @@ /// Set to TRUE to enable the use of hands and the hands hud var/has_hands = FALSE + //* Carry Weight + // todo: put all this on /datum/inventory after hand refactor + /// cached carry weight of all items + var/cached_carry_weight = 0 + /// cached encumbrance of all items + var/cached_carry_encumbrance = 0 + /// highest flat encumbrance of all items + var/cached_carry_flat_encumbrance = 0 + //? movement /// are we currently pushing (or trying to push) (or otherwise inside Bump() handling that deals with this crap) another atom? var/pushing_bumped_atom = FALSE diff --git a/code/modules/mob/living/silicon/robot/dogborg/dog_modules_vr.dm b/code/modules/mob/living/silicon/robot/dogborg/dog_modules_vr.dm index 592dad83d961..8d56d771c268 100644 --- a/code/modules/mob/living/silicon/robot/dogborg/dog_modules_vr.dm +++ b/code/modules/mob/living/silicon/robot/dogborg/dog_modules_vr.dm @@ -57,7 +57,7 @@ icon_state = "nose" desc = "The BOOP module, a simple reagent and atmosphere sniffer." damage_force = 0 - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD throw_force = 0 attack_verb = list("nuzzled", "nosed", "booped") w_class = ITEMSIZE_TINY @@ -181,7 +181,7 @@ icon = 'icons/mob/dogborg_vr.dmi' icon_state = "synthtongue" hitsound = 'sound/effects/attackblob.ogg' - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/emagged = 0 var/datum/matter_synth/water = null @@ -300,7 +300,7 @@ desc = "Toggles floor scrubbing." icon = 'icons/mob/dogborg_vr.dmi' icon_state = "scrub0" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/enabled = FALSE /obj/item/pupscrubber/attack_self(mob/user) @@ -379,7 +379,7 @@ icon_state = "pounce" desc = "Leap at your target to momentarily stun them." damage_force = 0 - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD throw_force = 0 /obj/item/dogborg/pounce/attack_self(mob/user) diff --git a/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper_vr.dm b/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper_vr.dm index 60c78dbc91cd..1a7e1589504b 100644 --- a/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper_vr.dm +++ b/code/modules/mob/living/silicon/robot/dogborg/dog_sleeper_vr.dm @@ -5,7 +5,7 @@ icon = 'icons/mob/dogborg_vr.dmi' icon_state = "sleeper" w_class = ITEMSIZE_TINY - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/mob/living/carbon/patient = null var/mob/living/silicon/robot/hound = null var/inject_amount = 10 diff --git a/code/modules/mob/mob.dm b/code/modules/mob/mob.dm index 70777dce0d63..f31ebce84b37 100644 --- a/code/modules/mob/mob.dm +++ b/code/modules/mob/mob.dm @@ -59,6 +59,9 @@ status_effects = null // mob lists mob_list_unregister(stat) + // physiology + QDEL_NULL(physiology) + physiology_modifiers = null // movespeed movespeed_modification = null // actionspeed diff --git a/code/modules/mob/mob_defines.dm b/code/modules/mob/mob_defines.dm index 1bdeba507663..edbd657f2a8e 100644 --- a/code/modules/mob/mob_defines.dm +++ b/code/modules/mob/mob_defines.dm @@ -1,3 +1,6 @@ +/** + * base BYOND type for an actor, if the game world is a scene. + */ /mob datum_flags = DF_USE_TAG density = 1 @@ -54,6 +57,9 @@ var/list/movespeed_mod_immunities //Lazy list, see mob_movespeed.dm /// The calculated mob speed slowdown based on the modifiers list var/cached_multiplicative_slowdown + /// cached legacy movespeed multiplier -_- + // todo: remove + var/cached_movespeed_multiply /// Next world.time we will be able to move. var/move_delay = 0 /// Last world.time we finished a normal, non relay/intercepted move @@ -63,7 +69,7 @@ //? Physiology /// overall physiology - see physiology.dm - var/datum/physiology/physiology + var/datum/global_physiology/physiology /// physiology modifiers - see physiology.dm; set to list of paths at init to initialize into instances. var/list/datum/physiology_modifier/physiology_modifiers @@ -72,8 +78,6 @@ var/list/actionspeed_modification //Lazy list, see mob_movespeed.dm /// List of action speed modifiers ignored by this mob. List -> List (id) -> List (sources) var/list/actionspeed_mod_immunities //Lazy list, see mob_movespeed.dm - /// The calculated mob action speed slowdown based on the modifiers list - var/cached_multiplicative_actions_slowdown //? Pixel Offsets /// are we shifted by the user? diff --git a/code/modules/mob/movement.dm b/code/modules/mob/movement.dm index a1d8a8784a62..9efbfb593477 100644 --- a/code/modules/mob/movement.dm +++ b/code/modules/mob/movement.dm @@ -257,6 +257,9 @@ // get additional delay from this move var/add_delay = mob.movement_delay() + //! TODO: REMOVE ; COMPATABILITY LAYER TO USE NEW MOVESPEED. + add_delay = min(10 / ((10 / add_delay) * (1 * mob.cached_movespeed_multiply)), 10 / MOVESPEED_ABSOLUTE_MINIMUM_TILES_PER_SECOND) + //! END // for grabs (legacy code moment) var/add_delay_grab = 0 diff --git a/code/modules/mob/physiology.dm b/code/modules/mob/physiology.dm index 776af71edb3b..8c548254a78c 100644 --- a/code/modules/mob/physiology.dm +++ b/code/modules/mob/physiology.dm @@ -3,15 +3,103 @@ * * todo: on biologies update, we might need to lazy-cache this, and have different physiologies for each biology. */ -/datum/physiology - // todo: /datum/physiology should hold global body physiology, limbs should hold modifiers/whatever themselves. +/datum/global_physiology + // back-reference to mob, for vv purposes. + var/mob/ownership + + // todo: /datum/global_physiology should hold global body physiology, limbs should hold modifiers/whatever themselves. // this way biologies can be supported as efficiently as possible. -/datum/physiology/proc/apply(datum/physiology_modifier/modifier) - // todo: modifier/apply_global, modifier/apply_bodypart + /// carry baseline modify + var/carry_strength = CARRY_STRENGTH_BASELINE + /// carry penalty modifier + var/carry_factor = CARRY_FACTOR_BASELINE + /// carry bias modify + var/carry_bias = 1 + /// carry weight add - added to carry_strength for carry weight only, not encumbrance. + var/carry_weight_add = 0 + /// carry weight factor - multiplied to carry_factor for carry weight only, not encumbrance. + var/carry_weight_factor = 1 + /// carry weight bias - multipled to carry_bias for carry weight only, not encumbrance + var/carry_weight_bias = 1 + +/datum/global_physiology/Destroy() + ownership = null + return ..() + +/datum/global_physiology/proc/reset() + carry_strength = initial(carry_strength) + carry_factor = initial(carry_factor) + carry_weight_add = initial(carry_weight_add) + carry_weight_factor = initial(carry_weight_factor) + carry_bias = initial(carry_bias) + carry_weight_bias = initial(carry_weight_bias) + +/datum/global_physiology/proc/apply(datum/physiology_modifier/modifier) + if(!isnull(modifier.carry_strength_add)) + carry_strength += modifier.carry_strength_add + if(!isnull(modifier.carry_strength_factor)) + carry_factor *= modifier.carry_strength_factor + if(!isnull(modifier.carry_weight_add)) + carry_weight_add += modifier.carry_weight_add + if(!isnull(modifier.carry_weight_factor)) + carry_weight_factor *= modifier.carry_weight_factor + if(!isnull(modifier.carry_strength_bias)) + carry_bias *= modifier.carry_strength_bias + if(!isnull(modifier.carry_weight_bias)) + carry_weight_bias *= modifier.carry_weight_bias + +/** + * return FALSE if we need to reset due to non-canonical operations + */ +/datum/global_physiology/proc/revert(datum/physiology_modifier/modifier) + . = TRUE + if(!isnull(modifier.carry_strength_add)) + carry_strength -= modifier.carry_strength_add + if(!isnull(modifier.carry_strength_factor)) + carry_factor /= modifier.carry_strength_factor + if(!isnull(modifier.carry_weight_add)) + carry_weight_add -= modifier.carry_weight_add + if(!isnull(modifier.carry_weight_factor)) + carry_weight_factor /= modifier.carry_weight_factor + if(!isnull(modifier.carry_strength_bias)) + carry_bias /= modifier.carry_strength_bias + if(!isnull(modifier.carry_weight_bias)) + carry_weight_bias /= modifier.carry_weight_bias -/datum/physiology/proc/revert(datum/physiology_modifier/modifier) - // todo: modifier/apply_global, modifier/apply_bodypart +/datum/global_physiology/vv_edit_var(var_name, var_value, mass_edit, raw_edit) + // we automatically hook varedits and change the admin varedit holder so rebuilds take it into account + // this is not necessarily the best of ideas, + // because things like multiplicative factors don't scale as admins usually would expect + // but having this is better than not having it, as otherwise things would silently be wiped. + if(raw_edit) + return ..() + if(isnull(ownership)) + return ..() + var/datum/physiology_modifier/varedit/varedit_modifier = ownership.get_varedit_physiology_modifier() + switch(var_name) + if(NAMEOF(src, carry_strength)) + if(!isnum(var_value)) + if(!mass_edit) + to_chat(usr, SPAN_WARNING("Invalid value [var_value] for [var_name] physiology edit rejected.")) + return FALSE + . = ..() + if(!.) + return + varedit_modifier.carry_strength_add = var_value - carry_strength + if(NAMEOF(src, carry_factor)) + if(!isnum(var_value)) + if(!mass_edit) + to_chat(usr, SPAN_WARNING("Invalid value [var_value] for [var_name] physiology edit rejected.")) + return FALSE + . = ..() + if(!.) + return + varedit_modifier.carry_strength_factor = var_value / carry_factor + else + return ..() + if(!mass_edit) + to_chat(usr, SPAN_NOTICE("Committing change to [var_name] on [ownership] ([REF(ownership)]) to physiology modifiers automatically.")) /** * physiology modifier @@ -19,17 +107,59 @@ /datum/physiology_modifier abstract_type = /datum/physiology_modifier + /// our name + var/name = "Some Modifier" /// is this a globally cached modifier? var/is_globally_cached = FALSE // todo: on biologies update, we need to specify what biologies this applies to + //? global modifiers + var/carry_strength_add = 0 + var/carry_strength_factor = 1 + var/carry_strength_bias = 1 + var/carry_weight_add = 0 + var/carry_weight_factor = 1 + var/carry_weight_bias = 1 + +/datum/physiology_modifier/serialize() + . = ..() + if(name != initial(name)) + .["name"] = name + if(carry_strength_add != initial(carry_strength_add)) + .["carry_strength_add"] = carry_strength_add + if(carry_strength_factor != initial(carry_strength_factor)) + .["carry_strength_factor"] = carry_strength_factor + +/datum/physiology_modifier/deserialize(list/data) + . = ..() + if(istext(data["name"])) + name = data["name"] + if(isnum(data["carry_strength_add"])) + carry_strength_add = data["carry_strength_add"] + if(isnum(data["carry_strength_factor"])) + carry_strength_factor = data["carry_strength_factor"] + if(isnum(data["carry_strength_bias"])) + carry_strength_bias = data["carry_strength_bias"] + if(isnum(data["carry_weight_add"])) + carry_weight_add = data["carry_weight_add"] + if(isnum(data["carry_weight_factor"])) + carry_weight_factor = data["carry_weight_factor"] + if(isnum(data["carry_weight_bias"])) + carry_weight_bias = data["carry_Weight_bias"] + /** * subtype for hardcoded physiology modifiers */ /datum/physiology_modifier/intrinsic abstract_type = /datum/physiology_modifier/intrinsic +/** + * subtype for admin varedit tracking + */ +/datum/physiology_modifier/varedit + name = "Admin Varedits" + GLOBAL_LIST_EMPTY(cached_physiology_modifiers) /proc/cached_physiology_modifier(datum/physiology_modifier/path) @@ -62,7 +192,7 @@ GLOBAL_LIST_EMPTY(cached_physiology_modifiers) if(ispath(modifier)) modifier = cached_physiology_modifier(modifier) ASSERT(!(modifier in physiology_modifiers)) - physiology_modifiers += modifier + LAZYADD(physiology_modifiers, modifier) physiology.apply(modifier) /** @@ -74,18 +204,86 @@ GLOBAL_LIST_EMPTY(cached_physiology_modifiers) if(ispath(modifier)) modifier = cached_physiology_modifier(modifier) ASSERT(modifier in physiology_modifiers) - physiology_modifiers -= modifier - physiology.revert(modifier) + LAZYREMOVE(physiology_modifiers, modifier) + if(!physiology.revert(modifier)) + // todo: optimize with reset(). + rebuild_physiology() /** * completely rebuilds physiology from our modifiers */ /mob/proc/rebuild_physiology() physiology = new + physiology.ownership = src for(var/datum/physiology_modifier/modifier as anything in physiology_modifiers) if(!istype(modifier)) physiology_modifiers -= modifier continue physiology.apply(modifier) -// todo: admin vv verb via tgui to input new modifier +/mob/vv_get_dropdown() + . = ..() + VV_DROPDOWN_OPTION(null, "-----") + VV_DROPDOWN_OPTION(VV_HK_ADD_PHYSIOLOGY_MODIFIER, "Add Physiology Modifier") + VV_DROPDOWN_OPTION(VV_HK_REMOVE_PHYSIOLOGY_MODIFIER, "Remove Physiology Modifier") + +/mob/vv_do_topic(list/href_list) + . = ..() + if(href_list[VV_HK_ADD_PHYSIOLOGY_MODIFIER]) + // todo: this should be able to be done globally via admin panel and then added to mobs + + var/datum/tgui_dynamic_query/query = new + query.string("name", "Name", "Name your modifier.", 64, FALSE, "Custom Modifier") + query.number("carry_strength_add", "Carry Strength - Add", "Modify the person's base carry strength. Higher is better.", default = 0) + query.number("carry_strength_factor", "Carry Factor - Multiply", "Multiply the person's carry weight/encumbrance to slowdown effect when carrying over their limit. Lower is better.", default = 1) + query.number("carry_strength_bias", "Carry Bias - Multiply", "Multiply the person's carry weight/encumbrance to slowdown bias when carrying over their limit. Lower is better.", default = 1) + query.number("carry_weight_add", "Carry Weight - Add", "Modify the person's base carry weight. Higher is better. This only applies to weight, not encumbrance.", default = 0) + query.number("carry_weight_factor", "Carry Weight - Multiply", "Multiply the person's weight to slowdown effect when carrying over their limit. Lower is better. This only applies to weight, not encumbrance.", default = 1) + query.number("carry_weight_bias", "Carry Weight - Bias", "Multiply the person's weight to slowdown calculation bias; lower is better.", default = 1) + + var/list/choices = tgui_dynamic_input(usr, "Add a physiology modifier", "Add Physiology Modifier", query) + + if(isnull(choices)) + return + if(QDELETED(src)) + return + + var/datum/physiology_modifier/modifier = new + + // we manually deserialize because we might have custom datatypes + // in the future that won't be serialized by the ui necessarily in the same way + // we would serialize it via json. + + modifier.name = choices["name"] + modifier.carry_strength_add = choices["carry_strength_add"] + modifier.carry_strength_factor = choices["carry_strength_factor"] + modifier.carry_strength_bias = choices["carry_strength_bias"] + modifier.carry_weight_add = choices["carry_weight_add"] + modifier.carry_weight_factor = choices["carry_weight_factor"] + modifier.carry_weight_bias = choices["carry_weight_bias"] + + log_admin("[key_name(usr)] --> [key_name(src)] - added physiology modifier [json_encode(modifier.serialize())]") + add_physiology_modifier(modifier) + return TRUE + + if(href_list[VV_HK_REMOVE_PHYSIOLOGY_MODIFIER]) + var/list/assembled = list() + var/i = 0 + for(var/datum/physiology_modifier/modifier as anything in physiology_modifiers) + assembled["[modifier.name] (#[++i])"] = modifier + var/picked = input(usr, "Which modifier to remove? Please do not do this unless you know what you are doing.", "Remove Physiology Modifier") as null|anything in assembled + var/datum/physiology_modifier/removing = assembled[picked] + if(!(removing in physiology_modifiers)) + return TRUE + log_admin("[key_name(usr)] --> [key_name(src)] - removed physiology modifier [json_encode(removing.serialize())]") + remove_physiology_modifier(removing) + return TRUE + +/mob/proc/get_varedit_physiology_modifier() + RETURN_TYPE(/datum/physiology_modifier) + . = locate(/datum/physiology_modifier/varedit) in physiology_modifiers + if(!isnull(.)) + return + var/datum/physiology_modifier/varedit/new_holder = new + add_physiology_modifier(new_holder) + return new_holder diff --git a/code/modules/movespeed/modifiers/mob.dm b/code/modules/movespeed/modifiers/mob.dm index 77c8fe51864a..e47e309ee594 100644 --- a/code/modules/movespeed/modifiers/mob.dm +++ b/code/modules/movespeed/modifiers/mob.dm @@ -3,3 +3,11 @@ /datum/movespeed_modifier/mob_staggered variable = TRUE + +/datum/movespeed_modifier/mob_inventory_carry + priority = MOVESPEED_PRIORITY_CARRY_WEIGHT + calculation_type = MOVESPEED_CALCULATION_LEGACY_MULTIPLY + variable = TRUE + +/datum/movespeed_modifier/mob_item_slowdown + variable = TRUE diff --git a/code/modules/movespeed/movespeed_modifier.dm b/code/modules/movespeed/movespeed_modifier.dm index 859326fa88ba..c8a9204223e7 100644 --- a/code/modules/movespeed/movespeed_modifier.dm +++ b/code/modules/movespeed/movespeed_modifier.dm @@ -33,13 +33,22 @@ Key procs var/id /// Determines order. Lower priorities are applied first. - var/priority = 0 - var/flags = NONE + var/priority = MOVESPEED_PRIORITY_DEFAULT + /// flags + var/movespeed_modifier_flags = NONE + /// calculation type + var/calculation_type = MOVESPEED_CALCULATION_HYPERBOLIC + + //* HYPERBOLIC, HYPERBOLIC_BOOST calculations /// Multiplicative slowdown var/multiplicative_slowdown = 0 - /// Next two variables depend on this: Should we do advanced calculations? - var/complex_calculation = FALSE + + //* MULTIPLY calculations + /// multiply resulting speed by + var/multiply_speed = 1 + + //* HYPERBOLIC_BOOST, MULTIPLY calculations /// Absolute max tiles we can boost to var/absolute_max_tiles_per_second = INFINITY /// Max tiles per second we can boost @@ -51,7 +60,8 @@ Key procs /// Movetypes this never applies to var/blacklisted_movetypes = NONE - /// Other modification datums this conflicts with. + /// Other modification datums this conflicts with. Enum string. + /// If there is, it prioritizes the highest slow *or* the highest speedup, with abs(). var/conflicts_with /datum/movespeed_modifier/New() @@ -61,15 +71,61 @@ Key procs /** * Returns new multiplicative movespeed after modification. + * + * The minimum move delay is always world.tick_lag. Attempting to go lower will result in the excess being cut. + * This is so math doesn't break down when something attempts to break through the asymptote at 0 for move delay to speed. */ /datum/movespeed_modifier/proc/apply_multiplicative(existing, mob/target) - if(!complex_calculation || (multiplicative_slowdown > 0)) // we aren't limiting how much things can slowdown.. yet. - return existing + multiplicative_slowdown - var/current_tiles = 10 / max(existing, world.tick_lag) - // multiplicative_slowdown is negative due to our first check - var/max_buff_to = max(existing + multiplicative_slowdown, 10 / absolute_max_tiles_per_second, 10 / (current_tiles + max_tiles_per_second_boost)) - // never slow the user - return min(existing, max_buff_to) + // todo: we should max/min to ticklag rather than 0, but, we can't until everything is moved to modifiers. + switch(calculation_type) + /* + if(MOVESPEED_CALCULATION_HYPERBOLIC) + return max(world.tick_lag, existing + multiplicative_slowdown) + if(MOVESPEED_CALCULATION_HYPERBOLIC_BOOST) + var/current_tiles = 10 / max(existing, world.tick_lag) + var/max_buff_to = max(existing + multiplicative_slowdown, 10 / absolute_max_tiles_per_second, 10 / (current_tiles + max_tiles_per_second_boost)) + return clamp(max_buff_to, world.tick_lag, existing) + if(MOVESPEED_CALCULATION_MULTIPLY) + var/current_tiles = 10 / max(world.tick_lag, existing) + return 10 / (current_tiles * multiply_speed) + */ + if(MOVESPEED_CALCULATION_HYPERBOLIC) + // going below 0 would fuck multipliers up pretty badly + return max(0, existing + multiplicative_slowdown) + if(MOVESPEED_CALCULATION_HYPERBOLIC_BOOST) + var/current_tiles = 10 / max(existing, world.tick_lag) + var/max_buff_to = max(existing + multiplicative_slowdown, 10 / absolute_max_tiles_per_second, 10 / (current_tiles + max_tiles_per_second_boost)) + return min(existing, max_buff_to) + if(MOVESPEED_CALCULATION_MULTIPLY) + if(existing > 0) + var/current_tiles = 10 / existing + return 10 / (current_tiles * multiply_speed) + else + var/current_tiles = 10 / config_legacy.run_speed + return 10 / (current_tiles * multiply_speed) + if(MOVESPEED_CALCULATION_LEGACY_MULTIPLY) + target.cached_movespeed_multiply *= multiply_speed + return existing + else + return existing + +/** + * applies from params + */ +/datum/movespeed_modifier/proc/parse(list/params) + . = FALSE + if(!isnull(params[MOVESPEED_PARAM_DELAY_MOD])) + . = TRUE + multiplicative_slowdown = params[MOVESPEED_PARAM_DELAY_MOD] + if(!isnull(params[MOVESPEED_PARAM_MULTIPLY_SPEED])) + . = TRUE + multiply_speed = params[MOVESPEED_PARAM_MULTIPLY_SPEED] + if(!isnull(params[MOVESPEED_PARAM_MAX_TILE_ABSOLUTE])) + . = TRUE + absolute_max_tiles_per_second = params[MOVESPEED_PARAM_MAX_TILE_ABSOLUTE] + if(!isnull(params[MOVESPEED_PARAM_MAX_TILE_BOOST])) + . = TRUE + max_tiles_per_second_boost = params[MOVESPEED_PARAM_MAX_TILE_BOOST] GLOBAL_LIST_EMPTY(movespeed_modification_cache) @@ -120,15 +176,16 @@ GLOBAL_LIST_EMPTY(movespeed_modification_cache) update_movespeed(FALSE) return TRUE -/*! Used for variable slowdowns like hunger/health loss/etc, works somewhat like the old list-based modification adds. Returns the modifier datum if successful - How this SHOULD work is: - 1. Ensures type_id_datum one way or another refers to a /variable datum. This makes sure it can't be cached. This includes if it's already in the modification list. - 2. Instantiate a new datum if type_id_datum isn't already instantiated + in the list, using the type. Obviously, wouldn't work for ID only. - 3. Add the datum if necessary using the regular add proc - 4. If any of the rest of the args are not null (see: multiplicative slowdown), modify the datum - 5. Update if necessary -*/ -/mob/proc/add_or_update_variable_movespeed_modifier(datum/movespeed_modifier/type_id_datum, update = TRUE, multiplicative_slowdown) +/** + * Used for variable slowdowns like hunger/health loss/etc, works somewhat like the old list-based modification adds. Returns the modifier datum if successful + * How this SHOULD work is: + * 1. Ensures type_id_datum one way or another refers to a /variable datum. This makes sure it can't be cached. This includes if it's already in the modification list. + * 2. Instantiate a new datum if type_id_datum isn't already instantiated + in the list, using the type. Obviously, wouldn't work for ID only. + * 3. Add the datum if necessary using the regular add proc + * 4. If any of the rest of the args are not null (see: multiplicative slowdown), modify the datum + * 5. Update if necessary + */ +/mob/proc/add_or_update_variable_movespeed_modifier(datum/movespeed_modifier/type_id_datum, update = TRUE, list/params) var/modified = FALSE var/inject = FALSE var/datum/movespeed_modifier/final @@ -151,8 +208,7 @@ GLOBAL_LIST_EMPTY(movespeed_modification_cache) if(!LAZYACCESS(movespeed_modification, final.id)) inject = TRUE modified = TRUE - if(!isnull(multiplicative_slowdown)) - final.multiplicative_slowdown = multiplicative_slowdown + if(final.parse(params)) modified = TRUE if(inject) add_movespeed_modifier(final, FALSE) @@ -169,7 +225,7 @@ GLOBAL_LIST_EMPTY(movespeed_modification_cache) diff = var_value - cached_multiplicative_slowdown . = ..() if(. && slowdown_edit && isnum(diff)) - add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/admin_varedit, multiplicative_slowdown = diff) + add_or_update_variable_movespeed_modifier(/datum/movespeed_modifier/admin_varedit, params = list(MOVESPEED_PARAM_DELAY_MOD = diff)) ///Is there a movespeed modifier for this mob /mob/proc/has_movespeed_modifier(datum/movespeed_modifier/datum_type_id) @@ -206,6 +262,9 @@ GLOBAL_LIST_EMPTY(movespeed_modification_cache) /mob/proc/update_movespeed() . = 0 var/list/conflict_tracker = list() + //! TODO: LEGACY + cached_movespeed_multiply = 1 + //! END for(var/datum/movespeed_modifier/M in get_movespeed_modifiers()) if(!(M.movement_type & movement_type)) // We don't affect any of these move types, skip continue @@ -221,12 +280,12 @@ GLOBAL_LIST_EMPTY(movespeed_modification_cache) else continue . = M.apply_multiplicative(., src) - // your delay decreases, "give" the delay back to the client - cached_multiplicative_slowdown = . + cached_multiplicative_slowdown = min(., 10 / MOVESPEED_ABSOLUTE_MINIMUM_TILES_PER_SECOND) if(!client) return var/diff = (last_move_time - move_delay) - cached_multiplicative_slowdown if(diff > 0) + // your delay decreases, "give" the delay back to the client if(move_delay > world.time + 1.5) move_delay -= diff #ifdef SMOOTH_MOVEMENT diff --git a/code/modules/photography/camera.dm b/code/modules/photography/camera.dm index c20953a79a1a..fbff55491976 100644 --- a/code/modules/photography/camera.dm +++ b/code/modules/photography/camera.dm @@ -7,7 +7,7 @@ worn_state = "camera" worn_render_flags = NONE desc = "A polaroid camera. 10 photos left." - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD w_class = ITEMSIZE_SMALL slot_flags = SLOT_BELT materials = list(MAT_STEEL = 2000) diff --git a/code/modules/projectiles/ammunition/ammo_casing.dm b/code/modules/projectiles/ammunition/ammo_casing.dm index cb3a53a228dc..9b79f0b5738b 100644 --- a/code/modules/projectiles/ammunition/ammo_casing.dm +++ b/code/modules/projectiles/ammunition/ammo_casing.dm @@ -4,7 +4,7 @@ icon = 'icons/obj/ammo.dmi' icon_state = "s-casing" slot_flags = SLOT_BELT | SLOT_EARS - item_flags = ITEM_EASY_LATHE_DECONSTRUCT + item_flags = ITEM_EASY_LATHE_DECONSTRUCT | ITEM_ENCUMBERS_WHILE_HELD throw_force = 1 w_class = ITEMSIZE_TINY preserve_item = 1 diff --git a/code/modules/projectiles/gun.dm b/code/modules/projectiles/gun.dm index 1490cfbff748..f7c9c1afac6d 100644 --- a/code/modules/projectiles/gun.dm +++ b/code/modules/projectiles/gun.dm @@ -38,6 +38,7 @@ ) icon_state = "detective" item_state = "gun" + item_flags = ITEM_ENCUMBERS_WHILE_HELD | ITEM_ENCUMBERS_ONLY_HELD slot_flags = SLOT_BELT|SLOT_HOLSTER materials = list(MAT_STEEL = 2000) rad_flags = RAD_BLOCK_CONTENTS diff --git a/code/modules/projectiles/guns/magnetic/magnetic_railgun.dm b/code/modules/projectiles/guns/magnetic/magnetic_railgun.dm index a42dac66fe66..73aaa29d0c20 100644 --- a/code/modules/projectiles/guns/magnetic/magnetic_railgun.dm +++ b/code/modules/projectiles/guns/magnetic/magnetic_railgun.dm @@ -12,13 +12,12 @@ heavy = TRUE slot_flags = SLOT_BELT loaded = /obj/item/rcd_ammo/large - slowdown = 1 // Slowdown equals slowdown_worn, until we decide to import the system to differentiate between held and worn items + weight = ITEM_WEIGHT_GUN_BULKY + encumbrance = ITEM_ENCUMBRANCE_GUN_BULKY fire_delay = 1 var/initial_cell_type = /obj/item/cell/hyper var/initial_capacitor_type = /obj/item/stock_parts/capacitor/adv - var/slowdown_held = 2 - var/slowdown_worn = 1 var/empty_sound = 'sound/machines/twobeep.ogg' /obj/item/gun/magnetic/railgun/Initialize(mapload) @@ -64,9 +63,8 @@ initial_capacitor_type = /obj/item/stock_parts/capacitor/super fire_delay = 0 - slowdown = 2 - slowdown_held = 3 - slowdown_worn = 2 + weight = ITEM_WEIGHT_GUN_RIDICULOUS + encumbrance = ITEM_ENCUMBRANCE_GUN_RIDICULOUS slot_flags = SLOT_BACK w_class = ITEMSIZE_NO_CONTAINER @@ -95,9 +93,8 @@ slot_flags = SLOT_BACK - slowdown = 0 - slowdown_held = 0 - slowdown_worn = 0 + weight = ITEM_WEIGHT_GUN_LIGHT + encumbrance = ITEM_ENCUMBRANCE_GUN_LIGHT power_cost = 100 load_type = /obj/item/magnetic_ammo @@ -127,9 +124,8 @@ slot_flags = SLOT_BACK - slowdown = 0 - slowdown_held = 0 - slowdown_worn = 0 + weight = ITEM_WEIGHT_GUN_LIGHT + encumbrance = ITEM_ENCUMBRANCE_GUN_LIGHT power_cost = 400 projectile_type = /obj/projectile/bullet/magnetic/heated @@ -185,7 +181,8 @@ slot_flags = SLOT_BACK - slowdown = 0.3 + weight = ITEM_WEIGHT_GUN_NORMAL + encumbrance = ITEM_ENCUMBRANCE_GUN_NORMAL power_cost = 200 projectile_type = /obj/projectile/bullet/magnetic/flechette/hunting diff --git a/code/modules/projectiles/guns/projectile/automatic.dm b/code/modules/projectiles/guns/projectile/automatic.dm index b4783605f4ab..9601f63211da 100644 --- a/code/modules/projectiles/guns/projectile/automatic.dm +++ b/code/modules/projectiles/guns/projectile/automatic.dm @@ -549,7 +549,6 @@ slot_flags = SLOT_BACK load_method = SPEEDLOADER ammo_type = /obj/item/ammo_casing/a762 - slowdown = 0.5 max_shells = 15 burst = 3 fire_delay = 7.2 diff --git a/code/modules/projectiles/magazines/magazine.dm b/code/modules/projectiles/magazines/magazine.dm index d50d31301ad1..fbfc27cdb404 100644 --- a/code/modules/projectiles/magazines/magazine.dm +++ b/code/modules/projectiles/magazines/magazine.dm @@ -4,7 +4,7 @@ desc = "A magazine for some kind of gun." icon_state = ".357" icon = 'icons/obj/ammo.dmi' - item_flags = ITEM_EASY_LATHE_DECONSTRUCT + item_flags = ITEM_EASY_LATHE_DECONSTRUCT | ITEM_ENCUMBERS_WHILE_HELD slot_flags = SLOT_BELT item_state = "syringe_kit" materials = list(MAT_STEEL = 500) diff --git a/code/modules/reagents/reagent_containers/spray.dm b/code/modules/reagents/reagent_containers/spray.dm index 727bd9a6c7af..3c691c49fa01 100644 --- a/code/modules/reagents/reagent_containers/spray.dm +++ b/code/modules/reagents/reagent_containers/spray.dm @@ -4,7 +4,7 @@ icon = 'icons/obj/janitor.dmi' icon_state = "cleaner" item_state = "cleaner" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD atom_flags = OPENCONTAINER slot_flags = SLOT_BELT | SLOT_HOLSTER throw_force = 3 diff --git a/code/modules/reagents/reagent_containers/syringes.dm b/code/modules/reagents/reagent_containers/syringes.dm index 4e87d47b3ae8..cb293dd571aa 100644 --- a/code/modules/reagents/reagent_containers/syringes.dm +++ b/code/modules/reagents/reagent_containers/syringes.dm @@ -17,7 +17,7 @@ sharp = 1 unacidable = 1 //glass rad_flags = RAD_NO_CONTAMINATE - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/mode = SYRINGE_DRAW var/image/filling //holds a reference to the current filling overlay var/visible_name = "a syringe" diff --git a/code/modules/resleeving/mirror.dm b/code/modules/resleeving/mirror.dm index 11e96ebbdae4..0bad24f9dd3b 100644 --- a/code/modules/resleeving/mirror.dm +++ b/code/modules/resleeving/mirror.dm @@ -10,7 +10,8 @@ icon_state = "mirror_implant_f" var/stored_mind = null var/tmp/mob/living/carbon/human/human - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD + //holder to prevent having to find it each time /mob/living/carbon/human/var/obj/item/implant/mirror/mirror @@ -106,7 +107,7 @@ throw_range = 10 materials = list(MAT_STEEL = 200) origin_tech = list(TECH_MAGNET = 2, TECH_BIO = 2) - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD /obj/item/mirrortool name = "Mirror Installation Tool" @@ -121,7 +122,7 @@ throw_range = 10 materials = list(MAT_STEEL = 200) origin_tech = list(TECH_MAGNET = 2, TECH_BIO = 2) - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/obj/item/implant/mirror/imp = null /obj/item/mirrortool/afterattack(atom/target, mob/user, clickchain_flags, list/params) diff --git a/code/modules/species/physiology.dm b/code/modules/species/physiology.dm new file mode 100644 index 000000000000..f32b69464ea7 --- /dev/null +++ b/code/modules/species/physiology.dm @@ -0,0 +1,4 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + +/datum/physiology_modifier/intrinsic/species diff --git a/code/modules/species/protean/protean.dm b/code/modules/species/protean/protean.dm index cf7518fcf1bf..f20b7b98266b 100644 --- a/code/modules/species/protean/protean.dm +++ b/code/modules/species/protean/protean.dm @@ -1,6 +1,10 @@ #define DAM_SCALE_FACTOR 0.01 #define METAL_PER_TICK 100 +/datum/physiology_modifier/intrinsic/species/protean + carry_strength_add = CARRY_STRENGTH_ADD_PROTEAN + carry_strength_factor = CARRY_FACTOR_MOD_PROTEAN + /datum/species/protean uid = SPECIES_ID_PROTEAN name = SPECIES_PROTEAN @@ -13,6 +17,7 @@ death_message = "rapidly loses cohesion, dissolving into a cloud of gray dust..." knockout_message = "collapses inwards, forming a disordered puddle of gray goo." remains_type = /obj/effect/debris/cleanable/ash + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/protean unarmed_types = list(/datum/unarmed_attack/stomp, /datum/unarmed_attack/kick, /datum/unarmed_attack/punch, /datum/unarmed_attack/bite) // Regular human attack verbs are enough. @@ -347,7 +352,7 @@ if(istype(back, /obj/item/hardsuit/protean)) var/obj/item/hardsuit/protean/suit = back - if(suit.myprotean == src) + if(suit.myprotean == src) suit.reset() suit.forceMove(src) to_chat(src, SPAN_WARNING("You retract your nanosuit.")) diff --git a/code/modules/species/species.dm b/code/modules/species/species.dm index e5b398ead756..549e5ef765c2 100644 --- a/code/modules/species/species.dm +++ b/code/modules/species/species.dm @@ -43,7 +43,8 @@ //? Traits / Physiology /// Intrinsic datum traits to apply to the mob var/list/mob_traits - // todo: list of physiologies to add. list, incase we want to have separate ones for separate biology flags. + /// physiology modifier to add - path or instance + var/datum/physiology_modifier/mob_physiology_modifier //? Additional info /// what you see on tooltip/examine @@ -527,6 +528,9 @@ H.maxHealth = total_health + if(!isnull(mob_physiology_modifier)) + H.add_physiology_modifier(mob_physiology_modifier) + add_inherent_verbs(H) for(var/name in traits) @@ -553,6 +557,9 @@ remove_inherent_verbs(H) H.holder_type = null + if(!isnull(mob_physiology_modifier)) + H.remove_physiology_modifier(mob_physiology_modifier) + for(var/name in traits) var/datum/trait/T = all_traits[name] T.remove(src, H) diff --git a/code/modules/species/station/standard/human.dm b/code/modules/species/station/standard/human.dm index 3c5413971319..72defa90b66f 100644 --- a/code/modules/species/station/standard/human.dm +++ b/code/modules/species/station/standard/human.dm @@ -1,3 +1,7 @@ +/datum/physiology_modifier/intrinsic/species/human + carry_strength_add = CARRY_STRENGTH_ADD_HUMAN + carry_strength_factor = CARRY_FACTOR_MOD_HUMAN + /datum/species/human id = SPECIES_ID_HUMAN uid = SPECIES_ID_HUMAN @@ -15,6 +19,7 @@ interests, rampant cyber and bio-augmentation initiatives, and secretive factions make life on most human \ worlds tumultous at best." catalogue_data = list(/datum/category_item/catalogue/fauna/humans) + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/human max_additional_languages = 3 intrinsic_languages = list( diff --git a/code/modules/species/station/standard/moth.dm b/code/modules/species/station/standard/moth.dm index c224674a65a2..9e416179ea4d 100644 --- a/code/modules/species/station/standard/moth.dm +++ b/code/modules/species/station/standard/moth.dm @@ -4,6 +4,8 @@ GLOBAL_LIST_INIT(moth_lore_data, init_moth_lore()) /proc/init_moth_lore() return json_decode(file2text('strings/misc/moth_species.json')) +/datum/physiology_modifier/intrinsic/species/nepid + /datum/species/moth name = SPECIES_MOTH uid = SPECIES_ID_MOTH @@ -157,20 +159,30 @@ GLOBAL_LIST_INIT(moth_lore_data, init_moth_lore()) "} value = CATALOGUER_REWARD_TRIVIAL +/datum/physiology_modifier/intrinsic/species/nepid/dark + carry_strength_add = CARRY_STRENGTH_ADD_MOTH_DARK + carry_strength_factor = CARRY_FACTOR_MOD_MOTH_DARK + /datum/species/moth/dark name = SPECIES_MOTH_DARK uid = SPECIES_ID_MOTH_DARK species_spawn_flags = SPECIES_SPAWN_CHARACTER + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/nepid/dark // darksight, but weak to light vision_innate = /datum/vision/baseline/species_tier_2 flash_burn = 5 flash_mod = 1.2 +/datum/physiology_modifier/intrinsic/species/nepid/light + carry_strength_add = CARRY_STRENGTH_ADD_MOTH_LIGHT + carry_strength_factor = CARRY_FACTOR_MOD_MOTH_LIGHT + /datum/species/moth/light name = SPECIES_MOTH_LIGHT uid = SPECIES_ID_MOTH_LIGHT species_spawn_flags = SPECIES_SPAWN_CHARACTER + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/nepid/light // hardy, but no darksight vision_innate = /datum/vision/baseline/species_tier_0 diff --git a/code/modules/species/station/standard/tajaran.dm b/code/modules/species/station/standard/tajaran.dm index da2949b6ef7a..f87fa59449ba 100644 --- a/code/modules/species/station/standard/tajaran.dm +++ b/code/modules/species/station/standard/tajaran.dm @@ -1,3 +1,7 @@ +/datum/physiology_modifier/intrinsic/species/tajaran + carry_strength_add = CARRY_STRENGTH_ADD_TAJARAN + carry_strength_factor = CARRY_FACTOR_MOD_TAJARAN + /datum/species/tajaran uid = SPECIES_ID_TAJARAN id = SPECIES_ID_TAJARAN @@ -5,6 +9,7 @@ name_plural = "Tajaran" category = "Tajaran" default_bodytype = BODYTYPE_TAJARAN + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/tajaran icobase = 'icons/mob/species/tajaran/body_greyscale.dmi' deform = 'icons/mob/species/tajaran/deformed_body_greyscale.dmi' diff --git a/code/modules/species/station/standard/teshari.dm b/code/modules/species/station/standard/teshari.dm index 48d92f38c5e4..27a319c4b071 100644 --- a/code/modules/species/station/standard/teshari.dm +++ b/code/modules/species/station/standard/teshari.dm @@ -1,3 +1,7 @@ +/datum/physiology_modifier/intrinsic/species/teshari + carry_strength_add = CARRY_STRENGTH_ADD_TESHARI + carry_strength_factor = CARRY_FACTOR_MOD_TESHARI + /datum/species/teshari uid = SPECIES_ID_TESHARI id = SPECIES_ID_TESHARI @@ -6,6 +10,7 @@ category = "Teshari" name_plural = "Tesharii" uid = SPECIES_ID_TESHARI + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/teshari blurb = {" A race of feathered raptors who developed alongside the Skrell, inhabiting diff --git a/code/modules/species/station/standard/unathi.dm b/code/modules/species/station/standard/unathi.dm index dd491e80d0be..51b906ec8009 100644 --- a/code/modules/species/station/standard/unathi.dm +++ b/code/modules/species/station/standard/unathi.dm @@ -1,3 +1,7 @@ +/datum/physiology_modifier/intrinsic/species/unathi + carry_strength_add = CARRY_STRENGTH_ADD_UNATHI + carry_strength_factor = CARRY_FACTOR_MOD_UNATHI + /datum/species/unathi uid = SPECIES_ID_UNATHI id = SPECIES_ID_UNATHI @@ -7,6 +11,8 @@ primitive_form = SPECIES_MONKEY_UNATHI default_bodytype = BODYTYPE_UNATHI + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/unathi + // icon_template = 'icons/mob/species/template_tall.dmi' //TODO: Tall Unathi :D icobase = 'icons/mob/species/unathi/body_greyscale.dmi' deform = 'icons/mob/species/unathi/deformed_body_greyscale.dmi' diff --git a/code/modules/species/station/xenochimera.dm b/code/modules/species/station/xenochimera.dm index 31c5acc12e89..70c42b5e68fd 100644 --- a/code/modules/species/station/xenochimera.dm +++ b/code/modules/species/station/xenochimera.dm @@ -1,3 +1,7 @@ +/datum/physiology_modifier/intrinsic/species/xenochimera + carry_strength_add = CARRY_STRENGTH_ADD_XENOCHIMERA + carry_strength_factor = CARRY_FACTOR_MOD_XENOCHIMERA + /datum/species/shapeshifter/xenochimera //Scree's race. uid = SPECIES_ID_XENOCHIMERA id = SPECIES_ID_XENOCHIMERA @@ -5,6 +9,7 @@ name_plural = "Xenochimeras" base_species = SPECIES_XENOCHIMERA category = "Special" + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/xenochimera selects_bodytype = TRUE diff --git a/code/modules/species/station/xenomorph_hybrids/xeno_hybrids.dm b/code/modules/species/station/xenomorph_hybrids/xeno_hybrids.dm index a80036c40593..94983c04321c 100644 --- a/code/modules/species/station/xenomorph_hybrids/xeno_hybrids.dm +++ b/code/modules/species/station/xenomorph_hybrids/xeno_hybrids.dm @@ -1,9 +1,14 @@ +/datum/physiology_modifier/intrinsic/species/xenohybrid + carry_strength_add = CARRY_STRENGTH_ADD_XENOHYBRID + carry_strength_factor = CARRY_FACTOR_MOD_XENOHYBRID + /datum/species/xenohybrid name = SPECIES_XENOHYBRID name_plural = "Xenomorph Hybrids" uid = SPECIES_ID_XENOHYBRID id = SPECIES_ID_XENOHYBRID default_bodytype = BODYTYPE_XENOHYBRID + mob_physiology_modifier = /datum/physiology_modifier/intrinsic/species/xenohybrid icobase = 'icons/mob/species/xenohybrid/body.dmi' deform = 'icons/mob/species/xenohybrid/deformed_body.dmi' diff --git a/code/modules/tgui/modal_vr.dm b/code/modules/tgui/modal_vr_legacy.dm similarity index 100% rename from code/modules/tgui/modal_vr.dm rename to code/modules/tgui/modal_vr_legacy.dm diff --git a/code/modules/tgui/tgui_alert.dm b/code/modules/tgui/modals/tgui_alert.dm similarity index 100% rename from code/modules/tgui/tgui_alert.dm rename to code/modules/tgui/modals/tgui_alert.dm diff --git a/code/modules/tgui/modals/tgui_dynamic_input.dm b/code/modules/tgui/modals/tgui_dynamic_input.dm new file mode 100644 index 000000000000..8fc7338ccc83 --- /dev/null +++ b/code/modules/tgui/modals/tgui_dynamic_input.dm @@ -0,0 +1,217 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + +/** + * Helper datum used to build a query for tgui_dynamic_input + * High overhead, technically not necessary, but, this is easy to use as an API. + */ +/datum/tgui_dynamic_query + /// options list + var/list/options = list() + +/datum/tgui_dynamic_query/proc/string(key, name, desc, max_length = 512, multi_line = FALSE, default) + RETURN_TYPE(/datum/tgui_dynamic_query) + options[key] = list( + "name" = name, + "desc" = desc, + "default" = default, + "type" = TGUI_INPUT_DATATYPE_TEXT, + "constraints" = list(max_length), + ) + return src + +/datum/tgui_dynamic_query/proc/number(key, name, desc, min_value = -INFINITY, max_value = INFINITY, round_to, default) + RETURN_TYPE(/datum/tgui_dynamic_query) + options[key] = list( + "name" = name, + "desc" = desc, + "default" = default, + "type" = TGUI_INPUT_DATATYPE_NUM, + "constraints" = list(min_value, max_value, round_to), + ) + return src + +/datum/tgui_dynamic_query/proc/toggle(key, name, desc, default) + RETURN_TYPE(/datum/tgui_dynamic_query) + options[key] = list( + "name" = name, + "desc" = desc, + "default" = default, + "type" = TGUI_INPUT_DATATYPE_TOGGLE, + "constraints" = list(), + ) + return src + +/datum/tgui_dynamic_query/proc/pick_one(key, name, desc, list/choices = list(), default) + RETURN_TYPE(/datum/tgui_dynamic_query) + options[key] = list( + "name" = name, + "desc" = desc, + "default" = default, + "type" = TGUI_INPUT_DATATYPE_LIST_PICK, + "constraints" = choices, + ) + return src + +/** + * builds return list of results + */ +/datum/tgui_dynamic_query/proc/get_results(list/choices) + . = list() + var/got + for(var/key in options) + var/list/params = options[key] + var/val = choices[key] + switch(params[TGUI_INPUT_DATA_TYPE]) + if(TGUI_INPUT_DATATYPE_TEXT) + got = isnull(val) ? params[TGUI_INPUT_DATA_DEFAULT] : val + if(!isnull(got)) + if(length(got) > params[TGUI_INPUT_DATA_CONSTRAINTS][1]) + got = copytext_char(got, 1, params[TGUI_INPUT_DATA_CONSTRAINTS][1] + 1) + .[key] = got + if(TGUI_INPUT_DATATYPE_NUM) + got = isnull(val) ? params[TGUI_INPUT_DATA_DEFAULT] : text2num(val) + if(!isnull(got)) + got = clamp(got, params[TGUI_INPUT_DATA_CONSTRAINTS][1], params[TGUI_INPUT_DATA_CONSTRAINTS][2]) + if(!isnull(params[TGUI_INPUT_DATA_CONSTRAINTS][3])) + got = round(got, params[TGUI_INPUT_DATA_CONSTRAINTS][3]) + .[key] = got + if(TGUI_INPUT_DATATYPE_LIST_PICK) + got = isnull(val) ? params[TGUI_INPUT_DATA_DEFAULT] : val + if(!isnull(got)) + if(!(got in params[TGUI_INPUT_DATA_CONSTRAINTS])) + if(length(params[TGUI_INPUT_DATA_CONSTRAINTS])) + got = params[TGUI_INPUT_DATA_CONSTRAINTS][1] + else + got = null + .[key] = got + if(TGUI_INPUT_DATATYPE_TOGGLE) + got = isnull(val) ? params[TGUI_INPUT_DATA_DEFAULT] : val + if(!isnull(got)) + got = !!got + .[key] = got + +/** + * returns list to be sent to UI + */ +/datum/tgui_dynamic_query/proc/get_query() + return options + +/** + * Creates a TGUI input window and returns the user's response + * + * This is used to grab a set of responses to various datatypes. + * This proc blocks until finished. + * + * @params + * * user - who to send this to + * * message - description in interface + * * title - self explanatory + * * query - built query + * * timeout - timeout before menu closes. if it times out, choices will be null. + * + * @return list of key-value pairs (the TGUI_INPUT_DATA_KEY's you put in) associated to values + */ +/proc/tgui_dynamic_input(mob/user, message, title = "Input", datum/tgui_dynamic_query/query, timeout = 0) + var/datum/tgui_dynamic_input/modal = new(user, message, title, query, timeout) + modal.block_on_finished() + return modal.query.get_results(modal.choices) + +/** + * Creates a TGUI input window and returns the user's response + * + * This is used to grab a set of responses to various datatypes. + * This proc immediately returns. + * + * @params + * * user - who to send this to + * * message - description in interface + * * title - self explanatory + * * query - built query + * * timeout - timeout before menu closes. if it times out, choices will be null. + * * callback - callback called with first arg being the picked list when we're done. + * + * @return the /datum/tgui_dynamic_input instance created. you should probably not touch this unless you know what you're doing. + */ +/proc/tgui_dynamic_input_async(mob/user, message, title = "Input", datum/tgui_dynamic_query/query, timeout = 0, datum/callback/callback) + return new /datum/tgui_dynamic_input(user, message, title, query, timeout, callback) + +/datum/tgui_dynamic_input + /// title of the windo + var/title + /// message that appears inside the window + var/message + /// query datum + var/datum/tgui_dynamic_query/query + /// list of user's choices; null if they haven't picked yet + var/list/choices + /// when we were opened + var/opened_time + /// how long our timeout is; null for infinite + var/timeout + /// did user close us yet? also set to true if we're qdeleted + var/closed + /// callback to invoke on finish + var/datum/callback/callback + /// are we finished? set to true on close, here to prevent double close. + var/finished = FALSE + +/datum/tgui_dynamic_input/New(mob/user, message, title, datum/tgui_dynamic_query/query, timeout, datum/callback/callback) + src.title = title + src.message = message + src.query = query + src.timeout = timeout + if(timeout) + QDEL_IN(src, timeout) + src.callback = callback + ui_interact(user) + +/datum/tgui_dynamic_input/Destroy() + // 'choices' and 'query' intentionally kept + if(!finished) + finish(null) + closed = TRUE + return ..() + +/datum/tgui_dynamic_input/ui_static_data(mob/user, datum/tgui/ui, datum/ui_state/state) + . = ..() + .["query"] = query.get_query() + .["title"] = title + .["message"] = message + .["timeout"] = timeout + +/datum/tgui_dynamic_input/ui_interact(mob/user, datum/tgui/ui, datum/tgui/parent_ui) + ui = SStgui.try_update_ui(user, src, ui) + if(!ui) + ui = new(user, src, "UIDynamicInputModal") + ui.set_autoupdate(FALSE) + ui.open() + +/datum/tgui_dynamic_input/ui_act(action, list/params, datum/tgui/ui) + . = ..() + if(.) + return + switch(action) + if("submit") + finish(params["choices"]) + return TRUE + if("cancel") + closed = TRUE + SStgui.close_uis(src) + if(!finished) + finish(null) + return TRUE + +/datum/tgui_dynamic_input/ui_state(mob/user, datum/tgui_module/module) + return GLOB.always_state + +/datum/tgui_dynamic_input/proc/block_on_finished() + UNTIL(closed) + return choices + +/datum/tgui_dynamic_input/proc/finish(list/choices) + finished = TRUE + choices = query.get_results(choices) + callback?.InvokeAsync(choices) + if(!QDESTROYING(src)) + qdel(src) diff --git a/code/modules/tgui/tgui_input_list.dm b/code/modules/tgui/modals/tgui_input_list.dm similarity index 100% rename from code/modules/tgui/tgui_input_list.dm rename to code/modules/tgui/modals/tgui_input_list.dm diff --git a/code/modules/tgui/tgui_input_number.dm b/code/modules/tgui/modals/tgui_input_number.dm similarity index 100% rename from code/modules/tgui/tgui_input_number.dm rename to code/modules/tgui/modals/tgui_input_number.dm diff --git a/code/modules/tgui/tgui_input_text.dm b/code/modules/tgui/modals/tgui_input_text.dm similarity index 100% rename from code/modules/tgui/tgui_input_text.dm rename to code/modules/tgui/modals/tgui_input_text.dm diff --git a/code/modules/tgui/module.dm b/code/modules/tgui/module.dm index 2f5ce0b17dda..309c79ee2bc3 100644 --- a/code/modules/tgui/module.dm +++ b/code/modules/tgui/module.dm @@ -1,6 +1,5 @@ -/** - *! SPDX-License-Identifier: MIT - */ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// /** * new, more-modular tgui_module system diff --git a/code/modules/tgui/modules/general/cardmod.dm b/code/modules/tgui/modules/general/cardmod.dm index 6038b1d7c132..8159736558c7 100644 --- a/code/modules/tgui/modules/general/cardmod.dm +++ b/code/modules/tgui/modules/general/cardmod.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + /** * ID mod module * diff --git a/code/modules/tgui/modules/specific/lathe_control.dm b/code/modules/tgui/modules/specific/lathe_control.dm index bee1c7cb14a0..11bac06b7df4 100644 --- a/code/modules/tgui/modules/specific/lathe_control.dm +++ b/code/modules/tgui/modules/specific/lathe_control.dm @@ -1,3 +1,6 @@ +//* This file is explicitly licensed under the MIT license. *// +//* Copyright (c) 2023 Citadel Station developers. *// + /** * So why do we have discrete modules for lathe control? * diff --git a/code/modules/unit_tests/core/priority_queue.dm b/code/modules/unit_tests/core/priority_queue.dm index e1759b43f2cc..28e0339f0c15 100644 --- a/code/modules/unit_tests/core/priority_queue.dm +++ b/code/modules/unit_tests/core/priority_queue.dm @@ -1,5 +1,5 @@ /datum/unit_test/priority_queue/Run() - var/datum/priority_queue/queue = new(/proc/cmp_numeric_asc) + var/datum/priority_queue/queue = new /datum/priority_queue(/proc/cmp_numeric_asc) for(var/i in 1 to 1000) queue.enqueue(rand(1, 100000)) var/last = queue.dequeue() diff --git a/code/modules/vehicles_legacy/construction.dm b/code/modules/vehicles_legacy/construction.dm index f290ab767cac..6da492e2f5df 100644 --- a/code/modules/vehicles_legacy/construction.dm +++ b/code/modules/vehicles_legacy/construction.dm @@ -11,7 +11,7 @@ item_state = "buildpipe" density = TRUE - slowdown = 10 //It's a vehicle frame, what do you expect? + weight = ITEM_WEIGHT_VEHICLE_FRAME w_class = 5 pixel_x = -16 diff --git a/code/modules/vore/fluffstuff/custom_items.dm b/code/modules/vore/fluffstuff/custom_items.dm index a49ccfa82bf9..1da2469624e8 100644 --- a/code/modules/vore/fluffstuff/custom_items.dm +++ b/code/modules/vore/fluffstuff/custom_items.dm @@ -676,7 +676,7 @@ desc = "Seems absurd, doesn't it? Yet, here we are. Generally considered dangerous contraband unless the user has permission from Central Command." icon = 'icons/obj/device_alt.dmi' icon_state = "hand_tele" - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD w_class = ITEMSIZE_SMALL origin_tech = list(TECH_MAGNET = 5, TECH_BLUESPACE = 5, TECH_ILLEGAL = 7) @@ -972,7 +972,7 @@ icon = 'icons/obj/device_alt.dmi' icon_state = "motion2" w_class = ITEMSIZE_TINY - item_flags = ITEM_NOBLUDGEON + item_flags = ITEM_NOBLUDGEON | ITEM_ENCUMBERS_WHILE_HELD var/tele_name var/obj/item/perfect_tele/tele_hand diff --git a/code/modules/xenoarcheaology/tools/equipment.dm b/code/modules/xenoarcheaology/tools/equipment.dm index 554668ad21a7..327169c1b7d4 100644 --- a/code/modules/xenoarcheaology/tools/equipment.dm +++ b/code/modules/xenoarcheaology/tools/equipment.dm @@ -7,6 +7,8 @@ armor_type = /datum/armor/general/biosuit/anomaly max_pressure_protection = 5 * ONE_ATMOSPHERE // Not very good protection, but if an anomaly starts doing gas stuff you're not screwed min_pressure_protection = 0.4 * ONE_ATMOSPHERE + encumbrance = ITEM_ENCUMBRANCE_ARMOR_ANOMALY + weight = ITEM_WEIGHT_ARMOR_ANOMALY /obj/item/clothing/head/bio_hood/anomaly name = "Anomaly hood" @@ -16,6 +18,8 @@ armor_type = /datum/armor/general/biosuit/anomaly max_pressure_protection = 5 * ONE_ATMOSPHERE // Not very good protection, but if an anomaly starts doing gas stuff you're not screwed min_pressure_protection = 0.4 * ONE_ATMOSPHERE + encumbrance = ITEM_ENCUMBRANCE_ARMOR_ANOMALY_HELMET + weight = ITEM_WEIGHT_ARMOR_ANOMALY_HELMET /obj/item/clothing/suit/space/anomaly name = "Excavation suit" @@ -24,7 +28,8 @@ item_state = "cespace_suit" armor_type = /datum/armor/general/biosuit/anomaly allowed = list(/obj/item/flashlight,/obj/item/tank,/obj/item/suit_cooling_unit,/obj/item/pickaxe) - slowdown = 1 + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_ANOMALY + weight = ITEM_WEIGHT_VOIDSUIT_ANOMALY // Pressure protection inherited from space suits /obj/item/clothing/head/helmet/space/anomaly @@ -33,3 +38,5 @@ icon_state = "cespace_helmet" item_state = "cespace_helmet" armor_type = /datum/armor/general/biosuit/anomaly + encumbrance = ITEM_ENCUMBRANCE_VOIDSUIT_ANOMALY_HELMET + weight = ITEM_WEIGHT_VOIDSUIT_ANOMALY_HELMET diff --git a/icons/screen/alerts/backgrounds.dmi b/icons/screen/alerts/backgrounds.dmi new file mode 100644 index 000000000000..2c328fea468e Binary files /dev/null and b/icons/screen/alerts/backgrounds.dmi differ diff --git a/icons/screen/alerts/encumbered.dmi b/icons/screen/alerts/encumbered.dmi new file mode 100644 index 000000000000..cd840acc6b73 Binary files /dev/null and b/icons/screen/alerts/encumbered.dmi differ diff --git a/tgui/packages/tgui/interfaces/ui/UIDynamicInputModal.tsx b/tgui/packages/tgui/interfaces/ui/UIDynamicInputModal.tsx new file mode 100644 index 000000000000..5eb69ae7c00e --- /dev/null +++ b/tgui/packages/tgui/interfaces/ui/UIDynamicInputModal.tsx @@ -0,0 +1,235 @@ +import { round } from "common/math"; +import { BooleanLike } from "common/react"; +import { useBackend, useLocalState } from "../../backend"; +import { Button, Dropdown, Input, NumberInput, Section, Stack, Tooltip } from "../../components"; +import { Window } from "../../layouts"; + +interface UIDynamicInputContext { + title: string; + message: string; + timeout: number; + // key to entry data + query: Record; +} + +type UIDynamicInputEntry = StringEntry | NumberEntry | PickEntry | ToggleEntry; + +interface BaseEntry { + name: string; + desc: string; +} + +interface StringEntry extends BaseEntry { + type: UIDynamicInputType.String; + constraints: StringConstraint; + default: StringOption; +} + +interface NumberEntry extends BaseEntry { + type: UIDynamicInputType.Number; + constraints: NumberConstraint; + default: NumberOption; +} + +interface PickEntry extends BaseEntry { + type: UIDynamicInputType.ListSingle; + constraints: ListConstraint; + default: ListOption; +} + +interface ToggleEntry extends BaseEntry { + type: UIDynamicInputType.Toggle; + constraints: ToggleConstraint; + default: ToggleOption; +} + +enum UIDynamicInputType { + String = "text", + Number = "num", + ListSingle = "list_single", + Toggle = "bool", +} + +type UIDynamicInputConstraint = StringConstraint | NumberConstraint | ListConstraint | ToggleConstraint; + +type StringConstraint = [number]; +type NumberConstraint = [number, number, number | null]; +type ListConstraint = string[]; +type ToggleConstraint = []; + +type UIDynamicInputOption = StringOption | NumberOption | ListOption | ToggleOption; + +type StringOption = string | null | undefined; +type NumberOption = number | null | undefined; +type ListOption = string | null | undefined; +type ToggleOption = BooleanLike; + +export const UIDynamicInputModal = (props, context) => { + const { data, act } = useBackend(context); + const [options, setOptions] =useLocalState>(context, 'options', {}); + return ( + + + + +
+ {data.message} +
+
+ +
+ + {Object.entries(data.query).map(([key, entry]) => ( + + + + + + {`${entry.name} `} + + + +
+
+ +
+ + + act('submit', { choices: preprocessOptions(options, data.query) })} /> + + + act('cancel')} /> + + +
+
+
+
+
+ ); +}; + +const preprocessOptions = (picked: Record, query: Record) => { + let built = {}; + for (let key in Object.keys(query)) { + built[key] = picked[key] === undefined? query[key].default : picked[key]; + } + return built; +}; + +interface DynamicEntryProps { + // eslint-disable-next-line react/no-unused-prop-types + id: string; + entry: UIDynamicInputEntry; + current: UIDynamicInputOption; + pick: (val: any) => void; +} + +const DynamicEntry = (props: DynamicEntryProps, context) => { + switch (props.entry.type) { + case UIDynamicInputType.ListSingle: + return ( + + ); + case UIDynamicInputType.Number: + return ( + + ); + case UIDynamicInputType.String: + return ( + + ); + case UIDynamicInputType.Toggle: + return ( + + ); + } +}; + +interface DynamicEntryNumberProps extends DynamicEntryProps { + entry: NumberEntry; + current: NumberOption; +} + +const DynamicEntryNumber = (props: DynamicEntryNumberProps, context) => { + let current = props.current === undefined? props.entry.default === null? 0 : props.entry.default : props.current; + return ( + props.pick( + props.entry.constraints[2] === null? val : round(val, props.entry.constraints[2]) + )} width="100%" /> + ); +}; + +interface DynamicEntryStringProps extends DynamicEntryProps { + entry: StringEntry; + current: StringOption; +} + +const DynamicEntryString = (props: DynamicEntryStringProps, context) => { + let current = props.current === undefined? props.entry.default === null? "" : props.entry.default : props.current; + return ( + props.pick( + val + )} width="100%" /> + ); +}; + +interface DynamicEntryPickProps extends DynamicEntryProps { + entry: PickEntry; + current: ListOption; +} + +const DynamicEntryPick = (props: DynamicEntryPickProps, context) => { + let current = props.current === undefined? ( + props.entry.constraints.length > 0? props.entry.constraints[0] : "" + ) : props.current; + return ( + props.pick(v)} /> + ); +}; + +interface DynamicEntryToggleProps extends DynamicEntryProps { + entry: ToggleEntry; + current: ToggleOption; +} + +const DynamicEntryToggle = (props: DynamicEntryToggleProps, context) => { + let current = props.current === undefined? !!props.entry.default : props.current; + return ( + props.pick(!current)} /> + ); +}; + +