diff --git a/code/game/objects/items/weapons/material/material_armor.dm b/code/game/objects/items/weapons/material/material_armor.dm index dccd65b567..1041fb5d1f 100644 --- a/code/game/objects/items/weapons/material/material_armor.dm +++ b/code/game/objects/items/weapons/material/material_armor.dm @@ -1,6 +1,29 @@ -// SEE code/modules/materials/materials.dm FOR DETAILS ON INHERITED DATUM. -// This class of weapons takes armor and appearance data from a material datum. -// They are also fragile based on material data and many can break/smash apart when hit. +#define MATERIAL_ARMOR_COEFFICENT 0.05 +/* +SEE code/modules/materials/materials.dm FOR DETAILS ON INHERITED DATUM. +This class of armor takes armor and appearance data from a material "datum". +They are also fragile based on material data and many can break/smash apart when hit. + +Materials has a var called protectiveness which plays a major factor in how good it is for armor. +With the coefficent being 0.05, this is how strong different levels of protectiveness are (for melee) +For bullets and lasers, material hardness and reflectivity also play a major role, respectively. + + +Protectiveness | Armor % + 0 = 0% + 5 = 20% + 10 = 33% + 15 = 42% + 20 = 50% + 25 = 55% + 30 = 60% + 40 = 66% + 50 = 71% + 60 = 75% + 70 = 77% + 80 = 80% +*/ + // Putting these at /clothing/ level saves a lot of code duplication in armor/helmets/gauntlets/etc /obj/item/clothing @@ -8,6 +31,7 @@ var/applies_material_color = TRUE var/unbreakable = FALSE var/default_material = null // Set this to something else if you want material attributes on init. + var/material_armor_modifer = 1 // Adjust if you want seperate types of armor made from the same material to have different protectiveness (e.g. makeshift vs real armor) /obj/item/clothing/New(var/newloc, var/material_key) ..(newloc) @@ -23,51 +47,115 @@ /obj/item/clothing/get_material() return material -// Debating if this should be made an /atom/movable/ proc. +// Debating if this should be made an /obj/item/ proc. /obj/item/clothing/proc/set_material(var/new_material) material = get_material_by_name(new_material) if(!material) qdel(src) else name = "[material.display_name] [initial(name)]" + health = round(material.integrity/10) if(applies_material_color) color = material.icon_colour if(material.products_need_process()) processing_objects |= src update_armor() -//f(x) = (x*a) / (x+b) + c -// a + c essentially* becomes your maximum possible output, -// c is your minimum, and b controls how quickly the output values scale and its effectiveness is relative to the value of a. +// This is called when someone wearing the object gets hit in some form (melee, bullet_act(), etc). +// Note that this cannot change if someone gets hurt, as it merely reacts to being hit. +/obj/item/clothing/proc/clothing_impact(var/obj/source, var/damage) + if(material && damage) + material_impact(source, damage) -// Max is the cap, excluding min. -// Mid is the midpoint on the curve. -// Min adds a floor to the answer. Min + Max is the maximum possible output. -/proc/calculate_curve(var/X, var/max, var/mid, var/min) - return (X * max) / (X + mid) + min +/obj/item/clothing/proc/material_impact(var/obj/source, var/damage) + if(!material || unbreakable) + return + + if(istype(source, /obj/item/projectile)) + var/obj/item/projectile/P = source + if(P.pass_flags & PASSGLASS) + if(material.opacity - 0.3 <= 0) + return // Lasers ignore 'fully' transparent material. + + if(material.is_brittle()) + health = 0 + else if(!prob(material.hardness)) + health-- + + if(health <= 0) + shatter() + +/obj/item/clothing/proc/shatter() + if(!material) + return + var/turf/T = get_turf(src) + T.visible_message("\The [src] [material.destruction_desc]!") + if(istype(loc, /mob/living)) + var/mob/living/M = loc + M.drop_from_inventory(src) + if(material.shard_type == SHARD_SHARD) // Wearing glass armor is a bad idea. + var/obj/item/weapon/material/shard/S = material.place_shard(T) + M.embed(S) + + playsound(src, "shatter", 70, 1) + qdel(src) + +// Might be best to make ablative vests a material armor using a new material to cut down on this copypaste. +/obj/item/clothing/suit/armor/handle_shield(mob/user, var/damage, atom/damage_source = null, mob/attacker = null, var/def_zone = null, var/attack_text = "the attack") + if(!material) // No point checking for reflection. + return ..() + + if(material.reflectivity) + if(istype(damage_source, /obj/item/projectile/energy) || istype(damage_source, /obj/item/projectile/beam)) + var/obj/item/projectile/P = damage_source + + if(P.reflected) // Can't reflect twice + return ..() + + var/reflectchance = (40 * material.reflectivity) - round(damage/3) + reflectchance *= material_armor_modifer + if(!(def_zone in list(BP_TORSO, BP_GROIN))) + reflectchance /= 2 + if(P.starting && prob(reflectchance)) + visible_message("\The [user]'s [src.name] reflects [attack_text]!") + + // Find a turf near or on the original location to bounce to + var/new_x = P.starting.x + pick(0, 0, 0, 0, 0, -1, 1, -2, 2) + var/new_y = P.starting.y + pick(0, 0, 0, 0, 0, -1, 1, -2, 2) + var/turf/curloc = get_turf(user) + + // redirect the projectile + P.redirect(new_x, new_y, curloc, user) + P.reflected = 1 + + return PROJECTILE_CONTINUE // complete projectile permutation + +/proc/calculate_material_armor(amount) + var/result = 1 - MATERIAL_ARMOR_COEFFICENT * amount / (1 + MATERIAL_ARMOR_COEFFICENT * abs(amount)) + result = result * 100 + result = abs(result - 100) + return round(result) -/client/verb/test_curve(var/X as num, var/A as num, var/B as num, var/C as num) - src << "Testing values: X:[X], A:[A], B:[B], C:[C]." - src << calculate_curve(X, A, B, C) /obj/item/clothing/proc/update_armor() if(material) var/melee_armor = 0, bullet_armor = 0, laser_armor = 0, energy_armor = 0, bomb_armor = 0 - melee_armor = round(Clamp(material.hardness, 0, 90)) + melee_armor = calculate_material_armor(material.protectiveness * material_armor_modifer) - bullet_armor = round(Clamp(material.hardness * 0.6, 0, 90)) + bullet_armor = calculate_material_armor((material.protectiveness * (material.hardness / 100) * material_armor_modifer) * 0.7) - laser_armor = material.hardness * 0.6 - if(material.reflectivity) - laser_armor *= (material.reflectivity + 1) // Each 0.1th of reflectivity gives 10% more protection. + laser_armor = calculate_material_armor((material.protectiveness * (material.reflectivity + 1) * material_armor_modifer) * 0.7) if(material.opacity != 1) laser_armor *= max(material.opacity - 0.3, 0) // Glass and such has an opacity of 0.3, but lasers should go through glass armor entirely. - laser_armor = round(Clamp(laser_armor, 0, 90)) - energy_armor = round(Clamp(laser_armor * 0.7, 0, 90)) + energy_armor = calculate_material_armor((material.protectiveness * material_armor_modifer) * 0.4) - bomb_armor = round(Clamp(material.explosion_resistance * 2, 0, 90)) + bomb_armor = calculate_material_armor((material.protectiveness * material_armor_modifer) * 0.5) + + // Makes sure the numbers stay capped. + for(var/number in list(melee_armor, bullet_armor, laser_armor, energy_armor, bomb_armor)) + number = between(0, number, 100) armor["melee"] = melee_armor armor["bullet"] = bullet_armor @@ -76,29 +164,100 @@ armor["bomb"] = bomb_armor if(!isnull(material.conductivity)) - siemens_coefficient = Clamp(material.conductivity / 10, 0, 4) - slowdown = Clamp(round(material.weight / 10, 0.1), 0, 6) -// armor = list( -// melee = melee_armor, -// bullet = bullet_armor, -// laser = laser_armor, -// energy = energy_armor, -// bomb = bomb_armor, -// bio = 0, -// rad = 0) -/* -/obj/item/weapon/material/proc/update_force() - if(edge || sharp) - force = material.get_edge_damage() - else - force = material.get_blunt_damage() - force = round(force*force_divisor) - throwforce = round(material.get_blunt_damage()*thrown_force_divisor) - //spawn(1) - // world << "[src] has force [force] and throwforce [throwforce] when made from default material [material.name]" -*/ + siemens_coefficient = between(0, material.conductivity / 10, 10) + slowdown = between(0, round(material.weight / 10, 0.1), 6) + /obj/item/clothing/suit/armor/material - icon_state = "material_armor_makeshift" // placeholder + name = "armor" default_material = DEFAULT_WALL_MATERIAL +/obj/item/clothing/suit/armor/material/makeshift + name = "sheet armor" + desc = "This appears to be two 'sheets' of a material held together by cable. If the sheets are strong, this could be rather protective." + icon_state = "material_armor_makeshift" +/obj/item/clothing/suit/armor/material/makeshift/durasteel + default_material = "durasteel" + +/obj/item/clothing/suit/armor/material/makeshift/glass + default_material = "glass" + +// Used to craft sheet armor, and possibly other things in the Future(tm). +/obj/item/weapon/material/armor_plating + name = "armor plating" + desc = "A sheet designed to protect something." + icon = 'icons/obj/items.dmi' + icon_state = "armor_plate" + unbreakable = TRUE + force_divisor = 0.05 // Really bad as a weapon. + thrown_force_divisor = 0.2 + var/wired = FALSE + +/obj/item/weapon/material/armor_plating/attackby(var/obj/O, mob/user) + if(istype(O, /obj/item/stack/cable_coil)) + var/obj/item/stack/cable_coil/S = O + if(wired) + to_chat(user, "This already has enough wires on it.") + return + if(S.use(20)) + to_chat(user, "You attach several wires to \the [src]. Now it needs another plate.") + wired = TRUE + icon_state = "[initial(icon_state)]_wired" + return + else + to_chat(user, "You need more wire for that.") + return + if(istype(O, /obj/item/weapon/material/armor_plating)) + var/obj/item/weapon/material/armor_plating/second_plate = O + if(!wired && !second_plate.wired) + to_chat(user, "You need something to hold the two pieces of plating together.") + return + if(second_plate.material != src.material) + to_chat(user, "Both plates need to be the same type of material.") + return + user.drop_from_inventory(src) + user.drop_from_inventory(second_plate) + var/obj/item/clothing/suit/armor/material/makeshift/new_armor = new(null, src.material.name) + user.put_in_hands(new_armor) + qdel(second_plate) + qdel(src) + else + ..() + + +// Used to craft the makeshift helmet +/obj/item/clothing/head/helmet/bucket + name = "bucket" + desc = "It's a bucket with a large hole cut into it. You could wear it on your head and look really stupid." + flags_inv = HIDEEARS|HIDEEYES|BLOCKHAIR + icon_state = "bucket" + armor = list(melee = 5, bullet = 0, laser = 0, energy = 0, bomb = 0, bio = 0, rad = 0) + +/obj/item/clothing/head/helmet/bucket/attackby(var/obj/O, mob/user) + if(istype(O, /obj/item/stack/material)) + var/obj/item/stack/material/S = O + if(S.use(2)) + to_chat(user, "You apply some [S.material.use_name] to \the [src]. Hopefully it'll make the makeshift helmet stronger.") + var/obj/item/clothing/head/helmet/material/makeshift/helmet = new(null, S.material.name) + user.put_in_hands(helmet) + user.drop_from_inventory(src) + qdel(src) + return + else + to_chat(user, "You don't have enough material to build a helmet!") + else + ..() + +/obj/item/clothing/head/helmet/material + name = "helmet" + flags_inv = HIDEEARS|HIDEEYES|BLOCKHAIR + default_material = DEFAULT_WALL_MATERIAL + +/obj/item/clothing/head/helmet/material/makeshift + name = "bucket" + desc = "A bucket with plating applied to the outside. Very crude, but could potentially be rather protective, if \ + it was plated with something strong." + icon_state = "material_armor_makeshift" + +/obj/item/clothing/head/helmet/material/makeshift/durasteel + default_material = "durasteel" \ No newline at end of file diff --git a/code/modules/clothing/suits/armor.dm b/code/modules/clothing/suits/armor.dm index d08726371a..f090312320 100644 --- a/code/modules/clothing/suits/armor.dm +++ b/code/modules/clothing/suits/armor.dm @@ -80,6 +80,9 @@ if(istype(damage_source, /obj/item/projectile/energy) || istype(damage_source, /obj/item/projectile/beam)) var/obj/item/projectile/P = damage_source + if(P.reflected) // Can't reflect twice + return ..() + var/reflectchance = 40 - round(damage/3) if(!(def_zone in list(BP_TORSO, BP_GROIN))) reflectchance /= 2 diff --git a/code/modules/materials/material_recipes.dm b/code/modules/materials/material_recipes.dm index 11f6021c75..68fb129108 100644 --- a/code/modules/materials/material_recipes.dm +++ b/code/modules/materials/material_recipes.dm @@ -10,6 +10,7 @@ recipes += new/datum/stack_recipe("[display_name] baseball bat", /obj/item/weapon/material/twohanded/baseballbat, 10, time = 20, one_per_turf = 0, on_floor = 1, supplied_material = "[name]") recipes += new/datum/stack_recipe("[display_name] ashtray", /obj/item/weapon/material/ashtray, 2, one_per_turf = 1, on_floor = 1, supplied_material = "[name]") recipes += new/datum/stack_recipe("[display_name] spoon", /obj/item/weapon/material/kitchen/utensil/spoon/plastic, 1, on_floor = 1, supplied_material = "[name]") + recipes += new/datum/stack_recipe("[display_name] armor plate", /obj/item/weapon/material/armor_plating, 1, time = 20, on_floor = 1, supplied_material = "[name]") if(integrity>=50) recipes += new/datum/stack_recipe("[display_name] door", /obj/structure/simple_door, 10, one_per_turf = 1, on_floor = 1, supplied_material = "[name]") diff --git a/code/modules/materials/materials.dm b/code/modules/materials/materials.dm index 5886c8447f..db4fbebc00 100644 --- a/code/modules/materials/materials.dm +++ b/code/modules/materials/materials.dm @@ -90,11 +90,12 @@ var/list/name_to_material var/ignition_point // K, point at which the material catches on fire. var/melting_point = 1800 // K, walls will take damage if they're next to a fire hotter than this var/integrity = 150 // General-use HP value for products. + var/protectiveness = 10 // How well this material works as armor. Higher numbers are better, diminishing returns applies. var/opacity = 1 // Is the material transparent? 0.5< makes transparent walls/doors. - var/reflectivity = 0 // How reflective to light is the material? Currently used for laser defense. + var/reflectivity = 0 // How reflective to light is the material? Currently used for laser reflection and defense. var/explosion_resistance = 5 // Only used by walls currently. var/conductive = 1 // Objects with this var add CONDUCTS to flags on spawn. - var/conductivity = null // How conductive the material is. Based somewhat on megasiemens / metre at 20c + var/conductivity = null // How conductive the material is. Iron acts as the baseline, at 10. var/list/composite_material // If set, object matter var will be a list containing these values. // Placeholder vars for the time being, todo properly integrate windows/light tiles/rods. @@ -104,7 +105,7 @@ var/list/name_to_material var/list/window_options = list() // Damage values. - var/hardness = 60 // Prob of wall destruction by hulk, used for edge damage in weapons. + var/hardness = 60 // Prob of wall destruction by hulk, used for edge damage in weapons. Also used for bullet protection in armor. var/weight = 20 // Determines blunt damage/throwforce for weapons. // Noise when someone is faceplanted onto a table made of this material. @@ -237,6 +238,7 @@ var/list/name_to_material icon_colour = "#00FFE1" opacity = 0.4 reflectivity = 0.6 + conductivity = 1 shard_type = SHARD_SHARD tableslam_noise = 'sound/effects/Glasshit.ogg' hardness = 100 @@ -307,6 +309,8 @@ var/list/name_to_material shard_type = SHARD_STONE_PIECE weight = 22 hardness = 55 + protectiveness = 5 // 20% + conductivity = 5 door_icon_base = "stone" sheet_singular_name = "brick" sheet_plural_name = "bricks" @@ -323,7 +327,8 @@ var/list/name_to_material name = DEFAULT_WALL_MATERIAL stack_type = /obj/item/stack/material/steel integrity = 150 - conductivity = 6.99 // Assuming this is carbon steel + conductivity = 11 // Assuming this is carbon steel, it would actually be slightly less conductive than iron, but lets ignore that. + protectiveness = 10 // 33% icon_base = "solid" icon_reinf = "reinf_over" icon_colour = "#666666" @@ -359,6 +364,8 @@ var/list/name_to_material explosion_resistance = 25 hardness = 80 weight = 23 + protectiveness = 20 // 50% + conductivity = 13 // For the purposes of balance. stack_origin_tech = list(TECH_MATERIAL = 2) composite_material = list(DEFAULT_WALL_MATERIAL = SHEET_MATERIAL_AMOUNT, "platinum" = SHEET_MATERIAL_AMOUNT) //todo @@ -374,6 +381,7 @@ var/list/name_to_material explosion_resistance = 75 hardness = 100 weight = 28 + protectiveness = 60 // 75% reflectivity = 0.7 // Not a perfect mirror, but close. stack_origin_tech = list(TECH_MATERIAL = 8) composite_material = list("plasteel" = SHEET_MATERIAL_AMOUNT, "diamond" = SHEET_MATERIAL_AMOUNT) //shrug @@ -398,6 +406,8 @@ var/list/name_to_material tableslam_noise = 'sound/effects/Glasshit.ogg' hardness = 30 weight = 15 + protectiveness = 0 // 0% + conductivity = 1 // Glass shards don't conduct. door_icon_base = "stone" destruction_desc = "shatters" window_options = list("One Direction" = 1, "Full Window" = 4, "Windoor" = 2) @@ -531,6 +541,8 @@ var/list/name_to_material icon_colour = "#CCCCCC" hardness = 10 weight = 12 + protectiveness = 5 // 20% + conductivity = 2 // For the sake of material armor diversity, we're gonna pretend this plastic is a good insulator. melting_point = T0C+371 //assuming heat resistant plastic stack_origin_tech = list(TECH_MATERIAL = 3) @@ -561,6 +573,7 @@ var/list/name_to_material stack_type = /obj/item/stack/material/mhydrogen icon_colour = "#E6C5DE" stack_origin_tech = list(TECH_MATERIAL = 6, TECH_POWER = 6, TECH_MAGNET = 5) + conductivity = 100 /material/platinum name = "platinum" @@ -592,6 +605,7 @@ var/list/name_to_material explosion_resistance = 200 // Hull plating. hardness = 500 weight = 500 + protectiveness = 80 // 80% // Likewise. /material/alienalloy/elevatorium @@ -610,6 +624,8 @@ var/list/name_to_material shard_can_repair = 0 // you can't weld splinters back into planks hardness = 15 weight = 18 + protectiveness = 8 // 28% + conductivity = 1 melting_point = T0C+300 //okay, not melting in this case, but hot enough to destroy wood ignition_point = T0C+288 stack_origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1) @@ -641,6 +657,7 @@ var/list/name_to_material icon_colour = "#AAAAAA" hardness = 1 weight = 1 + protectiveness = 0 // 0% ignition_point = T0C+232 //"the temperature at which book-paper catches fire, and burns." close enough melting_point = T0C+232 //temperature at which cardboard walls would be destroyed stack_origin_tech = list(TECH_MATERIAL = 1) @@ -657,6 +674,7 @@ var/list/name_to_material integrity = 1 hardness = 1 weight = 1 + protectiveness = 0 // 0% stack_origin_tech = list(TECH_MATERIAL = 1) melting_point = T0C+1 destruction_desc = "crumples" @@ -669,6 +687,7 @@ var/list/name_to_material door_icon_base = "wood" ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% flags = MATERIAL_PADDING /material/cult @@ -702,6 +721,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+300 melting_point = T0C+300 + protectiveness = 3 // 13% /material/carpet name = "carpet" @@ -713,6 +733,7 @@ var/list/name_to_material melting_point = T0C+300 sheet_singular_name = "tile" sheet_plural_name = "tiles" + protectiveness = 1 // 4% /material/cotton name = "cotton" @@ -721,7 +742,9 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% +// This all needs to be OOP'd and use inheritence if its ever used in the future. /material/cloth_teal name = "teal" display_name ="teal" @@ -730,6 +753,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_black name = "black" @@ -739,6 +763,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_green name = "green" @@ -748,6 +773,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_puple name = "purple" @@ -757,6 +783,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_blue name = "blue" @@ -766,6 +793,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_beige name = "beige" @@ -775,6 +803,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/cloth_lime name = "lime" @@ -784,6 +813,7 @@ var/list/name_to_material flags = MATERIAL_PADDING ignition_point = T0C+232 melting_point = T0C+300 + protectiveness = 1 // 4% /material/toy_foam name = "foam" @@ -794,4 +824,5 @@ var/list/name_to_material melting_point = T0C+300 icon_colour = "#ff9900" hardness = 1 - weight = 1 \ No newline at end of file + weight = 1 + protectiveness = 0 // 0% \ No newline at end of file diff --git a/code/modules/mob/living/carbon/human/human_defense.dm b/code/modules/mob/living/carbon/human/human_defense.dm index 86bbdebc15..f5fa2f582c 100644 --- a/code/modules/mob/living/carbon/human/human_defense.dm +++ b/code/modules/mob/living/carbon/human/human_defense.dm @@ -27,6 +27,11 @@ emp_act if(!P.nodamage) organ.add_autopsy_data("[P.name]", P.damage) + // Tell clothing we're wearing that it got hit by a bullet/laser/etc + var/list/clothing = get_clothing_list_organ(organ) + for(var/obj/item/clothing/C in clothing) + C.clothing_impact(P, P.damage) + //Shrapnel if(P.can_embed()) var/armor = getarmor_organ(organ, "bullet") @@ -130,6 +135,15 @@ emp_act return siemens_coefficient +// Returns a list of clothing that is currently covering def_zone. +/mob/living/carbon/human/proc/get_clothing_list_organ(var/obj/item/organ/external/def_zone, var/type) + var/list/results = list() + var/list/clothing_items = list(head, wear_mask, wear_suit, w_uniform, gloves, shoes) + for(var/obj/item/clothing/C in clothing_items) + if(istype(C) && (C.body_parts_covered & def_zone.body_part)) + results.Add(C) + return results + //this proc returns the armour value for a particular external organ. /mob/living/carbon/human/proc/getarmor_organ(var/obj/item/organ/external/def_zone, var/type) if(!type || !def_zone) return 0 @@ -246,6 +260,12 @@ emp_act if(!affecting) return 0 + // Allow clothing to respond to being hit. + // This is done up here so that clothing damage occurs even if fully blocked. + var/list/clothing = get_clothing_list_organ(affecting) + for(var/obj/item/clothing/C in clothing) + C.clothing_impact(I, effective_force) + if(soaked >= effective_force) return 0 diff --git a/code/modules/reagents/reagent_containers/glass.dm b/code/modules/reagents/reagent_containers/glass.dm index ed27e1a259..bd670cc8bc 100644 --- a/code/modules/reagents/reagent_containers/glass.dm +++ b/code/modules/reagents/reagent_containers/glass.dm @@ -243,6 +243,12 @@ user.drop_from_inventory(src) qdel(src) return + else if(istype(D, /obj/item/weapon/wirecutters)) + to_chat(user, "You cut a big hole in \the [src] with \the [D]. It's kinda useless as a bucket now.") + user.put_in_hands(new /obj/item/clothing/head/helmet/bucket) + user.drop_from_inventory(src) + qdel(src) + return else if(istype(D, /obj/item/weapon/mop)) if(reagents.total_volume < 1) user << "\The [src] is empty!" diff --git a/icons/mob/head.dmi b/icons/mob/head.dmi index 7407aeefb5..44f920fe30 100644 Binary files a/icons/mob/head.dmi and b/icons/mob/head.dmi differ diff --git a/icons/obj/clothing/hats.dmi b/icons/obj/clothing/hats.dmi index 9337d5127c..ef18c7bf49 100644 Binary files a/icons/obj/clothing/hats.dmi and b/icons/obj/clothing/hats.dmi differ diff --git a/icons/obj/items.dmi b/icons/obj/items.dmi index dc3456ba67..778ec461bb 100644 Binary files a/icons/obj/items.dmi and b/icons/obj/items.dmi differ