Merge branch 'master' into upstream-merge-33246
This commit is contained in:
+16
-13
@@ -94,19 +94,22 @@
|
||||
#define BANTYPE_ANY_JOB 9 //used to remove jobbans
|
||||
|
||||
//Admin Permissions
|
||||
#define R_BUILDMODE 1
|
||||
#define R_ADMIN 2
|
||||
#define R_BAN 4
|
||||
#define R_FUN 8
|
||||
#define R_SERVER 16
|
||||
#define R_DEBUG 32
|
||||
#define R_POSSESS 64
|
||||
#define R_PERMISSIONS 128
|
||||
#define R_STEALTH 256
|
||||
#define R_POLL 512
|
||||
#define R_VAREDIT 1024
|
||||
#define R_SOUNDS 2048
|
||||
#define R_SPAWN 4096
|
||||
#define R_BUILDMODE 0x1
|
||||
#define R_ADMIN 0x2
|
||||
#define R_BAN 0x4
|
||||
#define R_FUN 0x8
|
||||
#define R_SERVER 0x10
|
||||
#define R_DEBUG 0x20
|
||||
#define R_POSSESS 0x40
|
||||
#define R_PERMISSIONS 0x80
|
||||
#define R_STEALTH 0x100
|
||||
#define R_POLL 0x200
|
||||
#define R_VAREDIT 0x400
|
||||
#define R_SOUNDS 0x800
|
||||
#define R_SPAWN 0x1000
|
||||
#define R_AUTOLOGIN 0x2000
|
||||
|
||||
#define R_DEFAULT R_AUTOLOGIN
|
||||
|
||||
#if DM_VERSION > 512
|
||||
#error Remove the flag below , its been long enough
|
||||
|
||||
@@ -12,6 +12,12 @@
|
||||
|
||||
//ATMOS
|
||||
//stuff you should probably leave well alone!
|
||||
#define R_IDEAL_GAS_EQUATION 8.31 //kPa*L/(K*mol)
|
||||
#define ONE_ATMOSPHERE 101.325 //kPa
|
||||
#define T0C 273.15 // 0degC
|
||||
#define T20C 293.15 // 20degC
|
||||
#define TCMB 2.7 // -270.3degC
|
||||
|
||||
#define MOLES_CELLSTANDARD (ONE_ATMOSPHERE*CELL_VOLUME/(T20C*R_IDEAL_GAS_EQUATION)) //moles in a 2.5 m^3 cell at 101.325 Pa and 20 degC
|
||||
#define M_CELL_WITH_RATIO (MOLES_CELLSTANDARD * 0.005) //compared against for superconductivity
|
||||
#define O2STANDARD 0.21 //percentage of oxygen in a normal mixture of air
|
||||
|
||||
+17
-15
@@ -17,8 +17,9 @@
|
||||
#define DIAG_TRACK_HUD "13"// Mech tracking beacon
|
||||
#define DIAG_AIRLOCK_HUD "14"//Airlock shock overlay
|
||||
#define DIAG_PATH_HUD "15"//Bot path indicators
|
||||
#define GLAND_HUD "16"//Gland indicators for abductors
|
||||
//for antag huds. these are used at the /mob level
|
||||
#define ANTAG_HUD "16"
|
||||
#define ANTAG_HUD "17"
|
||||
|
||||
//by default everything in the hud_list of an atom is an image
|
||||
//a value in hud_list with one of these will change that behavior
|
||||
@@ -32,21 +33,22 @@
|
||||
#define DATA_HUD_MEDICAL_ADVANCED 4
|
||||
#define DATA_HUD_DIAGNOSTIC_BASIC 5
|
||||
#define DATA_HUD_DIAGNOSTIC_ADVANCED 6
|
||||
#define DATA_HUD_ABDUCTOR 7
|
||||
//antag HUD defines
|
||||
#define ANTAG_HUD_CULT 7
|
||||
#define ANTAG_HUD_REV 8
|
||||
#define ANTAG_HUD_OPS 9
|
||||
#define ANTAG_HUD_WIZ 10
|
||||
#define ANTAG_HUD_SHADOW 11
|
||||
#define ANTAG_HUD_TRAITOR 12
|
||||
#define ANTAG_HUD_NINJA 13
|
||||
#define ANTAG_HUD_CHANGELING 14
|
||||
#define ANTAG_HUD_ABDUCTOR 15
|
||||
#define ANTAG_HUD_DEVIL 16
|
||||
#define ANTAG_HUD_SINTOUCHED 17
|
||||
#define ANTAG_HUD_SOULLESS 18
|
||||
#define ANTAG_HUD_CLOCKWORK 19
|
||||
#define ANTAG_HUD_BROTHER 20
|
||||
#define ANTAG_HUD_CULT 8
|
||||
#define ANTAG_HUD_REV 9
|
||||
#define ANTAG_HUD_OPS 10
|
||||
#define ANTAG_HUD_WIZ 11
|
||||
#define ANTAG_HUD_SHADOW 12
|
||||
#define ANTAG_HUD_TRAITOR 13
|
||||
#define ANTAG_HUD_NINJA 14
|
||||
#define ANTAG_HUD_CHANGELING 15
|
||||
#define ANTAG_HUD_ABDUCTOR 16
|
||||
#define ANTAG_HUD_DEVIL 17
|
||||
#define ANTAG_HUD_SINTOUCHED 18
|
||||
#define ANTAG_HUD_SOULLESS 19
|
||||
#define ANTAG_HUD_CLOCKWORK 20
|
||||
#define ANTAG_HUD_BROTHER 21
|
||||
|
||||
// Notification action types
|
||||
#define NOTIFY_JUMP "jump"
|
||||
|
||||
@@ -61,6 +61,8 @@
|
||||
#define COMSIG_ITEM_ATTACK "item_attack" //from base of obj/item/attack(): (/mob/living/target, /mob/living/user)
|
||||
#define COMSIG_ITEM_ATTACK_SELF "item_attack_self" //from base of obj/item/attack_self(): (/mob)
|
||||
#define COMSIG_ITEM_ATTACK_OBJ "item_attack_obj" //from base of obj/item/attack_obj(): (/obj, /mob)
|
||||
#define COMSIG_ITEM_EQUIPPED "item_equip" //from base of obj/item/equipped(): (/mob/equipper, slot)
|
||||
#define COMSIG_ITEM_DROPPED "item_drop" //from base of obj/item/dropped(): (/mob/dropper)
|
||||
|
||||
// /obj/item/clothing signals
|
||||
#define COMSIG_SHOES_STEP_ACTION "shoes_step_action" //from base of obj/item/clothing/shoes/proc/step_action(): ()
|
||||
@@ -77,7 +79,6 @@
|
||||
#define COMSIG_MACHINE_PROCESS "machine_process" //from machinery subsystem fire(): ()
|
||||
#define COMSIG_MACHINE_PROCESS_ATMOS "machine_process_atmos" //from air subsystem process_atmos_machinery(): ()
|
||||
|
||||
|
||||
// /mob/living/carbon/human signals
|
||||
#define COMSIG_HUMAN_MELEE_UNARMED_ATTACK "human_melee_unarmed_attack" //from mob/living/carbon/human/UnarmedAttack(): (atom/target)
|
||||
#define COMSIG_HUMAN_MELEE_UNARMED_ATTACKBY "human_melee_unarmed_attackby" //from mob/living/carbon/human/UnarmedAttack(): (mob/living/carbon/human/attacker)
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
//config files
|
||||
#define CONFIG_DEF(X) /datum/config_entry/##X { resident_file = CURRENT_RESIDENT_FILE }; /datum/config_entry/##X
|
||||
#define CONFIG_GET(X) global.config.Get(/datum/config_entry/##X)
|
||||
#define CONFIG_SET(X, Y) global.config.Set(/datum/config_entry/##X, ##Y)
|
||||
#define CONFIG_TWEAK(X) /datum/config_entry/##X
|
||||
|
||||
#define CONFIG_MAPS_FILE "maps.txt"
|
||||
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#define INVESTIGATE_TELESCI "telesci"
|
||||
#define INVESTIGATE_WIRES "wires"
|
||||
#define INVESTIGATE_PORTAL "portals"
|
||||
#define INVESTIGATE_RESEARCH "research"
|
||||
#define INVESTIGATE_HALLUCINATIONS "hallucinations"
|
||||
#define INVESTIGATE_RADIATION "radiation"
|
||||
#define INVESTIGATE_EXONET "exonet"
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
#define PI 3.1415
|
||||
#define SPEED_OF_LIGHT 3e8 //not exact but hey!
|
||||
#define SPEED_OF_LIGHT_SQ 9e+16
|
||||
#define INFINITY 1e31 //closer then enough
|
||||
|
||||
//atmos
|
||||
#define R_IDEAL_GAS_EQUATION 8.31 //kPa*L/(K*mol)
|
||||
#define ONE_ATMOSPHERE 101.325 //kPa
|
||||
#define T0C 273.15 // 0degC
|
||||
#define T20C 293.15 // 20degC
|
||||
#define TCMB 2.7 // -270.3degC
|
||||
|
||||
#define SHORT_REAL_LIMIT 16777216
|
||||
|
||||
//"fancy" math for calculating time in ms from tick_usage percentage and the length of ticks
|
||||
//percent_of_tick_used * (ticklag * 100(to convert to ms)) / 100(percent ratio)
|
||||
//collapsed to percent_of_tick_used * tick_lag
|
||||
#define TICK_DELTA_TO_MS(percent_of_tick_used) ((percent_of_tick_used) * world.tick_lag)
|
||||
#define TICK_USAGE_TO_MS(starting_tickusage) (TICK_DELTA_TO_MS(TICK_USAGE_REAL - starting_tickusage))
|
||||
|
||||
#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))
|
||||
#define MIDNIGHT_ROLLOVER_CHECK ( GLOB.rollovercheck_last_timeofday != world.timeofday ? update_midnight_rollover() : GLOB.midnight_rollovers )
|
||||
@@ -0,0 +1,209 @@
|
||||
// Credits to Nickr5 for the useful procs I've taken from his library resource.
|
||||
// This file is quadruple wrapped for your pleasure
|
||||
// (
|
||||
|
||||
#define NUM_E 2.71828183
|
||||
#define NUM_SQRT2 1.41421356
|
||||
|
||||
#define PI 3.1415
|
||||
#define SPEED_OF_LIGHT 3e8 //not exact but hey!
|
||||
#define SPEED_OF_LIGHT_SQ 9e+16
|
||||
#define INFINITY 1e31 //closer then enough
|
||||
|
||||
#define SHORT_REAL_LIMIT 16777216
|
||||
|
||||
//"fancy" math for calculating time in ms from tick_usage percentage and the length of ticks
|
||||
//percent_of_tick_used * (ticklag * 100(to convert to ms)) / 100(percent ratio)
|
||||
//collapsed to percent_of_tick_used * tick_lag
|
||||
#define TICK_DELTA_TO_MS(percent_of_tick_used) ((percent_of_tick_used) * world.tick_lag)
|
||||
#define TICK_USAGE_TO_MS(starting_tickusage) (TICK_DELTA_TO_MS(TICK_USAGE_REAL - starting_tickusage))
|
||||
|
||||
#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))
|
||||
#define MIDNIGHT_ROLLOVER_CHECK ( GLOB.rollovercheck_last_timeofday != world.timeofday ? update_midnight_rollover() : GLOB.midnight_rollovers )
|
||||
|
||||
#define SIGN(x) ( (x)!=0 ? (x) / abs(x) : 0 )
|
||||
|
||||
#define CEILING(x, y) ( -round(-(x) / (y)) * (y) )
|
||||
|
||||
// round() acts like floor(x, 1) by default but can't handle other values
|
||||
#define FLOOR(x, y) ( round((x) / (y)) * (y) )
|
||||
|
||||
#define CLAMP(CLVALUE,CLMIN,CLMAX) ( max( (CLMIN), min((CLVALUE), (CLMAX)) ) )
|
||||
|
||||
// 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) ( min == max ? min : (val) - (round(((val) - (min))/((max) - (min))) * ((max) - (min))) )
|
||||
|
||||
// Real modulus that handles decimals
|
||||
#define MODULUS(x, y) ( (x) - (y) * round((x) / (y)) )
|
||||
|
||||
// Tangent
|
||||
#define TAN(x) (sin(x) / cos(x))
|
||||
|
||||
// Cotangent
|
||||
#define COT(x) (1 / TAN(x))
|
||||
|
||||
// Secant
|
||||
#define SEC(x) (1 / cos(x))
|
||||
|
||||
// Cosecant
|
||||
#define CSC(x) (1 / sin(x))
|
||||
|
||||
#define ATAN2(x, y) ( !(x) && !(y) ? 0 : (y) >= 0 ? arccos((x) / sqrt((x)*(x) + (y)*(y))) : -arccos((x) / sqrt((x)*(x) + (y)*(y))) )
|
||||
|
||||
// Greatest Common Divisor - Euclid's algorithm
|
||||
/proc/Gcd(a, b)
|
||||
return b ? Gcd(b, (a) % (b)) : a
|
||||
|
||||
// Least Common Multiple
|
||||
#define Lcm(a, b) (abs(a) / Gcd(a, b) * abs(b))
|
||||
|
||||
#define INVERSE(x) ( 1/(x) )
|
||||
|
||||
// Used for calculating the radioactive strength falloff
|
||||
#define INVERSE_SQUARE(initial_strength,cur_distance,initial_distance) ( (initial_strength)*((initial_distance)**2/(cur_distance)**2) )
|
||||
|
||||
#define ISABOUTEQUAL(a, b, deviation) (deviation ? abs((a) - (b)) <= deviation : abs((a) - (b)) <= 0.1)
|
||||
|
||||
#define ISEVEN(x) (x % 2 == 0)
|
||||
|
||||
#define ISODD(x) (x % 2 != 0)
|
||||
|
||||
// Returns true if val is from min to max, inclusive.
|
||||
#define ISINRANGE(val, min, max) (min <= val && val <= max)
|
||||
|
||||
// Same as above, exclusive.
|
||||
#define ISINRANGE_EX(val, min, max) (min < val && val > max)
|
||||
|
||||
#define ISINTEGER(x) (round(x) == x)
|
||||
|
||||
#define ISMULTIPLE(x, y) ((x) % (y) == 0)
|
||||
|
||||
// Performs a linear interpolation between a and b.
|
||||
// Note that amount=0 returns a, amount=1 returns b, and
|
||||
// amount=0.5 returns the mean of a and b.
|
||||
#define LERP(a, b, amount) (amount ? ((a) + ((b) - (a)) * (amount)) : ((a) + ((b) - (a)) * 0.5)
|
||||
|
||||
// Returns the nth root of x.
|
||||
#define ROOT(n, x) ((x) ** (1 / (n)))
|
||||
|
||||
// The quadratic formula. Returns a list with the solutions, or an empty list
|
||||
// if they are imaginary.
|
||||
/proc/SolveQuadratic(a, b, c)
|
||||
ASSERT(a)
|
||||
. = list()
|
||||
var/d = b*b - 4 * a * c
|
||||
var/bottom = 2 * a
|
||||
if(d < 0)
|
||||
return
|
||||
var/root = sqrt(d)
|
||||
. += (-b + root) / bottom
|
||||
if(!d)
|
||||
return
|
||||
. += (-b - root) / bottom
|
||||
|
||||
#define TODEGREES(radians) ((radians) * 57.2957795)
|
||||
|
||||
#define TORADIANS(degrees) ((degrees) * 0.0174532925)
|
||||
|
||||
// Will filter out extra rotations and negative rotations
|
||||
// E.g: 540 becomes 180. -180 becomes 180.
|
||||
#define SIMPLIFY_DEGREES(degrees) (MODULUS((degrees), 360))
|
||||
|
||||
#define GET_ANGLE_OF_INCIDENCE(face, input) (MODULUS((face) - (input), 360))
|
||||
|
||||
//A logarithm that converts an integer to a number scaled between 0 and 1.
|
||||
//Currently, this is used for hydroponics-produce sprite transforming, but could be useful for other transform functions.
|
||||
#define TRANSFORM_USING_VARIABLE(input, max) ( sin((90*(input))/(max))**2 )
|
||||
|
||||
//converts a uniform distributed random number into a normal distributed one
|
||||
//since this method produces two random numbers, one is saved for subsequent calls
|
||||
//(making the cost negligble for every second call)
|
||||
//This will return +/- decimals, situated about mean with standard deviation stddev
|
||||
//68% chance that the number is within 1stddev
|
||||
//95% chance that the number is within 2stddev
|
||||
//98% chance that the number is within 3stddev...etc
|
||||
#define ACCURACY 10000
|
||||
/proc/gaussian(mean, stddev)
|
||||
var/static/gaussian_next
|
||||
var/R1;var/R2;var/working
|
||||
if(gaussian_next != null)
|
||||
R1 = gaussian_next
|
||||
gaussian_next = null
|
||||
else
|
||||
do
|
||||
R1 = rand(-ACCURACY,ACCURACY)/ACCURACY
|
||||
R2 = rand(-ACCURACY,ACCURACY)/ACCURACY
|
||||
working = R1*R1 + R2*R2
|
||||
while(working >= 1 || working==0)
|
||||
working = sqrt(-2 * log(working) / working)
|
||||
R1 *= working
|
||||
gaussian_next = R2 * working
|
||||
return (mean + stddev * R1)
|
||||
#undef ACCURACY
|
||||
|
||||
/proc/mouse_angle_from_client(client/client)
|
||||
var/list/mouse_control = params2list(client.mouseParams)
|
||||
if(mouse_control["screen-loc"] && client)
|
||||
var/list/screen_loc_params = splittext(mouse_control["screen-loc"], ",")
|
||||
var/list/screen_loc_X = splittext(screen_loc_params[1],":")
|
||||
var/list/screen_loc_Y = splittext(screen_loc_params[2],":")
|
||||
var/x = (text2num(screen_loc_X[1]) * 32 + text2num(screen_loc_X[2]) - 32)
|
||||
var/y = (text2num(screen_loc_Y[1]) * 32 + text2num(screen_loc_Y[2]) - 32)
|
||||
var/list/screenview = getviewsize(client.view)
|
||||
var/screenviewX = screenview[1] * world.icon_size
|
||||
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))
|
||||
return angle
|
||||
|
||||
/proc/get_turf_in_angle(angle, turf/starting, increments)
|
||||
var/pixel_x = 0
|
||||
var/pixel_y = 0
|
||||
for(var/i in 1 to increments)
|
||||
pixel_x += sin(angle)+16*sin(angle)*2
|
||||
pixel_y += cos(angle)+16*cos(angle)*2
|
||||
var/new_x = starting.x
|
||||
var/new_y = starting.y
|
||||
while(pixel_x > 16)
|
||||
pixel_x -= 32
|
||||
new_x++
|
||||
while(pixel_x < -16)
|
||||
pixel_x += 32
|
||||
new_x--
|
||||
while(pixel_y > 16)
|
||||
pixel_y -= 32
|
||||
new_y++
|
||||
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)
|
||||
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
|
||||
/proc/get_overlap(x1, y1, x2, y2, x3, y3, x4, y4)
|
||||
var/list/region_x1 = list()
|
||||
var/list/region_y1 = list()
|
||||
var/list/region_x2 = list()
|
||||
var/list/region_y2 = list()
|
||||
|
||||
// These loops create loops filled with x/y values that the boundaries inhabit
|
||||
// ex: list(5, 6, 7, 8, 9)
|
||||
for(var/i in min(x1, x2) to max(x1, x2))
|
||||
region_x1["[i]"] = TRUE
|
||||
for(var/i in min(y1, y2) to max(y1, y2))
|
||||
region_y1["[i]"] = TRUE
|
||||
for(var/i in min(x3, x4) to max(x3, x4))
|
||||
region_x2["[i]"] = TRUE
|
||||
for(var/i in min(y3, y4) to max(y3, y4))
|
||||
region_y2["[i]"] = TRUE
|
||||
|
||||
return list(region_x1 & region_x2, region_y1 & region_y2)
|
||||
|
||||
// )
|
||||
@@ -484,6 +484,9 @@ GLOBAL_LIST_INIT(ghost_others_options, list(GHOST_OTHERS_SIMPLE, GHOST_OTHERS_DE
|
||||
#define SYRINGE_DRAW 0
|
||||
#define SYRINGE_INJECT 1
|
||||
|
||||
#define RESEARCH_MATERIAL_RECLAMATION_ID "0"
|
||||
|
||||
|
||||
//gold slime core spawning
|
||||
#define NO_SPAWN 0
|
||||
#define HOSTILE_SPAWN 1
|
||||
|
||||
@@ -0,0 +1,61 @@
|
||||
|
||||
//RDSCREEN screens
|
||||
#define RDSCREEN_MENU 0
|
||||
#define RDSCREEN_TECHDISK 1
|
||||
#define RDSCREEN_DESIGNDISK 20
|
||||
#define RDSCREEN_DESIGNDISK_UPLOAD 21
|
||||
#define RDSCREEN_DECONSTRUCT 3
|
||||
#define RDSCREEN_PROTOLATHE 40
|
||||
#define RDSCREEN_PROTOLATHE_MATERIALS 41
|
||||
#define RDSCREEN_PROTOLATHE_CHEMICALS 42
|
||||
#define RDSCREEN_PROTOLATHE_CATEGORY_VIEW 43
|
||||
#define RDSCREEN_PROTOLATHE_SEARCH 44
|
||||
#define RDSCREEN_IMPRINTER 50
|
||||
#define RDSCREEN_IMPRINTER_MATERIALS 51
|
||||
#define RDSCREEN_IMPRINTER_CHEMICALS 52
|
||||
#define RDSCREEN_IMPRINTER_CATEGORY_VIEW 53
|
||||
#define RDSCREEN_IMPRINTER_SEARCH 54
|
||||
#define RDSCREEN_SETTINGS 61
|
||||
#define RDSCREEN_DEVICE_LINKING 62
|
||||
#define RDSCREEN_TECHWEB 70
|
||||
#define RDSCREEN_TECHWEB_NODEVIEW 71
|
||||
#define RDSCREEN_TECHWEB_DESIGNVIEW 72
|
||||
|
||||
#define RDSCREEN_NOBREAK "<NO_HTML_BREAK>"
|
||||
|
||||
#define RDSCREEN_TEXT_NO_PROTOLATHE "<div><h3>No Protolathe Linked!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_IMPRINTER "<div><h3>No Circuit Imprinter Linked!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_DECONSTRUCT "<div><h3>No Deconstructive Analyzer Linked!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_TDISK "<div><h3>No Technology Disk Inserted!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_DDISK "<div><h3>No Design Disk Inserted!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_SNODE "<div><h3>No Technology Node Selected!</h3></div><br>"
|
||||
#define RDSCREEN_TEXT_NO_SDESIGN "<div><h3>No Design Selected!</h3></div><br>"
|
||||
|
||||
#define RDSCREEN_UI_LATHE_CHECK if(!linked_lathe) { return RDSCREEN_TEXT_NO_PROTOLATHE }
|
||||
#define RDSCREEN_UI_IMPRINTER_CHECK if(!linked_imprinter) { return RDSCREEN_TEXT_NO_IMPRINTER }
|
||||
#define RDSCREEN_UI_DECONSTRUCT_CHECK if(!linked_destroy) { return RDSCREEN_TEXT_NO_DECONSTRUCT }
|
||||
#define RDSCREEN_UI_TDISK_CHECK if(!t_disk) { return RDSCREEN_TEXT_NO_TDISK }
|
||||
#define RDSCREEN_UI_DDISK_CHECK if(!d_disk) { return RDSCREEN_TEXT_NO_DDISK }
|
||||
#define RDSCREEN_UI_SNODE_CHECK if(!selected_node) { return RDSCREEN_TEXT_NO_SNODE }
|
||||
#define RDSCREEN_UI_SDESIGN_CHECK if(!selected_design) { return RDSCREEN_TEXT_NO_SDESIGN }
|
||||
|
||||
#define DEPLATHE_SCREEN_PRIMARY 1
|
||||
#define DEPLATHE_SCREEN_SEARCH 2
|
||||
#define DEPLATHE_SCREEN_MATERIALS 3
|
||||
#define DEPLATHE_SCREEN_CHEMICALS 4
|
||||
|
||||
#define DEPPRINTER_SCREEN_PRIMARY 1
|
||||
#define DEPPRINTER_SCREEN_SEARCH 2
|
||||
#define DEPPRINTER_SCREEN_MATERIALS 3
|
||||
#define DEPPRINTER_SCREEN_CHEMICALS 4
|
||||
|
||||
#define DEPARTMENTAL_FLAG_SECURITY 1
|
||||
#define DEPARTMENTAL_FLAG_MEDICAL 2
|
||||
#define DEPARTMENTAL_FLAG_CARGO 4
|
||||
#define DEPARTMENTAL_FLAG_SCIENCE 8
|
||||
#define DEPARTMENTAL_FLAG_ENGINEERING 16
|
||||
#define DEPARTMENTAL_FLAG_SERVICE 32
|
||||
#define DEPARTMENTAL_FLAG_ALL 64 //NO THIS DOESN'T ALLOW YOU TO PRINT EVERYTHING, IT'S FOR ALL DEPARTMENTS!
|
||||
//#define DEPARTMENTAL_FLAG_MINING 128
|
||||
|
||||
#define DESIGN_ID_IGNORE "IGNORE_THIS_DESIGN"
|
||||
@@ -0,0 +1,8 @@
|
||||
#define SERVER_TOOLS_EXTERNAL_CONFIGURATION
|
||||
#define SERVER_TOOLS_DEFINE_AND_SET_GLOBAL(Name, Value) GLOBAL_VAR_INIT(##Name, ##Value); GLOBAL_PROTECT(##Name)
|
||||
#define SERVER_TOOLS_READ_GLOBAL(Name) GLOB.##Name
|
||||
#define SERVER_TOOLS_WRITE_GLOBAL(Name, Value) GLOB.##Name = ##Value
|
||||
#define SERVER_TOOLS_WORLD_ANNOUNCE(message) to_chat(world, "<span class='boldannounce'>[html_encode(##message)]</span>")
|
||||
#define SERVER_TOOLS_LOG(message) log_world("SERVICE: [##message]")
|
||||
#define SERVER_TOOLS_NOTIFY_ADMINS(event) message_admins(##event)
|
||||
#define SERVER_TOOLS_CLIENT_COUNT GLOB.clients.len
|
||||
@@ -1,4 +1,5 @@
|
||||
// /tg/station 13 server tools API v3.1.0.2
|
||||
// /tg/station 13 server tools API
|
||||
#define SERVICE_API_VERSION_STRING "3.2.0.1"
|
||||
|
||||
//CONFIGURATION
|
||||
//use this define if you want to do configuration outside of this file
|
||||
@@ -10,19 +11,19 @@
|
||||
|
||||
//create a global variable named `Name` and set it to `Value`
|
||||
//These globals must not be modifiable from anywhere outside of the server tools
|
||||
#define SERVER_TOOLS_DEFINE_AND_SET_GLOBAL(Name, Value) GLOBAL_VAR_INIT(##Name, ##Value); GLOBAL_PROTECT(##Name)
|
||||
#define SERVER_TOOLS_DEFINE_AND_SET_GLOBAL(Name, Value)
|
||||
//Read the value in the global variable `Name`
|
||||
#define SERVER_TOOLS_READ_GLOBAL(Name) GLOB.##Name
|
||||
#define SERVER_TOOLS_READ_GLOBAL(Name)
|
||||
//Set the value in the global variable `Name` to `Value`
|
||||
#define SERVER_TOOLS_WRITE_GLOBAL(Name, Value) GLOB.##Name = ##Value
|
||||
#define SERVER_TOOLS_WRITE_GLOBAL(Name, Value)
|
||||
//display an announcement `message` from the server to all players
|
||||
#define SERVER_TOOLS_WORLD_ANNOUNCE(message) to_chat(world, "<span class='boldannounce'>[html_encode(##message)]</span>")
|
||||
#define SERVER_TOOLS_WORLD_ANNOUNCE(message)
|
||||
//Write a string `message` to a server log
|
||||
#define SERVER_TOOLS_LOG(message) log_world("SERVICE: [##message]")
|
||||
#define SERVER_TOOLS_LOG(message)
|
||||
//Notify current in-game administrators of a string `event`
|
||||
#define SERVER_TOOLS_NOTIFY_ADMINS(event) message_admins(##event)
|
||||
#define SERVER_TOOLS_NOTIFY_ADMINS(event)
|
||||
//The current amount of connected clients
|
||||
#define SERVER_TOOLS_CLIENT_COUNT GLOB.clients.len
|
||||
#define SERVER_TOOLS_CLIENT_COUNT
|
||||
#endif
|
||||
|
||||
//Required hooks:
|
||||
@@ -64,16 +65,15 @@
|
||||
|
||||
//IMPLEMENTATION
|
||||
|
||||
#define SERVICE_API_VERSION_STRING "3.1.0.2"
|
||||
|
||||
#define REBOOT_MODE_NORMAL 0
|
||||
#define REBOOT_MODE_HARD 1
|
||||
#define REBOOT_MODE_SHUTDOWN 2
|
||||
|
||||
#define SERVICE_WORLD_PARAM "server_service"
|
||||
#define SERVICE_VERSION_PARAM "server_service_version"
|
||||
#define SERVICE_INSTANCE_PARAM "server_instance"
|
||||
#define SERVICE_PR_TEST_JSON "prtestjob.json"
|
||||
#define SERVICE_INTERFACE_DLL "TGServiceInterface.dll"
|
||||
#define SERVICE_INTERFACE_DLL "TGDreamDaemonBridge.dll"
|
||||
#define SERVICE_INTERFACE_FUNCTION "DDEntryPoint"
|
||||
|
||||
#define SERVICE_CMD_HARD_REBOOT "hard_reboot"
|
||||
@@ -98,11 +98,12 @@
|
||||
#define SERVICE_REQUEST_WORLD_REBOOT "worldreboot"
|
||||
#define SERVICE_REQUEST_API_VERSION "api_ver"
|
||||
|
||||
#define SERVICE_RETURN_SUCCESS "SUCCESS"
|
||||
|
||||
/*
|
||||
The MIT License
|
||||
|
||||
Copyright (c) 2011 Dominic Tarr
|
||||
|
||||
Copyright (c) 2017 Jordan Brown
|
||||
Permission is hereby granted, free of charge,
|
||||
to any person obtaining a copy of this software and
|
||||
associated documentation files (the "Software"), to
|
||||
|
||||
@@ -23,8 +23,8 @@
|
||||
#define FLIGHTSUIT_PROCESSING_FULL 1
|
||||
|
||||
#define INITIALIZATION_INSSATOMS 0 //New should not call Initialize
|
||||
#define INITIALIZATION_INNEW_MAPLOAD 1 //New should call Initialize(TRUE)
|
||||
#define INITIALIZATION_INNEW_REGULAR 2 //New should call Initialize(FALSE)
|
||||
#define INITIALIZATION_INNEW_MAPLOAD 2 //New should call Initialize(TRUE)
|
||||
#define INITIALIZATION_INNEW_REGULAR 1 //New should call Initialize(FALSE)
|
||||
|
||||
#define INITIALIZE_HINT_NORMAL 0 //Nothing happens
|
||||
#define INITIALIZE_HINT_LATELOAD 1 //Call LateInitialize
|
||||
@@ -46,15 +46,16 @@
|
||||
#define INIT_ORDER_DBCORE 18
|
||||
#define INIT_ORDER_BLACKBOX 17
|
||||
#define INIT_ORDER_SERVER_MAINT 16
|
||||
#define INIT_ORDER_EVENTS 15
|
||||
#define INIT_ORDER_JOBS 14
|
||||
#define INIT_ORDER_TICKER 13
|
||||
#define INIT_ORDER_MAPPING 12
|
||||
#define INIT_ORDER_ATOMS 11
|
||||
#define INIT_ORDER_NETWORKS 10
|
||||
#define INIT_ORDER_LANGUAGE 9
|
||||
#define INIT_ORDER_MACHINES 8
|
||||
#define INIT_ORDER_CIRCUIT 7
|
||||
#define INIT_ORDER_RESEARCH 15
|
||||
#define INIT_ORDER_EVENTS 14
|
||||
#define INIT_ORDER_JOBS 13
|
||||
#define INIT_ORDER_TICKER 12
|
||||
#define INIT_ORDER_MAPPING 11
|
||||
#define INIT_ORDER_ATOMS 10
|
||||
#define INIT_ORDER_NETWORKS 9
|
||||
#define INIT_ORDER_LANGUAGE 8
|
||||
#define INIT_ORDER_MACHINES 7
|
||||
#define INIT_ORDER_CIRCUIT 6
|
||||
#define INIT_ORDER_TIMER 1
|
||||
#define INIT_ORDER_DEFAULT 0
|
||||
#define INIT_ORDER_AIR -1
|
||||
|
||||
@@ -43,8 +43,8 @@
|
||||
//Returns list element or null. Should prevent "index out of bounds" error.
|
||||
/proc/listgetindex(list/L, index)
|
||||
if(LAZYLEN(L))
|
||||
if(isnum(index) && IsInteger(index))
|
||||
if(IsInRange(index,1,L.len))
|
||||
if(isnum(index) && ISINTEGER(index))
|
||||
if(ISINRANGE(index,1,L.len))
|
||||
return L[index]
|
||||
else if(index in L)
|
||||
return L[index]
|
||||
|
||||
@@ -72,11 +72,6 @@
|
||||
var/datum/material/D = new path()
|
||||
GLOB.materials_list[D.id] = D
|
||||
|
||||
//Techs
|
||||
for(var/path in subtypesof(/datum/tech))
|
||||
var/datum/tech/D = new path()
|
||||
GLOB.tech_list[D.id] = D
|
||||
|
||||
//Emotes
|
||||
for(var/path in subtypesof(/datum/emote))
|
||||
var/datum/emote/E = new path()
|
||||
|
||||
@@ -1,257 +0,0 @@
|
||||
// Credits to Nickr5 for the useful procs I've taken from his library resource.
|
||||
|
||||
GLOBAL_VAR_INIT(E, 2.71828183)
|
||||
GLOBAL_VAR_INIT(Sqrt2, 1.41421356)
|
||||
|
||||
// List of square roots for the numbers 1-100.
|
||||
GLOBAL_LIST_INIT(sqrtTable, list(1, 1, 1, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5,
|
||||
5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7, 7,
|
||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8,
|
||||
8, 8, 8, 8, 8, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 10))
|
||||
|
||||
/proc/sign(x)
|
||||
return x!=0?x/abs(x):0
|
||||
|
||||
/proc/Atan2(x, y)
|
||||
if(!x && !y)
|
||||
return 0
|
||||
var/a = arccos(x / sqrt(x*x + y*y))
|
||||
return y >= 0 ? a : -a
|
||||
|
||||
/proc/Ceiling(x, y=1)
|
||||
return -round(-x / y) * y
|
||||
|
||||
/proc/Floor(x, y=1)
|
||||
return round(x / y) * y
|
||||
|
||||
#define Clamp(CLVALUE,CLMIN,CLMAX) ( max( (CLMIN), min((CLVALUE), (CLMAX)) ) )
|
||||
|
||||
/proc/Modulus(x, y) //Byond's modulus doesn't work with decimals.
|
||||
return x - y * round(x / y)
|
||||
|
||||
// cotangent
|
||||
/proc/Cot(x)
|
||||
return 1 / Tan(x)
|
||||
|
||||
// cosecant
|
||||
/proc/Csc(x)
|
||||
return 1 / sin(x)
|
||||
|
||||
/proc/Default(a, b)
|
||||
return a ? a : b
|
||||
|
||||
// Greatest Common Divisor - Euclid's algorithm
|
||||
/proc/Gcd(a, b)
|
||||
return b ? Gcd(b, a % b) : a
|
||||
|
||||
/proc/Inverse(x)
|
||||
return 1 / x
|
||||
|
||||
#define InverseSquareLaw(initial_strength,cur_distance,initial_distance) (initial_strength*(initial_distance**2/cur_distance**2))
|
||||
|
||||
/proc/IsAboutEqual(a, b, deviation = 0.1)
|
||||
return abs(a - b) <= deviation
|
||||
|
||||
/proc/IsEven(x)
|
||||
return x % 2 == 0
|
||||
|
||||
// Returns true if val is from min to max, inclusive.
|
||||
/proc/IsInRange(val, min, max)
|
||||
return min <= val && val <= max
|
||||
|
||||
/proc/IsInteger(x)
|
||||
return round(x) == x
|
||||
|
||||
/proc/IsOdd(x)
|
||||
return !IsEven(x)
|
||||
|
||||
/proc/IsMultiple(x, y)
|
||||
return x % y == 0
|
||||
|
||||
// Least Common Multiple
|
||||
/proc/Lcm(a, b)
|
||||
return abs(a) / Gcd(a, b) * abs(b)
|
||||
|
||||
// Performs a linear interpolation between a and b.
|
||||
// Note that amount=0 returns a, amount=1 returns b, and
|
||||
// amount=0.5 returns the mean of a and b.
|
||||
/proc/Lerp(a, b, amount = 0.5)
|
||||
return a + (b - a) * amount
|
||||
|
||||
//Calculates the sum of a list of numbers.
|
||||
/proc/Sum(var/list/data)
|
||||
. = 0
|
||||
for(var/val in data)
|
||||
.+= val
|
||||
|
||||
//Calculates the mean of a list of numbers.
|
||||
/proc/Mean(var/list/data)
|
||||
. = Sum(data) / (data.len)
|
||||
|
||||
|
||||
// Returns the nth root of x.
|
||||
/proc/Root(n, x)
|
||||
return x ** (1 / n)
|
||||
|
||||
// secant
|
||||
/proc/Sec(x)
|
||||
return 1 / cos(x)
|
||||
|
||||
// The quadratic formula. Returns a list with the solutions, or an empty list
|
||||
// if they are imaginary.
|
||||
/proc/SolveQuadratic(a, b, c)
|
||||
ASSERT(a)
|
||||
. = list()
|
||||
var/d = b*b - 4 * a * c
|
||||
var/bottom = 2 * a
|
||||
if(d < 0)
|
||||
return
|
||||
var/root = sqrt(d)
|
||||
. += (-b + root) / bottom
|
||||
if(!d)
|
||||
return
|
||||
. += (-b - root) / bottom
|
||||
|
||||
// tangent
|
||||
/proc/Tan(x)
|
||||
return sin(x) / cos(x)
|
||||
|
||||
/proc/ToDegrees(radians)
|
||||
// 180 / Pi
|
||||
return radians * 57.2957795
|
||||
|
||||
/proc/ToRadians(degrees)
|
||||
// Pi / 180
|
||||
return degrees * 0.0174532925
|
||||
|
||||
// Will filter out extra rotations and negative rotations
|
||||
// E.g: 540 becomes 180. -180 becomes 180.
|
||||
/proc/SimplifyDegrees(degrees)
|
||||
degrees = degrees % 360
|
||||
if(degrees < 0)
|
||||
degrees += 360
|
||||
return degrees
|
||||
|
||||
// min is inclusive, max is exclusive
|
||||
/proc/Wrap(val, min, max)
|
||||
var/d = max - min
|
||||
var/t = round((val - min) / d)
|
||||
return val - (t * d)
|
||||
|
||||
#define NORM_ROT(rot) ((((rot % 360) + (rot - round(rot, 1))) >= 0) ? ((rot % 360) + (rot - round(rot, 1))) : (((rot % 360) + (rot - round(rot, 1))) + 360))
|
||||
|
||||
/proc/get_angle_of_incidence(face_angle, angle_in, auto_normalize = TRUE)
|
||||
|
||||
var/angle_in_s = NORM_ROT(angle_in)
|
||||
var/face_angle_s = NORM_ROT(face_angle)
|
||||
var/incidence = face_angle_s - angle_in_s
|
||||
var/incidence_s = incidence
|
||||
while(incidence_s < -90)
|
||||
incidence_s += 180
|
||||
while(incidence_s > 90)
|
||||
incidence_s -= 180
|
||||
if(auto_normalize)
|
||||
return incidence_s
|
||||
else
|
||||
return incidence
|
||||
|
||||
//A logarithm that converts an integer to a number scaled between 0 and 1 (can be tweaked to be higher).
|
||||
//Currently, this is used for hydroponics-produce sprite transforming, but could be useful for other transform functions.
|
||||
/proc/TransformUsingVariable(input, inputmaximum, scaling_modifier = 0)
|
||||
|
||||
var/inputToDegrees = (input/inputmaximum)*180 //Converting from a 0 -> 100 scale to a 0 -> 180 scale. The 0 -> 180 scale corresponds to degrees
|
||||
var/size_factor = ((-cos(inputToDegrees) +1) /2) //returns a value from 0 to 1
|
||||
|
||||
return size_factor + scaling_modifier //scale mod of 0 results in a number from 0 to 1. A scale modifier of +0.5 returns 0.5 to 1.5
|
||||
|
||||
//converts a uniform distributed random number into a normal distributed one
|
||||
//since this method produces two random numbers, one is saved for subsequent calls
|
||||
//(making the cost negligble for every second call)
|
||||
//This will return +/- decimals, situated about mean with standard deviation stddev
|
||||
//68% chance that the number is within 1stddev
|
||||
//95% chance that the number is within 2stddev
|
||||
//98% chance that the number is within 3stddev...etc
|
||||
#define ACCURACY 10000
|
||||
/proc/gaussian(mean, stddev)
|
||||
var/static/gaussian_next
|
||||
var/R1;var/R2;var/working
|
||||
if(gaussian_next != null)
|
||||
R1 = gaussian_next
|
||||
gaussian_next = null
|
||||
else
|
||||
do
|
||||
R1 = rand(-ACCURACY,ACCURACY)/ACCURACY
|
||||
R2 = rand(-ACCURACY,ACCURACY)/ACCURACY
|
||||
working = R1*R1 + R2*R2
|
||||
while(working >= 1 || working==0)
|
||||
working = sqrt(-2 * log(working) / working)
|
||||
R1 *= working
|
||||
gaussian_next = R2 * working
|
||||
return (mean + stddev * R1)
|
||||
#undef ACCURACY
|
||||
|
||||
/proc/mouse_angle_from_client(client/client)
|
||||
var/list/mouse_control = params2list(client.mouseParams)
|
||||
if(mouse_control["screen-loc"] && client)
|
||||
var/list/screen_loc_params = splittext(mouse_control["screen-loc"], ",")
|
||||
var/list/screen_loc_X = splittext(screen_loc_params[1],":")
|
||||
var/list/screen_loc_Y = splittext(screen_loc_params[2],":")
|
||||
var/x = (text2num(screen_loc_X[1]) * 32 + text2num(screen_loc_X[2]) - 32)
|
||||
var/y = (text2num(screen_loc_Y[1]) * 32 + text2num(screen_loc_Y[2]) - 32)
|
||||
var/list/screenview = getviewsize(client.view)
|
||||
var/screenviewX = screenview[1] * world.icon_size
|
||||
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 = NORM_ROT(Atan2(y - oy, x - ox))
|
||||
return angle
|
||||
|
||||
/proc/get_turf_in_angle(angle, turf/starting, increments)
|
||||
var/pixel_x = 0
|
||||
var/pixel_y = 0
|
||||
for(var/i in 1 to increments)
|
||||
pixel_x += sin(angle)+16*sin(angle)*2
|
||||
pixel_y += cos(angle)+16*cos(angle)*2
|
||||
var/new_x = starting.x
|
||||
var/new_y = starting.y
|
||||
while(pixel_x > 16)
|
||||
pixel_x -= 32
|
||||
new_x++
|
||||
while(pixel_x < -16)
|
||||
pixel_x += 32
|
||||
new_x--
|
||||
while(pixel_y > 16)
|
||||
pixel_y -= 32
|
||||
new_y++
|
||||
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)
|
||||
return locate(new_x, new_y, starting.z)
|
||||
|
||||
/proc/round_down(num)
|
||||
if(round(num) != num)
|
||||
return round(num--)
|
||||
else return num
|
||||
|
||||
//proc/get_overlap()
|
||||
// Returns a list where [1] is all x values and [2] is all y values that overlap between the given pair of rectangles
|
||||
/proc/get_overlap(x1, y1, x2, y2, x3, y3, x4, y4)
|
||||
var/list/region_x1 = list()
|
||||
var/list/region_y1 = list()
|
||||
var/list/region_x2 = list()
|
||||
var/list/region_y2 = list()
|
||||
|
||||
// These loops create loops filled with x/y values that the boundaries inhabit
|
||||
// ex: list(5, 6, 7, 8, 9)
|
||||
for(var/i in min(x1, x2) to max(x1, x2))
|
||||
region_x1["[i]"] = TRUE
|
||||
for(var/i in min(y1, y2) to max(y1, y2))
|
||||
region_y1["[i]"] = TRUE
|
||||
for(var/i in min(x3, x4) to max(x3, x4))
|
||||
region_x2["[i]"] = TRUE
|
||||
for(var/i in min(y3, y4) to max(y3, y4))
|
||||
region_y2["[i]"] = TRUE
|
||||
|
||||
return list(region_x1 & region_x2, region_y1 & region_y2)
|
||||
@@ -121,9 +121,6 @@ GLOBAL_VAR(command_name)
|
||||
return new_station_name
|
||||
|
||||
/proc/syndicate_name()
|
||||
var/static/syndicate_name
|
||||
if (syndicate_name)
|
||||
return syndicate_name
|
||||
|
||||
var/name = ""
|
||||
|
||||
@@ -146,8 +143,7 @@ GLOBAL_VAR(command_name)
|
||||
else
|
||||
name += pick("-", "*", "")
|
||||
name += pick("Tech", "Sun", "Co", "Tek", "X", "Inc", "Gen", "Star", "Dyne", "Code", "Hive")
|
||||
|
||||
syndicate_name = name
|
||||
|
||||
return name
|
||||
|
||||
|
||||
|
||||
+14
-14
@@ -1,14 +1,14 @@
|
||||
// Ensure the frequency is within bounds of what it should be sending/recieving at
|
||||
/proc/sanitize_frequency(frequency, free = FALSE)
|
||||
. = round(frequency)
|
||||
if(free)
|
||||
. = Clamp(frequency, MIN_FREE_FREQ, MAX_FREE_FREQ)
|
||||
else
|
||||
. = Clamp(frequency, MIN_FREQ, MAX_FREQ)
|
||||
if(!(. % 2)) // Ensure the last digit is an odd number
|
||||
. += 1
|
||||
|
||||
// Format frequency by moving the decimal.
|
||||
/proc/format_frequency(frequency)
|
||||
frequency = text2num(frequency)
|
||||
return "[round(frequency / 10)].[frequency % 10]"
|
||||
// Ensure the frequency is within bounds of what it should be sending/recieving at
|
||||
/proc/sanitize_frequency(frequency, free = FALSE)
|
||||
. = round(frequency)
|
||||
if(free)
|
||||
. = CLAMP(frequency, MIN_FREE_FREQ, MAX_FREE_FREQ)
|
||||
else
|
||||
. = CLAMP(frequency, MIN_FREQ, MAX_FREQ)
|
||||
if(!(. % 2)) // Ensure the last digit is an odd number
|
||||
. += 1
|
||||
|
||||
// Format frequency by moving the decimal.
|
||||
/proc/format_frequency(frequency)
|
||||
frequency = text2num(frequency)
|
||||
return "[round(frequency / 10)].[frequency % 10]"
|
||||
|
||||
@@ -60,7 +60,7 @@ GLOBAL_VAR_INIT(rollovercheck_last_timeofday, 0)
|
||||
if(!second)
|
||||
return "0 seconds"
|
||||
if(second >= 60)
|
||||
minute = round_down(second/60)
|
||||
minute = FLOOR(second/60, 1)
|
||||
second = round(second - (minute*60), 0.1)
|
||||
second_rounded = TRUE
|
||||
if(second) //check if we still have seconds remaining to format, or if everything went into minute.
|
||||
@@ -91,7 +91,7 @@ GLOBAL_VAR_INIT(rollovercheck_last_timeofday, 0)
|
||||
if(!minute)
|
||||
return "[second]"
|
||||
if(minute >= 60)
|
||||
hour = round_down(minute/60,1)
|
||||
hour = FLOOR(minute/60, 1)
|
||||
minute = (minute - (hour*60))
|
||||
if(minute) //alot simpler from here since you don't have to worry about fractions
|
||||
if(minute != 1)
|
||||
@@ -114,7 +114,7 @@ GLOBAL_VAR_INIT(rollovercheck_last_timeofday, 0)
|
||||
if(!hour)
|
||||
return "[minute][second]"
|
||||
if(hour >= 24)
|
||||
day = round_down(hour/24,1)
|
||||
day = FLOOR(hour/24, 1)
|
||||
hour = (hour - (day*24))
|
||||
if(hour)
|
||||
if(hour != 1)
|
||||
|
||||
@@ -117,7 +117,7 @@
|
||||
//Converts an angle (degrees) into an ss13 direction
|
||||
/proc/angle2dir(degree)
|
||||
|
||||
degree = SimplifyDegrees(degree)
|
||||
degree = SIMPLIFY_DEGREES(degree)
|
||||
switch(degree)
|
||||
if(0 to 22.5) //north requires two angle ranges
|
||||
return NORTH
|
||||
|
||||
@@ -147,10 +147,10 @@ Turf and target are separate in case you want to teleport some distance from a t
|
||||
var/line[] = list(locate(px,py,M.z))
|
||||
var/dx=N.x-px //x distance
|
||||
var/dy=N.y-py
|
||||
var/dxabs=abs(dx)//Absolute value of x distance
|
||||
var/dyabs=abs(dy)
|
||||
var/sdx=sign(dx) //Sign of x distance (+ or -)
|
||||
var/sdy=sign(dy)
|
||||
var/dxabs = abs(dx)//Absolute value of x distance
|
||||
var/dyabs = abs(dy)
|
||||
var/sdx = SIGN(dx) //Sign of x distance (+ or -)
|
||||
var/sdy = SIGN(dy)
|
||||
var/x=dxabs>>1 //Counters for steps taken, setting to distance/2
|
||||
var/y=dyabs>>1 //Bit-shifting makes me l33t. It also makes getline() unnessecarrily fast.
|
||||
var/j //Generic integer for counting
|
||||
@@ -953,8 +953,8 @@ GLOBAL_LIST_INIT(WALLITEMS_INVERSE, typecacheof(list(
|
||||
tY = tY[1]
|
||||
tX = splittext(tX[1], ":")
|
||||
tX = tX[1]
|
||||
tX = Clamp(origin.x + text2num(tX) - world.view - 1, 1, world.maxx)
|
||||
tY = Clamp(origin.y + text2num(tY) - world.view - 1, 1, world.maxy)
|
||||
tX = CLAMP(origin.x + text2num(tX) - world.view - 1, 1, world.maxx)
|
||||
tY = CLAMP(origin.y + text2num(tY) - world.view - 1, 1, world.maxy)
|
||||
return locate(tX, tY, tZ)
|
||||
|
||||
/proc/screen_loc2turf(text, turf/origin)
|
||||
@@ -966,8 +966,8 @@ GLOBAL_LIST_INIT(WALLITEMS_INVERSE, typecacheof(list(
|
||||
tX = splittext(tZ[2], "-")
|
||||
tX = text2num(tX[2])
|
||||
tZ = origin.z
|
||||
tX = Clamp(origin.x + 7 - tX, 1, world.maxx)
|
||||
tY = Clamp(origin.y + 7 - tY, 1, world.maxy)
|
||||
tX = CLAMP(origin.x + 7 - tX, 1, world.maxx)
|
||||
tY = CLAMP(origin.y + 7 - tY, 1, world.maxy)
|
||||
return locate(tX, tY, tZ)
|
||||
|
||||
/proc/IsValidSrc(datum/D)
|
||||
@@ -1272,7 +1272,7 @@ proc/pick_closest_path(value, list/matches = get_fancy_list_of_atom_types())
|
||||
. = 0
|
||||
var/i = DS2TICKS(initial_delay)
|
||||
do
|
||||
. += Ceiling(i*DELTA_CALC)
|
||||
. += CEILING(i*DELTA_CALC, 1)
|
||||
sleep(i*world.tick_lag*DELTA_CALC)
|
||||
i *= 2
|
||||
while (TICK_USAGE > min(TICK_LIMIT_TO_RUN, Master.current_ticklimit))
|
||||
|
||||
@@ -257,8 +257,8 @@
|
||||
view = world.view
|
||||
|
||||
var/list/viewscales = getviewsize(view)
|
||||
var/countx = Ceiling((viewscales[1]/2)/(480/world.icon_size))+1
|
||||
var/county = Ceiling((viewscales[2]/2)/(480/world.icon_size))+1
|
||||
var/countx = CEILING((viewscales[1]/2)/(480/world.icon_size), 1)+1
|
||||
var/county = CEILING((viewscales[2]/2)/(480/world.icon_size), 1)+1
|
||||
var/list/new_overlays = new
|
||||
for(var/x in -countx to countx)
|
||||
for(var/y in -county to county)
|
||||
|
||||
+277
-277
@@ -1,277 +1,277 @@
|
||||
/obj/screen/robot
|
||||
icon = 'icons/mob/screen_cyborg.dmi'
|
||||
|
||||
/obj/screen/robot/module
|
||||
name = "cyborg module"
|
||||
icon_state = "nomod"
|
||||
|
||||
/obj/screen/robot/Click()
|
||||
if(isobserver(usr))
|
||||
return 1
|
||||
|
||||
/obj/screen/robot/module/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
if(R.module.type != /obj/item/robot_module)
|
||||
R.hud_used.toggle_show_robot_modules()
|
||||
return 1
|
||||
R.pick_module()
|
||||
|
||||
/obj/screen/robot/module1
|
||||
name = "module1"
|
||||
icon_state = "inv1"
|
||||
|
||||
/obj/screen/robot/module1/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(1)
|
||||
|
||||
/obj/screen/robot/module2
|
||||
name = "module2"
|
||||
icon_state = "inv2"
|
||||
|
||||
/obj/screen/robot/module2/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(2)
|
||||
|
||||
/obj/screen/robot/module3
|
||||
name = "module3"
|
||||
icon_state = "inv3"
|
||||
|
||||
/obj/screen/robot/module3/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(3)
|
||||
|
||||
/obj/screen/robot/radio
|
||||
name = "radio"
|
||||
icon_state = "radio"
|
||||
|
||||
/obj/screen/robot/radio/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.radio.interact(R)
|
||||
|
||||
/obj/screen/robot/store
|
||||
name = "store"
|
||||
icon_state = "store"
|
||||
|
||||
/obj/screen/robot/store/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.uneq_active()
|
||||
|
||||
/obj/screen/robot/lamp
|
||||
name = "headlamp"
|
||||
icon_state = "lamp0"
|
||||
|
||||
/obj/screen/robot/lamp/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.control_headlamp()
|
||||
|
||||
/obj/screen/robot/thrusters
|
||||
name = "ion thrusters"
|
||||
icon_state = "ionpulse0"
|
||||
|
||||
/obj/screen/robot/thrusters/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_ionpulse()
|
||||
|
||||
/datum/hud/robot
|
||||
ui_style_icon = 'icons/mob/screen_cyborg.dmi'
|
||||
|
||||
/datum/hud/robot/New(mob/owner, ui_style = 'icons/mob/screen_cyborg.dmi')
|
||||
..()
|
||||
var/mob/living/silicon/robot/mymobR = mymob
|
||||
var/obj/screen/using
|
||||
|
||||
using = new/obj/screen/language_menu
|
||||
using.screen_loc = ui_borg_language_menu
|
||||
static_inventory += using
|
||||
|
||||
//Radio
|
||||
using = new /obj/screen/robot/radio()
|
||||
using.screen_loc = ui_borg_radio
|
||||
static_inventory += using
|
||||
|
||||
//Module select
|
||||
using = new /obj/screen/robot/module1()
|
||||
using.screen_loc = ui_inv1
|
||||
static_inventory += using
|
||||
mymobR.inv1 = using
|
||||
|
||||
using = new /obj/screen/robot/module2()
|
||||
using.screen_loc = ui_inv2
|
||||
static_inventory += using
|
||||
mymobR.inv2 = using
|
||||
|
||||
using = new /obj/screen/robot/module3()
|
||||
using.screen_loc = ui_inv3
|
||||
static_inventory += using
|
||||
mymobR.inv3 = using
|
||||
|
||||
//End of module select
|
||||
|
||||
//Photography stuff
|
||||
using = new /obj/screen/ai/image_take()
|
||||
using.screen_loc = ui_borg_camera
|
||||
static_inventory += using
|
||||
|
||||
using = new /obj/screen/ai/image_view()
|
||||
using.screen_loc = ui_borg_album
|
||||
static_inventory += using
|
||||
|
||||
//Sec/Med HUDs
|
||||
using = new /obj/screen/ai/sensors()
|
||||
using.screen_loc = ui_borg_sensor
|
||||
static_inventory += using
|
||||
|
||||
//Headlamp control
|
||||
using = new /obj/screen/robot/lamp()
|
||||
using.screen_loc = ui_borg_lamp
|
||||
static_inventory += using
|
||||
mymobR.lamp_button = using
|
||||
|
||||
//Thrusters
|
||||
using = new /obj/screen/robot/thrusters()
|
||||
using.screen_loc = ui_borg_thrusters
|
||||
static_inventory += using
|
||||
mymobR.thruster_button = using
|
||||
|
||||
//Intent
|
||||
action_intent = new /obj/screen/act_intent/robot()
|
||||
action_intent.icon_state = mymob.a_intent
|
||||
static_inventory += action_intent
|
||||
|
||||
//Health
|
||||
healths = new /obj/screen/healths/robot()
|
||||
infodisplay += healths
|
||||
|
||||
//Installed Module
|
||||
mymobR.hands = new /obj/screen/robot/module()
|
||||
mymobR.hands.screen_loc = ui_borg_module
|
||||
static_inventory += mymobR.hands
|
||||
|
||||
//Store
|
||||
module_store_icon = new /obj/screen/robot/store()
|
||||
module_store_icon.screen_loc = ui_borg_store
|
||||
|
||||
pull_icon = new /obj/screen/pull()
|
||||
pull_icon.icon = 'icons/mob/screen_cyborg.dmi'
|
||||
pull_icon.update_icon(mymob)
|
||||
pull_icon.screen_loc = ui_borg_pull
|
||||
hotkeybuttons += pull_icon
|
||||
|
||||
|
||||
zone_select = new /obj/screen/zone_sel/robot()
|
||||
zone_select.update_icon(mymob)
|
||||
static_inventory += zone_select
|
||||
|
||||
|
||||
/datum/hud/proc/toggle_show_robot_modules()
|
||||
if(!iscyborg(mymob))
|
||||
return
|
||||
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
R.shown_robot_modules = !R.shown_robot_modules
|
||||
update_robot_modules_display()
|
||||
|
||||
/datum/hud/proc/update_robot_modules_display(mob/viewer)
|
||||
if(!iscyborg(mymob))
|
||||
return
|
||||
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
var/mob/screenmob = viewer || R
|
||||
|
||||
if(!R.module)
|
||||
return
|
||||
|
||||
if(!R.client)
|
||||
return
|
||||
|
||||
if(R.shown_robot_modules && screenmob.hud_used.hud_shown)
|
||||
//Modules display is shown
|
||||
screenmob.client.screen += module_store_icon //"store" icon
|
||||
|
||||
if(!R.module.modules)
|
||||
to_chat(usr, "<span class='danger'>Selected module has no modules to select</span>")
|
||||
return
|
||||
|
||||
if(!R.robot_modules_background)
|
||||
return
|
||||
|
||||
var/display_rows = Ceiling(length(R.module.get_inactive_modules()) / 8)
|
||||
R.robot_modules_background.screen_loc = "CENTER-4:16,SOUTH+1:7 to CENTER+3:16,SOUTH+[display_rows]:7"
|
||||
screenmob.client.screen += R.robot_modules_background
|
||||
|
||||
var/x = -4 //Start at CENTER-4,SOUTH+1
|
||||
var/y = 1
|
||||
|
||||
for(var/atom/movable/A in R.module.get_inactive_modules())
|
||||
//Module is not currently active
|
||||
screenmob.client.screen += A
|
||||
if(x < 0)
|
||||
A.screen_loc = "CENTER[x]:16,SOUTH+[y]:7"
|
||||
else
|
||||
A.screen_loc = "CENTER+[x]:16,SOUTH+[y]:7"
|
||||
A.layer = ABOVE_HUD_LAYER
|
||||
A.plane = ABOVE_HUD_PLANE
|
||||
|
||||
x++
|
||||
if(x == 4)
|
||||
x = -4
|
||||
y++
|
||||
|
||||
else
|
||||
//Modules display is hidden
|
||||
screenmob.client.screen -= module_store_icon //"store" icon
|
||||
|
||||
for(var/atom/A in R.module.get_inactive_modules())
|
||||
//Module is not currently active
|
||||
screenmob.client.screen -= A
|
||||
R.shown_robot_modules = 0
|
||||
screenmob.client.screen -= R.robot_modules_background
|
||||
|
||||
/mob/living/silicon/robot/create_mob_hud()
|
||||
if(client && !hud_used)
|
||||
hud_used = new /datum/hud/robot(src)
|
||||
|
||||
|
||||
/datum/hud/robot/persistent_inventory_update(mob/viewer)
|
||||
if(!mymob)
|
||||
return
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
var/mob/screenmob = viewer || R
|
||||
|
||||
if(screenmob.hud_used)
|
||||
if(screenmob.hud_used.hud_shown)
|
||||
for(var/i in 1 to R.held_items.len)
|
||||
var/obj/item/I = R.held_items[i]
|
||||
if(I)
|
||||
switch(i)
|
||||
if(1)
|
||||
I.screen_loc = ui_inv1
|
||||
if(2)
|
||||
I.screen_loc = ui_inv2
|
||||
if(3)
|
||||
I.screen_loc = ui_inv3
|
||||
else
|
||||
return
|
||||
screenmob.client.screen += I
|
||||
else
|
||||
for(var/obj/item/I in R.held_items)
|
||||
screenmob.client.screen -= I
|
||||
/obj/screen/robot
|
||||
icon = 'icons/mob/screen_cyborg.dmi'
|
||||
|
||||
/obj/screen/robot/module
|
||||
name = "cyborg module"
|
||||
icon_state = "nomod"
|
||||
|
||||
/obj/screen/robot/Click()
|
||||
if(isobserver(usr))
|
||||
return 1
|
||||
|
||||
/obj/screen/robot/module/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
if(R.module.type != /obj/item/robot_module)
|
||||
R.hud_used.toggle_show_robot_modules()
|
||||
return 1
|
||||
R.pick_module()
|
||||
|
||||
/obj/screen/robot/module1
|
||||
name = "module1"
|
||||
icon_state = "inv1"
|
||||
|
||||
/obj/screen/robot/module1/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(1)
|
||||
|
||||
/obj/screen/robot/module2
|
||||
name = "module2"
|
||||
icon_state = "inv2"
|
||||
|
||||
/obj/screen/robot/module2/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(2)
|
||||
|
||||
/obj/screen/robot/module3
|
||||
name = "module3"
|
||||
icon_state = "inv3"
|
||||
|
||||
/obj/screen/robot/module3/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_module(3)
|
||||
|
||||
/obj/screen/robot/radio
|
||||
name = "radio"
|
||||
icon_state = "radio"
|
||||
|
||||
/obj/screen/robot/radio/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.radio.interact(R)
|
||||
|
||||
/obj/screen/robot/store
|
||||
name = "store"
|
||||
icon_state = "store"
|
||||
|
||||
/obj/screen/robot/store/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.uneq_active()
|
||||
|
||||
/obj/screen/robot/lamp
|
||||
name = "headlamp"
|
||||
icon_state = "lamp0"
|
||||
|
||||
/obj/screen/robot/lamp/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.control_headlamp()
|
||||
|
||||
/obj/screen/robot/thrusters
|
||||
name = "ion thrusters"
|
||||
icon_state = "ionpulse0"
|
||||
|
||||
/obj/screen/robot/thrusters/Click()
|
||||
if(..())
|
||||
return
|
||||
var/mob/living/silicon/robot/R = usr
|
||||
R.toggle_ionpulse()
|
||||
|
||||
/datum/hud/robot
|
||||
ui_style_icon = 'icons/mob/screen_cyborg.dmi'
|
||||
|
||||
/datum/hud/robot/New(mob/owner, ui_style = 'icons/mob/screen_cyborg.dmi')
|
||||
..()
|
||||
var/mob/living/silicon/robot/mymobR = mymob
|
||||
var/obj/screen/using
|
||||
|
||||
using = new/obj/screen/language_menu
|
||||
using.screen_loc = ui_borg_language_menu
|
||||
static_inventory += using
|
||||
|
||||
//Radio
|
||||
using = new /obj/screen/robot/radio()
|
||||
using.screen_loc = ui_borg_radio
|
||||
static_inventory += using
|
||||
|
||||
//Module select
|
||||
using = new /obj/screen/robot/module1()
|
||||
using.screen_loc = ui_inv1
|
||||
static_inventory += using
|
||||
mymobR.inv1 = using
|
||||
|
||||
using = new /obj/screen/robot/module2()
|
||||
using.screen_loc = ui_inv2
|
||||
static_inventory += using
|
||||
mymobR.inv2 = using
|
||||
|
||||
using = new /obj/screen/robot/module3()
|
||||
using.screen_loc = ui_inv3
|
||||
static_inventory += using
|
||||
mymobR.inv3 = using
|
||||
|
||||
//End of module select
|
||||
|
||||
//Photography stuff
|
||||
using = new /obj/screen/ai/image_take()
|
||||
using.screen_loc = ui_borg_camera
|
||||
static_inventory += using
|
||||
|
||||
using = new /obj/screen/ai/image_view()
|
||||
using.screen_loc = ui_borg_album
|
||||
static_inventory += using
|
||||
|
||||
//Sec/Med HUDs
|
||||
using = new /obj/screen/ai/sensors()
|
||||
using.screen_loc = ui_borg_sensor
|
||||
static_inventory += using
|
||||
|
||||
//Headlamp control
|
||||
using = new /obj/screen/robot/lamp()
|
||||
using.screen_loc = ui_borg_lamp
|
||||
static_inventory += using
|
||||
mymobR.lamp_button = using
|
||||
|
||||
//Thrusters
|
||||
using = new /obj/screen/robot/thrusters()
|
||||
using.screen_loc = ui_borg_thrusters
|
||||
static_inventory += using
|
||||
mymobR.thruster_button = using
|
||||
|
||||
//Intent
|
||||
action_intent = new /obj/screen/act_intent/robot()
|
||||
action_intent.icon_state = mymob.a_intent
|
||||
static_inventory += action_intent
|
||||
|
||||
//Health
|
||||
healths = new /obj/screen/healths/robot()
|
||||
infodisplay += healths
|
||||
|
||||
//Installed Module
|
||||
mymobR.hands = new /obj/screen/robot/module()
|
||||
mymobR.hands.screen_loc = ui_borg_module
|
||||
static_inventory += mymobR.hands
|
||||
|
||||
//Store
|
||||
module_store_icon = new /obj/screen/robot/store()
|
||||
module_store_icon.screen_loc = ui_borg_store
|
||||
|
||||
pull_icon = new /obj/screen/pull()
|
||||
pull_icon.icon = 'icons/mob/screen_cyborg.dmi'
|
||||
pull_icon.update_icon(mymob)
|
||||
pull_icon.screen_loc = ui_borg_pull
|
||||
hotkeybuttons += pull_icon
|
||||
|
||||
|
||||
zone_select = new /obj/screen/zone_sel/robot()
|
||||
zone_select.update_icon(mymob)
|
||||
static_inventory += zone_select
|
||||
|
||||
|
||||
/datum/hud/proc/toggle_show_robot_modules()
|
||||
if(!iscyborg(mymob))
|
||||
return
|
||||
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
R.shown_robot_modules = !R.shown_robot_modules
|
||||
update_robot_modules_display()
|
||||
|
||||
/datum/hud/proc/update_robot_modules_display(mob/viewer)
|
||||
if(!iscyborg(mymob))
|
||||
return
|
||||
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
var/mob/screenmob = viewer || R
|
||||
|
||||
if(!R.module)
|
||||
return
|
||||
|
||||
if(!R.client)
|
||||
return
|
||||
|
||||
if(R.shown_robot_modules && screenmob.hud_used.hud_shown)
|
||||
//Modules display is shown
|
||||
screenmob.client.screen += module_store_icon //"store" icon
|
||||
|
||||
if(!R.module.modules)
|
||||
to_chat(usr, "<span class='danger'>Selected module has no modules to select</span>")
|
||||
return
|
||||
|
||||
if(!R.robot_modules_background)
|
||||
return
|
||||
|
||||
var/display_rows = CEILING(length(R.module.get_inactive_modules()) / 8, 1)
|
||||
R.robot_modules_background.screen_loc = "CENTER-4:16,SOUTH+1:7 to CENTER+3:16,SOUTH+[display_rows]:7"
|
||||
screenmob.client.screen += R.robot_modules_background
|
||||
|
||||
var/x = -4 //Start at CENTER-4,SOUTH+1
|
||||
var/y = 1
|
||||
|
||||
for(var/atom/movable/A in R.module.get_inactive_modules())
|
||||
//Module is not currently active
|
||||
screenmob.client.screen += A
|
||||
if(x < 0)
|
||||
A.screen_loc = "CENTER[x]:16,SOUTH+[y]:7"
|
||||
else
|
||||
A.screen_loc = "CENTER+[x]:16,SOUTH+[y]:7"
|
||||
A.layer = ABOVE_HUD_LAYER
|
||||
A.plane = ABOVE_HUD_PLANE
|
||||
|
||||
x++
|
||||
if(x == 4)
|
||||
x = -4
|
||||
y++
|
||||
|
||||
else
|
||||
//Modules display is hidden
|
||||
screenmob.client.screen -= module_store_icon //"store" icon
|
||||
|
||||
for(var/atom/A in R.module.get_inactive_modules())
|
||||
//Module is not currently active
|
||||
screenmob.client.screen -= A
|
||||
R.shown_robot_modules = 0
|
||||
screenmob.client.screen -= R.robot_modules_background
|
||||
|
||||
/mob/living/silicon/robot/create_mob_hud()
|
||||
if(client && !hud_used)
|
||||
hud_used = new /datum/hud/robot(src)
|
||||
|
||||
|
||||
/datum/hud/robot/persistent_inventory_update(mob/viewer)
|
||||
if(!mymob)
|
||||
return
|
||||
var/mob/living/silicon/robot/R = mymob
|
||||
|
||||
var/mob/screenmob = viewer || R
|
||||
|
||||
if(screenmob.hud_used)
|
||||
if(screenmob.hud_used.hud_shown)
|
||||
for(var/i in 1 to R.held_items.len)
|
||||
var/obj/item/I = R.held_items[i]
|
||||
if(I)
|
||||
switch(i)
|
||||
if(1)
|
||||
I.screen_loc = ui_inv1
|
||||
if(2)
|
||||
I.screen_loc = ui_inv2
|
||||
if(3)
|
||||
I.screen_loc = ui_inv3
|
||||
else
|
||||
return
|
||||
screenmob.client.screen += I
|
||||
else
|
||||
for(var/obj/item/I in R.held_items)
|
||||
screenmob.client.screen -= I
|
||||
|
||||
@@ -119,9 +119,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"
|
||||
|
||||
@@ -14,7 +14,7 @@
|
||||
|
||||
// Otherwise jump
|
||||
else if(A.loc)
|
||||
loc = get_turf(A)
|
||||
forceMove(get_turf(A))
|
||||
update_parallax_contents()
|
||||
|
||||
/mob/dead/observer/ClickOn(var/atom/A, var/params)
|
||||
|
||||
@@ -62,14 +62,14 @@
|
||||
/mob/living/proc/adjustArousalLoss(amount, updating_arousal=1)
|
||||
if(status_flags & GODMODE || !canbearoused)
|
||||
return 0
|
||||
arousalloss = Clamp(arousalloss + amount, min_arousal, max_arousal)
|
||||
arousalloss = CLAMP(arousalloss + amount, min_arousal, max_arousal)
|
||||
if(updating_arousal)
|
||||
updatearousal()
|
||||
|
||||
/mob/living/proc/setArousalLoss(amount, updating_arousal=1)
|
||||
if(status_flags & GODMODE || !canbearoused)
|
||||
return 0
|
||||
arousalloss = Clamp(amount, min_arousal, max_arousal)
|
||||
arousalloss = CLAMP(amount, min_arousal, max_arousal)
|
||||
if(updating_arousal)
|
||||
updatearousal()
|
||||
|
||||
|
||||
@@ -8,7 +8,6 @@
|
||||
throw_speed = 3
|
||||
throw_range = 5
|
||||
w_class = WEIGHT_CLASS_TINY
|
||||
origin_tech = "biotech=3"
|
||||
var/applied_region = "chest"
|
||||
var/list/add_mutations = list()
|
||||
var/list/remove_mutations = list()
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "lasernew"
|
||||
item_state = "laser"
|
||||
origin_tech = "combat=4;magnets=4"
|
||||
force = 10
|
||||
throwforce = 10
|
||||
ammo_type = list(/obj/item/ammo_casing/energy/lasergun)
|
||||
@@ -22,7 +21,6 @@
|
||||
name = "Laser Carbine"
|
||||
desc = "Beefed up version of a standard laser gun."
|
||||
id = "lasercarbine"
|
||||
req_tech = list("combat" = 5, "magnets" = 5, "powerstorage" = 4)
|
||||
build_type = PROTOLATHE
|
||||
materials = list(MAT_GOLD = 2500, MAT_METAL = 5000, MAT_GLASS = 5000)
|
||||
build_path = /obj/item/gun/energy/laser/carbine/nopin
|
||||
@@ -40,7 +38,6 @@
|
||||
mag_type = /obj/item/ammo_box/magazine/sniper_rounds
|
||||
fire_delay = 50
|
||||
burst_size = 1
|
||||
origin_tech = "combat=7"
|
||||
can_suppress = 0
|
||||
w_class = WEIGHT_CLASS_NORMAL
|
||||
actions_types = list()
|
||||
@@ -60,7 +57,6 @@
|
||||
name = "Syndicate Anti Tank Pistol"
|
||||
desc = "A massively impractical and silly monstrosity of a pistol that fires .50 calliber rounds. The recoil is likely to dislocate a variety of joints without proper bracing."
|
||||
pin = /obj/item/device/firing_pin/implant/pindicate
|
||||
origin_tech = "combat=7;syndicate=6"
|
||||
|
||||
/////////////spinfusor stuff////////////////
|
||||
|
||||
@@ -115,7 +111,6 @@
|
||||
select = 0
|
||||
actions_types = list()
|
||||
casing_ejector = 0
|
||||
origin_tech = "combat=6;magnets=6"
|
||||
|
||||
/obj/item/gun/ballistic/automatic/spinfusor/attackby(obj/item/A, mob/user, params)
|
||||
var/num_loaded = magazine.attackby(A, user, params, 1)
|
||||
@@ -163,7 +158,6 @@
|
||||
icon_state = "x9"
|
||||
item_state = "arg"
|
||||
slot_flags = 0
|
||||
origin_tech = "combat=7;engineering=7"
|
||||
mag_type = /obj/item/ammo_box/magazine/m556 //Uses the m90gl's magazine, just like the NT-ARG
|
||||
fire_sound = 'sound/weapons/gunshot_smg.ogg'
|
||||
can_suppress = 0
|
||||
@@ -194,7 +188,6 @@
|
||||
spread = 90 //MAXIMUM XCOM MEMES (actually that'd be 180 spread)
|
||||
w_class = WEIGHT_CLASS_BULKY
|
||||
weapon_weight = WEAPON_HEAVY
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/datum/design/foam_x9
|
||||
name = "Foam Force X9 Rifle"
|
||||
@@ -254,7 +247,6 @@
|
||||
name = "magpistol magazine (non-lethal disabler)"
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "nlmagmag"
|
||||
origin_tech = "magnets=5"
|
||||
ammo_type = /obj/item/ammo_casing/caseless/anlmags
|
||||
caliber = "mags"
|
||||
max_ammo = 15
|
||||
@@ -264,7 +256,6 @@
|
||||
name = "magpistol magazine (lethal)"
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "smallmagmag"
|
||||
origin_tech = "combat=5"
|
||||
ammo_type = /obj/item/ammo_casing/caseless/amags
|
||||
|
||||
//////the gun itself//////
|
||||
@@ -280,7 +271,6 @@
|
||||
can_suppress = 0
|
||||
casing_ejector = 0
|
||||
fire_delay = 2
|
||||
origin_tech = "combat=4;magnets=4"
|
||||
|
||||
/obj/item/gun/ballistic/automatic/pistol/mag/update_icon()
|
||||
..()
|
||||
@@ -301,7 +291,6 @@
|
||||
name = "Magpistol"
|
||||
desc = "A weapon which fires ferromagnetic slugs."
|
||||
id = "magpisol"
|
||||
req_tech = list("combat" = 5, "magnets" = 6, "powerstorage" = 5)
|
||||
build_type = PROTOLATHE
|
||||
materials = list(MAT_METAL = 7500, MAT_GLASS = 1000, MAT_URANIUM = 1000, MAT_TITANIUM = 5000, MAT_SILVER = 2000)
|
||||
build_path = /obj/item/gun/ballistic/automatic/pistol/mag/nopin
|
||||
@@ -311,7 +300,6 @@
|
||||
name = "Magpistol Magazine"
|
||||
desc = "A 7 round magazine for the Magpistol."
|
||||
id = "mag_magpistol"
|
||||
req_tech = list("combat" = 5, "magnets" = 6, "materials" = 5, "syndicate" = 3)
|
||||
build_type = PROTOLATHE
|
||||
materials = list(MAT_METAL = 4000, MAT_SILVER = 500)
|
||||
build_path = /obj/item/ammo_box/magazine/mmag/small/lethal
|
||||
@@ -321,7 +309,6 @@
|
||||
name = "Magpistol Magazine (Non-Lethal)"
|
||||
desc = "A 7 round non-lethal magazine for the Magpistol."
|
||||
id = "mag_magpistol_nl"
|
||||
req_tech = list("combat" = 5, "magnets" = 6, "materials" = 5)
|
||||
materials = list(MAT_METAL = 3000, MAT_SILVER = 250, MAT_TITANIUM = 250)
|
||||
build_path = /obj/item/ammo_box/magazine/mmag/small
|
||||
|
||||
@@ -354,7 +341,6 @@
|
||||
fire_sound = 'sound/weapons/magpistol.ogg'
|
||||
slot_flags = SLOT_BELT
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/obj/item/ammo_box/foambox/mag
|
||||
name = "ammo box (Magnetic Foam Darts)"
|
||||
@@ -427,7 +413,6 @@
|
||||
name = "magrifle magazine (non-lethal disabler)"
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "mediummagmag"
|
||||
origin_tech = "magnets=6"
|
||||
ammo_type = /obj/item/ammo_casing/caseless/anlmagm
|
||||
caliber = "magm"
|
||||
max_ammo = 27
|
||||
@@ -437,7 +422,6 @@
|
||||
name = "magrifle magazine (lethal)"
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "mediummagmag"
|
||||
origin_tech = "combat=6"
|
||||
ammo_type = /obj/item/ammo_casing/caseless/amagm
|
||||
max_ammo = 21
|
||||
|
||||
@@ -450,7 +434,6 @@
|
||||
icon_state = "magrifle"
|
||||
item_state = "arg"
|
||||
slot_flags = 0
|
||||
origin_tech = "combat=6;engineering=6;magnets=6"
|
||||
mag_type = /obj/item/ammo_box/magazine/mmag
|
||||
fire_sound = 'sound/weapons/magrifle.ogg'
|
||||
can_suppress = 0
|
||||
@@ -470,7 +453,6 @@
|
||||
name = "Magrifle"
|
||||
desc = "An upscaled Magpistol in rifle form."
|
||||
id = "magrifle"
|
||||
req_tech = list("combat" = 7, "magnets" = 7, "powerstorage" = 7)
|
||||
build_type = PROTOLATHE
|
||||
materials = list(MAT_METAL = 10000, MAT_GLASS = 2000, MAT_URANIUM = 2000, MAT_TITANIUM = 10000, MAT_SILVER = 4000, MAT_GOLD = 2000)
|
||||
build_path = /obj/item/gun/ballistic/automatic/magrifle/nopin
|
||||
@@ -480,7 +462,6 @@
|
||||
name = "Magrifle Magazine (Lethal)"
|
||||
desc = "A 15 round magazine for the Magrifle."
|
||||
id = "mag_magrifle"
|
||||
req_tech = list("combat" = 7, "magnets" = 7, "materials" = 5, "syndicate" = 4)
|
||||
build_type = PROTOLATHE
|
||||
materials = list(MAT_METAL = 8000, MAT_SILVER = 1000)
|
||||
build_path = /obj/item/ammo_box/magazine/mmag/lethal
|
||||
@@ -490,7 +471,6 @@
|
||||
name = "Magrifle Magazine (Non-Lethal)"
|
||||
desc = "A 15 round non-lethal magazine for the Magrifle."
|
||||
id = "mag_magrifle_nl"
|
||||
req_tech = list("combat" = 7, "magnets" = 7, "materials" = 5)
|
||||
materials = list(MAT_METAL = 6000, MAT_SILVER = 500, MAT_TITANIUM = 500)
|
||||
build_path = /obj/item/ammo_box/magazine/mmag
|
||||
|
||||
@@ -512,7 +492,6 @@
|
||||
needs_permit = FALSE
|
||||
mag_type = /obj/item/ammo_box/magazine/toy/foamag
|
||||
casing_ejector = FALSE
|
||||
origin_tech = "combat=1;engineering=1;magnets=1"
|
||||
spread = 60
|
||||
w_class = WEIGHT_CLASS_BULKY
|
||||
weapon_weight = WEAPON_HEAVY
|
||||
@@ -598,7 +577,6 @@
|
||||
icon_state = "hyperburst"
|
||||
item_state = "arg"
|
||||
slot_flags = 0
|
||||
origin_tech = "combat=6;engineering=6;magnets=6;syndicate=6"
|
||||
mag_type = /obj/item/ammo_box/magazine/mhyper
|
||||
fire_sound = 'sound/weapons/magburst.ogg'
|
||||
can_suppress = 0
|
||||
@@ -646,7 +624,6 @@
|
||||
charge_delay = 2
|
||||
recoil = 2
|
||||
cell_type = /obj/item/stock_parts/cell/toymagburst
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/obj/item/stock_parts/cell/toymagburst
|
||||
name = "toy mag burst rifle power supply"
|
||||
@@ -669,7 +646,6 @@
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "stealthpistol"
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
origin_tech = "combat=3;materials=3;syndicate=4"
|
||||
mag_type = /obj/item/ammo_box/magazine/m10mm
|
||||
can_suppress = 0
|
||||
fire_sound = 'sound/weapons/gunshot_silenced.ogg'
|
||||
@@ -703,7 +679,6 @@
|
||||
fire_delay = 0
|
||||
spread = 60
|
||||
actions_types = list()
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/obj/item/gun/ballistic/automatic/toy/pistol/stealth/update_icon()
|
||||
..()
|
||||
@@ -805,7 +780,6 @@ obj/item/projectile/bullet/c10mm/soporific
|
||||
name = "flechette magazine (armor piercing)"
|
||||
icon = 'icons/obj/guns/cit_guns.dmi'
|
||||
icon_state = "flechettemag"
|
||||
origin_tech = "combat=5;syndicate=1"
|
||||
ammo_type = /obj/item/ammo_casing/caseless/flechetteap
|
||||
caliber = "flechette"
|
||||
max_ammo = 40
|
||||
@@ -826,7 +800,6 @@ obj/item/projectile/bullet/c10mm/soporific
|
||||
w_class = WEIGHT_CLASS_NORMAL
|
||||
slot_flags = 0
|
||||
/obj/item/device/firing_pin/implant/pindicate
|
||||
origin_tech = "combat=6;materials=2;syndicate=5"
|
||||
mag_type = /obj/item/ammo_box/magazine/flechette/
|
||||
fire_sound = 'sound/weapons/gunshot_smg.ogg'
|
||||
can_suppress = 0
|
||||
@@ -930,7 +903,6 @@ obj/item/projectile/bullet/c10mm/soporific
|
||||
desc = "A toy laser with a classic, retro feel and look. Compatible with existing laser tag systems."
|
||||
ammo_type = list(/obj/item/ammo_casing/energy/laser/raytag)
|
||||
selfcharge = TRUE
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/datum/design/toyray
|
||||
name = "RayTag Gun"
|
||||
@@ -1186,7 +1158,6 @@ obj/item/projectile/bullet/c10mm/soporific
|
||||
mag_type = /obj/item/ammo_box/magazine/toy/pistol
|
||||
can_suppress = FALSE
|
||||
actions_types = list(/datum/action/item_action/pick_color)
|
||||
origin_tech = "combat=1;magnets=1"
|
||||
|
||||
/datum/design/foam_p37
|
||||
name = "Foam Force Mk.37F"
|
||||
@@ -1209,7 +1180,6 @@ obj/item/gun/energy/e_gun/cx
|
||||
lefthand_file = 'icons/mob/citadel/guns_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/citadel/guns_righthand.dmi'
|
||||
ammo_type = list(/obj/item/ammo_casing/energy/disabler, /obj/item/ammo_casing/energy/laser)
|
||||
origin_tech = "combat=4;magnets=3"
|
||||
flight_x_offset = 15
|
||||
flight_y_offset = 10
|
||||
actions_types = list(/datum/action/item_action/pick_color)
|
||||
|
||||
@@ -1,242 +0,0 @@
|
||||
/obj/item/toy/sword/cx
|
||||
name = "\improper DX Non-Euplastic LightSword"
|
||||
desc = "A deluxe toy replica of an energy sword. Realistic visuals and sounds! Ages 8 and up."
|
||||
icon = 'icons/obj/cit_weapons.dmi'
|
||||
icon_state = "cxsword_hilt"
|
||||
item_state = "cxsword"
|
||||
lefthand_file = 'icons/mob/citadel/melee_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/citadel/melee_righthand.dmi'
|
||||
active = FALSE
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
attack_verb = list("poked", "jabbed", "hit")
|
||||
light_color = "#37FFF7"
|
||||
var/light_brightness = 3
|
||||
actions_types = list()
|
||||
|
||||
/obj/item/toy/sword/cx/attack_self(mob/user)
|
||||
active = !( active )
|
||||
|
||||
if (active)
|
||||
to_chat(user, "<span class='notice'>You activate the holographic blade with a press of a button.</span>")
|
||||
playsound(user, 'sound/weapons/nebon.ogg', 50, 1)
|
||||
w_class = WEIGHT_CLASS_BULKY
|
||||
attack_verb = list("slashed", "stabbed", "ravaged")
|
||||
set_light(light_brightness)
|
||||
update_icon()
|
||||
|
||||
else
|
||||
to_chat(user, "<span class='notice'>You deactivate the holographic blade with a press of a button.</span>")
|
||||
playsound(user, 'sound/weapons/neboff.ogg', 50, 1)
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
attack_verb = list("poked", "jabbed", "hit")
|
||||
set_light(0)
|
||||
update_icon()
|
||||
|
||||
for(var/X in actions)
|
||||
var/datum/action/A = X
|
||||
A.UpdateButtonIcon()
|
||||
|
||||
add_fingerprint(user)
|
||||
|
||||
/obj/item/toy/sword/cx/update_icon()
|
||||
var/mutable_appearance/blade_overlay = mutable_appearance('icons/obj/cit_weapons.dmi', "cxsword_blade")
|
||||
var/mutable_appearance/gem_overlay = mutable_appearance('icons/obj/cit_weapons.dmi', "cxsword_gem")
|
||||
|
||||
if(light_color)
|
||||
blade_overlay.color = light_color
|
||||
gem_overlay.color = light_color
|
||||
|
||||
cut_overlays() //So that it doesn't keep stacking overlays non-stop on top of each other
|
||||
|
||||
add_overlay(gem_overlay)
|
||||
|
||||
if(active)
|
||||
add_overlay(blade_overlay)
|
||||
|
||||
if(ismob(loc))
|
||||
var/mob/M = loc
|
||||
M.update_inv_hands()
|
||||
|
||||
/obj/item/toy/sword/cx/AltClick(mob/living/user)
|
||||
if(user.incapacitated() || !istype(user))
|
||||
to_chat(user, "<span class='warning'>You can't do that right now!</span>")
|
||||
return
|
||||
if(!in_range(src, user))
|
||||
return
|
||||
if(user.incapacitated() || !istype(user) || !in_range(src, user))
|
||||
return
|
||||
|
||||
if(alert("Are you sure you want to recolor your blade?", "Confirm Repaint", "Yes", "No") == "Yes")
|
||||
var/energy_color_input = input(usr,"Choose Energy Color") as color|null
|
||||
if(energy_color_input)
|
||||
light_color = sanitize_hexcolor(energy_color_input, desired_format=6, include_crunch=1)
|
||||
update_icon()
|
||||
update_light()
|
||||
|
||||
/obj/item/toy/sword/cx/worn_overlays(isinhands, icon_file)
|
||||
. = ..()
|
||||
if(active)
|
||||
if(isinhands)
|
||||
var/mutable_appearance/blade_inhand = mutable_appearance(icon_file, "cxsword_blade")
|
||||
blade_inhand.color = light_color
|
||||
. += blade_inhand
|
||||
|
||||
/obj/item/toy/sword/cx/attackby(obj/item/W, mob/living/user, params)
|
||||
if(istype(W, /obj/item/toy/sword/cx))
|
||||
if((W.flags_1 & NODROP_1) || (flags_1 & NODROP_1))
|
||||
to_chat(user, "<span class='warning'>\the [flags_1 & NODROP_1 ? src : W] is stuck to your hand, you can't attach it to \the [flags_1 & NODROP_1 ? W : src]!</span>")
|
||||
return
|
||||
else
|
||||
to_chat(user, "<span class='notice'>You combine the two plastic swords, making a single supermassive toy! You're fake-cool.</span>")
|
||||
new /obj/item/twohanded/hypereutactic/toy(user.loc)
|
||||
qdel(W)
|
||||
qdel(src)
|
||||
else
|
||||
return ..()
|
||||
|
||||
/obj/item/toy/sword/cx/examine(mob/user)
|
||||
..()
|
||||
to_chat(user, "<span class='notice'>Alt-click to recolor it.</span>")
|
||||
|
||||
/*///autolathe memes/// I really need to stop doing this and find a proper way of adding in my toys
|
||||
|
||||
/datum/design/toyneb
|
||||
name = "Non-Euplastic Blade"
|
||||
id = "toyneb"
|
||||
build_type = AUTOLATHE
|
||||
materials = list(MAT_METAL = 10000, MAT_GLASS = 1000)
|
||||
build_path = /obj/item/toy/sword/cx
|
||||
category = list("hacked", "Misc")
|
||||
*/ // There, I stopped doing it
|
||||
|
||||
/datum/crafting_recipe/toyneb
|
||||
name = "Non-Euplastic Blade"
|
||||
reqs = list(/obj/item/light/bulb = 1, /obj/item/stack/cable_coil = 1, /obj/item/toy/sword = 1)
|
||||
result = /obj/item/toy/sword/cx
|
||||
category = CAT_MISC
|
||||
|
||||
/*/////////////////////////////////////////////////////////////////////////
|
||||
///////////// The TRUE Energy Sword ///////////////////////////
|
||||
*//////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx
|
||||
name = "non-eutactic blade"
|
||||
desc = "The CX Armories Type-69 Non-Eutactic Blade utilizes a hardlight blade that is dynamically 'forged' on demand to create a deadly sharp edge that is unbreakable."
|
||||
icon_state = "cxsword_hilt"
|
||||
icon = 'icons/obj/cit_weapons.dmi'
|
||||
item_state = "cxsword"
|
||||
lefthand_file = 'icons/mob/citadel/melee_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/citadel/melee_righthand.dmi'
|
||||
force = 3
|
||||
throwforce = 5
|
||||
hitsound = "swing_hit" //it starts deactivated
|
||||
hitsound_on = 'sound/weapons/nebhit.ogg'
|
||||
attack_verb_off = list("tapped", "poked")
|
||||
throw_speed = 3
|
||||
throw_range = 5
|
||||
sharpness = IS_SHARP
|
||||
embed_chance = 40
|
||||
embedded_impact_pain_multiplier = 10
|
||||
armour_penetration = 0
|
||||
origin_tech = "combat=3;magnets=4"
|
||||
block_chance = 60
|
||||
light_color = "#37FFF7"
|
||||
actions_types = list()
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/transform_weapon(mob/living/user, supress_message_text)
|
||||
active = !active //I'd use a ..() here but it'd inherit from the regular esword's proc instead, so SPAGHETTI CODE
|
||||
if(active) //also I need to rip out the iconstate changing bits
|
||||
force = force_on
|
||||
throwforce = throwforce_on
|
||||
hitsound = hitsound_on
|
||||
throw_speed = 4
|
||||
if(attack_verb_on.len)
|
||||
attack_verb = attack_verb_on
|
||||
w_class = w_class_on
|
||||
START_PROCESSING(SSobj, src)
|
||||
set_light(brightness_on)
|
||||
update_icon()
|
||||
else
|
||||
force = initial(force)
|
||||
throwforce = initial(throwforce)
|
||||
hitsound = initial(hitsound)
|
||||
throw_speed = initial(throw_speed)
|
||||
if(attack_verb_off.len)
|
||||
attack_verb = attack_verb_off
|
||||
w_class = initial(w_class)
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
set_light(0)
|
||||
update_icon()
|
||||
transform_messages(user, supress_message_text)
|
||||
add_fingerprint(user)
|
||||
return TRUE
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/transform_messages(mob/living/user, supress_message_text)
|
||||
playsound(user, active ? 'sound/weapons/nebon.ogg' : 'sound/weapons/neboff.ogg', 65, 1)
|
||||
if(!supress_message_text)
|
||||
to_chat(user, "<span class='notice'>[src] [active ? "is now active":"can now be concealed"].</span>")
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/update_icon()
|
||||
var/mutable_appearance/blade_overlay = mutable_appearance('icons/obj/cit_weapons.dmi', "cxsword_blade")
|
||||
var/mutable_appearance/gem_overlay = mutable_appearance('icons/obj/cit_weapons.dmi', "cxsword_gem")
|
||||
|
||||
if(light_color)
|
||||
blade_overlay.color = light_color
|
||||
gem_overlay.color = light_color
|
||||
|
||||
cut_overlays() //So that it doesn't keep stacking overlays non-stop on top of each other
|
||||
|
||||
add_overlay(gem_overlay)
|
||||
|
||||
if(active)
|
||||
add_overlay(blade_overlay)
|
||||
|
||||
if(ismob(loc))
|
||||
var/mob/M = loc
|
||||
M.update_inv_hands()
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/AltClick(mob/living/user)
|
||||
if(user.incapacitated() || !istype(user))
|
||||
to_chat(user, "<span class='warning'>You can't do that right now!</span>")
|
||||
return
|
||||
if(!in_range(src, user))
|
||||
return
|
||||
if(user.incapacitated() || !istype(user) || !in_range(src, user))
|
||||
return
|
||||
|
||||
if(alert("Are you sure you want to recolor your blade?", "Confirm Repaint", "Yes", "No") == "Yes")
|
||||
var/energy_color_input = input(usr,"Choose Energy Color") as color|null
|
||||
if(energy_color_input)
|
||||
light_color = sanitize_hexcolor(energy_color_input, desired_format=6, include_crunch=1)
|
||||
update_icon()
|
||||
update_light()
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/examine(mob/user)
|
||||
..()
|
||||
to_chat(user, "<span class='notice'>Alt-click to recolor it.</span>")
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/worn_overlays(isinhands, icon_file)
|
||||
. = ..()
|
||||
if(active)
|
||||
if(isinhands)
|
||||
var/mutable_appearance/blade_inhand = mutable_appearance(icon_file, "cxsword_blade")
|
||||
blade_inhand.color = light_color
|
||||
. += blade_inhand
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/traitor
|
||||
name = "\improper Dragon's Tooth Sword"
|
||||
desc = "The Dragon's Tooth sword is a blackmarket modification of the CX Armouries Type-69 NEB, \
|
||||
which utilizes a hardlight blade that is dynamically 'forged' on demand to create a deadly sharp edge that is unbreakable. \
|
||||
It appears to have a wooden grip and a shaved down guard."
|
||||
icon_state = "cxsword_hilt_traitor"
|
||||
armour_penetration = 35
|
||||
embed_chance = 75
|
||||
block_chance = 50
|
||||
origin_tech = "combat=3;magnets=4;syndicate=4"
|
||||
hitsound_on = 'sound/weapons/blade1.ogg'
|
||||
light_color = "#37F0FF"
|
||||
|
||||
/obj/item/melee/transforming/energy/sword/cx/traitor/transform_messages(mob/living/user, supress_message_text)
|
||||
playsound(user, active ? 'sound/weapons/saberon.ogg' : 'sound/weapons/saberoff.ogg', 35, 1)
|
||||
if(!supress_message_text)
|
||||
to_chat(user, "<span class='notice'>[src] [active ? "is now active":"can now be concealed"].</span>")
|
||||
@@ -38,8 +38,8 @@
|
||||
explanation_text = "Make sure the research required to produce a [initial(targetdesign.name)] is available on the R&D server by the end of the shift."
|
||||
|
||||
/datum/objective/crew/research/check_completion()
|
||||
for(var/obj/machinery/r_n_d/server/S in GLOB.machines)
|
||||
if(S && S.files && S.files.known_designs)
|
||||
if(targetdesign in S.files.known_designs)
|
||||
for(var/obj/machinery/rnd/server/S in GLOB.machines)
|
||||
if(S && S.stored_research)
|
||||
if(S.stored_research.researched_designs[initial(targetdesign.id)])
|
||||
return TRUE
|
||||
return FALSE
|
||||
|
||||
@@ -17,9 +17,9 @@
|
||||
name = "Kiara's Cloak"
|
||||
desc = "The design on this seems a little too familiar."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "infcloak-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "infcloak-w"
|
||||
icon_state = "infcloak"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "infcloak"
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
body_parts_covered = CHEST|GROIN|LEGS|ARMS
|
||||
|
||||
@@ -27,9 +27,9 @@
|
||||
name = "Kiara's Collar"
|
||||
desc = "A soft black collar that seems to stretch to fit whoever wears it."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "infcollar-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "infcollar-w"
|
||||
icon_state = "infcollar"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "infcollar"
|
||||
item_color = null
|
||||
tagname = null
|
||||
|
||||
@@ -62,19 +62,19 @@
|
||||
/obj/item/clothing/neck/scarf/zomb //Default white color, same functionality as beanies.
|
||||
name = "A special scarf"
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "zombscarf-i"
|
||||
icon_state = "zombscarf"
|
||||
desc = "A fashionable collar"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_color = "zombscarf-w"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_color = "zombscarf"
|
||||
dog_fashion = /datum/dog_fashion/head
|
||||
|
||||
/obj/item/clothing/suit/toggle/labcoat/mad/red
|
||||
name = "\improper The Mad's labcoat"
|
||||
desc = "An oddly special looking coat."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "labred-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "labred-w"
|
||||
icon_state = "labred"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "labred"
|
||||
|
||||
|
||||
/*PLACEHOLDER*/
|
||||
@@ -94,9 +94,9 @@
|
||||
name = "carrot cloak"
|
||||
desc = "A cloak in the shape and color of a carrot!"
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
icon_state = "carrotcloak-i"
|
||||
item_state = "carrotcloak-w"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
icon_state = "carrotcloak"
|
||||
item_state = "carrotcloak"
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
body_parts_covered = CHEST|GROIN|LEGS|ARMS
|
||||
|
||||
@@ -115,9 +115,9 @@
|
||||
name = "Celebratory Cloak of Morozko"
|
||||
desc = " It probably will protect from snow, charcoal or elves."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "festive-i"
|
||||
item_state = "festive-w"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
icon_state = "festive"
|
||||
item_state = "festive"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
w_class = WEIGHT_CLASS_SMALL
|
||||
body_parts_covered = CHEST|GROIN|LEGS|ARMS
|
||||
|
||||
@@ -127,9 +127,9 @@
|
||||
/obj/item/clothing/mask/luchador/zigfie
|
||||
name = "Alboroto Rosa mask"
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "lucharzigfie-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "lucharzigfie-w"
|
||||
icon_state = "lucharzigfie"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "lucharzigfie"
|
||||
|
||||
|
||||
/*PLACEHOLDER*/
|
||||
@@ -168,9 +168,9 @@
|
||||
name = "Reece's Great Coat"
|
||||
desc = "You would swear this was in your nightmares after eating too many veggies."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "hos-g-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "hos-g-w"
|
||||
icon_state = "hos-g"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "hos-g"
|
||||
body_parts_covered = CHEST|GROIN|ARMS|LEGS
|
||||
|
||||
|
||||
@@ -186,9 +186,9 @@
|
||||
name = "S.T.A.L.K.E.R. mask"
|
||||
desc = "Smells like reactor four."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
item_state = "stalker-w"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
icon_state = "stalker-i"
|
||||
item_state = "stalker"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
icon_state = "stalker"
|
||||
|
||||
|
||||
/*Sylas*/
|
||||
@@ -196,9 +196,9 @@
|
||||
name = "collar"
|
||||
desc = "It's a collar..."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "petcollar-stripe-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "petcollar-stripe-w"
|
||||
icon_state = "petcollar-stripe"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "petcollar-stripe"
|
||||
tagname = null
|
||||
|
||||
|
||||
@@ -207,10 +207,10 @@
|
||||
name = "bluish performer's outfit"
|
||||
desc = "Just looking at this makes you want to sing."
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "singer-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "singer-w"
|
||||
item_color = "singer-i"
|
||||
icon_state = "singer"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "singer"
|
||||
item_color = "singer"
|
||||
fitted = NO_FEMALE_UNIFORM
|
||||
alternate_worn_layer = ABOVE_SHOES_LAYER
|
||||
can_adjust = 0
|
||||
@@ -218,9 +218,9 @@
|
||||
|
||||
/obj/item/clothing/shoes/sneakers/pink
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_state = "pink-i"
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
item_state = "pink-w"
|
||||
icon_state = "pink"
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
item_state = "pink"
|
||||
|
||||
|
||||
/*Fractious*/
|
||||
@@ -228,8 +228,8 @@
|
||||
/obj/item/clothing/suit/vermillion
|
||||
name = "vermillion clothing"
|
||||
desc = "Some clothing."
|
||||
icon_state = "vermillion-i"
|
||||
item_state = "vermillion-w"
|
||||
icon_state = "vermillion"
|
||||
item_state = "vermillion"
|
||||
body_parts_covered = CHEST|GROIN|LEGS|ARMS|HANDS
|
||||
icon = 'icons/obj/custom.dmi'
|
||||
icon_override = 'icons/obj/custom.dmi'
|
||||
icon_override = 'icons/mob/custom_w.dmi'
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
var/value
|
||||
var/default //read-only, just set value directly
|
||||
|
||||
var/resident_file //the file which this belongs to, must be set
|
||||
var/resident_file //the file which this was loaded from, if any
|
||||
var/modified = FALSE //set to TRUE if the default has been overridden by a config entry
|
||||
|
||||
var/protection = NONE
|
||||
@@ -18,8 +18,6 @@
|
||||
var/dupes_allowed = FALSE
|
||||
|
||||
/datum/config_entry/New()
|
||||
if(!resident_file)
|
||||
CRASH("Config entry [type] has no resident_file set")
|
||||
if(type == abstract_type)
|
||||
CRASH("Abstract config entry [type] instatiated!")
|
||||
name = lowertext(type2top(type))
|
||||
@@ -110,7 +108,7 @@
|
||||
/datum/config_entry/number/ValidateAndSet(str_val)
|
||||
var/temp = text2num(trim(str_val))
|
||||
if(!isnull(temp))
|
||||
value = Clamp(integer ? round(temp) : temp, min_val, max_val)
|
||||
value = CLAMP(integer ? round(temp) : temp, min_val, max_val)
|
||||
if(value != temp && !var_edited)
|
||||
log_config("Changing [name] from [temp] to [value]!")
|
||||
return TRUE
|
||||
|
||||
@@ -20,10 +20,13 @@ GLOBAL_PROTECT(config_dir)
|
||||
|
||||
/datum/controller/configuration/New()
|
||||
config = src
|
||||
var/list/config_files = InitEntries()
|
||||
InitEntries()
|
||||
LoadModes()
|
||||
for(var/I in config_files)
|
||||
LoadEntries(I)
|
||||
if(!LoadEntries("config.txt"))
|
||||
log_config("No $include directives found in config.txt! Loading legacy game_options/dbconfig/comms files...")
|
||||
LoadEntries("game_options.txt")
|
||||
LoadEntries("dbconfig.txt")
|
||||
LoadEntries("comms.txt")
|
||||
loadmaplist(CONFIG_MAPS_FILE)
|
||||
|
||||
/datum/controller/configuration/Destroy()
|
||||
@@ -42,8 +45,6 @@ GLOBAL_PROTECT(config_dir)
|
||||
var/list/_entries_by_type = list()
|
||||
entries_by_type = _entries_by_type
|
||||
|
||||
. = list()
|
||||
|
||||
for(var/I in typesof(/datum/config_entry)) //typesof is faster in this case
|
||||
var/datum/config_entry/E = I
|
||||
if(initial(E.abstract_type) == I)
|
||||
@@ -57,24 +58,30 @@ GLOBAL_PROTECT(config_dir)
|
||||
continue
|
||||
_entries[esname] = E
|
||||
_entries_by_type[I] = E
|
||||
.[E.resident_file] = TRUE
|
||||
|
||||
/datum/controller/configuration/proc/RemoveEntry(datum/config_entry/CE)
|
||||
entries -= CE.name
|
||||
entries_by_type -= CE.type
|
||||
|
||||
/datum/controller/configuration/proc/LoadEntries(filename)
|
||||
/datum/controller/configuration/proc/LoadEntries(filename, list/stack = list())
|
||||
var/filename_to_test = world.system_type == MS_WINDOWS ? lowertext(filename) : filename
|
||||
if(filename_to_test in stack)
|
||||
log_config("Warning: Config recursion detected ([english_list(stack)]), breaking!")
|
||||
return
|
||||
stack = stack + filename_to_test
|
||||
|
||||
log_config("Loading config file [filename]...")
|
||||
var/list/lines = world.file2list("[GLOB.config_dir][filename]")
|
||||
var/list/_entries = entries
|
||||
for(var/L in lines)
|
||||
if(!L)
|
||||
continue
|
||||
|
||||
if(copytext(L, 1, 2) == "#")
|
||||
|
||||
var/firstchar = copytext(L, 1, 2)
|
||||
if(firstchar == "#")
|
||||
continue
|
||||
|
||||
var/lockthis = copytext(L, 1, 2) == "@"
|
||||
var/lockthis = firstchar == "@"
|
||||
if(lockthis)
|
||||
L = copytext(L, 2)
|
||||
|
||||
@@ -91,14 +98,17 @@ GLOBAL_PROTECT(config_dir)
|
||||
if(!entry)
|
||||
continue
|
||||
|
||||
if(entry == "$include")
|
||||
if(!value)
|
||||
log_config("Warning: Invalid $include directive: [value]")
|
||||
else
|
||||
LoadEntries(value, stack)
|
||||
continue
|
||||
|
||||
var/datum/config_entry/E = _entries[entry]
|
||||
if(!E)
|
||||
log_config("Unknown setting in configuration: '[entry]'")
|
||||
continue
|
||||
|
||||
if(filename != E.resident_file)
|
||||
log_config("Found [entry] in [filename] when it should have been in [E.resident_file]! Ignoring.")
|
||||
continue
|
||||
|
||||
if(lockthis)
|
||||
E.protection |= CONFIG_ENTRY_LOCKED
|
||||
@@ -107,10 +117,14 @@ GLOBAL_PROTECT(config_dir)
|
||||
if(!validated)
|
||||
log_config("Failed to validate setting \"[value]\" for [entry]")
|
||||
else if(E.modified && !E.dupes_allowed)
|
||||
log_config("Duplicate setting for [entry] ([value]) detected! Using latest.")
|
||||
log_config("Duplicate setting for [entry] ([value], [E.resident_file]) detected! Using latest.")
|
||||
|
||||
E.resident_file = filename
|
||||
|
||||
if(validated)
|
||||
E.modified = TRUE
|
||||
|
||||
. = TRUE
|
||||
|
||||
/datum/controller/configuration/can_vv_get(var_name)
|
||||
return (var_name != "entries_by_type" || !hiding_entries_by_type) && ..()
|
||||
|
||||
@@ -1,22 +1,20 @@
|
||||
#define CURRENT_RESIDENT_FILE "comms.txt"
|
||||
|
||||
CONFIG_DEF(string/comms_key)
|
||||
/datum/config_entry/string/comms_key
|
||||
protection = CONFIG_ENTRY_HIDDEN
|
||||
|
||||
/datum/config_entry/string/comms_key/ValidateAndSet(str_val)
|
||||
return str_val != "default_pwd" && length(str_val) > 6 && ..()
|
||||
|
||||
CONFIG_DEF(string/cross_server_address)
|
||||
/datum/config_entry/keyed_string_list/cross_server
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/string/cross_server_address/ValidateAndSet(str_val)
|
||||
return str_val != "byond:\\address:port" && ..()
|
||||
|
||||
CONFIG_DEF(string/cross_comms_name)
|
||||
/datum/config_entry/string/cross_comms_name
|
||||
|
||||
GLOBAL_VAR_INIT(medals_enabled, TRUE) //will be auto set to false if the game fails contacting the medal hub to prevent unneeded calls.
|
||||
|
||||
CONFIG_DEF(string/medal_hub_address)
|
||||
/datum/config_entry/string/medal_hub_address
|
||||
|
||||
CONFIG_DEF(string/medal_hub_password)
|
||||
protection = CONFIG_ENTRY_HIDDEN
|
||||
/datum/config_entry/string/medal_hub_password
|
||||
protection = CONFIG_ENTRY_HIDDEN
|
||||
|
||||
@@ -1,390 +0,0 @@
|
||||
#define CURRENT_RESIDENT_FILE "config.txt"
|
||||
|
||||
CONFIG_DEF(flag/autoadmin) // if autoadmin is enabled
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(string/autoadmin_rank) // the rank for autoadmins
|
||||
value = "Game Master"
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(string/servername) // server name (the name of the game window)
|
||||
|
||||
CONFIG_DEF(string/serversqlname) // short form server name used for the DB
|
||||
|
||||
CONFIG_DEF(string/stationname) // station name (the name of the station in-game)
|
||||
|
||||
CONFIG_DEF(number/lobby_countdown) // In between round countdown.
|
||||
value = 120
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/round_end_countdown) // Post round murder death kill countdown
|
||||
value = 25
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/hub) // if the game appears on the hub or not
|
||||
|
||||
CONFIG_DEF(flag/log_ooc) // log OOC channel
|
||||
|
||||
CONFIG_DEF(flag/log_access) // log login/logout
|
||||
|
||||
CONFIG_DEF(flag/log_say) // log client say
|
||||
|
||||
CONFIG_DEF(flag/log_admin) // log admin actions
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(flag/log_prayer) // log prayers
|
||||
|
||||
CONFIG_DEF(flag/log_law) // log lawchanges
|
||||
|
||||
CONFIG_DEF(flag/log_game) // log game events
|
||||
|
||||
CONFIG_DEF(flag/log_vote) // log voting
|
||||
|
||||
CONFIG_DEF(flag/log_whisper) // log client whisper
|
||||
|
||||
CONFIG_DEF(flag/log_attack) // log attack messages
|
||||
|
||||
CONFIG_DEF(flag/log_emote) // log emotes
|
||||
|
||||
CONFIG_DEF(flag/log_adminchat) // log admin chat messages
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(flag/log_pda) // log pda messages
|
||||
|
||||
CONFIG_DEF(flag/log_twitter) // log certain expliotable parrots and other such fun things in a JSON file of twitter valid phrases.
|
||||
|
||||
CONFIG_DEF(flag/log_world_topic) // log all world.Topic() calls
|
||||
|
||||
CONFIG_DEF(flag/log_manifest) // log crew manifest to seperate file
|
||||
|
||||
CONFIG_DEF(flag/allow_admin_ooccolor) // Allows admins with relevant permissions to have their own ooc colour
|
||||
|
||||
CONFIG_DEF(flag/allow_vote_restart) // allow votes to restart
|
||||
|
||||
CONFIG_DEF(flag/allow_vote_mode) // allow votes to change mode
|
||||
|
||||
CONFIG_DEF(number/vote_delay) // minimum time between voting sessions (deciseconds, 10 minute default)
|
||||
value = 6000
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/vote_period) // length of voting period (deciseconds, default 1 minute)
|
||||
value = 600
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/default_no_vote) // vote does not default to nochange/norestart
|
||||
|
||||
CONFIG_DEF(flag/no_dead_vote) // dead people can't vote
|
||||
|
||||
CONFIG_DEF(flag/allow_metadata) // Metadata is supported.
|
||||
|
||||
CONFIG_DEF(flag/popup_admin_pm) // adminPMs to non-admins show in a pop-up 'reply' window when set
|
||||
|
||||
CONFIG_DEF(number/fps)
|
||||
value = 20
|
||||
min_val = 1
|
||||
max_val = 100 //byond will start crapping out at 50, so this is just ridic
|
||||
var/sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/number/fps/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
sync_validate = TRUE
|
||||
var/datum/config_entry/number/ticklag/TL = config.entries_by_type[/datum/config_entry/number/ticklag]
|
||||
if(!TL.sync_validate)
|
||||
TL.ValidateAndSet(10 / value)
|
||||
sync_validate = FALSE
|
||||
|
||||
CONFIG_DEF(number/ticklag)
|
||||
integer = FALSE
|
||||
var/sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/number/ticklag/New() //ticklag weirdly just mirrors fps
|
||||
var/datum/config_entry/CE = /datum/config_entry/number/fps
|
||||
value = 10 / initial(CE.value)
|
||||
..()
|
||||
|
||||
/datum/config_entry/number/ticklag/ValidateAndSet(str_val)
|
||||
. = text2num(str_val) > 0 && ..()
|
||||
if(.)
|
||||
sync_validate = TRUE
|
||||
var/datum/config_entry/number/fps/FPS = config.entries_by_type[/datum/config_entry/number/fps]
|
||||
if(!FPS.sync_validate)
|
||||
FPS.ValidateAndSet(10 / value)
|
||||
sync_validate = FALSE
|
||||
|
||||
CONFIG_DEF(flag/allow_holidays)
|
||||
|
||||
CONFIG_DEF(number/tick_limit_mc_init) //SSinitialization throttling
|
||||
value = TICK_LIMIT_MC_INIT_DEFAULT
|
||||
min_val = 0 //oranges warned us
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(flag/admin_legacy_system) //Defines whether the server uses the legacy admin system with admins.txt or the SQL system
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(string/hostedby)
|
||||
|
||||
CONFIG_DEF(flag/norespawn)
|
||||
|
||||
CONFIG_DEF(flag/guest_jobban)
|
||||
|
||||
CONFIG_DEF(flag/usewhitelist)
|
||||
|
||||
CONFIG_DEF(flag/ban_legacy_system) //Defines whether the server uses the legacy banning system with the files in /data or the SQL system.
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(flag/use_age_restriction_for_jobs) //Do jobs use account age restrictions? --requires database
|
||||
|
||||
CONFIG_DEF(flag/use_account_age_for_jobs) //Uses the time they made the account for the job restriction stuff. New player joining alerts should be unaffected.
|
||||
|
||||
CONFIG_DEF(flag/use_exp_tracking)
|
||||
|
||||
CONFIG_DEF(flag/use_exp_restrictions_heads)
|
||||
|
||||
CONFIG_DEF(number/use_exp_restrictions_heads_hours)
|
||||
value = 0
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/use_exp_restrictions_heads_department)
|
||||
|
||||
CONFIG_DEF(flag/use_exp_restrictions_other)
|
||||
|
||||
CONFIG_DEF(flag/use_exp_restrictions_admin_bypass)
|
||||
|
||||
CONFIG_DEF(string/server)
|
||||
|
||||
CONFIG_DEF(string/banappeals)
|
||||
|
||||
CONFIG_DEF(string/wikiurl)
|
||||
value = "http://www.tgstation13.org/wiki"
|
||||
|
||||
CONFIG_DEF(string/forumurl)
|
||||
value = "http://tgstation13.org/phpBB/index.php"
|
||||
|
||||
CONFIG_DEF(string/rulesurl)
|
||||
value = "http://www.tgstation13.org/wiki/Rules"
|
||||
|
||||
CONFIG_DEF(string/githuburl)
|
||||
value = "https://www.github.com/tgstation/-tg-station"
|
||||
|
||||
CONFIG_DEF(number/githubrepoid)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/guest_ban)
|
||||
|
||||
CONFIG_DEF(number/id_console_jobslot_delay)
|
||||
value = 30
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/inactivity_period) //time in ds until a player is considered inactive)
|
||||
value = 3000
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/inactivity_period/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
value *= 10 //documented as seconds in config.txt
|
||||
|
||||
CONFIG_DEF(number/afk_period) //time in ds until a player is considered inactive)
|
||||
value = 3000
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/afk_period/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
value *= 10 //documented as seconds in config.txt
|
||||
|
||||
CONFIG_DEF(flag/kick_inactive) //force disconnect for inactive players
|
||||
|
||||
CONFIG_DEF(flag/load_jobs_from_txt)
|
||||
|
||||
CONFIG_DEF(flag/forbid_singulo_possession)
|
||||
|
||||
CONFIG_DEF(flag/automute_on) //enables automuting/spam prevention
|
||||
|
||||
CONFIG_DEF(string/panic_server_name)
|
||||
|
||||
/datum/config_entry/string/panic_server_name/ValidateAndSet(str_val)
|
||||
return str_val != "\[Put the name here\]" && ..()
|
||||
|
||||
CONFIG_DEF(string/panic_server_address) //Reconnect a player this linked server if this server isn't accepting new players
|
||||
|
||||
/datum/config_entry/string/panic_server_address/ValidateAndSet(str_val)
|
||||
return str_val != "byond://address:port" && ..()
|
||||
|
||||
CONFIG_DEF(string/invoke_youtubedl)
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(flag/show_irc_name)
|
||||
|
||||
CONFIG_DEF(flag/see_own_notes) //Can players see their own admin notes (read-only)?
|
||||
|
||||
CONFIG_DEF(number/note_fresh_days)
|
||||
value = null
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(number/note_stale_days)
|
||||
value = null
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(flag/maprotation)
|
||||
|
||||
CONFIG_DEF(number/maprotatechancedelta)
|
||||
value = 0.75
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(number/soft_popcap)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/hard_popcap)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/extreme_popcap)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(string/soft_popcap_message)
|
||||
value = "Be warned that the server is currently serving a high number of users, consider using alternative game servers."
|
||||
|
||||
CONFIG_DEF(string/hard_popcap_message)
|
||||
value = "The server is currently serving a high number of users, You cannot currently join. You may wait for the number of living crew to decline, observe, or find alternative servers."
|
||||
|
||||
CONFIG_DEF(string/extreme_popcap_message)
|
||||
value = "The server is currently serving a high number of users, find alternative servers."
|
||||
|
||||
CONFIG_DEF(flag/panic_bunker) // prevents people the server hasn't seen before from connecting
|
||||
|
||||
CONFIG_DEF(number/notify_new_player_age) // how long do we notify admins of a new player
|
||||
min_val = -1
|
||||
|
||||
CONFIG_DEF(number/notify_new_player_account_age) // how long do we notify admins of a new byond account
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/irc_first_connection_alert) // do we notify the irc channel when somebody is connecting for the first time?
|
||||
|
||||
CONFIG_DEF(flag/check_randomizer)
|
||||
|
||||
CONFIG_DEF(string/ipintel_email)
|
||||
|
||||
/datum/config_entry/string/ipintel_email/ValidateAndSet(str_val)
|
||||
return str_val != "ch@nge.me" && ..()
|
||||
|
||||
CONFIG_DEF(number/ipintel_rating_bad)
|
||||
value = 1
|
||||
integer = FALSE
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
|
||||
CONFIG_DEF(number/ipintel_save_good)
|
||||
value = 12
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/ipintel_save_bad)
|
||||
value = 1
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(string/ipintel_domain)
|
||||
value = "check.getipintel.net"
|
||||
|
||||
CONFIG_DEF(flag/aggressive_changelog)
|
||||
|
||||
CONFIG_DEF(flag/autoconvert_notes) //if all connecting player's notes should attempt to be converted to the database
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(flag/allow_webclient)
|
||||
|
||||
CONFIG_DEF(flag/webclient_only_byond_members)
|
||||
|
||||
CONFIG_DEF(flag/announce_admin_logout)
|
||||
|
||||
CONFIG_DEF(flag/announce_admin_login)
|
||||
|
||||
CONFIG_DEF(flag/allow_map_voting)
|
||||
|
||||
CONFIG_DEF(flag/generate_minimaps)
|
||||
|
||||
CONFIG_DEF(number/client_warn_version)
|
||||
value = null
|
||||
min_val = 500
|
||||
max_val = DM_VERSION - 1
|
||||
|
||||
CONFIG_DEF(string/client_warn_message)
|
||||
value = "Your version of byond may have issues or be blocked from accessing this server in the future."
|
||||
|
||||
CONFIG_DEF(flag/client_warn_popup)
|
||||
|
||||
CONFIG_DEF(number/client_error_version)
|
||||
value = null
|
||||
min_val = 500
|
||||
max_val = DM_VERSION - 1
|
||||
|
||||
CONFIG_DEF(string/client_error_message)
|
||||
value = "Your version of byond is too old, may have issues, and is blocked from accessing this server."
|
||||
|
||||
CONFIG_DEF(number/minute_topic_limit)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/second_topic_limit)
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/error_cooldown) // The "cooldown" time for each occurrence of a unique error)
|
||||
value = 600
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/error_limit) // How many occurrences before the next will silence them
|
||||
value = 50
|
||||
|
||||
CONFIG_DEF(number/error_silence_time) // How long a unique error will be silenced for
|
||||
value = 6000
|
||||
|
||||
CONFIG_DEF(number/error_msg_delay) // How long to wait between messaging admins about occurrences of a unique error
|
||||
value = 50
|
||||
|
||||
CONFIG_DEF(flag/irc_announce_new_game)
|
||||
|
||||
CONFIG_DEF(flag/debug_admin_hrefs)
|
||||
|
||||
CONFIG_DEF(number/mc_tick_rate/base_mc_tick_rate)
|
||||
integer = FALSE
|
||||
value = 1
|
||||
|
||||
CONFIG_DEF(number/mc_tick_rate/high_pop_mc_tick_rate)
|
||||
integer = FALSE
|
||||
value = 1.1
|
||||
|
||||
CONFIG_DEF(number/mc_tick_rate/high_pop_mc_mode_amount)
|
||||
value = 65
|
||||
|
||||
CONFIG_DEF(number/mc_tick_rate/disable_high_pop_mc_mode_amount)
|
||||
value = 60
|
||||
|
||||
CONFIG_TWEAK(number/mc_tick_rate)
|
||||
abstract_type = /datum/config_entry/number/mc_tick_rate
|
||||
|
||||
CONFIG_TWEAK(number/mc_tick_rate/ValidateAndSet(str_val))
|
||||
. = ..()
|
||||
if (.)
|
||||
Master.UpdateTickRate()
|
||||
|
||||
CONFIG_DEF(flag/resume_after_initializations)
|
||||
|
||||
CONFIG_TWEAK(flag/resume_after_initializations/ValidateAndSet(str_val))
|
||||
. = ..()
|
||||
if(. && Master.current_runlevel)
|
||||
world.sleep_offline = !value
|
||||
|
||||
CONFIG_DEF(number/rounds_until_hard_restart)
|
||||
value = -1
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(string/default_view)
|
||||
value = "15x15"
|
||||
@@ -1,28 +1,26 @@
|
||||
#define CURRENT_RESIDENT_FILE "dbconfig.txt"
|
||||
|
||||
CONFIG_DEF(flag/sql_enabled) // for sql switching
|
||||
/datum/config_entry/flag/sql_enabled // for sql switching
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
CONFIG_DEF(string/address)
|
||||
/datum/config_entry/string/address
|
||||
value = "localhost"
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(number/port)
|
||||
/datum/config_entry/number/port
|
||||
value = 3306
|
||||
min_val = 0
|
||||
max_val = 65535
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(string/feedback_database)
|
||||
/datum/config_entry/string/feedback_database
|
||||
value = "test"
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(string/feedback_login)
|
||||
/datum/config_entry/string/feedback_login
|
||||
value = "root"
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(string/feedback_password)
|
||||
/datum/config_entry/string/feedback_password
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
CONFIG_DEF(string/feedback_tableprefix)
|
||||
/datum/config_entry/string/feedback_tableprefix
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
@@ -1,253 +1,255 @@
|
||||
#define CURRENT_RESIDENT_FILE "game_options.txt"
|
||||
/datum/config_entry/number_list/repeated_mode_adjust
|
||||
|
||||
CONFIG_DEF(number_list/repeated_mode_adjust)
|
||||
|
||||
CONFIG_DEF(keyed_number_list/probability)
|
||||
/datum/config_entry/keyed_number_list/probability
|
||||
|
||||
/datum/config_entry/keyed_number_list/probability/ValidateKeyName(key_name)
|
||||
return key_name in config.modes
|
||||
|
||||
CONFIG_DEF(keyed_number_list/max_pop)
|
||||
/datum/config_entry/keyed_number_list/max_pop
|
||||
|
||||
/datum/config_entry/keyed_number_list/max_pop/ValidateKeyName(key_name)
|
||||
return key_name in config.modes
|
||||
|
||||
CONFIG_DEF(keyed_number_list/min_pop)
|
||||
/datum/config_entry/keyed_number_list/min_pop
|
||||
|
||||
/datum/config_entry/keyed_number_list/min_pop/ValidateKeyName(key_name)
|
||||
return key_name in config.modes
|
||||
|
||||
CONFIG_DEF(keyed_flag_list/continuous) // which roundtypes continue if all antagonists die
|
||||
/datum/config_entry/keyed_flag_list/continuous // which roundtypes continue if all antagonists die
|
||||
|
||||
/datum/config_entry/keyed_flag_list/continuous/ValidateKeyName(key_name)
|
||||
return key_name in config.modes
|
||||
|
||||
CONFIG_DEF(keyed_flag_list/midround_antag) // which roundtypes use the midround antagonist system
|
||||
/datum/config_entry/keyed_flag_list/midround_antag // which roundtypes use the midround antagonist system
|
||||
|
||||
/datum/config_entry/keyed_flag_list/midround_antag/ValidateKeyName(key_name)
|
||||
return key_name in config.modes
|
||||
|
||||
CONFIG_DEF(keyed_string_list/policy)
|
||||
/datum/config_entry/keyed_string_list/policy
|
||||
|
||||
CONFIG_DEF(number/damage_multiplier)
|
||||
/datum/config_entry/number/damage_multiplier
|
||||
value = 1
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(number/minimal_access_threshold) //If the number of players is larger than this threshold, minimal access will be turned on.
|
||||
/datum/config_entry/number/minimal_access_threshold //If the number of players is larger than this threshold, minimal access will be turned on.
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/jobs_have_minimal_access) //determines whether jobs use minimal access or expanded access.
|
||||
/datum/config_entry/flag/jobs_have_minimal_access //determines whether jobs use minimal access or expanded access.
|
||||
|
||||
CONFIG_DEF(flag/assistants_have_maint_access)
|
||||
/datum/config_entry/flag/assistants_have_maint_access
|
||||
|
||||
CONFIG_DEF(flag/security_has_maint_access)
|
||||
/datum/config_entry/flag/security_has_maint_access
|
||||
|
||||
CONFIG_DEF(flag/everyone_has_maint_access)
|
||||
/datum/config_entry/flag/everyone_has_maint_access
|
||||
|
||||
CONFIG_DEF(flag/sec_start_brig) //makes sec start in brig instead of dept sec posts
|
||||
/datum/config_entry/flag/sec_start_brig //makes sec start in brig instead of dept sec posts
|
||||
|
||||
CONFIG_DEF(flag/force_random_names)
|
||||
/datum/config_entry/flag/force_random_names
|
||||
|
||||
CONFIG_DEF(flag/humans_need_surnames)
|
||||
/datum/config_entry/flag/humans_need_surnames
|
||||
|
||||
CONFIG_DEF(flag/allow_ai) // allow ai job
|
||||
/datum/config_entry/flag/allow_ai // allow ai job
|
||||
|
||||
CONFIG_DEF(flag/disable_secborg) // disallow secborg module to be chosen.
|
||||
/datum/config_entry/flag/disable_secborg // disallow secborg module to be chosen.
|
||||
|
||||
CONFIG_DEF(flag/disable_peaceborg)
|
||||
/datum/config_entry/flag/disable_peaceborg
|
||||
|
||||
CONFIG_DEF(number/traitor_scaling_coeff) //how much does the amount of players get divided by to determine traitors
|
||||
/datum/config_entry/number/traitor_scaling_coeff //how much does the amount of players get divided by to determine traitors
|
||||
value = 6
|
||||
min_val = 1
|
||||
|
||||
CONFIG_DEF(number/brother_scaling_coeff) //how many players per brother team
|
||||
/datum/config_entry/number/brother_scaling_coeff //how many players per brother team
|
||||
value = 25
|
||||
min_val = 1
|
||||
|
||||
CONFIG_DEF(number/changeling_scaling_coeff) //how much does the amount of players get divided by to determine changelings
|
||||
/datum/config_entry/number/changeling_scaling_coeff //how much does the amount of players get divided by to determine changelings
|
||||
value = 6
|
||||
min_val = 1
|
||||
|
||||
CONFIG_DEF(number/security_scaling_coeff) //how much does the amount of players get divided by to determine open security officer positions
|
||||
/datum/config_entry/number/security_scaling_coeff //how much does the amount of players get divided by to determine open security officer positions
|
||||
value = 8
|
||||
min_val = 1
|
||||
|
||||
CONFIG_DEF(number/abductor_scaling_coeff) //how many players per abductor team
|
||||
/datum/config_entry/number/abductor_scaling_coeff //how many players per abductor team
|
||||
value = 15
|
||||
min_val = 1
|
||||
|
||||
CONFIG_DEF(number/traitor_objectives_amount)
|
||||
/datum/config_entry/number/traitor_objectives_amount
|
||||
value = 2
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/brother_objectives_amount)
|
||||
/datum/config_entry/number/brother_objectives_amount
|
||||
value = 2
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/reactionary_explosions) //If we use reactionary explosions, explosions that react to walls and doors
|
||||
/datum/config_entry/flag/reactionary_explosions //If we use reactionary explosions, explosions that react to walls and doors
|
||||
|
||||
CONFIG_DEF(flag/protect_roles_from_antagonist) //If security and such can be traitor/cult/other
|
||||
/datum/config_entry/flag/protect_roles_from_antagonist //If security and such can be traitor/cult/other
|
||||
|
||||
CONFIG_DEF(flag/protect_assistant_from_antagonist) //If assistants can be traitor/cult/other
|
||||
/datum/config_entry/flag/protect_assistant_from_antagonist //If assistants can be traitor/cult/other
|
||||
|
||||
CONFIG_DEF(flag/enforce_human_authority) //If non-human species are barred from joining as a head of staff
|
||||
/datum/config_entry/flag/enforce_human_authority //If non-human species are barred from joining as a head of staff
|
||||
|
||||
CONFIG_DEF(flag/allow_latejoin_antagonists) // If late-joining players can be traitor/changeling
|
||||
/datum/config_entry/flag/allow_latejoin_antagonists // If late-joining players can be traitor/changeling
|
||||
|
||||
CONFIG_DEF(number/midround_antag_time_check) // How late (in minutes) you want the midround antag system to stay on, setting this to 0 will disable the system
|
||||
/datum/config_entry/number/midround_antag_time_check // How late (in minutes you want the midround antag system to stay on, setting this to 0 will disable the system)
|
||||
value = 60
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/midround_antag_life_check) // A ratio of how many people need to be alive in order for the round not to immediately end in midround antagonist
|
||||
/datum/config_entry/number/midround_antag_life_check // A ratio of how many people need to be alive in order for the round not to immediately end in midround antagonist
|
||||
value = 0.7
|
||||
integer = FALSE
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
|
||||
CONFIG_DEF(number/shuttle_refuel_delay)
|
||||
/datum/config_entry/number/shuttle_refuel_delay
|
||||
value = 12000
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/show_game_type_odds) //if set this allows players to see the odds of each roundtype on the get revision screen
|
||||
/datum/config_entry/flag/show_game_type_odds //if set this allows players to see the odds of each roundtype on the get revision screen
|
||||
|
||||
CONFIG_DEF(keyed_flag_list/roundstart_races) //races you can play as from the get go.
|
||||
/datum/config_entry/keyed_flag_list/roundstart_races //races you can play as from the get go.
|
||||
|
||||
CONFIG_DEF(flag/join_with_mutant_humans) //players can pick mutant bodyparts for humans before joining the game
|
||||
/datum/config_entry/flag/join_with_mutant_humans //players can pick mutant bodyparts for humans before joining the game
|
||||
|
||||
CONFIG_DEF(flag/no_summon_guns) //No
|
||||
/datum/config_entry/flag/no_summon_guns //No
|
||||
|
||||
CONFIG_DEF(flag/no_summon_magic) //Fun
|
||||
/datum/config_entry/flag/no_summon_magic //Fun
|
||||
|
||||
CONFIG_DEF(flag/no_summon_events) //Allowed
|
||||
/datum/config_entry/flag/no_summon_events //Allowed
|
||||
|
||||
CONFIG_DEF(flag/no_intercept_report) //Whether or not to send a communications intercept report roundstart. This may be overriden by gamemodes.
|
||||
/datum/config_entry/flag/no_intercept_report //Whether or not to send a communications intercept report roundstart. This may be overriden by gamemodes.
|
||||
|
||||
CONFIG_DEF(number/arrivals_shuttle_dock_window) //Time from when a player late joins on the arrivals shuttle to when the shuttle docks on the station
|
||||
/datum/config_entry/number/arrivals_shuttle_dock_window //Time from when a player late joins on the arrivals shuttle to when the shuttle docks on the station
|
||||
value = 55
|
||||
min_val = 30
|
||||
|
||||
CONFIG_DEF(flag/arrivals_shuttle_require_undocked) //Require the arrivals shuttle to be undocked before latejoiners can join
|
||||
/datum/config_entry/flag/arrivals_shuttle_require_undocked //Require the arrivals shuttle to be undocked before latejoiners can join
|
||||
|
||||
CONFIG_DEF(flag/arrivals_shuttle_require_safe_latejoin) //Require the arrivals shuttle to be operational in order for latejoiners to join
|
||||
/datum/config_entry/flag/arrivals_shuttle_require_safe_latejoin //Require the arrivals shuttle to be operational in order for latejoiners to join
|
||||
|
||||
CONFIG_DEF(string/alert_green)
|
||||
/datum/config_entry/string/alert_green
|
||||
value = "All threats to the station have passed. Security may not have weapons visible, privacy laws are once again fully enforced."
|
||||
|
||||
CONFIG_DEF(string/alert_blue_upto)
|
||||
/datum/config_entry/string/alert_blue_upto
|
||||
value = "The station has received reliable information about possible hostile activity on the station. Security staff may have weapons visible, random searches are permitted."
|
||||
|
||||
CONFIG_DEF(string/alert_blue_downto)
|
||||
/datum/config_entry/string/alert_blue_downto
|
||||
value = "The immediate threat has passed. Security may no longer have weapons drawn at all times, but may continue to have them visible. Random searches are still allowed."
|
||||
|
||||
CONFIG_DEF(string/alert_red_upto)
|
||||
/datum/config_entry/string/alert_red_upto
|
||||
value = "There is an immediate serious threat to the station. Security may have weapons unholstered at all times. Random searches are allowed and advised."
|
||||
|
||||
CONFIG_DEF(string/alert_red_downto)
|
||||
/datum/config_entry/string/alert_red_downto
|
||||
value = "The station's destruction has been averted. There is still however an immediate serious threat to the station. Security may have weapons unholstered at all times, random searches are allowed and advised."
|
||||
|
||||
CONFIG_DEF(string/alert_delta)
|
||||
/datum/config_entry/string/alert_delta
|
||||
value = "Destruction of the station is imminent. All crew are instructed to obey all instructions given by heads of staff. Any violations of these orders can be punished by death. This is not a drill."
|
||||
|
||||
CONFIG_DEF(flag/revival_pod_plants)
|
||||
/datum/config_entry/flag/revival_pod_plants
|
||||
|
||||
CONFIG_DEF(flag/revival_cloning)
|
||||
/datum/config_entry/flag/revival_cloning
|
||||
|
||||
CONFIG_DEF(number/revival_brain_life)
|
||||
/datum/config_entry/number/revival_brain_life
|
||||
value = -1
|
||||
min_val = -1
|
||||
|
||||
CONFIG_DEF(flag/rename_cyborg)
|
||||
/datum/config_entry/flag/rename_cyborg
|
||||
|
||||
CONFIG_DEF(flag/ooc_during_round)
|
||||
/datum/config_entry/flag/ooc_during_round
|
||||
|
||||
CONFIG_DEF(flag/emojis)
|
||||
/datum/config_entry/flag/emojis
|
||||
|
||||
CONFIG_DEF(number/run_delay) //Used for modifying movement speed for mobs.
|
||||
/datum/config_entry/number/run_delay //Used for modifying movement speed for mobs.
|
||||
var/static/value_cache = 0
|
||||
|
||||
CONFIG_TWEAK(number/run_delay/ValidateAndSet())
|
||||
/datum/config_entry/number/run_delay/ValidateAndSet()
|
||||
. = ..()
|
||||
if(.)
|
||||
value_cache = value
|
||||
|
||||
CONFIG_DEF(number/walk_delay)
|
||||
/datum/config_entry/number/walk_delay
|
||||
var/static/value_cache = 0
|
||||
|
||||
CONFIG_TWEAK(number/walk_delay/ValidateAndSet())
|
||||
/datum/config_entry/number/walk_delay/ValidateAndSet()
|
||||
. = ..()
|
||||
if(.)
|
||||
value_cache = value
|
||||
|
||||
CONFIG_DEF(number/human_delay) //Mob specific modifiers. NOTE: These will affect different mob types in different ways
|
||||
CONFIG_DEF(number/robot_delay)
|
||||
CONFIG_DEF(number/monkey_delay)
|
||||
CONFIG_DEF(number/alien_delay)
|
||||
CONFIG_DEF(number/slime_delay)
|
||||
CONFIG_DEF(number/animal_delay)
|
||||
/datum/config_entry/number/human_delay //Mob specific modifiers. NOTE: These will affect different mob types in different ways
|
||||
/datum/config_entry/number/robot_delay
|
||||
/datum/config_entry/number/monkey_delay
|
||||
/datum/config_entry/number/alien_delay
|
||||
/datum/config_entry/number/slime_delay
|
||||
/datum/config_entry/number/animal_delay
|
||||
|
||||
CONFIG_DEF(number/gateway_delay) //How long the gateway takes before it activates. Default is half an hour.
|
||||
/datum/config_entry/number/gateway_delay //How long the gateway takes before it activates. Default is half an hour.
|
||||
value = 18000
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/ghost_interaction)
|
||||
/datum/config_entry/flag/ghost_interaction
|
||||
|
||||
CONFIG_DEF(flag/silent_ai)
|
||||
CONFIG_DEF(flag/silent_borg)
|
||||
/datum/config_entry/flag/silent_ai
|
||||
/datum/config_entry/flag/silent_borg
|
||||
|
||||
CONFIG_DEF(flag/sandbox_autoclose) // close the sandbox panel after spawning an item, potentially reducing griff
|
||||
/datum/config_entry/flag/sandbox_autoclose // close the sandbox panel after spawning an item, potentially reducing griff
|
||||
|
||||
CONFIG_DEF(number/default_laws) //Controls what laws the AI spawns with.
|
||||
/datum/config_entry/number/default_laws //Controls what laws the AI spawns with.
|
||||
value = 0
|
||||
min_val = 0
|
||||
max_val = 3
|
||||
|
||||
CONFIG_DEF(number/silicon_max_law_amount)
|
||||
/datum/config_entry/number/silicon_max_law_amount
|
||||
value = 12
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(keyed_flag_list/random_laws)
|
||||
/datum/config_entry/keyed_flag_list/random_laws
|
||||
|
||||
CONFIG_DEF(keyed_number_list/law_weight)
|
||||
/datum/config_entry/keyed_number_list/law_weight
|
||||
splitter = ","
|
||||
|
||||
CONFIG_DEF(number/assistant_cap)
|
||||
/datum/config_entry/number/assistant_cap
|
||||
value = -1
|
||||
min_val = -1
|
||||
|
||||
CONFIG_DEF(flag/starlight)
|
||||
CONFIG_DEF(flag/grey_assistants)
|
||||
/datum/config_entry/flag/starlight
|
||||
/datum/config_entry/flag/grey_assistants
|
||||
|
||||
CONFIG_DEF(number/lavaland_budget)
|
||||
/datum/config_entry/number/lavaland_budget
|
||||
value = 60
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/space_budget)
|
||||
/datum/config_entry/number/space_budget
|
||||
value = 16
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(flag/allow_random_events) // Enables random events mid-round when set
|
||||
/datum/config_entry/flag/allow_random_events // Enables random events mid-round when set
|
||||
|
||||
CONFIG_DEF(number/events_min_time_mul) // Multipliers for random events minimal starting time and minimal players amounts
|
||||
/datum/config_entry/number/events_min_time_mul // Multipliers for random events minimal starting time and minimal players amounts
|
||||
value = 1
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(number/events_min_players_mul)
|
||||
/datum/config_entry/number/events_min_players_mul
|
||||
value = 1
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(number/mice_roundstart)
|
||||
/datum/config_entry/number/mice_roundstart
|
||||
value = 10
|
||||
min_val = 0
|
||||
|
||||
CONFIG_DEF(number/bombcap)
|
||||
/datum/config_entry/number/bombcap
|
||||
value = 14
|
||||
min_val = 4
|
||||
|
||||
CONFIG_DEF(flag/allow_crew_objectives)
|
||||
CONFIG_DEF(flag/allow_miscreants)
|
||||
CONFIG_DEF(flag/allow_extended_miscreants)
|
||||
//Cit changes - Adds config options for crew objectives and miscreants
|
||||
/datum/config_entry/flag/allow_crew_objectives
|
||||
|
||||
/datum/config_entry/flag/allow_miscreants
|
||||
|
||||
/datum/config_entry/flag/allow_extended_miscreants
|
||||
//End of Cit changes
|
||||
|
||||
/datum/config_entry/number/bombcap/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
@@ -258,9 +260,9 @@ CONFIG_DEF(flag/allow_extended_miscreants)
|
||||
GLOB.MAX_EX_FLASH_RANGE = value
|
||||
GLOB.MAX_EX_FLAME_RANGE = value
|
||||
|
||||
CONFIG_DEF(number/emergency_shuttle_autocall_threshold)
|
||||
/datum/config_entry/number/emergency_shuttle_autocall_threshold
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
integer = FALSE
|
||||
|
||||
CONFIG_DEF(flag/ic_printing)
|
||||
/datum/config_entry/flag/ic_printing
|
||||
|
||||
@@ -0,0 +1,388 @@
|
||||
/datum/config_entry/flag/autoadmin // if autoadmin is enabled
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/string/autoadmin_rank // the rank for autoadmins
|
||||
value = "Game Master"
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/string/servername // server name (the name of the game window)
|
||||
|
||||
/datum/config_entry/string/serversqlname // short form server name used for the DB
|
||||
|
||||
/datum/config_entry/string/stationname // station name (the name of the station in-game)
|
||||
|
||||
/datum/config_entry/number/lobby_countdown // In between round countdown.
|
||||
value = 120
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/round_end_countdown // Post round murder death kill countdown
|
||||
value = 25
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/flag/hub // if the game appears on the hub or not
|
||||
|
||||
/datum/config_entry/flag/log_ooc // log OOC channel
|
||||
|
||||
/datum/config_entry/flag/log_access // log login/logout
|
||||
|
||||
/datum/config_entry/flag/log_say // log client say
|
||||
|
||||
/datum/config_entry/flag/log_admin // log admin actions
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/flag/log_prayer // log prayers
|
||||
|
||||
/datum/config_entry/flag/log_law // log lawchanges
|
||||
|
||||
/datum/config_entry/flag/log_game // log game events
|
||||
|
||||
/datum/config_entry/flag/log_vote // log voting
|
||||
|
||||
/datum/config_entry/flag/log_whisper // log client whisper
|
||||
|
||||
/datum/config_entry/flag/log_attack // log attack messages
|
||||
|
||||
/datum/config_entry/flag/log_emote // log emotes
|
||||
|
||||
/datum/config_entry/flag/log_adminchat // log admin chat messages
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/flag/log_pda // log pda messages
|
||||
|
||||
/datum/config_entry/flag/log_twitter // log certain expliotable parrots and other such fun things in a JSON file of twitter valid phrases.
|
||||
|
||||
/datum/config_entry/flag/log_world_topic // log all world.Topic() calls
|
||||
|
||||
/datum/config_entry/flag/log_manifest // log crew manifest to seperate file
|
||||
|
||||
/datum/config_entry/flag/allow_admin_ooccolor // Allows admins with relevant permissions to have their own ooc colour
|
||||
|
||||
/datum/config_entry/flag/allow_vote_restart // allow votes to restart
|
||||
|
||||
/datum/config_entry/flag/allow_vote_mode // allow votes to change mode
|
||||
|
||||
/datum/config_entry/number/vote_delay // minimum time between voting sessions (deciseconds, 10 minute default)
|
||||
value = 6000
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/vote_period // length of voting period (deciseconds, default 1 minute)
|
||||
value = 600
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/flag/default_no_vote // vote does not default to nochange/norestart
|
||||
|
||||
/datum/config_entry/flag/no_dead_vote // dead people can't vote
|
||||
|
||||
/datum/config_entry/flag/allow_metadata // Metadata is supported.
|
||||
|
||||
/datum/config_entry/flag/popup_admin_pm // adminPMs to non-admins show in a pop-up 'reply' window when set
|
||||
|
||||
/datum/config_entry/number/fps
|
||||
value = 20
|
||||
min_val = 1
|
||||
max_val = 100 //byond will start crapping out at 50, so this is just ridic
|
||||
var/sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/number/fps/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
sync_validate = TRUE
|
||||
var/datum/config_entry/number/ticklag/TL = config.entries_by_type[/datum/config_entry/number/ticklag]
|
||||
if(!TL.sync_validate)
|
||||
TL.ValidateAndSet(10 / value)
|
||||
sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/number/ticklag
|
||||
integer = FALSE
|
||||
var/sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/number/ticklag/New() //ticklag weirdly just mirrors fps
|
||||
var/datum/config_entry/CE = /datum/config_entry/number/fps
|
||||
value = 10 / initial(CE.value)
|
||||
..()
|
||||
|
||||
/datum/config_entry/number/ticklag/ValidateAndSet(str_val)
|
||||
. = text2num(str_val) > 0 && ..()
|
||||
if(.)
|
||||
sync_validate = TRUE
|
||||
var/datum/config_entry/number/fps/FPS = config.entries_by_type[/datum/config_entry/number/fps]
|
||||
if(!FPS.sync_validate)
|
||||
FPS.ValidateAndSet(10 / value)
|
||||
sync_validate = FALSE
|
||||
|
||||
/datum/config_entry/flag/allow_holidays
|
||||
|
||||
/datum/config_entry/number/tick_limit_mc_init //SSinitialization throttling
|
||||
value = TICK_LIMIT_MC_INIT_DEFAULT
|
||||
min_val = 0 //oranges warned us
|
||||
integer = FALSE
|
||||
|
||||
/datum/config_entry/flag/admin_legacy_system //Defines whether the server uses the legacy admin system with admins.txt or the SQL system
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/string/hostedby
|
||||
|
||||
/datum/config_entry/flag/norespawn
|
||||
|
||||
/datum/config_entry/flag/guest_jobban
|
||||
|
||||
/datum/config_entry/flag/usewhitelist
|
||||
|
||||
/datum/config_entry/flag/ban_legacy_system //Defines whether the server uses the legacy banning system with the files in /data or the SQL system.
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/flag/use_age_restriction_for_jobs //Do jobs use account age restrictions? --requires database
|
||||
|
||||
/datum/config_entry/flag/use_account_age_for_jobs //Uses the time they made the account for the job restriction stuff. New player joining alerts should be unaffected.
|
||||
|
||||
/datum/config_entry/flag/use_exp_tracking
|
||||
|
||||
/datum/config_entry/flag/use_exp_restrictions_heads
|
||||
|
||||
/datum/config_entry/number/use_exp_restrictions_heads_hours
|
||||
value = 0
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/flag/use_exp_restrictions_heads_department
|
||||
|
||||
/datum/config_entry/flag/use_exp_restrictions_other
|
||||
|
||||
/datum/config_entry/flag/use_exp_restrictions_admin_bypass
|
||||
|
||||
/datum/config_entry/string/server
|
||||
|
||||
/datum/config_entry/string/banappeals
|
||||
|
||||
/datum/config_entry/string/wikiurl
|
||||
value = "http://www.tgstation13.org/wiki"
|
||||
|
||||
/datum/config_entry/string/forumurl
|
||||
value = "http://tgstation13.org/phpBB/index.php"
|
||||
|
||||
/datum/config_entry/string/rulesurl
|
||||
value = "http://www.tgstation13.org/wiki/Rules"
|
||||
|
||||
/datum/config_entry/string/githuburl
|
||||
value = "https://www.github.com/tgstation/-tg-station"
|
||||
|
||||
/datum/config_entry/number/githubrepoid
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/flag/guest_ban
|
||||
|
||||
/datum/config_entry/number/id_console_jobslot_delay
|
||||
value = 30
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/inactivity_period //time in ds until a player is considered inactive
|
||||
value = 3000
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/inactivity_period/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
value *= 10 //documented as seconds in config.txt
|
||||
|
||||
/datum/config_entry/number/afk_period //time in ds until a player is considered inactive
|
||||
value = 3000
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/afk_period/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(.)
|
||||
value *= 10 //documented as seconds in config.txt
|
||||
|
||||
/datum/config_entry/flag/kick_inactive //force disconnect for inactive players
|
||||
|
||||
/datum/config_entry/flag/load_jobs_from_txt
|
||||
|
||||
/datum/config_entry/flag/forbid_singulo_possession
|
||||
|
||||
/datum/config_entry/flag/automute_on //enables automuting/spam prevention
|
||||
|
||||
/datum/config_entry/string/panic_server_name
|
||||
|
||||
/datum/config_entry/string/panic_server_name/ValidateAndSet(str_val)
|
||||
return str_val != "\[Put the name here\]" && ..()
|
||||
|
||||
/datum/config_entry/string/panic_server_address //Reconnect a player this linked server if this server isn't accepting new players
|
||||
|
||||
/datum/config_entry/string/panic_server_address/ValidateAndSet(str_val)
|
||||
return str_val != "byond://address:port" && ..()
|
||||
|
||||
/datum/config_entry/string/invoke_youtubedl
|
||||
protection = CONFIG_ENTRY_LOCKED | CONFIG_ENTRY_HIDDEN
|
||||
|
||||
/datum/config_entry/flag/show_irc_name
|
||||
|
||||
/datum/config_entry/flag/see_own_notes //Can players see their own admin notes
|
||||
|
||||
/datum/config_entry/number/note_fresh_days
|
||||
value = null
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
/datum/config_entry/number/note_stale_days
|
||||
value = null
|
||||
min_val = 0
|
||||
integer = FALSE
|
||||
|
||||
/datum/config_entry/flag/maprotation
|
||||
|
||||
/datum/config_entry/number/maprotatechancedelta
|
||||
value = 0.75
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
integer = FALSE
|
||||
|
||||
/datum/config_entry/number/soft_popcap
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/hard_popcap
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/extreme_popcap
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/string/soft_popcap_message
|
||||
value = "Be warned that the server is currently serving a high number of users, consider using alternative game servers."
|
||||
|
||||
/datum/config_entry/string/hard_popcap_message
|
||||
value = "The server is currently serving a high number of users, You cannot currently join. You may wait for the number of living crew to decline, observe, or find alternative servers."
|
||||
|
||||
/datum/config_entry/string/extreme_popcap_message
|
||||
value = "The server is currently serving a high number of users, find alternative servers."
|
||||
|
||||
/datum/config_entry/flag/panic_bunker // prevents people the server hasn't seen before from connecting
|
||||
|
||||
/datum/config_entry/number/notify_new_player_age // how long do we notify admins of a new player
|
||||
min_val = -1
|
||||
|
||||
/datum/config_entry/number/notify_new_player_account_age // how long do we notify admins of a new byond account
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/flag/irc_first_connection_alert // do we notify the irc channel when somebody is connecting for the first time?
|
||||
|
||||
/datum/config_entry/flag/check_randomizer
|
||||
|
||||
/datum/config_entry/string/ipintel_email
|
||||
|
||||
/datum/config_entry/string/ipintel_email/ValidateAndSet(str_val)
|
||||
return str_val != "ch@nge.me" && ..()
|
||||
|
||||
/datum/config_entry/number/ipintel_rating_bad
|
||||
value = 1
|
||||
integer = FALSE
|
||||
min_val = 0
|
||||
max_val = 1
|
||||
|
||||
/datum/config_entry/number/ipintel_save_good
|
||||
value = 12
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/ipintel_save_bad
|
||||
value = 1
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/string/ipintel_domain
|
||||
value = "check.getipintel.net"
|
||||
|
||||
/datum/config_entry/flag/aggressive_changelog
|
||||
|
||||
/datum/config_entry/flag/autoconvert_notes //if all connecting player's notes should attempt to be converted to the database
|
||||
protection = CONFIG_ENTRY_LOCKED
|
||||
|
||||
/datum/config_entry/flag/allow_webclient
|
||||
|
||||
/datum/config_entry/flag/webclient_only_byond_members
|
||||
|
||||
/datum/config_entry/flag/announce_admin_logout
|
||||
|
||||
/datum/config_entry/flag/announce_admin_login
|
||||
|
||||
/datum/config_entry/flag/allow_map_voting
|
||||
|
||||
/datum/config_entry/flag/generate_minimaps
|
||||
|
||||
/datum/config_entry/number/client_warn_version
|
||||
value = null
|
||||
min_val = 500
|
||||
max_val = DM_VERSION - 1
|
||||
|
||||
/datum/config_entry/string/client_warn_message
|
||||
value = "Your version of byond may have issues or be blocked from accessing this server in the future."
|
||||
|
||||
/datum/config_entry/flag/client_warn_popup
|
||||
|
||||
/datum/config_entry/number/client_error_version
|
||||
value = null
|
||||
min_val = 500
|
||||
max_val = DM_VERSION - 1
|
||||
|
||||
/datum/config_entry/string/client_error_message
|
||||
value = "Your version of byond is too old, may have issues, and is blocked from accessing this server."
|
||||
|
||||
/datum/config_entry/number/minute_topic_limit
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/second_topic_limit
|
||||
value = null
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/error_cooldown // The "cooldown" time for each occurrence of a unique error
|
||||
value = 600
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/number/error_limit // How many occurrences before the next will silence them
|
||||
value = 50
|
||||
|
||||
/datum/config_entry/number/error_silence_time // How long a unique error will be silenced for
|
||||
value = 6000
|
||||
|
||||
/datum/config_entry/number/error_msg_delay // How long to wait between messaging admins about occurrences of a unique error
|
||||
value = 50
|
||||
|
||||
/datum/config_entry/flag/irc_announce_new_game
|
||||
|
||||
/datum/config_entry/flag/debug_admin_hrefs
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate/base_mc_tick_rate
|
||||
integer = FALSE
|
||||
value = 1
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate/high_pop_mc_tick_rate
|
||||
integer = FALSE
|
||||
value = 1.1
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate/high_pop_mc_mode_amount
|
||||
value = 65
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate/disable_high_pop_mc_mode_amount
|
||||
value = 60
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate
|
||||
abstract_type = /datum/config_entry/number/mc_tick_rate
|
||||
|
||||
/datum/config_entry/number/mc_tick_rate/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if (.)
|
||||
Master.UpdateTickRate()
|
||||
|
||||
/datum/config_entry/flag/resume_after_initializations
|
||||
|
||||
/datum/config_entry/flag/resume_after_initializations/ValidateAndSet(str_val)
|
||||
. = ..()
|
||||
if(. && Master.current_runlevel)
|
||||
world.sleep_offline = !value
|
||||
|
||||
/datum/config_entry/number/rounds_until_hard_restart
|
||||
value = -1
|
||||
min_val = 0
|
||||
|
||||
/datum/config_entry/string/default_view
|
||||
value = "15x15"
|
||||
@@ -301,7 +301,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
|
||||
continue
|
||||
|
||||
//Byond resumed us late. assume it might have to do the same next tick
|
||||
if (last_run + Ceiling(world.tick_lag * (processing * sleep_delta), world.tick_lag) < world.time)
|
||||
if (last_run + CEILING(world.tick_lag * (processing * sleep_delta), world.tick_lag) < world.time)
|
||||
sleep_delta += 1
|
||||
|
||||
sleep_delta = MC_AVERAGE_FAST(sleep_delta, 1) //decay sleep_delta
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
|
||||
var/flags = 0 //see MC.dm in __DEFINES Most flags must be set on world start to take full effect. (You can also restart the mc to force them to process again)
|
||||
|
||||
var/initialized = FALSE //set to TRUE after it has been initialized, will obviously never be set if the subsystem doesn't initialize
|
||||
|
||||
//set to 0 to prevent fire() calls, mostly for admin use or subsystems that may be resumed later
|
||||
// use the SS_NO_FIRE flag instead for systems that never fire to keep it from even being added to the list
|
||||
var/can_fire = TRUE
|
||||
@@ -156,6 +158,7 @@
|
||||
|
||||
//used to initialize the subsystem AFTER the map has loaded
|
||||
/datum/controller/subsystem/Initialize(start_timeofday)
|
||||
initialized = TRUE
|
||||
var/time = (REALTIMEOFDAY - start_timeofday) / 10
|
||||
var/msg = "Initialized [name] subsystem within [time] second[time == 1 ? "" : "s"]!"
|
||||
to_chat(world, "<span class='boldannounce'>[msg]</span>")
|
||||
|
||||
@@ -8,7 +8,6 @@ SUBSYSTEM_DEF(atoms)
|
||||
init_order = INIT_ORDER_ATOMS
|
||||
flags = SS_NO_FIRE
|
||||
|
||||
var/initialized = INITIALIZATION_INSSATOMS
|
||||
var/old_initialized
|
||||
|
||||
var/list/late_loaders
|
||||
|
||||
@@ -0,0 +1,12 @@
|
||||
SUBSYSTEM_DEF(input)
|
||||
name = "Input"
|
||||
wait = 1 //SS_TICKER means this runs every tick
|
||||
flags = SS_TICKER | SS_NO_INIT
|
||||
priority = 1000
|
||||
runlevels = RUNLEVELS_DEFAULT | RUNLEVEL_LOBBY
|
||||
|
||||
/datum/controller/subsystem/input/fire()
|
||||
var/list/clients = GLOB.clients // Let's sing the list cache song
|
||||
for(var/i in 1 to clients.len)
|
||||
var/client/C = clients[i]
|
||||
C.keyLoop()
|
||||
@@ -8,8 +8,6 @@ SUBSYSTEM_DEF(lighting)
|
||||
init_order = INIT_ORDER_LIGHTING
|
||||
flags = SS_TICKER
|
||||
|
||||
var/initialized = FALSE
|
||||
|
||||
/datum/controller/subsystem/lighting/stat_entry()
|
||||
..("L:[GLOB.lighting_update_lights.len]|C:[GLOB.lighting_update_corners.len]|O:[GLOB.lighting_update_objects.len]")
|
||||
|
||||
|
||||
@@ -1,14 +1,18 @@
|
||||
SUBSYSTEM_DEF(mobs)
|
||||
name = "Mobs"
|
||||
priority = 100
|
||||
flags = SS_KEEP_TIMING|SS_NO_INIT
|
||||
flags = SS_KEEP_TIMING
|
||||
runlevels = RUNLEVEL_GAME | RUNLEVEL_POSTGAME
|
||||
|
||||
var/list/currentrun = list()
|
||||
var/static/list/clients_by_zlevel[][]
|
||||
|
||||
/datum/controller/subsystem/mobs/stat_entry()
|
||||
..("P:[GLOB.mob_living_list.len]")
|
||||
|
||||
/datum/controller/subsystem/mobs/Initialize(start_timeofday)
|
||||
clients_by_zlevel = new /list(world.maxz,0)
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/mobs/fire(resumed = 0)
|
||||
var/seconds = wait * 0.1
|
||||
|
||||
@@ -10,7 +10,6 @@ SUBSYSTEM_DEF(overlays)
|
||||
var/list/stats
|
||||
var/list/overlay_icon_state_caches
|
||||
var/list/overlay_icon_cache
|
||||
var/initialized = FALSE
|
||||
|
||||
/datum/controller/subsystem/overlays/PreInit()
|
||||
overlay_icon_state_caches = list()
|
||||
|
||||
@@ -44,10 +44,20 @@ PROCESSING_SUBSYSTEM_DEF(circuit)
|
||||
|
||||
|
||||
circuit_fabricator_recipe_list["Assemblies"] = list(
|
||||
/obj/item/device/electronic_assembly,
|
||||
/obj/item/device/electronic_assembly/medium,
|
||||
/obj/item/device/electronic_assembly/large,
|
||||
/obj/item/device/electronic_assembly/drone
|
||||
/obj/item/device/electronic_assembly/default,
|
||||
/obj/item/device/electronic_assembly/calc,
|
||||
/obj/item/device/electronic_assembly/clam,
|
||||
/obj/item/device/electronic_assembly/simple,
|
||||
/obj/item/device/electronic_assembly/medium/default,
|
||||
/obj/item/device/electronic_assembly/medium/box,
|
||||
/obj/item/device/electronic_assembly/medium/clam,
|
||||
/obj/item/device/electronic_assembly/medium/medical,
|
||||
/obj/item/device/electronic_assembly/large/default,
|
||||
/obj/item/device/electronic_assembly/large/scope,
|
||||
/obj/item/device/electronic_assembly/large/terminal,
|
||||
/obj/item/device/electronic_assembly/large/arm,
|
||||
/obj/item/device/electronic_assembly/drone/default,
|
||||
/obj/item/device/electronic_assembly/drone/arms
|
||||
///obj/item/weapon/implant/integrated_circuit
|
||||
)
|
||||
|
||||
|
||||
@@ -0,0 +1,75 @@
|
||||
|
||||
SUBSYSTEM_DEF(research)
|
||||
name = "Research"
|
||||
flags = SS_KEEP_TIMING
|
||||
priority = 15 //My powergame is priority.
|
||||
wait = 10
|
||||
init_order = INIT_ORDER_RESEARCH
|
||||
var/list/invalid_design_ids = list() //associative id = number of times
|
||||
var/list/invalid_node_ids = list() //associative id = number of times
|
||||
var/list/invalid_node_boost = list() //associative id = error message
|
||||
var/list/obj/machinery/rnd/server/servers = list()
|
||||
var/datum/techweb/science/science_tech
|
||||
var/datum/techweb/admin/admin_tech
|
||||
var/list/techweb_nodes = list() //associative id = node datum
|
||||
var/list/techweb_categories = list() //category name = list(node.id = node)
|
||||
var/list/techweb_designs = list() //associative id = node datum
|
||||
var/list/techweb_nodes_starting = list() //associative id = node datum
|
||||
var/list/techweb_boost_items = list() //associative double-layer path = list(id = point_discount)
|
||||
var/list/techweb_nodes_hidden = list() //Nodes that should be hidden by default.
|
||||
var/list/techweb_point_items = list() //path = value
|
||||
var/list/errored_datums = list()
|
||||
//----------------------------------------------
|
||||
var/single_server_income = 40.7
|
||||
var/multiserver_calculation = FALSE
|
||||
var/last_income = 0
|
||||
//^^^^^^^^ ALL OF THESE ARE PER SECOND! ^^^^^^^^
|
||||
|
||||
//Aiming for 1.5 hours to max R&D
|
||||
//[88nodes * 5000points/node] / [1.5hr * 90min/hr * 60s/min]
|
||||
//Around 450000 points max???
|
||||
|
||||
var/bomb_research_point_scaling = 1800
|
||||
|
||||
/datum/controller/subsystem/research/Initialize()
|
||||
initialize_all_techweb_designs()
|
||||
initialize_all_techweb_nodes()
|
||||
science_tech = new /datum/techweb/science
|
||||
admin_tech = new /datum/techweb/admin
|
||||
autosort_categories()
|
||||
return ..()
|
||||
|
||||
/datum/controller/subsystem/research/fire()
|
||||
handle_research_income()
|
||||
|
||||
/datum/controller/subsystem/research/proc/handle_research_income()
|
||||
var/bitcoins = 0
|
||||
if(multiserver_calculation)
|
||||
var/eff = calculate_server_coefficient()
|
||||
for(var/obj/machinery/rnd/server/miner in servers)
|
||||
bitcoins += (miner.mine() * eff) //SLAVE AWAY, SLAVE.
|
||||
else
|
||||
for(var/obj/machinery/rnd/server/miner in servers)
|
||||
if(miner.working)
|
||||
bitcoins = single_server_income
|
||||
break //Just need one to work.
|
||||
var/income_time_difference = world.time - last_income
|
||||
bitcoins *= income_time_difference / 10
|
||||
science_tech.research_points += bitcoins
|
||||
last_income = world.time
|
||||
|
||||
/datum/controller/subsystem/research/proc/calculate_server_coefficient() //Diminishing returns.
|
||||
var/amt = servers.len
|
||||
if(!amt)
|
||||
return 0
|
||||
var/coeff = 100
|
||||
coeff = sqrt(coeff / amt)
|
||||
return coeff
|
||||
|
||||
/datum/controller/subsystem/research/proc/autosort_categories()
|
||||
for(var/i in techweb_nodes)
|
||||
var/datum/techweb_node/I = techweb_nodes[i]
|
||||
if(techweb_categories[I.category])
|
||||
techweb_categories[I.category][I.id] = I
|
||||
else
|
||||
techweb_categories[I.category] = list(I.id = I)
|
||||
@@ -307,6 +307,9 @@ SUBSYSTEM_DEF(shuttle)
|
||||
return 1
|
||||
|
||||
/datum/controller/subsystem/shuttle/proc/autoEvac()
|
||||
if (!SSticker.IsRoundInProgress())
|
||||
return
|
||||
|
||||
var/callShuttle = 1
|
||||
|
||||
for(var/thing in GLOB.shuttle_caller_list)
|
||||
|
||||
@@ -80,7 +80,7 @@ SUBSYSTEM_DEF(throwing)
|
||||
last_move = world.time
|
||||
|
||||
//calculate how many tiles to move, making up for any missed ticks.
|
||||
var/tilestomove = Ceiling(min(((((world.time+world.tick_lag) - start_time + delayed_time) * speed) - (dist_travelled ? dist_travelled : -1)), speed*MAX_TICKS_TO_MAKE_UP) * (world.tick_lag * SSthrowing.wait))
|
||||
var/tilestomove = CEILING(min(((((world.time+world.tick_lag) - start_time + delayed_time) * speed) - (dist_travelled ? dist_travelled : -1)), speed*MAX_TICKS_TO_MAKE_UP) * (world.tick_lag * SSthrowing.wait), 1)
|
||||
while (tilestomove-- > 0)
|
||||
if ((dist_travelled >= maxrange || AM.loc == target_turf) && AM.has_gravity(AM.loc))
|
||||
finalize()
|
||||
|
||||
@@ -165,7 +165,7 @@ SUBSYSTEM_DEF(vote)
|
||||
|
||||
var/admin = FALSE
|
||||
var/ckey = ckey(initiator_key)
|
||||
if((GLOB.admin_datums[ckey]) || (ckey in GLOB.deadmins))
|
||||
if(GLOB.admin_datums[ckey])
|
||||
admin = TRUE
|
||||
|
||||
if(next_allowed_time > world.time && !admin)
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
name = "Nuclear Operative"
|
||||
roundend_category = "syndicate operatives" //just in case
|
||||
job_rank = ROLE_OPERATIVE
|
||||
var/datum/objective_team/nuclear/nuke_team
|
||||
var/datum/team/nuclear/nuke_team
|
||||
var/always_new_team = FALSE //If not assigned a team by default ops will try to join existing ones, set this to TRUE to always create new team.
|
||||
var/send_to_spawnpoint = TRUE //Should the user be moved to default spawnpoint.
|
||||
var/nukeop_outfit = /datum/outfit/syndicate
|
||||
@@ -39,7 +39,7 @@
|
||||
if(!ishuman(owner.current))
|
||||
return
|
||||
var/mob/living/carbon/human/H = owner.current
|
||||
|
||||
|
||||
H.set_species(/datum/species/human) //Plasamen burn up otherwise, and lizards are vulnerable to asimov AIs
|
||||
|
||||
H.equipOutfit(nukeop_outfit)
|
||||
@@ -103,14 +103,14 @@
|
||||
/datum/antagonist/nukeop/leader/move_to_spawnpoint()
|
||||
owner.current.forceMove(pick(GLOB.nukeop_leader_start))
|
||||
|
||||
/datum/antagonist/nukeop/create_team(datum/objective_team/nuclear/new_team)
|
||||
/datum/antagonist/nukeop/create_team(datum/team/nuclear/new_team)
|
||||
if(!new_team)
|
||||
if(!always_new_team)
|
||||
for(var/datum/antagonist/nukeop/N in GLOB.antagonists)
|
||||
if(N.nuke_team)
|
||||
nuke_team = N.nuke_team
|
||||
return
|
||||
nuke_team = new /datum/objective_team/nuclear
|
||||
nuke_team = new /datum/team/nuclear
|
||||
nuke_team.update_objectives()
|
||||
assign_nuke() //This is bit ugly
|
||||
return
|
||||
@@ -158,7 +158,7 @@
|
||||
return
|
||||
nuke_team.rename_team(ask_name())
|
||||
|
||||
/datum/objective_team/nuclear/proc/rename_team(new_name)
|
||||
/datum/team/nuclear/proc/rename_team(new_name)
|
||||
syndicate_name = new_name
|
||||
name = "[syndicate_name] Team"
|
||||
for(var/I in members)
|
||||
@@ -201,40 +201,40 @@
|
||||
stack_trace("Station self destruct ot found during lone op team creation.")
|
||||
nuke_team.memorized_code = null
|
||||
|
||||
/datum/objective_team/nuclear
|
||||
/datum/team/nuclear
|
||||
var/syndicate_name
|
||||
var/obj/machinery/nuclearbomb/tracked_nuke
|
||||
var/core_objective = /datum/objective/nuclear
|
||||
var/memorized_code
|
||||
|
||||
/datum/objective_team/nuclear/New()
|
||||
/datum/team/nuclear/New()
|
||||
..()
|
||||
syndicate_name = syndicate_name()
|
||||
|
||||
/datum/objective_team/nuclear/proc/update_objectives()
|
||||
/datum/team/nuclear/proc/update_objectives()
|
||||
if(core_objective)
|
||||
var/datum/objective/O = new core_objective
|
||||
O.team = src
|
||||
objectives += O
|
||||
|
||||
/datum/objective_team/nuclear/proc/disk_rescued()
|
||||
/datum/team/nuclear/proc/disk_rescued()
|
||||
for(var/obj/item/disk/nuclear/D in GLOB.poi_list)
|
||||
if(!D.onCentCom())
|
||||
return FALSE
|
||||
return TRUE
|
||||
|
||||
/datum/objective_team/nuclear/proc/operatives_dead()
|
||||
/datum/team/nuclear/proc/operatives_dead()
|
||||
for(var/I in members)
|
||||
var/datum/mind/operative_mind = I
|
||||
if(ishuman(operative_mind.current) && (operative_mind.current.stat != DEAD))
|
||||
return FALSE
|
||||
return TRUE
|
||||
|
||||
/datum/objective_team/nuclear/proc/syndies_escaped()
|
||||
/datum/team/nuclear/proc/syndies_escaped()
|
||||
var/obj/docking_port/mobile/S = SSshuttle.getShuttle("syndicate")
|
||||
return (S && (S.z == ZLEVEL_CENTCOM || S.z == ZLEVEL_TRANSIT))
|
||||
|
||||
/datum/objective_team/nuclear/proc/get_result()
|
||||
/datum/team/nuclear/proc/get_result()
|
||||
var/evacuation = SSshuttle.emergency.mode == SHUTTLE_ENDGAME
|
||||
var/disk_rescued = disk_rescued()
|
||||
var/syndies_didnt_escape = !syndies_escaped()
|
||||
@@ -262,10 +262,10 @@
|
||||
else
|
||||
return //Undefined result
|
||||
|
||||
/datum/objective_team/nuclear/roundend_report()
|
||||
/datum/team/nuclear/roundend_report()
|
||||
var/list/parts = list()
|
||||
parts += "<span class='header'>[syndicate_name] Operatives:</span>"
|
||||
|
||||
|
||||
switch(get_result())
|
||||
if(NUKE_RESULT_FLUKE)
|
||||
parts += "<span class='redtext big'>Humiliating Syndicate Defeat</span>"
|
||||
@@ -306,7 +306,7 @@
|
||||
for(var/U in GLOB.uplinks)
|
||||
var/datum/component/uplink/H = U
|
||||
if(H.owner == syndicate.key)
|
||||
TC_uses += H.spent_telecrystals
|
||||
TC_uses += H.purchase_log.total_spent
|
||||
if(H.purchase_log)
|
||||
purchases += H.purchase_log.generate_render(show_key = FALSE)
|
||||
else
|
||||
@@ -316,7 +316,7 @@
|
||||
text += "(Syndicates used [TC_uses] TC) [purchases]"
|
||||
if(TC_uses == 0 && SSticker.mode.station_was_nuked && !operatives_dead())
|
||||
text += "<BIG>[icon2html('icons/badass.dmi', world, "badass")]</BIG>"
|
||||
|
||||
|
||||
parts += text
|
||||
|
||||
return "<div class='panel redborder'>[parts.Join("<br>")]</div>"
|
||||
|
||||
+2
-2
@@ -128,11 +128,11 @@
|
||||
//Position the effect so the beam is one continous line
|
||||
var/a
|
||||
if(abs(Pixel_x)>32)
|
||||
a = Pixel_x > 0 ? round(Pixel_x/32) : Ceiling(Pixel_x/32)
|
||||
a = Pixel_x > 0 ? round(Pixel_x/32) : CEILING(Pixel_x/32, 1)
|
||||
X.x += a
|
||||
Pixel_x %= 32
|
||||
if(abs(Pixel_y)>32)
|
||||
a = Pixel_y > 0 ? round(Pixel_y/32) : Ceiling(Pixel_y/32)
|
||||
a = Pixel_y > 0 ? round(Pixel_y/32) : CEILING(Pixel_y/32, 1)
|
||||
X.y += a
|
||||
Pixel_y %= 32
|
||||
|
||||
|
||||
@@ -27,6 +27,8 @@
|
||||
if(LAZYLEN(candidates))
|
||||
var/client/C = pick(candidates)
|
||||
stranger_backseat.key = C.key
|
||||
log_game("[key_name(stranger_backseat)] became [key_name(owner)]'s split personality.")
|
||||
message_admins("[key_name_admin(stranger_backseat)] became [key_name_admin(owner)]'s split personality.")
|
||||
else
|
||||
qdel(src)
|
||||
|
||||
@@ -59,7 +61,7 @@
|
||||
current_backseat = owner_backseat
|
||||
free_backseat = stranger_backseat
|
||||
|
||||
log_game("[current_backseat]/([current_backseat.ckey]) assumed control of [owner]/([owner.ckey] due to [src]. (Original owner: [current_controller == OWNER ? owner.ckey : current_backseat.ckey])")
|
||||
log_game("[key_name(current_backseat)] assumed control of [key_name(owner)] due to [src]. (Original owner: [current_controller == OWNER ? owner.ckey : current_backseat.ckey])")
|
||||
to_chat(owner, "<span class='userdanger'>You feel your control being taken away... your other personality is in charge now!</span>")
|
||||
to_chat(current_backseat, "<span class='userdanger'>You manage to take control of your body!</span>")
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
var/datum/callback/callback
|
||||
|
||||
/datum/component/archaeology/Initialize(_prob2drop, list/_archdrops = list(), datum/callback/_callback)
|
||||
prob2drop = Clamp(_prob2drop, 0, 100)
|
||||
prob2drop = CLAMP(_prob2drop, 0, 100)
|
||||
archdrops = _archdrops
|
||||
callback = _callback
|
||||
RegisterSignal(COMSIG_PARENT_ATTACKBY,.proc/Dig)
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
if(old_dir == new_dir)
|
||||
return
|
||||
remove()
|
||||
var/rotation = SimplifyDegrees(dir2angle(new_dir)-dir2angle(old_dir))
|
||||
var/rotation = SIMPLIFY_DEGREES(dir2angle(new_dir)-dir2angle(old_dir))
|
||||
pic.dir = turn(pic.dir, rotation)
|
||||
apply()
|
||||
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
/datum/component/jousting
|
||||
var/current_direction = NONE
|
||||
var/max_tile_charge = 5
|
||||
var/min_tile_charge = 2 //tiles before this code gets into effect.
|
||||
var/current_tile_charge = 0
|
||||
var/movement_reset_tolerance = 2 //deciseconds
|
||||
var/unmounted_damage_boost_per_tile = 0
|
||||
var/unmounted_knockdown_chance_per_tile = 0
|
||||
var/unmounted_knockdown_time = 0
|
||||
var/mounted_damage_boost_per_tile = 2
|
||||
var/mounted_knockdown_chance_per_tile = 20
|
||||
var/mounted_knockdown_time = 20
|
||||
var/requires_mob_riding = TRUE //whether this only works if the attacker is riding a mob, rather than anything they can buckle to.
|
||||
var/requires_mount = TRUE //kinda defeats the point of jousting if you're not mounted but whatever.
|
||||
var/mob/current_holder
|
||||
var/datum/component/redirect/listener
|
||||
var/current_timerid
|
||||
|
||||
/datum/component/jousting/Initialize()
|
||||
if(!isitem(parent))
|
||||
. = COMPONENT_INCOMPATIBLE
|
||||
stack_trace("Warning: Jousting component incorrectly applied to invalid parent type [parent.type]")
|
||||
RegisterSignal(COMSIG_ITEM_EQUIPPED, .proc/on_equip)
|
||||
RegisterSignal(COMSIG_ITEM_DROPPED, .proc/on_drop)
|
||||
RegisterSignal(COMSIG_ITEM_ATTACK, .proc/on_attack)
|
||||
|
||||
/datum/component/jousting/Destroy()
|
||||
QDEL_NULL(listener)
|
||||
return ..()
|
||||
|
||||
/datum/component/jousting/proc/on_equip(mob/user, slot)
|
||||
QDEL_NULL(listener)
|
||||
current_holder = user
|
||||
listener = new(user, COMSIG_MOVABLE_MOVED, CALLBACK(src, .proc/mob_move))
|
||||
|
||||
/datum/component/jousting/proc/on_drop(mob/user)
|
||||
QDEL_NULL(listener)
|
||||
current_holder = null
|
||||
current_direction = NONE
|
||||
current_tile_charge = 0
|
||||
|
||||
/datum/component/jousting/proc/on_attack(mob/living/target, mob/user)
|
||||
if(user != current_holder)
|
||||
return
|
||||
var/current = current_tile_charge
|
||||
var/obj/item/I = parent
|
||||
var/target_buckled = target.buckled ? TRUE : FALSE //we don't need the reference of what they're buckled to, just whether they are.
|
||||
if((requires_mount && ((requires_mob_riding && !ismob(user.buckled)) || (!user.buckled))) || !current_direction || (current_tile_charge < min_tile_charge))
|
||||
return
|
||||
var/turf/target_turf = get_step(user, current_direction)
|
||||
if(target in range(1, target_turf))
|
||||
var/knockdown_chance = (target_buckled? mounted_knockdown_chance_per_tile : unmounted_knockdown_chance_per_tile) * current
|
||||
var/knockdown_time = (target_buckled? mounted_knockdown_time : unmounted_knockdown_time)
|
||||
var/damage = (target_buckled? mounted_damage_boost_per_tile : unmounted_damage_boost_per_tile) * current
|
||||
var/sharp = I.is_sharp()
|
||||
var/msg
|
||||
if(damage)
|
||||
msg += "[user] [sharp? "impales" : "slams into"] [target] [sharp? "on" : "with"] their [parent]"
|
||||
target.apply_damage(damage, BRUTE, user.zone_selected, 0)
|
||||
if(prob(knockdown_chance))
|
||||
msg += " and knocks [target] [target_buckled? "off of [target.buckled]" : "down"]"
|
||||
if(target_buckled)
|
||||
target.buckled.unbuckle_mob(target)
|
||||
target.Knockdown(knockdown_time)
|
||||
if(length(msg))
|
||||
user.visible_message("<span class='danger'>[msg]!</span>")
|
||||
|
||||
/datum/component/jousting/proc/mob_move(newloc, dir)
|
||||
if(!current_holder || (requires_mount && ((requires_mob_riding && !ismob(current_holder.buckled)) || (!current_holder.buckled))))
|
||||
return
|
||||
if(dir != current_direction)
|
||||
current_tile_charge = 0
|
||||
current_direction = dir
|
||||
if(current_tile_charge < max_tile_charge)
|
||||
current_tile_charge++
|
||||
if(current_timerid)
|
||||
deltimer(current_timerid)
|
||||
current_timerid = addtimer(CALLBACK(src, .proc/reset_charge), movement_reset_tolerance, TIMER_STOPPABLE)
|
||||
|
||||
/datum/component/jousting/proc/reset_charge()
|
||||
current_tile_charge = 0
|
||||
@@ -70,6 +70,7 @@
|
||||
user_insert(I, user)
|
||||
|
||||
/datum/component/material_container/proc/user_insert(obj/item/I, mob/living/user)
|
||||
set waitfor = FALSE
|
||||
var/requested_amount
|
||||
var/Itype = I.type
|
||||
if(ispath(Itype, /obj/item/stack) && precise_insertion)
|
||||
|
||||
@@ -43,7 +43,7 @@
|
||||
addtimer(CALLBACK(src, .proc/charge), charge_rate)
|
||||
|
||||
/datum/action/innate/dash/proc/charge()
|
||||
current_charges = Clamp(current_charges + 1, 0, max_charges)
|
||||
current_charges = CLAMP(current_charges + 1, 0, max_charges)
|
||||
holder.update_action_buttons_icon()
|
||||
if(recharge_sound)
|
||||
playsound(dashing_item, recharge_sound, 50, 1)
|
||||
|
||||
@@ -185,10 +185,10 @@
|
||||
if(properties["stealth"] >= 2)
|
||||
visibility_flags = HIDDEN_SCANNER
|
||||
|
||||
SetSpread(Clamp(2 ** (properties["transmittable"] - symptoms.len), VIRUS_SPREAD_BLOOD, VIRUS_SPREAD_AIRBORNE))
|
||||
SetSpread(CLAMP(2 ** (properties["transmittable"] - symptoms.len), VIRUS_SPREAD_BLOOD, VIRUS_SPREAD_AIRBORNE))
|
||||
|
||||
permeability_mod = max(Ceiling(0.4 * properties["transmittable"]), 1)
|
||||
cure_chance = 15 - Clamp(properties["resistance"], -5, 5) // can be between 10 and 20
|
||||
permeability_mod = max(CEILING(0.4 * properties["transmittable"], 1), 1)
|
||||
cure_chance = 15 - CLAMP(properties["resistance"], -5, 5) // can be between 10 and 20
|
||||
stage_prob = max(properties["stage_rate"], 2)
|
||||
SetSeverity(properties["severity"])
|
||||
GenerateCure(properties)
|
||||
@@ -243,7 +243,7 @@
|
||||
// Will generate a random cure, the less resistance the symptoms have, the harder the cure.
|
||||
/datum/disease/advance/proc/GenerateCure()
|
||||
if(properties && properties.len)
|
||||
var/res = Clamp(properties["resistance"] - (symptoms.len / 2), 1, advance_cures.len)
|
||||
var/res = CLAMP(properties["resistance"] - (symptoms.len / 2), 1, advance_cures.len)
|
||||
cures = list(advance_cures[res])
|
||||
|
||||
// Get the cure name from the cure_id
|
||||
|
||||
@@ -85,9 +85,16 @@ GLOBAL_LIST_EMPTY(explosions)
|
||||
|
||||
var/max_range = max(devastation_range, heavy_impact_range, light_impact_range, flame_range)
|
||||
|
||||
var/area/epi_area = get_area(epicenter)
|
||||
if(adminlog)
|
||||
message_admins("Explosion with size ([devastation_range], [heavy_impact_range], [light_impact_range], [flame_range]) in area: [get_area(epicenter)] [ADMIN_COORDJMP(epicenter)]")
|
||||
message_admins("Explosion with size ([devastation_range], [heavy_impact_range], [light_impact_range], [flame_range]) in area: [epi_area] [ADMIN_COORDJMP(epicenter)]")
|
||||
log_game("Explosion with size ([devastation_range], [heavy_impact_range], [light_impact_range], [flame_range]) in area [epicenter.loc.name] ([epicenter.x],[epicenter.y],[epicenter.z])")
|
||||
|
||||
var/x0 = epicenter.x
|
||||
var/y0 = epicenter.y
|
||||
var/z0 = epicenter.z
|
||||
|
||||
SSblackbox.record_feedback("associative", "explosion", 1, list("dev" = devastation_range, "heavy" = heavy_impact_range, "light" = light_impact_range, "flash" = flash_range, "flame" = flame_range, "orig_dev" = orig_dev_range, "orig_heavy" = orig_heavy_range, "orig_light" = orig_light_range, "x" = x0, "y" = y0, "z" = z0, "area" = epi_area.type))
|
||||
|
||||
// Play sounds; we want sounds to be different depending on distance so we will manually do it ourselves.
|
||||
// Stereo users will also hear the direction of the explosion!
|
||||
@@ -99,10 +106,6 @@ GLOBAL_LIST_EMPTY(explosions)
|
||||
far_dist += heavy_impact_range * 5
|
||||
far_dist += devastation_range * 20
|
||||
|
||||
var/x0 = epicenter.x
|
||||
var/y0 = epicenter.y
|
||||
var/z0 = epicenter.z
|
||||
|
||||
if(!silent)
|
||||
var/frequency = get_rand_frequency()
|
||||
var/sound/explosion_sound = sound(get_sfx("explosion"))
|
||||
@@ -118,7 +121,7 @@ GLOBAL_LIST_EMPTY(explosions)
|
||||
M.playsound_local(epicenter, null, 100, 1, frequency, falloff = 5, S = explosion_sound)
|
||||
// You hear a far explosion if you're outside the blast radius. Small bombs shouldn't be heard all over the station.
|
||||
else if(dist <= far_dist)
|
||||
var/far_volume = Clamp(far_dist, 30, 50) // Volume is based on explosion size and dist
|
||||
var/far_volume = CLAMP(far_dist, 30, 50) // Volume is based on explosion size and dist
|
||||
far_volume += (dist <= far_dist * 0.5 ? 50 : 0) // add 50 volume if the mob is pretty close to the explosion
|
||||
M.playsound_local(epicenter, null, far_volume, 1, frequency, falloff = 5, S = far_explosion_sound)
|
||||
EX_PREPROCESS_CHECK_TICK
|
||||
|
||||
@@ -10,6 +10,7 @@ GLOBAL_LIST_INIT(huds, list(
|
||||
DATA_HUD_MEDICAL_ADVANCED = new/datum/atom_hud/data/human/medical/advanced(),
|
||||
DATA_HUD_DIAGNOSTIC_BASIC = new/datum/atom_hud/data/diagnostic/basic(),
|
||||
DATA_HUD_DIAGNOSTIC_ADVANCED = new/datum/atom_hud/data/diagnostic/advanced(),
|
||||
DATA_HUD_ABDUCTOR = new/datum/atom_hud/abductor(),
|
||||
ANTAG_HUD_CULT = new/datum/atom_hud/antag(),
|
||||
ANTAG_HUD_REV = new/datum/atom_hud/antag(),
|
||||
ANTAG_HUD_OPS = new/datum/atom_hud/antag(),
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
mid_sounds = list('sound/machines/fryer/deep_fryer_1.ogg' = 1, 'sound/machines/fryer/deep_fryer_2.ogg' = 1)
|
||||
mid_length = 2
|
||||
end_sound = 'sound/machines/fryer/deep_fryer_emerge.ogg'
|
||||
volume = 25
|
||||
volume = 15
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
@@ -101,7 +101,7 @@
|
||||
"<span class='userdanger'>[A] slams your chest! You can't breathe!</span>")
|
||||
playsound(get_turf(A), 'sound/effects/hit_punch.ogg', 50, 1, -1)
|
||||
if(D.losebreath <= 10)
|
||||
D.losebreath = Clamp(D.losebreath + 5, 0, 10)
|
||||
D.losebreath = CLAMP(D.losebreath + 5, 0, 10)
|
||||
D.adjustOxyLoss(10)
|
||||
add_logs(A, D, "quickchoked")
|
||||
return 1
|
||||
@@ -112,7 +112,7 @@
|
||||
playsound(get_turf(A), 'sound/effects/hit_punch.ogg', 50, 1, -1)
|
||||
D.apply_damage(5, BRUTE)
|
||||
if(D.silent <= 10)
|
||||
D.silent = Clamp(D.silent + 10, 0, 10)
|
||||
D.silent = CLAMP(D.silent + 10, 0, 10)
|
||||
add_logs(A, D, "neck chopped")
|
||||
return 1
|
||||
|
||||
|
||||
+13
-72
@@ -201,6 +201,7 @@
|
||||
remove_antag_datum(ANTAG_DATUM_BROTHER)
|
||||
SSticker.mode.update_brother_icons_removed(src)
|
||||
|
||||
|
||||
/datum/mind/proc/remove_nukeop()
|
||||
var/datum/antagonist/nukeop/nuke = has_antag_datum(/datum/antagonist/nukeop,TRUE)
|
||||
if(nuke)
|
||||
@@ -320,14 +321,19 @@ special_role = null
|
||||
SSticker.mode.add_cultist(src)
|
||||
|
||||
else if(is_revolutionary(creator))
|
||||
var/datum/antagonist/rev/converter = creator.mind.has_antag_datum(/datum/antagonist/rev)
|
||||
var/datum/antagonist/rev/converter = creator.mind.has_antag_datum(/datum/antagonist/rev,TRUE)
|
||||
converter.add_revolutionary(src,FALSE)
|
||||
|
||||
else if(is_servant_of_ratvar(creator))
|
||||
add_servant_of_ratvar(current)
|
||||
|
||||
else if(is_nuclear_operative(creator))
|
||||
make_Nuke(null, null, 0, FALSE)
|
||||
var/datum/antagonist/nukeop/converter = creator.mind.has_antag_datum(/datum/antagonist/nukeop,TRUE)
|
||||
var/datum/antagonist/nukeop/N = new(src)
|
||||
N.send_to_spawnpoint = FALSE
|
||||
N.nukeop_outfit = null
|
||||
add_antag_datum(N,converter.nuke_team)
|
||||
|
||||
|
||||
enslaved_to = creator
|
||||
|
||||
@@ -484,7 +490,8 @@ special_role = null
|
||||
if (SSticker.mode.config_tag=="nuclear")
|
||||
text = uppertext(text)
|
||||
text = "<i><b>[text]</b></i>: "
|
||||
if (src in SSticker.mode.syndicates)
|
||||
var/datum/antagonist/nukeop/N = has_antag_datum(/datum/antagonist/nukeop,TRUE)
|
||||
if(N)
|
||||
text += "<b>OPERATIVE</b> | <a href='?src=[REF(src)];nuclear=clear'>nanotrasen</a>"
|
||||
text += "<br><a href='?src=[REF(src)];nuclear=lair'>To shuttle</a>, <a href='?src=[REF(src)];common=undress'>undress</a>, <a href='?src=[REF(src)];nuclear=dressup'>dress up</a>."
|
||||
var/code
|
||||
@@ -704,7 +711,7 @@ special_role = null
|
||||
out += sections[i]+"<br>"
|
||||
|
||||
|
||||
if(((src in SSticker.mode.traitors) || (src in SSticker.mode.syndicates)) && ishuman(current))
|
||||
if(((src in SSticker.mode.traitors) || is_nuclear_operative(current)) && ishuman(current))
|
||||
text = "Uplink: <a href='?src=[REF(src)];common=uplink'>give</a>"
|
||||
var/datum/component/uplink/U = find_syndicate_uplink()
|
||||
if(U)
|
||||
@@ -1100,36 +1107,14 @@ special_role = null
|
||||
message_admins("[key_name_admin(usr)] has de-nuke op'ed [current].")
|
||||
log_admin("[key_name(usr)] has de-nuke op'ed [current].")
|
||||
if("nuclear")
|
||||
if(!(src in SSticker.mode.syndicates))
|
||||
SSticker.mode.syndicates += src
|
||||
SSticker.mode.update_synd_icons_added(src)
|
||||
if (SSticker.mode.syndicates.len==1)
|
||||
SSticker.mode.prepare_syndicate_leader(src)
|
||||
else
|
||||
current.real_name = "[syndicate_name()] Operative #[SSticker.mode.syndicates.len-1]"
|
||||
if(!has_antag_datum(/datum/antagonist/nukeop,TRUE))
|
||||
add_antag_datum(/datum/antagonist/nukeop)
|
||||
special_role = "Syndicate"
|
||||
assigned_role = "Syndicate"
|
||||
to_chat(current, "<span class='notice'>You are a [syndicate_name()] agent!</span>")
|
||||
SSticker.mode.forge_syndicate_objectives(src)
|
||||
SSticker.mode.greet_syndicate(src)
|
||||
message_admins("[key_name_admin(usr)] has nuke op'ed [current].")
|
||||
log_admin("[key_name(usr)] has nuke op'ed [current].")
|
||||
if("lair")
|
||||
current.forceMove(pick(GLOB.nukeop_start))
|
||||
if("dressup")
|
||||
var/mob/living/carbon/human/H = current
|
||||
qdel(H.belt)
|
||||
qdel(H.back)
|
||||
qdel(H.ears)
|
||||
qdel(H.gloves)
|
||||
qdel(H.head)
|
||||
qdel(H.shoes)
|
||||
qdel(H.wear_id)
|
||||
qdel(H.wear_suit)
|
||||
qdel(H.w_uniform)
|
||||
|
||||
if (!SSticker.mode.equip_syndicate(current))
|
||||
to_chat(usr, "<span class='danger'>Equipping a syndicate failed!</span>")
|
||||
if("tellcode")
|
||||
var/code
|
||||
for (var/obj/machinery/nuclearbomb/bombue in GLOB.machines)
|
||||
@@ -1377,50 +1362,6 @@ special_role = null
|
||||
T.should_specialise = TRUE
|
||||
add_antag_datum(T)
|
||||
|
||||
|
||||
/datum/mind/proc/make_Nuke(turf/spawnloc, nuke_code, leader=0, telecrystals = TRUE)
|
||||
if(!(src in SSticker.mode.syndicates))
|
||||
SSticker.mode.syndicates += src
|
||||
SSticker.mode.update_synd_icons_added(src)
|
||||
assigned_role = "Syndicate"
|
||||
special_role = "Syndicate"
|
||||
SSticker.mode.forge_syndicate_objectives(src)
|
||||
SSticker.mode.greet_syndicate(src)
|
||||
current.faction |= "syndicate"
|
||||
|
||||
if(spawnloc)
|
||||
current.forceMove(spawnloc)
|
||||
|
||||
if(ishuman(current))
|
||||
var/mob/living/carbon/human/H = current
|
||||
qdel(H.belt)
|
||||
qdel(H.back)
|
||||
qdel(H.ears)
|
||||
qdel(H.gloves)
|
||||
qdel(H.head)
|
||||
qdel(H.shoes)
|
||||
qdel(H.wear_id)
|
||||
qdel(H.wear_suit)
|
||||
qdel(H.w_uniform)
|
||||
|
||||
SSticker.mode.equip_syndicate(current, telecrystals)
|
||||
|
||||
if (nuke_code)
|
||||
store_memory("<B>Syndicate Nuclear Bomb Code</B>: [nuke_code]", 0, 0)
|
||||
to_chat(current, "The nuclear authorization code is: <B>[nuke_code]</B>")
|
||||
else
|
||||
var/obj/machinery/nuclearbomb/nuke = locate("syndienuke") in GLOB.nuke_list
|
||||
if(nuke)
|
||||
store_memory("<B>Syndicate Nuclear Bomb Code</B>: [nuke.r_code]", 0, 0)
|
||||
to_chat(current, "The nuclear authorization code is: <B>nuke.r_code</B>")
|
||||
else
|
||||
to_chat(current, "You were not provided with a nuclear code. Trying asking your team leader or contacting syndicate command.</B>")
|
||||
|
||||
if (leader)
|
||||
SSticker.mode.prepare_syndicate_leader(src,nuke_code)
|
||||
else
|
||||
current.real_name = "[syndicate_name()] Operative #[SSticker.mode.syndicates.len-1]"
|
||||
|
||||
/datum/mind/proc/make_Changling()
|
||||
var/datum/antagonist/changeling/C = has_antag_datum(/datum/antagonist/changeling)
|
||||
if(!C)
|
||||
|
||||
@@ -98,6 +98,7 @@
|
||||
/datum/mutation/human/unintelligible
|
||||
name = "Unintelligible"
|
||||
quality = NEGATIVE
|
||||
dna_block = NON_SCANNABLE
|
||||
text_gain_indication = "<span class='danger'>You can't seem to form any coherent thoughts!</span>"
|
||||
text_lose_indication = "<span class='danger'>Your mind feels more clear.</span>"
|
||||
|
||||
|
||||
@@ -38,7 +38,7 @@
|
||||
if (user.client)
|
||||
user.client.images += bar
|
||||
|
||||
progress = Clamp(progress, 0, goal)
|
||||
progress = CLAMP(progress, 0, goal)
|
||||
bar.icon_state = "prog_bar_[round(((progress / goal) * 100), 5)]"
|
||||
if (!shown)
|
||||
user.client.images += bar
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
|
||||
var/strength
|
||||
if(steps>1)
|
||||
strength = InverseSquareLaw(intensity, max(range_modifier*steps, 1), 1)
|
||||
strength = INVERSE_SQUARE(intensity, max(range_modifier*steps, 1), 1)
|
||||
else
|
||||
strength = intensity
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
qdel(src)
|
||||
return
|
||||
|
||||
radiate(atoms, Floor(strength))
|
||||
radiate(atoms, FLOOR(strength, 1))
|
||||
|
||||
check_obstructions(atoms) // reduce our overall strength if there are radiation insulators
|
||||
|
||||
|
||||
@@ -60,8 +60,8 @@
|
||||
if(istype(L)) //this is probably more safety than actually needed
|
||||
var/vanguard = L.stun_absorption["vanguard"]
|
||||
desc = initial(desc)
|
||||
desc += "<br><b>[Floor(vanguard["stuns_absorbed"] * 0.1)]</b> seconds of stuns held back.\
|
||||
[GLOB.ratvar_awakens ? "":"<br><b>[Floor(min(vanguard["stuns_absorbed"] * 0.025, 20))]</b> seconds of stun will affect you."]"
|
||||
desc += "<br><b>[FLOOR(vanguard["stuns_absorbed"] * 0.1, 1)]</b> seconds of stuns held back.\
|
||||
[GLOB.ratvar_awakens ? "":"<br><b>[FLOOR(min(vanguard["stuns_absorbed"] * 0.025, 20), 1)]</b> seconds of stun will affect you."]"
|
||||
..()
|
||||
|
||||
/datum/status_effect/vanguard_shield/Destroy()
|
||||
@@ -87,7 +87,7 @@
|
||||
var/vanguard = owner.stun_absorption["vanguard"]
|
||||
var/stuns_blocked = 0
|
||||
if(vanguard)
|
||||
stuns_blocked = Floor(min(vanguard["stuns_absorbed"] * 0.25, 400))
|
||||
stuns_blocked = FLOOR(min(vanguard["stuns_absorbed"] * 0.25, 400), 1)
|
||||
vanguard["end_time"] = 0 //so it doesn't absorb the stuns we're about to apply
|
||||
if(owner.stat != DEAD)
|
||||
var/message_to_owner = "<span class='warning'>You feel your Vanguard quietly fade...</span>"
|
||||
|
||||
@@ -230,7 +230,7 @@
|
||||
if(prob(severity * 0.15))
|
||||
to_chat(owner, "<span class='sevtug[span_part]'>\"[text2ratvar(pick(mania_messages))]\"</span>")
|
||||
owner.playsound_local(get_turf(motor), hum, severity, 1)
|
||||
owner.adjust_drugginess(Clamp(max(severity * 0.075, 1), 0, max(0, 50 - owner.druggy))) //7.5% of severity per second, minimum 1
|
||||
owner.adjust_drugginess(CLAMP(max(severity * 0.075, 1), 0, max(0, 50 - owner.druggy))) //7.5% of severity per second, minimum 1
|
||||
if(owner.hallucination < 50)
|
||||
owner.hallucination = min(owner.hallucination + max(severity * 0.075, 1), 50) //7.5% of severity per second, minimum 1
|
||||
if(owner.dizziness < 50)
|
||||
@@ -310,7 +310,7 @@
|
||||
var/icon/I = icon(owner.icon, owner.icon_state, owner.dir)
|
||||
var/icon_height = I.Height()
|
||||
bleed_overlay.pixel_x = -owner.pixel_x
|
||||
bleed_overlay.pixel_y = Floor(icon_height * 0.25)
|
||||
bleed_overlay.pixel_y = FLOOR(icon_height * 0.25, 1)
|
||||
bleed_overlay.transform = matrix() * (icon_height/world.icon_size) //scale the bleed overlay's size based on the target's icon size
|
||||
bleed_underlay.pixel_x = -owner.pixel_x
|
||||
bleed_underlay.transform = matrix() * (icon_height/world.icon_size) * 3
|
||||
|
||||
+11
-11
@@ -1,8 +1,8 @@
|
||||
/datum/wires/r_n_d
|
||||
holder_type = /obj/machinery/r_n_d
|
||||
/datum/wires/rnd
|
||||
holder_type = /obj/machinery/rnd
|
||||
randomize = TRUE
|
||||
|
||||
/datum/wires/r_n_d/New(atom/holder)
|
||||
/datum/wires/rnd/New(atom/holder)
|
||||
wires = list(
|
||||
WIRE_HACK, WIRE_DISABLE,
|
||||
WIRE_SHOCK
|
||||
@@ -10,22 +10,22 @@
|
||||
add_duds(5)
|
||||
..()
|
||||
|
||||
/datum/wires/r_n_d/interactable(mob/user)
|
||||
var/obj/machinery/r_n_d/R = holder
|
||||
/datum/wires/rnd/interactable(mob/user)
|
||||
var/obj/machinery/rnd/R = holder
|
||||
if(R.panel_open)
|
||||
return TRUE
|
||||
|
||||
/datum/wires/r_n_d/get_status()
|
||||
var/obj/machinery/r_n_d/R = holder
|
||||
/datum/wires/rnd/get_status()
|
||||
var/obj/machinery/rnd/R = holder
|
||||
var/list/status = list()
|
||||
status += "The red light is [R.disabled ? "off" : "on"]."
|
||||
status += "The green light is [R.shocked ? "off" : "on"]."
|
||||
status += "The blue light is [R.hacked ? "off" : "on"]."
|
||||
return status
|
||||
|
||||
/datum/wires/r_n_d/on_pulse(wire)
|
||||
/datum/wires/rnd/on_pulse(wire)
|
||||
set waitfor = FALSE
|
||||
var/obj/machinery/r_n_d/R = holder
|
||||
var/obj/machinery/rnd/R = holder
|
||||
switch(wire)
|
||||
if(WIRE_HACK)
|
||||
R.hacked = !R.hacked
|
||||
@@ -37,8 +37,8 @@
|
||||
if(R)
|
||||
R.shocked = FALSE
|
||||
|
||||
/datum/wires/r_n_d/on_cut(wire, mend)
|
||||
var/obj/machinery/r_n_d/R = holder
|
||||
/datum/wires/rnd/on_cut(wire, mend)
|
||||
var/obj/machinery/rnd/R = holder
|
||||
switch(wire)
|
||||
if(WIRE_HACK)
|
||||
R.hacked = !mend
|
||||
|
||||
@@ -20,7 +20,6 @@ GLOBAL_LIST_EMPTY(active_alternate_appearances)
|
||||
var/list/arguments = args.Copy(2)
|
||||
new type(arglist(arguments))
|
||||
|
||||
|
||||
/datum/atom_hud/alternate_appearance
|
||||
var/appearance_key
|
||||
|
||||
|
||||
+19
-24
@@ -200,7 +200,7 @@
|
||||
loc.handle_atom_del(src)
|
||||
for(var/atom/movable/AM in contents)
|
||||
qdel(AM)
|
||||
loc = null
|
||||
moveToNullspace()
|
||||
invisibility = INVISIBILITY_ABSTRACT
|
||||
if(pulledby)
|
||||
pulledby.stop_pulling()
|
||||
@@ -254,6 +254,12 @@
|
||||
loc = destination
|
||||
|
||||
if(!same_loc)
|
||||
var/turf/oldturf = get_turf(oldloc)
|
||||
var/turf/destturf = get_turf(destination)
|
||||
var/old_z = (oldturf ? oldturf.z : null)
|
||||
var/dest_z = (destturf ? destturf.z : null)
|
||||
if (old_z != dest_z)
|
||||
onTransitZ(old_z, dest_z)
|
||||
destination.Entered(src, oldloc)
|
||||
if(destarea && old_area != destarea)
|
||||
destarea.Entered(src, oldloc)
|
||||
@@ -268,30 +274,18 @@
|
||||
//If no destination, move the atom into nullspace (don't do this unless you know what you're doing)
|
||||
else
|
||||
. = TRUE
|
||||
var/atom/oldloc = loc
|
||||
var/area/old_area = get_area(oldloc)
|
||||
oldloc.Exited(src, null)
|
||||
if(old_area)
|
||||
old_area.Exited(src, null)
|
||||
if (loc)
|
||||
var/atom/oldloc = loc
|
||||
var/area/old_area = get_area(oldloc)
|
||||
oldloc.Exited(src, null)
|
||||
if(old_area)
|
||||
old_area.Exited(src, null)
|
||||
loc = null
|
||||
|
||||
/mob/living/forceMove(atom/destination)
|
||||
stop_pulling()
|
||||
if(buckled)
|
||||
buckled.unbuckle_mob(src, force = TRUE)
|
||||
if(has_buckled_mobs())
|
||||
unbuckle_all_mobs(force = TRUE)
|
||||
. = ..()
|
||||
if(.)
|
||||
if(client)
|
||||
reset_perspective(destination)
|
||||
update_canmove() //if the mob was asleep inside a container and then got forceMoved out we need to make them fall.
|
||||
|
||||
/mob/living/brain/forceMove(atom/destination)
|
||||
if(container)
|
||||
return container.forceMove(destination)
|
||||
else //something went very wrong.
|
||||
CRASH("Brainmob without container.")
|
||||
/atom/movable/proc/onTransitZ(old_z,new_z)
|
||||
for (var/item in src) // Notify contents of Z-transition. This can be overridden IF we know the items contents do not care.
|
||||
var/atom/movable/AM = item
|
||||
AM.onTransitZ(old_z,new_z)
|
||||
|
||||
//Called whenever an object moves and by mobs when they attempt to move themselves through space
|
||||
//And when an object or action applies a force on src, see newtonian_move() below
|
||||
@@ -420,7 +414,7 @@
|
||||
for(var/m in buckled_mobs)
|
||||
var/mob/living/buckled_mob = m
|
||||
if(!buckled_mob.Move(newloc, direct))
|
||||
loc = buckled_mob.loc
|
||||
forceMove(buckled_mob.loc)
|
||||
last_move = buckled_mob.last_move
|
||||
inertia_dir = last_move
|
||||
buckled_mob.inertia_dir = last_move
|
||||
@@ -522,6 +516,7 @@
|
||||
. = ..()
|
||||
. -= "Jump to"
|
||||
.["Follow"] = "?_src_=holder;[HrefToken()];adminplayerobservefollow=[REF(src)]"
|
||||
.["Get"] = "?_src=holder;[HrefToken()];admingetmovable=[REF(src)]"
|
||||
|
||||
/atom/movable/proc/ex_check(ex_id)
|
||||
if(!ex_id)
|
||||
|
||||
@@ -60,6 +60,9 @@
|
||||
/datum/atom_hud/data/bot_path
|
||||
hud_icons = list(DIAG_PATH_HUD)
|
||||
|
||||
/datum/atom_hud/abductor
|
||||
hud_icons = list(GLAND_HUD)
|
||||
|
||||
/* MED/SEC/DIAG HUD HOOKS */
|
||||
|
||||
/*
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
w_class = WEIGHT_CLASS_TINY
|
||||
var/used = 0
|
||||
|
||||
/obj/item/antag_spawner/proc/spawn_antag(client/C, turf/T, type = "")
|
||||
/obj/item/antag_spawner/proc/spawn_antag(client/C, turf/T, kind = "", datum/mind/user)
|
||||
return
|
||||
|
||||
/obj/item/antag_spawner/proc/equip_antag(mob/target)
|
||||
@@ -67,18 +67,16 @@
|
||||
else
|
||||
to_chat(H, "Unable to reach your apprentice! You can either attack the spellbook with the contract to refund your points, or wait and try again later.")
|
||||
|
||||
/obj/item/antag_spawner/contract/spawn_antag(client/C, turf/T, school,datum/mind/user)
|
||||
/obj/item/antag_spawner/contract/spawn_antag(client/C, turf/T, kind ,datum/mind/user)
|
||||
new /obj/effect/particle_effect/smoke(T)
|
||||
var/mob/living/carbon/human/M = new/mob/living/carbon/human(T)
|
||||
C.prefs.copy_to(M)
|
||||
M.key = C.key
|
||||
var/datum/mind/app_mind = M.mind
|
||||
|
||||
|
||||
|
||||
var/datum/antagonist/wizard/apprentice/app = new(app_mind)
|
||||
app.master = user
|
||||
app.school = school
|
||||
app.school = kind
|
||||
|
||||
var/datum/antagonist/wizard/master_wizard = user.has_antag_datum(/datum/antagonist/wizard)
|
||||
if(master_wizard)
|
||||
@@ -107,7 +105,7 @@
|
||||
if(used)
|
||||
to_chat(user, "<span class='warning'>[src] is out of power!</span>")
|
||||
return FALSE
|
||||
if(!(user.mind in SSticker.mode.syndicates))
|
||||
if(!user.mind.has_antag_datum(/datum/antagonist/nukeop,TRUE))
|
||||
to_chat(user, "<span class='danger'>AUTHENTICATION FAILURE. ACCESS DENIED.</span>")
|
||||
return FALSE
|
||||
if(user.z != ZLEVEL_CENTCOM)
|
||||
@@ -127,25 +125,25 @@
|
||||
return
|
||||
used = TRUE
|
||||
var/mob/dead/observer/theghost = pick(nuke_candidates)
|
||||
spawn_antag(theghost.client, get_turf(src), "syndieborg", user)
|
||||
spawn_antag(theghost.client, get_turf(src), "syndieborg")
|
||||
do_sparks(4, TRUE, src)
|
||||
qdel(src)
|
||||
else
|
||||
to_chat(user, "<span class='warning'>Unable to connect to Syndicate command. Please wait and try again later or use the teleporter on your uplink to get your points refunded.</span>")
|
||||
|
||||
/obj/item/antag_spawner/nuke_ops/spawn_antag(client/C, turf/T)
|
||||
/obj/item/antag_spawner/nuke_ops/spawn_antag(client/C, turf/T, kind, datum/mind/user)
|
||||
var/mob/living/carbon/human/M = new/mob/living/carbon/human(T)
|
||||
C.prefs.copy_to(M)
|
||||
M.key = C.key
|
||||
var/code = "BOMB-NOT-FOUND"
|
||||
var/obj/machinery/nuclearbomb/nuke = locate("syndienuke") in GLOB.nuke_list
|
||||
if(nuke)
|
||||
code = nuke.r_code
|
||||
M.mind.make_Nuke(null, code, 0, FALSE)
|
||||
var/newname = M.dna.species.random_name(M.gender,0,SSticker.mode.nukeops_lastname)
|
||||
M.mind.name = newname
|
||||
M.real_name = newname
|
||||
M.name = newname
|
||||
|
||||
var/datum/antagonist/nukeop/new_op = new(M.mind)
|
||||
new_op.send_to_spawnpoint = FALSE
|
||||
new_op.nukeop_outfit = /datum/outfit/syndicate/no_crystals
|
||||
|
||||
var/datum/antagonist/nukeop/creator_op = user.has_antag_datum(/datum/antagonist/nukeop,TRUE)
|
||||
if(creator_op)
|
||||
M.mind.add_antag_datum(new_op,creator_op.nuke_team)
|
||||
M.mind.special_role = "Nuclear Operative"
|
||||
|
||||
//////SYNDICATE BORG
|
||||
/obj/item/antag_spawner/nuke_ops/borg_tele
|
||||
@@ -162,8 +160,12 @@
|
||||
name = "syndicate medical teleporter"
|
||||
borg_to_spawn = "Medical"
|
||||
|
||||
/obj/item/antag_spawner/nuke_ops/borg_tele/spawn_antag(client/C, turf/T)
|
||||
/obj/item/antag_spawner/nuke_ops/borg_tele/spawn_antag(client/C, turf/T, kind, datum/mind/user)
|
||||
var/mob/living/silicon/robot/R
|
||||
var/datum/antagonist/nukeop/creator_op = user.has_antag_datum(/datum/antagonist/nukeop,TRUE)
|
||||
if(!creator_op)
|
||||
return
|
||||
|
||||
switch(borg_to_spawn)
|
||||
if("Medical")
|
||||
R = new /mob/living/silicon/robot/modules/syndicate/medical(T)
|
||||
@@ -174,8 +176,8 @@
|
||||
if(prob(50))
|
||||
brainfirstname = pick(GLOB.first_names_female)
|
||||
var/brainopslastname = pick(GLOB.last_names)
|
||||
if(SSticker.mode.nukeops_lastname) //the brain inside the syndiborg has the same last name as the other ops.
|
||||
brainopslastname = SSticker.mode.nukeops_lastname
|
||||
if(creator_op.nuke_team.syndicate_name) //the brain inside the syndiborg has the same last name as the other ops.
|
||||
brainopslastname = creator_op.nuke_team.syndicate_name
|
||||
var/brainopsname = "[brainfirstname] [brainopslastname]"
|
||||
|
||||
R.mmi.name = "Man-Machine Interface: [brainopsname]"
|
||||
@@ -185,7 +187,11 @@
|
||||
R.real_name = R.name
|
||||
|
||||
R.key = C.key
|
||||
R.mind.make_Nuke(null, nuke_code = null,leader=0, telecrystals = TRUE)
|
||||
|
||||
var/datum/antagonist/nukeop/new_borg = new(R.mind)
|
||||
new_borg.send_to_spawnpoint = FALSE
|
||||
R.mind.add_antag_datum(new_borg,creator_op.nuke_team)
|
||||
R.mind.special_role = "Syndicate Cyborg"
|
||||
|
||||
///////////SLAUGHTER DEMON
|
||||
|
||||
@@ -222,8 +228,7 @@
|
||||
to_chat(user, "<span class='notice'>You can't seem to work up the nerve to shatter the bottle. Perhaps you should try again later.</span>")
|
||||
|
||||
|
||||
/obj/item/antag_spawner/slaughter_demon/spawn_antag(client/C, turf/T, type = "")
|
||||
|
||||
/obj/item/antag_spawner/slaughter_demon/spawn_antag(client/C, turf/T, kind = "", datum/mind/user)
|
||||
var/obj/effect/dummy/slaughter/holder = new /obj/effect/dummy/slaughter(T)
|
||||
var/mob/living/simple_animal/slaughter/S = new demon_type(holder)
|
||||
S.holder = holder
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
/mob/living/simple_animal/hostile/blob/fire_act(exposed_temperature, exposed_volume)
|
||||
..()
|
||||
if(exposed_temperature)
|
||||
adjustFireLoss(Clamp(0.01 * exposed_temperature, 1, 5))
|
||||
adjustFireLoss(CLAMP(0.01 * exposed_temperature, 1, 5))
|
||||
else
|
||||
adjustFireLoss(5)
|
||||
|
||||
|
||||
@@ -153,7 +153,7 @@ GLOBAL_LIST_EMPTY(blob_nodes)
|
||||
B.hud_used.blobpwrdisplay.maptext = "<div align='center' valign='middle' style='position:relative; top:0px; left:6px'><font color='#82ed00'>[round(blob_core.obj_integrity)]</font></div>"
|
||||
|
||||
/mob/camera/blob/proc/add_points(points)
|
||||
blob_points = Clamp(blob_points + points, 0, max_blob_points)
|
||||
blob_points = CLAMP(blob_points + points, 0, max_blob_points)
|
||||
hud_used.blobpwrdisplay.maptext = "<div align='center' valign='middle' style='position:relative; top:0px; left:6px'><font color='#82ed00'>[round(blob_points)]</font></div>"
|
||||
|
||||
/mob/camera/blob/say(message)
|
||||
@@ -215,12 +215,12 @@ GLOBAL_LIST_EMPTY(blob_nodes)
|
||||
if(placed)
|
||||
var/obj/structure/blob/B = locate() in range("3x3", NewLoc)
|
||||
if(B)
|
||||
loc = NewLoc
|
||||
forceMove(NewLoc)
|
||||
else
|
||||
return 0
|
||||
else
|
||||
var/area/A = get_area(NewLoc)
|
||||
if(isspaceturf(NewLoc) || istype(A, /area/shuttle)) //if unplaced, can't go on shuttles or space tiles
|
||||
return 0
|
||||
loc = NewLoc
|
||||
forceMove(NewLoc)
|
||||
return 1
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
return 0
|
||||
else if(placement_override == 1)
|
||||
var/turf/T = pick(GLOB.blobstart)
|
||||
loc = T //got overrided? you're somewhere random, motherfucker
|
||||
forceMove(T) //got overrided? you're somewhere random, motherfucker
|
||||
if(placed && blob_core)
|
||||
blob_core.forceMove(loc)
|
||||
else
|
||||
@@ -74,7 +74,7 @@
|
||||
var/node_name = input(src, "Choose a node to jump to.", "Node Jump") in nodes
|
||||
var/obj/structure/blob/node/chosen_node = nodes[node_name]
|
||||
if(chosen_node)
|
||||
loc = chosen_node.loc
|
||||
forceMove(chosen_node.loc)
|
||||
|
||||
/mob/camera/blob/proc/createSpecial(price, blobType, nearEquals, needsNode, turf/T)
|
||||
if(!T)
|
||||
|
||||
@@ -207,7 +207,7 @@
|
||||
to_chat(cyborg, "<span class='brass'>You start to charge from the [sigil_name]...</span>")
|
||||
if(!do_after(cyborg, 50, target = src, extra_checks = CALLBACK(src, .proc/cyborg_checks, cyborg, TRUE)))
|
||||
return
|
||||
var/giving_power = min(Floor(cyborg.cell.maxcharge - cyborg.cell.charge, MIN_CLOCKCULT_POWER), get_clockwork_power()) //give the borg either all our power or their missing power floored to MIN_CLOCKCULT_POWER
|
||||
var/giving_power = min(FLOOR(cyborg.cell.maxcharge - cyborg.cell.charge, MIN_CLOCKCULT_POWER), get_clockwork_power()) //give the borg either all our power or their missing power floored to MIN_CLOCKCULT_POWER
|
||||
if(adjust_clockwork_power(-giving_power))
|
||||
cyborg.visible_message("<span class='warning'>[cyborg] glows a brilliant orange!</span>")
|
||||
var/previous_color = cyborg.color
|
||||
@@ -310,7 +310,7 @@
|
||||
else
|
||||
if(L.stat == DEAD)
|
||||
var/revival_cost = revive_cost
|
||||
if(GLOB.ratvar_awakens)
|
||||
if(GLOB.ratvar_awakens || L.suiciding) // No cost if Ratvar is summoned or if you're reviving a convert who suicided
|
||||
revival_cost = 0
|
||||
var/mob/dead/observer/ghost = L.get_ghost(TRUE)
|
||||
if(GLOB.clockwork_vitality >= revival_cost && (ghost || (L.mind && L.mind.active)))
|
||||
@@ -323,6 +323,20 @@
|
||||
L.visible_message("<span class='warning'>[L] suddenly gets back up, [L.p_their()] body dripping blue ichor!</span>", "<span class='inathneq'>\"[text2ratvar("You will be okay, child.")]\"</span>")
|
||||
GLOB.clockwork_vitality -= revival_cost
|
||||
break
|
||||
if(!L.client || L.client.is_afk())
|
||||
set waitfor = FALSE
|
||||
var/list/mob/dead/observer/candidates = pollCandidatesForMob("Do you want to play as a [L.name], an inactive clock cultist?", "[name]", null, "Clock Cultist", 50, L)
|
||||
var/mob/dead/observer/theghost = null
|
||||
if(candidates.len)
|
||||
to_chat(L, "Your physical form has been taken over by another soul due to your inactivity! Ahelp if you wish to regain your form!")
|
||||
message_admins("[key_name_admin(theghost)] has taken control of ([key_name_admin(L)]) to replace an inactive clock cultist.")
|
||||
L.ghostize(0)
|
||||
L.key = theghost.key
|
||||
var/obj/effect/temp_visual/ratvar/sigil/vitality/V = new /obj/effect/temp_visual/ratvar/sigil/vitality(get_turf(src))
|
||||
animate(V, alpha = 0, transform = matrix()*2, time = 8)
|
||||
playsound(L, 'sound/magic/staff_healing.ogg', 50, 1)
|
||||
L.visible_message("<span class='warning'>[L]'s eyes suddenly open wide, gleaming with renewed vigor for the cause!</span>", "<span class='inathneq'>\"[text2ratvar("Awaken!")]\"</span>")
|
||||
break
|
||||
var/vitality_for_cycle = 3
|
||||
if(!GLOB.ratvar_awakens)
|
||||
if(L.stat == CONSCIOUS)
|
||||
|
||||
@@ -90,7 +90,7 @@
|
||||
if(amount_temp < 2)
|
||||
to_chat(user, "<span class='warning'>You need at least <b>2</b> floor tiles to convert into power.</span>")
|
||||
return TRUE
|
||||
if(IsOdd(amount_temp))
|
||||
if(ISODD(amount_temp))
|
||||
amount_temp--
|
||||
no_delete = TRUE
|
||||
use(amount_temp)
|
||||
@@ -239,7 +239,7 @@
|
||||
if(!do_after(user, repair_values["healing_for_cycle"] * fabricator.speed_multiplier, target = src, \
|
||||
extra_checks = CALLBACK(fabricator, /obj/item/clockwork/replica_fabricator.proc/fabricator_repair_checks, repair_values, src, user, TRUE)))
|
||||
break
|
||||
obj_integrity = Clamp(obj_integrity + repair_values["healing_for_cycle"], 0, max_integrity)
|
||||
obj_integrity = CLAMP(obj_integrity + repair_values["healing_for_cycle"], 0, max_integrity)
|
||||
adjust_clockwork_power(-repair_values["power_required"])
|
||||
playsound(src, 'sound/machines/click.ogg', 50, 1)
|
||||
|
||||
|
||||
@@ -10,12 +10,15 @@
|
||||
for(var/obj/effect/clockwork/sigil/transmission/T in GLOB.all_clockwork_objects)
|
||||
T.update_icon()
|
||||
var/power_overwhelming = GLOB.clockwork_power
|
||||
var/unlock_message
|
||||
if(power_overwhelming >= SCRIPT_UNLOCK_THRESHOLD && !GLOB.script_scripture_unlocked)
|
||||
GLOB.script_scripture_unlocked = TRUE
|
||||
hierophant_message("<span class='large_brass bold'>The Ark swells as a key power threshold is reached. Script scriptures are now available.</span>")
|
||||
unlock_message = "<span class='large_brass bold'>The Ark swells as a key power threshold is reached. Script scriptures are now available.</span>"
|
||||
if(power_overwhelming >= APPLICATION_UNLOCK_THRESHOLD && !GLOB.application_scripture_unlocked)
|
||||
GLOB.application_scripture_unlocked = TRUE
|
||||
hierophant_message("<span class='large_brass bold'>The Ark surges as a key power threshold is reached. Application scriptures are now available.</span>")
|
||||
unlock_message = "<span class='large_brass bold'>The Ark surges as a key power threshold is reached. Application scriptures are now available.</span>"
|
||||
if(GLOB.servants_active)
|
||||
hierophant_message(unlock_message)
|
||||
return TRUE
|
||||
|
||||
/proc/can_access_clockwork_power(atom/movable/access_point, amount) //Returns true if the access point has access to clockwork power (and optionally, a number of watts for it)
|
||||
|
||||
@@ -11,6 +11,8 @@
|
||||
|
||||
//reports to servants when scripture is locked or unlocked
|
||||
/proc/scripture_unlock_alert(list/previous_states)
|
||||
if(!GLOB.servants_active)
|
||||
return
|
||||
. = scripture_unlock_check()
|
||||
for(var/i in .)
|
||||
if(.[i] != previous_states[i])
|
||||
|
||||
@@ -67,7 +67,6 @@
|
||||
name = "replicant manacles"
|
||||
desc = "Heavy manacles made out of freezing-cold metal. It looks like brass, but feels much more solid."
|
||||
icon_state = "brass_manacles"
|
||||
origin_tech = "materials=2;magnets=5"
|
||||
flags_1 = DROPDEL_1
|
||||
|
||||
/obj/item/restraints/handcuffs/clockwork/dropped(mob/user)
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
#define MARAUDER_SLOWDOWN_PERCENTAGE 0.40 //Below this percentage of health, marauders will become slower
|
||||
#define MARAUDER_SHIELD_REGEN_TIME 100 //In deciseconds, how long it takes for shields to regenerate after breaking
|
||||
#define MARAUDER_SHIELD_REGEN_TIME 200 //In deciseconds, how long it takes for shields to regenerate after breaking
|
||||
|
||||
//Clockwork marauder: A well-rounded frontline construct. Only one can exist for every two human servants.
|
||||
/mob/living/simple_animal/hostile/clockwork/marauder
|
||||
name = "clockwork marauder"
|
||||
desc = "The stalwart apparition of a soldier, blazing with crimson flames. It's armed with a gladius and shield."
|
||||
icon_state = "clockwork_marauder"
|
||||
health = 150
|
||||
maxHealth = 150
|
||||
health = 120
|
||||
maxHealth = 120
|
||||
force_threshold = 8
|
||||
speed = 0
|
||||
obj_damage = 40
|
||||
@@ -39,10 +39,11 @@
|
||||
speed = initial(speed) + 1 //Yes, this slows them down
|
||||
else
|
||||
speed = initial(speed)
|
||||
if(shield_health != max_shield_health && world.time >= shield_health_regen)
|
||||
to_chat(src, "<span class='neovgre'>Your shield has recovered. <b>[max_shield_health]</b> blocks remaining!</span>")
|
||||
if(shield_health < max_shield_health && world.time >= shield_health_regen)
|
||||
shield_health_regen = world.time + MARAUDER_SHIELD_REGEN_TIME
|
||||
to_chat(src, "<span class='neovgre'>Your shield has recovered, <b>[shield_health]</b> blocks remaining!</span>")
|
||||
playsound_local(src, "shatter", 75, TRUE, frequency = -1)
|
||||
shield_health = max_shield_health
|
||||
shield_health++
|
||||
|
||||
/mob/living/simple_animal/hostile/clockwork/marauder/update_values()
|
||||
if(GLOB.ratvar_awakens) //Massive attack damage bonuses and health increase, because Ratvar
|
||||
|
||||
@@ -97,7 +97,7 @@
|
||||
if(ishuman(M.current))
|
||||
human_servants++
|
||||
construct_limit = human_servants / 4 //1 per 4 human servants, and a maximum of 3 marauders
|
||||
construct_limit = Clamp(construct_limit, 1, 3)
|
||||
construct_limit = CLAMP(construct_limit, 1, 3)
|
||||
|
||||
/datum/clockwork_scripture/create_object/construct/clockwork_marauder/pre_recital()
|
||||
channel_time = initial(channel_time)
|
||||
|
||||
@@ -60,4 +60,4 @@
|
||||
break
|
||||
if(!M)
|
||||
M = H.apply_status_effect(STATUS_EFFECT_MANIAMOTOR, src)
|
||||
M.severity = Clamp(M.severity + ((11 - get_dist(src, H)) * efficiency * efficiency), 0, MAX_MANIA_SEVERITY)
|
||||
M.severity = CLAMP(M.severity + ((11 - get_dist(src, H)) * efficiency * efficiency), 0, MAX_MANIA_SEVERITY)
|
||||
|
||||
@@ -57,5 +57,5 @@
|
||||
L.confused = min(L.confused + 15, 50)
|
||||
L.dizziness = min(L.dizziness + 15, 50)
|
||||
if(L.confused >= 25)
|
||||
L.Knockdown(Floor(L.confused * 0.8))
|
||||
L.Knockdown(FLOOR(L.confused * 0.8, 1))
|
||||
take_damage(max_integrity)
|
||||
|
||||
@@ -510,10 +510,10 @@ structure_check() searches for nearby cultist structures required for the invoca
|
||||
message_admins("[key_name_admin(user)] erased a Narsie rune with a null rod")
|
||||
..()
|
||||
|
||||
//Rite of Resurrection: Requires the corpse of a cultist and that there have been less revives than the number of people GLOB.sacrificed
|
||||
//Rite of Resurrection: Requires a dead or inactive cultist. When reviving the dead, you can only perform one revival for every sacrifice your cult has carried out.
|
||||
/obj/effect/rune/raise_dead
|
||||
cultist_name = "Resurrect Cultist"
|
||||
cultist_desc = "requires the corpse of a cultist placed upon the rune. Provided there have been sufficient sacrifices, they will be revived."
|
||||
cultist_name = "Revive Cultist"
|
||||
cultist_desc = "requires a dead, mindless, or inactive cultist placed upon the rune. Provided there have been sufficient sacrifices, they will be given a new life."
|
||||
invocation = "Pasnar val'keriam usinar. Savrae ines amutan. Yam'toth remium il'tarat!" //Depends on the name of the user - see below
|
||||
icon_state = "1"
|
||||
color = RUNE_COLOR_MEDIUMRED
|
||||
@@ -534,16 +534,11 @@ structure_check() searches for nearby cultist structures required for the invoca
|
||||
return
|
||||
rune_in_use = TRUE
|
||||
for(var/mob/living/M in T.contents)
|
||||
if(iscultist(M) && M.stat == DEAD)
|
||||
if(iscultist(M) && (M.stat == DEAD || !M.client || M.client.is_afk()))
|
||||
potential_revive_mobs |= M
|
||||
if(!potential_revive_mobs.len)
|
||||
to_chat(user, "<span class='cultitalic'>There are no dead cultists on the rune!</span>")
|
||||
log_game("Raise Dead rune failed - no corpses to revive")
|
||||
fail_invoke()
|
||||
rune_in_use = FALSE
|
||||
return
|
||||
if(LAZYLEN(GLOB.sacrificed) <= revives_used)
|
||||
to_chat(user, "<span class='warning'>You have sacrificed too few people to revive a cultist!</span>")
|
||||
log_game("Raise Dead rune failed - no cultists to revive")
|
||||
fail_invoke()
|
||||
rune_in_use = FALSE
|
||||
return
|
||||
@@ -559,9 +554,25 @@ structure_check() searches for nearby cultist structures required for the invoca
|
||||
else
|
||||
invocation = initial(invocation)
|
||||
..()
|
||||
revives_used++
|
||||
mob_to_revive.revive(1, 1) //This does remove disabilities and such, but the rune might actually see some use because of it!
|
||||
mob_to_revive.grab_ghost()
|
||||
if(mob_to_revive.stat == DEAD)
|
||||
if(LAZYLEN(GLOB.sacrificed) <= revives_used)
|
||||
to_chat(user, "<span class='warning'>Your cult must carry out another sacrifice before it can revive a cultist!</span>")
|
||||
fail_invoke()
|
||||
rune_in_use = FALSE
|
||||
return
|
||||
revives_used++
|
||||
mob_to_revive.revive(1, 1) //This does remove disabilities and such, but the rune might actually see some use because of it!
|
||||
mob_to_revive.grab_ghost()
|
||||
else if(!mob_to_revive.client || mob_to_revive.client.is_afk())
|
||||
set waitfor = FALSE
|
||||
var/list/mob/dead/observer/candidates = pollCandidatesForMob("Do you want to play as a [mob_to_revive.name], an inactive blood cultist?", "[name]", null, "Blood Cultist", 50, mob_to_revive)
|
||||
var/mob/dead/observer/theghost = null
|
||||
if(candidates.len)
|
||||
theghost = pick(candidates)
|
||||
to_chat(mob_to_revive.mind, "Your physical form has been taken over by another soul due to your inactivity! Ahelp if you wish to regain your form.")
|
||||
message_admins("[key_name_admin(theghost)] has taken control of ([key_name_admin(mob_to_revive)]) to replace an AFK player.")
|
||||
mob_to_revive.ghostize(0)
|
||||
mob_to_revive.key = theghost.key
|
||||
to_chat(mob_to_revive, "<span class='cultlarge'>\"PASNAR SAVRAE YAM'TOTH. Arise.\"</span>")
|
||||
mob_to_revive.visible_message("<span class='warning'>[mob_to_revive] draws in a huge breath, red light shining from [mob_to_revive.p_their()] eyes.</span>", \
|
||||
"<span class='cultlarge'>You awaken suddenly from the void. You're alive!</span>")
|
||||
|
||||
@@ -338,7 +338,6 @@
|
||||
name = "cult shackles"
|
||||
desc = "Shackles that bind the wrists with sinister magic."
|
||||
trashtype = /obj/item/restraints/handcuffs/energy/used
|
||||
origin_tech = "materials=2;magnets=5"
|
||||
flags_1 = DROPDEL_1
|
||||
|
||||
/obj/item/restraints/handcuffs/energy/cult/used/dropped(mob/user)
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
var/probability = 0
|
||||
var/false_report_weight = 0 //How often will this show up incorrectly in a centcom report?
|
||||
var/station_was_nuked = 0 //see nuclearbomb.dm and malfunction.dm
|
||||
var/nuke_off_station = 0 //Used for tracking where the nuke hit
|
||||
var/round_ends_with_antag_death = 0 //flags the "one verse the station" antags as such
|
||||
var/list/datum/mind/antag_candidates = list() // List of possible starting antags goes here
|
||||
var/list/restricted_jobs = list() // Jobs it doesn't make sense to be. I.E chaplain or AI cultist
|
||||
@@ -448,6 +449,7 @@
|
||||
|
||||
//By default nuke just ends the round
|
||||
/datum/game_mode/proc/OnNukeExplosion(off_station)
|
||||
nuke_off_station = off_station
|
||||
if(off_station < 2)
|
||||
station_was_nuked = TRUE //Will end the round on next check.
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
* Gang Boss Pens
|
||||
*/
|
||||
/obj/item/pen/gang
|
||||
origin_tech = "materials=2;syndicate=3"
|
||||
var/cooldown
|
||||
var/last_used = 0
|
||||
var/charges = 1
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
throw_speed = 3
|
||||
throw_range = 7
|
||||
flags_1 = CONDUCT_1
|
||||
origin_tech = "programming=5;bluespace=2;syndicate=5"
|
||||
var/datum/gang/gang //Which gang uses this?
|
||||
var/recalling = 0
|
||||
var/outfits = 2
|
||||
|
||||
@@ -25,7 +25,7 @@
|
||||
if (prob(meteorminutes/2))
|
||||
wavetype = GLOB.meteors_catastrophic
|
||||
|
||||
var/ramp_up_final = Clamp(round(meteorminutes/rampupdelta), 1, 10)
|
||||
var/ramp_up_final = CLAMP(round(meteorminutes/rampupdelta), 1, 10)
|
||||
|
||||
spawn_meteors(ramp_up_final, wavetype)
|
||||
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
#define VEST_COMBAT 2
|
||||
#define GIZMO_SCAN 1
|
||||
#define GIZMO_MARK 2
|
||||
#define MIND_DEVICE_MESSAGE 1
|
||||
#define MIND_DEVICE_CONTROL 2
|
||||
|
||||
//AGENT VEST
|
||||
/obj/item/clothing/suit/armor/abductor/vest
|
||||
@@ -11,7 +13,6 @@
|
||||
icon_state = "vest_stealth"
|
||||
item_state = "armor"
|
||||
blood_overlay_type = "armor"
|
||||
origin_tech = "magnets=7;biotech=4;powerstorage=4;abductor=4"
|
||||
armor = list(melee = 15, bullet = 15, laser = 15, energy = 15, bomb = 15, bio = 15, rad = 15, fire = 70, acid = 70)
|
||||
actions_types = list(/datum/action/item_action/hands_free/activate)
|
||||
allowed = list(
|
||||
@@ -155,7 +156,6 @@
|
||||
item_state = "silencer"
|
||||
lefthand_file = 'icons/mob/inhands/antag/abductor_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/antag/abductor_righthand.dmi'
|
||||
origin_tech = "engineering=7;magnets=4;bluespace=4;abductor=3"
|
||||
var/mode = GIZMO_SCAN
|
||||
var/mob/living/marked = null
|
||||
var/obj/machinery/abductor/console/console
|
||||
@@ -244,7 +244,6 @@
|
||||
item_state = "gizmo"
|
||||
lefthand_file = 'icons/mob/inhands/antag/abductor_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/antag/abductor_righthand.dmi'
|
||||
origin_tech = "materials=4;programming=7;abductor=3"
|
||||
|
||||
/obj/item/device/abductor/silencer/attack(mob/living/M, mob/user)
|
||||
if(!AbductorCheck(user))
|
||||
@@ -281,6 +280,84 @@
|
||||
if(!istype(I, /obj/item/device/radio/headset))
|
||||
r.broadcasting = 0 //goddamned headset hacks
|
||||
|
||||
/obj/item/device/abductor/mind_device
|
||||
name = "mental interface device"
|
||||
desc = "A dual-mode tool for directly communicating with sentient brains. It can be used to send a direct message to a target, \
|
||||
or to send a command to a test subject with a charged gland."
|
||||
icon_state = "mind_device_message"
|
||||
item_state = "silencer"
|
||||
lefthand_file = 'icons/mob/inhands/antag/abductor_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/antag/abductor_righthand.dmi'
|
||||
var/mode = MIND_DEVICE_MESSAGE
|
||||
|
||||
/obj/item/device/abductor/mind_device/attack_self(mob/user)
|
||||
if(!ScientistCheck(user))
|
||||
return
|
||||
|
||||
if(mode == MIND_DEVICE_MESSAGE)
|
||||
mode = MIND_DEVICE_CONTROL
|
||||
icon_state = "mind_device_control"
|
||||
else
|
||||
mode = MIND_DEVICE_MESSAGE
|
||||
icon_state = "mind_device_message"
|
||||
to_chat(user, "<span class='notice'>You switch the device to [mode==MIND_DEVICE_MESSAGE? "TRANSMISSION": "COMMAND"] MODE</span>")
|
||||
|
||||
/obj/item/device/abductor/mind_device/afterattack(atom/target, mob/living/user, flag, params)
|
||||
if(!ScientistCheck(user))
|
||||
return
|
||||
|
||||
switch(mode)
|
||||
if(MIND_DEVICE_CONTROL)
|
||||
mind_control(target, user)
|
||||
if(MIND_DEVICE_MESSAGE)
|
||||
mind_message(target, user)
|
||||
|
||||
/obj/item/device/abductor/mind_device/proc/mind_control(atom/target, mob/living/user)
|
||||
if(iscarbon(target))
|
||||
var/mob/living/carbon/C = target
|
||||
var/obj/item/organ/heart/gland/G = C.getorganslot("heart")
|
||||
if(!istype(G))
|
||||
to_chat(user, "<span class='warning'>Your target does not have an experimental gland!</span>")
|
||||
return
|
||||
if(!G.mind_control_uses)
|
||||
to_chat(user, "<span class='warning'>Your target's gland is spent!</span>")
|
||||
return
|
||||
if(G.active_mind_control)
|
||||
to_chat(user, "<span class='warning'>Your target is already under a mind-controlling influence!</span>")
|
||||
return
|
||||
|
||||
var/command = stripped_input(user, "Enter the command for your target to follow.\
|
||||
Uses Left: [G.mind_control_uses], Duration: [G.mind_control_duration / 10] seconds","Enter command")
|
||||
|
||||
if(!command)
|
||||
return
|
||||
|
||||
if(QDELETED(user) || user.get_active_held_item() != src || loc != user)
|
||||
return
|
||||
|
||||
if(QDELETED(G))
|
||||
return
|
||||
|
||||
G.mind_control(command, user)
|
||||
to_chat(user, "<span class='notice'>You send the command to your target.</span>")
|
||||
|
||||
/obj/item/device/abductor/mind_device/proc/mind_message(atom/target, mob/living/user)
|
||||
if(isliving(target))
|
||||
var/mob/living/L = target
|
||||
if(L.stat == DEAD)
|
||||
to_chat(user, "<span class='warning'>Your target is dead!</span>")
|
||||
return
|
||||
var/message = stripped_input(user, "Write a message to send to your target's brain.","Enter message")
|
||||
if(!message)
|
||||
return
|
||||
if(QDELETED(L) || L.stat == DEAD)
|
||||
return
|
||||
|
||||
to_chat(L, "<span class='italics'>You hear a voice in your head saying: </span><span class='abductor'>[message]</span>")
|
||||
to_chat(user, "<span class='notice'>You send the message to your target.</span>")
|
||||
log_talk(user,"[key_name(user)] sent an abductor mind message to [L]/[L.ckey]: '[message]'", LOGSAY)
|
||||
|
||||
|
||||
/obj/item/device/firing_pin/abductor
|
||||
name = "alien firing pin"
|
||||
icon_state = "firing_pin_ayy"
|
||||
@@ -299,7 +376,6 @@
|
||||
pin = /obj/item/device/firing_pin/abductor
|
||||
icon_state = "alienpistol"
|
||||
item_state = "alienpistol"
|
||||
origin_tech = "combat=4;magnets=7;powerstorage=3;abductor=3"
|
||||
trigger_guard = TRIGGER_GUARD_ALLOW_ALL
|
||||
|
||||
/obj/item/paper/guides/antag/abductor
|
||||
@@ -346,7 +422,6 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
lefthand_file = 'icons/mob/inhands/antag/abductor_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/antag/abductor_righthand.dmi'
|
||||
slot_flags = SLOT_BELT
|
||||
origin_tech = "materials=4;combat=4;biotech=7;abductor=4"
|
||||
force = 7
|
||||
w_class = WEIGHT_CLASS_NORMAL
|
||||
actions_types = list(/datum/action/item_action/toggle_mode)
|
||||
@@ -496,7 +571,6 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
righthand_file = 'icons/mob/inhands/equipment/security_righthand.dmi'
|
||||
breakouttime = 450
|
||||
trashtype = /obj/item/restraints/handcuffs/energy/used
|
||||
origin_tech = "materials=4;magnets=5;abductor=2"
|
||||
|
||||
/obj/item/restraints/handcuffs/energy/used
|
||||
flags_1 = DROPDEL_1
|
||||
@@ -524,7 +598,6 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
/obj/item/device/radio/headset/abductor
|
||||
name = "alien headset"
|
||||
desc = "An advanced alien headset designed to monitor communications of human space stations. Why does it have a microphone? No one knows."
|
||||
origin_tech = "magnets=2;abductor=3"
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
icon_state = "abductor_headset"
|
||||
item_state = "abductor_headset"
|
||||
@@ -545,35 +618,30 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
name = "alien scalpel"
|
||||
desc = "It's a gleaming sharp knife made out of silvery-green metal."
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/hemostat/alien
|
||||
name = "alien hemostat"
|
||||
desc = "You've never seen this before."
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/retractor/alien
|
||||
name = "alien retractor"
|
||||
desc = "You're not sure if you want the veil pulled back."
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/circular_saw/alien
|
||||
name = "alien saw"
|
||||
desc = "Do the aliens also lose this, and need to find an alien hatchet?"
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/surgicaldrill/alien
|
||||
name = "alien drill"
|
||||
desc = "Maybe alien surgeons have finally found a use for the drill."
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/cautery/alien
|
||||
@@ -581,7 +649,6 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
desc = "Why would bloodless aliens have a tool to stop bleeding? \
|
||||
Unless..."
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
origin_tech = "materials=2;biotech=2;abductor=2"
|
||||
toolspeed = 0.25
|
||||
|
||||
/obj/item/clothing/head/helmet/abductor
|
||||
@@ -590,7 +657,6 @@ Congratulations! You are now trained for invasive xenobiology research!"}
|
||||
icon_state = "alienhelmet"
|
||||
item_state = "alienhelmet"
|
||||
blockTracking = 1
|
||||
origin_tech = "materials=7;magnets=4;abductor=3"
|
||||
flags_inv = HIDEMASK|HIDEEARS|HIDEEYES|HIDEFACE|HIDEHAIR|HIDEFACIALHAIR
|
||||
|
||||
// Operating Table / Beds / Lockers
|
||||
|
||||
@@ -4,7 +4,6 @@
|
||||
icon = 'icons/obj/abductor.dmi'
|
||||
icon_state = "gland"
|
||||
status = ORGAN_ROBOTIC
|
||||
origin_tech = "materials=4;biotech=7;abductor=3"
|
||||
beating = TRUE
|
||||
var/cooldown_low = 300
|
||||
var/cooldown_high = 300
|
||||
@@ -13,28 +12,68 @@
|
||||
var/human_only = 0
|
||||
var/active = 0
|
||||
|
||||
var/mind_control_uses = 1
|
||||
var/mind_control_duration = 1800
|
||||
var/active_mind_control = FALSE
|
||||
|
||||
/obj/item/organ/heart/gland/proc/ownerCheck()
|
||||
if(ishuman(owner))
|
||||
return 1
|
||||
return TRUE
|
||||
if(!human_only && iscarbon(owner))
|
||||
return 1
|
||||
return 0
|
||||
return TRUE
|
||||
return FALSE
|
||||
|
||||
/obj/item/organ/heart/gland/proc/Start()
|
||||
active = 1
|
||||
next_activation = world.time + rand(cooldown_low,cooldown_high)
|
||||
|
||||
/obj/item/organ/heart/gland/proc/update_gland_hud()
|
||||
if(!owner)
|
||||
return
|
||||
var/image/holder = owner.hud_list[GLAND_HUD]
|
||||
var/icon/I = icon(owner.icon, owner.icon_state, owner.dir)
|
||||
holder.pixel_y = I.Height() - world.icon_size
|
||||
if(active_mind_control)
|
||||
holder.icon_state = "hudgland_active"
|
||||
else if(mind_control_uses)
|
||||
holder.icon_state = "hudgland_ready"
|
||||
else
|
||||
holder.icon_state = "hudgland_spent"
|
||||
|
||||
/obj/item/organ/heart/gland/Remove(var/mob/living/carbon/M, special = 0)
|
||||
/obj/item/organ/heart/gland/proc/mind_control(command, mob/living/user)
|
||||
if(!ownerCheck() || !mind_control_uses || active_mind_control)
|
||||
return
|
||||
mind_control_uses--
|
||||
to_chat(owner, "<span class='userdanger'>You suddenly feel an irresistible compulsion to follow an order...</span>")
|
||||
to_chat(owner, "<span class='mind_control'>[command]</span>")
|
||||
active_mind_control = TRUE
|
||||
log_admin("[key_name(user)] sent an abductor mind control message to [key_name(owner)]: [command]")
|
||||
update_gland_hud()
|
||||
|
||||
addtimer(CALLBACK(src, .proc/clear_mind_control), mind_control_duration)
|
||||
|
||||
/obj/item/organ/heart/gland/proc/clear_mind_control()
|
||||
if(!ownerCheck() || !active_mind_control)
|
||||
return
|
||||
to_chat(owner, "<span class='userdanger'>You feel the compulsion fade, and you completely forget about your previous orders.</span>")
|
||||
active_mind_control = FALSE
|
||||
|
||||
/obj/item/organ/heart/gland/Remove(mob/living/carbon/M, special = 0)
|
||||
active = 0
|
||||
if(initial(uses) == 1)
|
||||
uses = initial(uses)
|
||||
var/datum/atom_hud/abductor/hud = GLOB.huds[DATA_HUD_ABDUCTOR]
|
||||
hud.remove_from_hud(owner)
|
||||
clear_mind_control()
|
||||
..()
|
||||
|
||||
/obj/item/organ/heart/gland/Insert(var/mob/living/carbon/M, special = 0)
|
||||
/obj/item/organ/heart/gland/Insert(mob/living/carbon/M, special = 0)
|
||||
..()
|
||||
if(special != 2 && uses) // Special 2 means abductor surgery
|
||||
Start()
|
||||
var/datum/atom_hud/abductor/hud = GLOB.huds[DATA_HUD_ABDUCTOR]
|
||||
hud.add_to_hud(owner)
|
||||
update_gland_hud()
|
||||
|
||||
/obj/item/organ/heart/gland/on_life()
|
||||
if(!beating)
|
||||
@@ -60,6 +99,8 @@
|
||||
cooldown_high = 400
|
||||
uses = -1
|
||||
icon_state = "health"
|
||||
mind_control_uses = 3
|
||||
mind_control_duration = 3000
|
||||
|
||||
/obj/item/organ/heart/gland/heals/activate()
|
||||
to_chat(owner, "<span class='notice'>You feel curiously revitalized.</span>")
|
||||
@@ -72,6 +113,8 @@
|
||||
cooldown_high = 1200
|
||||
uses = -1
|
||||
icon_state = "slime"
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 2400
|
||||
|
||||
/obj/item/organ/heart/gland/slime/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel nauseous!</span>")
|
||||
@@ -83,11 +126,12 @@
|
||||
Slime.Leader = owner
|
||||
|
||||
/obj/item/organ/heart/gland/mindshock
|
||||
origin_tech = "materials=4;biotech=4;magnets=6;abductor=3"
|
||||
cooldown_low = 300
|
||||
cooldown_high = 300
|
||||
uses = -1
|
||||
icon_state = "mindshock"
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 6000
|
||||
|
||||
/obj/item/organ/heart/gland/mindshock/activate()
|
||||
to_chat(owner, "<span class='notice'>You get a headache.</span>")
|
||||
@@ -105,6 +149,8 @@
|
||||
uses = -1
|
||||
human_only = 1
|
||||
icon_state = "species"
|
||||
mind_control_uses = 5
|
||||
mind_control_duration = 300
|
||||
|
||||
/obj/item/organ/heart/gland/pop/activate()
|
||||
to_chat(owner, "<span class='notice'>You feel unlike yourself.</span>")
|
||||
@@ -112,11 +158,12 @@
|
||||
owner.set_species(species)
|
||||
|
||||
/obj/item/organ/heart/gland/ventcrawling
|
||||
origin_tech = "materials=4;biotech=5;bluespace=4;abductor=3"
|
||||
cooldown_low = 1800
|
||||
cooldown_high = 2400
|
||||
uses = 1
|
||||
icon_state = "vent"
|
||||
mind_control_uses = 4
|
||||
mind_control_duration = 1800
|
||||
|
||||
/obj/item/organ/heart/gland/ventcrawling/activate()
|
||||
to_chat(owner, "<span class='notice'>You feel very stretchy.</span>")
|
||||
@@ -128,6 +175,8 @@
|
||||
cooldown_high = 2400
|
||||
uses = 1
|
||||
icon_state = "viral"
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 1800
|
||||
|
||||
/obj/item/organ/heart/gland/viral/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel sick.</span>")
|
||||
@@ -140,11 +189,12 @@
|
||||
|
||||
|
||||
/obj/item/organ/heart/gland/emp //TODO : Replace with something more interesting
|
||||
origin_tech = "materials=4;biotech=4;magnets=6;abductor=3"
|
||||
cooldown_low = 900
|
||||
cooldown_high = 1600
|
||||
uses = 10
|
||||
icon_state = "emp"
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 1800
|
||||
|
||||
/obj/item/organ/heart/gland/emp/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel a spike of pain in your head.</span>")
|
||||
@@ -155,6 +205,8 @@
|
||||
cooldown_high = 900
|
||||
uses = 10
|
||||
icon_state = "spider"
|
||||
mind_control_uses = 2
|
||||
mind_control_duration = 2400
|
||||
|
||||
/obj/item/organ/heart/gland/spiderman/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel something crawling in your skin.</span>")
|
||||
@@ -168,6 +220,8 @@
|
||||
icon_state = "egg"
|
||||
lefthand_file = 'icons/mob/inhands/misc/food_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/misc/food_righthand.dmi'
|
||||
mind_control_uses = 2
|
||||
mind_control_duration = 1800
|
||||
|
||||
/obj/item/organ/heart/gland/egg/activate()
|
||||
to_chat(owner, "<span class='boldannounce'>You lay an egg!</span>")
|
||||
@@ -179,6 +233,8 @@
|
||||
cooldown_low = 200
|
||||
cooldown_high = 400
|
||||
uses = -1
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 450
|
||||
|
||||
/obj/item/organ/heart/gland/bloody/activate()
|
||||
owner.blood_volume -= 20
|
||||
@@ -196,6 +252,8 @@
|
||||
cooldown_high = 600
|
||||
human_only = 1
|
||||
uses = 1
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 600
|
||||
|
||||
/obj/item/organ/heart/gland/bodysnatch/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel something moving around inside you...</span>")
|
||||
@@ -229,15 +287,16 @@
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
for(var/mob/M in contents)
|
||||
src.visible_message("<span class='warning'>[src] hatches!</span>")
|
||||
M.loc = src.loc
|
||||
M.forceMove(drop_location())
|
||||
qdel(src)
|
||||
|
||||
|
||||
/obj/item/organ/heart/gland/plasma
|
||||
cooldown_low = 1200
|
||||
cooldown_high = 1800
|
||||
origin_tech = "materials=4;biotech=4;plasmatech=6;abductor=3"
|
||||
uses = -1
|
||||
mind_control_uses = 1
|
||||
mind_control_duration = 800
|
||||
|
||||
/obj/item/organ/heart/gland/plasma/activate()
|
||||
to_chat(owner, "<span class='warning'>You feel bloated.</span>")
|
||||
|
||||
@@ -48,6 +48,7 @@
|
||||
dat += "<a href='?src=[REF(src)];dispense=vest'>Agent Vest</A><br>"
|
||||
dat += "<a href='?src=[REF(src)];dispense=silencer'>Radio Silencer</A><br>"
|
||||
dat += "<a href='?src=[REF(src)];dispense=tool'>Science Tool</A><br>"
|
||||
dat += "<a href='?src=[REF(src)];dispense=mind_device'>Mental Interface Device</A><br>"
|
||||
else
|
||||
dat += "<span class='bad'>NO EXPERIMENT MACHINE DETECTED</span> <br>"
|
||||
|
||||
@@ -109,6 +110,8 @@
|
||||
Dispense(/obj/item/device/abductor/gizmo)
|
||||
if("vest")
|
||||
Dispense(/obj/item/clothing/suit/armor/abductor/vest)
|
||||
if("mind_device")
|
||||
Dispense(/obj/item/device/abductor/mind_device,cost=2)
|
||||
updateUsrDialog()
|
||||
|
||||
/obj/machinery/abductor/console/proc/TeleporterRetrieve()
|
||||
|
||||
@@ -4,8 +4,7 @@
|
||||
desc = "A shell of swarmer that was completely powered down. It can no longer activate itself."
|
||||
icon = 'icons/mob/swarmer.dmi'
|
||||
icon_state = "swarmer_unactivated"
|
||||
origin_tech = "bluespace=4;materials=4;programming=7"
|
||||
materials = list(MAT_METAL = 10000, MAT_GLASS = 4000)
|
||||
materials = list(MAT_METAL=10000, MAT_GLASS=4000)
|
||||
|
||||
/obj/effect/mob_spawn/swarmer
|
||||
name = "unactivated swarmer"
|
||||
@@ -168,9 +167,13 @@
|
||||
/turf/closed/indestructible/swarmer_act()
|
||||
return FALSE
|
||||
|
||||
/obj/swarmer_act()
|
||||
/obj/swarmer_act(mob/living/simple_animal/hostile/swarmer/S)
|
||||
if(resistance_flags & INDESTRUCTIBLE)
|
||||
return FALSE
|
||||
for(var/mob/living/L in contents)
|
||||
if(!issilicon(L) && !isbrain(L))
|
||||
to_chat(S, "<span class='warning'>An organism has been detected inside this object. Aborting.</span>")
|
||||
return FALSE
|
||||
return ..()
|
||||
|
||||
/obj/item/swarmer_act(mob/living/simple_animal/hostile/swarmer/S)
|
||||
|
||||
@@ -375,7 +375,7 @@
|
||||
return
|
||||
var/key_of_revenant
|
||||
message_admins("Revenant ectoplasm was left undestroyed for 1 minute and is reforming into a new revenant.")
|
||||
loc = get_turf(src) //In case it's in a backpack or someone's hand
|
||||
forceMove(drop_location()) //In case it's in a backpack or someone's hand
|
||||
revenant.forceMove(loc)
|
||||
if(client_to_revive)
|
||||
for(var/mob/M in GLOB.dead_mob_list)
|
||||
|
||||
@@ -79,7 +79,6 @@
|
||||
desc = "Still it beats furiously, emanating an aura of utter hate."
|
||||
icon = 'icons/obj/surgery.dmi'
|
||||
icon_state = "demon_heart-on"
|
||||
origin_tech = "combat=5;biotech=7"
|
||||
|
||||
/obj/item/organ/heart/demon/update_icon()
|
||||
return //always beating visually
|
||||
|
||||
@@ -1,7 +1,3 @@
|
||||
/datum/game_mode
|
||||
var/list/datum/mind/syndicates = list()
|
||||
var/nukeops_lastname = ""
|
||||
|
||||
/datum/game_mode/nuclear
|
||||
name = "nuclear emergency"
|
||||
config_tag = "nuclear"
|
||||
@@ -18,12 +14,11 @@
|
||||
<span class='notice'>Crew</span>: Defend the nuclear authentication disk and ensure that it leaves with you on the emergency shuttle."
|
||||
|
||||
var/const/agents_possible = 5 //If we ever need more syndicate agents.
|
||||
|
||||
var/nukes_left = 1 // Call 3714-PRAY right now and order more nukes! Limited offer!
|
||||
var/nuke_off_station = 0 //Used for tracking if the syndies actually haul the nuke to the station
|
||||
var/syndies_didnt_escape = 0 //Used for tracking if the syndies got the shuttle off of the z-level
|
||||
var/list/pre_nukeops = list()
|
||||
|
||||
var/datum/objective_team/nuclear/nuke_team
|
||||
|
||||
/datum/game_mode/nuclear/pre_setup()
|
||||
var/n_agents = min(round(num_players() / 10), antag_candidates.len, agents_possible)
|
||||
for(var/i = 0, i < n_agents, ++i)
|
||||
@@ -33,120 +28,23 @@
|
||||
new_op.special_role = "Nuclear Operative"
|
||||
log_game("[new_op.key] (ckey) has been selected as a nuclear operative")
|
||||
return TRUE
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
/datum/game_mode/proc/update_synd_icons_added(datum/mind/synd_mind)
|
||||
var/datum/atom_hud/antag/opshud = GLOB.huds[ANTAG_HUD_OPS]
|
||||
opshud.join_hud(synd_mind.current)
|
||||
set_antag_hud(synd_mind.current, "synd")
|
||||
|
||||
/datum/game_mode/proc/update_synd_icons_removed(datum/mind/synd_mind)
|
||||
var/datum/atom_hud/antag/opshud = GLOB.huds[ANTAG_HUD_OPS]
|
||||
opshud.leave_hud(synd_mind.current)
|
||||
set_antag_hud(synd_mind.current, null)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/datum/game_mode/nuclear/post_setup()
|
||||
var/nuke_code = random_nukecode()
|
||||
var/agent_number = 1
|
||||
var/datum/mind/leader = pick(pre_nukeops)
|
||||
syndicates += pre_nukeops
|
||||
for(var/i = 1 to pre_nukeops.len)
|
||||
var/datum/mind/op = pre_nukeops[i]
|
||||
|
||||
forge_syndicate_objectives(op)
|
||||
greet_syndicate(op)
|
||||
equip_syndicate(op.current)
|
||||
|
||||
if(nuke_code)
|
||||
op.store_memory("<B>Syndicate Nuclear Bomb Code</B>: [nuke_code]", 0, 0)
|
||||
to_chat(op.current, "The nuclear authorization code is: <B>[nuke_code]</B>")
|
||||
|
||||
if(op == leader)
|
||||
op.current.forceMove(pick(GLOB.nukeop_leader_start))
|
||||
prepare_syndicate_leader(op, nuke_code)
|
||||
else
|
||||
op.current.forceMove(GLOB.nukeop_start[((i - 1) % GLOB.nukeop_start.len) + 1])
|
||||
op.current.real_name = "[syndicate_name()] Operative #[agent_number++]"
|
||||
|
||||
update_synd_icons_added(op)
|
||||
op.current.playsound_local(get_turf(op.current), 'sound/ambience/antag/ops.ogg',100,0)
|
||||
|
||||
var/obj/machinery/nuclearbomb/nuke = locate("syndienuke") in GLOB.nuke_list
|
||||
if(nuke)
|
||||
nuke.r_code = nuke_code
|
||||
//Assign leader
|
||||
var/datum/mind/leader_mind = pre_nukeops[1]
|
||||
var/datum/antagonist/nukeop/L = leader_mind.add_antag_datum(/datum/antagonist/nukeop/leader)
|
||||
nuke_team = L.nuke_team
|
||||
//Assign the remaining operatives
|
||||
for(var/i = 2 to pre_nukeops.len)
|
||||
var/datum/mind/nuke_mind = pre_nukeops[i]
|
||||
nuke_mind.add_antag_datum(/datum/antagonist/nukeop,nuke_team)
|
||||
return ..()
|
||||
|
||||
/datum/game_mode/proc/prepare_syndicate_leader(datum/mind/synd_mind, nuke_code)
|
||||
var/leader_title = pick("Czar", "Boss", "Commander", "Chief", "Kingpin", "Director", "Overlord")
|
||||
addtimer(CALLBACK(src, .proc/nuketeam_name_assign, synd_mind), 1)
|
||||
synd_mind.current.real_name = "[syndicate_name()] [leader_title]"
|
||||
to_chat(synd_mind.current, "<B>You are the Syndicate [leader_title] for this mission. You are responsible for the distribution of telecrystals and your ID is the only one who can open the launch bay doors.</B>")
|
||||
to_chat(synd_mind.current, "<B>If you feel you are not up to this task, give your ID to another operative.</B>")
|
||||
to_chat(synd_mind.current, "<B>In your hand you will find a special item capable of triggering a greater challenge for your team. Examine it carefully and consult with your fellow operatives before activating it.</B>")
|
||||
|
||||
var/obj/item/device/nuclear_challenge/challenge = new /obj/item/device/nuclear_challenge
|
||||
synd_mind.current.put_in_hands(challenge, TRUE)
|
||||
|
||||
var/static/id_cache = typecacheof(/obj/item/card/id)
|
||||
var/list/foundIDs = typecache_filter_list(synd_mind.current.GetAllContents(), id_cache)
|
||||
if(foundIDs.len)
|
||||
for(var/i in 1 to foundIDs.len)
|
||||
var/obj/item/card/id/ID = foundIDs[i]
|
||||
ID.name = "lead agent card"
|
||||
ID.access += ACCESS_SYNDICATE_LEADER
|
||||
else
|
||||
message_admins("Warning: Nuke Ops spawned without access to leave their spawn area!")
|
||||
|
||||
var/obj/item/device/radio/headset/syndicate/alt/A = locate() in synd_mind.current
|
||||
if(A)
|
||||
A.command = TRUE
|
||||
|
||||
if(nuke_code)
|
||||
var/obj/item/paper/P = new
|
||||
P.info = "The nuclear authorization code is: <b>[nuke_code]</b>"
|
||||
P.name = "nuclear bomb code"
|
||||
var/mob/living/carbon/human/H = synd_mind.current
|
||||
H.put_in_hands(P, TRUE)
|
||||
H.update_icons()
|
||||
else
|
||||
nuke_code = "code will be provided later"
|
||||
return
|
||||
|
||||
/datum/game_mode/proc/nuketeam_name_assign(datum/mind/synd_mind)
|
||||
nukeops_lastname = nukelastname(synd_mind.current)
|
||||
NukeNameAssign(nukeops_lastname, syndicates)
|
||||
|
||||
|
||||
/datum/game_mode/proc/forge_syndicate_objectives(datum/mind/syndicate)
|
||||
var/datum/objective/nuclear/syndobj = new
|
||||
syndobj.owner = syndicate
|
||||
syndicate.objectives += syndobj
|
||||
|
||||
|
||||
/datum/game_mode/proc/greet_syndicate(datum/mind/syndicate, you_are=1)
|
||||
if(you_are)
|
||||
to_chat(syndicate.current, "<span class='notice'>You are a [syndicate_name()] agent!</span>")
|
||||
syndicate.announce_objectives()
|
||||
|
||||
/datum/game_mode/proc/equip_syndicate(mob/living/carbon/human/synd_mob, telecrystals = TRUE)
|
||||
synd_mob.set_species(/datum/species/human) //Plasamen burn up otherwise, and lizards are vulnerable to asimov AIs
|
||||
|
||||
if(telecrystals)
|
||||
synd_mob.equipOutfit(/datum/outfit/syndicate)
|
||||
else
|
||||
synd_mob.equipOutfit(/datum/outfit/syndicate/no_crystals)
|
||||
return TRUE
|
||||
|
||||
/datum/game_mode/nuclear/OnNukeExplosion(off_station)
|
||||
..()
|
||||
nukes_left--
|
||||
var/obj/docking_port/mobile/Shuttle = SSshuttle.getShuttle("syndicate")
|
||||
syndies_didnt_escape = (Shuttle && (Shuttle.z == ZLEVEL_CENTCOM || Shuttle.z == ZLEVEL_TRANSIT)) ? 0 : 1
|
||||
nuke_off_station = off_station
|
||||
|
||||
/datum/game_mode/nuclear/check_win()
|
||||
if (nukes_left == 0)
|
||||
@@ -154,8 +52,8 @@
|
||||
return ..()
|
||||
|
||||
/datum/game_mode/proc/are_operatives_dead()
|
||||
for(var/datum/mind/operative_mind in syndicates)
|
||||
if(ishuman(operative_mind.current) && (operative_mind.current.stat!=2))
|
||||
for(var/datum/mind/operative_mind in get_antagonists(/datum/antagonist/nukeop))
|
||||
if(ishuman(operative_mind.current) && (operative_mind.current.stat != DEAD))
|
||||
return FALSE
|
||||
return TRUE
|
||||
|
||||
@@ -164,7 +62,7 @@
|
||||
return replacementmode.check_finished()
|
||||
if((SSshuttle.emergency.mode == SHUTTLE_ENDGAME) || station_was_nuked)
|
||||
return TRUE
|
||||
if(are_operatives_dead())
|
||||
if(nuke_team.operatives_dead())
|
||||
var/obj/machinery/nuclearbomb/N
|
||||
pass(N) //suppress unused warning
|
||||
if(N.bomb_set) //snaaaaaaaaaake! It's not over yet!
|
||||
@@ -172,85 +70,39 @@
|
||||
..()
|
||||
|
||||
/datum/game_mode/nuclear/declare_completion()
|
||||
var/disk_rescued = 1
|
||||
for(var/obj/item/disk/nuclear/D in GLOB.poi_list)
|
||||
if(!D.onCentCom())
|
||||
disk_rescued = 0
|
||||
break
|
||||
var/crew_evacuated = (SSshuttle.emergency.mode == SHUTTLE_ENDGAME)
|
||||
|
||||
if(nuke_off_station == NUKE_SYNDICATE_BASE)
|
||||
SSticker.mode_result = "loss - syndicate nuked - disk secured"
|
||||
to_chat(world, "<FONT size = 3><B>Humiliating Syndicate Defeat</B></FONT>")
|
||||
to_chat(world, "<B>The crew of [station_name()] gave [syndicate_name()] operatives back their bomb! The syndicate base was destroyed!</B> Next time, don't lose the nuke!")
|
||||
|
||||
SSticker.news_report = NUKE_SYNDICATE_BASE
|
||||
|
||||
else if(!disk_rescued && station_was_nuked && !syndies_didnt_escape)
|
||||
SSticker.mode_result = "win - syndicate nuke"
|
||||
to_chat(world, "<FONT size = 3><B>Syndicate Major Victory!</B></FONT>")
|
||||
to_chat(world, "<B>[syndicate_name()] operatives have destroyed [station_name()]!</B>")
|
||||
|
||||
SSticker.news_report = STATION_NUKED
|
||||
|
||||
else if (!disk_rescued && station_was_nuked && syndies_didnt_escape)
|
||||
SSticker.mode_result = "halfwin - syndicate nuke - did not evacuate in time"
|
||||
to_chat(world, "<FONT size = 3><B>Total Annihilation</B></FONT>")
|
||||
to_chat(world, "<B>[syndicate_name()] operatives destroyed [station_name()] but did not leave the area in time and got caught in the explosion.</B> Next time, don't lose the disk!")
|
||||
|
||||
SSticker.news_report = STATION_NUKED
|
||||
|
||||
else if (!disk_rescued && !station_was_nuked && nuke_off_station && !syndies_didnt_escape)
|
||||
SSticker.mode_result = "halfwin - blew wrong station"
|
||||
to_chat(world, "<FONT size = 3><B>Crew Minor Victory</B></FONT>")
|
||||
to_chat(world, "<B>[syndicate_name()] operatives secured the authentication disk but blew up something that wasn't [station_name()].</B> Next time, don't do that!")
|
||||
|
||||
SSticker.news_report = NUKE_MISS
|
||||
|
||||
else if (!disk_rescued && !station_was_nuked && nuke_off_station && syndies_didnt_escape)
|
||||
SSticker.mode_result = "halfwin - blew wrong station - did not evacuate in time"
|
||||
to_chat(world, "<FONT size = 3><B>[syndicate_name()] operatives have earned Darwin Award!</B></FONT>")
|
||||
to_chat(world, "<B>[syndicate_name()] operatives blew up something that wasn't [station_name()] and got caught in the explosion.</B> Next time, don't do that!")
|
||||
|
||||
SSticker.news_report = NUKE_MISS
|
||||
|
||||
else if ((disk_rescued || SSshuttle.emergency.mode != SHUTTLE_ENDGAME) && are_operatives_dead())
|
||||
SSticker.mode_result = "loss - evacuation - disk secured - syndi team dead"
|
||||
to_chat(world, "<FONT size = 3><B>Crew Major Victory!</B></FONT>")
|
||||
to_chat(world, "<B>The Research Staff has saved the disk and killed the [syndicate_name()] Operatives</B>")
|
||||
|
||||
SSticker.news_report = OPERATIVES_KILLED
|
||||
|
||||
else if (disk_rescued)
|
||||
SSticker.mode_result = "loss - evacuation - disk secured"
|
||||
to_chat(world, "<FONT size = 3><B>Crew Major Victory</B></FONT>")
|
||||
to_chat(world, "<B>The Research Staff has saved the disk and stopped the [syndicate_name()] Operatives!</B>")
|
||||
|
||||
SSticker.news_report = OPERATIVES_KILLED
|
||||
|
||||
else if (!disk_rescued && are_operatives_dead())
|
||||
SSticker.mode_result = "halfwin - evacuation - disk not secured"
|
||||
to_chat(world, "<FONT size = 3><B>Neutral Victory!</B></FONT>")
|
||||
to_chat(world, "<B>The Research Staff failed to secure the authentication disk but did manage to kill most of the [syndicate_name()] Operatives!</B>")
|
||||
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
|
||||
else if (!disk_rescued && crew_evacuated)
|
||||
SSticker.mode_result = "halfwin - detonation averted"
|
||||
to_chat(world, "<FONT size = 3><B>Syndicate Minor Victory!</B></FONT>")
|
||||
to_chat(world, "<B>[syndicate_name()] operatives survived the assault but did not achieve the destruction of [station_name()].</B> Next time, don't lose the disk!")
|
||||
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
|
||||
else if (!disk_rescued && !crew_evacuated)
|
||||
SSticker.mode_result = "halfwin - interrupted"
|
||||
to_chat(world, "<FONT size = 3><B>Neutral Victory</B></FONT>")
|
||||
to_chat(world, "<B>Round was mysteriously interrupted!</B>")
|
||||
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
|
||||
..()
|
||||
return
|
||||
var result = nuke_team.get_result()
|
||||
switch(result)
|
||||
if(NUKE_RESULT_FLUKE)
|
||||
SSticker.mode_result = "loss - syndicate nuked - disk secured"
|
||||
SSticker.news_report = NUKE_SYNDICATE_BASE
|
||||
if(NUKE_RESULT_NUKE_WIN)
|
||||
SSticker.mode_result = "win - syndicate nuke"
|
||||
SSticker.news_report = STATION_NUKED
|
||||
if(NUKE_RESULT_NOSURVIVORS)
|
||||
SSticker.mode_result = "halfwin - syndicate nuke - did not evacuate in time"
|
||||
SSticker.news_report = STATION_NUKED
|
||||
if(NUKE_RESULT_WRONG_STATION)
|
||||
SSticker.mode_result = "halfwin - blew wrong station"
|
||||
SSticker.news_report = NUKE_MISS
|
||||
if(NUKE_RESULT_WRONG_STATION_DEAD)
|
||||
SSticker.mode_result = "halfwin - blew wrong station - did not evacuate in time"
|
||||
SSticker.news_report = NUKE_MISS
|
||||
if(NUKE_RESULT_CREW_WIN_SYNDIES_DEAD)
|
||||
SSticker.mode_result = "loss - evacuation - disk secured - syndi team dead"
|
||||
SSticker.news_report = OPERATIVES_KILLED
|
||||
if(NUKE_RESULT_CREW_WIN)
|
||||
SSticker.mode_result = "loss - evacuation - disk secured"
|
||||
SSticker.news_report = OPERATIVES_KILLED
|
||||
if(NUKE_RESULT_DISK_LOST)
|
||||
SSticker.mode_result = "halfwin - evacuation - disk not secured"
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
if(NUKE_RESULT_DISK_STOLEN)
|
||||
SSticker.mode_result = "halfwin - detonation averted"
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
else
|
||||
SSticker.mode_result = "halfwin - interrupted"
|
||||
SSticker.news_report = OPERATIVE_SKIRMISH
|
||||
return ..()
|
||||
|
||||
/datum/game_mode/nuclear/generate_report()
|
||||
return "One of Central Command's trading routes was recently disrupted by a raid carried out by the Gorlex Marauders. They seemed to only be after one ship - a highly-sensitive \
|
||||
@@ -258,48 +110,16 @@
|
||||
can activate this explosive is on your station. Ensure that it is protected at all times, and remain alert for possible intruders."
|
||||
|
||||
/datum/game_mode/proc/auto_declare_completion_nuclear()
|
||||
if( syndicates.len || (SSticker && istype(SSticker.mode, /datum/game_mode/nuclear)) )
|
||||
var/text = "<br><FONT size=3><B>The syndicate operatives were:</B></FONT>"
|
||||
var/purchases = ""
|
||||
var/TC_uses = 0
|
||||
for(var/datum/mind/syndicate in syndicates)
|
||||
text += printplayer(syndicate)
|
||||
for(var/datum/component/uplink/H in GLOB.uplinks)
|
||||
if(H.purchase_log)
|
||||
purchases += H.purchase_log.generate_render()
|
||||
else
|
||||
stack_trace("WARNING: Uplink with no purchase_log in nuclear mode! Owner: [H.owner]")
|
||||
text += "<br>"
|
||||
text += "(Syndicates used [TC_uses] TC) [purchases]"
|
||||
if(TC_uses == 0 && station_was_nuked && !are_operatives_dead())
|
||||
text += "<BIG>[icon2html('icons/badass.dmi', world, "badass")]</BIG>"
|
||||
to_chat(world, text)
|
||||
var/list/nuke_teams = list()
|
||||
for(var/datum/antagonist/nukeop/N in GLOB.antagonists) //collect all nuke teams
|
||||
nuke_teams |= N.nuke_team
|
||||
for(var/datum/objective_team/nuclear/nuke_team in nuke_teams)
|
||||
nuke_team.roundend_display()
|
||||
return TRUE
|
||||
|
||||
|
||||
/proc/nukelastname(mob/M) //--All praise goes to NEO|Phyte, all blame goes to DH, and it was Cindi-Kate's idea. Also praise Urist for copypasta ho.
|
||||
var/randomname = pick(GLOB.last_names)
|
||||
var/newname = copytext(sanitize(input(M,"You are the nuke operative [pick("Czar", "Boss", "Commander", "Chief", "Kingpin", "Director", "Overlord")]. Please choose a last name for your family.", "Name change",randomname)),1,MAX_NAME_LEN)
|
||||
|
||||
if (!newname)
|
||||
newname = randomname
|
||||
|
||||
else
|
||||
if (newname == "Unknown" || newname == "floor" || newname == "wall" || newname == "rwall" || newname == "_")
|
||||
to_chat(M, "That name is reserved.")
|
||||
return nukelastname(M)
|
||||
|
||||
return capitalize(newname)
|
||||
|
||||
/proc/NukeNameAssign(lastname,list/syndicates)
|
||||
for(var/datum/mind/synd_mind in syndicates)
|
||||
var/mob/living/carbon/human/H = synd_mind.current
|
||||
synd_mind.name = H.dna.species.random_name(H.gender,0,lastname)
|
||||
synd_mind.current.real_name = synd_mind.name
|
||||
return
|
||||
|
||||
/proc/is_nuclear_operative(mob/M)
|
||||
return M && istype(M) && M.mind && SSticker && SSticker.mode && M.mind in SSticker.mode.syndicates
|
||||
return M && istype(M) && M.mind && M.mind.has_antag_datum(/datum/antagonist/nukeop)
|
||||
|
||||
/datum/outfit/syndicate
|
||||
name = "Syndicate Operative - Basic"
|
||||
@@ -315,15 +135,24 @@
|
||||
backpack_contents = list(/obj/item/storage/box/syndie=1)
|
||||
|
||||
var/tc = 25
|
||||
var/command_radio = FALSE
|
||||
|
||||
|
||||
/datum/outfit/syndicate/leader
|
||||
name = "Syndicate Leader - Basic"
|
||||
id = /obj/item/card/id/syndicate/nuke_leader
|
||||
r_hand = /obj/item/device/nuclear_challenge
|
||||
command_radio = TRUE
|
||||
|
||||
/datum/outfit/syndicate/no_crystals
|
||||
tc = 0
|
||||
|
||||
|
||||
/datum/outfit/syndicate/post_equip(mob/living/carbon/human/H)
|
||||
var/obj/item/device/radio/R = H.ears
|
||||
R.set_frequency(GLOB.SYND_FREQ)
|
||||
R.freqlock = 1
|
||||
if(command_radio)
|
||||
R.command = TRUE
|
||||
|
||||
if(tc)
|
||||
var/obj/item/device/radio/uplink/nuclear/U = new(H, H.key, tc)
|
||||
|
||||
@@ -77,16 +77,16 @@
|
||||
icon = 'icons/obj/machines/nuke_terminal.dmi'
|
||||
icon_state = "nuclearbomb_base"
|
||||
anchored = TRUE //stops it being moved
|
||||
use_tag = TRUE
|
||||
|
||||
/obj/machinery/nuclearbomb/syndicate
|
||||
use_tag = TRUE
|
||||
//ui_style = "syndicate" // actually the nuke op bomb is a stole nt bomb
|
||||
|
||||
/obj/machinery/nuclearbomb/syndicate/get_cinematic_type(off_station)
|
||||
var/datum/game_mode/nuclear/NM = SSticker.mode
|
||||
switch(off_station)
|
||||
if(0)
|
||||
if(istype(NM) && NM.syndies_didnt_escape)
|
||||
if(istype(NM) && !NM.nuke_team.syndies_escaped())
|
||||
return CINEMATIC_ANNIHILATION
|
||||
else
|
||||
return CINEMATIC_NUKE_WIN
|
||||
@@ -353,7 +353,7 @@
|
||||
var/N = text2num(user_input)
|
||||
if(!N)
|
||||
return
|
||||
timer_set = Clamp(N,minimum_timer_set,maximum_timer_set)
|
||||
timer_set = CLAMP(N,minimum_timer_set,maximum_timer_set)
|
||||
. = TRUE
|
||||
if("safety")
|
||||
if(auth && yes_code)
|
||||
@@ -572,4 +572,4 @@ This is here to make the tiles around the station mininuke change when it's arme
|
||||
user.visible_message("<span class='suicide'>[user] is pretending to go delta! It looks like [user.p_theyre()] trying to commit suicide!</span>")
|
||||
playsound(src, 'sound/machines/alarm.ogg', 30, -1, 1)
|
||||
addtimer(CALLBACK(src, .proc/manual_suicide, user), 101)
|
||||
return MANUAL_SUICIDE
|
||||
return MANUAL_SUICIDE
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user