Merge branch 'master' into various-misc
@@ -3,14 +3,14 @@
|
||||
"h" = (/obj/structure/bed,/obj/item/bedsheet/wiz,/obj/machinery/light_switch{pixel_y = -24},/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"j" = (/obj/structure/table/wood,/obj/item/book/codex_gigas,/obj/machinery/light{dir = 8},/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"p" = (/obj/machinery/door/airlock/external,/obj/effect/mapping_helpers/airlock/cyclelink_helper,/turf/open/floor/plating,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"t" = (/obj/structure/table/wood,/obj/item/gun/magic/staff,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"t" = (/obj/structure/table/wood,/obj/item/gun/magic/staff/healing{attack_verb = list("struck","hit","bashed", "bonked"); can_charge = 0; desc = "The famous Staff of Revival toted by wizards. Supposedly able to heal all ailments, and even revive the dead. This one has the name 'Chloe' etched on the side. It feels cold."; max_charges = 0; name = "Chloe's staff of healing"; recharge_rate = 0},/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"v" = (/obj/structure/destructible/cult/tome,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"w" = (/turf/closed/indestructible/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"y" = (/turf/open/floor/carpet,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"z" = (/obj/structure/table/wood,/obj/item/storage/pill_bottle/dice{icon_state = "magicdicebag"},/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"B" = (/obj/structure/chair/wood/wings{dir = 1},/turf/open/floor/carpet,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"G" = (/obj/structure/showcase{desc = "A historical figure of great importance to the wizard federation. He spent his long life learning magic, stealing artifacts, and harassing idiots with swords. May he rest forever, Rodney."; icon = 'icons/mob/mob.dmi'; icon_state = "nim"; name = "wizard of yendor showcase"},/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"I" = (/obj/machinery/vending/magivend_novirus,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"I" = (/obj/machinery/vending/magivend_novirus,/obj/item/storage/backpack/satchel/flat/secret/chloe_ruin,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"K" = (/obj/item/clothing/shoes/sandal/marisa,/obj/item/clothing/suit/wizrobe/marisa,/obj/item/clothing/head/wizard/marisa,/obj/effect/decal/remains/human,/turf/open/floor/carpet,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"P" = (/obj/structure/table/wood,/obj/item/book/granter/spell/smoke,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
"S" = (/obj/machinery/light,/turf/open/floor/wood,/area/ruin/space/has_grav/powered/wiz_home)
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
#define FORCE_MAP "_maps/layeniastation.json"
|
||||
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"map_name": "Layenia Station",
|
||||
"map_path": "map_files/LayeniaStation",
|
||||
"map_file": "LayeniaStation.dmm",
|
||||
"shuttles": {
|
||||
"cargo": "cargo_box",
|
||||
"ferry": "ferry_fancy",
|
||||
"whiteship": "whiteship_box",
|
||||
"emergency": "emergency_box"
|
||||
},
|
||||
"traits":[
|
||||
{
|
||||
"Gravity":true
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -1,30 +1,39 @@
|
||||
"a" = (/obj/machinery/door/airlock/titanium{name = "Supply Shuttle Airlock"; req_access_txt = "31"},/obj/structure/fans/tiny,/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"a" = (/obj/machinery/conveyor{dir = 8; id = "QMLoad"},/obj/machinery/door/poddoor{dir = 8; id = "QMLoaddoor2"; name = "supply dock loading door"},/obj/structure/fans/tiny,/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"b" = (/turf/closed/wall/mineral/titanium,/area/shuttle/supply)
|
||||
"c" = (/obj/machinery/door/airlock/titanium{name = "Supply Shuttle Airlock"; req_access_txt = "31"},/obj/docking_port/mobile/supply{dwidth = 5; width = 12},/obj/structure/fans/tiny,/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"e" = (/turf/open/floor/mineral/titanium/blue,/area/shuttle/supply)
|
||||
"f" = (/obj/machinery/conveyor{dir = 4; id = "QMLoad2"},/obj/machinery/door/poddoor{id = "QMLoaddoor2"; name = "supply dock loading door"},/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"h" = (/obj/machinery/button/door{dir = 2; id = "QMLoaddoor2"; name = "Loading Doors"; pixel_x = 24; pixel_y = 8},/obj/machinery/button/door{id = "QMLoaddoor"; name = "Loading Doors"; pixel_x = 24; pixel_y = -8},/obj/machinery/light{dir = 4},/turf/open/floor/mineral/titanium/blue,/area/shuttle/supply)
|
||||
"j" = (/obj/machinery/conveyor{dir = 8; id = "QMLoad"},/obj/machinery/door/poddoor{id = "QMLoaddoor"; name = "supply dock loading door"},/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"c" = (/obj/structure/fans/tiny,/obj/machinery/door/airlock/titanium{name = "Supply Shuttle Airlock"; req_access_txt = "31"},/obj/docking_port/mobile/supply{dwidth = 5; width = 12},/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"e" = (/obj/effect/turf_decal/stripes/line{dir = 9},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"f" = (/obj/machinery/door/airlock/titanium{name = "Supply Shuttle Airlock"; req_access_txt = "31"},/obj/structure/fans/tiny,/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"h" = (/obj/machinery/light{dir = 4},/obj/effect/turf_decal/stripes/line{dir = 4},/obj/machinery/button/door{id = "QMLoaddoor2"; name = "Loading Doors"; pixel_x = 24; pixel_y = 8},/obj/machinery/button/door{id = "QMLoaddoor"; name = "Loading Doors"; pixel_x = 24; pixel_y = -8},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"i" = (/obj/machinery/door/poddoor{dir = 8; id = "QMLoaddoor"; name = "supply dock loading door"},/obj/machinery/conveyor{dir = 4; id = "QMLoad2"},/obj/structure/fans/tiny,/turf/open/floor/plating,/area/shuttle/supply)
|
||||
"l" = (/turf/closed/wall/mineral/titanium/interior,/area/shuttle/supply)
|
||||
"q" = (/obj/structure/window/reinforced{dir = 1},/obj/structure/shuttle/engine/heater,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"q" = (/obj/structure/window/reinforced{dir = 1},/obj/structure/shuttle/engine/heater,/obj/effect/turf_decal/stripes/line,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"s" = (/turf/template_noop,/area/template_noop)
|
||||
"t" = (/obj/structure/shuttle/engine/propulsion/burst/left,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"u" = (/obj/structure/shuttle/engine/propulsion,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"v" = (/obj/structure/shuttle/engine/propulsion/burst/right,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"w" = (/obj/machinery/light{dir = 1},/turf/open/floor/mineral/titanium/blue,/area/shuttle/supply)
|
||||
"x" = (/obj/machinery/light{dir = 8},/turf/open/floor/mineral/titanium/blue,/area/shuttle/supply)
|
||||
"t" = (/obj/structure/shuttle/engine/propulsion/burst/left,/obj/effect/turf_decal/stripes/line,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"u" = (/obj/structure/shuttle/engine/propulsion,/obj/effect/turf_decal/stripes/line,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"v" = (/obj/structure/shuttle/engine/propulsion/burst/right,/obj/effect/turf_decal/stripes/line,/turf/open/floor/plating/airless,/area/shuttle/supply)
|
||||
"w" = (/obj/effect/turf_decal/stripes/line{dir = 1},/obj/machinery/light{dir = 1},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"x" = (/obj/machinery/light{dir = 8},/obj/effect/turf_decal/stripes/line{dir = 8},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"y" = (/obj/effect/turf_decal/stripes/line{dir = 10},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"A" = (/obj/effect/turf_decal/stripes/line{dir = 1},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"C" = (/obj/effect/turf_decal/delivery,/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"D" = (/obj/effect/turf_decal/stripes/line{dir = 4},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"F" = (/obj/effect/turf_decal/bot,/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"K" = (/obj/effect/turf_decal/stripes/line{dir = 6},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"M" = (/obj/effect/turf_decal/stripes/line{dir = 8},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"S" = (/obj/effect/turf_decal/stripes/line{dir = 5},/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
"X" = (/obj/effect/turf_decal/stripes/line,/turf/open/floor/plasteel,/area/shuttle/supply)
|
||||
|
||||
(1,1,1) = {"
|
||||
bbbbbbb
|
||||
beeweeb
|
||||
beeeeeb
|
||||
beeeeef
|
||||
beeeeea
|
||||
bxeeehb
|
||||
beeeeec
|
||||
beeeeej
|
||||
beeeeeb
|
||||
bleeelb
|
||||
beAwASb
|
||||
bMFFFDb
|
||||
bMFFFDa
|
||||
bMFFFDf
|
||||
bxFFFhb
|
||||
bMFFFDc
|
||||
bMFFFDi
|
||||
byXXXKb
|
||||
blCCClb
|
||||
bbqqqbb
|
||||
stuuuvs
|
||||
"}
|
||||
|
||||
@@ -294,6 +294,7 @@
|
||||
#define SPEECH_LANGUAGE 5
|
||||
#define SPEECH_IGNORE_SPAM 6
|
||||
#define SPEECH_FORCED 7 */
|
||||
#define COMSIG_MOB_ANTAG_ON_GAIN "mob_antag_on_gain" //from base of /datum/antagonist/on_gain(): (antag_datum)
|
||||
|
||||
///from base of /mob/Login(): ()
|
||||
#define COMSIG_MOB_LOGIN "mob_login"
|
||||
@@ -378,6 +379,7 @@
|
||||
|
||||
///from base of mob/living/carbon/soundbang_act(): (list(intensity))
|
||||
#define COMSIG_CARBON_SOUNDBANG "carbon_soundbang"
|
||||
#define COMSIG_CARBON_IDENTITY_TRANSFERRED_TO "carbon_id_transferred_to" //from datum/dna/transfer_identity(): (datum/dna, transfer_SE)
|
||||
///from /item/organ/proc/Insert() (/obj/item/organ/)
|
||||
#define COMSIG_CARBON_GAIN_ORGAN "carbon_gain_organ"
|
||||
///from /item/organ/proc/Remove() (/obj/item/organ/)
|
||||
@@ -566,6 +568,9 @@
|
||||
#define COMSIG_HUMAN_MELEE_UNARMED_ATTACKBY "human_melee_unarmed_attackby"
|
||||
///Hit by successful disarm attack (mob/living/carbon/human/attacker,zone_targeted)
|
||||
#define COMSIG_HUMAN_DISARM_HIT "human_disarm_hit"
|
||||
#define COMSIG_HUMAN_PREFS_COPIED_TO "human_prefs_copied_to" //from datum/preferences/copy_to(): (datum/preferences, icon_updates, roundstart_checks)
|
||||
#define COMSIG_HUMAN_HARDSET_DNA "human_hardset_dna" //from mob/living/carbon/human/hardset_dna(): (ui, se, newreal_name, newblood_type, datum/species, newfeatures)
|
||||
#define COMSIG_HUMAN_ON_RANDOMIZE "humman_on_randomize" //from base of proc/randomize_human()
|
||||
///Whenever EquipRanked is called, called after job is set
|
||||
#define COMSIG_JOB_RECEIVED "job_received"
|
||||
|
||||
|
||||
@@ -187,6 +187,13 @@
|
||||
#define TRAIT_NEVER_CLONE "donotclone"
|
||||
#define TRAIT_COLDBLOODED "coldblooded" // Your body is literal room temperature. Does not make you immune to the temp.
|
||||
#define TRAIT_FLIMSY "flimsy" //you have 20% less maxhealth
|
||||
|
||||
|
||||
//Hyper
|
||||
#define TRAIT_VIRILE "virile" //you have 20% more chance of impreg
|
||||
#define TRAIT_MACROPHILE "macrophile" //likes the big
|
||||
#define TRAIT_MICROPHILE "microphile" //likes the small
|
||||
|
||||
#define TRAIT_TOUGH "tough" //you have 10% more maxhealth
|
||||
#define TRAIT_AUTO_CATCH_ITEM "auto_catch_item"
|
||||
#define TRAIT_CLOWN_MENTALITY "clown_mentality" // The future is now, clownman.
|
||||
|
||||
@@ -104,17 +104,6 @@ GLOBAL_VAR_INIT(miscreants_allowed, FALSE)
|
||||
if(!src.holder) return
|
||||
message_admins("[key_name_admin(usr)] manually reloaded mentors")
|
||||
|
||||
//Flavor Text
|
||||
/mob/living/carbon/human/verb/set_flavor()
|
||||
set name = "Set Flavor Text"
|
||||
set desc = "Sets an extended description of your character's features."
|
||||
set category = "IC"
|
||||
|
||||
var/new_flavor = input(src, "Enter your new flavor text:", "Flavor text", null) as message|null
|
||||
if(!isnull(new_flavor))
|
||||
flavor_text = html_encode(new_flavor)
|
||||
to_chat(src, "Your flavor text has been updated.")
|
||||
|
||||
//LOOC toggles
|
||||
/client/verb/listen_looc()
|
||||
set name = "Show/Hide LOOC"
|
||||
|
||||
@@ -231,6 +231,7 @@
|
||||
"ipc_screen" = snowflake_ipc_antenna_list ? pick(snowflake_ipc_antenna_list) : "None",
|
||||
"ipc_antenna" = "None",
|
||||
"flavor_text" = "",
|
||||
"silicon_flavor_text" = "",
|
||||
"ooc_text" = ""))
|
||||
|
||||
/proc/random_hair_style(gender)
|
||||
|
||||
@@ -163,6 +163,7 @@
|
||||
set waitfor = FALSE
|
||||
|
||||
to_chat(world, "<BR><BR><BR><span class='big bold'>The round has ended.</span>")
|
||||
var/botmsg = "**The Round has ended!**```Round ID: [GLOB.round_id]\nRound Time: [DisplayTimeText(world.time - SSticker.round_start_time)]\nTotal Population: [GLOB.joined_player_list.len]```"
|
||||
if(LAZYLEN(GLOB.round_end_notifiees))
|
||||
send2irc("Notice", "[GLOB.round_end_notifiees.Join(", ")] the round has ended.")
|
||||
|
||||
@@ -179,6 +180,20 @@
|
||||
var/popcount = gather_roundend_feedback()
|
||||
display_report(popcount)
|
||||
|
||||
|
||||
CHECK_TICK
|
||||
|
||||
//Hyper bot list players
|
||||
botmsg += "\n**The Crew!** ```"
|
||||
for(var/p in GLOB.player_list)
|
||||
var/mob/living/P = p //the living crew members
|
||||
if(P)
|
||||
botmsg += "[P.real_name]"
|
||||
if(P.job)
|
||||
botmsg += " ([P.job])"
|
||||
botmsg += "\n"
|
||||
botmsg += "```"
|
||||
|
||||
CHECK_TICK
|
||||
|
||||
// Add AntagHUD to everyone, see who was really evil the whole time!
|
||||
@@ -208,10 +223,6 @@
|
||||
if(length(CONFIG_GET(keyed_list/cross_server)))
|
||||
send_news_report()
|
||||
|
||||
//tell the nice people on discord what went on before the salt cannon happens.
|
||||
world.TgsTargetedChatBroadcast("The current round has ended. Please standby for your shift interlude Kinaris News Network's report!", FALSE)
|
||||
world.TgsTargetedChatBroadcast(send_news_report(),FALSE)
|
||||
|
||||
CHECK_TICK
|
||||
|
||||
//These need update to actually reflect the real antagonists
|
||||
@@ -226,7 +237,6 @@
|
||||
total_antagonists[A.name] += "[key_name(A.owner)]"
|
||||
|
||||
CHECK_TICK
|
||||
|
||||
//Now print them all into the log!
|
||||
log_game("Antagonists at round end were...")
|
||||
for(var/antag_name in total_antagonists)
|
||||
@@ -243,6 +253,7 @@
|
||||
SSblackbox.Seal()
|
||||
|
||||
sleep(50)
|
||||
world.hypermessage(botmsg)
|
||||
ready_for_reboot = TRUE
|
||||
standard_reboot()
|
||||
|
||||
|
||||
@@ -25,6 +25,12 @@
|
||||
if(SSparallax.random_layer)
|
||||
C.parallax_layers_cached += new SSparallax.random_layer
|
||||
C.parallax_layers_cached += new /obj/screen/parallax_layer/layer_3(null, C.view)
|
||||
if(SSmapping.config?.map_name == "Layenia Station")
|
||||
C.parallax_layers_cached += new /obj/screen/parallax_layer/layenia/horizon(null, C.view)
|
||||
C.parallax_layers_cached += new /obj/screen/parallax_layer/layenia/clouds1(null, C.view)
|
||||
C.parallax_layers_cached += new /obj/screen/parallax_layer/layenia/clouds2(null, C.view)
|
||||
C.parallax_layers_cached += new /obj/screen/parallax_layer/layenia/clouds3(null, C.view)
|
||||
|
||||
|
||||
C.parallax_layers = C.parallax_layers_cached.Copy()
|
||||
|
||||
@@ -66,24 +72,24 @@
|
||||
switch(C.prefs.parallax)
|
||||
if (PARALLAX_INSANE)
|
||||
C.parallax_throttle = FALSE
|
||||
C.parallax_layers_max = 5
|
||||
C.parallax_layers_max = 10
|
||||
return TRUE
|
||||
|
||||
if (PARALLAX_MED)
|
||||
C.parallax_throttle = PARALLAX_DELAY_MED
|
||||
C.parallax_layers_max = 3
|
||||
C.parallax_layers_max = 8
|
||||
return TRUE
|
||||
|
||||
if (PARALLAX_LOW)
|
||||
C.parallax_throttle = PARALLAX_DELAY_LOW
|
||||
C.parallax_layers_max = 1
|
||||
C.parallax_layers_max = 7
|
||||
return TRUE
|
||||
|
||||
if (PARALLAX_DISABLE)
|
||||
return FALSE
|
||||
|
||||
C.parallax_throttle = PARALLAX_DELAY_DEFAULT
|
||||
C.parallax_layers_max = 4
|
||||
C.parallax_layers_max = 10
|
||||
return TRUE
|
||||
|
||||
/datum/hud/proc/update_parallax_pref(mob/viewmob)
|
||||
@@ -320,7 +326,7 @@
|
||||
blend_mode = BLEND_OVERLAY
|
||||
absolute = TRUE //Status of seperation
|
||||
speed = 3
|
||||
layer = 30
|
||||
layer = 4
|
||||
|
||||
/obj/screen/parallax_layer/planet/update_status(mob/M)
|
||||
var/client/C = M.client
|
||||
@@ -331,3 +337,44 @@
|
||||
|
||||
/obj/screen/parallax_layer/planet/update_o()
|
||||
return //Shit wont move
|
||||
|
||||
//Layenia parallaxes
|
||||
|
||||
/obj/screen/parallax_layer/layenia
|
||||
icon_state = null
|
||||
blend_mode = BLEND_OVERLAY
|
||||
absolute = TRUE
|
||||
speed = 0.6
|
||||
layer = 5
|
||||
|
||||
/obj/screen/parallax_layer/layenia/horizon
|
||||
icon_state = "layeniahorizon"
|
||||
speed = 0.3
|
||||
absolute = FALSE
|
||||
|
||||
/obj/screen/parallax_layer/layenia/clouds1
|
||||
icon_state = "layenia1"
|
||||
speed = 0.6
|
||||
layer = 6
|
||||
|
||||
/obj/screen/parallax_layer/layenia/clouds2
|
||||
icon_state = "layenia2"
|
||||
speed = 1
|
||||
layer = 7
|
||||
|
||||
/obj/screen/parallax_layer/layenia/clouds3
|
||||
icon_state = "layenia3"
|
||||
speed = 1.4
|
||||
layer = 8
|
||||
|
||||
/obj/screen/parallax_layer/layenia/update_status(mob/M)
|
||||
var/client/C = M.client
|
||||
var/turf/posobj = get_turf(C.eye)
|
||||
if(!posobj)
|
||||
return
|
||||
invisibility = is_station_level(posobj.z) ? 0 : INVISIBILITY_ABSTRACT
|
||||
|
||||
/*
|
||||
/obj/screen/parallax_layer/tparallax1/update_status(mob/M)
|
||||
if(SSmapping.config?.map_name != "Layenia Station")
|
||||
*/
|
||||
|
||||
@@ -454,7 +454,9 @@ SUBSYSTEM_DEF(job)
|
||||
to_chat(M, "<b>[job.custom_spawn_text]</b>")
|
||||
if(CONFIG_GET(number/minimal_access_threshold))
|
||||
to_chat(M, "<span class='notice'><B>As this station was initially staffed with a [CONFIG_GET(flag/jobs_have_minimal_access) ? "full crew, only your job's necessities" : "skeleton crew, additional access may"] have been added to your ID card.</B></span>")
|
||||
|
||||
|
||||
job.after_spawn(H, M, joined_late)
|
||||
|
||||
//Account ID. ID is handled by human initialization
|
||||
if(ishuman(H))
|
||||
var/mob/living/carbon/human/wageslave = H
|
||||
|
||||
@@ -38,7 +38,7 @@
|
||||
|
||||
/datum/component/chasm/proc/is_safe()
|
||||
//if anything matching this typecache is found in the chasm, we don't drop things
|
||||
var/static/list/chasm_safeties_typecache = typecacheof(list(/obj/structure/lattice/catwalk, /obj/structure/stone_tile))
|
||||
var/static/list/chasm_safeties_typecache = typecacheof(list(/obj/structure/lattice/catwalk, /obj/structure/lattice, /obj/structure/stone_tile))
|
||||
|
||||
var/atom/parent = src.parent
|
||||
var/list/found_safeties = typecache_filter_list(parent.contents, chasm_safeties_typecache)
|
||||
|
||||
@@ -46,6 +46,12 @@
|
||||
|
||||
//begin playsound shenanigans//
|
||||
|
||||
//for big characters, add alittle boom
|
||||
if(LM.size_multiplier > 1.5)
|
||||
var/stompsound = pick( 'sound/effects/footstep/giant1.ogg','sound/effects/footstep/giant2.ogg')
|
||||
var/giantvolume = LM.size_multiplier * 9
|
||||
playsound(T, stompsound, giantvolume)
|
||||
|
||||
//for barefooted non-clawed mobs like monkeys
|
||||
if(isbarefoot(LM))
|
||||
playsound(T, pick(GLOB.barefootstep[T.barefootstep][1]),
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
var/insanity_effect = 0 //is the owner being punished for low mood? If so, how much?
|
||||
var/holdmyinsanityeffect = 0 //before we edit our sanity lets take a look
|
||||
var/obj/screen/mood/screen_obj
|
||||
var/lastupdate = 0
|
||||
|
||||
/datum/component/mood/Initialize()
|
||||
if(!isliving(parent))
|
||||
@@ -91,6 +92,7 @@
|
||||
mood += event.mood_change
|
||||
if(!event.hidden)
|
||||
shown_mood += event.mood_change
|
||||
|
||||
mood *= mood_modifier
|
||||
shown_mood *= mood_modifier
|
||||
|
||||
|
||||
@@ -54,11 +54,12 @@
|
||||
if(ishuman(destination))
|
||||
var/mob/living/carbon/human/H = destination
|
||||
H.give_genitals(TRUE)//This gives the body the genitals of this DNA. Used for any transformations based on DNA
|
||||
destination.flavor_text = destination.dna.features["flavor_text"] //Update the flavor_text to use new dna text
|
||||
destination.ooc_text = destination.dna.features["ooc_text"] //Update the flavor_text to use new dna text
|
||||
if(transfer_SE)
|
||||
destination.dna.mutation_index = mutation_index
|
||||
|
||||
SEND_SIGNAL(destination, COMSIG_CARBON_IDENTITY_TRANSFERRED_TO, src, transfer_SE)
|
||||
|
||||
/datum/dna/proc/copy_dna(datum/dna/new_dna)
|
||||
new_dna.unique_enzymes = unique_enzymes
|
||||
new_dna.mutation_index = mutation_index
|
||||
@@ -356,7 +357,6 @@
|
||||
|
||||
if(newfeatures)
|
||||
dna.features = newfeatures
|
||||
flavor_text = dna.features["flavor_text"] //Update the flavor_text to use new dna text
|
||||
ooc_text = dna.features["ooc_text"] //Update the flavor_text to use new dna text
|
||||
|
||||
if(mrace)
|
||||
@@ -379,6 +379,9 @@
|
||||
dna.mutation_index = mutation_index
|
||||
domutcheck()
|
||||
|
||||
SEND_SIGNAL(src, COMSIG_HUMAN_HARDSET_DNA, ui, newreal_name, newblood_type, mrace, newfeatures)
|
||||
// change to SEND_SIGNAL(src, COMSIG_HUMAN_HARDSET_DNA, ui, se, newreal_name, newblood_type, mrace, newfeatures) if we add structural enzymes.
|
||||
|
||||
if(mrace || newfeatures || ui)
|
||||
update_body()
|
||||
update_hair()
|
||||
|
||||
@@ -0,0 +1,188 @@
|
||||
GLOBAL_LIST_EMPTY(mobs_with_editable_flavor_text) //et tu, hacky code
|
||||
|
||||
/datum/element/flavor_text
|
||||
element_flags = ELEMENT_BESPOKE|ELEMENT_DETACH
|
||||
id_arg_index = 3
|
||||
var/flavor_name = "Flavor Text"
|
||||
var/list/texts_by_atom = list()
|
||||
var/addendum = ""
|
||||
var/always_show = FALSE
|
||||
var/max_len = MAX_FLAVOR_LEN
|
||||
var/can_edit = TRUE
|
||||
/// For preference/DNA saving/loading. Null to prevent. Prefs are only loaded from obviously if it exists in preferences.features.
|
||||
var/save_key
|
||||
/// Do not attempt to render a preview on examine. If this is on, it will display as \[flavor_name\]
|
||||
var/examine_no_preview = FALSE
|
||||
var/examineTabOutput = ""
|
||||
|
||||
/datum/element/flavor_text/Attach(datum/target, text = "", _name = "Flavor Text", _addendum, _max_len = MAX_FLAVOR_LEN, _always_show = FALSE, _edit = TRUE, _save_key, _examine_no_preview = FALSE)
|
||||
. = ..()
|
||||
|
||||
if(. == ELEMENT_INCOMPATIBLE || !isatom(target)) //no reason why this shouldn't work on atoms too.
|
||||
return ELEMENT_INCOMPATIBLE
|
||||
|
||||
if(_max_len)
|
||||
max_len = _max_len
|
||||
texts_by_atom[target] = copytext(text, 1, max_len)
|
||||
if(_name)
|
||||
flavor_name = _name
|
||||
if(!isnull(addendum))
|
||||
addendum = _addendum
|
||||
always_show = _always_show
|
||||
can_edit = _edit
|
||||
save_key = _save_key
|
||||
examine_no_preview = _examine_no_preview
|
||||
|
||||
RegisterSignal(target, COMSIG_PARENT_EXAMINE, .proc/show_flavor)
|
||||
|
||||
if(can_edit && ismob(target)) //but only mobs receive the proc/verb for the time being
|
||||
var/mob/M = target
|
||||
LAZYOR(GLOB.mobs_with_editable_flavor_text[M], src)
|
||||
M.verbs |= /mob/proc/manage_flavor_tests
|
||||
|
||||
if(save_key && ishuman(target))
|
||||
RegisterSignal(target, COMSIG_HUMAN_PREFS_COPIED_TO, .proc/update_prefs_flavor_text)
|
||||
|
||||
/datum/element/flavor_text/Detach(atom/A)
|
||||
. = ..()
|
||||
UnregisterSignal(A, list(COMSIG_PARENT_EXAMINE, COMSIG_HUMAN_PREFS_COPIED_TO))
|
||||
texts_by_atom -= A
|
||||
if(can_edit && ismob(A))
|
||||
var/mob/M = A
|
||||
LAZYREMOVE(GLOB.mobs_with_editable_flavor_text[M], src)
|
||||
if(!GLOB.mobs_with_editable_flavor_text[M])
|
||||
GLOB.mobs_with_editable_flavor_text -= M
|
||||
M.verbs -= /mob/proc/manage_flavor_tests
|
||||
|
||||
/datum/element/flavor_text/proc/show_flavor(atom/target, mob/user, list/examine_list)
|
||||
if(!always_show && isliving(target))
|
||||
var/mob/living/L = target
|
||||
var/unknown = L.get_visible_name() == "Unknown"
|
||||
if(!unknown && iscarbon(target))
|
||||
var/mob/living/carbon/C = L
|
||||
unknown = (C.wear_mask && (C.wear_mask.flags_inv & HIDEFACE)) || (C.head && (C.head.flags_inv & HIDEFACE))
|
||||
if(unknown)
|
||||
if(!("...?" in examine_list)) //can't think of anything better in case of multiple flavor texts.
|
||||
examine_list += "...?"
|
||||
return
|
||||
var/text = texts_by_atom[target]
|
||||
if(!text)
|
||||
return
|
||||
if(examine_no_preview)
|
||||
examine_list += "<span class='notice'><a href='?src=[REF(src)];show_flavor=[REF(target)]'>\[[flavor_name]\]</a></span>"
|
||||
return
|
||||
var/msg = replacetext(text, "\n", " ")
|
||||
if(length_char(msg) <= 40)
|
||||
examine_list += "<span class='notice'>[msg]</span>"
|
||||
else
|
||||
examine_list += "<span class='notice'>[copytext_char(msg, 1, 37)]... <a href='?src=[REF(src)];show_flavor=[REF(target)]'>More...</span></a>"
|
||||
|
||||
//Examine Tab stuff - Hyperstation
|
||||
examineTabOutput = "<center>"
|
||||
if(ishuman(target)) //user just returned, y'know, the user's own species. dumb.
|
||||
var/mob/living/carbon/human/L = target
|
||||
if(L.gender)
|
||||
examineTabOutput += "[icon2html('hyperstation/icons/chat/gender.dmi', world, L.gender)]"
|
||||
examineTabOutput += "[L.name] "
|
||||
examineTabOutput += "([L.dna.custom_species ? L.dna.custom_species : L.dna.species.name])"
|
||||
examineTabOutput += "</center>"
|
||||
examineTabOutput += "<br>[url_encode(msg)]"
|
||||
if(ismob(target))
|
||||
var/mob/M = target
|
||||
if(M.ooc_text)
|
||||
examineTabOutput += "<br><br><i><b>OOC</b>"
|
||||
examineTabOutput += "<br>[url_encode(M.ooc_text)]"
|
||||
user.client << output(examineTabOutput, "statbrowser:update_examine") //open the examine window
|
||||
user.client << output(null, "statbrowser:create_mobexamine") //open the examine window
|
||||
|
||||
/datum/element/flavor_text/Topic(href, href_list)
|
||||
. = ..()
|
||||
if(.)
|
||||
return
|
||||
if(href_list["show_flavor"])
|
||||
var/atom/target = locate(href_list["show_flavor"])
|
||||
var/text = texts_by_atom[target]
|
||||
if(text)
|
||||
usr << browse("<HTML><HEAD><meta http-equiv='Content-Type' content='text/html; charset=UTF-8'><TITLE>[target.name]</TITLE></HEAD><BODY><TT>[replacetext(texts_by_atom[target], "\n", "<BR>")]</TT></BODY></HTML>", "window=[target.name];size=500x200")
|
||||
onclose(usr, "[target.name]")
|
||||
return TRUE
|
||||
|
||||
/mob/proc/manage_flavor_tests()
|
||||
set name = "Manage Flavor Texts"
|
||||
set desc = "Used to manage your various flavor texts."
|
||||
set category = "IC"
|
||||
|
||||
var/list/L = GLOB.mobs_with_editable_flavor_text[src]
|
||||
|
||||
if(length(L) == 1)
|
||||
var/datum/element/flavor_text/F = L[1]
|
||||
F.set_flavor(src)
|
||||
return
|
||||
|
||||
var/list/choices = list()
|
||||
|
||||
for(var/i in L)
|
||||
var/datum/element/flavor_text/F = i
|
||||
choices[F.flavor_name] = F
|
||||
|
||||
var/chosen = input(src, "Which flavor text would you like to modify?") as null|anything in choices
|
||||
if(!chosen)
|
||||
return
|
||||
var/datum/element/flavor_text/F = choices[chosen]
|
||||
F.set_flavor(src)
|
||||
|
||||
/datum/element/flavor_text/proc/set_flavor(mob/user)
|
||||
if(!(user in texts_by_atom))
|
||||
return FALSE
|
||||
|
||||
var/lower_name = lowertext(flavor_name)
|
||||
var/new_text = stripped_multiline_input(user, "Set the [lower_name] displayed on 'examine'. [addendum]", flavor_name, html_decode(texts_by_atom[usr]), max_len, TRUE)
|
||||
if(!isnull(new_text) && (user in texts_by_atom))
|
||||
texts_by_atom[user] = new_text
|
||||
to_chat(src, "Your [lower_name] has been updated.")
|
||||
return TRUE
|
||||
return FALSE
|
||||
|
||||
/datum/element/flavor_text/proc/update_prefs_flavor_text(mob/living/carbon/human/H, datum/preferences/P, icon_updates = TRUE, roundstart_checks = TRUE)
|
||||
if(P.features.Find(save_key))
|
||||
texts_by_atom[H] = P.features[save_key]
|
||||
|
||||
//subtypes with additional hooks for DNA and preferences.
|
||||
/datum/element/flavor_text/carbon
|
||||
//list of antagonists etcetera that should have nothing to do with people's snowflakes.
|
||||
var/static/list/i_dont_even_know_who_you_are = typecacheof(list(/datum/antagonist/abductor, /datum/antagonist/ert,
|
||||
/datum/antagonist/nukeop, /datum/antagonist/wizard))
|
||||
|
||||
/datum/element/flavor_text/carbon/Attach(datum/target, text = "", _name = "Flavor Text", _addendum, _max_len = MAX_FLAVOR_LEN, _always_show = FALSE, _edit = TRUE, _save_key = "flavor_text", _examine_no_preview = FALSE)
|
||||
if(!iscarbon(target))
|
||||
return ELEMENT_INCOMPATIBLE
|
||||
. = ..()
|
||||
if(. == ELEMENT_INCOMPATIBLE)
|
||||
return
|
||||
RegisterSignal(target, COMSIG_CARBON_IDENTITY_TRANSFERRED_TO, .proc/update_dna_flavor_text)
|
||||
RegisterSignal(target, COMSIG_MOB_ANTAG_ON_GAIN, .proc/on_antag_gain)
|
||||
if(ishuman(target))
|
||||
RegisterSignal(target, COMSIG_HUMAN_HARDSET_DNA, .proc/update_dna_flavor_text)
|
||||
RegisterSignal(target, COMSIG_HUMAN_ON_RANDOMIZE, .proc/unset_flavor)
|
||||
|
||||
/datum/element/flavor_text/carbon/Detach(mob/living/carbon/C)
|
||||
. = ..()
|
||||
UnregisterSignal(C, list(COMSIG_CARBON_IDENTITY_TRANSFERRED_TO, COMSIG_MOB_ANTAG_ON_GAIN, COMSIG_HUMAN_PREFS_COPIED_TO, COMSIG_HUMAN_HARDSET_DNA, COMSIG_HUMAN_ON_RANDOMIZE))
|
||||
|
||||
/datum/element/flavor_text/carbon/proc/update_dna_flavor_text(mob/living/carbon/C)
|
||||
texts_by_atom[C] = C.dna.features[save_key]
|
||||
|
||||
/datum/element/flavor_text/carbon/set_flavor(mob/living/carbon/user)
|
||||
. = ..()
|
||||
if(. && user.dna)
|
||||
user.dna.features[save_key] = texts_by_atom[user]
|
||||
|
||||
/datum/element/flavor_text/carbon/proc/unset_flavor(mob/living/carbon/user)
|
||||
texts_by_atom[user] = ""
|
||||
|
||||
|
||||
/datum/element/flavor_text/carbon/proc/on_antag_gain(mob/living/carbon/user, datum/antagonist/antag)
|
||||
if(is_type_in_typecache(antag, i_dont_even_know_who_you_are))
|
||||
texts_by_atom[user] = ""
|
||||
if(user.dna)
|
||||
user.dna.features[save_key] = ""
|
||||
@@ -312,3 +312,9 @@
|
||||
suffix = "advancedlab.dmm"
|
||||
name = "Abductor Replication Lab"
|
||||
description = "Some scientists tried and almost succeeded to recreate abductor tools. Somewhat slower and a bit less modern than their originals, these tools are the best you can get if you aren't an alien."
|
||||
|
||||
/datum/map_template/ruin/space/wiz_home
|
||||
id = "wizhome"
|
||||
suffix = "wizardden.dmm"
|
||||
name = "Wizards Cabin"
|
||||
description = "The wooden cabin of a wizard in space, it smells like mana in there."
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
/datum/weather/ash_storm/layenia //because fuck writing my own code
|
||||
name = "Layenia Weather"
|
||||
desc = "A subset of weather affecting Layenia"
|
||||
weather_color = "white"
|
||||
|
||||
telegraph_message = "<span class='warning'>Thundering clouds pass overhead, swept up by a steady wind.</span>"
|
||||
telegraph_duration = 300
|
||||
telegraph_overlay = "light_snow"
|
||||
|
||||
weather_message = "<span class='boldwarning'><i>Clouds storm over the station slowly...</i></span>"
|
||||
weather_duration_lower = 600
|
||||
weather_duration_upper = 8200
|
||||
weather_overlay = "snow_storm"
|
||||
|
||||
end_message = "<span class='boldannounce'>Sunlight arches over the station once more; the storm has passed.</span>"
|
||||
end_duration = 300
|
||||
end_overlay = "light_snow"
|
||||
|
||||
area_type = /area/layenia
|
||||
target_trait = ZTRAIT_STATION
|
||||
|
||||
probability = 100
|
||||
|
||||
barometer_predictable = TRUE
|
||||
|
||||
aesthetic = TRUE
|
||||
|
||||
//datum/weather/layenia/telegraph()
|
||||
|
||||
//datum/weather/layenia/start()
|
||||
|
||||
//datum/weather/layenia/wind_down()
|
||||
|
||||
//datum/weather/layenia/end()
|
||||
|
||||
//datum/weather/ash_storm/layenia/weather_act
|
||||
@@ -1380,3 +1380,7 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
|
||||
name = "Nothing Here"
|
||||
icon_state = "yellow"
|
||||
ambientsounds = SPOOKY
|
||||
|
||||
/area/arcade
|
||||
name = "Arcade"
|
||||
icon_state = "yellow"
|
||||
|
||||
@@ -53,6 +53,7 @@
|
||||
*/
|
||||
/area/holodeck/rec_center
|
||||
name = "\improper Recreational Holodeck"
|
||||
has_gravity = STANDARD_GRAVITY
|
||||
|
||||
/area/holodeck/rec_center/offline
|
||||
name = "Holodeck - Offline"
|
||||
|
||||
@@ -0,0 +1,29 @@
|
||||
area/layenia
|
||||
name = "Layenia"
|
||||
icon_state = "mining"
|
||||
has_gravity = STANDARD_GRAVITY
|
||||
blob_allowed = FALSE
|
||||
requires_power = TRUE
|
||||
outdoors = TRUE
|
||||
dynamic_lighting = DYNAMIC_LIGHTING_DISABLED
|
||||
ambientsounds = MINING
|
||||
atmos = FALSE
|
||||
flags_1 = NONE
|
||||
|
||||
area/layenia/cloudlayer
|
||||
name = "Laneya clouds"
|
||||
icon_state = "space"
|
||||
dynamic_lighting = DYNAMIC_LIGHTING_DISABLED
|
||||
atmos = FALSE
|
||||
|
||||
area/layenia/powered
|
||||
name = "Layenia Powered"
|
||||
icon_state = "centcom"
|
||||
requires_power = FALSE
|
||||
has_gravity = STANDARD_GRAVITY
|
||||
noteleport = FALSE
|
||||
blob_allowed = TRUE
|
||||
flags_1 = NONE
|
||||
outdoors = FALSE
|
||||
dynamic_lighting = DYNAMIC_LIGHTING_FORCED
|
||||
atmos = FALSE
|
||||
@@ -58,8 +58,8 @@
|
||||
/area/ruin/space/has_grav/powered/cat_man
|
||||
name = "Kitty Den"
|
||||
|
||||
/area/ruin/space/has_grav/powered/wiz_home/area/ruin/space/has_grav/powered/wiz_home
|
||||
name = "Wizard's Cabin"
|
||||
/area/ruin/space/has_grav/powered/wiz_home
|
||||
name = "Wizards Cabin"
|
||||
|
||||
/area/ruin/space/has_grav/powered/authorship
|
||||
name = "Authorship"
|
||||
|
||||
@@ -15,6 +15,12 @@
|
||||
var/list/list_observers = list()
|
||||
|
||||
/datum/dynamic_ruleset/event/acceptable(population=0, threat=0)
|
||||
if(istype(controller, /datum/round_event_control))
|
||||
var/datum/round_event_control/R = controller
|
||||
if(R.map_blacklist.len && (SSmapping.config.map_file in R.map_blacklist)) //Apparently dynamic doesn't call a controller's canSpawnEvent :>
|
||||
return FALSE
|
||||
if(R.map_whitelist.len && !(SSmapping.config.map_file in R.map_whitelist))
|
||||
return FALSE
|
||||
return ..()
|
||||
|
||||
/datum/dynamic_ruleset/event/ready(forced = 0)
|
||||
|
||||
@@ -133,6 +133,7 @@
|
||||
|
||||
/obj/machinery/door/airlock/LateInitialize()
|
||||
. = ..()
|
||||
autorotation() //auto rotate door
|
||||
if (cyclelinkeddir)
|
||||
cyclelinkairlock()
|
||||
if(abandoned)
|
||||
@@ -159,11 +160,20 @@
|
||||
update_icon()
|
||||
|
||||
|
||||
/obj/machinery/door/airlock/proc/getrotation() //for auto rotating doors, because im sick of doing it
|
||||
for(var/turf/O in get_step(src,SOUTH))
|
||||
log_mapping("[src]: [O]")
|
||||
if(O.density)
|
||||
log_mapping("[src]: [O] is dense")
|
||||
/obj/machinery/door/airlock/proc/autorotation() //for auto rotating doors, because im sick of doing it
|
||||
var/turf/N = get_step(src, NORTH)
|
||||
var/turf/S = get_step(src, SOUTH)
|
||||
|
||||
if(istype(N, /turf/closed)) //Wall
|
||||
dir = 4
|
||||
if(istype(S, /turf/closed))
|
||||
dir = 4
|
||||
var/obj/structure/window/W = locate(/obj/structure/window, N) //Window
|
||||
if(W)
|
||||
dir = 4
|
||||
var/obj/structure/window/R = locate(/obj/structure/window, S)
|
||||
if(R)
|
||||
dir = 4
|
||||
|
||||
/obj/machinery/door/airlock/ComponentInitialize()
|
||||
. = ..()
|
||||
|
||||
@@ -350,7 +350,10 @@
|
||||
icon = 'icons/obj/doors/airlocks/external/external.dmi'
|
||||
overlays_file = 'icons/obj/doors/airlocks/external/overlays.dmi'
|
||||
note_overlay_file = 'icons/obj/doors/airlocks/external/overlays.dmi'
|
||||
color_overlay_file = 'icons/obj/doors/airlocks/external/color.dmi'
|
||||
assemblytype = /obj/structure/door_assembly/door_assembly_ext
|
||||
basecolor = "#ff0000" //red
|
||||
|
||||
|
||||
/obj/machinery/door/airlock/external/glass
|
||||
opacity = 0
|
||||
|
||||
@@ -319,6 +319,9 @@
|
||||
new R(src)
|
||||
revealed = TRUE
|
||||
|
||||
/obj/item/storage/backpack/satchel/flat/secret/chloe_ruin
|
||||
reward_one_of_these = list(/obj/item/book/granter/spell/summonitem, /obj/item/book_of_babel)
|
||||
|
||||
/obj/item/storage/backpack/duffelbag
|
||||
name = "duffel bag"
|
||||
desc = "A large duffel bag for holding extra things."
|
||||
|
||||
@@ -656,3 +656,60 @@
|
||||
|
||||
if(islist(icon_states && icon_states.len))
|
||||
icon_state = pick(icon_states)
|
||||
|
||||
|
||||
/obj/structure/flora/crystal
|
||||
name = "crystal"
|
||||
desc = "You shouldnt see this!"
|
||||
gender = PLURAL //trans rights
|
||||
max_integrity = 30
|
||||
|
||||
/obj/structure/flora/crystal/small
|
||||
name = "small crystals"
|
||||
icon = 'icons/obj/flora/layeniasmall.dmi'
|
||||
light_range = 2
|
||||
light_power = 0.25
|
||||
light_color = LIGHT_COLOR_BLUE
|
||||
|
||||
//Small crystal clusters
|
||||
/obj/structure/flora/crystal/small/pile
|
||||
name = "small crystals"
|
||||
desc = "A pile of small crystals"
|
||||
icon_state = "crystals"
|
||||
|
||||
/obj/structure/flora/crystal/small/pile/Initialize()
|
||||
if(icon_state == "crystals")
|
||||
icon_state = "crystals[rand(1, 4)]"
|
||||
. = ..()
|
||||
|
||||
//Small crystal growths
|
||||
/obj/structure/flora/crystal/small/growth
|
||||
name = "small crystals"
|
||||
desc = "A growth of small crystals"
|
||||
icon_state = "crystalgrowth"
|
||||
|
||||
/obj/structure/flora/crystal/small/growth/Initialize()
|
||||
if(icon_state == "crystalgrowth")
|
||||
icon_state = "crystalgrowth[rand(1, 4)]"
|
||||
. = ..()
|
||||
|
||||
/obj/structure/flora/crystal/medium
|
||||
name = "medium crystals"
|
||||
icon = 'icons/obj/flora/layeniamedium.dmi'
|
||||
pixel_x = -16
|
||||
pixel_y = -3
|
||||
layer = ABOVE_ALL_MOB_LAYER
|
||||
light_range = 4
|
||||
light_power = 0.75
|
||||
light_color = LIGHT_COLOR_BLUE
|
||||
|
||||
//Medium crystal growths
|
||||
/obj/structure/flora/crystal/medium/growth
|
||||
name = "medium crystals"
|
||||
desc = "A growth of medium crystals"
|
||||
icon_state = "crystalgrowth"
|
||||
|
||||
/obj/structure/flora/crystal/medium/growth/Initialize()
|
||||
if(icon_state == "crystalgrowth")
|
||||
icon_state = "crystalgrowth[rand(1, 3)]"
|
||||
. = ..()
|
||||
|
||||
@@ -15,7 +15,9 @@
|
||||
/turf/closed/wall,
|
||||
/obj/structure/falsewall)
|
||||
smooth = SMOOTH_MORE
|
||||
obj_flags = BLOCK_Z_FALL
|
||||
// flags = CONDUCT_1
|
||||
//planetary_atmos = TRUE
|
||||
|
||||
/obj/structure/lattice/examine(mob/user)
|
||||
. = ..()
|
||||
|
||||
@@ -74,6 +74,19 @@
|
||||
if(istype(AM))
|
||||
playsound(src,sound,50,1)
|
||||
|
||||
/turf/open/indestructible/concrete
|
||||
name = "concrete"
|
||||
icon = 'icons/turf/floors.dmi'
|
||||
icon_state = "concrete"
|
||||
baseturfs = /turf/open/floor/plating/asteroid/layenia
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
planetary_atmos = TRUE
|
||||
|
||||
/turf/open/indestructible/concrete/smooth
|
||||
icon_state = "concrete2"
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
planetary_atmos = TRUE
|
||||
|
||||
/turf/open/indestructible/cobble/side
|
||||
icon_state = "cobble_side"
|
||||
|
||||
@@ -92,6 +105,27 @@
|
||||
heavyfootstep = FOOTSTEP_GENERIC_HEAVY
|
||||
tiled_dirt = FALSE
|
||||
|
||||
/turf/open/indestructible/layenia/crystal
|
||||
name = "Lattice Crystal"
|
||||
desc = "A glowing azure crystal, with strange properties to make things float."
|
||||
icon = 'icons/turf/floors/crystal_floor.dmi'
|
||||
baseturfs = /turf/open/indestructible/layenia/crystal
|
||||
slowdown = 1
|
||||
light_range = 4
|
||||
light_power = 0.5
|
||||
barefootstep = FOOTSTEP_HARD_BAREFOOT
|
||||
clawfootstep = FOOTSTEP_HARD_CLAW
|
||||
heavyfootstep = FOOTSTEP_GENERIC_HEAVY
|
||||
light_color = LIGHT_COLOR_BLUE
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
planetary_atmos = TRUE
|
||||
smooth = SMOOTH_TRUE | SMOOTH_BORDER | SMOOTH_MORE
|
||||
canSmoothWith = list(/turf/open/indestructible/layenia/crystal)
|
||||
|
||||
/turf/open/indestructible/layenia/crystal/garden
|
||||
initial_gas_mix = OPENTURF_DEFAULT_ATMOS
|
||||
planetary_atmos = TRUE
|
||||
|
||||
/turf/open/indestructible/necropolis
|
||||
name = "necropolis floor"
|
||||
desc = "It's regarding you suspiciously."
|
||||
@@ -208,6 +242,13 @@
|
||||
//testing("Active turf found. Return value of compare(): [is_active]")
|
||||
excited = TRUE
|
||||
SSair.active_turfs |= src
|
||||
//Issues with air runtiming and you don't know where? Uncomment the following code.
|
||||
/*
|
||||
if(air == null)
|
||||
log_game("Bad air from [src] at [src.loc]")
|
||||
if(enemy_air == null)
|
||||
log_game("Bad air from [enemy_tile] at [enemy_tile.loc]")
|
||||
*/
|
||||
|
||||
/turf/open/proc/GetHeatCapacity()
|
||||
. = air.heat_capacity()
|
||||
|
||||
@@ -115,3 +115,25 @@
|
||||
var/turf/T = safepick(get_area_turfs(/area/fabric_of_reality))
|
||||
if(T)
|
||||
set_target(T)
|
||||
|
||||
/turf/open/chasm/cloud
|
||||
name = "clouds"
|
||||
gender = PLURAL
|
||||
desc = "Clouds as far as the eye can see... Watch your step."
|
||||
icon = 'icons/turf/space.dmi'
|
||||
icon_state = "0"
|
||||
plane = PLANE_SPACE
|
||||
tiled_dirt = FALSE
|
||||
baseturfs = /turf/open/chasm/cloud
|
||||
smooth = SMOOTH_FALSE
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
|
||||
/turf/open/chasm/cloud/Initialize()
|
||||
. = ..()
|
||||
icon_state = SPACE_ICON_STATE
|
||||
|
||||
/turf/open/chasm/cloud/get_smooth_underlay_icon(mutable_appearance/underlay_appearance, turf/asking_turf, adjacency_dir)
|
||||
underlay_appearance.icon = 'icons/turf/space.dmi'
|
||||
underlay_appearance.icon_state = SPACE_ICON_STATE
|
||||
underlay_appearance.plane = PLANE_SPACE
|
||||
return TRUE
|
||||
|
||||
@@ -19,13 +19,14 @@
|
||||
attachment_holes = FALSE
|
||||
var/obj/item/stack/digResult = /obj/item/stack/ore/glass/basalt
|
||||
var/dug
|
||||
var/quantity_of_available_tiles = 12 //How many sprites do you have in the DMI? Note, consider tile 0. 12 here means = 13 titles. 13 tiles is the golden standard.
|
||||
|
||||
/turf/open/floor/plating/asteroid/Initialize()
|
||||
var/proper_name = name
|
||||
. = ..()
|
||||
name = proper_name
|
||||
if(prob(floor_variance))
|
||||
icon_state = "[environment_type][rand(0,12)]"
|
||||
icon_state = "[environment_type][rand(0,quantity_of_available_tiles)]"
|
||||
|
||||
/turf/open/floor/plating/asteroid/proc/getDug()
|
||||
new digResult(src, 5)
|
||||
@@ -363,3 +364,42 @@
|
||||
/turf/open/floor/plating/asteroid/snow/atmosphere
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
planetary_atmos = FALSE
|
||||
|
||||
//Layenia stuff
|
||||
|
||||
/turf/open/floor/plating/asteroid/layenia
|
||||
gender = PLURAL //trans rights
|
||||
name = "crimson Rock"
|
||||
desc = "A cold rock, rusted scarlet in color."
|
||||
icon = 'icons/turf/floors.dmi'
|
||||
baseturfs = /turf/open/floor/plating/asteroid/layenia
|
||||
icon_state = "layenia"
|
||||
icon_plating = "layenia"
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
slowdown = 1
|
||||
environment_type = "layenia"
|
||||
flags_1 = NONE
|
||||
planetary_atmos = TRUE
|
||||
burnt_states = null
|
||||
bullet_sizzle = TRUE
|
||||
bullet_bounce_sound = null
|
||||
digResult = /obj/item/stack/ore/glass/basalt
|
||||
floor_variance = 50 //This means 50% chance of variating from the default tile.
|
||||
quantity_of_available_tiles = 4
|
||||
//light_range = 2
|
||||
//light_power = 0.15
|
||||
//light_color = LIGHT_COLOR_WHITE
|
||||
|
||||
/turf/open/floor/plating/asteroid/layenia/Initialize()
|
||||
. = ..()
|
||||
//We no longer randomize the icon state here. That is done by the supercall in our parent, asteroid.
|
||||
set_layenia_light(src)
|
||||
|
||||
/turf/open/floor/plating/asteroid/layenia/garden
|
||||
initial_gas_mix = OPENTURF_DEFAULT_ATMOS
|
||||
planetary_atmos = TRUE
|
||||
|
||||
/proc/set_layenia_light(turf/open/floor/B)
|
||||
switch(B.icon_state)
|
||||
if("layenia3", "layenia4")
|
||||
B.set_light(2, 0.6, LIGHT_COLOR_BLUE) //more light
|
||||
|
||||
@@ -240,5 +240,3 @@
|
||||
|
||||
/turf/open/floor/plating/snowed/temperatre
|
||||
temperature = 255.37
|
||||
|
||||
|
||||
|
||||
@@ -522,4 +522,16 @@
|
||||
turf_type = /turf/open/floor/plating/asteroid/basalt/lava_land_surface
|
||||
baseturfs = /turf/open/floor/plating/asteroid/basalt/lava_land_surface
|
||||
initial_gas_mix = LAVALAND_DEFAULT_ATMOS
|
||||
defer_change = 1
|
||||
defer_change = 1
|
||||
|
||||
/turf/closed/mineral/layenia
|
||||
name = "Crimson rock"
|
||||
icon = 'icons/turf/mining.dmi'
|
||||
smooth_icon = 'icons/turf/layeniarocks.dmi'
|
||||
icon_state = "layenia"
|
||||
smooth = SMOOTH_MORE|SMOOTH_BORDER
|
||||
canSmoothWith = null
|
||||
baseturfs = /turf/open/floor/plating/asteroid/layenia
|
||||
initial_gas_mix = FROZEN_ATMOS
|
||||
environment_type = "layenia"
|
||||
turf_type = /turf/open/floor/plating/asteroid/layenia
|
||||
|
||||
@@ -72,6 +72,7 @@ GLOBAL_LIST_INIT(admin_verbs_admin, world.AVerbsAdmin())
|
||||
/client/proc/cmd_admin_pm_panel, /*admin-pm list*/
|
||||
/client/proc/panicbunker,
|
||||
/client/proc/addbunkerbypass,
|
||||
/client/proc/discordmessage,
|
||||
/client/proc/revokebunkerbypass,
|
||||
/client/proc/stop_sounds,
|
||||
/client/proc/debugstatpanel,
|
||||
|
||||
@@ -37,7 +37,10 @@
|
||||
H.dna.features["moth_wings"] = pick(GLOB.moth_wings_list)
|
||||
H.dna.features["moth_fluff"] = pick(GLOB.moth_fluffs_list)
|
||||
H.dna.features["deco_wings"] = pick(GLOB.deco_wings_list)
|
||||
H.dna.features["flavor_text"] = "" //Oh no.
|
||||
|
||||
SEND_SIGNAL(H, COMSIG_HUMAN_ON_RANDOMIZE)
|
||||
|
||||
H.update_body()
|
||||
H.update_hair()
|
||||
H.update_body_parts()
|
||||
H.update_body_parts()
|
||||
|
||||
@@ -72,6 +72,7 @@ GLOBAL_LIST_EMPTY(antagonists)
|
||||
give_antag_moodies()
|
||||
if(is_banned(owner.current) && replace_banned)
|
||||
replace_banned_player()
|
||||
SEND_SIGNAL(owner.current, COMSIG_MOB_ANTAG_ON_GAIN, src)
|
||||
|
||||
/datum/antagonist/proc/is_banned(mob/M)
|
||||
if(!M)
|
||||
|
||||
@@ -134,6 +134,9 @@
|
||||
else
|
||||
to_chat(user, status())
|
||||
|
||||
/obj/machinery/meter/attack_ghost(mob/user)
|
||||
to_chat(user, status())
|
||||
|
||||
/obj/machinery/meter/singularity_pull(S, current_size)
|
||||
..()
|
||||
if(current_size >= STAGE_FIVE)
|
||||
@@ -141,6 +144,7 @@
|
||||
|
||||
// TURF METER - REPORTS A TILE'S AIR CONTENTS
|
||||
// why are you yelling?
|
||||
// i hope they aren't mad
|
||||
/obj/machinery/meter/turf
|
||||
|
||||
/obj/machinery/meter/turf/reattach_to_layer()
|
||||
|
||||
@@ -377,6 +377,17 @@
|
||||
air_update_turf() // Update the environment if needed.
|
||||
update_icon()
|
||||
|
||||
/obj/machinery/portable_atmospherics/canister/attack_ghost(mob/user)
|
||||
if(user.client)
|
||||
if(IsAdminGhost(user))
|
||||
attack_ai(user)
|
||||
return FALSE
|
||||
else if(user.client.prefs.inquisitive_ghost)
|
||||
user.examinate(src)
|
||||
return FALSE
|
||||
atmosanalyzer_scan(air_contents, user, src, FALSE)
|
||||
return FALSE
|
||||
|
||||
/obj/machinery/portable_atmospherics/canister/ui_interact(mob/user, ui_key = "main", datum/tgui/ui = null, force_open = FALSE, \
|
||||
datum/tgui/master_ui = null, datum/ui_state/state = GLOB.physical_state)
|
||||
ui = SStgui.try_update_ui(user, src, ui_key, ui, force_open)
|
||||
|
||||
@@ -181,6 +181,7 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
"ipc_screen" = "Sunburst",
|
||||
"ipc_antenna" = "None",
|
||||
"flavor_text" = "",
|
||||
"silicon_flavor_text" = "",
|
||||
"ooc_text" = ""
|
||||
)
|
||||
|
||||
@@ -395,6 +396,15 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
dat += "[features["flavor_text"]]"
|
||||
else
|
||||
dat += "[TextPreview(features["flavor_text"])]...<BR>"
|
||||
dat += "<h2>Silicon Flavor Text</h2>"
|
||||
dat += "<a href='?_src_=prefs;preference=silicon_flavor_text;task=input'><b>Set Silicon Examine Text</b></a><br>"
|
||||
if(length(features["silicon_flavor_text"]) <= 40)
|
||||
if(!length(features["silicon_flavor_text"]))
|
||||
dat += "\[...\]"
|
||||
else
|
||||
dat += "[features["silicon_flavor_text"]]"
|
||||
else
|
||||
dat += "[TextPreview(features["silicon_flavor_text"])]...<BR>"
|
||||
dat += "<h2>OOC Text</h2>"
|
||||
dat += "<a href='?_src_=prefs;preference=ooc_text;task=input'><b>Set OOC Text</b></a><br>"
|
||||
if(length(features["ooc_text"]) <= 40)
|
||||
@@ -1747,6 +1757,12 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
msg = msg
|
||||
features["flavor_text"] = msg
|
||||
|
||||
if("silicon_flavor_text")
|
||||
var/msg = stripped_multiline_input(usr, "Set the silicon flavor text in your 'examine' verb. This can also be used for OOC notes and preferences!", "Silicon Flavor Text", features["silicon_flavor_text"], MAX_FLAVOR_LEN, TRUE)
|
||||
if(msg)
|
||||
msg = msg
|
||||
features["silicon_flavor_text"] = msg
|
||||
|
||||
if("ooc_text")
|
||||
var/msg = stripped_multiline_input(usr, "Set the OOC text in your 'examine' verb. This should be OOC only!", "OOC Text", html_decode(features["ooc_text"]), MAX_MESSAGE_LEN, TRUE)
|
||||
if(msg)
|
||||
@@ -2790,6 +2806,8 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
else
|
||||
character.Digitigrade_Leg_Swap(TRUE)
|
||||
|
||||
SEND_SIGNAL(character, COMSIG_HUMAN_PREFS_COPIED_TO, src, icon_updates, roundstart_checks)
|
||||
|
||||
//speech stuff
|
||||
if(custom_tongue != "default")
|
||||
var/new_tongue = GLOB.roundstart_tongues[custom_tongue]
|
||||
|
||||
@@ -436,6 +436,7 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
|
||||
else //We have no old flavortext, default to new
|
||||
S["feature_flavor_text"] >> features["flavor_text"]
|
||||
|
||||
S["feature_silicon_flavor_text"] >> features["silicon_flavor_text"]
|
||||
if((S["ooc_text"] != "") && (S["ooc_text"] != null) && S["ooc_text"])
|
||||
S["ooc_text"] >> features["ooc_text"]
|
||||
|
||||
@@ -513,6 +514,9 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
|
||||
custom_speech_verb = sanitize_inlist(custom_speech_verb, GLOB.speech_verbs, "default")
|
||||
custom_tongue = sanitize_inlist(custom_tongue, GLOB.roundstart_tongues, "default")
|
||||
|
||||
features["flavor_text"] = copytext(features["flavor_text"], 1, MAX_FLAVOR_LEN)
|
||||
features["silicon_flavor_text"] = copytext(features["silicon_flavor_text"], 1, MAX_FLAVOR_LEN)
|
||||
|
||||
joblessrole = sanitize_integer(joblessrole, 1, 3, initial(joblessrole))
|
||||
job_civilian_high = sanitize_integer(job_civilian_high, 0, 65535, initial(job_civilian_high))
|
||||
job_civilian_med = sanitize_integer(job_civilian_med, 0, 65535, initial(job_civilian_med))
|
||||
|
||||
@@ -796,6 +796,7 @@
|
||||
item_color = "greenplaidshirt"
|
||||
body_parts_covered = CHEST|GROIN|ARMS|LEGS
|
||||
can_adjust = FALSE
|
||||
fitted = NO_FEMALE_UNIFORM
|
||||
//yes
|
||||
|
||||
//Enzo_Leon patron stuff
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
max_occurrences = 1
|
||||
weight = 4
|
||||
earliest_start = 5 MINUTES
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
/datum/round_event_control/aurora_caelus/canSpawnEvent(players, gamemode)
|
||||
if(!CONFIG_GET(flag/starlight))
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
min_players = 5 //increased min players from 2 to 5 to reduce chances of half the crew dying in a carp breach
|
||||
earliest_start = 10 MINUTES
|
||||
max_occurrences = 6
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
/datum/round_event/carp_migration
|
||||
announceWhen = 3
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
typepath = /datum/round_event/meteor_wave/meaty
|
||||
weight = 2
|
||||
max_occurrences = 1
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
/datum/round_event/meteor_wave/meaty
|
||||
wave_name = "meaty"
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
min_players = 20
|
||||
max_occurrences = 3
|
||||
earliest_start = 25 MINUTES
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
/datum/round_event/meteor_wave
|
||||
startWhen = 6
|
||||
|
||||
@@ -14,7 +14,7 @@
|
||||
return ..()
|
||||
|
||||
/datum/round_event/pirates
|
||||
startWhen = 60 //2 minutes to answer
|
||||
startWhen = 300 //5 minutes to answer
|
||||
var/datum/comm_message/threat
|
||||
var/payoff = 0
|
||||
var/paid_off = FALSE
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
typepath = /datum/round_event/grey_tide
|
||||
max_occurrences = 2
|
||||
min_players = 5
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
/datum/round_event/grey_tide
|
||||
announceWhen = 50
|
||||
@@ -67,4 +68,4 @@
|
||||
temp.prison_open()
|
||||
else if(istype(O, /obj/machinery/door_timer))
|
||||
var/obj/machinery/door_timer/temp = O
|
||||
temp.timer_end(forced = TRUE)
|
||||
temp.timer_end(forced = TRUE)
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
max_occurrences = 3
|
||||
weight = 2
|
||||
min_players = 2
|
||||
map_blacklist = list("LayeniaStation.dmm")
|
||||
|
||||
|
||||
/datum/round_event/wormholes
|
||||
|
||||
@@ -23,7 +23,7 @@
|
||||
/obj/machinery/gibber/RefreshParts()
|
||||
var/gib_time = 40
|
||||
for(var/obj/item/stock_parts/matter_bin/B in component_parts)
|
||||
meat_produced += B.rating
|
||||
meat_produced += 1.6 * B.rating
|
||||
for(var/obj/item/stock_parts/manipulator/M in component_parts)
|
||||
gib_time -= 5 * M.rating
|
||||
gibtime = gib_time
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
GLOBAL_LIST_EMPTY(monkey_recyclers)
|
||||
|
||||
/obj/machinery/monkey_recycler
|
||||
name = "monkey recycler"
|
||||
desc = "A machine used for recycling dead monkeys into monkey cubes. It currently produces 1 cube for every 5 monkeys inserted." // except it literally never does
|
||||
desc = "A machine used for recycling dead monkeys into monkey cubes. You can use a multitool to link it to a xenobiology console. It currently produces 0.2 cubes for every monkey inserted."
|
||||
icon = 'icons/obj/kitchen.dmi'
|
||||
icon_state = "grinder"
|
||||
layer = BELOW_OBJ_LAYER
|
||||
@@ -9,20 +11,29 @@
|
||||
idle_power_usage = 5
|
||||
active_power_usage = 50
|
||||
circuit = /obj/item/circuitboard/machine/monkey_recycler
|
||||
var/grinded = 0
|
||||
var/required_grind = 5
|
||||
var/cube_production = 1
|
||||
var/stored_matter = 0
|
||||
var/cube_production = 0.2
|
||||
var/list/connected = list() //Xenobio consoles
|
||||
|
||||
/obj/machinery/monkey_recycler/Initialize(mapload)
|
||||
. = ..()
|
||||
GLOB.monkey_recyclers += src
|
||||
|
||||
/obj/machinery/monkey_recycler/RefreshParts()
|
||||
var/req_grind = 5
|
||||
var/cubes_made = 1
|
||||
/obj/machinery/monkey_recycler/Destroy()
|
||||
if(src in GLOB.monkey_recyclers)
|
||||
GLOB.monkey_recyclers -= src
|
||||
for(var/obj/machinery/computer/camera_advanced/xenobio/C in connected)
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/console = C
|
||||
console.connected_recycler = null
|
||||
return ..()
|
||||
|
||||
/obj/machinery/monkey_recycler/RefreshParts() //Ranges from 0.2 to 0.8 per monkey recycled
|
||||
cube_production = 0
|
||||
for(var/obj/item/stock_parts/manipulator/B in component_parts)
|
||||
req_grind -= B.rating
|
||||
cube_production += B.rating * 0.1
|
||||
for(var/obj/item/stock_parts/matter_bin/M in component_parts)
|
||||
cubes_made = M.rating
|
||||
cube_production = cubes_made
|
||||
required_grind = req_grind
|
||||
src.desc = "A machine used for recycling dead monkeys into monkey cubes. It currently produces [cubes_made] cube(s) for every [required_grind] monkey(s) inserted."
|
||||
cube_production += M.rating * 0.1
|
||||
desc = "A machine used for recycling dead monkeys into monkey cubes. You can use a multitool to link it to a xenobiology console. It currently produces [cube_production] cubes for every monkey inserted."
|
||||
|
||||
/obj/machinery/monkey_recycler/attackby(obj/item/O, mob/user, params)
|
||||
if(default_deconstruction_screwdriver(user, "grinder_open", "grinder", O))
|
||||
@@ -64,17 +75,23 @@
|
||||
var/offset = prob(50) ? -2 : 2
|
||||
animate(src, pixel_x = pixel_x + offset, time = 0.2, loop = 200) //start shaking
|
||||
use_power(500)
|
||||
grinded++
|
||||
stored_matter += cube_production
|
||||
addtimer(VARSET_CALLBACK(src, pixel_x, initial(pixel_x)))
|
||||
addtimer(CALLBACK(GLOBAL_PROC, /proc/to_chat, user, "<span class='notice'>The machine now has [grinded] monkey\s worth of material stored.</span>"))
|
||||
addtimer(CALLBACK(GLOBAL_PROC, /proc/to_chat, user, "<span class='notice'>The machine now has [stored_matter] monkey\s worth of material stored.</span>"))
|
||||
|
||||
/obj/machinery/monkey_recycler/interact(mob/user)
|
||||
if(grinded >= required_grind)
|
||||
to_chat(user, "<span class='notice'>The machine hisses loudly as it condenses the grinded monkey meat. After a moment, it dispenses a brand new monkey cube.</span>")
|
||||
if(stored_matter >= 1)
|
||||
to_chat(user, "<span class='notice'>The machine hisses loudly as it condenses the ground monkey meat. After a moment, it dispenses a brand new monkey cube.</span>")
|
||||
playsound(src.loc, 'sound/machines/hiss.ogg', 50, 1)
|
||||
grinded -= required_grind
|
||||
for(var/i = 0, i < cube_production, i++)
|
||||
new /obj/item/reagent_containers/food/snacks/monkeycube(src.loc)
|
||||
to_chat(user, "<span class='notice'>The machine's display flashes that it has [grinded] monkeys worth of material left.</span>")
|
||||
for(var/i in 1 to max(stored_matter, 1))
|
||||
new /obj/item/reagent_containers/food/snacks/monkeycube(loc)
|
||||
stored_matter--
|
||||
to_chat(user, "<span class='notice'>The machine's display flashes that it has [stored_matter] monkeys worth of material left.</span>")
|
||||
else
|
||||
to_chat(user, "<span class='danger'>The machine needs at least [required_grind] monkey(s) worth of material to produce a monkey cube. It only has [grinded].</span>")
|
||||
to_chat(user, "<span class='danger'>The machine needs at least 1 monkey worth of material to produce a monkey cube. It currently has [stored_matter].</span>")
|
||||
|
||||
/obj/machinery/monkey_recycler/multitool_act(mob/living/user, obj/item/multitool/I)
|
||||
if(istype(I))
|
||||
to_chat(user, "<span class='notice'>You log [src] in the multitool's buffer.</span>")
|
||||
I.buffer = src
|
||||
return TRUE
|
||||
|
||||
@@ -368,7 +368,7 @@
|
||||
C.reagents.add_reagent(/datum/reagent/fermi/eigenstate, 30)
|
||||
if(5)
|
||||
visible_message("<b>[src]</b> waves their arms around, <span class='spooky'>\"A new familiar for me, and you'll see it's thee!\"</span>")
|
||||
C.reagents.add_reagent("secretcatchem", 30)
|
||||
C.reagents.add_reagent(/datum/reagent/fermi/secretcatchem, 30)
|
||||
if(6)
|
||||
visible_message("<b>[src]</b> waves their arms around, <span class='spooky'>\"While you may not be a ghost, for this sheet you'll always be it's host.\"</span>")
|
||||
var/mob/living/carbon/human/H = C
|
||||
|
||||
@@ -18,7 +18,7 @@ Clown
|
||||
minimal_access = list(ACCESS_THEATRE)
|
||||
|
||||
/datum/job/clown/after_spawn(mob/living/carbon/human/H, mob/M)
|
||||
. = ..()
|
||||
..()
|
||||
H.apply_pref_name("clown", M.client)
|
||||
|
||||
/datum/outfit/job/clown
|
||||
@@ -83,6 +83,7 @@ Mime
|
||||
minimal_access = list(ACCESS_THEATRE)
|
||||
|
||||
/datum/job/mime/after_spawn(mob/living/carbon/human/H, mob/M)
|
||||
..()
|
||||
H.apply_pref_name("mime", M.client)
|
||||
|
||||
/datum/outfit/job/mime
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
//Only override this proc
|
||||
//H is usually a human unless an /equip override transformed it
|
||||
/datum/job/proc/after_spawn(mob/living/H, mob/M, latejoin = FALSE)
|
||||
//do actions on H but send messages to M as the key may not have been transferred_yet
|
||||
//do actions on H but send messages to M as the key may not have been transferred yet
|
||||
if(mind_traits)
|
||||
for(var/t in mind_traits)
|
||||
ADD_TRAIT(H.mind, t, JOB_TRAIT)
|
||||
|
||||
@@ -21,7 +21,7 @@ AI
|
||||
. = H.AIize(latejoin)
|
||||
|
||||
/datum/job/ai/after_spawn(mob/H, mob/M, latejoin)
|
||||
. = ..()
|
||||
..()
|
||||
if(latejoin)
|
||||
var/obj/structure/AIcore/latejoin_inactive/lateJoinCore
|
||||
for(var/obj/structure/AIcore/latejoin_inactive/P in GLOB.latejoin_ai_cores)
|
||||
|
||||
@@ -64,6 +64,14 @@
|
||||
name = "asteroid snow baseturf editor"
|
||||
baseturf = /turf/open/floor/plating/asteroid/snow
|
||||
|
||||
/obj/effect/baseturf_helper/asteroid/layenia
|
||||
name = "layenia baseturf editor"
|
||||
baseturf = /turf/open/floor/plating/asteroid/layenia
|
||||
|
||||
/obj/effect/baseturf_helper/cloud
|
||||
name = "cloud baseturf editor"
|
||||
baseturf = /turf/open/chasm/cloud
|
||||
|
||||
/obj/effect/baseturf_helper/beach/sand
|
||||
name = "beach sand baseturf editor"
|
||||
baseturf = /turf/open/floor/plating/beach/sand
|
||||
|
||||
@@ -597,7 +597,7 @@
|
||||
if (H.custom_body_size) //Do they have it set?
|
||||
H.resize(H.custom_body_size * 0.01)
|
||||
if (H.breedable == TRUE)
|
||||
H.impregchance = 30
|
||||
H.impregchance = 25
|
||||
. = H
|
||||
new_character = .
|
||||
if(transfer_after)
|
||||
|
||||
@@ -17,3 +17,8 @@
|
||||
name = "Round + Light"
|
||||
icon_state = "roundlight"
|
||||
|
||||
/datum/sprite_accessory/snouts/gator
|
||||
name = "Gator"
|
||||
icon_state = "gator"
|
||||
color_src = MATRIXED
|
||||
|
||||
|
||||
@@ -11,14 +11,20 @@
|
||||
toggle_combat_mode(TRUE, TRUE)
|
||||
|
||||
. = ..()
|
||||
|
||||
|
||||
for(var/T in get_traumas())
|
||||
var/datum/brain_trauma/BT = T
|
||||
BT.on_death()
|
||||
|
||||
|
||||
if(SSticker.mode)
|
||||
SSticker.mode.check_win() //Calls the rounds wincheck, mainly for wizard, malf, and changeling now
|
||||
|
||||
//watching someone die is traumatic
|
||||
for(var/mob/living/carbon/human/H in oview(5, src))
|
||||
SEND_SIGNAL(H, COMSIG_ADD_MOOD_EVENT, "death", /datum/mood_event/deathsaw)
|
||||
if(prob(10)) //10% chance to pump adrenaline into their body
|
||||
H.jitteriness += 5
|
||||
|
||||
/mob/living/carbon/gib(no_brain, no_organs, no_bodyparts)
|
||||
var/atom/Tsec = drop_location()
|
||||
for(var/mob/M in src)
|
||||
|
||||
@@ -8,7 +8,6 @@
|
||||
var/t_is = p_are()
|
||||
var/obscure_name
|
||||
var/dispSize = round(12*size_multiplier) // gets the character's sprite size percent and converts it to the nearest half foot
|
||||
var/output = ""
|
||||
|
||||
if(isliving(user))
|
||||
var/mob/living/L = user
|
||||
@@ -24,25 +23,13 @@
|
||||
if (vassDesc != "")
|
||||
. += vassDesc
|
||||
|
||||
output = "<center>"
|
||||
var/list/obscured = check_obscured_slots()
|
||||
var/skipface = (wear_mask && (wear_mask.flags_inv & HIDEFACE)) || (head && (head.flags_inv & HIDEFACE))
|
||||
|
||||
if(ishuman(src)) //user just returned, y'know, the user's own species. dumb.
|
||||
var/mob/living/carbon/human/H = src
|
||||
if(gender)
|
||||
output += "[icon2html('hyperstation/icons/chat/gender.dmi', world, gender)]"
|
||||
|
||||
output += "<b>[src.name]</b>"
|
||||
var/datum/species/pref_species = H.dna.species
|
||||
if(get_visible_name() == "Unknown") // same as flavor text, but hey it works.
|
||||
. += "You can't make out what species they are."
|
||||
else if(skipface)
|
||||
. += "You can't make out what species they are."
|
||||
else
|
||||
. += "[t_He] [t_is] a [H.dna.custom_species ? H.dna.custom_species : pref_species.name]!"
|
||||
output += "([H.dna.custom_species ? H.dna.custom_species : pref_species.name])"
|
||||
output += "</center>"
|
||||
|
||||
if(skipface || get_visible_name() == "Unknown")
|
||||
. += "You can't make out what species they are."
|
||||
else
|
||||
. += "[t_He] [t_is] a [dna.custom_species ? dna.custom_species : dna.species.name]!"
|
||||
|
||||
//uniform
|
||||
if(w_uniform && !(SLOT_W_UNIFORM in obscured))
|
||||
@@ -416,30 +403,9 @@
|
||||
else if(isobserver(user) && traitstring)
|
||||
. += "<span class='info'><b>Traits:</b> [traitstring]</span>"
|
||||
|
||||
|
||||
if(print_flavor_text())
|
||||
output += "<br><b>General</b>"
|
||||
if(get_visible_name() == "Unknown") //Are we sure we know who this is? Don't show flavor text unless we can recognize them. Prevents certain metagaming with impersonation.
|
||||
. += "...?"
|
||||
output += "<br>...?"
|
||||
else if(skipface) //Sometimes we're not unknown, but impersonating someone in a hardsuit, let's not reveal our flavor text then either.
|
||||
. += "...?"
|
||||
output += "<br>...?"
|
||||
else
|
||||
. += "[print_flavor_text()]"
|
||||
output += "<br>[url_encode(flavor_text)]"
|
||||
if(ooc_text)
|
||||
output += "<br><br><i><b>OOC</b>"
|
||||
output += "<br>[url_encode(ooc_text)]"
|
||||
|
||||
SEND_SIGNAL(src, COMSIG_PARENT_EXAMINE, user, msg)
|
||||
SEND_SIGNAL(src, COMSIG_PARENT_EXAMINE, user, .) //This also handles flavor texts now
|
||||
. += "*---------*</span>"
|
||||
|
||||
//stat panel
|
||||
if(ishuman(src))
|
||||
user.client << output(output, "statbrowser:update_examine") //open the examine window
|
||||
user.client << output(null, "statbrowser:create_mobexamine") //open the examine window
|
||||
|
||||
/mob/living/proc/status_effect_examines(pronoun_replacement) //You can include this in any mob's examine() to show the examine texts of status effects!
|
||||
var/list/dat = list()
|
||||
if(!pronoun_replacement)
|
||||
|
||||
@@ -37,6 +37,8 @@
|
||||
if(!CONFIG_GET(flag/disable_human_mood))
|
||||
AddComponent(/datum/component/mood)
|
||||
AddElement(/datum/element/mob_holder/micro, "micro")
|
||||
AddElement(/datum/element/flavor_text/carbon, "", "Flavor Text", "", MAX_FLAVOR_LEN, FALSE, TRUE, "flavor_text")
|
||||
AddElement(/datum/element/flavor_text, "", "Temporary Flavor Text", "This should be used only for things pertaining to the current round!")
|
||||
|
||||
/mob/living/carbon/human/Destroy()
|
||||
QDEL_NULL(physiology)
|
||||
|
||||
@@ -58,7 +58,7 @@
|
||||
//H13 custom body size and impregnation
|
||||
var/custom_body_size = 100
|
||||
var/breedable = 0
|
||||
var/impregchance = 0
|
||||
var/impregchance = 30
|
||||
//h13 noncon settings
|
||||
var/Noncon = 0
|
||||
var/ERP = 0
|
||||
|
||||
@@ -437,11 +437,11 @@
|
||||
|
||||
var/obj/item/reagent_containers/spray/cyborg_drying/CD = locate(/obj/item/reagent_containers/spray/cyborg_drying) in basic_modules
|
||||
if(CD)
|
||||
CD.reagents.add_reagent("drying_agent", 5 * coeff)
|
||||
CD.reagents.add_reagent(/datum/reagent/drying_agent, 5 * coeff)
|
||||
|
||||
var/obj/item/reagent_containers/spray/cyborg_lube/CL = locate(/obj/item/reagent_containers/spray/cyborg_lube) in emag_modules
|
||||
if(CL)
|
||||
CL.reagents.add_reagent("lube", 2 * coeff)
|
||||
CL.reagents.add_reagent(/datum/reagent/lube, 2 * coeff)
|
||||
|
||||
/obj/item/robot_module/clown
|
||||
name = "Clown"
|
||||
|
||||
@@ -55,6 +55,11 @@
|
||||
diag_hud_set_status()
|
||||
diag_hud_set_health()
|
||||
|
||||
/mob/living/silicon/ComponentInitialize()
|
||||
. = ..()
|
||||
AddElement(/datum/element/flavor_text, "", "Silicon Flavor Text", "", MAX_FLAVOR_LEN, FALSE, TRUE, "silicon_flavor_text")
|
||||
AddElement(/datum/element/flavor_text, "", "Temporary Flavor Text", "This should be used only for things pertaining to the current round!")
|
||||
|
||||
/mob/living/silicon/med_hud_set_health()
|
||||
return //we use a different hud
|
||||
|
||||
|
||||
@@ -316,9 +316,9 @@ GLOBAL_VAR_INIT(floor_cluwnes, 0)
|
||||
to_chat(H, "<span class='userdanger'>WHAT THE FUCK IS THAT?!</span>")
|
||||
to_chat(H, "<i>.KNOH !nuf hcum os si uoy htiw gniyalP .KNOH KNOH KNOH</i>")
|
||||
H.playsound_local(src,'sound/hallucinations/im_here1.ogg', 25)
|
||||
H.reagents.add_reagent("mindbreaker", 3)
|
||||
H.reagents.add_reagent("laughter", 5)
|
||||
H.reagents.add_reagent("mercury", 3)
|
||||
H.reagents.add_reagent(/datum/reagent/toxin/mindbreaker, 3)
|
||||
H.reagents.add_reagent(/datum/reagent/consumable/laughter, 5)
|
||||
H.reagents.add_reagent(/datum/reagent/mercury, 3)
|
||||
Appear()
|
||||
manifested = FALSE
|
||||
addtimer(CALLBACK(src, /mob/living/simple_animal/hostile/floor_cluwne/.proc/Manifest), 2)
|
||||
|
||||
@@ -525,13 +525,6 @@ mob/visible_message(message, self_message, blind_message, vision_distance = DEFA
|
||||
unset_machine()
|
||||
src << browse(null, t1)
|
||||
|
||||
if(href_list["flavor_more"])
|
||||
usr << browse(text("<HTML><HEAD><TITLE>[]</TITLE></HEAD><BODY><TT>[]</TT></BODY></HTML>", name, replacetext(flavor_text, "\n", "<BR>")), text("window=[];size=500x200", name))
|
||||
onclose(usr, "[name]")
|
||||
|
||||
if(href_list["flavor_change"])
|
||||
update_flavor_text()
|
||||
|
||||
if(href_list["refresh"])
|
||||
if(machine && in_range(src, usr))
|
||||
show_inv(machine)
|
||||
|
||||
@@ -129,9 +129,7 @@
|
||||
///Whether the mob is updating glide size when movespeed updates or not
|
||||
var/updating_glide_size = TRUE
|
||||
|
||||
var/flavor_text = ""
|
||||
var/ooc_text = ""
|
||||
var/flavor_text_2 = "" //version of the above that only lasts for the current round.
|
||||
|
||||
///////TYPING INDICATORS///////
|
||||
/// Set to true if we want to show typing indicators.
|
||||
|
||||
@@ -2,31 +2,6 @@
|
||||
////////////////////SUBTLE COMMAND////////////////////
|
||||
//////////////////////////////////////////////////////
|
||||
|
||||
/mob/proc/update_flavor_text()
|
||||
set src in usr
|
||||
if(usr != src)
|
||||
to_chat(usr, "No.")
|
||||
var/msg = stripped_multiline_input(usr, "Set the flavor text in your 'examine' verb. IC only!", "Flavor Text", html_decode(flavor_text), MAX_MESSAGE_LEN, TRUE)
|
||||
|
||||
if(msg)
|
||||
flavor_text = html_encode(msg)
|
||||
|
||||
flavor_text = msg
|
||||
|
||||
/mob/proc/warn_flavor_changed()
|
||||
if(flavor_text && flavor_text != "") // don't spam people that don't use it!
|
||||
to_chat(src, "<h2 class='alert'>OOC Warning:</h2>")
|
||||
to_chat(src, "<span class='alert'>Your flavor text is likely out of date! <a href='?src=[REF(src)];flavor_change=1'>Change</a></span>")
|
||||
|
||||
/mob/proc/print_flavor_text()
|
||||
if(flavor_text && flavor_text != "")
|
||||
// We are decoding and then encoding to not only get correct amount of characters, but also to prevent partial escaping characters being shown.
|
||||
var/msg = html_decode(replacetext(flavor_text, "\n", " "))
|
||||
if(length_char(msg) <= 40)
|
||||
return "<span class='notice'>[html_encode(msg)]</span>"
|
||||
else
|
||||
return "<span class='notice'>[html_encode(copytext_char(msg, 1, 37))]... <a href='?src=[REF(src)];flavor_more=1'>More...</span></a>"
|
||||
|
||||
/mob/proc/get_top_level_mob()
|
||||
if(istype(src.loc,/mob)&&src.loc!=src)
|
||||
var/mob/M=src.loc
|
||||
|
||||
@@ -171,7 +171,7 @@
|
||||
|
||||
/turf/open/pool/attackby(obj/item/W, mob/living/user)
|
||||
if(istype(W, /obj/item/mop) && filled)
|
||||
W.reagents.add_reagent("water", 5)
|
||||
W.reagents.add_reagent(/datum/reagent/water, 5)
|
||||
to_chat(user, "<span class='notice'>You wet [W] in [src].</span>")
|
||||
playsound(src, 'sound/effects/slosh.ogg', 25, TRUE)
|
||||
else
|
||||
|
||||
@@ -18,8 +18,8 @@
|
||||
var/grumping = 0 // is the engine currently doing grumpy things
|
||||
var/list/grump_prefix = list("an upsetting", "an unsettling",
|
||||
"a scary", "a loud", "a sassy", "a grouchy", "a grumpy",
|
||||
"an awful", "a horrible", "a despicable", "a pretty rad", "a godawful")
|
||||
var/list/grump_suffix = list("noise", "racket", "ruckus", "sound", "clatter", "fracas", "hubbub")
|
||||
"an awful", "a horrible", "a despicable", "a pretty rad", "a godawful, a wocky")
|
||||
var/list/grump_suffix = list("noise", "racket", "ruckus", "sound", "clatter", "fracas", "hubbub, slush")
|
||||
var/sound_engine1 = 'sound/machines/tractor_running.ogg'
|
||||
var/sound_engine2 = 'sound/machines/engine_highpower.ogg'
|
||||
var/sound_tractorrev = 'sound/machines/tractorrev.ogg'
|
||||
|
||||
@@ -337,70 +337,6 @@
|
||||
construction_time = 600
|
||||
category = list("Durand")
|
||||
|
||||
//H.O.N.K
|
||||
/datum/design/honk_chassis
|
||||
name = "Exosuit Chassis (\"H.O.N.K\")"
|
||||
id = "honk_chassis"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/chassis/honker
|
||||
materials = list(MAT_METAL=20000)
|
||||
construction_time = 100
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_torso
|
||||
name = "Exosuit Torso (\"H.O.N.K\")"
|
||||
id = "honk_torso"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/part/honker_torso
|
||||
materials = list(MAT_METAL=20000,MAT_GLASS=10000,MAT_BANANIUM=10000)
|
||||
construction_time = 300
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_head
|
||||
name = "Exosuit Head (\"H.O.N.K\")"
|
||||
id = "honk_head"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/part/honker_head
|
||||
materials = list(MAT_METAL=10000,MAT_GLASS=5000,MAT_BANANIUM=5000)
|
||||
construction_time = 200
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_left_arm
|
||||
name = "Exosuit Left Arm (\"H.O.N.K\")"
|
||||
id = "honk_left_arm"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/part/honker_left_arm
|
||||
materials = list(MAT_METAL=15000,MAT_BANANIUM=5000)
|
||||
construction_time = 200
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_right_arm
|
||||
name = "Exosuit Right Arm (\"H.O.N.K\")"
|
||||
id = "honk_right_arm"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/part/honker_right_arm
|
||||
materials = list(MAT_METAL=15000,MAT_BANANIUM=5000)
|
||||
construction_time = 200
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_left_leg
|
||||
name = "Exosuit Left Leg (\"H.O.N.K\")"
|
||||
id = "honk_left_leg"
|
||||
build_type = MECHFAB
|
||||
build_path =/obj/item/mecha_parts/part/honker_left_leg
|
||||
materials = list(MAT_METAL=20000,MAT_BANANIUM=5000)
|
||||
construction_time = 200
|
||||
category = list("H.O.N.K")
|
||||
|
||||
/datum/design/honk_right_leg
|
||||
name = "Exosuit Right Leg (\"H.O.N.K\")"
|
||||
id = "honk_right_leg"
|
||||
build_type = MECHFAB
|
||||
build_path = /obj/item/mecha_parts/part/honker_right_leg
|
||||
materials = list(MAT_METAL=20000,MAT_BANANIUM=5000)
|
||||
construction_time = 200
|
||||
category = list("H.O.N.K")
|
||||
|
||||
|
||||
//Phazon
|
||||
/datum/design/phazon_chassis
|
||||
|
||||
@@ -464,16 +464,6 @@
|
||||
research_costs = list(TECHWEB_POINT_TYPE_GENERIC = 3000)
|
||||
export_price = 5000
|
||||
|
||||
/////////////////////////Clown tech/////////////////////////
|
||||
/datum/techweb_node/clown
|
||||
id = "clown"
|
||||
display_name = "Clown Technology"
|
||||
description = "Honk?!"
|
||||
prereq_ids = list("base")
|
||||
design_ids = list("air_horn", "honker_main", "honker_peri", "honker_targ", "honk_chassis", "honk_head", "honk_torso", "honk_left_arm", "honk_right_arm",
|
||||
"honk_left_leg", "honk_right_leg", "mech_banana_mortar", "mech_mousetrap_mortar", "mech_honker", "mech_punching_face", "implant_trombone", "borg_transform_clown")
|
||||
research_costs = list(TECHWEB_POINT_TYPE_GENERIC = 2500)
|
||||
export_price = 5000
|
||||
|
||||
////////////////////////Computer tech////////////////////////
|
||||
/datum/techweb_node/comptech
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
//Xenobio control console
|
||||
/mob/camera/aiEye/remote/xenobio
|
||||
visible_icon = 1
|
||||
visible_icon = TRUE
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
icon_state = "camera_target"
|
||||
var/allowed_area = null
|
||||
@@ -22,15 +22,11 @@
|
||||
desc = "A computer used for remotely handling slimes."
|
||||
networks = list("ss13")
|
||||
circuit = /obj/item/circuitboard/computer/xenobiology
|
||||
var/datum/action/innate/slime_place/slime_place_action
|
||||
var/datum/action/innate/slime_pick_up/slime_up_action
|
||||
var/datum/action/innate/feed_slime/feed_slime_action
|
||||
var/datum/action/innate/monkey_recycle/monkey_recycle_action
|
||||
var/datum/action/innate/slime_scan/scan_action
|
||||
var/datum/action/innate/feed_potion/potion_action
|
||||
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
|
||||
var/max_slimes = 5
|
||||
@@ -43,14 +39,13 @@
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/Initialize()
|
||||
. = ..()
|
||||
slime_place_action = new
|
||||
slime_up_action = new
|
||||
feed_slime_action = new
|
||||
monkey_recycle_action = new
|
||||
scan_action = new
|
||||
potion_action = new
|
||||
hotkey_help = new
|
||||
stored_slimes = list()
|
||||
listener = AddComponent(/datum/component/redirect, list(COMSIG_ATOM_CONTENTS_DEL = CALLBACK(src, .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
|
||||
connected_recycler.connected += src
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/Destroy()
|
||||
stored_slimes = null
|
||||
@@ -61,45 +56,56 @@
|
||||
S.forceMove(drop_location())
|
||||
return ..()
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/examine(mob/user)
|
||||
. = ..()
|
||||
var/thing = "It has "
|
||||
if((upgradetier & XENOBIO_UPGRADE_SLIMEADV))
|
||||
thing += "an advanced slime upgrade disk "
|
||||
if((upgradetier & XENOBIO_UPGRADE_MONKEYS))
|
||||
thing += "and a monkey upgrade disk "
|
||||
else if((upgradetier & XENOBIO_UPGRADE_SLIMEBASIC))
|
||||
thing += "a basic slime upgrade disk "
|
||||
if((upgradetier & XENOBIO_UPGRADE_MONKEYS))
|
||||
thing += "and a monkey upgrade disk "
|
||||
else if((upgradetier & XENOBIO_UPGRADE_MONKEYS))
|
||||
thing += "a monkey upgrade disk "
|
||||
else
|
||||
thing += "no upgrades installed."
|
||||
. += thing
|
||||
return
|
||||
thing += "installed."
|
||||
. += thing
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/CreateEye()
|
||||
eyeobj = new /mob/camera/aiEye/remote/xenobio(get_turf(src))
|
||||
eyeobj.origin = src
|
||||
eyeobj.visible_icon = 1
|
||||
eyeobj.visible_icon = TRUE
|
||||
eyeobj.icon = 'icons/obj/abductor.dmi'
|
||||
eyeobj.icon_state = "camera_target"
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/GrantActions(mob/living/user)
|
||||
..()
|
||||
|
||||
if(slime_up_action && (upgradetier & XENOBIO_UPGRADE_SLIMEBASIC)) //CIT CHANGE - makes slime-related actions require XENOBIO_UPGRADE_SLIMEBASIC
|
||||
slime_up_action.target = src
|
||||
slime_up_action.Grant(user)
|
||||
actions += slime_up_action
|
||||
if(hotkey_help)
|
||||
hotkey_help.target = src
|
||||
hotkey_help.Grant(user)
|
||||
actions += hotkey_help
|
||||
|
||||
if(slime_place_action && (upgradetier & XENOBIO_UPGRADE_SLIMEBASIC)) //CIT CHANGE - makes slime-related actions require XENOBIO_UPGRADE_SLIMEBASIC
|
||||
slime_place_action.target = src
|
||||
slime_place_action.Grant(user)
|
||||
actions += slime_place_action
|
||||
RegisterSignal(user, COMSIG_XENO_SLIME_CLICK_CTRL, .proc/XenoSlimeClickCtrl)
|
||||
RegisterSignal(user, COMSIG_XENO_SLIME_CLICK_ALT, .proc/XenoSlimeClickAlt)
|
||||
RegisterSignal(user, COMSIG_XENO_SLIME_CLICK_SHIFT, .proc/XenoSlimeClickShift)
|
||||
RegisterSignal(user, COMSIG_XENO_TURF_CLICK_SHIFT, .proc/XenoTurfClickShift)
|
||||
RegisterSignal(user, COMSIG_XENO_TURF_CLICK_CTRL, .proc/XenoTurfClickCtrl)
|
||||
RegisterSignal(user, COMSIG_XENO_MONKEY_CLICK_CTRL, .proc/XenoMonkeyClickCtrl)
|
||||
|
||||
if(feed_slime_action && (upgradetier & XENOBIO_UPGRADE_MONKEYS)) //CIT CHANGE - makes monkey-related actions require XENOBIO_UPGRADE_MONKEYS
|
||||
feed_slime_action.target = src
|
||||
feed_slime_action.Grant(user)
|
||||
actions += feed_slime_action
|
||||
|
||||
if(monkey_recycle_action && (upgradetier & XENOBIO_UPGRADE_MONKEYS)) //CIT CHANGE - makes monkey-related actions require XENOBIO_UPGRADE_MONKEYS
|
||||
monkey_recycle_action.target = src
|
||||
monkey_recycle_action.Grant(user)
|
||||
actions += monkey_recycle_action
|
||||
|
||||
if(scan_action)
|
||||
scan_action.target = src
|
||||
scan_action.Grant(user)
|
||||
actions += scan_action
|
||||
|
||||
if(potion_action && (upgradetier & XENOBIO_UPGRADE_SLIMEADV)) // CIT CHANGE - makes giving slimes potions via console require XENOBIO_UPGRADE_SLIMEADV
|
||||
potion_action.target = src
|
||||
potion_action.Grant(user)
|
||||
actions += potion_action
|
||||
/obj/machinery/computer/camera_advanced/xenobio/remove_eye_control(mob/living/user)
|
||||
UnregisterSignal(user, COMSIG_XENO_SLIME_CLICK_CTRL)
|
||||
UnregisterSignal(user, COMSIG_XENO_SLIME_CLICK_ALT)
|
||||
UnregisterSignal(user, COMSIG_XENO_SLIME_CLICK_SHIFT)
|
||||
UnregisterSignal(user, COMSIG_XENO_TURF_CLICK_SHIFT)
|
||||
UnregisterSignal(user, COMSIG_XENO_TURF_CLICK_CTRL)
|
||||
UnregisterSignal(user, COMSIG_XENO_MONKEY_CLICK_CTRL)
|
||||
..()
|
||||
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/on_contents_del(atom/deleted)
|
||||
if(current_potion == deleted)
|
||||
@@ -134,135 +140,161 @@
|
||||
current_potion = O
|
||||
to_chat(user, "<span class='notice'>You load [O] in the console's potion slot[replaced ? ", replacing the one that was there before" : ""].</span>")
|
||||
return
|
||||
else if(istype(O, /obj/item/multitool))
|
||||
var/obj/item/multitool/M = O
|
||||
if(istype(M.buffer))
|
||||
to_chat(user, "<span class='notice'>You link [src] with [M.buffer] in [M] buffer.</span>")
|
||||
connected_recycler = M.buffer
|
||||
connected_recycler += src
|
||||
return
|
||||
else
|
||||
to_chat(user, "<span class='warning'>[M] has no buffer.</span>")
|
||||
return
|
||||
..()
|
||||
|
||||
/datum/action/innate/slime_place
|
||||
name = "Place Slimes"
|
||||
/datum/action/innate/hotkey_help
|
||||
name = "Hotkey Help"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "slime_down"
|
||||
button_icon_state = "hotkey_help"
|
||||
|
||||
/datum/action/innate/slime_place/Activate()
|
||||
/datum/action/innate/hotkey_help/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
return
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/X = target
|
||||
to_chat(owner, "<b>Click shortcuts:</b>")
|
||||
to_chat(owner, "Shift-click a slime to pick it up, or the floor to drop all held slimes.")
|
||||
to_chat(owner, "Ctrl-click a slime to scan it.")
|
||||
to_chat(owner, "Alt-click a slime to feed it a potion.")
|
||||
to_chat(owner, "Ctrl-click on a dead monkey to recycle it, or the floor to place a new monkey.")
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
for(var/mob/living/simple_animal/slime/S in X.stored_slimes)
|
||||
S.forceMove(remote_eye.loc)
|
||||
//
|
||||
// Alternate clicks for slime, monkey and open turf if using a xenobio console
|
||||
|
||||
//Picks up slime
|
||||
/mob/living/simple_animal/slime/ShiftClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_SLIME_CLICK_SHIFT, src)
|
||||
..()
|
||||
|
||||
//Place slimes
|
||||
/turf/open/ShiftClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_TURF_CLICK_SHIFT, src)
|
||||
..()
|
||||
|
||||
//Place monkey
|
||||
/turf/open/CtrlClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_TURF_CLICK_CTRL, src)
|
||||
..()
|
||||
|
||||
//Pick up monkey
|
||||
/mob/living/carbon/monkey/CtrlClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_MONKEY_CLICK_CTRL, src)
|
||||
..()
|
||||
|
||||
// Scans slime
|
||||
/mob/living/simple_animal/slime/CtrlClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_SLIME_CLICK_CTRL, src)
|
||||
..()
|
||||
|
||||
//Feeds a potion to slime
|
||||
/mob/living/simple_animal/slime/AltClick(mob/user)
|
||||
SEND_SIGNAL(user, COMSIG_XENO_SLIME_CLICK_ALT, src)
|
||||
..()
|
||||
|
||||
//Picks up slime
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoSlimeClickShift(mob/living/user, mob/living/simple_animal/slime/S)
|
||||
if(!(upgradetier & XENOBIO_UPGRADE_SLIMEBASIC))
|
||||
return
|
||||
if(!GLOB.cameranet.checkTurfVis(S.loc))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/area/mobarea = get_area(S.loc)
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(mobarea.name == X.allowed_area || mobarea.xenobiology_compatible)
|
||||
if(stored_slimes.len >= max_slimes)
|
||||
to_chat(user, "<span class='warning'>Slime storage is full.</span>")
|
||||
return
|
||||
if(S.ckey)
|
||||
to_chat(user, "<span class='warning'>The slime wiggled free!</span>")
|
||||
return
|
||||
if(S.buckled)
|
||||
S.Feedstop(silent = TRUE)
|
||||
S.visible_message("[S] vanishes in a flash of light!")
|
||||
S.forceMove(src)
|
||||
stored_slimes += S
|
||||
|
||||
//Place slimes
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoTurfClickShift(mob/living/user, turf/open/T)
|
||||
if(!(upgradetier & XENOBIO_UPGRADE_SLIMEBASIC))
|
||||
return
|
||||
if(!GLOB.cameranet.checkTurfVis(T))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/area/turfarea = get_area(T)
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(turfarea.name == X.allowed_area || turfarea.xenobiology_compatible)
|
||||
for(var/mob/living/simple_animal/slime/S in stored_slimes)
|
||||
S.forceMove(T)
|
||||
S.visible_message("[S] warps in!")
|
||||
X.stored_slimes -= S
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
stored_slimes -= S
|
||||
|
||||
/datum/action/innate/slime_pick_up
|
||||
name = "Pick up Slime"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "slime_up"
|
||||
|
||||
/datum/action/innate/slime_pick_up/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
//Place monkey
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoTurfClickCtrl(mob/living/user, turf/open/T)
|
||||
if(!(upgradetier & XENOBIO_UPGRADE_MONKEYS))
|
||||
return
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/X = target
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
for(var/mob/living/simple_animal/slime/S in remote_eye.loc)
|
||||
if(X.stored_slimes.len >= X.max_slimes)
|
||||
break
|
||||
if(!S.ckey)
|
||||
if(S.buckled)
|
||||
S.Feedstop(silent = TRUE)
|
||||
S.visible_message("[S] vanishes in a flash of light!")
|
||||
S.forceMove(X)
|
||||
X.stored_slimes += S
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
|
||||
|
||||
/datum/action/innate/feed_slime
|
||||
name = "Feed Slimes"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "monkey_down"
|
||||
|
||||
/datum/action/innate/feed_slime/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
if(!GLOB.cameranet.checkTurfVis(T))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/X = target
|
||||
var/area/turfarea = get_area(T)
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(turfarea.name == X.allowed_area || turfarea.xenobiology_compatible)
|
||||
if(monkeys >= 1)
|
||||
var/mob/living/carbon/monkey/food = new/mob/living/carbon/monkey(T, TRUE, user)
|
||||
if(!QDELETED(food))
|
||||
food.LAssailant = user
|
||||
monkeys = round(monkeys-1, 0.1)
|
||||
to_chat(user, "[src] now has [monkeys] monkeys stored.")
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
if(X.monkeys >= 1)
|
||||
var/mob/living/carbon/monkey/food = new /mob/living/carbon/monkey(remote_eye.loc, TRUE, owner)
|
||||
if (!QDELETED(food))
|
||||
food.LAssailant = C
|
||||
X.monkeys --
|
||||
to_chat(owner, "[X] now has [X.monkeys] monkeys left.")
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
|
||||
|
||||
/datum/action/innate/monkey_recycle
|
||||
name = "Recycle Monkeys"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "monkey_up"
|
||||
|
||||
/datum/action/innate/monkey_recycle/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
//Pick up monkey
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoMonkeyClickCtrl(mob/living/user, mob/living/carbon/monkey/M)
|
||||
if(!(upgradetier & XENOBIO_UPGRADE_MONKEYS))
|
||||
return
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/X = target
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
for(var/mob/living/carbon/monkey/M in remote_eye.loc)
|
||||
if(M.stat)
|
||||
M.visible_message("[M] vanishes as [M.p_theyre()] reclaimed for recycling!")
|
||||
X.monkeys = round(X.monkeys + 0.2,0.1)
|
||||
qdel(M)
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
|
||||
/datum/action/innate/slime_scan
|
||||
name = "Scan Slime"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "slime_scan"
|
||||
|
||||
/datum/action/innate/slime_scan/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
if(!connected_recycler)
|
||||
to_chat(user, "<span class='notice'>There is no connected monkey recycler. You can connect one with a multitool.</span>")
|
||||
return
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
for(var/mob/living/simple_animal/slime/S in remote_eye.loc)
|
||||
slime_scan(S, C)
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
|
||||
/datum/action/innate/feed_potion
|
||||
name = "Apply Potion"
|
||||
icon_icon = 'icons/mob/actions/actions_silicon.dmi'
|
||||
button_icon_state = "slime_potion"
|
||||
|
||||
/datum/action/innate/feed_potion/Activate()
|
||||
if(!target || !isliving(owner))
|
||||
if(!GLOB.cameranet.checkTurfVis(M.loc))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/area/mobarea = get_area(M.loc)
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(mobarea.name == X.allowed_area || mobarea.xenobiology_compatible)
|
||||
if(!M.stat)
|
||||
return
|
||||
M.visible_message("[M] vanishes as [M.p_theyre()] reclaimed for recycling!")
|
||||
connected_recycler.use_power(500)
|
||||
monkeys += connected_recycler.cube_production
|
||||
to_chat(user, "[src] now has [monkeys] monkeys available.")
|
||||
qdel(M)
|
||||
|
||||
var/mob/living/C = owner
|
||||
var/mob/camera/aiEye/remote/xenobio/remote_eye = C.remote_control
|
||||
var/obj/machinery/computer/camera_advanced/xenobio/X = target
|
||||
|
||||
if(QDELETED(X.current_potion))
|
||||
to_chat(owner, "<span class='notice'>No potion loaded.</span>")
|
||||
// Scans slime
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoSlimeClickCtrl(mob/living/user, mob/living/simple_animal/slime/S)
|
||||
if(!GLOB.cameranet.checkTurfVis(S.loc))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/area/mobarea = get_area(S.loc)
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(mobarea.name == X.allowed_area || mobarea.xenobiology_compatible)
|
||||
slime_scan(S, user)
|
||||
|
||||
if(GLOB.cameranet.checkTurfVis(remote_eye.loc))
|
||||
for(var/mob/living/simple_animal/slime/S in remote_eye.loc)
|
||||
X.current_potion.attack(S, C)
|
||||
break
|
||||
else
|
||||
to_chat(owner, "<span class='notice'>Target is not near a camera. Cannot proceed.</span>")
|
||||
//Feeds a potion to slime
|
||||
/obj/machinery/computer/camera_advanced/xenobio/proc/XenoSlimeClickAlt(mob/living/user, mob/living/simple_animal/slime/S)
|
||||
if(!(upgradetier & XENOBIO_UPGRADE_SLIMEBASIC))
|
||||
return
|
||||
if(!GLOB.cameranet.checkTurfVis(S.loc))
|
||||
to_chat(user, "<span class='warning'>Target is not near a camera. Cannot proceed.</span>")
|
||||
return
|
||||
var/area/mobarea = get_area(S.loc)
|
||||
if(QDELETED(current_potion))
|
||||
to_chat(user, "<span class='warning'>No potion loaded.</span>")
|
||||
return
|
||||
var/mob/camera/aiEye/remote/xenobio/X = eyeobj
|
||||
if(mobarea.name == X.allowed_area || mobarea.xenobiology_compatible)
|
||||
current_potion.attack(S, user)
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
#_maps/RandomRuins/SpaceRuins/asteroid5.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/bigderelict1.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/bus.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/wizardden.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/caravanambush.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/cloning_facility.dmm
|
||||
#_maps/RandomRuins/SpaceRuins/crashedclownship.dmm
|
||||
|
||||
@@ -11,4 +11,9 @@
|
||||
/datum/mood_event/kiss
|
||||
description = "<span class='nicegreen'>Someone kissed me, I feel happy!</span>\n"
|
||||
mood_change = 2
|
||||
timeout = 3 MINUTES
|
||||
timeout = 3 MINUTES
|
||||
|
||||
/datum/mood_event/deathsaw
|
||||
description = "<span class='boldwarning'>I saw someone die!</span>\n"
|
||||
mood_change = -8
|
||||
timeout = 20 MINUTES //takes a long time to get over
|
||||
@@ -56,10 +56,10 @@
|
||||
/datum/quirk/virile
|
||||
name = "Virile"
|
||||
desc = "Either through higher quality sperms, more of them, or just being more horny, your impregnation chance will increase by 20-30%."
|
||||
value = 1
|
||||
value = 0
|
||||
category = CATEGORY_SEXUAL
|
||||
medical_record_text = "Patient has a higher sperm count."
|
||||
//mob_trait = TRAIT_VIRILE
|
||||
mob_trait = TRAIT_VIRILE
|
||||
gain_text = "<span class='notice'>You feel more potent."
|
||||
lose_text = "<span class='notice'>You feel less potent."
|
||||
var/ichange = 0
|
||||
@@ -72,13 +72,12 @@
|
||||
if(quirk_holder)
|
||||
quirk_holder.impregchance -= ichange
|
||||
|
||||
|
||||
/datum/quirk/macrophile
|
||||
name = "Macrophile"
|
||||
desc = "You are attracted to larger people, and being stepped on by them."
|
||||
value = 0
|
||||
category = CATEGORY_SEXUAL
|
||||
//mob_trait = TRAIT_MACROPHILE
|
||||
mob_trait = TRAIT_MACROPHILE
|
||||
gain_text = "<span class='notice'>You feel attracted to people larger than you."
|
||||
lose_text = "<span class='notice'>You feel less attracted to people larger than you."
|
||||
|
||||
@@ -87,6 +86,6 @@
|
||||
desc = "You are attracted to smaller people, and stepping on them."
|
||||
value = 0
|
||||
category = CATEGORY_SEXUAL
|
||||
//mob_trait = TRAIT_MICROPHILE
|
||||
mob_trait = TRAIT_MICROPHILE
|
||||
gain_text = "<span class='notice'>You feel attracted to people smaller than you."
|
||||
lose_text = "<span class='notice'>You feel less attracted to people smaller than you."
|
||||
|
||||
@@ -0,0 +1,108 @@
|
||||
//ported from virgo
|
||||
|
||||
/obj/structure/railing
|
||||
name = "railing"
|
||||
desc = "A railing to stop people from falling"
|
||||
|
||||
icon = 'hyperstation/icons/obj/railings.dmi'
|
||||
var/icon_modifier = "grey_"
|
||||
icon_state = "grey_railing0"
|
||||
|
||||
density = TRUE
|
||||
layer = 4
|
||||
anchored = TRUE
|
||||
flags_1 = ON_BORDER_1
|
||||
max_integrity = 250
|
||||
var/heat_resistance = 800
|
||||
|
||||
resistance_flags = ACID_PROOF
|
||||
armor = list("melee" = 0, "bullet" = 0, "laser" = 0, "energy" = 0, "bomb" = 0, "bio" = 0, "rad" = 0, "fire" = 80, "acid" = 100)
|
||||
CanAtmosPass = ATMOS_PASS_PROC
|
||||
var/real_explosion_block //ignore this, just use explosion_block
|
||||
var/breaksound = "shatter"
|
||||
var/hitsound = 'sound/effects/Glasshit.ogg'
|
||||
rad_insulation = RAD_VERY_LIGHT_INSULATION
|
||||
rad_flags = RAD_PROTECT_CONTENTS
|
||||
var/check = 0
|
||||
|
||||
|
||||
/obj/structure/railing/CanPass(atom/movable/mover, turf/target)
|
||||
if(istype(mover) && (mover.pass_flags & PASSGLASS))
|
||||
return 1
|
||||
if(get_dir(loc, target) == dir)
|
||||
return !density
|
||||
return 1
|
||||
|
||||
/obj/structure/railing/CheckExit(atom/movable/O, turf/target)
|
||||
if(istype(O) && (O.pass_flags & PASSGLASS))
|
||||
return 1
|
||||
if(get_dir(O.loc, target) == dir)
|
||||
return 0
|
||||
return 1
|
||||
|
||||
/obj/structure/railing/Initialize()
|
||||
. = ..()
|
||||
if(src.anchored)
|
||||
update_icon(0)
|
||||
|
||||
/obj/structure/railing/proc/NeighborsCheck(var/UpdateNeighbors = 1)
|
||||
check = 0
|
||||
//if (!anchored) return
|
||||
var/Rturn = turn(src.dir, -90)
|
||||
var/Lturn = turn(src.dir, 90)
|
||||
|
||||
for(var/obj/structure/railing/R in src.loc)
|
||||
if ((R.dir == Lturn) && R.anchored)
|
||||
check |= 32
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
if ((R.dir == Rturn) && R.anchored)
|
||||
check |= 2
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
|
||||
for (var/obj/structure/railing/R in get_step(src, Lturn))
|
||||
if ((R.dir == src.dir) && R.anchored)
|
||||
check |= 16
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
for (var/obj/structure/railing/R in get_step(src, Rturn))
|
||||
if ((R.dir == src.dir) && R.anchored)
|
||||
check |= 1
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
|
||||
for (var/obj/structure/railing/R in get_step(src, (Lturn + src.dir)))
|
||||
if ((R.dir == Rturn) && R.anchored)
|
||||
check |= 64
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
for (var/obj/structure/railing/R in get_step(src, (Rturn + src.dir)))
|
||||
if ((R.dir == Lturn) && R.anchored)
|
||||
check |= 4
|
||||
if (UpdateNeighbors)
|
||||
R.update_icon(0)
|
||||
|
||||
/obj/structure/railing/update_icon(var/UpdateNeighgors = 1)
|
||||
NeighborsCheck(UpdateNeighgors)
|
||||
overlays.Cut()
|
||||
if (!check || !anchored)//|| !anchored
|
||||
icon_state = "[icon_modifier]railing0"
|
||||
else
|
||||
icon_state = "[icon_modifier]railing1"
|
||||
if (check & 32)
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]corneroverlay")
|
||||
if ((check & 16) || !(check & 32) || (check & 64))
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]frontoverlay_l")
|
||||
if (!(check & 2) || (check & 1) || (check & 4))
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]frontoverlay_r")
|
||||
if(check & 4)
|
||||
switch (src.dir)
|
||||
if (NORTH)
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]mcorneroverlay", pixel_x = 32)
|
||||
if (SOUTH)
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]mcorneroverlay", pixel_x = -32)
|
||||
if (EAST)
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]mcorneroverlay", pixel_y = -32)
|
||||
if (WEST)
|
||||
overlays += image ('hyperstation/icons/obj/railings.dmi', src, "[icon_modifier]mcorneroverlay", pixel_y = 32)
|
||||
@@ -0,0 +1,16 @@
|
||||
//not the most effient bot in the world, but it does its job.
|
||||
|
||||
/client/proc/discordmessage(input as message)
|
||||
set category = "Special Verbs"
|
||||
set name = "Hyperbot Message"
|
||||
set desc = "Makes the local bot say something in general chat on discord."
|
||||
|
||||
if(input)
|
||||
world.hypermessage(input)
|
||||
message_admins("[key_name_admin(usr)] has made the Hyperbot post '[input]' in General.")
|
||||
|
||||
/world/proc/hypermessage(message)
|
||||
fdel("Hyperbot/message.txt") //cleaning up old message
|
||||
if(message)
|
||||
var botmsg = "![message]"
|
||||
text2file(botmsg,"Hyperbot/message.txt") //the bot on local reads a new text file and sends it to the discord.
|
||||
@@ -0,0 +1,56 @@
|
||||
/mob/living/dancercaptain
|
||||
name = "Captain Beats"
|
||||
desc = "A captain cursed to dance for all eternity!"
|
||||
icon = 'hyperstation/icons/mobs/dancer/captain.dmi'
|
||||
icon_state = "idle"
|
||||
var/danceaction = 1
|
||||
var/lastaction = 0 //when the last action was!
|
||||
var/actiontime = 4
|
||||
var/list/dancefloor_turfs
|
||||
var/list/dancefloor_turfs_types
|
||||
var/dancefloor_exists = FALSE
|
||||
|
||||
/mob/living/dancercaptain/Move(atom/newloc, direct)
|
||||
|
||||
if(!danceaction)
|
||||
if(!(world.time > lastaction))
|
||||
return // no move for you!
|
||||
|
||||
animate(src, pixel_x, pixel_y = pixel_y + 10, time = 0.7, 0)
|
||||
. = ..()
|
||||
danceaction = 0 //you did your move
|
||||
lastaction = world.time+actiontime //next action time
|
||||
sleep(1)
|
||||
animate(src, pixel_x, pixel_y = pixel_y - 10, time = 0.7, 0)
|
||||
sleep(1)
|
||||
|
||||
LAZYINITLIST(dancefloor_turfs)
|
||||
LAZYINITLIST(dancefloor_turfs_types)
|
||||
|
||||
if(dancefloor_exists) //remove the old one!
|
||||
dancefloor_exists = FALSE
|
||||
for(var/i in 1 to dancefloor_turfs.len)
|
||||
var/turf/T = dancefloor_turfs[i]
|
||||
T.ChangeTurf(dancefloor_turfs_types[i])
|
||||
var/list/funky_turfs = RANGE_TURFS(2, src)
|
||||
|
||||
|
||||
dancefloor_exists = TRUE
|
||||
var/i = 1
|
||||
dancefloor_turfs.len = funky_turfs.len
|
||||
dancefloor_turfs_types.len = funky_turfs.len
|
||||
for(var/t in funky_turfs)
|
||||
if(!(istype(t, /turf/closed))) //dont change walls
|
||||
var/turf/T = t
|
||||
dancefloor_turfs[i] = T
|
||||
dancefloor_turfs_types[i] = T.type
|
||||
T.ChangeTurf((i % 2 == 0) ? /turf/open/floor/light/colour_cycle/dancefloor_a : /turf/open/floor/light/colour_cycle/dancefloor_b)
|
||||
i++
|
||||
|
||||
|
||||
/mob/living/dancercaptain/Initialize()
|
||||
. = ..()
|
||||
|
||||
lastaction = round(world.time) //round to the nearest second! to keep in beat!
|
||||
|
||||
/mob/living/dancercaptain/proc/mtimer()
|
||||
@@ -32,10 +32,14 @@
|
||||
if(user.pulling)
|
||||
dat += "<a href='byond://?src=[REF(src)];kiss=1'>Kiss [user.pulling]</A>"
|
||||
dat += "(Kiss a partner, or object.)<BR>"
|
||||
else
|
||||
dat += "<span class='linkOff'>Kiss</span></A>"
|
||||
dat += "(Requires a partner)<BR>"
|
||||
|
||||
|
||||
if(user.pulling)
|
||||
dat += "<a href='byond://?src=[REF(src)];climaxover=1'>Climax over [user.pulling]</A>" //you can cum on objects if you really want...
|
||||
dat += "(Orgasm over a person or object.)<BR>"
|
||||
|
||||
if(isliving(user.pulling))
|
||||
if(iscarbon(user.pulling))
|
||||
dat += "<a href='byond://?src=[REF(src)];climaxwith=1'>Climax with [user.pulling]</A>"
|
||||
@@ -43,8 +47,13 @@
|
||||
|
||||
var/mob/living/carbon/human/H = user.pulling
|
||||
if(H.breedable && P && H)
|
||||
dat += "<a href='byond://?src=[REF(src)];impreg=1'>Impregnate [user.pulling]</A>"
|
||||
dat += "(Climax inside another person, knocking them up.)<BR>"
|
||||
dat += "<a href='byond://?src=[REF(src)];impreg=1'>Impregnate [U.pulling] ([clamp(U.impregchance,0,100)]%)</A>"
|
||||
dat += "(Climax inside another person, and attempt to knock them up.)<BR>"
|
||||
else
|
||||
dat += "<span class='linkOff'>Climax over</span></A>"
|
||||
dat += "(Requires a partner)<BR>"
|
||||
dat += "<span class='linkOff'>Climax with</span></A>"
|
||||
dat += "(Requires a partner)<BR>"
|
||||
|
||||
//old code needs to be cleaned
|
||||
if(P)
|
||||
|
||||
@@ -7,6 +7,5 @@
|
||||
metabolization_rate = 1 * REAGENTS_METABOLISM
|
||||
taste_description = "sweetness"
|
||||
|
||||
/datum/reagent/consumable/alienhoney/on_mob_life(mob/living/carbon/M) //can still be eaten/drank, but will provide no benefits like normal honey. Still good for a food sauce.
|
||||
M.reagents.add_reagent(/datum/reagent/consumable/sugar,2) //metabolisms in the system as sugar.
|
||||
/datum/reagent/consumable/alienhoney/on_mob_life(mob/living/carbon/M)
|
||||
..()
|
||||
@@ -44,7 +44,7 @@ mob/living/get_effective_size()
|
||||
if(size_multiplier == previous_size)
|
||||
return 1
|
||||
src.update_transform() //WORK DAMN YOU
|
||||
src.update_mobsize()
|
||||
src.update_mobsize()
|
||||
//Going to change the health and speed values too
|
||||
src.remove_movespeed_modifier(MOVESPEED_ID_SIZE)
|
||||
src.add_movespeed_modifier(MOVESPEED_ID_SIZE, multiplicative_slowdown = (abs(size_multiplier - 1) * 0.8 ))
|
||||
@@ -67,7 +67,7 @@ mob/living/get_effective_size()
|
||||
|
||||
if(tmob.pulledby == H)
|
||||
return 0
|
||||
|
||||
|
||||
//Micro is on a table.
|
||||
var/turf/steppyspot = tmob.loc
|
||||
for(var/thing in steppyspot.contents)
|
||||
@@ -91,6 +91,7 @@ mob/living/get_effective_size()
|
||||
tmob.visible_message("<span class='notice'>[src] carefully slithers around [tmob].</span>", "<span class='notice'>[src]'s huge tail slithers besides you.</span>")
|
||||
else
|
||||
tmob.visible_message("<span class='notice'>[src] carefully steps over [tmob].</span>", "<span class='notice'>[src] steps over you carefully.</span>")
|
||||
|
||||
return 1
|
||||
|
||||
//Smaller person stepping under a larger person
|
||||
@@ -133,7 +134,20 @@ mob/living/get_effective_size()
|
||||
tmob.visible_message("<span class='danger'>[src] carefully rolls their tail over [tmob]!</span>", "<span class='danger'>[src]'s huge tail rolls over you!</span>")
|
||||
else
|
||||
tmob.visible_message("<span class='danger'>[src] carefully steps on [tmob]!</span>", "<span class='danger'>[src] steps onto you with force!</span>")
|
||||
return 1
|
||||
|
||||
//horny traits
|
||||
|
||||
if(HAS_TRAIT(src, TRAIT_MICROPHILE))
|
||||
src.adjustArousalLoss(8)
|
||||
if (src.getArousalLoss() >= 100 && ishuman(tmob) && tmob.has_dna())
|
||||
src.mob_climax(forced_climax=TRUE)
|
||||
|
||||
if(HAS_TRAIT(tmob, TRAIT_MACROPHILE))
|
||||
tmob.adjustArousalLoss(10)
|
||||
if (tmob.getArousalLoss() >= 100 && ishuman(tmob) && tmob.has_dna())
|
||||
tmob.mob_climax(forced_climax=TRUE)
|
||||
|
||||
return 1
|
||||
|
||||
if(H.a_intent == "harm" && H.canmove && !H.buckled)
|
||||
now_pushing = 0
|
||||
@@ -149,6 +163,19 @@ mob/living/get_effective_size()
|
||||
tmob.visible_message("<span class='danger'>[src] mows down [tmob] under their tail!</span>", "<span class='userdanger'>[src] plows their tail over you mercilessly!</span>")
|
||||
else
|
||||
tmob.visible_message("<span class='danger'>[src] slams their foot down on [tmob], crushing them!</span>", "<span class='userdanger'>[src] crushes you under their foot!</span>")
|
||||
|
||||
//horny traits
|
||||
|
||||
if(HAS_TRAIT(src, TRAIT_MICROPHILE))
|
||||
src.adjustArousalLoss((get_effective_size()/tmob.get_effective_size()*3))
|
||||
if (src.getArousalLoss() >= 100 && ishuman(tmob) && tmob.has_dna())
|
||||
src.mob_climax(forced_climax=TRUE)
|
||||
|
||||
if(HAS_TRAIT(tmob, TRAIT_MACROPHILE))
|
||||
tmob.adjustArousalLoss((get_effective_size()/tmob.get_effective_size()*3))
|
||||
if (tmob.getArousalLoss() >= 100 && ishuman(tmob) && tmob.has_dna())
|
||||
tmob.mob_climax(forced_climax=TRUE)
|
||||
|
||||
return 1
|
||||
|
||||
if(H.a_intent == "grab" && H.canmove && !H.buckled)
|
||||
@@ -215,7 +242,7 @@ mob/living/get_effective_size()
|
||||
mob_size = 2 //the default human size
|
||||
if(size_multiplier > 1)
|
||||
mob_size = 3
|
||||
|
||||
|
||||
//Proc for instantly grabbing valid size difference. Code optimizations soon(TM)
|
||||
/*
|
||||
/mob/living/proc/sizeinteractioncheck(var/mob/living/tmob)
|
||||
|
||||
@@ -170,7 +170,7 @@
|
||||
|
||||
if (C.getArousalLoss() >= 100 && ishuman(C) && C.has_dna())
|
||||
var/mob/living/carbon/human/O = C
|
||||
O.mob_climax_partner(P, M, TRUE, FALSE, FALSE, TRUE) //climax with their partner remotely!
|
||||
O.mob_climax_partner(P, M, FALSE, FALSE, FALSE, TRUE) //climax with their partner remotely!
|
||||
return
|
||||
..()
|
||||
|
||||
@@ -189,6 +189,9 @@
|
||||
if(H.dna.species.name == "Slimeperson") // slime nerd
|
||||
sleeve = mutable_appearance('hyperstation/icons/obj/fleshlight.dmi', "portal_sleeve_slime")
|
||||
|
||||
if(H.dna.species.name == "Avian") // bird nerd
|
||||
sleeve = mutable_appearance('hyperstation/icons/obj/fleshlight.dmi', "portal_sleeve_avian")
|
||||
|
||||
sleeve.color = "#" + H.dna.features["mcolor"]
|
||||
add_overlay(sleeve)
|
||||
|
||||
|
||||
@@ -124,6 +124,14 @@
|
||||
icon_state = "commissar_beret"
|
||||
item_state = "commissar_beret"
|
||||
|
||||
/obj/item/clothing/under/touchinfuzzy
|
||||
name = "provocative jumpsuit"
|
||||
desc = "A form fitting jumpsuit with a golden trim zipper! Smells faintly of succubus milk."
|
||||
icon_state = "touchinfuzzyuni"
|
||||
item_state = "touchinfuzzyuni"
|
||||
body_parts_covered = CHEST|GROIN|ARMS|LEGS
|
||||
fitted = NO_FEMALE_UNIFORM
|
||||
|
||||
/obj/item/toy/sword/chloesabre
|
||||
name = "Fleet Commander's Sabre"
|
||||
desc = "An elegant weapon, similar in design to the Captain's Sabre, but with a syndicate twist."
|
||||
@@ -143,4 +151,50 @@
|
||||
return mutable_appearance('icons/obj/custom.dmi', "darksheath-darksabre")
|
||||
|
||||
/obj/item/toy/sword/chloesabre/get_worn_belt_overlay(icon_file)
|
||||
return mutable_appearance(icon_file, "darksheath-darksabre")
|
||||
return mutable_appearance(icon_file, "darksheath-darksabre")
|
||||
|
||||
/obj/item/mialasscale
|
||||
name = "Miala's Scale"
|
||||
desc = "A bright, and familiar, cyan scale from an equally familiar snake being."
|
||||
icon = 'hyperstation/icons/obj/rewards.dmi'
|
||||
icon_state = "m_scale"
|
||||
item_state = "m_scale"
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
|
||||
/obj/item/bong/kiseru
|
||||
name = "black lacquered kiseru"
|
||||
desc = "it is a black lacquered kiseru with a ornate silver head and mouthpiece, you can feel it's old age as you hold it"
|
||||
icon = 'hyperstation/icons/obj/rewards.dmi'
|
||||
icon_state = null
|
||||
item_state = null
|
||||
w_class = WEIGHT_CLASS_NORMAL
|
||||
light_color = "#FFCC66"
|
||||
icon_off = "pipe"
|
||||
icon_on = "pipe_lit"
|
||||
|
||||
/obj/item/clothing/suit/hooded/occultrobes
|
||||
name = "Occult Robes"
|
||||
desc = "I didn't even know they made these in XXS..."
|
||||
icon_state = "coatwinter"
|
||||
item_state = "coatwinter"
|
||||
body_parts_covered = CHEST|GROIN|ARMS
|
||||
cold_protection = CHEST|GROIN|ARMS
|
||||
min_cold_protection_temperature = FIRE_SUIT_MIN_TEMP_PROTECT
|
||||
armor = list("melee" = 0, "bullet" = 0, "laser" = 0,"energy" = 0, "bomb" = 0, "bio" = 10, "rad" = 0, "fire" = 0, "acid" = 0)
|
||||
allowed = list(/obj/item/flashlight, /obj/item/tank/internals/emergency_oxygen, /obj/item/tank/internals/plasmaman, /obj/item/toy, /obj/item/storage/fancy/cigarettes, /obj/item/lighter)
|
||||
|
||||
/obj/item/clothing/suit/hooded/occultrobes
|
||||
name = "occult robes"
|
||||
desc = "I didn't even know they made these in XXS..."
|
||||
icon_state = "occultrobes"
|
||||
hoodtype = /obj/item/clothing/head/hooded/occultrobeshood
|
||||
mutantrace_variation = NO_MUTANTRACE_VARIATION
|
||||
|
||||
/obj/item/clothing/head/hooded/occultrobeshood
|
||||
name = "occult hood"
|
||||
icon_state = "occultrobeshood"
|
||||
body_parts_covered = HEAD
|
||||
cold_protection = HEAD
|
||||
min_cold_protection_temperature = FIRE_SUIT_MIN_TEMP_PROTECT
|
||||
flags_inv = HIDEHAIR
|
||||
mutantrace_variation = NO_MUTANTRACE_VARIATION
|
||||
|
After Width: | Height: | Size: 1.4 KiB |
|
Before Width: | Height: | Size: 3.6 KiB After Width: | Height: | Size: 3.8 KiB |
|
After Width: | Height: | Size: 3.9 KiB |
|
Before Width: | Height: | Size: 605 B After Width: | Height: | Size: 1.0 KiB |
|
Before Width: | Height: | Size: 426 KiB After Width: | Height: | Size: 691 KiB |
|
Before Width: | Height: | Size: 18 KiB After Width: | Height: | Size: 18 KiB |
|
Before Width: | Height: | Size: 6.9 KiB After Width: | Height: | Size: 7.5 KiB |
|
Before Width: | Height: | Size: 212 KiB After Width: | Height: | Size: 213 KiB |
|
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 34 KiB |
|
Before Width: | Height: | Size: 427 KiB After Width: | Height: | Size: 429 KiB |
|
Before Width: | Height: | Size: 372 KiB After Width: | Height: | Size: 374 KiB |
|
Before Width: | Height: | Size: 144 KiB After Width: | Height: | Size: 145 KiB |
|
Before Width: | Height: | Size: 107 KiB After Width: | Height: | Size: 107 KiB |
|
Before Width: | Height: | Size: 112 KiB After Width: | Height: | Size: 115 KiB |
|
After Width: | Height: | Size: 1.9 KiB |
|
Before Width: | Height: | Size: 6.4 KiB After Width: | Height: | Size: 6.2 KiB |