diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md
index 403526d30b..a553cef999 100644
--- a/.github/CONTRIBUTING.md
+++ b/.github/CONTRIBUTING.md
@@ -210,6 +210,8 @@ This prevents nesting levels from getting deeper then they need to be.
* Do not divide when you can easily convert it to a multiplication. (ie `4/2` should be done as `4*0.5`)
+* Do not use the shorthand sql insert format (where no column names are specified) because it unnecessarily breaks all queries on minor column changes and prevents using these tables for tracking outside related info such as in a connected site/forum.
+
#### Enforced not enforced
The following different coding styles are not only not enforced, but it is generally frowned upon to change them over from one to the other for little reason:
diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE.md
index f5fa86a76d..a1c37bc290 100644
--- a/.github/ISSUE_TEMPLATE.md
+++ b/.github/ISSUE_TEMPLATE.md
@@ -1,3 +1,3 @@
-[Note]: # (Please enter the commit hash and active testmerge numbers from the "Show Server Revision" verb if you can. If you believe the issue to be caused by a testmerge, please report it in its relative PR thread. State what the issue is from a "whats wrong" prospective. Issue reports should clearly allow maintainers to understand whats wrong and how to test/reproduce if that is not obvious. Avoid ambiguity. Start your issue report below both of these lines (or remove them))
+[Note]: # (State what the issue is from a "whats wrong" perspective. Issue reports should clearly allow maintainers to understand whats wrong and how to test/reproduce if that is not obvious. Avoid ambiguity. Please enter the commit hash from the "Show Server Revision" verb if you can. Remove these notes before submitting your report.)
-[Admins]: # (If you are reporting a bug that occured AFTER you used varedit/admin buttons to alter an object out of normal operating conditions, please verify that you can re-create the bug without the varedit usage/admin buttons before reporting the issue.)
+[GameAdmins]: # (If you are reporting a bug that occurred AFTER you used varedit/admin buttons to alter an object out of normal operating conditions, please verify that you can re-create the bug without the varedit usage/admin buttons before reporting the issue.)
diff --git a/SQL/database_changelog.txt b/SQL/database_changelog.txt
index c34c6b694b..d0546da131 100644
--- a/SQL/database_changelog.txt
+++ b/SQL/database_changelog.txt
@@ -1,3 +1,13 @@
+21 April 2017, by Jordie0608
+
+Modified table 'player', adding the column 'accountjoindate', removing the column 'id' and making the column 'ckey' the primary key.
+
+ALTER TABLE `feedback`.`player` DROP COLUMN `id`, ADD COLUMN `accountjoindate` DATE NULL AFTER `lastadminrank`, DROP PRIMARY KEY, ADD PRIMARY KEY (`ckey`), DROP INDEX `ckey`;
+
+Remember to add a prefix to the table name if you use them.
+
+----------------------------------------------------
+
10 March 2017, by Jordie0608
Modified table 'death', adding the columns 'toxloss', 'cloneloss', and 'staminaloss' and table 'legacy_population', adding the columns 'server_ip' and 'server_port'.
diff --git a/SQL/tgstation_schema.sql b/SQL/tgstation_schema.sql
index 77e9b9429e..0d0817bf1f 100644
--- a/SQL/tgstation_schema.sql
+++ b/SQL/tgstation_schema.sql
@@ -261,15 +261,14 @@ DROP TABLE IF EXISTS `player`;
/*!40101 SET @saved_cs_client = @@character_set_client */;
/*!40101 SET character_set_client = utf8 */;
CREATE TABLE `player` (
- `id` int(11) NOT NULL AUTO_INCREMENT,
`ckey` varchar(32) NOT NULL,
`firstseen` datetime NOT NULL,
`lastseen` datetime NOT NULL,
`ip` int(10) unsigned NOT NULL,
`computerid` varchar(32) NOT NULL,
`lastadminrank` varchar(32) NOT NULL DEFAULT 'Player',
- PRIMARY KEY (`id`),
- UNIQUE KEY `ckey` (`ckey`),
+ `accountjoindate` DATE DEFAULT NULL,
+ PRIMARY KEY (`ckey`),
KEY `idx_player_cid_ckey` (`computerid`,`ckey`),
KEY `idx_player_ip_ckey` (`ip`,`ckey`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
diff --git a/SQL/tgstation_schema_prefixed.sql b/SQL/tgstation_schema_prefixed.sql
index be27384ea5..4d74b9deaa 100644
--- a/SQL/tgstation_schema_prefixed.sql
+++ b/SQL/tgstation_schema_prefixed.sql
@@ -261,15 +261,14 @@ DROP TABLE IF EXISTS `SS13_player`;
/*!40101 SET @saved_cs_client = @@character_set_client */;
/*!40101 SET character_set_client = utf8 */;
CREATE TABLE `SS13_player` (
- `id` int(11) NOT NULL AUTO_INCREMENT,
`ckey` varchar(32) NOT NULL,
`firstseen` datetime NOT NULL,
`lastseen` datetime NOT NULL,
`ip` int(10) unsigned NOT NULL,
`computerid` varchar(32) NOT NULL,
`lastadminrank` varchar(32) NOT NULL DEFAULT 'Player',
- PRIMARY KEY (`id`),
- UNIQUE KEY `ckey` (`ckey`),
+ `accountjoindate` DATE DEFAULT NULL,
+ PRIMARY KEY (`ckey`),
KEY `idx_player_cid_ckey` (`computerid`,`ckey`),
KEY `idx_player_ip_ckey` (`ip`,`ckey`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
diff --git a/Test.txt b/Test.txt
deleted file mode 100644
index fc816240e4..0000000000
--- a/Test.txt
+++ /dev/null
@@ -1 +0,0 @@
-Ignore this
\ No newline at end of file
diff --git a/_maps/map_files/Cerestation/cerestation.dmm b/_maps/map_files/Cerestation/cerestation.dmm
index f10211f5b1..860ff65d60 100644
--- a/_maps/map_files/Cerestation/cerestation.dmm
+++ b/_maps/map_files/Cerestation/cerestation.dmm
@@ -7034,8 +7034,8 @@
"anI" = (
/obj/docking_port/stationary/random{
dir = 1;
- id = "pod_asteroid1";
- name = "asteroid"
+ id = "pod_lavaland1";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -8103,7 +8103,7 @@
/obj/machinery/computer/shuttle/pod{
pixel_x = -32;
pixel_y = 0;
- possible_destinations = "pod_asteroid1";
+ possible_destinations = "pod_lavaland1";
shuttleId = "pod1"
},
/obj/machinery/light/small{
@@ -40738,7 +40738,7 @@
/obj/machinery/computer/shuttle/pod{
pixel_x = 0;
pixel_y = 32;
- possible_destinations = "pod_asteroid3";
+ possible_destinations = "pod_lavaland3";
shuttleId = "pod3"
},
/obj/item/device/radio/intercom{
@@ -40760,8 +40760,8 @@
"btw" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid3";
- name = "asteroid"
+ id = "pod_lavaland3";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -68963,8 +68963,8 @@
"crd" = (
/obj/docking_port/stationary/random{
dir = 8;
- id = "pod_asteroid2";
- name = "asteroid"
+ id = "pod_lavaland2";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -68979,7 +68979,7 @@
/obj/machinery/computer/shuttle/pod{
pixel_x = 0;
pixel_y = -32;
- possible_destinations = "pod_asteroid2";
+ possible_destinations = "pod_lavaland2";
shuttleId = "pod2"
},
/obj/structure/chair{
diff --git a/_maps/map_files/CitadelStation/CitadelStation-1.2.1.dmm b/_maps/map_files/CitadelStation/CitadelStation-1.2.1.dmm
index 7553242b36..84fb806587 100644
--- a/_maps/map_files/CitadelStation/CitadelStation-1.2.1.dmm
+++ b/_maps/map_files/CitadelStation/CitadelStation-1.2.1.dmm
@@ -1361,7 +1361,7 @@
"aAi" = (/obj/structure/table/wood,/obj/item/weapon/folder,/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
"aAj" = (/obj/machinery/power/apc{dir = 8;name = "Library APC";pixel_x = -25},/obj/structure/cable{icon_state = "0-4";d2 = 4},/turf/open/floor/wood,/area/library)
"aAk" = (/obj/structure/cable{d1 = 2;d2 = 8;icon_state = "2-8"},/turf/open/floor/wood,/area/library)
-"aAl" = (/obj/effect/landmark/start{name = "Librarian"},/turf/open/floor/wood,/area/library)
+"aAl" = (/obj/effect/landmark/start{name = "Curator"},/turf/open/floor/wood,/area/library)
"aAm" = (/obj/machinery/light/small{dir = 4},/turf/open/floor/wood,/area/library)
"aAn" = (/obj/machinery/light/small/built{tag = "icon-bulb1 (WEST)";icon_state = "bulb1";dir = 8},/obj/machinery/airalarm{frequency = 1439;locked = 0;pixel_y = 23},/turf/open/floor/wood,/area/crew_quarters/cafeteria{name = "Cafe"})
"aAo" = (/turf/open/floor/wood,/area/crew_quarters/cafeteria{name = "Cafe"})
@@ -1393,7 +1393,7 @@
"aAO" = (/obj/machinery/light/small{dir = 8},/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/maintenance/fore)
"aAP" = (/obj/structure/chair/stool,/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/maintenance/fore)
"aAQ" = (/obj/machinery/door/airlock/maintenance_hatch,/turf/open/floor/noslip,/area/construction/hallway{name = "Secure Workstations Hallway"})
-"aAR" = (/obj/structure/closet/cabinet,/obj/item/toy/figure/assistant,/obj/item/toy/figure/atmos,/obj/item/toy/figure/bartender,/obj/item/toy/figure/borg,/obj/item/toy/figure/botanist,/obj/item/toy/figure/captain,/obj/item/toy/figure/cargotech,/obj/item/toy/figure/ce,/obj/item/toy/figure/chaplain,/obj/item/toy/figure/chef,/obj/item/toy/figure/chemist,/obj/item/toy/figure/clown,/obj/item/toy/figure/cmo,/obj/item/toy/figure/detective,/obj/item/toy/figure/dsquad,/obj/item/toy/figure/engineer,/obj/item/toy/figure/geneticist,/obj/item/toy/figure/hop,/obj/item/toy/figure/hos,/obj/item/toy/figure/ian,/obj/item/toy/figure/janitor,/obj/item/toy/figure/lawyer,/obj/item/toy/figure/librarian,/obj/item/toy/figure/md,/obj/item/toy/figure/mime,/obj/item/toy/figure/miner,/obj/item/toy/figure/ninja,/obj/item/toy/figure/qm,/obj/item/toy/figure/rd,/obj/item/toy/figure/roboticist,/obj/item/toy/figure/scientist,/obj/item/toy/figure/secofficer,/obj/item/toy/figure/syndie,/obj/item/toy/figure/virologist,/obj/item/toy/figure/warden,/obj/item/toy/figure/wizard,/obj/item/toy/minimeteor,/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
+"aAR" = (/obj/structure/closet/cabinet,/obj/item/toy/figure/assistant,/obj/item/toy/figure/atmos,/obj/item/toy/figure/bartender,/obj/item/toy/figure/borg,/obj/item/toy/figure/botanist,/obj/item/toy/figure/captain,/obj/item/toy/figure/cargotech,/obj/item/toy/figure/ce,/obj/item/toy/figure/chaplain,/obj/item/toy/figure/chef,/obj/item/toy/figure/chemist,/obj/item/toy/figure/clown,/obj/item/toy/figure/cmo,/obj/item/toy/figure/detective,/obj/item/toy/figure/dsquad,/obj/item/toy/figure/engineer,/obj/item/toy/figure/geneticist,/obj/item/toy/figure/hop,/obj/item/toy/figure/hos,/obj/item/toy/figure/ian,/obj/item/toy/figure/janitor,/obj/item/toy/figure/lawyer,/obj/item/toy/figure/curator,/obj/item/toy/figure/md,/obj/item/toy/figure/mime,/obj/item/toy/figure/miner,/obj/item/toy/figure/ninja,/obj/item/toy/figure/qm,/obj/item/toy/figure/rd,/obj/item/toy/figure/roboticist,/obj/item/toy/figure/scientist,/obj/item/toy/figure/secofficer,/obj/item/toy/figure/syndie,/obj/item/toy/figure/virologist,/obj/item/toy/figure/warden,/obj/item/toy/figure/wizard,/obj/item/toy/minimeteor,/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
"aAS" = (/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden,/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
"aAT" = (/obj/item/device/radio/intercom{dir = 4;name = "Station Intercom (General)";pixel_x = 0;pixel_y = -27},/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
"aAU" = (/obj/machinery/atmospherics/pipe/manifold/supply/hidden{dir = 8;initialize_directions = 11},/turf/open/floor/wood{baseturf = /turf/open/floor/plating/asteroid},/area/library)
diff --git a/_maps/map_files/Deltastation/DeltaStation2.dmm b/_maps/map_files/Deltastation/DeltaStation2.dmm
index 2e275a194f..267a2a7b50 100644
--- a/_maps/map_files/Deltastation/DeltaStation2.dmm
+++ b/_maps/map_files/Deltastation/DeltaStation2.dmm
@@ -142,15 +142,15 @@
/area/solar/auxstarboard)
"aap" = (
/obj/docking_port/stationary/random{
- id = "pod_asteroid1";
- name = "asteroid"
+ id = "pod_lavaland1";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
"aaq" = (
/obj/docking_port/stationary/random{
- id = "pod_asteroid2";
- name = "asteroid"
+ id = "pod_lavaland2";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -203,7 +203,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_x = -32;
- possible_destinations = "pod_asteroid1";
+ possible_destinations = "pod_lavaland1";
shuttleId = "pod1"
},
/obj/effect/turf_decal/stripes/line{
@@ -226,7 +226,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_x = -32;
- possible_destinations = "pod_asteroid2";
+ possible_destinations = "pod_lavaland2";
shuttleId = "pod2"
},
/obj/effect/turf_decal/stripes/line{
@@ -10753,7 +10753,7 @@
/obj/effect/decal/cleanable/dirt,
/obj/effect/decal/cleanable/dirt,
/turf/open/floor/plasteel/loadingarea{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 8
},
/area/quartermaster/storage)
@@ -11240,7 +11240,7 @@
/area/quartermaster/storage)
"awJ" = (
/turf/open/floor/plasteel/loadingarea{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 8
},
/area/quartermaster/storage)
@@ -25977,7 +25977,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_y = -32;
- possible_destinations = "pod_asteroid3";
+ possible_destinations = "pod_lavaland3";
shuttleId = "pod3"
},
/obj/effect/turf_decal/stripes/line{
@@ -25996,8 +25996,8 @@
"aXK" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid4";
- name = "asteroid"
+ id = "pod_lavaland4";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -31236,7 +31236,7 @@
icon_state = "1-4"
},
/turf/open/floor/plasteel/loadingarea{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 8
},
/area/quartermaster/miningdock{
@@ -34793,7 +34793,6 @@
dir = 4
},
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L14"
},
/area/hallway/primary/central)
@@ -44697,9 +44696,7 @@
/obj/effect/turf_decal/stripes/line{
dir = 2
},
-/turf/open/floor/plating{
- icon_state = "plating_warn_side"
- },
+/turf/open/floor/plating,
/area/maintenance/starboard)
"bGN" = (
/obj/effect/decal/cleanable/dirt,
@@ -52478,7 +52475,7 @@
name = "Queue Shutters"
},
/turf/open/floor/plasteel/loadingarea{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 8
},
/area/hallway/primary/central)
@@ -62920,7 +62917,7 @@
"cpl" = (
/obj/structure/table/wood,
/obj/item/weapon/clipboard,
-/obj/item/toy/figure/librarian,
+/obj/item/toy/figure/curator,
/obj/machinery/airalarm{
dir = 8;
icon_state = "alarm0";
@@ -63738,7 +63735,7 @@
/area/library)
"cqF" = (
/obj/machinery/door/morgue{
- name = "Librarian's Study";
+ name = "Curator's Study";
req_access_txt = "37"
},
/obj/machinery/atmospherics/pipe/simple/supply/hidden,
@@ -64358,10 +64355,12 @@
/turf/open/floor/plasteel/black,
/area/library)
"crP" = (
-/obj/structure/dresser,
-/obj/machinery/computer/security/telescreen/entertainment{
- pixel_x = -32
- },
+/obj/structure/closet/crate,
+/obj/item/clothing/shoes/workboots/mining,
+/obj/item/clothing/under/rank/curator/treasure_hunter,
+/obj/item/clothing/suit/curator,
+/obj/item/clothing/head/curator,
+/obj/item/weapon/storage/backpack/satchel/explorer,
/turf/open/floor/plasteel/black,
/area/library)
"crQ" = (
@@ -67500,7 +67499,7 @@
desc = "This looks awfully familiar...";
icon_state = "curator"
},
-/obj/item/clothing/under/rank/librarian/curator,
+/obj/item/clothing/under/rank/curator/treasure_hunter,
/turf/open/floor/carpet,
/area/crew_quarters/sleep)
"cxC" = (
@@ -70988,7 +70987,6 @@
"cDW" = (
/obj/machinery/atmospherics/pipe/manifold/supply/hidden,
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L13";
name = "floor"
},
@@ -79514,8 +79512,13 @@
name = "Medbay Central"
})
"cUf" = (
-/obj/machinery/smartfridge/chemistry,
-/turf/closed/wall,
+/obj/structure/grille,
+/obj/machinery/door/poddoor/shutters/preopen{
+ id = "chemisttop";
+ name = "Chemisty Lobby Shutters"
+ },
+/obj/structure/window/reinforced/fulltile,
+/turf/open/floor/plating,
/area/medical/medbay{
name = "Medbay Central"
})
@@ -79538,14 +79541,9 @@
name = "Medbay Central"
})
"cUh" = (
-/obj/structure/grille,
-/obj/structure/window/reinforced/fulltile,
-/obj/machinery/door/poddoor/shutters/preopen{
- id = "chemisttop";
- name = "Chemisty Lobby Shutters"
- },
/obj/structure/disposalpipe/segment,
-/turf/open/floor/plating,
+/obj/machinery/smartfridge/chemistry,
+/turf/closed/wall,
/area/medical/medbay{
name = "Medbay Central"
})
@@ -82191,6 +82189,7 @@
/obj/item/weapon/grenade/chem_grenade,
/obj/item/weapon/grenade/chem_grenade,
/obj/item/weapon/grenade/chem_grenade,
+/obj/item/weapon/screwdriver,
/turf/open/floor/plasteel/whiteyellow/corner{
icon_state = "whiteyellowcorner";
dir = 8
@@ -96355,7 +96354,6 @@
},
/area/medical/morgue)
"dAn" = (
-/turf/open/floor/plating,
/obj/effect/decal/cleanable/dirt,
/obj/machinery/atmospherics/pipe/manifold/supply/hidden{
icon_state = "manifold";
@@ -104162,7 +104160,7 @@
name = "emergency shower"
},
/turf/open/floor/plasteel/whiteblue/side{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 4
},
/area/shuttle/escape)
@@ -105518,7 +105516,7 @@
/area/library/abandoned_library)
"dSu" = (
/obj/structure/table/wood,
-/obj/item/clothing/under/rank/librarian,
+/obj/item/clothing/under/rank/curator,
/obj/effect/spawner/lootdrop/maintenance{
lootcount = 2;
name = "2maintenance loot spawner"
@@ -108178,7 +108176,7 @@
/area/maintenance/fpmaint2/aft_port_maintenance)
"dXu" = (
/obj/structure/table/wood/fancy,
-/obj/item/weapon/spellbook/oneuse/smoke,
+/obj/item/weapon/spellbook/oneuse/smoke/lesser,
/obj/item/weapon/nullrod,
/obj/item/organ/heart,
/obj/item/weapon/reagent_containers/food/drinks/bottle/holywater,
@@ -112313,6 +112311,22 @@
},
/turf/open/floor/plasteel/neutral,
/area/atmos)
+"ehO" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
+"ehP" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
+"ehQ" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
+"ehR" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
(1,1,1) = {"
aaa
@@ -143546,7 +143560,7 @@ cbA
cdn
ceS
cgp
-chQ
+ehO
cjl
ckP
cjl
@@ -143803,7 +143817,7 @@ cbB
cdo
ceS
cgq
-chQ
+ehO
cjl
ckP
cjl
@@ -144317,7 +144331,7 @@ bWi
cdq
ceS
cgp
-chQ
+ehO
cjm
ckP
cmk
@@ -144574,7 +144588,7 @@ cbC
cdr
ceT
cgp
-chQ
+ehO
cjn
ckP
cmk
diff --git a/_maps/map_files/MetaStation/MetaStation.dmm b/_maps/map_files/MetaStation/MetaStation.dmm
index 320823a490..f30c7b69f3 100644
--- a/_maps/map_files/MetaStation/MetaStation.dmm
+++ b/_maps/map_files/MetaStation/MetaStation.dmm
@@ -1910,8 +1910,8 @@
/area/shuttle/pod_3)
"adG" = (
/obj/docking_port/stationary/random{
- id = "pod_asteroid2";
- name = "asteroid"
+ id = "pod_lavaland2";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -1927,7 +1927,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_x = -32;
- possible_destinations = "pod_asteroid2";
+ possible_destinations = "pod_lavaland2";
shuttleId = "pod2"
},
/turf/open/floor/mineral/titanium/blue,
@@ -23696,7 +23696,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_y = -32;
- possible_destinations = "pod_asteroid3";
+ possible_destinations = "pod_lavaland3";
shuttleId = "pod3"
},
/turf/open/floor/mineral/titanium/blue,
@@ -27963,7 +27963,6 @@
dir = 4
},
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L13";
name = "floor"
},
@@ -28813,7 +28812,6 @@
icon_state = "4-8"
},
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L14"
},
/area/hallway/primary/central)
@@ -34140,8 +34138,8 @@
"bii" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid3";
- name = "asteroid"
+ id = "pod_lavaland3";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -45372,12 +45370,12 @@
name = "Port Maintenance"
})
"bBr" = (
-/obj/structure/table/wood,
/obj/machinery/airalarm{
dir = 4;
pixel_x = -23;
pixel_y = 0
},
+/obj/structure/displaycase/trophy,
/turf/open/floor/wood,
/area/library)
"bBs" = (
@@ -47035,7 +47033,6 @@
name = "\improper Auxiliary Restrooms"
})
"bEw" = (
-/obj/structure/table/wood,
/obj/machinery/computer/security/telescreen/entertainment{
pixel_x = -32;
pixel_y = 0
@@ -47044,6 +47041,7 @@
dir = 4;
network = list("SS13")
},
+/obj/structure/displaycase/trophy,
/turf/open/floor/wood,
/area/library)
"bEx" = (
@@ -53664,6 +53662,12 @@
pixel_x = 30;
pixel_y = 0
},
+/obj/structure/closet/crate,
+/obj/item/clothing/shoes/workboots/mining,
+/obj/item/clothing/under/rank/curator/treasure_hunter,
+/obj/item/clothing/suit/curator,
+/obj/item/clothing/head/curator,
+/obj/item/weapon/storage/backpack/satchel/explorer,
/turf/open/floor/engine/cult,
/area/library)
"bPY" = (
@@ -82483,7 +82487,7 @@
/area/chapel/office)
"cMa" = (
/obj/structure/table/wood,
-/obj/item/weapon/spellbook/oneuse/smoke{
+/obj/item/weapon/spellbook/oneuse/smoke/lesser{
name = "mysterious old book of "
},
/obj/item/weapon/reagent_containers/food/drinks/bottle/holywater{
@@ -86084,8 +86088,8 @@
/area/toxins/xenobiology)
"cSP" = (
/obj/docking_port/stationary/random{
- id = "pod_asteroid1";
- name = "asteroid"
+ id = "pod_lavaland1";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -86175,7 +86179,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_x = -32;
- possible_destinations = "pod_asteroid1";
+ possible_destinations = "pod_lavaland1";
shuttleId = "pod1"
},
/turf/open/floor/mineral/titanium/blue,
@@ -86368,7 +86372,7 @@
},
/obj/machinery/computer/shuttle/pod{
pixel_y = -32;
- possible_destinations = "pod_asteroid4";
+ possible_destinations = "pod_lavaland4";
shuttleId = "pod4"
},
/turf/open/floor/mineral/titanium/blue,
@@ -87162,8 +87166,8 @@
"cUL" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid4";
- name = "asteroid"
+ id = "pod_lavaland4";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -95333,6 +95337,14 @@
icon_state = "xenomaint";
name = "Xeno Maintenance"
})
+"dmD" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
+"dmE" = (
+/obj/structure/displaycase/trophy,
+/turf/open/floor/wood,
+/area/library)
(1,1,1) = {"
aaa
@@ -114481,7 +114493,7 @@ bwa
bxU
bzD
bBr
-bCT
+bSx
bEw
bzE
bHR
@@ -114737,9 +114749,9 @@ bue
bwb
bxV
bzE
-bBs
-bCU
-bBs
+dmD
+bzE
+dmD
bzE
bHR
bJz
@@ -128192,7 +128204,7 @@ cRi
cRi
daP
cLE
-cRi
+dlV
aaa
aaa
aaf
@@ -128448,7 +128460,7 @@ daF
daJ
cRi
bvT
-dlV
+cRi
cRi
cRi
cRi
@@ -128705,7 +128717,7 @@ cSn
cSn
cRi
dmq
-dlV
+cRi
cZv
cZv
cRi
@@ -129733,7 +129745,7 @@ cSn
daN
cRi
dmr
-dlV
+cRi
cZv
dbw
cRi
@@ -129990,7 +130002,7 @@ daI
daM
cRi
cTA
-dlV
+cRi
cRi
cRi
cRi
diff --git a/_maps/map_files/Mining/Lavaland.dmm b/_maps/map_files/Mining/Lavaland.dmm
index 778fb50c88..c37c4ca3a3 100644
--- a/_maps/map_files/Mining/Lavaland.dmm
+++ b/_maps/map_files/Mining/Lavaland.dmm
@@ -513,7 +513,7 @@
/obj/structure/cable{
d1 = 1;
d2 = 4;
- icon_state = "1-4";
+ icon_state = "1-4"
},
/obj/structure/cable{
d1 = 1;
@@ -1040,7 +1040,7 @@
/obj/machinery/atmospherics/pipe/simple/supply/hidden,
/turf/open/floor/plasteel/brown{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/living_quarters)
"cg" = (
@@ -1074,7 +1074,7 @@
/obj/structure/cable{
d1 = 1;
d2 = 4;
- icon_state = "1-4";
+ icon_state = "1-4"
},
/turf/open/floor/plasteel{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
@@ -1497,10 +1497,21 @@
/area/mine/living_quarters)
"dd" = (
/obj/structure/table,
-/obj/item/weapon/reagent_containers/food/drinks/beer,
+/obj/item/weapon/reagent_containers/food/drinks/beer{
+ pixel_x = 7;
+ pixel_y = 5
+ },
/obj/machinery/atmospherics/pipe/simple/supply/hidden{
dir = 5
},
+/obj/item/weapon/reagent_containers/food/drinks/beer{
+ pixel_x = -1;
+ pixel_y = 9
+ },
+/obj/item/weapon/reagent_containers/food/drinks/beer{
+ pixel_x = -8;
+ pixel_y = 0
+ },
/turf/open/floor/plasteel/bar{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
},
@@ -1772,6 +1783,9 @@
pixel_x = -5;
pixel_y = 30
},
+/obj/machinery/shower{
+ dir = 8
+ },
/turf/open/floor/plasteel/purple/corner{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
},
@@ -2192,7 +2206,7 @@
},
/turf/open/floor/plasteel/vault{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 8;
+ dir = 8
},
/area/mine/maintenance)
"ez" = (
@@ -2214,13 +2228,13 @@
/obj/machinery/iv_drip,
/turf/open/floor/plasteel/whiteblue/side{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/living_quarters)
"eB" = (
/turf/open/floor/plasteel/whiteblue/side{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/living_quarters)
"eC" = (
@@ -2231,7 +2245,7 @@
},
/turf/open/floor/plasteel/whiteblue/side{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 5;
+ dir = 5
},
/area/mine/living_quarters)
"eD" = (
@@ -2398,7 +2412,7 @@
/obj/item/weapon/storage/firstaid/regular,
/turf/open/floor/plasteel/whiteblue/side{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 4;
+ dir = 4
},
/area/mine/living_quarters)
"eU" = (
@@ -2512,6 +2526,7 @@
dir = 2;
network = list("MINE")
},
+/obj/structure/reagent_dispensers/watertank,
/turf/open/floor/plasteel/brown{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
dir = 5
@@ -2520,7 +2535,7 @@
"fe" = (
/turf/open/floor/plasteel/brown/corner{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/production)
"ff" = (
@@ -2578,7 +2593,7 @@
},
/turf/open/floor/plasteel/brown{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/living_quarters)
"fm" = (
@@ -2600,7 +2615,7 @@
/obj/machinery/atmospherics/pipe/simple/supply/hidden,
/turf/open/floor/plasteel/brown{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
- dir = 1;
+ dir = 1
},
/area/mine/living_quarters)
"fp" = (
@@ -2674,7 +2689,7 @@
/obj/structure/cable{
d1 = 1;
d2 = 4;
- icon_state = "1-4";
+ icon_state = "1-4"
},
/turf/open/floor/plasteel{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
@@ -2712,6 +2727,10 @@
/obj/machinery/light/small{
dir = 1
},
+/obj/structure/extinguisher_cabinet{
+ pixel_x = -5;
+ pixel_y = 30
+ },
/turf/open/floor/plasteel/purple/corner{
baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
dir = 4
@@ -2794,6 +2813,41 @@
/turf/open/floor/plating/asteroid/basalt/lava_land_surface,
/turf/closed/indestructible/riveted,
/area/space)
+"fQ" = (
+/obj/machinery/shower{
+ dir = 8
+ },
+/obj/effect/turf_decal/delivery,
+/turf/open/floor/plasteel/white,
+/area/mine/laborcamp)
+"fR" = (
+/obj/structure/sink/kitchen{
+ dir = 4;
+ icon_state = "sink_alt";
+ pixel_x = -13;
+ tag = "icon-sink_alt (EAST)"
+ },
+/turf/open/floor/plasteel{
+ baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
+ },
+/area/mine/laborcamp)
+"fS" = (
+/obj/structure/reagent_dispensers/watertank,
+/turf/open/floor/plasteel/purple/corner{
+ baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
+ },
+/area/mine/production)
+"fT" = (
+/obj/structure/sink{
+ dir = 4;
+ icon_state = "sink";
+ pixel_x = 11;
+ tag = "icon-sink (EAST)"
+ },
+/turf/open/floor/plasteel/bar{
+ baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface
+ },
+/area/mine/living_quarters)
(1,1,1) = {"
aa
@@ -8919,7 +8973,7 @@ aA
at
at
at
-at
+fR
at
au
fH
@@ -9175,7 +9229,7 @@ an
an
at
at
-at
+fQ
at
dr
an
@@ -14594,8 +14648,8 @@ fj
ee
cT
cZ
-dg
dk
+fT
ee
al
al
@@ -18433,7 +18487,7 @@ af
ab
ab
dx
-dC
+fS
dK
bI
bS
diff --git a/_maps/map_files/OmegaStation/OmegaStation.dmm b/_maps/map_files/OmegaStation/OmegaStation.dmm
index d841a0f335..2af4f3bd30 100644
--- a/_maps/map_files/OmegaStation/OmegaStation.dmm
+++ b/_maps/map_files/OmegaStation/OmegaStation.dmm
@@ -7303,7 +7303,6 @@
icon_state = "1-2"
},
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L14"
},
/area/hallway/primary/central{
@@ -9155,7 +9154,7 @@
},
/obj/effect/landmark/start/shaft_miner,
/turf/open/floor/plasteel/loadingarea{
- baseturf = /turf/open/floor/plating/lava/smooth/lava_land_surface;
+ baseturf = /turf/open/space;
dir = 8
},
/area/quartermaster/miningdock)
@@ -16523,6 +16522,9 @@
/obj/machinery/status_display{
pixel_x = -32
},
+/obj/machinery/light{
+ dir = 8
+ },
/turf/open/floor/mineral/plastitanium/brig,
/area/shuttle/escape)
"aAb" = (
@@ -16558,6 +16560,9 @@
"aAf" = (
/obj/structure/table/reinforced,
/obj/item/weapon/storage/fancy/donut_box,
+/obj/machinery/light{
+ dir = 4
+ },
/turf/open/floor/plasteel/vault{
dir = 8
},
@@ -24133,6 +24138,9 @@
},
/obj/effect/decal/cleanable/dirt,
/obj/effect/turf_decal/delivery,
+/obj/machinery/light{
+ dir = 8
+ },
/turf/open/floor/plasteel,
/area/shuttle/escape)
"aME" = (
@@ -24187,6 +24195,9 @@
/obj/machinery/status_display{
pixel_x = 32
},
+/obj/machinery/light{
+ dir = 4
+ },
/turf/open/floor/plasteel/whiteblue/side{
dir = 5
},
@@ -25964,7 +25975,6 @@
icon_state = "4-8"
},
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L13";
name = "floor"
},
@@ -30548,7 +30558,7 @@
/area/maintenance/starboard)
"aXL" = (
/obj/machinery/door/morgue{
- name = "Librarian's Study";
+ name = "Curator's Study";
req_access_txt = "37"
},
/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden,
@@ -41920,6 +41930,294 @@
/area/ruin/unpowered{
name = "Asteroid"
})
+"bvO" = (
+/obj/machinery/light{
+ dir = 1
+ },
+/turf/open/floor/plasteel/neutral/side{
+ dir = 1
+ },
+/area/shuttle/escape)
+"bvP" = (
+/obj/structure/chair{
+ dir = 8
+ },
+/obj/effect/turf_decal/bot,
+/obj/machinery/light/small{
+ dir = 4
+ },
+/turf/open/floor/plasteel,
+/area/shuttle/escape)
+"bvQ" = (
+/obj/structure/chair{
+ dir = 4
+ },
+/obj/effect/turf_decal/bot,
+/obj/machinery/light/small{
+ dir = 8
+ },
+/turf/open/floor/plasteel,
+/area/shuttle/escape)
+"bvR" = (
+/obj/machinery/light,
+/turf/open/floor/plasteel/neutral/side,
+/area/shuttle/escape)
+"bvS" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bvT" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bvU" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bvV" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bvW" = (
+/obj/machinery/door/airlock/external,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bvX" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bvY" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bvZ" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bwa" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwb" = (
+/obj/structure/shuttle/engine/propulsion{
+ dir = 8;
+ icon_state = "propulsion_l"
+ },
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwc" = (
+/obj/structure/shuttle/engine/heater{
+ icon_state = "heater";
+ dir = 8
+ },
+/obj/structure/window/reinforced,
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwd" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwe" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwf" = (
+/obj/structure/chair,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwg" = (
+/obj/structure/chair,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwh" = (
+/obj/machinery/light{
+ dir = 1
+ },
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwi" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwj" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwk" = (
+/obj/structure/chair,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwl" = (
+/obj/structure/chair,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwm" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bwn" = (
+/obj/structure/shuttle/engine/propulsion{
+ dir = 8;
+ icon_state = "propulsion_l"
+ },
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwo" = (
+/obj/structure/shuttle/engine/heater{
+ icon_state = "heater";
+ dir = 8
+ },
+/obj/structure/window/reinforced{
+ dir = 4;
+ pixel_x = 0
+ },
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwp" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwq" = (
+/obj/machinery/light/small,
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwr" = (
+/obj/machinery/door/airlock/titanium,
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bws" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwt" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwu" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwv" = (
+/obj/machinery/computer/shuttle/ferry/request,
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bww" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwx" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwy" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwz" = (
+/obj/machinery/door/airlock/titanium,
+/obj/docking_port/mobile{
+ dir = 8;
+ dwidth = 2;
+ height = 13;
+ id = "ferry";
+ name = "ferry shuttle";
+ port_angle = 0;
+ preferred_direction = 4;
+ roundstart_move = "ferry_away";
+ width = 5
+ },
+/obj/docking_port/stationary{
+ dir = 8;
+ dwidth = 2;
+ height = 13;
+ id = "ferry_home";
+ name = "port bay 2";
+ turf_type = /turf/open/space;
+ width = 5
+ },
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwA" = (
+/obj/structure/shuttle/engine/propulsion{
+ dir = 8;
+ icon_state = "propulsion_l"
+ },
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwB" = (
+/obj/structure/shuttle/engine/heater{
+ icon_state = "heater";
+ dir = 8
+ },
+/obj/structure/window/reinforced{
+ dir = 1;
+ pixel_y = 1
+ },
+/turf/open/floor/plating/airless,
+/area/shuttle/transport)
+"bwC" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwD" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwE" = (
+/obj/structure/chair{
+ dir = 1
+ },
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwF" = (
+/obj/structure/chair{
+ dir = 1
+ },
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwG" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwH" = (
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwI" = (
+/obj/machinery/light,
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwJ" = (
+/obj/structure/chair{
+ dir = 1
+ },
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwK" = (
+/obj/structure/chair{
+ dir = 1
+ },
+/turf/open/floor/pod/dark,
+/area/shuttle/transport)
+"bwL" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bwM" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwN" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bwO" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwP" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwQ" = (
+/obj/machinery/door/airlock/external,
+/turf/open/floor/pod/light,
+/area/shuttle/transport)
+"bwR" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwS" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
+"bwT" = (
+/obj/structure/grille,
+/obj/structure/window/shuttle,
+/turf/open/floor/plating,
+/area/shuttle/transport)
+"bwU" = (
+/turf/closed/wall/mineral/titanium,
+/area/shuttle/transport)
(1,1,1) = {"
aaa
@@ -72622,11 +72920,11 @@ aHl
aIi
aJs
aKz
-buW
+buX
aMR
buZ
-buZ
-buW
+bva
+bvb
aQL
aRI
aSS
@@ -72883,7 +73181,7 @@ aLP
aMS
aMS
aOC
-buW
+bvc
aQM
aRJ
aST
@@ -73911,7 +74209,7 @@ aLT
aMW
aMW
aOD
-buW
+bve
aQQ
aRN
aSX
@@ -74164,11 +74462,11 @@ aHr
aIo
aJw
aKE
-buW
+buY
aMX
aMX
aMX
-buW
+bvf
aQR
aRO
aSY
@@ -77290,7 +77588,7 @@ aaa
aaa
aaa
aaa
-aaa
+bwn
aaa
aaa
aaa
@@ -77546,9 +77844,9 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
+bwb
+bwo
+bwA
aaa
aaa
aaa
@@ -77803,9 +78101,9 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
+bwc
+bwp
+bwB
aaa
aaa
aaa
@@ -78060,9 +78358,9 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
+bwd
+bwq
+bwC
aaa
aaa
aaa
@@ -78316,11 +78614,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvS
+bwe
+bwr
+bwD
+bwM
aaa
aaa
aaa
@@ -78573,11 +78871,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvT
+bwf
+bws
+bwE
+bwN
aaa
aaa
aaa
@@ -78830,11 +79128,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvU
+bwg
+bwt
+bwF
+bwO
aaa
aaa
aaa
@@ -79087,11 +79385,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvV
+bwh
+bwu
+bwG
+bwP
aaa
aaa
aaa
@@ -79344,11 +79642,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvW
+bwi
+bwv
+bwH
+bwQ
aaa
aaa
aaa
@@ -79601,11 +79899,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvX
+bwj
+bww
+bwI
+bwR
aaa
aaa
aaa
@@ -79858,11 +80156,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvY
+bwk
+bwx
+bwJ
+bwS
aaa
aaa
aaa
@@ -80115,11 +80413,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bvZ
+bwl
+bwy
+bwK
+bwT
aaa
aaa
aaa
@@ -80372,11 +80670,11 @@ aaa
aaa
aaa
aaa
-aaa
-aaa
-aaa
-aaa
-aaa
+bwa
+bwm
+bwz
+bwL
+bwU
aaa
aaa
aaa
@@ -94203,7 +94501,7 @@ aAb
axY
aDl
aEi
-aEi
+bvP
aEi
aEi
aEi
@@ -94715,13 +95013,13 @@ axY
aAc
axY
aCp
-aDl
+bvO
aEk
aEj
aGd
aEl
aEk
-aJf
+bvR
aKn
aLz
axY
@@ -95231,7 +95529,7 @@ aAd
aCq
aDl
aEm
-aEm
+bvQ
aEm
aEm
aEm
diff --git a/_maps/map_files/PubbyStation/PubbyStation.dmm b/_maps/map_files/PubbyStation/PubbyStation.dmm
index e0e721840d..56bcff286e 100644
--- a/_maps/map_files/PubbyStation/PubbyStation.dmm
+++ b/_maps/map_files/PubbyStation/PubbyStation.dmm
@@ -15105,7 +15105,7 @@
/area/maintenance/apmaint)
"aEl" = (
/obj/structure/closet/coffin,
-/obj/item/toy/figure/librarian,
+/obj/item/toy/figure/curator,
/turf/open/floor/plating,
/area/maintenance/apmaint)
"aEm" = (
@@ -32850,10 +32850,6 @@
/turf/open/floor/plasteel/white,
/area/toxins/xenobiology)
"bnU" = (
-/obj/machinery/door/airlock/research{
- name = "Kill Room Access";
- req_access_txt = "55"
- },
/obj/structure/disposalpipe/segment{
dir = 4
},
diff --git a/_maps/map_files/PubbyStation/job_changes.dm b/_maps/map_files/PubbyStation/job_changes.dm
index 8b26cd5b68..d366a15ae3 100644
--- a/_maps/map_files/PubbyStation/job_changes.dm
+++ b/_maps/map_files/PubbyStation/job_changes.dm
@@ -18,5 +18,5 @@
access += GLOB.access_crematorium
minimal_access += GLOB.access_crematorium
-MAP_REMOVE_JOB(librarian)
+MAP_REMOVE_JOB(curator)
MAP_REMOVE_JOB(lawyer)
\ No newline at end of file
diff --git a/_maps/map_files/TgStation/tgstation.2.1.3.dmm b/_maps/map_files/TgStation/tgstation.2.1.3.dmm
index f2bf5eb504..220c1bd671 100644
--- a/_maps/map_files/TgStation/tgstation.2.1.3.dmm
+++ b/_maps/map_files/TgStation/tgstation.2.1.3.dmm
@@ -2501,7 +2501,7 @@
"afq" = (
/obj/machinery/computer/shuttle/pod{
pixel_y = -32;
- possible_destinations = "pod_asteroid3";
+ possible_destinations = "pod_lavaland3";
shuttleId = "pod3"
},
/obj/structure/chair{
@@ -7787,8 +7787,8 @@
"aqG" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid3";
- name = "asteroid"
+ id = "pod_lavaland3";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -17330,7 +17330,6 @@
/area/hallway/primary/central)
"aMf" = (
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L13";
name = "floor"
},
@@ -17836,7 +17835,6 @@
/area/hallway/primary/central)
"aNB" = (
/turf/open/floor/plasteel{
- desc = "";
icon_state = "L14"
},
/area/hallway/primary/central)
@@ -19015,6 +19013,12 @@
/turf/open/floor/wood,
/area/library)
"aQr" = (
+/obj/structure/closet/crate,
+/obj/item/clothing/shoes/workboots/mining,
+/obj/item/clothing/under/rank/curator/treasure_hunter,
+/obj/item/clothing/suit/curator,
+/obj/item/clothing/head/curator,
+/obj/item/weapon/storage/backpack/satchel/explorer,
/obj/machinery/light/small,
/turf/open/floor/engine/cult,
/area/library)
@@ -19510,7 +19514,7 @@
/turf/open/floor/wood,
/area/library)
"aRO" = (
-/obj/structure/bookcase/random/nonfiction,
+/obj/structure/displaycase/trophy,
/turf/open/floor/wood,
/area/library)
"aRP" = (
@@ -53823,8 +53827,8 @@
"cpe" = (
/obj/docking_port/stationary/random{
dir = 8;
- id = "pod_asteroid2";
- name = "asteroid"
+ id = "pod_lavaland2";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -54079,7 +54083,7 @@
/obj/machinery/computer/shuttle/pod{
pixel_x = 0;
pixel_y = -32;
- possible_destinations = "pod_asteroid2";
+ possible_destinations = "pod_lavaland2";
shuttleId = "pod2"
},
/obj/structure/chair{
@@ -57394,8 +57398,8 @@
"cwV" = (
/obj/docking_port/stationary/random{
dir = 8;
- id = "pod_asteroid1";
- name = "asteroid"
+ id = "pod_lavaland1";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -57508,7 +57512,7 @@
/obj/machinery/computer/shuttle/pod{
pixel_x = 0;
pixel_y = -32;
- possible_destinations = "pod_asteroid1";
+ possible_destinations = "pod_lavaland1";
shuttleId = "pod1"
},
/obj/structure/chair{
@@ -58424,7 +58428,7 @@
"czL" = (
/obj/machinery/computer/shuttle/pod{
pixel_y = -32;
- possible_destinations = "pod_asteroid4";
+ possible_destinations = "pod_lavaland4";
shuttleId = "pod4"
},
/obj/structure/chair{
@@ -58455,8 +58459,8 @@
"czN" = (
/obj/docking_port/stationary/random{
dir = 4;
- id = "pod_asteroid4";
- name = "asteroid"
+ id = "pod_lavaland4";
+ name = "lavaland"
},
/turf/open/space,
/area/space)
@@ -106507,7 +106511,7 @@ aIt
aPd
aIt
aRO
-aIt
+aRO
aUC
aVP
aXu
@@ -106764,7 +106768,7 @@ aNV
aPd
aIt
aRO
-aIt
+aRO
aIt
aVQ
aXu
diff --git a/_maps/map_files/generic/Centcomm.dmm b/_maps/map_files/generic/Centcomm.dmm
index d36c5165dc..e3870a49f8 100644
--- a/_maps/map_files/generic/Centcomm.dmm
+++ b/_maps/map_files/generic/Centcomm.dmm
@@ -5586,7 +5586,7 @@
/area/centcom/ferry)
"ot" = (
/obj/structure/closet/secure_closet/personal/cabinet,
-/obj/item/clothing/under/rank/librarian/curator,
+/obj/item/clothing/under/rank/curator/treasure_hunter,
/obj/item/clothing/under/skirt/black,
/obj/item/clothing/under/shorts/black,
/obj/item/clothing/under/pants/track,
@@ -14883,6 +14883,20 @@
/obj/machinery/computer/emergency_shuttle,
/turf/open/floor/mineral/titanium,
/area/shuttle/escape)
+"Me" = (
+/obj/machinery/light{
+ icon_state = "tube1";
+ dir = 8
+ },
+/turf/open/floor/mineral/titanium,
+/area/shuttle/escape)
+"Mf" = (
+/obj/machinery/light{
+ icon_state = "tube1";
+ dir = 4
+ },
+/turf/open/floor/mineral/titanium,
+/area/shuttle/escape)
(1,1,1) = {"
aa
@@ -64444,7 +64458,7 @@ Fa
Fh
Fh
Fh
-Fh
+Me
Fh
Fh
Fa
@@ -65729,7 +65743,7 @@ Fa
Md
Fp
FC
-Fh
+Mf
Fh
Fh
Fa
diff --git a/code/__DEFINES/clockcult.dm b/code/__DEFINES/clockcult.dm
index 9c86e031ab..acc0cdc9ab 100644
--- a/code/__DEFINES/clockcult.dm
+++ b/code/__DEFINES/clockcult.dm
@@ -37,15 +37,15 @@ GLOBAL_LIST_EMPTY(all_scripture) //a list containing scripture instances; not us
#define JUDGEMENT_CV_REQ 300
//general component/cooldown things
-#define SLAB_PRODUCTION_TIME 900 //how long(deciseconds) slabs require to produce a single component; defaults to 1 minute 30 seconds
+#define SLAB_PRODUCTION_TIME 450 //how long(deciseconds) slabs require to produce a single component; defaults to 45 seconds
-#define SLAB_SERVANT_SLOWDOWN 300 //how much each servant above 5 slows down slab-based generation; defaults to 30 seconds per sevant
+#define SLAB_SERVANT_SLOWDOWN 150 //how much each servant above 5 slows down slab-based generation; defaults to 15 seconds per sevant
-#define SLAB_SLOWDOWN_MAXIMUM 2700 //maximum slowdown from additional servants; defaults to 4 minutes 30 seconds
+#define SLAB_SLOWDOWN_MAXIMUM 1350 //maximum slowdown from additional servants; defaults to 2 minutes 15 seconds
-#define CACHE_PRODUCTION_TIME 600 //how long(deciseconds) caches require to produce a component; defaults to 1 minute
+#define CACHE_PRODUCTION_TIME 300 //how long(deciseconds) caches require to produce a component; defaults to 30 seconds
-#define ACTIVE_CACHE_SLOWDOWN 100 //how many additional deciseconds caches take to produce a component for each linked cache; defaults to 10 seconds
+#define ACTIVE_CACHE_SLOWDOWN 50 //how many additional deciseconds caches take to produce a component for each linked cache; defaults to 5 seconds
#define LOWER_PROB_PER_COMPONENT 10 //how much each component in the cache reduces the weight of getting another of that component type
@@ -87,9 +87,9 @@ GLOBAL_LIST_EMPTY(all_scripture) //a list containing scripture instances; not us
#define GATEWAY_RATVAR_ARRIVAL 300 //when progress is at or above this, game over ratvar's here everybody go home
-#define ARK_SUMMON_COST 3 //how many of each component an Ark costs to summon
+#define ARK_SUMMON_COST 5 //how many of each component an Ark costs to summon
-#define ARK_CONSUME_COST 7 //how many of each component an Ark needs to consume to activate
+#define ARK_CONSUME_COST 15 //how many of each component an Ark needs to consume to activate
//Objective text define
#define CLOCKCULT_OBJECTIVE "Construct the Ark of the Clockwork Justicar and free Ratvar."
diff --git a/code/__DEFINES/jobs.dm b/code/__DEFINES/jobs.dm
index 6d5310364f..cea01afc2a 100644
--- a/code/__DEFINES/jobs.dm
+++ b/code/__DEFINES/jobs.dm
@@ -32,7 +32,7 @@
#define BOTANIST (1<<2)
#define COOK (1<<3)
#define JANITOR (1<<4)
-#define LIBRARIAN (1<<5)
+#define CURATOR (1<<5)
#define QUARTERMASTER (1<<6)
#define CARGOTECH (1<<7)
#define MINER (1<<8)
diff --git a/code/__DEFINES/lighting.dm b/code/__DEFINES/lighting.dm
index fd98a68e07..7cfed2b483 100644
--- a/code/__DEFINES/lighting.dm
+++ b/code/__DEFINES/lighting.dm
@@ -16,10 +16,10 @@
#define LIGHTING_BASE_MATRIX \
list \
( \
- LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, 0, \
- LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, 0, \
- LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, 0, \
- LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, LIGHTING_SOFT_THRESHOLD, 0, \
+ 1, 1, 1, 0, \
+ 1, 1, 1, 0, \
+ 1, 1, 1, 0, \
+ 1, 1, 1, 0, \
0, 0, 0, 1 \
) \
@@ -78,4 +78,11 @@
#define DYNAMIC_LIGHTING_ENABLED 1 //dynamic lighting enabled
#define DYNAMIC_LIGHTING_FORCED 2 //dynamic lighting enabled even if the area doesn't require power
#define DYNAMIC_LIGHTING_IFSTARLIGHT 3 //dynamic lighting enabled only if starlight is.
-#define IS_DYNAMIC_LIGHTING(A) A.dynamic_lighting
\ No newline at end of file
+#define IS_DYNAMIC_LIGHTING(A) A.dynamic_lighting
+
+
+//code assumes higher numbers override lower numbers.
+#define LIGHTING_NO_UPDATE 0
+#define LIGHTING_VIS_UPDATE 1
+#define LIGHTING_CHECK_UPDATE 2
+#define LIGHTING_FORCE_UPDATE 3
\ No newline at end of file
diff --git a/code/__DEFINES/menu.dm b/code/__DEFINES/menu.dm
new file mode 100644
index 0000000000..2730adf87c
--- /dev/null
+++ b/code/__DEFINES/menu.dm
@@ -0,0 +1,3 @@
+#define CHECKBOX_NONE 0
+#define CHECKBOX_GROUP 1
+#define CHECKBOX_TOGGLE 2
\ No newline at end of file
diff --git a/code/__DEFINES/misc.dm b/code/__DEFINES/misc.dm
index efb9b3addf..321bbf7b67 100644
--- a/code/__DEFINES/misc.dm
+++ b/code/__DEFINES/misc.dm
@@ -201,6 +201,21 @@ GLOBAL_LIST_EMPTY(bloody_footprints_cache)
#define BLOOD_STATE_XENO "xeno"
#define BLOOD_STATE_OIL "oil"
#define BLOOD_STATE_NOT_BLOODY "no blood whatsoever"
+
+//suit sensors: sensor_mode defines
+
+#define SENSOR_OFF 0
+#define SENSOR_LIVING 1
+#define SENSOR_VITALS 2
+#define SENSOR_COORDS 3
+
+//suit sensors: has_sensor defines
+
+#define BROKEN_SENSORS -1
+#define NO_SENSORS 0
+#define HAS_SENSORS 1
+#define LOCKED_SENSORS 2
+
//Turf wet states
#define TURF_DRY 0
#define TURF_WET_WATER 1
diff --git a/code/__DEFINES/status_effects.dm b/code/__DEFINES/status_effects.dm
index bc5816dbb9..0bfbe31fb1 100644
--- a/code/__DEFINES/status_effects.dm
+++ b/code/__DEFINES/status_effects.dm
@@ -31,5 +31,6 @@
/////////////
#define STATUS_EFFECT_SIGILMARK /datum/status_effect/sigil_mark
+#define STATUS_EFFECT_BELLIGERENT /datum/status_effect/belligerent //forces the affected to walk, doing damage if they try to run
#define STATUS_EFFECT_HISWRATH /datum/status_effect/his_wrath //His Wrath.
diff --git a/code/__DEFINES/subsystems.dm.rej b/code/__DEFINES/subsystems.dm.rej
deleted file mode 100644
index cf39977224..0000000000
--- a/code/__DEFINES/subsystems.dm.rej
+++ /dev/null
@@ -1,18 +0,0 @@
-diff a/code/__DEFINES/subsystems.dm b/code/__DEFINES/subsystems.dm (rejected hunks)
-@@ -26,4 +26,13 @@
-
- #define INITIALIZE_HINT_NORMAL 0 //Nothing happens
- #define INITIALIZE_HINT_LATELOAD 1 //Call LateInitialize
--#define INITIALIZE_HINT_QDEL 2 //Call qdel on the atom
-\ No newline at end of file
-+#define INITIALIZE_HINT_QDEL 2 //Call qdel on the atom
-+
-+//type and all subtypes should always call Initialize in New()
-+#define INITIALIZE_IMMEDIATE(X) ##X/New(loc, ...){\
-+ ..();\
-+ if(!initialized) {\
-+ args[1] = TRUE;\
-+ SSatoms.InitAtom(src, args);\
-+ }\
-+}
-\ No newline at end of file
diff --git a/code/__HELPERS/_lists.dm b/code/__HELPERS/_lists.dm
index c0797819bc..8f340bff46 100644
--- a/code/__HELPERS/_lists.dm
+++ b/code/__HELPERS/_lists.dm
@@ -457,6 +457,7 @@
#define LAZYACCESS(L, I) (L ? (isnum(I) ? (I > 0 && I <= L.len ? L[I] : null) : L[I]) : null)
#define LAZYLEN(L) length(L)
#define LAZYCLEARLIST(L) if(L) L.Cut()
+#define SANITIZE_LIST(L) ( islist(L) ? L : list() )
/* Definining a counter as a series of key -> numeric value entries
diff --git a/code/__HELPERS/_logging.dm b/code/__HELPERS/_logging.dm
index 2785ba896f..a2a878211a 100644
--- a/code/__HELPERS/_logging.dm
+++ b/code/__HELPERS/_logging.dm
@@ -20,13 +20,13 @@
/proc/log_admin(text)
GLOB.admin_log.Add(text)
if (config.log_admin)
- GLOB.diary << "\[[time_stamp()]]ADMIN: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]ADMIN: [text]"
//Items using this proc are stripped from public logs - use with caution
/proc/log_admin_private(text)
GLOB.admin_log.Add(text)
if (config.log_admin)
- GLOB.diary << "\[[time_stamp()]]ADMINPRIVATE: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]ADMINPRIVATE: [text]"
/proc/log_adminsay(text)
if (config.log_adminchat)
@@ -38,67 +38,64 @@
/proc/log_game(text)
if (config.log_game)
- GLOB.diary << "\[[time_stamp()]]GAME: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]GAME: [text]"
/proc/log_vote(text)
if (config.log_vote)
- GLOB.diary << "\[[time_stamp()]]VOTE: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]VOTE: [text]"
/proc/log_access(text)
if (config.log_access)
- GLOB.diary << "\[[time_stamp()]]ACCESS: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]ACCESS: [text]"
/proc/log_say(text)
if (config.log_say)
- GLOB.diary << "\[[time_stamp()]]SAY: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]SAY: [text]"
/proc/log_prayer(text)
if (config.log_prayer)
- GLOB.diary << "\[[time_stamp()]]PRAY: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]PRAY: [text]"
/proc/log_law(text)
if (config.log_law)
- GLOB.diary << "\[[time_stamp()]]LAW: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]LAW: [text]"
/proc/log_ooc(text)
if (config.log_ooc)
- GLOB.diary << "\[[time_stamp()]]OOC: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]OOC: [text]"
/proc/log_whisper(text)
if (config.log_whisper)
- GLOB.diary << "\[[time_stamp()]]WHISPER: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]WHISPER: [text]"
/proc/log_emote(text)
if (config.log_emote)
- GLOB.diary << "\[[time_stamp()]]EMOTE: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]EMOTE: [text]"
/proc/log_attack(text)
if (config.log_attack)
- GLOB.diaryofmeanpeople << "\[[time_stamp()]]ATTACK: [text]"
+ GLOB.world_attack_log << "\[[time_stamp()]]ATTACK: [text]"
/proc/log_pda(text)
if (config.log_pda)
- GLOB.diary << "\[[time_stamp()]]PDA: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]PDA: [text]"
/proc/log_comment(text)
if (config.log_pda)
//reusing the PDA option because I really don't think news comments are worth a config option
- GLOB.diary << "\[[time_stamp()]]COMMENT: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]COMMENT: [text]"
/proc/log_chat(text)
if (config.log_pda)
- GLOB.diary << "\[[time_stamp()]]CHAT: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]CHAT: [text]"
/proc/log_sql(text)
if(config.sql_enabled)
- GLOB.diary << "\[[time_stamp()]]SQL: [text]"
+ GLOB.world_game_log << "\[[time_stamp()]]SQL: [text]"
//This replaces world.log so it displays both in DD and the file
/proc/log_world(text)
- if(config && config.log_runtimes)
- world.log = GLOB.runtime_diary
- world.log << text
- world.log = null
+ GLOB.world_runtime_log << text
world.log << text
// Helper procs for building detailed log lines
diff --git a/code/__HELPERS/bandetect.dm b/code/__HELPERS/bandetect.dm
deleted file mode 100644
index 19c0d37838..0000000000
--- a/code/__HELPERS/bandetect.dm
+++ /dev/null
@@ -1,37 +0,0 @@
-#define YOUNG 4
-
-
-/client/proc/join_date_check(y,m,d)
- var/datum/DBQuery/query_datediff = SSdbcore.NewQuery("SELECT DATEDIFF(Now(),'[y]-[m]-[d]')")
-
- if(!query_datediff.Execute())
- return FALSE
-
- if(query_datediff.NextRow())
- var/diff = text2num(query_datediff.item[1])
- if(config.use_account_age_for_jobs)
- player_age = max(0,diff) //So job code soesn't freak out if they are time traveling.
- if(diff < YOUNG)
- var/msg = "(IP: [address], ID: [computer_id]) is a new BYOND account made on [y]-[m]-[d]."
- if(diff < 0)
- msg += " They are also apparently from the future."
- message_admins("[key_name_admin(src)] [msg]")
- return TRUE
-#undef YOUNG
-
-
-/client/proc/findJoinDate()
- var/http[] = world.Export("http://byond.com/members/[src.ckey]?format=text")
- if(!http)
- log_world("Failed to connect to byond age check for [src.ckey]")
- return FALSE
-
- var/F = file2text(http["CONTENT"])
- if(F)
- var/regex/R = regex("joined = \"(\\d{4})-(\\d{2})-(\\d{2})\"")
- if(!R.Find(F))
- CRASH("Age check regex failed")
- var/y = R.group[1]
- var/m = R.group[2]
- var/d = R.group[3]
- return join_date_check(y,m,d)
diff --git a/code/__HELPERS/game.dm b/code/__HELPERS/game.dm
index 6fd41f7ea1..6bc79fb7d5 100644
--- a/code/__HELPERS/game.dm
+++ b/code/__HELPERS/game.dm
@@ -513,7 +513,7 @@
winset(C, "mainwindow", "flash=5")
/proc/AnnounceArrival(var/mob/living/carbon/human/character, var/rank)
- if(SSticker.current_state != GAME_STATE_PLAYING || !character)
+ if(!SSticker.IsRoundInProgress() || !character)
return
var/area/A = get_area(character)
var/message = "\
diff --git a/code/__HELPERS/text_vr.dm b/code/__HELPERS/text_vr.dm
index 06aadb6708..7cd683f456 100644
--- a/code/__HELPERS/text_vr.dm
+++ b/code/__HELPERS/text_vr.dm
@@ -24,4 +24,4 @@ GLOBAL_LIST_EMPTY(whitelisted_species_list)
/proc/log_mentor(text)
GLOB.mentor_log.Add(text)
- GLOB.diary << "\[[time_stamp()]]MENTOR: [text]"
\ No newline at end of file
+ GLOB.world_game_log << "\[[time_stamp()]]MENTOR: [text]"
\ No newline at end of file
diff --git a/code/__HELPERS/unsorted.dm b/code/__HELPERS/unsorted.dm
index 1da1b50aa3..d0fcb3bcbe 100644
--- a/code/__HELPERS/unsorted.dm
+++ b/code/__HELPERS/unsorted.dm
@@ -1342,6 +1342,7 @@ GLOBAL_DATUM_INIT(dview_mob, /mob/dview, new)
//This prevents RCEs from badmins
//kevinz000 if you touch this I will hunt you down
GLOBAL_VAR_INIT(valid_HTTPSGet, FALSE)
+GLOBAL_PROTECT(valid_HTTPSGet)
/proc/HTTPSGet(url)
if(findtext(url, "\""))
GLOB.valid_HTTPSGet = FALSE
diff --git a/code/_globalvars/lists/objects.dm b/code/_globalvars/lists/objects.dm
index be771e0676..e82976d4a3 100644
--- a/code/_globalvars/lists/objects.dm
+++ b/code/_globalvars/lists/objects.dm
@@ -29,6 +29,7 @@ GLOBAL_LIST_EMPTY(zombie_infection_list) // A list of all zombie_infection org
GLOBAL_LIST_EMPTY(meteor_list) // List of all meteors.
GLOBAL_LIST_EMPTY(active_jammers) // List of active radio jammers
GLOBAL_LIST_EMPTY(ladders)
+GLOBAL_LIST_EMPTY(trophy_cases)
GLOBAL_LIST_EMPTY(wire_color_directory)
GLOBAL_LIST_EMPTY(wire_name_directory)
\ No newline at end of file
diff --git a/code/_globalvars/lists/poll_ignore.dm b/code/_globalvars/lists/poll_ignore.dm
index ff6a4edd40..fadd68526d 100644
--- a/code/_globalvars/lists/poll_ignore.dm
+++ b/code/_globalvars/lists/poll_ignore.dm
@@ -5,5 +5,6 @@
#define POLL_IGNORE_POSSESSED_BLADE "possessed_blade"
#define POLL_IGNORE_ALIEN_LARVA "alien_larva"
#define POLL_IGNORE_CLOCKWORK_MARAUDER "clockwork_marauder"
+#define POLL_IGNORE_SYNDICATE "syndicate"
GLOBAL_LIST_EMPTY(poll_ignore)
diff --git a/code/_globalvars/logging.dm b/code/_globalvars/logging.dm
index 35adcef36c..00665bdfe2 100644
--- a/code/_globalvars/logging.dm
+++ b/code/_globalvars/logging.dm
@@ -1,28 +1,34 @@
-GLOBAL_VAR(diary)
-GLOBAL_PROTECT(diary)
-GLOBAL_VAR(runtime_diary)
-GLOBAL_PROTECT(runtime_diary)
-GLOBAL_VAR(diaryofmeanpeople)
-GLOBAL_PROTECT(diaryofmeanpeople)
-GLOBAL_VAR(href_logfile)
-GLOBAL_PROTECT(href_logfile)
-
-GLOBAL_LIST_EMPTY(bombers)
-GLOBAL_PROTECT(bombers)
-GLOBAL_LIST_EMPTY(admin_log)
-GLOBAL_PROTECT(admin_log)
-GLOBAL_LIST_EMPTY(lastsignalers) //keeps last 100 signals here in format: "[src] used \ref[src] @ location [src.loc]: [freq]/[code]"
-GLOBAL_PROTECT(lastsignalers)
-GLOBAL_LIST_EMPTY(lawchanges) //Stores who uploaded laws to which silicon-based lifeform, and what the law was
-GLOBAL_PROTECT(lawchanges)
-
-GLOBAL_LIST_EMPTY(combatlog)
-GLOBAL_PROTECT(combatlog)
-GLOBAL_LIST_EMPTY(IClog)
-GLOBAL_PROTECT(IClog)
-GLOBAL_LIST_EMPTY(OOClog)
-GLOBAL_PROTECT(OOClog)
-GLOBAL_LIST_EMPTY(adminlog)
-GLOBAL_PROTECT(adminlog)
-
+GLOBAL_VAR(log_directory)
+GLOBAL_PROTECT(log_directory)
+GLOBAL_VAR(world_game_log)
+GLOBAL_PROTECT(world_game_log)
+GLOBAL_VAR(world_runtime_log)
+GLOBAL_PROTECT(world_runtime_log)
+GLOBAL_VAR(world_attack_log)
+GLOBAL_PROTECT(world_attack_log)
+GLOBAL_VAR(world_href_log)
+GLOBAL_PROTECT(world_href_log)
+GLOBAL_VAR(round_id)
+GLOBAL_PROTECT(round_id)
+GLOBAL_VAR(config_error_log)
+GLOBAL_PROTECT(config_error_log)
+
+GLOBAL_LIST_EMPTY(bombers)
+GLOBAL_PROTECT(bombers)
+GLOBAL_LIST_EMPTY(admin_log)
+GLOBAL_PROTECT(admin_log)
+GLOBAL_LIST_EMPTY(lastsignalers) //keeps last 100 signals here in format: "[src] used \ref[src] @ location [src.loc]: [freq]/[code]"
+GLOBAL_PROTECT(lastsignalers)
+GLOBAL_LIST_EMPTY(lawchanges) //Stores who uploaded laws to which silicon-based lifeform, and what the law was
+GLOBAL_PROTECT(lawchanges)
+
+GLOBAL_LIST_EMPTY(combatlog)
+GLOBAL_PROTECT(combatlog)
+GLOBAL_LIST_EMPTY(IClog)
+GLOBAL_PROTECT(IClog)
+GLOBAL_LIST_EMPTY(OOClog)
+GLOBAL_PROTECT(OOClog)
+GLOBAL_LIST_EMPTY(adminlog)
+GLOBAL_PROTECT(adminlog)
+
GLOBAL_LIST_EMPTY(active_turfs_startlist)
\ No newline at end of file
diff --git a/code/_onclick/hud/_defines.dm b/code/_onclick/hud/_defines.dm
index 90c953a110..ce7014d765 100644
--- a/code/_onclick/hud/_defines.dm
+++ b/code/_onclick/hud/_defines.dm
@@ -21,7 +21,7 @@
#define ui_inventory "WEST:6,SOUTH:5"
//Middle left indicators
-#define ui_lingchemdisplay "WEST:6,CENTER-1:15"
+#define ui_lingchemdisplay "WEST,CENTER-1:15"
#define ui_lingstingdisplay "WEST:6,CENTER-3:11"
#define ui_crafting "12:-10,1:5"
#define ui_building "12:-10,1:21"
@@ -104,12 +104,17 @@
#define ui_health "EAST-1:28,CENTER-1:15"
#define ui_internal "EAST-1:28,CENTER:17"
-//borgs and aliens
-#define ui_alien_nightvision "EAST-1:28,CENTER:17"
+//borgs
#define ui_borg_health "EAST-1:28,CENTER-1:15" //borgs have the health display where humans have the pressure damage indicator.
-#define ui_alien_health "EAST-1:28,CENTER-1:15" //aliens have the health display where humans have the pressure damage indicator.
-#define ui_alienplasmadisplay "EAST-1:28,CENTER-2:15"
-#define ui_alien_queen_finder "EAST-1:28,CENTER-3:15"
+
+//aliens
+#define ui_alien_health "EAST,CENTER-1:15" //aliens have the health display where humans have the pressure damage indicator.
+#define ui_alienplasmadisplay "EAST,CENTER-2:15"
+#define ui_alien_queen_finder "EAST,CENTER-3:15"
+
+//constructs
+#define ui_construct_pull "EAST,CENTER-2:15"
+#define ui_construct_health "EAST,CENTER:15" //same as borgs and humans
// AI
diff --git a/code/_onclick/hud/alert.dm b/code/_onclick/hud/alert.dm
index 9c8fe9750a..b376706a42 100644
--- a/code/_onclick/hud/alert.dm
+++ b/code/_onclick/hud/alert.dm
@@ -393,6 +393,7 @@ or shoot a gun to move around via Newton's 3rd Law of Motion."
textlist += "
"
else
textlist += "Seconds until Ratvar's arrival: [G.get_arrival_text(TRUE)]
"
+ break
if(unconverted_ais_exist)
if(unconverted_ais_exist > 1)
textlist += "[unconverted_ais_exist] unconverted AIs exist!
"
diff --git a/code/_onclick/hud/constructs.dm b/code/_onclick/hud/constructs.dm
new file mode 100644
index 0000000000..dc3cea7f99
--- /dev/null
+++ b/code/_onclick/hud/constructs.dm
@@ -0,0 +1,18 @@
+
+/datum/hud/construct
+ ui_style_icon = 'icons/mob/screen_construct.dmi'
+
+/datum/hud/construct/New(mob/owner)
+ ..()
+ pull_icon = new /obj/screen/pull()
+ pull_icon.icon = ui_style_icon
+ pull_icon.update_icon(mymob)
+ pull_icon.screen_loc = ui_pull_resist
+ static_inventory += pull_icon
+
+ healths = new /obj/screen/healths/construct()
+ infodisplay += healths
+
+/mob/living/simple_animal/hostile/construct/create_mob_hud()
+ if(client && !hud_used)
+ hud_used = new /datum/hud/construct(src)
diff --git a/code/_onclick/hud/hud.dm b/code/_onclick/hud/hud.dm
index b1b4a1cbb3..f6a3688626 100644
--- a/code/_onclick/hud/hud.dm
+++ b/code/_onclick/hud/hud.dm
@@ -208,7 +208,6 @@
mymob.reload_fullscreen()
update_parallax_pref(screenmob)
-
/datum/hud/human/show_hud(version = 0,mob/viewmob)
..()
hidden_inventory_update(viewmob)
@@ -266,3 +265,6 @@
E.screen_loc = ui_equip_position(mymob)
if(mymob.hud_used)
show_hud(HUD_STYLE_STANDARD,mymob)
+
+/datum/hud/proc/update_locked_slots()
+ return
\ No newline at end of file
diff --git a/code/_onclick/hud/human.dm b/code/_onclick/hud/human.dm
index f35579c16b..8453b12085 100644
--- a/code/_onclick/hud/human.dm
+++ b/code/_onclick/hud/human.dm
@@ -124,7 +124,6 @@
inv_box.icon = ui_style
inv_box.slot_id = slot_w_uniform
inv_box.icon_state = "uniform"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_iclothing
toggleable_inventory += inv_box
@@ -133,7 +132,6 @@
inv_box.icon = ui_style
inv_box.slot_id = slot_wear_suit
inv_box.icon_state = "suit"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_oclothing
toggleable_inventory += inv_box
@@ -155,7 +153,6 @@
inv_box.name = "id"
inv_box.icon = ui_style
inv_box.icon_state = "id"
-// inv_box.icon_full = "template_small"
inv_box.screen_loc = ui_id
inv_box.slot_id = slot_wear_id
static_inventory += inv_box
@@ -164,7 +161,6 @@
inv_box.name = "mask"
inv_box.icon = ui_style
inv_box.icon_state = "mask"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_mask
inv_box.slot_id = slot_wear_mask
toggleable_inventory += inv_box
@@ -173,7 +169,6 @@
inv_box.name = "neck"
inv_box.icon = ui_style
inv_box.icon_state = "neck"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_neck
inv_box.slot_id = slot_neck
toggleable_inventory += inv_box
@@ -182,7 +177,6 @@
inv_box.name = "back"
inv_box.icon = ui_style
inv_box.icon_state = "back"
-// inv_box.icon_full = "template_small"
inv_box.screen_loc = ui_back
inv_box.slot_id = slot_back
static_inventory += inv_box
@@ -191,7 +185,6 @@
inv_box.name = "storage1"
inv_box.icon = ui_style
inv_box.icon_state = "pocket"
-// inv_box.icon_full = "template_small"
inv_box.screen_loc = ui_storage1
inv_box.slot_id = slot_l_store
static_inventory += inv_box
@@ -200,7 +193,6 @@
inv_box.name = "storage2"
inv_box.icon = ui_style
inv_box.icon_state = "pocket"
-// inv_box.icon_full = "template_small"
inv_box.screen_loc = ui_storage2
inv_box.slot_id = slot_r_store
static_inventory += inv_box
@@ -209,7 +201,6 @@
inv_box.name = "suit storage"
inv_box.icon = ui_style
inv_box.icon_state = "suit_storage"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_sstore1
inv_box.slot_id = slot_s_store
static_inventory += inv_box
@@ -233,7 +224,6 @@
inv_box.name = "gloves"
inv_box.icon = ui_style
inv_box.icon_state = "gloves"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_gloves
inv_box.slot_id = slot_gloves
toggleable_inventory += inv_box
@@ -242,7 +232,6 @@
inv_box.name = "eyes"
inv_box.icon = ui_style
inv_box.icon_state = "glasses"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_glasses
inv_box.slot_id = slot_glasses
toggleable_inventory += inv_box
@@ -251,7 +240,6 @@
inv_box.name = "ears"
inv_box.icon = ui_style
inv_box.icon_state = "ears"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_ears
inv_box.slot_id = slot_ears
toggleable_inventory += inv_box
@@ -260,7 +248,6 @@
inv_box.name = "head"
inv_box.icon = ui_style
inv_box.icon_state = "head"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_head
inv_box.slot_id = slot_head
toggleable_inventory += inv_box
@@ -269,7 +256,6 @@
inv_box.name = "shoes"
inv_box.icon = ui_style
inv_box.icon_state = "shoes"
-// inv_box.icon_full = "template"
inv_box.screen_loc = ui_shoes
inv_box.slot_id = slot_shoes
toggleable_inventory += inv_box
@@ -327,6 +313,18 @@
inv_slots[inv.slot_id] = inv
inv.update_icon()
+/datum/hud/human/update_locked_slots()
+ if(!mymob)
+ return
+ var/mob/living/carbon/human/H = mymob
+ var/datum/species/S = H.dna.species
+ for(var/obj/screen/inventory/inv in (static_inventory + toggleable_inventory))
+ if(inv.slot_id)
+ if(inv.slot_id in S.no_equip)
+ inv.alpha = 128
+ else
+ inv.alpha = initial(inv.alpha)
+
/datum/hud/human/hidden_inventory_update(mob/viewer)
if(!mymob)
return
diff --git a/code/_onclick/hud/screen_objects.dm b/code/_onclick/hud/screen_objects.dm
index 81754efc93..bfab19ba5f 100644
--- a/code/_onclick/hud/screen_objects.dm
+++ b/code/_onclick/hud/screen_objects.dm
@@ -532,6 +532,12 @@
screen_loc = ui_health
mouse_opacity = 0
+/obj/screen/healths/construct
+ icon = 'icons/mob/screen_construct.dmi'
+ icon_state = "artificer_health0"
+ screen_loc = ui_construct_health
+ mouse_opacity = 0
+
/obj/screen/healthdoll
name = "health doll"
screen_loc = ui_healthdoll
diff --git a/code/citadel/_cit_helpers.dm b/code/citadel/_cit_helpers.dm
index 6e4ea762f1..db0626fa9c 100644
--- a/code/citadel/_cit_helpers.dm
+++ b/code/citadel/_cit_helpers.dm
@@ -117,7 +117,7 @@ GLOBAL_VAR_INIT(dlooc_allowed, 1)
prefs.chat_toggles ^= CHAT_LOOC
prefs.save_preferences()
src << "You will [(prefs.chat_toggles & CHAT_LOOC) ? "now" : "no longer"] see messages on the LOOC channel."
- feedback_add_details("admin_verb","TLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+ SSblackbox.add_details("admin_verb","TLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/datum/admins/proc/togglelooc()
set category = "Server"
@@ -126,7 +126,7 @@ GLOBAL_VAR_INIT(dlooc_allowed, 1)
toggle_looc()
log_admin("[key_name(usr)] toggled LOOC.")
message_admins("[key_name_admin(usr)] toggled LOOC.")
- feedback_add_details("admin_verb","TLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+ SSblackbox.add_details("admin_verb","TLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/proc/toggle_looc(toggle = null)
if(toggle != null) //if we're specifically en/disabling ooc
@@ -146,7 +146,7 @@ GLOBAL_VAR_INIT(dlooc_allowed, 1)
log_admin("[key_name(usr)] toggled Dead LOOC.")
message_admins("[key_name_admin(usr)] toggled Dead LOOC.")
- feedback_add_details("admin_verb","TDLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+ SSblackbox.add_details("admin_verb","TDLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/mob/living/carbon/proc/has_penis()
diff --git a/code/controllers/admin.dm b/code/controllers/admin.dm
index 2be7139a27..3565620c88 100644
--- a/code/controllers/admin.dm
+++ b/code/controllers/admin.dm
@@ -45,9 +45,9 @@ INITIALIZE_IMMEDIATE(/obj/effect/statclick)
switch(controller)
if("Master")
Recreate_MC()
- feedback_add_details("admin_verb","Restart Master Controller")
+ SSblackbox.add_details("admin_verb","Restart Master Controller")
if("Failsafe")
new /datum/controller/failsafe()
- feedback_add_details("admin_verb","Restart Failsafe Controller")
+ SSblackbox.add_details("admin_verb","Restart Failsafe Controller")
message_admins("Admin [key_name_admin(usr)] has restarted the [controller] controller.")
diff --git a/code/controllers/configuration.dm b/code/controllers/configuration.dm
index fd3fe6d685..4d9c819ef9 100644
--- a/code/controllers/configuration.dm
+++ b/code/controllers/configuration.dm
@@ -43,10 +43,8 @@
var/log_attack = 0 // log attack messages
var/log_adminchat = 0 // log admin chat messages
var/log_pda = 0 // log pda messages
- var/log_hrefs = 0 // log all links clicked in-game. Could be used for debugging and tracking down exploits
var/log_twitter = 0 // log certain expliotable parrots and other such fun things in a JSON file of twitter valid phrases.
var/log_world_topic = 0 // log all world.Topic() calls
- var/log_runtimes = FALSE // log runtimes into a file
var/sql_enabled = 0 // for sql switching
var/allow_admin_ooccolor = 0 // Allows admins with relevant permissions to have their own ooc colour
var/allow_vote_restart = 0 // allow votes to restart
@@ -66,9 +64,9 @@
var/respawn = 1
var/guest_jobban = 1
var/usewhitelist = 0
- var/inactivity_period = 3000 //time in ds until a player is considered inactive
- var/afk_period = 6000 //time in ds until a player is considered afk and kickable
- var/kick_inactive = FALSE //force disconnect for inactive players
+ var/inactivity_period = 3000 //time in ds until a player is considered inactive
+ var/afk_period = 6000 //time in ds until a player is considered afk and kickable
+ var/kick_inactive = FALSE //force disconnect for inactive players
var/load_jobs_from_txt = 0
var/automute_on = 0 //enables automuting/spam prevention
var/minimal_access_threshold = 0 //If the number of players is larger than this threshold, minimal access will be turned on.
@@ -129,6 +127,7 @@
var/forbid_peaceborg = 0
var/panic_bunker = 0 // prevents new people it hasn't seen before from connecting
var/notify_new_player_age = 0 // how long do we notify admins of a new player
+ var/notify_new_player_account_age = 0 // how long do we notify admins of a new byond account
var/irc_first_connection_alert = 0 // do we notify the irc channel when somebody is connecting for the first time?
var/traitor_scaling_coeff = 6 //how much does the amount of players get divided by to determine traitors
@@ -269,7 +268,7 @@
if(M.config_tag)
if(!(M.config_tag in modes)) // ensure each mode is added only once
- GLOB.diary << "Adding game mode [M.name] ([M.config_tag]) to configuration."
+ GLOB.config_error_log << "Adding game mode [M.name] ([M.config_tag]) to configuration."
modes += M.config_tag
mode_names[M.config_tag] = M.name
probabilities[M.config_tag] = M.probability
@@ -291,7 +290,7 @@
GLOB.abandon_allowed = respawn
/datum/configuration/proc/load(filename, type = "config") //the type can also be game_options, in which case it uses a different switch. not making it separate to not copypaste code - Urist
- var/list/Lines = world.file2list(filename)
+ var/list/Lines = world.file2list(filename)
for(var/t in Lines)
if(!t)
@@ -358,8 +357,6 @@
log_adminchat = 1
if("log_pda")
log_pda = 1
- if("log_hrefs")
- log_hrefs = 1
if("log_twitter")
log_twitter = 1
if("log_world_topic")
@@ -410,12 +407,12 @@
usewhitelist = TRUE
if("allow_metadata")
allow_Metadata = 1
- if("inactivity_period")
- inactivity_period = text2num(value) * 10 //documented as seconds in config.txt
- if("afk_period")
- afk_period = text2num(value) * 10 // ^^^
+ if("inactivity_period")
+ inactivity_period = text2num(value) * 10 //documented as seconds in config.txt
+ if("afk_period")
+ afk_period = text2num(value) * 10 // ^^^
if("kick_inactive")
- kick_inactive = TRUE
+ kick_inactive = TRUE
if("load_jobs_from_txt")
load_jobs_from_txt = 1
if("forbid_singulo_possession")
@@ -476,6 +473,8 @@
panic_bunker = 1
if("notify_new_player_age")
notify_new_player_age = text2num(value)
+ if("notify_new_player_account_age")
+ notify_new_player_account_age = text2num(value)
if("irc_first_connection_alert")
irc_first_connection_alert = 1
if("check_randomizer")
@@ -493,12 +492,6 @@
ipintel_save_bad = text2num(value)
if("aggressive_changelog")
aggressive_changelog = 1
- if("log_runtimes")
- log_runtimes = TRUE
- var/newlog = file("data/logs/runtimes/runtime-[time2text(world.realtime, "YYYY-MM-DD")].log")
- if(GLOB.runtime_diary != newlog)
- world.log << "Now logging runtimes to data/logs/runtimes/runtime-[time2text(world.realtime, "YYYY-MM-DD")].log"
- GLOB.runtime_diary = newlog
if("autoconvert_notes")
autoconvert_notes = 1
if("allow_webclient")
@@ -542,7 +535,7 @@
if("error_msg_delay")
error_msg_delay = text2num(value)
else
- GLOB.diary << "Unknown setting in configuration: '[name]'"
+ GLOB.config_error_log << "Unknown setting in configuration: '[name]'"
else if(type == "game_options")
switch(name)
@@ -605,13 +598,13 @@
if(mode_name in modes)
continuous[mode_name] = 1
else
- GLOB.diary << "Unknown continuous configuration definition: [mode_name]."
+ GLOB.config_error_log << "Unknown continuous configuration definition: [mode_name]."
if("midround_antag")
var/mode_name = lowertext(value)
if(mode_name in modes)
midround_antag[mode_name] = 1
else
- GLOB.diary << "Unknown midround antagonist configuration definition: [mode_name]."
+ GLOB.config_error_log << "Unknown midround antagonist configuration definition: [mode_name]."
if("midround_antag_time_check")
midround_antag_time_check = text2num(value)
if("midround_antag_life_check")
@@ -627,9 +620,9 @@
if(mode_name in modes)
min_pop[mode_name] = text2num(mode_value)
else
- GLOB.diary << "Unknown minimum population configuration definition: [mode_name]."
+ GLOB.config_error_log << "Unknown minimum population configuration definition: [mode_name]."
else
- GLOB.diary << "Incorrect minimum population configuration definition: [mode_name] [mode_value]."
+ GLOB.config_error_log << "Incorrect minimum population configuration definition: [mode_name] [mode_value]."
if("max_pop")
var/pop_pos = findtext(value, " ")
var/mode_name = null
@@ -641,9 +634,9 @@
if(mode_name in modes)
max_pop[mode_name] = text2num(mode_value)
else
- GLOB.diary << "Unknown maximum population configuration definition: [mode_name]."
+ GLOB.config_error_log << "Unknown maximum population configuration definition: [mode_name]."
else
- GLOB.diary << "Incorrect maximum population configuration definition: [mode_name] [mode_value]."
+ GLOB.config_error_log << "Incorrect maximum population configuration definition: [mode_name] [mode_value]."
if("shuttle_refuel_delay")
shuttle_refuel_delay = text2num(value)
if("show_game_type_odds")
@@ -671,9 +664,9 @@
if(prob_name in modes)
probabilities[prob_name] = text2num(prob_value)
else
- GLOB.diary << "Unknown game mode probability configuration definition: [prob_name]."
+ GLOB.config_error_log << "Unknown game mode probability configuration definition: [prob_name]."
else
- GLOB.diary << "Incorrect probability configuration definition: [prob_name] [prob_value]."
+ GLOB.config_error_log << "Incorrect probability configuration definition: [prob_name] [prob_value]."
if("protect_roles_from_antagonist")
protect_roles_from_antagonist = 1
@@ -720,7 +713,7 @@
// Value is in the form "LAWID,NUMBER"
var/list/L = splittext(value, ",")
if(L.len != 2)
- GLOB.diary << "Invalid LAW_WEIGHT: " + t
+ GLOB.config_error_log << "Invalid LAW_WEIGHT: " + t
continue
var/lawid = L[1]
var/weight = text2num(L[2])
@@ -776,8 +769,8 @@
mentors_mobname_only = 1
if ("mentor_legacy_system")
mentor_legacy_system = 1
- else
- GLOB.diary << "Unknown setting in configuration: '[name]'"
+ // else
+ // GLOB.config_error_log << "Adding game mode [M.name] ([M.config_tag]) to configuration."
fps = round(fps)
if(fps <= 0)
@@ -785,7 +778,7 @@
/datum/configuration/proc/loadmaplist(filename)
- var/list/Lines = world.file2list(filename)
+ var/list/Lines = world.file2list(filename)
var/datum/map_config/currentmap = null
for(var/t in Lines)
@@ -831,11 +824,11 @@
maplist[currentmap.map_name] = currentmap
currentmap = null
else
- GLOB.diary << "Unknown command in map vote config: '[command]'"
+ GLOB.config_error_log << "Unknown command in map vote config: '[command]'"
/datum/configuration/proc/loadsql(filename)
- var/list/Lines = world.file2list(filename)
+ var/list/Lines = world.file2list(filename)
for(var/t in Lines)
if(!t)
continue
@@ -875,7 +868,7 @@
if("feedback_tableprefix")
global.sqlfdbktableprefix = value
else
- GLOB.diary << "Unknown setting in configuration: '[name]'"
+ GLOB.config_error_log << "Unknown setting in configuration: '[name]'"
/datum/configuration/proc/pick_mode(mode_name)
// I wish I didn't have to instance the game modes in order to look up
diff --git a/code/controllers/globals.dm b/code/controllers/globals.dm
index cd86e0d97c..89f8a81f20 100644
--- a/code/controllers/globals.dm
+++ b/code/controllers/globals.dm
@@ -52,6 +52,12 @@ GLOBAL_REAL(GLOB, /datum/controller/global_vars)
/datum/controller/global_vars/Initialize()
gvars_datum_init_order = list()
gvars_datum_protected_varlist = list("gvars_datum_protected_varlist")
+
+ //See https://github.com/tgstation/tgstation/issues/26954
+ for(var/I in typesof(/datum/controller/global_vars/proc))
+ var/CLEANBOT_RETURNS = "[I]"
+ pass(CLEANBOT_RETURNS)
+
for(var/I in vars - gvars_datum_in_built_vars)
var/start_tick = world.time
call(src, "InitGlobal[I]")()
diff --git a/code/controllers/master.dm b/code/controllers/master.dm
index ab4ff43b04..c8157748c5 100644
--- a/code/controllers/master.dm
+++ b/code/controllers/master.dm
@@ -48,7 +48,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
var/initializations_finished_with_no_players_logged_in //I wonder what this could be?
// Has round started? (So we know what subsystems to run)
- var/round_started = 0
+ var/local_round_started = FALSE //Don't read this var, use SSticker.HasRoundStarted() instead
// The type of the last subsystem to be process()'d.
var/last_type_processed
@@ -189,7 +189,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
// Notify the MC that the round has started.
/datum/controller/master/proc/RoundStart()
- round_started = 1
+ local_round_started = TRUE
var/timer = world.time
for (var/datum/controller/subsystem/SS in subsystems)
if (SS.flags & SS_FIRE_IN_LOBBY || SS.flags & SS_TICKER)
@@ -222,7 +222,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
// local vars rock
// Schedule the first run of the Subsystems.
- round_started = world.has_round_started()
+ local_round_started = world.has_round_started()
//all this shit is here so that flag edits can be refreshed by restarting the MC. (and for speed)
var/list/tickersubsystems = list()
var/list/normalsubsystems = list()
@@ -245,7 +245,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
lobbysubsystems += SS
timer += world.tick_lag * rand(1, 5)
SS.next_fire = timer
- else if (round_started)
+ else if (local_round_started)
timer += world.tick_lag * rand(1, 5)
SS.next_fire = timer
normalsubsystems += SS
@@ -280,7 +280,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
// because sleeps are processed in the order received, so longer sleeps are more likely to run first
if (world.tick_usage > TICK_LIMIT_MC)
sleep_delta += 2
- GLOB.CURRENT_TICKLIMIT = TICK_LIMIT_RUNNING - (TICK_LIMIT_RUNNING * 0.5)
+ GLOB.CURRENT_TICKLIMIT = TICK_LIMIT_RUNNING * 0.5
sleep(world.tick_lag * (processing + sleep_delta))
continue
@@ -296,7 +296,7 @@ GLOBAL_VAR_INIT(CURRENT_TICKLIMIT, TICK_LIMIT_RUNNING)
if (!Failsafe || (Failsafe.processing_interval > 0 && (Failsafe.lasttick+(Failsafe.processing_interval*5)) < world.time))
new/datum/controller/failsafe() // (re)Start the failsafe.
if (!queue_head || !(iteration % 3))
- if (round_started)
+ if (local_round_started)
subsystems_to_check = normalsubsystems
else
subsystems_to_check = lobbysubsystems
diff --git a/code/controllers/subsystem/atoms.dm.rej b/code/controllers/subsystem/atoms.dm.rej
deleted file mode 100644
index 4d7225164f..0000000000
--- a/code/controllers/subsystem/atoms.dm.rej
+++ /dev/null
@@ -1,9 +0,0 @@
-diff a/code/controllers/subsystem/atoms.dm b/code/controllers/subsystem/atoms.dm (rejected hunks)
-@@ -12,6 +12,7 @@ SUBSYSTEM_DEF(atoms)
- var/old_initialized
-
- var/list/late_loaders
-+ var/list/created_atoms
-
- var/list/BadInitializeCalls = list()
-
diff --git a/code/orphaned_procs/statistics.dm b/code/controllers/subsystem/blackbox.dm
similarity index 55%
rename from code/orphaned_procs/statistics.dm
rename to code/controllers/subsystem/blackbox.dm
index d6cdcda6c1..a807202c9e 100644
--- a/code/orphaned_procs/statistics.dm
+++ b/code/controllers/subsystem/blackbox.dm
@@ -1,9 +1,7 @@
-GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
-
-//the feedback datum; stores all feedback
-/datum/feedback
- var/list/messages = list()
- var/list/messages_admin = list()
+SUBSYSTEM_DEF(blackbox)
+ name = "Blackbox"
+ wait = 6000
+ flags = SS_NO_TICK_CHECK
var/list/msg_common = list()
var/list/msg_science = list()
@@ -15,21 +13,48 @@ GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
var/list/msg_syndicate = list()
var/list/msg_service = list()
var/list/msg_cargo = list()
+ var/list/msg_other = list()
- var/list/datum/feedback_variable/feedback = new()
+ var/list/feedback = list() //list of datum/feedback_variable
-/datum/feedback/proc/find_feedback_datum(variable)
- for (var/datum/feedback_variable/FV in feedback)
- if (FV.get_variable() == variable)
- return FV
- var/datum/feedback_variable/FV = new(variable)
- feedback += FV
- return FV
+//poll population
+/datum/controller/subsystem/blackbox/fire()
+ if(!SSdbcore.Connect())
+ return
+ var/playercount = 0
+ for(var/mob/M in GLOB.player_list)
+ if(M.client)
+ playercount += 1
+ var/admincount = GLOB.admins.len
+ var/datum/DBQuery/query_record_playercount = SSdbcore.NewQuery("INSERT INTO [format_table_name("legacy_population")] (playercount, admincount, time, server_ip, server_port) VALUES ([playercount], [admincount], '[SQLtime()]', INET_ATON('[world.internet_address]'), '[world.port]')")
+ query_record_playercount.Execute()
-/datum/feedback/proc/get_round_feedback()
- return feedback
+/datum/controller/subsystem/blackbox/Recover()
+ msg_common = SSblackbox.msg_common
+ msg_science = SSblackbox.msg_science
+ msg_command = SSblackbox.msg_command
+ msg_medical = SSblackbox.msg_medical
+ msg_engineering = SSblackbox.msg_engineering
+ msg_security = SSblackbox.msg_security
+ msg_deathsquad = SSblackbox.msg_deathsquad
+ msg_syndicate = SSblackbox.msg_syndicate
+ msg_service = SSblackbox.msg_service
+ msg_cargo = SSblackbox.msg_cargo
+ msg_other = SSblackbox.msg_other
-/datum/feedback/proc/round_end_data_gathering()
+
+ feedback = SSblackbox.feedback
+
+//no touchie
+/datum/controller/subsystem/blackbox/can_vv_get(var_name)
+ if(var_name == "feedback")
+ return FALSE
+ return ..()
+
+/datum/controller/subsystem/blackbox/vv_edit_var(var_name, var_value)
+ return FALSE
+
+/datum/controller/subsystem/blackbox/Shutdown()
var/pda_msg_amt = 0
var/rc_msg_amt = 0
@@ -39,41 +64,26 @@ GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
if (MS.rc_msgs.len > rc_msg_amt)
rc_msg_amt = MS.rc_msgs.len
- feedback_set_details("radio_usage","")
+ set_details("radio_usage","")
- feedback_add_details("radio_usage","COM-[msg_common.len]")
- feedback_add_details("radio_usage","SCI-[msg_science.len]")
- feedback_add_details("radio_usage","HEA-[msg_command.len]")
- feedback_add_details("radio_usage","MED-[msg_medical.len]")
- feedback_add_details("radio_usage","ENG-[msg_engineering.len]")
- feedback_add_details("radio_usage","SEC-[msg_security.len]")
- feedback_add_details("radio_usage","DTH-[msg_deathsquad.len]")
- feedback_add_details("radio_usage","SYN-[msg_syndicate.len]")
- feedback_add_details("radio_usage","SRV-[msg_service.len]")
- feedback_add_details("radio_usage","CAR-[msg_cargo.len]")
- feedback_add_details("radio_usage","OTH-[messages.len]")
- feedback_add_details("radio_usage","PDA-[pda_msg_amt]")
- feedback_add_details("radio_usage","RC-[rc_msg_amt]")
+ add_details("radio_usage","COM-[msg_common.len]")
+ add_details("radio_usage","SCI-[msg_science.len]")
+ add_details("radio_usage","HEA-[msg_command.len]")
+ add_details("radio_usage","MED-[msg_medical.len]")
+ add_details("radio_usage","ENG-[msg_engineering.len]")
+ add_details("radio_usage","SEC-[msg_security.len]")
+ add_details("radio_usage","DTH-[msg_deathsquad.len]")
+ add_details("radio_usage","SYN-[msg_syndicate.len]")
+ add_details("radio_usage","SRV-[msg_service.len]")
+ add_details("radio_usage","CAR-[msg_cargo.len]")
+ add_details("radio_usage","OTH-[msg_other.len]")
+ add_details("radio_usage","PDA-[pda_msg_amt]")
+ add_details("radio_usage","RC-[rc_msg_amt]")
- feedback_set_details("round_end","[time2text(world.realtime)]") //This one MUST be the last one that gets set.
+ set_details("round_end","[time2text(world.realtime)]") //This one MUST be the last one that gets set.
-//This proc is only to be called at round end.
-/datum/feedback/proc/save_all_data_to_sql()
- if (!feedback) return
-
- round_end_data_gathering() //round_end time logging and some other data processing
- if (!SSdbcore.Connect()) return
- var/round_id
-
- var/datum/DBQuery/query_feedback_max_id = SSdbcore.NewQuery("SELECT MAX(round_id) AS round_id FROM [format_table_name("feedback")]")
- if(!query_feedback_max_id.Execute())
+ if (!SSdbcore.Connect())
return
- while (query_feedback_max_id.NextRow())
- round_id = query_feedback_max_id.item[1]
-
- if (!isnum(round_id))
- round_id = text2num(round_id)
- round_id++
var/sqlrowlist = ""
@@ -81,7 +91,7 @@ GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
if (sqlrowlist != "")
sqlrowlist += ", " //a comma (,) at the start of the first row to insert will trigger a SQL error
- sqlrowlist += "(null, Now(), [round_id], \"[sanitizeSQL(FV.get_variable())]\", [FV.get_value()], \"[sanitizeSQL(FV.get_details())]\")"
+ sqlrowlist += "(null, Now(), [GLOB.round_id], \"[sanitizeSQL(FV.get_variable())]\", [FV.get_value()], \"[sanitizeSQL(FV.get_details())]\")"
if (sqlrowlist == "")
return
@@ -89,69 +99,99 @@ GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
var/datum/DBQuery/query_feedback_save = SSdbcore.NewQuery("INSERT DELAYED IGNORE INTO [format_table_name("feedback")] VALUES " + sqlrowlist)
query_feedback_save.Execute()
+/datum/controller/subsystem/blackbox/proc/LogBroadcast(blackbox_msg, freq)
+ switch(freq)
+ if(1459)
+ msg_common += blackbox_msg
+ if(1351)
+ msg_science += blackbox_msg
+ if(1353)
+ msg_command += blackbox_msg
+ if(1355)
+ msg_medical += blackbox_msg
+ if(1357)
+ msg_engineering += blackbox_msg
+ if(1359)
+ msg_security += blackbox_msg
+ if(1441)
+ msg_deathsquad += blackbox_msg
+ if(1213)
+ msg_syndicate += blackbox_msg
+ if(1349)
+ msg_service += blackbox_msg
+ if(1347)
+ msg_cargo += blackbox_msg
+ else
+ msg_other += blackbox_msg
-/proc/feedback_set(variable,value)
- if(!GLOB.blackbox)
- return
+/datum/controller/subsystem/blackbox/proc/find_feedback_datum(variable)
+ for(var/datum/feedback_variable/FV in feedback)
+ if(FV.get_variable() == variable)
+ return FV
- var/datum/feedback_variable/FV = GLOB.blackbox.find_feedback_datum(variable)
-
- if(!FV)
- return
+ var/datum/feedback_variable/FV = new(variable)
+ feedback += FV
+ return FV
+/datum/controller/subsystem/blackbox/proc/set_val(variable, value)
+ var/datum/feedback_variable/FV = find_feedback_datum(variable)
FV.set_value(value)
-/proc/feedback_inc(variable,value)
- if(!GLOB.blackbox)
- return
-
- var/datum/feedback_variable/FV = GLOB.blackbox.find_feedback_datum(variable)
-
- if(!FV)
- return
-
+/datum/controller/subsystem/blackbox/proc/inc(variable, value)
+ var/datum/feedback_variable/FV = find_feedback_datum(variable)
FV.inc(value)
-/proc/feedback_dec(variable,value)
- if(!GLOB.blackbox)
- return
-
- var/datum/feedback_variable/FV = GLOB.blackbox.find_feedback_datum(variable)
-
- if(!FV)
- return
-
+/datum/controller/subsystem/blackbox/proc/dec(variable,value)
+ var/datum/feedback_variable/FV = find_feedback_datum(variable)
FV.dec(value)
-/proc/feedback_set_details(variable,details)
- if(!GLOB.blackbox)
- return
-
- var/datum/feedback_variable/FV = GLOB.blackbox.find_feedback_datum(variable)
-
- if(!FV)
- return
-
+/datum/controller/subsystem/blackbox/proc/set_details(variable,details)
+ var/datum/feedback_variable/FV = find_feedback_datum(variable)
FV.set_details(details)
-/proc/feedback_add_details(variable,details)
- if(!GLOB.blackbox)
- return
-
- var/datum/feedback_variable/FV = GLOB.blackbox.find_feedback_datum(variable)
-
- if(!FV)
- return
-
+/datum/controller/subsystem/blackbox/proc/add_details(variable,details)
+ var/datum/feedback_variable/FV = find_feedback_datum(variable)
FV.add_details(details)
+/datum/controller/subsystem/blackbox/proc/ReportDeath(mob/living/L)
+ if(!SSdbcore.Connect())
+ return
+ if(!L || !L.key || !L.mind)
+ return
+ var/turf/T = get_turf(L)
+ var/area/placeofdeath = get_area(T.loc)
+ var/sqlname = sanitizeSQL(L.real_name)
+ var/sqlkey = sanitizeSQL(L.ckey)
+ var/sqljob = sanitizeSQL(L.mind.assigned_role)
+ var/sqlspecial = sanitizeSQL(L.mind.special_role)
+ var/sqlpod = sanitizeSQL(placeofdeath.name)
+ var/laname
+ var/lakey
+ if(L.lastattacker && ismob(L.lastattacker))
+ var/mob/LA = L.lastattacker
+ laname = sanitizeSQL(LA.real_name)
+ lakey = sanitizeSQL(LA.key)
+ var/sqlgender = sanitizeSQL(L.gender)
+ var/sqlbrute = sanitizeSQL(L.getBruteLoss())
+ var/sqlfire = sanitizeSQL(L.getFireLoss())
+ var/sqlbrain = sanitizeSQL(L.getBrainLoss())
+ var/sqloxy = sanitizeSQL(L.getOxyLoss())
+ var/sqltox = sanitizeSQL(L.getStaminaLoss())
+ var/sqlclone = sanitizeSQL(L.getStaminaLoss())
+ var/sqlstamina = sanitizeSQL(L.getStaminaLoss())
+ var/coord = sanitizeSQL("[L.x], [L.y], [L.z]")
+ var/map = sanitizeSQL(SSmapping.config.map_name)
+ var/datum/DBQuery/query_report_death = SSdbcore.NewQuery("INSERT INTO [format_table_name("death")] (name, byondkey, job, special, pod, tod, laname, lakey, gender, bruteloss, fireloss, brainloss, oxyloss, toxloss, cloneloss, staminaloss, coord, mapname, server_ip, server_port) VALUES ('[sqlname]', '[sqlkey]', '[sqljob]', '[sqlspecial]', '[sqlpod]', '[SQLtime()]', '[laname]', '[lakey]', '[sqlgender]', [sqlbrute], [sqlfire], [sqlbrain], [sqloxy], [sqltox], [sqlclone], [sqlstamina], '[coord]', '[map]', INET_ATON('[world.internet_address]'), '[world.port]')")
+ query_report_death.Execute()
+
+
//feedback variable datum, for storing all kinds of data
/datum/feedback_variable
var/variable
var/value
var/details
-/datum/feedback_variable/New(var/param_variable,var/param_value = 0)
+/datum/feedback_variable/New(param_variable, param_value = 0)
variable = param_variable
value = param_value
@@ -204,50 +244,3 @@ GLOBAL_DATUM_INIT(blackbox, /datum/feedback, new)
/datum/feedback_variable/proc/get_parsed()
return list(variable,value,details)
-
-//sql reporting procs
-/proc/sql_poll_population()
- if(!config.sql_enabled)
- return
- if(!SSdbcore.Connect())
- return
- var/playercount = 0
- for(var/mob/M in GLOB.player_list)
- if(M.client)
- playercount += 1
- var/admincount = GLOB.admins.len
- var/datum/DBQuery/query_record_playercount = SSdbcore.NewQuery("INSERT INTO [format_table_name("legacy_population")] (playercount, admincount, time, server_ip, server_port) VALUES ([playercount], [admincount], '[SQLtime()]', INET_ATON('[world.internet_address]'), '[world.port]')")
- query_record_playercount.Execute()
-
-/proc/sql_report_death(mob/living/L)
- if(!config.sql_enabled)
- return
- if(!SSdbcore.Connect())
- return
- if(!L || !L.key || !L.mind)
- return
- var/turf/T = get_turf(L)
- var/area/placeofdeath = get_area(T.loc)
- var/sqlname = sanitizeSQL(L.real_name)
- var/sqlkey = sanitizeSQL(L.ckey)
- var/sqljob = sanitizeSQL(L.mind.assigned_role)
- var/sqlspecial = sanitizeSQL(L.mind.special_role)
- var/sqlpod = sanitizeSQL(placeofdeath.name)
- var/laname
- var/lakey
- if(L.lastattacker && ismob(L.lastattacker))
- var/mob/LA = L.lastattacker
- laname = sanitizeSQL(LA.real_name)
- lakey = sanitizeSQL(LA.key)
- var/sqlgender = sanitizeSQL(L.gender)
- var/sqlbrute = sanitizeSQL(L.getBruteLoss())
- var/sqlfire = sanitizeSQL(L.getFireLoss())
- var/sqlbrain = sanitizeSQL(L.getBrainLoss())
- var/sqloxy = sanitizeSQL(L.getOxyLoss())
- var/sqltox = sanitizeSQL(L.getStaminaLoss())
- var/sqlclone = sanitizeSQL(L.getStaminaLoss())
- var/sqlstamina = sanitizeSQL(L.getStaminaLoss())
- var/coord = sanitizeSQL("[L.x], [L.y], [L.z]")
- var/map = sanitizeSQL(SSmapping.config.map_name)
- var/datum/DBQuery/query_report_death = SSdbcore.NewQuery("INSERT INTO [format_table_name("death")] (name, byondkey, job, special, pod, tod, laname, lakey, gender, bruteloss, fireloss, brainloss, oxyloss, toxloss, cloneloss, staminaloss, coord, mapname, server_ip, server_port) VALUES ('[sqlname]', '[sqlkey]', '[sqljob]', '[sqlspecial]', '[sqlpod]', '[SQLtime()]', '[laname]', '[lakey]', '[sqlgender]', [sqlbrute], [sqlfire], [sqlbrain], [sqloxy], [sqltox], [sqlclone], [sqlstamina], '[coord]', '[map]', INET_ATON('[world.internet_address]'), '[world.port]')")
- query_report_death.Execute()
diff --git a/code/controllers/subsystem/job.dm b/code/controllers/subsystem/job.dm
index 137bd2a2c1..a3255b73e4 100644
--- a/code/controllers/subsystem/job.dm
+++ b/code/controllers/subsystem/job.dm
@@ -483,7 +483,7 @@ SUBSYSTEM_DEF(job)
else level4++ //not selected
tmp_str += "HIGH=[level1]|MEDIUM=[level2]|LOW=[level3]|NEVER=[level4]|BANNED=[level5]|YOUNG=[level6]|-"
- feedback_add_details("job_preferences",tmp_str)
+ SSblackbox.add_details("job_preferences",tmp_str)
/datum/controller/subsystem/job/proc/PopcapReached()
if(config.hard_popcap || config.extreme_popcap)
diff --git a/code/controllers/subsystem/lighting.dm b/code/controllers/subsystem/lighting.dm
index eb61e5ef39..35d8a3d08f 100644
--- a/code/controllers/subsystem/lighting.dm
+++ b/code/controllers/subsystem/lighting.dm
@@ -36,18 +36,10 @@ SUBSYSTEM_DEF(lighting)
for (i in 1 to GLOB.lighting_update_lights.len)
var/datum/light_source/L = GLOB.lighting_update_lights[i]
- if (L.check() || QDELETED(L) || L.force_update)
- L.remove_lum()
- if (!QDELETED(L))
- L.apply_lum()
+ L.update_corners()
- else if (L.vis_update) //We smartly update only tiles that became (in) visible to use.
- L.smart_vis_update()
+ L.needs_update = LIGHTING_NO_UPDATE
- L.vis_update = FALSE
- L.force_update = FALSE
- L.needs_update = FALSE
-
if(init_tick_checks)
CHECK_TICK
else if (MC_TICK_CHECK)
diff --git a/code/controllers/subsystem/mapping.dm b/code/controllers/subsystem/mapping.dm
index a27235c592..85c580f4d9 100644
--- a/code/controllers/subsystem/mapping.dm
+++ b/code/controllers/subsystem/mapping.dm
@@ -119,7 +119,7 @@ SUBSYSTEM_DEF(mapping)
INIT_ANNOUNCE("Loading [config.map_name]...")
TryLoadZ(config.GetFullMapPath(), FailedZs, ZLEVEL_STATION)
INIT_ANNOUNCE("Loaded station in [(REALTIMEOFDAY - start_time)/10]s!")
- feedback_add_details("map_name", config.map_name)
+ SSblackbox.add_details("map_name", config.map_name)
if(config.minetype != "lavaland")
INIT_ANNOUNCE("WARNING: A map without lavaland set as it's minetype was loaded! This is being ignored! Update the maploader code!")
diff --git a/code/controllers/subsystem/pai.dm b/code/controllers/subsystem/pai.dm
index dfb41c8905..ea6d57088f 100644
--- a/code/controllers/subsystem/pai.dm
+++ b/code/controllers/subsystem/pai.dm
@@ -150,7 +150,7 @@ SUBSYSTEM_DEF(pai)
if(!(ROLE_PAI in G.client.prefs.be_special))
continue
//G << 'sound/misc/server-ready.ogg' //Alerting them to their consideration
- to_chat(G, "Someone is requesting a pAI personality! Use the pAI button to submit yourself as one.")
+ to_chat(G, "[user] is requesting a pAI personality! Use the pAI button to submit yourself as one.")
addtimer(CALLBACK(src, .proc/spam_again), spam_delay)
var/list/available = list()
for(var/datum/paiCandidate/c in SSpai.candidates)
diff --git a/code/controllers/subsystem/persistence.dm b/code/controllers/subsystem/persistence.dm
index e1cf992e8b..c42dfc38e2 100644
--- a/code/controllers/subsystem/persistence.dm
+++ b/code/controllers/subsystem/persistence.dm
@@ -11,10 +11,14 @@ SUBSYSTEM_DEF(persistence)
var/list/saved_messages = list()
var/savefile/chisel_messages_sav
+ var/savefile/trophy_sav
+ var/list/saved_trophies = list()
+
/datum/controller/subsystem/persistence/Initialize()
LoadSatchels()
LoadPoly()
LoadChiselMessages()
+ LoadTrophies()
..()
/datum/controller/subsystem/persistence/proc/LoadSatchels()
@@ -105,10 +109,52 @@ SUBSYSTEM_DEF(persistence)
M.persists = FALSE
qdel(M)
+/datum/controller/subsystem/persistence/proc/LoadTrophies()
+ trophy_sav = new /savefile("data/npc_saves/TrophyItems.sav")
+ var/saved_json
+ trophy_sav >> saved_json
+
+ if(!saved_json)
+ return
+
+ var/decoded_json = json_decode(saved_json)
+
+ if(!islist(decoded_json))
+ return
+
+ saved_trophies = decoded_json
+
+ SetUpTrophies(saved_trophies.Copy())
+
+/datum/controller/subsystem/persistence/proc/SetUpTrophies(list/trophy_items)
+ for(var/A in GLOB.trophy_cases)
+ var/obj/structure/displaycase/trophy/T = A
+ T.added_roundstart = TRUE
+
+ var/trophy_data = pick_n_take(trophy_items)
+
+ if(!islist(trophy_data))
+ continue
+
+ var/list/chosen_trophy = trophy_data
+
+ if(!chosen_trophy || isemptylist(chosen_trophy)) //Malformed
+ continue
+
+ var/path = text2path(chosen_trophy["path"]) //If the item no longer exist, this returns null
+ if(!path)
+ continue
+
+ T.showpiece = new /obj/item/showpiece_dummy(T, path)
+ T.trophy_message = chosen_trophy["message"]
+ T.placer_key = chosen_trophy["placer_key"]
+ T.update_icon()
+
/datum/controller/subsystem/persistence/proc/CollectData()
CollectChiselMessages()
CollectSecretSatchels()
+ CollectTrophies()
/datum/controller/subsystem/persistence/proc/CollectSecretSatchels()
for(var/A in new_secret_satchels)
@@ -135,4 +181,16 @@ SUBSYSTEM_DEF(persistence)
chisel_messages_sav[SSmapping.config.map_name] << json_encode(saved_messages)
/datum/controller/subsystem/persistence/proc/SaveChiselMessage(obj/structure/chisel_message/M)
- saved_messages += list(M.pack()) // dm eats one list.
+ saved_messages += list(M.pack()) // dm eats one list
+
+
+/datum/controller/subsystem/persistence/proc/CollectTrophies()
+ trophy_sav << json_encode(saved_trophies)
+
+/datum/controller/subsystem/persistence/proc/SaveTrophy(obj/structure/displaycase/trophy/T)
+ if(!T.added_roundstart && T.showpiece)
+ var/list/data = list()
+ data["path"] = T.showpiece.type
+ data["message"] = T.trophy_message
+ data["placer_key"] = T.placer_key
+ saved_trophies += list(data)
\ No newline at end of file
diff --git a/code/controllers/subsystem/ping.dm b/code/controllers/subsystem/ping.dm
index 0829766174..a6b444c4e7 100644
--- a/code/controllers/subsystem/ping.dm
+++ b/code/controllers/subsystem/ping.dm
@@ -3,14 +3,20 @@
SUBSYSTEM_DEF(ping)
name = "Ping"
wait = 6
- flags = SS_NO_INIT|SS_POST_FIRE_TIMING|SS_FIRE_IN_LOBBY
+ flags = SS_POST_FIRE_TIMING|SS_FIRE_IN_LOBBY
priority = 10
var/list/currentrun
+/datum/controller/subsystem/ping/Initialize()
+ if (config.hub)
+ world.visibility = 1
+ ..()
+
/datum/controller/subsystem/ping/fire(resumed = FALSE)
if (!resumed)
src.currentrun = GLOB.clients.Copy()
+ var/round_started = Master.round_started
var/list/currentrun = src.currentrun
while (length(currentrun))
var/client/C = currentrun[currentrun.len]
@@ -19,7 +25,15 @@ SUBSYSTEM_DEF(ping)
if (MC_TICK_CHECK)
return
continue
+
+ if(round_started && C.is_afk(INACTIVITY_KICK))
+ if(!istype(C.mob, /mob/dead))
+ log_access("AFK: [key_name(C)]")
+ to_chat(C, "You have been inactive for more than 10 minutes and have been disconnected.")
+ qdel(C)
+
winset(C, null, "command=.update_ping+[world.time+world.tick_lag*world.tick_usage/100]")
+
if (MC_TICK_CHECK) //one day, when ss13 has 1000 people per server, you guys are gonna be glad I added this tick check
return
diff --git a/code/controllers/subsystem/processing/flightpacks.dm b/code/controllers/subsystem/processing/flightpacks.dm
index 1d85811878..0639f64810 100644
--- a/code/controllers/subsystem/processing/flightpacks.dm
+++ b/code/controllers/subsystem/processing/flightpacks.dm
@@ -5,7 +5,7 @@ PROCESSING_SUBSYSTEM_DEF(flightpacks)
stat_tag = "FM"
flags = SS_NO_INIT|SS_TICKER|SS_KEEP_TIMING
- var/flightsuit_processing = FLIGHTSUIT_PROCESSING_FULL
+ var/flightsuit_processing = FLIGHTSUIT_PROCESSING_NONE
/datum/controller/subsystem/processing/flightpacks/Initialize()
sync_flightsuit_processing()
diff --git a/code/controllers/subsystem/server_maint.dm b/code/controllers/subsystem/server_maint.dm
index 3ef088b328..08f60d23e6 100644
--- a/code/controllers/subsystem/server_maint.dm
+++ b/code/controllers/subsystem/server_maint.dm
@@ -1,17 +1,28 @@
+#define PING_BUFFER_TIME 25
+
SUBSYSTEM_DEF(server_maint)
name = "Server Tasks"
- wait = 6000
- flags = SS_NO_TICK_CHECK
+ wait = 6
+ flags = SS_POST_FIRE_TIMING|SS_FIRE_IN_LOBBY
+ priority = 10
+ var/list/currentrun
/datum/controller/subsystem/server_maint/Initialize(timeofday)
if (config.hub)
world.visibility = 1
..()
-/datum/controller/subsystem/server_maint/fire()
- //handle kicking inactive players
- if(config.kick_inactive)
- for(var/client/C in GLOB.clients)
+/datum/controller/subsystem/server_maint/fire(resumed = FALSE)
+ if(!resumed)
+ src.currentrun = GLOB.clients.Copy()
+
+ var/list/currentrun = src.currentrun
+ var/round_started = SSticker.HasRoundStarted()
+
+ for(var/I in currentrun)
+ var/client/C = I
+ //handle kicking inactive players
+ if(round_started && config.kick_inactive)
if(C.is_afk(config.afk_period))
var/cmob = C.mob
if(!(istype(cmob, /mob/dead/observer) || (istype(cmob, /mob/dead) && C.holder)))
@@ -19,5 +30,10 @@ SUBSYSTEM_DEF(server_maint)
to_chat(C, "You have been inactive for more than [config.afk_period / 600] minutes and have been disconnected.")
qdel(C)
- if(config.sql_enabled)
- sql_poll_population()
+ if (!(!C || world.time - C.connection_time < PING_BUFFER_TIME || C.inactivity >= (wait-1)))
+ winset(C, null, "command=.update_ping+[world.time+world.tick_lag*world.tick_usage/100]")
+
+ if (MC_TICK_CHECK) //one day, when ss13 has 1000 people per server, you guys are gonna be glad I added this tick check
+ return
+
+#undef PING_BUFFER_TIME
diff --git a/code/controllers/subsystem/ticker.dm b/code/controllers/subsystem/ticker.dm
index f701c051da..abf05aad72 100644
--- a/code/controllers/subsystem/ticker.dm
+++ b/code/controllers/subsystem/ticker.dm
@@ -243,7 +243,7 @@ SUBSYSTEM_DEF(ticker)
send2irc("Server", "Round of [hide_mode ? "secret":"[mode.name]"] has started[allmins.len ? ".":" with no active admins online!"]")
/datum/controller/subsystem/ticker/proc/OnRoundstart(datum/callback/cb)
- if(current_state < GAME_STATE_PLAYING)
+ if(!HasRoundStarted())
LAZYADD(round_start_events, cb)
else
cb.InvokeAsync()
@@ -625,8 +625,8 @@ SUBSYSTEM_DEF(ticker)
if(selected_tip)
m = selected_tip
else
- var/list/randomtips = world.file2list("config/tips.txt")
- var/list/memetips = world.file2list("config/sillytips.txt")
+ var/list/randomtips = world.file2list("strings/tips.txt")
+ var/list/memetips = world.file2list("strings/sillytips.txt")
if(randomtips.len && prob(95))
m = pick(randomtips)
else if(memetips.len)
@@ -672,15 +672,16 @@ SUBSYSTEM_DEF(ticker)
return
INVOKE_ASYNC(SSmapping, /datum/controller/subsystem/mapping/.proc/maprotate)
+/datum/controller/subsystem/ticker/proc/HasRoundStarted()
+ return current_state >= GAME_STATE_PLAYING
+
+/datum/controller/subsystem/ticker/proc/IsRoundInProgress()
+ return current_state == GAME_STATE_PLAYING
+
/proc/send_gamemode_vote()
SSticker.modevoted = TRUE
SSvote.initiate_vote("roundtype","server")
-/world/proc/has_round_started()
- if (SSticker && SSticker.current_state >= GAME_STATE_PLAYING)
- return TRUE
- return FALSE
-
/datum/controller/subsystem/ticker/Recover()
current_state = SSticker.current_state
force_ending = SSticker.force_ending
diff --git a/code/controllers/subsystem/vote.dm b/code/controllers/subsystem/vote.dm
index b3b6dce98a..5deb0adf85 100644
--- a/code/controllers/subsystem/vote.dm
+++ b/code/controllers/subsystem/vote.dm
@@ -124,7 +124,7 @@ SUBSYSTEM_DEF(vote)
if("gamemode")
if(GLOB.master_mode != .)
world.save_mode(.)
- if(SSticker && SSticker.mode)
+ if(SSticker.HasRoundStarted())
restart = 1
else
GLOB.master_mode = .
diff --git a/code/datums/antagonists/antag_datum.dm b/code/datums/antagonists/antag_datum.dm
index deee1111c0..396c185961 100644
--- a/code/datums/antagonists/antag_datum.dm
+++ b/code/datums/antagonists/antag_datum.dm
@@ -8,13 +8,26 @@
var/can_coexist_with_others = TRUE //Whether or not the person will be able to have more than one datum
var/list/typecache_datum_blacklist = list() //List of datums this type can't coexist with
-
/datum/antagonist/New(datum/mind/new_owner)
- . = ..()
typecache_datum_blacklist = typecacheof(typecache_datum_blacklist)
if(new_owner)
owner = new_owner
+/datum/antagonist/Destroy()
+ if(owner)
+ LAZYREMOVE(owner.antag_datums, src)
+ owner = null
+ return ..()
+
+/datum/antagonist/proc/can_be_owned(datum/mind/new_owner)
+ . = TRUE
+ if(owner.has_antag_datum(type))
+ return FALSE
+ for(var/i in owner.antag_datums)
+ var/datum/antagonist/A = i
+ if(is_type_in_typecache(src, A.typecache_datum_blacklist))
+ return FALSE
+
/datum/antagonist/proc/on_body_transfer(mob/living/old_body, mob/living/new_body)
remove_innate_effects(old_body)
apply_innate_effects(new_body)
@@ -37,7 +50,7 @@
/datum/antagonist/proc/on_removal()
remove_innate_effects()
if(owner)
- owner.antag_datums -= src
+ LAZYREMOVE(owner.antag_datums, src)
if(!silent && owner.current)
farewell()
qdel(src)
@@ -46,4 +59,4 @@
return
/datum/antagonist/proc/farewell()
- return
\ No newline at end of file
+ return
diff --git a/code/datums/antagonists/datum_clockcult.dm b/code/datums/antagonists/datum_clockcult.dm
index ba18e76f02..b8dfa00f23 100644
--- a/code/datums/antagonists/datum_clockcult.dm
+++ b/code/datums/antagonists/datum_clockcult.dm
@@ -9,23 +9,49 @@
qdel(hierophant_network)
return ..()
+/datum/antagonist/clockcult/can_be_owned(datum/mind/new_owner)
+ . = ..()
+ if(.)
+ if(iscyborg(new_owner.current))
+ var/mob/living/silicon/robot/R = new_owner.current
+ if(R.deployed)
+ var/mob/living/silicon/ai/AI = R.mainframe
+ R.undeploy()
+ to_chat(AI, "Anomaly Detected. Returned to core!") //The AI needs to be in its core to properly be converted
+ . = is_eligible_servant(new_owner.current)
+ if(!silent && new_owner.current)
+ if(issilicon(new_owner.current))
+ to_chat(new_owner.current, "You are unable to compute this truth. Your vision glows a brilliant yellow, and all at once it comes to you. Ratvar, the \
+ Clockwork Justiciar, lies in exile, derelict and forgotten in an unseen realm.")
+ else
+ to_chat(new_owner.current, "[iscarbon(new_owner.current) ? "Your mind is racing! Your body feels incredibly light! ":""]Your world glows a brilliant \
+ yellow! All at once it comes to you. Ratvar, the Clockwork Justiciar, lies in exile, derelict and forgotten in an unseen realm.")
+ if(!.)
+ new_owner.current.visible_message("[new_owner.current] seems to resist an unseen force!")
+ to_chat(new_owner.current, "And yet, you somehow push it all away.")
+
+/datum/antagonist/clockcult/greet()
+ if(!owner.current || silent)
+ return
+ owner.current.visible_message("[owner.current]'s eyes glow a blazing yellow!")
+ to_chat(owner.current, "Assist your new companions in their righteous efforts. Your goal is theirs, and theirs yours. You serve the Clockwork \
+ Justiciar above all else. Perform his every whim without hesitation.")
+
/datum/antagonist/clockcult/on_gain()
- if(!owner)
- return
var/mob/living/current = owner.current
- if(!istype(current))
- return
+ SSticker.mode.servants_of_ratvar += owner
+ SSticker.mode.update_servant_icons_added(owner)
if(jobban_isbanned(current, ROLE_SERVANT_OF_RATVAR))
- addtimer(CALLBACK(SSticker.mode, /datum/game_mode.proc/replace_jobbaned_player, owner, ROLE_SERVANT_OF_RATVAR, ROLE_SERVANT_OF_RATVAR), 0)
+ addtimer(CALLBACK(SSticker.mode, /datum/game_mode.proc/replace_jobbaned_player, current, ROLE_SERVANT_OF_RATVAR, ROLE_SERVANT_OF_RATVAR), 0)
+ owner.special_role = "Servant of Ratvar"
owner.current.log_message("Has been converted to the cult of Ratvar!", INDIVIDUAL_ATTACK_LOG)
if(issilicon(current))
- var/mob/living/silicon/S = owner
- if(iscyborg(S) && !silent)
- to_chat(S, "You have been desynced from your master AI.")
- to_chat(S, "In addition, your onboard camera is no longer active and you have gained additional equipment, including a limited clockwork slab.")
- if(isAI(S))
- to_chat(S, "You are able to use your cameras to listen in on conversations.")
- to_chat(S, "You can communicate with other servants by using the Hierophant Network action button in the upper left.")
+ if(iscyborg(current) && !silent)
+ to_chat(current, "You have been desynced from your master AI.")
+ to_chat(current, "In addition, your onboard camera is no longer active and you have gained additional equipment, including a limited clockwork slab.")
+ if(isAI(current))
+ to_chat(current, "You are able to use your cameras to listen in on conversations.")
+ to_chat(current, "You can communicate with other servants by using the Hierophant Network action button in the upper left.")
else if(isbrain(current) || isclockmob(current))
to_chat(current, "You can communicate with other servants by using the Hierophant Network action button in the upper left.")
..()
@@ -39,7 +65,6 @@
if(istype(mob_override))
current = mob_override
GLOB.all_clockwork_mobs += current
- SSticker.mode.update_servant_icons_added(owner)
current.faction |= "ratvar"
current.grant_language(/datum/language/ratvar)
current.update_action_buttons_icon() //because a few clockcult things are action buttons and we may be wearing/holding them for whatever reason, we need to update buttons
@@ -47,11 +72,17 @@
var/mob/living/silicon/S = current
if(iscyborg(S))
var/mob/living/silicon/robot/R = S
- R.UnlinkSelf()
+ if(!R.shell)
+ R.UnlinkSelf()
R.module.rebuild_modules()
else if(isAI(S))
var/mob/living/silicon/ai/A = S
+ A.can_be_carded = FALSE
A.requires_power = POWER_REQ_CLOCKCULT
+ var/list/AI_frame = list(mutable_appearance('icons/mob/clockwork_mobs.dmi', "aiframe")) //make the AI's cool frame
+ for(var/d in GLOB.cardinal)
+ AI_frame += image('icons/mob/clockwork_mobs.dmi', A, "eye[rand(1, 10)]", dir = d) //the eyes are randomly fast or slow
+ A.add_overlay(AI_frame)
if(!A.lacks_power())
A.ai_restore_power()
if(A.eyeobj)
@@ -84,8 +115,6 @@
current.throw_alert("clockinfo", /obj/screen/alert/clockwork/infodump)
if(!GLOB.clockwork_gateway_activated)
current.throw_alert("scripturereq", /obj/screen/alert/clockwork/scripture_reqs)
- update_slab_info()
-
/datum/antagonist/clockcult/remove_innate_effects(mob/living/mob_override)
var/mob/living/current = owner.current
@@ -102,7 +131,9 @@
var/mob/living/silicon/S = current
if(isAI(S))
var/mob/living/silicon/ai/A = S
+ A.can_be_carded = initial(A.can_be_carded)
A.requires_power = initial(A.requires_power)
+ A.cut_overlays()
S.make_laws()
S.update_icons()
S.show_laws()
@@ -113,13 +144,16 @@
R.module.rebuild_modules()
if(temp_owner)
temp_owner.update_action_buttons_icon() //because a few clockcult things are action buttons and we may be wearing/holding them, we need to update buttons
- update_slab_info()
/datum/antagonist/clockcult/on_removal()
- . = ..()
+ SSticker.mode.servants_of_ratvar -= owner
+ SSticker.mode.update_servant_icons_removed(owner)
if(!silent)
owner.current.visible_message("[owner] seems to have remembered their true allegiance!", \
"A cold, cold darkness flows through your mind, extinguishing the Justiciar's light and all of your memories as his servant.")
owner.current.log_message("Has renounced the cult of Ratvar!", INDIVIDUAL_ATTACK_LOG)
+ owner.wipe_memory()
+ owner.special_role = null
if(iscyborg(owner.current))
- to_chat(owner.current, "Despite your freedom from Ratvar's influence, you are still irreparably damaged and no longer possess certain functions such as AI linking.")
\ No newline at end of file
+ to_chat(owner.current, "Despite your freedom from Ratvar's influence, you are still irreparably damaged and no longer possess certain functions such as AI linking.")
+ . = ..()
diff --git a/code/datums/antagonists/datum_cult.dm b/code/datums/antagonists/datum_cult.dm
index 69c9849782..30c0aa8450 100644
--- a/code/datums/antagonists/datum_cult.dm
+++ b/code/datums/antagonists/datum_cult.dm
@@ -5,29 +5,46 @@
qdel(communion)
return ..()
+/datum/antagonist/cult/can_be_owned(datum/mind/new_owner)
+ . = ..()
+ if(.)
+ . = is_convertable_to_cult(new_owner.current)
+
/datum/antagonist/cult/on_gain()
. = ..()
- if(!owner)
- return
+ SSticker.mode.cult += owner
+ SSticker.mode.update_cult_icons_added(owner)
+ if(istype(SSticker.mode, /datum/game_mode/cult))
+ var/datum/game_mode/cult/C = SSticker.mode
+ C.memorize_cult_objectives(owner)
if(jobban_isbanned(owner.current, ROLE_CULTIST))
- addtimer(CALLBACK(SSticker.mode, /datum/game_mode.proc/replace_jobbaned_player, owner, ROLE_CULTIST, ROLE_CULTIST), 0)
+ addtimer(CALLBACK(SSticker.mode, /datum/game_mode.proc/replace_jobbaned_player, owner.current, ROLE_CULTIST, ROLE_CULTIST), 0)
owner.current.log_message("Has been converted to the cult of Nar'Sie!", INDIVIDUAL_ATTACK_LOG)
-/datum/antagonist/cult/apply_innate_effects()
+/datum/antagonist/cult/apply_innate_effects(mob/living/mob_override)
. = ..()
- owner.current.faction |= "cult"
- owner.current.verbs += /mob/living/proc/cult_help
- communion.Grant(owner)
+ var/mob/living/current = owner.current
+ if(mob_override)
+ current = mob_override
+ current.faction |= "cult"
+ current.verbs += /mob/living/proc/cult_help
+ communion.Grant(current)
-/datum/antagonist/cult/remove_innate_effects()
+/datum/antagonist/cult/remove_innate_effects(mob/living/mob_override)
. = ..()
- owner.current.faction -= "cult"
- owner.current.verbs -= /mob/living/proc/cult_help
-
+ var/mob/living/current = owner.current
+ if(mob_override)
+ current = mob_override
+ current.faction -= "cult"
+ current.verbs -= /mob/living/proc/cult_help
+ communion.Remove(current)
/datum/antagonist/cult/on_removal()
- . = ..()
+ owner.wipe_memory()
+ SSticker.mode.cult -= owner
+ SSticker.mode.update_cult_icons_removed(owner)
to_chat(owner, "An unfamiliar white light flashes through your mind, cleansing the taint of the Dark One and all your memories as its servant.")
owner.current.log_message("Has renounced the cult of Nar'Sie!", INDIVIDUAL_ATTACK_LOG)
if(!silent)
- owner.current.visible_message("[owner] looks like [owner.current.p_they()] just reverted to their old faith!")
\ No newline at end of file
+ owner.current.visible_message("[owner] looks like [owner.current.p_they()] just reverted to their old faith!")
+ . = ..()
diff --git a/code/datums/datumvars.dm b/code/datums/datumvars.dm
index 7de57e4bb9..fbbf97a6ca 100644
--- a/code/datums/datumvars.dm
+++ b/code/datums/datumvars.dm
@@ -27,7 +27,7 @@
. += "---"
.["Call Proc"] = "?_src_=vars;proc_call=\ref[src]"
.["Mark Object"] = "?_src_=vars;mark_object=\ref[src]"
- .["Delete"] = "?_src_=vars;delete=\ref[src]"
+ .["Delete"] = "?_src_=vars;delete=\ref[src]"
/datum/proc/on_reagent_change()
@@ -94,7 +94,6 @@
CLONE:[M.getCloneLoss()]
BRAIN:[M.getBrainLoss()]
STAMINA:[M.getStaminaLoss()]
- AROUSAL:[M.getArousalLoss()]
"}
else
@@ -447,7 +446,7 @@
var/list/L = value
var/list/items = list()
- if (L.len > 0 && !(name == "underlays" || name == "overlays" || L.len > (IS_NORMAL_LIST(L) ? 50 : 150)))
+ if (L.len > 0 && !(name == "underlays" || name == "overlays" || L.len > (IS_NORMAL_LIST(L) ? 50 : 150)))
for (var/i in 1 to L.len)
var/key = L[i]
var/val
@@ -527,16 +526,16 @@
if(T)
callproc_datum(T)
- else if(href_list["delete"])
- if(!check_rights(R_DEBUG, 0))
- return
-
- var/datum/D = locate(href_list["delete"])
- if(!D)
- to_chat(usr, "Unable to locate item!")
- admin_delete(D)
- href_list["datumrefresh"] = href_list["delete"]
-
+ else if(href_list["delete"])
+ if(!check_rights(R_DEBUG, 0))
+ return
+
+ var/datum/D = locate(href_list["delete"])
+ if(!D)
+ to_chat(usr, "Unable to locate item!")
+ admin_delete(D)
+ href_list["datumrefresh"] = href_list["delete"]
+
else if(href_list["regenerateicons"])
if(!check_rights(0))
return
@@ -1166,8 +1165,6 @@
L.adjustCloneLoss(amount)
if("stamina")
L.adjustStaminaLoss(amount)
- if("arousal")
- L.adjustArousalLoss(amount)
else
to_chat(usr, "You caused an error. DEBUG: Text:[Text] Mob:[L]")
return
@@ -1178,3 +1175,4 @@
message_admins(msg)
admin_ticket_log(L, msg)
href_list["datumrefresh"] = href_list["mobToDamage"]
+
diff --git a/code/datums/helper_datums/getrev.dm b/code/datums/helper_datums/getrev.dm
index 8c9d7d7704..b90e2ec652 100644
--- a/code/datums/helper_datums/getrev.dm
+++ b/code/datums/helper_datums/getrev.dm
@@ -25,7 +25,7 @@
for(var/line in testmerge)
if(line)
log_world("Test merge active of PR #[line]")
- feedback_add_details("testmerged_prs","[line]")
+ SSblackbox.add_details("testmerged_prs","[line]")
log_world("Based off master commit [parentcommit]")
else
log_world(parentcommit)
@@ -75,10 +75,12 @@
if(GLOB.revdata.parentcommit)
to_chat(src, "Server revision compiled on: [GLOB.revdata.date]")
+ var/prefix = ""
if(GLOB.revdata.testmerge.len)
to_chat(src, GLOB.revdata.GetTestMergeInfo())
- to_chat(src, "Based off master commit:")
- to_chat(src, "[GLOB.revdata.parentcommit]")
+ prefix = "Based off master commit: "
+ var/pc = GLOB.revdata.parentcommit
+ to_chat(src, "[prefix][copytext(pc, 1, min(length(pc), 7))]")
else
to_chat(src, "Revision unknown")
to_chat(src, "Current Infomational Settings:")
@@ -89,7 +91,7 @@
to_chat(src, "Enforce Continuous Rounds: [config.continuous.len] of [config.modes.len] roundtypes")
to_chat(src, "Allow Midround Antagonists: [config.midround_antag.len] of [config.modes.len] roundtypes")
if(config.show_game_type_odds)
- if(SSticker.current_state == GAME_STATE_PLAYING)
+ if(SSticker.IsRoundInProgress())
var/prob_sum = 0
var/current_odds_differ = FALSE
var/list/probs = list()
diff --git a/code/datums/holocall.dm b/code/datums/holocall.dm
new file mode 100644
index 0000000000..24774da158
--- /dev/null
+++ b/code/datums/holocall.dm
@@ -0,0 +1,159 @@
+#define HOLOPAD_MAX_DIAL_TIME 200
+
+/mob/camera/aiEye/remote/holo/setLoc()
+ . = ..()
+ var/obj/machinery/holopad/H = origin
+ H.move_hologram(eye_user, loc)
+
+//this datum manages it's own references
+
+/datum/holocall
+ var/mob/living/user //the one that called
+ var/obj/machinery/holopad/calling_holopad //the one that sent the call
+ var/obj/machinery/holopad/connected_holopad //the one that answered the call (may be null)
+ var/list/dialed_holopads //all things called, will be cleared out to just connected_holopad once answered
+
+ var/mob/camera/aiEye/remote/holo/eye //user's eye, once connected
+ var/obj/effect/overlay/holo_pad_hologram/hologram //user's hologram, once connected
+
+ var/call_start_time
+
+//creates a holocall made by `caller` from `calling_pad` to `callees`
+/datum/holocall/New(mob/living/caller, obj/machinery/holopad/calling_pad, list/callees)
+ call_start_time = world.time
+ user = caller
+ calling_pad.outgoing_call = src
+ calling_holopad = calling_pad
+ dialed_holopads = list()
+
+ for(var/I in callees)
+ var/obj/machinery/holopad/H = I
+ if(!QDELETED(H) && H.is_operational())
+ dialed_holopads += H
+ LAZYADD(H.holo_calls, src)
+
+ if(!dialed_holopads.len)
+ calling_pad.say("Connection failure.")
+ qdel(src)
+ return
+
+ testing("Holocall started")
+
+//cleans up ALL references :)
+/datum/holocall/Destroy()
+ QDEL_NULL(eye)
+
+ user.reset_perspective()
+
+ user = null
+ hologram.HC = null
+ hologram = null
+ calling_holopad.outgoing_call = null
+
+ for(var/I in dialed_holopads)
+ var/obj/machinery/holopad/H = I
+ LAZYREMOVE(H.holo_calls, src)
+ dialed_holopads.Cut()
+
+ if(calling_holopad)
+ calling_holopad.SetLightsAndPower()
+ calling_holopad = null
+ if(connected_holopad)
+ connected_holopad.SetLightsAndPower()
+ connected_holopad = null
+
+ testing("Holocall destroyed")
+
+ return ..()
+
+//Gracefully disconnects a holopad `H` from a call. Pads not in the call are ignored. Notifies participants of the disconnection
+/datum/holocall/proc/Disconnect(obj/machinery/holopad/H)
+ testing("Holocall disconnect")
+ if(H == connected_holopad)
+ calling_holopad.say("[usr] disconnected.")
+ else if(H == calling_holopad && connected_holopad)
+ connected_holopad.say("[usr] disconnected.")
+
+ ConnectionFailure(H, TRUE)
+
+//Forcefully disconnects a holopad `H` from a call. Pads not in the call are ignored.
+/datum/holocall/proc/ConnectionFailure(obj/machinery/holopad/H, graceful = FALSE)
+ testing("Holocall connection failure: graceful [graceful]")
+ if(H == connected_holopad || H == calling_holopad)
+ if(!graceful)
+ calling_holopad.say("Connection failure.")
+ qdel(src)
+ return
+
+ LAZYREMOVE(H.holo_calls, src)
+ dialed_holopads -= H
+ if(!dialed_holopads.len)
+ if(graceful)
+ calling_holopad.say("Call rejected.")
+ testing("No recipients, terminating")
+ qdel(src)
+
+//Answers a call made to a holopad `H` which cannot be the calling holopad. Pads not in the call are ignored
+/datum/holocall/proc/Answer(obj/machinery/holopad/H)
+ testing("Holocall answer")
+ if(H == calling_holopad)
+ CRASH("How cute, a holopad tried to answer itself.")
+
+ if(!(H in dialed_holopads))
+ return
+
+ if(connected_holopad)
+ CRASH("Multi-connection holocall")
+
+ for(var/I in dialed_holopads)
+ if(I == H)
+ continue
+ Disconnect(I)
+
+ for(var/I in H.holo_calls)
+ var/datum/holocall/HC = I
+ if(HC != src)
+ HC.Disconnect(H)
+
+ connected_holopad = H
+
+ if(!Check())
+ return
+
+ hologram = H.activate_holo(user)
+ hologram.HC = src
+
+ //eyeobj code is horrid, this is the best copypasta I could make
+ eye = new
+ eye.origin = H
+ eye.eye_initialized = TRUE
+ eye.eye_user = user
+ eye.name = "Camera Eye ([user.name])"
+ user.remote_control = eye
+ user.reset_perspective(eye)
+ eye.setLoc(H.loc)
+
+//Checks the validity of a holocall and qdels itself if it's not. Returns TRUE if valid, FALSE otherwise
+/datum/holocall/proc/Check()
+ for(var/I in dialed_holopads)
+ var/obj/machinery/holopad/H = I
+ if(!H.is_operational())
+ ConnectionFailure(H)
+
+ if(QDELETED(src))
+ return FALSE
+
+ . = !QDELETED(user) && !user.incapacitated() && !QDELETED(calling_holopad) && calling_holopad.is_operational() && user.loc == calling_holopad.loc
+
+ if(.)
+ if(connected_holopad)
+ . = !QDELETED(connected_holopad) && connected_holopad.is_operational()
+ else
+ . = world.time < (call_start_time + HOLOPAD_MAX_DIAL_TIME)
+ if(!.)
+ calling_holopad.say("No answer recieved.")
+ calling_holopad.temp = ""
+
+ if(!.)
+ testing("Holocall Check fail")
+ qdel(src)
diff --git a/code/datums/mind.dm b/code/datums/mind.dm
index 5a1ba5b8c5..e99d5bb59a 100644
--- a/code/datums/mind.dm
+++ b/code/datums/mind.dm
@@ -44,9 +44,7 @@
var/datum/job/assigned_job
var/list/datum/objective/objectives = list()
- var/list/datum/objective/special_verbs = list()
- var/list/cult_words = list()
var/list/spell_list = list() // Wizard mode & "Give Spell" badmin button.
var/datum/faction/faction //associated faction
@@ -54,7 +52,7 @@
var/linglink
var/miming = 0 // Mime's vow of silence
- var/list/antag_datums = list()
+ var/list/antag_datums
var/antag_hud_icon_state = null //this mind's ANTAG_HUD should have this icon_state
var/datum/atom_hud/antag/antag_hud = null //this mind's antag HUD
var/datum/gang/gang_datum //Which gang this mind belongs to, if any
@@ -71,6 +69,10 @@
/datum/mind/Destroy()
SSticker.minds -= src
+ if(islist(antag_datums))
+ for(var/i in antag_datums)
+ qdel(i)
+ antag_datums = null
return ..()
/datum/mind/proc/transfer_to(mob/new_character, var/force_key_move = 0)
@@ -110,15 +112,16 @@
memory = null
// Datum antag mind procs
-/datum/mind/proc/add_antag_datum(datum_type, on_gain = TRUE)
+/datum/mind/proc/add_antag_datum(datum_type)
if(!datum_type)
return
- if(!can_hold_antag_datum(datum_type))
- return
var/datum/antagonist/A = new datum_type(src)
- antag_datums += A
- if(on_gain)
- A.on_gain()
+ if(!A.can_be_owned(src))
+ qdel(A)
+ return
+ LAZYADD(antag_datums, A)
+ A.on_gain()
+ return A
/datum/mind/proc/remove_antag_datum(datum_type)
if(!datum_type)
@@ -126,6 +129,7 @@
var/datum/antagonist/A = has_antag_datum(datum_type)
if(A)
A.on_removal()
+ return TRUE
/datum/mind/proc/remove_all_antag_datums() //For the Lazy amongst us.
for(var/a in antag_datums)
@@ -143,18 +147,6 @@
else if(A.type == datum_type)
return A
-/datum/mind/proc/can_hold_antag_datum(datum_type)
- if(!datum_type)
- return
- . = TRUE
- if(has_antag_datum(datum_type))
- return FALSE
- for(var/i in antag_datums)
- var/datum/antagonist/A = i
- if(is_type_in_typecache(A, A.typecache_datum_blacklist))
- return FALSE
-
-
/*
Removes antag type's references from a mind.
objectives, uplinks, powers etc are all handled.
@@ -301,7 +293,7 @@
to_chat(recipient, "[output]")
/datum/mind/proc/edit_memory()
- if(!SSticker || !SSticker.mode)
+ if(!SSticker.HasRoundStarted())
alert("Not before round-start!", "Alert")
return
diff --git a/code/datums/ruins/lavaland.dm b/code/datums/ruins/lavaland.dm
index 3a54db4e0a..011363f001 100644
--- a/code/datums/ruins/lavaland.dm
+++ b/code/datums/ruins/lavaland.dm
@@ -42,6 +42,7 @@
However, all the inhabitants seem to do is grow drugs and guns."
suffix = "lavaland_surface_seed_vault.dmm"
cost = 10
+ allow_duplicates = FALSE
/datum/map_template/ruin/lavaland/ash_walker
name = "Ash Walker Nest"
diff --git a/code/datums/shuttles.dm b/code/datums/shuttles.dm
index 774e0794ff..d3427ac983 100644
--- a/code/datums/shuttles.dm
+++ b/code/datums/shuttles.dm
@@ -72,7 +72,7 @@
/datum/map_template/shuttle/emergency/meteor
suffix = "meteor"
- name = "An Asteroid With Engines Strapped To It"
+ name = "Asteroid With Engines Strapped To It"
description = "A hollowed out asteroid with engines strapped to it. Due to its size and difficulty in steering it, this shuttle may damage the docking area."
admin_notes = "This shuttle will likely crush escape, killing anyone there."
credit_cost = -5000
diff --git a/code/datums/status_effects/buffs.dm b/code/datums/status_effects/buffs.dm
index d07f66609b..7b00a17e41 100644
--- a/code/datums/status_effects/buffs.dm
+++ b/code/datums/status_effects/buffs.dm
@@ -13,6 +13,7 @@
/datum/status_effect/shadow_mend/on_apply()
owner.visible_message("Violet light wraps around [owner]'s body!", "Violet light wraps around your body!")
playsound(owner, 'sound/magic/Teleport_app.ogg', 50, 1)
+ return ..()
/datum/status_effect/shadow_mend/tick()
owner.adjustBruteLoss(-15)
@@ -72,9 +73,12 @@
add_logs(owner, null, "gained Vanguard stun immunity")
owner.add_stun_absorption("vanguard", 200, 1, "'s yellow aura momentarily intensifies!", "Your ward absorbs the stun!", " radiating with a soft yellow light!")
owner.visible_message("[owner] begins to faintly glow!", "You will absorb all stuns for the next twenty seconds.")
+ owner.SetStunned(0, FALSE)
+ owner.SetWeakened(0)
progbar = new(owner, duration, owner)
progbar.bar.color = list("#FAE48C", "#FAE48C", "#FAE48C", rgb(0,0,0))
progbar.update(duration - world.time)
+ return ..()
/datum/status_effect/vanguard_shield/tick()
progbar.update(duration - world.time)
@@ -127,6 +131,7 @@
animate(owner, color = oldcolor, time = 150, easing = EASE_IN)
addtimer(CALLBACK(owner, /atom/proc/update_atom_colour), 150)
playsound(owner, 'sound/magic/Ethereal_Enter.ogg', 50, 1)
+ return ..()
/datum/status_effect/inathneqs_endowment/on_remove()
add_logs(owner, null, "lost Inath-neq's invulnerability")
@@ -178,6 +183,7 @@
/datum/status_effect/his_grace/on_apply()
add_logs(owner, null, "gained His Grace's stun immunity")
owner.add_stun_absorption("hisgrace", INFINITY, 3, null, "His Grace protects you from the stun!")
+ return ..()
/datum/status_effect/his_grace/tick()
bloodlust = 0
@@ -211,6 +217,7 @@
/datum/status_effect/wish_granters_gift/on_apply()
to_chat(owner, "Death is not your end! The Wish Granter's energy suffuses you, and you begin to rise...")
+ return ..()
/datum/status_effect/wish_granters_gift/on_remove()
owner.revive(full_heal = 1, admin_revive = 1)
diff --git a/code/datums/status_effects/debuffs.dm b/code/datums/status_effects/debuffs.dm
index f78a3ae522..8eec853047 100644
--- a/code/datums/status_effects/debuffs.dm
+++ b/code/datums/status_effects/debuffs.dm
@@ -29,3 +29,50 @@
owner.adjustBruteLoss(0.1)
owner.adjustFireLoss(0.1)
owner.adjustToxLoss(0.2, TRUE, TRUE)
+
+/datum/status_effect/belligerent
+ id = "belligerent"
+ duration = 70
+ tick_interval = 0 //tick as fast as possible
+ status_type = STATUS_EFFECT_REPLACE
+ alert_type = /obj/screen/alert/status_effect/belligerent
+ var/leg_damage_on_toggle = 2 //damage on initial application and when the owner tries to toggle to run
+ var/cultist_damage_on_toggle = 10 //damage on initial application and when the owner tries to toggle to run, but to cultists
+
+/obj/screen/alert/status_effect/belligerent
+ name = "Belligerent"
+ desc = "Kneel, her-eti'c."
+ icon_state = "belligerent"
+ alerttooltipstyle = "clockcult"
+
+/datum/status_effect/belligerent/on_apply()
+ return do_movement_toggle(TRUE)
+
+/datum/status_effect/belligerent/tick()
+ if(!do_movement_toggle())
+ qdel(src)
+
+/datum/status_effect/belligerent/proc/do_movement_toggle(force_damage)
+ var/number_legs = owner.get_num_legs()
+ if(iscarbon(owner) && !is_servant_of_ratvar(owner) && !owner.null_rod_check() && number_legs)
+ if(force_damage || owner.m_intent != MOVE_INTENT_WALK)
+ if(GLOB.ratvar_awakens)
+ owner.Weaken(1)
+ if(iscultist(owner))
+ owner.apply_damage(cultist_damage_on_toggle * 0.5, BURN, "l_leg")
+ owner.apply_damage(cultist_damage_on_toggle * 0.5, BURN, "r_leg")
+ else
+ owner.apply_damage(leg_damage_on_toggle * 0.5, BURN, "l_leg")
+ owner.apply_damage(leg_damage_on_toggle * 0.5, BURN, "r_leg")
+ if(owner.m_intent != MOVE_INTENT_WALK)
+ if(!iscultist(owner))
+ to_chat(owner, "Your leg[number_legs > 1 ? "s shiver":" shivers"] with pain!")
+ else //Cultists take extra burn damage
+ to_chat(owner, "Your leg[number_legs > 1 ? "s burn":" burns"] with pain!")
+ owner.toggle_move_intent()
+ return TRUE
+ return FALSE
+
+/datum/status_effect/belligerent/on_remove()
+ if(owner.m_intent == MOVE_INTENT_WALK)
+ owner.toggle_move_intent()
diff --git a/code/datums/status_effects/gas.dm b/code/datums/status_effects/gas.dm
index c2c070dbec..ff92b67978 100644
--- a/code/datums/status_effects/gas.dm
+++ b/code/datums/status_effects/gas.dm
@@ -16,6 +16,7 @@
cube = icon('icons/effects/freeze.dmi', "ice_cube")
owner.add_overlay(cube)
owner.update_canmove()
+ return ..()
/datum/status_effect/freon/tick()
owner.update_canmove()
diff --git a/code/datums/status_effects/status_effect.dm b/code/datums/status_effects/status_effect.dm
index 51b4f8fc5f..10dbd1a602 100644
--- a/code/datums/status_effects/status_effect.dm
+++ b/code/datums/status_effects/status_effect.dm
@@ -10,6 +10,7 @@
var/status_type = STATUS_EFFECT_UNIQUE //How many of the effect can be on one mob, and what happens when you try to add another
var/on_remove_on_mob_delete = FALSE //if we call on_remove() when the mob is deleted
var/alert_type = /obj/screen/alert/status_effect //the alert thrown by the status effect, contains name and description
+ var/obj/screen/alert/status_effect/linked_alert = null //the alert itself, if it exists
/datum/status_effect/New(mob/living/new_owner)
if(new_owner)
@@ -30,16 +31,16 @@
/datum/status_effect/proc/start_ticking()
if(!src)
return
- if(!owner)
+ if(!owner || !on_apply())
qdel(src)
return
- on_apply()
if(duration != -1)
duration = world.time + initial(duration)
tick_interval = world.time + initial(tick_interval)
if(alert_type)
var/obj/screen/alert/status_effect/A = owner.throw_alert(id, alert_type)
A.attached_effect = src //so the alert can reference us, if it needs to
+ linked_alert = A //so we can reference the alert, if we need to
START_PROCESSING(SSfastprocess, src)
/datum/status_effect/process()
@@ -53,6 +54,8 @@
qdel(src)
/datum/status_effect/proc/on_apply() //Called whenever the buff is applied.
+ return TRUE
+
/datum/status_effect/proc/tick() //Called every tick.
/datum/status_effect/proc/on_remove() //Called whenever the buff expires or is removed; do note that at the point this is called, it is out of the owner's status_effects but owner is not yet null
/datum/status_effect/proc/be_replaced() //Called instead of on_remove when a status effect is replaced by itself or when a status effect with on_remove_on_mob_delete = FALSE has its mob deleted
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index ab0038f7be..e4adbb91ef 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -274,6 +274,7 @@
return
/atom/proc/ex_act(severity, target)
+ set waitfor = FALSE
contents_explosion(severity, target)
/atom/proc/blob_act(obj/structure/blob/B)
diff --git a/code/game/data_huds.dm b/code/game/data_huds.dm
index de830c856b..2e5854509a 100644
--- a/code/game/data_huds.dm
+++ b/code/game/data_huds.dm
@@ -24,7 +24,7 @@
if(!istype(H)) return 0
var/obj/item/clothing/under/U = H.w_uniform
if(!istype(U)) return 0
- if(U.sensor_mode <= 2) return 0
+ if(U.sensor_mode <= SENSOR_VITALS) return 0
return 1
/datum/atom_hud/data/human/medical/basic/add_to_single_hud(mob/M, mob/living/carbon/H)
diff --git a/code/game/gamemodes/antag_spawner.dm b/code/game/gamemodes/antag_spawner.dm
index 74c16cf132..5b568970d9 100644
--- a/code/game/gamemodes/antag_spawner.dm
+++ b/code/game/gamemodes/antag_spawner.dm
@@ -155,7 +155,8 @@
if(!(check_usability(user)))
return
- var/list/nuke_candidates = pollCandidatesForMob("Do you want to play as a syndicate [borg_to_spawn ? "[lowertext(borg_to_spawn)] cyborg":"operative"]?", ROLE_OPERATIVE, null, ROLE_OPERATIVE, 150, src)
+ to_chat(user, "You activate [src] and wait for confirmation.")
+ var/list/nuke_candidates = pollCandidatesForMob("Do you want to play as a syndicate [borg_to_spawn ? "[lowertext(borg_to_spawn)] cyborg":"operative"]?", ROLE_OPERATIVE, null, ROLE_OPERATIVE, 150, POLL_IGNORE_SYNDICATE, src)
if(nuke_candidates.len)
if(!(check_usability(user)))
return
diff --git a/code/game/gamemodes/blob/blob_finish.dm b/code/game/gamemodes/blob/blob_finish.dm
index a5fc5e339a..47e2ce6a14 100644
--- a/code/game/gamemodes/blob/blob_finish.dm
+++ b/code/game/gamemodes/blob/blob_finish.dm
@@ -20,7 +20,7 @@
if(round_converted) //So badmin blobs later don't step on the dead natural blobs metaphorical toes
..()
if(blobwincount <= GLOB.blobs_legit.len)
- feedback_set_details("round_end_result","win - blob took over")
+ SSblackbox.set_details("round_end_result","win - blob took over")
to_chat(world, "The blob has taken over the station!")
to_chat(world, "The entire station was eaten by the Blob!")
log_game("Blob mode completed with a blob victory.")
@@ -28,7 +28,7 @@
SSticker.news_report = BLOB_WIN
else if(station_was_nuked)
- feedback_set_details("round_end_result","halfwin - nuke")
+ SSblackbox.set_details("round_end_result","halfwin - nuke")
to_chat(world, "Partial Win: The station has been destroyed!")
to_chat(world, "Directive 7-12 has been successfully carried out, preventing the Blob from spreading.")
log_game("Blob mode completed with a tie (station destroyed).")
@@ -36,7 +36,7 @@
SSticker.news_report = BLOB_NUKE
else if(!GLOB.blob_cores.len)
- feedback_set_details("round_end_result","loss - blob eliminated")
+ SSblackbox.set_details("round_end_result","loss - blob eliminated")
to_chat(world, "The staff has won!")
to_chat(world, "The alien organism has been eradicated from the station!")
log_game("Blob mode completed with a crew victory.")
diff --git a/code/game/gamemodes/changeling/changeling.dm b/code/game/gamemodes/changeling/changeling.dm
index fc39f2222e..9d281b5f2f 100644
--- a/code/game/gamemodes/changeling/changeling.dm
+++ b/code/game/gamemodes/changeling/changeling.dm
@@ -254,19 +254,19 @@ GLOBAL_LIST_INIT(slot2type, list("head" = /obj/item/clothing/head/changeling, "w
for(var/datum/objective/objective in changeling.objectives)
if(objective.check_completion())
text += "
Objective #[count]: [objective.explanation_text] Success!"
- feedback_add_details("changeling_objective","[objective.type]|SUCCESS")
+ SSblackbox.add_details("changeling_objective","[objective.type]|SUCCESS")
else
text += "
Objective #[count]: [objective.explanation_text] Fail."
- feedback_add_details("changeling_objective","[objective.type]|FAIL")
+ SSblackbox.add_details("changeling_objective","[objective.type]|FAIL")
changelingwin = 0
count++
if(changelingwin)
text += "
The changeling was successful!"
- feedback_add_details("changeling_success","SUCCESS")
+ SSblackbox.add_details("changeling_success","SUCCESS")
else
text += "
The changeling has failed."
- feedback_add_details("changeling_success","FAIL")
+ SSblackbox.add_details("changeling_success","FAIL")
text += "
"
to_chat(world, text)
diff --git a/code/game/gamemodes/changeling/changeling_power.dm b/code/game/gamemodes/changeling/changeling_power.dm
index 1673e59f49..489228a30c 100644
--- a/code/game/gamemodes/changeling/changeling_power.dm
+++ b/code/game/gamemodes/changeling/changeling_power.dm
@@ -13,15 +13,13 @@
var/req_dna = 0 //amount of dna needed to use this ability. Changelings always have atleast 1
var/req_human = 0 //if you need to be human to use this ability
var/req_stat = CONSCIOUS // CONSCIOUS, UNCONSCIOUS or DEAD
- var/genetic_damage = 0 // genetic damage caused by using the sting. Nothing to do with cloneloss.
- var/max_genetic_damage = 100 // hard counter for spamming abilities. Not used/balanced much yet.
var/always_keep = 0 // important for abilities like revive that screw you if you lose them.
var/ignores_fakedeath = FALSE // usable with the FAKEDEATH flag
/obj/effect/proc_holder/changeling/proc/on_purchase(mob/user, is_respec)
if(!is_respec)
- feedback_add_details("changeling_power_purchase",name)
+ SSblackbox.add_details("changeling_power_purchase",name)
/obj/effect/proc_holder/changeling/proc/on_refund(mob/user)
return
@@ -37,9 +35,9 @@
return
var/datum/changeling/c = user.mind.changeling
if(sting_action(user, target))
- feedback_add_details("changeling_powers",name)
+ SSblackbox.add_details("changeling_powers",name)
sting_feedback(user, target)
- take_chemical_cost(c)
+ c.chem_charges -= chemical_cost
/obj/effect/proc_holder/changeling/proc/sting_action(mob/user, mob/target)
return 0
@@ -47,10 +45,6 @@
/obj/effect/proc_holder/changeling/proc/sting_feedback(mob/user, mob/target)
return 0
-/obj/effect/proc_holder/changeling/proc/take_chemical_cost(datum/changeling/changeling)
- changeling.chem_charges -= chemical_cost
- changeling.geneticdamage += genetic_damage
-
//Fairly important to remember to return 1 on success >.<
/obj/effect/proc_holder/changeling/proc/can_sting(mob/user, mob/target)
if(!ishuman(user) && !ismonkey(user)) //typecast everything from mob to carbon from this point onwards
@@ -71,9 +65,6 @@
if((user.status_flags & FAKEDEATH) && (!ignores_fakedeath))
to_chat(user, "We are incapacitated.")
return 0
- if(c.geneticdamage > max_genetic_damage)
- to_chat(user, "Our genomes are still reassembling. We need time to recover first.")
- return 0
return 1
//used in /mob/Stat()
diff --git a/code/game/gamemodes/changeling/evolution_menu.dm b/code/game/gamemodes/changeling/evolution_menu.dm
index db1405537f..fdfec9e270 100644
--- a/code/game/gamemodes/changeling/evolution_menu.dm
+++ b/code/game/gamemodes/changeling/evolution_menu.dm
@@ -68,7 +68,7 @@
mind.changeling.purchasedpowers+=S
S.on_purchase(src, is_respec)
if(is_respec)
- feedback_add_details("changeling_power_purchase","Readapt")
+ SSblackbox.add_details("changeling_power_purchase","Readapt")
var/mob/living/carbon/C = src //only carbons have dna now, so we have to typecaste
if(ishuman(C))
diff --git a/code/game/gamemodes/changeling/powers/absorb.dm b/code/game/gamemodes/changeling/powers/absorb.dm
index 0f1fb93071..b6b3372ae3 100644
--- a/code/game/gamemodes/changeling/powers/absorb.dm
+++ b/code/game/gamemodes/changeling/powers/absorb.dm
@@ -4,7 +4,6 @@
chemical_cost = 0
dna_cost = 0
req_human = 1
- max_genetic_damage = 100
/obj/effect/proc_holder/changeling/absorbDNA/can_sting(mob/living/carbon/user)
if(!..())
@@ -42,13 +41,13 @@
to_chat(target, "You feel a sharp stabbing pain!")
target.take_overall_damage(40)
- feedback_add_details("changeling_powers","Absorb DNA|[i]")
+ SSblackbox.add_details("changeling_powers","Absorb DNA|[i]")
if(!do_mob(user, target, 150))
to_chat(user, "Our absorption of [target] has been interrupted!")
changeling.isabsorbing = 0
return
- feedback_add_details("changeling_powers","Absorb DNA|4")
+ SSblackbox.add_details("changeling_powers","Absorb DNA|4")
user.visible_message("[user] sucks the fluids from [target]!", "We have absorbed [target].")
to_chat(target, "You are absorbed by the changeling!")
diff --git a/code/game/gamemodes/changeling/powers/biodegrade.dm b/code/game/gamemodes/changeling/powers/biodegrade.dm
index 453dec9375..6e2d6b0ddd 100644
--- a/code/game/gamemodes/changeling/powers/biodegrade.dm
+++ b/code/game/gamemodes/changeling/powers/biodegrade.dm
@@ -5,9 +5,6 @@
chemical_cost = 30 //High cost to prevent spam
dna_cost = 2
req_human = 1
- genetic_damage = 10
- max_genetic_damage = 0
-
/obj/effect/proc_holder/changeling/biodegrade/sting_action(mob/living/carbon/human/user)
var/used = FALSE // only one form of shackles removed per use
diff --git a/code/game/gamemodes/changeling/powers/chameleon_skin.dm b/code/game/gamemodes/changeling/powers/chameleon_skin.dm
index 1f18f628a8..3be5103105 100644
--- a/code/game/gamemodes/changeling/powers/chameleon_skin.dm
+++ b/code/game/gamemodes/changeling/powers/chameleon_skin.dm
@@ -5,9 +5,6 @@
dna_cost = 2
chemical_cost = 25
req_human = 1
- genetic_damage = 10
- max_genetic_damage = 50
-
/obj/effect/proc_holder/changeling/chameleon_skin/sting_action(mob/user)
var/mob/living/carbon/human/H = user //SHOULD always be human, because req_human = 1
diff --git a/code/game/gamemodes/changeling/powers/fakedeath.dm b/code/game/gamemodes/changeling/powers/fakedeath.dm
index 798f8030e0..e35f04d9e7 100644
--- a/code/game/gamemodes/changeling/powers/fakedeath.dm
+++ b/code/game/gamemodes/changeling/powers/fakedeath.dm
@@ -5,8 +5,6 @@
dna_cost = 0
req_dna = 1
req_stat = DEAD
- max_genetic_damage = 100
-
//Fake our own death and fully heal. You will appear to be dead but regenerate fully after a short delay.
/obj/effect/proc_holder/changeling/fakedeath/sting_action(mob/living/user)
diff --git a/code/game/gamemodes/changeling/powers/humanform.dm b/code/game/gamemodes/changeling/powers/humanform.dm
index 743dbc91e9..d92e622c2d 100644
--- a/code/game/gamemodes/changeling/powers/humanform.dm
+++ b/code/game/gamemodes/changeling/powers/humanform.dm
@@ -2,10 +2,7 @@
name = "Human Form"
desc = "We change into a human."
chemical_cost = 5
- genetic_damage = 3
req_dna = 1
- max_genetic_damage = 3
-
//Transform into a human.
/obj/effect/proc_holder/changeling/humanform/sting_action(mob/living/carbon/user)
diff --git a/code/game/gamemodes/changeling/powers/lesserform.dm b/code/game/gamemodes/changeling/powers/lesserform.dm
index 538803de00..06824f9bed 100644
--- a/code/game/gamemodes/changeling/powers/lesserform.dm
+++ b/code/game/gamemodes/changeling/powers/lesserform.dm
@@ -3,7 +3,6 @@
desc = "We debase ourselves and become lesser. We become a monkey."
chemical_cost = 5
dna_cost = 1
- genetic_damage = 3
req_human = 1
//Transform into a monkey.
diff --git a/code/game/gamemodes/changeling/powers/linglink.dm b/code/game/gamemodes/changeling/powers/linglink.dm
index 5a64d551b5..232774c937 100644
--- a/code/game/gamemodes/changeling/powers/linglink.dm
+++ b/code/game/gamemodes/changeling/powers/linglink.dm
@@ -4,7 +4,6 @@
chemical_cost = 0
dna_cost = 0
req_human = 1
- max_genetic_damage = 100
/obj/effect/proc_holder/changeling/linglink/can_sting(mob/living/carbon/user)
if(!..())
@@ -56,7 +55,7 @@
to_chat(target, "You can now communicate in the changeling hivemind, say \":g message\" to communicate!")
target.reagents.add_reagent("salbutamol", 40) // So they don't choke to death while you interrogate them
sleep(1800)
- feedback_add_details("changeling_powers","Hivemind Link|[i]")
+ SSblackbox.add_details("changeling_powers","Hivemind Link|[i]")
if(!do_mob(user, target, 20))
to_chat(user, "Our link with [target] has ended!")
changeling.islinking = 0
diff --git a/code/game/gamemodes/changeling/powers/mutations.dm b/code/game/gamemodes/changeling/powers/mutations.dm
index 54e8ea1e38..aef9b6f1d2 100644
--- a/code/game/gamemodes/changeling/powers/mutations.dm
+++ b/code/game/gamemodes/changeling/powers/mutations.dm
@@ -16,7 +16,6 @@
helptext = "Yell at Miauw and/or Perakp"
chemical_cost = 1000
dna_cost = -1
- genetic_damage = 1000
var/silent = FALSE
var/weapon_type
@@ -67,7 +66,6 @@
helptext = "Yell at Miauw and/or Perakp"
chemical_cost = 1000
dna_cost = -1
- genetic_damage = 1000
var/helmet_type = /obj/item
var/suit_type = /obj/item
@@ -89,7 +87,7 @@
return 1
var/mob/living/carbon/human/H = user
if(istype(H.wear_suit, suit_type) || istype(H.head, helmet_type))
- H.visible_message("[H] casts off their [suit_name_simple]!", "We cast off our [suit_name_simple][genetic_damage > 0 ? ", temporarily weakening our genomes." : "."]", "You hear the organic matter ripping and tearing!")
+ H.visible_message("[H] casts off their [suit_name_simple]!", "We cast off our [suit_name_simple].", "You hear the organic matter ripping and tearing!")
H.temporarilyRemoveItemFromInventory(H.head, TRUE) //The qdel on dropped() takes care of it
H.temporarilyRemoveItemFromInventory(H.wear_suit, TRUE)
H.update_inv_wear_suit()
@@ -100,7 +98,6 @@
H.add_splatter_floor()
playsound(H.loc, 'sound/effects/splat.ogg', 50, 1) //So real sounds
- changeling.geneticdamage += genetic_damage //Casting off a space suit leaves you weak for a few seconds.
changeling.chem_recharge_slowdown -= recharge_slowdown
return 1
@@ -139,9 +136,7 @@
helptext = "We may retract our armblade in the same manner as we form it. Cannot be used while in lesser form."
chemical_cost = 20
dna_cost = 2
- genetic_damage = 10
req_human = 1
- max_genetic_damage = 20
weapon_type = /obj/item/weapon/melee/arm_blade
weapon_name_simple = "blade"
@@ -217,9 +212,7 @@
and Harm will stun it, and stab it if we're also holding a sharp weapon. Cannot be used while in lesser form."
chemical_cost = 10
dna_cost = 2
- genetic_damage = 5
req_human = 1
- max_genetic_damage = 10
weapon_type = /obj/item/weapon/gun/magic/tentacle
weapon_name_simple = "tentacle"
silent = TRUE
@@ -381,9 +374,7 @@
helptext = "Organic tissue cannot resist damage forever; the shield will break after it is hit too much. The more genomes we absorb, the stronger it is. Cannot be used while in lesser form."
chemical_cost = 20
dna_cost = 1
- genetic_damage = 12
req_human = 1
- max_genetic_damage = 20
weapon_type = /obj/item/weapon/shield/changeling
weapon_name_simple = "shield"
@@ -430,12 +421,10 @@
/obj/effect/proc_holder/changeling/suit/organic_space_suit
name = "Organic Space Suit"
desc = "We grow an organic suit to protect ourselves from space exposure."
- helptext = "We must constantly repair our form to make it space-proof, reducing chemical production while we are protected. Retreating the suit damages our genomes. Cannot be used in lesser form."
+ helptext = "We must constantly repair our form to make it space-proof, reducing chemical production while we are protected. Cannot be used in lesser form."
chemical_cost = 20
dna_cost = 2
- genetic_damage = 8
req_human = 1
- max_genetic_damage = 20
suit_type = /obj/item/clothing/suit/space/changeling
helmet_type = /obj/item/clothing/head/helmet/space/changeling
@@ -477,12 +466,10 @@
/obj/effect/proc_holder/changeling/suit/armor
name = "Chitinous Armor"
desc = "We turn our skin into tough chitin to protect us from damage."
- helptext = "Upkeep of the armor requires a low expenditure of chemicals. The armor is strong against brute force, but does not provide much protection from lasers. Retreating the armor damages our genomes. Cannot be used in lesser form."
+ helptext = "Upkeep of the armor requires a low expenditure of chemicals. The armor is strong against brute force, but does not provide much protection from lasers. Cannot be used in lesser form."
chemical_cost = 20
dna_cost = 1
- genetic_damage = 11
req_human = 1
- max_genetic_damage = 20
recharge_slowdown = 0.25
suit_type = /obj/item/clothing/suit/armor/changeling
diff --git a/code/game/gamemodes/changeling/powers/tiny_prick.dm b/code/game/gamemodes/changeling/powers/tiny_prick.dm
index c44a32c24d..ad6bf81e7c 100644
--- a/code/game/gamemodes/changeling/powers/tiny_prick.dm
+++ b/code/game/gamemodes/changeling/powers/tiny_prick.dm
@@ -40,10 +40,9 @@
return
if(!AStar(user, target.loc, /turf/proc/Distance, user.mind.changeling.sting_range, simulated_only = 0))
return
- if(target.mind && target.mind.changeling)
- sting_feedback(user,target)
- take_chemical_cost(user.mind.changeling)
- return
+ if(target.mind && target.mind.changeling)
+ sting_feedback(user, target)
+ user.mind.changeling.chem_charges -= chemical_cost
return 1
/obj/effect/proc_holder/changeling/sting/sting_feedback(mob/user, mob/target)
@@ -62,7 +61,6 @@
sting_icon = "sting_transform"
chemical_cost = 40
dna_cost = 3
- genetic_damage = 100
var/datum/changelingprofile/selected_dna = null
/obj/effect/proc_holder/changeling/sting/transformation/Click()
@@ -117,8 +115,6 @@
sting_icon = "sting_armblade"
chemical_cost = 20
dna_cost = 1
- genetic_damage = 20
- max_genetic_damage = 10
/obj/item/weapon/melee/arm_blade/false
desc = "A grotesque mass of flesh that used to be your arm. Although it looks dangerous at first, you can tell it's actually quite dull and useless."
diff --git a/code/game/gamemodes/changeling/powers/transform.dm b/code/game/gamemodes/changeling/powers/transform.dm
index f9aca83d04..9d0b095cc2 100644
--- a/code/game/gamemodes/changeling/powers/transform.dm
+++ b/code/game/gamemodes/changeling/powers/transform.dm
@@ -5,7 +5,6 @@
dna_cost = 0
req_dna = 1
req_human = 1
- max_genetic_damage = 3
/obj/item/clothing/glasses/changeling
name = "flesh"
diff --git a/code/game/gamemodes/clock_cult/clock_cult.dm b/code/game/gamemodes/clock_cult/clock_cult.dm
index 65e6b4ca6b..7fccb37d3c 100644
--- a/code/game/gamemodes/clock_cult/clock_cult.dm
+++ b/code/game/gamemodes/clock_cult/clock_cult.dm
@@ -198,7 +198,7 @@ Credit where due:
var/datum/game_mode/clockwork_cult/C = SSticker.mode
if(C.check_clockwork_victory())
text += "Ratvar's servants have succeeded in fulfilling His goals!"
- feedback_set_details("round_end_result", "win - servants completed their objective (summon ratvar)")
+ SSblackbox.set_details("round_end_result", "win - servants completed their objective (summon ratvar)")
else
var/half_victory = FALSE
var/obj/structure/destructible/clockwork/massive/celestial_gateway/G = locate() in GLOB.all_clockwork_objects
@@ -207,10 +207,10 @@ Credit where due:
if(half_victory)
text += "The crew escaped before Ratvar could rise, but the gateway \
was successfully constructed!"
- feedback_set_details("round_end_result", "halfwin - servants constructed the gateway but their objective was not completed (summon ratvar)")
+ SSblackbox.set_details("round_end_result", "halfwin - servants constructed the gateway but their objective was not completed (summon ratvar)")
else
text += "Ratvar's servants have failed!"
- feedback_set_details("round_end_result", "loss - servants failed their objective (summon ratvar)")
+ SSblackbox.set_details("round_end_result", "loss - servants failed their objective (summon ratvar)")
text += "
The servants' objective was:
[CLOCKCULT_OBJECTIVE]"
text += "
Ratvar's servants had [GLOB.clockwork_caches] Tinkerer's Caches."
text += "
Construction Value(CV) was: [GLOB.clockwork_construction_value]"
diff --git a/code/game/gamemodes/clock_cult/clock_effects/clock_sigils.dm b/code/game/gamemodes/clock_cult/clock_effects/clock_sigils.dm
index 6c56295c05..cf709f09b0 100644
--- a/code/game/gamemodes/clock_cult/clock_effects/clock_sigils.dm
+++ b/code/game/gamemodes/clock_cult/clock_effects/clock_sigils.dm
@@ -54,8 +54,11 @@
clockwork_desc = "A sigil that will stun the next non-Servant to cross it."
icon_state = "sigildull"
layer = HIGH_SIGIL_LAYER
- alpha = 60
+ alpha = 75
color = "#FAE48C"
+ light_range = 1.4
+ light_power = 1
+ light_color = "#FAE48C"
sigil_name = "Sigil of Transgression"
/obj/effect/clockwork/sigil/transgression/sigil_effects(mob/living/L)
@@ -93,10 +96,6 @@
sigil_name = "Sigil of Submission"
var/glow_type
-/obj/effect/clockwork/sigil/submission/New()
- ..()
- update_light()
-
/obj/effect/clockwork/sigil/submission/proc/post_channel(mob/living/L)
/obj/effect/clockwork/sigil/submission/sigil_effects(mob/living/L)
@@ -202,6 +201,21 @@
and [structure_number] Clockwork Structure[structure_number == 1 ? "":"s"] [structure_number == 1 ? "is":"are"] in range.")
if(iscyborg(user))
to_chat(user, "You can recharge from the [sigil_name] by crossing it.")
+ else if(!GLOB.ratvar_awakens)
+ to_chat(user, "Hitting the [sigil_name] with brass sheets will convert them to power at a rate of 1 brass sheet to [POWER_FLOOR]W power.")
+ if(!GLOB.ratvar_awakens)
+ to_chat(user, "You can recharge Clockwork Proselytizers from the [sigil_name].")
+
+/obj/effect/clockwork/sigil/transmission/attackby(obj/item/I, mob/living/user, params)
+ if(is_servant_of_ratvar(user) && istype(I, /obj/item/stack/tile/brass) && !GLOB.ratvar_awakens)
+ var/obj/item/stack/tile/brass/B = I
+ user.visible_message("[user] places [B] on [src], causing it to disintegrate into glowing orange energy!", \
+ "You charge the [sigil_name] with [B], providing it with [B.amount * POWER_FLOOR]W of power.")
+ modify_charge(-(B.amount * POWER_FLOOR))
+ playsound(src, 'sound/effects/light_flicker.ogg', (B.amount * POWER_FLOOR) * 0.01, 1)
+ qdel(B)
+ return TRUE
+ return ..()
/obj/effect/clockwork/sigil/transmission/sigil_effects(mob/living/L)
if(is_servant_of_ratvar(L))
@@ -214,9 +228,7 @@
if(!cyborg_checks(cyborg))
return
to_chat(cyborg, "You start to charge from the [sigil_name]...")
- if(!do_after(cyborg, 50, target = src))
- return
- if(!cyborg_checks(cyborg))
+ if(!do_after(cyborg, 50, target = src, extra_checks = CALLBACK(src, .proc/cyborg_checks, cyborg, TRUE)))
return
var/giving_power = min(Floor(cyborg.cell.maxcharge - cyborg.cell.charge, MIN_CLOCKCULT_POWER), power_charge) //give the borg either all our power or their missing power floored to MIN_CLOCKCULT_POWER
if(modify_charge(giving_power))
@@ -228,23 +240,27 @@
animate(cyborg, color = previous_color, time = 100)
addtimer(CALLBACK(cyborg, /atom/proc/update_atom_colour), 100)
-/obj/effect/clockwork/sigil/transmission/proc/cyborg_checks(mob/living/silicon/robot/cyborg)
+/obj/effect/clockwork/sigil/transmission/proc/cyborg_checks(mob/living/silicon/robot/cyborg, silent)
if(!cyborg.cell)
- to_chat(cyborg, "You have no cell!")
+ if(!silent)
+ to_chat(cyborg, "You have no cell!")
return FALSE
if(!power_charge)
- to_chat(cyborg, "The [sigil_name] has no stored power!")
+ if(!silent)
+ to_chat(cyborg, "The [sigil_name] has no stored power!")
return FALSE
if(cyborg.cell.charge > cyborg.cell.maxcharge - MIN_CLOCKCULT_POWER)
- to_chat(cyborg, "You are already at maximum charge!")
+ if(!silent)
+ to_chat(cyborg, "You are already at maximum charge!")
return FALSE
if(cyborg.has_status_effect(STATUS_EFFECT_POWERREGEN))
- to_chat(cyborg, "You are already regenerating power!")
+ if(!silent)
+ to_chat(cyborg, "You are already regenerating power!")
return FALSE
return TRUE
-/obj/effect/clockwork/sigil/transmission/New()
- ..()
+/obj/effect/clockwork/sigil/transmission/Initialize()
+ . = ..()
update_glow()
/obj/effect/clockwork/sigil/transmission/proc/modify_charge(amount)
@@ -265,7 +281,7 @@
if(!power_charge)
set_light(0)
else
- set_light(round(alpha*0.02, 1), round(alpha*0.005, 1))
+ set_light(max(alpha*0.02, 1.4), max(alpha*0.01, 0.1))
//Vitality Matrix: Drains health from non-servants to heal or even revive servants.
/obj/effect/clockwork/sigil/vitality
@@ -299,8 +315,7 @@
if((is_servant_of_ratvar(L) && L.suiciding) || sigil_active)
return
visible_message("[src] begins to glow bright blue!")
- animate(src, alpha = 255, time = 10)
- addtimer(CALLBACK(src, .proc/update_alpha), 10)
+ animate(src, alpha = 255, time = 10, flags = ANIMATION_END_NOW) //we may have a previous animation going. finish it first, then do this one without delay.
sleep(10)
//as long as they're still on the sigil and are either not a servant or they're a servant AND it has remaining vitality
while(L && (!is_servant_of_ratvar(L) || (is_servant_of_ratvar(L) && (GLOB.ratvar_awakens || vitality))) && get_turf(L) == get_turf(src))
@@ -369,12 +384,4 @@
animation_number = initial(animation_number)
sigil_active = FALSE
visible_message("[src] slowly stops glowing!")
- if(sigil_active || alpha == 255)
- animate(src, alpha = initial(alpha), time = 10)
- addtimer(CALLBACK(src, .proc/update_alpha), 10)
-
-/obj/effect/clockwork/sigil/vitality/proc/update_alpha()
- if(sigil_active)
- alpha = 255
- else
- alpha = initial(alpha)
+ animate(src, alpha = initial(alpha), time = 10, flags = ANIMATION_END_NOW)
diff --git a/code/game/gamemodes/clock_cult/clock_effects/spatial_gateway.dm b/code/game/gamemodes/clock_cult/clock_effects/spatial_gateway.dm
index f376410124..5c1d3fb5fb 100644
--- a/code/game/gamemodes/clock_cult/clock_effects/spatial_gateway.dm
+++ b/code/game/gamemodes/clock_cult/clock_effects/spatial_gateway.dm
@@ -15,9 +15,8 @@
var/obj/effect/clockwork/spatial_gateway/linked_gateway //The gateway linked to this one
var/timerid
-/obj/effect/clockwork/spatial_gateway/New()
- ..()
- update_light()
+/obj/effect/clockwork/spatial_gateway/Initialize()
+ . = ..()
addtimer(CALLBACK(src, .proc/check_setup), 1)
/obj/effect/clockwork/spatial_gateway/Destroy()
@@ -99,12 +98,12 @@
if(severity == 1 && uses)
uses = 0
visible_message("[src] is disrupted!")
- animate(src, alpha = 0, transform = matrix()*2, time = 10)
+ animate(src, alpha = 0, transform = matrix()*2, time = 10, flags = ANIMATION_END_NOW)
deltimer(timerid)
timerid = QDEL_IN(src, 10)
linked_gateway.uses = 0
linked_gateway.visible_message("[linked_gateway] is disrupted!")
- animate(linked_gateway, alpha = 0, transform = matrix()*2, time = 10)
+ animate(linked_gateway, alpha = 0, transform = matrix()*2, time = 10, flags = ANIMATION_END_NOW)
deltimer(linked_gateway.timerid)
linked_gateway.timerid = QDEL_IN(linked_gateway, 10)
return TRUE
@@ -131,9 +130,9 @@
playsound(src, 'sound/effects/EMPulse.ogg', 50, 1)
playsound(linked_gateway, 'sound/effects/EMPulse.ogg', 50, 1)
transform = matrix() * 1.5
- animate(src, transform = matrix() / 1.5, time = 10)
+ animate(src, transform = matrix() / 1.5, time = 10, flags = ANIMATION_END_NOW)
linked_gateway.transform = matrix() * 1.5
- animate(linked_gateway, transform = matrix() / 1.5, time = 10)
+ animate(linked_gateway, transform = matrix() / 1.5, time = 10, flags = ANIMATION_END_NOW)
A.forceMove(get_turf(linked_gateway))
if(!no_cost)
uses = max(0, uses - 1)
@@ -181,17 +180,26 @@
return procure_gateway(invoker, time_duration, gateway_uses, two_way)
var/istargetobelisk = istype(target, /obj/structure/destructible/clockwork/powered/clockwork_obelisk)
var/issrcobelisk = istype(src, /obj/structure/destructible/clockwork/powered/clockwork_obelisk)
- if(issrcobelisk && !anchored)
- to_chat(invoker, "[src] is no longer secured!")
- return FALSE
+ if(issrcobelisk)
+ if(!anchored)
+ to_chat(invoker, "[src] is no longer secured!")
+ return FALSE
+ var/obj/structure/destructible/clockwork/powered/clockwork_obelisk/CO = src //foolish as I am, how I set this proc up makes substypes unfeasible
+ if(CO.active)
+ to_chat(invoker, "[src] is now sustaining a gateway!")
+ return FALSE
if(istargetobelisk)
if(!target.anchored)
to_chat(invoker, "That [target.name] is no longer secured!")
return procure_gateway(invoker, time_duration, gateway_uses, two_way)
var/obj/structure/destructible/clockwork/powered/clockwork_obelisk/CO = target
+ if(CO.active)
+ to_chat(invoker, "That [target.name] is sustaining a gateway, and cannot recieve another!")
+ return procure_gateway(invoker, time_duration, gateway_uses, two_way)
var/efficiency = CO.get_efficiency_mod()
gateway_uses = round(gateway_uses * (2 * efficiency), 1)
time_duration = round(time_duration * (2 * efficiency), 1)
+ CO.active = TRUE //you'd be active in a second but you should update immediately
invoker.visible_message("The air in front of [invoker] ripples before suddenly tearing open!", \
"With a word, you rip open a [two_way ? "two-way":"one-way"] rift to [input_target_key]. It will last for [time_duration / 10] seconds and has [gateway_uses] use[gateway_uses > 1 ? "s" : ""].")
var/obj/effect/clockwork/spatial_gateway/S1 = new(issrcobelisk ? get_turf(src) : get_step(get_turf(invoker), invoker.dir))
diff --git a/code/game/gamemodes/clock_cult/clock_helpers/component_helpers.dm b/code/game/gamemodes/clock_cult/clock_helpers/component_helpers.dm
index e3c456460c..120ed0ff60 100644
--- a/code/game/gamemodes/clock_cult/clock_helpers/component_helpers.dm
+++ b/code/game/gamemodes/clock_cult/clock_helpers/component_helpers.dm
@@ -22,6 +22,12 @@
else
for(var/i in GLOB.clockwork_component_cache)
.[i] = max(MAX_COMPONENTS_BEFORE_RAND - LOWER_PROB_PER_COMPONENT*GLOB.clockwork_component_cache[i], 1)
+ for(var/obj/structure/destructible/clockwork/massive/celestial_gateway/G in GLOB.all_clockwork_objects)
+ if(G.still_needs_components())
+ for(var/i in G.required_components)
+ if(!G.required_components[i])
+ . -= i
+ break
. = pickweight(.)
//returns a component name from a component id
@@ -37,6 +43,8 @@
return "Replicant Alloy"
if(HIEROPHANT_ANSIBLE)
return "Hierophant Ansible"
+ else
+ return null
//returns a component acronym from a component id
/proc/get_component_acronym(id)
@@ -51,6 +59,8 @@
return "RA"
if(HIEROPHANT_ANSIBLE)
return "HA"
+ else
+ return null
//returns a component id from a component name
/proc/get_component_id(name)
@@ -65,6 +75,8 @@
return REPLICANT_ALLOY
if("Hierophant Ansible")
return HIEROPHANT_ANSIBLE
+ else
+ return null
//returns a component spanclass from a component id
/proc/get_component_span(id)
@@ -121,6 +133,8 @@
return /obj/effect/overlay/temp/ratvar/component/alloy
if(HIEROPHANT_ANSIBLE)
return /obj/effect/overlay/temp/ratvar/component/ansible
+ else
+ return null
//returns a type for a component from a component id
/proc/get_component_type(id)
@@ -134,4 +148,6 @@
if(REPLICANT_ALLOY)
return /obj/item/clockwork/component/replicant_alloy
if(HIEROPHANT_ANSIBLE)
- return /obj/item/clockwork/component/hierophant_ansible
\ No newline at end of file
+ return /obj/item/clockwork/component/hierophant_ansible
+ else
+ return null
\ No newline at end of file
diff --git a/code/game/gamemodes/clock_cult/clock_helpers/proselytizer_helpers.dm b/code/game/gamemodes/clock_cult/clock_helpers/proselytizer_helpers.dm
index c6954bb67e..529f38d832 100644
--- a/code/game/gamemodes/clock_cult/clock_helpers/proselytizer_helpers.dm
+++ b/code/game/gamemodes/clock_cult/clock_helpers/proselytizer_helpers.dm
@@ -286,6 +286,28 @@
user.visible_message("[user]'s [proselytizer.name] stops covering [src] with glowing orange energy.", \
"You finish repairing [src]. It is now at [obj_integrity]/[max_integrity] integrity.")
+//Hitting a sigil of transmission will try to charge from it.
+/obj/effect/clockwork/sigil/transmission/proselytize_vals(mob/living/user, obj/item/clockwork/clockwork_proselytizer/proselytizer)
+ . = TRUE
+ var/list/charge_values = list()
+ if(!proselytizer.sigil_charge_checks(charge_values, src, user))
+ return
+ user.visible_message("[user]'s [proselytizer.name] starts draining glowing orange energy from [src]...", \
+ "You start recharging your [proselytizer.name]...")
+ proselytizer.recharging = src
+ while(proselytizer && user && src)
+ if(!do_after(user, 10, target = src, extra_checks = CALLBACK(proselytizer, /obj/item/clockwork/clockwork_proselytizer.proc/sigil_charge_checks, charge_values, src, user, TRUE)))
+ break
+ modify_charge(charge_values["power_gain"])
+ proselytizer.modify_stored_power(charge_values["power_gain"])
+ playsound(src, 'sound/effects/light_flicker.ogg', charge_values["power_gain"] * 0.1, 1)
+
+ if(proselytizer)
+ proselytizer.recharging = null
+ if(user)
+ user.visible_message("[user]'s [proselytizer.name] stops draining glowing orange energy from [src].", \
+ "You finish recharging your [proselytizer.name]. It now contains [proselytizer.get_power()]W/[proselytizer.get_max_power()]W power.")
+
//Proselytizer mob heal proc, to avoid as much copypaste as possible.
/mob/living/proc/proselytizer_heal(mob/living/user, obj/item/clockwork/clockwork_proselytizer/proselytizer)
var/list/repair_values = list()
diff --git a/code/game/gamemodes/clock_cult/clock_items/clockwork_proselytizer.dm b/code/game/gamemodes/clock_cult/clock_items/clockwork_proselytizer.dm
index 25e2138b81..60df56b6ef 100644
--- a/code/game/gamemodes/clock_cult/clock_items/clockwork_proselytizer.dm
+++ b/code/game/gamemodes/clock_cult/clock_items/clockwork_proselytizer.dm
@@ -12,6 +12,7 @@
var/uses_power = TRUE
var/metal_to_power = FALSE
var/repairing = null //what we're currently repairing, if anything
+ var/obj/effect/clockwork/sigil/transmission/recharging = null //the sigil we're charging from, if any
var/speed_multiplier = 1 //how fast this proselytizer works
var/charge_rate = MIN_CLOCKCULT_POWER //how much power we gain every two seconds
var/charge_delay = 2 //how many proccess ticks remain before we can start to charge
@@ -140,10 +141,11 @@
/obj/item/clockwork/clockwork_proselytizer/attack_self(mob/living/user)
if(is_servant_of_ratvar(user))
- if(!can_use_power(POWER_WALL_TOTAL))
- to_chat(user, "[src] requires [POWER_WALL_TOTAL]W of power to produce brass sheets!")
- return
- modify_stored_power(-POWER_WALL_TOTAL)
+ if(uses_power)
+ if(!can_use_power(POWER_WALL_TOTAL))
+ to_chat(user, "[src] requires [POWER_WALL_TOTAL]W of power to produce brass sheets!")
+ return
+ modify_stored_power(-POWER_WALL_TOTAL)
playsound(src, 'sound/items/Deconstruct.ogg', 50, 1)
new/obj/item/stack/tile/brass(user.loc, 5)
to_chat(user, "You user [stored_power ? "some":"all"] of [src]'s power to produce some brass sheets. It now stores [get_power()]W/[get_max_power()]W of power.")
@@ -182,6 +184,9 @@
if(repairing)
to_chat(user, "You are currently repairing [repairing] with [src]!")
return FALSE
+ if(recharging)
+ to_chat(user, "You are currently recharging [src] from the [recharging.sigil_name]!")
+ return FALSE
var/list/proselytize_values = target.proselytize_vals(user, src) //relevant values for proselytizing stuff, given as an associated list
if(!islist(proselytize_values))
if(proselytize_values != TRUE) //if we get true, fail, but don't send a message for whatever reason
@@ -237,7 +242,7 @@
/obj/item/clockwork/clockwork_proselytizer/proc/proselytize_checks(list/proselytize_values, atom/target, expected_type, mob/user, silent) //checked constantly while proselytizing
if(!islist(proselytize_values) || !target || QDELETED(target) || !user)
return FALSE
- if(repairing)
+ if(repairing || recharging)
return FALSE
if(target.type != expected_type)
return FALSE
@@ -296,3 +301,20 @@
[round(repair_values["amount_to_heal"]*MIN_CLOCKCULT_POWER, MIN_CLOCKCULT_POWER)]W to fully repair [target == user ? "yourself" : "[target.p_them()]"]!")
return FALSE
return TRUE
+
+//checked constantly while charging from a sigil
+/obj/item/clockwork/clockwork_proselytizer/proc/sigil_charge_checks(list/charge_values, obj/effect/clockwork/sigil/transmission/sigil, mob/user, silent)
+ if(!islist(charge_values) || !sigil || QDELETED(sigil) || !user)
+ return FALSE
+ if(can_use_power(RATVAR_POWER_CHECK))
+ return FALSE
+ charge_values["power_gain"] = Clamp(sigil.power_charge, 0, POWER_WALL_MINUS_FLOOR)
+ if(!charge_values["power_gain"])
+ if(!silent)
+ to_chat(user, "The [sigil.sigil_name] contains no power!")
+ return FALSE
+ if(stored_power + charge_values["power_gain"] > max_power)
+ if(!silent)
+ to_chat(user, "Your [name] contains too much power to charge from the [sigil.sigil_name]!")
+ return FALSE
+ return TRUE
diff --git a/code/game/gamemodes/clock_cult/clock_items/clockwork_slab.dm b/code/game/gamemodes/clock_cult/clock_items/clockwork_slab.dm
index 35caabab5a..8b3aa01533 100644
--- a/code/game/gamemodes/clock_cult/clock_items/clockwork_slab.dm
+++ b/code/game/gamemodes/clock_cult/clock_items/clockwork_slab.dm
@@ -326,13 +326,19 @@
if(production_time != SLAB_PRODUCTION_TIME+SLAB_SLOWDOWN_MAXIMUM)
production_text_addon = ", which increases for each human or silicon servant above [SCRIPT_SERVANT_REQ]"
production_time = production_time/600
- var/production_text = "[round(production_time)] minute\s"
+ var/list/production_text
+ if(round(production_time))
+ production_text = list("[round(production_time)] minute\s")
if(production_time != round(production_time))
production_time -= round(production_time)
production_time *= 60
- production_text += " and [round(production_time, 1)] second\s"
+ if(!LAZYLEN(production_text))
+ production_text = list("[round(production_time, 1)] second\s")
+ else
+ production_text += " and [round(production_time, 1)] second\s"
production_text += ""
production_text += production_text_addon
+ production_text = production_text.Join()
textlist = list("