diff --git a/_maps/map_files/MiniStation/MiniStation.dmm b/_maps/map_files/MiniStation/MiniStation.dmm
index 3d04818ef2a9d3d..d63590ecb3c9612 100644
--- a/_maps/map_files/MiniStation/MiniStation.dmm
+++ b/_maps/map_files/MiniStation/MiniStation.dmm
@@ -1194,7 +1194,7 @@
"wX" = (/obj/structure/cable{d1 = 1; d2 = 4; icon_state = "1-4"},/turf/simulated/floor/plating{icon_state = "warnplatecorner"; dir = 2},/area/hallway/primary/central)
"wY" = (/obj/machinery/atmospherics/binary/pump/on,/obj/structure/cable{d1 = 2; d2 = 8; icon_state = "2-8"},/turf/simulated/floor/plating{dir = 2; icon_state = "warnplate"},/area/hallway/primary/central)
"wZ" = (/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden{dir = 5},/obj/machinery/meter{use_power = 0},/turf/simulated/floor/plating{icon_state = "warnplatecorner"; dir = 1},/area/hallway/primary/central)
-"xa" = (/obj/structure/closet/crate{desc = "It's a storage unit for kitchen clothes and equipment."; name = "Kitchen Crate"},/obj/item/clothing/head/chefhat,/obj/item/clothing/under/rank/chef,/obj/item/weapon/storage/box/mousetraps{pixel_x = 5; pixel_y = 5},/obj/item/weapon/storage/box/mousetraps,/obj/item/clothing/under/waiter,/obj/item/clothing/under/waiter,/obj/item/weapon/reagent_containers/food/drinks/flour,/obj/item/weapon/reagent_containers/food/drinks/flour,/obj/item/weapon/reagent_containers/food/drinks/flour,/obj/item/weapon/reagent_containers/food/drinks/flour,/turf/simulated/floor/plasteel{icon_state = "showroomfloor"},/area/crew_quarters/bar)
+"xa" = (/obj/structure/closet/crate{desc = "It's a storage unit for kitchen clothes and equipment."; name = "Kitchen Crate"},/obj/item/clothing/head/chefhat,/obj/item/clothing/under/rank/chef,/obj/item/weapon/storage/box/mousetraps{pixel_x = 5; pixel_y = 5},/obj/item/weapon/storage/box/mousetraps,/obj/item/clothing/under/waiter,/obj/item/clothing/under/waiter,/obj/item/weapon/reagent_containers/food/condiment/flour,/obj/item/weapon/reagent_containers/food/condiment/flour,/obj/item/weapon/reagent_containers/food/condiment/flour,/obj/item/weapon/reagent_containers/food/condiment/flour,/turf/simulated/floor/plasteel{icon_state = "showroomfloor"},/area/crew_quarters/bar)
"xb" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden,/obj/machinery/firealarm{dir = 2; pixel_y = 24},/obj/machinery/camera/autoname,/mob/living/simple_animal/mouse/brown/Tom,/turf/simulated/floor/plasteel{icon_state = "freezerfloor"},/area/crew_quarters/bar)
"xc" = (/obj/machinery/door/firedoor/border_only{dir = 4; name = "Firelock East"},/obj/item/device/radio/intercom{broadcasting = 0; freerange = 0; listening = 1; name = "Common Channel"; pixel_y = 25},/turf/simulated/floor/plasteel{icon_state = "freezerfloor"},/area/crew_quarters/bar)
"xd" = (/obj/machinery/door/airlock{name = "Frozen Storage"; req_access_txt = "25"},/turf/simulated/floor/plasteel{icon_state = "freezerfloor"},/area/crew_quarters/bar)
@@ -1703,7 +1703,7 @@
"GM" = (/obj/structure/grille,/obj/structure/window/reinforced{dir = 8},/obj/structure/window/reinforced{dir = 1},/obj/structure/window/reinforced,/obj/structure/window/reinforced{dir = 4},/turf/simulated/floor/plating,/area/tcommsat/computer)
"GN" = (/obj/structure/closet/radiation,/turf/simulated/floor/plating{icon_state = "warnplate"; dir = 1},/area/tcommsat/computer)
"GO" = (/obj/docking_port/stationary{dir = 8; dwidth = 2; height = 12; id = "ferry_home"; name = "station"; turf_type = /turf/space; width = 5},/turf/simulated/floor/plating,/area/space)
-
+
(1,1,1) = {"
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
diff --git a/_maps/map_files/MiniStation/z2.dmm b/_maps/map_files/MiniStation/z2.dmm
index d21ff7b45902058..7660fecb54ebd3b 100644
--- a/_maps/map_files/MiniStation/z2.dmm
+++ b/_maps/map_files/MiniStation/z2.dmm
@@ -294,7 +294,7 @@
"jc" = (/obj/structure/table,/obj/item/weapon/storage/box/handcuffs,/turf/unsimulated/floor{icon_state = "dark"},/area/centcom/evac)
"jd" = (/turf/unsimulated/wall/fakeglass{icon_state = "fakewindows"; dir = 9},/area/syndicate_mothership)
"je" = (/turf/unsimulated/wall/fakeglass{icon_state = "fakewindows2"; dir = 8},/area/syndicate_mothership)
-"jf" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/snacks/mushroompizzaslice,/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
+"jf" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/snacks/pizzaslice/mushroompizza,/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
"jg" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/drinks/beer{pixel_x = 5; pixel_y = -2; step_x = 0},/obj/item/toy/cards/deck/syndicate{icon_state = "deck_syndicate_full"; pixel_x = -6; pixel_y = 6},/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
"jh" = (/obj/machinery/computer/telecrystals/uplinker,/turf/unsimulated/floor{tag = "icon-podhatch (WEST)"; icon_state = "podhatch"; dir = 8},/area/syndicate_mothership)
"ji" = (/turf/unsimulated/floor{icon_state = "red"; dir = 10},/area/tdome/tdomeobserve)
@@ -453,7 +453,7 @@
"mV" = (/turf/unsimulated/floor{icon_state = "delivery"},/area/centcom/holding)
"mW" = (/obj/structure/grille,/obj/structure/window/reinforced,/obj/structure/window/reinforced{dir = 4},/obj/structure/window/reinforced{dir = 1},/obj/structure/window/reinforced{dir = 8},/turf/unsimulated/floor{name = "plating"},/area/centcom/holding)
"mX" = (/obj/effect/landmark{name = "Holding Facility"},/turf/unsimulated/floor{icon_state = "engine"},/area/centcom/holding)
-
+
(1,1,1) = {"
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaMacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaM
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaMacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaMaM
diff --git a/_maps/map_files/generic/z2.dmm b/_maps/map_files/generic/z2.dmm
index d831d1ba2ae5caf..1721c241e6dc36d 100644
--- a/_maps/map_files/generic/z2.dmm
+++ b/_maps/map_files/generic/z2.dmm
@@ -537,7 +537,7 @@
"kv" = (/obj/structure/stool/bed/chair{dir = 8},/turf/simulated/shuttle/floor{icon_state = "floor4"},/area/space)
"kw" = (/turf/unsimulated/wall/fakeglass{icon_state = "fakewindows"; dir = 9},/area/syndicate_mothership)
"kx" = (/turf/unsimulated/wall/fakeglass{icon_state = "fakewindows2"; dir = 8},/area/syndicate_mothership)
-"ky" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/snacks/mushroompizzaslice,/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
+"ky" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/snacks/pizzaslice/mushroompizza,/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
"kz" = (/obj/structure/table/wood,/obj/item/weapon/reagent_containers/food/drinks/beer{pixel_x = 5; pixel_y = -2; step_x = 0},/obj/item/toy/cards/deck/syndicate{icon_state = "deck_syndicate_full"; pixel_x = -6; pixel_y = 6},/turf/unsimulated/floor{icon_state = "bar"; dir = 2},/area/syndicate_mothership)
"kA" = (/obj/machinery/computer/telecrystals/uplinker,/turf/unsimulated/floor{tag = "icon-podhatch (WEST)"; icon_state = "podhatch"; dir = 8},/area/syndicate_mothership)
"kI" = (/turf/unsimulated/wall/fakeglass{color = "#008000"; dir = 6; icon_state = "fakewindows2"},/area/wizard_station)
@@ -810,7 +810,7 @@
"qb" = (/obj/structure/grille,/obj/structure/window/reinforced,/obj/structure/window/reinforced{dir = 4},/obj/structure/window/reinforced{dir = 1},/obj/structure/window/reinforced{dir = 8},/turf/unsimulated/floor{name = "plating"},/area/centcom/holding)
"qc" = (/obj/effect/landmark{name = "Holding Facility"},/turf/unsimulated/floor{icon_state = "engine"},/area/centcom/holding)
"qd" = (/obj/docking_port/stationary/transit{dheight = 0; dir = 2; dwidth = 11; height = 22; id = "whiteship_transit"; width = 35},/turf/space/transit/horizontal,/area/space)
-
+
(1,1,1) = {"
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababadaeaeaeaeaeafaeaeaeaeaeafaeaeaeaeaeafaeaeaeaeaeag
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaabacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacacabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababahaiaiaiaiaiajakakakakakajalalalalalajamanananaoap
diff --git a/code/__HELPERS/text.dm b/code/__HELPERS/text.dm
index 71a290ec08fdea8..9945a13fcadf24b 100644
--- a/code/__HELPERS/text.dm
+++ b/code/__HELPERS/text.dm
@@ -37,12 +37,12 @@
return t
//Removes a few problematic characters
-/proc/sanitize_simple(var/t,var/list/repl_chars = list("\n"="#","\t"="#","�"="�"))
+/proc/sanitize_simple(var/t,var/list/repl_chars = list("\n"="#","\t"="#"))
for(var/char in repl_chars)
var/index = findtext(t, char)
while(index)
t = copytext(t, 1, index) + repl_chars[char] + copytext(t, index+1)
- index = findtext(t, char)
+ index = findtext(t, char, index+1)
return t
//Runs byond's sanitization proc along-side sanitize_simple
@@ -147,32 +147,63 @@
return t_out
-//this proc strips html properly, but it's not lazy like the other procs.
-//this means that it doesn't just remove < and > and call it a day. seriously, who the fuck thought that would be useful.
+//this proc strips html properly, this means that it removes everything between < and >, and between "http" and "://"
//also limit the size of the input, if specified to
/proc/strip_html_properly(var/input,var/max_length=MAX_MESSAGE_LEN)
if(!input)
return
- var/opentag = 1 //These store the position of < and > respectively.
- var/closetag = 1
- while(1)
- opentag = findtext(input, "<")
- closetag = findtext(input, ">")
- if(closetag && opentag)
- if(closetag < opentag)
- input = copytext(input, (closetag + 1))
- else
- input = copytext(input, 1, opentag) + copytext(input, (closetag + 1))
- else if(closetag || opentag)
- if(opentag)
- input = copytext(input, 1, opentag)
- else
- input = copytext(input, (closetag + 1))
- else
- break
+
if(max_length)
input = copytext(input,1,max_length)
- return input
+
+ var/sanitized_output
+ var/next_html_tag = findtext(input, "<")
+ var/next_http = findtext(input, "http", 1, next_html_tag)
+
+ //the opening and closing of the expression to skip, e.g '<' and '>'
+ var/opening = non_zero_min(next_html_tag, next_http)
+ var/closing
+
+ sanitized_output = copytext(input, 1, opening)
+
+ while(next_html_tag || next_http)
+
+ //we treat < ... >
+ if(opening == next_html_tag)
+ closing = findtext(input, ">", opening + 1)
+ if(closing)
+ next_html_tag = findtext(input, "<", closing)
+ next_http = findtext(input, "http", closing, next_html_tag)
+ else //no matching ">"
+ next_html_tag = 0
+
+ //we treat "http(s)://"
+ else
+ closing = findtext(input, "://", opening + 1)
+ if(closing)
+ closing += 2 //skip these extra //
+ next_http = findtext(input, "http", closing)
+ next_html_tag = findtext(input, "<", closing, next_http)
+ else //no matching "://"
+ next_http = 0
+
+ //check if we've something to skip
+ if(closing)
+ opening = non_zero_min(next_html_tag, next_http)
+ sanitized_output += copytext(input, closing + 1, opening)
+
+ sanitized_output += copytext(input, opening) //don't forget the remaining text
+
+ return sanitized_output
+
+//strip_html_properly helper proc that returns the smallest non null of two numbers
+//or 0 if they're both null (needed because of findtext returning 0 when a value is not present)
+/proc/non_zero_min(var/a, var/b)
+ if(!a)
+ return b
+ if(!b)
+ return a
+ return (a < b ? a : b)
/*
* Text searches
diff --git a/code/__HELPERS/unsorted.dm b/code/__HELPERS/unsorted.dm
index d7a9b4c3afb538e..426acbdcaaaa66b 100644
--- a/code/__HELPERS/unsorted.dm
+++ b/code/__HELPERS/unsorted.dm
@@ -1343,27 +1343,43 @@ var/global/list/common_tools = list(
//Is this even used for anything besides balloons? Yes I took out the W:lit stuff because : really shouldnt be used.
/proc/is_sharp(obj/item/W as obj) // For the record, WHAT THE HELL IS THIS METHOD OF DOING IT?
- return ( \
- istype(W, /obj/item/weapon/screwdriver) || \
- istype(W, /obj/item/weapon/pen) || \
- istype(W, /obj/item/weapon/weldingtool) || \
- istype(W, /obj/item/weapon/lighter/zippo) || \
- istype(W, /obj/item/weapon/match) || \
- istype(W, /obj/item/clothing/mask/cigarette) || \
- istype(W, /obj/item/weapon/wirecutters) || \
- istype(W, /obj/item/weapon/circular_saw) || \
- istype(W, /obj/item/weapon/melee/energy/sword) || \
- istype(W, /obj/item/weapon/melee/energy/blade) || \
- istype(W, /obj/item/weapon/shovel) || \
- istype(W, /obj/item/weapon/kitchenknife) || \
- istype(W, /obj/item/weapon/scalpel) || \
- istype(W, /obj/item/weapon/kitchen/utensil/knife) || \
- istype(W, /obj/item/weapon/shard) || \
- istype(W, /obj/item/weapon/broken_bottle) || \
- istype(W, /obj/item/weapon/reagent_containers/syringe) || \
- istype(W, /obj/item/weapon/kitchen/utensil/fork) && W.icon_state != "forkloaded" || \
- istype(W, /obj/item/weapon/twohanded/fireaxe) \
- )
+ if(istype(W, /obj/item/weapon/circular_saw))
+ return 1
+ if(istype(W, /obj/item/weapon/melee/energy))
+ var/obj/item/weapon/melee/energy/E = W
+ if(E.active)
+ return 1
+ else
+ return 0
+ if(istype(W, /obj/item/weapon/shovel))
+ return 1
+ if(istype(W, /obj/item/weapon/kitchenknife))
+ return 2
+ if(istype(W, /obj/item/weapon/scalpel))
+ return 2
+ if(istype(W, /obj/item/weapon/kitchen/utensil/knife))
+ return 2
+ if(istype(W, /obj/item/weapon/shard))
+ return 1
+ if(istype(W, /obj/item/weapon/broken_bottle))
+ return 1
+ if(istype(W, /obj/item/weapon/twohanded/fireaxe))
+ return 1
+ if(istype(W, /obj/item/weapon/hatchet))
+ return 1
+
+/proc/is_pointed(obj/item/W as obj)
+ if(istype(W, /obj/item/weapon/pen))
+ return 1
+ if(istype(W, /obj/item/weapon/screwdriver))
+ return 1
+ if(istype(W, /obj/item/weapon/reagent_containers/syringe))
+ return 1
+ if(istype(W, /obj/item/weapon/kitchen/utensil/fork))
+ return 1
+ else
+ return 0
+
/*
Checks if that loc and dir has a item on the wall
diff --git a/code/_globalvars/station.dm b/code/_globalvars/station.dm
index fe6552163549021..e8512549c1c55a4 100644
--- a/code/_globalvars/station.dm
+++ b/code/_globalvars/station.dm
@@ -1,4 +1,4 @@
-var/global/obj/effect/datacore/data_core = null
+var/global/datum/datacore/data_core = null
//var/global/defer_powernet_rebuild = 0 // true if net rebuild will be called manually after an event
//Noble idea, but doing this made GC fail. The gains from waiting on deffering are lost by using del()
diff --git a/code/datums/datacore.dm b/code/datums/datacore.dm
index e04adb83d04b6bc..4014d4eb0ebdb90 100644
--- a/code/datums/datacore.dm
+++ b/code/datums/datacore.dm
@@ -1,6 +1,5 @@
-/obj/effect/datacore
- name = "datacore"
+/datum/datacore
var/medical[] = list()
var/medicalPrintCount = 0
var/general[] = list()
@@ -25,7 +24,7 @@
var/time = ""
var/dataId = 0
-/obj/effect/datacore/proc/createCrimeEntry(cname = "", cdetails = "", author = "", time = "")
+/datum/datacore/proc/createCrimeEntry(cname = "", cdetails = "", author = "", time = "")
var/datum/data/crime/c = new /datum/data/crime
c.crimeName = cname
c.crimeDetails = cdetails
@@ -34,14 +33,14 @@
c.dataId = ++securityCrimeCounter
return c
-/obj/effect/datacore/proc/addMinorCrime(id = "", var/datum/data/crime/crime)
+/datum/datacore/proc/addMinorCrime(id = "", var/datum/data/crime/crime)
for(var/datum/data/record/R in security)
if(R.fields["id"] == id)
var/list/crimes = R.fields["mi_crim"]
crimes |= crime
return
-/obj/effect/datacore/proc/removeMinorCrime(id, cDataId)
+/datum/datacore/proc/removeMinorCrime(id, cDataId)
for(var/datum/data/record/R in security)
if(R.fields["id"] == id)
var/list/crimes = R.fields["mi_crim"]
@@ -50,7 +49,7 @@
crimes -= crime
return
-/obj/effect/datacore/proc/removeMajorCrime(id, cDataId)
+/datum/datacore/proc/removeMajorCrime(id, cDataId)
for(var/datum/data/record/R in security)
if(R.fields["id"] == id)
var/list/crimes = R.fields["ma_crim"]
@@ -59,14 +58,14 @@
crimes -= crime
return
-/obj/effect/datacore/proc/addMajorCrime(id = "", var/datum/data/crime/crime)
+/datum/datacore/proc/addMajorCrime(id = "", var/datum/data/crime/crime)
for(var/datum/data/record/R in security)
if(R.fields["id"] == id)
var/list/crimes = R.fields["ma_crim"]
crimes |= crime
return
-/obj/effect/datacore/proc/manifest(var/nosleep = 0)
+/datum/datacore/proc/manifest(var/nosleep = 0)
spawn()
if(!nosleep)
sleep(40)
@@ -74,12 +73,12 @@
manifest_inject(H)
return
-/obj/effect/datacore/proc/manifest_modify(var/name, var/assignment)
+/datum/datacore/proc/manifest_modify(var/name, var/assignment)
var/datum/data/record/foundrecord = find_record("name", name, data_core.general)
if(foundrecord)
foundrecord.fields["rank"] = assignment
-/obj/effect/datacore/proc/get_manifest(monochrome, OOC)
+/datum/datacore/proc/get_manifest(monochrome, OOC)
var/list/heads = list()
var/list/sec = list()
var/list/eng = list()
@@ -135,49 +134,49 @@
misc[name] = rank
if(heads.len > 0)
dat += "
Heads |
"
- for(name in heads)
+ for(var/name in heads)
dat += "[name] | [heads[name]] |
"
even = !even
if(sec.len > 0)
dat += "Security |
"
- for(name in sec)
+ for(var/name in sec)
dat += "[name] | [sec[name]] |
"
even = !even
if(eng.len > 0)
dat += "Engineering |
"
- for(name in eng)
+ for(var/name in eng)
dat += "[name] | [eng[name]] |
"
even = !even
if(med.len > 0)
dat += "Medical |
"
- for(name in med)
+ for(var/name in med)
dat += "[name] | [med[name]] |
"
even = !even
if(sci.len > 0)
dat += "Science |
"
- for(name in sci)
+ for(var/name in sci)
dat += "[name] | [sci[name]] |
"
even = !even
if(sup.len > 0)
dat += "Supply |
"
- for(name in sup)
+ for(var/name in sup)
dat += "[name] | [sup[name]] |
"
even = !even
if(civ.len > 0)
dat += "Civilian |
"
- for(name in civ)
+ for(var/name in civ)
dat += "[name] | [civ[name]] |
"
even = !even
// in case somebody is insane and added them to the manifest, why not
if(bot.len > 0)
dat += "Silicon |
"
- for(name in bot)
+ for(var/name in bot)
dat += "[name] | [bot[name]] |
"
even = !even
// misc guys
if(misc.len > 0)
dat += "Miscellaneous |
"
- for(name in misc)
+ for(var/name in misc)
dat += "[name] | [misc[name]] |
"
even = !even
@@ -188,7 +187,7 @@
var/record_id_num = 1001
-/obj/effect/datacore/proc/manifest_inject(var/mob/living/carbon/human/H)
+/datum/datacore/proc/manifest_inject(var/mob/living/carbon/human/H)
if(H.mind && (H.mind.assigned_role != "MODE"))
var/assignment
if(H.mind.assigned_role)
@@ -199,6 +198,11 @@ var/record_id_num = 1001
assignment = "Unassigned"
var/id = num2hex(record_id_num++,6)
+ var/image = get_id_photo(H)
+ var/obj/item/weapon/photo/photo_front = new()
+ var/obj/item/weapon/photo/photo_side = new()
+ photo_front.photocreate(null, icon(image, dir = SOUTH))
+ photo_side.photocreate(null, icon(image, dir = WEST))
//These records should ~really~ be merged or something
//General Record
@@ -207,10 +211,14 @@ var/record_id_num = 1001
G.fields["name"] = H.real_name
G.fields["rank"] = assignment
G.fields["age"] = H.age
+ if(config.mutant_races)
+ G.fields["species"] = H.dna.species.name
G.fields["fingerprint"] = md5(H.dna.uni_identity)
G.fields["p_stat"] = "Active"
G.fields["m_stat"] = "Stable"
G.fields["sex"] = H.gender
+ G.fields["photo_front"] = photo_front
+ G.fields["photo_side"] = photo_side
general += G
//Medical Record
@@ -251,7 +259,166 @@ var/record_id_num = 1001
L.fields["b_dna"] = H.dna.unique_enzymes
L.fields["enzymes"] = H.dna.struc_enzymes
L.fields["identity"] = H.dna.uni_identity
- L.fields["image"] = getFlatIcon(H) //This is god-awful
+ L.fields["image"] = image
locked += L
return
+/datum/datacore/proc/get_id_photo(var/mob/living/carbon/human/H)
+ var/icon/photo = null
+ var/g = (H.gender == FEMALE) ? "f" : "m"
+ if(!config.mutant_races || H.dna.species.use_skintones)
+ photo = icon("icon" = 'icons/mob/human.dmi', "icon_state" = "[H.skin_tone]_[g]_s")
+ else
+ photo = icon("icon" = 'icons/mob/human.dmi', "icon_state" = "[H.dna.species.id]_[g]_s")
+ photo.Blend("#[H.dna.mutant_color]", ICON_MULTIPLY)
+
+ var/icon/eyes_s
+ if(EYECOLOR in H.dna.species.specflags)
+ eyes_s = icon("icon" = 'icons/mob/human_face.dmi', "icon_state" = "[H.dna.species.eyes]_s")
+ eyes_s.Blend("#[H.eye_color]", ICON_MULTIPLY)
+
+ var/datum/sprite_accessory/S
+ S = hair_styles_list[H.hair_style]
+ if(S && (HAIR in H.dna.species.specflags))
+ var/icon/hair_s = icon("icon" = S.icon, "icon_state" = "[S.icon_state]_s")
+ hair_s.Blend("#[H.hair_color]", ICON_MULTIPLY)
+ eyes_s.Blend(hair_s, ICON_OVERLAY)
+
+ S = facial_hair_styles_list[H.facial_hair_style]
+ if(S && (FACEHAIR in H.dna.species.specflags))
+ var/icon/facial_s = icon("icon" = S.icon, "icon_state" = "[S.icon_state]_s")
+ facial_s.Blend("#[H.facial_hair_color]", ICON_MULTIPLY)
+ eyes_s.Blend(facial_s, ICON_OVERLAY)
+
+ if(eyes_s)
+ photo.Blend(eyes_s, ICON_OVERLAY)
+
+ var/icon/clothes_s = null
+ switch(H.mind.assigned_role)
+ if("Assistant")
+ clothes_s = icon('icons/mob/uniform.dmi', "grey_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ if("Scientist")
+ clothes_s = icon('icons/mob/uniform.dmi', "toxinswhite_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "white"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat_tox"), ICON_OVERLAY)
+ if("Station Engineer")
+ clothes_s = icon('icons/mob/uniform.dmi', "engine_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "orange"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/belt.dmi', "utility"), ICON_OVERLAY)
+ if("Security Officer")
+ clothes_s = icon('icons/mob/uniform.dmi', "security_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "jackboots"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "bgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "armor"), ICON_OVERLAY)
+ if("Medical Doctor")
+ clothes_s = icon('icons/mob/uniform.dmi', "medical_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "white"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat"), ICON_OVERLAY)
+ if("Cargo Technician")
+ clothes_s = icon('icons/mob/uniform.dmi', "cargo_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ if("Shaft Miner")
+ clothes_s = icon('icons/mob/uniform.dmi', "miner_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ if("Atmospheric Technician")
+ clothes_s = icon('icons/mob/uniform.dmi', "atmos_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/belt.dmi', "utility"), ICON_OVERLAY)
+ if("Botanist")
+ clothes_s = icon('icons/mob/uniform.dmi', "hydroponics_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "ggloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "apron"), ICON_OVERLAY)
+ if("Chemist")
+ clothes_s = icon('icons/mob/uniform.dmi', "chemistrywhite_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "white"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat_chem"), ICON_OVERLAY)
+ if("Cook")
+ clothes_s = icon('icons/mob/uniform.dmi', "chef_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "chef"), ICON_OVERLAY)
+ if("Janitor")
+ clothes_s = icon('icons/mob/uniform.dmi', "janitor_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ if("Geneticist")
+ clothes_s = icon('icons/mob/uniform.dmi', "geneticswhite_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "white"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat_gen"), ICON_OVERLAY)
+ if("Virologist")
+ clothes_s = icon('icons/mob/uniform.dmi', "virologywhite_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "white"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat_vir"), ICON_OVERLAY)
+ if("Roboticist")
+ clothes_s = icon('icons/mob/uniform.dmi', "robotics_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat"), ICON_OVERLAY)
+ if("Lawyer")
+ clothes_s = icon('icons/mob/uniform.dmi', "bluesuit_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "laceups"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "suitjacket_blue"), ICON_OVERLAY)
+ if("Clown")
+ clothes_s = icon('icons/mob/uniform.dmi', "clown_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "clown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/mask.dmi', "clown"), ICON_OVERLAY)
+ if("Mime")
+ clothes_s = icon('icons/mob/uniform.dmi', "mime_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "lgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/mask.dmi', "mime"), ICON_OVERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "suspenders"), ICON_OVERLAY)
+ if("Bartender")
+ clothes_s = icon('icons/mob/uniform.dmi', "ba_suit_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "armoralt"), ICON_OVERLAY)
+ if("Quartermaster")
+ clothes_s = icon('icons/mob/uniform.dmi', "qm_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ if("Chaplain")
+ clothes_s = icon('icons/mob/uniform.dmi', "chapblack_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+ if("Research Director")
+ clothes_s = icon('icons/mob/uniform.dmi', "director_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat"), ICON_OVERLAY)
+ if("Chief Medical Officer")
+ clothes_s = icon('icons/mob/uniform.dmi', "cmo_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "labcoat_cmo"), ICON_OVERLAY)
+ if("Captain")
+ clothes_s = icon('icons/mob/uniform.dmi', "captain_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "capcarapace"), ICON_OVERLAY)
+ if("Head of Security")
+ clothes_s = icon('icons/mob/uniform.dmi', "hos_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "jackboots"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "bgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "hostrench"), ICON_OVERLAY)
+ if("Warden")
+ clothes_s = icon('icons/mob/uniform.dmi', "warden_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "jackboots"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "bgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "warden_jacket"), ICON_OVERLAY)
+ if("Detective")
+ clothes_s = icon('icons/mob/uniform.dmi', "detective_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "bgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/mask.dmi', "cigaron"), ICON_OVERLAY)
+ clothes_s.Blend(icon('icons/mob/head.dmi', "detective"), ICON_OVERLAY)
+ clothes_s.Blend(icon('icons/mob/suit.dmi', "detective"), ICON_OVERLAY)
+ if("Chief Engineer")
+ clothes_s = icon('icons/mob/uniform.dmi', "chief_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/hands.dmi', "bgloves"), ICON_UNDERLAY)
+ clothes_s.Blend(icon('icons/mob/belt.dmi', "utility"), ICON_OVERLAY)
+ if("Head of Personnel")
+ clothes_s = icon('icons/mob/uniform.dmi', "hop_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "brown"), ICON_UNDERLAY)
+ if("Librarian")
+ clothes_s = icon('icons/mob/uniform.dmi', "red_suit_s")
+ clothes_s.Blend(icon('icons/mob/feet.dmi', "black"), ICON_UNDERLAY)
+
+ if(clothes_s)
+ photo.Blend(clothes_s, ICON_OVERLAY)
+
+ return photo
diff --git a/code/datums/diseases/advance/advance.dm b/code/datums/diseases/advance/advance.dm
index 60f500503015865..28b088522404cab 100644
--- a/code/datums/diseases/advance/advance.dm
+++ b/code/datums/diseases/advance/advance.dm
@@ -396,7 +396,7 @@ var/list/advance_cures = list(
if(D.symptoms.len > 0)
- var/new_name = input(user, "Name your new disease.", "New Name")
+ var/new_name = stripped_input(user, "Name your new disease.", "New Name")
if(!new_name)
return
D.AssignName(new_name)
diff --git a/code/datums/diseases/advance/symptoms/fire.dm b/code/datums/diseases/advance/symptoms/fire.dm
new file mode 100644
index 000000000000000..bc63c1709607310
--- /dev/null
+++ b/code/datums/diseases/advance/symptoms/fire.dm
@@ -0,0 +1,40 @@
+/*
+//////////////////////////////////////
+
+Spontaneous Combustion
+
+ Slightly hidden.
+ Lowers resistance tremendously.
+ Decreases stage tremendously.
+ Decreases transmittablity tremendously.
+ Fatal Level.
+
+Bonus
+ Ignites infected mob.
+
+//////////////////////////////////////
+*/
+
+/datum/symptom/fire
+
+ name = "Spontaneous Combustion"
+ stealth = 1
+ resistance = -4
+ stage_speed = -4
+ transmittable = -4
+ level = 6
+ severity = 5
+
+/datum/symptom/fire/Activate(var/datum/disease/advance/A)
+ ..()
+ if(prob(SYMPTOM_ACTIVATION_PROB))
+ var/mob/living/M = A.affected_mob
+ switch(A.stage)
+ if(4)
+ M.adjust_fire_stacks(5)
+ M.IgniteMob()
+
+ if(5)
+ M.adjust_fire_stacks(10)
+ M.IgniteMob()
+ return
\ No newline at end of file
diff --git a/code/datums/diseases/advance/symptoms/heal.dm b/code/datums/diseases/advance/symptoms/heal.dm
index 1280be88102e0ad..16e16c914a6a04b 100644
--- a/code/datums/diseases/advance/symptoms/heal.dm
+++ b/code/datums/diseases/advance/symptoms/heal.dm
@@ -58,7 +58,7 @@ Bonus
/datum/symptom/heal/metabolism
- name = "Anti-Bodies Metabolism "
+ name = "Anti-Bodies Metabolism"
stealth = -1
resistance = -1
stage_speed = -1
diff --git a/code/datums/diseases/advance/symptoms/skin.dm b/code/datums/diseases/advance/symptoms/skin.dm
new file mode 100644
index 000000000000000..d2bcf62735850ca
--- /dev/null
+++ b/code/datums/diseases/advance/symptoms/skin.dm
@@ -0,0 +1,86 @@
+/*
+//////////////////////////////////////
+Vitiligo
+
+ Extremely Noticable.
+ Decreases resistance slightly.
+ Reduces stage speed slightly.
+ Reduces transmission.
+ Critical Level.
+
+BONUS
+ Makes the mob lose skin pigmentation.
+
+//////////////////////////////////////
+*/
+
+/datum/symptom/vitiligo
+
+ name = "Vitiligo"
+ stealth = -3
+ resistance = -1
+ stage_speed = -1
+ transmittable = -2
+ level = 4
+ severity = 1
+
+/datum/symptom/vitiligo/Activate(var/datum/disease/advance/A)
+ ..()
+ if(prob(SYMPTOM_ACTIVATION_PROB))
+ var/mob/living/M = A.affected_mob
+ if(istype(M, /mob/living/carbon/human))
+ var/mob/living/carbon/human/H = M
+ if(H.skin_tone == "albino")
+ return
+ switch(A.stage)
+ if(5)
+ H.skin_tone = "albino"
+ H.update_body(0)
+ else
+ H.visible_message("[H] looks a bit pale...", "You look a bit pale...")
+
+ return
+
+
+/*
+//////////////////////////////////////
+Revitiligo
+
+ Extremely Noticable.
+ Decreases resistance slightly.
+ Reduces stage speed slightly.
+ Reduces transmission.
+ Critical Level.
+
+BONUS
+ Makes the mob gain skin pigmentation.
+
+//////////////////////////////////////
+*/
+
+/datum/symptom/revitiligo
+
+ name = "Revitiligo"
+ stealth = -3
+ resistance = -1
+ stage_speed = -1
+ transmittable = -2
+ level = 4
+ severity = 1
+
+/datum/symptom/vitiligo/Activate(var/datum/disease/advance/A)
+ ..()
+ if(prob(SYMPTOM_ACTIVATION_PROB))
+ var/mob/living/M = A.affected_mob
+ if(istype(M, /mob/living/carbon/human))
+ var/mob/living/carbon/human/H = M
+ if(H.skin_tone == "african2")
+ return
+ switch(A.stage)
+ if(5)
+ H.skin_tone = "african2"
+ H.update_body(0)
+ else
+ H.visible_message("[H] looks a bit dark...", "You look a bit dark...")
+
+ return
\ No newline at end of file
diff --git a/code/datums/diseases/advance/symptoms/visionloss.dm b/code/datums/diseases/advance/symptoms/vision.dm
similarity index 54%
rename from code/datums/diseases/advance/symptoms/visionloss.dm
rename to code/datums/diseases/advance/symptoms/vision.dm
index c80b5a35d6c42fa..b63a4ee729faef8 100644
--- a/code/datums/diseases/advance/symptoms/visionloss.dm
+++ b/code/datums/diseases/advance/symptoms/vision.dm
@@ -1,49 +1,89 @@
-/*
-//////////////////////////////////////
-
-Hyphema (Eye bleeding)
-
- Slightly noticable.
- Lowers resistance tremendously.
- Decreases stage speed tremendously.
- Decreases transmittablity.
- Critical Level.
-
-Bonus
- Causes blindness.
-
-//////////////////////////////////////
-*/
-
-/datum/symptom/visionloss
-
- name = "Hyphema"
- stealth = -1
- resistance = -4
- stage_speed = -4
- transmittable = -3
- level = 5
- severity = 4
-
-/datum/symptom/visionloss/Activate(var/datum/disease/advance/A)
- ..()
- if(prob(SYMPTOM_ACTIVATION_PROB))
- var/mob/living/M = A.affected_mob
- switch(A.stage)
- if(1, 2)
- M << "Your eyes itch."
- if(3, 4)
- M << "Your eyes ache."
- M.eye_blurry = 10
- M.eye_stat += 1
- else
- M << "Your eyes burn horrificly!"
- M.eye_blurry = 20
- M.eye_stat += 5
- if (M.eye_stat >= 10)
- M.disabilities |= NEARSIGHT
- if (prob(M.eye_stat - 10 + 1) && !(M.eye_blind))
- M << "You go blind!"
- M.disabilities |= BLIND
- M.eye_blind = 1
- return
\ No newline at end of file
+/*
+//////////////////////////////////////
+
+Hyphema (Eye bleeding)
+
+ Slightly noticable.
+ Lowers resistance tremendously.
+ Decreases stage speed tremendously.
+ Decreases transmittablity.
+ Critical Level.
+
+Bonus
+ Causes blindness.
+
+//////////////////////////////////////
+*/
+
+/datum/symptom/visionloss
+
+ name = "Hyphema"
+ stealth = -1
+ resistance = -4
+ stage_speed = -4
+ transmittable = -3
+ level = 5
+ severity = 4
+
+/datum/symptom/visionloss/Activate(var/datum/disease/advance/A)
+ ..()
+ if(prob(SYMPTOM_ACTIVATION_PROB))
+ var/mob/living/M = A.affected_mob
+ switch(A.stage)
+ if(1, 2)
+ M << "Your eyes itch."
+ if(3, 4)
+ M << "Your eyes ache."
+ M.eye_blurry = 10
+ M.eye_stat += 1
+ else
+ M << "Your eyes burn horrificly!"
+ M.eye_blurry = 20
+ M.eye_stat += 5
+ if (M.eye_stat >= 10)
+ M.disabilities |= NEARSIGHT
+ if (prob(M.eye_stat - 10 + 1) && !(M.eye_blind))
+ M << "You go blind!"
+ M.disabilities |= BLIND
+ M.eye_blind = 1
+ return
+
+
+/*
+//////////////////////////////////////
+
+Ocular Restoration
+
+ Noticable.
+ Lowers resistance significantly.
+ Decreases stage speed moderately..
+ Decreases transmittablity tremendously.
+ High level.
+
+Bonus
+ Restores eyesight.
+
+//////////////////////////////////////
+*/
+
+/datum/symptom/visionaid
+
+ name = "Ocular Restoration"
+ stealth = -1
+ resistance = -3
+ stage_speed = -2
+ transmittable = -4
+ level = 4
+
+/datum/symptom/visionaid/Activate(var/datum/disease/advance/A)
+ ..()
+ if(prob(SYMPTOM_ACTIVATION_PROB * 5))
+ var/mob/living/M = A.affected_mob
+ switch(A.stage)
+ if(4, 5)
+ if (M.reagents.get_reagent_amount("oculine") < 20)
+ M.reagents.add_reagent("oculine", 20)
+ else
+ if(prob(SYMPTOM_ACTIVATION_PROB * 5))
+ M << "[pick("Your eyes feel great.", "You are now blinking manually.", "You don't feel the need to blink.")]"
+ return
diff --git a/code/datums/diseases/advance/symptoms/vitiligo.dm b/code/datums/diseases/advance/symptoms/vitiligo.dm
deleted file mode 100644
index e24be2c36b5f5cd..000000000000000
--- a/code/datums/diseases/advance/symptoms/vitiligo.dm
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
-//////////////////////////////////////
-Vitiligo
-
- Extremely Noticable.
- Decreases resistance slightly.
- Reduces stage speed slightly.
- Reduces transmission.
- Critical Level.
-
-BONUS
- Makes the mob lose skin pigmentation.
-
-//////////////////////////////////////
-*/
-
-/datum/symptom/vitiligo
-
- name = "Vitiligo"
- stealth = -3
- resistance = -1
- stage_speed = -1
- transmittable = -2
- level = 5
- severity = 1
-
-/datum/symptom/vitiligo/Activate(var/datum/disease/advance/A)
- ..()
- if(prob(SYMPTOM_ACTIVATION_PROB))
- var/mob/living/M = A.affected_mob
- if(istype(M, /mob/living/carbon/human))
- var/mob/living/carbon/human/H = M
- if(H.skin_tone == "albino")
- return
- switch(A.stage)
- if(5)
- H.skin_tone = "albino"
- H.update_body(0)
- else
- H.visible_message("[H] looks a bit pale...", "You look a bit pale...")
-
- return
\ No newline at end of file
diff --git a/code/datums/goon_mutations_powers.dm b/code/datums/goon_mutations_powers.dm
index 38069f484886122..e164eced75250a5 100644
--- a/code/datums/goon_mutations_powers.dm
+++ b/code/datums/goon_mutations_powers.dm
@@ -6,6 +6,7 @@
text_gain_indication = "You begin to fade into the shadows."
text_lose_indication = "You become fully visible."
+
/datum/mutation/human/stealth/on_life(mob/living/carbon/human/owner)
var/turf/simulated/T = get_turf(owner)
if(!istype(T))
@@ -26,8 +27,11 @@
lowest_value = 256 * 14
text_gain_indication = "You feel one with your surroundings."
text_lose_indication = "You feel oddly exposed."
-
+ var/last_location
/datum/mutation/human/chameleon/on_life(mob/living/carbon/human/owner)
+ if(owner.loc != last_location)
+ owner.alpha = round(255 * 0.80)
+ last_location = owner.loc
if((world.time - owner.last_movement) >= 30 && !owner.stat && owner.canmove && !owner.restrained())
owner.alpha -= 25
else
diff --git a/code/datums/spell.dm b/code/datums/spell.dm
index c49252f1a1ec503..7137bbf9ad1b575 100644
--- a/code/datums/spell.dm
+++ b/code/datums/spell.dm
@@ -58,6 +58,8 @@ var/list/spells = typesof(/obj/effect/proc_holder/spell) //needed for the badmin
if(user.z == ZLEVEL_CENTCOM && !centcom_cancast) //Certain spells are not allowed on the centcom zlevel
return 0
+ if(user.z == ZLEVEL_CENTCOM && ticker.mode.name == "ragin' mages")
+ return 0
if(!skipcharge)
switch(charge_type)
diff --git a/code/datums/supplypacks.dm b/code/datums/supplypacks.dm
index 846e90a51bf680c..d00eb9d40308435 100644
--- a/code/datums/supplypacks.dm
+++ b/code/datums/supplypacks.dm
@@ -723,9 +723,9 @@ var/list/all_supply_groups = list(supply_emergency,supply_security,supply_engine
/datum/supply_packs/organic/food
name = "Food Crate"
- contains = list(/obj/item/weapon/reagent_containers/food/drinks/flour,
- /obj/item/weapon/reagent_containers/food/drinks/milk,
- /obj/item/weapon/reagent_containers/food/drinks/soymilk,
+ contains = list(/obj/item/weapon/reagent_containers/food/condiment/flour,
+ /obj/item/weapon/reagent_containers/food/condiment/milk,
+ /obj/item/weapon/reagent_containers/food/condiment/soymilk,
/obj/item/weapon/storage/fancy/egg_box,
/obj/item/weapon/reagent_containers/food/condiment/enzyme,
/obj/item/weapon/reagent_containers/food/condiment/sugar,
diff --git a/code/game/gamemodes/blob/blob.dm b/code/game/gamemodes/blob/blob.dm
index a8613af17f54d7b..ae0b05441c64018 100644
--- a/code/game/gamemodes/blob/blob.dm
+++ b/code/game/gamemodes/blob/blob.dm
@@ -18,6 +18,7 @@ var/list/blob_nodes = list()
restricted_jobs = list("Cyborg", "AI")
var/declared = 0
+ var/burst = 0
var/cores_to_spawn = 1
var/players_per_core = 30
@@ -52,6 +53,39 @@ var/list/blob_nodes = list()
return 1
+/datum/game_mode/blob/proc/get_blob_candidates()
+ var/list/candidates = list()
+ for(var/mob/living/carbon/human/player in player_list)
+ if(!player.stat && player.mind && !player.mind.special_role && !jobban_isbanned(player, "Syndicate") && (player.client.prefs.be_special & BE_BLOB))
+ candidates += player
+ return candidates
+
+
+/datum/game_mode/blob/proc/blobize(var/mob/living/carbon/human/blob)
+ var/datum/mind/blobmind = blob.mind
+ if(!istype(blobmind))
+ return 0
+ infected_crew += blobmind
+ blobmind.special_role = "Blob"
+ log_game("[blob.key] (ckey) has been selected as a Blob")
+ greet_blob(blobmind)
+ blob << "You feel very tired and bloated! You don't have long before you burst!"
+ spawn(600)
+ burst_blob(blobmind)
+ return 1
+
+/datum/game_mode/blob/proc/make_blobs(var/count)
+ var/list/candidates = get_blob_candidates()
+ var/mob/living/carbon/human/blob = null
+ count=min(count, candidates.len)
+ for(var/i = 0, i < count, i++)
+ blob = pick(candidates)
+ candidates -= blob
+ blobize(blob)
+ return count
+
+
+
/datum/game_mode/blob/announce()
world << "The current game mode is - Blob!"
world << "A dangerous alien organism is rapidly spreading throughout the station!"
@@ -72,27 +106,39 @@ var/list/blob_nodes = list()
/datum/game_mode/blob/proc/burst_blobs()
for(var/datum/mind/blob in infected_crew)
-
- var/client/blob_client = null
- var/turf/location = null
-
- if(iscarbon(blob.current))
- var/mob/living/carbon/C = blob.current
- if(directory[ckey(blob.key)])
- blob_client = directory[ckey(blob.key)]
- location = get_turf(C)
- if(location.z != ZLEVEL_STATION || istype(location, /turf/space))
- location = null
+ burst_blob(blob)
+
+/datum/game_mode/blob/proc/burst_blob(var/datum/mind/blob, var/warned=0)
+ var/client/blob_client = null
+ var/turf/location = null
+
+ if(iscarbon(blob.current))
+ var/mob/living/carbon/C = blob.current
+ if(directory[ckey(blob.key)])
+ blob_client = directory[ckey(blob.key)]
+ location = get_turf(C)
+ if(location.z != ZLEVEL_STATION || istype(location, /turf/space))
+ if(!warned)
+ C << "You feel ready to burst, but this isn't an appropriate place! You must return to the station!"
+ message_admins("[key_name(C)] was in space when the blobs burst, and will die if he doesn't return to the station.")
+ spawn(300)
+ burst_blob(blob, 1)
+ else
+ burst ++
+ log_admin("[key_name(C)] was in space when attempting to burst as a blob.")
+ message_admins("[key_name(C)] was in space when attempting to burst as a blob.")
+ C.gib()
+ make_blobs(1)
+ check_finished() //Still needed in case we can't make any blobs
+
+ else if(blob_client && location)
+ burst ++
C.gib()
-
-
- if(blob_client && location)
- var/obj/effect/blob/core/core = new(location, 200, blob_client, blob_point_rate)
- if(core.overmind && core.overmind.mind)
- core.overmind.mind.name = blob.name
- infected_crew -= blob
- infected_crew += core.overmind.mind
-
+ var/obj/effect/blob/core/core = new(location, 200, blob_client, blob_point_rate)
+ if(core.overmind && core.overmind.mind)
+ core.overmind.mind.name = blob.name
+ infected_crew -= blob
+ infected_crew += core.overmind.mind
/datum/game_mode/blob/post_setup()
diff --git a/code/game/gamemodes/blob/blob_finish.dm b/code/game/gamemodes/blob/blob_finish.dm
index f83550796b7a7a5..56c1b4449c823ed 100644
--- a/code/game/gamemodes/blob/blob_finish.dm
+++ b/code/game/gamemodes/blob/blob_finish.dm
@@ -1,5 +1,5 @@
/datum/game_mode/blob/check_finished()
- if(!declared)//No blobs have been spawned yet
+ if(infected_crew.len > burst)//Some blobs have yet to burst
return 0
if(blobwincount <= blobs.len)//Blob took over
return 1
diff --git a/code/game/gamemodes/nuclear/pinpointer.dm b/code/game/gamemodes/nuclear/pinpointer.dm
index 5a378980f8f5f84..bfccd051890d842 100644
--- a/code/game/gamemodes/nuclear/pinpointer.dm
+++ b/code/game/gamemodes/nuclear/pinpointer.dm
@@ -12,6 +12,9 @@
var/obj/item/weapon/disk/nuclear/the_disk = null
var/active = 0
+/obj/item/weapon/pinpointer/Destroy()
+ active = 0
+ ..()
/obj/item/weapon/pinpointer/attack_self()
if(!active)
@@ -239,7 +242,8 @@
if(16 to INFINITY)
icon_state = "pinonfar"
- spawn(5) .()
+ spawn(5)
+ .()
/obj/item/weapon/pinpointer/operative
name = "operative pinpointer"
diff --git a/code/game/gamemodes/wizard/spellbook.dm b/code/game/gamemodes/wizard/spellbook.dm
index 34cc59457e975f5..084cefb272ccaa7 100644
--- a/code/game/gamemodes/wizard/spellbook.dm
+++ b/code/game/gamemodes/wizard/spellbook.dm
@@ -12,6 +12,7 @@
var/op = 1
var/activepage
var/list/active_challenges = list()
+ var/mob/living/carbon/human/owner
/obj/item/weapon/spellbook/attackby(obj/item/O as obj, mob/user as mob)
if(istype(O, /obj/item/weapon/antag_spawner/contract))
@@ -28,6 +29,13 @@
/obj/item/weapon/spellbook/attack_self(mob/user as mob)
+ if(!owner)
+ user << "You bind the spellbook to yourself."
+ owner = user
+ return
+ if(user != owner)
+ user << "The [name] does not recognize you as it's owner and refuses to open."
+ return
user.set_machine(src)
var/dat
if(temp)
@@ -38,7 +46,7 @@
dat += "
"
dat += "Learn and Improve Magical Abilities
"
dat += "Summon Magical Tools and Weapons
"
- if(ticker.mode != "ragin' mages") // we totally need summon guns x100
+ if(ticker.mode.name != "ragin' mages") // we totally need summon guns x100
dat += "Raise The Stakes For More Power
"
dat += "
"
dat += "Re-memorize Spells
"
@@ -100,7 +108,7 @@
dat += "Instant Summons (10)
"
dat += "This spell can be used to bind a valuable item to you, bringing it to your hand at will. Using this spell while holding the bound item will allow you to unbind it. It does not require wizard garb.
"
- if(ticker.mode != "ragin' mages") // we totally need summon guns x100
+ if(ticker.mode.name != "ragin' mages") // we totally need summon greentext x100
dat += "Summon Events (One time use, persistent global spell)
"
dat += "Give Murphy's law a little push and replace all events with special wizard ones that will confound and confuse everyone. Multiple castings increase the rate of these events.
"
diff --git a/code/game/gamemodes/wizard/wizard.dm b/code/game/gamemodes/wizard/wizard.dm
index ff3763796bb8246..1b6b18b7c899bed 100644
--- a/code/game/gamemodes/wizard/wizard.dm
+++ b/code/game/gamemodes/wizard/wizard.dm
@@ -156,9 +156,12 @@
wizard_mob.equip_to_slot_or_del(new /obj/item/weapon/storage/box/survival(wizard_mob), slot_in_backpack)
// wizard_mob.equip_to_slot_or_del(new /obj/item/weapon/scrying_gem(wizard_mob), slot_l_store) For scrying gem.
wizard_mob.equip_to_slot_or_del(new /obj/item/weapon/teleportation_scroll(wizard_mob), slot_r_store)
- wizard_mob.equip_to_slot_or_del(new /obj/item/weapon/spellbook(wizard_mob), slot_r_hand)
+ var/obj/item/weapon/spellbook/spellbook = new /obj/item/weapon/spellbook(wizard_mob)
+ spellbook.owner = wizard_mob
+ wizard_mob.equip_to_slot_or_del(spellbook, slot_r_hand)
wizard_mob << "You will find a list of available spells in your spell book. Choose your magic arsenal carefully."
+ wizard_mob << "The spellbook is bound to you, and others cannot use it."
wizard_mob << "In your pockets you will find a teleport scroll. Use it as needed."
wizard_mob.mind.store_memory("Remember: do not forget to prepare your spells.")
wizard_mob.update_icons()
diff --git a/code/game/jobs/job/engineering.dm b/code/game/jobs/job/engineering.dm
index 0136e52eb2839c1..8c8c69ce873ace9 100644
--- a/code/game/jobs/job/engineering.dm
+++ b/code/game/jobs/job/engineering.dm
@@ -70,7 +70,7 @@ Station Engineer
/datum/job/engineer/equip_items(var/mob/living/carbon/human/H)
H.equip_to_slot_or_del(new /obj/item/clothing/under/rank/engineer(H), slot_w_uniform)
- H.equip_to_slot_or_del(new /obj/item/clothing/shoes/sneakers/orange(H), slot_shoes)
+ H.equip_to_slot_or_del(new /obj/item/clothing/shoes/workboots(H), slot_shoes)
H.equip_to_slot_or_del(new /obj/item/weapon/storage/belt/utility/full(H), slot_belt)
H.equip_to_slot_or_del(new /obj/item/clothing/head/hardhat(H), slot_head)
H.equip_to_slot_or_del(new /obj/item/device/t_scanner(H), slot_r_store)
diff --git a/code/game/machinery/computer/medical.dm b/code/game/machinery/computer/medical.dm
index d673cf214a5c37e..45e0278b5df8ede 100644
--- a/code/game/machinery/computer/medical.dm
+++ b/code/game/machinery/computer/medical.dm
@@ -32,11 +32,11 @@
if(..())
return
var/dat
- if (src.temp)
+ if(src.temp)
dat = text("[src.temp]
Clear Screen")
else
dat = text("Confirm Identity: []
", src, (src.scan ? text("[]", src.scan.name) : "----------"))
- if (src.authenticated)
+ if(src.authenticated)
switch(src.screen)
if(1.0)
dat += {"
@@ -73,7 +73,7 @@
var/blood_type = ""
var/b_dna = ""
for(var/datum/data/record/E in data_core.medical)
- if ((E.fields["name"] == R.fields["name"] && E.fields["id"] == R.fields["id"]))
+ if((E.fields["name"] == R.fields["name"] && E.fields["id"] == R.fields["id"]))
blood_type = E.fields["blood_type"]
b_dna = E.fields["b_dna"]
var/background
@@ -105,10 +105,20 @@
dat += "Medical Record |
"
if(active1 in data_core.general)
- dat += "Name: | [active1.fields["name"]] |
"
+ if(istype(active1.fields["photo_front"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P1 = active1.fields["photo_front"]
+ user << browse_rsc(P1.img, "photo_front")
+ if(istype(active1.fields["photo_side"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P2 = active1.fields["photo_side"]
+ user << browse_rsc(P2.img, "photo_side")
+ dat += "Name: | [active1.fields["name"]] | "
+ dat += "![](photo_front) | "
+ dat += "![](photo_side) |
"
dat += "ID: | [active1.fields["id"]] |
"
dat += "Sex: | [active1.fields["sex"]] |
"
dat += "Age: | [active1.fields["age"]] |
"
+ if(config.mutant_races)
+ dat += "Species: | [active1.fields["species"]] |
"
dat += "Fingerprint: | [active1.fields["fingerprint"]] |
"
dat += "Physical Status: | [active1.fields["p_stat"]] |
"
dat += "Mental Status: | [active1.fields["m_stat"]] |
"
@@ -185,33 +195,34 @@
return
/obj/machinery/computer/med_data/Topic(href, href_list)
- if(..())
- return
+ . = ..()
+ if(.)
+ return .
if(!(active1 in data_core.general))
src.active1 = null
if(!(active2 in data_core.medical))
src.active2 = null
- if ((usr.contents.Find(src) || (in_range(src, usr) && istype(src.loc, /turf))) || (istype(usr, /mob/living/silicon)))
+ if((usr.contents.Find(src) || (in_range(src, usr) && istype(src.loc, /turf))) || (istype(usr, /mob/living/silicon)))
usr.set_machine(src)
- if (href_list["temp"])
+ if(href_list["temp"])
src.temp = null
- if (href_list["scan"])
- if (src.scan)
+ if(href_list["scan"])
+ if(src.scan)
src.scan.loc = src.loc
src.scan = null
else
var/obj/item/I = usr.get_active_hand()
- if (istype(I, /obj/item/weapon/card/id))
+ if(istype(I, /obj/item/weapon/card/id))
usr.drop_item()
I.loc = src
src.scan = I
- else if (href_list["logout"])
+ else if(href_list["logout"])
src.authenticated = null
src.screen = null
src.active1 = null
src.active2 = null
- else if (href_list["choice"])
+ else if(href_list["choice"])
// SORTING!
if(href_list["choice"] == "Sorting")
// Reverse the order if clicked twice
@@ -224,21 +235,21 @@
// New sorting order!
sortBy = href_list["sort"]
order = initial(order)
- else if (href_list["login"])
- if (istype(usr, /mob/living/silicon))
+ else if(href_list["login"])
+ if(istype(usr, /mob/living/silicon))
src.active1 = null
src.active2 = null
src.authenticated = 1
src.rank = "AI"
src.screen = 1
- else if (istype(src.scan, /obj/item/weapon/card/id))
+ else if(istype(src.scan, /obj/item/weapon/card/id))
src.active1 = null
src.active2 = null
- if (src.check_access(src.scan))
+ if(src.check_access(src.scan))
src.authenticated = src.scan.registered_name
src.rank = src.scan.assignment
src.screen = 1
- if (src.authenticated)
+ if(src.authenticated)
if(href_list["screen"])
src.screen = text2num(href_list["screen"])
@@ -264,88 +275,94 @@
Severity: [Dis.severity]"}
- else if (href_list["del_all"])
+ else if(href_list["del_all"])
src.temp = text("Are you sure you wish to delete all records?
\n\tYes
\n\tNo
", src, src)
- else if (href_list["del_all2"])
+ else if(href_list["del_all2"])
investigate_log("[usr.name] ([usr.key]) has deleted all medical records.", "records")
data_core.medical.Cut()
src.temp = "All records deleted."
- else if (href_list["field"])
+ else if(href_list["field"])
var/a1 = src.active1
var/a2 = src.active2
switch(href_list["field"])
if("fingerprint")
if(active1)
- var/t1 = copytext(sanitize(input("Please input fingerprint hash:", "Med. records", src.active1.fields["fingerprint"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active1 != a1))
+ var/t1 = stripped_input("Please input fingerprint hash:", "Med. records", src.active1.fields["fingerprint"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, a1))
return
src.active1.fields["fingerprint"] = t1
if("sex")
if(active1)
- if (src.active1.fields["sex"] == "Male")
+ if(src.active1.fields["sex"] == "Male")
src.active1.fields["sex"] = "Female"
else
src.active1.fields["sex"] = "Male"
if("age")
if(active1)
var/t1 = input("Please input age:", "Med. records", src.active1.fields["age"], null) as num
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active1 != a1))
+ if(!canUseMedicalRecordsConsole(usr, t1, a1))
return
src.active1.fields["age"] = t1
+ if("species")
+ if(active1)
+ var/t1 = stripped_input("Please input species name", "Med. records", src.active1.fields["species"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, a1))
+ return
+ active1.fields["species"] = t1
if("mi_dis")
if(active2)
- var/t1 = copytext(sanitize(input("Please input minor disabilities list:", "Med. records", src.active2.fields["mi_dis"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_input("Please input minor disabilities list:", "Med. records", src.active2.fields["mi_dis"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["mi_dis"] = t1
if("mi_dis_d")
if(active2)
- var/t1 = copytext(sanitize(input("Please summarize minor dis.:", "Med. records", src.active2.fields["mi_dis_d"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Please summarize minor dis.:", "Med. records", src.active2.fields["mi_dis_d"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["mi_dis_d"] = t1
if("ma_dis")
if(active2)
- var/t1 = copytext(sanitize(input("Please input major diabilities list:", "Med. records", src.active2.fields["ma_dis"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_input("Please input major diabilities list:", "Med. records", src.active2.fields["ma_dis"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["ma_dis"] = t1
if("ma_dis_d")
if(active2)
- var/t1 = copytext(sanitize(input("Please summarize major dis.:", "Med. records", src.active2.fields["ma_dis_d"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Please summarize major dis.:", "Med. records", src.active2.fields["ma_dis_d"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["ma_dis_d"] = t1
if("alg")
if(active2)
- var/t1 = copytext(sanitize(input("Please state allergies:", "Med. records", src.active2.fields["alg"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_input("Please state allergies:", "Med. records", src.active2.fields["alg"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["alg"] = t1
if("alg_d")
if(active2)
- var/t1 = copytext(sanitize(input("Please summarize allergies:", "Med. records", src.active2.fields["alg_d"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Please summarize allergies:", "Med. records", src.active2.fields["alg_d"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["alg_d"] = t1
if("cdi")
if(active2)
- var/t1 = copytext(sanitize(input("Please state diseases:", "Med. records", src.active2.fields["cdi"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_input("Please state diseases:", "Med. records", src.active2.fields["cdi"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["cdi"] = t1
if("cdi_d")
if(active2)
- var/t1 = copytext(sanitize(input("Please summarize diseases:", "Med. records", src.active2.fields["cdi_d"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Please summarize diseases:", "Med. records", src.active2.fields["cdi_d"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["cdi_d"] = t1
if("notes")
if(active2)
- var/t1 = copytext(sanitize(input("Please summarize notes:", "Med. records", src.active2.fields["notes"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Please summarize notes:", "Med. records", src.active2.fields["notes"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["notes"] = t1
if("p_stat")
@@ -359,13 +376,25 @@
src.temp = text("Blood Type:
\n\tA- A+
\n\tB- B+
\n\tAB- AB+
\n\tO- O+
", src, src, src, src, src, src, src, src)
if("b_dna")
if(active2)
- var/t1 = copytext(sanitize(input("Please input DNA hash:", "Med. records", src.active2.fields["b_dna"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_input("Please input DNA hash:", "Med. records", src.active2.fields["b_dna"], null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
src.active2.fields["b_dna"] = t1
+ if("show_photo_front")
+ if(active1)
+ if(active1.fields["photo_front"])
+ if(istype(active1.fields["photo_front"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P = active1.fields["photo_front"]
+ P.show(usr)
+ if("show_photo_side")
+ if(active1)
+ if(active1.fields["photo_side"])
+ if(istype(active1.fields["photo_side"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P = active1.fields["photo_side"]
+ P.show(usr)
else
- else if (href_list["p_stat"])
+ else if(href_list["p_stat"])
if(active1)
switch(href_list["p_stat"])
if("deceased")
@@ -377,7 +406,7 @@
if("unfit")
src.active1.fields["p_stat"] = "Physically Unfit"
- else if (href_list["m_stat"])
+ else if(href_list["m_stat"])
if(active1)
switch(href_list["m_stat"])
if("insane")
@@ -390,7 +419,7 @@
src.active1.fields["m_stat"] = "Stable"
- else if (href_list["blood_type"])
+ else if(href_list["blood_type"])
if(active2)
switch(href_list["blood_type"])
if("an")
@@ -411,17 +440,17 @@
src.active2.fields["blood_type"] = "O+"
- else if (href_list["del_r"])
+ else if(href_list["del_r"])
if(active2)
src.temp = text("Are you sure you wish to delete the record (Medical Portion Only)?
\n\tYes
\n\tNo
", src, src)
- else if (href_list["del_r2"])
+ else if(href_list["del_r2"])
investigate_log("[usr.name] ([usr.key]) has deleted the medical records for [active1.fields["name"]].", "records")
if(active2)
data_core.medical -= active2
active2 = null
- else if (href_list["d_rec"])
+ else if(href_list["d_rec"])
active1 = find_record("id", href_list["d_rec"], data_core.general)
if(active1)
active2 = find_record("id", href_list["d_rec"], data_core.medical)
@@ -429,8 +458,8 @@
active1 = null
screen = 4
- else if (href_list["new"])
- if ((istype(src.active1, /datum/data/record) && !( istype(src.active2, /datum/data/record) )))
+ else if(href_list["new"])
+ if((istype(src.active1, /datum/data/record) && !( istype(src.active2, /datum/data/record) )))
var/datum/data/record/R = new /datum/data/record( )
R.fields["name"] = src.active1.fields["name"]
R.fields["id"] = src.active1.fields["id"]
@@ -450,46 +479,46 @@
src.active2 = R
src.screen = 4
- else if (href_list["add_c"])
+ else if(href_list["add_c"])
if(!(active2 in data_core.medical))
return
var/a2 = src.active2
- var/t1 = copytext(sanitize(input("Add Comment:", "Med. records", null, null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( src.authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || src.active2 != a2))
+ var/t1 = stripped_multiline_input("Add Comment:", "Med. records", null, null)
+ if(!canUseMedicalRecordsConsole(usr, t1, null, a2))
return
var/counter = 1
while(src.active2.fields[text("com_[]", counter)])
counter++
src.active2.fields[text("com_[]", counter)] = text("Made by [] ([]) on [] [], []
[]", src.authenticated, src.rank, worldtime2text(), time2text(world.realtime, "MMM DD"), year_integer+540, t1,)
- else if (href_list["del_c"])
- if ((istype(src.active2, /datum/data/record) && src.active2.fields[text("com_[]", href_list["del_c"])]))
+ else if(href_list["del_c"])
+ if((istype(src.active2, /datum/data/record) && src.active2.fields[text("com_[]", href_list["del_c"])]))
src.active2.fields[text("com_[]", href_list["del_c"])] = "Deleted"
- else if (href_list["search"])
+ else if(href_list["search"])
var/t1 = stripped_input(usr, "Search String: (Name, DNA, or ID)", "Med. records")
- if ((!( t1 ) || usr.stat || !( src.authenticated ) || usr.restrained() || ((!in_range(src, usr)) && (!istype(usr, /mob/living/silicon)))))
+ if(!canUseMedicalRecordsConsole(usr, t1))
return
src.active1 = null
src.active2 = null
t1 = lowertext(t1)
for(var/datum/data/record/R in data_core.medical)
- if ((lowertext(R.fields["name"]) == t1 || t1 == lowertext(R.fields["id"]) || t1 == lowertext(R.fields["b_dna"])))
+ if((lowertext(R.fields["name"]) == t1 || t1 == lowertext(R.fields["id"]) || t1 == lowertext(R.fields["b_dna"])))
src.active2 = R
else
//Foreach continue //goto(3229)
- if (!( src.active2 ))
+ if(!( src.active2 ))
src.temp = text("Could not locate record [].", t1)
else
for(var/datum/data/record/E in data_core.general)
- if ((E.fields["name"] == src.active2.fields["name"] || E.fields["id"] == src.active2.fields["id"]))
+ if((E.fields["name"] == src.active2.fields["name"] || E.fields["id"] == src.active2.fields["id"]))
src.active1 = E
else
//Foreach continue //goto(3334)
src.screen = 4
- else if (href_list["print_p"])
- if (!( src.printing ))
+ else if(href_list["print_p"])
+ if(!( src.printing ))
src.printing = 1
data_core.medicalPrintCount++
playsound(loc, 'sound/items/poster_being_created.ogg', 100, 1)
@@ -497,7 +526,10 @@
var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( src.loc )
P.info = "Medical Record - (MR-[data_core.medicalPrintCount])
"
if(active1 in data_core.general)
- P.info += text("Name: [] ID: []
\nSex: []
\nAge: []
\nFingerprint: []
\nPhysical Status: []
\nMental Status: []
", src.active1.fields["name"], src.active1.fields["id"], src.active1.fields["sex"], src.active1.fields["age"], src.active1.fields["fingerprint"], src.active1.fields["p_stat"], src.active1.fields["m_stat"])
+ P.info += text("Name: [] ID: []
\nSex: []
\nAge: []
", src.active1.fields["name"], src.active1.fields["id"], src.active1.fields["sex"], src.active1.fields["age"])
+ if(config.mutant_races)
+ P.info += "\nSpecies: [active1.fields["species"]]
"
+ P.info += text("\nFingerprint: []
\nPhysical Status: []
\nMental Status: []
", src.active1.fields["fingerprint"], src.active1.fields["p_stat"], src.active1.fields["m_stat"])
else
P.info += "General Record Lost!
"
if(active2 in data_core.medical)
@@ -545,6 +577,15 @@
..(severity)
+/obj/machinery/computer/med_data/proc/canUseMedicalRecordsConsole(mob/user, message = 1, record1, record2)
+ if(user)
+ if(message)
+ if(authenticated)
+ if(user.canUseTopic(src))
+ if(!record1 || record1 == active1)
+ if(!record2 || record2 == active2)
+ return 1
+ return 0
/obj/machinery/computer/med_data/laptop
name = "medical laptop"
diff --git a/code/game/machinery/computer/security.dm b/code/game/machinery/computer/security.dm
index 6b4d124790fd295..480c87c596588d0 100644
--- a/code/game/machinery/computer/security.dm
+++ b/code/game/machinery/computer/security.dm
@@ -36,16 +36,16 @@
/obj/machinery/computer/secure_data/attack_hand(mob/user as mob)
if(..())
return
- if (src.z > 6)
+ if(src.z > 6)
user << "Unable to establish a connection: \black You're too far away from the station!"
return
var/dat
- if (temp)
+ if(temp)
dat = text("[]
Clear Screen", temp, src)
else
dat = text("Confirm Identity: []
", src, (scan ? text("[]", scan.name) : "----------"))
- if (authenticated)
+ if(authenticated)
switch(screen)
if(1.0)
@@ -122,7 +122,7 @@
for(var/datum/data/record/R in sortRecord(data_core.general, sortBy, order))
var/crimstat = ""
for(var/datum/data/record/E in data_core.security)
- if ((E.fields["name"] == R.fields["name"]) && (E.fields["id"] == R.fields["id"]))
+ if((E.fields["name"] == R.fields["name"]) && (E.fields["id"] == R.fields["id"]))
crimstat = E.fields["criminal"]
var/background
switch(crimstat)
@@ -159,21 +159,34 @@
dat += "
Delete All Records
Back"
if(3.0)
dat += "Security Record
"
- if ((istype(active1, /datum/data/record) && data_core.general.Find(active1)))
- dat += {"
+ if(istype(active1, /datum/data/record) && data_core.general.Find(active1))
+ if(istype(active1.fields["photo_front"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P1 = active1.fields["photo_front"]
+ user << browse_rsc(P1.img, "photo_front")
+ if(istype(active1.fields["photo_side"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P2 = active1.fields["photo_side"]
+ user << browse_rsc(P2.img, "photo_side")
+ dat += {"
+
+ |
"}
else
- dat += "General Record Lost!
"
- if ((istype(active2, /datum/data/record) && data_core.security.Find(active2)))
- dat += "
Security Data"
+ dat += "
General Record Lost!
"
+ if((istype(active2, /datum/data/record) && data_core.security.Find(active2)))
+ dat += "Security Data"
dat += "
Criminal Status: [active2.fields["criminal"]]"
dat += "
Minor Crimes: Add New"
@@ -244,13 +257,14 @@
I can't be bothered to look more of the actual code outside of switch but that probably needs revising too.
What a mess.*/
/obj/machinery/computer/secure_data/Topic(href, href_list)
- if(..())
- return
- if (!( data_core.general.Find(active1) ))
+ . = ..()
+ if(.)
+ return .
+ if(!( data_core.general.Find(active1) ))
active1 = null
- if (!( data_core.security.Find(active2) ))
+ if(!( data_core.security.Find(active2) ))
active2 = null
- if ((usr.contents.Find(src) || (in_range(src, usr) && istype(loc, /turf))) || (istype(usr, /mob/living/silicon)))
+ if((usr.contents.Find(src) || (in_range(src, usr) && istype(loc, /turf))) || (istype(usr, /mob/living/silicon)))
usr.set_machine(src)
switch(href_list["choice"])
// SORTING!
@@ -269,13 +283,13 @@ What a mess.*/
if("Clear Screen")
temp = null
- if ("Return")
+ if("Return")
screen = 1
active1 = null
active2 = null
if("Confirm Identity")
- if (scan)
+ if(scan)
if(istype(usr,/mob/living/carbon/human) && !usr.get_active_hand())
usr.put_in_hands(scan)
else
@@ -283,7 +297,7 @@ What a mess.*/
scan = null
else
var/obj/item/I = usr.get_active_hand()
- if (istype(I, /obj/item/weapon/card/id))
+ if(istype(I, /obj/item/weapon/card/id))
usr.drop_item()
I.loc = src
scan = I
@@ -295,14 +309,14 @@ What a mess.*/
active2 = null
if("Log In")
- if (istype(usr, /mob/living/silicon))
+ if(istype(usr, /mob/living/silicon))
var/mob/living/silicon/borg = usr
active1 = null
active2 = null
authenticated = borg.name
rank = "AI"
screen = 1
- else if (istype(scan, /obj/item/weapon/card/id))
+ else if(istype(scan, /obj/item/weapon/card/id))
active1 = null
active2 = null
if(check_access(scan))
@@ -315,50 +329,53 @@ What a mess.*/
active1 = null
active2 = null
- if ("Browse Record")
+ if("Browse Record")
var/datum/data/record/R = locate(href_list["d_rec"])
var/S = locate(href_list["d_rec"])
- if (!( data_core.general.Find(R) ))
+ if(!( data_core.general.Find(R) ))
temp = "Record Not Found!"
else
for(var/datum/data/record/E in data_core.security)
- if ((E.fields["name"] == R.fields["name"] || E.fields["id"] == R.fields["id"]))
+ if((E.fields["name"] == R.fields["name"] || E.fields["id"] == R.fields["id"]))
S = E
active1 = R
active2 = S
screen = 3
-/* if ("Search Fingerprints")
+/* if("Search Fingerprints")
var/t1 = input("Search String: (Fingerprint)", "Secure. records", null, null) as text
- if ((!( t1 ) || usr.stat || !( authenticated ) || usr.restrained() || (!in_range(src, usr)) && (!istype(usr, /mob/living/silicon))))
+ if((!( t1 ) || usr.stat || !( authenticated ) || usr.restrained() || (!in_range(src, usr)) && (!istype(usr, /mob/living/silicon))))
return
active1 = null
active2 = null
t1 = lowertext(t1)
for(var/datum/data/record/R in data_core.general)
- if (lowertext(R.fields["fingerprint"]) == t1)
+ if(lowertext(R.fields["fingerprint"]) == t1)
active1 = R
- if (!( active1 ))
+ if(!( active1 ))
temp = text("Could not locate record [].", t1)
else
for(var/datum/data/record/E in data_core.security)
- if ((E.fields["name"] == active1.fields["name"] || E.fields["id"] == active1.fields["id"]))
+ if((E.fields["name"] == active1.fields["name"] || E.fields["id"] == active1.fields["id"]))
active2 = E
screen = 3 */
- if ("Print Record")
- if (!( printing ))
+ if("Print Record")
+ if(!( printing ))
printing = 1
data_core.securityPrintCount++
playsound(loc, 'sound/items/poster_being_created.ogg', 100, 1)
sleep(30)
var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( loc )
P.info = "Security Record - (SR-[data_core.securityPrintCount])
"
- if ((istype(active1, /datum/data/record) && data_core.general.Find(active1)))
- P.info += text("Name: [] ID: []
\nSex: []
\nAge: []
\nFingerprint: []
\nPhysical Status: []
\nMental Status: []
", active1.fields["name"], active1.fields["id"], active1.fields["sex"], active1.fields["age"], active1.fields["fingerprint"], active1.fields["p_stat"], active1.fields["m_stat"])
+ if((istype(active1, /datum/data/record) && data_core.general.Find(active1)))
+ P.info += text("Name: [] ID: []
\nSex: []
\nAge: []
", active1.fields["name"], active1.fields["id"], active1.fields["sex"], active1.fields["age"])
+ if(config.mutant_races)
+ P.info += "\nSpecies: [active1.fields["species"]]
"
+ P.info += text("\nFingerprint: []
\nPhysical Status: []
\nMental Status: []
", active1.fields["fingerprint"], active1.fields["p_stat"], active1.fields["m_stat"])
else
P.info += "General Record Lost!
"
- if ((istype(active2, /datum/data/record) && data_core.security.Find(active2)))
+ if((istype(active2, /datum/data/record) && data_core.security.Find(active2)))
P.info += text("
\nSecurity Data
\nCriminal Status: []", active2.fields["criminal"])
P.info += "
\n
\nMinor Crimes:
\n"
@@ -406,49 +423,49 @@ What a mess.*/
P.info += ""
printing = null
//RECORD DELETE
- if ("Delete All Records")
+ if("Delete All Records")
temp = ""
temp += "Are you sure you wish to delete all Security records?
"
temp += "Yes
"
temp += "No"
- if ("Purge All Records")
+ if("Purge All Records")
investigate_log("[usr.name] ([usr.key]) has purged all the security records.", "records")
for(var/datum/data/record/R in data_core.security)
del(R)
data_core.security.Cut()
temp = "All Security records deleted."
- if ("Add Entry")
- if (!( istype(active2, /datum/data/record) ))
+ if("Add Entry")
+ if(!( istype(active2, /datum/data/record) ))
return
var/a2 = active2
- var/t1 = copytext(sanitize(input("Add Comment:", "Secure. records", null, null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ var/t1 = stripped_multiline_input("Add Comment:", "Secure. records", null, null)
+ if(!canUseSecurityRecordsConsole(t1, usr, null, a2))
return
var/counter = 1
while(active2.fields[text("com_[]", counter)])
counter++
active2.fields[text("com_[]", counter)] = text("Made by [] ([]) on [] [], []
[]", src.authenticated, src.rank, worldtime2text(), time2text(world.realtime, "MMM DD"), year_integer+540, t1,)
- if ("Delete Record (ALL)")
- if (active1)
+ if("Delete Record (ALL)")
+ if(active1)
temp = "Are you sure you wish to delete the record (ALL)?
"
temp += "Yes
"
temp += "No"
- if ("Delete Record (Security)")
- if (active2)
+ if("Delete Record (Security)")
+ if(active2)
temp = "Are you sure you wish to delete the record (Security Portion Only)?
"
temp += "Yes
"
temp += "No"
- if ("Delete Entry")
- if ((istype(active2, /datum/data/record) && active2.fields[text("com_[]", href_list["del_c"])]))
+ if("Delete Entry")
+ if((istype(active2, /datum/data/record) && active2.fields[text("com_[]", href_list["del_c"])]))
active2.fields[text("com_[]", href_list["del_c"])] = "Deleted"
//RECORD CREATE
- if ("New Record (Security)")
- if ((istype(active1, /datum/data/record) && !( istype(active2, /datum/data/record) )))
+ if("New Record (Security)")
+ if((istype(active1, /datum/data/record) && !( istype(active2, /datum/data/record) )))
var/datum/data/record/R = new /datum/data/record()
R.fields["name"] = active1.fields["name"]
R.fields["id"] = active1.fields["id"]
@@ -461,7 +478,7 @@ What a mess.*/
active2 = R
screen = 3
- if ("New Record (General)")
+ if("New Record (General)")
//General Record
var/datum/data/record/G = new /datum/data/record()
G.fields["name"] = "New Record"
@@ -469,6 +486,10 @@ What a mess.*/
G.fields["rank"] = "Unassigned"
G.fields["sex"] = "Male"
G.fields["age"] = "Unknown"
+ if(config.mutant_races)
+ G.fields["species"] = "Human"
+ G.fields["photo_front"] = new /icon()
+ G.fields["photo_side"] = new /icon()
G.fields["fingerprint"] = "?????"
G.fields["p_stat"] = "Active"
G.fields["m_stat"] = "Stable"
@@ -507,15 +528,15 @@ What a mess.*/
//FIELD FUNCTIONS
- if ("Edit Field")
+ if("Edit Field")
var/a1 = active1
var/a2 = active2
switch(href_list["field"])
if("name")
- if (istype(active1, /datum/data/record) || istype(active2, /datum/data/record))
+ if(istype(active1, /datum/data/record) || istype(active2, /datum/data/record))
var/t1 = stripped_input(usr, "Please input name:", "Secure. records", active1.fields["name"], null)
- if ((!( t1 ) || !length(trim(t1)) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon)))) || active1 != a1)
+ if(!canUseSecurityRecordsConsole(usr, t1, null, a1))
return
if(istype(active1, /datum/data/record))
active1.fields["name"] = t1
@@ -523,67 +544,93 @@ What a mess.*/
active2.fields["name"] = t1
if("id")
if(istype(active2,/datum/data/record) || istype(active1,/datum/data/record))
- var/t1 = copytext(sanitize(input("Please input id:", "Secure. records", active1.fields["id"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active1 != a1))
+ var/t1 = stripped_input(usr, "Please input id:", "Secure. records", active1.fields["id"], null)
+ if(!canUseSecurityRecordsConsole(usr, t1, null, a1))
return
if(istype(active1,/datum/data/record))
active1.fields["id"] = t1
if(istype(active2,/datum/data/record))
active2.fields["id"] = t1
if("fingerprint")
- if (istype(active1, /datum/data/record))
- var/t1 = copytext(sanitize(input("Please input fingerprint hash:", "Secure. records", active1.fields["fingerprint"], null) as text),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active1 != a1))
+ if(istype(active1, /datum/data/record))
+ var/t1 = stripped_input(usr, "Please input fingerprint hash:", "Secure. records", active1.fields["fingerprint"], null)
+ if(!canUseSecurityRecordsConsole(usr, t1, null, a1))
return
active1.fields["fingerprint"] = t1
if("sex")
- if (istype(active1, /datum/data/record))
- if (active1.fields["sex"] == "Male")
+ if(istype(active1, /datum/data/record))
+ if(active1.fields["sex"] == "Male")
active1.fields["sex"] = "Female"
else
active1.fields["sex"] = "Male"
if("age")
- if (istype(active1, /datum/data/record))
- var/t1 = input("Please input age:", "Secure. records", active1.fields["age"], null) as num
- if ((!( t1 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active1 != a1))
+ if(istype(active1, /datum/data/record))
+ var/t1 = input("Please input age:", "Secure. records", active1.fields["age"], null) as num
+ if(!canUseSecurityRecordsConsole(usr, null, null, a1) || !t1)
return
active1.fields["age"] = t1
+ if("species")
+ if(istype(active1, /datum/data/record))
+ var/t1 = input("Select a species", "Species Selection") as null|anything in roundstart_species
+ if(!canUseSecurityRecordsConsole(usr, t1, null, a1))
+ return
+ active1.fields["species"] = t1
+ if("show_photo_front")
+ if(active1.fields["photo_front"])
+ if(istype(active1.fields["photo_front"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P = active1.fields["photo_front"]
+ P.show(usr)
+ if("upd_photo_front")
+ var/icon/photo = get_photo(usr)
+ if(photo)
+ qdel(active1.fields["photo_front"])
+ active1.fields["photo_front"] = photo
+ if("show_photo_side")
+ if(active1.fields["photo_side"])
+ if(istype(active1.fields["photo_side"], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/P = active1.fields["photo_side"]
+ P.show(usr)
+ if("upd_photo_side")
+ var/icon/photo = get_photo(usr)
+ if(photo)
+ qdel(active1.fields["photo_side"])
+ active1.fields["photo_side"] = photo
if("mi_crim_add")
- if (istype(active1, /datum/data/record))
- var/t1 = copytext(sanitize(input("Please input minor crime names:", "Secure. records", "", null) as text),1,MAX_MESSAGE_LEN)
- var/t2 = copytext(sanitize(input("Please input minor crime details:", "Secure. records", "", null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( t2 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ if(istype(active1, /datum/data/record))
+ var/t1 = stripped_input(usr, "Please input minor crime names:", "Secure. records", "", null)
+ var/t2 = stripped_multiline_input(usr, "Please input minor crime details:", "Secure. records", "", null)
+ if(!canUseSecurityRecordsConsole(usr, t1, t2, null, a2))
return
var/crime = data_core.createCrimeEntry(t1, t2, authenticated, worldtime2text())
data_core.addMinorCrime(active1.fields["id"], crime)
if("mi_crim_delete")
- if (istype(active1, /datum/data/record))
- if (href_list["cdataid"])
- if ((!( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ if(istype(active1, /datum/data/record))
+ if(href_list["cdataid"])
+ if(!canUseSecurityRecordsConsole(usr, null, null, a2))
return
data_core.removeMinorCrime(active1.fields["id"], href_list["cdataid"])
if("ma_crim_add")
- if (istype(active1, /datum/data/record))
- var/t1 = copytext(sanitize(input("Please input major crime names:", "Secure. records", "", null) as text),1,MAX_MESSAGE_LEN)
- var/t2 = copytext(sanitize(input("Please input major crime details:", "Secure. records", "", null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( t2 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ if(istype(active1, /datum/data/record))
+ var/t1 = stripped_input(usr, "Please input major crime names:", "Secure. records", "", null)
+ var/t2 = stripped_multiline_input(usr, "Please input major crime details:", "Secure. records", "", null)
+ if(!canUseSecurityRecordsConsole(usr, t1, t2, a2))
return
var/crime = data_core.createCrimeEntry(t1, t2, authenticated, worldtime2text())
data_core.addMajorCrime(active1.fields["id"], crime)
if("ma_crim_delete")
- if (istype(active1, /datum/data/record))
- if (href_list["cdataid"])
- if ((!( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ if(istype(active1, /datum/data/record))
+ if(href_list["cdataid"])
+ if(!canUseSecurityRecordsConsole(usr, null, null, a2))
return
data_core.removeMajorCrime(active1.fields["id"], href_list["cdataid"])
if("notes")
- if (istype(active2, /datum/data/record))
- var/t1 = copytext(sanitize(input("Please summarize notes:", "Secure. records", active2.fields["notes"], null) as message),1,MAX_MESSAGE_LEN)
- if ((!( t1 ) || !( authenticated ) || usr.stat || usr.restrained() || (!in_range(src, usr) && (!istype(usr, /mob/living/silicon))) || active2 != a2))
+ if(istype(active2, /datum/data/record))
+ var/t1 = stripped_input(usr, "Please summarize notes:", "Secure. records", active2.fields["notes"], null)
+ if(!canUseSecurityRecordsConsole(usr, t1, null, a2))
return
active2.fields["notes"] = t1
if("criminal")
- if (istype(active2, /datum/data/record))
+ if(istype(active2, /datum/data/record))
temp = "Criminal Status:
"
temp += ""
temp += "- None
"
@@ -595,7 +642,7 @@ What a mess.*/
if("rank")
var/list/L = list( "Head of Personnel", "Captain", "AI" )
//This was so silly before the change. Now it actually works without beating your head against the keyboard. /N
- if ((istype(active1, /datum/data/record) && L.Find(rank)))
+ if((istype(active1, /datum/data/record) && L.Find(rank)))
temp = "Rank:
"
temp += ""
for(var/rank in get_all_jobs())
@@ -607,14 +654,14 @@ What a mess.*/
else//To properly clear as per clear screen.
temp=null
switch(href_list["choice"])
- if ("Change Rank")
- if (active1)
+ if("Change Rank")
+ if(active1)
active1.fields["rank"] = href_list["rank"]
if(href_list["rank"] in get_all_jobs())
active1.fields["real_rank"] = href_list["real_rank"]
- if ("Change Criminal Status")
- if (active2)
+ if("Change Criminal Status")
+ if(active2)
var/old_field = active2.fields["criminal"]
switch(href_list["criminal2"])
if("none")
@@ -630,24 +677,24 @@ What a mess.*/
investigate_log("[active1.fields["name"]] has been set from [old_field] to [active2.fields["criminal"]] by [usr.name] ([usr.key]).", "records")
for(var/mob/living/carbon/human/H in mob_list) //thanks for forcing me to do this, whoever wrote this shitty records system
H.sec_hud_set_security_status()
- if ("Delete Record (Security) Execute")
+ if("Delete Record (Security) Execute")
investigate_log("[usr.name] ([usr.key]) has deleted the security records for [active1.fields["name"]].", "records")
- if (active2)
+ if(active2)
data_core.security -= active2
del(active2)
- if ("Delete Record (ALL) Execute")
- if (active1)
+ if("Delete Record (ALL) Execute")
+ if(active1)
investigate_log("[usr.name] ([usr.key]) has deleted all records for [active1.fields["name"]].", "records")
for(var/datum/data/record/R in data_core.medical)
- if ((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
+ if((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
data_core.medical -= R
del(R)
break
data_core.general -= active1
del(active1)
- if (active2)
+ if(active2)
data_core.security -= active2
del(active2)
else
@@ -657,6 +704,18 @@ What a mess.*/
updateUsrDialog()
return
+/obj/machinery/computer/secure_data/proc/get_photo(var/mob/user)
+ var/obj/item/weapon/photo/P = null
+ if(istype(user, /mob/living/silicon))
+ var/mob/living/silicon/tempAI = user
+ var/datum/picture/selection = tempAI.GetPhoto()
+ if(selection)
+ P = new()
+ P.photocreate(selection.fields["icon"], selection.fields["img"], selection.fields["desc"])
+ else if(istype(user.get_active_hand(), /obj/item/weapon/photo))
+ P = user.get_active_hand()
+ return P
+
/obj/machinery/computer/secure_data/emp_act(severity)
if(stat & (BROKEN|NOPOWER))
..(severity)
@@ -664,11 +723,11 @@ What a mess.*/
for(var/datum/data/record/R in data_core.security)
if(prob(10/severity))
- switch(rand(1,6))
+ switch(rand(1,8))
if(1)
R.fields["name"] = "[pick(pick(first_names_male), pick(first_names_female))] [pick(last_names)]"
if(2)
- R.fields["sex"] = pick("Male", "Female")
+ R.fields["sex"] = pick("Male", "Female")
if(3)
R.fields["age"] = rand(5, 85)
if(4)
@@ -677,6 +736,12 @@ What a mess.*/
R.fields["p_stat"] = pick("*Unconcious*", "Active", "Physically Unfit")
if(6)
R.fields["m_stat"] = pick("*Insane*", "*Unstable*", "*Watch*", "Stable")
+ if(7)
+ R.fields["species"] = pick(roundstart_species)
+ if(8)
+ var/datum/data/record/G = pick(data_core.general)
+ R.fields["photo_front"] = G.fields["photo_front"]
+ R.fields["photo_side"] = G.fields["photo_side"]
continue
else if(prob(1))
@@ -685,6 +750,17 @@ What a mess.*/
..(severity)
+/obj/machinery/computer/secure_data/proc/canUseSecurityRecordsConsole(mob/user, message1 = 1, message2 = 1, record1, record2)
+ if(user)
+ if(trim(message1))
+ if(trim(message2))
+ if(authenticated)
+ if(user.canUseTopic(src))
+ if(!record1 || record1 == active1)
+ if(!record2 || record2 == active2)
+ return 1
+ return 0
+
/obj/machinery/computer/secure_data/detective_computer
icon = 'icons/obj/computer.dmi'
icon_state = "messyfiles"
diff --git a/code/game/machinery/cryo.dm b/code/game/machinery/cryo.dm
index d90968524f07ed8..b0f83365b214d9f 100644
--- a/code/game/machinery/cryo.dm
+++ b/code/game/machinery/cryo.dm
@@ -84,12 +84,26 @@
open_machine()
/obj/machinery/atmospherics/unary/cryo_cell/container_resist()
- if(stat & DEAD)
- return
- sleep(usr.stat * 1200)
open_machine()
return
+/obj/machinery/atmospherics/unary/cryo_cell/verb/move_eject()
+ set name = "Eject Cryo Cell"
+ set desc = "Begin the release sequence inside the cryo tube."
+ set category = "Object"
+ set src in oview(1)
+ if(usr == occupant || contents.Find(usr)) //If the user is inside the tube...
+ if(usr.stat == DEAD) //and he's not dead....
+ return
+ usr << "Release sequence activated. This will take about a minute."
+ sleep(600)
+ if(!src || !usr || (!occupant && !contents.Find(usr))) //Check if someone's released/replaced/bombed him already
+ return
+ open_machine()
+ add_fingerprint(usr)
+ else
+ open_machine()
+
/obj/machinery/atmospherics/unary/cryo_cell/examine(mob/user)
..()
diff --git a/code/game/machinery/vending.dm b/code/game/machinery/vending.dm
index eb030504a43284c..deca054d322f2ee 100644
--- a/code/game/machinery/vending.dm
+++ b/code/game/machinery/vending.dm
@@ -151,14 +151,14 @@
if(istype(W, /obj/item/weapon/reagent_containers/food/snacks))
if(!compartment_access_check(user))
return
- if(nosugar_check(W))
+ if(junk_check(W))
if(!iscompartmentfull(user))
user.drop_item()
W.loc = src
food_load(W)
user << "You insert [W] into [src]'s chef compartment."
else
- user << "[src]'s chef compartment does not accept sugary food."
+ user << "[src]'s chef compartment does not accept junk food."
return
if(istype(W, /obj/item/weapon/storage/bag/tray))
@@ -170,7 +170,7 @@
for(var/obj/item/weapon/reagent_containers/food/snacks/S in T.contents)
if(iscompartmentfull(user))
break
- if(nosugar_check(S))
+ if(junk_check(S))
T.remove_from_storage(S, src)
food_load(S)
loaded++
@@ -194,8 +194,8 @@
req_access_txt = "0"
return 1
-/obj/machinery/vending/snack/proc/nosugar_check(obj/item/weapon/W)
- if(W.reagents.has_reagent("sugar"))
+/obj/machinery/vending/snack/proc/junk_check(obj/item/weapon/reagent_containers/food/snacks/S)
+ if(S.junkiness)
return 0
return 1
@@ -889,7 +889,7 @@
desc = "A kitchen and restaurant equipment vendor"
product_ads = "Mm, food stuffs!;Food and food accessories.;Get your plates!;You like forks?;I like forks.;Woo, utensils.;You don't really need these..."
icon_state = "dinnerware"
- products = list(/obj/item/weapon/storage/bag/tray = 8,/obj/item/weapon/kitchen/utensil/fork = 6,/obj/item/weapon/kitchenknife = 3,/obj/item/weapon/reagent_containers/food/drinks/drinkingglass = 8,/obj/item/clothing/suit/apron/chef = 2,/obj/item/weapon/reagent_containers/food/condiment/pack/ketchup = 5,/obj/item/weapon/reagent_containers/food/condiment/pack/hotsauce = 5)
+ products = list(/obj/item/weapon/storage/bag/tray = 8,/obj/item/weapon/kitchen/utensil/fork = 6,/obj/item/weapon/kitchenknife = 3,/obj/item/weapon/reagent_containers/food/drinks/drinkingglass = 8,/obj/item/clothing/suit/apron/chef = 2,/obj/item/weapon/reagent_containers/food/condiment/pack/ketchup = 5,/obj/item/weapon/reagent_containers/food/condiment/pack/hotsauce = 5,/obj/item/weapon/reagent_containers/glass/bowl = 10)
contraband = list(/obj/item/weapon/kitchen/rollingpin = 2, /obj/item/weapon/kitchenknife/butcher = 2)
/obj/machinery/vending/sovietsoda
diff --git a/code/game/objects/items/stacks/rods.dm b/code/game/objects/items/stacks/rods.dm
index f3ad7db4378f8b8..379ce34d2cd73c2 100644
--- a/code/game/objects/items/stacks/rods.dm
+++ b/code/game/objects/items/stacks/rods.dm
@@ -8,7 +8,6 @@ var/global/list/datum/stack_recipe/rod_recipes = list ( \
desc = "Some rods. Can be used for building, or something."
singular_name = "metal rod"
icon_state = "rods"
- item_state = "rods"
flags = CONDUCT
w_class = 3.0
force = 9.0
@@ -32,7 +31,6 @@ var/global/list/datum/stack_recipe/rod_recipes = list ( \
icon_state = "rods"
/obj/item/stack/rods/attackby(obj/item/W as obj, mob/user as mob)
- ..()
if (istype(W, /obj/item/weapon/weldingtool))
var/obj/item/weapon/weldingtool/WT = W
@@ -53,6 +51,17 @@ var/global/list/datum/stack_recipe/rod_recipes = list ( \
if (!R && replace)
user.put_in_hands(new_item)
return
+
+ if(istype(W,/obj/item/weapon/reagent_containers/food/snacks))
+ var/obj/item/weapon/reagent_containers/food/snacks/S = W
+ if(amount != 1)
+ user << "You must use a single rod."
+ else if(S.w_class > 2)
+ user << "The ingredient is too big for [src]."
+ else
+ var/obj/item/weapon/reagent_containers/food/snacks/customizable/A = new/obj/item/weapon/reagent_containers/food/snacks/customizable/kebab(get_turf(src))
+ A.initialize_custom_food(src, S, user)
+ return
..()
/obj/item/stack/rods/cyborg/
diff --git a/code/game/objects/items/trash.dm b/code/game/objects/items/trash.dm
index 12911c16baa7dfd..da2e082ca486749 100644
--- a/code/game/objects/items/trash.dm
+++ b/code/game/objects/items/trash.dm
@@ -40,10 +40,6 @@
name = "plate"
icon_state = "plate"
-/obj/item/trash/snack_bowl
- name = "snack bowl"
- icon_state = "snack_bowl"
-
/obj/item/trash/pistachios
name = "pistachios pack"
icon_state = "pistachios_pack"
diff --git a/code/game/objects/items/weapons/grenades/chem_grenade.dm b/code/game/objects/items/weapons/grenades/chem_grenade.dm
index 2098d686ea9216c..ac865a96dc51d51 100644
--- a/code/game/objects/items/weapons/grenades/chem_grenade.dm
+++ b/code/game/objects/items/weapons/grenades/chem_grenade.dm
@@ -203,8 +203,11 @@
qdel(src) //correctly before deleting the grenade.
/obj/item/weapon/grenade/chem_grenade/proc/mix_reagents()
+ var/total_temp
for(var/obj/item/weapon/reagent_containers/glass/G in beakers)
G.reagents.trans_to(src, G.reagents.total_volume)
+ total_temp += G.reagents.chem_temp
+ reagents.chem_temp = total_temp
/obj/item/weapon/grenade/chem_grenade/proc/can_flood_from(myloc, maxrange)
var/list/reachable = list(myloc)
diff --git a/code/game/objects/items/weapons/manuals.dm b/code/game/objects/items/weapons/manuals.dm
index d39fbf35fc79ef2..75d7957007e38ef 100644
--- a/code/game/objects/items/weapons/manuals.dm
+++ b/code/game/objects/items/weapons/manuals.dm
@@ -677,33 +677,56 @@
Food for Dummies
Here is a guide on basic food recipes and also how to not poison your customers accidentally.
- Burger:
- Put 1 meat and 1 flour into the microwave and turn it on. Then wait.
-
- Bread:
- Put 3 flour into the microwave and then wait.
-
- Waffles:
- Add 2 flour and 2 egg to the microwave and then wait.
-
- Popcorn:
- Add 1 corn to the microwave and wait.
-
- Meat Steak:
- Put 1 meat, 1 unit of salt and 1 unit of pepper into the microwave and wait.
-
- Meat Pie:
- Put 1 meat and 2 flour into the microwave and wait.
-
- Boiled Spagetti:
- Put 1 spagetti and 5 units of water into the microwave and wait.
-
- Donuts:
- Add 1 egg and 1 flour to the microwave and wait.
-
- Fries:
- Add one potato to the processor and wait.
+ Basic ingredients preparation:
+
+ Dough: Add an egg to 15 flour. Dough can be transformed by using your knife and rolling pin or by adding milk. All doughs can be microwaved.
+ Bowl: Add water to it for soup preparation.
+ Meat: Microwave it, process it, slice it into microwavable cutlets with your knife, or use it raw.
+ Cheese: Add 5u universal enzyme (catalyst) to milk and soy milk to prepare cheese (sliceable) and tofu.
+
+ Custom food:
+ Add ingredients to a base item to prepare a custom meal.
+ The bases are:
+ - bun (burger)
+ - breadslices(sandwich)
+ - plain bread
+ - plain pie
+ - vanilla cake
+ - empty bowl (salad)
+ - bowl with 10u water (soup)
+ - boiled spaghetti
+ - pizza bread
+ - metal rod (kebab)
+
+ Table Craft:
+ Put ingredients on table, then click and drag the table onto yourself to prepare recipes.
+
+ Microwave:
+ Use it to cook or boil food ingredients (meats, doughs, egg, spaghetti, donkpocket, etc...).
+ It can cook multiple items at once. Use the higher power settings for faster (and riskier) cooking.
+
+ Processor:
+ Use it to process certain ingredients (meat into faggot, doughslice into spaghetti, potato into fries,etc...)
+
+ Gibber:
+ Stuff an animal in it to grind it into meat.
+
+ Meat spike:
+ Stick an animal on it then begin collecting its meat.
+
+
+ Example recipes:
+ Vanilla Cake: Microwave cake batter.
+ Burger: 1 bun + 1 meat
+ Bread: Microwave dough.
+ Waffles: 2 doughslices
+ Popcorn: Microwave corn.
+ Meat Steak: Microwave meat.
+ Meat Pie: 1 plain pie + 1u black pepper + 1u salt + 1 meat
+ Boiled Spagetti: Microwave spaghetti.
+ Donuts: 1u sugar + 1 doughslice
+ Fries: Process potato.