diff --git a/SQL/tgstation_schema.sql b/SQL/tgstation_schema.sql index 9696082994db..9991a037ee06 100644 --- a/SQL/tgstation_schema.sql +++ b/SQL/tgstation_schema.sql @@ -802,6 +802,23 @@ CREATE TABLE `subsystem_metrics` ( PRIMARY KEY (`id`) USING BTREE ) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; +-- +-- Table structure for table `cassettes` +-- +DROP TABLE IF EXISTS `cassettes`; +CREATE TABLE `cassettes` ( + `id` VARCHAR(255) NOT NULL PRIMARY KEY, + `name` VARCHAR(42) NOT NULL, + `desc` VARCHAR(144) NOT NULL, + `status` TINYINT UNSIGNED NOT NULL, + `author_name` VARCHAR(42) NOT NULL, + `author_ckey` VARCHAR(30) NOT NULL, + `front` TEXT NOT NULL DEFAULT '{}', + `back` TEXT NOT NULL DEFAULT '{}', + CONSTRAINT `front` CHECK (json_valid(`front`)), + CONSTRAINT `back` CHECK (json_valid(`back`)) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci; + /*!40101 SET SQL_MODE=@OLD_SQL_MODE */; /*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */; /*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */; diff --git a/_maps/map_files/BoxStation/BoxStation.dmm b/_maps/map_files/BoxStation/BoxStation.dmm index c49ff8f8fab3..8d659b8767c2 100644 --- a/_maps/map_files/BoxStation/BoxStation.dmm +++ b/_maps/map_files/BoxStation/BoxStation.dmm @@ -342,6 +342,10 @@ /obj/effect/landmark/start/librarian, /turf/open/floor/iron/vaporwave, /area/station/service/library/printer) +"afe" = ( +/obj/machinery/light/directional/west, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "afh" = ( /obj/structure/disposalpipe/segment{ dir = 4 @@ -925,6 +929,9 @@ /obj/effect/spawner/random/structure/steam_vent, /turf/open/floor/catwalk_floor, /area/station/maintenance/starboard/aft) +"apq" = ( +/turf/open/space/basic, +/area/shipbreak) "apr" = ( /obj/machinery/power/apc/auto_name/directional/south, /obj/structure/cable, @@ -1725,6 +1732,10 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron/dark/textured, /area/station/security/prison) +"aCb" = ( +/obj/structure/cable, +/turf/open/floor/iron/airless, +/area/station/engineering/shipbreaker_hut) "aCx" = ( /obj/structure/disposalpipe/segment{ dir = 4 @@ -2296,15 +2307,6 @@ /obj/machinery/power/rad_collector, /turf/open/floor/plating, /area/station/engineering/main) -"aNC" = ( -/obj/machinery/status_display/evac/directional/west, -/obj/machinery/newscaster/directional/north, -/obj/structure/table, -/obj/item/paper_bin, -/turf/open/floor/iron/dark/side/airless{ - dir = 9 - }, -/area/station/engineering/shipbreaker_hut) "aNK" = ( /obj/structure/closet/firecloset/full, /turf/open/floor/plating, @@ -2965,10 +2967,6 @@ /obj/effect/spawner/random/bureaucracy/stamp, /turf/open/floor/plating, /area/station/maintenance/port/fore) -"aYq" = ( -/obj/structure/cable, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "aYu" = ( /obj/effect/decal/cleanable/dirt, /obj/structure/cable, @@ -3257,6 +3255,10 @@ /obj/machinery/duct, /turf/open/floor/plating, /area/station/maintenance/port/fore) +"bdI" = ( +/obj/structure/cable, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "bdX" = ( /obj/machinery/atmospherics/pipe/smart/simple/purple/visible{ dir = 6 @@ -3549,6 +3551,18 @@ }, /turf/open/floor/iron/dark, /area/station/maintenance/disposal/incinerator) +"bhU" = ( +/obj/machinery/light/small/directional/east, +/obj/machinery/camera/directional/east{ + c_tag = "Engineering - Shipbreaking, Control Room"; + name = "engineering camera" + }, +/obj/machinery/light_switch/directional/south, +/obj/item/radio/intercom/directional/east, +/turf/open/floor/iron/dark/side/airless{ + dir = 6 + }, +/area/station/engineering/shipbreaker_hut) "bia" = ( /obj/structure/disposalpipe/segment, /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, @@ -3885,6 +3899,13 @@ /obj/machinery/light/small/directional/south, /turf/open/floor/iron/dark, /area/station/hallway/secondary/entry) +"bnI" = ( +/obj/machinery/door/airlock/external{ + name = "Shipbreaking Storage Room" + }, +/obj/effect/mapping_helpers/airlock/access/any/engineering/general, +/turf/open/floor/iron/dark/textured/airless, +/area/station/engineering/shipbreaker_hut) "bnL" = ( /obj/effect/turf_decal/tile/neutral/fourcorners, /obj/structure/extinguisher_cabinet/directional/east, @@ -4169,6 +4190,11 @@ /obj/effect/landmark/event_spawn, /turf/open/floor/glass/reinforced, /area/station/commons/fitness/recreation) +"brl" = ( +/turf/open/floor/iron/dark/side/airless{ + dir = 4 + }, +/area/station/engineering/shipbreaker_hut) "brx" = ( /obj/effect/turf_decal/tile/red/fourcorners, /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, @@ -7744,6 +7770,29 @@ }, /turf/open/floor/plating, /area/station/maintenance/port/fore) +"cwY" = ( +/obj/structure/table/reinforced, +/obj/item/paper_bin{ + pixel_y = 5 + }, +/obj/item/folder/white{ + pixel_y = 7 + }, +/obj/item/pen{ + pixel_y = 7 + }, +/obj/item/stamp/head/rd{ + pixel_y = 10 + }, +/obj/item/toy/figure/rd{ + pixel_x = -13 + }, +/obj/item/stamp/denied{ + pixel_y = 5 + }, +/obj/item/stamp/granted, +/turf/open/floor/carpet/purple, +/area/station/command/heads_quarters/rd) "cxf" = ( /obj/effect/turf_decal/sand/plating, /obj/machinery/light/small/directional/north, @@ -8396,6 +8445,23 @@ /obj/effect/landmark/navigate_destination/library, /turf/open/floor/iron/dark/textured, /area/station/service/library) +"cJt" = ( +/obj/machinery/keycard_auth/directional/east, +/obj/structure/table/wood, +/obj/item/paper_bin, +/obj/item/folder/blue, +/obj/item/pen/fountain, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/head/captain, +/turf/open/floor/wood, +/area/station/command/heads_quarters/captain) "cJu" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -9949,17 +10015,6 @@ /obj/structure/closet/secure_closet/bar, /turf/open/floor/wood, /area/station/service/bar/backroom) -"dia" = ( -/obj/machinery/coffeemaker/impressa{ - pixel_y = 5 - }, -/obj/item/storage/box/coffeepack{ - pixel_x = 9; - pixel_y = -1 - }, -/obj/structure/table/wood, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "did" = ( /obj/machinery/light/directional/west, /obj/structure/sign/poster/official/there_is_no_gas_giant/directional/west, @@ -10031,6 +10086,53 @@ /obj/structure/closet/crate/rcd, /turf/open/floor/iron/dark, /area/station/ai_monitored/command/storage/eva) +"dju" = ( +/obj/structure/sign/painting/library_private{ + pixel_y = -32 + }, +/obj/structure/table/wood, +/obj/item/cassette_tape/friday{ + pixel_y = 2; + pixel_x = 9 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/obj/item/device/walkman{ + pixel_y = 7; + pixel_x = -8 + }, +/turf/open/floor/iron/vaporwave, +/area/station/service/library/printer) "djD" = ( /obj/machinery/field/generator, /turf/open/floor/plating, @@ -10467,6 +10569,9 @@ }, /turf/open/floor/carpet, /area/station/service/chapel) +"drP" = ( +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "drQ" = ( /obj/effect/turf_decal/stripes/line{ dir = 1 @@ -13434,6 +13539,14 @@ }, /turf/open/floor/eighties/red, /area/station/service/theater) +"erI" = ( +/obj/machinery/computer/shipbreaker{ + dir = 4 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 8 + }, +/area/station/engineering/shipbreaker_hut) "erK" = ( /obj/effect/turf_decal/stripes/end, /obj/structure/window/reinforced/spawner/directional/south, @@ -13458,6 +13571,50 @@ }, /turf/open/floor/iron/dark, /area/station/hallway/primary/port) +"esj" = ( +/obj/machinery/digital_clock/directional/south, +/obj/machinery/button/door/directional/west{ + id = "nt_rep_office_door"; + name = "Office Door Bolt Control"; + req_access = list("nt_rep"); + pixel_y = -6; + normaldoorcontrol = 1; + specialfunctions = 4 + }, +/obj/machinery/button/door/directional/west{ + id = "nt_rep_desk_shutters"; + name = "Desk Shutters Control"; + req_access = list("nt_rep"); + pixel_y = 6 + }, +/obj/structure/table/wood, +/obj/item/stamp/granted{ + pixel_y = 6; + pixel_x = 8 + }, +/obj/item/stamp/denied{ + pixel_x = 8 + }, +/obj/item/folder/blue{ + pixel_x = -6 + }, +/obj/item/folder/blue{ + pixel_y = 3; + pixel_x = -6 + }, +/obj/item/folder/blue{ + pixel_y = 6; + pixel_x = -6 + }, +/obj/item/pen/fountain{ + pixel_x = -6 + }, +/obj/item/pen/fourcolor{ + pixel_y = 6; + pixel_x = -3 + }, +/turf/open/floor/wood/parquet, +/area/station/command/heads_quarters/nt_rep) "esr" = ( /obj/effect/turf_decal/trimline/blue/filled/warning, /obj/effect/turf_decal/trimline/blue/warning{ @@ -13757,6 +13914,15 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/plating, /area/station/maintenance/port/aft) +"ewi" = ( +/obj/structure/frame/computer{ + anchored = 1; + dir = 4 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 8 + }, +/area/station/engineering/shipbreaker_hut) "ewB" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -13956,6 +14122,12 @@ }, /turf/open/floor/iron, /area/station/maintenance/disposal) +"ezq" = ( +/obj/machinery/conveyor{ + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "ezP" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4{ dir = 8 @@ -14228,6 +14400,9 @@ /obj/machinery/duct, /turf/open/floor/iron/showroomfloor, /area/station/science/research) +"eES" = ( +/turf/closed/wall, +/area/station/engineering/shipbreaker_hut) "eFe" = ( /obj/effect/turf_decal/trimline/green/filled/line{ dir = 8 @@ -14340,13 +14515,6 @@ /obj/machinery/atmospherics/components/binary/tank_compressor, /turf/open/floor/iron, /area/station/science/ordnance) -"eGu" = ( -/obj/machinery/light/small/directional/east, -/obj/structure/filingcabinet, -/turf/open/floor/iron/dark/side/airless{ - dir = 5 - }, -/area/station/engineering/shipbreaker_hut) "eGw" = ( /turf/open/floor/plating, /area/station/maintenance/central) @@ -14479,6 +14647,11 @@ /obj/structure/filingcabinet, /turf/open/floor/iron/dark, /area/station/security/prison/visit) +"eIP" = ( +/turf/open/floor/iron/dark/side/airless{ + dir = 8 + }, +/area/station/engineering/shipbreaker_hut) "eIW" = ( /obj/structure/sign/poster/official/random/directional/north, /obj/machinery/status_display/evac/directional/east, @@ -14597,9 +14770,6 @@ /obj/machinery/telecomms/server/presets/command, /turf/open/floor/circuit/green/telecomms, /area/station/tcommsat/server) -"eKX" = ( -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "eKY" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 1 @@ -15234,18 +15404,6 @@ "eUW" = ( /turf/open/floor/wood, /area/station/service/chapel/funeral) -"eVx" = ( -/obj/structure/closet/mini_fridge, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/storage/cans/sixbeer, -/obj/machinery/light/directional/west, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "eVz" = ( /obj/effect/turf_decal/stripes/line, /obj/effect/turf_decal/stripes/line{ @@ -15450,20 +15608,6 @@ /obj/machinery/iv_drip, /turf/open/floor/iron/white, /area/station/medical/surgery) -"fak" = ( -/obj/machinery/status_display/ai/directional/west, -/obj/structure/extinguisher_cabinet/directional/south, -/obj/structure/table, -/obj/item/weldingtool/electric/raynewelder{ - pixel_y = -5 - }, -/obj/item/weldingtool/electric/raynewelder{ - pixel_y = 6 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 10 - }, -/area/station/engineering/shipbreaker_hut) "faw" = ( /obj/effect/turf_decal/tile/neutral/fourcorners, /obj/machinery/light/small/directional/west, @@ -15522,15 +15666,6 @@ /obj/machinery/computer/exoscanner_control, /turf/open/floor/iron, /area/station/cargo/drone_bay) -"fbA" = ( -/obj/structure/frame/computer{ - anchored = 1; - dir = 4 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 8 - }, -/area/station/engineering/shipbreaker_hut) "fbE" = ( /obj/structure/disposalpipe/segment{ dir = 9 @@ -15888,17 +16023,6 @@ /obj/effect/spawner/random/trash/garbage, /turf/open/floor/plating, /area/station/maintenance/port/fore) -"fho" = ( -/obj/structure/table, -/obj/item/pen, -/obj/item/pen/red{ - pixel_x = 6; - pixel_y = 6 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 8 - }, -/area/station/engineering/shipbreaker_hut) "fhs" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 4 @@ -16933,21 +17057,6 @@ }, /turf/open/floor/iron/white, /area/station/science/research) -"fzZ" = ( -/obj/structure/rack, -/obj/item/tank/internals/oxygen/yellow{ - pixel_x = 4; - pixel_y = -3 - }, -/obj/item/tank/internals/oxygen/yellow, -/obj/item/tank/internals/oxygen/yellow{ - pixel_x = -4; - pixel_y = 3 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 10 - }, -/area/station/engineering/shipbreaker_hut) "fAa" = ( /obj/machinery/firealarm/directional/north{ pixel_x = -5 @@ -18217,13 +18326,6 @@ }, /turf/open/floor/iron, /area/station/cargo/office) -"fVP" = ( -/obj/structure/chair{ - dir = 8 - }, -/obj/structure/cable, -/turf/open/floor/iron/airless, -/area/station/engineering/shipbreaker_hut) "fVR" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -19781,9 +19883,6 @@ }, /turf/open/floor/plating, /area/station/maintenance/starboard/aft) -"gwf" = ( -/turf/closed/wall, -/area/station/engineering/shipbreaker_hut) "gwq" = ( /obj/effect/turf_decal/siding/wood/corner{ dir = 1 @@ -20028,6 +20127,12 @@ }, /turf/open/floor/iron/white/textured, /area/station/science/genetics) +"gzh" = ( +/obj/structure/chair/comfy/teal{ + dir = 4 + }, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "gzw" = ( /obj/structure/disposalpipe/segment, /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, @@ -21389,53 +21494,6 @@ /obj/machinery/quantum_server, /turf/open/floor/iron/dark, /area/station/security/bitden) -"gSC" = ( -/obj/structure/sign/painting/library_private{ - pixel_y = -32 - }, -/obj/structure/table/wood, -/obj/item/device/cassette_tape/friday{ - pixel_y = 2; - pixel_x = 9 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/obj/item/device/walkman{ - pixel_y = 7; - pixel_x = -8 - }, -/turf/open/floor/iron/vaporwave, -/area/station/service/library/printer) "gSE" = ( /turf/open/floor/carpet/purple, /area/station/command/heads_quarters/rd) @@ -22215,6 +22273,21 @@ /obj/effect/decal/cleanable/dirt, /turf/open/floor/iron/dark, /area/station/commons/vacant_room/commissary) +"hgp" = ( +/obj/structure/rack, +/obj/item/radio/off{ + pixel_x = -6; + pixel_y = 4 + }, +/obj/item/radio/off{ + pixel_x = 6; + pixel_y = 4 + }, +/obj/item/radio/off, +/turf/open/floor/iron/dark/side/airless{ + dir = 9 + }, +/area/station/engineering/shipbreaker_hut) "hgQ" = ( /obj/machinery/duct, /obj/effect/decal/cleanable/dirt, @@ -23160,6 +23233,17 @@ /obj/machinery/camera/autoname/directional/north, /turf/open/floor/iron/dark, /area/station/security/prison/workout) +"hvx" = ( +/obj/machinery/camera/directional/north{ + c_tag = "Engineering - Shipbreaking, Storage Room"; + name = "engineering camera" + }, +/obj/structure/closet/emcloset/wall/directional/north, +/obj/structure/reagent_dispensers/fueltank, +/turf/open/floor/iron/dark/side/airless{ + dir = 1 + }, +/area/station/engineering/shipbreaker_hut) "hvz" = ( /obj/machinery/light/small/directional/south, /obj/structure/sign/warning/vacuum/external/directional/south, @@ -23314,16 +23398,6 @@ "hxY" = ( /turf/closed/wall, /area/station/maintenance/central) -"hxZ" = ( -/obj/machinery/light/directional/west{ - dir = 4 - }, -/obj/machinery/conveyor/inverted{ - dir = 10; - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "hya" = ( /obj/machinery/atmospherics/pipe/smart/simple/cyan/visible/layer2{ dir = 6 @@ -24146,14 +24220,6 @@ dir = 10 }, /area/station/security/prison) -"hLk" = ( -/obj/structure/cable, -/obj/machinery/door/airlock/external{ - name = "Shipbreaking Control Room" - }, -/obj/effect/mapping_helpers/airlock/access/any/engineering/general, -/turf/open/floor/iron/dark/textured/airless, -/area/station/engineering/shipbreaker_hut) "hLs" = ( /obj/machinery/computer/security/telescreen/entertainment/directional/north, /obj/effect/landmark/start/gary/rare, @@ -24735,14 +24801,6 @@ /obj/structure/cable, /turf/open/floor/iron/dark, /area/station/security/brig) -"hVt" = ( -/obj/machinery/conveyor{ - id = "shitbreaker"; - dir = 4 - }, -/obj/machinery/shipbreaker, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "hVF" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -24797,10 +24855,6 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron/dark/textured, /area/station/hallway/primary/port) -"hXf" = ( -/obj/structure/cable, -/turf/open/floor/iron/airless, -/area/station/engineering/shipbreaker_hut) "hXt" = ( /turf/open/floor/iron/white, /area/station/science/genetics) @@ -25040,6 +25094,21 @@ /obj/effect/landmark/event_spawn, /turf/open/floor/iron, /area/station/hallway/primary/aft) +"icm" = ( +/obj/structure/rack, +/obj/item/tank/internals/oxygen/yellow{ + pixel_x = 4; + pixel_y = -3 + }, +/obj/item/tank/internals/oxygen/yellow, +/obj/item/tank/internals/oxygen/yellow{ + pixel_x = -4; + pixel_y = 3 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 10 + }, +/area/station/engineering/shipbreaker_hut) "icu" = ( /obj/structure/cable, /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4, @@ -25059,6 +25128,10 @@ /obj/structure/cable, /turf/open/space/basic, /area/station/solars/starboard/fore) +"icU" = ( +/obj/effect/spawner/structure/window/reinforced, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "icV" = ( /obj/structure/sign/painting/library{ pixel_x = -32 @@ -25083,11 +25156,6 @@ dir = 1 }, /area/station/engineering/break_room) -"idr" = ( -/turf/open/floor/iron/dark/side/airless{ - dir = 4 - }, -/area/station/engineering/shipbreaker_hut) "idJ" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4, /turf/open/floor/iron/dark/side{ @@ -27092,11 +27160,6 @@ /obj/effect/decal/cleanable/dirt, /turf/open/floor/plating, /area/station/maintenance/starboard/fore) -"iLC" = ( -/turf/open/floor/iron/dark/side/airless{ - dir = 8 - }, -/area/station/engineering/shipbreaker_hut) "iLF" = ( /obj/structure/disposalpipe/segment{ dir = 4 @@ -27503,10 +27566,6 @@ /obj/effect/decal/cleanable/dirt, /turf/open/floor/plating, /area/station/maintenance/starboard/fore) -"iRr" = ( -/obj/machinery/light/directional/west, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "iRs" = ( /obj/structure/sign/poster/official/random/directional/east, /turf/open/floor/iron/dark/side{ @@ -27619,13 +27678,6 @@ /obj/effect/landmark/start/station_engineer, /turf/open/floor/iron, /area/station/engineering/break_room) -"iUd" = ( -/obj/machinery/door/airlock/external{ - name = "Shipbreaking Storage Room" - }, -/obj/effect/mapping_helpers/airlock/access/any/engineering/general, -/turf/open/floor/iron/dark/textured/airless, -/area/station/engineering/shipbreaker_hut) "iUf" = ( /obj/structure/chair/sofa/bench/left{ dir = 4 @@ -28559,6 +28611,27 @@ /obj/machinery/holopad, /turf/open/floor/iron/dark/smooth_large, /area/station/command/heads_quarters/cmo) +"jlk" = ( +/obj/machinery/light/directional/south, +/obj/structure/table/wood, +/obj/item/toy/figure/cmo{ + pixel_y = 12; + pixel_x = -8 + }, +/obj/item/clothing/neck/stethoscope, +/obj/item/flashlight/pen, +/obj/item/clothing/glasses/hud/health, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/head/cmo, +/turf/open/floor/iron/dark, +/area/station/command/heads_quarters/cmo) "jlr" = ( /obj/effect/turf_decal/tile/yellow/opposingcorners, /turf/open/floor/iron/white, @@ -29941,6 +30014,17 @@ dir = 1 }, /area/station/commons/fitness/recreation) +"jHR" = ( +/obj/item/radio/intercom/directional/south, +/obj/effect/spawner/random/entertainment/cigarette{ + pixel_y = -1 + }, +/obj/effect/spawner/random/entertainment/lighter{ + pixel_x = 7 + }, +/obj/structure/table/wood, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "jHT" = ( /obj/machinery/button/door/directional/north{ id = "dorm_4"; @@ -32101,17 +32185,6 @@ }, /turf/open/floor/iron, /area/station/engineering/main) -"krJ" = ( -/obj/machinery/camera/directional/north{ - c_tag = "Engineering - Shipbreaking, Storage Room"; - name = "engineering camera" - }, -/obj/structure/closet/emcloset/wall/directional/north, -/obj/structure/reagent_dispensers/fueltank, -/turf/open/floor/iron/dark/side/airless{ - dir = 1 - }, -/area/station/engineering/shipbreaker_hut) "krQ" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 9 @@ -32704,6 +32777,12 @@ /obj/machinery/light/small/directional/north, /turf/open/floor/iron, /area/station/cargo/warehouse) +"kCB" = ( +/obj/machinery/portable_atmospherics/canister/oxygen, +/turf/open/floor/iron/dark/side/airless{ + dir = 6 + }, +/area/station/engineering/shipbreaker_hut) "kCD" = ( /obj/effect/turf_decal/tile/red/fourcorners, /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer2, @@ -33300,9 +33379,6 @@ /obj/effect/spawner/random/trash/box, /turf/open/floor/plating, /area/station/maintenance/department/science) -"kND" = ( -/turf/open/floor/glass/reinforced/airless, -/area/station/engineering/shipbreaker_hut) "kNH" = ( /obj/effect/turf_decal/stripes/line, /obj/effect/turf_decal/stripes/line{ @@ -37095,50 +37171,22 @@ }, /turf/open/floor/iron/white, /area/station/science/xenobiology) -"lYB" = ( -/obj/machinery/digital_clock/directional/south, -/obj/machinery/button/door/directional/west{ - id = "nt_rep_office_door"; - name = "Office Door Bolt Control"; - req_access = list("nt_rep"); - pixel_y = -6; - normaldoorcontrol = 1; - specialfunctions = 4 - }, -/obj/machinery/button/door/directional/west{ - id = "nt_rep_desk_shutters"; - name = "Desk Shutters Control"; - req_access = list("nt_rep"); +"lYA" = ( +/obj/structure/rack, +/obj/item/storage/toolbox/electrical{ pixel_y = 6 }, -/obj/structure/table/wood, -/obj/item/stamp/granted{ - pixel_y = 6; - pixel_x = 8 - }, -/obj/item/stamp/denied{ - pixel_x = 8 - }, -/obj/item/folder/blue{ - pixel_x = -6 - }, -/obj/item/folder/blue{ - pixel_y = 3; - pixel_x = -6 - }, -/obj/item/folder/blue{ - pixel_y = 6; - pixel_x = -6 - }, -/obj/item/pen/fountain{ - pixel_x = -6 +/obj/item/storage/toolbox/mechanical, +/obj/item/storage/toolbox/emergency{ + pixel_y = -6 }, -/obj/item/pen/fourcolor{ - pixel_y = 6; - pixel_x = -3 +/turf/open/floor/iron/dark/side/airless{ + dir = 5 }, -/turf/open/floor/wood/parquet, -/area/station/command/heads_quarters/nt_rep) +/area/station/engineering/shipbreaker_hut) +"lYF" = ( +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "lYM" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -37795,6 +37843,15 @@ }, /turf/open/floor/stone, /area/station/science/xenobiology) +"mjq" = ( +/obj/machinery/status_display/evac/directional/west, +/obj/machinery/newscaster/directional/north, +/obj/structure/table, +/obj/item/paper_bin, +/turf/open/floor/iron/dark/side/airless{ + dir = 9 + }, +/area/station/engineering/shipbreaker_hut) "mjw" = ( /obj/structure/table/wood, /obj/item/paper_bin, @@ -38765,18 +38822,6 @@ /obj/effect/mapping_helpers/airlock/access/all/science/general, /turf/open/floor/iron/white/textured, /area/station/science/auxlab) -"mzC" = ( -/obj/machinery/light/small/directional/east, -/obj/machinery/camera/directional/east{ - c_tag = "Engineering - Shipbreaking, Control Room"; - name = "engineering camera" - }, -/obj/machinery/light_switch/directional/south, -/obj/item/radio/intercom/directional/east, -/turf/open/floor/iron/dark/side/airless{ - dir = 6 - }, -/area/station/engineering/shipbreaker_hut) "mzF" = ( /obj/effect/turf_decal/trimline/neutral/line{ dir = 4 @@ -39140,6 +39185,9 @@ /obj/effect/decal/cleanable/dirt, /turf/open/floor/iron, /area/station/maintenance/department/science) +"mGX" = ( +/turf/open/floor/glass/reinforced/airless, +/area/station/engineering/shipbreaker_hut) "mHe" = ( /obj/effect/turf_decal/siding/wood/corner{ dir = 8 @@ -41649,15 +41697,6 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron/dark/textured, /area/station/hallway/primary/aft) -"nyZ" = ( -/obj/machinery/conveyor_switch/oneway{ - id = "shitbreaker" - }, -/obj/structure/window/spawner/directional/south, -/obj/structure/window/spawner/directional/east, -/obj/structure/window/spawner/directional/west, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "nzl" = ( /obj/machinery/firealarm/directional/east, /turf/open/floor/iron/dark, @@ -41782,6 +41821,13 @@ }, /turf/open/floor/iron/dark, /area/station/cargo/sorting) +"nBd" = ( +/obj/machinery/conveyor{ + id = "shitbreaker"; + dir = 1 + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "nBk" = ( /obj/effect/turf_decal/stripes/line{ dir = 1 @@ -43239,6 +43285,17 @@ /obj/effect/mapping_helpers/airlock/access/any/supply/mining, /turf/open/floor/iron/dark/textured, /area/station/cargo/miningoffice) +"nYX" = ( +/obj/structure/table, +/obj/item/pen, +/obj/item/pen/red{ + pixel_x = 6; + pixel_y = 6 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 8 + }, +/area/station/engineering/shipbreaker_hut) "nZa" = ( /obj/machinery/light/small/directional/east, /obj/machinery/camera/directional/east{ @@ -44107,6 +44164,31 @@ /obj/structure/sign/warning/rad_shelter/directional/west, /turf/open/floor/iron/dark, /area/station/security/prison) +"onS" = ( +/obj/structure/table/reinforced, +/obj/item/paper_bin{ + pixel_y = 6 + }, +/obj/item/clipboard{ + pixel_y = 6 + }, +/obj/item/folder/yellow{ + pixel_y = 6 + }, +/obj/item/pen{ + pixel_y = 4 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/head/ce, +/turf/open/floor/iron, +/area/station/command/heads_quarters/ce) "onZ" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -44874,6 +44956,18 @@ /obj/effect/mapping_helpers/airlock/cyclelink_helper, /turf/open/floor/iron/dark/textured_large, /area/station/cargo/miningoffice) +"oBm" = ( +/obj/structure/closet/mini_fridge, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/storage/cans/sixbeer, +/obj/machinery/light/directional/west, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "oBo" = ( /obj/effect/turf_decal/trimline/red/filled/corner{ dir = 1 @@ -45229,12 +45323,6 @@ /obj/machinery/component_printer, /turf/open/floor/iron/white, /area/station/science/circuits) -"oIh" = ( -/obj/structure/chair/comfy/teal{ - dir = 4 - }, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "oIs" = ( /obj/machinery/camera/directional/east{ c_tag = "Command - Bridge, Hall, West"; @@ -46553,6 +46641,20 @@ }, /turf/open/floor/iron/dark, /area/station/security/processing) +"pey" = ( +/obj/machinery/status_display/ai/directional/west, +/obj/structure/extinguisher_cabinet/directional/south, +/obj/structure/table, +/obj/item/weldingtool/electric/raynewelder{ + pixel_y = -5 + }, +/obj/item/weldingtool/electric/raynewelder{ + pixel_y = 6 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 10 + }, +/area/station/engineering/shipbreaker_hut) "peO" = ( /obj/machinery/light/small/directional/south, /obj/machinery/light_switch/directional/south{ @@ -47540,12 +47642,6 @@ "pvL" = ( /turf/closed/wall, /area/station/medical/psychology) -"pvQ" = ( -/obj/machinery/door/airlock/engineering, -/obj/structure/cable, -/obj/structure/fans/tiny, -/turf/open/floor/plating, -/area/station/engineering/shipbreaker_hut) "pwg" = ( /obj/effect/turf_decal/stripes/line{ dir = 4 @@ -48313,9 +48409,6 @@ /obj/effect/landmark/start/hangover, /turf/open/floor/iron, /area/station/service/hydroponics/garden) -"pHR" = ( -/turf/open/space/basic, -/area/shipbreak) "pHW" = ( /obj/machinery/atmospherics/pipe/layer_manifold/scrubbers/hidden{ dir = 4 @@ -48814,10 +48907,6 @@ /obj/machinery/light/directional/south, /turf/open/floor/iron/white, /area/station/medical/medbay/central) -"pRf" = ( -/obj/effect/spawner/structure/window, -/turf/open/floor/plating, -/area/station/engineering/shipbreaker_hut) "pRn" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/iron/dark, @@ -48833,27 +48922,6 @@ }, /turf/open/floor/iron/dark/textured, /area/station/hallway/primary/fore) -"pRD" = ( -/obj/machinery/light/directional/south, -/obj/structure/table/wood, -/obj/item/toy/figure/cmo{ - pixel_y = 12; - pixel_x = -8 - }, -/obj/item/clothing/neck/stethoscope, -/obj/item/flashlight/pen, -/obj/item/clothing/glasses/hud/health, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/head/cmo, -/turf/open/floor/iron/dark, -/area/station/command/heads_quarters/cmo) "pSn" = ( /obj/machinery/light/small/directional/south, /obj/structure/table, @@ -51374,6 +51442,45 @@ /obj/machinery/firealarm/directional/north, /turf/open/floor/iron/dark, /area/station/security/detectives_office) +"qKg" = ( +/obj/effect/turf_decal/siding/wood{ + dir = 4 + }, +/obj/machinery/camera/directional/west{ + c_tag = "Security - Head of Security Room"; + name = "security camera" + }, +/obj/item/radio/intercom/directional/west, +/obj/structure/table/wood, +/obj/item/phone{ + pixel_x = -6; + pixel_y = 12 + }, +/obj/machinery/recharger{ + pixel_x = -6 + }, +/obj/item/paper_bin{ + pixel_y = 3; + pixel_x = 7 + }, +/obj/item/folder/red{ + pixel_x = 7; + pixel_y = 5 + }, +/obj/item/stamp/granted{ + pixel_y = 11; + pixel_x = 7 + }, +/obj/item/stamp/head/hos{ + pixel_x = 7; + pixel_y = 7 + }, +/obj/item/stamp/denied{ + pixel_x = 7; + pixel_y = 3 + }, +/turf/open/floor/wood, +/area/station/command/heads_quarters/hos) "qKk" = ( /obj/effect/turf_decal/stripes/line, /obj/effect/turf_decal/stripes/line{ @@ -51961,6 +52068,14 @@ "qUS" = ( /turf/closed/wall, /area/station/medical/patients_rooms/room_a) +"qUT" = ( +/obj/structure/cable, +/obj/machinery/door/airlock/external{ + name = "Shipbreaking Control Room" + }, +/obj/effect/mapping_helpers/airlock/access/any/engineering/general, +/turf/open/floor/iron/dark/textured/airless, +/area/station/engineering/shipbreaker_hut) "qVf" = ( /obj/structure/disposalpipe/segment, /turf/open/floor/plating, @@ -53244,6 +53359,14 @@ /obj/effect/mapping_helpers/airlock/access/all/science/general, /turf/open/floor/catwalk_floor/iron_dark, /area/station/science/research) +"ruq" = ( +/obj/machinery/light/directional/west, +/obj/machinery/conveyor/inverted{ + dir = 9; + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "ruu" = ( /obj/structure/cable, /obj/structure/cable/layer3, @@ -54655,51 +54778,6 @@ /obj/machinery/camera/autoname/directional/west, /turf/open/floor/iron/dark, /area/station/hallway/secondary/exit/departure_lounge) -"rPY" = ( -/obj/machinery/light/directional/south, -/obj/structure/reagent_dispensers/watertank, -/obj/structure/extinguisher_cabinet/directional/south, -/turf/open/floor/iron/dark/side/airless, -/area/station/engineering/shipbreaker_hut) -"rQs" = ( -/obj/effect/turf_decal/siding/wood{ - dir = 4 - }, -/obj/machinery/camera/directional/west{ - c_tag = "Security - Head of Security Room"; - name = "security camera" - }, -/obj/item/radio/intercom/directional/west, -/obj/structure/table/wood, -/obj/item/phone{ - pixel_x = -6; - pixel_y = 12 - }, -/obj/machinery/recharger{ - pixel_x = -6 - }, -/obj/item/paper_bin{ - pixel_y = 3; - pixel_x = 7 - }, -/obj/item/folder/red{ - pixel_x = 7; - pixel_y = 5 - }, -/obj/item/stamp/granted{ - pixel_y = 11; - pixel_x = 7 - }, -/obj/item/stamp/head/hos{ - pixel_x = 7; - pixel_y = 7 - }, -/obj/item/stamp/denied{ - pixel_x = 7; - pixel_y = 3 - }, -/turf/open/floor/wood, -/area/station/command/heads_quarters/hos) "rQv" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 10 @@ -56477,9 +56555,6 @@ /obj/machinery/photocopier, /turf/open/floor/wood, /area/station/service/lawoffice) -"sxb" = ( -/turf/closed/wall/r_wall, -/area/station/engineering/shipbreaker_hut) "sxf" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 1 @@ -57174,10 +57249,6 @@ /obj/effect/spawner/random/maintenance, /turf/open/floor/plating, /area/station/maintenance/department/engine) -"sKS" = ( -/obj/structure/cable, -/turf/open/floor/iron/dark/side/airless, -/area/station/engineering/shipbreaker_hut) "sKX" = ( /obj/structure/lattice, /obj/machinery/atmospherics/pipe/smart/simple/cyan/visible/layer2{ @@ -57587,14 +57658,6 @@ dir = 1 }, /area/station/commons/storage/primary) -"sQK" = ( -/obj/machinery/light/directional/west, -/obj/machinery/conveyor/inverted{ - dir = 9; - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "sQL" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 4 @@ -59736,10 +59799,6 @@ dir = 4 }, /area/station/commons/dorms) -"txb" = ( -/obj/machinery/computer/security/telescreen/entertainment/directional/east, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "txf" = ( /obj/machinery/atmospherics/components/trinary/mixer/airmix{ dir = 1 @@ -60086,6 +60145,10 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /turf/open/floor/iron/dark/telecomms, /area/station/tcommsat/server) +"tBV" = ( +/obj/machinery/computer/security/telescreen/entertainment/directional/east, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "tCb" = ( /obj/machinery/chem_master/condimaster{ name = "CondiMaster Neo" @@ -60396,17 +60459,6 @@ /obj/effect/turf_decal/vg_decals/atmos/nitrous_oxide, /turf/open/floor/engine/n2o, /area/station/engineering/atmos) -"tJo" = ( -/obj/item/radio/intercom/directional/south, -/obj/effect/spawner/random/entertainment/cigarette{ - pixel_y = -1 - }, -/obj/effect/spawner/random/entertainment/lighter{ - pixel_x = 7 - }, -/obj/structure/table/wood, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "tJu" = ( /obj/machinery/atmospherics/pipe/smart/simple/scrubbers/visible, /obj/structure/cable, @@ -60493,6 +60545,27 @@ /obj/effect/landmark/start/shaft_miner, /turf/open/floor/iron, /area/station/cargo/miningoffice) +"tKI" = ( +/obj/machinery/power/apc/auto_name/directional/north, +/obj/structure/cable, +/obj/structure/table, +/obj/item/folder{ + pixel_x = -3; + pixel_y = -3 + }, +/obj/item/folder, +/obj/item/folder{ + pixel_x = 3; + pixel_y = 3 + }, +/obj/item/folder{ + pixel_x = 6; + pixel_y = 6 + }, +/turf/open/floor/iron/dark/side/airless{ + dir = 1 + }, +/area/station/engineering/shipbreaker_hut) "tKL" = ( /obj/effect/turf_decal/trimline/brown/filled/line{ dir = 4 @@ -62160,21 +62233,6 @@ dir = 4 }, /area/station/hallway/secondary/exit/departure_lounge) -"umW" = ( -/obj/structure/rack, -/obj/item/radio/off{ - pixel_x = -6; - pixel_y = 4 - }, -/obj/item/radio/off{ - pixel_x = 6; - pixel_y = 4 - }, -/obj/item/radio/off, -/turf/open/floor/iron/dark/side/airless{ - dir = 9 - }, -/area/station/engineering/shipbreaker_hut) "umX" = ( /obj/effect/mapping_helpers/iannewyear, /turf/open/floor/carpet/royalblue, @@ -62262,10 +62320,6 @@ /obj/effect/decal/cleanable/dirt, /turf/open/floor/iron, /area/station/maintenance/department/science) -"uoC" = ( -/obj/effect/spawner/structure/window/reinforced, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "uoE" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -62841,6 +62895,9 @@ }, /turf/open/floor/iron/dark, /area/station/engineering/atmos) +"uye" = ( +/turf/closed/wall/r_wall, +/area/station/engineering/shipbreaker_hut) "uym" = ( /obj/machinery/firealarm/directional/north, /turf/open/floor/carpet/neon/simple/pink, @@ -63143,10 +63200,6 @@ /obj/machinery/duct, /turf/open/floor/iron/white, /area/station/medical/medbay/aft) -"uEM" = ( -/obj/effect/spawner/structure/window, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "uEU" = ( /obj/effect/turf_decal/siding/thinplating/dark{ dir = 8 @@ -63691,19 +63744,6 @@ /obj/machinery/recharge_station, /turf/open/floor/iron/white, /area/station/medical/storage) -"uMx" = ( -/obj/structure/rack, -/obj/item/storage/toolbox/electrical{ - pixel_y = 6 - }, -/obj/item/storage/toolbox/mechanical, -/obj/item/storage/toolbox/emergency{ - pixel_y = -6 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 5 - }, -/area/station/engineering/shipbreaker_hut) "uMz" = ( /obj/structure/disposalpipe/segment{ dir = 4 @@ -64030,6 +64070,15 @@ /obj/structure/closet/secure_closet/exile, /turf/open/floor/iron/dark/textured, /area/station/command/gateway) +"uSe" = ( +/obj/machinery/conveyor_switch/oneway{ + id = "shitbreaker" + }, +/obj/structure/window/spawner/directional/south, +/obj/structure/window/spawner/directional/east, +/obj/structure/window/spawner/directional/west, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "uSp" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -64331,6 +64380,13 @@ dir = 8 }, /area/station/hallway/primary/aft) +"uWs" = ( +/obj/machinery/light/small/directional/east, +/obj/structure/filingcabinet, +/turf/open/floor/iron/dark/side/airless{ + dir = 5 + }, +/area/station/engineering/shipbreaker_hut) "uWv" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 9 @@ -64381,6 +64437,16 @@ /obj/structure/sign/warning/vacuum/external/directional/south, /turf/open/floor/iron/dark, /area/station/engineering/atmos/storage) +"uWQ" = ( +/obj/machinery/light/directional/west{ + dir = 4 + }, +/obj/machinery/conveyor/inverted{ + dir = 10; + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "uWY" = ( /obj/structure/table/wood, /obj/item/toy/plush/beeplushie, @@ -64493,27 +64559,6 @@ /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4, /turf/open/floor/carpet/blue, /area/station/commons/dorms/room2) -"uZR" = ( -/obj/machinery/power/apc/auto_name/directional/north, -/obj/structure/cable, -/obj/structure/table, -/obj/item/folder{ - pixel_x = -3; - pixel_y = -3 - }, -/obj/item/folder, -/obj/item/folder{ - pixel_x = 3; - pixel_y = 3 - }, -/obj/item/folder{ - pixel_x = 6; - pixel_y = 6 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 1 - }, -/area/station/engineering/shipbreaker_hut) "vac" = ( /obj/structure/closet/crate, /obj/item/stock_parts/micro_laser, @@ -65634,6 +65679,17 @@ /obj/item/assembly/timer, /turf/open/floor/plating, /area/station/maintenance/department/engine) +"vqA" = ( +/obj/machinery/coffeemaker/impressa{ + pixel_y = 5 + }, +/obj/item/storage/box/coffeepack{ + pixel_x = 9; + pixel_y = -1 + }, +/obj/structure/table/wood, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "vqJ" = ( /obj/effect/turf_decal/tile/bar/opposingcorners{ dir = 1 @@ -65801,6 +65857,10 @@ }, /turf/open/floor/wood, /area/station/security/detectives_office) +"vtb" = ( +/obj/effect/spawner/structure/window, +/turf/open/floor/plating, +/area/station/engineering/shipbreaker_hut) "vtc" = ( /obj/structure/disposalpipe/segment, /turf/open/floor/iron/dark/side, @@ -67181,6 +67241,10 @@ /obj/machinery/holopad, /turf/open/floor/iron/dark/smooth_large, /area/station/hallway/primary/starboard) +"vOR" = ( +/obj/effect/spawner/structure/window, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "vOS" = ( /obj/effect/turf_decal/stripes/line{ dir = 1 @@ -67202,11 +67266,6 @@ /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, /area/station/engineering/atmos) -"vOV" = ( -/obj/structure/bed/dogbed/runtime, -/mob/living/basic/pet/cat/runtime, -/turf/open/floor/carpet/blue, -/area/station/command/heads_quarters/cmo) "vOX" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -67496,29 +67555,6 @@ }, /turf/open/floor/iron/white, /area/station/science/lab) -"vSA" = ( -/obj/structure/table/reinforced, -/obj/item/paper_bin{ - pixel_y = 5 - }, -/obj/item/folder/white{ - pixel_y = 7 - }, -/obj/item/pen{ - pixel_y = 7 - }, -/obj/item/stamp/head/rd{ - pixel_y = 10 - }, -/obj/item/toy/figure/rd{ - pixel_x = -13 - }, -/obj/item/stamp/denied{ - pixel_y = 5 - }, -/obj/item/stamp/granted, -/turf/open/floor/carpet/purple, -/area/station/command/heads_quarters/rd) "vSE" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /turf/open/floor/wood, @@ -67602,23 +67638,6 @@ /obj/structure/cable, /turf/open/floor/iron/dark, /area/station/command/gateway) -"vUx" = ( -/obj/machinery/keycard_auth/directional/east, -/obj/structure/table/wood, -/obj/item/paper_bin, -/obj/item/folder/blue, -/obj/item/pen/fountain, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/head/captain, -/turf/open/floor/wood, -/area/station/command/heads_quarters/captain) "vUA" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4{ dir = 4 @@ -68786,6 +68805,11 @@ /obj/structure/cable, /turf/open/floor/iron/dark, /area/station/hallway/primary/aft) +"wmv" = ( +/obj/structure/bed/dogbed/runtime, +/mob/living/basic/pet/cat/runtime, +/turf/open/floor/carpet/blue, +/area/station/command/heads_quarters/cmo) "wmy" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 10 @@ -69707,12 +69731,6 @@ /obj/effect/turf_decal/delivery, /turf/open/floor/iron/large, /area/station/engineering/storage) -"wCP" = ( -/obj/machinery/conveyor{ - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "wCX" = ( /obj/effect/turf_decal/siding/thinplating/dark, /obj/machinery/light/small/directional/west, @@ -70252,6 +70270,13 @@ /obj/structure/cable/layer3, /turf/open/floor/engine, /area/station/ai_monitored/turret_protected/ai) +"wLX" = ( +/obj/structure/chair{ + dir = 8 + }, +/obj/structure/cable, +/turf/open/floor/iron/airless, +/area/station/engineering/shipbreaker_hut) "wMm" = ( /obj/effect/turf_decal/trimline/neutral/filled/corner, /obj/effect/turf_decal/trimline/neutral/line{ @@ -70464,13 +70489,6 @@ /obj/machinery/duct, /turf/open/floor/iron/dark, /area/station/command/bridge) -"wPq" = ( -/obj/machinery/conveyor{ - id = "shitbreaker"; - dir = 1 - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "wPy" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 4 @@ -70584,12 +70602,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/catwalk_floor, /area/station/maintenance/starboard/aft) -"wRh" = ( -/obj/machinery/portable_atmospherics/canister/oxygen, -/turf/open/floor/iron/dark/side/airless{ - dir = 6 - }, -/area/station/engineering/shipbreaker_hut) "wRs" = ( /obj/effect/decal/cleanable/dirt, /obj/effect/spawner/random/structure/grille, @@ -70716,9 +70728,6 @@ /obj/machinery/status_display/ai/directional/west, /turf/open/floor/iron/dark, /area/station/engineering/engine_smes) -"wUb" = ( -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "wUe" = ( /obj/machinery/digital_clock/directional/east, /turf/open/floor/wood/large, @@ -71910,14 +71919,6 @@ /obj/machinery/growing/tray, /turf/open/floor/iron/dark/side, /area/station/service/hydroponics) -"xqV" = ( -/obj/machinery/computer/shipbreaker{ - dir = 4 - }, -/turf/open/floor/iron/dark/side/airless{ - dir = 8 - }, -/area/station/engineering/shipbreaker_hut) "xqW" = ( /obj/effect/turf_decal/tile/neutral/fourcorners, /obj/effect/turf_decal/bot_red, @@ -72382,6 +72383,10 @@ dir = 6 }, /area/station/service/hydroponics) +"xyn" = ( +/obj/structure/cable, +/turf/open/floor/iron/dark/side/airless, +/area/station/engineering/shipbreaker_hut) "xyv" = ( /turf/closed/wall, /area/station/cargo/drone_bay) @@ -72603,31 +72608,6 @@ dir = 1 }, /area/station/service/hydroponics) -"xBX" = ( -/obj/structure/table/reinforced, -/obj/item/paper_bin{ - pixel_y = 6 - }, -/obj/item/clipboard{ - pixel_y = 6 - }, -/obj/item/folder/yellow{ - pixel_y = 6 - }, -/obj/item/pen{ - pixel_y = 4 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/head/ce, -/turf/open/floor/iron, -/area/station/command/heads_quarters/ce) "xCa" = ( /obj/structure/table, /obj/item/stack/cable_coil, @@ -73093,6 +73073,14 @@ /obj/item/kirbyplants/random, /turf/open/floor/iron/dark, /area/station/security/prison) +"xKK" = ( +/obj/machinery/conveyor{ + id = "shitbreaker"; + dir = 4 + }, +/obj/machinery/shipbreaker, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "xKM" = ( /obj/machinery/airalarm/directional/south, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden, @@ -73668,6 +73656,12 @@ /obj/item/radio/intercom/directional/east, /turf/open/floor/iron/dark, /area/station/security/courtroom) +"xTH" = ( +/obj/machinery/door/airlock/engineering, +/obj/structure/cable, +/obj/structure/fans/tiny, +/turf/open/floor/plating, +/area/station/engineering/shipbreaker_hut) "xTL" = ( /obj/effect/decal/cleanable/dirt, /obj/effect/landmark/start/gary, @@ -74798,6 +74792,12 @@ /obj/effect/mapping_helpers/requests_console/ore_update, /turf/open/floor/carpet/purple, /area/station/command/heads_quarters/rd) +"ylk" = ( +/obj/machinery/light/directional/south, +/obj/structure/reagent_dispensers/watertank, +/obj/structure/extinguisher_cabinet/directional/south, +/turf/open/floor/iron/dark/side/airless, +/area/station/engineering/shipbreaker_hut) "ylx" = ( /obj/machinery/power/apc/auto_name/directional/north, /obj/structure/cable, @@ -82501,31 +82501,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -82758,31 +82758,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -83015,31 +83015,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -83272,31 +83272,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -83529,31 +83529,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -83786,31 +83786,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -84043,31 +84043,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -84300,31 +84300,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -84557,31 +84557,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -84814,31 +84814,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -85071,31 +85071,31 @@ ksa ndy uoo rxc -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq rxc uoo ndy @@ -85211,7 +85211,7 @@ rDF biQ dpZ biQ -lYB +esj nZL qPR iHO @@ -85328,31 +85328,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -85585,31 +85585,31 @@ ksa ndy uoo aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH uoo ndy @@ -85842,31 +85842,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -86099,31 +86099,31 @@ ksa ndy uoo rxc -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq rxc uoo ndy @@ -86356,31 +86356,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -86613,31 +86613,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -86870,31 +86870,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -87127,31 +87127,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -87384,31 +87384,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -87641,31 +87641,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -87898,31 +87898,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -88155,31 +88155,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -88412,31 +88412,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -88669,31 +88669,31 @@ ksa fdt ksa aVH -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR -pHR +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq +apq aVH ksa fdt @@ -92795,9 +92795,9 @@ ksa aVH aVH aVH -uEM -gwf -gwf +vOR +eES +eES ksa ksa ksa @@ -93041,20 +93041,20 @@ ksa ksa ksa ksa -sxb -sxb -uoC -uoC -uoC -sxb -sxb +uye +uye +icU +icU +icU +uye +uye iCE uoo aVH -wUb -wCP -sQK -gwf +drP +ezq +ruq +eES ksa ksa ksa @@ -93298,20 +93298,20 @@ ksa ksa ksa ksa -sxb -aNC -fho -xqV -fbA -fak -sxb +uye +mjq +nYX +erI +ewi +pey +uye uoo aVH aVH -wUb -nyZ -hVt -gwf +drP +uSe +xKK +eES ksa ksa ksa @@ -93555,21 +93555,21 @@ ksa ksa ksa ksa -sxb -uZR -hXf -fVP -hXf -sKS -hLk +uye +tKI +aCb +wLX +aCb +xyn +qUT vCp vCp vCp -wUb -wPq -hxZ -gwf -gwf +drP +nBd +uWQ +eES +eES ksa ksa ksa @@ -93812,21 +93812,21 @@ ksa ksa ksa ksa -sxb -eGu -idr -idr -idr -mzC -sxb +uye +uWs +brl +brl +brl +bhU +uye uoo aVH vCp -wUb -wUb -wUb -wUb -gwf +drP +drP +drP +drP +eES ksa ksa ksa @@ -94069,22 +94069,22 @@ uoo fdt ksa ksa -sxb -sxb -sxb -iUd -sxb -sxb -sxb +uye +uye +uye +bnI +uye +uye +uye iCE uoo vCp uoo -gwf -gwf -pvQ -gwf -gwf +eES +eES +xTH +eES +eES ksa ksa ksa @@ -94327,21 +94327,21 @@ fdt ksa ksa ksa -sxb -umW -iLC -fzZ -sxb +uye +hgp +eIP +icm +uye ksa uoo ksa vCp ksa -pRf -iRr -aYq -eVx -pRf +vtb +afe +bdI +oBm +vtb ksa ksa ksa @@ -94584,21 +94584,21 @@ fdt ksa ksa ksa -sxb -krJ -kND -rPY -sxb +uye +hvx +mGX +ylk +uye uoo jra vCp vCp uoo -pRf -oIh -eKX -dia -pRf +vtb +gzh +lYF +vqA +vtb ksa ksa ksa @@ -94841,21 +94841,21 @@ fdt ksa ksa ksa -sxb -uMx -idr -wRh -sxb +uye +lYA +brl +kCB +uye ksa uoo ksa aVH ksa -gwf -txb -eKX -tJo -gwf +eES +tBV +lYF +jHR +eES ksa ksa ksa @@ -95098,21 +95098,21 @@ fdt ksa ksa ksa -sxb -sxb -uoC -sxb -sxb +uye +uye +icU +uye +uye uoo uoo uoo aVH uoo -gwf -gwf -gwf -pRf -gwf +eES +eES +eES +vtb +eES ksa ksa niB @@ -104069,7 +104069,7 @@ enU dTZ dsX xOy -xBX +onS iHk wOC kYR @@ -107042,7 +107042,7 @@ ksa xXP mrP pOC -rQs +qKg mkx lFE bLO @@ -107105,7 +107105,7 @@ rTS xvo lnK lpE -vUx +cJt twv hDl uFK @@ -112484,7 +112484,7 @@ kaP qvC mkl gSE -vSA +cwY min cst qQz @@ -114565,7 +114565,7 @@ tzV qrH nTa vaW -vOV +wmv sWO kOa lWn @@ -114824,7 +114824,7 @@ uaC kSU kYU oWu -pRD +jlk lWn aio nCY @@ -123054,7 +123054,7 @@ qaG gji dOL nVc -gSC +dju nBE nep mhc diff --git a/_maps/map_files/MetaStation/MetaStation.dmm b/_maps/map_files/MetaStation/MetaStation.dmm index 37db730a9365..fff4dce1f233 100644 --- a/_maps/map_files/MetaStation/MetaStation.dmm +++ b/_maps/map_files/MetaStation/MetaStation.dmm @@ -936,6 +936,10 @@ /obj/machinery/atmospherics/components/unary/portables_connector/visible, /turf/open/floor/plating, /area/station/maintenance/starboard/greater) +"arb" = ( +/obj/effect/spawner/structure/window, +/turf/open/floor/plating, +/area/station/engineering/shipbreaker_hut) "arg" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /obj/effect/spawner/random/structure/closet_maintenance, @@ -1093,6 +1097,9 @@ /obj/effect/turf_decal/tile/red/fourcorners, /turf/open/floor/iron/dark, /area/station/security/checkpoint/medical) +"atX" = ( +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "auh" = ( /obj/effect/turf_decal/stripes/corner{ dir = 8 @@ -1596,14 +1603,6 @@ }, /turf/open/floor/iron/checker, /area/station/science/research) -"aDq" = ( -/obj/machinery/conveyor{ - dir = 4; - id = "shitbreaker" - }, -/obj/machinery/shipbreaker, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "aDA" = ( /obj/machinery/light/small/directional/south, /obj/item/folder, @@ -1950,13 +1949,6 @@ /obj/effect/mapping_helpers/airlock/access/all/medical/general, /turf/open/floor/plating, /area/station/maintenance/port/aft) -"aIC" = ( -/obj/effect/turf_decal/stripes/line, -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "aID" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -3623,6 +3615,10 @@ }, /turf/closed/wall, /area/station/security/courtroom) +"bjC" = ( +/obj/machinery/computer/security/telescreen/entertainment/directional/east, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "bjH" = ( /obj/machinery/modular_computer/preset/cargochat/engineering, /obj/effect/turf_decal/trimline/brown/filled/line{ @@ -3730,6 +3726,13 @@ }, /turf/open/floor/wood/large, /area/station/medical/pathology) +"blu" = ( +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/effect/landmark/start/gary, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "blw" = ( /obj/structure/transit_tube/curved{ dir = 8 @@ -4398,12 +4401,6 @@ /obj/effect/landmark/event_spawn, /turf/open/floor/iron, /area/station/ai_monitored/command/storage/eva) -"bwP" = ( -/obj/structure/cable, -/obj/machinery/power/apc/auto_name/directional/north, -/obj/effect/mapping_helpers/apc/full_charge, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "bxf" = ( /obj/effect/turf_decal/tile/neutral{ dir = 8 @@ -4663,6 +4660,15 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /turf/open/floor/iron, /area/station/security/prison) +"bBQ" = ( +/obj/effect/turf_decal/tile/blue/anticorner/contrasted{ + dir = 4 + }, +/obj/structure/bed/dogbed/runtime, +/obj/item/toy/cattoy, +/mob/living/basic/pet/cat/runtime, +/turf/open/floor/iron/white, +/area/station/command/heads_quarters/cmo) "bCc" = ( /obj/effect/turf_decal/stripes/line{ dir = 8 @@ -4959,13 +4965,6 @@ }, /turf/open/floor/sandy_dirt, /area/station/service/hydroponics) -"bJC" = ( -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/effect/landmark/start/gary, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "bJQ" = ( /obj/machinery/vending/coffee, /obj/effect/turf_decal/bot, @@ -4990,6 +4989,13 @@ /obj/effect/spawner/random/vending/colavend, /turf/open/floor/iron/dark, /area/station/command/bridge) +"bKu" = ( +/obj/machinery/conveyor{ + dir = 6; + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "bKv" = ( /obj/item/pen, /obj/structure/table/reinforced, @@ -6020,9 +6026,6 @@ /obj/structure/cable, /turf/open/floor/iron/dark/textured_large, /area/station/security/bitden) -"ciU" = ( -/turf/open/space/basic, -/area/shipbreak) "cji" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 8 @@ -7001,12 +7004,6 @@ /obj/effect/mapping_helpers/airlock/access/all/medical/general, /turf/open/floor/iron/white, /area/station/medical/abandoned) -"czs" = ( -/obj/structure/easel, -/obj/effect/mapping_helpers/broken_floor, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "czG" = ( /obj/effect/turf_decal/tile/neutral{ dir = 1 @@ -8043,6 +8040,13 @@ /obj/effect/mapping_helpers/airlock/access/all/engineering/aux_base, /turf/open/floor/plating, /area/station/construction/mining/aux_base) +"cWO" = ( +/obj/effect/turf_decal/stripes/line{ + dir = 1 + }, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "cWT" = ( /obj/machinery/door/firedoor, /obj/structure/disposalpipe/segment, @@ -9218,11 +9222,6 @@ }, /turf/open/floor/iron, /area/station/security/warden) -"dso" = ( -/obj/structure/chair/office/light, -/obj/structure/cable, -/turf/open/floor/iron/white, -/area/station/command/heads_quarters/cmo) "dsq" = ( /obj/machinery/door/airlock/research{ name = "Ordnance Lab" @@ -9339,10 +9338,6 @@ }, /turf/open/floor/plating, /area/station/maintenance/starboard/aft) -"dtN" = ( -/obj/structure/cable, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "dtY" = ( /obj/machinery/meter/monitored/waste_loop, /obj/effect/turf_decal/tile/yellow{ @@ -9572,6 +9567,12 @@ }, /turf/open/floor/plating, /area/station/science/lab) +"dzk" = ( +/obj/structure/chair/comfy/teal{ + dir = 4 + }, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "dzq" = ( /obj/item/radio/intercom/directional/north, /obj/machinery/light/directional/north, @@ -11267,25 +11268,6 @@ /obj/docking_port/stationary/escape_pod, /turf/open/space/basic, /area/space) -"edo" = ( -/obj/structure/table/glass, -/obj/item/paper_bin, -/obj/item/clipboard, -/obj/item/toy/figure/cmo, -/obj/structure/cable, -/obj/item/stamp/head/cmo{ - pixel_y = 12 - }, -/obj/item/stamp/denied{ - pixel_x = -8; - pixel_y = 12 - }, -/obj/item/stamp/granted{ - pixel_y = 12; - pixel_x = 8 - }, -/turf/open/floor/iron/white, -/area/station/command/heads_quarters/cmo) "edu" = ( /turf/closed/wall/r_wall, /area/station/maintenance/solars/starboard/aft) @@ -12141,13 +12123,6 @@ /obj/effect/spawner/random/maintenance, /turf/open/floor/plating, /area/station/maintenance/port/aft) -"erv" = ( -/obj/machinery/conveyor{ - dir = 6; - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "erF" = ( /obj/structure/cable, /obj/machinery/door/airlock/virology/glass{ @@ -12288,17 +12263,6 @@ /obj/structure/light_construct/small/directional/east, /turf/open/floor/wood, /area/station/maintenance/port/aft) -"ety" = ( -/obj/structure/lattice/catwalk, -/obj/structure/rack, -/obj/item/weldingtool/electric/raynewelder{ - pixel_y = -5 - }, -/obj/item/weldingtool/electric/raynewelder{ - pixel_y = 6 - }, -/turf/open/space/basic, -/area/space/nearstation) "etz" = ( /obj/structure/window/spawner/directional/west, /obj/effect/turf_decal/siding/wood{ @@ -14166,10 +14130,6 @@ "ffH" = ( /turf/closed/wall, /area/station/hallway/primary/fore) -"ffP" = ( -/obj/structure/cable, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "ffU" = ( /obj/effect/turf_decal/siding/purple, /obj/machinery/camera/directional/south{ @@ -14309,6 +14269,10 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /turf/open/floor/iron, /area/station/construction/storage_wing) +"fhF" = ( +/obj/structure/cable, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "fhG" = ( /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4{ dir = 1 @@ -14733,17 +14697,6 @@ /obj/structure/table/wood, /turf/open/floor/carpet, /area/station/service/chapel/funeral) -"fmA" = ( -/obj/machinery/coffeemaker/impressa{ - pixel_y = 5 - }, -/obj/item/storage/box/coffeepack{ - pixel_x = 9; - pixel_y = -1 - }, -/obj/structure/table/wood, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "fmJ" = ( /obj/structure/rack, /obj/item/circuitboard/machine/telecomms/bus, @@ -14968,18 +14921,6 @@ "fru" = ( /turf/closed/wall, /area/station/cargo/drone_bay) -"frF" = ( -/obj/structure/closet/mini_fridge, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/reagent_containers/cup/soda_cans/sol_dry, -/obj/item/storage/cans/sixbeer, -/obj/machinery/light/directional/west, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "frH" = ( /obj/machinery/door/firedoor, /obj/machinery/door/airlock/security/glass{ @@ -15370,9 +15311,6 @@ /obj/machinery/atm/directional/north, /turf/open/floor/iron, /area/station/hallway/primary/starboard) -"fAx" = ( -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "fAI" = ( /obj/effect/spawner/random/structure/crate, /obj/effect/decal/cleanable/dirt, @@ -18992,13 +18930,6 @@ "gQQ" = ( /turf/closed/wall, /area/station/engineering/break_room) -"gQX" = ( -/obj/machinery/light/directional/east, -/obj/machinery/conveyor_switch/oneway{ - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "gRb" = ( /obj/effect/spawner/structure/window/reinforced, /turf/open/floor/plating, @@ -19232,6 +19163,17 @@ /obj/structure/sign/warning/electric_shock/directional/north, /turf/open/floor/iron, /area/station/hallway/primary/fore) +"gUA" = ( +/obj/item/radio/intercom/directional/south, +/obj/effect/spawner/random/entertainment/cigarette{ + pixel_y = -1 + }, +/obj/effect/spawner/random/entertainment/lighter{ + pixel_x = 7 + }, +/obj/structure/table/wood, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "gUP" = ( /obj/structure/chair{ dir = 1 @@ -21168,6 +21110,9 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/iron/dark, /area/station/medical/break_room) +"hyw" = ( +/turf/open/space/basic, +/area/shipbreak) "hyN" = ( /obj/structure/sign/warning/secure_area, /turf/closed/wall/r_wall, @@ -23100,14 +23045,6 @@ /obj/effect/landmark/start/hangover, /turf/open/floor/plating, /area/station/maintenance/fore) -"iid" = ( -/obj/machinery/conveyor{ - dir = 10; - id = "shitbreaker" - }, -/obj/structure/window/spawner/directional/south, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "iio" = ( /obj/effect/turf_decal/tile/purple/fourcorners, /obj/machinery/door/airlock/command{ @@ -23399,12 +23336,6 @@ /obj/effect/turf_decal/tile/neutral/fourcorners, /turf/open/floor/iron/dark, /area/station/security/brig) -"inF" = ( -/obj/structure/chair/comfy/teal{ - dir = 4 - }, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "inG" = ( /obj/machinery/light/small/directional/south, /obj/effect/decal/cleanable/dirt, @@ -25958,12 +25889,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/iron/white, /area/station/science/circuits) -"jbJ" = ( -/obj/machinery/conveyor{ - id = "shitbreaker" - }, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "jbR" = ( /obj/effect/turf_decal/siding/wood{ dir = 1 @@ -26259,15 +26184,6 @@ /obj/structure/window/reinforced/spawner/directional/west, /turf/open/floor/engine, /area/station/science/xenobiology) -"jgs" = ( -/obj/effect/turf_decal/tile/blue/anticorner/contrasted{ - dir = 4 - }, -/obj/structure/bed/dogbed/runtime, -/obj/item/toy/cattoy, -/mob/living/basic/pet/cat/runtime, -/turf/open/floor/iron/white, -/area/station/command/heads_quarters/cmo) "jgt" = ( /obj/machinery/atmospherics/components/binary/pump{ dir = 1; @@ -26567,12 +26483,6 @@ /obj/effect/turf_decal/tile/neutral/fourcorners, /turf/open/floor/iron/dark, /area/station/commons/fitness/recreation) -"jlM" = ( -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "jlU" = ( /turf/closed/wall/r_wall, /area/station/science/xenobiology) @@ -26775,12 +26685,6 @@ /obj/effect/landmark/event_spawn, /turf/open/floor/iron/freezer, /area/station/commons/toilet/restrooms) -"jpO" = ( -/obj/machinery/door/airlock/external, -/obj/effect/mapping_helpers/airlock/cyclelink_helper, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "jpQ" = ( /obj/machinery/door/window/right/directional/south{ dir = 1; @@ -27296,6 +27200,14 @@ }, /turf/open/floor/iron, /area/station/cargo/miningoffice) +"jwN" = ( +/obj/machinery/conveyor{ + dir = 4; + id = "shitbreaker" + }, +/obj/structure/window/spawner/directional/south, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "jwW" = ( /obj/machinery/door/firedoor, /obj/machinery/door/airlock/command{ @@ -29031,6 +28943,10 @@ }, /turf/open/floor/iron/dark, /area/station/security/evidence) +"kbe" = ( +/obj/machinery/computer/shipbreaker, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "kbo" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -29334,10 +29250,6 @@ }, /turf/open/space/basic, /area/space/nearstation) -"kiE" = ( -/obj/effect/spawner/random/structure/grille, -/turf/open/space/basic, -/area/space) "kiH" = ( /obj/structure/reagent_dispensers/watertank, /turf/open/floor/plating, @@ -30672,6 +30584,23 @@ }, /turf/open/floor/iron, /area/station/security/checkpoint/supply) +"kHc" = ( +/obj/structure/table, +/obj/item/folder/white, +/obj/item/toy/figure/rd{ + pixel_y = 10 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/head/rd, +/turf/open/floor/iron/white, +/area/station/command/heads_quarters/rd) "kHg" = ( /obj/structure/cable, /obj/machinery/atmospherics/components/unary/vent_pump/on/layer4{ @@ -31447,18 +31376,6 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron, /area/station/hallway/primary/aft) -"kVs" = ( -/obj/machinery/door/airlock/maintenance{ - name = "Storage Room" - }, -/obj/effect/mapping_helpers/airlock/abandoned, -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/obj/effect/mapping_helpers/airlock/unres, -/obj/effect/mapping_helpers/airlock/access/all/engineering/maintenance, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "kVJ" = ( /obj/machinery/newscaster/directional/west, /obj/machinery/light/directional/west, @@ -31595,12 +31512,6 @@ /obj/structure/cable, /turf/open/floor/iron, /area/station/hallway/primary/port) -"kXx" = ( -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "kXA" = ( /obj/machinery/space_heater, /obj/structure/sign/warning/vacuum/external/directional/north, @@ -31974,6 +31885,27 @@ /obj/structure/cable, /turf/open/floor/catwalk_floor/iron_dark, /area/station/maintenance/solars/starboard/fore) +"leP" = ( +/obj/structure/table/reinforced, +/obj/item/folder/yellow, +/obj/item/stamp/head/ce{ + pixel_y = 11 + }, +/obj/item/reagent_containers/pill/patch/aiuri, +/obj/effect/turf_decal/tile/neutral/half/contrasted, +/obj/item/stamp/head/ce{ + pixel_y = 11 + }, +/obj/item/stamp/denied{ + pixel_x = -9; + pixel_y = 11 + }, +/obj/item/stamp/granted{ + pixel_x = 9; + pixel_y = 11 + }, +/turf/open/floor/iron, +/area/station/command/heads_quarters/ce) "lfc" = ( /obj/machinery/newscaster/directional/north, /obj/effect/turf_decal/stripes/corner{ @@ -32053,6 +31985,25 @@ }, /turf/open/floor/iron/white, /area/station/security/execution/transfer) +"lgk" = ( +/obj/structure/table/glass, +/obj/item/paper_bin, +/obj/item/clipboard, +/obj/item/toy/figure/cmo, +/obj/structure/cable, +/obj/item/stamp/head/cmo{ + pixel_y = 12 + }, +/obj/item/stamp/denied{ + pixel_x = -8; + pixel_y = 12 + }, +/obj/item/stamp/granted{ + pixel_y = 12; + pixel_x = 8 + }, +/turf/open/floor/iron/white, +/area/station/command/heads_quarters/cmo) "lgl" = ( /obj/machinery/light/small/directional/south, /obj/effect/turf_decal/tile/blue{ @@ -32337,6 +32288,17 @@ }, /turf/open/floor/iron/solarpanel/airless, /area/station/solars/port/aft) +"llm" = ( +/obj/machinery/coffeemaker/impressa{ + pixel_y = 5 + }, +/obj/item/storage/box/coffeepack{ + pixel_x = 9; + pixel_y = -1 + }, +/obj/structure/table/wood, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "lln" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -32478,11 +32440,6 @@ "lnc" = ( /turf/closed/wall, /area/station/commons/dorms) -"lnd" = ( -/obj/machinery/portable_atmospherics/canister/oxygen, -/obj/structure/lattice/catwalk, -/turf/open/space/basic, -/area/space/nearstation) "lnv" = ( /obj/structure/cable, /obj/machinery/door/airlock/maintenance{ @@ -33210,6 +33167,10 @@ }, /turf/open/floor/iron/dark, /area/station/medical/break_room) +"lxF" = ( +/obj/machinery/light/directional/west, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "lxM" = ( /obj/machinery/door/airlock/maintenance, /obj/structure/cable, @@ -33262,23 +33223,6 @@ }, /turf/open/floor/iron, /area/station/hallway/secondary/command) -"lzB" = ( -/obj/structure/table/wood, -/obj/structure/window/reinforced/spawner/directional/south, -/obj/item/radio/intercom/directional/east, -/obj/item/folder/blue, -/obj/item/hand_tele, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/head/captain, -/turf/open/floor/wood, -/area/station/command/heads_quarters/captain/private) "lzJ" = ( /obj/effect/turf_decal/stripes/line{ dir = 1 @@ -34686,6 +34630,12 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/iron/dark, /area/station/medical/break_room) +"lYF" = ( +/obj/machinery/door/airlock/external, +/obj/effect/mapping_helpers/airlock/cyclelink_helper, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "lYG" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -36549,12 +36499,6 @@ /obj/structure/sign/poster/random/directional/north, /turf/open/floor/wood, /area/station/service/bar/backroom) -"mFD" = ( -/obj/machinery/door/airlock/engineering, -/obj/structure/cable, -/obj/structure/fans/tiny, -/turf/open/floor/plating, -/area/station/engineering/shipbreaker_hut) "mFQ" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer2{ dir = 8 @@ -37160,6 +37104,11 @@ dir = 1 }, /area/station/security/prison) +"mQv" = ( +/obj/effect/spawner/random/structure/grille, +/obj/effect/spawner/random/structure/grille, +/turf/open/space/basic, +/area/space/nearstation) "mRg" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, @@ -39496,6 +39445,12 @@ /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer2, /turf/open/floor/iron, /area/station/engineering/atmos/pumproom) +"nCW" = ( +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "nDk" = ( /obj/structure/table, /obj/item/storage/fancy/cigarettes{ @@ -39526,14 +39481,6 @@ }, /turf/open/floor/iron, /area/station/hallway/secondary/entry) -"nDR" = ( -/obj/machinery/conveyor{ - dir = 4; - id = "shitbreaker" - }, -/obj/structure/window/spawner/directional/south, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "nDS" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/effect/mapping_helpers/broken_floor, @@ -39548,14 +39495,6 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/plating, /area/station/maintenance/port/aft) -"nDW" = ( -/obj/machinery/door/airlock/external, -/obj/effect/mapping_helpers/airlock/cyclelink_helper{ - dir = 1 - }, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "nEb" = ( /obj/structure/table, /obj/item/clothing/mask/gas, @@ -39743,9 +39682,6 @@ /obj/effect/mapping_helpers/burnt_floor, /turf/open/floor/plating, /area/station/medical/abandoned) -"nIZ" = ( -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "nJn" = ( /obj/machinery/chem_dispenser{ layer = 2.7 @@ -40615,6 +40551,34 @@ /obj/structure/cable, /turf/open/floor/plating, /area/station/maintenance/starboard/aft) +"nZe" = ( +/obj/structure/table/wood, +/obj/item/device/walkman{ + pixel_y = 4; + pixel_x = -6 + }, +/obj/item/device/walkman{ + pixel_y = 4; + pixel_x = -6 + }, +/obj/item/device/walkman{ + pixel_y = 4; + pixel_x = -6 + }, +/obj/item/cassette_tape/blank{ + pixel_y = 3; + pixel_x = 5 + }, +/obj/item/cassette_tape/blank{ + pixel_y = 3; + pixel_x = 5 + }, +/obj/item/cassette_tape/blank{ + pixel_y = 3; + pixel_x = 5 + }, +/turf/open/floor/wood, +/area/station/service/library) "nZf" = ( /obj/effect/decal/cleanable/dirt, /turf/open/floor/circuit/green, @@ -40937,6 +40901,23 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron/white, /area/station/medical/office) +"odG" = ( +/obj/structure/table/wood, +/obj/structure/window/reinforced/spawner/directional/south, +/obj/item/radio/intercom/directional/east, +/obj/item/folder/blue, +/obj/item/hand_tele, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/head/captain, +/turf/open/floor/wood, +/area/station/command/heads_quarters/captain/private) "odI" = ( /obj/machinery/door/firedoor, /obj/machinery/door/airlock{ @@ -41222,6 +41203,10 @@ /obj/effect/mapping_helpers/broken_floor, /turf/open/floor/wood, /area/station/maintenance/port/aft) +"ojh" = ( +/obj/effect/spawner/random/structure/grille, +/turf/open/space/basic, +/area/space) "ojo" = ( /obj/effect/turf_decal/siding/wood{ dir = 6 @@ -41865,6 +41850,46 @@ /obj/machinery/light/directional/east, /turf/open/floor/iron, /area/station/hallway/secondary/entry) +"ouI" = ( +/obj/structure/table/wood, +/obj/machinery/button/ticket_machine{ + pixel_x = 32 + }, +/obj/item/paper_bin/carbon{ + pixel_x = -2; + pixel_y = 4 + }, +/obj/item/stamp/granted{ + pixel_y = 9; + pixel_x = -4 + }, +/obj/item/stamp/head/hop{ + pixel_x = -4; + pixel_y = 4 + }, +/obj/machinery/light_switch/directional/south{ + pixel_x = 6; + pixel_y = -34 + }, +/obj/machinery/button/door/directional/south{ + id = "hop"; + name = "Privacy Shutters Control"; + pixel_x = -6; + req_access = list("hop") + }, +/obj/machinery/button/door/directional/south{ + id = "hopqueue"; + name = "Queue Shutters Control"; + pixel_x = -6; + pixel_y = -34; + req_access = list("hop") + }, +/obj/item/stamp/denied{ + pixel_x = -4; + pixel_y = -1 + }, +/turf/open/floor/wood, +/area/station/command/heads_quarters/hop) "ouM" = ( /obj/structure/sign/painting/library{ pixel_y = -32 @@ -42275,6 +42300,14 @@ /obj/structure/cable, /turf/open/floor/iron/kitchen_coldroom/freezerfloor, /area/station/medical/coldroom) +"oBy" = ( +/obj/machinery/conveyor{ + dir = 10; + id = "shitbreaker" + }, +/obj/structure/window/spawner/directional/south, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "oBz" = ( /turf/closed/wall, /area/station/security/checkpoint/science) @@ -43542,6 +43575,12 @@ /obj/effect/decal/cleanable/blood/old, /turf/open/floor/iron/showroomfloor, /area/station/maintenance/starboard/lesser) +"oZt" = ( +/obj/machinery/conveyor{ + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "oZG" = ( /obj/effect/turf_decal/tile/neutral{ dir = 4 @@ -43943,10 +43982,6 @@ /obj/machinery/door/firedoor, /turf/open/floor/iron/white/diagonal, /area/station/medical/pathology) -"phw" = ( -/obj/machinery/light/directional/west, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "phz" = ( /obj/machinery/navbeacon{ codes_txt = "patrol;next_patrol=7-Command-Starboard"; @@ -45770,6 +45805,9 @@ }, /turf/open/floor/iron/dark/textured, /area/station/medical/pathology) +"pQd" = ( +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "pQf" = ( /turf/open/floor/engine, /area/station/science/explab) @@ -46155,6 +46193,18 @@ /obj/structure/cable, /turf/open/floor/iron, /area/station/hallway/primary/central) +"pWC" = ( +/obj/machinery/door/airlock/maintenance{ + name = "Storage Room" + }, +/obj/effect/mapping_helpers/airlock/abandoned, +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/obj/effect/mapping_helpers/airlock/unres, +/obj/effect/mapping_helpers/airlock/access/all/engineering/maintenance, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "pWD" = ( /obj/effect/turf_decal/tile/blue/anticorner/contrasted{ dir = 1 @@ -46275,6 +46325,14 @@ }, /turf/open/floor/iron, /area/station/hallway/primary/port) +"pYp" = ( +/obj/machinery/conveyor{ + dir = 4; + id = "shitbreaker" + }, +/obj/machinery/shipbreaker, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "pYw" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer2{ dir = 4 @@ -47476,9 +47534,6 @@ }, /turf/open/floor/iron/dark, /area/station/command/bridge) -"qsN" = ( -/turf/closed/wall/r_wall, -/area/station/engineering/shipbreaker_hut) "qsQ" = ( /obj/machinery/light/directional/north, /obj/machinery/computer/security/wooden_tv, @@ -47519,17 +47574,6 @@ }, /turf/open/floor/iron, /area/station/hallway/primary/port) -"qtd" = ( -/obj/item/radio/intercom/directional/south, -/obj/effect/spawner/random/entertainment/cigarette{ - pixel_y = -1 - }, -/obj/effect/spawner/random/entertainment/lighter{ - pixel_x = 7 - }, -/obj/structure/table/wood, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "qtf" = ( /obj/structure/chair/office{ dir = 8 @@ -47822,6 +47866,29 @@ "qyC" = ( /turf/closed/wall, /area/station/engineering/atmos/pumproom) +"qyD" = ( +/obj/structure/table/wood, +/obj/effect/turf_decal/siding/wood{ + dir = 4 + }, +/obj/item/folder/red{ + pixel_x = -7 + }, +/obj/item/folder/red{ + pixel_x = -7; + pixel_y = 6 + }, +/obj/item/stamp/denied{ + pixel_y = 5; + pixel_x = -4 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/head/hos, +/turf/open/floor/wood, +/area/station/command/heads_quarters/hos) "qyI" = ( /obj/effect/turf_decal/tile/neutral{ dir = 1 @@ -49573,6 +49640,11 @@ }, /turf/open/floor/iron, /area/station/engineering/atmos) +"rdQ" = ( +/obj/machinery/portable_atmospherics/canister/oxygen, +/obj/structure/lattice/catwalk, +/turf/open/space/basic, +/area/space/nearstation) "rdT" = ( /obj/structure/toilet{ pixel_y = 8 @@ -49877,6 +49949,11 @@ /obj/structure/cable, /turf/open/floor/iron, /area/station/hallway/primary/aft) +"rku" = ( +/obj/structure/chair/office/light, +/obj/structure/cable, +/turf/open/floor/iron/white, +/area/station/command/heads_quarters/cmo) "rkx" = ( /obj/machinery/vending/cigarette, /obj/effect/turf_decal/tile/bar/opposingcorners, @@ -51296,34 +51373,6 @@ }, /turf/open/floor/iron, /area/station/engineering/atmos) -"rIa" = ( -/obj/structure/table/wood, -/obj/item/device/walkman{ - pixel_y = 4; - pixel_x = -6 - }, -/obj/item/device/walkman{ - pixel_y = 4; - pixel_x = -6 - }, -/obj/item/device/walkman{ - pixel_y = 4; - pixel_x = -6 - }, -/obj/item/device/cassette_tape/blank{ - pixel_y = 3; - pixel_x = 5 - }, -/obj/item/device/cassette_tape/blank{ - pixel_y = 3; - pixel_x = 5 - }, -/obj/item/device/cassette_tape/blank{ - pixel_y = 3; - pixel_x = 5 - }, -/turf/open/floor/wood, -/area/station/service/library) "rIh" = ( /obj/machinery/light/directional/east, /obj/effect/turf_decal/tile/neutral{ @@ -53178,10 +53227,6 @@ /obj/item/training_toolbox, /turf/open/floor/iron, /area/station/commons/fitness/recreation) -"soH" = ( -/obj/effect/spawner/structure/window, -/turf/open/floor/plating, -/area/station/engineering/shipbreaker_hut) "soW" = ( /obj/structure/rack, /obj/effect/spawner/random/techstorage/security_all, @@ -53493,10 +53538,6 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/stone, /area/station/smithing) -"suC" = ( -/obj/machinery/computer/security/telescreen/entertainment/directional/east, -/turf/open/floor/iron, -/area/station/engineering/shipbreaker_hut) "suD" = ( /obj/effect/spawner/structure/window/reinforced, /obj/structure/cable, @@ -53795,10 +53836,6 @@ }, /turf/open/floor/plating, /area/station/security/warden) -"szm" = ( -/obj/machinery/computer/shipbreaker, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "szp" = ( /turf/closed/wall, /area/station/commons/fitness/recreation) @@ -54994,14 +55031,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/iron/white, /area/station/science/ordnance/storage) -"sUY" = ( -/obj/machinery/conveyor{ - dir = 8; - id = "shitbreaker" - }, -/obj/structure/window/spawner/directional/south, -/turf/open/floor/plating/airless, -/area/station/engineering/shipbreaker_hut) "sVc" = ( /obj/effect/decal/cleanable/cobweb, /obj/machinery/field/generator, @@ -55281,13 +55310,6 @@ /obj/effect/turf_decal/delivery, /turf/open/floor/iron, /area/station/science/xenobiology) -"sZU" = ( -/obj/effect/turf_decal/stripes/line{ - dir = 1 - }, -/obj/structure/cable, -/turf/open/floor/plating, -/area/station/maintenance/starboard/fore) "tak" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -55546,12 +55568,6 @@ }, /turf/open/floor/iron, /area/station/hallway/primary/central) -"ter" = ( -/obj/item/book/manual/nuclear, -/turf/open/floor/plating/foam{ - initial_gas_mix = "TEMP=2.7" - }, -/area/space) "tew" = ( /obj/machinery/door/firedoor, /obj/machinery/door/airlock/security/glass{ @@ -56394,46 +56410,6 @@ /obj/item/knife/kitchen, /turf/open/floor/iron/white, /area/station/science/cytology) -"tsT" = ( -/obj/structure/table/wood, -/obj/machinery/button/ticket_machine{ - pixel_x = 32 - }, -/obj/item/paper_bin/carbon{ - pixel_x = -2; - pixel_y = 4 - }, -/obj/item/stamp/granted{ - pixel_y = 9; - pixel_x = -4 - }, -/obj/item/stamp/head/hop{ - pixel_x = -4; - pixel_y = 4 - }, -/obj/machinery/light_switch/directional/south{ - pixel_x = 6; - pixel_y = -34 - }, -/obj/machinery/button/door/directional/south{ - id = "hop"; - name = "Privacy Shutters Control"; - pixel_x = -6; - req_access = list("hop") - }, -/obj/machinery/button/door/directional/south{ - id = "hopqueue"; - name = "Queue Shutters Control"; - pixel_x = -6; - pixel_y = -34; - req_access = list("hop") - }, -/obj/item/stamp/denied{ - pixel_x = -4; - pixel_y = -1 - }, -/turf/open/floor/wood, -/area/station/command/heads_quarters/hop) "tsZ" = ( /obj/machinery/atmospherics/pipe/smart/simple/orange/visible, /obj/structure/lattice/catwalk, @@ -56538,6 +56514,9 @@ }, /turf/open/floor/iron/white, /area/station/medical/treatment_center) +"tvh" = ( +/turf/closed/wall/r_wall, +/area/station/engineering/shipbreaker_hut) "tvn" = ( /obj/structure/bodycontainer/morgue, /obj/effect/turf_decal/trimline/blue/filled/line{ @@ -56915,6 +56894,12 @@ }, /turf/open/floor/iron, /area/station/security/brig) +"tDD" = ( +/obj/machinery/door/airlock/engineering, +/obj/structure/cable, +/obj/structure/fans/tiny, +/turf/open/floor/plating, +/area/station/engineering/shipbreaker_hut) "tDN" = ( /obj/structure/chair{ dir = 8 @@ -57595,6 +57580,9 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/iron/dark, /area/station/ai_monitored/aisat/exterior) +"tRq" = ( +/turf/closed/wall, +/area/station/engineering/shipbreaker_hut) "tRt" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -57696,6 +57684,12 @@ /obj/effect/turf_decal/delivery, /turf/open/floor/iron, /area/station/commons/locker) +"tTW" = ( +/obj/item/book/manual/nuclear, +/turf/open/floor/plating/foam{ + initial_gas_mix = "TEMP=2.7" + }, +/area/space) "tUc" = ( /obj/item/radio/intercom/directional/east, /obj/structure/table, @@ -58894,23 +58888,6 @@ /obj/structure/cable, /turf/open/floor/iron, /area/station/security/brig) -"uoO" = ( -/obj/structure/table, -/obj/item/folder/white, -/obj/item/toy/figure/rd{ - pixel_y = 10 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/head/rd, -/turf/open/floor/iron/white, -/area/station/command/heads_quarters/rd) "upe" = ( /obj/machinery/camera/directional/east{ c_tag = "Interrogation room"; @@ -59529,11 +59506,6 @@ }, /turf/open/space/basic, /area/space) -"uzu" = ( -/obj/effect/spawner/random/structure/grille, -/obj/effect/spawner/random/structure/grille, -/turf/open/space/basic, -/area/space/nearstation) "uzw" = ( /obj/effect/turf_decal/tile/red, /obj/effect/turf_decal/tile/red{ @@ -60112,6 +60084,13 @@ /obj/structure/cable, /turf/open/floor/iron/dark, /area/station/engineering/atmospherics_engine) +"uIf" = ( +/obj/effect/turf_decal/stripes/line, +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "uIi" = ( /obj/structure/cable, /obj/machinery/power/solar_control{ @@ -60422,27 +60401,6 @@ }, /turf/open/floor/iron, /area/station/engineering/atmos) -"uOy" = ( -/obj/structure/table/reinforced, -/obj/item/folder/yellow, -/obj/item/stamp/head/ce{ - pixel_y = 11 - }, -/obj/item/reagent_containers/pill/patch/aiuri, -/obj/effect/turf_decal/tile/neutral/half/contrasted, -/obj/item/stamp/head/ce{ - pixel_y = 11 - }, -/obj/item/stamp/denied{ - pixel_x = -9; - pixel_y = 11 - }, -/obj/item/stamp/granted{ - pixel_x = 9; - pixel_y = 11 - }, -/turf/open/floor/iron, -/area/station/command/heads_quarters/ce) "uOH" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -60737,9 +60695,6 @@ /obj/structure/cable/layer3, /turf/open/floor/circuit, /area/station/ai_monitored/turret_protected/ai) -"uVa" = ( -/turf/closed/wall, -/area/station/engineering/shipbreaker_hut) "uVd" = ( /obj/structure/chair{ dir = 8 @@ -61498,6 +61453,13 @@ /obj/structure/fireaxecabinet/mechremoval/directional/east, /turf/open/floor/iron, /area/station/science/robotics/lab) +"vkY" = ( +/obj/machinery/light/directional/east, +/obj/machinery/conveyor_switch/oneway{ + id = "shitbreaker" + }, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "vlh" = ( /obj/structure/rack, /obj/effect/spawner/random/techstorage/rnd_secure_all, @@ -62115,6 +62077,12 @@ /mob/living/basic/slime, /turf/open/floor/engine, /area/station/science/xenobiology) +"vxA" = ( +/obj/structure/cable, +/obj/machinery/power/apc/auto_name/directional/north, +/obj/effect/mapping_helpers/apc/full_charge, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "vxC" = ( /obj/effect/turf_decal/trimline/red/filled/line{ dir = 10 @@ -62156,6 +62124,14 @@ /obj/structure/sign/warning/secure_area, /turf/closed/wall/r_wall, /area/station/command/corporate_showroom) +"vyq" = ( +/obj/machinery/door/airlock/external, +/obj/effect/mapping_helpers/airlock/cyclelink_helper{ + dir = 1 + }, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "vyM" = ( /obj/machinery/holopad, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -62901,6 +62877,18 @@ /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /turf/open/floor/plating, /area/station/maintenance/port/fore) +"vMl" = ( +/obj/structure/closet/mini_fridge, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/reagent_containers/cup/soda_cans/sol_dry, +/obj/item/storage/cans/sixbeer, +/obj/machinery/light/directional/west, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "vME" = ( /obj/structure/chair/stool/directional/north, /obj/structure/cable, @@ -66010,6 +65998,12 @@ }, /turf/open/floor/plating, /area/station/maintenance/port/fore) +"wQr" = ( +/obj/structure/easel, +/obj/effect/mapping_helpers/broken_floor, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "wQI" = ( /obj/machinery/door/poddoor/shutters/preopen{ dir = 8; @@ -66470,6 +66464,14 @@ /obj/machinery/duct, /turf/open/floor/iron/cafeteria, /area/station/service/kitchen) +"wXo" = ( +/obj/machinery/conveyor{ + dir = 8; + id = "shitbreaker" + }, +/obj/structure/window/spawner/directional/south, +/turf/open/floor/plating/airless, +/area/station/engineering/shipbreaker_hut) "wXr" = ( /obj/machinery/disposal/bin, /obj/machinery/light/directional/south, @@ -66615,6 +66617,10 @@ /obj/effect/spawner/random/structure/closet_maintenance, /turf/open/floor/plating, /area/station/maintenance/aft/greater) +"xak" = ( +/obj/structure/cable, +/turf/open/floor/iron, +/area/station/engineering/shipbreaker_hut) "xar" = ( /obj/effect/turf_decal/trimline/blue/filled/line{ dir = 8 @@ -66683,29 +66689,6 @@ }, /turf/open/floor/iron, /area/station/hallway/primary/port) -"xbE" = ( -/obj/structure/table/wood, -/obj/effect/turf_decal/siding/wood{ - dir = 4 - }, -/obj/item/folder/red{ - pixel_x = -7 - }, -/obj/item/folder/red{ - pixel_x = -7; - pixel_y = 6 - }, -/obj/item/stamp/denied{ - pixel_y = 5; - pixel_x = -4 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/head/hos, -/turf/open/floor/wood, -/area/station/command/heads_quarters/hos) "xbT" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -66813,6 +66796,12 @@ "xdJ" = ( /turf/closed/wall, /area/station/medical/surgery/aft) +"xdM" = ( +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/obj/structure/cable, +/turf/open/floor/plating, +/area/station/maintenance/starboard/fore) "xdQ" = ( /obj/structure/sign/warning/hot_temp/directional/south, /turf/open/floor/plating, @@ -68071,6 +68060,17 @@ /obj/machinery/duct, /turf/open/floor/iron/cafeteria, /area/station/service/kitchen) +"xzl" = ( +/obj/structure/lattice/catwalk, +/obj/structure/rack, +/obj/item/weldingtool/electric/raynewelder{ + pixel_y = -5 + }, +/obj/item/weldingtool/electric/raynewelder{ + pixel_y = 6 + }, +/turf/open/space/basic, +/area/space/nearstation) "xzm" = ( /obj/effect/mapping_helpers/broken_floor, /turf/open/floor/plating, @@ -89324,7 +89324,7 @@ nxF sVY cyk qzS -rIa +nZe ahD wki jIY @@ -94237,8 +94237,8 @@ jhk cOR vgZ ijZ -dso -edo +rku +lgk pXM iNc bqX @@ -94492,7 +94492,7 @@ gQG tFr tar cOR -jgs +bBQ uyw pcM cNk @@ -95233,7 +95233,7 @@ pJR lJn psy htG -tsT +ouI pJR uwC ndS @@ -99036,7 +99036,7 @@ aaa aaa aaa aaa -ter +tTW iTZ ahj ahj @@ -101142,7 +101142,7 @@ uGj tyY iDh csS -lzB +odG gpS xuH rVC @@ -102638,7 +102638,7 @@ aaa rrg iFF gfk -xbE +qyD mBf sjM sPj @@ -104260,7 +104260,7 @@ yeI gIM tAg tcx -uoO +kHc vYE eDf nfs @@ -104401,10 +104401,10 @@ aaa aaa aaa aaa -kiE -kiE -kiE -kiE +ojh +ojh +ojh +ojh aaa aaa aaa @@ -104416,10 +104416,10 @@ aaa aaa aaa aaa -kiE -kiE -kiE -kiE +ojh +ojh +ojh +ojh aaa aaa aaa @@ -104657,7 +104657,7 @@ aaa aaa aaa aaa -kiE +ojh lMJ lMJ lMJ @@ -104914,33 +104914,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -105171,33 +105171,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -105428,33 +105428,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -105685,33 +105685,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -105944,31 +105944,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -106201,31 +106201,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -106458,31 +106458,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -106715,31 +106715,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -106972,31 +106972,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -107229,31 +107229,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -107486,31 +107486,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -107743,31 +107743,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -108000,31 +108000,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -108257,31 +108257,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -108514,31 +108514,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -108771,31 +108771,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -109028,31 +109028,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -109285,31 +109285,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -109542,31 +109542,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -109612,7 +109612,7 @@ acs uXd qJd nLz -uOy +leP rSi pCt aRS @@ -109799,31 +109799,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -110056,31 +110056,31 @@ aaa aaa aaa lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -110311,33 +110311,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -110568,33 +110568,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -110825,33 +110825,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -111082,33 +111082,33 @@ aaa aaa aaa aaa -kiE +ojh lMJ -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU -ciU +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw +hyw lMJ aaa aaa @@ -111125,12 +111125,12 @@ dxq oPc cyS izd -jlM -jlM -bJC -kXx -aIC -kVs +xdM +xdM +blu +nCW +uIf +pWC jUu kCN lCN @@ -111339,7 +111339,7 @@ aaa aaa aaa aaa -kiE +ojh lMJ lMJ lMJ @@ -111382,7 +111382,7 @@ qXB qXB qXB qXB -czs +wQr wrn wrn tjR @@ -111597,19 +111597,19 @@ aaa aaa aaa aaa -kiE -kiE -kiE -kiE -kiE +ojh +ojh +ojh +ojh +ojh aaa aaa aaa aaa aaa aaa -kiE -kiE +ojh +ojh aox aox aox @@ -111635,10 +111635,10 @@ dJN dJN dJN dJN -jpO -sZU -nDW -sZU +lYF +cWO +vyq +cWO jcy qIB rCn @@ -111866,7 +111866,7 @@ aaa aaa aaa aaa -kiE +ojh aaa aaa aaa @@ -111879,13 +111879,13 @@ aaa aaa aaa lMJ -ffP +fhF lMJ lMJ lMJ cpH -ety -lnd +xzl +rdQ aox dJN aox @@ -112123,8 +112123,8 @@ aaa aaa aaa aaa -kiE -kiE +ojh +ojh aaa aaa aaa @@ -112136,17 +112136,17 @@ aaa aaa aaa lMJ -ffP +fhF lMJ aaa aUn lMJ aox -uVa -uVa -mFD -uVa -uVa +tRq +tRq +tDD +tRq +tRq aaa aox nqL @@ -112381,8 +112381,8 @@ aaa aaa aaa aaa -kiE -kiE +ojh +ojh aaa aaa aaa @@ -112391,19 +112391,19 @@ aaa aaa aaa aaa -qsN -szm -ffP -fAx +tvh +kbe +fhF +pQd aox -uzu +mQv lMJ aaa -soH -phw -dtN -frF -soH +arb +lxF +xak +vMl +arb aaa aox nqL @@ -112639,28 +112639,28 @@ aaa aaa aaa aaa -kiE -kiE -kiE -kiE +ojh +ojh +ojh +ojh aaa aaa aaa aaa aaa -qsN -bwP -ffP -fAx +tvh +vxA +fhF +pQd aox aUn lMJ aaa -soH -inF -nIZ -fmA -soH +arb +dzk +atX +llm +arb aaa aox nqL @@ -112899,25 +112899,25 @@ aaa aaa aaa aaa -kiE +ojh aaa aaa aaa aaa aaa -qsN -nDR -gQX -fAx +tvh +jwN +vkY +pQd aox aox cpH aaa -uVa -suC -nIZ -qtd -uVa +tRq +bjC +atX +gUA +tRq aaa aox nqL @@ -113156,25 +113156,25 @@ aaa aaa aaa aaa -kiE -kiE -kiE -kiE -kiE +ojh +ojh +ojh +ojh +ojh dPw -qsN -aDq -qsN -sUY +tvh +pYp +tvh +wXo aox aox lMJ aaa -uVa -uVa -uVa -soH -uVa +tRq +tRq +tRq +arb +tRq aaa aox nqL @@ -113419,12 +113419,12 @@ aaa aaa aWl aaa -uVa -erv -jbJ -iid +tRq +bKu +oZt +oBy aox -kiE +ojh lMJ lMJ lMJ @@ -113676,12 +113676,12 @@ aaa aaa rrt aaa -uVa -uVa -uVa -uVa +tRq +tRq +tRq +tRq aox -kiE +ojh lMJ aaa aaa @@ -113938,7 +113938,7 @@ aaa aaa aaa aaa -kiE +ojh cpH aaa aaa diff --git a/_maps/map_files/Voidraptor/VoidRaptor.dmm b/_maps/map_files/Voidraptor/VoidRaptor.dmm index d1edfa49ee0c..5a881020867d 100644 --- a/_maps/map_files/Voidraptor/VoidRaptor.dmm +++ b/_maps/map_files/Voidraptor/VoidRaptor.dmm @@ -1788,6 +1788,29 @@ }, /turf/open/floor/iron/dark/textured_edge, /area/station/hallway/primary/fore) +"azw" = ( +/obj/item/folder/blue{ + pixel_x = 3; + pixel_y = 3 + }, +/obj/item/folder/white{ + pixel_x = -4; + pixel_y = 3 + }, +/obj/structure/table/reinforced/rglass, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/head/cmo{ + pixel_y = 3 + }, +/turf/open/floor/carpet/blue, +/area/station/command/heads_quarters/cmo) "azx" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, @@ -10005,22 +10028,6 @@ /obj/structure/sign/warning/secure_area, /turf/closed/wall/r_wall, /area/station/maintenance/aft/greater) -"cYI" = ( -/obj/structure/table/wood, -/obj/item/radio/intercom/directional/east, -/obj/machinery/light/warm/directional/east, -/obj/effect/turf_decal/siding/thinplating/dark{ - dir = 4 - }, -/obj/item/radio/radio_mic{ - pixel_y = 7 - }, -/obj/item/device/cassette_tape/friday{ - pixel_y = -6; - pixel_x = -8 - }, -/turf/open/floor/cult, -/area/station/service/library) "cYN" = ( /obj/structure/chair/sofa/corp/right{ dir = 8; @@ -11893,11 +11900,6 @@ /obj/effect/turf_decal/bot_red, /turf/open/floor/vault, /area/station/ai_monitored/turret_protected/ai_upload) -"dzp" = ( -/obj/structure/window/spawner/directional/south, -/mob/living/basic/pet/cat/cak, -/turf/open/floor/iron/textured_large, -/area/station/maintenance/starboard/greater) "dzx" = ( /obj/effect/turf_decal/siding/wood{ dir = 4 @@ -12562,16 +12564,6 @@ /obj/machinery/light/small/blacklight/directional/north, /turf/open/floor/iron/textured_edge, /area/station/engineering/gravity_generator) -"dHS" = ( -/obj/machinery/power/apc/auto_name/directional/west, -/obj/structure/cable, -/obj/structure/bed/dogbed{ - anchored = 1; - name = "Jerry's bed" - }, -/mob/living/basic/pet/cat/jerry, -/turf/open/floor/wood, -/area/station/security/prison/garden) "dIf" = ( /obj/machinery/modular_computer/preset/civilian{ dir = 4 @@ -30086,28 +30078,6 @@ /obj/structure/disposalpipe/segment, /turf/open/floor/catwalk_floor/iron_smooth, /area/station/maintenance/aft/upper) -"iCg" = ( -/obj/structure/table/wood, -/obj/item/stamp/denied{ - pixel_x = -7; - pixel_y = 9 - }, -/obj/item/stamp{ - pixel_x = -7; - pixel_y = 2 - }, -/obj/item/folder/red{ - pixel_x = 11; - pixel_y = 4 - }, -/obj/item/folder/blue{ - pixel_x = 4; - pixel_y = 4 - }, -/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, -/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, -/turf/open/floor/carpet/green, -/area/station/command/heads_quarters/nt_rep) "iCx" = ( /obj/structure/chair/plastic{ dir = 4 @@ -30811,6 +30781,28 @@ /obj/machinery/camera/directional/north, /turf/open/floor/iron/dark/textured_large, /area/station/engineering/power_room) +"iNB" = ( +/obj/structure/table/wood, +/obj/item/stamp/denied{ + pixel_x = -7; + pixel_y = 9 + }, +/obj/item/stamp{ + pixel_x = -7; + pixel_y = 2 + }, +/obj/item/folder/red{ + pixel_x = 11; + pixel_y = 4 + }, +/obj/item/folder/blue{ + pixel_x = 4; + pixel_y = 4 + }, +/obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, +/obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, +/turf/open/floor/carpet/green, +/area/station/command/heads_quarters/nt_rep) "iNL" = ( /obj/structure/chair/comfy{ color = "#596479" @@ -36706,6 +36698,19 @@ /obj/structure/cable, /turf/open/floor/iron/dark/textured_large, /area/station/security/execution/transfer) +"ktU" = ( +/obj/structure/bed/dogbed/runtime, +/mob/living/basic/pet/cat/runtime{ + icon_dead = "original_dead"; + icon_living = "original"; + icon_state = "original" + }, +/obj/item/toy/cattoy, +/obj/machinery/digital_clock/directional/north{ + pixel_y = 37 + }, +/turf/open/floor/carpet/blue, +/area/station/command/heads_quarters/cmo) "kub" = ( /obj/machinery/conveyor{ dir = 8; @@ -39000,29 +39005,6 @@ /obj/machinery/duct, /turf/open/floor/catwalk_floor/iron_smooth, /area/station/maintenance/department/engine/atmos) -"kXu" = ( -/obj/item/folder/blue{ - pixel_x = 3; - pixel_y = 3 - }, -/obj/item/folder/white{ - pixel_x = -4; - pixel_y = 3 - }, -/obj/structure/table/reinforced/rglass, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/head/cmo{ - pixel_y = 3 - }, -/turf/open/floor/carpet/blue, -/area/station/command/heads_quarters/cmo) "kXw" = ( /obj/machinery/atmospherics/pipe/smart/manifold4w/scrubbers/hidden/layer2, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -39674,6 +39656,29 @@ /obj/item/radio/intercom/directional/north, /turf/open/floor/carpet/executive, /area/station/command/heads_quarters/hop) +"lgG" = ( +/obj/structure/table/reinforced, +/obj/item/folder/yellow{ + pixel_x = -2; + pixel_y = 3 + }, +/obj/item/computer_disk/engineering{ + pixel_x = 13; + pixel_y = 2 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/head/ce{ + pixel_y = 3 + }, +/turf/open/floor/carpet/orange, +/area/station/command/heads_quarters/ce) "lgX" = ( /obj/structure/cable, /obj/machinery/atmospherics/pipe/smart/manifold4w/supply/hidden/layer4, @@ -44507,25 +44512,6 @@ }, /turf/open/floor/iron/textured, /area/space/nearstation) -"mAr" = ( -/obj/structure/table/reinforced/rglass, -/obj/structure/cable, -/obj/item/folder/white{ - pixel_y = 4 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/head/rd{ - pixel_y = 4 - }, -/turf/open/floor/carpet/purple, -/area/station/command/heads_quarters/rd) "mAs" = ( /obj/effect/mapping_helpers/airlock/cyclelink_helper{ dir = 8 @@ -47321,6 +47307,22 @@ }, /turf/open/floor/iron/white/textured_edge, /area/station/medical/medbay/central) +"nmA" = ( +/obj/structure/table/wood, +/obj/item/radio/intercom/directional/east, +/obj/machinery/light/warm/directional/east, +/obj/effect/turf_decal/siding/thinplating/dark{ + dir = 4 + }, +/obj/item/radio/radio_mic{ + pixel_y = 7 + }, +/obj/item/cassette_tape/friday{ + pixel_y = -6; + pixel_x = -8 + }, +/turf/open/floor/cult, +/area/station/service/library) "nmB" = ( /obj/effect/turf_decal/trimline/green/filled/corner{ dir = 4 @@ -71291,19 +71293,6 @@ }, /turf/open/floor/iron/textured, /area/station/engineering/atmos) -"tLD" = ( -/obj/structure/bed/dogbed/runtime, -/mob/living/basic/pet/cat/runtime{ - icon_dead = "original_dead"; - icon_living = "original"; - icon_state = "original" - }, -/obj/item/toy/cattoy, -/obj/machinery/digital_clock/directional/north{ - pixel_y = 37 - }, -/turf/open/floor/carpet/blue, -/area/station/command/heads_quarters/cmo) "tLN" = ( /obj/effect/turf_decal/trimline/purple/filled/line{ dir = 4 @@ -71977,29 +71966,6 @@ }, /turf/open/space/basic, /area/space/nearstation) -"tXP" = ( -/obj/structure/table/reinforced, -/obj/item/folder/yellow{ - pixel_x = -2; - pixel_y = 3 - }, -/obj/item/computer_disk/engineering{ - pixel_x = 13; - pixel_y = 2 - }, -/obj/item/stamp/denied{ - pixel_x = -5; - pixel_y = 4 - }, -/obj/item/stamp/granted{ - pixel_y = 4; - pixel_x = 5 - }, -/obj/item/stamp/head/ce{ - pixel_y = 3 - }, -/turf/open/floor/carpet/orange, -/area/station/command/heads_quarters/ce) "tYp" = ( /obj/machinery/chem_mass_spec, /obj/effect/turf_decal/trimline/yellow/filled/line, @@ -76143,6 +76109,16 @@ /obj/item/target/syndicate, /turf/open/floor/engine, /area/station/security/range) +"vdv" = ( +/obj/machinery/power/apc/auto_name/directional/west, +/obj/structure/cable, +/obj/structure/bed/dogbed{ + anchored = 1; + name = "Jerry's bed" + }, +/mob/living/basic/pet/cat/jerry, +/turf/open/floor/wood, +/area/station/security/prison/garden) "vdw" = ( /obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer2{ dir = 1 @@ -76626,6 +76602,25 @@ /obj/machinery/newscaster/directional/north, /turf/open/floor/iron/freezer, /area/station/medical/surgery) +"vkZ" = ( +/obj/structure/table/reinforced/rglass, +/obj/structure/cable, +/obj/item/folder/white{ + pixel_y = 4 + }, +/obj/item/stamp/granted{ + pixel_y = 4; + pixel_x = 5 + }, +/obj/item/stamp/denied{ + pixel_x = -5; + pixel_y = 4 + }, +/obj/item/stamp/head/rd{ + pixel_y = 4 + }, +/turf/open/floor/carpet/purple, +/area/station/command/heads_quarters/rd) "vlh" = ( /turf/closed/wall/r_wall, /area/station/maintenance/starboard/aft) @@ -83161,6 +83156,11 @@ /obj/effect/landmark/navigate_destination/disposals, /turf/open/floor/catwalk_floor/iron_smooth, /area/station/maintenance/disposal) +"xer" = ( +/obj/structure/window/spawner/directional/south, +/mob/living/basic/pet/cat/cak, +/turf/open/floor/iron/textured_large, +/area/station/maintenance/starboard/greater) "xfa" = ( /obj/machinery/atmospherics/components/unary/thermomachine/freezer{ dir = 4 @@ -111272,7 +111272,7 @@ mCM fsR kCQ cdo -tLD +ktU bKK oQw lYd @@ -111532,7 +111532,7 @@ xCP sgB dTG oQw -kXu +azw bTK lAB uLt @@ -116078,7 +116078,7 @@ lKw ted uHB rMc -mAr +vkZ sor bFO sma @@ -123509,7 +123509,7 @@ baK fgd pIk wMB -iCg +iNB uTz iVF xlE @@ -125117,7 +125117,7 @@ jzQ nQl fLp dWg -cYI +nmA vZM uuO rCr @@ -125455,7 +125455,7 @@ nku rHN mWT qHi -tXP +lgG oEE dhx jDY @@ -126386,7 +126386,7 @@ aMk pAD cuF iNV -dzp +xer beq pMG vLe @@ -132778,7 +132778,7 @@ ttw ttw arU tUq -dHS +vdv eTa bpy agC diff --git a/code/__DEFINES/subsystems.dm b/code/__DEFINES/subsystems.dm index 78d1283bcc46..3692aa4d4b9a 100644 --- a/code/__DEFINES/subsystems.dm +++ b/code/__DEFINES/subsystems.dm @@ -164,6 +164,7 @@ #define INIT_ORDER_OUTPUTS 35 #define INIT_ORDER_RESTAURANT 34 #define INIT_ORDER_POLLUTION 32 +#define INIT_ORDER_CASSETTES 31 // monkestation addition: cassettes initialize before atoms, so that cassette stuff can be used in Initialize() #define INIT_ORDER_ATOMS 30 #define INIT_ORDER_ARMAMENTS 27 #define INIT_ORDER_LANGUAGE 25 diff --git a/code/__DEFINES/traits/monkestation/declarations.dm b/code/__DEFINES/traits/monkestation/declarations.dm index f43063a99422..98d4f955a2af 100644 --- a/code/__DEFINES/traits/monkestation/declarations.dm +++ b/code/__DEFINES/traits/monkestation/declarations.dm @@ -1,5 +1,9 @@ // BEGIN TRAIT DEFINES +// /mob +/// This mob can hear the music from the DJ station. +#define TRAIT_CAN_HEAR_MUSIC "can_hear_radio" + // /mob/living /// Monkeys are friendly/neutral to this mob by defaulot. #define TRAIT_MONKEYFRIEND "monkeyfriend" diff --git a/code/__DEFINES/~monkestation/cassettes.dm b/code/__DEFINES/~monkestation/cassettes.dm new file mode 100644 index 000000000000..e4ec6a1cdcb2 --- /dev/null +++ b/code/__DEFINES/~monkestation/cassettes.dm @@ -0,0 +1,13 @@ +/// Path to the base directory for cassette stuff +#define CASSETTE_BASE_DIR "data/cassette_storage/" +/// Path to the file containing a list of cassette IDs. +#define CASSETTE_ID_FILE (CASSETTE_BASE_DIR + "ids.json") +/// Path to the data for the cassette of the given ID. +#define CASSETTE_FILE(id) (CASSETTE_BASE_DIR + "[id].json") + +/// This cassette is unapproved, and has not been submitted for review. +#define CASSETTE_STATUS_UNAPPROVED 0 +/// This cassette is under review. +#define CASSETTE_STATUS_REVIEWING 1 +/// This cassette has been approved. +#define CASSETTE_STATUS_APPROVED 2 diff --git a/code/__DEFINES/~monkestation/dcs/signals/signals_global.dm b/code/__DEFINES/~monkestation/dcs/signals/signals_global.dm index d090af76972c..335269043492 100644 --- a/code/__DEFINES/~monkestation/dcs/signals/signals_global.dm +++ b/code/__DEFINES/~monkestation/dcs/signals/signals_global.dm @@ -1,2 +1,6 @@ /// Sent whenever a new goldeneye key is spawned: (obj/item/goldeneye_key) #define COMSIG_GLOB_GOLDENEYE_KEY_CREATED "!goldeneye_key_created" +/// Sent whenever a mob becomes capable of hearing DJ music: (mob/listener) +#define COMSIG_GLOB_ADD_MUSIC_LISTENER "!add_music_listener" +/// Sent whenever a mob becomes no longer capable of hearing DJ music: (mob/listener) +#define COMSIG_GLOB_REMOVE_MUSIC_LISTENER "!remove_music_listener" diff --git a/code/__HELPERS/roundend.dm b/code/__HELPERS/roundend.dm index 7112c0447ae6..4fedbe19a931 100644 --- a/code/__HELPERS/roundend.dm +++ b/code/__HELPERS/roundend.dm @@ -301,7 +301,8 @@ GLOBAL_LIST_INIT(round_end_images, world.file2list("data/image_urls.txt")) // MO // monkestation start: token backups, monkecoin rewards, challenges, and roundend webhook save_tokens() - refund_cassette() +#warn TODO: cassette refunds + // refund_cassette() distribute_rewards() sleep(5 SECONDS) ready_for_reboot = TRUE diff --git a/code/__HELPERS/~monkestation-helpers/roundend.dm b/code/__HELPERS/~monkestation-helpers/roundend.dm index 5351e9d2bcff..544031be499f 100644 --- a/code/__HELPERS/~monkestation-helpers/roundend.dm +++ b/code/__HELPERS/~monkestation-helpers/roundend.dm @@ -37,6 +37,8 @@ if(total_payout) client?.prefs?.adjust_metacoins(client?.ckey, total_payout, "Challenge rewards.") +#warn TODO: cassette refunds +/* /datum/controller/subsystem/ticker/proc/refund_cassette() if(!length(GLOB.cassette_reviews)) return @@ -62,3 +64,4 @@ message_admins("Balance not adjusted for Cassette:[review.submitted_tape.name], Balance for [client]; Previous:[prev_bal], Expected:[prev_bal + 5000], Current:[client?.prefs?.metacoins]. Issue logged.") log_admin("Balance not adjusted for Cassette:[review.submitted_tape.name], Balance for [client]; Previous:[prev_bal], Expected:[prev_bal + 5000], Current:[client?.prefs?.metacoins].") qdel(review) +*/ diff --git a/code/__HELPERS/~monkestation-helpers/text.dm b/code/__HELPERS/~monkestation-helpers/text.dm new file mode 100644 index 000000000000..cb6383f2e031 --- /dev/null +++ b/code/__HELPERS/~monkestation-helpers/text.dm @@ -0,0 +1,6 @@ +/// Checks to see if a string starts with http:// or https:// +/proc/is_http_protocol(text) + var/static/regex/http_regex + if(isnull(http_regex)) + http_regex = new("^https?://") + return findtext(text, http_regex) diff --git a/code/_globalvars/_regexes.dm b/code/_globalvars/_regexes.dm index 7297d509a918..e850889a42b7 100644 --- a/code/_globalvars/_regexes.dm +++ b/code/_globalvars/_regexes.dm @@ -1,7 +1,4 @@ //These are a bunch of regex datums for use /((any|every|no|some|head|foot)where(wolf)?\sand\s)+(\.[\.\s]+\s?where\?)?/i -GLOBAL_DATUM_INIT(is_http_protocol, /regex, regex("^https?://")) -GLOBAL_DATUM_INIT(is_http_protocol_non_secure, /regex, regex("^http?://")) - GLOBAL_DATUM_INIT(is_website, /regex, regex("http|www.|\[a-z0-9_-]+.(com|org|net|mil|edu)+", "i")) GLOBAL_DATUM_INIT(is_email, /regex, regex("\[a-z0-9_-]+@\[a-z0-9_-]+.\[a-z0-9_-]+", "i")) diff --git a/code/controllers/configuration/entries/monkestation.dm b/code/controllers/configuration/entries/monkestation.dm index c49237131fec..342063dd62a9 100644 --- a/code/controllers/configuration/entries/monkestation.dm +++ b/code/controllers/configuration/entries/monkestation.dm @@ -62,3 +62,5 @@ . = ..() if(.) config_entry_value *= 600 // documented as minutes + +/datum/config_entry/flag/cassettes_in_db diff --git a/code/modules/admin/admin_verbs.dm b/code/modules/admin/admin_verbs.dm index 877a998ee651..d882ba9ba36e 100644 --- a/code/modules/admin/admin_verbs.dm +++ b/code/modules/admin/admin_verbs.dm @@ -19,7 +19,8 @@ GLOBAL_PROTECT(admin_verbs_default) /client/proc/reload_admins, /client/proc/requests, /client/proc/secrets, - /client/proc/review_cassettes, /*monkestation addition Opens the Cassette Review menu*/ +#warn TODO: cassette reviews + // /client/proc/review_cassettes, /*monkestation addition Opens the Cassette Review menu*/ /client/proc/stop_sounds, /client/proc/tag_datum_mapview, ) diff --git a/code/modules/admin/topic.dm b/code/modules/admin/topic.dm index 88daf9cf16a2..e035b57447f7 100644 --- a/code/modules/admin/topic.dm +++ b/code/modules/admin/topic.dm @@ -1794,6 +1794,8 @@ user_client.client_token_holder.reject_antag_token() log_admin("[user_client]'s token has been rejected by [owner].") +#warn TODO: cassette reviews +/* else if(href_list["open_music_review"]) if(!check_rights(R_ADMIN)) return @@ -1802,7 +1804,7 @@ if(!istype(cassette_review)) return cassette_review.ui_interact(usr) - +*/ else if(href_list["approve_token_event"]) if(!check_rights(R_ADMIN)) return diff --git a/code/modules/admin/verbs/playsound.dm b/code/modules/admin/verbs/playsound.dm index 784963f00d13..15e12625c8a9 100644 --- a/code/modules/admin/verbs/playsound.dm +++ b/code/modules/admin/verbs/playsound.dm @@ -150,7 +150,7 @@ message_admins("[key_name(user)] stopped web sounds.") web_sound_url = null stop_web_sounds = TRUE - if(web_sound_url && !findtext(web_sound_url, GLOB.is_http_protocol)) + if(web_sound_url && !is_http_protocol(web_sound_url)) tgui_alert(user, "The media provider returned a content URL that isn't using the HTTP or HTTPS protocol. This is a security risk and the sound will not be played.", "Security Risk", list("OK")) to_chat(user, span_boldwarning("BLOCKED: Content URL not using HTTP(S) Protocol!"), confidential = TRUE) @@ -183,7 +183,7 @@ if(length(web_sound_input)) web_sound_input = trim(web_sound_input) - if(findtext(web_sound_input, ":") && !findtext(web_sound_input, GLOB.is_http_protocol)) + if(findtext(web_sound_input, ":") && !is_http_protocol(web_sound_input)) to_chat(src, span_boldwarning("Non-http(s) URIs are not allowed."), confidential = TRUE) to_chat(src, span_warning("For youtube-dl shortcuts like ytsearch: please use the appropriate full URL from the website."), confidential = TRUE) return diff --git a/code/modules/mob/dead/new_player/new_player.dm b/code/modules/mob/dead/new_player/new_player.dm index 6fb429925942..5500820e12b7 100644 --- a/code/modules/mob/dead/new_player/new_player.dm +++ b/code/modules/mob/dead/new_player/new_player.dm @@ -244,12 +244,6 @@ humanc.load_persistent_scars() SSpersistence.load_modular_persistence(humanc.get_organ_slot(ORGAN_SLOT_BRAIN)) - //monkestation edit start - if(GLOB.dj_booth) - var/obj/machinery/cassette/dj_station/dj = GLOB.dj_booth - dj.add_new_player(humanc) - //monkestation edit end - if(GLOB.curse_of_madness_triggered) give_madness(humanc, GLOB.curse_of_madness_triggered) diff --git a/code/modules/requests/request_manager.dm b/code/modules/requests/request_manager.dm index eb16a38fc3bc..408889b86eef 100644 --- a/code/modules/requests/request_manager.dm +++ b/code/modules/requests/request_manager.dm @@ -245,7 +245,7 @@ GLOBAL_DATUM_INIT(requests, /datum/request_manager, new) if(request.req_type != REQUEST_INTERNET_SOUND) to_chat(usr, "Request doesn't have a sound to play.", confidential = TRUE) return TRUE - if(findtext(request.message, ":") && !findtext(request.message, GLOB.is_http_protocol)) + if(findtext(request.message, ":") && !is_http_protocol(request.message)) to_chat(usr, "Request is not a valid URL.", confidential = TRUE) return TRUE diff --git a/code/modules/tgui_panel/audio.dm b/code/modules/tgui_panel/audio.dm index 680696159943..3397434b8970 100644 --- a/code/modules/tgui_panel/audio.dm +++ b/code/modules/tgui_panel/audio.dm @@ -20,9 +20,7 @@ * optional extra_data list Optional settings. */ /datum/tgui_panel/proc/play_music(url, extra_data) - if(!is_ready()) - return - if(!findtext(url, GLOB.is_http_protocol)) + if(!is_ready() || !is_http_protocol(url)) return var/list/payload = list() if(length(extra_data) > 0) diff --git a/code/modules/unit_tests/unit_test.dm b/code/modules/unit_tests/unit_test.dm index e3446e24618a..1cc258a6efa0 100644 --- a/code/modules/unit_tests/unit_test.dm +++ b/code/modules/unit_tests/unit_test.dm @@ -326,8 +326,8 @@ GLOBAL_VAR_INIT(focused_tests, focused_tests()) ///we generate mobs in these and create destroy does this in null space ignore += typesof(/obj/item/loot_table_maker) ///we need to use json_decode to run randoms properly - ignore += typesof(/obj/item/device/cassette_tape) - ignore += typesof(/datum/cassette/cassette_tape) + ignore += typesof(/obj/item/cassette_tape) + ignore += typesof(/datum/cassette) ///we also dont want weathers or weather events as they will hold refs to alot of stuff as they shouldn't be deleted ignore += typesof(/datum/weather_event) ignore += typesof(/datum/particle_weather) diff --git a/config/config.txt b/config/config.txt index 464b95aa5078..46f90548fe35 100644 --- a/config/config.txt +++ b/config/config.txt @@ -566,3 +566,5 @@ CONFIG_ERRORS_RUNTIME ## The age in days if minimum account age is on #MINIMUM_AGE +## If enabled, cassette tapes will be stored in the database, rather than JSON files on-disk. +#CASSETTES_IN_DB diff --git a/monkestation/code/game/objects/items/devices/radio/headset.dm b/monkestation/code/game/objects/items/devices/radio/headset.dm index 8be0cd0cbe8d..d51020d250b9 100644 --- a/monkestation/code/game/objects/items/devices/radio/headset.dm +++ b/monkestation/code/game/objects/items/devices/radio/headset.dm @@ -1,3 +1,12 @@ +/obj/item/radio/headset/equipped(mob/user, slot, initial) + . = ..() + if(slot_flags & slot) + ADD_TRAIT(user, TRAIT_CAN_HEAR_MUSIC, REF(src)) + +/obj/item/radio/headset/dropped(mob/user, silent) + . = ..() + REMOVE_TRAIT(user, TRAIT_CAN_HEAR_MUSIC, REF(src)) + /obj/item/radio/headset/headset_secmed name = "brig physician radio headset" desc = "This is used by your secure doctor." diff --git a/monkestation/code/game/objects/items/implants/implant_misc.dm b/monkestation/code/game/objects/items/implants/implant_misc.dm new file mode 100644 index 000000000000..a84c63c522fd --- /dev/null +++ b/monkestation/code/game/objects/items/implants/implant_misc.dm @@ -0,0 +1,9 @@ +/obj/item/implant/radio/implant(mob/living/target, mob/user, silent, force) + . = ..() + if(.) + ADD_TRAIT(target, TRAIT_CAN_HEAR_MUSIC, REF(src)) + +/obj/item/implant/radio/removed(mob/living/source, silent, special) + . = ..() + if(.) + REMOVE_TRAIT(source, TRAIT_CAN_HEAR_MUSIC, REF(src)) diff --git a/monkestation/code/modules/admin/verbs/spawn_mixtape.dm b/monkestation/code/modules/admin/verbs/spawn_mixtape.dm index bffca51317a0..db39c7529087 100644 --- a/monkestation/code/modules/admin/verbs/spawn_mixtape.dm +++ b/monkestation/code/modules/admin/verbs/spawn_mixtape.dm @@ -3,19 +3,22 @@ set name = "Spawn Mixtape" set desc = "Select an approved mixtape to spawn at your location." - var/datum/mixtape_spawner/tgui = new(usr)//create the datum - tgui.ui_interact(usr)//datum has a tgui component, here we open the window + if(!check_rights(R_ADMIN)) + return + new /datum/mixtape_spawner(src) /datum/mixtape_spawner - var/client/holder //client of whoever is using this datum + /// The client of whoever is using this datum. + var/client/holder /datum/mixtape_spawner/New(user)//user can either be a client or a mob due to byondcode(tm) - if (istype(user, /client)) - var/client/user_client = user - holder = user_client //if its a client, assign it to holder - else - var/mob/user_mob = user - holder = user_mob.client //if its a mob, assign the mob's client to holder + . = ..() + holder = get_player_client(user) + ui_interact(holder.mob) + +/datum/mixtape_spawner/Destroy(force) + holder = null + return ..() /datum/mixtape_spawner/ui_state(mob/user) return GLOB.admin_state @@ -27,31 +30,38 @@ ui = SStgui.try_update_ui(user, src, ui) if(!ui) ui = new(user, src, "MixtapeSpawner") + ui.set_autoupdate(FALSE) ui.open() -/datum/mixtape_spawner/ui_data(mob/user) - var/list/data = list() - if(!length(SScassette_storage.cassette_datums)) - return - for(var/datum/cassette_data/cassette in SScassette_storage.cassette_datums) - data["approved_cassettes"] += list(list( - "name" = cassette.cassette_name, - "desc" = cassette.cassette_desc, - "cassette_design_front" = cassette.cassette_design_front, - "creator_ckey" = cassette.cassette_author_ckey, - "creator_name" = cassette.cassette_author, - "song_names" = cassette.song_names, - "id" = cassette.cassette_id +/datum/mixtape_spawner/ui_static_data(mob/user) + var/list/approved_cassettes = list() + for(var/datum/cassette/cassette as anything in SScassettes.cassettes) + if(cassette.status != CASSETTE_STATUS_APPROVED) + continue + approved_cassettes += list(list( + "name" = cassette.name, + "desc" = cassette.desc, + "cassette_design_front" = cassette.front.design, + "creator_ckey" = ckey(cassette.author.ckey), + "creator_name" = cassette.author.name, + "song_names" = cassette.list_song_names(), + "id" = cassette.id, )) - return data + return list("approved_cassettes" = approved_cassettes) -/datum/mixtape_spawner/ui_act(action, params) +/datum/mixtape_spawner/ui_act(action, list/params, datum/tgui/ui) . = ..() if(.) return + var/mob/user = ui.user switch(action) if("spawn") - if (params["id"]) - new/obj/item/device/cassette_tape(usr.loc, params["id"]) - SSblackbox.record_feedback("tally", "admin_verb", 1, "Spawn Mixtape") - log_admin("[key_name(usr)] created mixtape [params["id"]] at [usr.loc].") + var/id = params["id"] + if(!id) + return + var/atom/spawn_loc = user.drop_location() + new /obj/item/cassette_tape(spawn_loc, id) + SSblackbox.record_feedback("tally", "admin_verb", 1, "Spawn Mixtape") + message_admins("[key_name_admin(user)] spawned mixtape [id] at [ADMIN_COORDJMP(spawn_loc)].") + log_admin("[key_name(user)] spawned mixtape [id] at [loc_name(spawn_loc)].") + return TRUE diff --git a/monkestation/code/modules/cargo/crates/goodies.dm b/monkestation/code/modules/cargo/crates/goodies.dm index 79ed63cfb20d..d199df9b2f9f 100644 --- a/monkestation/code/modules/cargo/crates/goodies.dm +++ b/monkestation/code/modules/cargo/crates/goodies.dm @@ -8,10 +8,10 @@ name = "Cassette Mini-Pack" desc = "Alright, we'll admit it, 10 cassettes are too much for the majority of our users. Contains 3 Approved Cassettes." cost = PAYCHECK_CREW * 5 - contains = list(/obj/item/device/cassette_tape/random = 3) + contains = list(/obj/item/cassette_tape/random = 3) /datum/supply_pack/goody/blankcassette name = "Blank Cassette Mini-Pack" desc = "NO! We wont admit defeat! You will march yourself down to the Service section and purchase the 10 Blank Cassette pack instead of this Weak 3 Blank Cassette Pack!" cost = PAYCHECK_CREW * 3 - contains = list(/obj/item/device/cassette_tape/blank = 3) + contains = list(/obj/item/cassette_tape/blank = 3) diff --git a/monkestation/code/modules/cargo/crates/service.dm b/monkestation/code/modules/cargo/crates/service.dm index 3b0c69c0efe9..fe7fbcd48ba3 100644 --- a/monkestation/code/modules/cargo/crates/service.dm +++ b/monkestation/code/modules/cargo/crates/service.dm @@ -45,13 +45,13 @@ /datum/supply_pack/service/cassettes/fill(obj/structure/closet/crate/our_crate) for(var/id in unique_random_tapes(10)) - new /obj/item/device/cassette_tape(our_crate, id) + new /obj/item/cassette_tape(our_crate, id) /datum/supply_pack/service/blankcassettes name = "Blank Cassettes Crate" desc = "in the VERY unlikely event you have run out of blank cassettes, you can get 10 blank ones here. Contains 10 blank cassettes for use in Walkmans." cost = CARGO_CRATE_VALUE * 2 - contains = list(/obj/item/device/cassette_tape/blank = 10) + contains = list(/obj/item/cassette_tape/blank = 10) crate_name = "cassette crate" /datum/supply_pack/service/walkmen diff --git a/monkestation/code/modules/cassettes/cassette.dm b/monkestation/code/modules/cassettes/cassette.dm index 9fdfe816cb7e..06aed098d961 100644 --- a/monkestation/code/modules/cassettes/cassette.dm +++ b/monkestation/code/modules/cassettes/cassette.dm @@ -1,86 +1,74 @@ -/obj/item/device/cassette_tape +/obj/item/cassette_tape name = "Debug Cassette Tape" desc = "You shouldn't be seeing this!" icon = 'monkestation/code/modules/cassettes/icons/walkman.dmi' icon_state = "cassette_flip" w_class = WEIGHT_CLASS_SMALL - ///icon of the cassettes front side - var/side1_icon = "cassette_worstmap" - var/side2_icon = "cassette_worstmap" - ///if the cassette is flipped, for playing second list of songs + /// If the cassette is flipped, for playing second list of songs. var/flipped = FALSE - ///list of songs each side has to play - var/list/songs = list("side1" = list(), - "side2" = list()) - ///list of each songs name in the order they appear - var/list/song_names = list("side1" = list(), - "side2" = list()) - ///the id of the cassette - var/id - ///the ckey of the cassette author - var/ckey_author - ///the authors name displayed in examine text - var/author_name - ///are we an approved tape? - var/approved_tape = FALSE - ///are we random? + /// The data for this cassette. + var/datum/cassette/cassette_data + /// Should we just spawn a random cassette? var/random = FALSE - var/cassette_desc_string = "Generic Desc" + /// ID of the cassette to spawn in as by default. + var/id -/obj/item/device/cassette_tape/Initialize(mapload, spawned_id) +/obj/item/cassette_tape/Initialize(mapload, spawned_id) . = ..() - if(!length(GLOB.approved_ids)) - GLOB.approved_ids = initialize_approved_ids() - - if(length(GLOB.approved_ids)) - if(spawned_id && (spawned_id in GLOB.approved_ids)) - id = spawned_id - else if(random) - id = pick(GLOB.approved_ids) - - var/file = file("data/cassette_storage/[id].json") - if(!fexists(file)) - return + spawned_id ||= id + if(!isnull(spawned_id)) + cassette_data = SScassettes.load_cassette(spawned_id) + else if(random) + var/list/random_cassette = SScassettes.unique_random_cassettes(amount = 1, status = CASSETTE_STATUS_APPROVED) + if(length(random_cassette)) + cassette_data = random_cassette[1] + cassette_data ||= new + update_appearance(UPDATE_DESC | UPDATE_ICON_STATE) - var/list/data = json_decode(file2text(file)) - name = data["name"] - cassette_desc_string = data["desc"] - icon_state = data["side1_icon"] - side1_icon = data["side1_icon"] - side2_icon = data["side2_icon"] - songs = data["songs"] - song_names = data["song_names"] - author_name = data["author_name"] - ckey_author = data["author_ckey"] - approved_tape = data["approved"] +/obj/item/cassette_tape/Destroy(force) + cassette_data = null + return ..() - update_appearance() - -/obj/item/device/cassette_tape/attack_self(mob/user) - ..() - icon_state = flipped ? side1_icon : side2_icon +/obj/item/cassette_tape/attack_self(mob/user) + . = ..() flipped = !flipped to_chat(user, span_notice("You flip [src].")) + update_appearance(UPDATE_ICON_STATE) + +/obj/item/cassette_tape/update_desc(updates) + desc = cassette_data.desc || "A generic cassette." + return ..() -/obj/item/device/cassette_tape/update_desc(updates) +/obj/item/cassette_tape/update_icon_state() + icon_state = cassette_data.get_side(!flipped)?.design || src::icon_state + return ..() + +/obj/item/cassette_tape/examine(mob/user) . = ..() - desc = cassette_desc_string - desc += "\n" - if(!approved_tape) - desc += span_warning("It appears to be a bootleg tape, quality is not a guarantee!\n") - if(author_name) - desc += span_notice("Mixed by [author_name]\n") + switch(cassette_data.status) + if(CASSETTE_STATUS_UNAPPROVED) + . += span_warning("It appears to be a bootleg tape, quality is not a guarantee!") + . += span_notice("In order to play this tape for the whole station, it must be submitted to the Space Board of Music and approved.") + if(CASSETTE_STATUS_REVIEWING) + . += span_warning("It seems this tape is still being reviewed by the Space Board of Music.") + if(CASSETTE_STATUS_APPROVED) + . += span_info("This cassette has been approved by the Space Board of Music, and can be played for the whole station with the Cassette Player.") + else + stack_trace("Unknown status [cassette_data.status] for cassette [cassette_data.name] ([cassette_data.id])") -/obj/item/device/cassette_tape/attackby(obj/item/item, mob/living/user) + if(cassette_data.author.name) + . += span_info("Mixed by [span_name(cassette_data.author.name)]") + +/obj/item/cassette_tape/attackby(obj/item/item, mob/living/user) if(!istype(item, /obj/item/pen)) return ..() - var/choice = tgui_input_list(usr, "What would you like to change?", items = list("Cassette Name", "Cassette Description", "Cancel")) + var/choice = tgui_input_list(user, "What would you like to change?", items = list("Cassette Name", "Cassette Description", "Cancel")) switch(choice) if("Cassette Name") ///the name we are giving the cassette - var/newcassettename = reject_bad_text(tgui_input_text(user, "Write a new Cassette name:", name, name, max_length = MAX_NAME_LEN)) - if(!user.can_perform_action (src, TRUE)) + var/newcassettename = reject_bad_text(tgui_input_text(user, "Write a new Cassette name:", name, html_decode(name), max_length = MAX_NAME_LEN)) + if(!user.can_perform_action(src, TRUE)) return if(length(newcassettename) > MAX_NAME_LEN) to_chat(user, span_warning("That name is too long!")) @@ -92,7 +80,7 @@ name = "[lowertext(newcassettename)]" if("Cassette Description") ///the description we are giving the cassette - var/newdesc = tgui_input_text(user, "Write a new description:", name, desc, max_length = 180) + var/newdesc = tgui_input_text(user, "Write a new description:", name, html_decode(desc), max_length = 180) if(!user.can_perform_action(src, TRUE)) return if (length(newdesc) > 180) @@ -101,29 +89,11 @@ if(!newdesc) to_chat(user, span_warning("That description is invalid.")) return - cassette_desc_string = newdesc - update_appearance() - else - return - -/datum/cassette/cassette_tape - var/name = "Broken Cassette" - var/desc = "You shouldn't be seeing this! Make an issue about it" - var/icon_state = "cassette_flip" - var/side1_icon = "cassette_flip" - var/side2_icon = "cassette_flip" - var/id = "blank" - var/creator_ckey = "Dwasint" - var/creator_name = "Collects-The-Candy" - var/approved = TRUE - var/list/song_names = list("side1" = list(), - "side2" = list()) - - var/list/songs = list("side1" = list(), - "side2" = list()) + cassette_data.desc = newdesc + update_appearance(UPDATE_DESC) -/obj/item/device/cassette_tape/blank +/obj/item/cassette_tape/blank id = "blank" -/obj/item/device/cassette_tape/friday +/obj/item/cassette_tape/friday id = "friday" diff --git a/monkestation/code/modules/cassettes/cassette_approval.dm b/monkestation/code/modules/cassettes/cassette_approval.dm index e53173d972aa..099307a903e5 100644 --- a/monkestation/code/modules/cassettes/cassette_approval.dm +++ b/monkestation/code/modules/cassettes/cassette_approval.dm @@ -1,7 +1,9 @@ +#warn TODO: cassette reviewing/approvals +/* GLOBAL_LIST_INIT(cassette_reviews, list()) #define ADMIN_OPEN_REVIEW(id) "(Open Review)" -/proc/submit_cassette_for_review(obj/item/device/cassette_tape/submitted, mob/user) +/proc/submit_cassette_for_review(obj/item/cassette_tape/submitted, mob/user) if(!user.client) return var/datum/cassette_review/new_review = new @@ -25,7 +27,7 @@ GLOBAL_LIST_INIT(cassette_reviews, list()) has requested a review on their cassette."))]") to_chat(user, span_notice("Your Cassette has been sent to the Space Board of Music for review, you will be notified when an outcome has been made.")) -/obj/item/device/cassette_tape/proc/generate_cassette_json() +/obj/item/cassette_tape/proc/generate_cassette_json() if(approved_tape) return if(!length(GLOB.approved_ids)) @@ -70,7 +72,7 @@ GLOBAL_LIST_INIT(cassette_reviews, list()) "song_url" = list() ) ) - var/obj/item/device/cassette_tape/submitted_tape + var/obj/item/cassette_tape/submitted_tape var/action_taken = FALSE var/verdict = "NONE" @@ -220,3 +222,4 @@ GLOBAL_LIST_INIT(cassette_reviews, list()) return +*/ diff --git a/monkestation/code/modules/cassettes/cassette_db/cassette_datum.dm b/monkestation/code/modules/cassettes/cassette_db/cassette_datum.dm index 07efe51ea95e..3671e96c50c1 100644 --- a/monkestation/code/modules/cassettes/cassette_db/cassette_datum.dm +++ b/monkestation/code/modules/cassettes/cassette_db/cassette_datum.dm @@ -1,61 +1,182 @@ -/datum/cassette_data - var/cassette_name - var/cassette_author - var/cassette_desc - var/cassette_author_ckey - - var/cassette_design_front - var/cassette_design_back - - var/list/songs - - var/list/song_names - - var/cassette_id - var/approved - var/file_name - - -/datum/cassette_data/proc/populate_data(file_id) - var/file = file("data/cassette_storage/[file_id].json") - if(!fexists(file)) +/datum/cassette + /// The unique ID of the cassette. + var/id + /// The name of the cassette. + var/name + /// The description of the cassette. + var/desc + /// The status of this cassette. + var/status = CASSETTE_STATUS_UNAPPROVED + /// Information about the author of this cassette. + var/datum/cassette_author/author + + /// The front side of the cassette. + var/datum/cassette_side/front + /// The back side of the cassette. + var/datum/cassette_side/back + +/datum/cassette/New() + . = ..() + author = new + front = new + back = new + +/datum/cassette/Destroy(force) + QDEL_NULL(author) + QDEL_NULL(front) + QDEL_NULL(back) + return ..() + +/// Imports cassette date from the old format. +/datum/cassette/proc/import_old_format(list/data) + name = data["name"] + desc = data["desc"] + if("status" in data) + status = data["status"] + else + status = data["approved"] ? CASSETTE_STATUS_APPROVED : CASSETTE_STATUS_UNAPPROVED + + author.name = data["author_name"] + author.ckey = ckey(data["author_ckey"]) + + for(var/i in 1 to 2) + var/datum/cassette_side/side = get_side(i % 2) // side2 = 0, side1 = 1 + var/side_name = "side[i]" + var/list/song_urls = data["songs"][side_name] + var/list/song_names = data["song_names"][side_name] + if(length(song_urls) != length(song_names)) + stack_trace("amount of song urls for [side_name] ([length(song_urls)]) did not match amount of song names for [side_name] ([length(song_names)])") + continue + side.design = data["[side_name]_icon"] + for(var/idx in 1 to length(song_urls)) + side.songs += new /datum/cassette_song(song_names[idx], song_urls[idx]) + +/// Exports cassette date in the old format. +/datum/cassette/proc/export_old_format() as /list + RETURN_TYPE(/list) + . = list( + "name" = name, + "desc" = desc, + "side1_icon" = /datum/cassette_side::design, + "side2_icon" = /datum/cassette_side::design, + "author_name" = author.name, + "author_ckey" = ckey(author.ckey), + "approved" = status == CASSETTE_STATUS_APPROVED, + "status" = status, + "songs" = list( + "side1" = list(), + "side2" = list(), + ), + "song_names" = list( + "side1" = list(), + "side2" = list(), + ), + ) + for(var/i in 1 to 2) + var/datum/cassette_side/side = get_side(i % 2) // side2 = 0, side1 = 1 + var/side_name = "side[i]" + var/list/names = list() + var/list/urls = list() + .["[side_name]_icon"] = side.design + for(var/datum/cassette_song/song as anything in side.songs) + names += song.name + urls += song.url + .["song_names"][side_name] = names + .["songs"][side_name] = urls + +/// Saves the cassette to the data folder, in JSON format. +/datum/cassette/proc/save_to_file() + if(!id) + CRASH("Attempted to save cassette without an ID to disk") + rustg_file_write(json_encode(export_old_format(), JSON_PRETTY_PRINT), CASSETTE_FILE(id)) + +/// Saves the cassette to the database. +/// Returns TRUE if successful, FALSE otherwise. +/datum/cassette/proc/save_to_db() + if(!id) + CRASH("Attempted to save cassette without an ID to database") + if(!SSdbcore.Connect()) + CRASH("Could not save cassette [id], database not connected") + var/datum/db_query/query_save_cassette = SSdbcore.NewQuery({" + INSERT INTO [format_table_name("cassettes")] + (id, name, desc, status, author_name, author_ckey, front, back) + VALUES + (:id, :name, :desc, :status, :author_name, :author_ckey, :front, :back) + ON DUPLICATE KEY UPDATE + name = VALUES(name), + desc = VALUES(desc), + status = VALUES(status), + author_name = VALUES(author_name), + author_ckey = VALUES(author_ckey), + front = VALUES(front), + back = VALUES(back) + "}, list( + "id" = id, + "name" = name, + "desc" = desc, + "status" = status, + "author_name" = author.name, + "author_name" = ckey(author.ckey), + "front" = json_encode(front.export_for_db()), + "back" = json_encode(back.export_for_db()), + )) + if(!query_save_cassette.warn_execute()) + qdel(query_save_cassette) + stack_trace("Failed to save cassette [id] to database") return FALSE - var/list/data = json_decode(file2text(file)) - - cassette_name = data["name"] - cassette_desc = data["desc"] - - cassette_design_front = data["side1_icon"] - cassette_design_back = data["side2_icon"] - - songs = data["songs"] - - song_names = data["song_names"] - - cassette_author = data["author_name"] - cassette_author_ckey = data["author_ckey"] - - cassette_id = file_id - - approved = data["approved"] - - file_name = "data/cassette_storage/[file_id].json" - + qdel(query_save_cassette) return TRUE -/datum/cassette_data/proc/generate_cassette(turf/location) - if(!location) - return - var/obj/item/device/cassette_tape/new_tape = new(location) - new_tape.name = cassette_name - new_tape.cassette_desc_string = cassette_desc - new_tape.icon_state = cassette_design_front - new_tape.side1_icon = cassette_design_front - new_tape.side2_icon = cassette_design_back - new_tape.songs = songs - new_tape.song_names = song_names - new_tape.author_name = cassette_author - new_tape.ckey_author = cassette_author_ckey - new_tape.approved_tape = approved - - new_tape.update_appearance() + +/// Simple helper to get a side of the cassette. +/// TRUE is front side, FALSE is back side. +/datum/cassette/proc/get_side(front_side = TRUE) as /datum/cassette_side + RETURN_TYPE(/datum/cassette_side) + return front_side ? front : back + +/// Returns a list of all the song names in this cassette. +/// Really only useful for searching for cassettes via contained song names. +/datum/cassette/proc/list_song_names() as /list + RETURN_TYPE(/list) + . = list() + for(var/datum/cassette_song/song as anything in front.songs + back.songs) + . |= song.name + +/datum/cassette_author + /// The character name of the cassette author. + var/name + /// The ckey of the cassette author. + var/ckey + +/datum/cassette_side + /// The design of this side of the cassette. + var/design = "cassette_flip" + /// The songs on this side of the cassette. + var/list/datum/cassette_song/songs = list() + +/// Imports data for this cassette side to the JSON format used by the database. +/datum/cassette_side/proc/import_from_db(list/data) + design = data["design"] + for(var/list/song as anything in data["songs"]) + songs += new /datum/cassette_song(song["name"], song["url"]) + +/// Exports data from this cassette side in the JSON format used by the database. +/datum/cassette_side/proc/export_for_db() + . = list("design" = design, "songs" = list()) + for(var/datum/cassette_song/song as anything in songs) + .["songs"] += list(list("name" = song.name, "url" = song.url)) + +/datum/cassette_side/Destroy(force) + QDEL_LIST(songs) + return ..() + +/datum/cassette_song + /// The name of the song. + var/name + /// The URL of the song. + var/url + +/datum/cassette_song/New(name, url) + . = ..() + src.name = name + src.url = url diff --git a/monkestation/code/modules/cassettes/cassette_db/cassette_manager.dm b/monkestation/code/modules/cassettes/cassette_db/cassette_manager.dm new file mode 100644 index 000000000000..043786409120 --- /dev/null +++ b/monkestation/code/modules/cassettes/cassette_db/cassette_manager.dm @@ -0,0 +1,206 @@ +SUBSYSTEM_DEF(cassettes) + name = "Cassetes" + init_order = INIT_ORDER_CASSETTES + flags = SS_NO_FIRE + /// An associative list of IDs to cassette data. + var/list/datum/cassette/cassettes = list() + +/datum/controller/subsystem/cassettes/Initialize() + . = SS_INIT_FAILURE + if(CONFIG_GET(flag/cassettes_in_db) && !CONFIG_GET(flag/sql_enabled)) + stack_trace("CASSETTES_IN_DB was enabled, despite the SQL database not being enabled! Disabling CASSETTES_IN_DB.") + CONFIG_SET(flag/cassettes_in_db, FALSE) + if(CONFIG_GET(flag/cassettes_in_db)) + if(!SSdbcore.Connect()) + CRASH("Database-based cassettes are enabled, but a connection to the database could not be established!") + if(!load_all_cassettes_from_db()) + CRASH("Failed to load all cassettes from database!") + else + if(!load_all_cassettes_from_json()) + CRASH("Failed to load all cassettes from data folder!") + return SS_INIT_SUCCESS + +/datum/controller/subsystem/cassettes/Recover() + flags |= SS_NO_INIT + cassettes = SScassettes.cassettes + +/// Loads the cassette with the given ID. +/// If `db` is TRUE, it will load the cassette from the database. +/// If `db` is FALSE, the cassette will be loaded from a JSON in the `data/cassette_storage` folder. +/// If `db` is null (the default), it will load from the database if the `CASSETTES_IN_DB` config option is set, otherwise it will load from the JSON files. +/datum/controller/subsystem/cassettes/proc/load_cassette(id, db = null) as /datum/cassette + RETURN_TYPE(/datum/cassette) + if(!id) + return null + else if(istype(id, /datum/cassette)) // so i can be lazy + return id + if(id in cassettes) + return cassettes[id] + if(isnull(db)) + db = CONFIG_GET(flag/cassettes_in_db) + var/datum/cassette/cassette_data = db ? load_cassette_from_db_raw(id) : load_cassette_from_json_raw(id) + if(cassette_data) + cassettes[id] = cassette_data + return cassette_data + +/// Loads the cassette with the given ID from a JSON in the `data/cassette_storage` folder. +/// This does not check the SScassettes.cassettes cache, and you should not use this - this is only used to initialize SScassettes.cassettes +/datum/controller/subsystem/cassettes/proc/load_cassette_from_json_raw(id) as /datum/cassette + RETURN_TYPE(/datum/cassette) + var/cassette_file = CASSETTE_FILE(id) + if(!rustg_file_exists(cassette_file)) + return null + var/cassette_file_data = rustg_file_read(cassette_file) + if(!rustg_json_is_valid(cassette_file_data)) + CRASH("Cassette file [cassette_file] had invalid JSON!") + var/list/cassette_json = json_decode(cassette_file_data) + var/datum/cassette/cassette_data = new + cassette_data.import_old_format(cassette_json) + cassette_data.id = id + return cassette_data + +/// Loads the cassette with the given ID from the database. +/datum/controller/subsystem/cassettes/proc/load_cassette_from_db_raw(id) as /datum/cassette + RETURN_TYPE(/datum/cassette) + if(!SSdbcore.Connect() || !id) + return + var/datum/db_query/query_cassette = SSdbcore.NewQuery("SELECT name, desc, status, author_name, author_ckey, front, back FROM [format_table_name("cassettes")] WHERE id = :id", list("id" = id)) + if(!query_cassette.Execute() || !query_cassette.NextRow()) + qdel(query_cassette) + return + var/name = query_cassette.item[1] + var/desc = query_cassette.item[2] + var/status = query_cassette.item[3] + var/author_name = query_cassette.item[4] + var/author_ckey = query_cassette.item[5] + var/list/front = json_decode(query_cassette.item[6]) + var/list/back = json_decode(query_cassette.item[7]) + qdel(query_cassette) + + var/datum/cassette/cassette = new + cassette.id = id + cassette.name = name + cassette.desc = desc + cassette.status = status + cassette.author.name = author_name + cassette.author.ckey = author_ckey + cassette.front.import_from_db(front) + cassette.back.import_from_db(back) + return cassette + +/// Returns an associative list of id to cassette datums, of all existing saved cassettes. +/// This uses the database. +/datum/controller/subsystem/cassettes/proc/load_all_cassettes_from_db() + . = FALSE + if(!SSdbcore.Connect()) + CRASH("Failed to connect to database") + var/datum/db_query/query_cassettes = SSdbcore.NewQuery("SELECT id, name, desc, status, author_name, author_ckey, front, back FROM [format_table_name("cassettes")]") + if(!query_cassettes.Execute()) + qdel(query_cassettes) + CRASH("Failed to load cassettes from database") + while(query_cassettes.NextRow()) + var/id = query_cassettes.item[1] + var/name = query_cassettes.item[2] + var/desc = query_cassettes.item[3] + var/status = query_cassettes.item[4] + var/author_name = query_cassettes.item[5] + var/author_ckey = query_cassettes.item[6] + var/list/front = json_decode(query_cassettes.item[7]) + var/list/back = json_decode(query_cassettes.item[8]) + + var/datum/cassette/cassette = new + cassette.id = id + cassette.name = name + cassette.desc = desc + cassette.status = status + cassette.author.name = author_name + cassette.author.ckey = author_ckey + cassette.front.import_from_db(front) + cassette.back.import_from_db(back) + + cassettes[id] = cassette + qdel(query_cassettes) + return TRUE + +/// Returns an associative list of id to cassette datums, of all existing saved cassettes. +/// This uses JSON files. +/datum/controller/subsystem/cassettes/proc/load_all_cassettes_from_json() + . = FALSE + if(!rustg_file_exists(CASSETTE_ID_FILE)) // this just means there's no cassettes at all i guess? which is valid. + return TRUE + var/list/ids = json_decode(rustg_file_read(CASSETTE_ID_FILE)) + for(var/id in ids) + if(!ids) + continue + var/datum/cassette/cassette_data = load_cassette_from_json_raw(id) + if(isnull(cassette_data)) + stack_trace("Failed to load cassette [id]") + continue + cassettes[id] = cassette_data + return TRUE + +/// Updates the ids.json file on-disk. +/datum/controller/subsystem/cassettes/proc/save_ids_json() + var/list/ids = list() + if(rustg_file_exists(CASSETTE_ID_FILE)) + // Verify that each cassette ID still exists and is still considered "approved" before adding them to the list. + for(var/id in json_decode(rustg_file_read(CASSETTE_ID_FILE))) + if(!rustg_file_exists(CASSETTE_FILE(id))) + continue + ids += id + for(var/id in cassettes) + var/datum/cassette/cassette = cassettes[id] + if(cassette.status == CASSETTE_STATUS_UNAPPROVED) + ids -= id + else + ids |= id + rustg_file_write(ids, CASSETTE_ID_FILE) + +/// Returns all the cassettes that match the given arguments. +/datum/controller/subsystem/cassettes/proc/filtered_cassettes(status, user_ckey, list/id_blacklist) as /list + RETURN_TYPE(/list/datum/cassette) + . = list() + if(!isnull(user_ckey)) + user_ckey = ckey(user_ckey) + for(var/id in cassettes) + if(!isnull(id_blacklist) && (id in id_blacklist)) + continue + var/datum/cassette/cassette = cassettes[id] + if(!isnull(user_ckey) && ckey(cassette.author.ckey) != user_ckey) + continue + if(!isnull(status) && cassette.status != status) + continue + . += cassette + +/// Returns a list containing up to the specified amount of random, unique cassettes that match the given arguments. +/datum/controller/subsystem/cassettes/proc/unique_random_cassettes(amount = 1, status = CASSETTE_STATUS_APPROVED, user_ckey, list/id_blacklist) as /list + RETURN_TYPE(/list/datum/cassette) + . = list() + var/list/cassettes = filtered_cassettes(status, user_ckey, id_blacklist) + for(var/i in min(amount, length(cassettes))) + . += pick_n_take(cassettes) + +/datum/controller/subsystem/cassettes/proc/migrate_json_cassettes_to_db() + if(!SSdbcore.Connect()) + CRASH("Cannot migrate JSON cassettes to the database if we can't even connect to the database!") + var/list/old_cassettes = cassettes.Copy() + cassettes.Cut() + if(!load_all_cassettes_from_json()) + cassettes = old_cassettes + CRASH("Failed to load cassettes from JSON") + var/list/sql_cassettes = list() + for(var/id in cassettes) + var/datum/cassette/cassette = cassettes[id] + sql_cassettes += list(list( + "id" = id, + "name" = cassette.name, + "desc" = cassette.desc, + "status" = cassette.status, + "author_name" = cassette.author.name, + "author_ckey" = ckey(cassette.author.ckey), + "front" = cassette.front.export_for_db(), + "back" = cassette.back.export_for_db(), + )) + if(!length(sql_cassettes)) + return + SSdbcore.MassInsert(format_table_name("cassettes"), sql_cassettes, duplicate_key = TRUE, warn = TRUE) diff --git a/monkestation/code/modules/cassettes/cassette_db/subsystem.dm b/monkestation/code/modules/cassettes/cassette_db/subsystem.dm deleted file mode 100644 index bbca8076a20c..000000000000 --- a/monkestation/code/modules/cassettes/cassette_db/subsystem.dm +++ /dev/null @@ -1,30 +0,0 @@ -SUBSYSTEM_DEF(cassette_storage) - name = "Cassette Storage" - flags = SS_NO_FIRE - runlevels = RUNLEVEL_LOBBY | RUNLEVELS_DEFAULT - var/list/cassette_datums = list() - - -/datum/controller/subsystem/cassette_storage/Initialize() - if(!length(GLOB.approved_ids)) - GLOB.approved_ids = initialize_approved_ids() - generate_cassette_datums() - return SS_INIT_SUCCESS - -/datum/controller/subsystem/cassette_storage/proc/generate_cassette_datums() - for(var/id in GLOB.approved_ids) - var/datum/cassette_data/new_data = new - if(!new_data.populate_data(id)) - qdel(new_data) - continue - cassette_datums += new_data - -/datum/controller/subsystem/cassette_storage/proc/get_cassettes_by_ckey(user_ckey) as /list - RETURN_TYPE(/list) - . = list() - if(!user_ckey) - return - user_ckey = ckey(user_ckey) - for(var/datum/cassette_data/tape as anything in SScassette_storage.cassette_datums) - if(ckey(tape.cassette_author_ckey) == user_ckey) - . += tape diff --git a/monkestation/code/modules/cassettes/dj/dj_music_field.dm b/monkestation/code/modules/cassettes/dj/dj_music_field.dm new file mode 100644 index 000000000000..7ae01f489138 --- /dev/null +++ b/monkestation/code/modules/cassettes/dj/dj_music_field.dm @@ -0,0 +1,48 @@ +/// A proximity monitor field that allows mobs near objects to hear DJ music. +/datum/proximity_monitor/advanced/dj_music + edge_is_a_field = TRUE + /// List of mobs that can currently hear music from this field. + var/list/mob/listeners + +/datum/proximity_monitor/advanced/dj_music/Destroy() + for(var/mob/listener as anything in listeners) + remove_mob(listener) + return ..() + +/datum/proximity_monitor/advanced/dj_music/field_turf_crossed(atom/movable/crosser, turf/old_location, turf/new_location) + if(isliving(crosser)) + add_mob(crosser) + var/list/hearing_contents = crosser.important_recursive_contents?[RECURSIVE_CONTENTS_HEARING_SENSITIVE] + for(var/mob/living/target in hearing_contents) + add_mob(target) + +/datum/proximity_monitor/advanced/dj_music/field_turf_uncrossed(atom/movable/crosser, turf/old_location, turf/new_location) + if(isliving(crosser)) + remove_mob(crosser) + var/list/hearing_contents = crosser.important_recursive_contents?[RECURSIVE_CONTENTS_HEARING_SENSITIVE] + for(var/mob/living/target in hearing_contents) + remove_mob(target) + +/datum/proximity_monitor/advanced/dj_music/setup_field_turf(turf/target) + for(var/atom/movable/thing in target) + if(isliving(thing) || length(thing.important_recursive_contents?[RECURSIVE_CONTENTS_HEARING_SENSITIVE])) + field_turf_crossed(thing) + +/datum/proximity_monitor/advanced/dj_music/cleanup_field_turf(turf/target) + for(var/atom/movable/thing in target) + if(isliving(thing) || length(thing.important_recursive_contents?[RECURSIVE_CONTENTS_HEARING_SENSITIVE])) + field_turf_uncrossed(thing) + +/datum/proximity_monitor/advanced/dj_music/proc/add_mob(mob/living/target) + if(QDELING(src) || !isliving(target) || QDELING(target) || HAS_TRAIT_FROM(target, TRAIT_CAN_HEAR_MUSIC, INNATE_TRAIT) || (target in listeners)) + return + LAZYADD(listeners, target) + ADD_TRAIT(target, TRAIT_CAN_HEAR_MUSIC, REF(src)) + RegisterSignal(target, COMSIG_QDELETING, PROC_REF(remove_mob)) + +/datum/proximity_monitor/advanced/dj_music/proc/remove_mob(mob/living/target) + if(!isliving(target) || !(target in listeners)) + return + LAZYREMOVE(listeners, target) + REMOVE_TRAIT(target, TRAIT_CAN_HEAR_MUSIC, REF(src)) + UnregisterSignal(target, COMSIG_QDELETING) diff --git a/monkestation/code/modules/cassettes/dj/intercom.dm b/monkestation/code/modules/cassettes/dj/intercom.dm new file mode 100644 index 000000000000..5c12cc6cd5ac --- /dev/null +++ b/monkestation/code/modules/cassettes/dj/intercom.dm @@ -0,0 +1,13 @@ +/obj/item/radio/intercom + /// The proximity monitor used to allow people to hear DJ music while in hearing range. + var/datum/proximity_monitor/advanced/dj_music/music_field + +/obj/item/radio/intercom/Initialize(mapload, ndir, building) + . = ..() + var/range = isnull(listening_range) ? canhear_range : listening_range + if(isturf(loc) && range > 0 && (is_station_level(loc.z) || is_centcom_level(loc.z))) + music_field = new(src, range) + +/obj/item/radio/intercom/Destroy() + QDEL_NULL(music_field) + return ..() diff --git a/monkestation/code/modules/cassettes/dj/mob_can_hear.dm b/monkestation/code/modules/cassettes/dj/mob_can_hear.dm new file mode 100644 index 000000000000..4c09e1cd1406 --- /dev/null +++ b/monkestation/code/modules/cassettes/dj/mob_can_hear.dm @@ -0,0 +1,29 @@ +/// A list of all mobs that can hear music. +GLOBAL_LIST_EMPTY_TYPED(music_listeners, /mob) + +/mob/Initialize(mapload) + . = ..() + RegisterSignal(src, SIGNAL_ADDTRAIT(TRAIT_CAN_HEAR_MUSIC), PROC_REF(on_can_hear_music_trait_gain)) + RegisterSignal(src, SIGNAL_REMOVETRAIT(TRAIT_CAN_HEAR_MUSIC), PROC_REF(on_can_hear_music_trait_loss)) + + // just in case we already have the trait + if(HAS_TRAIT(src, TRAIT_CAN_HEAR_MUSIC)) + on_can_hear_music_trait_gain(src) + +/mob/Destroy(force) + on_can_hear_music_trait_loss(src) + return ..() + +/mob/proc/on_can_hear_music_trait_gain(datum/source) + SIGNAL_HANDLER + if(src in GLOB.music_listeners) + return + GLOB.music_listeners += src + SEND_GLOBAL_SIGNAL(COMSIG_GLOB_ADD_MUSIC_LISTENER, src) + +/mob/proc/on_can_hear_music_trait_loss(datum/source) + SIGNAL_HANDLER + if(!(src in GLOB.music_listeners)) + return + GLOB.music_listeners -= src + SEND_GLOBAL_SIGNAL(COMSIG_GLOB_REMOVE_MUSIC_LISTENER, src) diff --git a/monkestation/code/modules/cassettes/machines/cassette_rack.dm b/monkestation/code/modules/cassettes/machines/cassette_rack.dm index 9abbeabb0371..f6c683baadba 100644 --- a/monkestation/code/modules/cassettes/machines/cassette_rack.dm +++ b/monkestation/code/modules/cassettes/machines/cassette_rack.dm @@ -29,7 +29,7 @@ /datum/storage/cassette_rack/New() . = ..() - set_holdable(/obj/item/device/cassette_tape) + set_holdable(/obj/item/cassette_tape) // Allow opening on a normal left click /datum/storage/cassette_rack/on_attack(datum/source, mob/user) @@ -50,9 +50,9 @@ REGISTER_REQUIRED_MAP_ITEM(1, INFINITY) RegisterSignal(SSdcs, COMSIG_GLOB_CREWMEMBER_JOINED, PROC_REF(spawn_curator_tapes)) for(var/i in 1 to spawn_blanks) - new /obj/item/device/cassette_tape/blank(src) + new /obj/item/cassette_tape/blank(src) for(var/id in unique_random_tapes(spawn_random)) - new /obj/item/device/cassette_tape(src, id) + new /obj/item/cassette_tape(src, id) update_appearance() /obj/structure/cassette_rack/prefilled/Destroy() @@ -68,23 +68,17 @@ add_user_tapes(new_crewmember.ckey) /obj/structure/cassette_rack/prefilled/proc/add_user_tapes(user_ckey, max_amt = 3, expand_max_size = TRUE) - var/list/user_tapes = SScassette_storage.get_cassettes_by_ckey(user_ckey) - if(!length(user_tapes)) - return FALSE - var/list/existing_tapes = list() - for(var/obj/item/device/cassette_tape/tape in src) - if(tape.id) - existing_tapes[tape.id] = TRUE - for(var/iter in 1 to max_amt) - if(!length(user_tapes)) - break - var/datum/cassette_data/tape = pick_n_take(user_tapes) - if(existing_tapes[tape.cassette_id]) - continue - new /obj/item/device/cassette_tape(src, tape.cassette_id) - if(expand_max_size && !QDELETED(atom_storage)) - atom_storage.max_slots += max_amt - atom_storage.max_total_storage += max_amt * WEIGHT_CLASS_SMALL + var/list/existing_cassettes = list() + for(var/obj/item/cassette_tape/tape in src) + if(tape.cassette_data.id) + existing_cassettes |= tape.cassette_data.id + var/amount_spawned = 0 + for(var/datum/cassette/cassette as anything in SScassettes.unique_random_cassettes(max_amt, CASSETTE_STATUS_APPROVED, user_ckey, existing_cassettes)) + new /obj/item/cassette_tape(src, cassette) + amount_spawned++ + if(expand_max_size && !QDELETED(atom_storage) && amount_spawned > 0) + atom_storage.max_slots += amount_spawned + atom_storage.max_total_storage += amount_spawned * WEIGHT_CLASS_SMALL return TRUE #undef DEFAULT_BLANKS_TO_SPAWN diff --git a/monkestation/code/modules/cassettes/machines/dj_station.dm b/monkestation/code/modules/cassettes/machines/dj_station.dm index 386de43c5f57..a7742247f810 100644 --- a/monkestation/code/modules/cassettes/machines/dj_station.dm +++ b/monkestation/code/modules/cassettes/machines/dj_station.dm @@ -1,6 +1,5 @@ GLOBAL_VAR(dj_broadcast) -GLOBAL_VAR(dj_booth) - +GLOBAL_DATUM(dj_booth, /obj/machinery/cassette/dj_station) /obj/item/clothing/ears //can we be used to listen to radio? @@ -8,42 +7,35 @@ GLOBAL_VAR(dj_booth) /obj/machinery/cassette/dj_station name = "Cassette Player" - desc = "Plays Space Music Board approved cassettes for anyone in the station to listen to " + desc = "Plays Space Music Board approved cassettes for anyone in the station to listen to." icon = 'monkestation/code/modules/cassettes/icons/radio_station.dmi' icon_state = "cassette_player" - active_power_usage = BASE_MACHINE_ACTIVE_CONSUMPTION + use_power = NO_POWER_USE + + resistance_flags = INDESTRUCTIBLE | LAVA_PROOF | FIRE_PROOF | UNACIDABLE | ACID_PROOF + move_resist = MOVE_FORCE_OVERPOWERING - resistance_flags = INDESTRUCTIBLE anchored = TRUE density = TRUE - var/broadcasting = FALSE - var/obj/item/device/cassette_tape/inserted_tape - var/time_left = 0 - var/current_song_duration = 0 - var/list/people_with_signals = list() - var/list/active_listeners = list() - var/waiting_for_yield = FALSE - - //tape stuff goes here - var/pl_index = 0 - var/list/current_playlist = list() - var/list/current_namelist = list() + var/broadcasting = FALSE COOLDOWN_DECLARE(next_song_timer) /obj/machinery/cassette/dj_station/Initialize(mapload) . = ..() REGISTER_REQUIRED_MAP_ITEM(1, INFINITY) - GLOB.dj_booth = src register_context() + if(QDELETED(GLOB.dj_booth)) + GLOB.dj_booth = src /obj/machinery/cassette/dj_station/Destroy() - . = ..() - GLOB.dj_booth = null - STOP_PROCESSING(SSprocessing, src) + if(GLOB.dj_booth == src) + GLOB.dj_booth = null + return ..() +/* /obj/machinery/cassette/dj_station/add_context(atom/source, list/context, obj/item/held_item, mob/user) . = ..() if(inserted_tape) @@ -51,327 +43,4 @@ GLOBAL_VAR(dj_booth) if(!broadcasting) context[SCREENTIP_CONTEXT_LMB] = "Play Tape" return CONTEXTUAL_SCREENTIP_SET - -/obj/machinery/cassette/dj_station/examine(mob/user) - . = ..() - if(time_left > 0 || next_song_timer) - . += span_notice("It seems to be cooling down, you estimate it will take about [time_left ? DisplayTimeText(((time_left * 10) + 6000)) : DisplayTimeText(COOLDOWN_TIMELEFT(src, next_song_timer))].") - -/obj/machinery/cassette/dj_station/process(seconds_per_tick) - if(waiting_for_yield) - return - time_left -= round(seconds_per_tick) - if(time_left <= 0) - time_left = 0 - if(COOLDOWN_FINISHED(src, next_song_timer) && broadcasting) - COOLDOWN_START(src, next_song_timer, 10 MINUTES) - broadcasting = FALSE - -/obj/machinery/cassette/dj_station/attack_hand(mob/user) - . = ..() - if(!inserted_tape) - return - if((!COOLDOWN_FINISHED(src, next_song_timer)) && !broadcasting) - to_chat(user, span_notice("The [src] feels hot to the touch and needs time to cooldown.")) - to_chat(user, span_info("You estimate it will take about [time_left ? DisplayTimeText(((time_left * 10) + 6000)) : DisplayTimeText(COOLDOWN_TIMELEFT(src, next_song_timer))] to cool down.")) - return - message_admins("[src] started broadcasting [inserted_tape] interacted with by [user]") - logger.Log(LOG_CATEGORY_MUSIC, "[src] started broadcasting [inserted_tape]") - start_broadcast() - -/obj/machinery/cassette/dj_station/AltClick(mob/user) - . = ..() - if(!isliving(user) || !user.Adjacent(src)) - return - if(!inserted_tape) - return - if(broadcasting) - next_song() - -/obj/machinery/cassette/dj_station/CtrlClick(mob/user) - . = ..() - if(!inserted_tape || broadcasting) - return - if(Adjacent(user) && !issiliconoradminghost(user)) - if(!user.put_in_hands(inserted_tape)) - inserted_tape.forceMove(drop_location()) - else - inserted_tape.forceMove(drop_location()) - inserted_tape = null - time_left = 0 - current_song_duration = 0 - pl_index = 0 - current_playlist = list() - current_namelist = list() - stop_broadcast(TRUE) - -/obj/machinery/cassette/dj_station/attackby(obj/item/weapon, mob/user, params) - if(!istype(weapon, /obj/item/device/cassette_tape)) - return - var/obj/item/device/cassette_tape/attacked = weapon - if(!attacked.approved_tape) - to_chat(user, span_warning("The [src] smartly rejects the bootleg cassette tape")) - return - if(!inserted_tape) - insert_tape(attacked) - else - if(!broadcasting) - if(Adjacent(user) && !issiliconoradminghost(user)) - if(!user.put_in_hands(inserted_tape)) - inserted_tape.forceMove(drop_location()) - else - inserted_tape.forceMove(drop_location()) - inserted_tape = null - time_left = 0 - current_song_duration = 0 - pl_index = 0 - current_playlist = list() - current_namelist = list() - insert_tape(attacked) - if(broadcasting) - stop_broadcast(TRUE) - -/obj/machinery/cassette/dj_station/proc/insert_tape(obj/item/device/cassette_tape/CTape) - if(inserted_tape || !istype(CTape)) - return - - inserted_tape = CTape - CTape.forceMove(src) - - update_appearance() - pl_index = 1 - if(inserted_tape.songs["side1"] && inserted_tape.songs["side2"]) - var/list/list = inserted_tape.songs["[inserted_tape.flipped ? "side2" : "side1"]"] - for(var/song in list) - current_playlist += song - - var/list/name_list = inserted_tape.song_names["[inserted_tape.flipped ? "side2" : "side1"]"] - for(var/song in name_list) - current_namelist += song - -/obj/machinery/cassette/dj_station/proc/stop_broadcast(soft = FALSE) - STOP_PROCESSING(SSprocessing, src) - GLOB.dj_broadcast = FALSE - broadcasting = FALSE - message_admins("[src] has stopped broadcasting [inserted_tape].") - logger.Log(LOG_CATEGORY_MUSIC, "[src] has stopped broadcasting [inserted_tape]") - for(var/client/anything as anything in active_listeners) - if(!istype(anything)) - continue - anything.tgui_panel?.stop_music() - GLOB.youtube_exempt["dj-station"] -= anything - active_listeners = list() - - if(!soft) - for(var/mob/living/carbon/anything as anything in people_with_signals) - if(!istype(anything)) - continue - UnregisterSignal(anything, COMSIG_CARBON_UNEQUIP_EARS) - UnregisterSignal(anything, COMSIG_CARBON_EQUIP_EARS) - UnregisterSignal(anything, COMSIG_MOVABLE_Z_CHANGED) - people_with_signals = list() - -/obj/machinery/cassette/dj_station/proc/start_broadcast() - var/choice = tgui_input_list(usr, "Choose which song to play.", "[src]", current_namelist) - if(!choice) - return - var/list_index = current_namelist.Find(choice) - if(!list_index) - return - GLOB.dj_broadcast = TRUE - pl_index = list_index - - var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM, ZTRAIT_RESERVED)) - for(var/mob/person as anything in GLOB.player_list) - if(issilicon(person) || isobserver(person) || isaicamera(person) || isbot(person)) - active_listeners |= person.client - continue - if(iscarbon(person)) - var/mob/living/carbon/anything = person - if(!(anything in people_with_signals)) - if(!istype(anything)) - continue - - RegisterSignal(anything, COMSIG_CARBON_UNEQUIP_EARS, PROC_REF(stop_solo_broadcast)) - RegisterSignal(anything, COMSIG_CARBON_EQUIP_EARS, PROC_REF(check_solo_broadcast)) - RegisterSignal(anything, COMSIG_MOVABLE_Z_CHANGED, PROC_REF(check_solo_broadcast)) - people_with_signals |= anything - - if(!(anything.client in active_listeners)) - if(!(anything.z in viable_z)) - continue - - if(!anything.client) - continue - - if(anything.client in GLOB.youtube_exempt["walkman"]) - continue - - var/obj/item/ear_slot = anything.get_item_by_slot(ITEM_SLOT_EARS) - if(istype(ear_slot, /obj/item/clothing/ears)) - var/obj/item/clothing/ears/worn - if(!worn || !worn?.radio_compat) - continue - else if(!istype(ear_slot, /obj/item/radio/headset)) - continue - - if(!anything.client.prefs?.read_preference(/datum/preference/toggle/hear_music)) - continue - - active_listeners |= anything.client - - if(!length(active_listeners)) - return - - start_playing(active_listeners) - START_PROCESSING(SSprocessing, src) - - -/obj/machinery/cassette/dj_station/proc/check_solo_broadcast(mob/living/carbon/source, obj/item/clothing/ears/ear_item) - SIGNAL_HANDLER - - if(!istype(source)) - return - - if(istype(ear_item, /obj/item/clothing/ears)) - var/obj/item/clothing/ears/worn - if(!worn || !worn?.radio_compat) - return - else if(!istype(ear_item, /obj/item/radio/headset)) - return - - var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM)) - if(!(source.z in viable_z) || !source.client) - return - - if(!source.client.prefs?.read_preference(/datum/preference/toggle/hear_music)) - return - - active_listeners |= source.client - GLOB.youtube_exempt["dj-station"] |= source.client - INVOKE_ASYNC(src, PROC_REF(start_playing),list(source.client)) - -/obj/machinery/cassette/dj_station/proc/stop_solo_broadcast(mob/living/carbon/source) - SIGNAL_HANDLER - - if(!source.client || !(source.client in active_listeners)) - return - - active_listeners -= source.client - GLOB.youtube_exempt["dj-station"] -= source.client - source.client.tgui_panel?.stop_music() - -/obj/machinery/cassette/dj_station/proc/start_playing(list/clients) - if(!inserted_tape) - if(broadcasting) - stop_broadcast(TRUE) - return - - waiting_for_yield = TRUE - if(findtext(current_playlist[pl_index], GLOB.is_http_protocol)) - ///invoking youtube-dl - var/ytdl = CONFIG_GET(string/invoke_youtubedl) - ///the input for ytdl handled by the song list - var/web_sound_input - ///the url for youtube-dl - var/web_sound_url = "" - ///all extra data from the youtube-dl really want the name - var/list/music_extra_data = list() - web_sound_input = trim(current_playlist[pl_index]) - if(!(web_sound_input in GLOB.parsed_audio)) - ///scrubbing the input before putting it in the shell - var/shell_scrubbed_input = shell_url_scrub(web_sound_input) - ///putting it in the shell - var/list/output = world.shelleo("[ytdl] --geo-bypass --format \"bestaudio\[ext=mp3]/best\[ext=mp4]\[height <= 360]/bestaudio\[ext=m4a]/bestaudio\[ext=aac]\" --dump-single-json --no-playlist --extractor-args \"youtube:lang=en\" -- \"[shell_scrubbed_input]\"") - ///any errors - var/errorlevel = output[SHELLEO_ERRORLEVEL] - ///the standard output - var/stdout = output[SHELLEO_STDOUT] - if(!errorlevel) - ///list for all the output data to go to - var/list/data - try - data = json_decode(stdout) - catch(var/exception/error) ///catch errors here - to_chat(src, "Youtube-dl JSON parsing FAILED:", confidential = TRUE) - to_chat(src, "[error]: [stdout]", confidential = TRUE) - return - - if (data["url"]) - web_sound_url = data["url"] - music_extra_data["start"] = data["start_time"] - music_extra_data["end"] = data["end_time"] - music_extra_data["link"] = data["webpage_url"] - music_extra_data["title"] = data["title"] - if(music_extra_data["start"]) - time_left = data["duration"] - music_extra_data["start"] - else - time_left = data["duration"] - - current_song_duration = data["duration"] - - GLOB.parsed_audio["[web_sound_input]"] = data - else - var/list/data = GLOB.parsed_audio["[web_sound_input]"] - web_sound_url = data["url"] - music_extra_data["start"] = data["start_time"] - music_extra_data["end"] = data["end_time"] - music_extra_data["link"] = data["webpage_url"] - music_extra_data["title"] = data["title"] - if(time_left <= 0) - if(music_extra_data["start"]) - time_left = data["duration"] - music_extra_data["start"] - else - time_left = data["duration"] - - current_song_duration = data["duration"] - music_extra_data["duration"] = data["duration"] - - if(time_left > 0) - music_extra_data["start"] = music_extra_data["duration"] - time_left - - for(var/client/anything as anything in clients) - if(!istype(anything)) - continue - anything.tgui_panel?.play_music(web_sound_url, music_extra_data) - GLOB.youtube_exempt["dj-station"] |= anything - broadcasting = TRUE - waiting_for_yield = FALSE - -/obj/machinery/cassette/dj_station/proc/add_new_player(mob/living/carbon/new_player) - if(!(new_player in people_with_signals)) - RegisterSignal(new_player, COMSIG_CARBON_UNEQUIP_EARS, PROC_REF(stop_solo_broadcast)) - RegisterSignal(new_player, COMSIG_CARBON_EQUIP_EARS, PROC_REF(check_solo_broadcast)) - RegisterSignal(new_player, COMSIG_MOVABLE_Z_CHANGED, PROC_REF(check_solo_broadcast)) - people_with_signals |= new_player - - if(!broadcasting) - return - - var/obj/item/ear_slot = new_player.get_item_by_slot(ITEM_SLOT_EARS) - if(istype(ear_slot, /obj/item/clothing/ears)) - var/obj/item/clothing/ears/worn - if(!worn || !worn?.radio_compat) - return - else if(!istype(ear_slot, /obj/item/radio/headset)) - return - var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM)) - if(!(new_player.z in viable_z)) - return - - if(!(new_player.client in active_listeners)) - active_listeners |= new_player.client - start_playing(list(new_player.client)) - -/obj/machinery/cassette/dj_station/proc/next_song() - waiting_for_yield = TRUE - var/choice = tgui_input_number(usr, "Choose which song number to play.", "[src]", 1, length(current_playlist), 1) - if(!choice) - waiting_for_yield = FALSE - stop_broadcast() - return - GLOB.dj_broadcast = TRUE - pl_index = choice - - pl_index++ - start_playing(active_listeners) +*/ diff --git a/monkestation/code/modules/cassettes/machines/dj_station_old.dm b/monkestation/code/modules/cassettes/machines/dj_station_old.dm new file mode 100644 index 000000000000..f9b24f679fc8 --- /dev/null +++ b/monkestation/code/modules/cassettes/machines/dj_station_old.dm @@ -0,0 +1,377 @@ +GLOBAL_VAR(dj_broadcast) +GLOBAL_DATUM(dj_booth, /obj/machinery/cassette/dj_station) + +/obj/item/clothing/ears + //can we be used to listen to radio? + var/radio_compat = FALSE + +/obj/machinery/cassette/dj_station + name = "Cassette Player" + desc = "Plays Space Music Board approved cassettes for anyone in the station to listen to." + + icon = 'monkestation/code/modules/cassettes/icons/radio_station.dmi' + icon_state = "cassette_player" + + active_power_usage = BASE_MACHINE_ACTIVE_CONSUMPTION + + resistance_flags = INDESTRUCTIBLE + anchored = TRUE + density = TRUE + var/broadcasting = FALSE + var/obj/item/cassette_tape/inserted_tape + var/time_left = 0 + var/current_song_duration = 0 + var/list/people_with_signals = list() + var/list/active_listeners = list() + var/waiting_for_yield = FALSE + + //tape stuff goes here + var/pl_index = 0 + var/list/current_playlist = list() + var/list/current_namelist = list() + + COOLDOWN_DECLARE(next_song_timer) + +/obj/machinery/cassette/dj_station/Initialize(mapload) + . = ..() + REGISTER_REQUIRED_MAP_ITEM(1, INFINITY) + register_context() + if(QDELETED(GLOB.dj_booth)) + GLOB.dj_booth = src + +/obj/machinery/cassette/dj_station/Destroy() + if(GLOB.dj_booth == src) + GLOB.dj_booth = null + return ..() + +/obj/machinery/cassette/dj_station/add_context(atom/source, list/context, obj/item/held_item, mob/user) + . = ..() + if(inserted_tape) + context[SCREENTIP_CONTEXT_CTRL_LMB] = "Eject Tape" + if(!broadcasting) + context[SCREENTIP_CONTEXT_LMB] = "Play Tape" + return CONTEXTUAL_SCREENTIP_SET + +/obj/machinery/cassette/dj_station/examine(mob/user) + . = ..() + if(time_left > 0 || next_song_timer) + . += span_notice("It seems to be cooling down, you estimate it will take about [time_left ? DisplayTimeText(((time_left * 10) + 6000)) : DisplayTimeText(COOLDOWN_TIMELEFT(src, next_song_timer))].") + +/obj/machinery/cassette/dj_station/process(seconds_per_tick) + if(waiting_for_yield) + return + time_left -= round(seconds_per_tick) + if(time_left <= 0) + time_left = 0 + if(COOLDOWN_FINISHED(src, next_song_timer) && broadcasting) + COOLDOWN_START(src, next_song_timer, 10 MINUTES) + broadcasting = FALSE + +/obj/machinery/cassette/dj_station/attack_hand(mob/user) + . = ..() + if(!inserted_tape) + return + if((!COOLDOWN_FINISHED(src, next_song_timer)) && !broadcasting) + to_chat(user, span_notice("The [src] feels hot to the touch and needs time to cooldown.")) + to_chat(user, span_info("You estimate it will take about [time_left ? DisplayTimeText(((time_left * 10) + 6000)) : DisplayTimeText(COOLDOWN_TIMELEFT(src, next_song_timer))] to cool down.")) + return + message_admins("[src] started broadcasting [inserted_tape] interacted with by [user]") + logger.Log(LOG_CATEGORY_MUSIC, "[src] started broadcasting [inserted_tape]") + start_broadcast() + +/obj/machinery/cassette/dj_station/AltClick(mob/user) + . = ..() + if(!isliving(user) || !user.Adjacent(src)) + return + if(!inserted_tape) + return + if(broadcasting) + next_song() + +/obj/machinery/cassette/dj_station/CtrlClick(mob/user) + . = ..() + if(!inserted_tape || broadcasting) + return + if(Adjacent(user) && !issiliconoradminghost(user)) + if(!user.put_in_hands(inserted_tape)) + inserted_tape.forceMove(drop_location()) + else + inserted_tape.forceMove(drop_location()) + inserted_tape = null + time_left = 0 + current_song_duration = 0 + pl_index = 0 + current_playlist = list() + current_namelist = list() + stop_broadcast(TRUE) + +/obj/machinery/cassette/dj_station/attackby(obj/item/weapon, mob/user, params) + if(!istype(weapon, /obj/item/cassette_tape)) + return + var/obj/item/cassette_tape/attacked = weapon + if(!attacked.approved_tape) + to_chat(user, span_warning("The [src] smartly rejects the bootleg cassette tape")) + return + if(!inserted_tape) + insert_tape(attacked) + else + if(!broadcasting) + if(Adjacent(user) && !issiliconoradminghost(user)) + if(!user.put_in_hands(inserted_tape)) + inserted_tape.forceMove(drop_location()) + else + inserted_tape.forceMove(drop_location()) + inserted_tape = null + time_left = 0 + current_song_duration = 0 + pl_index = 0 + current_playlist = list() + current_namelist = list() + insert_tape(attacked) + if(broadcasting) + stop_broadcast(TRUE) + +/obj/machinery/cassette/dj_station/proc/insert_tape(obj/item/cassette_tape/CTape) + if(inserted_tape || !istype(CTape)) + return + + inserted_tape = CTape + CTape.forceMove(src) + + update_appearance() + pl_index = 1 + if(inserted_tape.songs["side1"] && inserted_tape.songs["side2"]) + var/list/list = inserted_tape.songs["[inserted_tape.flipped ? "side2" : "side1"]"] + for(var/song in list) + current_playlist += song + + var/list/name_list = inserted_tape.song_names["[inserted_tape.flipped ? "side2" : "side1"]"] + for(var/song in name_list) + current_namelist += song + +/obj/machinery/cassette/dj_station/proc/stop_broadcast(soft = FALSE) + STOP_PROCESSING(SSprocessing, src) + GLOB.dj_broadcast = FALSE + broadcasting = FALSE + message_admins("[src] has stopped broadcasting [inserted_tape].") + logger.Log(LOG_CATEGORY_MUSIC, "[src] has stopped broadcasting [inserted_tape]") + for(var/client/anything as anything in active_listeners) + if(!istype(anything)) + continue + anything.tgui_panel?.stop_music() + GLOB.youtube_exempt["dj-station"] -= anything + active_listeners = list() + + if(!soft) + for(var/mob/living/carbon/anything as anything in people_with_signals) + if(!istype(anything)) + continue + UnregisterSignal(anything, COMSIG_CARBON_UNEQUIP_EARS) + UnregisterSignal(anything, COMSIG_CARBON_EQUIP_EARS) + UnregisterSignal(anything, COMSIG_MOVABLE_Z_CHANGED) + people_with_signals = list() + +/obj/machinery/cassette/dj_station/proc/start_broadcast() + var/choice = tgui_input_list(usr, "Choose which song to play.", "[src]", current_namelist) + if(!choice) + return + var/list_index = current_namelist.Find(choice) + if(!list_index) + return + GLOB.dj_broadcast = TRUE + pl_index = list_index + + var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM, ZTRAIT_RESERVED)) + for(var/mob/person as anything in GLOB.player_list) + if(issilicon(person) || isobserver(person) || isaicamera(person) || isbot(person)) + active_listeners |= person.client + continue + if(iscarbon(person)) + var/mob/living/carbon/anything = person + if(!(anything in people_with_signals)) + if(!istype(anything)) + continue + + RegisterSignal(anything, COMSIG_CARBON_UNEQUIP_EARS, PROC_REF(stop_solo_broadcast)) + RegisterSignal(anything, COMSIG_CARBON_EQUIP_EARS, PROC_REF(check_solo_broadcast)) + RegisterSignal(anything, COMSIG_MOVABLE_Z_CHANGED, PROC_REF(check_solo_broadcast)) + people_with_signals |= anything + + if(!(anything.client in active_listeners)) + if(!(anything.z in viable_z)) + continue + + if(!anything.client) + continue + + if(anything.client in GLOB.youtube_exempt["walkman"]) + continue + + var/obj/item/ear_slot = anything.get_item_by_slot(ITEM_SLOT_EARS) + if(istype(ear_slot, /obj/item/clothing/ears)) + var/obj/item/clothing/ears/worn + if(!worn || !worn?.radio_compat) + continue + else if(!istype(ear_slot, /obj/item/radio/headset)) + continue + + if(!anything.client.prefs?.read_preference(/datum/preference/toggle/hear_music)) + continue + + active_listeners |= anything.client + + if(!length(active_listeners)) + return + + start_playing(active_listeners) + START_PROCESSING(SSprocessing, src) + + +/obj/machinery/cassette/dj_station/proc/check_solo_broadcast(mob/living/carbon/source, obj/item/clothing/ears/ear_item) + SIGNAL_HANDLER + + if(!istype(source)) + return + + if(istype(ear_item, /obj/item/clothing/ears)) + var/obj/item/clothing/ears/worn + if(!worn || !worn?.radio_compat) + return + else if(!istype(ear_item, /obj/item/radio/headset)) + return + + var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM)) + if(!(source.z in viable_z) || !source.client) + return + + if(!source.client.prefs?.read_preference(/datum/preference/toggle/hear_music)) + return + + active_listeners |= source.client + GLOB.youtube_exempt["dj-station"] |= source.client + INVOKE_ASYNC(src, PROC_REF(start_playing),list(source.client)) + +/obj/machinery/cassette/dj_station/proc/stop_solo_broadcast(mob/living/carbon/source) + SIGNAL_HANDLER + + if(!source.client || !(source.client in active_listeners)) + return + + active_listeners -= source.client + GLOB.youtube_exempt["dj-station"] -= source.client + source.client.tgui_panel?.stop_music() + +/obj/machinery/cassette/dj_station/proc/start_playing(list/clients) + if(!inserted_tape) + if(broadcasting) + stop_broadcast(TRUE) + return + + waiting_for_yield = TRUE + if(is_http_protocol(current_playlist[pl_index])) + ///invoking youtube-dl + var/ytdl = CONFIG_GET(string/invoke_youtubedl) + ///the input for ytdl handled by the song list + var/web_sound_input + ///the url for youtube-dl + var/web_sound_url = "" + ///all extra data from the youtube-dl really want the name + var/list/music_extra_data = list() + web_sound_input = trim(current_playlist[pl_index]) + if(!(web_sound_input in GLOB.parsed_audio)) + ///scrubbing the input before putting it in the shell + var/shell_scrubbed_input = shell_url_scrub(web_sound_input) + ///putting it in the shell + var/list/output = world.shelleo("[ytdl] --geo-bypass --format \"bestaudio\[ext=mp3]/best\[ext=mp4]\[height <= 360]/bestaudio\[ext=m4a]/bestaudio\[ext=aac]\" --dump-single-json --no-playlist --extractor-args \"youtube:lang=en\" -- \"[shell_scrubbed_input]\"") + ///any errors + var/errorlevel = output[SHELLEO_ERRORLEVEL] + ///the standard output + var/stdout = output[SHELLEO_STDOUT] + if(!errorlevel) + ///list for all the output data to go to + var/list/data + try + data = json_decode(stdout) + catch(var/exception/error) ///catch errors here + to_chat(src, "Youtube-dl JSON parsing FAILED:", confidential = TRUE) + to_chat(src, "[error]: [stdout]", confidential = TRUE) + return + + if (data["url"]) + web_sound_url = data["url"] + music_extra_data["start"] = data["start_time"] + music_extra_data["end"] = data["end_time"] + music_extra_data["link"] = data["webpage_url"] + music_extra_data["title"] = data["title"] + if(music_extra_data["start"]) + time_left = data["duration"] - music_extra_data["start"] + else + time_left = data["duration"] + + current_song_duration = data["duration"] + + GLOB.parsed_audio["[web_sound_input]"] = data + else + var/list/data = GLOB.parsed_audio["[web_sound_input]"] + web_sound_url = data["url"] + music_extra_data["start"] = data["start_time"] + music_extra_data["end"] = data["end_time"] + music_extra_data["link"] = data["webpage_url"] + music_extra_data["title"] = data["title"] + if(time_left <= 0) + if(music_extra_data["start"]) + time_left = data["duration"] - music_extra_data["start"] + else + time_left = data["duration"] + + current_song_duration = data["duration"] + music_extra_data["duration"] = data["duration"] + + if(time_left > 0) + music_extra_data["start"] = music_extra_data["duration"] - time_left + + for(var/client/anything as anything in clients) + if(!istype(anything)) + continue + anything.tgui_panel?.play_music(web_sound_url, music_extra_data) + GLOB.youtube_exempt["dj-station"] |= anything + broadcasting = TRUE + waiting_for_yield = FALSE + +/obj/machinery/cassette/dj_station/proc/add_new_player(mob/living/carbon/new_player) + if(!(new_player in people_with_signals)) + RegisterSignal(new_player, COMSIG_CARBON_UNEQUIP_EARS, PROC_REF(stop_solo_broadcast)) + RegisterSignal(new_player, COMSIG_CARBON_EQUIP_EARS, PROC_REF(check_solo_broadcast)) + RegisterSignal(new_player, COMSIG_MOVABLE_Z_CHANGED, PROC_REF(check_solo_broadcast)) + people_with_signals |= new_player + + if(!broadcasting) + return + + var/obj/item/ear_slot = new_player.get_item_by_slot(ITEM_SLOT_EARS) + if(istype(ear_slot, /obj/item/clothing/ears)) + var/obj/item/clothing/ears/worn + if(!worn || !worn?.radio_compat) + return + else if(!istype(ear_slot, /obj/item/radio/headset)) + return + var/list/viable_z = SSmapping.levels_by_any_trait(list(ZTRAIT_STATION, ZTRAIT_MINING, ZTRAIT_CENTCOM)) + if(!(new_player.z in viable_z)) + return + + if(!(new_player.client in active_listeners)) + active_listeners |= new_player.client + start_playing(list(new_player.client)) + +/obj/machinery/cassette/dj_station/proc/next_song() + waiting_for_yield = TRUE + var/choice = tgui_input_number(usr, "Choose which song number to play.", "[src]", 1, length(current_playlist), 1) + if(!choice) + waiting_for_yield = FALSE + stop_broadcast() + return + GLOB.dj_broadcast = TRUE + pl_index = choice + + pl_index++ + start_playing(active_listeners) diff --git a/monkestation/code/modules/cassettes/machines/portable_mixer.dm b/monkestation/code/modules/cassettes/machines/portable_mixer.dm index 4f95b833c7da..a3f77b0639e4 100644 --- a/monkestation/code/modules/cassettes/machines/portable_mixer.dm +++ b/monkestation/code/modules/cassettes/machines/portable_mixer.dm @@ -1,3 +1,4 @@ +#warn TODO: cassette mixer /obj/item/device/cassette_deck name = "Dual Cassette Deck" desc = "A Dual Cassette Deck, popular for its ability to copy songs from a cassette. A relic of the old times" @@ -5,13 +6,13 @@ icon_state = "walkman" w_class = WEIGHT_CLASS_SMALL ///The cassette that is being copied from - var/obj/item/device/cassette_tape/send + var/obj/item/cassette_tape/send ///List of songs the sender has var/list/sender_list ///List of names the Sender has var/list/sender_names ///The cassette you are copying to - var/obj/item/device/cassette_tape/recieve + var/obj/item/cassette_tape/recieve ///List of songs the Reciever has var/list/reciever_list ///List of song names the Reciever has @@ -23,7 +24,7 @@ /obj/item/device/cassette_deck/AltClick(mob/user) if(recieve || send) - eject_tape(user) + //eject_tape(user) return return ..() @@ -32,15 +33,16 @@ removal = !removal /obj/item/device/cassette_deck/attackby(obj/item/cassette, mob/user) - if(!istype(cassette, /obj/item/device/cassette_tape)) + if(!istype(cassette, /obj/item/cassette_tape)) return if(!send || !recieve) - insert_tape(cassette) + //insert_tape(cassette) playsound(src,'sound/weapons/handcuffs.ogg',20,1) to_chat(user,("You insert \the [cassette] into \the [src]")) else to_chat(user,("Remove a tape first!")) +/* /obj/item/device/cassette_deck/attack_self(mob/user) . = ..() if(!recieve) @@ -76,7 +78,7 @@ reciever_list.Remove(reciever_list[num]) reciever_names.Remove(reciever_names[num]) -/obj/item/device/cassette_deck/proc/insert_tape(obj/item/device/cassette_tape/CTape) +/obj/item/device/cassette_deck/proc/insert_tape(obj/item/cassette_tape/CTape) if(send && recieve || !istype(CTape)) return @@ -113,3 +115,4 @@ send = null broke_approval = FALSE playsound(src,'sound/weapons/handcuffs.ogg',20,1) +*/ diff --git a/monkestation/code/modules/cassettes/machines/postbox.dm b/monkestation/code/modules/cassettes/machines/postbox.dm index 3b60a4326667..86d3767ed60b 100644 --- a/monkestation/code/modules/cassettes/machines/postbox.dm +++ b/monkestation/code/modules/cassettes/machines/postbox.dm @@ -1,3 +1,4 @@ +#warn TODO: cassette submission postbox /obj/machinery/cassette/mailbox name = "Space Board of Music Postbox" desc = "Has a slit specifically to fit cassettes into it." @@ -14,12 +15,12 @@ . = ..() REGISTER_REQUIRED_MAP_ITEM(1, INFINITY) - +/* /obj/machinery/cassette/mailbox/attackby(obj/item/weapon, mob/user, params) - if(!istype(weapon, /obj/item/device/cassette_tape) || !user.client) + if(!istype(weapon, /obj/item/cassette_tape) || !user.client) return - var/obj/item/device/cassette_tape/attacked_tape = weapon + var/obj/item/cassette_tape/attacked_tape = weapon var/list/admin_count = get_admin_counts(R_FUN) if(!length(admin_count["present"])) @@ -58,3 +59,4 @@ attacked_tape.moveToNullspace() submit_cassette_for_review(attacked_tape, user) return TRUE +*/ diff --git a/monkestation/code/modules/cassettes/machines/radio_mic.dm b/monkestation/code/modules/cassettes/machines/radio_mic.dm index 7336728ff584..7863adb076bc 100644 --- a/monkestation/code/modules/cassettes/machines/radio_mic.dm +++ b/monkestation/code/modules/cassettes/machines/radio_mic.dm @@ -26,6 +26,8 @@ /// overlay when speaking a message (is displayed simultaniously with speaker_active) overlay_mic_active = null + /// The proximity monitor used to allow people to hear DJ music while in hearing range. + var/datum/proximity_monitor/advanced/dj_music/music_field /obj/item/radio/radio_mic/Initialize(mapload) . = ..() @@ -40,6 +42,12 @@ set_broadcasting(TRUE) + music_field = new(src, isnull(listening_range) ? canhear_range : listening_range) + +/obj/item/radio/radio_mic/Destroy() + QDEL_NULL(music_field) + return ..() + /obj/item/radio/radio_mic/ui_interact(mob/user, datum/tgui/ui, datum/ui_state/state) return diff --git a/monkestation/code/modules/cassettes/machines/stationary_mixer.dm b/monkestation/code/modules/cassettes/machines/stationary_mixer.dm index 632e9426e8ae..ef901d9bcd6e 100644 --- a/monkestation/code/modules/cassettes/machines/stationary_mixer.dm +++ b/monkestation/code/modules/cassettes/machines/stationary_mixer.dm @@ -1,3 +1,4 @@ +#warn TODO: advanced cassette deck /obj/machinery/cassette/adv_cassette_deck name = "Advanced Cassette Deck" desc = "A more advanced less portable Cassette Deck. Useful for recording songs from our generation, or customizing the style of your cassettes." @@ -6,7 +7,7 @@ density = TRUE pass_flags = PASSTABLE ///cassette tape used in adding songs or customizing - var/obj/item/device/cassette_tape/tape + var/obj/item/cassette_tape/tape ///Selection used to remove songs var/selection @@ -20,7 +21,7 @@ return TRUE /obj/machinery/cassette/adv_cassette_deck/attackby(obj/item/cassette, mob/user) - if(!istype(cassette, /obj/item/device/cassette_tape)) + if(!istype(cassette, /obj/item/cassette_tape)) return ..() if(!tape) insert_tape(cassette) @@ -29,7 +30,7 @@ else to_chat(user,"Remove a tape first!") -/obj/machinery/cassette/adv_cassette_deck/proc/insert_tape(obj/item/device/cassette_tape/CTape) +/obj/machinery/cassette/adv_cassette_deck/proc/insert_tape(obj/item/cassette_tape/CTape) if(tape || !istype(CTape)) return tape = CTape @@ -57,6 +58,7 @@ ui = new(user, src, "CassetteDeck", name) ui.open() +/* /obj/machinery/cassette/adv_cassette_deck/ui_data(mob/user) ///all data for the tgui var/list/data = list() @@ -193,3 +195,4 @@ else tape.icon_state = design_path[design_names.Find(selection)] tape.side2_icon = design_path[design_names.Find(selection)] +*/ diff --git a/monkestation/code/modules/cassettes/random_cassette_selection.dm b/monkestation/code/modules/cassettes/random_cassette_selection.dm index 19b27f0fdd81..0cc292301f09 100644 --- a/monkestation/code/modules/cassettes/random_cassette_selection.dm +++ b/monkestation/code/modules/cassettes/random_cassette_selection.dm @@ -17,7 +17,7 @@ GLOBAL_LIST_INIT(approved_ids, initialize_approved_ids()) return list() return json_decode(file2text(ids_exist)) -/obj/item/device/cassette_tape/random +/obj/item/cassette_tape/random name = "Not Correctly Created Random Cassette" desc = "How did this happen?" random = TRUE diff --git a/monkestation/code/modules/cassettes/walkman/_walkmen.dm b/monkestation/code/modules/cassettes/walkman/_walkmen.dm index 6eee606c9ff9..cbf0c6c76f39 100644 --- a/monkestation/code/modules/cassettes/walkman/_walkmen.dm +++ b/monkestation/code/modules/cassettes/walkman/_walkmen.dm @@ -1,3 +1,4 @@ +#warn TODO: walkmen GLOBAL_LIST_INIT(parsed_audio, list()) GLOBAL_LIST_INIT(youtube_exempt, list( @@ -15,7 +16,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( w_class = WEIGHT_CLASS_SMALL actions_types = list(/datum/action/item_action/walkman/play_pause,/datum/action/item_action/walkman/next_song,/datum/action/item_action/walkman/restart_song) ///the cassette tape object - var/obj/item/device/cassette_tape/tape + var/obj/item/cassette_tape/tape ///if the walkman is paused or not var/paused = TRUE ///songs inside the current playlist @@ -43,6 +44,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( ///cooldown used by the next song to stop overlapping sounds between url based songs and normal ones COOLDOWN_DECLARE(next_song_use) +/* /obj/item/device/walkman/Initialize() . = ..() design = rand(1, 5) @@ -58,7 +60,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( . = ..() /obj/item/device/walkman/attackby(obj/item/cassette, mob/user) - if(!istype(cassette, /obj/item/device/cassette_tape)) + if(!istype(cassette, /obj/item/cassette_tape)) return if(!tape) insert_tape(cassette) @@ -142,7 +144,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( /obj/item/device/walkman/proc/play() if(!current_song) if(current_playlist.len > 0) - if(findtext(current_playlist[pl_index], GLOB.is_http_protocol)) + if(is_http_protocol(current_playlist[pl_index])) ///invoking youtube-dl var/ytdl = CONFIG_GET(string/invoke_youtubedl) ///the input for ytdl handled by the song list @@ -232,9 +234,9 @@ GLOBAL_LIST_INIT(youtube_exempt, list( /*Called when - *Arguments: obj/item/device/cassette_tape/CT -> the cassette in question that you are inserting into the walkman + *Arguments: obj/item/cassette_tape/CT -> the cassette in question that you are inserting into the walkman */ -/obj/item/device/walkman/proc/insert_tape(obj/item/device/cassette_tape/CTape) +/obj/item/device/walkman/proc/insert_tape(obj/item/cassette_tape/CTape) if(tape || !istype(CTape)) return @@ -285,7 +287,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( break_sound() pl_index = pl_index + 1 <= current_playlist.len ? (pl_index += 1) : 1 - link_play = findtext(current_playlist[pl_index], GLOB.is_http_protocol) ? TRUE : FALSE + link_play = is_http_protocol(current_playlist[pl_index]) if(!link_play) @@ -359,6 +361,7 @@ GLOBAL_LIST_INIT(youtube_exempt, list( return update_song(current_song, current_listener, 0) +*/ /* ACTION BUTTONS @@ -390,10 +393,12 @@ GLOBAL_LIST_INIT(youtube_exempt, list( ..() name = "Next song" +/* /datum/action/item_action/walkman/next_song/Trigger(trigger_flags) if(target) var/obj/item/device/walkman/walkM = target walkM.next_song(owner) +*/ /datum/action/item_action/walkman/restart_song button_icon_state = "walkman_restart" @@ -402,10 +407,13 @@ GLOBAL_LIST_INIT(youtube_exempt, list( ..() name = "Restart song" +/* /datum/action/item_action/walkman/restart_song/Trigger(trigger_flags) if(target) var/obj/item/device/walkman/walkM = target walkM.restart_song(owner) +*/ + #undef sound_to #undef NEXT_SONG_USE_TIMER diff --git a/monkestation/code/modules/mob/dead/observer/observer.dm b/monkestation/code/modules/mob/dead/observer/observer.dm new file mode 100644 index 000000000000..ab145f403285 --- /dev/null +++ b/monkestation/code/modules/mob/dead/observer/observer.dm @@ -0,0 +1,3 @@ +/mob/dead/observer/Initialize(mapload) + . = ..() + ADD_TRAIT(src, TRAIT_CAN_HEAR_MUSIC, INNATE_TRAIT) diff --git a/monkestation/code/modules/mob/living/silicon/silicon.dm b/monkestation/code/modules/mob/living/silicon/silicon.dm new file mode 100644 index 000000000000..6dab07329bf6 --- /dev/null +++ b/monkestation/code/modules/mob/living/silicon/silicon.dm @@ -0,0 +1,3 @@ +/mob/living/silicon/Initialize(mapload) + . = ..() + ADD_TRAIT(src, TRAIT_CAN_HEAR_MUSIC, INNATE_TRAIT) diff --git a/tgstation.dme b/tgstation.dme index 154c696ea91d..59ceb44b06d9 100644 --- a/tgstation.dme +++ b/tgstation.dme @@ -412,6 +412,7 @@ #include "code\__DEFINES\~monkestation\blueshift.dm" #include "code\__DEFINES\~monkestation\botany.dm" #include "code\__DEFINES\~monkestation\cargo.dm" +#include "code\__DEFINES\~monkestation\cassettes.dm" #include "code\__DEFINES\~monkestation\chat.dm" #include "code\__DEFINES\~monkestation\chewin.dm" #include "code\__DEFINES\~monkestation\clock_cult.dm" @@ -611,6 +612,7 @@ #include "code\__HELPERS\~monkestation-helpers\mobs.dm" #include "code\__HELPERS\~monkestation-helpers\records.dm" #include "code\__HELPERS\~monkestation-helpers\roundend.dm" +#include "code\__HELPERS\~monkestation-helpers\text.dm" #include "code\__HELPERS\~monkestation-helpers\time.dm" #include "code\__HELPERS\~monkestation-helpers\uwuify.dm" #include "code\__HELPERS\~monkestation-helpers\virology.dm" @@ -6169,6 +6171,7 @@ #include "monkestation\code\game\objects\items\guns\SRN.dm" #include "monkestation\code\game\objects\items\guns\wt_ammo.dm" #include "monkestation\code\game\objects\items\implants\hardlight.dm" +#include "monkestation\code\game\objects\items\implants\implant_misc.dm" #include "monkestation\code\game\objects\items\rayne_corp\rayne_lantern.dm" #include "monkestation\code\game\objects\items\rayne_corp\rayne_mender.dm" #include "monkestation\code\game\objects\items\robot\items\hypo.dm" @@ -7107,7 +7110,10 @@ #include "monkestation\code\modules\cassettes\cassette_approval.dm" #include "monkestation\code\modules\cassettes\random_cassette_selection.dm" #include "monkestation\code\modules\cassettes\cassette_db\cassette_datum.dm" -#include "monkestation\code\modules\cassettes\cassette_db\subsystem.dm" +#include "monkestation\code\modules\cassettes\cassette_db\cassette_manager.dm" +#include "monkestation\code\modules\cassettes\dj\dj_music_field.dm" +#include "monkestation\code\modules\cassettes\dj\intercom.dm" +#include "monkestation\code\modules\cassettes\dj\mob_can_hear.dm" #include "monkestation\code\modules\cassettes\machines\cassette_rack.dm" #include "monkestation\code\modules\cassettes\machines\dj_station.dm" #include "monkestation\code\modules\cassettes\machines\portable_mixer.dm" @@ -7622,6 +7628,7 @@ #include "monkestation\code\modules\mob\dead\new_player\sprite_accessories\multi_part.dm" #include "monkestation\code\modules\mob\dead\new_player\sprite_accessories\sock_color.dm" #include "monkestation\code\modules\mob\dead\new_player\sprite_accessories\underwear.dm" +#include "monkestation\code\modules\mob\dead\observer\observer.dm" #include "monkestation\code\modules\mob\living\emote.dm" #include "monkestation\code\modules\mob\living\init_signals.dm" #include "monkestation\code\modules\mob\living\living.dm" @@ -7689,6 +7696,7 @@ #include "monkestation\code\modules\mob\living\carbon\human\species_type\tundra_moths\mothaccessories.dm" #include "monkestation\code\modules\mob\living\carbon\human\species_type\tundra_moths\tundramoths.dm" #include "monkestation\code\modules\mob\living\silicon\death.dm" +#include "monkestation\code\modules\mob\living\silicon\silicon.dm" #include "monkestation\code\modules\mob\living\simple_animal\megafauna\wendigo.dm" #include "monkestation\code\modules\mob\living\simple_animal\pets\bees.dm" #include "monkestation\code\modules\mob_spawn\ghost_roles\space_roles\oldchef.dm"