Merge branch 'master' into feet

This commit is contained in:
CornMyCob
2020-06-25 13:53:54 +01:00
273 changed files with 2536 additions and 6004 deletions
+3
View File
@@ -490,6 +490,9 @@
if(SSticker.mode.wizards.len)
dat += check_role_table("Wizards", SSticker.mode.wizards)
if(SSticker.mode.apprentices.len)
dat += check_role_table("Apprentices", SSticker.mode.apprentices)
if(SSticker.mode.raiders.len)
dat += check_role_table("Raiders", SSticker.mode.raiders)
+4 -4
View File
@@ -1,7 +1,6 @@
/client/proc/atmosscan()
set category = "Mapping"
set name = "Check Piping"
set background = 1
if(!src.holder)
to_chat(src, "Only administrators may use this command.")
return
@@ -12,17 +11,18 @@
to_chat(usr, "Checking for disconnected pipes...")
//all plumbing - yes, some things might get stated twice, doesn't matter.
for(var/obj/machinery/atmospherics/plumbing in world)
for(var/thing in SSair.atmos_machinery)
var/obj/machinery/atmospherics/plumbing = thing
if(plumbing.nodealert)
to_chat(usr, "Unconnected [plumbing.name] located at [plumbing.x],[plumbing.y],[plumbing.z] ([get_area(plumbing.loc)])")
//Manifolds
for(var/obj/machinery/atmospherics/pipe/manifold/pipe in world)
for(var/obj/machinery/atmospherics/pipe/manifold/pipe in SSair.atmos_machinery)
if(!pipe.node1 || !pipe.node2 || !pipe.node3)
to_chat(usr, "Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])")
//Pipes
for(var/obj/machinery/atmospherics/pipe/simple/pipe in world)
for(var/obj/machinery/atmospherics/pipe/simple/pipe in SSair.atmos_machinery)
if(!pipe.node1 || !pipe.node2)
to_chat(usr, "Unconnected [pipe.name] located at [pipe.x],[pipe.y],[pipe.z] ([get_area(pipe.loc)])")
+9 -7
View File
@@ -487,7 +487,8 @@ GLOBAL_PROTECT(AdminProcCaller)
for(var/area/A in world)
areas_all |= A.type
for(var/obj/machinery/power/apc/APC in world)
for(var/thing in GLOB.apcs)
var/obj/machinery/power/apc/APC = thing
var/area/A = get_area(APC)
if(!A)
continue
@@ -496,7 +497,8 @@ GLOBAL_PROTECT(AdminProcCaller)
else
areas_with_multiple_APCs |= A.type
for(var/obj/machinery/alarm/alarm in world)
for(var/thing in GLOB.air_alarms)
var/obj/machinery/alarm/alarm = thing
var/area/A = get_area(alarm)
if(!A)
continue
@@ -505,31 +507,31 @@ GLOBAL_PROTECT(AdminProcCaller)
else
areas_with_multiple_air_alarms |= A.type
for(var/obj/machinery/requests_console/RC in world)
for(var/obj/machinery/requests_console/RC in GLOB.machines)
var/area/A = get_area(RC)
if(!A)
continue
areas_with_RC |= A.type
for(var/obj/machinery/light/L in world)
for(var/obj/machinery/light/L in GLOB.machines)
var/area/A = get_area(L)
if(!A)
continue
areas_with_light |= A.type
for(var/obj/machinery/light_switch/LS in world)
for(var/obj/machinery/light_switch/LS in GLOB.machines)
var/area/A = get_area(LS)
if(!A)
continue
areas_with_LS |= A.type
for(var/obj/item/radio/intercom/I in world)
for(var/obj/item/radio/intercom/I in GLOB.global_radios)
var/area/A = get_area(I)
if(!A)
continue
areas_with_intercom |= A.type
for(var/obj/machinery/camera/C in world)
for(var/obj/machinery/camera/C in GLOB.machines)
var/area/A = get_area(C)
if(!A)
continue
+1 -3
View File
@@ -15,9 +15,7 @@
if(T.active_hotspot)
burning = 1
to_chat(usr, "<span class='notice'>@[target.x],[target.y]: O:[GM.oxygen] T:[GM.toxins] N:[GM.nitrogen] C:[GM.carbon_dioxide] w [GM.temperature] Kelvin, [GM.return_pressure()] kPa [(burning)?("<span class='warning'>BURNING</span>"):(null)]</span>")
for(var/datum/gas/trace_gas in GM.trace_gases)
to_chat(usr, "[trace_gas.type]: [trace_gas.moles]")
to_chat(usr, "<span class='notice'>@[target.x],[target.y]: O:[GM.oxygen] T:[GM.toxins] N:[GM.nitrogen] C:[GM.carbon_dioxide] N2O: [GM.sleeping_agent] Agent B: [GM.agent_b] w [GM.temperature] Kelvin, [GM.return_pressure()] kPa [(burning)?("<span class='warning'>BURNING</span>"):(null)]</span>")
message_admins("[key_name_admin(usr)] has checked the air status of [target]")
log_admin("[key_name(usr)] has checked the air status of [target]")
+2 -1
View File
@@ -48,7 +48,8 @@ GLOBAL_VAR_INIT(sent_honksquad, 0)
commandos += candidate//Add their ghost to commandos.
//Spawns HONKsquad and equips them.
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(honksquad_number<=0) break
if(L.name == "HONKsquad")
honk_leader_selected = honksquad_number == 1?1:0
@@ -66,7 +66,8 @@ GLOBAL_VAR_INIT(sent_syndicate_infiltration_team, 0)
var/list/sit_spawns = list()
var/list/sit_spawns_leader = list()
var/list/sit_spawns_mgmt = list()
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "Syndicate-Infiltrator")
sit_spawns += L
if(L.name == "Syndicate-Infiltrator-Leader")
+1 -1
View File
@@ -118,7 +118,7 @@ GLOBAL_VAR_INIT(intercom_range_display_status, 0)
qdel(M)
if(GLOB.intercom_range_display_status)
for(var/obj/item/radio/intercom/I in world)
for(var/obj/item/radio/intercom/I in GLOB.global_radios)
for(var/turf/T in orange(7,I))
var/obj/effect/debugging/marker/F = new/obj/effect/debugging/marker(T)
if(!(F in view(7,I.loc)))
@@ -627,6 +627,7 @@ GLOBAL_LIST_INIT(VVpixelmovement, list("step_x", "step_y", "step_size", "bound_h
if(!O.vv_edit_var(variable, var_new))
to_chat(src, "Your edit was rejected by the object.")
return
SEND_GLOBAL_SIGNAL(COMSIG_GLOB_VAR_EDIT, args)
log_world("### VarEdit by [src]: [O.type] [variable]=[html_encode("[var_new]")]")
log_admin("[key_name(src)] modified [original_name]'s [variable] to [var_new]")
var/msg = "[key_name_admin(src)] modified [original_name]'s [variable] to [var_new]"
+5 -3
View File
@@ -267,7 +267,7 @@ client/proc/one_click_antag()
var/I = image('icons/mob/mob.dmi', loc = synd_mind_1.current, icon_state = "synd")
synd_mind.current.client.images += I
for(var/obj/machinery/nuclearbomb/bomb in world)
for(var/obj/machinery/nuclearbomb/bomb in GLOB.machines)
bomb.r_code = nuke_code // All the nukes are set to this code.
return 1
@@ -455,7 +455,8 @@ client/proc/one_click_antag()
if(candidates.len)
var/raiders = min(antnum, candidates.len)
//Spawns vox raiders and equips them.
for(var/obj/effect/landmark/L in world)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "voxstart")
if(raiders<=0)
break
@@ -583,7 +584,8 @@ client/proc/one_click_antag()
var/teamOneMembers = 5
var/teamTwoMembers = 5
var/datum/preferences/A = new()
for(var/obj/effect/landmark/L in world)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "tdome1")
if(teamOneMembers<=0)
break
+7 -4
View File
@@ -30,7 +30,7 @@ GLOBAL_VAR_INIT(sent_strike_team, 0)
// Find the nuclear auth code
var/nuke_code
var/temp_code
for(var/obj/machinery/nuclearbomb/N in world)
for(var/obj/machinery/nuclearbomb/N in GLOB.machines)
temp_code = text2num(N.r_code)
if(temp_code)//if it's actually a number. It won't convert any non-numericals.
nuke_code = N.r_code
@@ -48,7 +48,8 @@ GLOBAL_VAR_INIT(sent_strike_team, 0)
var/commando_number = COMMANDOS_POSSIBLE //for selecting a leader
var/is_leader = TRUE // set to FALSE after leader is spawned
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(commando_number <= 0)
break
@@ -109,7 +110,8 @@ GLOBAL_VAR_INIT(sent_strike_team, 0)
commando_number--
//Spawns the rest of the commando gear.
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "Commando_Manual")
//new /obj/item/gun/energy/pulse_rifle(L.loc)
var/obj/item/paper/P = new(L.loc)
@@ -120,7 +122,8 @@ GLOBAL_VAR_INIT(sent_strike_team, 0)
P.stamp(stamp)
qdel(stamp)
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "Commando-Bomb")
new /obj/effect/spawner/newbomb/timer/syndicate(L.loc)
qdel(L)
@@ -38,7 +38,7 @@ GLOBAL_VAR_INIT(sent_syndicate_strike_team, 0)
// Find the nuclear auth code
var/nuke_code
var/temp_code
for(var/obj/machinery/nuclearbomb/N in world)
for(var/obj/machinery/nuclearbomb/N in GLOB.machines)
temp_code = text2num(N.r_code)
if(temp_code)//if it's actually a number. It won't convert any non-numericals.
nuke_code = N.r_code
@@ -53,7 +53,8 @@ GLOBAL_VAR_INIT(sent_syndicate_strike_team, 0)
GLOB.sent_syndicate_strike_team = 1
//Spawns commandos and equips them.
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(syndicate_commando_number <= 0)
break
+2 -4
View File
@@ -59,8 +59,7 @@
cooldown--
if(cooldown <= 0)
return FALSE
spawn(10)
process_cooldown()
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
return TRUE
/obj/item/assembly/Destroy()
@@ -94,8 +93,7 @@
if(!secured || cooldown > 0)
return FALSE
cooldown = 2
spawn(10)
process_cooldown()
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
return TRUE
/obj/item/assembly/toggle_secure()
+3 -4
View File
@@ -127,13 +127,12 @@
/obj/item/assembly/infra/proc/trigger_beam()
if(!secured || !on || cooldown > 0)
return FALSE
pulse(0)
cooldown = 2
pulse(FALSE)
audible_message("[bicon(src)] *beep* *beep*", null, 3)
if(first)
qdel(first)
cooldown = 2
spawn(10)
process_cooldown()
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
/obj/item/assembly/infra/interact(mob/user)//TODO: change this this to the wire control panel
if(!secured) return
+3 -4
View File
@@ -47,11 +47,10 @@
/obj/item/assembly/prox_sensor/proc/sense()
if(!secured || !scanning || cooldown > 0)
return FALSE
pulse(0)
visible_message("[bicon(src)] *beep* *beep*", "*beep* *beep*")
cooldown = 2
spawn(10)
process_cooldown()
pulse(FALSE)
visible_message("[bicon(src)] *beep* *beep*", "*beep* *beep*")
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
/obj/item/assembly/prox_sensor/process()
if(timing && (time >= 0))
+1 -2
View File
@@ -41,8 +41,7 @@
if(cooldown > 0)
return FALSE
cooldown = 2
spawn(10)
process_cooldown()
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
signal()
return TRUE
+3 -4
View File
@@ -39,12 +39,11 @@
/obj/item/assembly/timer/proc/timer_end()
if(!secured || cooldown > 0)
return FALSE
pulse(0)
cooldown = 2
pulse(FALSE)
if(loc)
loc.visible_message("[bicon(src)] *beep* *beep*", "*beep* *beep*")
cooldown = 2
spawn(10)
process_cooldown()
addtimer(CALLBACK(src, .proc/process_cooldown), 10)
/obj/item/assembly/timer/process()
if(timing && (time > 0))
-454
View File
@@ -1,454 +0,0 @@
/obj/machinery/computer/general_air_control/atmos_automation
icon = 'icons/obj/computer.dmi'
icon_screen = "area_atmos"
icon_keyboard = "atmos_key"
circuit = /obj/item/circuitboard/atmos_automation
req_one_access_txt = "24;10"
Mtoollink = 1
show_sensors = 0
var/on = 0
name = "Atmospherics Automations Console"
var/list/datum/automation/automations = list()
/obj/machinery/computer/general_air_control/atmos_automation/receive_signal(datum/signal/signal)
if(!signal || signal.encryption) return
var/id_tag = signal.data["tag"]
if(!id_tag)
return
sensor_information[id_tag] = signal.data
/obj/machinery/computer/general_air_control/atmos_automation/process()
if(on)
for(var/datum/automation/A in automations)
A.process()
/obj/machinery/computer/general_air_control/atmos_automation/update_icon()
icon_state = initial(icon_state)
// Broken
if(stat & BROKEN)
icon_state += "b"
// Powered
else if(stat & NOPOWER)
icon_state = initial(icon_state)
icon_state += "0"
else if(on)
icon_state += "_active"
/obj/machinery/computer/general_air_control/atmos_automation/proc/request_device_refresh(device)
send_signal(list("tag"=device, "status"))
/obj/machinery/computer/general_air_control/atmos_automation/proc/send_signal(list/data, filter = RADIO_ATMOSIA)//filter's here so the AAC can cross communicate to things like vents, which have a different filter
var/datum/signal/signal = new
signal.transmission_method = 1 //radio signal
signal.source = src
signal.data=data
signal.data["sigtype"]="command"
signal.data["advcontrol"]=1//AAC balancing, you need to manually get up to the machine to make it listen to this
radio_connection.post_signal(src, signal, range = 8, filter = filter)
/obj/machinery/computer/general_air_control/atmos_automation/proc/selectValidChildFor(datum/automation/parent, mob/user, list/valid_returntypes)
var/list/choices=list()
for(var/childtype in GLOB.automation_types)
var/datum/automation/A = new childtype(src)
if(A.returntype == null)
continue
if(!(A.returntype in valid_returntypes))
continue
choices[A.name]=A
if(choices.len==0)
testing("Unable to find automations with returntype in [english_list(valid_returntypes)]!")
return 0
var/label=input(user, "Select new automation:", "Automations", "Cancel") as null|anything in choices
if(!label)
return 0
return choices[label]
/obj/machinery/computer/general_air_control/atmos_automation/return_text()
var/out=..()
if(on)
out += "<a href=\"?src=[UID()];on=1\" style=\"font-size:large;font-weight:bold;color:red;\">RUNNING</a>"
else
out += "<a href=\"?src=[UID()];on=1\" style=\"font-size:large;font-weight:bold;color:green;\">STOPPED</a>"
out += {"
<h2>Automations</h2>
<p>\[
<a href="?src=[UID()];add=1">
Add
</a>
|
<a href="?src=[UID()];reset=*">
Reset All
</a>
|
<a href="?src=[UID()];remove=*">
Clear
</a>
\]</p>
<p>\[
<a href="?src=[UID()];dump=1">
Export
</a>
|
<a href="?src=[UID()];read=1">
Import
</a>
\]</p>"}
if(automations.len==0)
out += "<i>No automations present.</i>"
else
for(var/datum/automation/A in automations)
out += {"
<fieldset>
<legend>
<a href="?src=[UID()];label=\ref[A]">[A.label]</a>
(<a href="?src=[UID()];reset=\ref[A]">Reset</a> |
<a href="?src=[UID()];remove=\ref[A]">&times;</a>)
</legend>
[A.GetText()]
</fieldset>
"}
return out
/obj/machinery/computer/general_air_control/atmos_automation/Topic(href,href_list)
if(..())
return 1
if(href_list["on"])
on = !on
updateUsrDialog()
update_icon()
return 1
if(href_list["add"])
var/new_child=selectValidChildFor(null,usr,list(0))
if(!new_child)
return 1
automations += new_child
updateUsrDialog()
return 1
if(href_list["label"])
var/datum/automation/A=locate(href_list["label"])
if(!A) return 1
var/nl=input(usr, "Please enter a label for this automation task.") as text|null
if(!nl) return 1
nl = copytext(sanitize(nl), 1, 50)
A.label=nl
updateUsrDialog()
return 1
if(href_list["reset"])
if(href_list["reset"]=="*")
for(var/datum/automation/A in automations)
if(!A) continue
A.OnReset()
else
var/datum/automation/A=locate(href_list["reset"])
if(!A) return 1
A.OnReset()
updateUsrDialog()
return 1
if(href_list["remove"])
if(href_list["remove"]=="*")
var/confirm=alert("Are you sure you want to remove ALL automations?","Automations","Yes","No")
if(confirm == "No") return 0
for(var/datum/automation/A in automations)
if(!A) continue
A.OnRemove()
automations.Remove(A)
else
var/datum/automation/A=locate(href_list["remove"])
if(!A) return 1
A.OnRemove()
automations.Remove(A)
updateUsrDialog()
return 1
if(href_list["read"])
var/code = input("Input exported AAC code.","Automations","") as message|null
if(!code) return 0
ReadCode(code)
updateUsrDialog()
return 1
if(href_list["dump"])
input("Exported AAC code:","Automations",DumpCode()) as message|null
return 0
/obj/machinery/computer/general_air_control/atmos_automation/proc/MakeCompare(datum/automation/a, datum/automation/b, comparetype)
var/datum/automation/compare/compare=new(src)
compare.comparator = comparetype
compare.children[1] = a
compare.children[2] = b
return compare
/obj/machinery/computer/general_air_control/atmos_automation/proc/MakeNumber(value)
var/datum/automation/static_value/val = new(src)
val.value=value
return val
/obj/machinery/computer/general_air_control/atmos_automation/proc/MakeGetSensorData(sns_tag,field)
var/datum/automation/get_sensor_data/sensor=new(src)
sensor.sensor=sns_tag
sensor.field=field
return sensor
/obj/machinery/computer/general_air_control/atmos_automation/proc/DumpCode()
var/list/json[0]
for(var/datum/automation/A in automations)
json += list(A.Export())
return json_encode(json)
/obj/machinery/computer/general_air_control/atmos_automation/proc/ReadCode(jsonStr)
automations.Cut()
var/list/json = json_decode(jsonStr)
if(json.len>0)
for(var/list/cData in json)
if(isnull(cData) || !("type" in cData))
testing("AAC: Null cData in root JS array.")
continue
var/Atype=text2path(cData["type"])
if(!(Atype in GLOB.automation_types))
testing("AAC: Unrecognized Atype [Atype].")
continue
var/datum/automation/A = new Atype(src)
A.Import(cData)
automations += A
/obj/machinery/computer/general_air_control/atmos_automation/burnchamber
var/injector_tag="inc_in"
var/output_tag="inc_out"
var/sensor_tag="inc_sensor"
frequency=AIRLOCK_FREQ
var/temperature=1000
/obj/machinery/computer/general_air_control/atmos_automation/burnchamber/New()
..()
// On State
// Pretty much this:
/*
if(get_sensor("inc_sensor","temperature") < 200)
set_injector_state("inc_in",1)
set_vent_pump_power("inc_out",0)
else
set_vent_pump_power("inc_out",1
*/
var/datum/automation/get_sensor_data/sensor=new(src)
sensor.sensor=sensor_tag
sensor.field="temperature"
var/datum/automation/static_value/val = new(src)
val.value=temperature - 800
var/datum/automation/compare/compare=new(src)
compare.comparator = "Less Than"
compare.children[1] = sensor
compare.children[2] = val
var/datum/automation/set_injector_power/inj_on=new(src)
inj_on.injector=injector_tag
inj_on.state=1
var/datum/automation/set_vent_pump_power/vp_on=new(src)
vp_on.vent_pump=output_tag
vp_on.state=1
var/datum/automation/set_vent_pump_power/vp_off=new(src)
vp_off.vent_pump=output_tag
vp_off.state=0
var/datum/automation/if_statement/i = new (src)
i.label = "Fuel Injector On"
i.condition = compare
i.children_then.Add(inj_on)
i.children_then.Add(vp_off)
i.children_else.Add(vp_on)
automations += i
// Off state
/*
if(get_sensor("inc_sensor","temperature") > 1000)
set_injector_state("inc_in",0)
*/
sensor=new(src)
sensor.sensor=sensor_tag
sensor.field="temperature"
val = new(src)
val.value=temperature
compare=new(src)
compare.comparator = "Greater Than"
compare.children[1] = sensor
compare.children[2] = val
var/datum/automation/set_injector_power/inj_off=new(src)
inj_off.injector=injector_tag
inj_off.state=0
i = new (src)
i.label = "Fuel Injector Off"
i.condition = compare
i.children_then.Add(inj_off)
automations += i
/obj/machinery/computer/general_air_control/atmos_automation/air_mixing
var/n2_injector_tag="air_n2_in"
var/o2_injector_tag="air_o2_in"
var/output_tag="air_out"
var/sensor_tag="air_sensor"
frequency=ATMOS_DISTRO_FREQ
var/temperature=1000
/obj/machinery/computer/general_air_control/atmos_automation/air_mixing/New()
..()
buildO2()
buildN2()
buildOutletVent()
/obj/machinery/computer/general_air_control/atmos_automation/air_mixing/proc/buildO2()
///////////////////////////////////////////////////////////////
// Oxygen Injection
///////////////////////////////////////////////////////////////
var/datum/automation/set_injector_power/inj_on=new(src)
inj_on.injector=o2_injector_tag
inj_on.state=1
var/datum/automation/set_injector_power/inj_off=new(src)
inj_off.injector=o2_injector_tag
inj_off.state=0
var/datum/automation/if_statement/i = new (src)
i.label = "Oxygen Injection"
i.condition = MakeCompare(
MakeGetSensorData(sensor_tag,"oxygen"),
MakeNumber(20),
"Less Than or Equal to"
)
i.children_then.Add(inj_on)
i.children_else.Add(inj_off)
automations += i
/obj/machinery/computer/general_air_control/atmos_automation/air_mixing/proc/buildN2()
///////////////////////////////////////////////////////////////
// Nitrogen Injection
///////////////////////////////////////////////////////////////
/*
if(get_sensor_data("pressure") < 100)
injector_on()
else
if(get_sensor_data("pressure") > 5000)
injector_off()
*/
var/datum/automation/set_injector_power/inj_on=new(src)
inj_on.injector=n2_injector_tag
inj_on.state=1
var/datum/automation/set_injector_power/inj_off=new(src)
inj_off.injector=n2_injector_tag
inj_off.state=0
var/datum/automation/if_statement/if_on = new (src)
if_on.label = "Nitrogen Injection"
if_on.condition = MakeCompare(
MakeGetSensorData(sensor_tag,"pressure"),
MakeNumber(100),
"Less Than"
)
if_on.children_then.Add(inj_on)
var/datum/automation/if_statement/if_off=new(src)
if_off.condition=MakeCompare(
MakeGetSensorData(sensor_tag,"pressure"),
MakeNumber(5000),
"Greater Than"
)
if_off.children_then.Add(inj_off)
if_on.children_else.Add(if_off)
automations += if_on
/obj/machinery/computer/general_air_control/atmos_automation/air_mixing/proc/buildOutletVent()
///////////////////////////////////////////////////////////////
// Outlet Management
///////////////////////////////////////////////////////////////
/*
if(get_sensor_data("pressure") >= 5000 && get_sensor_data("oxygen") >= 20)
vent_on()
else
if(get_sensor_data("oxygen") < 20 || get_sensor_data("pressure") < 100)
vent_off()
*/
var/datum/automation/set_vent_pump_power/vp_on=new(src)
vp_on.vent_pump=output_tag
vp_on.state=1
var/datum/automation/set_vent_pump_power/vp_off=new(src)
vp_off.vent_pump=output_tag
vp_off.state=0
var/datum/automation/if_statement/if_on=new(src)
if_on.label="Air Output"
var/datum/automation/and/and_on=new(src)
and_on.children.Add(
MakeCompare(
MakeGetSensorData(sensor_tag,"pressure"),
MakeNumber(5000),
"Greater Than or Equal to"
)
)
and_on.children.Add(
MakeCompare(
MakeGetSensorData(sensor_tag,"oxygen"),
MakeNumber(20),
"Greater Than or Equal to"
)
)
if_on.condition=and_on
if_on.children_then.Add(vp_on)
//////////////////////////////
var/datum/automation/if_statement/if_off=new(src)
var/datum/automation/or/or_off=new(src)
or_off.children.Add(
MakeCompare(
MakeGetSensorData(sensor_tag,"pressure"),
MakeNumber(100),
"Less Than"
)
)
or_off.children.Add(
MakeCompare(
MakeGetSensorData(sensor_tag,"oxygen"),
MakeNumber(20),
"Less Than"
)
)
if_off.condition=or_off
if_off.children_then.Add(vp_off)
if_on.children_else.Add(if_off)
automations += if_on
@@ -1,44 +0,0 @@
/datum/automation/set_valve_state
name = "Digital Valve: Set Open/Closed"
var/valve=null
var/state=0
Export()
var/list/json = ..()
json["valve"]=valve
json["state"]=state
return json
Import(var/list/json)
..(json)
valve = json["valve"]
state = text2num(json["state"])
process()
if(valve)
parent.send_signal(list ("tag" = valve, "command"="valve_set","valve_set"=state))
return 0
GetText()
return "Set digital valve <a href=\"?src=[UID()];set_subject=1\">[fmtString(valve)]</a> to <a href=\"?src=[UID()];set_state=1\">[state?"open":"closed"]</a>."
Topic(href,href_list)
if(..())
return 1
if(href_list["set_state"])
state=!state
parent.updateUsrDialog()
return 1
if(href_list["set_subject"])
var/list/valves=list()
for(var/obj/machinery/atmospherics/binary/valve/digital/V in world)
if(!isnull(V.id_tag) && V.frequency == parent.frequency)
valves|=V.id_tag
if(valves.len==0)
to_chat(usr, "<span class='warning'>Unable to find any digital valves on this frequency.</span>")
return
valve = input("Select a valve:", "Sensor Data", valve) as null|anything in valves
parent.updateUsrDialog()
return 1
@@ -1,42 +0,0 @@
/datum/automation/set_emitter_power
name = "Emitter: Set Power"
var/emitter=null
var/on=0
Export()
var/list/json = ..()
json["emitter"]=emitter
json["on"]=on
return json
Import(var/list/json)
..(json)
emitter = json["emitter"]
on = text2num(json["on"])
process()
if(emitter)
parent.send_signal(list("tag" = emitter, "command"="set", "state" = on, "hiddenprints" = parent.fingerprintshidden))
return 0
GetText()
return "Set emitter <a href=\"?src=[UID()];set_subject=1\">[fmtString(emitter)]</a> to <a href=\"?src=[UID()];set_power=1\">[on?"on":"off"]</a>."
Topic(href,href_list)
if(..())
return 1
if(href_list["set_power"])
on=!on
parent.updateUsrDialog()
return 1
if(href_list["set_subject"])
var/list/emitters=list()
for(var/obj/machinery/power/emitter/E in GLOB.machines)
if(!isnull(E.id_tag) && E.frequency == parent.frequency)
emitters|=E.id_tag
if(emitters.len==0)
to_chat(usr, "<span class='warning'>Unable to find any emitters on this frequency.</span>")
return
emitter = input("Select an emitter:", "Emitter", emitter) as null|anything in emitters
parent.updateUsrDialog()
return 1
@@ -1,83 +0,0 @@
////////////////////////////////////////////
// Injector
////////////////////////////////////////////
/datum/automation/set_injector_power
name = "Injector: Power"
var/injector=null
var/state=0
Export()
var/list/json = ..()
json["injector"]=injector
json["state"]=state
return json
Import(var/list/json)
..(json)
injector = json["injector"]
state = text2num(json["state"])
process()
if(injector)
parent.send_signal(list ("tag" = injector, "power"=state))
return 0
GetText()
return "Set injector <a href=\"?src=[UID()];set_injector=1\">[fmtString(injector)]</a> power to <a href=\"?src=[UID()];toggle_state=1\">[state ? "on" : "off"]</a>."
Topic(href,href_list)
if(..())
return 1
if(href_list["toggle_state"])
state = !state
parent.updateUsrDialog()
return 1
if(href_list["set_injector"])
var/list/injector_names=list()
for(var/obj/machinery/atmospherics/unary/outlet_injector/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
injector = input("Select an injector:", "Sensor Data", injector) as null|anything in injector_names
parent.updateUsrDialog()
return 1
/datum/automation/set_injector_rate
name = "Injector: Rate"
var/injector = null
var/rate = 0
Export()
var/list/json = ..()
json["injector"] = injector
json["rate"] = rate
return json
Import(var/list/json)
..(json)
injector = json["injector"]
rate = text2num(json["rate"])
process()
if(injector)
parent.send_signal(list ("tag" = injector, "set_volume_rate"=rate))
return 0
GetText()
return "Set injector <a href=\"?src=[UID()];set_injector=1\">[fmtString(injector)]</a> transfer rate to <a href=\"?src=[UID()];set_rate=1\">[rate]</a> L/s."
Topic(href,href_list)
if(..())
return 1
if(href_list["set_rate"])
rate = input("Set rate in L/s.", "Rate", rate) as num
parent.updateUsrDialog()
return 1
if(href_list["set_injector"])
var/list/injector_names=list()
for(var/obj/machinery/atmospherics/unary/outlet_injector/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
injector = input("Select an injector:", "Sensor Data", injector) as null|anything in injector_names
parent.updateUsrDialog()
return 1
@@ -1,153 +0,0 @@
/datum/automation/set_scrubber_mode
name="Scrubber: Mode"
var/scrubber=null
var/mode=1
Export()
var/list/json = ..()
json["scrubber"]=scrubber
json["mode"]=mode
return json
Import(var/list/json)
..(json)
scrubber = json["scrubber"]
mode = text2num(json["mode"])
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
children=list(null)
process()
if(scrubber)
parent.send_signal(list ("tag" = scrubber, "sigtype"="command", "scrubbing"=mode),filter = RADIO_FROM_AIRALARM)
return 0
GetText()
return "Set Scrubber <a href=\"?src=[UID()];set_scrubber=1\">[fmtString(scrubber)]</a> mode to <a href=\"?src=[UID()];set_mode=1\">[mode?"Scrubbing":"Syphoning"]</a>."
Topic(href,href_list)
if(..()) return
if(href_list["set_mode"])
mode=!mode
parent.updateUsrDialog()
return 1
if(href_list["set_scrubber"])
var/list/injector_names=list()
for(var/obj/machinery/atmospherics/unary/vent_scrubber/S in GLOB.machines)
if(!isnull(S.id_tag) && S.frequency == parent.frequency)
injector_names|=S.id_tag
scrubber = input("Select a scrubber:", "Scrubbers", scrubber) as null|anything in injector_names
parent.updateUsrDialog()
return 1
/datum/automation/set_scrubber_power
name="Scrubber: Power"
var/scrubber=null
var/state=0
Export()
var/list/json = ..()
json["scrubber"]=scrubber
json["state"]=state
return json
Import(var/list/json)
..(json)
scrubber = json["scrubber"]
state = text2num(json["state"])
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
process()
if(scrubber)
parent.send_signal(list ("tag" = scrubber, "sigtype"="command", "power"=state),filter = RADIO_FROM_AIRALARM)
GetText()
return "Set Scrubber <a href=\"?src=[UID()];set_scrubber=1\">[fmtString(scrubber)]</a> power to <a href=\"?src=[UID()];set_power=1\">[state ? "on" : "off"]</a>."
Topic(href,href_list)
if(..()) return
if(href_list["set_power"])
state = !state
parent.updateUsrDialog()
return 1
if(href_list["set_scrubber"])
var/list/injector_names=list()
for(var/obj/machinery/atmospherics/unary/vent_scrubber/S in GLOB.machines)
if(!isnull(S.id_tag) && S.frequency == parent.frequency)
injector_names|=S.id_tag
scrubber = input("Select a scrubber:", "Scrubbers", scrubber) as null|anything in injector_names
parent.updateUsrDialog()
return 1
GLOBAL_LIST_INIT(gas_labels, list(
"co2" = "CO<sub>2</sub>",
"tox" = "Plasma",
"n2o" = "N<sub>2</sub>O",
"o2" = "O<sub>2</sub>",
"n2" = "N<sub>2</sub>"
))
/datum/automation/set_scrubber_gasses
name="Scrubber: Gasses"
var/scrubber=null
var/list/gasses=list(
"co2" = 1,
"tox" = 0,
"n2o" = 0,
"o2" = 0,
"n2" = 0
)
Export()
var/list/json = ..()
json["scrubber"]=scrubber
json["gasses"]=gasses
return json
Import(var/list/json)
..(json)
scrubber = json["scrubber"]
var/list/newgasses=json["gasses"]
for(var/key in newgasses)
gasses[key]=newgasses[key]
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
process()
if(scrubber)
var/list/data = list ("tag" = scrubber, "sigtype"="command")
for(var/gas in gasses)
data[gas+"_scrub"]=gasses[gas]
parent.send_signal(data,filter = RADIO_FROM_AIRALARM)
GetText()
var/txt = "Set Scrubber <a href=\"?src=[UID()];set_scrubber=1\">[fmtString(scrubber)]</a> to scrub "
for(var/gas in gasses)
txt += " [GLOB.gas_labels[gas]] (<a href=\"?src=[UID()];tog_gas=[gas]\">[gasses[gas] ? "on" : "off"]</a>),"
return txt
Topic(href,href_list)
if(..()) return
if(href_list["tog_gas"])
var/gas = href_list["tog_gas"]
if(!(gas in gasses))
return
gasses[gas] = !gasses[gas]
parent.updateUsrDialog()
return 1
if(href_list["set_scrubber"])
var/list/injector_names=list()
for(var/obj/machinery/atmospherics/unary/vent_scrubber/S in GLOB.machines)
if(!isnull(S.id_tag) && S.frequency == parent.frequency)
injector_names|=S.id_tag
scrubber = input("Select a scrubber:", "Scrubbers", scrubber) as null|anything in injector_names
parent.updateUsrDialog()
return 1
@@ -1,56 +0,0 @@
///////////////////////////////////////////
// sensor data
///////////////////////////////////////////
/datum/automation/get_sensor_data
name = "Sensor: Get Data"
var/field="temperature"
var/sensor=null
returntype=AUTOM_RT_NUM
Export()
var/list/json = ..()
json["sensor"]=sensor
json["field"]=field
return json
Import(var/list/json)
..(json)
sensor = json["sensor"]
field = json["field"]
Evaluate()
if(sensor && field && (sensor in parent.sensor_information))
return parent.sensor_information[sensor][field]
return 0
GetText()
return "<a href=\"?src=[UID()];set_field=1\">[fmtString(field)]</a> from sensor <a href=\"?src=[UID()];set_sensor=1\">[fmtString(sensor)]</a>"
Topic(href,href_list)
if(..())
return 1
if(href_list["set_field"])
field = input("Select a sensor output:", "Sensor Data", field) as null|anything in list(
"temperature",
"pressure",
"oxygen",
"toxins",
"nitrogen",
"carbon_dioxide"
)
parent.updateUsrDialog()
return 1
if(href_list["set_sensor"])
var/list/sensor_list = list()
for(var/obj/machinery/air_sensor/G in GLOB.machines)
if(!isnull(G.id_tag) && G.frequency == parent.frequency)
sensor_list|=G.id_tag
for(var/obj/machinery/meter/M in GLOB.machines)
if(!isnull(M.id_tag) && M.frequency == parent.frequency)
sensor_list|=M.id_tag
sensor = input("Select a sensor:", "Sensor Data", field) as null|anything in sensor_list
parent.updateUsrDialog()
return 1
@@ -1,314 +0,0 @@
/datum/automation/set_vent_pump_mode
name="Vent Pump: Mode"
var/vent_pump = null
var/mode = "stabilize"
var/vent_type = 0//0 for unary vents, 1 for DP vents
var/list/modes = list("stabilize","purge")
Export()
var/list/json = ..()
json["vent_pump"] = vent_pump
json["mode"] = mode
json["vent_type"] = vent_type
return json
Import(var/list/json)
..(json)
vent_pump = json["vent_pump"]
mode = json["mode"]
vent_type = text2num(json["vent_type"])
process()
if(vent_pump)
var/dirvalue = (mode == "stabilize" ? 1 : mode == "purge" ? 0 : 1)
parent.send_signal(list("tag" = vent_pump, "direction" = dirvalue), filter = (vent_type ? RADIO_ATMOSIA : RADIO_FROM_AIRALARM))
return 0
GetText()
return "Set <a href=\"?src=[UID()];toggle_type=1\">[vent_type ? "Dual-Port" : "Unary"]</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a> mode to <a href=\"?src=[UID()];set_mode=1\">[mode]</a>."
Topic(href,href_list)
if(..())
return 1
if(href_list["set_mode"])
mode = input("Select a mode to put this pump into.",mode) in modes
parent.updateUsrDialog()
return 1
if(href_list["set_vent_pump"])
var/list/injector_names = list()
if(!vent_type)
for(var/obj/machinery/atmospherics/unary/vent_pump/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names |= I.id_tag
else
for(var/obj/machinery/atmospherics/binary/dp_vent_pump/I in world)
// to_chat(world, "test")
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names |= I.id_tag
vent_pump = input("Select a vent:", "Vent Pumps", vent_pump) as null|anything in injector_names
parent.updateUsrDialog()
return 1
if(href_list["toggle_type"])
vent_type = !vent_type
parent.updateUsrDialog()
return 1
/datum/automation/set_vent_pump_power
name="Vent Pump: Power"
var/vent_pump = null
var/state = 0
var/mode = 0//0 for unary vents, 1 for DP vents.
Export()
var/list/json = ..()
json["vent_pump"] = vent_pump
json["state"] = state
json["mode"] = mode
return json
Import(var/list/json)
..(json)
vent_pump = json["vent_pump"]
state = text2num(json["state"])
mode = text2num(json["mode"])
process()
if(vent_pump)
parent.send_signal(list ("tag" = vent_pump, "power" = state), filter = (mode ? RADIO_ATMOSIA : RADIO_FROM_AIRALARM))
GetText()
return "Set <a href=\"?src=[UID()];toggle_mode=1\">[mode ? "Dual-Port" : "Unary"]</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a> power to <a href=\"?src=[UID()];set_power=1\">[state ? "on" : "off"]</a>."
Topic(href,href_list)
if(..())
return 1
if(href_list["set_power"])
state = !state
parent.updateUsrDialog()
return 1
if(href_list["set_vent_pump"])
var/list/injector_names=list()
if(!mode)
for(var/obj/machinery/atmospherics/unary/vent_pump/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
else
for(var/obj/machinery/atmospherics/binary/dp_vent_pump/I in world)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
vent_pump = input("Select a vent:", "Vent Pumps", vent_pump) as null|anything in injector_names
parent.updateUsrDialog()
return 1
if(href_list["toggle_mode"])
mode = !mode
parent.updateUsrDialog()
return 1
/datum/automation/set_vent_pump_pressure//controls the internal/external pressure bounds of a vent pump.
name = "Vent Pump: Pressure Settings"
var/vent_pump = null
var/intpressureout = 0//these 2 are for DP vents, if it's a unary vent you're sending to it will take intpressureout as var
var/intpressurein = 0
var/extpressure = 0
var/mode = 0//0 for unary vents, 1 for DP vents.
Export()
var/list/json = ..()
json["vent_pump"] = vent_pump
json["intpressureout"] = intpressureout
json["intpressurein"] = intpressurein
json["extpressure"] = extpressure
json["mode"] = mode
return json
Import(var/list/json)
..(json)
vent_pump = json["vent_pump"]
intpressureout = text2num(json["intpressureout"])
intpressurein = text2num(json["intpressurein"])
extpressure = text2num(json["extpressure"])
mode = text2num(json["mode"])
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
process()
if(vent_pump)
var/list/data = list( \
"tag" = vent_pump, \
)
var/filter = RADIO_ATMOSIA
if(mode)//it's a DP vent
if(intpressurein)
data.Add(list("set_input_pressure" = intpressurein))
if(intpressureout)
data.Add(list("set_output_pressure" = intpressureout))
if(extpressure)
data.Add(list("set_external_pressure" = extpressure))
else
if(intpressureout)
data.Add(list("set_internal_pressure" = intpressureout))
if(extpressure)
data.Add(list("set_external_pressure" = extpressure))
filter = RADIO_FROM_AIRALARM
parent.send_signal(data, filter)
GetText()
if(mode)//DP vent
return {"Set <a href=\"?src=[UID()];swap_modes=1\">dual-port</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a>
pressure bounds: internal outwards: <a href=\"?src=[UID()];set_intpressure_out=1">[fmtString(intpressureout)]</a>
internal inwards: <a href=\"?src=[UID()];set_intpressure_in=1">[fmtString(intpressurein)]</a>
external: <a href=\"?src=[UID()];set_external=1">[fmtString(extpressure)]</a>
"}//well that was a lot to type
else
return {"Set <a href=\"?src=[UID()];swap_modes=1\">unary</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a>
pressure bounds: internal: <a href=\"?src=[UID()];set_intpressure_out=1">[fmtString(intpressureout)]</a>
external: <a href=\"?src=[UID()];set_external=1">[fmtString(extpressure)]</a>
"}//copy paste FTW
Topic(href, href_list)
if(..())
return 1
if(href_list["set_vent_pump"])
var/list/injector_names=list()
if(mode)//DP vent selection
for(var/obj/machinery/atmospherics/binary/dp_vent_pump/I in world)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
else
for(var/obj/machinery/atmospherics/unary/vent_pump/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
vent_pump = input("Select a vent:", "Vent Pumps", vent_pump) as null|anything in injector_names
parent.updateUsrDialog()
return 1
if(href_list["set_intpressure_out"])
var/response = input("Set new pressure, in kPa. \[0-[50*ONE_ATMOSPHERE]\]") as num
intpressureout = text2num(response)
intpressureout = between(0, intpressureout, 50*ONE_ATMOSPHERE)
parent.updateUsrDialog()
return 1
if(href_list["set_intpressure_in"])
var/response = input("Set new pressure, in kPa. \[0-[50*ONE_ATMOSPHERE]\]") as num
intpressurein = text2num(response)
intpressurein = between(0, intpressurein, 50*ONE_ATMOSPHERE)
parent.updateUsrDialog()
return 1
if(href_list["set_external"])
var/response = input(usr,"Set new pressure, in kPa. \[0-[50*ONE_ATMOSPHERE]\]") as num
extpressure = text2num(response)
extpressure = between(0, extpressure, 50*ONE_ATMOSPHERE)
parent.updateUsrDialog()
return 1
if(href_list["swap_modes"])
mode = !mode
vent_pump = null//if we don't clear this is could get glitchy, by which I mean not at all, whatever, stay clean
parent.updateUsrDialog()
return 1
/datum/automation/set_vent_pressure_checks
name = "Vent Pump: Pressure Checks"
var/vent_pump = null
var/checks = 1
var/mode = 0//1 for DP vent, 0 for unary vent
/*
checks bitflags
1 = external
2 = internal in (regular internal for unaries)
4 = internal out (ignored by unaries)
*/
Export()
var/list/json = ..()
json["vent_pump"] = vent_pump
json["checks"] = checks
json["mode"] = mode
return json
Import(var/list/json)
..(json)
vent_pump = json["vent_pump"]
checks = text2num(json["checks"])
mode = text2num(json["mode"])
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
process()
if(vent_pump)
parent.send_signal(list("tag" = vent_pump, "checks" = checks), filter = (mode ? RADIO_ATMOSIA : RADIO_FROM_AIRALARM))//not gonna bother with a sanity check here, there *should* not be any problems
GetText()
if(mode)
return {"Set <a href=\"?src=[UID()];swap_modes=1\">dual-port</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a> pressure checks to:
external <a href=\"?src=[UID()];togglecheck=1\">[checks&1 ? "Enabled" : "Disabled"]</a>
internal inwards <a href=\"?src=[UID()];togglecheck=2\">[checks&2 ? "Enabled" : "Disabled"]</a>
internal outwards <a href=\"?src=[UID()];togglecheck=4\">[checks&4 ? "Enabled" : "Disabled"]</a>
"}
else
return {"Set <a href=\"?src=[UID()];swap_modes=1\">unary</a> vent pump <a href=\"?src=[UID()];set_vent_pump=1\">[fmtString(vent_pump)]</a> pressure checks to:
external: <a href=\"?src=[UID()];togglecheck=1\">[checks&1 ? "Enabled" : "Disabled"]</a>,
internal: <a href=\"?src=[UID()];togglecheck=2\">[checks&2 ? "Enabled" : "Disabled"]</a>
"}
Topic(href, href_list)
if(..())
return 1
if(href_list["set_vent_pump"])
var/list/injector_names=list()
if(mode)//DP vent selection
for(var/obj/machinery/atmospherics/binary/dp_vent_pump/I in world)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
else
for(var/obj/machinery/atmospherics/unary/vent_pump/I in GLOB.machines)
if(!isnull(I.id_tag) && I.frequency == parent.frequency)
injector_names|=I.id_tag
vent_pump = input("Select a vent:", "Vent Pumps", vent_pump) as null|anything in injector_names
parent.updateUsrDialog()
return 1
if(href_list["swap_modes"])
mode = !mode
vent_pump = null//if we don't clear this is could get glitchy, by which I mean not at all, whatever, stay clean
if(!mode && checks&4)//disable this bitflag since we're switching to unaries
checks &= ~4
parent.updateUsrDialog()
return 1
if(href_list["togglecheck"])
var/bitflagvalue = text2num(href_list["togglecheck"])
if(mode)
if(!(bitflagvalue in list(1, 2, 4)))
return 0
else if(!(bitflagvalue in list(1, 2)))
return 0
if(checks&bitflagvalue)//the bitflag is on ATM
checks &= ~bitflagvalue
else//can't not be off
checks |= bitflagvalue
parent.updateUsrDialog()
return 1
-457
View File
@@ -1,457 +0,0 @@
GLOBAL_LIST_INIT(automation_types, subtypesof(/datum/automation))
#define AUTOM_RT_NULL 0
#define AUTOM_RT_NUM 1
#define AUTOM_RT_STRING 2
/datum/automation
// Name of the Automation
var/name="Base Automation"
// For labelling what shit does on the AAC.
var/label="Unnamed Script"
var/desc ="No Description."
var/obj/machinery/computer/general_air_control/atmos_automation/parent
var/list/valid_child_returntypes=list()
var/list/datum/automation/children=list()
var/returntype=AUTOM_RT_NULL
/datum/automation/New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
parent=aa
/datum/automation/proc/GetText()
return "[type] doesn't override GetText()!"
/datum/automation/proc/OnReset()
return
/datum/automation/proc/OnRemove()
return
/datum/automation/process()
return
/datum/automation/proc/Evaluate()
return 0
/datum/automation/proc/Export()
var/list/R = list("type"=type)
if(initial(label)!=label)
R["label"]=label
if(initial(desc)!=desc)
R["desc"]=desc
if(children.len>0)
var/list/C=list()
for(var/datum/automation/A in children)
C += list(A.Export())
R["children"]=C
return R
/datum/automation/proc/unpackChild(var/list/cData)
if(isnull(cData) || !("type" in cData))
return null
var/Atype=text2path(cData["type"])
if(!(Atype in GLOB.automation_types))
return null
var/datum/automation/A = new Atype(parent)
A.Import(cData)
return A
/datum/automation/proc/unpackChildren(var/list/childList)
. = list()
if(childList.len>0)
for(var/list/cData in childList)
if(isnull(cData) || !("type" in cData))
. += null
continue
var/Atype=text2path(cData["type"])
if(!(Atype in GLOB.automation_types))
continue
var/datum/automation/A = new Atype(parent)
A.Import(cData)
. += A
/datum/automation/proc/packChildren(var/list/childList)
. = list()
if(childList.len>0)
for(var/datum/automation/A in childList)
if(isnull(A) || !istype(A))
. += null
continue
. += list(A.Export())
/datum/automation/proc/Import(var/list/json)
if("label" in json)
label = json["label"]
if("desc" in json)
desc = json["desc"]
if("children" in json)
children = unpackChildren(json["children"])
/datum/automation/proc/fmtString(var/str)
if(str==null || str == "")
return "-----"
return str
/datum/automation/Topic(href,href_list)
if(parent.Topic("src=[parent.UID()]", list("src" = parent)))//dumb hack to check sanity, empty topic shouldn't trigger a 1 on anything but sanity checks
return 1
if(href_list["add"])
var/new_child=selectValidChildFor(usr)
if(!new_child) return 1
children += new_child
parent.updateUsrDialog()
return 1
if(href_list["remove"])
if(href_list["remove"]=="*")
var/confirm=alert("Are you sure you want to remove ALL automations?","Automations","Yes","No")
if(confirm == "No") return 0
for(var/datum/automation/A in children)
A.OnRemove()
children.Remove(A)
else
var/datum/automation/A=locate(href_list["remove"])
if(!A) return 1
var/confirm=alert("Are you sure you want to remove this automation?","Automations","Yes","No")
if(confirm == "No") return 0
A.OnRemove()
children.Remove(A)
parent.updateUsrDialog()
return 1
if(href_list["reset"])
if(href_list["reset"]=="*")
for(var/datum/automation/A in children)
A.OnReset()
else
var/datum/automation/A=locate(href_list["reset"])
if(!A) return 1
A.OnReset()
parent.updateUsrDialog()
return 1
return 0 // 1 if handled
/datum/automation/proc/selectValidChildFor(var/mob/user, var/list/returntypes=valid_child_returntypes)
return parent.selectValidChildFor(src, user, returntypes)
///////////////////////////////////////////
// AND
///////////////////////////////////////////
/datum/automation/and
name = "AND statement"
returntype=AUTOM_RT_NUM
valid_child_returntypes=list(AUTOM_RT_NUM)
Evaluate()
if(children.len==0) return 0
for(var/datum/automation/stmt in children)
if(!stmt.Evaluate())
return 0
return 1
GetText()
var/out="AND (<a href=\"?src=[UID()];add=1\">Add</a>)"
if(children.len>0)
out += "<ul>"
for(var/datum/automation/stmt in children)
out += {"<li>
\[<a href="?src=[UID()];reset=\ref[stmt]">Reset</a> |
<a href="?src=[UID()];remove=\ref[stmt]">&times;</a>\]
[stmt.GetText()]
</li>"}
out += "</ul>"
else
out += "<blockquote><i>No statements to evaluate.</i></blockquote>"
return out
///////////////////////////////////////////
// OR
///////////////////////////////////////////
/datum/automation/or
name = "OR statement"
returntype=AUTOM_RT_NUM
valid_child_returntypes=list(AUTOM_RT_NUM)
Evaluate()
if(children.len==0) return 0
for(var/datum/automation/stmt in children)
if(stmt.Evaluate())
return 1
return 0
GetText()
var/out="OR (<a href=\"?src=[UID()];add=1\">Add</a>)"
if(children.len>0)
out += "<ul>"
for(var/datum/automation/stmt in children)
out += {"<li>
\[<a href="?src=[UID()];reset=\ref[stmt]">Reset</a> |
<a href="?src=[UID()];remove=\ref[stmt]">&times;</a>\]
[stmt.GetText()]
</li>"}
out += "</ul>"
else
out += "<blockquote><i>No statements to evaluate.</i></blockquote>"
return out
///////////////////////////////////////////
// if .. then
///////////////////////////////////////////
/datum/automation/if_statement
name = "IF statement"
var/datum/automation/condition=null
valid_child_returntypes=list(AUTOM_RT_NULL)
var/list/valid_conditions=list(AUTOM_RT_NUM)
var/list/children_then=list()
var/list/children_else=list()
Export()
var/list/R = ..()
if(children_then.len>0)
R["then"]=packChildren(children_then)
if(children_else.len>0)
R["else"]=packChildren(children_else)
if(condition)
R["condition"]=condition.Export()
return R
Import(var/list/json)
..(json)
if("then" in json)
children_then = unpackChildren(json["then"])
if("else" in json)
children_else = unpackChildren(json["else"])
if("condition" in json)
condition = unpackChild(json["condition"])
GetText()
var/out="<b>IF</b> (<a href=\"?src=[UID()];set_condition=1\">SET</a>):<blockquote>"
if(condition)
out += condition.GetText()
else
out += "<i>Not set</i>"
out += "</blockquote>"
out += "<b>THEN:</b> (<a href=\"?src=[UID()];add=then\">Add</a>)"
if(children_then.len>0)
out += "<ul>"
for(var/datum/automation/stmt in children_then)
out += {"<li>
\[<a href="?src=[UID()];reset=\ref[stmt];context=then">Reset</a> |
<a href="?src=[UID()];remove=\ref[stmt];context=then">&times;</a>\]
[stmt.GetText()]
</li>"}
out += "</ul>"
else
out += "<blockquote><i>(No statements to run)</i></blockquote>"
out += "<b>ELSE:</b> (<a href=\"?src=[UID()];add=else\">Add</a>)"
if(children_then.len>0)
out += "<ul>"
for(var/datum/automation/stmt in children_else)
out += {"<li>
\[<a href="?src=[UID()];reset=\ref[stmt];context=else">Reset</a> |
<a href="?src=[UID()];remove=\ref[stmt];context=else">&times;</a>\]
[stmt.GetText()]
</li>"}
out += "</ul>"
else
out += "<blockquote><i>(No statements to run)</i></blockquote>"
return out
Topic(href,href_list)
if(href_list["add"])
var/new_child=selectValidChildFor(usr)
if(!new_child) return 1
switch(href_list["add"])
if("then")
children_then += new_child
if("else")
children_else += new_child
else
warning("Unknown add value given to [type]/Topic():[__LINE__]: [href]")
return 1
parent.updateUsrDialog()
return 1
if(href_list["remove"])
if(href_list["remove"]=="*")
var/confirm=input("Are you sure you want to remove ALL automations?","Automations","No") in list("Yes","No")
if(confirm == "No") return 0
for(var/datum/automation/A in children_then)
A.OnRemove()
children_then.Remove(A)
for(var/datum/automation/A in children_else)
A.OnRemove()
children_else.Remove(A)
else
var/datum/automation/A=locate(href_list["remove"])
if(!A) return 1
var/confirm=input("Are you sure you want to remove this automation?","Automations","No") in list("Yes","No")
if(confirm == "No") return 0
A.OnRemove()
switch(href_list["context"])
if("then")
children_then.Remove(A)
if("else")
children_else.Remove(A)
parent.updateUsrDialog()
return 1
if(href_list["reset"])
if(href_list["reset"]=="*")
for(var/datum/automation/A in children_then)
A.OnReset()
for(var/datum/automation/A in children_else)
A.OnReset()
else
var/datum/automation/A=locate(href_list["reset"])
if(!A) return 1
A.OnReset()
parent.updateUsrDialog()
return 1
if(href_list["set_condition"])
var/new_condition = selectValidChildFor(usr,valid_conditions)
testing("Selected condition: [new_condition]")
if(!new_condition)
return 1
condition = new_condition
parent.updateUsrDialog()
return 1
process()
if(condition)
if(condition.Evaluate())
for(var/datum/automation/stmt in children_then)
stmt.process()
else
for(var/datum/automation/stmt in children_else)
stmt.process()
///////////////////////////////////////////
// compare
///////////////////////////////////////////
/datum/automation/compare
name = "comparison"
var/comparator="Greater Than"
returntype=AUTOM_RT_NUM
valid_child_returntypes=list(AUTOM_RT_NUM)
New(var/obj/machinery/computer/general_air_control/atmos_automation/aa)
..(aa)
children=list(null,null)
Export()
var/list/json = ..()
json["cmp"]=comparator
return json
Import(var/list/json)
..(json)
comparator = json["cmp"]
Evaluate()
if(children.len<2)
return 0
var/datum/automation/d_left =children[1]
var/datum/automation/d_right=children[2]
if(!d_left || !d_right)
return 0
var/left=d_left.Evaluate()
var/right=d_right.Evaluate()
switch(comparator)
if("Greater Than")
return left>right
if("Greater Than or Equal to")
return left>=right
if("Less Than")
return left<right
if("Less Than or Equal to")
return left<=right
if("Equal to")
return left==right
if("NOT Equal To")
return left!=right
else
return 0
GetText()
var/datum/automation/left =children[1]
var/datum/automation/right=children[2]
var/out = "<a href=\"?src=[UID()];set_field=1\">(Set Left)</a> ("
if(left==null)
out += "-----"
else
out += left.GetText()
out += ") is <a href=\"?src=[UID()];set_comparator=left\">[comparator]</a>: <a href=\"?src=[UID()];set_field=2\">(Set Right)</a> ("
if(right==null)
out += "-----"
else
out += right.GetText()
out +=")"
return out
Topic(href,href_list)
if(href_list["set_comparator"])
comparator = input("Select a comparison operator:", "Compare", "Greater Than") in list("Greater Than","Greater Than or Equal to","Less Than","Less Than or Equal to","Equal to","NOT Equal To")
parent.updateUsrDialog()
return 1
if(href_list["set_field"])
var/idx = text2num(href_list["set_field"])
var/new_child = selectValidChildFor(usr)
if(!new_child)
return 1
children[idx] = new_child
parent.updateUsrDialog()
return 1
///////////////////////////////////////////
// static value
///////////////////////////////////////////
/datum/automation/static_value
name = "Number"
var/value=0
returntype=AUTOM_RT_NUM
Evaluate()
return value
Export()
var/list/json = ..()
json["value"]=value
return json
Import(var/list/json)
..(json)
value = text2num(json["value"])
GetText()
return "<a href=\"?src=[UID()];set_value=1\">[value]</a>"
Topic(href,href_list)
if(href_list["set_value"])
value = input("Set a value:", "Static Value", value) as num
parent.updateUsrDialog()
return 1
+4 -4
View File
@@ -48,7 +48,7 @@ GLOBAL_DATUM_INIT(the_gateway, /obj/machinery/gateway/centerstation, null)
..()
update_icon()
wait = world.time + config.gateway_delay //+ thirty minutes default
awaygate = locate(/obj/machinery/gateway/centeraway) in world
awaygate = locate(/obj/machinery/gateway/centeraway) in GLOB.machines
/obj/machinery/gateway/centerstation/update_density_from_dir()
return
@@ -103,7 +103,7 @@ GLOBAL_DATUM_INIT(the_gateway, /obj/machinery/gateway/centerstation, null)
if(!powered())
return
if(!awaygate)
awaygate = locate(/obj/machinery/gateway/centeraway) in world
awaygate = locate(/obj/machinery/gateway/centeraway) in GLOB.machines
if(!awaygate)
to_chat(user, "<span class='notice'>Error: No destination found.</span>")
return
@@ -180,7 +180,7 @@ GLOBAL_DATUM_INIT(the_gateway, /obj/machinery/gateway/centerstation, null)
/obj/machinery/gateway/centeraway/Initialize()
..()
update_icon()
stationgate = locate(/obj/machinery/gateway/centerstation) in world
stationgate = locate(/obj/machinery/gateway/centerstation) in GLOB.machines
/obj/machinery/gateway/centeraway/update_density_from_dir()
@@ -219,7 +219,7 @@ GLOBAL_DATUM_INIT(the_gateway, /obj/machinery/gateway/centerstation, null)
if(linked.len != 8)
return
if(!stationgate)
stationgate = locate(/obj/machinery/gateway/centerstation) in world
stationgate = locate(/obj/machinery/gateway/centerstation) in GLOB.machines
if(!stationgate)
to_chat(user, "<span class='notice'>Error: No destination found.</span>")
return
@@ -191,26 +191,27 @@
origin_tech = null
selfcharge = 1
can_charge = 0
var/inawaymission = 1
// Selfcharge is enabled and disabled, and used as the away mission tracker
selfcharge = TRUE
/obj/item/gun/energy/laser/awaymission_aeg/process()
var/turf/my_loc = get_turf(src)
if(is_away_level(my_loc.z))
if(inawaymission)
return ..()
/obj/item/gun/energy/laser/awaymission_aeg/Initialize(mapload)
. = ..()
// Force update it incase it spawns outside an away mission and shouldnt be charged
onTransitZ(new_z = loc.z)
/obj/item/gun/energy/laser/awaymission_aeg/onTransitZ(old_z, new_z)
if(is_away_level(new_z))
if(ismob(loc))
to_chat(loc, "<span class='notice'>Your [src] activates, starting to draw power from a nearby wireless power source.</span>")
inawaymission = 1
selfcharge = TRUE
else
if(inawaymission)
if(selfcharge)
if(ismob(loc))
to_chat(loc, "<span class='danger'>Your [src] deactivates, as it is out of range from its power source.</span>")
cell.charge = 0
inawaymission = 0
selfcharge = FALSE
update_icon()
/obj/item/reagent_containers/glass/beaker/terror_black_toxin
name = "beaker 'Black Terror Venom'"
@@ -117,10 +117,8 @@
if("Peace")
to_chat(user, "<B>Whatever alien sentience that the Wish Granter possesses is satisfied with your wish. There is a distant wailing as the last of the Faithless begin to die, then silence.</B>")
to_chat(user, "You feel as if you just narrowly avoided a terrible fate...")
for(var/mob/living/simple_animal/hostile/faithless/F in world)
F.health = -10
F.stat = 2
F.icon_state = "faithless_dead"
for(var/mob/living/simple_animal/hostile/faithless/F in GLOB.mob_living_list)
F.death()
///////////////Meatgrinder//////////////
@@ -220,7 +218,8 @@
to_chat(user, "<span class='warning'>The communicator buzzes, and you hear the voice again: 'Really? I think not. Get them!'</span>")
if(option_threat)
to_chat(user, "<span class='warning'>The communicator buzzes, and you hear the voice again: 'Oh really now?' You hear a clicking sound. 'Team, get back here. We have trouble'. Then the line goes dead.</span>")
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name == "wildwest_syndipod")
var/obj/spacepod/syndi/P = new /obj/spacepod/syndi(get_turf(L))
P.name = "Syndi Recon Pod"
+4 -2
View File
@@ -56,7 +56,8 @@ GLOBAL_LIST_INIT(potentialRandomZlevels, generateMapList(filename = "config/away
GLOB.space_manager.remove_dirt(zlev)
log_world(" Away mission loaded: [map]")
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name != "awaystart")
continue
GLOB.awaydestinations.Add(L)
@@ -89,7 +90,8 @@ GLOBAL_LIST_INIT(potentialRandomZlevels, generateMapList(filename = "config/away
//map_transition_config.Add(AWAY_MISSION_LIST)
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(L.name != "awaystart")
continue
GLOB.awaydestinations.Add(L)
+1 -1
View File
@@ -28,8 +28,8 @@
return "buildmode_[key]"
/datum/buildmode_mode/proc/show_help(mob/user)
CRASH("No help defined, yell at a coder")
to_chat(user, "<span class='warning'>There is no help defined for this mode, this is a bug.</span>")
CRASH("No help defined, yell at a coder")
/datum/buildmode_mode/proc/change_settings(mob/user)
to_chat(user, "<span class='warning'>There is no configuration available for this mode</span>")
+6 -6
View File
@@ -9,6 +9,7 @@
var/plasma = 0
var/cdiox = 0
var/nitrox = 0
var/agentbx = 0
/datum/buildmode_mode/atmos/show_help(mob/user)
@@ -29,6 +30,7 @@
plasma = input(user, "Plasma ratio", "Input", 0) as num|null
cdiox = input(user, "CO2 ratio", "Input", 0) as num|null
nitrox = input(user, "N2O ratio", "Input", 0) as num|null
agentbx = input(user, "Agent B ratio", "Input", 0) as num|null
/datum/buildmode_mode/atmos/proc/ppratio_to_moles(ppratio)
// ideal gas equation: Pressure * Volume = Moles * r * Temperature
@@ -52,11 +54,8 @@
S.air.nitrogen = ppratio_to_moles(nitrogen)
S.air.toxins = ppratio_to_moles(plasma)
S.air.carbon_dioxide = ppratio_to_moles(cdiox)
S.air.trace_gases.Cut()
if(nitrox)
var/datum/gas/TG = new /datum/gas/sleeping_agent
TG.moles = ppratio_to_moles(nitrox)
S.air.trace_gases += TG
S.air.sleeping_agent = ppratio_to_moles(nitrox)
S.air.agent_b = ppratio_to_moles(agentbx)
S.update_visuals()
S.air_update_turf()
else if(ctrl_click) // overwrite "default" unsimulated air
@@ -65,7 +64,8 @@
T.nitrogen = ppratio_to_moles(nitrogen)
T.toxins = ppratio_to_moles(plasma)
T.carbon_dioxide = ppratio_to_moles(cdiox)
// no interface for trace gases on unsim turfs
T.sleeping_agent = ppratio_to_moles(nitrox)
T.agent_b = ppratio_to_moles(agentbx)
T.air_update_turf()
// admin log
@@ -54,7 +54,6 @@ GLOBAL_LIST_INIT(special_role_times, list( //minimum age (in days) for accounts
return C.player_age
else
return max(0, days - C.player_age)
return 0
#define MAX_SAVE_SLOTS 30 // Save slots for regular players
#define MAX_SAVE_SLOTS_MEMBER 30 // Save slots for BYOND members
@@ -624,6 +623,9 @@ GLOBAL_LIST_INIT(special_role_times, list( //minimum age (in days) for accounts
if(job.admin_only)
continue
if(job.hidden_from_job_prefs)
continue
index += 1
if((index >= limit) || (job.title in splitJobs))
if((index < limit) && (lastJob != null))
+2 -3
View File
@@ -73,16 +73,15 @@ obj/item/clothing/shoes/magboots/syndie/advance //For the Syndicate Strike Team
shoe_sound = "clownstep"
origin_tech = "magnets=4;syndicate=2"
var/enabled_waddle = TRUE
var/datum/component/waddle
/obj/item/clothing/shoes/magboots/clown/equipped(mob/user, slot)
. = ..()
if(slot == slot_shoes && enabled_waddle)
waddle = user.AddComponent(/datum/component/waddling)
user.AddElement(/datum/element/waddling)
/obj/item/clothing/shoes/magboots/clown/dropped(mob/user)
. = ..()
QDEL_NULL(waddle)
user.RemoveElement(/datum/element/waddling)
/obj/item/clothing/shoes/magboots/clown/CtrlClick(mob/living/user)
if(!isliving(user))
+2 -3
View File
@@ -71,16 +71,15 @@
var/footstep = 1 //used for squeeks whilst walking
shoe_sound = "clownstep"
var/enabled_waddle = TRUE
var/datum/component/waddle
/obj/item/clothing/shoes/clown_shoes/equipped(mob/user, slot)
. = ..()
if(slot == slot_shoes && enabled_waddle)
waddle = user.AddComponent(/datum/component/waddling)
user.AddElement(/datum/element/waddling)
/obj/item/clothing/shoes/clown_shoes/dropped(mob/user)
. = ..()
QDEL_NULL(waddle)
user.RemoveElement(/datum/element/waddling)
/obj/item/clothing/shoes/clown_shoes/CtrlClick(mob/living/user)
if(!isliving(user))
+1 -1
View File
@@ -5,7 +5,7 @@
////////////////////////
/proc/get_money_account(var/account_number, var/from_z=-1)
for(var/obj/machinery/computer/account_database/DB in world)
for(var/obj/machinery/computer/account_database/DB in GLOB.machines)
if(from_z > -1 && DB.z != from_z) continue
if((DB.stat & NOPOWER) || !DB.activated ) continue
var/datum/money_account/acct = DB.get_account(account_number)
+1 -1
View File
@@ -17,7 +17,7 @@
playercount = length(GLOB.clients)//grab playercount when event starts not when game starts
if(playercount >= highpop_trigger) //spawn with 4 if highpop
spawncount = 4
for(var/obj/machinery/atmospherics/unary/vent_pump/temp_vent in world)
for(var/obj/machinery/atmospherics/unary/vent_pump/temp_vent in SSair.atmos_machinery)
if(is_station_level(temp_vent.loc.z) && !temp_vent.welded)
if(temp_vent.parent.other_atmosmch.len > 50) //Stops Aliens getting stuck in small networks. See: Security, Virology
vents += temp_vent
+1 -1
View File
@@ -18,7 +18,7 @@
// Calculate new position (searches through beacons in world)
var/obj/item/radio/beacon/chosen
var/list/possible = list()
for(var/obj/item/radio/beacon/W in world)
for(var/obj/item/radio/beacon/W in GLOB.global_radios)
if(!is_station_level(W.z))
continue
possible += W
+2 -1
View File
@@ -36,7 +36,8 @@
// break APC_BREAK_PROBABILITY% of all of the APCs on the station
var/affected_apc_count = 0
for(var/obj/machinery/power/apc/C in GLOB.apcs)
for(var/thing in GLOB.apcs)
var/obj/machinery/power/apc/C = thing
// skip any APCs that are too critical to break
var/area/current_area = get_area(C)
if((current_area.type in skipped_areas_apc) || !is_station_level(C.z))
+2 -1
View File
@@ -36,7 +36,8 @@
// break APC_BREAK_PROBABILITY% of all of the APCs on the station
var/affected_apc_count = 0
for(var/obj/machinery/power/apc/C in GLOB.apcs)
for(var/thing in GLOB.apcs)
var/obj/machinery/power/apc/C = thing
// skip any APCs that are too critical to disable
var/area/current_area = get_area(C)
if((current_area.type in skipped_areas_apc) || !is_station_level(C.z))
+2 -1
View File
@@ -30,7 +30,8 @@
/datum/event/carp_migration/proc/spawn_fish(num_groups, group_size_min = 3, group_size_max = 5)
var/list/spawn_locations = list()
for(var/obj/effect/landmark/C in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/C = thing
if(C.name == "carpspawn")
spawn_locations.Add(C.loc)
spawn_locations = shuffle(spawn_locations)
+5 -3
View File
@@ -10,7 +10,8 @@
for(var/i=1, i <= lightsoutAmount, i++)
var/list/possibleEpicentres = list()
for(var/obj/effect/landmark/newEpicentre in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/newEpicentre = thing
if(newEpicentre.name == "lightsout" && !(newEpicentre in epicentreList))
possibleEpicentres += newEpicentre
if(possibleEpicentres.len)
@@ -21,7 +22,8 @@
if(!epicentreList.len)
return
for(var/obj/effect/landmark/epicentre in epicentreList)
for(var/obj/machinery/power/apc/apc in range(epicentre,lightsoutRange))
for(var/thing in epicentreList)
var/obj/effect/landmark/epicentre = thing
for(var/obj/machinery/power/apc/apc in range(epicentre, lightsoutRange))
apc.overload_lighting()
+2 -2
View File
@@ -23,7 +23,7 @@ GLOBAL_VAR_INIT(account_hack_attempted, 0)
Notifications will be sent as updates occur.<br>"
var/my_department = "[station_name()] firewall subroutines"
for(var/obj/machinery/message_server/MS in world)
for(var/obj/machinery/message_server/MS in GLOB.machines)
if(!MS.active) continue
MS.send_rc_message("Head of Personnel's Desk", my_department, message, "", "", 2)
@@ -64,7 +64,7 @@ GLOBAL_VAR_INIT(account_hack_attempted, 0)
var/my_department = "[station_name()] firewall subroutines"
for(var/obj/machinery/message_server/MS in world)
for(var/obj/machinery/message_server/MS in GLOB.machines)
if(!MS.active) continue
MS.send_rc_message("Head of Personnel's Desk", my_department, message, "", "", 2)
+1 -1
View File
@@ -47,7 +47,7 @@
if(areas && areas.len > 0)
var/my_department = "[station_name()] firewall subroutines"
var/rc_message = "An unknown malicious program has been detected in the [english_list(areaName)] lighting and airlock control systems at [station_time_timestamp()]. Systems will be fully compromised within approximately three minutes. Direct intervention is required immediately.<br>"
for(var/obj/machinery/message_server/MS in world)
for(var/obj/machinery/message_server/MS in GLOB.machines)
MS.send_rc_message("Engineering", my_department, rc_message, "", "", 2)
for(var/mob/living/silicon/ai/A in GLOB.player_list)
to_chat(A, "<span class='danger'>Malicious program detected in the [english_list(areaName)] lighting and airlock control systems by [my_department].</span>")
+2 -1
View File
@@ -6,7 +6,8 @@
/datum/event/rogue_drone/start()
//spawn them at the same place as carp
var/list/possible_spawns = list()
for(var/obj/effect/landmark/C in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/C = thing
if(C.name == "carpspawn")
possible_spawns.Add(C)
+4 -2
View File
@@ -16,13 +16,15 @@
var/datum/mind/player_mind = new /datum/mind(key_of_slaughter)
player_mind.active = 1
var/list/spawn_locs = list()
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(isturf(L.loc))
switch(L.name)
if("revenantspawn")
spawn_locs += L.loc
if(!spawn_locs) //If we can't find any revenant spawns, try the carp spawns
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/L = thing
if(isturf(L.loc))
switch(L.name)
if("carpspawn")
+1 -1
View File
@@ -15,7 +15,7 @@ GLOBAL_VAR_INIT(sent_spiders_to_station, 0)
/datum/event/spider_infestation/start()
var/list/vents = list()
for(var/obj/machinery/atmospherics/unary/vent_pump/temp_vent in world)
for(var/obj/machinery/atmospherics/unary/vent_pump/temp_vent in SSair.atmos_machinery)
if(is_station_level(temp_vent.loc.z) && !temp_vent.welded)
if(temp_vent.parent.other_atmosmch.len > 50)
vents += temp_vent
+2 -1
View File
@@ -24,7 +24,8 @@ GLOBAL_LIST_INIT(unused_trade_stations, list("sol"))
return
var/list/spawnlocs = list()
for(var/obj/effect/landmark/landmark in GLOB.landmarks_list)
for(var/thing in GLOB.landmarks_list)
var/obj/effect/landmark/landmark = thing
if(landmark.name == "traderstart_[station]")
spawnlocs += get_turf(landmark)
if(!spawnlocs.len)
@@ -82,7 +82,6 @@
else //If it doesn't qualify in the above checks, we don't want it. Inform the person so they (ideally) stop trying to put the nuke disc in.
to_chat(user, "<span class='warning'>You aren't sure this is able to be processed by the machine.</span>")
return 0
return ..()
/obj/machinery/bottler/wrench_act(mob/user, obj/item/I)
. = TRUE
@@ -166,6 +166,15 @@
list_reagents = list("nutriment" = 2, "vitamin" = 2)
tastes = list("bread" = 2)
/obj/item/reagent_containers/food/snacks/toast
name = "Toast"
desc = "Yeah! Toast!"
icon_state = "toast"
filling_color = "#B2580E"
bitesize = 3
list_reagents = list("nutriment" = 3)
tastes = list("toast" = 2)
/obj/item/reagent_containers/food/snacks/jelliedtoast
name = "Jellied Toast"
desc = "A slice of bread covered with delicious jam."
@@ -198,3 +207,5 @@
trash = /obj/item/trash/waffles
filling_color = "#E6DEB5"
list_reagents = list("nutriment" = 8, "vitamin" = 1)
@@ -129,7 +129,7 @@
tastes = list("shrimp" = 1, "batter" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Ebi_maki
name = "ebi makiroll"
name = "ebi maki roll"
desc = "A large unsliced roll of Ebi Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Ebi_maki"
@@ -149,7 +149,7 @@
tastes = list("shrimp" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Ikura_maki
name = "ikura makiroll"
name = "ikura maki roll"
desc = "A large unsliced roll of Ikura Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Ikura_maki"
@@ -169,7 +169,7 @@
tastes = list("salmon roe" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Sake_maki
name = "sake makiroll"
name = "sake maki roll"
desc = "A large unsliced roll of Sake Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Sake_maki"
@@ -189,7 +189,7 @@
tastes = list("raw salmon" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/SmokedSalmon_maki
name = "smoked salmon makiroll"
name = "smoked salmon maki roll"
desc = "A large unsliced roll of Smoked Salmon Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "SmokedSalmon_maki"
@@ -209,7 +209,7 @@
tastes = list("smoked salmon" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Tamago_maki
name = "tamago makiroll"
name = "tamago maki roll"
desc = "A large unsliced roll of Tamago Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Tamago_maki"
@@ -229,7 +229,7 @@
tastes = list("egg" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Inari_maki
name = "inari makiroll"
name = "inari maki roll"
desc = "A large unsliced roll of Inari Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Inari_maki"
@@ -249,7 +249,7 @@
tastes = list("fried tofu" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Masago_maki
name = "masago makiroll"
name = "masago maki roll"
desc = "A large unsliced roll of Masago Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Masago_maki"
@@ -269,7 +269,7 @@
tastes = list("goldfish roe" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Tobiko_maki
name = "tobiko makiroll"
name = "tobiko maki roll"
desc = "A large unsliced roll of Tobkio Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Tobiko_maki"
@@ -289,7 +289,7 @@
tastes = list("shark roe" = 1, "rice" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/TobikoEgg_maki
name = "tobiko and egg makiroll"
name = "tobiko and egg maki roll"
desc = "A large unsliced roll of Tobkio and Egg Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "TobikoEgg_maki"
@@ -309,7 +309,7 @@
tastes = list("shark roe" = 1, "rice" = 1, "egg" = 1, "seaweed" = 1)
/obj/item/reagent_containers/food/snacks/sliceable/Tai_maki
name = "tai makiroll"
name = "tai maki roll"
desc = "A large unsliced roll of Tai Sushi."
icon = 'icons/obj/food/seafood.dmi'
icon_state = "Tai_maki"
@@ -175,7 +175,7 @@
if(default_unfasten_wrench(user, O))
return
default_deconstruction_crowbar(user, O)
default_deconstruction_crowbar(user, O)
var/obj/item/what = O
@@ -602,7 +602,7 @@
if(stat & (NOPOWER|BROKEN))
return 0
if(usr.contents.Find(src) || (in_range(src, usr) && istype(loc, /turf)))
if(!allowed(usr) && !emagged && locked != -1 && href_list["vend"])
if(!allowed(usr) && !emagged && locked != -1 && scan_id && href_list["vend"])
to_chat(usr, "<span class='warning'>Access denied.</span>")
SSnanoui.update_uis(src)
return 0
@@ -90,7 +90,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Ebi_maki
name = "Ebi Makiroll"
name = "Ebi Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/reagent_containers/food/snacks/boiled_shrimp = 4,
@@ -111,7 +111,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Ikura_maki
name = "Ikura Makiroll"
name = "Ikura Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/fish_eggs/salmon = 4,
@@ -132,7 +132,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Inari_maki
name = "Inari Makiroll"
name = "Inari Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/reagent_containers/food/snacks/fried_tofu = 4,
@@ -153,7 +153,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Sake_maki
name = "Sake Makiroll"
name = "Sake Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/reagent_containers/food/snacks/salmonmeat = 4,
@@ -174,7 +174,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/SmokedSalmon_maki
name = "Smoked Salmon Makiroll"
name = "Smoked Salmon Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/reagent_containers/food/snacks/salmonsteak = 4,
@@ -195,7 +195,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Masago_maki
name = "Masago Makiroll"
name = "Masago Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/fish_eggs/goldfish = 4,
@@ -216,7 +216,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Tobiko_maki
name = "Tobiko Makiroll"
name = "Tobiko Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/fish_eggs/shark = 4,
@@ -237,18 +237,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/TobikoEgg_maki
name = "Tobiko Makiroll"
reqs = list(
/obj/item/reagent_containers/food/snacks/sushi_Tobiko = 4,
/obj/item/reagent_containers/food/snacks/egg = 4,
)
pathtools = list(/obj/item/kitchen/sushimat)
result = /obj/item/reagent_containers/food/snacks/sliceable/TobikoEgg_maki
category = CAT_FOOD
subcategory = CAT_SUSHI
/datum/crafting_recipe/Sake_maki
name = "Sake Makiroll"
name = "Tobiko and Egg Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/sushi_Tobiko = 4,
/obj/item/reagent_containers/food/snacks/egg = 4,
@@ -269,7 +258,7 @@
subcategory = CAT_SUSHI
/datum/crafting_recipe/Tai_maki
name = "Tai Makiroll"
name = "Tai Maki Roll"
reqs = list(
/obj/item/reagent_containers/food/snacks/boiledrice = 1,
/obj/item/reagent_containers/food/snacks/catfishmeat = 4,
-6
View File
@@ -154,12 +154,6 @@
T.on_consume(src, usr)
..()
/obj/item/reagent_containers/food/snacks/grown/Crossed(atom/movable/AM, oldloc)
if(seed)
for(var/datum/plant_gene/trait/T in seed.genes)
T.on_cross(src, AM)
..()
/obj/item/reagent_containers/food/snacks/grown/after_slip(mob/living/carbon/human/H)
if(!seed)
return
@@ -50,13 +50,6 @@
return 1
return 0
/obj/item/grown/Crossed(atom/movable/AM, oldloc)
if(seed)
for(var/datum/plant_gene/trait/T in seed.genes)
T.on_cross(src, AM)
..()
/obj/item/grown/after_slip(mob/living/carbon/human/H)
if(!seed)
return
-3
View File
@@ -175,9 +175,6 @@
/datum/plant_gene/trait/proc/on_consume(obj/item/reagent_containers/food/snacks/grown/G, mob/living/carbon/target)
return
/datum/plant_gene/trait/proc/on_cross(obj/item/reagent_containers/food/snacks/grown/G, atom/target)
return
/datum/plant_gene/trait/proc/on_slip(obj/item/reagent_containers/food/snacks/grown/G, mob/living/carbon/target)
return
+12 -12
View File
@@ -25,7 +25,7 @@ GLOBAL_LIST_INIT(LIGHTING_CORNER_DIAGONAL, list(NORTHEAST, SOUTHEAST, SOUTHWEST,
var/cache_b = LIGHTING_SOFT_THRESHOLD
var/cache_mx = 0
/datum/lighting_corner/New(var/turf/new_turf, var/diagonal)
/datum/lighting_corner/New(turf/new_turf, diagonal)
. = ..()
masters = list()
masters[new_turf] = turn(diagonal, 180)
@@ -79,15 +79,16 @@ GLOBAL_LIST_INIT(LIGHTING_CORNER_DIAGONAL, list(NORTHEAST, SOUTHEAST, SOUTHWEST,
active = FALSE
var/turf/T
var/thing
for (thing in masters)
for(thing in masters)
T = thing
if(T.lighting_object)
active = TRUE
return
// God that was a mess, now to do the rest of the corner code! Hooray!
/datum/lighting_corner/proc/update_lumcount(var/delta_r, var/delta_g, var/delta_b)
/datum/lighting_corner/proc/update_lumcount(delta_r, delta_g, delta_b)
if((abs(delta_r)+abs(delta_g)+abs(delta_b)) == 0)
if(!(delta_r || delta_g || delta_b)) // 0 is falsey ok
return
lum_r += delta_r
@@ -96,10 +97,10 @@ GLOBAL_LIST_INIT(LIGHTING_CORNER_DIAGONAL, list(NORTHEAST, SOUTHEAST, SOUTHWEST,
if(!needs_update)
needs_update = TRUE
GLOB.lighting_update_corners += src
SSlighting.corners_queue += src
/datum/lighting_corner/proc/update_objects()
// Cache these values a head of time so 4 individual lighting objects don't all calculate them individually.
// Cache these values ahead of time so 4 individual lighting objects don't all calculate them individually.
var/lum_r = src.lum_r
var/lum_g = src.lum_g
var/lum_b = src.lum_b
@@ -122,19 +123,18 @@ GLOBAL_LIST_INIT(LIGHTING_CORNER_DIAGONAL, list(NORTHEAST, SOUTHEAST, SOUTHWEST,
#endif
cache_mx = round(mx, LIGHTING_ROUND_VALUE)
for (var/TT in masters)
for(var/TT in masters)
var/turf/T = TT
if(T.lighting_object)
if(!T.lighting_object.needs_update)
T.lighting_object.needs_update = TRUE
GLOB.lighting_update_objects += T.lighting_object
if(T.lighting_object && !T.lighting_object.needs_update)
T.lighting_object.needs_update = TRUE
SSlighting.objects_queue += T.lighting_object
/datum/lighting_corner/dummy/New()
return
/datum/lighting_corner/Destroy(var/force)
/datum/lighting_corner/Destroy(force)
if(!force)
return QDEL_HINT_LETMELIVE
+8 -5
View File
@@ -5,7 +5,7 @@
icon = LIGHTING_ICON
icon_state = "transparent"
color = LIGHTING_BASE_MATRIX
color = null //we manually set color in init instead
plane = LIGHTING_PLANE
mouse_opacity = MOUSE_OPACITY_TRANSPARENT
layer = LIGHTING_LAYER
@@ -18,6 +18,9 @@
/atom/movable/lighting_object/Initialize(mapload)
. = ..()
verbs.Cut()
//We avoid setting this in the base as if we do then the parent atom handling will add_atom_color it and that
//is totally unsuitable for this object, as we are always changing it's colour manually
color = LIGHTING_BASE_MATRIX
myturf = loc
if(myturf.lighting_object)
@@ -29,11 +32,11 @@
S.update_starlight()
needs_update = TRUE
GLOB.lighting_update_objects += src
SSlighting.objects_queue += src
/atom/movable/lighting_object/Destroy(var/force)
/atom/movable/lighting_object/Destroy(force)
if(force)
GLOB.lighting_update_objects -= src
SSlighting.objects_queue -= src
if(loc != myturf)
var/turf/oldturf = get_turf(myturf)
var/turf/newturf = get_turf(loc)
@@ -143,6 +146,6 @@
return
// Override here to prevent things accidentally moving around overlays.
/atom/movable/lighting_object/forceMove(atom/destination, var/no_tp=FALSE, var/harderforce = FALSE)
/atom/movable/lighting_object/forceMove(atom/destination, no_tp = FALSE, harderforce = FALSE)
if(harderforce)
. = ..()
+5 -5
View File
@@ -29,7 +29,7 @@
var/needs_update = LIGHTING_NO_UPDATE // Whether we are queued for an update.
/datum/light_source/New(var/atom/owner, var/atom/top)
/datum/light_source/New(atom/owner, atom/top)
source_atom = owner // Set our new owner.
LAZYADD(source_atom.light_sources, src)
top_atom = top
@@ -56,7 +56,7 @@
LAZYREMOVE(top_atom.light_sources, src)
if(needs_update)
GLOB.lighting_update_lights -= src
SSlighting.sources_queue -= src
. = ..()
@@ -65,13 +65,13 @@
// Actually that'd be great if you could!
#define EFFECT_UPDATE(level) \
if(needs_update == LIGHTING_NO_UPDATE) \
GLOB.lighting_update_lights += src; \
SSlighting.sources_queue += src; \
if(needs_update < level) \
needs_update = level; \
// This proc will cause the light source to update the top atom, and add itself to the update queue.
/datum/light_source/proc/update(var/atom/new_top_atom)
/datum/light_source/proc/update(atom/new_top_atom)
// This top atom is different.
if(new_top_atom && new_top_atom != top_atom)
if(top_atom != source_atom && top_atom.light_sources) // Remove ourselves from the light sources of that top atom.
@@ -141,7 +141,7 @@
effect_str = null
/datum/light_source/proc/recalc_corner(var/datum/lighting_corner/C)
/datum/light_source/proc/recalc_corner(datum/lighting_corner/C)
LAZYINITLIST(effect_str)
if(effect_str[C]) // Already have one.
REMOVE_CORNER(C)
+2 -2
View File
@@ -57,7 +57,7 @@
C.active = TRUE
// Used to get a scaled lumcount.
/turf/proc/get_lumcount(var/minlum = 0, var/maxlum = 1)
/turf/proc/get_lumcount(minlum = 0, maxlum = 1)
if(!lighting_object)
return 1
@@ -102,7 +102,7 @@
recalc_atom_opacity() // Make sure to do this before reconsider_lights(), incase we're on instant updates.
reconsider_lights()
/turf/proc/change_area(var/area/old_area, var/area/new_area)
/turf/proc/change_area(area/old_area, area/new_area)
if(SSlighting.initialized)
if(new_area.dynamic_lighting != old_area.dynamic_lighting)
if(new_area.dynamic_lighting)
-143
View File
@@ -1,143 +0,0 @@
//////////////////////////////////
// Converter Gate //
//////////////////////////////////
/*
This gate is special enough to warrant its own file, as it overrides a lot of the logic_gate procs as well as adds a new one.
- CONVERT Gates convert signaler and logic signals, to allow logic gates to actually be used in tandem with assemblies and station equipment like doors.
- While technically a mono-input device, the input and output are actually completely different types of signals, and thus incompatible without this gate.
- A signaler must be attached manually before the gate is fully functional, and will retain any frequency and code settings it had when attached.
- You can adjust these settings through a link in the multitool menu, but the receiving mode is automatically controlled by the converter.
- While attached, the ability to manually send the signal on the signaler through its menu is also disabled, to avoid messing up the logic system.
*/
//CONVERT Gate
/obj/machinery/logic_gate/convert
name = "CONVERT Gate"
desc = "Converts signals between radio and logic types, allowing for signaller input/output from logic systems."
icon_state = "logic_convert"
mono_input = 1
var/logic_output = 0 //When set to 1, the logic signal is the output. When set to 0, the logic signal is the input.
var/obj/item/assembly/signaler/attached_signaler = null
/obj/machinery/logic_gate/convert/handle_logic()
output_state = input1_state
return
/obj/machinery/logic_gate/convert/attackby(obj/item/O, mob/user, params)
if(tamperproof) //Extra precaution to avoid people attaching/removing signalers from tamperproofed converters
return
if(istype(O, /obj/item/assembly/signaler))
var/obj/item/assembly/signaler/S = O
if(S.secured)
to_chat(user, "<span class='warning'>The [S] is already secured.</span>")
return
if(attached_signaler)
to_chat(user, "<span class='warning'>There is already a device attached, remove it first.</span>")
return
user.unEquip(S)
S.forceMove(src)
S.holder = src
S.toggle_secure()
if(logic_output) //Make sure we are set to receive if the converter is set to output logic, and send if the converter is set to accept logic input
S.receiving = 1
else
S.receiving = 0
attached_signaler = S
to_chat(user, "<span class='notice'>You attach \the [S] to the I/O connection port and secure it.</span>")
return
if(attached_signaler && istype(O, /obj/item/screwdriver)) //Makes sure we remove the attached signaler before we can open up and deconstruct the machine
var/obj/item/assembly/signaler/S = attached_signaler
attached_signaler = null
S.forceMove(get_turf(src))
S.holder = null
S.toggle_secure()
to_chat(user, "<span class='notice'>You unsecure and detach \the [S] from the I/O connection port.</span>")
return
return ..()
/obj/machinery/logic_gate/convert/multitool_menu(var/mob/user, var/obj/item/multitool/P)
var/logic_state_string
var/menu_contents = {"
<dl>
"}
if(logic_output)
switch(output_state)
if(LOGIC_OFF)
logic_state_string = "OFF"
if(LOGIC_ON)
logic_state_string = "ON"
if(LOGIC_FLICKER)
logic_state_string = "FLICKER"
else
logic_state_string = "ERROR: UNKNOWN STATE"
menu_contents += {"
<dt><b>Output:</b> [format_tag("ID Tag","output_id_tag")]</dt>
<dd>Output State: [logic_state_string]</dd>
"}
else
switch(input1_state)
if(LOGIC_OFF)
logic_state_string = "OFF"
if(LOGIC_ON)
logic_state_string = "ON"
if(LOGIC_FLICKER)
logic_state_string = "FLICKER"
else
logic_state_string = "ERROR: UNKNOWN STATE"
menu_contents += {"
<dt><b>Input:</b> [format_tag("ID Tag","input1_id_tag")]</dt>
<dd>Input State: [logic_state_string]</dd>
"}
menu_contents += {"
<dt><b>Logic Signal Designation:</b> <a href='?src=[UID()];toggle_logic=1'>[logic_output ? "Output" : "Input"]</a></dt>
"}
if(attached_signaler)
menu_contents += "<dt><a href='?src=[UID()];adjust_signaler=1'>Adjust Signaler Settings</a></dt>"
else
menu_contents += "<dt><b>NO SIGNALER ATTACHED!</b></dt>"
menu_contents += {"
</dl>
"}
return menu_contents
/obj/machinery/logic_gate/convert/multitool_topic(var/mob/user,var/list/href_list,var/obj/O)
..()
if("toggle_logic" in href_list)
logic_output = !logic_output
if(attached_signaler) //If we have a signaler attached, make sure we update it to send/receive when we change the logic signal desgination
if(logic_output)
attached_signaler.receiving = 1
else
attached_signaler.receiving = 0
if(("adjust_signaler" in href_list) && attached_signaler) //Make sure that we have a signaler attached to handle this one, otherwise ignore this command
attached_signaler.interact(user, 1)
update_multitool_menu(user)
/obj/machinery/logic_gate/convert/receive_signal(datum/signal/signal, receive_method, receive_param)
if(logic_output)
if(attached_signaler)
attached_signaler.receive_signal(signal)
return
else
..()
/obj/machinery/logic_gate/convert/handle_output()
if(logic_output)
..()
else
if(attached_signaler && (output_state == LOGIC_ON || output_state == LOGIC_FLICKER))
attached_signaler.signal()
return
/obj/machinery/logic_gate/convert/proc/process_activation(var/obj/item/D)
if(!logic_output) //Don't bother if our input is a logic signal
return
if(D == attached_signaler) //Ignore if we somehow got called by a device that isn't what we have attached
input1_state = LOGIC_FLICKER
spawn(LOGIC_FLICKER_TIME)
if(input1_state == LOGIC_FLICKER)
input1_state = LOGIC_OFF
return
-100
View File
@@ -1,100 +0,0 @@
//////////////////////////////////
// Dual-Input Gates //
//////////////////////////////////
// OR Gate
/obj/machinery/logic_gate/or
name = "OR Gate"
desc = "Outputs ON when at least one input is ON."
icon_state = "logic_or"
/obj/machinery/logic_gate/or/handle_logic()
if(input1_state == LOGIC_ON || input1_state == LOGIC_FLICKER || input2_state == LOGIC_ON || input2_state == LOGIC_FLICKER)
if(input1_state == LOGIC_ON || input2_state == LOGIC_ON) //continuous signal takes priority in determining what to output
output_state = LOGIC_ON
else
output_state = LOGIC_FLICKER
else //Both inputs were off, so input is off
output_state = LOGIC_OFF
return
// AND Gate
/obj/machinery/logic_gate/and
name = "AND Gate"
desc = "Outputs ON only when both inputs are ON."
icon_state = "logic_and"
/obj/machinery/logic_gate/and/handle_logic()
if((input1_state == LOGIC_ON || input1_state == LOGIC_FLICKER) && (input2_state == LOGIC_ON || input2_state == LOGIC_FLICKER))
if(input1_state == LOGIC_ON && input2_state == LOGIC_ON) //only output a continuous signal when both inputs are continuous signals
output_state = LOGIC_ON
else
output_state = LOGIC_FLICKER
else //At least one input was off, so output is off
output_state = LOGIC_OFF
return
// NAND Gate
/obj/machinery/logic_gate/nand
name = "NAND Gate"
desc = "Outputs OFF only when both inputs are ON."
output_state = LOGIC_ON
icon_state = "logic_nand"
/obj/machinery/logic_gate/nand/handle_logic()
if((input1_state == LOGIC_ON || input1_state == LOGIC_FLICKER) && (input2_state == LOGIC_ON || input2_state == LOGIC_FLICKER))
output_state = LOGIC_OFF //Both inputs are ON/FLICKER, so output is off
else
output_state = LOGIC_ON //This can only output continuous signals
return
// NOR Gate
/obj/machinery/logic_gate/nor
name = "NOR Gate"
desc = "Outputs OFF when at least one input is ON."
icon_state = "logic_nor"
output_state = LOGIC_ON
/obj/machinery/logic_gate/nor/handle_logic()
if(input1_state == LOGIC_OFF && input2_state == LOGIC_OFF) //Both inputs are OFF, so output is ON
output_state = LOGIC_ON //This can only output continuous signals
else
output_state = LOGIC_OFF
return
// XOR Gate
/obj/machinery/logic_gate/xor
name = "XOR Gate"
desc = "Outputs ON when only one input is ON."
icon_state = "logic_xor"
/obj/machinery/logic_gate/xor/handle_logic()
if((input1_state == LOGIC_ON || input1_state == LOGIC_FLICKER) && (input2_state == LOGIC_OFF)) //Only input1 is ON/FLICKER, so output matches input1
output_state = input1_state
else if((input2_state == LOGIC_ON || input2_state == LOGIC_FLICKER) && (input1_state == LOGIC_OFF)) //Only input2 is ON/FLICKER, so output matches input2
output_state = input2_state
else //Both inputs are ON or OFF, so output is OFF
output_state = LOGIC_OFF
return
// XNOR Gate
/obj/machinery/logic_gate/xnor
name = "XNOR Gate"
desc = "Outputs ON when both inputs are ON or OFF."
icon_state = "logic_xnor"
output_state = LOGIC_ON
/obj/machinery/logic_gate/xnor/handle_logic()
if((input1_state == LOGIC_ON || input1_state == LOGIC_FLICKER) && (input2_state == LOGIC_ON || input2_state == LOGIC_FLICKER)) //Both inputs are ON/FLICKER
if(input1_state == LOGIC_ON && input2_state == LOGIC_ON) //Only continuous signal when both inputs are ON
output_state = LOGIC_ON
else //If at least one input is FLICKER, output FLICKER
output_state = LOGIC_FLICKER
else if(input1_state == LOGIC_OFF && input2_state == LOGIC_OFF) //Both inputs are OFF
output_state = LOGIC_ON //Always continuous in this case
else //Only one input is ON/FLICKER
output_state = LOGIC_OFF
return
-284
View File
@@ -1,284 +0,0 @@
/obj/machinery/logic_gate
name = "Logic Base"
desc = "This does nothing except connect to things. Highly illogical, report to a coder at once if you see this in-game."
icon = 'icons/obj/computer3.dmi'
icon_state = "serverframe"
density = 1
anchored = 1
settagwhitelist = list("input1_id_tag", "input2_id_tag", "output_id_tag")
var/tamperproof = 0 //if set, will make the machine unable to be destroyed, adjusted, etc. via in-game interaction (USE ONLY FOR MAPPING STUFF)
var/mono_input = 0 //if set, will ignore input2
var/datum/radio_frequency/radio_connection
var/frequency = 0
/*
Some notes on Input/Output:
- Multiple things can be linked to the same input or output tag, just like how wires can connect multiple sources and receivers.
- For inputs, only the last signal received BEFORE a process() call will be used in the logic handling.
- Input states are updated immediately whenever an input signal is received, so it is possible to update multiple times within a single process cycle.
- This means if you have multiple connected inputs, but the last signal received before the process() call is OFF, it won't matter if the others are both ON.
- For this reason, please set up your logic properly. You can theoretically chain these infinitely, so there's no need to link multiple things to a single input.
- For outputs, the signal will attempt to be sent out every process() call, to ensure newly connected things are updated within one process cycle
- Connecting an output to multiple inputs should not cause issues, as long as you don't have multiple connections to a given input (see previous notes on inputs).
- The output state is determined immediately preceeding the signal broadcast, using the input states at the time of the process() call, not when a signal is received.
- Because of how the process cycle works, it is possible that it may take multiple cycles for a signal to fully propogate through a logic chain.
- This is because machines attempt to process in the order they were added to the scheduler.
- Building the logic gates at the end of the chain first may cause delays in signal propogation.
If you take all this into consideration when linking and using logic machinery, you should have no unexpected issues with input/output. Your design flaws are on you though.
*/
var/input1_id_tag = null
var/input1_state = LOGIC_OFF
var/input2_id_tag = null
var/input2_state = LOGIC_OFF
var/output_id_tag = null
var/output_state = LOGIC_OFF
/obj/machinery/logic_gate/New()
if(tamperproof) //doing this during New so we don't have to worry about forgetting to set these vars during editting / defining
resistance_flags |= ACID_PROOF
..()
if(SSradio)
set_frequency(frequency)
component_parts = list()
var/obj/item/circuitboard/logic_gate/LG = new(null)
LG.set_type(type)
component_parts += LG
component_parts += new /obj/item/stack/cable_coil(null, 1)
/obj/machinery/logic_gate/Initialize()
..()
set_frequency(frequency)
/obj/machinery/logic_gate/proc/set_frequency(new_frequency)
SSradio.remove_object(src, frequency)
frequency = new_frequency
radio_connection = SSradio.add_object(src, frequency, RADIO_LOGIC)
return
/obj/machinery/logic_gate/Destroy()
if(SSradio)
SSradio.remove_object(src, frequency)
radio_connection = null
return ..()
/obj/machinery/logic_gate/process()
handle_logic()
handle_output() //All output will send for at least one cycle, and will attempt to send every cycle. Hopefully this won't be too taxing.
return
/obj/machinery/logic_gate/proc/handle_logic()
return
/obj/machinery/logic_gate/proc/handle_output()
if(!radio_connection) //can't output without this
return
if(output_id_tag == null) //Don't output to an undefined id_tag
return
var/datum/signal/signal = new
signal.transmission_method = 1 //radio signal
signal.source = src
signal.data = list(
"tag" = output_id_tag,
"sigtype" = "logic",
"state" = output_state,
)
radio_connection.post_signal(src, signal, filter = RADIO_LOGIC)
/obj/machinery/logic_gate/receive_signal(datum/signal/signal, receive_method, receive_param)
if(!signal.data["tag"] || ((signal.data["tag"] != input1_id_tag) && (signal.data["tag"] != input2_id_tag)) || (signal.data["sigtype"] != "logic"))
//If the signal lacks tag data, the signal's tag data doesn't match either input id tag, or is not a "logic" signal, ignore it since it's not for us
return
if(signal.data["tag"] == input1_id_tag) //If the signal is for input1
if(signal.data["state"] == input1_state) //If we already match, ignore the new signal since nothing changes
return
if(signal.data["state"] == LOGIC_OFF) //Shut it down and keep it off
input1_state = LOGIC_OFF
return
if(signal.data["state"] == LOGIC_ON) //Turn it on and keep it on
input1_state = LOGIC_ON
return
if(signal.data["state"] == LOGIC_FLICKER) //Turn it on then turn it off
if(input1_state == LOGIC_ON) //An existing continuous ON state overrides new flicker signals
return
input1_state = LOGIC_FLICKER
spawn(LOGIC_FLICKER_TIME)
if(input1_state == LOGIC_FLICKER) //Make sure we didn't get a new continuous signal set while we waited (those take priority)
input1_state = LOGIC_OFF
return
//Now, you may be wondering why I included those returns.
//The answer is "If you link both inputs to the same source, you're an idiot and deserve to have it break", so yeah. Deal with it.
if(mono_input)
//We only care about input1, so if we didn't receive a signal for that, we're done.
return
if(signal.data["tag"] == input2_id_tag) //If the signal is for input2 (reaching this point assumes mono_input is not set)
if(signal.data["state"] == input2_state) //If we already match, ignore the new signal since nothing changes
return
if(signal.data["state"] == LOGIC_OFF) //Shut it down and keep it off
input2_state = LOGIC_OFF
return
if(signal.data["state"] == LOGIC_ON) //Turn it on and keep it on
input2_state = LOGIC_ON
return
if(signal.data["state"] == LOGIC_FLICKER) //Turn it on then turn it off
if(input2_state == LOGIC_ON) //An existing continuous ON state overrides new flicker signals
return
input2_state = LOGIC_FLICKER
spawn(LOGIC_FLICKER_TIME)
if(input2_state == LOGIC_FLICKER) //Make sure we didn't get a new continuous signal set while we waited (those take priority)
input2_state = LOGIC_OFF
return
/obj/machinery/logic_gate/multitool_menu(var/mob/user, var/obj/item/multitool/P)
var/input1_state_string
var/input2_state_string
var/output_state_string
switch(input1_state)
if(LOGIC_OFF)
input1_state_string = "OFF"
if(LOGIC_ON)
input1_state_string = "ON"
if(LOGIC_FLICKER)
input1_state_string = "FLICKER"
else
input1_state_string = "ERROR: UNKNOWN STATE"
switch(input2_state)
if(LOGIC_OFF)
input2_state_string = "OFF"
if(LOGIC_ON)
input2_state_string = "ON"
if(LOGIC_FLICKER)
input2_state_string = "FLICKER"
else
input2_state_string = "ERROR: UNKNOWN STATE"
switch(output_state)
if(LOGIC_OFF)
output_state_string = "OFF"
if(LOGIC_ON)
output_state_string = "ON"
if(LOGIC_FLICKER)
output_state_string = "FLICKER"
else
output_state_string = "ERROR: UNKNOWN STATE"
var/menu_contents = {"
<dl>
<dt><b>Input:</b> [format_tag("ID Tag","input1_id_tag")]</dt>
<dd>Input State: [input1_state_string]</dd>
"}
if(!mono_input)
menu_contents = {"
<dt><b>Input 1:</b> [format_tag("ID Tag","input1_id_tag")]</dt>
<dd>Input 1 State: [input1_state_string]</dd>
<dt><b>Input 2:</b> [format_tag("ID Tag","input2_id_tag")]</dt>
<dd>Input 2 State: [input2_state_string]</dd>
"}
menu_contents += {"
<dt><b>Output:</b> [format_tag("ID Tag","output_id_tag")]</dt>
<dd>Output State: [output_state_string]</dd>
</dl>
"}
return menu_contents
/obj/machinery/logic_gate/convert/multitool_topic(var/mob/user,var/list/href_list,var/obj/O)
..()
update_multitool_menu(user)
/obj/machinery/logic_gate/attackby(obj/item/O, mob/user, params)
if(tamperproof)
to_chat(user, "<span class='warning'>The [src] appears to be tamperproofed! You can't interact with it!</span>")
return 0
if(istype(O, /obj/item/multitool))
update_multitool_menu(user)
return 1
if(istype(O, /obj/item/screwdriver))
panel_open = !panel_open
to_chat(user, "<span class='notice'>You [panel_open ? "open" : "close"] the access panel.</span>")
return 1
if(panel_open && istype(O, /obj/item/crowbar))
default_deconstruction_crowbar(user, O)
return 1
return ..()
//////////////////////////////////////
// Attack procs //
//////////////////////////////////////
/obj/machinery/logic_gate/attack_ai(mob/user)
if(tamperproof)
to_chat(user, "<span class='warning'>The [src] appears to be tamperproofed! You can't interface with it!</span>")
return 0
add_hiddenprint(user)
return ui_interact(user)
/obj/machinery/logic_gate/attack_ghost(mob/user)
if(tamperproof)
to_chat(user, "<span class='warning'>The [src] appears to be tamperproofed! You can't haunt it!</span>")
return 0
return ui_interact(user)
/obj/machinery/logic_gate/attack_hand(mob/user)
if(tamperproof)
to_chat(user, "<span class='warning'>The [src] appears to be tamperproofed! You can't interact with it!</span>")
return 0
. = ..()
if(.)
return 0
return interact(user)
/obj/machinery/logic_gate/attack_alien(mob/user) //No xeno logic, that's too silly.
to_chat(user, "<span class='warning'>The [src] appears to be too complex! You can't comprehend it and back off in fear!</span>")
return 0
/obj/machinery/logic_gate/attack_animal(mob/user) //No animal logic either.
to_chat(user, "<span class='warning'>The [src] appears to be beyond your comprehension! You can't fathom it!</span>")
return 0
/obj/machinery/logic_gate/attack_slime(mob/user) //No slime logic. Seriously.
to_chat(user, "<span class='warning'>The [src] appears to be beyond your gelatinous understanding! You ignore it!</span>")
return 0
/obj/machinery/logic_gate/emp_act(severity)
if(tamperproof)
return 0
..()
/obj/machinery/logic_gate/ex_act(severity)
if(tamperproof)
return 0
..()
/obj/machinery/logic_gate/blob_act(obj/structure/blob/B)
if(!tamperproof)
return ..()
/obj/machinery/logic_gate/singularity_act()
if(tamperproof)
//This is some top-level tamperproofing right here, that's for sure. It can even defy a singularity!
return 0
..()
/obj/machinery/logic_gate/bullet_act()
if(tamperproof)
return 0
..()
/obj/machinery/logic_gate/tesla_act(var/power)
if(tamperproof)
tesla_zap(src, 3, power) //If we're tamperproof, we'll just bounce the full shock of the tesla zap we got hit by, so it continues on normally without diminishing
return 0
..()
-62
View File
@@ -1,62 +0,0 @@
//////////////////////////////////
// Mono-Input Gates //
//////////////////////////////////
//NOT Gate
/obj/machinery/logic_gate/not
name = "NOT Gate"
desc = "Accepts one input and outputs the reverse state."
icon_state = "logic_not"
mono_input = 1 //NOT Gates are the simplest logic gate because they only utilize one input.
output_state = LOGIC_ON //Starts with an active output, since the input will be OFF at start
/*
A quick note regarding NOT Gates:
- Connecting multiple things to the input of a NOT Gate can cause weird behaviour due to updating both when it receives a signal and when it calls process().
- This means it will attempt to output once for every logic machine connected to its input's own process() call.
- It will then attempt to output an additional time based on the current state when it comes to its own process() call.
- For this reason, it is HIGHLY RECOMMENDED that you only connect a single signal source to the input of a NOT Gate to avoid signal spasms.
- Connecting multiple things to the output of a NOT Gate should not cause this unusual behavior.
*/
/obj/machinery/logic_gate/not/handle_logic() //Our output will always be a continuous signal, even with a FLICKER, it just will update the output when the FLICKER ends
if(input1_state == LOGIC_ON) //Output is OFF while input is ON
output_state = LOGIC_OFF
else if(input1_state == LOGIC_FLICKER) //Output is OFF while input is FLICKER, then output returns to ON when input returns to OFF
output_state = LOGIC_OFF
spawn(LOGIC_FLICKER_TIME + 1) //Call handle_logic again after this delay (the input should update from the spawn(LOGIC_FLICKER_TIME) in receive_signal() by then)
handle_logic()
else //Output is ON while input is OFF
output_state = LOGIC_ON
handle_output()
return
//STATUS Gate
/obj/machinery/logic_gate/status
name = "Status Gate"
desc = "Accepts one input and outputs the same state, showing a colored light based on current state."
icon_state = "logic_status"
mono_input = 1 //STATUS Gate doesn't actually perform logic operations, but instead acts as a testing conduit.
/*
STATUS Gates are largely a diagnostics tool, but I'm sure someone will still make a logic gate rave with them anyways.
- There is no need to actually connect an output for these to work, they just need an input to sample from.
- STATUS Gates attempt to update their lights whenever they receive a signal.
*/
/obj/machinery/logic_gate/status/receive_signal(datum/signal/signal, receive_method, receive_params)
..()
handle_logic() //STATUS Gate calls handle_logic() when it receives a signal to update its light and output_state
/obj/machinery/logic_gate/status/handle_logic()
output_state = input1_state //Output is equal to input, since it is simply a connection with an attached light
if(output_state == LOGIC_OFF) //Red light when OFF
set_light(2,2,"#ff0000")
return
if(output_state == LOGIC_ON) //Green light when ON
set_light(2,2,"#009933")
return
if(output_state == LOGIC_FLICKER) //Orange light when FLICKER, then update after LOGIC_FLICKER_TIME + 1 to reflect the changed state
set_light(2,2,"#ff9900")
spawn(LOGIC_FLICKER_TIME + 1)
handle_logic()
return
-1
View File
@@ -275,7 +275,6 @@
return
else
return ..()
return ..()
/obj/item/twohanded/bostaff/hit_reaction(mob/living/carbon/human/owner, atom/movable/hitby, attack_text = "the attack", final_block_chance = 0, damage = 0, attack_type = MELEE_ATTACK)
if(wielded)
@@ -26,7 +26,7 @@
/obj/item/wormhole_jaunter/proc/get_destinations(mob/user)
var/list/destinations = list()
for(var/obj/item/radio/beacon/B in world)
for(var/obj/item/radio/beacon/B in GLOB.global_radios)
var/turf/T = get_turf(B)
if(is_station_level(T.z))
destinations += B
@@ -93,7 +93,7 @@
blast_range = initial(blast_range)
if(isliving(user))
var/mob/living/L = user
var/health_percent = L.health / L.maxHealth
var/health_percent = max(L.health / L.maxHealth, 0) // Don't go negative
chaser_cooldown += round(health_percent * 20) //two tenths of a second for each missing 10% of health
cooldown_time += round(health_percent * 10) //one tenth of a second for each missing 10% of health
chaser_speed = max(chaser_speed + health_percent, 0.5) //one tenth of a second faster for each missing 10% of health
+6 -6
View File
@@ -98,7 +98,7 @@
/obj/machinery/mineral/processing_unit/Destroy()
CONSOLE = null
QDEL_NULL(files)
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
materials.retrieve_all()
return ..()
@@ -120,7 +120,7 @@
CONSOLE.updateUsrDialog()
/obj/machinery/mineral/processing_unit/proc/process_ore(obj/item/stack/ore/O)
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
var/material_amount = materials.get_item_material_amount(O)
if(!materials.has_space(material_amount))
unload_mineral(O)
@@ -132,7 +132,7 @@
/obj/machinery/mineral/processing_unit/proc/get_machine_data()
var/dat = "<b>Smelter control console</b><br><br>"
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in materials.materials)
var/datum/material/M = materials.materials[mat_id]
dat += "<span class=\"res_name\">[M.name]: </span>[M.amount] cm&sup3;"
@@ -165,7 +165,7 @@
return dat
/obj/machinery/mineral/processing_unit/proc/smelt_ore()
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
var/datum/material/mat = materials.materials[selected_material]
if(mat)
var/sheets_to_remove = (mat.amount >= (MINERAL_MATERIAL_AMOUNT * SMELT_AMOUNT) ) ? SMELT_AMOUNT : round(mat.amount / MINERAL_MATERIAL_AMOUNT)
@@ -187,7 +187,7 @@
on = FALSE
return
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
materials.use_amount(alloy.materials, amount)
generate_mineral(alloy.build_path)
@@ -198,7 +198,7 @@
var/build_amount = SMELT_AMOUNT
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in D.materials)
var/M = D.materials[mat_id]
+6 -6
View File
@@ -67,7 +67,7 @@
/obj/machinery/mineral/ore_redemption/Destroy()
QDEL_NULL(files)
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
materials.retrieve_all()
return ..()
@@ -92,7 +92,7 @@
if(O && O.refined_type)
points += O.points * point_upgrade * O.amount
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
var/material_amount = materials.get_item_material_amount(O)
if(!material_amount)
@@ -111,7 +111,7 @@
var/build_amount = 0
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in D.materials)
var/M = D.materials[mat_id]
var/datum/material/redemption_mat = materials.materials[mat_id]
@@ -147,7 +147,7 @@
var/has_minerals = FALSE
var/mineral_name = null
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in materials.materials)
var/datum/material/M = materials.materials[mat_id]
var/mineral_amount = M.amount / MINERAL_MATERIAL_AMOUNT
@@ -251,7 +251,7 @@
else
dat += "No ID inserted. <A href='?src=[UID()];insert_id=1'>Insert ID.</A><br><br>"
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in materials.materials)
var/datum/material/M = materials.materials[mat_id]
if(M.amount)
@@ -302,7 +302,7 @@
/obj/machinery/mineral/ore_redemption/Topic(href, href_list)
if(..())
return
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
if(href_list["eject_id"])
usr.put_in_hands(inserted_id)
inserted_id = null
+3 -3
View File
@@ -23,7 +23,7 @@
if(!T)
return
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/obj/item/stack/sheet/O in T)
materials.insert_stack(O, O.amount)
@@ -32,7 +32,7 @@
return
var/dat = "<b>Coin Press</b><br>"
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
for(var/mat_id in materials.materials)
var/datum/material/M = materials.materials[mat_id]
if(!M.amount && chosen != mat_id)
@@ -65,7 +65,7 @@
if(processing == 1)
to_chat(usr, "<span class='notice'>The machine is processing.</span>")
return
GET_COMPONENT(materials, /datum/component/material_container)
var/datum/component/material_container/materials = GetComponent(/datum/component/material_container)
if(href_list["choose"])
if(materials.materials[href_list["choose"]])
chosen = href_list["choose"]
+5
View File
@@ -14,3 +14,8 @@
/mob/camera/experience_pressure_difference()
return
/mob/camera/forceMove(atom/destination)
var/oldloc = loc
loc = destination
Moved(oldloc, NONE)
+1 -1
View File
@@ -15,7 +15,7 @@
onTransitZ(old_turf?.z, new_turf?.z)
var/oldloc = loc
loc = destination
Moved(oldloc, NONE, TRUE)
Moved(oldloc, NONE)
/mob/dead/onTransitZ(old_z,new_z)
..()
@@ -616,7 +616,6 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp
/mob/dead/observer/Topic(href, href_list)
if(usr != src)
return
..()
if(href_list["track"])
var/atom/target = locate(href_list["track"])
@@ -167,4 +167,4 @@ Doesn't work on other aliens/AI.*/
adjustPlasma(-amount)
return 1
return 0
return 0
@@ -55,7 +55,7 @@
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
visible_message("<span class='danger'>[M] has attempted to disarm [src]!</span>")
/mob/living/carbon/alien/humanoid/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
/mob/living/carbon/alien/humanoid/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect)
if(!no_effect && !visual_effect_icon)
visual_effect_icon = ATTACK_EFFECT_CLAW
..()
@@ -31,7 +31,7 @@
step_away(src, user, 15)
return TRUE
/mob/living/carbon/alien/larva/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
/mob/living/carbon/alien/larva/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect)
if(!no_effect && !visual_effect_icon)
visual_effect_icon = ATTACK_EFFECT_BITE
..()
+5 -1
View File
@@ -2,6 +2,10 @@
var/canEnterVentWith = "/obj/item/implant=0&/obj/item/clothing/mask/facehugger=0&/obj/item/radio/borg=0&/obj/machinery/camera=0"
var/datum/middleClickOverride/middleClickOverride = null
/mob/living/carbon/Initialize(mapload)
. = ..()
GLOB.carbon_list += src
/mob/living/carbon/Destroy()
// This clause is here due to items falling off from limb deletion
for(var/obj/item in get_all_slots())
@@ -14,6 +18,7 @@
if(B)
B.leave_host()
qdel(B)
GLOB.carbon_list -= src
return ..()
/mob/living/carbon/handle_atom_del(atom/A)
@@ -870,7 +875,6 @@ GLOBAL_LIST_INIT(ventcrawl_machinery, list(/obj/machinery/atmospherics/unary/ven
unEquip(I)
I.dropped()
return
return 1
else
to_chat(src, "<span class='warning'>You fail to remove [I]!</span>")
@@ -12,7 +12,7 @@
visible_message("<span class='warning'>[src] catches [AM]!</span>")
throw_mode_off()
return TRUE
..()
return ..()
/mob/living/carbon/water_act(volume, temperature, source, method = REAGENT_TOUCH)
. = ..()
@@ -41,6 +41,7 @@
sync_organ_dna(1)
UpdateAppearance()
GLOB.human_list += src
/mob/living/carbon/human/OpenCraftingMenu()
handcrafting.ui_interact(src)
@@ -60,6 +61,7 @@
SSmobs.cubemonkeys -= src
QDEL_LIST(bodyparts)
splinted_limbs.Cut()
GLOB.human_list -= src
/mob/living/carbon/human/dummy
real_name = "Test Dummy"
+1 -1
View File
@@ -138,7 +138,7 @@
span = mind.speech_span
if((COMIC in mutations) \
|| (locate(/obj/item/organ/internal/cyberimp/brain/clown_voice) in internal_organs) \
|| GetComponent(/datum/component/jestosterone))
|| HAS_TRAIT(src, TRAIT_JESTER))
span = "sans"
if(WINGDINGS in mutations)
@@ -636,12 +636,11 @@
H.mutations.Add(COMIC)
H.equip_to_slot_or_del(new /obj/item/reagent_containers/food/drinks/bottle/bottleofbanana(H), slot_r_store)
H.equip_to_slot_or_del(new /obj/item/bikehorn(H), slot_l_store)
H.AddComponent(/datum/component/waddling)
H.AddElement(/datum/element/waddling)
/datum/species/golem/bananium/on_species_loss(mob/living/carbon/C)
. = ..()
GET_COMPONENT_FROM(waddling, /datum/component/waddling, C)
waddling.Destroy()
C.RemoveElement(/datum/element/waddling)
/datum/species/golem/bananium/get_random_name()
var/clown_name = pick(GLOB.clown_names)
@@ -39,10 +39,10 @@
/datum/action/innate/shadow/darkvision/Activate()
var/mob/living/carbon/human/H = owner
if(!H.vision_type)
H.vision_type = new /datum/vision_override/nightvision
H.set_sight(/datum/vision_override/nightvision)
to_chat(H, "<span class='notice'>You adjust your vision to pierce the darkness.</span>")
else
H.vision_type = null
H.set_sight(null)
to_chat(H, "<span class='notice'>You adjust your vision to recognize the shadows.</span>")
/datum/species/shadow/on_species_gain(mob/living/carbon/human/H)
+9 -11
View File
@@ -122,7 +122,7 @@
var/O2_partialpressure = (breath.oxygen/breath.total_moles())*breath_pressure
var/Toxins_partialpressure = (breath.toxins/breath.total_moles())*breath_pressure
var/CO2_partialpressure = (breath.carbon_dioxide/breath.total_moles())*breath_pressure
var/SA_partialpressure = (breath.sleeping_agent/breath.total_moles())*breath_pressure
//OXYGEN
if(O2_partialpressure < safe_oxy_min) //Not enough oxygen
@@ -168,16 +168,14 @@
clear_alert("too_much_tox")
//TRACE GASES
if(breath.trace_gases.len)
for(var/datum/gas/sleeping_agent/SA in breath.trace_gases)
var/SA_partialpressure = (SA.moles/breath.total_moles())*breath_pressure
if(SA_partialpressure > SA_para_min)
Paralyse(3)
if(SA_partialpressure > SA_sleep_min)
AdjustSleeping(2, bound_lower = 0, bound_upper = 10)
else if(SA_partialpressure > 0.01)
if(prob(20))
emote(pick("giggle","laugh"))
if(breath.sleeping_agent)
if(SA_partialpressure > SA_para_min)
Paralyse(3)
if(SA_partialpressure > SA_sleep_min)
AdjustSleeping(2, bound_lower = 0, bound_upper = 10)
else if(SA_partialpressure > 0.01)
if(prob(20))
emote(pick("giggle","laugh"))
//BREATH TEMPERATURE
handle_breath_temperature(breath)
+3 -3
View File
@@ -740,7 +740,8 @@
clear_alert("weightless")
else
throw_alert("weightless", /obj/screen/alert/weightless)
float(!has_gravity)
if(!flying)
float(!has_gravity)
/mob/living/proc/float(on)
if(throwing)
@@ -825,8 +826,7 @@
spawn_dust()
gib()
/mob/living/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect, end_pixel_y)
end_pixel_y = get_standard_pixel_y_offset(lying)
/mob/living/do_attack_animation(atom/A, visual_effect_icon, obj/item/used_item, no_effect)
if(!used_item)
used_item = get_active_hand()
..()
+2 -1
View File
@@ -336,7 +336,8 @@ proc/get_radio_key_from_channel(var/channel)
var/datum/multilingual_say_piece/S = message_pieces // Yay BYOND's hilarious typecasting
S.speaking.broadcast(src, S.message)
return 1
// Log it here since it skips the default way say handles it
create_log(SAY_LOG, "(whisper) '[message]'")
whisper_say(message_pieces)
// for weird circumstances where you're inside an atom that is also you, like pai's
+1 -1
View File
@@ -34,7 +34,7 @@
spawn(10)
explosion(src.loc, 3, 6, 12, 15)
for(var/obj/machinery/ai_status_display/O in world) //change status
for(var/obj/machinery/ai_status_display/O in GLOB.machines) //change status
O.mode = 2
if(istype(loc, /obj/item/aicard))
@@ -67,9 +67,6 @@
// The actual updating. It gathers the visible turfs from cameras and puts them into the appropiate lists.
/datum/camerachunk/proc/update()
set background = BACKGROUND_ENABLED
var/list/newVisibleTurfs = list()
for(var/camera in cameras)
+1 -1
View File
@@ -1,6 +1,6 @@
/mob/living/silicon/ai/Logout()
..()
for(var/obj/machinery/ai_status_display/O in world) //change status
for(var/obj/machinery/ai_status_display/O in GLOB.machines) //change status
O.mode = 0
src.view_core()
return
@@ -4,7 +4,7 @@
if(!.)
return FALSE
icon_state = "ai-crash"
for(var/obj/machinery/ai_status_display/O in world) //change status
for(var/obj/machinery/ai_status_display/O in GLOB.machines) //change status
if(atoms_share_level(O, src))
O.mode = 2
gib()
@@ -144,7 +144,7 @@
user.visible_message("<span class='warning'>\the [user] swipes [user.p_their()] ID card through [src], attempting to reboot it.</span>", "<span class='warning'>You swipe your ID card through [src], attempting to reboot it.</span>")
last_reboot = world.time / 10
var/drones = 0
for(var/mob/living/silicon/robot/drone/D in world)
for(var/mob/living/silicon/robot/drone/D in GLOB.silicon_mob_list)
if(D.key && D.client)
drones++
if(drones < config.max_maint_drones)
@@ -34,7 +34,7 @@
var/dat
dat += "<B>Maintenance Units</B><BR>"
for(var/mob/living/silicon/robot/drone/D in world)
for(var/mob/living/silicon/robot/drone/D in GLOB.silicon_mob_list)
dat += "<BR>[D.real_name] ([D.stat == 2 ? "<font color='red'>INACTIVE" : "<font color='green'>ACTIVE"]</FONT>)"
dat += "<font dize = 9><BR>Cell charge: [D.cell.charge]/[D.cell.maxcharge]."
dat += "<BR>Currently located in: [get_area(D)]."
@@ -74,7 +74,7 @@
else if(href_list["ping"])
to_chat(usr, "<span class='notice'>You issue a maintenance request for all active drones, highlighting [drone_call_area].</span>")
for(var/mob/living/silicon/robot/drone/D in world)
for(var/mob/living/silicon/robot/drone/D in GLOB.silicon_mob_list)
if(D.client && D.stat == 0)
to_chat(D, "-- Maintenance drone presence requested in: [drone_call_area].")
@@ -52,7 +52,7 @@
/obj/machinery/drone_fabricator/proc/count_drones()
var/drones = 0
for(var/mob/living/silicon/robot/drone/D in world)
for(var/mob/living/silicon/robot/drone/D in GLOB.silicon_mob_list)
if(D.key && D.client)
drones++
return drones
@@ -142,7 +142,7 @@
if(alert("Are you sure you want to respawn as a drone?", "Are you sure?", "Yes", "No") != "Yes")
return
for(var/obj/machinery/drone_fabricator/DF in world)
for(var/obj/machinery/drone_fabricator/DF in GLOB.machines)
if(DF.stat & NOPOWER || !DF.produce_drones)
continue
@@ -118,7 +118,7 @@
/mob/living/simple_animal/blob_act(obj/structure/blob/B)
adjustBruteLoss(20)
/mob/living/simple_animal/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
/mob/living/simple_animal/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect)
if(!no_effect && !visual_effect_icon && melee_damage_upper)
if(melee_damage_upper < 10)
visual_effect_icon = ATTACK_EFFECT_PUNCH
@@ -18,7 +18,7 @@
/mob/living/simple_animal/pet/penguin/Initialize(mapload)
. = ..()
AddComponent(/datum/component/waddling)
AddElement(/datum/element/waddling)
/mob/living/simple_animal/pet/penguin/emperor
name = "Emperor penguin"
@@ -123,8 +123,6 @@
if(health >= maxHealth)
to_chat(user, "<span class='warning'>[src] does not need repairing!</span>")
return
to_chat(user, "<span class='warning'>Unable to repair with the maintenance panel closed!</span>")
return
. = TRUE
if(!I.use_tool(src, user, volume = I.tool_volume))
return
@@ -60,6 +60,7 @@
/mob/living/simple_animal/hostile/poison/bees/New()
..()
generate_bee_visuals()
AddComponent(/datum/component/swarming)
/mob/living/simple_animal/hostile/poison/bees/Destroy()
beegent = null
@@ -452,6 +452,7 @@ Difficulty: Hard
else
burst_range = 3
INVOKE_ASYNC(src, .proc/burst, get_turf(src), 0.25) //melee attacks on living mobs cause it to release a fast burst if on cooldown
OpenFire()
else
devour(L)
else
@@ -90,6 +90,7 @@
/mob/living/simple_animal/hostile/asteroid/hivelordbrood/Initialize(mapload)
. = ..()
addtimer(CALLBACK(src, .proc/death), 100)
AddComponent(/datum/component/swarming)
/mob/living/simple_animal/hostile/asteroid/hivelordbrood/blood
@@ -335,7 +335,7 @@
//Jiggle the whole worm forwards towards the next segment
/mob/living/simple_animal/hostile/spaceWorm/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
/mob/living/simple_animal/hostile/spaceWorm/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect)
..()
if(previousWorm)
previousWorm.do_attack_animation(src)
@@ -349,7 +349,8 @@
icon = 'icons/mob/critter.dmi'
icon_state = "viscerator_attack"
icon_living = "viscerator_attack"
pass_flags = PASSTABLE
pass_flags = PASSTABLE | PASSMOB
a_intent = INTENT_HARM
health = 15
maxHealth = 15
obj_damage = 0
@@ -365,3 +366,7 @@
gold_core_spawnable = HOSTILE_SPAWN
del_on_death = 1
deathmessage = "is smashed into pieces!"
/mob/living/simple_animal/hostile/viscerator/Initialize(mapload)
. = ..()
AddComponent(/datum/component/swarming)
@@ -27,7 +27,7 @@
. += "<span class='warning'>[src] appears to be having trouble staying afloat!</span>"
/mob/living/simple_animal/possessed_object/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect, end_pixel_y)
/mob/living/simple_animal/possessed_object/do_attack_animation(atom/A, visual_effect_icon, used_item, no_effect)
..()
animate_ghostly_presence(src, -1, 20, 1) // Restart the floating animation after the attack animation, as it will be cancelled.

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