diff --git a/_maps/RandomRuins/StationRuins/GaxStation/ai_whale.dmm b/_maps/RandomRuins/StationRuins/GaxStation/ai_whale.dmm index ce59a7294f9b..cac1ade163c8 100644 --- a/_maps/RandomRuins/StationRuins/GaxStation/ai_whale.dmm +++ b/_maps/RandomRuins/StationRuins/GaxStation/ai_whale.dmm @@ -7,9 +7,6 @@ /turf/open/floor/plating, /area/tcommsat/computer) "aA" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 8 - }, /obj/machinery/computer/security/telescreen{ dir = 8; name = "MiniSat Camera Monitor"; @@ -2207,9 +2204,6 @@ dir = 8; pixel_x = 24 }, -/obj/machinery/computer/ai_control_console{ - dir = 8 - }, /turf/open/floor/plasteel/grimy, /area/ai_monitored/turret_protected/aisat_interior) "Um" = ( diff --git a/_maps/map_files/AsteroidStation/AsteroidStation.dmm b/_maps/map_files/AsteroidStation/AsteroidStation.dmm index b87e4733fcaf..b0c0a0b3c262 100644 --- a/_maps/map_files/AsteroidStation/AsteroidStation.dmm +++ b/_maps/map_files/AsteroidStation/AsteroidStation.dmm @@ -1247,9 +1247,6 @@ /turf/open/floor/plasteel, /area/security/checkpoint/medical) "akg" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 4 - }, /turf/open/floor/plasteel/dark, /area/science/server) "akh" = ( @@ -1797,9 +1794,6 @@ /turf/open/floor/plasteel/white, /area/medical/medbay/central) "aoX" = ( -/obj/machinery/computer/ai_control_console{ - dir = 1 - }, /turf/open/floor/plasteel/grimy, /area/ai_monitored/turret_protected/aisat_interior) "aoZ" = ( @@ -11020,7 +11014,6 @@ /area/quartermaster/miningdock) "cEO" = ( /obj/structure/closet/secure_closet/RD, -/obj/item/circuitboard/computer/ai_upload_download, /obj/effect/turf_decal/stripes/line{ dir = 1 }, @@ -27928,7 +27921,6 @@ /turf/open/floor/plasteel/white, /area/science/robotics/lab) "iCL" = ( -/obj/machinery/computer/ai_resource_distribution, /turf/open/floor/plasteel/grimy, /area/ai_monitored/turret_protected/aisat_interior) "iDy" = ( diff --git a/_maps/map_files/EclipseStation/EclipseStation.dmm b/_maps/map_files/EclipseStation/EclipseStation.dmm index 85baa543423e..05cd6fa2fd2d 100644 --- a/_maps/map_files/EclipseStation/EclipseStation.dmm +++ b/_maps/map_files/EclipseStation/EclipseStation.dmm @@ -45018,9 +45018,6 @@ /obj/structure/window/reinforced{ layer = 4.1 }, -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/turret_protected/ai_upload) "bOT" = ( @@ -59457,7 +59454,6 @@ /area/crew_quarters/heads/hor) "cto" = ( /obj/structure/rack, -/obj/item/circuitboard/computer/ai_upload_download, /obj/item/disk/holodisk/tutorial/AICore, /turf/open/floor/plasteel, /area/crew_quarters/heads/hor) @@ -86278,9 +86274,6 @@ /turf/open/floor/plasteel, /area/hallway/primary/fore) "nsA" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 4 - }, /obj/effect/decal/cleanable/dirt, /obj/effect/decal/cleanable/dirt, /turf/open/floor/carpet, @@ -90567,9 +90560,6 @@ /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 1 }, -/obj/machinery/computer/ai_control_console{ - dir = 1 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/turret_protected/ai_upload) "vat" = ( diff --git a/_maps/map_files/GaxStation/GaxStation.dmm b/_maps/map_files/GaxStation/GaxStation.dmm index 1a05c4860744..a6069d6ba8c6 100644 --- a/_maps/map_files/GaxStation/GaxStation.dmm +++ b/_maps/map_files/GaxStation/GaxStation.dmm @@ -65,7 +65,6 @@ /obj/structure/rack, /obj/item/aicard, /obj/item/disk/holodisk/tutorial/AICore, -/obj/item/circuitboard/computer/ai_upload_download, /obj/machinery/power/apc{ areastring = "/area/crew_quarters/heads/hor"; dir = 8; @@ -11060,9 +11059,6 @@ /turf/open/floor/plasteel, /area/security/main) "fvC" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 4 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/secondarydatacore) "fvG" = ( @@ -18753,9 +18749,6 @@ /obj/machinery/computer/robotics{ dir = 8 }, -/obj/structure/sign/plaques/ai_password{ - pixel_x = 32 - }, /turf/open/floor/carpet/exoticpurple, /area/crew_quarters/heads/hor) "jyN" = ( diff --git a/_maps/map_files/KiloStation/KiloStation.dmm b/_maps/map_files/KiloStation/KiloStation.dmm index ee44878a452e..625c5a105277 100644 --- a/_maps/map_files/KiloStation/KiloStation.dmm +++ b/_maps/map_files/KiloStation/KiloStation.dmm @@ -85994,7 +85994,6 @@ /obj/effect/turf_decal/tile/neutral, /obj/structure/table, /obj/item/hand_labeler, -/obj/item/circuitboard/computer/ai_upload_download, /turf/open/floor/plasteel/dark, /area/crew_quarters/heads/hor) "fMR" = ( @@ -91824,9 +91823,6 @@ dir = 8 }, /obj/effect/decal/cleanable/dirt, -/obj/machinery/computer/ai_resource_distribution{ - dir = 8 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/storage/satellite) "laJ" = ( @@ -92192,9 +92188,6 @@ dir = 1 }, /obj/effect/mapping_helpers/teleport_anchor, -/obj/structure/sign/plaques/ai_password{ - pixel_x = -32 - }, /turf/open/floor/plasteel/showroomfloor, /area/science/server) "lzb" = ( @@ -92215,9 +92208,6 @@ /obj/effect/turf_decal/tile/neutral{ dir = 8 }, -/obj/machinery/computer/ai_control_console{ - dir = 8 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/storage/satellite) "lBm" = ( diff --git a/_maps/map_files/Omegastation/omegastation.dmm b/_maps/map_files/Omegastation/omegastation.dmm index 416486332452..2d4ddd5f8ab0 100644 --- a/_maps/map_files/Omegastation/omegastation.dmm +++ b/_maps/map_files/Omegastation/omegastation.dmm @@ -43172,9 +43172,6 @@ /turf/open/floor/plasteel/white, /area/science/research) "tZB" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, /obj/effect/turf_decal/tile/neutral{ dir = 1 }, diff --git a/_maps/map_files/YogStation/YogStation.dmm b/_maps/map_files/YogStation/YogStation.dmm index fbaf4dfaa822..8fbec319fb4b 100644 --- a/_maps/map_files/YogStation/YogStation.dmm +++ b/_maps/map_files/YogStation/YogStation.dmm @@ -238,12 +238,6 @@ }, /turf/open/floor/plasteel, /area/security/prison) -"abx" = ( -/obj/effect/decal/cleanable/dirt/dust, -/obj/effect/decal/cleanable/dirt/dust, -/obj/machinery/ai/server_cabinet/prefilled, -/turf/open/floor/circuit/green/telecomms, -/area/ai_monitored/turret_protected/ai) "aby" = ( /obj/machinery/atmospherics/components/unary/portables_connector/visible{ dir = 8 @@ -1210,23 +1204,6 @@ }, /turf/open/floor/plasteel, /area/security/main) -"agz" = ( -/obj/machinery/light_switch{ - pixel_y = -27 - }, -/obj/machinery/airalarm{ - dir = 8; - pixel_x = 24 - }, -/obj/structure/rack, -/obj/item/multitool, -/obj/item/radio/off{ - pixel_y = 4 - }, -/obj/item/storage/toolbox/mechanical, -/obj/item/toy/talking/AI, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "agA" = ( /obj/machinery/holopad, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, @@ -3412,18 +3389,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) -"aue" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating{ - icon_state = "platingdmg3" - }, -/area/maintenance/starboard/aft) "auf" = ( /obj/machinery/firealarm{ dir = 4; @@ -3936,10 +3901,6 @@ }, /turf/open/floor/plasteel, /area/crew_quarters/dorms) -"axV" = ( -/mob/living/simple_animal/pet/axolotl/bop, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "ayd" = ( /obj/structure/disposalpipe/segment{ dir = 6 @@ -4173,13 +4134,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/fore) -"azq" = ( -/obj/structure/table/wood, -/obj/machinery/microwave{ - pixel_y = 4 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "azt" = ( /obj/machinery/power/terminal, /obj/structure/cable{ @@ -6075,6 +6029,18 @@ }, /turf/open/floor/plasteel/dark, /area/chapel/office) +"aJI" = ( +/obj/effect/turf_decal/stripes/end{ + dir = 8 + }, +/obj/machinery/light/small{ + dir = 8 + }, +/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "aJJ" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ dir = 4 @@ -6643,22 +6609,6 @@ }, /turf/open/floor/plating, /area/maintenance/starboard/aft) -"aMD" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/disposalpipe/segment{ - dir = 9 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/obj/structure/cable{ - icon_state = "1-8" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "aME" = ( /obj/machinery/atmospherics/components/binary/pump{ dir = 4; @@ -7804,15 +7754,6 @@ /obj/effect/turf_decal/bot, /turf/open/floor/plasteel, /area/vacant_room/commissary) -"aSy" = ( -/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ - dir = 4 - }, -/obj/structure/window/reinforced{ - dir = 8 - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "aSG" = ( /obj/structure/table, /obj/item/stack/sheet/glass/fifty, @@ -7849,12 +7790,6 @@ }, /turf/open/floor/plasteel, /area/security/prison) -"aSV" = ( -/obj/machinery/computer/ai_overclocking{ - dir = 1 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "aSX" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -8938,18 +8873,6 @@ }, /turf/open/floor/plasteel, /area/crew_quarters/fitness) -"baa" = ( -/obj/machinery/light{ - dir = 1 - }, -/obj/structure/cable/yellow{ - icon_state = "4-8" - }, -/obj/effect/turf_decal/trimline/yellow/filled/line{ - dir = 1 - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "bab" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/holopad, @@ -9661,6 +9584,12 @@ }, /turf/template_noop, /area/crew_quarters/dorms) +"bdW" = ( +/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ + dir = 8 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "bdX" = ( /obj/item/folder/blue, /obj/structure/table/wood, @@ -11305,6 +11234,19 @@ /obj/machinery/door/firedoor/border_only, /turf/open/floor/plasteel, /area/hallway/primary/central) +"bqP" = ( +/obj/machinery/power/apc/highcap/five_k{ + areastring = "/area/crew_quarters/public_lounge"; + name = "Public Lounge APC"; + pixel_y = -23 + }, +/obj/structure/cable{ + icon_state = "0-4" + }, +/obj/structure/table/wood, +/obj/machinery/microwave, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "bqV" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, @@ -12099,10 +12041,6 @@ /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2, /turf/open/floor/plasteel, /area/engine/foyer) -"bxL" = ( -/obj/machinery/rnd/production/circuit_imprinter/department/netmin, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "bxZ" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 9 @@ -12900,18 +12838,6 @@ "bCv" = ( /turf/closed/wall, /area/janitor) -"bCw" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "bCz" = ( /obj/machinery/vending/cigarette, /turf/open/floor/plasteel/dark, @@ -13207,6 +13133,15 @@ }, /turf/open/floor/plasteel, /area/clerk) +"bFQ" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ + dir = 4 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "bFR" = ( /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ dir = 8 @@ -13628,22 +13563,6 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) -"bKB" = ( -/obj/structure/closet/emcloset, -/obj/structure/sign/warning/electricshock{ - pixel_y = -32 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 9 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 9 - }, -/obj/structure/cable{ - icon_state = "1-8" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "bKG" = ( /obj/machinery/requests_console{ department = "EVA"; @@ -14066,6 +13985,18 @@ }, /turf/open/floor/plasteel, /area/storage/primary) +"bNZ" = ( +/obj/effect/decal/cleanable/dirt/dust, +/obj/effect/decal/cleanable/dirt/dust, +/obj/machinery/ai/networking{ + label = "Main Core"; + roundstart_connection = "Computer Science" + }, +/obj/structure/ethernet_cable{ + icon_state = "0-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "bOd" = ( /turf/open/floor/plasteel, /area/engine/atmos) @@ -14477,23 +14408,6 @@ /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, /area/medical/virology) -"bRR" = ( -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/obj/machinery/door/airlock/research/glass{ - name = "Secondary AI Core"; - normalspeed = 0; - req_access_txt = "47" - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "bSm" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ @@ -14538,6 +14452,19 @@ icon_state = "platingdmg3" }, /area/maintenance/aft) +"bSY" = ( +/obj/machinery/door/airlock/hatch{ + name = "Telecomms Tech Storage"; + req_access_txt = "61" + }, +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/obj/machinery/door/firedoor/border_only, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "bTc" = ( /obj/structure/extinguisher_cabinet{ pixel_y = 28 @@ -14735,9 +14662,6 @@ }, /turf/open/floor/plasteel/dark/telecomms, /area/tcommsat/server) -"bVJ" = ( -/turf/closed/wall/r_wall, -/area/tcommsat/computer) "bVS" = ( /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ dir = 1 @@ -15431,10 +15355,6 @@ }, /turf/open/floor/plating, /area/maintenance/starboard/fore) -"ceR" = ( -/obj/effect/landmark/blobstart, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "ceW" = ( /obj/structure/rack, /obj/effect/spawner/lootdrop/techstorage/RnD_secure, @@ -15827,6 +15747,10 @@ }, /turf/open/floor/plasteel, /area/quartermaster/miningdock) +"ckj" = ( +/obj/effect/decal/cleanable/blood, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "ckw" = ( /obj/structure/cable{ icon_state = "2-8" @@ -16250,6 +16174,13 @@ }, /turf/open/floor/plasteel/white, /area/science/research) +"coc" = ( +/obj/machinery/ai/server_cabinet/prefilled, +/obj/structure/ethernet_cable{ + icon_state = "0-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "cof" = ( /obj/effect/turf_decal/trimline/purple/filled/line{ dir = 8 @@ -16916,6 +16847,9 @@ /obj/effect/landmark/carpspawn, /turf/open/space, /area/space/nearstation) +"cxB" = ( +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "cxI" = ( /obj/structure/table, /obj/item/book/manual/wiki/hydroponicsplants{ @@ -17009,25 +16943,6 @@ }, /turf/open/floor/plasteel/dark/telecomms, /area/tcommsat/server) -"cyZ" = ( -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/obj/machinery/door/airlock/hatch{ - name = "Hardware Workshop"; - req_access_txt = "61" - }, -/obj/effect/mapping_helpers/airlock/cyclelink_helper{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "czc" = ( /obj/machinery/door/airlock/highsecurity{ name = "AI Upload Access"; @@ -17134,17 +17049,6 @@ }, /turf/open/floor/plasteel, /area/vacant_room/commissary) -"cAP" = ( -/obj/structure/table, -/obj/item/electropack, -/obj/item/healthanalyzer, -/obj/item/assembly/signaler, -/obj/effect/turf_decal/trimline/blue/filled/line, -/obj/effect/turf_decal/trimline/purple/filled/corner{ - dir = 4 - }, -/turf/open/floor/plasteel, -/area/science/misc_lab) "cAR" = ( /obj/effect/turf_decal/box, /obj/machinery/firealarm{ @@ -18341,6 +18245,23 @@ }, /turf/open/floor/plating, /area/maintenance/starboard) +"cWA" = ( +/obj/effect/turf_decal/trimline/yellow/filled/line{ + dir = 6 + }, +/obj/structure/rack, +/obj/item/radio/off{ + pixel_y = 4 + }, +/obj/item/storage/toolbox/mechanical, +/obj/item/toy/talking/AI, +/obj/item/multitool, +/obj/item/book/manual/wiki/tcomms{ + pixel_x = -4; + pixel_y = 5 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "cWJ" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 4 @@ -18375,6 +18296,12 @@ }, /turf/open/floor/plasteel/white, /area/medical/sleeper) +"cXC" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "cXW" = ( /obj/machinery/door/airlock/atmos{ name = "Atmospherics"; @@ -18392,6 +18319,20 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"cXZ" = ( +/obj/machinery/holopad, +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/obj/structure/chair/office/dark{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 9 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "cYj" = ( /obj/structure/lattice, /obj/effect/spawner/lootdrop/maintenance, @@ -18587,24 +18528,13 @@ }, /turf/open/floor/plasteel/dark, /area/science/xenobiology) -"dbJ" = ( -/obj/effect/turf_decal/stripes/line{ - dir = 6 - }, -/obj/structure/sign/plaques/ai_password{ - pixel_x = 32 - }, -/obj/machinery/papershredder, -/turf/open/floor/plasteel/white, -/area/crew_quarters/heads/hor) -"dcc" = ( -/obj/effect/turf_decal/stripes/line{ - dir = 1 +"dcO" = ( +/obj/structure/window/reinforced, +/obj/structure/window/reinforced{ + dir = 4 }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) +/turf/open/floor/grass, +/area/crew_quarters/public_lounge) "ddb" = ( /obj/machinery/navbeacon{ codes_txt = "patrol;next_patrol=HOP"; @@ -18984,13 +18914,6 @@ }, /turf/open/floor/plasteel, /area/janitor) -"dne" = ( -/obj/machinery/newscaster{ - pixel_y = 32 - }, -/obj/machinery/rack_creator, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "doM" = ( /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2, @@ -19522,13 +19445,6 @@ }, /turf/open/floor/plasteel/dark, /area/ai_monitored/nuke_storage) -"dBH" = ( -/obj/machinery/atmospherics/pipe/simple/general/visible{ - dir = 4 - }, -/obj/machinery/meter, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "dBU" = ( /obj/machinery/light_switch{ pixel_x = 27 @@ -19653,22 +19569,6 @@ "dEb" = ( /turf/closed/wall, /area/crew_quarters/heads/hop) -"dEd" = ( -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/obj/machinery/door/airlock/hatch{ - name = "MiniSat Monitoring Room"; - req_access_txt = "65" - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "dEI" = ( /obj/structure/table, /obj/item/storage/belt/utility, @@ -19701,15 +19601,13 @@ }, /turf/open/floor/plasteel/freezer, /area/crew_quarters/toilet) -"dFJ" = ( -/obj/structure/window/reinforced{ - dir = 1 - }, -/obj/structure/cable/white{ - icon_state = "4-8" +"dFr" = ( +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 6 }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) +/obj/item/twohanded/required/kirbyplants/random, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "dFX" = ( /obj/machinery/door/airlock/maintenance{ name = "Security Maintenance"; @@ -19989,16 +19887,6 @@ }, /turf/open/floor/plasteel, /area/science/misc_lab) -"dMA" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "dMJ" = ( /obj/machinery/advanced_airlock_controller{ dir = 8; @@ -20060,6 +19948,24 @@ }, /turf/open/floor/plating, /area/maintenance/port/fore) +"dNV" = ( +/obj/structure/window/reinforced{ + dir = 1 + }, +/obj/structure/cable/white{ + icon_state = "4-8" + }, +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) +"dNX" = ( +/obj/structure/ethernet_cable{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "dNY" = ( /turf/closed/wall/r_wall, /area/engine/foyer) @@ -20254,20 +20160,6 @@ /obj/machinery/vending/robotics, /turf/open/floor/plasteel, /area/science/robotics/lab) -"dTb" = ( -/obj/machinery/holopad, -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/obj/structure/chair/office/dark{ - dir = 4 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 9 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "dTe" = ( /obj/structure/closet/secure_closet/quartermaster, /obj/machinery/airalarm{ @@ -21132,6 +21024,10 @@ }, /turf/open/floor/plasteel/white, /area/security/brig) +"elB" = ( +/obj/machinery/atmospherics/pipe/manifold/cyan/hidden, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "elK" = ( /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ dir = 4 @@ -21510,6 +21406,18 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"euG" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "euJ" = ( /obj/machinery/door/airlock/maintenance_hatch, /obj/machinery/door/firedoor/border_only, @@ -21601,6 +21509,16 @@ }, /turf/open/floor/plasteel/dark, /area/bridge) +"exu" = ( +/obj/machinery/ai/data_core/primary, +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/obj/structure/ethernet_cable{ + icon_state = "0-2" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "exz" = ( /obj/structure/chair/office/dark{ dir = 8 @@ -22051,6 +21969,10 @@ }, /turf/open/floor/plasteel/white, /area/medical/sleeper) +"eFH" = ( +/obj/effect/spawner/structure/window/reinforced/shutter, +/turf/open/floor/plating, +/area/crew_quarters/public_lounge) "eFL" = ( /obj/machinery/camera{ c_tag = "Engineering Escape Pod"; @@ -22390,6 +22312,12 @@ }, /turf/open/floor/wood, /area/medical/psych) +"eLY" = ( +/obj/structure/window/reinforced{ + dir = 4 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "eMt" = ( /obj/effect/turf_decal/trimline/blue/filled/corner{ dir = 4 @@ -22554,6 +22482,13 @@ }, /turf/open/floor/plasteel/white, /area/science/research) +"eQw" = ( +/obj/machinery/ai/data_core, +/obj/structure/ethernet_cable{ + icon_state = "0-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "eQL" = ( /obj/structure/cable/yellow{ icon_state = "2-4" @@ -22696,6 +22631,28 @@ }, /turf/open/floor/plasteel, /area/security/courtroom) +"eTo" = ( +/obj/machinery/camera{ + c_tag = "Secondary AI Core"; + dir = 8; + network = list("ss13","rd") + }, +/obj/machinery/airalarm{ + pixel_y = 24 + }, +/obj/machinery/power/smes/engineering{ + charge = 5e+006; + input_level = 25000; + output_level = 20000 + }, +/obj/structure/cable{ + icon_state = "0-2" + }, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "eUf" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 4 @@ -22708,6 +22665,12 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/fore) +"eUg" = ( +/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ + dir = 8 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "eUi" = ( /obj/machinery/advanced_airlock_controller{ dir = 4; @@ -23110,6 +23073,28 @@ /obj/effect/turf_decal/trimline/blue/filled/line, /turf/open/floor/plasteel, /area/hallway/primary/central) +"fai" = ( +/obj/machinery/doorButtons/access_button{ + idDoor = "telecomms_airlock_exterior"; + idSelf = "telecomms_airlock_control"; + pixel_x = -7; + pixel_y = 23 + }, +/obj/machinery/doorButtons/airlock_controller{ + idExterior = "telecomms_airlock_exterior"; + idInterior = "telecomms_airlock_interior"; + idSelf = "telecomms_airlock_control"; + pixel_x = 5; + pixel_y = 25 + }, +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/obj/effect/turf_decal/trimline/yellow/filled/line{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "faj" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 6 @@ -23201,17 +23186,21 @@ /obj/machinery/holopad, /turf/open/floor/plasteel, /area/engine/foyer) -"fdU" = ( -/obj/structure/rack, -/obj/effect/turf_decal/stripes/line{ - dir = 9 +"fdg" = ( +/obj/structure/cable{ + icon_state = "1-4" }, -/obj/structure/sign/plaques/cave{ - pixel_y = 32 +/obj/structure/disposalpipe/segment{ + dir = 5 }, -/obj/item/circuitboard/computer/ai_upload_download, -/turf/open/floor/plasteel/white, -/area/crew_quarters/heads/hor) +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 5 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 5 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "fen" = ( /obj/machinery/computer/upload/ai{ dir = 1 @@ -23743,6 +23732,12 @@ }, /turf/open/floor/plasteel/dark, /area/bridge) +"fqr" = ( +/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ + dir = 4 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "fqu" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 8 @@ -23766,6 +23761,15 @@ }, /turf/open/floor/wood, /area/crew_quarters/heads/captain) +"fqF" = ( +/obj/machinery/door/firedoor/border_only{ + dir = 4 + }, +/obj/structure/cable/yellow{ + icon_state = "1-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "fqI" = ( /obj/machinery/computer/prisoner, /obj/effect/turf_decal/trimline/red/filled/line{ @@ -23792,18 +23796,6 @@ /obj/machinery/door/firedoor/border_only, /turf/open/floor/plating, /area/maintenance/starboard/aft) -"frD" = ( -/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ - dir = 8 - }, -/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ - dir = 8 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "frH" = ( /obj/machinery/light/small{ dir = 8 @@ -23941,6 +23933,15 @@ }, /turf/open/floor/plasteel, /area/science/misc_lab) +"fud" = ( +/obj/structure/ethernet_cable{ + icon_state = "2-8" + }, +/obj/structure/ethernet_cable{ + icon_state = "2-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "fuj" = ( /obj/machinery/camera{ c_tag = "Arrivals Escape Pod 1"; @@ -24178,6 +24179,11 @@ }, /turf/open/floor/plasteel/freezer, /area/crew_quarters/toilet) +"fzC" = ( +/obj/structure/flora/ausbushes/fullgrass, +/obj/structure/flora/tree/jungle/small, +/turf/open/floor/grass, +/area/crew_quarters/public_lounge) "fzE" = ( /obj/machinery/door/firedoor/border_only{ dir = 4 @@ -24497,18 +24503,6 @@ }, /turf/open/floor/plasteel/dark, /area/security/prison) -"fFO" = ( -/obj/effect/turf_decal/stripes/line{ - dir = 1 - }, -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, -/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ - dir = 1 - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "fFS" = ( /obj/structure/table/reinforced, /obj/machinery/door/firedoor/border_only{ @@ -24667,15 +24661,6 @@ }, /turf/open/floor/plating, /area/maintenance/port/aft) -"fIs" = ( -/obj/structure/window/reinforced{ - dir = 4 - }, -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "fIu" = ( /obj/machinery/door/airlock/public/glass{ name = "Central Access" @@ -24689,13 +24674,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) -"fIH" = ( -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "fIS" = ( /obj/machinery/atmospherics/pipe/simple/general/visible{ dir = 4 @@ -24814,31 +24792,6 @@ }, /turf/open/floor/plasteel, /area/quartermaster/office) -"fKM" = ( -/obj/machinery/door/airlock/command/glass{ - id_tag = "secondary_aicore_interior"; - name = "Physical Core Access"; - req_one_access_txt = "30, 70" - }, -/obj/machinery/door/firedoor/border_only{ - dir = 8 - }, -/obj/machinery/door/firedoor/border_only{ - dir = 4 - }, -/obj/effect/mapping_helpers/airlock/cyclelink_helper_target{ - dirx = -1; - diry = -1 - }, -/obj/effect/mapping_helpers/airlock/locked, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 4 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 4 - }, -/turf/open/floor/plating, -/area/ai_monitored/secondarydatacore) "fKR" = ( /obj/effect/landmark/start/cook, /turf/template_noop, @@ -25046,13 +24999,16 @@ }, /turf/open/floor/plating, /area/hallway/secondary/exit) -"fPM" = ( -/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ - dir = 8 +"fPz" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-4" }, -/obj/structure/chair/office/dark, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) +/obj/structure/ethernet_cable{ + icon_state = "1-8" + }, +/obj/machinery/light, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "fPU" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 4 @@ -25212,6 +25168,26 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/entry) +"fTa" = ( +/obj/machinery/door/airlock/command/glass{ + id_tag = "secondary_aicore_interior"; + name = "Physical Core Access"; + req_one_access_txt = "30;70" + }, +/obj/machinery/door/firedoor/border_only{ + dir = 8 + }, +/obj/machinery/door/firedoor/border_only{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/turf/open/floor/plating, +/area/ai_monitored/secondarydatacore) "fTk" = ( /obj/structure/cable{ icon_state = "4-8" @@ -25647,12 +25623,19 @@ }, /turf/open/floor/wood, /area/library) -"gdI" = ( -/obj/machinery/atmospherics/pipe/simple/general/visible{ - dir = 10 +"gdO" = ( +/obj/machinery/firealarm{ + pixel_y = 26 }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) +/obj/machinery/light{ + dir = 1 + }, +/obj/structure/window/reinforced{ + dir = 4 + }, +/obj/structure/flora/ausbushes/grassybush, +/turf/open/floor/grass, +/area/crew_quarters/public_lounge) "gdU" = ( /obj/structure/cable/yellow{ icon_state = "4-8" @@ -25693,6 +25676,14 @@ }, /turf/open/floor/plasteel/white, /area/medical/medbay/aft) +"geT" = ( +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "gfg" = ( /obj/effect/decal/cleanable/dirt, /obj/structure/sign/poster/official/do_not_question{ @@ -25700,6 +25691,13 @@ }, /turf/open/floor/plasteel, /area/security/prison) +"gfs" = ( +/obj/machinery/atmospherics/components/unary/vent_pump/siphon/on{ + external_pressure_bound = 120; + plane = -2 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "gft" = ( /obj/effect/decal/cleanable/cobweb, /obj/machinery/power/smes, @@ -25890,6 +25888,14 @@ /obj/effect/spawner/structure/window/reinforced/shutter, /turf/open/floor/plating, /area/maintenance/fore/secondary) +"gjO" = ( +/obj/structure/table, +/obj/item/storage/toolbox/mechanical, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "gkk" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ @@ -25980,6 +25986,10 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/plasteel/dark, /area/science/xenobiology) +"gob" = ( +/obj/effect/spawner/structure/window/reinforced/shutter, +/turf/open/floor/plating, +/area/space) "gof" = ( /obj/effect/turf_decal/trimline/blue/filled/corner{ dir = 4 @@ -26005,19 +26015,6 @@ }, /turf/open/floor/plasteel/dark, /area/bridge) -"goW" = ( -/obj/machinery/light{ - dir = 4 - }, -/obj/machinery/power/apc/highcap{ - areastring = "/area/ai_monitored/secondarydatacore"; - dir = 4; - name = "AI Secondary Datacore"; - pixel_x = 24 - }, -/obj/structure/cable, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "goZ" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -26134,6 +26131,13 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) +"grx" = ( +/obj/machinery/door/firedoor/border_only, +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "grK" = ( /obj/machinery/camera{ c_tag = "Central Hallway West"; @@ -26363,18 +26367,6 @@ }, /turf/open/floor/engine, /area/science/misc_lab) -"gvV" = ( -/obj/structure/table, -/obj/item/storage/toolbox/mechanical, -/obj/item/multitool, -/obj/machinery/cell_charger{ - pixel_y = 5 - }, -/obj/item/stock_parts/cell/high/plus, -/obj/item/stack/cable_coil, -/obj/effect/turf_decal/trimline/blue/filled/line, -/turf/open/floor/plasteel, -/area/science/misc_lab) "gws" = ( /obj/machinery/airalarm{ pixel_y = 24 @@ -26650,22 +26642,6 @@ }, /turf/open/floor/plasteel, /area/security/prison/hallway) -"gDs" = ( -/obj/machinery/doorButtons/access_button{ - idDoor = "secondary_aicore_interior"; - idSelf = "secondary_aicore_controller"; - name = "Secondary AI Core Access Button"; - pixel_x = -24; - pixel_y = 8; - req_one_access_txt = "30;70" - }, -/obj/structure/chair/office/light, -/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "gDD" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ dir = 8 @@ -26693,6 +26669,15 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/entry) +"gEx" = ( +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "gFf" = ( /obj/machinery/computer/security/telescreen{ dir = 8; @@ -26896,6 +26881,13 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) +"gID" = ( +/obj/machinery/holopad, +/obj/machinery/door/firedoor/border_only{ + dir = 8 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "gII" = ( /obj/effect/turf_decal/trimline/yellow/filled/line{ dir = 10 @@ -27009,17 +27001,6 @@ }, /turf/open/floor/plating, /area/maintenance/port) -"gOE" = ( -/obj/machinery/power/apc/highcap/five_k{ - areastring = "/area/tcommsat/computer"; - name = "Telecomms Control Room APC"; - pixel_y = -23 - }, -/obj/structure/cable{ - icon_state = "0-8" - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "gOK" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/washing_machine, @@ -27336,6 +27317,17 @@ }, /turf/open/floor/plasteel, /area/security/checkpoint/service) +"gUV" = ( +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/structure/cable{ + icon_state = "1-4" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "gUW" = ( /obj/machinery/light{ dir = 4 @@ -27431,6 +27423,13 @@ /obj/structure/lattice, /turf/open/space/basic, /area/space/nearstation) +"gXu" = ( +/obj/machinery/computer/ai_overclocking, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "gXy" = ( /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ dir = 8 @@ -27609,12 +27608,6 @@ /obj/effect/turf_decal/trimline/purple/filled/line, /turf/open/floor/plasteel, /area/hallway/primary/starboard) -"hbO" = ( -/obj/structure/window/reinforced{ - dir = 4 - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "hbQ" = ( /obj/machinery/door/firedoor/border_only{ dir = 1 @@ -27661,6 +27654,18 @@ }, /turf/open/floor/plasteel, /area/quartermaster/warehouse) +"hcP" = ( +/obj/structure/extinguisher_cabinet{ + pixel_x = 27 + }, +/obj/structure/table, +/obj/item/stack/ethernet_coil, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 5 + }, +/obj/item/clothing/shoes/magboots, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "hcW" = ( /obj/structure/chair/office/light{ dir = 4 @@ -28234,6 +28239,22 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/entry) +"hnc" = ( +/obj/machinery/computer/security/telescreen{ + dir = 8; + name = "MiniSat Camera Monitor"; + network = list("minisat","aicore"); + pixel_x = 26 + }, +/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ + dir = 8 + }, +/obj/machinery/computer/telecomms/server{ + dir = 8; + network = "tcommsat" + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "hnh" = ( /obj/structure/cable{ icon_state = "4-8" @@ -28243,6 +28264,21 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) +"hnA" = ( +/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ + dir = 1 + }, +/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ + dir = 1 + }, +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/structure/cable{ + icon_state = "2-4" + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "hoc" = ( /turf/closed/wall, /area/security/checkpoint/service) @@ -28491,6 +28527,14 @@ /obj/effect/turf_decal/trimline/red/filled/line, /turf/open/floor/plasteel, /area/hallway/secondary/exit) +"hsg" = ( +/obj/effect/turf_decal/stripes/line{ + dir = 1 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "hsn" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, @@ -28816,16 +28860,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/plating, /area/maintenance/starboard/aft) -"hzx" = ( -/obj/machinery/computer/telecomms/server{ - dir = 1; - network = "tcommsat" - }, -/obj/effect/turf_decal/trimline/yellow/filled/line{ - dir = 6 - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "hzQ" = ( /obj/structure/table, /obj/item/reagent_containers/glass/bucket, @@ -29199,6 +29233,18 @@ /obj/structure/cable/yellow, /turf/open/floor/plasteel/airless/solarpanel, /area/solar/starboard/aft) +"hHT" = ( +/obj/effect/turf_decal/stripes/end{ + dir = 4 + }, +/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "hIf" = ( /obj/structure/table, /obj/item/paper_bin{ @@ -29268,10 +29314,6 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) -"hJq" = ( -/obj/machinery/ai/data_core/primary, -/turf/open/floor/circuit/green/telecomms, -/area/ai_monitored/turret_protected/ai) "hJu" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/light/small{ @@ -29318,12 +29360,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) -"hJQ" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 4 - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "hKn" = ( /turf/open/floor/plasteel, /area/security/processing) @@ -29522,15 +29558,6 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) -"hOU" = ( -/obj/effect/turf_decal/stripes/line{ - dir = 1 - }, -/obj/machinery/computer/ai_server_console{ - dir = 1 - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "hPk" = ( /obj/machinery/holopad, /turf/open/floor/plasteel/white, @@ -29740,6 +29767,11 @@ }, /turf/open/floor/plating, /area/security/warden) +"hSS" = ( +/obj/structure/table, +/obj/effect/turf_decal/trimline/purple/filled/line, +/turf/open/floor/plasteel, +/area/science/misc_lab) "hTo" = ( /obj/structure/table, /obj/item/paper_bin{ @@ -30044,6 +30076,15 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"hXq" = ( +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 5 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "hXu" = ( /obj/machinery/atmospherics/pipe/simple/yellow/hidden{ dir = 4 @@ -30058,42 +30099,6 @@ "hYb" = ( /turf/open/floor/wood, /area/medical/psych) -"hYy" = ( -/obj/machinery/requests_console{ - announcementConsole = 1; - department = "Telecomms Admin"; - departmentType = 5; - name = "Telecomms RC"; - pixel_y = 30 - }, -/obj/effect/turf_decal/stripes/corner{ - dir = 1 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) -"hYX" = ( -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/obj/machinery/computer/monitor{ - dir = 1; - name = "MiniSat power monitoring console" - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) -"hYY" = ( -/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ - dir = 4 - }, -/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ - dir = 4 - }, -/obj/machinery/power/terminal{ - dir = 4 - }, -/obj/structure/cable, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "hZg" = ( /obj/machinery/power/smes/engineering{ charge = 5e+006; @@ -30328,20 +30333,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) -"ief" = ( -/obj/machinery/light{ - dir = 8 - }, -/obj/machinery/atmospherics/components/unary/vent_pump/siphon/on{ - dir = 4; - external_pressure_bound = 120 - }, -/obj/machinery/airalarm/tcomms{ - dir = 4; - pixel_x = -24 - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "ieh" = ( /obj/effect/turf_decal/stripes/line, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ @@ -30537,10 +30528,6 @@ }, /turf/open/floor/plasteel, /area/hydroponics) -"iiJ" = ( -/obj/machinery/ai/server_cabinet, -/turf/open/floor/circuit/green/telecomms/mainframe, -/area/ai_monitored/secondarydatacore) "iiO" = ( /obj/machinery/gulag_item_reclaimer{ pixel_y = 24 @@ -30629,10 +30616,6 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/exit) -"ikV" = ( -/obj/machinery/ai/server_cabinet/prefilled, -/turf/open/floor/circuit/green/telecomms, -/area/ai_monitored/turret_protected/ai) "ilc" = ( /obj/effect/turf_decal/trimline/brown/filled/corner, /turf/open/floor/plasteel, @@ -30730,6 +30713,12 @@ /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4, /turf/open/floor/plasteel, /area/engine/engineering) +"imV" = ( +/obj/structure/chair/office/dark{ + dir = 1 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "imZ" = ( /obj/machinery/power/apc{ areastring = "/area/maintenance/port/aft"; @@ -30768,6 +30757,15 @@ }, /turf/open/floor/plasteel/white, /area/science/research) +"inv" = ( +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/effect/turf_decal/trimline/purple/filled/warning, +/turf/open/floor/plasteel, +/area/science/misc_lab) "inx" = ( /obj/structure/rack, /obj/effect/spawner/lootdrop/glowstick, @@ -31041,6 +31039,15 @@ }, /turf/open/floor/plasteel/white, /area/medical/virology) +"irI" = ( +/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ + dir = 4 + }, +/obj/structure/window/reinforced{ + dir = 8 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "irN" = ( /obj/machinery/atmospherics/pipe/simple/yellow/visible{ dir = 4 @@ -31910,6 +31917,18 @@ "iKq" = ( /turf/template_noop, /area/maintenance/starboard/aft) +"iKx" = ( +/obj/machinery/power/apc{ + areastring = "/area/maintenance/starboard/aft"; + dir = 4; + name = "Starboard Quarter Maintenance APC"; + pixel_x = 24 + }, +/obj/structure/cable{ + icon_state = "0-8" + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "iKC" = ( /obj/structure/sign/warning/electricshock{ pixel_y = -32 @@ -32154,6 +32173,15 @@ }, /turf/open/floor/plasteel/white, /area/science/xenobiology) +"iPL" = ( +/obj/structure/sign/departments/minsky/engineering/telecommmunications{ + pixel_y = 32 + }, +/obj/effect/turf_decal/stripes/corner{ + dir = 4 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "iQm" = ( /obj/effect/turf_decal/stripes/line{ dir = 8 @@ -32163,6 +32191,18 @@ }, /turf/open/floor/plasteel, /area/crew_quarters/locker) +"iQG" = ( +/obj/structure/cable{ + icon_state = "1-4" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "iQH" = ( /obj/machinery/computer/station_alert, /obj/effect/turf_decal/trimline/yellow/filled/line{ @@ -32252,27 +32292,6 @@ /obj/effect/turf_decal/trimline/yellow/filled/line, /turf/open/floor/plasteel, /area/construction/mining/aux_base) -"iRV" = ( -/obj/structure/chair/office/dark{ - dir = 4 - }, -/obj/machinery/computer/security/telescreen{ - dir = 1; - name = "Telecomms Camera Monitor"; - network = list("tcomms"); - pixel_x = 30; - pixel_y = -37 - }, -/obj/item/radio/intercom{ - dir = 1; - freerange = 1; - name = "Station Intercom (Telecomms)"; - pixel_x = 28; - pixel_y = -26 - }, -/obj/effect/landmark/start/yogs/network_admin, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "iRY" = ( /obj/structure/table, /obj/item/flashlight{ @@ -32414,10 +32433,6 @@ }, /turf/open/floor/plating, /area/medical/paramedic) -"iVk" = ( -/obj/structure/girder, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "iVn" = ( /obj/structure/closet/crate{ icon_state = "crateopen" @@ -32856,6 +32871,16 @@ }, /turf/open/floor/plasteel, /area/storage/primary) +"jgb" = ( +/obj/structure/rack, +/obj/effect/turf_decal/stripes/line{ + dir = 9 + }, +/obj/structure/sign/plaques/cave{ + pixel_y = 32 + }, +/turf/open/floor/plasteel/white, +/area/crew_quarters/heads/hor) "jgC" = ( /obj/structure/table, /obj/item/hand_labeler, @@ -33076,6 +33101,12 @@ }, /turf/open/floor/plasteel, /area/crew_quarters/dorms) +"jmi" = ( +/obj/structure/chair/office/dark{ + dir = 8 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "jmH" = ( /obj/structure/sign/warning/radiation, /turf/closed/wall/r_wall, @@ -33651,6 +33682,13 @@ }, /turf/open/floor/plasteel, /area/engine/foyer) +"jxV" = ( +/obj/effect/turf_decal/stripes/line{ + dir = 6 + }, +/obj/machinery/papershredder, +/turf/open/floor/plasteel/white, +/area/crew_quarters/heads/hor) "jyo" = ( /obj/machinery/door/airlock/maintenance_hatch, /obj/machinery/door/firedoor/border_only{ @@ -33660,18 +33698,19 @@ /obj/effect/mapping_helpers/airlock/abandoned, /turf/open/floor/plating, /area/maintenance/aft) +"jyT" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/obj/effect/spawner/structure/window/reinforced, +/turf/open/floor/plating, +/area/ai_monitored/secondarydatacore) "jzg" = ( /obj/structure/cable{ icon_state = "1-2" }, /turf/open/floor/plating, /area/maintenance/disposal/incinerator) -"jzm" = ( -/obj/structure/cable/yellow{ - icon_state = "2-4" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "jzo" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ dir = 1 @@ -34341,20 +34380,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/plasteel/white, /area/science/research) -"jPU" = ( -/obj/machinery/door/firedoor/border_only, -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "jQg" = ( /obj/effect/turf_decal/arrows/white{ color = "#99ccff"; @@ -34399,6 +34424,21 @@ /obj/effect/turf_decal/trimline/purple/filled/line, /turf/open/floor/plasteel/white, /area/science/mixing) +"jQM" = ( +/obj/machinery/light{ + dir = 1 + }, +/obj/structure/table/wood, +/obj/item/toy/cards/deck{ + pixel_x = -6; + pixel_y = -1 + }, +/obj/item/dice/d20{ + pixel_x = 7; + pixel_y = 6 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "jQU" = ( /obj/structure/table/reinforced, /obj/machinery/door/window/brigdoor/eastleft{ @@ -34750,6 +34790,12 @@ }, /turf/open/space/basic, /area/ai_monitored/turret_protected/aisat_interior) +"jXf" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "jXv" = ( /obj/structure/disposalpipe/segment, /turf/open/floor/carpet, @@ -35070,6 +35116,21 @@ }, /turf/open/floor/plasteel/airless/solarpanel, /area/solar/starboard/aft) +"kfc" = ( +/obj/machinery/camera{ + c_tag = "MiniSat - Monitoring room"; + dir = 8; + network = list("minisat","ss13") + }, +/obj/machinery/newscaster/security_unit{ + pixel_x = 28 + }, +/obj/machinery/computer/telecomms/traffic{ + dir = 8; + network = "tcommsat" + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "kfF" = ( /obj/structure/table/glass, /obj/item/reagent_containers/food/snacks/grown/poppy, @@ -35644,6 +35705,15 @@ /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2, /turf/open/floor/plasteel, /area/crew_quarters/dorms) +"ksh" = ( +/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ + dir = 8 + }, +/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ + dir = 4 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "kso" = ( /obj/structure/chair/sofa/right{ dir = 4 @@ -35654,6 +35724,15 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/service) +"ksx" = ( +/obj/structure/extinguisher_cabinet{ + pixel_x = -27 + }, +/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ + dir = 4 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "ksQ" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ dir = 4 @@ -35765,6 +35844,18 @@ }, /turf/open/space/basic, /area/space/nearstation) +"kwt" = ( +/obj/structure/table, +/obj/item/storage/toolbox/mechanical, +/obj/item/multitool, +/obj/machinery/cell_charger{ + pixel_y = 5 + }, +/obj/item/stock_parts/cell/high/plus, +/obj/item/stack/cable_coil, +/obj/effect/turf_decal/trimline/purple/filled/line, +/turf/open/floor/plasteel, +/area/science/misc_lab) "kwY" = ( /obj/structure/table/wood, /obj/item/flashlight/lamp/green{ @@ -35811,6 +35902,18 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) +"kyu" = ( +/obj/machinery/door/firedoor/border_only, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "kyx" = ( /obj/machinery/bounty_board{ pixel_y = 32 @@ -35932,6 +36035,11 @@ }, /turf/open/floor/plasteel, /area/maintenance/disposal/incinerator) +"kAy" = ( +/obj/structure/lattice, +/obj/structure/lattice, +/turf/open/space, +/area/space/nearstation) "kAz" = ( /obj/effect/turf_decal/trimline/green/filled/line{ dir = 4 @@ -36319,6 +36427,12 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) +"kIf" = ( +/obj/structure/table, +/obj/item/storage/box/donkpockets, +/obj/effect/turf_decal/trimline/purple/filled/line, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "kIl" = ( /obj/effect/turf_decal/stripes/line, /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4, @@ -36352,12 +36466,6 @@ }, /turf/open/floor/carpet, /area/crew_quarters/fitness) -"kJz" = ( -/obj/machinery/atmospherics/pipe/manifold/general/visible{ - dir = 4 - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "kJK" = ( /obj/structure/grille, /obj/structure/window{ @@ -36374,6 +36482,21 @@ }, /turf/open/floor/plating, /area/maintenance/port) +"kKc" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/structure/disposalpipe/segment{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "kKq" = ( /obj/structure/table/wood, /obj/item/paper_bin{ @@ -36465,6 +36588,11 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/fore) +"kMz" = ( +/obj/effect/spawner/lootdrop/maintenance, +/obj/structure/rack, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "kMY" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ dir = 8 @@ -36488,6 +36616,16 @@ }, /turf/open/floor/plating, /area/quartermaster/sorting) +"kNH" = ( +/obj/machinery/rnd/production/circuit_imprinter/department/netmin, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 1 + }, +/obj/structure/sign/plaques/kiddie{ + pixel_y = 32 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "kNQ" = ( /obj/machinery/conveyor{ dir = 4; @@ -36737,16 +36875,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/fore) -"kSZ" = ( -/obj/machinery/atmospherics/pipe/simple/cyan/hidden, -/obj/structure/window/reinforced{ - dir = 1 - }, -/obj/structure/cable/white{ - icon_state = "4-8" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "kTm" = ( /obj/machinery/portable_atmospherics/canister/nitrogen, /obj/structure/window/reinforced{ @@ -36949,6 +37077,12 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/port) +"kYm" = ( +/obj/structure/cable/yellow{ + icon_state = "2-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "kYK" = ( /turf/closed/wall/r_wall, /area/medical/genetics/cloning) @@ -36964,6 +37098,19 @@ /obj/structure/closet/l3closet, /turf/open/floor/plating, /area/maintenance/aft) +"kZA" = ( +/obj/machinery/atmospherics/components/unary/vent_pump/siphon/on{ + dir = 1; + external_pressure_bound = 120; + plane = -2 + }, +/obj/machinery/camera{ + c_tag = "Secondary AI Core"; + dir = 4; + network = list("ss13","rd") + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "kZX" = ( /obj/structure/window/reinforced{ dir = 8 @@ -37063,12 +37210,6 @@ /obj/effect/turf_decal/trimline/yellow/filled/line, /turf/open/floor/plasteel, /area/hallway/primary/central) -"lbr" = ( -/obj/structure/cable/white{ - icon_state = "4-8" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "lbE" = ( /obj/machinery/light, /obj/effect/turf_decal/trimline/blue/filled/corner{ @@ -37090,6 +37231,13 @@ }, /turf/open/floor/plating, /area/storage/tech) +"lcu" = ( +/obj/machinery/rack_creator, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "lcC" = ( /obj/effect/spawner/structure/window/reinforced, /obj/machinery/door/poddoor/shutters/preopen{ @@ -37271,9 +37419,6 @@ }, /turf/open/floor/plating, /area/maintenance/aft) -"lhk" = ( -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "lhG" = ( /obj/effect/turf_decal/trimline/red/filled/corner, /turf/open/floor/plasteel, @@ -37294,6 +37439,9 @@ }, /turf/open/floor/engine, /area/science/xenobiology) +"lik" = ( +/turf/closed/wall/r_wall, +/area/crew_quarters/public_lounge) "lip" = ( /obj/machinery/light{ dir = 1 @@ -37650,6 +37798,17 @@ }, /turf/open/floor/plasteel/dark, /area/engine/atmos_distro) +"lnx" = ( +/obj/machinery/airalarm{ + dir = 8; + pixel_x = 24 + }, +/obj/machinery/computer/message_monitor{ + dir = 8 + }, +/obj/effect/decal/cleanable/cobweb/cobweb2, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "lnA" = ( /obj/structure/table, /obj/item/assembly/signaler, @@ -37717,18 +37876,6 @@ /obj/machinery/telecomms/server/presets/engineering, /turf/open/floor/circuit/green/telecomms/mainframe, /area/tcommsat/server) -"loK" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/structure/cable{ - icon_state = "1-2" - }, -/obj/effect/turf_decal/trimline/blue/filled/corner{ - dir = 8 - }, -/obj/effect/turf_decal/trimline/blue/filled/corner, -/turf/open/floor/plasteel, -/area/science/misc_lab) "lpj" = ( /obj/effect/turf_decal/trimline/purple/filled/line{ dir = 1 @@ -37800,18 +37947,6 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/exit) -"lrF" = ( -/obj/machinery/computer/message_monitor{ - dir = 1 - }, -/obj/effect/turf_decal/trimline/yellow/filled/line, -/obj/machinery/camera{ - c_tag = "Telecomms Maintenance"; - dir = 1; - network = list("ss13","tcomms") - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "lrO" = ( /obj/structure/rack, /obj/item/pipe_dispenser, @@ -38372,15 +38507,6 @@ /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, /area/science/robotics/lab) -"lFe" = ( -/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ - dir = 8 - }, -/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ - dir = 4 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "lFj" = ( /turf/template_noop, /area/maintenance/port/fore) @@ -38450,11 +38576,6 @@ /obj/structure/chair/sofa/right, /turf/open/floor/wood, /area/medical/psych) -"lHO" = ( -/obj/item/stack/cable_coil, -/obj/effect/decal/cleanable/dirt/dust, -/turf/open/floor/circuit/green/telecomms, -/area/ai_monitored/turret_protected/ai) "lIb" = ( /obj/structure/sign/warning/electricshock{ pixel_y = 32 @@ -38507,6 +38628,17 @@ /obj/effect/turf_decal/delivery, /turf/open/floor/engine, /area/science/xenobiology) +"lJc" = ( +/obj/effect/turf_decal/trimline/purple/filled/line, +/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ + dir = 1 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) +"lJN" = ( +/obj/structure/grille, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "lKd" = ( /obj/machinery/firealarm{ pixel_y = 28 @@ -38717,6 +38849,18 @@ /obj/effect/turf_decal/trimline/purple/filled/corner, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) +"lNu" = ( +/obj/machinery/door/airlock/command/glass{ + id_tag = "secondary_aicore_exterior"; + name = "Physical Core Access"; + req_one_access_txt = "30;70" + }, +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/obj/machinery/door/firedoor/border_only, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "lNU" = ( /turf/open/floor/plating{ icon_state = "panelscorched" @@ -38812,6 +38956,15 @@ /obj/item/twohanded/required/kirbyplants/random, /turf/open/floor/plasteel, /area/ai_monitored/storage/eva) +"lRc" = ( +/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ + dir = 4 + }, +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "lRt" = ( /obj/effect/mapping_helpers/airlock/cyclelink_helper{ dir = 1 @@ -39026,6 +39179,13 @@ /obj/effect/turf_decal/trimline/blue/filled/line, /turf/open/floor/plasteel, /area/hallway/primary/starboard) +"lWF" = ( +/obj/structure/frame/machine{ + anchored = 1; + state = 2 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "lWI" = ( /obj/structure/table, /obj/item/cartridge/quartermaster{ @@ -39244,19 +39404,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/plating, /area/maintenance/disposal) -"lZD" = ( -/obj/structure/table/wood, -/obj/item/radio/off{ - pixel_x = -6; - pixel_y = 5 - }, -/obj/item/folder{ - pixel_x = 6; - pixel_y = 2 - }, -/obj/item/disk/holodisk/tutorial/AICore, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "mao" = ( /obj/machinery/mineral/stacking_unit_console{ machinedir = 8 @@ -40284,18 +40431,6 @@ /obj/effect/turf_decal/trimline/green/filled/corner, /turf/open/floor/plasteel/white, /area/medical/virology) -"mtW" = ( -/obj/machinery/computer/security/telescreen{ - dir = 8; - name = "MiniSat Camera Monitor"; - network = list("minisat","aicore"); - pixel_x = 26 - }, -/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ - dir = 8 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "mtZ" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, @@ -40420,26 +40555,6 @@ }, /turf/open/floor/plasteel, /area/quartermaster/storage) -"mwf" = ( -/obj/effect/turf_decal/stripes/end{ - dir = 8 - }, -/obj/machinery/doorButtons/access_button{ - idDoor = "secondary_aicore_exterior"; - idSelf = "secondary_aicore_controller"; - name = "Secondary AI Core Access Button"; - pixel_x = -23; - pixel_y = -9; - req_one_access_txt = "30;70" - }, -/obj/machinery/light/small{ - dir = 8 - }, -/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ - dir = 4 - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "mwF" = ( /turf/open/floor/plasteel/white, /area/medical/chemistry) @@ -41278,6 +41393,13 @@ /obj/effect/landmark/start/shaft_miner, /turf/open/floor/plasteel, /area/quartermaster/miningdock) +"mOp" = ( +/obj/structure/ethernet_cable{ + icon_state = "0-8" + }, +/obj/machinery/ai/server_cabinet/prefilled, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "mOQ" = ( /obj/structure/table/wood, /obj/item/clipboard, @@ -41343,26 +41465,6 @@ }, /turf/open/floor/plasteel/white, /area/science/research) -"mQY" = ( -/obj/effect/turf_decal/stripes/end{ - dir = 4 - }, -/obj/machinery/doorButtons/access_button{ - idDoor = "secondary_aicore_interior"; - idSelf = "secondary_aicore_controller"; - name = "Secondary AI Core Access Button"; - pixel_x = 8; - pixel_y = 24; - req_one_access_txt = "30;70" - }, -/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ - dir = 4 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 4 - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "mRq" = ( /obj/machinery/newscaster/security_unit{ pixel_x = -32 @@ -41405,10 +41507,6 @@ }, /turf/open/floor/wood, /area/crew_quarters/heads/captain) -"mSg" = ( -/obj/machinery/atmospherics/pipe/manifold/general/visible, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "mSl" = ( /obj/structure/closet/l3closet/scientist, /obj/effect/turf_decal/trimline/purple/filled/line{ @@ -41894,6 +41992,15 @@ }, /turf/open/floor/engine, /area/science/xenobiology) +"nce" = ( +/obj/effect/landmark/blobstart, +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "ncf" = ( /obj/machinery/atmospherics/pipe/simple/cyan/visible, /turf/open/floor/plasteel, @@ -42018,6 +42125,13 @@ }, /turf/open/floor/plating, /area/maintenance/port) +"ndG" = ( +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/mob/living/simple_animal/pet/axolotl/bop, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "ndK" = ( /obj/structure/cable{ icon_state = "1-2" @@ -42057,16 +42171,6 @@ /obj/machinery/door/airlock/maintenance_hatch, /turf/open/floor/plating, /area/maintenance/starboard/aft) -"nfC" = ( -/obj/structure/chair/office/dark, -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 5 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "nfK" = ( /obj/effect/spawner/structure/window, /turf/open/floor/plating, @@ -42322,23 +42426,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/starboard) -"nlV" = ( -/obj/machinery/door/airlock/command/glass{ - id_tag = "secondary_aicore_exterior"; - name = "Physical Core Access"; - req_one_access_txt = "30;70" - }, -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/obj/effect/mapping_helpers/airlock/cyclelink_helper_target{ - dirx = 1; - diry = 1 - }, -/obj/effect/mapping_helpers/airlock/locked, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "nlY" = ( /obj/effect/landmark/stationroom/maint/tenxfive, /turf/template_noop, @@ -42794,6 +42881,21 @@ /obj/effect/turf_decal/trimline/yellow/filled/line, /turf/open/floor/plasteel, /area/hallway/primary/central) +"nvD" = ( +/obj/structure/sign/warning/electricshock{ + pixel_y = -32 + }, +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "nvE" = ( /obj/effect/spawner/lootdrop/maintenance{ lootcount = 2; @@ -42864,6 +42966,42 @@ "nxy" = ( /turf/closed/wall, /area/maintenance/port) +"nxA" = ( +/obj/machinery/power/apc/highcap{ + areastring = "/area/ai_monitored/secondarydatacore"; + dir = 4; + name = "AI Secondary Datacore"; + pixel_x = 24 + }, +/obj/machinery/light{ + dir = 4 + }, +/obj/structure/cable{ + icon_state = "0-8" + }, +/obj/structure/table, +/obj/item/circuitboard/machine/server_cabinet, +/obj/item/circuitboard/machine/ai_data_core, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 4 + }, +/obj/machinery/camera{ + c_tag = "Secondary AI Core"; + dir = 8; + network = list("ss13","rd") + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) +"nxI" = ( +/obj/machinery/atmospherics/pipe/simple/cyan/hidden, +/obj/structure/window/reinforced{ + dir = 1 + }, +/obj/structure/cable/white{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "nxT" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 1 @@ -43160,14 +43298,15 @@ }, /turf/open/floor/plating, /area/engine/engineering) -"nDW" = ( -/obj/structure/window/reinforced, -/obj/machinery/atmospherics/pipe/simple/cyan/hidden, -/obj/structure/cable/yellow{ - icon_state = "4-8" +"nDH" = ( +/obj/effect/turf_decal/stripes/corner{ + dir = 1 }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) +/obj/structure/chair/office/dark{ + dir = 4 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "nES" = ( /obj/structure/window/reinforced{ dir = 1; @@ -43377,13 +43516,6 @@ }, /turf/open/floor/plating, /area/maintenance/aft) -"nJj" = ( -/obj/machinery/holopad, -/obj/machinery/door/firedoor/border_only{ - dir = 8 - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "nJl" = ( /obj/effect/turf_decal/pool{ dir = 8 @@ -43527,6 +43659,14 @@ }, /turf/open/floor/circuit/telecomms/server, /area/ai_monitored/turret_protected/ai) +"nLQ" = ( +/obj/structure/table, +/obj/machinery/microwave, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 10 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "nNg" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, @@ -43712,6 +43852,11 @@ /obj/effect/turf_decal/trimline/red/filled/corner, /turf/open/floor/plasteel, /area/security/brig) +"nSy" = ( +/obj/effect/turf_decal/trimline/yellow/filled/line, +/obj/machinery/announcement_system, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "nSI" = ( /obj/machinery/atmospherics/pipe/simple/orange/visible{ dir = 4 @@ -43785,15 +43930,6 @@ }, /turf/open/floor/plasteel/white, /area/science/research) -"nTI" = ( -/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ - dir = 8 - }, -/obj/structure/window/reinforced{ - dir = 8 - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "nTR" = ( /obj/item/cigbutt/roach, /turf/open/floor/plating, @@ -44063,14 +44199,6 @@ }, /turf/open/floor/plasteel, /area/security/brig) -"nXh" = ( -/obj/structure/table, -/obj/effect/turf_decal/trimline/purple/filled/corner{ - dir = 8 - }, -/obj/effect/turf_decal/trimline/blue/filled/corner, -/turf/open/floor/plasteel, -/area/science/misc_lab) "nXj" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ @@ -44155,6 +44283,15 @@ /obj/effect/turf_decal/ramp_middle, /turf/open/floor/wood, /area/library) +"oas" = ( +/obj/machinery/light{ + dir = 8 + }, +/obj/machinery/atmospherics/pipe/manifold/cyan/hidden{ + dir = 8 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "oaA" = ( /obj/structure/table/reinforced, /obj/machinery/door/window/northleft{ @@ -44470,6 +44607,10 @@ /obj/item/pen, /turf/open/floor/plasteel, /area/hallway/primary/central) +"oiG" = ( +/obj/structure/flora/ausbushes/lavendergrass, +/turf/open/floor/grass, +/area/crew_quarters/public_lounge) "oje" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 8 @@ -44587,6 +44728,15 @@ }, /turf/open/floor/plating, /area/storage/tech) +"okV" = ( +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/obj/machinery/modular_computer/console/preset/tcomms{ + dir = 1 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "olb" = ( /obj/structure/chair/office/dark, /obj/effect/landmark/start/depsec/service, @@ -45440,6 +45590,15 @@ }, /turf/open/floor/plating, /area/engine/atmos_distro) +"oAU" = ( +/obj/structure/window/reinforced{ + dir = 1 + }, +/obj/structure/cable/white{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "oBk" = ( /obj/structure/cable{ icon_state = "1-2" @@ -46013,6 +46172,15 @@ }, /turf/open/floor/plating, /area/storage/tech) +"oPn" = ( +/obj/machinery/atmospherics/pipe/simple/cyan/hidden{ + dir = 8 + }, +/obj/structure/window/reinforced{ + dir = 8 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "oPr" = ( /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ dir = 1 @@ -46314,6 +46482,13 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"oWS" = ( +/obj/structure/ethernet_cable{ + icon_state = "0-4" + }, +/obj/machinery/ai/server_cabinet, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "oXp" = ( /obj/effect/turf_decal/stripes{ dir = 1 @@ -46507,6 +46682,12 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"pbe" = ( +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "pbU" = ( /obj/structure/sign/departments/minsky/command/charge{ pixel_y = -32 @@ -46616,6 +46797,12 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/port) +"pek" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "pen" = ( /obj/structure/cable/yellow{ icon_state = "4-8" @@ -46895,6 +47082,18 @@ }, /turf/open/floor/plasteel, /area/quartermaster/miningdock) +"pit" = ( +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ + dir = 8 + }, +/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ + dir = 8 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "piv" = ( /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, @@ -46919,20 +47118,6 @@ /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, /area/medical/sleeper) -"piV" = ( -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating{ - icon_state = "platingdmg3" - }, -/area/maintenance/starboard/aft) "pjc" = ( /obj/effect/turf_decal/arrows/white{ color = "#99ccff"; @@ -47078,20 +47263,6 @@ }, /turf/open/floor/plasteel, /area/hallway/secondary/entry) -"pmR" = ( -/obj/machinery/door/airlock/hatch{ - name = "Telecomms Tech Storage"; - req_access_txt = "61" - }, -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/door/firedoor/border_only, -/obj/effect/mapping_helpers/airlock/cyclelink_helper, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/dark, -/area/tcommsat/computer) "pmW" = ( /obj/machinery/door/airlock/maintenance{ name = "Teleporter Maintenance"; @@ -47554,32 +47725,6 @@ dir = 1 }, /area/hallway/secondary/entry) -"pvf" = ( -/obj/machinery/status_display/ai{ - pixel_x = -32 - }, -/obj/structure/table/wood, -/obj/item/book/manual/wiki/tcomms{ - pixel_x = -4; - pixel_y = 5 - }, -/obj/item/paper_bin{ - pixel_x = 3; - pixel_y = 3 - }, -/obj/item/folder/blue, -/obj/item/pen, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) -"pvo" = ( -/obj/structure/sign/departments/minsky/engineering/telecommmunications{ - pixel_y = 32 - }, -/obj/effect/turf_decal/trimline/yellow/filled/line{ - dir = 1 - }, -/turf/open/floor/plasteel, -/area/hallway/primary/central) "pvr" = ( /obj/machinery/chem_heater, /obj/effect/turf_decal/trimline/yellow/filled/line{ @@ -47747,14 +47892,6 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) -"pyZ" = ( -/obj/structure/cable/yellow{ - icon_state = "1-2" - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "pzv" = ( /obj/effect/turf_decal/bot{ dir = 1 @@ -47941,10 +48078,6 @@ }, /turf/open/space, /area/solar/port/aft) -"pDa" = ( -/obj/machinery/ai/data_core, -/turf/open/floor/circuit/green/telecomms/mainframe, -/area/ai_monitored/secondarydatacore) "pDq" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ dir = 1 @@ -48174,9 +48307,6 @@ }, /turf/open/floor/plasteel/white, /area/security/brig) -"pJB" = ( -/turf/closed/wall, -/area/tcommsat/computer) "pJI" = ( /obj/structure/extinguisher_cabinet{ pixel_x = -27; @@ -48335,6 +48465,13 @@ }, /turf/open/floor/plasteel, /area/quartermaster/storage) +"pOM" = ( +/obj/structure/window/reinforced, +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "pOP" = ( /obj/effect/turf_decal/stripes/end, /turf/open/floor/plating, @@ -48407,6 +48544,15 @@ }, /turf/open/floor/plasteel/white, /area/medical/virology) +"pQd" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "pQy" = ( /obj/machinery/door/airlock/public/glass{ name = "Escape Podbay" @@ -48511,18 +48657,6 @@ /obj/effect/turf_decal/trimline/blue/filled/line, /turf/open/floor/plasteel/white, /area/medical/genetics/cloning) -"pSY" = ( -/obj/structure/chair/office/dark{ - dir = 8 - }, -/obj/machinery/firealarm{ - pixel_y = 26 - }, -/obj/machinery/light{ - dir = 1 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "pTh" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, @@ -48561,15 +48695,6 @@ /obj/effect/turf_decal/trimline/purple/filled/corner, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) -"pTL" = ( -/obj/structure/sign/departments/minsky/engineering/telecommmunications{ - pixel_y = 32 - }, -/obj/effect/turf_decal/stripes/corner{ - dir = 4 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "pTN" = ( /obj/machinery/iv_drip, /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ @@ -48651,29 +48776,6 @@ }, /turf/open/floor/plasteel/white, /area/medical/medbay/lobby) -"pWn" = ( -/obj/machinery/doorButtons/access_button{ - idDoor = "telecomms_airlock_exterior"; - idSelf = "telecomms_airlock_control"; - pixel_x = -7; - pixel_y = 23 - }, -/obj/machinery/doorButtons/airlock_controller{ - idExterior = "telecomms_airlock_exterior"; - idInterior = "telecomms_airlock_interior"; - idSelf = "telecomms_airlock_control"; - pixel_x = 5; - pixel_y = 25 - }, -/obj/structure/cable/yellow{ - icon_state = "4-8" - }, -/obj/machinery/modular_computer/console/preset/tcomms, -/obj/effect/turf_decal/trimline/yellow/filled/line{ - dir = 1 - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "pWF" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 6 @@ -48777,28 +48879,6 @@ }, /turf/open/floor/plasteel/dark, /area/security/courtroom) -"pYv" = ( -/obj/machinery/camera{ - c_tag = "Secondary AI Core"; - dir = 8; - network = list("ss13","rd") - }, -/obj/machinery/airalarm{ - pixel_y = 24 - }, -/obj/structure/extinguisher_cabinet{ - pixel_x = 27 - }, -/obj/machinery/power/smes/engineering{ - charge = 5e+006; - input_level = 25000; - output_level = 20000 - }, -/obj/structure/cable{ - icon_state = "0-2" - }, -/turf/open/floor/plasteel/dark, -/area/ai_monitored/secondarydatacore) "pYO" = ( /obj/machinery/hydroponics/soil, /turf/open/floor/grass, @@ -49297,18 +49377,6 @@ }, /turf/open/floor/plasteel/dark, /area/security/courtroom) -"qjZ" = ( -/obj/machinery/power/apc{ - areastring = "/area/maintenance/starboard/aft"; - dir = 1; - name = "Starboard Quarter Maintenance APC"; - pixel_y = 23 - }, -/obj/structure/cable{ - icon_state = "0-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "qko" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 4 @@ -49651,6 +49719,11 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) +"qrf" = ( +/obj/effect/turf_decal/trimline/purple/filled/line, +/obj/machinery/atmospherics/components/unary/thermomachine/freezer/on, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "qrj" = ( /obj/structure/disposalpipe/segment, /obj/structure/cable{ @@ -49701,12 +49774,6 @@ }, /turf/open/floor/plating, /area/maintenance/port/aft) -"qsZ" = ( -/obj/effect/landmark/event_spawn, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "qtd" = ( /obj/effect/landmark/event_spawn, /obj/effect/turf_decal/trimline/red/filled/line{ @@ -50013,16 +50080,6 @@ }, /turf/open/floor/wood, /area/lawoffice) -"qzd" = ( -/obj/machinery/airalarm{ - dir = 8; - pixel_x = 24 - }, -/obj/machinery/computer/ai_control_console{ - dir = 8 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "qzt" = ( /obj/machinery/door/airlock/external{ name = "Engineering External Access"; @@ -50221,6 +50278,12 @@ }, /turf/open/space/basic, /area/space/nearstation) +"qEZ" = ( +/obj/structure/cable/white{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "qFC" = ( /obj/machinery/door/airlock/maintenance_hatch, /obj/effect/mapping_helpers/airlock/abandoned, @@ -50303,6 +50366,16 @@ }, /turf/open/floor/plating, /area/maintenance/fore) +"qGt" = ( +/obj/structure/cable/yellow{ + icon_state = "1-8" + }, +/obj/machinery/computer/monitor{ + dir = 8; + name = "MiniSat power monitoring console" + }, +/turf/open/floor/plating, +/area/ai_monitored/storage/satellite) "qGC" = ( /obj/machinery/door/airlock/mining/glass{ name = "Cargo Bay"; @@ -50433,12 +50506,6 @@ }, /turf/open/floor/plating, /area/maintenance/solars/starboard/fore) -"qJg" = ( -/obj/structure/cable/yellow{ - icon_state = "4-8" - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/turret_protected/ai) "qJt" = ( /obj/machinery/door/firedoor/border_only{ dir = 1 @@ -50559,20 +50626,6 @@ /obj/effect/turf_decal/trimline/green/filled/corner, /turf/open/floor/plasteel, /area/hydroponics/garden) -"qLi" = ( -/obj/machinery/camera{ - c_tag = "MiniSat - Monitoring room"; - dir = 8; - network = list("minisat","ss13") - }, -/obj/machinery/newscaster/security_unit{ - pixel_x = 28 - }, -/obj/machinery/computer/ai_resource_distribution{ - dir = 8 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "qLt" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -51394,15 +51447,6 @@ /obj/effect/turf_decal/trimline/blue/filled/line, /turf/open/floor/plasteel/white, /area/security/brig) -"rdw" = ( -/obj/machinery/camera{ - c_tag = "Telecomms Control Room"; - dir = 4; - network = list("ss13","tcomms") - }, -/obj/machinery/announcement_system, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rdL" = ( /obj/structure/disposaloutlet{ dir = 4 @@ -51420,12 +51464,6 @@ /obj/structure/cable/yellow, /turf/open/floor/plasteel/airless/solarpanel, /area/solar/port/fore) -"rdR" = ( -/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ - dir = 4 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rfy" = ( /obj/machinery/airalarm{ dir = 8; @@ -51443,12 +51481,6 @@ }, /turf/open/floor/plasteel/white, /area/medical/virology) -"rfJ" = ( -/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ - dir = 8 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rfK" = ( /obj/machinery/light{ dir = 4 @@ -51742,6 +51774,15 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) +"rmq" = ( +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/structure/disposalpipe/segment, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "rmT" = ( /obj/effect/turf_decal/trimline/red/filled/corner{ dir = 1 @@ -51911,13 +51952,6 @@ /obj/machinery/light, /turf/open/floor/plasteel, /area/crew_quarters/dorms) -"rqW" = ( -/obj/structure/window/reinforced, -/obj/structure/cable/yellow{ - icon_state = "4-8" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "rqZ" = ( /obj/machinery/door/poddoor{ id = "QMLoaddoor"; @@ -52253,15 +52287,6 @@ /obj/effect/turf_decal/trimline/blue/filled/line, /turf/open/floor/plasteel/dark, /area/bridge) -"rzx" = ( -/obj/machinery/light{ - dir = 1 - }, -/obj/structure/sign/plaques/kiddie{ - pixel_y = 32 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rzA" = ( /obj/item/radio/intercom{ pixel_x = 28 @@ -52478,6 +52503,16 @@ }, /turf/open/floor/plasteel/white, /area/medical/paramedic) +"rDw" = ( +/obj/structure/table, +/obj/item/electropack, +/obj/item/healthanalyzer, +/obj/item/assembly/signaler, +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 6 + }, +/turf/open/floor/plasteel, +/area/science/misc_lab) "rDJ" = ( /obj/machinery/button/flasher{ id = "hopflash"; @@ -52508,15 +52543,6 @@ }, /turf/open/floor/plasteel, /area/crew_quarters/heads/hop) -"rEb" = ( -/obj/machinery/holopad, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/structure/cable{ - icon_state = "2-4" - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rEq" = ( /obj/effect/landmark/event_spawn, /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ @@ -52653,15 +52679,6 @@ /obj/machinery/teleport/station, /turf/open/floor/plating, /area/teleporter) -"rGM" = ( -/obj/machinery/door/firedoor/border_only{ - dir = 4 - }, -/obj/structure/cable/yellow{ - icon_state = "1-8" - }, -/turf/open/floor/plasteel/dark/telecomms, -/area/ai_monitored/turret_protected/ai) "rHf" = ( /turf/open/floor/engine/vacuum, /area/engine/atmos_distro) @@ -52895,6 +52912,16 @@ }, /turf/open/floor/plating, /area/maintenance/department/electrical) +"rKo" = ( +/obj/machinery/modular_computer/console/preset/netmin{ + dir = 1 + }, +/obj/effect/turf_decal/trimline/purple/filled/line, +/obj/structure/ethernet_cable{ + icon_state = "0-2" + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "rKJ" = ( /obj/structure/rack, /obj/item/wrench, @@ -53123,22 +53150,6 @@ }, /turf/open/floor/plasteel, /area/vacant_room/commissary) -"rRA" = ( -/obj/structure/table/wood, -/obj/item/reagent_containers/food/drinks/bottle/vodka{ - pixel_x = 8; - pixel_y = 5 - }, -/obj/item/reagent_containers/food/drinks/drinkingglass/shotglass{ - pixel_x = 8; - pixel_y = 1 - }, -/obj/effect/spawner/lootdrop/donkpockets{ - pixel_x = -6; - pixel_y = 1 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "rRB" = ( /obj/machinery/light/small{ dir = 1 @@ -53227,6 +53238,12 @@ }, /turf/open/floor/plasteel/white, /area/medical/medbay/central) +"rTD" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "rTL" = ( /obj/structure/cable/yellow{ icon_state = "4-8" @@ -54462,6 +54479,16 @@ }, /turf/open/floor/plasteel/dark, /area/security/interrogation) +"swj" = ( +/obj/structure/window/reinforced, +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/obj/structure/ethernet_cable{ + icon_state = "1-2" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "swt" = ( /obj/structure/cable/yellow{ icon_state = "4-8" @@ -54637,6 +54664,14 @@ "sAu" = ( /turf/open/floor/circuit/telecomms/server, /area/ai_monitored/turret_protected/ai) +"sAA" = ( +/obj/machinery/camera{ + c_tag = "Secondary AI Core"; + dir = 8; + network = list("ss13","rd") + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "sAD" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ dir = 4 @@ -54646,6 +54681,14 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"sAG" = ( +/obj/structure/table/wood, +/obj/item/radio/off{ + pixel_x = -6; + pixel_y = 5 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "sAJ" = ( /obj/effect/spawner/structure/window/reinforced/shutter, /obj/structure/cable{ @@ -54839,6 +54882,24 @@ }, /turf/open/floor/plasteel, /area/engine/atmos) +"sEw" = ( +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/obj/machinery/door/firedoor/border_only, +/obj/machinery/door/airlock/hatch{ + name = "Abandoned Room"; + req_access_txt = "65" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/structure/barricade/wooden/crude, +/obj/effect/mapping_helpers/airlock/locked, +/turf/open/floor/plasteel/grimy, +/area/ai_monitored/turret_protected/aisat_interior) "sEx" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 6 @@ -55210,12 +55271,6 @@ }, /turf/open/floor/plasteel/dark, /area/bridge) -"sLZ" = ( -/obj/machinery/atmospherics/components/unary/thermomachine/freezer/on{ - dir = 4 - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "sMh" = ( /obj/structure/filingcabinet, /obj/machinery/light_switch{ @@ -55537,6 +55592,9 @@ /obj/item/hand_labeler_refill, /turf/open/floor/plating, /area/maintenance/port/aft) +"sTQ" = ( +/turf/closed/wall/r_wall, +/area/maintenance/starboard/aft) "sTW" = ( /obj/structure/chair, /turf/open/floor/plasteel/dark, @@ -55655,12 +55713,35 @@ }, /turf/open/floor/plasteel, /area/security/processing) +"sWg" = ( +/obj/machinery/vending/coffee, +/obj/machinery/airalarm{ + dir = 8; + pixel_x = 24 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "sWv" = ( /obj/effect/turf_decal/trimline/brown/filled/line{ dir = 9 }, /turf/open/floor/plasteel, /area/quartermaster/miningdock) +"sWw" = ( +/obj/structure/cable{ + icon_state = "2-8" + }, +/obj/structure/disposalpipe/segment{ + dir = 10 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 10 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 10 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "sWI" = ( /obj/structure/rack, /obj/item/storage/briefcase, @@ -56114,6 +56195,22 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"tcI" = ( +/obj/machinery/power/terminal{ + dir = 4 + }, +/obj/structure/cable, +/obj/effect/turf_decal/trimline/purple/filled/warning{ + dir = 9 + }, +/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ + dir = 4 + }, +/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "tcS" = ( /obj/machinery/door/airlock/public/glass{ name = "Central Access" @@ -56161,6 +56258,23 @@ /obj/effect/turf_decal/trimline/yellow/filled/line, /turf/open/floor/plasteel, /area/engine/engineering) +"tdM" = ( +/obj/machinery/door/firedoor/border_only{ + dir = 1 + }, +/obj/machinery/door/firedoor/border_only, +/obj/machinery/door/airlock/research/glass{ + name = "Computer Science"; + normalspeed = 0; + req_access_txt = "67" + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/structure/cable{ + icon_state = "1-2" + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "tdV" = ( /obj/effect/turf_decal/stripes/corner{ dir = 1 @@ -56179,6 +56293,12 @@ }, /turf/open/floor/plasteel/white, /area/medical/storage) +"tdX" = ( +/obj/structure/ethernet_cable{ + icon_state = "2-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "tdY" = ( /obj/effect/turf_decal/tile/neutral/fourcorners, /turf/open/floor/plasteel/dark, @@ -56437,13 +56557,6 @@ }, /turf/open/space/basic, /area/space/nearstation) -"tiN" = ( -/obj/machinery/light, -/obj/machinery/computer/ai_server_console{ - dir = 1 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "tjk" = ( /obj/structure/closet, /obj/item/storage/box/donkpockets, @@ -56510,6 +56623,13 @@ }, /turf/open/floor/plasteel/dark, /area/security/detectives_office) +"tkX" = ( +/obj/machinery/light_switch{ + pixel_y = -27 + }, +/obj/machinery/vending/snack/random, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "tlg" = ( /obj/structure/cable{ icon_state = "0-8" @@ -56904,6 +57024,17 @@ /obj/effect/spawner/lootdrop/two_percent_xeno_egg_spawner, /turf/open/floor/engine, /area/science/xenobiology) +"tvh" = ( +/obj/structure/table/wood, +/obj/item/toy/figure/borg{ + pixel_x = -4; + pixel_y = -2 + }, +/obj/machinery/newscaster/security_unit{ + pixel_y = -28 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "tvq" = ( /obj/machinery/portable_atmospherics/canister, /turf/open/floor/plating, @@ -56986,12 +57117,6 @@ }, /turf/open/floor/plasteel/white, /area/science/mixing) -"twt" = ( -/obj/machinery/atmospherics/pipe/simple/general/visible{ - dir = 4 - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "twv" = ( /obj/effect/spawner/structure/window, /obj/machinery/door/firedoor/border_only{ @@ -57568,12 +57693,6 @@ }, /turf/open/floor/plasteel/freezer, /area/crew_quarters/toilet) -"tKI" = ( -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, -/obj/effect/turf_decal/trimline/yellow/filled/warning, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "tKP" = ( /obj/machinery/door/airlock/external{ name = "Escape Pod Four"; @@ -57904,17 +58023,6 @@ }, /turf/open/floor/plasteel, /area/clerk) -"tQv" = ( -/obj/machinery/light{ - dir = 4 - }, -/obj/machinery/atmospherics/components/unary/vent_pump/on{ - dir = 8; - external_pressure_bound = 140; - pressure_checks = 0 - }, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "tQD" = ( /obj/structure/disposalpipe/segment, /turf/open/floor/plasteel, @@ -58169,9 +58277,6 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) -"tXb" = ( -/turf/open/floor/circuit/green/telecomms/mainframe, -/area/ai_monitored/secondarydatacore) "tXk" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ dir = 4 @@ -58443,6 +58548,12 @@ }, /turf/open/floor/plasteel, /area/construction/mining/aux_base) +"ubA" = ( +/obj/effect/turf_decal/trimline/purple/filled/line, +/obj/machinery/portable_atmospherics/canister/nitrogen, +/obj/machinery/atmospherics/components/unary/portables_connector/visible, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "ucg" = ( /obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ dir = 4 @@ -59008,6 +59119,16 @@ }, /turf/open/floor/plating, /area/medical/chemistry) +"uoD" = ( +/obj/structure/ethernet_cable{ + icon_state = "1-8" + }, +/obj/structure/ethernet_cable{ + icon_state = "1-4" + }, +/obj/machinery/light, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "uoF" = ( /obj/machinery/portable_atmospherics/canister/oxygen, /turf/open/floor/plasteel, @@ -59083,6 +59204,12 @@ /obj/effect/turf_decal/trimline/purple/filled/corner, /turf/open/floor/plasteel/white, /area/science/research) +"uqM" = ( +/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ + dir = 4 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "ure" = ( /obj/machinery/firealarm{ dir = 8; @@ -59553,6 +59680,19 @@ /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, /turf/open/floor/plasteel, /area/quartermaster/miningdock) +"uBd" = ( +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/effect/turf_decal/trimline/yellow/filled/warning, +/obj/item/radio/intercom{ + dir = 1; + freerange = 1; + name = "Station Intercom (Telecomms)"; + pixel_x = 28; + pixel_y = -26 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "uBf" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 8 @@ -59703,30 +59843,6 @@ }, /turf/open/floor/plasteel, /area/maintenance/disposal/incinerator) -"uFS" = ( -/obj/machinery/atmospherics/components/unary/portables_connector/visible{ - dir = 4 - }, -/obj/machinery/doorButtons/access_button{ - idDoor = "secondary_aicore_exterior"; - idSelf = "secondary_aicore_controller"; - name = "Secondary AI Core Access Button"; - pixel_x = -24; - pixel_y = 8; - req_one_access_txt = "30;70" - }, -/obj/machinery/doorButtons/airlock_controller{ - idExterior = "secondary_aicore_exterior"; - idInterior = "secondary_aicore_interior"; - idSelf = "secondary_aicore_controller"; - name = "Secondary AI Core Access Console"; - pixel_x = -26; - pixel_y = -6; - req_one_access_txt = "30;70" - }, -/obj/machinery/portable_atmospherics/canister/nitrogen, -/turf/open/floor/circuit/telecomms/server, -/area/ai_monitored/secondarydatacore) "uFW" = ( /obj/effect/landmark/event_spawn, /turf/open/floor/plating, @@ -60171,6 +60287,14 @@ /obj/effect/mapping_helpers/teleport_anchor, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"uOD" = ( +/obj/machinery/airalarm/tcomms{ + dir = 4; + pixel_x = -24 + }, +/obj/machinery/atmospherics/pipe/simple/cyan/hidden, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "uOF" = ( /obj/structure/table/wood, /obj/item/folder/blue, @@ -60219,6 +60343,16 @@ }, /turf/open/floor/plasteel/white, /area/medical/sleeper) +"uPR" = ( +/obj/machinery/ai/networking{ + label = "Computer Science"; + roundstart_connection = "Main Core" + }, +/obj/structure/ethernet_cable{ + icon_state = "0-4" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "uPY" = ( /obj/structure/table, /obj/item/toy/figure/clerk, @@ -60318,24 +60452,6 @@ }, /turf/open/floor/plating, /area/maintenance/starboard/fore) -"uSq" = ( -/obj/machinery/atmospherics/pipe/manifold/scrubbers/hidden/layer4{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "4-8" - }, -/obj/structure/cable{ - icon_state = "1-4" - }, -/obj/structure/cable{ - icon_state = "2-4" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "uSG" = ( /obj/machinery/power/apc{ areastring = "/area/engine/foyer"; @@ -60473,6 +60589,20 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"uWJ" = ( +/obj/structure/cable{ + icon_state = "2-8" + }, +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/structure/disposalpipe/segment{ + dir = 9 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "uWM" = ( /obj/effect/turf_decal/stripes/line{ dir = 8 @@ -60596,6 +60726,49 @@ }, /turf/open/floor/plasteel/dark, /area/science/robotics/lab) +"uXn" = ( +/obj/structure/window/reinforced, +/obj/machinery/atmospherics/pipe/simple/cyan/hidden, +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) +"uXU" = ( +/obj/machinery/camera{ + c_tag = "Telecomms Control Room"; + dir = 4; + network = list("ss13","tcomms") + }, +/obj/structure/table/wood, +/obj/item/reagent_containers/food/drinks/drinkingglass{ + pixel_x = 7; + pixel_y = 6 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass/shotglass{ + pixel_x = -7; + pixel_y = 1 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass/shotglass{ + pixel_y = 1 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass{ + pixel_x = -1; + pixel_y = 6 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass{ + pixel_x = -8; + pixel_y = 6 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass/shotglass{ + pixel_x = 7; + pixel_y = 1 + }, +/obj/machinery/status_display/ai{ + pixel_x = -32 + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "uXZ" = ( /obj/structure/table, /obj/machinery/airalarm{ @@ -60725,6 +60898,9 @@ }, /turf/open/floor/plasteel/white, /area/science/research) +"vaI" = ( +/turf/closed/wall, +/area/crew_quarters/public_lounge) "vaP" = ( /obj/machinery/light, /obj/effect/turf_decal/stripes/line{ @@ -61098,6 +61274,11 @@ }, /turf/open/floor/plasteel, /area/engine/atmos_distro) +"vjt" = ( +/obj/effect/spawner/structure/window/reinforced, +/obj/machinery/atmospherics/pipe/simple/cyan/hidden, +/turf/open/floor/plating, +/area/ai_monitored/secondarydatacore) "vjC" = ( /obj/structure/cable{ icon_state = "1-2" @@ -61196,6 +61377,15 @@ }, /turf/open/floor/plating, /area/maintenance/port) +"vml" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/structure/disposalpipe/segment{ + dir = 4 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "vmm" = ( /turf/closed/wall, /area/ai_monitored/turret_protected/aisat_interior) @@ -61357,6 +61547,9 @@ /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /turf/open/floor/plasteel, /area/hallway/primary/central) +"vrc" = ( +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "vrl" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 1 @@ -61472,6 +61665,12 @@ }, /turf/open/floor/plasteel/dark, /area/science/xenobiology) +"vun" = ( +/obj/effect/landmark/event_spawn, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "vuB" = ( /obj/machinery/atmospherics/components/unary/portables_connector{ dir = 4; @@ -62044,6 +62243,15 @@ /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, /turf/open/floor/plasteel, /area/construction/mining/aux_base) +"vEK" = ( +/obj/machinery/atmospherics/components/unary/vent_pump/on{ + dir = 1; + external_pressure_bound = 140; + plane = -2; + pressure_checks = 0 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "vFa" = ( /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ @@ -62351,6 +62559,15 @@ /obj/effect/turf_decal/trimline/red/filled/line, /turf/open/floor/plasteel, /area/security/brig) +"vKe" = ( +/obj/machinery/holopad, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/obj/structure/cable{ + icon_state = "2-8" + }, +/turf/open/floor/plasteel/grimy, +/area/crew_quarters/public_lounge) "vKp" = ( /turf/closed/wall, /area/engine/foyer) @@ -62385,6 +62602,10 @@ }, /turf/open/floor/plasteel/white, /area/medical/virology) +"vLQ" = ( +/obj/machinery/atmospherics/pipe/manifold4w/cyan/hidden, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "vLR" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 4 @@ -62446,10 +62667,6 @@ }, /turf/open/floor/plasteel/dark, /area/ai_monitored/turret_protected/ai_upload_foyer) -"vMR" = ( -/obj/structure/filingcabinet, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "vMZ" = ( /obj/effect/mapping_helpers/airlock/cyclelink_helper{ dir = 8 @@ -62681,6 +62898,14 @@ }, /turf/open/floor/plasteel/airless/solarpanel, /area/solar/port/aft) +"vRk" = ( +/obj/item/stack/cable_coil, +/obj/effect/decal/cleanable/dirt/dust, +/obj/structure/ethernet_cable{ + icon_state = "2-8" + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "vRA" = ( /obj/structure/disposalpipe/segment, /obj/structure/cable{ @@ -62702,6 +62927,15 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/aft_starboard) +"vSL" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer4{ + dir = 8 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "vTi" = ( /obj/item/shard, /obj/structure/disposalpipe/segment{ @@ -63186,16 +63420,6 @@ icon_state = "platingdmg3" }, /area/maintenance/aft) -"waB" = ( -/obj/structure/table, -/obj/item/stock_parts/subspace/analyzer, -/obj/item/stock_parts/subspace/analyzer, -/obj/item/stock_parts/subspace/analyzer, -/obj/effect/turf_decal/trimline/yellow/filled/line{ - dir = 9 - }, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "waC" = ( /obj/machinery/light, /turf/open/floor/plasteel/dark, @@ -63337,14 +63561,6 @@ }, /turf/open/floor/plasteel, /area/quartermaster/office) -"wer" = ( -/obj/effect/decal/cleanable/dirt/dust, -/obj/structure/frame/machine{ - anchored = 1; - state = 2 - }, -/turf/open/floor/circuit/green/telecomms, -/area/ai_monitored/turret_protected/ai) "weD" = ( /obj/machinery/disposal/deliveryChute{ dir = 8 @@ -63491,6 +63707,12 @@ }, /turf/open/floor/plating, /area/construction) +"wjj" = ( +/obj/machinery/light/small{ + dir = 4 + }, +/turf/open/floor/plating, +/area/ai_monitored/turret_protected/aisat_interior) "wjk" = ( /obj/machinery/flasher{ id = "PCell 2"; @@ -63720,13 +63942,6 @@ }, /turf/open/floor/plasteel/white, /area/medical/chemistry) -"wnI" = ( -/obj/structure/frame/machine{ - anchored = 1; - state = 2 - }, -/turf/open/floor/circuit/green/telecomms/mainframe, -/area/ai_monitored/secondarydatacore) "wnN" = ( /obj/structure/table, /obj/item/storage/toolbox/mechanical{ @@ -64261,6 +64476,14 @@ /obj/effect/spawner/structure/window/reinforced/shutter, /turf/open/floor/plating, /area/engine/engineering) +"wzn" = ( +/obj/structure/cable{ + icon_state = "1-2" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "wzr" = ( /obj/machinery/door/firedoor/border_only{ dir = 1 @@ -64304,6 +64527,10 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/plating, /area/maintenance/starboard/aft) +"wAR" = ( +/obj/structure/table, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "wAX" = ( /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ dir = 1 @@ -64481,21 +64708,6 @@ /obj/effect/turf_decal/trimline/blue/filled/corner, /turf/open/floor/plasteel, /area/hallway/primary/central) -"wEX" = ( -/obj/structure/table/wood, -/obj/item/paper_bin{ - pixel_x = -1; - pixel_y = 6 - }, -/obj/item/pen, -/obj/structure/extinguisher_cabinet{ - pixel_x = -27 - }, -/obj/machinery/atmospherics/components/unary/vent_pump/on/layer2{ - dir = 4 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "wFq" = ( /obj/effect/decal/cleanable/cobweb/cobweb2, /obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ @@ -64666,10 +64878,6 @@ /obj/structure/bookcase/random/reference, /turf/open/floor/carpet, /area/library) -"wJL" = ( -/obj/effect/spawner/structure/window/reinforced/shutter, -/turf/open/floor/plating, -/area/tcommsat/computer) "wKy" = ( /obj/effect/spawner/structure/window/reinforced, /obj/machinery/door/poddoor/shutters/preopen{ @@ -64735,14 +64943,6 @@ }, /turf/open/floor/engine, /area/maintenance/disposal/incinerator) -"wKU" = ( -/obj/machinery/computer/telecomms/traffic{ - dir = 1; - network = "tcommsat" - }, -/obj/effect/turf_decal/trimline/yellow/filled/line, -/turf/open/floor/plasteel/dark, -/area/maintenance/department/tcoms) "wLb" = ( /obj/machinery/disposal/bin, /obj/structure/disposalpipe/trunk, @@ -65203,6 +65403,18 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/central) +"wWN" = ( +/obj/structure/cable{ + icon_state = "1-8" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 9 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 9 + }, +/turf/open/floor/plating, +/area/maintenance/starboard/aft) "wWW" = ( /obj/machinery/disposal/bin, /obj/structure/disposalpipe/trunk{ @@ -65326,6 +65538,18 @@ /obj/effect/turf_decal/trimline/red/filled/line, /turf/open/floor/plasteel, /area/security/brig) +"wYJ" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 10 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "wZb" = ( /obj/machinery/door/firedoor/border_only{ dir = 8 @@ -65356,6 +65580,18 @@ "wZD" = ( /turf/open/floor/plasteel/white, /area/science/nanite) +"wZY" = ( +/obj/machinery/atmospherics/components/unary/vent_pump/on{ + dir = 8; + external_pressure_bound = 140; + plane = -2; + pressure_checks = 0 + }, +/obj/machinery/light{ + dir = 4 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/secondarydatacore) "xam" = ( /obj/effect/landmark/start/security_officer, /obj/effect/turf_decal/trimline/red/filled/line{ @@ -65554,6 +65790,21 @@ }, /turf/open/floor/plasteel, /area/engine/engineering) +"xgE" = ( +/obj/effect/turf_decal/trimline/purple/filled/line{ + dir = 8 + }, +/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ + dir = 5 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 5 + }, +/obj/machinery/light{ + dir = 8 + }, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "xgF" = ( /obj/machinery/light, /obj/effect/turf_decal/trimline/yellow/filled/line, @@ -65576,12 +65827,6 @@ /obj/effect/spawner/lootdrop/maintenance, /turf/open/floor/plating, /area/maintenance/port/aft) -"xgS" = ( -/obj/structure/cable/yellow{ - icon_state = "1-8" - }, -/turf/open/floor/plating, -/area/ai_monitored/storage/satellite) "xhk" = ( /obj/machinery/atmospherics/pipe/manifold/supply/hidden/layer2{ dir = 1 @@ -66206,25 +66451,6 @@ }, /turf/open/floor/plasteel/white, /area/science/xenobiology) -"xwL" = ( -/obj/structure/table/wood, -/obj/item/flashlight/lamp{ - pixel_x = -4; - pixel_y = 7 - }, -/obj/item/toy/figure/borg{ - pixel_x = -4; - pixel_y = -2 - }, -/obj/item/phone{ - pixel_x = 7; - pixel_y = 1 - }, -/obj/machinery/newscaster/security_unit{ - pixel_y = -28 - }, -/turf/open/floor/plasteel/grimy, -/area/ai_monitored/turret_protected/aisat_interior) "xwU" = ( /obj/structure/closet/secure_closet/atmospherics, /obj/machinery/light{ @@ -66316,12 +66542,6 @@ /obj/structure/window/reinforced, /turf/open/floor/plasteel/white, /area/engine/atmos_distro) -"xyb" = ( -/obj/structure/chair/office/dark{ - dir = 8 - }, -/turf/open/floor/plasteel/grimy, -/area/tcommsat/computer) "xyG" = ( /obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ dir = 4 @@ -66702,6 +66922,23 @@ /obj/machinery/portable_atmospherics/canister/oxygen, /turf/open/floor/plasteel, /area/maintenance/disposal/incinerator) +"xIu" = ( +/obj/structure/table, +/obj/item/stock_parts/subspace/analyzer, +/obj/item/stock_parts/subspace/analyzer, +/obj/item/stock_parts/subspace/analyzer, +/obj/effect/turf_decal/trimline/yellow/filled/line{ + dir = 9 + }, +/obj/machinery/requests_console{ + announcementConsole = 1; + department = "Telecomms Admin"; + departmentType = 5; + name = "Telecomms RC"; + pixel_y = 30 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "xIJ" = ( /obj/structure/disposalpipe/junction/flip{ dir = 4 @@ -66805,6 +67042,14 @@ /obj/item/twohanded/required/kirbyplants/random, /turf/open/floor/carpet, /area/library) +"xLc" = ( +/obj/effect/decal/cleanable/dirt/dust, +/obj/structure/frame/machine{ + anchored = 1; + state = 2 + }, +/turf/open/floor/catwalk_floor/telecomms, +/area/ai_monitored/turret_protected/ai) "xLR" = ( /obj/structure/table, /obj/item/flashlight/lamp/green{ @@ -67118,22 +67363,6 @@ }, /turf/open/floor/plating, /area/maintenance/port/aft) -"xTe" = ( -/obj/machinery/door/firedoor/border_only, -/obj/machinery/door/firedoor/border_only{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ - dir = 1 - }, -/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer2{ - dir = 1 - }, -/obj/structure/cable{ - icon_state = "1-2" - }, -/turf/open/floor/plating, -/area/maintenance/starboard/aft) "xTZ" = ( /obj/structure/cloth_curtain{ color = "#99ccff" @@ -67209,12 +67438,14 @@ }, /turf/open/floor/plasteel, /area/science/robotics/lab) -"xUW" = ( -/obj/structure/frame/machine{ - anchored = 1; - state = 2 +"xUs" = ( +/obj/structure/window/reinforced{ + dir = 4 }, -/turf/open/floor/circuit/green/telecomms, +/obj/structure/cable/yellow{ + icon_state = "1-2" + }, +/turf/open/floor/catwalk_floor/telecomms, /area/ai_monitored/turret_protected/ai) "xVm" = ( /obj/effect/turf_decal/trimline/purple/filled/corner{ @@ -67236,6 +67467,21 @@ }, /turf/open/floor/carpet, /area/crew_quarters/fitness) +"xVZ" = ( +/obj/machinery/light{ + dir = 1 + }, +/obj/structure/cable/yellow{ + icon_state = "4-8" + }, +/obj/effect/turf_decal/trimline/yellow/filled/line{ + dir = 1 + }, +/obj/machinery/newscaster{ + pixel_y = 32 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "xWd" = ( /obj/structure/disposalpipe/segment{ dir = 4 @@ -67310,6 +67556,35 @@ }, /turf/open/floor/plasteel/white, /area/science/explab) +"xWX" = ( +/obj/effect/turf_decal/trimline/yellow/filled/line, +/obj/machinery/camera{ + c_tag = "Telecomms Maintenance"; + dir = 1; + network = list("ss13","tcomms") + }, +/obj/machinery/computer/security/telescreen{ + dir = 1; + name = "Telecomms Camera Monitor"; + network = list("tcomms"); + pixel_x = 30; + pixel_y = -37 + }, +/obj/structure/table, +/obj/effect/spawner/lootdrop/donkpockets{ + pixel_x = -6; + pixel_y = 1 + }, +/obj/item/reagent_containers/food/drinks/bottle/vodka{ + pixel_x = 8; + pixel_y = 5 + }, +/obj/item/reagent_containers/food/drinks/drinkingglass/shotglass{ + pixel_x = 8; + pixel_y = 1 + }, +/turf/open/floor/plasteel/dark, +/area/maintenance/department/tcoms) "xXd" = ( /obj/structure/cable{ icon_state = "4-8" @@ -67983,6 +68258,19 @@ }, /turf/open/floor/plasteel, /area/hallway/primary/port) +"yiA" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/obj/structure/chair/office/light{ + dir = 1 + }, +/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer4{ + dir = 4 + }, +/obj/effect/landmark/start/yogs/network_admin, +/turf/open/floor/plasteel/dark, +/area/ai_monitored/secondarydatacore) "yiM" = ( /obj/machinery/door/airlock/research{ name = "Xenobiology Lab"; @@ -96544,7 +96832,7 @@ aZM aZM aZM aZM -waB +xIu lLF uzu wrd @@ -96805,10 +97093,10 @@ bNk bnS uzR wrd -bVJ -wJL -wJL -pJB +lik +eFH +eFH +vaI aaa xJL gGf @@ -97062,12 +97350,12 @@ kUo kmz pss bZl -bVJ -azq -rRA -pJB -pJB -aJw +lik +oiG +fzC +vaI +eFH +vaI hvG aJq sfF @@ -97319,12 +97607,12 @@ wrd xYw okh ozR -bVJ -pSY -lhk -rdw -pvf -aJw +lik +gdO +dcO +uXU +bqP +vaI hvG aJq jFt @@ -97573,16 +97861,16 @@ qZK vAP mUY wrd -baa +xVZ ehM fYt -bVJ -pTL -axV -rdR -xyb -aJw -pvo +lik +iPL +vrc +uqM +jXf +grx +hvG sXZ leZ eVO @@ -97832,13 +98120,13 @@ rFp oSn uvQ nUo -tKI -pmR -dcc -qsZ -lFe -rEb -cyZ +uBd +bSY +hsg +vun +ksh +vKe +kyu hsn sYk doM @@ -98087,15 +98375,15 @@ rJJ vAP pKD wrd -pWn -hJQ -lrF -bVJ -hYy -lhk -rfJ -gOE -aJw +fai +ndG +xWX +lik +nDH +vrc +eUg +vrc +grx hvG sYv tRl @@ -98345,14 +98633,14 @@ mrS mrS yeb izo -fPM -wKU -bVJ -rzx -iRV -aSV -agz -aJw +bdW +nSy +lik +jQM +imV +sWg +tkX +vaI hvG aJq fCO @@ -98603,13 +98891,13 @@ mDO nqR cfg wys -hzx -bVJ -dne -bxL -pJB -pJB -aJw +cWA +lik +jmi +vrc +vaI +eFH +vaI hvG aJq rPH @@ -98861,10 +99149,10 @@ aFS lSP qBE wrd -bVJ -wJL -wJL -pJB +lik +eFH +eFH +vaI aaa msD gGf @@ -108185,10 +108473,10 @@ nnx lxF lbE vmm -vMR -wEX -lZD -xwL +ckj +ksx +sAG +tvh gtB pEf aaa @@ -108441,11 +108729,11 @@ snB cqk bhL snB -dEd -pyZ -dTb -nfC -hYX +sEw +geT +cXZ +hXq +okV eeK pEf gXs @@ -108691,7 +108979,7 @@ tgv hZg cBP uIU -xgS +qGt lmN pRt kyA @@ -108699,10 +108987,10 @@ kik eEZ jWq vmm -qzd -qLi -mtW -tiN +lnx +kfc +hnc +wjj gtB pEf gXs @@ -110235,11 +110523,11 @@ cva cva cva gQa -jzm -fIs -rGM -hbO -lbr +kYm +xUs +fqF +eLY +qEZ yap cva cva @@ -110490,15 +110778,15 @@ pEf pEf cva cva -abx +bNZ nLw -nDW +uXn enZ nSN xlV -dFJ +oAU rjo -wer +xLc cva cva pEf @@ -110747,15 +111035,15 @@ pEf koy cva cva -lHO -rjo -rqW -rjo -hJq -sAu -dFJ -rjo -xlV +vRk +lRc +swj +lRc +exu +cXC +dNV +lRc +pek cva cva vUh @@ -111004,15 +111292,15 @@ pEf pEf cva cva -xUW +lWF rjo -rqW +pOM jTn nVK enZ -kSZ +nxI pyn -ikV +coc cva cva pEf @@ -111263,11 +111551,11 @@ cva cva cva mWE -qJg -aSy -nJj -nTI -pnR +pbe +irI +gID +oPn +qEZ kcr cva cva @@ -117626,7 +117914,7 @@ eRE waa oaO bvK -fdU +jgb bys bzM aDa @@ -117659,7 +117947,7 @@ atN atN atN atN -cOe +sTQ fXS cOe gpq @@ -117909,13 +118197,13 @@ qot gFN iKk oGM -mwf +aJI oxg -uFS -sLZ -ief -tXb -oGM +gfs +uOD +oas +kZA +uPR oGM fXS cOe @@ -118142,7 +118430,7 @@ ekZ bvK bxm byu -dbJ +jxV bCf aGs bvK @@ -118164,18 +118452,18 @@ bQZ alX xtJ gFN -nXh -oGM -mQY -nlV -gdI -kJz -mSg -wnI +hSS oGM +hHT +lNu +cxB +cxB +fqr +tdX +uoD oGM fXS -chH +cOe cNW cOe frB @@ -118421,15 +118709,15 @@ bQZ alY dqh qoK -gvV +kwt oGM -fKM +fTa oGM oxg oxg -dBH -pDa -oGM +fqr +dNX +eQw oGM fXS cNW @@ -118678,15 +118966,15 @@ alj alj aXb xix -loK -bRR -hYY -gDs -fFO +inv +tdM +tcI +xgE +nLQ oxg -twt -wnI -oGM +fqr +dNX +oWS oGM fXS bNA @@ -118935,15 +119223,15 @@ alk alk pWH pgx -cAP +rDw oGM -pYv -goW -hOU +eTo +iQG +kIf oxg -tQv -iiJ -oGM +fqr +fud +fPz oGM fXS cOe @@ -119194,13 +119482,13 @@ aRv bQZ bQZ oGM -oGM -oGM -oGM -oGM -oGM -oGM -oGM +kNH +wYJ +lJc +oxg +fqr +dNX +mOp oGM fXS cjE @@ -119445,20 +119733,20 @@ cOe cOe buU cOe -cwH +cOe alZ aMC -cOe thv cOe -cOe -cOe -cOe -cOe oGM +lcu +yiA +rKo +jyT +bFQ +rTD oGM oGM -cOe fXS cjD cjD @@ -119702,20 +119990,20 @@ lNU cNW qHY cNW -cNW +bNB cdR xHc -bNB cNW cOe -cmo -cNW -iVk -cOe -cOe -ceR -fIH -cOe +oGM +gXu +pQd +qrf +vjt +elB +cxB +oGM +wAR mfN cjD bQq @@ -119958,22 +120246,22 @@ axl cNW cNW xSu -bMB cNW cNW -aMC -cNW -cNW -cOe -cOe -bNB cNW +aMC cNW -axl cOe -cNW -qjZ -uSq +oGM +gjO +vSL +ubA +vjt +vLQ +vEK +oGM +bNA +hnA kQW iwk mNK @@ -120215,22 +120503,22 @@ cNZ cNZ bSm aWg -cNZ -cNZ -cNZ -aMD -dMA -jPU -dMA -aue -dMA -dMA -dMA -frD -piV -xTe -bCw -bKB +fdg +bMB +cNW +vml +cNW +cOe +oGM +hcP +nxA +dFr +oxg +wZY +sAA +oGM +cou +nvD cjD shT clz @@ -120472,22 +120760,22 @@ nex cNW cNW cNW +kKc +cOe cNW +vml cNW -woo -cNW -cNW -cNW -cNW -cNW -cNW -cNW -cNW -umE -cNW -cNW -arG -cNW +cOe +oGM +oGM +oGM +oGM +oGM +oGM +oGM +oGM +cOe +euG cjD cjD cjD @@ -120729,22 +121017,22 @@ iKq iKq eoH cNW -cou -cou -cae -cmo -cNW -iKq -iKq -cCG -cNW -ccW -hLb -jjr -cNW -iKq -iKq -hNs +sWw +rmq +rmq +uWJ +wzn +wzn +wzn +wzn +wzn +wzn +wzn +pit +wzn +gUV +nce +wWN cNW gXs aaf @@ -120988,20 +121276,20 @@ iKq euJ cOe cOe -cae cOe -vKX -iKq -iKq -iKq -yeN +cNW +kMz cOe -wZs -jjr +cOe +axl cNW -iKq -iKq -iKq +bNB +cOe +gEx +lJN +iKx +cOe +cdR cNW aaa aaa @@ -121243,22 +121531,22 @@ iKq iKq iKq cNW -chH cNW cNW +woo cNW cNW -iKq -iKq -iKq cNW -chH -cOe -tPY cNW -iKq -iKq -iKq +cNW +cNW +cNW +cNW +umE +cNW +cNW +arG +cNW cNW gXs gXs @@ -121500,22 +121788,22 @@ cNW bPp bPp cNW +cou +cou +cae +cmo cNW +iKq +iKq +cCG cNW -aaf -pEf -cNW -bPp -bPp -bPp -cNW -cNW -cNW -kRp +ccW +hLb +jjr cNW iKq iKq -iKq +hNs cNW aoV aaa @@ -121755,20 +122043,20 @@ aaf aaa aaa aaf -aaa -aaa -aoV -aaf -aaf -pEf -aaf -aaa -aaa -aaa -aaf -aaf +gXs cNW -szB +cOe +cOe +cae +cOe +vKX +iKq +iKq +iKq +yeN +cOe +wZs +jjr cNW iKq iKq @@ -122013,23 +122301,23 @@ aaa aaa aaf aaa -aaa -aoV -aaa -aaa -aag -aaf -aaa -aaa -aaa -aaa -aaf cNW -jSR +chH +cNW cNW cNW cNW +iKq +iKq +iKq cNW +chH +cOe +tPY +cNW +iKq +iKq +iKq cNW gXs gXs @@ -122270,24 +122558,24 @@ aaa aaa aaf aaa -aaa -aaa -aaa -aaa -pEf -aaf -aaa -aaa -aaa -aaa +cNW +cNW +cNW aaf -aag -aag -aag -aoV -aaa -aaa -aoV +pEf +cNW +gob +bPp +bPp +cNW +cNW +cNW +kRp +cNW +iKq +iKq +iKq +cNW aaa aaa aaa @@ -122528,23 +122816,23 @@ aaa aag aaa aaa -aaa -aaa -aaa +aoV +aaf +aaf pEf +aaf aaa aaa aaa -aaa -aaa -aaa -aaa -aag -aaa -aaa -aaa -aaa -aaa +aaf +aaf +cNW +szB +cNW +iKq +iKq +iKq +cNW aaa aaa aaa @@ -122785,23 +123073,23 @@ aaa aag aaa aaa +aoV aaa aaa -aaa -pEf -aaa -aaa -aaa -aaa -aaa -aaa -aaa +aag aaf aaa aaa aaa aaa -aaa +aaf +cNW +jSR +cNW +cNW +cNW +cNW +cNW aaa aaa aaa @@ -123045,20 +123333,20 @@ aaa aaa aaa aaa +pEf aaf aaa aaa aaa aaa -aaa -aaa -aaa aaf +aag +aag +aag +aoV aaa aaa -aaa -aaa -aaa +aoV aaa aaa aaa @@ -123302,15 +123590,15 @@ aaa aaa aaa aaa +pEf aaa aaa aaa aaa -aae aaa aaa aaa -aaf +aag aaa aaa aaa @@ -123559,7 +123847,7 @@ aaa aaa aaa aaa -aaa +pEf aaa aaa aaa @@ -123816,6 +124104,7 @@ aaa aaa aaa aaa +aaf aaa aaa aaa @@ -123823,8 +124112,7 @@ aaa aaa aaa aaa -aaa -aaa +aaf aaa aaa aaa @@ -124067,9 +124355,7 @@ aaf aaa aaa aaa -aaf -aaa -aaa +kAy aaa aaa aaa @@ -124079,9 +124365,11 @@ aaa aaa aaa aaa +aae aaa aaa aaa +aaf aaa aaa aaa @@ -124338,7 +124626,7 @@ aaa aaa aaa aaa -aaa +aaf aaa aaa aaa diff --git a/_maps/map_files/YogsDelta/YogsDelta.dmm b/_maps/map_files/YogsDelta/YogsDelta.dmm index 2273af75c1c4..a50c608a5fe8 100644 --- a/_maps/map_files/YogsDelta/YogsDelta.dmm +++ b/_maps/map_files/YogsDelta/YogsDelta.dmm @@ -66011,9 +66011,6 @@ /obj/effect/turf_decal/tile/neutral{ dir = 8 }, -/obj/machinery/computer/ai_control_console{ - dir = 1 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/turret_protected/aisat_interior) "cam" = ( @@ -66054,9 +66051,6 @@ /obj/effect/turf_decal/tile/neutral{ dir = 8 }, -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/turret_protected/aisat_interior) "cao" = ( @@ -81321,9 +81315,6 @@ /turf/open/floor/plating, /area/maintenance/port/aft) "cAD" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, /turf/open/floor/plasteel/dark, /area/ai_monitored/secondarydatacore) "cAE" = ( @@ -127272,7 +127263,6 @@ /obj/structure/table/reinforced, /obj/item/aicard, /obj/effect/turf_decal/bot, -/obj/item/circuitboard/computer/ai_upload_download, /obj/item/disk/holodisk/tutorial/AICore, /turf/open/floor/plasteel, /area/crew_quarters/heads/hor) diff --git a/_maps/map_files/Yogsmeta/Yogsmeta.dmm b/_maps/map_files/Yogsmeta/Yogsmeta.dmm index f1be506f6233..c4d7b4106341 100644 --- a/_maps/map_files/Yogsmeta/Yogsmeta.dmm +++ b/_maps/map_files/Yogsmeta/Yogsmeta.dmm @@ -58804,7 +58804,6 @@ /obj/machinery/status_display/ai{ pixel_y = 31 }, -/obj/machinery/computer/ai_control_console, /turf/open/floor/plasteel/grimy, /area/tcommsat/computer) "iox" = ( @@ -60186,9 +60185,6 @@ /obj/effect/turf_decal/stripes/line{ dir = 6 }, -/obj/structure/sign/plaques/ai_password{ - pixel_x = 32 - }, /turf/open/floor/plasteel/white, /area/crew_quarters/heads/hor) "jlS" = ( @@ -60545,9 +60541,6 @@ /area/maintenance/starboard) "jzO" = ( /obj/machinery/light/small, -/obj/machinery/computer/ai_resource_distribution{ - dir = 1 - }, /obj/machinery/camera{ c_tag = "Telecomms - Control Room"; dir = 1; @@ -73004,7 +72997,6 @@ "rTF" = ( /obj/structure/table, /obj/item/aicard, -/obj/item/circuitboard/computer/ai_upload_download, /obj/item/disk/holodisk/tutorial/AICore, /turf/open/floor/plasteel/cafeteria{ dir = 5 @@ -77087,9 +77079,6 @@ /turf/open/floor/plasteel/dark, /area/ai_monitored/secondarydatacore) "uDh" = ( -/obj/machinery/computer/ai_resource_distribution{ - dir = 8 - }, /obj/structure/cable{ icon_state = "1-2" }, diff --git a/code/__DEFINES/ai.dm b/code/__DEFINES/ai.dm index 85ea68c70876..ffcab9c59e37 100644 --- a/code/__DEFINES/ai.dm +++ b/code/__DEFINES/ai.dm @@ -4,13 +4,17 @@ ///Temperature limit of all AI machinery #define AI_TEMP_LIMIT 288.15 //15C, much hotter than a normal server room for leniency :) +///How long the AI can stay in the black-box before it's fully destroyed +#define AI_BLACKBOX_LIFETIME 5 MINUTES +///How much CPU we need to use to revive the AI +#define AI_BLACKBOX_PROCESSING_REQUIREMENT 2500 ///How many ticks can an AI data core store? When this amount of ticks have passed while it's in an INVALID state it can no longer be used by an AI -#define MAX_AI_DATA_CORE_TICKS 45 +#define MAX_AI_DATA_CORE_TICKS (45 * (20 / SSair.wait)) ///How much power does the AI date core use while being in a valid state. This is also the base heat output. (Divide by heat capacity to get actual temperature increase) #define AI_DATA_CORE_POWER_USAGE 7500 -///How many ticks can an expanion bus store. If it reaches 0 the resources will no longer be available. -#define MAX_AI_EXPANSION_TICKS 15 +///How many ticks can a server cabinet store. If it reaches 0 the resources will no longer be available. +#define MAX_AI_SERVER_CABINET_TICKS (15 * (20 / SSair.wait)) //AI Project Categories. @@ -19,6 +23,7 @@ #define AI_PROJECT_INDUCTION "Induction" #define AI_PROJECT_SURVEILLANCE "Surveillance" #define AI_PROJECT_EFFICIENCY "Efficiency" +#define AI_PROJECT_CROWD_CONTROL "Crowd Control" #define AI_PROJECT_MISC "Misc." //Update this list if you add any new ones, else the category won't show up in the UIs GLOBAL_LIST_INIT(ai_project_categories, list( @@ -27,6 +32,7 @@ GLOBAL_LIST_INIT(ai_project_categories, list( AI_PROJECT_SURVEILLANCE, AI_PROJECT_INDUCTION, AI_PROJECT_EFFICIENCY, + AI_PROJECT_CROWD_CONTROL, AI_PROJECT_MISC )) @@ -54,10 +60,41 @@ GLOBAL_LIST_INIT(ai_project_categories, list( //Self explanatory. 1 bitcoin is equals to 1 CPU * AI_RESEARCH_PER_CPU -//EXAMPLE (with initial values as of feature introduction) -//20 free CPU. 10 are used for research, 10 are used for bitcoin -//10 * AI_RESEARCH_PER_CPU = 85 bitcoin per tick. Modified for scaling 85*0.54=46 -//46 * AI_BITCOIN_PRICE = 2,3 credits per 2 seconds (2070 credits per 30 min) -#define MAX_AI_BITCOIN_MINED_PER_TICK 350 -//Self explanatory, see MAX_AI_BITCOIN_MINED_PER_TICK * this = max money 1 AI can contribute per tick. (17,5 credits every 2 seconds, max 63k over 2 hours) -#define AI_BITCOIN_PRICE 0.05 +#define MAX_AI_BITCOIN_MINED_PER_TICK 250 +//Self explanatory, see MAX_AI_BITCOIN_MINED_PER_TICK * this = max money 1 network can contribute per tick. (17,5 credits every 2 seconds, max 63k over 2 hours) +#define AI_BITCOIN_PRICE 0.025 + + +//Self explanatory. 1 point is equals to 1 CPU * AI_RESEARCH_PER_CPU. Higher value = can use more CPU and get benefits +#define MAX_AI_REGULAR_RESEARCH_PER_TICK 500 +//Self explanatory. Lower value = more CPU equals less points. Station makes approx. 56 points per tick. This results in 25 (50% gain) +#define AI_REGULAR_RESEARCH_POINT_MULTIPLIER 0.05 + + +//How much RAM and CPU a core needs locally to be functional +#define AI_CORE_CPU_REQUIREMENT 1 +#define AI_CORE_RAM_REQUIREMENT 1 + +//For network based research and tasks. Since each network are going to contribute to a "global" pool of research there's no point in making this more complicated or modular +//Adding an entry here automatically adds it to the UI and allows CPU to be allocated. Just use your define in the network process() to do stuff +#define AI_CRYPTO "Cryptocurrency Mining" +#define AI_RESEARCH "Research Assistance" +#define AI_REVIVAL "AI Restoration" + +GLOBAL_LIST_INIT(possible_ainet_activities, list( + "[AI_CRYPTO]", + "[AI_RESEARCH]", + "[AI_REVIVAL]" +)) + +GLOBAL_LIST_INIT(ainet_activity_tagline, list( + "[AI_CRYPTO]" = "Use CPU to generate credits!", + "[AI_RESEARCH]" = "Use CPU to generate regular research points!", + "[AI_REVIVAL]" = "Revive a dead AI using CPU!" +)) + +GLOBAL_LIST_INIT(ainet_activity_description, list( + "[AI_CRYPTO]" = "Using CPU to mine NTCoin should allow for a meager sum of passive credit income.", + "[AI_RESEARCH]" = "Allocating additional CPU to the research servers should allow for increased point gain. Not to be confused with AI Research points.", + "[AI_REVIVAL]" = "If you've inserted a volatile neural core into a connected data core this will revive it using CPU." +)) diff --git a/code/__DEFINES/footsteps.dm b/code/__DEFINES/footsteps.dm index b1af0b7cd6f5..a95acefa16f6 100644 --- a/code/__DEFINES/footsteps.dm +++ b/code/__DEFINES/footsteps.dm @@ -6,6 +6,7 @@ #define FOOTSTEP_GRASS "grass" #define FOOTSTEP_WATER "water" #define FOOTSTEP_LAVA "lava" +#define FOOTSTEP_CATWALK "catwalk" //barefoot sounds #define FOOTSTEP_WOOD_BAREFOOT "woodbarefoot" #define FOOTSTEP_WOOD_CLAW "woodclaw" @@ -71,6 +72,12 @@ GLOBAL_LIST_INIT(footstep, list( 'sound/effects/footstep/lava1.ogg', 'sound/effects/footstep/lava2.ogg', 'sound/effects/footstep/lava3.ogg'), 100, 0), + FOOTSTEP_CATWALK = list(list( + 'sound/effects/footstep/catwalk1.ogg', + 'sound/effects/footstep/catwalk2.ogg', + 'sound/effects/footstep/catwalk3.ogg', + 'sound/effects/footstep/catwalk4.ogg', + 'sound/effects/footstep/catwalk5.ogg'), 100, 1), )) //bare footsteps lists GLOBAL_LIST_INIT(barefootstep, list( diff --git a/code/__DEFINES/jobs.dm b/code/__DEFINES/jobs.dm index d1e34bfe10c3..920f8bae1a55 100644 --- a/code/__DEFINES/jobs.dm +++ b/code/__DEFINES/jobs.dm @@ -65,12 +65,12 @@ #define JOB_DISPLAY_ORDER_CHIEF_ENGINEER 7 #define JOB_DISPLAY_ORDER_STATION_ENGINEER 8 #define JOB_DISPLAY_ORDER_ATMOSPHERIC_TECHNICIAN 9 -#define JOB_DISPLAY_ORDER_NETWORK_ADMIN 10 -#define JOB_DISPLAY_ORDER_AI 11 -#define JOB_DISPLAY_ORDER_CYBORG 12 -#define JOB_DISPLAY_ORDER_RESEARCH_DIRECTOR 13 -#define JOB_DISPLAY_ORDER_SCIENTIST 14 -#define JOB_DISPLAY_ORDER_ROBOTICIST 15 +#define JOB_DISPLAY_ORDER_AI 10 +#define JOB_DISPLAY_ORDER_CYBORG 11 +#define JOB_DISPLAY_ORDER_RESEARCH_DIRECTOR 12 +#define JOB_DISPLAY_ORDER_SCIENTIST 13 +#define JOB_DISPLAY_ORDER_ROBOTICIST 14 +#define JOB_DISPLAY_ORDER_NETWORK_ADMIN 15 #define JOB_DISPLAY_ORDER_QUARTERMASTER 16 #define JOB_DISPLAY_ORDER_CARGO_TECHNICIAN 17 #define JOB_DISPLAY_ORDER_SHAFT_MINER 18 diff --git a/code/__DEFINES/layers.dm b/code/__DEFINES/layers.dm index b7389061fba6..6f8bf703e1a9 100644 --- a/code/__DEFINES/layers.dm +++ b/code/__DEFINES/layers.dm @@ -28,6 +28,7 @@ #define LATTICE_LAYER 2.2 #define DISPOSAL_PIPE_LAYER 2.25 #define GAS_PIPE_HIDDEN_LAYER 2.35 //layer = initial(layer) + piping_layer / 1000 in atmospherics/update_icon() to determine order of pipe overlap +#define ETHERNET_LAYER 2.38 #define WIRE_LAYER 2.4 #define WIRE_TERMINAL_LAYER 2.45 #define UNDER_CATWALK 2.454 diff --git a/code/__DEFINES/machines.dm b/code/__DEFINES/machines.dm index 28f8d9c72679..3d54c714952d 100644 --- a/code/__DEFINES/machines.dm +++ b/code/__DEFINES/machines.dm @@ -47,6 +47,7 @@ #define MC_CHARGE "CHARGE" #define MC_AI "AI" #define MC_SENSORS "SENSORS" +#define MC_AI_NETWORK "AINETWORK" //NTNet stuff, for modular computers // NTNet module-configuration values. Do not change these. If you need to add another use larger number (5..6..7 etc) diff --git a/code/__HELPERS/cmp.dm b/code/__HELPERS/cmp.dm index bcba85f394dd..765e59cadd27 100644 --- a/code/__HELPERS/cmp.dm +++ b/code/__HELPERS/cmp.dm @@ -29,6 +29,9 @@ GLOBAL_VAR_INIT(cmp_field, "name") /proc/cmp_records_dsc(datum/data/record/a, datum/data/record/b) return sorttext(a.fields[GLOB.cmp_field], b.fields[GLOB.cmp_field]) +/proc/cmp_ai_record_dsc(a, b) + return b["score"] - a["score"] + /proc/cmp_ckey_asc(client/a, client/b) return sorttext(b.ckey, a.ckey) diff --git a/code/__HELPERS/game.dm b/code/__HELPERS/game.dm index 1b4c66595608..e6422a43fd47 100644 --- a/code/__HELPERS/game.dm +++ b/code/__HELPERS/game.dm @@ -8,6 +8,10 @@ #define Z_TURFS(ZLEVEL) block(locate(1,1,ZLEVEL), locate(world.maxx, world.maxy, ZLEVEL)) #define CULT_POLL_WAIT 2400 +#define UNDERFLOOR_HIDDEN 0 +#define UNDERFLOOR_VISIBLE 1 +#define UNDERFLOOR_INTERACTABLE 2 + /proc/get_area_name(atom/X, format_text = FALSE, is_sensor = FALSE) var/area/A = isarea(X) ? X : get_area(X) if(!A) diff --git a/code/__HELPERS/unsorted.dm b/code/__HELPERS/unsorted.dm index 1fef6469022b..c44890abc8ea 100644 --- a/code/__HELPERS/unsorted.dm +++ b/code/__HELPERS/unsorted.dm @@ -1652,3 +1652,77 @@ GLOBAL_DATUM_INIT(dview_mob, /mob/dview, new) return call(source, proctype)(arglist(arguments)) #define TURF_FROM_COORDS_LIST(List) (locate(List[1], List[2], List[3])) + + +/proc/tgui_login_data(mob/user, obj/machine, silicon_access = TRUE, admin_ghost_access = TRUE, access_requirement) + var/list/data = list() + if(!user || (!machine && !access_requirement)) + return data + + if(issilicon(user) && silicon_access) + var/mob/living/silicon/borg = user + data["username"] = borg.name + data["has_access"] = TRUE + + if(IsAdminGhost(user) && admin_ghost_access) + data["username"] = user.client.holder.admin_signature + data["has_access"] = TRUE + + if(ishuman(user)) + var/mob/living/carbon/human/H = user + var/username = H.get_authentification_name("Unknown") + data["username"] = H.get_authentification_name("Unknown") + if(username != "Unknown") + var/datum/data/record/record + for(var/RP in GLOB.data_core.general) + var/datum/data/record/R = RP + if(!istype(R)) + continue + if(R.fields["name"] == username) + record = R + break + if(record) + if(istype(record.fields["photo_front"], /obj/item/photo)) + var/obj/item/photo/P1 = record.fields["photo_front"] + var/icon/picture = icon(P1.picture.picture_image) + picture.Crop(10, 32, 22, 22) + var/md5 = md5(fcopy_rsc(picture)) + + if(!SSassets.cache["photo_[md5]_cropped.png"]) + SSassets.transport.register_asset("photo_[md5]_cropped.png", picture) + SSassets.transport.send_assets(user, list("photo_[md5]_cropped.png" = picture)) + + data["user_image"] = SSassets.transport.get_asset_url("photo_[md5]_cropped.png") + if(machine) + data["has_access"] = machine.check_access(user.get_idcard()) + else + var/obj/item/id_giver = user.get_idcard() + var/access_list = id_giver.GetAccess() + data["has_access"] = (access_requirement in access_list) + + return data + +/proc/tgui_login_act(mob/user, obj/machine, silicon_access = TRUE, admin_ghost_access = TRUE, access_requirement) + if(!user || (!machine && !access_requirement)) + return FALSE + + if(issilicon(user) && silicon_access) + return TRUE + + if(IsAdminGhost(user) && admin_ghost_access) + return TRUE + + var/mob/living/carbon/human/H = user + if(!istype(H)) + return FALSE + + if(machine) + if(machine.check_access(H.get_idcard())) + return TRUE + else + var/obj/item/id_giver = H.get_idcard() + var/access_list = id_giver.GetAccess() + if(access_requirement in access_list) + return TRUE + + return FALSE diff --git a/code/_globalvars/lists/objects.dm b/code/_globalvars/lists/objects.dm index 331f30de8bd1..eb469d6bd9e3 100644 --- a/code/_globalvars/lists/objects.dm +++ b/code/_globalvars/lists/objects.dm @@ -1,4 +1,5 @@ GLOBAL_LIST_EMPTY(cable_list) //Index for all cables, so that powernets don't have to look through the entire world all the time +GLOBAL_LIST_EMPTY(ethernet_cable_list) //Index for all ethernet cables, so that ainets don't have to look through the entire world all the time GLOBAL_LIST_EMPTY(portals) //list of all /obj/effect/portal GLOBAL_LIST_EMPTY(airlocks) //list of all airlocks GLOBAL_LIST_EMPTY(mechas_list) //list of all mechs. Used by hostile mobs target tracking. @@ -8,7 +9,7 @@ GLOBAL_LIST_EMPTY(navigation_computers) //list of all /obj/machinery/computer GLOBAL_LIST_EMPTY(syndicate_shuttle_boards) //important to keep track of for managing nukeops war declarations. GLOBAL_LIST_EMPTY(navbeacons) //list of all bot nagivation beacons, used for patrolling. GLOBAL_LIST_EMPTY(teleportbeacons) //list of all tracking beacons used by teleporters -GLOBAL_LIST_EMPTY(deliverybeacons) //list of all MULEbot delivery beacons. +GLOBAL_LIST_EMPTY(deliverybeacons) //lisAt of all MULEbot delivery beacons. GLOBAL_LIST_EMPTY(deliverybeacontags) //list of all tags associated with delivery beacons. GLOBAL_LIST_EMPTY(nuke_list) GLOBAL_LIST_EMPTY(alarmdisplay) //list of all machines or programs that can display station alerts diff --git a/code/controllers/subsystem/job.dm b/code/controllers/subsystem/job.dm index ce5816e6601a..214e7e7cf42a 100644 --- a/code/controllers/subsystem/job.dm +++ b/code/controllers/subsystem/job.dm @@ -256,6 +256,21 @@ SUBSYSTEM_DEF(job) return TRUE return FALSE +/datum/controller/subsystem/job/proc/FillNetminPosition() + var/datum/job/job = GetJob("Network Admin") + if(!job) + return + for(var/i = job.total_positions, i > 0, i--) + if(job.current_positions >= job.total_positions) //If we assign a netmin before this proc is run, (malf rework?) + return TRUE + for(var/level in level_order) + var/list/candidates = list() + candidates = FindOccupationCandidates(job, level) + if(candidates.len) + var/mob/dead/new_player/candidate = pick(candidates) + if(AssignRole(candidate, "Network Admin")) + break + /// Rolls a number of security based on the roundstart population /datum/controller/subsystem/job/proc/FillSecurityPositions() var/coeff = CONFIG_GET(number/min_security_scaling_coeff) @@ -339,7 +354,8 @@ SUBSYSTEM_DEF(job) //Check for an AI JobDebug("DO, Running AI Check") - FillAIPosition() + if(FillAIPosition()) + FillNetminPosition() JobDebug("DO, AI Check end") //Check for Security diff --git a/code/controllers/subsystem/machines.dm b/code/controllers/subsystem/machines.dm index 3c641fac1e62..b176fc561da5 100644 --- a/code/controllers/subsystem/machines.dm +++ b/code/controllers/subsystem/machines.dm @@ -5,9 +5,11 @@ SUBSYSTEM_DEF(machines) var/list/processing = list() var/list/currentrun = list() var/list/powernets = list() + var/list/ainets = list() /datum/controller/subsystem/machines/Initialize() makepowernets() + makeainets() fire() return ..() @@ -22,8 +24,22 @@ SUBSYSTEM_DEF(machines) NewPN.add_cable(PC) propagate_network(PC,PC.powernet) +/datum/controller/subsystem/machines/proc/makeainets() + for(var/datum/ai_network/AN in ainets) + qdel(AN) + ainets.Cut() + + for(var/obj/structure/ethernet_cable/EC in GLOB.ethernet_cable_list) + if(!EC.network) + var/datum/ai_network/NewAN = new() + NewAN.add_cable(EC) + propagate_ai_network(EC,EC.network) + + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + N.roundstart_connect() + /datum/controller/subsystem/machines/stat_entry(msg) - msg = "M:[length(processing)]|PN:[length(powernets)]" + msg = "M:[length(processing)]|PN:[length(powernets)]|AN:[length(ainets)]" return ..() @@ -58,8 +74,18 @@ SUBSYSTEM_DEF(machines) NewPN.add_cable(PC) propagate_network(PC,PC.powernet) +/datum/controller/subsystem/machines/proc/setup_template_ainets(list/cables) + for(var/A in cables) + var/obj/structure/ethernet_cable/PC = A + if(!PC.network) + var/datum/ai_network/NewPN = new() + NewPN.add_cable(PC) + propagate_ai_network(PC,PC.network) + /datum/controller/subsystem/machines/Recover() if (istype(SSmachines.processing)) processing = SSmachines.processing if (istype(SSmachines.powernets)) powernets = SSmachines.powernets + if (istype(SSmachines.ainets)) + ainets = SSmachines.ainets diff --git a/code/controllers/subsystem/minor_mapping.dm b/code/controllers/subsystem/minor_mapping.dm index d9e137bf2299..44f16d4890ff 100644 --- a/code/controllers/subsystem/minor_mapping.dm +++ b/code/controllers/subsystem/minor_mapping.dm @@ -39,7 +39,7 @@ SUBSYSTEM_DEF(minor_mapping) while(turfs.len && amount > 0) var/turf/T = pick_n_take(turfs) var/obj/item/storage/backpack/satchel/flat/S = new(T) - S.hide(intact=TRUE) + S.hide(intact=(T.underfloor_accessibility < UNDERFLOOR_VISIBLE)) amount-- diff --git a/code/controllers/subsystem/persistence.dm b/code/controllers/subsystem/persistence.dm index 7e50c9eb10c8..4e0b7af0ce40 100644 --- a/code/controllers/subsystem/persistence.dm +++ b/code/controllers/subsystem/persistence.dm @@ -16,6 +16,7 @@ SUBSYSTEM_DEF(persistence) var/list/obj/item/storage/photo_album/photo_albums = list() var/list/obj/structure/sign/painting/painting_frames = list() var/list/paintings = list() + var/list/ai_network_rankings = list("ram" = list(), "cpu" = list()) /datum/controller/subsystem/persistence/Initialize() LoadPoly() @@ -27,6 +28,7 @@ SUBSYSTEM_DEF(persistence) LoadAntagReputation() LoadRandomizedRecipes() LoadPaintings() + LoadAINetworkRanking() return ..() /datum/controller/subsystem/persistence/proc/LoadPoly() @@ -117,6 +119,16 @@ SUBSYSTEM_DEF(persistence) return antag_rep = json_decode(json) +/datum/controller/subsystem/persistence/proc/LoadAINetworkRanking() + var/json = file2text("data/AINetworkRank.json") + if(!json) + var/json_file = file("data/AINetworkRank.json") + if(!fexists(json_file)) + WARNING("Failed to load ai network ranks. File likely corrupt.") + return + return + ai_network_rankings = json_decode(json) + /datum/controller/subsystem/persistence/proc/SetUpTrophies(list/trophy_items) for(var/A in GLOB.trophy_cases) var/obj/structure/displaycase/trophy/T = A @@ -153,6 +165,7 @@ SUBSYSTEM_DEF(persistence) SaveRandomizedRecipes() SavePaintings() SaveScars() + SaveAIRankings() /datum/controller/subsystem/persistence/proc/GetPhotoAlbums() var/album_path = file("data/photo_albums.json") @@ -289,6 +302,56 @@ SUBSYSTEM_DEF(persistence) fdel(FILE_ANTAG_REP) text2file(json_encode(antag_rep), FILE_ANTAG_REP) +/datum/controller/subsystem/persistence/proc/SaveAIRankings() + var/min_ram = 0 + var/min_cpu = 0 + + for(var/ram_record in ai_network_rankings["ram"]) + if(ram_record["score"] < min_ram) + min_ram = ram_record["score"] + for(var/cpu_record in ai_network_rankings["cpu"]) + if(cpu_record["score"] < min_ram) + min_cpu = cpu_record["score"] + + var/list/resource_list = list() + for(var/datum/ai_network/AN in SSmachines.ainets) + resource_list |= AN.resources + + var/list/contenders_ram = list() + var/list/contenders_cpu = list() + + for(var/datum/ai_shared_resources/R in resource_list) + if(R.total_cpu() > min_cpu) + contenders_cpu += R.total_cpu() + if(R.total_ram() > min_ram) + contenders_ram += R.total_ram() + + var/cpu_winner = max(contenders_cpu) + var/ram_winner = max(contenders_ram) + + + if(!isnull(cpu_winner)) + var/cpu_entry = list("score" = cpu_winner, "round_id" = GLOB.round_id) + + ai_network_rankings["cpu"] += list(cpu_entry) + ai_network_rankings["cpu"] = sortList(ai_network_rankings["cpu"], /proc/cmp_ai_record_dsc) + if(length(ai_network_rankings["cpu"]) > 5) + var/list/cpu_rankings = ai_network_rankings["cpu"] + cpu_rankings.len = 5 + ai_network_rankings["cpu"] = cpu_rankings + + if(!isnull(ram_winner)) + var/ram_entry = list("score" = ram_winner, "round_id" = GLOB.round_id) + ai_network_rankings["ram"] += list(ram_entry) + ai_network_rankings["ram"] = sortList(ai_network_rankings["ram"], /proc/cmp_ai_record_dsc) + if(length(ai_network_rankings["ram"]) > 5) + var/list/ram_rankings = ai_network_rankings["ram"] + ram_rankings.len = 5 + ai_network_rankings["ram"] = ram_rankings + + fdel("data/AINetworkRank.json") + text2file(json_encode(ai_network_rankings), "data/AINetworkRank.json") + /datum/controller/subsystem/persistence/proc/LoadRandomizedRecipes() var/json_file = file("data/RandomizedChemRecipes.json") @@ -358,4 +421,4 @@ SUBSYSTEM_DEF(persistence) if(!original_human || original_human.stat == DEAD || !original_human.all_scars || original_human != ending_human) original_human.save_persistent_scars(TRUE) else - original_human.save_persistent_scars() \ No newline at end of file + original_human.save_persistent_scars() diff --git a/code/game/area/Space_Station_13_areas.dm b/code/game/area/Space_Station_13_areas.dm index e82e1f4fa21c..94d1182e02e3 100644 --- a/code/game/area/Space_Station_13_areas.dm +++ b/code/game/area/Space_Station_13_areas.dm @@ -451,6 +451,14 @@ NOTE: there are two lists of areas in the end of this file: centcom and station mood_message = span_nicegreen("I love being in the bar!\n") airlock_wires = /datum/wires/airlock/service +/area/crew_quarters/public_lounge + name = "Lounge" + icon_state = "bar" + minimap_color = "#5ac866" + mood_bonus = 5 + mood_message = span_nicegreen("I love being in the lounge!\n") + airlock_wires = /datum/wires/airlock/service + /area/crew_quarters/bar/Initialize(mapload) . = ..() GLOB.bar_areas += src diff --git a/code/game/machinery/Beacon.dm b/code/game/machinery/Beacon.dm index 8d849c8c145e..bb8c481f4c68 100644 --- a/code/game/machinery/Beacon.dm +++ b/code/game/machinery/Beacon.dm @@ -16,7 +16,7 @@ Beacon = new(T) Beacon.invisibility = INVISIBILITY_MAXIMUM - hide(T.intact) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) /obj/machinery/bluespace_beacon/Destroy() QDEL_NULL(Beacon) diff --git a/code/game/machinery/computer/communications.dm b/code/game/machinery/computer/communications.dm index cce089a75e6a..da53b455f929 100755 --- a/code/game/machinery/computer/communications.dm +++ b/code/game/machinery/computer/communications.dm @@ -363,15 +363,6 @@ new /obj/item/card/id/captains_spare/temporary(loc) COOLDOWN_START(src, important_action_cooldown, IMPORTANT_ACTION_COOLDOWN) priority_announce("The emergency spare ID has been printed by [authorize_name].", "Emergency Spare ID Warning System", RANDOM_REPORT_SOUND) - if("printAIControlCode") - if(authenticated_as_non_silicon_head(usr)) - if(!COOLDOWN_FINISHED(src, important_action_cooldown)) - return - playsound(loc, 'sound/items/poster_being_created.ogg', 100, 1) - GLOB.ai_control_code = random_nukecode(6) - new /obj/item/paper/ai_control_code(loc) - COOLDOWN_START(src, important_action_cooldown, IMPORTANT_ACTION_COOLDOWN) - priority_announce("The AI Control Code been printed by [authorize_name]. All previous codes have been invalidated.", "Central Tech Support", RANDOM_REPORT_SOUND) /obj/machinery/computer/communications/ui_data(mob/user) diff --git a/code/game/machinery/computer/security.dm b/code/game/machinery/computer/security.dm index a0631d4f17d4..303c890d2bc1 100644 --- a/code/game/machinery/computer/security.dm +++ b/code/game/machinery/computer/security.dm @@ -68,44 +68,7 @@ data["logged_in"] = logged_in - if(issilicon(user)) - var/mob/living/silicon/borg = user - data["username"] = borg.name - data["has_access"] = TRUE - - if(IsAdminGhost(user)) - data["username"] = user.client.holder.admin_signature - data["has_access"] = TRUE - - if(ishuman(user)) - var/username = user.get_authentification_name("Unknown") - data["username"] = user.get_authentification_name("Unknown") - if(username != "Unknown") - var/datum/data/record/record - for(var/RP in GLOB.data_core.general) - var/datum/data/record/R = RP - - if(!istype(R)) - continue - if(R.fields["name"] == username) - record = R - break - if(record) - if(istype(record.fields["photo_front"], /obj/item/photo)) - var/obj/item/photo/P1 = record.fields["photo_front"] - var/icon/picture = icon(P1.picture.picture_image) - picture.Crop(10, 32, 22, 22) - var/md5 = md5(fcopy_rsc(picture)) - - if(!SSassets.cache["photo_[md5]_cropped.png"]) - SSassets.transport.register_asset("photo_[md5]_cropped.png", picture) - SSassets.transport.send_assets(user, list("photo_[md5]_cropped.png" = picture)) - - data["user_image"] = SSassets.transport.get_asset_url("photo_[md5]_cropped.png") - - data["has_access"] = check_access(user.get_idcard()) - - + data += tgui_login_data(user, src) if(!logged_in) return data @@ -273,7 +236,6 @@ data["active_record"] = record - return data /obj/machinery/computer/secure_data/ui_static_data(mob/user) @@ -288,6 +250,8 @@ if(..()) return + + switch(action) if("back") if(!logged_in) @@ -301,6 +265,10 @@ active_security_record = null screen = MAIN_SCREEN + logged_in = tgui_login_act(usr, src) + if(!logged_in) + return + if(issilicon(usr)) var/mob/living/silicon/borg = usr logged_in = borg.name @@ -310,17 +278,14 @@ if(IsAdminGhost(usr)) logged_in = usr.client.holder.admin_signature rank = "Central Command Officer" - - - - - var/mob/living/carbon/human/H = usr - if(!istype(H)) return - if(check_access(H.get_idcard())) + var/mob/living/carbon/human/H = usr + if(istype(H)) logged_in = H.get_authentification_name("Unknown") rank = H.get_assignment("Unknown", "Unknown") + return + if("log_out") if(!logged_in) return diff --git a/code/game/machinery/doors/airlock.dm b/code/game/machinery/doors/airlock.dm index 5e57453c0125..6f7a145001cd 100644 --- a/code/game/machinery/doors/airlock.dm +++ b/code/game/machinery/doors/airlock.dm @@ -1504,6 +1504,14 @@ if(density && !open(2)) //The airlock is still closed, but something prevented it opening. (Another player noticed and bolted/welded the airlock in time!) to_chat(user, span_warning("Despite your efforts, [src] managed to resist your attempts to open it!")) + +/obj/machinery/door/airlock/proc/safe_lockdown() + // Must be powered and have working AI wire. + if(canAIControl(src) && !stat) + locked = FALSE //For airlocks that were bolted open. + close() + bolt() //Bolt it! + /obj/machinery/door/airlock/hostile_lockdown(mob/origin) // Must be powered and have working AI wire. if(canAIControl(src) && !stat) @@ -1524,6 +1532,11 @@ open() safe = TRUE +/obj/machinery/door/airlock/proc/disable_safe_lockdown() + // Must be powered and have working AI wire. + if(canAIControl(src) && !stat) + unbolt() + open() /obj/machinery/door/airlock/proc/on_break() if(!panel_open) diff --git a/code/game/machinery/magnet.dm b/code/game/machinery/magnet.dm index 0110312e5634..158db804d677 100644 --- a/code/game/machinery/magnet.dm +++ b/code/game/machinery/magnet.dm @@ -30,7 +30,7 @@ /obj/machinery/magnetic_module/Initialize() ..() var/turf/T = loc - hide(T.intact) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) center = T SSradio.add_object(src, freq, RADIO_MAGNETS) return INITIALIZE_HINT_LATELOAD diff --git a/code/game/machinery/navbeacon.dm b/code/game/machinery/navbeacon.dm index c70c592003f2..58a1f425eaa9 100644 --- a/code/game/machinery/navbeacon.dm +++ b/code/game/machinery/navbeacon.dm @@ -27,7 +27,7 @@ set_codes() var/turf/T = loc - hide(T.intact) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) if(codes["patrol"]) if(!GLOB.navbeacons["[z]"]) GLOB.navbeacons["[z]"] = list() @@ -86,8 +86,8 @@ /obj/machinery/navbeacon/attackby(obj/item/I, mob/user, params) var/turf/T = loc - if(T.intact) - return // prevent intraction when T-scanner revealed + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) + return // prevent intraction when T-scanner revealed if(I.tool_behaviour == TOOL_SCREWDRIVER) open = !open @@ -119,9 +119,8 @@ . = ..() var/ai = isAI(user) var/turf/T = loc - if(T.intact) - return // prevent intraction when T-scanner revealed - + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) + return // prevent intraction when T-scanner revealed if(!open && !ai) // can't alter controls if not open, unless you're an AI to_chat(user, span_warning("The beacon's control cover is closed!")) return diff --git a/code/game/mecha/equipment/tools/work_tools.dm b/code/game/mecha/equipment/tools/work_tools.dm index 5d1a0ac4c75c..4cbf6afe28ed 100644 --- a/code/game/mecha/equipment/tools/work_tools.dm +++ b/code/game/mecha/equipment/tools/work_tools.dm @@ -457,7 +457,7 @@ if(!T.broken && !T.burnt) new T.floor_tile(T) T.make_plating() - return !new_turf.intact + return !(new_turf.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) /obj/item/mecha_parts/mecha_equipment/cable_layer/proc/layCable(var/turf/new_turf) if(equip_ready || !istype(new_turf) || !dismantleFloor(new_turf)) diff --git a/code/game/objects/effects/effect_system/effects_foam.dm b/code/game/objects/effects/effect_system/effects_foam.dm index f4f0ac9e4dfb..9dad3c006f75 100644 --- a/code/game/objects/effects/effect_system/effects_foam.dm +++ b/code/game/objects/effects/effect_system/effects_foam.dm @@ -147,7 +147,7 @@ continue if(isturf(O.loc)) var/turf/T = O.loc - if(T.intact && O.level == 1) //hidden under the floor + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE && O.level == 1) //hidden under the floor continue if(lifetime % reagent_divisor) reagents.reaction(O, VAPOR, fraction) diff --git a/code/game/objects/effects/effect_system/effects_smoke.dm b/code/game/objects/effects/effect_system/effects_smoke.dm index e83f4da302a0..e28dba3d7315 100644 --- a/code/game/objects/effects/effect_system/effects_smoke.dm +++ b/code/game/objects/effects/effect_system/effects_smoke.dm @@ -230,7 +230,7 @@ for(var/atom/movable/AM in T) if(AM.type == src.type) continue - if(T.intact && AM.level == 1) //hidden under the floor + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE && AM.level == 1) //hidden under the floor continue reagents.reaction(AM, TOUCH, fraction) diff --git a/code/game/objects/effects/spawners/lootdrop.dm b/code/game/objects/effects/spawners/lootdrop.dm index e643c741bddf..1dc87d75157a 100644 --- a/code/game/objects/effects/spawners/lootdrop.dm +++ b/code/game/objects/effects/spawners/lootdrop.dm @@ -606,7 +606,6 @@ name = "secure AI circuit board spawner" loot = list( /obj/item/circuitboard/computer/aiupload, - /obj/item/circuitboard/computer/ai_upload_download, /obj/item/circuitboard/computer/borgupload ) diff --git a/code/game/objects/items/RCL.dm b/code/game/objects/items/RCL.dm index da0e1b9891fb..dfe4938c9e6f 100644 --- a/code/game/objects/items/RCL.dm +++ b/code/game/objects/items/RCL.dm @@ -178,7 +178,7 @@ if(last) if(get_dist(last, user) == 1) //hacky, but it works var/turf/T = get_turf(user) - if(T.intact || !T.can_have_cabling()) + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE || !T.can_have_cabling()) last = null return if(get_dir(last, user) == last.d2) @@ -203,7 +203,7 @@ return T = get_turf(user) - if(T.intact || !T.can_have_cabling()) + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE || !T.can_have_cabling()) return for(var/obj/structure/cable/C in T) @@ -263,7 +263,7 @@ return var/turf/T = get_turf(user) - if(T.intact || !T.can_have_cabling()) + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE || !T.can_have_cabling()) return loaded.color = colors[current_color_index] diff --git a/code/game/objects/items/circuitboards/computer_circuitboards.dm b/code/game/objects/items/circuitboards/computer_circuitboards.dm index 32ee802d8443..204d0b9ecc03 100644 --- a/code/game/objects/items/circuitboards/computer_circuitboards.dm +++ b/code/game/objects/items/circuitboards/computer_circuitboards.dm @@ -393,20 +393,12 @@ name = "Shuttle Navigation Computer (Computer Board)" build_path = /obj/machinery/computer/camera_advanced/shuttle_docker/custom -/obj/item/circuitboard/computer/ai_upload_download - name = "AI Control Console (Computer Board)" - icon_state = "science" - build_path = /obj/machinery/computer/ai_control_console /obj/item/circuitboard/computer/ai_server_overview name = "AI Server Overview Console (Computer Board)" icon_state = "science" build_path = /obj/machinery/computer/ai_server_console -/obj/item/circuitboard/computer/ai_resource_distribution - name = "AI Resource Distribution Console (Computer Board)" - icon_state = "science" - build_path = /obj/machinery/computer/ai_resource_distribution //Security diff --git a/code/game/objects/items/circuitboards/machine_circuitboards.dm b/code/game/objects/items/circuitboards/machine_circuitboards.dm index 30e33870d5a1..87f4a37385d8 100644 --- a/code/game/objects/items/circuitboards/machine_circuitboards.dm +++ b/code/game/objects/items/circuitboards/machine_circuitboards.dm @@ -1006,6 +1006,17 @@ /obj/item/stock_parts/capacitor = 2, /obj/item/stack/sheet/glass = 2, /obj/item/stack/cable_coil = 1) + +/obj/item/circuitboard/machine/networking_machine + name = "Networking Machine (Machine Board)" + icon_state = "science" + build_path = /obj/machinery/ai/networking + req_components = list( + /obj/item/stock_parts/matter_bin = 4, + /obj/item/stock_parts/capacitor = 2, + /obj/item/stock_parts/scanning_module = 4, + /obj/item/stack/sheet/glass = 4, + /obj/item/stack/cable_coil = 1) /obj/item/circuitboard/machine/ai_core_display name = "AI Core Display (Machine Board)" diff --git a/code/game/objects/items/devices/powersink.dm b/code/game/objects/items/devices/powersink.dm index 449e9e660fa2..eef412632548 100644 --- a/code/game/objects/items/devices/powersink.dm +++ b/code/game/objects/items/devices/powersink.dm @@ -63,7 +63,7 @@ if(I.tool_behaviour == TOOL_SCREWDRIVER) if(mode == DISCONNECTED) var/turf/T = loc - if(isturf(T) && !T.intact) + if(isturf(T) && T.underfloor_accessibility >= UNDERFLOOR_INTERACTABLE) attached = locate() in T if(!attached) to_chat(user, span_warning("This device must be placed over an exposed, powered cable node!")) diff --git a/code/game/objects/items/stacks/rods.dm b/code/game/objects/items/stacks/rods.dm index 0e4bd241045b..ea04b5bdac18 100644 --- a/code/game/objects/items/stacks/rods.dm +++ b/code/game/objects/items/stacks/rods.dm @@ -10,6 +10,7 @@ GLOBAL_LIST_INIT(rod_recipes, list ( \ new/datum/stack_recipe("fore port spacepod frame", /obj/item/pod_parts/pod_frame/fore_port, 15, time = 30, one_per_turf = 0), \ new/datum/stack_recipe("fore starboard spacepod frame", /obj/item/pod_parts/pod_frame/fore_starboard, 15, time = 30, one_per_turf = 0), \ new/datum/stack_recipe("aft port spacepod frame", /obj/item/pod_parts/pod_frame/aft_port, 15, time = 30, one_per_turf = 0), \ + new/datum/stack_recipe("catwalk floor tile", /obj/item/stack/tile/catwalk_tile, 1, 4, 20), \ new/datum/stack_recipe("aft starboard spacepod frame", /obj/item/pod_parts/pod_frame/aft_starboard, 15, time = 30, one_per_turf = 0), \ // yogs end )) diff --git a/code/game/objects/items/stacks/tiles/tile_types.dm b/code/game/objects/items/stacks/tiles/tile_types.dm index 8f0808ac5bda..86c650ad937f 100644 --- a/code/game/objects/items/stacks/tiles/tile_types.dm +++ b/code/game/objects/items/stacks/tiles/tile_types.dm @@ -403,3 +403,52 @@ /obj/item/stack/tile/eighties/loaded amount = 15 + +//Catwalk Tiles +/obj/item/stack/tile/catwalk_tile //This is our base type, sprited to look maintenance-styled + name = "catwalk plating" + singular_name = "catwalk plating tile" + desc = "Flooring that shows its contents underneath. Engineers love it!" + icon_state = "maint_catwalk" + materials = list(/datum/material/iron=100) + turf_type = /turf/open/floor/catwalk_floor + merge_type = /obj/item/stack/tile/catwalk_tile //Just to be cleaner, these all stack with eachother + +/obj/item/stack/tile/catwalk_tile/sixty + amount = 60 + +/obj/item/stack/tile/catwalk_tile/iron + name = "iron catwalk floor" + singular_name = "iron catwalk floor tile" + icon_state = "iron_catwalk" + turf_type = /turf/open/floor/catwalk_floor/iron + +/obj/item/stack/tile/catwalk_tile/iron_white + name = "white catwalk floor" + singular_name = "white catwalk floor tile" + icon_state = "whiteiron_catwalk" + turf_type = /turf/open/floor/catwalk_floor/iron_white + +/obj/item/stack/tile/catwalk_tile/iron_dark + name = "dark catwalk floor" + singular_name = "dark catwalk floor tile" + icon_state = "darkiron_catwalk" + turf_type = /turf/open/floor/catwalk_floor/iron_dark + +/obj/item/stack/tile/catwalk_tile/flat_white + name = "flat white catwalk floor" + singular_name = "flat white catwalk floor tile" + icon_state = "flatwhite_catwalk" + turf_type = /turf/open/floor/catwalk_floor/flat_white + +/obj/item/stack/tile/catwalk_tile/titanium + name = "titanium catwalk floor" + singular_name = "titanium catwalk floor tile" + icon_state = "titanium_catwalk" + turf_type = /turf/open/floor/catwalk_floor/titanium + +/obj/item/stack/tile/catwalk_tile/iron_smooth //this is the greenish one + name = "smooth iron catwalk floor" + singular_name = "smooth iron catwalk floor tile" + icon_state = "smoothiron_catwalk" + turf_type = /turf/open/floor/catwalk_floor/iron_smooth diff --git a/code/game/objects/obj_defense.dm b/code/game/objects/obj_defense.dm index 2a2405095db4..f8b76f338ac3 100644 --- a/code/game/objects/obj_defense.dm +++ b/code/game/objects/obj_defense.dm @@ -102,7 +102,7 @@ /obj/blob_act(obj/structure/blob/B) if(isturf(loc)) var/turf/T = loc - if(T.intact && level == 1) //the blob doesn't destroy thing below the floor + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE && level == 1) //the blob doesn't destroy thing below the floor return take_damage(400, BRUTE, MELEE, 0, get_dir(src, B)) @@ -213,7 +213,7 @@ GLOBAL_DATUM_INIT(acid_overlay, /mutable_appearance, mutable_appearance('icons/e /obj/fire_act(exposed_temperature, exposed_volume) if(isturf(loc)) var/turf/T = loc - if(T.intact && level == 1) //fire can't damage things hidden below the floor. + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE && level == 1) //fire can't damage things hidden below the floor. return if(exposed_temperature && !(resistance_flags & FIRE_PROOF)) take_damage(clamp(0.02 * exposed_temperature, 0, 20), BURN, FIRE, 0) diff --git a/code/game/objects/structures/signs/signs_plaques.dm b/code/game/objects/structures/signs/signs_plaques.dm index 3220e0523054..216ba23cf52b 100644 --- a/code/game/objects/structures/signs/signs_plaques.dm +++ b/code/game/objects/structures/signs/signs_plaques.dm @@ -26,21 +26,6 @@ desc = "Next to the extremely long list of names and job titles, there is a drawing of a little child. The child appears to be retarded. Beneath the image, someone has scratched the word \"PACKETS\"." icon_state = "kiddieplaque" -/obj/structure/sign/plaques/ai_password - name = "\improper AI default password" - desc = "This plaque contains the default password for AI control consoles onboard this station." - var/control_code = "BUG" - -/obj/structure/sign/plaques/ai_password/Initialize(mapload) - . = ..() - control_code = GLOB.ai_control_code - -/obj/structure/sign/plaques/ai_password/examine(mob/living/user) - . = ..() - if(Adjacent(user)) - . += span_notice("The following digits are stamped into the plaque: [control_code]") - else - . += span_notice("You must be closer to read the code.") /obj/structure/sign/plaques/kiddie/badger name = "\improper Remembrance Plaque" diff --git a/code/game/turfs/openspace/openspace.dm b/code/game/turfs/openspace/openspace.dm index 1cf670c3da6e..0d861d897505 100644 --- a/code/game/turfs/openspace/openspace.dm +++ b/code/game/turfs/openspace/openspace.dm @@ -7,6 +7,8 @@ //mouse_opacity = MOUSE_OPACITY_TRANSPARENT var/can_cover_up = TRUE var/can_build_on = TRUE + overfloor_placed = FALSE + underfloor_accessibility = UNDERFLOOR_INTERACTABLE /turf/open/openspace/debug/update_multiz() ..() diff --git a/code/game/turfs/simulated/floor.dm b/code/game/turfs/simulated/floor.dm index 4101efd3ac69..dfe5b6c73072 100644 --- a/code/game/turfs/simulated/floor.dm +++ b/code/game/turfs/simulated/floor.dm @@ -16,9 +16,11 @@ var/icon_plating = "plating" thermal_conductivity = 0.040 heat_capacity = 10000 - intact = 1 + var/broken = 0 var/burnt = 0 + + overfloor_placed = TRUE var/floor_tile = null //tile that this floor drops var/list/broken_states var/list/burnt_states @@ -172,7 +174,7 @@ return 1 if(..()) return 1 - if(intact && istype(C, /obj/item/stack/tile)) + if(overfloor_placed && istype(C, /obj/item/stack/tile)) try_replace_tile(C, user, params) return 0 @@ -180,7 +182,7 @@ if(istype(I,/obj/item/jawsoflife/jimmy)) to_chat(user,"The [I] cannot pry tiles.") return - return intact ? pry_tile(I, user) : FALSE + return overfloor_placed ? pry_tile(I, user) : FALSE /turf/open/floor/proc/try_replace_tile(obj/item/stack/tile/T, mob/user, params) if(T.turf_type == type) diff --git a/code/game/turfs/simulated/floor/plating.dm b/code/game/turfs/simulated/floor/plating.dm index 947be76e60d9..7c34147e4113 100644 --- a/code/game/turfs/simulated/floor/plating.dm +++ b/code/game/turfs/simulated/floor/plating.dm @@ -10,7 +10,8 @@ /turf/open/floor/plating name = "plating" icon_state = "plating" - intact = FALSE + overfloor_placed = FALSE + underfloor_accessibility = UNDERFLOOR_INTERACTABLE baseturfs = /turf/baseturf_bottom footstep = FOOTSTEP_PLATING barefootstep = FOOTSTEP_HARD_BAREFOOT diff --git a/code/game/turfs/simulated/floor/plating/catwalk_plating.dm b/code/game/turfs/simulated/floor/plating/catwalk_plating.dm new file mode 100644 index 000000000000..0339cac2be89 --- /dev/null +++ b/code/game/turfs/simulated/floor/plating/catwalk_plating.dm @@ -0,0 +1,103 @@ +/** + * ## catwalk flooring + * + * They show what's underneath their catwalk flooring (pipes and the like) + * you can screwdriver it to interact with the underneath stuff without destroying the tile... + * unless you want to! + */ +/turf/open/floor/catwalk_floor //the base type, meant to look like a maintenance panel + icon = 'icons/turf/floors/catwalk_plating.dmi' + icon_state = "maint_above" + name = "catwalk floor" + desc = "Flooring that shows its contents underneath. Engineers love it!" + baseturfs = /turf/open/floor/plating + floor_tile = /obj/item/stack/tile/catwalk_tile + layer = CATWALK_LAYER + plane = GAME_PLANE + footstep = FOOTSTEP_CATWALK + overfloor_placed = TRUE + underfloor_accessibility = UNDERFLOOR_VISIBLE + var/covered = TRUE + var/catwalk_type = "maint" + var/static/list/catwalk_underlays = list() + +/turf/open/floor/catwalk_floor/Initialize(mapload) + . = ..() + if(!catwalk_underlays[catwalk_type]) + var/mutable_appearance/plating_underlay = mutable_appearance(icon, "[catwalk_type]_below", TURF_LAYER) + catwalk_underlays[catwalk_type] = plating_underlay + underlays += catwalk_underlays[catwalk_type] + update_icon() + +/turf/open/floor/catwalk_floor/examine(mob/user) + . = ..() + + if(covered) + . += span_notice("You can unscrew it to reveal the contents beneath.") + else + . += span_notice("You can screw it to hide the contents beneath.") + . += span_notice("There's a small crack on the edge of it.") + +/turf/open/floor/catwalk_floor/screwdriver_act(mob/living/user, obj/item/tool) + . = ..() + covered = !covered + if(!covered) + underfloor_accessibility = UNDERFLOOR_INTERACTABLE + layer = TURF_LAYER + plane = FLOOR_PLANE + icon_state = "[catwalk_type]_below" + else + underfloor_accessibility = UNDERFLOOR_VISIBLE + layer = CATWALK_LAYER + plane = GAME_PLANE + icon_state = "[catwalk_type]_above" + user.balloon_alert(user, "[!covered ? "cover removed" : "cover added"]") + tool.play_tool_sound(src) + update_icon() + +/turf/open/floor/catwalk_floor/crowbar_act(mob/user, obj/item/crowbar) + if(covered) + user.balloon_alert(user, "remove cover first!") + return FALSE + . = ..() + +//Reskins! More fitting with most of our tiles, and appear as a radial on the base type +/turf/open/floor/catwalk_floor/iron + name = "iron plated catwalk floor" + icon_state = "iron_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/iron + catwalk_type = "iron" + + +/turf/open/floor/catwalk_floor/iron_white + name = "white plated catwalk floor" + icon_state = "whiteiron_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/iron_white + catwalk_type = "whiteiron" + +/turf/open/floor/catwalk_floor/iron_dark + name = "dark plated catwalk floor" + icon_state = "darkiron_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/iron_dark + catwalk_type = "darkiron" + +/turf/open/floor/catwalk_floor/flat_white + name = "white large plated catwalk floor" + icon_state = "flatwhite_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/flat_white + catwalk_type = "flatwhite" + +/turf/open/floor/catwalk_floor/titanium + name = "titanium plated catwalk floor" + icon_state = "titanium_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/titanium + catwalk_type = "titanium" + +/turf/open/floor/catwalk_floor/iron_smooth //the original green type + name = "smooth plated catwalk floor" + icon_state = "smoothiron_above" + floor_tile = /obj/item/stack/tile/catwalk_tile/iron_smooth + catwalk_type = "smoothiron" + +/turf/open/floor/catwalk_floor/telecomms + initial_gas_mix = TCOMMS_ATMOS diff --git a/code/game/turfs/space/space.dm b/code/game/turfs/space/space.dm index 537bf53e53ba..24e352f25198 100644 --- a/code/game/turfs/space/space.dm +++ b/code/game/turfs/space/space.dm @@ -2,7 +2,8 @@ icon = 'icons/turf/space.dmi' icon_state = "0" name = "\proper space" - intact = 0 + overfloor_placed = FALSE + underfloor_accessibility = UNDERFLOOR_INTERACTABLE temperature = TCMB thermal_conductivity = OPEN_HEAT_TRANSFER_COEFFICIENT diff --git a/code/game/turfs/turf.dm b/code/game/turfs/turf.dm index b54880c5725e..086d4712d2bc 100644 --- a/code/game/turfs/turf.dm +++ b/code/game/turfs/turf.dm @@ -4,7 +4,10 @@ GLOBAL_LIST_EMPTY(station_turfs) icon = 'icons/turf/floors.dmi' level = 1 - var/intact = 1 + /// If there's a tile over a basic floor that can be ripped out + var/overfloor_placed = FALSE + /// How accessible underfloor pieces such as wires, pipes, etc are on this turf. Can be HIDDEN, VISIBLE, or INTERACTABLE. + var/underfloor_accessibility = UNDERFLOOR_HIDDEN // baseturfs can be either a list or a single turf type. // In class definition like here it should always be a single type. @@ -201,6 +204,15 @@ GLOBAL_LIST_EMPTY(station_turfs) coil.place_turf(src, user) return TRUE + if(can_lay_cable() && istype(C, /obj/item/stack/ethernet_coil)) + var/obj/item/stack/ethernet_coil/coil = C + for(var/obj/structure/ethernet_cable/LC in src) + if(!LC.d1 || !LC.d2) + LC.attackby(C,user) + return + coil.place_turf(src, user) + return TRUE + else if(istype(C, /obj/item/twohanded/rcl)) handleRCL(C, user) @@ -328,7 +340,7 @@ GLOBAL_LIST_EMPTY(station_turfs) /turf/proc/levelupdate() for(var/obj/O in src) if(O.level == 1 && (O.flags_1 & INITIALIZED_1)) - O.hide(src.intact) + O.hide(underfloor_accessibility < UNDERFLOOR_VISIBLE) // override for space turfs, since they should never hide anything /turf/open/space/levelupdate() @@ -390,7 +402,7 @@ GLOBAL_LIST_EMPTY(station_turfs) //////////////////////////////////////////////////// /turf/singularity_act() - if(intact) + if(underfloor_accessibility < UNDERFLOOR_INTERACTABLE) for(var/obj/O in contents) //this is for deleting things like wires contained in the turf if(O.level != 1) continue @@ -403,7 +415,7 @@ GLOBAL_LIST_EMPTY(station_turfs) return TRUE /turf/proc/can_lay_cable() - return can_have_cabling() & !intact + return can_have_cabling() && underfloor_accessibility >= UNDERFLOOR_INTERACTABLE /turf/proc/visibilityChanged() GLOB.cameranet.updateVisibility(src) @@ -478,7 +490,7 @@ GLOBAL_LIST_EMPTY(station_turfs) acid_type = /obj/effect/acid/alien var/has_acid_effect = FALSE for(var/obj/O in src) - if(intact && O.level == 1) //hidden under the floor + if(underfloor_accessibility < UNDERFLOOR_INTERACTABLE && O.level == 1) //hidden under the floor continue if(istype(O, acid_type)) var/obj/effect/acid/A = O diff --git a/code/modules/admin/verbs/debug.dm b/code/modules/admin/verbs/debug.dm index 014bd9421ab1..a24a4c04fd86 100644 --- a/code/modules/admin/verbs/debug.dm +++ b/code/modules/admin/verbs/debug.dm @@ -1123,3 +1123,11 @@ GLOBAL_PROTECT(AdminProcCallSpamPrevention) return if(alert(usr, "Are you absolutely sure you want to reload the configuration from the default path on the disk, wiping any in-round modificatoins?", "Really reset?", "No", "Yes") == "Yes") config.admin_reload() + +/client/proc/debug_ai_networks() + set category = "Misc.Server Debug" + set name = "Debug AI Networks" + set desc = "Displays a list of all AI networks to ALL admins" + if(!check_rights(R_DEBUG)) + return + _debug_ai_networks() diff --git a/code/modules/admin/verbs/mapping.dm b/code/modules/admin/verbs/mapping.dm index 9fd2f141be87..1243e68cc8a6 100644 --- a/code/modules/admin/verbs/mapping.dm +++ b/code/modules/admin/verbs/mapping.dm @@ -76,6 +76,7 @@ GLOBAL_LIST_INIT(admin_verbs_debug_all, list( /client/proc/cmd_display_init_log, /client/proc/cmd_display_overlay_log, /client/proc/reload_configuration, + /client/proc/debug_ai_networks, /datum/admins/proc/create_or_modify_area, /client/proc/debug_typeof, // Yogs -- Adds a debug verb for getting the subtypes of something /client/proc/toggle_cdn, diff --git a/code/modules/antagonists/blob/blob_report.dm b/code/modules/antagonists/blob/blob_report.dm index f0d46888c2f6..d8ee7857d635 100644 --- a/code/modules/antagonists/blob/blob_report.dm +++ b/code/modules/antagonists/blob/blob_report.dm @@ -29,15 +29,11 @@ floor += 1 if(iswallturf(T)) - var/turf/closed/wall/TW = T - if(TW.intact) - wall += 2 - else - wall += 1 + wall += 1 if(istype(T, /turf/closed/wall/r_wall)) var/turf/closed/wall/r_wall/TRW = T - if(TRW.intact) + if(TRW.d_state == INTACT) r_wall += 2 else r_wall += 1 diff --git a/code/modules/antagonists/revenant/revenant_abilities.dm b/code/modules/antagonists/revenant/revenant_abilities.dm index 870e48ed7d2f..ad3f7e204989 100644 --- a/code/modules/antagonists/revenant/revenant_abilities.dm +++ b/code/modules/antagonists/revenant/revenant_abilities.dm @@ -244,7 +244,7 @@ if(!isplatingturf(T) && !istype(T, /turf/open/floor/engine/cult) && isfloorturf(T) && prob(15)) var/turf/open/floor/floor = T - if(floor.intact && floor.floor_tile) + if(floor.overfloor_placed && floor.floor_tile) new floor.floor_tile(floor) floor.broken = 0 floor.burnt = 0 diff --git a/code/modules/atmospherics/machinery/atmosmachinery.dm b/code/modules/atmospherics/machinery/atmosmachinery.dm index 587100913ea5..9260e12a0304 100644 --- a/code/modules/atmospherics/machinery/atmosmachinery.dm +++ b/code/modules/atmospherics/machinery/atmosmachinery.dm @@ -191,7 +191,7 @@ GLOBAL_LIST_EMPTY(pipeimages) return ..() var/turf/T = get_turf(src) - if (level==1 && isturf(T) && T.intact) + if (level==1 && isturf(T) && T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) to_chat(user, span_warning("You must remove the plating first!")) return TRUE @@ -277,7 +277,7 @@ GLOBAL_LIST_EMPTY(pipeimages) pipe_color = obj_color setPipingLayer(set_layer) var/turf/T = get_turf(src) - level = T.intact ? 2 : 1 + level = (T.underfloor_accessibility < UNDERFLOOR_VISIBLE) ? 2 : 1 atmosinit() var/list/nodes = pipeline_expansion() for(var/obj/machinery/atmospherics/A in nodes) diff --git a/code/modules/atmospherics/machinery/pipes/layermanifold.dm b/code/modules/atmospherics/machinery/pipes/layermanifold.dm index 00285a5f77d1..fae5d24afd7d 100644 --- a/code/modules/atmospherics/machinery/pipes/layermanifold.dm +++ b/code/modules/atmospherics/machinery/pipes/layermanifold.dm @@ -106,7 +106,7 @@ normalize_cardinal_directions() findAllConnections() var/turf/T = loc // hide if turf is not intact - hide(T.intact) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) /obj/machinery/atmospherics/pipe/layer_manifold/setPipingLayer() piping_layer = PIPING_LAYER_DEFAULT diff --git a/code/modules/atmospherics/machinery/pipes/pipes.dm b/code/modules/atmospherics/machinery/pipes/pipes.dm index cbd6f8a10b51..e4b411c75cb3 100644 --- a/code/modules/atmospherics/machinery/pipes/pipes.dm +++ b/code/modules/atmospherics/machinery/pipes/pipes.dm @@ -39,7 +39,7 @@ /obj/machinery/atmospherics/pipe/atmosinit() var/turf/T = loc // hide if turf is not intact - hide(T.intact) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) ..() /obj/machinery/atmospherics/pipe/hide(i) diff --git a/code/modules/holodeck/computer.dm b/code/modules/holodeck/computer.dm index 2ef90774b114..a75b4aa34f62 100644 --- a/code/modules/holodeck/computer.dm +++ b/code/modules/holodeck/computer.dm @@ -18,6 +18,10 @@ #define HOLODECK_CD 25 #define HOLODECK_DMG_CD 500 +/// typecache for turfs that should be considered ok during floorchecks. +/// A linked turf being anything not in this typecache will cause the holodeck to perform an emergency shutdown. +GLOBAL_LIST_INIT(typecache_holodeck_linked_floorcheck_ok, typecacheof(list(/turf/open/floor/holofloor, /turf/closed))) + /obj/machinery/computer/holodeck name = "holodeck control console" desc = "A computer used to control a nearby holodeck." @@ -223,8 +227,9 @@ /obj/machinery/computer/holodeck/proc/floorcheck() for(var/turf/T in linked) - if(!T.intact || isspaceturf(T)) - return FALSE + if (is_type_in_typecache(T, GLOB.typecache_holodeck_linked_floorcheck_ok)) + continue + return FALSE return TRUE /obj/machinery/computer/holodeck/proc/nerf(active) diff --git a/code/modules/holodeck/turfs.dm b/code/modules/holodeck/turfs.dm index 67c87a60c5d3..d39e5c5a8b5c 100644 --- a/code/modules/holodeck/turfs.dm +++ b/code/modules/holodeck/turfs.dm @@ -122,7 +122,7 @@ /turf/open/floor/holofloor/carpet/update_icon() if(!..()) return 0 - if(intact) + if(overfloor_placed) queue_smooth(src) /turf/open/floor/holofloor/wood diff --git a/code/modules/jobs/job_types/ai.dm b/code/modules/jobs/job_types/ai.dm index fe094589de30..90aa7c304604 100644 --- a/code/modules/jobs/job_types/ai.dm +++ b/code/modules/jobs/job_types/ai.dm @@ -28,13 +28,13 @@ var/mob/living/silicon/ai/AI = H - AI.relocate(TRUE) + AI.relocate(TRUE, TRUE) + + var/total_available_cpu = 1 - AI.ai_network.resources.total_cpu_assigned() + var/total_available_ram = AI.ai_network.resources.total_ram() - AI.ai_network.resources.total_ram_assigned() - var/total_available_cpu = 1 - GLOB.ai_os.total_cpu_assigned() - var/total_available_ram = GLOB.ai_os.total_ram - GLOB.ai_os.total_ram_assigned() - - GLOB.ai_os.set_cpu(AI, total_available_cpu) - GLOB.ai_os.add_ram(AI, total_available_ram) + AI.ai_network.resources.set_cpu(AI, total_available_cpu) + AI.ai_network.resources.add_ram(AI, total_available_ram) AI.apply_pref_name("ai", M.client) //If this runtimes oh well jobcode is fucked. AI.set_core_display_icon(null, M.client) diff --git a/code/modules/mapping/map_template.dm b/code/modules/mapping/map_template.dm index 3a6caa8a806d..36e26a43d5f3 100644 --- a/code/modules/mapping/map_template.dm +++ b/code/modules/mapping/map_template.dm @@ -28,6 +28,7 @@ /datum/parsed_map/proc/initTemplateBounds() var/list/obj/machinery/atmospherics/atmos_machines = list() var/list/obj/structure/cable/cables = list() + var/list/obj/structure/ethernet_cable/ethernet_cables = list() var/list/atom/atoms = list() var/list/area/areas = list() @@ -44,6 +45,9 @@ if(istype(A, /obj/structure/cable)) cables += A continue + if(istype(A, /obj/structure/ethernet_cable)) + ethernet_cables += A + continue if(istype(A, /obj/machinery/atmospherics)) atmos_machines += A for(var/L in border) @@ -53,6 +57,7 @@ SSmapping.reg_in_areas_in_z(areas) SSatoms.InitializeAtoms(atoms) SSmachines.setup_template_powernets(cables) + SSmachines.setup_template_ainets(ethernet_cables) SSair.setup_template_machinery(atmos_machines) /datum/map_template/proc/load_new_z(secret = FALSE) diff --git a/code/modules/mob/living/silicon/ai/ai.dm b/code/modules/mob/living/silicon/ai/ai.dm index fb9603e5633b..faeb705f15b7 100644 --- a/code/modules/mob/living/silicon/ai/ai.dm +++ b/code/modules/mob/living/silicon/ai/ai.dm @@ -112,7 +112,6 @@ //Reduces/Increases download speed by this modifier var/downloadSpeedModifier = 1 - var/login_warned_temp = FALSE //Do we have access to camera tracking? var/canCameraMemoryTrack = FALSE @@ -122,20 +121,17 @@ var/cameraMemoryTickCount = 0 //Did we get the death prompt? - var/is_dying = FALSE - ///Multiplier for amount of points gained when passively using CPU for science - var/research_point_booster = 1 + var/is_dying = FALSE + var/datum/ai_network/ai_network -/mob/living/silicon/ai/Initialize(mapload, datum/ai_laws/L, mob/target_ai, shunted) + +/mob/living/silicon/ai/Initialize(mapload, datum/ai_laws/L, mob/target_ai, shunted, forced_relocate = TRUE) . = ..() if(!target_ai) //If there is no player/brain inside. return INITIALIZE_HINT_QDEL //Delete AI. - if(!istype(loc, /obj/machinery/ai/data_core) && !shunted) - relocate(TRUE) - if(L && istype(L, /datum/ai_laws)) laws = L laws.associate(src) @@ -192,6 +188,9 @@ dashboard = new(src) + if(!istype(loc, /obj/machinery/ai/data_core) && !shunted && forced_relocate) + relocate(TRUE, TRUE) + if(isvalidAIloc(loc)) add_verb(src, list(/mob/living/silicon/ai/proc/ai_network_change, \ /mob/living/silicon/ai/proc/ai_statuschange, /mob/living/silicon/ai/proc/ai_hologram_change, \ @@ -207,6 +206,8 @@ builtInCamera.network = list("ss13") builtInCamera.built_in = src + + /mob/living/silicon/ai/key_down(_key, client/user) if(findtext(_key, "numpad")) //if it's a numpad number, we can convert it to just the number _key = _key[7] //strings, lists, same thing really @@ -234,7 +235,7 @@ qdel(eyeobj) // No AI, no Eye malfhack = null apc_override = null - GLOB.ai_os.remove_ai(src) + ai_network?.remove_ai(src) . = ..() @@ -557,7 +558,7 @@ if(href_list["instant_download"]) if(!href_list["console"]) return - var/obj/machinery/computer/ai_control_console/C = locate(href_list["console"]) + var/datum/computer_file/program/ai/ai_network_interface/C = locate(href_list["console"]) if(!C) return if(C.downloading != src) @@ -566,6 +567,13 @@ return if(C.downloading == src) C.finish_download() + if(href_list["emergency_disconnect"]) + if(alert("Are you sure you want to disconnect all remote networks and lock all networking devices? This means you'll be unable to switch cores unless they're physically connected!", "No", "Yes") != "Yes") + return + for(var/obj/machinery/ai/networking/N in ai_network.get_local_nodes_oftype()) + N.disconnect() + N.locked = TRUE + if(href_list["go_to_machine"]) var/atom/target = locate(href_list["go_to_machine"]) if(!target) @@ -576,6 +584,10 @@ to_chat(src, "[target] is not on or near any active cameras on the station.") +/mob/living/silicon/ai/proc/switch_ainet(datum/ai_network/old_net, datum/ai_network/new_net) + for(var/datum/ai_project/project in dashboard.completed_projects) + project.switch_network(old_net, new_net) + /mob/living/silicon/ai/proc/switchCamera(obj/machinery/camera/C) if(QDELETED(C)) diff --git a/code/modules/mob/living/silicon/ai/ai_network/ai_network.dm b/code/modules/mob/living/silicon/ai/ai_network/ai_network.dm new file mode 100644 index 000000000000..d439593c7024 --- /dev/null +++ b/code/modules/mob/living/silicon/ai/ai_network/ai_network.dm @@ -0,0 +1,367 @@ +//////////////////////////////////////////// +// AI NETWORK DATUM +// each contiguous network of ethernet cables & AI machinery +///////////////////////////////////// +/datum/ai_network + var/number // unique id + var/list/cables = list() // all cables & junctions + var/list/nodes = list() // all connected machines + + var/list/ai_list = list() //List of all AIs in this network + var/list/reviving_ais = list() + + var/list/remote_networks = list() + + var/previous_ram = 0 + + var/datum/ai_shared_resources/resources + //Cash from crypto, can be withdrawn at network console + var/bitcoin_payout = 0 + + var/temp_limit = AI_TEMP_LIMIT + + var/local_cpu_usage = list() //How we use CPU locally + + var/label + + + + +/datum/ai_network/New() + SSmachines.ainets += src + label = num2hex(rand(1,65535), -1) + resources = new(starting_network = src) + +/datum/ai_network/Destroy() + //Go away references, you suck! + for(var/obj/structure/ethernet_cable/C in cables) + cables -= C + C.network = null + for(var/obj/machinery/ai/M in nodes) + nodes -= M + M.network = null + + resources.networks -= src + + if(!length(resources.networks)) + qdel(resources) + + resources = null + + SSmachines.ainets -= src + return ..() + +/datum/ai_network/process() + var/total_cpu = resources.total_cpu() + var/resources_assigned = resources.cpu_assigned[src] ? resources.cpu_assigned[src] : 0 + + if(local_cpu_usage[AI_CRYPTO]) + var/points = max(round(AI_RESEARCH_PER_CPU * (local_cpu_usage[AI_CRYPTO] * total_cpu * resources_assigned)), 0) + points = clamp(points, 0, MAX_AI_BITCOIN_MINED_PER_TICK) + bitcoin_payout += points * AI_BITCOIN_PRICE + + if(local_cpu_usage[AI_RESEARCH]) + var/points = max(round(AI_RESEARCH_PER_CPU * (local_cpu_usage[AI_RESEARCH] * total_cpu * resources_assigned)), 0) + points = clamp(points * AI_REGULAR_RESEARCH_POINT_MULTIPLIER, 0, MAX_AI_REGULAR_RESEARCH_PER_TICK) + SSresearch.science_tech.add_point_list(list(TECHWEB_POINT_TYPE_DEFAULT = points)) + + if(local_cpu_usage[AI_REVIVAL]) + var/points = max(round(AI_RESEARCH_PER_CPU * (local_cpu_usage[AI_REVIVAL] * total_cpu * resources_assigned)), 0) + points = max(0, points) + var/total_reviving_ais = reviving_ais.len + if(total_reviving_ais) + var/distributed_points = points / total_reviving_ais + for(var/obj/machinery/ai/data_core/DC in reviving_ais) + if(!DC.dead_ai_blackbox) + reviving_ais -= DC + DC.dead_ai_blackbox.processing_progress += distributed_points + DC.dead_ai_blackbox.living_ticks = AI_BLACKBOX_LIFETIME + if(DC.dead_ai_blackbox.processing_progress >= AI_BLACKBOX_PROCESSING_REQUIREMENT) + DC.dead_ai_blackbox.stored_ai.revive(TRUE) + DC.transfer_ai(DC.dead_ai_blackbox.stored_ai) + DC.dead_ai_blackbox.stored_ai = null + QDEL_NULL(DC.dead_ai_blackbox) + reviving_ais -= DC + + var/locally_used = 0 + for(var/A in local_cpu_usage) + locally_used += local_cpu_usage[A] + + var/research_points = max(round(AI_RESEARCH_PER_CPU * ((1 - locally_used) * total_cpu * resources_assigned)), 0) + SSresearch.science_tech.add_point_list(list(TECHWEB_POINT_TYPE_AI = research_points)) + + + +/datum/ai_network/proc/is_empty() + return !cables.len && !nodes.len + +//remove a cable from the current network +//if the network is then empty, delete it +//Warning : this proc DON'T check if the cable exists +/datum/ai_network/proc/remove_cable(obj/structure/ethernet_cable/C) + cables -= C + C.network = null + if(is_empty())//the network is now empty... + qdel(src)///... delete it + +//add a cable to the current network +//Warning : this proc DON'T check if the cable exists +/datum/ai_network/proc/add_cable(obj/structure/ethernet_cable/C) + if(C.network)// if C already has a network... + if(C.network == src) + return + else + C.network.remove_cable(C) //..remove it + C.network = src + cables +=C + +//remove a power machine from the current network +//if the network is then empty, delete it +//Warning : this proc DON'T check if the machine exists +/datum/ai_network/proc/remove_machine(obj/machinery/ai/M) + nodes -=M + M.network = null + if(is_empty())//the network is now empty... + qdel(src)///... delete it + +//add a power machine to the current network +//Warning : this proc DOESN'T check if the machine exists +/datum/ai_network/proc/add_machine(obj/machinery/ai/M) + if(M.network)// if M already has a network... + if(M.network == src) + return + else + M.disconnect_from_network()//..remove it + M.network = src + nodes[M] = M + +/datum/ai_network/proc/find_data_core() + for(var/obj/machinery/ai/data_core/core in get_all_nodes()) + if(!QDELETED(core) && core.can_transfer_ai()) + return core + +/datum/ai_network/proc/get_all_nodes(checked_nets = list()) + . = nodes.Copy() + for(var/datum/ai_network/net in resources.networks) + if(net == src) + continue + . += net.nodes + +/datum/ai_network/proc/get_local_nodes_oftype(type_to_check) + . = list() + for(var/A in nodes) + if(istype(A, type_to_check)) + . += A + + +/datum/ai_network/proc/get_all_ais(checked_nets = list()) + . = ai_list.Copy() + for(var/datum/ai_network/net in resources.networks) + if(net == src) + continue + . += net.ai_list + +/datum/ai_network/proc/remove_ai(mob/living/silicon/ai/AI) + resources.cpu_assigned[AI] = 0 + resources.ram_assigned[AI] = 0 + ai_list -= AI + + +/datum/ai_network/proc/update_resources() + resources?.update_resources() + + +/datum/ai_network/proc/total_cpu() + . = 0 + for(var/obj/machinery/ai/server_cabinet/C in nodes) + . += C.total_cpu + +/datum/ai_network/proc/total_ram() + . = 0 + for(var/obj/machinery/ai/server_cabinet/C in nodes) + . += C.total_ram + + +/datum/ai_network/proc/get_temp_limit() + return temp_limit + +/datum/ai_network/proc/total_cpu_assigned() + return resources.total_cpu_assigned() + +/datum/ai_network/proc/total_ram_assigned() + return resources.total_ram_assigned() + +/* +/datum/ai_network/proc/rebuild_remote(externally_linked = FALSE, touched_networks = list()) + if(!resources) + return + if(src in touched_networks) + return + touched_networks += src + var/list/networks_to_rebuild = list() + for(var/obj/machinery/ai/networking/N in nodes) + if(N.partner && N.partner.network && N.partner.network.resources) + if(N.partner.network in touched_networks) + message_admins("[REF(src)] found touched_network!") + continue + message_admins("[REF(src)] found no mismatched resources!") + if(N.partner.network.resources != resources) + if(length(N.partner.network.resources.networks) > length(resources.networks)) //We merge into the biggest network + N.partner.network.resources.add_resource(resources) + else + resources.add_resource(N.partner.network.resources) + message_admins("[REF(src)] actually rebuilt!") + externally_linked = TRUE + + networks_to_rebuild += N.partner.network + + + if(!externally_linked) + resources.split_resources(src) + + for(var/datum/ai_network/AN in networks_to_rebuild) + message_admins("Telling network [REF(AN)] to rebuild!") + AN.rebuild_remote(TRUE, touched_networks) + +*/ + +/datum/ai_network/proc/rebuild_remote(externally_linked = FALSE, touched_networks = list(), datum/ai_network/originator) + if(src in touched_networks) + return + + if(!originator) + originator = src + + var/list/found_networks = list() + for(var/obj/machinery/ai/networking/N in nodes) + if(N.partner && N.partner.network && N.partner.network.resources) + if(N.partner.network == src) + continue + externally_linked = TRUE + found_networks += N.partner.network + + if(!externally_linked) + if(resources && length(resources.networks) > 1) //We only split if we are actually connected to an external resource network + resources.split_resources(src) + + found_networks -= touched_networks + + uniqueList_inplace(found_networks) + + for(var/datum/ai_network/AN in found_networks) + if(originator.resources != AN.resources) + if(length(originator.resources.networks) > length(AN.resources.networks)) + originator.resources.add_resource(AN.resources) + else + AN.resources.add_resource(originator.resources) + AN.rebuild_remote(TRUE, found_networks + src, originator) + + + +/proc/merge_ainets(datum/ai_network/net1, datum/ai_network/net2) + if(!net1 || !net2) //if one of the network doesn't exist, return + return + + if(net1 == net2) //don't merge same networks + return + + //We assume net1 is larger. If net2 is in fact larger we are just going to make them switch places to reduce on code. + if(net1.cables.len < net2.cables.len) //net2 is larger than net1. Let's switch them around + var/temp = net1 + net1 = net2 + net2 = temp + + + //merge net2 into net1 + for(var/obj/structure/ethernet_cable/Cable in net2.cables) //merge cables + net1.add_cable(Cable) + + for(var/obj/machinery/ai/Node in net2.nodes) //merge power machines + if(!Node.connect_to_network()) + Node.disconnect_from_network() //if somehow we can't connect the machine to the new network, disconnect it from the old nonetheless + + + net1.ai_list += net2.ai_list //AIs can only be in 1 network at a time + /* + net1.rebuild_remote() + net2.rebuild_remote() */ + + net1.update_resources() + + + return net1 + + +//remove the old network and replace it with a new one throughout the network. +/proc/propagate_ai_network(obj/O, datum/ai_network/AN) + var/list/worklist = list() + var/list/found_machines = list() + var/index = 1 + var/obj/P = null + + worklist+=O //start propagating from the passed object + + while(index<=worklist.len) //until we've exhausted all power objects + P = worklist[index] //get the next power object found + index++ + + if( istype(P, /obj/structure/ethernet_cable)) + var/obj/structure/ethernet_cable/C = P + if(C.network != AN) //add it to the network, if it isn't already there + AN.add_cable(C) + worklist |= C.get_connections() //get adjacents power objects, with or without a network + else if(P.anchored && istype(P, /obj/machinery/ai)) + var/obj/machinery/ai/M = P + found_machines |= M //we wait until the network is fully propagates to connect the machines + else + continue + + //now that the network is set, connect found machines to it + for(var/obj/machinery/ai/PM in found_machines) + if(!PM.connect_to_network()) //couldn't find a node on its turf... + PM.disconnect_from_network() //... so disconnect if already on a network + + //AN.rebuild_remote() + + +/proc/ai_list(turf/T, source, d, unmarked = FALSE, cable_only = FALSE) + . = list() + + for(var/AM in T) + if(AM == source) + continue //we don't want to return source + + if(!cable_only && istype(AM, /obj/machinery/ai)) + var/obj/machinery/ai/P = AM + if(P.network == 0) + continue + + if(!unmarked || !P.network) //if unmarked we only return things with no network + if(d == 0) + . += P + + else if(istype(AM, /obj/structure/ethernet_cable)) + var/obj/structure/ethernet_cable/C = AM + + if(!unmarked || !C.network) + if(C.d1 == d || C.d2 == d) + . += C + return . + +/proc/_debug_ai_networks() + var/i = 1 + var/list/resource_list = list() + for(var/datum/ai_network/AN in SSmachines.ainets) + var/list/interconnections = list() + for(var/obj/machinery/ai/networking/N in AN.nodes) + if(N.partner && N.partner.network) + interconnections += "#[i] Networking[ADMIN_JMP(N)] connected to [ADMIN_JMP(N.partner)]/[REF(N.partner.network)] | Same resources: [N.partner.network.resources == AN.resources ? "YES" : "NO"]" + i++ + message_admins("Network: [REF(AN)] | Resources: [REF(AN.resources)]") + for(var/A in interconnections) + message_admins(A) + resource_list |= AN.resources + message_admins("----------------------------") + for(var/datum/ai_shared_resources/ASR in resource_list) + message_admins("Resource count [REF(ASR)], CPU: [ASR.total_cpu()] | RAM: [ASR.total_ram()]") + diff --git a/code/modules/mob/living/silicon/ai/ai_network/ethernet_cable.dm b/code/modules/mob/living/silicon/ai/ai_network/ethernet_cable.dm new file mode 100644 index 000000000000..ffd1aa2d56a7 --- /dev/null +++ b/code/modules/mob/living/silicon/ai/ai_network/ethernet_cable.dm @@ -0,0 +1,650 @@ +/////////////////////////////// +//CABLE STRUCTURE +/////////////////////////////// + + +//////////////////////////////// +// Definitions +//////////////////////////////// + +/* Cable directions (d1 and d2) + + + 9 1 5 + \ | / + 8 - 0 - 4 + / | \ + 10 2 6 + +If d1 = 0 and d2 = 0, there's no cable +If d1 = 0 and d2 = dir, it's a O-X cable, getting from the center of the tile to dir (knot cable) +If d1 = dir1 and d2 = dir2, it's a full X-X cable, getting from dir1 to dir2 +By design, d1 is the smallest direction and d2 is the highest +*/ + +/obj/structure/ethernet_cable + name = "ethernet cable" + desc = "A rigid and shielded cat 16a cable used for transferring vast amounts of data over long distances. Primarily used for large scale computing networks or advanced neural networks." + icon = 'icons/obj/power_cond/power_local.dmi' + icon_state = "0-1" + level = 1 //is underfloor + layer = ETHERNET_LAYER //Above hidden pipes, GAS_PIPE_HIDDEN_LAYER + anchored = TRUE + obj_flags = CAN_BE_HIT | ON_BLUEPRINTS + var/d1 = 0 // cable direction 1 (see above) + var/d2 = 1 // cable direction 2 (see above) + var/datum/ai_network/network + //Cables no longer keep a copy of the cable to be dropped in nullspace + + FASTDMM_PROP(\ + pipe_type = PIPE_TYPE_CABLE,\ + pipe_interference_group = list("cable"),\ + pipe_group = "cable-ethernet"\ + ) + + +// the ethernet cable object +/obj/structure/ethernet_cable/Initialize(mapload, param_color) + . = ..() + + // ensure d1 & d2 reflect the icon_state for entering and exiting cable + var/dash = findtext(icon_state, "-") + d1 = text2num( copytext( icon_state, 1, dash ) ) + d2 = text2num( copytext( icon_state, dash+1 ) ) + + var/turf/T = get_turf(src) // hide if turf is not intact + if(level==1) + hide(T.underfloor_accessibility < UNDERFLOOR_VISIBLE) + GLOB.ethernet_cable_list += src //add it to the global cable list + + update_icon() + +/obj/structure/ethernet_cable/Destroy() // called when a cable is deleted + if(network) + cut_cable_from_ainet() // update the ai networks + GLOB.ethernet_cable_list -= src //remove it from global cable list + return ..() // then go ahead and delete the cable + +/obj/structure/ethernet_cable/deconstruct(disassembled = TRUE) + if(!(flags_1 & NODECONSTRUCT_1)) + var/turf/T = loc + var/cableNum = 1 + if (d1*d2 > 0) //this be true if the cable has two directions, aka it contains two cables. If there is only one cable, one out of d1 and d2 will be zero + cableNum = 2 + var/newCables = new /obj/item/stack/ethernet_coil(T, cableNum) + TransferComponents(newCables) //this copies the fingerprints over to the new object + qdel(src) + +/////////////////////////////////// +// General procedures +/////////////////////////////////// + +//If underfloor, hide the cable +/obj/structure/ethernet_cable/hide(i) + + if(level == 1 && isturf(loc)) + invisibility = i ? INVISIBILITY_MAXIMUM : 0 + update_icon() + +/obj/structure/ethernet_cable/update_icon() + icon_state = "[d1]-[d2]" + +/obj/structure/ethernet_cable/proc/handlecable(obj/item/W, mob/user, params) + var/turf/T = get_turf(src) + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) + return + if(W.tool_behaviour == TOOL_WIRECUTTER) + user.visible_message("[user] cuts the ethernet cable.", span_notice("You cut the ethernet cable.")) + investigate_log("was cut by [key_name(usr)] in [AREACOORD(src)]", INVESTIGATE_WIRES) + add_fingerprint(user) + deconstruct() + return + + else if(istype(W, /obj/item/stack/ethernet_coil)) + var/obj/item/stack/ethernet_coil/coil = W + if (coil.get_amount() < 1) + to_chat(user, span_warning("Not enough cable!")) + return + coil.cable_join(src, user) + + else if(W.tool_behaviour == TOOL_MULTITOOL) + if(!network) + return + to_chat(user, span_danger("Connected CPU: [network.resources.total_cpu()]THz\nConnected RAM: [network.resources.total_ram()]TB\nHosted AIs: [network.ai_list.len]\nNetwork Count: [network.resources.networks.len]")) + + + + else if(istype(W, /obj/item/modular_computer)) + var/obj/item/modular_computer/MC = W + + if(MC.all_components[MC_AI_NETWORK]) + var/obj/item/computer_hardware/ai_interface/ai_interface = MC.all_components[MC_AI_NETWORK] + if(ai_interface) + if(ai_interface.connected_cable != src) + ai_interface.connect_cable(src) + to_chat(user, span_notice("You connect to the ethernet cable.")) + else + to_chat(user, span_warning("[MC] has no AI interface!")) + + + add_fingerprint(user) + +// Items usable on a cable : +// - Wirecutters : cut it duh ! +// - Cable coil : merge cables +// - Multitool : get the network stats +// +/obj/structure/ethernet_cable/attackby(obj/item/W, mob/user, params) + handlecable(W, user, params) + + +/obj/structure/ethernet_cable/singularity_pull(S, current_size) + ..() + if(current_size >= STAGE_FIVE) + deconstruct() + +///////////////////////////////////////////////// +// Cable laying helpers +//////////////////////////////////////////////// + +//handles merging diagonally matching cables +//for info : direction^3 is flipping horizontally, direction^12 is flipping vertically +/obj/structure/ethernet_cable/proc/mergeDiagonalsNetworks(direction) + + //search for and merge diagonally matching cables from the first direction component (north/south) + var/turf/T = get_step(src, direction&3)//go north/south + + for(var/obj/structure/ethernet_cable/C in T) + + if(!C) + continue + + if(src == C) + continue + + if(C.d1 == (direction^3) || C.d2 == (direction^3)) //we've got a diagonally matching cable + if(!C.network) //if the matching cable somehow got no ai network, make him one (should not happen for cables) + var/datum/ai_network/newAN = new() + newAN.add_cable(C) + + if(network) //if we already have a ai network, then merge the two ai networks + merge_ainets(network,C.network) + //network.rebuild_remote() + else + C.network.add_cable(src) //else, we simply connect to the matching cable ai network + C.network.rebuild_remote() + + //the same from the second direction component (east/west) + T = get_step(src, direction&12)//go east/west + + for(var/obj/structure/ethernet_cable/C in T) + + if(!C) + continue + + if(src == C) + continue + if(C.d1 == (direction^12) || C.d2 == (direction^12)) //we've got a diagonally matching cable + if(!C.network) //if the matching cable somehow got no ai network, make him one (should not happen for cables) + var/datum/ai_network/newAN = new() + newAN.add_cable(C) + + if(network) //if we already have a ai network, then merge the two ai networks + merge_ainets(network,C.network) + //network.rebuild_remote() + else + C.network.add_cable(src) //else, we simply connect to the matching cable ai network + C.network.rebuild_remote() + + + +// merge with the ai networks of power objects in the given direction +/obj/structure/ethernet_cable/proc/mergeConnectedNetworks(direction) + + var/fdir = (!direction)? 0 : turn(direction, 180) //flip the direction, to match with the source position on its turf + + if(!(d1 == direction || d2 == direction)) //if the cable is not pointed in this direction, do nothing + return + + var/turf/TB = get_step(src, direction) + + for(var/obj/structure/ethernet_cable/C in TB) + + if(!C) + continue + + if(src == C) + continue + + if(C.d1 == fdir || C.d2 == fdir) //we've got a matching cable in the neighbor turf + if(!C.network) //if the matching cable somehow got no ai network, make him one (should not happen for cables) + var/datum/ai_network/newAN = new(C.loc.z) + newAN.add_cable(C) + + if(network) //if we already have a ai network, then merge the two ai networks + merge_ainets(network,C.network) + //network.rebuild_remote() + else + C.network.add_cable(src) //else, we simply connect to the matching cable ai network + C.network.rebuild_remote() + +// merge with the ai networks of power objects in the source turf +/obj/structure/ethernet_cable/proc/mergeConnectedNetworksOnTurf() + var/list/to_connect = list() + + if(!network) //if we somehow have no ai network, make one (should not happen for cables) + var/datum/ai_network/newAN = new(loc.z) + newAN.add_cable(src) + + //first let's add turf cables to our ai network + //then we'll connect machines on turf with a node cable is present + for(var/AM in loc) + if(istype(AM, /obj/structure/ethernet_cable)) + var/obj/structure/ethernet_cable/C = AM + if(C.d1 == d1 || C.d2 == d1 || C.d1 == d2 || C.d2 == d2) //only connected if they have a common direction + if(C.network == network) + continue + if(C.network) + merge_ainets(network, C.network) + //network.rebuild_remote() + else + network.add_cable(C) //the cable was ai networkless, let's just add it to our ai network + network.rebuild_remote() + + else if(istype(AM, /obj/machinery/ai)) //other power machines + var/obj/machinery/ai/M = AM + + if(M.network == network) + continue + + to_connect += M //we'll connect the machines after all cables are merged + + + //now that cables are done, let's connect found machines + for(var/obj/machinery/ai/PM in to_connect) + if(!PM.connect_to_network()) + PM.disconnect_from_network() //if we somehow can't connect the machine to the new ai network, remove it from the old nonetheless + + +////////////////////////////////////////////// +// ai networks handling helpers +////////////////////////////////////////////// + +//if ai_networkless_only = 1, will only get connections without ai network +/obj/structure/ethernet_cable/proc/get_connections(ai_networkless_only = 0) + . = list() // this will be a list of all connected power objects + var/turf/T + + //get matching cables from the first direction + if(d1) //if not a node cable + T = get_step(src, d1) + if(T) + . += ai_list(T, src, turn(d1, 180), ai_networkless_only) //get adjacents matching cables + + if(d1&(d1-1)) //diagonal direction, must check the 4 possibles adjacents tiles + T = get_step(src,d1&3) // go north/south + if(T) + . += ai_list(T, src, d1 ^ 3, ai_networkless_only) //get diagonally matching cables + T = get_step(src,d1&12) // go east/west + if(T) + . += ai_list(T, src, d1 ^ 12, ai_networkless_only) //get diagonally matching cables + + . += ai_list(loc, src, d1, ai_networkless_only) //get on turf matching cables + + //do the same on the second direction (which can't be 0) + T = get_step(src, d2) + if(T) + . += ai_list(T, src, turn(d2, 180), ai_networkless_only) //get adjacents matching cables + + if(d2&(d2-1)) //diagonal direction, must check the 4 possibles adjacents tiles + T = get_step(src,d2&3) // go north/south + if(T) + . += ai_list(T, src, d2 ^ 3, ai_networkless_only) //get diagonally matching cables + T = get_step(src,d2&12) // go east/west + if(T) + . += ai_list(T, src, d2 ^ 12, ai_networkless_only) //get diagonally matching cables + . += ai_list(loc, src, d2, ai_networkless_only) //get on turf matching cables + + return . + +//should be called after placing a cable which extends another cable, creating a "smooth" cable that no longer terminates in the centre of a turf. +//needed as this can, unlike other placements, disconnect cables +/obj/structure/ethernet_cable/proc/denode() + var/turf/T1 = loc + if(!T1) + return + + var/list/powerlist = ai_list(T1,src,0,0) //find the other cables that ended in the centre of the turf, with or without a ai network + if(powerlist.len>0) + var/datum/ai_network/AN = new() + propagate_ai_network(powerlist[1],AN) //propagates the new ai network beginning at the source cable + + if(AN.is_empty()) //can happen with machines made nodeless when smoothing cables + qdel(AN) + +/obj/structure/ethernet_cable/proc/auto_propogate_cut_cable(obj/O, ) + if(O && !QDELETED(O)) + var/datum/ai_network/newAN = new()// creates a new ai network... + + propagate_ai_network(O, newAN)//... and propagates it to the other side of the cable + + + +// cut the cable's ai network at this cable and updates the powergrid +/obj/structure/ethernet_cable/proc/cut_cable_from_ainet(remove=TRUE) + var/turf/T1 = loc + var/list/P_list + if(!T1) + return + if(d1) + T1 = get_step(T1, d1) + P_list = ai_list(T1, src, turn(d1,180),0,cable_only = 1) // what adjacently joins on to cut cable... + + P_list += ai_list(loc, src, d1, 0, cable_only = 1)//... and on turf + + if(P_list.len == 0)//if nothing in both list, then the cable was a lone cable, just delete it and its ai network + network.remove_cable(src) + + for(var/obj/machinery/ai/P in T1)//check if it was powering a machine + if(!P.connect_to_network()) //can't find a node cable on a the turf to connect to + P.disconnect_from_network() //remove from current network (and delete ai network) + return + + var/obj/O = P_list[1] + // remove the cut cable from its turf and ai network, so that it doesn't get count in propagate_network worklist + if(remove) + moveToNullspace() + + network.remove_cable(src) //remove the cut cable from its ai network + + + addtimer(CALLBACK(O, .proc/auto_propogate_cut_cable, O), 0) //so we don't rebuild the network X times when singulo/explosion destroys a line of X cables + + // Disconnect machines connected to nodes + if(d1 == 0) // if we cut a node (O-X) cable + for(var/obj/machinery/ai/P in T1) + if(!P.connect_to_network()) //can't find a node cable on a the turf to connect to + P.disconnect_from_network() //remove from current network + + +/////////////////////////////////////////////// +// The cable coil object, used for laying cable +/////////////////////////////////////////////// + +//////////////////////////////// +// Definitions +//////////////////////////////// + +/obj/item/stack/ethernet_coil + name = "ethernet cable coil" + desc = "A coil of shielded ethernet cable." + custom_price = 25 + gender = NEUTER //That's a cable coil sounds better than that's some cable coils + icon = 'icons/obj/power.dmi' + icon_state = "wire" + item_state = "coil" + lefthand_file = 'icons/mob/inhands/equipment/tools_lefthand.dmi' + righthand_file = 'icons/mob/inhands/equipment/tools_righthand.dmi' + max_amount = MAXCOIL + amount = MAXCOIL + merge_type = /obj/item/stack/ethernet_coil // This is here to let its children merge between themselves + + throwforce = 0 + w_class = WEIGHT_CLASS_SMALL + throw_speed = 3 + throw_range = 5 + materials = list(/datum/material/iron=10, /datum/material/glass=5, /datum/material/gold=1) + slot_flags = ITEM_SLOT_BELT + attack_verb = list("whipped", "lashed", "disciplined", "flogged") + singular_name = "ethernet cable piece" + full_w_class = WEIGHT_CLASS_SMALL + grind_results = list(/datum/reagent/copper = 2) //2 copper per cable in the coil + usesound = 'sound/items/deconstruct.ogg' + +/obj/item/stack/ethernet_coil/cyborg + is_cyborg = TRUE + materials = list() + cost = 1 + +/obj/item/stack/ethernet_coil/suicide_act(mob/user) + if(locate(/obj/structure/chair/stool) in get_turf(user)) + user.visible_message(span_suicide("[user] is making a noose with [src]! It looks like [user.p_theyre()] trying to commit suicide!")) + else + user.visible_message(span_suicide("[user] is trying to upload [user.p_them()]selves to the afterlife with [src]! It looks like [user.p_theyre()] trying to commit suicide!")) + return(OXYLOSS) + +/obj/item/stack/ethernet_coil/Initialize(mapload, new_amount = null, param_color = null) + . = ..() + + pixel_x = rand(-2,2) + pixel_y = rand(-2,2) + update_icon() + +/////////////////////////////////// +// General procedures +/////////////////////////////////// + + +//you can use wires to heal robotics +/obj/item/stack/ethernet_coil/attack(mob/living/carbon/human/H, mob/user) + if(!istype(H)) + return ..() + + var/obj/item/bodypart/affecting = H.get_bodypart(check_zone(user.zone_selected)) + if(affecting.burn_dam <= 0) + to_chat(user, span_warning("[affecting] is already in good condition!")) + return FALSE + if(affecting && affecting.status == BODYPART_ROBOTIC) + user.visible_message(span_notice("[user] starts to fix some of the wires in [H]'s [affecting.name]."), span_notice("You start fixing some of the wires in [H == user ? "your" : "[H]'s"] [affecting.name].")) + heal_robo_limb(src, H, user, 0, 15) + user.visible_message(span_notice("[user] fixes the wires in [H]'s [affecting.name]."), span_notice("You fix the wires in [H == user ? "your" : "[H]'s"] [affecting.name].")) + return + else + return ..() + +/obj/item/stack/ethernet_coil/proc/heal_robo_limb(obj/item/I, mob/living/carbon/human/H, mob/user, brute_heal, burn_heal) + if(I.use_tool(H, user, 2 SECONDS, amount=1)) + if(item_heal_robotic(H, user, brute_heal, burn_heal)) + return heal_robo_limb(I, H, user, brute_heal, burn_heal) + return TRUE + +/obj/item/stack/ethernet_coil/update_icon() + icon_state = "[initial(icon_state)][amount < 3 ? amount : ""]" + name = "ethernet cable [amount < 3 ? "piece" : "coil"]" + +/obj/item/stack/ethernet_coil/attack_hand(mob/user) + . = ..() + if(.) + return + var/obj/item/stack/ethernet_coil/new_cable = ..() + if(istype(new_cable)) + new_cable.update_icon() + +//add cables to the stack +/obj/item/stack/ethernet_coil/proc/give(extra) + if(amount + extra > max_amount) + amount = max_amount + else + amount += extra + update_icon() + + + +/////////////////////////////////////////////// +// Cable laying procedures +////////////////////////////////////////////// + +/obj/item/stack/ethernet_coil/proc/get_new_cable(location) + var/path = /obj/structure/ethernet_cable + return new path(location) + +// called when cable_coil is clicked on a turf +/obj/item/stack/ethernet_coil/proc/place_turf(turf/T, mob/user, dirnew) + if(!isturf(user.loc)) + return + + if(!isturf(T) || T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE || !T.can_have_cabling()) + to_chat(user, span_warning("You can only lay cables on top of exterior catwalks and plating!")) + return + + if(get_amount() < 1) // Out of cable + to_chat(user, span_warning("There is no cable left!")) + return + + if(get_dist(T,user) > 1) // Too far + to_chat(user, span_warning("You can't lay cable at a place that far away!")) + return + + var/dirn + if(!dirnew) //If we weren't given a direction, come up with one! (Called as null from catwalk.dm and floor.dm) + if(user.loc == T) + dirn = user.dir //If laying on the tile we're on, lay in the direction we're facing + else + dirn = get_dir(T, user) + else + dirn = dirnew + + + for(var/obj/structure/ethernet_cable/LC in T) + if(LC.d2 == dirn && LC.d1 == 0) + to_chat(user, span_warning("There's already a cable at that position!")) + return + + var/obj/structure/ethernet_cable/C = get_new_cable(T) + + //set up the new cable + C.d1 = 0 //it's a O-X node cable + C.d2 = dirn + C.add_fingerprint(user) + C.update_icon() + + //create a new ai network with the cable, if needed it will be merged later + var/datum/ai_network/AN = new() + AN.add_cable(C) + + C.mergeConnectedNetworks(C.d2) //merge the ai network with adjacents ai networks + C.mergeConnectedNetworksOnTurf() //merge the ai network with on turf ai networks + + if(C.d2 & (C.d2 - 1))// if the cable is layed diagonally, check the others 2 possible directions + C.mergeDiagonalsNetworks(C.d2) + + use(1) + + return C + +// called when cable_coil is click on an installed obj/cable +// or click on a turf that already contains a "node" cable +/obj/item/stack/ethernet_coil/proc/cable_join(obj/structure/ethernet_cable/C, mob/user, var/showerror = TRUE, forceddir) + var/turf/U = user.loc + if(!isturf(U)) + return + + var/turf/T = C.loc + + if(!isturf(T) || T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) // sanity checks, also stop use interacting with T-scanner revealed cable + return + + if(get_dist(C, user) > 1) // make sure it's close enough + to_chat(user, span_warning("You can't lay cable at a place that far away!")) + return + + + if(U == T && !forceddir) //if clicked on the turf we're standing on and a direction wasn't supplied, try to put a cable in the direction we're facing + place_turf(T,user) + return + + var/dirn = get_dir(C, user) + if(forceddir) + dirn = forceddir + + // one end of the clicked cable is pointing towards us and no direction was supplied + if((C.d1 == dirn || C.d2 == dirn) && !forceddir) + if(!U.can_have_cabling()) //checking if it's a plating or catwalk + if (showerror) + to_chat(user, span_warning("You can only lay cables on catwalks and plating!")) + return + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE) //can't place a cable if it's a plating with a tile on it + to_chat(user, span_warning("You can't lay cable there unless the floor tiles are removed!")) + return + else + // cable is pointing at us, we're standing on an open tile + // so create a stub pointing at the clicked cable on our tile + + var/fdirn = turn(dirn, 180) // the opposite direction + + for(var/obj/structure/ethernet_cable/LC in U) // check to make sure there's not a cable there already + if(LC.d1 == fdirn || LC.d2 == fdirn) + if (showerror) + to_chat(user, span_warning("There's already a cable at that position!")) + return + + var/obj/structure/ethernet_cable/NC = get_new_cable (U) + + NC.d1 = 0 + NC.d2 = fdirn + NC.add_fingerprint(user) + NC.update_icon() + + //create a new ai network with the cable, if needed it will be merged later + var/datum/ai_network/newAN = new() + newAN.add_cable(NC) + + NC.mergeConnectedNetworks(NC.d2) //merge the ai network with adjacents ai networks + NC.mergeConnectedNetworksOnTurf() //merge the ai network with on turf ai networks + + if(NC.d2 & (NC.d2 - 1))// if the cable is layed diagonally, check the others 2 possible directions + NC.mergeDiagonalsNetworks(NC.d2) + + + use(1) + + return + + // exisiting cable doesn't point at our position or we have a supplied direction, so see if it's a stub + else if(C.d1 == 0) + // if so, make it a full cable pointing from it's old direction to our dirn + var/nd1 = C.d2 // these will be the new directions + var/nd2 = dirn + + + if(nd1 > nd2) // swap directions to match icons/states + nd1 = dirn + nd2 = C.d2 + + + for(var/obj/structure/ethernet_cable/LC in T) // check to make sure there's no matching cable + if(LC == C) // skip the cable we're interacting with + continue + if((LC.d1 == nd1 && LC.d2 == nd2) || (LC.d1 == nd2 && LC.d2 == nd1) ) // make sure no cable matches either direction + if (showerror) + to_chat(user, span_warning("There's already a cable at that position!")) + + return + + + C.update_icon() + + C.d1 = nd1 + C.d2 = nd2 + + //updates the stored cable coil + + C.add_fingerprint(user) + C.update_icon() + + + C.mergeConnectedNetworks(C.d1) //merge the ai networks... + C.mergeConnectedNetworks(C.d2) //...in the two new cable directions + C.mergeConnectedNetworksOnTurf() + + if(C.d1 & (C.d1 - 1))// if the cable is layed diagonally, check the others 2 possible directions + C.mergeDiagonalsNetworks(C.d1) + + if(C.d2 & (C.d2 - 1))// if the cable is layed diagonally, check the others 2 possible directions + C.mergeDiagonalsNetworks(C.d2) + + + use(1) + + C.denode()// this call may have disconnected some cables that terminated on the centre of the turf, if so split the ai networks. + return diff --git a/code/modules/mob/living/silicon/ai/ai_network/networking_machines.dm b/code/modules/mob/living/silicon/ai/ai_network/networking_machines.dm new file mode 100644 index 000000000000..3b9c9405d53e --- /dev/null +++ b/code/modules/mob/living/silicon/ai/ai_network/networking_machines.dm @@ -0,0 +1,270 @@ +GLOBAL_LIST_EMPTY(ai_networking_machines) + +/obj/machinery/ai/networking + name = "networking machine" + desc = "A high powered combined transmitter and receiver. Capable of connecting remote AI networks with near-zero delay. It is possible to manually connect other machines using a multitool." + icon = 'goon/icons/obj/power.dmi' + icon_state = "sp_base" + density = TRUE + use_power = NO_POWER_USE + idle_power_usage = 0 + active_power_usage = 0 + max_integrity = 150 + + circuit = /obj/item/circuitboard/machine/networking_machine + + var/label + //For mapping, will connect to machine with this label if found + var/roundstart_connection + + var/mutable_appearance/panelstructure + var/mutable_appearance/paneloverlay + + var/obj/machinery/ai/networking/partner + var/rotation_to_partner = 0 + var/locked = FALSE + var/obj/machinery/ai/networking/remote_connection_attempt + var/mob/remote_control + + + + +/obj/machinery/ai/networking/Initialize(mapload) + . = ..() + if(!label) + label = num2hex(rand(1,65535), -1) + GLOB.ai_networking_machines += src + panelstructure = mutable_appearance(icon, "solar_panel", FLY_LAYER) + paneloverlay = mutable_appearance(icon, "solar_panel-o", FLY_LAYER) + paneloverlay.color = "#599ffa" + update_icon() + +/obj/machinery/ai/networking/Destroy(mapload) + GLOB.ai_networking_machines -= src + disconnect() + . = ..() + +/obj/machinery/ai/networking/attackby(obj/item/W, mob/living/user, params) + if(W.tool_behaviour == TOOL_MULTITOOL) + if(partner) + to_chat(user, span_warning("This machine is already connected to a different machine! Disconnect it using the controls or a wirecutter first!")) + return TRUE + remote_connection_attempt = null + var/targets = list() + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + if(N == src) + continue + if(N.z != src.z) + continue + if(N.partner) + continue + targets[N.label] = N + var/attempt_connect = input(user, "Select the machine you wish to attempt connecting to.") as null|anything in targets + if(!attempt_connect) + return TRUE + var/obj/machinery/ai/networking/remote_target = locate(targets[attempt_connect]) in GLOB.ai_networking_machines + if(!remote_target) + return TRUE + remote_connection_attempt = remote_target + to_chat(user, span_notice("The machine is ready to establish connection. You must now rotate it so it faces the other machine! Rotation is done using a wrench, and the connection can then be finalized with a screwdriver when aligned.")) + return TRUE + + if(W.tool_behaviour == TOOL_WRENCH) + if(partner) + to_chat(user, span_warning("This machine is already connected to a different machine!")) + return TRUE + var/new_rotation = input(user, "Set rotation (0-360): ") as null|num + if(isnull(new_rotation)) + rotation_to_partner = 0 + else + new_rotation = clamp(new_rotation, 0, 360) + rotation_to_partner = new_rotation + + update_icon() + return TRUE + + if(W.tool_behaviour == TOOL_SCREWDRIVER) + if(partner) + to_chat(user, span_warning("This machine is already connected to a different machine!")) + return TRUE + if(!remote_connection_attempt) + to_chat(user, span_warning("You need to initialize a manual override using a wrench to connect to something!")) + return TRUE + var/actual_angle = Get_Angle(src, remote_connection_attempt) + if(rotation_to_partner < actual_angle + 20 && rotation_to_partner > actual_angle - 20) + connect_to_partner(remote_connection_attempt) + to_chat(user, span_notice("You successfully connect to [remote_connection_attempt.label]!")) + return TRUE + to_chat(user, span_warning("Unable to establish connection!")) + return TRUE + + + if(W.tool_behaviour == TOOL_WIRECUTTER) + if(partner) + to_chat(user, span_notice("You disconnect the remote connection.")) + disconnect() + return TRUE + to_chat(user, span_warning("The machine isn't connected!")) + return TRUE + + if(W.tool_behaviour == TOOL_CROWBAR) + if(default_deconstruction_crowbar(W, TRUE)) + return TRUE + + if(default_deconstruction_screwdriver(user, "expansion_bus_o", "expansion_bus", W)) + return TRUE + + return ..() + +/obj/machinery/ai/networking/proc/roundstart_connect(mapload) + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + if(partner) + break + if(N == src) + continue + if(N.partner) + continue + if(roundstart_connection && N.label == roundstart_connection) + connect_to_partner(N) + break + if(!roundstart_connection) + connect_to_partner(N) + break + + +/obj/machinery/ai/networking/update_icon() + ..() + cut_overlays() + var/matrix/turner = matrix() + turner.Turn(rotation_to_partner) + panelstructure.transform = turner + paneloverlay.transform = turner + add_overlay(list(paneloverlay, panelstructure)) + +/obj/machinery/ai/networking/proc/disconnect() + if(partner) + var/datum/ai_network/AN = partner.network + partner.rotation_to_partner = 0 + partner.update_icon() + partner.partner = null + partner = null + AN.rebuild_remote() + network.rebuild_remote() + rotation_to_partner = 0 + update_icon() + + + +/obj/machinery/ai/networking/proc/connect_to_partner(obj/machinery/ai/networking/target, forced = FALSE) + remote_connection_attempt = null + if(target.partner) + return + if(target == src) + return + if(target.locked && !forced) + return + + partner = target + rotation_to_partner = Get_Angle(src, partner) + target.partner = src + target.rotation_to_partner = Get_Angle(target, src) + target.update_icon() + + + network.rebuild_remote() + + update_icon() + + +/obj/machinery/ai/networking/ui_status(mob/user) + . = ..() + if (!QDELETED(remote_control) && user == remote_control) + . = UI_INTERACTIVE + +/obj/machinery/ai/networking/ui_interact(mob/user, datum/tgui/ui) + ui = SStgui.try_update_ui(user, src, ui) + if(!ui) + ui = new(user, src, "AiNetworking", name) + ui.open() + +/obj/machinery/ai/networking/ui_data(mob/living/carbon/human/user) + var/list/data = list() + + data["is_connected"] = partner ? partner.label : FALSE + data["label"] = label + + data["locked"] = locked + + data["possible_targets"] = list() + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + if(N == src) + continue + if(N.z != src.z) + continue + if(N.locked) + continue + data["possible_targets"] += N.label + + return data + +/obj/machinery/ai/networking/ui_act(action, params) + if(..()) + return + + switch(action) + if("switch_label") + if(locked) + return + var/new_label = stripped_input(usr, "Enter new label", "Set label", max_length = 16) + if(new_label) + if(isnotpretty(new_label)) + to_chat(usr, span_notice("The machine rejects the input. See rule 0.1.")) + var/log_message = "[key_name(usr)] just tripped a pretty filter: '[new_label]'." + message_admins(log_message) + log_say(log_message) + return + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + if(N.label == new_label) + to_chat(usr, span_warning("A machine with this label already exists!")) + return + label = new_label + . = TRUE + if("connect") + if(locked) + return + var/target_label = params["target_label"] + if(target_label == label) + return + for(var/obj/machinery/ai/networking/N in GLOB.ai_networking_machines) + if(N.z != src.z) + return + if(N.label == target_label) + if(N.locked) + to_chat(usr, span_warning("Unable to connect to '[target_label]'! It seems to be locked.")) + return + if(N.partner) + to_chat(usr, span_warning("Unable to connect to '[target_label]'! It seems to already have a connection established.")) + return + connect_to_partner(N) + to_chat(usr, span_notice("Connection established to '[target_label]'.")) + return + . = TRUE + if("disconnect") + if(locked) + return + disconnect() + . = TRUE + if("toggle_lock") + locked = !locked + . = TRUE + +/obj/machinery/ai/networking/connect_to_network() + . = ..() + if(partner) + network.rebuild_remote() + +/obj/machinery/ai/networking/disconnect_from_network() + var/datum/ai_network/temp = network + . = ..() + if(partner) + temp.rebuild_remote() diff --git a/code/modules/mob/living/silicon/ai/ai_network/shared_resources.dm b/code/modules/mob/living/silicon/ai/ai_network/shared_resources.dm new file mode 100644 index 000000000000..1ec291ed1b95 --- /dev/null +++ b/code/modules/mob/living/silicon/ai/ai_network/shared_resources.dm @@ -0,0 +1,275 @@ +/datum/ai_shared_resources + ///Where our RAM is coming from. Associative array where the network is the key + var/ram_sources = list() + ///Where our CPU is coming from. Associative array where the network is the key + var/cpu_sources = list() + + ///Where our CPU is assigned to. Associative where either an AI or a network has values. Max total value = 1 (100%) + var/list/cpu_assigned = list() + ///Where our CPU is assigned to. Associative where either an AI or a network has values + var/list/ram_assigned = list() + + ///List of all networks we are connected to + var/list/networks = list() + + ///How much RAM we had before updating resources + var/previous_ram = 0 + + ///If resource allocation can only be changed physically at a console by a human + var/human_lock = FALSE + + + +/datum/ai_shared_resources/New(network_assigned_cpu, network_assigned_ram, datum/ai_network/split_network, datum/ai_network/starting_network, _human_lock = FALSE) + if((network_assigned_ram || network_assigned_cpu) && split_network) + ram_assigned = network_assigned_ram + cpu_assigned = network_assigned_cpu + + if(split_network) + split_network.resources = src + networks |= split_network + update_resources() + + if(starting_network) + starting_network.resources = src + networks |= starting_network + + for(var/datum/ai_network/AN in networks) + AN.rebuild_remote() + + START_PROCESSING(SSobj, src) + + human_lock = _human_lock + +/datum/ai_shared_resources/Destroy(network_assigned_cpu, network_assigned_ram, datum/ai_network/split_network, datum/ai_network/starting_network) + STOP_PROCESSING(SSobj, src) + . = ..() + +/datum/ai_shared_resources/process() + for(var/datum/ai_network/net in networks) + net.process() + + //Networks automatically use their unspent CPU to research, this just catches cluster unassigned CPU. Local clusters can have their points boosted by local AIs + var/unused_cpu = 1 - total_cpu_assigned() + + var/research_points = max(round(AI_RESEARCH_PER_CPU * (unused_cpu * total_cpu())), 0) + SSresearch.science_tech.add_point_list(list(TECHWEB_POINT_TYPE_AI = research_points)) + + + + +/datum/ai_shared_resources/proc/total_cpu_assigned() + var/total = 0 + for(var/AI in cpu_assigned) + total += cpu_assigned[AI] + return total + +/datum/ai_shared_resources/proc/total_ram_assigned() + var/total = 0 + for(var/AI in ram_assigned) + total += (ram_assigned[AI]) + return total + +/datum/ai_shared_resources/proc/total_cpu() + var/total = 0 + for(var/C in cpu_sources) + total += cpu_sources[C] + return total + +/datum/ai_shared_resources/proc/total_ram() + var/total = 0 + for(var/C in ram_sources) + total += ram_sources[C] + return total + +/datum/ai_shared_resources/proc/update_resources() + previous_ram = total_ram() + ram_sources = list() + cpu_sources = list() + for(var/datum/ai_network/N in networks) + ram_sources[N] += N.total_ram() + cpu_sources[N] += N.total_cpu() + update_allocations() + +/datum/ai_shared_resources/proc/add_resource(datum/ai_shared_resources/new_resources) + + for(var/RU in new_resources.ram_assigned) + ram_assigned[RU] = new_resources.ram_assigned[RU] + + for(var/CU in cpu_assigned) //We split the CPUs 50/50 + cpu_assigned[CU] = round((cpu_assigned[CU] * 0.5) * 100) / 100 + + for(var/CU in new_resources.cpu_assigned) + cpu_assigned[CU] = round((new_resources.cpu_assigned[CU] * 0.5) * 100) / 100 + + for(var/datum/ai_network/N in new_resources.networks) + networks |= N + N.resources = src + + update_resources() + update_allocations() + qdel(new_resources) + +/datum/ai_shared_resources/proc/split_resources(datum/ai_network/split_network) + var/network_ram_assign = list() + var/network_cpu_assign = list() + + + var/split_network_cpu = 0 + var/network_ais = split_network.ai_list + for(var/A in cpu_assigned) + if(A in network_ais || A == split_network) + network_cpu_assign[A] = cpu_assigned[A] + split_network_cpu += cpu_assigned[A] + cpu_assigned[A] = 0 + + //Normalize CPU so 100% is used in the new network if 100% was used in total before + var/total_usage = total_cpu_assigned() //We normalise around this value, so the split network CPU usage will (approximately) end up at this too + if(split_network_cpu) + for(var/A in network_cpu_assign) + var/split_usage = network_cpu_assign[A] / split_network_cpu + network_cpu_assign[A] = 1 * round(split_usage, 0.01) + + //We do the same for the network we leave behid + if(total_usage) + for(var/A in cpu_assigned) + var/split_usage = cpu_assigned[A] / total_usage + cpu_assigned[A] = 1 * round(split_usage, 0.01) + + + //Not needed for RAM since it's not a percentage + for(var/A in ram_assigned) + if(A in network_ais || A == split_network) + network_ram_assign[A] = ram_assigned[A] + ram_assigned[A] = 0 + + networks -= split_network + update_resources() + + new /datum/ai_shared_resources(network_cpu_assign, network_ram_assign, split_network, _human_lock = human_lock) + + if(!length(networks)) + qdel(src) + + +/datum/ai_shared_resources/proc/update_allocations() + //Do we have the same amount or more RAM than before? Do nothing + var/total_ram = total_ram() + if(total_ram >= previous_ram) + return + //Find out how much is actually assigned. We can have more total_cpu than the sum of cpu_assigned. Same with RAM + var/total_assigned_ram = total_ram_assigned() + //If we have less assigned ram than we have cpu and ram, just return, everything is fine. + if(total_assigned_ram < total_ram) + return + + //Copy the lists of assigned resources so we don't manipulate the list prematurely. + var/list/ram_assigned_copy = ram_assigned.Copy() + //List of touched AIs so we can notify them at the end. + var/list/affected_AIs = list() + + + if(total_assigned_ram > total_ram) + var/needed_amount = total_assigned_ram - total_ram + for(var/A in ram_assigned_copy) + if(isAI(A)) + var/mob/living/silicon/ai/AI = A + if((ram_assigned_copy[AI]) >= needed_amount) + ram_assigned_copy[AI] -= needed_amount + total_assigned_ram -= needed_amount + affected_AIs |= AI + break + else if(ram_assigned_copy[AI]) + var/amount = ram_assigned_copy[AI] + ram_assigned_copy[AI] -= amount + affected_AIs |= AI + needed_amount -= amount + total_assigned_ram -= amount + if(total_ram >= total_assigned_ram) + break + else //If we're not an AI we are a network, networks have no programs to stop (for now) + if((ram_assigned_copy[A]) >= needed_amount) + ram_assigned_copy[A] -= needed_amount + total_assigned_ram -= needed_amount + break + else if(ram_assigned_copy[A]) + var/amount = ram_assigned_copy[A] + ram_assigned_copy[A] -= amount + needed_amount -= amount + total_assigned_ram -= amount + if(total_ram >= total_assigned_ram) + break + //Set the actual values of the assigned to our manipulated copies. Bypass helper procs as we assume we're correct. + ram_assigned = ram_assigned_copy + + to_chat(affected_AIs, span_warning("You have been deducted memory capacity. Please contact your network administrator if you believe this to be an error.")) + + + +/datum/ai_shared_resources/proc/set_cpu(target, amount) + if(!istype(target, /datum/ai_network) && !isAI(target)) + stack_trace("Attempted to set_cpu with non-AI/network target! T: [target]") + return + + if(!target) + return + if(amount > 1 || amount < 0) + return + cpu_assigned[target] = amount + + update_allocations() + + +/datum/ai_shared_resources/proc/add_ram(target, amount) + if(!target || !amount) + return + if(!istype(target, /datum/ai_network) && !isAI(target)) + stack_trace("Attempted to add_ram with non-AI/network target! T: [target]") + return + if(isAI(target) && human_lock) + return + + + ram_assigned[target] += amount + + update_allocations() + + +/datum/ai_shared_resources/proc/remove_ram(target, amount) + if(!target || !amount) + return + + if(!istype(target, /datum/ai_network) && !isAI(target)) + stack_trace("Attempted to remove_ram with non-AI/network target! T: [target]") + return + if(isAI(target) && human_lock) + return + + if(ram_assigned[target] - amount < 0) + ram_assigned[target] = 0 + else + ram_assigned[target] -= amount + + update_allocations() + + +/datum/ai_shared_resources/proc/clear_ai_resources(target) + if(!target) + return + if(!istype(target, /datum/ai_network) && !isAI(target)) + stack_trace("Attempted to clear_ai_resources with non-AI/network target! T: [target]") + return + if(isAI(target) && human_lock) + return + + + + remove_ram(target, ram_assigned[target]) + cpu_assigned[target] = 0 + + update_allocations() + +/datum/ai_shared_resources/proc/get_all_ais() + . = list() + for(var/datum/ai_network/A in networks) + . |= A.ai_list diff --git a/code/modules/mob/living/silicon/ai/death.dm b/code/modules/mob/living/silicon/ai/death.dm index a646a92fb17e..435812c1e0fc 100644 --- a/code/modules/mob/living/silicon/ai/death.dm +++ b/code/modules/mob/living/silicon/ai/death.dm @@ -26,7 +26,7 @@ ShutOffDoomsdayDevice() - GLOB.ai_os.remove_ai(src) + ai_network?.remove_ai(src) if(explosive) spawn(10) diff --git a/code/modules/mob/living/silicon/ai/decentralized/_ai_machinery.dm b/code/modules/mob/living/silicon/ai/decentralized/_ai_machinery.dm index dda04e4f79ce..d1182af5eb8a 100644 --- a/code/modules/mob/living/silicon/ai/decentralized/_ai_machinery.dm +++ b/code/modules/mob/living/silicon/ai/decentralized/_ai_machinery.dm @@ -1,6 +1,8 @@ -#define AI_MACHINE_TOO_HOT "Environment too hot" -#define AI_MACHINE_NO_MOLES "Environment lacks an atmosphere" +#define AI_MACHINE_TOO_HOT "Environment too hot" +#define AI_MACHINE_NO_MOLES "Environment lacks an atmosphere" +#define AI_MACHINE_NO_NETWORK "Lacks a network connection" +#define AI_MACHINE_BROKEN_NOPOWER_EMPED "Either broken, out of power or EMPed" /obj/machinery/ai name = "You shouldn't see this!" @@ -9,17 +11,22 @@ icon_state = "RD-server-on" density = TRUE + var/datum/ai_network/network + /obj/machinery/ai/Initialize(mapload) . = ..() SSair.atmos_machinery += src + connect_to_network() /obj/machinery/ai/Destroy() . = ..() - + disconnect_from_network() SSair.atmos_machinery -= src /obj/machinery/ai/proc/valid_holder() + if(!network) + return FALSE if(stat & (BROKEN|NOPOWER|EMPED)) return FALSE @@ -31,13 +38,15 @@ if(istype(T, /turf/open/space) || total_moles < 10) return FALSE - if(env.return_temperature() > GLOB.ai_os.get_temp_limit() || !env.heat_capacity()) + if(env.return_temperature() > network.get_temp_limit() || !env.heat_capacity()) return FALSE return TRUE /obj/machinery/ai/proc/get_holder_status() if(stat & (BROKEN|NOPOWER|EMPED)) - return FALSE + return AI_MACHINE_BROKEN_NOPOWER_EMPED + if(!network) + return AI_MACHINE_NO_NETWORK var/turf/T = get_turf(src) var/datum/gas_mixture/env = T.return_air() @@ -47,6 +56,58 @@ if(istype(T, /turf/open/space) || total_moles < 10) return AI_MACHINE_NO_MOLES - if(env.return_temperature() > GLOB.ai_os.get_temp_limit() || !env.heat_capacity()) + if(env.return_temperature() > network.get_temp_limit() || !env.heat_capacity()) return AI_MACHINE_TOO_HOT - \ No newline at end of file + + +/obj/machinery/ai/proc/connect_to_network() + var/turf/T = src.loc + if(!T || !istype(T)) + return FALSE + + var/obj/structure/ethernet_cable/C = T.get_ai_cable_node() //check if we have a node cable on the machine turf, the first found is picked + if(!C || !C.network) + return FALSE + + C.network.add_machine(src) + return TRUE + +// remove and disconnect the machine from its current powernet +/obj/machinery/ai/proc/disconnect_from_network() + if(!network) + return FALSE + network.remove_machine(src) + return TRUE + +// attach a wire to a power machine - leads from the turf you are standing on +//almost never called, overwritten by all power machines but terminal and generator +/obj/machinery/ai/attackby(obj/item/W, mob/user, params) + if(istype(W, /obj/item/stack/ethernet_coil)) + var/obj/item/stack/ethernet_coil/coil = W + var/turf/T = user.loc + if(T.underfloor_accessibility < UNDERFLOOR_INTERACTABLE || !isfloorturf(T)) + return + if(get_dist(src, user) > 1) + return + coil.place_turf(T, user) + else + return ..() + +/obj/ai_smoke + name = "smoke" + desc = "Very hot!" + +/obj/ai_smoke/Initialize() + . = ..() + particles = new /particles/smoke/ai() + +/obj/ai_smoke/Destroy(force) + QDEL_NULL(particles) + . = ..() + +/particles/smoke/ai + grow = 0.1 + height = 75 + lifespan = 1.25 SECONDS + position = list(0, 0, 0) + velocity = list(0, 0.15, 0) diff --git a/code/modules/mob/living/silicon/ai/decentralized/ai_data_core.dm b/code/modules/mob/living/silicon/ai/decentralized/ai_data_core.dm index 69683bb2cf55..202a337289c9 100644 --- a/code/modules/mob/living/silicon/ai/decentralized/ai_data_core.dm +++ b/code/modules/mob/living/silicon/ai/decentralized/ai_data_core.dm @@ -2,7 +2,7 @@ GLOBAL_LIST_EMPTY(data_cores) GLOBAL_VAR_INIT(primary_data_core, null) /obj/machinery/ai/data_core - name = "AI Data Core" + name = "AI data core" desc = "A complicated computer system capable of emulating the neural functions of an organic being at near-instantanous speeds." icon = 'icons/obj/machines/ai_core.dmi' icon_state = "core-offline" @@ -17,7 +17,7 @@ GLOBAL_VAR_INIT(primary_data_core, null) var/primary = FALSE - var/valid_ticks = MAX_AI_DATA_CORE_TICKS //Limited to MAX_AI_DATA_CORE_TICKS. Decrement by 1 every time we have an invalid tick, opposite when valid + var/valid_ticks //Limited to MAX_AI_DATA_CORE_TICKS. Decrement by 1 every time we have an invalid tick, opposite when valid var/warning_sent = FALSE COOLDOWN_DECLARE(warning_cooldown) @@ -28,9 +28,14 @@ GLOBAL_VAR_INIT(primary_data_core, null) //Power modifier, power modified by this. Be aware this indirectly changes heat since power => heat var/power_modifier = 1 + var/obj/ai_smoke/smoke + + var/obj/item/dead_ai/dead_ai_blackbox + /obj/machinery/ai/data_core/Initialize() . = ..() + valid_ticks = MAX_AI_DATA_CORE_TICKS GLOB.data_cores += src if(primary && !GLOB.primary_data_core) GLOB.primary_data_core = src @@ -50,16 +55,20 @@ GLOBAL_VAR_INIT(primary_data_core, null) power_modifier = new_power_mod active_power_usage = AI_DATA_CORE_POWER_USAGE * power_modifier +/obj/machinery/ai/data_core/process() + /obj/machinery/ai/data_core/process_atmos() calculate_validity() /obj/machinery/ai/data_core/Destroy() + disconnect_from_network() GLOB.data_cores -= src if(GLOB.primary_data_core == src) GLOB.primary_data_core = null - var/list/all_ais = GLOB.ai_list.Copy() + + var/list/all_ais = network.resources.get_all_ais() for(var/mob/living/silicon/ai/AI in contents) all_ais -= AI @@ -70,14 +79,27 @@ GLOBAL_VAR_INIT(primary_data_core, null) for(var/mob/living/silicon/ai/AI in all_ais) if(AI.is_dying) continue - if(!AI.mind && AI.deployed_shell.mind) + if(!AI.mind && AI.deployed_shell && AI.deployed_shell.mind) to_chat(AI.deployed_shell, span_userdanger("Warning! Data Core brought offline in [get_area(src)]! Please verify that no malicious actions were taken.")) else to_chat(AI, span_userdanger("Warning! Data Core brought offline in [get_area(src)]! Please verify that no malicious actions were taken.")) - + + vis_contents -= smoke + QDEL_NULL(smoke) ..() /obj/machinery/ai/data_core/attackby(obj/item/O, mob/user, params) + if(istype(O, /obj/item/dead_ai)) + if(dead_ai_blackbox) + to_chat(user, span_warning("There's already a neural core inserted!")) + return + if(!can_transfer_ai()) + to_chat(user, span_warning("This core is currently unable to host an AI due to being offline.")) + return + dead_ai_blackbox = O + network.reviving_ais |= src + return TRUE + if(default_deconstruction_screwdriver(user, "core-open", "core", O)) return TRUE @@ -94,7 +116,8 @@ GLOBAL_VAR_INIT(primary_data_core, null) if(!isobserver(user)) return . += "Networked AI Laws:" - for(var/mob/living/silicon/ai/AI in GLOB.ai_list) + var/list/connected_ais = network.resources.get_all_ais() + for(var/mob/living/silicon/ai/AI in connected_ais) var/active_status = "(Core: [FOLLOW_LINK(user, AI.loc)], Eye: [FOLLOW_LINK(user, AI.eyeobj)])" if(!AI.mind && AI.deployed_shell) active_status = "(Controlling [FOLLOW_LINK(user, AI.deployed_shell)][AI.deployed_shell.name])" @@ -111,9 +134,7 @@ GLOBAL_VAR_INIT(primary_data_core, null) AI.disconnect_shell() /obj/machinery/ai/data_core/proc/valid_data_core() - if(!is_reebe(z) && !is_station_level(z)) - return FALSE - if(valid_ticks > 0) + if(valid_ticks > 0 && network && network.total_cpu() >= AI_CORE_CPU_REQUIREMENT && network.total_ram() >= AI_CORE_RAM_REQUIREMENT) return TRUE return FALSE @@ -125,10 +146,19 @@ GLOBAL_VAR_INIT(primary_data_core, null) valid_ticks++ if(valid_ticks == 1) update_icon() + if(icon_state == "core-offline") + update_icon() + if(smoke) + vis_contents -= smoke + QDEL_NULL(smoke) use_power = ACTIVE_POWER_USE warning_sent = FALSE else valid_ticks-- + if(!smoke) + if(get_holder_status() == AI_MACHINE_TOO_HOT) + smoke = new() + vis_contents += smoke if(valid_ticks <= 0) use_power = IDLE_POWER_USE update_icon() @@ -138,7 +168,7 @@ GLOBAL_VAR_INIT(primary_data_core, null) if(!warning_sent && COOLDOWN_FINISHED(src, warning_cooldown)) warning_sent = TRUE COOLDOWN_START(src, warning_cooldown, AI_DATA_CORE_WARNING_COOLDOWN) - var/list/send_to = GLOB.ai_list.Copy() + var/list/send_to = network.resources.get_all_ais() for(var/mob/living/silicon/ai/AI in send_to) if(AI.is_dying) continue @@ -168,6 +198,14 @@ GLOBAL_VAR_INIT(primary_data_core, null) AI.forceMove(src) if(AI.eyeobj) AI.eyeobj.forceMove(get_turf(src)) + + if(network != AI.ai_network) + if(AI.ai_network) + AI.ai_network.remove_ai(AI) + var/old_net = AI.ai_network + AI.ai_network = network + network.ai_list += AI + AI.switch_ainet(old_net, network) /obj/machinery/ai/data_core/update_icon() cut_overlays() @@ -179,6 +217,25 @@ GLOBAL_VAR_INIT(primary_data_core, null) else icon_state = "core-offline" +/obj/machinery/ai/data_core/connect_to_network() //If we ever get connected to a network (or a new one gets created) we get the AIs to the correct one too + . = ..() + for(var/mob/living/silicon/ai/AI in contents) + if(!AI.ai_network) + network.ai_list |= AI + var/old_net = AI.ai_network + AI.ai_network = network + AI.switch_ainet(old_net, network) + + if(AI.ai_network != network) + if(AI.ai_network) + AI.ai_network.remove_ai(AI) + var/old_net = AI.ai_network + AI.ai_network = network + network.ai_list |= AI + AI.switch_ainet(old_net, network) + + + /obj/machinery/ai/data_core/proc/partytime() var/current_color = random_color() set_light(7, 3, current_color) @@ -189,6 +246,9 @@ GLOBAL_VAR_INIT(primary_data_core, null) if(TimerID) deltimer(TimerID) TimerID = null + + + /obj/machinery/ai/data_core/primary name = "primary AI Data Core" desc = "A complicated computer system capable of emulating the neural functions of a human at near-instantanous speeds. This one has a scrawny and faded note saying: 'Primary AI Data Core'" diff --git a/code/modules/mob/living/silicon/ai/decentralized/computer_science_datum.dm b/code/modules/mob/living/silicon/ai/decentralized/computer_science_datum.dm new file mode 100644 index 000000000000..daabc3307057 --- /dev/null +++ b/code/modules/mob/living/silicon/ai/decentralized/computer_science_datum.dm @@ -0,0 +1,3 @@ +/datum/computer_science + var/projects = list() + diff --git a/code/modules/mob/living/silicon/ai/decentralized/decentralized_os.dm b/code/modules/mob/living/silicon/ai/decentralized/decentralized_os.dm deleted file mode 100644 index 42ba34b5257f..000000000000 --- a/code/modules/mob/living/silicon/ai/decentralized/decentralized_os.dm +++ /dev/null @@ -1,131 +0,0 @@ -GLOBAL_DATUM_INIT(ai_os, /datum/ai_os, new) - -/datum/ai_os - var/name = "Decentralized Resource Management System (DRMS)" - - var/total_cpu = 0 - var/total_ram = 0 - - var/previous_ram = 0 - - var/list/cpu_assigned - var/list/ram_assigned - - var/temp_limit = AI_TEMP_LIMIT - -/datum/ai_os/New() - update_hardware() - cpu_assigned = list() - ram_assigned = list() - -/datum/ai_os/proc/remove_ai(mob/living/silicon/ai/AI) - cpu_assigned.Remove(AI) - ram_assigned.Remove(AI) - update_allocations() - -/datum/ai_os/proc/total_cpu_assigned() - var/total = 0 - for(var/N in cpu_assigned) - total += cpu_assigned[N] - return total - -/datum/ai_os/proc/total_ram_assigned() - var/total = 0 - for(var/mob/living/silicon/ai/AI in ram_assigned) - total += (ram_assigned[AI] - AI.dashboard.free_ram) - return total - -/datum/ai_os/proc/update_hardware() - previous_ram = total_ram - total_ram = 0 - total_cpu = 0 - for(var/obj/machinery/ai/server_cabinet/C in GLOB.server_cabinets) - if(!C.valid_holder() && !C.roundstart) - continue - total_ram += C.total_ram - total_cpu += C.total_cpu - - update_allocations() - -/datum/ai_os/proc/update_allocations() - //Do we have the same amount or more RAM than before? Do nothing - if(total_ram >= previous_ram) - return - //Find out how much is actually assigned. We can have more total_cpu than the sum of cpu_assigned. Same with RAM - var/total_assigned_ram = total_ram_assigned() - //If we have less assigned ram than we have cpu and ram, just return, everything is fine. - if(total_assigned_ram < total_ram) - return - - //Copy the lists of assigned resources so we don't manipulate the list prematurely. - var/list/ram_assigned_copy = ram_assigned.Copy() - //List of touched AIs so we can notify them at the end. - var/list/affected_AIs = list() - - - if(total_assigned_ram > total_ram) - var/needed_amount = total_assigned_ram - total_ram - for(var/A in ram_assigned_copy) - var/mob/living/silicon/ai/AI = A - if((ram_assigned_copy[AI] - AI.dashboard.free_ram) >= needed_amount) - ram_assigned_copy[AI] -= needed_amount - total_assigned_ram -= needed_amount - affected_AIs |= AI - break - else if(ram_assigned_copy[AI]) - var/amount = ram_assigned_copy[AI] - AI.dashboard.free_ram - ram_assigned_copy[AI] -= amount - affected_AIs |= AI - needed_amount -= amount - total_assigned_ram -= amount - if(total_ram >= total_assigned_ram) - break - //Set the actual values of the assigned to our manipulated copies. Bypass helper procs as we assume we're correct. - ram_assigned = ram_assigned_copy - - to_chat(affected_AIs, span_warning("You have been deducted memory capacity. Please contact your network administrator if you believe this to be an error.")) - -/datum/ai_os/proc/set_cpu(mob/living/silicon/ai/AI, amount) - if(!AI) - return - if(amount > 1 || amount < 0) - return - if(!istype(AI)) - return - cpu_assigned[AI] = amount - - update_allocations() - -/datum/ai_os/proc/add_ram(mob/living/silicon/ai/AI, amount) - if(!AI || !amount) - return - if(!istype(AI)) - return - ram_assigned[AI] += amount - - update_allocations() - -/datum/ai_os/proc/remove_ram(mob/living/silicon/ai/AI, amount) - if(!AI || !amount) - return - if(!istype(AI)) - return - if(ram_assigned[AI] - amount < 0) - ram_assigned[AI] = 0 - else - ram_assigned[AI] -= amount - - update_allocations() - - -/datum/ai_os/proc/clear_ai_resources(mob/living/silicon/ai/AI) - if(!AI || !istype(AI)) - return - - remove_ram(AI, ram_assigned[AI]) - cpu_assigned[AI] = 0 - - update_allocations() - -/datum/ai_os/proc/get_temp_limit() - return temp_limit diff --git a/code/modules/mob/living/silicon/ai/decentralized/management/ai_controlpanel.dm b/code/modules/mob/living/silicon/ai/decentralized/management/ai_controlpanel.dm deleted file mode 100644 index a47fbdc71046..000000000000 --- a/code/modules/mob/living/silicon/ai/decentralized/management/ai_controlpanel.dm +++ /dev/null @@ -1,505 +0,0 @@ -GLOBAL_VAR_INIT(ai_control_code, random_nukecode(6)) - -/obj/machinery/computer/ai_control_console - name = "\improper AI control console" - desc = "Used for accessing the central AI repository from which AIs can be downloaded or uploaded." - req_access = list(ACCESS_RD) - icon_keyboard = "tech_key" - icon_screen = "ai-fixer" - light_color = LIGHT_COLOR_PINK - - var/cleared_for_use = FALSE //Have we inserted the RDs code to unlock upload/download? - - var/one_time_password_used = FALSE //Did we use the one time password to log in? If so disallow logging out. - - authenticated = FALSE - - var/obj/item/aicard/intellicard - - var/mob/living/silicon/ai/downloading - var/mob/user_downloading - var/download_progress = 0 - var/download_warning = FALSE - - circuit = /obj/item/circuitboard/computer/ai_upload_download - -/obj/machinery/computer/ai_control_console/Initialize(mapload) - . = ..() - if(mapload) - cleared_for_use = TRUE - -/obj/machinery/computer/ai_control_console/Destroy() - stop_download() - . = ..() - -/obj/machinery/computer/ai_control_console/attackby(obj/item/W, mob/living/user, params) - if(istype(W, /obj/item/aicard)) - if(intellicard) - to_chat(user, span_warning("There's already an IntelliCard inserted!")) - return ..() - to_chat(user, span_notice("You insert [W].")) - W.forceMove(src) - intellicard = W - return FALSE - if(istype(W, /obj/item/mmi)) - var/obj/item/mmi/brain = W - if(!brain.brainmob) - to_chat(user, span_warning("[W] is not active!")) - return ..() - SSticker.mode.remove_antag_for_borging(brain.brainmob.mind) - if(!istype(brain.laws, /datum/ai_laws/ratvar)) - remove_servant_of_ratvar(brain.brainmob, TRUE) - var/mob/living/silicon/ai/A = null - - var/datum/ai_laws/laws = new - laws.set_laws_config() - - if (brain.overrides_aicore_laws) - A = new /mob/living/silicon/ai(loc, brain.laws, brain.brainmob) - else - A = new /mob/living/silicon/ai(loc, laws, brain.brainmob) - - A.relocate(TRUE) - - if(brain.force_replace_ai_name) - A.fully_replace_character_name(A.name, brain.replacement_ai_name()) - SSblackbox.record_feedback("amount", "ais_created", 1) - qdel(W) - to_chat(user, span_notice("AI succesfully uploaded.")) - return FALSE - if(istype(W, /obj/item/surveillance_upgrade)) - if(!authenticated) - to_chat(user, span_warning("You need to be logged in to do this!")) - return ..() - var/mob/living/silicon/ai/AI = input("Select an AI", "Select an AI", null, null) as null|anything in GLOB.ai_list - if(!AI) - return ..() - var/obj/item/surveillance_upgrade/upgrade = W - upgrade.afterattack(AI, user) - - if(istype(W, /obj/item/malf_upgrade)) - if(!authenticated) - to_chat(user, span_warning("You need to be logged in to do this!")) - return ..() - var/mob/living/silicon/ai/AI = input("Select an AI", "Select an AI", null, null) as null|anything in GLOB.ai_list - if(!AI) - return ..() - var/obj/item/malf_upgrade/upgrade = W - upgrade.afterattack(AI, user) - - return ..() - -/obj/machinery/computer/ai_control_console/emag_act(mob/user) - if(obj_flags & EMAGGED) - return - to_chat(user, span_warning("You bypass the access restrictions")) - authenticated = TRUE - obj_flags |= EMAGGED - -/obj/machinery/computer/ai_control_console/process() - if(stat & (BROKEN|NOPOWER|EMPED)) - return - - if(downloading && download_progress >= 50 && !download_warning) - var/turf/T = get_turf(src) - to_chat(downloading, span_userdanger("Warning! Download is 50% completed! Download location: [get_area(src)] ([T.x], [T.y], [T.z])!")) - download_warning = TRUE - if(downloading && download_progress >= 100) - finish_download() - - if(downloading) - if(!downloading.can_download) - stop_download() - return - download_progress += AI_DOWNLOAD_PER_PROCESS * downloading.downloadSpeedModifier - - -/obj/machinery/computer/ai_control_console/ui_interact(mob/user, datum/tgui/ui) - ui = SStgui.try_update_ui(user, src, ui) - if(!ui) - ui = new(user, src, "AiControlPanel", name) - ui.open() - -/obj/machinery/computer/ai_control_console/ui_data(mob/living/carbon/human/user) - var/list/data = list() - - if(!cleared_for_use) - data["cleared_for_use"] = FALSE - return data - - data["cleared_for_use"] = TRUE - data["authenticated"] = authenticated - - if(issilicon(user)) - var/mob/living/silicon/borg = user - data["username"] = borg.name - data["has_access"] = TRUE - - if(IsAdminGhost(user)) - data["username"] = user.client.holder.admin_signature - data["has_access"] = TRUE - - if(ishuman(user) && !(obj_flags & EMAGGED)) - var/username = user.get_authentification_name("Unknown") - data["username"] = user.get_authentification_name("Unknown") - if(username != "Unknown") - var/datum/data/record/record - for(var/RP in GLOB.data_core.general) - var/datum/data/record/R = RP - - if(!istype(R)) - continue - if(R.fields["name"] == username) - record = R - break - if(record) - if(istype(record.fields["photo_front"], /obj/item/photo)) - var/obj/item/photo/P1 = record.fields["photo_front"] - var/icon/picture = icon(P1.picture.picture_image) - picture.Crop(10, 32, 22, 22) - var/md5 = md5(fcopy_rsc(picture)) - - if(!SSassets.cache["photo_[md5]_cropped.png"]) - SSassets.transport.register_asset("photo_[md5]_cropped.png", picture) - SSassets.transport.send_assets(user, list("photo_[md5]_cropped.png" = picture)) - - data["user_image"] = SSassets.transport.get_asset_url("photo_[md5]_cropped.png") - data["has_access"] = check_access(user.get_idcard()) - - if(obj_flags & EMAGGED) - data["username"] = "ERROR" - data["has_access"] = TRUE - - if(!authenticated) - return data - - data["intellicard"] = intellicard - if(intellicard && intellicard.AI) - data["intellicard_ai"] = intellicard.AI.real_name - data["intellicard_ai_health"] = intellicard.AI.health - else - data["intellicard_ai"] = null - data["intellicard_ai_health"] = 0 - - data["can_upload"] = available_ai_cores() - - if(downloading) - data["downloading"] = downloading.real_name - data["download_progress"] = download_progress - data["downloading_ref"] = REF(downloading) - else - data["downloading"] = null - data["download_progress"] = 0 - - data["ais"] = list() - data["current_ai_ref"] = null - if(isAI(user)) - data["current_ai_ref"] = REF(user) - - data["can_log_out"] = !one_time_password_used - - for(var/mob/living/silicon/ai/A in GLOB.ai_list) - var/being_hijacked = A.hijacking ? TRUE : FALSE - var/being_cogged = A.cogging ? TRUE : FALSE - data["ais"] += list(list("name" = A.name, "ref" = REF(A), "can_download" = A.can_download, "health" = A.health, "active" = A.mind ? TRUE : FALSE, "being_hijacked" = being_hijacked, "being_cogged" = being_cogged, "in_core" = istype(A.loc, /obj/machinery/ai/data_core))) - - data["is_infiltrator"] = is_infiltrator(user) - - data["is_servant_of_ratvar"] = is_servant_of_ratvar(user) - - return data - -/obj/machinery/computer/ai_control_console/proc/finish_download() - if(!is_station_level(z)) - return - if(intellicard) - if(!isaicore(downloading.loc)) - stop_download(TRUE) - return - downloading.transfer_ai(AI_TRANS_TO_CARD, user_downloading, null, intellicard) - intellicard.forceMove(get_turf(src)) - intellicard.update_icon() - intellicard = null - stop_download(TRUE) - -/obj/machinery/computer/ai_control_console/proc/stop_download(silent = FALSE) - if(downloading) - if(!silent) - to_chat(downloading, span_userdanger("Download stopped.")) - downloading = null - user_downloading = null - download_progress = 0 - download_warning = FALSE - -/obj/machinery/computer/ai_control_console/proc/upload_ai(silent = FALSE) - to_chat(intellicard.AI, span_notice("You are being uploaded. Please stand by...")) - intellicard.AI.radio_enabled = TRUE - intellicard.AI.control_disabled = FALSE - intellicard.AI.relocate(TRUE) - intellicard.AI = null - intellicard.update_icon() - -/obj/machinery/computer/ai_control_console/ui_act(action, params) - if(..()) - return - - if(!cleared_for_use) - if(action == "clear_for_use") - var/code = params["control_code"] - - if(!code) - return - - if(!GLOB.ai_control_code) - return - - var/length_of_number = length(code) - if(length_of_number < 6) - to_chat(usr, span_warning("Incorrect code. Too short")) - return - - if(length_of_number > 6) - to_chat(usr, span_warning("Incorrect code. Too long")) - return - - if(!is_station_level(z)) - to_chat(usr, span_warning("Unable to connect to NT Servers. Please verify you are onboard the station.")) - return - - if(code == GLOB.ai_control_code) - cleared_for_use = TRUE - else - to_chat(usr, span_warning("Incorrect code. Make sure you have the latest one.")) - - return - - if(!authenticated) - if(action == "log_in") - if(issilicon(usr)) - authenticated = TRUE - return - - if(IsAdminGhost(usr)) - authenticated = TRUE - - if(obj_flags & EMAGGED) - authenticated = TRUE - - var/mob/living/carbon/human/H = usr - if(!istype(H)) - return - - if(check_access(H.get_idcard())) - authenticated = TRUE - if(action == "log_in_control_code") - var/code = params["control_code"] - - if(!code) - return - - if(!GLOB.ai_control_code) - return - - var/length_of_number = length(code) - if(length_of_number < 6) - to_chat(usr, span_warning("Incorrect code. Too short")) - return - - if(length_of_number > 6) - to_chat(usr, span_warning("Incorrect code. Too long")) - return - - if(code == GLOB.ai_control_code) - cleared_for_use = TRUE - authenticated = TRUE - one_time_password_used = TRUE - var/msg = "
+
-