diff --git a/_maps/map_files/cyberiad/z2.dmm b/_maps/map_files/cyberiad/z2.dmm index bbe4923497e..5f561cd6cd3 100644 --- a/_maps/map_files/cyberiad/z2.dmm +++ b/_maps/map_files/cyberiad/z2.dmm @@ -206,19 +206,19 @@ "dX" = (/obj/structure/filingcabinet/filingcabinet,/turf/unsimulated/floor{dir = 5; icon_state = "carpetside"},/area/centcom/control) "dY" = (/turf/unsimulated/floor{dir = 1; icon_state = "carpet15-11"},/area/centcom/control) "dZ" = (/obj/structure/table/woodentable,/obj/item/weapon/paper_bin{pixel_y = 5},/obj/item/weapon/pen/multi,/turf/unsimulated/floor{dir = 9; icon_state = "carpetside"},/area/centcom/control) -"ea" = (/obj/machinery/computer/artillerycontrol,/turf/unsimulated/floor{dir = 5; icon_state = "carpetside"},/area/centcom/control) +"ea" = (/obj/machinery/computer/bsa_control/admin,/turf/unsimulated/floor{dir = 5; icon_state = "carpetside"},/area/centcom/control) "eb" = (/obj/structure/stool/bed/chair/office/dark{dir = 4},/turf/unsimulated/floor{dir = 8; icon_state = "carpet15-14"; tag = "icon-carpet (WEST)"},/area/centcom/control) -"ec" = (/obj/structure/artilleryplaceholder{tag = "icon-1"; icon_state = "1"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTHWEST)"; icon_state = "warnplate"; dir = 9},/area/centcom/control) +"ec" = (/turf/unsimulated/floor{tag = "icon-warnplate (NORTHWEST)"; icon_state = "warnplate"; dir = 9},/area/centcom/control) "ed" = (/turf/unsimulated/floor{icon_state = "platingdmg1"},/area/prison/solitary) "ee" = (/turf/unsimulated/floor{icon_state = "floorscorched2"},/area/prison/solitary) -"ef" = (/obj/structure/artilleryplaceholder{tag = "icon-3"; icon_state = "3"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"eg" = (/obj/structure/artilleryplaceholder{tag = "icon-2"; icon_state = "2"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"eh" = (/obj/structure/artilleryplaceholder{tag = "icon-5"; icon_state = "5"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"ei" = (/obj/structure/artilleryplaceholder{tag = "icon-4"; icon_state = "4"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) +"ef" = (/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) +"eg" = (/obj/machinery/bsa/full/admin/east,/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) +"eh" = (/turf/unsimulated/floor{tag = "icon-warnplate (NORTHEAST)"; icon_state = "warnplate"; dir = 5},/area/centcom/control) +"ei" = (/turf/space,/area/centcom/control) "ej" = (/obj/structure/window/reinforced,/obj/structure/window/reinforced{dir = 1},/turf/unsimulated/wall{tag = "icon-iron12"; icon_state = "iron12"},/area/space) "ek" = (/obj/structure/window/reinforced{dir = 1},/obj/structure/window/reinforced,/turf/unsimulated/wall{tag = "icon-iron12"; icon_state = "iron12"},/area/space) "el" = (/turf/unsimulated/wall{tag = "icon-iron11"; icon_state = "iron11"},/area/space) -"em" = (/obj/structure/artilleryplaceholder{tag = "icon-7"; icon_state = "7"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) +"em" = (/turf/unsimulated/floor{tag = "icon-warnplate (SOUTHWEST)"; icon_state = "warnplate"; dir = 10},/area/centcom/control) "en" = (/turf/simulated/floor/holofloor{tag = "icon-1 (NORTHEAST)"; icon_state = "1"; dir = 5},/area/holodeck/source_space) "eo" = (/turf/simulated/floor/holofloor{tag = "icon-17 (NORTHEAST)"; icon_state = "17"; dir = 5},/area/holodeck/source_space) "ep" = (/turf/simulated/floor/holofloor{tag = "icon-22 (NORTHEAST)"; icon_state = "22"; dir = 5},/area/holodeck/source_space) @@ -234,7 +234,7 @@ "ez" = (/obj/structure/table/holotable,/obj/item/clothing/gloves/boxing/hologlove,/turf/simulated/floor/holofloor{dir = 9; icon_state = "red"},/area/holodeck/source_boxingcourt) "eA" = (/turf/simulated/floor/holofloor{dir = 1; icon_state = "red"},/area/holodeck/source_boxingcourt) "eB" = (/obj/structure/table/holotable,/obj/item/clothing/gloves/boxing/hologlove,/turf/simulated/floor/holofloor{dir = 5; icon_state = "red"},/area/holodeck/source_boxingcourt) -"eC" = (/obj/structure/artilleryplaceholder{tag = "icon-6"; icon_state = "6"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) +"eC" = (/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) "eD" = (/obj/structure/flora/grass/both,/turf/simulated/floor/holofloor{tag = "icon-snow"; icon_state = "snow"},/area/holodeck/source_snowfield) "eE" = (/turf/simulated/floor/holofloor{tag = "icon-carpet4-0 (EAST)"; icon_state = "carpet4-0"; dir = 4},/area/holodeck/source_meetinghall) "eF" = (/turf/simulated/floor/holofloor{tag = "icon-carpetsymbol (SOUTHEAST)"; icon_state = "carpetsymbol"; dir = 6},/area/holodeck/source_meetinghall) @@ -250,33 +250,20 @@ "eP" = (/turf/simulated/floor/holofloor{dir = 8; icon_state = "red"},/area/holodeck/source_boxingcourt) "eQ" = (/turf/simulated/floor/holofloor,/area/holodeck/source_boxingcourt) "eR" = (/turf/simulated/floor/holofloor{dir = 4; icon_state = "red"},/area/holodeck/source_boxingcourt) -"eS" = (/obj/structure/artilleryplaceholder{tag = "icon-9"; icon_state = "9"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"eT" = (/obj/structure/artilleryplaceholder{tag = "icon-8"; icon_state = "8"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"eU" = (/obj/structure/artilleryplaceholder{tag = "icon-11"; icon_state = "11"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTHEAST)"; icon_state = "warnplate"; dir = 5},/area/centcom/control) -"eV" = (/obj/structure/artilleryplaceholder{tag = "icon-10"; icon_state = "10"},/turf/unsimulated/floor{tag = "icon-warnplate (NORTH)"; icon_state = "warnplate"; dir = 1},/area/centcom/control) -"eW" = (/obj/structure/artilleryplaceholder{tag = "icon-12"; icon_state = "12"},/turf/space,/area/centcom/control) +"eS" = (/turf/unsimulated/floor{tag = "icon-warnplate (SOUTHEAST)"; icon_state = "warnplate"; dir = 6},/area/centcom/control) +"eT" = (/turf/unsimulated/floor{dir = 4; icon_state = "carpetside"},/area/centcom/specops) "eX" = (/obj/structure/flora/tree/pine,/turf/simulated/floor/holofloor{tag = "icon-snow"; icon_state = "snow"},/area/holodeck/source_snowfield) "eY" = (/obj/structure/table/woodentable,/turf/simulated/floor/holofloor{tag = "icon-grimy"; icon_state = "grimy"; dir = 2},/area/holodeck/source_meetinghall) "eZ" = (/turf/simulated/floor/holofloor{dir = 1; icon_state = "red"},/area/holodeck/source_basketball) "fa" = (/turf/unsimulated/floor{dir = 2; icon_state = "carpet15-5"},/area/centcom/control) "fb" = (/obj/structure/table/woodentable,/obj/machinery/photocopier{icon_state = "fax"; name = "fax machine"},/obj/item/weapon/photo{name = "butts"},/turf/unsimulated/floor{dir = 10; icon_state = "carpetside"},/area/centcom/control) "fc" = (/obj/machinery/computer/communications,/turf/unsimulated/floor{dir = 6; icon_state = "carpetside"},/area/centcom/control) -"fd" = (/obj/structure/artilleryplaceholder{tag = "icon-13"; icon_state = "13"},/turf/unsimulated/floor{tag = "icon-warnplate (SOUTHWEST)"; icon_state = "warnplate"; dir = 10},/area/centcom/control) -"fe" = (/obj/structure/artilleryplaceholder{tag = "icon-15"; icon_state = "15"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) "ff" = (/turf/unsimulated/wall,/area/ninja/outpost) "fg" = (/turf/unsimulated/wall,/area/ninja/holding) "fh" = (/turf/unsimulated/wall/fakeglass{tag = "icon-fakewindows (WEST)"; icon_state = "fakewindows"; dir = 8},/area/ninja/holding) "fi" = (/turf/unsimulated/wall/fakeglass{tag = "icon-fakewindows2 (WEST)"; icon_state = "fakewindows2"; dir = 8},/area/ninja/holding) "fj" = (/turf/unsimulated/wall/fakeglass{tag = "icon-fakewindows (EAST)"; icon_state = "fakewindows"; dir = 4},/area/ninja/holding) "fk" = (/turf/unsimulated/wall{desc = "The door appears to be locked tightly."; icon = 'icons/obj/doors/Doorhatchele.dmi'; icon_state = "door_closed"; name = "Locked Door"},/area/ninja/holding) -"fl" = (/obj/structure/artilleryplaceholder{tag = "icon-14"; icon_state = "14"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fm" = (/obj/structure/artilleryplaceholder{tag = "icon-17"; icon_state = "17"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fn" = (/obj/structure/artilleryplaceholder{tag = "icon-16"; icon_state = "16"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fo" = (/obj/structure/artilleryplaceholder{tag = "icon-19"; icon_state = "19"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fp" = (/obj/structure/artilleryplaceholder{tag = "icon-18"; icon_state = "18"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fq" = (/obj/structure/artilleryplaceholder{tag = "icon-21"; icon_state = "21"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fr" = (/obj/structure/artilleryplaceholder{tag = "icon-20"; icon_state = "20"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fs" = (/obj/structure/artilleryplaceholder{tag = "icon-23"; icon_state = "23"},/turf/unsimulated/floor{tag = "icon-warnplate (SOUTHEAST)"; icon_state = "warnplate"; dir = 6},/area/centcom/control) "ft" = (/turf/unsimulated/wall{desc = "The door appears to be locked tightly."; icon = 'icons/obj/doors/Doorhatchele.dmi'; icon_state = "door_closed"; name = "Locked Door"},/area/ninja/outpost) "fu" = (/turf/unsimulated/floor{icon_state = "dark"},/area/ninja/outpost) "fv" = (/obj/structure/ninjatele{pixel_y = 25},/turf/unsimulated/floor{icon_state = "dark"},/area/ninja/outpost) @@ -288,8 +275,6 @@ "fB" = (/obj/machinery/vending/boozeomat,/turf/unsimulated/floor{icon_state = "freezerfloor"; dir = 2},/area/ninja/holding) "fC" = (/obj/structure/table,/obj/item/weapon/storage/box/donkpockets{pixel_x = 3; pixel_y = 3},/obj/item/weapon/storage/box/donkpockets{pixel_x = 3; pixel_y = 3},/obj/item/weapon/storage/box/donkpockets{pixel_x = 3; pixel_y = 3},/obj/item/weapon/storage/box/donkpockets{pixel_x = 3; pixel_y = 3},/turf/unsimulated/floor{icon_state = "freezerfloor"; dir = 2},/area/ninja/holding) "fD" = (/obj/structure/rack,/obj/item/device/camera,/obj/machinery/light/spot{tag = "icon-tube1 (NORTH)"; icon_state = "tube1"; dir = 1},/turf/unsimulated/floor{icon_state = "cafeteria"; dir = 2},/area/ninja/holding) -"fE" = (/obj/structure/artilleryplaceholder{tag = "icon-22"; icon_state = "22"},/turf/unsimulated/floor{tag = "icon-warnplate"; icon_state = "warnplate"; dir = 2},/area/centcom/control) -"fF" = (/obj/structure/artilleryplaceholder{tag = "icon-24"; icon_state = "24"},/turf/space,/area/centcom/control) "fG" = (/obj/machinery/computer/arcade,/turf/unsimulated/floor{icon_state = "cafeteria"; dir = 2},/area/ninja/holding) "fH" = (/turf/unsimulated/beach/sand,/area/ninja/holding) "fI" = (/obj/effect/overlay/palmtree_r,/obj/effect/overlay/coconut,/turf/unsimulated/beach/sand,/area/ninja/holding) @@ -999,7 +984,6 @@ "vJ" = (/obj/machinery/newscaster{layer = 3.3; pixel_x = 0; pixel_y = -27},/turf/unsimulated/floor{icon_state = "dark"},/area/centcom/specops) "vL" = (/obj/item/device/radio/intercom/specops{pixel_y = -28},/turf/unsimulated/floor{icon_state = "dark"},/area/centcom/specops) "vM" = (/obj/structure/table/woodentable{dir = 10},/obj/machinery/door_control{desc = "A remote control switch to block view of the singularity."; icon_state = "doorctrl0"; id = "SPECOPS"; name = "Ready Room"; pixel_y = 16; req_access_txt = "114"},/obj/machinery/door_control{desc = "A remote control switch to block view of the singularity."; icon_state = "doorctrl0"; id = "ASSAULT"; name = "Assault Armor"; pixel_y = -4; req_access_txt = "114"},/obj/machinery/door_control{desc = "A remote control switch to block view of the singularity."; icon_state = "doorctrl0"; id = "specopsoffice"; name = "Privacy Shutters"; pixel_y = 6; req_access_txt = "114"},/turf/unsimulated/floor{dir = 8; icon_state = "carpetside"},/area/centcom/specops) -"vO" = (/obj/machinery/computer/artillerycontrol{luminosity = 255},/turf/unsimulated/floor{dir = 4; icon_state = "carpetside"},/area/centcom/specops) "vP" = (/obj/structure/stool/bed/chair{dir = 1},/turf/unsimulated/floor{icon_state = "grimy"},/area/centcom/specops) "vQ" = (/obj/machinery/telecomms/processor/preset_cent,/turf/unsimulated/floor{icon_state = "green"; dir = 8},/area/centcom/control) "vS" = (/obj/machinery/newscaster/security_unit{pixel_x = -32},/turf/unsimulated/floor{icon_state = "grimy"},/area/centcom/specops) @@ -1304,7 +1288,6 @@ "Gs" = (/obj/structure/table/woodentable,/obj/item/toy/cards/deck/syndicate,/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/area/admin) "Gt" = (/obj/structure/table/woodentable,/obj/item/weapon/reagent_containers/food/drinks/drinkingglass/devilskiss,/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/area/admin) "Gu" = (/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/turf/unsimulated/wall{desc = "This window appears to be reinforced, it looks nearly impossible to break."; dir = 8; icon = 'icons/turf/shuttle.dmi'; icon_state = "window5_end"; name = "window"; opacity = 0; tag = "icon-window5_end (WEST)"},/area/admin) -"Gv" = (/obj/machinery/computer/artillerycontrol{luminosity = 255},/turf/unsimulated/floor{tag = "icon-floor"; icon_state = "floor"},/area/admin) "Gx" = (/obj/item/weapon/stool,/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/area/admin) "Gy" = (/obj/structure/table/woodentable,/obj/item/weapon/lighter/zippo/engraved,/obj/item/weapon/storage/fancy/cigarettes/dromedaryco,/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/area/admin) "Gz" = (/turf/unsimulated/floor{dir = 8; icon_state = "wood"},/turf/unsimulated/wall{desc = "This window appears to be reinforced, it looks nearly impossible to break."; dir = 4; icon = 'icons/turf/shuttle.dmi'; icon_state = "window5_end"; name = "window"; opacity = 0; tag = "icon-window5 (EAST)"},/area/admin) @@ -1560,8 +1543,8 @@ aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXsXsXsXsXsXsXsXtatbtctdtdtesqsqsqsqsqsEsEmnsMsCmnsEsEsEsEsEsQsQsQsQtfsQsQtgsqsqsqdVaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNthtitititititititititjtktitititjtltmtntdtdtdsqsrssstsqtosEmnsMtpmnsEsEsEsEsutqsQsQsQtrsQsQtssqsqsqsqdVaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXsXsXsXsXsXsXsXtatttutdtdtdsqswsssssxsEsEsEsEsEsEsEsEsEsEsqsusususususususqsqdWdXsqsqsqsqsqsqsqsqsqsqsqsqsqdVaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN -aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNthtitititititititititvtktitititvtwtmtntdtdtdsqsqsqsqsqsqsqtxsqsqsqsqsEsEtysqtztztztztztztzsudZdYebeasuecegefeieheCemeTeSeVeUeWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN -aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXsXsXsXsXsXsXsXtatttutdtdtAsqtBtCtDsqtEtFtFtFtFtGsqsEsEtHsqtztztztztztztzsufbfatLfcsufdflfefnfmfpfofrfqfEfsfFaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN +aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNthtitititititititititvtktitititvtwtmtntdtdtdsqsqsqsqsqsqsqtxsqsqsqsqsEsEtysqtztztztztztztzsudZdYebeasuecefefefefefegefefefeheiaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN +aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXsXsXsXsXsXsXsXtatttutdtdtAsqtBtCtDsqtEtFtFtFtFtGsqsEsEtHsqtztztztztztztzsufbfatLfcsuemeCeCeCeCeCeCeCeCeCeSeiaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNthtitititititititititItktitititItJtmtntdtdtdsqtKtLtMtNtFtFtFtFtFtOsqsusxsusqsusususususususqsqfLsqsqsqsqsqsqsqsqsqsqsqsqsqsqfXaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXsXsXsXsXsXsXsXtatttutdtdtdsqsqsususqsqsqsususususqtQtRtStTtTtTtTtTtTtTtTtTuEtRtZsqfXaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNthtitititititititititVtktitititVtWtXtYtdtdtdsqtztztztztztztztztztzsqtQtRtRtRtRtRtRtRtRtRtRtRtRtRtZsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN @@ -1574,7 +1557,7 @@ aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXuWsXsXujuXuRooonvavbujvcvdvdvdvdvesXuosXsXsXsXsqtQtRtZsuvfuuvgvgvgvhvisutQtRtZsqaNaNohogogogogogogogohaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXvjvkvlsXujujvauRvmuRujujvnvdvovpvqvdsXsXsXvrtTtUsqtQtRtZsqsqvsvtvuvvvwsqsqtQtRtZsqaNaNohogogogopogogogohaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXvkvkvkvxujujujvyvyujujujvzvdvAvBvCbesXvEtTuEtRtRvFtRtRtZsqsqsusususususqsqtQtRtZsqaNaNoqodododododododoraNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN -aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXvGvHsXvIvJujujujujvLujsXvdvMmjvOvPsXvQtRtRtRtZsutQtRtStTtTtTtTtTtTtTtTtTuEtRtZsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN +aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXvGvHsXvIvJujujujujvLujsXvdvMmjeTvPsXvQtRtRtRtZsutQtRtStTtTtTtTtTtTtTtTtTuEtRtZsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNsXsXsXsXsXsXsXsXbfbfsXsXsXvSvTvUvVvdsXvWtRtRtRvXsutQtRtRtRtRtRtRtRtRtRtRtRtRtRtZsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNwbwcwdwbwesXiDwgwhwiwjsXwkudududwlsuwmudududududuetRucudududududwnsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNwrwswtwrwesXsXsXsXsXsXsXsqsqsqsqsqsqsqsqsqsqsqsqsqwusqsqsqsqsqsqsqsqaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaN @@ -1654,7 +1637,7 @@ aNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNbWbWbWbWbWbWbWbWbWbW aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWbWaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNDtDAGaGdGeGfGgGhGiGjGbDAGaDKDKDKDKDKDKGbDwDwDwDwDwGaDKGbDwDwGkDwFWFXFXFXGlFXFXFXFYDAaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNDIGmlhDKDKlvDKDKDKDKDKGoDKDKGpGpGpGpDKDKDKDKDKDKDKDKDKDKGqFXFXFXFXFXFXGrGsGtFXFXFXGuaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNDNDKlwDKDKDKDKDKDKDKDKGoDKDKGpGpGpGpDKDKDKDKDKDKDKDKDKDKGqFXFXFXFXFXGxGyGrGrGxFXFXGzaNaNaNaNaN -aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNEfGAGvDKDKlJDKDKDKDKDKGoDKDKGpGpGpGpDKDKDKDKDKDKDKDKDKFkDwDwGkDwGCFXFXGxGxGxFXFXGDDAaNaNaNaNaN +aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNEfGADKDKDKlJDKDKDKDKDKGoDKDKGpGpGpGpDKDKDKDKDKDKDKDKDKFkDwDwGkDwGCFXFXGxGxGxFXFXGDDAaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNEMDAEIGEGFGGGHGIGJGKFkDAEIDKDKDKDKDKDKFkDwDwEIDKFkDwDwDwDAEnaNEMDwGCFXFXFXFXFXGDDAEnaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNEMDwDwDwDwDwDwDwDwDwDwDwDwEIDKDKFkDwDwDwDwDwGLDwDwDwDADAaNaNaNEMDwGCFXFXFXGDDwEnaNaNaNaNaNaN aNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNFLFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFZFLaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNaNDvDAGMGMDAaNDAFvGNFvFvFvGNFvDADAaNaNaNaNEMDwFIFJFKDwEnaNaNaNaNaNaNaN diff --git a/code/__DEFINES/misc.dm b/code/__DEFINES/misc.dm index b9f32e9b49a..75f953f6c79 100644 --- a/code/__DEFINES/misc.dm +++ b/code/__DEFINES/misc.dm @@ -316,4 +316,7 @@ #define DRAKE_SCORE "Drakes Killed" #define BIRD_SCORE "Hierophants Killed" #define BOSS_SCORE "Bosses Killed" -#define TENDRIL_CLEAR_SCORE "Tendrils Killed" \ No newline at end of file +#define TENDRIL_CLEAR_SCORE "Tendrils Killed" + +// The number of station goals generated each round. +#define STATION_GOAL_BUDGET 1 \ No newline at end of file diff --git a/code/_globalvars/lists/flavor_misc.dm b/code/_globalvars/lists/flavor_misc.dm index 713289c737c..c139b969df1 100644 --- a/code/_globalvars/lists/flavor_misc.dm +++ b/code/_globalvars/lists/flavor_misc.dm @@ -46,4 +46,20 @@ var/list/TAGGERLOCATIONS = list("Disposals", "Robotics", "HoP Office", "Library", "Chapel", "Captain's Office", "Bar", "Kitchen", "Hydroponics", "Janitor Closet","Genetics","Brig Physician") -var/list/hit_appends = list("-OOF", "-ACK", "-UGH", "-HRNK", "-HURGH", "-GLORF") \ No newline at end of file +var/list/hit_appends = list("-OOF", "-ACK", "-UGH", "-HRNK", "-HURGH", "-GLORF") + +var/global/list/greek_letters = list("Alpha", "Beta", "Gamma", "Delta", + "Epsilon", "Zeta", "Eta", "Theta", "Iota", "Kappa", "Lambda", "Mu", + "Nu", "Xi", "Omicron", "Pi", "Rho", "Sigma", "Tau", "Upsilon", "Phi", + "Chi", "Psi", "Omega") + +var/global/list/phonetic_alphabet = list("Alpha", "Bravo", "Charlie", + "Delta", "Echo", "Foxtrot", "Golf", "Hotel", "India", "Juliet", + "Kilo", "Lima", "Mike", "November", "Oscar", "Papa", "Quebec", + "Romeo", "Sierra", "Tango", "Uniform", "Victor", "Whiskey", "X-ray", + "Yankee", "Zulu") + +var/global/list/numbers_as_words = list("One", "Two", "Three", "Four", + "Five", "Six", "Seven", "Eight", "Nine", "Ten", "Eleven", "Twelve", + "Thirteen", "Fourteen", "Fifteen", "Sixteen", "Seventeen", + "Eighteen", "Nineteen") \ No newline at end of file diff --git a/code/_globalvars/lists/objects.dm b/code/_globalvars/lists/objects.dm index 6733f43b050..41588a7b07a 100644 --- a/code/_globalvars/lists/objects.dm +++ b/code/_globalvars/lists/objects.dm @@ -35,8 +35,9 @@ var/global/list/tracked_implants = list() //list of all current implants that var/global/list/pinpointer_list = list() //list of all pinpointers. Used to change stuff they are pointing to all at once. var/global/list/abductor_equipment = list() //list of all abductor equipment - var/global/list/global_intercoms = list() //list of all intercomms, across all z-levels var/global/list/global_radios = list() //list of all radios, across all z-levels -var/global/list/poi_list = list() //list of points of interest for observe/follow \ No newline at end of file +var/global/list/meteor_list = list() //list of all meteors +var/global/list/poi_list = list() //list of points of interest for observe/follow + diff --git a/code/datums/beam.dm b/code/datums/beam.dm index 1b48dd37560..7a8c802b42d 100644 --- a/code/datums/beam.dm +++ b/code/datums/beam.dm @@ -15,7 +15,6 @@ var/static_beam = 0 var/beam_type = /obj/effect/ebeam //must be subtype - /datum/beam/New(beam_origin,beam_target,beam_icon='icons/effects/beam.dmi',beam_icon_state="b_beam",time=50,maxdistance=10,btype = /obj/effect/ebeam) endtime = world.time+time origin = beam_origin @@ -30,7 +29,6 @@ icon_state = beam_icon_state beam_type = btype - /datum/beam/proc/Start() Draw() while(!finished && origin && target && world.time < endtime && get_dist(origin,target)Notice: [src] did not define announce()") @@ -78,6 +80,7 @@ // if(revdata) // feedback_set_details("revision","[revdata.revision]") feedback_set_details("server_ip","[world.internet_address]:[world.port]") + generate_station_goals() start_state = new /datum/station_state() start_state.count() return 1 @@ -222,7 +225,7 @@ /datum/game_mode/proc/check_win() //universal trigger to be called at mob death, nuke explosion, etc. To be called from everywhere. return 0 - + /datum/game_mode/proc/get_players_for_role(var/role, override_jobbans=0) var/list/players = list() var/list/candidates = list() @@ -475,3 +478,36 @@ proc/get_nt_opposed() text += "
Objective #[count]: [objective.explanation_text] Fail." count++ return text + +/datum/game_mode/proc/generate_station_goals() + var/list/possible = list() + for(var/T in subtypesof(/datum/station_goal)) + var/datum/station_goal/G = T + if(config_tag in initial(G.gamemode_blacklist)) + continue + possible += T + var/goal_weights = 0 + while(possible.len && goal_weights < STATION_GOAL_BUDGET) + var/datum/station_goal/picked = pick_n_take(possible) + goal_weights += initial(picked.weight) + station_goals += new picked + + if(station_goals.len) + send_station_goals_message() + +/datum/game_mode/proc/send_station_goals_message() + var/message_text = "
" + message_text += "

[command_name()] Orders


" + message_text += "Special Orders for [station_name()]:

" + + for(var/datum/station_goal/G in station_goals) + G.on_report() + message_text += G.get_report() + message_text += "
" + + print_command_report(message_text, "[command_name()] Orders") + +/datum/game_mode/proc/declare_station_goal_completion() + for(var/V in station_goals) + var/datum/station_goal/G = V + G.print_result() \ No newline at end of file diff --git a/code/game/gamemodes/gameticker.dm b/code/game/gamemodes/gameticker.dm index 5a3d0599c8c..8067aabe719 100644 --- a/code/game/gamemodes/gameticker.dm +++ b/code/game/gamemodes/gameticker.dm @@ -416,7 +416,6 @@ var/round_start_time = 0 /datum/controller/gameticker/proc/declare_completion() - nologevent = 1 //end of round murder and shenanigans are legal; there's no need to jam up attack logs past this point. //Round statistics report var/datum/station_state/end_state = new /datum/station_state() @@ -471,6 +470,9 @@ var/round_start_time = 0 scoreboard() karmareminder() + // Declare the completion of the station goals + mode.declare_station_goal_completion() + //Ask the event manager to print round end information event_manager.RoundEnd() diff --git a/code/game/gamemodes/meteor/meteors.dm b/code/game/gamemodes/meteor/meteors.dm index 890cc4e151c..e634a47c590 100644 --- a/code/game/gamemodes/meteor/meteors.dm +++ b/code/game/gamemodes/meteor/meteors.dm @@ -118,11 +118,13 @@ return . /obj/effect/meteor/Destroy() + meteor_list -= src walk(src,0) //this cancels the walk_towards() proc return ..() /obj/effect/meteor/New() ..() + meteor_list += src SpinAnimation() /obj/effect/meteor/Bump(atom/A) diff --git a/code/game/gamemodes/miniantags/bot_swarm/swarmer_event.dm b/code/game/gamemodes/miniantags/bot_swarm/swarmer_event.dm index d93bc601f89..7a16ef17857 100644 --- a/code/game/gamemodes/miniantags/bot_swarm/swarmer_event.dm +++ b/code/game/gamemodes/miniantags/bot_swarm/swarmer_event.dm @@ -1,26 +1,14 @@ /datum/event/spawn_swarmer - //name = "Sawrmer Spawn" - //one_shot = 1 startWhen = 3 //30 minutes announceWhen = 10 - /datum/event/spawn_swarmer/announce() if(prob(25)) //25% chance to announce it to the crew var/swarmer_report = "[command_name()] High-Priority Update" swarmer_report += "

Our long-range sensors have detected an odd signal emanating from your station's gateway. We recommend immediate investigation of your gateway, as something may have come \ through." - for(var/obj/machinery/computer/communications/C in machines) - if(! (C.stat & (BROKEN|NOPOWER) ) ) - var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( C.loc ) - P.name = "'Classified [command_name()] Update'" - P.info = swarmer_report - P.update_icon() - C.messagetitle.Add("Classified [command_name()] Update") - C.messagetext.Add(P.info) - command_announcement.Announce("A report has been downloaded and printed out at all communications consoles.", "Incoming Classified Message", 'sound/AI/commandreport.ogg') - - + print_command_report(swarmer_report, "Classified [command_name()] Update") + event_announcement.Announce("A report has been downloaded and printed out at all communications consoles.", "Incoming Classified Message", 'sound/AI/commandreport.ogg') /datum/event/spawn_swarmer/start() if(find_swarmer()) diff --git a/code/game/machinery/computer/atmos_control.dm b/code/game/machinery/computer/atmos_control.dm index 197008c40f7..0f555a1169b 100644 --- a/code/game/machinery/computer/atmos_control.dm +++ b/code/game/machinery/computer/atmos_control.dm @@ -25,7 +25,7 @@ return 1 ui_interact(user) -/obj/machinery/computer/atmoscontrol/emag_act(var/remaining_carges, var/mob/user) +/obj/machinery/computer/atmoscontrol/emag_act(mob/user) if(!emagged) user.visible_message("\The [user] does something \the [src], causing the screen to flash!",\ "You cause the screen to flash as you gain full control.",\ diff --git a/code/game/machinery/computer/buildandrepair.dm b/code/game/machinery/computer/buildandrepair.dm index 71aad1085ff..d3d7b8cf3d1 100644 --- a/code/game/machinery/computer/buildandrepair.dm +++ b/code/game/machinery/computer/buildandrepair.dm @@ -30,7 +30,12 @@ var/frame_desc = null var/contain_parts = 1 - +/obj/item/weapon/circuitboard/computer + board_type = "computer" + +/obj/item/weapon/circuitboard/machine + board_type = "machine" + /obj/item/weapon/circuitboard/message_monitor name = "Circuit board (Message Monitor)" build_path = /obj/machinery/computer/message_monitor diff --git a/code/game/machinery/computer/communications.dm b/code/game/machinery/computer/communications.dm index 8b838ceade5..6087bc68d08 100644 --- a/code/game/machinery/computer/communications.dm +++ b/code/game/machinery/computer/communications.dm @@ -53,6 +53,24 @@ to_chat(user, "Access denied.") return COMM_AUTHENTICATION_NONE +/obj/machinery/computer/communications/proc/change_security_level(var/new_level) + tmp_alertlevel = new_level + var/old_level = security_level + if(!tmp_alertlevel) tmp_alertlevel = SEC_LEVEL_GREEN + if(tmp_alertlevel < SEC_LEVEL_GREEN) tmp_alertlevel = SEC_LEVEL_GREEN + if(tmp_alertlevel > SEC_LEVEL_BLUE) tmp_alertlevel = SEC_LEVEL_BLUE //Cannot engage delta with this + set_security_level(tmp_alertlevel) + if(security_level != old_level) + //Only notify the admins if an actual change happened + log_game("[key_name(usr)] has changed the security level to [get_security_level()].") + message_admins("[key_name_admin(usr)] has changed the security level to [get_security_level()].") + switch(security_level) + if(SEC_LEVEL_GREEN) + feedback_inc("alert_comms_green",1) + if(SEC_LEVEL_BLUE) + feedback_inc("alert_comms_blue",1) + tmp_alertlevel = 0 + /obj/machinery/computer/communications/Topic(href, href_list) if(..(href, href_list)) return 1 @@ -100,35 +118,25 @@ if("newalertlevel") if(isAI(usr) || isrobot(usr)) to_chat(usr, "Firewalls prevent you from changing the alert level.") - nanomanager.update_uis(src) return 1 - tmp_alertlevel = text2num(href_list["level"]) + else if(usr.can_admin_interact()) + change_security_level(text2num(href_list["level"])) + return 1 + else if(!ishuman(usr)) + to_chat(usr, "Security measures prevent you from changing the alert level.") + return 1 + var/mob/living/carbon/human/L = usr var/obj/item/card = L.get_active_hand() - var/obj/item/weapon/card/id/I = (card && card.GetID())||L.wear_id||L.wear_pda + var/obj/item/weapon/card/id/I = (card && card.GetID()) || L.wear_id || L.wear_pda if(istype(I, /obj/item/device/pda)) var/obj/item/device/pda/pda = I I = pda.id if(I && istype(I)) if(access_captain in I.access) - var/old_level = security_level - if(!tmp_alertlevel) tmp_alertlevel = SEC_LEVEL_GREEN - if(tmp_alertlevel < SEC_LEVEL_GREEN) tmp_alertlevel = SEC_LEVEL_GREEN - if(tmp_alertlevel > SEC_LEVEL_BLUE) tmp_alertlevel = SEC_LEVEL_BLUE //Cannot engage delta with this - set_security_level(tmp_alertlevel) - if(security_level != old_level) - //Only notify the admins if an actual change happened - log_game("[key_name(usr)] has changed the security level to [get_security_level()].") - message_admins("[key_name_admin(usr)] has changed the security level to [get_security_level()].") - switch(security_level) - if(SEC_LEVEL_GREEN) - feedback_inc("alert_comms_green",1) - if(SEC_LEVEL_BLUE) - feedback_inc("alert_comms_blue",1) - tmp_alertlevel = 0 + change_security_level(text2num(href_list["level"])) else to_chat(usr, "You are not authorized to do this.") - tmp_alertlevel = 0 setMenuState(usr,COMM_SCREEN_MAIN) else to_chat(usr, "You need to swipe your ID.") @@ -172,24 +180,26 @@ setMenuState(usr,COMM_SCREEN_MAIN) if("messagelist") - src.currmsg = 0 + currmsg = 0 if(href_list["msgid"]) setCurrentMessage(usr, text2num(href_list["msgid"])) setMenuState(usr,COMM_SCREEN_MESSAGES) if("delmessage") if(href_list["msgid"]) - src.currmsg = text2num(href_list["msgid"]) + currmsg = text2num(href_list["msgid"]) var/response = alert("Are you sure you wish to delete this message?", "Confirm", "Yes", "No") if(response == "Yes") - if(src.currmsg) + if(currmsg) var/id = getCurrentMessage() - var/title = src.messagetitle[id] - var/text = src.messagetext[id] - src.messagetitle.Remove(title) - src.messagetext.Remove(text) - if(currmsg==id) currmsg=0 - if(aicurrmsg==id) aicurrmsg=0 + var/title = messagetitle[id] + var/text = messagetext[id] + messagetitle.Remove(title) + messagetext.Remove(text) + if(currmsg == id) + currmsg = 0 + if(aicurrmsg == id) + aicurrmsg = 0 setMenuState(usr,COMM_SCREEN_MESSAGES) if("status") @@ -336,7 +346,7 @@ /obj/machinery/computer/communications/ui_data(mob/user, ui_key = "main", datum/topic_state/state = default_state) var/data[0] - data["is_ai"] = isAI(user)||isrobot(user) + data["is_ai"] = isAI(user) || isrobot(user) data["menu_state"] = data["is_ai"] ? ai_menu_state : menu_state data["emagged"] = emagged data["authenticated"] = is_authenticated(user, 0) @@ -368,16 +378,15 @@ list("id" = SEC_LEVEL_BLUE, "name" = "Blue"), //SEC_LEVEL_RED = list("name"="Red"), ) - - var/msg_data[0] - for(var/i = 1; i <= src.messagetext.len; i++) - var/cur_msg[0] - cur_msg["title"] = messagetitle[i] - cur_msg["body"] = messagetext[i] - msg_data += list(cur_msg) + + var/list/msg_data = list() + for(var/i = 1; i <= messagetext.len; i++) + msg_data.Add(list(list("title" = messagetitle[i], "body" = messagetext[i], "id" = i))) data["messages"] = msg_data - data["current_message"] = data["is_ai"] ? aicurrmsg : currmsg + if((data["is_ai"] && aicurrmsg) || (!data["is_ai"] && currmsg)) + data["current_message"] = data["is_ai"] ? messagetext[aicurrmsg] : messagetext[currmsg] + data["current_message_title"] = data["is_ai"] ? messagetitle[aicurrmsg] : messagetitle[currmsg] data["lastCallLoc"] = shuttle_master.emergencyLastCallLoc ? format_text(shuttle_master.emergencyLastCallLoc.name) : null @@ -403,9 +412,9 @@ /obj/machinery/computer/communications/proc/setCurrentMessage(var/mob/user,var/value) if(isAI(user) || isrobot(user)) - aicurrmsg=value + aicurrmsg = value else - currmsg=value + currmsg = value /obj/machinery/computer/communications/proc/getCurrentMessage(var/mob/user) if(isAI(user) || isrobot(user)) @@ -540,3 +549,13 @@ message_admins("All the AI's, communication consoles and boards are destroyed. Shuttle called.", 1) return ..() + +/proc/print_command_report(text = "", title = "Central Command Update") + for(var/obj/machinery/computer/communications/C in machines) + if(!(C.stat & (BROKEN|NOPOWER)) && is_station_contact(C.z)) + var/obj/item/weapon/paper/P = new /obj/item/weapon/paper(C.loc) + P.name = "paper- '[title]'" + P.info = text + C.messagetitle.Add("[title]") + C.messagetext.Add(text) + P.update_icon() \ No newline at end of file diff --git a/code/modules/admin/admin_verbs.dm b/code/modules/admin/admin_verbs.dm index ac419bcb592..e7ddc633aee 100644 --- a/code/modules/admin/admin_verbs.dm +++ b/code/modules/admin/admin_verbs.dm @@ -110,7 +110,8 @@ var/list/admin_verbs_event = list( /client/proc/response_team, // Response Teams admin verb /client/proc/cmd_admin_create_centcom_report, /client/proc/fax_panel, - /client/proc/event_manager_panel + /client/proc/event_manager_panel, + /client/proc/modify_goals ) var/list/admin_verbs_spawn = list( diff --git a/code/modules/admin/topic.dm b/code/modules/admin/topic.dm index c8a9bb78926..fde15986d0b 100644 --- a/code/modules/admin/topic.dm +++ b/code/modules/admin/topic.dm @@ -3115,6 +3115,27 @@ error_viewer.showTo(usr, locate(href_list["viewruntime_backto"]), href_list["viewruntime_linear"]) else error_viewer.showTo(usr, null, href_list["viewruntime_linear"]) + + else if(href_list["add_station_goal"]) + if(!check_rights(R_EVENT)) + return + var/list/type_choices = typesof(/datum/station_goal) + var/picked = input("Choose goal type") in type_choices|null + if(!picked) + return + var/datum/station_goal/G = new picked() + if(picked == /datum/station_goal) + var/newname = input("Enter goal name:") as text|null + if(!newname) + return + G.name = newname + var/description = input("Enter [command_name()] message contents:") as message|null + if(!description) + return + G.report_message = description + message_admins("[key_name_admin(usr)] created \"[G.name]\" station goal.") + ticker.mode.station_goals += G + modify_goals() /proc/admin_jump_link(var/atom/target) if(!target) return diff --git a/code/modules/admin/verbs/randomverbs.dm b/code/modules/admin/verbs/randomverbs.dm index 79ee34fb635..6b4660a8a37 100644 --- a/code/modules/admin/verbs/randomverbs.dm +++ b/code/modules/admin/verbs/randomverbs.dm @@ -561,36 +561,22 @@ Traitors and the like can also be revived with the previous role mostly intact. if("Yes") communications_announcement.Announce(input, customname, , , , from); if("No") - to_chat(world, "\red [from] available at all communications consoles.") - - for(var/obj/machinery/computer/communications/C in machines) - if(! (C.stat & (BROKEN|NOPOWER) ) ) - var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( C.loc ) - P.name = "[from]" - P.info = input - P.update_icon() - C.messagetitle.Add("[from]") - C.messagetext.Add(P.info) + to_chat(world, "[from] available at all communications consoles.") + print_command_report(input, from) if(type == "Centcom Report") if(!customname) customname = "Nanotrasen Update" - switch(alert("Should this be announced to the general population?",,"Yes","No")) + var/announce = alert("Should this be announced to the general population?",,"Yes","No") + switch(announce) if("Yes") command_announcement.Announce(input, customname); if("No") - to_chat(world, "\red New Nanotrasen Update available at all communication consoles.") + to_chat(world, "New Nanotrasen Update available at all communication consoles.") - for(var/obj/machinery/computer/communications/C in machines) - if(! (C.stat & (BROKEN|NOPOWER) ) ) - var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( C.loc ) - P.name = "'[command_name()] Update.'" - P.info = input - P.update_icon() - C.messagetitle.Add("[command_name()] Update") - C.messagetext.Add(P.info) + print_command_report(input, "[announce == "No" ? "Classified " : ""][command_name()] Update") // world << sound('sound/AI/commandreport.ogg') log_admin("[key_name(src)] has created a communications report: [input]") @@ -892,7 +878,6 @@ Traitors and the like can also be revived with the previous role mostly intact. message_admins("[key_name_admin(usr)] blanked all telecomms scripts.") feedback_add_details("admin_verb","RAT") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc! - /client/proc/toggle_ert_calling() set category = "Event" set name = "Toggle ERT" @@ -911,3 +896,19 @@ Traitors and the like can also be revived with the previous role mostly intact. to_chat(usr, "\red ERT has been Disabled.") log_admin("Admin [key_name(src)] has disabled ERT calling.") message_admins("Admin [key_name_admin(usr)] has disabled ERT calling.", 1) + +/client/proc/modify_goals() + set category = "Event" + set name = "Modify Station Goals" + + if(!check_rights(R_EVENT)) + return + + holder.modify_goals() + +/datum/admins/proc/modify_goals() + var/dat = "" + for(var/datum/station_goal/S in ticker.mode.station_goals) + dat += "[S.name] - Announce | Remove
" + dat += "
Add New Goal" + usr << browse(dat, "window=goals;size=400x400") \ No newline at end of file diff --git a/code/modules/awaymissions/bluespaceartillery.dm b/code/modules/awaymissions/bluespaceartillery.dm deleted file mode 100644 index 1da3d3bfc55..00000000000 --- a/code/modules/awaymissions/bluespaceartillery.dm +++ /dev/null @@ -1,79 +0,0 @@ -/obj/machinery/computer/artillerycontrol - name = "bluespace artillery control" - icon_screen = "accelerator" - icon_keyboard = "accelerator_key" - icon_state = "computer-wires" - req_access = list(access_cent_commander) - var/last_fire = 0 - var/reload_cooldown = 180 // 3 minute cooldown - var/area/targetarea - - light_color = LIGHT_COLOR_LIGHTBLUE - -/obj/machinery/computer/artillerycontrol/attack_ai(user as mob) - to_chat(user, "Access denied.") - return - -/obj/machinery/computer/artillerycontrol/attack_hand(user as mob) - ui_interact(user) - -/obj/machinery/computer/artillerycontrol/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) - ui = nanomanager.try_update_ui(user, src, ui_key, ui, force_open) - if(!ui) - ui = new(user, src, ui_key, "bluespace_artillery.tmpl", "Bluespace Control", 400, 260) - ui.open() - ui.set_auto_update(1) - -/obj/machinery/computer/artillerycontrol/ui_data(mob/user, ui_key = "main", datum/topic_state/state = default_state) - var/data[0] - - var/time_to_wait = round(reload_cooldown - ((world.time / 10) - last_fire), 1) - var/mins = round(time_to_wait / 60) - var/seconds = time_to_wait - (60*mins) - data["reloadtime_mins"] = mins - data["reloadtime_secs"] = (seconds < 10) ? "0[seconds]" : seconds - if(targetarea) - var/areaname = sanitize(targetarea.name) - data["target"] = "Locked on to [areaname]" - else - data["target"] = "No Lock" - - return data - -/obj/machinery/computer/artillerycontrol/Topic(href, href_list) - if(..()) - return 1 - - if(href_list["area"]) - var/A - A = input("Select the target area.", "Select Area", A) in ghostteleportlocs|null - var/area/thearea = ghostteleportlocs[A] - if(..() || !istype(thearea)) - return - - targetarea = thearea - - if(href_list["fire"]) - var/delta = (world.time / 10) - last_fire - if(reload_cooldown > delta) - return 1 - - event_announcement.Announce("Bluespace artillery fire detected. Brace for impact.") - message_admins("[key_name_admin(usr)] has launched an artillery strike.", 1) - var/list/L = list() - for(var/turf/T in get_area_turfs(targetarea.type)) - L += T - var/loc = pick(L) - explosion(loc,2,5,11) - last_fire = world.time / 10 - - nanomanager.update_uis(src) - -/obj/structure/artilleryplaceholder - name = "artillery" - icon = 'icons/obj/machines/artillery.dmi' - anchored = 1 - density = 1 - -/obj/structure/artilleryplaceholder/decorative - density = 0 diff --git a/code/modules/mob/living/carbon/human/human_defense.dm b/code/modules/mob/living/carbon/human/human_defense.dm index 65361960042..7685e5ab898 100644 --- a/code/modules/mob/living/carbon/human/human_defense.dm +++ b/code/modules/mob/living/carbon/human/human_defense.dm @@ -86,6 +86,7 @@ emp_act for(var/obj/item/organ/external/organ in organs) armorval += getarmor_organ(organ, type) organnum++ + return (armorval/max(organnum, 1)) @@ -99,7 +100,8 @@ emp_act if(bp && istype(bp ,/obj/item/clothing)) var/obj/item/clothing/C = bp if(C.body_parts_covered & def_zone.body_part) - protection += C.armor[type] + protection += C.armor[type] + return protection //this proc returns the Siemens coefficient of electrical resistivity for a particular external organ. diff --git a/code/modules/mob/living/carbon/human/life.dm b/code/modules/mob/living/carbon/human/life.dm index 8448c786302..b2e609c92f2 100644 --- a/code/modules/mob/living/carbon/human/life.dm +++ b/code/modules/mob/living/carbon/human/life.dm @@ -171,7 +171,7 @@ if(gene.is_active(src)) speech_problem_flag = 1 gene.OnMobLife(src) - if(gene_stability < GENETIC_DAMAGE_STAGE_1) + if(!ignore_gene_stability && gene_stability < GENETIC_DAMAGE_STAGE_1) var/instability = DEFAULT_GENE_STABILITY - gene_stability if(prob(instability * 0.1)) adjustFireLoss(min(5, instability * 0.67)) diff --git a/code/modules/mob/living/living_defines.dm b/code/modules/mob/living/living_defines.dm index e1488648731..23b7abe06d3 100644 --- a/code/modules/mob/living/living_defines.dm +++ b/code/modules/mob/living/living_defines.dm @@ -52,6 +52,7 @@ var/list/surgeries = list() //a list of surgery datums. generally empty, they're added when the player wants them. var/gene_stability = DEFAULT_GENE_STABILITY + var/ignore_gene_stability = 0 var/obj/effect/proc_holder/ranged_ability //Any ranged ability the mob has, as a click override diff --git a/code/modules/shuttle/supply.dm b/code/modules/shuttle/supply.dm index ff799fd45c8..5e57fb4eff9 100644 --- a/code/modules/shuttle/supply.dm +++ b/code/modules/shuttle/supply.dm @@ -446,7 +446,7 @@ var/packs_list[0] for(var/set_name in shuttle_master.supply_packs) var/datum/supply_packs/pack = shuttle_master.supply_packs[set_name] - if(!pack.contraband && !pack.hidden && pack.group == cat) + if(!pack.contraband && !pack.hidden && !pack.special && pack.group == cat) // 0/1 after the pack name (set_name) is a boolean for ordering multiple crates packs_list.Add(list(list("name" = pack.name, "amount" = pack.amount, "cost" = pack.cost, "command1" = list("doorder" = "[set_name]0"), "command2" = list("doorder" = "[set_name]1"), "command3" = list("contents" = set_name)))) @@ -595,7 +595,7 @@ var/packs_list[0] for(var/set_name in shuttle_master.supply_packs) var/datum/supply_packs/pack = shuttle_master.supply_packs[set_name] - if((pack.hidden && src.hacked) || (pack.contraband && src.can_order_contraband) || (!pack.contraband && !pack.hidden)) + if((pack.hidden && hacked) || (pack.contraband && can_order_contraband) || (pack.special && pack.special_enabled) || (!pack.contraband && !pack.hidden && !pack.special)) if(pack.group == cat) // 0/1 after the pack name (set_name) is a boolean for ordering multiple crates packs_list.Add(list(list("name" = pack.name, "amount" = pack.amount, "cost" = pack.cost, "command1" = list("doorder" = "[set_name]0"), "command2" = list("doorder" = "[set_name]1"), "command3" = list("contents" = set_name)))) diff --git a/code/modules/station_goals/bsa.dm b/code/modules/station_goals/bsa.dm new file mode 100644 index 00000000000..6697aa0af26 --- /dev/null +++ b/code/modules/station_goals/bsa.dm @@ -0,0 +1,408 @@ +// Crew has to build a bluespace cannon +// Cargo orders part for high price +// Requires high amount of power +// Requires high level stock parts +/datum/station_goal/bluespace_cannon + name = "Bluespace Artillery" + +/datum/station_goal/bluespace_cannon/get_report() + return {"Bluespace Artillery position construction
+ Our military presence is inadequate in your sector. We need you to construct BSA-[rand(1,99)] Artillery position aboard your station. +

+ Its base parts should be available for shipping by your cargo shuttle. +
+ -Nanotrasen Naval Command"} + +/datum/station_goal/bluespace_cannon/on_report() + //Unlock BSA parts + var/datum/supply_packs/misc/bsa/P = shuttle_master.supply_packs["[/datum/supply_packs/misc/bsa]"] + P.special_enabled = TRUE + +/datum/station_goal/bluespace_cannon/check_completion() + if(..()) + return TRUE + var/obj/machinery/bsa/full/B = locate() + if(B && !B.stat && is_station_contact(B.z)) + return TRUE + return FALSE + +/obj/machinery/bsa + icon = 'icons/obj/machines/particle_accelerator3.dmi' + density = 1 + anchored = 1 + +/obj/machinery/bsa/back + name = "Bluespace Artillery Generator" + desc = "Generates cannon pulse. Needs to be linked with a fusor. " + icon_state = "power_box" + +/obj/machinery/bsa/back/attackby(obj/item/weapon/W, mob/user, params) + if(istype(W, /obj/item/device/multitool)) + var/obj/item/device/multitool/M = W + M.buffer = src + to_chat(user, "You store linkage information in [W]'s buffer.") + else if(istype(W, /obj/item/weapon/wrench)) + default_unfasten_wrench(user, W, 10) + return TRUE + else + return ..() + +/obj/machinery/bsa/front + name = "Bluespace Artillery Bore" + desc = "Do not stand in front of cannon during operation. Needs to be linked with a fusor." + icon_state = "emitter_center" + +/obj/machinery/bsa/front/attackby(obj/item/weapon/W, mob/user, params) + if(istype(W, /obj/item/device/multitool)) + var/obj/item/device/multitool/M = W + M.buffer = src + to_chat(user, "You store linkage information in [W]'s buffer.") + else if(istype(W, /obj/item/weapon/wrench)) + default_unfasten_wrench(user, W, 10) + return TRUE + else + return ..() + +/obj/machinery/bsa/middle + name = "Bluespace Artillery Fusor" + desc = "Contents classifed by Nanotrasen Naval Command. Needs to be linked with the other BSA parts using multitool." + icon_state = "fuel_chamber" + var/obj/machinery/bsa/back/back + var/obj/machinery/bsa/front/front + +/obj/machinery/bsa/middle/attackby(obj/item/weapon/W, mob/user, params) + if(istype(W, /obj/item/device/multitool)) + var/obj/item/device/multitool/M = W + if(M.buffer) + if(istype(M.buffer,/obj/machinery/bsa/back)) + back = M.buffer + M.buffer = null + to_chat(user, "You link [src] with [back].") + else if(istype(M.buffer,/obj/machinery/bsa/front)) + front = M.buffer + M.buffer = null + to_chat(user, "You link [src] with [front].") + else if(istype(W, /obj/item/weapon/wrench)) + default_unfasten_wrench(user, W, 10) + return TRUE + else + return ..() + +/obj/machinery/bsa/middle/proc/check_completion() + if(!front || !back) + return "No linked parts detected!" + if(!front.anchored || !back.anchored || !anchored) + return "Linked parts unwrenched!" + if(front.y != y || back.y != y || !(front.x > x && back.x < x || front.x < x && back.x > x) || front.z != z || back.z != z) + return "Parts misaligned!" + if(!has_space()) + return "Not enough free space!" + +/obj/machinery/bsa/middle/proc/has_space() + var/cannon_dir = get_cannon_direction() + var/x_min + var/x_max + switch(cannon_dir) + if(EAST) + x_min = x - 4 //replace with defines later + x_max = x + 6 + if(WEST) + x_min = x + 4 + x_max = x - 6 + + for(var/turf/T in block(locate(x_min,y-1,z),locate(x_max,y+1,z))) + if(T.density || isspaceturf(T)) + return FALSE + return TRUE + +/obj/machinery/bsa/middle/proc/get_cannon_direction() + if(front.x > x && back.x < x) + return EAST + else if(front.x < x && back.x > x) + return WEST + +/obj/machinery/bsa/full + name = "Bluespace Artillery" + desc = "Long range bluespace artillery." + icon = 'icons/obj/lavaland/cannon.dmi' + icon_state = "cannon_west" + + var/obj/machinery/computer/bsa_control/controller + var/cannon_direction = WEST + var/static/image/top_layer = null + var/ex_power = 3 + var/power_used_per_shot = 2000000 //enough to kil standard apc - todo : make this use wires instead and scale explosion power with it + var/last_fire_time = 0 // The time at which the gun was last fired + var/reload_cooldown = 600 // The gun's cooldown + + pixel_y = -32 + pixel_x = -192 + bound_width = 352 + bound_x = -192 + +/obj/machinery/bsa/full/Destroy() + if(controller && controller.cannon == src) + controller.cannon = null + controller = null + return ..() + +/obj/machinery/bsa/full/east + icon_state = "cannon_east" + cannon_direction = EAST + +/obj/machinery/bsa/full/admin + power_used_per_shot = 0 + reload_cooldown = 100 + +/obj/machinery/bsa/full/admin/east + icon_state = "cannon_east" + cannon_direction = EAST + +/obj/machinery/bsa/full/proc/get_front_turf() + switch(dir) + if(WEST) + return locate(x - 6,y,z) + if(EAST) + return locate(x + 4,y,z) + return get_turf(src) + +/obj/machinery/bsa/full/proc/get_back_turf() + switch(dir) + if(WEST) + return locate(x + 4,y,z) + if(EAST) + return locate(x - 6,y,z) + return get_turf(src) + +/obj/machinery/bsa/full/proc/get_target_turf() + switch(dir) + if(WEST) + return locate(1,y,z) + if(EAST) + return locate(world.maxx,y,z) + return get_turf(src) + +/obj/machinery/bsa/full/New(loc, direction) + ..() + + if(direction) + cannon_direction = direction + + switch(cannon_direction) + if(WEST) + dir = WEST + pixel_x = -192 + top_layer = image("icons/obj/lavaland/orbital_cannon.dmi", "top_west") + top_layer.layer = 4.1 + icon_state = "cannon_west" + if(EAST) + dir = EAST + top_layer = image("icons/obj/lavaland/orbital_cannon.dmi", "top_east") + top_layer.layer = 4.1 + icon_state = "cannon_east" + overlays += top_layer + reload() + +/obj/machinery/bsa/full/proc/fire(mob/user, turf/bullseye) + var/turf/point = get_front_turf() + for(var/turf/T in getline(get_step(point,dir),get_target_turf())) + T.ex_act(1) + for(var/atom/A in T) + A.ex_act(1) + + point.Beam(get_target_turf(), icon_state = "bsa_beam", time = 50, maxdistance = world.maxx, beam_type = /obj/effect/ebeam/deadly) //ZZZAP + playsound(src, 'sound/machines/bsa_fire.ogg', 100, 1) + + message_admins("[key_name_admin(user)] has launched an artillery strike.") + explosion(bullseye,ex_power,ex_power*2,ex_power*4) + + reload() + +/obj/machinery/bsa/full/proc/reload() + use_power(power_used_per_shot) + last_fire_time = world.time / 10 + +/obj/item/weapon/circuitboard/machine/bsa/back + name = "Bluespace Artillery Generator (Machine Board)" + build_path = /obj/machinery/bsa/back + origin_tech = "engineering=2;combat=2;bluespace=2" //No freebies! + req_components = list( + /obj/item/weapon/stock_parts/capacitor/quadratic = 5, + /obj/item/stack/cable_coil = 2) + +/obj/item/weapon/circuitboard/machine/bsa/middle + name = "Bluespace Artillery Fusor (Machine Board)" + build_path = /obj/machinery/bsa/middle + origin_tech = "engineering=2;combat=2;bluespace=2" + req_components = list( + /obj/item/weapon/ore/bluespace_crystal = 20, + /obj/item/stack/cable_coil = 2) + +/obj/item/weapon/circuitboard/machine/bsa/front + name = "Bluespace Artillery Bore (Machine Board)" + build_path = /obj/machinery/bsa/front + origin_tech = "engineering=2;combat=2;bluespace=2" + req_components = list( + /obj/item/weapon/stock_parts/manipulator/femto = 5, + /obj/item/stack/cable_coil = 2) + +/obj/item/weapon/circuitboard/computer/bsa_control + name = "Bluespace Artillery Controls (Computer Board)" + build_path = /obj/machinery/computer/bsa_control + origin_tech = "engineering=2;combat=2;bluespace=2" + +/obj/machinery/computer/bsa_control + name = "Bluespace Artillery Control" + var/obj/machinery/bsa/full/cannon + var/notice + var/target + use_power = 0 + circuit = /obj/item/weapon/circuitboard/computer/bsa_control + icon = 'icons/obj/machines/particle_accelerator3.dmi' + icon_state = "control_boxp" + var/icon_state_broken = "control_box" + var/icon_state_nopower = "control_boxw" + var/icon_state_reloading = "control_boxp1" + var/icon_state_active = "control_boxp0" + layer = 3.1 // Just above the cannon sprite + + var/area_aim = FALSE //should also show areas for targeting + var/target_all_areas = FALSE //allows all areas (including admin areas) to be targeted + +/obj/machinery/computer/bsa_control/admin + area_aim = TRUE + target_all_areas = TRUE + +/obj/machinery/computer/bsa_control/admin/initialize() + ..() + if(!cannon) + cannon = deploy() + +/obj/machinery/computer/bsa_control/Destroy() + if(cannon && cannon.controller == src) + cannon.controller = null + cannon = null + return ..() + +/obj/machinery/computer/bsa_control/process() + ..() + update_icon() + +/obj/machinery/computer/bsa_control/update_icon() + if(stat & BROKEN) + icon_state = icon_state_broken + else if(stat & NOPOWER) + icon_state = icon_state_nopower + else if(cannon && (cannon.last_fire_time + cannon.reload_cooldown) > (world.time / 10)) + icon_state = icon_state_reloading + else if(cannon) + icon_state = icon_state_active + else + icon_state = initial(icon_state) + +/obj/machinery/computer/bsa_control/attack_hand(mob/user) + if(..()) + return 1 + ui_interact(user) + +/obj/machinery/computer/bsa_control/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + ui = nanomanager.try_update_ui(user, src, ui_key, ui, force_open) + if(!ui) + ui = new(user, src, ui_key, "bsa.tmpl", name, 400, 305) + ui.open() + ui.set_auto_update(1) + +/obj/machinery/computer/bsa_control/ui_data(mob/user, ui_key = "main", datum/topic_state/state = physical_state) + var/list/data = list() + data["connected"] = cannon + data["notice"] = notice + if(target) + data["target"] = get_target_name() + + if(cannon) + var/reload_cooldown = cannon.reload_cooldown + var/last_fire_time = cannon.last_fire_time + var/time_to_wait = max(0, round(reload_cooldown - ((world.time / 10) - last_fire_time))) + var/minutes = max(0, round(time_to_wait / 60)) + var/seconds = max(0, time_to_wait - (60 * minutes)) + + data["reloadtime_mins"] = minutes + data["reloadtime_secs"] = (seconds < 10) ? "0[seconds]" : seconds + data["ready"] = minutes == 0 && seconds == 0 + else + data["ready"] = FALSE + + return data + +/obj/machinery/computer/bsa_control/Topic(href, href_list) + if(..()) + return 1 + + if(href_list["build"]) + cannon = deploy() + . = TRUE + else if(href_list["fire"]) + fire(usr) + . = TRUE + else if(href_list["recalibrate"]) + calibrate(usr) + . = TRUE + update_icon() + +/obj/machinery/computer/bsa_control/proc/calibrate(mob/user) + var/list/gps_locators = list() + for(var/obj/item/device/gps/G in GPS_list) //nulls on the list somehow + gps_locators[G.gpstag] = G + + var/list/options = gps_locators + if(area_aim) + options += target_all_areas ? ghostteleportlocs : teleportlocs + var/V = input(user,"Select target", "Select target",null) in options|null + target = options[V] + +/obj/machinery/computer/bsa_control/proc/get_target_name() + if(istype(target,/area)) + var/area/A = target + return A.name + else if(istype(target,/obj/item/device/gps)) + var/obj/item/device/gps/G = target + return G.gpstag + +/obj/machinery/computer/bsa_control/proc/get_impact_turf() + if(istype(target,/area)) + return pick(get_area_turfs(target)) + else if(istype(target,/obj/item/device/gps)) + return get_turf(target) + +/obj/machinery/computer/bsa_control/proc/fire(mob/user) + if(!cannon || !target) + return + if(cannon.stat) + notice = "Cannon unpowered!" + return + notice = null + cannon.fire(user, get_impact_turf()) + +/obj/machinery/computer/bsa_control/proc/deploy() + var/obj/machinery/bsa/full/prebuilt = locate() in range(7, src) //In case of adminspawn + if(prebuilt) + prebuilt.controller = src + return prebuilt + + var/obj/machinery/bsa/middle/centerpiece = locate() in range(7, src) + if(!centerpiece) + notice = "No BSA parts detected nearby." + return null + notice = centerpiece.check_completion() + if(notice) + return null + //Totally nanite construction system not an immersion breaking spawning + var/datum/effect/system/harmless_smoke_spread/s = new /datum/effect/system/harmless_smoke_spread() + s.set_up(4, 0, get_turf(centerpiece)) + s.start() + var/obj/machinery/bsa/full/cannon = new(get_turf(centerpiece),centerpiece.get_cannon_direction()) + cannon.controller = src + qdel(centerpiece.front) + qdel(centerpiece.back) + qdel(centerpiece) + return cannon diff --git a/code/modules/station_goals/dna_vault.dm b/code/modules/station_goals/dna_vault.dm new file mode 100644 index 00000000000..26d00e6360d --- /dev/null +++ b/code/modules/station_goals/dna_vault.dm @@ -0,0 +1,301 @@ +//Crew has to create dna vault +// Cargo can order DNA samplers + DNA vault boards +// DNA vault requires x animals ,y plants, z human dna +// DNA vaults require high tier stock parts and cold +// After completion each crewmember can receive single upgrade chosen out of 2 for the mob. +#define VAULT_SPACEIMMUNE "Space Immunity" +#define VAULT_XRAY "X-Ray Vision" +#define VAULT_TELEKINESIS "Telekinesis" +#define VAULT_PSYCHIC "Psychic Powers" +#define VAULT_SPEED "Speediness" + +/datum/station_goal/dna_vault + name = "DNA Vault" + var/animal_count + var/human_count + var/plant_count + +/datum/station_goal/dna_vault/New() + ..() + animal_count = rand(15,20) //might be too few given ~15 roundstart stationside ones + human_count = rand(round(0.75 * ticker.mode.num_players_started()), ticker.mode.num_players_started()) // 75%+ roundstart population. + var/non_standard_plants = non_standard_plants_count() + plant_count = rand(round(0.5 * non_standard_plants),round(0.7 * non_standard_plants)) + +/datum/station_goal/dna_vault/proc/non_standard_plants_count() + . = 0 + for(var/T in subtypesof(/obj/item/seeds)) //put a cache if it's used anywhere else + var/obj/item/seeds/S = T + if(initial(S.rarity) > 0) + .++ + +/datum/station_goal/dna_vault/get_report() + return {"DNA Vault construction
+ Our long term prediction systems say there's 99% chance of system-wide cataclysm in near future. As such, we need you to construct a DNA Vault aboard your station. +

+ The DNA Vault needs to contain samples of: + + The base vault parts should be available for shipping by your cargo shuttle."} + +/datum/station_goal/dna_vault/on_report() + var/datum/supply_packs/P = shuttle_master.supply_packs["[/datum/supply_packs/misc/dna_vault]"] + P.special_enabled = TRUE + + P = shuttle_master.supply_packs["[/datum/supply_packs/misc/dna_probes]"] + P.special_enabled = TRUE + +/datum/station_goal/dna_vault/check_completion() + if(..()) + return TRUE + for(var/obj/machinery/dna_vault/V in machines) + if(V.animals.len >= animal_count && V.plants.len >= plant_count && V.dna.len >= human_count && is_station_contact(V.z)) + return TRUE + return FALSE + +/obj/item/device/dna_probe + name = "DNA Sampler" + desc = "Can be used to take chemical and genetic samples of pretty much anything." + icon = 'icons/obj/hypo.dmi' + item_state = "hypo" + icon_state = "hypo" + flags = NOBLUDGEON + var/list/animals = list() + var/list/plants = list() + var/list/dna = list() + +/obj/item/device/dna_probe/proc/clear_data() + animals = list() + plants = list() + dna = list() + +var/list/non_simple_animals = typecacheof(list(/mob/living/carbon/human/monkey,/mob/living/carbon/alien)) + +/obj/item/device/dna_probe/afterattack(atom/target, mob/user, proximity) + ..() + if(!proximity || !target) + return + //tray plants + if(istype(target,/obj/machinery/hydroponics)) + var/obj/machinery/hydroponics/H = target + if(!H.myseed) + return + if(!H.harvest)// So it's bit harder. + to_chat(user, "Plants needs to be ready to harvest to perform full data scan.") //Because space dna is actually magic + return + if(plants[H.myseed.type]) + to_chat(user, "Plant data already present in local storage.") + return + plants[H.myseed.type] = 1 + to_chat(user, "Plant data added to local storage.") + + //animals + if(isanimal(target) || is_type_in_typecache(target, non_simple_animals)) + if(isanimal(target)) + var/mob/living/simple_animal/A = target + if(!A.healable)//simple approximation of being animal not a robot or similar + to_chat(user, "No compatible DNA detected") + return + if(animals[target.type]) + to_chat(user, "Animal data already present in local storage.") + return + animals[target.type] = 1 + to_chat(user, "Animal data added to local storage.") + + //humans + if(ishuman(target)) + var/mob/living/carbon/human/H = target + if(dna[H.dna.uni_identity]) + to_chat(user, "Humanoid data already present in local storage.") + return + dna[H.dna.uni_identity] = 1 + to_chat(user, "Humanoid data added to local storage.") + + +/obj/item/weapon/circuitboard/machine/dna_vault + name = "DNA Vault (Machine Board)" + build_path = /obj/machinery/dna_vault + origin_tech = "engineering=2;combat=2;bluespace=2" //No freebies! + req_components = list( + /obj/item/weapon/stock_parts/capacitor/quadratic = 5, + /obj/item/stack/cable_coil = 2) + +/obj/structure/filler + name = "big machinery part" + density = 1 + anchored = 1 + invisibility = 101 + var/obj/machinery/parent + +/obj/structure/filler/ex_act() + return + +/obj/machinery/dna_vault + name = "DNA Vault" + desc = "Break glass in case of apocalypse." + icon = 'icons/obj/machines/dna_vault.dmi' + icon_state = "vault" + density = 1 + anchored = 1 + idle_power_usage = 5000 + pixel_x = -32 + pixel_y = -64 + luminosity = 1 + + //High defaults so it's not completed automatically if there's no station goal + var/animals_max = 100 + var/plants_max = 100 + var/dna_max = 100 + var/list/animals = list() + var/list/plants = list() + var/list/dna = list() + + var/completed = FALSE + var/list/power_lottery = list() + + var/list/obj/structure/fillers = list() + +/obj/machinery/dna_vault/New() + //TODO: Replace this,bsa and gravgen with some big machinery datum + var/list/occupied = list() + for(var/direct in list(EAST,WEST,SOUTHEAST,SOUTHWEST)) + occupied += get_step(src,direct) + occupied += locate(x+1,y-2,z) + occupied += locate(x-1,y-2,z) + + for(var/T in occupied) + var/obj/structure/filler/F = new(T) + F.parent = src + fillers += F + + if(ticker.mode) + for(var/datum/station_goal/dna_vault/G in ticker.mode.station_goals) + animals_max = G.animal_count + plants_max = G.plant_count + dna_max = G.human_count + break + +/obj/machinery/dna_vault/Destroy() + for(var/V in fillers) + var/obj/structure/filler/filler = V + filler.parent = null + qdel(filler) + . = ..() + +/obj/machinery/dna_vault/attack_ghost(mob/user) + if(stat & (BROKEN|MAINT)) + return + return ui_interact(user) + +/obj/machinery/dna_vault/attack_hand(mob/user) + if(..()) + return 1 + ui_interact(user) + +/obj/machinery/dna_vault/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + ui = nanomanager.try_update_ui(user, src, ui_key, ui, force_open) + if(!ui) + roll_powers(user) + ui = new(user, src, ui_key, "dna_vault.tmpl", name, 550, 400) + ui.open() + +/obj/machinery/dna_vault/proc/roll_powers(mob/user) + if(user in power_lottery) + return + var/list/L = list() + var/list/possible_powers = list(VAULT_SPACEIMMUNE,VAULT_XRAY,VAULT_TELEKINESIS,VAULT_PSYCHIC,VAULT_SPEED) + L += pick_n_take(possible_powers) + L += pick_n_take(possible_powers) + power_lottery[user] = L + +/obj/machinery/dna_vault/ui_data(mob/user, ui_key = "main", datum/topic_state/state = physical_state) //TODO Make it % bars maybe + var/list/data = list() + data["plants"] = plants.len + data["plants_max"] = plants_max + data["animals"] = animals.len + data["animals_max"] = animals_max + data["dna"] = dna.len + data["dna_max"] = dna_max + data["completed"] = completed + data["used"] = TRUE + data["choiceA"] = "" + data["choiceB"] = "" + if(user && completed) + var/list/L = power_lottery[user] + if(L && L.len) + data["used"] = FALSE + data["choiceA"] = L[1] + data["choiceB"] = L[2] + return data + +/obj/machinery/dna_vault/Topic(href, href_list) + if(..()) + return 1 + + if(href_list["gene"]) + upgrade(usr,href_list["choice"]) + . = TRUE + +/obj/machinery/dna_vault/proc/check_goal() + if(plants.len >= plants_max && animals.len >= animals_max && dna.len >= dna_max) + completed = TRUE + +/obj/machinery/dna_vault/attackby(obj/item/I, mob/user, params) + if(istype(I, /obj/item/device/dna_probe)) + var/obj/item/device/dna_probe/P = I + var/uploaded = 0 + for(var/plant in P.plants) + if(!plants[plant]) + uploaded++ + plants[plant] = 1 + for(var/animal in P.animals) + if(!animals[animal]) + uploaded++ + animals[animal] = 1 + for(var/ui in P.dna) + if(!dna[ui]) + uploaded++ + dna[ui] = 1 + check_goal() + to_chat(user, "[uploaded] new datapoints uploaded.") + else + return ..() + +/obj/machinery/dna_vault/proc/upgrade(mob/living/carbon/human/H, upgrade_type) + if(!(upgrade_type in power_lottery[H])) + return + if(!completed) + return + if(!H.ignore_gene_stability) + to_chat(H, "[src] stabilizes your genes, granting you the ability to have multiple powers.") + H.ignore_gene_stability = 1 + switch(upgrade_type) + if(VAULT_SPACEIMMUNE) + to_chat(H, "You suddenly don't feel the need to breathe anymore. You also don't feel any cold anymore.") + grant_power(H, NOBREATHBLOCK, NO_BREATH) + grant_power(H, FIREBLOCK, RESIST_COLD) + if(VAULT_XRAY) + to_chat(H, "You can suddenly see through walls.") + grant_power(H, XRAYBLOCK, XRAY) + if(VAULT_TELEKINESIS) + to_chat(H, "You gain the ability to control objects from a distance.") + grant_power(H, TELEBLOCK, TK) + if(VAULT_PSYCHIC) + to_chat(H, "Your mind expands, giving you psychic powers.") + grant_power(H, REMOTETALKBLOCK, REMOTE_TALK) + grant_power(H, REMOTEVIEWBLOCK, REMOTE_VIEW) + grant_power(H, EMPATHBLOCK, EMPATH) + grant_power(H, PSYRESISTBLOCK, PSY_RESIST) + if(VAULT_SPEED) + to_chat(H, "You feel very fast and agile.") + grant_power(H, JUMPBLOCK, JUMPY) + grant_power(H, INCREASERUNBLOCK, RUN) + power_lottery[H] = list() + +/obj/machinery/dna_vault/proc/grant_power(mob/living/carbon/human/H, block, power) + H.dna.SetSEState(block, 1, 1) + H.mutations |= power + genemutcheck(H, block, null, MUTCHK_FORCED) \ No newline at end of file diff --git a/code/modules/station_goals/shield.dm b/code/modules/station_goals/shield.dm new file mode 100644 index 00000000000..2090b34baa5 --- /dev/null +++ b/code/modules/station_goals/shield.dm @@ -0,0 +1,193 @@ +//Station Shield +// A chain of satellites encircles the station +// Satellites be actived to generate a shield that will block unorganic matter from passing it. +/datum/station_goal/station_shield + name = "Station Shield" + var/coverage_goal = 500 + +/datum/station_goal/station_shield/get_report() + return {"Station Shield construction
+ The station is located in a zone full of space debris. We have a prototype shielding system you will deploy to reduce collision related accidents. +

+ You can order the satellites and control systems through cargo shuttle."} + +/datum/station_goal/station_shield/on_report() + //Unlock + var/datum/supply_packs/P = shuttle_master.supply_packs["[/datum/supply_packs/misc/shield_sat]"] + P.special_enabled = TRUE + + P = shuttle_master.supply_packs["[/datum/supply_packs/misc/shield_sat_control]"] + P.special_enabled = TRUE + +/datum/station_goal/station_shield/check_completion() + if(..()) + return TRUE + if(get_coverage() >= coverage_goal) + return TRUE + return FALSE + +/datum/station_goal/proc/get_coverage() + var/list/coverage = list() + for(var/obj/machinery/satellite/meteor_shield/A in machines) + if(!A.active || !is_station_level(A.z)) + continue + coverage |= view(A.kill_range, A) + return coverage.len + +/obj/item/weapon/circuitboard/computer/sat_control + name = "Satellite Network Control (Computer Board)" + build_path = /obj/machinery/computer/sat_control + origin_tech = "engineering=3" + +/obj/machinery/computer/sat_control + name = "Satellite control" + desc = "Used to control the satellite network." + circuit = /obj/item/weapon/circuitboard/computer/sat_control + icon_screen = "accelerator" + icon_keyboard = "accelerator_key" + var/notice + +/obj/machinery/computer/sat_control/attack_hand(mob/user) + if(..()) + return 1 + ui_interact(user) + +/obj/machinery/computer/sat_control/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + ui = nanomanager.try_update_ui(user, src, ui_key, ui, force_open) + if(!ui) + ui = new(user, src, ui_key, "sat_control.tmpl", name, 475, 400) + ui.open() + +/obj/machinery/computer/sat_control/Topic(href, href_list) + if(..()) + return 1 + + if(href_list["toggle"]) + toggle(text2num(href_list["id"])) + . = TRUE + +/obj/machinery/computer/sat_control/proc/toggle(id) + for(var/obj/machinery/satellite/S in machines) + if(S.id == id && atoms_share_level(src, S)) + S.toggle() + +/obj/machinery/computer/sat_control/ui_data(mob/user, ui_key = "main", datum/topic_state/state = physical_state) + var/list/data = list() + + data["satellites"] = list() + for(var/obj/machinery/satellite/S in machines) + data["satellites"] += list(list( + "id" = S.id, + "active" = S.active, + "mode" = S.mode + )) + data["notice"] = notice + + var/datum/station_goal/station_shield/G = locate() in ticker.mode.station_goals + if(G) + data["meteor_shield"] = 1 + data["meteor_shield_coverage"] = G.get_coverage() + data["meteor_shield_coverage_max"] = G.coverage_goal + data["meteor_shield_coverage_percentage"] = (G.get_coverage() / G.coverage_goal) * 100 + return data + +/obj/machinery/satellite + name = "Defunct Satellite" + desc = "" + icon = 'icons/obj/machines/satellite.dmi' + icon_state = "sat_inactive" + var/mode = "NTPROBEV0.8" + var/active = FALSE + density = 1 + use_power = FALSE + var/static/gid = 0 + var/id = 0 + +/obj/machinery/satellite/New() + ..() + id = gid++ + +/obj/machinery/satellite/attack_hand(mob/user) + if(..()) + return 1 + interact(user) + +/obj/machinery/satellite/interact(mob/user) + toggle(user) + +/obj/machinery/satellite/proc/toggle(mob/user) + if(!active && !isinspace()) + if(user) + to_chat(user, "You can only active the [src] in space.") + return TRUE + if(user) + to_chat(user, "You [active ? "deactivate": "activate"] the [src]") + active = !active + if(active) + animate(src, pixel_y = 2, time = 10, loop = -1) + anchored = 1 + else + animate(src, pixel_y = 0, time = 10) + anchored = 0 + update_icon() + +/obj/machinery/satellite/update_icon() + icon_state = active ? "sat_active" : "sat_inactive" + +/obj/machinery/satellite/attackby(obj/item/I, mob/user, params) + if(istype(I, /obj/item/device/multitool)) + to_chat(user, "// NTSAT-[id] // Mode : [active ? "PRIMARY" : "STANDBY"] //[emagged ? "DEBUG_MODE //" : ""]") + else + return ..() + +/obj/machinery/satellite/meteor_shield + name = "Meteor Shield Satellite" + desc = "Meteor Point Defense Satellite" + mode = "M-SHIELD" + speed_process = TRUE + var/kill_range = 14 + +/obj/machinery/satellite/meteor_shield/proc/space_los(meteor) + for(var/turf/T in getline(src,meteor)) + if(!isspaceturf(T)) + return FALSE + return TRUE + +/obj/machinery/satellite/meteor_shield/process() + if(!active) + return + for(var/obj/effect/meteor/M in meteor_list) + if(M.z != z) + continue + if(get_dist(M, src) > kill_range) + continue + if(!emagged && space_los(M)) + Beam(get_turf(M), icon_state = "sat_beam", time = 5, maxdistance = kill_range) + qdel(M) + +/obj/machinery/satellite/meteor_shield/toggle(user) + if(..(user)) + return TRUE + if(emagged) + if(active) + change_meteor_chance(2) + else + change_meteor_chance(0.5) + +/obj/machinery/satellite/meteor_shield/proc/change_meteor_chance(mod) + for(var/datum/event_container/container in event_manager.event_containers) + for(var/datum/event_meta/M in container.available_events) + if(M.event_type == /datum/event/meteor_wave) + M.weight *= mod + +/obj/machinery/satellite/meteor_shield/Destroy() + . = ..() + if(active && emagged) + change_meteor_chance(0.5) + +/obj/machinery/satellite/meteor_shield/emag_act(mob/user) + if(!emagged) + to_chat(user, "You override the shield's circuits, causing it to attract meteors instead of destroying them.") + emagged = 1 + if(active) + change_meteor_chance(2) diff --git a/code/modules/station_goals/station_goal.dm b/code/modules/station_goals/station_goal.dm new file mode 100644 index 00000000000..5a97f0ee2f3 --- /dev/null +++ b/code/modules/station_goals/station_goal.dm @@ -0,0 +1,49 @@ +//TODO +// Admin button to override with your own +// Sabotage objective for tators +// Multiple goals with less impact but more department focused + +/datum/station_goal + var/name = "Generic Goal" + var/weight = 1 //In case of multiple goals later. + var/required_crew = 10 + var/list/gamemode_blacklist = list() + var/completed = FALSE + var/report_message = "Complete this goal." + +/datum/station_goal/proc/send_report() + priority_announcement.Announce("Priority Nanotrasen directive received. Project \"[name]\" details inbound.", "Incoming Priority Message", 'sound/AI/commandreport.ogg') + print_command_report(get_report(), "Nanotrasen Directive [pick(phonetic_alphabet)] \Roman[rand(1,50)]") + on_report() + +/datum/station_goal/proc/on_report() + //Additional unlocks/changes go here + return + +/datum/station_goal/proc/get_report() + return report_message + +/datum/station_goal/proc/check_completion() + return completed + +/datum/station_goal/proc/print_result() + if(check_completion()) + to_chat(world, "Station Goal : [name] : Completed!") + else + to_chat(world, "Station Goal : [name] : Failed!") + +/datum/station_goal/Destroy() + ticker.mode.station_goals -= src + . = ..() + +/datum/station_goal/Topic(href, href_list) + ..() + + if(!check_rights(R_EVENT)) + return + + if(href_list["announce"]) + on_report() + send_report() + else if(href_list["remove"]) + qdel(src) \ No newline at end of file diff --git a/icons/effects/beam.dmi b/icons/effects/beam.dmi index 67da41362f8..ec06922a07d 100644 Binary files a/icons/effects/beam.dmi and b/icons/effects/beam.dmi differ diff --git a/icons/obj/lavaland/cannon.dmi b/icons/obj/lavaland/cannon.dmi new file mode 100644 index 00000000000..82efad1bc5e Binary files /dev/null and b/icons/obj/lavaland/cannon.dmi differ diff --git a/icons/obj/machines/artillery.dmi b/icons/obj/machines/artillery.dmi deleted file mode 100644 index 887af9fdc07..00000000000 Binary files a/icons/obj/machines/artillery.dmi and /dev/null differ diff --git a/icons/obj/machines/dna_vault.dmi b/icons/obj/machines/dna_vault.dmi new file mode 100644 index 00000000000..35503336d42 Binary files /dev/null and b/icons/obj/machines/dna_vault.dmi differ diff --git a/icons/obj/machines/particle_accelerator3.dmi b/icons/obj/machines/particle_accelerator3.dmi new file mode 100644 index 00000000000..c601b8d1b6a Binary files /dev/null and b/icons/obj/machines/particle_accelerator3.dmi differ diff --git a/icons/obj/machines/satellite.dmi b/icons/obj/machines/satellite.dmi new file mode 100644 index 00000000000..efe3dade763 Binary files /dev/null and b/icons/obj/machines/satellite.dmi differ diff --git a/nano/templates/bluespace_artillery.tmpl b/nano/templates/bluespace_artillery.tmpl deleted file mode 100644 index 344a6d1fd48..00000000000 --- a/nano/templates/bluespace_artillery.tmpl +++ /dev/null @@ -1,26 +0,0 @@ - -

Bluespace Artillery Control

-
-
Target Lock
-
{{:data.target}}
-
-
-
Fire Cooldown
-
- {{if data.reloadtime_mins > 0 || data.reloadtime_mins == 0 && data.reloadtime_secs > 0}} - {{:data.reloadtime_mins}}:{{:data.reloadtime_secs}} - {{else}} - Ready - {{/if}} -
-
-
- {{:helper.link('Select Target', 'exclamation-triangle', { 'area' : 1 })}} - {{:helper.link('Fire', 'exclamation-triangle', { 'fire' : 1 }, data.reloadtime_mins > 0 || data.reloadtime_mins == 0 && data.reloadtime_secs > 0 ? 'disabled' : '')}} -
-
-Deployment of weapon authorized by Nanotrasen Naval Command. Remember, friendly fire is grounds for termination of your contract and life. - diff --git a/nano/templates/bsa.tmpl b/nano/templates/bsa.tmpl new file mode 100644 index 00000000000..a0e8a60deb5 --- /dev/null +++ b/nano/templates/bsa.tmpl @@ -0,0 +1,51 @@ + +{{if data.notice}} +
{{:data.notice}}
+{{/if}} +

Bluespace Artillery Control

+
+
+ Target: +
+
+ {{:helper.link(data.target ? data.target : "None", 'crosshairs', {'recalibrate' : 1})}} +
+
+
+
+ Reload Cooldown: +
+
+ {{if data.ready}} + Ready + {{else data.reloadtime_mins || data.reloadtime_secs}} + {{:data.reloadtime_mins}}:{{:data.reloadtime_secs}} + {{else}} + No cannon connected! + {{/if}} +
+
+
+
+ Controls: +
+
+ {{:helper.link('FIRE!', 'warning', {'fire' : 1}, data.ready && data.target ? null : 'disabled')}} +
+
+{{if !data.connected}} +
+
+ Maintenance: +
+
+ {{:helper.link('Complete Deployment', 'wrench', {'build' : 1})}} +
+
+{{else}} +
+Deployment of weapon authorized by Nanotrasen Naval Command. Remember, friendly fire is grounds for termination of your contract and life. +{{/if}} \ No newline at end of file diff --git a/nano/templates/comm_console.tmpl b/nano/templates/comm_console.tmpl index c4e1799afcf..062c8d844f3 100644 --- a/nano/templates/comm_console.tmpl +++ b/nano/templates/comm_console.tmpl @@ -111,17 +111,17 @@ Used In File(s): /code/game/machinery/computers/communications.dm

Messages

{{if data.current_message}} {{:helper.link('Messages','home',{'operation':'messagelist'})}} -

{{>title}}

+

{{:data.current_message_title}}

- {{>body}} + {{:data.current_message}}
{{else}} {{:helper.link('Back','home',{'operation':'main'})}} {{for data.messages}}
- {{:helper.link('Open','envelope-o',{'operation':'messagelist','msgid':data.id})}} - {{:helper.link('Delete','close',{'operation':'delmessage','msgid':data.id},'red')}} - {{>data.title}} + {{:value.title}}
+ {{:helper.link('Open','envelope-o',{'operation':'messagelist','msgid':value.id})}} + {{:helper.link('Delete','close',{'operation':'delmessage','msgid':value.id})}}
{{/for}} {{/if}} diff --git a/nano/templates/dna_vault.tmpl b/nano/templates/dna_vault.tmpl new file mode 100644 index 00000000000..a5d631414d1 --- /dev/null +++ b/nano/templates/dna_vault.tmpl @@ -0,0 +1,49 @@ + +

DNA Vault Database

+
+
+ Human DNA: +
+
+ {{:helper.displayBar(data.dna, 0, data.dna_max, data.dna >= data.dna_max ? 'good' : 'average')}} +
+ {{:data.dna}}/{{:data.dna_max}} Samples +
+
+
+
+
+ Plant Data: +
+
+ {{:helper.displayBar(data.plants, 0, data.plants_max, data.plants >= data.plants_max ? 'good' : 'average')}} +
+ {{:data.plants}}/{{:data.plants_max}} Samples +
+
+
+
+
+ Animal Data: +
+
+ {{:helper.displayBar(data.animals, 0, data.animals_max, data.animals >= data.animals_max ? 'good' : 'average')}} +
+ {{:data.animals}}/{{:data.animals_max}} Samples +
+
+
+{{if data.completed && !data.used}} +
+
+ Applicable gene therapy treatments: +
+
+ {{:helper.link(data.choiceA, null, {'gene' : 1, 'choice' : data.choiceA})}} + {{:helper.link(data.choiceB, null, {'gene' : 1, 'choice' : data.choiceB})}} +
+
+{{/if}} \ No newline at end of file diff --git a/nano/templates/sat_control.tmpl b/nano/templates/sat_control.tmpl new file mode 100644 index 00000000000..a3b5ad40cb1 --- /dev/null +++ b/nano/templates/sat_control.tmpl @@ -0,0 +1,32 @@ + +{{if data.notice}} +
{{:data.notice}}
+{{/if}} +

Satellite Network Control

+{{for data.satellites}} +
+
+ #{{:value.id}} - {{:value.mode}} +
+
+ + {{:helper.link(value.active ? 'Deactivate' : 'Activate', null, {'toggle' : 1, 'id' : value.id})}} +
+
+{{/for}} +{{if data.meteor_shield}} +
+
+ Station Shield Coverage: +
+
+ {{:helper.displayBar(data.meteor_shield_coverage, 0, data.meteor_shield_coverage_max, data.meteor_shield_coverage_percentage >= 100 ? 'good' : 'average')}} +
+ {{:data.meteor_shield_coverage_percentage}}% +
+
+
+{{/if}} \ No newline at end of file diff --git a/paradise.dme b/paradise.dme index cdcdcb9a6c9..566614547bc 100644 --- a/paradise.dme +++ b/paradise.dme @@ -1091,7 +1091,6 @@ #include "code\modules\atmos_automation\implementation\scrubbers.dm" #include "code\modules\atmos_automation\implementation\sensors.dm" #include "code\modules\atmos_automation\implementation\vent_pump.dm" -#include "code\modules\awaymissions\bluespaceartillery.dm" #include "code\modules\awaymissions\corpse.dm" #include "code\modules\awaymissions\exile.dm" #include "code\modules\awaymissions\gateway.dm" @@ -2081,6 +2080,10 @@ #include "code\modules\spacepods\parts.dm" #include "code\modules\spacepods\pod_fabricator.dm" #include "code\modules\spacepods\spacepod.dm" +#include "code\modules\station_goals\bsa.dm" +#include "code\modules\station_goals\dna_vault.dm" +#include "code\modules\station_goals\shield.dm" +#include "code\modules\station_goals\station_goal.dm" #include "code\modules\store\items.dm" #include "code\modules\store\store.dm" #include "code\modules\surgery\bones.dm" diff --git a/sound/machines/bsa_fire.ogg b/sound/machines/bsa_fire.ogg new file mode 100644 index 00000000000..19244ff69d6 Binary files /dev/null and b/sound/machines/bsa_fire.ogg differ