Tried to fix merge conflicts, hopefully worked.

This commit is contained in:
kingofkosmos
2015-04-24 21:52:36 +03:00
parent 761d31cea0
commit d9b8b146c8
17 changed files with 4905 additions and 26 deletions
@@ -0,0 +1,572 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31
/*
The broadcaster sends processed messages to all radio devices in the game. They
do not have to be headsets; intercoms and station-bounced radios suffice.
They receive their message from a server after the message has been logged.
*/
var/list/recentmessages = list() // global list of recent messages broadcasted : used to circumvent massive radio spam
var/message_delay = 0 // To make sure restarting the recentmessages list is kept in sync
/obj/machinery/telecomms/broadcaster
name = "subspace broadcaster"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "broadcaster"
desc = "A dish-shaped machine used to broadcast processed subspace signals."
density = 1
anchored = 1
use_power = 1
idle_power_usage = 25
machinetype = 5
/*heatgen = 0
delay = 7*/
circuitboard = "/obj/item/weapon/circuitboard/telecomms/broadcaster"
/obj/machinery/telecomms/broadcaster/receive_information(datum/signal/signal, obj/machinery/telecomms/machine_from)
// Don't broadcast rejected signals
if(signal.data["reject"])
return
if(signal.data["message"])
// Prevents massive radio spam
signal.data["done"] = 1 // mark the signal as being broadcasted
// Search for the original signal and mark it as done as well
var/datum/signal/original = signal.data["original"]
if(original)
original.data["done"] = 1
original.data["compression"] = signal.data["compression"]
original.data["level"] = signal.data["level"]
var/signal_message = "[signal.frequency]:[signal.data["message"]]:[signal.data["realname"]]"
if(signal_message in recentmessages)
return
recentmessages.Add(signal_message)
if(signal.data["slow"] > 0)
sleep(signal.data["slow"]) // simulate the network lag if necessary
signal.data["level"] |= listening_level
/** #### - Normal Broadcast - #### **/
if(signal.data["type"] == 0)
/* ###### Broadcast a message using signal.data ###### */
Broadcast_Message(signal.data["mob"],
signal.data["vmask"], signal.data["radio"],
signal.data["message"], signal.data["name"], signal.data["job"], signal.data["realname"],
0, signal.data["compression"], signal.data["level"], signal.frequency, signal.data["spans"],
signal.data["verb_say"], signal.data["verb_ask"], signal.data["verb_exclaim"], signal.data["verb_yell"])
/** #### - Simple Broadcast - #### **/
if(signal.data["type"] == 1)
/* ###### Broadcast a message using signal.data ###### */
Broadcast_SimpleMessage(signal.data["name"], signal.frequency,
signal.data["message"],null, null,
signal.data["compression"], listening_level)
/** #### - Artificial Broadcast - #### **/
// (Imitates a mob)
if(signal.data["type"] == 2)
/* ###### Broadcast a message using signal.data ###### */
// Parameter "data" as 4: AI can't track this person/mob
Broadcast_Message(signal.data["mob"],
signal.data["vmask"],
signal.data["radio"], signal.data["message"],
signal.data["name"], signal.data["job"],
signal.data["realname"], 4, signal.data["compression"], signal.data["level"], signal.frequency, signal.data["spans"],
signal.data["verb_say"], signal.data["verb_ask"], signal.data["verb_exclaim"], signal.data["verb_yell"])
if(!message_delay)
message_delay = 1
spawn(10)
message_delay = 0
recentmessages = list()
/* --- Do a snazzy animation! --- */
flick("broadcaster_send", src)
/obj/machinery/telecomms/broadcaster/Destroy()
// In case message_delay is left on 1, otherwise it won't reset the list and people can't say the same thing twice anymore.
if(message_delay)
message_delay = 0
..()
/*
Basically just an empty shell for receiving and broadcasting radio messages. Not
very flexible, but it gets the job done.
*/
/obj/machinery/telecomms/allinone
name = "telecommunications mainframe"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "comm_server"
desc = "A compact machine used for portable subspace telecommuniations processing."
density = 1
anchored = 1
use_power = 0
idle_power_usage = 0
machinetype = 6
//heatgen = 0
var/intercept = 0 // if nonzero, broadcasts all messages to syndicate channel
/obj/machinery/telecomms/allinone/receive_signal(datum/signal/signal)
if(!on) // has to be on to receive messages
return
if(is_freq_listening(signal)) // detect subspace signals
signal.data["done"] = 1 // mark the signal as being broadcasted
signal.data["compression"] = 0
// Search for the original signal and mark it as done as well
var/datum/signal/original = signal.data["original"]
if(original)
original.data["done"] = 1
if(signal.data["slow"] > 0)
sleep(signal.data["slow"]) // simulate the network lag if necessary
/* ###### Broadcast a message using signal.data ###### */
if(signal.frequency == SYND_FREQ) // if syndicate broadcast, just
Broadcast_Message(signal.data["mob"],
signal.data["vmask"],
signal.data["radio"], signal.data["message"],
signal.data["name"], signal.data["job"],
signal.data["realname"],, signal.data["compression"], list(0, z), signal.frequency, signal.data["spans"],
signal.data["verb_say"], signal.data["verb_ask"], signal.data["verb_exclaim"], signal.data["verb_yell"])
/**
Here is the big, bad function that broadcasts a message given the appropriate
parameters.
@param M:
Reference to the mob/speaker, stored in signal.data["mob"]
@param vmask:
Boolean value if the mob is "hiding" its identity via voice mask, stored in
signal.data["vmask"]
@param vmessage:
If specified, will display this as the message; such as "chimpering"
for monkeys if the mob is not understood. Stored in signal.data["vmessage"].
@param radio:
Reference to the radio broadcasting the message, stored in signal.data["radio"]
@param message:
The actual string message to display to mobs who understood mob M. Stored in
signal.data["message"]
@param name:
The name to display when a mob receives the message. signal.data["name"]
@param job:
The name job to display for the AI when it receives the message. signal.data["job"]
@param realname:
The "real" name associated with the mob. signal.data["realname"]
@param vname:
If specified, will use this name when mob M is not understood. signal.data["vname"]
@param data:
If specified:
1 -- Will only broadcast to intercoms
2 -- Will only broadcast to intercoms and station-bounced radios
3 -- Broadcast to syndicate frequency
4 -- AI can't track down this person. Useful for imitation broadcasts where you can't find the actual mob
@param compression:
If 0, the signal is audible
If nonzero, the signal may be partially inaudible or just complete gibberish.
@param level:
The list of Z levels that the sending radio is broadcasting to. Having 0 in the list broadcasts on all levels
@param freq
The frequency of the signal
**/
/proc/Broadcast_Message(var/atom/movable/AM,
var/vmask, var/obj/item/device/radio/radio,
var/message, var/name, var/job, var/realname,
var/data, var/compression, var/list/level, var/freq, var/list/spans,
var/verb_say, var/verb_ask, var/verb_exclaim, var/verb_yell)
message = copytext(message, 1, MAX_BROADCAST_LEN)
if(!message)
return
var/list/radios = list()
var/atom/movable/virtualspeaker/virt = PoolOrNew(/atom/movable/virtualspeaker,null)
virt.name = name
virt.job = job
virt.languages = AM.languages
virt.source = AM
virt.faketrack = data == 4 ? 1 : 0
virt.radio = radio
virt.verb_say = verb_say
virt.verb_ask = verb_ask
virt.verb_exclaim = verb_exclaim
virt.verb_yell = verb_yell
if(compression > 0)
message = Gibberish(message, compression + 40)
// --- Broadcast only to intercom devices ---
if(data == 1)
for(var/obj/item/device/radio/intercom/R in all_radios["[freq]"])
if(R.receive_range(freq, level) > -1)
radios += R
// --- Broadcast only to intercoms and station-bounced radios ---
else if(data == 2)
for(var/obj/item/device/radio/R in all_radios["[freq]"])
if(istype(R, /obj/item/device/radio/headset))
continue
if(R.receive_range(freq, level) > -1)
radios += R
// --- Broadcast to ALL radio devices ---
else
for(var/obj/item/device/radio/R in all_radios["[freq]"])
if(R.receive_range(freq, level) > -1)
radios += R
var/freqtext = num2text(freq)
for(var/obj/item/device/radio/R in all_radios["[SYND_FREQ]"]) //syndicate radios use magic that allows them to hear everything. this was already the case, now it just doesn't need the allinone anymore. solves annoying bugs that aren't worth solving.
if(R.receive_range(SYND_FREQ, list(R.z)) > -1 && freqtext in radiochannelsreverse)
radios |= R
// Get a list of mobs who can hear from the radios we collected.
var/list/receive = get_mobs_in_radio_ranges(radios) //this includes all hearers.
for(var/mob/R in receive) //Filter receiver list.
if (R.client && R.client.holder && !(R.client.prefs.chat_toggles & CHAT_RADIO)) //Adminning with 80 people on can be fun when you're trying to talk and all you can hear is radios.
receive -= R
for(var/mob/M in player_list)
if(isobserver(M) && M.client && (M.client.prefs.chat_toggles & CHAT_GHOSTRADIO))
receive |= M
var/rendered = virt.compose_message(virt, virt.languages, message, freq, spans) //Always call this on the virtualspeaker to advoid issues.
for(var/atom/movable/hearer in receive)
hearer.Hear(rendered, virt, AM.languages, message, freq, spans)
if(length(receive))
// --- This following recording is intended for research and feedback in the use of department radio channels ---
var/blackbox_msg = "[AM] [AM.say_quote(message, spans)]"
if(istype(blackbox))
switch(freq)
if(1459)
blackbox.msg_common += blackbox_msg
if(1351)
blackbox.msg_science += blackbox_msg
if(1353)
blackbox.msg_command += blackbox_msg
if(1355)
blackbox.msg_medical += blackbox_msg
if(1357)
blackbox.msg_engineering += blackbox_msg
if(1359)
blackbox.msg_security += blackbox_msg
if(1441)
blackbox.msg_deathsquad += blackbox_msg
if(1213)
blackbox.msg_syndicate += blackbox_msg
if(1349)
blackbox.msg_service += blackbox_msg
if(1347)
blackbox.msg_cargo += blackbox_msg
else
blackbox.messages += blackbox_msg
spawn(50)
PlaceInPool(virt)
/proc/Broadcast_SimpleMessage(var/source, var/frequency, var/text, var/data, var/mob/M, var/compression, var/level)
/* ###### Prepare the radio connection ###### */
if(!M)
var/mob/living/carbon/human/H = new
M = H
var/datum/radio_frequency/connection = radio_controller.return_frequency(frequency)
var/display_freq = connection.frequency
var/list/receive = list()
// --- Broadcast only to intercom devices ---
if(data == 1)
for (var/obj/item/device/radio/intercom/R in connection.devices["[RADIO_CHAT]"])
var/turf/position = get_turf(R)
if(position && position.z == level)
receive |= R.send_hear(display_freq, level)
// --- Broadcast only to intercoms and station-bounced radios ---
else if(data == 2)
for (var/obj/item/device/radio/R in connection.devices["[RADIO_CHAT]"])
if(istype(R, /obj/item/device/radio/headset))
continue
var/turf/position = get_turf(R)
if(position && position.z == level)
receive |= R.send_hear(display_freq)
// --- Broadcast to syndicate radio! ---
else if(data == 3)
var/datum/radio_frequency/syndicateconnection = radio_controller.return_frequency(SYND_FREQ)
for (var/obj/item/device/radio/R in syndicateconnection.devices["[RADIO_CHAT]"])
var/turf/position = get_turf(R)
if(position && position.z == level)
receive |= R.send_hear(SYND_FREQ)
// --- Broadcast to ALL radio devices ---
else
for (var/obj/item/device/radio/R in connection.devices["[RADIO_CHAT]"])
var/turf/position = get_turf(R)
if(position && position.z == level)
receive |= R.send_hear(display_freq)
/* ###### Organize the receivers into categories for displaying the message ###### */
// Understood the message:
var/list/heard_normal = list() // normal message
// Did not understand the message:
var/list/heard_garbled = list() // garbled message (ie "f*c* **u, **i*er!")
var/list/heard_gibberish= list() // completely screwed over message (ie "F%! (O*# *#!<>&**%!")
for (var/mob/R in receive)
/* --- Loop through the receivers and categorize them --- */
if (R.client && !(R.client.prefs.chat_toggles & CHAT_RADIO)) //Adminning with 80 people on can be fun when you're trying to talk and all you can hear is radios.
continue
// --- Check for compression ---
if(compression > 0)
heard_gibberish += R
continue
// --- Can understand the speech ---
if (R.languages & M.languages)
heard_normal += R
// --- Can't understand the speech ---
else
// - Just display a garbled message -
heard_garbled += R
/* ###### Begin formatting and sending the message ###### */
if (length(heard_normal) || length(heard_garbled) || length(heard_gibberish))
/* --- Some miscellaneous variables to format the string output --- */
var/part_a = "<span class='radio'><span class='name'>" // goes in the actual output
var/freq_text // the name of the channel
// --- Set the name of the channel ---
switch(display_freq)
if(SYND_FREQ)
freq_text = "#unkn"
if(COMM_FREQ)
freq_text = "Command"
if(SCI_FREQ)
freq_text = "Science"
if(MED_FREQ)
freq_text = "Medical"
if(ENG_FREQ)
freq_text = "Engineering"
if(SEC_FREQ)
freq_text = "Security"
if(SERV_FREQ)
freq_text = "Service"
if(SUPP_FREQ)
freq_text = "Supply"
if(AIPRIV_FREQ)
freq_text = "AI Private"
//There's probably a way to use the list var of channels in code\game\communications.dm to make the dept channels non-hardcoded, but I wasn't in an experimentive mood. --NEO
// --- If the frequency has not been assigned a name, just use the frequency as the name ---
if(!freq_text)
freq_text = format_frequency(display_freq)
// --- Some more pre-message formatting ---
var/part_b_extra = ""
if(data == 3) // intercepted radio message
part_b_extra = " <i>(Intercepted)</i>"
// Create a radio headset for the sole purpose of using its icon
var/obj/item/device/radio/headset/radio = new
var/part_b = "</span><b> \icon[radio]\[[freq_text]\][part_b_extra]</b> <span class='message'>"
var/part_c = "</span></span>"
if (display_freq==SYND_FREQ)
part_a = "<span class='syndradio'><span class='name'>"
else if (display_freq==COMM_FREQ)
part_a = "<span class='comradio'><span class='name'>"
else if (display_freq==SCI_FREQ)
part_a = "<span class='sciradio'><span class='name'>"
else if (display_freq==MED_FREQ)
part_a = "<span class='medradio'><span class='name'>"
else if (display_freq==ENG_FREQ)
part_a = "<span class='engradio'><span class='name'>"
else if (display_freq==SEC_FREQ)
part_a = "<span class='secradio'><span class='name'>"
else if (display_freq==SERV_FREQ)
part_a = "<span class='servradio'><span class='name'>"
else if (display_freq==SUPP_FREQ)
part_a = "<span class='suppradio'><span class='name'>"
else if (display_freq==CENTCOM_FREQ)
part_a = "<span class='centcomradio'><span class='name'>"
else if (display_freq==AIPRIV_FREQ)
part_a = "<span class='aiprivradio'><span class='name'>"
// --- This following recording is intended for research and feedback in the use of department radio channels ---
var/part_blackbox_b = "</span><b> \[[freq_text]\]</b> <span class='message'>"
var/blackbox_msg = "[part_a][source][part_blackbox_b]\"[text]\"[part_c]"
//var/blackbox_admin_msg = "[part_a][M.name] (Real name: [M.real_name])[part_blackbox_b][quotedmsg][part_c]"
//BR.messages_admin += blackbox_admin_msg
if(istype(blackbox))
switch(display_freq)
if(1459)
blackbox.msg_common += blackbox_msg
if(1351)
blackbox.msg_science += blackbox_msg
if(1353)
blackbox.msg_command += blackbox_msg
if(1355)
blackbox.msg_medical += blackbox_msg
if(1357)
blackbox.msg_engineering += blackbox_msg
if(1359)
blackbox.msg_security += blackbox_msg
if(1441)
blackbox.msg_deathsquad += blackbox_msg
if(1213)
blackbox.msg_syndicate += blackbox_msg
if(1349)
blackbox.msg_service += blackbox_msg
if(1347)
blackbox.msg_cargo += blackbox_msg
else
blackbox.messages += blackbox_msg
//End of research and feedback code.
/* ###### Send the message ###### */
/* --- Process all the mobs that heard the voice normally (understood) --- */
if (length(heard_normal))
var/rendered = "[part_a][source][part_b]\"[text]\"[part_c]"
for (var/mob/R in heard_normal)
R.show_message(rendered, 2)
/* --- Process all the mobs that heard a garbled voice (did not understand) --- */
// Displays garbled message (ie "f*c* **u, **i*er!")
if (length(heard_garbled))
var/quotedmsg = "\"[stars(text)]\""
var/rendered = "[part_a][source][part_b][quotedmsg][part_c]"
for (var/mob/R in heard_garbled)
R.show_message(rendered, 2)
/* --- Complete gibberish. Usually happens when there's a compressed message --- */
if (length(heard_gibberish))
var/quotedmsg = "\"[Gibberish(text, compression + 50)]\""
var/rendered = "[part_a][Gibberish(source, compression + 50)][part_b][quotedmsg][part_c]"
for (var/mob/R in heard_gibberish)
R.show_message(rendered, 2)
//Use this to test if an obj can communicate with a Telecommunications Network
/atom/proc/test_telecomms()
var/datum/signal/signal = src.telecomms_process()
var/turf/position = get_turf(src)
return (position.z in signal.data["level"] && signal.data["done"])
/atom/proc/telecomms_process()
// First, we want to generate a new radio signal
var/datum/signal/signal = new
signal.transmission_method = 2 // 2 would be a subspace transmission.
var/turf/pos = get_turf(src)
// --- Finally, tag the actual signal with the appropriate values ---
signal.data = list(
"slow" = 0, // how much to sleep() before broadcasting - simulates net lag
"message" = "TEST",
"compression" = rand(45, 50), // If the signal is compressed, compress our message too.
"traffic" = 0, // dictates the total traffic sum that the signal went through
"type" = 4, // determines what type of radio input it is: test broadcast
"reject" = 0,
"done" = 0,
"level" = pos.z // The level it is being broadcasted at.
)
signal.frequency = 1459// Common channel
//#### Sending the signal to all subspace receivers ####//
for(var/obj/machinery/telecomms/receiver/R in telecomms_list)
R.receive_signal(signal)
sleep(rand(10,25))
return signal
+232
View File
@@ -0,0 +1,232 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31
/obj/machinery/computer/telecomms/server
name = "telecommunications server monitoring console"
icon_state = "comm_logs"
var/screen = 0 // the screen number:
var/list/servers = list() // the servers located by the computer
var/obj/machinery/telecomms/server/SelectedServer
var/network = "NULL" // the network to probe
var/temp = "" // temporary feedback messages
var/universal_translate = 0 // set to 1 if it can translate nonhuman speech
req_access = list(access_tcomsat)
circuit = "/obj/item/weapon/circuitboard/comm_server"
/obj/machinery/computer/telecomms/server/attack_hand(mob/user as mob)
if(..())
return
user.set_machine(src)
var/dat = "<TITLE>Telecommunication Server Monitor</TITLE><center><b>Telecommunications Server Monitor</b></center>"
switch(screen)
// --- Main Menu ---
if(0)
dat += "<br>[temp]<br>"
dat += "<br>Current Network: <a href='?src=\ref[src];network=1'>[network]</a><br>"
if(servers.len)
dat += "<br>Detected Telecommunication Servers:<ul>"
for(var/obj/machinery/telecomms/T in servers)
dat += "<li><a href='?src=\ref[src];viewserver=[T.id]'>\ref[T] [T.name]</a> ([T.id])</li>"
dat += "</ul>"
dat += "<br><a href='?src=\ref[src];operation=release'>\[Flush Buffer\]</a>"
else
dat += "<br>No servers detected. Scan for servers: <a href='?src=\ref[src];operation=scan'>\[Scan\]</a>"
// --- Viewing Server ---
if(1)
dat += "<br>[temp]<br>"
dat += "<center><a href='?src=\ref[src];operation=mainmenu'>\[Main Menu\]</a> <a href='?src=\ref[src];operation=refresh'>\[Refresh\]</a></center>"
dat += "<br>Current Network: [network]"
dat += "<br>Selected Server: [SelectedServer.id]"
if(SelectedServer.totaltraffic >= 1024)
dat += "<br>Total recorded traffic: [round(SelectedServer.totaltraffic / 1024)] Terrabytes<br><br>"
else
dat += "<br>Total recorded traffic: [SelectedServer.totaltraffic] Gigabytes<br><br>"
dat += "Stored Logs: <ol>"
var/i = 0
for(var/datum/comm_log_entry/C in SelectedServer.log_entries)
i++
// If the log is a speech file
if(C.input_type == "Speech File")
dat += "<li><font color = #008F00>[C.name]</font color> <font color = #FF0000><a href='?src=\ref[src];delete=[i]'>\[X\]</a></font color><br>"
// -- Determine race of orator --
var/race // The actual race of the mob
var/language = "Human" // MMIs, pAIs, Cyborgs and humans all speak Human
var/mobtype = C.parameters["mobtype"]
var/list/humans = typesof(/mob/living/carbon/human, /mob/living/carbon/brain)
var/list/monkeys = typesof(/mob/living/carbon/monkey)
var/list/silicons = typesof(/mob/living/silicon)
var/list/slimes = typesof(/mob/living/simple_animal/slime)
var/list/animals = typesof(/mob/living/simple_animal)
if(mobtype in humans)
race = "Human"
language = race
else if(mobtype in slimes) // NT knows a lot about slimes, but not aliens. Can identify slimes
race = "Slime"
language = race
else if(mobtype in monkeys)
race = "Monkey"
language = race
else if(mobtype in silicons || C.parameters["job"] == "AI") // sometimes M gets deleted prematurely for AIs... just check the job
race = "Artificial Life"
language = race
else if(istype(mobtype, /obj))
race = "Machinery"
language = race
else if(mobtype in animals)
race = "Domestic Animal"
language = race
else
race = "<i>Unidentifiable</i>"
language = race
// -- If the orator is a human, or universal translate is active, OR mob has universal speech on --
if(language == "Human" || universal_translate || C.parameters["uspeech"])
dat += "<u><font color = #18743E>Data type</font color></u>: [C.input_type]<br>"
dat += "<u><font color = #18743E>Source</font color></u>: [C.parameters["name"]] (Job: [C.parameters["job"]])<br>"
dat += "<u><font color = #18743E>Class</font color></u>: [race]<br>"
dat += "<u><font color = #18743E>Contents</font color></u>: \"[C.parameters["message"]]\"<br>"
// -- Orator is not human and universal translate not active --
else
dat += "<u><font color = #18743E>Data type</font color></u>: Audio File<br>"
dat += "<u><font color = #18743E>Source</font color></u>: <i>Unidentifiable</i><br>"
dat += "<u><font color = #18743E>Class</font color></u>: [race]<br>"
dat += "<u><font color = #18743E>Contents</font color></u>: <i>Unintelligble</i><br>"
dat += "</li><br>"
else if(C.input_type == "Execution Error")
dat += "<li><font color = #990000>[C.name]</font color> <font color = #FF0000><a href='?src=\ref[src];delete=[i]'>\[X\]</a></font color><br>"
dat += "<u><font color = #787700>Output</font color></u>: \"[C.parameters["message"]]\"<br>"
dat += "</li><br>"
dat += "</ol>"
user << browse(dat, "window=comm_monitor;size=575x400")
onclose(user, "server_control")
temp = ""
return
/obj/machinery/computer/telecomms/server/Topic(href, href_list)
if(..())
return
add_fingerprint(usr)
usr.set_machine(src)
if(href_list["viewserver"])
screen = 1
for(var/obj/machinery/telecomms/T in servers)
if(T.id == href_list["viewserver"])
SelectedServer = T
break
if(href_list["operation"])
switch(href_list["operation"])
if("release")
servers = list()
screen = 0
if("mainmenu")
screen = 0
if("scan")
if(servers.len > 0)
temp = "<font color = #D70B00>- FAILED: CANNOT PROBE WHEN BUFFER FULL -</font color>"
else
for(var/obj/machinery/telecomms/server/T in range(25, src))
if(T.network == network)
servers.Add(T)
if(!servers.len)
temp = "<font color = #D70B00>- FAILED: UNABLE TO LOCATE SERVERS IN \[[network]\] -</font color>"
else
temp = "<font color = #336699>- [servers.len] SERVERS PROBED & BUFFERED -</font color>"
screen = 0
if(href_list["delete"])
if(!src.allowed(usr) && !emagged)
usr << "<span class='danger'>ACCESS DENIED.</span>"
return
if(SelectedServer)
var/datum/comm_log_entry/D = SelectedServer.log_entries[text2num(href_list["delete"])]
temp = "<font color = #336699>- DELETED ENTRY: [D.name] -</font color>"
SelectedServer.log_entries.Remove(D)
del(D)
else
temp = "<font color = #D70B00>- FAILED: NO SELECTED MACHINE -</font color>"
if(href_list["network"])
var/newnet = stripped_input(usr, "Which network do you want to view?", "Comm Monitor", network)
if(newnet && ((usr in range(1, src) || issilicon(usr))))
if(length(newnet) > 15)
temp = "<font color = #D70B00>- FAILED: NETWORK TAG STRING TOO LENGHTLY -</font color>"
else
network = newnet
screen = 0
servers = list()
temp = "<font color = #336699>- NEW NETWORK TAG SET IN ADDRESS \[[network]\] -</font color>"
updateUsrDialog()
return
/obj/machinery/computer/telecomms/server/attackby()
..()
src.updateUsrDialog()
return
/obj/machinery/computer/telecomms/server/emag_act(mob/user as mob)
if(!emagged)
playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1)
emagged = 1
user << "<span class='notice'>You you disable the security protocols.</span>"
+187
View File
@@ -0,0 +1,187 @@
// ### Preset machines ###
//Relay
/obj/machinery/telecomms/relay/preset
network = "tcommsat"
/obj/machinery/telecomms/relay/preset/station
id = "Station Relay"
listening_level = 1
autolinkers = list("s_relay")
/obj/machinery/telecomms/relay/preset/telecomms
id = "Telecomms Relay"
autolinkers = list("relay")
/obj/machinery/telecomms/relay/preset/mining
id = "Mining Relay"
autolinkers = list("m_relay")
/obj/machinery/telecomms/relay/preset/ruskie
id = "Ruskie Relay"
hide = 1
toggled = 0
autolinkers = list("r_relay")
//HUB
/obj/machinery/telecomms/hub/preset
id = "Hub"
network = "tcommsat"
autolinkers = list("hub", "relay", "s_relay", "m_relay", "r_relay", "science", "medical",
"supply", "service", "common", "command", "engineering", "security",
"receiverA", "receiverB", "broadcasterA", "broadcasterB")
//Receivers
//--PRESET LEFT--//
/obj/machinery/telecomms/receiver/preset_left
id = "Receiver A"
network = "tcommsat"
autolinkers = list("receiverA") // link to relay
freq_listening = list(1351, 1355, 1347, 1349) // science, medical, supply, service
//--PRESET RIGHT--//
/obj/machinery/telecomms/receiver/preset_right
id = "Receiver B"
network = "tcommsat"
autolinkers = list("receiverB") // link to relay
freq_listening = list(1353, 1357, 1359) //command, engineering, security
//Common and other radio frequencies for people to freely use
New()
for(var/i = 1441, i < 1489, i += 2)
freq_listening |= i
..()
//Buses
/obj/machinery/telecomms/bus/preset_one
id = "Bus 1"
network = "tcommsat"
freq_listening = list(1351, 1355)
autolinkers = list("processor1", "science", "medical")
/obj/machinery/telecomms/bus/preset_two
id = "Bus 2"
network = "tcommsat"
freq_listening = list(1347,1349)
autolinkers = list("processor2", "supply", "service")
/obj/machinery/telecomms/bus/preset_three
id = "Bus 3"
network = "tcommsat"
freq_listening = list(1359, 1353)
autolinkers = list("processor3", "security", "command")
/obj/machinery/telecomms/bus/preset_four
id = "Bus 4"
network = "tcommsat"
freq_listening = list(1357)
autolinkers = list("processor4", "engineering", "common")
/obj/machinery/telecomms/bus/preset_four/New()
for(var/i = 1441, i < 1489, i += 2)
freq_listening |= i
..()
//Processors
/obj/machinery/telecomms/processor/preset_one
id = "Processor 1"
network = "tcommsat"
autolinkers = list("processor1") // processors are sort of isolated; they don't need backward links
/obj/machinery/telecomms/processor/preset_two
id = "Processor 2"
network = "tcommsat"
autolinkers = list("processor2")
/obj/machinery/telecomms/processor/preset_three
id = "Processor 3"
network = "tcommsat"
autolinkers = list("processor3")
/obj/machinery/telecomms/processor/preset_four
id = "Processor 4"
network = "tcommsat"
autolinkers = list("processor4")
//Servers
/obj/machinery/telecomms/server/presets
network = "tcommsat"
/obj/machinery/telecomms/server/presets/New()
..()
name = id
/obj/machinery/telecomms/server/presets/science
id = "Science Server"
freq_listening = list(1351)
autolinkers = list("science")
/obj/machinery/telecomms/server/presets/medical
id = "Medical Server"
freq_listening = list(1355)
autolinkers = list("medical")
/obj/machinery/telecomms/server/presets/supply
id = "Supply Server"
freq_listening = list(1347)
autolinkers = list("supply")
/obj/machinery/telecomms/server/presets/service
id = "Service Server"
freq_listening = list(1349)
autolinkers = list("service")
/obj/machinery/telecomms/server/presets/common
id = "Common Server"
freq_listening = list()
autolinkers = list("common")
//Common and other radio frequencies for people to freely use
// 1441 to 1489
/obj/machinery/telecomms/server/presets/common/New()
for(var/i = 1441, i < 1489, i += 2)
freq_listening |= i
..()
/obj/machinery/telecomms/server/presets/command
id = "Command Server"
freq_listening = list(1353)
autolinkers = list("command")
/obj/machinery/telecomms/server/presets/engineering
id = "Engineering Server"
freq_listening = list(1357)
autolinkers = list("engineering")
/obj/machinery/telecomms/server/presets/security
id = "Security Server"
freq_listening = list(1359)
autolinkers = list("security")
//Broadcasters
//--PRESET LEFT--//
/obj/machinery/telecomms/broadcaster/preset_left
id = "Broadcaster A"
network = "tcommsat"
autolinkers = list("broadcasterA")
//--PRESET RIGHT--//
/obj/machinery/telecomms/broadcaster/preset_right
id = "Broadcaster B"
network = "tcommsat"
autolinkers = list("broadcasterB")
@@ -0,0 +1,136 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32
/*
Telecomms monitor tracks the overall trafficing of a telecommunications network
and displays a heirarchy of linked machines.
*/
/obj/machinery/computer/telecomms/monitor
name = "telecommunications monitoring console"
icon_state = "comm_monitor"
var/screen = 0 // the screen number:
var/list/machinelist = list() // the machines located by the computer
var/obj/machinery/telecomms/SelectedMachine
var/network = "NULL" // the network to probe
var/temp = "" // temporary feedback messages
circuit = "/obj/item/weapon/circuitboard/comm_monitor"
/obj/machinery/computer/telecomms/monitor/attack_hand(mob/user as mob)
if(..())
return
user.set_machine(src)
var/dat = "<TITLE>Telecommunications Monitor</TITLE><center><b>Telecommunications Monitor</b></center>"
switch(screen)
// --- Main Menu ---
if(0)
dat += "<br>[temp]<br><br>"
dat += "<br>Current Network: <a href='?src=\ref[src];network=1'>[network]</a><br>"
if(machinelist.len)
dat += "<br>Detected Network Entities:<ul>"
for(var/obj/machinery/telecomms/T in machinelist)
dat += "<li><a href='?src=\ref[src];viewmachine=[T.id]'>\ref[T] [T.name]</a> ([T.id])</li>"
dat += "</ul>"
dat += "<br><a href='?src=\ref[src];operation=release'>\[Flush Buffer\]</a>"
else
dat += "<a href='?src=\ref[src];operation=probe'>\[Probe Network\]</a>"
// --- Viewing Machine ---
if(1)
dat += "<br>[temp]<br>"
dat += "<center><a href='?src=\ref[src];operation=mainmenu'>\[Main Menu\]</a></center>"
dat += "<br>Current Network: [network]<br>"
dat += "Selected Network Entity: [SelectedMachine.name] ([SelectedMachine.id])<br>"
dat += "Linked Entities: <ol>"
for(var/obj/machinery/telecomms/T in SelectedMachine.links)
if(!T.hide)
dat += "<li><a href='?src=\ref[src];viewmachine=[T.id]'>\ref[T.id] [T.name]</a> ([T.id])</li>"
dat += "</ol>"
user << browse(dat, "window=comm_monitor;size=575x400")
onclose(user, "server_control")
temp = ""
return
/obj/machinery/computer/telecomms/monitor/Topic(href, href_list)
if(..())
return
add_fingerprint(usr)
usr.set_machine(src)
if(href_list["viewmachine"])
screen = 1
for(var/obj/machinery/telecomms/T in machinelist)
if(T.id == href_list["viewmachine"])
SelectedMachine = T
break
if(href_list["operation"])
switch(href_list["operation"])
if("release")
machinelist = list()
screen = 0
if("mainmenu")
screen = 0
if("probe")
if(machinelist.len > 0)
temp = "<font color = #D70B00>- FAILED: CANNOT PROBE WHEN BUFFER FULL -</font color>"
else
for(var/obj/machinery/telecomms/T in range(25, src))
if(T.network == network)
machinelist.Add(T)
if(!machinelist.len)
temp = "<font color = #D70B00>- FAILED: UNABLE TO LOCATE NETWORK ENTITIES IN \[[network]\] -</font color>"
else
temp = "<font color = #336699>- [machinelist.len] ENTITIES LOCATED & BUFFERED -</font color>"
screen = 0
if(href_list["network"])
var/newnet = stripped_input(usr, "Which network do you want to view?", "Comm Monitor", network)
if(newnet && ((usr in range(1, src) || issilicon(usr))))
if(length(newnet) > 15)
temp = "<font color = #D70B00>- FAILED: NETWORK TAG STRING TOO LENGHTLY -</font color>"
else
network = newnet
screen = 0
machinelist = list()
temp = "<font color = #336699>- NEW NETWORK TAG SET IN ADDRESS \[[network]\] -</font color>"
updateUsrDialog()
return
/obj/machinery/computer/telecomms/monitor/attackby()
..()
src.updateUsrDialog()
return
/obj/machinery/computer/telecomms/monitor/emag_act(mob/user as mob)
if(!emagged)
playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1)
emagged = 1
user << "<span class='notice'>You you disable the security protocols.</span>"
@@ -0,0 +1,290 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32
/obj/machinery/computer/telecomms/traffic
name = "telecommunications traffic control console"
icon_state = "computer_generic"
var/screen = 0 // the screen number:
var/list/servers = list() // the servers located by the computer
var/mob/editingcode
var/mob/lasteditor
var/list/viewingcode = list()
var/obj/machinery/telecomms/server/SelectedServer
var/network = "NULL" // the network to probe
var/temp = "" // temporary feedback messages
var/storedcode = "" // code stored
var/obj/item/weapon/card/id/auth = null
var/list/access_log = list()
var/process = 0
circuit = "/obj/item/weapon/circuitboard/comm_traffic"
req_access = list(access_tcomsat)
/obj/machinery/computer/telecomms/traffic/proc/stop_editing()
if(editingcode)
if(editingcode.client)
winshow(editingcode, "Telecomms IDE", 0) // hide the window!
editingcode.unset_machine()
editingcode = null
/obj/machinery/computer/telecomms/traffic/process()
if(stat & (NOPOWER|BROKEN))
stop_editing()
return
if(editingcode && editingcode.machine != src)
stop_editing()
return
if(!editingcode)
if(length(viewingcode) > 0)
editingcode = pick(viewingcode)
viewingcode.Remove(editingcode)
return
process = !process
if(!process)
return
// loop if there's someone manning the keyboard
if(!editingcode.client)
stop_editing()
return
// For the typer, the input is enabled. Buffer the typed text
storedcode = "[winget(editingcode, "tcscode", "text")]"
winset(editingcode, "tcscode", "is-disabled=false")
// If the player's not manning the keyboard anymore, adjust everything
if(!in_range(editingcode, src) && !issilicon(editingcode) || editingcode.machine != src)
winshow(editingcode, "Telecomms IDE", 0) // hide the window!
editingcode = null
return
// For other people viewing the typer type code, the input is disabled and they can only view the code
// (this is put in place so that there's not any magical shenanigans with 50 people inputting different code all at once)
if(length(viewingcode))
// This piece of code is very important - it escapes quotation marks so string aren't cut off by the input element
var/showcode = replacetext(storedcode, "\\\"", "\\\\\"")
showcode = replacetext(storedcode, "\"", "\\\"")
for(var/mob/M in viewingcode)
if( (M.machine == src && in_range(M, src) ) || issilicon(M))
winset(M, "tcscode", "is-disabled=true")
winset(M, "tcscode", "text=\"[showcode]\"")
else
viewingcode.Remove(M)
winshow(M, "Telecomms IDE", 0) // hide the windows
/obj/machinery/computer/telecomms/traffic/attack_hand(mob/user as mob)
if(..())
return
user.set_machine(src)
var/dat = "<TITLE>Telecommunication Traffic Control</TITLE><center><b>Telecommunications Traffic Control</b></center>"
dat += "<br><b><font color='[(auth ? "green" : "red")]'>[(auth ? "AUTHED" : "NOT AUTHED")]:</font></b> <A href='?src=\ref[src];auth=1'>[(!auth ? "Insert ID" : auth)]</A><BR>"
dat += "<A href='?src=\ref[src];print=1'>View System Log</A><HR>"
if(issilicon(user) || auth)
switch(screen)
// --- Main Menu ---
if(0)
dat += "<br>[temp]<br>"
dat += "<br>Current Network: <a href='?src=\ref[src];network=1'>[network]</a><br>"
if(servers.len)
dat += "<br>Detected Telecommunication Servers:<ul>"
for(var/obj/machinery/telecomms/T in servers)
dat += "<li><a href='?src=\ref[src];viewserver=[T.id]'>\ref[T] [T.name]</a> ([T.id])</li>"
dat += "</ul>"
dat += "<br><a href='?src=\ref[src];operation=release'>\[Flush Buffer\]</a>"
else
dat += "<br>No servers detected. Scan for servers: <a href='?src=\ref[src];operation=scan'>\[Scan\]</a>"
// --- Viewing Server ---
if(1)
if(SelectedServer)
dat += "<br>[temp]<br>"
dat += "<center><a href='?src=\ref[src];operation=mainmenu'>\[Main Menu\]</a> <a href='?src=\ref[src];operation=refresh'>\[Refresh\]</a></center>"
dat += "<br>Current Network: [network]"
dat += "<br>Selected Server: [SelectedServer.id]<br><br>"
dat += "<br><a href='?src=\ref[src];operation=editcode'>\[Edit Code\]</a>"
dat += "<br>Signal Execution: "
if(SelectedServer.autoruncode)
dat += "<a href='?src=\ref[src];operation=togglerun'>ALWAYS</a>"
else
dat += "<a href='?src=\ref[src];operation=togglerun'>NEVER</a>"
else
screen = 0
return
user << browse(dat, "window=traffic_control;size=575x400")
onclose(user, "server_control")
temp = ""
return
/obj/machinery/computer/telecomms/traffic/proc/create_log(var/entry, var/mob/user)
var/id = null
if(issilicon(user))
id = "System Administrator"
else
if(auth)
id = "[auth.registered_name] ([auth.assignment])"
else
ERROR("There is a null auth while the user isn't a silicon! ([user.name], [user.type])")
return
access_log += "\[[get_timestamp()]\] [id] [entry]"
/obj/machinery/computer/telecomms/traffic/proc/print_logs()
. = "<center><h2>Traffic Control Telecomms System Log</h2></center><HR>"
for(var/entry in access_log)
. += entry + "<BR>"
return .
/obj/machinery/computer/telecomms/traffic/Topic(href, href_list)
if(..())
return
add_fingerprint(usr)
usr.set_machine(src)
if(href_list["auth"])
if(iscarbon(usr))
var/mob/living/carbon/C = usr
if(!auth)
var/obj/item/weapon/card/id/I = C.get_active_hand()
if(istype(I))
if(check_access(I))
C.drop_item()
I.loc = src
auth = I
create_log("has logged in.", usr)
else
create_log("has logged out.", usr)
auth.loc = src.loc
C.put_in_hands(auth)
auth = null
updateUsrDialog()
return
if(href_list["print"])
usr << browse(print_logs(), "window=traffic_logs")
return
if(!auth && !issilicon(usr) && !emagged)
usr << "<span class='danger'>ACCESS DENIED.</span>"
return
if(href_list["viewserver"])
screen = 1
for(var/obj/machinery/telecomms/T in servers)
if(T.id == href_list["viewserver"])
SelectedServer = T
create_log("selected server [T.name]", usr)
break
if(href_list["operation"])
create_log("has performed action: [href_list["operation"]].", usr)
switch(href_list["operation"])
if("release")
servers = list()
screen = 0
if("mainmenu")
screen = 0
if("scan")
if(servers.len > 0)
temp = "<font color = #D70B00>- FAILED: CANNOT PROBE WHEN BUFFER FULL -</font color>"
else
for(var/obj/machinery/telecomms/server/T in range(25, src))
if(T.network == network)
servers.Add(T)
if(!servers.len)
temp = "<font color = #D70B00>- FAILED: UNABLE TO LOCATE SERVERS IN \[[network]\] -</font color>"
else
temp = "<font color = #336699>- [servers.len] SERVERS PROBED & BUFFERED -</font color>"
screen = 0
if("editcode")
if(editingcode == usr) return
if(usr in viewingcode) return
if(!editingcode)
lasteditor = usr
editingcode = usr
winshow(editingcode, "Telecomms IDE", 1) // show the IDE
winset(editingcode, "tcscode", "is-disabled=false")
winset(editingcode, "tcscode", "text=\"\"")
var/showcode = replacetext(storedcode, "\\\"", "\\\\\"")
showcode = replacetext(storedcode, "\"", "\\\"")
winset(editingcode, "tcscode", "text=\"[showcode]\"")
else
viewingcode.Add(usr)
winshow(usr, "Telecomms IDE", 1) // show the IDE
winset(usr, "tcscode", "is-disabled=true")
winset(editingcode, "tcscode", "text=\"\"")
var/showcode = replacetext(storedcode, "\"", "\\\"")
winset(usr, "tcscode", "text=\"[showcode]\"")
if("togglerun")
SelectedServer.autoruncode = !(SelectedServer.autoruncode)
if(href_list["network"])
var/newnet = stripped_input(usr, "Which network do you want to view?", "Comm Monitor", network)
if(newnet && canAccess(usr))
if(length(newnet) > 15)
temp = "<font color = #D70B00>- FAILED: NETWORK TAG STRING TOO LENGHTLY -</font color>"
else
network = newnet
screen = 0
servers = list()
temp = "<font color = #336699>- NEW NETWORK TAG SET IN ADDRESS \[[network]\] -</font color>"
create_log("has set the network to [network].", usr)
updateUsrDialog()
return
/obj/machinery/computer/telecomms/traffic/attackby()
..()
src.updateUsrDialog()
return
/obj/machinery/computer/telecomms/traffic/emag_act(mob/user as mob)
if(!emagged)
playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1)
emagged = 1
user << "<span class='notice'>You you disable the security protocols.</span>"
/obj/machinery/computer/telecomms/traffic/proc/canAccess(var/mob/user)
if(issilicon(user) || in_range(user, src))
return 1
return 0
+15 -18
View File
@@ -54,10 +54,10 @@
if(istype(O, /obj/item/weapon/reagent_containers/glass))
if(O.reagents)
if(O.reagents.total_volume < 1)
user << "The [O] is empty."
user << "<span class='notice'>The [O] is empty.</span>"
else if(O.reagents.total_volume >= 1)
if(O.reagents.has_reagent("facid", 1))
user << "The acid chews through the balloon!"
user << "<span class='warning'>The acid chews through the balloon!</span>"
O.reagents.reaction(user)
qdel(src)
else
@@ -135,17 +135,17 @@
if (istype(A, /obj/item/toy/ammo/gun))
if (src.bullets >= 7)
user << "<span class='notice'>It's already fully loaded!</span>"
user << "<span class='warning'>It's already fully loaded!</span>"
return 1
if (A.amount_left <= 0)
user << "<span class='danger'>There are no more caps!</span>"
user << "<span class='warning'>There are no more caps!</span>"
return 1
if (A.amount_left < (7 - src.bullets))
src.bullets += A.amount_left
user << text("<span class='danger'>You reload [] cap\s!</span>", A.amount_left)
user << text("<span class='notice'>You reload [] cap\s.</span>", A.amount_left)
A.amount_left = 0
else
user << text("<span class='danger'>You reload [] cap\s!</span>", 7 - src.bullets)
user << text("<span class='notice'>You reload [] cap\s.</span>", 7 - src.bullets)
A.amount_left -= 7 - src.bullets
src.bullets = 7
A.update_icon()
@@ -227,7 +227,7 @@
..()
if(istype(W, /obj/item/toy/sword))
if(W == src)
user << "<span class='notice'>You try to attach the end of the plastic sword to... itself. You're not very smart, are you?</span>"
user << "<span class='warning'>You try to attach the end of the plastic sword to... itself. You're not very smart, are you?</span>"
if(ishuman(user))
user.adjustBrainLoss(10)
else if((W.flags & NODROP) || (flags & NODROP))
@@ -442,8 +442,6 @@
graf_rot = 270
else
graf_rot = 0
user << "<span class='notice'>You start drawing a [temp] on the [target.name]...</span>"
user << "<span class='notice'>You finish drawing [temp].</span>"
user << "<span class='notice'>You start [instant ? "spraying" : "drawing"] a [temp] on the [target.name]...</span>"
if(instant)
@@ -475,9 +473,8 @@
return
/obj/item/toy/crayon/attack(mob/M as mob, mob/user as mob)
user << "<span class='notice'>You take a [huffable ? "huff" : "bite"] of the [src.name]. Delicious!</span>"
if(edible && (M == user))
user << "<span class='notice'>You take a bite of the [src.name]. Delicious!</span>"
user << "You take a bite of the [src.name]. Delicious!"
user.nutrition += 5
if(uses)
uses -= 5
@@ -748,7 +745,7 @@ obj/item/toy/cards/deck/attack_hand(mob/user as mob)
var/choice = null
if(cards.len == 0)
src.icon_state = "deck_[deckstyle]_empty"
user << "<span class='notice'>There are no more cards to draw.</span>"
user << "<span class='warning'>There are no more cards to draw!</span>"
return
var/obj/item/toy/cards/singlecard/H = new/obj/item/toy/cards/singlecard(user.loc)
choice = cards[1]
@@ -876,7 +873,7 @@ obj/item/toy/cards/cardhand/Topic(href, href_list)
C.apply_card_vars(C,O)
C.pickup(cardUser)
cardUser.put_in_any_hand_if_possible(C)
cardUser.visible_message("[cardUser] draws a card from \his hand.", "<span class='notice'>You take the [C.cardname] from your hand.</span>")
cardUser.visible_message("<span class='notice'>[cardUser] draws a card from \his hand.</span>", "<span class='notice'>You take the [C.cardname] from your hand.</span>")
interact(cardUser)
if(src.currenthand.len < 3)
@@ -1057,7 +1054,7 @@ obj/item/toy/cards/deck/syndicate
/obj/item/toy/nuke/attack_self(mob/user)
if (cooldown < world.time)
cooldown = world.time + 1800 //3 minutes
user.visible_message("[user] presses a button on [src].", "<span class='notice'>You activate [src], it plays a loud noise!</span>", "<span class='italics'>You hear the click of a button.</span>")
user.visible_message("<span class='warning'>[user] presses a button on [src].</span>", "<span class='notice'>You activate [src], it plays a loud noise!</span>", "<span class='italics'>You hear the click of a button.</span>")
spawn(5) //gia said so
icon_state = "nuketoy"
playsound(src, 'sound/machines/Alarm.ogg', 100, 0, surround = 0)
@@ -1075,7 +1072,7 @@ obj/item/toy/cards/deck/syndicate
/obj/item/toy/minimeteor
name = "\improper Mini-Meteor"
desc = "Relive the excitement of a meteor shower! SweetMeat-eor. Co is not responsible for any injuries, headaches or hearing loss caused by Mini-Meteor"
desc = "Relive the excitement of a meteor shower! SweetMeat-eor. Co is not responsible for any injuries, headaches or hearing loss caused by Mini-Meteor?"
icon = 'icons/obj/toy.dmi'
icon_state = "minimeteor"
w_class = 2.0
@@ -1116,7 +1113,7 @@ obj/item/toy/cards/deck/syndicate
*/
/obj/item/toy/redbutton
name = "big red button"
desc = "A big, plastic red button. Reads 'From HonkCo Pranks©' on the back."
desc = "A big, plastic red button. Reads 'From HonkCo Pranks?' on the back."
icon = 'icons/obj/assemblies.dmi'
icon_state = "bigred"
w_class = 2.0
@@ -1125,7 +1122,7 @@ obj/item/toy/cards/deck/syndicate
/obj/item/toy/redbutton/attack_self(mob/user)
if (cooldown < world.time)
cooldown = (world.time + 300) // Sets cooldown at 30 seconds
user.visible_message("<span class='warning'>[user] presses the big red button.</span>", "<span class='notice'>You press the button, it plays a loud noise!</span>", "<span class='italics'>You hear a loud click.</span>")
user.visible_message("<span class='warning'>[user] presses the big red button.</span>", "<span class='notice'>You press the button, it plays a loud noise!</span>", "<span class='italics'>The button clicks loudly.</span>")
playsound(src, 'sound/effects/explosionfar.ogg', 50, 0, surround = 0)
for(var/mob/M in range(10, src)) // Checks range
if(!M.stat && !istype(M, /mob/living/silicon/ai)) // Checks to make sure whoever's getting shaken is alive/not the AI
@@ -1133,4 +1130,4 @@ obj/item/toy/cards/deck/syndicate
shake_camera(M, 2, 1) // Shakes player camera 2 squares for 1 second.
else
user << "<span class='warning'>Nothing happens!</span>"
user << "<span class='alert'>Nothing happens.</span>"
@@ -4,11 +4,4 @@
locked = 1
icon_state = "secure"
health = 200
user << "<span class='warning'>You have no idea how this thing is supposed to work!</span>"
user << "<span class='warning'>You can't do that right now!</span>"
user.visible_message("[user] has [locked ? null : "un"]locked the locker.", "<span class='notice'>You [locked ? null : "un"]lock the locker.</span>")
user << "<span class='danger'>Access Denied.</span>"
user << "<span class='warning'>The locker appears to be broken!</span>"
O.show_message("<span class='warning'>The locker has been broken by [user] with an electromagnetic card!</span>", 1, "<span class='italics'>You hear a faint electrical spark.</span>", 2)
user << "<span class='warning'>The locker is locked!</span>"
secure = 1
@@ -0,0 +1,373 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
datum/reagent/nicotine
name = "Nicotine"
id = "nicotine"
description = "Slightly reduces stun times. If overdosed it will deal toxin and oxygen damage."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
overdose_threshold = 35
addiction_threshold = 30
datum/reagent/nicotine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/smoke_message = pick("You can just feel your lungs dying!", "You feel relaxed.", "You feel calmed.", "You feel the lung cancer forming.", "You feel the money you wasted.", "You feel like a space cowboy.", "You feel rugged.")
if(prob(5))
M << "<span class='notice'>[smoke_message]</span>"
M.AdjustStunned(-1)
M.adjustStaminaLoss(-1*REM)
..()
return
datum/reagent/nicotine/overdose_process(var/mob/living/M as mob)
if(prob(20))
M << "<span class='notice'>You feel like you've smoked too much.</span>"
M.adjustToxLoss(1*REM)
M.adjustOxyLoss(1*REM)
..()
return
datum/reagent/crank
name = "Crank"
id = "crank"
description = "Reduces stun times by about 200%. If overdosed or addicted it will deal significant Toxin, Brute and Brain damage."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
overdose_threshold = 20
addiction_threshold = 10
datum/reagent/crank/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/high_message = pick("You feel jittery.", "You feel like you gotta go fast.", "You feel like you need to step it up.")
if(prob(5))
M << "<span class='notice'>[high_message]</span>"
M.AdjustParalysis(-2)
M.AdjustStunned(-2)
M.AdjustWeakened(-2)
..()
return
datum/reagent/crank/overdose_process(var/mob/living/M as mob)
M.adjustBrainLoss(rand(1,10)*REM)
M.adjustToxLoss(rand(1,10)*REM)
M.adjustBruteLoss(rand(1,10)*REM)
..()
return
datum/reagent/crank/addiction_act_stage1(var/mob/living/M as mob)
M.adjustBrainLoss(rand(1,10)*REM)
..()
return
datum/reagent/crank/addiction_act_stage2(var/mob/living/M as mob)
M.adjustToxLoss(rand(1,10)*REM)
..()
return
datum/reagent/crank/addiction_act_stage3(var/mob/living/M as mob)
M.adjustBruteLoss(rand(1,10)*REM)
..()
return
datum/reagent/crank/addiction_act_stage4(var/mob/living/M as mob)
M.adjustBrainLoss(rand(1,10)*REM)
M.adjustToxLoss(rand(1,10)*REM)
M.adjustBruteLoss(rand(1,10)*REM)
..()
return
/datum/chemical_reaction/crank
name = "Crank"
id = "crank"
result = "crank"
required_reagents = list("diphenhydramine" = 1, "ammonia" = 1, "lithium" = 1, "sacid" = 1, "fuel" = 1)
result_amount = 5
mix_message = "The mixture violently reacts, leaving behind a few crystalline shards."
required_temp = 390
/datum/reagent/krokodil
name = "Krokodil"
id = "krokodil"
description = "Cools and calms you down. If overdosed it will deal significant Brain and Toxin damage. If addicted it will begin to deal fatal amounts of Brute damage as the subject's skin falls off."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
overdose_threshold = 20
addiction_threshold = 15
/datum/reagent/krokodil/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/high_message = pick("You feel calm.", "You feel collected.", "You feel like you need to relax.")
if(prob(5))
M << "<span class='notice'>[high_message]</span>"
..()
return
/datum/reagent/krokodil/overdose_process(var/mob/living/M as mob)
if(prob(10))
M.adjustBrainLoss(rand(1,5)*REM)
M.adjustToxLoss(rand(1,5)*REM)
..()
return
/datum/reagent/krokodil/addiction_act_stage1(var/mob/living/M as mob)
M.adjustBrainLoss(rand(1,5)*REM)
M.adjustToxLoss(rand(1,5)*REM)
..()
return
/datum/reagent/krokodil/addiction_act_stage2(var/mob/living/M as mob)
if(prob(25))
M << "<span class='danger'>Your skin feels loose...</span>"
..()
return
/datum/reagent/krokodil/addiction_act_stage3(var/mob/living/M as mob)
if(prob(25))
M << "<span class='danger'>Your skin starts to peel away...</span>"
M.adjustBruteLoss(3*REM)
..()
return
/datum/reagent/krokodil/addiction_act_stage4(var/mob/living/carbon/human/M as mob)
if(!istype(M.dna.species, /datum/species/cosmetic_zombie))
M << "<span class='userdanger'>Your skin falls off easily!</span>"
M.adjustBruteLoss(rand(50,80)*REM) // holy shit your skin just FELL THE FUCK OFF
hardset_dna(M, null, null, null, null, /datum/species/cosmetic_zombie)
else
M.adjustBruteLoss(5*REM)
..()
return
/datum/chemical_reaction/krokodil
name = "Krokodil"
id = "krokodil"
result = "krokodil"
required_reagents = list("diphenhydramine" = 1, "morphine" = 1, "cleaner" = 1, "potassium" = 1, "phosphorus" = 1, "fuel" = 1)
result_amount = 6
mix_message = "The mixture dries into a pale blue powder."
required_temp = 380
/datum/reagent/methamphetamine
name = "Methamphetamine"
id = "methamphetamine"
description = "Reduces stun times by about 300%, speeds the user up, and allows the user to quickly recover stamina while dealing a small amount of Brain damage. If overdosed the subject will move randomly, laugh randomly, drop items and suffer from Toxin and Brain damage. If addicted the subject will constantly jitter and drool, before becoming dizzy and losing motor control and eventually suffer heavy toxin damage."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
overdose_threshold = 20
addiction_threshold = 10
metabolization_rate = 0.6
/datum/reagent/methamphetamine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/high_message = pick("You feel hyper.", "You feel like you need to go faster.", "You feel like you can run the world.")
if(prob(5))
M << "<span class='notice'>[high_message]</span>"
M.AdjustParalysis(-3)
M.AdjustStunned(-3)
M.AdjustWeakened(-3)
M.adjustStaminaLoss(-3)
M.status_flags |= GOTTAGOREALLYFAST
M.Jitter(3)
M.adjustBrainLoss(0.5)
if(prob(5))
M.emote(pick("twitch", "shiver"))
..()
return
/datum/reagent/methamphetamine/overdose_process(var/mob/living/M as mob)
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 4, i++)
step(M, pick(cardinal))
if(prob(20))
M.emote("laugh")
if(prob(33))
M.visible_message("<span class = 'danger'>[M]'s hands flip out and flail everywhere!</span>")
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
..()
if(prob(20))
M.adjustToxLoss(5)
M.adjustBrainLoss(pick(0.5, 0.6, 0.7, 0.8, 0.9, 1))
return
/datum/reagent/methamphetamine/addiction_act_stage1(var/mob/living/M as mob)
M.Jitter(5)
if(prob(20))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/methamphetamine/addiction_act_stage2(var/mob/living/M as mob)
M.Jitter(10)
M.Dizzy(10)
if(prob(30))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/methamphetamine/addiction_act_stage3(var/mob/living/M as mob)
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 4, i++)
step(M, pick(cardinal))
M.Jitter(15)
M.Dizzy(15)
if(prob(40))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/methamphetamine/addiction_act_stage4(var/mob/living/carbon/human/M as mob)
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 8, i++)
step(M, pick(cardinal))
M.Jitter(20)
M.Dizzy(20)
M.adjustToxLoss(5)
if(prob(50))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/chemical_reaction/methamphetamine
name = "methamphetamine"
id = "methamphetamine"
result = "methamphetamine"
required_reagents = list("ephedrine" = 1, "iodine" = 1, "phosphorus" = 1, "hydrogen" = 1)
result_amount = 4
required_temp = 374
/datum/chemical_reaction/saltpetre
name = "saltpetre"
id = "saltpetre"
result = "saltpetre"
required_reagents = list("potassium" = 1, "nitrogen" = 1, "oxygen" = 3)
result_amount = 3
/datum/reagent/saltpetre
name = "Saltpetre"
id = "saltpetre"
description = "Volatile."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
/datum/reagent/bath_salts
name = "Bath Salts"
id = "bath_salts"
description = "Makes you nearly impervious to stuns and grants a stamina regeneration buff, but you will be a nearly uncontrollable tramp-bearded raving lunatic."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
overdose_threshold = 20
addiction_threshold = 10
/datum/reagent/bath_salts/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/high_message = pick("You feel amped up.", "You feel ready.", "You feel like you can push it to the limit.")
if(prob(5))
M << "<span class='notice'>[high_message]</span>"
M.AdjustParalysis(-5)
M.AdjustStunned(-5)
M.AdjustWeakened(-5)
M.adjustStaminaLoss(-10)
M.adjustBrainLoss(1)
M.adjustToxLoss(0.1)
M.hallucination += 10
if(M.canmove && !istype(M.loc, /atom/movable))
step(M, pick(cardinal))
step(M, pick(cardinal))
..()
return
/datum/chemical_reaction/bath_salts
name = "bath_salts"
id = "bath_salts"
result = "bath_salts"
required_reagents = list("????" = 1, "saltpetre" = 1, "nutriment" = 1, "cleaner" = 1, "enzyme" = 1, "tea" = 1, "mercury" = 1)
result_amount = 7
required_temp = 374
/datum/reagent/bath_salts/overdose_process(var/mob/living/M as mob)
M.hallucination += 10
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 8, i++)
step(M, pick(cardinal))
if(prob(20))
M.emote(pick("twitch","drool","moan"))
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
..()
return
/datum/reagent/bath_salts/addiction_act_stage1(var/mob/living/M as mob)
M.hallucination += 10
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 8, i++)
step(M, pick(cardinal))
M.Jitter(5)
M.adjustBrainLoss(10)
if(prob(20))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/bath_salts/addiction_act_stage2(var/mob/living/M as mob)
M.hallucination += 20
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 8, i++)
step(M, pick(cardinal))
M.Jitter(10)
M.Dizzy(10)
M.adjustBrainLoss(10)
if(prob(30))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/bath_salts/addiction_act_stage3(var/mob/living/M as mob)
M.hallucination += 30
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 12, i++)
step(M, pick(cardinal))
M.Jitter(15)
M.Dizzy(15)
M.adjustBrainLoss(10)
if(prob(40))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/reagent/bath_salts/addiction_act_stage4(var/mob/living/carbon/human/M as mob)
M.hallucination += 40
if(M.canmove && !istype(M.loc, /atom/movable))
for(var/i = 0, i < 16, i++)
step(M, pick(cardinal))
M.Jitter(50)
M.Dizzy(50)
M.adjustToxLoss(5)
M.adjustBrainLoss(10)
if(prob(50))
M.emote(pick("twitch","drool","moan"))
..()
return
/datum/chemical_reaction/aranesp
name = "aranesp"
id = "aranesp"
result = "aranesp"
required_reagents = list("epinephrine" = 1, "atropine" = 1, "morphine" = 1)
result_amount = 3
/datum/reagent/aranesp
name = "Aranesp"
id = "aranesp"
description = "Amps you up and gets you going, fixes all stamina damage you might have but can cause toxin and oxygen damage.."
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
/datum/reagent/aranesp/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
var/high_message = pick("You feel amped up.", "You feel ready.", "You feel like you can push it to the limit.")
if(prob(5))
M << "<span class='notice'>[high_message]</span>"
M.adjustStaminaLoss(-35)
M.adjustToxLoss(1)
if(prob(50))
M.losebreath++
M.adjustOxyLoss(20)
..()
return
@@ -0,0 +1,831 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
datum/reagent/silver_sulfadiazine
name = "Silver Sulfadiazine"
id = "silver_sulfadiazine"
description = "On touch, quickly heals burn damage. Basic anti-burn healing drug. On ingestion, deals minor toxin damage."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 2
datum/reagent/silver_sulfadiazine/reaction_mob(var/mob/living/M as mob, var/method=TOUCH, var/volume, var/show_message = 1)
if(iscarbon(M))
if(method == TOUCH)
M.adjustFireLoss(-volume)
if(show_message)
M << "<span class='notice'>You feel your burns healing!</span>"
M.emote("scream")
if(method == INGEST)
M.adjustToxLoss(0.5*volume)
if(show_message)
M << "<span class='notice'>You probably shouldn't have eaten that. Maybe you should of splashed it on, or applied a patch?</span>"
..()
return
datum/reagent/silver_sulfadiazine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustFireLoss(-2*REM)
..()
return
datum/reagent/styptic_powder
name = "Styptic Powder"
id = "styptic_powder"
description = "On touch, quickly heals brute damage. Basic anti-brute healing drug. On ingestion, deals minor toxin damage."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 2
datum/reagent/styptic_powder/reaction_mob(var/mob/living/M as mob, var/method=TOUCH, var/volume, var/show_message = 1)
if(iscarbon(M))
if(method == TOUCH)
M.adjustBruteLoss(-volume)
if(show_message)
M << "<span class='notice'>You feel your wounds knitting back together!</span>"
M.emote("scream")
if(method == INGEST)
M.adjustToxLoss(0.5*volume)
if(show_message)
M << "<span class='notice'>You probably shouldn't have eaten that. Maybe you should of splashed it on, or applied a patch?</span>"
..()
return
datum/reagent/styptic_powder/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(prob(55))
M.adjustBruteLoss(-8*REM)
..()
return
datum/reagent/salglu_solution
name = "Saline-Glucose Solution"
id = "salglu_solution"
description = "Has a 33% chance per metabolism cycle to heal brute and burn damage."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/salglu_solution/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(prob(33))
M.adjustBruteLoss(-1*REM)
M.adjustFireLoss(-1*REM)
..()
return
datum/reagent/synthflesh
name = "Synthflesh"
id = "synthflesh"
description = "Has a 100% chance of instantly healing brute and burn damage. One unit of the chemical will heal one point of damage. Touch application only."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/synthflesh/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume,var/show_message = 1)
if(!M) M = holder.my_atom
if(iscarbon(M))
if(method == TOUCH)
M.adjustBruteLoss(-1.5*volume)
M.adjustFireLoss(-1.5*volume)
if(show_message)
M << "<span class='notice'>You feel your burns healing and your flesh knitting together!</span>"
..()
return
datum/reagent/charcoal
name = "Charcoal"
id = "charcoal"
description = "Heals toxin damage, and will also slowly remove any other chemicals."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/charcoal/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(-3*REM)
for(var/datum/reagent/R in M.reagents.reagent_list)
if(R != src)
M.reagents.remove_reagent(R.id,1)
..()
return
/datum/chemical_reaction/charcoal
name = "Charcoal"
id = "charcoal"
result = "charcoal"
required_reagents = list("ash" = 1, "sodiumchloride" = 1)
result_amount = 2
mix_message = "The mixture yields a fine black powder."
required_temp = 380
/datum/chemical_reaction/silver_sulfadiazine
name = "Silver Sulfadiazine"
id = "silver_sulfadiazine"
result = "silver_sulfadiazine"
required_reagents = list("ammonia" = 1, "silver" = 1, "sulfur" = 1, "oxygen" = 1, "chlorine" = 1)
result_amount = 5
/datum/chemical_reaction/salglu_solution
name = "Saline-Glucose Solution"
id = "salglu_solution"
result = "salglu_solution"
required_reagents = list("sodiumchloride" = 1, "water" = 1, "sugar" = 1)
result_amount = 3
/datum/chemical_reaction/synthflesh
name = "Synthflesh"
id = "synthflesh"
result = "synthflesh"
required_reagents = list("blood" = 1, "carbon" = 1, "styptic_powder" = 1)
result_amount = 3
/datum/chemical_reaction/styptic_powder
name = "Styptic Powder"
id = "styptic_powder"
result = "styptic_powder"
required_reagents = list("aluminium" = 1, "hydrogen" = 1, "oxygen" = 1, "sacid" = 1)
result_amount = 4
mix_message = "The solution yields an astringent powder."
datum/reagent/omnizine
name = "Omnizine"
id = "omnizine"
description = "Heals 1 of each damage type a cycle. If overdosed it will deal significant amounts of each damage type."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
overdose_threshold = 30
datum/reagent/omnizine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(-1*REM)
M.adjustOxyLoss(-1*REM)
M.adjustBruteLoss(-1*REM)
M.adjustFireLoss(-1*REM)
..()
return
datum/reagent/omnizine/overdose_process(var/mob/living/M as mob)
M.adjustToxLoss(3*REM)
M.adjustOxyLoss(3*REM)
M.adjustBruteLoss(3*REM)
M.adjustFireLoss(3*REM)
..()
return
datum/reagent/calomel
name = "Calomel"
id = "calomel"
description = "Quickly purges the body of all chemicals. If your health is above 20, toxin damage is dealt. When you hit 20 health or lower, the damage will cease."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/calomel/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
for(var/datum/reagent/R in M.reagents.reagent_list)
if(R != src)
M.reagents.remove_reagent(R.id,5)
if(M.health > 20)
M.adjustToxLoss(5*REM)
..()
return
/datum/chemical_reaction/calomel
name = "Calomel"
id = "calomel"
result = "calomel"
required_reagents = list("mercury" = 1, "chlorine" = 1)
result_amount = 2
required_temp = 374
datum/reagent/potass_iodide
name = "Potassium Iodide"
id = "potass_iodide"
description = "Reduces low radiation damage very effectively."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/potass_iodide/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.radiation > 0)
if(prob(80))
M.radiation--
if(M.radiation < 0)
M.radiation = 0
..()
return
/datum/chemical_reaction/potass_iodide
name = "Potassium Iodide"
id = "potass_iodide"
result = "potass_iodide"
required_reagents = list("potassium" = 1, "iodine" = 1)
result_amount = 2
datum/reagent/pen_acid
name = "Pentetic Acid"
id = "pen_acid"
description = "Reduces massive amounts of radiation and toxin damage while purging other chemicals from the body. Has a chance of dealing brute damage."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/pen_acid/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.radiation > 0)
M.radiation -= 7
M.adjustToxLoss(-4*REM)
if(prob(33))
M.adjustBruteLoss(1*REM)
if(M.radiation < 0)
M.radiation = 0
for(var/datum/reagent/R in M.reagents.reagent_list)
if(R != src)
M.reagents.remove_reagent(R.id,4)
..()
return
/datum/chemical_reaction/pen_acid
name = "Pentetic Acid"
id = "pen_acid"
result = "pen_acid"
required_reagents = list("fuel" = 1, "chlorine" = 1, "ammonia" = 1, "formaldehyde" = 1, "sodium" = 1, "cyanide" = 1)
result_amount = 6
datum/reagent/sal_acid
name = "Salicyclic Acid"
id = "sal_acid"
description = "If you have less than 50 brute damage, there is a 50% chance to heal one unit. If overdosed it will have a 50% chance to deal 2 brute damage if the patient has less than 50 brute damage already."
reagent_state = LIQUID
color = "#C8A5DC"
overdose_threshold = 25
datum/reagent/sal_acid/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.getBruteLoss() < 50)
if(prob(50))
M.adjustBruteLoss(-1*REM)
..()
return
datum/reagent/sal_acid/overdose_process(var/mob/living/M as mob)
if(M.getBruteLoss() < 50)
if(prob(50))
M.adjustBruteLoss(2*REM)
..()
return
/datum/chemical_reaction/sal_acid
name = "Salicyclic Acid"
id = "sal_acid"
result = "sal_acid"
required_reagents = list("sodium" = 1, "phenol" = 1, "carbon" = 1, "oxygen" = 1, "sacid" = 1)
result_amount = 5
datum/reagent/salbutamol
name = "Salbutamol"
id = "salbutamol"
description = "Quickly heals oxygen damage while slowing down suffocation. Great for stabilizing critical patients!"
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
datum/reagent/salbutamol/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustOxyLoss(-6*REM)
if(M.losebreath >= 4)
M.losebreath -= 4
..()
return
/datum/chemical_reaction/salbutamol
name = "Salbutamol"
id = "salbutamol"
result = "salbutamol"
required_reagents = list("sal_acid" = 1, "lithium" = 1, "aluminium" = 1, "bromine" = 1, "ammonia" = 1)
result_amount = 5
datum/reagent/perfluorodecalin
name = "Perfluorodecalin"
id = "perfluorodecalin"
description = "Heals suffocation damage so quickly that you could have a spacewalk, but it mutes your voice. Has a 33% chance of healing brute and burn damage per cycle as well."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
datum/reagent/perfluorodecalin/on_mob_life(var/mob/living/carbon/human/M as mob)
if(!M) M = holder.my_atom
M.adjustOxyLoss(-25*REM)
M.silent = max(M.silent, 5)
if(prob(33))
M.adjustBruteLoss(-1*REM)
M.adjustFireLoss(-1*REM)
..()
return
/datum/chemical_reaction/perfluorodecalin
name = "Perfluorodecalin"
id = "perfluorodecalin"
result = "perfluorodecalin"
required_reagents = list("hydrogen" = 1, "fluorine" = 1, "oil" = 1)
result_amount = 3
required_temp = 370
mix_message = "The mixture rapidly turns into a dense pink liquid."
datum/reagent/ephedrine
name = "Ephedrine"
id = "ephedrine"
description = "Reduces stun times, increases run speed. If overdosed it will deal toxin and oxyloss damage."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.3
overdose_threshold = 45
addiction_threshold = 30
datum/reagent/ephedrine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.status_flags |= IGNORESLOWDOWN
M.AdjustParalysis(-1)
M.AdjustStunned(-1)
M.AdjustWeakened(-1)
M.adjustStaminaLoss(-1*REM)
..()
return
datum/reagent/ephedrine/overdose_process(var/mob/living/M as mob)
if(prob(33))
M.adjustToxLoss(1*REM)
M.losebreath++
..()
return
datum/reagent/ephedrine/addiction_act_stage1(var/mob/living/M as mob)
if(prob(33))
M.adjustToxLoss(2*REM)
M.losebreath += 2
..()
return
datum/reagent/ephedrine/addiction_act_stage2(var/mob/living/M as mob)
if(prob(33))
M.adjustToxLoss(3*REM)
M.losebreath += 3
..()
return
datum/reagent/ephedrine/addiction_act_stage3(var/mob/living/M as mob)
if(prob(33))
M.adjustToxLoss(4*REM)
M.losebreath += 4
..()
return
datum/reagent/ephedrine/addiction_act_stage4(var/mob/living/M as mob)
if(prob(33))
M.adjustToxLoss(5*REM)
M.losebreath += 5
..()
return
/datum/chemical_reaction/ephedrine
name = "Ephedrine"
id = "ephedrine"
result = "ephedrine"
required_reagents = list("sugar" = 1, "oil" = 1, "hydrogen" = 1, "diethylamine" = 1)
result_amount = 4
mix_message = "The solution fizzes and gives off toxic fumes."
datum/reagent/diphenhydramine
name = "Diphenhydramine"
id = "diphenhydramine"
description = "Purges body of lethal Histamine and reduces jitteriness while causing minor drowsiness."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/diphenhydramine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.drowsyness += 1
M.jitteriness -= 1
M.reagents.remove_reagent("histamine",3)
..()
return
/datum/chemical_reaction/diphenhydramine
name = "Diphenhydramine"
id = "diphenhydramine"
result = "diphenhydramine"
required_reagents = list("oil" = 1, "carbon" = 1, "bromine" = 1, "diethylamine" = 1, "ethanol" = 1)
result_amount = 4
mix_message = "The mixture dries into a pale blue powder."
datum/reagent/morphine
name = "Morphine"
id = "morphine"
description = "Will allow you to ignore slowdown from equipment and damage. Will eventually knock you out if you take too much. If overdosed it will cause jitteriness, dizziness, force the victim to drop items in their hands and eventually deal toxin damage."
reagent_state = LIQUID
color = "#C8A5DC"
var/cycle_count = 0
overdose_threshold = 30
addiction_threshold = 25
datum/reagent/morphine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.status_flags |= IGNORESLOWDOWN
if(cycle_count >= 36)
M.sleeping += 3
cycle_count++
..()
return
datum/reagent/morphine/overdose_process(var/mob/living/M as mob)
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
M.Dizzy(1)
M.Jitter(1)
..()
return
datum/reagent/morphine/addiction_act_stage1(var/mob/living/M as mob)
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
M.Dizzy(2)
M.Jitter(2)
..()
return
datum/reagent/morphine/addiction_act_stage2(var/mob/living/M as mob)
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
M.adjustToxLoss(1*REM)
M.Dizzy(3)
M.Jitter(3)
..()
return
datum/reagent/morphine/addiction_act_stage3(var/mob/living/M as mob)
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
M.adjustToxLoss(2*REM)
M.Dizzy(4)
M.Jitter(4)
..()
return
datum/reagent/morphine/addiction_act_stage4(var/mob/living/M as mob)
if(prob(33))
var/obj/item/I = M.get_active_hand()
if(I)
M.drop_item()
M.adjustToxLoss(3*REM)
M.Dizzy(5)
M.Jitter(5)
..()
return
datum/reagent/oculine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
cycle_amount++
if(M.eye_blind > 0 && cycle_amount > 20)
if(prob(30))
M.eye_blind = 0
else if(prob(80))
M.eye_blind = 0
M.eye_blurry = 1
if(M.eye_blurry > 0)
if(prob(80))
M.eye_blurry = 0
..()
return
/datum/chemical_reaction/oculine
name = "Oculine"
id = "oculine"
result = "oculine"
required_reagents = list("charcoal" = 1, "carbon" = 1, "hydrogen" = 1)
result_amount = 3
mix_message = "The mixture sputters loudly and becomes a pale pink color."
datum/reagent/oculine
name = "Oculine"
id = "oculine"
description = "Cures blindness and heals eye damage over time."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.4
var/cycle_amount = 0
datum/reagent/atropine
name = "Atropine"
id = "atropine"
description = "If patients health is below -25 it will heal 3 brute and burn damage per cycle, as well as stop any oxyloss. Good for stabilising critical patients."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
overdose_threshold = 35
datum/reagent/atropine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.health > -60)
M.adjustToxLoss(1*REM)
if(M.health < -25)
M.adjustBruteLoss(-3*REM)
M.adjustFireLoss(-3*REM)
if(M.oxyloss > 65)
M.setOxyLoss(65)
if(M.losebreath > 5)
M.losebreath = 5
if(prob(30))
M.Dizzy(5)
M.Jitter(5)
..()
return
datum/reagent/atropine/overdose_process(var/mob/living/M as mob)
if(prob(50))
M.adjustToxLoss(2*REM)
M.Dizzy(1)
M.Jitter(1)
..()
return
/datum/chemical_reaction/atropine
name = "Atropine"
id = "atropine"
result = "atropine"
required_reagents = list("ethanol" = 1, "acetone" = 1, "diethylamine" = 1, "phenol" = 1, "sacid" = 1)
result_amount = 5
datum/reagent/epinephrine
name = "Epinephrine"
id = "epinephrine"
description = "mReduces most of the knockout/stun effects, minor stamina regeneration buff. Attempts to stop you taking too much oxygen damage. If the patient is in low to severe crit, heals toxins, brute, and burn very effectively. Will not heal patients who are almost dead. If overdosed will stun and deal toxin damage"
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
overdose_threshold = 30
datum/reagent/epinephrine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.health < -10 && M.health > -65)
M.adjustToxLoss(-1*REM)
M.adjustBruteLoss(-1*REM)
M.adjustFireLoss(-1*REM)
if(M.oxyloss > 35)
M.setOxyLoss(35)
if(M.losebreath >= 4)
M.losebreath -= 4
if(M.losebreath < 0)
M.losebreath = 0
M.adjustStaminaLoss(-1*REM)
if(prob(30))
M.AdjustParalysis(-1)
M.AdjustStunned(-1)
M.AdjustWeakened(-1)
..()
return
datum/reagent/epinephrine/overdose_process(var/mob/living/M as mob)
if(prob(33))
M.adjustStaminaLoss(5*REM)
M.adjustToxLoss(2*REM)
M.losebreath++
..()
return
/datum/chemical_reaction/epinephrine
name = "Epinephrine"
id = "epinephrine"
result = "epinephrine"
required_reagents = list("phenol" = 1, "acetone" = 1, "diethylamine" = 1, "oxygen" = 1, "chlorine" = 1, "hydrogen" = 1)
result_amount = 6
datum/reagent/strange_reagent
name = "Strange Reagent"
id = "strange_reagent"
description = "A miracle drug that can bring a dead body back to life! If the corpse has suffered too much damage, however, no change will occur to the body. If used on a living person it will deal Brute and Burn damage."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/strange_reagent/reaction_mob(var/mob/living/carbon/human/M as mob, var/method=TOUCH, var/volume)
if(M.stat == DEAD)
if(M.getBruteLoss() >= 100 || M.getFireLoss() >= 100)
M.visible_message("<span class='warning'>[M]'s body convulses a bit, and then falls still once more.</span>")
return
var/mob/dead/observer/ghost = M.get_ghost()
M.visible_message("<span class='warning'>[M]'s body convulses a bit.</span>")
if(!M.suiciding && !ghost && !(NOCLONE in M.mutations))
M.stat = 1
M.adjustOxyLoss(-20)
M.adjustToxLoss(-20)
dead_mob_list -= M
living_mob_list |= list(M)
M.emote("gasp")
add_logs(M, M, "revived", object="strange reagent")
..()
return
datum/reagent/strange_reagent/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(prob(50))
M.adjustBruteLoss(2*REM)
M.adjustFireLoss(2*REM)
..()
return
/datum/chemical_reaction/strange_reagent
name = "Strange Reagent"
id = "strange_reagent"
result = "strange_reagent"
required_reagents = list("omnizine" = 1, "holywater" = 1, "mutagen" = 1)
result_amount = 3
datum/reagent/life
name = "Life"
id = "life"
description = "Can create a life form, however it is not guaranteed to be friendly. May want to have Security on hot standby."
reagent_state = LIQUID
color = "#C8A5DC"
metabolization_rate = 0.2
/datum/chemical_reaction/life
name = "Life"
id = "life"
result = "life"
required_reagents = list("strange_reagent" = 1, "synthflesh" = 1, "blood" = 1)
result_amount = 3
required_temp = 374
/datum/chemical_reaction/life/on_reaction(var/datum/reagents/holder, var/created_volume)
chemical_mob_spawn(holder, 1, "Life")
proc/chemical_mob_spawn(var/datum/reagents/holder, var/amount_to_spawn, var/reaction_name, var/mob_faction = "chemicalsummon")
if(holder && holder.my_atom)
var/blocked = list(/mob/living/simple_animal/hostile,
/mob/living/simple_animal/hostile/pirate,
/mob/living/simple_animal/hostile/pirate/ranged,
/mob/living/simple_animal/hostile/russian,
/mob/living/simple_animal/hostile/russian/ranged,
/mob/living/simple_animal/hostile/syndicate,
/mob/living/simple_animal/hostile/syndicate/melee,
/mob/living/simple_animal/hostile/syndicate/melee/space,
/mob/living/simple_animal/hostile/syndicate/ranged,
/mob/living/simple_animal/hostile/syndicate/ranged/space,
/mob/living/simple_animal/hostile/alien/queen/large,
/mob/living/simple_animal/hostile/retaliate,
/mob/living/simple_animal/hostile/retaliate/clown,
/mob/living/simple_animal/hostile/mushroom,
/mob/living/simple_animal/hostile/asteroid,
/mob/living/simple_animal/hostile/asteroid/basilisk,
/mob/living/simple_animal/hostile/asteroid/goldgrub,
/mob/living/simple_animal/hostile/asteroid/goliath,
/mob/living/simple_animal/hostile/asteroid/hivelord,
/mob/living/simple_animal/hostile/asteroid/hivelordbrood,
/mob/living/simple_animal/hostile/carp/holocarp,
/mob/living/simple_animal/hostile/mining_drone,
/mob/living/simple_animal/hostile/poison,
/mob/living/simple_animal/hostile/blob,
/mob/living/simple_animal/ascendant_shadowling
)//exclusion list for things you don't want the reaction to create.
var/list/critters = typesof(/mob/living/simple_animal/hostile) - blocked // list of possible hostile mobs
var/atom/A = holder.my_atom
var/turf/T = get_turf(A)
var/area/my_area = get_area(T)
var/message = "A [reaction_name] reaction has occured in [my_area.name]. (<A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[T.x];Y=[T.y];Z=[T.z]'>JMP</A>)"
message += " (<A HREF='?_src_=vars;Vars=\ref[A]'>VV</A>)"
var/mob/M = get(A, /mob)
if(M)
message += " - Carried By: [M.real_name] ([M.key]) (<A HREF='?_src_=holder;adminplayeropts=\ref[M]'>PP</A>) (<A HREF='?_src_=holder;adminmoreinfo=\ref[M]'>?</A>)"
else
message += " - Last Fingerprint: [(A.fingerprintslast ? A.fingerprintslast : "N/A")]"
message_admins(message, 0, 1)
playsound(get_turf(holder.my_atom), 'sound/effects/phasein.ogg', 100, 1)
for(var/mob/living/carbon/human/H in viewers(get_turf(holder.my_atom), null))
H.flash_eyes()
for(var/i = 1, i <= amount_to_spawn, i++)
var/chosen = pick(critters)
var/mob/living/simple_animal/hostile/C = new chosen
C.faction |= mob_faction
C.loc = get_turf(holder.my_atom)
if(prob(50))
for(var/j = 1, j <= rand(1, 3), j++)
step(C, pick(NORTH,SOUTH,EAST,WEST))
/datum/reagent/mannitol/on_mob_life(mob/living/M as mob)
M.adjustBrainLoss(-3)
..()
return
/datum/chemical_reaction/mannitol
name = "Mannitol"
id = "mannitol"
result = "mannitol"
required_reagents = list("sugar" = 1, "hydrogen" = 1, "water" = 1)
result_amount = 3
mix_message = "The solution slightly bubbles, becoming thicker."
/datum/reagent/mannitol
name = "Mannitol"
id = "mannitol"
description = "Heals brain damage effectively. Use it in cyro tubes alongside Cryoxadone."
color = "#C8A5DC"
/datum/reagent/mutadone/on_mob_life(var/mob/living/carbon/human/M as mob)
M.jitteriness = 0
if(istype(M) && M.dna)
M.dna.remove_all_mutations()
..()
return
/datum/chemical_reaction/mutadone
name = "Mutadone"
id = "mutadone"
result = "mutadone"
required_reagents = list("mutagen" = 1, "acetone" = 1, "bromine" = 1)
result_amount = 3
/datum/reagent/mutadone
name = "Mutadone"
id = "mutadone"
description = "Heals your genetic defects."
color = "#C8A5DC"
datum/reagent/antihol
name = "Antihol"
id = "antihol"
description = "Helps remove Alcohol from someone's body, as well as eliminating its side effects."
color = "#C8A5DC"
datum/reagent/antihol/on_mob_life(var/mob/living/M as mob)
M.dizziness = 0
M.drowsyness = 0
M.slurring = 0
M.confused = 0
M.reagents.remove_reagent("ethanol", 8)
M.adjustToxLoss(-0.2*REM)
..()
/datum/chemical_reaction/antihol
name = "antihol"
id = "antihol"
result = "antihol"
required_reagents = list("ethanol" = 1, "charcoal" = 1)
result_amount = 2
/datum/chemical_reaction/cryoxadone
name = "Cryoxadone"
id = "cryoxadone"
result = "cryoxadone"
required_reagents = list("stable_plasma" = 1, "acetone" = 1, "mutagen" = 1)
result_amount = 3
/datum/reagent/stimulants
name = "Stimulants"
id = "stimulants"
description = "Increases run speed and eliminates stuns, can heal minor damage. If overdosed it will deal toxin damage and stun."
color = "#C8A5DC"
metabolization_rate = 0.4
overdose_threshold = 60
datum/reagent/stimulants/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.status_flags |= IGNORESLOWDOWN
if(M.health < 50 && M.health > 0)
if(prob(50))
M.adjustOxyLoss(-5*REM)
M.adjustToxLoss(-5*REM)
M.adjustBruteLoss(-5*REM)
M.adjustFireLoss(-5*REM)
M.adjustFireLoss(-3*REM)
M.AdjustParalysis(-1)
M.AdjustStunned(-1)
M.AdjustWeakened(-1)
M.adjustStaminaLoss(-3*REM)
..()
datum/reagent/stimulants/overdose_process(var/mob/living/M as mob)
if(prob(33))
M.adjustStaminaLoss(5*REM)
M.adjustToxLoss(2*REM)
M.losebreath++
..()
return
datum/reagent/insulin
name = "Insulin"
id = "insulin"
description = "Increases sugar depletion rates."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/insulin/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(M.sleeping)
M.sleeping--
M.reagents.remove_reagent("sugar", 5)
..()
return
@@ -0,0 +1,286 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
var/list/random_color_list = list("#00aedb","#a200ff","#f47835","#d41243","#d11141","#00b159","#00aedb","#f37735","#ffc425","#008744","#0057e7","#d62d20","#ffa700")
datum/reagent/oil
name = "Oil"
id = "oil"
description = "Burns in a small smoky fire, mostly used to get Ash."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/stable_plasma
name = "Stable Plasma"
id = "stable_plasma"
description = "Non-flammable plasma locked into a liquid form that cannot ignite or become gaseous/solid."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/iodine
name = "Iodine"
id = "iodine"
description = "A slippery solution."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/fluorine
name = "Fluorine"
id = "fluorine"
description = "A slippery solution."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/carpet
name = "Carpet"
id = "carpet"
description = "A slippery solution."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/reagent/carpet/reaction_turf(var/turf/simulated/T, var/volume)
if(istype(T, /turf/simulated/floor/plating) || istype(T, /turf/simulated/floor/plasteel))
var/turf/simulated/floor/F = T
F.ChangeTurf(/turf/simulated/floor/fancy/carpet)
..()
return
datum/reagent/bromine
name = "Bromine"
id = "bromine"
description = "A slippery solution."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/phenol
name = "Phenol"
id = "phenol"
description = "Used for certain medical recipes."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/ash
name = "Ash"
id = "ash"
description = "Basic ingredient in a couple of recipes."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/acetone
name = "Acetone"
id = "acetone"
description = "Common ingredient in other recipes."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/acetone
name = "acetone"
id = "acetone"
result = "acetone"
required_reagents = list("oil" = 1, "fuel" = 1, "oxygen" = 1)
result_amount = 3
/datum/chemical_reaction/carpet
name = "carpet"
id = "carpet"
result = "carpet"
required_reagents = list("space_drugs" = 1, "blood" = 1)
result_amount = 2
/datum/chemical_reaction/oil
name = "Oil"
id = "oil"
result = "oil"
required_reagents = list("fuel" = 1, "carbon" = 1, "hydrogen" = 1)
result_amount = 3
/datum/chemical_reaction/phenol
name = "phenol"
id = "phenol"
result = "phenol"
required_reagents = list("water" = 1, "chlorine" = 1, "oil" = 1)
result_amount = 3
/datum/chemical_reaction/ash
name = "Ash"
id = "ash"
result = "ash"
required_reagents = list("oil" = 1)
result_amount = 1
required_temp = 480
datum/reagent/colorful_reagent
name = "Colorful Reagent"
id = "colorful_reagent"
description = "A solution."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/colorful_reagent
name = "colorful_reagent"
id = "colorful_reagent"
result = "colorful_reagent"
required_reagents = list("stable_plasma" = 1, "radium" = 1, "space_drugs" = 1, "cryoxadone" = 1, "triple_citrus" = 1)
result_amount = 5
datum/reagent/colorful_reagent/on_mob_life(var/mob/living/M as mob)
if(M && isliving(M))
M.color = pick(random_color_list)
..()
return
datum/reagent/colorful_reagent/reaction_mob(var/mob/living/M, var/volume)
if(M && isliving(M))
M.color = pick(random_color_list)
..()
return
datum/reagent/colorful_reagent/reaction_obj(var/obj/O, var/volume)
if(O)
O.color = pick(random_color_list)
..()
return
datum/reagent/colorful_reagent/reaction_turf(var/turf/T, var/volume)
if(T)
T.color = pick(random_color_list)
..()
return
datum/reagent/triple_citrus
name = "Triple Citrus"
id = "triple_citrus"
description = "A solution."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/triple_citrus
name = "triple_citrus"
id = "triple_citrus"
result = "triple_citrus"
required_reagents = list("lemonjuice" = 1, "limejuice" = 1, "orangejuice" = 1)
result_amount = 5
datum/reagent/corn_starch
name = "Corn Starch"
id = "corn_starch"
description = "A slippery solution."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/corn_syrup
name = "corn_syrup"
id = "corn_syrup"
result = "corn_syrup"
required_reagents = list("corn_starch" = 1, "sacid" = 1)
result_amount = 5
required_temp = 374
datum/reagent/corn_syrup
name = "Corn Syrup"
id = "corn_syrup"
description = "Decays into sugar."
reagent_state = LIQUID
color = "#C8A5DC"
datum/reagent/corn_syrup/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.reagents.add_reagent("sugar", 3)
M.reagents.remove_reagent("corn_syrup", 1)
..()
return
/datum/chemical_reaction/corgium
name = "corgium"
id = "corgium"
result = "corgium"
required_reagents = list("nutriment" = 1, "colorful_reagent" = 1, "strange_reagent" = 1, "blood" = 1)
result_amount = 3
required_temp = 374
datum/reagent/corgium
name = "Corgium"
id = "corgium"
description = "Creates a corgi at the reaction location."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/corgium/on_reaction(var/datum/reagents/holder, var/created_volume)
var/location = get_turf(holder.my_atom)
new /mob/living/simple_animal/pet/corgi(location)
..()
return
datum/reagent/hair_dye
name = "Quantum Hair Dye"
id = "hair_dye"
description = "A solution."
reagent_state = LIQUID
color = "#C8A5DC"
var/list/potential_colors = list("0ad","a0f","f73","d14","d14","0b5","0ad","f73","fc2","084","05e","d22","fa0") // fucking hair code
/datum/chemical_reaction/hair_dye
name = "hair_dye"
id = "hair_dye"
result = "hair_dye"
required_reagents = list("colorful_reagent" = 1, "radium" = 1, "space_drugs" = 1)
result_amount = 5
datum/reagent/hair_dye/reaction_mob(var/mob/living/M, var/volume)
if(M && ishuman(M))
var/mob/living/carbon/human/H = M
H.hair_color = pick(potential_colors)
H.facial_hair_color = pick(potential_colors)
H.update_hair()
..()
return
datum/reagent/barbers_aid
name = "Barber's Aid"
id = "barbers_aid"
description = "A solution to hair loss across the world."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/barbers_aid
name = "barbers_aid"
id = "barbers_aid"
result = "barbers_aid"
required_reagents = list("carpet" = 1, "radium" = 1, "space_drugs" = 1)
result_amount = 5
datum/reagent/barbers_aid/reaction_mob(var/mob/living/M, var/volume)
if(M && ishuman(M))
var/mob/living/carbon/human/H = M
var/datum/sprite_accessory/hair/picked_hair = pick(hair_styles_list)
var/datum/sprite_accessory/facial_hair/picked_beard = pick(facial_hair_styles_list)
H.hair_style = picked_hair
H.facial_hair_style = picked_beard
H.update_hair()
..()
return
datum/reagent/concentrated_barbers_aid
name = "Concentrated Barber's Aid"
id = "concentrated_barbers_aid"
description = "A concentrated solution to hair loss across the world."
reagent_state = LIQUID
color = "#C8A5DC"
/datum/chemical_reaction/concentrated_barbers_aid
name = "concentrated_barbers_aid"
id = "concentrated_barbers_aid"
result = "concentrated_barbers_aid"
required_reagents = list("barbers_aid" = 1, "mutagen" = 1)
result_amount = 2
datum/reagent/concentrated_barbers_aid/reaction_mob(var/mob/living/M, var/volume)
if(M && ishuman(M))
var/mob/living/carbon/human/H = M
H.hair_style = "Very Long Hair"
H.facial_hair_style = "Very Long Beard"
H.update_hair()
..()
return
@@ -0,0 +1,486 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
/datum/reagent/stabilizing_agent
name = "Stabilizing Agent"
id = "stabilizing_agent"
description = "Keeps unstable chemicals stable. This does not work on everything."
reagent_state = LIQUID
color = "#FFFFFF"
/datum/chemical_reaction/stabilizing_agent
name = "stabilizing_agent"
id = "stabilizing_agent"
result = "stabilizing_agent"
required_reagents = list("iron" = 1, "oxygen" = 1, "hydrogen" = 1)
result_amount = 3
/datum/reagent/clf3
name = "Chlorine Trifluoride"
id = "clf3"
description = "Makes a temporary 3x3 fireball when it comes into existence, so be careful when mixing. ClF3 applied to a surface burns things that wouldn't otherwise burn, sometimes through the very floors of the station and exposing it to the vacuum of space."
reagent_state = LIQUID
color = "#FF0000"
metabolization_rate = 4
/datum/chemical_reaction/clf3
name = "Chlorine Trifluoride"
id = "clf3"
result = "clf3"
required_reagents = list("chlorine" = 1, "fluorine" = 3)
result_amount = 4
required_temp = 424
/datum/reagent/clf3/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjust_fire_stacks(4)
M.adjustFireLoss(0.35*M.fire_stacks)
..()
return
/datum/chemical_reaction/clf3/on_reaction(var/datum/reagents/holder, var/created_volume)
var/turf/T = get_turf(holder.my_atom)
for(var/turf/turf in range(1,T))
new /obj/effect/hotspot(turf)
holder.chem_temp = 1000 // hot as shit
return
/datum/reagent/clf3/reaction_turf(var/turf/simulated/T, var/volume)
if(istype(T, /turf/simulated/floor/plating))
var/turf/simulated/floor/plating/F = T
if(prob(1))
F.ChangeTurf(/turf/space)
if(istype(T, /turf/simulated/floor/))
var/turf/simulated/floor/F = T
if(prob(volume/10))
F.make_plating()
if(istype(F, /turf/simulated/floor/))
new /obj/effect/hotspot(F)
if(istype(T, /turf/simulated/wall/))
var/turf/simulated/wall/W = T
if(prob(volume/10))
W.ChangeTurf(/turf/simulated/floor)
return
/datum/reagent/clf3/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume)
if(method == TOUCH && isliving(M))
M.adjust_fire_stacks(5)
M.IgniteMob()
new /obj/effect/hotspot(M.loc)
return
/datum/reagent/sorium
name = "Sorium"
id = "sorium"
description = "Sends everything flying from the detonation point."
reagent_state = LIQUID
color = "#FFA500"
/datum/chemical_reaction/sorium
name = "Sorium"
id = "sorium"
result = "sorium"
required_reagents = list("mercury" = 1, "oxygen" = 1, "nitrogen" = 1, "carbon" = 1)
result_amount = 4
/datum/chemical_reaction/sorium_vortex
name = "sorium_vortex"
id = "sorium_vortex"
result = null
required_reagents = list("sorium" = 1)
required_temp = 474
/datum/chemical_reaction/sorium_vortex/on_reaction(var/datum/reagents/holder, var/created_volume)
var/turf/simulated/T = get_turf(holder.my_atom)
goonchem_vortex(T, 1, 5, 6)
/datum/chemical_reaction/sorium/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
holder.remove_reagent("sorium", created_volume)
var/turf/simulated/T = get_turf(holder.my_atom)
goonchem_vortex(T, 1, 5, 6)
/datum/reagent/liquid_dark_matter
name = "Liquid Dark Matter"
id = "liquid_dark_matter"
description = "Sucks everything into the detonation point."
reagent_state = LIQUID
color = "#800080"
/datum/chemical_reaction/liquid_dark_matter
name = "Liquid Dark Matter"
id = "liquid_dark_matter"
result = "liquid_dark_matter"
required_reagents = list("stable_plasma" = 1, "radium" = 1, "carbon" = 1)
result_amount = 3
/datum/chemical_reaction/ldm_vortex
name = "LDM Vortex"
id = "ldm_vortex"
result = null
required_reagents = list("liquid_dark_matter" = 1)
required_temp = 474
/datum/chemical_reaction/ldm_vortex/on_reaction(var/datum/reagents/holder, var/created_volume)
var/turf/simulated/T = get_turf(holder.my_atom)
goonchem_vortex(T, 0, 5, 6)
return
/datum/chemical_reaction/liquid_dark_matter/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
holder.remove_reagent("liquid_dark_matter", created_volume)
var/turf/simulated/T = get_turf(holder.my_atom)
goonchem_vortex(T, 0, 5, 6)
return
/proc/goonchem_vortex(var/turf/simulated/T, var/setting_type, var/range, var/pull_times)
for(var/atom/movable/X in orange(range, T))
if(istype(X, /obj/effect))
continue //stop pulling smoke and hotspots please
if(istype(X, /atom/movable))
if((X) && !X.anchored)
if(setting_type)
for(var/i = 0, i < pull_times, i++)
step_away(X,T)
else
for(var/i = 0, i < pull_times, i++)
step_towards(X,T)
/datum/reagent/blackpowder
name = "Black Powder"
id = "blackpowder"
description = "Explodes. Violently."
reagent_state = LIQUID
color = "#000000"
metabolization_rate = 0.05
/datum/chemical_reaction/blackpowder
name = "Black Powder"
id = "blackpowder"
result = "blackpowder"
required_reagents = list("saltpetre" = 1, "charcoal" = 1, "sulfur" = 1)
result_amount = 3
/datum/chemical_reaction/blackpowder_explosion
name = "Black Powder Kaboom"
id = "blackpowder_explosion"
result = null
required_reagents = list("blackpowder" = 1)
result_amount = 1
required_temp = 474
mix_message = "<span class = 'boldannounce'>Sparks start flying around the black powder!</span>"
/datum/chemical_reaction/blackpowder_explosion/on_reaction(var/datum/reagents/holder, var/created_volume)
sleep(rand(50,100))
blackpowder_detonate(holder, created_volume)
return
/datum/reagent/blackpowder/on_ex_act()
blackpowder_detonate(holder, volume)
return
/proc/blackpowder_detonate(var/datum/reagents/holder, var/created_volume)
var/turf/simulated/T = get_turf(holder.my_atom)
var/ex_severe = round(created_volume / 100)
var/ex_heavy = round(created_volume / 42)
var/ex_light = round(created_volume / 21)
var/ex_flash = round(created_volume / 8)
explosion(T,ex_severe,ex_heavy,ex_light,ex_flash, 1)
return
/datum/reagent/flash_powder
name = "Flash Powder"
id = "flash_powder"
description = "Makes a very bright flash."
reagent_state = LIQUID
color = "#FFFF00"
/datum/chemical_reaction/flash_powder
name = "Flash powder"
id = "flash_powder"
result = "flash_powder"
required_reagents = list("aluminium" = 1, "potassium" = 1, "sulfur" = 1 )
result_amount = 3
/datum/chemical_reaction/flash_powder_flash
name = "Flash powder activation"
id = "flash_powder_flash"
result = null
required_reagents = list("flash_powder" = 1)
required_temp = 374
/datum/chemical_reaction/flash_powder_flash/on_reaction(var/datum/reagents/holder, var/created_volume)
var/location = get_turf(holder.my_atom)
var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
s.set_up(2, 1, location)
s.start()
for(var/mob/living/carbon/C in get_hearers_in_view(created_volume/10, location))
if(C.check_eye_prot())
continue
flick("e_flash", C.flash)
if(get_dist(C, location) < 4)
C.Weaken(5)
continue
C.Stun(5)
/datum/chemical_reaction/flash_powder/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
var/location = get_turf(holder.my_atom)
var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
s.set_up(2, 1, location)
s.start()
for(var/mob/living/carbon/C in get_hearers_in_view(created_volume/10, location))
if(C.check_eye_prot())
continue
flick("e_flash", C.flash)
if(get_dist(C, location) < 4)
C.Weaken(5)
continue
C.Stun(5)
holder.remove_reagent("flash_powder", created_volume)
/datum/reagent/smoke_powder
name = "Smoke Powder"
id = "smoke_powder"
description = "Makes a large cloud of smoke that can carry reagents."
reagent_state = LIQUID
color = "#808080"
/datum/chemical_reaction/smoke_powder
name = "smoke_powder"
id = "smoke_powder"
result = "smoke_powder"
required_reagents = list("potassium" = 1, "sugar" = 1, "phosphorus" = 1)
result_amount = 3
/datum/chemical_reaction/smoke_powder_smoke
name = "smoke_powder_smoke"
id = "smoke_powder_smoke"
result = null
required_reagents = list("smoke_powder" = 1)
required_temp = 374
secondary = 1
mob_react = 1
/datum/chemical_reaction/smoke_powder_smoke/on_reaction(var/datum/reagents/holder, var/created_volume)
var/location = get_turf(holder.my_atom)
var/datum/effect/effect/system/chem_smoke_spread/S = new /datum/effect/effect/system/chem_smoke_spread
S.attach(location)
playsound(location, 'sound/effects/smoke.ogg', 50, 1, -3)
spawn(0)
if(S)
S.set_up(holder, 10, 0, location)
S.start()
sleep(10)
S.start()
if(holder && holder.my_atom)
holder.clear_reagents()
return
/datum/chemical_reaction/smoke_powder/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
holder.remove_reagent("smoke_powder", created_volume)
var/location = get_turf(holder.my_atom)
var/datum/effect/effect/system/chem_smoke_spread/S = new /datum/effect/effect/system/chem_smoke_spread
S.attach(location)
playsound(location, 'sound/effects/smoke.ogg', 50, 1, -3)
spawn(0)
if(S)
S.set_up(holder, 10, 0, location)
S.start()
sleep(10)
S.start()
if(holder && holder.my_atom)
holder.clear_reagents()
return
/datum/reagent/sonic_powder
name = "Sonic Powder"
id = "sonic_powder"
description = "Makes a deafening noise."
reagent_state = LIQUID
color = "#0000FF"
/datum/chemical_reaction/sonic_powder
name = "sonic_powder"
id = "sonic_powder"
result = "sonic_powder"
required_reagents = list("oxygen" = 1, "cola" = 1, "phosphorus" = 1)
result_amount = 3
/datum/chemical_reaction/sonic_powder_deafen
name = "sonic_powder_deafen"
id = "sonic_powder_deafen"
result = null
required_reagents = list("sonic_powder" = 1)
required_temp = 374
/datum/chemical_reaction/sonic_powder_deafen/on_reaction(var/datum/reagents/holder, var/created_volume)
var/location = get_turf(holder.my_atom)
playsound(location, 'sound/effects/bang.ogg', 25, 1)
for(var/mob/living/carbon/C in get_hearers_in_view(created_volume/10, location))
if(ishuman(C))
var/mob/living/carbon/human/H = C
if((H.ears && (H.ears.flags & EARBANGPROTECT)) || (H.head && (H.head.flags & HEADBANGPROTECT)))
continue
C.show_message("<span class='warning'>BANG</span>", 2)
C.Stun(5)
C.Weaken(5)
C.setEarDamage(C.ear_damage + rand(0, 5), max(C.ear_deaf,15))
if(C.ear_damage >= 15)
C << "<span class='warning'>Your ears start to ring badly!</span>"
else if(C.ear_damage >= 5)
C << "<span class='warning'>Your ears start to ring!</span>"
/datum/chemical_reaction/sonic_powder/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
holder.remove_reagent("sonic_powder", created_volume)
var/location = get_turf(holder.my_atom)
playsound(location, 'sound/effects/bang.ogg', 25, 1)
for(var/mob/living/carbon/C in get_hearers_in_view(created_volume/10, location))
if(ishuman(C))
var/mob/living/carbon/human/H = C
if((H.ears && (H.ears.flags & EARBANGPROTECT)) || (H.head && (H.head.flags & HEADBANGPROTECT)))
continue
C.show_message("<span class='warning'>BANG</span>", 2)
C.Stun(5)
C.Weaken(5)
C.setEarDamage(C.ear_damage + rand(0, 5), max(C.ear_deaf,15))
if(C.ear_damage >= 15)
C << "<span class='warning'>Your ears start to ring badly!</span>"
else if(C.ear_damage >= 5)
C << "<span class='warning'>Your ears start to ring!</span>"
/datum/reagent/phlogiston
name = "Phlogiston"
id = "phlogiston"
description = "Catches you on fire and makes you ignite."
reagent_state = LIQUID
color = "#FF9999"
/datum/chemical_reaction/phlogiston
name = "phlogiston"
id = "phlogiston"
result = "phlogiston"
required_reagents = list("phosphorus" = 1, "sacid" = 1, "stable_plasma" = 1)
result_amount = 3
/datum/chemical_reaction/phlogiston/on_reaction(var/datum/reagents/holder, var/created_volume)
if(holder.has_reagent("stabilizing_agent"))
return
var/turf/simulated/T = get_turf(holder.my_atom)
if(istype(T))
T.atmos_spawn_air(SPAWN_HEAT | SPAWN_TOXINS, created_volume)
return
/datum/reagent/phlogiston/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjust_fire_stacks(1)
M.IgniteMob()
M.adjustFireLoss(0.2*M.fire_stacks)
..()
return
/datum/reagent/napalm
name = "Napalm"
id = "napalm"
description = "Very flammable."
reagent_state = LIQUID
color = "#FF9999"
/datum/reagent/napalm/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjust_fire_stacks(1)
..()
return
/datum/reagent/napalm/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume)
if(method == TOUCH && isliving(M))
M.adjust_fire_stacks(7)
return
/datum/chemical_reaction/napalm
name = "Napalm"
id = "napalm"
result = "napalm"
required_reagents = list("sugar" = 1, "fuel" = 1, "ethanol" = 1 )
result_amount = 3
datum/reagent/cryostylane
name = "Cryostylane"
id = "cryostylane"
description = "Comes into existence at 20K. As long as there is sufficient oxygen for it to react with, Cryostylane slowly cools all other reagents in the mob down to 0K."
color = "#B2B2FF" // rgb: 139, 166, 233
/datum/chemical_reaction/cryostylane
name = "cryostylane"
id = "cryostylane"
result = "cryostylane"
required_reagents = list("water" = 1, "stable_plasma" = 1, "nitrogen" = 1)
result_amount = 3
/datum/chemical_reaction/cryostylane/on_reaction(var/datum/reagents/holder, var/created_volume)
holder.chem_temp = 20 // cools the fuck down
return
datum/reagent/cryostylane/on_mob_life(var/mob/living/M as mob) //TODO: code freezing into an ice cube
if(M.reagents.has_reagent("oxygen"))
M.reagents.remove_reagent("oxygen", 1)
M.bodytemperature -= 30
..()
return
datum/reagent/cryostylane/on_tick()
if(holder.has_reagent("oxygen"))
holder.remove_reagent("oxygen", 1)
holder.chem_temp -= 10
holder.handle_reactions()
..()
return
datum/reagent/cryostylane/reaction_turf(var/turf/simulated/T, var/volume)
if(volume >= 5)
for(var/mob/living/simple_animal/slime/M in T)
M.adjustToxLoss(rand(15,30))
datum/reagent/pyrosium
name = "Pyrosium"
id = "pyrosium"
description = "Comes into existence at 20K. As long as there is sufficient oxygen for it to react with, Pyrosium slowly cools all other reagents in the mob down to 0K."
color = "#B20000" // rgb: 139, 166, 233
/datum/chemical_reaction/pyrosium
name = "pyrosium"
id = "pyrosium"
result = "pyrosium"
required_reagents = list("stable_plasma" = 1, "radium" = 1, "phosphorus" = 1)
result_amount = 3
/datum/chemical_reaction/pyrosium/on_reaction(var/datum/reagents/holder, var/created_volume)
holder.chem_temp = 20 // also cools the fuck down
return
datum/reagent/pyrosium/on_mob_life(var/mob/living/M as mob)
if(M.reagents.has_reagent("oxygen"))
M.reagents.remove_reagent("oxygen", 1)
M.bodytemperature += 30
..()
return
datum/reagent/pyrosium/on_tick()
if(holder.has_reagent("oxygen"))
holder.remove_reagent("oxygen", 1)
holder.chem_temp += 10
holder.handle_reactions()
..()
return
@@ -0,0 +1,34 @@
/*
Credit goes to Cogwerks, and all the other goonstation coders
for the original idea and implementation of this over at goonstation.
THE REQUESTED DON'T PORT LIST: IF YOU PORT THESE THE GOONS WILL MURDER US IN OUR SLEEP SO PLEASE DON'T KTHX - Iamgoofball
Any of the Secret Chems
Goon in-joke chems (Eg. Cat Drugs, Hairgrownium)
Liquid Electricity
Rajajajah
/datum/reagent/blankgoonchembase
name = "blank goonchem base"
id = "blankgoonchembase"
description = "A blank chem"
reagent_state = LIQUID
color = "#60A584" // rgb: 96, 165, 132
/datum/reagent/blankgoonchembase/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
..()
return
/datum/chemical_reaction/blankgoonchembase
name = "blank goonchem base"
id = "blankgoonchembase"
result = "blankgoonchembase"
required_reagents = list("diphenhydramine" = 1, "morphine" = 1, "cleaner" = 1)
result_amount = 3
mix_message = "The mixture dries into a pale blue powder."
required_temp = 420
*/
@@ -0,0 +1,369 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
datum/reagent/polonium
name = "Polonium"
id = "polonium"
description = "Cause significant Radiation damage over time."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.1
datum/reagent/polonium/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.radiation += 8
..()
return
datum/reagent/histamine
name = "Histamine"
id = "histamine"
description = "A dose-dependent toxin, ranges from annoying to incredibly lethal."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.2
overdose_threshold = 30
datum/reagent/histamine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
switch(pick(1, 2, 3, 4))
if(1)
M << "<span class='danger'>You can barely see!</span>"
M.eye_blurry = 3
if(2)
M.emote("cough")
if(3)
M.emote("sneeze")
if(4)
if(prob(75))
M << "You scratch at an itch."
M.adjustBruteLoss(2*REM)
..()
return
datum/reagent/histamine/overdose_process(var/mob/living/M as mob)
M.adjustOxyLoss(pick(1,3)*REM)
M.adjustBruteLoss(pick(1,3)*REM)
M.adjustToxLoss(pick(1,3)*REM)
..()
return
datum/reagent/formaldehyde
name = "Formaldehyde"
id = "formaldehyde"
description = "Deals a moderate amount of Toxin damage over time. 10% chance to decay into 10-15 histamine."
reagent_state = LIQUID
color = "#CF3600"
datum/reagent/formaldehyde/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(1*REM)
if(prob(10))
M.reagents.add_reagent("histamine",pick(5,15))
M.reagents.remove_reagent("formaldehyde",1)
..()
return
/datum/chemical_reaction/formaldehyde
name = "formaldehyde"
id = "Formaldehyde"
result = "formaldehyde"
required_reagents = list("ethanol" = 1, "oxygen" = 1, "silver" = 1)
result_amount = 3
required_temp = 420
datum/reagent/venom
name = "Venom"
id = "venom"
description = "Will deal scaling amounts of Toxin and Brute damage over time. 25% chance to decay into 5-10 histamine."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.2
datum/reagent/venom/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss((0.1*volume)*REM)
M.adjustBruteLoss((0.1*volume)*REM)
if(prob(25))
M.reagents.add_reagent("histamine",pick(5,10))
M.reagents.remove_reagent("venom",1)
..()
return
datum/reagent/neurotoxin2
name = "Neurotoxin"
id = "neurotoxin2"
description = "Deals toxin and brain damage up to 60 before it slows down, causing confusion and a knockout after 17 elapsed cycles."
reagent_state = LIQUID
color = "#CF3600"
var/cycle_count = 0
metabolization_rate = 1
datum/reagent/neurotoxin2/on_mob_life(var/mob/living/M as mob)
cycle_count++
if(M.brainloss + M.toxloss <= 60)
M.adjustBrainLoss(1*REM)
M.adjustToxLoss(1*REM)
if(cycle_count == 17)
M.sleeping += 10 // buffed so it works
..()
return
/datum/chemical_reaction/neurotoxin2
name = "neurotoxin2"
id = "neurotoxin2"
result = "neurotoxin2"
required_reagents = list("space_drugs" = 1)
result_amount = 1
required_temp = 674
datum/reagent/cyanide
name = "Cyanide"
id = "cyanide"
description = "Deals toxin damage, alongside some oxygen loss. 8% chance of stun and some extra toxin damage."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.1
datum/reagent/cyanide/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(1.5*REM)
if(prob(10))
M.losebreath += 1
if(prob(8))
M << "You feel horrendously weak!"
M.Stun(2)
M.adjustToxLoss(2*REM)
..()
return
/datum/chemical_reaction/cyanide
name = "Cyanide"
id = "cyanide"
result = "cyanide"
required_reagents = list("oil" = 1, "ammonia" = 1, "oxygen" = 1)
result_amount = 3
required_temp = 380
/datum/reagent/questionmark // food poisoning
name = "Bad Food"
id = "????"
description = "????"
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.2
datum/reagent/questionmark/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(1*REM)
..()
return
datum/reagent/itching_powder
name = "Itching Powder"
id = "itching_powder"
description = "Lots of annoying random effects, chances to do some brute damage from scratching. 6% chance to decay into 1-3 units of histamine."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.3
/datum/reagent/itching_powder/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume)
if(method == TOUCH)
M.reagents.add_reagent("itching_powder", volume)
return
datum/reagent/itching_powder/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(prob(27))
M << "You scratch at your head."
M.adjustBruteLoss(0.2*REM)
if(prob(27))
M << "You scratch at your leg."
M.adjustBruteLoss(0.2*REM)
if(prob(27))
M << "You scratch at your arm."
M.adjustBruteLoss(0.2*REM)
if(prob(6))
M.reagents.add_reagent("histamine",rand(1,3))
M.reagents.remove_reagent("itching_powder",1)
..()
return
/datum/chemical_reaction/itching_powder
name = "Itching Powder"
id = "itching_powder"
result = "itching_powder"
required_reagents = list("fuel" = 1, "ammonia" = 1, "charcoal" = 1)
result_amount = 3
/datum/chemical_reaction/facid
name = "Fluorosulfuric acid"
id = "facid"
result = "facid"
required_reagents = list("sacid" = 1, "fluorine" = 1, "hydrogen" = 1, "potassium" = 1)
result_amount = 4
required_temp = 380
datum/reagent/initropidril
name = "Initropidril"
id = "initropidril"
description = "33% chance to hit with a random amount of toxin damage, 5-10% chances to cause stunning, suffocation, or immediate heart failure."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.4
datum/reagent/initropidril/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(prob(33))
M.adjustToxLoss(rand(5,25))
if(prob(7))
var/picked_option = rand(1,3)
switch(picked_option)
if(1)
M.Stun(3)
M.Weaken(3)
if(2)
M.losebreath += 10
M.adjustOxyLoss(rand(5,25))
if(3)
var/mob/living/carbon/human/H = M
if(!H.heart_attack)
H.visible_message("<span class = 'danger'>[H] clutches at their chest as if their heart stopped!</span>", "<span class = 'userdanger'>You clutch at your chest as if your heart stopped!</span>")
H.heart_attack = 1 // rip in pepperoni
else
H.losebreath += 10
H.adjustOxyLoss(rand(5,25))
..()
return
datum/reagent/pancuronium
name = "Pancuronium"
id = "pancuronium"
description = "Knocks you out after 30 seconds, 7% chance to cause some oxygen loss."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.2
datum/reagent/pancuronium/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(current_cycle >= 10)
M.SetParalysis(3)
if(prob(7))
M.losebreath += rand(3,5)
..()
return
datum/reagent/sodium_thiopental
name = "Sodium Thiopental"
id = "sodium_thiopental"
description = "Puts you to sleep after 30 seconds, along with some major stamina loss."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.7
datum/reagent/sodium_thiopental/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(current_cycle >= 10)
M.sleeping += 3
M.adjustStaminaLoss(10)
..()
return
datum/reagent/sulfonal
name = "Sulfonal"
id = "sulfonal"
description = "Deals some toxin damage, and puts you to sleep after 66 seconds."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.1
/datum/chemical_reaction/sulfonal
name = "sulfonal"
id = "sulfonal"
result = "sulfonal"
required_reagents = list("acetone" = 1, "diethylamine" = 1, "sulfur" = 1)
result_amount = 3
datum/reagent/sulfonal/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(current_cycle >= 22)
M.sleeping += 3
M.adjustToxLoss(1)
..()
return
datum/reagent/amanitin
name = "Amanitin"
id = "amanitin"
description = "On the last second that it's in you, it hits you with a stack of toxin damage based on how long it's been in you. The more you use, the longer it takes before anything happens, but the harder it hits when it does."
reagent_state = LIQUID
color = "#CF3600"
datum/reagent/amanitin/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
..()
return
datum/reagent/amanitin/on_mob_delete(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.adjustToxLoss(current_cycle*rand(2,4))
..()
datum/reagent/lipolicide
name = "Lipolicide"
id = "lipolicide"
description = "Deals some toxin damage unless they keep eating food. Will reduce nutrition values."
reagent_state = LIQUID
color = "#CF3600"
/datum/chemical_reaction/lipolicide
name = "lipolicide"
id = "lipolicide"
result = "lipolicide"
required_reagents = list("mercury" = 1, "diethylamine" = 1, "ephedrine" = 1)
result_amount = 3
datum/reagent/lipolicide/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(!holder.has_reagent("nutriment"))
M.adjustToxLoss(1)
M.nutrition -= 10 * REAGENTS_METABOLISM
M.overeatduration = 0
if(M.nutrition < 0)//Prevent from going into negatives.
M.nutrition = 0
..()
return
datum/reagent/coniine
name = "Coniine"
id = "coniine"
description = "Does moderate toxin damage and oxygen loss."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.05
datum/reagent/coniine/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
M.losebreath += 5
M.adjustToxLoss(2)
..()
return
datum/reagent/curare
name = "Curare"
id = "curare"
description = "Does some oxygen and toxin damage, weakens you after 33 seconds."
reagent_state = LIQUID
color = "#CF3600"
metabolization_rate = 0.1
datum/reagent/curare/on_mob_life(var/mob/living/M as mob)
if(!M) M = holder.my_atom
if(current_cycle >= 11)
M.Weaken(3)
M.adjustToxLoss(1)
M.adjustOxyLoss(1)
..()
return
@@ -0,0 +1,956 @@
#define SOLID 1
#define LIQUID 2
#define GAS 3
#define REM REAGENTS_EFFECT_MULTIPLIER
//The reaction procs must ALWAYS set src = null, this detaches the proc from the object (the reagent)
//so that it can continue working when the reagent is deleted while the proc is still active.
//Various reagents
//Toxin & acid reagents
//Hydroponics stuff
datum/reagent
var/name = "Reagent"
var/id = "reagent"
var/description = ""
var/datum/reagents/holder = null
var/reagent_state = LIQUID
var/list/data
var/current_cycle = 0
var/volume = 0
var/color = "#000000" // rgb: 0, 0, 0
var/can_synth = 1
var/metabolization_rate = REAGENTS_METABOLISM
var/overrides_metab = 0
var/overdose_threshold = 0
var/addiction_threshold = 0
var/addiction_stage = 0
var/overdosed = 0 // You fucked up and this is now triggering it's overdose effects, purge that shit quick.
datum/reagent/Destroy() // This should only be called by the holder, so it's already handled clearing its references
..()
holder = null
datum/reagent/proc/reaction_mob(var/mob/M, var/method=TOUCH, var/volume, var/show_message = 1) //By default we have a chance to transfer some
if(!istype(M, /mob/living))
return 0
var/datum/reagent/self = src
src = null //of the reagent to the mob on TOUCHING it.
if(!istype(self.holder.my_atom, /obj/effect/effect/chem_smoke))
// If the chemicals are in a smoke cloud, do not try to let the chemicals "penetrate" into the mob's system (balance station 13) -- Doohl
if(method == TOUCH)
var/chance = 1
var/block = 0
for(var/obj/item/clothing/C in M.get_equipped_items())
if(C.permeability_coefficient < chance) chance = C.permeability_coefficient
if(istype(C, /obj/item/clothing/suit/bio_suit))
// bio suits are just about completely fool-proof - Doohl
// kind of a hacky way of making bio suits more resistant to chemicals but w/e
if(prob(75))
block = 1
if(istype(C, /obj/item/clothing/head/bio_hood))
if(prob(75))
block = 1
chance = chance * 100
if(prob(chance) && !block)
if(M.reagents)
M.reagents.add_reagent(self.id,self.volume/2)
return 1
datum/reagent/proc/reaction_obj(var/obj/O, var/volume) //By default we transfer a small part of the reagent to the object
src = null //if it can hold reagents. nope!
//if(O.reagents)
// O.reagents.add_reagent(id,volume/3)
return
datum/reagent/proc/reaction_turf(var/turf/T, var/volume)
src = null
return
datum/reagent/proc/on_mob_life(var/mob/living/M as mob)
current_cycle++
if(!istype(M, /mob/living))
return //Noticed runtime errors from facid trying to damage ghosts, this should fix. --NEO
holder.remove_reagent(src.id, metabolization_rate * M.metabolism_efficiency) //By default it slowly disappears.
return
// Called when this reagent is removed while inside a mob
datum/reagent/proc/on_mob_delete(mob/M)
return
datum/reagent/proc/on_move(var/mob/M)
return
// Called after add_reagents creates a new reagent.
datum/reagent/proc/on_new(var/data)
return
// Called when two reagents of the same are mixing.
datum/reagent/proc/on_merge(var/data)
return
datum/reagent/proc/on_update(var/atom/A)
return
// Called every time reagent containers process.
datum/reagent/proc/on_tick(var/data)
return
// Called when the reagent container is hit by an explosion
datum/reagent/proc/on_ex_act(var/severity)
return
// Called if the reagent has passed the overdose threshold and is set to be triggering overdose effects
datum/reagent/proc/overdose_process(var/mob/living/M as mob)
return
datum/reagent/proc/overdose_start(var/mob/living/M as mob)
return
datum/reagent/proc/addiction_act_stage1(var/mob/living/M as mob)
if(prob(30))
M << "<span class = 'notice'>You feel like some [name] right about now.</span>"
return
datum/reagent/proc/addiction_act_stage2(var/mob/living/M as mob)
if(prob(30))
M << "<span class = 'notice'>You feel like you need [name]. You just can't get enough.</span>"
return
datum/reagent/proc/addiction_act_stage3(var/mob/living/M as mob)
if(prob(30))
M << "<span class = 'danger'>You have an intense craving for [name].</span>"
return
datum/reagent/proc/addiction_act_stage4(var/mob/living/M as mob)
if(prob(30))
M << "<span class = 'boldannounce'>You're not feeling good at all! You really need some [name].</span>"
return
datum/reagent/blood
data = list("donor"=null,"viruses"=null,"blood_DNA"=null,"blood_type"=null,"resistances"=null,"trace_chem"=null,"mind"=null,"ckey"=null,"gender"=null,"real_name"=null,"cloneable"=null,"factions"=null)
name = "Blood"
id = "blood"
color = "#C80000" // rgb: 200, 0, 0
datum/reagent/blood/reaction_mob(var/mob/M, var/method=TOUCH, var/volume)
var/datum/reagent/blood/self = src
src = null
if(self.data && self.data["viruses"])
for(var/datum/disease/D in self.data["viruses"])
if(D.spread_flags & SPECIAL || D.spread_flags & NON_CONTAGIOUS)
continue
if(method == TOUCH)
M.ContractDisease(D)
else //injected
M.ForceContractDisease(D)
datum/reagent/blood/on_new(var/list/data)
if(istype(data))
SetViruses(src, data)
datum/reagent/blood/on_merge(var/list/data)
if(src.data && data)
src.data["cloneable"] = 0 //On mix, consider the genetic sampling unviable for pod cloning, or else we won't know who's even getting cloned, etc
if(src.data["viruses"] || data["viruses"])
var/list/mix1 = src.data["viruses"]
var/list/mix2 = data["viruses"]
// Stop issues with the list changing during mixing.
var/list/to_mix = list()
for(var/datum/disease/advance/AD in mix1)
to_mix += AD
for(var/datum/disease/advance/AD in mix2)
to_mix += AD
var/datum/disease/advance/AD = Advance_Mix(to_mix)
if(AD)
var/list/preserve = list(AD)
for(var/D in src.data["viruses"])
if(!istype(D, /datum/disease/advance))
preserve += D
src.data["viruses"] = preserve
return 1
datum/reagent/blood/reaction_turf(var/turf/simulated/T, var/volume)//splash the blood all over the place
if(!istype(T)) return
var/datum/reagent/blood/self = src
src = null
if(!(volume >= 3)) return
//var/datum/disease/D = self.data["virus"]
if(!self.data["donor"] || istype(self.data["donor"], /mob/living/carbon/human))
var/obj/effect/decal/cleanable/blood/blood_prop = locate() in T //find some blood here
if(!blood_prop) //first blood!
blood_prop = new(T)
blood_prop.blood_DNA[self.data["blood_DNA"]] = self.data["blood_type"]
for(var/datum/disease/D in self.data["viruses"])
var/datum/disease/newVirus = D.Copy(1)
blood_prop.viruses += newVirus
newVirus.holder = blood_prop
else if(istype(self.data["donor"], /mob/living/carbon/monkey))
var/obj/effect/decal/cleanable/blood/blood_prop = locate() in T
if(!blood_prop)
blood_prop = new(T)
blood_prop.blood_DNA["Non-Human DNA"] = "A+"
for(var/datum/disease/D in self.data["viruses"])
var/datum/disease/newVirus = D.Copy(1)
blood_prop.viruses += newVirus
newVirus.holder = blood_prop
else if(istype(self.data["donor"], /mob/living/carbon/alien))
var/obj/effect/decal/cleanable/xenoblood/blood_prop = locate() in T
if(!blood_prop)
blood_prop = new(T)
blood_prop.blood_DNA["UNKNOWN DNA STRUCTURE"] = "X*"
for(var/datum/disease/D in self.data["viruses"])
var/datum/disease/newVirus = D.Copy(1)
blood_prop.viruses += newVirus
newVirus.holder = blood_prop
return
datum/reagent/vaccine
//data must contain virus type
name = "Vaccine"
id = "vaccine"
color = "#C81040" // rgb: 200, 16, 64
datum/reagent/vaccine/reaction_mob(var/mob/M, var/method=TOUCH, var/volume)
var/datum/reagent/vaccine/self = src
src = null
if(islist(self.data) && method == INGEST)
for(var/datum/disease/D in M.viruses)
if(D.GetDiseaseID() in self.data)
D.cure()
M.resistances |= self.data
return
datum/reagent/vaccine/on_merge(var/list/data)
if(istype(data))
src.data |= data.Copy()
datum/reagent/water
name = "Water"
id = "water"
description = "A ubiquitous chemical substance that is composed of hydrogen and oxygen."
color = "#AAAAAA77" // rgb: 170, 170, 170, 77 (alpha)
var/cooling_temperature = 2
/*
* Water reaction to turf
*/
datum/reagent/water/reaction_turf(var/turf/simulated/T, var/volume)
if (!istype(T)) return
var/CT = cooling_temperature
src = null
if(volume >= 10)
T.MakeSlippery()
for(var/mob/living/simple_animal/slime/M in T)
M.apply_water()
var/hotspot = (locate(/obj/effect/hotspot) in T)
if(hotspot && !istype(T, /turf/space))
if(T.air)
var/datum/gas_mixture/G = T.air
G.temperature = max(min(G.temperature-(CT*1000),G.temperature/CT),0)
G.react()
qdel(hotspot)
return
/*
* Water reaction to an object
*/
datum/reagent/water/reaction_obj(var/obj/O, var/volume)
src = null
// Monkey cube
if(istype(O,/obj/item/weapon/reagent_containers/food/snacks/monkeycube))
var/obj/item/weapon/reagent_containers/food/snacks/monkeycube/cube = O
if(!cube.wrapped)
cube.Expand()
// Dehydrated carp
if(istype(O,/obj/item/toy/carpplushie/dehy_carp))
var/obj/item/toy/carpplushie/dehy_carp/dehy = O
dehy.Swell() // Makes a carp
return
/*
* Water reaction to a mob
*/
datum/reagent/water/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume)//Splashing people with water can help put them out!
if(!istype(M, /mob/living))
return
if(method == TOUCH)
M.adjust_fire_stacks(-(volume / 10))
if(M.fire_stacks <= 0)
M.ExtinguishMob()
return
datum/reagent/water/holywater
name = "Holy Water"
id = "holywater"
description = "Water blessed by some deity."
color = "#E0E8EF" // rgb: 224, 232, 239
datum/reagent/water/holywater/on_mob_life(var/mob/living/M as mob)
if(!data) data = 1
data++
M.jitteriness = max(M.jitteriness-5,0)
if(data >= 30) // 12 units, 54 seconds @ metabolism 0.4 units & tick rate 1.8 sec
if (!M.stuttering) M.stuttering = 1
M.stuttering += 4
M.Dizzy(5)
if(iscultist(M) && prob(5))
M.say(pick("Av'te Nar'sie","Pa'lid Mors","INO INO ORA ANA","SAT ANA!","Daim'niodeis Arc'iai Le'eones","Egkau'haom'nai en Chaous","Ho Diak'nos tou Ap'iron","R'ge Na'sie","Diabo us Vo'iscum","Si gn'um Co'nu"))
if(data >= 75 && prob(33)) // 30 units, 135 seconds
if (!M.confused) M.confused = 1
M.confused += 3
if(iscultist(M))
ticker.mode.remove_cultist(M.mind)
holder.remove_reagent(src.id, src.volume) // maybe this is a little too perfect and a max() cap on the statuses would be better??
M.jitteriness = 0
M.stuttering = 0
M.confused = 0
holder.remove_reagent(src.id, 0.4) //fixed consumption to prevent balancing going out of whack
return
datum/reagent/water/holywater/reaction_turf(var/turf/simulated/T, var/volume)
..()
if(!istype(T)) return
if(volume>=10)
for(var/obj/effect/rune/R in T)
qdel(R)
T.Bless()
datum/reagent/fuel/unholywater //if you somehow managed to extract this from someone, dont splash it on yourself and have a smoke
name = "Unholy Water"
id = "unholywater"
description = "Something that shouldn't exist on this plane of existance."
datum/reagent/fuel/unholywater/on_mob_life(var/mob/living/M as mob)
M.adjustBrainLoss(3)
if(iscultist(M))
M.status_flags |= GOTTAGOFAST
M.drowsyness = max(M.drowsyness-5, 0)
M.AdjustParalysis(-2)
M.AdjustStunned(-2)
M.AdjustWeakened(-2)
else
M.adjustToxLoss(2)
M.adjustFireLoss(2)
M.adjustOxyLoss(2)
M.adjustBruteLoss(2)
holder.remove_reagent(src.id, 1)
datum/reagent/hellwater //if someone has this in their system they've really pissed off an eldrich god
name = "Hell Water"
id = "hell_water"
description = "YOUR FLESH! IT BURNS!"
datum/reagent/hellwater/on_mob_life(var/mob/living/M as mob)
M.fire_stacks = min(5,M.fire_stacks + 3)
M.IgniteMob() //Only problem with igniting people is currently the commonly availible fire suits make you immune to being on fire
M.adjustToxLoss(1)
M.adjustFireLoss(1) //Hence the other damages... ain't I a bastard?
M.adjustBrainLoss(5)
holder.remove_reagent(src.id, 1)
datum/reagent/lube
name = "Space Lube"
id = "lube"
description = "Lubricant is a substance introduced between two moving surfaces to reduce the friction and wear between them. giggity."
color = "#009CA8" // rgb: 0, 156, 168
datum/reagent/lube/reaction_turf(var/turf/simulated/T, var/volume)
if (!istype(T)) return
src = null
if(volume >= 1)
T.MakeSlippery(2)
datum/reagent/slimetoxin
name = "Mutation Toxin"
id = "mutationtoxin"
description = "A corruptive toxin produced by slimes."
color = "#13BC5E" // rgb: 19, 188, 94
datum/reagent/unstableslimetoxin
name = "Unstable Mutation Toxin"
id = "unstablemutationtoxin"
description = "An unstable and unpredictable corruptive toxin produced by slimes."
color = "#5EFF3B" //RGB: 94, 255, 59
metabolization_rate = INFINITY //So it instantly removes all of itself
datum/reagent/unstableslimetoxin/on_mob_life(var/mob/living/carbon/human/H as mob)
..()
H << "<span class='warning'><b>You crumple in agony as your flesh wildly morphs into new forms!</b></span>"
H.visible_message("<b>[H]</b> falls to the ground and screams as their skin bubbles and froths!") //'froths' sounds painful when used with SKIN.
H.Weaken(3)
sleep(30)
var/list/blacklisted_species = list(/datum/species/zombie, /datum/species/skeleton, /datum/species/human, /datum/species/golem, /datum/species/golem/adamantine, /datum/species/shadow)
var/list/possible_morphs = typesof(/datum/species/) - blacklisted_species
var/datum/species/mutation = pick(possible_morphs)
if(prob(90) && mutation && H.dna.species != /datum/species/golem && H.dna.species != /datum/species/golem/adamantine)
H << "<span class='danger'>The pain subsides. You feel... different.</span>"
H.dna.species = new mutation()
H.regenerate_icons()
if(mutation == /datum/species/slime)
H.faction |= "slime"
else
H.faction -= "slime"
else
H << "<span class='danger'>The pain vanishes suddenly. You feel no different.</span>"
return 1
datum/reagent/aslimetoxin
name = "Advanced Mutation Toxin"
id = "amutationtoxin"
description = "An advanced corruptive toxin produced by slimes."
color = "#13BC5E" // rgb: 19, 188, 94
datum/reagent/aslimetoxin/reaction_mob(var/mob/M, var/volume)
src = null
M.ForceContractDisease(new /datum/disease/transformation/slime(0))
datum/reagent/space_drugs
name = "Space drugs"
id = "space_drugs"
description = "An illegal chemical compound used as drug."
color = "#60A584" // rgb: 96, 165, 132
metabolization_rate = 0.5 * REAGENTS_METABOLISM
datum/reagent/space_drugs/on_mob_life(var/mob/living/M as mob)
M.druggy = max(M.druggy, 15)
if(isturf(M.loc) && !istype(M.loc, /turf/space))
if(M.canmove)
if(prob(10)) step(M, pick(cardinal))
if(prob(7)) M.emote(pick("twitch","drool","moan","giggle"))
..()
return
datum/reagent/serotrotium
name = "Serotrotium"
id = "serotrotium"
description = "A chemical compound that promotes concentrated production of the serotonin neurotransmitter in humans."
color = "#202040" // rgb: 20, 20, 40
metabolization_rate = 0.25 * REAGENTS_METABOLISM
datum/reagent/serotrotium/on_mob_life(var/mob/living/M as mob)
if(ishuman(M))
if(prob(7)) M.emote(pick("twitch","drool","moan","gasp"))
..()
return
datum/reagent/oxygen
name = "Oxygen"
id = "oxygen"
description = "A colorless, odorless gas."
reagent_state = GAS
color = "#808080" // rgb: 128, 128, 128
datum/reagent/copper
name = "Copper"
id = "copper"
description = "A highly ductile metal."
reagent_state = SOLID
color = "#6E3B08" // rgb: 110, 59, 8
datum/reagent/nitrogen
name = "Nitrogen"
id = "nitrogen"
description = "A colorless, odorless, tasteless gas."
reagent_state = GAS
color = "#808080" // rgb: 128, 128, 128
datum/reagent/hydrogen
name = "Hydrogen"
id = "hydrogen"
description = "A colorless, odorless, nonmetallic, tasteless, highly combustible diatomic gas."
reagent_state = GAS
color = "#808080" // rgb: 128, 128, 128
datum/reagent/potassium
name = "Potassium"
id = "potassium"
description = "A soft, low-melting solid that can easily be cut with a knife. Reacts violently with water."
reagent_state = SOLID
color = "#A0A0A0" // rgb: 160, 160, 160
datum/reagent/mercury
name = "Mercury"
id = "mercury"
description = "A chemical element."
color = "#484848" // rgb: 72, 72, 72
datum/reagent/mercury/on_mob_life(var/mob/living/M as mob)
if(M.canmove && istype(M.loc, /turf/space))
step(M, pick(cardinal))
if(prob(5))
M.emote(pick("twitch","drool","moan"))
M.adjustBrainLoss(2)
..()
return
datum/reagent/sulfur
name = "Sulfur"
id = "sulfur"
description = "A chemical element."
reagent_state = SOLID
color = "#BF8C00" // rgb: 191, 140, 0
datum/reagent/carbon
name = "Carbon"
id = "carbon"
description = "A chemical element."
reagent_state = SOLID
color = "#1C1300" // rgb: 30, 20, 0
datum/reagent/carbon/reaction_turf(var/turf/T, var/volume)
src = null
if(!istype(T, /turf/space))
new /obj/effect/decal/cleanable/dirt(T)
datum/reagent/chlorine
name = "Chlorine"
id = "chlorine"
description = "A chemical element."
reagent_state = GAS
color = "#808080" // rgb: 128, 128, 128
datum/reagent/chlorine/on_mob_life(var/mob/living/M as mob)
M.take_organ_damage(1*REM, 0)
..()
return
datum/reagent/fluorine
name = "Fluorine"
id = "fluorine"
description = "A highly-reactive chemical element."
reagent_state = GAS
color = "#808080" // rgb: 128, 128, 128
datum/reagent/fluorine/on_mob_life(var/mob/living/M as mob)
M.adjustToxLoss(1*REM)
..()
return
datum/reagent/sodium
name = "Sodium"
id = "sodium"
description = "A chemical element."
reagent_state = SOLID
color = "#808080" // rgb: 128, 128, 128
datum/reagent/phosphorus
name = "Phosphorus"
id = "phosphorus"
description = "A chemical element."
reagent_state = SOLID
color = "#832828" // rgb: 131, 40, 40
datum/reagent/lithium
name = "Lithium"
id = "lithium"
description = "A chemical element."
reagent_state = SOLID
color = "#808080" // rgb: 128, 128, 128
datum/reagent/lithium/on_mob_life(var/mob/living/M as mob)
if(M.canmove && istype(M.loc, /turf/space))
step(M, pick(cardinal))
if(prob(5))
M.emote(pick("twitch","drool","moan"))
..()
return
datum/reagent/glycerol
name = "Glycerol"
id = "glycerol"
description = "Glycerol is a simple polyol compound. Glycerol is sweet-tasting and of low toxicity."
color = "#808080" // rgb: 128, 128, 128
datum/reagent/nitroglycerin
name = "Nitroglycerin"
id = "nitroglycerin"
description = "Nitroglycerin is a heavy, colorless, oily, explosive liquid obtained by nitrating glycerol."
color = "#808080" // rgb: 128, 128, 128
datum/reagent/radium
name = "Radium"
id = "radium"
description = "Radium is an alkaline earth metal. It is extremely radioactive."
reagent_state = SOLID
color = "#C7C7C7" // rgb: 199,199,199
datum/reagent/radium/on_mob_life(var/mob/living/M as mob)
M.apply_effect(2*REM/M.metabolism_efficiency,IRRADIATE,0)
..()
return
datum/reagent/radium/reaction_turf(var/turf/T, var/volume)
src = null
if(volume >= 3)
if(!istype(T, /turf/space))
var/obj/effect/decal/cleanable/reagentdecal = new/obj/effect/decal/cleanable/greenglow(T)
reagentdecal.reagents.add_reagent("uranium", volume)
datum/reagent/thermite
name = "Thermite"
id = "thermite"
description = "Thermite produces an aluminothermic reaction known as a thermite reaction. Can be used to melt walls."
reagent_state = SOLID
color = "#673910" // rgb: 103, 57, 16
datum/reagent/thermite/reaction_turf(var/turf/T, var/volume)
src = null
if(volume >= 1 && istype(T, /turf/simulated/wall))
var/turf/simulated/wall/Wall = T
if(istype(Wall, /turf/simulated/wall/r_wall))
Wall.thermite = Wall.thermite+(volume*2.5)
else
Wall.thermite = Wall.thermite+(volume*10)
Wall.overlays = list()
Wall.overlays += image('icons/effects/effects.dmi',"thermite")
return
datum/reagent/thermite/on_mob_life(var/mob/living/M as mob)
M.adjustFireLoss(1)
..()
return
datum/reagent/sterilizine
name = "Sterilizine"
id = "sterilizine"
description = "Sterilizes wounds in preparation for surgery."
color = "#C8A5DC" // rgb: 200, 165, 220
datum/reagent/iron
name = "Iron"
id = "iron"
description = "Pure iron is a metal."
reagent_state = SOLID
color = "#C8A5DC" // rgb: 200, 165, 220
datum/reagent/gold
name = "Gold"
id = "gold"
description = "Gold is a dense, soft, shiny metal and the most malleable and ductile metal known."
reagent_state = SOLID
color = "#F7C430" // rgb: 247, 196, 48
datum/reagent/silver
name = "Silver"
id = "silver"
description = "A soft, white, lustrous transition metal, it has the highest electrical conductivity of any element and the highest thermal conductivity of any metal."
reagent_state = SOLID
color = "#D0D0D0" // rgb: 208, 208, 208
datum/reagent/uranium
name ="Uranium"
id = "uranium"
description = "A silvery-white metallic chemical element in the actinide series, weakly radioactive."
reagent_state = SOLID
color = "#B8B8C0" // rgb: 184, 184, 192
datum/reagent/uranium/on_mob_life(var/mob/living/M as mob)
M.apply_effect(1/M.metabolism_efficiency,IRRADIATE,0)
..()
return
datum/reagent/uranium/reaction_turf(var/turf/T, var/volume)
src = null
if(volume >= 3)
if(!istype(T, /turf/space))
var/obj/effect/decal/cleanable/reagentdecal = new/obj/effect/decal/cleanable/greenglow(T)
reagentdecal.reagents.add_reagent("uranium", volume)
datum/reagent/aluminium
name = "Aluminium"
id = "aluminium"
description = "A silvery white and ductile member of the boron group of chemical elements."
reagent_state = SOLID
color = "#A8A8A8" // rgb: 168, 168, 168
datum/reagent/silicon
name = "Silicon"
id = "silicon"
description = "A tetravalent metalloid, silicon is less reactive than its chemical analog carbon."
reagent_state = SOLID
color = "#A8A8A8" // rgb: 168, 168, 168
datum/reagent/fuel
name = "Welding fuel"
id = "fuel"
description = "Required for welders. Flamable."
color = "#660000" // rgb: 102, 0, 0
datum/reagent/fuel/reaction_mob(var/mob/living/M, var/method=TOUCH, var/volume)//Splashing people with welding fuel to make them easy to ignite!
if(!istype(M, /mob/living))
return
if(method == TOUCH)
M.adjust_fire_stacks(volume / 10)
return
datum/reagent/fuel/on_mob_life(var/mob/living/M as mob)
M.adjustToxLoss(1)
..()
return
datum/reagent/space_cleaner
name = "Space cleaner"
id = "cleaner"
description = "A compound used to clean things. Now with 50% more sodium hypochlorite!"
color = "#A5F0EE" // rgb: 165, 240, 238
datum/reagent/space_cleaner/reaction_obj(var/obj/O, var/volume)
if(istype(O,/obj/effect/decal/cleanable))
qdel(O)
else
if(O)
O.clean_blood()
datum/reagent/space_cleaner/reaction_turf(var/turf/T, var/volume)
if(volume >= 1)
T.clean_blood()
for(var/obj/effect/decal/cleanable/C in T)
qdel(C)
for(var/mob/living/simple_animal/slime/M in T)
M.adjustToxLoss(rand(5,10))
if(istype(T, /turf/simulated/floor))
var/turf/simulated/floor/F = T
if(volume >= 1)
F.dirt = 0
datum/reagent/space_cleaner/reaction_mob(var/mob/M, var/method=TOUCH, var/volume)
if(iscarbon(M))
var/mob/living/carbon/C = M
if(istype(M,/mob/living/carbon/human))
var/mob/living/carbon/human/H = M
if(H.lip_style)
H.lip_style = null
H.update_body()
if(C.r_hand)
C.r_hand.clean_blood()
if(C.l_hand)
C.l_hand.clean_blood()
if(C.wear_mask)
if(C.wear_mask.clean_blood())
C.update_inv_wear_mask(0)
if(ishuman(M))
var/mob/living/carbon/human/H = C
if(H.head)
if(H.head.clean_blood())
H.update_inv_head(0)
if(H.wear_suit)
if(H.wear_suit.clean_blood())
H.update_inv_wear_suit(0)
else if(H.w_uniform)
if(H.w_uniform.clean_blood())
H.update_inv_w_uniform(0)
if(H.shoes)
if(H.shoes.clean_blood())
H.update_inv_shoes(0)
M.clean_blood()
datum/reagent/cryptobiolin
name = "Cryptobiolin"
id = "cryptobiolin"
description = "Cryptobiolin causes confusion and dizzyness."
color = "#C8A5DC" // rgb: 200, 165, 220
metabolization_rate = 1.5 * REAGENTS_METABOLISM
datum/reagent/cryptobiolin/on_mob_life(var/mob/living/M as mob)
M.Dizzy(1)
if(!M.confused)
M.confused = 1
M.confused = max(M.confused, 20)
..()
return
datum/reagent/impedrezene
name = "Impedrezene"
id = "impedrezene"
description = "Impedrezene is a narcotic that impedes one's ability by slowing down the higher brain cell functions."
color = "#C8A5DC" // rgb: 200, 165, 220
datum/reagent/impedrezene/on_mob_life(var/mob/living/M as mob)
M.jitteriness = max(M.jitteriness-5,0)
if(prob(80)) M.adjustBrainLoss(1*REM)
if(prob(50)) M.drowsyness = max(M.drowsyness, 3)
if(prob(10)) M.emote("drool")
..()
return
datum/reagent/nanites
name = "Nanomachines"
id = "nanomachines"
description = "Microscopic construction robots."
color = "#535E66" // rgb: 83, 94, 102
datum/reagent/nanites/reaction_mob(var/mob/M, var/method=TOUCH, var/volume)
src = null
if( (prob(10) && method==TOUCH) || method==INGEST)
M.ForceContractDisease(new /datum/disease/transformation/robot(0))
datum/reagent/xenomicrobes
name = "Xenomicrobes"
id = "xenomicrobes"
description = "Microbes with an entirely alien cellular structure."
color = "#535E66" // rgb: 83, 94, 102
datum/reagent/xenomicrobes/reaction_mob(var/mob/M, var/method=TOUCH, var/volume)
src = null
if( (prob(10) && method==TOUCH) || method==INGEST)
M.ContractDisease(new /datum/disease/transformation/xeno(0))
datum/reagent/fluorosurfactant//foam precursor
name = "Fluorosurfactant"
id = "fluorosurfactant"
description = "A perfluoronated sulfonic acid that forms a foam when mixed with water."
color = "#9E6B38" // rgb: 158, 107, 56
datum/reagent/foaming_agent// Metal foaming agent. This is lithium hydride. Add other recipes (e.g. LiH + H2O -> LiOH + H2) eventually.
name = "Foaming agent"
id = "foaming_agent"
description = "A agent that yields metallic foam when mixed with light metal and a strong acid."
reagent_state = SOLID
color = "#664B63" // rgb: 102, 75, 99
datum/reagent/ammonia
name = "Ammonia"
id = "ammonia"
description = "A caustic substance commonly used in fertilizer or household cleaners."
reagent_state = GAS
color = "#404030" // rgb: 64, 64, 48
datum/reagent/diethylamine
name = "Diethylamine"
id = "diethylamine"
description = "A secondary amine, mildly corrosive."
color = "#604030" // rgb: 96, 64, 48
/////////////////////////Coloured Crayon Powder////////////////////////////
//For colouring in /proc/mix_color_from_reagents
datum/reagent/crayonpowder
name = "Crayon Powder"
id = "crayon powder"
var/colorname = "none"
description = "A powder made by grinding down crayons, good for colouring chemical reagents."
reagent_state = SOLID
color = "#FFFFFF" // rgb: 207, 54, 0
datum/reagent/crayonpowder/New()
description = "\an [colorname] powder made by grinding down crayons, good for colouring chemical reagents."
datum/reagent/crayonpowder/red
name = "Red Crayon Powder"
id = "redcrayonpowder"
colorname = "red"
datum/reagent/crayonpowder/orange
name = "Orange Crayon Powder"
id = "orangecrayonpowder"
colorname = "orange"
color = "#FF9300" // orange
datum/reagent/crayonpowder/yellow
name = "Yellow Crayon Powder"
id = "yellowcrayonpowder"
colorname = "yellow"
color = "#FFF200" // yellow
datum/reagent/crayonpowder/green
name = "Green Crayon Powder"
id = "greencrayonpowder"
colorname = "green"
color = "#A8E61D" // green
datum/reagent/crayonpowder/blue
name = "Blue Crayon Powder"
id = "bluecrayonpowder"
colorname = "blue"
color = "#00B7EF" // blue
datum/reagent/crayonpowder/purple
name = "Purple Crayon Powder"
id = "purplecrayonpowder"
colorname = "purple"
color = "#DA00FF" // purple
datum/reagent/crayonpowder/invisible
name = "Invisible Crayon Powder"
id = "invisiblecrayonpowder"
colorname = "invisible"
color = "#FFFFFF00" // white + no alpha
//////////////////////////////////Hydroponics stuff///////////////////////////////
datum/reagent/plantnutriment
name = "Generic nutriment"
id = "plantnutriment"
description = "Some kind of nutriment. You can't really tell what it is. You should probably report it, along with how you obtained it."
color = "#000000" // RBG: 0, 0, 0
var/tox_prob = 0
datum/reagent/plantnutriment/on_mob_life(var/mob/living/M as mob)
if(prob(tox_prob))
M.adjustToxLoss(1*REM)
..()
return
datum/reagent/plantnutriment/eznutriment
name = "E-Z-Nutrient"
id = "eznutriment"
description = "Cheap and extremely common type of plant nutriment."
color = "#376400" // RBG: 50, 100, 0
tox_prob = 10
datum/reagent/plantnutriment/left4zednutriment
name = "Left 4 Zed"
id = "left4zednutriment"
description = "Unstable nutriment that makes plants mutate more often than usual."
color = "#1A1E4D" // RBG: 26, 30, 77
tox_prob = 25
datum/reagent/plantnutriment/robustharvestnutriment
name = "Robust Harvest"
id = "robustharvestnutriment"
description = "Very potent nutriment that prevents plants from mutating."
color = "#9D9D00" // RBG: 157, 157, 0
tox_prob = 15
// Undefine the alias for REAGENTS_EFFECT_MULTIPLER
#undef REM
@@ -46,7 +46,6 @@ datum/reagent/drug/nicotine/on_mob_life(var/mob/living/M as mob)
M.adjustStaminaLoss(-0.5*REM)
..()
M << "<span class='notice'>You feel like you smoked too much.</span>"
datum/reagent/drug/crank
name = "Crank"
id = "crank"
+61
View File
@@ -0,0 +1,61 @@
/obj/item/weapon/gun/grenadelauncher
name = "grenade launcher"
desc = "a terrible, terrible thing. it's really awful!"
icon = 'icons/obj/guns/projectile.dmi'
icon_state = "riotgun"
item_state = "riotgun"
w_class = 4.0
throw_speed = 2
throw_range = 7
force = 5.0
var/list/grenades = new/list()
var/max_grenades = 3
m_amt = 2000
/obj/item/weapon/gun/grenadelauncher/examine(mob/user)
..()
user << "[grenades] / [max_grenades] grenades loaded."
/obj/item/weapon/gun/grenadelauncher/attackby(obj/item/I as obj, mob/user as mob, params)
if((istype(I, /obj/item/weapon/grenade)))
if(grenades.len < max_grenades)
user.drop_item()
I.loc = src
grenades += I
user << "<span class='notice'>You put the grenade in the grenade launcher.</span>"
user << "<span class='notice'>[grenades.len] / [max_grenades] Grenades.</span>"
else
usr << "<span class='warning'>The grenade launcher cannot hold more grenades!</span>"
/obj/item/weapon/gun/grenadelauncher/afterattack(obj/target, mob/user , flag)
if (istype(target, /obj/item/weapon/storage/backpack ))
return
else if (locate (/obj/structure/table, src.loc))
return
else if(target == user)
return
if(grenades.len)
spawn(0) fire_grenade(target,user)
else
usr << "<span class='warning'>The grenade launcher is empty!</span>"
/obj/item/weapon/gun/grenadelauncher/proc/fire_grenade(atom/target, mob/user)
for(var/mob/O in viewers(world.view, user))
O.show_message(text("<span class='danger'>[] fired a grenade!</span>", user), 1)
user << "<span class='danger'>You fire the grenade launcher!</span>"
var/obj/item/weapon/grenade/chem_grenade/F = grenades[1] //Now with less copypasta!
grenades -= F
F.loc = user.loc
F.throw_at(target, 30, 2)
message_admins("[key_name_admin(user)] fired a grenade ([F.name]) from a grenade launcher ([src.name]).")
log_game("[key_name(user)] fired a grenade ([F.name]) from a grenade launcher ([src.name]).")
F.active = 1
F.icon_state = initial(icon_state) + "_active"
playsound(user.loc, 'sound/weapons/armbomb.ogg', 75, 1, -3)
spawn(15)
F.prime()
+77
View File
@@ -0,0 +1,77 @@
/obj/item/weapon/gun/syringe
name = "syringe gun"
desc = "A spring loaded rifle designed to fit syringes, used to incapacitate unruly patients from a distance."
icon_state = "syringegun"
item_state = "syringegun"
w_class = 3
throw_speed = 3
throw_range = 7
force = 4
m_amt = 2000
clumsy_check = 0
fire_sound = 'sound/items/syringeproj.ogg'
var/list/syringes = list()
var/max_syringes = 1
/obj/item/weapon/gun/syringe/New()
..()
chambered = new /obj/item/ammo_casing/syringegun(src)
/obj/item/weapon/gun/syringe/proc/newshot()
if(!syringes.len) return
var/obj/item/weapon/reagent_containers/syringe/S = syringes[1]
if(!S) return
chambered.BB = new /obj/item/projectile/bullet/dart/syringe(src)
S.reagents.trans_to(chambered.BB, S.reagents.total_volume)
chambered.BB.name = S.name
syringes.Remove(S)
qdel(S)
return
/obj/item/weapon/gun/syringe/process_chamber()
return
/obj/item/weapon/gun/syringe/afterattack(atom/target as mob|obj|turf, mob/living/user as mob|obj, params)
newshot()
..()
/obj/item/weapon/gun/syringe/examine(mob/user)
..()
user << "Can hold [max_syringes] syringe\s. Has [syringes.len] syringe\s remaining."
/obj/item/weapon/gun/syringe/attack_self(mob/living/user as mob)
if(!syringes.len)
user << "<span class='notice'>[src] is empty.</span>"
return 0
var/obj/item/weapon/reagent_containers/syringe/S = syringes[syringes.len]
if(!S) return 0
S.loc = user.loc
syringes.Remove(S)
user << "<span class ='notice'>You unload [S] from \the [src].</span>"
return 1
/obj/item/weapon/gun/syringe/attackby(var/obj/item/A as obj, mob/user as mob, params, var/show_msg = 1)
if(istype(A, /obj/item/weapon/reagent_containers/syringe))
if(syringes.len < max_syringes)
user.drop_item()
user << "<span class='notice'>You load [A] into \the [src].</span>"
syringes.Add(A)
A.loc = src
return 1
else
usr << "<span class='warning'>[src] cannot hold more syringes!</span>"
return 0
/obj/item/weapon/gun/syringe/rapidsyringe
name = "rapid syringe gun"
desc = "A modification of the syringe gun design, using a rotating cylinder to store up to six syringes."
icon_state = "rapidsyringegun"
max_syringes = 6