Merge branch 'master' of https://github.com/Citadel-Station-13/Citadel-Station-13 into cache-locality-experiments
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
// Defines for managed input/keybinding system.
|
||||
/// Max length of a keypress command before it's considered to be a forged packet/bogus command
|
||||
#define MAX_KEYPRESS_COMMANDLENGTH 32
|
||||
#define MAX_KEYPRESS_COMMANDLENGTH 64
|
||||
/// Maximum keys that can be bound to one button
|
||||
#define MAX_COMMANDS_PER_KEY 5
|
||||
/// Maximum keys per keybind
|
||||
|
||||
@@ -246,6 +246,8 @@
|
||||
#define COMPONENT_BLOCK_SWAP 1
|
||||
|
||||
#define COMSIG_PROCESS_BORGCHARGER_OCCUPANT "living_charge"
|
||||
///from base of mob/AltClickOn(): (atom/A)
|
||||
#define COMSIG_MOB_ALTCLICKON "mob_altclickon"
|
||||
|
||||
// /client signals
|
||||
#define COMSIG_MOB_CLIENT_LOGIN "mob_client_login" //sent when a mob/login() finishes: (client)
|
||||
@@ -290,6 +292,10 @@
|
||||
#define COMPONENT_INTERRUPT_LIFE_BIOLOGICAL 1 // interrupt biological processes
|
||||
#define COMPONENT_INTERRUPT_LIFE_PHYSICAL 2 // interrupt physical handling
|
||||
|
||||
#define COMSIG_LIVING_BIOLOGICAL_LIFE "biological_life" //from base of mob/living/BiologicalLife() (seconds, times_fired)
|
||||
|
||||
#define COMSIG_LIVING_PHYSICAL_LIFE "physical_life" //from base of mob/living/PhysicalLife() (seconds, times_fired)
|
||||
|
||||
// /mob/living/carbon physiology signals
|
||||
#define COMSIG_CARBON_GAIN_WOUND "carbon_gain_wound" //from /datum/wound/proc/apply_wound() (/mob/living/carbon/C, /datum/wound/W, /obj/item/bodypart/L)
|
||||
#define COMSIG_CARBON_LOSE_WOUND "carbon_lose_wound" //from /datum/wound/proc/remove_wound() (/mob/living/carbon/C, /datum/wound/W, /obj/item/bodypart/L)
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
#define TOXIC (1<<11)
|
||||
#define PINEAPPLE (1<<12)
|
||||
#define BREAKFAST (1<<13)
|
||||
#define ANTITOXIC (1<<14)
|
||||
|
||||
#define DRINK_NICE 1
|
||||
#define DRINK_GOOD 2
|
||||
|
||||
@@ -54,3 +54,16 @@
|
||||
|
||||
//donator items
|
||||
#define LOADOUT_CATEGORY_DONATOR "Donator"
|
||||
|
||||
//how many prosthetics can we have
|
||||
#define MAXIMUM_LOADOUT_PROSTHETICS 2
|
||||
|
||||
//what limbs can be amputated or be prosthetic
|
||||
#define LOADOUT_ALLOWED_LIMB_TARGETS list(BODY_ZONE_L_ARM,BODY_ZONE_R_ARM,BODY_ZONE_L_LEG,BODY_ZONE_R_LEG)
|
||||
|
||||
//options for modifiying limbs
|
||||
#define LOADOUT_LIMB_NORMAL "Normal"
|
||||
#define LOADOUT_LIMB_PROSTHETIC "Prosthetic"
|
||||
#define LOADOUT_LIMB_AMPUTATED "Amputated"
|
||||
|
||||
#define LOADOUT_LIMBS list(LOADOUT_LIMB_NORMAL,LOADOUT_LIMB_PROSTHETIC,LOADOUT_LIMB_AMPUTATED) //you can amputate your legs/arms though
|
||||
@@ -22,3 +22,5 @@
|
||||
var/category as text
|
||||
/// Only clients/mobs with `see_invisibility` higher can use the verb.
|
||||
var/invisibility as num
|
||||
/// Whether or not the verb appears in statpanel and commandbar when you press space
|
||||
var/hidden as num
|
||||
|
||||
@@ -51,7 +51,8 @@
|
||||
#define INIT_ORDER_FAIL2TOPIC 99
|
||||
#define INIT_ORDER_TITLE 98
|
||||
#define INIT_ORDER_GARBAGE 95
|
||||
#define INIT_ORDER_DBCORE 93
|
||||
#define INIT_ORDER_DBCORE 94
|
||||
#define INIT_ORDER_STATPANELS 93
|
||||
#define INIT_ORDER_BLACKBOX 92
|
||||
#define INIT_ORDER_SERVER_MAINT 91
|
||||
#define INIT_ORDER_INPUT 90
|
||||
@@ -86,6 +87,7 @@
|
||||
#define INIT_ORDER_MINOR_MAPPING -40
|
||||
#define INIT_ORDER_PATH -50
|
||||
#define INIT_ORDER_PERSISTENCE -95
|
||||
#define INIT_ORDER_DEMO -99 // o avoid a bunch of changes related to initialization being written, do this last
|
||||
#define INIT_ORDER_CHAT -100 //Should be last to ensure chat remains smooth during init.
|
||||
|
||||
|
||||
|
||||
+28
-10
@@ -205,18 +205,36 @@
|
||||
/proc/start_log(log)
|
||||
WRITE_LOG(log, "Starting up round ID [GLOB.round_id].\n-------------------------")
|
||||
|
||||
/* ui logging */
|
||||
/proc/log_tgui(user_or_client, text)
|
||||
/**
|
||||
* Appends a tgui-related log entry. All arguments are optional.
|
||||
*/
|
||||
/proc/log_tgui(user, message, context,
|
||||
datum/tgui_window/window,
|
||||
datum/src_object)
|
||||
var/entry = ""
|
||||
if(!user_or_client)
|
||||
entry += "no user"
|
||||
else if(istype(user_or_client, /mob))
|
||||
var/mob/user = user_or_client
|
||||
entry += "[user.ckey] (as [user])"
|
||||
else if(istype(user_or_client, /client))
|
||||
var/client/client = user_or_client
|
||||
// Insert user info
|
||||
if(!user)
|
||||
entry += "<nobody>"
|
||||
else if(istype(user, /mob))
|
||||
var/mob/mob = user
|
||||
entry += "[mob.ckey] (as [mob] at [mob.x],[mob.y],[mob.z])"
|
||||
else if(istype(user, /client))
|
||||
var/client/client = user
|
||||
entry += "[client.ckey]"
|
||||
entry += ":\n[text]"
|
||||
// Insert context
|
||||
if(context)
|
||||
entry += " in [context]"
|
||||
else if(window)
|
||||
entry += " in [window.id]"
|
||||
// Resolve src_object
|
||||
if(!src_object && window && window.locked_by)
|
||||
src_object = window.locked_by.src_object
|
||||
// Insert src_object info
|
||||
if(src_object)
|
||||
entry += "\nUsing: [src_object.type] [REF(src_object)]"
|
||||
// Insert message
|
||||
if(message)
|
||||
entry += "\n[message]"
|
||||
WRITE_LOG(GLOB.tgui_log, entry)
|
||||
|
||||
/* Close open log handles. This should be called as late as possible, and no logging should hapen after. */
|
||||
|
||||
@@ -349,7 +349,7 @@
|
||||
if(!previous)
|
||||
var/list/report_parts = list(personal_report(C), GLOB.common_report)
|
||||
content = report_parts.Join()
|
||||
C.verbs -= /client/proc/show_previous_roundend_report
|
||||
remove_verb(C, /client/proc/show_previous_roundend_report)
|
||||
fdel(filename)
|
||||
text2file(content, filename)
|
||||
else
|
||||
|
||||
@@ -0,0 +1,96 @@
|
||||
/**
|
||||
* handles adding verbs and updating the stat panel browser
|
||||
*
|
||||
* pass the verb type path to this instead of adding it directly to verbs so the statpanel can update
|
||||
* Arguments:
|
||||
* * target - Who the verb is being added to, client or mob typepath
|
||||
* * verb - typepath to a verb, or a list of verbs, supports lists of lists
|
||||
*/
|
||||
/proc/add_verb(client/target, verb_or_list_to_add)
|
||||
if(!target)
|
||||
CRASH("add_verb called without a target")
|
||||
if(IsAdminAdvancedProcCall())
|
||||
return
|
||||
var/mob/mob_target = null
|
||||
|
||||
if(ismob(target))
|
||||
mob_target = target
|
||||
target = mob_target.client
|
||||
else if(!istype(target, /client))
|
||||
CRASH("add_verb called on a non-mob and non-client")
|
||||
var/list/verbs_list = list()
|
||||
if(!islist(verb_or_list_to_add))
|
||||
verbs_list += verb_or_list_to_add
|
||||
else
|
||||
var/list/verb_listref = verb_or_list_to_add
|
||||
var/list/elements_to_process = verb_listref.Copy()
|
||||
while(length(elements_to_process))
|
||||
var/element_or_list = elements_to_process[length(elements_to_process)] //Last element
|
||||
elements_to_process.len--
|
||||
if(islist(element_or_list))
|
||||
elements_to_process += element_or_list //list/a += list/b adds the contents of b into a, not the reference to the list itself
|
||||
else
|
||||
verbs_list += element_or_list
|
||||
|
||||
if(mob_target)
|
||||
mob_target.verbs += verbs_list
|
||||
if(!target)
|
||||
return //Our work is done.
|
||||
else
|
||||
target.verbs += verbs_list
|
||||
|
||||
var/list/output_list = list()
|
||||
for(var/thing in verbs_list)
|
||||
var/procpath/verb_to_add = thing
|
||||
output_list[++output_list.len] = list(verb_to_add.category, verb_to_add.name)
|
||||
output_list = url_encode(json_encode(output_list))
|
||||
|
||||
target << output("[output_list];", "statbrowser:add_verb_list")
|
||||
|
||||
/**
|
||||
* handles removing verb and sending it to browser to update, use this for removing verbs
|
||||
*
|
||||
* pass the verb type path to this instead of removing it from verbs so the statpanel can update
|
||||
* Arguments:
|
||||
* * target - Who the verb is being removed from, client or mob typepath
|
||||
* * verb - typepath to a verb, or a list of verbs, supports lists of lists
|
||||
*/
|
||||
/proc/remove_verb(client/target, verb_or_list_to_remove)
|
||||
if(IsAdminAdvancedProcCall())
|
||||
return
|
||||
|
||||
var/mob/mob_target = null
|
||||
if(ismob(target))
|
||||
mob_target = target
|
||||
target = mob_target.client
|
||||
else if(!istype(target, /client))
|
||||
CRASH("remove_verb called on a non-mob and non-client")
|
||||
|
||||
var/list/verbs_list = list()
|
||||
if(!islist(verb_or_list_to_remove))
|
||||
verbs_list += verb_or_list_to_remove
|
||||
else
|
||||
var/list/verb_listref = verb_or_list_to_remove
|
||||
var/list/elements_to_process = verb_listref.Copy()
|
||||
while(length(elements_to_process))
|
||||
var/element_or_list = elements_to_process[length(elements_to_process)] //Last element
|
||||
elements_to_process.len--
|
||||
if(islist(element_or_list))
|
||||
elements_to_process += element_or_list //list/a += list/b adds the contents of b into a, not the reference to the list itself
|
||||
else
|
||||
verbs_list += element_or_list
|
||||
|
||||
if(mob_target)
|
||||
mob_target.verbs -= verbs_list
|
||||
if(!target)
|
||||
return //Our work is done.
|
||||
else
|
||||
target.verbs -= verbs_list
|
||||
|
||||
var/list/output_list = list()
|
||||
for(var/thing in verbs_list)
|
||||
var/procpath/verb_to_remove = thing
|
||||
output_list[++output_list.len] = list(verb_to_remove.category, verb_to_remove.name)
|
||||
output_list = url_encode(json_encode(output_list))
|
||||
|
||||
target << output("[output_list];", "statbrowser:remove_verb_list")
|
||||
@@ -279,7 +279,8 @@ GLOBAL_LIST_INIT(unlocked_mutant_parts, list("horns", "insect_fluff"))
|
||||
//parts in either of the above two lists that require a second option that allows them to be coloured
|
||||
GLOBAL_LIST_INIT(colored_mutant_parts, list("insect_wings" = "wings_color", "deco_wings" = "wings_color", "horns" = "horns_color"))
|
||||
|
||||
//species ids that have greyscale sprites
|
||||
//body ids that have greyscale sprites
|
||||
GLOBAL_LIST_INIT(greyscale_limb_types, list("human","moth","lizard","pod","plant","jelly","slime","golem","lum","stargazer","mush","ethereal","snail","c_golem","b_golem","mammal","xeno","ipc","insect","synthliz","avian","aquatic"))
|
||||
|
||||
//species ids that need snowflake coloring applied
|
||||
//body ids that have prosthetic sprites
|
||||
GLOBAL_LIST_INIT(prosthetic_limb_types, list("xion","bishop","cybersolutions","grayson","hephaestus","nanotrasen","talon"))
|
||||
|
||||
+2
-2
@@ -112,8 +112,8 @@
|
||||
/mob/living/silicon/ai/CtrlClickOn(var/atom/A)
|
||||
A.AICtrlClick(src)
|
||||
/mob/living/silicon/ai/AltClickOn(var/atom/A)
|
||||
if(!A.AIAltClick(src))
|
||||
altclick_listed_turf(A)
|
||||
A.AIAltClick(src)
|
||||
|
||||
|
||||
/*
|
||||
The following criminally helpful code is just the previous code cleaned up;
|
||||
|
||||
+17
-13
@@ -319,20 +319,13 @@
|
||||
return ..()
|
||||
/*
|
||||
Alt click
|
||||
Unused except for AI
|
||||
Used as an alternate way to interact with things.
|
||||
*/
|
||||
/mob/proc/AltClickOn(atom/A)
|
||||
if(!A.AltClick(src))
|
||||
altclick_listed_turf(A)
|
||||
|
||||
/mob/proc/altclick_listed_turf(atom/A)
|
||||
var/turf/T = get_turf(A)
|
||||
if(T == A.loc || T == A)
|
||||
if(T == listed_turf)
|
||||
listed_turf = null
|
||||
else if(TurfAdjacent(T))
|
||||
listed_turf = T
|
||||
client.statpanel = T.name
|
||||
. = SEND_SIGNAL(src, COMSIG_MOB_ALTCLICKON, A)
|
||||
if(. & COMSIG_MOB_CANCEL_CLICKON)
|
||||
return
|
||||
A.AltClick(src)
|
||||
|
||||
/mob/living/carbon/AltClickOn(atom/A)
|
||||
if(!stat && mind && iscarbon(A) && A != src)
|
||||
@@ -344,7 +337,18 @@
|
||||
..()
|
||||
|
||||
/atom/proc/AltClick(mob/user)
|
||||
. = SEND_SIGNAL(src, COMSIG_CLICK_ALT, user)
|
||||
SEND_SIGNAL(src, COMSIG_CLICK_ALT, user)
|
||||
var/turf/T = get_turf(src)
|
||||
if(T && (isturf(loc) || isturf(src)) && user.TurfAdjacent(T))
|
||||
user.listed_turf = T
|
||||
user.client << output("[url_encode(json_encode(T.name))];", "statbrowser:create_listedturf")
|
||||
|
||||
/// Use this instead of [/mob/proc/AltClickOn] where you only want turf content listing without additional atom alt-click interaction
|
||||
/atom/proc/AltClickNoInteract(mob/user, atom/A)
|
||||
var/turf/T = get_turf(A)
|
||||
if(T && user.TurfAdjacent(T))
|
||||
user.listed_turf = T
|
||||
user.client << output("[url_encode(json_encode(T.name))];", "statbrowser:create_listedturf")
|
||||
|
||||
/mob/proc/TurfAdjacent(turf/T)
|
||||
return T.Adjacent(src)
|
||||
|
||||
@@ -98,8 +98,7 @@
|
||||
/mob/living/silicon/robot/CtrlClickOn(atom/A)
|
||||
A.BorgCtrlClick(src)
|
||||
/mob/living/silicon/robot/AltClickOn(atom/A)
|
||||
if(!A.BorgAltClick(src))
|
||||
altclick_listed_turf(A)
|
||||
A.BorgAltClick(src)
|
||||
|
||||
/atom/proc/BorgCtrlShiftClick(mob/living/silicon/robot/user) //forward to human click if not overridden
|
||||
CtrlShiftClick(user)
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
var/icon/credits_icon = new(CREDITS_PATH)
|
||||
LAZYINITLIST(credits)
|
||||
var/list/_credits = credits
|
||||
verbs += /client/proc/ClearCredits
|
||||
add_verb(src, /client/proc/ClearCredits)
|
||||
var/static/list/credit_order_for_this_round
|
||||
if(isnull(credit_order_for_this_round))
|
||||
credit_order_for_this_round = list("Thanks for playing!") + (shuffle(icon_states(credits_icon)) - "Thanks for playing!")
|
||||
@@ -21,13 +21,13 @@
|
||||
_credits += new /obj/screen/credit(null, I, src, credits_icon)
|
||||
sleep(CREDIT_SPAWN_SPEED)
|
||||
sleep(CREDIT_ROLL_SPEED - CREDIT_SPAWN_SPEED)
|
||||
verbs -= /client/proc/ClearCredits
|
||||
remove_verb(src, /client/proc/ClearCredits)
|
||||
qdel(credits_icon)
|
||||
|
||||
/client/proc/ClearCredits()
|
||||
set name = "Hide Credits"
|
||||
set category = "OOC"
|
||||
verbs -= /client/proc/ClearCredits
|
||||
remove_verb(src, /client/proc/ClearCredits)
|
||||
QDEL_LIST(credits)
|
||||
credits = null
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@
|
||||
ShiftClickOn(A)
|
||||
return
|
||||
if(modifiers["alt"])
|
||||
altclick_listed_turf(A)
|
||||
AltClickNoInteract(src, A)
|
||||
return
|
||||
if(modifiers["ctrl"])
|
||||
CtrlClickOn(A)
|
||||
|
||||
@@ -197,10 +197,9 @@
|
||||
var/list/banned_edits = list(NAMEOF(src, entries_by_type), NAMEOF(src, entries), NAMEOF(src, directory))
|
||||
return !(var_name in banned_edits) && ..()
|
||||
|
||||
/datum/controller/configuration/stat_entry()
|
||||
if(!statclick)
|
||||
statclick = new/obj/effect/statclick/debug(null, "Edit", src)
|
||||
stat("[name]:", statclick)
|
||||
/datum/controller/configuration/stat_entry(msg)
|
||||
msg = "Edit"
|
||||
return msg
|
||||
|
||||
/// Your typical GET but returns a config.
|
||||
/datum/controller/configuration/proc/GetEntryDatum(entry_type)
|
||||
|
||||
@@ -16,4 +16,4 @@
|
||||
|
||||
/datum/controller/proc/Recover()
|
||||
|
||||
/datum/controller/proc/stat_entry()
|
||||
/datum/controller/proc/stat_entry(msg)
|
||||
|
||||
@@ -95,8 +95,6 @@ GLOBAL_REAL(Failsafe, /datum/controller/failsafe)
|
||||
/datum/controller/failsafe/proc/defcon_pretty()
|
||||
return defcon
|
||||
|
||||
/datum/controller/failsafe/stat_entry()
|
||||
if(!statclick)
|
||||
statclick = new/obj/effect/statclick/debug(null, "Initializing...", src)
|
||||
|
||||
stat("Failsafe Controller:", statclick.update("Defcon: [defcon_pretty()] (Interval: [Failsafe.processing_interval] | Iteration: [Failsafe.master_iteration])"))
|
||||
/datum/controller/failsafe/stat_entry(msg)
|
||||
msg = "Defcon: [defcon_pretty()] (Interval: [Failsafe.processing_interval] | Iteration: [Failsafe.master_iteration])"
|
||||
return msg
|
||||
|
||||
@@ -24,11 +24,9 @@ GLOBAL_REAL(GLOB, /datum/controller/global_vars)
|
||||
//fuck off kevinz
|
||||
return QDEL_HINT_IWILLGC
|
||||
|
||||
/datum/controller/global_vars/stat_entry()
|
||||
if(!statclick)
|
||||
statclick = new/obj/effect/statclick/debug(null, "Initializing...", src)
|
||||
|
||||
stat("Globals:", statclick.update("Edit"))
|
||||
/datum/controller/global_vars/stat_entry(msg)
|
||||
msg = "Edit"
|
||||
return msg
|
||||
|
||||
/datum/controller/global_vars/vv_edit_var(var_name, var_value)
|
||||
if(gvars_datum_protected_varlist[var_name])
|
||||
|
||||
@@ -615,13 +615,10 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
|
||||
skip_ticks = 1
|
||||
|
||||
|
||||
/datum/controller/master/stat_entry()
|
||||
if(!statclick)
|
||||
statclick = new/obj/effect/statclick/debug(null, "Initializing...", src)
|
||||
/datum/controller/master/stat_entry(msg)
|
||||
msg = "(TickRate:[Master.processing]) (Iteration:[Master.iteration]) (TickLimit: [round(Master.current_ticklimit, 0.1)])"
|
||||
return msg
|
||||
|
||||
stat("Byond:", "(FPS:[world.fps]) (TickCount:[world.time/world.tick_lag]) (TickDrift:[round(Master.tickdrift,1)]([round((Master.tickdrift/(world.time/world.tick_lag))*100,0.1)]%)) (Internal Tick Usage: [round(MAPTICK_LAST_INTERNAL_TICK_USAGE,0.1)]%)")
|
||||
stat("Master Controller:", statclick.update("(TickRate:[Master.processing]) (Iteration:[Master.iteration]) (TickLimit: [round(Master.current_ticklimit, 0.1)])"))
|
||||
stat("Misc Subsystems", misc_statclick)
|
||||
|
||||
/datum/controller/master/StartLoadingMap()
|
||||
//disallow more than one map to load at once, multithreading it will just cause race conditions
|
||||
|
||||
@@ -223,23 +223,12 @@
|
||||
log_subsystem("INIT", msg)
|
||||
return time
|
||||
|
||||
//hook for printing stats to the "MC" statuspanel for admins to see performance and related stats etc.
|
||||
/datum/controller/subsystem/stat_entry(msg)
|
||||
if(!statclick)
|
||||
statclick = new/obj/effect/statclick/debug(null, "Initializing...", src)
|
||||
|
||||
|
||||
|
||||
if(can_fire && !(SS_NO_FIRE & flags))
|
||||
msg = "[round(cost,1)]ms|[round(tick_usage,1)]%([round(tick_overrun,1)]%)|[round(ticks,0.1)]\t[msg]"
|
||||
else
|
||||
msg = "OFFLINE\t[msg]"
|
||||
|
||||
var/title = name
|
||||
if (can_fire)
|
||||
title = "\[[state_letter()]][title]"
|
||||
|
||||
stat(title, statclick.update(msg))
|
||||
return msg
|
||||
|
||||
/datum/controller/subsystem/proc/state_letter()
|
||||
switch (state)
|
||||
|
||||
@@ -7,8 +7,9 @@ SUBSYSTEM_DEF(acid)
|
||||
var/list/currentrun = list()
|
||||
var/list/processing = list()
|
||||
|
||||
/datum/controller/subsystem/acid/stat_entry()
|
||||
..("P:[processing.len]")
|
||||
/datum/controller/subsystem/acid/stat_entry(msg)
|
||||
msg = "P:[length(processing)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/acid/fire(resumed = 0)
|
||||
|
||||
@@ -6,12 +6,13 @@ SUBSYSTEM_DEF(adjacent_air)
|
||||
priority = FIRE_PRIORITY_ATMOS_ADJACENCY
|
||||
var/list/queue = list()
|
||||
|
||||
/datum/controller/subsystem/adjacent_air/stat_entry()
|
||||
/datum/controller/subsystem/adjacent_air/stat_entry(msg)
|
||||
#ifdef TESTING
|
||||
..("P:[length(queue)], S:[GLOB.atmos_adjacent_savings[1]], T:[GLOB.atmos_adjacent_savings[2]]")
|
||||
msg = "P:[length(queue)], S:[GLOB.atmos_adjacent_savings[1]], T:[GLOB.atmos_adjacent_savings[2]]"
|
||||
#else
|
||||
..("P:[length(queue)]")
|
||||
msg = "P:[length(queue)]"
|
||||
#endif
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/adjacent_air/Initialize()
|
||||
while(length(queue))
|
||||
|
||||
@@ -63,7 +63,7 @@ SUBSYSTEM_DEF(air)
|
||||
msg += "GA:[get_amt_gas_mixes()]|"
|
||||
msg += "MG:[get_max_gas_mixes()]|"
|
||||
msg += "AT/MS:[round((cost ? active_turfs_len/cost : 0),0.1)]"
|
||||
..(msg)
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/air/Initialize(timeofday)
|
||||
extools_update_ssair()
|
||||
|
||||
@@ -9,7 +9,8 @@ SUBSYSTEM_DEF(augury)
|
||||
var/list/observers_given_action = list()
|
||||
|
||||
/datum/controller/subsystem/augury/stat_entry(msg)
|
||||
..("W:[watchers.len]|D:[doombringers.len]")
|
||||
msg = "W:[watchers.len]|D:[length(doombringers)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/augury/proc/register_doom(atom/A, severity)
|
||||
doombringers[A] = severity
|
||||
|
||||
@@ -1,3 +1,8 @@
|
||||
/**
|
||||
* Copyright (c) 2020 Aleksej Komarov
|
||||
* SPDX-License-Identifier: MIT
|
||||
*/
|
||||
|
||||
SUBSYSTEM_DEF(chat)
|
||||
name = "Chat"
|
||||
flags = SS_TICKER
|
||||
@@ -16,24 +21,18 @@ SUBSYSTEM_DEF(chat)
|
||||
// Send to tgchat
|
||||
client.tgui_panel?.window.send_message("chat/message", payload)
|
||||
// Send to old chat
|
||||
for(var/msg in payload)
|
||||
SEND_TEXT(client, msg["text"])
|
||||
for(var/message in payload)
|
||||
SEND_TEXT(client, message_to_html(message))
|
||||
if(MC_TICK_CHECK)
|
||||
return
|
||||
|
||||
/datum/controller/subsystem/chat/proc/queue(target, text, flags)
|
||||
/datum/controller/subsystem/chat/proc/queue(target, message)
|
||||
if(islist(target))
|
||||
for(var/_target in target)
|
||||
var/client/client = CLIENT_FROM_VAR(_target)
|
||||
if(client)
|
||||
LAZYADD(payload_by_client[client], list(list(
|
||||
"text" = text,
|
||||
"flags" = flags,
|
||||
)))
|
||||
LAZYADD(payload_by_client[client], list(message))
|
||||
return
|
||||
var/client/client = CLIENT_FROM_VAR(target)
|
||||
if(client)
|
||||
LAZYADD(payload_by_client[client], list(list(
|
||||
"text" = text,
|
||||
"flags" = flags,
|
||||
)))
|
||||
LAZYADD(payload_by_client[client], list(message))
|
||||
|
||||
@@ -20,7 +20,8 @@ SUBSYSTEM_DEF(disease)
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/disease/stat_entry(msg)
|
||||
..("P:[active_diseases.len]")
|
||||
msg = "P:[length(active_diseases)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/disease/proc/get_disease_name(id)
|
||||
var/datum/disease/advance/A = archive_diseases[id]
|
||||
|
||||
@@ -7,8 +7,9 @@ SUBSYSTEM_DEF(fire_burning)
|
||||
var/list/currentrun = list()
|
||||
var/list/processing = list()
|
||||
|
||||
/datum/controller/subsystem/fire_burning/stat_entry()
|
||||
..("P:[processing.len]")
|
||||
/datum/controller/subsystem/fire_burning/stat_entry(msg)
|
||||
msg = "P:[length(processing)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/fire_burning/fire(resumed = 0)
|
||||
@@ -34,4 +35,3 @@ SUBSYSTEM_DEF(fire_burning)
|
||||
|
||||
if (MC_TICK_CHECK)
|
||||
return
|
||||
|
||||
|
||||
@@ -58,7 +58,7 @@ SUBSYSTEM_DEF(garbage)
|
||||
msg += "TGR:[round((totalgcs/(totaldels+totalgcs))*100, 0.01)]%"
|
||||
msg += " P:[pass_counts.Join(",")]"
|
||||
msg += "|F:[fail_counts.Join(",")]"
|
||||
..(msg)
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/garbage/Shutdown()
|
||||
//Adds the del() log to the qdel log file
|
||||
|
||||
@@ -8,10 +8,11 @@ SUBSYSTEM_DEF(idlenpcpool)
|
||||
var/list/currentrun = list()
|
||||
var/static/list/idle_mobs_by_zlevel[][]
|
||||
|
||||
/datum/controller/subsystem/idlenpcpool/stat_entry()
|
||||
/datum/controller/subsystem/idlenpcpool/stat_entry(msg)
|
||||
var/list/idlelist = GLOB.simple_animals[AI_IDLE]
|
||||
var/list/zlist = GLOB.simple_animals[AI_Z_OFF]
|
||||
..("IdleNPCS:[idlelist.len]|Z:[zlist.len]")
|
||||
msg = "IdleNPCS:[length(idlelist)]|Z:[length(zlist)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/idlenpcpool/proc/MaxZChanged()
|
||||
if (!islist(idle_mobs_by_zlevel))
|
||||
|
||||
@@ -7,8 +7,9 @@ SUBSYSTEM_DEF(lighting)
|
||||
wait = 2
|
||||
init_order = INIT_ORDER_LIGHTING
|
||||
|
||||
/datum/controller/subsystem/lighting/stat_entry()
|
||||
..("L:[GLOB.lighting_update_lights.len]|C:[GLOB.lighting_update_corners.len]|O:[GLOB.lighting_update_objects.len]")
|
||||
/datum/controller/subsystem/lighting/stat_entry(msg)
|
||||
msg = "L:[length(GLOB.lighting_update_lights)]|C:[length(GLOB.lighting_update_corners)]|O:[length(GLOB.lighting_update_objects)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/lighting/Initialize(timeofday)
|
||||
|
||||
@@ -22,8 +22,9 @@ SUBSYSTEM_DEF(machines)
|
||||
NewPN.add_cable(PC)
|
||||
propagate_network(PC,PC.powernet)
|
||||
|
||||
/datum/controller/subsystem/machines/stat_entry()
|
||||
..("M:[processing.len]|PN:[powernets.len]")
|
||||
/datum/controller/subsystem/machines/stat_entry(msg)
|
||||
msg = "M:[length(processing)]|PN:[length(powernets)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/machines/fire(resumed = 0)
|
||||
|
||||
@@ -10,8 +10,9 @@ SUBSYSTEM_DEF(mobs)
|
||||
var/static/list/cubemonkeys = list()
|
||||
var/static/list/cheeserats = list()
|
||||
|
||||
/datum/controller/subsystem/mobs/stat_entry()
|
||||
..("P:[GLOB.mob_living_list.len]")
|
||||
/datum/controller/subsystem/mobs/stat_entry(msg)
|
||||
msg = "P:[length(GLOB.mob_living_list)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/mobs/proc/MaxZChanged()
|
||||
if (!islist(clients_by_zlevel))
|
||||
|
||||
@@ -6,9 +6,10 @@ SUBSYSTEM_DEF(npcpool)
|
||||
|
||||
var/list/currentrun = list()
|
||||
|
||||
/datum/controller/subsystem/npcpool/stat_entry()
|
||||
/datum/controller/subsystem/npcpool/stat_entry(msg)
|
||||
var/list/activelist = GLOB.simple_animals[AI_ON]
|
||||
..("NPCS:[activelist.len]")
|
||||
msg = "NPCS:[length(activelist)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/npcpool/fire(resumed = FALSE)
|
||||
|
||||
|
||||
@@ -22,8 +22,9 @@ SUBSYSTEM_DEF(overlays)
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/overlays/stat_entry()
|
||||
..("Ov:[length(queue)]")
|
||||
/datum/controller/subsystem/overlays/stat_entry(msg)
|
||||
msg = "Ov:[length(queue)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/overlays/Shutdown()
|
||||
|
||||
@@ -48,25 +48,6 @@ SUBSYSTEM_DEF(persistence)
|
||||
/datum/controller/subsystem/persistence/proc/LoadSatchels()
|
||||
var/placed_satchel = 0
|
||||
var/path
|
||||
if(fexists("data/npc_saves/SecretSatchels.sav")) //legacy conversion. Will only ever run once.
|
||||
var/savefile/secret_satchels = new /savefile("data/npc_saves/SecretSatchels.sav")
|
||||
for(var/map in secret_satchels)
|
||||
var/json_file = file("data/npc_saves/SecretSatchels[map].json")
|
||||
var/list/legacy_secret_satchels = splittext(secret_satchels[map],"#")
|
||||
var/list/satchels = list()
|
||||
for(var/i=1,i<=legacy_secret_satchels.len,i++)
|
||||
var/satchel_string = legacy_secret_satchels[i]
|
||||
var/list/chosen_satchel = splittext(satchel_string,"|")
|
||||
if(chosen_satchel.len == 3)
|
||||
var/list/data = list()
|
||||
data["x"] = text2num(chosen_satchel[1])
|
||||
data["y"] = text2num(chosen_satchel[2])
|
||||
data["saved_obj"] = chosen_satchel[3]
|
||||
satchels += list(data)
|
||||
var/list/file_data = list()
|
||||
file_data["data"] = satchels
|
||||
WRITE_FILE(json_file, json_encode(file_data))
|
||||
fdel("data/npc_saves/SecretSatchels.sav")
|
||||
|
||||
var/json_file = file("data/npc_saves/SecretSatchels[SSmapping.config.map_name].json")
|
||||
var/list/json = list()
|
||||
|
||||
@@ -10,8 +10,9 @@ SUBSYSTEM_DEF(processing)
|
||||
var/list/processing = list()
|
||||
var/list/currentrun = list()
|
||||
|
||||
/datum/controller/subsystem/processing/stat_entry()
|
||||
..("[stat_tag]:[processing.len]")
|
||||
/datum/controller/subsystem/processing/stat_entry(msg)
|
||||
msg = "[stat_tag]:[length(processing)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/processing/fire(resumed = 0)
|
||||
if (!resumed)
|
||||
|
||||
@@ -12,7 +12,7 @@ SUBSYSTEM_DEF(profiler)
|
||||
/datum/controller/subsystem/profiler/stat_entry(msg)
|
||||
msg += "F:[round(fetch_cost,1)]ms"
|
||||
msg += "|W:[round(write_cost,1)]ms"
|
||||
..(msg)
|
||||
return msg
|
||||
|
||||
/datum/controller/subsystem/profiler/Initialize()
|
||||
if(CONFIG_GET(flag/auto_profile))
|
||||
|
||||
@@ -8,8 +8,9 @@ SUBSYSTEM_DEF(spacedrift)
|
||||
var/list/currentrun = list()
|
||||
var/list/processing = list()
|
||||
|
||||
/datum/controller/subsystem/spacedrift/stat_entry()
|
||||
..("P:[processing.len]")
|
||||
/datum/controller/subsystem/spacedrift/stat_entry(msg)
|
||||
msg = "P:[length(processing)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/spacedrift/fire(resumed = 0)
|
||||
@@ -56,4 +57,3 @@ SUBSYSTEM_DEF(spacedrift)
|
||||
AM.inertia_last_loc = AM.loc
|
||||
if (MC_TICK_CHECK)
|
||||
return
|
||||
|
||||
|
||||
@@ -0,0 +1,119 @@
|
||||
SUBSYSTEM_DEF(statpanels)
|
||||
name = "Stat Panels"
|
||||
wait = 4
|
||||
init_order = INIT_ORDER_STATPANELS //Really early so we can debug MC roundstart
|
||||
runlevels = RUNLEVELS_DEFAULT | RUNLEVEL_LOBBY
|
||||
var/list/currentrun = list()
|
||||
var/encoded_global_data
|
||||
var/mc_data_encoded
|
||||
var/list/cached_images = list()
|
||||
|
||||
/datum/controller/subsystem/statpanels/fire(resumed = FALSE)
|
||||
if(!resumed)
|
||||
var/datum/map_config/cached = SSmapping.next_map_config
|
||||
var/list/global_data = list(
|
||||
"Map: [SSmapping.config?.map_name || "Loading..."]",
|
||||
cached ? "Next Map: [cached.map_name]" : null,
|
||||
"Round ID: [GLOB.round_id ? GLOB.round_id : "NULL"]",
|
||||
"[SStime_track.stat_time_text]",
|
||||
"Station Time: [STATION_TIME_TIMESTAMP("hh:mm:ss", world.time)]",
|
||||
"Time Dilation: [round(SStime_track.time_dilation_current,1)]% AVG:([round(SStime_track.time_dilation_avg_fast,1)]%, [round(SStime_track.time_dilation_avg,1)]%, [round(SStime_track.time_dilation_avg_slow,1)]%)"
|
||||
)
|
||||
|
||||
if(SSshuttle.emergency)
|
||||
var/ETA = SSshuttle.emergency.getModeStr()
|
||||
if(ETA)
|
||||
global_data += "[ETA] [SSshuttle.emergency.getTimerStr()]"
|
||||
encoded_global_data = url_encode(json_encode(global_data))
|
||||
|
||||
var/list/mc_data = list(
|
||||
list("CPU:", world.cpu),
|
||||
list("Instances:", "[num2text(world.contents.len, 10)]"),
|
||||
list("World Time:", "[world.time]"),
|
||||
list("Globals:", GLOB.stat_entry(), "\ref[GLOB]"),
|
||||
list("[config]:", config.stat_entry(), "\ref[config]"),
|
||||
list("Byond:", "(FPS:[world.fps]) (TickCount:[world.time/world.tick_lag]) (TickDrift:[round(Master.tickdrift,1)]([round((Master.tickdrift/(world.time/world.tick_lag))*100,0.1)]%)) (Internal Tick Usage: [round(MAPTICK_LAST_INTERNAL_TICK_USAGE,0.1)]%)"),
|
||||
list("Master Controller:", Master.stat_entry(), "\ref[Master]"),
|
||||
list("Failsafe Controller:", Failsafe.stat_entry(), "\ref[Failsafe]"),
|
||||
list("","")
|
||||
)
|
||||
for(var/ss in Master.subsystems)
|
||||
var/datum/controller/subsystem/sub_system = ss
|
||||
mc_data[++mc_data.len] = list("\[[sub_system.state_letter()]][sub_system.name]", sub_system.stat_entry(), "\ref[sub_system]")
|
||||
mc_data[++mc_data.len] = list("Camera Net", "Cameras: [GLOB.cameranet.cameras.len] | Chunks: [GLOB.cameranet.chunks.len]", "\ref[GLOB.cameranet]")
|
||||
mc_data_encoded = url_encode(json_encode(mc_data))
|
||||
src.currentrun = GLOB.clients.Copy()
|
||||
|
||||
var/list/currentrun = src.currentrun
|
||||
while(length(currentrun))
|
||||
var/client/target = currentrun[length(currentrun)]
|
||||
currentrun.len--
|
||||
var/ping_str = url_encode("Ping: [round(target.lastping, 1)]ms (Average: [round(target.avgping, 1)]ms)")
|
||||
var/other_str = url_encode(json_encode(target.mob.get_status_tab_items()))
|
||||
target << output("[encoded_global_data];[ping_str];[other_str]", "statbrowser:update")
|
||||
if(!target.holder)
|
||||
target << output("", "statbrowser:remove_admin_tabs")
|
||||
else
|
||||
var/turf/eye_turf = get_turf(target.eye)
|
||||
var/coord_entry = url_encode(COORD(eye_turf))
|
||||
target << output("[mc_data_encoded];[coord_entry];[url_encode(target.holder.href_token)]", "statbrowser:update_mc")
|
||||
var/list/ahelp_tickets = GLOB.ahelp_tickets.stat_entry()
|
||||
target << output("[url_encode(json_encode(ahelp_tickets))];", "statbrowser:update_tickets")
|
||||
if(!length(GLOB.sdql2_queries))
|
||||
target << output("", "statbrowser:remove_sdql2")
|
||||
else
|
||||
var/list/sqdl2A = list()
|
||||
sqdl2A[++sqdl2A.len] = list("", "Access Global SDQL2 List", REF(GLOB.sdql2_vv_statobj))
|
||||
var/list/sqdl2B = list()
|
||||
for(var/i in GLOB.sdql2_queries)
|
||||
var/datum/SDQL2_query/Q = i
|
||||
sqdl2B = Q.generate_stat()
|
||||
sqdl2A += sqdl2B
|
||||
target << output(url_encode(json_encode(sqdl2A)), "statbrowser:update_sdql2")
|
||||
var/list/proc_holders = target.mob.get_proc_holders()
|
||||
target.spell_tabs.Cut()
|
||||
for(var/phl in proc_holders)
|
||||
var/list/proc_holder_list = phl
|
||||
target.spell_tabs |= proc_holder_list[1]
|
||||
var/proc_holders_encoded = ""
|
||||
if(length(proc_holders))
|
||||
proc_holders_encoded = url_encode(json_encode(proc_holders))
|
||||
target << output("[url_encode(json_encode(target.spell_tabs))];[proc_holders_encoded]", "statbrowser:update_spells")
|
||||
if(target.mob?.listed_turf)
|
||||
var/mob/target_mob = target.mob
|
||||
if(!target_mob.TurfAdjacent(target_mob.listed_turf))
|
||||
target << output("", "statbrowser:remove_listedturf")
|
||||
target_mob.listed_turf = null
|
||||
else
|
||||
var/list/overrides = list()
|
||||
var/list/turfitems = list()
|
||||
for(var/img in target.images)
|
||||
var/image/target_image = img
|
||||
if(!target_image.loc || target_image.loc.loc != target_mob.listed_turf || !target_image.override)
|
||||
continue
|
||||
overrides += target_image.loc
|
||||
if(!(REF(target_mob.listed_turf) in cached_images))
|
||||
target << browse_rsc(getFlatIcon(target_mob.listed_turf, no_anim = TRUE), "[REF(target_mob.listed_turf)].png")
|
||||
cached_images += REF(target_mob.listed_turf)
|
||||
turfitems[++turfitems.len] = list("[target_mob.listed_turf]", REF(target_mob.listed_turf), "[REF(target_mob.listed_turf)].png")
|
||||
for(var/tc in target_mob.listed_turf)
|
||||
var/atom/movable/turf_content = tc
|
||||
if(turf_content.mouse_opacity == MOUSE_OPACITY_TRANSPARENT)
|
||||
continue
|
||||
if(turf_content.invisibility > target_mob.see_invisible)
|
||||
continue
|
||||
if(turf_content in overrides)
|
||||
continue
|
||||
if(turf_content.IsObscured())
|
||||
continue
|
||||
if(length(turfitems) < 30) // only create images for the first 30 items on the turf, for performance reasons
|
||||
if(!(REF(turf_content) in cached_images))
|
||||
target << browse_rsc(getFlatIcon(turf_content, no_anim = TRUE), "[REF(turf_content)].png")
|
||||
cached_images += REF(turf_content)
|
||||
turfitems[++turfitems.len] = list("[turf_content.name]", REF(turf_content), "[REF(turf_content)].png")
|
||||
else
|
||||
turfitems[++turfitems.len] = list("[turf_content.name]", REF(turf_content))
|
||||
turfitems = url_encode(json_encode(turfitems))
|
||||
target << output("[turfitems];", "statbrowser:update_listedturf")
|
||||
if(MC_TICK_CHECK)
|
||||
return
|
||||
@@ -24,15 +24,16 @@ SUBSYSTEM_DEF(tgui)
|
||||
var/basehtml
|
||||
|
||||
/datum/controller/subsystem/tgui/PreInit()
|
||||
basehtml = file2text('tgui/packages/tgui/public/tgui.html')
|
||||
basehtml = file2text('tgui/public/tgui.html')
|
||||
|
||||
/datum/controller/subsystem/tgui/Shutdown()
|
||||
close_all_uis()
|
||||
|
||||
/datum/controller/subsystem/tgui/stat_entry()
|
||||
..("P:[open_uis.len]")
|
||||
/datum/controller/subsystem/tgui/stat_entry(msg)
|
||||
msg = "P:[length(open_uis)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/tgui/fire(resumed = 0)
|
||||
/datum/controller/subsystem/tgui/fire(resumed = FALSE)
|
||||
if(!resumed)
|
||||
src.current_run = open_uis.Copy()
|
||||
// Cache for sanic speed (lists are references anyways)
|
||||
@@ -81,7 +82,8 @@ SUBSYSTEM_DEF(tgui)
|
||||
window_found = TRUE
|
||||
break
|
||||
if(!window_found)
|
||||
log_tgui(user, "Error: Pool exhausted")
|
||||
log_tgui(user, "Error: Pool exhausted",
|
||||
context = "SStgui/request_pooled_window")
|
||||
return null
|
||||
return window
|
||||
|
||||
@@ -93,7 +95,7 @@ SUBSYSTEM_DEF(tgui)
|
||||
* required user mob
|
||||
*/
|
||||
/datum/controller/subsystem/tgui/proc/force_close_all_windows(mob/user)
|
||||
log_tgui(user, "force_close_all_windows")
|
||||
log_tgui(user, context = "SStgui/force_close_all_windows")
|
||||
if(user.client)
|
||||
user.client.tgui_windows = list()
|
||||
for(var/i in 1 to TGUI_WINDOW_HARD_LIMIT)
|
||||
@@ -109,7 +111,7 @@ SUBSYSTEM_DEF(tgui)
|
||||
* required window_id string
|
||||
*/
|
||||
/datum/controller/subsystem/tgui/proc/force_close_window(mob/user, window_id)
|
||||
log_tgui(user, "force_close_window")
|
||||
log_tgui(user, context = "SStgui/force_close_window")
|
||||
// Close all tgui datums based on window_id.
|
||||
for(var/datum/tgui/ui in user.tgui_open_uis)
|
||||
if(ui.window && ui.window.id == window_id)
|
||||
|
||||
@@ -11,8 +11,9 @@ SUBSYSTEM_DEF(throwing)
|
||||
var/list/currentrun
|
||||
var/list/processing = list()
|
||||
|
||||
/datum/controller/subsystem/throwing/stat_entry()
|
||||
..("P:[processing.len]")
|
||||
/datum/controller/subsystem/throwing/stat_entry(msg)
|
||||
msg = "P:[length(processing)]"
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/controller/subsystem/throwing/fire(resumed = 0)
|
||||
|
||||
@@ -396,6 +396,7 @@ SUBSYSTEM_DEF(ticker)
|
||||
SSjob.EquipRank(N, player.mind.assigned_role, 0)
|
||||
if(CONFIG_GET(flag/roundstart_traits) && ishuman(N.new_character))
|
||||
SSquirks.AssignQuirks(N.new_character, N.client, TRUE, TRUE, SSjob.GetJob(player.mind.assigned_role), FALSE, N)
|
||||
N.client.prefs.post_copy_to(player)
|
||||
CHECK_TICK
|
||||
if(captainless)
|
||||
for(var/mob/dead/new_player/N in GLOB.player_list)
|
||||
@@ -416,6 +417,7 @@ SUBSYSTEM_DEF(ticker)
|
||||
living.client.prefs.chat_toggles ^= CHAT_OOC
|
||||
var/obj/screen/splash/S = new(living.client, TRUE)
|
||||
S.Fade(TRUE)
|
||||
living.client.init_verbs()
|
||||
livings += living
|
||||
if(livings.len)
|
||||
addtimer(CALLBACK(src, .proc/release_characters, livings), 30, TIMER_CLIENT_TIME)
|
||||
|
||||
@@ -34,7 +34,8 @@ SUBSYSTEM_DEF(timer)
|
||||
bucket_resolution = world.tick_lag
|
||||
|
||||
/datum/controller/subsystem/timer/stat_entry(msg)
|
||||
..("B:[bucket_count] P:[length(second_queue)] H:[length(hashes)] C:[length(clienttime_timers)] S:[length(timer_id_dict)]")
|
||||
msg = "B:[bucket_count] P:[length(second_queue)] H:[length(hashes)] C:[length(clienttime_timers)] S:[length(timer_id_dict)]"
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/timer/fire(resumed = FALSE)
|
||||
var/lit = last_invoke_tick
|
||||
|
||||
@@ -99,7 +99,6 @@ Bonus
|
||||
*/
|
||||
|
||||
/datum/symptom/alkali
|
||||
|
||||
name = "Alkali perspiration"
|
||||
desc = "The virus attaches to sudoriparous glands, synthesizing a chemical that bursts into flames when reacting with water, leading to self-immolation."
|
||||
stealth = 2
|
||||
|
||||
@@ -51,7 +51,7 @@ GLOBAL_LIST_EMPTY(mobs_with_editable_flavor_text) //et tu, hacky code
|
||||
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
|
||||
remove_verb(M, /mob/proc/manage_flavor_tests)
|
||||
|
||||
/datum/element/flavor_text/proc/show_flavor(atom/target, mob/user, list/examine_list)
|
||||
if(!always_show && isliving(target))
|
||||
|
||||
@@ -61,7 +61,7 @@
|
||||
A.AddElement(/datum/element/update_icon_updates_onmob)
|
||||
RegisterSignal(A, COMSIG_ITEM_WORN_OVERLAYS, .proc/apply_worn_overlays)
|
||||
if(suits_with_helmet_typecache[A.type])
|
||||
RegisterSignal(A, COMSIG_SUIT_MADE_HELMET, .proc/register_helmet)
|
||||
RegisterSignal(A, COMSIG_SUIT_MADE_HELMET, .proc/register_helmet) //you better work now you slut
|
||||
else if(_flags & POLYCHROMIC_ACTION && ismob(A)) //in the event mob update icon procs are ever standarized.
|
||||
var/datum/action/polychromic/P = new(A)
|
||||
RegisterSignal(P, COMSIG_ACTION_TRIGGER, .proc/activate_action)
|
||||
@@ -166,6 +166,15 @@
|
||||
examine_list += "<span class='notice'>Alt-click to recolor it.</span>"
|
||||
|
||||
/datum/element/polychromic/proc/register_helmet(atom/source, obj/item/clothing/head/H)
|
||||
if(!isitem(H)) //backup in case if it messes up somehow
|
||||
if(istype(source,/obj/item/clothing/suit/hooded)) //so how come it be like this, where toggleable headslots are named separately (helmet/hood) anyways?
|
||||
var/obj/item/clothing/suit/hooded/sourcesuit = source
|
||||
H = sourcesuit.hood
|
||||
else if(istype(source,/obj/item/clothing/suit/space/hardsuit))
|
||||
var/obj/item/clothing/suit/space/hardsuit/sourcesuit = source
|
||||
H = sourcesuit.helmet
|
||||
else
|
||||
return
|
||||
suit_by_helmet[H] = source
|
||||
helmet_by_suit[source] = H
|
||||
colors_by_atom[H] = colors_by_atom[source]
|
||||
|
||||
@@ -64,7 +64,7 @@
|
||||
else if(make_temporary)
|
||||
base = H.mind.default_martial_art
|
||||
if(help_verb)
|
||||
H.verbs += help_verb
|
||||
add_verb(H, help_verb)
|
||||
H.mind.martial_art = src
|
||||
if(pugilist)
|
||||
ADD_TRAIT(H, TRAIT_PUGILIST, MARTIAL_ARTIST_TRAIT)
|
||||
@@ -90,7 +90,7 @@
|
||||
|
||||
/datum/martial_art/proc/on_remove(mob/living/carbon/human/H)
|
||||
if(help_verb)
|
||||
H.verbs -= help_verb
|
||||
remove_verb(H, help_verb)
|
||||
return
|
||||
|
||||
///Gets called when a projectile hits the owner. Returning anything other than BULLET_ACT_HIT will stop the projectile from hitting the mob.
|
||||
|
||||
@@ -285,6 +285,17 @@ Unless you know what you're doing, only use the first three numbers. They're in
|
||||
beauty_modifier = -0.15
|
||||
texture_layer_icon_state = "runed"
|
||||
|
||||
/datum/material/brass
|
||||
name = "brass"
|
||||
desc = "Tybel gb-Ratvar"
|
||||
color = "#917010"
|
||||
categories = list(MAT_CATEGORY_RIGID = TRUE, MAT_CATEGORY_BASE_RECIPES = TRUE)
|
||||
strength_modifier = 1.3 // Replicant Alloy is very good for skull beatings..
|
||||
sheet_type = /obj/item/stack/tile/brass
|
||||
value_per_unit = 0.75
|
||||
armor_modifiers = list("melee" = 1.4, "bullet" = 1.4, "laser" = 0, "energy" = 0, "bomb" = 1.4, "bio" = 1.2, "rad" = 1.5, "fire" = 1.5, "acid" = 1.5) //But it has.. a few problems that can't easily be compensated for.
|
||||
beauty_modifier = 0.3 //It really beats the cold plain plating of the station, doesn't it?
|
||||
|
||||
/datum/material/bronze
|
||||
name = "bronze"
|
||||
desc = "Clock Cult? Never heard of it."
|
||||
|
||||
@@ -132,6 +132,7 @@
|
||||
new_character.key = key //now transfer the key to link the client to our new body
|
||||
if(new_character.client)
|
||||
LAZYCLEARLIST(new_character.client.recent_examines)
|
||||
new_character.client.init_verbs() // re-initialize character specific verbs
|
||||
current.update_atom_languages()
|
||||
|
||||
//CIT CHANGE - makes arousal update when transfering bodies
|
||||
@@ -693,6 +694,7 @@
|
||||
if(istype(S, spell))
|
||||
spell_list -= S
|
||||
qdel(S)
|
||||
current?.client << output(null, "statbrowser:check_spells")
|
||||
|
||||
/datum/mind/proc/RemoveAllSpells()
|
||||
for(var/obj/effect/proc_holder/S in spell_list)
|
||||
|
||||
@@ -204,6 +204,11 @@
|
||||
mood_change = -1
|
||||
timeout = 2 MINUTES
|
||||
|
||||
/datum/mood_event/plush_bite
|
||||
description = "<span class='warning'>IT BIT ME!! OW!</span>\n"
|
||||
mood_change = -3
|
||||
timeout = 2 MINUTES
|
||||
|
||||
//Cursed stuff below
|
||||
|
||||
/datum/mood_event/emptypred
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
var/lowest_value = 256 * 8
|
||||
var/text_gain_indication = ""
|
||||
var/text_lose_indication = ""
|
||||
var/list/mutable_appearance/visual_indicators = list()
|
||||
var/list/visual_indicators = list()
|
||||
var/obj/effect/proc_holder/spell/power
|
||||
var/layer_used = MUTATIONS_LAYER //which mutation layer to use
|
||||
var/list/species_allowed = list() //to restrict mutation to only certain species
|
||||
|
||||
@@ -211,24 +211,27 @@ GLOBAL_LIST_EMPTY(family_heirlooms)
|
||||
H.gain_trauma(T, TRAUMA_RESILIENCE_ABSOLUTE)
|
||||
|
||||
/datum/quirk/paraplegic/on_spawn()
|
||||
if(quirk_holder.buckled) // Handle late joins being buckled to arrival shuttle chairs.
|
||||
quirk_holder.buckled.unbuckle_mob(quirk_holder)
|
||||
if(quirk_holder.client)
|
||||
var/modified_limbs = quirk_holder.client.prefs.modified_limbs
|
||||
if(!(modified_limbs[BODY_ZONE_L_LEG] == LOADOUT_LIMB_AMPUTATED && modified_limbs[BODY_ZONE_R_LEG] == LOADOUT_LIMB_AMPUTATED && !isjellyperson(quirk_holder)))
|
||||
if(quirk_holder.buckled) // Handle late joins being buckled to arrival shuttle chairs.
|
||||
quirk_holder.buckled.unbuckle_mob(quirk_holder)
|
||||
|
||||
var/turf/T = get_turf(quirk_holder)
|
||||
var/obj/structure/chair/spawn_chair = locate() in T
|
||||
var/turf/T = get_turf(quirk_holder)
|
||||
var/obj/structure/chair/spawn_chair = locate() in T
|
||||
|
||||
var/obj/vehicle/ridden/wheelchair/wheels = new(T)
|
||||
if(spawn_chair) // Makes spawning on the arrivals shuttle more consistent looking
|
||||
wheels.setDir(spawn_chair.dir)
|
||||
var/obj/vehicle/ridden/wheelchair/wheels = new(T)
|
||||
if(spawn_chair) // Makes spawning on the arrivals shuttle more consistent looking
|
||||
wheels.setDir(spawn_chair.dir)
|
||||
|
||||
wheels.buckle_mob(quirk_holder)
|
||||
wheels.buckle_mob(quirk_holder)
|
||||
|
||||
// During the spawning process, they may have dropped what they were holding, due to the paralysis
|
||||
// So put the things back in their hands.
|
||||
// During the spawning process, they may have dropped what they were holding, due to the paralysis
|
||||
// So put the things back in their hands.
|
||||
|
||||
for(var/obj/item/I in T)
|
||||
if(I.fingerprintslast == quirk_holder.ckey)
|
||||
quirk_holder.put_in_hands(I)
|
||||
for(var/obj/item/I in T)
|
||||
if(I.fingerprintslast == quirk_holder.ckey)
|
||||
quirk_holder.put_in_hands(I)
|
||||
|
||||
/datum/quirk/poor_aim
|
||||
name = "Poor Aim"
|
||||
@@ -244,42 +247,6 @@ GLOBAL_LIST_EMPTY(family_heirlooms)
|
||||
mob_trait = TRAIT_PROSOPAGNOSIA
|
||||
medical_record_text = "Patient suffers from prosopagnosia and cannot recognize faces."
|
||||
|
||||
/datum/quirk/prosthetic_limb
|
||||
name = "Prosthetic Limb"
|
||||
desc = "An accident caused you to lose one of your limbs. Because of this, you now have a random prosthetic!"
|
||||
value = -1
|
||||
var/slot_string = "limb"
|
||||
|
||||
/datum/quirk/prosthetic_limb/on_spawn()
|
||||
var/mob/living/carbon/human/H = quirk_holder
|
||||
var/limb_slot
|
||||
if(HAS_TRAIT(H, TRAIT_PARA))//Prevent paraplegic legs being replaced
|
||||
limb_slot = pick(BODY_ZONE_L_ARM, BODY_ZONE_R_ARM)
|
||||
else
|
||||
limb_slot = pick(BODY_ZONE_L_ARM, BODY_ZONE_R_ARM, BODY_ZONE_L_LEG, BODY_ZONE_R_LEG)
|
||||
var/obj/item/bodypart/old_part = H.get_bodypart(limb_slot)
|
||||
var/obj/item/bodypart/prosthetic
|
||||
switch(limb_slot)
|
||||
if(BODY_ZONE_L_ARM)
|
||||
prosthetic = new/obj/item/bodypart/l_arm/robot/surplus(quirk_holder)
|
||||
slot_string = "left arm"
|
||||
if(BODY_ZONE_R_ARM)
|
||||
prosthetic = new/obj/item/bodypart/r_arm/robot/surplus(quirk_holder)
|
||||
slot_string = "right arm"
|
||||
if(BODY_ZONE_L_LEG)
|
||||
prosthetic = new/obj/item/bodypart/l_leg/robot/surplus(quirk_holder)
|
||||
slot_string = "left leg"
|
||||
if(BODY_ZONE_R_LEG)
|
||||
prosthetic = new/obj/item/bodypart/r_leg/robot/surplus(quirk_holder)
|
||||
slot_string = "right leg"
|
||||
prosthetic.replace_limb(H)
|
||||
qdel(old_part)
|
||||
H.regenerate_icons()
|
||||
|
||||
/datum/quirk/prosthetic_limb/post_add()
|
||||
to_chat(quirk_holder, "<span class='boldannounce'>Your [slot_string] has been replaced with a surplus prosthetic. It is fragile and will easily come apart under duress. Additionally, \
|
||||
you need to use a welding tool and cables to repair it, instead of bruise packs and ointment.</span>")
|
||||
|
||||
/datum/quirk/insanity
|
||||
name = "Reality Dissociation Syndrome"
|
||||
desc = "You suffer from a severe disorder that causes very vivid hallucinations. Mindbreaker toxin can suppress its effects, and you are immune to mindbreaker's hallucinogenic properties. <b>This is not a license to grief.</b>"
|
||||
|
||||
@@ -71,7 +71,7 @@
|
||||
/datum/wires/airlock/on_pulse(wire)
|
||||
set waitfor = FALSE
|
||||
var/obj/machinery/door/airlock/A = holder
|
||||
if(!A.hasSiliconAccessInArea(usr) && A.isElectrified() && A.shock(usr, 100))
|
||||
if(usr && !A.hasSiliconAccessInArea(usr) && A.isElectrified() && A.shock(usr, 100))
|
||||
return FALSE
|
||||
switch(wire)
|
||||
if(WIRE_POWER1, WIRE_POWER2) // Pulse to loose power.
|
||||
@@ -127,7 +127,7 @@
|
||||
|
||||
/datum/wires/airlock/on_cut(wire, mend)
|
||||
var/obj/machinery/door/airlock/A = holder
|
||||
if(!A.hasSiliconAccessInArea(usr) && A.isElectrified() && A.shock(usr, 100))
|
||||
if(usr && !A.hasSiliconAccessInArea(usr) && A.isElectrified() && A.shock(usr, 100))
|
||||
return FALSE
|
||||
switch(wire)
|
||||
if(WIRE_POWER1, WIRE_POWER2) // Cut to loose power, repair all to gain power.
|
||||
|
||||
@@ -40,7 +40,7 @@
|
||||
new_ai = select_active_ai(R)
|
||||
R.notify_ai(DISCONNECT)
|
||||
if(new_ai && (new_ai != R.connected_ai))
|
||||
R.connected_ai = new_ai
|
||||
R.set_connected_ai(new_ai)
|
||||
if(R.shell)
|
||||
R.undeploy() //If this borg is an AI shell, disconnect the controlling AI and assign ti to a new AI
|
||||
R.notify_ai(AI_SHELL)
|
||||
@@ -69,7 +69,7 @@
|
||||
R.notify_ai(DISCONNECT)
|
||||
if(R.shell)
|
||||
R.undeploy()
|
||||
R.connected_ai = null
|
||||
R.set_connected_ai(null)
|
||||
if(WIRE_LAWSYNC) // Cut the law wire, and the borg will no longer receive law updates from its AI. Repair and it will re-sync.
|
||||
if(mend)
|
||||
if(!R.emagged)
|
||||
|
||||
@@ -43,6 +43,7 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
|
||||
outdoors = TRUE
|
||||
ambientsounds = SPACE
|
||||
blob_allowed = FALSE //Eating up space doesn't count for victory as a blob.
|
||||
considered_hull_exterior = TRUE
|
||||
|
||||
/area/space/nearstation
|
||||
icon_state = "space_near"
|
||||
@@ -1592,4 +1593,4 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
|
||||
valid_territory = FALSE
|
||||
outdoors = TRUE
|
||||
ambientsounds = SPACE
|
||||
blob_allowed = FALSE //While part of the station, what good will it do you?
|
||||
blob_allowed = FALSE //While part of the station, what good will it do you?
|
||||
|
||||
@@ -34,6 +34,9 @@
|
||||
/// If megafauna can be spawned by natural random generation
|
||||
var/megafauna_spawn_allowed = FALSE
|
||||
|
||||
/// Considered space for hull shielding
|
||||
var/considered_hull_exterior = FALSE
|
||||
|
||||
var/fire = null
|
||||
var/atmos = TRUE
|
||||
var/atmosalm = FALSE
|
||||
|
||||
@@ -1127,3 +1127,21 @@
|
||||
*/
|
||||
/atom/proc/rust_heretic_act()
|
||||
return
|
||||
|
||||
///Passes Stat Browser Panel clicks to the game and calls client click on an atom
|
||||
/atom/Topic(href, list/href_list)
|
||||
. = ..()
|
||||
if(!usr?.client)
|
||||
return
|
||||
var/client/usr_client = usr.client
|
||||
var/list/paramslist = list()
|
||||
if(href_list["statpanel_item_shiftclick"])
|
||||
paramslist["shift"] = "1"
|
||||
if(href_list["statpanel_item_ctrlclick"])
|
||||
paramslist["ctrl"] = "1"
|
||||
if(href_list["statpanel_item_altclick"])
|
||||
paramslist["alt"] = "1"
|
||||
if(href_list["statpanel_item_click"])
|
||||
// first of all make sure we valid
|
||||
var/mouseparams = list2params(paramslist)
|
||||
usr_client.Click(src, loc, null, mouseparams)
|
||||
|
||||
@@ -8,7 +8,8 @@ GLOBAL_VAR_INIT(hsboxspawn, TRUE)
|
||||
sandbox.owner = src.ckey
|
||||
if(src.client.holder)
|
||||
sandbox.admin = 1
|
||||
verbs += new/mob/proc/sandbox_panel
|
||||
add_verb(src, /mob/proc/sandbox_panel)
|
||||
|
||||
/mob/proc/sandbox_panel()
|
||||
set name = "Sandbox Panel"
|
||||
if(sandbox)
|
||||
|
||||
@@ -178,9 +178,12 @@
|
||||
table[y1][x1] += 10
|
||||
if(href_list["same_board"]) //Reset the board... kinda
|
||||
if(game_status != MINESWEEPER_GAME_PLAYING)
|
||||
mine_sound = TRUE
|
||||
game_status = MINESWEEPER_GAME_PLAYING
|
||||
if(table[y1][x1] >= 10) //If revealed, become unrevealed!
|
||||
playsound(loc, 'sound/arcade/minesweeper_menuselect.ogg', 50, 0, extrarange = -3, falloff = 10)
|
||||
if(mine_sound)
|
||||
playsound(loc, 'sound/arcade/minesweeper_menuselect.ogg', 50, 0, extrarange = -3, falloff = 10)
|
||||
mine_sound = FALSE
|
||||
table[y1][x1] -= 10
|
||||
if(table[y1][x1] > 10 && !reset_board)
|
||||
safe_squares_revealed += 1
|
||||
|
||||
@@ -38,3 +38,14 @@
|
||||
if(stat & (BROKEN|NOPOWER))
|
||||
return
|
||||
drive()
|
||||
|
||||
/obj/machinery/mass_driver/pressure_plate
|
||||
name = "pressure plated mass driver"
|
||||
var/drive_delay = 10
|
||||
|
||||
/obj/machinery/mass_driver/pressure_plate/Crossed(atom/movable/O)
|
||||
. = ..()
|
||||
if(isliving(O))
|
||||
var/mob/living/L = O
|
||||
to_chat(L, "<span class='warning'>You feel something click beneath you!</span>")
|
||||
addtimer(CALLBACK(src, .proc/drive), drive_delay)
|
||||
@@ -100,7 +100,7 @@
|
||||
// So he can't jump out the gate right away.
|
||||
R.SetLockdown()
|
||||
if(masterAI)
|
||||
R.connected_ai = masterAI
|
||||
R.set_connected_ai(masterAI)
|
||||
R.lawsync()
|
||||
R.lawupdate = 1
|
||||
addtimer(CALLBACK(src, .proc/unlock_new_robot, R), 50)
|
||||
|
||||
@@ -113,8 +113,7 @@
|
||||
if (loc != user)
|
||||
return ..()
|
||||
if(SEND_SIGNAL(src, COMSIG_IS_STORAGE_LOCKED))
|
||||
ui_interact(user)
|
||||
return
|
||||
INVOKE_ASYNC(src, /datum.proc/ui_interact, user)
|
||||
|
||||
/obj/item/storage/portable_chem_mixer/attack_self(mob/user)
|
||||
if(loc == user)
|
||||
|
||||
@@ -255,7 +255,7 @@
|
||||
/obj/item/choice_beacon/box/plushie/generate_display_names()
|
||||
var/list/plushie_list = list()
|
||||
//plushie set 1: just subtypes of /obj/item/toy/plush
|
||||
var/list/plushies_set_one = subtypesof(/obj/item/toy/plush) - list(/obj/item/toy/plush/narplush, /obj/item/toy/plush/awakenedplushie, /obj/item/toy/plush/random_snowflake, /obj/item/toy/plush/random) //don't allow these special ones (you can still get narplush/hugbox)
|
||||
var/list/plushies_set_one = subtypesof(/obj/item/toy/plush) - list(/obj/item/toy/plush/narplush, /obj/item/toy/plush/awakenedplushie, /obj/item/toy/plush/random_snowflake, /obj/item/toy/plush/plushling, /obj/item/toy/plush/random) //don't allow these special ones (you can still get narplush/hugbox)
|
||||
for(var/V in plushies_set_one)
|
||||
var/atom/A = V
|
||||
plushie_list[initial(A.name)] = A
|
||||
@@ -272,4 +272,3 @@
|
||||
icon_state = "skub"
|
||||
w_class = WEIGHT_CLASS_BULKY
|
||||
attack_verb = list("skubbed")
|
||||
|
||||
|
||||
@@ -167,7 +167,7 @@
|
||||
return
|
||||
log_game("[key_name(user)] activated a hidden grenade in [src].")
|
||||
grenade.preprime(user, msg = FALSE, volume = 10)
|
||||
SEND_SIGNAL(user, COMSIG_ADD_MOOD_EVENT,"plushpet", /datum/mood_event/plushpet)
|
||||
SEND_SIGNAL(user, COMSIG_ADD_MOOD_EVENT,"plushpet", /datum/mood_event/plushpet)
|
||||
else
|
||||
to_chat(user, "<span class='notice'>You try to pet [src], but it has no stuffing. Aww...</span>")
|
||||
SEND_SIGNAL(user, COMSIG_ADD_MOOD_EVENT,"plush_nostuffing", /datum/mood_event/plush_nostuffing)
|
||||
@@ -754,8 +754,8 @@ GLOBAL_LIST_INIT(valid_plushie_paths, valid_plushie_paths())
|
||||
attack_verb = list("headbutt", "scritched", "bit")
|
||||
squeak_override = list('modular_citadel/sound/voice/nya.ogg' = 1)
|
||||
can_random_spawn = FALSE
|
||||
|
||||
|
||||
|
||||
|
||||
/obj/item/toy/plush/hairball
|
||||
name = "Hairball"
|
||||
desc = "A bundle of undigested fibers and scales. Yuck."
|
||||
@@ -765,3 +765,78 @@ GLOBAL_LIST_INIT(valid_plushie_paths, valid_plushie_paths())
|
||||
squeak_override = list('sound/misc/splort.ogg'=1)
|
||||
attack_verb = list("sploshed", "splorted", "slushed")
|
||||
can_random_spawn = FALSE
|
||||
|
||||
/obj/item/toy/plush/plushling
|
||||
name = "peculiar plushie"
|
||||
desc = "An adorable stuffed toy- wait, did it just move?"
|
||||
can_random_spawn = FALSE
|
||||
var/absorb_cooldown = 100 //ticks cooldown between absorbs
|
||||
var/next_absorb = 0 //When can it absorb another plushie
|
||||
var/check_interval = 20
|
||||
var/next_check = 0
|
||||
|
||||
//Overrides parent proc
|
||||
/obj/item/toy/plush/plushling/attack_self(mob/user)
|
||||
if(!user) //hmmmmm
|
||||
return
|
||||
to_chat(user, "<span class='warning'>You try to pet the plushie, but recoil as it bites your hand instead! OW!</span>")
|
||||
SEND_SIGNAL(user, COMSIG_ADD_MOOD_EVENT,"plush_bite", /datum/mood_event/plush_bite)
|
||||
var/mob/living/carbon/human/H = user
|
||||
if(!H)
|
||||
return //Type safety.
|
||||
H.apply_damage(5, BRUTE, pick(BODY_ZONE_L_ARM, BODY_ZONE_R_ARM))
|
||||
addtimer(CALLBACK(H, /mob/living/carbon/human.proc/dropItemToGround, src, TRUE), 1)
|
||||
|
||||
/obj/item/toy/plush/plushling/New()
|
||||
var/initial_state = pick("plushie_lizard", "plushie_snake", "plushie_slime", "fox")
|
||||
icon_state = initial_state
|
||||
item_state = initial_state
|
||||
START_PROCESSING(SSobj, src)
|
||||
. = ..()
|
||||
|
||||
/obj/item/toy/plush/plushling/Destroy()
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
. = ..()
|
||||
|
||||
/obj/item/toy/plush/plushling/process()
|
||||
if(world.time < next_absorb || world.time < next_check)
|
||||
return
|
||||
next_check = world.time + check_interval
|
||||
var/obj/item/toy/plush/target
|
||||
for(var/obj/item/toy/plush/possible_target in loc) //First, it tries to get anything in its same location, be it a tile or a backpack
|
||||
if(possible_target == src || istype(possible_target, /obj/item/toy/plush/plushling))
|
||||
continue
|
||||
target = possible_target
|
||||
break
|
||||
if(!target)
|
||||
if(!isturf(loc))
|
||||
return
|
||||
for(var/obj/item/toy/plush/P in oview(1, src)) //If that doesn't work, it hunts for plushies adjacent to its own tile
|
||||
if(istype(P, /obj/item/toy/plush/plushling)) //These do not hunt their own kind
|
||||
continue
|
||||
src.throw_at(P, 1, 2)
|
||||
visible_message("<span class='danger'>[src] leaps at [P]!</span>")
|
||||
break
|
||||
return
|
||||
if(istype(target, /obj/item/toy/plush/plushling)) //These do not consume their own.
|
||||
return
|
||||
next_absorb = world.time + absorb_cooldown
|
||||
plushie_absorb(target)
|
||||
|
||||
/obj/item/toy/plush/plushling/proc/plushie_absorb(obj/item/toy/plush/victim)
|
||||
if(!victim)
|
||||
return
|
||||
visible_message("<span class='warning'>[src] gruesomely mutilliates [victim], leaving nothing more than dust!</span>")
|
||||
name = victim.name
|
||||
desc = victim.desc + " Wait, did it just move..?"
|
||||
icon_state = victim.icon_state
|
||||
item_state = victim.item_state
|
||||
squeak_override = victim.squeak_override
|
||||
attack_verb = victim.attack_verb
|
||||
new /obj/effect/decal/cleanable/ash(get_turf(victim))
|
||||
qdel(victim)
|
||||
|
||||
/obj/item/toy/plush/plushling/love(obj/item/toy/plush/Kisser, mob/living/user) //You shouldn't have come here, poor plush.
|
||||
if(!Kisser)
|
||||
return
|
||||
plushie_absorb(Kisser)
|
||||
|
||||
@@ -281,12 +281,12 @@
|
||||
O.custom_name = created_name
|
||||
O.locked = panel_locked
|
||||
if(!aisync)
|
||||
lawsync = 0
|
||||
O.connected_ai = null
|
||||
lawsync = FALSE
|
||||
O.set_connected_ai(null)
|
||||
else
|
||||
O.notify_ai(NEW_BORG)
|
||||
if(forced_ai)
|
||||
O.connected_ai = forced_ai
|
||||
O.set_connected_ai(forced_ai)
|
||||
if(!lawsync)
|
||||
O.lawupdate = 0
|
||||
if(M.laws.id == DEFAULT_AI_LAWID)
|
||||
@@ -337,10 +337,10 @@
|
||||
|
||||
if(!aisync)
|
||||
lawsync = FALSE
|
||||
O.connected_ai = null
|
||||
O.set_connected_ai(null)
|
||||
else
|
||||
if(forced_ai)
|
||||
O.connected_ai = forced_ai
|
||||
O.set_connected_ai(forced_ai)
|
||||
O.notify_ai(AI_SHELL)
|
||||
if(!lawsync)
|
||||
O.lawupdate = FALSE
|
||||
|
||||
@@ -269,8 +269,8 @@
|
||||
to_chat(user, "<span class='notice'>[M] is at full health.</span>")
|
||||
return FALSE
|
||||
user.visible_message("<span class='green'>[user] applies \the [src] on [M].</span>", "<span class='green'>You apply \the [src] on [M].</span>")
|
||||
return heal_carbon(M, user, heal_brute, heal_burn)
|
||||
|
||||
M.heal_bodypart_damage(heal_brute)
|
||||
return TRUE
|
||||
to_chat(user, "<span class='warning'>You can't heal [M] with \the [src]!</span>")
|
||||
|
||||
/obj/item/stack/medical/ointment
|
||||
|
||||
@@ -636,7 +636,7 @@ GLOBAL_LIST_INIT(brass_recipes, list ( \
|
||||
null, \
|
||||
new/datum/stack_recipe("brass flask", /obj/item/reagent_containers/food/drinks/bottle/holyoil/empty), \
|
||||
new/datum/stack_recipe("brass smith's hammer", /obj/item/melee/smith/hammer/ratvar, 6), \
|
||||
new/datum/stack_recipe("brass ingot", /obj/item/ingot/bronze/ratvar, 6, time = 100), \
|
||||
new/datum/stack_recipe("brass ingot", /obj/item/ingot/ratvar, 6, time = 100), \
|
||||
))
|
||||
|
||||
/obj/item/stack/tile/brass
|
||||
|
||||
@@ -204,9 +204,6 @@ GLOBAL_DATUM_INIT(acid_overlay, /mutable_appearance, mutable_appearance('icons/e
|
||||
/obj/proc/acid_processing()
|
||||
. = 1
|
||||
if(!(resistance_flags & ACID_PROOF))
|
||||
for(var/armour_value in armor)
|
||||
if(armour_value != "acid" && armour_value != "fire")
|
||||
armor = armor.modifyAllRatings(0 - round(sqrt(acid_level)*0.1))
|
||||
if(prob(33))
|
||||
playsound(loc, 'sound/items/welder.ogg', 150, 1)
|
||||
take_damage(min(1 + round(sqrt(acid_level)*0.3), 300), BURN, "acid", 0)
|
||||
|
||||
@@ -138,7 +138,7 @@
|
||||
if(prob(hardness))
|
||||
playsound(src, 'sound/effects/meteorimpact.ogg', 100, TRUE)
|
||||
user.say(pick(";RAAAAAAAARGH!", ";HNNNNNNNNNGGGGGGH!", ";GWAAAAAAAARRRHHH!", "NNNNNNNNGGGGGGGGHH!", ";AAAAAAARRRGH!" ), forced = "hulk")
|
||||
hulk_recoil(arm, user)
|
||||
//hulk_recoil(arm, user) // citadel edit - no, hulks are already subject to stamina combat
|
||||
dismantle_wall(1)
|
||||
|
||||
else
|
||||
|
||||
@@ -11,7 +11,8 @@ GLOBAL_PROTECT(admin_verbs_default)
|
||||
/client/proc/investigate_show, /*various admintools for investigation. Such as a singulo grief-log*/
|
||||
/client/proc/debug_variables, /*allows us to -see- the variables of any instance in the game. +VAREDIT needed to modify*/
|
||||
/client/proc/toggleprayers,
|
||||
/client/proc/toggleadminhelpsound
|
||||
/client/proc/toggleadminhelpsound,
|
||||
/client/proc/debugstatpanel,
|
||||
)
|
||||
GLOBAL_LIST_INIT(admin_verbs_admin, world.AVerbsAdmin())
|
||||
GLOBAL_PROTECT(admin_verbs_admin)
|
||||
@@ -260,36 +261,36 @@ GLOBAL_PROTECT(admin_verbs_hideable)
|
||||
control_freak = CONTROL_FREAK_SKIN | CONTROL_FREAK_MACROS
|
||||
|
||||
var/rights = holder.rank.rights
|
||||
verbs += GLOB.admin_verbs_default
|
||||
add_verb(src, GLOB.admin_verbs_default)
|
||||
if(rights & R_BUILDMODE)
|
||||
verbs += /client/proc/togglebuildmodeself
|
||||
add_verb(src, /client/proc/togglebuildmodeself)
|
||||
if(rights & R_ADMIN)
|
||||
verbs += GLOB.admin_verbs_admin
|
||||
add_verb(src, GLOB.admin_verbs_admin)
|
||||
if(rights & R_BAN)
|
||||
verbs += GLOB.admin_verbs_ban
|
||||
add_verb(src, GLOB.admin_verbs_ban)
|
||||
if(rights & R_FUN)
|
||||
verbs += GLOB.admin_verbs_fun
|
||||
add_verb(src, GLOB.admin_verbs_fun)
|
||||
if(rights & R_SERVER)
|
||||
verbs += GLOB.admin_verbs_server
|
||||
add_verb(src, GLOB.admin_verbs_server)
|
||||
if(rights & R_DEBUG)
|
||||
verbs += GLOB.admin_verbs_debug
|
||||
add_verb(src, GLOB.admin_verbs_debug)
|
||||
if(rights & R_POSSESS)
|
||||
verbs += GLOB.admin_verbs_possess
|
||||
add_verb(src, GLOB.admin_verbs_possess)
|
||||
if(rights & R_PERMISSIONS)
|
||||
verbs += GLOB.admin_verbs_permissions
|
||||
add_verb(src, GLOB.admin_verbs_permissions)
|
||||
if(rights & R_STEALTH)
|
||||
verbs += /client/proc/stealth
|
||||
add_verb(src, /client/proc/stealth)
|
||||
if(rights & R_ADMIN)
|
||||
verbs += GLOB.admin_verbs_poll
|
||||
add_verb(src, GLOB.admin_verbs_poll)
|
||||
if(rights & R_SOUNDS)
|
||||
verbs += GLOB.admin_verbs_sounds
|
||||
add_verb(src, GLOB.admin_verbs_sounds)
|
||||
if(CONFIG_GET(string/invoke_youtubedl))
|
||||
verbs += /client/proc/play_web_sound
|
||||
add_verb(src, /client/proc/play_web_sound)
|
||||
if(rights & R_SPAWN)
|
||||
verbs += GLOB.admin_verbs_spawn
|
||||
add_verb(src, GLOB.admin_verbs_spawn)
|
||||
|
||||
/client/proc/remove_admin_verbs()
|
||||
verbs.Remove(
|
||||
remove_verb(src, list(
|
||||
GLOB.admin_verbs_default,
|
||||
/client/proc/togglebuildmodeself,
|
||||
GLOB.admin_verbs_admin,
|
||||
@@ -308,14 +309,15 @@ GLOBAL_PROTECT(admin_verbs_hideable)
|
||||
GLOB.admin_verbs_debug_mapping,
|
||||
/client/proc/disable_debug_verbs,
|
||||
/client/proc/readmin
|
||||
)
|
||||
))
|
||||
|
||||
/client/proc/hide_most_verbs()//Allows you to keep some functionality while hiding some verbs
|
||||
set name = "Adminverbs - Hide Most"
|
||||
set category = "Admin"
|
||||
|
||||
verbs.Remove(/client/proc/hide_most_verbs, GLOB.admin_verbs_hideable)
|
||||
verbs += /client/proc/show_verbs
|
||||
remove_verb(src, GLOB.admin_verbs_hideable)
|
||||
remove_verb(src, /client/proc/hide_most_verbs)
|
||||
add_verb(src, /client/proc/show_verbs)
|
||||
|
||||
to_chat(src, "<span class='interface'>Most of your adminverbs have been hidden.</span>")
|
||||
SSblackbox.record_feedback("tally", "admin_verb", 1, "Hide Most Adminverbs") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
@@ -326,7 +328,7 @@ GLOBAL_PROTECT(admin_verbs_hideable)
|
||||
set category = "Admin"
|
||||
|
||||
remove_admin_verbs()
|
||||
verbs += /client/proc/show_verbs
|
||||
add_verb(src, /client/proc/show_verbs)
|
||||
|
||||
to_chat(src, "<span class='interface'>Almost all of your adminverbs have been hidden.</span>")
|
||||
SSblackbox.record_feedback("tally", "admin_verb", 1, "Hide All Adminverbs") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
@@ -336,7 +338,7 @@ GLOBAL_PROTECT(admin_verbs_hideable)
|
||||
set name = "Adminverbs - Show"
|
||||
set category = "Admin"
|
||||
|
||||
verbs -= /client/proc/show_verbs
|
||||
remove_verb(src, /client/proc/show_verbs)
|
||||
add_admin_verbs()
|
||||
|
||||
to_chat(src, "<span class='interface'>All of your adminverbs are now visible.</span>")
|
||||
@@ -724,3 +726,9 @@ GLOBAL_PROTECT(admin_verbs_hideable)
|
||||
|
||||
log_admin("[key_name(usr)] has [AI_Interact ? "activated" : "deactivated"] Admin AI Interact")
|
||||
message_admins("[key_name_admin(usr)] has [AI_Interact ? "activated" : "deactivated"] their AI interaction")
|
||||
|
||||
/client/proc/debugstatpanel()
|
||||
set name = "Debug Stat Panel"
|
||||
set category = "Debug"
|
||||
|
||||
src << output("", "statbrowser:create_debug")
|
||||
|
||||
@@ -91,7 +91,7 @@ GLOBAL_PROTECT(href_token)
|
||||
var/client/C
|
||||
if ((C = owner) || (C = GLOB.directory[target]))
|
||||
disassociate()
|
||||
C.verbs += /client/proc/readmin
|
||||
add_verb(C, /client/proc/readmin)
|
||||
|
||||
/datum/admins/proc/associate(client/C)
|
||||
if(IsAdminAdvancedProcCall())
|
||||
@@ -111,7 +111,8 @@ GLOBAL_PROTECT(href_token)
|
||||
owner = C
|
||||
owner.holder = src
|
||||
owner.add_admin_verbs() //TODO <--- todo what? the proc clearly exists and works since its the backbone to our entire admin system
|
||||
owner.verbs -= /client/proc/readmin
|
||||
remove_verb(owner, /client/proc/readmin)
|
||||
owner.init_verbs() //re-initialize the verb list
|
||||
GLOB.admins |= C
|
||||
|
||||
/datum/admins/proc/disassociate()
|
||||
@@ -123,6 +124,7 @@ GLOBAL_PROTECT(href_token)
|
||||
if(owner)
|
||||
GLOB.admins -= owner
|
||||
owner.remove_admin_verbs()
|
||||
owner.init_verbs()
|
||||
owner.holder = null
|
||||
owner = null
|
||||
|
||||
|
||||
@@ -397,11 +397,13 @@ GLOBAL_DATUM_INIT(sdql2_vv_statobj, /obj/effect/statclick/SDQL2_VV_all, new(null
|
||||
delete_click = new(null, "INITIALIZING", src)
|
||||
if(!action_click)
|
||||
action_click = new(null, "INITIALIZNG", src)
|
||||
stat("[id] ", delete_click.update("DELETE QUERY | STATE : [text_state()] | ALL/ELIG/FIN \
|
||||
var/list/L = list()
|
||||
L[++L.len] = list("[id] ", "[delete_click.update("DELETE QUERY | STATE : [text_state()] | ALL/ELIG/FIN \
|
||||
[islist(obj_count_all)? length(obj_count_all) : (isnull(obj_count_all)? "0" : obj_count_all)]/\
|
||||
[islist(obj_count_eligible)? length(obj_count_eligible) : (isnull(obj_count_eligible)? "0" : obj_count_eligible)]/\
|
||||
[islist(obj_count_finished)? length(obj_count_finished) : (isnull(obj_count_finished)? "0" : obj_count_finished)] - [get_query_text()]"))
|
||||
stat(" ", action_click.update("[SDQL2_IS_RUNNING? "HALT" : "RUN"]"))
|
||||
[islist(obj_count_finished)? length(obj_count_finished) : (isnull(obj_count_finished)? "0" : obj_count_finished)] - [get_query_text()]")]", REF(delete_click))
|
||||
L[++L.len] = list(" ", "[action_click.update("[SDQL2_IS_RUNNING? "HALT" : "RUN"]")]", REF(action_click))
|
||||
return L
|
||||
|
||||
/datum/SDQL2_query/proc/delete_click()
|
||||
admin_del(usr)
|
||||
@@ -1189,15 +1191,27 @@ GLOBAL_DATUM_INIT(sdql2_vv_statobj, /obj/effect/statclick/SDQL2_VV_all, new(null
|
||||
return query_list
|
||||
|
||||
/obj/effect/statclick/SDQL2_delete/Click()
|
||||
if(!usr.client?.holder)
|
||||
message_admins("[key_name_admin(usr)] non-holder clicked on a statclick! ([src])")
|
||||
log_game("[key_name(usr)] non-holder clicked on a statclick! ([src])")
|
||||
return
|
||||
var/datum/SDQL2_query/Q = target
|
||||
Q.delete_click()
|
||||
|
||||
/obj/effect/statclick/SDQL2_action/Click()
|
||||
if(!usr.client?.holder)
|
||||
message_admins("[key_name_admin(usr)] non-holder clicked on a statclick! ([src])")
|
||||
log_game("[key_name(usr)] non-holder clicked on a statclick! ([src])")
|
||||
return
|
||||
var/datum/SDQL2_query/Q = target
|
||||
Q.action_click()
|
||||
|
||||
/obj/effect/statclick/SDQL2_VV_all
|
||||
name = "VIEW VARIABLES"
|
||||
|
||||
/obj/effect/statclick/SDQL2_VV_all/Click()
|
||||
/obj/effect/statclick/sdql2_vv_all/Click()
|
||||
if(!usr.client?.holder)
|
||||
message_admins("[key_name_admin(usr)] non-holder clicked on a statclick! ([src])")
|
||||
log_game("[key_name(usr)] non-holder clicked on a statclick! ([src])")
|
||||
return
|
||||
usr.client.debug_variables(GLOB.sdql2_queries)
|
||||
|
||||
@@ -89,18 +89,23 @@ GLOBAL_DATUM_INIT(ahelp_tickets, /datum/admin_help_tickets, new)
|
||||
|
||||
//Tickets statpanel
|
||||
/datum/admin_help_tickets/proc/stat_entry()
|
||||
SHOULD_CALL_PARENT(TRUE)
|
||||
SHOULD_NOT_SLEEP(TRUE)
|
||||
var/list/L = list()
|
||||
var/num_disconnected = 0
|
||||
stat("Active Tickets:", astatclick.update("[active_tickets.len]"))
|
||||
L[++L.len] = list("Active Tickets:", "[astatclick.update("[active_tickets.len]")]", null, REF(astatclick))
|
||||
astatclick.update("[active_tickets.len]")
|
||||
for(var/I in active_tickets)
|
||||
var/datum/admin_help/AH = I
|
||||
if(AH.initiator)
|
||||
stat("#[AH.id]. [AH.initiator_key_name]:", AH.statclick.update())
|
||||
L[++L.len] = list("#[AH.id]. [AH.initiator_key_name]:", "[AH.statclick.update()]", REF(AH))
|
||||
else
|
||||
++num_disconnected
|
||||
if(num_disconnected)
|
||||
stat("Disconnected:", astatclick.update("[num_disconnected]"))
|
||||
stat("Closed Tickets:", cstatclick.update("[closed_tickets.len]"))
|
||||
stat("Resolved Tickets:", rstatclick.update("[resolved_tickets.len]"))
|
||||
L[++L.len] = list("Disconnected:", "[astatclick.update("[num_disconnected]")]", null, REF(astatclick))
|
||||
L[++L.len] = list("Closed Tickets:", "[cstatclick.update("[closed_tickets.len]")]", null, REF(cstatclick))
|
||||
L[++L.len] = list("Resolved Tickets:", "[rstatclick.update("[resolved_tickets.len]")]", null, REF(rstatclick))
|
||||
return L
|
||||
|
||||
//Reassociate still open ticket if one exists
|
||||
/datum/admin_help_tickets/proc/ClientLogin(client/C)
|
||||
@@ -137,6 +142,10 @@ GLOBAL_DATUM_INIT(ahelp_tickets, /datum/admin_help_tickets, new)
|
||||
/obj/effect/statclick/ticket_list/Click()
|
||||
GLOB.ahelp_tickets.BrowseTickets(current_state)
|
||||
|
||||
//called by admin topic
|
||||
/obj/effect/statclick/ticket_list/proc/Action()
|
||||
Click()
|
||||
|
||||
//
|
||||
//TICKET DATUM
|
||||
//
|
||||
@@ -218,7 +227,7 @@ GLOBAL_DATUM_INIT(ahelp_tickets, /datum/admin_help_tickets, new)
|
||||
|
||||
//Removes the ahelp verb and returns it after 2 minutes
|
||||
/datum/admin_help/proc/TimeoutVerb()
|
||||
initiator.verbs -= /client/verb/adminhelp
|
||||
remove_verb(initiator, /client/verb/adminhelp)
|
||||
initiator.adminhelptimerid = addtimer(CALLBACK(initiator, /client/proc/giveadminhelpverb), 1200, TIMER_STOPPABLE) //2 minute cooldown of admin helps
|
||||
|
||||
//private
|
||||
@@ -490,7 +499,7 @@ GLOBAL_DATUM_INIT(ahelp_tickets, /datum/admin_help_tickets, new)
|
||||
//
|
||||
|
||||
/client/proc/giveadminhelpverb()
|
||||
src.verbs |= /client/verb/adminhelp
|
||||
add_verb(src, /client/verb/adminhelp)
|
||||
deltimer(adminhelptimerid)
|
||||
adminhelptimerid = 0
|
||||
|
||||
|
||||
@@ -199,7 +199,7 @@
|
||||
borg.notify_ai(DISCONNECT)
|
||||
if(borg.shell)
|
||||
borg.undeploy()
|
||||
borg.connected_ai = newai
|
||||
borg.set_connected_ai(newai)
|
||||
borg.notify_ai(TRUE)
|
||||
message_admins("[key_name_admin(user)] slaved [ADMIN_LOOKUPFLW(borg)] to the AI [ADMIN_LOOKUPFLW(newai)].")
|
||||
log_admin("[key_name(user)] slaved [key_name(borg)] to the AI [key_name(newai)].")
|
||||
@@ -207,7 +207,7 @@
|
||||
borg.notify_ai(DISCONNECT)
|
||||
if(borg.shell)
|
||||
borg.undeploy()
|
||||
borg.connected_ai = null
|
||||
borg.set_connected_ai(null)
|
||||
message_admins("[key_name_admin(user)] freed [ADMIN_LOOKUPFLW(borg)] from being slaved to an AI.")
|
||||
log_admin("[key_name(user)] freed [key_name(borg)] from being slaved to an AI.")
|
||||
if (borg.lawupdate)
|
||||
|
||||
@@ -205,15 +205,15 @@ GLOBAL_LIST_EMPTY(dirty_vars)
|
||||
set name = "Debug verbs - Enable"
|
||||
if(!check_rights(R_DEBUG))
|
||||
return
|
||||
verbs -= /client/proc/enable_debug_verbs
|
||||
verbs.Add(/client/proc/disable_debug_verbs, GLOB.admin_verbs_debug_mapping)
|
||||
remove_verb(src, /client/proc/enable_debug_verbs)
|
||||
add_verb(src, list(/client/proc/disable_debug_verbs, GLOB.admin_verbs_debug_mapping))
|
||||
SSblackbox.record_feedback("tally", "admin_verb", 1, "Enable Debug Verbs") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/disable_debug_verbs()
|
||||
set category = "Debug"
|
||||
set name = "Debug verbs - Disable"
|
||||
verbs.Remove(/client/proc/disable_debug_verbs, GLOB.admin_verbs_debug_mapping)
|
||||
verbs += /client/proc/enable_debug_verbs
|
||||
remove_verb(src, list(/client/proc/disable_debug_verbs, GLOB.admin_verbs_debug_mapping))
|
||||
add_verb(src, /client/proc/enable_debug_verbs)
|
||||
SSblackbox.record_feedback("tally", "admin_verb", 1, "Disable Debug Verbs") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
/client/proc/count_objects_on_z_level()
|
||||
|
||||
@@ -48,6 +48,6 @@
|
||||
set desc = "Give this guy possess/release verbs"
|
||||
set category = "Debug"
|
||||
set name = "Give Possessing Verbs"
|
||||
M.verbs += /proc/possess
|
||||
M.verbs += /proc/release
|
||||
add_verb(M, /proc/possess)
|
||||
add_verb(M, /proc/release)
|
||||
SSblackbox.record_feedback("tally", "admin_verb", 1, "Give Possessing Verbs") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
|
||||
|
||||
@@ -138,7 +138,7 @@
|
||||
if(owner.current.gender == MALE)
|
||||
if(prob(10)) // Gender override
|
||||
bloodsucker_reputation = pick("King of the Damned", "Blood King", "Emperor of Blades", "Sinlord", "God-King")
|
||||
else
|
||||
else if(owner.current.gender == FEMALE)
|
||||
if(prob(10)) // Gender override
|
||||
bloodsucker_reputation = pick("Queen of the Damned", "Blood Queen", "Empress of Blades", "Sinlady", "God-Queen")
|
||||
|
||||
@@ -341,10 +341,12 @@
|
||||
|
||||
//This handles the application of antag huds/special abilities
|
||||
/datum/antagonist/bloodsucker/apply_innate_effects(mob/living/mob_override)
|
||||
RegisterSignal(owner.current,COMSIG_LIVING_BIOLOGICAL_LIFE,.proc/LifeTick)
|
||||
return
|
||||
|
||||
//This handles the removal of antag huds/special abilities
|
||||
/datum/antagonist/bloodsucker/remove_innate_effects(mob/living/mob_override)
|
||||
UnregisterSignal(owner.current,COMSIG_LIVING_BIOLOGICAL_LIFE)
|
||||
return
|
||||
|
||||
//Assign default team and creates one for one of a kind team antagonists
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
|
||||
|
||||
/datum/action/bloodsucker/targeted/brawn
|
||||
name = "Brawn"//"Cellular Emporium"
|
||||
name = "Brawn"
|
||||
desc = "Snap restraints with ease, or deal terrible damage with your bare hands."
|
||||
button_icon_state = "power_strength"
|
||||
bloodcost = 10
|
||||
@@ -107,8 +107,6 @@
|
||||
if(user_C.handcuffed)
|
||||
var/obj/O = user_C.get_item_by_slot(SLOT_HANDCUFFED)
|
||||
if(istype(O))
|
||||
//user_C.visible_message("<span class='warning'>[user_C] attempts to remove [O]!</span>", \
|
||||
// "<span class='warning'>You snap [O] like it's nothing!</span>")
|
||||
user_C.clear_cuffs(O,TRUE)
|
||||
playsound(get_turf(usr), 'sound/effects/grillehit.ogg', 80, 1, -1)
|
||||
return TRUE
|
||||
@@ -128,8 +126,6 @@
|
||||
if(user_C.legcuffed)
|
||||
var/obj/O = user_C.get_item_by_slot(SLOT_LEGCUFFED)
|
||||
if(istype(O))
|
||||
//user_C.visible_message("<span class='warning'>[user_C] attempts to remove [O]!</span>", \
|
||||
// "<span class='warning'>You snap [O] like it's nothing!</span>")
|
||||
user_C.clear_cuffs(O,TRUE)
|
||||
playsound(get_turf(usr), 'sound/effects/grillehit.ogg', 80, 1, -1)
|
||||
return TRUE
|
||||
|
||||
@@ -165,8 +165,8 @@
|
||||
// Broadcast Message
|
||||
if(amSilent)
|
||||
//if (!iscarbon(target))
|
||||
// user.visible_message("<span class='notice'>[user] shifts [target] closer to [user.p_their()] mouth.</span>", \
|
||||
// "<span class='notice'>You secretly slip your fangs into [target]'s flesh.</span>", \
|
||||
// user.visible_message("<span class='notice'>[user] shifts [target] closer to [user.p_their()] mouth.</span>",
|
||||
// "<span class='notice'>You secretly slip your fangs into [target]'s flesh.</span>",
|
||||
// vision_distance = 2, ignored_mobs=target) // Only people who AREN'T the target will notice this action.
|
||||
//else
|
||||
var/deadmessage = target.stat == DEAD ? "" : " <i>[target.p_they(TRUE)] looks dazed, and will not remember this.</i>"
|
||||
|
||||
@@ -94,6 +94,7 @@
|
||||
B.decoy_override = FALSE
|
||||
remove_changeling_powers()
|
||||
owner.special_role = null
|
||||
owner.current.hud_used?.lingchemdisplay?.invisibility = INVISIBILITY_ABSTRACT
|
||||
. = ..()
|
||||
|
||||
/datum/antagonist/changeling/proc/remove_clownmut()
|
||||
@@ -225,6 +226,8 @@
|
||||
else //not dead? no chem/geneticdamage caps.
|
||||
chem_charges = min(max(0, chem_charges + chem_recharge_rate - chem_recharge_slowdown), chem_storage)
|
||||
geneticdamage = max(0, geneticdamage-1)
|
||||
owner.current.hud_used?.lingchemdisplay?.invisibility = 0
|
||||
owner.current.hud_used?.lingchemdisplay?.maptext = "<div align='center' valign='middle' style='position:relative; top:0px; left:6px'><font color='#dd66dd'>[round(chem_charges)]</font></div>"
|
||||
|
||||
|
||||
/datum/antagonist/changeling/proc/get_dna(dna_owner)
|
||||
@@ -357,10 +360,12 @@
|
||||
B.organ_flags &= ~ORGAN_VITAL
|
||||
B.decoy_override = TRUE
|
||||
update_changeling_icons_added()
|
||||
RegisterSignal(owner.current,COMSIG_LIVING_BIOLOGICAL_LIFE,.proc/regenerate)
|
||||
return
|
||||
|
||||
/datum/antagonist/changeling/remove_innate_effects()
|
||||
update_changeling_icons_removed()
|
||||
UnregisterSignal(owner.current,COMSIG_LIVING_BIOLOGICAL_LIFE)
|
||||
return
|
||||
|
||||
|
||||
|
||||
@@ -83,17 +83,16 @@ the new instance inside the host to be updated to the template's stats.
|
||||
to_chat(src, "<span class='warning'>You have [DisplayTimeText(freemove_end - world.time)] to select your first host. Click on a human to select your host.</span>")
|
||||
|
||||
|
||||
/mob/camera/disease/Stat()
|
||||
/mob/camera/disease/get_status_tab_items()
|
||||
..()
|
||||
if(statpanel("Status"))
|
||||
if(freemove)
|
||||
stat("Host Selection Time: [round((freemove_end - world.time)/10)]s")
|
||||
else
|
||||
stat("Adaptation Points: [points]/[total_points]")
|
||||
stat("Hosts: [disease_instances.len]")
|
||||
var/adapt_ready = next_adaptation_time - world.time
|
||||
if(adapt_ready > 0)
|
||||
stat("Adaptation Ready: [round(adapt_ready/10, 0.1)]s")
|
||||
if(freemove)
|
||||
. += "Host Selection Time: [round((freemove_end - world.time)/10)]s"
|
||||
else
|
||||
. += "Adaptation Points: [points]/[total_points]"
|
||||
. += "Hosts: [disease_instances.len]"
|
||||
var/adapt_ready = next_adaptation_time - world.time
|
||||
if(adapt_ready > 0)
|
||||
. += "Adaptation Ready: [round(adapt_ready/10, 0.1)]s"
|
||||
|
||||
|
||||
/mob/camera/disease/examine(mob/user)
|
||||
|
||||
@@ -130,12 +130,11 @@
|
||||
update_spooky_icon()
|
||||
update_health_hud()
|
||||
|
||||
/mob/living/simple_animal/revenant/Stat()
|
||||
..()
|
||||
if(statpanel("Status"))
|
||||
stat(null, "Current essence: [essence]/[essence_regen_cap]E")
|
||||
stat(null, "Stolen essence: [essence_accumulated]E")
|
||||
stat(null, "Stolen perfect souls: [perfectsouls]")
|
||||
/mob/living/simple_animal/revenant/get_status_tab_items()
|
||||
. = ..()
|
||||
. += "Current essence: [essence]/[essence_regen_cap]E"
|
||||
. += "Stolen essence: [essence_accumulated]E"
|
||||
. += "Stolen perfect souls: [perfectsouls]"
|
||||
|
||||
/mob/living/simple_animal/revenant/update_health_hud()
|
||||
if(hud_used)
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
ShiftClickOn(A)
|
||||
return
|
||||
if(modifiers["alt"])
|
||||
altclick_listed_turf(A)
|
||||
AltClickNoInteract(src, A)
|
||||
return
|
||||
|
||||
if(ishuman(A))
|
||||
|
||||
@@ -109,7 +109,7 @@
|
||||
|
||||
/mob/living/simple_animal/hostile/swarmer/Initialize()
|
||||
. = ..()
|
||||
verbs -= /mob/living/verb/pulled
|
||||
remove_verb(src, /mob/living/verb/pulled)
|
||||
for(var/datum/atom_hud/data/diagnostic/diag_hud in GLOB.huds)
|
||||
diag_hud.add_to_hud(src)
|
||||
|
||||
|
||||
@@ -49,7 +49,7 @@
|
||||
/datum/traitor_class/ai/on_removal(datum/antagonist/traitor/T)
|
||||
var/mob/living/silicon/ai/A = T.owner.current
|
||||
A.set_zeroth_law("")
|
||||
A.verbs -= /mob/living/silicon/ai/proc/choose_modules
|
||||
remove_verb(A, /mob/living/silicon/ai/proc/choose_modules)
|
||||
A.malf_picker.remove_malf_verbs(A)
|
||||
qdel(A.malf_picker)
|
||||
|
||||
|
||||
@@ -13,7 +13,9 @@ GLOBAL_LIST_INIT(blacklisted_malf_machines, typecacheof(list(
|
||||
/obj/machinery/syndicatebomb/badmin/clown,
|
||||
/obj/machinery/syndicatebomb/empty,
|
||||
/obj/machinery/syndicatebomb/self_destruct,
|
||||
/obj/machinery/syndicatebomb/training
|
||||
/obj/machinery/syndicatebomb/training,
|
||||
/obj/machinery/gravity_generator,
|
||||
/obj/machinery/gravity_generator/main
|
||||
)))
|
||||
|
||||
//The malf AI action subtype. All malf actions are subtypes of this.
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
var/hidden_socks = FALSE
|
||||
|
||||
//Mob procs
|
||||
/mob/living/carbon/human/proc/underwear_toggle()
|
||||
/mob/living/carbon/human/verb/underwear_toggle()
|
||||
set name = "Toggle undergarments"
|
||||
set category = "IC"
|
||||
|
||||
@@ -68,7 +68,7 @@
|
||||
R.reaction(turfing ? target : target.loc, TOUCH, 1, 0)
|
||||
if(!turfing)
|
||||
R.trans_to(target, R.total_volume * (spill ? G.fluid_transfer_factor : 1))
|
||||
G.time_since_last_orgasm = 0
|
||||
G.last_orgasmed = world.time
|
||||
R.clear_reagents()
|
||||
|
||||
/mob/living/carbon/human/proc/mob_climax_outside(obj/item/organ/genital/G, mb_time = 30) //This is used for forced orgasms and other hands-free climaxes
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
var/fluid_efficiency = 1
|
||||
var/fluid_rate = CUM_RATE
|
||||
var/fluid_mult = 1
|
||||
var/time_since_last_orgasm = 500
|
||||
var/last_orgasmed = 0
|
||||
var/aroused_state = FALSE //Boolean used in icon_state strings
|
||||
var/obj/item/organ/genital/linked_organ
|
||||
var/linked_organ_slot //used for linking an apparatus' organ to its other half on update_link().
|
||||
@@ -24,10 +24,6 @@
|
||||
|
||||
/obj/item/organ/genital/Initialize(mapload, do_update = TRUE)
|
||||
. = ..()
|
||||
if(fluid_id)
|
||||
create_reagents(fluid_max_volume, NONE, NO_REAGENTS_VALUE)
|
||||
if(CHECK_BITFIELD(genital_flags, GENITAL_FUID_PRODUCTION))
|
||||
reagents.add_reagent(fluid_id, fluid_max_volume)
|
||||
if(do_update)
|
||||
update()
|
||||
|
||||
@@ -140,8 +136,6 @@
|
||||
/obj/item/organ/genital/proc/modify_size(modifier, min = -INFINITY, max = INFINITY)
|
||||
fluid_max_volume += modifier*2.5
|
||||
fluid_rate += modifier/10
|
||||
if(reagents)
|
||||
reagents.maximum_volume = fluid_max_volume
|
||||
return
|
||||
|
||||
/obj/item/organ/genital/proc/update_size()
|
||||
@@ -151,18 +145,14 @@
|
||||
if(!owner || owner.stat == DEAD)
|
||||
aroused_state = FALSE
|
||||
|
||||
/obj/item/organ/genital/on_life()
|
||||
. = ..()
|
||||
if(!reagents || !.)
|
||||
return
|
||||
reagents.maximum_volume = fluid_max_volume
|
||||
if(fluid_id && CHECK_BITFIELD(genital_flags, GENITAL_FUID_PRODUCTION))
|
||||
time_since_last_orgasm++
|
||||
|
||||
/obj/item/organ/genital/proc/generate_fluid(datum/reagents/R)
|
||||
var/amount = clamp(fluid_rate * time_since_last_orgasm * fluid_mult,0,fluid_max_volume)
|
||||
var/amount = clamp((fluid_rate * ((world.time - last_orgasmed) / SSmobs.wait) * fluid_mult),0,fluid_max_volume)
|
||||
R.clear_reagents()
|
||||
R.add_reagent(fluid_id,amount)
|
||||
R.maximum_volume = fluid_max_volume
|
||||
if(fluid_id)
|
||||
R.add_reagent(fluid_id,amount)
|
||||
else if(linked_organ?.fluid_id)
|
||||
R.add_reagent(linked_organ.fluid_id,amount)
|
||||
return TRUE
|
||||
|
||||
/obj/item/organ/genital/proc/update_link()
|
||||
|
||||
@@ -3,21 +3,21 @@
|
||||
/datum/asset/simple/tgui_common
|
||||
keep_local_name = TRUE
|
||||
assets = list(
|
||||
"tgui-common.chunk.js" = 'tgui/packages/tgui/public/tgui-common.chunk.js',
|
||||
"tgui-common.chunk.js" = 'tgui/public/tgui-common.chunk.js',
|
||||
)
|
||||
|
||||
/datum/asset/simple/tgui
|
||||
keep_local_name = TRUE
|
||||
assets = list(
|
||||
"tgui.bundle.js" = 'tgui/packages/tgui/public/tgui.bundle.js',
|
||||
"tgui.bundle.css" = 'tgui/packages/tgui/public/tgui.bundle.css',
|
||||
"tgui.bundle.js" = 'tgui/public/tgui.bundle.js',
|
||||
"tgui.bundle.css" = 'tgui/public/tgui.bundle.css',
|
||||
)
|
||||
|
||||
/datum/asset/simple/tgui_panel
|
||||
keep_local_name = TRUE
|
||||
assets = list(
|
||||
"tgui-panel.bundle.js" = 'tgui/packages/tgui/public/tgui-panel.bundle.js',
|
||||
"tgui-panel.bundle.css" = 'tgui/packages/tgui/public/tgui-panel.bundle.css',
|
||||
"tgui-panel.bundle.js" = 'tgui/public/tgui-panel.bundle.js',
|
||||
"tgui-panel.bundle.css" = 'tgui/public/tgui-panel.bundle.css',
|
||||
)
|
||||
|
||||
/datum/asset/simple/headers
|
||||
@@ -113,15 +113,15 @@
|
||||
)
|
||||
|
||||
|
||||
/datum/asset/simple/IRV
|
||||
/datum/asset/simple/irv
|
||||
assets = list(
|
||||
"jquery-ui.custom-core-widgit-mouse-sortable-min.js" = 'html/IRV/jquery-ui.custom-core-widgit-mouse-sortable-min.js',
|
||||
)
|
||||
|
||||
/datum/asset/group/IRV
|
||||
/datum/asset/group/irv
|
||||
children = list(
|
||||
/datum/asset/simple/jquery,
|
||||
/datum/asset/simple/IRV
|
||||
/datum/asset/simple/irv
|
||||
)
|
||||
|
||||
/datum/asset/simple/namespaced/changelog
|
||||
@@ -247,6 +247,7 @@
|
||||
"clownthanks" = 'icons/UI_Icons/Achievements/Misc/clownthanks.png',
|
||||
"rule8" = 'icons/UI_Icons/Achievements/Misc/rule8.png',
|
||||
"snail" = 'icons/UI_Icons/Achievements/Misc/snail.png',
|
||||
"ascension" = 'icons/UI_Icons/Achievements/Misc/ascension.png',
|
||||
"mining" = 'icons/UI_Icons/Achievements/Skills/mining.png',
|
||||
"assistant" = 'icons/UI_Icons/Achievements/Mafia/assistant.png',
|
||||
"changeling" = 'icons/UI_Icons/Achievements/Mafia/changeling.png',
|
||||
@@ -263,7 +264,8 @@
|
||||
"psychologist" = 'icons/UI_Icons/Achievements/Mafia/psychologist.png',
|
||||
"thoughtfeeder" = 'icons/UI_Icons/Achievements/Mafia/thoughtfeeder.png',
|
||||
"traitor" = 'icons/UI_Icons/Achievements/Mafia/traitor.png',
|
||||
"basemafia" ='icons/UI_Icons/Achievements/basemafia.png'
|
||||
"basemafia" ='icons/UI_Icons/Achievements/basemafia.png',
|
||||
"frenching" = 'icons/UI_Icons/Achievements/Misc/frenchingthebubble.png'
|
||||
)
|
||||
*/
|
||||
|
||||
@@ -447,11 +449,9 @@
|
||||
Insert("polycrystal", 'icons/obj/telescience.dmi', "polycrystal")
|
||||
..()
|
||||
|
||||
|
||||
/datum/asset/spritesheet/mafia
|
||||
name = "mafia"
|
||||
|
||||
/datum/asset/spritesheet/mafia/register()
|
||||
InsertAll("", 'icons/obj/mafia.dmi')
|
||||
..()
|
||||
|
||||
|
||||
@@ -43,10 +43,10 @@
|
||||
return "[url][get_asset_suffex(asset_cache_item)]"
|
||||
|
||||
/datum/asset_transport/webroot/proc/get_asset_suffex(datum/asset_cache_item/asset_cache_item)
|
||||
var/base = ""
|
||||
var/base = "[copytext(asset_cache_item.hash, 1, 3)]/"
|
||||
var/filename = "asset.[asset_cache_item.hash][asset_cache_item.ext]"
|
||||
if (length(asset_cache_item.namespace))
|
||||
base = "namespaces/[asset_cache_item.namespace]/"
|
||||
base = "namespaces/[copytext(asset_cache_item.namespace, 1, 3)]/[asset_cache_item.namespace]/"
|
||||
if (!asset_cache_item.namespace_parent)
|
||||
filename = "[asset_cache_item.name]"
|
||||
return base + filename
|
||||
|
||||
@@ -40,6 +40,9 @@
|
||||
/datum/gas_reaction/proc/react(datum/gas_mixture/air, atom/location)
|
||||
return NO_REACTION
|
||||
|
||||
/datum/gas_reaction/proc/test()
|
||||
return list("success" = TRUE)
|
||||
|
||||
/datum/gas_reaction/nobliumsupression
|
||||
priority = INFINITY
|
||||
name = "Hyper-Noblium Reaction Suppression"
|
||||
@@ -70,6 +73,8 @@
|
||||
air.adjust_moles(/datum/gas/water_vapor,-MOLES_GAS_VISIBLE)
|
||||
. = REACTING
|
||||
|
||||
// no test cause it's entirely based on location
|
||||
|
||||
//tritium combustion: combustion of oxygen and tritium (treated as hydrocarbons). creates hotspots. exothermic
|
||||
/datum/gas_reaction/tritfire
|
||||
priority = -1 //fire should ALWAYS be last, but tritium fires happen before plasma fires
|
||||
@@ -126,6 +131,18 @@
|
||||
|
||||
return cached_results["fire"] ? REACTING : NO_REACTION
|
||||
|
||||
/datum/gas_reaction/tritfire/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/tritium,50)
|
||||
G.set_moles(/datum/gas/oxygen,50)
|
||||
G.set_temperature(500)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(!G.reaction_results["fire"])
|
||||
return list("success" = FALSE, "message" = "Trit fires aren't setting fire results correctly!")
|
||||
return ..()
|
||||
|
||||
//plasma combustion: combustion of oxygen and plasma (treated as hydrocarbons). creates hotspots. exothermic
|
||||
/datum/gas_reaction/plasmafire
|
||||
priority = -2 //fire should ALWAYS be last, but plasma fires happen after tritium fires
|
||||
@@ -198,6 +215,28 @@
|
||||
|
||||
return cached_results["fire"] ? REACTING : NO_REACTION
|
||||
|
||||
/datum/gas_reaction/plasmafire/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/plasma,50)
|
||||
G.set_moles(/datum/gas/oxygen,50)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(500)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(!G.reaction_results["fire"])
|
||||
return list("success" = FALSE, "message" = "Plasma fires aren't setting fire results correctly!")
|
||||
if(!G.get_moles(/datum/gas/carbon_dioxide))
|
||||
return list("success" = FALSE, "message" = "Plasma fires aren't making CO2!")
|
||||
G.clear()
|
||||
G.set_moles(/datum/gas/plasma,10)
|
||||
G.set_moles(/datum/gas/oxygen,1000)
|
||||
G.set_temperature(500)
|
||||
result = G.react()
|
||||
if(!G.get_moles(/datum/gas/tritium))
|
||||
return list("success" = FALSE, "message" = "Plasma fires aren't making trit!")
|
||||
return ..()
|
||||
|
||||
//fusion: a terrible idea that was fun but broken. Now reworked to be less broken and more interesting. Again (and again, and again). Again!
|
||||
//Fusion Rework Counter: Please increment this if you make a major overhaul to this system again.
|
||||
//6 reworks
|
||||
@@ -282,6 +321,31 @@
|
||||
air.set_temperature(clamp(((air.return_temperature()*old_heat_capacity + reaction_energy)/new_heat_capacity),TCMB,INFINITY))
|
||||
return REACTING
|
||||
|
||||
/datum/gas_reaction/fusion/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/carbon_dioxide,300)
|
||||
G.set_moles(/datum/gas/plasma,1000)
|
||||
G.set_moles(/datum/gas/tritium,100.61)
|
||||
G.set_moles(/datum/gas/nitryl,1)
|
||||
G.set_temperature(15000)
|
||||
G.set_volume(1000)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(abs(G.analyzer_results["fusion"] - 3) > 0.0000001)
|
||||
var/instability = G.analyzer_results["fusion"]
|
||||
return list("success" = FALSE, "message" = "Fusion is not calculating analyzer results correctly, should be 3.000000045, is instead [instability]")
|
||||
if(abs(G.get_moles(/datum/gas/plasma) - 850.616) > 0.5)
|
||||
var/plas = G.get_moles(/datum/gas/plasma)
|
||||
return list("success" = FALSE, "message" = "Fusion is not calculating plasma correctly, should be 850.616, is instead [plas]")
|
||||
if(abs(G.get_moles(/datum/gas/carbon_dioxide) - 1699.384) > 0.5)
|
||||
var/co2 = G.get_moles(/datum/gas/carbon_dioxide)
|
||||
return list("success" = FALSE, "message" = "Fusion is not calculating co2 correctly, should be 1699.384, is instead [co2]")
|
||||
if(abs(G.return_temperature() - 27600) > 200) // calculating this manually sucks dude
|
||||
var/temp = G.return_temperature()
|
||||
return list("success" = FALSE, "message" = "Fusion is not calculating temperature correctly, should be around 27600, is instead [temp]")
|
||||
return ..()
|
||||
|
||||
/datum/gas_reaction/nitrylformation //The formation of nitryl. Endothermic. Requires N2O as a catalyst.
|
||||
priority = 3
|
||||
name = "Nitryl formation"
|
||||
@@ -313,6 +377,20 @@
|
||||
air.set_temperature(max(((temperature*old_heat_capacity - energy_used)/new_heat_capacity),TCMB))
|
||||
return REACTING
|
||||
|
||||
/datum/gas_reaction/nitrylformation/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/oxygen,30)
|
||||
G.set_moles(/datum/gas/nitrogen,30)
|
||||
G.set_moles(/datum/gas/nitrous_oxide,10)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(150000)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(!G.get_moles(/datum/gas/nitryl) < 0.8)
|
||||
return list("success" = FALSE, "message" = "Nitryl isn't being generated correctly!")
|
||||
return ..()
|
||||
|
||||
/datum/gas_reaction/bzformation //Formation of BZ by combining plasma and tritium at low pressures. Exothermic.
|
||||
priority = 4
|
||||
name = "BZ Gas formation"
|
||||
@@ -348,6 +426,19 @@
|
||||
air.set_temperature(max(((temperature*old_heat_capacity + energy_released)/new_heat_capacity),TCMB))
|
||||
return REACTING
|
||||
|
||||
/datum/gas_reaction/bzformation/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/plasma,15)
|
||||
G.set_moles(/datum/gas/nitrous_oxide,15)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(10)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(!G.get_moles(/datum/gas/bz) < 4) // efficiency is 4.0643 and bz generation == efficiency
|
||||
return list("success" = FALSE, "message" = "Nitryl isn't being generated correctly!")
|
||||
return ..()
|
||||
|
||||
/datum/gas_reaction/stimformation //Stimulum formation follows a strange pattern of how effective it will be at a given temperature, having some multiple peaks and some large dropoffs. Exo and endo thermic.
|
||||
priority = 5
|
||||
name = "Stimulum formation"
|
||||
@@ -380,6 +471,23 @@
|
||||
air.set_temperature(max(((air.return_temperature()*old_heat_capacity + stim_energy_change)/new_heat_capacity),TCMB))
|
||||
return REACTING
|
||||
|
||||
/datum/gas_reaction/stimformation/test()
|
||||
//above mentioned "strange pattern" is a basic quintic polynomial, it's fine, can calculate it manually
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/bz,30)
|
||||
G.set_moles(/datum/gas/plasma,1000)
|
||||
G.set_moles(/datum/gas/tritium,1000)
|
||||
G.set_moles(/datum/gas/nitryl,1000)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(12998000) // yeah, really
|
||||
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(!G.get_moles(/datum/gas/stimulum) < 900)
|
||||
return list("success" = FALSE, "message" = "Stimulum isn't being generated correctly!")
|
||||
return ..()
|
||||
|
||||
/datum/gas_reaction/nobliumformation //Hyper-Noblium formation is extrememly endothermic, but requires high temperatures to start. Due to its high mass, hyper-nobelium uses large amounts of nitrogen and tritium. BZ can be used as a catalyst to make it less endothermic.
|
||||
priority = 6
|
||||
name = "Hyper-Noblium condensation"
|
||||
@@ -408,6 +516,19 @@
|
||||
if(new_heat_capacity > MINIMUM_HEAT_CAPACITY)
|
||||
air.set_temperature(max(((air.return_temperature()*old_heat_capacity - energy_taken)/new_heat_capacity),TCMB))
|
||||
|
||||
/datum/gas_reaction/nobliumformation/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/nitrogen,100)
|
||||
G.set_moles(/datum/gas/tritium,500)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(5000000) // yeah, really
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
if(abs(G.thermal_energy() - 23000000000) > 1000000) // god i hate floating points
|
||||
return list("success" = FALSE, "message" = "Hyper-nob formation isn't removing the right amount of heat! Should be 23,000,000,000, is instead [G.thermal_energy()]")
|
||||
return ..()
|
||||
|
||||
|
||||
/datum/gas_reaction/miaster //dry heat sterilization: clears out pathogens in the air
|
||||
priority = -10 //after all the heating from fires etc. is done
|
||||
@@ -433,3 +554,20 @@
|
||||
//Possibly burning a bit of organic matter through maillard reaction, so a *tiny* bit more heat would be understandable
|
||||
air.set_temperature(air.return_temperature() + cleaned_air * 0.002)
|
||||
SSresearch.science_tech.add_point_type(TECHWEB_POINT_TYPE_DEFAULT, cleaned_air*MIASMA_RESEARCH_AMOUNT)//Turns out the burning of miasma is kinda interesting to scientists
|
||||
|
||||
/datum/gas_reaction/miaster/test()
|
||||
var/datum/gas_mixture/G = new
|
||||
G.set_moles(/datum/gas/miasma,1)
|
||||
G.set_volume(1000)
|
||||
G.set_temperature(450)
|
||||
var/result = G.react()
|
||||
if(result != REACTING)
|
||||
return list("success" = FALSE, "message" = "Reaction didn't go at all!")
|
||||
G.clear()
|
||||
G.set_moles(/datum/gas/miasma,1)
|
||||
G.set_temperature(450)
|
||||
G.set_moles(/datum/gas/water_vapor,0.5)
|
||||
result = G.react()
|
||||
if(result != NO_REACTION)
|
||||
return list("success" = FALSE, "message" = "Miasma sterilization not stopping due to water vapor correctly!")
|
||||
return ..()
|
||||
|
||||
@@ -11,15 +11,15 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
/datum/gateway_destination
|
||||
var/name = "Unknown Destination"
|
||||
var/wait = 0 /// How long after roundstart this destination becomes active
|
||||
var/enabled = TRUE /// If disabled, the destination won't be availible
|
||||
var/enabled = TRUE /// If disabled, the destination won't be available
|
||||
var/hidden = FALSE /// Will not show on gateway controls at all.
|
||||
|
||||
/* Can a gateway link to this destination right now. */
|
||||
/datum/gateway_destination/proc/is_availible()
|
||||
/datum/gateway_destination/proc/is_available()
|
||||
return enabled && (world.time - SSticker.round_start_time >= wait)
|
||||
|
||||
/* Returns user-friendly description why you can't connect to this destination, displayed in UI */
|
||||
/datum/gateway_destination/proc/get_availible_reason()
|
||||
/datum/gateway_destination/proc/get_available_reason()
|
||||
. = "Unreachable"
|
||||
if(world.time - SSticker.round_start_time < wait)
|
||||
. = "Connection desynchronized. Recalibration in progress."
|
||||
@@ -52,8 +52,8 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
. = list()
|
||||
.["ref"] = REF(src)
|
||||
.["name"] = name
|
||||
.["availible"] = is_availible()
|
||||
.["reason"] = get_availible_reason()
|
||||
.["available"] = is_available()
|
||||
.["reason"] = get_available_reason()
|
||||
if(wait)
|
||||
.["timeout"] = max(1 - (wait - (world.time - SSticker.round_start_time)) / wait, 0)
|
||||
|
||||
@@ -72,10 +72,10 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
if(target_gateway.target == deactivated.destination)
|
||||
target_gateway.deactivate()
|
||||
|
||||
/datum/gateway_destination/gateway/is_availible()
|
||||
/datum/gateway_destination/gateway/is_available()
|
||||
return ..() && target_gateway.calibrated && !target_gateway.target && target_gateway.powered()
|
||||
|
||||
/datum/gateway_destination/gateway/get_availible_reason()
|
||||
/datum/gateway_destination/gateway/get_available_reason()
|
||||
. = ..()
|
||||
if(!target_gateway.calibrated)
|
||||
. = "Exit gateway malfunction. Manual recalibration required."
|
||||
@@ -217,8 +217,7 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
target = D
|
||||
target.activate(destination)
|
||||
generate_bumper()
|
||||
if(use_power == IDLE_POWER_USE)
|
||||
use_power = ACTIVE_POWER_USE
|
||||
use_power = ACTIVE_POWER_USE
|
||||
update_icon()
|
||||
|
||||
/obj/machinery/gateway/proc/Transfer(atom/movable/AM)
|
||||
@@ -261,8 +260,7 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
if(!GLOB.the_gateway)
|
||||
to_chat(user,"<span class='warning'>Home gateway is not responding!</span>")
|
||||
if(GLOB.the_gateway.target)
|
||||
to_chat(user,"<span class='warning'>Home gateway already in use!</span>")
|
||||
return
|
||||
GLOB.the_gateway.deactivate() //this will turn the home gateway off so that it's free for us to connect to
|
||||
activate(GLOB.the_gateway.destination)
|
||||
else
|
||||
deactivate()
|
||||
@@ -319,7 +317,7 @@ GLOBAL_LIST_EMPTY(gateway_destinations)
|
||||
/obj/machinery/computer/gateway_control/proc/try_to_connect(datum/gateway_destination/D)
|
||||
if(!D || !G)
|
||||
return
|
||||
if(!D.is_availible() || G.target)
|
||||
if(!D.is_available() || G.target)
|
||||
return
|
||||
G.activate(D)
|
||||
|
||||
|
||||
@@ -105,7 +105,7 @@
|
||||
if("Immortality")
|
||||
to_chat(user, "<B>Your wish is granted, but at a terrible cost...</B>")
|
||||
to_chat(user, "The Wish Granter punishes you for your selfishness, claiming your soul and warping your body to match the darkness in your heart.")
|
||||
user.verbs += /mob/living/carbon/proc/immortality
|
||||
add_verb(user, /mob/living/carbon/proc/immortality)
|
||||
user.set_species(/datum/species/shadow)
|
||||
if("To Kill")
|
||||
to_chat(user, "<B>Your wish is granted, but at a terrible cost...</B>")
|
||||
|
||||
@@ -7,6 +7,9 @@
|
||||
////////////////
|
||||
//ADMIN THINGS//
|
||||
////////////////
|
||||
/// hides the byond verb panel as we use our own custom version
|
||||
show_verb_panel = FALSE
|
||||
///Contains admin info. Null if client is not an admin.
|
||||
var/datum/admins/holder = null
|
||||
var/datum/click_intercept = null // Needs to implement InterceptClickOn(user,params,atom) proc
|
||||
var/AI_Interact = 0
|
||||
@@ -123,6 +126,14 @@
|
||||
|
||||
/// Messages currently seen by this client
|
||||
var/list/seen_messages
|
||||
|
||||
/// datum wrapper for client view
|
||||
var/datum/view_data/view_size
|
||||
|
||||
/// list of tabs containing spells and abilities
|
||||
var/list/spell_tabs = list()
|
||||
/// list of tabs containing verbs
|
||||
var/list/verb_tabs = list()
|
||||
///A lazy list of atoms we've examined in the last EXAMINE_MORE_TIME (default 1.5) seconds, so that we will call [atom/proc/examine_more()] instead of [atom/proc/examine()] on them when examining
|
||||
var/list/recent_examines
|
||||
///When was the last time we warned them about not cryoing without an ahelp, set to -5 minutes so that rounstart cryo still warns
|
||||
@@ -152,3 +163,4 @@
|
||||
|
||||
//world.time of when the crew manifest can be accessed
|
||||
var/crew_manifest_delay
|
||||
|
||||
|
||||
@@ -237,7 +237,7 @@ GLOBAL_LIST_INIT(blacklisted_builds, list(
|
||||
debug_tools_allowed = TRUE
|
||||
//END CITADEL EDIT
|
||||
else if(GLOB.deadmins[ckey])
|
||||
verbs += /client/proc/readmin
|
||||
add_verb(src, /client/proc/readmin)
|
||||
connecting_admin = TRUE
|
||||
if(CONFIG_GET(flag/autoadmin))
|
||||
if(!GLOB.admin_datums[ckey])
|
||||
@@ -275,7 +275,7 @@ GLOBAL_LIST_INIT(blacklisted_builds, list(
|
||||
fps = prefs.clientfps //(prefs.clientfps < 0) ? RECOMMENDED_FPS : prefs.clientfps
|
||||
|
||||
if(fexists(roundend_report_file()))
|
||||
verbs += /client/proc/show_previous_roundend_report
|
||||
add_verb(src, /client/proc/show_previous_roundend_report)
|
||||
|
||||
var/full_version = "[byond_version].[byond_build ? byond_build : "xxx"]"
|
||||
log_access("Login: [key_name(src)] from [address ? address : "localhost"]-[computer_id] || BYOND v[full_version]")
|
||||
@@ -342,6 +342,8 @@ GLOBAL_LIST_INIT(blacklisted_builds, list(
|
||||
|
||||
// Initialize tgui panel
|
||||
tgui_panel.initialize()
|
||||
src << browse(file('html/statbrowser.html'), "window=statbrowser")
|
||||
|
||||
|
||||
if(alert_mob_dupe_login)
|
||||
spawn()
|
||||
@@ -857,9 +859,9 @@ GLOBAL_LIST_INIT(blacklisted_builds, list(
|
||||
|
||||
/client/proc/add_verbs_from_config()
|
||||
if(CONFIG_GET(flag/see_own_notes))
|
||||
verbs += /client/proc/self_notes
|
||||
add_verb(src, /client/proc/self_notes)
|
||||
if(CONFIG_GET(flag/use_exp_tracking))
|
||||
verbs += /client/proc/self_playtime
|
||||
add_verb(src, /client/proc/self_playtime)
|
||||
|
||||
|
||||
#undef UPLOAD_LIMIT
|
||||
@@ -1001,3 +1003,21 @@ GLOBAL_LIST_INIT(blacklisted_builds, list(
|
||||
|
||||
/client/proc/can_have_part(part_name)
|
||||
return prefs.pref_species.mutant_bodyparts[part_name] || (part_name in GLOB.unlocked_mutant_parts)
|
||||
|
||||
/// compiles a full list of verbs and sends it to the browser
|
||||
/client/proc/init_verbs()
|
||||
if(IsAdminAdvancedProcCall())
|
||||
return
|
||||
var/list/verblist = list()
|
||||
verb_tabs.Cut()
|
||||
for(var/thing in (verbs + mob?.verbs))
|
||||
var/procpath/verb_to_init = thing
|
||||
if(!verb_to_init)
|
||||
continue
|
||||
if(verb_to_init.hidden)
|
||||
continue
|
||||
if(!istext(verb_to_init.category))
|
||||
continue
|
||||
verb_tabs |= verb_to_init.category
|
||||
verblist[++verblist.len] = list(verb_to_init.category, verb_to_init.name)
|
||||
src << output("[url_encode(json_encode(verb_tabs))];[url_encode(json_encode(verblist))]", "statbrowser:init_verbs")
|
||||
|
||||
@@ -163,6 +163,7 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
)
|
||||
var/custom_speech_verb = "default" //if your say_mod is to be something other than your races
|
||||
var/custom_tongue = "default" //if your tongue is to be something other than your races
|
||||
var/modified_limbs = list() //prosthetic/amputated limbs
|
||||
var/chosen_limb_id //body sprite selected to load for the users limbs, null means default, is sanitized when loaded
|
||||
|
||||
/// Security record note section
|
||||
@@ -429,12 +430,19 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
dat += "<b>Gender:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=gender;task=input'>[gender == MALE ? "Male" : (gender == FEMALE ? "Female" : (gender == PLURAL ? "Non-binary" : "Object"))]</a><BR>"
|
||||
if(gender != NEUTER && pref_species.sexes)
|
||||
dat += "<b>Body Model:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=body_model'>[features["body_model"] == MALE ? "Masculine" : "Feminine"]</a><BR>"
|
||||
dat += "<b>Limb Modification:</b><BR>"
|
||||
dat += "<a href='?_src_=prefs;preference=modify_limbs;task=input'>Modify Limbs</a><BR>"
|
||||
for(var/modification in modified_limbs)
|
||||
if(modified_limbs[modification][1] == LOADOUT_LIMB_PROSTHETIC)
|
||||
dat += "<b>[modification]: [modified_limbs[modification][2]]</b><BR>"
|
||||
else
|
||||
dat += "<b>[modification]: [modified_limbs[modification][1]]</b><BR>"
|
||||
dat += "<BR>"
|
||||
dat += "<b>Species:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=species;task=input'>[pref_species.name]</a><BR>"
|
||||
dat += "<b>Custom Species Name:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=custom_species;task=input'>[custom_species ? custom_species : "None"]</a><BR>"
|
||||
dat += "<b>Random Body:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=all;task=random'>Randomize!</A><BR>"
|
||||
dat += "<b>Always Random Body:</b><a href='?_src_=prefs;preference=all'>[be_random_body ? "Yes" : "No"]</A><BR>"
|
||||
dat += "<br><b>Cycle background:</b><a style='display:block;width:100px' href='?_src_=prefs;preference=cycle_bg;task=input'>[bgstate]</a><BR>"
|
||||
|
||||
var/use_skintones = pref_species.use_skintones
|
||||
if(use_skintones)
|
||||
dat += APPEARANCE_CATEGORY_COLUMN
|
||||
@@ -1235,6 +1243,9 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
for(var/V in all_quirks)
|
||||
var/datum/quirk/T = SSquirks.quirks[V]
|
||||
bal -= initial(T.value)
|
||||
for(var/modification in modified_limbs)
|
||||
if(modified_limbs[modification][1] == LOADOUT_LIMB_PROSTHETIC)
|
||||
return bal + 1 //max 1 point regardless of how many prosthetics
|
||||
return bal
|
||||
|
||||
/datum/preferences/proc/GetPositiveQuirkCount()
|
||||
@@ -1492,6 +1503,29 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
if("cycle_bg")
|
||||
bgstate = next_list_item(bgstate, bgstate_options)
|
||||
|
||||
if("modify_limbs")
|
||||
var/limb_type = input(user, "Choose the limb to modify:", "Character Preference") as null|anything in LOADOUT_ALLOWED_LIMB_TARGETS
|
||||
if(limb_type)
|
||||
var/modification_type = input(user, "Choose the modification to the limb:", "Character Preference") as null|anything in LOADOUT_LIMBS
|
||||
if(modification_type)
|
||||
if(modification_type == LOADOUT_LIMB_PROSTHETIC)
|
||||
var/prosthetic_type = input(user, "Choose the type of prosthetic", "Character Preference") as null|anything in (list("prosthetic") + GLOB.prosthetic_limb_types)
|
||||
if(prosthetic_type)
|
||||
var/number_of_prosthetics = 0
|
||||
for(var/modification in modified_limbs)
|
||||
if(modified_limbs[modification][1] == LOADOUT_LIMB_PROSTHETIC)
|
||||
number_of_prosthetics += 1
|
||||
if(number_of_prosthetics >= MAXIMUM_LOADOUT_PROSTHETICS && !(limb_type in modified_limbs && modified_limbs[limb_type][1] == LOADOUT_LIMB_PROSTHETIC))
|
||||
to_chat(user, "<span class='danger'>You can only have up to two prosthetic limbs!</span>")
|
||||
else
|
||||
//save the actual prosthetic data
|
||||
modified_limbs[limb_type] = list(modification_type, prosthetic_type)
|
||||
else
|
||||
if(modification_type == LOADOUT_LIMB_NORMAL)
|
||||
modified_limbs -= limb_type
|
||||
else
|
||||
modified_limbs[limb_type] = list(modification_type)
|
||||
|
||||
if("underwear")
|
||||
var/new_underwear = input(user, "Choose your character's underwear:", "Character Preference") as null|anything in GLOB.underwear_list
|
||||
if(new_underwear)
|
||||
@@ -2478,7 +2512,7 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
ShowChoices(user)
|
||||
return 1
|
||||
|
||||
/datum/preferences/proc/copy_to(mob/living/carbon/human/character, icon_updates = 1, roundstart_checks = TRUE)
|
||||
/datum/preferences/proc/copy_to(mob/living/carbon/human/character, icon_updates = 1, roundstart_checks = TRUE, initial_spawn = FALSE)
|
||||
if(be_random_name)
|
||||
real_name = pref_species.random_name(gender)
|
||||
|
||||
@@ -2573,6 +2607,34 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
if(custom_speech_verb != "default")
|
||||
character.dna.species.say_mod = custom_speech_verb
|
||||
|
||||
//limb stuff, only done when initially spawning in
|
||||
if(initial_spawn)
|
||||
//delete any existing prosthetic limbs to make sure no remnant prosthetics are left over
|
||||
for(var/obj/item/bodypart/part in character.bodyparts)
|
||||
if(part.status == BODYPART_ROBOTIC)
|
||||
qdel(part)
|
||||
character.regenerate_limbs() //regenerate limbs so now you only have normal limbs
|
||||
for(var/modified_limb in modified_limbs)
|
||||
var/modification = modified_limbs[modified_limb][1]
|
||||
var/obj/item/bodypart/old_part = character.get_bodypart(modified_limb)
|
||||
if(modification == LOADOUT_LIMB_PROSTHETIC)
|
||||
var/obj/item/bodypart/new_limb
|
||||
switch(modified_limb)
|
||||
if(BODY_ZONE_L_ARM)
|
||||
new_limb = new/obj/item/bodypart/l_arm/robot/surplus(character)
|
||||
if(BODY_ZONE_R_ARM)
|
||||
new_limb = new/obj/item/bodypart/r_arm/robot/surplus(character)
|
||||
if(BODY_ZONE_L_LEG)
|
||||
new_limb = new/obj/item/bodypart/l_leg/robot/surplus(character)
|
||||
if(BODY_ZONE_R_LEG)
|
||||
new_limb = new/obj/item/bodypart/r_leg/robot/surplus(character)
|
||||
var/prosthetic_type = modified_limbs[modified_limb][2]
|
||||
if(prosthetic_type != "prosthetic") //lets just leave the old sprites as they are
|
||||
new_limb.icon = file("icons/mob/augmentation/cosmetic_prosthetic/[prosthetic_type].dmi")
|
||||
new_limb.replace_limb(character)
|
||||
qdel(old_part)
|
||||
|
||||
character.regenerate_icons()
|
||||
|
||||
SEND_SIGNAL(character, COMSIG_HUMAN_PREFS_COPIED_TO, src, icon_updates, roundstart_checks)
|
||||
|
||||
@@ -2581,6 +2643,18 @@ GLOBAL_LIST_EMPTY(preferences_datums)
|
||||
character.update_body()
|
||||
character.update_hair()
|
||||
|
||||
/datum/preferences/proc/post_copy_to(mob/living/carbon/human/character)
|
||||
//if no legs, and not a paraplegic or a slime, give them a free wheelchair
|
||||
if(modified_limbs[BODY_ZONE_L_LEG] == LOADOUT_LIMB_AMPUTATED && modified_limbs[BODY_ZONE_R_LEG] == LOADOUT_LIMB_AMPUTATED && !character.has_quirk(/datum/quirk/paraplegic) && !isjellyperson(character))
|
||||
if(character.buckled)
|
||||
character.buckled.unbuckle_mob(character)
|
||||
var/turf/T = get_turf(character)
|
||||
var/obj/structure/chair/spawn_chair = locate() in T
|
||||
var/obj/vehicle/ridden/wheelchair/wheels = new(T)
|
||||
if(spawn_chair) // Makes spawning on the arrivals shuttle more consistent looking
|
||||
wheels.setDir(spawn_chair.dir)
|
||||
wheels.buckle_mob(character)
|
||||
|
||||
/datum/preferences/proc/get_default_name(name_id)
|
||||
switch(name_id)
|
||||
if("human")
|
||||
|
||||
@@ -514,6 +514,12 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
|
||||
S["scars3"] >> scars_list["3"]
|
||||
S["scars4"] >> scars_list["4"]
|
||||
S["scars5"] >> scars_list["5"]
|
||||
var/limbmodstr
|
||||
S["modified_limbs"] >> limbmodstr
|
||||
if(length(limbmodstr))
|
||||
modified_limbs = safe_json_decode(limbmodstr)
|
||||
else
|
||||
modified_limbs = list()
|
||||
S["chosen_limb_id"] >> chosen_limb_id
|
||||
S["hide_ckey"] >> hide_ckey //saved per-character
|
||||
|
||||
@@ -845,8 +851,6 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
|
||||
|
||||
WRITE_FILE(S["feature_ooc_notes"], features["ooc_notes"])
|
||||
|
||||
WRITE_FILE(S["chosen_limb_id"], chosen_limb_id)
|
||||
|
||||
//Custom names
|
||||
for(var/custom_name_id in GLOB.preferences_custom_names)
|
||||
var/savefile_slot_name = custom_name_id + "_name" //TODO remove this
|
||||
@@ -874,6 +878,9 @@ SAVEFILE UPDATING/VERSIONING - 'Simplified', or rather, more coder-friendly ~Car
|
||||
WRITE_FILE(S["scars3"] , scars_list["3"])
|
||||
WRITE_FILE(S["scars4"] , scars_list["4"])
|
||||
WRITE_FILE(S["scars5"] , scars_list["5"])
|
||||
if(islist(modified_limbs))
|
||||
WRITE_FILE(S["modified_limbs"] , safe_json_encode(modified_limbs))
|
||||
WRITE_FILE(S["chosen_limb_id"], chosen_limb_id)
|
||||
|
||||
|
||||
//gear loadout
|
||||
|
||||
@@ -280,3 +280,9 @@ GLOBAL_VAR_INIT(normal_ooc_colour, "#002eb8")
|
||||
|
||||
pct += delta
|
||||
winset(src, "mainwindow.split", "splitter=[pct]")
|
||||
|
||||
/client/verb/fix_stat_panel()
|
||||
set name = "Fix Stat Panel"
|
||||
set hidden = TRUE
|
||||
|
||||
init_verbs()
|
||||
|
||||
@@ -5,9 +5,9 @@
|
||||
var/obj/item/clothing/head/hooded/hood
|
||||
var/hoodtype = /obj/item/clothing/head/hooded/winterhood //so the chaplain hoodie or other hoodies can override this
|
||||
|
||||
/obj/item/clothing/suit/hooded/New()
|
||||
/obj/item/clothing/suit/hooded/Initialize()
|
||||
. = ..()
|
||||
hood = MakeHelmet()
|
||||
..()
|
||||
|
||||
/obj/item/clothing/suit/hooded/Destroy()
|
||||
. = ..()
|
||||
@@ -48,7 +48,7 @@
|
||||
|
||||
/obj/item/clothing/suit/hooded/update_icon_state()
|
||||
icon_state = "[initial(icon_state)]"
|
||||
if(ishuman(hood.loc))
|
||||
if(ishuman(hood?.loc))
|
||||
var/mob/living/carbon/human/H = hood.loc
|
||||
if(H.head == hood)
|
||||
icon_state += "_t"
|
||||
@@ -131,8 +131,8 @@
|
||||
|
||||
//Hardsuit toggle code
|
||||
/obj/item/clothing/suit/space/hardsuit/Initialize()
|
||||
helmet = MakeHelmet()
|
||||
. = ..()
|
||||
helmet = MakeHelmet()
|
||||
|
||||
/obj/item/clothing/suit/space/hardsuit/Destroy()
|
||||
if(helmet)
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user