diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm
index 5486cac1252..f1ac1af1afa 100644
--- a/code/_onclick/item_attack.dm
+++ b/code/_onclick/item_attack.dm
@@ -79,7 +79,7 @@
var/turf/location = get_turf(src)
add_splatter_floor(location)
if(get_dist(user, src) <= 1) //people with TK won't get smeared with blood
- user.forensics.add_mob_blood(src)
+ user.add_mob_blood(src)
return TRUE //successful attack
/mob/living/simple_animal/attacked_by(obj/item/I, mob/living/user)
diff --git a/code/datums/forensics.dm b/code/datums/forensics.dm
deleted file mode 100644
index bb93642fa98..00000000000
--- a/code/datums/forensics.dm
+++ /dev/null
@@ -1,202 +0,0 @@
-//////////////////////FORENSICS DATUM
-/datum/forensics
- var/list/gsr
- var/list/prints
- var/list/hiddenprints
- var/list/fibers
- var/list/blood
- var/maxSize = 5
-
-/datum/forensics/proc/transfer_mob_blood_dna(mob/living/L)
- // Returns 0 if we have that blood already
- var/new_blood_dna = blood
- if(!new_blood_dna)
- return FALSE
- var/old_length = blood.len
- blood |= new_blood_dna
- if(blood.len == old_length)
- return FALSE
- return TRUE
-
-/obj/proc/transfer_mob_blood_dna(mob/living/L)
- . = forensics.transfer_mob_blood_dna(L)
-
-//to add blood dna info to the object's blood_DNA list
-/datum/forensics/proc/transfer_blood_dna(list/blood_dna)
- var/old_length = blood.len
- blood |= blood_dna
- if(blood.len > old_length)
- return TRUE //some new blood DNA was added
-
-/obj/proc/transfer_blood_dna(list/blood_dna)
- . = forensics.transfer_blood_dna(blood_dna)
-
-//to add blood from a mob onto something, and transfer their dna info
-/datum/forensics/proc/add_mob_blood(mob/living/M)
- var/list/blood_dna = M.forensics.blood
- if(!blood_dna)
- return FALSE
- return add_blood(blood_dna)
-
-/obj/proc/add_mob_blood(mob/living/M)
- . = forensics.add_mob_blood(M)
-
-/datum/forensics/proc/add_blood(list/blood_dna)
- return FALSE
-
-/obj/proc/add_blood(list/blood_dna)
- . = forensics.transfer_blood_dna(blood_dna)
-
-//to add blood onto something, with blood dna info to include.
-
-
-/obj/item/add_blood(list/blood_dna)
- var/blood_count = !forensics.blood ? 0 : forensics.blood.len
- if(!..())
- return FALSE
- if(!blood_count)//apply the blood-splatter overlay if it isn't already in there
- add_blood_overlay()
- return TRUE //we applied blood to the item
-
-/datum/forensics/proc/clean_blood()
- if(islist(blood))
- blood = list()
- return TRUE
- return FALSE
-
-/obj/proc/clean_blood()
- . = forensics.clean_blood()
-
-/datum/forensics/proc/clean_prints()
- if(islist(prints))
- prints = list()
- return TRUE
- return FALSE
-
-/obj/proc/clean_prints()
- . = forensics.clean_prints()
-
-
-/datum/forensics/proc/add_hiddenprint(mob/living/M)
- if(!M || !M.key)
- return
-
- if(M.forensics.hiddenprints) //Add the list if it does not exist
- M.forensics.hiddenprints = list()
-
- var/hasgloves = ""
- if(ishuman(M))
- var/mob/living/carbon/human/H = M
- if(H.gloves)
- hasgloves = "(gloves)"
-
- var/current_time = time_stamp()
- if(!M.forensics.hiddenprints[M.key])
- M.forensics.hiddenprints[M.key] = "First: [M.real_name]\[[current_time]\][hasgloves]. Ckey: [M.ckey]"
- else
- var/laststamppos = findtext(M.forensics.hiddenprints[M.key], " Last: ")
- if(laststamppos)
- M.forensics.hiddenprints[M.key] = copytext(M.forensics.hiddenprints[M.key], 1, laststamppos)
- M.forensics.hiddenprints[M.key] += " Last: [M.real_name]\[[current_time]\][hasgloves]. Ckey: [M.ckey]"
-
- fingerprintslast = M.ckey
-
-//Set ignoregloves to add prints irrespective of the mob having gloves on.
-/datum/forensics/proc/add_fingerprint(mob/living/M, ignoregloves = 0)
- if(!M || !M.key)
- return
-
- M.add_hiddenprint(M)
-
- if(ishuman(M))
- var/mob/living/carbon/human/H = M
-
- M.forensics.add_fibers(H)
-
- if(H.gloves) //Check if the gloves (if any) hide fingerprints
- var/obj/item/clothing/gloves/G = H.gloves
- if(G.transfer_prints)
- ignoregloves = 1
-
- if(!ignoregloves)
- H.gloves.add_fingerprint(H, 1) //ignoregloves = 1 to avoid infinite loop.
- return
-
- if(!M.forensics.prints) //Add the list if it does not exist
- M.forensics.prints = list()
- var/full_print = md5(H.dna.uni_identity)
- M.forensics.prints[full_print] = full_print
-
-/datum/forensics/proc/add_fibers(mob/living/carbon/human/M)
- var/datum/forensics/forensics = M.forensics
- if(M.gloves && istype(M.gloves, /obj/item/clothing/))
- var/obj/item/clothing/gloves/G = M.gloves
- if(G.transfer_blood > 1) //bloodied gloves transfer blood to touched objects
- if(forensics.add_blood(G.forensics.blood)) //only reduces the bloodiness of our gloves if the item wasn't already bloody
- G.transfer_blood--
- else if(M.bloody_hands > 1)
- if(forensics.add_blood(M.forensics.blood))
- M.bloody_hands--
- if(!forensics.fibers) forensics.fibers = list()
- var/fibertext
- var/item_multiplier = isitem(src)?1.2:1
- if(M.wear_suit)
- fibertext = "Material from \a [M.wear_suit]."
- if(prob(10*item_multiplier) && !(fibertext in forensics.fibers))
- forensics.fibers += fibertext
- if(!(M.wear_suit.body_parts_covered & CHEST))
- if(M.w_uniform)
- fibertext = "Fibers from \a [M.w_uniform]."
- if(prob(12*item_multiplier) && !(fibertext in forensics.fibers)) //Wearing a suit means less of the uniform exposed.
- forensics.fibers += fibertext
- if(!(M.wear_suit.body_parts_covered & HANDS))
- if(M.gloves)
- forensics.fibers = "Material from a pair of [M.gloves.name]."
- if(prob(20*item_multiplier) && !(fibertext in forensics.fibers))
- forensics.fibers += fibertext
- else if(M.w_uniform)
- fibertext = "Fibers from \a [M.w_uniform]."
- if(prob(15*item_multiplier) && !(fibertext in forensics.fibers))
- // "Added fibertext: [fibertext]"
- forensics.fibers += fibertext
- if(M.gloves)
- fibertext = "Material from a pair of [M.gloves.name]."
- if(prob(20*item_multiplier) && !(fibertext in forensics.fibers))
- forensics.fibers += "Material from a pair of [M.gloves.name]."
- else if(M.gloves)
- fibertext = "Material from a pair of [M.gloves.name]."
- if(prob(20*item_multiplier) && !(fibertext in forensics.fibers))
- forensics.fibers += "Material from a pair of [M.gloves.name]."
-
-/atom/proc/add_fibers(mob/living/carbon/human/M)
- . = forensics.add_fibers(M)
-
-/datum/forensics/proc/transfer_fingerprints_to(atom/A)
-
- // Make sure everything are lists.
- if(!islist(A.forensics.prints))
- A.forensics.prints = list()
- if(!islist(A.forensics.hiddenprints))
- A.forensics.hiddenprints = list()
-
- if(!islist(prints))
- prints = list()
- if(!islist(hiddenprints))
- hiddenprints = list()
-
- // Transfer
- if(LAZYLEN(prints))
- A.forensics.prints |= prints.Copy() //detective
- if(LAZYLEN(hiddenprints))
- A.forensics.hiddenprints |= hiddenprints.Copy() //admin
- A.fingerprintslast = fingerprintslast
-
-
-/atom/proc/transfer_fingerprints_to(atom/A)
- return forensics.transfer_fingerprints_to(A)
-
-/atom/proc/add_fingerprint(mob/living/M, ignoregloves = 0)
- return forensics.add_fingerprint(M, ignoregloves)
-
-/atom/proc/add_hiddenprint(mob/living/M)
- return forensics.add_hiddenprint(M)
\ No newline at end of file
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index 03db8f1ed0a..938f6c6f100 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -6,10 +6,12 @@
var/flags_1 = 0
var/flags_2 = 0
+ var/list/fingerprints
+ var/list/fingerprintshidden
+ var/list/blood_DNA
var/container_type = 0
var/admin_spawned = 0 //was this spawned by an admin? used for stat tracking stuff.
- var/datum/reagents/reagents
- var/datum/forensics/forensics
+ var/datum/reagents/reagents = null
//This atom's HUD (med/sec, etc) images. Associative list.
var/list/image/hud_list = null
@@ -64,9 +66,6 @@
stack_trace("Warning: [src]([type]) initialized multiple times!")
initialized = TRUE
- if(!forensics)
- forensics = new
-
//atom color stuff
if(color)
add_atom_colour(color, FIXED_COLOUR_PRIORITY)
@@ -89,8 +88,8 @@
var/datum/atom_hud/alternate_appearance/AA = alternate_appearances[K]
AA.remove_from_hud(src)
- QDEL_NULL(reagents)
- QDEL_NULL(forensics)
+ if(reagents)
+ qdel(reagents)
LAZYCLEARLIST(overlays)
LAZYCLEARLIST(priority_overlays)
@@ -162,9 +161,6 @@
reagents = new()
reagents.reagent_list.Add(A)
reagents.conditional_update()
- if(istype(A, /datum/forensics))
- if(!forensics)
- forensics = new
else if(ismovableatom(A))
var/atom/movable/M = A
if(isliving(M.loc))
@@ -267,7 +263,7 @@
/atom/proc/examine(mob/user)
//This reformat names to get a/an properly working on item descriptions when they are bloody
var/f_name = "\a [src]."
- if(forensics.blood.len > 0 && !istype(src, /obj/effect/decal))
+ if(src.blood_DNA && !istype(src, /obj/effect/decal))
if(gender == PLURAL)
f_name = "some "
else
@@ -343,8 +339,51 @@ GLOBAL_LIST_EMPTY(blood_splatter_icons)
/mob/living/carbon/alien/get_blood_dna_list()
return list("UNKNOWN DNA" = "X*")
+//to add a mob's dna info into an object's blood_DNA list.
+/atom/proc/transfer_mob_blood_dna(mob/living/L)
+ // Returns 0 if we have that blood already
+ var/new_blood_dna = L.get_blood_dna_list()
+ if(!new_blood_dna)
+ return 0
+ if(!blood_DNA) //if our list of DNA doesn't exist yet, initialise it.
+ blood_DNA = list()
+ var/old_length = blood_DNA.len
+ blood_DNA |= new_blood_dna
+ if(blood_DNA.len == old_length)
+ return 0
+ return 1
+
+//to add blood dna info to the object's blood_DNA list
+/atom/proc/transfer_blood_dna(list/blood_dna)
+ if(!blood_DNA)
+ blood_DNA = list()
+ var/old_length = blood_DNA.len
+ blood_DNA |= blood_dna
+ if(blood_DNA.len > old_length)
+ return 1//some new blood DNA was added
+//to add blood from a mob onto something, and transfer their dna info
+/atom/proc/add_mob_blood(mob/living/M)
+ var/list/blood_dna = M.get_blood_dna_list()
+ if(!blood_dna)
+ return 0
+ return add_blood(blood_dna)
+
+//to add blood onto something, with blood dna info to include.
+/atom/proc/add_blood(list/blood_dna)
+ return 0
+
+/obj/add_blood(list/blood_dna)
+ return transfer_blood_dna(blood_dna)
+
+/obj/item/add_blood(list/blood_dna)
+ var/blood_count = !blood_DNA ? 0 : blood_DNA.len
+ if(!..())
+ return 0
+ if(!blood_count)//apply the blood-splatter overlay if it isn't already in there
+ add_blood_overlay()
+ return 1 //we applied blood to the item
/obj/item/proc/add_blood_overlay()
if(initial(icon) && initial(icon_state))
@@ -363,29 +402,33 @@ GLOBAL_LIST_EMPTY(blood_splatter_icons)
. = ..()
transfer_blood = rand(2, 4)
-/turf/proc/add_blood(list/blood_dna)
+/turf/add_blood(list/blood_dna)
var/obj/effect/decal/cleanable/blood/splatter/B = locate() in src
if(!B)
B = new /obj/effect/decal/cleanable/blood/splatter(src)
- B.forensics.transfer_blood_dna(blood_dna) //give blood info to the blood decal.
+ B.transfer_blood_dna(blood_dna) //give blood info to the blood decal.
return 1 //we bloodied the floor
-/mob/living/carbon/human/proc/add_blood(list/blood_dna)
+/mob/living/carbon/human/add_blood(list/blood_dna)
if(wear_suit)
- wear_suit.forensics.add_blood(blood_dna)
+ wear_suit.add_blood(blood_dna)
update_inv_wear_suit()
else if(w_uniform)
- w_uniform.forensics.add_blood(blood_dna)
+ w_uniform.add_blood(blood_dna)
update_inv_w_uniform()
if(gloves)
var/obj/item/clothing/gloves/G = gloves
- G.forensics.add_blood(blood_dna)
+ G.add_blood(blood_dna)
else
- forensics.transfer_blood_dna(blood_dna)
+ transfer_blood_dna(blood_dna)
bloody_hands = rand(2, 4)
update_inv_gloves() //handles bloody hands overlays and updating
return 1
+/atom/proc/clean_blood()
+ if(islist(blood_DNA))
+ blood_DNA = null
+ return 1
/atom/proc/wash_cream()
return 1
diff --git a/code/game/atoms_movable.dm b/code/game/atoms_movable.dm
index a413510fb02..b4e6db1ebe0 100644
--- a/code/game/atoms_movable.dm
+++ b/code/game/atoms_movable.dm
@@ -149,7 +149,7 @@
/atom/movable/proc/clean_on_move()
var/turf/tile = loc
if(isturf(tile))
- tile.forensics.clean_blood()
+ tile.clean_blood()
for(var/A in tile)
if(is_cleanable(A))
qdel(A)
@@ -171,7 +171,7 @@
if(cleaned_human.shoes)
cleaned_human.shoes.clean_blood()
cleaned_human.update_inv_shoes()
- cleaned_human.forensics.clean_blood()
+ cleaned_human.clean_blood()
cleaned_human.wash_cream()
to_chat(cleaned_human, "[src] cleans your face!")
diff --git a/code/game/gamemodes/changeling/powers/mutations.dm b/code/game/gamemodes/changeling/powers/mutations.dm
index 0c6e3924a58..443720fefc4 100644
--- a/code/game/gamemodes/changeling/powers/mutations.dm
+++ b/code/game/gamemodes/changeling/powers/mutations.dm
@@ -307,7 +307,7 @@
C.visible_message("[H] impales [C] with [H.p_their()] [I.name]!", "[H] impales you with [H.p_their()] [I.name]!")
C.apply_damage(I.force, BRUTE, "chest")
H.do_item_attack_animation(C, used_item = I)
- H.forensics.add_mob_blood(C)
+ H.add_mob_blood(C)
playsound(get_turf(H),I.hitsound,75,1)
return
diff --git a/code/game/gamemodes/devil/true_devil/_true_devil.dm b/code/game/gamemodes/devil/true_devil/_true_devil.dm
index 89ee9a9c7d4..5b85cbd811c 100644
--- a/code/game/gamemodes/devil/true_devil/_true_devil.dm
+++ b/code/game/gamemodes/devil/true_devil/_true_devil.dm
@@ -66,7 +66,7 @@
//Left hand items
for(var/obj/item/I in held_items)
if(!(I.flags_1 & ABSTRACT_1))
- if(LAZYLEN(I.forensics.blood))
+ if(I.blood_DNA)
msg += "It is holding [icon2html(I, user)] [I.gender==PLURAL?"some":"a"] blood-stained [I.name] in its [get_held_index_name(get_held_index_of_item(I))]!\n"
else
msg += "It is holding [icon2html(I, user)] \a [I] in its [get_held_index_name(get_held_index_of_item(I))].\n"
diff --git a/code/game/gamemodes/miniantags/abduction/gland.dm b/code/game/gamemodes/miniantags/abduction/gland.dm
index 42cbc2c5181..8c408c007e4 100644
--- a/code/game/gamemodes/miniantags/abduction/gland.dm
+++ b/code/game/gamemodes/miniantags/abduction/gland.dm
@@ -188,7 +188,7 @@
for(var/turf/T in oview(3,owner)) //Make this respect walls and such
owner.add_splatter_floor(T)
for(var/mob/living/carbon/human/H in oview(3,owner)) //Blood decals for simple animals would be neat. aka Carp with blood on it.
- H.forensics.add_mob_blood(owner)
+ H.add_mob_blood(owner)
/obj/item/organ/heart/gland/bodysnatch
diff --git a/code/game/gamemodes/wizard/artefact.dm b/code/game/gamemodes/wizard/artefact.dm
index 5c4e7b550d1..03e5d70b7a4 100644
--- a/code/game/gamemodes/wizard/artefact.dm
+++ b/code/game/gamemodes/wizard/artefact.dm
@@ -542,7 +542,7 @@
if(!link)
return
for(var/mob/living/carbon/human/H in GLOB.living_mob_list)
- if(md5(H.dna.uni_identity) in link.forensics.prints)
+ if(md5(H.dna.uni_identity) in link.fingerprints)
possible |= H
/obj/item/voodoo/proc/GiveHint(mob/victim,force=0)
diff --git a/code/game/machinery/suit_storage_unit.dm b/code/game/machinery/suit_storage_unit.dm
index d1bc5475b7e..5393bd9a9e7 100644
--- a/code/game/machinery/suit_storage_unit.dm
+++ b/code/game/machinery/suit_storage_unit.dm
@@ -234,8 +234,8 @@
visible_message("[src]'s door slides open, barraging you with the nauseating smell of charred flesh.")
playsound(src, 'sound/machines/airlockclose.ogg', 25, 1)
for(var/obj/item/I in src) //Scorches away blood and forensic evidence, although the SSU itself is unaffected
- I.forensics.clean_blood()
- I.forensics.clean_prints()
+ I.clean_blood()
+ I.fingerprints = list()
open_machine(FALSE)
if(occupant)
dump_contents()
diff --git a/code/game/machinery/washing_machine.dm b/code/game/machinery/washing_machine.dm
index 18870d291b7..f1384c0ea33 100644
--- a/code/game/machinery/washing_machine.dm
+++ b/code/game/machinery/washing_machine.dm
@@ -49,7 +49,7 @@
/obj/machinery/washing_machine/proc/wash_cycle()
for(var/X in contents)
var/atom/movable/AM = X
- AM.forensics.clean_blood()
+ AM.clean_blood()
AM.machine_wash(src)
busy = FALSE
diff --git a/code/game/objects/effects/decals/cleanable.dm b/code/game/objects/effects/decals/cleanable.dm
index e5e725fc30f..45772661843 100644
--- a/code/game/objects/effects/decals/cleanable.dm
+++ b/code/game/objects/effects/decals/cleanable.dm
@@ -76,8 +76,8 @@
add_blood = bloodiness
bloodiness -= add_blood
S.bloody_shoes[blood_state] = min(MAX_SHOE_BLOODINESS,S.bloody_shoes[blood_state]+add_blood)
- if(LAZYLEN(forensics.blood))
- S.add_blood(forensics.blood)
+ if(blood_DNA && blood_DNA.len)
+ S.add_blood(blood_DNA)
S.blood_state = blood_state
update_icon()
H.update_inv_shoes()
diff --git a/code/game/objects/effects/decals/cleanable/aliens.dm b/code/game/objects/effects/decals/cleanable/aliens.dm
index 10884ee0453..26b5bca1ec1 100644
--- a/code/game/objects/effects/decals/cleanable/aliens.dm
+++ b/code/game/objects/effects/decals/cleanable/aliens.dm
@@ -6,15 +6,9 @@
icon = 'icons/effects/blood.dmi'
icon_state = "xfloor1"
random_icon_states = list("xfloor1", "xfloor2", "xfloor3", "xfloor4", "xfloor5", "xfloor6", "xfloor7")
+ blood_DNA = list("UNKNOWN DNA" = "X*")
bloodiness = MAX_SHOE_BLOODINESS
blood_state = BLOOD_STATE_XENO
- var/list/viruses
-
-/obj/effect/decal/cleanable/xenoblood/Initialize()
- . = ..()
- forensics.blood = list("UNKNOWN DNA" = "X*")
- viruses = list()
-
/obj/effect/decal/cleanable/xenoblood/xsplatter
random_icon_states = list("xgibbl1", "xgibbl2", "xgibbl3", "xgibbl4", "xgibbl5")
@@ -68,7 +62,4 @@
/obj/effect/decal/cleanable/blood/xtracks
icon_state = "xtracks"
random_icon_states = null
-
-/obj/effect/decal/cleanable/blood/xtracks/Initialize()
- . = ..()
- forensics.blood = list("UNKNOWN DNA" = "X*")
\ No newline at end of file
+ blood_DNA = list("UNKNOWN DNA" = "X*")
diff --git a/code/game/objects/effects/decals/cleanable/humans.dm b/code/game/objects/effects/decals/cleanable/humans.dm
index 8fd933e7780..72a721911fe 100644
--- a/code/game/objects/effects/decals/cleanable/humans.dm
+++ b/code/game/objects/effects/decals/cleanable/humans.dm
@@ -4,13 +4,13 @@
icon = 'icons/effects/blood.dmi'
icon_state = "floor1"
random_icon_states = list("floor1", "floor2", "floor3", "floor4", "floor5", "floor6", "floor7")
+ blood_DNA = list()
blood_state = BLOOD_STATE_HUMAN
bloodiness = MAX_SHOE_BLOODINESS
- var/list/viruses = list()
/obj/effect/decal/cleanable/blood/replace_decal(obj/effect/decal/cleanable/blood/C)
- if (C.forensics && C.forensics.blood)
- forensics.blood |= C.forensics.blood.Copy()
+ if (C.blood_DNA)
+ blood_DNA |= C.blood_DNA.Copy()
..()
/obj/effect/decal/cleanable/blood/old
@@ -21,7 +21,7 @@
/obj/effect/decal/cleanable/blood/old/Initialize()
..()
icon_state += "-old" //This IS necessary because the parent /blood type uses icon randomization.
- forensics.blood["Non-human DNA"] = "A+"
+ blood_DNA["Non-human DNA"] = "A+"
/obj/effect/decal/cleanable/blood/splatter
random_icon_states = list("gibbl1", "gibbl2", "gibbl3", "gibbl4", "gibbl5")
@@ -37,6 +37,8 @@
desc = "Your instincts say you shouldn't be following these."
random_icon_states = null
var/list/existing_dirs = list()
+ blood_DNA = list()
+
/obj/effect/decal/cleanable/trail_holder/can_bloodcrawl_in()
return 1
@@ -95,7 +97,7 @@
..()
setDir(pick(1,2,4,8))
icon_state += "-old"
- forensics.blood["Non-human DNA"] = "A+"
+ blood_DNA["Non-human DNA"] = "A+"
/obj/effect/decal/cleanable/blood/drip
diff --git a/code/game/objects/effects/spawners/gibspawner.dm b/code/game/objects/effects/spawners/gibspawner.dm
index 9822565ad04..4750e2c5278 100644
--- a/code/game/objects/effects/spawners/gibspawner.dm
+++ b/code/game/objects/effects/spawners/gibspawner.dm
@@ -30,9 +30,9 @@
digester.stomach_contents += gib
if(MobDNA)
- gib.forensics.blood[MobDNA.unique_enzymes] = MobDNA.blood_type
+ gib.blood_DNA[MobDNA.unique_enzymes] = MobDNA.blood_type
else if(istype(src, /obj/effect/gibspawner/generic)) // Probably a monkey
- gib.forensics.blood["Non-human DNA"] = "A+"
+ gib.blood_DNA["Non-human DNA"] = "A+"
var/list/directions = gibdirections[i]
if(isturf(loc))
if(directions.len)
diff --git a/code/game/objects/items/clown_items.dm b/code/game/objects/items/clown_items.dm
index 8378b0fca57..da8edb2e5ae 100644
--- a/code/game/objects/items/clown_items.dm
+++ b/code/game/objects/items/clown_items.dm
@@ -83,7 +83,7 @@
var/obj/effect/decal/cleanable/C = locate() in target
qdel(C)
target.remove_atom_colour(WASHABLE_COLOUR_PRIORITY)
- target.forensics.clean_blood()
+ target.clean_blood()
target.wash_cream()
return
diff --git a/code/game/objects/items/mop.dm b/code/game/objects/items/mop.dm
index 41b5615a044..cac64e8f3ab 100644
--- a/code/game/objects/items/mop.dm
+++ b/code/game/objects/items/mop.dm
@@ -25,7 +25,7 @@
/obj/item/mop/proc/clean(turf/A)
if(reagents.has_reagent("water", 1) || reagents.has_reagent("holywater", 1) || reagents.has_reagent("vodka", 1) || reagents.has_reagent("cleaner", 1))
- A.forensics.clean_blood()
+ A.clean_blood()
for(var/obj/effect/O in A)
if(is_cleanable(O))
qdel(O)
diff --git a/code/game/objects/items/stacks/stack.dm b/code/game/objects/items/stacks/stack.dm
index 53cd462aa81..2a5561a5979 100644
--- a/code/game/objects/items/stacks/stack.dm
+++ b/code/game/objects/items/stacks/stack.dm
@@ -304,10 +304,10 @@
. = ..()
/obj/item/stack/proc/copy_evidences(obj/item/stack/from as obj)
- forensics.blood = from.forensics.blood
- forensics.prints = from.forensics.prints
- forensics.hiddenprints = from.forensics.hiddenprints
- fingerprintslast = from.fingerprintslast
+ src.blood_DNA = from.blood_DNA
+ src.fingerprints = from.fingerprints
+ src.fingerprintshidden = from.fingerprintshidden
+ src.fingerprintslast = from.fingerprintslast
//TODO bloody overlay
/obj/item/stack/microwave_act(obj/machinery/microwave/M)
diff --git a/code/game/objects/items/twohanded.dm b/code/game/objects/items/twohanded.dm
index 507454abded..323527fc887 100644
--- a/code/game/objects/items/twohanded.dm
+++ b/code/game/objects/items/twohanded.dm
@@ -291,7 +291,7 @@
icon_state = "dualsaber[item_color][wielded]"
else
icon_state = "dualsaber0"
- forensics.clean_blood()//blood overlays get weird otherwise, because the sprite changes.
+ clean_blood()//blood overlays get weird otherwise, because the sprite changes.
/obj/item/twohanded/dualsaber/attack(mob/target, mob/living/carbon/human/user)
if(user.has_dna())
diff --git a/code/game/objects/structures/watercloset.dm b/code/game/objects/structures/watercloset.dm
index e2958988767..ea1f1f5214a 100644
--- a/code/game/objects/structures/watercloset.dm
+++ b/code/game/objects/structures/watercloset.dm
@@ -286,8 +286,8 @@
wash_obj(O)
-/obj/machinery/shower/proc/wash_obj(atom/movable/O)
- . = O.forensics.clean_blood()
+/obj/machinery/shower/proc/wash_obj(obj/O)
+ . = O.clean_blood()
O.remove_atom_colour(WASHABLE_COLOUR_PRIORITY)
if(isitem(O))
var/obj/item/I = O
@@ -299,7 +299,7 @@
if(isturf(loc))
var/turf/tile = loc
tile.remove_atom_colour(WASHABLE_COLOUR_PRIORITY)
- tile.forensics.clean_blood()
+ tile.clean_blood()
for(var/obj/effect/E in tile)
if(is_cleanable(E))
qdel(E)
@@ -349,7 +349,7 @@
else if(H.w_uniform && wash_obj(H.w_uniform))
H.update_inv_w_uniform()
if(washgloves)
- H.forensics.clean_blood()
+ H.clean_blood()
if(H.shoes && washshoes && wash_obj(H.shoes))
H.update_inv_shoes()
if(H.wear_mask && washmask && wash_obj(H.wear_mask))
@@ -366,9 +366,9 @@
else
if(M.wear_mask && wash_obj(M.wear_mask))
M.update_inv_wear_mask(0)
- M.forensics.clean_blood()
+ M.clean_blood()
else
- L.forensics.clean_blood()
+ L.clean_blood()
/obj/machinery/shower/process()
@@ -452,7 +452,7 @@
H.regenerate_icons()
user.drowsyness = max(user.drowsyness - rand(2,3), 0) //Washing your face wakes you up if you're falling asleep
else
- user.forensics.clean_blood()
+ user.clean_blood()
/obj/structure/sink/attackby(obj/item/O, mob/living/user, params)
@@ -509,7 +509,7 @@
busy = FALSE
return 1
busy = FALSE
- O.forensics.clean_blood()
+ O.clean_blood()
O.acid_level = 0
create_reagents(5)
reagents.add_reagent("[dispensedreagent]", 5)
diff --git a/code/game/turfs/open.dm b/code/game/turfs/open.dm
index 4dcc313aa51..bc0af068c56 100644
--- a/code/game/turfs/open.dm
+++ b/code/game/turfs/open.dm
@@ -139,7 +139,7 @@
for(var/mob/living/simple_animal/slime/M in src)
M.apply_water()
- forensics.clean_blood()
+ clean_blood()
for(var/obj/effect/O in src)
if(is_cleanable(O))
qdel(O)
diff --git a/code/modules/clothing/clothing.dm b/code/modules/clothing/clothing.dm
index 84af3299fe2..1447d03ef7e 100644
--- a/code/modules/clothing/clothing.dm
+++ b/code/modules/clothing/clothing.dm
@@ -223,12 +223,13 @@ BLIND // can't see anything
strip_delay = 20
equip_delay_other = 40
+
/obj/item/clothing/gloves/worn_overlays(isinhands = FALSE)
. = list()
if(!isinhands)
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damagedgloves")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "bloodyhands")
/obj/item/clothing/gloves/update_clothes_damaged_state(damaging = TRUE)
@@ -264,7 +265,7 @@ BLIND // can't see anything
if(!isinhands)
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damagedhelmet")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "helmetblood")
/obj/item/clothing/head/update_clothes_damaged_state(damaging = TRUE)
@@ -299,7 +300,7 @@ BLIND // can't see anything
if(body_parts_covered & HEAD)
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damagedmask")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "maskblood")
@@ -321,7 +322,7 @@ BLIND // can't see anything
if(body_parts_covered & HEAD)
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damagedmask")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "maskblood")
/obj/item/clothing/mask/update_clothes_damaged_state(damaging = TRUE)
@@ -383,7 +384,7 @@ BLIND // can't see anything
. = list()
if(!isinhands)
var/bloody = 0
- if(forensics.blood)
+ if(blood_DNA)
bloody = 1
else
bloody = bloody_shoes[BLOOD_STATE_HUMAN]
@@ -445,7 +446,7 @@ BLIND // can't see anything
if(!isinhands)
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damaged[blood_overlay_type]")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "[blood_overlay_type]blood")
var/mob/living/carbon/human/M = loc
if(ishuman(M) && M.w_uniform)
@@ -534,7 +535,7 @@ BLIND // can't see anything
if(damaged_clothes)
. += mutable_appearance('icons/effects/item_damage.dmi', "damageduniform")
- if(forensics.blood)
+ if(blood_DNA)
. += mutable_appearance('icons/effects/blood.dmi', "uniformblood")
if(accessory_overlay)
. += accessory_overlay
diff --git a/code/modules/detectivework/detective_work.dm b/code/modules/detectivework/detective_work.dm
index e69de29bb2d..5b92b1e88f8 100644
--- a/code/modules/detectivework/detective_work.dm
+++ b/code/modules/detectivework/detective_work.dm
@@ -0,0 +1,118 @@
+//CONTAINS: Suit fibers and Detective's Scanning Computer
+
+/atom/var/list/suit_fibers
+
+/atom/proc/add_fibers(mob/living/carbon/human/M)
+ if(M.gloves && istype(M.gloves, /obj/item/clothing/))
+ var/obj/item/clothing/gloves/G = M.gloves
+ if(G.transfer_blood > 1) //bloodied gloves transfer blood to touched objects
+ if(add_blood(G.blood_DNA)) //only reduces the bloodiness of our gloves if the item wasn't already bloody
+ G.transfer_blood--
+ else if(M.bloody_hands > 1)
+ if(add_blood(M.blood_DNA))
+ M.bloody_hands--
+ if(!suit_fibers) suit_fibers = list()
+ var/fibertext
+ var/item_multiplier = isitem(src)?1.2:1
+ if(M.wear_suit)
+ fibertext = "Material from \a [M.wear_suit]."
+ if(prob(10*item_multiplier) && !(fibertext in suit_fibers))
+ suit_fibers += fibertext
+ if(!(M.wear_suit.body_parts_covered & CHEST))
+ if(M.w_uniform)
+ fibertext = "Fibers from \a [M.w_uniform]."
+ if(prob(12*item_multiplier) && !(fibertext in suit_fibers)) //Wearing a suit means less of the uniform exposed.
+ suit_fibers += fibertext
+ if(!(M.wear_suit.body_parts_covered & HANDS))
+ if(M.gloves)
+ fibertext = "Material from a pair of [M.gloves.name]."
+ if(prob(20*item_multiplier) && !(fibertext in suit_fibers))
+ suit_fibers += fibertext
+ else if(M.w_uniform)
+ fibertext = "Fibers from \a [M.w_uniform]."
+ if(prob(15*item_multiplier) && !(fibertext in suit_fibers))
+ // "Added fibertext: [fibertext]"
+ suit_fibers += fibertext
+ if(M.gloves)
+ fibertext = "Material from a pair of [M.gloves.name]."
+ if(prob(20*item_multiplier) && !(fibertext in suit_fibers))
+ suit_fibers += "Material from a pair of [M.gloves.name]."
+ else if(M.gloves)
+ fibertext = "Material from a pair of [M.gloves.name]."
+ if(prob(20*item_multiplier) && !(fibertext in suit_fibers))
+ suit_fibers += "Material from a pair of [M.gloves.name]."
+
+
+/atom/proc/add_hiddenprint(mob/living/M)
+ if(!M || !M.key)
+ return
+
+ if(!fingerprintshidden) //Add the list if it does not exist
+ fingerprintshidden = list()
+
+ var/hasgloves = ""
+ if(ishuman(M))
+ var/mob/living/carbon/human/H = M
+ if(H.gloves)
+ hasgloves = "(gloves)"
+
+ var/current_time = time_stamp()
+ if(!fingerprintshidden[M.key])
+ fingerprintshidden[M.key] = "First: [M.real_name]\[[current_time]\][hasgloves]. Ckey: [M.ckey]"
+ else
+ var/laststamppos = findtext(fingerprintshidden[M.key], " Last: ")
+ if(laststamppos)
+ fingerprintshidden[M.key] = copytext(fingerprintshidden[M.key], 1, laststamppos)
+ fingerprintshidden[M.key] += " Last: [M.real_name]\[[current_time]\][hasgloves]. Ckey: [M.ckey]"
+
+ fingerprintslast = M.ckey
+
+
+//Set ignoregloves to add prints irrespective of the mob having gloves on.
+/atom/proc/add_fingerprint(mob/living/M, ignoregloves = 0)
+ if(!M || !M.key)
+ return
+
+ add_hiddenprint(M)
+
+ if(ishuman(M))
+ var/mob/living/carbon/human/H = M
+
+ add_fibers(H)
+
+ if(H.gloves) //Check if the gloves (if any) hide fingerprints
+ var/obj/item/clothing/gloves/G = H.gloves
+ if(G.transfer_prints)
+ ignoregloves = 1
+
+ if(!ignoregloves)
+ H.gloves.add_fingerprint(H, 1) //ignoregloves = 1 to avoid infinite loop.
+ return
+
+ if(!fingerprints) //Add the list if it does not exist
+ fingerprints = list()
+ var/full_print = md5(H.dna.uni_identity)
+ fingerprints[full_print] = full_print
+
+
+
+
+/atom/proc/transfer_fingerprints_to(atom/A)
+
+ // Make sure everything are lists.
+ if(!islist(A.fingerprints))
+ A.fingerprints = list()
+ if(!islist(A.fingerprintshidden))
+ A.fingerprintshidden = list()
+
+ if(!islist(fingerprints))
+ fingerprints = list()
+ if(!islist(fingerprintshidden))
+ fingerprintshidden = list()
+
+ // Transfer
+ if(fingerprints)
+ A.fingerprints |= fingerprints.Copy() //detective
+ if(fingerprintshidden)
+ A.fingerprintshidden |= fingerprintshidden.Copy() //admin
+ A.fingerprintslast = fingerprintslast
diff --git a/code/modules/detectivework/footprints_and_rag.dm b/code/modules/detectivework/footprints_and_rag.dm
index b2ae1c9354d..b4dd10f275c 100644
--- a/code/modules/detectivework/footprints_and_rag.dm
+++ b/code/modules/detectivework/footprints_and_rag.dm
@@ -46,6 +46,6 @@
user.visible_message("[user] starts to wipe down [A] with [src]!", "You start to wipe down [A] with [src]...")
if(do_after(user,30, target = A))
user.visible_message("[user] finishes wiping off the [A]!", "You finish wiping off the [A].")
- A.forensics.clean_blood()
+ A.clean_blood()
A.wash_cream()
return
diff --git a/code/modules/detectivework/scanner.dm b/code/modules/detectivework/scanner.dm
index 5a890cb6e83..5a81686d16d 100644
--- a/code/modules/detectivework/scanner.dm
+++ b/code/modules/detectivework/scanner.dm
@@ -76,13 +76,11 @@
// Start gathering
+ if(A.blood_DNA && A.blood_DNA.len)
+ blood = A.blood_DNA.Copy()
-
- if(LAZYLEN(A.forensics.blood))
- blood = A.forensics.blood.Copy()
-
- if(LAZYLEN(A.forensics.fibers))
- fibers = A.forensics.fibers.Copy()
+ if(A.suit_fibers && A.suit_fibers.len)
+ fibers = A.suit_fibers.Copy()
if(ishuman(A))
@@ -92,11 +90,11 @@
else if(!ismob(A))
- if(LAZYLEN(A.forensics.prints))
- fingerprints = A.forensics.prints.Copy()
+ if(A.fingerprints && A.fingerprints.len)
+ fingerprints = A.fingerprints.Copy()
// Only get reagents from non-mobs.
- if(LAZYLEN(A.reagents.reagent_list))
+ if(A.reagents && A.reagents.reagent_list.len)
for(var/datum/reagent/R in A.reagents.reagent_list)
reagents[R.name] = R.volume
@@ -115,7 +113,7 @@
add_log("[worldtime2text()][get_timestamp()] - [target_name]", 0)
// Fingerprints
- if(LAZYLEN(forensics.prints))
+ if(fingerprints && fingerprints.len)
sleep(30)
add_log("Prints:")
for(var/finger in fingerprints)
@@ -123,7 +121,7 @@
found_something = 1
// Blood
- if (LAZYLEN(forensics.blood))
+ if (blood && blood.len)
sleep(30)
add_log("Blood:")
found_something = 1
@@ -131,7 +129,7 @@
add_log("Type: [blood[B]] DNA: [B]")
//Fibers
- if(LAZYLEN(forensics.fibers))
+ if(fibers && fibers.len)
sleep(30)
add_log("Fibers:")
for(var/fiber in fibers)
@@ -139,7 +137,7 @@
found_something = 1
//Reagents
- if(LAZYLEN(reagents)) //reagants aren't forensics, so they aren't in the datum
+ if(reagents && reagents.len)
sleep(30)
add_log("Reagents:")
for(var/R in reagents)
@@ -173,4 +171,4 @@
CRASH("[src] \ref[src] is adding a log when it was never put in scanning mode!")
/proc/get_timestamp()
- return time2text(world.time + 432000, ":ss")
\ No newline at end of file
+ return time2text(world.time + 432000, ":ss")
diff --git a/code/modules/mob/living/blood.dm b/code/modules/mob/living/blood.dm
index 09c148a612b..8e547eeb120 100644
--- a/code/modules/mob/living/blood.dm
+++ b/code/modules/mob/living/blood.dm
@@ -255,7 +255,7 @@
return
else
temp_blood_DNA = list()
- temp_blood_DNA |= drop.forensics.blood.Copy() //we transfer the dna from the drip to the splatter
+ temp_blood_DNA |= drop.blood_DNA.Copy() //we transfer the dna from the drip to the splatter
qdel(drop)//the drip is replaced by a bigger splatter
else
drop = new(T)
@@ -268,7 +268,7 @@
B = new /obj/effect/decal/cleanable/blood/splatter(T)
B.transfer_mob_blood_dna(src) //give blood info to the blood decal.
if(temp_blood_DNA)
- B.forensics.blood |= temp_blood_DNA
+ B.blood_DNA |= temp_blood_DNA
/mob/living/carbon/human/add_splatter_floor(turf/T, small_drip)
if(!(NOBLOOD in dna.species.species_traits))
@@ -280,7 +280,7 @@
var/obj/effect/decal/cleanable/xenoblood/B = locate() in T.contents
if(!B)
B = new(T)
- B.forensics.blood["UNKNOWN DNA"] = "X*"
+ B.blood_DNA["UNKNOWN DNA"] = "X*"
/mob/living/silicon/robot/add_splatter_floor(turf/T, small_drip)
if(!T)
diff --git a/code/modules/mob/living/carbon/carbon_defense.dm b/code/modules/mob/living/carbon/carbon_defense.dm
index b9ea89964c4..c7eb9bcc5c3 100644
--- a/code/modules/mob/living/carbon/carbon_defense.dm
+++ b/code/modules/mob/living/carbon/carbon_defense.dm
@@ -85,7 +85,7 @@
var/turf/location = get_turf(src)
add_splatter_floor(location)
if(get_dist(user, src) <= 1) //people with TK won't get smeared with blood
- user.forensics.add_mob_blood(src)
+ user.add_mob_blood(src)
if(affecting.body_zone == "head")
if(wear_mask)
diff --git a/code/modules/mob/living/carbon/examine.dm b/code/modules/mob/living/carbon/examine.dm
index e85b5784b70..600a50e5952 100644
--- a/code/modules/mob/living/carbon/examine.dm
+++ b/code/modules/mob/living/carbon/examine.dm
@@ -19,7 +19,7 @@
for(var/obj/item/I in held_items)
if(!(I.flags_1 & ABSTRACT_1))
- if(LAZYLEN(I.forensics.blood))
+ if(I.blood_DNA)
msg += "[t_He] [t_is] holding [icon2html(I, user)] [I.gender==PLURAL?"some":"a"] blood-stained [I.name] in [t_his] [get_held_index_name(get_held_index_of_item(I))]!\n"
else
msg += "[t_He] [t_is] holding [icon2html(I, user)] \a [I] in [t_his] [get_held_index_name(get_held_index_of_item(I))].\n"
diff --git a/code/modules/mob/living/carbon/human/examine.dm b/code/modules/mob/living/carbon/human/examine.dm
index a5d452b598c..df2e0f654e1 100644
--- a/code/modules/mob/living/carbon/human/examine.dm
+++ b/code/modules/mob/living/carbon/human/examine.dm
@@ -21,35 +21,35 @@
if(U.attached_accessory)
accessory_msg += " with [icon2html(U.attached_accessory, user)] \a [U.attached_accessory]"
- if(LAZYLEN(w_uniform.forensics.blood))
+ if(w_uniform.blood_DNA)
msg += "[t_He] [t_is] wearing [icon2html(w_uniform, user)] [w_uniform.gender==PLURAL?"some":"a"] blood-stained [w_uniform.name][accessory_msg]!\n"
else
msg += "[t_He] [t_is] wearing [icon2html(w_uniform, user)] \a [w_uniform][accessory_msg].\n"
//head
if(head)
- if(LAZYLEN(head.forensics.blood))
+ if(head.blood_DNA)
msg += "[t_He] [t_is] wearing [icon2html(head, user)] [head.gender==PLURAL?"some":"a"] blood-stained [head.name] on [t_his] head!\n"
else
msg += "[t_He] [t_is] wearing [icon2html(head, user)] \a [head] on [t_his] head.\n"
//suit/armor
if(wear_suit)
- if(LAZYLEN(wear_suit.forensics.blood))
+ if(wear_suit.blood_DNA)
msg += "[t_He] [t_is] wearing [icon2html(wear_suit, user)] [wear_suit.gender==PLURAL?"some":"a"] blood-stained [wear_suit.name]!\n"
else
msg += "[t_He] [t_is] wearing [icon2html(wear_suit, user)] \a [wear_suit].\n"
//suit/armor storage
if(s_store)
- if(LAZYLEN(s_store.forensics.blood))
+ if(s_store.blood_DNA)
msg += "[t_He] [t_is] carrying [icon2html(s_store, user)] [s_store.gender==PLURAL?"some":"a"] blood-stained [s_store.name] on [t_his] [wear_suit.name]!\n"
else
msg += "[t_He] [t_is] carrying [icon2html(s_store, user)] \a [s_store] on [t_his] [wear_suit.name].\n"
//back
if(back)
- if(LAZYLEN(back.forensics.blood))
+ if(back.blood_DNA)
msg += "[t_He] [t_has] [icon2html(back, user)] [back.gender==PLURAL?"some":"a"] blood-stained [back] on [t_his] back.\n"
else
msg += "[t_He] [t_has] [icon2html(back, user)] \a [back] on [t_his] back.\n"
@@ -57,18 +57,18 @@
//Hands
for(var/obj/item/I in held_items)
if(!(I.flags_1 & ABSTRACT_1))
- if(LAZYLEN(I.forensics.blood))
+ if(I.blood_DNA)
msg += "[t_He] [t_is] holding [icon2html(I, user)] [I.gender==PLURAL?"some":"a"] blood-stained [I.name] in [t_his] [get_held_index_name(get_held_index_of_item(I))]!\n"
else
msg += "[t_He] [t_is] holding [icon2html(I, user)] \a [I] in [t_his] [get_held_index_name(get_held_index_of_item(I))].\n"
//gloves
if(gloves && !(slot_gloves in obscured))
- if(LAZYLEN(gloves.forensics.blood))
+ if(gloves.blood_DNA)
msg += "[t_He] [t_has] [icon2html(gloves, user)] [gloves.gender==PLURAL?"some":"a"] blood-stained [gloves.name] on [t_his] hands!\n"
else
msg += "[t_He] [t_has] [icon2html(gloves, user)] \a [gloves] on [t_his] hands.\n"
- else if(forensics.blood)
+ else if(blood_DNA)
var/hand_number = get_num_arms()
if(hand_number)
msg += "[t_He] [t_has] [hand_number > 1 ? "" : "a"] blood-stained hand[hand_number > 1 ? "s" : ""]!\n"
@@ -84,21 +84,21 @@
//belt
if(belt)
- if(LAZYLEN(belt.forensics.blood))
+ if(belt.blood_DNA)
msg += "[t_He] [t_has] [icon2html(belt, user)] [belt.gender==PLURAL?"some":"a"] blood-stained [belt.name] about [t_his] waist!\n"
else
msg += "[t_He] [t_has] [icon2html(belt, user)] \a [belt] about [t_his] waist.\n"
//shoes
if(shoes && !(slot_shoes in obscured))
- if(LAZYLEN(shoes.forensics.blood))
+ if(shoes.blood_DNA)
msg += "[t_He] [t_is] wearing [icon2html(shoes, user)] [shoes.gender==PLURAL?"some":"a"] blood-stained [shoes.name] on [t_his] feet!\n"
else
msg += "[t_He] [t_is] wearing [icon2html(shoes, user)] \a [shoes] on [t_his] feet.\n"
//mask
if(wear_mask && !(slot_wear_mask in obscured))
- if(LAZYLEN(wear_mask.forensics.blood))
+ if(wear_mask.blood_DNA)
msg += "[t_He] [t_has] [icon2html(wear_mask, user)] [wear_mask.gender==PLURAL?"some":"a"] blood-stained [wear_mask.name] on [t_his] face!\n"
else
msg += "[t_He] [t_has] [icon2html(wear_mask, user)] \a [wear_mask] on [t_his] face.\n"
@@ -108,7 +108,7 @@
//eyes
if(glasses && !(slot_glasses in obscured))
- if(LAZYLEN(glasses.forensics.blood))
+ if(glasses.blood_DNA)
msg += "[t_He] [t_has] [icon2html(glasses, user)] [glasses.gender==PLURAL?"some":"a"] blood-stained [glasses] covering [t_his] eyes!\n"
else
msg += "[t_He] [t_has] [icon2html(glasses, user)] \a [glasses] covering [t_his] eyes.\n"
diff --git a/code/modules/mob/living/carbon/human/human.dm b/code/modules/mob/living/carbon/human/human.dm
index 624a045c493..79e2700e0fe 100644
--- a/code/modules/mob/living/carbon/human/human.dm
+++ b/code/modules/mob/living/carbon/human/human.dm
@@ -718,7 +718,7 @@ INITIALIZE_IMMEDIATE(/mob/living/carbon/human/dummy)
if(..())
dropItemToGround(I)
-/mob/living/carbon/human/proc/clean_blood()
+/mob/living/carbon/human/clean_blood()
var/mob/living/carbon/human/H = src
if(H.gloves)
if(H.gloves.clean_blood())
diff --git a/code/modules/mob/living/carbon/human/human_movement.dm b/code/modules/mob/living/carbon/human/human_movement.dm
index dcdb5372e3e..812d09a34fd 100644
--- a/code/modules/mob/living/carbon/human/human_movement.dm
+++ b/code/modules/mob/living/carbon/human/human_movement.dm
@@ -48,8 +48,8 @@
FP.blood_state = S.blood_state
FP.entered_dirs |= dir
FP.bloodiness = S.bloody_shoes[S.blood_state]
- if(LAZYLEN(S.forensics.blood))
- FP.transfer_blood_dna(S.forensics.blood)
+ if(S.blood_DNA && S.blood_DNA.len)
+ FP.transfer_blood_dna(S.blood_DNA)
FP.update_icon()
update_inv_shoes()
//End bloody footprints
diff --git a/code/modules/mob/living/carbon/human/species.dm b/code/modules/mob/living/carbon/human/species.dm
index b7b421339d4..39f4f995832 100644
--- a/code/modules/mob/living/carbon/human/species.dm
+++ b/code/modules/mob/living/carbon/human/species.dm
@@ -1252,7 +1252,7 @@
if(istype(location))
H.add_splatter_floor(location)
if(get_dist(user, H) <= 1) //people with TK won't get smeared with blood
- user.forensics.add_mob_blood(H)
+ user.add_mob_blood(H)
switch(hit_area)
if("head")
diff --git a/code/modules/mob/living/carbon/human/update_icons.dm b/code/modules/mob/living/carbon/human/update_icons.dm
index f687bb8e6cb..1aef45aff8e 100644
--- a/code/modules/mob/living/carbon/human/update_icons.dm
+++ b/code/modules/mob/living/carbon/human/update_icons.dm
@@ -166,7 +166,7 @@ There are several things that need to be remembered:
var/obj/screen/inventory/inv = hud_used.inv_slots[slot_gloves]
inv.update_icon()
- if(!gloves && forensics.blood)
+ if(!gloves && blood_DNA)
var/mutable_appearance/bloody_overlay = mutable_appearance('icons/effects/blood.dmi', "bloodyhands", -GLOVES_LAYER)
if(get_num_arms() < 2)
if(has_left_hand())
diff --git a/code/modules/mob/living/simple_animal/bot/mulebot.dm b/code/modules/mob/living/simple_animal/bot/mulebot.dm
index 1921ca6fe21..0d4edd53f59 100644
--- a/code/modules/mob/living/simple_animal/bot/mulebot.dm
+++ b/code/modules/mob/living/simple_animal/bot/mulebot.dm
@@ -478,8 +478,8 @@
if(bloodiness)
var/obj/effect/decal/cleanable/blood/tracks/B = new(loc)
- if(forensics.blood && forensics.blood.len)
- B.forensics.blood |= forensics.blood.Copy()
+ if(blood_DNA && blood_DNA.len)
+ B.blood_DNA |= blood_DNA.Copy()
var/newdir = get_dir(next, loc)
if(newdir == dir)
B.setDir(newdir)
@@ -662,8 +662,11 @@
H.apply_damage(0.5*damage, BRUTE, "r_arm", run_armor_check("r_arm", "melee"))
var/turf/T = get_turf(src)
- T.forensics.add_mob_blood(H)
+ T.add_mob_blood(H)
+ var/list/blood_dna = H.get_blood_dna_list()
+ if(blood_dna)
+ transfer_blood_dna(blood_dna)
bloodiness += 4
// player on mulebot attempted to move
diff --git a/code/modules/mob/living/simple_animal/friendly/drone/_drone.dm b/code/modules/mob/living/simple_animal/friendly/drone/_drone.dm
index 312d1484e98..a8eb8ad12be 100644
--- a/code/modules/mob/living/simple_animal/friendly/drone/_drone.dm
+++ b/code/modules/mob/living/simple_animal/friendly/drone/_drone.dm
@@ -176,22 +176,21 @@
//Hands
for(var/obj/item/I in held_items)
if(!(I.flags_1 & ABSTRACT_1))
- if(LAZYLEN(I.forensics.blood))
+ if(I.blood_DNA)
msg += "It has [icon2html(I, user)] [I.gender==PLURAL?"some":"a"] blood-stained [I.name] in its [get_held_index_name(get_held_index_of_item(I))]!\n"
else
msg += "It has [icon2html(I, user)] \a [I] in its [get_held_index_name(get_held_index_of_item(I))].\n"
//Internal storage
- var/flagcheck = internal_storage.flags_1&ABSTRACT_1
- if(internal_storage && !flagcheck)
- if(LAZYLEN(internal_storage.forensics.blood))
+ if(internal_storage && !(internal_storage.flags_1&ABSTRACT_1))
+ if(internal_storage.blood_DNA)
msg += "It is holding [icon2html(internal_storage, user)] [internal_storage.gender==PLURAL?"some":"a"] blood-stained [internal_storage.name] in its internal storage!\n"
else
msg += "It is holding [icon2html(internal_storage, user)] \a [internal_storage] in its internal storage.\n"
//Cosmetic hat - provides no function other than looks
if(head && !(head.flags_1&ABSTRACT_1))
- if(LAZYLEN(head.forensics.blood))
+ if(head.blood_DNA)
msg += "It is wearing [icon2html(head, user)] [head.gender==PLURAL?"some":"a"] blood-stained [head.name] on its head!\n"
else
msg += "It is wearing [icon2html(head, user)] \a [head] on its head.\n"
diff --git a/code/modules/mob/living/simple_animal/guardian/types/dextrous.dm b/code/modules/mob/living/simple_animal/guardian/types/dextrous.dm
index 19f926ca024..2f3ee4cefb3 100644
--- a/code/modules/mob/living/simple_animal/guardian/types/dextrous.dm
+++ b/code/modules/mob/living/simple_animal/guardian/types/dextrous.dm
@@ -31,13 +31,13 @@
for(var/obj/item/I in held_items)
if(!(I.flags_1 & ABSTRACT_1))
- if(I.forensics && I.forensics.blood)
+ if(I.blood_DNA)
msg += "It has [icon2html(I, user)] [I.gender==PLURAL?"some":"a"] blood-stained [I.name] in its [get_held_index_name(get_held_index_of_item(I))]!\n"
else
msg += "It has [icon2html(I, user)] \a [I] in its [get_held_index_name(get_held_index_of_item(I))].\n"
if(internal_storage && !(internal_storage.flags_1&ABSTRACT_1))
- if(internal_storage.forensics && internal_storage.forensics.blood)
+ if(internal_storage.blood_DNA)
msg += "It is holding [icon2html(internal_storage, user)] [internal_storage.gender==PLURAL?"some":"a"] blood-stained [internal_storage.name] in its internal storage!\n"
else
msg += "It is holding [icon2html(internal_storage, user)] \a [internal_storage] in its internal storage.\n"
diff --git a/code/modules/mob/living/simple_animal/hostile/alien.dm b/code/modules/mob/living/simple_animal/hostile/alien.dm
index 0140264a1a0..e06de7b762c 100644
--- a/code/modules/mob/living/simple_animal/hostile/alien.dm
+++ b/code/modules/mob/living/simple_animal/hostile/alien.dm
@@ -171,6 +171,6 @@
qdel(target)
return TRUE
var/atom/movable/M = target
- M.forensics.clean_blood()
+ M.clean_blood()
visible_message("[src] polishes \the [target].")
return TRUE
diff --git a/code/modules/reagents/chemistry/reagents/other_reagents.dm b/code/modules/reagents/chemistry/reagents/other_reagents.dm
index 7f78c9c4761..d6d7c11aa78 100644
--- a/code/modules/reagents/chemistry/reagents/other_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/other_reagents.dm
@@ -79,7 +79,7 @@
if(!B)
B = new(T)
if(data["blood_DNA"])
- B.forensics.blood[data["blood_DNA"]] = data["blood_type"]
+ B.blood_DNA[data["blood_DNA"]] = data["blood_type"]
/datum/reagent/liquidgibs
@@ -941,12 +941,12 @@
else
if(O)
O.remove_atom_colour(WASHABLE_COLOUR_PRIORITY)
- O.forensics.clean_blood()
+ O.clean_blood()
/datum/reagent/space_cleaner/reaction_turf(turf/T, reac_volume)
if(reac_volume >= 1)
T.remove_atom_colour(WASHABLE_COLOUR_PRIORITY)
- T.forensics.clean_blood()
+ T.clean_blood()
for(var/obj/effect/decal/cleanable/C in T)
qdel(C)
@@ -964,7 +964,7 @@
H.lip_style = null
H.update_body()
for(var/obj/item/I in C.held_items)
- I.forensics.clean_blood()
+ I.clean_blood()
if(C.wear_mask)
if(C.wear_mask.clean_blood())
C.update_inv_wear_mask()
@@ -983,7 +983,7 @@
if(H.shoes.clean_blood())
H.update_inv_shoes()
H.wash_cream()
- M.forensics.clean_blood()
+ M.clean_blood()
/datum/reagent/space_cleaner/ez_clean
name = "EZ Clean"
diff --git a/tgstation.dme b/tgstation.dme
index a22878ab84e..0f4b25199b0 100755
--- a/tgstation.dme
+++ b/tgstation.dme
@@ -225,7 +225,6 @@
#include "code\datums\emotes.dm"
#include "code\datums\explosion.dm"
#include "code\datums\forced_movement.dm"
-#include "code\datums\forensics.dm"
#include "code\datums\holocall.dm"
#include "code\datums\hud.dm"
#include "code\datums\map_config.dm"
@@ -1224,6 +1223,7 @@
#include "code\modules\crafting\craft.dm"
#include "code\modules\crafting\guncrafting.dm"
#include "code\modules\crafting\recipes.dm"
+#include "code\modules\detectivework\detective_work.dm"
#include "code\modules\detectivework\evidence.dm"
#include "code\modules\detectivework\footprints_and_rag.dm"
#include "code\modules\detectivework\scanner.dm"