Merge conflict fix

This commit is contained in:
Artur
2020-05-13 12:37:18 +03:00
985 changed files with 295527 additions and 16121 deletions
+10 -7
View File
@@ -25,35 +25,38 @@
//SubSystem flags (Please design any new flags so that the default is off, to make adding flags to subsystems easier)
//subsystem does not initialize.
#define SS_NO_INIT 1
#define SS_NO_INIT (1<<0)
//subsystem does not fire.
// (like can_fire = 0, but keeps it from getting added to the processing subsystems list)
// (Requires a MC restart to change)
#define SS_NO_FIRE 2
#define SS_NO_FIRE (1<<1)
//subsystem only runs on spare cpu (after all non-background subsystems have ran that tick)
// SS_BACKGROUND has its own priority bracket
#define SS_BACKGROUND 4
#define SS_BACKGROUND (1<<2)
//subsystem does not tick check, and should not run unless there is enough time (or its running behind (unless background))
#define SS_NO_TICK_CHECK 8
#define SS_NO_TICK_CHECK (1<<3)
//Treat wait as a tick count, not DS, run every wait ticks.
// (also forces it to run first in the tick, above even SS_NO_TICK_CHECK subsystems)
// (implies all runlevels because of how it works)
// (overrides SS_BACKGROUND)
// This is designed for basically anything that works as a mini-mc (like SStimer)
#define SS_TICKER 16
#define SS_TICKER (1<<4)
//keep the subsystem's timing on point by firing early if it fired late last fire because of lag
// ie: if a 20ds subsystem fires say 5 ds late due to lag or what not, its next fire would be in 15ds, not 20ds.
#define SS_KEEP_TIMING 32
#define SS_KEEP_TIMING (1<<5)
//Calculate its next fire after its fired.
// (IE: if a 5ds wait SS takes 2ds to run, its next fire should be 5ds away, not 3ds like it normally would be)
// This flag overrides SS_KEEP_TIMING
#define SS_POST_FIRE_TIMING 64
#define SS_POST_FIRE_TIMING (1<<6)
/// Show in stat() by default even if SS_NO_FIRE
#define SS_ALWAYS_SHOW_STAT (1<<7)
//SUBSYSTEM STATES
#define SS_IDLE 0 //aint doing shit.
-32
View File
@@ -1,32 +0,0 @@
#if DM_VERSION < 513
#define ismovableatom(A) (istype(A, /atom/movable))
#define islist(L) (istype(L, /list))
#define CLAMP01(x) (CLAMP(x, 0, 1))
#define CLAMP(CLVALUE,CLMIN,CLMAX) ( max( (CLMIN), min((CLVALUE), (CLMAX)) ) )
#define ATAN2(x, y) ( !(x) && !(y) ? 0 : (y) >= 0 ? arccos((x) / sqrt((x)*(x) + (y)*(y))) : -arccos((x) / sqrt((x)*(x) + (y)*(y))) )
#define TAN(x) (sin(x) / cos(x))
#define arctan(x) (arcsin(x/sqrt(1+x*x)))
//////////////////////////////////////////////////
#else
#define ismovableatom(A) ismovable(A)
#define CLAMP01(x) clamp(x, 0, 1)
#define CLAMP(CLVALUE, CLMIN, CLMAX) clamp(CLVALUE, CLMIN, CLMAX)
#define TAN(x) tan(x)
#define ATAN2(x, y) arctan(x, y)
#endif
+19 -4
View File
@@ -1,13 +1,28 @@
#define TICK_LIMIT_RUNNING 80
/// Percentage of tick to leave for master controller to run
#define MAPTICK_MC_MIN_RESERVE 70
/// internal_tick_usage is updated every tick by extools
#define MAPTICK_LAST_INTERNAL_TICK_USAGE ((GLOB.internal_tick_usage / world.tick_lag) * 100)
/// Tick limit while running normally
#define TICK_BYOND_RESERVE 2
#define TICK_LIMIT_RUNNING (max(100 - TICK_BYOND_RESERVE - MAPTICK_LAST_INTERNAL_TICK_USAGE, MAPTICK_MC_MIN_RESERVE))
/// Tick limit used to resume things in stoplag
#define TICK_LIMIT_TO_RUN 70
/// Tick limit for MC while running
#define TICK_LIMIT_MC 70
#define TICK_LIMIT_MC_INIT_DEFAULT 98
/// Tick limit while initializing
#define TICK_LIMIT_MC_INIT_DEFAULT (100 - TICK_BYOND_RESERVE)
#define TICK_USAGE world.tick_usage //for general usage
#define TICK_USAGE_REAL world.tick_usage //to be used where the result isn't checked
/// for general usage of tick_usage
#define TICK_USAGE world.tick_usage
/// to be used where the result isn't checked
#define TICK_USAGE_REAL world.tick_usage
/// Returns true if tick_usage is above the limit
#define TICK_CHECK ( TICK_USAGE > Master.current_ticklimit )
/// runs stoplag if tick_usage is above the limit
#define CHECK_TICK ( TICK_CHECK ? stoplag() : 0 )
/// Returns true if tick usage is above 95, for high priority usage
#define TICK_CHECK_HIGH_PRIORITY ( TICK_USAGE > 95 )
/// runs stoplag if tick_usage is above 95, for high priority usage
#define CHECK_TICK_HIGH_PRIORITY ( TICK_CHECK_HIGH_PRIORITY? stoplag() : 0 )
+8 -2
View File
@@ -161,10 +161,14 @@
#define ATMOS_TANK_O2 "o2=100000;TEMP=293.15"
#define ATMOS_TANK_N2 "n2=100000;TEMP=293.15"
#define ATMOS_TANK_AIRMIX "o2=2644;n2=10580;TEMP=293.15"
//LAVALAND
#define LAVALAND_EQUIPMENT_EFFECT_PRESSURE 50 //what pressure you have to be under to increase the effect of equipment meant for lavaland
#define LAVALAND_DEFAULT_ATMOS "o2=14;n2=23;TEMP=300"
//SNOSTATION
#define ICEMOON_DEFAULT_ATMOS "o2=17;n2=63;TEMP=180"
//ATMOSIA GAS MONITOR TAGS
#define ATMOS_GAS_MONITOR_INPUT_O2 "o2_in"
#define ATMOS_GAS_MONITOR_OUTPUT_O2 "o2_out"
@@ -255,10 +259,10 @@
//HELPERS
#define PIPING_LAYER_SHIFT(T, PipingLayer) \
if(T.dir & NORTH || T.dir & SOUTH) { \
if(T.dir & (NORTH|SOUTH)) { \
T.pixel_x = (PipingLayer - PIPING_LAYER_DEFAULT) * PIPING_LAYER_P_X;\
} \
if(T.dir & WEST || T.dir & EAST) { \
if(T.dir & (WEST|EAST)) { \
T.pixel_y = (PipingLayer - PIPING_LAYER_DEFAULT) * PIPING_LAYER_P_Y;\
}
@@ -294,6 +298,8 @@ GLOBAL_LIST_INIT(atmos_adjacent_savings, list(0,0))
#define ARCHIVE_TEMPERATURE(gas) gas.temperature_archived = gas.temperature
#define ARCHIVE(gas) gas.temperature_archived = gas.temperature; gas.gas_archive = gas.gases.Copy();
GLOBAL_LIST_INIT(pipe_paint_colors, list(
"amethyst" = rgb(130,43,255), //supplymain
"blue" = rgb(0,0,255),
+1
View File
@@ -43,6 +43,7 @@
#define COLOR_RED_GRAY "#B4696A"
#define COLOR_PALE_BLUE_GRAY "#98C5DF"
#define COLOR_PALE_GREEN_GRAY "#B7D993"
#define COLOR_PALE_ORANGE "#FFC066"
#define COLOR_PALE_RED_GRAY "#D59998"
#define COLOR_PALE_PURPLE_GRAY "#CBB1CA"
#define COLOR_PURPLE_GRAY "#AE8CA8"
+27 -7
View File
@@ -35,9 +35,9 @@
/// Default combat flags for those affected by ((stamina combat))
#define COMBAT_FLAGS_DEFAULT NONE
/// Default combat flags for everyone else (so literally everyone but humans)
#define COMBAT_FLAGS_STAMSYSTEM_EXEMPT (COMBAT_FLAG_SPRINT_ACTIVE | COMBAT_FLAG_COMBAT_ACTIVE | COMBAT_FLAG_SPRINT_TOGGLED | COMBAT_FLAG_COMBAT_TOGGLED)
#define COMBAT_FLAGS_STAMSYSTEM_EXEMPT (COMBAT_FLAG_SPRINT_ACTIVE | COMBAT_FLAG_COMBAT_ACTIVE | COMBAT_FLAG_SPRINT_TOGGLED | COMBAT_FLAG_COMBAT_TOGGLED | COMBAT_FLAG_SPRINT_FORCED | COMBAT_FLAG_COMBAT_FORCED)
/// Default combat flags for those only affected by sprint (so just silicons)
#define COMBAT_FLAGS_STAMEXEMPT_YESSPRINT (COMBAT_FLAG_COMBAT_ACTIVE | COMBAT_FLAG_COMBAT_TOGGLED)
#define COMBAT_FLAGS_STAMEXEMPT_YESSPRINT (COMBAT_FLAG_COMBAT_ACTIVE | COMBAT_FLAG_COMBAT_TOGGLED | COMBAT_FLAG_COMBAT_FORCED)
/// The user wants combat mode on
#define COMBAT_FLAG_COMBAT_TOGGLED (1<<0)
@@ -57,6 +57,10 @@
#define COMBAT_FLAG_INTENTIONALLY_RESTING (1<<7)
/// Currently stamcritted but not as violently
#define COMBAT_FLAG_SOFT_STAMCRIT (1<<8)
/// Force combat mode on at all times, overrides everything including combat disable traits.
#define COMBAT_FLAG_COMBAT_FORCED (1<<9)
/// Force sprint mode on at all times, overrides everything including sprint disable traits.
#define COMBAT_FLAG_SPRINT_FORCED (1<<10)
// Helpers for getting someone's stamcrit state. Cast to living.
#define NOT_STAMCRIT 0
@@ -111,9 +115,6 @@
#define GRAB_NECK 2
#define GRAB_KILL 3
//slowdown when in softcrit
#define SOFTCRIT_ADD_SLOWDOWN 6
/// Attack types for check_block()/run_block(). Flags, combinable.
/// Attack was melee, whether or not armed.
#define ATTACK_TYPE_MELEE (1<<0)
@@ -251,13 +252,32 @@ GLOBAL_LIST_INIT(shove_disarming_types, typecacheof(list(
#define TOTAL_MASS_MEDIEVAL_WEAPON 3.6 //very, very generic average sword/warpick/etc. weight in pounds.
#define TOTAL_MASS_TOY_SWORD 1.5
//stamina cost defines.
#define STAM_COST_ATTACK_OBJ_MULT 1.2
#define STAM_COST_ATTACK_MOB_MULT 0.8
#define STAM_COST_BATON_MOB_MULT 1
#define STAM_COST_NO_COMBAT_MULT 1.25
#define STAM_COST_W_CLASS_MULT 1.25
#define STAM_COST_THROW_MULT 2
//bullet_act() return values
#define BULLET_ACT_HIT "HIT" //It's a successful hit, whatever that means in the context of the thing it's hitting.
#define BULLET_ACT_BLOCK "BLOCK" //It's a blocked hit, whatever that means in the context of the thing it's hitting.
#define BULLET_ACT_FORCE_PIERCE "PIERCE" //It pierces through the object regardless of the bullet being piercing by default.
#define BULLET_ACT_TURF "TURF" //It hit us but it should hit something on the same turf too. Usually used for turfs.
/// Bitflags for check_block() and handle_block(). Meant to be combined. You can be hit and still reflect, for example, if you do not use BLOCK_SUCCESS.
/// Check whether or not we can block, without "triggering" a block. Basically run checks without effects like depleting shields.
/// Wrapper for do_run_block(). The arguments on that means the same as for this.
#define mob_check_block(object, damage, attack_text, attack_type, armour_penetration, attacker, def_zone, return_list)\
do_run_block(FALSE, object, damage, attack_text, attack_type, armour_penetration, attacker, check_zone(def_zone), return_list)
/// Runs a block "sequence", effectively checking and then doing effects if necessary.
/// Wrapper for do_run_block(). The arguments on that means the same as for this.
#define mob_run_block(object, damage, attack_text, attack_type, armour_penetration, attacker, def_zone, return_list)\
do_run_block(TRUE, object, damage, attack_text, attack_type, armour_penetration, attacker, check_zone(def_zone), return_list)
/// Bitflags for check_block() and run_block(). Meant to be combined. You can be hit and still reflect, for example, if you do not use BLOCK_SUCCESS.
/// Attack was not blocked
#define BLOCK_NONE NONE
/// Attack was blocked, do not do damage. THIS FLAG MUST BE THERE FOR DAMAGE/EFFECT PREVENTION!
@@ -302,8 +322,8 @@ GLOBAL_LIST_INIT(shove_disarming_types, typecacheof(list(
/// Block priorities
#define BLOCK_PRIORITY_HELD_ITEM 100
#define BLOCK_PRIORITY_CLOTHING 50
#define BLOCK_PRIORITY_WEAR_SUIT 75
#define BLOCK_PRIORITY_CLOTHING 50
#define BLOCK_PRIORITY_UNIFORM 25
#define BLOCK_PRIORITY_DEFAULT BLOCK_PRIORITY_HELD_ITEM
-2
View File
@@ -59,8 +59,6 @@
//let's just pretend fulltile windows being children of border windows is fine
#define FULLTILE_WINDOW_DIR NORTHEAST
//The amount of materials you get from a sheet of mineral like iron/diamond/glass etc
#define MINERAL_MATERIAL_AMOUNT 2000
//The maximum size of a stack object.
#define MAX_STACK_SIZE 50
//maximum amount of cable in a coil
+22
View File
@@ -40,6 +40,7 @@
#define CALTROP_BYPASS_SHOES 1
#define CALTROP_IGNORE_WALKERS 2
// Spellcasting
#define SPELL_SKIP_ALL_REQS (1<<0)
#define SPELL_SKIP_CENTCOM (1<<1)
#define SPELL_SKIP_STAT (1<<2)
@@ -53,3 +54,24 @@
#define SPELL_CULT_ARMOR (1<<10)
#define SPELL_WIZARD_GARB (SPELL_WIZARD_HAT|SPELL_WIZARD_ROBE)
#define SPELL_CULT_GARB (SPELL_CULT_HELMET|SPELL_CULT_ARMOR)
//// Identification ////
// /datum/component/identification/identification_flags
/// Delete on successful broad identification (so the main way we "uncover" how an object works, since this won't be on it to obfuscate it)
#define ID_COMPONENT_DEL_ON_IDENTIFY (1<<0)
/// We've already been successfully deepscanned by a deconstructive analyzer
#define ID_COMPONENT_DECONSTRUCTOR_DEEPSCANNED (1<<1)
// /datum/component/identification/identification_effect_flags
/// Block user from getting actions if they don't know how to use this. Triggered on equip.
#define ID_COMPONENT_EFFECT_NO_ACTIONS (1<<0)
// /datum/component/identification/identification_method_flags
/// Can be identified in a deconstructive analyzer
#define ID_COMPONENT_IDENTIFY_WITH_DECONSTRUCTOR (1<<0)
// Return values for /datum/component/deitnfication/check_knowledge()
/// Has no knowledge, default
#define ID_COMPONENT_KNOWLEDGE_NONE 0
/// Has full knowledge
#define ID_COMPONENT_KNOWLEDGE_FULL 1
+38 -5
View File
@@ -30,7 +30,7 @@
#define COMSIG_PARENT_ATTACKBY "atom_attackby" //from base of atom/attackby(): (/obj/item, /mob/living, params)
#define COMPONENT_NO_AFTERATTACK 1 //Return this in response if you don't want afterattack to be called
#define COMSIG_ATOM_HULK_ATTACK "hulk_attack" //from base of atom/attack_hulk(): (/mob/living/carbon/human)
#define COMSIG_PARENT_EXAMINE "atom_examine" //from base of atom/examine(): (/mob)
#define COMSIG_PARENT_EXAMINE "atom_examine" //from base of atom/examine(): (/mob, list/examine_return_text)
#define COMSIG_ATOM_GET_EXAMINE_NAME "atom_examine_name" //from base of atom/get_examine_name(): (/mob, list/overrides)
//Positions for overrides list
#define EXAMINE_POSITION_ARTICLE 1
@@ -110,7 +110,8 @@
#define COMSIG_TURF_MULTIZ_NEW "turf_multiz_new" //from base of turf/New(): (turf/source, direction)
// /atom/movable signals
#define COMSIG_MOVABLE_PRE_MOVE "movable_pre_move" //from base of atom/movable/Moved(): (/atom)
#define COMSIG_MOVABLE_PRE_MOVE "movable_pre_move" ///from base of atom/movable/Moved(): (/atom)
#define COMPONENT_MOVABLE_BLOCK_PRE_MOVE 1
#define COMSIG_MOVABLE_MOVED "movable_moved" //from base of atom/movable/Moved(): (/atom, dir)
#define COMSIG_MOVABLE_CROSS "movable_cross" //from base of atom/movable/Cross(): (/atom/movable)
#define COMSIG_MOVABLE_CROSSED "movable_crossed" //from base of atom/movable/Crossed(): (/atom/movable)
@@ -119,6 +120,8 @@
#define COMSIG_MOVABLE_UNCROSSED "movable_uncrossed" //from base of atom/movable/Uncrossed(): (/atom/movable)
#define COMSIG_MOVABLE_BUMP "movable_bump" //from base of atom/movable/Bump(): (/atom)
#define COMSIG_MOVABLE_IMPACT "movable_impact" //from base of atom/movable/throw_impact(): (/atom/hit_atom, /datum/thrownthing/throwingdatum)
#define COMPONENT_MOVABLE_IMPACT_FLIP_HITPUSH 1 ///if true, flip if the impact will push what it hits
#define COMPONENT_MOVABLE_IMPACT_NEVERMIND 2 ///return true if you destroyed whatever it was you're impacting and there won't be anything for hitby() to run on
#define COMSIG_MOVABLE_IMPACT_ZONE "item_impact_zone" //from base of mob/living/hitby(): (mob/living/target, hit_zone)
#define COMSIG_MOVABLE_BUCKLE "buckle" //from base of atom/movable/buckle_mob(): (mob, force)
#define COMSIG_MOVABLE_UNBUCKLE "unbuckle" //from base of atom/movable/unbuckle_mob(): (mob, force)
@@ -138,7 +141,6 @@
#define HEARING_SOURCE 8*/
#define COMSIG_MOVABLE_DISPOSING "movable_disposing" //called when the movable is added to a disposal holder object for disposal movement: (obj/structure/disposalholder/holder, obj/machinery/disposal/source)
#define COMSIG_MOVABLE_TELEPORTED "movable_teleported" //from base of do_teleport(): (channel, turf/origin, turf/destination)
// /mind signals
#define COMSIG_PRE_MIND_TRANSFER "pre_mind_transfer" //from base of mind/transfer_to() before it's done: (new_character, old_character)
#define COMPONENT_STOP_MIND_TRANSFER 1 //stops the mind transfer from happening.
@@ -148,6 +150,8 @@
#define COMSIG_MOB_EXAMINATE "mob_examinate" //from base of /mob/verb/examinate(): (atom/A)
#define COMSIG_MOB_DEATH "mob_death" //from base of mob/death(): (gibbed)
#define COMPONENT_BLOCK_DEATH_BROADCAST 1 //stops the death from being broadcasted in deadchat.
#define COMSIG_MOB_CLICKON "mob_clickon" //from base of mob/clickon(): (atom/A, params)
#define COMSIG_MOB_CANCEL_CLICKON 1
#define COMSIG_MOB_GHOSTIZE "mob_ghostize" //from base of mob/Ghostize(): (can_reenter_corpse, special, penalize)
#define COMPONENT_BLOCK_GHOSTING (1<<0)
#define COMPONENT_DO_NOT_PENALIZE_GHOSTING (1<<1)
@@ -179,7 +183,28 @@
// #define SPEECH_FORCED 7
#define COMSIG_MOB_ANTAG_ON_GAIN "mob_antag_on_gain" //from base of /datum/antagonist/on_gain(): (antag_datum)
#define COMSIG_MOB_SPELL_CAN_CAST "mob_spell_can_cast" //called from base of /obj/effect/proc_holder/spell/can_cast(): (spell)
#define COMSIG_MOB_SPELL_CAN_CAST "mob_spell_can_cast" //from base of /obj/effect/proc_holder/spell/can_cast(): (spell)
#define COMSIG_MOB_ACTION_SKILL_MOD "mob_action_skill_mod" //from base of /datum/skill_holder/action_skills_mod() : (proc args list, list/mod_values)
#define ACTION_SKILL_MOD_SKILL 1 //redundancy.
#define ACTION_SKILL_MOD_VALUE 2
#define ACTION_SKILL_MOD_THRESHOLD 3
#define ACTION_SKILL_MOD_IS_MULTI 4
//other mod values, kept separate from the args
#define MOD_VALUES_SKILL_MOD 1
#define COMSIG_MOB_ITEM_ACTION_SKILLS_MOD "mob_item_action_skills_mod" //from base of /datum/skill_holder/item_action_skills_mod() : (proc args list, mod_values)
#define ITEM_SKILLS_MOD_ITEM 1 //redundancy
#define ITEM_SKILLS_MOD_VALUE 2
#define ITEM_SKILLS_MOD_FLAGS 3
#define ITEM_SKILLS_MOD_BAD_FLAGS 4
#define ITEM_SKILLS_MOD_IS_MULTI 5
//other mod values, kept separate from the args
#define MOD_VALUES_ITEM_SKILLS_SUM 1
#define MOD_VALUES_ITEM_SKILLS_DIV 2
#define MOD_VALUES_ITEM_SKILLS_CHECKED 3
#define COMSIG_MOB_SKILL_GET_AFFINITY "mob_skill_get_affinity" //from base of /datum/skill_holder/get_skill_affinity(): (skill_path, list/return_value)
// /mob/living signals
#define COMSIG_LIVING_REGENERATE_LIMBS "living_regenerate_limbs" //from base of /mob/living/regenerate_limbs(): (noheal, excluded_limbs)
@@ -197,6 +222,7 @@
#define COMSIG_LIVING_RUN_BLOCK "living_do_run_block" //from base of mob/living/do_run_block(): (real_attack, atom/object, damage, attack_text, attack_type, armour_penetration, mob/attacker, def_zone)
#define COMSIG_LIVING_COMBAT_ENABLED "combatmode_enabled" //from base of mob/living/enable_combat_mode() (was_forced)
#define COMSIG_LIVING_COMBAT_DISABLED "combatmode_disabled" //from base of mob/living/disable_combat_mode() (was_forced)
#define COMSIG_LIVING_GET_BLOCKING_ITEMS "get_blocking_items" //from base of mob/living/get_blocking_items(): (list/items)
//ALL OF THESE DO NOT TAKE INTO ACCOUNT WHETHER AMOUNT IS 0 OR LOWER AND ARE SENT REGARDLESS!
#define COMSIG_LIVING_STATUS_STUN "living_stun" //from base of mob/living/Stun() (amount, update, ignore)
@@ -212,7 +238,7 @@
// /mob/living/carbon signals
#define COMSIG_CARBON_SOUNDBANG "carbon_soundbang" //from base of mob/living/carbon/soundbang_act(): (list(intensity))
#define COMSIG_CARBON_IDENTITY_TRANSFERRED_TO "carbon_id_transferred_to" //from datum/dna/transfer_identity(): (datum/dna, transfer_SE)
#define COMSIG_CARBON_TACKLED "carbon_tackled" //sends from tackle.dm on tackle completion
// /mob/living/simple_animal/hostile signals
#define COMSIG_HOSTILE_ATTACKINGTARGET "hostile_attackingtarget"
#define COMPONENT_HOSTILE_NO_ATTACK 1
@@ -237,7 +263,11 @@
#define COMSIG_ITEM_AFTERATTACK "item_afterattack" //from base of obj/item/afterattack(): (atom/target, mob/user, params)
#define COMSIG_ITEM_ALT_AFTERATTACK "item_alt_afterattack" //from base of obj/item/altafterattack(): (atom/target, mob/user, proximity, params)
#define COMSIG_ITEM_EQUIPPED "item_equip" //from base of obj/item/equipped(): (/mob/equipper, slot)
// Do not grant actions on equip.
#define COMPONENT_NO_GRANT_ACTIONS 1
#define COMSIG_ITEM_DROPPED "item_drop" //from base of obj/item/dropped(): (mob/user)
// relocated, tell inventory procs if those called this that the item isn't available anymore.
#define COMPONENT_DROPPED_RELOCATION 1
#define COMSIG_ITEM_PICKUP "item_pickup" //from base of obj/item/pickup(): (/mob/taker)
#define COMSIG_ITEM_ATTACK_ZONE "item_attack_zone" //from base of mob/living/carbon/attacked_by(): (mob/living/carbon/target, mob/living/user, hit_zone)
#define COMSIG_ITEM_IMBUE_SOUL "item_imbue_soul" //return a truthy value to prevent ensouling, checked in /obj/effect/proc_holder/spell/targeted/lichdom/cast(): (mob/user)
@@ -247,6 +277,9 @@
// THE FOLLOWING TWO BLOCKS SHOULD RETURN BLOCK FLAGS AS DEFINED IN __DEFINES/combat.dm!
#define COMSIG_ITEM_CHECK_BLOCK "check_block" //from base of obj/item/check_block(): (mob/living/owner, atom/object, damage, attack_text, attack_type, armour_penetration, mob/attacker, def_zone, final_block_chance, list/block_return)
#define COMSIG_ITEM_RUN_BLOCK "run_block" //from base of obj/item/run_block(): (mob/living/owner, atom/object, damage, attack_text, attack_type, armour_penetration, mob/attacker, def_zone, final_block_chance, list/block_return)
#define COMSIG_ITEM_DECONSTRUCTOR_DEEPSCAN "deconstructor_deepscan" //Called by deconstructive analyzers deepscanning an item: (obj/machinery/rnd/destructive_analyzer/analyzer_machine, mob/user, list/information_list)
// Uncovered information
#define COMPONENT_DEEPSCAN_UNCOVERED_INFORMATION 1
// /obj/item/clothing signals
#define COMSIG_SHOES_STEP_ACTION "shoes_step_action" //from base of obj/item/clothing/shoes/proc/step_action(): ()
+4 -1
View File
@@ -132,7 +132,7 @@
#define FEMALE_UNIFORM_FULL 1
#define FEMALE_UNIFORM_TOP 2
//flags for outfits that have mutantrace variants: These are hard sprited too.
//flags for outfits that have mutant race variants: Most of these require additional sprites to work.
#define STYLE_DIGITIGRADE (1<<0) //jumpsuits, suits and shoes
#define STYLE_MUZZLE (1<<1) //hats or masks
#define STYLE_SNEK_TAURIC (1<<2) //taur-friendly suits
@@ -140,6 +140,9 @@
#define STYLE_HOOF_TAURIC (1<<4)
#define STYLE_ALL_TAURIC (STYLE_SNEK_TAURIC|STYLE_PAW_TAURIC|STYLE_HOOF_TAURIC)
#define STYLE_NO_ANTHRO_ICON (1<<5) //When digis fit the default sprite fine and need no copypasted states. This is the case of skirts and winter coats, for example.
#define USE_SNEK_CLIP_MASK (1<<6)
#define USE_QUADRUPED_CLIP_MASK (1<<7)
#define USE_TAUR_CLIP_MASK (USE_SNEK_CLIP_MASK|USE_QUADRUPED_CLIP_MASK)
//digitigrade legs settings.
#define NOT_DIGITIGRADE 0
+4 -1
View File
@@ -174,7 +174,10 @@ GLOBAL_LIST_INIT(clawfootmob, typecacheof(list(
/mob/living/simple_animal/pet/fox,
/mob/living/simple_animal/chicken,
/mob/living/simple_animal/hostile/bear,
/mob/living/simple_animal/hostile/jungle/mega_arachnid
/mob/living/simple_animal/hostile/jungle/mega_arachnid,
/mob/living/simple_animal/hostile/asteroid/ice_whelp,
/mob/living/simple_animal/hostile/asteroid/wolf,
/mob/living/simple_animal/hostile/asteroid/polarbear
)))
GLOBAL_LIST_INIT(barefootmob, typecacheof(list(
+21 -2
View File
@@ -3,5 +3,24 @@
#define LANGUAGE_HIDE_ICON_IF_UNDERSTOOD 4
#define LANGUAGE_HIDE_ICON_IF_NOT_UNDERSTOOD 8
#define LANGUAGE_KNOWN "language_known"
#define LANGUAGE_SHADOWED "language_shadowed"
// LANGUAGE SOURCE DEFINES
#define LANGUAGE_ALL "all" // For use in full removal only.
#define LANGUAGE_ATOM "atom"
#define LANGUAGE_MIND "mind"
#define LANGUAGE_ABSORB "absorb"
#define LANGUAGE_APHASIA "aphasia"
#define LANGUAGE_BLOODSUCKER "bloodsucker"
#define LANGUAGE_CLOCKIE "clockie"
#define LANGUAGE_CULTIST "cultist"
#define LANGUAGE_CURATOR "curator"
#define LANGUAGE_DEVIL "devil"
#define LANGUAGE_GLAND "gland"
#define LANGUAGE_HAT "hat"
#define LANGUAGE_HIGH "high"
#define LANGUAGE_MALF "malf"
#define LANGUAGE_MASTER "master"
#define LANGUAGE_SOFTWARE "software"
#define LANGUAGE_STONER "stoner"
#define LANGUAGE_VASSAL "vassal"
#define LANGUAGE_VOICECHANGE "voicechange"
+10 -4
View File
@@ -1,6 +1,8 @@
//Defines for atom layers and planes
//KEEP THESE IN A NICE ACSCENDING ORDER, PLEASE
#define PLANE_VOID -100
#define CLICKCATCHER_PLANE -99
#define PLANE_SPACE -95
@@ -8,6 +10,10 @@
#define PLANE_SPACE_PARALLAX -90
#define PLANE_SPACE_PARALLAX_RENDER_TARGET "PLANE_SPACE_PARALLAX"
#define OPENSPACE_LAYER 17 //Openspace layer over all
#define OPENSPACE_PLANE -4 //Openspace plane below all turfs
#define OPENSPACE_BACKDROP_PLANE -3 //Black square just over openspace plane to guaranteed cover all in openspace turf
#define FLOOR_PLANE -2
#define FLOOR_PLANE_RENDER_TARGET "FLOOR_PLANE"
#define GAME_PLANE -1
@@ -61,7 +67,9 @@
#define BELOW_MOB_LAYER 3.7
#define LYING_MOB_LAYER 3.8
#define MOB_LOWER_LAYER 3.95
//#define MOB_LAYER 4 //For easy recordkeeping; this is a byond define
#define MOB_UPPER_LAYER 4.05
#define ABOVE_MOB_LAYER 4.1
#define WALL_OBJ_LAYER 4.25
#define EDGED_TURF_LAYER 4.3
@@ -83,6 +91,8 @@
#define MASSIVE_OBJ_LAYER 11
#define POINT_LAYER 12
#define CHAT_LAYER 12.1
#define EMISSIVE_BLOCKER_PLANE 12
#define EMISSIVE_BLOCKER_LAYER 12
#define EMISSIVE_BLOCKER_RENDER_TARGET "*EMISSIVE_BLOCKER_PLANE"
@@ -103,10 +113,6 @@
#define ABOVE_LIGHTING_LAYER 16
#define ABOVE_LIGHTING_RENDER_TARGET "ABOVE_LIGHTING_PLANE"
#define FLOOR_OPENSPACE_PLANE 17
#define OPENSPACE_LAYER 17
#define OPENSPACE_RENDER_TARGET "OPENSPACE_PLANE"
#define BYOND_LIGHTING_PLANE 18
#define BYOND_LIGHTING_LAYER 18
#define BYOND_LIGHTING_RENDER_TARGET "BYOND_LIGHTING_PLANE"
+8 -8
View File
@@ -22,14 +22,14 @@
//used in design to specify which machine can build it
#define IMPRINTER (1<<0) //For circuits. Uses glass/chemicals.
#define PROTOLATHE (1<<1) //New stuff. Uses glass/metal/chemicals
#define AUTOLATHE (1<<2) //Uses glass/metal only.
#define CRAFTLATHE (1<<3) //Uses fuck if I know. For use eventually.
#define MECHFAB (1<<4) //Remember, objects utilising this flag should have construction_time and construction_cost vars.
#define BIOGENERATOR (1<<5) //Uses biomass
#define LIMBGROWER (1<<6) //Uses synthetic flesh
#define SMELTER (1<<7) //uses various minerals
#define AUTOYLATHE (1<<8) // CITADEL ADD
#define PROTOLATHE (1<<1) //New stuff. Uses materials/chemicals
#define AUTOLATHE (1<<2) //Uses materials only.
#define TOYLATHE (1<<3) //Glass/metal/plastic. Meant for toys.
#define NO_PUBLIC_LATHE (1<<4) //prevents the design from being auto-unlocked by public auto(y)lathes.
#define MECHFAB (1<<5) //Remember, objects utilising this flag should have construction_time and construction_cost vars.
#define BIOGENERATOR (1<<6) //Uses biomass
#define LIMBGROWER (1<<7) //Uses synthetic flesh
#define SMELTER (1<<8) //uses various minerals
#define NANITE_COMPILER (1<<9) //Prints nanite disks
#define AUTOBOTTLER (1<<10) //Uses booze, for printing
//Note: More then one of these can be added to a design but imprinter and lathe designs are incompatable.
+3
View File
@@ -0,0 +1,3 @@
//map template annihilate_bounds
#define MAP_TEMPLATE_ANNIHILATE_PRELOAD 1 //annihilate bounds before starting loading
#define MAP_TEMPLATE_ANNIHILATE_LOADING 2 //"sweeping" delete during loading
+14 -1
View File
@@ -35,10 +35,18 @@ require only minor tweaks.
#define ZTRAIT_REEBE "Reebe"
#define ZTRAIT_RESERVED "Transit/Reserved"
#define ZTRAIT_AWAY "Away Mission"
#define ZTRAIT_VR "Virtual Reality"
#define ZTRAIT_SPACE_RUINS "Space Ruins"
#define ZTRAIT_LAVA_RUINS "Lava Ruins"
#define ZTRAIT_ICE_RUINS "Ice Ruins"
#define ZTRAIT_ICE_RUINS_UNDERGROUND "Ice Ruins Underground"
#define ZTRAIT_ISOLATED_RUINS "Isolated Ruins" //Placing ruins on z levels with this trait will use turf reservation instead of usual placement.
//boolean - weather types that occur on the level
#define ZTRAIT_SNOWSTORM "Weather_Snowstorm"
#define ZTRAIT_ASHSTORM "Weather_Ashstorm"
#define ZTRAIT_ACIDRAIN "Weather_Acidrain"
// number - bombcap is multiplied by this before being applied to bombs
#define ZTRAIT_BOMBCAP_MULTIPLIER "Bombcap Multiplier"
@@ -67,6 +75,7 @@ require only minor tweaks.
#define ZTRAITS_SPACE list(ZTRAIT_LINKAGE = CROSSLINKED, ZTRAIT_SPACE_RUINS = TRUE)
#define ZTRAITS_LAVALAND list(\
ZTRAIT_MINING = TRUE, \
ZTRAIT_ASHSTORM = TRUE, \
ZTRAIT_LAVA_RUINS = TRUE, \
ZTRAIT_BOMBCAP_MULTIPLIER = 5, \
ZTRAIT_BASETURF = /turf/open/lava/smooth/lava_land_surface)
@@ -101,4 +110,8 @@ require only minor tweaks.
#define PLACE_BELOW "below" //On z levl below - centered on same tile
#define PLACE_ISOLATED "isolated" //On isolated ruin z level
//Map type stuff.
#define MAP_TYPE_STATION "station"
#define MAP_TYPE_STATION "station"
//Random z-levels name defines.
#define AWAY_MISSION_NAME "Away Mission"
#define VIRT_REALITY_NAME "Virtual Reality"
+2
View File
@@ -0,0 +1,2 @@
/// cm3 of material matter per sheet
#define MINERAL_MATERIAL_AMOUNT 2000
+1 -1
View File
@@ -7,5 +7,5 @@
/// Flag for atoms, this flag ensures it isn't re-colored by materials. Useful for snowflake icons such as default toolboxes.
#define MATERIAL_COLOR (1<<0)
#define MATERIAL_ADD_PREFIX (1<<1)
#define MATERIAL_NO_EFFECTS (1<<2)
#define MATERIAL_EFFECTS (1<<2)
#define MATERIAL_AFFECT_STATISTICS (1<<3)
+7 -5
View File
@@ -17,6 +17,8 @@
#define PERCENT(val) (round((val)*100, 0.1))
#define CLAMP01(x) clamp(x, 0, 1)
//time of day but automatically adjusts to the server going into the next day within the same round.
//for when you need a reliable time number that doesn't depend on byond time.
#define REALTIMEOFDAY (world.timeofday + (MIDNIGHT_ROLLOVER * MIDNIGHT_ROLLOVER_CHECK))
@@ -30,13 +32,13 @@
#define FLOOR(x, y) ( round((x) / (y)) * (y) )
// Similar to clamp but the bottom rolls around to the top and vice versa. min is inclusive, max is exclusive
#define WRAP(val, min, max) CLAMP(( min == max ? min : (val) - (round(((val) - (min))/((max) - (min))) * ((max) - (min))) ),min,max-1)
#define WRAP(val, min, max) clamp(( min == max ? min : (val) - (round(((val) - (min))/((max) - (min))) * ((max) - (min))) ),min,max-1)
// Real modulus that handles decimals
#define MODULUS(x, y) ( (x) - (y) * round((x) / (y)) )
// Cotangent
#define COT(x) (1 / TAN(x))
#define COT(x) (1 / tan(x))
// Secant
#define SEC(x) (1 / cos(x))
@@ -169,8 +171,8 @@
while(pixel_y < -16)
pixel_y += 32
new_y--
new_x = CLAMP(new_x, 0, world.maxx)
new_y = CLAMP(new_y, 0, world.maxy)
new_x = clamp(new_x, 0, world.maxx)
new_y = clamp(new_y, 0, world.maxy)
return locate(new_x, new_y, starting.z)
// Returns a list where [1] is all x values and [2] is all y values that overlap between the given pair of rectangles
@@ -195,7 +197,7 @@
#define EXP_DISTRIBUTION(desired_mean) ( -(1/(1/desired_mean)) * log(rand(1, 1000) * 0.001) )
#define LORENTZ_DISTRIBUTION(x, s) ( s*TAN(TODEGREES(PI*(rand()-0.5))) + x )
#define LORENTZ_DISTRIBUTION(x, s) ( s*tan(TODEGREES(PI*(rand()-0.5))) + x )
#define LORENTZ_CUMULATIVE_DISTRIBUTION(x, y, s) ( (1/PI)*TORADIANS(arctan((x-y)/s)) + 1/2 )
#define RULE_OF_THREE(a, b, x) ((a*x)/b)
+23 -17
View File
@@ -35,15 +35,15 @@ Will print: "/mob/living/carbon/human/death" (you can optionally embed it in a s
#define BODY_ADJ_LAYER 27 //certain mutantrace features (snout, body markings) that must appear above the body parts
#define GENITALS_FRONT_LAYER 26 //Draws some genitalia above clothes and the TAUR body if need be.
#define BODY_LAYER 25 //underwear, undershirts, socks, eyes, lips(makeup)
#define FRONT_MUTATIONS_LAYER 24 //mutations that should appear above body, body_adj and bodyparts layer (e.g. laser eyes)
#define DAMAGE_LAYER 23 //damage indicators (cuts and burns)
#define UNIFORM_LAYER 22
#define ID_LAYER 21
#define HANDS_PART_LAYER 20
#define SHOES_LAYER 19
#define GLOVES_LAYER 18
#define EARS_LAYER 17
#define BODY_TAUR_LAYER 16
#define BODY_ADJ_UPPER_LAYER 24
#define FRONT_MUTATIONS_LAYER 23 //mutations that should appear above body, body_adj and bodyparts layer (e.g. laser eyes)
#define DAMAGE_LAYER 22 //damage indicators (cuts and burns)
#define UNIFORM_LAYER 21
#define ID_LAYER 20
#define HANDS_PART_LAYER 19
#define SHOES_LAYER 18
#define GLOVES_LAYER 17
#define EARS_LAYER 16
#define SUIT_LAYER 15
#define GENITALS_EXPOSED_LAYER 14
#define GLASSES_LAYER 13
@@ -71,14 +71,6 @@ Will print: "/mob/living/carbon/human/death" (you can optionally embed it in a s
#define ABOVE_SHOES_LAYER (SHOES_LAYER-1)
#define ABOVE_BODY_FRONT_LAYER (BODY_FRONT_LAYER-1)
//Security levels
#define SEC_LEVEL_GREEN 0
#define SEC_LEVEL_BLUE 1
#define SEC_LEVEL_AMBER 2
#define SEC_LEVEL_RED 3
#define SEC_LEVEL_DELTA 4
//some arbitrary defines to be used by self-pruning global lists. (see master_controller)
#define PROCESS_KILL 26 //Used to trigger removal from a processing list
@@ -524,4 +516,18 @@ GLOBAL_LIST_INIT(pda_reskins, list(PDA_SKIN_CLASSIC = 'icons/obj/pda.dmi', PDA_S
#define UNTIL(X) while(!(X)) stoplag()
//Scavenging element defines for special loot "events".
#define SCAVENGING_FOUND_NOTHING "found_nothing"
#define SCAVENGING_SPAWN_MOUSE "spawn_mouse"
#define SCAVENGING_SPAWN_MICE "spawn_mice"
#define SCAVENGING_SPAWN_TOM "spawn_tom_the_mouse"
//Scavenging element defines for ckey/mind restrictions.
#define NO_LOOT_RESTRICTION 0
#define LOOT_RESTRICTION_MIND 1
#define LOOT_RESTRICTION_CKEY 2
#define LOOT_RESTRICTION_MIND_PILE 3 //limited to the current pile.
#define LOOT_RESTRICTION_CKEY_PILE 4 //Idem
#define WANTED_FILE "wanted_message.json"
+3
View File
@@ -0,0 +1,3 @@
// obj/item/dropped
/// dropped() relocated this item, return FALSE for doUnEquip.
#define ITEM_RELOCATED_BY_DROPPED "relocated_by_dropped"
+7 -3
View File
@@ -138,6 +138,7 @@
#define MOOD_LEVEL_SAD4 -25
//Sanity levels for humans
#define SANITY_AMAZING 150
#define SANITY_GREAT 125
#define SANITY_NEUTRAL 100
#define SANITY_DISTURBED 75
@@ -265,6 +266,7 @@
#define WIZARD_AGE_MIN 30 //youngest a wizard can be
#define APPRENTICE_AGE_MIN 29 //youngest an apprentice can be
#define SHOES_SLOWDOWN 0 //How much shoes slow you down by default. Negative values speed you up
#define SHOES_SPEED_SLIGHT SHOES_SLOWDOWN - 1 // slightest speed boost to movement
#define POCKET_STRIP_DELAY 40 //time taken (in deciseconds) to search somebody's pockets
#define DOOR_CRUSH_DAMAGE 15 //the amount of damage that airlocks deal when they crush you
@@ -288,6 +290,8 @@
#define HUMAN_FIRE_STACK_ICON_NUM 3
#define PULL_PRONE_SLOWDOWN 0.6
#define FIREMAN_CARRY_SLOWDOWN 0
#define PIGGYBACK_CARRY_SLOWDOWN 1
#define GRAB_PIXEL_SHIFT_PASSIVE 6
#define GRAB_PIXEL_SHIFT_AGGRESSIVE 12
#define GRAB_PIXEL_SHIFT_NECK 16
#define SLEEP_CHECK_DEATH(X) sleep(X); if(QDELETED(src) || stat == DEAD) return;
+10
View File
@@ -0,0 +1,10 @@
/// How much someone is slowed from pulling a prone human
#define PULL_PRONE_SLOWDOWN 0.6
/// How much someone is slowed from fireman carrying a human
#define FIREMAN_CARRY_SLOWDOWN 0
/// How much someone is slowed by piggybacking a human
#define PIGGYBACK_CARRY_SLOWDOWN 1
/// slowdown when in softcrit. Note that crawling slowdown will also apply at the same time!
#define SOFTCRIT_ADD_SLOWDOWN 2
/// slowdown when crawling
#define CRAWLING_ADD_SLOWDOWN 4
+3 -75
View File
@@ -1,12 +1,3 @@
#define MOVESPEED_DATA_INDEX_PRIORITY 1
#define MOVESPEED_DATA_INDEX_FLAGS 2
#define MOVESPEED_DATA_INDEX_MULTIPLICATIVE_SLOWDOWN 3
#define MOVESPEED_DATA_INDEX_MOVETYPE 4
#define MOVESPEED_DATA_INDEX_BL_MOVETYPE 5
#define MOVESPEED_DATA_INDEX_CONFLICT 6
#define MOVESPEED_DATA_INDEX_MAX 6
//flags
#define IGNORE_NOSLOW (1 << 0)
@@ -15,70 +6,7 @@
#define MOVE_CONFLICT_JETPACK "JETPACK"
//ids
#define MOVESPEED_ID_SANITY "mood_sanity"
#define MOVESPEED_ID_MOB_WALK_RUN_CONFIG_SPEED "MOB_WALK_RUN"
#define MOVESPEED_ID_MOB_GRAB_STATE "MOB_GRAB_STATE"
#define MOVESPEED_ID_MOB_EQUIPMENT "MOB_EQUIPMENT"
#define MOVESPEED_ID_MOB_GRAVITY "MOB_GRAVITY"
#define MOVESPEED_ID_CONFIG_SPEEDMOD "MOB_CONFIG_MODIFIER"
#define MOVESPEED_ID_SLIME_REAGENTMOD "SLIME_REAGENT_MODIFIER"
#define MOVESPEED_ID_SLIME_HEALTHMOD "SLIME_HEALTH_MODIFIER"
#define MOVESPEED_ID_SLIME_TEMPMOD "SLIME_TEMPERATURE_MODIFIER"
#define MOVESPEED_ID_SLIME_STATUS "SLIME_STATUS"
#define MOVESPEED_ID_TARANTULA_WEB "TARANTULA_WEB"
#define MOVESPEED_ID_LIVING_TURF_SPEEDMOD "LIVING_TURF_SPEEDMOD"
#define MOVESPEED_ID_LIVING_LIMBLESS "LIVING_LIMBLESS"
#define MOVESPEED_ID_CARBON_SOFTCRIT "CARBON_SOFTCRIT"
#define MOVESPEED_ID_CARBON_OLDSPEED "CARBON_DEPRECATED_SPEED"
#define MOVESPEED_ID_DNA_VAULT "DNA_VAULT"
#define MOVESPEED_ID_YELLOW_ORB "YELLOW_ORB"
#define MOVESPEED_ID_TARFOOT "TARFOOT"
#define MOVESPEED_ID_SEPIA "SEPIA"
#define MOVESPEED_ID_MONKEY_REAGENT_SPEEDMOD "MONKEY_REAGENT_SPEEDMOD"
#define MOVESPEED_ID_MONKEY_TEMPERATURE_SPEEDMOD "MONKEY_TEMPERATURE_SPEEDMOD"
#define MOVESPEED_ID_MONKEY_HEALTH_SPEEDMOD "MONKEY_HEALTH_SPEEDMOD"
#define MOVESPEED_ID_CHANGELING_MUSCLES "CHANGELING_MUSCLES"
#define MOVESPEED_ID_SIMPLEMOB_VARSPEED "SIMPLEMOB_VARSPEED_MODIFIER"
#define MOVESPEED_ID_ADMIN_VAREDIT "ADMIN_VAREDIT_MODIFIER"
#define MOVESPEED_ID_PAI_SPACEWALK_SPEEDMOD "PAI_SPACEWALK_MODIFIER"
#define MOVESPEED_ID_SANITY "MOOD_SANITY"
#define MOVESPEED_ID_SPECIES "SPECIES_SPEED_MOD"
#define MOVESPEED_ID_SMALL_STRIDE "SMALL_STRIDE"
#define MOVESPEED_ID_PRONE_DRAGGING "PRONE_DRAG"
#define MOVESPEED_ID_HUMAN_CARRYING "HUMAN_CARRY"
#define MOVESPEED_ID_SHRINK_RAY "SHRUNKEN_SPEED_MODIFIER"
#define MOVESPEED_ID_SLAUGHTER "SLAUGHTER"
#define MOVESPEED_ID_CYBER_THRUSTER "CYBER_IMPLANT_THRUSTER"
#define MOVESPEED_ID_JETPACK "JETPACK"
#define MOVESPEED_ID_MKULTRA "MKULTRA"
#define MOVESPEED_ID_TASED_STATUS "TASED"
#define MOVESPEED_ID_ELECTROSTAFF "ELECTROSTAFF"
#define MOVESPEED_ID_SHOVE "SHOVE"
#define MOVESPEED_ID_FAT "FAT"
#define MOVESPEED_ID_COLD "COLD"
#define MOVESPEED_ID_HUNGRY "HUNGRY"
#define MOVESPEED_ID_DAMAGE_SLOWDOWN "DAMAGE"
#define MOVESPEED_ID_DAMAGE_SLOWDOWN_FLYING "FLYING"
#define MOVESPEED_ID_CIRRHOSIS "CIRRHOSIS"
#define MOVESPEED_ID_MOB_GRAB_STATE "mob_grab_state"
#define MOVESPEED_ID_MOB_WALK_RUN "mob_walk_run"
+4
View File
@@ -12,6 +12,10 @@
#define NANITE_CLOUD_DISABLE 2
#define NANITE_CLOUD_ENABLE 3
///Nanite Protocol types
#define NANITE_PROTOCOL_REPLICATION "nanite_replication"
#define NANITE_PROTOCOL_STORAGE "nanite_storage"
///Nanite extra settings types: used to help uis know what type an extra setting is
#define NESTYPE_TEXT "text"
#define NESTYPE_NUMBER "number"
+7 -5
View File
@@ -38,11 +38,12 @@
#define BLOCK_GAS_SMOKE_EFFECT (1<<2) //blocks the effect that chemical clouds would have on a mob --glasses, mask and helmets ONLY!
#define ALLOWINTERNALS (1<<3) //mask allows internals
#define NOSLIP (1<<4) //prevents from slipping on wet floors, in space etc
#define THICKMATERIAL (1<<5) //prevents syringes, parapens and hypos if the external suit or helmet (if targeting head) has this flag. Example: space suits, biosuit, bombsuits, thick suits that cover your body.
#define VOICEBOX_TOGGLABLE (1<<6) //The voicebox in this clothing can be toggled.
#define VOICEBOX_DISABLED (1<<7) //The voicebox is currently turned off.
#define IGNORE_HAT_TOSS (1<<8) //Hats with negative effects when worn (i.e the tinfoil hat).
#define SCAN_REAGENTS (1<<9) // Allows helmets and glasses to scan reagents.
#define NOSLIP_ICE (1<<5) //prevents from slipping on frozen floors
#define THICKMATERIAL (1<<6) //prevents syringes, parapens and hypos if the external suit or helmet (if targeting head) has this flag. Example: space suits, biosuit, bombsuits, thick suits that cover your body.
#define VOICEBOX_TOGGLABLE (1<<7) //The voicebox in this clothing can be toggled.
#define VOICEBOX_DISABLED (1<<8) //The voicebox is currently turned off.
#define IGNORE_HAT_TOSS (1<<9) //Hats with negative effects when worn (i.e the tinfoil hat).
#define SCAN_REAGENTS (1<<10) // Allows helmets and glasses to scan reagents.
// Flags for the organ_flags var on /obj/item/organ
@@ -52,3 +53,4 @@
#define ORGAN_EXTERNAL (1<<3) //Was this organ implanted/inserted/etc, if true will not be removed during species change.
#define ORGAN_VITAL (1<<4) //Currently only the brain
#define ORGAN_NO_SPOIL (1<<5) //Do not spoil under any circumstances
#define ORGAN_NO_DISMEMBERMENT (1<<6) //Immune to disembowelment.
+1
View File
@@ -65,6 +65,7 @@
#define FREQ_ENGINEERING 1357 // Engineering comms frequency, orange
#define FREQ_SECURITY 1359 // Security comms frequency, red
#define FREQ_HOLOGRID_SOLUTION 1433
#define FREQ_STATUS_DISPLAYS 1435
#define FREQ_ATMOS_ALARMS 1437 // air alarms <-> alert computers
#define FREQ_ATMOS_CONTROL 1439 // air alarms <-> vents and scrubbers
+13 -1
View File
@@ -22,11 +22,23 @@
// Is an open container for all intents and purposes.
#define OPENCONTAINER (REFILLABLE | DRAINABLE | TRANSPARENT)
//reagents_value defines, for cargo stuff.
//reagents_value defines, basically a multiplier used in reagent containers cargo selling.
#define DEFAULT_REAGENTS_VALUE 1
#define NO_REAGENTS_VALUE 0
#define HARVEST_REAGENTS_VALUE 0.3
/// Standard reagents value defines.
/// Take a grain of salt, only "rare" reagents should have a decent value here, for balance reasons.
/// TL;DR Think of it also like general market request price more than rarity.
#define REAGENT_VALUE_NONE 0 //all the stuff pretty much available in potentially unlimited quantities.
#define REAGENT_VALUE_VERY_COMMON 0.1 //same as above, just not so unlimited.
#define REAGENT_VALUE_COMMON 0.5
#define REAGENT_VALUE_UNCOMMON 1
#define REAGENT_VALUE_RARE 2.5
#define REAGENT_VALUE_VERY_RARE 5
#define REAGENT_VALUE_EXCEPTIONAL 10 //extremely rare or tedious to craft, possibly unsynthetizable, reagents.
#define REAGENT_VALUE_AMAZING 30 //reserved ONLY for non-mass produceable, unsynthetizable reagents.
#define REAGENT_VALUE_GLORIOUS 300 //reagents that shouldn't be possible to get or farm under normal conditions. e.g. Romerol, fungal TB, adminordrazine...
#define TOUCH 1 // splashing
#define INGEST 2 // ingestion
+2 -1
View File
@@ -60,7 +60,8 @@
#define DESIGN_ID_IGNORE "IGNORE_THIS_DESIGN"
#define RESEARCH_MATERIAL_RECLAMATION_ID "__materials"
#define RESEARCH_MATERIAL_RECLAMATION_ID "__materials"
#define RESEARCH_DEEP_SCAN_ID "__deepscan"
//When adding new types, update the list below!
#define TECHWEB_POINT_TYPE_GENERIC "General Research"
+5
View File
@@ -0,0 +1,5 @@
// the clamps are just sanity checks.
/// Efficiency scaling for stock part level to material usage. All code concerning lathing and production from raw material sheet should be using this.
#define STANDARD_PART_LEVEL_LATHE_COEFFICIENT(level) clamp(1 - (level * 0.1), 0, 1)
/// Efficiency scaling for stock part level to ore factor. All code concerning lathing and production from raw ores to raw material sheets should be using this.
#define STANDARD_PART_LEVEL_ORE_COEFFICIENT(level) clamp(1 + (level * 0.125), 1, 10)
+10
View File
@@ -0,0 +1,10 @@
//Security levels
#define SEC_LEVEL_GREEN 1
#define SEC_LEVEL_BLUE 2
#define SEC_LEVEL_AMBER 3
#define SEC_LEVEL_RED 4
#define SEC_LEVEL_DELTA 5
//Macro helpers.
#define SECLEVEL2NUM(text) (GLOB.all_security_levels.Find(text))
#define NUM2SECLEVEL(num) (ISINRANGE(num, 1, length(GLOB.all_security_levels)) ? GLOB.all_security_levels[num] : null)
+77
View File
@@ -0,0 +1,77 @@
/// true/false
#define SKILL_PROGRESSION_BINARY 1
/// numerical
#define SKILL_PROGRESSION_NUMERICAL 2
/// Enum
#define SKILL_PROGRESSION_ENUM 3
/// Levels
#define SKILL_PROGRESSION_LEVEL 4
/// Max value of skill for numerical skills
#define SKILL_NUMERICAL_MAX 100
/// Min value of skill for numerical skills
#define SKILL_NUMERICAL_MIN 0
// Standard values for job starting skills
#define STARTING_SKILL_SURGERY_MEDICAL 35 //out of SKILL_NUMERICAL_MAX
// Standard values for job starting skill affinities
#define STARTING_SKILL_AFFINITY_SURGERY_MEDICAL 1.2
#define STARTING_SKILL_AFFINITY_WIRING_ENGI_ROBO 1.2
// Standard values for skill gain (this is multiplied by affinity)
#define DEF_SKILL_GAIN 1
#define SKILL_GAIN_SURGERY_PER_STEP 0.25
#define SKILL_AFFINITY_MOOD_BONUS 1.25
///Items skill_flags and other defines
#define SKILL_USE_TOOL (1<<0)
#define SKILL_TRAINING_TOOL (1<<1)
#define SKILL_ATTACK_MOB (1<<2)
#define SKILL_TRAIN_ATTACK_MOB (1<<3)
#define SKILL_ATTACK_OBJ (1<<4)
#define SKILL_TRAIN_ATTACK_OBJ (1<<5)
#define SKILL_STAMINA_COST (1<<6) //Influences the stamina cost from weapon usage.
#define SKILL_THROW_STAM_COST (1<<7)
#define SKILL_COMBAT_MODE (1<<8) //The user must have combat mode on.
#define SKILL_USE_MOOD (1<<9) //Is the skill negatively affected by bad mood.
#define SKILL_TRAIN_MOOD (1<<10) //Is this skill training affected by good mood.
///competency_threshold index defines
#define THRESHOLD_COMPETENT 1
#define THRESHOLD_EXPERT 2
#define THRESHOLD_MASTER 3
/// Level/Experience skills defines.
#define STD_XP_LVL_UP 100
#define STD_XP_LVL_MULTI 2
#define STD_MAX_LVL 4
#define RPG_MAX_LVL 100
#define DORF_XP_LVL_UP 400
#define DORF_XP_LVL_MULTI 100
#define DORF_MAX_LVL 20 // Dabbling, novice, adequate, [...], legendary +3, legendary +4, legendary +5
//level up methods defines
#define STANDARD_LEVEL_UP "standard_level_up"
#define DWARFY_LEVEL_UP "dwarfy_level_up"
//job skill level defines
#define JOB_SKILL_UNTRAINED 0
#define JOB_SKILL_BASIC 1
#define JOB_SKILL_TRAINED 2
#define JOB_SKILL_EXPERT 3
#define JOB_SKILL_MASTER 4
//other skill level defines, not an exhaustive catalogue, only contains be most relevant ones.
#define DORF_SKILL_COMPETENT 3
#define DORF_SKILL_EXPERT 8
#define DORF_SKILL_MASTER 12
+8
View File
@@ -0,0 +1,8 @@
//How experience levels are calculated.
#define XP_LEVEL(std, multi, lvl) (std*((multi**lvl)/(multi-1))-std/(multi-1)) //don't use 1 as multi, you'll get division by zero errors
#define DORF_XP_LEVEL(std, extra, lvl) (std*lvl+extra*(lvl*(lvl/2+0.5)))
//More experience value getter macros
#define GET_STANDARD_LVL(lvl) XP_LEVEL(STD_XP_LVL_UP, STD_XP_LVL_MULTI, lvl)
#define GET_DORF_LVL(lvl) DORF_XP_LEVEL(DORF_XP_LVL_UP, DORF_XP_LVL_MULTI, lvl)
+3 -1
View File
@@ -34,6 +34,8 @@
#define STATUS_EFFECT_HIPPOCRATIC_OATH /datum/status_effect/hippocraticOath //Gives you an aura of healing as well as regrowing the Rod of Asclepius if lost
#define STATUS_EFFECT_REGENERATIVE_CORE /datum/status_effect/regenerative_core //removes damage slowdown while giving a slow regenerating effect
/////////////
// DEBUFFS //
/////////////
@@ -78,7 +80,7 @@
#define STATUS_EFFECT_CRUSHERMARK /datum/status_effect/crusher_mark //if struck with a proto-kinetic crusher, takes a ton of damage
#define STATUS_EFFECT_SAWBLEED /datum/status_effect/saw_bleed //if the bleed builds up enough, takes a ton of damage
#define STATUS_EFFECT_SAWBLEED /datum/status_effect/stacking/saw_bleed //if the bleed builds up enough, takes a ton of damage
#define STATUS_EFFECT_NECKSLICE /datum/status_effect/neck_slice //Creates the flavor messages for the neck-slice
+9 -2
View File
@@ -132,8 +132,15 @@
#define RUNLEVELS_DEFAULT (RUNLEVEL_SETUP | RUNLEVEL_GAME | RUNLEVEL_POSTGAME)
// SSair run section
#define SSAIR_PIPENETS 1
#define SSAIR_ATMOSMACHINERY 2
#define SSAIR_REACTQUEUE 3
#define SSAIR_EXCITEDGROUPS 4
#define SSAIR_HIGHPRESSURE 5
#define SSAIR_HOTSPOTS 6
#define SSAIR_SUPERCONDUCTIVITY 7
#define SSAIR_REBUILD_PIPENETS 8
#define COMPILE_OVERLAYS(A)\
if (TRUE) {\
+40 -37
View File
@@ -78,6 +78,7 @@
#define TRAIT_MONKEYLIKE "monkeylike" //sets IsAdvancedToolUser to FALSE
#define TRAIT_PACIFISM "pacifism"
#define TRAIT_IGNORESLOWDOWN "ignoreslow"
#define TRAIT_IGNOREDAMAGESLOWDOWN "ignoredamageslowdown"
#define TRAIT_DEATHCOMA "deathcoma" //Causes death-like unconsciousness
#define TRAIT_FAKEDEATH "fakedeath" //Makes the owner appear as dead to most forms of medical examination
#define TRAIT_DISFIGURED "disfigured"
@@ -150,6 +151,44 @@
#define TRAIT_PUGILIST "pugilist" //This guy punches people for a living
#define TRAIT_KI_VAMPIRE "ki-vampire" //when someone with this trait rolls maximum damage on a punch and stuns the target, they regain some stamina and do clone damage
#define TRAIT_PASSTABLE "passtable"
#define TRAIT_GIANT "giant"
#define TRAIT_DWARF "dwarf"
#define TRAIT_ALCOHOL_TOLERANCE "alcohol_tolerance"
#define TRAIT_AGEUSIA "ageusia"
#define TRAIT_HEAVY_SLEEPER "heavy_sleeper"
#define TRAIT_NIGHT_VISION "night_vision"
#define TRAIT_LIGHT_STEP "light_step"
#define TRAIT_SILENT_STEP "silent_step"
#define TRAIT_SPEEDY_STEP "speedy_step"
#define TRAIT_SPIRITUAL "spiritual"
#define TRAIT_VORACIOUS "voracious"
#define TRAIT_SELF_AWARE "self_aware"
#define TRAIT_FREERUNNING "freerunning"
#define TRAIT_SKITTISH "skittish"
#define TRAIT_POOR_AIM "poor_aim"
#define TRAIT_PROSOPAGNOSIA "prosopagnosia"
#define TRAIT_DRUNK_HEALING "drunk_healing"
#define TRAIT_TAGGER "tagger"
#define TRAIT_PHOTOGRAPHER "photographer"
#define TRAIT_MUSICIAN "musician"
#define TRAIT_PERMABONER "permanent_arousal"
#define TRAIT_NEVERBONER "never_aroused"
#define TRAIT_MASO "masochism"
#define TRAIT_HIGH_BLOOD "high_blood"
#define TRAIT_PARA "paraplegic"
#define TRAIT_EMPATH "empath"
#define TRAIT_FRIENDLY "friendly"
#define TRAIT_CULT_EYES "cult_eyes"
#define TRAIT_AUTO_CATCH_ITEM "auto_catch_item"
#define TRAIT_CLOWN_MENTALITY "clown_mentality" // The future is now, clownman.
#define TRAIT_FREESPRINT "free_sprinting"
#define TRAIT_XRAY_VISION "xray_vision"
#define TRAIT_THERMAL_VISION "thermal_vision"
#define TRAIT_NO_TELEPORT "no-teleport" //you just can't
#define TRAIT_NO_INTERNALS "no-internals"
#define TRAIT_NO_ALCOHOL "alcohol_intolerance"
#define TRAIT_MUTATION_STASIS "mutation_stasis" //Prevents processed genetics mutations from processing.
#define TRAIT_FAST_PUMP "fast_pump"
// mobility flag traits
// IN THE FUTURE, IT WOULD BE NICE TO DO SOMETHING SIMILAR TO https://github.com/tgstation/tgstation/pull/48923/files (ofcourse not nearly the same because I have my.. thoughts on it)
@@ -183,43 +222,6 @@
// item traits
#define TRAIT_NODROP "nodrop"
#define TRAIT_ALCOHOL_TOLERANCE "alcohol_tolerance"
#define TRAIT_AGEUSIA "ageusia"
#define TRAIT_HEAVY_SLEEPER "heavy_sleeper"
#define TRAIT_NIGHT_VISION "night_vision"
#define TRAIT_LIGHT_STEP "light_step"
#define TRAIT_SILENT_STEP "silent_step"
#define TRAIT_SPEEDY_STEP "speedy_step"
#define TRAIT_SPIRITUAL "spiritual"
#define TRAIT_VORACIOUS "voracious"
#define TRAIT_SELF_AWARE "self_aware"
#define TRAIT_FREERUNNING "freerunning"
#define TRAIT_SKITTISH "skittish"
#define TRAIT_POOR_AIM "poor_aim"
#define TRAIT_PROSOPAGNOSIA "prosopagnosia"
#define TRAIT_DRUNK_HEALING "drunk_healing"
#define TRAIT_TAGGER "tagger"
#define TRAIT_PHOTOGRAPHER "photographer"
#define TRAIT_MUSICIAN "musician"
#define TRAIT_PERMABONER "permanent_arousal"
#define TRAIT_NEVERBONER "never_aroused"
#define TRAIT_NYMPHO "nymphomania"
#define TRAIT_MASO "masochism"
#define TRAIT_HIGH_BLOOD "high_blood"
#define TRAIT_PARA "paraplegic"
#define TRAIT_EMPATH "empath"
#define TRAIT_FRIENDLY "friendly"
#define TRAIT_CULT_EYES "cult_eyes"
#define TRAIT_AUTO_CATCH_ITEM "auto_catch_item"
#define TRAIT_CLOWN_MENTALITY "clown_mentality" // The future is now, clownman.
#define TRAIT_FREESPRINT "free_sprinting"
#define TRAIT_XRAY_VISION "xray_vision"
#define TRAIT_THERMAL_VISION "thermal_vision"
#define TRAIT_NO_TELEPORT "no-teleport" //you just can't
#define TRAIT_NO_INTERNALS "no-internals"
#define TRAIT_NO_ALCOHOL "alcohol_intolerance"
#define TRAIT_MUTATION_STASIS "mutation_stasis" //Prevents processed genetics mutations from processing.
// common trait sources
#define TRAIT_GENERIC "generic"
#define EYE_DAMAGE "eye_damage"
@@ -244,6 +246,7 @@
#define BLOODSUCKER_TRAIT "bloodsucker"
#define SHOES_TRAIT "shoes" //inherited from your sweet kicks
#define GLOVE_TRAIT "glove" //inherited by your cool gloves
#define BOOK_TRAIT "granter (book)" // knowledge is power
// unique trait sources, still defines
#define STATUE_MUTE "statue"
+1
View File
@@ -73,6 +73,7 @@
#define VV_HK_EXPOSE "expose"
#define VV_HK_CALLPROC "proc_call"
#define VV_HK_MARK "mark"
#define VV_HK_ADDCOMPONENT "addcomponent"
#define VV_HK_MODIFY_TRAITS "modtraits"
// /atom
+98 -40
View File
@@ -11,6 +11,7 @@
#define LAZYINITLIST(L) if (!L) L = list()
#define UNSETEMPTY(L) if (L && !length(L)) L = null
#define LAZYCOPY(L) (L ? L.Copy() : list() )
#define LAZYREMOVE(L, I) if(L) { L -= I; if(!length(L)) { L = null; } }
#define LAZYADD(L, I) if(!L) { L = list(); } L += I;
#define LAZYOR(L, I) if(!L) { L = list(); } L |= I;
@@ -21,34 +22,47 @@
#define LAZYCLEARLIST(L) if(L) L.Cut()
#define SANITIZE_LIST(L) ( islist(L) ? L : list() )
#define reverseList(L) reverseRange(L.Copy())
#define LAZYADDASSOC(L, K, V) if(!L) { L = list(); } L[K] += list(V);
#define LAZYREMOVEASSOC(L, K, V) if(L) { if(L[K]) { L[K] -= V; if(!length(L[K])) L -= K; } if(!length(L)) L = null; }
// binary search sorted insert
// IN: Object to be inserted
// LIST: List to insert object into
// TYPECONT: The typepath of the contents of the list
// COMPARE: The variable on the objects to compare
#define BINARY_INSERT(IN, LIST, TYPECONT, COMPARE) \
var/__BIN_CTTL = length(LIST);\
if(!__BIN_CTTL) {\
LIST += IN;\
} else {\
var/__BIN_LEFT = 1;\
var/__BIN_RIGHT = __BIN_CTTL;\
var/__BIN_MID = (__BIN_LEFT + __BIN_RIGHT) >> 1;\
var/##TYPECONT/__BIN_ITEM;\
while(__BIN_LEFT < __BIN_RIGHT) {\
__BIN_ITEM = LIST[__BIN_MID];\
if(__BIN_ITEM.##COMPARE <= IN.##COMPARE) {\
__BIN_LEFT = __BIN_MID + 1;\
} else {\
__BIN_RIGHT = __BIN_MID;\
/// Passed into BINARY_INSERT to compare keys
#define COMPARE_KEY __BIN_LIST[__BIN_MID]
/// Passed into BINARY_INSERT to compare values
#define COMPARE_VALUE __BIN_LIST[__BIN_LIST[__BIN_MID]]
/****
* Binary search sorted insert
* INPUT: Object to be inserted
* LIST: List to insert object into
* TYPECONT: The typepath of the contents of the list
* COMPARE: The object to compare against, usualy the same as INPUT
* COMPARISON: The variable on the objects to compare
*/
#define BINARY_INSERT(INPUT, LIST, TYPECONT, COMPARE, COMPARISON, COMPTYPE) \
do {\
var/list/__BIN_LIST = LIST;\
var/__BIN_CTTL = length(__BIN_LIST);\
if(!__BIN_CTTL) {\
__BIN_LIST += INPUT;\
} else {\
var/__BIN_LEFT = 1;\
var/__BIN_RIGHT = __BIN_CTTL;\
var/__BIN_MID = (__BIN_LEFT + __BIN_RIGHT) >> 1;\
var/##TYPECONT/__BIN_ITEM;\
while(__BIN_LEFT < __BIN_RIGHT) {\
__BIN_ITEM = COMPTYPE;\
if(__BIN_ITEM.##COMPARISON <= COMPARE.##COMPARISON) {\
__BIN_LEFT = __BIN_MID + 1;\
} else {\
__BIN_RIGHT = __BIN_MID;\
};\
__BIN_MID = (__BIN_LEFT + __BIN_RIGHT) >> 1;\
};\
__BIN_MID = (__BIN_LEFT + __BIN_RIGHT) >> 1;\
__BIN_ITEM = COMPTYPE;\
__BIN_MID = __BIN_ITEM.##COMPARISON > COMPARE.##COMPARISON ? __BIN_MID : __BIN_MID + 1;\
__BIN_LIST.Insert(__BIN_MID, INPUT);\
};\
__BIN_ITEM = LIST[__BIN_MID];\
__BIN_MID = __BIN_ITEM.##COMPARE > IN.##COMPARE ? __BIN_MID : __BIN_MID + 1;\
LIST.Insert(__BIN_MID, IN);\
}
} while(FALSE)
//Returns a list in plain english as a string
/proc/english_list(list/input, nothing_text = "nothing", and_text = " and ", comma_text = ", ", final_comma_text = "" )
@@ -231,40 +245,77 @@
//Picks a random element from a list based on a weighting system:
//1. Adds up the total of weights for each element
//2. Gets a number between 1 and that total
//2. Gets the total from 0% to 100% of previous total value.
//3. For each element in the list, subtracts its weighting from that number
//4. If that makes the number 0 or less, return that element.
/proc/pickweight(list/L)
/proc/pickweight(list/L, base_weight = 1)
var/total = 0
var/item
for (item in L)
if (!L[item])
L[item] = 1
L[item] = base_weight
total += L[item]
total = rand(1, total)
total = rand() * total
for (item in L)
total -=L [item]
total -= L[item]
if (total <= 0)
return item
return null
/proc/pickweightAllowZero(list/L) //The original pickweight proc will sometimes pick entries with zero weight. I'm not sure if changing the original will break anything, so I left it be.
//Picks a number of elements from a list based on weight.
//This is highly optimised and good for things like grabbing 200 items from a list of 40,000
//Much more efficient than many pickweight calls
/proc/pickweight_mult(list/L, quantity, base_weight = 1)
//First we total the list as normal
var/total = 0
var/item
for (item in L)
if (!L[item])
L[item] = 0
L[item] = base_weight
total += L[item]
total = rand(0, total)
for (item in L)
total -=L [item]
if (total <= 0 && L[item])
return item
//Next we will make a list of randomly generated numbers, called Requests
//It is critical that this list be sorted in ascending order, so we will build it in that order
//First one is free, so we start counting at 2
var/list/requests = list(rand(1, total))
for (var/i in 2 to quantity)
//Each time we generate the next request
var/newreq = rand()* total
//We will loop through all existing requests
for (var/j in 1 to requests.len)
//We keep going through the list until we find an element which is bigger than the one we want to add
if (requests[j] > newreq)
//And then we insert the newqreq at that point, pushing everything else forward
requests.Insert(j, newreq)
break
return null
//Now when we get here, we have a list of random numbers sorted in ascending order.
//The length of that list is equal to Quantity passed into this function
//Next we make a list to store results
var/list/results = list()
//Zero the total, we'll reuse it
total = 0
//Now we will iterate forward through the items list, adding each weight to the total
for (item in L)
total += L[item]
//After each item we do a while loop
while (requests.len && total >= requests[1])
//If the total is higher than the value of the first request
results += item //We add this item to the results list
requests.Cut(1,2) //And we cut off the top of the requests list
//This while loop will repeat until the next request is higher than the total.
//The current item might be added to the results list many times, in this process
//By the time we get here:
//Requests will be empty
//Results will have a length of quality
return results
//Pick a random element from the list and remove it from the list.
/proc/pick_n_take(list/L)
@@ -274,6 +325,13 @@
. = L[picked]
L.Cut(picked,picked+1) //Cut is far more efficient that Remove()
//Pick a random element from the list by weight and remove it from the list.
//Result is returned as a list in the format list(key, value)
/proc/pickweight_n_take(list/L, base_weight = 1)
if (L.len)
. = pickweight(L, base_weight)
L.Remove(.)
//Returns the top(last) element from the list and removes it from the list (typical stack function)
/proc/pop(list/L)
if(L.len)
+5
View File
@@ -58,6 +58,11 @@ GLOBAL_LIST_INIT(typecache_powerfailure_safe_areas, typecacheof(/area/engine/eng
else if(isarea(areatype))
var/area/areatemp = areatype
areatype = areatemp.type
else if(islist(areatype))
var/list/turfs = list()
for(var/A in areatype)
turfs += get_area_turfs(A)
return turfs
else if(!ispath(areatype))
return null
+23
View File
@@ -88,6 +88,7 @@
init_subtypes(/datum/crafting_recipe, GLOB.crafting_recipes)
INVOKE_ASYNC(GLOBAL_PROC, /proc/init_ref_coin_values) //so the current procedure doesn't sleep because of UNTIL()
INVOKE_ASYNC(GLOBAL_PROC, /proc/setupGenetics)
//creates every subtype of prototype (excluding prototype) and adds it to list L.
//if no list/L is provided, one is created.
@@ -113,3 +114,25 @@
UNTIL(C.flags_1 & INITIALIZED_1) //we want to make sure the value is calculated and not null.
GLOB.coin_values[path] = C.value
qdel(C)
/proc/setupGenetics()
var/list/mutations = subtypesof(/datum/mutation/human)
shuffle_inplace(mutations)
for(var/A in subtypesof(/datum/generecipe))
var/datum/generecipe/GR = A
GLOB.mutation_recipes[initial(GR.required)] = initial(GR.result)
for(var/i in 1 to LAZYLEN(mutations))
var/path = mutations[i] //byond gets pissy when we do it in one line
var/datum/mutation/human/B = new path ()
B.alias = "Mutation #[i]"
GLOB.all_mutations[B.type] = B
GLOB.full_sequences[B.type] = generate_gene_sequence(B.blocks)
if(B.locked)
continue
if(B.quality == POSITIVE)
GLOB.good_mutations |= B
else if(B.quality == NEGATIVE)
GLOB.bad_mutations |= B
else if(B.quality == MINOR_NEGATIVE)
GLOB.not_good_mutations |= B
CHECK_TICK
+1 -1
View File
@@ -61,7 +61,7 @@
var/adjacencies = 0
var/atom/movable/AM
if(ismovableatom(A))
if(ismovable(A))
AM = A
if(AM.can_be_unanchored && !AM.anchored)
return 0
+2
View File
@@ -12,3 +12,5 @@
#define is_reserved_level(z) SSmapping.level_trait(z, ZTRAIT_RESERVED)
#define is_away_level(z) SSmapping.level_trait(z, ZTRAIT_AWAY)
#define is_vr_level(z) SSmapping.level_trait(z, ZTRAIT_VR)
+19 -11
View File
@@ -47,7 +47,7 @@
init_sprite_accessory_subtypes(/datum/sprite_accessory/underwear/socks, GLOB.socks_list)
return pick(GLOB.socks_list)
/proc/random_features(intendedspecies)
/proc/random_features(intendedspecies, intended_gender)
if(!GLOB.tails_list_human.len)
init_sprite_accessory_subtypes(/datum/sprite_accessory/tails/human, GLOB.tails_list_human)
if(!GLOB.tails_list_lizard.len)
@@ -149,7 +149,13 @@
var/color2 = random_short_color()
var/color3 = random_short_color()
//CIT CHANGE - changes this entire return to support cit's snowflake parts
var/body_model = MALE
switch(intended_gender)
if(MALE, FEMALE)
body_model = intended_gender
if(PLURAL)
body_model = pick(MALE,FEMALE)
return(list(
"mcolor" = color1,
"mcolor2" = color2,
@@ -157,9 +163,11 @@
"tail_lizard" = pick(GLOB.tails_list_lizard),
"tail_human" = "None",
"wings" = "None",
"wings_color" = "FFF",
"deco_wings" = "None",
"snout" = pick(GLOB.snouts_list),
"horns" = pick(GLOB.horns_list),
"horns" = "None",
"horns_color" = "85615a",
"ears" = "None",
"frills" = pick(GLOB.frills_list),
"spines" = pick(GLOB.spines_list),
@@ -168,7 +176,7 @@
"caps" = pick(GLOB.caps_list),
"insect_wings" = pick(GLOB.insect_wings_list),
"insect_fluff" = "None",
"insect_markings" = pick(GLOB.insect_markings_list),
"insect_markings" = pick(GLOB.insect_markings_list),
"taur" = "None",
"mam_body_markings" = snowflake_markings_list.len ? pick(snowflake_markings_list) : "None",
"mam_ears" = snowflake_ears_list ? pick(snowflake_ears_list) : "None",
@@ -209,7 +217,7 @@
"ipc_antenna" = "None",
"flavor_text" = "",
"meat_type" = "Mammalian",
"body_model" = MALE,
"body_model" = body_model,
"body_size" = RESIZE_DEFAULT_SIZE
))
@@ -311,7 +319,7 @@ GLOBAL_LIST_EMPTY(species_list)
else
return "unknown"
/proc/do_mob(mob/user , mob/target, time = 30, uninterruptible = 0, progress = 1, datum/callback/extra_checks = null, ignorehelditem = 0)
/proc/do_mob(mob/user , mob/target, time = 30, uninterruptible = 0, progress = 1, datum/callback/extra_checks = null, ignorehelditem = FALSE, resume_time = 0 SECONDS)
if(!user || !target)
return 0
var/user_loc = user.loc
@@ -330,10 +338,10 @@ GLOBAL_LIST_EMPTY(species_list)
var/endtime = world.time+time
var/starttime = world.time
. = 1
while (world.time < endtime)
while (world.time + resume_time < endtime)
stoplag(1)
if (progress)
progbar.update(world.time - starttime)
progbar.update(world.time - starttime + resume_time)
if(QDELETED(user) || QDELETED(target))
. = 0
break
@@ -365,7 +373,7 @@ GLOBAL_LIST_EMPTY(species_list)
checked_health["health"] = health
return ..()
/proc/do_after(mob/user, var/delay, needhand = 1, atom/target = null, progress = 1, datum/callback/extra_checks = null, required_mobility_flags = (MOBILITY_USE|MOBILITY_MOVE))
/proc/do_after(mob/user, var/delay, needhand = 1, atom/target = null, progress = 1, datum/callback/extra_checks = null, required_mobility_flags = (MOBILITY_USE|MOBILITY_MOVE), resume_time = 0 SECONDS)
if(!user)
return 0
var/atom/Tloc = null
@@ -394,10 +402,10 @@ GLOBAL_LIST_EMPTY(species_list)
var/starttime = world.time
. = 1
var/mob/living/L = isliving(user) && user //evals to last thing eval'd
while (world.time < endtime)
while (world.time + resume_time < endtime)
stoplag(1)
if (progress)
progbar.update(world.time - starttime)
progbar.update(world.time - starttime + resume_time)
if(drifting && !user.inertia_dir)
drifting = 0
+1 -1
View File
@@ -11,7 +11,7 @@
var/screenviewY = screenview[2] * world.icon_size
var/ox = round(screenviewX/2) - client.pixel_x //"origin" x
var/oy = round(screenviewY/2) - client.pixel_y //"origin" y
var/angle = SIMPLIFY_DEGREES(ATAN2(y - oy, x - ox))
var/angle = SIMPLIFY_DEGREES(arctan(y - oy, x - ox))
return angle
//Wow, specific name!
+2 -2
View File
@@ -2,9 +2,9 @@
/proc/sanitize_frequency(frequency, free = FALSE)
frequency = round(frequency)
if(free)
. = CLAMP(frequency, MIN_FREE_FREQ, MAX_FREE_FREQ)
. = clamp(frequency, MIN_FREE_FREQ, MAX_FREE_FREQ)
else
. = CLAMP(frequency, MIN_FREQ, MAX_FREQ)
. = clamp(frequency, MIN_FREQ, MAX_FREQ)
if(!(. % 2)) // Ensure the last digit is an odd number
. += 1
+1 -1
View File
@@ -563,7 +563,7 @@
if(objective.completable)
var/completion = objective.check_completion()
if(completion >= 1)
objective_parts += "<B>Objective #[count]</B>: [objective.explanation_text] <span class='greentext'><B>Success!</span>"
objective_parts += "<B>Objective #[count]</B>: [objective.explanation_text] <span class='greentext'><B>Success!</B></span>"
else if(completion <= 0)
objective_parts += "<B>Objective #[count]</B>: [objective.explanation_text] <span class='redtext'>Fail.</span>"
else
+7
View File
@@ -6,6 +6,13 @@
return number
return default
/proc/sanitize_num_clamp(number, min=0, max=1, default=0, quantize=0)
if(!isnum(number))
return default
. = clamp(number, min, max)
if(quantize)
. = round(number, quantize)
/proc/sanitize_text(text, default="")
if(istext(text))
return text
+28 -5
View File
@@ -434,6 +434,29 @@ Turf and target are separate in case you want to teleport some distance from a t
return locate(x,y,A.z)
/**
* Get ranged target turf, but with direct targets as opposed to directions
*
* Starts at atom A and gets the exact angle between A and target
* Moves from A with that angle, Range amount of times, until it stops, bound to map size
* Arguments:
* * A - Initial Firer / Position
* * target - Target to aim towards
* * range - Distance of returned target turf from A
* * offset - Angle offset, 180 input would make the returned target turf be in the opposite direction
*/
/proc/get_ranged_target_turf_direct(atom/A, atom/target, range, offset)
var/angle = arctan(target.x - A.x, target.y - A.y)
if(offset)
angle += offset
var/turf/T = get_turf(A)
for(var/i in 1 to range)
var/turf/check = locate(A.x + cos(angle) * i, A.y + sin(angle) * i, A.z)
if(!check)
break
T = check
return T
// returns turf relative to A offset in dx and dy tiles
// bound to map limits
@@ -777,8 +800,8 @@ GLOBAL_LIST_INIT(WALLITEMS_INVERSE, typecacheof(list(
tX = splittext(tX[1], ":")
tX = tX[1]
var/list/actual_view = getviewsize(C ? C.view : world.view)
tX = CLAMP(origin.x + text2num(tX) - round(actual_view[1] / 2) - 1, 1, world.maxx)
tY = CLAMP(origin.y + text2num(tY) - round(actual_view[2] / 2) - 1, 1, world.maxy)
tX = clamp(origin.x + text2num(tX) - round(actual_view[1] / 2) - 1, 1, world.maxx)
tY = clamp(origin.y + text2num(tY) - round(actual_view[2] / 2) - 1, 1, world.maxy)
return locate(tX, tY, tZ)
/proc/screen_loc2turf(text, turf/origin, client/C)
@@ -791,8 +814,8 @@ GLOBAL_LIST_INIT(WALLITEMS_INVERSE, typecacheof(list(
tX = text2num(tX[2])
tZ = origin.z
var/list/actual_view = getviewsize(C ? C.view : world.view)
tX = CLAMP(origin.x + round(actual_view[1] / 2) - tX, 1, world.maxx)
tY = CLAMP(origin.y + round(actual_view[2] / 2) - tY, 1, world.maxy)
tX = clamp(origin.x + round(actual_view[1] / 2) - tX, 1, world.maxx)
tY = clamp(origin.y + round(actual_view[2] / 2) - tY, 1, world.maxy)
return locate(tX, tY, tZ)
/proc/IsValidSrc(datum/D)
@@ -1570,7 +1593,7 @@ GLOBAL_DATUM_INIT(dview_mob, /mob/dview, new)
/proc/blood_sucking_checks(var/mob/living/carbon/target, check_neck, check_blood)
//Bypass this if the target isnt carbon.
if(!iscarbon(target))
return TRUE
return TRUE
if(check_neck)
if(istype(target.get_item_by_slot(SLOT_NECK), /obj/item/clothing/neck/garlic_necklace))
return FALSE
+4 -23
View File
@@ -32,31 +32,12 @@
#endif
//Update this whenever you need to take advantage of more recent byond features
#define MIN_COMPILER_VERSION 512
#if DM_VERSION < MIN_COMPILER_VERSION
#define MIN_COMPILER_VERSION 513
#define MIN_COMPILER_BUILD 1508
#if DM_VERSION < MIN_COMPILER_VERSION || DM_BUILD < MIN_COMPILER_BUILD
//Don't forget to update this part
#error Your version of BYOND is too out-of-date to compile this project. Go to https://secure.byond.com/download and update.
#error You need version 512 or higher
#endif
//Compatability -- These procs were added in 513.1493, not 513.1490
//Which really shoulda bumped us up to 514 right then and there but instead Lummox is a dumb dumb
#if DM_BUILD < 1493
#define length_char(args...) length(args)
#define text2ascii_char(args...) text2ascii(args)
#define copytext_char(args...) copytext(args)
#define splittext_char(args...) splittext(args)
#define spantext_char(args...) spantext(args)
#define nonspantext_char(args...) nonspantext(args)
#define findtext_char(args...) findtext(args)
#define findtextEx_char(args...) findtextEx(args)
#define findlasttext_char(args...) findlasttext(args)
#define findlasttextEx_char(args...) findlasttextEx(args)
#define replacetext_char(args...) replacetext(args)
#define replacetextEx_char(args...) replacetextEx(args)
// /regex procs
#define Find_char(args...) Find(args)
#define Replace_char(args...) Replace(args)
#error You need version 513.1508 or higher
#endif
//Additional code for the above flags.
+20
View File
@@ -265,5 +265,25 @@ GLOBAL_LIST_INIT(bitfields, list(
"STORAGE_LIMIT_MAX_W_CLASS" = STORAGE_LIMIT_MAX_W_CLASS,
"STORAGE_LIMIT_COMBINED_W_CLASS" = STORAGE_LIMIT_COMBINED_W_CLASS,
"STORAGE_LIMIT_VOLUME" = STORAGE_LIMIT_VOLUME
),
"mutantrace_variation" = list(
"STYLE_DIGITIGRADE" = STYLE_DIGITIGRADE,
"STYLE_MUZZLE" = STYLE_MUZZLE,
"STYLE_SNEK_TAURIC" = STYLE_SNEK_TAURIC,
"STYLE_PAW_TAURIC" = STYLE_PAW_TAURIC,
"STYLE_HOOF_TAURIC" = STYLE_HOOF_TAURIC,
"STYLE_NO_ANTHRO_ICON" = STYLE_NO_ANTHRO_ICON,
"USE_SNEK_CLIP_MASK" = USE_SNEK_CLIP_MASK,
"USE_QUADRUPED_CLIP_MASK" = USE_QUADRUPED_CLIP_MASK
),
"vis_flags" = list(
"VIS_INHERIT_ICON" = VIS_INHERIT_ICON,
"VIS_INHERIT_ICON_STATE" = VIS_INHERIT_ICON_STATE,
"VIS_INHERIT_DIR" = VIS_INHERIT_DIR,
"VIS_INHERIT_LAYER" = VIS_INHERIT_LAYER,
"VIS_INHERIT_PLANE" = VIS_INHERIT_PLANE,
"VIS_INHERIT_ID" = VIS_INHERIT_ID,
"VIS_UNDERLAY" = VIS_UNDERLAY,
"VIS_HIDE" = VIS_HIDE
)
))
+2 -2
View File
@@ -137,8 +137,8 @@ GLOBAL_LIST_INIT(jumpsuitlist, list(PREF_SUIT, PREF_SKIRT))
#define UPLINK_PEN "Pen" //like a real spy!
GLOBAL_LIST_INIT(uplink_spawn_loc_list, list(UPLINK_PDA, UPLINK_RADIO, UPLINK_PEN))
//Female Uniforms
GLOBAL_LIST_EMPTY(female_clothing_icons)
//List of cached alpha masked icons.
GLOBAL_LIST_EMPTY(alpha_masked_worn_icons)
//radical shit
GLOBAL_LIST_INIT(hit_appends, list("-OOF", "-ACK", "-UGH", "-HRNK", "-HURGH", "-GLORF"))
@@ -115,5 +115,6 @@ GLOBAL_LIST_INIT(maintenance_loot, list(
/obj/item/autosurgeon/penis = 1,
/obj/item/autosurgeon/testicles = 1,
/obj/item/storage/box/marshmallow = 2,
/obj/item/clothing/gloves/tackler/offbrand = 1,
"" = 3
))
+5
View File
@@ -49,3 +49,8 @@ GLOBAL_LIST_EMPTY_TYPED(areas_by_type, /area)
GLOBAL_LIST_EMPTY(all_abstract_markers)
GLOBAL_LIST_EMPTY(stationroom_landmarks) //List of all spawns for stationrooms
///Away missions, VR, random z levels stuff.
GLOBAL_LIST_EMPTY(random_zlevels_generated)
GLOBAL_LIST_INIT(potential_away_levels, generateMapList(filename = "[global.config.directory]/awaymissionconfig.txt"))
GLOBAL_LIST_INIT(potential_vr_levels, generateMapList(filename = "[global.config.directory]/vr_config.txt"))
+15 -4
View File
@@ -43,15 +43,26 @@ GLOBAL_LIST_EMPTY(mob_config_movespeed_type_lookup)
GLOBAL_LIST_EMPTY(latejoiners) //CIT CHANGE - All latejoining people, for traitor-target purposes.
/proc/update_config_movespeed_type_lookup(update_mobs = TRUE)
var/list/mob_types = list()
// NOTE: This is entirely based on the fact that byond typesof/subtypesof gets longer/deeper paths before shallower ones.
// If that ever breaks this entire proc breaks.
var/list/mob_types = typesof(/mob)
var/list/entry_value = CONFIG_GET(keyed_list/multiplicative_movespeed)
var/list/configured_types = list()
for(var/path in entry_value)
var/value = entry_value[path]
if(!value)
if(isnull(value))
continue
// associative list sets for elements that already exist preserve order
mob_types[path] = value
// now go back up through it to set everything, making absolute sure that base paths are overridden by child paths all the way down the path tree.
for(var/i in length(mob_types) to 1 step -1)
var/path = mob_types[i]
if(isnull(mob_types[path]))
continue
// we're going from bottom to top so it should be safe to do this without further checks..
for(var/subpath in typesof(path))
mob_types[subpath] = value
GLOB.mob_config_movespeed_type_lookup = mob_types
configured_types[subpath] = mob_types[path]
GLOB.mob_config_movespeed_type_lookup = configured_types
if(update_mobs)
update_mob_config_movespeeds()
+2
View File
@@ -33,3 +33,5 @@ GLOBAL_VAR(bible_icon_state)
GLOBAL_VAR(bible_item_state)
GLOBAL_VAR(holy_weapon_type)
GLOBAL_VAR(holy_armor_type)
GLOBAL_VAR_INIT(internal_tick_usage, 0.2 * world.tick_lag)
+138
View File
@@ -0,0 +1,138 @@
/*
FUN ZONE OF ADMIN LISTINGS
Try to keep this in sync with __DEFINES/traits.dm
quirks have it's own panel so we don't need them here.
*/
GLOBAL_LIST_INIT(traits_by_type, list(
/mob = list(
"TRAIT_BLIND" = TRAIT_BLIND,
"TRAIT_MUTE" = TRAIT_MUTE,
"TRAIT_EMOTEMUTE " = TRAIT_EMOTEMUTE,
"TRAIT_DEAF" = TRAIT_DEAF,
"TRAIT_NEARSIGHT" = TRAIT_NEARSIGHT,
"TRAIT_FAT" = TRAIT_FAT,
"TRAIT_HUSK" = TRAIT_HUSK,
"TRAIT_NOCLONE" = TRAIT_NOCLONE,
"TRAIT_CLUMSY" = TRAIT_CLUMSY,
"TRAIT_CHUNKYFINGERS" = TRAIT_CHUNKYFINGERS,
"TRAIT_DUMB" = TRAIT_DUMB,
"TRAIT_MONKEYLIKE" = TRAIT_MONKEYLIKE,
"TRAIT_PACIFISM" = TRAIT_PACIFISM,
"TRAIT_IGNORESLOWDOWN" = TRAIT_IGNORESLOWDOWN,
"TRAIT_DEATHCOMA" = TRAIT_DEATHCOMA,
"TRAIT_FAKEDEATH" = TRAIT_FAKEDEATH,
"TRAIT_DISFIGURED" = TRAIT_DISFIGURED,
"TRAIT_XENO_HOST" = TRAIT_XENO_HOST,
"TRAIT_STUNIMMUNE" = TRAIT_STUNIMMUNE,
"TRAIT_TASED_RESISTANCE" = TRAIT_TASED_RESISTANCE,
"TRAIT_SLEEPIMMUNE" = TRAIT_SLEEPIMMUNE,
"TRAIT_PUSHIMMUNE" = TRAIT_PUSHIMMUNE,
"TRAIT_SHOCKIMMUNE" = TRAIT_SHOCKIMMUNE,
"TRAIT_STABLEHEART" = TRAIT_STABLEHEART,
"TRAIT_STABLELIVER" = TRAIT_STABLELIVER,
"TRAIT_RESISTHEAT" = TRAIT_RESISTHEAT,
"TRAIT_RESISTHEATHANDS" = TRAIT_RESISTHEATHANDS,
"TRAIT_RESISTCOLD" = TRAIT_RESISTCOLD,
"TRAIT_RESISTHIGHPRESSURE" = TRAIT_RESISTHIGHPRESSURE,
"TRAIT_RESISTLOWPRESSURE" = TRAIT_RESISTLOWPRESSURE,
"TRAIT_RADIMMUNE" = TRAIT_RADIMMUNE,
"TRAIT_VIRUSIMMUNE" = TRAIT_VIRUSIMMUNE,
"TRAIT_PIERCEIMMUNE" = TRAIT_PIERCEIMMUNE,
"TRAIT_NODISMEMBER" = TRAIT_NODISMEMBER,
"TRAIT_NOFIRE" = TRAIT_NOFIRE,
"TRAIT_NOGUNS" = TRAIT_NOGUNS,
"TRAIT_NOHUNGER" = TRAIT_NOHUNGER,
"TRAIT_EASYDISMEMBER" = TRAIT_EASYDISMEMBER,
"TRAIT_LIMBATTACHMENT" = TRAIT_LIMBATTACHMENT,
"TRAIT_NOLIMBDISABLE" = TRAIT_NOLIMBDISABLE,
"TRAIT_EASYLIMBDISABLE" = TRAIT_EASYLIMBDISABLE,
"TRAIT_TOXINLOVER" = TRAIT_TOXINLOVER,
"TRAIT_NOBREATH" = TRAIT_NOBREATH,
"TRAIT_ANTIMAGIC" = TRAIT_ANTIMAGIC,
"TRAIT_HOLY" = TRAIT_HOLY,
"TRAIT_DEPRESSION" = TRAIT_DEPRESSION,
"TRAIT_JOLLY" = TRAIT_JOLLY,
"TRAIT_NOCRITDAMAGE" = TRAIT_NOCRITDAMAGE,
"TRAIT_NOSLIPWATER" = TRAIT_NOSLIPWATER,
"TRAIT_NOSLIPALL" = TRAIT_NOSLIPALL,
"TRAIT_NODEATH" = TRAIT_NODEATH,
"TRAIT_NOHARDCRIT" = TRAIT_NOHARDCRIT,
"TRAIT_NOSOFTCRIT" = TRAIT_NOSOFTCRIT,
"TRAIT_MINDSHIELD" = TRAIT_MINDSHIELD,
"TRAIT_HIJACKER" = TRAIT_HIJACKER,
"TRAIT_DISSECTED" = TRAIT_DISSECTED,
"TRAIT_SIXTHSENSE" = TRAIT_SIXTHSENSE,
"TRAIT_FEARLESS" = TRAIT_FEARLESS,
"TRAIT_PARALYSIS_L_ARM" = TRAIT_PARALYSIS_L_ARM,
"TRAIT_PARALYSIS_R_ARM" = TRAIT_PARALYSIS_R_ARM,
"TRAIT_PARALYSIS_L_LEG" = TRAIT_PARALYSIS_L_LEG,
"TRAIT_PARALYSIS_R_LEG" = TRAIT_PARALYSIS_R_LEG,
"TRAIT_DISK_VERIFIER" = TRAIT_DISK_VERIFIER,
"TRAIT_XRAY_VISION" = TRAIT_XRAY_VISION,
"TRAIT_THERMAL_VISION" = TRAIT_THERMAL_VISION,
"TRAIT_ABDUCTOR_TRAINING" = TRAIT_ABDUCTOR_TRAINING,
"TRAIT_ABDUCTOR_SCIENTIST_TRAINING" = TRAIT_ABDUCTOR_SCIENTIST_TRAINING,
"TRAIT_SURGEON" = TRAIT_SURGEON,
"TRAIT_STRONG_GRABBER" = TRAIT_STRONG_GRABBER,
"TRAIT_MAGIC_CHOKE" = TRAIT_MAGIC_CHOKE,
"TRAIT_SOOTHED_THROAT" = TRAIT_SOOTHED_THROAT,
"TRAIT_LAW_ENFORCEMENT_METABOLISM" = TRAIT_LAW_ENFORCEMENT_METABOLISM,
"TRAIT_UNINTELLIGIBLE_SPEECH" = TRAIT_UNINTELLIGIBLE_SPEECH,
"TRAIT_UNSTABLE" = TRAIT_UNSTABLE,
"TRAIT_COLDBLOODED" = TRAIT_COLDBLOODED,
"TRAIT_NONATURALHEAL" = TRAIT_NONATURALHEAL,
"TRAIT_NORUNNING" = TRAIT_NORUNNING,
"TRAIT_NOMARROW" = TRAIT_NOMARROW,
"TRAIT_NOPULSE" = TRAIT_NOPULSE,
"TRAIT_EXEMPT_HEALTH_EVENTS" = TRAIT_EXEMPT_HEALTH_EVENTS,
"TRAIT_NO_MIDROUND_ANTAG" = TRAIT_NO_MIDROUND_ANTAG,
"TRAIT_PUGILIST" = TRAIT_PUGILIST,
"TRAIT_KI_VAMPIRE" = TRAIT_KI_VAMPIRE,
"TRAIT_PASSTABLE" = TRAIT_PASSTABLE,
"TRAIT_GIANT" = TRAIT_GIANT,
"TRAIT_DWARF" = TRAIT_DWARF,
"TRAIT_COMBAT_MODE_LOCKED" = TRAIT_COMBAT_MODE_LOCKED,
"TRAIT_SPRINT_LOCKED" = TRAIT_SPRINT_LOCKED,
"TRAIT_AUTO_CATCH_ITEM" = TRAIT_AUTO_CATCH_ITEM,
"TRAIT_FREESPRINT" = TRAIT_FREESPRINT,
"TRAIT_NO_INTERNALS" = TRAIT_NO_INTERNALS,
"TRAIT_NO_ALCOHOL" = TRAIT_NO_ALCOHOL,
"TRAIT_MUTATION_STASIS" = TRAIT_MUTATION_STASIS,
"TRAIT_HEAVY_SLEEPER" = TRAIT_HEAVY_SLEEPER,
"TRAIT_LIGHT_STEP" = TRAIT_LIGHT_STEP,
"TRAIT_SILENT_STEP" = TRAIT_SILENT_STEP,
"TRAIT_VORACIOUS" = TRAIT_VORACIOUS,
"TRAIT_SELF_AWARE" = TRAIT_SELF_AWARE,
"TRAIT_FREERUNNING" = TRAIT_FREERUNNING,
"TRAIT_SKITTISH" = TRAIT_SKITTISH,
"TRAIT_POOR_AIM" = TRAIT_POOR_AIM,
"TRAIT_PROSOPAGNOSIA" = TRAIT_PROSOPAGNOSIA,
"TRAIT_DRUNK_HEALING" = TRAIT_DRUNK_HEALING,
"TRAIT_TAGGER" = TRAIT_TAGGER,
"TRAIT_PHOTOGRAPHER" = TRAIT_PHOTOGRAPHER,
"TRAIT_MUSICIAN" = TRAIT_MUSICIAN,
"TRAIT_MASO" = TRAIT_MASO,
"TRAIT_HIGH_BLOOD" = TRAIT_HIGH_BLOOD,
"TRAIT_EMPATH" = TRAIT_EMPATH,
"TRAIT_FRIENDLY" = TRAIT_FRIENDLY
),
/obj/item/bodypart = list(
"TRAIT_PARALYSIS" = TRAIT_PARALYSIS
),
/obj/item = list(
"TRAIT_NODROP" = TRAIT_NODROP,
"TRAIT_NO_TELEPORT" = TRAIT_NO_TELEPORT
)
))
/// value -> trait name, generated on use from trait_by_type global
GLOBAL_LIST(trait_name_map)
/proc/generate_trait_name_map()
. = list()
for(var/key in GLOB.traits_by_type)
for(var/tname in GLOB.traits_by_type[key])
var/val = GLOB.traits_by_type[key][tname]
.[val] = tname
+3
View File
@@ -75,6 +75,9 @@
if(notransform)
return
if(SEND_SIGNAL(src, COMSIG_MOB_CLICKON, A, params) & COMSIG_MOB_CANCEL_CLICKON)
return
var/list/modifiers = params2list(params)
if(modifiers["shift"] && modifiers["middle"])
ShiftMiddleClickOn(A)
+1 -1
View File
@@ -162,7 +162,7 @@
#define ui_ghost_orbit "SOUTH:6,CENTER-1:24"
#define ui_ghost_reenter_corpse "SOUTH:6,CENTER:24"
#define ui_ghost_teleport "SOUTH:6,CENTER+1:24"
#define ui_ghost_pai "SOUTH: 6, CENTER+2:24"
#define ui_ghost_spawners "SOUTH: 6, CENTER+2:24"
//UI position overrides for 1:1 screen layout. (default is 7:5)
+7 -7
View File
@@ -36,13 +36,13 @@
var/mob/dead/observer/G = usr
G.dead_tele()
/obj/screen/ghost/pai
name = "pAI Candidate"
icon_state = "pai"
/obj/screen/ghost/spawners
name = "Ghost role spawners"
icon_state = "spawners"
/obj/screen/ghost/pai/Click()
/obj/screen/ghost/spawners/Click()
var/mob/dead/observer/G = usr
G.register_pai()
G.open_spawners_menu()
/datum/hud/ghost/New(mob/owner)
..()
@@ -68,8 +68,8 @@
using.hud = src
static_inventory += using
using = new /obj/screen/ghost/pai()
using.screen_loc = ui_ghost_pai
using = new /obj/screen/ghost/spawners()
using.screen_loc = ui_ghost_spawners
using.hud = src
static_inventory += using
+2 -2
View File
@@ -102,8 +102,8 @@
add_overlay(standard_background)
/obj/screen/movable/pic_in_pic/proc/set_view_size(width, height, do_refresh = TRUE)
width = CLAMP(width, 0, max_dimensions)
height = CLAMP(height, 0, max_dimensions)
width = clamp(width, 0, max_dimensions)
height = clamp(height, 0, max_dimensions)
src.width = width
src.height = height
+3 -3
View File
@@ -19,7 +19,7 @@
///Things rendered on "openspace"; holes in multi-z
/obj/screen/plane_master/openspace
name = "open space plane master"
plane = FLOOR_OPENSPACE_PLANE
plane = OPENSPACE_BACKDROP_PLANE
appearance_flags = PLANE_MASTER
blend_mode = BLEND_MULTIPLY
alpha = 255
@@ -106,8 +106,8 @@
*
* You really shouldn't be directly using this, use atom helpers instead
*/
/obj/screen/plane_master/emissive_unblockable
name = "emissive mob plane master"
/obj/screen/plane_master/emissive_blocker
name = "emissive blocker plane master"
plane = EMISSIVE_BLOCKER_PLANE
mouse_opacity = MOUSE_OPACITY_TRANSPARENT
render_target = EMISSIVE_BLOCKER_RENDER_TARGET
+10 -1
View File
@@ -255,6 +255,7 @@ GLOBAL_LIST_EMPTY(radial_menus)
current_user = M.client
//Blank
menu_holder = image(icon='icons/effects/effects.dmi',loc=anchor,icon_state="nothing",layer = ABOVE_HUD_LAYER)
menu_holder.plane = ABOVE_HUD_PLANE
menu_holder.appearance_flags |= KEEP_APART
menu_holder.vis_contents += elements + close_button
current_user.images += menu_holder
@@ -285,13 +286,16 @@ GLOBAL_LIST_EMPTY(radial_menus)
Choices should be a list where list keys are movables or text used for element names and return value
and list values are movables/icons/images used for element icons
*/
/proc/show_radial_menu(mob/user, atom/anchor, list/choices, uniqueid, radius, datum/callback/custom_check, require_near = FALSE, tooltips = FALSE)
/proc/show_radial_menu(mob/user, atom/anchor, list/choices, uniqueid, radius, datum/callback/custom_check, require_near = FALSE, tooltips = FALSE, no_repeat_close = FALSE)
if(!user || !anchor || !length(choices))
return
if(!uniqueid)
uniqueid = "defmenu_[REF(user)]_[REF(anchor)]"
if(GLOB.radial_menus[uniqueid])
if(!no_repeat_close)
var/datum/radial_menu/menu = GLOB.radial_menus[uniqueid]
menu.finished = TRUE
return
var/datum/radial_menu/menu = new
@@ -308,4 +312,9 @@ GLOBAL_LIST_EMPTY(radial_menus)
var/answer = menu.selected_choice
qdel(menu)
GLOB.radial_menus -= uniqueid
if(require_near && !in_range(anchor, user))
return
if(istype(custom_check))
if(!custom_check.Invoke())
return
return answer
+58 -22
View File
@@ -91,7 +91,7 @@
log_combat(user, M, "attacked", src.name, "(INTENT: [uppertext(user.a_intent)]) (DAMTYPE: [uppertext(damtype)])")
add_fingerprint(user)
user.adjustStaminaLossBuffered(getweight()*0.8)//CIT CHANGE - makes attacking things cause stamina loss
user.adjustStaminaLossBuffered(getweight(user, STAM_COST_ATTACK_MOB_MULT))//CIT CHANGE - makes attacking things cause stamina loss
//the equivalent of the standard version of attack() but for object targets.
/obj/item/proc/attack_obj(obj/O, mob/living/user)
@@ -102,7 +102,7 @@
if(IS_STAMCRIT(user)) // CIT CHANGE - makes it impossible to attack in stamina softcrit
to_chat(user, "<span class='warning'>You're too exhausted.</span>") // CIT CHANGE - ditto
return // CIT CHANGE - ditto
user.adjustStaminaLossBuffered(getweight()*1.2)//CIT CHANGE - makes attacking things cause stamina loss
user.adjustStaminaLossBuffered(getweight(user, STAM_COST_ATTACK_OBJ_MULT))//CIT CHANGE - makes attacking things cause stamina loss
user.changeNext_move(CLICK_CD_MELEE)
user.do_attack_animation(O)
O.attacked_by(src, user)
@@ -111,26 +111,32 @@
return
/obj/attacked_by(obj/item/I, mob/living/user)
if(I.force)
var/totitemdamage = I.force
var/bad_flag = NONE
if(!(user.combat_flags & COMBAT_FLAG_COMBAT_ACTIVE) && iscarbon(user))
totitemdamage *= 0.5
bad_flag |= SKILL_COMBAT_MODE //blacklist combat skills.
if(I.used_skills && user.mind)
if(totitemdamage)
totitemdamage = user.mind.skill_holder.item_action_skills_mod(I, totitemdamage, I.skill_difficulty, SKILL_ATTACK_OBJ, bad_flag)
for(var/skill in I.used_skills)
if(!(I.used_skills[skill] & SKILL_TRAIN_ATTACK_OBJ))
continue
user.mind.skill_holder.auto_gain_experience(skill, I.skill_gain)
if(totitemdamage)
visible_message("<span class='danger'>[user] has hit [src] with [I]!</span>", null, null, COMBAT_MESSAGE_RANGE)
//only witnesses close by and the victim see a hit message.
log_combat(user, src, "attacked", I)
take_damage(I.force, I.damtype, "melee", 1)
take_damage(totitemdamage, I.damtype, "melee", 1)
/mob/living/attacked_by(obj/item/I, mob/living/user)
//CIT CHANGES START HERE - combatmode and resting checks
var/totitemdamage = I.force
if(!(user.combat_flags & COMBAT_FLAG_COMBAT_ACTIVE))
totitemdamage *= 0.5
if(!CHECK_MOBILITY(user, MOBILITY_STAND))
totitemdamage *= 0.5
//CIT CHANGES END HERE
if((user != src) && run_block(I, totitemdamage, "the [I.name]", ATTACK_TYPE_MELEE, I.armour_penetration, user) & BLOCK_SUCCESS)
var/totitemdamage = pre_attacked_by(I, user)
if((user != src) && mob_run_block(I, totitemdamage, "the [I.name]", ATTACK_TYPE_MELEE, I.armour_penetration, user, null, null) & BLOCK_SUCCESS)
return FALSE
send_item_attack_message(I, user)
I.do_stagger_action(src, user)
I.do_stagger_action(src, user, totitemdamage)
if(I.force)
apply_damage(totitemdamage, I.damtype) //CIT CHANGE - replaces I.force with totitemdamage
apply_damage(totitemdamage, I.damtype)
if(I.damtype == BRUTE)
if(prob(33))
I.add_mob_blood(src)
@@ -146,6 +152,28 @@
else
return ..()
/mob/living/proc/pre_attacked_by(obj/item/I, mob/living/user)
. = I.force
var/bad_flag = NONE
if(!(user.combat_flags & COMBAT_FLAG_COMBAT_ACTIVE) && iscarbon(user))
. *= 0.5
bad_flag |= SKILL_COMBAT_MODE //blacklist combat skills.
if(!CHECK_MOBILITY(user, MOBILITY_STAND))
. *= 0.5
if(!user.mind || !I.used_skills)
return
if(.)
. = user.mind.skill_holder.item_action_skills_mod(I, ., I.skill_difficulty, SKILL_ATTACK_MOB, bad_flag)
for(var/skill in I.used_skills)
if(!(I.used_skills[skill] & SKILL_TRAIN_ATTACK_MOB))
continue
user.mind.skill_holder.auto_gain_experience(skill, I.skill_gain)
/mob/living/carbon/pre_attacked_by(obj/item/I, mob/living/user)
. = ..()
if(!(combat_flags & COMBAT_FLAG_COMBAT_ACTIVE))
. *= 1.5
// Proximity_flag is 1 if this afterattack was called on something adjacent, in your square, or on your person.
// Click parameters is the params string from byond Click() code, see that documentation.
/obj/item/proc/afterattack(atom/target, mob/user, proximity_flag, click_parameters)
@@ -155,9 +183,9 @@
/obj/item/proc/get_clamped_volume()
if(w_class)
if(force)
return CLAMP((force + w_class) * 4, 30, 100)// Add the item's force to its weight class and multiply by 4, then clamp the value between 30 and 100
return clamp((force + w_class) * 4, 30, 100)// Add the item's force to its weight class and multiply by 4, then clamp the value between 30 and 100
else
return CLAMP(w_class * 6, 10, 100) // Multiply the item's weight class by 6, then clamp the value between 10 and 100
return clamp(w_class * 6, 10, 100) // Multiply the item's weight class by 6, then clamp the value between 10 and 100
/mob/living/proc/send_item_attack_message(obj/item/I, mob/living/user, hit_area)
var/message_verb = "attacked"
@@ -179,22 +207,30 @@
return 1
/// How much stamina this takes to swing this is not for realism purposes hecc off.
/obj/item/proc/getweight()
return total_mass || w_class * 1.25
/obj/item/proc/getweight(mob/living/user, multiplier = 1, flags = SKILL_STAMINA_COST)
. = (total_mass || w_class * STAM_COST_W_CLASS_MULT) * multiplier
if(!user)
return
var/bad_flag = NONE
if(iscarbon(user) && !(user.combat_flags & COMBAT_FLAG_COMBAT_ACTIVE))
. *= STAM_COST_NO_COMBAT_MULT
bad_flag |= SKILL_COMBAT_MODE
if(used_skills && user.mind)
. = user.mind.skill_holder.item_action_skills_mod(src, ., skill_difficulty, flags, bad_flag, FALSE)
/// How long this staggers for. 0 and negatives supported.
/obj/item/proc/melee_stagger_duration()
/obj/item/proc/melee_stagger_duration(force_override)
if(!isnull(stagger_force))
return stagger_force
/// totally not an untested, arbitrary equation.
return clamp((1.5 + (w_class/7.5)) * (force / 2), 0, 10 SECONDS)
return clamp((1.5 + (w_class/7.5)) * ((force_override || force) / 2), 0, 10 SECONDS)
/obj/item/proc/do_stagger_action(mob/living/target, mob/living/user)
/obj/item/proc/do_stagger_action(mob/living/target, mob/living/user, force_override)
if(!CHECK_BITFIELD(target.status_flags, CANSTAGGER))
return FALSE
if(target.combat_flags & COMBAT_FLAG_SPRINT_ACTIVE)
target.do_staggered_animation()
var/duration = melee_stagger_duration()
var/duration = melee_stagger_duration(force_override)
if(!duration) //0
return FALSE
else if(duration > 0)
+1 -1
View File
@@ -5,7 +5,7 @@
return // seems legit.
// Things you might plausibly want to follow
if(ismovableatom(A))
if(ismovable(A))
ManualFollow(A)
// Otherwise jump
+9 -3
View File
@@ -3,9 +3,7 @@
name = "Initializing..."
var/target
INITIALIZE_IMMEDIATE(/obj/effect/statclick)
/obj/effect/statclick/Initialize(mapload, text, target) //Don't port this to Initialize it's too critical
/obj/effect/statclick/New(loc, text, target) //Don't port this to Initialize it's too critical
. = ..()
name = text
src.target = target
@@ -33,6 +31,14 @@ INITIALIZE_IMMEDIATE(/obj/effect/statclick)
usr.client.debug_variables(target)
message_admins("Admin [key_name_admin(usr)] is debugging the [target] [class].")
/obj/effect/statclick/misc_subsystems/Click()
if(!usr.client.holder)
return
var/subsystem = input(usr, "Debug which subsystem?", "Debug nonprocessing subsystem") as null|anything in (Master.subsystems - Master.statworthy_subsystems)
if(!subsystem)
return
usr.client.debug_variables(subsystem)
message_admins("Admin [key_name_admin(usr)] is debugging the [subsystem] subsystem.")
// Debug verbs.
/client/proc/restart_controller(controller in list("Master", "Failsafe"))
@@ -103,7 +103,7 @@
return FALSE
var/temp = text2num(trim(str_val))
if(!isnull(temp))
config_entry_value = CLAMP(integer ? round(temp) : temp, min_val, max_val)
config_entry_value = clamp(integer ? round(temp) : temp, min_val, max_val)
if(config_entry_value != temp && !(datum_flags & DF_VAR_EDITED))
log_config("Changing [name] from [temp] to [config_entry_value]!")
return TRUE
@@ -35,6 +35,13 @@
/datum/config_entry/keyed_list/midround_antag/ValidateListEntry(key_name, key_value)
return key_name in config.modes
/datum/config_entry/keyed_list/force_antag_count
key_mode = KEY_MODE_TEXT
value_mode = VALUE_MODE_FLAG
/datum/config_entry/keyed_list/force_antag_count/ValidateListEntry(key_name, key_value)
return key_name in config.modes
/datum/config_entry/keyed_list/policy
key_mode = KEY_MODE_TEXT
value_mode = VALUE_MODE_TEXT
@@ -217,7 +224,8 @@
config_entry_value = list( //DEFAULTS
/mob/living/simple_animal = 1,
/mob/living/silicon/pai = 1,
/mob/living/carbon/alien/humanoid/hunter = -1,
/mob/living/carbon/alien/humanoid/sentinel = 0.25,
/mob/living/carbon/alien/humanoid/drone = 0.5,
/mob/living/carbon/alien/humanoid/royal/praetorian = 1,
/mob/living/carbon/alien/humanoid/royal/queen = 3
)
@@ -248,8 +256,18 @@
/datum/config_entry/number/movedelay/run_delay
/datum/config_entry/number/movedelay/run_delay/ValidateAndSet()
. = ..()
var/datum/movespeed_modifier/config_walk_run/M = get_cached_movespeed_modifier(/datum/movespeed_modifier/config_walk_run/run)
M.sync()
/datum/config_entry/number/movedelay/walk_delay
/datum/config_entry/number/movedelay/walk_delay/ValidateAndSet()
. = ..()
var/datum/movespeed_modifier/config_walk_run/M = get_cached_movespeed_modifier(/datum/movespeed_modifier/config_walk_run/walk)
M.sync()
/datum/config_entry/number/movedelay/sprint_speed_increase
config_entry_value = 1
@@ -288,6 +306,8 @@
/datum/config_entry/flag/roundstart_away //Will random away mission be loaded.
/datum/config_entry/flag/roundstart_vr //Will virtual reality missions be loaded?
/datum/config_entry/number/gateway_delay //How long the gateway takes before it activates. Default is half an hour. Only matters if roundstart_away is enabled.
config_entry_value = 18000
min_val = 0
@@ -335,6 +355,11 @@
config_entry_value = 16
min_val = 0
/datum/config_entry/number/icemoon_budget
config_entry_value = 90
integer = FALSE
min_val = 0
/datum/config_entry/number/station_space_budget
config_entry_value = 10
min_val = 0
@@ -455,10 +480,12 @@
config_entry_value = RESIZE_DEFAULT_SIZE
min_val = 0.1 //to avoid issues with zeros and negative values.
max_val = RESIZE_DEFAULT_SIZE
integer = FALSE
/datum/config_entry/number/body_size_max
config_entry_value = RESIZE_DEFAULT_SIZE
min_val = RESIZE_DEFAULT_SIZE
integer = FALSE
//Pun-Pun movement slowdown given to characters with a body size smaller than this value,
//to compensate for their smaller hitbox.
@@ -467,13 +494,14 @@
config_entry_value = RESIZE_DEFAULT_SIZE * 0.85
min_val = 0
max_val = RESIZE_DEFAULT_SIZE
integer = FALSE
//multiplicative slowdown multiplier. See 'dna.update_body_size' for the operation.
//doesn't apply to floating or crawling mobs
/datum/config_entry/number/body_size_slowdown_multiplier
config_entry_value = 0.25
min_val = 0.1 //To encourage folks to disable the slowdown through the above config instead.
integer = FALSE
//Allows players to set a hexadecimal color of their choice as skin tone, on top of the standard ones.
/datum/config_entry/number/allow_custom_skintones
config_entry_value = 1
/datum/config_entry/flag/allow_custom_skintones
+38 -11
View File
@@ -28,6 +28,8 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
// List of subsystems to process().
var/list/subsystems
/// List of subsystems to include in the MC stat panel.
var/list/statworthy_subsystems
// Vars for keeping track of tick drift.
var/init_timeofday
@@ -36,6 +38,9 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
var/sleep_delta = 1
///Only run ticker subsystems for the next n ticks.
var/skip_ticks = 0
var/make_runtime = 0
var/initializations_finished_with_no_players_logged_in //I wonder what this could be?
@@ -62,6 +67,9 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
//used by CHECK_TICK as well so that the procs subsystems call can obey that SS's tick limits
var/static/current_ticklimit = TICK_LIMIT_RUNNING
/// Statclick for misc subsystems
var/obj/effect/statclick/misc_subsystems/misc_statclick
/datum/controller/master/New()
if(!config)
config = new
@@ -84,6 +92,11 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
_subsystems += new I
Master = src
// We want to see all subsystems during init.
statworthy_subsystems = subsystems.Copy()
misc_statclick = new(null, "Debug")
if(!GLOB)
new /datum/controller/global_vars
@@ -254,10 +267,14 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
var/list/tickersubsystems = list()
var/list/runlevel_sorted_subsystems = list(list()) //ensure we always have at least one runlevel
var/timer = world.time
statworthy_subsystems = list()
for (var/thing in subsystems)
var/datum/controller/subsystem/SS = thing
if (SS.flags & SS_NO_FIRE)
if(SS.flags & SS_ALWAYS_SHOW_STAT)
statworthy_subsystems += SS
continue
statworthy_subsystems += SS
SS.queued_time = 0
SS.queue_next = null
SS.queue_prev = null
@@ -335,7 +352,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
new/datum/controller/failsafe() // (re)Start the failsafe.
//now do the actual stuff
if (!queue_head || !(iteration % 3))
if (!skip_ticks)
var/checking_runlevel = current_runlevel
if(cached_runlevel != checking_runlevel)
//resechedule subsystems
@@ -381,6 +398,8 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
iteration++
last_run = world.time
if (skip_ticks)
skip_ticks--
src.sleep_delta = MC_AVERAGE_FAST(src.sleep_delta, sleep_delta)
current_ticklimit = TICK_LIMIT_RUNNING
if (processing * sleep_delta <= world.tick_lag)
@@ -444,10 +463,12 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
while (queue_node)
if (ran && TICK_USAGE > TICK_LIMIT_RUNNING)
break
queue_node_flags = queue_node.flags
queue_node_priority = queue_node.queued_priority
if (!(queue_node_flags & SS_TICKER) && skip_ticks)
queue_node = queue_node.queue_next
continue
//super special case, subsystems where we can't make them pause mid way through
//if we can't run them this tick (without going over a tick)
//we bump up their priority and attempt to run them next tick
@@ -455,14 +476,15 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
// in those cases, so we just let them run)
if (queue_node_flags & SS_NO_TICK_CHECK)
if (queue_node.tick_usage > TICK_LIMIT_RUNNING - TICK_USAGE && ran_non_ticker)
queue_node.queued_priority += queue_priority_count * 0.1
queue_priority_count -= queue_node_priority
queue_priority_count += queue_node.queued_priority
current_tick_budget -= queue_node_priority
queue_node = queue_node.queue_next
if (!(queue_node_flags & SS_BACKGROUND))
queue_node.queued_priority += queue_priority_count * 0.1
queue_priority_count -= queue_node_priority
queue_priority_count += queue_node.queued_priority
current_tick_budget -= queue_node_priority
queue_node = queue_node.queue_next
continue
if ((queue_node_flags & SS_BACKGROUND) && !bg_calc)
if (!bg_calc && (queue_node_flags & SS_BACKGROUND))
current_tick_budget = queue_priority_count_bg
bg_calc = TRUE
@@ -515,7 +537,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
queue_node.paused_ticks = 0
queue_node.paused_tick_usage = 0
if (queue_node_flags & SS_BACKGROUND) //update our running total
if (bg_calc) //update our running total
queue_priority_count_bg -= queue_node_priority
else
queue_priority_count -= queue_node_priority
@@ -583,14 +605,19 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
log_world("MC: SoftReset: Finished.")
. = 1
/// Warns us that the end of tick byond map_update will be laggier then normal, so that we can just skip running subsystems this tick.
/datum/controller/master/proc/laggy_byond_map_update_incoming()
if (!skip_ticks)
skip_ticks = 1
/datum/controller/master/stat_entry()
if(!statclick)
statclick = new/obj/effect/statclick/debug(null, "Initializing...", src)
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)]%))")
stat("Master Controller:", statclick.update("(TickRate:[Master.processing]) (Iteration:[Master.iteration])"))
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
+20 -12
View File
@@ -1,11 +1,3 @@
#define SSAIR_PIPENETS 1
#define SSAIR_ATMOSMACHINERY 2
#define SSAIR_REACTQUEUE 3
#define SSAIR_EXCITEDGROUPS 4
#define SSAIR_HIGHPRESSURE 5
#define SSAIR_HOTSPOTS 6
#define SSAIR_SUPERCONDUCTIVITY 7
SUBSYSTEM_DEF(air)
name = "Atmospherics"
init_order = INIT_ORDER_AIR
@@ -20,6 +12,7 @@ SUBSYSTEM_DEF(air)
var/cost_hotspots = 0
var/cost_superconductivity = 0
var/cost_pipenets = 0
var/cost_rebuilds = 0
var/cost_atmos_machinery = 0
var/list/excited_groups = list()
@@ -27,6 +20,7 @@ SUBSYSTEM_DEF(air)
var/list/turf_react_queue = list()
var/list/hotspots = list()
var/list/networks = list()
var/list/pipenets_needing_rebuilt = list()
var/list/obj/machinery/atmos_machinery = list()
var/list/pipe_init_dirs_cache = list()
@@ -39,7 +33,7 @@ SUBSYSTEM_DEF(air)
var/list/currentrun = list()
var/currentpart = SSAIR_PIPENETS
var/currentpart = SSAIR_REBUILD_PIPENETS
var/map_loading = TRUE
var/list/queued_for_activation
@@ -52,6 +46,7 @@ SUBSYSTEM_DEF(air)
msg += "HS:[round(cost_hotspots,1)]|"
msg += "SC:[round(cost_superconductivity,1)]|"
msg += "PN:[round(cost_pipenets,1)]|"
msg += "RB:[round(cost_rebuilds,1)]|"
msg += "AM:[round(cost_atmos_machinery,1)]"
msg += "} "
msg += "AT:[active_turfs.len]|"
@@ -77,6 +72,18 @@ SUBSYSTEM_DEF(air)
/datum/controller/subsystem/air/fire(resumed = 0)
var/timer = TICK_USAGE_REAL
if(currentpart == SSAIR_REBUILD_PIPENETS)
var/list/pipenet_rebuilds = pipenets_needing_rebuilt
for(var/thing in pipenet_rebuilds)
var/obj/machinery/atmospherics/AT = thing
AT.build_network()
cost_rebuilds = MC_AVERAGE(cost_rebuilds, TICK_DELTA_TO_MS(TICK_USAGE_REAL - timer))
pipenets_needing_rebuilt.Cut()
if(state != SS_RUNNING)
return
resumed = FALSE
currentpart = SSAIR_PIPENETS
if(currentpart == SSAIR_PIPENETS || !resumed)
process_pipenets(resumed)
cost_pipenets = MC_AVERAGE(cost_pipenets, TICK_DELTA_TO_MS(TICK_USAGE_REAL - timer))
@@ -137,9 +144,7 @@ SUBSYSTEM_DEF(air)
if(state != SS_RUNNING)
return
resumed = 0
currentpart = SSAIR_PIPENETS
currentpart = SSAIR_REBUILD_PIPENETS
/datum/controller/subsystem/air/proc/process_pipenets(resumed = 0)
if (!resumed)
@@ -156,6 +161,9 @@ SUBSYSTEM_DEF(air)
if(MC_TICK_CHECK)
return
/datum/controller/subsystem/air/proc/add_to_rebuild_queue(atmos_machine)
if(istype(atmos_machine, /obj/machinery/atmospherics))
pipenets_needing_rebuilt += atmos_machine
/datum/controller/subsystem/air/proc/process_atmos_machinery(resumed = 0)
var/seconds = wait * 0.1
-1
View File
@@ -16,7 +16,6 @@ SUBSYSTEM_DEF(atoms)
/datum/controller/subsystem/atoms/Initialize(timeofday)
GLOB.fire_overlay.appearance_flags = RESET_COLOR
setupGenetics() //to set the mutations' sequence.
initialized = INITIALIZATION_INNEW_MAPLOAD
InitializeAtoms()
return ..()
+1 -2
View File
@@ -6,7 +6,6 @@ SUBSYSTEM_DEF(lighting)
name = "Lighting"
wait = 2
init_order = INIT_ORDER_LIGHTING
flags = SS_TICKER
/datum/controller/subsystem/lighting/stat_entry()
..("L:[GLOB.lighting_update_lights.len]|C:[GLOB.lighting_update_corners.len]|O:[GLOB.lighting_update_objects.len]")
@@ -85,4 +84,4 @@ SUBSYSTEM_DEF(lighting)
/datum/controller/subsystem/lighting/Recover()
initialized = SSlighting.initialized
..()
..()
+102 -32
View File
@@ -1,3 +1,5 @@
#define INIT_ANNOUNCE(X) to_chat(world, "<span class='boldannounce'>[X]</span>"); log_world(X)
SUBSYSTEM_DEF(mapping)
name = "Mapping"
init_order = INIT_ORDER_MAPPING
@@ -14,6 +16,8 @@ SUBSYSTEM_DEF(mapping)
var/list/ruins_templates = list()
var/list/space_ruins_templates = list()
var/list/lava_ruins_templates = list()
var/list/ice_ruins_templates = list()
var/list/ice_ruins_underground_templates = list()
var/list/station_ruins_templates = list()
var/datum/space_level/isolated_ruins_z //Created on demand during ruin loading.
@@ -40,6 +44,13 @@ SUBSYSTEM_DEF(mapping)
var/stat_map_name = "Loading..."
/// Lookup list for random generated IDs.
var/list/random_generated_ids_by_original = list()
/// next id for separating obfuscated ids.
var/obfuscation_next_id = 1
/// "secret" key
var/obfuscation_secret
//dlete dis once #39770 is resolved
/datum/controller/subsystem/mapping/proc/HACK_LoadMapConfig()
if(!config)
@@ -50,6 +61,10 @@ SUBSYSTEM_DEF(mapping)
#endif
stat_map_name = config.map_name
/datum/controller/subsystem/mapping/PreInit()
if(!obfuscation_secret)
obfuscation_secret = md5(GUID()) //HAH! Guess this!
/datum/controller/subsystem/mapping/Initialize(timeofday)
HACK_LoadMapConfig()
if(initialized)
@@ -81,25 +96,40 @@ SUBSYSTEM_DEF(mapping)
// Pick a random away mission.
if(CONFIG_GET(flag/roundstart_away))
createRandomZlevel()
// Pick a random VR level.
if(CONFIG_GET(flag/roundstart_vr))
createRandomZlevel(VIRT_REALITY_NAME, list(ZTRAIT_AWAY = TRUE, ZTRAIT_VR = TRUE), GLOB.potential_vr_levels)
// Generate mining ruins
loading_ruins = TRUE
var/list/lava_ruins = levels_by_trait(ZTRAIT_LAVA_RUINS)
if (lava_ruins.len)
seedRuins(lava_ruins, CONFIG_GET(number/lavaland_budget), /area/lavaland/surface/outdoors/unexplored, lava_ruins_templates)
seedRuins(lava_ruins, CONFIG_GET(number/lavaland_budget), list(/area/lavaland/surface/outdoors/unexplored), lava_ruins_templates)
for (var/lava_z in lava_ruins)
spawn_rivers(lava_z)
var/list/ice_ruins = levels_by_trait(ZTRAIT_ICE_RUINS)
if (ice_ruins.len)
// needs to be whitelisted for underground too so place_below ruins work
seedRuins(ice_ruins, CONFIG_GET(number/icemoon_budget), list(/area/icemoon/surface/outdoors/unexplored, /area/icemoon/underground/unexplored), ice_ruins_templates)
for (var/ice_z in ice_ruins)
spawn_rivers(ice_z, 4, /turf/open/openspace/icemoon, /area/icemoon/surface/outdoors/unexplored/rivers)
var/list/ice_ruins_underground = levels_by_trait(ZTRAIT_ICE_RUINS_UNDERGROUND)
if (ice_ruins_underground.len)
seedRuins(ice_ruins_underground, CONFIG_GET(number/icemoon_budget), list(/area/icemoon/underground/unexplored), ice_ruins_underground_templates)
for (var/ice_z in ice_ruins_underground)
spawn_rivers(ice_z, 4, level_trait(ice_z, ZTRAIT_BASETURF), /area/icemoon/underground/unexplored/rivers)
// Generate deep space ruins
var/list/space_ruins = levels_by_trait(ZTRAIT_SPACE_RUINS)
if (space_ruins.len)
seedRuins(space_ruins, CONFIG_GET(number/space_budget), /area/space, space_ruins_templates)
seedRuins(space_ruins, CONFIG_GET(number/space_budget), list(/area/space), space_ruins_templates)
// Generate station space ruins
var/list/station_ruins = levels_by_trait(ZTRAIT_STATION)
if (station_ruins.len)
seedRuins(station_ruins, CONFIG_GET(number/station_space_budget), /area/space/station_ruins, station_ruins_templates)
seedRuins(station_ruins, (SSmapping.config.station_ruin_budget < 0) ? CONFIG_GET(number/station_space_budget) : SSmapping.config.station_ruin_budget, list(/area/space/station_ruins), station_ruins_templates)
SSmapping.seedStation()
loading_ruins = FALSE
#endif
@@ -167,6 +197,8 @@ SUBSYSTEM_DEF(mapping)
ruins_templates = SSmapping.ruins_templates
space_ruins_templates = SSmapping.space_ruins_templates
lava_ruins_templates = SSmapping.lava_ruins_templates
ice_ruins_templates = SSmapping.ice_ruins_templates
ice_ruins_underground_templates = SSmapping.ice_ruins_underground_templates
station_ruins_templates = SSmapping.station_ruins_templates
shuttle_templates = SSmapping.shuttle_templates
shelter_templates = SSmapping.shelter_templates
@@ -181,8 +213,7 @@ SUBSYSTEM_DEF(mapping)
z_list = SSmapping.z_list
#define INIT_ANNOUNCE(X) to_chat(world, "<span class='boldannounce'>[X]</span>"); log_world(X)
/datum/controller/subsystem/mapping/proc/LoadGroup(list/errorList, name, path, files, list/traits, list/default_traits, silent = FALSE)
/datum/controller/subsystem/mapping/proc/LoadGroup(list/errorList, name, path, files, list/traits, list/default_traits, silent = FALSE, orientation = SOUTH)
. = list()
var/start_time = REALTIMEOFDAY
@@ -222,7 +253,7 @@ SUBSYSTEM_DEF(mapping)
// load the maps
for (var/P in parsed_maps)
var/datum/parsed_map/pm = P
if (!pm.load(1, 1, start_z + parsed_maps[P], no_changeturf = TRUE))
if (!pm.load(1, 1, start_z + parsed_maps[P], no_changeturf = TRUE, orientation = orientation))
errorList |= pm.original_path
if(!silent)
INIT_ANNOUNCE("Loaded [name] in [(REALTIMEOFDAY - start_time)/10]s!")
@@ -238,7 +269,7 @@ SUBSYSTEM_DEF(mapping)
// load the station
station_start = world.maxz + 1
INIT_ANNOUNCE("Loading [config.map_name]...")
LoadGroup(FailedZs, "Station", config.map_path, config.map_file, config.traits, ZTRAITS_STATION)
LoadGroup(FailedZs, "Station", config.map_path, config.map_file, config.traits, ZTRAITS_STATION, FALSE, config.orientation)
if(SSdbcore.Connect())
var/datum/DBQuery/query_round_map_name = SSdbcore.NewQuery("UPDATE [format_table_name("round")] SET map_name = '[config.map_name]' WHERE id = [GLOB.round_id]")
@@ -254,7 +285,7 @@ SUBSYSTEM_DEF(mapping)
// load mining
if(config.minetype == "lavaland")
LoadGroup(FailedZs, "Lavaland", "map_files/Mining", "Lavaland.dmm", default_traits = ZTRAITS_LAVALAND)
else if (!isnull(config.minetype))
else if (!isnull(config.minetype) && config.minetype != "none")
INIT_ANNOUNCE("WARNING: An unknown minetype '[config.minetype]' was set! This is being ignored! Update the maploader code!")
#endif
@@ -265,7 +296,6 @@ SUBSYSTEM_DEF(mapping)
msg += ", [FailedZs[I]]"
msg += ". Yell at your server host!"
INIT_ANNOUNCE(msg)
#undef INIT_ANNOUNCE
GLOBAL_LIST_EMPTY(the_station_areas)
@@ -359,6 +389,7 @@ GLOBAL_LIST_EMPTY(the_station_areas)
// Still supporting bans by filename
var/list/banned = generateMapList("[global.config.directory]/lavaruinblacklist.txt")
banned += generateMapList("[global.config.directory]/spaceruinblacklist.txt")
banned += generateMapList("[global.config.directory]/iceruinblacklist.txt")
banned += generateMapList("[global.config.directory]/stationruinblacklist.txt")
for(var/item in sortList(subtypesof(/datum/map_template/ruin), /proc/cmp_ruincost_priority))
@@ -376,6 +407,10 @@ GLOBAL_LIST_EMPTY(the_station_areas)
if(istype(R, /datum/map_template/ruin/lavaland))
lava_ruins_templates[R.name] = R
else if(istype(R, /datum/map_template/ruin/icemoon/underground))
ice_ruins_underground_templates[R.name] = R
else if(istype(R, /datum/map_template/ruin/icemoon))
ice_ruins_templates[R.name] = R
else if(istype(R, /datum/map_template/ruin/space))
space_ruins_templates[R.name] = R
else if(istype(R, /datum/map_template/ruin/station))
@@ -410,46 +445,69 @@ GLOBAL_LIST_EMPTY(the_station_areas)
//Manual loading of away missions.
/client/proc/admin_away()
set name = "Load Away Mission"
set name = "Load Away Mission / Virtual Reality"
set category = "Fun"
if(!holder ||!check_rights(R_FUN))
return
var/choice = alert(src, "What kind of level would you like to load?", "Load Away/VR", AWAY_MISSION_NAME, VIRT_REALITY_NAME, "Cancel")
if(!GLOB.the_gateway)
if(alert("There's no home gateway on the station. You sure you want to continue ?", "Uh oh", "Yes", "No") != "Yes")
var/list/possible_options
var/list/ztraits
switch(choice)
if(VIRT_REALITY_NAME)
possible_options = GLOB.potential_vr_levels
ztraits = list(ZTRAIT_AWAY = TRUE, ZTRAIT_VR = TRUE)
if(AWAY_MISSION_NAME)
if(!GLOB.the_gateway)
if(alert("There's no home gateway on the station. You sure you want to continue ?", "Uh oh", "Yes", "No") != "Yes")
return
possible_options = GLOB.potential_away_levels
ztraits = list(ZTRAIT_AWAY = TRUE)
else
return
var/list/possible_options = GLOB.potentialRandomZlevels + "Custom"
var/away_name
var/datum/space_level/away_level
possible_options += "Custom"
var/lvl_name
var/datum/space_level/level
var/answer = input("What kind ? ","Away") as null|anything in possible_options
var/answer = input("What kind ? ","Away/VR") as null|anything in possible_options
switch(answer)
if(null)
return
if("Custom")
var/mapfile = input("Pick file:", "File") as null|file
if(!mapfile)
return
away_name = "[mapfile] custom"
to_chat(usr,"<span class='notice'>Loading [away_name]...</span>")
var/datum/map_template/template = new(mapfile, "Away Mission")
away_level = template.load_new_z()
lvl_name = "[mapfile] custom"
to_chat(usr,"<span class='notice'>Loading [lvl_name]...</span>")
var/datum/map_template/template = new(mapfile, choice, ztraits)
level = template.load_new_z(ztraits)
else
if(answer in GLOB.potentialRandomZlevels)
away_name = answer
to_chat(usr,"<span class='notice'>Loading [away_name]...</span>")
var/datum/map_template/template = new(away_name, "Away Mission")
away_level = template.load_new_z()
else
return
lvl_name = answer
to_chat(usr,"<span class='notice'>Loading [lvl_name]...</span>")
var/datum/map_template/template = new(lvl_name, choice)
level = template.load_new_z(ztraits)
message_admins("Admin [key_name_admin(usr)] has loaded [away_name] away mission.")
log_admin("Admin [key_name(usr)] has loaded [away_name] away mission.")
if(!away_level)
message_admins("Loading [away_name] failed!")
message_admins("Admin [key_name_admin(usr)] has loaded [lvl_name] [choice].")
log_admin("Admin [key_name(usr)] has loaded [lvl_name] [choice].")
if(!level)
message_admins("Loading [lvl_name] failed!")
return
if(choice == AWAY_MISSION_NAME && GLOB.the_gateway)
//Link any found away gate with station gate
var/obj/machinery/gateway/centeraway/new_gate
for(var/obj/machinery/gateway/centeraway/G in GLOB.machines)
if(G.z == level.z_value) //I'll have to refactor gateway shitcode before multi-away support.
new_gate = G
break
//Link station gate with away gate and remove wait time.
GLOB.the_gateway.awaygate = new_gate
GLOB.the_gateway.wait = world.time
/datum/controller/subsystem/mapping/proc/RequestBlockReservation(width, height, z, type = /datum/turf_reservation, turf_type_override, border_type_override)
UNTIL((!z || reservation_ready["[z]"]) && !clearing_reserved_turfs)
var/datum/turf_reservation/reserve = new type
@@ -543,3 +601,15 @@ GLOBAL_LIST_EMPTY(the_station_areas)
LM.load()
if(GLOB.stationroom_landmarks.len)
seedStation() //I'm sure we can trust everyone not to insert a 1x1 rooms which loads a landmark which loads a landmark which loads a la...
/**
* Generates an obfuscated but constant id for an original id for cases where you don't want players codediving for an id.
* WARNING: MAKE SURE PLAYERS ARE NOT ABLE TO ACCESS THIS. To save performance, it's just secret + an incrementing number. Very guessable if you know what the secret is.
*/
/datum/controller/subsystem/mapping/proc/get_obfuscated_id(original, id_type = "GENERAL")
if(!original)
return //no.
var/key = "[original]%[id_type]"
if(random_generated_ids_by_original[key])
return random_generated_ids_by_original[key]
. = random_generated_ids_by_original[key] = "[obfuscation_secret]%[obfuscation_next_id++]"
@@ -1,25 +0,0 @@
PROCESSING_SUBSYSTEM_DEF(flightpacks)
name = "Flightpack Movement"
priority = FIRE_PRIORITY_FLIGHTPACKS
wait = 2
stat_tag = "FM"
flags = SS_NO_INIT|SS_TICKER|SS_KEEP_TIMING
var/flightsuit_processing = FLIGHTSUIT_PROCESSING_FULL
/datum/controller/subsystem/processing/flightpacks/Initialize()
sync_flightsuit_processing()
/datum/controller/subsystem/processing/flightpacks/vv_edit_var(var_name, var_value)
..()
switch(var_name)
if("flightsuit_processing")
sync_flightsuit_processing()
/datum/controller/subsystem/processing/flightpacks/proc/sync_flightsuit_processing()
for(var/obj/item/flightpack/FP in processing)
FP.sync_processing(src)
if(flightsuit_processing == FLIGHTSUIT_PROCESSING_NONE) //Don't even bother firing.
can_fire = FALSE
else
can_fire = TRUE
@@ -3,7 +3,6 @@ PROCESSING_SUBSYSTEM_DEF(projectiles)
wait = 1
stat_tag = "PP"
flags = SS_NO_INIT|SS_TICKER
var/global_max_tick_moves = 10
var/global_pixel_speed = 2
var/global_iterations_per_move = 16
+1 -13
View File
@@ -5,7 +5,7 @@ SUBSYSTEM_DEF(profiler)
init_order = INIT_ORDER_PROFILER
runlevels = RUNLEVELS_DEFAULT | RUNLEVEL_LOBBY
wait = 3000
flags = SS_NO_TICK_CHECK
flags = SS_NO_TICK_CHECK
var/fetch_cost = 0
var/write_cost = 0
@@ -31,23 +31,12 @@ SUBSYSTEM_DEF(profiler)
return ..()
/datum/controller/subsystem/profiler/proc/StartProfiling()
#if DM_BUILD < 1506 || DM_VERSION < 513
stack_trace("Auto profiling unsupported on this byond version")
CONFIG_SET(flag/auto_profile, FALSE)
#else
world.Profile(PROFILE_START)
#endif
/datum/controller/subsystem/profiler/proc/StopProfiling()
#if DM_BUILD >= 1506 && DM_VERSION >= 513
world.Profile(PROFILE_STOP)
#endif
/datum/controller/subsystem/profiler/proc/DumpFile()
#if DM_BUILD < 1506 || DM_VERSION < 513
stack_trace("Auto profiling unsupported on this byond version")
CONFIG_SET(flag/auto_profile, FALSE)
#else
var/timer = TICK_USAGE_REAL
var/current_profile_data = world.Profile(PROFILE_REFRESH,format="json")
fetch_cost = MC_AVERAGE(fetch_cost, TICK_DELTA_TO_MS(TICK_USAGE_REAL - timer))
@@ -60,4 +49,3 @@ SUBSYSTEM_DEF(profiler)
timer = TICK_USAGE_REAL
WRITE_FILE(json_file, current_profile_data)
write_cost = MC_AVERAGE(write_cost, TICK_DELTA_TO_MS(TICK_USAGE_REAL - timer))
#endif
+4 -4
View File
@@ -231,13 +231,13 @@ SUBSYSTEM_DEF(shuttle)
call_reason = trim(html_encode(call_reason))
if(length(call_reason) < CALL_SHUTTLE_REASON_LENGTH && seclevel2num(get_security_level()) > SEC_LEVEL_GREEN)
if(length(call_reason) < CALL_SHUTTLE_REASON_LENGTH && GLOB.security_level > SEC_LEVEL_GREEN)
to_chat(user, "<span class='alert'>You must provide a reason.</span>")
return
var/area/signal_origin = get_area(user)
var/emergency_reason = "\nNature of emergency:\n\n[call_reason]"
var/security_num = seclevel2num(get_security_level())
var/security_num = GLOB.security_level
switch(security_num)
if(SEC_LEVEL_RED,SEC_LEVEL_DELTA)
emergency.request(null, signal_origin, html_decode(emergency_reason), 1) //There is a serious threat we gotta move no time to give them five minutes.
@@ -299,7 +299,7 @@ SUBSYSTEM_DEF(shuttle)
/datum/controller/subsystem/shuttle/proc/canRecall()
if(!emergency || emergency.mode != SHUTTLE_CALL || emergencyNoRecall || SSticker.mode.name == "meteor")
return
var/security_num = seclevel2num(get_security_level())
var/security_num = GLOB.security_level
switch(security_num)
if(SEC_LEVEL_GREEN)
if(emergency.timeLeft(1) < emergencyCallTime)
@@ -664,7 +664,7 @@ SUBSYSTEM_DEF(shuttle)
/datum/controller/subsystem/shuttle/proc/autoEnd() //CIT CHANGE - allows shift to end without being a proper shuttle call?
if(EMERGENCY_IDLE_OR_RECALLED)
SSshuttle.emergency.request(silent = TRUE)
priority_announce("The shift has come to an end and the shuttle called. [seclevel2num(get_security_level()) == SEC_LEVEL_RED ? "Red Alert state confirmed: Dispatching priority shuttle. " : "" ]It will arrive in [emergency.timeLeft(600)] minutes.", null, "shuttlecalled", "Priority")
priority_announce("The shift has come to an end and the shuttle called. [GLOB.security_level == SEC_LEVEL_RED ? "Red Alert state confirmed: Dispatching priority shuttle. " : "" ]It will arrive in [emergency.timeLeft(600)] minutes.", null, "shuttlecalled", "Priority")
log_game("Round end vote passed. Shuttle has been auto-called.")
message_admins("Round end vote passed. Shuttle has been auto-called.")
emergencyNoRecall = TRUE
+3
View File
@@ -387,6 +387,9 @@ SUBSYSTEM_DEF(ticker)
for(var/mob/dead/new_player/N in GLOB.player_list)
var/mob/living/carbon/human/player = N.new_character
if(istype(player) && player.mind && player.mind.assigned_role)
var/datum/job/J = SSjob.GetJob(player.mind.assigned_role)
if(J)
J.standard_assign_skills(player.mind)
if(player.mind.assigned_role == "Captain")
captainless=0
if(player.mind.assigned_role != player.mind.special_role)
+2 -2
View File
@@ -94,7 +94,7 @@ SUBSYSTEM_DEF(timer)
if(ctime_timer.flags & TIMER_LOOP)
ctime_timer.spent = 0
ctime_timer.timeToRun = REALTIMEOFDAY + ctime_timer.wait
BINARY_INSERT(ctime_timer, clienttime_timers, datum/timedevent, timeToRun)
BINARY_INSERT(ctime_timer, clienttime_timers, datum/timedevent, ctime_timer, timeToRun, COMPARE_KEY)
else
qdel(ctime_timer)
@@ -423,7 +423,7 @@ SUBSYSTEM_DEF(timer)
L = SStimer.second_queue
if(L)
BINARY_INSERT(src, L, datum/timedevent, timeToRun)
BINARY_INSERT(src, L, datum/timedevent, src, timeToRun, COMPARE_KEY)
return
//get the list of buckets
+2 -2
View File
@@ -352,7 +352,6 @@ SUBSYSTEM_DEF(vote)
if("dynamic")
if(SSticker.current_state > GAME_STATE_PREGAME)//Don't change the mode if the round already started.
return message_admins("A vote has tried to change the gamemode, but the game has already started. Aborting.")
GLOB.master_mode = "dynamic"
var/list/runnable_storytellers = config.get_runnable_storytellers()
var/datum/dynamic_storyteller/picked
for(var/T in runnable_storytellers)
@@ -361,7 +360,7 @@ SUBSYSTEM_DEF(vote)
picked = S
runnable_storytellers[S] *= round(stored_gamemode_votes[initial(S.name)]*100000,1)
if(!picked)
picked = pickweightAllowZero(runnable_storytellers)
picked = pickweight(runnable_storytellers, 0)
GLOB.dynamic_storyteller_type = picked
if("map")
var/datum/map_config/VM = config.maplist[.]
@@ -489,6 +488,7 @@ SUBSYSTEM_DEF(vote)
modes_to_add -= "traitor" // makes it so that traitor is always available
choices.Add(modes_to_add)
if("dynamic")
GLOB.master_mode = "dynamic"
var/list/probabilities = CONFIG_GET(keyed_list/storyteller_weight)
for(var/T in config.storyteller_cache)
var/datum/dynamic_storyteller/S = T
+1 -1
View File
@@ -171,7 +171,7 @@
if(!..())
return 0
var/mob/M = target
M.ghostize(1)
M.ghostize(can_reenter_corpse = TRUE, voluntary = TRUE)
/datum/action/proc/OnUpdatedIcon()
UpdateButtonIcon()
+1 -1
View File
@@ -253,7 +253,7 @@
var/datum/ai_laws/lawtype
var/list/law_weights = CONFIG_GET(keyed_list/law_weight)
while(!lawtype && law_weights.len)
var/possible_id = pickweightAllowZero(law_weights)
var/possible_id = pickweight(law_weights, 0)
lawtype = lawid_to_type(possible_id)
if(!lawtype)
law_weights -= possible_id
+2 -1
View File
@@ -91,7 +91,6 @@
trauma = _trauma
owner = trauma.owner
copy_known_languages_from(owner, TRUE)
setup_friend()
@@ -150,6 +149,8 @@
friend_talk(message)
/mob/camera/imaginary_friend/Hear(message, atom/movable/speaker, datum/language/message_language, raw_message, radio_freq, list/spans, message_mode, atom/movable/source)
if (client?.prefs.chat_on_map && (client.prefs.see_chat_non_mob || ismob(speaker)))
create_chat_message(speaker, message_language, raw_message, spans, message_mode)
to_chat(src, compose_message(speaker, message_language, raw_message, radio_freq, spans, message_mode, FALSE, source))
/mob/camera/imaginary_friend/proc/friend_talk(message)
+4 -10
View File
@@ -26,21 +26,15 @@
scan_desc = "extensive damage to the brain's language center"
gain_text = "<span class='warning'>You have trouble forming words in your head...</span>"
lose_text = "<span class='notice'>You suddenly remember how languages work.</span>"
var/datum/language_holder/prev_language
var/datum/language_holder/mob_language
/datum/brain_trauma/severe/aphasia/on_gain()
mob_language = owner.get_language_holder()
prev_language = mob_language.copy()
mob_language.remove_all_languages()
mob_language.grant_language(/datum/language/aphasia)
owner.add_blocked_language(subtypesof(/datum/language/) - /datum/language/aphasia, LANGUAGE_APHASIA)
owner.grant_language(/datum/language/aphasia, TRUE, TRUE, LANGUAGE_APHASIA)
..()
/datum/brain_trauma/severe/aphasia/on_lose()
mob_language.remove_language(/datum/language/aphasia)
mob_language.copy_known_languages_from(prev_language) //this will also preserve languages learned during the trauma
QDEL_NULL(prev_language)
mob_language = null
owner.remove_blocked_language(subtypesof(/datum/language/), LANGUAGE_APHASIA)
owner.remove_language(/datum/language/aphasia, TRUE, TRUE, LANGUAGE_APHASIA)
..()
/datum/brain_trauma/severe/blindness
+236
View File
@@ -0,0 +1,236 @@
#define CHAT_MESSAGE_SPAWN_TIME 0.2 SECONDS
#define CHAT_MESSAGE_LIFESPAN 5 SECONDS
#define CHAT_MESSAGE_EOL_FADE 0.7 SECONDS
#define CHAT_MESSAGE_EXP_DECAY 0.7 // Messages decay at pow(factor, idx in stack)
#define CHAT_MESSAGE_HEIGHT_DECAY 0.9 // Increase message decay based on the height of the message
#define CHAT_MESSAGE_APPROX_LHEIGHT 11 // Approximate height in pixels of an 'average' line, used for height decay
#define CHAT_MESSAGE_WIDTH 96 // pixels
#define CHAT_MESSAGE_MAX_LENGTH 110 // characters
#define WXH_TO_HEIGHT(x) text2num(copytext((x), findtextEx((x), "x") + 1)) // thanks lummox
/**
* # Chat Message Overlay
*
* Datum for generating a message overlay on the map
*/
/datum/chatmessage
/// The visual element of the chat messsage
var/image/message
/// The location in which the message is appearing
var/atom/message_loc
/// The client who heard this message
var/client/owned_by
/// Contains the scheduled destruction time
var/scheduled_destruction
/// Contains the approximate amount of lines for height decay
var/approx_lines
/**
* Constructs a chat message overlay
*
* Arguments:
* * text - The text content of the overlay
* * target - The target atom to display the overlay at
* * owner - The mob that owns this overlay, only this mob will be able to view it
* * extra_classes - Extra classes to apply to the span that holds the text
* * lifespan - The lifespan of the message in deciseconds
*/
/datum/chatmessage/New(text, atom/target, mob/owner, list/extra_classes = null, lifespan = CHAT_MESSAGE_LIFESPAN)
. = ..()
if (!istype(target))
CRASH("Invalid target given for chatmessage")
if(QDELETED(owner) || !istype(owner) || !owner.client)
stack_trace("/datum/chatmessage created with [isnull(owner) ? "null" : "invalid"] mob owner")
qdel(src)
return
INVOKE_ASYNC(src, .proc/generate_image, text, target, owner, extra_classes, lifespan)
/datum/chatmessage/Destroy()
if (owned_by)
if (owned_by.seen_messages)
LAZYREMOVEASSOC(owned_by.seen_messages, message_loc, src)
owned_by.images.Remove(message)
owned_by = null
message_loc = null
message = null
return ..()
/**
* Generates a chat message image representation
*
* Arguments:
* * text - The text content of the overlay
* * target - The target atom to display the overlay at
* * owner - The mob that owns this overlay, only this mob will be able to view it
* * extra_classes - Extra classes to apply to the span that holds the text
* * lifespan - The lifespan of the message in deciseconds
*/
/datum/chatmessage/proc/generate_image(text, atom/target, mob/owner, list/extra_classes, lifespan)
// Register client who owns this message
owned_by = owner.client
RegisterSignal(owned_by, COMSIG_PARENT_QDELETING, .proc/qdel, src)
// Clip message
var/maxlen = owned_by.prefs.max_chat_length
if (length_char(text) > maxlen)
text = copytext_char(text, 1, maxlen + 1) + "..." // BYOND index moment
// Calculate target color if not already present
if (!target.chat_color || target.chat_color_name != target.name)
target.chat_color = colorize_string(target.name)
target.chat_color_darkened = colorize_string(target.name, 0.85, 0.85)
target.chat_color_name = target.name
// Get rid of any URL schemes that might cause BYOND to automatically wrap something in an anchor tag
var/static/regex/url_scheme = new(@"[A-Za-z][A-Za-z0-9+-\.]*:\/\/", "g")
text = replacetext(text, url_scheme, "")
// Reject whitespace
var/static/regex/whitespace = new(@"^\s*$")
if (whitespace.Find(text))
qdel(src)
return
// Non mobs speakers can be small
if (!ismob(target))
extra_classes |= "small"
// Append radio icon if from a virtual speaker
if (extra_classes.Find("virtual-speaker"))
var/image/r_icon = image('icons/UI_Icons/chat/chat_icons.dmi', icon_state = "radio")
text = "\icon[r_icon]&nbsp;" + text
// We dim italicized text to make it more distinguishable from regular text
var/tgt_color = extra_classes.Find("italics") ? target.chat_color_darkened : target.chat_color
// Approximate text height
// Note we have to replace HTML encoded metacharacters otherwise MeasureText will return a zero height
// BYOND Bug #2563917
// Construct text
var/static/regex/html_metachars = new(@"&[A-Za-z]{1,7};", "g")
var/complete_text = "<span class='center maptext [extra_classes != null ? extra_classes.Join(" ") : ""]' style='color: [tgt_color]'>[text]</span>"
var/mheight = WXH_TO_HEIGHT(owned_by.MeasureText(replacetext(complete_text, html_metachars, "m"), null, CHAT_MESSAGE_WIDTH))
approx_lines = max(1, mheight / CHAT_MESSAGE_APPROX_LHEIGHT)
// Translate any existing messages upwards, apply exponential decay factors to timers
message_loc = target
if (owned_by.seen_messages)
var/idx = 1
var/combined_height = approx_lines
for(var/msg in owned_by.seen_messages[message_loc])
var/datum/chatmessage/m = msg
animate(m.message, pixel_y = m.message.pixel_y + mheight, time = CHAT_MESSAGE_SPAWN_TIME)
combined_height += m.approx_lines
var/sched_remaining = m.scheduled_destruction - world.time
if (sched_remaining > CHAT_MESSAGE_SPAWN_TIME)
var/remaining_time = (sched_remaining) * (CHAT_MESSAGE_EXP_DECAY ** idx++) * (CHAT_MESSAGE_HEIGHT_DECAY ** combined_height)
m.scheduled_destruction = world.time + remaining_time
addtimer(CALLBACK(m, .proc/end_of_life), remaining_time, TIMER_UNIQUE|TIMER_OVERRIDE)
// Build message image
message = image(loc = message_loc, layer = CHAT_LAYER)
message.plane = GAME_PLANE
message.appearance_flags = APPEARANCE_UI_IGNORE_ALPHA | KEEP_APART
message.alpha = 0
message.pixel_y = owner.bound_height * 0.95
message.maptext_width = CHAT_MESSAGE_WIDTH
message.maptext_height = mheight
message.maptext_x = (CHAT_MESSAGE_WIDTH - owner.bound_width) * -0.5
message.maptext = complete_text
// View the message
LAZYADDASSOC(owned_by.seen_messages, message_loc, src)
owned_by.images |= message
animate(message, alpha = 255, time = CHAT_MESSAGE_SPAWN_TIME)
// Prepare for destruction
scheduled_destruction = world.time + (lifespan - CHAT_MESSAGE_EOL_FADE)
addtimer(CALLBACK(src, .proc/end_of_life), lifespan - CHAT_MESSAGE_EOL_FADE, TIMER_UNIQUE|TIMER_OVERRIDE)
/**
* Applies final animations to overlay CHAT_MESSAGE_EOL_FADE deciseconds prior to message deletion
*/
/datum/chatmessage/proc/end_of_life(fadetime = CHAT_MESSAGE_EOL_FADE)
animate(message, alpha = 0, time = fadetime, flags = ANIMATION_PARALLEL)
QDEL_IN(src, fadetime)
/**
* Creates a message overlay at a defined location for a given speaker
*
* Arguments:
* * speaker - The atom who is saying this message
* * message_language - The language that the message is said in
* * raw_message - The text content of the message
* * spans - Additional classes to be added to the message
* * message_mode - Bitflags relating to the mode of the message
*/
/mob/proc/create_chat_message(atom/movable/speaker, datum/language/message_language, raw_message, list/spans, message_mode)
// Ensure the list we are using, if present, is a copy so we don't modify the list provided to us
spans = spans?.Copy()
// Check for virtual speakers (aka hearing a message through a radio)
var/atom/movable/originalSpeaker = speaker
if (istype(speaker, /atom/movable/virtualspeaker))
var/atom/movable/virtualspeaker/v = speaker
speaker = v.source
spans |= "virtual-speaker"
// Ignore virtual speaker (most often radio messages) from ourself
if (originalSpeaker != src && speaker == src)
return
// Display visual above source
new /datum/chatmessage(lang_treat(speaker, message_language, raw_message, spans, null, TRUE), speaker, src, spans)
// Tweak these defines to change the available color ranges
#define CM_COLOR_SAT_MIN 0.6
#define CM_COLOR_SAT_MAX 0.7
#define CM_COLOR_LUM_MIN 0.65
#define CM_COLOR_LUM_MAX 0.75
/**
* Gets a color for a name, will return the same color for a given string consistently within a round.atom
*
* Note that this proc aims to produce pastel-ish colors using the HSL colorspace. These seem to be favorable for displaying on the map.
*
* Arguments:
* * name - The name to generate a color for
* * sat_shift - A value between 0 and 1 that will be multiplied against the saturation
* * lum_shift - A value between 0 and 1 that will be multiplied against the luminescence
*/
/datum/chatmessage/proc/colorize_string(name, sat_shift = 1, lum_shift = 1)
// seed to help randomness
var/static/rseed = rand(1,26)
// get hsl using the selected 6 characters of the md5 hash
var/hash = copytext(md5(name + GLOB.round_id), rseed, rseed + 6)
var/h = hex2num(copytext(hash, 1, 3)) * (360 / 255)
var/s = (hex2num(copytext(hash, 3, 5)) >> 2) * ((CM_COLOR_SAT_MAX - CM_COLOR_SAT_MIN) / 63) + CM_COLOR_SAT_MIN
var/l = (hex2num(copytext(hash, 5, 7)) >> 2) * ((CM_COLOR_LUM_MAX - CM_COLOR_LUM_MIN) / 63) + CM_COLOR_LUM_MIN
// adjust for shifts
s *= clamp(sat_shift, 0, 1)
l *= clamp(lum_shift, 0, 1)
// convert to rgb
var/h_int = round(h/60) // mapping each section of H to 60 degree sections
var/c = (1 - abs(2 * l - 1)) * s
var/x = c * (1 - abs((h / 60) % 2 - 1))
var/m = l - c * 0.5
x = (x + m) * 255
c = (c + m) * 255
m *= 255
switch(h_int)
if(0)
return "#[num2hex(c, 2)][num2hex(x, 2)][num2hex(m, 2)]"
if(1)
return "#[num2hex(x, 2)][num2hex(c, 2)][num2hex(m, 2)]"
if(2)
return "#[num2hex(m, 2)][num2hex(c, 2)][num2hex(x, 2)]"
if(3)
return "#[num2hex(m, 2)][num2hex(x, 2)][num2hex(c, 2)]"
if(4)
return "#[num2hex(x, 2)][num2hex(m, 2)][num2hex(c, 2)]"
if(5)
return "#[num2hex(c, 2)][num2hex(m, 2)][num2hex(x, 2)]"
-95
View File
@@ -1,95 +0,0 @@
/datum/component/archaeology
dupe_mode = COMPONENT_DUPE_UNIQUE
var/list/archdrops = list(/obj/item/bikehorn = list(ARCH_PROB = 100, ARCH_MAXDROP = 1)) // honk~
var/prob2drop
var/dug
var/datum/callback/callback
/datum/component/archaeology/Initialize(list/_archdrops = list(), datum/callback/_callback)
archdrops = _archdrops
for(var/i in archdrops)
if(isnull(archdrops[i][ARCH_MAXDROP]))
archdrops[i][ARCH_MAXDROP] = 1
stack_trace("ARCHAEOLOGY WARNING: [parent] contained a null max_drop value in [i].")
if(isnull(archdrops[i][ARCH_PROB]))
archdrops[i][ARCH_PROB] = 100
stack_trace("ARCHAEOLOGY WARNING: [parent] contained a null probability value in [i].")
callback = _callback
RegisterSignal(parent, COMSIG_PARENT_ATTACKBY,.proc/Dig)
RegisterSignal(parent, COMSIG_ATOM_EX_ACT, .proc/BombDig)
RegisterSignal(parent, COMSIG_ATOM_SING_PULL, .proc/SingDig)
/datum/component/archaeology/InheritComponent(datum/component/archaeology/A, i_am_original)
var/list/other_archdrops = A.archdrops
var/list/_archdrops = archdrops
for(var/I in other_archdrops)
_archdrops[I] += other_archdrops[I]
/datum/component/archaeology/proc/Dig(datum/source, obj/item/I, mob/living/user)
if(dug)
to_chat(user, "<span class='notice'>Looks like someone has dug here already.</span>")
return
if(!isturf(user.loc))
return
if(I.tool_behaviour == TOOL_SHOVEL || I.tool_behaviour == TOOL_MINING)
to_chat(user, "<span class='notice'>You start digging...</span>")
if(I.use_tool(parent, user, 40, volume=50))
to_chat(user, "<span class='notice'>You dig a hole.</span>")
gets_dug()
dug = TRUE
SSblackbox.record_feedback("tally", "pick_used_mining", 1, I.type)
return COMPONENT_NO_AFTERATTACK
/datum/component/archaeology/proc/gets_dug()
if(dug)
return
else
var/turf/open/OT = get_turf(parent)
for(var/thing in archdrops)
var/maxtodrop = archdrops[thing][ARCH_MAXDROP]
for(var/i in 1 to maxtodrop)
if(prob(archdrops[thing][ARCH_PROB])) // can't win them all!
new thing(OT)
if(isopenturf(OT))
if(OT.postdig_icon_change)
if(istype(OT, /turf/open/floor/plating/asteroid/) && !OT.postdig_icon)
var/turf/open/floor/plating/asteroid/AOT = parent
AOT.icon_plating = "[AOT.environment_type]_dug"
AOT.icon_state = "[AOT.environment_type]_dug"
else
if(isplatingturf(OT))
var/turf/open/floor/plating/POT = parent
POT.icon_plating = "[POT.postdig_icon]"
POT.icon_state = "[OT.postdig_icon]"
if(OT.slowdown) //Things like snow slow you down until you dig them.
OT.slowdown = 0
dug = TRUE
if(callback)
callback.Invoke()
/datum/component/archaeology/proc/SingDig(datum/source, S, current_size)
switch(current_size)
if(STAGE_THREE)
if(prob(30))
gets_dug()
if(STAGE_FOUR)
if(prob(50))
gets_dug()
else
if(current_size >= STAGE_FIVE && prob(70))
gets_dug()
/datum/component/archaeology/proc/BombDig(datum/source, severity, target)
switch(severity)
if(3)
return
if(2)
if(prob(20))
gets_dug()
if(1)
gets_dug()
+1 -1
View File
@@ -4,7 +4,7 @@
var/list/bounce_signals = list(COMSIG_MOVABLE_IMPACT, COMSIG_ITEM_HIT_REACT, COMSIG_ITEM_ATTACK)
/datum/component/bouncy/Initialize(_bouncy_mod, list/_bounce_signals)
if(!ismovableatom(parent))
if(!ismovable(parent))
return COMPONENT_INCOMPATIBLE
if(_bouncy_mod)
bouncy_mod = _bouncy_mod
+2 -2
View File
@@ -55,7 +55,7 @@
log_combat(user, H, "starts slicing the throat of")
playsound(H.loc, butcher_sound, 50, TRUE, -1)
if(do_mob(user, H, CLAMP(500 / source.force, 30, 100)) && H.Adjacent(source))
if(do_mob(user, H, clamp(500 / source.force, 30, 100)) && H.Adjacent(source))
if(H.has_status_effect(/datum/status_effect/neck_slice))
user.show_message("<span class='warning'>[H]'s neck has already been already cut, you can't make the bleeding any worse!</span>", 1, \
"<span class='warning'>Their neck has already been already cut, you can't make the bleeding any worse!</span>")
@@ -65,7 +65,7 @@
"<span class='userdanger'>[user] slits your throat...</span>")
log_combat(user, H, "finishes slicing the throat of")
H.apply_damage(source.force, BRUTE, BODY_ZONE_HEAD)
H.bleed_rate = CLAMP(H.bleed_rate + 20, 0, 30)
H.bleed_rate = clamp(H.bleed_rate + 20, 0, 30)
H.apply_status_effect(/datum/status_effect/neck_slice)
/datum/component/butchering/proc/Butcher(mob/living/butcher, mob/living/meat)
@@ -23,3 +23,4 @@
*/
/datum/crafting_recipe/proc/check_requirements(mob/user, list/collected_requirements)
return TRUE
@@ -327,3 +327,16 @@
/obj/item/stack/cable_coil = 10)
time = 100 //Takes awhile to put all the garlics on the coil and knot it.
category = CAT_CLOTHING
/datum/crafting_recipe/gripperoffbrand
name = "Improvised Gripper Gloves"
reqs = list(
/obj/item/clothing/gloves/fingerless = 1,
// /obj/item/stack/sticky_tape = 1
/obj/item/stack/cable_coil = 5,
/obj/item/stack/sheet/cloth = 2,
)
result = /obj/item/clothing/gloves/tackler/offbrand
category = CAT_CLOTHING
tools = list(TOOL_WIRECUTTER)
time = 20
@@ -115,6 +115,33 @@
//Tools & Storage//
///////////////////
/datum/crafting_recipe/upgraded_gauze
name = "Improved Gauze"
result = /obj/item/stack/medical/gauze/adv/one
time = 1
reqs = list(/obj/item/stack/medical/gauze = 1,
/datum/reagent/space_cleaner/sterilizine = 10)
category = CAT_MISC
subcategory = CAT_TOOL
/datum/crafting_recipe/bruise_pack
name = "Bruise Pack"
result = /obj/item/stack/medical/bruise_pack/one
time = 1
reqs = list(/obj/item/stack/medical/gauze = 1,
/datum/reagent/medicine/styptic_powder = 10)
category = CAT_MISC
subcategory = CAT_TOOL
/datum/crafting_recipe/burn_pack
name = "Burn Ointment"
result = /obj/item/stack/medical/ointment/one
time = 1
reqs = list(/obj/item/stack/medical/gauze = 1,
/datum/reagent/medicine/silver_sulfadiazine = 10)
category = CAT_MISC
subcategory = CAT_TOOL
/datum/crafting_recipe/ghettojetpack
name = "Improvised Jetpack"
result = /obj/item/tank/jetpack/improvised
@@ -233,6 +260,15 @@
subcategory = CAT_TOOL
category = CAT_MISC
/datum/crafting_recipe/electrochromatic_kit
name = "Electrochromatic Kit"
result = /obj/item/electronics/electrochromatic_kit
reqs = list(/obj/item/stack/sheet/metal = 1,
/obj/item/stack/cable_coil = 1)
time = 5
subcategory = CAT_TOOL
category = CAT_MISC
////////////
//Vehicles//
////////////
@@ -377,15 +413,6 @@
subcategory = CAT_MISCELLANEOUS
category = CAT_MISC
/datum/crafting_recipe/paperwork
name = "Filed Paper Work"
result = /obj/item/folder/paperwork_correct
time = 10 //Takes time for people to file and complete paper work!
tools = list(/obj/item/pen)
reqs = list(/obj/item/folder/paperwork = 1)
subcategory = CAT_MISCELLANEOUS
category = CAT_MISC
/datum/crafting_recipe/coconut_bong
name = "Coconut Bong"
result = /obj/item/bong/coconut
+1 -1
View File
@@ -3,7 +3,7 @@
var/list/say_lines
/datum/component/edit_complainer/Initialize(list/text)
if(!ismovableatom(parent))
if(!ismovable(parent))
return COMPONENT_INCOMPATIBLE
var/static/list/default_lines = list(
+1 -1
View File
@@ -13,7 +13,7 @@
RegisterSignal(parent, COMSIG_PARENT_ATTACKBY, .proc/explodable_attack)
RegisterSignal(parent, COMSIG_TRY_STORAGE_INSERT, .proc/explodable_insert_item)
RegisterSignal(parent, COMSIG_ATOM_EX_ACT, .proc/detonate)
if(ismovableatom(parent))
if(ismovable(parent))
RegisterSignal(parent, COMSIG_MOVABLE_IMPACT, .proc/explodable_impact)
RegisterSignal(parent, COMSIG_MOVABLE_BUMP, .proc/explodable_bump)
if(isitem(parent))
+1 -1
View File
@@ -54,7 +54,7 @@
/datum/fantasy_affix/pyromantic/apply(datum/component/fantasy/comp, newName)
var/obj/item/master = comp.parent
comp.appliedComponents += master.AddComponent(/datum/component/igniter, CLAMP(comp.quality, 1, 10))
comp.appliedComponents += master.AddComponent(/datum/component/igniter, clamp(comp.quality, 1, 10))
return "pyromantic [newName]"
/datum/fantasy_affix/vampiric
+88
View File
@@ -0,0 +1,88 @@
/**
* Identification components
*/
/datum/component/identification
/// General flags for how we should work.
var/identification_flags = NONE
/// General flags for what we should do.
var/identification_effect_flags = NONE
/// General flags for how we can be identified.
var/identification_method_flags = NONE
/// If this is set, show this on examine to the examiner if they know how to use it.
var/additional_examine_text = "<span class='notice'>You seem to know more about this item than others..</span>"
/// Added to deconstructive analyzer say on success if set
var/deconstructor_reveal_text = "item operation instructions"
/datum/component/identification/Initialize(id_flags, id_effect_flags, id_method_flags)
if(!isobj(parent))
return COMPONENT_INCOMPATIBLE
. = ..()
if(. & COMPONENT_INCOMPATIBLE)
return
identification_flags = id_flags
identification_effect_flags = id_effect_flags
identification_method_flags = id_method_flags
/datum/component/identification/RegisterWithParent()
RegisterSignal(parent, COMSIG_PARENT_EXAMINE, .proc/on_examine)
if(identification_effect_flags & ID_COMPONENT_EFFECT_NO_ACTIONS)
RegisterSignal(parent, COMSIG_ITEM_EQUIPPED, .proc/on_equip)
if(identification_method_flags & ID_COMPONENT_IDENTIFY_WITH_DECONSTRUCTOR)
RegisterSignal(parent, COMSIG_ITEM_DECONSTRUCTOR_DEEPSCAN, .proc/on_deconstructor_deepscan)
/datum/component/identification/UnregisterFromParent()
var/list/unregister = list(COMSIG_PARENT_EXAMINE)
if(identification_effect_flags & ID_COMPONENT_EFFECT_NO_ACTIONS)
unregister += COMSIG_ITEM_EQUIPPED
if(identification_method_flags & ID_COMPONENT_IDENTIFY_WITH_DECONSTRUCTOR)
unregister += COMSIG_ITEM_DECONSTRUCTOR_DEEPSCAN
UnregisterSignal(parent, unregister)
/datum/component/identification/proc/on_examine(datum/source, mob/user, list/returnlist)
if(check_knowledge(user) != ID_COMPONENT_KNOWLEDGE_FULL)
return
if(!additional_examine_text)
return
returnlist += additional_examine_text
/datum/component/identification/vv_edit_var(var_name, var_value)
// since i care SOOO much about memory optimization, we only register signals we need to
// so when someone vv's us, we should probably make sure we have the ones we need to with an update.
if((var_value == NAMEOF(src, identification_flags)) || (var_value == NAMEOF(src, identification_effect_flags)) || (var_value == NAMEOF(src, identification_method_flags)))
UnregisterFromParent()
. = ..()
if((var_value == NAMEOF(src, identification_flags)) || (var_value == NAMEOF(src, identification_effect_flags)) || (var_value == NAMEOF(src, identification_method_flags)))
RegisterWithParent()
/datum/component/identification/proc/on_equip(datum/source, mob/user)
if(check_knowledge(user) == ID_COMPONENT_KNOWLEDGE_FULL)
return
if(identification_method_flags & ID_COMPONENT_EFFECT_NO_ACTIONS)
return COMPONENT_NO_GRANT_ACTIONS
/datum/component/identification/proc/check_knowledge(mob/user)
return ID_COMPONENT_KNOWLEDGE_NONE
/datum/component/identification/proc/on_identify(mob/user)
if(identification_flags & ID_COMPONENT_DEL_ON_IDENTIFY)
qdel(src)
/datum/component/identification/proc/on_deconstructor_deepscan(datum/source, obj/machinery/rnd/destructive_analyzer/analyzer, mob/user, list/information = list())
if((identification_method_flags & ID_COMPONENT_IDENTIFY_WITH_DECONSTRUCTOR) && !(identification_flags & ID_COMPONENT_DECONSTRUCTOR_DEEPSCANNED))
identification_flags |= ID_COMPONENT_DECONSTRUCTOR_DEEPSCANNED
on_identify(user)
if(deconstructor_reveal_text)
information += deconstructor_reveal_text
return COMPONENT_DEEPSCAN_UNCOVERED_INFORMATION
/**
* Identification component subtype - Syndicate
*
* Checks if the user is a traitor.
*/
/datum/component/identification/syndicate
/datum/component/identification/syndicate/check_knowledge(mob/user)
. = ..()
if(user?.mind?.has_antag_datum(/datum/antagonist/traitor))
. = max(., ID_COMPONENT_KNOWLEDGE_FULL)
+1 -1
View File
@@ -13,7 +13,7 @@
expire_time = world.time + expire_in
QDEL_IN(src, expire_in)
if(!ismovableatom(parent))
if(!ismovable(parent))
return COMPONENT_INCOMPATIBLE
RegisterSignal(parent, COMSIG_COMPONENT_CLEAN_ACT, .proc/clean)
RegisterSignal(parent, COMSIG_MOVABLE_BUCKLE, .proc/try_infect_buckle)
+20 -3
View File
@@ -1,13 +1,18 @@
/datum/component/knockback
/// distance the atom will be thrown
var/throw_distance
/// whether this can throw anchored targets (tables, etc)
var/throw_anchored
/// whether this is a gentle throw (default false means people thrown into walls are stunned / take damage)
var/throw_gentle
/datum/component/knockback/Initialize(throw_distance=1)
/datum/component/knockback/Initialize(throw_distance=1, throw_gentle=FALSE)
if(!isitem(parent) && !ishostile(parent) && !isgun(parent) && !ismachinery(parent) && !isstructure(parent))
return COMPONENT_INCOMPATIBLE
src.throw_distance = throw_distance
src.throw_anchored = throw_anchored
src.throw_gentle = throw_gentle
/datum/component/knockback/RegisterWithParent()
. = ..()
@@ -22,19 +27,31 @@
. = ..()
UnregisterSignal(parent, list(COMSIG_ITEM_AFTERATTACK, COMSIG_HOSTILE_ATTACKINGTARGET, COMSIG_PROJECTILE_ON_HIT))
/// triggered after an item attacks something
/datum/component/knockback/proc/item_afterattack(obj/item/source, atom/target, mob/user, proximity_flag, click_parameters)
if(!proximity_flag)
return
do_knockback(target, user, get_dir(source, target))
/// triggered after a hostile simplemob attacks something
/datum/component/knockback/proc/hostile_attackingtarget(mob/living/simple_animal/hostile/attacker, atom/target)
do_knockback(target, attacker, get_dir(attacker, target))
/// triggered after a projectile hits something
/datum/component/knockback/proc/projectile_hit(atom/fired_from, atom/movable/firer, atom/target, Angle)
do_knockback(target, null, angle2dir(Angle))
/**
* Throw a target in a direction
*
* Arguments:
* * target - Target atom to throw
* * thrower - Thing that caused this atom to be thrown
* * throw_dir - Direction to throw the atom
*/
/datum/component/knockback/proc/do_knockback(atom/target, mob/thrower, throw_dir)
if(!ismovableatom(target) || throw_dir == null)
if(!ismovable(target) || throw_dir == null)
return
var/atom/movable/throwee = target
if(throwee.anchored && !throw_anchored)
@@ -43,4 +60,4 @@
throw_dir = turn(throw_dir, 180)
throw_distance *= -1
var/atom/throw_target = get_edge_target_turf(throwee, throw_dir)
throwee.safe_throw_at(throw_target, throw_distance, 1, thrower)
throwee.safe_throw_at(throw_target, throw_distance, 1, thrower) //, gentle = throw_gentle)
+1 -1
View File
@@ -2,7 +2,7 @@
if(!isatom(parent))
return COMPONENT_INCOMPATIBLE
RegisterSignal(parent, COMSIG_PARENT_EXAMINE, .proc/examine)
if(ismovableatom(parent))
if(ismovable(parent))
RegisterSignal(parent, COMSIG_MOVABLE_CROSSED, .proc/crossed_react)
RegisterSignal(parent, COMSIG_MOVABLE_UNCROSSED, .proc/uncrossed_react)
for(var/i in get_turf(parent))
+3 -2
View File
@@ -14,8 +14,8 @@
var/x = target.x
var/y = target.y
var/z = target.z
var/turf/southwest = locate(CLAMP(x - (direction & WEST ? range : 0), 1, world.maxx), CLAMP(y - (direction & SOUTH ? range : 0), 1, world.maxy), CLAMP(z, 1, world.maxz))
var/turf/northeast = locate(CLAMP(x + (direction & EAST ? range : 0), 1, world.maxx), CLAMP(y + (direction & NORTH ? range : 0), 1, world.maxy), CLAMP(z, 1, world.maxz))
var/turf/southwest = locate(clamp(x - (direction & WEST ? range : 0), 1, world.maxx), clamp(y - (direction & SOUTH ? range : 0), 1, world.maxy), clamp(z, 1, world.maxz))
var/turf/northeast = locate(clamp(x + (direction & EAST ? range : 0), 1, world.maxx), clamp(y + (direction & NORTH ? range : 0), 1, world.maxy), clamp(z, 1, world.maxz))
//holder.vis_contents += block(southwest, northeast) // This doesnt work because of beta bug memes
for(var/i in block(southwest, northeast))
holder.vis_contents += i
@@ -39,4 +39,5 @@
/obj/effect/abstract/mirage_holder
name = "Mirage holder"
anchored = TRUE
plane = PLANE_SPACE
mouse_opacity = MOUSE_OPACITY_TRANSPARENT
+58 -10
View File
@@ -1,5 +1,7 @@
#define SLIGHT_INSANITY_PEN 1
#define MINOR_INSANITY_PEN 5
#define MAJOR_INSANITY_PEN 10
#define MOOD_INSANITY_MALUS 0.0054 // per point of sanity below SANITY_DISTURBED, a 40% debuff to skills at rock bottom depression.
/datum/component/mood
var/mood //Real happiness
@@ -22,7 +24,6 @@
RegisterSignal(parent, COMSIG_CLEAR_MOOD_EVENT, .proc/clear_event)
RegisterSignal(parent, COMSIG_MODIFY_SANITY, .proc/modify_sanity)
RegisterSignal(parent, COMSIG_LIVING_REVIVE, .proc/on_revive)
RegisterSignal(parent, COMSIG_MOB_HUD_CREATED, .proc/modify_hud)
var/mob/living/owner = parent
if(owner.hud_used)
@@ -150,7 +151,7 @@
if(8)
setSanity(sanity+0.25, maximum=SANITY_GREAT)
if(9)
setSanity(sanity+0.4, maximum=SANITY_GREAT)
setSanity(sanity+0.4, maximum=SANITY_AMAZING)
HandleNutrition(owner)
@@ -166,6 +167,7 @@
else if(sanity > maximum && amount > sanity - 0.5)
amount = sanity - 0.5
var/old_sanity = sanity
// Disturbed stops you from getting any more sane
if(HAS_TRAIT(master, TRAIT_UNSTABLE))
sanity = min(amount,sanity)
@@ -175,28 +177,34 @@
switch(sanity)
if(-INFINITY to SANITY_CRAZY)
setInsanityEffect(MAJOR_INSANITY_PEN)
master.add_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE, 100, override=TRUE, multiplicative_slowdown=1.5) //Did we change something ? movetypes is runtiming, movetypes=(~FLYING))
master.add_movespeed_modifier(/datum/movespeed_modifier/sanity/insane)
sanity_level = 6
if(SANITY_CRAZY to SANITY_UNSTABLE)
setInsanityEffect(MINOR_INSANITY_PEN)
master.add_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE, 100, override=TRUE, multiplicative_slowdown=1)//, movetypes=(~FLYING))
master.add_movespeed_modifier(/datum/movespeed_modifier/sanity/crazy)
sanity_level = 5
if(SANITY_UNSTABLE to SANITY_DISTURBED)
setInsanityEffect(0)
master.add_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE, 100, override=TRUE, multiplicative_slowdown=0.5)//, movetypes=(~FLYING))
setInsanityEffect(SLIGHT_INSANITY_PEN)
master.add_movespeed_modifier(/datum/movespeed_modifier/sanity/disturbed)
sanity_level = 4
if(SANITY_DISTURBED to SANITY_NEUTRAL)
setInsanityEffect(0)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY)
sanity_level = 3
if(SANITY_NEUTRAL+1 to SANITY_GREAT+1) //shitty hack but +1 to prevent it from responding to super small differences
setInsanityEffect(0)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY)
sanity_level = 2
if(SANITY_GREAT+1 to INFINITY)
setInsanityEffect(0)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY, TRUE)
master.remove_movespeed_modifier(MOVESPEED_ID_SANITY)
sanity_level = 1
if(old_sanity > 1 && sanity == 1)
RegisterSignal(master, COMSIG_MOB_SKILL_GET_AFFINITY, .proc/on_get_skill_affinity)
else if(old_sanity == 1 && sanity > 1)
UnregisterSignal(master, COMSIG_MOB_SKILL_GET_AFFINITY)
//update_mood_icon()
/datum/component/mood/proc/setInsanityEffect(newval)//More code so that the previous proc works
@@ -204,9 +212,14 @@
return
//var/mob/living/master = parent
//master.crit_threshold = (master.crit_threshold - insanity_effect) + newval
if(!insanity_effect && newval)
RegisterSignal(parent, COMSIG_MOB_ACTION_SKILL_MOD, .proc/on_mob_action_skill_mod)
RegisterSignal(parent, COMSIG_MOB_ITEM_ACTION_SKILLS_MOD, .proc/on_item_action_skills_mod)
else if(insanity_effect && !newval)
UnregisterSignal(parent, list(COMSIG_MOB_ACTION_SKILL_MOD, COMSIG_MOB_ITEM_ACTION_SKILLS_MOD))
insanity_effect = newval
/datum/component/mood/proc/modify_sanity(datum/source, amount, minimum = -INFINITY, maximum = INFINITY)
/datum/component/mood/proc/modify_sanity(datum/source, amount, minimum = SANITY_INSANE, maximum = SANITY_AMAZING)
setSanity(sanity + amount, minimum, maximum)
/datum/component/mood/proc/add_event(datum/source, category, type, param) //Category will override any events in the same category, should be unique unless the event is based on the same thing like hunger.
@@ -288,5 +301,40 @@
remove_temp_moods()
setSanity(initial(sanity))
/datum/component/mood/proc/on_mob_action_skill_mod(mob/source, list/skill_args, list/mod_values)
var/datum/skill/S = GLOB.skill_datums[skill_args[ACTION_SKILL_MOD_SKILL]]
if(!(S.skill_flags & SKILL_USE_MOOD))
return
var/debuff = 1 - (SANITY_DISTURBED - sanity) * MOOD_INSANITY_MALUS
mod_values[MOD_VALUES_SKILL_MOD] *= skill_args[ACTION_SKILL_MOD_IS_MULTI] ? debuff : 1/debuff
/datum/component/mood/proc/on_item_action_skills_mod(mob/source, list/skill_args, list/mod_values)
if(skill_args[ITEM_SKILLS_MOD_BAD_FLAGS] & SKILL_USE_MOOD)
return
var/divisor = mod_values[MOD_VALUES_ITEM_SKILLS_DIV]
if(!divisor)
return
var/obj/item/I = skill_args[ITEM_SKILLS_MOD_ITEM]
var/list/L = mod_values[MOD_VALUES_ITEM_SKILLS_CHECKED]
var/skills_len = length(L)
var/affected_skills = skills_len
for(var/k in L)
var/datum/skill/S = k
var/our_flags = I.used_skills[S.type]|S.skill_flags
if(!(our_flags & SKILL_USE_MOOD))
affected_skills--
if(!affected_skills)
return
var/debuff = 1 - (SANITY_DISTURBED - sanity) * MOOD_INSANITY_MALUS * (affected_skills/skills_len)
mod_values[MOD_VALUES_ITEM_SKILLS_SUM] *= skill_args[ITEM_SKILLS_MOD_IS_MULTI] ? debuff : 1/debuff
/datum/component/mood/proc/on_get_skill_affinity(mob/source, skill_path, list/return_value)
var/datum/skill/S = GLOB.skill_datums[skill_path]
if(!S || !(S.skill_flags & SKILL_TRAIN_MOOD))
return
return_value[1] *= SKILL_AFFINITY_MOOD_BONUS
#undef SLIGHT_INSANITY_PEN
#undef MINOR_INSANITY_PEN
#undef MAJOR_INSANITY_PEN
#undef MOOD_INSANITY_MALUS
+6 -6
View File
@@ -12,7 +12,7 @@
var/list/datum/nanite_program/programs = list()
var/max_programs = NANITE_PROGRAM_LIMIT
var/list/datum/nanite_program/protocol/protocols = list() ///Separate list of protocol programs, to avoid looping through the whole programs list when cheking for conflicts
var/list/datum/nanite_program/protocol/protocols = list() ///Separate list of protocol programs, to avoid looping through the whole programs list when checking for conflicts
var/start_time = 0 ///Timestamp to when the nanites were first inserted in the host
var/stealth = FALSE //if TRUE, does not appear on HUDs and health scans
var/diagnostics = TRUE //if TRUE, displays program list when scanned by nanite scanners
@@ -175,7 +175,7 @@
return (nanite_volume > 0)
/datum/component/nanites/proc/adjust_nanites(datum/source, amount)
nanite_volume = CLAMP(nanite_volume + amount, 0, max_nanites)
nanite_volume = clamp(nanite_volume + amount, 0, max_nanites)
if(nanite_volume <= 0) //oops we ran out
qdel(src)
@@ -187,7 +187,7 @@
if(remove || stealth)
return //bye icon
var/nanite_percent = (nanite_volume / max_nanites) * 100
nanite_percent = CLAMP(CEILING(nanite_percent, 10), 10, 100)
nanite_percent = clamp(CEILING(nanite_percent, 10), 10, 100)
holder.icon_state = "nanites[nanite_percent]"
/datum/component/nanites/proc/on_emp(datum/source, severity)
@@ -249,13 +249,13 @@
return FALSE
/datum/component/nanites/proc/set_volume(datum/source, amount)
nanite_volume = CLAMP(amount, 0, max_nanites)
nanite_volume = clamp(amount, 0, max_nanites)
/datum/component/nanites/proc/set_max_volume(datum/source, amount)
max_nanites = max(1, max_nanites)
/datum/component/nanites/proc/set_cloud(datum/source, amount)
cloud_id = CLAMP(amount, 0, 100)
cloud_id = clamp(amount, 0, 100)
/datum/component/nanites/proc/set_cloud_sync(datum/source, method)
switch(method)
@@ -267,7 +267,7 @@
cloud_active = TRUE
/datum/component/nanites/proc/set_safety(datum/source, amount)
safety_threshold = CLAMP(amount, 0, max_nanites)
safety_threshold = clamp(amount, 0, max_nanites)
/datum/component/nanites/proc/set_regen(datum/source, amount)
regen_rate = amount

Some files were not shown because too many files have changed in this diff Show More