diff --git a/_maps/RandomZLevels/away_mission/stargate.dmm b/_maps/RandomZLevels/away_mission/stargate.dmm
index a2dff503..65663d91 100644
--- a/_maps/RandomZLevels/away_mission/stargate.dmm
+++ b/_maps/RandomZLevels/away_mission/stargate.dmm
@@ -2,14 +2,14 @@
"ab" = (/turf/closed/mineral/random/labormineral/jungle,/area/awaymission/stargate/building/mountain)
"ac" = (/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"ad" = (/obj/structure/table/wood,/obj/item/reagent_containers/food/drinks/trophy,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"ae" = (/obj/item/flashlight/lantern{icon_state = "lantern-on"},/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"ae" = (/obj/item/flashlight/lantern{icon_state = "lantern-on"},/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"af" = (/obj/structure/flora/ausbushes/ywflowers,/mob/living/simple_animal/chicken,/turf/open/floor/grass,/area/awaymission/stargate)
"ag" = (/obj/structure/flora/rock/jungle,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
-"ah" = (/obj/item/storage/firstaid/regular,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"ah" = (/obj/item/storage/firstaid/regular,/obj/structure/table/wood,/turf/open/floor/wood,/area/awaymission/stargate/building)
"ai" = (/obj/structure/rack/shelf,/obj/item/clothing/suit/armor/riot/knight/yellow,/obj/item/shield/riot/tower,/obj/item/clothing/head/helmet/knight/yellow,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"aj" = (/turf/closed/indestructible/necropolis,/area/awaymission/stargate/building/flesh)
"ak" = (/turf/open/indestructible/necropolis/air,/area/awaymission/stargate/building/flesh)
-"al" = (/obj/structure/destructible/cult/talisman,/obj/item/dragons_blood,/turf/open/indestructible/necropolis/air,/area/awaymission/stargate/building/flesh)
+"al" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"am" = (/mob/living/simple_animal/hostile/carrion,/turf/open/indestructible/necropolis/air,/area/awaymission/stargate/building/flesh)
"an" = (/obj/structure/table/wood,/obj/item/nullrod/egyptian,/turf/open/floor/wood,/area/awaymission/stargate/building)
"ao" = (/obj/item/bedsheet/cult,/obj/effect/mob_spawn/human/villager,/turf/open/floor/wood,/area/awaymission/stargate/building)
@@ -20,46 +20,136 @@
"at" = (/obj/item/bedsheet/black,/obj/effect/mob_spawn/human/villager,/turf/open/floor/wood,/area/awaymission/stargate/building)
"au" = (/obj/item/bedsheet/red,/obj/effect/mob_spawn/human/villager,/turf/open/floor/wood,/area/awaymission/stargate/building)
"av" = (/obj/machinery/aug_manipulator,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
-"aw" = (/mob/living/simple_animal/hostile/netherworld/migo,/turf/open/floor/plasteel/cult,/area/awaymission/stargate/building)
-"ax" = (/obj/structure/rack/shelf,/obj/item/ammo_box/magazine/wt550m9/wtrubber,/obj/item/ammo_box/magazine/wt550m9/wtrubber,/obj/item/ammo_box/magazine/wt550m9/wtrubber,/obj/item/ammo_box/magazine/wt550m9/wtrubber,/obj/item/ammo_box/magazine/wt550m9/wtrubber,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"ay" = (/obj/structure/rack/shelf,/obj/item/ammo_box/magazine/wt550m9,/obj/item/ammo_box/magazine/wt550m9,/obj/item/ammo_box/magazine/wt550m9,/obj/item/ammo_box/magazine/wt550m9,/obj/item/ammo_box/magazine/wt550m9,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"az" = (/obj/structure/rack/shelf,/obj/item/ammo_box/magazine/wt550m9/wtic,/obj/item/ammo_box/magazine/wt550m9/wtic,/obj/item/ammo_box/magazine/wt550m9/wtic,/obj/item/ammo_box/magazine/wt550m9/wtic,/obj/item/ammo_box/magazine/wt550m9/wtic,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aw" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
+"ay" = (/obj/structure/rack/shelf,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"az" = (/obj/structure/closet/secure_closet/freezer/fridge,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"aA" = (/obj/item/clothing/mask/gas,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"aB" = (/obj/item/clothing/shoes/sneakers/black,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"aC" = (/obj/structure/closet/supplypod/centcompod,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"aD" = (/obj/item/clothing/gloves/color/fyellow/old,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"aE" = (/obj/item/clothing/under/color/grey,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"aF" = (/obj/item/twohanded/spear,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"aG" = (/obj/item/gun/ballistic/shotgun/riot,/obj/item/gun/ballistic/shotgun/riot{pixel_x = 3; pixel_y = -3},/obj/structure/rack/shelf,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"aH" = (/obj/effect/landmark/awaystart,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aH" = (/obj/structure/table/wood,/obj/machinery/microwave,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aI" = (/obj/structure/closet/secure_closet/freezer/meat,/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aJ" = (/obj/structure/table/wood,/obj/item/kitchen/knife,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aK" = (/obj/structure/table/wood,/obj/machinery/reagentgrinder,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aL" = (/obj/structure/sink{dir = 8; pixel_x = -12; pixel_y = 2},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aM" = (/obj/machinery/door/airlock/wood,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aN" = (/obj/structure/dresser,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"aO" = (/obj/structure/closet/crate/wooden,/obj/item/stack/sheet/cloth/thirty,/obj/item/stack/sheet/cloth/thirty,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"aP" = (/obj/structure/closet/crate/wooden,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aQ" = (/obj/machinery/light{dir = 8},/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aR" = (/obj/structure/bed,/obj/item/bedsheet/brown,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aS" = (/obj/structure/rack/shelf,/obj/item/gun/ballistic/shotgun/riot,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"aT" = (/turf/open/floor/cobble/corner{dir = 1; icon_state = "cobble_corner"},/area/awaymission/stargate)
+"aU" = (/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"aV" = (/turf/open/floor/cobble/corner,/area/awaymission/stargate)
"aW" = (/obj/structure/flora/rock,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"aX" = (/turf/open/floor/cobble,/area/awaymission/stargate)
+"aY" = (/turf/open/floor/cobble/side{dir = 4; icon_state = "cobble_side"},/area/awaymission/stargate)
+"aZ" = (/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
+"ba" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bb" = (/turf/open/floor/cobble/corner{dir = 8; icon_state = "cobble_corner"},/area/awaymission/stargate)
"bc" = (/obj/structure/table/reinforced,/obj/item/clothing/mask/gas/clown_hat,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"bd" = (/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"be" = (/turf/open/floor/cobble/corner{dir = 4; icon_state = "cobble_corner"},/area/awaymission/stargate)
+"bf" = (/obj/structure/barricade/wooden,/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
+"bg" = (/obj/structure/barricade/wooden,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bh" = (/obj/structure/barricade/wooden,/turf/open/floor/cobble/side{dir = 4; icon_state = "cobble_side"},/area/awaymission/stargate)
"bi" = (/obj/structure/flora/grass/jungle,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
+"bj" = (/mob/living/simple_animal/butterfly,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bk" = (/obj/effect/landmark/awaystart,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bl" = (/mob/living/simple_animal/butterfly,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"bm" = (/obj/item/lighter,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bn" = (/obj/item/grown/log/tree,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bo" = (/mob/living/simple_animal/butterfly,/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
+"bp" = (/obj/structure/bonfire,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bq" = (/obj/structure/barricade/sandbags,/obj/structure/barricade/sandbags,/turf/open/floor/cobble,/area/awaymission/stargate)
+"br" = (/obj/structure/barricade/sandbags,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bs" = (/obj/structure/fence{dir = 4},/turf/open/floor/plating/dirt,/area/awaymission/stargate/building/mountain)
+"bt" = (/obj/structure/fence/door,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"bu" = (/obj/structure/fence{dir = 4},/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"bv" = (/obj/structure/falsewall/abductor,/turf/open/space/basic,/area/awaymission/stargate/building)
+"bw" = (/obj/machinery/door/airlock/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"bx" = (/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"by" = (/turf/closed/wall/mineral/abductor,/area/awaymission/stargate/building)
+"bz" = (/obj/structure/barricade/sandbags,/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
"bA" = (/obj/effect/decal/cleanable/blood/gibs/human/body,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"bB" = (/obj/structure/barricade/sandbags,/turf/open/floor/cobble/side{dir = 4; icon_state = "cobble_side"},/area/awaymission/stargate)
"bC" = (/obj/machinery/hydroponics/soil,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
+"bD" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
+"bE" = (/obj/machinery/gateway{dir = 9},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bF" = (/obj/structure/fence{dir = 4},/turf/open/floor/cobble/side{dir = 8; icon_state = "cobble_side"},/area/awaymission/stargate)
+"bG" = (/obj/structure/fence/door,/turf/open/floor/cobble,/area/awaymission/stargate)
+"bH" = (/obj/structure/fence{dir = 4},/turf/open/floor/cobble,/area/awaymission/stargate)
+"bI" = (/obj/structure/fence{dir = 4},/turf/open/floor/cobble/side{dir = 4; icon_state = "cobble_side"},/area/awaymission/stargate)
+"bJ" = (/obj/machinery/gateway{dir = 1},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bK" = (/obj/machinery/gateway{dir = 5},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"bL" = (/obj/structure/table/wood/fancy/blackred,/obj/machinery/chem_dispenser/drinks,/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
+"bM" = (/obj/machinery/gateway{dir = 8},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bN" = (/obj/machinery/gateway/centeraway,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bO" = (/obj/machinery/gateway{dir = 4},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"bP" = (/obj/structure/chair/sofa{dir = 4},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"bQ" = (/obj/effect/decal/remains/robot,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"bR" = (/obj/structure/flora/ausbushes/brflowers,/obj/structure/flora/ausbushes/ywflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"bS" = (/obj/structure/flora/junglebush/large,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
+"bT" = (/obj/machinery/gateway{dir = 10},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bU" = (/obj/structure/door_assembly/door_assembly_abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"bV" = (/obj/machinery/gateway,/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bW" = (/obj/machinery/gateway{dir = 6},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bX" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
+"bY" = (/obj/structure/barricade/wooden/crude,/obj/machinery/door/airlock/wood,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"bZ" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"ca" = (/obj/structure/barricade/sandbags,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"cb" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/cobble,/area/awaymission/stargate)
+"cc" = (/turf/open/floor/concrete,/area/awaymission/stargate)
+"cd" = (/turf/open/floor/concrete/smooth,/area/awaymission/stargate)
+"ce" = (/mob/living/simple_animal/hostile/carrion,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"cf" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/cobble,/area/awaymission/stargate)
+"cg" = (/obj/effect/decal/cleanable/blood/gibs/human,/turf/open/floor/cobble,/area/awaymission/stargate)
+"ch" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"ci" = (/obj/structure/barricade/wooden,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
"cj" = (/obj/machinery/door/airlock/wood/glass,/obj/structure/barricade/wooden/crude,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"cp" = (/mob/living/simple_animal/hostile/hs13mimic,/turf/open/floor/grass,/area/awaymission/stargate)
+"ck" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"cl" = (/obj/effect/decal/remains/human,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"cm" = (/obj/effect/decal/cleanable/blood/gibs,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"cn" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"co" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/cobble/corner,/area/awaymission/stargate)
+"cp" = (/obj/structure/barricade/sandbags,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"cq" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/cobble,/area/awaymission/stargate)
+"cr" = (/obj/effect/decal/cleanable/blood/gibs/torso,/turf/open/floor/cobble,/area/awaymission/stargate)
"cs" = (/turf/open/floor/wood,/area/awaymission/stargate/building)
+"ct" = (/obj/effect/decal/cleanable/blood/gibs,/turf/open/floor/cobble,/area/awaymission/stargate)
+"cu" = (/obj/effect/decal/remains/human,/turf/open/floor/cobble,/area/awaymission/stargate)
+"cv" = (/obj/structure/closet/crate,/obj/item/stack/ore/bananium,/obj/item/stack/ore/bananium,/obj/item/stack/ore/bananium,/obj/item/stack/ore/bananium,/obj/item/stack/ore/bananium,/obj/item/stack/ore/bananium,/turf/open/floor/mineral/titanium/yellow,/area/awaymission/stargate/building)
+"cw" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/cobble,/area/awaymission/stargate)
"cx" = (/obj/structure/table/reinforced,/obj/item/robot_module/clown,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"cy" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"cz" = (/turf/open/floor/mineral/diamond,/area/awaymission/stargate/building)
+"cB" = (/obj/structure/statue/bananium/clown,/turf/open/floor/cobble/side{dir = 4; icon_state = "cobble_side"},/area/awaymission/stargate)
+"cD" = (/obj/structure/barricade/sandbags,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"cE" = (/obj/structure/barricade/wooden,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"cF" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"cG" = (/obj/effect/decal/remains/human,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"cH" = (/obj/effect/decal/remains/xeno,/turf/open/floor/cobble/side,/area/awaymission/stargate)
"cI" = (/obj/structure/flora/tree/palm,/obj/structure/flora/ausbushes/ywflowers,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
+"cJ" = (/obj/effect/decal/cleanable/blood/gibs/torso,/turf/open/floor/cobble/side,/area/awaymission/stargate)
+"cK" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/cobble/side,/area/awaymission/stargate)
"db" = (/obj/structure/table/wood,/obj/item/flashlight/lantern{icon_state = "lantern-on"},/turf/open/floor/wood,/area/awaymission/stargate/building)
-"di" = (/obj/structure/barricade/wooden,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
"dt" = (/turf/closed/wall/mineral/bananium,/area/awaymission/stargate/building)
"dz" = (/obj/machinery/conveyor{dir = 8; id = "mining_internal"},/turf/open/floor/wood,/area/awaymission/stargate/building)
-"dO" = (/obj/item/gun/ballistic/shotgun/riot,/obj/item/gun/ballistic/shotgun/riot,/obj/structure/rack/shelf,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"dO" = (/obj/item/gun/ballistic/shotgun/riot,/obj/structure/rack/shelf,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"dQ" = (/obj/structure/flora/junglebush/c,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"dT" = (/obj/machinery/vending/hydronutrients,/turf/open/floor/wood,/area/awaymission/stargate/building)
"ea" = (/obj/machinery/computer/rdconsole/core,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"ec" = (/obj/structure/reagent_dispensers/keg/semen,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"ee" = (/obj/structure/chair/wood{dir = 1},/turf/open/floor/wood,/area/awaymission/stargate/building)
"el" = (/obj/structure/flora/rock/jungle,/turf/open/floor/grass,/area/awaymission/stargate)
+"es" = (/obj/machinery/light{dir = 4},/obj/structure/flora/junglebush,/turf/open/floor/grass,/area/awaymission/stargate/building)
"et" = (/obj/effect/decal/cleanable/blood/gibs/up,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"eI" = (/obj/structure/barricade/sandbags,/turf/open/indestructible/cobble/side{dir = 4},/area/awaymission/stargate)
+"eC" = (/obj/structure/statue/sandstone/abs,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"eG" = (/obj/structure/table/wood/fancy/black,/obj/item/stack/sheet/mineral/diamond{amount = 2},/turf/open/floor/mineral/diamond,/area/awaymission/stargate/building)
+"eI" = (/obj/machinery/light,/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
"eJ" = (/obj/structure/closet/secure_closet/freezer/meat,/turf/open/floor/wood,/area/awaymission/stargate/building)
"eL" = (/obj/structure/kitchenspike,/turf/open/floor/wood,/area/awaymission/stargate/building)
"eM" = (/obj/effect/decal/cleanable/blood/gibs/human,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
@@ -67,53 +157,59 @@
"eZ" = (/obj/machinery/light{dir = 4},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"fm" = (/obj/structure/table/plasmaglass,/obj/item/ashtray,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"fB" = (/obj/structure/table/wood,/obj/item/kitchen/rollingpin,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"fH" = (/obj/structure/fence{dir = 4},/turf/open/indestructible/cobble/side{dir = 4},/area/awaymission/stargate)
-"fJ" = (/obj/effect/decal/cleanable/blood,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
+"fC" = (/obj/machinery/abductor/gland_dispenser,/turf/open/floor/plating/abductor{initial_gas_mix = "o2=14;n2=23;TEMP=300"},/area/awaymission/stargate/building)
"fN" = (/obj/machinery/door/airlock/wood,/turf/open/floor/wood,/area/awaymission/stargate/building)
"fO" = (/obj/structure/flora/junglebush/b,/turf/open/floor/grass,/area/awaymission/stargate)
"fU" = (/obj/structure/table/wood,/obj/item/reagent_containers/glass/bottle/charcoal,/obj/item/reagent_containers/glass/bottle/charcoal,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"gc" = (/mob/living/simple_animal/butterfly,/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
-"gn" = (/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"fY" = (/obj/structure/chair/stool/alien,/obj/effect/decal/cleanable/greenglow,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"gB" = (/mob/living/simple_animal/hostile/retaliate/clown/lube,/turf/open/floor/cobble,/area/awaymission/stargate)
"gC" = (/obj/structure/flora/grass/jungle/b,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"gI" = (/obj/structure/mineral_door/woodrustic,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"gJ" = (/mob/living/simple_animal/hostile/netherworld/migo,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"hc" = (/obj/structure/chair/sofa/left{dir = 1},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"he" = (/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"hm" = (/obj/effect/decal/cleanable/blood/old,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"hs" = (/turf/closed/wall/mineral/cult/artificer,/area/awaymission/stargate/building)
"ht" = (/obj/structure/flora/rock/pile/largejungle,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
+"hw" = (/obj/structure/flora/junglebush/c,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"hC" = (/obj/structure/flora/junglebush/b,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
+"hG" = (/mob/living/simple_animal/hostile/retaliate/clown/mutant,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"hK" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"hM" = (/obj/effect/turf_decal/loading_area{dir = 4; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"hQ" = (/obj/structure/flora/junglebush,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"ik" = (/obj/machinery/shower{dir = 8; pixel_y = -4},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"il" = (/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
"iA" = (/obj/machinery/conveyor{dir = 10; id = "mining_internal"},/turf/open/floor/wood,/area/awaymission/stargate/building)
+"iK" = (/obj/effect/decal/cleanable/semen,/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate/building)
"iX" = (/obj/structure/flora/grass/jungle/b,/mob/living/simple_animal/butterfly,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
+"ja" = (/obj/machinery/light{dir = 1; light_color = "#cee5d2"},/obj/structure/table/wood/fancy/black,/obj/item/nullrod/claymore/chainsaw_sword,/turf/open/floor/mineral/diamond,/area/awaymission/stargate/building)
"je" = (/obj/structure/bed,/obj/item/bedsheet,/turf/open/floor/wood,/area/awaymission/stargate/building)
"jf" = (/obj/structure/closet/crate/wooden,/obj/item/twohanded/fireaxe/boneaxe,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"jz" = (/obj/structure/flora/grass/jungle,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/grass,/area/awaymission/stargate/building)
"jD" = (/turf/open/floor/carpet,/area/awaymission/stargate/building)
"jF" = (/obj/structure/table/wood/fancy/black,/obj/item/clothing/head/nemes,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"jH" = (/obj/structure/flora/ausbushes/reedbush,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
-"jR" = (/obj/machinery/rnd/production/protolathe,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"jR" = (/obj/machinery/rnd/production/protolathe/department/science,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"jX" = (/obj/structure/closet/crate/wooden,/obj/item/stack/sheet/glass/fifty,/obj/item/stack/sheet/glass/fifty,/turf/open/floor/wood,/area/awaymission/stargate/building)
"jZ" = (/obj/structure/flora/grass/jungle,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"ke" = (/obj/structure/flora/tree/desertdead,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"kh" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/indestructible/cobble/corner,/area/awaymission/stargate)
"ki" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"kp" = (/obj/machinery/light,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"ky" = (/obj/machinery/pool/filter{pixel_y = 24},/turf/open/pool,/area/awaymission/stargate/building)
"kM" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"kQ" = (/obj/machinery/autolathe,/turf/open/floor/wood,/area/awaymission/stargate/building)
"lg" = (/obj/structure/table/optable,/obj/effect/decal/cleanable/blood,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"lj" = (/obj/structure/flora/junglebush/c,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"ln" = (/obj/structure/closet/crate/wooden,/obj/item/stack/sheet/mineral/wood/fifty,/obj/item/stack/sheet/mineral/wood/fifty,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"lt" = (/obj/machinery/chem_heater,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"lt" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/mineral/diamond,/area/awaymission/stargate/building)
+"lQ" = (/obj/effect/decal/cleanable/greenglow,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"ma" = (/obj/structure/reagent_dispensers/water_cooler,/turf/open/floor/wood,/area/awaymission/stargate/building)
"mb" = (/obj/structure/rack/shelf,/obj/item/storage/box/lethalshot,/obj/item/storage/box/lethalshot,/obj/item/storage/box/lethalshot,/obj/item/storage/box/lethalshot,/obj/item/storage/box/lethalshot,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"md" = (/obj/structure/table/wood,/obj/item/reagent_containers/food/drinks/bottle/wine,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"me" = (/obj/structure/table/wood,/obj/item/storage/fancy/candle_box,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"mk" = (/obj/effect/decal/remains/human,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"mt" = (/obj/machinery/door/airlock/wood/glass,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"mv" = (/obj/machinery/chem_dispenser,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"mv" = (/obj/effect/decal/remains/human,/turf/open/floor/mineral/diamond,/area/awaymission/stargate/building)
"mx" = (/obj/structure/table/wood,/obj/item/storage/box/drinkingglasses,/obj/item/storage/box/drinkingglasses,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"mB" = (/obj/machinery/gateway{dir = 6},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"mB" = (/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
"mD" = (/mob/living/simple_animal/butterfly,/turf/open/water/jungle,/area/awaymission/stargate)
"mF" = (/obj/machinery/conveyor_switch/oneway{id = "mining_internal"; name = "mining conveyor"},/turf/open/floor/wood,/area/awaymission/stargate/building)
"mJ" = (/obj/structure/flora/tree/palm,/turf/open/floor/grass,/area/awaymission/stargate)
@@ -123,61 +219,69 @@
"nh" = (/obj/effect/decal/cleanable/blood/gibs,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"nm" = (/obj/structure/bonfire,/turf/open/floor/wood,/area/awaymission/stargate/building)
"nn" = (/obj/structure/table/wood/fancy/blackred,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
-"np" = (/obj/effect/decal/cleanable/blood,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"ny" = (/turf/open/indestructible/cobble/side{dir = 4},/area/awaymission/stargate)
+"nC" = (/obj/structure/pool/ladder{pixel_x = -3},/turf/open/pool,/area/awaymission/stargate/building)
+"nG" = (/obj/machinery/light{dir = 8; light_color = "#e8eaff"},/obj/structure/flora/junglebush,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"nK" = (/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate/building)
"nL" = (/obj/structure/table/reinforced,/obj/item/storage/backpack/duffelbag/med/surgery,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"nQ" = (/obj/structure/flora/junglebush/b,/turf/open/floor/grass,/area/awaymission/stargate/building)
"nR" = (/obj/structure/table/wood/fancy/black,/obj/item/reagent_containers/food/drinks/trophy,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"nX" = (/obj/machinery/light{dir = 8; light_color = "#e8eaff"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"nY" = (/obj/structure/flora/rock/pile/largejungle,/turf/open/floor/grass,/area/awaymission/stargate)
"of" = (/obj/effect/spawner/structure/window,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"oh" = (/obj/machinery/smartfridge/chemistry,/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
+"oh" = (/obj/structure/table/wood/fancy/black,/obj/item/stack/sheet/mineral/gold{amount = 25},/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
"ox" = (/obj/structure/chair/sofa/left{dir = 4},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"oy" = (/obj/effect/decal/cleanable/semen,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"oz" = (/obj/structure/chair/sofa{dir = 8},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"oC" = (/obj/machinery/abductor/gland_dispenser,/turf/open/floor/plating/abductor{initial_gas_mix = "o2=14;n2=23;TEMP=300"},/area/awaymission/stargate/building)
"oQ" = (/mob/living/simple_animal/chicken,/turf/open/floor/grass,/area/awaymission/stargate)
-"oS" = (/obj/machinery/gateway/centeraway,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"oS" = (/obj/effect/rune/apocalypse,/obj/structure/spawner/nether,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"oX" = (/obj/machinery/light{dir = 8},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"pd" = (/obj/machinery/light{dir = 4},/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"pm" = (/obj/structure/table/wood,/obj/item/lighter,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"pu" = (/turf/closed/wall/mineral/cult,/area/awaymission/stargate/building)
-"pA" = (/mob/living/simple_animal/butterfly,/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"pI" = (/obj/machinery/door/airlock/wood,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"pV" = (/obj/structure/flora/junglebush/large,/turf/open/floor/grass,/area/awaymission/stargate)
+"pY" = (/obj/structure/table/wood/fancy,/obj/item/dildo/flared/gigantic,/turf/open/floor/grass,/area/awaymission/stargate/building)
"qf" = (/obj/structure/flora/rock/jungle,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
-"qw" = (/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate/building/mountain)
+"qr" = (/obj/structure/flora/tree/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"qw" = (/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
+"qB" = (/obj/effect/decal/cleanable/blood/gibs/up,/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
"qC" = (/obj/machinery/light{dir = 4},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"qD" = (/obj/structure/flora/ausbushes/brflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"qK" = (/obj/structure/falsewall/sandstone,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"qP" = (/obj/structure/fence{dir = 4},/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
-"qS" = (/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"qR" = (/mob/living/simple_animal/hostile/jungle/mook,/obj/structure/flora/grass/jungle/b,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"qS" = (/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"qU" = (/obj/structure/sink/puddle,/turf/open/floor/grass,/area/awaymission/stargate)
-"rg" = (/obj/effect/decal/cleanable/blood,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
+"rb" = (/obj/structure/flora/junglebush/b,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"rh" = (/obj/effect/decal/cleanable/blood,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"rm" = (/mob/living/simple_animal/hostile/retaliate/clown/clownhulk/destroyer,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"rn" = (/obj/structure/table/optable/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"rt" = (/obj/machinery/light{dir = 8},/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"ry" = (/obj/structure/flora/junglebush/large,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"rC" = (/obj/structure/flora/ausbushes/brflowers,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
-"rD" = (/obj/effect/decal/cleanable/blood/gibs/human,/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"rL" = (/obj/structure/table/wood/fancy,/obj/item/reagent_containers/food/drinks/trophy{pixel_y = 8},/turf/open/floor/grass,/area/awaymission/stargate/building)
+"rS" = (/obj/effect/turf_decal/loading_area{dir = 1; icon_state = "drain"; name = "drain"},/obj/effect/turf_decal/loading_area{dir = 1; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"rU" = (/obj/structure/table/wood/fancy/blackred,/obj/machinery/reagentgrinder,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
"rX" = (/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"sn" = (/obj/machinery/door/airlock/wood/glass,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"su" = (/obj/structure/barricade/wooden,/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
-"sy" = (/obj/structure/fence/door,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"sC" = (/turf/open/indestructible/cobble/corner{dir = 4},/area/awaymission/stargate)
+"sr" = (/turf/open/floor/grass/fairy/red,/area/awaymission/stargate/building)
"sE" = (/obj/structure/flora/ausbushes/palebush,/turf/open/floor/grass,/area/awaymission/stargate)
"sL" = (/turf/closed/wall/mineral/wood/nonmetal,/area/awaymission/stargate/building)
"sM" = (/obj/structure/flora/ausbushes/ywflowers,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
+"sR" = (/obj/structure/flora/junglebush/b,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/grass,/area/awaymission/stargate/building)
"sW" = (/obj/structure/flora/tree/palm,/obj/structure/flora/grass/jungle/b,/turf/open/floor/grass,/area/awaymission/stargate)
-"sY" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"tc" = (/obj/structure/flora/junglebush,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
-"th" = (/obj/structure/barricade/sandbags,/obj/structure/barricade/sandbags,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"tj" = (/obj/structure/falsewall/sandstone,/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
"tz" = (/obj/structure/table/wood,/obj/item/twohanded/bonespear,/turf/open/floor/wood,/area/awaymission/stargate/building)
"tC" = (/obj/structure/chair/sofa/right{dir = 1},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"tD" = (/mob/living/simple_animal/hostile/retaliate/clown/mutant/blob,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"tI" = (/obj/machinery/light{dir = 4; light_color = "#c1caff"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"tN" = (/obj/structure/chair/wood{dir = 8},/turf/open/floor/wood,/area/awaymission/stargate/building)
+"tT" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"ua" = (/obj/structure/barricade/wooden,/obj/effect/decal/cleanable/blood/tracks{dir = 8},/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"uw" = (/obj/structure/flora/grass/jungle/b,/turf/open/floor/grass,/area/awaymission/stargate/building)
"uA" = (/obj/structure/chair/wood{dir = 8},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"uB" = (/obj/structure/flora/ausbushes/ppflowers,/turf/open/floor/grass,/area/awaymission/stargate)
-"uC" = (/obj/structure/barricade/wooden,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
+"uD" = (/obj/structure/showcase/horrific_experiment,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"uI" = (/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
"uO" = (/mob/living/simple_animal/cow,/turf/open/floor/grass,/area/awaymission/stargate)
"uR" = (/turf/open/indestructible/cobble/corner,/area/awaymission/stargate)
@@ -187,21 +291,24 @@
"vu" = (/mob/living/simple_animal/hostile/hs13mimic,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"vv" = (/obj/effect/spawner/structure/window,/turf/open/floor/wood,/area/awaymission/stargate/building)
"vz" = (/obj/structure/table/wood/fancy/black,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
+"vD" = (/obj/structure/flora/junglebush/large,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"vM" = (/obj/structure/closet/crate/wooden,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"vO" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"vS" = (/obj/machinery/light{dir = 8},/obj/structure/showcase/horrific_experiment,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
-"wl" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
-"wv" = (/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
+"vX" = (/obj/machinery/light{dir = 8; light_color = "#e8eaff"},/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"vZ" = (/obj/machinery/pool/controller,/obj/effect/turf_decal/loading_area{icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"wc" = (/obj/structure/reagent_dispensers/keg/aphro/strong,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"wC" = (/obj/machinery/light{dir = 4},/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate/building)
"wF" = (/obj/structure/rack/shelf,/obj/item/melee/classic_baton/telescopic,/obj/item/melee/classic_baton/telescopic,/obj/item/melee/classic_baton/telescopic,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"wL" = (/obj/structure/flora/ausbushes/palebush,/obj/structure/flora/ausbushes/ppflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"wP" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"wY" = (/obj/effect/decal/remains/xeno,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
-"wZ" = (/obj/machinery/door/airlock/wood,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"wZ" = (/obj/structure/table/wood/fancy/black,/obj/item/storage/fancy/ringbox/diamond,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"xm" = (/obj/structure/table/wood/fancy,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"xn" = (/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"xA" = (/obj/structure/pool/ladder{dir = 8; pixel_x = 2},/turf/open/pool,/area/awaymission/stargate/building)
"xG" = (/obj/structure/chair/wood{dir = 4},/turf/open/floor/wood,/area/awaymission/stargate/building)
"xK" = (/obj/structure/table/wood,/obj/item/shield/riot/buckler,/obj/item/shield/riot/buckler,/obj/item/shield/riot/buckler,/obj/item/shield/riot/buckler,/turf/open/floor/wood,/area/awaymission/stargate/building)
"xT" = (/obj/structure/chair/sofa/right{dir = 1},/obj/machinery/light,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"yc" = (/obj/machinery/light{dir = 4; light_color = "#c1caff"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"yv" = (/turf/open/indestructible/cobble/corner{dir = 1},/area/awaymission/stargate)
"yw" = (/obj/structure/reagent_dispensers/keg/aphro/strong,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"yA" = (/obj/structure/flora/junglebush/b,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
@@ -212,33 +319,35 @@
"yT" = (/obj/machinery/hydroponics/soil,/turf/open/floor/grass,/area/awaymission/stargate)
"yX" = (/obj/structure/fence{dir = 4},/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"yZ" = (/turf/open/water/jungle,/area/awaymission/stargate)
+"zc" = (/obj/machinery/light,/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate/building)
"zn" = (/obj/structure/chair/stool/bar,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"zC" = (/obj/structure/table/abductor,/obj/item/surgical_drapes,/obj/item/scalpel/alien,/obj/item/cautery/alien,/obj/item/circular_saw/alien,/obj/item/hemostat/alien,/obj/item/retractor/alien,/obj/item/surgicaldrill/alien,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"zD" = (/obj/structure/closet/crate/wooden,/obj/item/clothing/suit/armor/bone,/obj/item/clothing/head/helmet/skull,/obj/item/clothing/gloves/bracer,/obj/item/clothing/accessory/talisman,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"zF" = (/mob/living/simple_animal/hostile/netherworld/migo,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"zW" = (/obj/effect/rune/apocalypse,/obj/structure/spawner/nether,/turf/open/floor/plasteel/cult,/area/awaymission/stargate/building)
-"Al" = (/obj/item/lighter,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"Av" = (/turf/open/indestructible/concrete,/area/awaymission/stargate)
+"Ac" = (/obj/machinery/light{dir = 8; light_color = "#e8eaff"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Aw" = (/obj/structure/table/wood,/obj/item/storage/toolbox/mechanical/old,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Az" = (/obj/structure/dresser,/turf/open/floor/wood,/area/awaymission/stargate/building)
"AA" = (/obj/structure/table/wood,/obj/item/stack/sheet/leather,/obj/item/stack/sheet/leather,/obj/item/stack/sheet/leather,/obj/item/stack/sheet/leather,/obj/item/stack/sheet/leather,/turf/open/floor/wood,/area/awaymission/stargate/building)
"AC" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"AO" = (/obj/machinery/door/airlock/wood/glass,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"AW" = (/obj/structure/barricade/sandbags,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
"Be" = (/obj/effect/decal/cleanable/blood/gibs/up,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"BB" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/obj/structure/closet/crate/coffin/metalcoffin,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"Bh" = (/obj/effect/turf_decal/loading_area{dir = 1; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"Bj" = (/obj/structure/flora/grass/jungle/b,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/grass,/area/awaymission/stargate/building)
"BC" = (/obj/structure/flora/ausbushes/palebush,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
-"BI" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"BP" = (/obj/machinery/light,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"BR" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"BZ" = (/obj/structure/table/wood/fancy/black,/obj/item/export/bottle/champagne,/obj/item/reagent_containers/food/drinks/drinkingglass,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"Cb" = (/turf/open/indestructible/concrete/smooth,/area/awaymission/stargate)
+"BZ" = (/obj/structure/table/wood/fancy/black,/obj/item/export/bottle/champagne,/obj/item/reagent_containers/food/drinks/drinkingglass,/obj/machinery/light,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"Cc" = (/obj/structure/table/wood/fancy/blackred,/obj/machinery/chem_dispenser/drinks/beer/fullupgrade,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
-"Cj" = (/obj/structure/showcase/horrific_experiment,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"Cf" = (/obj/effect/turf_decal/loading_area{icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Cp" = (/obj/structure/chair/sofa/right{dir = 8},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"Cq" = (/turf/open/floor/plasteel/cult,/area/awaymission/stargate/building)
"Ct" = (/obj/machinery/smartfridge/drying_rack,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Cw" = (/obj/structure/flora/junglebush,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"Cy" = (/obj/machinery/computer/operating,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
-"Df" = (/obj/machinery/gateway{dir = 1},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"CA" = (/obj/structure/table/wood/fancy/blackred,/turf/open/floor/grass/fairy/red,/area/awaymission/stargate/building)
+"CO" = (/obj/structure/closet/secure_closet/freezer/fridge,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Da" = (/obj/effect/decal/cleanable/semen,/obj/structure/flora/grass/jungle/b,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/grass,/area/awaymission/stargate/building)
+"Df" = (/obj/machinery/light{dir = 8},/obj/structure/table/wood/fancy/black,/obj/item/stack/sheet/mineral/gold{amount = 25},/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
"Di" = (/obj/structure/flora/ausbushes/ppflowers,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
"Dj" = (/obj/machinery/light{dir = 4},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"Dk" = (/turf/open/floor/mineral/titanium/yellow,/area/awaymission/stargate/building)
@@ -248,105 +357,99 @@
"DD" = (/obj/structure/table/wood/fancy/black,/obj/structure/table/wood/fancy/black,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"DE" = (/mob/living/simple_animal/hostile/retaliate/clown/fleshclown,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"DF" = (/obj/machinery/smartfridge/food,/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
-"DM" = (/obj/effect/decal/remains/human,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
-"DQ" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"DM" = (/obj/effect/decal/remains/human,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"Ed" = (/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
"Eh" = (/obj/effect/decal/remains/robot,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"Ei" = (/mob/living/simple_animal/hostile/retaliate/clown/clownhulk/destroyer,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"Ej" = (/obj/effect/decal/cleanable/blood/gibs/torso,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"En" = (/obj/machinery/chem_master,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"En" = (/obj/structure/bed,/obj/item/bedsheet/grey,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Et" = (/obj/effect/decal/cleanable/semen,/obj/machinery/light,/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Ey" = (/obj/structure/table/reinforced,/obj/item/stack/sheet/glass/fifty,/obj/item/stack/sheet/metal/fifty,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"EI" = (/obj/machinery/door/airlock/shuttle,/turf/open/floor/mineral/titanium,/area/awaymission/stargate/building)
-"EQ" = (/mob/living/simple_animal/hostile/netherworld,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"ER" = (/obj/machinery/light{dir = 1},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"EY" = (/obj/effect/decal/cleanable/semen,/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Fc" = (/obj/structure/table/wood,/obj/item/flashlight/lantern{icon_state = "lantern-on"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Fg" = (/obj/structure/flora/grass/jungle,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
-"Fr" = (/obj/machinery/gateway,/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"Fs" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"Fw" = (/obj/structure/barricade/sandbags,/turf/open/indestructible/cobble/side{dir = 8},/area/awaymission/stargate)
+"Fk" = (/obj/machinery/pool/drain,/turf/open/pool,/area/awaymission/stargate/building)
+"Fr" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
+"Fw" = (/obj/structure/statue/sandstone/abs,/turf/open/floor/cobble,/area/awaymission/stargate)
"FA" = (/obj/structure/ore_box,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"FI" = (/obj/machinery/gateway{dir = 5},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"FI" = (/obj/machinery/light{dir = 4},/obj/structure/table/wood/fancy/black,/obj/item/reagent_containers/food/drinks/trophy/gold_cup,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"FM" = (/obj/structure/table/wood,/obj/item/storage/firstaid/regular,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"FO" = (/obj/structure/chair/stool/alien,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"FQ" = (/obj/machinery/conveyor{id = "mining_internal"},/turf/open/floor/wood,/area/awaymission/stargate/building)
-"Gb" = (/obj/effect/decal/cleanable/blood/gibs/torso,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
"Gg" = (/obj/machinery/mecha_part_fabricator,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"GS" = (/obj/structure/table/wood/fancy,/obj/item/seeds/chili/pink,/obj/item/seeds/chili/pink,/obj/item/seeds/chili/pink,/turf/open/floor/grass,/area/awaymission/stargate/building)
"GT" = (/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"GV" = (/obj/machinery/light{dir = 8},/obj/structure/closet/crate/wooden,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
+"GY" = (/obj/effect/turf_decal/loading_area{icon_state = "drain"; name = "drain"},/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"Hc" = (/obj/effect/turf_decal/loading_area{icon_state = "drain"; name = "drain"},/obj/effect/turf_decal/loading_area{dir = 4; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Hi" = (/obj/machinery/light{light_color = "#e8eaff"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Ho" = (/obj/structure/flora/tree/palm,/obj/structure/flora/ausbushes/ywflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"Hp" = (/obj/structure/flora/grass/jungle/b,/turf/open/floor/grass,/area/awaymission/stargate)
"HE" = (/obj/effect/decal/remains/xeno,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"Ia" = (/obj/structure/table/wood,/obj/item/storage/box/beakers,/obj/item/storage/box/syringes,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"Ib" = (/mob/living/simple_animal/butterfly,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
+"HH" = (/obj/machinery/abductor/experiment{team_number = 100},/turf/open/floor/plating/abductor{initial_gas_mix = "o2=14;n2=23;TEMP=300"},/area/awaymission/stargate/building)
+"Ia" = (/obj/structure/table/wood,/obj/item/storage/box/syringes,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Ic" = (/obj/structure/mineral_door/woodrustic,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Ie" = (/obj/machinery/mineral/processing_unit{dir = 1},/turf/open/floor/wood,/area/awaymission/stargate/building)
"Ik" = (/obj/structure/chair/sofa{dir = 8},/obj/machinery/light{dir = 4},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"Im" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"Ip" = (/turf/open/indestructible/cobble/corner{dir = 8},/area/awaymission/stargate)
-"Iu" = (/obj/structure/table/optable/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
-"Iv" = (/obj/machinery/gateway{dir = 8},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"Iv" = (/obj/effect/decal/remains/robot,/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
+"IA" = (/obj/structure/statue/sandstone/abs,/turf/open/floor/grass/fairy/red,/area/awaymission/stargate/building)
"IJ" = (/obj/structure/closet/crate/wooden,/obj/item/stack/sheet/metal/fifty,/obj/item/stack/sheet/metal/fifty,/turf/open/floor/wood,/area/awaymission/stargate/building)
"IP" = (/obj/structure/chair/wood,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"IQ" = (/obj/effect/decal/cleanable/semen,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"IU" = (/obj/machinery/door/airlock/bananium,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
-"IV" = (/obj/effect/decal/remains/human,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
"IX" = (/obj/structure/flora/ausbushes/palebush,/obj/structure/flora/ausbushes/ywflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"Jb" = (/obj/effect/decal/remains/human,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Jc" = (/obj/effect/decal/remains/human,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"Jh" = (/obj/structure/rack/shelf,/obj/item/gun/ballistic/automatic/wt550,/obj/item/gun/ballistic/automatic/wt550,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"Jh" = (/obj/structure/rack/shelf,/obj/item/storage/firstaid/regular,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Jm" = (/obj/machinery/door/airlock/wood,/obj/structure/barricade/wooden/crude,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Jp" = (/obj/structure/flora/junglebush/c,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
-"Jw" = (/obj/effect/decal/cleanable/blood/gibs/human/limb,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
"JB" = (/obj/structure/shuttle/engine/heater,/obj/structure/window/reinforced{dir = 1},/turf/open/floor/plating,/area/awaymission/stargate/building)
-"JX" = (/obj/machinery/sleeper{dir = 4; icon_state = "sleeper"},/turf/open/floor/wood,/area/awaymission/stargate/building)
-"Kc" = (/mob/living/simple_animal/hostile/retaliate/clown/mutant,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"JP" = (/mob/living/simple_animal/hostile/netherworld,/turf/open/indestructible/necropolis/air,/area/awaymission/stargate/building/flesh)
+"JX" = (/obj/structure/table/wood,/obj/item/defibrillator/loaded,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Kc" = (/obj/structure/table/wood/fancy/black,/obj/item/storage/fancy/ringbox,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"Kg" = (/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Km" = (/obj/structure/table/wood/fancy/blackred,/obj/item/storage/box/drinkingglasses,/obj/item/storage/box/drinkingglasses,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
"Kn" = (/turf/open/floor/mineral/titanium,/area/awaymission/stargate/building)
+"Ku" = (/obj/machinery/light{dir = 8},/obj/structure/showcase/horrific_experiment,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"Kv" = (/obj/structure/flora/junglebush/c,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/grass,/area/awaymission/stargate/building)
"KE" = (/obj/structure/flora/junglebush/c,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
"KG" = (/obj/structure/chair/wood{dir = 1},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"KO" = (/obj/structure/statue/bananium/clown,/turf/open/indestructible/cobble/side{dir = 4},/area/awaymission/stargate)
"KQ" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/wood,/area/awaymission/stargate/building)
"KY" = (/obj/structure/dresser,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"KZ" = (/obj/structure/flora/grass/jungle/b,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"Lb" = (/obj/structure/loom,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Lf" = (/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate)
-"Lj" = (/obj/structure/bonfire,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate/building/mountain)
-"Lp" = (/obj/machinery/gateway{dir = 4},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"Lk" = (/obj/machinery/light{dir = 8},/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"Lp" = (/obj/structure/table/wood/fancy/blackred,/obj/item/storage/firstaid/regular,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
"Lq" = (/obj/structure/table/wood,/obj/machinery/reagentgrinder,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Ls" = (/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"Lv" = (/obj/effect/decal/remains/human,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
"Ly" = (/obj/structure/showcase/horrific_experiment,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"Lz" = (/obj/machinery/shower{dir = 4},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"LB" = (/obj/effect/decal/remains/human,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"LC" = (/obj/effect/decal/remains/xeno,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"LI" = (/obj/structure/flora/rock/pile,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"LJ" = (/obj/effect/decal/cleanable/blood/tracks,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"LK" = (/obj/structure/flora/ausbushes/reedbush,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
+"LM" = (/obj/structure/table/wood,/obj/item/storage/firstaid/regular,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"LO" = (/obj/structure/flora/tree/palm,/obj/structure/flora/junglebush/c,/turf/open/floor/grass,/area/awaymission/stargate)
"LP" = (/obj/structure/shuttle/engine/propulsion,/turf/open/floor/plating,/area/awaymission/stargate/building)
"LQ" = (/obj/structure/toilet,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"Mk" = (/obj/item/kitchen/knife/combat/bone,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"Mr" = (/turf/closed/wall/mineral/wood/nonmetal,/area/awaymission/stargate)
"Ms" = (/obj/structure/chair/comfy/shuttle{dir = 1},/turf/open/floor/mineral/titanium/blue,/area/awaymission/stargate/building)
"Mu" = (/obj/structure/mineral_door/woodrustic,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Mx" = (/obj/machinery/light{dir = 8; light_color = "#e8eaff"},/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
+"MB" = (/obj/effect/turf_decal/loading_area{icon_state = "drain"; name = "drain"},/obj/effect/turf_decal/loading_area{dir = 8; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"MC" = (/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"MD" = (/obj/structure/chair/sofa{dir = 4},/obj/machinery/light{dir = 8},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"MI" = (/obj/structure/flora/ausbushes/ywflowers,/turf/open/floor/grass,/area/awaymission/stargate)
-"MZ" = (/obj/structure/reagent_dispensers/keg/semen,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
-"Ne" = (/obj/effect/decal/cleanable/blood/gibs,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
+"MM" = (/obj/effect/turf_decal/loading_area{dir = 8; icon_state = "drain"; name = "drain"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"Nh" = (/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Nk" = (/obj/structure/frame/computer,/obj/effect/decal/cleanable/glass,/obj/item/shard,/turf/open/floor/mineral/titanium/yellow,/area/awaymission/stargate/building)
"Nr" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
"Nv" = (/obj/machinery/light{dir = 4; light_color = "#c1caff"},/turf/open/floor/mineral/basaltstone_floor,/area/awaymission/stargate/building)
-"NA" = (/obj/structure/table/abductor,/obj/item/surgical_drapes,/obj/item/scalpel/alien,/obj/item/cautery/alien,/obj/item/circular_saw/alien,/obj/item/hemostat/alien,/obj/item/retractor/alien,/obj/item/surgicaldrill/alien,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"ND" = (/obj/structure/mirror,/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
"NN" = (/obj/effect/decal/cleanable/blood/gibs/torso,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"NR" = (/obj/machinery/processor,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"NU" = (/obj/structure/barricade/wooden,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"Oi" = (/turf/closed/wall/mineral/titanium,/area/awaymission/stargate/building)
-"Ol" = (/obj/structure/bonfire,/turf/open/indestructible/cobble,/area/awaymission/stargate)
-"Om" = (/obj/machinery/door/airlock/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"On" = (/obj/structure/curtain,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Op" = (/obj/structure/closet/crate/wooden,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Ov" = (/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
@@ -355,15 +458,15 @@
"OE" = (/turf/open/floor/wood,/area/awaymission/stargate)
"OK" = (/obj/structure/rack/shelf,/obj/item/storage/box/lethalslugs,/obj/item/storage/box/lethalslugs,/obj/item/storage/box/lethalslugs,/obj/item/storage/box/lethalslugs,/obj/item/storage/box/lethalslugs,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"OM" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"OZ" = (/obj/machinery/abductor/experiment{team_number = 100},/turf/open/floor/plating/abductor{initial_gas_mix = "o2=14;n2=23;TEMP=300"},/area/awaymission/stargate/building)
+"Pd" = (/obj/structure/table/wood/fancy,/obj/item/seeds/watermelon/milk,/obj/item/seeds/watermelon/milk,/obj/item/seeds/watermelon/milk,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Ph" = (/obj/structure/barricade/sandbags,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"Pi" = (/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"Pw" = (/obj/structure/fence{dir = 4},/turf/open/indestructible/cobble,/area/awaymission/stargate)
"Pz" = (/obj/structure/table/wood,/obj/item/pickaxe,/obj/item/pickaxe,/obj/item/shovel,/obj/item/shovel,/turf/open/floor/wood,/area/awaymission/stargate/building)
"PA" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"PC" = (/obj/structure/table,/turf/open/floor/mineral/titanium/white,/area/awaymission/stargate/building)
"PD" = (/obj/structure/table/wood,/obj/item/storage/bag/ore,/obj/item/storage/bag/ore,/obj/item/mining_scanner,/obj/item/mining_scanner,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"PG" = (/obj/structure/barricade/sandbags,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"PG" = (/obj/structure/table/wood,/obj/item/storage/box/beakers,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"PR" = (/mob/living/simple_animal/hostile/netherworld,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"PS" = (/obj/machinery/light{light_color = "#e8eaff"},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
"PT" = (/obj/structure/flora/grass/jungle,/mob/living/simple_animal/butterfly,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"PW" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
@@ -372,36 +475,42 @@
"Qv" = (/turf/open/floor/grass,/area/awaymission/stargate)
"Qx" = (/obj/structure/chair/wood,/turf/open/floor/mineral/gold,/area/awaymission/stargate/building)
"QA" = (/obj/structure/flora/junglebush,/turf/open/floor/grass,/area/awaymission/stargate)
-"QM" = (/obj/effect/decal/cleanable/blood/gibs,/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"QF" = (/obj/structure/flora/grass/jungle,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"QN" = (/obj/effect/decal/cleanable/blood/tracks{dir = 8},/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"QZ" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Rb" = (/obj/machinery/rnd/destructive_analyzer,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"Rf" = (/mob/living/simple_animal/hostile/retaliate/clown/lube,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"Rj" = (/obj/structure/chair/comfy/shuttle{dir = 1},/turf/open/floor/mineral/titanium/yellow,/area/awaymission/stargate/building)
"Rq" = (/mob/living/simple_animal/butterfly,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"Rt" = (/obj/effect/decal/cleanable/blood,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"Rx" = (/obj/machinery/vending/cigarette/beach,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"Ry" = (/obj/structure/table/wood,/obj/item/storage/backpack/duffelbag/med/surgery,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Rx" = (/obj/machinery/vending/cigarette{extended_inventory = 1; free = 1},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"Ry" = (/obj/structure/table/wood,/obj/item/storage/backpack/duffelbag/med/surgery,/obj/item/flashlight/lantern{icon_state = "lantern-on"},/turf/open/floor/wood,/area/awaymission/stargate/building)
"RC" = (/obj/structure/pole,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
"RL" = (/obj/structure/table/wood,/obj/item/storage/fancy/candle_box,/obj/item/lighter,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"RM" = (/turf/closed/indestructible/sandstone,/area/awaymission/stargate/building/mountain)
"RO" = (/obj/machinery/vending/kink{free = 1},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"RS" = (/obj/structure/flora/grass/jungle/b,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"RT" = (/obj/structure/flora/grass/jungle/b,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
"RX" = (/obj/structure/chair/sofa/corner{dir = 8},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
-"Sh" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/indestructible/cobble,/area/awaymission/stargate)
+"Ss" = (/obj/effect/decal/cleanable/semen,/obj/structure/flora/grass/jungle/b,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Su" = (/mob/living/simple_animal/hostile/retaliate/clown/clownhulk/honcmunculus,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
+"SE" = (/obj/effect/decal/cleanable/blood/gibs/body,/mob/living/simple_animal/hostile/retaliate/clown/lube,/turf/open/floor/cobble,/area/awaymission/stargate)
"SF" = (/obj/structure/table/wood,/obj/item/kitchen/knife/ritual,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"SI" = (/obj/item/storage/box/rubbershot{pixel_x = -3; pixel_y = 3},/obj/item/storage/box/rubbershot{pixel_x = -3; pixel_y = 3},/obj/item/storage/box/rubbershot,/obj/item/storage/box/rubbershot,/obj/item/storage/box/rubbershot{pixel_x = 3; pixel_y = -3},/obj/structure/rack/shelf,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"SP" = (/obj/machinery/door/airlock/wood/glass,/obj/structure/barricade/wooden/crude,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Tb" = (/obj/structure/chair/sofa/corner{dir = 4},/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"Te" = (/mob/living/simple_animal/hostile/retaliate/clown/lube,/turf/open/floor/concrete,/area/awaymission/stargate)
"Tn" = (/obj/structure/table/wood/fancy,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"Tu" = (/mob/living/simple_animal/butterfly,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"Tv" = (/obj/structure/flora/tree/palm,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
-"TD" = (/obj/effect/decal/remains/xeno,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"TC" = (/mob/living/simple_animal/hostile/retaliate/clown/clownhulk/destroyer,/turf/open/floor/cobble/side{dir = 1; icon_state = "cobble_side"},/area/awaymission/stargate)
+"TD" = (/obj/effect/decal/remains/xeno,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"TE" = (/obj/machinery/deepfryer,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"TG" = (/obj/item/grown/log/tree,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"TI" = (/obj/structure/flora/tree/palm,/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate)
"TM" = (/obj/machinery/rnd/production/circuit_imprinter,/obj/item/reagent_containers/dropper,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"TR" = (/obj/structure/mineral_door/woodrustic,/turf/open/floor/carpet,/area/awaymission/stargate/building)
"TX" = (/obj/effect/decal/cleanable/blood/innards,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
+"Ub" = (/obj/structure/table/wood,/obj/item/reagent_containers/glass/bottle/mutagen,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Uc" = (/obj/structure/flora/junglebush/large,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"Ue" = (/obj/structure/flora/rock/pile/largejungle,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate)
"Um" = (/obj/machinery/light{dir = 1; light_color = "#d1dfff"},/obj/structure/reagent_dispensers/water_cooler,/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
@@ -410,51 +519,54 @@
"UC" = (/turf/closed/indestructible/sandstone,/area/awaymission/stargate/building)
"UF" = (/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"UG" = (/obj/effect/spawner/structure/window/shuttle,/turf/open/floor/plating,/area/awaymission/stargate/building)
-"UI" = (/obj/structure/bed,/obj/item/bedsheet/grey,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"UH" = (/turf/open/pool,/area/awaymission/stargate/building)
+"UI" = (/obj/effect/decal/cleanable/blood,/obj/structure/chair/wood{dir = 8},/turf/open/floor/wood,/area/awaymission/stargate/building)
+"UM" = (/mob/living/simple_animal/hostile/retaliate/clown/lube,/turf/open/floor/concrete/smooth,/area/awaymission/stargate)
"UN" = (/obj/machinery/biogenerator,/turf/open/floor/wood,/area/awaymission/stargate/building)
+"Vd" = (/obj/structure/flora/junglebush,/turf/open/floor/grass,/area/awaymission/stargate/building)
"Vh" = (/obj/structure/flora/junglebush/b,/mob/living/simple_animal/butterfly,/turf/open/floor/grass,/area/awaymission/stargate)
"Vk" = (/obj/structure/table/plasmaglass,/obj/structure/table/plasmaglass,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"Vl" = (/obj/effect/decal/remains/xeno,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"Vx" = (/obj/effect/decal/cleanable/semen,/obj/structure/table/optable/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"Vy" = (/mob/living/simple_animal/hostile/retaliate/clown/fleshclown,/turf/open/floor/mineral/titanium,/area/awaymission/stargate/building)
"VG" = (/obj/structure/table/plasmaglass,/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
"VJ" = (/obj/structure/table/wood,/obj/machinery/microwave,/turf/open/floor/wood,/area/awaymission/stargate/building)
"VM" = (/obj/structure/table/reinforced,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
-"VU" = (/obj/structure/barricade/wooden,/turf/open/indestructible/cobble/side{dir = 4},/area/awaymission/stargate)
"VY" = (/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate)
"VZ" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Wa" = (/obj/structure/bed,/obj/effect/decal/cleanable/semen,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"Wh" = (/turf/open/floor/carpet/royalblack,/area/awaymission/stargate/building)
+"Wx" = (/obj/structure/chair/stool/alien,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"WB" = (/obj/machinery/gibber,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"WJ" = (/obj/structure/closet/crate/coffin/metalcoffin,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"WC" = (/obj/effect/decal/cleanable/greenglow,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
"WL" = (/obj/machinery/mineral/unloading_machine{dir = 1; icon_state = "unloader-corner"; input_dir = 1; output_dir = 2},/turf/open/floor/wood,/area/awaymission/stargate/building)
"WO" = (/obj/machinery/mineral/processing_unit_console,/turf/closed/wall/mineral/sandstone,/area/awaymission/stargate/building)
-"WR" = (/obj/machinery/gateway{dir = 9},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
-"WU" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/indestructible/cobble/side,/area/awaymission/stargate)
+"WR" = (/obj/structure/table/wood,/obj/machinery/cell_charger,/turf/open/floor/wood,/area/awaymission/stargate/building)
"WW" = (/obj/machinery/vending/boozeomat/all_access,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
-"Xg" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate/building/mountain)
-"Xh" = (/obj/effect/decal/cleanable/semen,/obj/structure/table/optable/abductor,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
+"Xg" = (/mob/living/simple_animal/hostile/skeleton,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"Xi" = (/obj/structure/mineral_door/wood,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Xp" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"Xr" = (/obj/structure/barricade/sandbags,/turf/open/indestructible/cobble,/area/awaymission/stargate)
"XE" = (/obj/structure/flora/tree/palm,/obj/structure/flora/ausbushes/ppflowers,/turf/open/floor/grass,/area/awaymission/stargate)
"XF" = (/obj/structure/bonfire,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
"XH" = (/obj/structure/barricade/wooden,/turf/open/floor/plating/asteroid,/area/awaymission/stargate)
-"XI" = (/obj/machinery/light{dir = 8},/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
-"XJ" = (/obj/machinery/gateway{dir = 10},/turf/open/floor/mineral/crimsonstone_floor,/area/awaymission/stargate/building)
+"XJ" = (/obj/effect/decal/cleanable/blood/gibs/body,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"XW" = (/obj/machinery/door/airlock/wood,/turf/open/floor/carpet/red,/area/awaymission/stargate/building)
"Yg" = (/obj/structure/chair/comfy/shuttle{dir = 1},/obj/machinery/light,/turf/open/floor/mineral/titanium/blue,/area/awaymission/stargate/building)
"Yo" = (/obj/machinery/vending/hydroseeds,/turf/open/floor/wood,/area/awaymission/stargate/building)
"Yv" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/carpet/orange,/area/awaymission/stargate/building)
-"Yw" = (/obj/effect/decal/cleanable/blood/old,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate/building/mountain)
-"YN" = (/obj/item/kitchen/knife/combat/bone,/turf/open/floor/plating/dirt/dark/jungle,/area/awaymission/stargate/building/mountain)
+"Yw" = (/obj/effect/decal/cleanable/blood/old,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
+"YN" = (/obj/item/kitchen/knife/combat/bone,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
"YP" = (/obj/machinery/conveyor{dir = 8; id = "mining_internal"},/obj/structure/plasticflaps,/turf/open/floor/wood,/area/awaymission/stargate/building)
"YQ" = (/obj/structure/closet/crate/wooden,/obj/item/stack/sheet/mineral/sandstone/twelve,/obj/item/stack/sheet/mineral/sandstone/twelve,/turf/open/floor/wood,/area/awaymission/stargate/building)
"YS" = (/obj/structure/table/wood,/obj/item/mop,/obj/item/reagent_containers/glass/bucket,/obj/item/soap,/turf/open/floor/wood,/area/awaymission/stargate/building)
-"Za" = (/mob/living/simple_animal/hostile/jungle/mook,/turf/open/indestructible/cobble/side{dir = 1},/area/awaymission/stargate)
"Zh" = (/obj/structure/table/wood,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
+"Zk" = (/obj/effect/decal/cleanable/greenglow,/turf/open/floor/mineral/abductor,/area/awaymission/stargate/building)
"Zl" = (/obj/structure/flora/grass/jungle,/turf/open/floor/grass,/area/awaymission/stargate)
+"Zp" = (/obj/structure/table/wood/fancy,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/obj/item/reagent_containers/rag/towel,/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
"Zq" = (/obj/machinery/light,/turf/open/floor/mineral/bananium,/area/awaymission/stargate/building)
"ZM" = (/obj/structure/chair/wood{dir = 4},/turf/open/floor/mineral/sandstone_floor,/area/awaymission/stargate/building)
-"ZW" = (/obj/structure/bonfire,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"ZP" = (/obj/structure/flora/grass/jungle/b,/mob/living/simple_animal/hostile/jungle/mook,/turf/open/floor/plating/dirt/jungle,/area/awaymission/stargate/building/mountain)
+"ZW" = (/obj/structure/bonfire,/turf/open/floor/plating/asteroid,/area/awaymission/stargate/building/mountain)
(1,1,1) = {"
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
@@ -466,131 +578,131 @@ aaaaabababababababababababababababababababababababababababababababababababababab
aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsababababababababababababababababababababababababababababababababababababLsLsababLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsabababababababababababababababababababababababababababababLsababLsLsLsLsLsLILsLsLsLsabababababababababababababababababababLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLILsLsLsLsLsLsLsabababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsabLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsabababababLsabLsababababLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLskeLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsababababababababababababababababababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsababLsLsLskeLsLsLsLILsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLsaWLsLsLsLsLsababababababLsLsLsLsLILsBRLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsLskeLsLsBRLsLsaWLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLILsLsLsLsLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLILsLsLsLsLsLsLsLsLILsLsLsLsLsLILsLsLsLILsLsLsaWLsLsLsLILsLsLsLsabababLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLILsBRLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLskeLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsBRLsLsLsLsLskeLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsLsLILsLsLsLsLsLsOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvLsLsLsLskeLsLsLsLsLsLsabababLsLsLsLsLsLBLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababLsLsLsLsLsLsLsLsLsLsabababababababLsLsLsLsLsLsLsLsLsLsLsLsLsUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsBRLsLsLsLsLsLsLsOvKYUFTnOvKYUFTnOvkQcsOvKYUFTnOvKYUFTnOvLsLsLsLsLsLsLsLsabababababababLsLsLsLsLILsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsBRLsabababababababababLsababLsLsLsLsLsLsLsLsUCrXrXDDvzyOvzvzrXrXUCWJNhBBNhWJUCwPPiUCNhNhNhNhPWNhNhNhNhUCLsLsLsLILsBRLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLskeLsLsLsLsLsLsLsLskeLsLsLsOvGVUFWaOvGVUFWaOveQVZOvvMUFDzOvvMUFDzOvLsLsLILsLILsLsababababababababLsLsLsLsLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsLsLsLsLsLsBRLILsabababababababababababababLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLILsLsUCrXrXnRQxjFQxnRrXrXUCNhNhOMNhNhmtPiqCUCNhEhNhRtNhNhJbNhBeUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLILsLsOvUFUFUFOvUFUFUFOvaqcsOvUFUFUFOvUFUFUFOvLsLsLsLsLsLsababababababababababLsLsLsOvOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsababababababababababababababLsLsLsLsLsLsLsUCMxrXrXrXrXrXrXrXNvUCWJNhWJNhWJUCPiQgUCNhNhPibQPiPiPiNhNhUCLsLsLsLsLsLsLsLsLsLILsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLILsLBLsLsaWLsLsLsLsLsOvOvXWOvOvOvXWOvOvOvSPOvOvXWOvOvOvXWOvOvLsLsLsLsLsLsababababababababababLsLsLsOvRylgvcOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsLsUCrXNrrXPiPiPirXrXrXUCUCUCUCUCUCUCJcPiUCNhBeJcWRDfFIPiNhNhUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvDrWhvOWhWhWhACWhWhWhWhACWhWhWhWhWhWhOvLsLsLsLsababababababababababababLsLsLsOvcsQZcsOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsLsLsabababababababababababababababababLsLsLsLsababababababababababababababLsLskeLsLsLsLsLsUCNhNhNhPiPiPiPiPiPiJmPiQgPiPibQPiPiqCUCoXNhPiIvoSLpPiRteZUCLsLsLsLsLsLsLsLsLsLsLsLskeLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLsOvWhWhWhWhWhWhWhWhvOWhWhWhWhvOWhWhWhWhOvLsLsLsabababababababababababababLsLsLsOvcscscsOvLsLsLsLsLsLsLsLskeLsLsLsLsabababababababababababababababababababababLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsLsUCNhNhNhPiPiPiPiPiPiJmkpwPPiJcPiPiPiPiUCNhEhwPXJFrmBPiNhNhUCLsLsBRLsLsLskeLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsOvOvsnOvOvOvOvOvOvOvOvOvOvOvOvOvOvsnOvOvLsLsLsababababababababababababLsLsLsLsOvOvfNOvOvOvOvOvOvLsLsLsLsLsLsLsLsabababababababababababababababababababababababLsLsLsLILsLsabababababababababababababLsLsLsLsLsLILsLsUCNhNhNhPiPiPiNhOMNhUCUCUCOmUCUCUCwPbQUCNhNhetPiLJPiJcNhNhUCLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsOvROWhROnnrUCcbLWWKmKmWWbLCcrUnnROWhROOvLsLsLsabababababababababababLskeLsLsLsOvcscsIaUILqcsEnOvLsLsLsLsLsLsLsLsLsabababababababababababababababababababababLsLsLskeLsLsLsLsababababababababababababLsLsLsLsLsLsLsLsUCKGKGKGPiPiPiKGKGKGUCgnEQgngngnUCPiPiUCRtJbNhPGPGPGNhBeNhUCLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsOvDrWhWhEdEdEdEdEdEdEdYvEdEdEdEdWhWhDjOvLsLsLsLsababababababababababLsLsLsLsLsOvJXcscscsltQZmvOvLsLsLsLsLsLsLsLsababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsababababababababababababLsLILsLsLsaWLsLsUCnXNhNhPiPiPiNhNhtIUCvSgnNAgnCjUCQgqCUCNhNhNhPikpPiNhNhRtUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsaWLsLsLsLskeLsLsLsLsaWLsLsOvWhWhznnnEdYvEdEdEdEdEdEdEdEdnnznWhWhOvLsHELsLsabababababababababababLsLsLsLsOvcsKQQZcscsKQcsOvLsLsLsLsLILsLsLsabababababababababababababababababababababLsLsLBLsLsLsLsLsababababababababababababababLsLsLsLsLsLsLsUCKGKGKGPiPiPiKGKGKGUCgnFOIugngnUCPiPiUCUCUCUCcjUCcjUCUCUCUCLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLILsLsababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLILsLsLsLsLsLsLsLsLsLsLsLsOvywWhznyCnnnnnnnnnnnnnnnnnnnnyCznWhywOvLsLsLsLsabababababababababababLsLsLsLsOvJXcscscscscscsOvLsLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsLsLILsLsLsababababababababababababababLsLsLsLsLsLsLsUCNhNhNhPiPiQgNhNhNhUCCjEQNAgnCjUCPiJckMPiPiPiwPERPiPiPiUmUCLsLsLsLsLsLsLsLILsBRLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLILsLsLsLsLsLsOvoxWhWhznznznznznznznznznznznznvOWhCpOvLsLsLsLsLsLsababababababababLsLsLsLsLsOvOvOvAOOvOvAOohOvLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsLsLsLsLsLsLsababababababababababababababLsLsLskeLsLsLsUCKGKGKGPiPiPiKGKGKGUCXIFOIugngnUCPiPiPiQgPiJcPiPiPiPiPiQgUCLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsOvMDVGWhWhWhEdEdEdWhWhEdEdEdWhWhWhVGIkOvLsLsLsLsLsLsLsLsabababababLsLsLsLsLsLsvvapapcsmaapcscsOvLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLILsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsUCnXNhNhPiPiPiNhNhtIUCCjLCNAgnCjUCUCUCUCUCUCUCUCmtUCUCUCUCUCLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLILsLsLsLILsLskeLsOvbPVkWhvOWhEdRCEdWhvOEdRCEdWhWhWhfmozOvLsLsLILsLsLsLsLsabababababLsLsLsLsLsLsvvxGcscscsahtNQZOvLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababLsLsLsLILsLsUCKGKGKGPiPiPiKGKGKGUCgnFOXhEQgnUCJhPWOKNhaxPWaiNhNhmbPWSIUCLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvbPVGWhWhWhEdEdEdWhWhEdEdEdWhWhWhVGozOvLskeLsLsLsLsLsLsLsabababababLsLsLsLsLsOvxGQZcscsapcscsOvLskeLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsUCNhNhOMPiPiPiNhNhNhUCvSgngngnCjUCJhNhOMNhNhOMNhNhOMNhNhdOUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsOvTbDxWhWhWhWhWhWhWhWhWhWhWhWhWhWhxTRXOvLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsvvxGcsKQcsahtNcsOvLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsabababababababababababababLsLsLsLsLsUCHiNhNhPiPSPiNhNhHiUCoCEQMZgnOZUCayNhazNhaiNhaiNhNhwFNhaGUCLsLsLsLILsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLILsLILsLsLsLsaWLsLsLsLsLsLsOvOvOvOvOvWhtChcBZWhWhBZtChcWhOvOvOvOvOvLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLskeLsOvxGcscsQZapcscsOvLsLsLsaWLsLsLsLsLsLsLsababababLsabLsLsabLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsababababababababababababababLsLsLsLsUCUCUCUCJmqKJmUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsLsLsLsLsLsLsLsBRLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvWhWhWhWhWhvOWhWhWhWhOvLsLsLsLsLsLsaWLsLskeLsLsLsLsLsLsLsLsaWLsLsLsLsvvxGcscscsahtNcsOvLsLsLsLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsyvmTmTmTuRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLILsLskeLsLsOvRxBPWhWhWhWhWhWhBPRxOvLsLILsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsvvapapcscsapcsKQOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsabababababababababababababababLsLsLskeLsLsuIxnxnxnnyLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLBLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvOvOvOvwZOvOvwZOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvOvOvSPSPOvvvvvOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsuIxnxnxnnyLsLsLILsLskeLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsBRLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsaWLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLILsLsyvmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTuRLsLsLsLsabababababababababababababababLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsabababababababababababababababababLsBRLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsHELsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababLsLsLskeLsLsLsLsLsLILsLsLsLsLsababLsLsLsLsLsLsLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsabababababababababababababababababLsLsLsLsLsuIxnxnsYnyLsLsLsaWLsLsLsLsLsLsLskeLsLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababLsLsLskeLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsababababababababababababababababababLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsababababLsLsLsLILsLsLsLsLsLsBRLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLILsLsLsLsLsLsLsLsLsabababababababLsLsLsLsIpwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvxnxnxnxnnyLsLsLsabababababababababababababababababLsLsLsLILsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLsLsLsBRLsLsababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLILsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsuIxnxnxnnyLsLsLsLsabababababababababababababababLsLsLsLsLsLsuIxnxnxnnyLsLsBRLsLsLsLsLsLsLsLsLsLsababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsaWLsLsLsLsLsLsLsabababLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLskeLsLsababababababababababababababLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLBLsLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsaWLsLsLILsLsLsLILsLsLILsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsabababababababLsLsuIxnxnxnnyLsLsLsLsabababababababababLsababababLsLsLsLskeLsLsuIxnxnxnnyLsLsLsLsLILsLsLsLsLsababababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsababLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsHELsLsLsLsLsLsLsLsLsabababababababababababLsuIxnxnxnnyLsLsLsababababababababLsLsLsababLsLsLsLILBLsLsLsLsuIsYxnxnnyLsLILsLsLsLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsabLsabLsLsLsLsLsLsLILsLsLsBRLsLsLsLsLsLsLsLsababababLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsuIxnxnxnnyLsLsLsLsLsababababababLsLsLsabLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsababababababababababababLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsabLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababLsLsLsLsLsuIxnxnxnnyLsLILsLsLsLsLsLsababLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsuIxnxnxnnyLsLskeLsLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsaWLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababLsLsLsLsLsBRLsLILsLskeLsLsLsLsabababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsabababababLsLsLsLsaWLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsLILskeLsLsLsLsLILsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLILsLsLsLsababababLsLsLsLsLsLsLskeLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLILsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLILskeLsLsabababababababababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLILsLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLskeLsLsababababababLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnxnmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTxnxnxnxnnyLsLsLsLsLsLsLsLsacacababababababababababababLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababLsLskeLsLsLILsLsLsabLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsabababababababababLsLILsLsLsabababababLsLsLsLsLskeLsLsLsLsLsLsLsLILsLsLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLILsLsLsLsacacBIababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababLsLsLsLsababababababababababLsLsLsabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsLsLsLsabababacabababababababababababLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLskeLsLsLsLsLsLsLsabababababababababababababababababababababLsababababababababababababababababababababababababLsLsLsLILsLsLsLILsLsLsLsLsLsLsuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsLsLsLsabababacacacababababababababLsLsLsLsvuLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLILsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsaWLsLsLILsuIxnxnxnxnwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvsCLsLsLsLsLsabababacacacacabababababababLsLsLILsLsLsLsLsLsvuLsLsLILsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLsLsabLsLsLsababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsabababababacabababababababLsLsLsLsLsvuLsaELsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababLsLILsLsLsLsLsLsLsLsLsababababababMrMrMrMrXHMrMrMrMrababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLILsLsLsLsLsLsLsLILsLsLsLsLskeLsLsLsLsLsLsLsLsLskeLsLsLsLsababababacacabababababababLsLsLsLsLsLsLsLsLsLsLsLsaFLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsImLsLsLsLsabababLsLsLsLsLILsLskeLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLskeLsLsLILsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababacacababababababLsLsLsLsLsLsLsaCLBLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLskiLsLsXpLsLsLILsLsLsLsLsabLsLsLsLsImLsLsLsLsLskeLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLILsLsLsLsLsLsuIxnxnxnnyLsLsaWLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsababLsabababababacacabababababLsLsLsLsvuLsLsLsaWaDLsLsLsLsLsvuLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLBLsLskeLsLsUsLsLsLsLsLsTXLsLsLsLsLsLsXpkiLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsababababLsLsLsababLsLsLsLsLsLsLsLsababababababababababacacacacababababLsLsLsLsLsLILsLsLsLsLsLsvuLsLILsLsLsLsvuLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLILsLsLsLILsLsLsLsLsrhLsLsLILsLsLsLsaWLsLsLsLsLsLsLsLsababababababababLsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsabababababababababababababLsLsLsLsLsabababababababababababacacabababababLsLsLsvuLsLsLsLsaBLsLsLsLsLsLsLsaALsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsImLsLsLshKLsLsLsLsLsLsLsLsLsXpLsLsLsLshKLsLsLsUsLsLsLsababababababLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsaWLsLsLsLsuIxnxnxnnyLsLILsLsabababababababababababababababababLsLsLsababababababababababababacabababababLsLsLsLsLsvuLskeLsLsvuLsLsLsLsLsLILsLsLskeLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLBTXLsLsLsLBLskeLsLsLsLsLsLsLBLsLILsLsLsLsababababababLsLILsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsuIxnxnxnnyLsLsLsLsabababababababababababababababababababababababababababababababacacabababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsvuLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLskeLsXpLsLsLsXpLsLsLsLsLskebALsLsLsLsLsXFLsLskeLsLsLsLBLsLsLsabababababababLskeLsLsabLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsuIxnxnxnnyLsLsLsLsababababababababababababababababababababababababababababababacacababababababababLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsTXLsLsLBLskeLsLsIQLsLILsLsLsXpLsLsLsLsLsLsbALsLsLsLsXpLsLsLsLsababababababLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababLsLsLILsLsuIxnxnxnnyLsLsLsLsLsababababababababababababababababababababababababababababacacacabababababababababababababababLsLsLsLskeLsababLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLskiLsLsLsXFLsLsLsLsLsLILsTXLsXpLsLsLsTXLsLsLsLILsLsababababababLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsuIxnxnxnnyLsLsLsLsLsababababababababababababababababababababababababababababacacababababababababababababababababababLsLsLsLsabababababababababLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsaWLsLsXpLsLsLsLsLsLsLsLsLsImhKLskeLsLsLsLskeLsLsLsLsLsLsLsLsLsMrLsLsLsababLsLsLsLILsLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsuIxnxnxnnyLsLsLsLsLsabababababababababababababababababababababababababababababacacabababababababababababababababababababLsLsLsabLsLsababababLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsImLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLBLsLsLsLsLsImLsLsLsXFLsLsLsMrLskeLsLsLsLsLsLsLsLsLsabLsabababLsLsLsabLsabababababababababababababababababababababababababababababababababababXHXHXHXHXHsuNUNUNUVUXHXHXHXHababababababababababababababababababababababababababababababacacabababababababababababababababababababLsLsLsLILsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsLILsLsImkiLsXpLsLBLsLsaWLsLsLsLILsLBLsLsLsLsLsLsLsLsQNQNuaQNQNQNLsLILsLskeLsLsLsLsLsLsLsabLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsabababababababababababababababababababababababababacabacacacababacacababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsXpLsLsbALsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsUsLsLsLsLsLsMrLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLsLskeLsLsuIxnxnxnnyLsLsababababababababababababababababababababababababhmacacDMacacacacacacababababababababababababababababababababLsabababababLskeLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsUsLsLsLsLsLsLsLsLILsLskeLsbALsLsLskiLsLsXpLsLsLsLsLsLsLsImLsLsLsMrLsLsLsLsLsLsLsLsLsLsLsababLsLsLsLsLsLsLskeLsLIabababababababababababababababababababababababababababababababLsLsLILsLsLsLsuIxnxnxnnyLsLsabababababababababababababababababababababababacacBIacacacMkacacacacababababababababababababababababababababababababababLsLsLsLsaWLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababLsLsLsLsLBLsLsLsLsXFLsLsUsLsLsLsLsHELskiLskeLsImLsLsLsXpLsLsLsLsLsabababLsLsLsLILsLsabLsLsLsabababLsLsLskeLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLILsLsuIxnxnxnnyLsLsababababababababababababababababababababababababacacacacZWhmacBIacababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsLsLsLsLsXpLsLsLskeLsLsLsTXLsLsLsXFLsLsLsLsLsLsaWLsLsLsLBLsLsLsabababababLsLsLsLsababLsLsLsababababLsLsLsLsLsLsLsLsLsLsabLsLsLsabababababLsLsabLsLsLsabababababababababababababababLsLsLsLsLsuIxnxnxnnyLsLILsabababababababababababababababababababababababacacMkacacacacacacababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLsLsLskeLsLsLsLsababababLsLsLsLsabLsLsLsLILsabababLsLsLsLILsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsababababababababababababababababLsLsLsLsuIxnxnxnnyLsLsLsababababababababababababababababababababacacacacacBIachmDMacacacacababababababababababababababababababababLsLsLsLILsLsLsLsLskeLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababLsLsLsLsImLsLsLILsabLsLsLsLsXpLsLsLsLBLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsababLsLsLsLsababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsuIxnxnxnnykeLsLsabababababababababababababababababababacacacabacacacacacacacBIacababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababLsLsLsLsLsLsababababLsLsLsLskeLsLsLsLsLsImLsLsLsLsababababLsLskeLsLsLsabLskeLsLsababLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsOvOvOvOvOvOvOvOvOvLsLsLsLsLsababababababababababLsLsLILsLsuIxnxnxnnyLsLsLsabababababababababababababababBIacacacacabababacacabababacacacacabababababababababababababababababababababLsLskeLsLsLsLsLILsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababLsLsLsLsLsabababababLsLsLsLsLsLsLsabababababababababababLsLILsLsLsQNQNQNLsLsLsLsLsLsLsLsabababLsLsLsLsababLsLsLsLsLsLsLsOvapcsOpOpOpAzdbOvLskeLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsuIxnxnxnnyLsLsababababababababababababababacacacacacacacababababababababacabababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababLsabababababababababababababLsLsLsLsabLsLsLILsLsLsLsababababLsLsLsLsLILsLsLsLsLsLsLsLILsOvancscscscscsaoOvLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsuIxnxnxnnyLsLsLsabababababababababababababacacacacababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsabababababLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvdbcscscscscsapOvLsLsOvOvOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsababababababababababababababacacabababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsababababababLsLsLsLsabLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsOvOvOvOvXiOvOvOvOvLsLsOvdbcscsRyOvLsLILsLsLsLsLsLsLskeLsLsuIxnxnxnnyLsLsLsababababababababababababacacacababababababababababababababababababababababababababababababababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLskeLsLsLsababababababLsLsLsLsOvFcNhNhNhNhNhFcOvLsLsOvFMcscsjeOvLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsabababababababababacacacababababababababababababababababababababababababababababababababababababLsLsLsLsLILsLsLsLsaWLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababLsLsLsOvNhNhIPIPIPNhNhOvLsLsOvfUcscsapOvLsLsLsLsLsLsaWLsLsLsLsLsuIxnxnxnnyLsLILsLsLsLsabababLsLsababacacababababababababababababababababababababababababababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLIHEabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababacacacacacacacabababababababababababababababababLsLsLsLsLsLsLsLILsLsLsabababababLsLsLsOvNhZMmdadvfuANhOvLsLsOvFMcscsjeOvLsLsLsLsLsLsLsLsLsLILsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsabacacabababLsababababababababababababababababababLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababacacacacacacacacababababababababababababOvOvOvOvOvOvOvOvLsLsLsLsLsLsLsLsLsababLsLsLsLsOvNhNhKGKGKGNhNhOvLsLsOvfUcscsapOvLsLskeLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsabababLsLskeLsLILsLsabqSabLsLsLsLsLsababababababababababababababababLsLsLsLsLsLsLILsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababacacacacacacacacacababababababababOvdbPDPzFAFAdbOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvFcNhNhNhNhNhFcOvLsLsOvdbcscsjeOvLsLsLsLsLsLsLskeLsLsLsLsuIxnxnxnnyLsLsLsabababLsLsLsLsLsLskeheLBLsLsLskeLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababacacacabababacacacacacaeacacabOvcscscscscscsOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsOvOvofOvMuOvofOvOvLsLsOvOvXiOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsababLsLsLsLsLsLsheLsLsaWLsLsLsLILsababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababacacacabacacacacacvhcscscscsOvWLvvcsdbOvyvmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTxnxnxnxnnyLsLskeLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLskeLsLsabLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababacabababababababababababababababababacacacabOvcscscsmFvvFQvvcscsgIuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsLsLsLsLsabababLsLsLsLsLsabababLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababacacacacacacababababababababababacacacacabababOvcscscscsWOIevvcscsOvuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsLsLsLsLsLsLsabababLsLIabababababababLsLsLsLILsLskeLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLspVZlQvLsLsLsababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababacacacacacacababababababTDababacacacacababababOvdbcsOvvvvvFQvvcscsgIuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyLsLsLsLILsLsLsLsLsLsabababababLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsMIQAQvLsLsLsLsLsLILsLsLsQvQvuBQvQvZlLsLsababababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababacacababacacabacacacacacacacacacabababababababOvcscsYPdzdziAvvcscsOvIpwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvxnxnxnxnnyLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsQvQvZlHpQvpVQvuBLsLsLsLsHpqDQvLfQvmJQvqDLfQvababababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababacacacababacacacacabababababababababOvcscsOvOvOvOvOvcscsOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLskeLsLsLsLsLsLsQvLfQvqDQvuBLfQvLfQvQvQvZlQvQvQvZluBZlQvQvuBababababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababacacababababababababababOvcscscscscscscscscsOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsLsLsLsLsaWLskeLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsQvpVQvZlsEMITIQvQvQvMIQvmJZlQvmJnYQvMIQAQvuBQAQvZlabababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababacacabababababababababababOvdbcscscsdbcscscsdbOvLsOveecscscsOpOvLsOveecscscsOpOvLsOveecscscsOpOvLsOveecscscsOpOvLsLILsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLILILsLsLsLsLsLsLsLsLsLsLsLsLsLsQvLOQvQvMIQvQvQvpVQAQvmJHpsEuBQvcIQvQvuBQvQvsEMIHpQvQvabababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababacacacababababababababababOvOvOvOvOvOvOvOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsLsLsLsLsLsLsLsLsuIxnxnxnnyOvOvOvOvvvvvOvOvvvvvOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLspVQvQvHpQvuBfOQvmJLfQvQvQvuBZlQvQvqDfOQvsEHpQvqDmJQvQvQvsEuBHpLfQvababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababacacacacacababacacacababababababLsLsLsLsLsLsLsLsLsLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsLsOvOvOvOvOvOvOvuIxnxnxnnyOvNReJeJVJeJyMLqTEfBWBcseLOvLsLsLsLILsLsLsLsLsLsLsaWLsLsLsLsLfLsMIQvsEZlQvpVQvQvQvrCQvHpQvmJMIQvQvmJZlQvZlQvQvZlQvQvpVQvTIQvfOQvQvpVQvZlababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababacababacacacacacacacacacababababababLsLsLsLsLsLsLILsLsLsLsOvcscsOncsarOvLsOvcscsOncsasOvLsOvcscsOncsatOvLsOvcscsOncsauOvLsLsOvFcZhZhNhNhOvuIxnpAxnnyOvcscscscscscscscscscscseLOvLsLsLsLsLsLsLsLsLsLsLsLsLsZlQvQvQvQvQvqDQvQvQvQvsEQvQAQvQvmJQvQvsELfQvHpsEQvQvHpQvmJsEQvHpuBQvHpMIQvmJQvmJHpababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababacacacacacacacacababababababababababababLsLskeLsLsLsLsLsLsLskeLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsLstjNhNhNhNhNhOvuIxnxnxnnyOvnacsdbcscscscscscsdbcseLOvLsLsLsLsLsLsLsLsQvQvQvQvqDQvQvmJpVQvmJQvmJuBfOQvZlQvMIZlQvQvpVQvQvQvqDQvQvQvmJLfMIQvQvLfsELfilmJsEQvLfQvqDQvQAabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababacababacacacabababacacababababababababababababLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsOvLzNhikOvNhOvuIxnxnxnnyOvOvDFOvXiOvOvOvOvXiOvOvOvOvLsLsLsQvLfQvsEQvQvmJHpfOQvLfuBMIQvsEQvHpQvMIQvmJqDfOQvsEuBLfQvQvmJbiQvmJLfuBQvQvQvpVQvqDQvQvHpQvqDQvZlQvHpabMIabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababacacacacababababababacacababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsOvLzNhikOvNhNhuIxnxnxnnyofFcaHaHNhNhRLFcNhNhaHaHFcOvLsQvQAZlQvqDQvLfQvMIuBQvQvQvQvQvQvbiQvQvmJLfQvsEQvHpQvMIHpQvHpqDQvLfQvQvQvmJZlQvmJQvsEQvmJZlQvQAQvpVQvmJababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababacacabacababababababababababababababababababLsLsLILsaWLsLsLsLsLsOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvLsLsOvOvOvOvOvOvOvOvOvLsLsOvOvOvOvOvLsHpOvLzNhikOvFcOvuIpAxnxnnyOvNhNhNhNhNhNhNhNhNhNhNhNhofLsqDQvQvQvmJQvQvQvZlQvZlQvmJQvnYQvQvQvQAQvQvQvQvZlQvQvmJQvmJQvmJfOuBQvpVQvQvQvQvQvpVQvMIZlQvQvMCJpQvuBMIababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLskeLsOvFcNhNhNhZMZMjDFcZMjDZMZMNhNhFcNhOvLsLsOvLbcscscscscsAwOvLsLsOvdbcsYQOvqDXEOvOvOvOvOvtjOvuIxnxnxnnyMuNhNhNhIPIPIPIPIPIPNhNhNhOvQvQvMIsEHpQvQvfOQvQvmJLfQvpVQvQvMIQvmJQvmJZlmJpVQvQAQvpVQvQvZlQvQvHpQvmJQvQAQvZlQAQvKZMCMCqfMCMCMCFgMCpVqDabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsOvmeNhNhNhZMZMjDvfZMjDZMZMNhNhNhNhOvLsLsOvLbcscsdbcscsAwOvLsLsOvIJcsYQOvyvuROvLQOvLQtjdbOvuIxnxnxnnyOvvfNhZMxmxmxmxmxmxmuANhvfofHpqDLfQvuBLfQvZlQvwLQvQvQvQvsEQvfOQvqDQvqDQvHpQvsEuBQvQvsEHpQvpVQvQvQvqDQvQvsEQvQvMCMCJpMCVYVYhCMCMChCVYVYabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsRqLsLsLsLsLsLsOvNhNhjDjDjDjDjDjDjDjDjDjDjDjDadNhOvLsQvOvCtcscsyMcscsUtOvLsLfOveQcscsXiuInyOvXiNDXitjcscsuIxnxnxnnyOvvfNhZMxmxmxmxmxmxmuANhvfofQvmJQvIXQvQvilQvMIQvHpQvmJqDQvQvQvLfmJuBLfQvQvMIQvQvLfQvQvQvmJQvQvndQvLfFgMCMCdQVYMCtcFgVYryMCFgjHyZVYdQjZMCtcFgababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLskeLsLsLsLsLsLILsLsOvNhNhjDjDjDjDjDjDjDjDjDjDjDjDSFNhOvLfqDOvCtcscsAAcscsUtOvuBQvOvYScscsOvuInyOvcscscstjcsOvuIxnxnxnnyMuNhNhNhKGKGKGKGKGKGNhNhNhOvQvqDQvpVQvQvqDmJLfQvfOQvQvpVQvmJQvRTQvQAQvQvmJLfQvmJQvMIZlmJQvZlQvQvMIMCMCryagVYyAjHMCyAgChQMCyZyZyZyZyZMCKZVYabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLILsLsLsLsLsLsLfLsLsOvpmNhNhNhZMZMjDvfZMjDZMZMNhNhNhNhOvMIQAOvUtcscsdbcscsUtOvHpsEOvjXcsaOvvuInyOvnacscscscsOvuIxnxnxnnyOvNhNhNhNhNhNhNhNhNhNhNhNhofZlsEuBMIQvmJQvQvQvsEQvMIQAQvQvQvuBQvQvQvuBQvQvQvQvQvLfQvqDQvQvQvLfQvFgyAMCJpTuMCyZyZyZyZjHMCyZyZyZyZyZyZqfMChCabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababQvLfHpQvLsLsLsLsLsLsLsLsQvmJqDLsOvFcNhNhNhZMZMjDFcZMjDZMZMNhNhFcNhOvHpQvOvUtcscscscscsUtOvMIqDOvdbcslnvvuInyOvdbcscscscsOvuIxnxnxnnyofFcaHaHNhNhmxFcNhNhaHaHFcOvQvQvQvfOQvQvnYQvQvHpZlQvQvQvsEQvTIQvLfsEQvLfZlHpQvTIQvmJQvQALfQvMCJpMCMCyZKZjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHMCababababababababababMCFgqfababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababababQvabababababababababababababababQvfOuBQvLsfOLsHpQvQAMIHpfOQvZlOvOvOvofofOvOvTROvOvTROvOvofofOvOvOvQvXEOvOvvvOvXiOvvvOvOvQAQvOvOvOvOvOvuInyOvOvOvOvOvOvOvuIxnxnxnnyOvOvOvOvXiOvOvOvOvXiOvOvOvOvHppVQvQvpVQvQvQvuBuBQvmJLfQvpVQvQvqDQvmJqDQvsEQvQvQvuBQvHpQvQvMCKZMCjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAUcFgMCabababababjHJpyAUcyZJpababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababababQvQvZlQvabababababababababababQvMIpVQvoQQvoQQvZlrCQvsLsLsLsLsLsLyvmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTxnxnmTmTmTmTmTmTmTxnpAxnxnnyOvtztzcscscscscscscscstztzOvQvQvmJQvMIQvsELfQvfOQvQvQvQvQvQvMIfOQvQvHpQvMIUcFgMCMCJpMCUcMCdQVYyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHtcJpKZyAFgtcyZyZyZyZtcjHKZababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababababababQvHpQvQvsEQvabqDabQvababZlQvHpLfLfQvHpQvQvQvQvoQQvmJQvsLdbUNdTYosLuIxnxnxnxnxnpAxnxnxnxnxnxnpAxnxnxnxnxnxnxnxnxnxnpAxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyOvdbcscscscscscscscscscsdbOvMIQvQvLfQvZlQvQvMIQvQvuBqDmJHpsEQvQvLfQvMCJpVYgCtcMCFgyAMCqfMCVYVYMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAKZabyAKZqfjHababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababababZlQvQvmJLfQvMIQvQvpVHpQvQvMIuBQvQvQvqDsEHpQvmJqDQvQvQvHpsLnacscscsXiuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyOvtztzzDxKdbjfjfdbxKzDtztzOvQvLfsEQvQvmJHpQvmJQvQAQvQvLfilQvMCtcMCKZyAMCdQLKyZyZyZKZMCMCFgyAFgKZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJptcFgyZyZUcababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababababHpQvMIQvqDilQvHpQvfOuBQvQvQAHpqDQvmJfOuBQvQvafQvQvQAQvpVsEuBsLapcscsapsLuIxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnpAxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnnyOvOvOvOvOvOvOvOvOvOvOvOvOvOvQvHpQvQvpVQvQvpVQvZlQvuBMCKZMChCVYUcMCMCMCjHFgyZyZyZyZyZyAjHyZyZjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababuBQvQvLfsEQvQvMIZlQvQvQvBCMIQvQvsEQvpVQvQvQvmJQvQvmJQvQvqUQvQvsLsLsLXisLsLIpwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvIbwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvxnxnxnxnnyMIpVsEQvQvHpQvLfQvQvuBQvQvQvMIQvfOQvQvLfQvQvMCKZMCMCyAMCqfgCjZMCyAKZqfyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababQvQvfOQvMIQvQvmJLfsEQvQvmJQvHpQvLfQvQvQvQvmJLfQvsEQvHpLfqDQvQvLfQvMIHpQvpVQvqDQvZlQvQvLfQvQvMIuOZlQvqDpVQvsEQvQvpVQvqDZlQvQvqDQvHpQvZlQvmJQvfOQvQvsEMIQvfOQvZlMIQvmJpVHpuIxnxnxnnysEQvQvZlmJQAQvZlsEqDHpmJZlQvXEQvQvBCMIQvMCJpVYhQMCyZyZjHMCJpMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZababababaaaa
-aaaaababababababababababababababababababababababababababMIZlababababababababQvsEQvHpQvQvQvpVQvuBQvQvpVuBQvZlQvfOQvQvLfQvHpQvMIQvLfQvMIyTQvbCQvyTQvyTQvyTQvyTQvyTQvyTZlQvsEHpQvQvQvQvuOMIQvLfQvmJQvsEQvQvMIfOQvsEMIelQvuBQvLfQvqDsWQvpVQvQvsEQvLfqDQvsEuBuIxnxnxnnyQvqDQAQvqDQvHpQvQvQvQvQvLfQvQvQvyAMCMCjZVYVYVYMCUcyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZababababaaaa
-aaaaababababababababababababababababababababababababababQvLfQvHpabababababZlQvQvMIQvqDQvmJQvQvQvHpQAQvQvLfsEQvMIQvmJQvQAqDQvfOQvQvqUuBQvQvQvQvQvQvQvQvQvQvilQvQvQvQvQvuBQvqUQvnYQvQvZlQvuOQvelQvuByvmTmTmTuRpVQvQvQvHpQvmJMIsEHpuBQvQvMCtcQvqDmJuBQAQvZluIxnxnxnnyQvZlQvuBQvmJQvQvmJLfpVMIQvVYVYqDKZMCJpVYhtVYjZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCjHFgyZyZyZyZyZyZyZyZUcyZyZKZqfjHyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZababababaaaa
-aaaaababababababababababababababababababababababababababqDHpsEQvpVQvababqDQvQAHpQvpVsEQvuBHpQvmJQvQvMIQvQvqDZlQvQvQvHpQvZlQvQvmJHpZlQvyTQvyTQvyTQvyTQvyTQvyTQvyTQvyTQvQAQvQvQvQvuOuBQvLfQvQvQvQvHpuIAlTGxnnyQvQvmJpVQvKZyAMCtcMCKZZlMCJpMCyAQvHpQvsEHpQvuIxnxnxnnyQvmJQvLfsEMILfQvQvhCVYMCMChQVYyAMCMCyAVYVYVYVYyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZKZjHMCMCyAMChQVYdQjHyZyZjHyZyAyZMCFgJpyAababKZtcFgyZyZyZjHFgtcJpyZyZyZyZyZyZyZyAababababaaaa
-aaaaabababababababababababababababababababababababababZlQvMIQvQvQvMIfOQvQvZlQvQvQvQvQvLfQvQvLfQvHpfOQvmJHpQvQvQAQvpVQvQvFgMCJpQvsEQvuBQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvqDmJZlQvJpMCKZQvLfHpMImJQvgcTGOlTGnyLfQvQAQvJpMCVYryMCJpMCyAKZqfMCMCZlfOQvmJMIQAuIxnxnxnnyLfQvHpqDQvKZMCqfMCVYryMCJpMCgCjHFgMCyZyZyZjHyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyAMCtcMCMCyAMCMCMCgCVYVYMCMCtcMCMCKZMCyAabababababababjHqfUcyAKZababKZqfUcyAyZyZyZqfJpababababaaaa
-aaaaababababababababababababababababababababababababababQvmJpVQvmJHpQvQvHpQvHpLfQvHpQvQvyFQvqDMIQvQvuBLfQvfOQvqDLfQvMCKZMCqfMCMCKZJpQvyTQvyTQvyTQvyTQvyTQvyTQvbCQvyTQvLfQvMIQvMCMCMCtcMCUcQvqDQvmJuIxnTGxnnyQvZlQvQvUcMCqfMCFgMCyZjHFgyZMCUcMCuBHpqDpVQvuIxnxnxnnyuBQvfOQvVYdQMCFgMCtcMCyAyZyAjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCKZMCMCMCKZQvFgqDMCMCTuhtVYgCMCUcagMCJpMCabababababababababababababababababJpKZtcyAFgabababababaaaa
-aaaaabababababababababababababababababababababababababababQvQvLfpVQvsEpVQvmJqDQvmJsEQvpVQvMIsEQvmJZlQvQvQvQvMIuBtcMCJptcFgMCUcyAiXMCUcQvQvHpQvpVQvQvHpQvZlQvfOQvuBQvHpMCMCtcKZMCagVYFgMCVYVYHpZlQvIpwvwvwvsCqDQvMCtcVYMCKZyZyZyAyZyZyZyZyAMCKZqfQvLfQvFguIxnxnxnnyQvsEUcKZVYLKyZyZKZMCjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCjHVYryagMCFgQvmJQvMIfOQvQvyAMCMCMCMCyAMCVYMCLfQvfOababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababfOZlQvQvQvsMQvQvQvQvuBQvfOMIQvsWQvQvqDQvQvmJpVQvsWQvHpMCKZjHyZyZyZyZyZjHtcMCMCKZqfMIQvqUQvMIQvmJqDHpQvLfQvMCFgyAMCMCUcVYVYKZtcMCyAKZJpQvLfQvMImJuBelQvMCFgLKyAyZyZyZyZyZyZyZyZyZyZyZjHKZJpLKUcuIxnxnxnnyKZJpjHMCyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAjHMCJpyAVYVYVYKZQvqDQvLfHpuBQvmJQvLfMCUcMCMIsEfOQvelHpQvababababababababababababababababababababababababababaaaa
+aaaaababababababababUCUCUCUCUCUCUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCalrXawrXrXUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCrXbEbJbKrXUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCrXbMbNbOrXUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCrXbTbVbWalUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCbXrXJcrXrXUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaababababababababUCUCUCbYUCUCUCababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCJbPiRtUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPiNhUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhbZJbUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhcacpUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcyPiNhUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsababababababababababababababababababababababababababababababababababababLsLsababLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCakPiRtUCabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsabababababababababababababababababababababababababababababLsababLsLsLsLsLsLILsLsLsLsabababababababababababababababababababLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCakakNhUCabababababababababababababababLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLILsLsLsLsLsLsLsabababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsabLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajajakakUCababababababababababababababLsLsLsBRLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsabababababLsabLsababababLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajajajakUCabababababababababababababLsLskeLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsababababababababababababababababababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsababLsLsLskeLsLsLsLILsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajajakakUCababababababababababababLsLsLsLsLsLsLsaWLsLsLsLsLsababababababLsLsLsLsLILsBRLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajamakakUCababababababababababababLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsLskeLsLsBRLsLsaWLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLILsLsLsBRLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajakakajajajababababababababababababLsLsLsLILsLsLsLsLsLsLsLsLILsLsLsLsLsLILsBRLsLILsLsLsaWLsLsLsLILsLsLsLsabababLsLILsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLILsBRLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLskeLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsBRLsLsLsLsLskeLsLsLsLsLsLsLILsLsBRLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajakakakajajajabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLILsLsLsBRLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsBRLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajakakakakakajajajabababababababababababLsLsLsLsLsLsLsLILsLsLsLsBRLsUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsBRLsLskeLsBRLsLsLsLsabababLsLsBRLsLsLBLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababLsLsLsLsLsLsLsLsLsLsabababababababLsLsLsLsLsLsLsLsLsLsLsLsLsUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajakakamakakakakajabababababababababababLsLsLsBRLsLsBRLsLsLsLsLsLsLsUCKYUFTnUCKYUFTnUCkQcsUCKYUFTnUCKYUFTnUCLsLsLsLsLsLsLsLsabababababababLsLsLsLsLILsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsBRLsabababababababababLsababLsLsLsLsLsLsLsLsUCrXrXDDvzyOvzvzrXrXUCazaHaIaJaKUCwPPiUCNhNhczeGjaeGczNhNhUCLsLsLsLILsBRLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababajajakakakakakajajajajababababababababLsLskeLsLsLsLsLsLsLsLskeLsLsLsUCGVUFWaUCGVUFWaUCeQVZUCvMUFDzUCvMUFDzUCLsLsLILsLILsLsababababababababLsLsLsLsLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsLsLsLsLsLsBRLILsabababababababababababababLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLILsLsUCrXrXnRQxjFQxnRrXrXUCNhNhOMNhNhmtPiqCUCNhEhczltczczmvNhBeUCLsBRLsLsLsLsLsLsLsLsLsBRLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabababababababababajajajajakakajajakakajababababababababLsLsLsLsLsLsLsLsLsLsLsLsLILsLsUCUFUFUFUCUFUFUFUCaqcsUCUFUFUFUCUFUFUFUCLsLsLsLsLsLsababababababababababLsLsLsUCUCUCUCUCLsLsLsLsLsLsLsLsLsBRLsLsLILsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsababababababababababababababLsLsLsLsLsLsLsUCMxrXrXrXrXrXrXrXNvUCaLZMvfuANhUCPiQgUCmBmBPibQPiPiPimBmBUCLsLsLsLsLsLsLsLsLsLILsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaababababababababajajakajajajakakakakakajababababababababLsLsLsLsLILsLBLsLsaWLsLsLsLsLsUCUCXWUCUCUCXWUCUCUCSPUCUCXWUCUCUCXWUCUCLsLsLsLsBRLsababababababababababLsLsLsUCRylgvcUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsBRLsUCrXNrrXPiPiPirXrXrXUCUCUCUCUCUCUCJcPiUCohqBJcrXrXrXPimBwZUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababajajakakakakajakakamakajajabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsUCDrWhvOWhWhWhACWhWhWhWhACWhWhWhWhWhWhUCLsLsLsLsababababababababababababLsLsLsUCcsQZcsOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsLsLsabababababababababababababababababLsBRLsLsababababababababababababababLsLskeLsLsLsLsLsUCNhNhNhPiPiPiPiPiPiJmPiQgPiPibQPiPiqCUCDfmBPirXoSrXPiFrFIUCLsLsLsLsLsLsLsLsLsLsLsLskeLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababajajakakakakakakakajajajababababababababababLsLsLsLsBRLsLsLsBRLsLsLsLsLsUCWhWhWhWhWhWhWhWhvOWhWhWhWhvOWhWhWhWhUCLsLsLsabababababababababababababLsLsLsUCcscscsUCLsLsLsLsLsLsLsLskeLsLsLsLsabababababababababababababababababababababLsLsLsLsLsLsLsabababababababababababababLsBRLsLsLsLsLsLsUCNhNhNhPiPiPiPiPiPiJmkpwPPiJcPiPiPiPiUCohIvwPrXrXrXPimBKcUCLsLsBRLsLsLskeLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaababababababajajakakajakamakakakajajajabababababababababLsLsLsLsLsLsLsLsLsLsLIBRLsLsLsUCUCsnUCUCUCUCUCUCUCUCUCUCUCUCUCUCsnUCUCLsBRLsababababababababababababLsLsBRLsUCUCfNUCUCUCUCUCUCLsLsLsLsLsLsLsLsabababababababababababababababababababababababLsLsLsLILsLsabababababababababababababLsLsLsLsLsLILsLsUCNhNhNhPiPiPiNhOMNhUCUCUCaMUCUCUCwPbQUCmBmBetPiLJPiJcmBmBUCLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaababababababajakakakajajakajajajajababababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsUCROWhROLprUCcbLWWKmKmWWbLCcrUnnROWhROUCLsLsLsabababababababababababLskeLsLsLsUCcscsIadbPGcsEnUCLsLsLsLsLsLsLsLsLsabababababababababababababababababababababLsLsLskeLsLsLsLsababababababababababababLsLsLsLsBRLsLsLsUCKGKGKGPiPiPiKGKGKGUCaNaPNhaPaNUCPiPiUCRtJbNhPiPiPiNhBeNhUCLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababajamakakajajajajajababababababababababababLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsUCDrvOWhEdEdEdEdEdEdEdYvEdEdEdEdWhvODjUCLsLsLsLsababababababababababLsLsLsLsLsUCJXcscscsQZcsapUCLsLsBRLsLsLsLsLsababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsababababababababababababLsLILsLsLsaWLsLsUCnXNhNhPiPiPiNhNhtIUCoXNhOMNhNhUCQgqCUCNhNhNhPikpPiNhNhRtUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
+aaaaababababababajajakakakakajajababababababababababababababLsLsaWLsLsLsLskeLsLsLsLsaWLsLsUCWhWhznnnEdYvEdEdEdEdEdEdEdEdnnznWhWhUCLsHELsLsabababababababababababLsLsLsLsUCUbUIQZcscsKQEnUCLsLsLsLsLILsLsLsabababababababababababababababababababababLsLsLBLsLsLsLsLsababababababababababababababLsLsLsLsLsLsLsUCKGKGKGPiPiPiKGKGKGUCNhNhNhNhNhUCPiPiUCUCUCUCcjUCcjUCUCUCUCLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLILsLsababababababababababababababababababababababababaaaa
+aaaaababababababajajajakakajajajababababababababababababababLsLsLILsLsLsLsLsLsLsLsLsLsLsLsUCywWhznyCnnnnnnnnnnnnnnnnnnnnyCznWhywUCLsLsLsLsabababababababababababLsLsLsLsUCWRcscscscscsapUCLsLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsLsLILsLsLsababababababababababababababLsLsLsLsLsLsLsUCNhNhNhPiPiQgNhNhNhUCNhvfNhvfNhUCPiJckMPiPiPiwPERPiPiPiUmUCLsLsLsLsLsLsLsLILsBRLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
+aaaaababababababababajakakakakajababababababababababababababLsLsLsLsLsLsBRLsLILsLsLsLsLsLsUCoxWhWhznznznznznznznznznznznznvOWhCpUCLsLsLsLsLsLsababababababababLsLsLsLsLsOvOvOvAOOvOvAOOvUCLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsLsLsLsLsLsLsababababababababababababababLsLsLskeBRLsLsUCKGKGKGPiPiPiKGKGKGUCaQaRNhaRNhUCPiPiPiQgPiJcPiPiPiPiPiQgUCLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsababababababababababababababababababababababababaaaa
+aaaaababababababababajUCakakakajabababababababababababababLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsUCMDVGWhWhWhEdEdEdWhWhEdEdEdWhWhWhVGIkUCLsLsLsLsLsLsLsLsabababababLsLsLsLsLsLsvvdbapcsmadbcscsOvLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLILsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsUCnXNhNhPiPiPiNhNhtIUCNhvfNhvfOMUCUCUCUCUCUCUCUCmtUCUCUCUCUCLsLskeLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsababababababababababababababababababababababababaaaa
+aaaaabababababababababUCXJamakajababababababababababababLsLsLsBRLsLsLsLsLILsLsLsLILsLskeLsUCbPVkWhvOWhEdRCEdWhvOEdRCEdWhWhWhfmozUCLsLsLILsLsLsLsLsabababababLsLsLsBRLsLsvvxGcscscsahtNQZOvLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababLsLsLsLILsLsUCKGKGKGPiPiPiKGKGKGUCNhaROMaRNhUCJhPWOKNhaSPWaiNhNhmbPWSIUCLsLsLsLsLsBRLsLsLskeLsLsLILsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPiakUCabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsUCbPVGWhWhWhEdEdEdWhWhEdEdEdWhWhWhVGozUCLskeLsLsLsLsBRLsLsabababababLsLsLsLsLsOvxGQZcscsapcscsOvLskeLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsBRLsLsLsLsLsBRBRLsLsLsabababababababababababababLsLsLsLsLsLsUCNhNhOMPiPiPiNhNhNhUCoXLMNhvfNhUCayNhOMNhNhOMNhNhOMNhNhdOUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCJbPiNhUCabababababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsUCTbDxWhWhWhvOWhWhWhWhWhWhWhvOWhWhxTRXUCLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsvvxGcsKQcsahtNcsOvLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsabababababababababababababLsLsLsLsLsUCHiNhNhPiPSPiNhNhHiUCNhaRNhaRNhUCayNhaSNhaiNhaiNhNhwFNhdOUCLsLsLsLILsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcpcacyUCabababababababababababababLsLsLILsLILsLsLsLsaWLsLsLsLsBRLsUCUCUCUCUCWhtChcBZWhWhBZtChcWhUCUCUCUCUCLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLskeLsOvxGcscsQZapcscsOvLsLsLsaWLsLsLsLsLsLsLsababababLsabLsLsabLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsBRLsababababababababababababababLsLsLsLsUCUCUCUCJmqKJmUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsLsLsLsLsLsLsLsBRLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcyPiJbUCababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsUCWhWhWhUCUCUCUCWhWhWhUCLsLsLsLsLsLsaWLsLskeLsLsLsLsBRLsLsLsaWLsLsLsLsvvxGcscscsaptNcsOvLsLsLsLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsaTaUaUaUaVLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcyPiRtUCababababababababababababLsLsBRLsLsLsLskeLsLsLsLsLsLsLsLILsLskeLsLsUCRxBPWhUCyvuRUCWhBPRxUCLsLILsLsLsBRLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsvvdbapcscsdbcsKQOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsabababababababababababababababLsLsLskeLsLsuIaXaXaXaYLsLsLsLsLsLsLsLILsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPiNhUCababababababababababababLsLsLsLsLsLBLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsUCUCUCpIUCuIaYUCpIOvUCUCLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvOvOvSPSPOvvvvvOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsuIaXaXaXaYLsLsLILsLskeLsLsLsLsLsLsLsLsLsLsLILsLsBRLsLsLsLsLsBRLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhwPXJUCababababababababababababLsLsaWLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLILsLsaTaUaUFwaXaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaVLsLsLsLsabababababababababababababababLsLsLsLsLsBRuIaXaXaXaYLsLsLsLsBRLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhJcNhUCabababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsLsabababababababababababababababababLsBRLsLsLsuIaXaXaXaYLsLsLsLsLsLsLsLsHELsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPiRtUCabababababababababababLsLsLskeLsLsLsLsLsLILsLsLsLsLsababLsLsLsLsLsLsLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsLsabababababababababababababababababLsLsLsLsLsuIaXaXbaaYLsLsLsaWLsLsLsLsLsLsLskeLsLsLsBRLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhPiNhUCabababababababababababLsLsLsLsLsLsLsLsLsLsLsBRLsLsabababababLsLsLskeLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsababababababababababababababababababLsLsLsLsLsuIaXaXaXaYLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsababababLsLsLsLILsLsLsLsLsLsBRLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcyPiakUCababababababababababababLsLsLILsLsLsLsLsLsLsLsLsabababababababLsLsLsLsbbbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdxnaXaXaXaYLsLsLsabababababababababababababababababLsLsLsLILsuIaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhbZakUCabababababababababababababLsLsLsLsLsLsLsLsBRLsLsababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLILsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsaWLsaZaXaXaXaYLsLsLsLsabababababababababababababababLsLsLsLsLsLsuIaXaXaXaYLsLsBRLsLsLsLsLsLsLsLsLsLsababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaababababababajajajUCNhakakUCabababababababababababababLsLsLsLsLsaWLsLsLsLsLsLsLsabababLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsBRLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLskeLsLsababababababababababababababLsLsLsLsLsLsLsuIaXaXaXaYLsLsLsLsLsLsLsLBLsLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababajakakUCakakakajabababababababababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsaWLsLsLILsLsLsLILsLsLILsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsabababababababLsLsaZaXaXaXaYLsLsLsLsabababababababababLsababababLsLsLsLskeLsLsuIaXaXaXaYLsLsLsLsLILsLsLsLsLsababababababababababababLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababajajakakakakajajababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsababLsLsLsLsBRLsLsBRLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsHELsLsLsLsLsLsLsLsLsabababababababababababLsaZaXaXaXaYLsLsLsababababababababLsLsLsababLsLsLsLILBLsLsLsLsuIbaaXaXaYLsLILsLsLsLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
+aaaaabababababababajamakakajajajabababababababababababababLsLsabLsabLsLsLsLsLsLsLILsLsLsBRLsLsLsLsLsLsLsLsababababLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsabababababababababLsLsaZaXaXaXaYLsLsLsLsLsababababababLsLsLsabLsLsLsLsLsLsLsLsLsLsuIaXaXaXaYLsLsLsLsLsBRLsLsLsababababababababababababLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababajajakakakajajababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsabLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsBRLsLsLsLsBRLsLsababababababLsLsLsLsLsaZaXaXaXaYLsLILsLsLsLsLsLsababLsLsLsLsLsLsLsLsBRLsLsLsLsaWLsuIaXaXaXaYLsLskeLsLsLsLsLsLsababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsaWLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababababajUCakakajajababababababababababababababababababababLsLsLsLsLsBRLsLILsLskeLsLsLsLsabababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsabababababLsLsLsLsaWLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsLILskeLsLsLsLsLILsLsLsLsuIaXaXaXaYLsLsLsLsLsLsLsLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababababUCXJakakUCababababababababababababababababababababababababLsLsLsLsLsLsLsLsLILsLsLsLsababababLsBRLsLsLsLsLskeLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLILsLsLsLsLsBRLsLsLsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIaXaXaXaYLsLsLsLsLILskeLsLsabababababababababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCJbPiakUCabababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLILsLsLsLsLsBRLsLsLsabababababababababababLsLsLsLsLskeLsLsababababababLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaXaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaXaXaXaXaYLsLsLsLsLsLsLsLsqwqwababababababababababababLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPicyUCabababababababababababababababababababababababababababababababLsLskeLsLsLILsLsLsabLsLsLsLsLsLsLsLsLsLsabababababababababababababababLsLsLsLsLsLsabababababababababLsLILsLsLsabababababLsLsBRLsLskeLsLsLsBRLsLsLsLILsLsLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsLILsLsLsLsqwqwXgababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhceRtUCababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsLsababababababababababababababababababLsLsLsLsababababababababababLsLsLsabababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsLsLsLsLsabababqwabababababababababababLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcywPNhUCababababababababababababababababababababababababababababababababLsLsLsLsLsLsLskeLsLsLsLsLsLsLsabababababababababababababababababababababLsababababababababababababababababababababababababLsLsLsLILsLsLsLILsLsLsLsLsLsLsaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYLsLsLsLsLsLsabababqwqwqwababababababababLsLsLsLsvuLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhJcNhUCababababababababababababababRMRMRMRMRMRMRMRMRMabababababababababLsLsLsLsLILsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababLsBRLsLsLsLsLsLsLsaWLsLsLILsaZaXaXaXaXbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbeLsBRLsLsLsabababqwqwqwqwabababababababLsLsLILsLsLsLsLsLsvuLsLsLILsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhPicyUCababababababababababababababRMLsLsLsRMLsLsLsRMRMRMRMRMabababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsabababababqwabababababababLsLsLsLsLsvuLsaELsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCcpbZNhUCababababababababababababRMRMRMLsLILsLsLsLsLsLsLsLsLsRMRMabRMRMRMMrMrMrMrXHMrMrMrMrababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLILsLsLsLsLsLsLsLILsLsLsLsLskeLsLsLsLsLsLsLsLsLskeLsLsLsLsababababqwXgabababababababLsLsLsLsLsLsLsLsLsLsLsLsaFLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCNhPiRtUCababababababababababababRMLsLsLsLsLsLsLsLsLsImLsLsLsLsRMRMRMLsLsLsLsLILsLskeLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLskeLsLsLILsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababqwqwababababababLsLsLsLsLsLsLsaCLBLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababUCRtPiNhUCababababababababababababRMLsLsLskiLsLsXpLsLsLILsLsLsLsLsRMLsLsLsLsImLsLsLsLsLskeLsabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLILsLsLsLsLsLsaZaXaXaXaYLsLsaWLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsaWLsLsLsLsLsLsababLsabababababqwqwabababababLsLsLsLsvuLsLsLsaWaDLsLsLsLsLsvuLsLsLsLsLsabababababababababababUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCUCabaaaa
+aaaaabababababababababUCNhPiNhUCUCUCUCUCUCUCUCUCUCUCUCUCUCLsLsLsLsLsLBLsLskeLsLsUsLsLsLsLsLsTXLsLsLsLsLsLsXpkiLsLsababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsLsLsababababLsLsLsababLsLsLsLsLsLsLsLsababababababababababXgqwqwqwababababLsLsLsLsLsLILsLsLsLsLsLsvuLsLILsLsLsLsvuLsLsLsababababababababababUCCACAUCUCUCCACAUCCACAUCUCUCCACAUCabaaaa
+aaaaabababababababababUCcyJcNhXJNhNhRtNhNhXJNhNhNhcyNhNhUCLsPhLILsLsLsLILsLsLsLsLsrhLsLsLILsLsLsLsaWLsLsLsLsLsLsLsLsababababababababLsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsabababababababababababababLsLsLsLsLsabababababababababababqwqwabababababLsLsLsvuLsLsLsLsaBLsLsLsLsLsLsLsaALsLsLsLsLsLsLsababababababababababUCCACAUCUCUCCACAUCCACAUCUCUCCACAUCabaaaa
+aaaaabababababababababUCNhPitTPiPiPiPiPiwPPiPiPiwPakPiPibYLsPhLsLsImLsLsLshKLsLsLsLsLsLsLsLsLsXpLsLsLsLshKLsLsLsUsLsLsLsababababababLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsaWLsLsLsLsaZaXaXaXaYLsLILsLsabababababababababababababababababLsLsLsababababababababababababqwabababababLsLsLsLsLsvuLskeLsLsvuLsLsLsLsLsLILsLsLskeLsLsLsLsabababababababababUCIAsrUCZpUCIAsrUCIAsrUCZpUCIAsrUCabaaaa
+aaaaabababababababababUCXJRtNhNhNhcyNhNhNhJbakXJakakcyNhUCLsPhLsLsLsLsLsLsLsLsLBTXLsLsLsLBLskeLsLsLsLsLsLsLBLsLILsLsLsLsababababababLsLILsLsabababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsaZaXaXaXaYLsLsLsLsabababababababababababababababababababababababababababababababqwqwabababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsvuLsLsLsLsLsLsabababababababababUCPiQgPiPikMoyoyPioyoykMPiPiQgPiUCabaaaa
+aaaaabababababababababUCUCUCUCUCUCUCUCUCajakakakakakajUCUCLskeLsXpLsLsLsXpLsLsLsLsLskebALsLsLsLsLsXFLsLskeLsLsLsLBLsLsLsabababababababLskeLsLsabLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsaZaXaXaXaYLsLsLsLsababababababababababababababababababababababababababababababqwXgababababababababLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababUCuwoyCfCfCfQguwnKEYQgCfvZCfoynQUCabaaaa
+aaaaababababababababababababababababababajakamakakajajabRMRMLsTXLsLsLBLskeLsLsIQLsLILsLsLsXpLsLsLsLsLsLsbALsLsLsLsXpLsLsLsLsababababababLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababLsLsLILsLsaZaXaXaXaYLsLsLsLsLsababababababababababababababababababababababababababababqwqwqwabababababababababababababababLsLsLsLskeLsababLsLsLsLsLsLsabababababababababababUCKghMUHkyUHMMiKqrnQhMUHUHUHMMKgUCabaaaa
+aaaaabababababababababababababababababababajakakajajababRMRMLsLsLsLsLsLsLskiLsLsLsXFLsLsLsLsLsLILsTXLsXpLsLsLsTXLsLsLsLILsLsababababababLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsaZaXaXaXaYLsLsLsLsLsababababababababababababababababababababababababababababqwqwababababababababababababababababababLsLsLsLsabababababababababLsabababababababababUCnGhMUHUHUHMMKguwSshMUHUHUHMMesUCabaaaa
+aaaaabababababababababababababababababababajajajajababRMRMLsLsaWLsLsXpLsLsLsLsLsLsLsLsLsImhKLskeLsLsLsLskeLsLsLsLsLsLsLsLsLsMrLsLsLsababLsLsLsLILsLsababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsaZaXaXaXaYLsLsLsLsLsabababababababababababababababababababababababababababababqwqwabababababababababababababababababababLsLsLsabLsLsababababLsLsLsababababababababUCuwhMUHUHUHMMPdpYGShMUHUHUHMMuwUCabaaaa
+aaaaababababababababababababababababababababajababababRMLsLsLsLsImLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLBLsLsLsLsLsImLsLsLsXFLsLsLsMrLskeLsLsLsLsLsLsLsLsLsabLsabababLsLsLsabLsabababababababababababababababababababababababababababababababababababXHXHXHXHXHbfbgbgbgbhXHXHXHXHababababababababababababababababababababababababababababababqwqwabababababababababababababababababababLsLsLsLILsLsLsLsLsLsLsLsabababababababababUCKghMUHUHUHMMjziKDahMUHUHUHMMnQUCabaaaa
+aaaaabababababababababababababababababababababababababRMRMLsLsLsLsLsLILsLsImkiLsXpLsLBLsLsaWLsLsLsLILsLBLsLsLsLsLsLsLsLsQNQNuaQNQNQNLsLILsLskeLsLsLsLsLsLsLsabLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsabababababababababababababababababababababababababqwabqwqwqwababXgqwababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababUCuwhMnCUHUHMMrLwcrLhMUHUHxAMMKgUCabaaaa
+aaaaabababababababababababababababababababababababababRMLsLsLsXpLsLsbALsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsUsLsLsLsLsLsMrLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLsLskeLsLsaZaXaXaXaYLsLsababababababababababababababababababababababababYwqwqwDMqwqwqwqwqwqwababababababababababababababababababababLsabababababLskeLsLsLsLsababababababababUCsRhMUHUHUHMBCfGYCfHcUHUHUHMMKvUCabaaaa
+aaaaabababababababababababababababababababababababababRMLsLsUsLsLsLsLsLsLsLsLILsLskeLsbALsLsLskiLsLsXpLsLsLsLsLsLsLsImLsLsLsMrLsLsLsLsLsLsLsLsLsLsLsababLsLsLsLsLsLsLskeLsLIabababababababababababababababababababababababababababababababLsLsLILsLsLsLsaZaXaXaXaYLsLsabababababababababababababababababababababababqwqwXgqwqwqwYNqwqwqwqwababababababababababababababababababababababababababLsLsLsLsaWLsLsabababababababUCvXhMUHUHUHUHUHUHUHUHUHUHUHMMwCUCabaaaa
+aaaaabababababababababababababababababababababababababRMLsLsLsLsLBLsLsLsLsXFLsLsUsLsLsLsLsHELskiLskeLsImLsLsLsXpLsLsLsLsLsabababLsLsLsLILsLsabLsLsLsabababLsLsLskeLsLsLsLsLsLsabababababababababababababababababababababababababababababababLsLsLsLILsLsaZaXaXaXaYLsLsababababababababababababababababababababababababqwqwqwXgZWYwqwXgqwababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababUCnKhMUHUHUHUHUHFkUHUHUHUHUHMMuwUCabaaaa
+aaaaabababababababababababababababababababababababababRMRMLsLsLsLsLsXpLsLsLskeLsLsLsTXLsLsLsXFLsLsLsLsLsLsaWLsLsLsLBLsLsLsabababababLsLsLsLsababLsLsLsababababLsLsLsLsLsLsLsLsLsLsabLsLsLsabababababLsLsabLsLsLsabababababababababababababababLsLsLsLsLsaZaXaXaXaYLsLILsabababababababababababababababababababababababXgqwYNqwqwqwqwqwqwababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsababababababababUCuwhMUHUHUHUHUHUHUHUHUHUHUHMMKgUCabaaaa
+aaaaababababababababababababababababababababababababababRMRMLsLsLsLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLsLsLskeLsLsLsLsababababLsLsLsLsabLsLsLsLILsabababLsLsLsLILsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsababababababababababababababababLsLsLsLsaZaXaXaXaYLsLsLsababababababababababababababababababababqwqwqwqwqwXgqwYwDMqwqwqwqwababababababababababababababababababababLsLsLsLILsLsLsLsLskeLsabababababababababUCnQPiBhrSBhBhBhBhBhBhBhBhBhPiVdUCabaaaa
+aaaaabababababababababababababababababababababababababababRMRMRMLsLsLsLsImLsLsLILsRMLsLsLsLsXpLsLsLsLBLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsababLsLsLsLsababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsaZaXaXaXaYkeLsLsabababababababababababababababababababqwqwqwabqwqwqwqwqwqwqwXgqwababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababababUCKguweIBjVdKguwzcKgnKoyPiEtqRnKUCabaaaa
+aaaaabababababababababababababababababababababababababababababRMRMRMLsLsLsLsLsLsRMRMRMRMLsLsLsLskeLsLsLsLsLsImLsLsLsLsababababLsLskeLsLsLsabLskeLsLsababLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsLsOvOvOvOvOvOvOvOvOvLsLsLsLsLsababababababababababLsLsLILsLsaZaXaXaXaYLsLsLsabababababababababababababababXgqwqwqwqwabababqwXgabababqwqwqwqwabababababababababababababababababababababLsLskeLsLsLsLsLILsLsababababababababababUCUCUCUCUCUCUCUCUCUCUCQgPiUCUCUCUCabaaaa
+aaaaabababababababababababababababababababababababababababababababRMRMLsLsLsLsLsRMababRMRMLsLsLsLsLsLsLsabababababababababababLsLILsLsLsQNQNQNLsLsLsLsLsLsLsLsabababLsLsLsLsababLsLsLsLsLsLsLsOvapcsOpOpOpAzdbOvLskeLsLsLsLsLsLsLsLsLsababababLsLsLsLsLsaZaXaXaXaYLsLsababababababababababababababqwqwqwqwqwXgqwababababababababqwabababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababUCCACAUCPiPiUCCACAUCabaaaa
+aaaaababababababababababababababababababababababababababababababababRMRMRMRMRMRMRMabababRMRMRMRMabababLsabababababababababababababLsLsLsLsabLsLsLILsLsLsLsababababLsLsLsLsLILsLsLsLsLsLsLsLILsOvancscscscscsaoOvLsLsLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsaZaXaXaXaYLsLsLsabababababababababababababqwqwqwqwababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababUCCACAUCPiPiUCCACAUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsabababababLsLsLsLsababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvdbcscscscscsapOvLsLsOvOvOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsababababababababababababababqwXgabababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababUCeCNhUCIcIcUCeCNhUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsababababababLsLsLsLsabLsLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsOvOvOvOvXiOvOvOvOvLsLsOvdbcscsapOvLsLILsLsLsLsLsLsLskeLsLsaZaXaXaXaYLsLsLsababababababababababababqwqwqwababababababababababababababababababababababababababababababababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsabababababababababababababababUCNhNhNhQgQgNhNhNhUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLskeLsLsLsababababababLsLsLsLsOvFcNhNhNhNhNhFcOvLsLsOvFMcscsjeOvLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsabababababababababqwqwqwababababababababababababababababababababababababababababababababababababLsLsLsLsLILsLsLsLsaWLsLsLsLsLsLsabababababababababababababababUCnXNhNhPiPiNhNheZUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsabababababababLsLsLsOvNhNhIPIPIPNhNhOvLsLsOvfUcscsapOvLsLsLsLsLsLsaWLsLsLsLsLsaZaXaXaXaYLsLILsLsLsLsabababLsLsababqwqwababababababababababababababababababababababababababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLskeLsLIHEababababababababababababababUCNhOMUCPiPiUCOMNhUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwqwabababababababababababababababababLsLsLsLsLsLsLsLILsLsLsabababababLsLsLsOvNhZMmdadvfuANhOvLsLsOvFMcscsjeOvLsLsLsLsLsLsLsLsLsLILsLsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsabqwababababLsababababababababababababababababababLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsabababababababababababababababUCNhNhNhPiPiNhNhNhUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwqwqwababababababababababababOvOvOvOvOvOvOvOvLsLsLsLsLsLsLsLsLsababLsLsLsLsOvNhNhKGKGKGNhNhOvLsLsOvWRcscsapOvLsLskeLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsabababLsLskeLsLILsLsabqSabLsLsLsLsLsababababababababababababababababLsLsLsLsLsLsLILsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababUCNhNhNhPiPiNhNhNhUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwqwqwqwababababababababOvdbPDPzFAFAdbOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsOvFcNhNhNhNhNhFcOvLsLsOvdbcscsjeOvLsLsLsLsLsLsLskeLsLsLsLsaZaXaXaXaYLsLsLsabababLsLsLsLsLsLskeheLBLsLsLskeLsLsabababababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLBLsLsLsLsLsLsLILsLsLsLsLsababababababababababababababababUCNhOMUCPiPiUCOMNhUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwabababqwqwqwqwqwaeqwqwabOvcscscscscscsOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsOvOvofOvMuOvofOvOvLsLsOvOvXiOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsababLsLsLsLsLsLsheLsLsaWLsLsLsLILsababababababababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsabababababababababababababababababUCNhNhNhPiPiNhNhNhUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwabqwqwqwqwqwvhcscscscsOvWLvvcsdbOvaTaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUxnaXaXaXaYLsLskeLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLskeLsLsabLsLsabababababababababababababababababUCnXNhNhPiPiNhNheZUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababqwabababababababababababababababababqwqwqwabOvcscscsmFvvFQvvcscsgIaZxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnaXaXaXaYLsLsLsLsLsLsLsabababLsLsLsLsLsabababLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababUCNhOMUCPiPiUCOMNhUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwababababababababababqwqwqwqwabababOvcscscscsWOIevvcscsOvaZxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnaXaXaXaYLsLsLsLsLsLsLsLsLsabababLsLIabababababababLsLsLsLILsLskeLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLspVZlQvLsLsLsabababababababababababababababababababababUCPiPiPiPiPiPiPiPiUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwababababababTDababqwqwqwqwababababOvdbcsOvvvvvFQvvcscsgIaZxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnaXaXaXaYLsLsLsLILsLsLsLsLsLsabababababLsLsLsLsLsabababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsMIQAQvLsLsLsLsLsLILsLsLsQvQvuBQvQvZlLsLsabababababababababababababababababababababUCPiPiQgPiPiQgPiPiUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababqwqwababqwqwabqwqwqwqwqwqwqwqwqwabababababababOvcscsYPdzdziAvvcscsOvbbbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdxnaXaXaXaYLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsQvQvZlHpQvpVQvuBLsLsLsLsHpqDQvLfQvmJQvqDLfQvabababababababababababababababababababababUCPiPiUCUCUCUCPiPiUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwababqwqwqwqwabababababababababOvcscsOvOvOvOvOvcscsOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsOvvvOvXiOvOvOvLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLskeLsLsLsLsLsLsQvLfQvqDQvuBLfQvLfQvQvQvZlQvQvQvZluBZlQvQvuBabababababababababababababababababababababUCPiPiUCCACAUCPiPiUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwababababababababababOvcscscscscscscscscsOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsOvdbtNcscsOpOvLsLsLsLsLsaWLskeLsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsQvpVQvZlsEMITIQvQvQvMIQvmJZlQvmJnYQvMIQAQvuBQAQvZlababababababababababababababababababababUCPiPiUCCACAUCPiPiUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwabababababababababababOvdbcscscsdbcscscsdbOvLsOveecscscsOpOvLsOveecscscsOpOvLsOveecscscsOpOvLsOveecscscsOpOvLsLILsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLILILsLsLsLsLsLsLsLsLsLsLsLsLsLsQvLOQvQvMIQvQvQvpVQAQvmJHpsEuBQvcIQvQvuBQvQvsEMIHpQvQvababababababababababababababababababababUCAcPiUCeCNhUCPiycUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwababababababababababOvOvOvOvOvOvOvOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsOvcscsOvOvOvOvLsLsLsLsLsLsLsLsLsaZaXaXaXaYOvOvOvOvvvvvOvOvvvvvOvOvOvOvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLspVQvQvHpQvuBfOQvmJLfQvQvQvuBZlQvQvqDfOQvsEHpQvqDmJQvQvQvsEuBHpLfQvabababababababababababababababababUCQgPiPiPiPiPiPiQgUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwababqwqwqwababababababLsLsLsLsLsLsLsLsLsLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsOvcscsOvAzdbOvLsLsOvOvOvOvOvOvOvaZaXaXaXaYOvNRCOCOVJeJyMLqTEfBWBcseLOvLsLsLsLILsLsLsLsLsLsLsaWLsLsLsLsLfLsMIQvsEZlQvpVQvQvQvrCQvHpQvmJMIQvQvmJZlQvZlQvQvZlQvQvpVQvTIQvfOQvQvpVQvZlabababababababababababababababUCPiPiPiPiPiPiPiPiUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababqwababqwqwqwqwqwqwqwqwqwababababababLsLsLsLsLsLsLILsLsLsLsOvcscsOncsarOvLsOvcscsOncsasOvLsOvcscsOncsatOvLsOvcscsOncsauOvLsLsOvFcZhZhNhNhOvaZaXbjaXaYOvcscscscscscscscscscscseLOvLsLsLsLsLsLsLsLsLsLsLsLsLsZlQvQvQvQvQvqDQvQvQvQvsEQvQAQvQvmJQvQvsELfQvHpsEQvQvHpQvmJsEQvHpuBQvHpMIQvmJQvmJHpabababababababababababababababUCUCUCUCPiPiUCUCUCUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwqwqwqwqwababababababababababababLsLskeLsLsLsLsLsLsLskeLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsOvOvOvOvOvOvOvLsLstjNhNhNhNhNhOvaZaXaXaXaYOvnacsdbcscscscscscsdbcseLOvLsLsLsLsLsLsLsLsQvQvQvQvqDQvQvmJpVQvmJQvmJuBfOQvZlQvMIZlQvQvpVQvQvQvqDQvQvQvmJLfMIQvQvLfsELfilmJsEQvLfQvqDQvQAababababababababababababababUCCACAUCPiPiUCCACAUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababqwababqwqwqwabababqwqwababababababababababababLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsOvLzNhikOvNhOvaZaXaXaXaYOvOvDFOvXiOvOvOvOvXiOvOvOvOvLsLsLsQvLfQvsEQvQvmJHpfOQvLfuBMIQvsEQvHpQvMIQvmJqDfOQvsEuBLfQvQvmJbiQvmJLfuBQvQvQvpVQvqDQvQvHpQvqDQvZlQvHpabMIababababababababababababababUCCACAUCPiPiUCCACAUCabaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababqwqwqwqwababababababqwqwababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsOvLzNhikOvNhNhaZaXaXaXaYofFcNhNhNhNhRLFcNhNhNhNhFcOvLsQvQAZlQvqDQvLfQvMIuBQvQvQvQvQvQvbiQvQvmJLfQvsEQvHpQvMIHpQvHpqDQvLfQvQvQvmJZlQvmJQvsEQvmJZlQvQAQvpVQvmJRMababababababababababababababababUCIAsrUCIcIcUCIAsrUCabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababqwqwabqwababababababababababababababababababLsLsLILsaWLsLsLsLsLsOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvOvLsLsOvOvOvOvOvOvOvOvOvLsLsOvOvOvOvOvLsHpOvLzNhikOvFcOvaZbjaXaXaYOvNhNhNhNhNhNhNhNhNhNhNhNhofLsqDQvQvQvmJQvQvQvZlQvZlQvmJQvnYQvQvQvQAQvQvQvQvZlQvQvmJQvmJQvmJfOuBQvpVQvQvQvQvQvpVQvMIZlQvQvMCJpQvuBMIRMRMabababababababababababababababRMQFljRSQFCwrbQFRSRMabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLskeLsOvFcNhNhNhZMZMjDFcZMjDZMZMNhNhFcNhOvLsLsOvLbcscscscscsAwOvLsLsOvdbcsYQOvqDXEOvOvOvOvOvtjOvaZaXaXaXaYMuNhNhNhIPIPIPIPIPIPNhNhNhOvQvQvMIsEHpQvQvfOQvQvmJLfQvpVQvQvMIQvmJQvmJZlmJpVQvQAQvpVQvQvZlQvQvHpQvmJQvQAQvZlQAQvKZMCMCqfMCMCMCFgMCpVqDRMabababababababababababababababRMRMCwrbvDljCwvDRMRMabaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsLsLsLsOvmeNhNhNhZMZMjDvfZMjDZMZMNhNhNhNhOvLsLsOvLbcscsdbcscsAwOvLsLsOvIJcsYQOvyvuROvLQOvLQtjdbOvaZaXaXaXaYOvvfNhZMxmxmxmxmxmxmuANhvfofHpqDLfQvuBLfQvZlQvwLQvQvQvQvsEQvfOQvqDQvqDQvHpQvsEuBQvQvsEHpQvpVQvQvQvqDQvQvsEQvQvMCMCJpMCVYVYhCMCMChCVYVYRMRMRMRMabababababababababababababRMRMhwCwQFZPRMRMababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLsRqLsLsLsLsLsLsOvNhNhjDjDjDjDjDjDjDjDjDjDjDjDadNhOvLsQvOvCtcscsyMcscsUtOvLsLfOveQcscsXiaZaYOvXiNDXitjcscsaZaXaXaXaYOvvfNhZMxmxmxmxmxmxmuANhvfofQvmJQvIXQvQvilQvMIQvHpQvmJqDQvQvQvLfmJuBLfQvQvMIQvQvLfQvQvQvmJQvQvndQvLfFgMCMCdQVYMCtcFgVYryMCFgjHyZVYdQjZMCtcFgRMababababababababababababababRMRMrbljRMRMabababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLskeLsLsLsLsLsLILsLsOvNhNhjDjDjDjDjDjDjDjDjDjDjDjDSFNhOvLfqDOvCtcscsAAcscsUtOvuBQvOvYScscsOvaZaYOvcscscstjcsOvaZaXaXaXaYMuNhNhNhKGKGKGKGKGKGNhNhNhOvQvqDQvpVQvQvqDmJLfQvfOQvQvpVQvmJQvRTQvQAQvQvmJLfQvmJQvMIZlmJQvZlQvQvMIMCMCryagVYyAjHMCyAgChQMCyZyZyZyZyZMCKZVYRMRMabababababababababababababababRMRSCwRMababababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsLILsLsLsLsLsLsLfLsLsOvpmNhNhNhZMZMjDvfZMjDZMZMNhNhNhNhOvMIQAOvUtcscsdbcscsUtOvHpsEOvjXcsaOvvaZaYOvnacscscscsOvaZaXaXaXaYOvNhNhNhNhNhNhNhNhNhNhNhNhofZlsEuBMIQvmJQvQvQvsEQvMIQAQvQvQvuBQvQvQvuBQvQvQvQvQvLfQvqDQvQvQvLfQvFgyAMCJpTuMCyZyZyZyZjHMCyZyZyZyZyZyZqfMChCRMababababababababRMRMRMRMRMabababRMCwrbRMababababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababQvLfHpQvLsLsLsLsLsLsLsLsQvmJqDLsOvFcNhNhNhZMZMjDFcZMjDZMZMNhNhFcNhOvHpQvOvUtcscscscscsUtOvMIqDOvdbcslnvvaZaYOvdbcscscscsOvaZaXaXaXaYofFcNhNhNhNhmxFcNhNhNhNhFcOvQvQvQvfOQvQvnYQvQvHpZlQvQvQvsEQvTIQvLfsEQvLfZlHpQvTIQvmJQvQALfQvMCJpMCMCyZKZjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHMCRMRMRMabababRMRMRMRMMCFgqfRMabababRMljvDRMababababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababababQvabababababababababababababababQvfOuBQvLsfOLsHpQvQAMIHpfOQvZlOvOvOvofofOvOvTROvOvTROvOvofofOvOvOvQvXEOvOvvvOvXiOvvvOvOvQAQvOvOvOvOvOvaZaYOvOvOvOvOvOvOvaZaXaXaXaYOvOvOvOvXiOvOvOvOvXiOvOvOvOvHppVQvQvpVQvQvQvuBuBQvmJLfQvpVQvQvqDQvmJqDQvsEQvQvQvuBQvHpQvQvMCKZMCjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAUcFgMCRMRMRMRMRMjHJpyAUcyZJpRMRMRMabRMQFCwRMababababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababababQvQvZlQvabababababababababababQvMIpVQvoQQvoQQvZlrCQvsLsLsLsLsLsLaTaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUxnxnaUaUaUaUaUaUaUaXbjaXaXaYOvtztzcscscscscscscscstztzOvQvQvmJQvMIQvsELfQvfOQvQvQvQvQvQvMIfOQvQvHpQvMIUcFgMCMCJpMCUcMCdQVYyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHtcJpKZyAFgtcyZyZyZyZtcjHKZRMRMRMvDljRMRMabababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababababababQvHpQvQvsEQvabqDabQvababZlQvHpLfLfQvHpQvQvQvQvoQQvmJQvsLdbUNdTYosLaZaXaXaXaXaXbjaXaXaXaXaXaXbjaXaXaXaXaXaXaXaXaXaXbjaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaYOvdbcscscscscscscscscscsdbOvMIQvQvLfQvZlQvQvMIQvQvuBqDmJHpsEQvQvLfQvMCJpVYgCtcMCFgyAMCqfMCVYVYMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAKZRMyAKZqfjHRMabababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababababZlQvQvmJLfQvMIQvQvpVHpQvQvMIuBQvQvQvqDsEHpQvmJqDQvQvQvHpsLnacscscsXiaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbkbkbkaYOvtztzzDxKdbjfjfdbxKzDtztzOvQvLfsEQvQvmJHpQvmJQvQAQvQvLfilQvMCtcMCKZyAMCdQLKyZyZyZKZMCMCFgyAFgKZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJptcFgyZyZUcRMabababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababababHpQvMIQvqDilQvHpQvfOuBQvQvQAHpqDQvmJfOuBQvQvafQvQvQAQvpVsEuBsLapcscsapsLaZaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbjaXaXaXaXaXaXaXaXaXaXaXaXbkbkbkaYOvOvOvOvOvOvOvOvOvOvOvOvOvOvQvHpQvQvpVQvQvpVQvZlQvuBMCKZMChCVYUcMCMCMCjHFgyZyZyZyZyZyAjHyZyZjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpRMabababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababuBQvQvLfsEQvQvMIZlQvQvQvBCMIQvQvsEQvpVQvQvQvmJQvQvmJQvQvqUQvQvsLsLsLXisLsLbbbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdblbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdaXbkbkbkaYMIpVsEQvQvHpQvLfQvQvuBQvQvQvMIQvfOQvQvLfQvQvMCKZMCMCyAMCqfgCjZMCyAKZqfyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZRMabababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababQvQvfOQvMIQvQvmJLfsEQvQvmJQvHpQvLfQvQvQvQvmJLfQvsEQvHpLfqDQvQvLfQvMIHpQvpVQvqDQvZlQvQvLfQvQvMIuOZlQvqDpVQvsEQvQvpVQvqDZlQvQvqDQvHpQvZlQvmJQvfOQvQvsEMIQvfOQvZlMIQvmJpVHpaZaXaXaXaYsEQvQvZlmJQAQvZlsEqDHpmJZlQvXEQvQvBCMIQvMCJpVYhQMCyZyZjHMCJpMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZRMabababaaaa
+aaaaababababababababababababababababababababababababababMIZlababababababababQvsEQvHpQvQvQvpVQvuBQvQvpVuBQvZlQvfOQvQvLfQvHpQvMIQvLfQvMIyTQvbCQvyTQvyTQvyTQvyTQvyTQvyTZlQvsEHpQvQvQvQvuOMIQvLfQvmJQvsEQvQvMIfOQvsEMIelQvuBQvLfQvqDsWQvpVQvQvsEQvLfqDQvsEuBaZaXaXaXaYQvqDQAQvqDQvHpQvQvQvQvQvLfQvQvQvyAMCMCjZVYVYVYMCUcyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZRMabababaaaa
+aaaaababababababababababababababababababababababababababQvLfQvHpabababababZlQvQvMIQvqDQvmJQvQvQvHpQAQvQvLfsEQvMIQvmJQvQAqDQvfOQvQvqUuBQvQvQvQvQvQvQvQvQvQvilQvQvQvQvQvuBQvqUQvnYQvQvZlQvuOQvelQvuBaTmTmTmTaVpVQvQvQvHpQvmJMIsEHpuBQvQvMCtcQvqDmJuBQAQvZlaZaXaXaXaYQvZlQvuBQvmJQvQvmJLfpVMIQvVYVYqDKZMCJpVYhtVYjZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCjHFgyZyZyZyZyZyZyZyZUcyZyZKZqfjHyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZRMabababaaaa
+aaaaababababababababababababababababababababababababababqDHpsEQvpVQvababqDQvQAHpQvpVsEQvuBHpQvmJQvQvMIQvQvqDZlQvQvQvHpQvZlQvQvmJHpZlQvyTQvyTQvyTQvyTQvyTQvyTQvyTQvyTQvQAQvQvQvQvuOuBQvLfQvQvQvQvHpaZbmbnaXaYQvQvmJpVQvKZyAMCtcMCKZZlMCJpMCyAQvHpQvsEHpQvaZaXaXaXaYQvmJQvLfsEMILfQvQvhCVYMCMChQVYyAMCMCyAVYVYVYVYyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZKZjHMCMCyAMChQVYdQjHyZyZjHyZyAyZMCFgJpyARMRMKZtcFgyZyZyZjHFgtcJpyZyZyZyZyZyZyZyARMabababaaaa
+aaaaabababababababababababababababababababababababababZlQvMIQvQvQvMIfOQvQvZlQvQvQvQvQvLfQvQvLfQvHpfOQvmJHpQvQvQAQvpVQvQvFgMCJpQvsEQvuBQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvQvqDmJZlQvJpMCKZQvLfHpMImJQvbobnbpbnaYLfQvQAQvJpMCVYryMCJpMCyAKZqfMCMCZlfOQvmJMIQAaZaXaXaXaYLfQvHpqDQvKZMCqfMCVYryMCJpMCgCjHFgMCyZyZyZjHyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyAMCtcMCMCyAMCMCMCgCVYVYMCMCtcMCMCKZMCyARMRMRMRMRMRMRMjHqfUcyAKZRMRMKZqfUcyAyZyZyZqfJpRMabababaaaa
+aaaaababababababababababababababababababababababababababQvmJpVQvmJHpQvQvHpQvHpLfQvHpQvQvyFQvqDMIQvQvuBLfQvfOQvqDLfQvMCKZMCqfMCMCKZJpQvyTQvyTQvyTQvyTQvyTQvyTQvbCQvyTQvLfQvMIQvMCMCMCtcMCUcQvqDQvmJaZaXbnaXaYQvZlQvQvUcMCqfMCFgMCyZjHFgyZMCUcMCuBHpqDpVQvaZaXaXaXaYuBQvfOQvVYdQMCFgMCtcMCyAyZyAjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCKZMCMCMCKZQvFgqDMCMCTuhtVYgCMCUcagMCJpMCRMRMababababRMRMRMRMRMRMRMRMRMRMRMJpKZtcyAFgRMRMabababaaaa
+aaaaabababababababababababababababababababababababababababQvQvLfpVQvsEpVQvmJqDQvmJsEQvpVQvMIsEQvmJZlQvQvQvQvMIuBtcMCJptcFgMCUcyAiXMCUcQvQvHpQvpVQvQvHpQvZlQvfOQvuBQvHpMCMCtcKZMCagVYFgMCVYVYHpZlQvbbbdbdbdbeqDQvMCtcVYMCKZyZyZyAyZyZyZyZyAMCKZqfQvLfQvFgaZaXaXaXaYQvsEUcKZVYLKyZyZKZMCjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCjHVYryagMCFgQvmJQvMIfOQvQvyAMCMCMCMCyAMCVYMCLfQvfORMababababababababababababababRMRMRMRMRMRMabababababaaaa
+aaaaabababababababababababababababababababababababababababfOZlQvQvQvsMQvQvQvQvuBQvfOMIQvsWQvQvqDQvQvmJpVQvsWQvHpMCKZjHyZyZyZyZyZjHtcMCMCKZqfMIQvqUQvMIQvmJqDHpQvLfQvMCFgyAMCMCUcVYVYKZtcMCyAKZJpQvLfQvMImJuBelQvMCFgLKyAyZyZyZyZyZyZyZyZyZyZyZjHKZJpLKUcaZaXaXaXaYKZJpjHMCyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAjHMCJpyAVYVYVYKZQvqDQvLfHpuBQvmJQvLfMCUcMCMIsEfOQvelHpQvRMabababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababQvqDsEDifOQvZlQvfOQAQvMIQvQvQvZlQvpVQvQvHpQvQvQvQvJpqfMCyAyZyZyZyZyZyZyZyZMCtcMCJpMCMCqDQvmJQAQvQvqUQvHpMCMCMCMCJpMCMCyAjHyZyZyZMCKZMCMCMCZlQvHpQvKZhCVYMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAyZaggCOEOEOEOEOEqfyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCqfMCMCuBQvmJHpQvfOQvpVQvQvsEQvLfQvQvMCfOQvQvQvQvqDQvMIQvfOabababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababQvfOQvQvQvQvmJqDQvHpQvmJQvnYQvuBilsEQvmJQvQAQvMCUcMCKZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyAMCLfQvQvuBHpQvZlMIVYVYUeMCKZjHyAyZyZyZyZyZyZyZMCagLKyAMCsEQvUcMCVYgCyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZOEOEOEOEOEyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZUcMCMCFgilHpQvQvQvuBQvQvQvuBfOQvQvQvMIfOQvQvMILfHpQvQvmJQvLfQvabababababababababababababababababababababababababaaaa
aaaaababababababababababababababababababababababababababMImJQvQvnYQvMIpVQvQvHpQvZlQvQvQvfOQvqDQvQvHpQvMIJpMCyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCMCUcMCMCQvQvmJKZMCVYgCMCJpyZyZyZyZyZyZyZyZyZyZyZUcyZKZJpMCKZMCqfMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZOEOEOEOEOEyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyAyZyZyZyZyZyZyZyZyZyZyZyZyZjHMCtcMCMIfOQvLfQvnYQvLfQvmJQvHpQvmJqDQvQvHpQvmJQvsEQvQvuBQvQvababababababababababababababababababababababababababaaaa
@@ -600,64 +712,64 @@ aaaaabababababababababababababababababababababababababababQvQAQvQvfOZlQvHpQvQAQv
aaaaababababababababababababababababababababababababababZlQvHpQvpVQvHpQvQvQvQvpVQvmJQvZlQvuBQvZlMCMCtcMCjHyZyZyZyZyZyZyZyZyZyZyZyZjHyZyZyZyZyZyZyZyZyZFgyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZOEOEOEOEOEyZyZyZyZyZMCjHFgyAyZyZyZyZUctcMCjZMCQvHpQvelQvfOQvQvelQvQvfOpVQvQvHpQvsEQvQvfOQvpVQvsEqDQvfOQvqDLfQvQvuBQvQvQvQvfOQvQvmJQvQvqDQvmJQvLfQvQvabababababababababababababababababababababababababaaaa
aaaaababababababababababababababababababababababababababMIsEfOQvpVsEuBQvLOQvbiQvQvQvLfQvsEQvQvMCqfUcMCKZyZyZyZyZyZyZyZyZUcyZyZyZJptcjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyAyZyZUcyZyZyZyZyZyZyZyZyZyZyZyZyZOEOEOEOEOEyZyZyZyZtcMCagVYMCMCjHFgyAMCMCQvLfQvHpQvQvQvMIQvmJHpQvQvuBHpQvQvfOQvQvQvQvLfmJMIQvilQvQvQvQvQvQvMIQvmJHpQvpVmJHpQvelQvHpLfQvQAQvQvHpQvuBababababababababababababababababababababababababababaaaa
aaaaababababababababababababababababababababababababababHpQvuBQvQvQvfOQvQvQvmJQvfOQvMIQvQvpVJpKZMCMCyAyZyZyZyZyZyZyZJpKZMCtcjHMCUcMCMCKZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCjHqfKZMCyZyZyZyZmDyZyZyZyZyZyZyZyZMCtcVYVYVYMCjHJpMCKZMCyZMCUcyZyZyZyZyZyZyZOEOEOEOEOEyZyZjHFgMCMCVYdQMCUcqfMCZlQvQvQvQvuBQvQvmJLfHpQvHpQvmJZlfOQvQvmJQvQvmJLfQvQvQvQvQvfOQvmJLfHpQvmJQvQvpVQvQvQvQvLfQvsEuBQvQvQvsEQvZlQvQvQvZlabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababQvLfQvmJpVQvmJqDsEpVQvQvZlQvHpQvUcMCKZMCtcMCJpyZyZyZyZyZyZyZjHMCMCMCMCMCqfVYMCtcMCyZyZyZyZyZyZyZyZyZyZyZyZyZMCtcJpMCUcMCKZMCyAMCyZyZyZyZyZyZyZyZyZyZUcjHFgJpMCfOZlQvqfQvuBMCyAMCtcMCjHyZyZyZyZdQjZuIxnxnxnnyKZhQMCyAMCQvQvqDQvMILfQvQvQvmJpVQvmJfOQvLfsEQvfOQvQvqDQvQvelQvZlQAQvqDMIQvHpQvmJqDQvMIpVQvQvQvQvZlfOQvQvmJQvZlQvQvLfQvsEQvMIQvQvQvmJfOQvababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababsEQvqDQvQAQvLfQvQvQvLfQvMCMCyAMCMCMCMCyAMCjHyZyZyZyZyZyZyZyZFgMCUeVYhCMCKZMCJpMCMCFgyZyZyZyZyZyZyZyZyZyZyZjHyAMCMCZltcQvQvfOMCUcVYdQyZyZyZyAMCqfjHFgyAMCQvMCQvMIuBQvQvQvfOQvMIJpVYgCVYJpyZyZyAVYgCuIxnxnxnnyJpFgQvfOQvQvfOQvsEQvQvQvHpMIQvQvQvQvQvQvQvZluBQvQvelQvpVMIilQvQvQvQvZlQvQAQvpVQvQvfOQvQvQvfOQvHpQvqDQvQvilelQvQvmJQvQvqDLfQvmJLfQvMIQvQvababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababQvpVfOHpQvHpQvfOfOtcMCJpqfjHMCgCVYhtMCMCyZyZyZyZyZyZyZyZyZKZyAMCMCVYVYPTQvyAMCqfVYVYyAjHKZJpMCyZyZyZyZyZUcJpQvqDQvuBQvQvLfQvQvMChQVYFgjHKZMCJpQvuBQvQvHpQvQvQvHpfOQvMILfQvHpQvQvVYVYhQMCFgjHMCVYhCuIthXrXrnyHpQviluBQvLfQvQvQvQvZlQvmJfOQvHpQvelQvpVsEQvQvQvpVQvQvsEQvfOQvfOQvmJuBQvQvsEQvfOQvmJQvnYQvQvQvmJuBQvQvLfQvMIQvHpQvfOQvQvQvQvQvQvuBHpababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababQvMIQvqfVYUcsEMCyAKZUcMCyZtcjZLKVYMCJpyZyZyZyZyZyZyZyZyZyZJpUcMChCVYMCelQvLfuBMCMCMChQVYMCqfjHMCyAMCJpMCVYQvQvelQvMImJQvQvZlQvMIQvMCyAMCMIQvQvMIfOLfQvQvmJpVsEQvLfQvmJMIsEQvLffOQvfOMCMCqfMCUcuBuIxnxnxnnyMIQvHpsEpVQvQvQvpVsEQvLfQvHpQvsEQvMIbRQvQvZlQvmJQvLfHpQvuBQvTvQvQvQvQvfOQvMIqDQvmJQvpVQvQvQvZlQvLfQvmJQvQvsEQvQvmJQvmJuBfOQvQAQvsEQvuBabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababZltcgCjZVYJpKZjHFgMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCMCMCMCQvHpQvLfQvZlQvQvHpMCUcMCFgMCMIMCMCqDKZMCZlQvQvpVQvQvQvQvZlQAQvQvfOQvLfQvQvQvQvfOQvQvQvQvuBQvQvuBQvQvQvQvQvQvpVQvQvuBQvHpQvQvMILfQvuIxnxnxnnyQvQvQvMIQvQvmJuBQvQvQvQvsEilZluBQvQvLfQvfOQvQvLfQvQvQvLfQAQvQvpVQvQAQvQvLfQvfOQvZlQvQvQvQvmJQvQvQvHpQvQvfOQvQvLfQvQvQvQvsEQvQvqDQvpVQvabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababMCJpKZyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZUctcMCyAqfMCqDQvQvfOQvQvfOQvLfMCQvuBHpQvpVQvQvQvQvuBQvQvQAHpQvfOsMQvQvQvQvQvMIuBQvQAQvpVQvQvelQvfOQvQvmJMIQvfOQvnYQvQvQvsEQvQvmJQvQvpVQvQvqDuIxnxnxnnyuBmJLfQvHpQvQvQvelQvfOQvpVQvfOQvQvmJQvQvmJpVLfQvfOQvmJHpQvMILfsEQvuBQvmJpVQvsEQvQvQvuBQvQvQvfOQvLsLsLsLsQvMIQvsEpVQvLfQvfOZlQvQvLfQvababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababMCUcFgtcyAJpqfjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZmDyZjHMCMCKZMCMCMCQvelQvuBQvmJZlQvQvHpQvsEQvMIQAQvuBQvfOQvMILfQvQvuBQvQvsELfQvmJHpsEQvZlQvsEQvQvmJQvHpQvpVQvQvfOilQvsEQvQvfOuBQvfOQvQvnYQvQvQvQvMIuIxnxnxnnyQvQvQvsEQvfOQvQvQvQvQvmJQvQvQvQvQvQvpVQvQvQvsEMIQvZlQvQvfOQvQvqDfOQvQvQvQvQvuBQvQAQvQvfOmJMILsaWLskeLILsLsLsQvHpQvfOQvmJQvQvQvmJQvMILfabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababJpyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHKZyZMCJpMCqfMCFgQvLfQvQvQvQvQAQvMIQvmJZlQvuBfOQvilQvQvsEQvQvmJQvQvQvQvmJLfQvQvZlQvQvQvQvQvpVQvLfQvqDQvQvsEQvLfQvQvfOQvQvQvHpQvfOQvQvMIQvQvQvQvmJuBZluIxnxnxnnyMIQvpVQvuBQvQvmJLfQvHpQvqDelQvpVQvfOQvQvQAQvHpQvfOQvsEQvQvsEQvQvQvQvfOQvmJsEQvHpQvLfQvQvLsLILsLsLsLsLsLsLILsLsLsQvQvQvQvQvQAQvQvHpQvababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababMCtcjHMCabqfjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZUcqfMCyAMCVYMCMCQvQvHpQvQvmJLfQvQvQvLfQvQvQvQvQvQvqDZlmJpVQvHpQvQvpVQvelQvQvQvQvQvmJQvfOQvmJQvQvQvQvQvQvLfQvuBQvsELfQvQvQvmJpVQvQvQvQvelLfQvuBQvMIQvQvQvuIxnxnxnnyQvQvQvZlQvsEQvMIQvQAQvQvsEQvQvmJQvZlQvmJQvuBilQvLfuBQvQvpVsEQvmJQvHpQvQvQvilfOMIQvLsLsLsLsababababababLsLsLsLskeLsLsLsZlQvQvHpQvfOabababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababJpMCKZyZyZFgyAMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCMCMCFgMCMChQMCyAQvLfQvQAQvQvfOQvsEHpuBQvelQvpVQvsEQvQvQvQvelQvfOQvQvQvLfqDQvfOHpQvQvQvuBQvQvQvnYQvsEZlQvmJQvQvpVQvQvQvQAQvQvQvsELfQvmJHpQvQvmJfOQvLfQvQvuIxnxnxnnyqDLfQvQvLfQvQvQvpVQvQvpVilMIQvQvQvQvMIQvHpQvQvmJfOQvHpQvHpfOQvQvLfsEQvMIfOQvQvQvLsabababababababLsLsababLsLsLILsLsLsLsLsLsLsLsMIababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCtcMCJpQvFgMCQvLfQvsEpVQvqDMIQvZlQvQvQvLfQvQvQvfOQvMILfQvZlQvQvQvQvQAQvLfsEQvpVQvQvpVQvQvQAQvHpQvQvQvQvQvMIQvLfilQvHpQvQvQvZlqDQvMIQvQvQvQvQvsEQvQvQvQvHpuIxnxnxnnyQvQvQvQAQvQvfOQvQvQvmJQvQvfOHpQvnYQvQvLfsEqDQvQvQvQvpVmJQvQvMIQvHpQvpVQvQvZlQvabLsababLsLsLBLsLsLsLILsabababLsababLsLsLsaWLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaababababKZFgtcjHyAUcFgtcyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHMCUcyZyZyZyZMCjHMCMCyAMCQvuBQvLfQvQvQvMIQvQvsEQvLfHpQvQvmJQvQvuBQvmJQvHpQvQvmJQvQvLfQvTIQvuBQvQvQvQvQvfOQvsELfQvQvQvuBQvLfQvHpQAQvQvQvmJQvQvmJMIQAQvQvZlQvuBQAQvfOQvQvQvmJMIMIuIxnxnxnnyQvHpQvilMImJHpQvLfQvuBZlQvQvQvQvQvpVQvQvQvQvLfQvQAQvQvQvLfQvfOuBQvQvmJMIQvLsLsLsLsLsLsLsLILsLsaWLsLskeLsLsabLsLsabababLsLsLsLILsababababababababababababababababababababababababababababababaaaa
-aaaaababqfUcyAyZyZyZyZyZqfyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyZyZyZUcVYhQVYagMCJpMCyAMCqfKZMCFgQvelHpQvQvQvfOQvHpQvLfQvilQveluBQvelqDQvQvZlQvQvpVQvQvelQvHpQvQvLfQvmJQvLfQvmJQvQvQvQvQvZlQvmJQvQvQvQvQvsEQvqDQvQAQvuBQvQvQvmJfOsEHpQvQvuBsEbiQvQvqDQvuIxnxnxnnyMIQvQvQvQvQvQveluBQvfOQvQvmJLfQvsEuBQvmJpVQvQvLfQvQvmJZlQvLsQvQvQvLsLsLskeLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
-aaaaababFgyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCqfgChCMCMCVYVYjZVYMCKZMCMCUcMCMCQvQvQvQvQvQvmJuBZlQvmJQvQvfOQvQvLfQvZlQvQvQvLfQvQvmJQvfOQvQvqDQvfOQvuBQvQvfOQvQvuBZlQvmJMIsEQvQvQvQAQvmJpVQvQvQvfOMIQvQvLfQvMIQvQvMIQvQvQvmJQvQvQvfOQvLfQvuIxnxnxnnyuBQvpVQvZlLfQvQvQvQvZlQvpVQvQvfOQvQvQvQvQvQvmJZluBQvQvQvLsLsLsLsLsLsLILsLsLsababLIabababqwacqwacDMacacacLsLsLsabLsLsLsLsLsLsLskeLsLsababababababababababababababababababababababababababababaaaa
-aaaaababyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCUcjZVYMCMCUeMCMCyAQvHpMCtcMCQvMIfOQvHoQvLfQvQvQvQvZlQvXEQvuBQvmJQvQvsEQvLfQvQAQvHpQvuBQvsEQvLfQvQvQvsEQvLfQvqDQvQvQvQvQvQvQvQvfOQvQvQvHpQvLfQvQvQvQvsEQvQvfOQvpVQvsEQvLfQvQvQvLfQvQvQvQvQvuIxnxnxnnyQvQvQvQvuBQvfOHpQvmJQvfOQvQvQvQvQvZlQvfOHpMIQvQvLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababacqwacacqwacacacacqwababababLsLsLILsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZtcyZKZJpyAjHMCQvMCtcQvmJMCMCMCFgMCQvMIQvZlQvZlQvQvQvQvHpQvQvpVsELfQvQvQvQvfOQvQvpVQvfOQvQvmJQvZlQvQvpVQvHpQvQvQvmJpVQvMIQvQAQvelQvmJLfQvpVQvqDQvQvsEQvMIQvsEQvQvmJuBQvHpQvQvmJQvQvZlQvQvqDelQvQvsEQvHpQvuBuIxnxnxnnyQvZlQvQvQvHpQvQvQvQvLIMILsLsuBQvLfLsQvQvQvLsLsLsLsLsLskeLsLsLsLsLsLsLsababababababababacqwqwacacqwacacqwacqwababababLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZFgFgMCyAababZlQvmJMIQvHpuBQvQvJpQvLfQvsEQvQvmJQvHpsELfuBQvmJsEQvQvQvQvKEQvQvQvMIQvsEHpQvpVilcpZlQvQvmJsEQvQvuBQvfOQvLfQvmJHpQvMIQvQvqDsEQvQAQvQvmJLfQvQvVhQvuBMIQvQvpVQvQvelQvQvQvQAQvQvfOQvQvQvuBMIQvQvQvmJuIxnxnxnnyQvQvQvQvTIQvQAQvLfLsLsLsLsLsLsLsQvpVLsLsLsLsLsLsLsLILsLsLsLsLsLILsLsLsabababababababqwqwqwXgYwMkqwacBIacacqwabababababLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyAababababababQvpVQvsEQvQvQvKEQvQvQvuBQvqDQvQvQAQvQvQvQvZlQvMIQvHpQvmJQvQvmJMIQvLfuBQvQvsEMIQvLfQAuBQvMIQvQAQvQvHpQvQvQvQvQvfOQvQvZlQvHpQvQvuBQvQvQvQvZlQvQvQvQAHpQvfOQvLfQvQvHpLfQvQvQvQvQvmJfOQvQvLfQvQvMIuIxnxnxnnyqDQvLfQvQvQvQvQvLsLsLILsLsLsLsLsLILskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababacBIqwacacqwacacqwacacababababababLskeLsLsLsLsLILsabababababababababababababababababababababababababababaaaa
-aaaaababyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZqfUctcjHababababababuBQvmJqDQvelQvQvQvZlQvfOQvmJLfQvQvQvQvHpelQvQvQvLfQvQvQvQAQvQvQvQvHpQvLfQvQvQvQvQvQvQvQvfOQvQvQvmJMIQvuBQvmJQvQvQvHpQvLsQvfOQvQvfOQvLsLILsLsLfQvQvQvLsLsQvQvfOuBQvQvLILsLsMIQvQvQvLsLsLILsLsLsuIxnxnxnnyQvQvQvQvpVLsLsLsLsLskeLsaWLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsLsLsLsababababababqwacacacacacLjqwYNqwYwacqwabababababLsLsLsLsLBLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababyAyZyZyZyZyZJpyZyZyAtcFgJpKZyAjHabababababababababQvZlQvfOQvpVQvmJQvQvsEMIQvpVQvQvpVQvmJQvQvQvQvmJQvQvMIQvQvqDQvLfelQvQvQvZlQvLfQvmJpVsEZlQvHpQvQvQvQvelQvQvQvQvpVQvLfLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsQvQvLsLsLsLsaWLsLsLsLsLsLsLILsLsLsuIxnxnxnnyQvQvHpQvLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababqwqwqwXghmqwqwacBIqwqwqwacabababababLsLsLILsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababFgyZyZyZyZFgqfjHUcMCabababababababababababababababababQvQvsEQvQvQvLfQvHpQvHpQvQvQvsEQvQvZlpVilqDQvZlQvnYQvQvsEuBQvQvpVQvmJQvsEQvqDQvQvQvQvLsLspVLsLfQvQvQvLfQvHpQvLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLILsuINUNUNUnyLsMIQvLsLsLsLsLsLsLILsLsLsLsLsLsLsLsBRLsLsLsLsLsLskeLsLsLsLsLsLsLILsababababababababacacqwacqwMkqwqwqwacqwqwabababababLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababJpjHtcUcyAKZababababababababababababababababababababQvQAQvHpQvMILfQvQvelQvQvmJQAQvqDQvuBQvQvQAQvQvQvmJQvpVQvQvQvQvfOQvQvQvLfuBQvQvQvLfQvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsabababLsabababLsLsLsLsLsLsLsLsLsLsLsLsLILsLskeLsLsLsLsLILsLsLILsLsLsLsuIxnxnxnnyLsLsLsLskeLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsabababababababababqwqwqwqwXgacqwqwqwababababababLsLsLsLsLsBRLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababQvQvMIQvQAQvQvQvmJQvpVQvQvQvQvLfQvHpmJQvQvQvpVQvQvQvQvQvLfZlQvQvLsLfLsQvQvHpfOQvQvLsLsLILsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsabababababababLsLsBRLsLskeLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsXHXHsuxnxnxnVUXHXHLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLBLsLsLsLsLskeLsLsLsababababababababababababqwqwqwqwabababababababLsLsLsLsLsLsLsLskeLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababfOQvQvmJQvQvfOQvQvQvilLfQvpVQvQvMIQvQvQvQvsEQvLfQvuBLsLsQvQvLsLsLILsLsLsLsLsLsLsLILsLsLsLsLsLsababLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsababababababLsLsLsLsLBLsuIxnxnxnnyLsLsLsLsLsaWLsLsababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababLsLILsLsLsaWLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababQvsEQvqDZlQvuBQvLfmJLfQvsEQvQvmJQvQvLfQvpVQvLsLsLsLsLsLsLsLsLsLsLsLsabababababLsLsLsLsLsLILsabababLsLsLsLsLsLsLILsLsabababababababLsLILsLsLsaWLsLsLsLILsLsLsLsLsababababababababLsLILsLsLsLIuIxnxnxnnyLsLsLsLsLsLsLsLsababababababababLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsababababababababababababababababababababLsLsLsLsLsLsLsLsLsBRLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababQvQvuBZlQvQvmJQvQvQvMIQvQvZlQvQvQvQAQvqDQvQvLsLsLsLILsLsLsLsLsLskeLsLsabababababLsLsLsBRLsLsLsabababababLsLsLsLsLsLsLsLsLsababababababababLsLsLsLsLsLBLsLsLsLsLsLsababababababababLsLsLsXpLsLsuIxnxnxnnyLsXpLsLsLsLsLsLsababababababababLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsBRLsLsLsLILsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababQvmJLfQvelQvQvsEQvfOQvLsLsLsLILsLsQvQvQvLsLskeLsLsLsLILsLsLsLsLsLsLsababababababababLsLsLskeLsLsababababLsLsLskeLsLsLILsLsLsababLsababababLsLsLsLsLsLsLsLsLsLILsabababababababababLsLsLsLsLsLsuIxnxnxnnyLsLsLsLILsLsababababababababababLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsLsLsLsLsabababababababababababababababLsLskeLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababQvpVQvQvQvpVQvQvLfQvQvLsLILsLsLsLsLsLsLBLsLsLsLsaWLsLsLsLsLILsLsLILsababababababLsLsLsLILsLsLsLsLsababLsLsLILsLsLsLsLskeLsLsababLsLsLskeLsLsLsLsLsLsLsLskeLsLsLsababababababababLsLsLsLsLskeLsFwXrXrXreILsLsLsLsLsLsababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLskeLsLsLsLsLILsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababQvQvQAQvBRLILsLsBRZlLIkeLsLsLsLsLILsLsLsLILsLILsLsLsLsLsLsLskeLsLsLsLsLsLsLsabLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsLsLILsLsLsLsFwxnxnxneILsLsLskeLsLsLsLsLsLsLsLsababLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLskeLsLsLsLsLsLsababLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababpVQvkeLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLswlxnxnxnnyXpLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXqPsyPwsyfHyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLILsLsLILsabababLsLsLsLskeLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLILsLsLILsLsLsLsLsLsLskeLsLsLsLsLsLILsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLILsLsLsuIxnxnxnnyLsLsLILsLsLskeLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLILsLsLsabLsLsLsLsLILsLsLILsLsLsLsLILsLsLsLsaWLsLsLsLILsLsLsLILsLsLsLsLsaWLskeLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababLsababababababababababLsLsLsLILsLsLsLsLsLsLskeLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsababLsLILsLsLsLsLskeLsLsLsLsLsLILsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsXpLsLILsuIxnxnxnnyLsLsLsLsLsLsLsLsLILsLsLsLILsLskeLsLsLsLsLsLsLsabLsababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsabababLsabLsLsababLsLIabababababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababajababababLILsLsLsLsLsLsLsLsLsLsLsababababLsababababababLsLsLskeLsLsaWLsLsLsLILsLsLsLsLsLILsLsabababpuCqCqCqpuLsLsLsLsLsLskeLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLILsLskeLsLsLsLsLsuIxnxnxnnyLsLsXpLsaWLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsabababababababababababababLsLILsLsLsLskeLsLsLsLILsabababababababababLIabababababababababLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababajajajabababababLsababababababababababababababababajajababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababpupuCqQuCqpupuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsuIxnxnxnnyLsLsLsLsLsLsLsLssLsLsLsLsLLsLsLsLsLsLsababababababababababababababababLsLsaWLsLILsLsababababababababababababababababababababababLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababajakajajababababababababababababajajajajajajajajajajajababababLsLsLsLsLILsLsababLsLsLsLsabababababCqCqCqCqCqCqCqCqCqLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLssLsLsLsLsLLsLsLsPhPhPhPhPhuIxnxnxnnysLsLsLsLsLLsLsLssLcscscssLLsLsLsLsLsLsababababababababababababababababLsabLsLsLsLsLsababababababababababababababababLsabababLsLsLsLsLsLILsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababajakakajajajajababababababababajajakakakakakakakakakajajababababababLsLsabababababababababababLspuCqCqCqCqOwCqCqCqCqpuLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLssLcscscssLLsLsLsLsLILsLsLsuIxnxnxnnysLVZcscssLLsXpLssLcsnmcssLLsLsLsXpLsabababababababababababababababababababLsababLsabababababababababababababLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababajajajajajakakalakajajajajajajajajajajajakakakakakakajajakakakajajabababababababababababababababababLspupuQuCqOwCqCqCqOwCqQupupuLsLsLsLsLsLsLsLsLsLsLsLsLILsXpLsLssLcsnmcscsLsLsLsLsLsLsLsLsuIFsxnxnnycscsnmcssLLsLsLssLVZcscssLLsLsLsLsLsababababababababababLsLsabLsLsLsabababababababababababLsLsLsababababLsLsLILsLsLsLsLsLsLsLsLsLskeLsLsabLsLsabababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababajakakakakakakakakajajakakakakakakakakakakakakakajajajakakakakajabababababababababababLsabLsLsLsLsLsCqCqCqCqCqCqCqCqCqCqCqCqCqLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLssLVZcscssLLsXpLssLsLsLsLsLuIxnxnxnnysLcscscssLLsLsLssLsLcssLsLLsLsLsLsLsabababababababLsLsLsLsLsLsLsLsLsabababababababLsLsLsLsLIDELsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababajakakakakamakakakajajajakakakakakakajajajakakajajajakakakakakajabababababababababLsLsLsLsLsLsLILsLsCqCqCqOwCqCqzWCqCqOwCqCqCqLsLsLsLsLsLskeLsLsLskeLsLsLsLsLsLssLsLsLsLsLLsLsLssLcsVZcssLuIxnxnxnnysLsLsLsLsLLsLsLsLsLsXpLsLsLsaWLsLsababababababLsLsLsLskeLsLsLsLsLILsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsaWLsLsLsLsDELsLsLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajajajajakakakakakakakakakajajakakakakakakakajajakakakakakakakakakakajajababababababhshsLsLsLsLskeLsLsLsLsCqCqCqCqCqCqCqCqCqCqCqCqCqLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskesLcsnmcscsuIxnxnxnnyLsLsLsLsLsLskeLsLILsLsLsLsLsLsLsLsabababababLsLsLsLILsLsLsDELsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsDELsLsLsLILsLsLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababajajakakakakakajakakakakakakakakakakakakamakakakakakamakakakakakakakakakajababababababCqhshsLsLsLILsLskeLsLspupuQuCqOwCqCqCqOwCqQupupuLsLsLsLsLsLsLskeLsLsLsLILsLsaWLsLsLssLsLsLsLsLLsLssLcscscssLuIxnxnxnnysLsLsLsLsLLsLsLssLsLsLsLsLLsLsLsLsLsababLsLsLskeLsLsLsLsaWLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLILsLsLsLsDELsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajakakakakajajajakakakakakakakakakakakajajakakakakakakajakajakakakamakajajajajajababCqCqhshsLsLsLsLsaWLsLsLspuCqCqCqCqOwCqCqCqCqpuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLssLcscscssLLsLssLsLsLsLsLuIxnxnxnnysLcscsVZsLLsLsLssLcscsVZsLLsLskeLsababLsLsLILsLsLseMLsLsLsLsLsLILskeLsdtdtdtdtdtdtdtdtdtdtLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajajakakakajajakakakakakakakakakakajajajajakakakakajajajajajakakakakakakakakakajajCqCqCqCqhshsLskeLsLsLsLsLILsCqCqCqCqCqCqCqCqCqLsLsLsLskeLsLILsLsLsLskeLsLsLsLsLsLsLsLssLcsnmVZsLLsLsLsXpLsLsPhuIxnFsxnnycscsnmcssLLsLsLscscsnmcssLLsLILsLsababLsLsLshKLsLBLsLskeLsDELsLsLsLsdtdtLyGTLyPALyGTLyGTdtdtLsLskeLsLsLsLILsAvAvAvAvAvAvAvAvAvLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababajakakakakakakakakakajajajakakakakajajakakakakakakajajajajajakakakakakakakakajajCqCqawCqCqhshsLsLsLskeLsLsLsLspupuCqQuCqpupuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLssLcscscssLLsLsLsLsLsLsPhuIxnxnxnnysLcscscssLLskeLssLcscsVZsLLsLsLsLsabababLseMLsLsDELILshKLsLsLseMLsdtdtPAGTGTGTGTGTGTGTGTPAdtdtLsLsLsLsLsLsLsAvCbCbCbCbCbCbCbAvLsLsLsababababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajajakakakakakakakakakakajakakamakakakakakakakakamakakakajajakakakakakakajajajajCqCqCqCqCqCqCqhsLsLsLsLsLsLsLsLsLspuCqCqCqpuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLssLsLcssLsLLsLsPhPhPhPhPhuIxnxnxnnysLsLsLsLsLLsLsLssLsLsLsLsLLsLsLsLsababLsLsLsLsNNLseMLsNNLsnhLBLsdtdtGTGTGTSuGTGTGTGTGTGTGTGTdtdtLsLsLsLsLsLsAvCbOiOiUGOiOiCbAvaWLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajajakakakamakakakakajajajakakakakakakakakajajakakakakakakakakakakakakakajmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTZamTmTmTmTmTmTmTmTmTmTmTmTmTmTmTxnxnxnxnxnmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTmTdimTJwIVNeJwmTNemTfJIVJwmTmTkhdtGTGTVMGTGTcxOyCyEyGTGTVMGTGTdtdtdtdtdtdtdtAvCbOiPCNkPCOiCbAvLsLsLsLsabababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababajakakakakakakakakajajakajakakakakakakajakakakakakakakakakakakajakakakajxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnXrxnxnxnxnxnxnxnxnFsxnxnxnxnxnxnxnxnXrxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnNUxnnpxnxnxnrDxnShEjxnxnShEjnyIUGTGTVMGTGTGTGTGTGTGTGTVMGTGTGTGTGTPAGTGTIUAvCbUGDkRjDkUGCbAvLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababajajajakajajajakakakakakakakakakakakakajajakakakakakajakakamakajajajakakajxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnXrxnxnxnxnxnxnxnxnxnxnxnxnxnOlxnxnxnXrxnxnxnxnFsxnxnxnxnxnxnxnxnxnxnxnNUxnxnxnQMxnmkDQDQmkxnEixnxnKOdtrtGTdtrtGTnLGgavbcGTpddtGTGTGTGTGTGTGTKcdtAvCbEIKnKnVyEICbAvLILskeLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababajajajabajakakakakakakakakajakakakajajakakakakajajajakakakakajakakakakxnxnxnxnzFxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnXrxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnXrxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnxnNUxnnpxnxnxnnpxnQMxnShxnxnrDnyIUGTGTVMGTGTGTGTGTGTGTGTVMGTGTZqGTGTGTGTGTIUAvCbEIMsYgMsEICbAvLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababajajajakakakakakakajajakakakakakakakajajajakakakakakajakakakajwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvAWwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvwvuCwvwvwvWULvwvwYGbwvwvLvrgwvsCdtGTGTVMGTGTeaRbjRTMGTGTVMGTGTdtdtdtdtdtdtdtAvCbOiOiOiOiOiCbAvLsDELsLILsLsabababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababajajakamakakajajajakakakakakakakakakakakakakakakakakakakajCqCqCqCqCqCqCqCqCqCqhsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsPhLsLsLsLssLsLcssLsLLsPhPhPhLssLsLcssLsLLssLsLcssLsLLsLsLsLsLILsLsLsLsababLsNNeMLsnhLsLseMLskiLsLBkidtdtGTGTGTSuGTGTGTGTGTGTGTGTdtdtLsLsLsLsLsLsAvCbOiJBJBJBOiCbAvLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababajajajakakakajakajakamakakakakakakakajakakakakakakakajajCqCqCqCqCqCqCqCqCqhshsLsLsLskeLsLskeLsLsLsLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLssLVZcscssLLsLskeLsLssLVZcscssLLssLcscscssLLsLskeLsLsLsLsLsababababLsLsLskeLsLBLsLshKLseMLsLsdtdtZqGTGTGTGTGTGTGTGTZqdtdtLsLsLsLILsLsLsAvCbLPLPLPLPLPCbAvLsLsLsaWLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababajakakakakakakakakakakakakakajajajakakakakakakajajCqCqCqCqCqCqCqCqCqhshsLsLsLsLsLsLsLsaWLsLsLILsLsLsLILsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsXpLsLssLcsnmVZsLLsaWLsLsLssLcsnmcssLLssLcsnmcssLLILsLsLsLsabababababababababLBLshKLskiLsLskeLsLsDELsdtdtLyGTLyZqLyGTLyGTdtdtLsLsLskeLsLsLsLsAvCbCbCbCbCbCbCbAvLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababajajakakakakakajajajakakakakajajajajakakamakajajCqCqawCqCqCqCqCqCqhshsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLssLcscscssLLsLsLsLsLssLcscscssLLssLVZcscssLLsLsababababababababababababLsLsLsLsLsDELsLsLsLsLsLsLsdtdtdtdtdtdtdtdtdtdtLsLsLsLsLsLsLILsLsAvAvAvAvAvAvAvAvAvLsLskeLsLsababababababababababababababababababababababababababaaaa
-aaaaababababababababababababababababababababababababababababababababababababababajakakakajajajabajajajajajajajajakakakakajajCqCqCqCqCqCqCqCqCqhshsLsLskeLsLsLsLsLskeLsLsLsLsLskeLsLsLsLsLsabLsLsLILsLsLsLsabLsLsLsLsLsLsLILsLsLsLsLsLsLssLsLsLsLsLLsLsLsababsLsLsLsLsLLssLsLsLsLsLabababababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLILsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababQvLfQvmJpVQvmJqDsEpVQvQvZlQvHpQvUcMCKZMCtcMCJpyZyZyZyZyZyZyZjHMCMCMCMCMCqfVYMCtcMCyZyZyZyZyZyZyZyZyZyZyZyZyZMCtcJpMCUcMCKZMCyAMCyZyZyZyZyZyZyZyZyZyZUcjHFgJpMCfOZlQvqfQvuBMCyAMCtcMCjHyZyZyZyZdQjZaZaXaXaXaYKZhQMCyAMCQvQvqDQvMILfQvQvQvmJpVQvmJfOQvLfsEQvfOQvQvqDQvQvelQvZlQAQvqDMIQvHpQvmJqDQvMIpVQvQvQvQvZlfOQvQvmJQvZlQvQvLfQvsEQvMIQvQvQvmJfOQvababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababsEQvqDQvQAQvLfQvQvQvLfQvMCMCyAMCMCMCMCyAMCjHyZyZyZyZyZyZyZyZFgMCUeVYhCMCKZMCJpMCMCFgyZyZyZyZyZyZyZyZyZyZyZjHyAMCMCZltcQvQvfOMCUcVYdQyZyZyZyAMCqfjHFgyAMCQvMCQvMIuBQvQvQvfOQvMIJpVYgCVYJpyZyZyAVYgCaZaXaXaXaYJpFgQvfOQvQvfOQvsEQvQvQvHpMIQvQvQvQvQvQvQvZluBQvQvelQvpVMIilQvQvQvQvZlQvQAQvpVQvQvfOQvQvQvfOQvHpQvqDQvQvilelQvQvmJQvQvqDLfQvmJLfQvMIQvQvababababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababRMQvpVfOHpQvHpQvfOfOtcMCJpqfjHMCgCVYhtMCMCyZyZyZyZyZyZyZyZyZKZyAMCMCVYVYPTQvyAMCqfVYVYyAjHKZJpMCyZyZyZyZyZUcJpQvqDQvuBQvQvLfQvQvMChQVYFgjHKZMCJpQvuBQvQvHpQvQvQvHpfOQvMILfQvHpQvQvVYVYhQMCFgjHMCVYhCaZbqbrbraYHpQviluBQvLfQvQvQvQvZlQvmJfOQvHpQvelQvpVsEQvQvQvpVQvQvsEQvfOQvfOQvmJuBQvQvsEQvfOQvmJQvnYQvQvQvmJuBQvQvLfQvMIQvHpQvfOQvQvQvQvQvQvuBHpababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababRMRMQvMIQvqfVYUcsEMCyAKZUcMCyZtcjZLKVYMCJpyZyZyZyZyZyZyZyZyZyZJpUcMChCVYMCelQvLfuBMCMCMChQVYMCqfjHMCyAMCJpMCVYQvQvelQvMImJQvQvZlQvMIQvMCyAMCMIQvQvMIfOLfQvQvmJpVsEQvLfQvmJMIsEQvLffOQvfOMCMCqfMCUcuBaZaXaXaXaYMIQvHpsEpVQvQvQvpVsEQvLfQvHpQvsEQvMIbRQvQvZlQvmJQvLfHpQvuBQvTvQvQvQvQvfOQvMIqDQvmJQvpVQvQvQvZlQvLfQvmJQvQvsEQvQvmJQvmJuBfOQvQAQvsEQvuBabababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababRMZltcgCjZVYJpKZjHFgMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCMCMCMCQvHpQvLfQvZlQvQvHpMCUcMCFgMCMIMCMCqDKZMCZlQvQvpVQvQvQvQvZlQAQvQvfOQvLfQvQvQvQvfOQvQvQvQvuBQvQvuBQvQvQvQvQvQvpVQvQvuBQvHpQvQvMILfQvaZaXaXaXaYQvQvQvMIQvQvmJuBQvQvQvQvsEilZluBQvQvLfQvfOQvQvLfQvQvQvLfQAQvQvpVQvQAQvQvLfQvfOQvZlQvQvQvQvmJQvQvQvHpQvQvfOQvQvLfQvQvQvQvsEQvQvqDQvpVQvabababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababRMRMRMRMRMRMRMMCJpKZyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZUctcMCyAqfMCqDQvQvfOQvQvfOQvLfMCQvuBHpQvpVQvQvQvQvuBQvQvQAHpQvfOsMQvQvQvQvQvMIuBQvQAQvpVQvQvelQvfOQvQvmJMIQvfOQvnYQvQvQvsEQvQvmJQvQvpVQvQvqDaZaXaXaXaYuBmJLfQvHpQvQvQvelQvfOQvpVQvfOQvQvmJQvQvmJpVLfQvfOQvmJHpQvMILfsEQvuBQvmJpVQvsEQvQvQvuBQvQvQvfOQvLsLsLsLsQvMIQvsEpVQvLfQvfOZlQvQvLfQvababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababRMRMMCUcFgtcyAJpqfjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZmDyZjHMCMCKZMCMCMCQvelQvuBQvmJZlQvQvHpQvsEQvMIQAQvuBQvfOQvMILfQvQvuBQvQvsELfQvmJHpsEQvZlQvsEQvQvmJQvHpQvpVQvQvfOilQvsEQvQvfOuBQvfOQvQvnYQvQvQvQvMIaZaXaXaXaYQvQvQvsEQvfOQvQvQvQvQvmJQvQvQvQvQvQvpVQvQvQvsEMIQvZlQvQvfOQvQvqDfOQvQvQvQvQvuBQvQAQvQvfOmJMILsaWLskeLILsLsLsQvHpQvfOQvmJQvQvQvmJQvMILfabababababababababababababababababababababababababababaaaa
+aaaaababababababababababababRMRMRMRMRMRMRMJpyAyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHKZyZMCJpMCqfMCFgQvLfQvQvQvQvQAQvMIQvmJZlQvuBfOQvilQvQvsEQvQvmJQvQvQvQvmJLfQvQvZlQvQvQvQvQvpVQvLfQvqDQvQvsEQvLfQvQvfOQvQvQvHpQvfOQvQvMIQvQvQvQvmJuBZlaZaXaXaXaYMIQvpVQvuBQvQvmJLfQvHpQvqDelQvpVQvfOQvQvQAQvHpQvfOQvsEQvQvsEQvQvQvQvfOQvmJsEQvHpQvLfQvQvLsLILsLsLsLsLsLsLILsLsLsQvQvQvQvQvQAQvQvHpQvababababababababababababababababababababababababababababaaaa
+aaaaababababababababababRMRMRMMCtcjHMCRMqfjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZUcqfMCyAMCVYMCMCQvQvHpQvQvmJLfQvQvQvLfQvQvQvQvQvQvqDZlmJpVQvHpQvQvpVQvelQvQvQvQvQvmJQvfOQvmJQvQvQvQvQvQvLfQvuBQvsELfQvQvQvmJpVQvQvQvQvelLfQvuBQvMIQvQvQvaZaXaXaXaYQvQvQvZlQvsEQvMIQvQAQvQvsEQvQvmJQvZlQvmJQvuBilQvLfuBQvQvpVsEQvmJQvHpQvQvQvilfOMIQvLsLsLsLsababababababLsLsLsLskeLsLsLsZlQvQvHpQvfOabababababababababababababababababababababababababababababaaaa
+aaaaababababababababababRMJpMCKZyZyZFgyAMCyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCMCMCFgMCMChQMCyAQvLfQvQAQvQvfOQvsEHpuBQvelQvpVQvsEQvQvQvQvelQvfOQvQvQvLfqDQvfOHpQvQvQvuBQvQvQvnYQvsEZlQvmJQvQvpVQvQvQvQAQvQvQvsELfQvmJHpQvQvmJfOQvLfQvQvaZaXaXaXaYqDLfQvQvLfQvQvQvpVQvQvpVilMIQvQvQvQvMIQvHpQvQvmJfOQvHpQvHpfOQvQvLfsEQvMIfOQvQvQvLsabababababababLsLsababLsLsLILsLsLsLsLsLsLsLsMIababababababababababababababababababababababababababababababaaaa
+aaaaabababRMRMRMRMRMRMRMRMjHyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCtcMCJpQvFgMCQvLfQvsEpVQvqDMIQvZlQvQvQvLfQvQvQvfOQvMILfQvZlQvQvQvQvQAQvLfsEQvpVQvQvpVQvQvQAQvHpQvQvQvQvQvMIQvLfilQvHpQvQvQvZlqDQvMIQvQvQvQvQvsEQvQvQvQvHpaZaXaXaXaYQvQvQvQAQvQvfOQvQvQvmJQvQvfOHpQvnYQvQvLfsEqDQvQvQvQvpVmJQvQvMIQvHpQvpVQvQvZlQvabLsababLsLsLBLsLsLsLILsabababLsababLsLsLsaWLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaabRMRMRMKZFgtcjHyAUcFgtcyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHMCUcyZyZyZyZMCjHMCMCyAMCQvuBQvLfQvQvQvMIQvQvsEQvLfHpQvQvmJQvQvuBQvmJQvHpQvQvmJQvQvLfQvTIQvuBQvQvQvQvQvfOQvsELfQvQvQvuBQvLfQvHpQAQvQvQvmJQvQvmJMIQAQvQvZlQvuBQAQvfOQvQvQvmJMIMIaZaXaXaXaYQvHpQvilMImJHpQvLfQvuBZlQvQvQvQvQvpVQvQvQvQvLfQvQAQvQvQvLfQvfOuBQvQvmJMIQvLsLsLsLsLsLsLsLILsLsaWLsLskeLsLsabLsLsabababLsLsLsLILsababababababababababababababababababababababababababababababaaaa
+aaaaabRMqfUcyAyZyZyZyZyZqfyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZjHyZyZyZUcVYhQVYagMCJpMCyAMCqfKZMCFgQvelHpQvQvQvfOQvHpQvLfQvilQveluBQvelqDQvQvZlQvQvpVQvQvelQvHpQvQvLfQvmJQvLfQvmJQvQvQvQvQvZlQvmJQvQvQvQvQvsEQvqDQvQAQvuBQvQvQvmJfOsEHpQvQvuBsEbiQvQvqDQvaZaXaXaXaYMIQvQvQvQvQvQveluBQvfOQvQvmJLfQvsEuBQvmJpVQvQvLfQvQvmJZlQvLsQvQvQvLsLsLskeLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsabababababababababababababababababababababababababababababaaaa
+aaaaabRMFgyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZMCqfgChCMCMCVYVYjZVYMCKZMCMCUcMCMCQvQvQvQvQvQvmJuBZlQvmJQvQvfOQvQvLfQvZlQvQvQvLfQvQvmJQvfOQvQvqDQvfOQvuBQvQvfOQvQvuBZlQvmJMIsEQvQvQvQAQvmJpVQvQvQvfOMIQvQvLfQvMIQvQvMIQvQvQvmJQvQvQvfOQvLfQvaZaXaXaXaYuBQvpVQvZlLfQvQvQvQvZlQvpVQvQvfOQvQvQvQvQvQvmJZluBQvQvQvLsLsLsLsLsLsLILsLsLsababLIabababqwqwqwqwDMqwqwqwLsLsLsabLsLsLsLsLsLsLskeLsLsababababababababababababababababababababababababababababaaaa
+aaaaabRMyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZJpMCUcjZVYMCMCUeMCMCyAQvHpMCtcMCQvMIfOQvHoQvLfQvQvQvQvZlQvXEQvuBQvmJQvQvsEQvLfQvQAQvHpQvuBQvsEQvLfQvQvQvsEQvLfQvqDQvQvQvQvQvQvQvQvfOQvQvQvHpQvLfQvQvQvQvsEQvQvfOQvpVQvsEQvLfQvQvQvLfQvQvQvQvQvaZaXaXaXaYQvQvQvQvuBQvfOHpQvmJQvfOQvQvQvQvQvZlQvfOHpMIQvQvLsLsLsLsLsLsLsLsLsBRLsLsLsabababababababqwqwqwqwqwqwqwqwqwqwababababLsLsLILsBRLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabRMyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZtcyZKZJpyAjHMCQvMCtcQvmJMCMCMCFgMCQvMIQvZlQvZlQvQvQvQvHpQvQvpVsELfQvQvQvQvfOQvQvpVQvfOQvQvmJQvZlQvQvpVQvHpQvQvQvmJpVQvMIQvQAQvelQvmJLfQvpVQvqDQvQvsEQvMIQvsEQvQvmJuBQvHpQvQvmJQvQvZlQvQvqDelQvQvsEQvHpQvuBaZaXaXaXaYQvZlQvQvQvHpQvQvQvQvLIMILsLsuBQvLfLsQvQvQvLsLsLsLsLsLskeLsLsLsLsLsLsLsababababababababqwqwqwqwqwqwqwqwqwqwqwababababLsLsLsLsLsLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabRMyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZFgFgMCyARMRMZlQvmJMIQvHpuBQvQvJpQvLfQvsEQvQvmJQvHpsELfuBQvmJsEQvQvQvQvKEQvQvQvMIQvsEHpQvpVilQvZlQvQvmJsEQvQvuBQvfOQvLfQvmJHpQvMIQvQvqDsEQvQAQvQvmJLfQvQvVhQvuBMIQvQvpVQvQvelQvQvQvQAQvQvfOQvQvQvuBMIQvQvQvmJaZaXaXaXaYQvQvQvQvTIQvQAQvLfLsLsLsLsLsLsLsQvpVLsLsLsLsLsLsLsLILsLsLsLsLsLILsLsLsabababababababqwqwqwXgYwYNqwqwXgqwqwqwabababababLsLsLsLsBRLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabRMyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZyARMRMRMRMRMRMQvpVQvsEQvQvQvKEQvQvQvuBQvqDQvQvQAQvQvQvQvZlQvMIQvHpQvmJQvQvmJMIQvLfuBQvQvsEMIQvLfQAuBQvMIQvQAQvQvHpQvQvQvQvQvfOQvQvZlQvHpQvQvuBQvQvQvQvZlQvQvQvQAHpQvfOQvLfQvQvHpLfQvQvQvQvQvmJfOQvQvLfQvQvMIaZaXaXaXaYqDQvLfQvQvQvQvQvLsLsLILsLsLsLsLsLILskeLsLsLsLsBRLsLsLsLsLsBRLsLsLsLsLsabababababababqwXgqwqwqwqwqwqwqwqwqwababababababLskeLsLsLsLsLILsabababababababababababababababababababababababababababaaaa
+aaaaabRMyZyZyZyZyZyZyZyZyZyZyZyZyZyZyZqfUctcjHRMababababRMuBQvmJqDQvelQvQvQvZlQvfOQvmJLfQvQvQvQvHpelQvQvQvLfQvQvQvQAQvQvQvQvHpQvLfQvQvQvQvQvQvQvQvfOQvQvQvmJMIQvuBQvmJQvQvQvHpQvLsQvfOQvQvfOQvLsLILsLsLfQvQvQvBRLsQvQvfOuBQvQvLILsLsMIQvQvQvLsLsLILsLsLsaZaXaXaXaYQvQvQvQvpVLsLsLsLsLskeLsaWLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsLsLsLsababababababqwqwqwqwqwqwZWqwYNqwYwqwqwabababababLsLsLsLsLBLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabRMyAyZyZyZyZyZJpyZyZyAtcFgJpKZyAjHRMRMRMRMababababRMQvZlQvfOQvpVQvmJQvQvsEMIQvpVQvQvpVQvmJQvQvQvQvmJQvQvMIQvQvqDQvLfelQvQvQvZlQvLfQvmJpVsEZlQvHpQvQvQvQvelQvQvQvQvpVQvLfLsLILsLsLsBRLsLsBRLsLsLsLsLsLsLsLsLILsLsQvQvLsLsLsLsaWLsLsLsLsLsLsLILsLsLsaZaXaXaXaYQvQvHpQvLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsabababababababqwqwqwXgYwqwqwqwXgqwqwqwqwabababababLsLsLILsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabRMFgyZyZyZyZFgqfjHUcMCRMRMRMRMRMRMRMababababababababababQvQvsEQvQvQvLfQvHpQvHpQvQvQvsEQvQvZlpVilqDQvZlQvnYQvQvsEuBQvQvpVQvmJQvsEQvqDQvQvQvQvLsLspVLsLfQvQvQvLfQvHpQvLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsLsLILsaZbgbgbgaYLsMIQvLsLsLsLsLsLsLILsLsLsLsLsLsLsLsBRLsLsLsLsLsLskeLsLsLsLsLsLsLILsababababababababqwqwqwqwqwYNqwqwqwqwqwqwabababababLsBRLsLsLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabRMJpjHtcUcyAKZlQRMRMRMRMabababababababababababababababQvQAQvHpQvMILfQvQvelQvQvmJQAQvqDQvuBQvQvQAQvQvQvmJQvpVQvQvQvQvfOQvQvQvLfuBQvQvQvLfQvLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLsabababLsabababLsLsLsLsLsLsLsLsLsLsLsLsLILsLskeLsLsLsLsLILsLsLILsLsLsLsaZaXaXaXaYLsLsLsLskeLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsabababababababababqwqwqwqwXgqwqwqwqwababababababLsLsLsLsLsBRLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabRMRMRMRMRMbsbtbuRMababababababababababababababababababQvQvMIQvQAQvQvQvmJQvpVQvQvQvQvLfQvHpmJQvQvQvpVQvQvQvQvQvLfZlQvQvLsLfLsQvQvHpfOQvQvLsLsLILsLsLsLsLsLILsLsaWLsLsLsLsLsLsLsabababababababLsLsBRLsLskeLsLsLsLsLsLsLsLsLsabababLsLsLsLsLsLsLsXHXHbfaXaXaXbhXHXHLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLBLsLsLsLsLskeLsLsLsababababababababababababqwqwqwqwabababababababLsLsLsLsLsLsLsLskeLsBRLsLsababababababababababababababababababababababababaaaa
+aaaaabababababRMWCacacRMababababababababababababababababababfOQvQvmJQvQvfOQvQvQvilLfQvpVQvQvMIQvQvQvQvsEQvLfQvuBLsLsQvQvLsLsLIBRLsLsLsLsLsLsLILsLsLsLsLsLsababLsLsLsLsLsLsLsLsLsabababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsababababababLsLsLsLsLBLsaZaXaXaXaYLsLsLsLsLsaWLsLsababababababLsLsLsLsLILsLsLsLsLsLsLsLsLsBRLsLsLsLsLsabababababababababababababababababababababababLsLILsLsLsaWLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababRMRMacRMRMababababababababababababababababababQvsEQvqDZlQvuBQvLfmJLfQvsEQvQvmJQvQvLfQvpVQvLsLsLsLsBRLsLsBRLsLsLsLsabababababLsLsLsLsLsLILsabababLsLsLsBRLsLsLILsLsabababababababLsLILsLsLsaWLsLsLsLILsLsLsLsLsababababababababLsLILsLsLsLIaZaXaXaXaYLsLsLsLsLsLsLsLsababababababababLsLsLsLsLsLsBRLsLsLsLILsLsLsLsLsBRLsLsLsababababababababababababababababababababLsLsLsLsLsLsLsLsLsBRLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababbvbvbwbvbvabababababababababababababababababQvQvuBZlQvQvmJQvQvQvMIQvQvZlQvQvQvQAQvqDQvQvLsLsLsLILsLsLsLsLsLskeLsLsabababababLsLsLsBRLsLsLsabababababLsLsLsLsLsLsLsLsLsababababababababLsLsLsLsLsLBLsLsLsLsLsLsababababababababLsLsLsXpLsLsaZaXaXaXaYLsXpLsLsLsLsLsLsababababababababLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabababababababababababababababababababLsLsLsLsBRLsLsLsLILsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababbvPRbxbxbybybybybybyababababababababababababQvmJLfQvelQvQvsEQvfOQvLsLsLsLILsLsQvQvQvLsBRkeLsLsLsLILsLsLsLsLsLsLsababababababababLsLsLskeLsLsababababLsLsLskeLsLsLILsLsLsababLsababababLsLsLsLsLsLsLsLsLsLILsabababababababababLsLsLsLsLsLsaZaXaXaXaYLsLsLsLILsLsababababababababababLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsBRLsLsLsabababababababababababababababLsLskeLsLsLsLsBRLsLsLsLsBRLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababbybxZkbxbxbxPRbxZkbyababababababababababababQvpVQvQvQvpVQvQvLfQvQvLsLIBRLsLsBRLsLsLBLsLsLsLsaWLsLsLsLsLILsLsLILsababababababLsLsLsLILsLsLsLsLsababLsLsLILsLsLsLsLskeLsLsababLsLsLskeLsLsLsLsLsLsLsLskeLsLsLsababababababababLsLsLsLsLskeLsbzbrbrbrbBLsLsLsLsLsLsababababababababLsLsLsLsLsLsLsLsBRLsLsLsLsLskeLsLsLsLsLILsLsLsLsLsLsLsLsabababababababababababLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababbybxPRbxPRbxbxbxPRbyabababababababababababQvQvQAQvBRLILsLsBRZlLIkeLsLsLsLsLILsLsLsLILsLILsLsLsLsLsLsLskeLsLsLsLsLsLsLsabLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababLsLsLILsLsLsLsbzaXaXaXbBLsLsLskeLsLsLsLsLsLsLsLsababLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsBRLsLsLsaWLsLsLskeLsLsLsLsLsLsababLsLsLsLsLsLsLsLsLILsLsLsLsBRLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
+aaaaabababababbybybybybybybybxbxbyababababababababababababpVQvkeLsLsLILsLsLsLsLsLsBRLsLsLsLsLsLsLsLsBRLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsbDaXaXaXaYXpLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababababbybxPRbyababababababababababababyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXbFbGbHbGbIyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXyXabababababababababababababababababababababababababababaaaa
+aaaaabababababababababababbyZkbxbyababababababababababababLILsLsLILsabababLsLsLsLskeLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLILsLsLILsLsLsLsLsLsLskeLsLsLsLsLsLILsLsLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLskeLsLsLsLILsLsLsLsLsLsLsLILsLsLsaZaXaXaXaYLsLsLILsLsLskeLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLILsLsLsabLsLsLsLsLILsLsLILsLsLsLsLILsLsLsLsaWLsLsLsLILsLsLsLILsLsLsLsLsaWLskeLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababababbyPRbxbyababababababababababababLsababababababababababLsLsLsLILsLsLsLsLsLsLskeLsLILsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLsLsLsababLsLILsLsLsLsLskeLsLsLsLsLsLILsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsXpLsLILsaZaXaXcbaYLsLsLsLsLsLsLsLsLILsLsLsLILsLskeLsLsLsLsLsLsLsabLsababababLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsabLsabababLsabLsLsababLsLIabababababababababababababababababababababababababababababababaaaa
+aaaaabababababababababababbybxbxbybybybyajajajababababababababababababajababababLILsLsLsLsLsLsLsLsLsLsLsababababLsababababababLsLsLskeLsLsaWLsLsLsLILsLsLsLsLsLILsLsabababpuCqCqCqpuLsLsLsLsLsLskeLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsXpLsLILsLskeLsLsLsLsXpaZaXaXaXaYLsLsXpLsaWLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsabababababababababababababLsLILsLsLsLskeLsLsLsLILsabababababababababLIabababababababababLsLsLsababababababababababababababababababababababababababaaaa
+aaaaabababababababababababbybxbxbxPRbUakajajajajajabababababababababajajajabababababLsababababababababababababababababajajababababLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababpupuCqQuCqpupuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsaZaXaXaXaYLsLsLsLsLsLsLsLssLsLsLsLsLLsLsLsLsLsLsababababababababababababababababLsLsaWLsLILsLsababababababababababababababababababababababLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababababababbybxPRbxbxakJPakajakakajajababababababababajakajajababababababababababababajajajajajajajajajajajababababLsLsLsLsLILsLsababLsLsLsLsabababababCqCqCqCqCqCqCqCqCqLsLsLsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLssLsLsLsLsLLsXpLsPhPhPhPhPhaZaXaXaXaYsLsLsLsLsLLsLsLssLcscscssLLsLsLsLsLsLsababababababababababababababababLsabLsLsLsLsLsababababababababababababababababLsabababLsLsLsLsLsLILsabababababababababababababababababababababababababaaaa
+aaaaabababababababababababbybybybybwbybybyajamakakajajabababababababajakakajajajajababababababababajajakakakakakakakakakajajababababababLsLsabababababababababababLspuCqCqCqCqOwCqCqCqCqpuLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLssLcscscssLLsLsLsLsLILsLsLsaZaXaXaXaYsLVZcscssLLsXpLssLcsnmcssLLsLsLsXpLsabababababababababababababababababababLsababLsabababababababababababababLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsabababababababababababababababababababababababaaaa
+aaaaababababababababababababbybxPRbxbxbxbyajajakakakajajababajajajajajakakakakajajajajajajajajajajajakakakakakakajajakakakajajabababababababababababababababababLspupuQuCqOwCqCqCqOwCqQupupuLsLsLsLsLsLsLsLsLsLsLsLsLILsXpLsLssLcsnmcscsLsLsLsLsLsLsLsLsaZcbaXaXaYcscsnmcssLLsLsLssLVZcscssLLsLsLsLsLsababababababababababLsLsabLsLsLsabababababababababababLsLsLsababababLsLsLILsLsLsLsLsLsLsLsLsLskeLsLsabLsLsabababababababababababababababababababababababaaaa
+aaaaababababababababababababbyKubxzCZkuDbyabajajajakakajajababajakakakakakakakakajajakakakakakakakakakakakakakajajajakakakakajabababababababababababLsabLsLsLsLsLsCqCqCqCqCqCqCqCqCqCqCqCqCqLsLsLsaWLsLsLsLsLsLsLsLsLsLsLsLsLssLVZcscssLLsXpLssLsLsLsLsLaZaXaXaXaYsLcscscssLLsXpLssLsLcssLsLLsLsLsLsLsabababababababLsLsLsLsLsLsLsLsLsabababababababLsLsLsLsLIDELsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbybxWxrnbxbxbyabababajajamakajajabajamakakakamakakakajajajakakakakakakajajajakakajajajakakakakakajabababababababababLsLsLsLsLsLsLILsLsCqCqCqOwCqCqzWCqCqOwCqCqCqLsLsLsLsLsLskeLsLsLskeLsLsLsLsLsLssLsLsLsLsLLsLsLssLcsVZcssLaZaXaXaXaYsLsLsLsLsLLsLsLsLsLsXpLsLsLsaWLsLsababababababLsLsLsLskeLsLsLsLsLILsLsLsabLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsaWLsLsLsLsDELsLsLsLsababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbyuDPRzCZkuDbyababababajajakakajajajakakakakakakakakakajajakakamakakakakajajakakakakakakakakakakajajababababababhshsLsLsLsLskeLsLsLsgJCqCqCqCqCqCqCqCqCqCqCqCqCqLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsXpLsLsLsLsLsLsLsLskesLcsnmcscsaZaXcbaXaYLsLsLsLsLsLskeLsLILsLsLsLsLsLsXpLsabababababLsLsLsLILsLsLsDELsLsLsLsLsLsLsLsLsLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsDELsLsLsLILsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbyLkfYrnbxbxbyabababababajajamakakakakakajakakakakakakakakakakakakamakakakakakamakakakakakakakakakajababababababCqhshsLsLsLIgJLskeLsLspupuQuCqOwCqCqCqOwCqQupupuLsLsLsLsLsLsLskeLsLsLsLILsLsaWLsLsLssLsLsLsLsLLsLssLcscscssLaZaXaXaXaYsLsLsLsLsLLsLsLssLsLsLsLsLLsLsLsLsLsababLsLsLskeLsLsLsLsaWLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLILsLsLsLsDELsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbyuDVlzCbxuDbyababababababajajakakakakajajajakakakamakakakakakakakajajakakakakakakajakajakakakamakajajajajajababCqCqhshsLsLsLsLsaWLsLsLspuCqCqCqCqOwCqCqCqCqpuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLskeLssLcscscssLLsLssLsLsLsLsLaZaXaXaXaYsLcscsVZsLLsLsXpsLcscsVZsLLsLskeLsababLsLsLILsLsLseMLsLsLsLsLsLILskeLsdtdtdtdtdtdtdtdtdtdtLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbybxWxVxPRbxbyabababababababajajakakakajajakakakakakakakakakakajajajajakakakakajajajajajakakakakakakakakakajajCqCqCqCqhshsLskeLsLsLsLsLIgJCqCqCqCqCqCqCqCqCqLsLsLsLskeLsLILsLsLsLskeLsLsLsLsLsLsLsLssLcsnmVZsLLsLsLsXpLsLsPhaZaXcbaXaYcscsnmcssLLsLsLscscsnmcssLLsLILsLsababLsLsLshKLsLBLsLskeLsDELsLsLsLsdtdtLyGTLyPALyGTLyGTdtdtLsLskeLsLsLsLILsccccccccccccccccccLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbyKuZkbxbxuDbyababababababababajakakakakakakakakakajajajakakakakajajakakakakakakajajajajajakamakakakakakakajajCqCqCqCqCqhshsLsLsLskeLsLsLsLspupuCqQuCqpupuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsXpLssLcscscssLLsXpLsLsLsLsPhaZaXaXaXaYsLcscscssLLskeXpsLcscsVZsLLsLsLsLsabababLseMLsLsDELILshKLsLsLseMLsdtdtPAGTGTGTGTGTGTGTGTPAdtdtLsLsLsLsLsLsLscccdcdcdcdcdcdcdccLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbyfCPRecZkHHbyabababababababajajakakakakakakakakakakajakakamakakakakakakakakamakakakajajakakakakakakajajajajCqCqCqCqCqCqCqhsLsLsgJLsLsgJgJLsLspuCqCqCqpuLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLssLsLcssLsLLsLsPhPhPhPhPhaZaXaXaXaYsLsLsLsLsLLsLsLssLsLsLsLsLLsLsLsLsababLsLsLsLsNNLseMLsNNLsnhLBLsdtdtGTGTGTSuGTGTGTGTGTGTGTGTdtdtLsLsLsLsLsLscccdOiOiUGOiOicdTeaWLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaababababababababababababbybybybybybybyabababababababajajakakakamakakakakajajajakakakakakakakakajajakakakakakakakakakakakakakajaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUchaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaXcbaXaXaXaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUaUciaUckclcmckaUcmaUcnclckTCaUcodtGTGTVMGTGTcxOyCyEyGTGTVMGTGTdtdtdtdtdtdtdtcccdOiPCNkPCOicdccLsLsLsLsabababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababababajakakakakakakakakajajakajakakakakakakajakakakakakakakakakakakajakakakajaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbraXaXaXaXaXaXaXaXcbaXaXaXaXaXaXaXaXbraXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbgaXcfaXgBaXcgaXSEcraXaXcqcraYIUGTGTVMGTGTGTGTGTGTGTGTVMGTGTGTGThGPAGTGTIUccUMUGcvRjDkUGcdccLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababababajajajakajajajakakakakakakakakakamakakajajakakamakakajakakamakajajajakakajaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbraXaXaXaXaXaXaXaXaXaXaXaXaXbpaXaXaXbraXaXaXaXcbaXaXaXaXaXaXaXaXaXaXaXbgaXaXaXctaXcucwcwcuaXaXaXaXcBdtrtSudtrttDnLGgavbcGTpddtGTGTGTGTGTGTGTGTdtcccdEIKnKnVyEIcdccLILskeLsLsLsLsababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababababababajajajabajakakakakakakakakajakakakajajakakakakajajajakakakakajakakakakaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXaXbraXcbaXcbaXaXaXaXaXaXaXaXaXaXaXaXaXbraXcbaXaXaXaXaXcbaXcbaXaXaXaXaXaXbgaXcfaXaXaXcfaXctaXcqaXaXcgaYIUGTGTVMGTGTGTGTGTGTGTGTVMGTGTZqGThGGTGTGTIUcccdEIMsYgMsEIcdccLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababababababababababajajajakakakakakakajajakakakakakakakajajajakakakakakajakakakajbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdcDbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdbdcEbdbdbdcFcGbdcHcJbdbdcGcKbdbedtGTGTVMGTGTeaRbjRTMGTGTVMGTGTdtdtdtdtdtdtdtcccdOiOiOiOiOicdccLsDELsLILsLsabababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababababababababababababajajakamakakajajajakakakakakakakakakakakakamakakakakakakajCqCqCqCqCqCqCqCqCqCqhsLsLsLsLsgJLsLsLsLsgJLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsXpLsPhLsLsLsLssLsLcssLsLLsPhPhPhLssLsLcssLsLLssLsLcssLsLLsLsLsLsLILsLsLsLsababLsNNeMLsnhLsrmeMLskiRfLBkidtdtGTGTGTSuGTGTGTGTGTGTGTGTdtdtLsLsLsLsLsLscccdOiJBJBJBOicdccLsLsLsLsLsLsLsababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababababababababababababajajajakakakajakajakamakakakakakakakajakakakakakakakajajCqCqCqCqCqCqCqCqCqhshsLsLsLskeLsLskeLsLsLsLsLskeLsLsLsLsLsLsaWLsLsLsLsLsLsLsLsLskeLsLsLILsLsLsLsLsLsLssLVZcscssLLsLskeLsLssLVZcscssLLssLcscscssLLsLskeLsLsLsLsLsababababLsLsLskeLsLBLsLshKLseMLsLsdtdtZqGTGTGTGTGTGTGTGTZqdtdtLsLsLsLILsLsLscccdLPLPLPLPLPcdccLsLsLsaWLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababajakakakakakakakakakakakakakajajajakakakakakakajajCqCqCqCqCqCqCqCqCqhshsLsgJLsLsLsLsLsaWLsLsLILsLsLsLILsLskeLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsXpLsLsXpLsLssLcsnmVZsLLsaWXpLsXpsLcsnmcssLLssLcsnmcssLLILsLsLsLsabababababababababLBLshKLskiLsLskeLsLsDELsdtdtLyGTLyZqLyGTLyGTdtdtLsLsLskeLsLsLsLscccdcdcdcdcdcdcdccLsLsLsLsLsLsabababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababajajakakakakakajajajakakakakajajajajakakamakajajCqCqCqCqCqCqCqCqCqhshsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsLsLsLsLsLsLsLssLcscscssLLsLsLsLsLssLcscscssLLssLVZcscssLLsLsababababababababababababLsLsLsLsLsDELsLsLsLsLsLsLsdtdtdtdtdtdtdtdtdtdtLsLsLsLsLsLsLILsLsccccccTeccccccccccLsLskeLsLsababababababababababababababababababababababababababaaaa
+aaaaababababababababababababababababababababababababababababababababababababababajakakakajajajabajajajajajajajajakakakakajajCqCqCqCqCqCqCqCqCqhshsLsLskeLsLsLsLsLskeLsLsgJLsLskeLsgJLsLsLsabLsLsLILsLsLsLsabLsLsLsLsLsLsLILsLsLsLsLsLsLssLsLsLsLsLLsLsLsababsLsLsLsLsLLssLsLsLsLsLabababababababababababababababLsLsLsLsLsLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsaWLsLsLILsaWLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababaaaa
aaaaababababababababababababababababababababababababababababababababababababababajajajajajababababababajabajajajajajajajajCqCqCqabCqCqCqCqCqhshsLsLsLsLsLsLsLsLsLsabLsLsLsLsLsLsLsLsLsabLsabLsLsLsLsababababababLsLsLsLsLsaWLsLskeLsLsLsLsLsLsLsLsLsabababababababLsLsLsabababababababababababababababababababababababLsLsLsaWLsLsLsLsLsLsaWLsLsLskeLsLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLILsLsDELsLsLILsLsLsababababababababababababababababababababababababababaaaa
-aaaaabababababababababababababababababababababababababababababababababababababababajajabajabababababababababababajabajajajabababababababCqhshsLsLsLsLsLsLsabababababababLsLsLsababababababababLsLsabababababababLsLsLsabLsabLsLsLsLsLsLsLILsLsLsababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsDELsLsLsLsLsLsLsLsabLsLsabLsLsLskeLsLsDELsLsLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
+aaaaabababababababababababababababababababababababababababababababababababababababajajabajabababababababababababajabajajajabababababababCqhshsLsLsLsLsgJLsabababababababLsLsLsababababababababLsLsabababababababLsLsLsabLsabLsLsLsLsLsLsLILsXpLsababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsDELsLsLsLsLsLsLsLsabLsLsabLsLsLskeLsLsDELsLsLskeLsLsLsLsLsLsLsLsLsababababababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababajajababababababababhsLsLsababLsLsababababababababLsLsabababababababababababababababababababababababababababLsLsLsLsLsLsLsabababababababababababababababababababababababababababababababababababababababLsLsLsLsLsLsLsabLsLsabLsabababababLsLsLsLsLsLsLsLsLsLsLsLsLILsLsLsLsLsabababababababababababababababababababababababababababababaaaa
aaaaababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsLsabababababababababababababababababababababababababababababababababababababababababababababLsabLsLsababababababababababababababababababababababababababababababababababababababababababLsLsababababababababababababLsLsLsLsLsLILsLsLsLsaWLsLsabababLsLsabababababababababababababababababababababababababababababaaaa
aaaaabababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababababLsLsabLsLsLsLsLsababababababababababababababababababababababababababababababababababababababaaaa
diff --git a/_maps/map_files/LayeniaStation/LayeniaStation.dmm b/_maps/map_files/LayeniaStation/LayeniaStation.dmm
index 56a6154a..0e119361 100644
--- a/_maps/map_files/LayeniaStation/LayeniaStation.dmm
+++ b/_maps/map_files/LayeniaStation/LayeniaStation.dmm
@@ -1603,7 +1603,7 @@
"evB" = (/obj/machinery/door/window/eastleft{dir = 2; name = "Monkey Pen"; req_one_access_txt = "9"},/obj/machinery/atmospherics/components/unary/vent_pump/on/layer3{name = "air vent"},/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer1{name = "scrubbers pipe"},/turf/open/floor/grass,/area/medical/genetics)
"evI" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden{dir = 9},/turf/closed/wall/r_wall,/area/science/mixing)
"evK" = (/obj/machinery/light{pixel_y = -1},/turf/open/floor/plasteel,/area/security/prison)
-"evQ" = (/obj/effect/turf_decal/tile/neutral{dir = 4},/obj/effect/turf_decal/tile/neutral{dir = 1},/turf/open/floor/plasteel/dark,/area/security/brig)
+"evQ" = (/obj/effect/turf_decal/tile/neutral{dir = 4},/obj/effect/turf_decal/tile/neutral{dir = 1},/obj/machinery/computer/lore_terminal/security,/turf/open/floor/plasteel/dark,/area/security/brig)
"evR" = (/obj/machinery/atmospherics/components/unary/vent_pump/siphon/atmos/incinerator_output{dir = 8},/turf/open/floor/engine,/area/maintenance/disposal/incinerator)
"evT" = (/obj/structure/cable{icon_state = "0-4"},/obj/machinery/power/apc{areastring = "/area/maintenance/solars/port/aft"; dir = 8; name = "Port Quarter Solar APC"; pixel_x = -25; pixel_y = 3},/turf/open/floor/plating,/area/maintenance/solars/port/aft)
"evV" = (/obj/structure/trash_pile,/obj/effect/decal/cleanable/dirt,/obj/effect/decal/cleanable/dirt,/turf/open/floor/plasteel/dark,/area/maintenance/fore)
@@ -3526,7 +3526,7 @@
"jUE" = (/obj/effect/turf_decal/loading_area{dir = 1; icon_state = "drain"; name = "drain"},/obj/effect/turf_decal/tile/purple{dir = 8},/turf/open/floor/plasteel/white/corner,/area/hallway/primary/aft)
"jUP" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{dir = 8; name = "air supply pipe"},/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer1{dir = 4; name = "scrubbers pipe"},/obj/structure/cable{icon_state = "4-8"},/obj/structure/cable{icon_state = "1-4"},/obj/structure/disposalpipe/segment{dir = 4},/obj/structure/cable{icon_state = "2-4"},/turf/open/floor/plasteel/white,/area/medical/genetics)
"jUT" = (/obj/structure/table,/obj/item/stack/ore/iron,/turf/open/floor/plating,/area/maintenance/starboard)
-"jUU" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{dir = 6; name = "air supply pipe"},/turf/open/floor/plasteel/dark,/area/security/prison)
+"jUU" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{dir = 6; name = "air supply pipe"},/obj/machinery/computer/lore_terminal/security,/turf/open/floor/plasteel/dark,/area/security/prison)
"jUY" = (/turf/open/floor/plating/asteroid/layenia,/area/layenia/cloudlayer)
"jVg" = (/obj/structure/railing{dir = 8},/turf/open/floor/plasteel/dark,/area/hallway/primary/starboard)
"jVq" = (/obj/effect/spawner/structure/window,/obj/machinery/door/firedoor,/turf/open/floor/plating,/area/medical/chemistry)
@@ -4361,7 +4361,7 @@
"mwm" = (/obj/machinery/atmospherics/pipe/manifold/general/visible{dir = 8},/obj/effect/turf_decal/stripes/line{dir = 8},/obj/effect/turf_decal/tile/neutral{dir = 1},/obj/effect/turf_decal/tile/neutral,/obj/effect/turf_decal/tile/neutral{dir = 4},/obj/effect/turf_decal/tile/neutral{dir = 8},/obj/effect/landmark/start/scientist,/turf/open/floor/plasteel/dark,/area/science/mixing)
"mwz" = (/obj/machinery/door/airlock/maintenance{name = "Bar Maintenance"; req_access_txt = "25"},/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer1{name = "scrubbers pipe"},/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{name = "air supply pipe"},/obj/structure/cable{icon_state = "1-2"},/obj/structure/disposalpipe/segment,/turf/open/floor/plasteel/dark,/area/maintenance/fore/secondary)
"mwC" = (/obj/effect/turf_decal/tile/blue{dir = 8},/obj/effect/turf_decal/tile/blue{dir = 1},/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{name = "air supply pipe"},/obj/structure/disposalpipe/segment{dir = 4},/obj/item/radio/intercom{frequency = 1485; name = "Station Intercom (Medbay)"; pixel_x = -30},/turf/open/floor/plasteel/white,/area/medical/sleeper)
-"mwT" = (/obj/effect/turf_decal/tile/red{dir = 1},/obj/effect/turf_decal/tile/red{dir = 4},/obj/effect/turf_decal/tile/neutral{dir = 8},/obj/effect/turf_decal/tile/neutral,/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer1{name = "air scrubber"},/turf/open/floor/plasteel/dark/side,/area/security/main)
+"mwT" = (/obj/effect/turf_decal/tile/red{dir = 1},/obj/effect/turf_decal/tile/red{dir = 4},/obj/effect/turf_decal/tile/neutral{dir = 8},/obj/effect/turf_decal/tile/neutral,/obj/machinery/atmospherics/components/unary/vent_scrubber/on/layer1{name = "air scrubber"},/obj/machinery/computer/lore_terminal/security,/turf/open/floor/plasteel/dark/side,/area/security/main)
"mwV" = (/turf/open/floor/plasteel/stairs/medium,/area/hallway/primary/port)
"mxe" = (/obj/structure/closet/secure_closet/detective,/turf/open/floor/wood,/area/security/detectives_office)
"mxg" = (/obj/machinery/light{pixel_y = -1},/turf/open/chasm/cloud,/area/layenia/cloudlayer)
@@ -8537,7 +8537,7 @@
"xxr" = (/obj/effect/turf_decal/stripes/line,/obj/docking_port/stationary/random{dir = 2; id = "pod_lavaland4"; name = "lavaland"},/turf/open/indestructible/concrete,/area/layenia/cloudlayer)
"xxA" = (/turf/open/floor/plasteel/yellowsiding{dir = 4},/area/maintenance/fore)
"xxF" = (/obj/machinery/atmospherics/pipe/simple/supply/hidden/layer3{dir = 8; name = "air supply pipe"},/obj/machinery/atmospherics/pipe/simple/scrubbers/hidden/layer1{dir = 4; name = "scrubbers pipe"},/turf/open/floor/plasteel,/area/security/main)
-"xxL" = (/obj/effect/turf_decal/tile/red{dir = 4},/obj/effect/turf_decal/tile/red{dir = 1},/obj/machinery/computer/lore_terminal,/turf/open/floor/plasteel{icon_state = "floor_plate"},/area/security/brig)
+"xxL" = (/obj/effect/turf_decal/tile/red{dir = 4},/obj/effect/turf_decal/tile/red{dir = 1},/obj/machinery/computer/lore_terminal/security,/turf/open/floor/plasteel{icon_state = "floor_plate"},/area/security/brig)
"xxU" = (/obj/item/twohanded/required/fuel_rod,/obj/effect/turf_decal/stripes/line{dir = 4},/turf/open/pool,/area/engine/engineering/reactor_core)
"xxV" = (/obj/structure/closet/secure_closet/medical1,/obj/effect/turf_decal/stripes/line{dir = 1},/obj/machinery/light{pixel_y = -1},/turf/open/floor/plasteel/dark,/area/gateway)
"xxW" = (/turf/open/floor/plasteel/stairs/medium{dir = 4},/area/security/main)
diff --git a/code/controllers/subsystem/vis_overlays.dm b/code/controllers/subsystem/vis_overlays.dm
index 07c786b1..fe433c3e 100644
--- a/code/controllers/subsystem/vis_overlays.dm
+++ b/code/controllers/subsystem/vis_overlays.dm
@@ -7,12 +7,10 @@ SUBSYSTEM_DEF(vis_overlays)
var/list/vis_overlay_cache
var/list/unique_vis_overlays
var/list/currentrun
- var/datum/callback/rotate_cb
/datum/controller/subsystem/vis_overlays/Initialize()
vis_overlay_cache = list()
unique_vis_overlays = list()
- rotate_cb = CALLBACK(src, .proc/rotate_vis_overlay)
return ..()
/datum/controller/subsystem/vis_overlays/fire(resumed = FALSE)
@@ -57,7 +55,7 @@ SUBSYSTEM_DEF(vis_overlays)
if(!thing.managed_vis_overlays)
thing.managed_vis_overlays = list(overlay)
- RegisterSignal(thing, COMSIG_ATOM_DIR_CHANGE, rotate_cb)
+ RegisterSignal(thing, COMSIG_ATOM_DIR_CHANGE, .proc/rotate_vis_overlay)
else
thing.managed_vis_overlays += overlay
diff --git a/code/controllers/subsystem/vote.dm b/code/controllers/subsystem/vote.dm
index a6c3e787..d0d228ac 100644
--- a/code/controllers/subsystem/vote.dm
+++ b/code/controllers/subsystem/vote.dm
@@ -1,6 +1,6 @@
#define DYNAMIC_DEFAULT_CHAOS 1.0 //The default chaos value for low pop low vote rounds
#define DYNAMIC_VOTE_NORMALIZATION 8 //If there are fewer than this many votes, the average will be skewed towards the default
-#define DYNAMIC_NONVOTER_FACTOR 0.6 // 1 means they count for a full vote
+#define DYNAMIC_NONVOTER_FACTOR 1 // 1 means they count for a full vote
#define DYNAMIC_NONVOTER_VALUE 1.5 // The chaos value that non-voters should account for.
SUBSYSTEM_DEF(vote)
diff --git a/code/datums/components/_component.dm b/code/datums/components/_component.dm
index ab0f7584..6c74f973 100644
--- a/code/datums/components/_component.dm
+++ b/code/datums/components/_component.dm
@@ -1,318 +1,315 @@
-/datum/component
- var/dupe_mode = COMPONENT_DUPE_HIGHLANDER
- var/dupe_type
- var/datum/parent
- //only set to true if you are able to properly transfer this component
- //At a minimum RegisterWithParent and UnregisterFromParent should be used
- //Make sure you also implement PostTransfer for any post transfer handling
- var/can_transfer = FALSE
-
-/datum/component/New(datum/P, ...)
- parent = P
- var/list/arguments = args.Copy(2)
- if(Initialize(arglist(arguments)) == COMPONENT_INCOMPATIBLE)
- qdel(src, TRUE, TRUE)
- CRASH("Incompatible [type] assigned to a [P.type]! args: [json_encode(arguments)]")
-
- _JoinParent(P)
-
-/datum/component/proc/_JoinParent()
- var/datum/P = parent
- //lazy init the parent's dc list
- var/list/dc = P.datum_components
- if(!dc)
- P.datum_components = dc = list()
-
- //set up the typecache
- var/our_type = type
- for(var/I in _GetInverseTypeList(our_type))
- var/test = dc[I]
- if(test) //already another component of this type here
- var/list/components_of_type
- if(!length(test))
- components_of_type = list(test)
- dc[I] = components_of_type
- else
- components_of_type = test
- if(I == our_type) //exact match, take priority
- var/inserted = FALSE
- for(var/J in 1 to components_of_type.len)
- var/datum/component/C = components_of_type[J]
- if(C.type != our_type) //but not over other exact matches
- components_of_type.Insert(J, I)
- inserted = TRUE
- break
- if(!inserted)
- components_of_type += src
- else //indirect match, back of the line with ya
- components_of_type += src
- else //only component of this type, no list
- dc[I] = src
-
- RegisterWithParent()
-
-// If you want/expect to be moving the component around between parents, use this to register on the parent for signals
-/datum/component/proc/RegisterWithParent()
- return
-
-/datum/component/proc/Initialize(...)
- return
-
-/datum/component/Destroy(force=FALSE, silent=FALSE)
- if(!force && parent)
- _RemoveFromParent()
- if(!silent)
- SEND_SIGNAL(parent, COMSIG_COMPONENT_REMOVING, src)
- parent = null
- return ..()
-
-/datum/component/proc/_RemoveFromParent()
- var/datum/P = parent
- var/list/dc = P.datum_components
- for(var/I in _GetInverseTypeList())
- var/list/components_of_type = dc[I]
- if(length(components_of_type)) //
- var/list/subtracted = components_of_type - src
- if(subtracted.len == 1) //only 1 guy left
- dc[I] = subtracted[1] //make him special
- else
- dc[I] = subtracted
- else //just us
- dc -= I
- if(!dc.len)
- P.datum_components = null
-
- UnregisterFromParent()
-
-/datum/component/proc/UnregisterFromParent()
- return
-
-/datum/proc/RegisterSignal(datum/target, sig_type_or_types, proc_or_callback, override = FALSE)
- if(QDELETED(src) || QDELETED(target))
- return
-
- var/list/procs = signal_procs
- if(!procs)
- signal_procs = procs = list()
- if(!procs[target])
- procs[target] = list()
- var/list/lookup = target.comp_lookup
- if(!lookup)
- target.comp_lookup = lookup = list()
-
- if(!istype(proc_or_callback, /datum/callback)) //if it wasnt a callback before, it is now
- proc_or_callback = CALLBACK(src, proc_or_callback)
-
- var/list/sig_types = islist(sig_type_or_types) ? sig_type_or_types : list(sig_type_or_types)
- for(var/sig_type in sig_types)
- if(!override && procs[target][sig_type])
- stack_trace("[sig_type] overridden. Use override = TRUE to suppress this warning")
-
- procs[target][sig_type] = proc_or_callback
-
- if(!lookup[sig_type]) // Nothing has registered here yet
- lookup[sig_type] = src
- else if(lookup[sig_type] == src) // We already registered here
- continue
- else if(!length(lookup[sig_type])) // One other thing registered here
- lookup[sig_type] = list(lookup[sig_type]=TRUE)
- lookup[sig_type][src] = TRUE
- else // Many other things have registered here
- lookup[sig_type][src] = TRUE
-
- signal_enabled = TRUE
-
-/datum/proc/UnregisterSignal(datum/target, sig_type_or_types)
- if(!target)
- CRASH("[src] tried to unregister a signal without having a target.")
- var/list/lookup = target.comp_lookup
- if(!signal_procs || !signal_procs[target] || !lookup)
- return
- if(!islist(sig_type_or_types))
- sig_type_or_types = list(sig_type_or_types)
- for(var/sig in sig_type_or_types)
- switch(length(lookup[sig]))
- if(2)
- lookup[sig] = (lookup[sig]-src)[1]
- if(1)
- stack_trace("[target] ([target.type]) somehow has single length list inside comp_lookup")
- if(src in lookup[sig])
- lookup -= sig
- if(!length(lookup))
- target.comp_lookup = null
- break
- if(0)
- lookup -= sig
- if(!length(lookup))
- target.comp_lookup = null
- break
- else
- lookup[sig] -= src
-
- signal_procs[target] -= sig_type_or_types
- if(!signal_procs[target].len)
- signal_procs -= target
-
-/datum/component/proc/InheritComponent(datum/component/C, i_am_original)
- return
-
-/datum/component/proc/PreTransfer()
- return
-
-/datum/component/proc/PostTransfer()
- return COMPONENT_INCOMPATIBLE //Do not support transfer by default as you must properly support it
-
-/datum/component/proc/_GetInverseTypeList(our_type = type)
- //we can do this one simple trick
- var/current_type = parent_type
- . = list(our_type, current_type)
- //and since most components are root level + 1, this won't even have to run
- while (current_type != /datum/component)
- current_type = type2parent(current_type)
- . += current_type
-
-/datum/proc/_SendSignal(sigtype, list/arguments)
- var/target = comp_lookup[sigtype]
- if(!length(target))
- var/datum/C = target
- if(!C.signal_enabled)
- return NONE
- var/datum/callback/CB = C.signal_procs[src][sigtype]
- return CB.InvokeAsync(arglist(arguments))
- . = NONE
- for(var/I in target)
- var/datum/C = I
- if(!C.signal_enabled)
- continue
- var/datum/callback/CB = C.signal_procs[src][sigtype]
- . |= CB.InvokeAsync(arglist(arguments))
-
-/datum/proc/GetComponent(c_type)
- var/list/dc = datum_components
- if(!dc)
- return null
- . = dc[c_type]
- if(length(.))
- return .[1]
-
-/datum/proc/GetExactComponent(c_type)
- var/list/dc = datum_components
- if(!dc)
- return null
- var/datum/component/C = dc[c_type]
- if(C)
- if(length(C))
- C = C[1]
- if(C.type == c_type)
- return C
- return null
-
-/datum/proc/GetComponents(c_type)
- var/list/dc = datum_components
- if(!dc)
- return null
- . = dc[c_type]
- if(!length(.))
- return list(.)
-
-/datum/proc/AddComponent(new_type, ...)
- var/datum/component/nt = new_type
- var/dm = initial(nt.dupe_mode)
- var/dt = initial(nt.dupe_type)
-
- var/datum/component/old_comp
- var/datum/component/new_comp
-
- if(ispath(nt))
- if(nt == /datum/component)
- CRASH("[nt] attempted instantiation!")
- if(!isnum(dm))
- CRASH("[nt]: Invalid dupe_mode ([dm])!")
- if(dt && !ispath(dt))
- CRASH("[nt]: Invalid dupe_type ([dt])!")
- else
- new_comp = nt
- nt = new_comp.type
-
- args[1] = src
-
- if(dm != COMPONENT_DUPE_ALLOWED)
- if(!dt)
- old_comp = GetExactComponent(nt)
- else
- old_comp = GetComponent(dt)
- if(old_comp)
- switch(dm)
- if(COMPONENT_DUPE_UNIQUE)
- if(!new_comp)
- new_comp = new nt(arglist(args))
- if(!QDELETED(new_comp))
- old_comp.InheritComponent(new_comp, TRUE)
- QDEL_NULL(new_comp)
- if(COMPONENT_DUPE_HIGHLANDER)
- if(!new_comp)
- new_comp = new nt(arglist(args))
- if(!QDELETED(new_comp))
- new_comp.InheritComponent(old_comp, FALSE)
- QDEL_NULL(old_comp)
- if(COMPONENT_DUPE_UNIQUE_PASSARGS)
- if(!new_comp)
- var/list/arguments = args.Copy(2)
- old_comp.InheritComponent(null, TRUE, arguments)
- else
- old_comp.InheritComponent(new_comp, TRUE)
- else if(!new_comp)
- new_comp = new nt(arglist(args)) // There's a valid dupe mode but there's no old component, act like normal
- else if(!new_comp)
- new_comp = new nt(arglist(args)) // Dupes are allowed, act like normal
-
- if(!old_comp && !QDELETED(new_comp)) // Nothing related to duplicate components happened and the new component is healthy
- SEND_SIGNAL(src, COMSIG_COMPONENT_ADDED, new_comp)
- return new_comp
- return old_comp
-
-/datum/proc/LoadComponent(component_type, ...)
- . = GetComponent(component_type)
- if(!.)
- return AddComponent(arglist(args))
-
-/datum/component/proc/RemoveComponent()
- if(!parent)
- return
- var/datum/old_parent = parent
- PreTransfer()
- _RemoveFromParent()
- parent = null
- SEND_SIGNAL(old_parent, COMSIG_COMPONENT_REMOVING, src)
-
-/datum/proc/TakeComponent(datum/component/target)
- if(!target || target.parent == src)
- return
- if(target.parent)
- target.RemoveComponent()
- target.parent = src
- var/result = target.PostTransfer()
- switch(result)
- if(COMPONENT_INCOMPATIBLE)
- var/c_type = target.type
- qdel(target)
- CRASH("Incompatible [c_type] transfer attempt to a [type]!")
- if(target == AddComponent(target))
- target._JoinParent()
-
-/datum/proc/TransferComponents(datum/target)
- var/list/dc = datum_components
- if(!dc)
- return
- var/comps = dc[/datum/component]
- if(islist(comps))
- for(var/datum/component/I in comps)
- if(I.can_transfer)
- target.TakeComponent(I)
- else
- var/datum/component/C = comps
- if(C.can_transfer)
- target.TakeComponent(comps)
-
-/datum/component/ui_host()
- return parent
+/datum/component
+ var/dupe_mode = COMPONENT_DUPE_HIGHLANDER
+ var/dupe_type
+ var/datum/parent
+ //only set to true if you are able to properly transfer this component
+ //At a minimum RegisterWithParent and UnregisterFromParent should be used
+ //Make sure you also implement PostTransfer for any post transfer handling
+ var/can_transfer = FALSE
+
+/datum/component/New(datum/P, ...)
+ parent = P
+ var/list/arguments = args.Copy(2)
+ if(Initialize(arglist(arguments)) == COMPONENT_INCOMPATIBLE)
+ qdel(src, TRUE, TRUE)
+ CRASH("Incompatible [type] assigned to a [P.type]! args: [json_encode(arguments)]")
+
+ _JoinParent(P)
+
+/datum/component/proc/_JoinParent()
+ var/datum/P = parent
+ //lazy init the parent's dc list
+ var/list/dc = P.datum_components
+ if(!dc)
+ P.datum_components = dc = list()
+
+ //set up the typecache
+ var/our_type = type
+ for(var/I in _GetInverseTypeList(our_type))
+ var/test = dc[I]
+ if(test) //already another component of this type here
+ var/list/components_of_type
+ if(!length(test))
+ components_of_type = list(test)
+ dc[I] = components_of_type
+ else
+ components_of_type = test
+ if(I == our_type) //exact match, take priority
+ var/inserted = FALSE
+ for(var/J in 1 to components_of_type.len)
+ var/datum/component/C = components_of_type[J]
+ if(C.type != our_type) //but not over other exact matches
+ components_of_type.Insert(J, I)
+ inserted = TRUE
+ break
+ if(!inserted)
+ components_of_type += src
+ else //indirect match, back of the line with ya
+ components_of_type += src
+ else //only component of this type, no list
+ dc[I] = src
+
+ RegisterWithParent()
+
+// If you want/expect to be moving the component around between parents, use this to register on the parent for signals
+/datum/component/proc/RegisterWithParent()
+ return
+
+/datum/component/proc/Initialize(...)
+ return
+
+/datum/component/Destroy(force=FALSE, silent=FALSE)
+ if(!force && parent)
+ _RemoveFromParent()
+ if(!silent)
+ SEND_SIGNAL(parent, COMSIG_COMPONENT_REMOVING, src)
+ parent = null
+ return ..()
+
+/datum/component/proc/_RemoveFromParent()
+ var/datum/P = parent
+ var/list/dc = P.datum_components
+ for(var/I in _GetInverseTypeList())
+ var/list/components_of_type = dc[I]
+ if(length(components_of_type)) //
+ var/list/subtracted = components_of_type - src
+ if(subtracted.len == 1) //only 1 guy left
+ dc[I] = subtracted[1] //make him special
+ else
+ dc[I] = subtracted
+ else //just us
+ dc -= I
+ if(!dc.len)
+ P.datum_components = null
+
+ UnregisterFromParent()
+
+/datum/component/proc/UnregisterFromParent()
+ return
+
+/datum/proc/RegisterSignal(datum/target, sig_type_or_types, proctype, override = FALSE)
+ if(QDELETED(src) || QDELETED(target))
+ return
+
+ var/list/procs = signal_procs
+ if(!procs)
+ signal_procs = procs = list()
+ if(!procs[target])
+ procs[target] = list()
+ var/list/lookup = target.comp_lookup
+ if(!lookup)
+ target.comp_lookup = lookup = list()
+
+ var/list/sig_types = islist(sig_type_or_types) ? sig_type_or_types : list(sig_type_or_types)
+ for(var/sig_type in sig_types)
+ if(!override && procs[target][sig_type])
+ stack_trace("[sig_type] overridden. Use override = TRUE to suppress this warning")
+
+ procs[target][sig_type] = proctype
+
+ if(!lookup[sig_type]) // Nothing has registered here yet
+ lookup[sig_type] = src
+ else if(lookup[sig_type] == src) // We already registered here
+ continue
+ else if(!length(lookup[sig_type])) // One other thing registered here
+ lookup[sig_type] = list(lookup[sig_type]=TRUE)
+ lookup[sig_type][src] = TRUE
+ else // Many other things have registered here
+ lookup[sig_type][src] = TRUE
+
+ signal_enabled = TRUE
+
+/datum/proc/UnregisterSignal(datum/target, sig_type_or_types)
+ if(!target)
+ CRASH("[src] tried to unregister a signal without having a target.")
+ var/list/lookup = target.comp_lookup
+ if(!signal_procs || !signal_procs[target] || !lookup)
+ return
+ if(!islist(sig_type_or_types))
+ sig_type_or_types = list(sig_type_or_types)
+ for(var/sig in sig_type_or_types)
+ switch(length(lookup[sig]))
+ if(2)
+ lookup[sig] = (lookup[sig]-src)[1]
+ if(1)
+ stack_trace("[target] ([target.type]) somehow has single length list inside comp_lookup")
+ if(src in lookup[sig])
+ lookup -= sig
+ if(!length(lookup))
+ target.comp_lookup = null
+ break
+ if(0)
+ lookup -= sig
+ if(!length(lookup))
+ target.comp_lookup = null
+ break
+ else
+ lookup[sig] -= src
+
+ signal_procs[target] -= sig_type_or_types
+ if(!signal_procs[target].len)
+ signal_procs -= target
+
+/datum/component/proc/InheritComponent(datum/component/C, i_am_original)
+ return
+
+/datum/component/proc/PreTransfer()
+ return
+
+/datum/component/proc/PostTransfer()
+ return COMPONENT_INCOMPATIBLE //Do not support transfer by default as you must properly support it
+
+/datum/component/proc/_GetInverseTypeList(our_type = type)
+ //we can do this one simple trick
+ var/current_type = parent_type
+ . = list(our_type, current_type)
+ //and since most components are root level + 1, this won't even have to run
+ while (current_type != /datum/component)
+ current_type = type2parent(current_type)
+ . += current_type
+
+/datum/proc/_SendSignal(sigtype, list/arguments)
+ var/target = comp_lookup[sigtype]
+ if(!length(target))
+ var/datum/C = target
+ if(!C.signal_enabled)
+ return NONE
+ var/proctype = C.signal_procs[src][sigtype]
+ return NONE | CallAsync(C, proctype, arguments)
+ . = NONE
+ for(var/I in target)
+ var/datum/C = I
+ if(!C.signal_enabled)
+ continue
+ var/proctype = C.signal_procs[src][sigtype]
+ . |= CallAsync(C, proctype, arguments)
+
+// The type arg is casted so initial works, you shouldn't be passing a real instance into this
+/datum/proc/GetComponent(datum/component/c_type)
+ if(initial(c_type.dupe_mode) == COMPONENT_DUPE_ALLOWED)
+ stack_trace("GetComponent was called to get a component of which multiple copies could be on an object. This can easily break and should be changed. Type: \[[c_type]\]")
+ var/list/dc = datum_components
+ if(!dc)
+ return null
+ . = dc[c_type]
+ if(length(.))
+ return .[1]
+
+/datum/proc/GetExactComponent(c_type)
+ var/list/dc = datum_components
+ if(!dc)
+ return null
+ var/datum/component/C = dc[c_type]
+ if(C)
+ if(length(C))
+ C = C[1]
+ if(C.type == c_type)
+ return C
+ return null
+
+/datum/proc/GetComponents(c_type)
+ var/list/dc = datum_components
+ if(!dc)
+ return null
+ . = dc[c_type]
+ if(!length(.))
+ return list(.)
+
+/datum/proc/AddComponent(new_type, ...)
+ var/datum/component/nt = new_type
+ var/dm = initial(nt.dupe_mode)
+ var/dt = initial(nt.dupe_type)
+
+ var/datum/component/old_comp
+ var/datum/component/new_comp
+
+ if(ispath(nt))
+ if(nt == /datum/component)
+ CRASH("[nt] attempted instantiation!")
+ else
+ new_comp = nt
+ nt = new_comp.type
+
+ args[1] = src
+
+ if(dm != COMPONENT_DUPE_ALLOWED)
+ if(!dt)
+ old_comp = GetExactComponent(nt)
+ else
+ old_comp = GetComponent(dt)
+ if(old_comp)
+ switch(dm)
+ if(COMPONENT_DUPE_UNIQUE)
+ if(!new_comp)
+ new_comp = new nt(arglist(args))
+ if(!QDELETED(new_comp))
+ old_comp.InheritComponent(new_comp, TRUE)
+ QDEL_NULL(new_comp)
+ if(COMPONENT_DUPE_HIGHLANDER)
+ if(!new_comp)
+ new_comp = new nt(arglist(args))
+ if(!QDELETED(new_comp))
+ new_comp.InheritComponent(old_comp, FALSE)
+ QDEL_NULL(old_comp)
+ if(COMPONENT_DUPE_UNIQUE_PASSARGS)
+ if(!new_comp)
+ var/list/arguments = args.Copy(2)
+ old_comp.InheritComponent(null, TRUE, arguments)
+ else
+ old_comp.InheritComponent(new_comp, TRUE)
+ else if(!new_comp)
+ new_comp = new nt(arglist(args)) // There's a valid dupe mode but there's no old component, act like normal
+ else if(!new_comp)
+ new_comp = new nt(arglist(args)) // Dupes are allowed, act like normal
+
+ if(!old_comp && !QDELETED(new_comp)) // Nothing related to duplicate components happened and the new component is healthy
+ SEND_SIGNAL(src, COMSIG_COMPONENT_ADDED, new_comp)
+ return new_comp
+ return old_comp
+
+/datum/proc/LoadComponent(component_type, ...)
+ . = GetComponent(component_type)
+ if(!.)
+ return AddComponent(arglist(args))
+
+/datum/component/proc/RemoveComponent()
+ if(!parent)
+ return
+ var/datum/old_parent = parent
+ PreTransfer()
+ _RemoveFromParent()
+ parent = null
+ SEND_SIGNAL(old_parent, COMSIG_COMPONENT_REMOVING, src)
+
+/datum/proc/TakeComponent(datum/component/target)
+ if(!target || target.parent == src)
+ return
+ if(target.parent)
+ target.RemoveComponent()
+ target.parent = src
+ var/result = target.PostTransfer()
+ switch(result)
+ if(COMPONENT_INCOMPATIBLE)
+ var/c_type = target.type
+ qdel(target)
+ CRASH("Incompatible [c_type] transfer attempt to a [type]!")
+
+ if(target == AddComponent(target))
+ target._JoinParent()
+
+/datum/proc/TransferComponents(datum/target)
+ var/list/dc = datum_components
+ if(!dc)
+ return
+ var/comps = dc[/datum/component]
+ if(islist(comps))
+ for(var/datum/component/I in comps)
+ if(I.can_transfer)
+ target.TakeComponent(I)
+ else
+ var/datum/component/C = comps
+ if(C.can_transfer)
+ target.TakeComponent(comps)
+
+/datum/component/ui_host()
+ return parent
diff --git a/code/datums/components/earprotection.dm b/code/datums/components/earprotection.dm
index 20849437..9256c431 100644
--- a/code/datums/components/earprotection.dm
+++ b/code/datums/components/earprotection.dm
@@ -1,11 +1,11 @@
/datum/component/wearertargeting/earprotection
signals = list(COMSIG_CARBON_SOUNDBANG)
mobtype = /mob/living/carbon
+ proctype = .proc/reducebang
/datum/component/wearertargeting/earprotection/Initialize(_valid_slots)
. = ..()
valid_slots = _valid_slots
- callback = CALLBACK(src, .proc/reducebang)
/datum/component/wearertargeting/earprotection/proc/reducebang(datum/source, list/reflist)
reflist[1]--
diff --git a/code/datums/components/mood.dm b/code/datums/components/mood.dm
index 43d13380..7297e8b7 100644
--- a/code/datums/components/mood.dm
+++ b/code/datums/components/mood.dm
@@ -261,8 +261,6 @@
if(the_event.timeout)
addtimer(CALLBACK(src, .proc/clear_event, null, category), the_event.timeout, TIMER_UNIQUE|TIMER_OVERRIDE)
- return the_event
-
/datum/component/mood/proc/clear_event(datum/source, category)
var/datum/mood_event/event = mood_events[category]
if(!event)
diff --git a/code/datums/components/orbiter.dm b/code/datums/components/orbiter.dm
index a9d2c73b..b23fe362 100644
--- a/code/datums/components/orbiter.dm
+++ b/code/datums/components/orbiter.dm
@@ -1,8 +1,7 @@
/datum/component/orbiter
+ can_transfer = TRUE
dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
var/list/orbiters
- var/datum/callback/orbiter_spy
- var/datum/callback/orbited_spy
//radius: range to orbit at, radius of the circle formed by orbiting (in pixels)
//clockwise: whether you orbit clockwise or anti clockwise
@@ -14,8 +13,6 @@
return COMPONENT_INCOMPATIBLE
orbiters = list()
- orbiter_spy = CALLBACK(src, .proc/orbiter_move_react)
- orbited_spy = CALLBACK(src, .proc/move_react)
var/atom/master = parent
master.orbiters = src
@@ -25,7 +22,7 @@
/datum/component/orbiter/RegisterWithParent()
var/atom/target = parent
while(ismovableatom(target))
- RegisterSignal(target, COMSIG_MOVABLE_MOVED, orbited_spy)
+ RegisterSignal(target, COMSIG_MOVABLE_MOVED, .proc/move_react)
target = target.loc
RegisterSignal(parent, COMSIG_MOVABLE_UPDATE_GLIDE_SIZE, .proc/orbiter_glide_size_update)
@@ -44,8 +41,6 @@
for(var/i in orbiters)
end_orbit(i)
orbiters = null
- QDEL_NULL(orbiter_spy)
- QDEL_NULL(orbited_spy)
return ..()
/datum/component/orbiter/InheritComponent(datum/component/orbiter/newcomp, original, list/arguments)
@@ -69,7 +64,7 @@
orbiter.orbiting.end_orbit(orbiter)
orbiters[orbiter] = TRUE
orbiter.orbiting = src
- RegisterSignal(orbiter, COMSIG_MOVABLE_MOVED, orbiter_spy)
+ RegisterSignal(orbiter, COMSIG_MOVABLE_MOVED, .proc/orbiter_move_react)
var/matrix/initial_transform = matrix(orbiter.transform)
orbiters[orbiter] = initial_transform
@@ -137,7 +132,7 @@
if(orbited?.loc && orbited.loc != newturf) // We want to know when anything holding us moves too
var/atom/target = orbited.loc
while(ismovableatom(target))
- RegisterSignal(target, COMSIG_MOVABLE_MOVED, orbited_spy, TRUE)
+ RegisterSignal(target, COMSIG_MOVABLE_MOVED, .proc/move_react, TRUE)
target = target.loc
var/atom/curloc = master.loc
diff --git a/code/datums/components/phantomthief.dm b/code/datums/components/phantomthief.dm
new file mode 100644
index 00000000..ff1c4893
--- /dev/null
+++ b/code/datums/components/phantomthief.dm
@@ -0,0 +1,39 @@
+//This component applies a customizable drop_shadow filter to its wearer when they toggle combat mode on or off. This can stack.
+
+/datum/component/wearertargeting/phantomthief
+ dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
+ signals = list(COMSIG_COMBAT_TOGGLED)
+ proctype = .proc/handlefilterstuff
+ var/filter_x
+ var/filter_y
+ var/filter_size
+ var/filter_border
+ var/filter_color
+
+/datum/component/wearertargeting/phantomthief/Initialize(_x = -2, _y = 0, _size = 0, _border = 0, _color = "#E62111", list/_valid_slots = list(SLOT_GLASSES))
+ . = ..()
+ if(. == COMPONENT_INCOMPATIBLE)
+ return
+ filter_x = _x
+ filter_y = _y
+ filter_size = _size
+ filter_border = _border
+ filter_color = _color
+ valid_slots = _valid_slots
+
+/datum/component/wearertargeting/phantomthief/proc/handlefilterstuff(datum/source, mob/user, combatmodestate)
+ if(istype(user))
+ var/thefilter = filter(type = "drop_shadow", x = filter_x, y = filter_y, size = filter_size, border = filter_border, color = filter_color)
+ if(!combatmodestate)
+ user.filters -= thefilter
+ else
+ user.filters += thefilter
+
+/datum/component/wearertargeting/phantomthief/proc/stripdesiredfilter(mob/user)
+ if(istype(user))
+ var/thefilter = filter(type = "drop_shadow", x = filter_x, y = filter_y, size = filter_size, border = filter_border, color = filter_color)
+ user.filters -= thefilter
+
+/datum/component/wearertargeting/phantomthief/on_drop(datum/source, mob/user)
+ . = ..()
+ stripdesiredfilter(user)
diff --git a/code/datums/components/signal_redirect.dm b/code/datums/components/signal_redirect.dm
deleted file mode 100644
index db98d566..00000000
--- a/code/datums/components/signal_redirect.dm
+++ /dev/null
@@ -1,33 +0,0 @@
-// This should only be used by non components trying to listen to a signal
-// If you use this inside a component I will replace your eyes with lemons ~ninjanomnom
-
-/datum/component/redirect
- dupe_mode = COMPONENT_DUPE_ALLOWED
- var/list/signals
- var/datum/callback/turfchangeCB
-
-/datum/component/redirect/Initialize(list/_signals, flags=NONE)
- //It's not our job to verify the right signals are registered here, just do it.
- if(!LAZYLEN(_signals))
- return COMPONENT_INCOMPATIBLE
- if(flags & REDIRECT_TRANSFER_WITH_TURF && isturf(parent))
- // If they also want to listen to the turf change then we need to set it up so both callbacks run
- if(_signals[COMSIG_TURF_CHANGE])
- turfchangeCB = _signals[COMSIG_TURF_CHANGE]
- if(!istype(turfchangeCB))
- . = COMPONENT_INCOMPATIBLE
- CRASH("Redirect components must be given instanced callbacks, not proc paths.")
- _signals[COMSIG_TURF_CHANGE] = CALLBACK(src, .proc/turf_change)
-
- signals = _signals
-
-/datum/component/redirect/RegisterWithParent()
- for(var/signal in signals)
- RegisterSignal(parent, signal, signals[signal])
-
-/datum/component/redirect/UnregisterFromParent()
- UnregisterSignal(parent, signals)
-
-/datum/component/redirect/proc/turf_change(datum/source, path, new_baseturfs, flags, list/transfers)
- transfers += src
- return turfchangeCB?.InvokeAsync(arglist(args))
diff --git a/code/datums/components/wearertargeting.dm b/code/datums/components/wearertargeting.dm
index 0aa08311..feaa88f9 100644
--- a/code/datums/components/wearertargeting.dm
+++ b/code/datums/components/wearertargeting.dm
@@ -3,7 +3,7 @@
/datum/component/wearertargeting
var/list/valid_slots = list()
var/list/signals = list()
- var/datum/callback/callback = CALLBACK(GLOBAL_PROC, .proc/pass)
+ var/proctype = .proc/pass
var/mobtype = /mob/living
/datum/component/wearertargeting/Initialize()
@@ -14,13 +14,9 @@
/datum/component/wearertargeting/proc/on_equip(datum/source, mob/equipper, slot)
if((slot in valid_slots) && istype(equipper, mobtype))
- RegisterSignal(equipper, signals, callback, TRUE)
+ RegisterSignal(equipper, signals, proctype, TRUE)
else
UnregisterSignal(equipper, signals)
/datum/component/wearertargeting/proc/on_drop(datum/source, mob/user)
- UnregisterSignal(user, signals)
-
-/datum/component/wearertargeting/Destroy()
- QDEL_NULL(callback) //is likely to ourselves.
- return ..()
\ No newline at end of file
+ UnregisterSignal(user, signals)
\ No newline at end of file
diff --git a/code/datums/components/wet_floor.dm b/code/datums/components/wet_floor.dm
index 526d482e..84b03203 100644
--- a/code/datums/components/wet_floor.dm
+++ b/code/datums/components/wet_floor.dm
@@ -1,206 +1,206 @@
-/datum/component/wet_floor
- dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
- can_transfer = TRUE
- var/highest_strength = TURF_DRY
- var/lube_flags = NONE //why do we have this?
- var/list/time_left_list //In deciseconds.
- var/static/mutable_appearance/permafrost_overlay = mutable_appearance('icons/effects/water.dmi', "ice_floor")
- var/static/mutable_appearance/ice_overlay = mutable_appearance('icons/turf/overlays.dmi', "snowfloor")
- var/static/mutable_appearance/water_overlay = mutable_appearance('icons/effects/water.dmi', "wet_floor_static")
- var/static/mutable_appearance/generic_turf_overlay = mutable_appearance('icons/effects/water.dmi', "wet_static")
- var/current_overlay
- var/permanent = FALSE
- var/last_process = 0
-
-/datum/component/wet_floor/InheritComponent(datum/newcomp, orig, argslist)
- if(!newcomp) //We are getting passed the arguments of a would-be new component, but not a new component
- add_wet(arglist(argslist))
- else //We are being passed in a full blown component
- var/datum/component/wet_floor/WF = newcomp //Lets make an assumption
- if(WF.gc()) //See if it's even valid, still. Also does LAZYLEN and stuff for us.
- CRASH("Wet floor component tried to inherit another, but the other was able to garbage collect while being inherited! What a waste of time!")
- return
- for(var/i in WF.time_left_list)
- add_wet(text2num(i), WF.time_left_list[i])
-
-/datum/component/wet_floor/Initialize(strength, duration_minimum, duration_add, duration_maximum, _permanent = FALSE)
- if(!isopenturf(parent))
- return COMPONENT_INCOMPATIBLE
- add_wet(strength, duration_minimum, duration_add, duration_maximum)
- permanent = _permanent
- if(!permanent)
- START_PROCESSING(SSwet_floors, src)
- addtimer(CALLBACK(src, .proc/gc, TRUE), 1) //GC after initialization.
- last_process = world.time
-
-/datum/component/wet_floor/RegisterWithParent()
- RegisterSignal(parent, COMSIG_TURF_IS_WET, .proc/is_wet)
- RegisterSignal(parent, COMSIG_TURF_MAKE_DRY, .proc/dry)
-
-/datum/component/wet_floor/UnregisterFromParent()
- UnregisterSignal(parent, list(COMSIG_TURF_IS_WET, COMSIG_TURF_MAKE_DRY))
-
-/datum/component/wet_floor/Destroy()
- STOP_PROCESSING(SSwet_floors, src)
- var/turf/T = parent
- qdel(T.GetComponent(/datum/component/slippery))
- if(istype(T)) //If this is false there is so many things wrong with it.
- T.cut_overlay(current_overlay)
- else
- stack_trace("Warning: Wet floor component wasn't on a turf when being destroyed! This is really bad!")
- return ..()
-
-/datum/component/wet_floor/proc/update_overlay()
- var/intended
- if(!istype(parent, /turf/open/floor))
- intended = generic_turf_overlay
- else
- switch(highest_strength)
- if(TURF_WET_PERMAFROST)
- intended = permafrost_overlay
- if(TURF_WET_ICE)
- intended = ice_overlay
- else
- intended = water_overlay
- if(current_overlay != intended)
- var/turf/T = parent
- T.cut_overlay(current_overlay)
- T.add_overlay(intended)
- current_overlay = intended
-
-/datum/component/wet_floor/proc/AfterSlip(mob/living/L)
- if(highest_strength == TURF_WET_LUBE)
- L.confused = max(L.confused, 8)
-
-/datum/component/wet_floor/proc/update_flags()
- var/intensity
- lube_flags = NONE
- switch(highest_strength)
- if(TURF_WET_WATER)
- intensity = 60
- lube_flags = NO_SLIP_WHEN_WALKING
- if(TURF_WET_LUBE)
- intensity = 80
- lube_flags = SLIDE | GALOSHES_DONT_HELP
- if(TURF_WET_ICE)
- intensity = 120
- lube_flags = SLIDE | GALOSHES_DONT_HELP
- if(TURF_WET_PERMAFROST)
- intensity = 120
- lube_flags = SLIDE_ICE | GALOSHES_DONT_HELP
- else
- qdel(parent.GetComponent(/datum/component/slippery))
- return
-
- var/datum/component/slippery/S = parent.LoadComponent(/datum/component/slippery, NONE, CALLBACK(src, .proc/AfterSlip))
- S.intensity = intensity
- S.lube_flags = lube_flags
-
-/datum/component/wet_floor/proc/dry(datum/source, strength = TURF_WET_WATER, immediate = FALSE, duration_decrease = INFINITY)
- for(var/i in time_left_list)
- if(text2num(i) <= strength)
- time_left_list[i] = max(0, time_left_list[i] - duration_decrease)
- if(immediate)
- check()
-
-/datum/component/wet_floor/proc/max_time_left()
- . = 0
- for(var/i in time_left_list)
- . = max(., time_left_list[i])
-
-/datum/component/wet_floor/process()
- var/turf/open/T = parent
- var/diff = world.time - last_process
- var/decrease = 0
- var/t = T.GetTemperature()
- switch(t)
- if(-INFINITY to T0C)
- add_wet(TURF_WET_ICE, max_time_left()) //Water freezes into ice!
- if(T0C to T0C + 100)
- decrease = ((T.air.temperature - T0C) / SSwet_floors.temperature_coeff) * (diff / SSwet_floors.time_ratio)
- if(T0C + 100 to INFINITY)
- decrease = INFINITY
- decrease = max(0, decrease)
- if((is_wet() & TURF_WET_ICE) && t > T0C) //Ice melts into water!
- for(var/obj/O in T.contents)
- if(O.obj_flags & FROZEN)
- O.make_unfrozen()
- add_wet(TURF_WET_WATER, max_time_left())
- dry(null, TURF_WET_ICE)
- dry(null, ALL, FALSE, decrease)
- check()
- last_process = world.time
-
-/datum/component/wet_floor/proc/update_strength()
- highest_strength = 0 //Not bitflag.
- for(var/i in time_left_list)
- highest_strength = max(highest_strength, text2num(i))
-
-/datum/component/wet_floor/proc/is_wet()
- . = 0
- for(var/i in time_left_list)
- . |= text2num(i)
-
-/datum/component/wet_floor/PreTransfer()
- var/turf/O = parent
- O.cut_overlay(current_overlay)
- //That turf is no longer slippery, we're out of here
- //Slippery components don't transfer due to callbacks
- qdel(O.GetComponent(/datum/component/slippery))
-
-/datum/component/wet_floor/PostTransfer()
- if(!isopenturf(parent))
- return COMPONENT_INCOMPATIBLE
- var/turf/T = parent
- T.add_overlay(current_overlay)
- //Make sure to add/update any slippery component on the new turf (update_flags calls LoadComponent)
- update_flags()
-
- //NB it's possible we get deleted after this, due to inherit
-
-/datum/component/wet_floor/proc/add_wet(type, duration_minimum = 0, duration_add = 0, duration_maximum = MAXIMUM_WET_TIME, _permanent = FALSE)
- var/static/list/allowed_types = list(TURF_WET_WATER, TURF_WET_LUBE, TURF_WET_ICE, TURF_WET_PERMAFROST)
- if(duration_minimum <= 0 || !type)
- return FALSE
- if(type in allowed_types)
- return _do_add_wet(type, duration_minimum, duration_add, duration_maximum)
- else
- . = NONE
- for(var/i in allowed_types)
- if(!(type & i))
- continue
- . |= _do_add_wet(i, duration_minimum, duration_add, duration_maximum)
- if(_permanent)
- permanent = TRUE
- STOP_PROCESSING(SSwet_floors, src)
-
-/datum/component/wet_floor/proc/_do_add_wet(type, duration_minimum, duration_add, duration_maximum)
- var/time = 0
- if(LAZYACCESS(time_left_list, "[type]"))
- time = CLAMP(LAZYACCESS(time_left_list, "[type]") + duration_add, duration_minimum, duration_maximum)
- else
- time = min(duration_minimum, duration_maximum)
- LAZYSET(time_left_list, "[type]", time)
- check(TRUE)
- return TRUE
-
-/datum/component/wet_floor/proc/gc(on_init = FALSE)
- if(!LAZYLEN(time_left_list))
- if(on_init)
- var/turf/T = parent
- stack_trace("Warning: Wet floor component gc'd right after initialization! What a waste of time and CPU! Type = [T? T.type : "ERROR - NO PARENT"], Location = [istype(T)? AREACOORD(T) : "ERROR - INVALID PARENT"].")
- qdel(src)
- return TRUE
- return FALSE
-
-/datum/component/wet_floor/proc/check(force_update = FALSE)
- var/changed = FALSE
- for(var/i in time_left_list)
- if(time_left_list[i] <= 0)
- time_left_list -= i
- changed = TRUE
- if(changed || force_update)
- update_strength()
- update_overlay()
- update_flags()
- gc()
+/datum/component/wet_floor
+ dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
+ can_transfer = TRUE
+ var/highest_strength = TURF_DRY
+ var/lube_flags = NONE //why do we have this?
+ var/list/time_left_list //In deciseconds.
+ var/static/mutable_appearance/permafrost_overlay = mutable_appearance('icons/effects/water.dmi', "ice_floor")
+ var/static/mutable_appearance/ice_overlay = mutable_appearance('icons/turf/overlays.dmi', "snowfloor")
+ var/static/mutable_appearance/water_overlay = mutable_appearance('icons/effects/water.dmi', "wet_floor_static")
+ var/static/mutable_appearance/generic_turf_overlay = mutable_appearance('icons/effects/water.dmi', "wet_static")
+ var/current_overlay
+ var/permanent = FALSE
+ var/last_process = 0
+
+/datum/component/wet_floor/InheritComponent(datum/newcomp, orig, argslist)
+ if(!newcomp) //We are getting passed the arguments of a would-be new component, but not a new component
+ add_wet(arglist(argslist))
+ else //We are being passed in a full blown component
+ var/datum/component/wet_floor/WF = newcomp //Lets make an assumption
+ if(WF.gc()) //See if it's even valid, still. Also does LAZYLEN and stuff for us.
+ CRASH("Wet floor component tried to inherit another, but the other was able to garbage collect while being inherited! What a waste of time!")
+ return
+ for(var/i in WF.time_left_list)
+ add_wet(text2num(i), WF.time_left_list[i])
+
+/datum/component/wet_floor/Initialize(strength, duration_minimum, duration_add, duration_maximum, _permanent = FALSE)
+ if(!isopenturf(parent))
+ return COMPONENT_INCOMPATIBLE
+ add_wet(strength, duration_minimum, duration_add, duration_maximum)
+ permanent = _permanent
+ if(!permanent)
+ START_PROCESSING(SSwet_floors, src)
+ addtimer(CALLBACK(src, .proc/gc, TRUE), 1) //GC after initialization.
+ last_process = world.time
+
+/datum/component/wet_floor/RegisterWithParent()
+ RegisterSignal(parent, COMSIG_TURF_IS_WET, .proc/is_wet)
+ RegisterSignal(parent, COMSIG_TURF_MAKE_DRY, .proc/dry)
+
+/datum/component/wet_floor/UnregisterFromParent()
+ UnregisterSignal(parent, list(COMSIG_TURF_IS_WET, COMSIG_TURF_MAKE_DRY))
+
+/datum/component/wet_floor/Destroy()
+ STOP_PROCESSING(SSwet_floors, src)
+ var/turf/T = parent
+ qdel(T.GetComponent(/datum/component/slippery))
+ if(istype(T)) //If this is false there is so many things wrong with it.
+ T.cut_overlay(current_overlay)
+ else
+ stack_trace("Warning: Wet floor component wasn't on a turf when being destroyed! This is really bad!")
+ return ..()
+
+/datum/component/wet_floor/proc/update_overlay()
+ var/intended
+ if(!istype(parent, /turf/open/floor))
+ intended = generic_turf_overlay
+ else
+ switch(highest_strength)
+ if(TURF_WET_PERMAFROST)
+ intended = permafrost_overlay
+ if(TURF_WET_ICE)
+ intended = ice_overlay
+ else
+ intended = water_overlay
+ if(current_overlay != intended)
+ var/turf/T = parent
+ T.cut_overlay(current_overlay)
+ T.add_overlay(intended)
+ current_overlay = intended
+
+/datum/component/wet_floor/proc/AfterSlip(mob/living/L)
+ if(highest_strength == TURF_WET_LUBE)
+ L.confused = max(L.confused, 8)
+
+/datum/component/wet_floor/proc/update_flags()
+ var/intensity
+ lube_flags = NONE
+ switch(highest_strength)
+ if(TURF_WET_WATER)
+ intensity = 60
+ lube_flags = NO_SLIP_WHEN_WALKING
+ if(TURF_WET_LUBE)
+ intensity = 80
+ lube_flags = SLIDE | GALOSHES_DONT_HELP
+ if(TURF_WET_ICE)
+ intensity = 120
+ lube_flags = SLIDE | GALOSHES_DONT_HELP
+ if(TURF_WET_PERMAFROST)
+ intensity = 120
+ lube_flags = SLIDE_ICE | GALOSHES_DONT_HELP
+ else
+ qdel(parent.GetComponent(/datum/component/slippery))
+ return
+
+ var/datum/component/slippery/S = parent.LoadComponent(/datum/component/slippery, NONE, CALLBACK(src, .proc/AfterSlip))
+ S.intensity = intensity
+ S.lube_flags = lube_flags
+
+/datum/component/wet_floor/proc/dry(datum/source, strength = TURF_WET_WATER, immediate = FALSE, duration_decrease = INFINITY)
+ for(var/i in time_left_list)
+ if(text2num(i) <= strength)
+ time_left_list[i] = max(0, time_left_list[i] - duration_decrease)
+ if(immediate)
+ check()
+
+/datum/component/wet_floor/proc/max_time_left()
+ . = 0
+ for(var/i in time_left_list)
+ . = max(., time_left_list[i])
+
+/datum/component/wet_floor/process()
+ var/turf/open/T = parent
+ var/diff = world.time - last_process
+ var/decrease = 0
+ var/t = T.GetTemperature()
+ switch(t)
+ if(-INFINITY to T0C)
+ add_wet(TURF_WET_ICE, max_time_left()) //Water freezes into ice!
+ if(T0C to T0C + 100)
+ decrease = ((T.air.temperature - T0C) / SSwet_floors.temperature_coeff) * (diff / SSwet_floors.time_ratio)
+ if(T0C + 100 to INFINITY)
+ decrease = INFINITY
+ decrease = max(0, decrease)
+ if((is_wet() & TURF_WET_ICE) && t > T0C) //Ice melts into water!
+ for(var/obj/O in T.contents)
+ if(O.obj_flags & FROZEN)
+ O.make_unfrozen()
+ add_wet(TURF_WET_WATER, max_time_left())
+ dry(null, TURF_WET_ICE)
+ dry(null, ALL, FALSE, decrease)
+ check()
+ last_process = world.time
+
+/datum/component/wet_floor/proc/update_strength()
+ highest_strength = 0 //Not bitflag.
+ for(var/i in time_left_list)
+ highest_strength = max(highest_strength, text2num(i))
+
+/datum/component/wet_floor/proc/is_wet()
+ . = 0
+ for(var/i in time_left_list)
+ . |= text2num(i)
+
+/datum/component/wet_floor/PreTransfer()
+ var/turf/O = parent
+ O.cut_overlay(current_overlay)
+ //That turf is no longer slippery, we're out of here
+ //Slippery components don't transfer due to callbacks
+ qdel(O.GetComponent(/datum/component/slippery))
+
+/datum/component/wet_floor/PostTransfer()
+ if(!isopenturf(parent))
+ return COMPONENT_INCOMPATIBLE
+ var/turf/T = parent
+ T.add_overlay(current_overlay)
+ //Make sure to add/update any slippery component on the new turf (update_flags calls LoadComponent)
+ update_flags()
+
+ //NB it's possible we get deleted after this, due to inherit
+
+/datum/component/wet_floor/proc/add_wet(type, duration_minimum = 0, duration_add = 0, duration_maximum = MAXIMUM_WET_TIME, _permanent = FALSE)
+ var/static/list/allowed_types = list(TURF_WET_WATER, TURF_WET_LUBE, TURF_WET_ICE, TURF_WET_PERMAFROST)
+ if(duration_minimum <= 0 || !type)
+ return FALSE
+ if(type in allowed_types)
+ return _do_add_wet(type, duration_minimum, duration_add, duration_maximum)
+ else
+ . = NONE
+ for(var/i in allowed_types)
+ if(!(type & i))
+ continue
+ . |= _do_add_wet(i, duration_minimum, duration_add, duration_maximum)
+ if(_permanent)
+ permanent = TRUE
+ STOP_PROCESSING(SSwet_floors, src)
+
+/datum/component/wet_floor/proc/_do_add_wet(type, duration_minimum, duration_add, duration_maximum)
+ var/time = 0
+ if(LAZYACCESS(time_left_list, "[type]"))
+ time = CLAMP(LAZYACCESS(time_left_list, "[type]") + duration_add, duration_minimum, duration_maximum)
+ else
+ time = min(duration_minimum, duration_maximum)
+ LAZYSET(time_left_list, "[type]", time)
+ check(TRUE)
+ return TRUE
+
+/datum/component/wet_floor/proc/gc(on_init = FALSE)
+ if(!LAZYLEN(time_left_list))
+ if(on_init)
+ var/turf/T = parent
+ stack_trace("Warning: Wet floor component gc'd right after initialization! What a waste of time and CPU! Type = [T? T.type : "ERROR - NO PARENT"], Location = [istype(T)? AREACOORD(T) : "ERROR - INVALID PARENT"].")
+ qdel(src)
+ return TRUE
+ return FALSE
+
+/datum/component/wet_floor/proc/check(force_update = FALSE)
+ var/changed = FALSE
+ for(var/i in time_left_list)
+ if(time_left_list[i] <= 0)
+ time_left_list -= i
+ changed = TRUE
+ if(changed || force_update)
+ update_strength()
+ update_overlay()
+ update_flags()
+ gc()
diff --git a/code/datums/status_effects/gas.dm b/code/datums/status_effects/gas.dm
index dfe0a1d9..00417993 100644
--- a/code/datums/status_effects/gas.dm
+++ b/code/datums/status_effects/gas.dm
@@ -5,7 +5,6 @@
alert_type = /obj/screen/alert/status_effect/freon
var/icon/cube
var/can_melt = TRUE
- var/datum/weakref/redirect_component
/obj/screen/alert/status_effect/freon
name = "Frozen Solid"
@@ -13,7 +12,7 @@
icon_state = "frozen"
/datum/status_effect/freon/on_apply()
- redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/owner_resist))))
+ RegisterSignal(owner, COMSIG_LIVING_RESIST, .proc/owner_resist)
if(!owner.stat)
to_chat(owner, "You become frozen in a cube!")
cube = icon('icons/effects/freeze.dmi', "ice_cube")
@@ -40,8 +39,7 @@
owner.cut_overlay(cube)
owner.adjust_bodytemperature(100)
owner.update_canmove()
- qdel(redirect_component.resolve())
- redirect_component = null
+ UnregisterSignal(owner, COMSIG_LIVING_RESIST)
/datum/status_effect/freon/watcher
duration = 8
diff --git a/code/game/gamemodes/dynamic/dynamic_rulesets_events.dm b/code/game/gamemodes/dynamic/dynamic_rulesets_events.dm
index 839cb035..efaa5eff 100644
--- a/code/game/gamemodes/dynamic/dynamic_rulesets_events.dm
+++ b/code/game/gamemodes/dynamic/dynamic_rulesets_events.dm
@@ -376,10 +376,11 @@
typepath = /datum/round_event/ghost_role/operative
required_enemies = list(0,0,0,0,0,0,0,0,0,0)
weight = 0 //This is changed in nuclearbomb.dm
- occurances_max = 1
+ occurances_max = 0 //Turned off. For now.
requirements = list(10,10,10,10,10,10,10,10,10,10) //SECURE THAT DISK
cost = 50
- chaos_min = 0.5
+ chaos_min = 3
+ map_blacklist = list("LayeniaStation.dmm")
/datum/dynamic_ruleset/event/operative/get_weight()
var/datum/round_event_control/operative/loneop = locate(/datum/round_event_control/operative) in SSevents.control
diff --git a/code/game/objects/effects/proximity.dm b/code/game/objects/effects/proximity.dm
index 23977746..34d6497d 100644
--- a/code/game/objects/effects/proximity.dm
+++ b/code/game/objects/effects/proximity.dm
@@ -1,112 +1,112 @@
-/datum/proximity_monitor
- var/atom/host //the atom we are tracking
- var/atom/hasprox_receiver //the atom that will receive HasProximity calls.
- var/atom/last_host_loc
- var/list/checkers //list of /obj/effect/abstract/proximity_checkers
- var/current_range
- var/ignore_if_not_on_turf //don't check turfs in range if the host's loc isn't a turf
- var/datum/component/movement_tracker
-
-/datum/proximity_monitor/New(atom/_host, range, _ignore_if_not_on_turf = TRUE)
- checkers = list()
- last_host_loc = _host.loc
- ignore_if_not_on_turf = _ignore_if_not_on_turf
- current_range = range
- SetHost(_host)
-
-/datum/proximity_monitor/proc/SetHost(atom/H,atom/R)
- if(R)
- hasprox_receiver = R
- else if(hasprox_receiver == host) //Default case
- hasprox_receiver = H
- host = H
- last_host_loc = host.loc
- if(movement_tracker)
- QDEL_NULL(movement_tracker)
- movement_tracker = host.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/HandleMove)))
- SetRange(current_range,TRUE)
-
-/datum/proximity_monitor/Destroy()
- host = null
- last_host_loc = null
- hasprox_receiver = null
- QDEL_LIST(checkers)
- QDEL_NULL(movement_tracker)
- return ..()
-
-/datum/proximity_monitor/proc/HandleMove()
- var/atom/_host = host
- var/atom/new_host_loc = _host.loc
- if(last_host_loc != new_host_loc)
- last_host_loc = new_host_loc //hopefully this won't cause GC issues with containers
- var/curr_range = current_range
- SetRange(curr_range, TRUE)
- if(curr_range)
- testing("HasProx: [host] -> [host]")
- hasprox_receiver.HasProximity(host) //if we are processing, we're guaranteed to be a movable
-
-/datum/proximity_monitor/proc/SetRange(range, force_rebuild = FALSE)
- if(!force_rebuild && range == current_range)
- return FALSE
- . = TRUE
-
- current_range = range
-
- var/list/checkers_local = checkers
- var/old_checkers_len = checkers_local.len
-
- var/atom/_host = host
-
- var/atom/loc_to_use = ignore_if_not_on_turf ? _host.loc : get_turf(_host)
- if(!isturf(loc_to_use)) //only check the host's loc
- if(range)
- var/obj/effect/abstract/proximity_checker/pc
- if(old_checkers_len)
- pc = checkers_local[old_checkers_len]
- --checkers_local.len
- QDEL_LIST(checkers_local)
- else
- pc = new(loc_to_use, src)
-
- checkers_local += pc //only check the host's loc
- return
-
- var/list/turfs = RANGE_TURFS(range, loc_to_use)
- var/turfs_len = turfs.len
- var/old_checkers_used = min(turfs_len, old_checkers_len)
-
- //reuse what we can
- for(var/I in 1 to old_checkers_len)
- if(I <= old_checkers_used)
- var/obj/effect/abstract/proximity_checker/pc = checkers_local[I]
- pc.forceMove(turfs[I])
- else
- qdel(checkers_local[I]) //delete the leftovers
-
- if(old_checkers_len < turfs_len)
- //create what we lack
- for(var/I in (old_checkers_used + 1) to turfs_len)
- checkers_local += new /obj/effect/abstract/proximity_checker(turfs[I], src)
- else
- checkers_local.Cut(old_checkers_used + 1, old_checkers_len)
-
-/obj/effect/abstract/proximity_checker
- invisibility = INVISIBILITY_ABSTRACT
- anchored = TRUE
- var/datum/proximity_monitor/monitor
-
-/obj/effect/abstract/proximity_checker/Initialize(mapload, datum/proximity_monitor/_monitor)
- . = ..()
- if(_monitor)
- monitor = _monitor
- else
- stack_trace("proximity_checker created without host")
- return INITIALIZE_HINT_QDEL
-
-/obj/effect/abstract/proximity_checker/Destroy()
- monitor = null
- return ..()
-
-/obj/effect/abstract/proximity_checker/Crossed(atom/movable/AM)
- set waitfor = FALSE
- monitor?.hasprox_receiver.HasProximity(AM)
+/datum/proximity_monitor
+ var/atom/host //the atom we are tracking
+ var/atom/hasprox_receiver //the atom that will receive HasProximity calls.
+ var/atom/last_host_loc
+ var/list/checkers //list of /obj/effect/abstract/proximity_checkers
+ var/current_range
+ var/ignore_if_not_on_turf //don't check turfs in range if the host's loc isn't a turf
+
+/datum/proximity_monitor/New(atom/_host, range, _ignore_if_not_on_turf = TRUE)
+ checkers = list()
+ last_host_loc = _host.loc
+ ignore_if_not_on_turf = _ignore_if_not_on_turf
+ current_range = range
+ SetHost(_host)
+
+/datum/proximity_monitor/proc/SetHost(atom/H,atom/R)
+ if(H == host)
+ return
+ if(host)
+ UnregisterSignal(host, COMSIG_MOVABLE_MOVED)
+ if(R)
+ hasprox_receiver = R
+ else if(hasprox_receiver == host) //Default case
+ hasprox_receiver = H
+ host = H
+ RegisterSignal(host, COMSIG_MOVABLE_MOVED, .proc/HandleMove)
+ last_host_loc = host.loc
+ SetRange(current_range,TRUE)
+
+/datum/proximity_monitor/Destroy()
+ host = null
+ last_host_loc = null
+ hasprox_receiver = null
+ QDEL_LIST(checkers)
+ return ..()
+
+/datum/proximity_monitor/proc/HandleMove()
+ var/atom/_host = host
+ var/atom/new_host_loc = _host.loc
+ if(last_host_loc != new_host_loc)
+ last_host_loc = new_host_loc //hopefully this won't cause GC issues with containers
+ var/curr_range = current_range
+ SetRange(curr_range, TRUE)
+ if(curr_range)
+ testing("HasProx: [host] -> [host]")
+ hasprox_receiver.HasProximity(host) //if we are processing, we're guaranteed to be a movable
+
+/datum/proximity_monitor/proc/SetRange(range, force_rebuild = FALSE)
+ if(!force_rebuild && range == current_range)
+ return FALSE
+ . = TRUE
+
+ current_range = range
+
+ var/list/checkers_local = checkers
+ var/old_checkers_len = checkers_local.len
+
+ var/atom/_host = host
+
+ var/atom/loc_to_use = ignore_if_not_on_turf ? _host.loc : get_turf(_host)
+ if(!isturf(loc_to_use)) //only check the host's loc
+ if(range)
+ var/obj/effect/abstract/proximity_checker/pc
+ if(old_checkers_len)
+ pc = checkers_local[old_checkers_len]
+ --checkers_local.len
+ QDEL_LIST(checkers_local)
+ else
+ pc = new(loc_to_use, src)
+
+ checkers_local += pc //only check the host's loc
+ return
+
+ var/list/turfs = RANGE_TURFS(range, loc_to_use)
+ var/turfs_len = turfs.len
+ var/old_checkers_used = min(turfs_len, old_checkers_len)
+
+ //reuse what we can
+ for(var/I in 1 to old_checkers_len)
+ if(I <= old_checkers_used)
+ var/obj/effect/abstract/proximity_checker/pc = checkers_local[I]
+ pc.forceMove(turfs[I])
+ else
+ qdel(checkers_local[I]) //delete the leftovers
+
+ if(old_checkers_len < turfs_len)
+ //create what we lack
+ for(var/I in (old_checkers_used + 1) to turfs_len)
+ checkers_local += new /obj/effect/abstract/proximity_checker(turfs[I], src)
+ else
+ checkers_local.Cut(old_checkers_used + 1, old_checkers_len)
+
+/obj/effect/abstract/proximity_checker
+ invisibility = INVISIBILITY_ABSTRACT
+ anchored = TRUE
+ var/datum/proximity_monitor/monitor
+
+/obj/effect/abstract/proximity_checker/Initialize(mapload, datum/proximity_monitor/_monitor)
+ . = ..()
+ if(_monitor)
+ monitor = _monitor
+ else
+ stack_trace("proximity_checker created without host")
+ return INITIALIZE_HINT_QDEL
+
+/obj/effect/abstract/proximity_checker/Destroy()
+ monitor = null
+ return ..()
+
+/obj/effect/abstract/proximity_checker/Crossed(atom/movable/AM)
+ set waitfor = FALSE
+ monitor?.hasprox_receiver.HasProximity(AM)
diff --git a/code/game/objects/items/RCL.dm b/code/game/objects/items/RCL.dm
index 16104f0b..0eb97a8d 100644
--- a/code/game/objects/items/RCL.dm
+++ b/code/game/objects/items/RCL.dm
@@ -20,8 +20,8 @@
var/ghetto = FALSE
lefthand_file = 'icons/mob/inhands/equipment/tools_lefthand.dmi'
righthand_file = 'icons/mob/inhands/equipment/tools_righthand.dmi'
- var/datum/component/mobhook
var/datum/radial_menu/persistent/wiring_gui_menu
+ var/mob/listeningTo
/obj/item/twohanded/rcl/attackby(obj/item/W, mob/user)
if(istype(W, /obj/item/stack/cable_coil))
@@ -86,7 +86,7 @@
/obj/item/twohanded/rcl/Destroy()
QDEL_NULL(loaded)
last = null
- QDEL_NULL(mobhook)
+ listeningTo = null
QDEL_NULL(wiring_gui_menu)
return ..()
@@ -141,9 +141,8 @@
/obj/item/twohanded/rcl/dropped(mob/wearer)
..()
- if(mobhook)
- active = FALSE
- QDEL_NULL(mobhook)
+ UnregisterSignal(wearer, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
last = null
/obj/item/twohanded/rcl/attack_self(mob/user)
@@ -158,13 +157,12 @@
break
obj/item/twohanded/rcl/proc/getMobhook(mob/to_hook)
- if(to_hook)
- if(mobhook && mobhook.parent != to_hook)
- QDEL_NULL(mobhook)
- if (!mobhook)
- mobhook = to_hook.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/trigger)))
- else
- QDEL_NULL(mobhook)
+ if(listeningTo == to_hook)
+ return
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ RegisterSignal(to_hook, COMSIG_MOVABLE_MOVED, .proc/trigger)
+ listeningTo = to_hook
/obj/item/twohanded/rcl/proc/trigger(mob/user)
if(active)
diff --git a/code/game/objects/items/defib.dm b/code/game/objects/items/defib.dm
index e3752ab4..f3efb52d 100644
--- a/code/game/objects/items/defib.dm
+++ b/code/game/objects/items/defib.dm
@@ -39,7 +39,6 @@
/obj/item/defibrillator/loaded/Initialize() //starts with hicap
. = ..()
- paddles = make_paddles()
cell = new(src)
update_icon()
return
@@ -204,8 +203,8 @@
var/M = get(paddles, /mob)
remove_paddles(M)
QDEL_NULL(paddles)
- . = ..()
- update_icon()
+ QDEL_NULL(cell)
+ return ..()
/obj/item/defibrillator/proc/deductcharge(chrgdeductamt)
if(cell)
@@ -246,7 +245,6 @@
/obj/item/defibrillator/compact/loaded/Initialize()
. = ..()
- paddles = make_paddles()
cell = new(src)
update_icon()
@@ -258,7 +256,6 @@
/obj/item/defibrillator/compact/combat/loaded/Initialize()
. = ..()
- paddles = make_paddles()
cell = new /obj/item/stock_parts/cell/infinite(src)
update_icon()
@@ -293,31 +290,28 @@
var/grab_ghost = FALSE
var/tlimit = DEFIB_TIME_LIMIT * 10
- var/datum/component/mobhook
+ var/mob/listeningTo
/obj/item/twohanded/shockpaddles/equipped(mob/user, slot)
. = ..()
- if(req_defib)
- if (mobhook && mobhook.parent != user)
- QDEL_NULL(mobhook)
- if (!mobhook)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/check_range)))
+ if(!req_defib)
+ return
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/check_range)
/obj/item/twohanded/shockpaddles/Moved()
. = ..()
check_range()
/obj/item/twohanded/shockpaddles/proc/check_range()
- if(!req_defib)
+ if(!req_defib || !defib)
return
if(!in_range(src,defib))
var/mob/living/L = loc
if(istype(L))
to_chat(L, "[defib]'s paddles overextend and come out of your hands!")
- L.temporarilyRemoveItemFromInventory(src,TRUE)
else
visible_message("[src] snap back into [defib].")
- snap_back()
+ snap_back()
/obj/item/twohanded/shockpaddles/proc/recharge(var/time)
if(req_defib || !time)
@@ -358,14 +352,14 @@
/obj/item/twohanded/shockpaddles/dropped(mob/user)
if(!req_defib)
return ..()
- if (mobhook)
- QDEL_NULL(mobhook)
if(user)
+ UnregisterSignal(user, COMSIG_MOVABLE_MOVED)
var/obj/item/twohanded/offhand/O = user.get_inactive_held_item()
if(istype(O))
O.unwield()
- to_chat(user, "The paddles snap back into the main unit.")
- snap_back()
+ if(user != loc)
+ to_chat(user, "The paddles snap back into the main unit.")
+ snap_back()
return unwield(user)
/obj/item/twohanded/shockpaddles/proc/snap_back()
diff --git a/code/game/objects/items/devices/geiger_counter.dm b/code/game/objects/items/devices/geiger_counter.dm
index 0dbede18..8d386842 100644
--- a/code/game/objects/items/devices/geiger_counter.dm
+++ b/code/game/objects/items/devices/geiger_counter.dm
@@ -205,21 +205,25 @@
obj_flags |= EMAGGED
/obj/item/geiger_counter/cyborg
- var/datum/component/mobhook
+ var/mob/listeningTo
/obj/item/geiger_counter/cyborg/equipped(mob/user)
. = ..()
- if (mobhook && mobhook.parent != user)
- QDEL_NULL(mobhook)
- if (!mobhook)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_ATOM_RAD_ACT = CALLBACK(src, .proc/redirect_rad_act)))
+ if(listeningTo == user)
+ return
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_ATOM_RAD_ACT)
+ RegisterSignal(user, COMSIG_ATOM_RAD_ACT, .proc/redirect_rad_act)
+ listeningTo = user
/obj/item/geiger_counter/cyborg/proc/redirect_rad_act(datum/source, amount)
rad_act(amount)
/obj/item/geiger_counter/cyborg/dropped()
. = ..()
- QDEL_NULL(mobhook)
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_ATOM_RAD_ACT)
+ listeningTo = null
#undef RAD_LEVEL_NORMAL
#undef RAD_LEVEL_MODERATE
diff --git a/code/game/objects/items/grenades/spawnergrenade.dm b/code/game/objects/items/grenades/spawnergrenade.dm
index 466caf93..52ebe761 100644
--- a/code/game/objects/items/grenades/spawnergrenade.dm
+++ b/code/game/objects/items/grenades/spawnergrenade.dm
@@ -48,4 +48,10 @@
icon_state = "clustaur"
item_state = "clustaur"
deliveryamt = 5
- spawner_type = /obj/item/reagent_containers/glass/beaker/waterbottle/wataur
\ No newline at end of file
+ spawner_type = /obj/item/reagent_containers/glass/beaker/waterbottle/wataur
+
+/obj/item/grenade/spawnergrenade/mimics
+ desc = "Months after their first arrival, compression tests were already successful and thus Kinaris created the first mimic bioweapon, a simple payload to quickly release a cluster of them."
+ name = "mimic delivery grenade"
+ spawner_type = /mob/living/simple_animal/hostile/hs13mimic
+ deliveryamt = 10
diff --git a/code/game/objects/items/his_grace.dm b/code/game/objects/items/his_grace.dm
index b5c7af4b..ce5810f5 100644
--- a/code/game/objects/items/his_grace.dm
+++ b/code/game/objects/items/his_grace.dm
@@ -29,7 +29,7 @@
. = ..()
START_PROCESSING(SSprocessing, src)
GLOB.poi_list += src
- AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_POST_THROW = CALLBACK(src, .proc/move_gracefully)))
+ RegisterSignal(src, COMSIG_MOVABLE_POST_THROW, .proc/move_gracefully)
/obj/item/his_grace/Destroy()
STOP_PROCESSING(SSprocessing, src)
diff --git a/code/game/objects/items/stacks/sheets/sheet_types.dm b/code/game/objects/items/stacks/sheets/sheet_types.dm
index 8f8afa9b..c86debe7 100644
--- a/code/game/objects/items/stacks/sheets/sheet_types.dm
+++ b/code/game/objects/items/stacks/sheets/sheet_types.dm
@@ -223,6 +223,7 @@ GLOBAL_LIST_INIT(wood_recipes, list ( \
new/datum/stack_recipe("coffin", /obj/structure/closet/crate/coffin, 5, time = 15, one_per_turf = TRUE, on_floor = TRUE), \
new/datum/stack_recipe("book case", /obj/structure/bookcase, 4, time = 15, one_per_turf = TRUE, on_floor = TRUE), \
new/datum/stack_recipe("drying rack", /obj/machinery/smartfridge/drying_rack, 10, time = 15, one_per_turf = TRUE, on_floor = TRUE), \
+ new/datum/stack_recipe("sauna oven", /obj/structure/sauna_oven, 30, time = 15, one_per_turf = TRUE, on_floor = TRUE), \
new/datum/stack_recipe("dog bed", /obj/structure/bed/dogbed, 10, time = 10, one_per_turf = TRUE, on_floor = TRUE), \
new/datum/stack_recipe("dresser", /obj/structure/dresser, 10, time = 15, one_per_turf = TRUE, on_floor = TRUE), \
new/datum/stack_recipe("ore box", /obj/structure/ore_box, 4, time = 50, one_per_turf = TRUE, on_floor = TRUE),\
@@ -900,4 +901,4 @@ GLOBAL_LIST_INIT(plaswood_recipes, list ( \
return ..()
/obj/item/stack/sheet/mineral/plaswood/fifty
- amount = 50
\ No newline at end of file
+ amount = 50
diff --git a/code/game/objects/items/storage/bags.dm b/code/game/objects/items/storage/bags.dm
index 14a8d793..6c3dbee7 100644
--- a/code/game/objects/items/storage/bags.dm
+++ b/code/game/objects/items/storage/bags.dm
@@ -1,439 +1,441 @@
-/*
- * These absorb the functionality of the plant bag, ore satchel, etc
- * They use the use_to_pickup, quick_gather, and quick_empty functions
- * that were already defined in weapon/storage, but which had been
- * re-implemented in other classes.
- *
- * Contains:
- * Trash Bag
- * Mining Satchel
- * Plant Bag
- * Sheet Snatcher
- * Book Bag
- * Biowaste Bag
- *
- * -Sayu
- */
-
-// Generic non-item
-/obj/item/storage/bag
- slot_flags = ITEM_SLOT_BELT
-
-/obj/item/storage/bag/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.allow_quick_gather = TRUE
- STR.allow_quick_empty = TRUE
- STR.display_numerical_stacking = TRUE
- STR.click_gather = TRUE
-
-// -----------------------------
-// Trash bag
-// -----------------------------
-/obj/item/storage/bag/trash
- name = "trash bag"
- desc = "It's the heavy-duty black polymer kind. Time to take out the trash!"
- icon = 'icons/obj/janitor.dmi'
- icon_state = "trashbag"
- item_state = "trashbag"
- lefthand_file = 'icons/mob/inhands/equipment/custodial_lefthand.dmi'
- righthand_file = 'icons/mob/inhands/equipment/custodial_righthand.dmi'
-
- w_class = WEIGHT_CLASS_BULKY
- var/insertable = TRUE
-
-/obj/item/storage/bag/trash/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_w_class = WEIGHT_CLASS_SMALL
- STR.max_combined_w_class = 30
- STR.max_items = 30
- STR.cant_hold = typecacheof(list(/obj/item/disk/nuclear))
-
-/obj/item/storage/bag/trash/suicide_act(mob/user)
- user.visible_message("[user] puts [src] over [user.p_their()] head and starts chomping at the insides! Disgusting!")
- playsound(loc, 'sound/items/eatfood.ogg', 50, 1, -1)
- return (TOXLOSS)
-
-/obj/item/storage/bag/trash/update_icon()
- if(contents.len == 0)
- icon_state = "[initial(icon_state)]"
- else if(contents.len < 12)
- icon_state = "[initial(icon_state)]1"
- else if(contents.len < 21)
- icon_state = "[initial(icon_state)]2"
- else icon_state = "[initial(icon_state)]3"
-
-/obj/item/storage/bag/trash/cyborg
- insertable = FALSE
-
-/obj/item/storage/bag/trash/proc/janicart_insert(mob/user, obj/structure/janitorialcart/J)
- if(insertable)
- J.put_in_cart(src, user)
- J.mybag=src
- J.update_icon()
- else
- to_chat(user, "You are unable to fit your [name] into the [J.name].")
- return
-
-/obj/item/storage/bag/trash/bluespace
- name = "trash bag of holding"
- desc = "The latest and greatest in custodial convenience, a trashbag that is capable of holding vast quantities of garbage."
- icon_state = "bluetrashbag"
- item_flags = NO_MAT_REDEMPTION
-
-/obj/item/storage/bag/trash/bluespace/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_combined_w_class = 60
- STR.max_items = 60
-
-/obj/item/storage/bag/trash/bluespace/cyborg
- insertable = FALSE
-
-// -----------------------------
-// Mining Satchel
-// -----------------------------
-
-/obj/item/storage/bag/ore
- name = "mining satchel"
- desc = "This little bugger can be used to store and transport ores."
- icon = 'icons/obj/mining.dmi'
- icon_state = "satchel"
- slot_flags = ITEM_SLOT_BELT | ITEM_SLOT_POCKET
- w_class = WEIGHT_CLASS_NORMAL
- component_type = /datum/component/storage/concrete/stack
- var/spam_protection = FALSE //If this is TRUE, the holder won't receive any messages when they fail to pick up ore through crossing it
- var/datum/component/mobhook
-
-/obj/item/storage/bag/ore/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.allow_quick_empty = TRUE
- STR.can_hold = typecacheof(list(/obj/item/stack/ore))
- STR.max_w_class = WEIGHT_CLASS_HUGE
- STR.max_combined_stack_amount = 50
-
-/obj/item/storage/bag/ore/equipped(mob/user)
- . = ..()
- if (mobhook && mobhook.parent != user)
- QDEL_NULL(mobhook)
- if (!mobhook)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/Pickup_ores)))
-
-/obj/item/storage/bag/ore/dropped()
- . = ..()
- if (mobhook)
- QDEL_NULL(mobhook)
-
-/obj/item/storage/bag/ore/proc/Pickup_ores(mob/living/user)
- var/show_message = FALSE
- var/obj/structure/ore_box/box
- var/turf/tile = user.loc
- if (!isturf(tile))
- return
- if (istype(user.pulling, /obj/structure/ore_box))
- box = user.pulling
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- if(STR)
- for(var/A in tile)
- if (!is_type_in_typecache(A, STR.can_hold))
- continue
- if (box)
- user.transferItemToLoc(A, box)
- show_message = TRUE
- else if(SEND_SIGNAL(src, COMSIG_TRY_STORAGE_INSERT, A, user, TRUE))
- show_message = TRUE
- else
- if(!spam_protection)
- to_chat(user, "Your [name] is full and can't hold any more!")
- spam_protection = TRUE
- continue
- if(show_message)
- playsound(user, "rustle", 50, TRUE)
- if (box)
- user.visible_message("[user] offloads the ores beneath [user.p_them()] into [box].", \
- "You offload the ores beneath you into your [box].")
- else
- user.visible_message("[user] scoops up the ores beneath [user.p_them()].", \
- "You scoop up the ores beneath you with your [name].")
- spam_protection = FALSE
-
-/obj/item/storage/bag/ore/cyborg
- name = "cyborg mining satchel"
-
-/obj/item/storage/bag/ore/cyborg/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.allow_quick_empty = TRUE
- STR.can_hold = typecacheof(list(/obj/item/stack/ore))
- STR.max_w_class = WEIGHT_CLASS_HUGE
- STR.max_combined_stack_amount = 150
-
-/obj/item/storage/bag/ore/large
- name = "large mining satchel"
- desc = "This bag can hold three times the ore in many small pockets. Shockingly foldable and compact for its volume."
-
-/obj/item/storage/bag/ore/large/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.allow_quick_empty = TRUE
- STR.can_hold = typecacheof(list(/obj/item/stack/ore))
- STR.max_w_class = WEIGHT_CLASS_HUGE
- STR.max_combined_stack_amount = 150
-
-/obj/item/storage/bag/ore/holding //miners, your messiah has arrived
- name = "mining satchel of holding"
- desc = "A revolution in convenience, this satchel allows for huge amounts of ore storage. It's been outfitted with anti-malfunction safety measures."
- icon_state = "satchel_bspace"
-
-/obj/item/storage/bag/ore/holding/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.max_items = INFINITY
- STR.max_combined_w_class = INFINITY
- STR.max_combined_stack_amount = INFINITY
-
-// -----------------------------
-// Plant bag
-// -----------------------------
-
-/obj/item/storage/bag/plants
- name = "plant bag"
- icon = 'icons/obj/hydroponics/equipment.dmi'
- icon_state = "plantbag"
- w_class = WEIGHT_CLASS_TINY
- resistance_flags = FLAMMABLE
-
-/obj/item/storage/bag/plants/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_w_class = WEIGHT_CLASS_NORMAL
- STR.max_combined_w_class = 100
- STR.max_items = 100
- STR.can_hold = typecacheof(list(/obj/item/reagent_containers/food/snacks/grown, /obj/item/seeds, /obj/item/grown, /obj/item/reagent_containers/honeycomb))
-
-////////
-
-/obj/item/storage/bag/plants/portaseeder
- name = "portable seed extractor"
- desc = "For the enterprising botanist on the go. Less efficient than the stationary model, it creates one seed per plant."
- icon_state = "portaseeder"
-
-/obj/item/storage/bag/plants/portaseeder/verb/dissolve_contents()
- set name = "Activate Seed Extraction"
- set category = "Object"
- set desc = "Activate to convert your plants into plantable seeds."
- if(usr.stat || !usr.canmove || usr.restrained())
- return
- for(var/obj/item/O in contents)
- seedify(O, 1)
-
-// -----------------------------
-// Sheet Snatcher
-// -----------------------------
-// Because it stacks stacks, this doesn't operate normally.
-// However, making it a storage/bag allows us to reuse existing code in some places. -Sayu
-
-/obj/item/storage/bag/sheetsnatcher
- name = "sheet snatcher"
- desc = "A patented Kinaris storage system designed for any kind of mineral sheet."
- icon = 'icons/obj/mining.dmi'
- icon_state = "sheetsnatcher"
-
- var/capacity = 300; //the number of sheets it can carry.
- w_class = WEIGHT_CLASS_NORMAL
- component_type = /datum/component/storage/concrete/stack
-
-/obj/item/storage/bag/sheetsnatcher/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.allow_quick_empty = TRUE
- STR.can_hold = typecacheof(list(/obj/item/stack/sheet))
- STR.cant_hold = typecacheof(list(/obj/item/stack/sheet/mineral/sandstone, /obj/item/stack/sheet/mineral/wood))
- STR.max_combined_stack_amount = 300
-
-// -----------------------------
-// Sheet Snatcher (Cyborg)
-// -----------------------------
-
-/obj/item/storage/bag/sheetsnatcher/borg
- name = "sheet snatcher 9000"
- desc = ""
- capacity = 500//Borgs get more because >specialization
-
-/obj/item/storage/bag/sheetsnatcher/borg/ComponentInitialize()
- . = ..()
- var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
- STR.max_combined_stack_amount = 500
-
-// -----------------------------
-// Book bag
-// -----------------------------
-
-/obj/item/storage/bag/books
- name = "book bag"
- desc = "A bag for books."
- icon = 'icons/obj/library.dmi'
- icon_state = "bookbag"
- w_class = WEIGHT_CLASS_BULKY //Bigger than a book because physics
- resistance_flags = FLAMMABLE
-
-/obj/item/storage/bag/books/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_w_class = WEIGHT_CLASS_NORMAL
- STR.max_combined_w_class = 21
- STR.max_items = 7
- STR.display_numerical_stacking = FALSE
- STR.can_hold = typecacheof(list(/obj/item/book, /obj/item/storage/book, /obj/item/spellbook))
-
-/*
- * Trays - Agouri
- */
-/obj/item/storage/bag/tray
- name = "tray"
- icon = 'icons/obj/food/containers.dmi'
- icon_state = "tray"
- desc = "A metal tray to lay food on."
- force = 5
- throwforce = 10
- throw_speed = 3
- throw_range = 5
- w_class = WEIGHT_CLASS_BULKY
- flags_1 = CONDUCT_1
- materials = list(MAT_METAL=3000)
-
-/obj/item/storage/bag/tray/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_items = 15 //I want my sushi god damn it
- STR.insert_preposition = "on"
- STR.can_hold = typecacheof(list(
- /obj/item/reagent_containers/food,
- /obj/item/kitchen,
- /obj/item/storage/box/donkpockets))
-
-/obj/item/storage/bag/tray/pre_attack(atom/A, mob/living/user, params)
- if(istype(A, /obj/structure/table) && user.a_intent == INTENT_HELP) //I want my tray god damn it
- if(user.transferItemToLoc(src, get_turf(A)))
- var/list/click_params = params2list(params)
- if(!click_params || !click_params["icon-x"] || !click_params["icon-y"])
- return
- pixel_x = CLAMP(text2num(click_params["icon-x"]) - 16, -(world.icon_size/2), world.icon_size/2)
- pixel_y = CLAMP(text2num(click_params["icon-y"]) - 16, -(world.icon_size/2), world.icon_size/2)
- return
- ..()
-
-/obj/item/storage/bag/tray/attack(mob/living/M, mob/living/user)
- . = ..()
- // Drop all the things. All of them.
- var/list/obj/item/oldContents = contents.Copy()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.quick_empty()
- // Make each item scatter a bit
- for(var/obj/item/I in oldContents)
- spawn()
- for(var/i = 1, i <= rand(1,2), i++)
- if(I)
- step(I, pick(NORTH,SOUTH,EAST,WEST))
- sleep(rand(2,4))
-
- if(prob(50))
- playsound(M, 'sound/items/trayhit1.ogg', 50, 1)
- else
- playsound(M, 'sound/items/trayhit2.ogg', 50, 1)
-
- if(ishuman(M) || ismonkey(M))
- if(prob(10))
- M.Knockdown(40)
- update_icon()
-
-/obj/item/storage/bag/tray/update_icon()
- cut_overlays()
- for(var/obj/item/I in contents)
- var/mutable_appearance/MA = new (I) //I want my icons god damn it
- MA.pixel_x = rand(-6, 6)
- MA.pixel_y = rand(-6, 6)
- add_overlay(MA)
-
-/obj/item/storage/bag/tray/Entered()
- . = ..()
- update_icon()
-
-/obj/item/storage/bag/tray/Exited()
- . = ..()
- update_icon()
-
-/*
- * Chemistry bag
- */
-
-/obj/item/storage/bag/chemistry
- name = "chemistry bag"
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bag"
- desc = "A bag for storing pills, patches, and bottles."
- w_class = WEIGHT_CLASS_TINY
- resistance_flags = FLAMMABLE
-
-/obj/item/storage/bag/chemistry/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_combined_w_class = 200
- STR.max_items = 50
- STR.insert_preposition = "in"
- STR.can_hold = typecacheof(list(/obj/item/reagent_containers/pill, /obj/item/reagent_containers/glass/beaker, /obj/item/reagent_containers/glass/bottle, /obj/item/reagent_containers/syringe/dart, /obj/item/reagent_containers/chem_pack))
-
-/*
- * Biowaste bag (mostly for xenobiologists)
- */
-
-/obj/item/storage/bag/bio
- name = "bio bag"
- icon = 'icons/obj/chemical.dmi'
- icon_state = "biobag"
- desc = "A bag for the safe transportation and disposal of biowaste and other biological materials."
- w_class = WEIGHT_CLASS_TINY
- resistance_flags = FLAMMABLE
-
-/obj/item/storage/bag/bio/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_combined_w_class = 200
- STR.max_items = 25
- STR.insert_preposition = "in"
- STR.can_hold = typecacheof(list(/obj/item/slime_extract, /obj/item/reagent_containers/syringe, /obj/item/reagent_containers/glass/beaker, /obj/item/reagent_containers/glass/bottle, /obj/item/reagent_containers/blood, /obj/item/reagent_containers/hypospray/medipen, /obj/item/reagent_containers/food/snacks/deadmouse, /obj/item/reagent_containers/food/snacks/monkeycube))
-
-/obj/item/storage/bag/bio/holding
- name = "bio bag of holding"
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bspace_biobag"
- desc = "A bag for the safe transportation and disposal of biowaste and other biological materials."
-
-/obj/item/storage/bag/bio/holding/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_combined_w_class = INFINITY
- STR.max_items = 100
-
-/*
- * Construction bag (for engineering, holds stock parts and electronics)
- */
-
-/obj/item/storage/bag/construction
- name = "construction bag"
- icon = 'icons/obj/tools.dmi'
- icon_state = "construction_bag"
- desc = "A bag for storing small construction components."
- w_class = WEIGHT_CLASS_TINY
- resistance_flags = FLAMMABLE
-
-/obj/item/storage/bag/construction/ComponentInitialize()
- . = ..()
- var/datum/component/storage/STR = GetComponent(/datum/component/storage)
- STR.max_combined_w_class = 100
- STR.max_items = 50
- STR.max_w_class = WEIGHT_CLASS_SMALL
- STR.insert_preposition = "in"
- STR.can_hold = typecacheof(list(/obj/item/stack/ore/bluespace_crystal, /obj/item/assembly, /obj/item/stock_parts, /obj/item/reagent_containers/glass/beaker, /obj/item/stack/cable_coil, /obj/item/circuitboard, /obj/item/electronics))
+/*
+ * These absorb the functionality of the plant bag, ore satchel, etc
+ * They use the use_to_pickup, quick_gather, and quick_empty functions
+ * that were already defined in weapon/storage, but which had been
+ * re-implemented in other classes.
+ *
+ * Contains:
+ * Trash Bag
+ * Mining Satchel
+ * Plant Bag
+ * Sheet Snatcher
+ * Book Bag
+ * Biowaste Bag
+ *
+ * -Sayu
+ */
+
+// Generic non-item
+/obj/item/storage/bag
+ slot_flags = ITEM_SLOT_BELT
+
+/obj/item/storage/bag/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.allow_quick_gather = TRUE
+ STR.allow_quick_empty = TRUE
+ STR.display_numerical_stacking = TRUE
+ STR.click_gather = TRUE
+
+// -----------------------------
+// Trash bag
+// -----------------------------
+/obj/item/storage/bag/trash
+ name = "trash bag"
+ desc = "It's the heavy-duty black polymer kind. Time to take out the trash!"
+ icon = 'icons/obj/janitor.dmi'
+ icon_state = "trashbag"
+ item_state = "trashbag"
+ lefthand_file = 'icons/mob/inhands/equipment/custodial_lefthand.dmi'
+ righthand_file = 'icons/mob/inhands/equipment/custodial_righthand.dmi'
+
+ w_class = WEIGHT_CLASS_BULKY
+ var/insertable = TRUE
+
+/obj/item/storage/bag/trash/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_w_class = WEIGHT_CLASS_SMALL
+ STR.max_combined_w_class = 30
+ STR.max_items = 30
+ STR.cant_hold = typecacheof(list(/obj/item/disk/nuclear))
+
+/obj/item/storage/bag/trash/suicide_act(mob/user)
+ user.visible_message("[user] puts [src] over [user.p_their()] head and starts chomping at the insides! Disgusting!")
+ playsound(loc, 'sound/items/eatfood.ogg', 50, 1, -1)
+ return (TOXLOSS)
+
+/obj/item/storage/bag/trash/update_icon()
+ if(contents.len == 0)
+ icon_state = "[initial(icon_state)]"
+ else if(contents.len < 12)
+ icon_state = "[initial(icon_state)]1"
+ else if(contents.len < 21)
+ icon_state = "[initial(icon_state)]2"
+ else icon_state = "[initial(icon_state)]3"
+
+/obj/item/storage/bag/trash/cyborg
+ insertable = FALSE
+
+/obj/item/storage/bag/trash/proc/janicart_insert(mob/user, obj/structure/janitorialcart/J)
+ if(insertable)
+ J.put_in_cart(src, user)
+ J.mybag=src
+ J.update_icon()
+ else
+ to_chat(user, "You are unable to fit your [name] into the [J.name].")
+ return
+
+/obj/item/storage/bag/trash/bluespace
+ name = "trash bag of holding"
+ desc = "The latest and greatest in custodial convenience, a trashbag that is capable of holding vast quantities of garbage."
+ icon_state = "bluetrashbag"
+ item_flags = NO_MAT_REDEMPTION
+
+/obj/item/storage/bag/trash/bluespace/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_combined_w_class = 60
+ STR.max_items = 60
+
+/obj/item/storage/bag/trash/bluespace/cyborg
+ insertable = FALSE
+
+// -----------------------------
+// Mining Satchel
+// -----------------------------
+
+/obj/item/storage/bag/ore
+ name = "mining satchel"
+ desc = "This little bugger can be used to store and transport ores."
+ icon = 'icons/obj/mining.dmi'
+ icon_state = "satchel"
+ slot_flags = ITEM_SLOT_BELT | ITEM_SLOT_POCKET
+ w_class = WEIGHT_CLASS_NORMAL
+ component_type = /datum/component/storage/concrete/stack
+ var/spam_protection = FALSE //If this is TRUE, the holder won't receive any messages when they fail to pick up ore through crossing it
+ var/mob/listeningTo
+ rad_flags = RAD_PROTECT_CONTENTS | RAD_NO_CONTAMINATE
+
+/obj/item/storage/bag/ore/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.allow_quick_empty = TRUE
+ STR.can_hold = typecacheof(list(/obj/item/stack/ore))
+ STR.max_w_class = WEIGHT_CLASS_HUGE
+ STR.max_combined_stack_amount = 50
+
+/obj/item/storage/bag/ore/equipped(mob/user)
+ . = ..()
+ if(listeningTo == user)
+ return
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/Pickup_ores)
+ listeningTo = user
+
+/obj/item/storage/bag/ore/dropped()
+ . = ..()
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
+
+/obj/item/storage/bag/ore/proc/Pickup_ores(mob/living/user)
+ var/show_message = FALSE
+ var/obj/structure/ore_box/box
+ var/turf/tile = user.loc
+ if (!isturf(tile))
+ return
+ if (istype(user.pulling, /obj/structure/ore_box))
+ box = user.pulling
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ if(STR)
+ for(var/A in tile)
+ if (!is_type_in_typecache(A, STR.can_hold))
+ continue
+ if (box)
+ user.transferItemToLoc(A, box)
+ show_message = TRUE
+ else if(SEND_SIGNAL(src, COMSIG_TRY_STORAGE_INSERT, A, user, TRUE))
+ show_message = TRUE
+ else
+ if(!spam_protection)
+ to_chat(user, "Your [name] is full and can't hold any more!")
+ spam_protection = TRUE
+ continue
+ if(show_message)
+ playsound(user, "rustle", 50, TRUE)
+ if (box)
+ user.visible_message("[user] offloads the ores beneath [user.p_them()] into [box].", \
+ "You offload the ores beneath you into your [box].")
+ else
+ user.visible_message("[user] scoops up the ores beneath [user.p_them()].", \
+ "You scoop up the ores beneath you with your [name].")
+ spam_protection = FALSE
+
+/obj/item/storage/bag/ore/cyborg
+ name = "cyborg mining satchel"
+
+/obj/item/storage/bag/ore/cyborg/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.allow_quick_empty = TRUE
+ STR.can_hold = typecacheof(list(/obj/item/stack/ore))
+ STR.max_w_class = WEIGHT_CLASS_HUGE
+ STR.max_combined_stack_amount = 150
+
+/obj/item/storage/bag/ore/large
+ name = "large mining satchel"
+ desc = "This bag can hold three times the ore in many small pockets. Shockingly foldable and compact for its volume."
+
+/obj/item/storage/bag/ore/large/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.allow_quick_empty = TRUE
+ STR.can_hold = typecacheof(list(/obj/item/stack/ore))
+ STR.max_w_class = WEIGHT_CLASS_HUGE
+ STR.max_combined_stack_amount = 150
+
+/obj/item/storage/bag/ore/holding //miners, your messiah has arrived
+ name = "mining satchel of holding"
+ desc = "A revolution in convenience, this satchel allows for huge amounts of ore storage. It's been outfitted with anti-malfunction safety measures."
+ icon_state = "satchel_bspace"
+
+/obj/item/storage/bag/ore/holding/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.max_items = INFINITY
+ STR.max_combined_w_class = INFINITY
+ STR.max_combined_stack_amount = INFINITY
+
+// -----------------------------
+// Plant bag
+// -----------------------------
+
+/obj/item/storage/bag/plants
+ name = "plant bag"
+ icon = 'icons/obj/hydroponics/equipment.dmi'
+ icon_state = "plantbag"
+ w_class = WEIGHT_CLASS_TINY
+ resistance_flags = FLAMMABLE
+
+/obj/item/storage/bag/plants/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_w_class = WEIGHT_CLASS_NORMAL
+ STR.max_combined_w_class = 100
+ STR.max_items = 100
+ STR.can_hold = typecacheof(list(/obj/item/reagent_containers/food/snacks/grown, /obj/item/seeds, /obj/item/grown, /obj/item/reagent_containers/honeycomb))
+
+////////
+
+/obj/item/storage/bag/plants/portaseeder
+ name = "portable seed extractor"
+ desc = "For the enterprising botanist on the go. Less efficient than the stationary model, it creates one seed per plant."
+ icon_state = "portaseeder"
+
+/obj/item/storage/bag/plants/portaseeder/verb/dissolve_contents()
+ set name = "Activate Seed Extraction"
+ set category = "Object"
+ set desc = "Activate to convert your plants into plantable seeds."
+ if(usr.stat || !usr.canmove || usr.restrained())
+ return
+ for(var/obj/item/O in contents)
+ seedify(O, 1)
+
+// -----------------------------
+// Sheet Snatcher
+// -----------------------------
+// Because it stacks stacks, this doesn't operate normally.
+// However, making it a storage/bag allows us to reuse existing code in some places. -Sayu
+
+/obj/item/storage/bag/sheetsnatcher
+ name = "sheet snatcher"
+ desc = "A patented Kinaris storage system designed for any kind of mineral sheet."
+ icon = 'icons/obj/mining.dmi'
+ icon_state = "sheetsnatcher"
+
+ var/capacity = 300; //the number of sheets it can carry.
+ w_class = WEIGHT_CLASS_NORMAL
+ component_type = /datum/component/storage/concrete/stack
+
+/obj/item/storage/bag/sheetsnatcher/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.allow_quick_empty = TRUE
+ STR.can_hold = typecacheof(list(/obj/item/stack/sheet))
+ STR.cant_hold = typecacheof(list(/obj/item/stack/sheet/mineral/sandstone, /obj/item/stack/sheet/mineral/wood))
+ STR.max_combined_stack_amount = 300
+
+// -----------------------------
+// Sheet Snatcher (Cyborg)
+// -----------------------------
+
+/obj/item/storage/bag/sheetsnatcher/borg
+ name = "sheet snatcher 9000"
+ desc = ""
+ capacity = 500//Borgs get more because >specialization
+
+/obj/item/storage/bag/sheetsnatcher/borg/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/concrete/stack/STR = GetComponent(/datum/component/storage/concrete/stack)
+ STR.max_combined_stack_amount = 500
+
+// -----------------------------
+// Book bag
+// -----------------------------
+
+/obj/item/storage/bag/books
+ name = "book bag"
+ desc = "A bag for books."
+ icon = 'icons/obj/library.dmi'
+ icon_state = "bookbag"
+ w_class = WEIGHT_CLASS_BULKY //Bigger than a book because physics
+ resistance_flags = FLAMMABLE
+
+/obj/item/storage/bag/books/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_w_class = WEIGHT_CLASS_NORMAL
+ STR.max_combined_w_class = 21
+ STR.max_items = 7
+ STR.display_numerical_stacking = FALSE
+ STR.can_hold = typecacheof(list(/obj/item/book, /obj/item/storage/book, /obj/item/spellbook))
+
+/*
+ * Trays - Agouri
+ */
+/obj/item/storage/bag/tray
+ name = "serving tray"
+ icon = 'icons/obj/food/containers.dmi'
+ icon_state = "tray"
+ desc = "A metal tray to lay food on."
+ force = 5
+ throwforce = 10
+ throw_speed = 3
+ throw_range = 5
+ w_class = WEIGHT_CLASS_BULKY
+ flags_1 = CONDUCT_1
+ materials = list(MAT_METAL=3000)
+
+/obj/item/storage/bag/tray/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_w_class = WEIGHT_CLASS_NORMAL //Allows stuff such as Bowls, and normal sized foods, to fit.
+ STR.can_hold = typecacheof(list(
+ /obj/item/reagent_containers/food,
+ /obj/item/reagent_containers/glass,
+ /obj/item/clothing/mask/cigarette,
+ /obj/item/storage/fancy,
+ /obj/item/storage/box/matches,
+ /obj/item/trash,
+ /obj/item/lighter,
+ /obj/item/rollingpaper,
+ /obj/item/kitchen,
+ /obj/item/organ,
+ )) //Should cover: Bottles, Beakers, Bowls, Booze, Glasses, Food, Food Containers, Food Trash, Organs, Tobacco Products, Lighters, and Kitchen Tools.
+ STR.insert_preposition = "on"
+ STR.max_items = 10
+
+/obj/item/storage/bag/tray/attack(mob/living/M, mob/living/user)
+ . = ..()
+ // Drop all the things. All of them.
+ var/list/obj/item/oldContents = contents.Copy()
+ SEND_SIGNAL(src, COMSIG_TRY_STORAGE_QUICK_EMPTY)
+ // Make each item scatter a bit
+ for(var/obj/item/I in oldContents)
+ INVOKE_ASYNC(src, .proc/do_scatter, I)
+
+ if(prob(50))
+ playsound(M, 'sound/items/trayhit1.ogg', 50, TRUE)
+ else
+ playsound(M, 'sound/items/trayhit2.ogg', 50, TRUE)
+
+ if(ishuman(M))
+ if(prob(10))
+ M.Knockdown(40)
+ update_icon()
+
+/obj/item/storage/bag/tray/proc/do_scatter(obj/item/I)
+ for(var/i in 1 to rand(1,2))
+ if(I)
+ step(I, pick(NORTH,SOUTH,EAST,WEST))
+ sleep(rand(2,4))
+
+/obj/item/storage/bag/tray/update_overlays()
+ . = ..()
+ for(var/obj/item/I in contents)
+ var/mutable_appearance/I_copy = new(I)
+ I_copy.plane = FLOAT_PLANE
+ I_copy.layer = FLOAT_LAYER
+ . += I_copy
+
+/obj/item/storage/bag/tray/Entered()
+ . = ..()
+ update_icon()
+
+/obj/item/storage/bag/tray/Exited()
+ . = ..()
+ update_icon()
+
+/*
+ * Chemistry bag
+ */
+
+/obj/item/storage/bag/chemistry
+ name = "chemistry bag"
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bag"
+ desc = "A bag for storing pills, patches, and bottles."
+ w_class = WEIGHT_CLASS_TINY
+ resistance_flags = FLAMMABLE
+
+/obj/item/storage/bag/chemistry/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_combined_w_class = 200
+ STR.max_items = 50
+ STR.insert_preposition = "in"
+ STR.can_hold = typecacheof(list(/obj/item/reagent_containers/pill, /obj/item/reagent_containers/glass/beaker, /obj/item/reagent_containers/glass/bottle, /obj/item/reagent_containers/syringe/dart, /obj/item/reagent_containers/chem_pack))
+
+/*
+ * Biowaste bag (mostly for xenobiologists)
+ */
+
+/obj/item/storage/bag/bio
+ name = "bio bag"
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "biobag"
+ desc = "A bag for the safe transportation and disposal of biowaste and other biological materials."
+ w_class = WEIGHT_CLASS_TINY
+ resistance_flags = FLAMMABLE
+
+/obj/item/storage/bag/bio/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_combined_w_class = 200
+ STR.max_items = 25
+ STR.insert_preposition = "in"
+ STR.can_hold = typecacheof(list(/obj/item/slime_extract, /obj/item/reagent_containers/syringe, /obj/item/reagent_containers/glass/beaker, /obj/item/reagent_containers/glass/bottle, /obj/item/reagent_containers/blood, /obj/item/reagent_containers/hypospray/medipen, /obj/item/reagent_containers/food/snacks/deadmouse, /obj/item/reagent_containers/food/snacks/monkeycube))
+
+/obj/item/storage/bag/bio/holding
+ name = "bio bag of holding"
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bspace_biobag"
+ desc = "A bag for the safe transportation and disposal of biowaste and other biological materials."
+
+/obj/item/storage/bag/bio/holding/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_combined_w_class = INFINITY
+ STR.max_items = 100
+
+/*
+ * Construction bag (for engineering, holds stock parts and electronics)
+ */
+
+/obj/item/storage/bag/construction
+ name = "construction bag"
+ icon = 'icons/obj/tools.dmi'
+ icon_state = "construction_bag"
+ desc = "A bag for storing small construction components."
+ w_class = WEIGHT_CLASS_TINY
+ resistance_flags = FLAMMABLE
+
+/obj/item/storage/bag/construction/ComponentInitialize()
+ . = ..()
+ var/datum/component/storage/STR = GetComponent(/datum/component/storage)
+ STR.max_combined_w_class = 100
+ STR.max_items = 50
+ STR.max_w_class = WEIGHT_CLASS_SMALL
+ STR.insert_preposition = "in"
+ STR.can_hold = typecacheof(list(/obj/item/stack/ore/bluespace_crystal, /obj/item/assembly, /obj/item/stock_parts, /obj/item/reagent_containers/glass/beaker, /obj/item/stack/cable_coil, /obj/item/circuitboard, /obj/item/electronics))
diff --git a/code/game/objects/items/twohanded.dm b/code/game/objects/items/twohanded.dm
index 0b6bc6af..bbfa5c29 100644
--- a/code/game/objects/items/twohanded.dm
+++ b/code/game/objects/items/twohanded.dm
@@ -849,18 +849,20 @@
righthand_file = 'icons/mob/inhands/items_righthand.dmi'
slot_flags = ITEM_SLOT_BELT
w_class = WEIGHT_CLASS_SMALL
- var/datum/component/mobhook
+ var/mob/listeningTo
var/zoom_out_amt = 6
var/zoom_amt = 10
+/obj/item/twohanded/binoculars/Destroy()
+ listeningTo = null
+ return ..()
+
/obj/item/twohanded/binoculars/wield(mob/user)
. = ..()
if(!wielded)
return
- if(QDELETED(mobhook))
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/unwield)))
- else
- user.TakeComponent(mobhook)
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/unwield)
+ listeningTo = user
user.visible_message("[user] holds [src] up to [user.p_their()] eyes.","You hold [src] up to your eyes.")
item_state = "binoculars_wielded"
user.regenerate_icons()
@@ -884,7 +886,8 @@
/obj/item/twohanded/binoculars/unwield(mob/user)
. = ..()
- mobhook.RemoveComponent()
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
user.visible_message("[user] lowers [src].","You lower [src].")
item_state = "binoculars"
user.regenerate_icons()
diff --git a/code/game/objects/structures/false_walls.dm b/code/game/objects/structures/false_walls.dm
index b194548f..e359325d 100644
--- a/code/game/objects/structures/false_walls.dm
+++ b/code/game/objects/structures/false_walls.dm
@@ -271,7 +271,7 @@
icon_state = "sandstone"
mineral = /obj/item/stack/sheet/mineral/sandstone
walltype = /turf/closed/wall/mineral/sandstone
- canSmoothWith = list(/obj/structure/falsewall/sandstone, /turf/closed/wall/mineral/sandstone)
+ canSmoothWith = list(/obj/structure/falsewall/sandstone, /turf/closed/wall/mineral/sandstone, /obj/structure/window/fulltile)
/obj/structure/falsewall/wood
name = "wooden wall"
diff --git a/code/game/objects/structures/statues.dm b/code/game/objects/structures/statues.dm
index dd28168c..8c4c9b7a 100644
--- a/code/game/objects/structures/statues.dm
+++ b/code/game/objects/structures/statues.dm
@@ -271,6 +271,14 @@
icon = 'icons/obj/statuelarge.dmi'
icon_state = "venus"
+/obj/structure/statue/sandstone/abs
+ max_integrity = 300
+ anchored = TRUE
+ name = "ancient statue"
+ desc = "An ancient statue, representing one of the gods. It almost seems like it's alive."
+ icon = 'icons/obj/statue_egypty.dmi'
+ icon_state = "abs"
+
/////////////////////snow/////////////////////////////////////////
/obj/structure/statue/snow
diff --git a/code/game/objects/structures/window.dm b/code/game/objects/structures/window.dm
index 4b6b0689..ca698d44 100644
--- a/code/game/objects/structures/window.dm
+++ b/code/game/objects/structures/window.dm
@@ -516,7 +516,9 @@
/obj/machinery/door/airlock/hatch,
/obj/machinery/door/airlock/engineering/glass/critical,
/obj/machinery/door/airlock/atmos,
- /obj/machinery/door/airlock/highsecurity,)
+ /obj/machinery/door/airlock/highsecurity,
+ /turf/closed/wall/mineral/sandstone,
+ /obj/structure/falsewall/sandstone,)
// canSmoothWith = list(/obj/structure/window/fulltile, /obj/structure/window/reinforced/fulltile, /obj/structure/window/reinforced/tinted/fulltile, /obj/structure/window/plasma/fulltile, /obj/structure/window/plasma/reinforced/fulltile)
glass_amount = 2
diff --git a/code/game/turfs/simulated/floor/misc_floor.dm b/code/game/turfs/simulated/floor/misc_floor.dm
index f75772a2..11850f81 100644
--- a/code/game/turfs/simulated/floor/misc_floor.dm
+++ b/code/game/turfs/simulated/floor/misc_floor.dm
@@ -260,3 +260,29 @@
icon = 'icons/obj/clockwork_objects.dmi'
icon_state = "clockwork_floor"
floor_tile = /obj/item/stack/tile/bronze
+
+/turf/open/floor/concrete/
+ name = "concrete"
+ icon = 'icons/turf/floors.dmi'
+ icon_state = "concrete"
+ baseturfs = /turf/open/floor/plating/asteroid
+
+/turf/open/floor/concrete/smooth
+ icon_state = "concrete2"
+
+/turf/open/floor/cobble/side
+ icon_state = "cobble_side"
+
+/turf/open/floor/cobble/corner
+ icon_state = "cobble_corner"
+
+/turf/open/floor/cobble
+ name = "cobblestone path"
+ desc = "A simple but beautiful path made of various sized stones."
+ icon = 'icons/turf/floors.dmi'
+ icon_state = "cobble"
+ baseturfs = /turf/open/floor/plating/asteroid
+ footstep = FOOTSTEP_FLOOR
+ barefootstep = FOOTSTEP_HARD_BAREFOOT
+ clawfootstep = FOOTSTEP_HARD_CLAW
+ heavyfootstep = FOOTSTEP_GENERIC_HEAVY
\ No newline at end of file
diff --git a/code/game/turfs/simulated/wall/mineral_walls.dm b/code/game/turfs/simulated/wall/mineral_walls.dm
index b37b5ec6..1e994b01 100644
--- a/code/game/turfs/simulated/wall/mineral_walls.dm
+++ b/code/game/turfs/simulated/wall/mineral_walls.dm
@@ -49,7 +49,7 @@
icon_state = "sandstone"
sheet_type = /obj/item/stack/sheet/mineral/sandstone
explosion_block = 0
- canSmoothWith = list(/turf/closed/wall/mineral/sandstone, /obj/structure/falsewall/sandstone)
+ canSmoothWith = list(/turf/closed/wall/mineral/sandstone, /obj/structure/falsewall/sandstone, /obj/structure/window/fulltile)
/turf/closed/wall/mineral/uranium
article = "a"
diff --git a/code/modules/admin/IsBanned.dm b/code/modules/admin/IsBanned.dm
index 13ee6a08..17b7668e 100644
--- a/code/modules/admin/IsBanned.dm
+++ b/code/modules/admin/IsBanned.dm
@@ -107,7 +107,7 @@
if(text2num(duration) > 0)
expires = " The ban is for [duration] minutes and expires on [expiration] (server time)."
else
- expires = " The is a permanent ban."
+ expires = " This is a permanent ban."
var/desc = "\nReason: You, or another user of this computer or connection ([pkey]) is banned from playing here. The ban reason is:\n[reason]\nThis ban (BanID #[banid]) was applied by [akey] on [bantime] during round ID [ban_round_id], [expires]"
diff --git a/code/modules/antagonists/_common/antag_spawner.dm b/code/modules/antagonists/_common/antag_spawner.dm
index 3f1c437f..40fbeb1f 100644
--- a/code/modules/antagonists/_common/antag_spawner.dm
+++ b/code/modules/antagonists/_common/antag_spawner.dm
@@ -110,7 +110,7 @@
if(!user.mind.has_antag_datum(/datum/antagonist/nukeop,TRUE))
to_chat(user, "AUTHENTICATION FAILURE. ACCESS DENIED.")
return FALSE
- if(!user.onSyndieBase())
+ if(!user.onSyndieBase() && !user.mind.has_antag_datum(/datum/antagonist/nukeop/lone,TRUE))
to_chat(user, "[src] is out of range! It can only be used at your base!")
return FALSE
return TRUE
diff --git a/code/modules/antagonists/disease/disease_mob.dm b/code/modules/antagonists/disease/disease_mob.dm
index 9c1f8720..a9992d05 100644
--- a/code/modules/antagonists/disease/disease_mob.dm
+++ b/code/modules/antagonists/disease/disease_mob.dm
@@ -31,7 +31,6 @@ the new instance inside the host to be updated to the template's stats.
var/browser_open = FALSE
var/mob/living/following_host
- var/datum/component/redirect/move_listener
var/list/disease_instances
var/list/hosts //this list is associative, affected_mob -> disease_instance
var/datum/disease/advance/sentient_disease/disease_template
@@ -260,16 +259,10 @@ the new instance inside the host to be updated to the template's stats.
refresh_adaptation_menu()
/mob/camera/disease/proc/set_following(mob/living/L)
+ if(following_host)
+ UnregisterSignal(following_host, COMSIG_MOVABLE_MOVED)
+ RegisterSignal(L, COMSIG_MOVABLE_MOVED, .proc/follow_mob)
following_host = L
- if(!move_listener)
- move_listener = L.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/follow_mob)))
- else
- if(L)
- L.TakeComponent(move_listener)
- if(QDELING(move_listener))
- move_listener = null
- else
- QDEL_NULL(move_listener)
follow_mob()
/mob/camera/disease/proc/follow_next(reverse = FALSE)
diff --git a/code/modules/antagonists/revenant/revenant_blight.dm b/code/modules/antagonists/revenant/revenant_blight.dm
index 89d8de28..3e05b8d9 100644
--- a/code/modules/antagonists/revenant/revenant_blight.dm
+++ b/code/modules/antagonists/revenant/revenant_blight.dm
@@ -12,8 +12,8 @@
disease_flags = CURABLE
permeability_mod = 1
severity = DISEASE_SEVERITY_DANGEROUS
- var/finalstage = 0 //Because we're spawning off the cure in the final stage, we need to check if we've done the final stage's effects.
- var/datum/mood_event/revenant_blight/depression
+ var/finalstage = FALSE //Because we're spawning off the cure in the final stage, we need to check if we've done the final stage's effects.
+ var/depression = FALSE
/datum/disease/revblight/cure()
if(affected_mob)
@@ -44,7 +44,8 @@
affected_mob.emote("pale")
if(3)
if(!depression)
- depression = SEND_SIGNAL(affected_mob, COMSIG_ADD_MOOD_EVENT, "rev_blight", /datum/mood_event/revenant_blight)
+ SEND_SIGNAL(affected_mob, COMSIG_ADD_MOOD_EVENT, "rev_blight", /datum/mood_event/revenant_blight)
+ depression = TRUE
SEND_SIGNAL(affected_mob, COMSIG_DECREASE_SANITY, 0.12, SANITY_CRAZY)
if(prob(10))
affected_mob.emote(pick("pale","shiver"))
diff --git a/code/modules/assembly/infrared.dm b/code/modules/assembly/infrared.dm
index a023e0e3..2fbb1095 100644
--- a/code/modules/assembly/infrared.dm
+++ b/code/modules/assembly/infrared.dm
@@ -1,235 +1,239 @@
-/obj/item/assembly/infra
- name = "infrared emitter"
- desc = "Emits a visible or invisible beam and is triggered when the beam is interrupted."
- icon_state = "infrared"
- materials = list(MAT_METAL=1000, MAT_GLASS=500)
- is_position_sensitive = TRUE
-
- var/on = FALSE
- var/visible = FALSE
- var/maxlength = 8
- var/list/obj/effect/beam/i_beam/beams
- var/olddir = 0
- var/datum/component/redirect/listener
- var/hearing_range = 3
-
-/obj/item/assembly/infra/Initialize()
- . = ..()
- beams = list()
- START_PROCESSING(SSobj, src)
-
-/obj/item/assembly/infra/ComponentInitialize()
- . = ..()
- AddComponent(
- /datum/component/simple_rotation,
- ROTATION_ALTCLICK | ROTATION_CLOCKWISE | ROTATION_COUNTERCLOCKWISE | ROTATION_FLIP | ROTATION_VERBS,
- null,
- null,
- CALLBACK(src,.proc/after_rotation)
- )
-
-/obj/item/assembly/infra/proc/after_rotation()
- refreshBeam()
-
-/obj/item/assembly/infra/Destroy()
- STOP_PROCESSING(SSobj, src)
- QDEL_NULL(listener)
- QDEL_LIST(beams)
- . = ..()
-
-/obj/item/assembly/infra/examine(mob/user)
- . = ..()
- . += "The infrared trigger is [on?"on":"off"]."
-
-/obj/item/assembly/infra/activate()
- if(!..())
- return FALSE//Cooldown check
- on = !on
- refreshBeam()
- update_icon()
- return TRUE
-
-/obj/item/assembly/infra/toggle_secure()
- secured = !secured
- if(secured)
- START_PROCESSING(SSobj, src)
- refreshBeam()
- else
- QDEL_LIST(beams)
- STOP_PROCESSING(SSobj, src)
- update_icon()
- return secured
-
-/obj/item/assembly/infra/update_icon()
- cut_overlays()
- attached_overlays = list()
- if(on)
- add_overlay("infrared_on")
- attached_overlays += "infrared_on"
- if(visible && secured)
- add_overlay("infrared_visible")
- attached_overlays += "infrared_visible"
-
- if(holder)
- holder.update_icon()
- return
-
-/obj/item/assembly/infra/dropped()
- . = ..()
- if(holder)
- holder_movement() //sync the dir of the device as well if it's contained in a TTV or an assembly holder
- else
- refreshBeam()
-
-/obj/item/assembly/infra/process()
- if(!on || !secured)
- refreshBeam()
- return
-
-/obj/item/assembly/infra/proc/refreshBeam()
- QDEL_LIST(beams)
- if(throwing || !on || !secured)
- return
- if(holder)
- if(holder.master) //incase the sensor is part of an assembly that's contained in another item, such as a single tank bomb
- if(!holder.master.IsSpecialAssembly() || !isturf(holder.master.loc))
- return
- else if(!isturf(holder.loc)) //else just check where the holder is
- return
- else if(!isturf(loc)) //or just where the fuck we are in general
- return
- var/turf/T = get_turf(src)
- var/_dir = dir
- var/turf/_T = get_step(T, _dir)
- if(_T)
- for(var/i in 1 to maxlength)
- var/obj/effect/beam/i_beam/I = new(T)
- if(istype(holder, /obj/item/assembly_holder))
- var/obj/item/assembly_holder/assembly_holder = holder
- I.icon_state = "[initial(I.icon_state)]_[(assembly_holder.a_left == src) ? "l":"r"]" //Sync the offset of the beam with the position of the sensor.
- else if(istype(holder, /obj/item/transfer_valve))
- I.icon_state = "[initial(I.icon_state)]_ttv"
- I.density = TRUE
- if(!I.Move(_T))
- qdel(I)
- switchListener(_T)
- break
- I.density = FALSE
- beams += I
- I.master = src
- I.setDir(_dir)
- I.invisibility = visible? 0 : INVISIBILITY_ABSTRACT
- T = _T
- _T = get_step(_T, _dir)
- CHECK_TICK
-
-/obj/item/assembly/infra/on_detach()
- . = ..()
- if(!.)
- return
- refreshBeam()
-
-/obj/item/assembly/infra/attack_hand()
- . = ..()
- refreshBeam()
-
-/obj/item/assembly/infra/Moved()
- var/t = dir
- . = ..()
- setDir(t)
-
-/obj/item/assembly/infra/throw_at()
- . = ..()
- olddir = dir
-
-/obj/item/assembly/infra/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum)
- . = ..()
- if(!olddir)
- return
- setDir(olddir)
- olddir = null
-
-/obj/item/assembly/infra/proc/trigger_beam(atom/movable/AM, turf/location)
- refreshBeam()
- switchListener(location)
- if(!secured || !on || next_activate > world.time)
- return FALSE
- pulse(FALSE)
- audible_message("[icon2html(src, hearers(src))] *beep* *beep* *beep*", null, hearing_range)
- for(var/CHM in get_hearers_in_view(hearing_range, src))
- if(ismob(CHM))
- var/mob/LM = CHM
- LM.playsound_local(get_turf(src), 'sound/machines/triple_beep.ogg', ASSEMBLY_BEEP_VOLUME, TRUE)
- next_activate = world.time + 30
-
-/obj/item/assembly/infra/proc/switchListener(turf/newloc)
- QDEL_NULL(listener)
- listener = newloc.AddComponent(/datum/component/redirect, list(COMSIG_ATOM_EXITED = CALLBACK(src, .proc/check_exit)))
-
-/obj/item/assembly/infra/proc/check_exit(datum/source, atom/movable/offender)
- if(QDELETED(src))
- return
- if(offender == src || istype(offender,/obj/effect/beam/i_beam))
- return
- if (offender && isitem(offender))
- var/obj/item/I = offender
- if (I.item_flags & ABSTRACT)
- return
- return refreshBeam()
-
-/obj/item/assembly/infra/ui_interact(mob/user)//TODO: change this this to the wire control panel
- . = ..()
- if(is_secured(user))
- user.set_machine(src)
- var/dat = "Infrared Laser"
- dat += "
Status: [on ? "On" : "Off"]"
- dat += "
Visibility: [visible ? "Visible" : "Invisible"]"
- dat += "
Refresh"
- dat += "
Close"
- user << browse(dat, "window=infra")
- onclose(user, "infra")
- return
-
-/obj/item/assembly/infra/Topic(href, href_list)
- ..()
- if(usr.incapacitated() || !in_range(loc, usr))
- usr << browse(null, "window=infra")
- onclose(usr, "infra")
- return
- if(href_list["state"])
- on = !(on)
- update_icon()
- refreshBeam()
- if(href_list["visible"])
- visible = !(visible)
- update_icon()
- refreshBeam()
- if(href_list["close"])
- usr << browse(null, "window=infra")
- return
- if(usr)
- attack_self(usr)
-
-/obj/item/assembly/infra/setDir()
- . = ..()
- refreshBeam()
-
-/***************************IBeam*********************************/
-
-/obj/effect/beam/i_beam
- name = "infrared beam"
- icon = 'icons/obj/projectiles.dmi'
- icon_state = "ibeam"
- var/obj/item/assembly/infra/master
- anchored = TRUE
- density = FALSE
- pass_flags = PASSTABLE|PASSGLASS|PASSGRILLE|LETPASSTHROW
-
-/obj/effect/beam/i_beam/Crossed(atom/movable/AM as mob|obj)
- if(istype(AM, /obj/effect/beam))
- return
- if (isitem(AM))
- var/obj/item/I = AM
- if (I.item_flags & ABSTRACT)
- return
- master.trigger_beam(AM, get_turf(src))
+/obj/item/assembly/infra
+ name = "infrared emitter"
+ desc = "Emits a visible or invisible beam and is triggered when the beam is interrupted."
+ icon_state = "infrared"
+ materials = list(MAT_METAL=1000, MAT_GLASS=500)
+ is_position_sensitive = TRUE
+
+ var/on = FALSE
+ var/visible = FALSE
+ var/maxlength = 8
+ var/list/obj/effect/beam/i_beam/beams
+ var/olddir = 0
+ var/turf/listeningTo
+ var/hearing_range = 3
+
+/obj/item/assembly/infra/Initialize()
+ . = ..()
+ beams = list()
+ START_PROCESSING(SSobj, src)
+
+/obj/item/assembly/infra/ComponentInitialize()
+ . = ..()
+ AddComponent(
+ /datum/component/simple_rotation,
+ ROTATION_ALTCLICK | ROTATION_CLOCKWISE | ROTATION_COUNTERCLOCKWISE | ROTATION_FLIP | ROTATION_VERBS,
+ null,
+ null,
+ CALLBACK(src,.proc/after_rotation)
+ )
+
+/obj/item/assembly/infra/proc/after_rotation()
+ refreshBeam()
+
+/obj/item/assembly/infra/Destroy()
+ STOP_PROCESSING(SSobj, src)
+ listeningTo = null
+ QDEL_LIST(beams)
+ . = ..()
+
+/obj/item/assembly/infra/examine(mob/user)
+ . = ..()
+ . += "The infrared trigger is [on?"on":"off"]."
+
+/obj/item/assembly/infra/activate()
+ if(!..())
+ return FALSE//Cooldown check
+ on = !on
+ refreshBeam()
+ update_icon()
+ return TRUE
+
+/obj/item/assembly/infra/toggle_secure()
+ secured = !secured
+ if(secured)
+ START_PROCESSING(SSobj, src)
+ refreshBeam()
+ else
+ QDEL_LIST(beams)
+ STOP_PROCESSING(SSobj, src)
+ update_icon()
+ return secured
+
+/obj/item/assembly/infra/update_icon()
+ cut_overlays()
+ attached_overlays = list()
+ if(on)
+ add_overlay("infrared_on")
+ attached_overlays += "infrared_on"
+ if(visible && secured)
+ add_overlay("infrared_visible")
+ attached_overlays += "infrared_visible"
+
+ if(holder)
+ holder.update_icon()
+ return
+
+/obj/item/assembly/infra/dropped()
+ . = ..()
+ if(holder)
+ holder_movement() //sync the dir of the device as well if it's contained in a TTV or an assembly holder
+ else
+ refreshBeam()
+
+/obj/item/assembly/infra/process()
+ if(!on || !secured)
+ refreshBeam()
+ return
+
+/obj/item/assembly/infra/proc/refreshBeam()
+ QDEL_LIST(beams)
+ if(throwing || !on || !secured)
+ return
+ if(holder)
+ if(holder.master) //incase the sensor is part of an assembly that's contained in another item, such as a single tank bomb
+ if(!holder.master.IsSpecialAssembly() || !isturf(holder.master.loc))
+ return
+ else if(!isturf(holder.loc)) //else just check where the holder is
+ return
+ else if(!isturf(loc)) //or just where the fuck we are in general
+ return
+ var/turf/T = get_turf(src)
+ var/_dir = dir
+ var/turf/_T = get_step(T, _dir)
+ if(_T)
+ for(var/i in 1 to maxlength)
+ var/obj/effect/beam/i_beam/I = new(T)
+ if(istype(holder, /obj/item/assembly_holder))
+ var/obj/item/assembly_holder/assembly_holder = holder
+ I.icon_state = "[initial(I.icon_state)]_[(assembly_holder.a_left == src) ? "l":"r"]" //Sync the offset of the beam with the position of the sensor.
+ else if(istype(holder, /obj/item/transfer_valve))
+ I.icon_state = "[initial(I.icon_state)]_ttv"
+ I.density = TRUE
+ if(!I.Move(_T))
+ qdel(I)
+ switchListener(_T)
+ break
+ I.density = FALSE
+ beams += I
+ I.master = src
+ I.setDir(_dir)
+ I.invisibility = visible? 0 : INVISIBILITY_ABSTRACT
+ T = _T
+ _T = get_step(_T, _dir)
+ CHECK_TICK
+
+/obj/item/assembly/infra/on_detach()
+ . = ..()
+ if(!.)
+ return
+ refreshBeam()
+
+/obj/item/assembly/infra/attack_hand()
+ . = ..()
+ refreshBeam()
+
+/obj/item/assembly/infra/Moved()
+ var/t = dir
+ . = ..()
+ setDir(t)
+
+/obj/item/assembly/infra/throw_at()
+ . = ..()
+ olddir = dir
+
+/obj/item/assembly/infra/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum)
+ . = ..()
+ if(!olddir)
+ return
+ setDir(olddir)
+ olddir = null
+
+/obj/item/assembly/infra/proc/trigger_beam(atom/movable/AM, turf/location)
+ refreshBeam()
+ switchListener(location)
+ if(!secured || !on || next_activate > world.time)
+ return FALSE
+ pulse(FALSE)
+ audible_message("[icon2html(src, hearers(src))] *beep* *beep* *beep*", null, hearing_range)
+ for(var/CHM in get_hearers_in_view(hearing_range, src))
+ if(ismob(CHM))
+ var/mob/LM = CHM
+ LM.playsound_local(get_turf(src), 'sound/machines/triple_beep.ogg', ASSEMBLY_BEEP_VOLUME, TRUE)
+ next_activate = world.time + 30
+
+/obj/item/assembly/infra/proc/switchListener(turf/newloc)
+ if(listeningTo == newloc)
+ return
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_ATOM_EXITED)
+ RegisterSignal(newloc, COMSIG_ATOM_EXITED, .proc/check_exit)
+ listeningTo = newloc
+
+/obj/item/assembly/infra/proc/check_exit(datum/source, atom/movable/offender)
+ if(QDELETED(src))
+ return
+ if(offender == src || istype(offender,/obj/effect/beam/i_beam))
+ return
+ if (offender && isitem(offender))
+ var/obj/item/I = offender
+ if (I.item_flags & ABSTRACT)
+ return
+ return refreshBeam()
+
+/obj/item/assembly/infra/ui_interact(mob/user)//TODO: change this this to the wire control panel
+ . = ..()
+ if(is_secured(user))
+ user.set_machine(src)
+ var/dat = "Infrared Laser"
+ dat += "
Status: [on ? "On" : "Off"]"
+ dat += "
Visibility: [visible ? "Visible" : "Invisible"]"
+ dat += "
Refresh"
+ dat += "
Close"
+ user << browse(dat, "window=infra")
+ onclose(user, "infra")
+ return
+
+/obj/item/assembly/infra/Topic(href, href_list)
+ ..()
+ if(usr.incapacitated() || !in_range(loc, usr))
+ usr << browse(null, "window=infra")
+ onclose(usr, "infra")
+ return
+ if(href_list["state"])
+ on = !(on)
+ update_icon()
+ refreshBeam()
+ if(href_list["visible"])
+ visible = !(visible)
+ update_icon()
+ refreshBeam()
+ if(href_list["close"])
+ usr << browse(null, "window=infra")
+ return
+ if(usr)
+ attack_self(usr)
+
+/obj/item/assembly/infra/setDir()
+ . = ..()
+ refreshBeam()
+
+/***************************IBeam*********************************/
+
+/obj/effect/beam/i_beam
+ name = "infrared beam"
+ icon = 'icons/obj/projectiles.dmi'
+ icon_state = "ibeam"
+ var/obj/item/assembly/infra/master
+ anchored = TRUE
+ density = FALSE
+ pass_flags = PASSTABLE|PASSGLASS|PASSGRILLE|LETPASSTHROW
+
+/obj/effect/beam/i_beam/Crossed(atom/movable/AM as mob|obj)
+ if(istype(AM, /obj/effect/beam))
+ return
+ if (isitem(AM))
+ var/obj/item/I = AM
+ if (I.item_flags & ABSTRACT)
+ return
+ master.trigger_beam(AM, get_turf(src))
diff --git a/code/modules/clothing/gloves/_gloves.dm b/code/modules/clothing/gloves/_gloves.dm
index 00cb9b1e..c7067c64 100644
--- a/code/modules/clothing/gloves/_gloves.dm
+++ b/code/modules/clothing/gloves/_gloves.dm
@@ -1,43 +1,43 @@
-/obj/item/clothing/gloves
- name = "gloves"
- gender = PLURAL //Carn: for grammarically correct text-parsing
- w_class = WEIGHT_CLASS_SMALL
- icon = 'icons/obj/clothing/gloves.dmi'
- siemens_coefficient = 0.5
- body_parts_covered = HANDS
- slot_flags = ITEM_SLOT_GLOVES
- attack_verb = list("challenged")
- var/transfer_prints = FALSE
- var/transfer_blood = 0
- strip_delay = 20
- equip_delay_other = 40
-
-/obj/item/clothing/gloves/ComponentInitialize()
- . = ..()
- AddComponent(/datum/component/redirect, list(COMSIG_COMPONENT_CLEAN_ACT = CALLBACK(src, /obj/item/clothing/gloves/clean_blood)))
-
-/obj/item/clothing/gloves/clean_blood(datum/source, strength)
- . = ..()
- transfer_blood = 0
-
-/obj/item/clothing/gloves/suicide_act(mob/living/carbon/user)
- user.visible_message("\the [src] are forcing [user]'s hands around [user.p_their()] neck! It looks like the gloves are possessed!")
- return OXYLOSS
-
-/obj/item/clothing/gloves/worn_overlays(isinhands = FALSE)
- . = list()
- if(!isinhands)
- if(damaged_clothes)
- . += mutable_appearance('icons/effects/item_damage.dmi', "damagedgloves")
- if(blood_DNA)
- . += mutable_appearance('icons/effects/blood.dmi', "bloodyhands", color = blood_DNA_to_color())
-
-/obj/item/clothing/gloves/update_clothes_damaged_state(damaging = TRUE)
- ..()
- if(ismob(loc))
- var/mob/M = loc
- M.update_inv_gloves()
-
-// Called just before an attack_hand(), in mob/UnarmedAttack()
-/obj/item/clothing/gloves/proc/Touch(atom/A, proximity)
- return FALSE // return TRUE to cancel attack_hand()
+/obj/item/clothing/gloves
+ name = "gloves"
+ gender = PLURAL //Carn: for grammarically correct text-parsing
+ w_class = WEIGHT_CLASS_SMALL
+ icon = 'icons/obj/clothing/gloves.dmi'
+ siemens_coefficient = 0.5
+ body_parts_covered = HANDS
+ slot_flags = ITEM_SLOT_GLOVES
+ attack_verb = list("challenged")
+ var/transfer_prints = FALSE
+ var/transfer_blood = 0
+ strip_delay = 20
+ equip_delay_other = 40
+
+/obj/item/clothing/gloves/ComponentInitialize()
+ . = ..()
+ RegisterSignal(src, COMSIG_COMPONENT_CLEAN_ACT, /obj/item/clothing/gloves/clean_blood)
+
+/obj/item/clothing/gloves/clean_blood(datum/source, strength)
+ . = ..()
+ transfer_blood = 0
+
+/obj/item/clothing/gloves/suicide_act(mob/living/carbon/user)
+ user.visible_message("\the [src] are forcing [user]'s hands around [user.p_their()] neck! It looks like the gloves are possessed!")
+ return OXYLOSS
+
+/obj/item/clothing/gloves/worn_overlays(isinhands = FALSE)
+ . = list()
+ if(!isinhands)
+ if(damaged_clothes)
+ . += mutable_appearance('icons/effects/item_damage.dmi', "damagedgloves")
+ if(blood_DNA)
+ . += mutable_appearance('icons/effects/blood.dmi', "bloodyhands", color = blood_DNA_to_color())
+
+/obj/item/clothing/gloves/update_clothes_damaged_state(damaging = TRUE)
+ ..()
+ if(ismob(loc))
+ var/mob/M = loc
+ M.update_inv_gloves()
+
+// Called just before an attack_hand(), in mob/UnarmedAttack()
+/obj/item/clothing/gloves/proc/Touch(atom/A, proximity)
+ return FALSE // return TRUE to cancel attack_hand()
diff --git a/code/modules/clothing/shoes/_shoes.dm b/code/modules/clothing/shoes/_shoes.dm
index b420ee67..7eaf05f2 100644
--- a/code/modules/clothing/shoes/_shoes.dm
+++ b/code/modules/clothing/shoes/_shoes.dm
@@ -1,113 +1,113 @@
-/obj/item/clothing/shoes
- name = "shoes"
- icon = 'icons/obj/clothing/shoes.dmi'
- desc = "Comfortable-looking shoes."
- gender = PLURAL //Carn: for grammarically correct text-parsing
- var/chained = 0
-
- body_parts_covered = FEET
- slot_flags = ITEM_SLOT_FEET
-
- permeability_coefficient = 0.5
- slowdown = SHOES_SLOWDOWN
- var/blood_state = BLOOD_STATE_NOT_BLOODY
- var/list/bloody_shoes = list(BLOOD_STATE_BLOOD = 0, BLOOD_STATE_OIL = 0, BLOOD_STATE_NOT_BLOODY = 0)
- var/offset = 0
- var/equipped_before_drop = FALSE
-
- //CITADEL EDIT Enables digitigrade shoe styles
- var/adjusted = NORMAL_STYLE
- mutantrace_variation = MUTANTRACE_VARIATION
- var/last_bloodtype = "" //used to track the last bloodtype to have graced these shoes; makes for better performing footprint shenanigans
- var/last_blood_DNA = "" //same as last one
-
-/obj/item/clothing/shoes/ComponentInitialize()
- . = ..()
- AddComponent(/datum/component/redirect, list(COMSIG_COMPONENT_CLEAN_ACT = CALLBACK(src, /obj/item/clothing/shoes/clean_blood)))
-
-/obj/item/clothing/shoes/suicide_act(mob/living/carbon/user)
- if(rand(2)>1)
- user.visible_message("[user] begins tying \the [src] up waaay too tightly! It looks like [user.p_theyre()] trying to commit suicide!")
- var/obj/item/bodypart/l_leg = user.get_bodypart(BODY_ZONE_L_LEG)
- var/obj/item/bodypart/r_leg = user.get_bodypart(BODY_ZONE_R_LEG)
- if(l_leg)
- l_leg.dismember()
- playsound(user,pick('sound/misc/desceration-01.ogg','sound/misc/desceration-02.ogg','sound/misc/desceration-01.ogg') ,50, 1, -1)
- if(r_leg)
- r_leg.dismember()
- playsound(user,pick('sound/misc/desceration-01.ogg','sound/misc/desceration-02.ogg','sound/misc/desceration-01.ogg') ,50, 1, -1)
- return BRUTELOSS
- else//didnt realize this suicide act existed (was in miscellaneous.dm) and didnt want to remove it, so made it a 50/50 chance. Why not!
- user.visible_message("[user] is bashing [user.p_their()] own head in with [src]! Ain't that a kick in the head?")
- for(var/i = 0, i < 3, i++)
- sleep(3)
- playsound(user, 'sound/weapons/genhit2.ogg', 50, 1)
- return(BRUTELOSS)
-
-/obj/item/clothing/shoes/transfer_blood_dna(list/blood_dna, diseases)
- ..()
- if(blood_dna.len)
- last_bloodtype = blood_dna[blood_dna[blood_dna.len]]//trust me this works
- last_blood_DNA = blood_dna[blood_dna.len]
-
-/obj/item/clothing/shoes/worn_overlays(isinhands = FALSE)
- . = list()
- if(!isinhands)
- var/bloody = FALSE
- if(blood_DNA)
- bloody = TRUE
- else
- bloody = bloody_shoes[BLOOD_STATE_BLOOD]
-
- if(damaged_clothes)
- . += mutable_appearance('icons/effects/item_damage.dmi', "damagedshoe")
- if(bloody)
- if(adjusted == NORMAL_STYLE)
- . += mutable_appearance('icons/effects/blood.dmi', "shoeblood", color = blood_DNA_to_color())
- else
- . += mutable_appearance('modular_citadel/icons/mob/digishoes.dmi', "shoeblood", color = blood_DNA_to_color())
-
-/obj/item/clothing/shoes/equipped(mob/user, slot)
- . = ..()
-
- if(mutantrace_variation && ishuman(user))
- var/mob/living/carbon/human/H = user
- if(DIGITIGRADE in H.dna.species.species_traits)
- adjusted = ALT_STYLE
- H.update_inv_shoes()
- else if(adjusted == ALT_STYLE)
- adjusted = NORMAL_STYLE
- H.update_inv_shoes()
-
- if(offset && slot_flags & slotdefine2slotbit(slot))
- user.pixel_y += offset
- worn_y_dimension -= (offset * 2)
- user.update_inv_shoes()
- equipped_before_drop = TRUE
-
-/obj/item/clothing/shoes/proc/restore_offsets(mob/user)
- equipped_before_drop = FALSE
- user.pixel_y -= offset
- worn_y_dimension = world.icon_size
-
-/obj/item/clothing/shoes/dropped(mob/user)
- if(offset && equipped_before_drop)
- restore_offsets(user)
- . = ..()
-
-/obj/item/clothing/shoes/update_clothes_damaged_state(damaging = TRUE)
- ..()
- if(ismob(loc))
- var/mob/M = loc
- M.update_inv_shoes()
-
-/obj/item/clothing/shoes/clean_blood(datum/source, strength)
- . = ..()
- bloody_shoes = list(BLOOD_STATE_BLOOD = 0, BLOOD_STATE_OIL = 0, BLOOD_STATE_NOT_BLOODY = 0)
- blood_state = BLOOD_STATE_NOT_BLOODY
- if(ismob(loc))
- var/mob/M = loc
- M.update_inv_shoes()
-
-/obj/item/proc/negates_gravity()
- return FALSE
+/obj/item/clothing/shoes
+ name = "shoes"
+ icon = 'icons/obj/clothing/shoes.dmi'
+ desc = "Comfortable-looking shoes."
+ gender = PLURAL //Carn: for grammarically correct text-parsing
+ var/chained = 0
+
+ body_parts_covered = FEET
+ slot_flags = ITEM_SLOT_FEET
+
+ permeability_coefficient = 0.5
+ slowdown = SHOES_SLOWDOWN
+ var/blood_state = BLOOD_STATE_NOT_BLOODY
+ var/list/bloody_shoes = list(BLOOD_STATE_BLOOD = 0, BLOOD_STATE_OIL = 0, BLOOD_STATE_NOT_BLOODY = 0)
+ var/offset = 0
+ var/equipped_before_drop = FALSE
+
+ //CITADEL EDIT Enables digitigrade shoe styles
+ var/adjusted = NORMAL_STYLE
+ mutantrace_variation = MUTANTRACE_VARIATION
+ var/last_bloodtype = "" //used to track the last bloodtype to have graced these shoes; makes for better performing footprint shenanigans
+ var/last_blood_DNA = "" //same as last one
+
+/obj/item/clothing/shoes/ComponentInitialize()
+ . = ..()
+ RegisterSignal(src, COMSIG_COMPONENT_CLEAN_ACT, /obj/item/clothing/shoes/clean_blood)
+
+/obj/item/clothing/shoes/suicide_act(mob/living/carbon/user)
+ if(rand(2)>1)
+ user.visible_message("[user] begins tying \the [src] up waaay too tightly! It looks like [user.p_theyre()] trying to commit suicide!")
+ var/obj/item/bodypart/l_leg = user.get_bodypart(BODY_ZONE_L_LEG)
+ var/obj/item/bodypart/r_leg = user.get_bodypart(BODY_ZONE_R_LEG)
+ if(l_leg)
+ l_leg.dismember()
+ playsound(user,pick('sound/misc/desceration-01.ogg','sound/misc/desceration-02.ogg','sound/misc/desceration-01.ogg') ,50, 1, -1)
+ if(r_leg)
+ r_leg.dismember()
+ playsound(user,pick('sound/misc/desceration-01.ogg','sound/misc/desceration-02.ogg','sound/misc/desceration-01.ogg') ,50, 1, -1)
+ return BRUTELOSS
+ else//didnt realize this suicide act existed (was in miscellaneous.dm) and didnt want to remove it, so made it a 50/50 chance. Why not!
+ user.visible_message("[user] is bashing [user.p_their()] own head in with [src]! Ain't that a kick in the head?")
+ for(var/i = 0, i < 3, i++)
+ sleep(3)
+ playsound(user, 'sound/weapons/genhit2.ogg', 50, 1)
+ return(BRUTELOSS)
+
+/obj/item/clothing/shoes/transfer_blood_dna(list/blood_dna, diseases)
+ ..()
+ if(blood_dna.len)
+ last_bloodtype = blood_dna[blood_dna[blood_dna.len]]//trust me this works
+ last_blood_DNA = blood_dna[blood_dna.len]
+
+/obj/item/clothing/shoes/worn_overlays(isinhands = FALSE)
+ . = list()
+ if(!isinhands)
+ var/bloody = FALSE
+ if(blood_DNA)
+ bloody = TRUE
+ else
+ bloody = bloody_shoes[BLOOD_STATE_BLOOD]
+
+ if(damaged_clothes)
+ . += mutable_appearance('icons/effects/item_damage.dmi', "damagedshoe")
+ if(bloody)
+ if(adjusted == NORMAL_STYLE)
+ . += mutable_appearance('icons/effects/blood.dmi', "shoeblood", color = blood_DNA_to_color())
+ else
+ . += mutable_appearance('modular_citadel/icons/mob/digishoes.dmi', "shoeblood", color = blood_DNA_to_color())
+
+/obj/item/clothing/shoes/equipped(mob/user, slot)
+ . = ..()
+
+ if(mutantrace_variation && ishuman(user))
+ var/mob/living/carbon/human/H = user
+ if(DIGITIGRADE in H.dna.species.species_traits)
+ adjusted = ALT_STYLE
+ H.update_inv_shoes()
+ else if(adjusted == ALT_STYLE)
+ adjusted = NORMAL_STYLE
+ H.update_inv_shoes()
+
+ if(offset && slot_flags & slotdefine2slotbit(slot))
+ user.pixel_y += offset
+ worn_y_dimension -= (offset * 2)
+ user.update_inv_shoes()
+ equipped_before_drop = TRUE
+
+/obj/item/clothing/shoes/proc/restore_offsets(mob/user)
+ equipped_before_drop = FALSE
+ user.pixel_y -= offset
+ worn_y_dimension = world.icon_size
+
+/obj/item/clothing/shoes/dropped(mob/user)
+ if(offset && equipped_before_drop)
+ restore_offsets(user)
+ . = ..()
+
+/obj/item/clothing/shoes/update_clothes_damaged_state(damaging = TRUE)
+ ..()
+ if(ismob(loc))
+ var/mob/M = loc
+ M.update_inv_shoes()
+
+/obj/item/clothing/shoes/clean_blood(datum/source, strength)
+ . = ..()
+ bloody_shoes = list(BLOOD_STATE_BLOOD = 0, BLOOD_STATE_OIL = 0, BLOOD_STATE_NOT_BLOODY = 0)
+ blood_state = BLOOD_STATE_NOT_BLOODY
+ if(ismob(loc))
+ var/mob/M = loc
+ M.update_inv_shoes()
+
+/obj/item/proc/negates_gravity()
+ return FALSE
diff --git a/code/modules/clothing/spacesuits/hardsuit.dm b/code/modules/clothing/spacesuits/hardsuit.dm
index 5893e970..83315a40 100644
--- a/code/modules/clothing/spacesuits/hardsuit.dm
+++ b/code/modules/clothing/spacesuits/hardsuit.dm
@@ -604,7 +604,6 @@
armor = list("melee" = 30, "bullet" = 5, "laser" = 5, "energy" = 0, "bomb" = 50, "bio" = 100, "rad" = 100, "fire" = 100, "acid" = 75)
item_color = "ancient"
resistance_flags = FIRE_PROOF
- var/datum/component/mobhook
/obj/item/clothing/suit/space/hardsuit/ancient
name = "prototype RIG hardsuit"
@@ -616,7 +615,7 @@
helmettype = /obj/item/clothing/head/helmet/space/hardsuit/ancient
resistance_flags = FIRE_PROOF
var/footstep = 1
- var/datum/component/mobhook
+ var/mob/listeningTo
/obj/item/clothing/suit/space/hardsuit/ancient/mason
name = "M.A.S.O.N RIG"
@@ -673,20 +672,24 @@
/obj/item/clothing/suit/space/hardsuit/ancient/equipped(mob/user, slot)
. = ..()
- if (slot == SLOT_WEAR_SUIT)
- if (mobhook && mobhook.parent != user)
- QDEL_NULL(mobhook)
- if (!mobhook)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_mob_move)))
- else
- QDEL_NULL(mobhook)
+ if(slot != SLOT_WEAR_SUIT)
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ return
+ if(listeningTo == user)
+ return
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/on_mob_move)
+ listeningTo = user
/obj/item/clothing/suit/space/hardsuit/ancient/dropped()
. = ..()
- QDEL_NULL(mobhook)
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
/obj/item/clothing/suit/space/hardsuit/ancient/Destroy()
- QDEL_NULL(mobhook) // mobhook is not our component
+ listeningTo = null
return ..()
/////////////SHIELDED//////////////////////////////////
diff --git a/code/modules/fields/fields.dm b/code/modules/fields/fields.dm
index 5e34c934..5b0b4bc1 100644
--- a/code/modules/fields/fields.dm
+++ b/code/modules/fields/fields.dm
@@ -283,7 +283,7 @@
var/field_type = /datum/proximity_monitor/advanced/debug
var/operating = FALSE
var/datum/proximity_monitor/advanced/current = null
- var/datum/component/mobhook
+ var/mob/listeningTo
/obj/item/multitool/field_debug/Initialize()
. = ..()
@@ -292,7 +292,7 @@
/obj/item/multitool/field_debug/Destroy()
STOP_PROCESSING(SSobj, src)
QDEL_NULL(current)
- QDEL_NULL(mobhook)
+ listeningTo = null
return ..()
/obj/item/multitool/field_debug/proc/setup_debug_field()
@@ -303,16 +303,20 @@
/obj/item/multitool/field_debug/attack_self(mob/user)
operating = !operating
to_chat(user, "You turn [src] [operating? "on":"off"].")
- QDEL_NULL(mobhook)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
if(!istype(current) && operating)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_mob_move)))
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/on_mob_move)
+ listeningTo = user
setup_debug_field()
else if(!operating)
QDEL_NULL(current)
/obj/item/multitool/field_debug/dropped()
. = ..()
- QDEL_NULL(mobhook)
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
/obj/item/multitool/field_debug/proc/on_mob_move()
check_turf(get_turf(src))
diff --git a/code/modules/flufftext/Hallucination.dm b/code/modules/flufftext/Hallucination.dm
index f229c0ce..e5aa0c3d 100644
--- a/code/modules/flufftext/Hallucination.dm
+++ b/code/modules/flufftext/Hallucination.dm
@@ -138,7 +138,7 @@ GLOBAL_LIST_INIT(hallucination_list, list(
Show()
/obj/effect/hallucination/simple/Destroy()
- if(target.client)
+ if(target && target.client)
target.client.images.Remove(current_image)
active = FALSE
return ..()
diff --git a/code/modules/mob/living/carbon/human/human.dm b/code/modules/mob/living/carbon/human/human.dm
index 60113b98..798a73f4 100644
--- a/code/modules/mob/living/carbon/human/human.dm
+++ b/code/modules/mob/living/carbon/human/human.dm
@@ -29,7 +29,7 @@
. = ..()
- AddComponent(/datum/component/redirect, list(COMSIG_COMPONENT_CLEAN_ACT = CALLBACK(src, /mob/living/carbon/human/clean_blood)))
+ RegisterSignal(src, COMSIG_COMPONENT_CLEAN_ACT, /mob/living/carbon/human/clean_blood)
/mob/living/carbon/human/ComponentInitialize()
diff --git a/code/modules/projectiles/guns/misc/beam_rifle.dm b/code/modules/projectiles/guns/misc/beam_rifle.dm
index bcf44805..b6e6a01d 100644
--- a/code/modules/projectiles/guns/misc/beam_rifle.dm
+++ b/code/modules/projectiles/guns/misc/beam_rifle.dm
@@ -1,567 +1,570 @@
-
-#define ZOOM_LOCK_AUTOZOOM_FREEMOVE 0
-#define ZOOM_LOCK_AUTOZOOM_ANGLELOCK 1
-#define ZOOM_LOCK_CENTER_VIEW 2
-#define ZOOM_LOCK_OFF 3
-
-#define AUTOZOOM_PIXEL_STEP_FACTOR 48
-
-#define AIMING_BEAM_ANGLE_CHANGE_THRESHOLD 0.1
-
-/obj/item/gun/energy/beam_rifle
- name = "particle acceleration rifle"
- desc = "An energy-based anti material marksman rifle that uses highly charged particle beams moving at extreme velocities to decimate whatever is unfortunate enough to be targeted by one. \
- Hold down left click while scoped to aim, when weapon is fully aimed (Tracer goes from red to green as it charges), release to fire. Moving while aiming or \
- changing where you're pointing at while aiming will delay the aiming process depending on how much you changed."
- icon = 'icons/obj/guns/energy.dmi'
- icon_state = "esniper"
- item_state = "esniper"
- fire_sound = 'sound/weapons/beam_sniper.ogg'
- slot_flags = ITEM_SLOT_BACK
- force = 15
- materials = list()
- recoil = 4
- ammo_x_offset = 3
- ammo_y_offset = 3
- modifystate = FALSE
- weapon_weight = WEAPON_HEAVY
- w_class = WEIGHT_CLASS_BULKY
- ammo_type = list(/obj/item/ammo_casing/energy/beam_rifle/hitscan)
- cell_type = /obj/item/stock_parts/cell/beam_rifle
- canMouseDown = TRUE
- //Cit changes: beam rifle stats.
- slowdown = 1
- item_flags = NO_MAT_REDEMPTION | SLOWS_WHILE_IN_HAND | NEEDS_PERMIT
- pin = null
- var/aiming = FALSE
- var/aiming_time = 14
- var/aiming_time_fire_threshold = 5
- var/aiming_time_left = 14
- var/aiming_time_increase_user_movement = 7
- var/aiming_time_increase_angle_multiplier = 0.30
- var/last_process = 0
-
- var/lastangle = 0
- var/aiming_lastangle = 0
- var/mob/current_user = null
- var/list/obj/effect/projectile/tracer/current_tracers
-
- var/structure_piercing = 1
- var/structure_bleed_coeff = 0.7
- var/wall_pierce_amount = 0
- var/wall_devastate = 0
- var/aoe_structure_range = 1
- var/aoe_structure_damage = 35
- var/aoe_fire_range = 1
- var/aoe_fire_chance = 100
- var/aoe_mob_range = 1
- var/aoe_mob_damage = 20
- var/impact_structure_damage = 75
- var/projectile_damage = 40
- var/projectile_stun = 0
- var/projectile_setting_pierce = TRUE
- var/delay = 30
- var/lastfire = 0
-
- //ZOOMING
- var/zoom_current_view_increase = 0
- var/zoom_target_view_increase = 10
- var/zooming = FALSE
- var/zoom_lock = ZOOM_LOCK_OFF
- var/zooming_angle
- var/current_zoom_x = 0
- var/current_zoom_y = 0
-
- var/static/image/charged_overlay = image(icon = 'icons/obj/guns/energy.dmi', icon_state = "esniper_charged")
- var/static/image/drained_overlay = image(icon = 'icons/obj/guns/energy.dmi', icon_state = "esniper_empty")
-
- var/datum/action/item_action/zoom_lock_action/zoom_lock_action
- var/datum/component/mobhook
-
-/obj/item/gun/energy/beam_rifle/debug
- delay = 0
- cell_type = /obj/item/stock_parts/cell/infinite
- aiming_time = 0
- recoil = 0
- pin = /obj/item/firing_pin
-
-/obj/item/gun/energy/beam_rifle/equipped(mob/user)
- set_user(user)
- . = ..()
-
-/obj/item/gun/energy/beam_rifle/pickup(mob/user)
- set_user(user)
- . = ..()
-
-/obj/item/gun/energy/beam_rifle/dropped(mob/user)
- set_user()
- . = ..()
-
-/obj/item/gun/energy/beam_rifle/ui_action_click(owner, action)
- if(istype(action, /datum/action/item_action/zoom_lock_action))
- zoom_lock++
- if(zoom_lock > 3)
- zoom_lock = 0
- switch(zoom_lock)
- if(ZOOM_LOCK_AUTOZOOM_FREEMOVE)
- to_chat(owner, "You switch [src]'s zooming processor to free directional.")
- if(ZOOM_LOCK_AUTOZOOM_ANGLELOCK)
- to_chat(owner, "You switch [src]'s zooming processor to locked directional.")
- if(ZOOM_LOCK_CENTER_VIEW)
- to_chat(owner, "You switch [src]'s zooming processor to center mode.")
- if(ZOOM_LOCK_OFF)
- to_chat(owner, "You disable [src]'s zooming system.")
- reset_zooming()
-
-/obj/item/gun/energy/beam_rifle/proc/set_autozoom_pixel_offsets_immediate(current_angle)
- if(zoom_lock == ZOOM_LOCK_CENTER_VIEW || zoom_lock == ZOOM_LOCK_OFF)
- return
- current_zoom_x = sin(current_angle) + sin(current_angle) * AUTOZOOM_PIXEL_STEP_FACTOR * zoom_current_view_increase
- current_zoom_y = cos(current_angle) + cos(current_angle) * AUTOZOOM_PIXEL_STEP_FACTOR * zoom_current_view_increase
-
-/obj/item/gun/energy/beam_rifle/proc/handle_zooming()
- if(!zooming || !check_user())
- return
- set_autozoom_pixel_offsets_immediate(zooming_angle)
-
-/obj/item/gun/energy/beam_rifle/proc/start_zooming()
- if(zoom_lock == ZOOM_LOCK_OFF)
- return
- zooming = TRUE
- current_user.client.change_view(world.view + zoom_target_view_increase)
- zoom_current_view_increase = zoom_target_view_increase
-
-/obj/item/gun/energy/beam_rifle/proc/stop_zooming(mob/user)
- if(zooming)
- zooming = FALSE
- reset_zooming(user)
-
-/obj/item/gun/energy/beam_rifle/proc/reset_zooming(mob/user)
- if(!user)
- user = current_user
- if(!user || !user.client)
- return FALSE
- animate(user.client, pixel_x = 0, pixel_y = 0, 0, FALSE, LINEAR_EASING, ANIMATION_END_NOW)
- zoom_current_view_increase = 0
- user.client.change_view(CONFIG_GET(string/default_view))
- zooming_angle = 0
- current_zoom_x = 0
- current_zoom_y = 0
-
-/obj/item/gun/energy/beam_rifle/update_icon()
- cut_overlays()
- var/obj/item/ammo_casing/energy/primary_ammo = ammo_type[1]
- if(!QDELETED(cell) && (cell.charge > primary_ammo.e_cost))
- add_overlay(charged_overlay)
- else
- add_overlay(drained_overlay)
-
-/obj/item/gun/energy/beam_rifle/attack_self(mob/user)
- projectile_setting_pierce = !projectile_setting_pierce
- to_chat(user, "You set \the [src] to [projectile_setting_pierce? "pierce":"impact"] mode.")
- aiming_beam()
-
-/obj/item/gun/energy/beam_rifle/Initialize()
- . = ..()
- fire_delay = delay
- current_tracers = list()
- START_PROCESSING(SSfastprocess, src)
- zoom_lock_action = new(src)
-
-/obj/item/gun/energy/beam_rifle/Destroy()
- STOP_PROCESSING(SSfastprocess, src)
- set_user(null)
- QDEL_LIST(current_tracers)
- QDEL_NULL(mobhook)
- return ..()
-
-/obj/item/gun/energy/beam_rifle/emp_act(severity)
- . = ..()
- if(. & EMP_PROTECT_SELF)
- return
- chambered = null
- recharge_newshot()
-
-/obj/item/gun/energy/beam_rifle/proc/aiming_beam(force_update = FALSE)
- var/diff = abs(aiming_lastangle - lastangle)
- check_user()
- if(diff < AIMING_BEAM_ANGLE_CHANGE_THRESHOLD && !force_update)
- return
- aiming_lastangle = lastangle
- var/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/P = new
- P.gun = src
- P.wall_pierce_amount = wall_pierce_amount
- P.structure_pierce_amount = structure_piercing
- P.do_pierce = projectile_setting_pierce
- if(aiming_time)
- var/percent = ((100/aiming_time)*aiming_time_left)
- P.color = rgb(255 * percent,255 * ((100 - percent) / 100),0)
- else
- P.color = rgb(0, 255, 0)
- var/turf/curloc = get_turf(src)
- var/turf/targloc = get_turf(current_user.client.mouseObject)
- if(!istype(targloc))
- if(!istype(curloc))
- return
- targloc = get_turf_in_angle(lastangle, curloc, 10)
- P.preparePixelProjectile(targloc, current_user, current_user.client.mouseParams, 0)
- P.fire(lastangle)
-
-/obj/item/gun/energy/beam_rifle/process()
- if(!aiming)
- last_process = world.time
- return
- check_user()
- handle_zooming()
- aiming_time_left = max(0, aiming_time_left - (world.time - last_process))
- aiming_beam(TRUE)
- last_process = world.time
-
-/obj/item/gun/energy/beam_rifle/proc/check_user(automatic_cleanup = TRUE)
- if(!istype(current_user) || !isturf(current_user.loc) || !(src in current_user.held_items) || current_user.incapacitated()) //Doesn't work if you're not holding it!
- if(automatic_cleanup)
- stop_aiming()
- set_user(null)
- return FALSE
- return TRUE
-
-/obj/item/gun/energy/beam_rifle/proc/process_aim()
- if(istype(current_user) && current_user.client && current_user.client.mouseParams)
- var/angle = mouse_angle_from_client(current_user.client)
- current_user.setDir(angle2dir_cardinal(angle))
- var/difference = abs(closer_angle_difference(lastangle, angle))
- delay_penalty(difference * aiming_time_increase_angle_multiplier)
- lastangle = angle
-
-/obj/item/gun/energy/beam_rifle/proc/on_mob_move()
- check_user()
- if(aiming)
- delay_penalty(aiming_time_increase_user_movement)
- process_aim()
- aiming_beam(TRUE)
-
-/obj/item/gun/energy/beam_rifle/proc/start_aiming()
- aiming_time_left = aiming_time
- aiming = TRUE
- process_aim()
- aiming_beam(TRUE)
- zooming_angle = lastangle
- start_zooming()
-
-/obj/item/gun/energy/beam_rifle/proc/stop_aiming(mob/user)
- set waitfor = FALSE
- aiming_time_left = aiming_time
- aiming = FALSE
- QDEL_LIST(current_tracers)
- stop_zooming(user)
-
-/obj/item/gun/energy/beam_rifle/proc/set_user(mob/user)
- if(user == current_user)
- return
- stop_aiming(current_user)
- QDEL_NULL(mobhook)
- if(istype(current_user))
- LAZYREMOVE(current_user.mousemove_intercept_objects, src)
- current_user = null
- if(istype(user))
- current_user = user
- LAZYOR(current_user.mousemove_intercept_objects, src)
- mobhook = user.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_mob_move)))
-
-/obj/item/gun/energy/beam_rifle/onMouseDrag(src_object, over_object, src_location, over_location, params, mob)
- if(aiming)
- process_aim()
- aiming_beam()
- if(zoom_lock == ZOOM_LOCK_AUTOZOOM_FREEMOVE)
- zooming_angle = lastangle
- set_autozoom_pixel_offsets_immediate(zooming_angle)
- return ..()
-
-/obj/item/gun/energy/beam_rifle/onMouseDown(object, location, params, mob/mob)
- if(istype(mob))
- set_user(mob)
- if(istype(object, /obj/screen) && !istype(object, /obj/screen/click_catcher))
- return
- if((object in mob.contents) || (object == mob))
- return
- start_aiming()
- return ..()
-
-/obj/item/gun/energy/beam_rifle/onMouseUp(object, location, params, mob/M)
- if(istype(object, /obj/screen) && !istype(object, /obj/screen/click_catcher))
- return
- process_aim()
- if(aiming_time_left <= aiming_time_fire_threshold && check_user())
- sync_ammo()
- afterattack(M.client.mouseObject, M, FALSE, M.client.mouseParams, passthrough = TRUE)
- stop_aiming()
- QDEL_LIST(current_tracers)
- return ..()
-
-/obj/item/gun/energy/beam_rifle/afterattack(atom/target, mob/living/user, flag, params, passthrough = FALSE)
- if(flag) //It's adjacent, is the user, or is on the user's person
- if(target in user.contents) //can't shoot stuff inside us.
- return
- if(!ismob(target) || user.a_intent == INTENT_HARM) //melee attack
- return
- if(target == user && user.zone_selected != BODY_ZONE_PRECISE_MOUTH) //so we can't shoot ourselves (unless mouth selected)
- return
- if(!passthrough && (aiming_time > aiming_time_fire_threshold))
- return
- if(lastfire > world.time + delay)
- return
- lastfire = world.time
- . = ..()
- stop_aiming()
-
-/obj/item/gun/energy/beam_rifle/proc/sync_ammo()
- for(var/obj/item/ammo_casing/energy/beam_rifle/AC in contents)
- AC.sync_stats()
-
-/obj/item/gun/energy/beam_rifle/proc/delay_penalty(amount)
- aiming_time_left = CLAMP(aiming_time_left + amount, 0, aiming_time)
-
-/obj/item/ammo_casing/energy/beam_rifle
- name = "particle acceleration lens"
- desc = "Don't look into barrel!"
- var/wall_pierce_amount = 0
- var/wall_devastate = 0
- var/aoe_structure_range = 1
- var/aoe_structure_damage = 30
- var/aoe_fire_range = 2
- var/aoe_fire_chance = 66
- var/aoe_mob_range = 1
- var/aoe_mob_damage = 20
- var/impact_structure_damage = 50
- var/projectile_damage = 40
- var/projectile_stun = 0
- var/structure_piercing = 2
- var/structure_bleed_coeff = 0.7
- var/do_pierce = TRUE
- var/obj/item/gun/energy/beam_rifle/host
-
-/obj/item/ammo_casing/energy/beam_rifle/proc/sync_stats()
- var/obj/item/gun/energy/beam_rifle/BR = loc
- if(!istype(BR))
- stack_trace("Beam rifle syncing error")
- host = BR
- do_pierce = BR.projectile_setting_pierce
- wall_pierce_amount = BR.wall_pierce_amount
- wall_devastate = BR.wall_devastate
- aoe_structure_range = BR.aoe_structure_range
- aoe_structure_damage = BR.aoe_structure_damage
- aoe_fire_range = BR.aoe_fire_range
- aoe_fire_chance = BR.aoe_fire_chance
- aoe_mob_range = BR.aoe_mob_range
- aoe_mob_damage = BR.aoe_mob_damage
- impact_structure_damage = BR.impact_structure_damage
- projectile_damage = BR.projectile_damage
- projectile_stun = BR.projectile_stun
- delay = BR.delay
- structure_piercing = BR.structure_piercing
- structure_bleed_coeff = BR.structure_bleed_coeff
-
-/obj/item/ammo_casing/energy/beam_rifle/ready_proj(atom/target, mob/living/user, quiet, zone_override = "")
- . = ..()
- var/obj/item/projectile/beam/beam_rifle/hitscan/HS_BB = BB
- if(!istype(HS_BB))
- return
- HS_BB.impact_direct_damage = projectile_damage
- HS_BB.stun = projectile_stun
- HS_BB.impact_structure_damage = impact_structure_damage
- HS_BB.aoe_mob_damage = aoe_mob_damage
- HS_BB.aoe_mob_range = CLAMP(aoe_mob_range, 0, 15) //Badmin safety lock
- HS_BB.aoe_fire_chance = aoe_fire_chance
- HS_BB.aoe_fire_range = aoe_fire_range
- HS_BB.aoe_structure_damage = aoe_structure_damage
- HS_BB.aoe_structure_range = CLAMP(aoe_structure_range, 0, 15) //Badmin safety lock
- HS_BB.wall_devastate = wall_devastate
- HS_BB.wall_pierce_amount = wall_pierce_amount
- HS_BB.structure_pierce_amount = structure_piercing
- HS_BB.structure_bleed_coeff = structure_bleed_coeff
- HS_BB.do_pierce = do_pierce
- HS_BB.gun = host
-
-/obj/item/ammo_casing/energy/beam_rifle/throw_proj(atom/target, turf/targloc, mob/living/user, params, spread)
- var/turf/curloc = get_turf(user)
- if(!istype(curloc) || !BB)
- return FALSE
- var/obj/item/gun/energy/beam_rifle/gun = loc
- if(!targloc && gun)
- targloc = get_turf_in_angle(gun.lastangle, curloc, 10)
- else if(!targloc)
- return FALSE
- var/firing_dir
- if(BB.firer)
- firing_dir = BB.firer.dir
- if(!BB.suppressed && firing_effect_type)
- new firing_effect_type(get_turf(src), firing_dir)
- BB.preparePixelProjectile(target, user, params, spread)
- BB.fire(gun? gun.lastangle : null, null)
- BB = null
- return TRUE
-
-/obj/item/ammo_casing/energy/beam_rifle/hitscan
- projectile_type = /obj/item/projectile/beam/beam_rifle/hitscan
- select_name = "beam"
- e_cost = 5000
- fire_sound = 'sound/weapons/beam_sniper.ogg'
-
-/obj/item/projectile/beam/beam_rifle
- name = "particle beam"
- icon = null
- hitsound = 'sound/effects/explosion3.ogg'
- damage = 0 //Handled manually.
- damage_type = BURN
- flag = "energy"
- range = 150
- jitter = 10
- var/obj/item/gun/energy/beam_rifle/gun
- var/structure_pierce_amount = 0 //All set to 0 so the gun can manually set them during firing.
- var/structure_bleed_coeff = 0
- var/structure_pierce = 0
- var/do_pierce = TRUE
- var/wall_pierce_amount = 0
- var/wall_pierce = 0
- var/wall_devastate = 0
- var/aoe_structure_range = 0
- var/aoe_structure_damage = 0
- var/aoe_fire_range = 0
- var/aoe_fire_chance = 0
- var/aoe_mob_range = 0
- var/aoe_mob_damage = 0
- var/impact_structure_damage = 0
- var/impact_direct_damage = 0
- var/turf/cached
- var/list/pierced = list()
-
-/obj/item/projectile/beam/beam_rifle/proc/AOE(turf/epicenter)
- set waitfor = FALSE
- if(!epicenter)
- return
- new /obj/effect/temp_visual/explosion/fast(epicenter)
- for(var/mob/living/L in range(aoe_mob_range, epicenter)) //handle aoe mob damage
- L.adjustFireLoss(aoe_mob_damage)
- to_chat(L, "\The [src] sears you!")
- for(var/turf/T in range(aoe_fire_range, epicenter)) //handle aoe fire
- if(prob(aoe_fire_chance))
- new /obj/effect/hotspot(T)
- for(var/obj/O in range(aoe_structure_range, epicenter))
- if(!isitem(O))
- if(O.level == 1) //Please don't break underfloor items!
- continue
- O.take_damage(aoe_structure_damage * get_damage_coeff(O), BURN, "laser", FALSE)
-
-/obj/item/projectile/beam/beam_rifle/proc/check_pierce(atom/target)
- if(!do_pierce)
- return FALSE
- if(pierced[target]) //we already pierced them go away
- return TRUE
- if(isclosedturf(target))
- if(wall_pierce++ < wall_pierce_amount)
- if(prob(wall_devastate))
- if(iswallturf(target))
- var/turf/closed/wall/W = target
- W.dismantle_wall(TRUE, TRUE)
- else
- target.ex_act(EXPLODE_HEAVY)
- return TRUE
- if(ismovableatom(target))
- var/atom/movable/AM = target
- if(AM.density && !AM.CanPass(src, get_turf(target)) && !ismob(AM))
- if(structure_pierce < structure_pierce_amount)
- if(isobj(AM))
- var/obj/O = AM
- O.take_damage((impact_structure_damage + aoe_structure_damage) * structure_bleed_coeff * get_damage_coeff(AM), BURN, "energy", FALSE)
- pierced[AM] = TRUE
- structure_pierce++
- return TRUE
- return FALSE
-
-/obj/item/projectile/beam/beam_rifle/proc/get_damage_coeff(atom/target)
- if(istype(target, /obj/machinery/door))
- return 0.4
- if(istype(target, /obj/structure/window))
- return 0.5
- if(istype(target, /obj/structure/blob))
- return 0.65 //CIT CHANGE.
- return 1
-
-/obj/item/projectile/beam/beam_rifle/proc/handle_impact(atom/target)
- if(isobj(target))
- var/obj/O = target
- O.take_damage(impact_structure_damage * get_damage_coeff(target), BURN, "laser", FALSE)
- if(isliving(target))
- var/mob/living/L = target
- L.adjustFireLoss(impact_direct_damage)
- L.emote("scream")
-
-/obj/item/projectile/beam/beam_rifle/proc/handle_hit(atom/target)
- set waitfor = FALSE
- if(!cached && !QDELETED(target))
- cached = get_turf(target)
- if(nodamage)
- return FALSE
- playsound(cached, 'sound/effects/explosion3.ogg', 100, 1)
- AOE(cached)
- if(!QDELETED(target))
- handle_impact(target)
-
-/obj/item/projectile/beam/beam_rifle/Bump(atom/target)
- if(check_pierce(target))
- permutated += target
- trajectory_ignore_forcemove = TRUE
- forceMove(target.loc)
- trajectory_ignore_forcemove = FALSE
- return FALSE
- if(!QDELETED(target))
- cached = get_turf(target)
- . = ..()
-
-/obj/item/projectile/beam/beam_rifle/on_hit(atom/target, blocked = FALSE)
- if(!QDELETED(target))
- cached = get_turf(target)
- handle_hit(target)
- . = ..()
-
-/obj/item/projectile/beam/beam_rifle/hitscan
- icon_state = ""
- hitscan = TRUE
- tracer_type = /obj/effect/projectile/tracer/tracer/beam_rifle
- var/constant_tracer = FALSE
-
-/obj/item/projectile/beam/beam_rifle/hitscan/generate_hitscan_tracers(cleanup = TRUE, duration = 5, impacting = TRUE, highlander)
- set waitfor = FALSE
- if(isnull(highlander))
- highlander = constant_tracer
- if(highlander && istype(gun))
- QDEL_LIST(gun.current_tracers)
- for(var/datum/point/p in beam_segments)
- gun.current_tracers += generate_tracer_between_points(p, beam_segments[p], tracer_type, color, 0, hitscan_light_range, hitscan_light_color_override, hitscan_light_intensity)
- else
- for(var/datum/point/p in beam_segments)
- generate_tracer_between_points(p, beam_segments[p], tracer_type, color, duration, hitscan_light_range, hitscan_light_color_override, hitscan_light_intensity)
- if(cleanup)
- QDEL_LIST(beam_segments)
- beam_segments = null
- QDEL_NULL(beam_index)
-
-/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam
- tracer_type = /obj/effect/projectile/tracer/tracer/aiming
- name = "aiming beam"
- hitsound = null
- hitsound_wall = null
- nodamage = TRUE
- damage = 0
- constant_tracer = TRUE
- hitscan_light_range = 0
- hitscan_light_intensity = 0
- hitscan_light_color_override = "#99ff99"
-
-/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/prehit(atom/target)
- qdel(src)
- return FALSE
-
-/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/on_hit()
- qdel(src)
- return FALSE
+
+#define ZOOM_LOCK_AUTOZOOM_FREEMOVE 0
+#define ZOOM_LOCK_AUTOZOOM_ANGLELOCK 1
+#define ZOOM_LOCK_CENTER_VIEW 2
+#define ZOOM_LOCK_OFF 3
+
+#define AUTOZOOM_PIXEL_STEP_FACTOR 48
+
+#define AIMING_BEAM_ANGLE_CHANGE_THRESHOLD 0.1
+
+/obj/item/gun/energy/beam_rifle
+ name = "particle acceleration rifle"
+ desc = "An energy-based anti material marksman rifle that uses highly charged particle beams moving at extreme velocities to decimate whatever is unfortunate enough to be targeted by one. \
+ Hold down left click while scoped to aim, when weapon is fully aimed (Tracer goes from red to green as it charges), release to fire. Moving while aiming or \
+ changing where you're pointing at while aiming will delay the aiming process depending on how much you changed."
+ icon = 'icons/obj/guns/energy.dmi'
+ icon_state = "esniper"
+ item_state = "esniper"
+ fire_sound = 'sound/weapons/beam_sniper.ogg'
+ slot_flags = ITEM_SLOT_BACK
+ force = 15
+ materials = list()
+ recoil = 4
+ ammo_x_offset = 3
+ ammo_y_offset = 3
+ modifystate = FALSE
+ weapon_weight = WEAPON_HEAVY
+ w_class = WEIGHT_CLASS_BULKY
+ ammo_type = list(/obj/item/ammo_casing/energy/beam_rifle/hitscan)
+ cell_type = /obj/item/stock_parts/cell/beam_rifle
+ canMouseDown = TRUE
+ //Cit changes: beam rifle stats.
+ slowdown = 1
+ item_flags = NO_MAT_REDEMPTION | SLOWS_WHILE_IN_HAND | NEEDS_PERMIT
+ pin = null
+ var/aiming = FALSE
+ var/aiming_time = 14
+ var/aiming_time_fire_threshold = 5
+ var/aiming_time_left = 14
+ var/aiming_time_increase_user_movement = 7
+ var/aiming_time_increase_angle_multiplier = 0.30
+ var/last_process = 0
+
+ var/lastangle = 0
+ var/aiming_lastangle = 0
+ var/mob/current_user = null
+ var/list/obj/effect/projectile/tracer/current_tracers
+
+ var/structure_piercing = 1
+ var/structure_bleed_coeff = 0.7
+ var/wall_pierce_amount = 0
+ var/wall_devastate = 0
+ var/aoe_structure_range = 1
+ var/aoe_structure_damage = 35
+ var/aoe_fire_range = 1
+ var/aoe_fire_chance = 100
+ var/aoe_mob_range = 1
+ var/aoe_mob_damage = 20
+ var/impact_structure_damage = 75
+ var/projectile_damage = 40
+ var/projectile_stun = 0
+ var/projectile_setting_pierce = TRUE
+ var/delay = 30
+ var/lastfire = 0
+
+ //ZOOMING
+ var/zoom_current_view_increase = 0
+ var/zoom_target_view_increase = 10
+ var/zooming = FALSE
+ var/zoom_lock = ZOOM_LOCK_OFF
+ var/zooming_angle
+ var/current_zoom_x = 0
+ var/current_zoom_y = 0
+
+ var/static/image/charged_overlay = image(icon = 'icons/obj/guns/energy.dmi', icon_state = "esniper_charged")
+ var/static/image/drained_overlay = image(icon = 'icons/obj/guns/energy.dmi', icon_state = "esniper_empty")
+
+ var/datum/action/item_action/zoom_lock_action/zoom_lock_action
+ var/mob/listeningTo
+
+/obj/item/gun/energy/beam_rifle/debug
+ delay = 0
+ cell_type = /obj/item/stock_parts/cell/infinite
+ aiming_time = 0
+ recoil = 0
+ pin = /obj/item/firing_pin
+
+/obj/item/gun/energy/beam_rifle/equipped(mob/user)
+ set_user(user)
+ . = ..()
+
+/obj/item/gun/energy/beam_rifle/pickup(mob/user)
+ set_user(user)
+ . = ..()
+
+/obj/item/gun/energy/beam_rifle/dropped(mob/user)
+ set_user()
+ . = ..()
+
+/obj/item/gun/energy/beam_rifle/ui_action_click(owner, action)
+ if(istype(action, /datum/action/item_action/zoom_lock_action))
+ zoom_lock++
+ if(zoom_lock > 3)
+ zoom_lock = 0
+ switch(zoom_lock)
+ if(ZOOM_LOCK_AUTOZOOM_FREEMOVE)
+ to_chat(owner, "You switch [src]'s zooming processor to free directional.")
+ if(ZOOM_LOCK_AUTOZOOM_ANGLELOCK)
+ to_chat(owner, "You switch [src]'s zooming processor to locked directional.")
+ if(ZOOM_LOCK_CENTER_VIEW)
+ to_chat(owner, "You switch [src]'s zooming processor to center mode.")
+ if(ZOOM_LOCK_OFF)
+ to_chat(owner, "You disable [src]'s zooming system.")
+ reset_zooming()
+
+/obj/item/gun/energy/beam_rifle/proc/set_autozoom_pixel_offsets_immediate(current_angle)
+ if(zoom_lock == ZOOM_LOCK_CENTER_VIEW || zoom_lock == ZOOM_LOCK_OFF)
+ return
+ current_zoom_x = sin(current_angle) + sin(current_angle) * AUTOZOOM_PIXEL_STEP_FACTOR * zoom_current_view_increase
+ current_zoom_y = cos(current_angle) + cos(current_angle) * AUTOZOOM_PIXEL_STEP_FACTOR * zoom_current_view_increase
+
+/obj/item/gun/energy/beam_rifle/proc/handle_zooming()
+ if(!zooming || !check_user())
+ return
+ set_autozoom_pixel_offsets_immediate(zooming_angle)
+
+/obj/item/gun/energy/beam_rifle/proc/start_zooming()
+ if(zoom_lock == ZOOM_LOCK_OFF)
+ return
+ zooming = TRUE
+ current_user.client.change_view(world.view + zoom_target_view_increase)
+ zoom_current_view_increase = zoom_target_view_increase
+
+/obj/item/gun/energy/beam_rifle/proc/stop_zooming(mob/user)
+ if(zooming)
+ zooming = FALSE
+ reset_zooming(user)
+
+/obj/item/gun/energy/beam_rifle/proc/reset_zooming(mob/user)
+ if(!user)
+ user = current_user
+ if(!user || !user.client)
+ return FALSE
+ animate(user.client, pixel_x = 0, pixel_y = 0, 0, FALSE, LINEAR_EASING, ANIMATION_END_NOW)
+ zoom_current_view_increase = 0
+ user.client.change_view(CONFIG_GET(string/default_view))
+ zooming_angle = 0
+ current_zoom_x = 0
+ current_zoom_y = 0
+
+/obj/item/gun/energy/beam_rifle/update_icon()
+ cut_overlays()
+ var/obj/item/ammo_casing/energy/primary_ammo = ammo_type[1]
+ if(!QDELETED(cell) && (cell.charge > primary_ammo.e_cost))
+ add_overlay(charged_overlay)
+ else
+ add_overlay(drained_overlay)
+
+/obj/item/gun/energy/beam_rifle/attack_self(mob/user)
+ projectile_setting_pierce = !projectile_setting_pierce
+ to_chat(user, "You set \the [src] to [projectile_setting_pierce? "pierce":"impact"] mode.")
+ aiming_beam()
+
+/obj/item/gun/energy/beam_rifle/Initialize()
+ . = ..()
+ fire_delay = delay
+ current_tracers = list()
+ START_PROCESSING(SSfastprocess, src)
+ zoom_lock_action = new(src)
+
+/obj/item/gun/energy/beam_rifle/Destroy()
+ STOP_PROCESSING(SSfastprocess, src)
+ set_user(null)
+ QDEL_LIST(current_tracers)
+ listeningTo = null
+ return ..()
+
+/obj/item/gun/energy/beam_rifle/emp_act(severity)
+ . = ..()
+ if(. & EMP_PROTECT_SELF)
+ return
+ chambered = null
+ recharge_newshot()
+
+/obj/item/gun/energy/beam_rifle/proc/aiming_beam(force_update = FALSE)
+ var/diff = abs(aiming_lastangle - lastangle)
+ check_user()
+ if(diff < AIMING_BEAM_ANGLE_CHANGE_THRESHOLD && !force_update)
+ return
+ aiming_lastangle = lastangle
+ var/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/P = new
+ P.gun = src
+ P.wall_pierce_amount = wall_pierce_amount
+ P.structure_pierce_amount = structure_piercing
+ P.do_pierce = projectile_setting_pierce
+ if(aiming_time)
+ var/percent = ((100/aiming_time)*aiming_time_left)
+ P.color = rgb(255 * percent,255 * ((100 - percent) / 100),0)
+ else
+ P.color = rgb(0, 255, 0)
+ var/turf/curloc = get_turf(src)
+ var/turf/targloc = get_turf(current_user.client.mouseObject)
+ if(!istype(targloc))
+ if(!istype(curloc))
+ return
+ targloc = get_turf_in_angle(lastangle, curloc, 10)
+ P.preparePixelProjectile(targloc, current_user, current_user.client.mouseParams, 0)
+ P.fire(lastangle)
+
+/obj/item/gun/energy/beam_rifle/process()
+ if(!aiming)
+ last_process = world.time
+ return
+ check_user()
+ handle_zooming()
+ aiming_time_left = max(0, aiming_time_left - (world.time - last_process))
+ aiming_beam(TRUE)
+ last_process = world.time
+
+/obj/item/gun/energy/beam_rifle/proc/check_user(automatic_cleanup = TRUE)
+ if(!istype(current_user) || !isturf(current_user.loc) || !(src in current_user.held_items) || current_user.incapacitated()) //Doesn't work if you're not holding it!
+ if(automatic_cleanup)
+ stop_aiming()
+ set_user(null)
+ return FALSE
+ return TRUE
+
+/obj/item/gun/energy/beam_rifle/proc/process_aim()
+ if(istype(current_user) && current_user.client && current_user.client.mouseParams)
+ var/angle = mouse_angle_from_client(current_user.client)
+ current_user.setDir(angle2dir_cardinal(angle))
+ var/difference = abs(closer_angle_difference(lastangle, angle))
+ delay_penalty(difference * aiming_time_increase_angle_multiplier)
+ lastangle = angle
+
+/obj/item/gun/energy/beam_rifle/proc/on_mob_move()
+ check_user()
+ if(aiming)
+ delay_penalty(aiming_time_increase_user_movement)
+ process_aim()
+ aiming_beam(TRUE)
+
+/obj/item/gun/energy/beam_rifle/proc/start_aiming()
+ aiming_time_left = aiming_time
+ aiming = TRUE
+ process_aim()
+ aiming_beam(TRUE)
+ zooming_angle = lastangle
+ start_zooming()
+
+/obj/item/gun/energy/beam_rifle/proc/stop_aiming(mob/user)
+ set waitfor = FALSE
+ aiming_time_left = aiming_time
+ aiming = FALSE
+ QDEL_LIST(current_tracers)
+ stop_zooming(user)
+
+/obj/item/gun/energy/beam_rifle/proc/set_user(mob/user)
+ if(user == current_user)
+ return
+ stop_aiming(current_user)
+ if(listeningTo)
+ UnregisterSignal(listeningTo, COMSIG_MOVABLE_MOVED)
+ listeningTo = null
+ if(istype(current_user))
+ LAZYREMOVE(current_user.mousemove_intercept_objects, src)
+ current_user = null
+ if(istype(user))
+ current_user = user
+ LAZYOR(current_user.mousemove_intercept_objects, src)
+ RegisterSignal(user, COMSIG_MOVABLE_MOVED, .proc/on_mob_move)
+ listeningTo = user
+
+/obj/item/gun/energy/beam_rifle/onMouseDrag(src_object, over_object, src_location, over_location, params, mob)
+ if(aiming)
+ process_aim()
+ aiming_beam()
+ if(zoom_lock == ZOOM_LOCK_AUTOZOOM_FREEMOVE)
+ zooming_angle = lastangle
+ set_autozoom_pixel_offsets_immediate(zooming_angle)
+ return ..()
+
+/obj/item/gun/energy/beam_rifle/onMouseDown(object, location, params, mob/mob)
+ if(istype(mob))
+ set_user(mob)
+ if(istype(object, /obj/screen) && !istype(object, /obj/screen/click_catcher))
+ return
+ if((object in mob.contents) || (object == mob))
+ return
+ start_aiming()
+ return ..()
+
+/obj/item/gun/energy/beam_rifle/onMouseUp(object, location, params, mob/M)
+ if(istype(object, /obj/screen) && !istype(object, /obj/screen/click_catcher))
+ return
+ process_aim()
+ if(aiming_time_left <= aiming_time_fire_threshold && check_user())
+ sync_ammo()
+ afterattack(M.client.mouseObject, M, FALSE, M.client.mouseParams, passthrough = TRUE)
+ stop_aiming()
+ QDEL_LIST(current_tracers)
+ return ..()
+
+/obj/item/gun/energy/beam_rifle/afterattack(atom/target, mob/living/user, flag, params, passthrough = FALSE)
+ if(flag) //It's adjacent, is the user, or is on the user's person
+ if(target in user.contents) //can't shoot stuff inside us.
+ return
+ if(!ismob(target) || user.a_intent == INTENT_HARM) //melee attack
+ return
+ if(target == user && user.zone_selected != BODY_ZONE_PRECISE_MOUTH) //so we can't shoot ourselves (unless mouth selected)
+ return
+ if(!passthrough && (aiming_time > aiming_time_fire_threshold))
+ return
+ if(lastfire > world.time + delay)
+ return
+ lastfire = world.time
+ . = ..()
+ stop_aiming()
+
+/obj/item/gun/energy/beam_rifle/proc/sync_ammo()
+ for(var/obj/item/ammo_casing/energy/beam_rifle/AC in contents)
+ AC.sync_stats()
+
+/obj/item/gun/energy/beam_rifle/proc/delay_penalty(amount)
+ aiming_time_left = CLAMP(aiming_time_left + amount, 0, aiming_time)
+
+/obj/item/ammo_casing/energy/beam_rifle
+ name = "particle acceleration lens"
+ desc = "Don't look into barrel!"
+ var/wall_pierce_amount = 0
+ var/wall_devastate = 0
+ var/aoe_structure_range = 1
+ var/aoe_structure_damage = 30
+ var/aoe_fire_range = 2
+ var/aoe_fire_chance = 66
+ var/aoe_mob_range = 1
+ var/aoe_mob_damage = 20
+ var/impact_structure_damage = 50
+ var/projectile_damage = 40
+ var/projectile_stun = 0
+ var/structure_piercing = 2
+ var/structure_bleed_coeff = 0.7
+ var/do_pierce = TRUE
+ var/obj/item/gun/energy/beam_rifle/host
+
+/obj/item/ammo_casing/energy/beam_rifle/proc/sync_stats()
+ var/obj/item/gun/energy/beam_rifle/BR = loc
+ if(!istype(BR))
+ stack_trace("Beam rifle syncing error")
+ host = BR
+ do_pierce = BR.projectile_setting_pierce
+ wall_pierce_amount = BR.wall_pierce_amount
+ wall_devastate = BR.wall_devastate
+ aoe_structure_range = BR.aoe_structure_range
+ aoe_structure_damage = BR.aoe_structure_damage
+ aoe_fire_range = BR.aoe_fire_range
+ aoe_fire_chance = BR.aoe_fire_chance
+ aoe_mob_range = BR.aoe_mob_range
+ aoe_mob_damage = BR.aoe_mob_damage
+ impact_structure_damage = BR.impact_structure_damage
+ projectile_damage = BR.projectile_damage
+ projectile_stun = BR.projectile_stun
+ delay = BR.delay
+ structure_piercing = BR.structure_piercing
+ structure_bleed_coeff = BR.structure_bleed_coeff
+
+/obj/item/ammo_casing/energy/beam_rifle/ready_proj(atom/target, mob/living/user, quiet, zone_override = "")
+ . = ..()
+ var/obj/item/projectile/beam/beam_rifle/hitscan/HS_BB = BB
+ if(!istype(HS_BB))
+ return
+ HS_BB.impact_direct_damage = projectile_damage
+ HS_BB.stun = projectile_stun
+ HS_BB.impact_structure_damage = impact_structure_damage
+ HS_BB.aoe_mob_damage = aoe_mob_damage
+ HS_BB.aoe_mob_range = CLAMP(aoe_mob_range, 0, 15) //Badmin safety lock
+ HS_BB.aoe_fire_chance = aoe_fire_chance
+ HS_BB.aoe_fire_range = aoe_fire_range
+ HS_BB.aoe_structure_damage = aoe_structure_damage
+ HS_BB.aoe_structure_range = CLAMP(aoe_structure_range, 0, 15) //Badmin safety lock
+ HS_BB.wall_devastate = wall_devastate
+ HS_BB.wall_pierce_amount = wall_pierce_amount
+ HS_BB.structure_pierce_amount = structure_piercing
+ HS_BB.structure_bleed_coeff = structure_bleed_coeff
+ HS_BB.do_pierce = do_pierce
+ HS_BB.gun = host
+
+/obj/item/ammo_casing/energy/beam_rifle/throw_proj(atom/target, turf/targloc, mob/living/user, params, spread)
+ var/turf/curloc = get_turf(user)
+ if(!istype(curloc) || !BB)
+ return FALSE
+ var/obj/item/gun/energy/beam_rifle/gun = loc
+ if(!targloc && gun)
+ targloc = get_turf_in_angle(gun.lastangle, curloc, 10)
+ else if(!targloc)
+ return FALSE
+ var/firing_dir
+ if(BB.firer)
+ firing_dir = BB.firer.dir
+ if(!BB.suppressed && firing_effect_type)
+ new firing_effect_type(get_turf(src), firing_dir)
+ BB.preparePixelProjectile(target, user, params, spread)
+ BB.fire(gun? gun.lastangle : null, null)
+ BB = null
+ return TRUE
+
+/obj/item/ammo_casing/energy/beam_rifle/hitscan
+ projectile_type = /obj/item/projectile/beam/beam_rifle/hitscan
+ select_name = "beam"
+ e_cost = 5000
+ fire_sound = 'sound/weapons/beam_sniper.ogg'
+
+/obj/item/projectile/beam/beam_rifle
+ name = "particle beam"
+ icon = null
+ hitsound = 'sound/effects/explosion3.ogg'
+ damage = 0 //Handled manually.
+ damage_type = BURN
+ flag = "energy"
+ range = 150
+ jitter = 10
+ var/obj/item/gun/energy/beam_rifle/gun
+ var/structure_pierce_amount = 0 //All set to 0 so the gun can manually set them during firing.
+ var/structure_bleed_coeff = 0
+ var/structure_pierce = 0
+ var/do_pierce = TRUE
+ var/wall_pierce_amount = 0
+ var/wall_pierce = 0
+ var/wall_devastate = 0
+ var/aoe_structure_range = 0
+ var/aoe_structure_damage = 0
+ var/aoe_fire_range = 0
+ var/aoe_fire_chance = 0
+ var/aoe_mob_range = 0
+ var/aoe_mob_damage = 0
+ var/impact_structure_damage = 0
+ var/impact_direct_damage = 0
+ var/turf/cached
+ var/list/pierced = list()
+
+/obj/item/projectile/beam/beam_rifle/proc/AOE(turf/epicenter)
+ set waitfor = FALSE
+ if(!epicenter)
+ return
+ new /obj/effect/temp_visual/explosion/fast(epicenter)
+ for(var/mob/living/L in range(aoe_mob_range, epicenter)) //handle aoe mob damage
+ L.adjustFireLoss(aoe_mob_damage)
+ to_chat(L, "\The [src] sears you!")
+ for(var/turf/T in range(aoe_fire_range, epicenter)) //handle aoe fire
+ if(prob(aoe_fire_chance))
+ new /obj/effect/hotspot(T)
+ for(var/obj/O in range(aoe_structure_range, epicenter))
+ if(!isitem(O))
+ if(O.level == 1) //Please don't break underfloor items!
+ continue
+ O.take_damage(aoe_structure_damage * get_damage_coeff(O), BURN, "laser", FALSE)
+
+/obj/item/projectile/beam/beam_rifle/proc/check_pierce(atom/target)
+ if(!do_pierce)
+ return FALSE
+ if(pierced[target]) //we already pierced them go away
+ return TRUE
+ if(isclosedturf(target))
+ if(wall_pierce++ < wall_pierce_amount)
+ if(prob(wall_devastate))
+ if(iswallturf(target))
+ var/turf/closed/wall/W = target
+ W.dismantle_wall(TRUE, TRUE)
+ else
+ target.ex_act(EXPLODE_HEAVY)
+ return TRUE
+ if(ismovableatom(target))
+ var/atom/movable/AM = target
+ if(AM.density && !AM.CanPass(src, get_turf(target)) && !ismob(AM))
+ if(structure_pierce < structure_pierce_amount)
+ if(isobj(AM))
+ var/obj/O = AM
+ O.take_damage((impact_structure_damage + aoe_structure_damage) * structure_bleed_coeff * get_damage_coeff(AM), BURN, "energy", FALSE)
+ pierced[AM] = TRUE
+ structure_pierce++
+ return TRUE
+ return FALSE
+
+/obj/item/projectile/beam/beam_rifle/proc/get_damage_coeff(atom/target)
+ if(istype(target, /obj/machinery/door))
+ return 0.4
+ if(istype(target, /obj/structure/window))
+ return 0.5
+ if(istype(target, /obj/structure/blob))
+ return 0.65 //CIT CHANGE.
+ return 1
+
+/obj/item/projectile/beam/beam_rifle/proc/handle_impact(atom/target)
+ if(isobj(target))
+ var/obj/O = target
+ O.take_damage(impact_structure_damage * get_damage_coeff(target), BURN, "laser", FALSE)
+ if(isliving(target))
+ var/mob/living/L = target
+ L.adjustFireLoss(impact_direct_damage)
+ L.emote("scream")
+
+/obj/item/projectile/beam/beam_rifle/proc/handle_hit(atom/target)
+ set waitfor = FALSE
+ if(!cached && !QDELETED(target))
+ cached = get_turf(target)
+ if(nodamage)
+ return FALSE
+ playsound(cached, 'sound/effects/explosion3.ogg', 100, 1)
+ AOE(cached)
+ if(!QDELETED(target))
+ handle_impact(target)
+
+/obj/item/projectile/beam/beam_rifle/Bump(atom/target)
+ if(check_pierce(target))
+ permutated += target
+ trajectory_ignore_forcemove = TRUE
+ forceMove(target.loc)
+ trajectory_ignore_forcemove = FALSE
+ return FALSE
+ if(!QDELETED(target))
+ cached = get_turf(target)
+ . = ..()
+
+/obj/item/projectile/beam/beam_rifle/on_hit(atom/target, blocked = FALSE)
+ if(!QDELETED(target))
+ cached = get_turf(target)
+ handle_hit(target)
+ . = ..()
+
+/obj/item/projectile/beam/beam_rifle/hitscan
+ icon_state = ""
+ hitscan = TRUE
+ tracer_type = /obj/effect/projectile/tracer/tracer/beam_rifle
+ var/constant_tracer = FALSE
+
+/obj/item/projectile/beam/beam_rifle/hitscan/generate_hitscan_tracers(cleanup = TRUE, duration = 5, impacting = TRUE, highlander)
+ set waitfor = FALSE
+ if(isnull(highlander))
+ highlander = constant_tracer
+ if(highlander && istype(gun))
+ QDEL_LIST(gun.current_tracers)
+ for(var/datum/point/p in beam_segments)
+ gun.current_tracers += generate_tracer_between_points(p, beam_segments[p], tracer_type, color, 0, hitscan_light_range, hitscan_light_color_override, hitscan_light_intensity)
+ else
+ for(var/datum/point/p in beam_segments)
+ generate_tracer_between_points(p, beam_segments[p], tracer_type, color, duration, hitscan_light_range, hitscan_light_color_override, hitscan_light_intensity)
+ if(cleanup)
+ QDEL_LIST(beam_segments)
+ beam_segments = null
+ QDEL_NULL(beam_index)
+
+/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam
+ tracer_type = /obj/effect/projectile/tracer/tracer/aiming
+ name = "aiming beam"
+ hitsound = null
+ hitsound_wall = null
+ nodamage = TRUE
+ damage = 0
+ constant_tracer = TRUE
+ hitscan_light_range = 0
+ hitscan_light_intensity = 0
+ hitscan_light_color_override = "#99ff99"
+
+/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/prehit(atom/target)
+ qdel(src)
+ return FALSE
+
+/obj/item/projectile/beam/beam_rifle/hitscan/aiming_beam/on_hit()
+ qdel(src)
+ return FALSE
diff --git a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
index 254b9d4a..0a57d5b7 100644
--- a/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
+++ b/code/modules/reagents/chemistry/reagents/toxin_reagents.dm
@@ -200,7 +200,8 @@
pH = 11
/datum/reagent/toxin/mindbreaker/on_mob_life(mob/living/carbon/M)
- M.hallucination += 5
+ if(!M.has_quirk(/datum/quirk/insanity))
+ M.hallucination += 5
return ..()
/datum/reagent/toxin/plantbgone
diff --git a/code/modules/research/xenobiology/crossbreeding/_status_effects.dm b/code/modules/research/xenobiology/crossbreeding/_status_effects.dm
index eba26ad2..8b8cd096 100644
--- a/code/modules/research/xenobiology/crossbreeding/_status_effects.dm
+++ b/code/modules/research/xenobiology/crossbreeding/_status_effects.dm
@@ -64,10 +64,9 @@
var/interrupted = FALSE
var/mob/target
var/icon/bluespace
- var/datum/weakref/redirect_component
/datum/status_effect/slimerecall/on_apply()
- redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/resistField))))
+ RegisterSignal(owner, COMSIG_LIVING_RESIST, .proc/resistField)
to_chat(owner, "You feel a sudden tug from an unknown force, and feel a pull to bluespace!")
to_chat(owner, "Resist if you wish avoid the force!")
bluespace = icon('icons/effects/effects.dmi',"chronofield")
@@ -77,9 +76,9 @@
/datum/status_effect/slimerecall/proc/resistField()
interrupted = TRUE
owner.remove_status_effect(src)
+
/datum/status_effect/slimerecall/on_remove()
- qdel(redirect_component.resolve())
- redirect_component = null
+ UnregisterSignal(owner, COMSIG_LIVING_RESIST)
owner.cut_overlay(bluespace)
if(interrupted || !ismob(target))
to_chat(owner, "The bluespace tug fades away, and you feel that the force has passed you by.")
@@ -98,10 +97,9 @@
duration = -1 //Will remove self when block breaks.
alert_type = /obj/screen/alert/status_effect/freon/stasis
var/obj/structure/ice_stasis/cube
- var/datum/weakref/redirect_component
/datum/status_effect/frozenstasis/on_apply()
- redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/breakCube))))
+ RegisterSignal(owner, COMSIG_LIVING_RESIST, .proc/breakCube)
cube = new /obj/structure/ice_stasis(get_turf(owner))
owner.forceMove(cube)
owner.status_flags |= GODMODE
@@ -118,8 +116,7 @@
if(cube)
qdel(cube)
owner.status_flags &= ~GODMODE
- qdel(redirect_component.resolve())
- redirect_component = null
+ UnregisterSignal(owner, COMSIG_LIVING_RESIST)
/datum/status_effect/slime_clone
id = "slime_cloned"
diff --git a/code/modules/research/xenobiology/xenobio_camera.dm b/code/modules/research/xenobiology/xenobio_camera.dm
index d0a924ee..9de6384a 100644
--- a/code/modules/research/xenobiology/xenobio_camera.dm
+++ b/code/modules/research/xenobiology/xenobio_camera.dm
@@ -24,8 +24,6 @@
circuit = /obj/item/circuitboard/computer/xenobiology
var/datum/action/innate/hotkey_help/hotkey_help
- var/datum/component/redirect/listener
-
var/obj/machinery/monkey_recycler/connected_recycler
var/list/stored_slimes
var/obj/item/slimepotion/slime/current_potion
@@ -41,7 +39,7 @@
. = ..()
hotkey_help = new
stored_slimes = list()
- listener = AddComponent(/datum/component/redirect, list(COMSIG_ATOM_CONTENTS_DEL = CALLBACK(src, .proc/on_contents_del)))
+ RegisterSignal(src, COMSIG_ATOM_CONTENTS_DEL, .proc/on_contents_del)
for(var/obj/machinery/monkey_recycler/recycler in GLOB.monkey_recyclers)
if(get_area(src) == get_area(recycler))
connected_recycler = recycler
diff --git a/code/modules/surgery/organs/vocal_cords.dm b/code/modules/surgery/organs/vocal_cords.dm
index 3f616d5a..309e554e 100644
--- a/code/modules/surgery/organs/vocal_cords.dm
+++ b/code/modules/surgery/organs/vocal_cords.dm
@@ -254,7 +254,8 @@
var/static/regex/clap_words = regex("clap|applaud")
var/static/regex/honk_words = regex("ho+nk") //hooooooonk
var/static/regex/multispin_words = regex("like a record baby|right round")
- var/static/regex/orgasm_words = regex("cum|orgasm|climax|squirt|heyo") //CITADEL CHANGE
+ var/static/regex/family_friendly_words = regex("family") //Hyper change
+ //var/static/regex/orgasm_words = regex("cum|orgasm|climax|squirt|heyo") //CITADEL CHANGE
var/static/regex/dab_words = regex("dab|mood") //CITADEL CHANGE
var/static/regex/snap_words = regex("snap") //CITADEL CHANGE
var/static/regex/bwoink_words = regex("what the fuck are you doing|bwoink|hey you got a moment?") //CITADEL CHANGE
@@ -572,6 +573,7 @@
var/mob/living/L = V
L.SpinAnimation(speed = 10, loops = 5)
+ /* Yeah nah fam.
//CITADEL CHANGES
//ORGASM
else if((findtext(message, orgasm_words)))
@@ -580,6 +582,13 @@
var/mob/living/carbon/human/H = V
if(H.canbearoused && H.has_dna() && HAS_TRAIT(H, TRAIT_NYMPHO)) // probably a redundant check but for good measure
H.mob_climax(forced_climax=TRUE)
+ */
+ else if((findtext(message, family_friendly_words)))
+ cooldown = COOLDOWN_MEME
+ for(var/V in listeners)
+ var/mob/living/M = V
+ M.say(pick("You don't turn your back on family.","...Even when they do."))
+ SEND_SOUND(M, sound('hyperstation/sound/misc/family.ogg',volume=75))
//DAB
else if((findtext(message, dab_words)))
diff --git a/code/modules/unit_tests/_unit_tests.dm b/code/modules/unit_tests/_unit_tests.dm
index c739d426..aae422bc 100644
--- a/code/modules/unit_tests/_unit_tests.dm
+++ b/code/modules/unit_tests/_unit_tests.dm
@@ -1,13 +1,13 @@
-//include unit test files in this module in this ifdef
-//Keep this sorted alphabetically
-
-#ifdef UNIT_TESTS
-#include "anchored_mobs.dm"
-#include "component_tests.dm"
-#include "reagent_id_typos.dm"
-#include "reagent_recipe_collisions.dm"
-#include "spawn_humans.dm"
-#include "subsystem_init.dm"
-#include "timer_sanity.dm"
-#include "unit_test.dm"
-#endif
+//include unit test files in this module in this ifdef
+//Keep this sorted alphabetically
+
+#ifdef UNIT_TESTS
+#include "anchored_mobs.dm"
+#include "component_tests.dm"
+#include "reagent_id_typos.dm"
+#include "reagent_recipe_collisions.dm"
+#include "spawn_humans.dm"
+#include "subsystem_init.dm"
+#include "timer_sanity.dm"
+#include "unit_test.dm"
+#endif
diff --git a/code/modules/unit_tests/component_tests.dm b/code/modules/unit_tests/component_tests.dm
new file mode 100644
index 00000000..409d7f43
--- /dev/null
+++ b/code/modules/unit_tests/component_tests.dm
@@ -0,0 +1,12 @@
+/datum/unit_test/component_duping/Run()
+ var/list/bad_dms = list()
+ var/list/bad_dts = list()
+ for(var/t in typesof(/datum/component))
+ var/datum/component/comp = t
+ if(!isnum(initial(comp.dupe_mode)))
+ bad_dms += t
+ var/dupe_type = initial(comp.dupe_type)
+ if(dupe_type && !ispath(dupe_type))
+ bad_dts += t
+ if(length(bad_dms) || length(bad_dts))
+ Fail("Components with invalid dupe modes: ([bad_dms.Join(",")]) ||| Components with invalid dupe types: ([bad_dts.Join(",")])")
\ No newline at end of file
diff --git a/hyperstation/code/game/machinery/lore_terminal.dm b/hyperstation/code/game/machinery/lore_terminal.dm
index 7381b128..d2510224 100644
--- a/hyperstation/code/game/machinery/lore_terminal.dm
+++ b/hyperstation/code/game/machinery/lore_terminal.dm
@@ -1,7 +1,7 @@
GLOBAL_DATUM_INIT(lore_terminal_controller, /datum/lore_controller, new)
/obj/machinery/computer/lore_terminal
- name = "Staff Seegson info-link terminal"
+ name = "Staff info-link terminal"
desc = "A small CRT display with an inbuilt microcomputer which is loaded with an extensive database. These terminals contain eveyrthing from information about historical events to instruction manuals for common ship appliances."
icon = 'nsv13/icons/obj/computers.dmi'
icon_state = "terminal"
@@ -9,16 +9,21 @@ GLOBAL_DATUM_INIT(lore_terminal_controller, /datum/lore_controller, new)
density = FALSE
anchored = TRUE
idle_power_usage = 15
- var/access_tag = "ntcommon" //Every subtype of this type will be readable by this console. Use this for away terms as seen here \/
+ var/access_tag = "kncommon" //Every subtype of this type will be readable by this console. Use this for away terms as seen here \/
var/list/entries = list() //Every entry that we've got.
var/in_use = FALSE //Stops sound spam
var/datum/looping_sound/computer_click/soundloop
/obj/machinery/computer/lore_terminal/command //Put sensitive information on this one
- name = "Command Seegson info-link terminal"
- access_tag = "ntcommand"
+ name = "Command info-link terminal"
+ access_tag = "kncommand"
req_access = list(ACCESS_HEADS)
+/obj/machinery/computer/lore_terminal/security
+ name = "Security info-link terminal"
+ access_tag = "knsecurity"
+ req_access = list(ACCESS_SECURITY)
+
/obj/machinery/computer/lore_terminal/awaymission //Example for having a terminal preloaded with only a set list of files.
access_tag = "awaymission_default"
@@ -201,12 +206,12 @@ SPECIAL KEYS RESPOND AS FOLLOWS:
name = "new_employees_memo.mail"
title = "Intercepted message"
path = "lore_entries/welcome.txt"
- access_tag = "ntcommon"
+ access_tag = "kncommon"
/datum/lore_entry/all
name = "nuclear_authdisk_instructions.mail"
title = "Handling the Nuclear Authentication Disk and You!"
- content = "SYSADMIN -> allcrew@seegnet.kin. RE: The Nuclear Authentication Disk. ` Greetings staff members! We're aware of the questions you have in regards to the Nuclear Authentication disk. The disk itself contains the codes needed to unlock nuclear devices used in a Nuclear Emergency and trigger a station self-destruction sequence. ` It is the duty of every member of this crew to take responsibility for the disk in the off chance that station command is currently absent. ` Don't leave it lying in the Captain's office. ` Keep it in movement to prevent Syndicate triangulation devices from functioning. ` If the disk location is unknown, look for a red pinpointer, the Head of Security and the Captain should always have one in their offices or lockers. These will help you locate the disk. ` If the disk is in enemy hands, call all hands on deck immediately and order a red alert. ` ` Protect the disk with your life, for the lives of the station's crew depend on it. Stay safe through vigilance."
+ content = "SYSADMIN -> allcrew@seegnet.kin. RE: The Nuclear Authentication Disk. ` Greetings staff members! We're aware of the questions you have in regards to the Nuclear Authentication disk. The disk itself contains the codes needed to unlock nuclear devices used in a Nuclear Emergency and trigger a station self-destruction sequence. ` It is the duty of every member of this crew to take responsibility for the disk in the off chance that station command is currently absent. ` Even though Layenia itself is a mobile facility and prevents Disk Triangulation in most circumstances, it is still important to hold onto the disk even when not needed- it is a good formality and keeps things secure! ` If the disk location is unknown, look for a red pinpointer, the Head of Security and the Captain should always have one in their offices or lockers. These will help you locate the disk. ` If the disk is in enemy hands, call all hands on deck immediately and order a red alert. ` ` Protect the disk with your life, for the lives of the station's crew depend on it. Stay safe through vigilance."
access_tag = "all"
/datum/lore_entry/all/meltdown_proceedures
@@ -217,7 +222,7 @@ SPECIAL KEYS RESPOND AS FOLLOWS:
/datum/lore_entry/command
name = "command_memo.mail"
title = "Intercepted Message"
- access_tag = "ntcommand"
+ access_tag = "kncommand"
classified = "Restricted"
content = "SYSADMIN -> command@seegnet.kin. RE: Orientation. ` Greetings station command staff, congratulations on your placement! It is now company policy to attend all briefings as issued by centcom staff. Please speak to your centcom officer for clarification on the new procedures."
@@ -238,3 +243,54 @@ SPECIAL KEYS RESPOND AS FOLLOWS:
/datum/lore_entry/away_example/weapons_log
name = "weapon_systems_dump2259/11/25.txt"
content = "Life support systems terminated. Railgun system status: A6E3. Torpedo system status: ~@##6#6#^^6 -=File Access Terminated=-"
+
+/datum/lore_entry/security
+ name = "usage_and_terms.memo"
+ title = "Usage and Terms"
+ access_tag = "knsecurity"
+ path = "lore_entries/security/usageandterms.txt"
+
+/datum/lore_entry/security/introduction
+ name = "introduction.memo"
+ title = "Security Introduction"
+ path = "lore_entries/security/introduction.txt"
+
+/datum/lore_entry/security/basicgearandyou
+ name = "gearbasics.memo"
+ title = "Basic Gear and You"
+ path = "lore_entries/security/basicgearandyou.txt"
+
+/datum/lore_entry/security/advancedgearandyou
+ name = "gearadvanced.memo"
+ title = "Advanced Gear and You"
+ path = "lore_entries/security/advancedgearandyou.txt"
+
+/datum/lore_entry/security/defensivegearandyou
+ name = "geardefensive.memo"
+ title = "Defensive Gear and You"
+ path = "lore_entries/security/defensivegearandyou.txt"
+
+/datum/lore_entry/security/sop
+ name = "standard_operating_procedure.txt"
+ title = "Standard Operating Procedure"
+ path = "lore_entries/security/wip.txt"
+
+/datum/lore_entry/security/lowcrime
+ name = "low_infractions.txt"
+ title = "Minor Infractions"
+ path = "lore_entries/security/wip.txt"
+
+/datum/lore_entry/security/mediumcrime
+ name = "medium_infractions.txt"
+ title = "Medium-risk Infractions"
+ path = "lore_entries/security/wip.txt"
+
+/datum/lore_entry/security/highcrime
+ name = "high_infractions.txt"
+ title = "Dangerous Infractions"
+ path = "lore_entries/security/wip.txt"
+
+/datum/lore_entry/security/deltacrime
+ name = "delta_infractions.txt"
+ title = "Zealot-class Notice and Warning"
+ path = "lore_entries/security/wip.txt"
\ No newline at end of file
diff --git a/hyperstation/code/game/objects/structures/sauna_oven.dm b/hyperstation/code/game/objects/structures/sauna_oven.dm
new file mode 100644
index 00000000..64727606
--- /dev/null
+++ b/hyperstation/code/game/objects/structures/sauna_oven.dm
@@ -0,0 +1,120 @@
+#define SAUNA_H2O_TEMP T20C + 20
+#define SAUNA_LOG_FUEL 150
+#define SAUNA_PAPER_FUEL 5
+#define SAUNA_MAXIMUM_FUEL 3000
+#define SAUNA_WATER_PER_WATER_UNIT 5
+
+/obj/structure/sauna_oven
+ name = "sauna oven"
+ desc = "A modest sauna oven with rocks. Add some fuel, pour some water and enjoy the moment."
+ icon = 'hyperstation/icons/obj/structures/sauna_oven.dmi'
+ icon_state = "sauna_oven"
+ density = TRUE
+ anchored = TRUE
+ resistance_flags = FIRE_PROOF
+ var/lit = FALSE
+ var/fuel_amount = 0
+ var/water_amount = 0
+
+/obj/structure/sauna_oven/examine(mob/user)
+ . = ..()
+ . += "The rocks are [water_amount ? "moist" : "dry"]."
+ . += "There's [fuel_amount ? "some fuel" : "no fuel"] in the oven."
+
+/obj/structure/sauna_oven/Destroy()
+ if(lit)
+ STOP_PROCESSING(SSobj, src)
+ return ..()
+
+/obj/structure/sauna_oven/attack_hand(mob/user)
+ . = ..()
+ if(.)
+ return
+ if(lit)
+ lit = FALSE
+ STOP_PROCESSING(SSobj, src)
+ user.visible_message("[user] turns on [src].", "You turn on [src].")
+ else if (fuel_amount)
+ lit = TRUE
+ START_PROCESSING(SSobj, src)
+ user.visible_message("[user] turns off [src].", "You turn off [src].")
+ update_icon()
+
+/obj/structure/sauna_oven/update_overlays()
+ . = ..()
+ if(lit)
+ . += "sauna_oven_on_overlay"
+
+/obj/structure/sauna_oven/update_icon()
+ ..()
+ icon_state = "[lit ? "sauna_oven_on" : initial(icon_state)]"
+
+/obj/structure/sauna_oven/attackby(obj/item/T, mob/user)
+ if(T.tool_behaviour == TOOL_WRENCH)
+ to_chat(user, "You begin to deconstruct [src].")
+ if(T.use_tool(src, user, 60, volume=50))
+ to_chat(user, "You successfully deconstructed [src].")
+ new /obj/item/stack/sheet/mineral/wood(get_turf(src), 30)
+ qdel(src)
+ return TRUE
+
+ else if(istype(T, /obj/item/reagent_containers))
+ var/obj/item/reagent_containers/reagent_container = T
+ if(!reagent_container.is_open_container())
+ return ..()
+ if(reagent_container.reagents.has_reagent(/datum/reagent/water))
+ reagent_container.reagents.remove_reagent(/datum/reagent/water, 5)
+ user.visible_message("[user] pours some \
+ water into [src].", "You pour \
+ some water to [src].")
+ water_amount += 5 * SAUNA_WATER_PER_WATER_UNIT
+ return TRUE
+ else
+ to_chat(user, "There's no water in [reagent_container]")
+ return FALSE
+
+ else if(istype(T, /obj/item/stack/sheet/mineral/wood))
+ var/obj/item/stack/sheet/mineral/wood/wood = T
+ if(fuel_amount > SAUNA_MAXIMUM_FUEL)
+ to_chat(user, "You can't fit any more of [T] in [src]!")
+ return FALSE
+ fuel_amount += SAUNA_LOG_FUEL * wood.amount
+ wood.use(wood.amount)
+ user.visible_message("[user] tosses some \
+ wood into [src].", "You add \
+ some fuel to [src].")
+ return TRUE
+ else if(istype(T, /obj/item/paper_bin))
+ var/obj/item/paper_bin/paper_bin = T
+ user.visible_message("[user] throws [T] into \
+ [src].", "You add [T] to [src].\
+ ")
+ fuel_amount += SAUNA_PAPER_FUEL * paper_bin.total_paper
+ qdel(paper_bin)
+ return TRUE
+ else if(istype(T, /obj/item/paper))
+ user.visible_message("[user] throws [T] into \
+ [src].", "You throw [T] into [src].\
+ ")
+ fuel_amount += SAUNA_PAPER_FUEL
+ qdel(T)
+ return TRUE
+ return ..()
+
+/obj/structure/sauna_oven/process()
+ if(water_amount)
+ water_amount--
+ var/turf/pos = get_turf(src)
+ if(pos)
+ pos.atmos_spawn_air("water_vapor=10;TEMP=[SAUNA_H2O_TEMP]")
+ fuel_amount--
+ if(fuel_amount <= 0)
+ lit = FALSE
+ STOP_PROCESSING(SSobj, src)
+ update_icon()
+
+#undef SAUNA_H2O_TEMP
+#undef SAUNA_LOG_FUEL
+#undef SAUNA_PAPER_FUEL
+#undef SAUNA_MAXIMUM_FUEL
+#undef SAUNA_WATER_PER_WATER_UNIT
diff --git a/hyperstation/code/obj/leash.dm b/hyperstation/code/obj/leash.dm
index cc057c92..46dcc35c 100644
--- a/hyperstation/code/obj/leash.dm
+++ b/hyperstation/code/obj/leash.dm
@@ -35,7 +35,7 @@ Icons, maybe?
/datum/status_effect/leash_pet
id = "leashed"
status_type = STATUS_EFFECT_UNIQUE
- var/datum/weakref/redirect_component
+ var/mob/redirect_component
alert_type = /obj/screen/alert/status_effect/leash_pet
/obj/screen/alert/status_effect/leash_pet
@@ -45,7 +45,9 @@ Icons, maybe?
/datum/status_effect/leash_pet/on_apply()
- redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/owner_resist))))
+ //redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/owner_resist))))
+ RegisterSignal(owner, COMSIG_LIVING_RESIST, .proc/owner_resist)
+ redirect_component = owner
if(!owner.stat)
to_chat(owner, "You have been leashed!")
return ..()
@@ -80,9 +82,9 @@ Icons, maybe?
var/leash_used = 0 //A flag to see if the leash has been used yet, because for some reason picking up an unused leash is weird
var/mob/living/leash_pet = "null" //Variable to store our pet later
var/mob/living/leash_master = "null" //And our master too
- var/datum/component/mobhook_leash_pet
- var/datum/component/mobhook_leash_master //Needed to watch for these entities to move
- var/datum/component/mobhook_leash_freepet
+ var/mob/mobhook_leash_pet
+ var/mob/mobhook_leash_master //Needed to watch for these entities to move
+ var/mob/mobhook_leash_freepet
var/leash_location[3] //Three digit list for us to store coordinates later
//Called when someone is clicked with the leash
@@ -101,8 +103,12 @@ Icons, maybe?
user.apply_status_effect(/datum/status_effect/leash_dom) //Is the leasher
leash_pet = C //Save pet reference for later
leash_master = user //Save dom reference for later
- mobhook_leash_pet = leash_pet.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_pet_move)))
- mobhook_leash_master = leash_master.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_master_move)))
+ //mobhook_leash_pet = leash_pet.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_pet_move)))
+ RegisterSignal(leash_pet, COMSIG_MOVABLE_MOVED, .proc/on_pet_move)
+ mobhook_leash_pet = leash_pet
+ //mobhook_leash_master = leash_master.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_master_move)))
+ RegisterSignal(leash_master, COMSIG_MOVABLE_MOVED, .proc/on_master_move)
+ mobhook_leash_master = leash_master
leash_used = 1
if(!leash_pet.has_status_effect(/datum/status_effect/leash_dom)) //Add slowdown if the pet didn't leash themselves
leash_pet.add_movespeed_modifier(MOVESPEED_ID_LEASH, multiplicative_slowdown = 5)
@@ -126,9 +132,12 @@ Icons, maybe?
leash_pet.remove_status_effect(/datum/status_effect/leash_pet)
if(!leash_pet.has_status_effect(/datum/status_effect/leash_pet)) //If there is no pet, there is no dom. Loop breaks.
- QDEL_NULL(mobhook_leash_master)
- QDEL_NULL(mobhook_leash_pet)
- QDEL_NULL(mobhook_leash_freepet)
+ //QDEL_NULL(mobhook_leash_master)
+ UnregisterSignal(mobhook_leash_master, COMSIG_MOVABLE_MOVED)
+ //QDEL_NULL(mobhook_leash_pet)
+ UnregisterSignal(mobhook_leash_pet, COMSIG_MOVABLE_MOVED)
+ //QDEL_NULL(mobhook_leash_freepet)
+ UnregisterSignal(mobhook_leash_freepet, COMSIG_MOVABLE_MOVED)
if(leash_pet.has_status_effect(/datum/status_effect/leash_freepet))
leash_pet.remove_status_effect(/datum/status_effect/leash_freepet)
if(leash_pet.has_movespeed_modifier(MOVESPEED_ID_LEASH))
@@ -183,7 +192,8 @@ Icons, maybe?
if(leash_pet == leash_master) //Pet is the master
return
if(!leash_pet.has_status_effect(/datum/status_effect/leash_pet))
- QDEL_NULL(mobhook_leash_master) //Probably redundant, but it's nice to be safe
+ //QDEL_NULL(mobhook_leash_master) //Probably redundant, but it's nice to be safe
+ UnregisterSignal(mobhook_leash_master, COMSIG_MOVABLE_MOVED)
leash_master.remove_status_effect(/datum/status_effect/leash_dom)
return
@@ -252,8 +262,10 @@ Icons, maybe?
leash_pet.remove_status_effect(/datum/status_effect/leash_pet)
leash_pet.remove_movespeed_modifier(MOVESPEED_ID_LEASH)
leash_master.remove_status_effect(/datum/status_effect/leash_dom)
- QDEL_NULL(mobhook_leash_master)
- QDEL_NULL(mobhook_leash_pet)
+ //QDEL_NULL(mobhook_leash_master)
+ UnregisterSignal(mobhook_leash_master, COMSIG_MOVABLE_MOVED)
+ //QDEL_NULL(mobhook_leash_pet)
+ UnregisterSignal(mobhook_leash_pet, COMSIG_MOVABLE_MOVED)
leash_pet = "null"
leash_master = "null"
leash_used = 0
@@ -267,7 +279,8 @@ Icons, maybe?
return
//Make sure the pet is still a pet
if(!leash_pet.has_status_effect(/datum/status_effect/leash_pet))
- QDEL_NULL(mobhook_leash_pet) //Probably redundant, but it's nice to be safe
+ //QDEL_NULL(mobhook_leash_pet) //Probably redundant, but it's nice to be safe
+ UnregisterSignal(mobhook_leash_pet, COMSIG_MOVABLE_MOVED)
return
//The pet has escaped. There is no DOM. GO PET RUN.
@@ -356,8 +369,10 @@ Icons, maybe?
leash_pet.adjustOxyLoss(5)
leash_pet.remove_status_effect(/datum/status_effect/leash_pet)
leash_pet.remove_status_effect(/datum/status_effect/leash_freepet)
- QDEL_NULL(mobhook_leash_pet)
- QDEL_NULL(mobhook_leash_freepet)
+ //QDEL_NULL(mobhook_leash_pet)
+ UnregisterSignal(mobhook_leash_pet, COMSIG_MOVABLE_MOVED)
+ //QDEL_NULL(mobhook_leash_freepet)
+ UnregisterSignal(mobhook_leash_freepet, COMSIG_MOVABLE_MOVED)
leash_pet = "null"
leash_used = 0
@@ -375,10 +390,13 @@ Icons, maybe?
viewing.show_message("[leash_master] has dropped the leash.", 1)
//DOM HAS DROPPED LEASH. PET IS FREE. SCP HAS BREACHED CONTAINMENT.
leash_pet.remove_movespeed_modifier(MOVESPEED_ID_LEASH)
- mobhook_leash_freepet = leash_pet.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_freepet_move)))
+ //mobhook_leash_freepet = leash_pet.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_freepet_move)))
+ RegisterSignal(leash_pet, COMSIG_MOVABLE_MOVED, .proc/on_freepet_move)
+ mobhook_leash_freepet = leash_pet
leash_master.remove_status_effect(/datum/status_effect/leash_dom) //No dom with no leash. We will get a new dom if the leash is picked back up.
leash_master = "null"
- QDEL_NULL(mobhook_leash_master)
+ //QDEL_NULL(mobhook_leash_master)
+ UnregisterSignal(mobhook_leash_master, COMSIG_MOVABLE_MOVED)
/obj/item/leash/equipped(mob/user)
. = ..()
@@ -392,9 +410,12 @@ Icons, maybe?
leash_master = "null"
return
leash_master.apply_status_effect(/datum/status_effect/leash_dom)
- mobhook_leash_master = leash_master.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_master_move)))
+ //mobhook_leash_master = leash_master.AddComponent(/datum/component/redirect, list(COMSIG_MOVABLE_MOVED = CALLBACK(src, .proc/on_master_move)))
+ RegisterSignal(leash_master, COMSIG_MOVABLE_MOVED, .proc/on_master_move)
+ mobhook_leash_master = leash_master
leash_pet.remove_status_effect(/datum/status_effect/leash_freepet)
- QDEL_NULL(mobhook_leash_freepet)
+ //QDEL_NULL(mobhook_leash_freepet)
+ UnregisterSignal(mobhook_leash_freepet, COMSIG_MOVABLE_MOVED)
leash_pet.add_movespeed_modifier(MOVESPEED_ID_LEASH, multiplicative_slowdown = 5)
/datum/crafting_recipe/leash
@@ -403,4 +424,4 @@ Icons, maybe?
time = 40
reqs = list(/obj/item/stack/sheet/metal = 1,
/obj/item/stack/sheet/cloth = 3)
- category = CAT_MISC
\ No newline at end of file
+ category = CAT_MISC
diff --git a/hyperstation/icons/obj/structures/sauna_oven.dmi b/hyperstation/icons/obj/structures/sauna_oven.dmi
new file mode 100644
index 00000000..fb0871ca
Binary files /dev/null and b/hyperstation/icons/obj/structures/sauna_oven.dmi differ
diff --git a/hyperstation/sound/misc/family.ogg b/hyperstation/sound/misc/family.ogg
new file mode 100644
index 00000000..39c97e7e
Binary files /dev/null and b/hyperstation/sound/misc/family.ogg differ
diff --git a/icons/obj/statue_egypty.dmi b/icons/obj/statue_egypty.dmi
new file mode 100644
index 00000000..3234f8bb
Binary files /dev/null and b/icons/obj/statue_egypty.dmi differ
diff --git a/icons/turf/walls/sandstone_wall.dmi b/icons/turf/walls/sandstone_wall.dmi
index 4118a3db..3eac01e9 100644
Binary files a/icons/turf/walls/sandstone_wall.dmi and b/icons/turf/walls/sandstone_wall.dmi differ
diff --git a/lore_entries/security/advancedgearandyou.txt b/lore_entries/security/advancedgearandyou.txt
new file mode 100644
index 00000000..7949e97b
--- /dev/null
+++ b/lore_entries/security/advancedgearandyou.txt
@@ -0,0 +1 @@
+SYSADMIN -> security@frontier.infolink.kin. Advanced Gear and You ` When threats start to intensify, standard gear may not work. As Layenia station is a recycled facility from NT subsystems, you don't have access to Holostasis Projectors and Blaze Javelins- however, there should be some noteworthy items in the armory should the threat level support it. ` ` DRAGnet ` A strong, versatile tool which is capable of teleporting those left within it's field once the charge is complete. This mode is semi-useless, however, it has an alternative fire which shoots an energy snare and trap. If it directly hits someone, it knocks them down and ties their legs together, making movement difficult. If it misses, it will deploy a trap on the ground that will snare anyone who steps on it, even yourself. Caution advised; please remember that this item may not work on animals and silicons. ` ` Blaster carbine ` An outdated and unreliable laser weapon to the likes of Kinaris's own, however it serves it's own purpose in light engagements. It's main firing mode is a disabler bolt of energy that is capable of slowly draining the stamina of a target. The alternate fire mode heats up the lasers intensely, causing them to be that much more lethal and burning. Avoid using this mode when unnecessary. Needs to be recharged after energy capacity is lost. ` ` Blaster rifle ` Similar to the carbine, this is a very old model of laser weaponry. However, it lacks a nonlethal option and has only one lethal firing mode. Because of this, it has a higher energy capacity and damage rate. Needs to be recharged after energy capacity is lost. ` ` Riot shotgun ` A pump-action shotgun that is not automatic. Load a round in, rack the shotgun, turn off the safety, and fire. Ammo types can be nonlethal beanbag slugs, which still do a slight amount of bruising, but aim to disable effectively with sheer stopping power compared to it's lethal counterpart. This weapon has a maximum ammo capacity of 6 at a time. Not to be confused with automatic combat shotguns, which don't need to be racked after it's been fired. ` ` Riot armor and shields ` A very bulky suit that is capable of stopping most blunt force in it's tracks. Best used with a shield, but it overall slows the wearer down. Not very worth it; you'd be better off trying not to tank damage. ` ` Reflector vest ` A worn vest with a toggle that is capable of reflecting energy projectiles from once they came. Ensure that the toggle is turned on, and the vest is applied properly. This will not protect against ballistics and melee. ` ` Ion rifle ` A bulky weapon that is capable of shooting ionized energy blasts that can disrupt mechanical subsystems and disable them in an area of effect. This is especially effective against cyborgs and mechs, as well as an augmented crew member. Otherwise, this may cause a lot of damage to the station itself. ` ` Security temperature gun ` A single-fire weapon that can blast either freezing-cold or blazing-hot waves of energy onto a target. This is especially effective against animals that struggle against extreme temperatures, such as using the cold mode on a slime. Be wary that it is lethal.
\ No newline at end of file
diff --git a/lore_entries/security/basicgearandyou.txt b/lore_entries/security/basicgearandyou.txt
new file mode 100644
index 00000000..43f1da58
--- /dev/null
+++ b/lore_entries/security/basicgearandyou.txt
@@ -0,0 +1 @@
+SYSADMIN -> security@frontier.infolink.kin. Basic Gear and You ` Not only must an SSP know what mindset to be in, they must also recognize the effects of their gear and items, as well as when they're needed. This section will cover some items, and how they can be useful given certain circumstances. Note that Layenia Station is using much older, and has access to less state-of-the-art technology, as it is using recycled Nanotrasen subsystems. ` ` Handcuffs ` A tool utilized for restraining criminals on the wrists. Apply on both wrists, fasten and lock. These should only be used when transporting prisoners, NOT when they're in a cell. Can only be applied on creatures with applicable limbs. ` ` Flash ` A device with a bright bulb, used to temporarily disorient visuals, both on cyborgs and living creatures. While harmless, extended use may result in eye damage. Using in hand will result in an area of flash, while using against another will flash that specific being. Useless against anything with flash protection ` ` Pepperspray ` A small nozzle used to spray irritant chemicals, most effective when used on the eyes of a living being who is not wearing eye protection. Otherwise, this item services as nothing more than an irritating spray. Can be refilled. ` ` Stunbaton ` An electrically charged rod with a prod on the end, which can be activated to deal incredible amounts of stamina drain. This is your primary melee-ranged tool, which should be applied to criminals approximately four times (size may vary, or until target is exhausted) followed up by handcuffing. Do not hit harmfully with this without just cause; requires a recharge after frequent use, and can be upgraded with better power cells. ` ` Flashbang ` A chemical payload that will prime upon activation, and will explode into a disorienting blast after a few seconds. Requires flash and ear protection to completely nullify it's effects, but being too close can override that. This is a prime tool for crowd control, and should only be used when it's absolutely necessary. Effective for dispersing crowds. ` ` Taser ` A handheld sidearm that is capable of launching an electric volt of energy which can temporarily stun and disarm most attackers via electric shock to the muscles. It can have it's firing mode switched to a disabler mode, which is capable of draining the stamina of the target, without the stun. Use only on creatures that aren't immune.
\ No newline at end of file
diff --git a/lore_entries/security/defensivegearandyou.txt b/lore_entries/security/defensivegearandyou.txt
new file mode 100644
index 00000000..c789909f
--- /dev/null
+++ b/lore_entries/security/defensivegearandyou.txt
@@ -0,0 +1 @@
+SYSADMIN - > security@frontier.infolink.kin Defensive Gear and You ` Sometimes, situations may call for a more defensive approach, especially when asset protection is kept in-mind. Layenia has access to some light defensive armaments within the station; it is not equipped with defensive battery cannons on the exterior. ` ` Barrier grenade ` These grenades are capable of deploying a barrier on it's location after explosion. The barrier itself cannot be clambered over, and can take quite a beating before it goes down. Effective for narrowing passageways. ` ` Portable flasher ` A bulky unit which can be bolted to the floor with a wrench, and will flash any fast-moving personnel within it's radius. Will not flash if people are walking by it. ` ` Security holobarrier projector ` A handheld device which can project a hardlight barrier- three total- at a location of choosing. It can be dispelled easily with the same device as well.
\ No newline at end of file
diff --git a/lore_entries/security/introduction.txt b/lore_entries/security/introduction.txt
new file mode 100644
index 00000000..f8926f32
--- /dev/null
+++ b/lore_entries/security/introduction.txt
@@ -0,0 +1 @@
+SYSADMIN -> security@frontier.infolink.kin. Introduction ` The act of securing and protection any Kinaris asset is not an easy one. Difficulty can range from monotanous and dreary, to outright hellish and overwhelming. It is a SSP's job to ensure that regardless of circumstance, they are both mentally and physically equipped to deal with any situation that may come up. This section will cover the very basics of what you need to know to be educated in the instance of standard security work. ` To act as a SSP, the first step would be to think like one. Sentient Security Personnel are equipped with a plethora of both resources and gear to apprehend criminals, as well an array of support from the station and heads alike. Do not betray your station's trust. Your job as an SSP should be- above all- securing peace. Before anything, you should always consider the outcome of your actions, and others' as well. A responsible SSP would understand when a good time to use a baton is, and when words will allow a better outcome. Lack of this proper resolve may result in uneasiness around your workplace, both from your team and those you are to protect. This is not only grounds for demotion when abuse is repeated, but may result in an abusive SSP's inevitable lynching. These effects can snowball into much worse; so ensure that you and your team are well-communicative, and are proper in terms of gear use and protocol. Catch problems at the source. Think like a proper SSP. ` Following up a proper mindset, it is important to note the infinite complexity that situations may involve themselves in. A responsible SSP will always keep in mind truths and lies when proposed with a situation, and must acknowledge that their guess can be wrong as well. Following Kinaris Security Protocol to the letter may also be problematic, due to the malleable nature that people can involve themselves within. Leeway is important to give when necessary, and a firm hand provided otherwise. Know when to apply proper protocol, and when to give leeway.
\ No newline at end of file
diff --git a/lore_entries/security/usageandterms.txt b/lore_entries/security/usageandterms.txt
new file mode 100644
index 00000000..4291ee2d
--- /dev/null
+++ b/lore_entries/security/usageandterms.txt
@@ -0,0 +1 @@
+SYSADMIN -> security@frontier.infolink.kin. Usage and Terms ` This specific protocol terminal refers to the processes and operation of Sentient Security Personnel (SSP) in regards to their workplace and behavior within reasonable operating conditions. The usage of this terminal is for both educational and referral purposes. Punishments given out by SSP should be based upon the data within this terminal. Note that these should be a baseline, and following to the letter may or may not be preffered. Case-by-case basis analysis is encouraged.
\ No newline at end of file
diff --git a/lore_entries/security/wip.txt b/lore_entries/security/wip.txt
new file mode 100644
index 00000000..3c829afd
--- /dev/null
+++ b/lore_entries/security/wip.txt
@@ -0,0 +1 @@
+SYSADMIN -> security@frontier.infolink.kin. Unauthorized Access ` File is currently undergoing approval via your local Central Command authority. Please seek previous methods for this specific file.
\ No newline at end of file
diff --git a/modular_citadel/code/datums/components/phantomthief.dm b/modular_citadel/code/datums/components/phantomthief.dm
deleted file mode 100644
index d34e16f6..00000000
--- a/modular_citadel/code/datums/components/phantomthief.dm
+++ /dev/null
@@ -1,49 +0,0 @@
-//This component applies a customizable drop_shadow filter to its wearer when they toggle combat mode on or off. This can stack.
-
-/datum/component/phantomthief
- dupe_mode = COMPONENT_DUPE_UNIQUE_PASSARGS
-
- var/filter_x
- var/filter_y
- var/filter_size
- var/filter_border
- var/filter_color
-
- var/datum/component/redirect/combattoggle_redir
-
-/datum/component/phantomthief/Initialize(_x = -2, _y = 0, _size = 0, _border = 0, _color = "#E62111")
- filter_x = _x
- filter_y = _y
- filter_size = _size
- filter_border = _border
- filter_color = _color
-
- RegisterSignal(parent, COMSIG_COMBAT_TOGGLED, .proc/handlefilterstuff)
- RegisterSignal(parent, COMSIG_ITEM_EQUIPPED, .proc/OnEquipped)
- RegisterSignal(parent, COMSIG_ITEM_DROPPED, .proc/OnDropped)
-
-/datum/component/phantomthief/proc/handlefilterstuff(mob/user, combatmodestate)
- if(istype(user))
- var/thefilter = filter(type = "drop_shadow", x = filter_x, y = filter_y, size = filter_size, border = filter_border, color = filter_color)
- if(!combatmodestate)
- user.filters -= thefilter
- else
- user.filters += thefilter
-
-/datum/component/phantomthief/proc/stripdesiredfilter(mob/user)
- if(istype(user))
- var/thefilter = filter(type = "drop_shadow", x = filter_x, y = filter_y, size = filter_size, border = filter_border, color = filter_color)
- user.filters -= thefilter
-
-/datum/component/phantomthief/proc/OnEquipped(mob/user, slot)
- if(!istype(user))
- return
- if(!combattoggle_redir)
- combattoggle_redir = user.AddComponent(/datum/component/redirect, list(COMSIG_COMBAT_TOGGLED = CALLBACK(src, .proc/handlefilterstuff)))
-
-/datum/component/phantomthief/proc/OnDropped(mob/user)
- if(!istype(user))
- return
- if(combattoggle_redir)
- QDEL_NULL(combattoggle_redir)
- stripdesiredfilter(user)
diff --git a/modular_citadel/code/datums/status_effects/chems.dm b/modular_citadel/code/datums/status_effects/chems.dm
index ef45e07b..a35a5f50 100644
--- a/modular_citadel/code/datums/status_effects/chems.dm
+++ b/modular_citadel/code/datums/status_effects/chems.dm
@@ -201,7 +201,6 @@
var/enthrallGender //Use master or mistress
var/mental_capacity //Higher it is, lower the cooldown on commands, capacity reduces with resistance.
- var/datum/weakref/redirect_component //resistance
var/distancelist = list(2,1.5,1,0.8,0.6,0.5,0.4,0.3,0.2) //Distance multipliers
@@ -231,7 +230,7 @@
master = get_mob_by_key(enthrallID)
//if(M.ckey == enthrallID)
// owner.remove_status_effect(src)//At the moment, a user can enthrall themselves, toggle this back in if that should be removed.
- redirect_component = WEAKREF(owner.AddComponent(/datum/component/redirect, list(COMSIG_LIVING_RESIST = CALLBACK(src, .proc/owner_resist)))) //Do resistance calc if resist is pressed#
+ RegisterSignal(owner, COMSIG_LIVING_RESIST, .proc/owner_resist) //Do resistance calc if resist is pressed#
RegisterSignal(owner, COMSIG_MOVABLE_HEAR, .proc/owner_hear)
//var/obj/item/organ/brain/B = M.getorganslot(ORGAN_SLOT_BRAIN) //removing this, may cause some issues unsure.
mental_capacity = 500 - M.getOrganLoss(ORGAN_SLOT_BRAIN)//It's their brain!
@@ -570,8 +569,7 @@
SEND_SIGNAL(M, COMSIG_CLEAR_MOOD_EVENT, "EnthMissing2")
SEND_SIGNAL(M, COMSIG_CLEAR_MOOD_EVENT, "EnthMissing3")
SEND_SIGNAL(M, COMSIG_CLEAR_MOOD_EVENT, "EnthMissing4")
- qdel(redirect_component.resolve())
- redirect_component = null
+ UnregisterSignal(M, COMSIG_LIVING_RESIST)
UnregisterSignal(owner, COMSIG_MOVABLE_HEAR)
REMOVE_TRAIT(owner, TRAIT_PACIFISM, "MKUltra")
to_chat(owner, "You're now free of [master]'s influence, and fully independent!'")
diff --git a/modular_citadel/code/modules/clothing/glasses/phantomthief.dm b/modular_citadel/code/modules/clothing/glasses/phantomthief.dm
index 716e33c7..669697c6 100644
--- a/modular_citadel/code/modules/clothing/glasses/phantomthief.dm
+++ b/modular_citadel/code/modules/clothing/glasses/phantomthief.dm
@@ -6,19 +6,18 @@
icon_state = "s-ninja"
item_state = "s-ninja"
-/obj/item/clothing/glasses/phantomthief/Initialize()
+/obj/item/clothing/glasses/phantomthief/ComponentInitialize()
. = ..()
- AddComponent(/datum/component/phantomthief)
+ AddComponent(/datum/component/wearertargeting/phantomthief)
/obj/item/clothing/glasses/phantomthief/syndicate
name = "suspicious plastic mask"
desc = "A cheap, bulky, Syndicate-branded plastic face mask. You have to break in to break out."
var/nextadrenalinepop
- var/datum/component/redirect/combattoggle_redir
-/obj/item/clothing/glasses/phantomthief/syndicate/examine(user)
+/obj/item/clothing/glasses/phantomthief/syndicate/examine(mob/user)
. = ..()
- if(combattoggle_redir)
+ if(user.get_item_by_slot(SLOT_GLASSES) == src)
if(world.time >= nextadrenalinepop)
. += "The built-in adrenaline injector is ready for use."
else
@@ -34,12 +33,12 @@
. = ..()
if(!istype(user))
return
- if(!combattoggle_redir)
- combattoggle_redir = user.AddComponent(/datum/component/redirect, list(COMSIG_COMBAT_TOGGLED = CALLBACK(src, .proc/injectadrenaline)))
+ if(slot != SLOT_GLASSES)
+ return
+ RegisterSignal(user, COMSIG_COMBAT_TOGGLED, .proc/injectadrenaline)
/obj/item/clothing/glasses/phantomthief/syndicate/dropped(mob/user)
. = ..()
if(!istype(user))
return
- if(combattoggle_redir)
- QDEL_NULL(combattoggle_redir)
+ UnregisterSignal(user, COMSIG_COMBAT_TOGGLED)
diff --git a/tgstation.dme b/tgstation.dme
index c95472b0..52811d1a 100644
--- a/tgstation.dme
+++ b/tgstation.dme
@@ -380,12 +380,12 @@
#include "code\datums\components\ntnet_interface.dm"
#include "code\datums\components\orbiter.dm"
#include "code\datums\components\paintable.dm"
+#include "code\datums\components\phantomthief.dm"
#include "code\datums\components\rad_insulation.dm"
#include "code\datums\components\radioactive.dm"
#include "code\datums\components\remote_materials.dm"
#include "code\datums\components\riding.dm"
#include "code\datums\components\rotation.dm"
-#include "code\datums\components\signal_redirect.dm"
#include "code\datums\components\sizzle.dm"
#include "code\datums\components\slippery.dm"
#include "code\datums\components\spawner.dm"
@@ -3071,6 +3071,7 @@
#include "hyperstation\code\game\objects\items\cosmetics.dm"
#include "hyperstation\code\game\objects\items\storage\big_bag.dm"
#include "hyperstation\code\game\objects\structures\ghost_role_spawners.dm"
+#include "hyperstation\code\game\objects\structures\sauna_oven.dm"
#include "hyperstation\code\gamemode\traitor_lewd.dm"
#include "hyperstation\code\gamemode\traitor_thief.dm"
#include "hyperstation\code\gamemode\werewolf\werewolf.dm"
@@ -3124,8 +3125,8 @@
#include "hyperstation\code\modules\power\reactor\rbmk.dm"
#include "hyperstation\code\modules\power\reactor\reactor_cargo.dm"
#include "hyperstation\code\modules\reagents\chemistry\reagents\food_reagents.dm"
-#include "hyperstation\code\modules\reagents\chemistry\reagents\medicine_reagents.dm"
#include "hyperstation\code\modules\reagents\chemistry\reagents\hydroponics_reactions.dm"
+#include "hyperstation\code\modules\reagents\chemistry\reagents\medicine_reagents.dm"
#include "hyperstation\code\modules\reagents\chemistry\recipes\medicine.dm"
#include "hyperstation\code\modules\resize\resize_action.dm"
#include "hyperstation\code\modules\resize\resizing.dm"
@@ -3169,7 +3170,6 @@
#include "modular_citadel\code\controllers\configuration\entries\general.dm"
#include "modular_citadel\code\controllers\subsystem\job.dm"
#include "modular_citadel\code\datums\components\material_container.dm"
-#include "modular_citadel\code\datums\components\phantomthief.dm"
#include "modular_citadel\code\datums\components\souldeath.dm"
#include "modular_citadel\code\datums\mood_events\chem_events.dm"
#include "modular_citadel\code\datums\mood_events\generic_negative_events.dm"