"
-
- body += "E - Edit, tries to determine the variable type by itself. "
- body += "C - Change, asks you for the var type first. "
- body += "M - Mass modify: changes this variable for all objects of this type. "
-
- body += "
Search:
"
-
- body += ""
-
- var/list/names = list()
- for (var/V in D.vars)
- names += V
-
- names = sortList(names)
-
- for (var/V in names)
- body += debug_variable(V, D.vars[V], 0, D)
-
- body += ""
-
- var/html = ""
- if (title)
- html += "[title]"
- html += {""}
- html += ""
- html += body
-
- html += {"
-
- "}
-
- html += ""
-
- usr << browse(html, "window=variables\ref[D];size=475x650")
-
- return
-
- proc/debug_variable(name, value, level, var/datum/DA = null)
- var/html = ""
-
- if(DA)
- html += "
"
-
- if (isnull(value))
- html += "[name] = null"
-
- else if (istext(value))
- html += "[name] = \"[value]\""
-
- else if (isicon(value))
- #ifdef VARSICON
- var/icon/I = new/icon(value)
- var/rnd = rand(1,10000)
- var/rname = "tmp\ref[I][rnd].png"
- usr << browse_rsc(I, rname)
- html += "[name] = ([value]) "
- #else
- html += "[name] = /icon ([value])"
- #endif
-
-/* else if (istype(value, /image))
- #ifdef VARSICON
- var/rnd = rand(1, 10000)
- var/image/I = value
-
- src << browse_rsc(I.icon, "tmp\ref[value][rnd].png")
- html += "[name] = "
- #else
- html += "[name] = /image ([value])"
- #endif
-*/
- else if (isfile(value))
- html += "[name] = '[value]'"
-
- else if (istype(value, /datum))
- var/datum/D = value
- html += "[name] \ref[value] = [D.type]"
-
- else if (istype(value, /client))
- var/client/C = value
- html += "[name] \ref[value] = [C] [C.type]"
- //
- else if (istype(value, /list))
- var/list/L = value
- html += "[name] = /list ([L.len])"
-
- if (L.len > 0 && !(name == "underlays" || name == "overlays" || name == "vars" || L.len > 500))
- // not sure if this is completely right...
- if(0) //(L.vars.len > 0)
- html += ""
- html += ""
- else
- html += "
"
- var/index = 1
- for (var/entry in L)
- if(istext(entry))
- html += debug_variable(entry, L[entry], level + 1)
- //html += debug_variable("[index]", L[index], level + 1)
- else
- html += debug_variable(index, L[index], level + 1)
- index++
- html += "
"
-
- else
- html += "[name] = [value]"
-
- html += "
"
-
- return html
-
-/client/proc/view_var_Topic(href, href_list, hsrc)
- //This should all be moved over to datum/admins/Topic() or something ~Carn
- if( (usr.client != src) || !src.holder )
- return
- if(href_list["Vars"])
- debug_variables(locate(href_list["Vars"]))
-
- //~CARN: for renaming mobs (updates their name, real_name, mind.name, their ID/PDA and datacore records).
- else if(href_list["rename"])
- if(!check_rights(R_VAREDIT)) return
-
- var/mob/M = locate(href_list["rename"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- var/new_name = sanitize(input(usr,"What would you like to name this mob?","Input a name",M.real_name) as text|null, MAX_NAME_LEN)
- if( !new_name || !M ) return
-
- message_admins("Admin [key_name_admin(usr)] renamed [key_name_admin(M)] to [new_name].")
- M.fully_replace_character_name(M.real_name,new_name)
- href_list["datumrefresh"] = href_list["rename"]
-
- else if(href_list["varnameedit"] && href_list["datumedit"])
- if(!check_rights(R_VAREDIT)) return
-
- var/D = locate(href_list["datumedit"])
- if(!istype(D,/datum) && !istype(D,/client))
- usr << "This can only be used on instances of types /client or /datum"
- return
-
- modify_variables(D, href_list["varnameedit"], 1)
-
- else if(href_list["varnamechange"] && href_list["datumchange"])
- if(!check_rights(R_VAREDIT)) return
-
- var/D = locate(href_list["datumchange"])
- if(!istype(D,/datum) && !istype(D,/client))
- usr << "This can only be used on instances of types /client or /datum"
- return
-
- modify_variables(D, href_list["varnamechange"], 0)
-
- else if(href_list["varnamemass"] && href_list["datummass"])
- if(!check_rights(R_VAREDIT)) return
-
- var/atom/A = locate(href_list["datummass"])
- if(!istype(A))
- usr << "This can only be used on instances of type /atom"
- return
-
- cmd_mass_modify_object_variables(A, href_list["varnamemass"])
-
- else if(href_list["mob_player_panel"])
- if(!check_rights(0)) return
-
- var/mob/M = locate(href_list["mob_player_panel"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.holder.show_player_panel(M)
- href_list["datumrefresh"] = href_list["mob_player_panel"]
-
- else if(href_list["give_spell"])
- if(!check_rights(R_ADMIN|R_FUN)) return
-
- var/mob/M = locate(href_list["give_spell"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.give_spell(M)
- href_list["datumrefresh"] = href_list["give_spell"]
-
- else if(href_list["give_disease"])
- if(!check_rights(R_ADMIN|R_FUN)) return
-
- var/mob/M = locate(href_list["give_disease"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.give_disease(M)
- href_list["datumrefresh"] = href_list["give_spell"]
-
- else if(href_list["give_disease2"])
- if(!check_rights(R_ADMIN|R_FUN)) return
-
- var/mob/M = locate(href_list["give_disease2"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.give_disease2(M)
- href_list["datumrefresh"] = href_list["give_spell"]
-
- else if(href_list["godmode"])
- if(!check_rights(R_REJUVINATE)) return
-
- var/mob/M = locate(href_list["godmode"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.cmd_admin_godmode(M)
- href_list["datumrefresh"] = href_list["godmode"]
-
- else if(href_list["gib"])
- if(!check_rights(0)) return
-
- var/mob/M = locate(href_list["gib"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- src.cmd_admin_gib(M)
-
- else if(href_list["build_mode"])
- if(!check_rights(R_BUILDMODE)) return
-
- var/mob/M = locate(href_list["build_mode"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- togglebuildmode(M)
- href_list["datumrefresh"] = href_list["build_mode"]
-
- else if(href_list["drop_everything"])
- if(!check_rights(R_DEBUG|R_ADMIN)) return
-
- var/mob/M = locate(href_list["drop_everything"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- if(usr.client)
- usr.client.cmd_admin_drop_everything(M)
-
- else if(href_list["direct_control"])
- if(!check_rights(0)) return
-
- var/mob/M = locate(href_list["direct_control"])
- if(!istype(M))
- usr << "This can only be used on instances of type /mob"
- return
-
- if(usr.client)
- usr.client.cmd_assume_direct_control(M)
-
- else if(href_list["make_skeleton"])
- if(!check_rights(R_FUN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["make_skeleton"])
- if(!istype(H))
- usr << "This can only be used on instances of type /mob/living/carbon/human"
- return
-
- H.ChangeToSkeleton()
- href_list["datumrefresh"] = href_list["make_skeleton"]
-
- else if(href_list["delall"])
- if(!check_rights(R_DEBUG|R_SERVER)) return
-
- var/obj/O = locate(href_list["delall"])
- if(!isobj(O))
- usr << "This can only be used on instances of type /obj"
- return
-
- var/action_type = alert("Strict type ([O.type]) or type and all subtypes?",,"Strict type","Type and subtypes","Cancel")
- if(action_type == "Cancel" || !action_type)
- return
-
- if(alert("Are you really sure you want to delete all objects of type [O.type]?",,"Yes","No") != "Yes")
- return
-
- if(alert("Second confirmation required. Delete?",,"Yes","No") != "Yes")
- return
-
- var/O_type = O.type
- switch(action_type)
- if("Strict type")
- var/i = 0
- for(var/obj/Obj in world)
- if(Obj.type == O_type)
- i++
- del(Obj)
- if(!i)
- usr << "No objects of this type exist"
- return
- log_admin("[key_name(usr)] deleted all objects of type [O_type] ([i] objects deleted) ")
- message_admins("\blue [key_name(usr)] deleted all objects of type [O_type] ([i] objects deleted) ")
- if("Type and subtypes")
- var/i = 0
- for(var/obj/Obj in world)
- if(istype(Obj,O_type))
- i++
- del(Obj)
- if(!i)
- usr << "No objects of this type exist"
- return
- log_admin("[key_name(usr)] deleted all objects of type or subtype of [O_type] ([i] objects deleted) ")
- message_admins("\blue [key_name(usr)] deleted all objects of type or subtype of [O_type] ([i] objects deleted) ")
-
- else if(href_list["explode"])
- if(!check_rights(R_DEBUG|R_FUN)) return
-
- var/atom/A = locate(href_list["explode"])
- if(!isobj(A) && !ismob(A) && !isturf(A))
- usr << "This can only be done to instances of type /obj, /mob and /turf"
- return
-
- src.cmd_admin_explosion(A)
- href_list["datumrefresh"] = href_list["explode"]
-
- else if(href_list["emp"])
- if(!check_rights(R_DEBUG|R_FUN)) return
-
- var/atom/A = locate(href_list["emp"])
- if(!isobj(A) && !ismob(A) && !isturf(A))
- usr << "This can only be done to instances of type /obj, /mob and /turf"
- return
-
- src.cmd_admin_emp(A)
- href_list["datumrefresh"] = href_list["emp"]
-
- else if(href_list["mark_object"])
- if(!check_rights(0)) return
-
- var/datum/D = locate(href_list["mark_object"])
- if(!istype(D))
- usr << "This can only be done to instances of type /datum"
- return
-
- src.holder.marked_datum = D
- href_list["datumrefresh"] = href_list["mark_object"]
-
- else if(href_list["rotatedatum"])
- if(!check_rights(0)) return
-
- var/atom/A = locate(href_list["rotatedatum"])
- if(!istype(A))
- usr << "This can only be done to instances of type /atom"
- return
-
- switch(href_list["rotatedir"])
- if("right") A.set_dir(turn(A.dir, -45))
- if("left") A.set_dir(turn(A.dir, 45))
- href_list["datumrefresh"] = href_list["rotatedatum"]
-
- else if(href_list["makemonkey"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["makemonkey"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- if(alert("Confirm mob type change?",,"Transform","Cancel") != "Transform") return
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- holder.Topic(href, list("monkeyone"=href_list["makemonkey"]))
-
- else if(href_list["makerobot"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["makerobot"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- if(alert("Confirm mob type change?",,"Transform","Cancel") != "Transform") return
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- holder.Topic(href, list("makerobot"=href_list["makerobot"]))
-
- else if(href_list["makealien"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["makealien"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- if(alert("Confirm mob type change?",,"Transform","Cancel") != "Transform") return
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- holder.Topic(href, list("makealien"=href_list["makealien"]))
-
- else if(href_list["makeslime"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["makeslime"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- if(alert("Confirm mob type change?",,"Transform","Cancel") != "Transform") return
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- holder.Topic(href, list("makeslime"=href_list["makeslime"]))
-
- else if(href_list["makeai"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["makeai"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- if(alert("Confirm mob type change?",,"Transform","Cancel") != "Transform") return
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- holder.Topic(href, list("makeai"=href_list["makeai"]))
-
- else if(href_list["setspecies"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/human/H = locate(href_list["setspecies"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living/carbon/human"
- return
-
- var/new_species = input("Please choose a new species.","Species",null) as null|anything in all_species
-
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
-
- if(H.set_species(new_species))
- usr << "Set species of [H] to [H.species]."
- else
- usr << "Failed! Something went wrong."
-
- else if(href_list["addlanguage"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/H = locate(href_list["addlanguage"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob"
- return
-
- var/new_language = input("Please choose a language to add.","Language",null) as null|anything in all_languages
-
- if(!new_language)
- return
-
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
-
- if(H.add_language(new_language))
- usr << "Added [new_language] to [H]."
- else
- usr << "Mob already knows that language."
-
- else if(href_list["remlanguage"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/H = locate(href_list["remlanguage"])
- if(!istype(H))
- usr << "This can only be done to instances of type /mob"
- return
-
- if(!H.languages.len)
- usr << "This mob knows no languages."
- return
-
- var/datum/language/rem_language = input("Please choose a language to remove.","Language",null) as null|anything in H.languages
-
- if(!rem_language)
- return
-
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
-
- if(H.remove_language(rem_language.name))
- usr << "Removed [rem_language] from [H]."
- else
- usr << "Mob doesn't know that language."
-
- else if(href_list["addverb"])
- if(!check_rights(R_DEBUG)) return
-
- var/mob/living/H = locate(href_list["addverb"])
-
- if(!istype(H))
- usr << "This can only be done to instances of type /mob/living"
- return
- var/list/possibleverbs = list()
- possibleverbs += "Cancel" // One for the top...
- possibleverbs += typesof(/mob/proc,/mob/verb,/mob/living/proc,/mob/living/verb)
- switch(H.type)
- if(/mob/living/carbon/human)
- possibleverbs += typesof(/mob/living/carbon/proc,/mob/living/carbon/verb,/mob/living/carbon/human/verb,/mob/living/carbon/human/proc)
- if(/mob/living/silicon/robot)
- possibleverbs += typesof(/mob/living/silicon/proc,/mob/living/silicon/robot/proc,/mob/living/silicon/robot/verb)
- if(/mob/living/silicon/ai)
- possibleverbs += typesof(/mob/living/silicon/proc,/mob/living/silicon/ai/proc,/mob/living/silicon/ai/verb)
- possibleverbs -= H.verbs
- possibleverbs += "Cancel" // ...And one for the bottom
-
- var/verb = input("Select a verb!", "Verbs",null) as anything in possibleverbs
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- if(!verb || verb == "Cancel")
- return
- else
- H.verbs += verb
-
- else if(href_list["remverb"])
- if(!check_rights(R_DEBUG)) return
-
- var/mob/H = locate(href_list["remverb"])
-
- if(!istype(H))
- usr << "This can only be done to instances of type /mob"
- return
- var/verb = input("Please choose a verb to remove.","Verbs",null) as null|anything in H.verbs
- if(!H)
- usr << "Mob doesn't exist anymore"
- return
- if(!verb)
- return
- else
- H.verbs -= verb
-
- else if(href_list["addorgan"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/M = locate(href_list["addorgan"])
- if(!istype(M))
- usr << "This can only be done to instances of type /mob/living/carbon"
- return
-
- var/new_organ = input("Please choose an organ to add.","Organ",null) as null|anything in typesof(/obj/item/organ)-/obj/item/organ
- if(!new_organ) return
-
- if(!M)
- usr << "Mob doesn't exist anymore"
- return
-
- if(locate(new_organ) in M.internal_organs)
- usr << "Mob already has that organ."
- return
-
-<<<<<<< HEAD
- new new_organ(M)
-
-=======
- if(istype(M,/mob/living/carbon/human))
- var/mob/living/carbon/human/H = M
- var/datum/organ/internal/I = new new_organ(H)
-
- var/organ_slot = input(usr, "Which slot do you want the organ to go in ('default' for default)?") as text|null
-
- if(!organ_slot)
- return
-
- if(organ_slot != "default")
- organ_slot = sanitize(organ_slot)
- else
- if(I.removed_type)
- var/obj/item/organ/O = new I.removed_type()
- organ_slot = O.organ_tag
- del(O)
- else
- organ_slot = "unknown organ"
-
- if(H.internal_organs_by_name[organ_slot])
- usr << "[H] already has an organ in that slot."
- del(I)
- return
-
- H.internal_organs |= I
- H.internal_organs_by_name[organ_slot] = I
- usr << "Added new [new_organ] to [H] as slot [organ_slot]."
- else
- new new_organ(M)
- usr << "Added new [new_organ] to [M]."
->>>>>>> 2aa4646fa0425bed412e2ef0e7852591ecb4bc40
-
- else if(href_list["remorgan"])
- if(!check_rights(R_SPAWN)) return
-
- var/mob/living/carbon/M = locate(href_list["remorgan"])
- if(!istype(M))
- usr << "This can only be done to instances of type /mob/living/carbon"
- return
-
- var/obj/item/organ/rem_organ = input("Please choose an organ to remove.","Organ",null) as null|anything in M.internal_organs
-
- if(!M)
- usr << "Mob doesn't exist anymore"
- return
-
- if(!(locate(rem_organ) in M.internal_organs))
- usr << "Mob does not have that organ."
- return
-
- usr << "Removed [rem_organ] from [M]."
- rem_organ.removed()
- del(rem_organ)
-
- else if(href_list["fix_nano"])
- if(!check_rights(R_DEBUG)) return
-
- var/mob/H = locate(href_list["fix_nano"])
-
- if(!istype(H) || !H.client)
- usr << "This can only be done on mobs with clients"
- return
-
- nanomanager.send_resources(H.client)
-
- usr << "Resource files sent"
- H << "Your NanoUI Resource files have been refreshed"
-
- log_admin("[key_name(usr)] resent the NanoUI resource files to [key_name(H)] ")
-
- else if(href_list["regenerateicons"])
- if(!check_rights(0)) return
-
- var/mob/M = locate(href_list["regenerateicons"])
- if(!ismob(M))
- usr << "This can only be done to instances of type /mob"
- return
- M.regenerate_icons()
-
- else if(href_list["adjustDamage"] && href_list["mobToDamage"])
- if(!check_rights(R_DEBUG|R_ADMIN|R_FUN)) return
-
- var/mob/living/L = locate(href_list["mobToDamage"])
- if(!istype(L)) return
-
- var/Text = href_list["adjustDamage"]
-
- var/amount = input("Deal how much damage to mob? (Negative values here heal)","Adjust [Text]loss",0) as num
-
- if(!L)
- usr << "Mob doesn't exist anymore"
- return
-
- switch(Text)
- if("brute") L.adjustBruteLoss(amount)
- if("fire") L.adjustFireLoss(amount)
- if("toxin") L.adjustToxLoss(amount)
- if("oxygen")L.adjustOxyLoss(amount)
- if("brain") L.adjustBrainLoss(amount)
- if("clone") L.adjustCloneLoss(amount)
- else
- usr << "You caused an error. DEBUG: Text:[Text] Mob:[L]"
- return
-
- if(amount != 0)
- log_admin("[key_name(usr)] dealt [amount] amount of [Text] damage to [L] ")
- message_admins("\blue [key_name(usr)] dealt [amount] amount of [Text] damage to [L] ")
- href_list["datumrefresh"] = href_list["mobToDamage"]
-
- if(href_list["datumrefresh"])
- var/datum/DAT = locate(href_list["datumrefresh"])
- if(!istype(DAT, /datum))
- return
- src.debug_variables(DAT)
-
- return
-
diff --git a/code/datums/disease.dm b/code/datums/disease.dm
index 93aa14f19b3..398dc73bbbc 100644
--- a/code/datums/disease.dm
+++ b/code/datums/disease.dm
@@ -11,7 +11,7 @@
/*
-IMPORTANT NOTE: Please delete the diseases by using cure() proc or del() instruction.
+IMPORTANT NOTE: Please delete the diseases by using cure() proc or qdel() instruction.
Diseases are referenced in a global list, so simply setting mob or obj vars
to null does not delete the object itself. Thank you.
@@ -158,7 +158,7 @@ var/list/diseases = typesof(/datum/disease) - /datum/disease
if(D != src)
if(IsSame(D))
//error("Deleting [D.name] because it's the same as [src.name].")
- del(D) // if there are somehow two viruses of the same kind in the system, delete the other one
+ qdel(D) // if there are somehow two viruses of the same kind in the system, delete the other one
if(holder == affected_mob)
if(affected_mob.stat != DEAD) //he's alive
@@ -183,7 +183,7 @@ var/list/diseases = typesof(/datum/disease) - /datum/disease
/*if(istype(src, /datum/disease/alien_embryo)) //Get rid of the infection flag if it's a xeno embryo.
affected_mob.status_flags &= ~(XENO_HOST)*/
affected_mob.viruses -= src //remove the datum from the list
- del(src) //delete the datum to stop it processing
+ qdel(src) //delete the datum to stop it processing
return
@@ -193,6 +193,9 @@ var/list/diseases = typesof(/datum/disease) - /datum/disease
active_diseases += src
initial_spread = spread
+/datum/disease/Destroy()
+ active_diseases.Remove(src)
+
/datum/disease/proc/IsSame(var/datum/disease/D)
if(istype(src, D.type))
return 1
@@ -200,8 +203,3 @@ var/list/diseases = typesof(/datum/disease) - /datum/disease
/datum/disease/proc/Copy(var/process = 0)
return new type(process, src)
-
-/*
-/datum/disease/Del()
- active_diseases.Remove(src)
-*/
diff --git a/code/datums/diseases/advance/advance.dm b/code/datums/diseases/advance/advance.dm
index 70acceca35d..d4effcf6cb1 100644
--- a/code/datums/diseases/advance/advance.dm
+++ b/code/datums/diseases/advance/advance.dm
@@ -71,7 +71,7 @@ var/list/advance_cures = list(
..(process, D)
return
-/datum/disease/advance/Del()
+/datum/disease/advance/Destroy()
if(processing)
for(var/datum/symptom/S in symptoms)
S.End(src)
@@ -109,7 +109,7 @@ var/list/advance_cures = list(
if(resistance && !(id in affected_mob.resistances))
affected_mob.resistances[id] = id
affected_mob.viruses -= src //remove the datum from the list
- del(src) //delete the datum to stop it processing
+ qdel(src) //delete the datum to stop it processing
return
// Returns the advance disease with a different reference memory.
diff --git a/code/datums/diseases/alien_embryo.dm b/code/datums/diseases/alien_embryo.dm
index 631c93b26c4..59d1dbe1605 100644
--- a/code/datums/diseases/alien_embryo.dm
+++ b/code/datums/diseases/alien_embryo.dm
@@ -113,7 +113,7 @@ Des: Removes all infection images from aliens and places an infection image on a
if (alien.client)
for(var/image/I in alien.client.images)
if(dd_hasprefix_case(I.icon_state, "infected"))
- del(I)
+ qdel(I)
for (var/mob/living/carbon/alien/alien in player_list)
if (alien.client)
@@ -149,5 +149,5 @@ Des: Removes the alien infection image from all aliens in the world located in p
for(var/image/I in alien.client.images)
if(I.loc == C)
if(dd_hasprefix_case(I.icon_state, "infected"))
- del(I)
+ qdel(I)
return
diff --git a/code/datums/diseases/dna_spread.dm b/code/datums/diseases/dna_spread.dm
index a4d85a56407..6d520fe2948 100644
--- a/code/datums/diseases/dna_spread.dm
+++ b/code/datums/diseases/dna_spread.dm
@@ -34,7 +34,7 @@
if(4)
if(!src.transformed)
if ((!strain_data["name"]) || (!strain_data["UI"]) || (!strain_data["SE"]))
- del(affected_mob.virus)
+ qdel(affected_mob.virus)
return
//Save original dna for when the disease is cured.
@@ -56,7 +56,7 @@
return
-/datum/disease/dnaspread/Del()
+/datum/disease/dnaspread/Destroy()
if ((original_dna["name"]) && (original_dna["UI"]) && (original_dna["SE"]))
var/list/newUI=original_dna["UI"]
var/list/newSE=original_dna["SE"]
diff --git a/code/datums/helper_datums/construction_datum.dm b/code/datums/helper_datums/construction_datum.dm
index 7c2fabbc9b8..0bda144e8aa 100644
--- a/code/datums/helper_datums/construction_datum.dm
+++ b/code/datums/helper_datums/construction_datum.dm
@@ -12,7 +12,7 @@
holder = atom
if(!holder) //don't want this without a holder
spawn
- del src
+ qdel(src)
set_desc(steps.len)
return
@@ -61,7 +61,7 @@
if(result)
new result(get_turf(holder))
spawn()
- del holder
+ qdel(holder)
return
proc/set_desc(index as num)
diff --git a/code/datums/helper_datums/global_iterator.dm b/code/datums/helper_datums/global_iterator.dm
index 0020859f1d9..4f4d680e9e0 100644
--- a/code/datums/helper_datums/global_iterator.dm
+++ b/code/datums/helper_datums/global_iterator.dm
@@ -151,4 +151,8 @@ Data storage vars:
start()
return active()
-
+/datum/global_iterator/Destroy()
+ tag = null
+ arg_list.Cut()
+ stop()
+ //Do not call ..()
diff --git a/code/datums/helper_datums/teleport.dm b/code/datums/helper_datums/teleport.dm
index 00899f47cb2..b562780aea3 100644
--- a/code/datums/helper_datums/teleport.dm
+++ b/code/datums/helper_datums/teleport.dm
@@ -14,179 +14,177 @@
var/force_teleport = 1 //if false, teleport will use Move() proc (dense objects will prevent teleportation)
- New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
- ..()
- if(!initTeleport(arglist(args)))
- return 0
- return 1
-
- proc/initTeleport(ateleatom,adestination,aprecision,afteleport,aeffectin,aeffectout,asoundin,asoundout)
- if(!setTeleatom(ateleatom))
- return 0
- if(!setDestination(adestination))
- return 0
- if(!setPrecision(aprecision))
- return 0
- setEffects(aeffectin,aeffectout)
- setForceTeleport(afteleport)
- setSounds(asoundin,asoundout)
- return 1
-
- //must succeed
- proc/setPrecision(aprecision)
- if(isnum(aprecision))
- precision = aprecision
- return 1
+/datum/teleport/New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
+ ..()
+ if(!initTeleport(arglist(args)))
return 0
+ return 1
- //must succeed
- proc/setDestination(atom/adestination)
- if(istype(adestination))
- destination = adestination
- return 1
+/datum/teleport/proc/initTeleport(ateleatom,adestination,aprecision,afteleport,aeffectin,aeffectout,asoundin,asoundout)
+ if(!setTeleatom(ateleatom))
return 0
-
- //must succeed in most cases
- proc/setTeleatom(atom/movable/ateleatom)
- if(istype(ateleatom, /obj/effect) && !istype(ateleatom, /obj/effect/dummy/chameleon))
- del(ateleatom)
- return 0
- if(istype(ateleatom))
- teleatom = ateleatom
- return 1
+ if(!setDestination(adestination))
return 0
+ if(!setPrecision(aprecision))
+ return 0
+ setEffects(aeffectin,aeffectout)
+ setForceTeleport(afteleport)
+ setSounds(asoundin,asoundout)
+ return 1
- //custom effects must be properly set up first for instant-type teleports
- //optional
- proc/setEffects(datum/effect/effect/system/aeffectin=null,datum/effect/effect/system/aeffectout=null)
- effectin = istype(aeffectin) ? aeffectin : null
- effectout = istype(aeffectout) ? aeffectout : null
+//must succeed
+/datum/teleport/proc/setPrecision(aprecision)
+ if(isnum(aprecision))
+ precision = aprecision
return 1
+ return 0
- //optional
- proc/setForceTeleport(afteleport)
+//must succeed
+/datum/teleport/proc/setDestination(atom/adestination)
+ if(istype(adestination))
+ destination = adestination
+ return 1
+ return 0
+
+//must succeed in most cases
+/datum/teleport/proc/setTeleatom(atom/movable/ateleatom)
+ if(istype(ateleatom, /obj/effect) && !istype(ateleatom, /obj/effect/dummy/chameleon))
+ qdel(ateleatom)
+ return 0
+ if(istype(ateleatom))
+ teleatom = ateleatom
+ return 1
+ return 0
+
+//custom effects must be properly set up first for instant-type teleports
+//optional
+/datum/teleport/proc/setEffects(datum/effect/effect/system/aeffectin=null,datum/effect/effect/system/aeffectout=null)
+ effectin = istype(aeffectin) ? aeffectin : null
+ effectout = istype(aeffectout) ? aeffectout : null
+ return 1
+
+//optional
+/datum/teleport/proc/setForceTeleport(afteleport)
force_teleport = afteleport
return 1
- //optional
- proc/setSounds(asoundin=null,asoundout=null)
+//optional
+/datum/teleport/proc/setSounds(asoundin=null,asoundout=null)
soundin = isfile(asoundin) ? asoundin : null
soundout = isfile(asoundout) ? asoundout : null
return 1
- //placeholder
- proc/teleportChecks()
+//placeholder
+/datum/teleport/proc/teleportChecks()
return 1
- proc/playSpecials(atom/location,datum/effect/effect/system/effect,sound)
- if(location)
- if(effect)
- spawn(-1)
- src = null
- effect.attach(location)
- effect.start()
- if(sound)
- spawn(-1)
- src = null
- playsound(location,sound,60,1)
- return
+/datum/teleport/proc/playSpecials(atom/location,datum/effect/effect/system/effect,sound)
+ if(location)
+ if(effect)
+ spawn(-1)
+ src = null
+ effect.attach(location)
+ effect.start()
+ if(sound)
+ spawn(-1)
+ src = null
+ playsound(location,sound,60,1)
+ return
- //do the monkey dance
- proc/doTeleport()
+//do the monkey dance
+/datum/teleport/proc/doTeleport()
- var/turf/destturf
- var/turf/curturf = get_turf(teleatom)
- var/area/destarea = get_area(destination)
- if(precision)
- var/list/posturfs = circlerangeturfs(destination,precision)
- destturf = safepick(posturfs)
- else
- destturf = get_turf(destination)
+ var/turf/destturf
+ var/turf/curturf = get_turf(teleatom)
+ var/area/destarea = get_area(destination)
+ if(precision)
+ var/list/posturfs = circlerangeturfs(destination,precision)
+ destturf = safepick(posturfs)
+ else
+ destturf = get_turf(destination)
- if(!destturf || !curturf)
- return 0
-
- playSpecials(curturf,effectin,soundin)
-
- var/obj/structure/bed/chair/C = null
- if(isliving(teleatom))
- var/mob/living/L = teleatom
- if(L.buckled)
- C = L.buckled
- if(force_teleport)
- teleatom.forceMove(destturf)
- playSpecials(destturf,effectout,soundout)
- else
- if(teleatom.Move(destturf))
- playSpecials(destturf,effectout,soundout)
- if(C)
- C.forceMove(destturf)
-
- destarea.Entered(teleatom)
-
- return 1
-
- proc/teleport()
- if(teleportChecks())
- return doTeleport()
+ if(!destturf || !curturf)
return 0
+ playSpecials(curturf,effectin,soundin)
+
+ var/obj/structure/bed/chair/C = null
+ if(isliving(teleatom))
+ var/mob/living/L = teleatom
+ if(L.buckled)
+ C = L.buckled
+ if(force_teleport)
+ teleatom.forceMove(destturf)
+ playSpecials(destturf,effectout,soundout)
+ else
+ if(teleatom.Move(destturf))
+ playSpecials(destturf,effectout,soundout)
+ if(C)
+ C.forceMove(destturf)
+
+ destarea.Entered(teleatom)
+
+ return 1
+
+/datum/teleport/proc/teleport()
+ if(teleportChecks())
+ return doTeleport()
+ return 0
+
/datum/teleport/instant //teleports when datum is created
- New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
- if(..())
- teleport()
- return
+/datum/teleport/instant/New(ateleatom, adestination, aprecision=0, afteleport=1, aeffectin=null, aeffectout=null, asoundin=null, asoundout=null)
+ if(..())
+ teleport()
+ return
-/datum/teleport/instant/science
-
- setEffects(datum/effect/effect/system/aeffectin,datum/effect/effect/system/aeffectout)
- if(!aeffectin || !aeffectout)
- var/datum/effect/effect/system/spark_spread/aeffect = new
- aeffect.set_up(5, 1, teleatom)
- effectin = effectin || aeffect
- effectout = effectout || aeffect
- return 1
- else
- return ..()
-
- setPrecision(aprecision)
- ..()
- if(istype(teleatom, /obj/item/weapon/storage/backpack/holding))
- precision = rand(1,100)
-
- var/list/bagholding = teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)
- if(bagholding.len)
- precision = max(rand(1,100)*bagholding.len,100)
- if(istype(teleatom, /mob/living))
- var/mob/living/MM = teleatom
- MM << "\red The Bluespace interface on your Bag of Holding interferes with the teleport!"
+/datum/teleport/instant/science/setEffects(datum/effect/effect/system/aeffectin,datum/effect/effect/system/aeffectout)
+ if(!aeffectin || !aeffectout)
+ var/datum/effect/effect/system/spark_spread/aeffect = new
+ aeffect.set_up(5, 1, teleatom)
+ effectin = effectin || aeffect
+ effectout = effectout || aeffect
return 1
+ else
+ return ..()
- teleportChecks()
- if(istype(teleatom, /obj/item/weapon/disk/nuclear)) // Don't let nuke disks get teleported --NeoFite
- teleatom.visible_message("\red The [teleatom] bounces off of the portal!")
+/datum/teleport/instant/science/setPrecision(aprecision)
+ ..()
+ if(istype(teleatom, /obj/item/weapon/storage/backpack/holding))
+ precision = rand(1,100)
+
+ var/list/bagholding = teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)
+ if(bagholding.len)
+ precision = max(rand(1,100)*bagholding.len,100)
+ if(istype(teleatom, /mob/living))
+ var/mob/living/MM = teleatom
+ MM << "\The [teleatom] bounces off of the portal!")
+ return 0
+
+ if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/disk/nuclear)))
+ if(istype(teleatom, /mob/living))
+ var/mob/living/MM = teleatom
+ MM.visible_message("\The [MM] bounces off of the portal!","Something you are carrying seems to be unable to pass through the portal. Better drop it if you want to go through.")
+ else
+ teleatom.visible_message("\The [teleatom] bounces off of the portal!")
+ return 0
+
+ if(destination.z in config.admin_levels) //centcomm z-level
+ if(istype(teleatom, /obj/mecha))
+ var/obj/mecha/MM = teleatom
+ MM.occupant << "\The [MM] would not survive the jump to a location so far away!"
+ return 0
+ if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)))
+ teleatom.visible_message("\The [teleatom] bounces off of the portal!")
return 0
- if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/disk/nuclear)))
- if(istype(teleatom, /mob/living))
- var/mob/living/MM = teleatom
- MM.visible_message("\red The [MM] bounces off of the portal!","\red Something you are carrying seems to be unable to pass through the portal. Better drop it if you want to go through.")
- else
- teleatom.visible_message("\red The [teleatom] bounces off of the portal!")
- return 0
- if(destination.z == 2) //centcomm z-level
- if(istype(teleatom, /obj/mecha))
- var/obj/mecha/MM = teleatom
- MM.occupant << "\red The mech would not survive the jump to a location so far away!"
- return 0
- if(!isemptylist(teleatom.search_contents_for(/obj/item/weapon/storage/backpack/holding)))
- teleatom.visible_message("\red The Bag of Holding bounces off of the portal!")
- return 0
-
-
- if(destination.z > 7) //Away mission z-levels
- return 0
- return 1
\ No newline at end of file
+ if(destination.z > max_default_z_level()) //Away mission z-levels
+ return 0
+ return 1
diff --git a/code/datums/mind.dm b/code/datums/mind.dm
index f6fbbc110c8..cfbd1551452 100644
--- a/code/datums/mind.dm
+++ b/code/datums/mind.dm
@@ -311,7 +311,7 @@ datum/mind
for(var/obj/item/weapon/implant/loyalty/I in H.contents)
for(var/obj/item/organ/external/organs in H.organs)
if(I in organs.implants)
- I.Del()
+ qdel(I)
break
H << "Your loyalty implant has been deactivated."
log_admin("[key_name_admin(usr)] has de-loyalty implanted [current].")
@@ -368,7 +368,7 @@ datum/mind
src = null
m2h.inject(M)
src = mobfinder.loc:mind
- del(mobfinder)
+ qdel(mobfinder)
current.radiation -= 50
*/
else if (href_list["silicon"])
@@ -445,10 +445,10 @@ datum/mind
var/list/L = current.get_contents()
for (var/t in L)
if (istype(t, /obj/item/device/pda))
- if (t:uplink) del(t:uplink)
+ if (t:uplink) qdel(t:uplink)
t:uplink = null
else if (istype(t, /obj/item/device/radio))
- if (t:traitorradio) del(t:traitorradio)
+ if (t:traitorradio) qdel(t:traitorradio)
t:traitorradio = null
t:traitor_frequency = 0.0
else if (istype(t, /obj/item/weapon/SWF_uplink) || istype(t, /obj/item/weapon/syndicate_uplink))
@@ -457,7 +457,7 @@ datum/mind
R.loc = current.loc
R.traitorradio = null
R.traitor_frequency = 0.0
- del(t)
+ qdel(t)
// remove wizards spells
//If there are more special powers that need removal, they can be procced into here./N
@@ -479,7 +479,7 @@ datum/mind
proc/take_uplink()
var/obj/item/device/uplink/hidden/H = find_syndicate_uplink()
if(H)
- del(H)
+ qdel(H)
// check whether this mind's mob has been brigged for the given duration
diff --git a/code/datums/modules.dm b/code/datums/modules.dm
index 896d920f994..43d25a2e25d 100644
--- a/code/datums/modules.dm
+++ b/code/datums/modules.dm
@@ -24,7 +24,8 @@ var/list/modules = list( // global associative list
var/mneed = mods.inmodlist(type) // find if this type has modules defined
if(!mneed) // not found in module list?
- del(src) // delete self, thus ending proc
+ qdel(src)
+ return
var/needed = mods.getbitmask(type) // get a bitmask for the number of modules in this object
status = needed
diff --git a/code/datums/recipe.dm b/code/datums/recipe.dm
index 9c72feef39d..6098315c11c 100644
--- a/code/datums/recipe.dm
+++ b/code/datums/recipe.dm
@@ -54,8 +54,8 @@
. = 1
if(fruit && fruit.len)
var/list/checklist = list()
- for(var/fruittype in fruit) // I do not trust Copy().
- checklist[fruittype] = fruit[fruittype]
+ // You should trust Copy().
+ checklist = fruit.Copy()
for(var/obj/item/weapon/reagent_containers/food/snacks/grown/G in container)
if(!G.seed || !G.seed.kitchen_tag || isnull(checklist[G.seed.kitchen_tag]))
continue
@@ -73,15 +73,15 @@
. = 1
if (items && items.len)
var/list/checklist = list()
- for(var/item_type in items)
- checklist |= item_type //Still don't trust Copy().
+ checklist = items.Copy() // You should really trust Copy
for(var/obj/O in container)
if(istype(O,/obj/item/weapon/reagent_containers/food/snacks/grown))
continue // Fruit is handled in check_fruit().
var/found = 0
- for(var/item_type in checklist)
+ for(var/i = 1; i < checklist.len+1; i++)
+ var/item_type = checklist[i]
if (istype(O,item_type))
- checklist-=item_type
+ checklist.Cut(i, i+1)
found = 1
break
if (!found)
@@ -94,8 +94,8 @@
/datum/recipe/proc/make(var/obj/container as obj)
var/obj/result_obj = new result(container)
for (var/obj/O in (container.contents-result_obj))
- O.reagents.trans_to(result_obj, O.reagents.total_volume)
- del(O)
+ O.reagents.trans_to_obj(result_obj, O.reagents.total_volume)
+ qdel(O)
container.reagents.clear_reagents()
return result_obj
@@ -109,8 +109,8 @@
if (O.reagents)
O.reagents.del_reagent("nutriment")
O.reagents.update_total()
- O.reagents.trans_to(result_obj, O.reagents.total_volume)
- del(O)
+ O.reagents.trans_to_obj(result_obj, O.reagents.total_volume)
+ qdel(O)
container.reagents.clear_reagents()
return result_obj
diff --git a/code/datums/supplypacks.dm b/code/datums/supplypacks.dm
index 3cc3107784d..1a7a9b8ae0b 100644
--- a/code/datums/supplypacks.dm
+++ b/code/datums/supplypacks.dm
@@ -43,10 +43,10 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/datum/supply_packs/food
name = "Kitchen supply crate"
- contains = list(/obj/item/weapon/reagent_containers/food/snacks/flour,
- /obj/item/weapon/reagent_containers/food/snacks/flour,
- /obj/item/weapon/reagent_containers/food/snacks/flour,
- /obj/item/weapon/reagent_containers/food/snacks/flour,
+ contains = list(/obj/item/weapon/reagent_containers/food/condiment/flour,
+ /obj/item/weapon/reagent_containers/food/condiment/flour,
+ /obj/item/weapon/reagent_containers/food/condiment/flour,
+ /obj/item/weapon/reagent_containers/food/condiment/flour,
/obj/item/weapon/reagent_containers/food/drinks/milk,
/obj/item/weapon/reagent_containers/food/drinks/milk,
/obj/item/weapon/storage/fancy/egg_box,
@@ -259,7 +259,7 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
name = "Corgi Crate"
contains = list()
cost = 50
- containertype = /obj/structure/largecrate/lisa
+ containertype = /obj/structure/largecrate/animal/corgi
containername = "Corgi Crate"
group = "Hydroponics"
@@ -289,7 +289,7 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/datum/supply_packs/cow
name = "Cow crate"
cost = 30
- containertype = /obj/structure/largecrate/cow
+ containertype = /obj/structure/largecrate/animal/cow
containername = "Cow crate"
access = access_hydroponics
group = "Hydroponics"
@@ -297,7 +297,7 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/datum/supply_packs/goat
name = "Goat crate"
cost = 25
- containertype = /obj/structure/largecrate/goat
+ containertype = /obj/structure/largecrate/animal/goat
containername = "Goat crate"
access = access_hydroponics
group = "Hydroponics"
@@ -305,19 +305,11 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/datum/supply_packs/chicken
name = "Chicken crate"
cost = 20
- containertype = /obj/structure/largecrate/chick
+ containertype = /obj/structure/largecrate/animal/chick
containername = "Chicken crate"
access = access_hydroponics
group = "Hydroponics"
-/datum/supply_packs/lisa
- name = "Corgi crate"
- contains = list()
- cost = 50
- containertype = /obj/structure/largecrate/lisa
- containername = "Corgi crate"
- group = "Hydroponics"
-
/datum/supply_packs/seeds
name = "Seeds crate"
contains = list(/obj/item/seeds/chiliseed,
@@ -345,11 +337,17 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/datum/supply_packs/weedcontrol
name = "Weed control crate"
- contains = list(/obj/item/weapon/scythe,
+ contains = list(/obj/item/weapon/hatchet,
+ /obj/item/weapon/hatchet,
+ /obj/item/weapon/reagent_containers/spray/plantbgone,
+ /obj/item/weapon/reagent_containers/spray/plantbgone,
+ /obj/item/weapon/reagent_containers/spray/plantbgone,
+ /obj/item/weapon/reagent_containers/spray/plantbgone,
+ /obj/item/clothing/mask/gas,
/obj/item/clothing/mask/gas,
/obj/item/weapon/grenade/chem_grenade/antiweed,
/obj/item/weapon/grenade/chem_grenade/antiweed)
- cost = 20
+ cost = 25
containertype = /obj/structure/closet/crate/secure/hydrosec
containername = "Weed control crate"
access = access_hydroponics
@@ -1506,5 +1504,45 @@ var/list/all_supply_groups = list("Operations","Security","Hospitality","Enginee
/obj/item/device/floor_painter,
/obj/item/device/floor_painter)
+/datum/supply_packs/bluespacerelay
+ name = "Emergency Bluespace Relay Assembly Kit"
+ cost = 75
+ containername = "emergency bluespace relay assembly kit"
+ containertype = /obj/structure/closet/crate
+ group = "Engineering"
+ contains = list(/obj/item/weapon/circuitboard/bluespacerelay,
+ /obj/item/weapon/stock_parts/manipulator,
+ /obj/item/weapon/stock_parts/manipulator,
+ /obj/item/weapon/stock_parts/subspace/filter,
+ /obj/item/weapon/stock_parts/subspace/crystal,
+ /obj/item/weapon/storage/toolbox/electrical)
+/datum/supply_packs/randomised/exosuit_mod
+ num_contained = 1
+ contains = list(
+ /obj/item/device/kit/paint/ripley,
+ /obj/item/device/kit/paint/ripley/death,
+ /obj/item/device/kit/paint/ripley/flames_red,
+ /obj/item/device/kit/paint/ripley/flames_blue
+ )
+ name = "Random APLU modkit"
+ cost = 200
+ containertype = /obj/structure/closet/crate
+ containername = "heavy crate"
+ group = "Miscellaneous"
+/datum/supply_packs/randomised/exosuit_mod/durand
+ contains = list(
+ /obj/item/device/kit/paint/durand,
+ /obj/item/device/kit/paint/durand/seraph,
+ /obj/item/device/kit/paint/durand/phazon
+ )
+ name = "Random Durand exosuit modkit"
+
+/datum/supply_packs/randomised/exosuit_mod/gygax
+ contains = list(
+ /obj/item/device/kit/paint/gygax,
+ /obj/item/device/kit/paint/gygax/darkgygax,
+ /obj/item/device/kit/paint/gygax/recitence
+ )
+ name = "Random Gygax exosuit modkit"
diff --git a/code/datums/wires/airlock.dm b/code/datums/wires/airlock.dm
index 7e8c8779cff..a0f1f9c7f1c 100644
--- a/code/datums/wires/airlock.dm
+++ b/code/datums/wires/airlock.dm
@@ -37,10 +37,11 @@ var/const/AIRLOCK_WIRE_LIGHT = 2048
var/haspower = A.arePowerSystemsOn() //If there's no power, then no lights will be on.
. += ..()
- . += text(" \n[] \n[] \n[] \n[] \n[] \n[] \n[]",
+ . += text(" \n[] \n[] \n[] \n[] \n[] \n[] \n[] \n[]",
(A.locked ? "The door bolts have fallen!" : "The door bolts look up."),
((A.lights && haspower) ? "The door bolt lights are on." : "The door bolt lights are off!"),
((haspower) ? "The test light is on." : "The test light is off!"),
+ ((A.backupPowerCablesCut()) ? "The backup power light is off!" : "The backup power light is on."),
((A.aiControlDisabled==0 && !A.emagged && haspower)? "The 'AI control allowed' light is on." : "The 'AI control allowed' light is off."),
((A.safe==0 && haspower)? "The 'Check Wiring' light is on." : "The 'Check Wiring' light is off."),
((A.normalspeed==0 && haspower)? "The 'Check Timing Mechanism' light is on." : "The 'Check Timing Mechanism' light is off."),
@@ -124,7 +125,7 @@ var/const/AIRLOCK_WIRE_LIGHT = 2048
//Sending a pulse through flashes the red light on the door (if the door has power).
if(A.arePowerSystemsOn() && A.density)
A.do_animate("deny")
- if(AIRLOCK_WIRE_MAIN_POWER1 || AIRLOCK_WIRE_MAIN_POWER2)
+ if(AIRLOCK_WIRE_MAIN_POWER1, AIRLOCK_WIRE_MAIN_POWER2)
//Sending a pulse through either one causes a breaker to trip, disabling the door for 10 seconds if backup power is connected, or 1 minute if not (or until backup power comes back on, whichever is shorter).
A.loseMainPower()
if(AIRLOCK_WIRE_DOOR_BOLTS)
@@ -135,7 +136,7 @@ var/const/AIRLOCK_WIRE_LIGHT = 2048
else
A.unlock()
- if(AIRLOCK_WIRE_BACKUP_POWER1 || AIRLOCK_WIRE_BACKUP_POWER2)
+ if(AIRLOCK_WIRE_BACKUP_POWER1, AIRLOCK_WIRE_BACKUP_POWER2)
//two wires for backup power. Sending a pulse through either one causes a breaker to trip, but this does not disable it unless main power is down too (in which case it is disabled for 1 minute or however long it takes main power to come back, whichever is shorter).
A.loseBackupPower()
if(AIRLOCK_WIRE_AI_CONTROL)
diff --git a/code/datums/wires/wires.dm b/code/datums/wires/wires.dm
index 3b0b54942f2..0555a140bd8 100644
--- a/code/datums/wires/wires.dm
+++ b/code/datums/wires/wires.dm
@@ -278,6 +278,11 @@ var/const/POWER = 8
var/r = rand(1, wires.len)
CutWireIndex(r)
+/datum/wires/proc/RandomCutAll(var/probability = 10)
+ for(var/i = 1; i < MAX_FLAG && i < (1 << wire_count); i += i)
+ if(prob(probability))
+ CutWireIndex(i)
+
/datum/wires/proc/CutAll()
for(var/i = 1; i < MAX_FLAG && i < (1 << wire_count); i += i)
CutWireIndex(i)
diff --git a/code/defines/obj.dm b/code/defines/obj.dm
index e105d67a5b4..a70822942fe 100644
--- a/code/defines/obj.dm
+++ b/code/defines/obj.dm
@@ -80,7 +80,8 @@
for(var/datum/data/record/t in data_core.general)
var/name = t.fields["name"]
var/rank = t.fields["rank"]
- var/real_rank = t.fields["real_rank"]
+ var/real_rank = make_list_rank(t.fields["real_rank"])
+
if(OOC)
var/active = 0
for(var/mob/M in player_list)
@@ -165,6 +166,15 @@
return dat
+/var/list/acting_rank_prefixes = list("acting", "temporary", "interim")
+
+/proc/make_list_rank(rank)
+ for(var/prefix in acting_rank_prefixes)
+ if(findtext(rank, "[prefix] ", 1, 2+length(prefix)))
+ return copytext(rank, 2+length(prefix))
+ return rank
+
+
/*
We can't just insert in HTML into the nanoUI so we need the raw data to play with.
Instead of creating this list over and over when someone leaves their PDA open to the page
@@ -189,7 +199,8 @@ var/global/ManifestJSON
for(var/datum/data/record/t in data_core.general)
var/name = sanitize(t.fields["name"])
var/rank = sanitize(t.fields["rank"])
- var/real_rank = t.fields["real_rank"]
+ var/real_rank = make_list_rank(t.fields["real_rank"])
+
var/isactive = t.fields["p_stat"]
var/department = 0
var/depthead = 0 // Department Heads will be placed at the top of their lists.
diff --git a/code/defines/obj/weapon.dm b/code/defines/obj/weapon.dm
index 27c233b3404..e0bd7bb486d 100644
--- a/code/defines/obj/weapon.dm
+++ b/code/defines/obj/weapon.dm
@@ -83,7 +83,7 @@
force = 5.0
throwforce = 7.0
w_class = 2.0
- matter = list("metal" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50)
attack_verb = list("bludgeoned", "whacked", "disciplined", "thrashed")
/obj/item/weapon/cane/concealed
@@ -91,9 +91,11 @@
/obj/item/weapon/cane/concealed/New()
..()
- concealed_blade = new/obj/item/weapon/butterfly/switchblade(src)
+ var/obj/item/weapon/butterfly/switchblade/temp_blade = new(src)
+ concealed_blade = temp_blade
+ temp_blade.attack_self()
-/obj/item/weapon/cane/concealed/attack_self(mob/user)
+/obj/item/weapon/cane/concealed/attack_self(var/mob/user)
if(concealed_blade)
user.visible_message("[user] has unsheathed \a [concealed_blade] from \his [src]!", "You unsheathe \the [concealed_blade] from \the [src].")
// Calling drop/put in hands to properly call item drop/pickup procs
@@ -101,8 +103,9 @@
user.drop_from_inventory(src)
user.put_in_hands(concealed_blade)
user.put_in_hands(src)
+ user.update_inv_l_hand(0)
+ user.update_inv_r_hand()
concealed_blade = null
- update_icon()
else
..()
@@ -172,47 +175,91 @@
origin_tech = list(TECH_MATERIAL = 1)
var/breakouttime = 300 //Deciseconds = 30s = 0.5 minute
-/obj/item/weapon/legcuffs/beartrap
+/obj/item/weapon/beartrap
name = "bear trap"
throw_speed = 2
throw_range = 1
+ gender = PLURAL
+ icon = 'icons/obj/items.dmi'
icon_state = "beartrap0"
desc = "A trap used to catch bears and other legged creatures."
- var/armed = 0
+ throwforce = 0
+ w_class = 3.0
+ origin_tech = "materials=1"
+ var/deployed = 0
suicide_act(mob/user)
- viewers(user) << "\red [user] is putting the [src.name] on \his head! It looks like \he's trying to commit suicide."
+ viewers(user) << "[user] is putting the [src.name] on \his head! It looks like \he's trying to commit suicide."
return (BRUTELOSS)
-/obj/item/weapon/legcuffs/beartrap/attack_self(mob/user as mob)
+/obj/item/weapon/beartrap/attack_self(mob/user as mob)
..()
if(ishuman(user) && !user.stat && !user.restrained())
- armed = !armed
- icon_state = "beartrap[armed]"
- user << "[src] is now [armed ? "armed" : "disarmed"]"
+ if(deployed==0)
+ user.visible_message("[user] is deploying \the [src]", "You are deploying \the [src]!")
+ if (do_after(user, 60))
+ user.visible_message("[user] has deployed \the [src]", "You have deployed \the [src]!")
+ deployed = 1
+ user.drop_from_inventory(src, user.loc)
+ update_icon()
+ anchored = 1
-/obj/item/weapon/legcuffs/beartrap/Crossed(AM as mob|obj)
- if(armed)
+/obj/item/weapon/beartrap/attack_hand(mob/user as mob)
+ if(ishuman(user) && !user.stat && !user.restrained())
+ if(deployed==1)
+ user.visible_message("[user] is disarming \the [src]", "You are disarming \the [src]!")
+ if (do_after(user, 60))
+ user.visible_message("[user] has disarmed \the [src]", "You have disarmed \the [src]!")
+ deployed = 0
+ anchored = 0
+ update_icon()
+
+ if(deployed==0)
+ ..()
+
+/obj/item/weapon/beartrap/Crossed(AM as mob|obj)
+ if(deployed)
if(ishuman(AM))
if(isturf(src.loc))
- var/mob/living/carbon/H = AM
+ var/mob/living/carbon/human/H = AM
if(H.m_intent == "run")
- armed = 0
- H.legcuffed = src
- src.loc = H
- H.update_inv_legcuffed()
- H << "\red You step on \the [src]!"
- feedback_add_details("handcuffs","B") //Yes, I know they're legcuffs. Don't change this, no need for an extra variable. The "B" is used to tell them apart.
+ deployed = 0
+ update_icon()
+ H << "You step on \the [src]!"
for(var/mob/O in viewers(H, null))
if(O == H)
continue
- O.show_message("\red [H] steps on \the [src].", 1)
+ O.show_message("[H] steps on \the [src].", 1)
+ if(H.lying)
+ var/obj/item/organ/external/affecting = pick(H.organs)
+ if(affecting.take_damage(30, 0))
+ H.UpdateDamageIcon()
+ affecting.embed(src)
+ else
+ var/list/potentialorgans = list()
+ for(var/organ in list("l_leg", "r_leg", "l_foot", "r_foot"))
+ var/obj/item/organ/external/R = H.get_organ(organ)
+ if(R && !(R.status & ORGAN_DESTROYED))
+ potentialorgans += R
+ var/obj/item/organ/external/affecting = pick(potentialorgans)
+ if(affecting.take_damage(30, 0))
+ H.UpdateDamageIcon()
+ affecting.embed(src)
+
+
if(isanimal(AM) && !istype(AM, /mob/living/simple_animal/parrot) && !istype(AM, /mob/living/simple_animal/construct) && !istype(AM, /mob/living/simple_animal/shade) && !istype(AM, /mob/living/simple_animal/hostile/viscerator))
- armed = 0
+ deployed = 0
var/mob/living/simple_animal/SA = AM
SA.health -= 20
..()
+/obj/item/weapon/beartrap/update_icon()
+ ..()
+
+ if(deployed == 0)
+ icon_state = "beartrap0"
+ else
+ icon_state = "beartrap1"
/obj/item/weapon/caution
@@ -267,9 +314,9 @@
throwforce = 5
w_class = 2.0
throw_speed = 4
- throw_range = 20
- matter = list("metal" = 100)
- origin_tech = list(TECH_MAGNET = 1)
+ throw_range = 20
+ matter = list(DEFAULT_WALL_MATERIAL = 100)
+ origin_tech = list(TECH_MAGNET = 1)
/obj/item/weapon/staff
name = "wizards staff"
@@ -318,7 +365,7 @@
var/amount = 1.0
var/laying = 0.0
var/old_lay = null
- matter = list("metal" = 40)
+ matter = list(DEFAULT_WALL_MATERIAL = 40)
attack_verb = list("whipped", "lashed", "disciplined", "tickled")
suicide_act(mob/user)
@@ -342,12 +389,12 @@
name = "power control module"
icon_state = "power_mod"
desc = "Heavy-duty switching circuits for power control."
- matter = list("metal" = 50, "glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50, "glass" = 50)
/obj/item/weapon/module/power_control/attackby(var/obj/item/weapon/W as obj, var/mob/user as mob)
if (istype(W, /obj/item/device/multitool))
var/obj/item/weapon/circuitboard/ghettosmes/newcircuit = new/obj/item/weapon/circuitboard/ghettosmes(user.loc)
- del(src)
+ qdel(src)
user.put_in_hands(newcircuit)
@@ -465,35 +512,35 @@
desc = "A basic capacitor used in the construction of a variety of devices."
icon_state = "capacitor"
origin_tech = list(TECH_POWER = 1)
- matter = list("metal" = 50, "glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 50)
/obj/item/weapon/stock_parts/scanning_module
name = "scanning module"
desc = "A compact, high resolution scanning module used in the construction of certain devices."
icon_state = "scan_module"
origin_tech = list(TECH_MAGNET = 1)
- matter = list("metal" = 50, "glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
/obj/item/weapon/stock_parts/manipulator
name = "micro-manipulator"
desc = "A tiny little manipulator used in the construction of certain devices."
icon_state = "micro_mani"
origin_tech = list(TECH_MATERIAL = 1, TECH_DATA = 1)
- matter = list("metal" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 30)
/obj/item/weapon/stock_parts/micro_laser
name = "micro-laser"
desc = "A tiny laser used in certain devices."
icon_state = "micro_laser"
origin_tech = list(TECH_MAGNET = 1)
- matter = list("metal" = 10, "glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 10,"glass" = 20)
/obj/item/weapon/stock_parts/matter_bin
name = "matter bin"
desc = "A container for hold compressed matter awaiting re-construction."
icon_state = "matter_bin"
origin_tech = list(TECH_MATERIAL = 1)
- matter = list("metal" = 80)
+ matter = list(DEFAULT_WALL_MATERIAL = 80)
//Rank 2
@@ -502,7 +549,7 @@
desc = "An advanced capacitor used in the construction of a variety of devices."
origin_tech = list(TECH_POWER = 3)
rating = 2
- matter = list("metal" = 50,"glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 50)
/obj/item/weapon/stock_parts/scanning_module/adv
name = "advanced scanning module"
@@ -510,7 +557,7 @@
icon_state = "scan_module"
origin_tech = list(TECH_MAGNET = 3)
rating = 2
- matter = list("metal" = 50,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
/obj/item/weapon/stock_parts/manipulator/nano
name = "nano-manipulator"
@@ -518,7 +565,7 @@
icon_state = "nano_mani"
origin_tech = list(TECH_MATERIAL = 3, TECH_DATA = 2)
rating = 2
- matter = list("metal" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 30)
/obj/item/weapon/stock_parts/micro_laser/high
name = "high-power micro-laser"
@@ -526,7 +573,7 @@
icon_state = "high_micro_laser"
origin_tech = list(TECH_MAGNET = 3)
rating = 2
- matter = list("metal" = 10,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 10,"glass" = 20)
/obj/item/weapon/stock_parts/matter_bin/adv
name = "advanced matter bin"
@@ -534,7 +581,7 @@
icon_state = "advanced_matter_bin"
origin_tech = list(TECH_MATERIAL = 3)
rating = 2
- matter = list("metal" = 80)
+ matter = list(DEFAULT_WALL_MATERIAL = 80)
//Rating 3
@@ -543,14 +590,14 @@
desc = "A super-high capacity capacitor used in the construction of a variety of devices."
origin_tech = list(TECH_POWER = 5, TECH_MATERIAL = 4)
rating = 3
- matter = list("metal" = 50,"glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 50)
/obj/item/weapon/stock_parts/scanning_module/phasic
name = "phasic scanning module"
desc = "A compact, high resolution phasic scanning module used in the construction of certain devices."
origin_tech = list(TECH_MAGNET = 5)
rating = 3
- matter = list("metal" = 50,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
/obj/item/weapon/stock_parts/manipulator/pico
name = "pico-manipulator"
@@ -558,7 +605,7 @@
icon_state = "pico_mani"
origin_tech = list(TECH_MATERIAL = 5, TECH_DATA = 2)
rating = 3
- matter = list("metal" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 30)
/obj/item/weapon/stock_parts/micro_laser/ultra
name = "ultra-high-power micro-laser"
@@ -566,7 +613,7 @@
desc = "A tiny laser used in certain devices."
origin_tech = list(TECH_MAGNET = 5)
rating = 3
- matter = list("metal" = 10,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 10,"glass" = 20)
/obj/item/weapon/stock_parts/matter_bin/super
name = "super matter bin"
@@ -574,7 +621,7 @@
icon_state = "super_matter_bin"
origin_tech = list(TECH_MATERIAL = 5)
rating = 3
- matter = list("metal" = 80)
+ matter = list(DEFAULT_WALL_MATERIAL = 80)
// Subspace stock parts
@@ -583,35 +630,35 @@
icon_state = "subspace_ansible"
desc = "A compact module capable of sensing extradimensional activity."
origin_tech = list(TECH_DATA = 3, TECH_MAGNET = 5 ,TECH_MATERIAL = 4, TECH_BLUESPACE = 2)
- matter = list("metal" = 30,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 10)
/obj/item/weapon/stock_parts/subspace/filter
name = "hyperwave filter"
icon_state = "hyperwave_filter"
desc = "A tiny device capable of filtering and converting super-intense radiowaves."
origin_tech = list(TECH_DATA = 4, TECH_MAGNET = 2)
- matter = list("metal" = 30,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 10)
/obj/item/weapon/stock_parts/subspace/amplifier
name = "subspace amplifier"
icon_state = "subspace_amplifier"
desc = "A compact micro-machine capable of amplifying weak subspace transmissions."
origin_tech = list(TECH_DATA = 3, TECH_MAGNET = 4, TECH_MATERIAL = 4, TECH_BLUESPACE = 2)
- matter = list("metal" = 30,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 10)
/obj/item/weapon/stock_parts/subspace/treatment
name = "subspace treatment disk"
icon_state = "treatment_disk"
desc = "A compact micro-machine capable of stretching out hyper-compressed radio waves."
origin_tech = list(TECH_DATA = 3, TECH_MAGNET = 2, TECH_MATERIAL = 5, TECH_BLUESPACE = 2)
- matter = list("metal" = 30,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 10)
/obj/item/weapon/stock_parts/subspace/analyzer
name = "subspace wavelength analyzer"
icon_state = "wavelength_analyzer"
desc = "A sophisticated analyzer capable of analyzing cryptic subspace wavelengths."
origin_tech = list(TECH_DATA = 3, TECH_MAGNETS = 4, TECH_MATERIAL = 4, TECH_BLUESPACE = 2)
- matter = list("metal" = 30,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 10)
/obj/item/weapon/stock_parts/subspace/crystal
name = "ansible crystal"
@@ -625,7 +672,7 @@
icon_state = "subspace_transmitter"
desc = "A large piece of equipment used to open a window into the subspace dimension."
origin_tech = list(TECH_MAGNET = 5, TECH_MATERIAL = 5, TECH_BLUESPACE = 3)
- matter = list("metal" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50)
/obj/item/weapon/ectoplasm
name = "ectoplasm"
diff --git a/code/defines/procs/admin.dm b/code/defines/procs/admin.dm
index 2bfb8b94364..6c5f27fa070 100644
--- a/code/defines/procs/admin.dm
+++ b/code/defines/procs/admin.dm
@@ -1,13 +1,36 @@
-proc/log_and_message_admins(var/message as text)
- log_admin(usr ? "[key_name(usr)] [message]" : "EVENT [message]")
- message_admins(usr ? "[key_name(usr)] [message]" : "EVENT [message]")
+proc/admin_notice(var/message, var/rights)
+ for(var/mob/M in mob_list)
+ if(check_rights(rights, 0, M))
+ M << message
+
+proc/log_and_message_admins(var/message as text, var/mob/user = usr)
+ log_admin(user ? "[key_name(user)] [message]" : "EVENT [message]")
+ message_admins(user ? "[key_name(user)] [message]" : "EVENT [message]")
+
+proc/log_and_message_admins_many(var/list/mob/users, var/message)
+ if(!users || !users.len)
+ return
+
+ var/list/user_keys = list()
+ for(var/mob/user in users)
+ user_keys += key_name(user)
+
+ log_admin("[english_list(user_keys)] [message]")
+ message_admins("[english_list(user_keys)] [message]")
proc/admin_log_and_message_admins(var/message as text)
log_admin(usr ? "[key_name_admin(usr)] [message]" : "EVENT [message]")
message_admins(usr ? "[key_name_admin(usr)] [message]" : "EVENT [message]", 1)
proc/admin_attack_log(var/mob/attacker, var/mob/victim, var/attacker_message, var/victim_message, var/admin_message)
- victim.attack_log += text("\[[time_stamp()]\] [victim_message] [key_name(attacker)]")
- attacker.attack_log += text("\[[time_stamp()]\] [attacker_message] [key_name(victim)]")
+ victim.attack_log += text("\[[time_stamp()]\] [key_name(attacker)] - [victim_message]")
+ attacker.attack_log += text("\[[time_stamp()]\] [key_name(victim)] - [attacker_message]")
msg_admin_attack("[key_name(attacker)] [admin_message] [key_name(victim)] (INTENT: [uppertext(attacker.a_intent)]) (JMP)")
+
+proc/admin_attacker_log_many_victims(var/mob/attacker, var/list/mob/victims, var/attacker_message, var/victim_message, var/admin_message)
+ if(!victims || !victims.len)
+ return
+
+ for(var/mob/victim in victims)
+ admin_attack_log(attacker, victim, attacker_message, victim_message, admin_message)
diff --git a/code/defines/procs/announce.dm b/code/defines/procs/announce.dm
index 3e5454d8ac0..0a64e895924 100644
--- a/code/defines/procs/announce.dm
+++ b/code/defines/procs/announce.dm
@@ -15,28 +15,29 @@
log = do_log
newscast = do_newscast
-/datum/announcement/priority/New(var/do_log = 1, var/new_sound = sound('sound/misc/notice2.ogg'), var/do_newscast = 0)
+/datum/announcement/priority/New(var/do_log = 1, var/new_sound = 'sound/misc/notice2.ogg', var/do_newscast = 0)
..(do_log, new_sound, do_newscast)
title = "Priority Announcement"
announcement_type = "Priority Announcement"
-/datum/announcement/priority/command/New(var/do_log = 1, var/new_sound = sound('sound/misc/notice2.ogg'), var/do_newscast = 0)
+/datum/announcement/priority/command/New(var/do_log = 1, var/new_sound = 'sound/misc/notice2.ogg', var/do_newscast = 0)
..(do_log, new_sound, do_newscast)
title = "[command_name()] Update"
announcement_type = "[command_name()] Update"
-/datum/announcement/priority/security/New(var/do_log = 1, var/new_sound = sound('sound/misc/notice2.ogg'), var/do_newscast = 0)
+/datum/announcement/priority/security/New(var/do_log = 1, var/new_sound = 'sound/misc/notice2.ogg', var/do_newscast = 0)
..(do_log, new_sound, do_newscast)
title = "Security Announcement"
announcement_type = "Security Announcement"
-/datum/announcement/proc/Announce(var/message as text, var/new_title = "", var/new_sound = null, var/do_newscast = newscast)
+/datum/announcement/proc/Announce(var/message as text, var/new_title = "", var/new_sound = null, var/do_newscast = newscast, var/msg_sanitized = 0)
if(!message)
return
- var/tmp/message_title = new_title ? new_title : title
- var/tmp/message_sound = new_sound ? sound(new_sound) : sound
+ var/message_title = new_title ? new_title : title
+ var/message_sound = new_sound ? new_sound : sound
- message = sanitize(message, extra = 0)
+ if(!msg_sanitized)
+ message = sanitize(message, extra = 0)
message_title = sanitizeSafe(message_title)
Message(message, message_title)
@@ -102,8 +103,8 @@ datum/announcement/proc/Sound(var/message_sound)
PlaySound(message_sound)
datum/announcement/priority/Sound(var/message_sound)
- if(sound)
- world << sound
+ if(message_sound)
+ world << message_sound
datum/announcement/priority/command/Sound(var/message_sound)
PlaySound(message_sound)
diff --git a/code/defines/procs/radio.dm b/code/defines/procs/radio.dm
index 1e0e045928b..0ee38f3b120 100644
--- a/code/defines/procs/radio.dm
+++ b/code/defines/procs/radio.dm
@@ -3,6 +3,16 @@
#define TELECOMMS_RECEPTION_RECEIVER 2
#define TELECOMMS_RECEPTION_BOTH 3
+/proc/register_radio(source, old_frequency, new_frequency, radio_filter)
+ if(old_frequency)
+ radio_controller.remove_object(source, old_frequency)
+ if(new_frequency)
+ return radio_controller.add_object(source, new_frequency, radio_filter)
+
+/proc/unregister_radio(source, frequency)
+ if(radio_controller)
+ radio_controller.remove_object(source, frequency)
+
/proc/get_frequency_name(var/display_freq)
var/freq_text
diff --git a/code/defines/procs/records.dm b/code/defines/procs/records.dm
index 4e9fbcc9afc..256ae51dbf2 100644
--- a/code/defines/procs/records.dm
+++ b/code/defines/procs/records.dm
@@ -22,7 +22,7 @@
G.fields["photo_side"] = side
data_core.general += G
- del(dummy)
+ qdel(dummy)
return G
/proc/CreateSecurityRecord(var/name as text, var/id as text)
diff --git a/code/defines/procs/sd_Alert.dm b/code/defines/procs/sd_Alert.dm
index c63cab8f8b7..e10416f1128 100644
--- a/code/defines/procs/sd_Alert.dm
+++ b/code/defines/procs/sd_Alert.dm
@@ -1,168 +1,168 @@
-/* sd_Alert library
- by Shadowdarke (shadowdarke@byond.com)
-
- sd_Alert() is a powerful and flexible alternative to the built in BYOND
- alert() proc. sd_Alert offers timed popups, unlimited buttons, custom
- appearance, and even the option to popup without stealing keyboard focus
- from the map or command line.
-
- Please see demo.dm for detailed examples.
-
-FORMAT
- sd_Alert(who, message, title, buttons, default, duration, unfocus, \
- size, table, style, tag, select, flags)
-
-ARGUMENTS
- who - the client or mob to display the alert to.
- message - text message to display
- title - title of the alert box
- buttons - list of buttons
- Default Value: list("Ok")
- default - default button selestion
- Default Value: the first button in the list
- duration - the number of ticks before this alert expires. If not
- set, the alert lasts until a button is clicked.
- Default Value: 0 (unlimited)
- unfocus - if this value is set, the popup will not steal keyboard
- focus from the map or command line.
- Default Value: 1 (do not take focus)
- size - size of the popup window in px
- Default Value: "300x200"
- table - optional parameters for the HTML table in the alert
- Default Value: "width=100% height=100%" (fill the window)
- style - optional style sheet information
- tag - lets you specify a certain tag for this sd_Alert so you may manipulate it
- externally. (i.e. force the alert to close, change options and redisplay,
- reuse the same window, etc.)
- select - if set, the buttons will be replaced with a selection box with a number of
- lines displayed equal to this value.
- Default value: 0 (use buttons)
- flags - optional flags effecting the alert display. These flags may be ORed (|)
- together for multiple effects.
- SD_ALERT_SCROLL = display a scrollbar
- SD_ALERT_SELECT_MULTI = forces selection box display (instead of
- buttons) allows the user to select multiple
- choices.
- SD_ALERT_LINKS = display each choice as a plain text link.
- Any selection box style overrides this flag.
- SD_ALERT_NOVALIDATE = don't validate responses
- Default value: SD_ALERT_SCROLL
- (button display with scroll bar, validate responses)
-RETURNS
- The text of the selected button, or null if the alert duration expired
- without a button click.
-
-Version 1 changes (from version 0):
-* Added the tag, select, and flags arguments, thanks to several suggestions from Foomer.
-* Split the sd_Alert/Alert() proc into New(), Display(), and Response() to allow more
- customization by developers. Primarily developers would want to use Display() to change
- the display of active tagged windows
-
-*/
-
-
-#define SD_ALERT_SCROLL 1
-#define SD_ALERT_SELECT_MULTI 2
-#define SD_ALERT_LINKS 4
-#define SD_ALERT_NOVALIDATE 8
-
-proc/sd_Alert(client/who, message, title, buttons = list("Ok"),\
- default, duration = 0, unfocus = 1, size = "300x200", \
- table = "width=100% height=100%", style, tag, select, flags = SD_ALERT_SCROLL)
-
- if(ismob(who))
- var/mob/M = who
- who = M.client
- if(!istype(who)) CRASH("sd_Alert: Invalid target:[who] (\ref[who])")
-
- var/sd_alert/T = locate(tag)
- if(T)
- if(istype(T)) del(T)
- else CRASH("sd_Alert: tag \"[tag]\" is already in use by datum '[T]' (type: [T.type])")
- T = new(who, tag)
- if(duration)
- spawn(duration)
- if(T) del(T)
- return
- T.Display(message,title,buttons,default,unfocus,size,table,style,select,flags)
- . = T.Response()
-
-sd_alert
- var
- client/target
- response
- list/validation
-
- Del()
- target << browse(null,"window=\ref[src]")
- ..()
-
- New(who, tag)
- ..()
- target = who
- src.tag = tag
-
- Topic(href,params[])
- if(usr.client != target) return
- response = params["clk"]
-
- proc/Display(message,title,list/buttons,default,unfocus,size,table,style,select,flags)
- if(unfocus) spawn() target << browse(null,null)
- if(istext(buttons)) buttons = list(buttons)
- if(!default) default = buttons[1]
- if(!(flags & SD_ALERT_NOVALIDATE)) validation = buttons.Copy()
-
- var/html = {"[title][style]
\
-
[message]
"}
-
- if(select || (flags & SD_ALERT_SELECT_MULTI)) // select style choices
- html += {""
- else if(flags & SD_ALERT_LINKS) // text link style
- for(var/b in buttons)
- var/list/L = list()
- L["clk"] = b
- var/html_string=list2params(L)
- var/focus
- if(b == default) focus = " ID=fcs"
- html += "[html_encode(b)]\
- "
- else // button style choices
- for(var/b in buttons)
- var/list/L = list()
- L["clk"] = b
- var/html_string=list2params(L)
- var/focus
- if(b == default) focus = " ID=fcs"
- html += " "
-
- html += "
"
-
- target << browse(html,"window=\ref[src];size=[size];can_close=0")
-
- proc/Response()
- var/validated
- while(!validated)
- while(target && !response) // wait for a response
- sleep(2)
-
- if(response && validation)
- if(istype(response, /list))
- var/list/L = response - validation
- if(L.len) response = null
- else validated = 1
- else if(response in validation) validated = 1
- else response=null
- else validated = 1
- spawn(2) del(src)
- return response
+/* sd_Alert library
+ by Shadowdarke (shadowdarke@byond.com)
+
+ sd_Alert() is a powerful and flexible alternative to the built in BYOND
+ alert() proc. sd_Alert offers timed popups, unlimited buttons, custom
+ appearance, and even the option to popup without stealing keyboard focus
+ from the map or command line.
+
+ Please see demo.dm for detailed examples.
+
+FORMAT
+ sd_Alert(who, message, title, buttons, default, duration, unfocus, \
+ size, table, style, tag, select, flags)
+
+ARGUMENTS
+ who - the client or mob to display the alert to.
+ message - text message to display
+ title - title of the alert box
+ buttons - list of buttons
+ Default Value: list("Ok")
+ default - default button selestion
+ Default Value: the first button in the list
+ duration - the number of ticks before this alert expires. If not
+ set, the alert lasts until a button is clicked.
+ Default Value: 0 (unlimited)
+ unfocus - if this value is set, the popup will not steal keyboard
+ focus from the map or command line.
+ Default Value: 1 (do not take focus)
+ size - size of the popup window in px
+ Default Value: "300x200"
+ table - optional parameters for the HTML table in the alert
+ Default Value: "width=100% height=100%" (fill the window)
+ style - optional style sheet information
+ tag - lets you specify a certain tag for this sd_Alert so you may manipulate it
+ externally. (i.e. force the alert to close, change options and redisplay,
+ reuse the same window, etc.)
+ select - if set, the buttons will be replaced with a selection box with a number of
+ lines displayed equal to this value.
+ Default value: 0 (use buttons)
+ flags - optional flags effecting the alert display. These flags may be ORed (|)
+ together for multiple effects.
+ SD_ALERT_SCROLL = display a scrollbar
+ SD_ALERT_SELECT_MULTI = forces selection box display (instead of
+ buttons) allows the user to select multiple
+ choices.
+ SD_ALERT_LINKS = display each choice as a plain text link.
+ Any selection box style overrides this flag.
+ SD_ALERT_NOVALIDATE = don't validate responses
+ Default value: SD_ALERT_SCROLL
+ (button display with scroll bar, validate responses)
+RETURNS
+ The text of the selected button, or null if the alert duration expired
+ without a button click.
+
+Version 1 changes (from version 0):
+* Added the tag, select, and flags arguments, thanks to several suggestions from Foomer.
+* Split the sd_Alert/Alert() proc into New(), Display(), and Response() to allow more
+ customization by developers. Primarily developers would want to use Display() to change
+ the display of active tagged windows
+
+*/
+
+
+#define SD_ALERT_SCROLL 1
+#define SD_ALERT_SELECT_MULTI 2
+#define SD_ALERT_LINKS 4
+#define SD_ALERT_NOVALIDATE 8
+
+proc/sd_Alert(client/who, message, title, buttons = list("Ok"),\
+ default, duration = 0, unfocus = 1, size = "300x200", \
+ table = "width=100% height=100%", style, tag, select, flags = SD_ALERT_SCROLL)
+
+ if(ismob(who))
+ var/mob/M = who
+ who = M.client
+ if(!istype(who)) CRASH("sd_Alert: Invalid target:[who] (\ref[who])")
+
+ var/sd_alert/T = locate(tag)
+ if(T)
+ if(istype(T)) qdel(T)
+ else CRASH("sd_Alert: tag \"[tag]\" is already in use by datum '[T]' (type: [T.type])")
+ T = new(who, tag)
+ if(duration)
+ spawn(duration)
+ if(T) qdel(T)
+ return
+ T.Display(message,title,buttons,default,unfocus,size,table,style,select,flags)
+ . = T.Response()
+
+sd_alert
+ var
+ client/target
+ response
+ list/validation
+
+ Destroy()
+ target << browse(null,"window=\ref[src]")
+ ..()
+
+ New(who, tag)
+ ..()
+ target = who
+ src.tag = tag
+
+ Topic(href,params[])
+ if(usr.client != target) return
+ response = params["clk"]
+
+ proc/Display(message,title,list/buttons,default,unfocus,size,table,style,select,flags)
+ if(unfocus) spawn() target << browse(null,null)
+ if(istext(buttons)) buttons = list(buttons)
+ if(!default) default = buttons[1]
+ if(!(flags & SD_ALERT_NOVALIDATE)) validation = buttons.Copy()
+
+ var/html = {"[title][style]
\
+
[message]
"}
+
+ if(select || (flags & SD_ALERT_SELECT_MULTI)) // select style choices
+ html += {""
+ else if(flags & SD_ALERT_LINKS) // text link style
+ for(var/b in buttons)
+ var/list/L = list()
+ L["clk"] = b
+ var/html_string=list2params(L)
+ var/focus
+ if(b == default) focus = " ID=fcs"
+ html += "[html_encode(b)]\
+ "
+ else // button style choices
+ for(var/b in buttons)
+ var/list/L = list()
+ L["clk"] = b
+ var/html_string=list2params(L)
+ var/focus
+ if(b == default) focus = " ID=fcs"
+ html += " "
+
+ html += "
"
+
+ target << browse(html,"window=\ref[src];size=[size];can_close=0")
+
+ proc/Response()
+ var/validated
+ while(!validated)
+ while(target && !response) // wait for a response
+ sleep(2)
+
+ if(response && validation)
+ if(istype(response, /list))
+ var/list/L = response - validation
+ if(L.len) response = null
+ else validated = 1
+ else if(response in validation) validated = 1
+ else response=null
+ else validated = 1
+ spawn(2) qdel(src)
+ return response
diff --git a/code/defines/procs/statistics.dm b/code/defines/procs/statistics.dm
index 8a9eb4042dc..60254577583 100644
--- a/code/defines/procs/statistics.dm
+++ b/code/defines/procs/statistics.dm
@@ -1,34 +1,20 @@
-proc/sql_poll_players()
+proc/sql_poll_population()
if(!sqllogging)
return
+ var/admincount = admins.len
var/playercount = 0
for(var/mob/M in player_list)
if(M.client)
playercount += 1
establish_db_connection()
if(!dbcon.IsConnected())
- log_game("SQL ERROR during player polling. Failed to connect.")
+ log_game("SQL ERROR during population polling. Failed to connect.")
else
var/sqltime = time2text(world.realtime, "YYYY-MM-DD hh:mm:ss")
- var/DBQuery/query = dbcon_old.NewQuery("INSERT INTO population (playercount, time) VALUES ([playercount], '[sqltime]')")
+ var/DBQuery/query = dbcon_old.NewQuery("INSERT INTO `tgstation`.`population` (`playercount`, `admincount`, `time`) VALUES ([playercount], [admincount], '[sqltime]')")
if(!query.Execute())
var/err = query.ErrorMsg()
- log_game("SQL ERROR during player polling. Error : \[[err]\]\n")
-
-
-proc/sql_poll_admins()
- if(!sqllogging)
- return
- var/admincount = admins.len
- establish_db_connection()
- if(!dbcon.IsConnected())
- log_game("SQL ERROR during admin polling. Failed to connect.")
- else
- var/sqltime = time2text(world.realtime, "YYYY-MM-DD hh:mm:ss")
- var/DBQuery/query = dbcon_old.NewQuery("INSERT INTO population (admincount, time) VALUES ([admincount], '[sqltime]')")
- if(!query.Execute())
- var/err = query.ErrorMsg()
- log_game("SQL ERROR during admin polling. Error : \[[err]\]\n")
+ log_game("SQL ERROR during population polling. Error : \[[err]\]\n")
proc/sql_report_round_start()
// TODO
@@ -111,10 +97,8 @@ proc/statistic_cycle()
if(!sqllogging)
return
while(1)
- sql_poll_players()
- sleep(600)
- sql_poll_admins()
- sleep(6000) // Poll every ten minutes
+ sql_poll_population()
+ sleep(6000)
//This proc is used for feedback. It is executed at round end.
proc/sql_commit_feedback()
@@ -157,4 +141,4 @@ proc/sql_commit_feedback()
var/DBQuery/query = dbcon.NewQuery("INSERT INTO erro_feedback (id, roundid, time, variable, value) VALUES (null, [newroundid], Now(), '[variable]', '[value]')")
if(!query.Execute())
var/err = query.ErrorMsg()
- log_game("SQL ERROR during death reporting. Error : \[[err]\]\n")
\ No newline at end of file
+ log_game("SQL ERROR during death reporting. Error : \[[err]\]\n")
diff --git a/code/game/antagonist/antagonist.dm b/code/game/antagonist/antagonist.dm
index 73e17a20430..aad02b1c6c6 100644
--- a/code/game/antagonist/antagonist.dm
+++ b/code/game/antagonist/antagonist.dm
@@ -199,7 +199,7 @@
for(var/datum/uplink_item/UI in H.purchase_log)
var/obj/I = new UI.path
refined_log.Add("[H.purchase_log[UI]]x\icon[I][UI.name]")
- del(I)
+ qdel(I)
purchases = english_list(refined_log, nothing_text = "")
if(uplink_true)
text += " (used [TC_uses] TC)"
@@ -215,7 +215,7 @@
if(antag.current && antag.current.client)
for(var/image/I in antag.current.client.images)
if(I.icon_state == antag_indicator)
- del(I)
+ qdel(I)
for(var/datum/mind/other_antag in current_antagonists)
if(other_antag.current)
antag.current.client.images |= image('icons/mob/mob.dmi', loc = other_antag.current, icon_state = antag_indicator)
@@ -241,10 +241,10 @@
if(antag.current.client)
for(var/image/I in antag.current.client.images)
if(I.icon_state == antag_indicator && I.loc == player.current)
- del(I)
+ qdel(I)
if(player.current && player.current.client)
for(var/image/I in player.current.client.images)
if(I.icon_state == antag_indicator)
- del(I)
+ qdel(I)
diff --git a/code/game/antagonist/antagonist_build.dm b/code/game/antagonist/antagonist_build.dm
index f0f92c62b7a..35af4e6f804 100644
--- a/code/game/antagonist/antagonist_build.dm
+++ b/code/game/antagonist/antagonist_build.dm
@@ -15,7 +15,7 @@
var/mob/holder = player.current
player.current = new mob_path(get_turf(player.current))
player.transfer_to(player.current)
- if(holder) del(holder)
+ if(holder) qdel(holder)
player.original = player.current
return player.current
@@ -28,11 +28,13 @@
// This could use work.
if(flags & ANTAG_CLEAR_EQUIPMENT)
for(var/obj/item/thing in player.contents)
- del(thing)
+ player.drop_from_inventory(thing)
+ if(thing.loc != player)
+ qdel(thing)
return 1
if(flags & ANTAG_SET_APPEARANCE)
- player.change_appearance(APPEARANCE_ALL, player, player, valid_species)
+ player.change_appearance(APPEARANCE_ALL, player.loc, player, valid_species, state = z_state)
/datum/antagonist/proc/unequip(var/mob/living/carbon/human/player)
if(!istype(player))
@@ -80,6 +82,7 @@
/datum/antagonist/proc/create_id(var/assignment, var/mob/living/carbon/human/player)
var/obj/item/weapon/card/id/W = new id_type(player)
+ if(!W) return
W.name = "[player.real_name]'s ID Card"
W.access |= default_access
W.assignment = "[assignment]"
diff --git a/code/game/antagonist/outsider/deathsquad.dm b/code/game/antagonist/outsider/deathsquad.dm
index 05fb6d1ec9b..73c2c7fd78a 100644
--- a/code/game/antagonist/outsider/deathsquad.dm
+++ b/code/game/antagonist/outsider/deathsquad.dm
@@ -44,8 +44,9 @@ var/datum/antagonist/deathsquad/deathsquad
player.implant_loyalty(player)
var/obj/item/weapon/card/id/id = create_id("Asset Protection", player)
- id.access |= get_all_accesses()
- id.icon_state = "centcom"
+ if(id)
+ id.access |= get_all_accesses()
+ id.icon_state = "centcom"
create_radio(DTH_FREQ, player)
/datum/antagonist/deathsquad/apply(var/datum/mind/player)
diff --git a/code/game/antagonist/outsider/ert.dm b/code/game/antagonist/outsider/ert.dm
index f52f031002c..946ff1dfc28 100644
--- a/code/game/antagonist/outsider/ert.dm
+++ b/code/game/antagonist/outsider/ert.dm
@@ -32,13 +32,9 @@ var/datum/antagonist/ert/ert
player.equip_to_slot_or_del(new /obj/item/clothing/gloves/swat(src), slot_gloves)
player.equip_to_slot_or_del(new /obj/item/clothing/glasses/sunglasses(src), slot_glasses)
- var/obj/item/weapon/card/id/W = new(src)
- W.assignment = "Emergency Response Team"
+ var/obj/item/weapon/card/id/centcom/ERT/W = new(src)
W.registered_name = player.real_name
W.name = "[player.real_name]'s ID Card ([W.assignment])"
- W.icon_state = "centcom"
- W.access = get_all_accesses()
- W.access += get_all_centcom_access()
player.equip_to_slot_or_del(W, slot_wear_id)
return 1
diff --git a/code/game/antagonist/outsider/raider.dm b/code/game/antagonist/outsider/raider.dm
index 92090515b16..a7949011fc5 100644
--- a/code/game/antagonist/outsider/raider.dm
+++ b/code/game/antagonist/outsider/raider.dm
@@ -30,8 +30,8 @@ var/datum/antagonist/raider/raiders
var/list/raider_glasses = list(
/obj/item/clothing/glasses/thermal,
- /obj/item/clothing/glasses/thermal/eyepatch,
- /obj/item/clothing/glasses/thermal/monocle
+ /obj/item/clothing/glasses/thermal/plain/eyepatch,
+ /obj/item/clothing/glasses/thermal/plain/monocle
)
var/list/raider_helmets = list(
diff --git a/code/game/antagonist/outsider/wizard.dm b/code/game/antagonist/outsider/wizard.dm
index 7b410cc7bc8..2923008a7b8 100644
--- a/code/game/antagonist/outsider/wizard.dm
+++ b/code/game/antagonist/outsider/wizard.dm
@@ -95,21 +95,31 @@ var/datum/antagonist/wizard/wizards
//To batch-remove wizard spells. Linked to mind.dm.
/mob/proc/spellremove(var/mob/M as mob)
- for(var/obj/effect/proc_holder/spell/spell_to_remove in src.spell_list)
- del(spell_to_remove)
+ for(var/spell/spell_to_remove in src.spell_list)
+ remove_spell(spell_to_remove)
-/*Checks if the wizard can cast spells.
+obj/item/clothing
+ var/wizard_garb = 0
+
+// Does this clothing slot count as wizard garb? (Combines a few checks)
+/proc/is_wiz_garb(var/obj/item/clothing/C)
+ return C && C.wizard_garb
+
+/*Checks if the wizard is wearing the proper attire.
Made a proc so this is not repeated 14 (or more) times.*/
-/mob/proc/casting()
-//Removed the stat check because not all spells require clothing now.
- if(!istype(usr:wear_suit, /obj/item/clothing/suit/wizrobe))
- usr << "I don't feel strong enough without my robe."
+/mob/proc/wearing_wiz_garb()
+ src << "Silly creature, you're not a human. Only humans can cast this spell."
+ return 0
+
+// Humans can wear clothes.
+/mob/living/carbon/human/wearing_wiz_garb()
+ if(!is_wiz_garb(src.wear_suit))
+ src << "I don't feel strong enough without my robe."
return 0
- if(!istype(usr:shoes, /obj/item/clothing/shoes/sandal))
- usr << "I don't feel strong enough without my sandals."
+ if(!is_wiz_garb(src.shoes))
+ src << "I don't feel strong enough without my sandals."
return 0
- if(!istype(usr:head, /obj/item/clothing/head/wizard))
- usr << "I don't feel strong enough without my hat."
+ if(!is_wiz_garb(src.head))
+ src << "I don't feel strong enough without my hat."
return 0
- else
- return 1
+ return 1
diff --git a/code/game/antagonist/station/cultist.dm b/code/game/antagonist/station/cultist.dm
index 3968418e023..3f5d65d21da 100644
--- a/code/game/antagonist/station/cultist.dm
+++ b/code/game/antagonist/station/cultist.dm
@@ -24,11 +24,13 @@ var/datum/antagonist/cultist/cult
flags = ANTAG_SUSPICIOUS | ANTAG_RANDSPAWN | ANTAG_VOTABLE
max_antags = 200 // No upper limit.
max_antags_round = 200
+ var/allow_narsie = 1
var/datum/mind/sacrifice_target
var/list/startwords = list("blood","join","self","hell")
var/list/allwords = list("travel","self","see","hell","blood","join","tech","destroy", "other", "hide")
var/list/sacrificed = list()
+ var/list/harvested = list()
/datum/antagonist/cultist/New()
..()
diff --git a/code/game/antagonist/station/highlander.dm b/code/game/antagonist/station/highlander.dm
index 0af6e1e23de..9b82b158525 100644
--- a/code/game/antagonist/station/highlander.dm
+++ b/code/game/antagonist/station/highlander.dm
@@ -32,7 +32,7 @@ var/datum/antagonist/highlander/highlanders
for (var/obj/item/I in player)
if (istype(I, /obj/item/weapon/implant))
continue
- del(I)
+ qdel(I)
player.equip_to_slot_or_del(new /obj/item/clothing/under/kilt(player), slot_w_uniform)
player.equip_to_slot_or_del(new /obj/item/device/radio/headset/heads/captain(player), slot_l_ear)
diff --git a/code/game/antagonist/station/rogue_ai.dm b/code/game/antagonist/station/rogue_ai.dm
index 372556c2051..3d9026ff88f 100644
--- a/code/game/antagonist/station/rogue_ai.dm
+++ b/code/game/antagonist/station/rogue_ai.dm
@@ -27,7 +27,7 @@ var/datum/antagonist/rogue_ai/malf
hacked_apcs |= apc
/datum/antagonist/rogue_ai/proc/update_takeover_time()
- hack_time -= ((hacked_apcs.len/6)*tickerProcess.getLastTickerTimeDuration())
+ hack_time -= ((hacked_apcs.len/6)*2.0)
/datum/antagonist/rogue_ai/tick()
if(revealed && hacked_apcs.len >= 3)
@@ -213,7 +213,7 @@ var/datum/antagonist/rogue_ai/malf
/client/proc/reactivate_camera)
current:laws = new /datum/ai_laws/nanotrasen
- del(current:malf_picker)
+ qdel(current:malf_picker)
current:show_laws()
current.icon_state = "ai"
diff --git a/code/game/area/Space Station 13 areas.dm b/code/game/area/Space Station 13 areas.dm
index c382ce4d078..21e965244bb 100755
--- a/code/game/area/Space Station 13 areas.dm
+++ b/code/game/area/Space Station 13 areas.dm
@@ -26,8 +26,8 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
icon = 'icons/turf/areas.dmi'
icon_state = "unknown"
layer = 10
+ luminosity = 1
mouse_opacity = 0
- invisibility = INVISIBILITY_LIGHTING
var/lightswitch = 1
var/eject = null
@@ -48,15 +48,12 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
var/has_gravity = 1
var/list/apc = list()
var/no_air = null
- var/area/master // master area used for power calcluations
- // (original area before splitting due to sd_DAL)
- var/list/related // the other areas of the same type as this
// var/list/lights // list of all lights on this area
var/list/all_doors = list() //Added by Strumpetplaya - Alarm Change - Contains a list of doors adjacent to this area
var/air_doors_activated = 0
var/list/ambience = list('sound/ambience/ambigen1.ogg','sound/ambience/ambigen3.ogg','sound/ambience/ambigen4.ogg','sound/ambience/ambigen5.ogg','sound/ambience/ambigen6.ogg','sound/ambience/ambigen7.ogg','sound/ambience/ambigen8.ogg','sound/ambience/ambigen9.ogg','sound/ambience/ambigen10.ogg','sound/ambience/ambigen11.ogg','sound/ambience/ambigen12.ogg','sound/ambience/ambigen14.ogg')
- var/sound/forced_ambience = null
-
+ var/list/forced_ambience = null
+ var/sound_env = 2 //reverb preset for sounds played in this area, see sound datum reference for more
/*Adding a wizard area teleport list because motherfucking lag -- Urist*/
/*I am far too lazy to make it a proper list of areas so I'll just make it run the usual telepot routine at the start of the game*/
var/list/teleportlocs = list()
@@ -102,7 +99,6 @@ var/list/ghostteleportlocs = list()
icon_state = "space"
requires_power = 1
always_unpowered = 1
- lighting_use_dynamic = 1
power_light = 0
power_equip = 0
power_environ = 0
@@ -145,10 +141,8 @@ area/space/atmosalert()
//place to another. Look at escape shuttle for example.
//All shuttles should now be under shuttle since we have smooth-wall code.
-/area/shuttle //DO NOT TURN THE lighting_use_dynamic STUFF ON FOR SHUTTLES. IT BREAKS THINGS.
+/area/shuttle
requires_power = 0
- luminosity = 1
- lighting_use_dynamic = 0
/area/shuttle/arrival
name = "\improper Arrival Shuttle"
@@ -249,15 +243,11 @@ area/space/atmosalert()
icon_state = "shuttle"
name = "\improper Alien Shuttle Base"
requires_power = 1
- luminosity = 0
- lighting_use_dynamic = 1
/area/shuttle/alien/mine
icon_state = "shuttle"
name = "\improper Alien Shuttle Mine"
requires_power = 1
- luminosity = 0
- lighting_use_dynamic = 1
/area/shuttle/prison/
name = "\improper Prison Shuttle"
@@ -343,7 +333,6 @@ area/space/atmosalert()
name = "start area"
icon_state = "start"
requires_power = 0
- luminosity = 1
lighting_use_dynamic = 0
has_gravity = 1
@@ -361,6 +350,7 @@ area/space/atmosalert()
icon_state = "centcom"
requires_power = 0
unlimited_power = 1
+ lighting_use_dynamic = 0
/area/centcom/control
name = "\improper Centcom Control"
@@ -399,6 +389,7 @@ area/space/atmosalert()
icon_state = "syndie-ship"
requires_power = 0
unlimited_power = 1
+ lighting_use_dynamic = 0
/area/syndicate_mothership/control
name = "\improper Mercenary Control Room"
@@ -808,6 +799,9 @@ area/space/atmosalert()
//Hallway
+/area/hallway/primary/
+ sound_env = 12 //hallway
+
/area/hallway/primary/fore
name = "\improper Fore Primary Hallway"
icon_state = "hallF"
@@ -873,27 +867,27 @@ area/space/atmosalert()
music = null
/area/crew_quarters/captain
- name = "\improper Captain's Office"
+ name = "\improper Command - Captain's Office"
icon_state = "captain"
/area/crew_quarters/heads/hop
- name = "\improper Head of Personnel's Office"
+ name = "\improper Command - HoP's Office"
icon_state = "head_quarters"
/area/crew_quarters/heads/hor
- name = "\improper Research Director's Office"
+ name = "\improper Research - RD's Office"
icon_state = "head_quarters"
/area/crew_quarters/heads/chief
- name = "\improper Chief Engineer's Office"
+ name = "\improper Engineering - CE's Office"
icon_state = "head_quarters"
/area/crew_quarters/heads/hos
- name = "\improper Head of Security's Office"
+ name = "\improper Security - HoS' Office"
icon_state = "head_quarters"
/area/crew_quarters/heads/cmo
- name = "\improper Chief Medical Officer's Office"
+ name = "\improper Medbay - CMO's Office"
icon_state = "head_quarters"
/area/crew_quarters/courtroom
@@ -1006,16 +1000,13 @@ area/space/atmosalert()
/area/holodeck
name = "\improper Holodeck"
icon_state = "Holodeck"
- luminosity = 1
lighting_use_dynamic = 0
/area/holodeck/alphadeck
name = "\improper Holodeck Alpha"
-
/area/holodeck/source_plating
name = "\improper Holodeck - Off"
- icon_state = "Holodeck"
/area/holodeck/source_emptycourt
name = "\improper Holodeck - Empty Court"
@@ -1031,11 +1022,9 @@ area/space/atmosalert()
/area/holodeck/source_courtroom
name = "\improper Holodeck - Courtroom"
- icon_state = "Holodeck"
/area/holodeck/source_beach
name = "\improper Holodeck - Beach"
- icon_state = "Holodeck" // Lazy.
/area/holodeck/source_burntest
name = "\improper Holodeck - Atmospheric Burn Test"
@@ -1062,9 +1051,6 @@ area/space/atmosalert()
name = "\improper Holodeck - Space"
has_gravity = 0
-
-
-
//Engineering
/area/engineering/
@@ -1085,7 +1071,7 @@ area/space/atmosalert()
icon_state = "atmos_storage"
/area/engineering/drone_fabrication
- name = "\improper Drone Fabrication"
+ name = "\improper Engineering Drone Fabrication"
icon_state = "drone_fab"
/area/engineering/engine_smes
@@ -1143,7 +1129,6 @@ area/space/atmosalert()
/area/solar
requires_power = 1
always_unpowered = 1
- luminosity = 1
lighting_use_dynamic = 0
auxport
@@ -1171,23 +1156,23 @@ area/space/atmosalert()
icon_state = "panelsP"
/area/maintenance/auxsolarport
- name = "Fore Port Solar Maintenance"
+ name = "Solar Maintenance - Fore Port"
icon_state = "SolarcontrolP"
/area/maintenance/starboardsolar
- name = "Aft Starboard Solar Maintenance"
+ name = "Solar Maintenance - Aft Starboard"
icon_state = "SolarcontrolS"
/area/maintenance/portsolar
- name = "Aft Port Solar Maintenance"
+ name = "Solar Maintenance - Aft Port"
icon_state = "SolarcontrolP"
/area/maintenance/auxsolarstarboard
- name = "Fore Starboard Solar Maintenance"
+ name = "Solar Maintenance - Fore Starboard"
icon_state = "SolarcontrolS"
/area/maintenance/foresolar
- name = "Fore Solar Maintenance"
+ name = "Solar Maintenance - Fore"
icon_state = "SolarcontrolA"
/area/assembly/chargebay
@@ -1362,35 +1347,35 @@ area/space/atmosalert()
icon_state = "security"
/area/security/lobby
- name = "\improper Security lobby"
+ name = "\improper Security Lobby"
icon_state = "security"
/area/security/brig
- name = "\improper Brig"
+ name = "\improper Security - Brig"
icon_state = "brig"
/area/security/prison
- name = "\improper Prison Wing"
+ name = "\improper Security - Prison Wing"
icon_state = "sec_prison"
/area/security/warden
- name = "\improper Warden"
+ name = "\improper Security - Warden's Office"
icon_state = "Warden"
/area/security/armoury
- name = "\improper Armory"
+ name = "\improper Security - Armory"
icon_state = "Warden"
/area/security/detectives_office
- name = "\improper Detective's Office"
+ name = "\improper Security - Forensic Office"
icon_state = "detective"
/area/security/range
- name = "\improper Firing Range"
+ name = "\improper Security - Firing Range"
icon_state = "firingrange"
/area/security/tactical
- name = "\improper Tactical Equipment"
+ name = "\improper Security - Tactical Equipment"
icon_state = "Tactical"
@@ -1420,7 +1405,7 @@ area/space/atmosalert()
icon_state = "checkpoint1"
/area/security/checkpoint2
- name = "\improper Security Checkpoint"
+ name = "\improper Security - Arrival Checkpoint"
icon_state = "security"
/area/security/checkpoint/supply
@@ -1451,14 +1436,6 @@ area/space/atmosalert()
name = "\improper Quartermasters"
icon_state = "quart"
-///////////WORK IN PROGRESS//////////
-
-/area/quartermaster/sorting
- name = "\improper Delivery Office"
- icon_state = "quartstorage"
-
-////////////WORK IN PROGRESS//////////
-
/area/quartermaster/office
name = "\improper Cargo Office"
icon_state = "quartoffice"
@@ -1468,21 +1445,13 @@ area/space/atmosalert()
icon_state = "quartstorage"
/area/quartermaster/qm
- name = "\improper Quartermaster's Office"
+ name = "\improper Cargo - Quartermaster's Office"
icon_state = "quart"
/area/quartermaster/miningdock
- name = "\improper Mining Dock"
+ name = "\improper Cargo Mining Dock"
icon_state = "mining"
-/area/quartermaster/miningstorage
- name = "\improper Mining Storage"
- icon_state = "green"
-
-/area/quartermaster/mechbay
- name = "\improper Mech Bay"
- icon_state = "yellow"
-
/area/janitor/
name = "\improper Custodial Closet"
icon_state = "janitor"
@@ -1770,7 +1739,7 @@ area/space/atmosalert()
//Construction
/area/construction
- name = "\improper Construction Area"
+ name = "\improper Engineering Construction Area"
icon_state = "yellow"
/area/construction/supplyshuttle
@@ -2041,6 +2010,7 @@ area/space/atmosalert()
luminosity = 1
lighting_use_dynamic = 0
requires_power = 0
+ ambience = list()
var/sound/mysound = null
New()
diff --git a/code/game/area/areas.dm b/code/game/area/areas.dm
index 0778f50174a..38452c3d5bd 100644
--- a/code/game/area/areas.dm
+++ b/code/game/area/areas.dm
@@ -10,44 +10,38 @@
/area/New()
icon_state = ""
layer = 10
- master = src //moved outside the spawn(1) to avoid runtimes in lighting.dm when it references loc.loc.master ~Carn
uid = ++global_uid
- related = list(src)
all_areas += src
- if(requires_power)
- luminosity = 0
- else
+ if(!requires_power)
power_light = 0 //rastaf0
power_equip = 0 //rastaf0
power_environ = 0 //rastaf0
- luminosity = 1
- lighting_use_dynamic = 0
..()
// spawn(15)
power_change() // all machines set to current power level, also updates lighting icon
- InitializeLighting()
+
+/area/proc/get_contents()
+ return contents
/area/proc/get_cameras()
var/list/cameras = list()
- for (var/area/RA in related)
- for (var/obj/machinery/camera/C in RA)
- cameras += C
+ for (var/obj/machinery/camera/C in src)
+ cameras += C
return cameras
/area/proc/atmosalert(danger_level, var/alarm_source)
if (danger_level == 0)
- atmosphere_alarm.clearAlarm(master, alarm_source)
+ atmosphere_alarm.clearAlarm(src, alarm_source)
else
- atmosphere_alarm.triggerAlarm(master, alarm_source, severity = danger_level)
+ atmosphere_alarm.triggerAlarm(src, alarm_source, severity = danger_level)
//Check all the alarms before lowering atmosalm. Raising is perfectly fine.
- for (var/area/RA in related)
- for (var/obj/machinery/alarm/AA in RA)
- if (!(AA.stat & (NOPOWER|BROKEN)) && !AA.shorted && AA.report_danger_level)
- danger_level = max(danger_level, AA.danger_level)
+ for (var/obj/machinery/alarm/AA in src)
+ if (!(AA.stat & (NOPOWER|BROKEN)) && !AA.shorted && AA.report_danger_level)
+ danger_level = max(danger_level, AA.danger_level)
if(danger_level != atmosalm)
if (danger_level < 1 && atmosalm >= 1)
@@ -57,17 +51,16 @@
air_doors_close()
atmosalm = danger_level
- for(var/area/RA in related)
- for (var/obj/machinery/alarm/AA in RA)
- AA.update_icon()
+ for (var/obj/machinery/alarm/AA in src)
+ AA.update_icon()
return 1
return 0
/area/proc/air_doors_close()
- if(!src.master.air_doors_activated)
- src.master.air_doors_activated = 1
- for(var/obj/machinery/door/firedoor/E in src.master.all_doors)
+ if(!air_doors_activated)
+ air_doors_activated = 1
+ for(var/obj/machinery/door/firedoor/E in all_doors)
if(!E.blocked)
if(E.operating)
E.nextstate = CLOSED
@@ -76,9 +69,9 @@
E.close()
/area/proc/air_doors_open()
- if(src.master.air_doors_activated)
- src.master.air_doors_activated = 0
- for(var/obj/machinery/door/firedoor/E in src.master.all_doors)
+ if(air_doors_activated)
+ air_doors_activated = 0
+ for(var/obj/machinery/door/firedoor/E in all_doors)
if(!E.blocked)
if(E.operating)
E.nextstate = OPEN
@@ -89,11 +82,8 @@
/area/proc/fire_alert()
if(!fire)
- master.fire = 1 //used for firedoor checks
- master.updateicon()
- for(var/area/A in related)
- A.fire = 1
- A.updateicon()
+ fire = 1 //used for firedoor checks
+ updateicon()
mouse_opacity = 0
for(var/obj/machinery/door/firedoor/D in all_doors)
if(!D.blocked)
@@ -105,11 +95,8 @@
/area/proc/fire_reset()
if (fire)
- master.fire = 0 //used for firedoor checks
- master.updateicon()
- for(var/area/A in related)
- A.fire = 0
- A.updateicon()
+ fire = 0 //used for firedoor checks
+ updateicon()
mouse_opacity = 0
for(var/obj/machinery/door/firedoor/D in all_doors)
if(!D.blocked)
@@ -153,7 +140,7 @@
return
/area/proc/updateicon()
- if ((fire || eject || party) && (!requires_power||power_environ) && !lighting_space)//If it doesn't require power, can still activate this proc.
+ if ((fire || eject || party) && (!requires_power||power_environ) && !istype(src, /area/space))//If it doesn't require power, can still activate this proc.
if(fire && !eject && !party)
icon_state = "blue"
/*else if(atmosalm && !fire && !eject && !party)
@@ -177,56 +164,53 @@
/area/proc/powered(var/chan) // return true if the area has power to given channel
- if(!master.requires_power)
+ if(!requires_power)
return 1
- if(master.always_unpowered)
+ if(always_unpowered)
return 0
- if(src.lighting_space)
- return 0 // Nope sorry
switch(chan)
if(EQUIP)
- return master.power_equip
+ return power_equip
if(LIGHT)
- return master.power_light
+ return power_light
if(ENVIRON)
- return master.power_environ
+ return power_environ
return 0
// called when power status changes
/area/proc/power_change()
- for(var/area/RA in related)
- for(var/obj/machinery/M in RA) // for each machine in the area
- M.power_change() // reverify power status (to update icons etc.)
- if (fire || eject || party)
- RA.updateicon()
+ for(var/obj/machinery/M in src) // for each machine in the area
+ M.power_change() // reverify power status (to update icons etc.)
+ if (fire || eject || party)
+ updateicon()
/area/proc/usage(var/chan)
var/used = 0
switch(chan)
if(LIGHT)
- used += master.used_light
+ used += used_light
if(EQUIP)
- used += master.used_equip
+ used += used_equip
if(ENVIRON)
- used += master.used_environ
+ used += used_environ
if(TOTAL)
- used += master.used_light + master.used_equip + master.used_environ
+ used += used_light + used_equip + used_environ
return used
/area/proc/clear_usage()
- master.used_equip = 0
- master.used_light = 0
- master.used_environ = 0
+ used_equip = 0
+ used_light = 0
+ used_environ = 0
/area/proc/use_power(var/amount, var/chan)
switch(chan)
if(EQUIP)
- master.used_equip += amount
+ used_equip += amount
if(LIGHT)
- master.used_light += amount
+ used_light += amount
if(ENVIRON)
- master.used_environ += amount
+ used_environ += amount
var/list/mob/living/forced_ambiance_list = new
@@ -262,37 +246,35 @@ var/list/mob/living/forced_ambiance_list = new
L << sound('sound/ambience/shipambience.ogg', repeat = 1, wait = 0, volume = 35, channel = 2)
if(forced_ambience)
- forced_ambiance_list += L
- L << forced_ambience
+ if(forced_ambience.len)
+ forced_ambiance_list |= L
+ L << sound(pick(forced_ambience), repeat = 1, wait = 0, volume = 25, channel = 1)
+ else
+ L << sound(null, channel = 1)
else if(src.ambience.len && prob(35))
if((world.time >= L.client.played + 600))
- var/musVolume = 25
var/sound = pick(ambience)
- L << sound(sound, repeat = 0, wait = 0, volume = musVolume, channel = 1)
+ L << sound(sound, repeat = 0, wait = 0, volume = 25, channel = 1)
L.client.played = world.time
/area/proc/gravitychange(var/gravitystate = 0, var/area/A)
-
A.has_gravity = gravitystate
- for(var/area/SubA in A.related)
- SubA.has_gravity = gravitystate
-
- if(gravitystate)
- for(var/mob/living/carbon/human/M in SubA)
- thunk(M)
- for(var/mob/M1 in SubA)
- M1.make_floating(0)
- else
- for(var/mob/M in SubA)
- if(M.Check_Dense_Object() && istype(src,/mob/living/carbon/human/))
- var/mob/living/carbon/human/H = src
- if(istype(H.shoes, /obj/item/clothing/shoes/magboots) && (H.shoes.flags & NOSLIP)) //magboots + dense_object = no floaty effect
- H.make_floating(0)
- else
- H.make_floating(1)
+ if(gravitystate)
+ for(var/mob/living/carbon/human/M in A)
+ thunk(M)
+ for(var/mob/M1 in A)
+ M1.make_floating(0)
+ else
+ for(var/mob/M in A)
+ if(M.Check_Dense_Object() && istype(src,/mob/living/carbon/human/))
+ var/mob/living/carbon/human/H = src
+ if(istype(H.shoes, /obj/item/clothing/shoes/magboots) && (H.shoes.flags & NOSLIP)) //magboots + dense_object = no floaty effect
+ H.make_floating(0)
else
- M.make_floating(1)
+ H.make_floating(1)
+ else
+ M.make_floating(1)
/area/proc/thunk(mob)
if(istype(get_turf(mob), /turf/space)) // Can't fall onto nothing.
diff --git a/code/game/area/asteroid_areas.dm b/code/game/area/asteroid_areas.dm
index edfb99f57f6..12ae5377ce2 100644
--- a/code/game/area/asteroid_areas.dm
+++ b/code/game/area/asteroid_areas.dm
@@ -3,6 +3,7 @@
/area/mine
icon_state = "mining"
music = 'sound/ambience/song_game.ogg'
+ sound_env = 5 //stoneroom
/area/mine/explored
name = "Mine"
diff --git a/code/game/asteroid.dm b/code/game/asteroid.dm
index e5b421e9afd..8aa6b1cd64e 100644
--- a/code/game/asteroid.dm
+++ b/code/game/asteroid.dm
@@ -32,7 +32,7 @@ proc/spawn_room(var/atom/start_loc,var/x_size,var/y_size,var/wall,var/floor , va
var/cur_loc = locate(start_loc.x+x,start_loc.y+y,start_loc.z)
if(clean)
for(var/O in cur_loc)
- del(O)
+ qdel(O)
var/area/asteroid/artifactroom/A = new
if(name)
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index 960a75d4fb5..742c6389a95 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -11,6 +11,7 @@
var/pass_flags = 0
var/throwpass = 0
var/germ_level = GERM_LEVEL_AMBIENT // The higher the germ level, the more germ on the atom.
+ var/simulated = 1 //filter for actions - used by lighting overlays
///Chemistry.
var/datum/reagents/reagents = null
@@ -22,6 +23,18 @@
//Detective Work, used for the duplicate data points kept in the scanners
var/list/original_atom
+/atom/Destroy()
+ . = ..()
+ density = 0
+ set_opacity(0)
+
+ if(reagents)
+ qdel(reagents)
+ reagents = null
+ for(var/atom/movable/AM in contents)
+ qdel(AM)
+ invisibility = 101
+
/atom/proc/assume_air(datum/gas_mixture/giver)
return null
@@ -66,7 +79,6 @@
return flags & INSERT_CONTAINER
*/
-
/atom/proc/meteorhit(obj/meteor as obj)
return
@@ -148,7 +160,7 @@ its easier to just keep the beam vertical.
for(var/obj/effect/overlay/beam/O in orange(10,src)) //This section erases the previously drawn beam because I found it was easier to
if(O.BeamSource==src) //just draw another instance of the beam instead of trying to manipulate all the
- del O //pieces to a new orientation.
+ qdel(O) //pieces to a new orientation.
var/Angle=round(Get_Angle(src,BeamTarget))
var/icon/I=new(icon,icon_state)
I.Turn(Angle)
@@ -189,7 +201,7 @@ its easier to just keep the beam vertical.
X.pixel_y=Pixel_y
sleep(3) //Changing this to a lower value will cause the beam to follow more smoothly with movement, but it will also be more laggy.
//I've found that 3 ticks provided a nice balance for my use.
- for(var/obj/effect/overlay/beam/O in orange(10,src)) if(O.BeamSource==src) del O
+ for(var/obj/effect/overlay/beam/O in orange(10,src)) if(O.BeamSource==src) qdel(O)
//All atoms
@@ -230,6 +242,9 @@ its easier to just keep the beam vertical.
/atom/proc/fire_act()
return
+/atom/proc/melt()
+ return
+
/atom/proc/hitby(atom/movable/AM as mob|obj)
if (density)
AM.throwing = 0
@@ -359,7 +374,7 @@ its easier to just keep the beam vertical.
//Cleaning up shit.
if(fingerprints && !fingerprints.len)
- del(fingerprints)
+ qdel(fingerprints)
return
@@ -416,7 +431,7 @@ its easier to just keep the beam vertical.
src.color = initial(src.color) //paint
src.germ_level = 0
if(istype(blood_DNA, /list))
- del(blood_DNA)
+ qdel(blood_DNA)
return 1
diff --git a/code/game/atoms_movable.dm b/code/game/atoms_movable.dm
index 79d6e8fd08d..f86c135da40 100644
--- a/code/game/atoms_movable.dm
+++ b/code/game/atoms_movable.dm
@@ -14,6 +14,29 @@
var/moved_recently = 0
var/mob/pulledby = null
+/atom/movable/New()
+ ..()
+ if(ticker && ticker.current_state == GAME_STATE_PLAYING)
+ initialize()
+
+/atom/movable/Del()
+ if(isnull(gcDestroyed) && loc)
+ testing("GC: -- [type] was deleted via del() rather than qdel() --")
+ CRASH() // Debug until I can get a clean server start.
+// else if(isnull(gcDestroyed))
+// testing("GC: [type] was deleted via GC without qdel()") //Not really a huge issue but from now on, please qdel()
+// else
+// testing("GC: [type] was deleted via GC with qdel()")
+ ..()
+
+/atom/movable/Destroy()
+ . = ..()
+
+ loc = null
+
+/atom/movable/proc/initialize()
+ return
+
/atom/movable/Bump(var/atom/A, yes)
if(src.throwing)
src.throw_impact(A)
@@ -187,4 +210,4 @@
/atom/movable/overlay/attack_hand(a, b, c)
if (src.master)
return src.master.attack_hand(a, b, c)
- return
\ No newline at end of file
+ return
diff --git a/code/game/dna/dna2_helpers.dm b/code/game/dna/dna2_helpers.dm
index 9bfdf9f0b65..ce6320cd88c 100644
--- a/code/game/dna/dna2_helpers.dm
+++ b/code/game/dna/dna2_helpers.dm
@@ -165,7 +165,8 @@
if((0 < beard) && (beard <= facial_hair_styles_list.len))
H.f_style = facial_hair_styles_list[beard]
- H.update_body(0)
+ H.force_update_limbs()
+ H.update_eyes()
H.update_hair()
return 1
diff --git a/code/game/dna/dna_misc.dm b/code/game/dna/dna_misc.dm
index 1362aa68882..cdc737c0076 100644
--- a/code/game/dna/dna_misc.dm
+++ b/code/game/dna/dna_misc.dm
@@ -235,9 +235,9 @@
H.r_eyes = hex2num(getblock(structure,8,3))
H.g_eyes = hex2num(getblock(structure,9,3))
H.b_eyes = hex2num(getblock(structure,10,3))
+
if(H.internal_organs_by_name["eyes"])
- var/obj/item/organ/eyes/eyes = H.internal_organs_by_name["eyes"]
- eyes.eye_colour = list(H.r_eyes,H.g_eyes,H.b_eyes)
+ H.update_eyes()
if (isblockon(getblock(structure, 11,3),11 , 1))
H.gender = FEMALE
@@ -420,7 +420,7 @@
animation.master = src
flick("h2monkey", animation)
sleep(48)
- del(animation)
+ qdel(animation)
var/mob/living/carbon/monkey/O = null
@@ -447,7 +447,7 @@
for(var/obj/T in (M.contents-implants))
- del(T)
+ qdel(T)
O.loc = M.loc
@@ -469,7 +469,7 @@
I.loc = O
I.implanted = O
// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
+ qdel(M)
return
if (!isblockon(getblock(M.dna.struc_enzymes, MONKEYBLOCK,3),MONKEYBLOCK) && !istype(M, /mob/living/carbon/human))
@@ -493,7 +493,7 @@
animation.master = src
flick("monkey2h", animation)
sleep(48)
- del(animation)
+ qdel(animation)
var/mob/living/carbon/human/O = new( src )
if(Mo.greaterform)
@@ -519,7 +519,7 @@
M.viruses -= D
//for(var/obj/T in M)
- // del(T)
+ // qdel(T)
O.loc = M.loc
@@ -553,7 +553,7 @@
I.loc = O
I.implanted = O
// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
+ qdel(M)
return
//////////////////////////////////////////////////////////// Monkey Block
if(M)
diff --git a/code/game/dna/dna_misc.dm.orig b/code/game/dna/dna_misc.dm.orig
deleted file mode 100644
index 00810f50e16..00000000000
--- a/code/game/dna/dna_misc.dm.orig
+++ /dev/null
@@ -1,1123 +0,0 @@
-<<<<<<< HEAD
-/////////////////////////// DNA HELPER-PROCS
-/proc/getleftblocks(input,blocknumber,blocksize)
- var/string
-
- if (blocknumber > 1)
- string = copytext(input,1,((blocksize*blocknumber)-(blocksize-1)))
- return string
- else
- return null
-
-/proc/getrightblocks(input,blocknumber,blocksize)
- var/string
- if (blocknumber < (length(input)/blocksize))
- string = copytext(input,blocksize*blocknumber+1,length(input)+1)
- return string
- else
- return null
-
-/proc/getblockstring(input,block,subblock,blocksize,src,ui) // src is probably used here just for urls; ui is 1 when requesting for the unique identifier screen, 0 for structural enzymes screen
- var/string
- var/subpos = 1 // keeps track of the current sub block
- var/blockpos = 1 // keeps track of the current block
-
-
- for(var/i = 1, i <= length(input), i++) // loop through each letter
-
- var/pushstring
-
- if(subpos == subblock && blockpos == block) // if the current block/subblock is selected, mark it
- pushstring = "[copytext(input, i, i+1)]"
- else
- if(ui) //This is for allowing block clicks to be differentiated
- pushstring = "[copytext(input, i, i+1)]"
- else
- pushstring = "[copytext(input, i, i+1)]"
-
- string += pushstring // push the string to the return string
-
- if(subpos >= blocksize) // add a line break for every block
- string += " | "
- subpos = 0
- blockpos++
-
- subpos++
-
- return string
-
-
-/proc/getblock(input,blocknumber,blocksize)
- var/result
- result = copytext(input ,(blocksize*blocknumber)-(blocksize-1),(blocksize*blocknumber)+1)
- return result
-
-/proc/getblockbuffer(input,blocknumber,blocksize)
- var/result[3]
- var/block = copytext(input ,(blocksize*blocknumber)-(blocksize-1),(blocksize*blocknumber)+1)
- for(var/i = 1, i <= 3, i++)
- result[i] = copytext(block, i, i+1)
- return result
-
-/proc/setblock(istring, blocknumber, replacement, blocksize)
- if(!blocknumber)
- return istring
- if(!istring || !replacement || !blocksize) return 0
- var/result = getleftblocks(istring, blocknumber, blocksize) + replacement + getrightblocks(istring, blocknumber, blocksize)
- return result
-
-/proc/add_zero2(t, u)
- var/temp1
- while (length(t) < u)
- t = "0[t]"
- temp1 = t
- if (length(t) > u)
- temp1 = copytext(t,2,u+1)
- return temp1
-
-/proc/miniscramble(input,rs,rd)
- var/output
- output = null
- if (input == "C" || input == "D" || input == "E" || input == "F")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"6",prob((rs*10));"7",prob((rs*5)+(rd));"0",prob((rs*5)+(rd));"1",prob((rs*10)-(rd));"2",prob((rs*10)-(rd));"3")
- if (input == "8" || input == "9" || input == "A" || input == "B")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"A",prob((rs*10));"B",prob((rs*5)+(rd));"C",prob((rs*5)+(rd));"D",prob((rs*5)+(rd));"2",prob((rs*5)+(rd));"3")
- if (input == "4" || input == "5" || input == "6" || input == "7")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"A",prob((rs*10));"B",prob((rs*5)+(rd));"C",prob((rs*5)+(rd));"D",prob((rs*5)+(rd));"2",prob((rs*5)+(rd));"3")
- if (input == "0" || input == "1" || input == "2" || input == "3")
- output = pick(prob((rs*10));"8",prob((rs*10));"9",prob((rs*10));"A",prob((rs*10));"B",prob((rs*10)-(rd));"C",prob((rs*10)-(rd));"D",prob((rs*5)+(rd));"E",prob((rs*5)+(rd));"F")
- if (!output) output = "5"
- return output
-
-//Instead of picking a value far from the input, this will pick values closer to it.
-//Sorry for the block of code, but it's more efficient then calling text2hex -> loop -> hex2text
-/proc/miniscrambletarget(input,rs,rd)
- var/output = null
- switch(input)
- if("0")
- output = pick(prob((rs*10)+(rd));"0",prob((rs*10)+(rd));"1",prob((rs*10));"2",prob((rs*10)-(rd));"3")
- if("1")
- output = pick(prob((rs*10)+(rd));"0",prob((rs*10)+(rd));"1",prob((rs*10)+(rd));"2",prob((rs*10));"3",prob((rs*10)-(rd));"4")
- if("2")
- output = pick(prob((rs*10));"0",prob((rs*10)+(rd));"1",prob((rs*10)+(rd));"2",prob((rs*10)+(rd));"3",prob((rs*10));"4",prob((rs*10)-(rd));"5")
- if("3")
- output = pick(prob((rs*10)-(rd));"0",prob((rs*10));"1",prob((rs*10)+(rd));"2",prob((rs*10)+(rd));"3",prob((rs*10)+(rd));"4",prob((rs*10));"5",prob((rs*10)-(rd));"6")
- if("4")
- output = pick(prob((rs*10)-(rd));"1",prob((rs*10));"2",prob((rs*10)+(rd));"3",prob((rs*10)+(rd));"4",prob((rs*10)+(rd));"5",prob((rs*10));"6",prob((rs*10)-(rd));"7")
- if("5")
- output = pick(prob((rs*10)-(rd));"2",prob((rs*10));"3",prob((rs*10)+(rd));"4",prob((rs*10)+(rd));"5",prob((rs*10)+(rd));"6",prob((rs*10));"7",prob((rs*10)-(rd));"8")
- if("6")
- output = pick(prob((rs*10)-(rd));"3",prob((rs*10));"4",prob((rs*10)+(rd));"5",prob((rs*10)+(rd));"6",prob((rs*10)+(rd));"7",prob((rs*10));"8",prob((rs*10)-(rd));"9")
- if("7")
- output = pick(prob((rs*10)-(rd));"4",prob((rs*10));"5",prob((rs*10)+(rd));"6",prob((rs*10)+(rd));"7",prob((rs*10)+(rd));"8",prob((rs*10));"9",prob((rs*10)-(rd));"A")
- if("8")
- output = pick(prob((rs*10)-(rd));"5",prob((rs*10));"6",prob((rs*10)+(rd));"7",prob((rs*10)+(rd));"8",prob((rs*10)+(rd));"9",prob((rs*10));"A",prob((rs*10)-(rd));"B")
- if("9")
- output = pick(prob((rs*10)-(rd));"6",prob((rs*10));"7",prob((rs*10)+(rd));"8",prob((rs*10)+(rd));"9",prob((rs*10)+(rd));"A",prob((rs*10));"B",prob((rs*10)-(rd));"C")
- if("10")//A
- output = pick(prob((rs*10)-(rd));"7",prob((rs*10));"8",prob((rs*10)+(rd));"9",prob((rs*10)+(rd));"A",prob((rs*10)+(rd));"B",prob((rs*10));"C",prob((rs*10)-(rd));"D")
- if("11")//B
- output = pick(prob((rs*10)-(rd));"8",prob((rs*10));"9",prob((rs*10)+(rd));"A",prob((rs*10)+(rd));"B",prob((rs*10)+(rd));"C",prob((rs*10));"D",prob((rs*10)-(rd));"E")
- if("12")//C
- output = pick(prob((rs*10)-(rd));"9",prob((rs*10));"A",prob((rs*10)+(rd));"B",prob((rs*10)+(rd));"C",prob((rs*10)+(rd));"D",prob((rs*10));"E",prob((rs*10)-(rd));"F")
- if("13")//D
- output = pick(prob((rs*10)-(rd));"A",prob((rs*10));"B",prob((rs*10)+(rd));"C",prob((rs*10)+(rd));"D",prob((rs*10)+(rd));"E",prob((rs*10));"F")
- if("14")//E
- output = pick(prob((rs*10)-(rd));"B",prob((rs*10));"C",prob((rs*10)+(rd));"D",prob((rs*10)+(rd));"E",prob((rs*10)+(rd));"F")
- if("15")//F
- output = pick(prob((rs*10)-(rd));"C",prob((rs*10));"D",prob((rs*10)+(rd));"E",prob((rs*10)+(rd));"F")
-
- if(!input || !output) //How did this happen?
- output = "8"
-
- return output
-
-/proc/isblockon(hnumber, bnumber , var/UI = 0)
-
- var/temp2
- temp2 = hex2num(hnumber)
-
- if(UI)
- if(temp2 >= 2050)
- return 1
- else
- return 0
-
- if (bnumber == HULKBLOCK || bnumber == TELEBLOCK || bnumber == NOBREATHBLOCK || bnumber == NOPRINTSBLOCK || bnumber == SMALLSIZEBLOCK || bnumber == SHOCKIMMUNITYBLOCK)
- if (temp2 >= 3500 + BLOCKADD)
- return 1
- else
- return 0
- if (bnumber == XRAYBLOCK || bnumber == FIREBLOCK || bnumber == REMOTEVIEWBLOCK || bnumber == REGENERATEBLOCK || bnumber == INCREASERUNBLOCK || bnumber == REMOTETALKBLOCK || bnumber == MORPHBLOCK)
- if (temp2 >= 3050 + BLOCKADD)
- return 1
- else
- return 0
-
-
- if (temp2 >= 2050 + BLOCKADD)
- return 1
- else
- return 0
-
-/proc/ismuton(var/block,var/mob/M)
- return isblockon(getblock(M.dna.struc_enzymes, block,3),block)
-
-/proc/randmutb(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = pick(GLASSESBLOCK,COUGHBLOCK,FAKEBLOCK,NERVOUSBLOCK,CLUMSYBLOCK,TWITCHBLOCK,HEADACHEBLOCK,BLINDBLOCK,DEAFBLOCK,HALLUCINATIONBLOCK)
- M.dna.check_integrity()
- newdna = setblock(M.dna.struc_enzymes,num,toggledblock(getblock(M.dna.struc_enzymes,num,3)),3)
- M.dna.struc_enzymes = newdna
- return
-
-/proc/randmutg(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = pick(HULKBLOCK,XRAYBLOCK,FIREBLOCK,TELEBLOCK,NOBREATHBLOCK,REMOTEVIEWBLOCK,REGENERATEBLOCK,INCREASERUNBLOCK,REMOTETALKBLOCK,MORPHBLOCK,BLENDBLOCK,NOPRINTSBLOCK,SHOCKIMMUNITYBLOCK,SMALLSIZEBLOCK)
- M.dna.check_integrity()
- newdna = setblock(M.dna.struc_enzymes,num,toggledblock(getblock(M.dna.struc_enzymes,num,3)),3)
- M.dna.struc_enzymes = newdna
- return
-
-/proc/scramble(var/type, mob/M as mob, var/p)
- if(!M) return
- M.dna.check_integrity()
- if(type)
- for(var/i = 1, i <= STRUCDNASIZE-1, i++)
- if(prob(p))
- M.dna.uni_identity = setblock(M.dna.uni_identity, i, add_zero2(num2hex(rand(1,4095), 1), 3), 3)
- updateappearance(M, M.dna.uni_identity)
-
- else
- for(var/i = 1, i <= STRUCDNASIZE-1, i++)
- if(prob(p))
- M.dna.struc_enzymes = setblock(M.dna.struc_enzymes, i, add_zero2(num2hex(rand(1,4095), 1), 3), 3)
- domutcheck(M, null)
- return
-
-/proc/randmuti(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = rand(1,UNIDNASIZE)
- M.dna.check_integrity()
- newdna = setblock(M.dna.uni_identity,num,add_zero2(num2hex(rand(1,4095),1),3),3)
- M.dna.uni_identity = newdna
- return
-
-/proc/toggledblock(hnumber) //unused
- var/temp3
- var/chtemp
- temp3 = hex2num(hnumber)
- if (temp3 < 2050)
- chtemp = rand(2050,4095)
- return add_zero2(num2hex(chtemp,1),3)
- else
- chtemp = rand(1,2049)
- return add_zero2(num2hex(chtemp,1),3)
-/////////////////////////// DNA HELPER-PROCS
-
-/////////////////////////// DNA MISC-PROCS
-/proc/updateappearance(mob/M as mob , structure)
- if(istype(M, /mob/living/carbon/human))
- M.dna.check_integrity()
- var/mob/living/carbon/human/H = M
- H.r_hair = hex2num(getblock(structure,1,3))
- H.b_hair = hex2num(getblock(structure,2,3))
- H.g_hair = hex2num(getblock(structure,3,3))
- H.r_facial = hex2num(getblock(structure,4,3))
- H.b_facial = hex2num(getblock(structure,5,3))
- H.g_facial = hex2num(getblock(structure,6,3))
- H.s_tone = round(((hex2num(getblock(structure,7,3)) / 16) - 220))
- H.r_eyes = hex2num(getblock(structure,8,3))
- H.g_eyes = hex2num(getblock(structure,9,3))
- H.b_eyes = hex2num(getblock(structure,10,3))
-
- if (isblockon(getblock(structure, 11,3),11 , 1))
- H.gender = FEMALE
- else
- H.gender = MALE
-
- //Hair
- var/hairnum = hex2num(getblock(structure,13,3))
- var/index = round(1 +(hairnum / 4096)*hair_styles_list.len)
- if((0 < index) && (index <= hair_styles_list.len))
- H.h_style = hair_styles_list[index]
-
- //Facial Hair
- var/beardnum = hex2num(getblock(structure,12,3))
- index = round(1 +(beardnum / 4096)*facial_hair_styles_list.len)
- if((0 < index) && (index <= facial_hair_styles_list.len))
- H.f_style = facial_hair_styles_list[index]
-
- H.update_body(0)
- H.update_hair()
-
- return 1
- else
- return 0
-
-/proc/probinj(var/pr, var/inj)
- return prob(pr+inj*pr)
-
-/proc/domutcheck(mob/living/M as mob, connected, inj)
- if (!M) return
-
- M.dna.check_integrity()
-
- M.disabilities = 0
- M.sdisabilities = 0
- var/old_mutations = M.mutations
- M.mutations = list()
-
-// M.see_in_dark = 2
-// M.see_invisible = 0
-
- if(PLANT in old_mutations)
- M.mutations.Add(PLANT)
- if(SKELETON in old_mutations)
- M.mutations.Add(SKELETON)
- if(FAT in old_mutations)
- M.mutations.Add(FAT)
- if(HUSK in old_mutations)
- M.mutations.Add(HUSK)
-
- if(ismuton(NOBREATHBLOCK,M))
- if(probinj(45,inj) || (mNobreath in old_mutations))
- M << "\blue You feel no need to breathe."
- M.mutations.Add(mNobreath)
- if(ismuton(REMOTEVIEWBLOCK,M))
- if(probinj(45,inj) || (mRemote in old_mutations))
- M << "\blue Your mind expands"
- M.mutations.Add(mRemote)
- if(ismuton(REGENERATEBLOCK,M))
- if(probinj(45,inj) || (mRegen in old_mutations))
- M << "\blue You feel strange"
- M.mutations.Add(mRegen)
- if(ismuton(INCREASERUNBLOCK,M))
- if(probinj(45,inj) || (mRun in old_mutations))
- M << "\blue You feel quick"
- M.mutations.Add(mRun)
- if(ismuton(REMOTETALKBLOCK,M))
- if(probinj(45,inj) || (mRemotetalk in old_mutations))
- M << "\blue You expand your mind outwards"
- M.mutations.Add(mRemotetalk)
- if(ismuton(MORPHBLOCK,M))
- if(probinj(45,inj) || (mMorph in old_mutations))
- M.mutations.Add(mMorph)
- M << "\blue Your skin feels strange"
- if(ismuton(BLENDBLOCK,M))
- if(probinj(45,inj) || (mBlend in old_mutations))
- M.mutations.Add(mBlend)
- M << "\blue You feel alone"
- if(ismuton(HALLUCINATIONBLOCK,M))
- if(probinj(45,inj) || (mHallucination in old_mutations))
- M.mutations.Add(mHallucination)
- M << "\blue Your mind says 'Hello'"
- if(ismuton(NOPRINTSBLOCK,M))
- if(probinj(45,inj) || (mFingerprints in old_mutations))
- M.mutations.Add(mFingerprints)
- M << "\blue Your fingers feel numb"
- if(ismuton(SHOCKIMMUNITYBLOCK,M))
- if(probinj(45,inj) || (mShock in old_mutations))
- M.mutations.Add(mShock)
- M << "\blue You feel strange"
- if(ismuton(SMALLSIZEBLOCK,M))
- if(probinj(45,inj) || (mSmallsize in old_mutations))
- M << "\blue Your skin feels rubbery"
- M.mutations.Add(mSmallsize)
-
-
-
- if (isblockon(getblock(M.dna.struc_enzymes, HULKBLOCK,3),HULKBLOCK))
- if(probinj(5,inj) || (HULK in old_mutations))
- M << "\blue Your muscles hurt."
- M.mutations.Add(HULK)
- if (isblockon(getblock(M.dna.struc_enzymes, HEADACHEBLOCK,3),HEADACHEBLOCK))
- M.disabilities |= EPILEPSY
- M << "\red You get a headache."
- if (isblockon(getblock(M.dna.struc_enzymes, FAKEBLOCK,3),FAKEBLOCK))
- M << "\red You feel strange."
- if (prob(95))
- if(prob(50))
- randmutb(M)
- else
- randmuti(M)
- else
- randmutg(M)
- if (isblockon(getblock(M.dna.struc_enzymes, COUGHBLOCK,3),COUGHBLOCK))
- M.disabilities |= COUGHING
- M << "\red You start coughing."
- if (isblockon(getblock(M.dna.struc_enzymes, CLUMSYBLOCK,3),CLUMSYBLOCK))
- M << "\red You feel lightheaded."
- M.mutations.Add(CLUMSY)
- if (isblockon(getblock(M.dna.struc_enzymes, TWITCHBLOCK,3),TWITCHBLOCK))
- M.disabilities |= TOURETTES
- M << "\red You twitch."
- if (isblockon(getblock(M.dna.struc_enzymes, XRAYBLOCK,3),XRAYBLOCK))
- if(probinj(30,inj) || (XRAY in old_mutations))
- M << "\blue The walls suddenly disappear."
-// M.sight |= (SEE_MOBS|SEE_OBJS|SEE_TURFS)
-// M.see_in_dark = 8
-// M.see_invisible = 2
- M.mutations.Add(XRAY)
- if (isblockon(getblock(M.dna.struc_enzymes, NERVOUSBLOCK,3),NERVOUSBLOCK))
- M.disabilities |= NERVOUS
- M << "\red You feel nervous."
- if (isblockon(getblock(M.dna.struc_enzymes, FIREBLOCK,3),FIREBLOCK))
- if(probinj(30,inj) || (COLD_RESISTANCE in old_mutations))
- M << "\blue Your body feels warm."
- M.mutations.Add(COLD_RESISTANCE)
- if (isblockon(getblock(M.dna.struc_enzymes, BLINDBLOCK,3),BLINDBLOCK))
- M.sdisabilities |= BLIND
- M << "\red You can't seem to see anything."
- if (isblockon(getblock(M.dna.struc_enzymes, TELEBLOCK,3),TELEBLOCK))
- if(probinj(15,inj) || (TK in old_mutations))
- M << "\blue You feel smarter."
- M.mutations.Add(TK)
- if (isblockon(getblock(M.dna.struc_enzymes, DEAFBLOCK,3),DEAFBLOCK))
- M.sdisabilities |= DEAF
- M.ear_deaf = 1
- M << "\red Its kinda quiet.."
- if (isblockon(getblock(M.dna.struc_enzymes, GLASSESBLOCK,3),GLASSESBLOCK))
- M.disabilities |= NEARSIGHTED
- M << "Your eyes feel weird..."
-
- /* If you want the new mutations to work, UNCOMMENT THIS.
- if(istype(M, /mob/living/carbon))
- for (var/datum/mutations/mut in global_mutations)
- mut.check_mutation(M)
- */
-
-//////////////////////////////////////////////////////////// Monkey Block
- if (isblockon(getblock(M.dna.struc_enzymes, MONKEYBLOCK,3),MONKEYBLOCK) && istype(M, /mob/living/carbon/human))
- // human > monkey
- var/mob/living/carbon/human/H = M
- H.monkeyizing = 1
- var/list/implants = list() //Try to preserve implants.
- for(var/obj/item/weapon/implant/W in H)
- implants += W
- W.loc = null
-
- if(!connected)
- for(var/obj/item/W in (H.contents-implants))
- if (W==H.w_uniform) // will be teared
- continue
- H.drop_from_inventory(W)
- M.monkeyizing = 1
- M.canmove = 0
- M.icon = null
- M.invisibility = 101
- var/atom/movable/overlay/animation = new( M.loc )
- animation.icon_state = "blank"
- animation.icon = 'icons/mob/mob.dmi'
- animation.master = src
- flick("h2monkey", animation)
- sleep(48)
- del(animation)
-
-
- var/mob/living/carbon/monkey/O = null
- if(H.species.primitive)
- O = new H.species.primitive(src)
- else
- H.gib() //Trying to change the species of a creature with no primitive var set is messy.
- return
-
- if(M)
- if (M.dna)
- O.dna = M.dna
- M.dna = null
-
- if (M.suiciding)
- O.suiciding = M.suiciding
- M.suiciding = null
-
-
- for(var/datum/disease/D in M.viruses)
- O.viruses += D
- D.affected_mob = O
- M.viruses -= D
-
-
- for(var/obj/T in (M.contents-implants))
- del(T)
-
- O.loc = M.loc
-
- if(M.mind)
- M.mind.transfer_to(O) //transfer our mind to the cute little monkey
-
- if (connected) //inside dna thing
- var/obj/machinery/dna_scannernew/C = connected
- O.loc = C
- C.occupant = O
- connected = null
- O.real_name = text("monkey ([])",copytext(md5(M.real_name), 2, 6))
- O.take_overall_damage(M.getBruteLoss() + 40, M.getFireLoss())
- O.adjustToxLoss(M.getToxLoss() + 20)
- O.adjustOxyLoss(M.getOxyLoss())
- O.stat = M.stat
- O.a_intent = I_HURT
- for (var/obj/item/weapon/implant/I in implants)
- I.loc = O
- I.implanted = O
-// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
- return
-
- if (!isblockon(getblock(M.dna.struc_enzymes, MONKEYBLOCK,3),MONKEYBLOCK) && !istype(M, /mob/living/carbon/human))
- // monkey > human,
- var/mob/living/carbon/monkey/Mo = M
- Mo.monkeyizing = 1
- var/list/implants = list() //Still preserving implants
- for(var/obj/item/weapon/implant/W in Mo)
- implants += W
- W.loc = null
- if(!connected)
- for(var/obj/item/W in (Mo.contents-implants))
- Mo.drop_from_inventory(W)
- M.monkeyizing = 1
- M.canmove = 0
- M.icon = null
- M.invisibility = 101
- var/atom/movable/overlay/animation = new( M.loc )
- animation.icon_state = "blank"
- animation.icon = 'icons/mob/mob.dmi'
- animation.master = src
- flick("monkey2h", animation)
- sleep(48)
- del(animation)
-
- var/mob/living/carbon/human/O = new( src )
- if(Mo.greaterform)
- O.set_species(Mo.greaterform)
-
- if (isblockon(getblock(M.dna.uni_identity, 11,3),11))
- O.gender = FEMALE
- else
- O.gender = MALE
-
- if (M)
- if (M.dna)
- O.dna = M.dna
- M.dna = null
-
- if (M.suiciding)
- O.suiciding = M.suiciding
- M.suiciding = null
-
- for(var/datum/disease/D in M.viruses)
- O.viruses += D
- D.affected_mob = O
- M.viruses -= D
-
- //for(var/obj/T in M)
- // del(T)
-
- O.loc = M.loc
-
- if(M.mind)
- M.mind.transfer_to(O) //transfer our mind to the human
-
- if (connected) //inside dna thing
- var/obj/machinery/dna_scannernew/C = connected
- O.loc = C
- C.occupant = O
- connected = null
-
- var/i
- while (!i)
- var/randomname
- if (O.gender == MALE)
- randomname = capitalize(pick(first_names_male) + " " + capitalize(pick(last_names)))
- else
- randomname = capitalize(pick(first_names_female) + " " + capitalize(pick(last_names)))
- if (findname(randomname))
- continue
- else
- O.real_name = randomname
- i++
- updateappearance(O,O.dna.uni_identity)
- O.take_overall_damage(M.getBruteLoss(), M.getFireLoss())
- O.adjustToxLoss(M.getToxLoss())
- O.adjustOxyLoss(M.getOxyLoss())
- O.stat = M.stat
- for (var/obj/item/weapon/implant/I in implants)
- I.loc = O
- I.implanted = O
-// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
- return
-//////////////////////////////////////////////////////////// Monkey Block
- if(M)
- M.update_icon = 1 //queue a full icon update at next life() call
- return null
-=======
-/////////////////////////// DNA HELPER-PROCS
-/proc/getleftblocks(input,blocknumber,blocksize)
- var/string
-
- if (blocknumber > 1)
- string = copytext(input,1,((blocksize*blocknumber)-(blocksize-1)))
- return string
- else
- return null
-
-/proc/getrightblocks(input,blocknumber,blocksize)
- var/string
- if (blocknumber < (length(input)/blocksize))
- string = copytext(input,blocksize*blocknumber+1,length(input)+1)
- return string
- else
- return null
-
-/proc/getblockstring(input,block,subblock,blocksize,src,ui) // src is probably used here just for urls; ui is 1 when requesting for the unique identifier screen, 0 for structural enzymes screen
- var/string
- var/subpos = 1 // keeps track of the current sub block
- var/blockpos = 1 // keeps track of the current block
-
-
- for(var/i = 1, i <= length(input), i++) // loop through each letter
-
- var/pushstring
-
- if(subpos == subblock && blockpos == block) // if the current block/subblock is selected, mark it
- pushstring = "[copytext(input, i, i+1)]"
- else
- if(ui) //This is for allowing block clicks to be differentiated
- pushstring = "[copytext(input, i, i+1)]"
- else
- pushstring = "[copytext(input, i, i+1)]"
-
- string += pushstring // push the string to the return string
-
- if(subpos >= blocksize) // add a line break for every block
- string += " | "
- subpos = 0
- blockpos++
-
- subpos++
-
- return string
-
-
-/proc/getblock(input,blocknumber,blocksize)
- var/result
- result = copytext(input ,(blocksize*blocknumber)-(blocksize-1),(blocksize*blocknumber)+1)
- return result
-
-/proc/getblockbuffer(input,blocknumber,blocksize)
- var/result[3]
- var/block = copytext(input ,(blocksize*blocknumber)-(blocksize-1),(blocksize*blocknumber)+1)
- for(var/i = 1, i <= 3, i++)
- result[i] = copytext(block, i, i+1)
- return result
-
-/proc/setblock(istring, blocknumber, replacement, blocksize)
- if(!blocknumber)
- return istring
- if(!istring || !replacement || !blocksize) return 0
- var/result = getleftblocks(istring, blocknumber, blocksize) + replacement + getrightblocks(istring, blocknumber, blocksize)
- return result
-
-/proc/add_zero2(t, u)
- var/temp1
- while (length(t) < u)
- t = "0[t]"
- temp1 = t
- if (length(t) > u)
- temp1 = copytext(t,2,u+1)
- return temp1
-
-/proc/miniscramble(input,rs,rd)
- var/output
- output = null
- if (input == "C" || input == "D" || input == "E" || input == "F")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"6",prob((rs*10));"7",prob((rs*5)+(rd));"0",prob((rs*5)+(rd));"1",prob((rs*10)-(rd));"2",prob((rs*10)-(rd));"3")
- if (input == "8" || input == "9" || input == "A" || input == "B")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"A",prob((rs*10));"B",prob((rs*5)+(rd));"C",prob((rs*5)+(rd));"D",prob((rs*5)+(rd));"2",prob((rs*5)+(rd));"3")
- if (input == "4" || input == "5" || input == "6" || input == "7")
- output = pick(prob((rs*10));"4",prob((rs*10));"5",prob((rs*10));"A",prob((rs*10));"B",prob((rs*5)+(rd));"C",prob((rs*5)+(rd));"D",prob((rs*5)+(rd));"2",prob((rs*5)+(rd));"3")
- if (input == "0" || input == "1" || input == "2" || input == "3")
- output = pick(prob((rs*10));"8",prob((rs*10));"9",prob((rs*10));"A",prob((rs*10));"B",prob((rs*10)-(rd));"C",prob((rs*10)-(rd));"D",prob((rs*5)+(rd));"E",prob((rs*5)+(rd));"F")
- if (!output) output = "5"
- return output
-
-//Instead of picking a value far from the input, this will pick values closer to it.
-//Sorry for the block of code, but it's more efficient then calling text2hex -> loop -> hex2text
-/proc/miniscrambletarget(input,rs,rd)
- var/output = null
- switch(input)
- if("0")
- output = pick(prob((rs*10)+(rd));"0",prob((rs*10)+(rd));"1",prob((rs*10));"2",prob((rs*10)-(rd));"3")
- if("1")
- output = pick(prob((rs*10)+(rd));"0",prob((rs*10)+(rd));"1",prob((rs*10)+(rd));"2",prob((rs*10));"3",prob((rs*10)-(rd));"4")
- if("2")
- output = pick(prob((rs*10));"0",prob((rs*10)+(rd));"1",prob((rs*10)+(rd));"2",prob((rs*10)+(rd));"3",prob((rs*10));"4",prob((rs*10)-(rd));"5")
- if("3")
- output = pick(prob((rs*10)-(rd));"0",prob((rs*10));"1",prob((rs*10)+(rd));"2",prob((rs*10)+(rd));"3",prob((rs*10)+(rd));"4",prob((rs*10));"5",prob((rs*10)-(rd));"6")
- if("4")
- output = pick(prob((rs*10)-(rd));"1",prob((rs*10));"2",prob((rs*10)+(rd));"3",prob((rs*10)+(rd));"4",prob((rs*10)+(rd));"5",prob((rs*10));"6",prob((rs*10)-(rd));"7")
- if("5")
- output = pick(prob((rs*10)-(rd));"2",prob((rs*10));"3",prob((rs*10)+(rd));"4",prob((rs*10)+(rd));"5",prob((rs*10)+(rd));"6",prob((rs*10));"7",prob((rs*10)-(rd));"8")
- if("6")
- output = pick(prob((rs*10)-(rd));"3",prob((rs*10));"4",prob((rs*10)+(rd));"5",prob((rs*10)+(rd));"6",prob((rs*10)+(rd));"7",prob((rs*10));"8",prob((rs*10)-(rd));"9")
- if("7")
- output = pick(prob((rs*10)-(rd));"4",prob((rs*10));"5",prob((rs*10)+(rd));"6",prob((rs*10)+(rd));"7",prob((rs*10)+(rd));"8",prob((rs*10));"9",prob((rs*10)-(rd));"A")
- if("8")
- output = pick(prob((rs*10)-(rd));"5",prob((rs*10));"6",prob((rs*10)+(rd));"7",prob((rs*10)+(rd));"8",prob((rs*10)+(rd));"9",prob((rs*10));"A",prob((rs*10)-(rd));"B")
- if("9")
- output = pick(prob((rs*10)-(rd));"6",prob((rs*10));"7",prob((rs*10)+(rd));"8",prob((rs*10)+(rd));"9",prob((rs*10)+(rd));"A",prob((rs*10));"B",prob((rs*10)-(rd));"C")
- if("10")//A
- output = pick(prob((rs*10)-(rd));"7",prob((rs*10));"8",prob((rs*10)+(rd));"9",prob((rs*10)+(rd));"A",prob((rs*10)+(rd));"B",prob((rs*10));"C",prob((rs*10)-(rd));"D")
- if("11")//B
- output = pick(prob((rs*10)-(rd));"8",prob((rs*10));"9",prob((rs*10)+(rd));"A",prob((rs*10)+(rd));"B",prob((rs*10)+(rd));"C",prob((rs*10));"D",prob((rs*10)-(rd));"E")
- if("12")//C
- output = pick(prob((rs*10)-(rd));"9",prob((rs*10));"A",prob((rs*10)+(rd));"B",prob((rs*10)+(rd));"C",prob((rs*10)+(rd));"D",prob((rs*10));"E",prob((rs*10)-(rd));"F")
- if("13")//D
- output = pick(prob((rs*10)-(rd));"A",prob((rs*10));"B",prob((rs*10)+(rd));"C",prob((rs*10)+(rd));"D",prob((rs*10)+(rd));"E",prob((rs*10));"F")
- if("14")//E
- output = pick(prob((rs*10)-(rd));"B",prob((rs*10));"C",prob((rs*10)+(rd));"D",prob((rs*10)+(rd));"E",prob((rs*10)+(rd));"F")
- if("15")//F
- output = pick(prob((rs*10)-(rd));"C",prob((rs*10));"D",prob((rs*10)+(rd));"E",prob((rs*10)+(rd));"F")
-
- if(!input || !output) //How did this happen?
- output = "8"
-
- return output
-
-/proc/isblockon(hnumber, bnumber , var/UI = 0)
-
- var/temp2
- temp2 = hex2num(hnumber)
-
- if(UI)
- if(temp2 >= 2050)
- return 1
- else
- return 0
-
- if (bnumber == HULKBLOCK || bnumber == TELEBLOCK || bnumber == NOBREATHBLOCK || bnumber == NOPRINTSBLOCK || bnumber == SMALLSIZEBLOCK || bnumber == SHOCKIMMUNITYBLOCK)
- if (temp2 >= 3500 + BLOCKADD)
- return 1
- else
- return 0
- if (bnumber == XRAYBLOCK || bnumber == FIREBLOCK || bnumber == REMOTEVIEWBLOCK || bnumber == REGENERATEBLOCK || bnumber == INCREASERUNBLOCK || bnumber == REMOTETALKBLOCK || bnumber == MORPHBLOCK)
- if (temp2 >= 3050 + BLOCKADD)
- return 1
- else
- return 0
-
-
- if (temp2 >= 2050 + BLOCKADD)
- return 1
- else
- return 0
-
-/proc/ismuton(var/block,var/mob/M)
- return isblockon(getblock(M.dna.struc_enzymes, block,3),block)
-
-/proc/randmutb(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = pick(GLASSESBLOCK,COUGHBLOCK,FAKEBLOCK,NERVOUSBLOCK,CLUMSYBLOCK,TWITCHBLOCK,HEADACHEBLOCK,BLINDBLOCK,DEAFBLOCK,HALLUCINATIONBLOCK)
- M.dna.check_integrity()
- newdna = setblock(M.dna.struc_enzymes,num,toggledblock(getblock(M.dna.struc_enzymes,num,3)),3)
- M.dna.struc_enzymes = newdna
- return
-
-/proc/randmutg(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = pick(HULKBLOCK,XRAYBLOCK,FIREBLOCK,TELEBLOCK,NOBREATHBLOCK,REMOTEVIEWBLOCK,REGENERATEBLOCK,INCREASERUNBLOCK,REMOTETALKBLOCK,MORPHBLOCK,BLENDBLOCK,NOPRINTSBLOCK,SHOCKIMMUNITYBLOCK,SMALLSIZEBLOCK)
- M.dna.check_integrity()
- newdna = setblock(M.dna.struc_enzymes,num,toggledblock(getblock(M.dna.struc_enzymes,num,3)),3)
- M.dna.struc_enzymes = newdna
- return
-
-/proc/scramble(var/type, mob/M as mob, var/p)
- if(!M) return
- M.dna.check_integrity()
- if(type)
- for(var/i = 1, i <= STRUCDNASIZE-1, i++)
- if(prob(p))
- M.dna.uni_identity = setblock(M.dna.uni_identity, i, add_zero2(num2hex(rand(1,4095), 1), 3), 3)
- updateappearance(M, M.dna.uni_identity)
-
- else
- for(var/i = 1, i <= STRUCDNASIZE-1, i++)
- if(prob(p))
- M.dna.struc_enzymes = setblock(M.dna.struc_enzymes, i, add_zero2(num2hex(rand(1,4095), 1), 3), 3)
- domutcheck(M, null)
- return
-
-/proc/randmuti(mob/M as mob)
- if(!M) return
- var/num
- var/newdna
- num = rand(1,UNIDNASIZE)
- M.dna.check_integrity()
- newdna = setblock(M.dna.uni_identity,num,add_zero2(num2hex(rand(1,4095),1),3),3)
- M.dna.uni_identity = newdna
- return
-
-/proc/toggledblock(hnumber) //unused
- var/temp3
- var/chtemp
- temp3 = hex2num(hnumber)
- if (temp3 < 2050)
- chtemp = rand(2050,4095)
- return add_zero2(num2hex(chtemp,1),3)
- else
- chtemp = rand(1,2049)
- return add_zero2(num2hex(chtemp,1),3)
-/////////////////////////// DNA HELPER-PROCS
-
-/////////////////////////// DNA MISC-PROCS
-/proc/updateappearance(mob/M as mob , structure)
- if(istype(M, /mob/living/carbon/human))
- M.dna.check_integrity()
- var/mob/living/carbon/human/H = M
- H.r_hair = hex2num(getblock(structure,1,3))
- H.b_hair = hex2num(getblock(structure,2,3))
- H.g_hair = hex2num(getblock(structure,3,3))
- H.r_facial = hex2num(getblock(structure,4,3))
- H.b_facial = hex2num(getblock(structure,5,3))
- H.g_facial = hex2num(getblock(structure,6,3))
- H.s_tone = round(((hex2num(getblock(structure,7,3)) / 16) - 220))
- H.r_eyes = hex2num(getblock(structure,8,3))
- H.g_eyes = hex2num(getblock(structure,9,3))
- H.b_eyes = hex2num(getblock(structure,10,3))
- if(H.internal_organs_by_name["eyes"])
- var/obj/item/organ/eyes/eyes = H.internal_organs_by_name["eyes"]
- eyes.eye_colour = list(H.r_eyes,H.g_eyes,H.b_eyes)
-
- if (isblockon(getblock(structure, 11,3),11 , 1))
- H.gender = FEMALE
- else
- H.gender = MALE
-
- //Hair
- var/hairnum = hex2num(getblock(structure,13,3))
- var/index = round(1 +(hairnum / 4096)*hair_styles_list.len)
- if((0 < index) && (index <= hair_styles_list.len))
- H.h_style = hair_styles_list[index]
-
- //Facial Hair
- var/beardnum = hex2num(getblock(structure,12,3))
- index = round(1 +(beardnum / 4096)*facial_hair_styles_list.len)
- if((0 < index) && (index <= facial_hair_styles_list.len))
- H.f_style = facial_hair_styles_list[index]
-
- H.update_body(0)
- H.update_hair()
-
- return 1
- else
- return 0
-
-/proc/probinj(var/pr, var/inj)
- return prob(pr+inj*pr)
-
-/proc/domutcheck(mob/living/M as mob, connected, inj)
- if (!M) return
-
- M.dna.check_integrity()
-
- M.disabilities = 0
- M.sdisabilities = 0
- var/old_mutations = M.mutations
- M.mutations = list()
-
-// M.see_in_dark = 2
-// M.see_invisible = 0
-
- if(PLANT in old_mutations)
- M.mutations.Add(PLANT)
- if(SKELETON in old_mutations)
- M.mutations.Add(SKELETON)
- if(FAT in old_mutations)
- M.mutations.Add(FAT)
- if(HUSK in old_mutations)
- M.mutations.Add(HUSK)
-
- if(ismuton(NOBREATHBLOCK,M))
- if(probinj(45,inj) || (mNobreath in old_mutations))
- M << "\blue You feel no need to breathe."
- M.mutations.Add(mNobreath)
- if(ismuton(REMOTEVIEWBLOCK,M))
- if(probinj(45,inj) || (mRemote in old_mutations))
- M << "\blue Your mind expands"
- M.mutations.Add(mRemote)
- if(ismuton(REGENERATEBLOCK,M))
- if(probinj(45,inj) || (mRegen in old_mutations))
- M << "\blue You feel strange"
- M.mutations.Add(mRegen)
- if(ismuton(INCREASERUNBLOCK,M))
- if(probinj(45,inj) || (mRun in old_mutations))
- M << "\blue You feel quick"
- M.mutations.Add(mRun)
- if(ismuton(REMOTETALKBLOCK,M))
- if(probinj(45,inj) || (mRemotetalk in old_mutations))
- M << "\blue You expand your mind outwards"
- M.mutations.Add(mRemotetalk)
- if(ismuton(MORPHBLOCK,M))
- if(probinj(45,inj) || (mMorph in old_mutations))
- M.mutations.Add(mMorph)
- M << "\blue Your skin feels strange"
- if(ismuton(BLENDBLOCK,M))
- if(probinj(45,inj) || (mBlend in old_mutations))
- M.mutations.Add(mBlend)
- M << "\blue You feel alone"
- if(ismuton(HALLUCINATIONBLOCK,M))
- if(probinj(45,inj) || (mHallucination in old_mutations))
- M.mutations.Add(mHallucination)
- M << "\blue Your mind says 'Hello'"
- if(ismuton(NOPRINTSBLOCK,M))
- if(probinj(45,inj) || (mFingerprints in old_mutations))
- M.mutations.Add(mFingerprints)
- M << "\blue Your fingers feel numb"
- if(ismuton(SHOCKIMMUNITYBLOCK,M))
- if(probinj(45,inj) || (mShock in old_mutations))
- M.mutations.Add(mShock)
- M << "\blue You feel strange"
- if(ismuton(SMALLSIZEBLOCK,M))
- if(probinj(45,inj) || (mSmallsize in old_mutations))
- M << "\blue Your skin feels rubbery"
- M.mutations.Add(mSmallsize)
-
-
-
- if (isblockon(getblock(M.dna.struc_enzymes, HULKBLOCK,3),HULKBLOCK))
- if(probinj(5,inj) || (HULK in old_mutations))
- M << "\blue Your muscles hurt."
- M.mutations.Add(HULK)
- if (isblockon(getblock(M.dna.struc_enzymes, HEADACHEBLOCK,3),HEADACHEBLOCK))
- M.disabilities |= EPILEPSY
- M << "\red You get a headache."
- if (isblockon(getblock(M.dna.struc_enzymes, FAKEBLOCK,3),FAKEBLOCK))
- M << "\red You feel strange."
- if (prob(95))
- if(prob(50))
- randmutb(M)
- else
- randmuti(M)
- else
- randmutg(M)
- if (isblockon(getblock(M.dna.struc_enzymes, COUGHBLOCK,3),COUGHBLOCK))
- M.disabilities |= COUGHING
- M << "\red You start coughing."
- if (isblockon(getblock(M.dna.struc_enzymes, CLUMSYBLOCK,3),CLUMSYBLOCK))
- M << "\red You feel lightheaded."
- M.mutations.Add(CLUMSY)
- if (isblockon(getblock(M.dna.struc_enzymes, TWITCHBLOCK,3),TWITCHBLOCK))
- M.disabilities |= TOURETTES
- M << "\red You twitch."
- if (isblockon(getblock(M.dna.struc_enzymes, XRAYBLOCK,3),XRAYBLOCK))
- if(probinj(30,inj) || (XRAY in old_mutations))
- M << "\blue The walls suddenly disappear."
-// M.sight |= (SEE_MOBS|SEE_OBJS|SEE_TURFS)
-// M.see_in_dark = 8
-// M.see_invisible = 2
- M.mutations.Add(XRAY)
- if (isblockon(getblock(M.dna.struc_enzymes, NERVOUSBLOCK,3),NERVOUSBLOCK))
- M.disabilities |= NERVOUS
- M << "\red You feel nervous."
- if (isblockon(getblock(M.dna.struc_enzymes, FIREBLOCK,3),FIREBLOCK))
- if(probinj(30,inj) || (COLD_RESISTANCE in old_mutations))
- M << "\blue Your body feels warm."
- M.mutations.Add(COLD_RESISTANCE)
- if (isblockon(getblock(M.dna.struc_enzymes, BLINDBLOCK,3),BLINDBLOCK))
- M.sdisabilities |= BLIND
- M << "\red You can't seem to see anything."
- if (isblockon(getblock(M.dna.struc_enzymes, TELEBLOCK,3),TELEBLOCK))
- if(probinj(15,inj) || (TK in old_mutations))
- M << "\blue You feel smarter."
- M.mutations.Add(TK)
- if (isblockon(getblock(M.dna.struc_enzymes, DEAFBLOCK,3),DEAFBLOCK))
- M.sdisabilities |= DEAF
- M.ear_deaf = 1
- M << "\red Its kinda quiet.."
- if (isblockon(getblock(M.dna.struc_enzymes, GLASSESBLOCK,3),GLASSESBLOCK))
- M.disabilities |= NEARSIGHTED
- M << "Your eyes feel weird..."
-
- /* If you want the new mutations to work, UNCOMMENT THIS.
- if(istype(M, /mob/living/carbon))
- for (var/datum/mutations/mut in global_mutations)
- mut.check_mutation(M)
- */
-
-//////////////////////////////////////////////////////////// Monkey Block
- if (isblockon(getblock(M.dna.struc_enzymes, MONKEYBLOCK,3),MONKEYBLOCK) && istype(M, /mob/living/carbon/human))
- // human > monkey
- var/mob/living/carbon/human/H = M
- H.monkeyizing = 1
- var/list/implants = list() //Try to preserve implants.
- for(var/obj/item/weapon/implant/W in H)
- implants += W
- W.loc = null
-
- if(!connected)
- for(var/obj/item/W in (H.contents-implants))
- if (W==H.w_uniform) // will be teared
- continue
- H.drop_from_inventory(W)
- M.monkeyizing = 1
- M.canmove = 0
- M.icon = null
- M.invisibility = 101
- var/atom/movable/overlay/animation = new( M.loc )
- animation.icon_state = "blank"
- animation.icon = 'icons/mob/mob.dmi'
- animation.master = src
- flick("h2monkey", animation)
- sleep(48)
- del(animation)
-
-
- var/mob/living/carbon/monkey/O = null
- if(H.species.primitive)
- O = new H.species.primitive(src)
- else
- H.gib() //Trying to change the species of a creature with no primitive var set is messy.
- return
-
- if(M)
- if (M.dna)
- O.dna = M.dna
- M.dna = null
-
- if (M.suiciding)
- O.suiciding = M.suiciding
- M.suiciding = null
-
-
- for(var/datum/disease/D in M.viruses)
- O.viruses += D
- D.affected_mob = O
- M.viruses -= D
-
-
- for(var/obj/T in (M.contents-implants))
- del(T)
-
- O.loc = M.loc
-
- if(M.mind)
- M.mind.transfer_to(O) //transfer our mind to the cute little monkey
-
- if (connected) //inside dna thing
- var/obj/machinery/dna_scannernew/C = connected
- O.loc = C
- C.occupant = O
- connected = null
- O.real_name = text("monkey ([])",copytext(md5(M.real_name), 2, 6))
- O.take_overall_damage(M.getBruteLoss() + 40, M.getFireLoss())
- O.adjustToxLoss(M.getToxLoss() + 20)
- O.adjustOxyLoss(M.getOxyLoss())
- O.stat = M.stat
- O.a_intent = "hurt"
- for (var/obj/item/weapon/implant/I in implants)
- I.loc = O
- I.implanted = O
-// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
- return
-
- if (!isblockon(getblock(M.dna.struc_enzymes, MONKEYBLOCK,3),MONKEYBLOCK) && !istype(M, /mob/living/carbon/human))
- // monkey > human,
- var/mob/living/carbon/monkey/Mo = M
- Mo.monkeyizing = 1
- var/list/implants = list() //Still preserving implants
- for(var/obj/item/weapon/implant/W in Mo)
- implants += W
- W.loc = null
- if(!connected)
- for(var/obj/item/W in (Mo.contents-implants))
- Mo.drop_from_inventory(W)
- M.monkeyizing = 1
- M.canmove = 0
- M.icon = null
- M.invisibility = 101
- var/atom/movable/overlay/animation = new( M.loc )
- animation.icon_state = "blank"
- animation.icon = 'icons/mob/mob.dmi'
- animation.master = src
- flick("monkey2h", animation)
- sleep(48)
- del(animation)
-
- var/mob/living/carbon/human/O = new( src )
- if(Mo.greaterform)
- O.set_species(Mo.greaterform)
-
- if (isblockon(getblock(M.dna.uni_identity, 11,3),11))
- O.gender = FEMALE
- else
- O.gender = MALE
-
- if (M)
- if (M.dna)
- O.dna = M.dna
- M.dna = null
-
- if (M.suiciding)
- O.suiciding = M.suiciding
- M.suiciding = null
-
- for(var/datum/disease/D in M.viruses)
- O.viruses += D
- D.affected_mob = O
- M.viruses -= D
-
- //for(var/obj/T in M)
- // del(T)
-
- O.loc = M.loc
-
- if(M.mind)
- M.mind.transfer_to(O) //transfer our mind to the human
-
- if (connected) //inside dna thing
- var/obj/machinery/dna_scannernew/C = connected
- O.loc = C
- C.occupant = O
- connected = null
-
- var/i
- while (!i)
- var/randomname
- if (O.gender == MALE)
- randomname = capitalize(pick(first_names_male) + " " + capitalize(pick(last_names)))
- else
- randomname = capitalize(pick(first_names_female) + " " + capitalize(pick(last_names)))
- if (findname(randomname))
- continue
- else
- O.real_name = randomname
- i++
- updateappearance(O,O.dna.uni_identity)
- O.take_overall_damage(M.getBruteLoss(), M.getFireLoss())
- O.adjustToxLoss(M.getToxLoss())
- O.adjustOxyLoss(M.getOxyLoss())
- O.stat = M.stat
- for (var/obj/item/weapon/implant/I in implants)
- I.loc = O
- I.implanted = O
-// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
- return
-//////////////////////////////////////////////////////////// Monkey Block
- if(M)
- M.update_icon = 1 //queue a full icon update at next life() call
- return null
->>>>>>> d77010221cbd08f6373edebee25d727b6409413b
-/////////////////////////// DNA MISC-PROCS
\ No newline at end of file
diff --git a/code/game/dna/dna_modifier.dm b/code/game/dna/dna_modifier.dm
index 86bfbeb0fef..deb4426cf56 100644
--- a/code/game/dna/dna_modifier.dm
+++ b/code/game/dna/dna_modifier.dm
@@ -144,7 +144,7 @@
return
put_in(G.affecting)
src.add_fingerprint(user)
- del(G)
+ qdel(G)
return
/obj/machinery/dna_scannernew/proc/put_in(var/mob/M)
@@ -187,7 +187,7 @@
ex_act(severity)
//Foreach goto(35)
//SN src = null
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
@@ -196,7 +196,7 @@
ex_act(severity)
//Foreach goto(108)
//SN src = null
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(25))
@@ -205,7 +205,7 @@
ex_act(severity)
//Foreach goto(181)
//SN src = null
- del(src)
+ qdel(src)
return
else
return
@@ -215,7 +215,7 @@
if(prob(75))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
- del(src)
+ qdel(src)
/obj/machinery/computer/scan_consolenew
name = "DNA Modifier Access Console"
@@ -262,12 +262,12 @@
switch(severity)
if(1.0)
//SN src = null
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
//SN src = null
- del(src)
+ qdel(src)
return
else
return
@@ -275,7 +275,7 @@
/obj/machinery/computer/scan_consolenew/blob_act()
if(prob(75))
- del(src)
+ qdel(src)
/obj/machinery/computer/scan_consolenew/power_change()
..()
@@ -598,8 +598,7 @@
inject_amount = 0
if (inject_amount > 50)
inject_amount = 50
- connected.beaker.reagents.trans_to(connected.occupant, inject_amount)
- connected.beaker.reagents.reaction(connected.occupant)
+ connected.beaker.reagents.trans_to_mob(connected.occupant, inject_amount, CHEM_BLOOD)
return 1 // return 1 forces an update to all Nano uis attached to src
////////////////////////////////////////////////////////
diff --git a/code/game/dna/genes/monkey.dm b/code/game/dna/genes/monkey.dm
index 2e0f6cdec2f..7d9da106366 100644
--- a/code/game/dna/genes/monkey.dm
+++ b/code/game/dna/genes/monkey.dm
@@ -33,7 +33,7 @@
animation.master = src
flick("h2monkey", animation)
sleep(48)
- del(animation)
+ qdel(animation)
var/mob/living/carbon/monkey/O = null
@@ -60,7 +60,7 @@
for(var/obj/T in (M.contents-implants))
- del(T)
+ qdel(T)
O.loc = M.loc
@@ -82,7 +82,7 @@
I.loc = O
I.implanted = O
// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
+ qdel(M)
return
/datum/dna/gene/monkey/deactivate(var/mob/living/M, var/connected, var/flags)
@@ -108,7 +108,7 @@
animation.master = src
flick("monkey2h", animation)
sleep(48)
- del(animation)
+ qdel(animation)
var/mob/living/carbon/human/O
if(Mo.greaterform)
@@ -136,7 +136,7 @@
M.viruses -= D
//for(var/obj/T in M)
- // del(T)
+ // qdel(T)
O.loc = M.loc
@@ -171,5 +171,5 @@
I.loc = O
I.implanted = O
// O.update_icon = 1 //queue a full icon update at next life() call
- del(M)
+ qdel(M)
return
diff --git a/code/game/gamemodes/blob/blobs/core.dm b/code/game/gamemodes/blob/blobs/core.dm
index f0a24001ba3..3897d444e8e 100644
--- a/code/game/gamemodes/blob/blobs/core.dm
+++ b/code/game/gamemodes/blob/blobs/core.dm
@@ -14,7 +14,7 @@
..(loc, h)
- Del()
+ Destroy()
blob_cores -= src
processing_objects.Remove(src)
..()
@@ -24,7 +24,7 @@
update_icon()
if(health <= 0)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
- del(src)
+ qdel(src)
return
return
diff --git a/code/game/gamemodes/blob/blobs/factory.dm b/code/game/gamemodes/blob/blobs/factory.dm
index bb8de8184ec..c1d14d00402 100644
--- a/code/game/gamemodes/blob/blobs/factory.dm
+++ b/code/game/gamemodes/blob/blobs/factory.dm
@@ -12,7 +12,7 @@
update_icon()
if(health <= 0)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
- del(src)
+ qdel(src)
return
return
@@ -22,6 +22,11 @@
new/mob/living/simple_animal/hostile/blobspore(src.loc, src)
return 1
+/obj/effect/blob/factory/Destroy()
+ for(var/mob/living/simple_animal/hostile/blobspore/spore in spores)
+ if(spore.factory == src)
+ spore.factory = null
+ ..()
/mob/living/simple_animal/hostile/blobspore
name = "blob"
@@ -58,9 +63,10 @@
..(loc)
return
death()
- ..()
- if(factory)
- factory.spores -= src
- ..()
- del(src)
+ qdel(src)
+/mob/living/simple_animal/hostile/blobspore/Destroy()
+ if(factory)
+ factory.spores -= src
+ factory = null
+ ..()
diff --git a/code/game/gamemodes/blob/blobs/node.dm b/code/game/gamemodes/blob/blobs/node.dm
index c9ffaf96f13..92572f9a7b0 100644
--- a/code/game/gamemodes/blob/blobs/node.dm
+++ b/code/game/gamemodes/blob/blobs/node.dm
@@ -14,7 +14,7 @@
..(loc, h)
- Del()
+ Destroy()
blob_nodes -= src
processing_objects.Remove(src)
..()
@@ -24,7 +24,7 @@
update_icon()
if(health <= 0)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
- del(src)
+ qdel(src)
return
return
diff --git a/code/game/gamemodes/blob/blobs/shield.dm b/code/game/gamemodes/blob/blobs/shield.dm
index 0e1b6c07eb4..c47696c72e3 100644
--- a/code/game/gamemodes/blob/blobs/shield.dm
+++ b/code/game/gamemodes/blob/blobs/shield.dm
@@ -14,7 +14,7 @@
update_icon()
if(health <= 0)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
- del(src)
+ qdel(src)
return
return
diff --git a/code/game/gamemodes/blob/theblob.dm b/code/game/gamemodes/blob/theblob.dm
index f6351c84809..44486d605b5 100644
--- a/code/game/gamemodes/blob/theblob.dm
+++ b/code/game/gamemodes/blob/theblob.dm
@@ -3,7 +3,7 @@
name = "blob"
icon = 'icons/mob/blob.dmi'
icon_state = "blob"
- luminosity = 3
+ light_range = 3
desc = "Some blob creature thingy"
density = 1
opacity = 0
@@ -31,7 +31,7 @@
return
- Del()
+ Destroy()
blobs -= src
..()
return
@@ -110,7 +110,7 @@
B.loc = T
else
T.blob_act()//If we cant move in hit the turf
- del(B)
+ qdel(B)
for(var/atom/A in T)//Hit everything in the turf
A.blob_act()
return 1
@@ -134,7 +134,7 @@
update_icon()//Needs to be updated with the types
if(health <= 0)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
- del(src)
+ qdel(src)
return
if(health <= 15)
icon_state = "blob_damaged"
@@ -158,7 +158,7 @@
attackby(var/obj/item/weapon/W, var/mob/user)
playsound(src.loc, 'sound/effects/attackblob.ogg', 50, 1)
- src.visible_message("\red The [src.name] has been attacked with \the [W][(user ? " by [user]." : ".")]")
+ src.visible_message("The [src.name] has been attacked with \the [W][(user ? " by [user]." : ".")]")
var/damage = 0
switch(W.damtype)
if("fire")
@@ -182,7 +182,7 @@
new/obj/effect/blob/factory(src.loc,src.health)
if("Shield")
new/obj/effect/blob/shield(src.loc,src.health*2)
- del(src)
+ qdel(src)
return
//////////////////////////////****IDLE BLOB***/////////////////////////////////////
@@ -201,7 +201,7 @@
proc/update_idle()
if(health<=0)
- del(src)
+ qdel(src)
return
if(health<4)
icon_state = "blobc0"
@@ -212,7 +212,7 @@
icon_state = "blobidle0"
- Del()
+ Destroy()
var/obj/effect/blob/B = new /obj/effect/blob( src.loc )
spawn(30)
B.Life()
diff --git a/code/game/gamemodes/changeling/changeling_powers.dm b/code/game/gamemodes/changeling/changeling_powers.dm
index 6f5ca5d8e92..29619503774 100644
--- a/code/game/gamemodes/changeling/changeling_powers.dm
+++ b/code/game/gamemodes/changeling/changeling_powers.dm
@@ -385,7 +385,7 @@ var/global/list/possible_changeling_IDs = list("Alpha","Beta","Gamma","Delta","E
animation.master = src
flick("monkey2h", animation)
sleep(48)
- del(animation)
+ qdel(animation)
for(var/obj/item/W in src)
C.drop_from_inventory(W)
@@ -400,7 +400,7 @@ var/global/list/possible_changeling_IDs = list("Alpha","Beta","Gamma","Delta","E
O.real_name = chosen_dna.real_name
for(var/obj/T in C)
- del(T)
+ qdel(T)
O.loc = C.loc
@@ -420,7 +420,7 @@ var/global/list/possible_changeling_IDs = list("Alpha","Beta","Gamma","Delta","E
O.changeling_update_languages(changeling.absorbed_languages)
feedback_add_details("changeling_powers","LFT")
- del(C)
+ qdel(C)
return 1
@@ -463,7 +463,6 @@ var/global/list/possible_changeling_IDs = list("Alpha","Beta","Gamma","Delta","E
// sending display messages
C << "We have regenerated."
- C.visible_message("[src] appears to wake from the dead, having healed all wounds.")
feedback_add_details("changeling_powers","FD")
diff --git a/code/game/gamemodes/cult/cult.dm b/code/game/gamemodes/cult/cult.dm
index 6a17d03a072..a1c0acf0081 100644
--- a/code/game/gamemodes/cult/cult.dm
+++ b/code/game/gamemodes/cult/cult.dm
@@ -8,4 +8,4 @@
required_enemies = 3
uplink_welcome = "Nar-Sie Uplink Console:"
end_on_antag_death = 1
- antag_tag = MODE_CULTIST
\ No newline at end of file
+ antag_tag = MODE_CULTIST
diff --git a/code/game/gamemodes/cult/cult_items.dm b/code/game/gamemodes/cult/cult_items.dm
index f2f5f96de78..a17c030b111 100644
--- a/code/game/gamemodes/cult/cult_items.dm
+++ b/code/game/gamemodes/cult/cult_items.dm
@@ -8,6 +8,8 @@
throwforce = 10
attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
+/obj/item/weapon/melee/cultblade/cultify()
+ return
/obj/item/weapon/melee/cultblade/attack(mob/living/target as mob, mob/living/carbon/human/user as mob)
if(iscultist(user))
@@ -40,15 +42,22 @@
min_cold_protection_temperature = SPACE_HELMET_MIN_COLD_PROTECTION_TEMPERATURE
siemens_coefficient = 0
+/obj/item/clothing/head/culthood/cultify()
+ return
+
+/obj/item/clothing/head/culthood/magus
+ name = "magus helm"
+ icon_state = "magus"
+ item_state = "magus"
+ desc = "A helm worn by the followers of Nar-Sie."
+ flags_inv = HIDEFACE
+ flags = HEADCOVERSEYES | HEADCOVERSMOUTH | BLOCKHAIR
+ body_parts_covered = HEAD|FACE|EYES
/obj/item/clothing/head/culthood/alt
icon_state = "cult_hoodalt"
item_state = "cult_hoodalt"
-/obj/item/clothing/suit/cultrobes/alt
- icon_state = "cultrobesalt"
- item_state = "cultrobesalt"
-
/obj/item/clothing/suit/cultrobes
name = "cult robes"
desc = "A set of armored robes worn by the followers of Nar-Sie"
@@ -60,27 +69,20 @@
flags_inv = HIDEJUMPSUIT
siemens_coefficient = 0
-/obj/item/clothing/head/magus
- name = "magus helm"
- icon_state = "magus"
- item_state = "magus"
- desc = "A helm worn by the followers of Nar-Sie."
- flags_inv = HIDEFACE
- flags = HEADCOVERSEYES | HEADCOVERSMOUTH | BLOCKHAIR
- body_parts_covered = HEAD|FACE|EYES
- armor = list(melee = 30, bullet = 30, laser = 30,energy = 20, bomb = 0, bio = 0, rad = 0)
- siemens_coefficient = 0
+/obj/item/clothing/suit/cultrobes/cultify()
+ return
-/obj/item/clothing/suit/magusred
+/obj/item/clothing/suit/cultrobes/alt
+ icon_state = "cultrobesalt"
+ item_state = "cultrobesalt"
+
+/obj/item/clothing/suit/cultrobes/magusred
name = "magus robes"
desc = "A set of armored robes worn by the followers of Nar-Sie"
icon_state = "magusred"
item_state = "magusred"
body_parts_covered = UPPER_TORSO|LOWER_TORSO|LEGS|FEET|ARMS|HANDS
- allowed = list(/obj/item/weapon/book/tome,/obj/item/weapon/melee/cultblade)
- armor = list(melee = 50, bullet = 30, laser = 50,energy = 20, bomb = 25, bio = 10, rad = 0)
flags_inv = HIDEGLOVES|HIDESHOES|HIDEJUMPSUIT
- siemens_coefficient = 0
/obj/item/clothing/head/helmet/space/cult
name = "cult helmet"
@@ -90,6 +92,8 @@
armor = list(melee = 60, bullet = 50, laser = 30,energy = 15, bomb = 30, bio = 30, rad = 30)
siemens_coefficient = 0
+/obj/item/clothing/head/helmet/space/cult/cultify()
+ return
/obj/item/clothing/suit/space/cult
name = "cult armour"
@@ -101,4 +105,7 @@
slowdown = 1
armor = list(melee = 60, bullet = 50, laser = 30,energy = 15, bomb = 30, bio = 30, rad = 30)
siemens_coefficient = 0
- body_parts_covered = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS|HANDS
\ No newline at end of file
+ body_parts_covered = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS|HANDS
+
+/obj/item/clothing/suit/space/cult/cultify()
+ return
diff --git a/code/game/gamemodes/cult/cult_structures.dm b/code/game/gamemodes/cult/cult_structures.dm
index bf2124ebb54..b5854ed9818 100644
--- a/code/game/gamemodes/cult/cult_structures.dm
+++ b/code/game/gamemodes/cult/cult_structures.dm
@@ -3,6 +3,9 @@
anchored = 1
icon = 'icons/obj/cult.dmi'
+/obj/structure/cult/cultify()
+ return
+
/obj/structure/cult/talisman
name = "Altar"
desc = "A bloodstained altar dedicated to Nar-Sie"
@@ -18,14 +21,57 @@
name = "Pylon"
desc = "A floating crystal that hums with an unearthly energy"
icon_state = "pylon"
- luminosity = 5
+ var/isbroken = 0
+ light_range = 5
+ light_color = "#3e0000"
+ var/obj/item/wepon = null
+/obj/structure/cult/pylon/attack_hand(mob/M as mob)
+ attackpylon(M, 5)
+
+/obj/structure/cult/pylon/attack_generic(var/mob/user, var/damage)
+ attackpylon(user, damage)
+
+/obj/structure/cult/pylon/attackby(obj/item/W as obj, mob/user as mob)
+ attackpylon(user, W.force)
+
+/obj/structure/cult/pylon/proc/attackpylon(mob/user as mob, var/damage)
+ if(!isbroken)
+ if(prob(1+ damage * 5))
+ user << "You hit the pylon, and its crystal breaks apart!"
+ for(var/mob/M in viewers(src))
+ if(M == user)
+ continue
+ M.show_message("[user.name] smashed the pylon!", 3, "You hear a tinkle of crystal shards", 2)
+ playsound(get_turf(src), 'sound/effects/Glassbr3.ogg', 75, 1)
+ isbroken = 1
+ density = 0
+ icon_state = "pylon-broken"
+ set_light(0)
+ else
+ user << "You hit the pylon!"
+ playsound(get_turf(src), 'sound/effects/Glasshit.ogg', 75, 1)
+ else
+ if(prob(damage * 2))
+ user << "You pulverize what was left of the pylon!"
+ qdel(src)
+ else
+ user << "You hit the pylon!"
+ playsound(get_turf(src), 'sound/effects/Glasshit.ogg', 75, 1)
+
+
+/obj/structure/cult/pylon/proc/repair(mob/user as mob)
+ if(isbroken)
+ user << "You repair the pylon."
+ isbroken = 0
+ density = 1
+ icon_state = "pylon"
+ set_light(5)
/obj/structure/cult/tome
name = "Desk"
desc = "A desk covered in arcane manuscripts and tomes in unknown languages. Looking at the text makes your skin crawl"
icon_state = "tomealtar"
-// luminosity = 5
//sprites for this no longer exist -Pete
//(they were stolen from another game anyway)
@@ -45,6 +91,7 @@
density = 1
unacidable = 1
anchored = 1.0
+ var/spawnable = null
/obj/effect/gateway/Bumped(mob/M as mob|obj)
spawn(0)
@@ -54,4 +101,74 @@
/obj/effect/gateway/Crossed(AM as mob|obj)
spawn(0)
return
- return
\ No newline at end of file
+ return
+
+/obj/effect/gateway/active
+ light_range=5
+ light_color="#ff0000"
+ spawnable=list(
+ /mob/living/simple_animal/hostile/scarybat,
+ /mob/living/simple_animal/hostile/creature,
+ /mob/living/simple_animal/hostile/faithless
+ )
+
+/obj/effect/gateway/active/cult
+ light_range=5
+ light_color="#ff0000"
+ spawnable=list(
+ /mob/living/simple_animal/hostile/scarybat/cult,
+ /mob/living/simple_animal/hostile/creature/cult,
+ /mob/living/simple_animal/hostile/faithless/cult
+ )
+
+/obj/effect/gateway/active/cult/cultify()
+ return
+
+/obj/effect/gateway/active/New()
+ spawn(rand(30,60) SECONDS)
+ var/t = pick(spawnable)
+ new t(src.loc)
+ qdel(src)
+
+/obj/effect/gateway/active/Crossed(var/atom/A)
+ if(!istype(A, /mob/living))
+ return
+
+ var/mob/living/M = A
+
+ if(M.stat != DEAD)
+ if(M.monkeyizing)
+ return
+ if(M.has_brain_worms())
+ return //Borer stuff - RR
+
+ if(iscultist(M)) return
+ if(!ishuman(M) && !isrobot(M)) return
+
+ M.monkeyizing = 1
+ M.canmove = 0
+ M.icon = null
+ M.overlays.len = 0
+ M.invisibility = 101
+
+ if(istype(M, /mob/living/silicon/robot))
+ var/mob/living/silicon/robot/Robot = M
+ if(Robot.mmi)
+ qdel(Robot.mmi)
+ else
+ for(var/obj/item/W in M)
+ if(istype(W, /obj/item/weapon/implant))
+ qdel(W)
+ continue
+ W.layer = initial(W.layer)
+ W.loc = M.loc
+ W.dropped(M)
+
+ var/mob/living/new_mob = new /mob/living/simple_animal/corgi(A.loc)
+ new_mob.a_intent = I_HURT
+ if(M.mind)
+ M.mind.transfer_to(new_mob)
+ else
+ new_mob.key = M.key
+
+ new_mob << "Your form morphs into that of a corgi." //Because we don't have cluwnes
diff --git a/code/game/gamemodes/cult/cultify/mob.dm b/code/game/gamemodes/cult/cultify/mob.dm
new file mode 100644
index 00000000000..154078de3d6
--- /dev/null
+++ b/code/game/gamemodes/cult/cultify/mob.dm
@@ -0,0 +1,63 @@
+/mob
+ //thou shall always be able to see the Geometer of Blood
+ var/image/narsimage = null
+ var/image/narglow = null
+
+/mob/proc/cultify()
+ return
+
+/mob/dead/cultify()
+ if(icon_state != "ghost-narsie")
+ icon = 'icons/mob/mob.dmi'
+ icon_state = "ghost-narsie"
+ overlays = 0
+ invisibility = 0
+ src << "Even as a non-corporal being, you can feel Nar-Sie's presence altering you. You are now visible to everyone."
+
+/mob/living/cultify()
+ if(iscultist(src) && client)
+ var/mob/living/simple_animal/construct/harvester/C = new(get_turf(src))
+ mind.transfer_to(C)
+ C << "The Geometer of Blood is overjoyed to be reunited with its followers, and accepts your body in sacrifice. As reward, you have been gifted with the shell of an Harvester. Your tendrils can use and draw runes without need for a tome, your eyes can see beings through walls, and your mind can open any door. Use these assets to serve Nar-Sie and bring him any remaining living human in the world. You can teleport yourself back to Nar-Sie along with any being under yourself at any time using your \"Harvest\" spell."
+ dust()
+ else if(client)
+ var/mob/dead/G = (ghostize())
+ G.icon = 'icons/mob/mob.dmi'
+ G.icon_state = "ghost-narsie"
+ G.overlays = 0
+ G.invisibility = 0
+ G << "You feel relieved as what's left of your soul finally escapes its prison of flesh."
+
+ cult.harvested += G.mind
+ else
+ dust()
+
+/mob/proc/see_narsie(var/obj/singularity/narsie/large/N, var/dir)
+ if(N.chained)
+ if(narsimage)
+ qdel(narsimage)
+ qdel(narglow)
+ return
+ if((N.z == src.z)&&(get_dist(N,src) <= (N.consume_range+10)) && !(N in view(src)))
+ if(!narsimage) //Create narsimage
+ narsimage = image('icons/obj/narsie.dmi',src.loc,"narsie",9,1)
+ narsimage.mouse_opacity = 0
+ if(!narglow) //Create narglow
+ narglow = image('icons/obj/narsie.dmi',narsimage.loc,"glow-narsie",12,1)
+ narglow.mouse_opacity = 0
+ //Else if no dir is given, simply send them the image of narsie
+ var/new_x = 32 * (N.x - src.x) + N.pixel_x
+ var/new_y = 32 * (N.y - src.y) + N.pixel_y
+ narsimage.pixel_x = new_x
+ narsimage.pixel_y = new_y
+ narglow.pixel_x = new_x
+ narglow.pixel_y = new_y
+ narsimage.loc = src.loc
+ narglow.loc = src.loc
+ //Display the new narsimage to the player
+ src << narsimage
+ src << narglow
+ else
+ if(narsimage)
+ qdel(narsimage)
+ qdel(narglow)
diff --git a/code/game/gamemodes/cult/cultify/obj.dm b/code/game/gamemodes/cult/cultify/obj.dm
new file mode 100644
index 00000000000..cbc3571896e
--- /dev/null
+++ b/code/game/gamemodes/cult/cultify/obj.dm
@@ -0,0 +1,153 @@
+/obj/proc/cultify()
+ qdel(src)
+
+/obj/effect/decal/cleanable/blood/cultify()
+ return
+
+/obj/effect/decal/remains/cultify()
+ return
+
+/obj/effect/overlay/cultify()
+ return
+
+/obj/item/device/flashlight/lamp/cultify()
+ new /obj/structure/cult/pylon(loc)
+ ..()
+
+/obj/item/stack/sheet/wood/cultify()
+ return
+
+/obj/item/weapon/book/cultify()
+ new /obj/item/weapon/book/tome(loc)
+ ..()
+
+/obj/item/weapon/claymore/cultify()
+ new /obj/item/weapon/melee/cultblade(loc)
+ ..()
+
+/obj/item/weapon/storage/backpack/cultify()
+ new /obj/item/weapon/storage/backpack/cultpack(loc)
+ ..()
+
+/obj/item/weapon/storage/backpack/cultpack/cultify()
+ return
+
+/obj/machinery/cultify()
+ // We keep the number of cultified machines down by only converting those that are dense
+ // The alternative is to keep a separate file of exceptions.
+ if(density)
+ var/list/random_structure = list(
+ /obj/structure/cult/talisman,
+ /obj/structure/cult/forge,
+ /obj/structure/cult/tome
+ )
+ var/I = pick(random_structure)
+ new I(loc)
+ ..()
+
+/obj/machinery/atmospherics/cultify()
+ if(src.invisibility != INVISIBILITY_MAXIMUM)
+ src.invisibility = INVISIBILITY_MAXIMUM
+ density = 0
+
+/obj/machinery/cooking/cultify()
+ new /obj/structure/cult/talisman(loc)
+ qdel(src)
+
+/obj/machinery/computer/cultify()
+ new /obj/structure/cult/tome(loc)
+ qdel(src)
+
+/obj/machinery/door/airlock/external/cultify()
+ new /obj/structure/mineral_door/wood(loc)
+ ..()
+
+/obj/machinery/door/cultify()
+ icon_state = "null"
+ density = 0
+ c_animation = new /atom/movable/overlay(src.loc)
+ c_animation.name = "cultification"
+ c_animation.density = 0
+ c_animation.anchored = 1
+ c_animation.icon = 'icons/effects/effects.dmi'
+ c_animation.layer = 5
+ c_animation.master = src.loc
+ c_animation.icon_state = "breakdoor"
+ flick("cultification",c_animation)
+ spawn(10)
+ qdel(c_animation)
+ qdel(src)
+
+/obj/machinery/door/firedoor/cultify()
+ qdel(src)
+
+/obj/machinery/light/cultify()
+ new /obj/structure/cult/pylon(loc)
+ qdel(src)
+
+/obj/machinery/mech_sensor/cultify()
+ qdel(src)
+
+/obj/machinery/power/apc/cultify()
+ if(src.invisibility != INVISIBILITY_MAXIMUM)
+ src.invisibility = INVISIBILITY_MAXIMUM
+
+/obj/machinery/vending/cultify()
+ new /obj/structure/cult/forge(loc)
+ qdel(src)
+
+/obj/structure/bed/chair/cultify()
+ var/obj/structure/bed/chair/wood/wings/I = new(loc)
+ I.dir = dir
+ ..()
+
+/obj/structure/bed/chair/wood/cultify()
+ return
+
+/obj/structure/bookcase/cultify()
+ return
+
+/obj/structure/grille/cultify()
+ new /obj/structure/grille/cult(get_turf(src))
+ ..()
+
+/obj/structure/grille/cult/cultify()
+ return
+
+/obj/structure/mineral_door/cultify()
+ new /obj/structure/mineral_door/wood(loc)
+ ..()
+
+/obj/structure/mineral_door/wood/cultify()
+ return
+
+/obj/singularity/cultify()
+ var/dist = max((current_size - 2), 1)
+ explosion(get_turf(src), dist, dist * 2, dist * 4)
+ qdel(src)
+
+/obj/structure/shuttle/engine/heater/cultify()
+ new /obj/structure/cult/pylon(loc)
+ ..()
+
+/obj/structure/shuttle/engine/propulsion/cultify()
+ var/turf/T = get_turf(src)
+ if(T)
+ T.ChangeTurf(/turf/simulated/wall/cult)
+ ..()
+
+/obj/structure/stool/cultify()
+ var/obj/structure/bed/chair/wood/wings/I = new(loc)
+ I.dir = dir
+ ..()
+
+/obj/structure/table/cultify()
+ // Make it a wood-reinforced wooden table.
+ // There are cult materials available, but it'd make the table non-deconstructable with how holotables work.
+ // Could possibly use a new material var for holographic-ness?
+ material = name_to_material["wood"]
+ reinforced = name_to_material["wood"]
+ update_desc()
+ update_connections(1)
+ update_icon()
+ update_material()
diff --git a/code/game/gamemodes/cult/cultify/turf.dm b/code/game/gamemodes/cult/cultify/turf.dm
new file mode 100644
index 00000000000..0005298c423
--- /dev/null
+++ b/code/game/gamemodes/cult/cultify/turf.dm
@@ -0,0 +1,43 @@
+/turf/proc/cultify()
+ ChangeTurf(/turf/space)
+ return
+
+/turf/simulated/floor/cultify()
+ cultify_floor()
+
+/turf/simulated/floor/carpet/cultify()
+ return
+
+/turf/simulated/shuttle/floor/cultify()
+ cultify_floor()
+
+/turf/simulated/shuttle/floor4/cultify()
+ cultify_floor()
+
+/turf/simulated/shuttle/wall/cultify()
+ cultify_wall()
+
+/turf/simulated/wall/cultify()
+ cultify_wall()
+
+/turf/simulated/wall/cult/cultify()
+ return
+
+/turf/unsimulated/beach/cultify()
+ return
+
+/turf/unsimulated/floor/cultify()
+ cultify_floor()
+
+/turf/unsimulated/wall/cultify()
+ cultify_wall()
+
+/turf/proc/cultify_floor()
+ if((icon_state != "cult")&&(icon_state != "cult-narsie"))
+ name = "engraved floor"
+ icon_state = "cult"
+ turf_animation('icons/effects/effects.dmi',"cultfloor",0,0,MOB_LAYER-1)
+
+/turf/proc/cultify_wall()
+ ChangeTurf(/turf/unsimulated/wall/cult)
+ turf_animation('icons/effects/effects.dmi',"cultwall",0,0,MOB_LAYER-1)
diff --git a/code/game/gamemodes/cult/hell_universe.dm b/code/game/gamemodes/cult/hell_universe.dm
new file mode 100644
index 00000000000..9a7344f036a
--- /dev/null
+++ b/code/game/gamemodes/cult/hell_universe.dm
@@ -0,0 +1,100 @@
+/*
+
+In short:
+ * Random area alarms
+ * All areas jammed
+ * Random gateways spawning hellmonsters (and turn people into cluwnes if ran into)
+ * Broken APCs/Fire Alarms
+ * Scary music
+ * Random tiles changing to culty tiles.
+
+*/
+/datum/universal_state/hell
+ name = "Hell Rising"
+ desc = "OH FUCK OH FUCK OH FUCK"
+
+ decay_rate = 5 // 5% chance of a turf decaying on lighting update/airflow (there's no actual tick for turfs)
+
+/datum/universal_state/hell/OnShuttleCall(var/mob/user)
+ return 1
+ /*
+ if(user)
+ user << "All you hear on the frequency is static and panicked screaming. There will be no shuttle call today."
+ return 0
+ */
+
+/datum/universal_state/hell/DecayTurf(var/turf/T)
+ if(!T.holy)
+ T.cultify()
+ for(var/obj/machinery/light/L in T.contents)
+ new /obj/structure/cult/pylon(L.loc)
+ qdel(L)
+ return
+
+
+/datum/universal_state/hell/OnTurfChange(var/turf/T)
+ var/turf/space/spess = T
+ if(istype(spess))
+ spess.overlays += "hell01"
+
+// Apply changes when entering state
+/datum/universal_state/hell/OnEnter()
+ set background = 1
+ garbage_collector.garbage_collect = 0
+ escape_list = get_area_turfs(locate(/area/hallway/secondary/exit))
+
+ //Separated into separate procs for profiling
+ AreaSet()
+ OverlaySet()
+ MiscSet()
+ APCSet()
+ KillMobs()
+ AmbientSet()
+
+ runedec += 9000 //basically removing the rune cap
+
+/datum/universal_state/hell/proc/AreaSet()
+ for(var/area/A in world)
+ if(A.name=="Space")
+ continue
+
+ // Reset all alarms.
+ A.fire = null
+ A.atmos = 1
+ A.atmosalm = 0
+ A.poweralm = 1
+ A.party = null
+
+ A.updateicon()
+
+/datum/universal_state/hell/proc/OverlaySet()
+ var/image/I = image("icon" = 'icons/turf/space.dmi', "icon_state" = "hell01", "layer" = 10)
+ for(var/turf/space/spess in world)
+ spess.overlays += I
+
+/datum/universal_state/hell/proc/AmbientSet()
+ for(var/atom/movable/lighting_overlay/L in world)
+ L.update_lumcount(1, 0, 0)
+
+/datum/universal_state/hell/proc/MiscSet()
+ for(var/turf/simulated/floor/T in world)
+ if(!T.holy && prob(1))
+ new /obj/effect/gateway/active/cult(T)
+
+ for (var/obj/machinery/firealarm/alm in machines)
+ if (!(alm.stat & BROKEN))
+ alm.ex_act(2)
+
+/datum/universal_state/hell/proc/APCSet()
+ for (var/obj/machinery/power/apc/APC in machines)
+ if (!(APC.stat & BROKEN) && !istype(APC.area,/area/turret_protected/ai))
+ APC.chargemode = 0
+ if(APC.cell)
+ APC.cell.charge = 0
+ APC.emagged = 1
+ APC.queue_icon_update()
+
+/datum/universal_state/hell/proc/KillMobs()
+ for(var/mob/living/simple_animal/M in mob_list)
+ if(M && !M.client)
+ M.stat = DEAD
diff --git a/code/game/gamemodes/cult/ritual.dm b/code/game/gamemodes/cult/ritual.dm
index 0fd706059e9..8a55a811654 100644
--- a/code/game/gamemodes/cult/ritual.dm
+++ b/code/game/gamemodes/cult/ritual.dm
@@ -2,7 +2,8 @@
var/cultwords = list()
var/runedec = 0
-var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology", "self", "see", "other", "hide")
+var/global/list/engwords = list("travel", "blood", "join", "hell", "destroy", "technology", "self", "see", "other", "hide")
+var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","mgar","balaq", "karazet", "geeri")
/client/proc/check_words() // -- Urist
set category = "Special Verbs"
@@ -14,7 +15,7 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
usr << "[cultwords[word]] is [word]"
/proc/runerandom() //randomizes word meaning
- var/list/runewords=list("ire","ego","nahlizet","certum","veri","jatkaa","mgar","balaq", "karazet", "geeri") ///"orkan" and "allaq" removed.
+ var/list/runewords=rnwords
for (var/word in engwords)
cultwords[word] = pick(runewords)
runewords-=cultwords[word]
@@ -32,8 +33,9 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
var/word1
var/word2
var/word3
+ var/image/blood_image
var/list/converting = list()
-
+
// Places these combos are mentioned: this file - twice in the rune code, once in imbued tome, once in tome's HTML runes.dm - in the imbue rune code. If you change a combination - dont forget to change it everywhere.
// travel self [word] - Teleport to random [rune with word destination matching]
@@ -65,10 +67,21 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
// join hide technology - stun rune. Rune color: bright pink.
New()
..()
- var/image/blood = image(loc = src)
- blood.override = 1
+ blood_image = image(loc = src)
+ blood_image.override = 1
for(var/mob/living/silicon/ai/AI in player_list)
- AI.client.images += blood
+ if(AI.client)
+ AI.client.images += blood_image
+ rune_list.Add(src)
+
+ Destroy()
+ for(var/mob/living/silicon/ai/AI in player_list)
+ if(AI.client)
+ AI.client.images -= blood_image
+ qdel(blood_image)
+ blood_image = null
+ rune_list.Remove(src)
+ ..()
examine(mob/user)
..()
@@ -79,11 +92,11 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
attackby(I as obj, user as mob)
if(istype(I, /obj/item/weapon/book/tome) && iscultist(user))
user << "You retrace your steps, carefully undoing the lines of the rune."
- del(src)
+ qdel(src)
return
else if(istype(I, /obj/item/weapon/nullrod))
user << "\blue You disrupt the vile magic with the deadening field of the null rod!"
- del(src)
+ qdel(src)
return
return
@@ -457,6 +470,8 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
user << "\red You slice open one of your fingers and begin drawing a rune on the floor whilst chanting the ritual that binds your life essence with the dark arcane energies flowing through the surrounding world."
user.take_overall_damage((rand(9)+1)/10) // 0.1 to 1.0 damage
if(do_after(user, 50))
+ var/area/A = get_area(user)
+ log_and_message_admins("created \an [chosen_rune] rune at \the [A.name] - [user.loc.x]-[user.loc.y]-[user.loc.z].")
if(usr.get_active_hand() != src)
return
var/mob/living/carbon/human/H = user
@@ -495,6 +510,9 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
else
user << "The scriptures of Nar-Sie, The One Who Sees, The Geometer of Blood. Contains the details of every ritual his followers could think of. Most of these are useless, though."
+/obj/item/weapon/book/tome/cultify()
+ return
+
/obj/item/weapon/book/tome/imbued //admin tome, spawns working runes without waiting
w_class = 2.0
var/cultistsonly = 1
@@ -514,6 +532,8 @@ var/engwords = list("travel", "blood", "join", "hell", "destroy", "technology",
var/mob/living/carbon/human/H = user
R.blood_DNA = list()
R.blood_DNA[H.dna.unique_enzymes] = H.dna.b_type
+ var/area/A = get_area(user)
+ log_and_message_admins("created \an [r] rune at \the [A.name] - [user.loc.x]-[user.loc.y]-[user.loc.z].")
switch(r)
if("teleport")
var/list/words = list("ire", "ego", "nahlizet", "certum", "veri", "jatkaa", "balaq", "mgar", "karazet", "geeri")
diff --git a/code/game/gamemodes/cult/runes.dm b/code/game/gamemodes/cult/runes.dm
index 9230436a056..8ead4b96bad 100644
--- a/code/game/gamemodes/cult/runes.dm
+++ b/code/game/gamemodes/cult/runes.dm
@@ -1,5 +1,8 @@
var/list/sacrificed = list()
+/obj/effect/rune/cultify()
+ return
+
/obj/effect/rune
/////////////////////////////////////////FIRST RUNE
@@ -21,7 +24,7 @@ var/list/sacrificed = list()
user << "\red You feel pain, as rune disappears in reality shift caused by too much wear of space-time fabric"
if (istype(user, /mob/living))
user.take_overall_damage(5, 0)
- del(src)
+ qdel(src)
if(allrunesloc && index != 0)
if(istype(src,/obj/effect/rune))
user.say("Sas[pick("'","`")]so c'arta forbici!")//Only you can stop auto-muting
@@ -58,7 +61,7 @@ var/list/sacrificed = list()
user << "\red You feel pain, as rune disappears in reality shift caused by too much wear of space-time fabric"
if (istype(user, /mob/living))
user.take_overall_damage(5, 0)
- del(src)
+ qdel(src)
for(var/mob/living/carbon/C in orange(1,src))
if(iscultist(C) && !C.stat)
culcount++
@@ -91,7 +94,7 @@ var/list/sacrificed = list()
new /obj/item/weapon/book/tome(src.loc)
else
new /obj/item/weapon/book/tome(usr.loc)
- del(src)
+ qdel(src)
return
@@ -99,6 +102,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////THIRD RUNE
convert()
+ var/mob/attacker = usr
var/mob/living/carbon/target = null
for(var/mob/living/carbon/M in src.loc)
if(!iscultist(M) && M.stat < DEAD && !(M in converting))
@@ -127,6 +131,7 @@ var/list/sacrificed = list()
target.take_overall_damage(0, rand(5, 20)) // You dirty resister cannot handle the damage to your mind. Easily. - even cultists who accept right away should experience some effects
// Resist messages go!
if(initial_message) //don't do this stuff right away, only if they resist or hesitate.
+ admin_attack_log(attacker, target, "Used a convert rune", "Was subjected to a convert rune", "used a convert rune on")
switch(target.getFireLoss())
if(0 to 25)
target << "Your blood boils as you force yourself to resist the corruption invading every corner of your mind."
@@ -176,13 +181,17 @@ var/list/sacrificed = list()
/////////////////////////////////////////FOURTH RUNE
tearreality()
- var/cultist_count = 0
+ if(!cult.allow_narsie)
+ return fizzle()
+
+ var/list/cultists = new()
for(var/mob/M in range(1,src))
if(iscultist(M) && !M.stat)
M.say("Tok-lyr rqa'nap g[pick("'","`")]lt-ulotf!")
- cultist_count += 1
- if(cultist_count >= 9)
- new /obj/machinery/singularity/narsie/large(src.loc)
+ cultists += 1
+ if(cultists.len >= 9)
+ log_and_message_admins_many(cultists, "summoned Nar-sie.")
+ new /obj/singularity/narsie/large(src.loc)
return
else
return fizzle()
@@ -190,6 +199,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////FIFTH RUNE
emp(var/U,var/range_red) //range_red - var which determines by which number to reduce the default emp range, U is the source loc, needed because of talisman emps which are held in hand at the moment of using and that apparently messes things up -- Urist
+ log_and_message_admins("activated an EMP rune.")
if(istype(src,/obj/effect/rune))
usr.say("Ta'gh fara[pick("'","`")]qha fel d'amar det!")
else
@@ -200,7 +210,7 @@ var/list/sacrificed = list()
T.hotspot_expose(700,125)
var/rune = src // detaching the proc - in theory
empulse(U, (range_red - 2), range_red)
- del(rune)
+ qdel(rune)
return
/////////////////////////////////////////SIXTH RUNE
@@ -211,6 +221,7 @@ var/list/sacrificed = list()
if(R.word1==cultwords["travel"] && R.word2==cultwords["blood"] && R.word3==cultwords["self"])
for(var/mob/living/carbon/D in R.loc)
if(D.stat!=2)
+ admin_attack_log(usr, D, "Used a blood drain rune.", "Was victim of a blood drain rune.", "used a blood drain rune on")
var/bdrain = rand(1,25)
D << "\red You feel weakened."
D.take_overall_damage(bdrain, 0)
@@ -359,7 +370,7 @@ var/list/sacrificed = list()
usr.say("Kla[pick("'","`")]atu barada nikt'o!")
for (var/mob/V in viewers(src))
V.show_message("\red The rune turns into gray dust, veiling the surrounding runes.", 3)
- del(src)
+ qdel(src)
else
usr.whisper("Kla[pick("'","`")]atu barada nikt'o!")
usr << "\red Your talisman turns into gray dust, veiling the surrounding runes."
@@ -407,6 +418,7 @@ var/list/sacrificed = list()
var/mob/dead/observer/ghost
for(var/mob/dead/observer/O in this_rune.loc)
if(!O.client) continue
+ if(!O.MayRespawn()) continue
if(O.mind && O.mind.current && O.mind.current.stat != DEAD) continue
ghost = O
break
@@ -443,6 +455,7 @@ var/list/sacrificed = list()
D.real_name += " "
D.real_name += pick("Apparition", "Aptrgangr", "Dis", "Draugr", "Dybbuk", "Eidolon", "Fetch", "Fylgja", "Ghast", "Ghost", "Gjenganger", "Haint", "Phantom", "Phantasm", "Poltergeist", "Revenant", "Shade", "Shadow", "Soul", "Spectre", "Spirit", "Spook", "Visitant", "Wraith")
+ log_and_message_admins("used a manifest rune.")
var/mob/living/user = usr
while(this_rune && user && user.stat==CONSCIOUS && user.client && user.loc==this_rune.loc)
user.take_organ_damage(1, 0)
@@ -534,8 +547,8 @@ var/list/sacrificed = list()
for (var/mob/V in viewers(src))
V.show_message("\red The runes turn into dust, which then forms into an arcane image on the paper.", 3)
usr.say("H'drak v[pick("'","`")]loso, mir'kanas verbot!")
- del(imbued_from)
- del(newtalisman)
+ qdel(imbued_from)
+ qdel(newtalisman)
else
return fizzle()
@@ -563,26 +576,26 @@ var/list/sacrificed = list()
// returns 0 if the rune is not used. returns 1 if the rune is used.
communicate()
. = 1 // Default output is 1. If the rune is deleted it will return 1
- var/input = sanitize(input(usr, "Please choose a message to tell to the other acolytes.", "Voice of Blood", ""))
+ var/input = input(usr, "Please choose a message to tell to the other acolytes.", "Voice of Blood", "")//sanitize() below, say() and whisper() have their own
if(!input)
if (istype(src))
fizzle()
return 0
else
return 0
- if(istype(src,/obj/effect/rune))
- usr.say("O bidai nabora se[pick("'","`")]sma!")
- else
- usr.whisper("O bidai nabora se[pick("'","`")]sma!")
if(istype(src,/obj/effect/rune))
+ usr.say("O bidai nabora se[pick("'","`")]sma!")
usr.say("[input]")
else
+ usr.whisper("O bidai nabora se[pick("'","`")]sma!")
usr.whisper("[input]")
+
+ input = sanitize(input)
for(var/datum/mind/H in cult.current_antagonists)
if (H.current)
H.current << "\red \b [input]"
- del(src)
+ qdel(src)
return 1
/////////////////////////////////////////FIFTEENTH RUNE
@@ -657,6 +670,7 @@ var/list/sacrificed = list()
usr << "\red The victim is still alive, you will need more cultists chanting for the sacrifice to succeed."
else
if(prob(40))
+
usr << "\red The Geometer of blood accepts this sacrifice."
cult.grant_runeword(usr)
else
@@ -733,7 +747,7 @@ var/list/sacrificed = list()
usr.say("Nikt[pick("'","`")]o barada kla'atu!")
for (var/mob/V in viewers(src))
V.show_message("\red The rune turns into red dust, reveaing the surrounding runes.", 3)
- del(src)
+ qdel(src)
return
if(istype(W,/obj/item/weapon/paper/talisman))
usr.whisper("Nikt[pick("'","`")]o barada kla'atu!")
@@ -806,7 +820,7 @@ var/list/sacrificed = list()
for(var/mob/living/carbon/C in users)
user.take_overall_damage(dam, 0)
C.say("Khari[pick("'","`")]d! Gual'te nikka!")
- del(src)
+ qdel(src)
return fizzle()
/////////////////////////////////////////NINETEENTH RUNE
@@ -846,14 +860,14 @@ var/list/sacrificed = list()
user.visible_message("\red Rune disappears with a flash of red light, and in its place now a body lies.", \
"\red You are blinded by the flash of red light! After you're able to see again, you see that now instead of the rune there's a body.", \
"\red You hear a pop and smell ozone.")
- del(src)
+ qdel(src)
return fizzle()
/////////////////////////////////////////TWENTIETH RUNES
deafen()
if(istype(src,/obj/effect/rune))
- var/affected = 0
+ var/list/affected = new()
for(var/mob/living/carbon/C in range(7,src))
if (iscultist(C))
continue
@@ -862,17 +876,18 @@ var/list/sacrificed = list()
continue
C.ear_deaf += 50
C.show_message("\red The world around you suddenly becomes quiet.", 3)
- affected++
+ affected += C
if(prob(1))
C.sdisabilities |= DEAF
- if(affected)
+ if(affected.len)
usr.say("Sti[pick("'","`")] kaliedir!")
usr << "\red The world becomes quiet as the deafening rune dissipates into fine dust."
- del(src)
+ admin_attacker_log_many_victims(usr, affected, "Used a deafen rune.", "Was victim of a deafen rune.", "used a deafen rune on")
+ qdel(src)
else
return fizzle()
else
- var/affected = 0
+ var/list/affected = new()
for(var/mob/living/carbon/C in range(7,usr))
if (iscultist(C))
continue
@@ -882,10 +897,11 @@ var/list/sacrificed = list()
C.ear_deaf += 30
//talismans is weaker.
C.show_message("\red The world around you suddenly becomes quiet.", 3)
- affected++
- if(affected)
+ affected += C
+ if(affected.len)
usr.whisper("Sti[pick("'","`")] kaliedir!")
usr << "\red Your talisman turns into gray dust, deafening everyone around."
+ admin_attacker_log_many_victims(usr, affected, "Used a deafen rune.", "Was victim of a deafen rune.", "used a deafen rune on")
for (var/mob/V in orange(1,src))
if(!(iscultist(V)))
V.show_message("\red Dust flows from [usr]'s hands for a moment, and the world suddenly becomes quiet..", 3)
@@ -893,7 +909,7 @@ var/list/sacrificed = list()
blind()
if(istype(src,/obj/effect/rune))
- var/affected = 0
+ var/list/affected = new()
for(var/mob/living/carbon/C in viewers(src))
if (iscultist(C))
continue
@@ -907,15 +923,16 @@ var/list/sacrificed = list()
if(prob(10))
C.sdisabilities |= BLIND
C.show_message("\red Suddenly you see red flash that blinds you.", 3)
- affected++
- if(affected)
+ affected += C
+ if(affected.len)
usr.say("Sti[pick("'","`")] kaliesin!")
usr << "\red The rune flashes, blinding those who not follow the Nar-Sie, and dissipates into fine dust."
- del(src)
+ admin_attacker_log_many_victims(usr, affected, "Used a blindness rune.", "Was victim of a blindness rune.", "used a blindness rune on")
+ qdel(src)
else
return fizzle()
else
- var/affected = 0
+ var/list/affected = new()
for(var/mob/living/carbon/C in view(2,usr))
if (iscultist(C))
continue
@@ -925,11 +942,12 @@ var/list/sacrificed = list()
C.eye_blurry += 30
C.eye_blind += 10
//talismans is weaker.
- affected++
+ affected += C
C.show_message("\red You feel a sharp pain in your eyes, and the world disappears into darkness..", 3)
- if(affected)
+ if(affected.len)
usr.whisper("Sti[pick("'","`")] kaliesin!")
usr << "\red Your talisman turns into gray dust, blinding those who not follow the Nar-Sie."
+ admin_attacker_log_many_victims(usr, affected, "Used a blindness rune.", "Was victim of a blindness rune.", "used a blindness rune on")
return
@@ -940,12 +958,13 @@ var/list/sacrificed = list()
if (istype(H.current,/mob/living/carbon))
cultists+=H.current
*/
- var/culcount = 0 //also, wording for it is old wording for obscure rune, which is now hide-see-blood.
+ var/list/cultists = new //also, wording for it is old wording for obscure rune, which is now hide-see-blood.
+ var/list/victims = new
// var/list/cultboil = list(cultists-usr) //and for this words are destroy-see-blood.
for(var/mob/living/carbon/C in orange(1,src))
if(iscultist(C) && !C.stat)
- culcount++
- if(culcount>=3)
+ cultists+=C
+ if(cultists.len>=3)
for(var/mob/living/carbon/M in viewers(usr))
if(iscultist(M))
continue
@@ -954,6 +973,7 @@ var/list/sacrificed = list()
continue
M.take_overall_damage(51,51)
M << "\red Your blood boils!"
+ victims += M
if(prob(5))
spawn(5)
M.gib()
@@ -964,7 +984,9 @@ var/list/sacrificed = list()
if(iscultist(C) && !C.stat)
C.say("Dedo ol[pick("'","`")]btoh!")
C.take_overall_damage(15, 0)
- del(src)
+ admin_attacker_log_many_victims(usr, victims, "Used a blood boil rune.", "Was the victim of a blood boil rune.", "used a blood boil rune on")
+ log_and_message_admins_many(cultists - usr, "assisted activating a blood boil rune.")
+ qdel(src)
else
return fizzle()
return
@@ -994,8 +1016,8 @@ var/list/sacrificed = list()
M << "\red Blood suddenly ignites, burning you!"
var/turf/T = get_turf(B)
T.hotspot_expose(700,125)
- del(B)
- del(src)
+ qdel(B)
+ qdel(src)
////////// Rune 24 (counting burningblood, which kinda doesnt work yet.)
@@ -1003,7 +1025,6 @@ var/list/sacrificed = list()
if(istype(src,/obj/effect/rune)) ///When invoked as rune, flash and stun everyone around.
usr.say("Fuu ma[pick("'","`")]jin!")
for(var/mob/living/L in viewers(src))
-
if(iscarbon(L))
var/mob/living/carbon/C = L
flick("e_flash", C.flash)
@@ -1012,12 +1033,14 @@ var/list/sacrificed = list()
C.Weaken(1)
C.Stun(1)
C.show_message("\red The rune explodes in a bright flash.", 3)
+ admin_attack_log(usr, C, "Used a stun rune.", "Was victim of a stun rune.", "used a stun rune on")
else if(issilicon(L))
var/mob/living/silicon/S = L
S.Weaken(5)
S.show_message("\red BZZZT... The rune has exploded in a bright flash.", 3)
- del(src)
+ admin_attack_log(usr, S, "Used a stun rune.", "Was victim of a stun rune.", "used a stun rune on")
+ qdel(src)
else ///When invoked as talisman, stun and mute the target mob.
usr.say("Dream sign ''Evil sealing talisman'[pick("'","`")]!")
var/obj/item/weapon/nullrod/N = locate() in T
@@ -1030,7 +1053,7 @@ var/list/sacrificed = list()
if(issilicon(T))
T.Weaken(15)
-
+ admin_attack_log(usr, T, "Used a stun rune.", "Was victim of a stun rune.", "used a stun rune on")
else if(iscarbon(T))
var/mob/living/carbon/C = T
flick("e_flash", C.flash)
@@ -1038,6 +1061,7 @@ var/list/sacrificed = list()
C.silent += 15
C.Weaken(25)
C.Stun(25)
+ admin_attack_log(usr, C, "Used a stun rune.", "Was victim of a stun rune.", "used a stun rune on")
return
/////////////////////////////////////////TWENTY-FIFTH RUNE
@@ -1059,5 +1083,5 @@ var/list/sacrificed = list()
//the below calls update_icons() at the end, which will update overlay icons by using the (now updated) cache
user.put_in_hands(new /obj/item/weapon/melee/cultblade(user)) //put in hands or on floor
- del(src)
+ qdel(src)
return
diff --git a/code/game/gamemodes/cult/talisman.dm b/code/game/gamemodes/cult/talisman.dm
index 0f5ab245d1f..d2b881d8913 100644
--- a/code/game/gamemodes/cult/talisman.dm
+++ b/code/game/gamemodes/cult/talisman.dm
@@ -35,7 +35,7 @@
user.take_organ_damage(5, 0)
if(src && src.imbue!="supply" && src.imbue!="runestun")
if(delete)
- del(src)
+ qdel(src)
return
else
user << "You see strange symbols on the paper. Are they supposed to mean something?"
@@ -47,7 +47,7 @@
if(imbue == "runestun")
user.take_organ_damage(5, 0)
call(/obj/effect/rune/proc/runestun)(T)
- del(src)
+ qdel(src)
else
..() ///If its some other talisman, use the generic attack code, is this supposed to work this way?
else
@@ -56,7 +56,7 @@
proc/supply(var/key)
if (!src.uses)
- del(src)
+ qdel(src)
return
var/dat = "There are [src.uses] bloody runes on the parchment. "
@@ -106,7 +106,7 @@
if("soulstone")
new /obj/item/device/soulstone(get_turf(usr))
if("construct")
- new /obj/structure/constructshell(get_turf(usr))
+ new /obj/structure/constructshell/cult(get_turf(usr))
src.uses--
supply()
return
diff --git a/code/game/gamemodes/endgame/endgame.dm b/code/game/gamemodes/endgame/endgame.dm
new file mode 100644
index 00000000000..ed1167dfe74
--- /dev/null
+++ b/code/game/gamemodes/endgame/endgame.dm
@@ -0,0 +1,68 @@
+/**********************
+ * ENDGAME STUFF
+ **********************/
+
+ // Universal State
+ // Handles stuff like space icon_state, constants, etc.
+ // Essentially a policy manager. Once shit hits the fan, this changes its policies.
+ // Called by master controller.
+
+ // Default shit.
+/datum/universal_state
+ // Just for reference, for now.
+ // Might eventually add an observatory job.
+ var/name = "Normal"
+ var/desc = "Nothing seems awry."
+
+ // Sets world.turf, replaces all turfs of type /turf/space.
+ var/space_type = /turf/space
+
+ // Replaces all turfs of type /turf/space/transit
+ var/transit_space_type = /turf/space/transit
+
+ // Chance of a floor or wall getting damaged [0-100]
+ // Simulates stuff getting broken due to molecular bonds decaying.
+ var/decay_rate = 0
+
+// Actually decay the turf.
+/datum/universal_state/proc/DecayTurf(var/turf/T)
+ if(istype(T,/turf/simulated/wall))
+ var/turf/simulated/wall/W=T
+ W.melt()
+ return
+ if(istype(T,/turf/simulated/floor))
+ var/turf/simulated/floor/F=T
+ // Burnt?
+ if(!F.burnt)
+ F.burn_tile()
+ else
+ F.ReplaceWithLattice()
+ return
+
+// Return 0 to cause shuttle call to fail.
+/datum/universal_state/proc/OnShuttleCall(var/mob/user)
+ return 1
+
+// Processed per tick
+/datum/universal_state/proc/OnTurfTick(var/turf/T)
+ if(decay_rate && prob(decay_rate))
+ DecayTurf(T)
+
+// Apply changes when exiting state
+/datum/universal_state/proc/OnExit()
+ // Does nothing by default
+
+// Apply changes when entering state
+/datum/universal_state/proc/OnEnter()
+ // Does nothing by default
+
+// Apply changes to a new turf.
+/datum/universal_state/proc/OnTurfChange(var/turf/NT)
+ return
+
+/proc/SetUniversalState(var/newstate,var/on_exit=1, var/on_enter=1)
+ if(on_exit)
+ universe.OnExit()
+ universe = new newstate
+ if(on_enter)
+ universe.OnEnter()
diff --git a/code/game/gamemodes/endgame/supermatter_cascade/blob.dm b/code/game/gamemodes/endgame/supermatter_cascade/blob.dm
new file mode 100644
index 00000000000..dc315ac5100
--- /dev/null
+++ b/code/game/gamemodes/endgame/supermatter_cascade/blob.dm
@@ -0,0 +1,118 @@
+// QUALITY COPYPASTA
+/turf/unsimulated/wall/supermatter
+ name = "Bluespace"
+ desc = "THE END IS right now actually."
+
+ icon = 'icons/turf/space.dmi'
+ icon_state = "bluespace"
+
+ //luminosity = 5
+ //l_color="#0066FF"
+ layer = 11
+
+ var/spawned=0 // DIR mask
+ var/next_check=0
+ var/list/avail_dirs = list(NORTH,SOUTH,EAST,WEST)
+
+/turf/unsimulated/wall/supermatter/New()
+ ..()
+ processing_turfs.Add(src)
+ next_check = world.time+5 SECONDS
+
+/turf/unsimulated/wall/supermatter/Destroy()
+ processing_turfs.Remove(src)
+ ..()
+
+/turf/unsimulated/wall/supermatter/process()
+ // Only check infrequently.
+ if(next_check>world.time) return
+
+ // No more available directions? Shut down process().
+ if(avail_dirs.len==0)
+ processing_objects.Remove(src)
+ return 1
+
+ // We're checking, reset the timer.
+ next_check = world.time+5 SECONDS
+
+ // Choose a direction.
+ var/pdir = pick(avail_dirs)
+ avail_dirs -= pdir
+ var/turf/T=get_step(src,pdir)
+
+ // EXPAND
+ if(!istype(T,type))
+ // Do pretty fadeout animation for 1s.
+ new /obj/effect/overlay/bluespacify(T)
+ spawn(10)
+ // Nom.
+ for(var/atom/movable/A in T)
+ if(A)
+ if(istype(A,/mob/living))
+ qdel(A)
+ continue
+ else if(istype(A,/mob)) // Observers, AI cameras.
+ continue
+ qdel(A)
+ T.ChangeTurf(type)
+
+ if((spawned & (NORTH|SOUTH|EAST|WEST)) == (NORTH|SOUTH|EAST|WEST))
+ processing_turfs -= src
+ return
+
+/turf/unsimulated/wall/supermatter/attack_generic(mob/user as mob)
+ return attack_hand(user)
+
+/turf/unsimulated/wall/supermatter/attack_robot(mob/user as mob)
+ if(Adjacent(user))
+ return attack_hand(user)
+ else
+ user << "What the fuck are you doing?"
+ return
+
+// /vg/: Don't let ghosts fuck with this.
+/turf/unsimulated/wall/supermatter/attack_ghost(mob/user as mob)
+ user.examinate(src)
+
+/turf/unsimulated/wall/supermatter/attack_ai(mob/user as mob)
+ return user.examinate(src)
+
+/turf/unsimulated/wall/supermatter/attack_hand(mob/user as mob)
+ user.visible_message("\The [user] reaches out and touches \the [src]... And then blinks out of existance.",\
+ "You reach out and touch \the [src]. Everything immediately goes quiet. Your last thought is \"That was not a wise decision.\"",\
+ "You hear an unearthly noise.")
+
+ playsound(src, 'sound/effects/supermatter.ogg', 50, 1)
+
+ Consume(user)
+
+/turf/unsimulated/wall/supermatter/attackby(obj/item/weapon/W as obj, mob/living/user as mob)
+ user.visible_message("\The [user] touches \a [W] to \the [src] as a silence fills the room...",\
+ "You touch \the [W] to \the [src] when everything suddenly goes silent.\"\n\The [W] flashes into dust as you flinch away from \the [src].",\
+ "Everything suddenly goes silent.")
+
+ playsound(src, 'sound/effects/supermatter.ogg', 50, 1)
+
+ user.drop_from_inventory(W)
+ Consume(W)
+
+
+/turf/unsimulated/wall/supermatter/Bumped(atom/AM as mob|obj)
+ if(istype(AM, /mob/living))
+ AM.visible_message("\The [AM] slams into \the [src] inducing a resonance... \his body starts to glow and catch flame before flashing into ash.",\
+ "You slam into \the [src] as your ears are filled with unearthly ringing. Your last thought is \"Oh, fuck.\"",\
+ "You hear an unearthly noise as a wave of heat washes over you.")
+ else
+ AM.visible_message("\The [AM] smacks into \the [src] and rapidly flashes to ash.",\
+ "You hear a loud crack as you are washed with a wave of heat.")
+
+ playsound(src, 'sound/effects/supermatter.ogg', 50, 1)
+
+ Consume(AM)
+
+
+/turf/unsimulated/wall/supermatter/proc/Consume(var/mob/living/user)
+ if(istype(user,/mob/dead/observer))
+ return
+
+ qdel(user)
diff --git a/code/game/gamemodes/endgame/supermatter_cascade/portal.dm b/code/game/gamemodes/endgame/supermatter_cascade/portal.dm
new file mode 100644
index 00000000000..8c826fe22db
--- /dev/null
+++ b/code/game/gamemodes/endgame/supermatter_cascade/portal.dm
@@ -0,0 +1,81 @@
+/*** EXIT PORTAL ***/
+
+/obj/singularity/narsie/large/exit
+ name = "Bluespace Rift"
+ desc = "NO TIME TO EXPLAIN, JUMP IN"
+ icon = 'icons/obj/rift.dmi'
+ icon_state = "rift"
+
+ move_self = 0
+ announce=0
+ narnar=0
+
+ layer=12 // ITS SO BRIGHT
+
+ consume_range = 6
+
+/obj/singularity/narsie/large/exit/New()
+ ..()
+ processing_objects.Add(src)
+
+/obj/singularity/narsie/large/exit/update_icon()
+ overlays = 0
+
+/obj/singularity/narsie/large/exit/process()
+ for(var/mob/M in player_list)
+ if(M.client)
+ M.see_rift(src)
+ eat()
+
+/obj/singularity/narsie/large/exit/acquire(var/mob/food)
+ return
+
+/obj/singularity/narsie/large/exit/consume(const/atom/A)
+ if(!(A.singuloCanEat()))
+ return 0
+
+ if (istype(A, /mob/living/))
+ do_teleport(A, pick(endgame_safespawns)) //dead-on precision
+ else if (isturf(A))
+ var/turf/T = A
+ var/dist = get_dist(T, src)
+ if (dist <= consume_range && T.density)
+ T.density = 0
+
+ for (var/atom/movable/AM in T.contents)
+ if (AM == src) // This is the snowflake.
+ continue
+
+ if (dist <= consume_range)
+ consume(AM)
+ continue
+
+ if (dist > consume_range)
+ if (101 == AM.invisibility)
+ continue
+
+ spawn (0)
+ AM.singularity_pull(src, src.current_size)
+
+
+/mob
+ //thou shall always be able to see the rift
+ var/image/riftimage = null
+
+/mob/proc/see_rift(var/obj/singularity/narsie/large/exit/R)
+ if((R.z == src.z) && (get_dist(R,src) <= (R.consume_range+10)) && !(R in view(src)))
+ if(!riftimage)
+ riftimage = image('icons/obj/rift.dmi',src.loc,"rift",12,1)
+ riftimage.mouse_opacity = 0
+
+ var/new_x = 32 * (R.x - src.x) + R.pixel_x
+ var/new_y = 32 * (R.y - src.y) + R.pixel_y
+ riftimage.pixel_x = new_x
+ riftimage.pixel_y = new_y
+ riftimage.loc = src.loc
+
+ src << riftimage
+
+ else
+ if(riftimage)
+ qdel(riftimage)
diff --git a/code/game/gamemodes/endgame/supermatter_cascade/universe.dm b/code/game/gamemodes/endgame/supermatter_cascade/universe.dm
new file mode 100644
index 00000000000..37b68340a8b
--- /dev/null
+++ b/code/game/gamemodes/endgame/supermatter_cascade/universe.dm
@@ -0,0 +1,139 @@
+
+/datum/universal_state/supermatter_cascade
+ name = "Supermatter Cascade"
+ desc = "Unknown harmonance affecting universal substructure, converting nearby matter to supermatter."
+
+ decay_rate = 5 // 5% chance of a turf decaying on lighting update/airflow (there's no actual tick for turfs)
+
+/datum/universal_state/supermatter_cascade/OnShuttleCall(var/mob/user)
+ if(user)
+ user << "All you hear on the frequency is static and panicked screaming. There will be no shuttle call today."
+ return 0
+
+/datum/universal_state/supermatter_cascade/OnTurfChange(var/turf/T)
+ var/turf/space/spess = T
+ if(istype(spess))
+ spess.overlays += "end01"
+
+/datum/universal_state/supermatter_cascade/DecayTurf(var/turf/T)
+ if(istype(T,/turf/simulated/wall))
+ var/turf/simulated/wall/W=T
+ W.melt()
+ return
+ if(istype(T,/turf/simulated/floor))
+ var/turf/simulated/floor/F=T
+ // Burnt?
+ if(!F.burnt)
+ F.burn_tile()
+ else
+ if(!istype(F,/turf/simulated/floor/plating))
+ F.break_tile_to_plating()
+ return
+
+// Apply changes when entering state
+/datum/universal_state/supermatter_cascade/OnEnter()
+ set background = 1
+ garbage_collector.garbage_collect = 0
+ world << "You are blinded by a brilliant flash of energy."
+
+ world << sound('sound/effects/cascade.ogg')
+
+ for(var/mob/M in player_list)
+ flick("e_flash", M.flash)
+
+ if(emergency_shuttle.can_recall())
+ priority_announcement.Announce("The emergency shuttle has returned due to bluespace distortion.")
+ emergency_shuttle.recall()
+
+ AreaSet()
+ OverlaySet()
+ MiscSet()
+ APCSet()
+ AmbientSet()
+
+ // Disable Nar-Sie.
+ cult.allow_narsie = 0
+ PlayerSet()
+
+ new /obj/singularity/narsie/large/exit(pick(endgame_exits))
+ spawn(rand(30,60) SECONDS)
+ var/txt = {"
+There's been a galaxy-wide electromagnetic pulse. All of our systems are heavily damaged and many personnel are dead or dying. We are seeing increasing indications of the universe itself beginning to unravel.
+
+[station_name()], you are the only facility nearby a bluespace rift, which is near your research outpost. You are hereby directed to enter the rift using all means necessary, quite possibly as the last of your species alive.
+
+You have five minutes before the universe collapses. Good l\[\[###!!!-
+
+AUTOMATED ALERT: Link to [command_name()] lost."}
+ priority_announcement.Announce(txt,"SUPERMATTER CASCADE DETECTED")
+ sleep(5 MINUTES)
+ ticker.declare_completion()
+ ticker.station_explosion_cinematic(0,null) // TODO: Custom cinematic
+
+ world << "Resetting in 30 seconds!"
+
+ feedback_set_details("end_error","Universe ended")
+
+ if(blackbox)
+ blackbox.save_all_data_to_sql()
+
+ sleep(300)
+ log_game("Rebooting due to universal collapse")
+ world.Reboot()
+ return
+
+/datum/universal_state/supermatter_cascade/proc/AreaSet()
+ for(var/area/A in world)
+ if(A.z in config.admin_levels)
+ continue
+ if(istype(A,/area/space))
+ continue
+
+ // Reset all alarms.
+ A.fire = null
+ A.atmos = 1
+ A.atmosalm = 0
+ A.poweralm = 1
+
+ // Slap on random alerts
+ if(prob(25))
+ switch(rand(1,4))
+ if(1)
+ A.fire=1
+ if(2)
+ A.atmosalm=1
+
+ A.updateicon()
+
+/datum/universal_state/supermatter_cascade/proc/OverlaySet()
+ for(var/turf/space/spess in world)
+ spess.overlays += "end01"
+
+/datum/universal_state/supermatter_cascade/proc/AmbientSet()
+ for(var/atom/movable/lighting_overlay/L in world)
+ if(!(L.z in config.admin_levels))
+ L.update_lumcount(0.5, 1, 0)
+
+/datum/universal_state/supermatter_cascade/proc/MiscSet()
+ for (var/obj/machinery/firealarm/alm in world)
+ if (!(alm.stat & BROKEN))
+ alm.ex_act(2)
+
+/datum/universal_state/supermatter_cascade/proc/APCSet()
+ for (var/obj/machinery/power/apc/APC in world)
+ if (!(APC.stat & BROKEN))
+ APC.chargemode = 0
+ if(APC.cell)
+ APC.cell.charge = 0
+ APC.emagged = 1
+ APC.queue_icon_update()
+
+/datum/universal_state/supermatter_cascade/proc/PlayerSet()
+ for(var/datum/mind/M in player_list)
+ if(!istype(M.current,/mob/living))
+ continue
+ if(M.current.stat!=2)
+ M.current.Weaken(10)
+ flick("e_flash", M.current.flash)
+
+ clear_antag_roles(M)
diff --git a/code/game/gamemodes/events.dm b/code/game/gamemodes/events.dm
index feed6092e27..d49247263f9 100644
--- a/code/game/gamemodes/events.dm
+++ b/code/game/gamemodes/events.dm
@@ -49,7 +49,7 @@
var/turf/T = pick(blobstart)
var/obj/effect/bhole/bh = new /obj/effect/bhole( T.loc, 30 )
spawn(rand(50, 300))
- del(bh)
+ qdel(bh)
/*
if(3) //Leaving the code in so someone can try and delag it, but this event can no longer occur randomly, per SoS's request. --NEO
command_alert("Space-time anomalies detected on the station. There is no additional data.", "Anomaly Alert")
@@ -71,7 +71,7 @@
P.icon_state = "anom"
P.name = "wormhole"
spawn(rand(300,600))
- del(P)
+ qdel(P)
*/
if(3)
if((world.time/10)>=3600 && config.ninjas_allowed && !sent_ninja_to_station)//If an hour has passed, relatively speaking. Also, if ninjas are allowed to spawn and if there is not already a ninja for the round.
diff --git a/code/game/gamemodes/events/PortalStorm.dm b/code/game/gamemodes/events/PortalStorm.dm
index 890755d6b8e..6144f3305bb 100644
--- a/code/game/gamemodes/events/PortalStorm.dm
+++ b/code/game/gamemodes/events/PortalStorm.dm
@@ -1,26 +1,26 @@
-/datum/event/portalstorm
-
- Announce()
- command_alert("Subspace disruption detected around the vessel", "Anomaly Alert")
- LongTerm()
-
- var/list/turfs = list( )
- var/turf/picked
-
- for(var/turf/T in world)
- if(T.z < 5 && istype(T,/turf/simulated/floor))
- turfs += T
-
- for(var/turf/T in world)
- if(prob(10) && T.z < 5 && istype(T,/turf/simulated/floor))
- spawn(50+rand(0,3000))
- picked = pick(turfs)
- var/obj/portal/P = new /obj/portal( T )
- P.target = picked
- P.creator = null
- P.icon = 'icons/obj/objects.dmi'
- P.failchance = 0
- P.icon_state = "anom"
- P.name = "wormhole"
- spawn(rand(100,150))
- del(P)
\ No newline at end of file
+/datum/event/portalstorm
+
+ Announce()
+ command_alert("Subspace disruption detected around the vessel", "Anomaly Alert")
+ LongTerm()
+
+ var/list/turfs = list( )
+ var/turf/picked
+
+ for(var/turf/T in world)
+ if(T.z < 5 && istype(T,/turf/simulated/floor))
+ turfs += T
+
+ for(var/turf/T in world)
+ if(prob(10) && T.z < 5 && istype(T,/turf/simulated/floor))
+ spawn(50+rand(0,3000))
+ picked = pick(turfs)
+ var/obj/portal/P = new /obj/portal( T )
+ P.target = picked
+ P.creator = null
+ P.icon = 'icons/obj/objects.dmi'
+ P.failchance = 0
+ P.icon_state = "anom"
+ P.name = "wormhole"
+ spawn(rand(100,150))
+ qdel(P)
diff --git a/code/game/gamemodes/events/black_hole.dm b/code/game/gamemodes/events/black_hole.dm
index 6ff7babbeba..60ab8a692fa 100644
--- a/code/game/gamemodes/events/black_hole.dm
+++ b/code/game/gamemodes/events/black_hole.dm
@@ -1,88 +1,88 @@
-/obj/effect/bhole
- name = "black hole"
- icon = 'icons/obj/objects.dmi'
- desc = "FUCK FUCK FUCK AAAHHH"
- icon_state = "bhole3"
- opacity = 1
- unacidable = 1
- density = 0
- anchored = 1
-
-/obj/effect/bhole/New()
- spawn(4)
- controller()
-
-/obj/effect/bhole/proc/controller()
- while(src)
-
- if(!isturf(loc))
- del(src)
- return
-
- //DESTROYING STUFF AT THE EPICENTER
- for(var/mob/living/M in orange(1,src))
- del(M)
- for(var/obj/O in orange(1,src))
- del(O)
- for(var/turf/simulated/ST in orange(1,src))
- ST.ChangeTurf(/turf/space)
-
- sleep(6)
- grav(10, 4, 10, 0 )
- sleep(6)
- grav( 8, 4, 10, 0 )
- sleep(6)
- grav( 9, 4, 10, 0 )
- sleep(6)
- grav( 7, 3, 40, 1 )
- sleep(6)
- grav( 5, 3, 40, 1 )
- sleep(6)
- grav( 6, 3, 40, 1 )
- sleep(6)
- grav( 4, 2, 50, 6 )
- sleep(6)
- grav( 3, 2, 50, 6 )
- sleep(6)
- grav( 2, 2, 75,25 )
- sleep(6)
-
-
-
- //MOVEMENT
- if( prob(50) )
- src.anchored = 0
- step(src,pick(alldirs))
- src.anchored = 1
-
-/obj/effect/bhole/proc/grav(var/r, var/ex_act_force, var/pull_chance, var/turf_removal_chance)
- if(!isturf(loc)) //blackhole cannot be contained inside anything. Weird stuff might happen
- del(src)
- return
- for(var/t = -r, t < r, t++)
- affect_coord(x+t, y-r, ex_act_force, pull_chance, turf_removal_chance)
- affect_coord(x-t, y+r, ex_act_force, pull_chance, turf_removal_chance)
- affect_coord(x+r, y+t, ex_act_force, pull_chance, turf_removal_chance)
- affect_coord(x-r, y-t, ex_act_force, pull_chance, turf_removal_chance)
- return
-
-/obj/effect/bhole/proc/affect_coord(var/x, var/y, var/ex_act_force, var/pull_chance, var/turf_removal_chance)
- //Get turf at coordinate
- var/turf/T = locate(x, y, z)
- if(isnull(T)) return
-
- //Pulling and/or ex_act-ing movable atoms in that turf
- if( prob(pull_chance) )
- for(var/obj/O in T.contents)
- if(O.anchored)
- O.ex_act(ex_act_force)
- else
- step_towards(O,src)
- for(var/mob/living/M in T.contents)
- step_towards(M,src)
-
- //Destroying the turf
- if( T && istype(T,/turf/simulated) && prob(turf_removal_chance) )
- var/turf/simulated/ST = T
- ST.ChangeTurf(/turf/space)
+/obj/effect/bhole
+ name = "black hole"
+ icon = 'icons/obj/objects.dmi'
+ desc = "FUCK FUCK FUCK AAAHHH"
+ icon_state = "bhole3"
+ opacity = 1
+ unacidable = 1
+ density = 0
+ anchored = 1
+
+/obj/effect/bhole/New()
+ spawn(4)
+ controller()
+
+/obj/effect/bhole/proc/controller()
+ while(src)
+
+ if(!isturf(loc))
+ qdel(src)
+ return
+
+ //DESTROYING STUFF AT THE EPICENTER
+ for(var/mob/living/M in orange(1,src))
+ qdel(M)
+ for(var/obj/O in orange(1,src))
+ qdel(O)
+ for(var/turf/simulated/ST in orange(1,src))
+ ST.ChangeTurf(/turf/space)
+
+ sleep(6)
+ grav(10, 4, 10, 0 )
+ sleep(6)
+ grav( 8, 4, 10, 0 )
+ sleep(6)
+ grav( 9, 4, 10, 0 )
+ sleep(6)
+ grav( 7, 3, 40, 1 )
+ sleep(6)
+ grav( 5, 3, 40, 1 )
+ sleep(6)
+ grav( 6, 3, 40, 1 )
+ sleep(6)
+ grav( 4, 2, 50, 6 )
+ sleep(6)
+ grav( 3, 2, 50, 6 )
+ sleep(6)
+ grav( 2, 2, 75,25 )
+ sleep(6)
+
+
+
+ //MOVEMENT
+ if( prob(50) )
+ src.anchored = 0
+ step(src,pick(alldirs))
+ src.anchored = 1
+
+/obj/effect/bhole/proc/grav(var/r, var/ex_act_force, var/pull_chance, var/turf_removal_chance)
+ if(!isturf(loc)) //blackhole cannot be contained inside anything. Weird stuff might happen
+ qdel(src)
+ return
+ for(var/t = -r, t < r, t++)
+ affect_coord(x+t, y-r, ex_act_force, pull_chance, turf_removal_chance)
+ affect_coord(x-t, y+r, ex_act_force, pull_chance, turf_removal_chance)
+ affect_coord(x+r, y+t, ex_act_force, pull_chance, turf_removal_chance)
+ affect_coord(x-r, y-t, ex_act_force, pull_chance, turf_removal_chance)
+ return
+
+/obj/effect/bhole/proc/affect_coord(var/x, var/y, var/ex_act_force, var/pull_chance, var/turf_removal_chance)
+ //Get turf at coordinate
+ var/turf/T = locate(x, y, z)
+ if(isnull(T)) return
+
+ //Pulling and/or ex_act-ing movable atoms in that turf
+ if( prob(pull_chance) )
+ for(var/obj/O in T.contents)
+ if(O.anchored)
+ O.ex_act(ex_act_force)
+ else
+ step_towards(O,src)
+ for(var/mob/living/M in T.contents)
+ step_towards(M,src)
+
+ //Destroying the turf
+ if( T && istype(T,/turf/simulated) && prob(turf_removal_chance) )
+ var/turf/simulated/ST = T
+ ST.ChangeTurf(/turf/space)
return
\ No newline at end of file
diff --git a/code/game/gamemodes/events/clang.dm b/code/game/gamemodes/events/clang.dm
index 7f4f6f70201..74fb9ee5079 100644
--- a/code/game/gamemodes/events/clang.dm
+++ b/code/game/gamemodes/events/clang.dm
@@ -36,7 +36,7 @@ In my current plan for it, 'solid' will be defined as anything with density == 1
if(clong.density || prob(10))
clong.meteorhit(src)
else
- del(src)
+ qdel(src)
if(clong && prob(25))
src.loc = clong.loc
@@ -81,7 +81,7 @@ In my current plan for it, 'solid' will be defined as anything with density == 1
if (isNotStationLevel(immrod.z))
immrod.z = pick(config.station_levels)
if(immrod.loc == end)
- del(immrod)
+ qdel(immrod)
sleep(10)
for(var/obj/effect/immovablerod/imm in world)
return
diff --git a/code/game/gamemodes/events/dust.dm b/code/game/gamemodes/events/dust.dm
index f2c510b9b98..4e064d8be6f 100644
--- a/code/game/gamemodes/events/dust.dm
+++ b/code/game/gamemodes/events/dust.dm
@@ -37,7 +37,7 @@ The "dust" will damage the hull of the station causin minor hull breaches.
density = 1
anchored = 1
var/strength = 2 //ex_act severity number
- var/life = 2 //how many things we hit before del(src)
+ var/life = 2 //how many things we hit before qdel(src)
weak
strength = 3
@@ -80,10 +80,11 @@ The "dust" will damage the hull of the station causin minor hull breaches.
startx = (TRANSITIONEDGE+1)
endy = rand(TRANSITIONEDGE,world.maxy-TRANSITIONEDGE)
endx = world.maxx-TRANSITIONEDGE
- var/goal = locate(endx, endy, 1)
+ var/z_level = pick(config.station_levels)
+ var/goal = locate(endx, endy, z_level)
src.x = startx
src.y = starty
- src.z = pick(config.station_levels)
+ src.z = z_level
spawn(0)
walk_towards(src, goal, 1)
return
@@ -106,8 +107,7 @@ The "dust" will damage the hull of the station causin minor hull breaches.
life--
if(life <= 0)
walk(src,0)
- spawn(1)
- del(src)
+ qdel(src)
return 0
return
@@ -118,5 +118,5 @@ The "dust" will damage the hull of the station causin minor hull breaches.
ex_act(severity)
- del(src)
+ qdel(src)
return
diff --git a/code/game/gamemodes/events/holidays/Christmas.dm b/code/game/gamemodes/events/holidays/Christmas.dm
index 7ca66789023..9c68ab879ee 100644
--- a/code/game/gamemodes/events/holidays/Christmas.dm
+++ b/code/game/gamemodes/events/holidays/Christmas.dm
@@ -14,7 +14,7 @@
evil_tree.icon_living = evil_tree.icon_state
evil_tree.icon_dead = evil_tree.icon_state
evil_tree.icon_gib = evil_tree.icon_state
- del(xmas)
+ qdel(xmas)
/obj/item/weapon/toy/xmas_cracker
name = "xmas cracker"
diff --git a/code/game/gamemodes/events/wormholes.dm b/code/game/gamemodes/events/wormholes.dm
index 9a8066887b9..a7830a2cb3e 100644
--- a/code/game/gamemodes/events/wormholes.dm
+++ b/code/game/gamemodes/events/wormholes.dm
@@ -59,4 +59,4 @@
P.icon_state = "anom"
P.name = "wormhole"
spawn(rand(300,600))
- del(P)
\ No newline at end of file
+ qdel(P)
\ No newline at end of file
diff --git a/code/game/gamemodes/gameticker.dm b/code/game/gamemodes/gameticker.dm
index 544776d1447..34a57a0768b 100644
--- a/code/game/gamemodes/gameticker.dm
+++ b/code/game/gamemodes/gameticker.dm
@@ -1,11 +1,5 @@
var/global/datum/controller/gameticker/ticker
-#define GAME_STATE_PREGAME 1
-#define GAME_STATE_SETTING_UP 2
-#define GAME_STATE_PLAYING 3
-#define GAME_STATE_FINISHED 4
-
-
/datum/controller/gameticker
var/const/restart_timeout = 600
var/current_state = GAME_STATE_PREGAME
@@ -98,8 +92,8 @@ var/global/datum/controller/gameticker/ticker
src.mode = config.pick_mode(master_mode)
if(!mode_started && !src.mode.can_start())
world << "Unable to start [mode.name]. Not enough players, [mode.required_players] players needed. Reverting to pre-game lobby."
- del(mode)
current_state = GAME_STATE_PREGAME
+ mode = null
job_master.ResetOccupations()
return 0
@@ -116,11 +110,11 @@ var/global/datum/controller/gameticker/ticker
else
src.mode.announce()
+ current_state = GAME_STATE_PLAYING
create_characters() //Create player characters and transfer them
collect_minds()
equip_characters()
data_core.manifest()
- current_state = GAME_STATE_PLAYING
callHook("roundstart")
@@ -135,7 +129,7 @@ var/global/datum/controller/gameticker/ticker
for(var/obj/effect/landmark/start/S in landmarks_list)
//Deleting Startpoints but we need the ai point to AI-ize people later
if (S.name != "AI")
- del(S)
+ qdel(S)
world << "Enjoy the game!"
world << sound('sound/AI/welcome.ogg') // Skie
//Holiday Round-start stuff ~Carn
@@ -161,7 +155,6 @@ var/global/datum/controller/gameticker/ticker
for(var/obj/multiz/ladder/L in world) L.connect() //Lazy hackfix for ladders. TODO: move this to an actual controller. ~ Z
if(config.sql_enabled)
- spawn(3000)
statistic_cycle() // Polls population totals regularly and stores them in an SQL DB -- TLE
return 1
@@ -265,8 +258,8 @@ var/global/datum/controller/gameticker/ticker
//Otherwise if its a verb it will continue on afterwards.
sleep(300)
- if(cinematic) del(cinematic) //end the cinematic
- if(temp_buckle) del(temp_buckle) //release everybody
+ if(cinematic) qdel(cinematic) //end the cinematic
+ if(temp_buckle) qdel(temp_buckle) //release everybody
return
@@ -280,7 +273,7 @@ var/global/datum/controller/gameticker/ticker
continue
else
player.create_character()
- del(player)
+ qdel(player)
proc/collect_minds()
@@ -298,7 +291,7 @@ var/global/datum/controller/gameticker/ticker
if(player.mind.assigned_role != "MODE")
job_master.EquipRank(player, player.mind.assigned_role, 0)
UpdateFactionList(player)
- EquipCustomItems(player)
+ equip_custom_items(player)
if(captainless)
for(var/mob/M in player_list)
if(!istype(M,/mob/new_player))
@@ -424,7 +417,7 @@ var/global/datum/controller/gameticker/ticker
robo.laws.show_laws(world)
if(dronecount)
- world << "There [dronecount>1 ? "were" : "was"] [dronecount] industrious maintenance [dronecount>1 ? "drones" : "drone"] at the end of this round."
+ world << "There [dronecount>1 ? "were" : "was"] [dronecount] industrious maintenance [dronecount>1 ? "drones" : "drone"] at the end of this round."
mode.declare_completion()//To declare normal completion.
diff --git a/code/game/gamemodes/heist/heist.dm b/code/game/gamemodes/heist/heist.dm
index f1de61f2865..7e1ba6d3684 100644
--- a/code/game/gamemodes/heist/heist.dm
+++ b/code/game/gamemodes/heist/heist.dm
@@ -26,6 +26,6 @@ var/global/list/obj/cortical_stacks = list() //Stacks for 'leave nobody behind'
var/area/skipjack = locate(/area/shuttle/skipjack/station)
for (var/mob/living/M in skipjack.contents)
//maybe send the player a message that they've gone home/been kidnapped? Someone responsible for vox lore should write that.
- del(M)
+ qdel(M)
for (var/obj/O in skipjack.contents)
- del(O) //no hiding in lockers or anything
\ No newline at end of file
+ qdel(O) //no hiding in lockers or anything
\ No newline at end of file
diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm
index c523b469f3f..850529661cc 100644
--- a/code/game/gamemodes/malfunction/Malf_Modules.dm
+++ b/code/game/gamemodes/malfunction/Malf_Modules.dm
@@ -89,7 +89,7 @@ rcd light flash thingy on matter drain
V.show_message("\blue You hear a loud electrical buzzing sound!", 2)
spawn(50)
explosion(get_turf(M), 0,1,2,3)
- del(M)
+ qdel(M)
else usr << "Out of uses."
else usr << "That's not a machine."
diff --git a/code/game/gamemodes/meme/meme.dm b/code/game/gamemodes/meme/meme.dm
index 2629b360139..2aa512264df 100644
--- a/code/game/gamemodes/meme/meme.dm
+++ b/code/game/gamemodes/meme/meme.dm
@@ -93,7 +93,7 @@
M.enter_host(first_host.current)
forge_meme_objectives(meme, first_host)
- del original
+ qdel(original)
log_admin("Created [memes.len] memes.")
diff --git a/code/game/gamemodes/meteor/meteors.dm b/code/game/gamemodes/meteor/meteors.dm
index 1edb533daaa..9d18216aa53 100644
--- a/code/game/gamemodes/meteor/meteors.dm
+++ b/code/game/gamemodes/meteor/meteors.dm
@@ -97,6 +97,10 @@
pass_flags = PASSTABLE | PASSGRILLE
power = 2
+/obj/effect/meteor/Destroy()
+ walk(src,0) //this cancels the walk_towards() proc
+ ..()
+
/obj/effect/meteor/Bump(atom/A)
spawn(0)
@@ -111,14 +115,14 @@
!istype(A,/obj/machinery/field_generator) && \
prob(detonation_chance))
explosion(loc, power, power + power_step, power + power_step * 2, power + power_step * 3, 0)
- del(src)
+ qdel(src)
return
/obj/effect/meteor/ex_act(severity)
if (severity < 4)
- del(src)
+ qdel(src)
return
/obj/effect/meteor/big
@@ -136,7 +140,7 @@
if(!istype(A,/obj/machinery/power/emitter) && \
!istype(A,/obj/machinery/field_generator))
if(--src.hits <= 0)
- del(src) //Dont blow up singularity containment if we get stuck there.
+ qdel(src) //Dont blow up singularity containment if we get stuck there.
if (A)
for(var/mob/M in player_list)
@@ -150,11 +154,11 @@
if (--src.hits <= 0)
if(prob(detonation_chance) && !istype(A, /obj/structure/grille))
explosion(loc, power, power + power_step, power + power_step * 2, power + power_step * 3, 0)
- del(src)
+ qdel(src)
return
/obj/effect/meteor/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/pickaxe))
- del(src)
+ qdel(src)
return
- ..()
\ No newline at end of file
+ ..()
diff --git a/code/game/gamemodes/nuclear/pinpointer.dm b/code/game/gamemodes/nuclear/pinpointer.dm
index d26f1a07892..530b9b9567b 100644
--- a/code/game/gamemodes/nuclear/pinpointer.dm
+++ b/code/game/gamemodes/nuclear/pinpointer.dm
@@ -8,7 +8,7 @@
item_state = "electronic"
throw_speed = 4
throw_range = 20
- matter = list("metal" = 500)
+ matter = list(DEFAULT_WALL_MATERIAL = 500)
var/obj/item/weapon/disk/nuclear/the_disk = null
var/active = 0
@@ -48,6 +48,9 @@
if(bomb.timing)
user << "Extreme danger. Arming signal detected. Time remaining: [bomb.timeleft]"
+/obj/item/weapon/pinpointer/Destroy()
+ active = 0
+ ..()
/obj/item/weapon/pinpointer/advpinpointer
name = "Advanced Pinpointer"
diff --git a/code/game/gamemodes/objective.dm b/code/game/gamemodes/objective.dm
index 27236dd8fbf..d13f90d2be4 100644
--- a/code/game/gamemodes/objective.dm
+++ b/code/game/gamemodes/objective.dm
@@ -13,7 +13,7 @@ datum/objective
if(text)
explanation_text = text
- Del()
+ Destroy()
all_objectives -= src
..()
@@ -541,7 +541,7 @@ datum/objective/steal
if (!custom_target) return
var/tmp_obj = new custom_target
var/custom_name = tmp_obj:name
- del(tmp_obj)
+ qdel(tmp_obj)
custom_name = sanitize(input("Enter target name:", "Objective target", custom_name) as text|null)
if (!custom_name) return
target_name = custom_name
@@ -798,7 +798,7 @@ datum/objective/heist/salvage
choose_target()
switch(rand(1,8))
if(1)
- target = "metal"
+ target = DEFAULT_WALL_MATERIAL
target_amount = 300
if(2)
target = "glass"
@@ -916,7 +916,7 @@ datum/objective/heist/salvage
explanation_text = "Summon Nar-Sie via the use of the appropriate rune (Hell join self). It will only work if nine cultists stand on and around it. The convert rune is join blood self."
/datum/objective/cult/eldergod/check_completion()
- return (locate(/obj/machinery/singularity/narsie/large) in machines)
+ return (locate(/obj/singularity/narsie/large) in machines)
/datum/objective/cult/sacrifice
explanation_text = "Conduct a ritual sacrifice for the glory of Nar-Sie."
diff --git a/code/game/gamemodes/sandbox/h_sandbox.dm b/code/game/gamemodes/sandbox/h_sandbox.dm
index 439befdc63a..ad2abb22360 100644
--- a/code/game/gamemodes/sandbox/h_sandbox.dm
+++ b/code/game/gamemodes/sandbox/h_sandbox.dm
@@ -120,7 +120,7 @@ datum/hSB
if("hsbtoolbox")
var/obj/item/weapon/storage/hsb = new/obj/item/weapon/storage/toolbox/mechanical
for(var/obj/item/device/radio/T in hsb)
- del(T)
+ qdel(T)
new/obj/item/weapon/crowbar (hsb)
hsb.loc = usr.loc
if("hsbmedkit")
diff --git a/code/game/gamemodes/setupgame.dm b/code/game/gamemodes/setupgame.dm
index 501335a19ff..3c029d52980 100644
--- a/code/game/gamemodes/setupgame.dm
+++ b/code/game/gamemodes/setupgame.dm
@@ -24,44 +24,6 @@
if (prob(75))
DIFFMUT = rand(0,20)
- /* Old, for reference (so I don't accidentally activate something) - N3X
- var/list/avnums = new/list()
- var/tempnum
-
- avnums.Add(2)
- avnums.Add(12)
- avnums.Add(10)
- avnums.Add(8)
- avnums.Add(4)
- avnums.Add(11)
- avnums.Add(13)
- avnums.Add(6)
-
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- HULKBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- TELEBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- FIREBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- XRAYBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- CLUMSYBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- FAKEBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- DEAFBLOCK = tempnum
- tempnum = pick(avnums)
- avnums.Remove(tempnum)
- BLINDBLOCK = tempnum
- */
var/list/numsToAssign=new()
for(var/i=1;iAI control for \the [src] interface has been disabled."
return STATUS_CLOSE
. = shorted ? STATUS_DISABLED : STATUS_INTERACTIVE
if(. == STATUS_INTERACTIVE)
- var/extra_href = custom_state.href_list(usr)
- // Prevent remote users from altering RCON settings unless they already have access (I realize the risks)
+ var/extra_href = state.href_list(usr)
+ // Prevent remote users from altering RCON settings unless they already have access
if(href_list["rcon"] && extra_href["remote_connection"] && !extra_href["remote_access"])
. = STATUS_UPDATE
- //TODO: Move the rest of if(!locked || extra_href["remote_access"] || usr.isAI()) and hrefs here
-
return min(..(), .)
-/obj/machinery/alarm/Topic(href, href_list, var/nowindow = 0, var/datum/topic_state/custom_state)
- if(..(href, href_list, nowindow, custom_state))
+/obj/machinery/alarm/Topic(href, href_list, var/nowindow = 0, var/datum/topic_state/state)
+ if(..(href, href_list, nowindow, state))
return 1
// hrefs that can always be called -walter0o
@@ -666,7 +664,7 @@
return 1
// hrefs that need the AA unlocked -walter0o
- var/extra_href = custom_state.href_list(usr)
+ var/extra_href = state.href_list(usr)
if(!(locked && !extra_href["remote_connection"]) || extra_href["remote_access"] || usr.isSilicon())
if(href_list["command"])
var/device_id = href_list["id_tag"]
@@ -833,17 +831,16 @@
if(0)
if(istype(W, /obj/item/weapon/airalarm_electronics))
user << "You insert the circuit!"
- del(W)
+ qdel(W)
buildstage = 1
update_icon()
return
else if(istype(W, /obj/item/weapon/wrench))
user << "You remove the fire alarm assembly from the wall!"
- var/obj/item/alarm_frame/frame = new /obj/item/alarm_frame()
- frame.loc = user.loc
+ new /obj/item/frame/air_alarm(get_turf(user))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- del(src)
+ qdel(src)
return ..()
@@ -868,51 +865,7 @@ Just a object used in constructing air alarms
icon_state = "door_electronics"
desc = "Looks like a circuit. Probably is."
w_class = 2.0
- matter = list("metal" = 50, "glass" = 50)
-
-
-/*
-AIR ALARM ITEM
-Handheld air alarm frame, for placing on walls
-Code shamelessly copied from apc_frame
-*/
-/obj/item/alarm_frame
- name = "air alarm frame"
- desc = "Used for building Air Alarms"
- icon = 'icons/obj/monitors.dmi'
- icon_state = "alarm_bitem"
- flags = CONDUCT
-
-/obj/item/alarm_frame/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/wrench))
- new /obj/item/stack/sheet/metal( get_turf(src.loc), 2 )
- del(src)
- return
- ..()
-
-/obj/item/alarm_frame/proc/try_build(turf/on_wall)
- if (get_dist(on_wall,usr)>1)
- return
-
- var/ndir = get_dir(on_wall,usr)
- if (!(ndir in cardinal))
- return
-
- var/turf/loc = get_turf(usr)
- var/area/A = loc.loc
- if (!istype(loc, /turf/simulated/floor))
- usr << "\red Air Alarm cannot be placed on this spot."
- return
- if (A.requires_power == 0 || A.name == "Space")
- usr << "\red Air Alarm cannot be placed in this area."
- return
-
- if(gotwallitem(loc, ndir))
- usr << "\red There's already an item on this wall!"
- return
-
- new /obj/machinery/alarm(loc, ndir, 1)
- del(src)
+ matter = list(DEFAULT_WALL_MATERIAL = 50, "glass" = 50)
/*
FIRE ALARM
@@ -1017,16 +970,15 @@ FIRE ALARM
if(0)
if(istype(W, /obj/item/weapon/firealarm_electronics))
user << "You insert the circuit!"
- del(W)
+ qdel(W)
buildstage = 1
update_icon()
else if(istype(W, /obj/item/weapon/wrench))
user << "You remove the fire alarm assembly from the wall!"
- var/obj/item/firealarm_frame/frame = new /obj/item/firealarm_frame()
- frame.loc = user.loc
+ new /obj/item/frame/fire_alarm(get_turf(user))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- del(src)
+ qdel(src)
return
src.alarm()
@@ -1070,7 +1022,6 @@ FIRE ALARM
var/d2
if (istype(user, /mob/living/carbon/human) || istype(user, /mob/living/silicon))
A = A.loc
- A = A.master
if (A.fire)
d1 = text("Reset - Lockdown", src)
@@ -1137,9 +1088,8 @@ FIRE ALARM
if (!( src.working ))
return
var/area/area = get_area(src)
- for(var/area/A in area.related)
- for(var/obj/machinery/firealarm/FA in A)
- fire_alarm.clearAlarm(loc, FA)
+ for(var/obj/machinery/firealarm/FA in area)
+ fire_alarm.clearAlarm(loc, FA)
update_icon()
return
@@ -1147,9 +1097,8 @@ FIRE ALARM
if (!( src.working))
return
var/area/area = get_area(src)
- for(var/area/A in area.related)
- for(var/obj/machinery/firealarm/FA in A)
- fire_alarm.triggerAlarm(loc, FA, duration)
+ for(var/obj/machinery/firealarm/FA in area)
+ fire_alarm.triggerAlarm(loc, FA, duration)
update_icon()
//playsound(src.loc, 'sound/ambience/signal.ogg', 75, 0)
return
@@ -1190,53 +1139,7 @@ Just a object used in constructing fire alarms
icon_state = "door_electronics"
desc = "A circuit. It has a label on it, it says \"Can handle heat levels up to 40 degrees celsius!\""
w_class = 2.0
- matter = list("metal" = 50, "glass" = 50)
-
-
-/*
-FIRE ALARM ITEM
-Handheld fire alarm frame, for placing on walls
-Code shamelessly copied from apc_frame
-*/
-/obj/item/firealarm_frame
- name = "fire alarm frame"
- desc = "Used for building Fire Alarms"
- icon = 'icons/obj/monitors.dmi'
- icon_state = "fire_bitem"
- flags = CONDUCT
-
-/obj/item/firealarm_frame/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/wrench))
- new /obj/item/stack/sheet/metal( get_turf(src.loc), 2 )
- del(src)
- return
- ..()
-
-/obj/item/firealarm_frame/proc/try_build(turf/on_wall)
- if (get_dist(on_wall,usr)>1)
- return
-
- var/ndir = get_dir(on_wall,usr)
- if (!(ndir in cardinal))
- return
-
- var/turf/loc = get_turf(usr)
- var/area/A = loc.loc
- if (!istype(loc, /turf/simulated/floor))
- usr << "\red Fire Alarm cannot be placed on this spot."
- return
- if (A.requires_power == 0 || A.name == "Space")
- usr << "\red Fire Alarm cannot be placed in this area."
- return
-
- if(gotwallitem(loc, ndir))
- usr << "\red There's already an item on this wall!"
- return
-
- new /obj/machinery/firealarm(loc, ndir, 1)
-
- del(src)
-
+ matter = list(DEFAULT_WALL_MATERIAL = 50, "glass" = 50)
/obj/machinery/partyalarm
name = "\improper PARTY BUTTON"
@@ -1260,8 +1163,6 @@ Code shamelessly copied from apc_frame
user.machine = src
var/area/A = get_area(src)
ASSERT(isarea(A))
- if(A.master)
- A = A.master
var/d1
var/d2
if (istype(user, /mob/living/carbon/human) || istype(user, /mob/living/silicon/ai))
@@ -1300,8 +1201,6 @@ Code shamelessly copied from apc_frame
return
var/area/A = get_area(src)
ASSERT(isarea(A))
- if(A.master)
- A = A.master
A.partyreset()
return
@@ -1310,8 +1209,6 @@ Code shamelessly copied from apc_frame
return
var/area/A = get_area(src)
ASSERT(isarea(A))
- if(A.master)
- A = A.master
A.partyalert()
return
diff --git a/code/game/machinery/atmo_control.dm b/code/game/machinery/atmo_control.dm
index 3c032a6bce5..09e55720a83 100644
--- a/code/game/machinery/atmo_control.dm
+++ b/code/game/machinery/atmo_control.dm
@@ -67,11 +67,10 @@
/obj/machinery/air_sensor/initialize()
set_frequency(frequency)
-/obj/machinery/air_sensor/New()
- ..()
-
+obj/machinery/air_sensor/Destroy()
if(radio_controller)
- set_frequency(frequency)
+ radio_controller.remove_object(src,frequency)
+ ..()
/obj/machinery/computer/general_air_control
icon = 'icons/obj/computer.dmi'
@@ -86,6 +85,11 @@
var/datum/radio_frequency/radio_connection
circuit = /obj/item/weapon/circuitboard/air_management
+obj/machinery/computer/general_air_control/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, frequency)
+ ..()
+
/obj/machinery/computer/general_air_control/attack_hand(mob/user)
if(..(user))
return
@@ -182,7 +186,7 @@
else
output += "ERROR: Can not find input port Search "
-
+
output += "Flow Rate Limit: ---- [round(input_flow_setting, 0.1)] L/s ++++ "
output += " "
@@ -230,7 +234,7 @@ Max Output Pressure: [output_pressure] kPa "}
spawn(1)
src.updateUsrDialog()
return 1
-
+
if(!radio_connection)
return 0
var/datum/signal/signal = new
@@ -239,32 +243,32 @@ Max Output Pressure: [output_pressure] kPa "}
if(href_list["in_refresh_status"])
input_info = null
signal.data = list ("tag" = input_tag, "status" = 1)
- return 1
+ . = 1
if(href_list["in_toggle_injector"])
input_info = null
signal.data = list ("tag" = input_tag, "power_toggle" = 1)
- return 1
+ . = 1
if(href_list["in_set_flowrate"])
input_info = null
signal.data = list ("tag" = input_tag, "set_volume_rate" = "[input_flow_setting]")
- return 1
+ . = 1
if(href_list["out_refresh_status"])
output_info = null
signal.data = list ("tag" = output_tag, "status" = 1)
- return 1
+ . = 1
if(href_list["out_toggle_power"])
output_info = null
signal.data = list ("tag" = output_tag, "power_toggle" = 1)
- return 1
+ . = 1
if(href_list["out_set_pressure"])
output_info = null
signal.data = list ("tag" = output_tag, "set_internal_pressure" = "[pressure_setting]")
- return 1
+ . = 1
signal.data["sigtype"]="command"
radio_connection.post_signal(src, signal, filter = RADIO_ATMOSIA)
@@ -302,7 +306,7 @@ Max Output Pressure: [output_pressure] kPa "}
else
output += "ERROR: Can not find input port Search "
-
+
output += "Flow Rate Limit: ---- [round(input_flow_setting, 0.1)] L/s ++++ "
output += " "
@@ -350,7 +354,7 @@ Min Core Pressure: [pressure_limit] kPa "}
spawn(1)
src.updateUsrDialog()
return 1
-
+
if(!radio_connection)
return 0
var/datum/signal/signal = new
@@ -359,32 +363,32 @@ Min Core Pressure: [pressure_limit] kPa "}
if(href_list["in_refresh_status"])
input_info = null
signal.data = list ("tag" = input_tag, "status" = 1)
- return 1
+ . = 1
if(href_list["in_toggle_injector"])
input_info = null
signal.data = list ("tag" = input_tag, "power_toggle" = 1)
- return 1
+ . = 1
if(href_list["in_set_flowrate"])
input_info = null
signal.data = list ("tag" = input_tag, "set_volume_rate" = "[input_flow_setting]")
- return 1
+ . = 1
if(href_list["out_refresh_status"])
output_info = null
signal.data = list ("tag" = output_tag, "status" = 1)
- return 1
+ . = 1
if(href_list["out_toggle_power"])
output_info = null
signal.data = list ("tag" = output_tag, "power_toggle" = 1)
- return 1
+ . = 1
if(href_list["out_set_pressure"])
output_info = null
signal.data = list ("tag" = output_tag, "set_external_pressure" = "[pressure_setting]", "checks" = 1)
- return 1
+ . = 1
signal.data["sigtype"]="command"
radio_connection.post_signal(src, signal, filter = RADIO_ATMOSIA)
diff --git a/code/game/machinery/atmoalter/area_atmos_computer.dm b/code/game/machinery/atmoalter/area_atmos_computer.dm
index 935feae3e21..984dc44782d 100644
--- a/code/game/machinery/atmoalter/area_atmos_computer.dm
+++ b/code/game/machinery/atmoalter/area_atmos_computer.dm
@@ -2,6 +2,7 @@
name = "Area Air Control"
desc = "A computer used to control the stationary scrubbers and pumps in the area."
icon_state = "area_atmos"
+ light_color = "#e6ffff"
circuit = "/obj/item/weapon/circuitboard/area_atmos"
var/list/connectedscrubbers = new()
@@ -147,14 +148,10 @@
var/turf/T_src = get_turf(src)
if(!T_src.loc) return 0
var/area/A_src = T_src.loc
- if (A_src.master)
- A_src = A_src.master
var/turf/T_scrub = get_turf(scrubber)
if(!T_scrub.loc) return 0
var/area/A_scrub = T_scrub.loc
- if (A_scrub.master)
- A_scrub = A_scrub.master
if(A_scrub != A_src)
return 0
@@ -169,13 +166,11 @@
var/turf/T = get_turf(src)
if(!T.loc) return
var/area/A = T.loc
- if (A.master)
- A = A.master
for(var/obj/machinery/portable_atmospherics/powered/scrubber/huge/scrubber in world )
var/turf/T2 = get_turf(scrubber)
if(T2 && T2.loc)
var/area/A2 = T2.loc
- if(istype(A2) && A2.master && A2.master == A )
+ if(istype(A2) && A2 == A)
connectedscrubbers += scrubber
found = 1
@@ -183,4 +178,4 @@
if(!found)
status = "ERROR: No scrubber found!"
- src.updateUsrDialog()
\ No newline at end of file
+ src.updateUsrDialog()
diff --git a/code/game/machinery/atmoalter/canister.dm b/code/game/machinery/atmoalter/canister.dm
index 9afb27b3cec..59e0f8beac0 100644
--- a/code/game/machinery/atmoalter/canister.dm
+++ b/code/game/machinery/atmoalter/canister.dm
@@ -8,6 +8,7 @@
var/valve_open = 0
var/release_pressure = ONE_ATMOSPHERE
+ var/release_flow_rate = ATMOS_DEFAULT_VOLUME_PUMP //in L/s
var/canister_color = "yellow"
var/can_label = 1
@@ -193,21 +194,15 @@ update_flag
environment = loc.return_air()
var/env_pressure = environment.return_pressure()
- var/pressure_delta = min(release_pressure - env_pressure, (air_contents.return_pressure() - env_pressure)/2)
- //Can not have a pressure delta that would cause environment pressure > tank pressure
+ var/pressure_delta = release_pressure - env_pressure
- var/transfer_moles = 0
if((air_contents.temperature > 0) && (pressure_delta > 0))
- transfer_moles = pressure_delta*environment.volume/(air_contents.temperature * R_IDEAL_GAS_EQUATION)
+ var/transfer_moles = calculate_transfer_moles(air_contents, environment, pressure_delta)
+ transfer_moles = min(transfer_moles, (release_flow_rate/air_contents.volume)*air_contents.total_moles) //flow rate limit
- //Actually transfer the gas
- var/datum/gas_mixture/removed = air_contents.remove(transfer_moles)
-
- if(holding)
- environment.merge(removed)
- else
- loc.assume_air(removed)
- src.update_icon()
+ var/returnval = pump_gas_passive(src, air_contents, environment, transfer_moles)
+ if(returnval >= 0)
+ src.update_icon()
if(air_contents.return_pressure() < 1)
can_label = 1
diff --git a/code/game/machinery/atmoalter/meter.dm b/code/game/machinery/atmoalter/meter.dm
index ad7d55c2aa5..095aec4a24a 100644
--- a/code/game/machinery/atmoalter/meter.dm
+++ b/code/game/machinery/atmoalter/meter.dm
@@ -104,7 +104,7 @@
"\blue You have unfastened \the [src].", \
"You hear ratchet.")
new /obj/item/pipe_meter(src.loc)
- del(src)
+ qdel(src)
// TURF METER - REPORTS A TILE'S AIR CONTENTS
diff --git a/code/game/machinery/atmoalter/portable_atmospherics.dm b/code/game/machinery/atmoalter/portable_atmospherics.dm
index 9308bae64e7..9ba8c2de49a 100644
--- a/code/game/machinery/atmoalter/portable_atmospherics.dm
+++ b/code/game/machinery/atmoalter/portable_atmospherics.dm
@@ -20,6 +20,11 @@
return 1
+/obj/machinery/portable_atmospherics/Destroy()
+ qdel(air_contents)
+ qdel(holding)
+ ..()
+
/obj/machinery/portable_atmospherics/initialize()
. = ..()
spawn()
@@ -35,8 +40,8 @@
else
update_icon()
-/obj/machinery/portable_atmospherics/Del()
- del(air_contents)
+/obj/machinery/portable_atmospherics/Destroy()
+ qdel(air_contents)
..()
@@ -63,6 +68,7 @@
//Perform the connection
connected_port = new_port
connected_port.connected_device = src
+ connected_port.on = 1 //Activate port updates
anchored = 1 //Prevent movement
diff --git a/code/game/machinery/atmoalter/pump.dm b/code/game/machinery/atmoalter/pump.dm
index 9f2c4023b2f..8d80e57e782 100644
--- a/code/game/machinery/atmoalter/pump.dm
+++ b/code/game/machinery/atmoalter/pump.dm
@@ -7,7 +7,10 @@
var/on = 0
var/direction_out = 0 //0 = siphoning, 1 = releasing
- var/target_pressure = 100
+ var/target_pressure = ONE_ATMOSPHERE
+
+ var/pressuremin = 0
+ var/pressuremax = 10 * ONE_ATMOSPHERE
volume = 1000
@@ -19,7 +22,7 @@
/obj/machinery/portable_atmospherics/powered/pump/New()
..()
- cell = new/obj/item/weapon/cell(src)
+ cell = new/obj/item/weapon/cell/apc(src)
var/list/air_mix = StandardAirMix()
src.air_contents.adjust_multi("oxygen", air_mix["oxygen"], "nitrogen", air_mix["nitrogen"])
@@ -75,7 +78,7 @@
output_volume = environment.volume * environment.group_multiplier
air_temperature = environment.temperature? environment.temperature : air_contents.temperature
else
- pressure_delta = target_pressure - air_contents.return_pressure()
+ pressure_delta = environment.return_pressure() - target_pressure
output_volume = air_contents.volume * air_contents.group_multiplier
air_temperature = air_contents.temperature? air_contents.temperature : environment.temperature
@@ -106,64 +109,59 @@
/obj/machinery/portable_atmospherics/powered/pump/return_air()
return air_contents
-/obj/machinery/portable_atmospherics/powered/pump/attack_ai(var/mob/user as mob)
+/obj/machinery/portable_atmospherics/powered/pump/attack_ai(var/mob/user)
+ src.add_hiddenprint(user)
return src.attack_hand(user)
-/obj/machinery/portable_atmospherics/powered/pump/attack_hand(var/mob/user as mob)
+/obj/machinery/portable_atmospherics/powered/pump/attack_ghost(var/mob/user)
+ return src.attack_hand(user)
- user.set_machine(src)
- var/holding_text
+/obj/machinery/portable_atmospherics/powered/pump/attack_hand(var/mob/user)
+ ui_interact(user)
- if(holding)
- holding_text = {" Tank Pressure: [round(holding.air_contents.return_pressure(), 0.01)] kPa
-Remove Tank
-"}
- var/output_text = {"[capitalize(name)]
-Pressure: [round(air_contents.return_pressure(), 0.01)] kPa
-Flow Rate: [round(last_flow_rate, 0.1)] L/s
-Port Status: [(connected_port)?("Connected"):("Disconnected")]
-[holding_text]
-
-Cell Charge: [cell? "[round(cell.percent())]%" : "N/A"] | Load: [round(last_power_draw)] W
-Power Switch: [on?("On"):("Off")]
-Pump Direction: [direction_out?("Out"):("In")]
-Target Pressure: ---- [target_pressure] kPa++++
-
-Close
-"}
+/obj/machinery/portable_atmospherics/powered/pump/ui_interact(mob/user, ui_key = "rcon", datum/nanoui/ui=null, force_open=1)
+ var/list/data[0]
+ data["portConnected"] = connected_port ? 1 : 0
+ data["tankPressure"] = round(air_contents.return_pressure() > 0 ? air_contents.return_pressure() : 0)
+ data["targetpressure"] = round(target_pressure)
+ data["pump_dir"] = direction_out
+ data["minpressure"] = round(pressuremin)
+ data["maxpressure"] = round(pressuremax)
+ data["powerDraw"] = round(last_power_draw)
+ data["cellCharge"] = cell ? cell.charge : 0
+ data["cellMaxCharge"] = cell ? cell.maxcharge : 1
+ data["on"] = on ? 1 : 0
- user << browse(output_text, "window=pump;size=600x300")
- onclose(user, "pump")
+ data["hasHoldingTank"] = holding ? 1 : 0
+ if (holding)
+ data["holdingTank"] = list("name" = holding.name, "tankPressure" = round(holding.air_contents.return_pressure() > 0 ? holding.air_contents.return_pressure() : 0))
- return
+ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open)
+ if (!ui)
+ ui = new(user, src, ui_key, "portpump.tmpl", "Portable Pump", 480, 410, state = physical_state)
+ ui.set_initial_data(data)
+ ui.open()
+ ui.set_auto_update(1)
/obj/machinery/portable_atmospherics/powered/pump/Topic(href, href_list)
- ..()
- if (usr.stat || usr.restrained())
- return
+ if(..())
+ return 1
- if (((get_dist(src, usr) <= 1) && istype(src.loc, /turf)))
- usr.set_machine(src)
+ if(href_list["power"])
+ on = !on
+ . = 1
+ if(href_list["direction"])
+ direction_out = !direction_out
+ . = 1
+ if (href_list["remove_tank"])
+ if(holding)
+ holding.loc = loc
+ holding = null
+ . = 1
+ if (href_list["pressure_adj"])
+ var/diff = text2num(href_list["pressure_adj"])
+ target_pressure = min(10*ONE_ATMOSPHERE, max(0, target_pressure+diff))
+ . = 1
- if(href_list["power"])
- on = !on
-
- if(href_list["direction"])
- direction_out = !direction_out
-
- if (href_list["remove_tank"])
- if(holding)
- holding.loc = loc
- holding = null
-
- if (href_list["pressure_adj"])
- var/diff = text2num(href_list["pressure_adj"])
- target_pressure = min(10*ONE_ATMOSPHERE, max(0, target_pressure+diff))
-
- src.updateUsrDialog()
- src.add_fingerprint(usr)
+ if(.)
update_icon()
- else
- usr << browse(null, "window=pump")
- return
- return
\ No newline at end of file
diff --git a/code/game/machinery/atmoalter/scrubber.dm b/code/game/machinery/atmoalter/scrubber.dm
index d8c23cc5f0d..6e52f88b3eb 100644
--- a/code/game/machinery/atmoalter/scrubber.dm
+++ b/code/game/machinery/atmoalter/scrubber.dm
@@ -13,11 +13,14 @@
power_rating = 7500 //7500 W ~ 10 HP
power_losses = 150
+ var/minrate = 0
+ var/maxrate = 10 * ONE_ATMOSPHERE
+
var/list/scrubbing_gas = list("phoron", "carbon_dioxide", "sleeping_agent", "oxygen_agent_b")
/obj/machinery/portable_atmospherics/powered/scrubber/New()
..()
- cell = new/obj/item/weapon/cell(src)
+ cell = new/obj/item/weapon/cell/apc(src)
/obj/machinery/portable_atmospherics/powered/scrubber/emp_act(severity)
if(stat & (BROKEN|NOPOWER))
@@ -82,63 +85,58 @@
/obj/machinery/portable_atmospherics/powered/scrubber/return_air()
return air_contents
-/obj/machinery/portable_atmospherics/powered/scrubber/attack_ai(var/mob/user as mob)
+/obj/machinery/portable_atmospherics/powered/scrubber/attack_ai(var/mob/user)
+ src.add_hiddenprint(user)
return src.attack_hand(user)
-/obj/machinery/portable_atmospherics/powered/scrubber/attack_hand(var/mob/user as mob)
+/obj/machinery/portable_atmospherics/powered/scrubber/attack_ghost(var/mob/user)
+ return src.attack_hand(user)
- user.set_machine(src)
- var/holding_text
-
- if(holding)
- holding_text = {" Tank Pressure: [round(holding.air_contents.return_pressure(), 0.01)] kPa
-Remove Tank
-"}
- var/output_text = {"[name]
-Pressure: [round(air_contents.return_pressure(), 0.01)] kPa
-Flow Rate: [round(last_flow_rate, 0.1)] L/s
-Port Status: [(connected_port)?("Connected"):("Disconnected")]
-[holding_text]
-
-Cell Charge: [cell? "[round(cell.percent())]%" : "N/A"] | Load: [round(last_power_draw)] W
-Power Switch: [on?("On"):("Off")]
-Flow Rate Regulator: ---- [volume_rate] L/s ++++
-
-
-Close
-"}
-
- user << browse(output_text, "window=scrubber;size=600x300")
- onclose(user, "scrubber")
+/obj/machinery/portable_atmospherics/powered/scrubber/attack_hand(var/mob/user)
+ ui_interact(user)
return
+/obj/machinery/portable_atmospherics/powered/scrubber/ui_interact(mob/user, ui_key = "rcon", datum/nanoui/ui=null, force_open=1)
+ var/list/data[0]
+ data["portConnected"] = connected_port ? 1 : 0
+ data["tankPressure"] = round(air_contents.return_pressure() > 0 ? air_contents.return_pressure() : 0)
+ data["rate"] = round(volume_rate)
+ data["minrate"] = round(minrate)
+ data["maxrate"] = round(maxrate)
+ data["powerDraw"] = round(last_power_draw)
+ data["cellCharge"] = cell ? cell.charge : 0
+ data["cellMaxCharge"] = cell ? cell.maxcharge : 1
+ data["on"] = on ? 1 : 0
+
+ data["hasHoldingTank"] = holding ? 1 : 0
+ if (holding)
+ data["holdingTank"] = list("name" = holding.name, "tankPressure" = round(holding.air_contents.return_pressure() > 0 ? holding.air_contents.return_pressure() : 0))
+
+ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open)
+ if (!ui)
+ ui = new(user, src, ui_key, "portscrubber.tmpl", "Portable Scrubber", 480, 400, state = physical_state)
+ ui.set_initial_data(data)
+ ui.open()
+ ui.set_auto_update(1)
+
+
/obj/machinery/portable_atmospherics/powered/scrubber/Topic(href, href_list)
- ..()
- if (usr.stat || usr.restrained())
- return
+ if(..())
+ return 1
- if (((get_dist(src, usr) <= 1) && istype(src.loc, /turf)))
- usr.set_machine(src)
-
- if(href_list["power"])
- on = !on
-
- if (href_list["remove_tank"])
- if(holding)
- holding.loc = loc
- holding = null
-
- if (href_list["volume_adj"])
- var/diff = text2num(href_list["volume_adj"])
- volume_rate = min(initial(volume_rate), max(0, volume_rate+diff))
-
- src.updateUsrDialog()
- src.add_fingerprint(usr)
- update_icon()
- else
- usr << browse(null, "window=scrubber")
- return
- return
+ if(href_list["power"])
+ on = !on
+ . = 1
+ if (href_list["remove_tank"])
+ if(holding)
+ holding.loc = loc
+ holding = null
+ . = 1
+ if (href_list["volume_adj"])
+ var/diff = text2num(href_list["volume_adj"])
+ volume_rate = Clamp(volume_rate+diff, minrate, maxrate)
+ . = 1
+ update_icon()
//Huge scrubber
diff --git a/code/game/machinery/autolathe.dm b/code/game/machinery/autolathe.dm
index 9b5cfaa526c..40db18e42f6 100644
--- a/code/game/machinery/autolathe.dm
+++ b/code/game/machinery/autolathe.dm
@@ -1,5 +1,5 @@
/obj/machinery/autolathe
- name = "\improper autolathe"
+ name = "autolathe"
desc = "It produces items using metal and glass."
icon_state = "autolathe"
density = 1
@@ -9,8 +9,8 @@
active_power_usage = 2000
var/list/machine_recipes
- var/list/stored_material = list("metal" = 0, "glass" = 0)
- var/list/storage_capacity = list("metal" = 0, "glass" = 0)
+ var/list/stored_material = list(DEFAULT_WALL_MATERIAL = 0, "glass" = 0)
+ var/list/storage_capacity = list(DEFAULT_WALL_MATERIAL = 0, "glass" = 0)
var/show_category = "All"
var/hacked = 0
@@ -140,6 +140,9 @@
if(O.loc != user && !(istype(O,/obj/item/stack)))
return 0
+ if(is_robot_module(O))
+ return 0
+
//Resources are being loaded.
var/obj/item/eating = O
if(!eating.matter)
@@ -189,8 +192,8 @@
var/obj/item/stack/stack = eating
stack.use(max(1, round(total_used/mass_per_sheet))) // Always use at least 1 to prevent infinite materials.
else
- user.drop_item(O)
- del(O)
+ user.remove_from_mob(O)
+ qdel(O)
updateUsrDialog()
return
@@ -279,18 +282,20 @@
for(var/obj/item/weapon/stock_parts/manipulator/M in component_parts)
man_rating += M.rating
- storage_capacity["metal"] = mb_rating * 25000
+ storage_capacity[DEFAULT_WALL_MATERIAL] = mb_rating * 25000
storage_capacity["glass"] = mb_rating * 12500
build_time = 50 / man_rating
mat_efficiency = 1.1 - man_rating * 0.1// Normally, price is 1.25 the amount of material, so this shouldn't go higher than 0.8. Maximum rating of parts is 3
/obj/machinery/autolathe/dismantle()
- var/list/sheets = list("metal" = /obj/item/stack/sheet/metal, "glass" = /obj/item/stack/sheet/glass)
for(var/mat in stored_material)
- var/T = sheets[mat]
- var/obj/item/stack/sheet/S = new T
+ var/material/M = name_to_material[mat]
+ if(!istype(M))
+ continue
+ var/obj/item/stack/sheet/S = new M.stack_type(get_turf(src))
if(stored_material[mat] > S.perunit)
S.amount = round(stored_material[mat] / S.perunit)
- S.loc = loc
+ else
+ qdel(S)
..()
diff --git a/code/game/machinery/autolathe_datums.dm b/code/game/machinery/autolathe_datums.dm
index 68bf61b7f11..3b323cd69fd 100644
--- a/code/game/machinery/autolathe_datums.dm
+++ b/code/game/machinery/autolathe_datums.dm
@@ -16,7 +16,7 @@
recipe.resources = list()
for(var/material in I.matter)
recipe.resources[material] = I.matter[material]*1.25 // More expensive to produce than they are to recycle.
- del(I)
+ qdel(I)
/datum/autolathe/recipe
var/name = "object"
@@ -42,6 +42,11 @@
path = /obj/item/weapon/extinguisher
category = "General"
+/datum/autolathe/recipe/jar
+ name = "jar"
+ path = /obj/item/glass_jar
+ category = "General"
+
/datum/autolathe/recipe/crowbar
name = "crowbar"
path = /obj/item/weapon/crowbar
diff --git a/code/game/machinery/bees_items.dm b/code/game/machinery/bees_items.dm
index 486b46d33c0..05f9231f8a3 100644
--- a/code/game/machinery/bees_items.dm
+++ b/code/game/machinery/bees_items.dm
@@ -20,7 +20,7 @@
for(var/mob/living/simple_animal/bee/B in T)
if(B.feral < 0)
caught_bees += B.strength
- del(B)
+ qdel(B)
user.visible_message("\blue [user] nets some bees.","\blue You net up some of the becalmed bees.")
else
user.visible_message("\red [user] swings at some bees, they don't seem to like it.","\red You swing at some bees, they don't seem to like it.")
diff --git a/code/game/machinery/biogenerator.dm b/code/game/machinery/biogenerator.dm
index 87399b597ac..61ed92d58e5 100644
--- a/code/game/machinery/biogenerator.dm
+++ b/code/game/machinery/biogenerator.dm
@@ -151,7 +151,7 @@
if(I.reagents.get_reagent_amount("nutriment") < 0.1)
points += 1
else points += I.reagents.get_reagent_amount("nutriment") * 10 * eat_eff
- del(I)
+ qdel(I)
if(S)
processing = 1
update_icon()
diff --git a/code/game/machinery/bioprinter.dm b/code/game/machinery/bioprinter.dm
index 48c0edb9846..5a8b25bb84b 100644
--- a/code/game/machinery/bioprinter.dm
+++ b/code/game/machinery/bioprinter.dm
@@ -70,7 +70,7 @@
stored_matter += 50
user.drop_item()
user << "\The [src] processes \the [W]. Levels of stored biomass now: [stored_matter]"
- del(W)
+ qdel(W)
return
// Steel for matter.
else if(prints_prosthetics && istype(W, /obj/item/stack/sheet/metal))
@@ -78,7 +78,7 @@
stored_matter += M.amount * 10
user.drop_item()
user << "\The [src] processes \the [W]. Levels of stored matter now: [stored_matter]"
- del(W)
+ qdel(W)
return
else
return..()
\ No newline at end of file
diff --git a/code/game/machinery/bluespacerelay.dm b/code/game/machinery/bluespacerelay.dm
new file mode 100644
index 00000000000..03d4a311b18
--- /dev/null
+++ b/code/game/machinery/bluespacerelay.dm
@@ -0,0 +1,34 @@
+/obj/machinery/bluespacerelay
+ name = "Emergency Bluespace Relay"
+ desc = "This sends messages through bluespace! Wow!"
+ icon = 'icons/obj/stationobjs.dmi'
+ icon_state = "bspacerelay"
+
+ anchored = 1
+ density = 1
+ use_power = 1
+ var/on = 1
+
+ idle_power_usage = 15000
+ active_power_usage = 15000
+
+/obj/machinery/bluespacerelay/process()
+
+ update_power()
+
+ update_icon()
+
+
+/obj/machinery/bluespacerelay/update_icon()
+ if(on)
+ icon_state = initial(icon_state)
+ else
+ icon_state = "[initial(icon_state)]_off"
+
+/obj/machinery/bluespacerelay/proc/update_power()
+
+ if(stat & (BROKEN|NOPOWER|EMPED))
+ on = 0
+ else
+ on = 1
+
diff --git a/code/game/machinery/bots/bots.dm b/code/game/machinery/bots/bots.dm
index f87ae33ee09..70740901fae 100644
--- a/code/game/machinery/bots/bots.dm
+++ b/code/game/machinery/bots/bots.dm
@@ -3,7 +3,7 @@
/obj/machinery/bot
icon = 'icons/obj/aibots.dmi'
layer = MOB_LAYER
- luminosity = 3
+ light_range = 3
use_power = 0
var/obj/item/weapon/card/id/botcard // the ID card that the bot "holds"
var/on = 1
@@ -15,19 +15,18 @@
var/locked = 1
//var/emagged = 0 //Urist: Moving that var to the general /bot tree as it's used by most bots
-
/obj/machinery/bot/proc/turn_on()
if(stat) return 0
on = 1
- SetLuminosity(initial(luminosity))
+ set_light(initial(light_range))
return 1
/obj/machinery/bot/proc/turn_off()
on = 0
- SetLuminosity(0)
+ set_light(0)
/obj/machinery/bot/proc/explode()
- del(src)
+ qdel(src)
/obj/machinery/bot/proc/healthcheck()
if (src.health <= 0)
@@ -117,7 +116,7 @@
/obj/machinery/bot/emp_act(severity)
var/was_on = on
stat |= EMPED
- var/obj/effect/overlay/pulse2 = new/obj/effect/overlay ( src.loc )
+ var/obj/effect/overlay/pulse2 = PoolOrNew(/obj/effect/overlay, src.loc )
pulse2.icon = 'icons/effects/effects.dmi'
pulse2.icon_state = "empdisable"
pulse2.name = "emp sparks"
@@ -125,7 +124,7 @@
pulse2.set_dir(pick(cardinal))
spawn(10)
- pulse2.delete()
+ qdel(pulse2)
if (on)
turn_off()
spawn(severity*300)
diff --git a/code/game/machinery/bots/cleanbot.dm b/code/game/machinery/bots/cleanbot.dm
deleted file mode 100644
index 4dcb8381521..00000000000
--- a/code/game/machinery/bots/cleanbot.dm
+++ /dev/null
@@ -1,363 +0,0 @@
-//Cleanbot assembly
-/obj/item/weapon/bucket_sensor
- desc = "It's a bucket. With a sensor attached."
- name = "proxy bucket"
- icon = 'icons/obj/aibots.dmi'
- icon_state = "bucket_proxy"
- force = 3.0
- throwforce = 10.0
- throw_speed = 2
- throw_range = 5
- w_class = 3.0
- var/created_name = "Cleanbot"
-
-
-//Cleanbot
-/obj/machinery/bot/cleanbot
- name = "Cleanbot"
- desc = "A little cleaning robot, he looks so excited!"
- icon = 'icons/obj/aibots.dmi'
- icon_state = "cleanbot0"
- layer = 5.0
- density = 0
- anchored = 0
- //weight = 1.0E7
- health = 25
- maxhealth = 25
- var/cleaning = 0
- var/screwloose = 0
- var/oddbutton = 0
- var/blood = 1
- var/list/target_types = list()
- var/obj/effect/decal/cleanable/target
- var/obj/effect/decal/cleanable/oldtarget
- var/oldloc = null
- req_access = list(access_janitor)
- var/path[] = new()
- var/patrol_path[] = null
- var/beacon_freq = 1445 // navigation beacon frequency
- var/closest_dist
- var/closest_loc
- var/failed_steps
- var/should_patrol
- var/next_dest
- var/next_dest_loc
-
-/obj/machinery/bot/cleanbot/New()
- ..()
- src.get_targets()
- src.icon_state = "cleanbot[src.on]"
-
- should_patrol = 1
-
- src.botcard = new /obj/item/weapon/card/id(src)
- src.botcard.access = list(access_janitor, access_maint_tunnels)
-
- src.locked = 0 // Start unlocked so roboticist can set them to patrol.
-
- if(radio_controller)
- radio_controller.add_object(src, beacon_freq, filter = RADIO_NAVBEACONS)
-
-
-/obj/machinery/bot/cleanbot/turn_on()
- . = ..()
- src.icon_state = "cleanbot[src.on]"
- src.updateUsrDialog()
-
-/obj/machinery/bot/cleanbot/turn_off()
- ..()
- if(!isnull(src.target))
- target.targeted_by = null
- src.target = null
- src.oldtarget = null
- src.oldloc = null
- src.icon_state = "cleanbot[src.on]"
- src.path = new()
- src.updateUsrDialog()
-
-/obj/machinery/bot/cleanbot/attack_hand(mob/user as mob)
- . = ..()
- if (.)
- return
- usr.set_machine(src)
- interact(user)
-
-/obj/machinery/bot/cleanbot/interact(mob/user as mob)
- var/dat
- dat += text({"
-Automatic Station Cleaner v1.0
-Status: []
-Behaviour controls are [src.locked ? "locked" : "unlocked"]
-Maintenance panel is [src.open ? "opened" : "closed"]"},
-text("[src.on ? "On" : "Off"]"))
- if(!src.locked || issilicon(user))
- dat += text({" Cleans Blood: [] "}, text("[src.blood ? "Yes" : "No"]"))
- dat += text({" Patrol station: [] "}, text("[src.should_patrol ? "Yes" : "No"]"))
- // dat += text({" Beacon frequency: [] "}, text("[src.beacon_freq]"))
- if(src.open && !src.locked)
- dat += text({"
-Odd looking screw twiddled: []
-Weird button pressed: []"},
-text("[src.screwloose ? "Yes" : "No"]"),
-text("[src.oddbutton ? "Yes" : "No"]"))
-
- user << browse("Cleaner v1.0 controls[dat]", "window=autocleaner")
- onclose(user, "autocleaner")
- return
-
-/obj/machinery/bot/cleanbot/Topic(href, href_list)
- if(..())
- return
- usr.set_machine(src)
- src.add_fingerprint(usr)
- switch(href_list["operation"])
- if("start")
- if (src.on)
- turn_off()
- else
- turn_on()
- if("blood")
- src.blood =!src.blood
- src.get_targets()
- src.updateUsrDialog()
- if("patrol")
- src.should_patrol =!src.should_patrol
- src.patrol_path = null
- src.updateUsrDialog()
- if("freq")
- var/freq = text2num(input("Select frequency for navigation beacons", "Frequnecy", num2text(beacon_freq / 10))) * 10
- if (freq > 0)
- src.beacon_freq = freq
- src.updateUsrDialog()
- if("screw")
- src.screwloose = !src.screwloose
- usr << "You press the weird button."
- src.updateUsrDialog()
-
-/obj/machinery/bot/cleanbot/attackby(obj/item/weapon/W, mob/user as mob)
- if (istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda))
- if(src.allowed(usr) && !open && !emagged)
- src.locked = !src.locked
- user << "You [ src.locked ? "lock" : "unlock"] the [src] behaviour controls."
- else
- if(emagged)
- user << "ERROR"
- if(open)
- user << "Please close the access panel before locking it."
- else
- user << "This [src] doesn't seem to respect your authority."
- else
- return ..()
-
-/obj/machinery/bot/cleanbot/Emag(mob/user as mob)
- ..()
- if(open && !locked)
- if(user) user << "The [src] buzzes and beeps."
- src.oddbutton = 1
- src.screwloose = 1
-
-/obj/machinery/bot/cleanbot/process()
- set background = 1
-
- if(!src.on)
- return
- if(src.cleaning)
- return
-
- if(!src.screwloose && !src.oddbutton && prob(5))
- visible_message("[src] makes an excited beeping booping sound!")
-
- if(src.screwloose && prob(5))
- if(istype(loc,/turf/simulated))
- var/turf/simulated/T = src.loc
- if(T.wet < 1)
- T.wet = 1
- if(T.wet_overlay)
- T.overlays -= T.wet_overlay
- T.wet_overlay = null
- T.wet_overlay = image('icons/effects/water.dmi',T,"wet_floor")
- T.overlays += T.wet_overlay
- spawn(800)
- if (istype(T) && T.wet < 2)
- T.wet = 0
- if(T.wet_overlay)
- T.overlays -= T.wet_overlay
- T.wet_overlay = null
- if(src.oddbutton && prob(5))
- visible_message("Something flies out of [src]. He seems to be acting oddly.")
- var/obj/effect/decal/cleanable/blood/gibs/gib = new /obj/effect/decal/cleanable/blood/gibs(src.loc)
- //gib.streak(list(NORTH, SOUTH, EAST, WEST, NORTHEAST, NORTHWEST, SOUTHEAST, SOUTHWEST))
- src.oldtarget = gib
- if(!src.target || src.target == null)
- for (var/obj/effect/decal/cleanable/D in view(7,src))
- for(var/T in src.target_types)
- if(isnull(D.targeted_by) && istype(D, T) && D != src.oldtarget) // If the mess isn't targeted (D.type == T || D.parent_type == T)
- src.oldtarget = D // or if it is but the bot is gone.
- src.target = D // and it's stuff we clean? Clean it.
- D.targeted_by = src // Claim the mess we are targeting.
- return
-
- if(!src.target || src.target == null)
- if(src.loc != src.oldloc)
- src.oldtarget = null
-
- if (!should_patrol)
- return
-
- if (!patrol_path || patrol_path.len < 1)
- var/datum/radio_frequency/frequency = radio_controller.return_frequency(beacon_freq)
-
- if(!frequency) return
-
- closest_dist = 9999
- closest_loc = null
- next_dest_loc = null
-
- var/datum/signal/signal = new()
- signal.source = src
- signal.transmission_method = 1
- signal.data = list("findbeacon" = "patrol")
- frequency.post_signal(src, signal, filter = RADIO_NAVBEACONS)
- spawn(5)
- if (!next_dest_loc)
- next_dest_loc = closest_loc
- if (next_dest_loc)
- src.patrol_path = AStar(src.loc, next_dest_loc, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 120, id=botcard, exclude=null)
- else
- patrol_move()
-
- return
-
- if(target && path.len == 0)
- spawn(0)
- if(!src || !target) return
- src.path = AStar(src.loc, src.target.loc, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 30, id=botcard)
- if (!path) path = list()
- if(src.path.len == 0)
- src.oldtarget = src.target
- target.targeted_by = null
- src.target = null
- return
- if(src.path.len > 0 && src.target && (src.target != null))
- step_to(src, src.path[1])
- src.path -= src.path[1]
- else if(src.path.len == 1)
- step_to(src, target)
-
- if(src.target && (src.target != null))
- patrol_path = null
- if(src.loc == src.target.loc)
- clean(src.target)
- src.path = new()
- src.target = null
- return
-
- src.oldloc = src.loc
-
-/obj/machinery/bot/cleanbot/proc/patrol_move()
- if (src.patrol_path.len <= 0)
- return
-
- var/next = src.patrol_path[1]
- src.patrol_path -= next
- if (next == src.loc)
- return
-
- var/moved = step_towards(src, next)
- if (!moved)
- failed_steps++
- if (failed_steps > 4)
- patrol_path = null
- next_dest = null
- failed_steps = 0
- else
- failed_steps = 0
-
-/obj/machinery/bot/cleanbot/receive_signal(datum/signal/signal)
- var/recv = signal.data["beacon"]
- var/valid = signal.data["patrol"]
- if(!recv || !valid)
- return
-
- var/dist = get_dist(src, signal.source.loc)
- if (dist < closest_dist && signal.source.loc != src.loc)
- closest_dist = dist
- closest_loc = signal.source.loc
- next_dest = signal.data["next_patrol"]
-
- if (recv == next_dest)
- next_dest_loc = signal.source.loc
- next_dest = signal.data["next_patrol"]
-
-/obj/machinery/bot/cleanbot/proc/get_targets()
- src.target_types = new/list()
-
- target_types += /obj/effect/decal/cleanable/blood/oil
- target_types += /obj/effect/decal/cleanable/vomit
- target_types += /obj/effect/decal/cleanable/crayon
- target_types += /obj/effect/decal/cleanable/liquid_fuel
- target_types += /obj/effect/decal/cleanable/mucus
- target_types += /obj/effect/decal/cleanable/dirt
-
- if(src.blood)
- target_types += /obj/effect/decal/cleanable/blood/
-
-/obj/machinery/bot/cleanbot/proc/clean(var/obj/effect/decal/cleanable/target)
- anchored = 1
- icon_state = "cleanbot-c"
- visible_message("\red [src] begins to clean up the [target]")
- cleaning = 1
- var/cleantime = 50
- if(istype(target,/obj/effect/decal/cleanable/dirt)) // Clean Dirt much faster
- cleantime = 10
- spawn(cleantime)
- if(istype(loc,/turf/simulated))
- var/turf/simulated/f = loc
- f.dirt = 0
- cleaning = 0
- del(target)
- icon_state = "cleanbot[on]"
- anchored = 0
- target = null
-
-/obj/machinery/bot/cleanbot/explode()
- src.on = 0
- src.visible_message("\red [src] blows apart!", 1)
- var/turf/Tsec = get_turf(src)
-
- new /obj/item/weapon/reagent_containers/glass/bucket(Tsec)
-
- new /obj/item/device/assembly/prox_sensor(Tsec)
-
- if (prob(50))
- new /obj/item/robot_parts/l_arm(Tsec)
-
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(3, 1, src)
- s.start()
- del(src)
- return
-
-/obj/item/weapon/bucket_sensor/attackby(var/obj/item/W, mob/user as mob)
- ..()
- if(istype(W, /obj/item/robot_parts/l_arm) || istype(W, /obj/item/robot_parts/r_arm))
- user.drop_item()
- del(W)
- var/turf/T = get_turf(src.loc)
- var/obj/machinery/bot/cleanbot/A = new /obj/machinery/bot/cleanbot(T)
- A.name = src.created_name
- user << "You add the robot arm to the bucket and sensor assembly. Beep boop!"
- user.drop_from_inventory(src)
- del(src)
-
- else if (istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
- if (!t)
- return
- if (!in_range(src, usr) && src.loc != usr)
- return
- src.created_name = t
diff --git a/code/game/machinery/bots/ed209bot.dm b/code/game/machinery/bots/ed209bot.dm
deleted file mode 100644
index a955efaa1f2..00000000000
--- a/code/game/machinery/bots/ed209bot.dm
+++ /dev/null
@@ -1,210 +0,0 @@
-/obj/machinery/bot/secbot/ed209
- name = "ED-209 Security Robot"
- desc = "A security robot. He looks less than thrilled."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "ed2090"
- density = 1
- health = 100
- maxhealth = 100
-
- bot_version = "2.5"
- search_range = 12
- has_laser = 1
-
- preparing_arrest_sounds = new()
- secbot_assembly = /obj/item/weapon/secbot_assembly/ed209_assembly
-
-/obj/item/weapon/secbot_assembly/ed209_assembly
- name = "ED-209 assembly"
- desc = "Some sort of bizarre assembly."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "ed209_frame"
- item_state = "ed209_frame"
- created_name = "ED-209 Security Robot" //To preserve the name if it's a unique securitron I guess
- var/lasercolor = ""
-
-/obj/machinery/bot/secbot/ed209/update_icon()
- if(on && is_attacking)
- src.icon_state = "[lasercolor]ed209-c"
- else
- src.icon_state = "[lasercolor]ed209[src.on]"
-
-/obj/machinery/bot/secbot/ed209/on_explosion(var/turf/Tsec)
- if(!lasercolor)
- var/obj/item/weapon/gun/energy/taser/G = new /obj/item/weapon/gun/energy/taser(Tsec)
- G.power_supply.charge = 0
- else if(lasercolor == "b")
- var/obj/item/weapon/gun/energy/lasertag/blue/G = new (Tsec)
- G.power_supply.charge = 0
- else if(lasercolor == "r")
- var/obj/item/weapon/gun/energy/lasertag/red/G = new (Tsec)
- G.power_supply.charge = 0
- if (prob(50))
- new /obj/item/robot_parts/l_leg(Tsec)
- if (prob(25))
- new /obj/item/robot_parts/r_leg(Tsec)
- if (prob(25))//50% chance for a helmet OR vest
- if (prob(50))
- new /obj/item/clothing/head/helmet(Tsec)
- else
- if(!lasercolor)
- new /obj/item/clothing/suit/armor/vest(Tsec)
- if(lasercolor == "b")
- new /obj/item/clothing/suit/bluetag(Tsec)
- if(lasercolor == "r")
- new /obj/item/clothing/suit/redtag(Tsec)
-
-/obj/item/weapon/secbot_assembly/ed209_assembly/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
-
- if(istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
- if(!t) return
- if(!in_range(src, usr) && src.loc != usr) return
- created_name = t
- return
-
- switch(build_step)
- if(0,1)
- if( istype(W, /obj/item/robot_parts/l_leg) || istype(W, /obj/item/robot_parts/r_leg) )
- user.drop_item()
- del(W)
- build_step++
- user << "You add the robot leg to [src]."
- name = "legs/frame assembly"
- if(build_step == 1)
- item_state = "ed209_leg"
- icon_state = "ed209_leg"
- else
- item_state = "ed209_legs"
- icon_state = "ed209_legs"
-
- if(2)
- if( istype(W, /obj/item/clothing/suit/redtag) )
- lasercolor = "r"
- else if( istype(W, /obj/item/clothing/suit/bluetag) )
- lasercolor = "b"
- if( lasercolor || istype(W, /obj/item/clothing/suit/storage/vest) )
- user.drop_item()
- del(W)
- build_step++
- user << "You add the armor to [src]."
- name = "vest/legs/frame assembly"
- item_state = "[lasercolor]ed209_shell"
- icon_state = "[lasercolor]ed209_shell"
-
- if(3)
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if(WT.remove_fuel(0,user))
- build_step++
- name = "shielded frame assembly"
- user << "You welded the vest to [src]."
- if(4)
- if( istype(W, /obj/item/clothing/head/helmet) )
- user.drop_item()
- del(W)
- build_step++
- user << "You add the helmet to [src]."
- name = "covered and shielded frame assembly"
- item_state = "[lasercolor]ed209_hat"
- icon_state = "[lasercolor]ed209_hat"
-
- if(5)
- if( isprox(W) )
- user.drop_item()
- del(W)
- build_step++
- user << "You add the prox sensor to [src]."
- name = "covered, shielded and sensored frame assembly"
- item_state = "[lasercolor]ed209_prox"
- icon_state = "[lasercolor]ed209_prox"
-
- if(6)
- if(istype(W, /obj/item/stack/cable_coil))
- var/obj/item/stack/cable_coil/C = W
- if (C.get_amount() < 1)
- user << "You need one coil of wire to do wire [src]."
- return
- user << "You start to wire [src]."
- if (do_after(user, 40) && build_step == 6)
- if (C.use(1))
- build_step++
- user << "You wire the ED-209 assembly."
- name = "wired ED-209 assembly"
- return
-
- if(7)
- switch(lasercolor)
- if("b")
- if( !istype(W, /obj/item/weapon/gun/energy/lasertag/blue) )
- return
- name = "bluetag ED-209 assembly"
- if("r")
- if( !istype(W, /obj/item/weapon/gun/energy/lasertag/red) )
- return
- name = "redtag ED-209 assembly"
- if("")
- if( !istype(W, /obj/item/weapon/gun/energy/taser) )
- return
- name = "taser ED-209 assembly"
- else
- return
- build_step++
- user << "You add [W] to [src]."
- src.item_state = "[lasercolor]ed209_taser"
- src.icon_state = "[lasercolor]ed209_taser"
- user.drop_item()
- del(W)
-
- if(8)
- if( istype(W, /obj/item/weapon/screwdriver) )
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 100, 1)
- var/turf/T = get_turf(user)
- user << "Now attaching the gun to the frame..."
- sleep(40)
- if(get_turf(user) == T && build_step == 8)
- build_step++
- name = "armed [name]"
- user << "Taser gun attached."
-
- if(9)
- if( istype(W, /obj/item/weapon/cell) )
- build_step++
- user << "You complete the ED-209."
- var/turf/T = get_turf(src)
- new /obj/machinery/bot/secbot/ed209(T,created_name,lasercolor)
- user.drop_item()
- del(W)
- user.drop_from_inventory(src)
- del(src)
-
-
-/obj/machinery/bot/secbot/ed209/bullet_act(var/obj/item/projectile/Proj)
- if((src.lasercolor == "b") && (src.disabled == 0))
- if(istype(Proj, /obj/item/projectile/beam/lastertag/red))
- src.disabled = 1
- del (Proj)
- sleep(100)
- src.disabled = 0
- else
- ..()
- else if((src.lasercolor == "r") && (src.disabled == 0))
- if(istype(Proj, /obj/item/projectile/beam/lastertag/blue))
- src.disabled = 1
- del (Proj)
- sleep(100)
- src.disabled = 0
- else
- ..()
- else
- ..()
-
-/obj/machinery/bot/secbot/ed209/bluetag/New()//If desired, you spawn red and bluetag bots easily
- new /obj/machinery/bot/secbot/ed209(get_turf(src),null,"b")
- del(src)
-
-
-/obj/machinery/bot/secbot/ed209/redtag/New()
- new /obj/machinery/bot/secbot/ed209(get_turf(src),null,"r")
- del(src)
diff --git a/code/game/machinery/bots/farmbot.dm b/code/game/machinery/bots/farmbot.dm
deleted file mode 100644
index ca32e937ed3..00000000000
--- a/code/game/machinery/bots/farmbot.dm
+++ /dev/null
@@ -1,595 +0,0 @@
-//Farmbots by GauHelldragon - 12/30/2012
-// A new type of buildable aiBot that helps out in hydroponics
-
-// Made by using a robot arm on a water tank and then adding:
-// A plant analyzer, a bucket, a mini-hoe and then a proximity sensor (in that order)
-
-// Will water, weed and fertilize plants that need it
-// When emagged, it will "water", "weed" and "fertilize" humans instead
-// Holds up to 10 fertilizers (only the type dispensed by the machines, not chemistry bottles)
-// It will fill up it's water tank at a sink when low.
-
-// The behavior panel can be unlocked with hydroponics access and be modified to disable certain behaviors
-// By default, it will ignore weeds and mushrooms, but can be set to tend to these types of plants as well.
-
-
-#define FARMBOT_MODE_WATER 1
-#define FARMBOT_MODE_FERTILIZE 2
-#define FARMBOT_MODE_WEED 3
-#define FARMBOT_MODE_REFILL 4
-#define FARMBOT_MODE_WAITING 5
-
-#define FARMBOT_ANIMATION_TIME 25 //How long it takes to use one of the action animations
-#define FARMBOT_EMAG_DELAY 60 //How long of a delay after doing one of the emagged attack actions
-#define FARMBOT_ACTION_DELAY 35 //How long of a delay after doing one of the normal actions
-
-/obj/machinery/bot/farmbot
- name = "Farmbot"
- desc = "The botanist's best friend."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "farmbot0"
- layer = 5.0
- density = 1
- anchored = 0
- health = 50
- maxhealth = 50
- req_access =list(access_hydroponics)
-
- var/Max_Fertilizers = 10
-
- var/setting_water = 1
- var/setting_refill = 1
- var/setting_fertilize = 1
- var/setting_weed = 1
- var/setting_ignoreWeeds = 1
- var/setting_ignoreMushrooms = 1
-
- var/atom/target //Current target, can be a human, a hydroponics tray, or a sink
- var/mode //Which mode is being used, 0 means it is looking for work
-
- var/obj/structure/reagent_dispensers/watertank/tank // the water tank that was used to make it, remains inside the bot.
-
- var/path[] = new() // used for pathing
- var/frustration
-
-/obj/machinery/bot/farmbot/New()
- ..()
- src.icon_state = "farmbot[src.on]"
- spawn (4)
- src.botcard = new /obj/item/weapon/card/id(src)
- src.botcard.access = req_access
-
- if ( !tank ) //Should be set as part of making it... but lets check anyway
- tank = locate(/obj/structure/reagent_dispensers/watertank/) in contents
- if ( !tank ) //An admin must have spawned the farmbot! Better give it a tank.
- tank = new /obj/structure/reagent_dispensers/watertank(src)
-
-/obj/machinery/bot/farmbot/Bump(M as mob|obj) //Leave no door unopened!
- spawn(0)
- if ((istype(M, /obj/machinery/door)) && (!isnull(src.botcard)))
- var/obj/machinery/door/D = M
- if (!istype(D, /obj/machinery/door/firedoor) && D.check_access(src.botcard))
- D.open()
- src.frustration = 0
- return
- return
-
-/obj/machinery/bot/farmbot/turn_on()
- . = ..()
- src.icon_state = "farmbot[src.on]"
- src.updateUsrDialog()
-
-/obj/machinery/bot/farmbot/turn_off()
- ..()
- src.path = new()
- src.icon_state = "farmbot[src.on]"
- src.updateUsrDialog()
-
-/obj/machinery/bot/farmbot/attack_paw(mob/user as mob)
- return attack_hand(user)
-
-
-/obj/machinery/bot/farmbot/proc/get_total_ferts()
- var total_fert = 0
- for (var/obj/item/nutrient/fert in contents)
- total_fert++
- return total_fert
-
-/obj/machinery/bot/farmbot/attack_hand(mob/user as mob)
- . = ..()
- if (.)
- return
- var/dat
- dat += "Automatic Hyrdoponic Assisting Unit v1.0
"
- dat += "Status: [src.on ? "On" : "Off"] "
-
- dat += "Water Tank: "
- if ( tank )
- dat += "\[[tank.reagents.total_volume]/[tank.reagents.maximum_volume]\]"
- else
- dat += "Error: Water Tank not Found"
-
- dat += " Fertilizer Storage: \[[get_total_ferts()]/[Max_Fertilizers]\]"
-
- dat += " Behaviour controls are [src.locked ? "locked" : "unlocked"]"
- if(!src.locked)
- dat += "Watering Controls: "
- dat += " Water Plants : [src.setting_water ? "Yes" : "No"] "
- dat += " Refill Watertank : [src.setting_refill ? "Yes" : "No"] "
- dat += " Fertilizer Controls: "
- dat += " Fertilize Plants : [src.setting_fertilize ? "Yes" : "No"] "
- dat += " Weeding Controls: "
- dat += " Weed Plants : [src.setting_weed ? "Yes" : "No"] "
- dat += " Ignore Weeds : [src.setting_ignoreWeeds ? "Yes" : "No"] "
- dat += "Ignore Mushrooms : [src.setting_ignoreMushrooms ? "Yes" : "No"] "
- dat += ""
-
- user << browse("Farmbot v1.0 controls[dat]", "window=autofarm")
- onclose(user, "autofarm")
- return
-
-/obj/machinery/bot/farmbot/Topic(href, href_list)
- if(..())
- return
- usr.machine = src
- src.add_fingerprint(usr)
- if ((href_list["power"]) && (src.allowed(usr)))
- if (src.on)
- turn_off()
- else
- turn_on()
-
- else if((href_list["water"]) && (!src.locked))
- setting_water = !setting_water
- else if((href_list["refill"]) && (!src.locked))
- setting_refill = !setting_refill
- else if((href_list["fertilize"]) && (!src.locked))
- setting_fertilize = !setting_fertilize
- else if((href_list["weed"]) && (!src.locked))
- setting_weed = !setting_weed
- else if((href_list["ignoreWeed"]) && (!src.locked))
- setting_ignoreWeeds = !setting_ignoreWeeds
- else if((href_list["ignoreMush"]) && (!src.locked))
- setting_ignoreMushrooms = !setting_ignoreMushrooms
- else if (href_list["eject"] )
- flick("farmbot_hatch",src)
- for (var/obj/item/nutrient/fert in contents)
- fert.loc = get_turf(src)
-
- src.updateUsrDialog()
- return
-
-/obj/machinery/bot/farmbot/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda))
- if (src.allowed(user))
- src.locked = !src.locked
- user << "Controls are now [src.locked ? "locked." : "unlocked."]"
- src.updateUsrDialog()
- else
- user << "\red Access denied."
-
- else if (istype(W, /obj/item/nutrient))
- if ( get_total_ferts() >= Max_Fertilizers )
- user << "The fertilizer storage is full!"
- return
- user.drop_item()
- W.loc = src
- user << "You insert [W]."
- flick("farmbot_hatch",src)
- src.updateUsrDialog()
- return
-
- else
- ..()
-
-/obj/machinery/bot/farmbot/Emag(mob/user as mob)
- ..()
- if(user) user << "\red You short out [src]'s plant identifier circuits."
- spawn(0)
- for(var/mob/O in hearers(src, null))
- O.show_message("\red [src] buzzes oddly!", 1)
- flick("farmbot_broke", src)
- src.emagged = 1
- src.on = 1
- src.icon_state = "farmbot[src.on]"
- target = null
- mode = FARMBOT_MODE_WAITING //Give the emagger a chance to get away! 15 seconds should be good.
- spawn(150)
- mode = 0
-
-/obj/machinery/bot/farmbot/explode()
- src.on = 0
- visible_message("\red [src] blows apart!", 1)
- var/turf/Tsec = get_turf(src)
-
- new /obj/item/weapon/minihoe(Tsec)
- new /obj/item/weapon/reagent_containers/glass/bucket(Tsec)
- new /obj/item/device/assembly/prox_sensor(Tsec)
- new /obj/item/device/analyzer/plant_analyzer(Tsec)
-
- if ( tank )
- tank.loc = Tsec
-
- for ( var/obj/item/nutrient/fert in contents )
- if ( prob(50) )
- fert.loc = Tsec
-
- if (prob(50))
- new /obj/item/robot_parts/l_arm(Tsec)
-
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(3, 1, src)
- s.start()
- del(src)
- return
-
-/obj/machinery/bot/farmbot/process()
- set background = 1
-
- if(!src.on)
- return
-
- if ( emagged && prob(1) )
- flick("farmbot_broke", src)
-
- if ( mode == FARMBOT_MODE_WAITING )
- return
-
- if ( !mode || !target || !(target in view(7,src)) ) //Don't bother chasing down targets out of view
-
- mode = 0
- target = null
- if ( !find_target() )
- // Couldn't find a target, wait a while before trying again.
- mode = FARMBOT_MODE_WAITING
- spawn(100)
- mode = 0
- return
-
- if ( mode && target )
- if ( get_dist(target,src) <= 1 || ( emagged && mode == FARMBOT_MODE_FERTILIZE ) )
- // If we are in emagged fertilize mode, we throw the fertilizer, so distance doesn't matter
- frustration = 0
- use_farmbot_item()
- else
- move_to_target()
- return
-
-/obj/machinery/bot/farmbot/proc/use_farmbot_item()
- if ( !target )
- mode = 0
- return 0
-
- if ( emagged && !ismob(target) ) // Humans are plants!
- mode = 0
- target = null
- return 0
-
- if ( !emagged && !istype(target,/obj/machinery/hydroponics) && !istype(target,/obj/structure/sink) ) // Humans are not plants!
- mode = 0
- target = null
- return 0
-
- if ( mode == FARMBOT_MODE_FERTILIZE )
- //Find which fertilizer to use
- var/obj/item/nutrient/fert
- for ( var/obj/item/nutrient/nut in contents )
- fert = nut
- break
- if ( !fert )
- target = null
- mode = 0
- return
- fertilize(fert)
-
- if ( mode == FARMBOT_MODE_WEED )
- weed()
-
- if ( mode == FARMBOT_MODE_WATER )
- water()
-
- if ( mode == FARMBOT_MODE_REFILL )
- refill()
-
-
-
-
-/obj/machinery/bot/farmbot/proc/find_target()
- if ( emagged ) //Find a human and help them!
- for ( var/mob/living/carbon/human/human in view(7,src) )
- if (human.stat == 2)
- continue
-
- var list/options = list(FARMBOT_MODE_WEED)
- if ( get_total_ferts() )
- options.Add(FARMBOT_MODE_FERTILIZE)
- if ( tank && tank.reagents.total_volume >= 1 )
- options.Add(FARMBOT_MODE_WATER)
- mode = pick(options)
- target = human
- return mode
- return 0
- else
- if ( setting_refill && tank && tank.reagents.total_volume < 100 )
- for ( var/obj/structure/sink/source in view(7,src) )
- target = source
- mode = FARMBOT_MODE_REFILL
- return 1
- for ( var/obj/machinery/hydroponics/tray in view(7,src) )
- var newMode = GetNeededMode(tray)
- if ( newMode )
- mode = newMode
- target = tray
- return 1
- return 0
-
-/obj/machinery/bot/farmbot/proc/GetNeededMode(obj/machinery/hydroponics/tray)
- if ( !tray.planted || tray.dead )
- return 0
- if ( tray.myseed.plant_type == 1 && setting_ignoreWeeds )
- return 0
- if ( tray.myseed.plant_type == 2 && setting_ignoreMushrooms )
- return 0
-
- if ( setting_water && tray.waterlevel <= 10 && tank && tank.reagents.total_volume >= 1 )
- return FARMBOT_MODE_WATER
-
- if ( setting_weed && tray.weedlevel >= 5 )
- return FARMBOT_MODE_WEED
-
- if ( setting_fertilize && tray.nutrilevel <= 2 && get_total_ferts() )
- return FARMBOT_MODE_FERTILIZE
-
- return 0
-
-/obj/machinery/bot/farmbot/proc/move_to_target()
- //Mostly copied from medibot code.
-
- if(src.frustration > 8)
- target = null
- mode = 0
- frustration = 0
- src.path = new()
- if(src.target && (src.path.len) && (get_dist(src.target,src.path[src.path.len]) > 2))
- src.path = new()
- if(src.target && src.path.len == 0 && (get_dist(src,src.target) > 1))
- spawn(0)
- var/turf/dest = get_step_towards(target,src) //Can't pathfind to a tray, as it is dense, so pathfind to the spot next to the tray
-
- src.path = AStar(src.loc, dest, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 30,id=botcard)
- if(src.path.len == 0)
- for ( var/turf/spot in orange(1,target) ) //The closest one is unpathable, try the other spots
- if ( spot == dest ) //We already tried this spot
- continue
- if ( spot.density )
- continue
- src.path = AStar(src.loc, spot, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 30,id=botcard)
- src.path = reverselist(src.path)
- if ( src.path.len > 0 )
- break
-
- if ( src.path.len == 0 )
- target = null
- mode = 0
- return
-
- if(src.path.len > 0 && src.target)
- step_to(src, src.path[1])
- src.path -= src.path[1]
- spawn(3)
- if(src.path.len)
- step_to(src, src.path[1])
- src.path -= src.path[1]
-
- if(src.path.len > 8 && src.target)
- src.frustration++
-
-
-/obj/machinery/bot/farmbot/proc/fertilize(obj/item/nutrient/fert)
- if ( !fert )
- target = null
- mode = 0
- return 0
-
- if ( emagged ) // Warning, hungry humans detected: throw fertilizer at them
- spawn(0)
- fert.loc = src.loc
- fert.throw_at(target, 16, 3, src)
- src.visible_message("\red [src] launches [fert.name] at [target.name]!")
- flick("farmbot_broke", src)
- spawn (FARMBOT_EMAG_DELAY)
- mode = 0
- target = null
- return 1
-
- else // feed them plants~
- var /obj/machinery/hydroponics/tray = target
- tray.nutrilevel = 10
- tray.yieldmod = fert.yieldmod
- tray.mutmod = fert.mutmod
- del fert
- tray.updateicon()
- icon_state = "farmbot_fertile"
- mode = FARMBOT_MODE_WAITING
-
- spawn (FARMBOT_ACTION_DELAY)
- mode = 0
- target = null
- spawn (FARMBOT_ANIMATION_TIME)
- icon_state = "farmbot[src.on]"
- return 1
-
-/obj/machinery/bot/farmbot/proc/weed()
- icon_state = "farmbot_hoe"
- spawn(FARMBOT_ANIMATION_TIME)
- icon_state = "farmbot[src.on]"
-
- if ( emagged ) // Warning, humans infested with weeds!
- mode = FARMBOT_MODE_WAITING
- spawn(FARMBOT_EMAG_DELAY)
- mode = 0
-
- if ( prob(50) ) // better luck next time little guy
- src.visible_message("\red [src] swings wildly at [target] with a minihoe, missing completely!")
-
- else // yayyy take that weeds~
- var/attackVerb = pick("slashed", "sliced", "cut", "clawed")
- var /mob/living/carbon/human/human = target
-
- src.visible_message("\red [src] [attackVerb] [human]!")
- var/damage = 5
- var/dam_zone = pick("chest", "l_hand", "r_hand", "l_leg", "r_leg")
- var/datum/organ/external/affecting = human.get_organ(ran_zone(dam_zone))
- var/armor = human.run_armor_check(affecting, "melee")
- human.apply_damage(damage,BRUTE,affecting,armor,sharp=1,edge=1)
-
- else // warning, plants infested with weeds!
- mode = FARMBOT_MODE_WAITING
- spawn(FARMBOT_ACTION_DELAY)
- mode = 0
-
- var /obj/machinery/hydroponics/tray = target
- tray.weedlevel = 0
- tray.updateicon()
-
-/obj/machinery/bot/farmbot/proc/water()
- if ( !tank || tank.reagents.total_volume < 1 )
- mode = 0
- target = null
- return 0
-
- icon_state = "farmbot_water"
- spawn(FARMBOT_ANIMATION_TIME)
- icon_state = "farmbot[src.on]"
-
- if ( emagged ) // warning, humans are thirsty!
- var splashAmount = min(70,tank.reagents.total_volume)
- src.visible_message("\red [src] splashes [target] with a bucket of water!")
- playsound(src.loc, 'sound/effects/slosh.ogg', 25, 1)
- if ( prob(50) )
- tank.reagents.reaction(target, TOUCH) //splash the human!
- else
- tank.reagents.reaction(target.loc, TOUCH) //splash the human's roots!
- spawn(5)
- tank.reagents.remove_any(splashAmount)
-
- mode = FARMBOT_MODE_WAITING
- spawn(FARMBOT_EMAG_DELAY)
- mode = 0
- else
- var /obj/machinery/hydroponics/tray = target
- var/b_amount = tank.reagents.get_reagent_amount("water")
- if(b_amount > 0 && tray.waterlevel < 100)
- if(b_amount + tray.waterlevel > 100)
- b_amount = 100 - tray.waterlevel
- tank.reagents.remove_reagent("water", b_amount)
- tray.waterlevel += b_amount
- playsound(src.loc, 'sound/effects/slosh.ogg', 25, 1)
-
- // Toxicity dilutation code. The more water you put in, the lesser the toxin concentration.
- tray.toxic -= round(b_amount/4)
- if (tray.toxic < 0 ) // Make sure it won't go overboard
- tray.toxic = 0
-
- tray.updateicon()
- mode = FARMBOT_MODE_WAITING
- spawn(FARMBOT_ACTION_DELAY)
- mode = 0
-
-/obj/machinery/bot/farmbot/proc/refill()
- if ( !tank || !tank.reagents.total_volume > 600 || !istype(target,/obj/structure/sink) )
- mode = 0
- target = null
- return
-
- mode = FARMBOT_MODE_WAITING
- playsound(src.loc, 'sound/effects/slosh.ogg', 25, 1)
- src.visible_message("\blue [src] starts filling it's tank from [target].")
- spawn(300)
- src.visible_message("\blue [src] finishes filling it's tank.")
- src.mode = 0
- tank.reagents.add_reagent("water", tank.reagents.maximum_volume - tank.reagents.total_volume )
- playsound(src.loc, 'sound/effects/slosh.ogg', 25, 1)
-
-
-/obj/item/weapon/farmbot_arm_assembly
- name = "water tank/robot arm assembly"
- desc = "A water tank with a robot arm permanently grafted to it."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "water_arm"
- var/build_step = 0
- var/created_name = "Farmbot" //To preserve the name if it's a unique farmbot I guess
- w_class = 3.0
-
- New()
- ..()
- spawn(4) // If an admin spawned it, it won't have a watertank it, so lets make one for em!
- var tank = locate(/obj/structure/reagent_dispensers/watertank) in contents
- if( !tank )
- new /obj/structure/reagent_dispensers/watertank(src)
-
-
-/obj/structure/reagent_dispensers/watertank/attackby(var/obj/item/robot_parts/S, mob/user as mob)
-
- if ((!istype(S, /obj/item/robot_parts/l_arm)) && (!istype(S, /obj/item/robot_parts/r_arm)))
- ..()
- return
-
- //Making a farmbot!
-
- var/obj/item/weapon/farmbot_arm_assembly/A = new /obj/item/weapon/farmbot_arm_assembly
-
- A.loc = src.loc
- user << "You add the robot arm to the [src]"
- src.loc = A //Place the water tank into the assembly, it will be needed for the finished bot
- user.remove_from_mob(S)
- del(S)
-
-/obj/item/weapon/farmbot_arm_assembly/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
- if((istype(W, /obj/item/device/analyzer/plant_analyzer)) && (!src.build_step))
- src.build_step++
- user << "You add the plant analyzer to [src]!"
- src.name = "farmbot assembly"
- user.remove_from_mob(W)
- del(W)
-
- else if(( istype(W, /obj/item/weapon/reagent_containers/glass/bucket)) && (src.build_step == 1))
- src.build_step++
- user << "You add a bucket to [src]!"
- src.name = "farmbot assembly with bucket"
- user.remove_from_mob(W)
- del(W)
-
- else if(( istype(W, /obj/item/weapon/minihoe)) && (src.build_step == 2))
- src.build_step++
- user << "You add a minihoe to [src]!"
- src.name = "farmbot assembly with bucket and minihoe"
- user.remove_from_mob(W)
- del(W)
-
- else if((isprox(W)) && (src.build_step == 3))
- src.build_step++
- user << "You complete the Farmbot! Beep boop."
- var/obj/machinery/bot/farmbot/S = new /obj/machinery/bot/farmbot
- for ( var/obj/structure/reagent_dispensers/watertank/wTank in src.contents )
- wTank.loc = S
- S.tank = wTank
- S.loc = get_turf(src)
- S.name = src.created_name
- user.remove_from_mob(W)
- del(W)
- del(src)
-
- else if(istype(W, /obj/item/weapon/pen))
- var/t = input(user, "Enter new robot name", src.name, src.created_name) as text
- t = sanitize(t, MAX_NAME_LEN)
- if (!t)
- return
- if (!in_range(src, usr) && src.loc != usr)
- return
-
- src.created_name = t
-
-/obj/item/weapon/farmbot_arm_assembly/attack_hand(mob/user as mob)
- return //it's a converted watertank, no you cannot pick it up and put it in your backpack
\ No newline at end of file
diff --git a/code/game/machinery/bots/floorbot.dm b/code/game/machinery/bots/floorbot.dm
deleted file mode 100644
index b3c1c0376f8..00000000000
--- a/code/game/machinery/bots/floorbot.dm
+++ /dev/null
@@ -1,449 +0,0 @@
-//Floorbot assemblies
-/obj/item/weapon/toolbox_tiles
- desc = "It's a toolbox with tiles sticking out the top"
- name = "tiles and toolbox"
- icon = 'icons/obj/aibots.dmi'
- icon_state = "toolbox_tiles"
- force = 3.0
- throwforce = 10.0
- throw_speed = 2
- throw_range = 5
- w_class = 3.0
- var/created_name = "Floorbot"
-
-/obj/item/weapon/toolbox_tiles_sensor
- desc = "It's a toolbox with tiles sticking out the top and a sensor attached"
- name = "tiles, toolbox and sensor arrangement"
- icon = 'icons/obj/aibots.dmi'
- icon_state = "toolbox_tiles_sensor"
- force = 3.0
- throwforce = 10.0
- throw_speed = 2
- throw_range = 5
- w_class = 3.0
- var/created_name = "Floorbot"
-
-//Floorbot
-/obj/machinery/bot/floorbot
- name = "Floorbot"
- desc = "A little floor repairing robot, he looks so excited!"
- icon = 'icons/obj/aibots.dmi'
- icon_state = "floorbot0"
- layer = 5.0
- density = 0
- anchored = 0
- health = 25
- maxhealth = 25
- //weight = 1.0E7
- var/amount = 10
- var/repairing = 0
- var/improvefloors = 0
- var/eattiles = 0
- var/maketiles = 0
- var/turf/target
- var/turf/oldtarget
- var/oldloc = null
- req_access = list(access_construction)
- var/path[] = new()
- var/targetdirection
-
-
-/obj/machinery/bot/floorbot/New()
- ..()
- src.updateicon()
-
-/obj/machinery/bot/floorbot/turn_on()
- . = ..()
- src.updateicon()
- src.updateUsrDialog()
-
-/obj/machinery/bot/floorbot/turn_off()
- ..()
- src.target = null
- src.oldtarget = null
- src.oldloc = null
- src.updateicon()
- src.path = new()
- src.updateUsrDialog()
-
-/obj/machinery/bot/floorbot/attack_hand(mob/user as mob)
- . = ..()
- if (.)
- return
- usr.set_machine(src)
- interact(user)
-
-/obj/machinery/bot/floorbot/interact(mob/user as mob)
- var/dat
- dat += "Automatic Station Floor Repairer v1.0
"
- dat += "Status: [src.on ? "On" : "Off"] "
- dat += "Maintenance panel is [src.open ? "opened" : "closed"] "
- dat += "Tiles left: [src.amount] "
- dat += "Behvaiour controls are [src.locked ? "locked" : "unlocked"] "
- if(!src.locked || issilicon(user))
- dat += "Improves floors: [src.improvefloors ? "Yes" : "No"] "
- dat += "Finds tiles: [src.eattiles ? "Yes" : "No"] "
- dat += "Make singles pieces of metal into tiles when empty: [src.maketiles ? "Yes" : "No"] "
- var/bmode
- if (src.targetdirection)
- bmode = dir2text(src.targetdirection)
- else
- bmode = "Disabled"
- dat += "
Bridge Mode : [bmode] "
-
- user << browse("Repairbot v1.0 controls[dat]", "window=autorepair")
- onclose(user, "autorepair")
- return
-
-
-/obj/machinery/bot/floorbot/attackby(var/obj/item/W , mob/user as mob)
- if(istype(W, /obj/item/stack/tile/plasteel))
- var/obj/item/stack/tile/plasteel/T = W
- if(src.amount >= 50)
- return
- var/loaded = min(50-src.amount, T.get_amount())
- T.use(loaded)
- src.amount += loaded
- user << "You load [loaded] tiles into the floorbot. He now contains [src.amount] tiles."
- src.updateicon()
- else if(istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda))
- if(src.allowed(usr) && !open && !emagged)
- src.locked = !src.locked
- user << "You [src.locked ? "lock" : "unlock"] the [src] behaviour controls."
- else
- if(emagged)
- user << "ERROR"
- if(open)
- user << "Please close the access panel before locking it."
- else
- user << "Access denied."
- src.updateUsrDialog()
- else
- ..()
-
-/obj/machinery/bot/floorbot/Emag(mob/user as mob)
- ..()
- if(open && !locked)
- if(user) user << "The [src] buzzes and beeps."
-
-/obj/machinery/bot/floorbot/Topic(href, href_list)
- if(..())
- return
- usr.set_machine(src)
- src.add_fingerprint(usr)
- switch(href_list["operation"])
- if("start")
- if (src.on)
- turn_off()
- else
- turn_on()
- if("improve")
- src.improvefloors = !src.improvefloors
- src.updateUsrDialog()
- if("tiles")
- src.eattiles = !src.eattiles
- src.updateUsrDialog()
- if("make")
- src.maketiles = !src.maketiles
- src.updateUsrDialog()
- if("bridgemode")
- switch(src.targetdirection)
- if(null)
- targetdirection = 1
- if(1)
- targetdirection = 2
- if(2)
- targetdirection = 4
- if(4)
- targetdirection = 8
- if(8)
- targetdirection = null
- else
- targetdirection = null
- src.updateUsrDialog()
-
-/obj/machinery/bot/floorbot/process()
- set background = 1
-
- if(!src.on)
- return
- if(src.repairing)
- return
- var/list/floorbottargets = list()
- if(src.amount <= 0 && ((src.target == null) || !src.target))
- if(src.eattiles)
- for(var/obj/item/stack/tile/plasteel/T in view(7, src))
- if(T != src.oldtarget && !(target in floorbottargets))
- src.oldtarget = T
- src.target = T
- break
- if(src.target == null || !src.target)
- if(src.maketiles)
- if(src.target == null || !src.target)
- for(var/obj/item/stack/sheet/metal/M in view(7, src))
- if(!(M in floorbottargets) && M != src.oldtarget && M.amount == 1 && !(istype(M.loc, /turf/simulated/wall)))
- src.oldtarget = M
- src.target = M
- break
- else
- return
- if(prob(5))
- visible_message("[src] makes an excited booping beeping sound!")
-
- if((!src.target || src.target == null) && emagged < 2)
- if(targetdirection != null)
- /*
- for (var/turf/space/D in view(7,src))
- if(!(D in floorbottargets) && D != src.oldtarget) // Added for bridging mode -- TLE
- if(get_dir(src, D) == targetdirection)
- src.oldtarget = D
- src.target = D
- break
- */
- var/turf/T = get_step(src, targetdirection)
- if(istype(T, /turf/space))
- src.oldtarget = T
- src.target = T
- if(!src.target || src.target == null)
- for (var/turf/space/D in view(7,src))
- if(!(D in floorbottargets) && D != src.oldtarget && (D.loc.name != "Space"))
- src.oldtarget = D
- src.target = D
- break
- if((!src.target || src.target == null ) && src.improvefloors)
- for (var/turf/simulated/floor/F in view(7,src))
- if(!(F in floorbottargets) && F != src.oldtarget && F.icon_state == "Floor1" && !(istype(F, /turf/simulated/floor/plating)))
- src.oldtarget = F
- src.target = F
- break
- if((!src.target || src.target == null) && src.eattiles)
- for(var/obj/item/stack/tile/plasteel/T in view(7, src))
- if(!(T in floorbottargets) && T != src.oldtarget)
- src.oldtarget = T
- src.target = T
- break
-
- if((!src.target || src.target == null) && emagged == 2)
- if(!src.target || src.target == null)
- for (var/turf/simulated/floor/D in view(7,src))
- if(!(D in floorbottargets) && D != src.oldtarget && D.floor_type)
- src.oldtarget = D
- src.target = D
- break
-
- if(!src.target || src.target == null)
- if(src.loc != src.oldloc)
- src.oldtarget = null
- return
-
- if(src.target && (src.target != null) && src.path.len == 0)
- spawn(0)
- if(!istype(src.target, /turf/))
- src.path = AStar(src.loc, src.target.loc, /turf/proc/AdjacentTurfsSpace, /turf/proc/Distance, 0, 30, id=botcard)
- else
- src.path = AStar(src.loc, src.target, /turf/proc/AdjacentTurfsSpace, /turf/proc/Distance, 0, 30, id=botcard)
- if (!src.path) src.path = list()
- if(src.path.len == 0)
- src.oldtarget = src.target
- src.target = null
- return
- if(src.path.len > 0 && src.target && (src.target != null))
- step_to(src, src.path[1])
- src.path -= src.path[1]
- else if(src.path.len == 1)
- step_to(src, target)
- src.path = new()
-
- if(src.loc == src.target || src.loc == src.target.loc)
- if(istype(src.target, /obj/item/stack/tile/plasteel))
- src.eattile(src.target)
- else if(istype(src.target, /obj/item/stack/sheet/metal))
- src.maketile(src.target)
- else if(istype(src.target, /turf/) && emagged < 2)
- repair(src.target)
- else if(emagged == 2 && istype(src.target,/turf/simulated/floor))
- var/turf/simulated/floor/F = src.target
- src.anchored = 1
- src.repairing = 1
- if(prob(90))
- F.break_tile_to_plating()
- else
- F.ReplaceWithLattice()
- visible_message("\red [src] makes an excited booping sound.")
- spawn(50)
- src.amount ++
- src.anchored = 0
- src.repairing = 0
- src.target = null
- src.path = new()
- return
-
- src.oldloc = src.loc
-
-
-/obj/machinery/bot/floorbot/proc/repair(var/turf/target)
- if(istype(target, /turf/space/))
- if(target.loc.name == "Space")
- return
- else if(!istype(target, /turf/simulated/floor))
- return
- if(src.amount <= 0)
- return
- src.anchored = 1
- src.icon_state = "floorbot-c"
- if(istype(target, /turf/space/))
- visible_message("\red [src] begins to repair the hole")
- var/obj/item/stack/tile/plasteel/T = new /obj/item/stack/tile/plasteel
- src.repairing = 1
- spawn(50)
- T.build(src.loc)
- src.repairing = 0
- src.amount -= 1
- src.updateicon()
- src.anchored = 0
- src.target = null
- else
- visible_message("\red [src] begins to improve the floor.")
- src.repairing = 1
- spawn(50)
- src.loc.icon_state = "floor"
- src.repairing = 0
- src.amount -= 1
- src.updateicon()
- src.anchored = 0
- src.target = null
-
-/obj/machinery/bot/floorbot/proc/eattile(var/obj/item/stack/tile/plasteel/T)
- if(!istype(T, /obj/item/stack/tile/plasteel))
- return
- visible_message("\red [src] begins to collect tiles.")
- src.repairing = 1
- spawn(20)
- if(isnull(T))
- src.target = null
- src.repairing = 0
- return
- if(src.amount + T.get_amount() > 50)
- var/i = 50 - src.amount
- src.amount += i
- T.use(i)
- else
- src.amount += T.get_amount()
- del(T)
- src.updateicon()
- src.target = null
- src.repairing = 0
-
-/obj/machinery/bot/floorbot/proc/maketile(var/obj/item/stack/sheet/metal/M)
- if(!istype(M, /obj/item/stack/sheet/metal))
- return
- if(M.get_amount() > 1)
- return
- visible_message("\red [src] begins to create tiles.")
- src.repairing = 1
- spawn(20)
- if(isnull(M))
- src.target = null
- src.repairing = 0
- return
- var/obj/item/stack/tile/plasteel/T = new /obj/item/stack/tile/plasteel
- T.amount = 4
- T.loc = M.loc
- del(M)
- src.target = null
- src.repairing = 0
-
-/obj/machinery/bot/floorbot/proc/updateicon()
- if(src.amount > 0)
- src.icon_state = "floorbot[src.on]"
- else
- src.icon_state = "floorbot[src.on]e"
-
-/obj/machinery/bot/floorbot/explode()
- src.on = 0
- src.visible_message("\red [src] blows apart!", 1)
- var/turf/Tsec = get_turf(src)
-
- var/obj/item/weapon/storage/toolbox/mechanical/N = new /obj/item/weapon/storage/toolbox/mechanical(Tsec)
- N.contents = list()
-
- new /obj/item/device/assembly/prox_sensor(Tsec)
-
- if (prob(50))
- new /obj/item/robot_parts/l_arm(Tsec)
-
- while (amount)//Dumps the tiles into the appropriate sized stacks
- if(amount >= 16)
- var/obj/item/stack/tile/plasteel/T = new (Tsec)
- T.amount = 16
- amount -= 16
- else
- var/obj/item/stack/tile/plasteel/T = new (Tsec)
- T.amount = src.amount
- amount = 0
-
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(3, 1, src)
- s.start()
- del(src)
- return
-
-
-/obj/item/weapon/storage/toolbox/mechanical/attackby(var/obj/item/stack/tile/plasteel/T, mob/user as mob)
- if(!istype(T, /obj/item/stack/tile/plasteel))
- ..()
- return
- if(src.contents.len >= 1)
- user << "They wont fit in as there is already stuff inside."
- return
- if(user.s_active)
- user.s_active.close(user)
- if (T.use(10))
- var/obj/item/weapon/toolbox_tiles/B = new /obj/item/weapon/toolbox_tiles
- user.put_in_hands(B)
- user << "You add the tiles into the empty toolbox. They protrude from the top."
- user.drop_from_inventory(src)
- del(src)
- else
- user << "You need 10 floortiles for a floorbot."
- return
-
-/obj/item/weapon/toolbox_tiles/attackby(var/obj/item/W, mob/user as mob)
- ..()
- if(isprox(W))
- del(W)
- var/obj/item/weapon/toolbox_tiles_sensor/B = new /obj/item/weapon/toolbox_tiles_sensor()
- B.created_name = src.created_name
- user.put_in_hands(B)
- user << "You add the sensor to the toolbox and tiles!"
- user.drop_from_inventory(src)
- del(src)
-
- else if (istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
- if (!t)
- return
- if (!in_range(src, usr) && src.loc != usr)
- return
-
- src.created_name = t
-
-/obj/item/weapon/toolbox_tiles_sensor/attackby(var/obj/item/W, mob/user as mob)
- ..()
- if(istype(W, /obj/item/robot_parts/l_arm) || istype(W, /obj/item/robot_parts/r_arm))
- del(W)
- var/turf/T = get_turf(user.loc)
- var/obj/machinery/bot/floorbot/A = new /obj/machinery/bot/floorbot(T)
- A.name = src.created_name
- user << "You add the robot arm to the odd looking toolbox assembly! Boop beep!"
- user.drop_from_inventory(src)
- del(src)
- else if (istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
-
- if (!t)
- return
- if (!in_range(src, usr) && src.loc != usr)
- return
-
- src.created_name = t
diff --git a/code/game/machinery/bots/medbot.dm b/code/game/machinery/bots/medbot.dm
deleted file mode 100644
index 8ce3522707f..00000000000
--- a/code/game/machinery/bots/medbot.dm
+++ /dev/null
@@ -1,596 +0,0 @@
-//MEDBOT
-//MEDBOT PATHFINDING
-//MEDBOT ASSEMBLY
-
-
-/obj/machinery/bot/medbot
- name = "Medibot"
- desc = "A little medical robot. He looks somewhat underwhelmed."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "medibot0"
- layer = 5.0
- density = 0
- anchored = 0
- health = 20
- maxhealth = 20
- req_access =list(access_medical)
- var/stunned = 0 //It can be stunned by tasers. Delicate circuits.
-//var/emagged = 0
- var/list/botcard_access = list(access_medical)
- var/obj/item/weapon/reagent_containers/glass/reagent_glass = null //Can be set to draw from this for reagents.
- var/skin = null //Set to "tox", "ointment" or "o2" for the other two firstaid kits.
- var/frustration = 0
- var/path[] = new()
- var/mob/living/carbon/patient = null
- var/mob/living/carbon/oldpatient = null
- var/oldloc = null
- var/last_found = 0
- var/last_newpatient_speak = 0 //Don't spam the "HEY I'M COMING" messages
- var/currently_healing = 0
- var/injection_amount = 15 //How much reagent do we inject at a time?
- var/heal_threshold = 10 //Start healing when they have this much damage in a category
- var/use_beaker = 0 //Use reagents in beaker instead of default treatment agents.
- //Setting which reagents to use to treat what by default. By id.
- var/treatment_brute = "tricordrazine"
- var/treatment_oxy = "tricordrazine"
- var/treatment_fire = "tricordrazine"
- var/treatment_tox = "tricordrazine"
- var/treatment_virus = "spaceacillin"
- var/declare_treatment = 0 //When attempting to treat a patient, should it notify everyone wearing medhuds?
- var/shut_up = 0 //self explanatory :)
-
-/obj/machinery/bot/medbot/mysterious
- name = "Mysterious Medibot"
- desc = "International Medibot of mystery."
- skin = "bezerk"
- treatment_oxy = "dexalinp"
- treatment_brute = "bicaridine"
- treatment_fire = "kelotane"
- treatment_tox = "anti_toxin"
-
-/obj/item/weapon/firstaid_arm_assembly
- name = "first aid/robot arm assembly"
- desc = "A first aid kit with a robot arm permanently grafted to it."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "firstaid_arm"
- var/build_step = 0
- var/created_name = "Medibot" //To preserve the name if it's a unique medbot I guess
- var/skin = null //Same as medbot, set to tox or ointment for the respective kits.
- w_class = 3.0
-
- New()
- ..()
- spawn(5)
- if(src.skin)
- src.overlays += image('icons/obj/aibots.dmi', "kit_skin_[src.skin]")
-
-
-/obj/machinery/bot/medbot/New()
- ..()
- src.icon_state = "medibot[src.on]"
-
- spawn(4)
- if(src.skin)
- src.overlays += image('icons/obj/aibots.dmi', "medskin_[src.skin]")
-
- src.botcard = new /obj/item/weapon/card/id(src)
- if(isnull(src.botcard_access) || (src.botcard_access.len < 1))
- src.botcard.access = list(access_medical, access_morgue, access_surgery, access_chemistry, access_virology, access_genetics)
- else
- src.botcard.access = src.botcard_access
-
-/obj/machinery/bot/medbot/turn_on()
- . = ..()
- src.icon_state = "medibot[src.on]"
- src.updateUsrDialog()
-
-/obj/machinery/bot/medbot/turn_off()
- ..()
- src.patient = null
- src.oldpatient = null
- src.oldloc = null
- src.path = new()
- src.currently_healing = 0
- src.last_found = world.time
- src.icon_state = "medibot[src.on]"
- src.updateUsrDialog()
-
-/obj/machinery/bot/medbot/attack_hand(mob/user as mob)
- . = ..()
- if (.)
- return
- var/dat
- dat += "Automatic Medical Unit v1.0
"
- dat += "Status: [src.on ? "On" : "Off"] "
- dat += "Maintenance panel is [src.open ? "opened" : "closed"] "
- dat += "Beaker: "
- if (src.reagent_glass)
- dat += "Loaded \[[src.reagent_glass.reagents.total_volume]/[src.reagent_glass.reagents.maximum_volume]\]"
- else
- dat += "None Loaded"
- dat += " Behaviour controls are [src.locked ? "locked" : "unlocked"]"
- if(!src.locked || issilicon(user))
- dat += "Healing Threshold: "
- dat += "-- "
- dat += "- "
- dat += "[src.heal_threshold] "
- dat += "+ "
- dat += "++"
- dat += " "
-
- dat += "Injection Level: "
- dat += "- "
- dat += "[src.injection_amount] "
- dat += "+ "
- dat += " "
-
- dat += "Reagent Source: "
- dat += "[src.use_beaker ? "Loaded Beaker (When available)" : "Internal Synthesizer"] "
-
- dat += "Treatment report is [src.declare_treatment ? "on" : "off"]. Toggle "
-
- dat += "The speaker switch is [src.shut_up ? "off" : "on"]. Toggle "
-
- user << browse("Medibot v1.0 controls[dat]", "window=automed")
- onclose(user, "automed")
- return
-
-/obj/machinery/bot/medbot/Topic(href, href_list)
- if(..())
- return
- usr.set_machine(src)
- src.add_fingerprint(usr)
- if ((href_list["power"]) && (src.allowed(usr)))
- if (src.on)
- turn_off()
- else
- turn_on()
-
- else if((href_list["adj_threshold"]) && (!src.locked || issilicon(usr)))
- var/adjust_num = text2num(href_list["adj_threshold"])
- src.heal_threshold += adjust_num
- if(src.heal_threshold < 5)
- src.heal_threshold = 5
- if(src.heal_threshold > 75)
- src.heal_threshold = 75
-
- else if((href_list["adj_inject"]) && (!src.locked || issilicon(usr)))
- var/adjust_num = text2num(href_list["adj_inject"])
- src.injection_amount += adjust_num
- if(src.injection_amount < 5)
- src.injection_amount = 5
- if(src.injection_amount > 15)
- src.injection_amount = 15
-
- else if((href_list["use_beaker"]) && (!src.locked || issilicon(usr)))
- src.use_beaker = !src.use_beaker
-
- else if (href_list["eject"] && (!isnull(src.reagent_glass)))
- if(!src.locked)
- src.reagent_glass.loc = get_turf(src)
- src.reagent_glass = null
- else
- usr << "You cannot eject the beaker because the panel is locked."
-
- else if ((href_list["togglevoice"]) && (!src.locked || issilicon(usr)))
- src.shut_up = !src.shut_up
-
- else if ((href_list["declaretreatment"]) && (!src.locked || issilicon(usr)))
- src.declare_treatment = !src.declare_treatment
-
- src.updateUsrDialog()
- return
-
-/obj/machinery/bot/medbot/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda))
- if (src.allowed(user) && !open && !emagged)
- src.locked = !src.locked
- user << "Controls are now [src.locked ? "locked." : "unlocked."]"
- src.updateUsrDialog()
- else
- if(emagged)
- user << "ERROR"
- if(open)
- user << "Please close the access panel before locking it."
- else
- user << "Access denied."
-
- else if (istype(W, /obj/item/weapon/reagent_containers/glass))
- if(src.locked)
- user << "You cannot insert a beaker because the panel is locked."
- return
- if(!isnull(src.reagent_glass))
- user << "There is already a beaker loaded."
- return
-
- user.drop_item()
- W.loc = src
- src.reagent_glass = W
- user << "You insert [W]."
- src.updateUsrDialog()
- return
-
- else
- ..()
- if (health < maxhealth && !istype(W, /obj/item/weapon/screwdriver) && W.force)
- step_to(src, (get_step_away(src,user)))
-
-/obj/machinery/bot/medbot/Emag(mob/user as mob)
- ..()
- if(open && !locked)
- if(user) user << "You short out [src]'s reagent synthesis circuits."
- spawn(0)
- for(var/mob/O in hearers(src, null))
- O.show_message("\red [src] buzzes oddly!", 1)
- flick("medibot_spark", src)
- src.patient = null
- if(user) src.oldpatient = user
- src.currently_healing = 0
- src.last_found = world.time
- src.anchored = 0
- src.emagged = 2
- src.on = 1
- src.icon_state = "medibot[src.on]"
-
-/obj/machinery/bot/medbot/process()
- set background = 1
-
- if(!src.on)
- src.stunned = 0
- return
-
- if(src.stunned)
- src.icon_state = "medibota"
- src.stunned--
-
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
-
- if(src.stunned <= 0)
- src.icon_state = "medibot[src.on]"
- src.stunned = 0
- return
-
- if(src.frustration > 8)
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
- src.last_found = world.time
- src.path = new()
-
- if(!src.patient)
- if(!src.shut_up && prob(1))
- var/message = pick("Radar, put a mask on!","There's always a catch, and it's the best there is.","I knew it, I should've been a plastic surgeon.","What kind of medbay is this? Everyone's dropping like dead flies.","Delicious!")
- src.speak(message)
-
- for (var/mob/living/carbon/C in view(7,src)) //Time to find a patient!
- if ((C.stat == 2) || !istype(C, /mob/living/carbon/human))
- continue
-
- if ((C == src.oldpatient) && (world.time < src.last_found + 100))
- continue
-
- if(src.assess_patient(C))
- src.patient = C
- src.oldpatient = C
- src.last_found = world.time
- if((src.last_newpatient_speak + 300) < world.time) //Don't spam these messages!
- var/message = pick("Hey, [C.name]! Hold on, I'm coming.","Wait [C.name]! I want to help!","[C.name], you appear to be injured!")
- src.speak(message)
- src.visible_message("[src] points at [C.name]!")
- src.last_newpatient_speak = world.time
- break
- else
- continue
-
-
- if(src.patient && Adjacent(patient))
- if(!src.currently_healing)
- src.currently_healing = 1
- src.frustration = 0
- src.medicate_patient(src.patient)
- return
-
- else if(src.patient && (src.path.len) && (get_dist(src.patient,src.path[src.path.len]) > 2))
- src.path = new()
- src.currently_healing = 0
- src.last_found = world.time
-
- if(src.patient && src.path.len == 0 && (get_dist(src,src.patient) > 1))
- spawn(0)
- src.path = AStar(src.loc, get_turf(src.patient), /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 30,id=botcard)
- if (!path) path = list()
- if(src.path.len == 0)
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
- src.last_found = world.time
- return
-
- if(src.path.len > 0 && src.patient)
- step_to(src, src.path[1])
- src.path -= src.path[1]
- spawn(3)
- if(src.path.len)
- step_to(src, src.path[1])
- src.path -= src.path[1]
-
- if(src.path.len > 8 && src.patient)
- src.frustration++
-
- return
-
-/obj/machinery/bot/medbot/proc/assess_patient(mob/living/carbon/C as mob)
- //Time to see if they need medical help!
- if(C.stat == 2)
- return 0 //welp too late for them!
-
- if(C.suiciding)
- return 0 //Kevorkian school of robotic medical assistants.
-
- if(src.emagged == 2) //Everyone needs our medicine. (Our medicine is toxins)
- return 1
-
- //If they're injured, we're using a beaker, and don't have one of our WONDERCHEMS.
- if((src.reagent_glass) && (src.use_beaker) && ((C.getBruteLoss() >= heal_threshold) || (C.getToxLoss() >= heal_threshold) || (C.getToxLoss() >= heal_threshold) || (C.getOxyLoss() >= (heal_threshold + 15))))
- for(var/datum/reagent/R in src.reagent_glass.reagents.reagent_list)
- if(!C.reagents.has_reagent(R))
- return 1
- continue
-
- //They're injured enough for it!
- if((C.getBruteLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_brute)))
- return 1 //If they're already medicated don't bother!
-
- if((C.getOxyLoss() >= (15 + heal_threshold)) && (!C.reagents.has_reagent(src.treatment_oxy)))
- return 1
-
- if((C.getFireLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_fire)))
- return 1
-
- if((C.getToxLoss() >= heal_threshold) && (!C.reagents.has_reagent(src.treatment_tox)))
- return 1
-
-
- for(var/datum/disease/D in C.viruses)
- if((D.stage > 1) || (D.spread_type == AIRBORNE))
-
- if (!C.reagents.has_reagent(src.treatment_virus))
- return 1 //STOP DISEASE FOREVER
-
- return 0
-
-/obj/machinery/bot/medbot/proc/medicate_patient(mob/living/carbon/C as mob)
- if(!src.on)
- return
-
- if(!istype(C))
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
- src.last_found = world.time
- return
-
- if(C.stat == 2)
- var/death_message = pick("No! NO!","Live, damnit! LIVE!","I...I've never lost a patient before. Not today, I mean.")
- src.speak(death_message)
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
- src.last_found = world.time
- return
-
- var/reagent_id = null
-
- //Use whatever is inside the loaded beaker. If there is one.
- if((src.use_beaker) && (src.reagent_glass) && (src.reagent_glass.reagents.total_volume))
- reagent_id = "internal_beaker"
-
- if(src.emagged == 2) //Emagged! Time to poison everybody.
- reagent_id = "toxin"
-
- var/virus = 0
- for(var/datum/disease/D in C.viruses)
- virus = 1
-
- if (!reagent_id && (virus))
- if(!C.reagents.has_reagent(src.treatment_virus))
- reagent_id = src.treatment_virus
-
- if (!reagent_id && (C.getBruteLoss() >= heal_threshold))
- if(!C.reagents.has_reagent(src.treatment_brute))
- reagent_id = src.treatment_brute
-
- if (!reagent_id && (C.getOxyLoss() >= (15 + heal_threshold)))
- if(!C.reagents.has_reagent(src.treatment_oxy))
- reagent_id = src.treatment_oxy
-
- if (!reagent_id && (C.getFireLoss() >= heal_threshold))
- if(!C.reagents.has_reagent(src.treatment_fire))
- reagent_id = src.treatment_fire
-
- if (!reagent_id && (C.getToxLoss() >= heal_threshold))
- if(!C.reagents.has_reagent(src.treatment_tox))
- reagent_id = src.treatment_tox
-
- if(!reagent_id) //If they don't need any of that they're probably cured!
- src.oldpatient = src.patient
- src.patient = null
- src.currently_healing = 0
- src.last_found = world.time
- var/message = pick("All patched up!","An apple a day keeps me away.","Feel better soon!")
- src.speak(message)
- return
- else
- src.icon_state = "medibots"
- visible_message("\red [src] is trying to inject [src.patient]!")
- spawn(30)
- if ((get_dist(src, src.patient) <= 1) && (src.on))
- if((reagent_id == "internal_beaker") && (src.reagent_glass) && (src.reagent_glass.reagents.total_volume))
- src.reagent_glass.reagents.trans_to(src.patient,src.injection_amount) //Inject from beaker instead.
- src.reagent_glass.reagents.reaction(src.patient, 2)
- else
- src.patient.reagents.add_reagent(reagent_id,src.injection_amount)
- visible_message("\red [src] injects [src.patient] with the syringe!")
-
- if(declare_treatment)
- var/area/location = get_area(src)
- broadcast_medical_hud_message("[src.name] is treating [C] in [location]", src)
-
- src.icon_state = "medibot[src.on]"
- src.currently_healing = 0
- return
-
-// src.speak(reagent_id)
- reagent_id = null
- return
-
-
-/obj/machinery/bot/medbot/proc/speak(var/message)
- if((!src.on) || (!message))
- return
- visible_message("[src] beeps, \"[message]\"")
- return
-
-/obj/machinery/bot/medbot/bullet_act(var/obj/item/projectile/Proj)
- if(Proj.taser_effect)
- src.stunned = min(stunned+10,20)
- ..()
-
-/obj/machinery/bot/medbot/explode()
- src.on = 0
- visible_message("\red [src] blows apart!", 1)
- var/turf/Tsec = get_turf(src)
-
- new /obj/item/weapon/storage/firstaid(Tsec)
-
- new /obj/item/device/assembly/prox_sensor(Tsec)
-
- new /obj/item/device/healthanalyzer(Tsec)
-
- if(src.reagent_glass)
- src.reagent_glass.loc = Tsec
- src.reagent_glass = null
-
- if (prob(50))
- new /obj/item/robot_parts/l_arm(Tsec)
-
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(3, 1, src)
- s.start()
- del(src)
- return
-
-/obj/machinery/bot/medbot/Bump(M as mob|obj) //Leave no door unopened!
- if ((istype(M, /obj/machinery/door)) && (!isnull(src.botcard)))
- var/obj/machinery/door/D = M
- if (!istype(D, /obj/machinery/door/firedoor) && D.check_access(src.botcard) && !istype(D,/obj/machinery/door/blast))
- D.open()
- src.frustration = 0
- else if ((istype(M, /mob/living/)) && (!src.anchored))
- src.loc = M:loc
- src.frustration = 0
- return
-
-/* terrible
-/obj/machinery/bot/medbot/Bumped(atom/movable/M as mob|obj)
- spawn(0)
- if (M)
- var/turf/T = get_turf(src)
- M:loc = T
-*/
-
-/*
- * Pathfinding procs, allow the medibot to path through doors it has access to.
- */
-
-//Pretty ugh
-/*
-/turf/proc/AdjacentTurfsAllowMedAccess()
- var/L[] = new()
- for(var/turf/t in oview(src,1))
- if(!t.density)
- if(!LinkBlocked(src, t) && !TurfBlockedNonWindowNonDoor(t,get_access("Medical Doctor")))
- L.Add(t)
- return L
-
-
-//It isn't blocked if we can open it, man.
-/proc/TurfBlockedNonWindowNonDoor(turf/loc, var/list/access)
- for(var/obj/O in loc)
- if(O.density && !istype(O, /obj/structure/window) && !istype(O, /obj/machinery/door))
- return 1
-
- if (O.density && (istype(O, /obj/machinery/door)) && (access.len))
- var/obj/machinery/door/D = O
- for(var/req in D.req_access)
- if(!(req in access)) //doesn't have this access
- return 1
-
- return 0
-*/
-
-/*
- * Medbot Assembly -- Can be made out of all three medkits.
- */
-
-/obj/item/weapon/storage/firstaid/attackby(var/obj/item/robot_parts/S, mob/user as mob)
-
- if ((!istype(S, /obj/item/robot_parts/l_arm)) && (!istype(S, /obj/item/robot_parts/r_arm)))
- ..()
- return
-
- //Making a medibot!
- if(src.contents.len >= 1)
- user << "You need to empty [src] out first."
- return
-
- var/obj/item/weapon/firstaid_arm_assembly/A = new /obj/item/weapon/firstaid_arm_assembly
- if(istype(src,/obj/item/weapon/storage/firstaid/fire))
- A.skin = "ointment"
- else if(istype(src,/obj/item/weapon/storage/firstaid/toxin))
- A.skin = "tox"
- else if(istype(src,/obj/item/weapon/storage/firstaid/o2))
- A.skin = "o2"
-
- del(S)
- user.put_in_hands(A)
- user << "You add the robot arm to the first aid kit."
- user.drop_from_inventory(src)
- del(src)
-
-
-/obj/item/weapon/firstaid_arm_assembly/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
- if(istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
- if (!t)
- return
- if (!in_range(src, usr) && src.loc != usr)
- return
- src.created_name = t
- else
- switch(build_step)
- if(0)
- if(istype(W, /obj/item/device/healthanalyzer))
- user.drop_item()
- del(W)
- src.build_step++
- user << "You add the health sensor to [src]."
- src.name = "First aid/robot arm/health analyzer assembly"
- src.overlays += image('icons/obj/aibots.dmi', "na_scanner")
-
- if(1)
- if(isprox(W))
- user.drop_item()
- del(W)
- src.build_step++
- user << "You complete the Medibot! Beep boop."
- var/turf/T = get_turf(src)
- var/obj/machinery/bot/medbot/S = new /obj/machinery/bot/medbot(T)
- S.skin = src.skin
- S.name = src.created_name
- user.drop_from_inventory(src)
- del(src)
-
diff --git a/code/game/machinery/bots/mulebot.dm b/code/game/machinery/bots/mulebot.dm
index bd39d2034c5..3e6f0d8e33a 100644
--- a/code/game/machinery/bots/mulebot.dm
+++ b/code/game/machinery/bots/mulebot.dm
@@ -76,6 +76,12 @@
suffix = "#[count]"
name = "Mulebot ([suffix])"
+/obj/machinery/bot/mulebot/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,beacon_freq)
+ radio_controller.remove_object(src,control_freq)
+ ..()
+
// attack by item
// emag : lock/unlock,
// screwdriver: open/close hatch
@@ -299,7 +305,14 @@
if("destination")
refresh=0
- var/new_dest = input("Enter new destination tag", "Mulebot [suffix ? "([suffix])" : ""]", destination) as text|null
+ var/new_dest
+ var/list/beaconlist = new()
+ for(var/obj/machinery/navbeacon/N in navbeacons)
+ beaconlist.Add(N.location)
+ if(beaconlist.len)
+ new_dest = input("Select new destination tag", "Mulebot [suffix ? "([suffix])" : ""]", destination) in beaconlist
+ else
+ alert("No destination beacons available.")
refresh=1
if(new_dest)
set_destination(new_dest)
@@ -735,11 +748,6 @@
if(!on)
return
- /*
- world << "rec signal: [signal.source]"
- for(var/x in signal.data)
- world << "* [x] = [signal.data[x]]"
- */
var/recv = signal.data["command"]
// process all-bot input
if(recv=="bot_status" && wires.RemoteRX())
@@ -862,8 +870,8 @@
var/turf/Tsec = get_turf(src)
new /obj/item/device/assembly/prox_sensor(Tsec)
- new /obj/item/stack/rods(Tsec)
- new /obj/item/stack/rods(Tsec)
+ PoolOrNew(/obj/item/stack/rods, Tsec)
+ PoolOrNew(/obj/item/stack/rods, Tsec)
new /obj/item/stack/cable_coil/cut(Tsec)
if (cell)
cell.loc = Tsec
@@ -876,4 +884,4 @@
new /obj/effect/decal/cleanable/blood/oil(src.loc)
unload(0)
- del(src)
+ qdel(src)
diff --git a/code/game/machinery/bots/secbot.dm b/code/game/machinery/bots/secbot.dm
deleted file mode 100644
index 92b7297c42d..00000000000
--- a/code/game/machinery/bots/secbot.dm
+++ /dev/null
@@ -1,924 +0,0 @@
-/obj/machinery/bot/secbot
- name = "Securitron"
- desc = "A little security robot. He looks less than thrilled."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "secbot0"
- layer = 5.0
- density = 0
- anchored = 0
- health = 25
- maxhealth = 25
- fire_dam_coeff = 0.7
- brute_dam_coeff = 0.5
- req_one_access = list(access_security, access_forensics_lockers)
-
- var/mob/target
- var/oldtarget_name
- var/threatlevel = 0
- var/target_lastloc //Loc of target when arrested.
- var/last_found //There's a delay
- var/frustration = 0
-
- var/idcheck = 0 //If false, all station IDs are authorized for weapons.
- var/check_records = 0 //Does it check security records?
- var/check_arrest = 1 //Does it check arrest status?
- var/arrest_type = 0 //If true, don't handcuff
- var/declare_arrests = 0 //When making an arrest, should it notify everyone wearing sechuds?
-
- var/has_laser = 0
- var/next_harm_time = 0
- var/lastfired = 0
- var/shot_delay = 3 //.3 seconds between shots
- var/lasercolor = ""
- var/projectile = null//Holder for projectile type, to avoid so many else if chains
- var/disabled = 0//A holder for if it needs to be disabled, if true it will not seach for targets, shoot at targets, or move, currently only used for lasertag
-
- var/mode = 0
-#define SECBOT_IDLE 0 // idle
-#define SECBOT_HUNT 1 // found target, hunting
-#define SECBOT_PREP_ARREST 2 // at target, preparing to arrest
-#define SECBOT_ARREST 3 // arresting target
-#define SECBOT_START_PATROL 4 // start patrol
-#define SECBOT_PATROL 5 // patrolling
-#define SECBOT_SUMMON 6 // summoned by PDA
-
- var/auto_patrol = 0 // set to make bot automatically patrol
-
- var/beacon_freq = 1445 // navigation beacon frequency
- var/control_freq = AI_FREQ // bot control frequency
-
-
- var/turf/patrol_target // this is turf to navigate to (location of beacon)
- var/new_destination // pending new destination (waiting for beacon response)
- var/destination // destination description tag
- var/next_destination // the next destination in the patrol route
- var/list/path = new // list of path turfs
-
- var/blockcount = 0 //number of times retried a blocked path
- var/awaiting_beacon = 0 // count of pticks awaiting a beacon response
-
- var/nearest_beacon // the nearest beacon's tag
- var/turf/nearest_beacon_loc // the nearest beacon's location
-
- var/bot_version = "1.3"
- var/search_range = 7
- var/is_attacking = 0
-
- var/obj/item/weapon/secbot_assembly = /obj/item/weapon/secbot_assembly
-
- var/list/threat_found_sounds = new('sound/voice/bcriminal.ogg', 'sound/voice/bjustice.ogg', 'sound/voice/bfreeze.ogg')
- var/list/preparing_arrest_sounds = new('sound/voice/bgod.ogg', 'sound/voice/biamthelaw.ogg', 'sound/voice/bsecureday.ogg', 'sound/voice/bradio.ogg', 'sound/voice/binsult.ogg', 'sound/voice/bcreep.ogg')
-
-/obj/machinery/bot/secbot/beepsky
- name = "Officer Beep O'sky"
- desc = "It's Officer Beep O'sky! Powered by a potato and a shot of whiskey."
- idcheck = 0
- auto_patrol = 1
-
-/obj/item/weapon/secbot_assembly
- name = "helmet/signaler assembly"
- desc = "Some sort of bizarre assembly."
- icon = 'icons/obj/aibots.dmi'
- icon_state = "helmet_signaler"
- item_state = "helmet"
- var/build_step = 0
- var/created_name = "Securitron" //To preserve the name if it's a unique securitron I guess
-
-/obj/machinery/bot/secbot/New(loc, created_name, created_lasercolor)
- ..()
- if(created_name) name = created_name
- if(created_lasercolor) lasercolor = created_lasercolor
- update_icon()
- spawn(3)
- src.botcard = new /obj/item/weapon/card/id(src)
- src.botcard.access = list(access_security, access_sec_doors, access_forensics_lockers, access_morgue, access_maint_tunnels, access_court)
- if(radio_controller)
- radio_controller.add_object(src, control_freq, filter = RADIO_SECBOT)
- radio_controller.add_object(src, beacon_freq, filter = RADIO_NAVBEACONS)
- if(lasercolor)
- shot_delay = 6 //Longer shot delay because JESUS CHRIST
- check_arrest = 0
- check_records = 0 //Don't actively target people set to arrest
- arrest_type = 1 //Don't even try to cuff
- req_access = list(access_maint_tunnels)
- arrest_type = 1
- if((lasercolor == "b") && (name == created_name))//Picks a name if there isn't already a custome one
- name = pick("BLUE BALLER","SANIC","BLUE KILLDEATH MURDERBOT")
- if((lasercolor == "r") && (name == created_name))
- name = pick("RED RAMPAGE","RED ROVER","RED KILLDEATH MURDERBOT")
-
-
-/obj/machinery/bot/secbot/update_icon()
- if(on && is_attacking)
- src.icon_state = "secbot-c"
- else
- src.icon_state = "secbot[src.on]"
-
-/obj/machinery/bot/secbot/turn_on()
- ..()
- update_icon()
- src.updateUsrDialog()
-
-/obj/machinery/bot/secbot/turn_off()
- ..()
- src.target = null
- src.oldtarget_name = null
- src.anchored = 0
- src.mode = SECBOT_IDLE
- walk_to(src,0)
- update_icon()
- src.updateUsrDialog()
-
-/obj/machinery/bot/secbot/attack_hand(mob/user as mob)
- . = ..()
- if(.)
- return
- usr.set_machine(src)
- interact(user)
-
-/obj/machinery/bot/secbot/interact(mob/user as mob)
- var/dat
-
- dat += text({"
-Automatic Security Unit v[bot_version]
-Status: []
-Behaviour controls are [src.locked ? "locked" : "unlocked"]
-Maintenance panel is [src.open ? "opened" : "closed"]"},
-
-"[src.on ? "On" : "Off"]" )
-
- if(!src.locked || issilicon(user))
- dat += text({"
-Check for Weapon Authorization: []
-Check Security Records: []
-Check Arrest Status: []
-Operating Mode: []
-Report Arrests: []
-Auto Patrol: []"},
-
-"[src.idcheck ? "Yes" : "No"]",
-"[src.check_records ? "Yes" : "No"]",
-"[src.check_arrest ? "Yes" : "No"]",
-"[src.arrest_type ? "Detain" : "Arrest"]",
-"[src.declare_arrests ? "Yes" : "No"]",
-"[auto_patrol ? "On" : "Off"]" )
-
-
- user << browse("Securitron v[bot_version] controls[dat]", "window=autosec")
- onclose(user, "autosec")
- return
-
-/obj/machinery/bot/secbot/Topic(href, href_list)
- if(..())
- return
- usr.set_machine(src)
- src.add_fingerprint(usr)
- if(lasercolor && (istype(usr,/mob/living/carbon/human)))
- var/mob/living/carbon/human/H = usr
- if((lasercolor == "b") && (istype(H.wear_suit, /obj/item/clothing/suit/redtag)))//Opposing team cannot operate it
- return
- else if((lasercolor == "r") && (istype(H.wear_suit, /obj/item/clothing/suit/bluetag)))
- return
- if((href_list["power"]) && (src.allowed(usr)))
- if(src.on)
- turn_off()
- else
- turn_on()
- src.updateUsrDialog()
- return
-
- switch(href_list["operation"])
- if("idcheck")
- src.idcheck = !src.idcheck
- if("ignorerec")
- src.check_records = !src.check_records
- if("ignorearr")
- src.check_arrest = !src.check_arrest
- if("switchmode")
- src.arrest_type = !src.arrest_type
- if("patrol")
- auto_patrol = !auto_patrol
- mode = SECBOT_IDLE
- if("declarearrests")
- src.declare_arrests = !src.declare_arrests
- src.updateUsrDialog()
-
-/obj/machinery/bot/secbot/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(istype(W, /obj/item/weapon/card/id)||istype(W, /obj/item/device/pda))
- if(src.allowed(user) && !open && !emagged)
- src.locked = !src.locked
- user << "Controls are now [src.locked ? "locked" : "unlocked"]."
- else
- if(emagged)
- user << "ERROR"
- if(open)
- user << "Please close the access panel before locking it."
- else
- user << "Access denied."
- else
- ..()
- if(!istype(W, /obj/item/weapon/screwdriver) && W.force && !src.target)
- src.target = user
- if(lasercolor)//To make up for the fact that lasertag bots don't hunt
- src.shootAt(user)
- src.mode = SECBOT_HUNT
-
-/obj/machinery/bot/secbot/Emag(mob/user as mob)
- ..()
- if(open && !locked)
- if(user) user << "You short out [src]'s target assessment circuits."
- spawn(0)
- for(var/mob/O in hearers(src, null))
- O.show_message("\red [src] buzzes oddly!", 1)
- src.target = null
- if(user) src.oldtarget_name = user.name
- src.last_found = world.time
- src.anchored = 0
- src.emagged = 2
- src.on = 1
- update_icon()
- src.projectile = null
- mode = SECBOT_IDLE
-
-/obj/machinery/bot/secbot/process()
- set background = 1
-
- if(!src.on)
- return
-
- switch(mode)
-
- if(SECBOT_IDLE) // idle
- walk_to(src,0)
- look_for_perp() // see if any criminals are in range
- if(!mode && auto_patrol) // still idle, and set to patrol
- mode = SECBOT_START_PATROL // switch to patrol mode
-
- if(SECBOT_HUNT) // hunting for perp
- // if can't reach perp for long enough, go idle
- if(src.frustration >= 8)
- // for(var/mob/O in hearers(src, null))
- // O << "[src] beeps, \"Backup requested! Suspect has evaded arrest.\""
- src.target = null
- src.last_found = world.time
- src.frustration = 0
- src.mode = 0
- walk_to(src,0)
-
- if(target) // make sure target exists
- // We re-assess human targets, before bashing their head in, in case their credentials change
- if(istype(target, /mob/living/carbon/human))
- var/threat = src.assess_perp(target, idcheck, check_records, check_arrest)
- if(threat < 4)
- frustration = 8
- return
-
- // The target must remain in view to complete the desire to bash its head in
- if(!(target in view(search_range,src)))
- frustration++
- return
-
- if(!lasercolor && Adjacent(target)) // If right next to perp. Lasertag bots do not arrest anyone, just patrol and shoot and whatnot
- if(istype(src.target,/mob/living/carbon))
- playsound(src.loc, 'sound/weapons/Egloves.ogg', 50, 1, -1)
- is_attacking = 1
- update_icon()
- spawn(2)
- is_attacking = 0
- update_icon()
- var/mob/living/carbon/M = src.target
- var/maxstuns = 4
- if(istype(M, /mob/living/carbon/human))
- if(M.stuttering < 10 && (!(HULK in M.mutations)))
- M.stuttering = 10
- M.Stun(10)
- M.Weaken(10)
- else
- M.Weaken(10)
- M.stuttering = 10
- M.Stun(10)
- maxstuns--
- if(maxstuns <= 0)
- target = null
-
- if(declare_arrests)
- var/area/location = get_area(src)
- broadcast_security_hud_message("[src.name] is [arrest_type ? "detaining" : "arresting"] level [threatlevel] suspect [target] in [location]", src)
- visible_message("\red [src.target] has been stunned by [src]!")
-
- mode = SECBOT_PREP_ARREST
- src.anchored = 1
- src.target_lastloc = M.loc
- return
- else if(istype(src.target,/mob/living/simple_animal))
- //just harmbaton them until dead
- if(world.time > next_harm_time)
- next_harm_time = world.time + 15
- playsound(src.loc, 'sound/weapons/Egloves.ogg', 50, 1, -1)
- visible_message("\red [src] beats [src.target] with the stun baton!")
- update_icon()
- spawn(2)
- is_attacking = 0
- update_icon()
-
- var/mob/living/simple_animal/S = src.target
- S.AdjustStunned(10)
- S.adjustBruteLoss(15)
- if(S.stat)
- src.frustration = 8
- if(preparing_arrest_sounds.len > 0)
- playsound(src.loc, pick(preparing_arrest_sounds), 50, 0)
- else // not next to perp
- var/turf/olddist = get_dist(src, src.target)
- walk_to(src, target,1,4)
- shootAt(target)
- if((get_dist(src, src.target)) >= (olddist))
- src.frustration++
- else
- src.frustration = 0
- else
- src.frustration = 8
-
- if(SECBOT_PREP_ARREST) // preparing to arrest target
- if(src.lasercolor)
- mode = SECBOT_IDLE
- return
- if(!target)
- mode = SECBOT_IDLE
- src.anchored = 0
- return
- // see if he got away
- if((get_dist(src, src.target) > 1) || ((src.target.loc != src.target_lastloc) && src.target.weakened < 2))
- src.anchored = 0
- mode = SECBOT_HUNT
- return
-
- if(istype(src.target,/mob/living/carbon))
- var/mob/living/carbon/C = target
- var/wearing_hardsuit
- if(istype(C,/mob/living/carbon/human))
- var/mob/living/carbon/human/H = C
- if(istype(H.back, /obj/item/weapon/rig) && istype(H.gloves,/obj/item/clothing/gloves/rig))
- wearing_hardsuit = 1
- if(!wearing_hardsuit && !C.handcuffed && !src.arrest_type)
- playsound(src.loc, 'sound/weapons/handcuffs.ogg', 30, 1, -2)
- mode = SECBOT_ARREST
- visible_message("\red [src] is trying to put handcuffs on [src.target]!")
-
- spawn(60)
- if(get_dist(src, src.target) <= 1)
- /*if(src.target.handcuffed)
- return*/
-
- if(istype(src.target,/mob/living/carbon))
- C = target
- if(!C.handcuffed)
- C.handcuffed = new /obj/item/weapon/handcuffs(target)
- C.update_inv_handcuffed() //update the handcuffs overlay
-
- mode = SECBOT_IDLE
- src.target = null
- src.anchored = 0
- src.last_found = world.time
- src.frustration = 0
-
- if(preparing_arrest_sounds.len > 0)
- playsound(src.loc, pick(preparing_arrest_sounds), 50, 0)
- // var/arrest_message = pick("Have a secure day!","I AM THE LAW.", "God made tomorrow for the crooks we don't catch today.","You can't outrun a radio.")
- // src.speak(arrest_message)
- else
- mode = SECBOT_IDLE
- src.target = null
- src.anchored = 0
- src.last_found = world.time
- src.frustration = 0
-
- if(SECBOT_ARREST) // arresting
- if(src.lasercolor)
- mode = SECBOT_IDLE
- return
- if(!target || !istype(target, /mob/living/carbon))
- src.anchored = 0
- mode = SECBOT_IDLE
- return
- else
- var/mob/living/carbon/C = target
- if(!C.handcuffed)
- src.anchored = 0
- mode = SECBOT_IDLE
- return
-
-
- if(SECBOT_START_PATROL) // start a patrol
-
- if(path.len > 0 && patrol_target) // have a valid path, so just resume
- mode = SECBOT_PATROL
- return
-
- else if(patrol_target) // has patrol target already
- spawn(0)
- calc_path() // so just find a route to it
- if(path.len == 0)
- patrol_target = 0
- return
- mode = SECBOT_PATROL
-
-
- else // no patrol target, so need a new one
- find_patrol_target()
- speak("Engaging patrol mode.")
-
-
- if(SECBOT_PATROL) // patrol mode
- patrol_step()
- spawn(5)
- if(mode == SECBOT_PATROL)
- patrol_step()
-
- if(SECBOT_SUMMON) // summoned to PDA
- patrol_step()
- spawn(4)
- if(mode == SECBOT_SUMMON)
- patrol_step()
- sleep(4)
- patrol_step()
-
- return
-
-
-// perform a single patrol step
-/obj/machinery/bot/secbot/proc/patrol_step()
- if(loc == patrol_target) // reached target
- at_patrol_target()
- return
- else if(path.len > 0 && patrol_target) // valid path
- var/turf/next = path[1]
- if(next == loc)
- path -= next
- return
-
- if(istype( next, /turf/simulated))
- var/moved = step_towards(src, next) // attempt to move
- if(moved) // successful move
- blockcount = 0
- path -= loc
-
- look_for_perp()
- if(lasercolor)
- sleep(20)
- else // failed to move
- blockcount++
- if(blockcount > 5) // attempt 5 times before recomputing
- // find new path excluding blocked turf
-
- spawn(2)
- calc_path(next)
- if(path.len == 0)
- find_patrol_target()
- else
- blockcount = 0
- return
- return
- else // not a valid turf
- mode = SECBOT_IDLE
- return
- else // no path, so calculate new one
- mode = SECBOT_START_PATROL
-
-// finds a new patrol target
-/obj/machinery/bot/secbot/proc/find_patrol_target()
- send_status()
- if(awaiting_beacon) // awaiting beacon response
- awaiting_beacon++
- if(awaiting_beacon > 5) // wait 5 secs for beacon response
- find_nearest_beacon() // then go to nearest instead
- return
-
- if(next_destination)
- set_destination(next_destination)
- else
- find_nearest_beacon()
- return
-
-// finds the nearest beacon to self
-// signals all beacons matching the patrol code
-/obj/machinery/bot/secbot/proc/find_nearest_beacon()
- nearest_beacon = null
- new_destination = "__nearest__"
- post_signal(beacon_freq, "findbeacon", "patrol")
- awaiting_beacon = 1
- spawn(10)
- awaiting_beacon = 0
- if(nearest_beacon)
- set_destination(nearest_beacon)
- else
- auto_patrol = 0
- mode = SECBOT_IDLE
- speak("Disengaging patrol mode.")
- send_status()
-
-/obj/machinery/bot/secbot/proc/at_patrol_target()
- find_patrol_target()
- return
-
-// sets the current destination
-// signals all beacons matching the patrol code
-// beacons will return a signal giving their locations
-/obj/machinery/bot/secbot/proc/set_destination(var/new_dest)
- new_destination = new_dest
- post_signal(beacon_freq, "findbeacon", "patrol")
- awaiting_beacon = 1
-
-
-// receive a radio signal
-// used for beacon reception
-/obj/machinery/bot/secbot/receive_signal(datum/signal/signal)
- //log_admin("DEBUG \[[world.timeofday]\]: /obj/machinery/bot/secbot/receive_signal([signal.debug_print()])")
- if(!on)
- return
-
- /*
- world << "rec signal: [signal.source]"
- for(var/x in signal.data)
- world << "* [x] = [signal.data[x]]"
- */
-
- var/recv = signal.data["command"]
- // process all-bot input
- if(recv=="bot_status")
- send_status()
-
- // check to see if we are the commanded bot
- if(signal.data["active"] == src)
- // process control input
- switch(recv)
- if("stop")
- mode = SECBOT_IDLE
- auto_patrol = 0
- return
-
- if("go")
- mode = SECBOT_IDLE
- auto_patrol = 1
- return
-
- if("summon")
- patrol_target = signal.data["target"]
- next_destination = destination
- destination = null
- awaiting_beacon = 0
- mode = SECBOT_SUMMON
- calc_path()
- speak("Responding.")
-
- return
-
-
-
- // receive response from beacon
- recv = signal.data["beacon"]
- var/valid = signal.data["patrol"]
- if(!recv || !valid)
- return
-
- if(recv == new_destination) // if the recvd beacon location matches the set destination
- // the we will navigate there
- destination = new_destination
- patrol_target = signal.source.loc
- next_destination = signal.data["next_patrol"]
- awaiting_beacon = 0
-
- // if looking for nearest beacon
- else if(new_destination == "__nearest__")
- var/dist = get_dist(src,signal.source.loc)
- if(nearest_beacon)
-
- // note we ignore the beacon we are located at
- if(dist>1 && dist 1)
- nearest_beacon = recv
- nearest_beacon_loc = signal.source.loc
- return
-
-
-// send a radio signal with a single data key/value pair
-/obj/machinery/bot/secbot/proc/post_signal(var/freq, var/key, var/value)
- post_signal_multiple(freq, list("[key]" = value) )
-
-// send a radio signal with multiple data key/values
-/obj/machinery/bot/secbot/proc/post_signal_multiple(var/freq, var/list/keyval)
-
- var/datum/radio_frequency/frequency = radio_controller.return_frequency(freq)
-
- if(!frequency) return
-
- var/datum/signal/signal = new()
- signal.source = src
- signal.transmission_method = 1
- //for(var/key in keyval)
- // signal.data[key] = keyval[key]
- signal.data = keyval
- //world << "sent [key],[keyval[key]] on [freq]"
- if(signal.data["findbeacon"])
- frequency.post_signal(src, signal, filter = RADIO_NAVBEACONS)
- else if(signal.data["type"] == "secbot")
- frequency.post_signal(src, signal, filter = RADIO_SECBOT)
- else
- frequency.post_signal(src, signal)
-
-// signals bot status etc. to controller
-/obj/machinery/bot/secbot/proc/send_status()
- var/list/kv = list(
- "type" = "secbot",
- "name" = name,
- "loca" = loc.loc, // area
- "mode" = mode
- )
- post_signal_multiple(control_freq, kv)
-
-// calculates a path to the current destination
-// given an optional turf to avoid
-/obj/machinery/bot/secbot/proc/calc_path(var/turf/avoid = null)
- src.path = AStar(src.loc, patrol_target, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance, 0, 120, id=botcard, exclude=avoid)
- if(!path) path = list()
-
-// look for a criminal in view of the bot
-/obj/machinery/bot/secbot/proc/look_for_perp()
- if(src.disabled)
- return
- src.anchored = 0
- for(var/mob/living/M in view(search_range,src)) //Let's find us a criminal
- if(M.invisibility >= INVISIBILITY_LEVEL_ONE) // Cannot see him. see_invisible is a mob-var
- continue
-
- if(istype(M, /mob/living/carbon))
- var/mob/living/carbon/C = M
- if(C.stat || C.handcuffed)
- continue
-
- if(src.lasercolor && C.lying)
- continue//Does not shoot at people lying down when in lasertag mode, because it's just annoying, and they can fire once they get up.
-
- if(C.name == src.oldtarget_name && world.time < src.last_found + 100)
- continue
-
- if(istype(C, /mob/living/carbon/human))
- src.threatlevel = src.assess_perp(C, idcheck, check_records, check_arrest)
-
- else if(istype(M, /mob/living/simple_animal/hostile))
- if(M.stat == DEAD)
- continue
- else
- src.threatlevel = 4
-
- if(!src.threatlevel)
- continue
-
- else if(M.stat != DEAD && src.threatlevel >= 4)
- src.target = M
- src.oldtarget_name = M.name
- src.speak("Level [src.threatlevel] infraction alert!")
- if(!src.lasercolor && threat_found_sounds.len > 0)
- playsound(src.loc, pick(threat_found_sounds), 50, 0)
- src.visible_message("[src] points at [M.name]!")
-
- mode = SECBOT_HUNT
- spawn(0)
- process() // ensure bot quickly responds to a perp
- break
- else
- continue
-
-/obj/machinery/bot/secbot/on_assess_perp(mob/living/carbon/human/perp)
- if(lasercolor)
- return laser_check(perp, lasercolor)
-
- var/threat = 0
- threat -= laser_check(perp, "b")
- threat -= laser_check(perp, "r")
-
- return threat
-
-/obj/machinery/bot/secbot/proc/laser_check(mob/living/carbon/human/perp, var/lasercolor)
- var/target_suit
- var/target_weapon
- var/threat = 0
- //Lasertag turrets target the opposing team, how great is that? -Sieve
- switch(lasercolor)
- if("b")
- target_suit = /obj/item/clothing/suit/redtag
- target_weapon = /obj/item/weapon/gun/energy/lasertag/red
- if("r")
- target_suit = /obj/item/clothing/suit/bluetag
- target_weapon = /obj/item/weapon/gun/energy/lasertag/blue
-
- if((istype(perp.r_hand, target_weapon)) || (istype(perp.l_hand, target_weapon)))
- threat += 4
-
- if(istype(perp, /mob/living/carbon/human))
- if(istype(perp.wear_suit, target_suit))
- threat += 4
- if(istype(perp.belt, target_weapon))
- threat += 2
-
- return threat
-
-/obj/machinery/bot/secbot/is_assess_emagged()
- return emagged == 2
-
-/obj/machinery/bot/secbot/Bump(M as mob|obj) //Leave no door unopened!
- if((istype(M, /obj/machinery/door)) && !isnull(src.botcard))
- var/obj/machinery/door/D = M
- if(!istype(D, /obj/machinery/door/firedoor) && D.check_access(src.botcard) && !istype(D,/obj/machinery/door/blast))
- D.open()
- src.frustration = 0
- else if(!src.anchored)
- if((istype(M, /mob/living/)))
- var/mob/living/O = M
- src.loc = O.loc
- src.frustration = 0
- else if(istype(M, /obj/machinery/bot))
- var/obj/machinery/bot/B = M
- if(B.dir != src.dir) // Avoids issues if two bots are currently patrolling in the same direction
- src.loc = B.loc
- src.frustration = 0
- return
-
-/obj/machinery/bot/secbot/proc/speak(var/message)
- for(var/mob/O in hearers(src, null))
- O.show_message("[src] beeps, \"[message]\"",2)
- return
-
-/obj/machinery/bot/secbot/explode()
- walk_to(src,0)
- src.visible_message("\red [src] blows apart!", 1)
- var/turf/Tsec = get_turf(src)
-
- var/obj/item/weapon/secbot_assembly/Sa = new secbot_assembly(Tsec)
- Sa.build_step = 1
- Sa.overlays += image('icons/obj/aibots.dmi', "hs_hole")
- Sa.created_name = src.name
- new /obj/item/device/assembly/prox_sensor(Tsec)
- new /obj/item/weapon/melee/baton(Tsec)
-
- on_explosion()
-
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(3, 1, src)
- s.start()
-
- new /obj/effect/decal/cleanable/blood/oil(src.loc)
- del(src)
-
-
-/obj/machinery/bot/secbot/proc/on_explosion(var/turf/Tsec)
- new /obj/item/weapon/melee/baton(Tsec)
- if(prob(50))
- new /obj/item/robot_parts/l_arm(Tsec)
-
-//Secbot Construction
-
-/obj/item/clothing/head/helmet/attackby(var/obj/item/device/assembly/signaler/S, mob/user as mob)
- ..()
- if(!issignaler(S))
- ..()
- return
-
- if(src.type != /obj/item/clothing/head/helmet) //Eh, but we don't want people making secbots out of space helmets.
- return
-
- if(S.secured)
- del(S)
- var/obj/item/weapon/secbot_assembly/A = new /obj/item/weapon/secbot_assembly
- user.put_in_hands(A)
- user << "You add the signaler to the helmet."
- user.drop_from_inventory(src)
- del(src)
- else
- return
-
-/obj/item/weapon/secbot_assembly/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
- if((istype(W, /obj/item/weapon/weldingtool)) && (!src.build_step))
- var/obj/item/weapon/weldingtool/WT = W
- if(WT.remove_fuel(0,user))
- src.build_step++
- src.overlays += image('icons/obj/aibots.dmi', "hs_hole")
- user << "You weld a hole in [src]!"
-
- else if(isprox(W) && (src.build_step == 1))
- user.drop_item()
- src.build_step++
- user << "You add the prox sensor to [src]!"
- src.overlays += image('icons/obj/aibots.dmi', "hs_eye")
- src.name = "helmet/signaler/prox sensor assembly"
- del(W)
-
- else if(((istype(W, /obj/item/robot_parts/l_arm)) || (istype(W, /obj/item/robot_parts/r_arm))) && (src.build_step == 2))
- user.drop_item()
- src.build_step++
- user << "You add the robot arm to [src]!"
- src.name = "helmet/signaler/prox sensor/robot arm assembly"
- src.overlays += image('icons/obj/aibots.dmi', "hs_arm")
- del(W)
-
- else if((istype(W, /obj/item/weapon/melee/baton)) && (src.build_step >= 3))
- user.drop_item()
- src.build_step++
- user << "You complete the Securitron! Beep boop."
- var/obj/machinery/bot/secbot/S = new /obj/machinery/bot/secbot
- S.loc = get_turf(src)
- S.name = src.created_name
- del(W)
- del(src)
-
- else if(istype(W, /obj/item/weapon/pen))
- var/t = sanitizeSafe(input(user, "Enter new robot name", src.name, src.created_name), MAX_NAME_LEN)
- if(!t)
- return
- if(!in_range(src, usr) && src.loc != usr)
- return
- src.created_name = t
-
-/obj/machinery/bot/secbot/proc/shootAt(var/mob/target)
- if(!has_laser || (lastfired && world.time - lastfired < shot_delay))
- return
- lastfired = world.time
- var/turf/T = loc
- var/atom/U = (istype(target, /atom/movable) ? target.loc : target)
- if((!( U ) || !( T )))
- return
- while(!( istype(U, /turf) ))
- U = U.loc
- if(!( istype(T, /turf) ))
- return
-
- if(!projectile)
- if(!lasercolor)
- if(src.emagged == 2)
- projectile = /obj/item/projectile/beam
- else
- projectile = /obj/item/projectile/beam/stun
- else if(lasercolor == "b")
- if(src.emagged == 2)
- projectile = /obj/item/projectile/beam/lastertag/omni
- else
- projectile = /obj/item/projectile/beam/lastertag/blue
- else if(lasercolor == "r")
- if(src.emagged == 2)
- projectile = /obj/item/projectile/beam/lastertag/omni
- else
- projectile = /obj/item/projectile/beam/lastertag/red
-
- if(!( istype(U, /turf) ))
- return
-
- playsound(src.loc, src.emagged == 2 ? 'sound/weapons/Laser.ogg' : 'sound/weapons/Taser.ogg', 50, 1)
- var/obj/item/projectile/A = new projectile (loc)
- A.current = U
- A.yo = U.y - T.y
- A.xo = U.x - T.x
- spawn( 0 )
- A.process()
- return
- return
-
-/obj/machinery/bot/secbot/emp_act(severity)
- if(severity==2 && prob(70))
- ..(severity-1)
- else
- var/obj/effect/overlay/pulse2 = new/obj/effect/overlay ( src.loc )
- pulse2.icon = 'icons/effects/effects.dmi'
- pulse2.icon_state = "empdisable"
- pulse2.name = "emp sparks"
- pulse2.anchored = 1
- pulse2.set_dir(pick(cardinal))
- spawn(10)
- pulse2.delete()
- var/list/mob/living/carbon/targets = new
- for(var/mob/living/carbon/C in view(12,src))
- if(C.stat==2)
- continue
- targets += C
- if(targets.len)
- if(prob(50))
- var/mob/toshoot = pick(targets)
- if(toshoot)
- targets-=toshoot
- if(prob(50) && emagged < 2)
- emagged = 2
- shootAt(toshoot)
- emagged = 0
- else
- shootAt(toshoot)
- else if(prob(50))
- if(targets.len)
- var/mob/toarrest = pick(targets)
- if(toarrest)
- src.target = toarrest
- src.mode = SECBOT_HUNT
diff --git a/code/game/machinery/camera/camera.dm b/code/game/machinery/camera/camera.dm
index bb997733625..43e26a7d46f 100644
--- a/code/game/machinery/camera/camera.dm
+++ b/code/game/machinery/camera/camera.dm
@@ -8,7 +8,7 @@
active_power_usage = 10
layer = 5
- var/list/network = list("SS13")
+ var/list/network = list("Exodus")
var/c_tag = null
var/c_tag_order = 999
var/status = 1
@@ -53,11 +53,19 @@
ASSERT(src.network.len > 0)
..()
+/obj/machinery/camera/Destroy()
+ deactivate(null, 0) //kick anyone viewing out
+ if(assembly)
+ qdel(assembly)
+ assembly = null
+ qdel(wires)
+ ..()
+
/obj/machinery/camera/emp_act(severity)
if(!isEmpProof())
if(prob(100/severity))
stat |= EMPED
- SetLuminosity(0)
+ set_light(0)
kick_viewers()
triggerCameraAlarm(30 / severity)
update_icon()
@@ -130,13 +138,15 @@
else if(iswelder(W) && (wires.CanDeconstruct() || (stat & BROKEN)))
if(weld(W, user))
if (stat & BROKEN)
- new /obj/item/weapon/circuitboard/broken(src.loc)
- new /obj/item/stack/cable_coil(src.loc, length=2)
+ stat &= ~BROKEN
+ cancelCameraAlarm()
+ update_icon()
+ update_coverage()
else if(assembly)
assembly.loc = src.loc
assembly.state = 1
new /obj/item/stack/cable_coil(src.loc, length=2)
- del(src)
+ qdel(src)
// OTHER
else if (can_use() && (istype(W, /obj/item/weapon/paper) || istype(W, /obj/item/device/pda)) && isliving(user))
@@ -216,6 +226,8 @@
//Used when someone breaks a camera
/obj/machinery/camera/proc/destroy()
stat |= BROKEN
+ wires.RandomCutAll()
+
kick_viewers()
triggerCameraAlarm()
update_icon()
diff --git a/code/game/machinery/camera/camera_assembly.dm b/code/game/machinery/camera/camera_assembly.dm
index a038ece4140..28691004f31 100644
--- a/code/game/machinery/camera/camera_assembly.dm
+++ b/code/game/machinery/camera/camera_assembly.dm
@@ -6,7 +6,7 @@
w_class = 2
anchored = 0
- matter = list("metal" = 700,"glass" = 300)
+ matter = list(DEFAULT_WALL_MATERIAL = 700,"glass" = 300)
// Motion, EMP-Proof, X-Ray
var/list/obj/item/possible_upgrades = list(/obj/item/device/assembly/prox_sensor, /obj/item/stack/sheet/mineral/osmium, /obj/item/weapon/stock_parts/scanning_module)
@@ -78,7 +78,7 @@
if(isscrewdriver(W))
playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
- var/input = sanitize(input(usr, "Which networks would you like to connect this camera to? Separate networks with a comma. No Spaces!\nFor example: SS13,Security,Secret ", "Set Network", "SS13"))
+ var/input = sanitize(input(usr, "Which networks would you like to connect this camera to? Separate networks with a comma. No Spaces!\nFor example: Exodus,Security,Secret ", "Set Network", "Exodus"))
if(!input)
usr << "No input found please hang up and try your call again."
return
@@ -90,7 +90,7 @@
var/area/camera_area = get_area(src)
var/temptag = "[sanitize(camera_area.name)] ([rand(1, 999)])"
- input = sanitizeSafe(input(usr, "How would you like to name the camera?", "Set Camera Name", temptag))
+ input = sanitizeSafe(input(usr, "How would you like to name the camera?", "Set Camera Name", temptag), MAX_NAME_LEN)
state = 4
var/obj/machinery/camera/C = new(src.loc)
@@ -125,7 +125,7 @@
if(is_type_in_list(W, possible_upgrades) && !is_type_in_list(W, upgrades)) // Is a possible upgrade and isn't in the camera already.
user << "You attach \the [W] into the assembly inner circuits."
upgrades += W
- user.drop_item(W)
+ user.remove_from_mob(W)
W.loc = src
return
diff --git a/code/game/machinery/camera/presets.dm b/code/game/machinery/camera/presets.dm
index fbbecec8257..d4b795730fb 100644
--- a/code/game/machinery/camera/presets.dm
+++ b/code/game/machinery/camera/presets.dm
@@ -1,4 +1,76 @@
// PRESETS
+var/global/list/station_networks = list(
+ NETWORK_CIVILIAN_EAST,
+ NETWORK_CIVILIAN_WEST,
+ NETWORK_COMMAND,
+ NETWORK_ENGINE,
+ NETWORK_ENGINEERING,
+ NETWORK_ENGINEERING_OUTPOST,
+ NETWORK_EXODUS,
+ NETWORK_MEDICAL,
+ NETWORK_MINE,
+ NETWORK_RESEARCH,
+ NETWORK_RESEARCH_OUTPOST,
+ NETWORK_PRISON,
+ NETWORK_SECURITY
+ )
+var/global/list/engineering_networks = list(
+ NETWORK_ENGINE,
+ NETWORK_ENGINEERING,
+ NETWORK_ENGINEERING_OUTPOST,
+ "Atmosphere Alarms",
+ "Fire Alarms",
+ "Power Alarms")
+/obj/machinery/camera/network/crescent
+ network = list(NETWORK_CRESCENT)
+
+/obj/machinery/camera/network/civilian_east
+ network = list(NETWORK_CIVILIAN_EAST)
+
+/obj/machinery/camera/network/civilian_west
+ network = list(NETWORK_CIVILIAN_WEST)
+
+/obj/machinery/camera/network/command
+ network = list(NETWORK_COMMAND)
+
+/obj/machinery/camera/network/engine
+ network = list(NETWORK_ENGINE)
+
+/obj/machinery/camera/network/engineering
+ network = list(NETWORK_ENGINEERING)
+
+/obj/machinery/camera/network/engineering_outpost
+ network = list(NETWORK_ENGINEERING_OUTPOST)
+
+/obj/machinery/camera/network/ert
+ network = list(NETWORK_ERT)
+
+/obj/machinery/camera/network/exodus
+ network = list(NETWORK_EXODUS)
+
+/obj/machinery/camera/network/mining
+ network = list(NETWORK_MINE)
+
+/obj/machinery/camera/network/prison
+ network = list(NETWORK_PRISON)
+
+/obj/machinery/camera/network/medbay
+ network = list(NETWORK_MEDICAL)
+
+/obj/machinery/camera/network/research
+ network = list(NETWORK_RESEARCH)
+
+/obj/machinery/camera/network/research_outpost
+ network = list(NETWORK_RESEARCH_OUTPOST)
+
+/obj/machinery/camera/network/security
+ network = list(NETWORK_SECURITY)
+
+/obj/machinery/camera/network/telecom
+ network = list(NETWORK_TELECOM)
+
+/obj/machinery/camera/network/thunder
+ network = list(NETWORK_THUNDER)
// EMP
@@ -11,6 +83,15 @@
/obj/machinery/camera/xray
icon_state = "xraycam" // Thanks to Krutchen for the icons.
+/obj/machinery/camera/xray/security
+ network = list(NETWORK_SECURITY)
+
+/obj/machinery/camera/xray/medbay
+ network = list(NETWORK_MEDICAL)
+
+/obj/machinery/camera/xray/research
+ network = list(NETWORK_RESEARCH)
+
/obj/machinery/camera/xray/New()
..()
upgradeXRay()
@@ -21,8 +102,18 @@
..()
upgradeMotion()
+/obj/machinery/camera/motion/engineering_outpost
+ network = list(NETWORK_ENGINEERING_OUTPOST)
+
+/obj/machinery/camera/motion/security
+ network = list(NETWORK_SECURITY)
+
// ALL UPGRADES
+
+/obj/machinery/camera/all/command
+ network = list(NETWORK_COMMAND)
+
/obj/machinery/camera/all/New()
..()
upgradeEmpProof()
@@ -30,16 +121,6 @@
upgradeMotion()
// AUTONAME
-
-/obj/machinery/camera/autoname/engineering_outpost
- network = list("SS13", "Engineering Outpost")
-
-/obj/machinery/camera/autoname/mining_outpost
- network = list("SS13", "MINE")
-
-/obj/machinery/camera/autoname/research_outpost
- network = list("SS13", "Research Outpost")
-
/obj/machinery/camera/autoname
var/number = 0 //camera number in area
@@ -57,6 +138,7 @@
if(C.number)
number = max(number, C.number+1)
c_tag = "[A.name] #[number]"
+ invalidateCameraCache()
// CHECKS
diff --git a/code/game/machinery/camera/tracking.dm b/code/game/machinery/camera/tracking.dm
index b781613d70e..6ccea2c3826 100644
--- a/code/game/machinery/camera/tracking.dm
+++ b/code/game/machinery/camera/tracking.dm
@@ -15,7 +15,6 @@
cameranet.process_sort()
var/list/T = list()
- T["Cancel"] = "Cancel"
for (var/obj/machinery/camera/C in cameranet.cameras)
var/list/tempnetwork = C.network&src.network
if (tempnetwork.len)
@@ -30,11 +29,10 @@
set category = "AI Commands"
set name = "Show Camera List"
- if(src.stat == 2)
- src << "You can't list the cameras because you are dead!"
+ if(check_unable())
return
- if (!camera || camera == "Cancel")
+ if (!camera)
return 0
var/obj/machinery/camera/C = track.cameras[camera]
diff --git a/code/game/machinery/cell_charger.dm b/code/game/machinery/cell_charger.dm
index a02553cc77e..683e6e12202 100644
--- a/code/game/machinery/cell_charger.dm
+++ b/code/game/machinery/cell_charger.dm
@@ -11,7 +11,7 @@
var/obj/item/weapon/cell/charging = null
var/chargelevel = -1
-/obj/machinery/cell_charger/proc/updateicon()
+/obj/machinery/cell_charger/update_icon()
icon_state = "ccharger[charging ? 1 : 0]"
if(charging && !(stat & (BROKEN|NOPOWER)) )
@@ -57,7 +57,7 @@
charging = W
user.visible_message("[user] inserts a cell into the charger.", "You insert a cell into the charger.")
chargelevel = -1
- updateicon()
+ update_icon()
else if(istype(W, /obj/item/weapon/wrench))
if(charging)
user << "\red Remove the cell first!"
@@ -76,7 +76,7 @@
src.charging = null
user.visible_message("[user] removes the cell from the charger.", "You remove the cell from the charger.")
chargelevel = -1
- updateicon()
+ update_icon()
/obj/machinery/cell_charger/attack_ai(mob/user)
if(istype(user, /mob/living/silicon/robot) && Adjacent(user)) // Borgs can remove the cell if they are near enough
@@ -108,6 +108,6 @@
charging.give(active_power_usage*CELLRATE)
update_use_power(2)
- updateicon()
+ update_icon()
else
update_use_power(1)
diff --git a/code/game/machinery/cloning.dm b/code/game/machinery/cloning.dm
index 0c133adc9bc..b4e75b046ff 100644
--- a/code/game/machinery/cloning.dm
+++ b/code/game/machinery/cloning.dm
@@ -174,17 +174,9 @@
//So clones don't die of oxyloss in a running pod.
if(occupant.reagents.get_reagent_amount("inaprovaline") < 30)
occupant.reagents.add_reagent("inaprovaline", 60)
-
- //So clones will remain asleep for long enough to get them into cryo (Bay RP edit)
- if(occupant.reagents.get_reagent_amount("stoxin") < 10)
- occupant.reagents.add_reagent("stoxin", 5)
- if(occupant.reagents.get_reagent_amount("chloralhydrate") < 1)
- occupant.reagents.add_reagent("chloralhydrate", 1)
-
+ occupant.Sleeping(30)
//Also heal some oxyloss ourselves because inaprovaline is so bad at preventing it!!
occupant.adjustOxyLoss(-4)
- if(notoxin)
- occupant.adjustToxLoss(-2) // If sufficiently upgraded - remove toxin damage from chloral
use_power(7500) //This might need tweaking.
return
@@ -235,7 +227,7 @@
user << "\The [src] processes \the [W]."
biomass += 50
user.drop_item()
- del(W)
+ qdel(W)
return
else if(istype(W, /obj/item/weapon/wrench))
if(locked && (anchored || occupant))
@@ -328,7 +320,7 @@
update_icon()
occupant.ghostize()
spawn(5)
- del(occupant)
+ qdel(occupant)
return
/obj/machinery/clonepod/relaymove(mob/user as mob)
@@ -348,21 +340,21 @@
for(var/atom/movable/A as mob|obj in src)
A.loc = loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(2.0)
if(prob(50))
for(var/atom/movable/A as mob|obj in src)
A.loc = loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(3.0)
if(prob(25))
for(var/atom/movable/A as mob|obj in src)
A.loc = loc
ex_act(severity)
- del(src)
+ qdel(src)
return
else
return
diff --git a/code/game/machinery/commsbantenna.dm b/code/game/machinery/commsbantenna.dm
new file mode 100644
index 00000000000..03d4a311b18
--- /dev/null
+++ b/code/game/machinery/commsbantenna.dm
@@ -0,0 +1,34 @@
+/obj/machinery/bluespacerelay
+ name = "Emergency Bluespace Relay"
+ desc = "This sends messages through bluespace! Wow!"
+ icon = 'icons/obj/stationobjs.dmi'
+ icon_state = "bspacerelay"
+
+ anchored = 1
+ density = 1
+ use_power = 1
+ var/on = 1
+
+ idle_power_usage = 15000
+ active_power_usage = 15000
+
+/obj/machinery/bluespacerelay/process()
+
+ update_power()
+
+ update_icon()
+
+
+/obj/machinery/bluespacerelay/update_icon()
+ if(on)
+ icon_state = initial(icon_state)
+ else
+ icon_state = "[initial(icon_state)]_off"
+
+/obj/machinery/bluespacerelay/proc/update_power()
+
+ if(stat & (BROKEN|NOPOWER|EMPED))
+ on = 0
+ else
+ on = 1
+
diff --git a/code/game/machinery/computer/Operating.dm b/code/game/machinery/computer/Operating.dm
index b35cfd95a67..3f38059618e 100644
--- a/code/game/machinery/computer/Operating.dm
+++ b/code/game/machinery/computer/Operating.dm
@@ -5,6 +5,7 @@
density = 1
anchored = 1.0
icon_state = "operating"
+ light_color = "#315ab4"
circuit = "/obj/item/weapon/circuitboard/operating"
var/mob/living/carbon/human/victim = null
var/obj/machinery/optable/table = null
diff --git a/code/game/machinery/computer/RCON_Console.dm b/code/game/machinery/computer/RCON_Console.dm
index f80f0b93c4d..cf275eb5ce8 100644
--- a/code/game/machinery/computer/RCON_Console.dm
+++ b/code/game/machinery/computer/RCON_Console.dm
@@ -9,6 +9,7 @@
desc = "Console used to remotely control machinery on the station."
icon = 'icons/obj/computer.dmi'
icon_state = "ai-fixer"
+ light_color = "#a97faa"
circuit = /obj/item/weapon/circuitboard/rcon_console
req_one_access = list(access_engine)
var/current_tag = null
diff --git a/code/game/machinery/computer/ai_core.dm b/code/game/machinery/computer/ai_core.dm
index 8778038ddf0..028f1ba307a 100644
--- a/code/game/machinery/computer/ai_core.dm
+++ b/code/game/machinery/computer/ai_core.dm
@@ -30,7 +30,7 @@
if(!src || !WT.remove_fuel(0, user)) return
user << "\blue You deconstruct the frame."
new /obj/item/stack/sheet/plasteel( loc, 4)
- del(src)
+ qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
@@ -178,7 +178,7 @@
if(A) //if there's no brain, the mob is deleted and a structure/AIcore is created
A.rename_self("ai", 1)
feedback_inc("cyborg_ais_created",1)
- del(src)
+ qdel(src)
/obj/structure/AIcore/deactivated
name = "inactive AI"
@@ -187,6 +187,11 @@
anchored = 1
state = 20//So it doesn't interact based on the above. Not really necessary.
+/obj/structure/AIcore/deactivated/Destroy()
+ if(src in empty_playable_ai_cores)
+ empty_playable_ai_cores -= src
+ ..()
+
/obj/structure/AIcore/deactivated/proc/load_ai(var/mob/living/silicon/ai/transfer, var/obj/item/device/aicard/card, var/mob/user)
if(!istype(transfer) || locate(/mob/living/silicon/ai) in src)
@@ -203,7 +208,7 @@
if(card)
card.clear()
- del(src)
+ qdel(src)
/obj/structure/AIcore/deactivated/proc/check_malf(var/mob/living/silicon/ai/ai)
if(!ai) return
diff --git a/code/game/machinery/computer/aifixer.dm b/code/game/machinery/computer/aifixer.dm
index 0613c6222b4..e64708907ec 100644
--- a/code/game/machinery/computer/aifixer.dm
+++ b/code/game/machinery/computer/aifixer.dm
@@ -2,6 +2,7 @@
name = "\improper AI system integrity restorer"
icon = 'icons/obj/computer.dmi'
icon_state = "ai-fixer"
+ light_color = "#a97faa"
circuit = /obj/item/weapon/circuitboard/aifixer
req_one_access = list(access_robotics, access_heads)
var/mob/living/silicon/ai/occupant = null
diff --git a/code/game/machinery/computer/atmos_alert.dm b/code/game/machinery/computer/atmos_alert.dm
index 8306b3a87e0..640eb9c4d26 100644
--- a/code/game/machinery/computer/atmos_alert.dm
+++ b/code/game/machinery/computer/atmos_alert.dm
@@ -9,12 +9,13 @@ var/global/list/minor_air_alarms = list()
desc = "Used to access the station's atmospheric sensors."
circuit = "/obj/item/weapon/circuitboard/atmos_alert"
icon_state = "alert:0"
+ light_color = "#e6ffff"
/obj/machinery/computer/atmos_alert/New()
..()
atmosphere_alarm.register(src, /obj/machinery/computer/station_alert/update_icon)
-
-/obj/machinery/computer/atmos_alert/Del()
+
+/obj/machinery/computer/atmos_alert/Destroy()
atmosphere_alarm.unregister(src)
..()
@@ -68,16 +69,13 @@ var/global/list/minor_air_alarms = list()
var/obj/machinery/alarm/air_alarm = alarm_source.source
if(istype(air_alarm))
var/list/new_ref = list("atmos_reset" = 1)
- air_alarm.Topic(href, new_ref, custom_state = atmos_alert_topic)
+ air_alarm.Topic(href, new_ref, state = air_alarm_topic)
return 1
-var/datum/topic_state/atmos_alert/atmos_alert_topic = new()
+var/datum/topic_state/air_alarm_topic/air_alarm_topic = new()
-/datum/topic_state/atmos_alert
- flags = NANO_IGNORE_DISTANCE
-
-/datum/topic_state/air_alarm/href_list(var/mob/user)
+/datum/topic_state/air_alarm_topic/href_list(var/mob/user)
var/list/extra_href = list()
extra_href["remote_connection"] = 1
extra_href["remote_access"] = 1
diff --git a/code/game/machinery/computer/atmos_control.dm b/code/game/machinery/computer/atmos_control.dm
index d63259bc4c5..c0c798f3eb8 100644
--- a/code/game/machinery/computer/atmos_control.dm
+++ b/code/game/machinery/computer/atmos_control.dm
@@ -6,14 +6,16 @@
name = "\improper Central Atmospherics Computer"
icon = 'icons/obj/computer.dmi'
icon_state = "computer_generic"
+ light_color = "#00b000"
density = 1
anchored = 1.0
circuit = "/obj/item/weapon/circuitboard/atmoscontrol"
- var/overridden = 0 //not set yet, can't think of a good way to do it
req_access = list(access_ce)
var/list/monitored_alarm_ids = null
- var/list/monitored_alarms = null
- var/ui_ref
+ var/obj/nano_module/atmos_control/atmos_control
+
+/obj/machinery/computer/atmoscontrol/New()
+ ..()
/obj/machinery/computer/atmoscontrol/laptop
name = "Atmospherics Laptop"
@@ -21,78 +23,24 @@
icon_state = "medlaptop"
density = 0
-/obj/machinery/computer/atmoscontrol/initialize()
- ..()
- if(!monitored_alarms && monitored_alarm_ids)
- monitored_alarms = new
- for(var/obj/machinery/alarm/alarm in machines)
- if(alarm.alarm_id && alarm.alarm_id in monitored_alarm_ids)
- monitored_alarms += alarm
- // machines may not yet be ordered at this point
- monitored_alarms = dd_sortedObjectList(monitored_alarms)
-
/obj/machinery/computer/atmoscontrol/attack_ai(var/mob/user as mob)
- return ui_interact(user)
+ ui_interact(user)
/obj/machinery/computer/atmoscontrol/attack_hand(mob/user)
if(..())
- return
- return ui_interact(user)
-
-/obj/machinery/computer/atmoscontrol/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1)
- var/data[0]
- var/alarms[0]
-
- // TODO: Move these to a cache, similar to cameras
- for(var/obj/machinery/alarm/alarm in (monitored_alarms ? monitored_alarms : machines))
- alarms[++alarms.len] = list("name" = sanitize(alarm.name), "ref"= "\ref[alarm]", "danger" = max(alarm.danger_level, alarm.alarm_area.atmosalm))
- data["alarms"] = alarms
-
- ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open)
- if(!ui)
- ui = new(user, src, ui_key, "atmos_control.tmpl", src.name, 625, 625)
- ui.set_initial_data(data)
- ui.open()
- ui.set_auto_update(1)
- ui_ref = ui
+ return 1
+ ui_interact(user)
/obj/machinery/computer/atmoscontrol/attackby(var/obj/item/I as obj, var/mob/user as mob)
if(istype(I, /obj/item/weapon/card/emag) && !emagged)
user.visible_message("\red \The [user] swipes \a [I] through \the [src], causing the screen to flash!",\
"\red You swipe your [I] through \the [src], the screen flashing as you gain full control.",\
"You hear the swipe of a card through a reader, and an electronic warble.")
- emagged = 1
- overridden = 1
+ atmos_control.emagged = 1
return
return ..()
-//a bunch of this is copied from atmos alarms
-/obj/machinery/computer/atmoscontrol/Topic(href, href_list)
- if(..())
- return 1
-
- if(href_list["alarm"])
- if(ui_ref)
- var/obj/machinery/alarm/alarm = locate(href_list["alarm"]) in (monitored_alarms ? monitored_alarms : machines)
- if(alarm)
- var/datum/topic_state/TS = generate_state(alarm)
- alarm.ui_interact(usr, master_ui = ui_ref, custom_state = TS)
- return 1
-
-/obj/machinery/computer/atmoscontrol/proc/generate_state(var/alarm)
- var/datum/topic_state/air_alarm/state = new()
- state.atmos_control = src
- state.air_alarm = alarm
- return state
-
-/datum/topic_state/air_alarm
- flags = NANO_IGNORE_DISTANCE
- var/obj/machinery/computer/atmoscontrol/atmos_control = null
- var/obj/machinery/alarm/air_alarm = null
-
-/datum/topic_state/air_alarm/href_list(var/mob/user)
- var/list/extra_href = list()
- extra_href["remote_connection"] = 1
- extra_href["remote_access"] = user && (user.isAI() || atmos_control.allowed(user) || atmos_control.emagged || air_alarm.rcon_setting == RCON_YES || (air_alarm.alarm_area.atmosalm && air_alarm.rcon_setting == RCON_AUTO))
-
- return extra_href
+/obj/machinery/computer/atmoscontrol/ui_interact(var/mob/user)
+ if(!atmos_control)
+ atmos_control = new(src, req_access, req_one_access, monitored_alarm_ids)
+ atmos_control.ui_interact(user)
diff --git a/code/game/machinery/computer/buildandrepair.dm b/code/game/machinery/computer/buildandrepair.dm
index ac648624f26..a325ab90f30 100644
--- a/code/game/machinery/computer/buildandrepair.dm
+++ b/code/game/machinery/computer/buildandrepair.dm
@@ -29,7 +29,7 @@
if(!src || !WT.isOn()) return
user << "\blue You deconstruct the frame."
new /obj/item/stack/sheet/metal( src.loc, 5 )
- del(src)
+ qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
@@ -111,4 +111,4 @@
user << "\blue You connect the monitor."
var/B = new src.circuit.build_path ( src.loc )
src.circuit.construct(B)
- del(src)
+ qdel(src)
diff --git a/code/game/machinery/computer/camera.dm b/code/game/machinery/computer/camera.dm
index 8cb58a14cbf..95235be3e4f 100644
--- a/code/game/machinery/computer/camera.dm
+++ b/code/game/machinery/computer/camera.dm
@@ -1,22 +1,28 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31
+/var/camera_cache_id = 1
+
/proc/invalidateCameraCache()
- for(var/obj/machinery/computer/security/s in world)
- s.camera_cache = null
- for(var/datum/alarm/A in world)
- A.cameras = null
+ camera_cache_id = (++camera_cache_id % 999999)
/obj/machinery/computer/security
name = "security camera monitor"
desc = "Used to access the various cameras on the station."
icon_state = "cameras"
+ light_color = "#a91515"
var/obj/machinery/camera/current = null
var/last_pic = 1.0
- var/list/network = list("SS13")
+ var/list/network
var/mapping = 0//For the overview file, interesting bit of code.
+ var/cache_id = 0
circuit = /obj/item/weapon/circuitboard/security
var/camera_cache = null
+ New()
+ if(!network)
+ network = station_networks
+ ..()
+
attack_ai(var/mob/user as mob)
return attack_hand(user)
@@ -37,7 +43,8 @@
data["current"] = null
- if(isnull(camera_cache))
+ if(camera_cache_id != cache_id)
+ cache_id = camera_cache_id
cameranet.process_sort()
var/cameras[0]
@@ -48,18 +55,11 @@
var/cam = C.nano_structure()
cameras[++cameras.len] = cam
- if(C == current)
- data["current"] = cam
+ camera_cache=list2json(cameras)
- var/list/camera_list = list("cameras" = cameras)
- camera_cache=list2json(camera_list)
- else
- if(current)
- data["current"] = current.nano_structure()
-
-
- if(ui)
- ui.load_cached_data(camera_cache)
+ if(current)
+ data["current"] = current.nano_structure()
+ data["cameras"] = list("__json_cache" = camera_cache)
ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open)
if (!ui)
@@ -69,8 +69,7 @@
ui.add_template("mapContent", "sec_camera_map_content.tmpl")
// adding a template with the key "mapHeader" replaces the map header content
ui.add_template("mapHeader", "sec_camera_map_header.tmpl")
-
- ui.load_cached_data(camera_cache)
+
ui.set_initial_data(data)
ui.open()
ui.set_auto_update(1)
@@ -215,6 +214,8 @@
desc = "Damn, why do they never have anything interesting on these things?"
icon = 'icons/obj/status_display.dmi'
icon_state = "entertainment"
+ light_color = "#FFEEDB"
+ light_range_on = 2
circuit = null
/obj/machinery/computer/security/wooden_tv
@@ -222,7 +223,8 @@
desc = "An old TV hooked into the stations camera network."
icon_state = "security_det"
circuit = null
-
+ light_color = "#3848B3"
+ light_power_on = 0.5
/obj/machinery/computer/security/mining
name = "outpost camera monitor"
@@ -230,13 +232,19 @@
icon_state = "miningcameras"
network = list("MINE")
circuit = /obj/item/weapon/circuitboard/security/mining
+ light_color = "#F9BBFC"
/obj/machinery/computer/security/engineering
name = "engineering camera monitor"
desc = "Used to monitor fires and breaches."
icon_state = "engineeringcameras"
- network = list("Engineering","Power Alarms","Atmosphere Alarms","Fire Alarms")
circuit = /obj/item/weapon/circuitboard/security/engineering
+ light_color = "#FAC54B"
+
+/obj/machinery/computer/security/engineering/New()
+ if(!network)
+ network = engineering_networks
+ ..()
/obj/machinery/computer/security/nuclear
name = "head mounted camera monitor"
diff --git a/code/game/machinery/computer/card.dm b/code/game/machinery/computer/card.dm
index 4e975060888..9879e345654 100644
--- a/code/game/machinery/computer/card.dm
+++ b/code/game/machinery/computer/card.dm
@@ -4,6 +4,7 @@
name = "\improper ID card modification console"
desc = "Terminal for programming NanoTrasen employee ID cards to access parts of the station."
icon_state = "id"
+ light_color = "#0099ff"
req_access = list(access_change_ids)
circuit = "/obj/item/weapon/circuitboard/card"
var/obj/item/weapon/card/id/scan = null
diff --git a/code/game/machinery/computer/cloning.dm b/code/game/machinery/computer/cloning.dm
index fd8386a7f86..6a274e4db40 100644
--- a/code/game/machinery/computer/cloning.dm
+++ b/code/game/machinery/computer/cloning.dm
@@ -2,6 +2,7 @@
name = "cloning control console"
icon = 'icons/obj/computer.dmi'
icon_state = "dna"
+ light_color = "#315ab4"
circuit = "/obj/item/weapon/circuitboard/cloning"
req_access = list(access_heads) //Only used for record deletion right now.
var/obj/machinery/dna_scannernew/scanner = null //Linked scanner. For scanning.
@@ -14,20 +15,18 @@
var/obj/item/weapon/disk/data/diskette = null //Mostly so the geneticist can steal everything.
var/loading = 0 // Nice loading text
-/obj/machinery/computer/cloning/New()
+/obj/machinery/computer/cloning/initialize()
+ ..()
+ updatemodules()
+
+/obj/machinery/computer/cloning/Destroy()
+ releasecloner()
..()
- spawn(5)
- updatemodules()
- return
- return
/obj/machinery/computer/cloning/proc/updatemodules()
src.scanner = findscanner()
+ releasecloner()
findcloner()
- var/num = 1
- for (var/obj/machinery/clonepod/pod in pods)
- pod.connected = src
- pod.name = "[initial(pod.name)] #[num++]"
/obj/machinery/computer/cloning/proc/findscanner()
var/obj/machinery/dna_scannernew/scannerf = null
@@ -40,18 +39,26 @@
//Then look for a free one in the area
if(!scannerf)
- for(var/obj/machinery/dna_scannernew/S in get_area(src))
+ var/area/A = get_area(src)
+ for(var/obj/machinery/dna_scannernew/S in A.get_contents())
return S
return
-/obj/machinery/computer/cloning/proc/findcloner()
+/obj/machinery/computer/cloning/proc/releasecloner()
+ for(var/obj/machinery/clonepod/P in pods)
+ P.connected = null
+ P.name = initial(P.name)
pods.Cut()
- for(var/obj/machinery/clonepod/P in get_area(src))
+
+/obj/machinery/computer/cloning/proc/findcloner()
+ var/num = 1
+ var/area/A = get_area(src)
+ for(var/obj/machinery/clonepod/P in A.get_contents())
if(!P.connected)
pods += P
-
- return
+ P.connected = src
+ P.name = "[initial(P.name)] #[num++]"
/obj/machinery/computer/cloning/attackby(obj/item/W as obj, mob/user as mob)
if (istype(W, /obj/item/weapon/disk/data)) //INSERT SOME DISKETTES
@@ -221,7 +228,7 @@
src.active_record = locate(href_list["view_rec"])
if(istype(src.active_record,/datum/dna2/record))
if ((isnull(src.active_record.ckey)))
- del(src.active_record)
+ qdel(src.active_record)
src.temp = "ERROR: Record Corrupt"
else
src.menu = 3
@@ -241,7 +248,7 @@
if (istype(C)||istype(C, /obj/item/device/pda))
if(src.check_access(C))
src.records.Remove(src.active_record)
- del(src.active_record)
+ qdel(src.active_record)
src.temp = "Record deleted."
src.menu = 2
else
@@ -313,7 +320,7 @@
else if(pod.growclone(C))
temp = "Initiating cloning cycle..."
records.Remove(C)
- del(C)
+ qdel(C)
menu = 1
else
@@ -323,7 +330,7 @@
if(answer != "No" && pod.growclone(C))
temp = "Initiating cloning cycle..."
records.Remove(C)
- del(C)
+ qdel(C)
menu = 1
else
temp = "Initiating cloning cycle... Error: Post-initialisation failed. Cloning cycle aborted."
diff --git a/code/game/machinery/computer/communications.dm b/code/game/machinery/computer/communications.dm
index 4015b907f97..686ac73af66 100644
--- a/code/game/machinery/computer/communications.dm
+++ b/code/game/machinery/computer/communications.dm
@@ -5,6 +5,7 @@
name = "command and communications console"
desc = "Used to command and control the station. Can relay long-range communications."
icon_state = "comm"
+ light_color = "#0099ff"
req_access = list(access_heads)
circuit = "/obj/item/weapon/circuitboard/communications"
var/prints_intercept = 1
@@ -48,9 +49,7 @@
/obj/machinery/computer/communications/Topic(href, href_list)
if(..())
return 1
- if (src.z > 1)
- usr << "\red Unable to establish a connection: \black You're too far away from the station!"
- return
+
usr.set_machine(src)
if(!href_list["operation"])
@@ -68,8 +67,8 @@
if (I && istype(I))
if(src.check_access(I))
authenticated = 1
- if(access_captain in I.access)
- authenticated = 2
+ //if(access_captain in I.access)
+ //authenticated = 2
crew_announcement.announcer = GetNameAndAssignmentFromId(I)
if("logout")
authenticated = 0
@@ -82,7 +81,7 @@
var/obj/item/device/pda/pda = I
I = pda.id
if (I && istype(I))
- if(access_captain in I.access || access_heads in I.access) //Let heads change the alert level.
+ if(access_heads in I.access) //Let heads change the alert level.
var/old_level = security_level
if(!tmp_alertlevel) tmp_alertlevel = SEC_LEVEL_GREEN
if(tmp_alertlevel < SEC_LEVEL_GREEN) tmp_alertlevel = SEC_LEVEL_GREEN
@@ -106,7 +105,7 @@
usr << "You need to swipe your ID."
if("announce")
- if(src.authenticated==2)
+ if(src.authenticated==1)
if(message_cooldown)
usr << "Please allow at least one minute to pass between announcements"
return
@@ -183,32 +182,35 @@
// OMG CENTCOMM LETTERHEAD
if("MessageCentcomm")
- if(src.authenticated==2)
+ if(src.authenticated==1)
if(centcomm_message_cooldown)
- usr << "\red Arrays recycling. Please stand by."
+ usr << "Arrays recycling. Please stand by."
+ return
+ if(!is_relay_online())//Contact Centcom has a check, Syndie doesn't to allow for Traitor funs.
+ usr <<"No Emergency Bluespace Relay detected. Unable to transmit message."
return
var/input = sanitize(input("Please choose a message to transmit to Centcomm via quantum entanglement. Please be aware that this process is very expensive, and abuse will lead to... termination. Transmission does not guarantee a response. There is a 30 second delay before you may send another message, be clear, full and concise.", "To abort, send an empty message.", ""))
if(!input || !(usr in view(1,src)))
return
Centcomm_announce(input, usr)
- usr << "\blue Message transmitted."
+ usr << "Message transmitted."
log_say("[key_name(usr)] has made an IA Centcomm announcement: [input]")
centcomm_message_cooldown = 1
- spawn(300)//10 minute cooldown
+ spawn(300)//30 second cooldown
centcomm_message_cooldown = 0
// OMG SYNDICATE ...LETTERHEAD
if("MessageSyndicate")
- if((src.authenticated==2) && (src.emagged))
+ if((src.authenticated==1) && (src.emagged))
if(centcomm_message_cooldown)
- usr << "\red Arrays recycling. Please stand by."
+ usr << "Arrays recycling. Please stand by."
return
var/input = sanitize(input(usr, "Please choose a message to transmit to \[ABNORMAL ROUTING CORDINATES\] via quantum entanglement. Please be aware that this process is very expensive, and abuse will lead to... termination. Transmission does not guarantee a response. There is a 30 second delay before you may send another message, be clear, full and concise.", "To abort, send an empty message.", ""))
if(!input || !(usr in view(1,src)))
return
Syndicate_announce(input, usr)
- usr << "\blue Message transmitted."
+ usr << "Message transmitted."
log_say("[key_name(usr)] has made an illegal announcement: [input]")
centcomm_message_cooldown = 1
spawn(300)//10 minute cooldown
@@ -279,9 +281,6 @@
/obj/machinery/computer/communications/attack_hand(var/mob/user as mob)
if(..())
return
- if (src.z > 6)
- user << "\red Unable to establish a connection: \black You're too far away from the station!"
- return
user.set_machine(src)
var/dat = "Communications Console"
@@ -301,7 +300,7 @@
if(STATE_DEFAULT)
if (src.authenticated)
dat += " \[ Log Out \]"
- if (src.authenticated==2)
+ if (src.authenticated==1)
dat += " \[ Make An Announcement \]"
if(src.emagged == 0)
dat += " \[ Send an emergency message to Centcomm \]"
@@ -430,6 +429,10 @@
if ((!( ticker ) || !emergency_shuttle.location()))
return
+ if(!universe.OnShuttleCall(usr))
+ user << "Cannot establish a bluespace connection."
+ return
+
if(deathsquad.deployed)
user << "Centcom will not allow the shuttle to be called. Consider all contracts terminated."
return
@@ -439,7 +442,7 @@
return
if(world.time < 6000) // Ten minute grace period to let the game get going without lolmetagaming. -- TLE
- user << "The emergency shuttle is refueling. Please wait another [round((6000-world.time)/60)] minutes before trying again."
+ user << "The emergency shuttle is refueling. Please wait another [round((6000-world.time)/600)] minute\s before trying again."
return
if(emergency_shuttle.going_to_centcom())
@@ -519,6 +522,13 @@
message_admins("[key_name_admin(user)] has recalled the shuttle.", 1)
return
+
+/proc/is_relay_online()
+ for(var/obj/machinery/bluespacerelay/M in world)
+ if(M.stat == 0)
+ return 1
+ return 0
+
/obj/machinery/computer/communications/proc/post_status(var/command, var/data1, var/data2)
var/datum/radio_frequency/frequency = radio_controller.return_frequency(1435)
@@ -542,7 +552,7 @@
frequency.post_signal(src, status_signal)
-/obj/machinery/computer/communications/Del()
+/obj/machinery/computer/communications/Destroy()
for(var/obj/machinery/computer/communications/commconsole in world)
if(istype(commconsole.loc,/turf) && commconsole != src)
@@ -565,7 +575,7 @@
..()
-/obj/item/weapon/circuitboard/communications/Del()
+/obj/item/weapon/circuitboard/communications/Destroy()
for(var/obj/machinery/computer/communications/commconsole in world)
if(istype(commconsole.loc,/turf))
diff --git a/code/game/machinery/computer/computer.dm b/code/game/machinery/computer/computer.dm
index 304ac7d1afb..37cb62c5cbf 100644
--- a/code/game/machinery/computer/computer.dm
+++ b/code/game/machinery/computer/computer.dm
@@ -9,11 +9,8 @@
var/circuit = null //The path to the circuit board type. If circuit==null, the computer can't be disassembled.
var/processing = 0
-/obj/machinery/computer/New()
- ..()
- if(ticker)
- initialize()
-
+ var/light_range_on = 3
+ var/light_power_on = 1
/obj/machinery/computer/initialize()
power_change()
@@ -27,7 +24,7 @@
for(var/x in verbs)
verbs -= x
set_broken()
- var/datum/effect/effect/system/smoke_spread/smoke = new /datum/effect/effect/system/smoke_spread()
+ var/datum/effect/effect/system/smoke_spread/smoke = PoolOrNew(/datum/effect/effect/system/smoke_spread)
smoke.set_up(5, 0, src)
smoke.start()
return
@@ -41,11 +38,11 @@
/obj/machinery/computer/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(25))
- del(src)
+ qdel(src)
return
if (prob(50))
for(var/x in verbs)
@@ -60,6 +57,9 @@
return
/obj/machinery/computer/bullet_act(var/obj/item/projectile/Proj)
+ if(!(Proj.damage_type == BRUTE || Proj.damage_type == BURN))
+ return
+
if(prob(Proj.damage))
set_broken()
..()
@@ -89,6 +89,10 @@
/obj/machinery/computer/power_change()
..()
update_icon()
+ if(stat & NOPOWER)
+ set_light(0)
+ else
+ set_light(light_range_on, light_power_on)
/obj/machinery/computer/proc/set_broken()
@@ -129,7 +133,7 @@
A.state = 4
A.icon_state = "4"
M.deconstruct(src)
- del(src)
+ qdel(src)
else
src.attack_hand(user)
return
diff --git a/code/game/machinery/computer/crew.dm b/code/game/machinery/computer/crew.dm
index b5394328b83..6928d104ca7 100644
--- a/code/game/machinery/computer/crew.dm
+++ b/code/game/machinery/computer/crew.dm
@@ -2,6 +2,7 @@
name = "crew monitoring computer"
desc = "Used to monitor active health sensors built into most of the crew's uniforms."
icon_state = "crew"
+ light_color = "#315ab4"
use_power = 1
idle_power_usage = 250
active_power_usage = 500
diff --git a/code/game/machinery/computer/guestpass.dm b/code/game/machinery/computer/guestpass.dm
index 40fc0b99145..5add587e77c 100644
--- a/code/game/machinery/computer/guestpass.dm
+++ b/code/game/machinery/computer/guestpass.dm
@@ -5,6 +5,7 @@
name = "guest pass"
desc = "Allows temporary access to station areas."
icon_state = "guest"
+ light_color = "#0099ff"
var/temp_access = list() //to prevent agent cards stealing access as permanent
var/expiration_time = 0
@@ -186,4 +187,4 @@
else
usr << "\red Cannot issue pass without issuing ID."
updateUsrDialog()
- return
\ No newline at end of file
+ return
diff --git a/code/game/machinery/computer/medical.dm b/code/game/machinery/computer/medical.dm
index c6a30995d20..65322b741da 100644
--- a/code/game/machinery/computer/medical.dm
+++ b/code/game/machinery/computer/medical.dm
@@ -4,6 +4,7 @@
name = "medical records console"
desc = "Used to view, edit and maintain medical records."
icon_state = "medcomp"
+ light_color = "#315ab4"
req_one_access = list(access_medical, access_forensics_lockers)
circuit = "/obj/item/weapon/circuitboard/med_data"
var/obj/item/weapon/card/id/scan = null
@@ -124,7 +125,7 @@
dat += "Back"
dat += " Medical Robots:"
var/bdat = null
- for(var/obj/machinery/bot/medbot/M in world)
+ for(var/mob/living/bot/medbot/M in world)
if(M.z != src.z) continue //only find medibots on the same z-level as the computer
var/turf/bl = get_turf(M)
@@ -240,7 +241,7 @@
if (href_list["del_all2"])
for(var/datum/data/record/R in data_core.medical)
//R = null
- del(R)
+ qdel(R)
//Foreach goto(494)
src.temp = "All records deleted."
@@ -408,7 +409,7 @@
if (href_list["del_r2"])
if (src.active2)
//src.active2 = null
- del(src.active2)
+ qdel(src.active2)
if (href_list["d_rec"])
var/datum/data/record/R = locate(href_list["d_rec"])
@@ -542,7 +543,7 @@
continue
else if(prob(1))
- del(R)
+ qdel(R)
continue
..(severity)
diff --git a/code/game/machinery/computer/message.dm b/code/game/machinery/computer/message.dm
index 94eadf7f11e..f775c5f9508 100644
--- a/code/game/machinery/computer/message.dm
+++ b/code/game/machinery/computer/message.dm
@@ -4,6 +4,7 @@
name = "messaging monitor console"
desc = "Used to access and maintain data on messaging servers. Allows you to view PDA and request console messages."
icon_state = "comm_logs"
+ light_color = "#00b000"
var/hack_icon = "comm_logsc"
var/normal_icon = "comm_logs"
circuit = "/obj/item/weapon/circuitboard/message_monitor"
diff --git a/code/game/machinery/computer/pod.dm b/code/game/machinery/computer/pod.dm
index 0c7830a78a7..257e76ede8b 100644
--- a/code/game/machinery/computer/pod.dm
+++ b/code/game/machinery/computer/pod.dm
@@ -4,6 +4,7 @@
name = "pod launch control console"
desc = "A control console for launching pods. Some people prefer firing Mechas."
icon_state = "computer_generic"
+ light_color = "#00b000"
circuit = /obj/item/weapon/circuitboard/pod
var/id = 1.0
var/obj/machinery/mass_driver/connected = null
@@ -77,7 +78,7 @@
A.state = 3
A.icon_state = "3"
A.anchored = 1
- del(src)
+ qdel(src)
else
user << "\blue You disconnect the monitor."
var/obj/structure/computerframe/A = new /obj/structure/computerframe( loc )
@@ -100,7 +101,7 @@
A.state = 4
A.icon_state = "4"
A.anchored = 1
- del(src)
+ qdel(src)
else
attack_hand(user)
return
diff --git a/code/game/machinery/computer/prisoner.dm b/code/game/machinery/computer/prisoner.dm
index 976209305a9..93d38fabeb6 100644
--- a/code/game/machinery/computer/prisoner.dm
+++ b/code/game/machinery/computer/prisoner.dm
@@ -4,6 +4,7 @@
name = "prisoner management console"
icon = 'icons/obj/computer.dmi'
icon_state = "explosive"
+ light_color = "#a91515"
req_access = list(access_armory)
circuit = "/obj/item/weapon/circuitboard/prisoner"
var/id = 0.0
diff --git a/code/game/machinery/computer/prisonshuttle.dm b/code/game/machinery/computer/prisonshuttle.dm
index 84ba06fa021..0fd1a2df05e 100644
--- a/code/game/machinery/computer/prisonshuttle.dm
+++ b/code/game/machinery/computer/prisonshuttle.dm
@@ -14,6 +14,7 @@ var/prison_shuttle_timeleft = 0
name = "prison shuttle control console"
icon = 'icons/obj/computer.dmi'
icon_state = "shuttle"
+ light_color = "#00ffff"
req_access = list(access_security)
circuit = "/obj/item/weapon/circuitboard/prison_shuttle"
var/temp = null
@@ -45,7 +46,7 @@ var/prison_shuttle_timeleft = 0
A.state = 4
A.icon_state = "4"
- del(src)
+ qdel(src)
else if(istype(I,/obj/item/weapon/card/emag) && (!hacked))
hacked = 1
user << "\blue You disable the lock."
@@ -194,7 +195,7 @@ var/prison_shuttle_timeleft = 0
for(var/atom/movable/AM as mob|obj in T)
AM.Move(D)
if(istype(T, /turf/simulated))
- del(T)
+ qdel(T)
start_location.move_contents_to(end_location)
if(1)
@@ -224,7 +225,7 @@ var/prison_shuttle_timeleft = 0
for(var/atom/movable/AM as mob|obj in T)
AM.Move(D)
if(istype(T, /turf/simulated))
- del(T)
+ qdel(T)
for(var/mob/living/carbon/bug in end_location) // If someone somehow is still in the shuttle's docking area...
bug.gib()
@@ -233,4 +234,4 @@ var/prison_shuttle_timeleft = 0
pest.gib()
start_location.move_contents_to(end_location)
- return
\ No newline at end of file
+ return
diff --git a/code/game/machinery/computer/robot.dm b/code/game/machinery/computer/robot.dm
index 41d73ee2ae5..84a6b7730c7 100644
--- a/code/game/machinery/computer/robot.dm
+++ b/code/game/machinery/computer/robot.dm
@@ -5,6 +5,7 @@
desc = "Used to remotely lockdown or detonate linked cyborgs."
icon = 'icons/obj/computer.dmi'
icon_state = "robot"
+ light_color = "#a97faa"
req_access = list(access_robotics)
circuit = "/obj/item/weapon/circuitboard/robotics"
diff --git a/code/game/machinery/computer/security.dm b/code/game/machinery/computer/security.dm
index c05f0f78be8..c97be5be09e 100644
--- a/code/game/machinery/computer/security.dm
+++ b/code/game/machinery/computer/security.dm
@@ -4,6 +4,7 @@
name = "security records console"
desc = "Used to view, edit and maintain security records"
icon_state = "security"
+ light_color = "#a91515"
req_one_access = list(access_security, access_forensics_lockers)
circuit = "/obj/item/weapon/circuitboard/secure_data"
var/obj/item/weapon/card/id/scan = null
@@ -377,7 +378,7 @@ What a mess.*/
if ("Purge All Records")
for(var/datum/data/record/R in data_core.security)
- del(R)
+ qdel(R)
temp = "All Security records deleted."
if ("Add Entry")
@@ -549,17 +550,17 @@ What a mess.*/
if ("Delete Record (Security) Execute")
if (active2)
- del(active2)
+ qdel(active2)
if ("Delete Record (ALL) Execute")
if (active1)
for(var/datum/data/record/R in data_core.medical)
if ((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
- del(R)
+ qdel(R)
else
- del(active1)
+ qdel(active1)
if (active2)
- del(active2)
+ qdel(active2)
else
temp = "This function does not appear to be working at the moment. Our apologies."
@@ -605,7 +606,7 @@ What a mess.*/
continue
else if(prob(1))
- del(R)
+ qdel(R)
continue
..(severity)
diff --git a/code/game/machinery/computer/shuttle.dm b/code/game/machinery/computer/shuttle.dm
index b8b25b3e34b..3fca14135a0 100644
--- a/code/game/machinery/computer/shuttle.dm
+++ b/code/game/machinery/computer/shuttle.dm
@@ -2,6 +2,7 @@
name = "Shuttle"
desc = "For shuttle control."
icon_state = "shuttle"
+ light_color = "#00ffff"
var/auth_need = 3.0
var/list/authorized = list( )
@@ -43,7 +44,7 @@
world << "\blue Alert: Shuttle launch time shortened to 10 seconds!"
emergency_shuttle.set_launch_countdown(10)
//src.authorized = null
- del(src.authorized)
+ qdel(src.authorized)
src.authorized = list( )
if("Repeal")
diff --git a/code/game/machinery/computer/skills.dm b/code/game/machinery/computer/skills.dm
index aa92a59094c..e0c6f724abf 100644
--- a/code/game/machinery/computer/skills.dm
+++ b/code/game/machinery/computer/skills.dm
@@ -4,6 +4,7 @@
name = "employment records console"
desc = "Used to view, edit and maintain employment records."
icon_state = "medlaptop"
+ light_color = "#00b000"
req_one_access = list(access_heads)
circuit = "/obj/item/weapon/circuitboard/skills"
var/obj/item/weapon/card/id/scan = null
@@ -289,7 +290,7 @@ What a mess.*/
if(PDA_Manifest.len)
PDA_Manifest.Cut()
for(var/datum/data/record/R in data_core.security)
- del(R)
+ qdel(R)
temp = "All Employment records deleted."
if ("Delete Record (ALL)")
@@ -373,9 +374,9 @@ What a mess.*/
PDA_Manifest.Cut()
for(var/datum/data/record/R in data_core.medical)
if ((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
- del(R)
+ qdel(R)
else
- del(active1)
+ qdel(active1)
else
temp = "This function does not appear to be working at the moment. Our apologies."
@@ -408,7 +409,7 @@ What a mess.*/
continue
else if(prob(1))
- del(R)
+ qdel(R)
continue
- ..(severity)
\ No newline at end of file
+ ..(severity)
diff --git a/code/game/machinery/computer/specops_shuttle.dm b/code/game/machinery/computer/specops_shuttle.dm
index 01728b4e504..3d44a7a260c 100644
--- a/code/game/machinery/computer/specops_shuttle.dm
+++ b/code/game/machinery/computer/specops_shuttle.dm
@@ -15,6 +15,7 @@ var/specops_shuttle_timeleft = 0
name = "special operations shuttle control console"
icon = 'icons/obj/computer.dmi'
icon_state = "shuttle"
+ light_color = "#00ffff"
req_access = list(access_cent_specops)
// req_access = list(ACCESS_CENT_SPECOPS)
var/temp = null
@@ -75,7 +76,7 @@ var/specops_shuttle_timeleft = 0
for(var/atom/movable/AM as mob|obj in T)
AM.Move(D)
if(istype(T, /turf/simulated))
- del(T)
+ qdel(T)
for(var/mob/living/carbon/bug in end_location) // If someone somehow is still in the shuttle's docking area...
bug.gib()
@@ -94,7 +95,7 @@ var/specops_shuttle_timeleft = 0
for(var/obj/machinery/computer/specops_shuttle/S in world)
S.specops_shuttle_timereset = world.time + SPECOPS_RETURN_DELAY
- del(announcer)
+ qdel(announcer)
/proc/specops_process()
var/area/centcom/specops/special_ops = locate()//Where is the specops area located?
@@ -224,7 +225,7 @@ var/specops_shuttle_timeleft = 0
for(var/atom/movable/AM as mob|obj in T)
AM.Move(D)
if(istype(T, /turf/simulated))
- del(T)
+ qdel(T)
start_location.move_contents_to(end_location)
@@ -235,7 +236,7 @@ var/specops_shuttle_timeleft = 0
for(var/obj/machinery/computer/specops_shuttle/S in world)
S.specops_shuttle_timereset = world.time + SPECOPS_RETURN_DELAY
- del(announcer)
+ qdel(announcer)
/proc/specops_can_move()
if(specops_shuttle_moving_to_station || specops_shuttle_moving_to_centcom)
diff --git a/code/game/machinery/computer/station_alert.dm b/code/game/machinery/computer/station_alert.dm
index ab136ca3714..696273d2ab8 100644
--- a/code/game/machinery/computer/station_alert.dm
+++ b/code/game/machinery/computer/station_alert.dm
@@ -3,17 +3,27 @@
name = "Station Alert Console"
desc = "Used to access the station's automated alert system."
icon_state = "alert:0"
- circuit = "/obj/item/weapon/circuitboard/stationalert"
- var/alarms = list("Fire"=list(), "Atmosphere"=list(), "Power"=list())
- var/obj/nano_module/alarm_monitor/engineering/alarm_monitor
+ light_color = "#e6ffff"
+ circuit = /obj/item/weapon/circuitboard/stationalert_engineering
+ var/obj/nano_module/alarm_monitor/alarm_monitor
+ var/monitor_type = /obj/nano_module/alarm_monitor/engineering
+
+/obj/machinery/computer/station_alert/security
+ monitor_type = /obj/nano_module/alarm_monitor/security
+ circuit = /obj/item/weapon/circuitboard/stationalert_security
+
+/obj/machinery/computer/station_alert/all
+ monitor_type = /obj/nano_module/alarm_monitor/all
+ circuit = /obj/item/weapon/circuitboard/stationalert_all
/obj/machinery/computer/station_alert/New()
- alarm_monitor = new(src)
- alarm_monitor.register(src, /obj/machinery/computer/station_alert/update_icon)
..()
+ alarm_monitor = new monitor_type(src)
+ alarm_monitor.register(src, /obj/machinery/computer/station_alert/update_icon)
-/obj/machinery/computer/station_alert/Del()
+/obj/machinery/computer/station_alert/Destroy()
alarm_monitor.unregister(src)
+ qdel(alarm_monitor)
..()
/obj/machinery/computer/station_alert/attack_ai(mob/user)
diff --git a/code/game/machinery/computer/supply.dm b/code/game/machinery/computer/supply.dm
index 233a2711085..b5df1127c95 100644
--- a/code/game/machinery/computer/supply.dm
+++ b/code/game/machinery/computer/supply.dm
@@ -2,6 +2,7 @@
name = "supply control console"
icon = 'icons/obj/computer.dmi'
icon_state = "supply"
+ light_color = "#b88b2e"
req_access = list(access_cargo)
circuit = "/obj/item/weapon/circuitboard/supplycomp"
var/temp = null
diff --git a/code/game/machinery/computer/syndicate_specops_shuttle.dm b/code/game/machinery/computer/syndicate_specops_shuttle.dm
index 970bb362c36..dd921abf090 100644
--- a/code/game/machinery/computer/syndicate_specops_shuttle.dm
+++ b/code/game/machinery/computer/syndicate_specops_shuttle.dm
@@ -14,6 +14,7 @@ var/syndicate_elite_shuttle_timeleft = 0
name = "elite syndicate squad shuttle control console"
icon = 'icons/obj/computer.dmi'
icon_state = "syndishuttle"
+ light_color = "#00ffff"
req_access = list(access_cent_specops)
var/temp = null
var/hacked = 0
@@ -160,7 +161,7 @@ var/syndicate_elite_shuttle_timeleft = 0
for(var/atom/movable/AM as mob|obj in T)
AM.Move(D)
if(istype(T, /turf/simulated))
- del(T)
+ qdel(T)
for(var/mob/living/carbon/bug in end_location) // If someone somehow is still in the shuttle's docking area...
bug.gib()
@@ -256,4 +257,4 @@ var/syndicate_elite_shuttle_timeleft = 0
add_fingerprint(usr)
updateUsrDialog()
- return
\ No newline at end of file
+ return
diff --git a/code/game/machinery/computer3/buildandrepair.dm b/code/game/machinery/computer3/buildandrepair.dm
index 720a61fd401..49ccc66dc87 100644
--- a/code/game/machinery/computer3/buildandrepair.dm
+++ b/code/game/machinery/computer3/buildandrepair.dm
@@ -15,7 +15,6 @@
var/list/req_components = null
var/powernet = null
var/list/records = null
- var/frame_desc = null
var/datum/file/program/OS = new/datum/file/program/ntos
@@ -95,7 +94,7 @@
if(!src || !WT.isOn()) return
user << "\blue You deconstruct the frame."
new /obj/item/stack/sheet/metal( src.loc, 5 )
- del(src)
+ qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
@@ -160,7 +159,7 @@
if(do_after(user, 20))
if(P)
P:amount -= 5
- if(!P:amount) del(P)
+ if(!P:amount) qdel(P)
user << "\blue You add cables to the frame."
src.state = 3
src.icon_state = "3"
@@ -212,7 +211,7 @@
if(circuit.OS)
circuit.OS.computer = B
B.RefreshParts() // todo
- del(src)
+ qdel(src)
/*
This will remove peripherals if you specify one, but the main function is to
diff --git a/code/game/machinery/computer3/computer.dm b/code/game/machinery/computer3/computer.dm
index 082d8a2ee27..7357957a379 100644
--- a/code/game/machinery/computer3/computer.dm
+++ b/code/game/machinery/computer3/computer.dm
@@ -215,11 +215,11 @@
ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(25))
- del(src)
+ qdel(src)
return
if (prob(50))
for(var/x in verbs)
@@ -278,8 +278,8 @@
chan = power_channel
var/area/A = get_area(loc)
- if(istype(A) && A.master && A.master.powered(chan))
- A.master.use_power(amount, chan)
+ if(istype(A) && A.powered(chan))
+ A.use_power(amount, chan)
else if(battery && battery.charge > 0)
battery.use(amount)
diff --git a/code/game/machinery/computer3/computers/HolodeckControl.dm b/code/game/machinery/computer3/computers/HolodeckControl.dm
index 80d60afd072..9e4532604b7 100644
--- a/code/game/machinery/computer3/computers/HolodeckControl.dm
+++ b/code/game/machinery/computer3/computers/HolodeckControl.dm
@@ -160,7 +160,7 @@
if(!silent)
var/obj/oldobj = obj
obj.visible_message("The [oldobj.name] fades away!")
- del(obj)
+ qdel(obj)
proc/checkInteg(var/area/A)
for(var/turf/T in A)
@@ -213,10 +213,10 @@
derez(item)
for(var/obj/effect/decal/cleanable/blood/B in linkedholodeck)
- del(B)
+ qdel(B)
for(var/mob/living/simple_animal/hostile/carp/C in linkedholodeck)
- del(C)
+ qdel(C)
holographic_items = A.copy_contents_to(linkedholodeck , 1)
diff --git a/code/game/machinery/computer3/computers/camera.dm b/code/game/machinery/computer3/computers/camera.dm
index 17f14e0cbfe..f90b0526ee5 100644
--- a/code/game/machinery/computer3/computers/camera.dm
+++ b/code/game/machinery/computer3/computers/camera.dm
@@ -238,7 +238,7 @@
camera_list = "Network Key: [key.title] [topic_link(src,"keyselect","\[ Select key \]")]"
for(var/obj/machinery/camera/C in temp_list)
- if(C.status)
+ if(C.can_use())
camera_list += "[C.c_tag] - [topic_link(src,"show=\ref[C]","Show")] "
else
camera_list += "[C.c_tag] - DEACTIVATED "
@@ -264,7 +264,7 @@
if("show" in href_list)
var/obj/machinery/camera/C = locate(href_list["show"])
- if(istype(C) && C.status)
+ if(istype(C) && C.can_use())
set_current(C)
usr.reset_view(C)
interact()
diff --git a/code/game/machinery/computer3/computers/medical.dm b/code/game/machinery/computer3/computers/medical.dm
index adb7ff90797..aec0b615f52 100644
--- a/code/game/machinery/computer3/computers/medical.dm
+++ b/code/game/machinery/computer3/computers/medical.dm
@@ -136,7 +136,7 @@
dat += "Back"
dat += " Medical Robots:"
var/bdat = null
- for(var/obj/machinery/bot/medbot/M in world)
+ for(var/mob/living/bot/medbot/M in world)
if(M.z != computer.z) continue //only find medibots on the same z-level as the computer
var/turf/bl = get_turf(M)
@@ -254,7 +254,7 @@
if (href_list["del_all2"])
for(var/datum/data/record/R in data_core.medical)
//R = null
- del(R)
+ qdel(R)
//Foreach goto(494)
src.temp = "All records deleted."
@@ -422,7 +422,7 @@
if (href_list["del_r2"])
if (src.active2)
//src.active2 = null
- del(src.active2)
+ qdel(src.active2)
if (href_list["d_rec"])
var/datum/data/record/R = locate(href_list["d_rec"])
diff --git a/code/game/machinery/computer3/computers/security.dm b/code/game/machinery/computer3/computers/security.dm
index 924f32b1b7d..f2de7648943 100644
--- a/code/game/machinery/computer3/computers/security.dm
+++ b/code/game/machinery/computer3/computers/security.dm
@@ -397,7 +397,7 @@ What a mess.*/
if ("Purge All Records")
for(var/datum/data/record/R in data_core.security)
- del(R)
+ qdel(R)
temp = "All Security records deleted."
if ("Add Entry")
@@ -558,17 +558,17 @@ What a mess.*/
if ("Delete Record (Security) Execute")
if (active2)
- del(active2)
+ qdel(active2)
if ("Delete Record (ALL) Execute")
if (active1)
for(var/datum/data/record/R in data_core.medical)
if ((R.fields["name"] == active1.fields["name"] || R.fields["id"] == active1.fields["id"]))
- del(R)
+ qdel(R)
else
- del(active1)
+ qdel(active1)
if (active2)
- del(active2)
+ qdel(active2)
else
temp = "This function does not appear to be working at the moment. Our apologies."
@@ -601,7 +601,7 @@ What a mess.*/
continue
else if(prob(1))
- del(R)
+ qdel(R)
continue
..(severity)
diff --git a/code/game/machinery/computer3/laptop.dm b/code/game/machinery/computer3/laptop.dm
index e0156e874e2..484db524625 100644
--- a/code/game/machinery/computer3/laptop.dm
+++ b/code/game/machinery/computer3/laptop.dm
@@ -52,7 +52,7 @@
O.loc = loc
usr << "\The [src] crumbles to pieces."
spawn(5)
- del src
+ qdel(src)
return
if(!stored_computer.manipulating)
@@ -65,7 +65,7 @@
spawn(5)
stored_computer.manipulating = 0
- del src
+ qdel(src)
else
usr << "\red You are already opening the computer!"
@@ -185,12 +185,12 @@
else
stat &= ~NOPOWER
- Del()
+ Destroy()
if(istype(loc,/obj/item/device/laptop))
var/obj/O = loc
spawn(5)
if(O)
- del O
+ qdel(O)
..()
diff --git a/code/game/machinery/computer3/lapvend.dm b/code/game/machinery/computer3/lapvend.dm
index 72531b5d8ee..b2e84f1cd27 100644
--- a/code/game/machinery/computer3/lapvend.dm
+++ b/code/game/machinery/computer3/lapvend.dm
@@ -31,7 +31,7 @@
/obj/machinery/lapvend/blob_act()
if (prob(50))
spawn(0)
- del(src)
+ qdel(src)
return
return
@@ -202,10 +202,10 @@
if (network == 3)
newlap.spawn_parts += (/obj/item/part/computer/networking/cable)
if (power == 1)
- del(newlap.battery)
+ qdel(newlap.battery)
newlap.battery = new /obj/item/weapon/cell/high(newlap)
if (power == 2)
- del(newlap.battery)
+ qdel(newlap.battery)
newlap.battery = new /obj/item/weapon/cell/super(newlap)
newlap.spawn_parts()
@@ -404,7 +404,7 @@
T.time = worldtime2text()
vendor_account.transaction_log.Add(T)
- del(relap)
+ qdel(relap)
vendmode = 0
cardreader = 0
floppy = 0
diff --git a/code/game/machinery/computer3/networking.dm b/code/game/machinery/computer3/networking.dm
index 27d77890087..66d25dda5ae 100644
--- a/code/game/machinery/computer3/networking.dm
+++ b/code/game/machinery/computer3/networking.dm
@@ -143,10 +143,9 @@
if(typekey == null)
typekey = /obj/machinery
var/list/machines = list()
- for(var/area/area in A.related)
- for(var/obj/O in area.contents)
- if(istype(O,typekey))
- machines |= O
+ for(var/obj/O in A.contents)
+ if(istype(O,typekey))
+ machines |= O
return machines
verify_machine(var/obj/previous)
if(!previous) return 0
diff --git a/code/game/machinery/computer3/program.dm b/code/game/machinery/computer3/program.dm
index 74083b8ffde..0667fe2f730 100644
--- a/code/game/machinery/computer3/program.dm
+++ b/code/game/machinery/computer3/program.dm
@@ -111,7 +111,7 @@ Programs are a file that can be executed
update_icon()
if(popup)
popup.close()
- del popup
+ qdel(popup)
return
/*
diff --git a/code/game/machinery/constructable_frame.dm b/code/game/machinery/constructable_frame.dm
index 54da833b6fd..977cda03b30 100644
--- a/code/game/machinery/constructable_frame.dm
+++ b/code/game/machinery/constructable_frame.dm
@@ -18,15 +18,11 @@
proc/update_desc()
var/D
if(req_components)
- D = "Requires "
- var/first = 1
+ var/list/component_list = new
for(var/I in req_components)
if(req_components[I] > 0)
- D += "[first?"":", "][num2text(req_components[I])] [req_component_names[I]]"
- first = 0
- if(first) // nothing needs to be added, then
- D += "nothing"
- D += "."
+ component_list += "[num2text(req_components[I])] [req_component_names[I]]"
+ D = "Requires [english_list(component_list)]."
desc = D
/obj/machinery/constructable_frame/machine_frame
@@ -50,7 +46,7 @@
playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
user << "\blue You dismantle the frame"
new /obj/item/stack/sheet/metal(src.loc, 5)
- del(src)
+ qdel(src)
if(2)
if(istype(P, /obj/item/weapon/circuitboard))
var/obj/item/weapon/circuitboard/B = P
@@ -71,10 +67,7 @@
var/cp = text2path(A)
var/obj/ct = new cp() // have to quickly instantiate it get name
req_component_names[A] = ct.name
- if(circuit.frame_desc)
- desc = circuit.frame_desc
- else
- update_desc()
+ update_desc()
user << desc
else
user << "\red This frame does not accept circuit boards of this type!"
@@ -126,7 +119,7 @@
else
circuit.loc = null
new_machine.RefreshParts()
- del(src)
+ qdel(src)
else
if(istype(P, /obj/item))
for(var/I in req_components)
diff --git a/code/game/machinery/cryo.dm b/code/game/machinery/cryo.dm
index a9858742c94..cb0620691c7 100644
--- a/code/game/machinery/cryo.dm
+++ b/code/game/machinery/cryo.dm
@@ -24,9 +24,11 @@
..()
initialize_directions = dir
-/obj/machinery/atmospherics/unary/cryo_cell/Del()
- if(occupant)
- occupant.loc = loc
+/obj/machinery/atmospherics/unary/cryo_cell/Destroy()
+ var/turf/T = loc
+ T.contents += contents
+ if(beaker)
+ beaker.loc = get_step(loc, SOUTH) //Beaker is carefully ejected from the wreckage of the cryotube
..()
/obj/machinery/atmospherics/unary/cryo_cell/initialize()
@@ -190,7 +192,7 @@
return
var/mob/M = G:affecting
if(put_mob(M))
- del(G)
+ qdel(G)
return
/obj/machinery/atmospherics/unary/cryo_cell/update_icon()
@@ -230,8 +232,7 @@
var/has_clonexa = occupant.reagents.get_reagent_amount("clonexadone") >= 1
var/has_cryo_medicine = has_cryo || has_clonexa
if(beaker && !has_cryo_medicine)
- beaker.reagents.trans_to(occupant, 1, 10)
- beaker.reagents.reaction(occupant)
+ beaker.reagents.trans_to_mob(occupant, 1, CHEM_BLOOD, 10)
/obj/machinery/atmospherics/unary/cryo_cell/proc/heat_gas_contents()
if(air_contents.total_moles < 1)
diff --git a/code/game/machinery/cryopod.dm b/code/game/machinery/cryopod.dm
index f56a271a0bf..fbb6e8b10ca 100644
--- a/code/game/machinery/cryopod.dm
+++ b/code/game/machinery/cryopod.dm
@@ -234,7 +234,7 @@
..()
-/obj/machinery/cryopod/Del()
+/obj/machinery/cryopod/Destroy()
if(occupant)
occupant.loc = loc
occupant.resting = 1
@@ -291,12 +291,12 @@
var/mob/living/silicon/robot/R = occupant
if(!istype(R)) return ..()
- del(R.mmi)
+ qdel(R.mmi)
for(var/obj/item/I in R.module) // the tools the borg has; metal, glass, guns etc
for(var/obj/item/O in I) // the things inside the tools, if anything; mainly for janiborg trash bags
O.loc = R
- del(I)
- del(R.module)
+ qdel(I)
+ qdel(R.module)
return ..()
@@ -308,14 +308,14 @@
occupant.drop_from_inventory(W)
W.loc = src
- if(W.contents.len) //Make sure we catch anything not handled by del() on the items.
+ if(W.contents.len) //Make sure we catch anything not handled by qdel() on the items.
for(var/obj/item/O in W.contents)
if(istype(O,/obj/item/weapon/storage/internal)) //Stop eating pockets, you fuck!
continue
O.loc = src
//Delete all items not on the preservation list.
- var/list/items = src.contents
+ var/list/items = src.contents.Copy()
items -= occupant // Don't delete the occupant
items -= announce // or the autosay radio.
@@ -328,7 +328,7 @@
break
if(!preserve)
- del(W)
+ qdel(W)
else
if(control_computer && control_computer.allow_items)
control_computer.frozen_items += W
@@ -341,7 +341,7 @@
// We don't want revs to get objectives that aren't for heads of staff. Letting
// them win or lose based on cryo is silly so we remove the objective.
if(istype(O,/datum/objective/mutiny) && O.target == occupant.mind)
- del(O)
+ qdel(O)
else if(O.target && istype(O.target,/datum/mind))
if(O.target == occupant.mind)
if(O.owner && O.owner.current)
@@ -353,7 +353,7 @@
if(!(O.target))
all_objectives -= O
O.owner.objectives -= O
- del(O)
+ qdel(O)
//Handle job slot/tater cleanup.
var/job = occupant.mind.assigned_role
@@ -361,7 +361,7 @@
job_master.FreeRole(job)
if(occupant.mind.objectives.len)
- del(occupant.mind.objectives)
+ qdel(occupant.mind.objectives)
occupant.mind.special_role = null
//else
//if(ticker.mode.name == "AutoTraitor")
@@ -374,13 +374,13 @@
PDA_Manifest.Cut()
for(var/datum/data/record/R in data_core.medical)
if ((R.fields["name"] == occupant.real_name))
- del(R)
+ qdel(R)
for(var/datum/data/record/T in data_core.security)
if ((T.fields["name"] == occupant.real_name))
- del(T)
+ qdel(T)
for(var/datum/data/record/G in data_core.general)
if ((G.fields["name"] == occupant.real_name))
- del(G)
+ qdel(G)
if(orient_right)
icon_state = "[base_icon_state]-r"
@@ -398,9 +398,9 @@
announce.autosay("[occupant.real_name] [on_store_message]", "[on_store_name]")
visible_message("\The [initial(name)] hums and hisses as it moves [occupant.real_name] into storage.", 3)
- set_occupant(null)
// Delete the mob.
- del(occupant)
+ qdel(occupant)
+ set_occupant(null)
/obj/machinery/cryopod/attackby(var/obj/item/weapon/G as obj, var/mob/user as mob)
diff --git a/code/game/machinery/deployable.dm b/code/game/machinery/deployable.dm
index 87e7adea035..e49fb262836 100644
--- a/code/game/machinery/deployable.dm
+++ b/code/game/machinery/deployable.dm
@@ -91,14 +91,14 @@ for reference:
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
- del(src)
+ qdel(src)
..()
ex_act(severity)
switch(severity)
if(1.0)
visible_message("\red The barricade is blown apart!")
- del(src)
+ qdel(src)
return
if(2.0)
src.health -= 25
@@ -107,7 +107,7 @@ for reference:
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
- del(src)
+ qdel(src)
return
meteorhit()
@@ -115,14 +115,14 @@ for reference:
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
new /obj/item/stack/sheet/wood(get_turf(src))
- del(src)
+ qdel(src)
return
blob_act()
src.health -= 25
if (src.health <= 0)
visible_message("\red The blob eats through the barricade!")
- del(src)
+ qdel(src)
return
CanPass(atom/movable/mover, turf/target, height=0, air_group=0)//So bullets will fly over and stuff.
@@ -264,7 +264,7 @@ for reference:
var/turf/Tsec = get_turf(src)
/* var/obj/item/stack/rods/ =*/
- new /obj/item/stack/rods(Tsec)
+ PoolOrNew(/obj/item/stack/rods, Tsec)
var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
s.set_up(3, 1, src)
@@ -272,4 +272,4 @@ for reference:
explosion(src.loc,-1,-1,0)
if(src)
- del(src)
\ No newline at end of file
+ qdel(src)
\ No newline at end of file
diff --git a/code/game/machinery/door_control.dm b/code/game/machinery/door_control.dm
index 928dda25410..e010264d4ad 100644
--- a/code/game/machinery/door_control.dm
+++ b/code/game/machinery/door_control.dm
@@ -1,27 +1,10 @@
-#define CONTROL_POD_DOORS 0
-#define CONTROL_NORMAL_DOORS 1
-#define CONTROL_EMITTERS 2
-
-/obj/machinery/door_control
- name = "remote door-control"
- desc = "It controls doors, remotely."
+/obj/machinery/button/remote
+ name = "remote object control"
+ desc = "It controls objects, remotely."
icon = 'icons/obj/stationobjs.dmi'
icon_state = "doorctrl0"
- desc = "A remote control-switch for a door."
power_channel = ENVIRON
- var/id = null
- var/normaldoorcontrol = CONTROL_POD_DOORS
- var/desiredstate = 0 // Zero is closed, 1 is open.
- var/specialfunctions = 1
- /*
- Bitflag, 1= open
- 2= idscan,
- 4= bolts
- 8= shock
- 16= door safties
-
- */
-
+ var/desiredstate = 0
var/exposedwires = 0
var/wires = 3
/*
@@ -34,14 +17,13 @@
idle_power_usage = 2
active_power_usage = 4
-
-/obj/machinery/door_control/attack_ai(mob/user as mob)
+/obj/machinery/button/remote/attack_ai(mob/user as mob)
if(wires & 2)
return src.attack_hand(user)
else
user << "Error, no route to host."
-/obj/machinery/door_control/attackby(obj/item/weapon/W, mob/user as mob)
+/obj/machinery/button/remote/attackby(obj/item/weapon/W, mob/user as mob)
/* For later implementation
if (istype(W, /obj/item/weapon/screwdriver))
{
@@ -64,7 +46,56 @@
playsound(src.loc, "sparks", 100, 1)
return src.attack_hand(user)
-/obj/machinery/door_control/proc/handle_door()
+/obj/machinery/button/remote/attack_hand(mob/user as mob)
+ if(..())
+ return
+
+ src.add_fingerprint(user)
+ if(stat & (NOPOWER|BROKEN))
+ return
+
+ if(!allowed(user) && (wires & 1))
+ user << "Access Denied"
+ flick("doorctrl-denied",src)
+ return
+
+ use_power(5)
+ icon_state = "doorctrl1"
+ desiredstate = !desiredstate
+ trigger()
+ spawn(15)
+ update_icon()
+
+/obj/machinery/button/remote/proc/trigger()
+ return
+
+/obj/machinery/button/remote/power_change()
+ ..()
+ update_icon()
+
+/obj/machinery/button/remote/update_icon()
+ if(stat & NOPOWER)
+ icon_state = "doorctrl-p"
+ else
+ icon_state = "doorctrl0"
+
+/*
+ Airlock remote control
+*/
+/obj/machinery/button/remote/airlock
+ name = "remote door-control"
+ desc = "It controls doors, remotely."
+
+ var/specialfunctions = 1
+ /*
+ Bitflag, 1= open
+ 2= idscan,
+ 4= bolts
+ 8= shock
+ 16= door safties
+ */
+
+/obj/machinery/button/remote/airlock/trigger()
for(var/obj/machinery/door/airlock/D in world)
if(D.id_tag == src.id)
if(specialfunctions & OPEN)
@@ -78,24 +109,31 @@
return
if(desiredstate == 1)
if(specialfunctions & IDSCAN)
- D.aiDisabledIdScanner = 1
+ D.set_idscan(0)
if(specialfunctions & BOLTS)
D.lock()
if(specialfunctions & SHOCK)
D.electrify(-1)
if(specialfunctions & SAFE)
- D.safe = 0
+ D.set_safeties(0)
else
if(specialfunctions & IDSCAN)
- D.aiDisabledIdScanner = 0
+ D.set_idscan(1)
if(specialfunctions & BOLTS)
D.unlock()
if(specialfunctions & SHOCK)
D.electrify(0)
if(specialfunctions & SAFE)
- D.safe = 1
+ D.set_safeties(1)
-/obj/machinery/door_control/proc/handle_pod()
+/*
+ Blast door remote control
+*/
+/obj/machinery/button/remote/blast_door
+ name = "remote blast door-control"
+ desc = "It controls blast doors, remotely."
+
+/obj/machinery/button/remote/blast_door/trigger()
for(var/obj/machinery/door/blast/M in world)
if(M.id == src.id)
if(M.density)
@@ -107,59 +145,32 @@
M.close()
return
-/obj/machinery/door_control/proc/handle_emitters(mob/user as mob)
+/*
+ Emitter remote control
+*/
+/obj/machinery/button/remote/emitter
+ name = "remote emitter control"
+ desc = "It controls emitters, remotely."
+
+/obj/machinery/button/remote/emitter/trigger(mob/user as mob)
for(var/obj/machinery/power/emitter/E in world)
if(E.id == src.id)
spawn(0)
E.activate(user)
return
-/obj/machinery/door_control/attack_hand(mob/user as mob)
- src.add_fingerprint(user)
- if(stat & (NOPOWER|BROKEN))
- return
-
- if(!allowed(user) && (wires & 1))
- user << "\red Access Denied"
- flick("doorctrl-denied",src)
- return
-
- use_power(5)
- icon_state = "doorctrl1"
- add_fingerprint(user)
-
- switch(normaldoorcontrol)
- if(CONTROL_NORMAL_DOORS)
- handle_door()
- if(CONTROL_POD_DOORS)
- handle_pod()
- if(CONTROL_EMITTERS)
- handle_emitters(user)
-
- desiredstate = !desiredstate
- spawn(15)
- if(!(stat & NOPOWER))
- icon_state = "doorctrl0"
-
-/obj/machinery/door_control/power_change()
- ..()
- if(stat & NOPOWER)
- icon_state = "doorctrl-p"
- else
- icon_state = "doorctrl0"
-
-/obj/machinery/button/driver
+/*
+ Mass driver remote control
+*/
+/obj/machinery/button/remote/driver
name = "mass driver button"
desc = "A remote control switch for a mass driver."
+ icon = 'icons/obj/objects.dmi'
+ icon_state = "launcherbtt"
-/obj/machinery/button/driver/attack_hand(mob/user as mob)
- if(..())
- return
-
- use_power(5)
-
+/obj/machinery/button/remote/driver/trigger(mob/user as mob)
active = 1
- icon_state = "launcheract"
+ update_icon()
for(var/obj/machinery/door/blast/M in machines)
if (M.id == src.id)
@@ -177,11 +188,17 @@
for(var/obj/machinery/door/blast/M in machines)
if (M.id == src.id)
- spawn( 0 )
+ spawn(0)
M.close()
return
icon_state = "launcherbtt"
- active = 0
+ update_icon()
return
+
+/obj/machinery/button/remote/driver/update_icon()
+ if(!active || (stat & NOPOWER))
+ icon_state = "launcherbtt"
+ else
+ icon_state = "launcheract"
diff --git a/code/game/machinery/doors/airlock.dm b/code/game/machinery/doors/airlock.dm
index 40c137e77b3..2211fced44e 100644
--- a/code/game/machinery/doors/airlock.dm
+++ b/code/game/machinery/doors/airlock.dm
@@ -4,7 +4,7 @@
icon_state = "door_closed"
power_channel = ENVIRON
- explosion_resistance = 15
+ explosion_resistance = 10
var/aiControlDisabled = 0 //If 1, AI control is disabled until the AI hacks back in and disables the lock. If 2, the AI has bypassed the lock. If -1, the control is enabled but the AI had bypassed it earlier, so if it is disabled again the AI would have no trouble getting back in.
var/hackProof = 0 // if 1, this door can't be hacked by the AI
var/electrified_until = 0 //World time when the door is no longer electrified. -1 if it is permanently electrified until someone fixes it.
@@ -36,10 +36,10 @@
if(damage >= 10)
if(src.density)
visible_message("\The [user] forces \the [src] open!")
- open()
+ open(1)
else
visible_message("\The [user] forces \the [src] closed!")
- close()
+ close(1)
else
visible_message("\The [user] strains fruitlessly to force \the [src] [density ? "open" : "closed"].")
return
@@ -80,6 +80,7 @@
icon = 'icons/obj/doors/Doorglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
glass = 1
@@ -91,6 +92,7 @@
/obj/machinery/door/airlock/vault
name = "Vault"
icon = 'icons/obj/doors/vault.dmi'
+ explosion_resistance = 20
opacity = 1
secured_wires = 1
assembly_type = /obj/structure/door_assembly/door_assembly_highsecurity //Until somebody makes better sprites.
@@ -108,12 +110,14 @@
/obj/machinery/door/airlock/hatch
name = "Airtight Hatch"
icon = 'icons/obj/doors/Doorhatchele.dmi'
+ explosion_resistance = 20
opacity = 1
assembly_type = /obj/structure/door_assembly/door_assembly_hatch
/obj/machinery/door/airlock/maintenance_hatch
name = "Maintenance Hatch"
icon = 'icons/obj/doors/Doorhatchmaint2.dmi'
+ explosion_resistance = 20
opacity = 1
assembly_type = /obj/structure/door_assembly/door_assembly_mhatch
@@ -122,6 +126,7 @@
icon = 'icons/obj/doors/Doorcomglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_com
glass = 1
@@ -131,6 +136,7 @@
icon = 'icons/obj/doors/Doorengglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_eng
glass = 1
@@ -140,6 +146,7 @@
icon = 'icons/obj/doors/Doorsecglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_sec
glass = 1
@@ -149,6 +156,7 @@
icon = 'icons/obj/doors/Doormedglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_med
glass = 1
@@ -173,6 +181,7 @@
icon = 'icons/obj/doors/Doorresearchglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_research
glass = 1
@@ -183,6 +192,7 @@
icon = 'icons/obj/doors/Doorminingglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_min
glass = 1
@@ -192,6 +202,7 @@
icon = 'icons/obj/doors/Dooratmoglass.dmi'
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 300
+ explosion_resistance = 5
opacity = 0
assembly_type = /obj/structure/door_assembly/door_assembly_atmo
glass = 1
@@ -261,16 +272,12 @@
for(var/turf/simulated/floor/target_tile in range(2,loc))
target_tile.assume_gas("phoron", 35, 400+T0C)
spawn (0) target_tile.hotspot_expose(temperature, 400)
- for(var/obj/structure/falsewall/phoron/F in range(3,src))//Hackish as fuck, but until temperature_expose works, there is nothing I can do -Sieve
- var/turf/T = get_turf(F)
- T.ChangeTurf(/turf/simulated/wall/mineral/phoron/)
- del (F)
- for(var/turf/simulated/wall/mineral/phoron/W in range(3,src))
+ for(var/turf/simulated/wall/W in range(3,src))
W.ignite((temperature/4))//Added so that you can't set off a massive chain reaction with a small flame
for(var/obj/machinery/door/airlock/phoron/D in range(3,src))
D.ignite(temperature/4)
new/obj/structure/door_assembly( src.loc )
- del (src)
+ qdel(src)
/obj/machinery/door/airlock/sandstone
name = "Sandstone Airlock"
@@ -292,6 +299,7 @@
/obj/machinery/door/airlock/highsecurity
name = "Secure Airlock"
icon = 'icons/obj/doors/hightechsecurity.dmi'
+ explosion_resistance = 20
secured_wires = 1
assembly_type = /obj/structure/door_assembly/door_assembly_highsecurity
@@ -421,6 +429,33 @@ About the new airlock wires panel:
if(feedback && message)
usr << message
+/obj/machinery/door/airlock/proc/set_idscan(var/activate, var/feedback = 0)
+ var/message = ""
+ if(src.isWireCut(AIRLOCK_WIRE_IDSCAN))
+ message = "The IdScan wire is cut - IdScan feature permanently disabled."
+ else if(activate && src.aiDisabledIdScanner)
+ src.aiDisabledIdScanner = 0
+ message = "IdScan feature has been enabled."
+ else if(!activate && !src.aiDisabledIdScanner)
+ src.aiDisabledIdScanner = 1
+ message = "IdScan feature has been disabled."
+
+ if(feedback && message)
+ usr << message
+
+/obj/machinery/door/airlock/proc/set_safeties(var/activate, var/feedback = 0)
+ var/message = ""
+ // Safeties! We don't need no stinking safeties!
+ if (src.isWireCut(AIRLOCK_WIRE_SAFETY))
+ message = text("The safety wire is cut - Cannot enable safeties.")
+ else if (!activate && src.safe)
+ safe = 0
+ else if (activate && !src.safe)
+ safe = 1
+
+ if(feedback && message)
+ usr << message
+
// shock user with probability prb (if all connections & power are working)
// returns 1 if shocked, 0 otherwise
// The preceding comment was borrowed from the grille's shock script
@@ -490,7 +525,8 @@ About the new airlock wires panel:
if("deny")
if(density && src.arePowerSystemsOn())
flick("door_deny", src)
- playsound(src.loc, 'sound/machines/buzz-two.ogg', 50, 0)
+ if(secured_wires)
+ playsound(src.loc, 'sound/machines/buzz-two.ogg', 50, 0)
return
/obj/machinery/door/airlock/attack_ai(mob/user as mob)
@@ -573,7 +609,7 @@ About the new airlock wires panel:
if (src.isElectrified())
if (istype(mover, /obj/item))
var/obj/item/i = mover
- if (i.matter && ("metal" in i.matter) && i.matter["metal"] > 0)
+ if (i.matter && (DEFAULT_WALL_MATERIAL in i.matter) && i.matter[DEFAULT_WALL_MATERIAL] > 0)
var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
s.set_up(5, 1, src)
s.start()
@@ -610,7 +646,7 @@ About the new airlock wires panel:
..(user)
return
-/obj/machinery/door/airlock/CanUseTopic(var/mob/user, href_list)
+/obj/machinery/door/airlock/CanUseTopic(var/mob/user)
if(!user.isSilicon())
return STATUS_CLOSE
@@ -627,7 +663,7 @@ About the new airlock wires panel:
user << "Unable to interface: Connection refused."
return STATUS_CLOSE
- return STATUS_INTERACTIVE
+ return ..()
/obj/machinery/door/airlock/Topic(href, href_list, var/nowindow = 0)
if(..())
@@ -636,14 +672,7 @@ About the new airlock wires panel:
var/activate = text2num(href_list["activate"])
switch (href_list["command"])
if("idscan")
- if(src.isWireCut(AIRLOCK_WIRE_IDSCAN))
- usr << "The IdScan wire has been cut - IdScan feature permanently disabled."
- else if(activate && src.aiDisabledIdScanner)
- src.aiDisabledIdScanner = 0
- usr << "IdScan feature has been enabled."
- else if(!activate && !src.aiDisabledIdScanner)
- src.aiDisabledIdScanner = 1
- usr << "IdScan feature has been disabled."
+ set_idscan(activate, 1)
if("main_power")
if(!main_power_lost_until)
src.loseMainPower()
@@ -652,7 +681,7 @@ About the new airlock wires panel:
src.loseBackupPower()
if("bolts")
if(src.isWireCut(AIRLOCK_WIRE_DOOR_BOLTS))
- usr << "The door bolt control wire has been cut - Door bolts permanently dropped."
+ usr << "The door bolt control wire is cut - Door bolts permanently dropped."
else if(activate && src.lock())
usr << "The door bolts have been dropped."
else if(!activate && src.unlock())
@@ -671,13 +700,7 @@ About the new airlock wires panel:
else if(!activate && !density)
close()
if("safeties")
- // Safeties! We don't need no stinking safeties!
- if (src.isWireCut(AIRLOCK_WIRE_SAFETY))
- usr << text("The safety wire is cut - Cannot secure the door.")
- else if (activate && src.safe)
- safe = 0
- else if (!activate && !src.safe)
- safe = 1
+ set_safeties(!activate, 1)
if("timing")
// Door speed control
if(src.isWireCut(AIRLOCK_WIRE_SPEED))
@@ -689,7 +712,7 @@ About the new airlock wires panel:
if("lights")
// Bolt lights
if(src.isWireCut(AIRLOCK_WIRE_LIGHT))
- usr << "The bolt lights wire has been cut - The door bolt lights are permanently disabled."
+ usr << "The bolt lights wire is cut - The door bolt lights are permanently disabled."
else if (!activate && src.lights)
lights = 0
usr << "The door bolt lights have been disabled."
@@ -770,13 +793,13 @@ About the new airlock wires panel:
electronics.loc = src.loc
electronics = null
- del(src)
+ qdel(src)
return
else if(arePowerSystemsOn())
user << "\blue The airlock's motors resist your efforts to force it."
else if(locked)
user << "\blue The airlock's bolts prevent it from being forced."
- else if( !welded && !operating )
+ else
if(density)
spawn(0) open(1)
else
@@ -825,11 +848,8 @@ About the new airlock wires panel:
return
/obj/machinery/door/airlock/open(var/forced=0)
- if(!can_open())
+ if(!can_open(forced))
return 0
- if(!forced)
- if( !arePowerSystemsOn() || isWireCut(AIRLOCK_WIRE_OPEN_DOOR) )
- return 0
use_power(360) //360 W seems much more appropriate for an actuator moving an industrial door capable of crushing people
if(istype(src, /obj/machinery/door/airlock/glass))
playsound(src.loc, 'sound/machines/windowdoor.ogg', 100, 1)
@@ -839,7 +859,11 @@ About the new airlock wires panel:
src.closeOther.close()
return ..()
-/obj/machinery/door/airlock/can_open()
+/obj/machinery/door/airlock/can_open(var/forced=0)
+ if(!forced)
+ if(!arePowerSystemsOn() || isWireCut(AIRLOCK_WIRE_OPEN_DOOR))
+ return 0
+
if(locked || welded)
return 0
return ..()
@@ -855,40 +879,68 @@ About the new airlock wires panel:
return ..()
+/atom/movable/proc/blocks_airlock()
+ return density
+
+/obj/machinery/door/blocks_airlock()
+ return 0
+
+/obj/machinery/mech_sensor/blocks_airlock()
+ return 0
+
+/mob/living/blocks_airlock()
+ return 1
+
+/atom/movable/proc/airlock_crush(var/crush_damage)
+ return 0
+
+/obj/machinery/portable_atmospherics/canister/airlock_crush(var/crush_damage)
+ . = ..()
+ health -= crush_damage
+ healthcheck()
+
+/obj/structure/closet/airlock_crush(var/crush_damage)
+ ..()
+ damage(crush_damage)
+ for(var/atom/movable/AM in src)
+ AM.airlock_crush()
+ return 1
+
+/mob/living/airlock_crush(var/crush_damage)
+ . = ..()
+ adjustBruteLoss(crush_damage)
+ SetStunned(5)
+ SetWeakened(5)
+ var/turf/T = get_turf(src)
+ T.add_blood(src)
+
+/mob/living/carbon/airlock_crush(var/crush_damage)
+ . = ..()
+ if (!(species && (species.flags & NO_PAIN)))
+ emote("scream")
+
+/mob/living/silicon/robot/airlock_crush(var/crush_damage)
+ adjustBruteLoss(crush_damage)
+ return 0
+
/obj/machinery/door/airlock/close(var/forced=0)
if(!can_close(forced))
return 0
if(safe)
for(var/turf/turf in locs)
- if(locate(/mob/living) in turf)
- if(world.time > next_beep_at)
- playsound(src.loc, 'sound/machines/buzz-two.ogg', 50, 0)
- next_beep_at = world.time + SecondsToTicks(10)
- close_door_at = world.time + 6
- return
+ for(var/atom/movable/AM in turf)
+ if(AM.blocks_airlock())
+ if(world.time > next_beep_at)
+ playsound(src.loc, 'sound/machines/buzz-two.ogg', 50, 0)
+ next_beep_at = world.time + SecondsToTicks(10)
+ close_door_at = world.time + 6
+ return
for(var/turf/turf in locs)
- for(var/mob/living/M in turf)
- if(isrobot(M))
- M.adjustBruteLoss(DOOR_CRUSH_DAMAGE)
- else
- M.adjustBruteLoss(DOOR_CRUSH_DAMAGE)
- M.SetStunned(5)
- M.SetWeakened(5)
- var/obj/effect/stop/S
- S = new /obj/effect/stop
- S.victim = M
- S.loc = M.loc
- spawn(20)
- del(S)
- if (iscarbon(M))
- var/mob/living/carbon/C = M
- if (!(C.species && (C.species.flags & NO_PAIN)))
- M.emote("scream")
- var/turf/location = src.loc
- if(istype(location, /turf/simulated))
- location.add_blood(M)
+ for(var/atom/movable/AM in turf)
+ if(AM.airlock_crush(DOOR_CRUSH_DAMAGE))
+ take_damage(DOOR_CRUSH_DAMAGE)
use_power(360) //360 W seems much more appropriate for an actuator moving an industrial door capable of crushing people
if(istype(src, /obj/machinery/door/airlock/glass))
@@ -927,6 +979,11 @@ About the new airlock wires panel:
update_icon()
return 1
+/obj/machinery/door/airlock/allowed(mob/M)
+ if(locked)
+ return 0
+ return ..(M)
+
/obj/machinery/door/airlock/New(var/newloc, var/obj/structure/door_assembly/assembly=null)
..()
@@ -958,12 +1015,18 @@ About the new airlock wires panel:
else
wires = new/datum/wires/airlock(src)
+/obj/machinery/door/airlock/initialize()
if(src.closeOtherId != null)
- spawn (5)
- for (var/obj/machinery/door/airlock/A in world)
- if(A.closeOtherId == src.closeOtherId && A != src)
- src.closeOther = A
- break
+ for (var/obj/machinery/door/airlock/A in world)
+ if(A.closeOtherId == src.closeOtherId && A != src)
+ src.closeOther = A
+ break
+
+/obj/machinery/door/airlock/Destroy()
+ if(wires)
+ qdel(wires)
+ wires = null
+ ..()
// Most doors will never be deconstructed over the course of a round,
// so as an optimization defer the creation of electronics until
diff --git a/code/game/machinery/doors/airlock_control.dm b/code/game/machinery/doors/airlock_control.dm
index ad9d9910365..053b776736e 100644
--- a/code/game/machinery/doors/airlock_control.dm
+++ b/code/game/machinery/doors/airlock_control.dm
@@ -30,7 +30,7 @@ obj/machinery/door/airlock/proc/execute_current_command()
if (!cur_command)
return
-
+
do_command(cur_command)
if (command_completed(cur_command))
cur_command = null
@@ -63,7 +63,7 @@ obj/machinery/door/airlock/proc/do_command(var/command)
lock()
sleep(2)
-
+
send_status()
obj/machinery/door/airlock/proc/command_completed(var/command)
@@ -85,7 +85,7 @@ obj/machinery/door/airlock/proc/command_completed(var/command)
if("secure_close")
return (locked && density)
-
+
return 1 //Unknown command. Just assume it's completed.
obj/machinery/door/airlock/proc/send_status(var/bumped = 0)
@@ -97,7 +97,7 @@ obj/machinery/door/airlock/proc/send_status(var/bumped = 0)
signal.data["door_status"] = density?("closed"):("open")
signal.data["lock_status"] = locked?("locked"):("unlocked")
-
+
if (bumped)
signal.data["bumped_with_access"] = 1
@@ -142,8 +142,10 @@ obj/machinery/door/airlock/New()
if(radio_controller)
set_frequency(frequency)
-
-
+obj/machinery/door/airlock/Destroy()
+ if(frequency && radio_controller)
+ radio_controller.remove_object(src,frequency)
+ ..()
obj/machinery/airlock_sensor
icon = 'icons/obj/airlock_machines.dmi'
@@ -215,6 +217,10 @@ obj/machinery/airlock_sensor/New()
if(radio_controller)
set_frequency(frequency)
+obj/machinery/airlock_sensor/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,frequency)
+ ..()
obj/machinery/airlock_sensor/airlock_interior
command = "cycle_interior"
@@ -283,6 +289,11 @@ obj/machinery/access_button/New()
if(radio_controller)
set_frequency(frequency)
+obj/machinery/access_button/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, frequency)
+ ..()
+
obj/machinery/access_button/airlock_interior
frequency = 1379
command = "cycle_interior"
diff --git a/code/game/machinery/doors/airlock_electronics.dm b/code/game/machinery/doors/airlock_electronics.dm
index 90bb72d40b0..80b36d30f9c 100644
--- a/code/game/machinery/doors/airlock_electronics.dm
+++ b/code/game/machinery/doors/airlock_electronics.dm
@@ -6,7 +6,7 @@
icon_state = "door_electronics"
w_class = 2.0 //It should be tiny! -Agouri
- matter = list("metal" = 50,"glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 50)
req_access = list(access_engine)
diff --git a/code/game/machinery/doors/alarmlock.dm b/code/game/machinery/doors/alarmlock.dm
index 67e5c83dc30..8b6ddb58344 100644
--- a/code/game/machinery/doors/alarmlock.dm
+++ b/code/game/machinery/doors/alarmlock.dm
@@ -13,6 +13,11 @@
..()
air_connection = new
+/obj/machinery/door/airlock/alarmlock/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,air_frequency)
+ ..()
+
/obj/machinery/door/airlock/alarmlock/initialize()
..()
radio_controller.remove_object(src, air_frequency)
@@ -29,8 +34,6 @@
var/alert = signal.data["alert"]
var/area/our_area = get_area(src)
- if (our_area.master)
- our_area = our_area.master
if(alarm_area == our_area.name)
switch(alert)
@@ -39,4 +42,4 @@
close()
if("minor", "clear")
autoclose = 0
- open()
\ No newline at end of file
+ open()
diff --git a/code/game/machinery/doors/blast_door.dm b/code/game/machinery/doors/blast_door.dm
index 19ac77d2c77..374f0426ada 100644
--- a/code/game/machinery/doors/blast_door.dm
+++ b/code/game/machinery/doors/blast_door.dm
@@ -23,8 +23,8 @@
var/id = 1.0
dir = 1
explosion_resistance = 25
-
- //Most blast doors are infrequently toggled and sometimes used with regular doors anyways,
+
+ //Most blast doors are infrequently toggled and sometimes used with regular doors anyways,
//turning this off prevents awkward zone geometry in places like medbay lobby, for example.
block_air_zones = 0
@@ -56,7 +56,7 @@
src.density = 0
update_nearby_tiles()
src.update_icon()
- src.SetOpacity(0)
+ src.set_opacity(0)
sleep(15)
src.layer = open_layer
src.operating = 0
@@ -71,7 +71,7 @@
src.density = 1
update_nearby_tiles()
src.update_icon()
- src.SetOpacity(initial(opacity))
+ src.set_opacity(initial(opacity))
sleep(15)
src.operating = 0
diff --git a/code/game/machinery/doors/brigdoors.dm b/code/game/machinery/doors/brigdoors.dm
index b3dc9bf978b..27ce595a779 100644
--- a/code/game/machinery/doors/brigdoors.dm
+++ b/code/game/machinery/doors/brigdoors.dm
@@ -35,11 +35,11 @@
..()
spawn(20)
- for(var/obj/machinery/door/window/brigdoor/M in world)
+ for(var/obj/machinery/door/window/brigdoor/M in machines)
if (M.id == src.id)
targets += M
- for(var/obj/machinery/flasher/F in world)
+ for(var/obj/machinery/flasher/F in machines)
if(F.id == src.id)
targets += F
@@ -345,4 +345,4 @@
#undef FONT_SIZE
#undef FONT_COLOR
#undef FONT_STYLE
-#undef CHARS_PER_LINE
\ No newline at end of file
+#undef CHARS_PER_LINE
diff --git a/code/game/machinery/doors/door.dm b/code/game/machinery/doors/door.dm
index f7058921da0..0f3760009d6 100644
--- a/code/game/machinery/doors/door.dm
+++ b/code/game/machinery/doors/door.dm
@@ -1,7 +1,4 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31
-#define DOOR_OPEN_LAYER 2.7 //Under all objects if opened. 2.7 due to tables being at 2.6
-#define DOOR_CLOSED_LAYER 3.1 //Above most items if closed
-
#define DOOR_REPAIR_AMOUNT 50 //amount of health regained per stack amount used
/obj/machinery/door
@@ -37,6 +34,9 @@
dir = EAST
var/width = 1
+ // turf animation
+ var/atom/movable/overlay/c_animation = null
+
/obj/machinery/door/attack_generic(var/mob/user, var/damage)
if(damage >= 10)
visible_message("\The [user] smashes into the [src]!")
@@ -68,8 +68,7 @@
update_nearby_tiles(need_rebuild=1)
return
-
-/obj/machinery/door/Del()
+/obj/machinery/door/Destroy()
density = 0
update_nearby_tiles()
..()
@@ -103,8 +102,8 @@
bumpopen(M)
return
- if(istype(AM, /obj/machinery/bot))
- var/obj/machinery/bot/bot = AM
+ if(istype(AM, /mob/living/bot))
+ var/mob/living/bot/bot = AM
if(src.check_access(bot.botcard))
if(density)
open()
@@ -165,10 +164,10 @@
switch (Proj.damage_type)
if(BRUTE)
new /obj/item/stack/sheet/metal(src.loc, 2)
- new /obj/item/stack/rods(src.loc, 3)
+ PoolOrNew(/obj/item/stack/rods, list(src.loc, 3))
if(BURN)
new /obj/effect/decal/cleanable/ash(src.loc) // Turn it to ashes!
- del(src)
+ qdel(src)
if(Proj.damage)
//cap projectile damage so that there's still a minimum number of hits required to break the door
@@ -251,7 +250,7 @@
user << "You finish repairing the damage to \the [src]."
health = between(health, health + repairing.amount*DOOR_REPAIR_AMOUNT, maxhealth)
update_icon()
- del(repairing)
+ qdel(repairing)
return
if(repairing && istype(I, /obj/item/weapon/crowbar))
@@ -307,6 +306,17 @@
update_icon()
return
+
+/obj/machinery/door/examine(mob/user)
+ . = ..()
+ if(src.health < src.maxhealth / 4)
+ user << "\The [src] looks like it's about to break!"
+ else if(src.health < src.maxhealth / 2)
+ user << "\The [src] looks seriously damaged!"
+ else if(src.health < src.maxhealth * 3/4)
+ user << "\The [src] shows signs of damage!"
+
+
/obj/machinery/door/proc/set_broken()
stat |= BROKEN
for (var/mob/O in viewers(src, null))
@@ -318,7 +328,7 @@
/obj/machinery/door/blob_act()
if(prob(40))
- del(src)
+ qdel(src)
return
@@ -331,10 +341,10 @@
/obj/machinery/door/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
if(2.0)
if(prob(25))
- del(src)
+ qdel(src)
else
take_damage(300)
if(3.0)
@@ -377,23 +387,23 @@
return
-/obj/machinery/door/proc/open()
- if(!can_open()) return
- if(!operating) operating = 1
+/obj/machinery/door/proc/open(var/forced = 0)
+ if(!can_open(forced))
+ return
+ operating = 1
do_animate("opening")
icon_state = "door0"
- src.SetOpacity(0)
+ set_opacity(0)
sleep(3)
src.density = 0
sleep(7)
src.layer = open_layer
explosion_resistance = 0
update_icon()
- SetOpacity(0)
+ set_opacity(0)
update_nearby_tiles()
-
- if(operating) operating = 0
+ operating = 0
if(autoclose)
close_door_at = next_close_time()
@@ -403,8 +413,8 @@
/obj/machinery/door/proc/next_close_time()
return world.time + (normalspeed ? 150 : 5)
-/obj/machinery/door/proc/close()
- if(!can_close())
+/obj/machinery/door/proc/close(var/forced = 0)
+ if(!can_close(forced))
return
operating = 1
@@ -417,14 +427,14 @@
sleep(7)
update_icon()
if(visible && !glass)
- SetOpacity(1) //caaaaarn!
+ set_opacity(1) //caaaaarn!
operating = 0
update_nearby_tiles()
//I shall not add a check every x ticks if a door has closed over some fire.
var/obj/fire/fire = locate() in loc
if(fire)
- del fire
+ qdel(fire)
return
/obj/machinery/door/proc/requiresID()
diff --git a/code/game/machinery/doors/firedoor.dm b/code/game/machinery/doors/firedoor.dm
index 9ae8751a7af..a3fca76a444 100644
--- a/code/game/machinery/doors/firedoor.dm
+++ b/code/game/machinery/doors/firedoor.dm
@@ -56,7 +56,7 @@
for(var/obj/machinery/door/firedoor/F in loc)
if(F != src)
spawn(1)
- del src
+ qdel(src)
return .
var/area/A = get_area(src)
ASSERT(istype(A))
@@ -70,14 +70,15 @@
A.all_doors.Add(src)
areas_added += A
-/obj/machinery/door/firedoor/Del()
+/obj/machinery/door/firedoor/Destroy()
for(var/area/A in areas_added)
A.all_doors.Remove(src)
. = ..()
/obj/machinery/door/firedoor/examine(mob/user)
- if(!..(user, 1) && !isAI(user))
+ . = ..(user, 1)
+ if(!. || !density)
return
if(pdiff >= FIREDOOR_MAX_PRESSURE_DIFF)
@@ -230,7 +231,7 @@
FA.density = 1
FA.wired = 1
FA.update_icon()
- del(src)
+ qdel(src)
return
if(blocked)
diff --git a/code/game/machinery/doors/firedoor_assembly.dm b/code/game/machinery/doors/firedoor_assembly.dm
index 435a9278577..d3a70fe85e7 100644
--- a/code/game/machinery/doors/firedoor_assembly.dm
+++ b/code/game/machinery/doors/firedoor_assembly.dm
@@ -42,8 +42,8 @@ obj/structure/firedoor_assembly/attackby(C as obj, mob/user as mob)
user.visible_message("[user] has inserted a circuit into \the [src]!",
"You have inserted the circuit into \the [src]!")
new /obj/machinery/door/firedoor(src.loc)
- del(C)
- del(src)
+ qdel(C)
+ qdel(src)
else
user << "You must secure \the [src] first!"
else if(istype(C, /obj/item/weapon/wrench))
@@ -62,7 +62,7 @@ obj/structure/firedoor_assembly/attackby(C as obj, mob/user as mob)
user.visible_message("[user] has dissassembled \the [src].",
"You have dissassembled \the [src].")
new /obj/item/stack/sheet/metal(src.loc, 2)
- del (src)
+ qdel(src)
else
user << "You need more welding fuel."
else
diff --git a/code/game/machinery/doors/windowdoor.dm b/code/game/machinery/doors/windowdoor.dm
index 362753cac8f..d693f848eb3 100644
--- a/code/game/machinery/doors/windowdoor.dm
+++ b/code/game/machinery/doors/windowdoor.dm
@@ -7,7 +7,7 @@
min_force = 4
hitsound = 'sound/effects/Glasshit.ogg'
maxhealth = 150 //If you change this, consiter changing ../door/window/brigdoor/ health at the bottom of this .dm file
- health
+ health = 150
visible = 0.0
use_power = 0
flags = ON_BORDER
@@ -49,16 +49,16 @@
playsound(src, "shatter", 70, 1)
if(display_message)
visible_message("[src] shatters!")
- del(src)
+ qdel(src)
-/obj/machinery/door/window/Del()
+/obj/machinery/door/window/Destroy()
density = 0
update_nearby_tiles()
..()
/obj/machinery/door/window/Bumped(atom/movable/AM as mob|obj)
if (!( ismob(AM) ))
- var/obj/machinery/bot/bot = AM
+ var/mob/living/bot/bot = AM
if(istype(bot))
if(density && src.check_access(bot.botcard))
open()
@@ -249,13 +249,14 @@
/obj/machinery/door/window/brigdoor
- name = "Secure Door"
+ name = "secure door"
icon = 'icons/obj/doors/windoor.dmi'
icon_state = "leftsecure"
base_state = "leftsecure"
req_access = list(access_security)
var/id = null
- health = 300.0 //Stronger doors for prison (regular window door health is 200)
+ maxhealth = 300
+ health = 300.0 //Stronger doors for prison (regular window door health is 150)
/obj/machinery/door/window/northleft
diff --git a/code/game/machinery/doppler_array.dm b/code/game/machinery/doppler_array.dm
index dbe7f1b8a70..ec9f4e7accc 100644
--- a/code/game/machinery/doppler_array.dm
+++ b/code/game/machinery/doppler_array.dm
@@ -9,7 +9,7 @@ var/list/doppler_arrays = list()
..()
doppler_arrays += src
-/obj/machinery/doppler_array/Del()
+/obj/machinery/doppler_array/Destroy()
doppler_arrays -= src
..()
diff --git a/code/game/machinery/embedded_controller/docking_program.dm b/code/game/machinery/embedded_controller/docking_program.dm
index 032676f0370..987634d02ab 100644
--- a/code/game/machinery/embedded_controller/docking_program.dm
+++ b/code/game/machinery/embedded_controller/docking_program.dm
@@ -71,6 +71,15 @@
var/override_enabled = 0 //when enabled, do not open/close doors or cycle airlocks and wait for the player to do it manually
var/received_confirm = 0 //for undocking, whether the server has recieved a confirmation from the client
+/datum/computer/file/embedded_program/docking/New()
+ ..()
+ var/datum/existing = locate(id_tag) //in case a datum already exists with our tag
+ if(existing)
+ existing.tag = null //take it from them
+
+ tag = id_tag //Greatly simplifies shuttle initialization
+
+
/datum/computer/file/embedded_program/docking/receive_signal(datum/signal/signal, receive_method, receive_param)
var/receive_tag = signal.data["tag"] //for docking signals, this is the sender id
var/command = signal.data["command"]
diff --git a/code/game/machinery/embedded_controller/embedded_controller_base.dm b/code/game/machinery/embedded_controller/embedded_controller_base.dm
index 8661651a396..a128e6c4e48 100644
--- a/code/game/machinery/embedded_controller/embedded_controller_base.dm
+++ b/code/game/machinery/embedded_controller/embedded_controller_base.dm
@@ -9,6 +9,11 @@
var/on = 1
+obj/machinery/embedded_controller/radio/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,frequency)
+ ..()
+
/obj/machinery/embedded_controller/proc/post_signal(datum/signal/signal, comm_line)
return 0
@@ -70,7 +75,7 @@
//use_power(radio_power_use) //neat idea, but causes way too much lag.
return radio_connection.post_signal(src, signal, filter)
else
- del(signal)
+ qdel(signal)
/obj/machinery/embedded_controller/radio/proc/set_frequency(new_frequency)
radio_controller.remove_object(src, frequency)
diff --git a/code/game/machinery/embedded_controller/embedded_program_base.dm b/code/game/machinery/embedded_controller/embedded_program_base.dm
index 611fcfc52e5..f579aca6f7a 100644
--- a/code/game/machinery/embedded_controller/embedded_program_base.dm
+++ b/code/game/machinery/embedded_controller/embedded_program_base.dm
@@ -1,27 +1,27 @@
-
-/datum/computer/file/embedded_program
- var/list/memory = list()
- var/obj/machinery/embedded_controller/master
-
- var/id_tag
-
-/datum/computer/file/embedded_program/New(var/obj/machinery/embedded_controller/M)
- master = M
- if (istype(M, /obj/machinery/embedded_controller/radio))
- var/obj/machinery/embedded_controller/radio/R = M
- id_tag = R.id_tag
-
-/datum/computer/file/embedded_program/proc/receive_user_command(command)
- return
-
-/datum/computer/file/embedded_program/proc/receive_signal(datum/signal/signal, receive_method, receive_param)
- return
-
-/datum/computer/file/embedded_program/proc/process()
- return
-
-/datum/computer/file/embedded_program/proc/post_signal(datum/signal/signal, comm_line)
- if(master)
- master.post_signal(signal, comm_line)
- else
- del(signal)
+
+/datum/computer/file/embedded_program
+ var/list/memory = list()
+ var/obj/machinery/embedded_controller/master
+
+ var/id_tag
+
+/datum/computer/file/embedded_program/New(var/obj/machinery/embedded_controller/M)
+ master = M
+ if (istype(M, /obj/machinery/embedded_controller/radio))
+ var/obj/machinery/embedded_controller/radio/R = M
+ id_tag = R.id_tag
+
+/datum/computer/file/embedded_program/proc/receive_user_command(command)
+ return
+
+/datum/computer/file/embedded_program/proc/receive_signal(datum/signal/signal, receive_method, receive_param)
+ return
+
+/datum/computer/file/embedded_program/proc/process()
+ return
+
+/datum/computer/file/embedded_program/proc/post_signal(datum/signal/signal, comm_line)
+ if(master)
+ master.post_signal(signal, comm_line)
+ else
+ qdel(signal)
diff --git a/code/game/machinery/floodlight.dm b/code/game/machinery/floodlight.dm
index d71b060bb07..b7272dc8294 100644
--- a/code/game/machinery/floodlight.dm
+++ b/code/game/machinery/floodlight.dm
@@ -26,7 +26,7 @@
else
on = 0
updateicon()
- SetLuminosity(0)
+ set_light(0)
src.visible_message("[src] shuts down due to lack of power!")
return
@@ -50,7 +50,7 @@
if(on)
on = 0
user << "\blue You turn off the light"
- SetLuminosity(0)
+ set_light(0)
else
if(!cell)
return
@@ -58,7 +58,7 @@
return
on = 1
user << "\blue You turn on the light"
- SetLuminosity(brightness_on)
+ set_light(brightness_on)
updateicon()
diff --git a/code/game/machinery/floorlayer.dm b/code/game/machinery/floorlayer.dm
new file mode 100644
index 00000000000..009d1c7694e
--- /dev/null
+++ b/code/game/machinery/floorlayer.dm
@@ -0,0 +1,114 @@
+/obj/machinery/floorlayer
+
+ name = "automatic floor layer"
+ icon = 'icons/obj/stationobjs.dmi'
+ icon_state = "pipe_d"
+ density = 1
+ var/turf/old_turf
+ var/on = 0
+ var/obj/item/stack/tile/T
+ var/list/mode = list("dismantle"=0,"laying"=0,"collect"=0)
+
+/obj/machinery/floorlayer/New()
+ T = new/obj/item/stack/tile/plasteel(src)
+ ..()
+
+/obj/machinery/floorlayer/Move(new_turf,M_Dir)
+ ..()
+
+ if(on)
+ if(mode["dismantle"])
+ dismantleFloor(old_turf)
+
+ if(mode["laying"])
+ layFloor(old_turf)
+
+ if(mode["collect"])
+ CollectTiles(old_turf)
+
+
+ old_turf = new_turf
+
+/obj/machinery/floorlayer/attack_hand(mob/user as mob)
+ on=!on
+ user.visible_message("[user] has [!on?"de":""]activated \the [src].", "You [!on?"de":""]activate \the [src].")
+ return
+
+/obj/machinery/floorlayer/attackby(var/obj/item/W as obj, var/mob/user as mob)
+
+ if (istype(W, /obj/item/weapon/wrench))
+ var/m = input("Choose work mode", "Mode") as null|anything in mode
+ mode[m] = !mode[m]
+ var/O = mode[m]
+ user.visible_message("[usr] has set \the [src] [m] mode [!O?"off":"on"].", "You set \the [src] [m] mode [!O?"off":"on"].")
+ return
+
+ if(istype(W, /obj/item/stack/tile))
+ user << "\The [W] successfully loaded."
+ user.drop_item(T)
+ TakeTile(T)
+ return
+
+ if(istype(W, /obj/item/weapon/crowbar))
+ if(!length(contents))
+ user << "\The [src] is empty."
+ else
+ var/obj/item/stack/tile/E = input("Choose remove tile type.", "Tiles") as null|anything in contents
+ if(E)
+ user << "You remove the [E] from /the [src]."
+ E.loc = src.loc
+ T = null
+ return
+
+ if(istype(W, /obj/item/weapon/screwdriver))
+ T = input("Choose tile type.", "Tiles") as null|anything in contents
+ return
+ ..()
+
+/obj/machinery/floorlayer/examine(mob/user)
+ ..()
+ var/dismantle = mode["dismantle"]
+ var/laying = mode["laying"]
+ var/collect = mode["collect"]
+ user << "\The [src] [!T?"don't ":""]has [!T?"":"[T.get_amount()] [T] "]tile\s, dismantle is [dismantle?"on":"off"], laying is [laying?"on":"off"], collect is [collect?"on":"off"]."
+
+/obj/machinery/floorlayer/proc/reset()
+ on=0
+ return
+
+/obj/machinery/floorlayer/proc/dismantleFloor(var/turf/new_turf)
+ if(istype(new_turf, /turf/simulated/floor))
+ var/turf/simulated/floor/T = new_turf
+ if(!T.is_plating())
+ if(!T.broken && !T.burnt)
+ new T.floor_type(T)
+ T.make_plating()
+ return !new_turf.intact
+
+/obj/machinery/floorlayer/proc/TakeNewStack()
+ for(var/obj/item/stack/tile/tile in contents)
+ T = tile
+ return 1
+ return 0
+
+/obj/machinery/floorlayer/proc/SortStacks()
+ for(var/obj/item/stack/tile/tile1 in contents)
+ for(var/obj/item/stack/tile/tile2 in contents)
+ tile2.transfer_to(tile1)
+
+/obj/machinery/floorlayer/proc/layFloor(var/turf/w_turf)
+ if(!T)
+ if(!TakeNewStack())
+ return 0
+ w_turf.attackby(T , src)
+ return 1
+
+/obj/machinery/floorlayer/proc/TakeTile(var/obj/item/stack/tile/tile)
+ if(!T) T = tile
+ tile.loc = src
+
+ SortStacks()
+
+/obj/machinery/floorlayer/proc/CollectTiles(var/turf/w_turf)
+ for(var/obj/item/stack/tile/tile in w_turf)
+ TakeTile(tile)
diff --git a/code/game/machinery/hologram.dm b/code/game/machinery/hologram.dm
index a286b530ca1..28bb2be7bcc 100644
--- a/code/game/machinery/hologram.dm
+++ b/code/game/machinery/hologram.dm
@@ -37,7 +37,7 @@ var/const/HOLOPAD_MODE = RANGE_BASED
icon_state = "holopad0"
layer = TURF_LAYER+0.1 //Preventing mice and drones from sneaking under them.
-
+
var/power_per_hologram = 500 //per usage per hologram
idle_power_usage = 5
use_power = 1
@@ -120,10 +120,10 @@ For the other part of the code, check silicon say.dm. Particularly robot talk.*/
hologram.layer = FLY_LAYER//Above all the other objects/mobs. Or the vast majority of them.
hologram.anchored = 1//So space wind cannot drag it.
hologram.name = "[A.name] (Hologram)"//If someone decides to right click.
- hologram.SetLuminosity(2) //hologram lighting
+ hologram.set_light(2) //hologram lighting
hologram.color = color //painted holopad gives coloured holograms
masters[A] = hologram
- SetLuminosity(2) //pad lighting
+ set_light(2) //pad lighting
icon_state = "holopad1"
A.holo = src
return 1
@@ -131,10 +131,10 @@ For the other part of the code, check silicon say.dm. Particularly robot talk.*/
/obj/machinery/hologram/holopad/proc/clear_holo(mob/living/silicon/ai/user)
if(user.holo == src)
user.holo = null
- del(masters[user])//Get rid of user's hologram //qdel
+ qdel(masters[user])//Get rid of user's hologram
masters -= user //Discard AI from the list of those who use holopad
if (!masters.len)//If no users left
- SetLuminosity(0) //pad lighting (hologram lighting will be handled automatically since its owner was deleted)
+ set_light(0) //pad lighting (hologram lighting will be handled automatically since its owner was deleted)
icon_state = "holopad0"
return 1
@@ -144,16 +144,15 @@ For the other part of the code, check silicon say.dm. Particularly robot talk.*/
if((stat & NOPOWER) || !active_ai)
clear_holo(master)
continue
-
+
if((HOLOPAD_MODE == RANGE_BASED && (get_dist(master.eyeobj, src) > holo_range)))
clear_holo(master)
continue
-
+
if(HOLOPAD_MODE == AREA_BASED)
var/area/holo_area = get_area(src)
var/area/eye_area = get_area(master.eyeobj)
-
- if(!(eye_area in holo_area.master.related))
+ if(eye_area != holo_area)
clear_holo(master)
continue
@@ -182,24 +181,24 @@ For the other part of the code, check silicon say.dm. Particularly robot talk.*/
/obj/machinery/hologram/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
/obj/machinery/hologram/blob_act()
- del(src)
+ qdel(src)
return
/obj/machinery/hologram/meteorhit()
- del(src)
+ qdel(src)
return
-/obj/machinery/hologram/holopad/Del()
+/obj/machinery/hologram/holopad/Destroy()
for (var/mob/living/silicon/ai/master in masters)
clear_holo(master)
..()
diff --git a/code/game/machinery/iv_drip.dm b/code/game/machinery/iv_drip.dm
index 63ad92f017d..99a2dc6607a 100644
--- a/code/game/machinery/iv_drip.dm
+++ b/code/game/machinery/iv_drip.dm
@@ -32,7 +32,7 @@
if(80 to 90) filling.icon_state = "reagent80"
if(91 to INFINITY) filling.icon_state = "reagent100"
- filling.icon += mix_color_from_reagents(reagents.reagent_list)
+ filling.icon += reagents.get_color()
overlays += filling
/obj/machinery/iv_drip/MouseDrop(over_object, src_location, over_location)
@@ -82,11 +82,11 @@
// Give blood
if(mode)
if(src.beaker.volume > 0)
- var/transfer_amount = REAGENTS_METABOLISM
+ var/transfer_amount = REM
if(istype(src.beaker, /obj/item/weapon/reagent_containers/blood))
// speed up transfer on blood packs
transfer_amount = 4
- src.beaker.reagents.trans_to(src.attached, transfer_amount)
+ src.beaker.reagents.trans_to_mob(src.attached, transfer_amount, CHEM_BLOOD)
update_icon()
// Take blood
diff --git a/code/game/machinery/jukebox.dm b/code/game/machinery/jukebox.dm
index 972f51bd485..90305a7a786 100644
--- a/code/game/machinery/jukebox.dm
+++ b/code/game/machinery/jukebox.dm
@@ -36,7 +36,7 @@ datum/track/New(var/title_name, var/audio)
)
-/obj/machinery/media/jukebox/Del()
+/obj/machinery/media/jukebox/Destroy()
StopPlaying()
..()
@@ -160,7 +160,7 @@ datum/track/New(var/title_name, var/audio)
s.start()
new /obj/effect/decal/cleanable/blood/oil(src.loc)
- del(src)
+ qdel(src)
/obj/machinery/media/jukebox/attackby(obj/item/W as obj, mob/user as mob)
src.add_fingerprint(user)
@@ -188,11 +188,10 @@ datum/track/New(var/title_name, var/audio)
/obj/machinery/media/jukebox/proc/StopPlaying()
var/area/main_area = get_area(src)
// Always kill the current sound
- for(var/area/related_area in main_area.related)
- for(var/mob/living/M in mobs_in_area(related_area))
- M << sound(null, channel = 1)
+ for(var/mob/living/M in mobs_in_area(main_area))
+ M << sound(null, channel = 1)
- related_area.forced_ambience = null
+ main_area.forced_ambience = null
playing = 0
update_use_power(1)
update_icon()
@@ -204,12 +203,10 @@ datum/track/New(var/title_name, var/audio)
return
var/area/main_area = get_area(src)
- for(var/area/related_area in main_area.related)
- related_area.forced_ambience = sound(current_track.sound, channel = 1, repeat = 1, volume = 25)
-
- for(var/mob/living/M in mobs_in_area(related_area))
- if(M.mind)
- related_area.play_ambience(related_area)
+ main_area.forced_ambience = list(current_track.sound)
+ for(var/mob/living/M in mobs_in_area(main_area))
+ if(M.mind)
+ main_area.play_ambience(M)
playing = 1
update_use_power(2)
diff --git a/code/game/machinery/kitchen/gibber.dm b/code/game/machinery/kitchen/gibber.dm
index 1283e7e52c3..8ee374e9610 100644
--- a/code/game/machinery/kitchen/gibber.dm
+++ b/code/game/machinery/kitchen/gibber.dm
@@ -31,7 +31,7 @@
if(isturf(input_obj.loc))
input_plate = input_obj.loc
gib_throw_dir = i
- del(input_obj)
+ qdel(input_obj)
break
if(!input_plate)
@@ -209,7 +209,7 @@
new_meat.reagents.add_reagent("nutriment",slab_nutrition)
if(src.occupant.reagents)
- src.occupant.reagents.trans_to(new_meat, round(occupant.reagents.total_volume/slab_count,1))
+ src.occupant.reagents.trans_to_obj(new_meat, round(occupant.reagents.total_volume/slab_count,1))
src.occupant.attack_log += "\[[time_stamp()]\] Was gibbed by [user]/[user.ckey]" //One shall not simply gib a mob unnoticed!
user.attack_log += "\[[time_stamp()]\] Gibbed [src.occupant]/[src.occupant.ckey]"
@@ -221,7 +221,7 @@
src.operating = 0
src.occupant.gib()
- del(src.occupant)
+ qdel(src.occupant)
playsound(src.loc, 'sound/effects/splat.ogg', 50, 1)
operating = 0
@@ -229,7 +229,7 @@
// Todo: unify limbs and internal organs
// There's a chance that the gibber will fail to destroy some evidence.
if((istype(thing,/obj/item/organ) || istype(thing,/obj/item/organ)) && prob(80))
- del(thing)
+ qdel(thing)
continue
thing.loc = get_turf(thing) // Drop it onto the turf for throwing.
thing.throw_at(get_edge_target_turf(src,gib_throw_dir),rand(0,3),emagged ? 100 : 50) // Being pelted with bits of meat and bone would hurt.
diff --git a/code/game/machinery/kitchen/microwave.dm b/code/game/machinery/kitchen/microwave.dm
index fbdcfd2760c..23efb8ab4c5 100644
--- a/code/game/machinery/kitchen/microwave.dm
+++ b/code/game/machinery/kitchen/microwave.dm
@@ -111,6 +111,7 @@
user.visible_message( \
"\blue [user] has added one of [O] to \the [src].", \
"\blue You add one of [O] to \the [src].")
+ return
else
// user.remove_from_mob(O) //This just causes problems so far as I can tell. -Pete
user.drop_item()
@@ -118,6 +119,7 @@
user.visible_message( \
"\blue [user] has added \the [O] to \the [src].", \
"\blue You add \the [O] to \the [src].")
+ return
else if(istype(O,/obj/item/weapon/reagent_containers/glass) || \
istype(O,/obj/item/weapon/reagent_containers/food/drinks) || \
istype(O,/obj/item/weapon/reagent_containers/food/condiment) \
@@ -135,11 +137,12 @@
return 1
else
user << "\red You have no idea what you can cook with this [O]."
- return 1
+ ..()
src.updateUsrDialog()
/obj/machinery/microwave/attack_ai(mob/user as mob)
- return 0
+ if(istype(user, /mob/living/silicon/robot) && Adjacent(user))
+ attack_hand(user)
/obj/machinery/microwave/attack_hand(mob/user as mob)
user.set_machine(src)
@@ -350,7 +353,7 @@
var/id = O.reagents.get_master_reagent_id()
if (id)
amount+=O.reagents.get_reagent_amount(id)
- del(O)
+ qdel(O)
src.reagents.clear_reagents()
ffuu.reagents.add_reagent("carbon", amount)
ffuu.reagents.add_reagent("toxin", amount/10)
diff --git a/code/game/machinery/kitchen/smartfridge.dm b/code/game/machinery/kitchen/smartfridge.dm
index 1b1bb9bfb5f..9bfa0e1c5dd 100644
--- a/code/game/machinery/kitchen/smartfridge.dm
+++ b/code/game/machinery/kitchen/smartfridge.dm
@@ -33,8 +33,8 @@
else
wires = new/datum/wires/smartfridge(src)
-/obj/machinery/smartfridge/Del()
- del(wires) // qdel
+/obj/machinery/smartfridge/Destroy()
+ qdel(wires)
..()
/obj/machinery/smartfridge/proc/accept_check(var/obj/item/O as obj)
@@ -140,12 +140,13 @@
S.dry = 1
item_quants[S.name]--
S.name = "dried [S.name]"
+ S.color = "#AAAAAA"
S.loc = loc
else
var/D = S.dried_type
new D(loc)
item_quants[S.name]--
- del(S)
+ qdel(S)
return
return
@@ -244,7 +245,7 @@
..()
/obj/machinery/smartfridge/attack_ai(mob/user as mob)
- return 0
+ attack_hand(user)
/obj/machinery/smartfridge/attack_hand(mob/user as mob)
if(stat & (NOPOWER|BROKEN))
diff --git a/code/game/machinery/lightswitch.dm b/code/game/machinery/lightswitch.dm
index dcf66a12b7b..ded7ebc9b98 100644
--- a/code/game/machinery/lightswitch.dm
+++ b/code/game/machinery/lightswitch.dm
@@ -42,15 +42,14 @@
on = !on
- for(var/area/A in area.master.related)
- A.lightswitch = on
- A.updateicon()
+ area.lightswitch = on
+ area.updateicon()
- for(var/obj/machinery/light_switch/L in A)
- L.on = on
- L.updateicon()
+ for(var/obj/machinery/light_switch/L in area)
+ L.on = on
+ L.updateicon()
- area.master.power_change()
+ area.power_change()
/obj/machinery/light_switch/power_change()
diff --git a/code/game/machinery/machinery.dm b/code/game/machinery/machinery.dm
index c0766b18240..4e158156bfa 100644
--- a/code/game/machinery/machinery.dm
+++ b/code/game/machinery/machinery.dm
@@ -49,7 +49,7 @@ Class Variables:
Class Procs:
New() 'game/machinery/machine.dm'
- Del() 'game/machinery/machine.dm'
+ Destroy() 'game/machinery/machine.dm'
auto_use_power() 'game/machinery/machine.dm'
This proc determines how power mode power is deducted by the machine.
@@ -121,7 +121,7 @@ Class Procs:
machines += src
machinery_sort_required = 1
-/obj/machinery/Del()
+/obj/machinery/Destroy()
machines -= src
..()
@@ -135,7 +135,7 @@ Class Procs:
if(use_power && stat == 0)
use_power(7500/severity)
- var/obj/effect/overlay/pulse2 = new/obj/effect/overlay ( src.loc )
+ var/obj/effect/overlay/pulse2 = PoolOrNew(/obj/effect/overlay, src.loc)
pulse2.icon = 'icons/effects/effects.dmi'
pulse2.icon_state = "empdisable"
pulse2.name = "emp sparks"
@@ -143,28 +143,28 @@ Class Procs:
pulse2.set_dir(pick(cardinal))
spawn(10)
- pulse2.delete()
+ qdel(pulse2)
..()
/obj/machinery/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(25))
- del(src)
+ qdel(src)
return
else
return
/obj/machinery/blob_act()
if(prob(50))
- del(src)
+ qdel(src)
//sets the use_power var and then forces an area power update
/obj/machinery/proc/update_use_power(var/new_use_power, var/force_update = 0)
@@ -185,7 +185,7 @@ Class Procs:
/obj/machinery/proc/inoperable(var/additional_flags = 0)
return (stat & (NOPOWER|BROKEN|additional_flags))
-/obj/machinery/CanUseTopic(var/mob/user, var/be_close)
+/obj/machinery/CanUseTopic(var/mob/user)
if(!interact_offline && (stat & (NOPOWER|BROKEN)))
return STATUS_CLOSE
@@ -264,8 +264,8 @@ Class Procs:
s.start()
if (electrocute_mob(user, get_area(src), src, 0.7))
var/area/temp_area = get_area(src)
- if(temp_area && temp_area.master)
- var/obj/machinery/power/apc/temp_apc = temp_area.master.get_apc()
+ if(temp_area)
+ var/obj/machinery/power/apc/temp_apc = temp_area.get_apc()
if(temp_apc && temp_apc.terminal && temp_apc.terminal.powernet)
temp_apc.terminal.powernet.trigger_warning()
@@ -329,53 +329,5 @@ Class Procs:
M.icon_state = "box_1"
for(var/obj/I in component_parts)
I.loc = loc
- del(src)
+ qdel(src)
return 1
-
-/obj/machinery/proc/on_assess_perp(mob/living/carbon/human/perp)
- return 0
-
-/obj/machinery/proc/is_assess_emagged()
- return emagged
-
-/obj/machinery/proc/assess_perp(mob/living/carbon/human/perp, var/auth_weapons, var/check_records, var/check_arrest)
- var/threatcount = 0 //the integer returned
-
- if(is_assess_emagged())
- return 10 //if emagged, always return 10.
-
- threatcount += on_assess_perp(perp)
- if(threatcount >= 10)
- return threatcount
-
- //Agent cards lower threatlevel.
- var/obj/item/weapon/card/id/id = GetIdCard(perp)
- if(id && istype(id, /obj/item/weapon/card/id/syndicate))
- threatcount -= 2
-
- if(auth_weapons && !src.allowed(perp))
- if(istype(perp.l_hand, /obj/item/weapon/gun) || istype(perp.l_hand, /obj/item/weapon/melee))
- threatcount += 4
-
- if(istype(perp.r_hand, /obj/item/weapon/gun) || istype(perp.r_hand, /obj/item/weapon/melee))
- threatcount += 4
-
- if(istype(perp.belt, /obj/item/weapon/gun) || istype(perp.belt, /obj/item/weapon/melee))
- threatcount += 2
-
- if(perp.species.name != "Human") //beepsky so racist.
- threatcount += 2
-
- if(check_records || check_arrest)
- var/perpname = perp.name
- if(id)
- perpname = id.registered_name
-
- var/datum/data/record/R = find_security_record("name", perpname)
- if(check_records && !R)
- threatcount += 4
-
- if(check_arrest && R && (R.fields["criminal"] == "*Arrest*"))
- threatcount += 4
-
- return threatcount
diff --git a/code/game/machinery/magnet.dm b/code/game/machinery/magnet.dm
index b04e9d1851b..501d7a0b758 100644
--- a/code/game/machinery/magnet.dm
+++ b/code/game/machinery/magnet.dm
@@ -164,7 +164,7 @@
if(prob(electricity_level))
explosion(loc, 0, 1, 2, 3) // ooo dat shit EXPLODES son
spawn(2)
- del(src)
+ qdel(src)
*/
updateicon()
@@ -190,8 +190,10 @@
pulling = 0
-
-
+/obj/machinery/magnetic_module/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, freq)
+ ..()
/obj/machinery/magnetic_controller
name = "Magnetic Control Console"
@@ -364,7 +366,7 @@
// N, S, E, W are directional
// C is center
// R is random (in magnetic field's bounds)
- del(signal)
+ qdel(signal)
break // break the loop if the character located is invalid
signal.data["command"] = nextmove
@@ -399,25 +401,7 @@
// there doesn't HAVE to be separators but it makes paths syntatically visible
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+/obj/machinery/magnetic_controller/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, frequency)
+ ..()
diff --git a/code/game/machinery/navbeacon.dm b/code/game/machinery/navbeacon.dm
index de2a13aab52..c9228000e25 100644
--- a/code/game/machinery/navbeacon.dm
+++ b/code/game/machinery/navbeacon.dm
@@ -1,6 +1,9 @@
// Navigation beacon for AI robots
// Functions as a transponder: looks for incoming signal matching
+
+var/global/list/navbeacons // no I don't like putting this in, but it will do for now
+
/obj/machinery/navbeacon
icon = 'icons/obj/objects.dmi'
@@ -27,6 +30,13 @@
var/turf/T = loc
hide(T.intact)
+
+ // add beacon to MULE bot beacon list
+ if(freq == 1400)
+ if(!navbeacons)
+ navbeacons = new()
+ navbeacons += src
+
spawn(5) // must wait for map loading to finish
if(radio_controller)
@@ -240,6 +250,8 @@ Transponder Codes:
"}
updateDialog()
-
-
-
+/obj/machinery/navbeacon/Destroy()
+ navbeacons.Remove(src)
+ if(radio_controller)
+ radio_controller.remove_object(src, freq)
+ ..()
diff --git a/code/game/machinery/newscaster.dm b/code/game/machinery/newscaster.dm
index 3a238e24b04..ff974fbe19d 100644
--- a/code/game/machinery/newscaster.dm
+++ b/code/game/machinery/newscaster.dm
@@ -164,7 +164,7 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
var/c_locked=0; //Will our new channel be locked to public submissions?
var/hitstaken = 0 //Death at 3 hits from an item with force>=15
var/datum/feed_channel/viewing_channel = null
- luminosity = 0
+ light_range = 0
anchored = 1
@@ -180,7 +180,7 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
src.update_icon() //for any custom ones on the map...
..() //I just realised the newscasters weren't in the global machines list. The superconstructor call will tend to that
-/obj/machinery/newscaster/Del()
+/obj/machinery/newscaster/Destroy()
allCasters -= src
..()
@@ -223,12 +223,12 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
/obj/machinery/newscaster/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
src.isbroken=1
if(prob(50))
- del(src)
+ qdel(src)
else
src.update_icon() //can't place it above the return and outside the if-else. or we might get runtimes of null.update_icon() if(prob(50)) goes in.
return
@@ -496,7 +496,7 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
if ((usr.contents.Find(src) || ((get_dist(src, usr) <= 1) && istype(src.loc, /turf))) || (istype(usr, /mob/living/silicon)))
usr.set_machine(src)
if(href_list["set_channel_name"])
- src.channel_name = sanitizeSafe(input(usr, "Provide a Feed Channel Name", "Network Channel Handler", ""))
+ src.channel_name = sanitizeSafe(input(usr, "Provide a Feed Channel Name", "Network Channel Handler", ""), MAX_LNAME_LEN)
src.updateUsrDialog()
//src.update_icon()
@@ -596,7 +596,7 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
src.updateUsrDialog()
else if(href_list["set_wanted_name"])
- src.channel_name = sanitizeSafe(input(usr, "Provide the name of the Wanted person", "Network Security Handler", ""))
+ src.channel_name = sanitizeSafe(input(usr, "Provide the name of the Wanted person", "Network Security Handler", ""), MAX_LNAME_LEN)
src.updateUsrDialog()
else if(href_list["set_wanted_desc"])
@@ -784,7 +784,7 @@ var/list/obj/machinery/newscaster/allCasters = list() //Global list that will co
photo_data.photo.loc = src.loc
if(!issilicon(user))
user.put_in_inactive_hand(photo_data.photo)
- del(photo_data)
+ qdel(photo_data)
if(istype(user.get_active_hand(), /obj/item/weapon/photo))
var/obj/item/photo = user.get_active_hand()
diff --git a/code/game/machinery/nuclear_bomb.dm b/code/game/machinery/nuclear_bomb.dm
index d13f18c3e9f..2fb1c721d3b 100644
--- a/code/game/machinery/nuclear_bomb.dm
+++ b/code/game/machinery/nuclear_bomb.dm
@@ -423,7 +423,7 @@ obj/machinery/nuclearbomb/proc/nukehack_win(mob/user as mob)
return
return
-/obj/item/weapon/disk/nuclear/Del()
+/obj/item/weapon/disk/nuclear/Destroy()
if(blobstart.len > 0)
var/obj/D = new /obj/item/weapon/disk/nuclear(pick(blobstart))
message_admins("[src] has been destroyed. Spawning [D] at ([D.x], [D.y], [D.z]).")
diff --git a/code/game/machinery/overview.dm b/code/game/machinery/overview.dm
index de67e7cea10..cb80bd20afc 100644
--- a/code/game/machinery/overview.dm
+++ b/code/game/machinery/overview.dm
@@ -180,8 +180,8 @@
HI.Insert(I, frame=1, delay = 5)
HI.Insert(J, frame=2, delay = 5)
- del(I)
- del(J)
+ qdel(I)
+ qdel(J)
H.icon = HI
H.layer = 25
usr.mapobjs += H
@@ -306,7 +306,7 @@
var/icon/I = imap[i+1]
H.icon = I
- del(I)
+ qdel(I)
H.layer = 25
usr.mapobjs += H
@@ -353,7 +353,7 @@ proc/getb(col)
/mob/proc/clearmap()
src.client.screen -= src.mapobjs
for(var/obj/screen/O in mapobjs)
- del(O)
+ qdel(O)
mapobjs = null
src.unset_machine()
diff --git a/code/game/machinery/pipe/construction.dm b/code/game/machinery/pipe/construction.dm
index 637bcbee11b..9bee0af72f4 100644
--- a/code/game/machinery/pipe/construction.dm
+++ b/code/game/machinery/pipe/construction.dm
@@ -1149,7 +1149,7 @@ Buildable meters
"[user] fastens the [src].", \
"\blue You have fastened the [src].", \
"You hear ratchet.")
- del(src) // remove the pipe item
+ qdel(src) // remove the pipe item
return
//TODO: DEFERRED
@@ -1177,7 +1177,7 @@ Buildable meters
new/obj/machinery/meter( src.loc )
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
user << "\blue You have fastened the meter to the pipe"
- del(src)
+ qdel(src)
//not sure why these are necessary
#undef PIPE_SIMPLE_STRAIGHT
#undef PIPE_SIMPLE_BENT
diff --git a/code/game/machinery/pipe/pipe_dispenser.dm b/code/game/machinery/pipe/pipe_dispenser.dm
index fb296d24091..eb0ec519620 100644
--- a/code/game/machinery/pipe/pipe_dispenser.dm
+++ b/code/game/machinery/pipe/pipe_dispenser.dm
@@ -103,7 +103,7 @@
if (istype(W, /obj/item/pipe) || istype(W, /obj/item/pipe_meter))
usr << "\blue You put [W] back to [src]."
user.drop_item()
- del(W)
+ qdel(W)
return
else if (istype(W, /obj/item/weapon/wrench))
if (unwrenched==0)
@@ -145,7 +145,7 @@
//Allow you to push disposal pipes into it (for those with density 1)
/obj/machinery/pipedispenser/disposal/Crossed(var/obj/structure/disposalconstruct/pipe as obj)
if(istype(pipe) && !pipe.anchored)
- del(pipe)
+ qdel(pipe)
Nah
*/
@@ -161,7 +161,7 @@ Nah
if (pipe.anchored)
return
- del(pipe)
+ qdel(pipe)
/obj/machinery/pipedispenser/disposal/attack_hand(user as mob)
if(..())
@@ -179,6 +179,11 @@ Nah
Chute Upwards Downwards
+Sorting
+Sorting (Wildcard)
+Sorting (Untagged)
+Tagger
+Tagger (Partial)
"}
///// Z-Level stuff
@@ -220,6 +225,19 @@ Nah
if(7)
C.ptype = 8
C.density = 1
+ if(8)
+ C.ptype = 9
+ C.subtype = 0
+ if(9)
+ C.ptype = 9
+ C.subtype = 1
+ if(10)
+ C.ptype = 9
+ C.subtype = 2
+ if(11)
+ C.ptype = 13
+ if(12)
+ C.ptype = 14
///// Z-Level stuff
if(21)
C.ptype = 11
diff --git a/code/game/machinery/pipe/pipelayer.dm b/code/game/machinery/pipe/pipelayer.dm
new file mode 100644
index 00000000000..32aafb21cd8
--- /dev/null
+++ b/code/game/machinery/pipe/pipelayer.dm
@@ -0,0 +1,137 @@
+/obj/machinery/pipelayer
+
+ name = "automatic pipe layer"
+ icon = 'icons/obj/stationobjs.dmi'
+ icon_state = "pipe_d"
+ density = 1
+ var/turf/old_turf
+ var/old_dir
+ var/on = 0
+ var/a_dis = 0
+ var/P_type = 0
+ var/P_type_t = ""
+ var/max_metal = 50
+ var/metal = 10
+ var/obj/item/weapon/wrench/W
+ var/list/Pipes = list("regular pipes"=0,"scrubbers pipes"=31,"supply pipes"=29,"heat exchange pipes"=2)
+
+/obj/machinery/pipelayer/New()
+ W = new(src)
+ ..()
+
+/obj/machinery/pipelayer/Move(new_turf,M_Dir)
+ ..()
+
+ if(on && a_dis)
+ dismantleFloor(old_turf)
+ layPipe(old_turf,M_Dir,old_dir)
+
+ old_turf = new_turf
+ old_dir = turn(M_Dir,180)
+
+/obj/machinery/pipelayer/attack_hand(mob/user as mob)
+ if(!metal&&!on)
+ user << "\The [src] doesn't work without metal."
+ return
+ on=!on
+ user.visible_message("[user] has [!on?"de":""]activated \the [src].", "You [!on?"de":""]activate \the [src].")
+ return
+
+/obj/machinery/pipelayer/attackby(var/obj/item/W as obj, var/mob/user as mob)
+
+ if (istype(W, /obj/item/weapon/wrench))
+ P_type_t = input("Choose pipe type", "Pipe type") as null|anything in Pipes
+ P_type = Pipes[P_type_t]
+ user.visible_message("[user] has set \the [src] to manufacture [P_type_t].", "You set \the [src] to manufacture [P_type_t].")
+ return
+
+ if(istype(W, /obj/item/weapon/crowbar))
+ a_dis=!a_dis
+ user.visible_message("[user] has [!a_dis?"de":""]activated auto-dismantling.", "You [!a_dis?"de":""]activate auto-dismantling.")
+ return
+
+ if(istype(W, /obj/item/stack/sheet/metal))
+
+ var/result = load_metal(W)
+ if(isnull(result))
+ user << "Unable to load [W] - no metal found."
+ else if(!result)
+ user << "\The [src] is full."
+ else
+ user.visible_message("[user] has loaded metal into \the [src].", "You load metal into \the [src]")
+
+ return
+
+ if(istype(W, /obj/item/weapon/screwdriver))
+ if(metal)
+ var/m = round(input(usr,"Please specify the amount of metal to remove","Remove metal",min(round(metal),50)) as num, 1)
+ m = min(m, 50)
+ m = min(m, round(metal))
+ m = round(m)
+ if(m)
+ use_metal(m)
+ var/obj/item/stack/sheet/metal/MM = new (get_turf(src))
+ MM.amount = m
+ user.visible_message("[user] removes [m] sheet\s of metal from the \the [src].", "You remove [m] sheet\s of metal from \the [src]")
+ else
+ user << "\The [src] is empty."
+ return
+ ..()
+
+/obj/machinery/pipelayer/examine(mob/user)
+ ..()
+ user << "\The [src] has [metal] sheet\s, is set to produce [P_type_t], and auto-dismantling is [!a_dis?"de":""]activated."
+
+/obj/machinery/pipelayer/proc/reset()
+ on=0
+ return
+
+/obj/machinery/pipelayer/proc/load_metal(var/obj/item/stack/sheet/metal/MM)
+ if(istype(MM) && MM.get_amount())
+ var/cur_amount = metal
+ var/to_load = max(max_metal - round(cur_amount),0)
+ if(to_load)
+ to_load = min(MM.get_amount(), to_load)
+ metal += to_load
+ MM.use(to_load)
+ return to_load
+ else
+ return 0
+ return
+
+/obj/machinery/pipelayer/proc/use_metal(amount)
+ if(!metal || metal\The [src] has to be secured first!
"
return STATUS_CLOSE
- return STATUS_INTERACTIVE
+ return ..()
/obj/machinery/porta_turret/Topic(href, href_list, var/nowindow = 0)
@@ -271,7 +272,7 @@
new /obj/item/device/assembly/prox_sensor(loc)
else
user << "You remove the turret but did not manage to salvage anything."
- del(src) // qdel
+ qdel(src) // qdel
if(istype(I, /obj/item/weapon/card/emag) && !emagged)
//Emagging the turret makes it go bonkers and stun everyone. It also makes
@@ -317,7 +318,7 @@
user << "You unsecure the exterior bolts on the turret."
invisibility = 0
update_icon()
- del(cover) //deletes the cover, and the turret instance itself becomes its own cover. - qdel
+ qdel(cover) //deletes the cover, and the turret instance itself becomes its own cover.
wrenching = 0
else if(istype(I, /obj/item/weapon/card/id)||istype(I, /obj/item/device/pda))
@@ -387,10 +388,10 @@
/obj/machinery/porta_turret/ex_act(severity)
switch (severity)
if (1)
- del(src)
+ qdel(src)
if (2)
if (prob(25))
- del(src)
+ qdel(src)
else
take_damage(150) //should instakill most turrets
if (3)
@@ -404,7 +405,7 @@
spark_system.start() //creates some sparks because they look cool
density = 1
update_icon()
- del(cover) //deletes the cover - no need on keeping it there! - del
+ qdel(cover) //deletes the cover - no need on keeping it there!
/obj/machinery/porta_turret/proc/create_cover()
if(cover == null && anchored)
@@ -418,7 +419,7 @@
if(cover == null && anchored) //if it has no cover and is anchored
if(stat & BROKEN) //if the turret is borked
- del(cover) //delete its cover, assuming it has one. Workaround for a pesky little bug - qdel
+ qdel(cover) //delete its cover, assuming it has one. Workaround for a pesky little bug
else
create_cover()
@@ -494,7 +495,7 @@
return check_anomalies ? TURRET_PRIORITY_TARGET : TURRET_NOT_TARGET
if(ishuman(L)) //if the target is a human, analyze threat level
- if(assess_perp(L, check_weapons, check_records, check_arrest) < 4)
+ if(assess_perp(L) < 4)
return TURRET_NOT_TARGET //if threat level < 4, keep going
if(L.lying) //if the perp is lying down, it's still a target but a less-important target
@@ -502,6 +503,15 @@
return TURRET_PRIORITY_TARGET //if the perp has passed all previous tests, congrats, it is now a "shoot-me!" nominee
+/obj/machinery/porta_turret/proc/assess_perp(var/mob/living/carbon/human/H)
+ if(!H || !istype(H))
+ return 0
+
+ if(emagged)
+ return 10
+
+ return H.assess_perp(src, check_weapons, check_records, check_arrest)
+
/obj/machinery/porta_turret/proc/tryToShootAt(var/list/mob/living/targets)
if(targets.len && last_target && (last_target in targets) && target(last_target))
return 1
@@ -548,15 +558,6 @@
invisibility = INVISIBILITY_LEVEL_TWO
update_icon()
-
-/obj/machinery/porta_turret/on_assess_perp(mob/living/carbon/human/perp)
- if((check_access || attacked) && !allowed(perp))
- //if the turret has been attacked or is angry, target all non-authorized personnel, see req_access
- return 10
-
- return ..()
-
-
/obj/machinery/porta_turret/proc/target(var/mob/living/target)
if(disabled)
return
@@ -572,7 +573,7 @@
/obj/machinery/porta_turret/proc/shootAt(var/mob/living/target)
//any emagged turrets will shoot extremely fast! This not only is deadly, but drains a lot power!
- if(!emagged) //if it hasn't been emagged, it has to obey a cooldown rate
+ if(!(emagged || attacked)) //if it hasn't been emagged or attacked, it has to obey a cooldown rate
if(last_fired || !raised) //prevents rapid-fire shooting, unless it's been emagged
return
last_fired = 1
@@ -671,7 +672,7 @@
playsound(loc, 'sound/items/Crowbar.ogg', 75, 1)
user << "You dismantle the turret construction."
new /obj/item/stack/sheet/metal( loc, 5)
- del(src) // qdel
+ qdel(src) // qdel
return
if(1)
@@ -736,7 +737,7 @@
target_type = /obj/machinery/porta_turret
build_step = 4
- del(I) //delete the gun :( qdel
+ qdel(I) //delete the gun :(
return
else if(istype(I, /obj/item/weapon/wrench))
@@ -752,7 +753,7 @@
user << "\the [I] is stuck to your hand, you cannot put it in \the [src]"
return
user << "You add the prox sensor to the turret."
- del(I) // qdel
+ qdel(I)
return
//attack_hand() removes the gun
@@ -807,7 +808,7 @@
// Turret.cover=new/obj/machinery/porta_turret_cover(loc)
// Turret.cover.Parent_Turret=Turret
// Turret.cover.name = finish_name
- del(src) // qdel
+ qdel(src) // qdel
else if(istype(I, /obj/item/weapon/crowbar))
playsound(loc, 'sound/items/Crowbar.ogg', 75, 1)
@@ -817,8 +818,7 @@
return
if(istype(I, /obj/item/weapon/pen)) //you can rename turrets like bots!
- var/t = input(user, "Enter new turret name", name, finish_name) as text
- t = sanitize(t)
+ var/t = sanitizeSafe(input(user, "Enter new turret name", name, finish_name) as text, MAX_NAME_LEN)
if(!t)
return
if(!in_range(src, usr) && loc != usr)
@@ -865,6 +865,10 @@
density = 0
var/obj/machinery/porta_turret/Parent_Turret = null
+/obj/machinery/porta_turret_cover/Destroy()
+ Parent_Turret = null
+ ..()
+
/obj/machinery/porta_turret_cover/attack_ai(mob/user)
return attack_hand(user)
diff --git a/code/game/machinery/requests_console.dm b/code/game/machinery/requests_console.dm
index 3c7e1613b97..23aba341697 100644
--- a/code/game/machinery/requests_console.dm
+++ b/code/game/machinery/requests_console.dm
@@ -54,7 +54,7 @@ var/list/obj/machinery/requests_console/allConsoles = list()
var/message = "";
var/dpt = ""; //the department which will be receiving the message
var/priority = -1 ; //Priority of the message being sent
- luminosity = 0
+ light_range = 0
var/datum/announcement/announcement = new
/obj/machinery/requests_console/power_change()
@@ -80,37 +80,48 @@ var/list/obj/machinery/requests_console/allConsoles = list()
//req_console_departments += department
switch(departmentType)
if(1)
- if(!("[department]" in req_console_assistance))
- req_console_assistance += department
+ req_console_assistance |= department
if(2)
- if(!("[department]" in req_console_supplies))
- req_console_supplies += department
+ req_console_supplies |= department
if(3)
- if(!("[department]" in req_console_information))
- req_console_information += department
+ req_console_information |= department
if(4)
- if(!("[department]" in req_console_assistance))
- req_console_assistance += department
- if(!("[department]" in req_console_supplies))
- req_console_supplies += department
+ req_console_assistance |= department
+ req_console_supplies |= department
if(5)
- if(!("[department]" in req_console_assistance))
- req_console_assistance += department
- if(!("[department]" in req_console_information))
- req_console_information += department
+ req_console_assistance |= department
+ req_console_information |= department
if(6)
- if(!("[department]" in req_console_supplies))
- req_console_supplies += department
- if(!("[department]" in req_console_information))
- req_console_information += department
+ req_console_supplies |= department
+ req_console_information |= department
if(7)
- if(!("[department]" in req_console_assistance))
- req_console_assistance += department
- if(!("[department]" in req_console_supplies))
- req_console_supplies += department
- if(!("[department]" in req_console_information))
- req_console_information += department
+ req_console_assistance |= department
+ req_console_supplies |= department
+ req_console_information |= department
+/obj/machinery/requests_console/Destroy()
+ allConsoles -= src
+ switch(departmentType)
+ if(1)
+ req_console_assistance -= department
+ if(2)
+ req_console_supplies -= department
+ if(3)
+ req_console_information -= department
+ if(4)
+ req_console_assistance -= department
+ req_console_supplies -= department
+ if(5)
+ req_console_assistance -= department
+ req_console_information -= department
+ if(6)
+ req_console_supplies -= department
+ req_console_information -= department
+ if(7)
+ req_console_assistance -= department
+ req_console_supplies -= department
+ req_console_information -= department
+ ..()
/obj/machinery/requests_console/attack_hand(user as mob)
if(..(user))
@@ -165,7 +176,7 @@ var/list/obj/machinery/requests_console/allConsoles = list()
if (Console.department == department)
Console.newmessagepriority = 0
Console.icon_state = "req_comp0"
- Console.luminosity = 1
+ Console.set_light(1)
newmessagepriority = 0
icon_state = "req_comp0"
for(var/msg in messages)
@@ -250,7 +261,7 @@ var/list/obj/machinery/requests_console/allConsoles = list()
if(href_list["sendAnnouncement"])
if(!announcementConsole) return
- announcement.Announce(message)
+ announcement.Announce(message, msg_sanitized = 1)
reset_announce()
screen = 0
@@ -309,7 +320,7 @@ var/list/obj/machinery/requests_console/allConsoles = list()
Console.messages += "Message from [department] [message]"
screen = 6
- Console.luminosity = 2
+ Console.set_light(2)
messages += "Message sent to [dpt] [message]"
else
for (var/mob/O in hearers(4, src.loc))
diff --git a/code/game/machinery/robot_fabricator.dm b/code/game/machinery/robot_fabricator.dm
index 0c3ae561157..6b0cb71fbd9 100644
--- a/code/game/machinery/robot_fabricator.dm
+++ b/code/game/machinery/robot_fabricator.dm
@@ -22,7 +22,7 @@
if(!M.get_amount())
return
while(metal_amount < 150000 && M.amount)
- src.metal_amount += O.matter["metal"] /*O:height * O:width * O:length * 100000.0*/
+ src.metal_amount += O.matter[DEFAULT_WALL_MATERIAL] /*O:height * O:width * O:length * 100000.0*/
M.use(1)
count++
diff --git a/code/game/machinery/seed_extractor.dm b/code/game/machinery/seed_extractor.dm
index 4778ac13ead..e9a2081fb2d 100644
--- a/code/game/machinery/seed_extractor.dm
+++ b/code/game/machinery/seed_extractor.dm
@@ -11,7 +11,7 @@ obj/machinery/seed_extractor/attackby(var/obj/item/O as obj, var/mob/user as mob
// Fruits and vegetables.
if(istype(O, /obj/item/weapon/reagent_containers/food/snacks/grown) || istype(O, /obj/item/weapon/grown))
- user.drop_item(O)
+ user.remove_from_mob(O)
var/datum/seed/new_seed_type
if(istype(O, /obj/item/weapon/grown))
@@ -31,7 +31,7 @@ obj/machinery/seed_extractor/attackby(var/obj/item/O as obj, var/mob/user as mob
else
user << "[O] doesn't seem to have any usable seeds inside it."
- del(O)
+ qdel(O)
//Grass.
else if(istype(O, /obj/item/stack/tile/grass))
diff --git a/code/game/machinery/status_display.dm b/code/game/machinery/status_display.dm
index 8d7ed7fccc4..cf67c4d01f0 100644
--- a/code/game/machinery/status_display.dm
+++ b/code/game/machinery/status_display.dm
@@ -45,6 +45,11 @@
var/const/STATUS_DISPLAY_TIME = 4
var/const/STATUS_DISPLAY_CUSTOM = 99
+/obj/machinery/status_display/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,frequency)
+ ..()
+
// register for radio system
/obj/machinery/status_display/initialize()
..()
diff --git a/code/game/machinery/suit_storage_unit.dm b/code/game/machinery/suit_storage_unit.dm
index 940ec0f104c..d1e728e6767 100644
--- a/code/game/machinery/suit_storage_unit.dm
+++ b/code/game/machinery/suit_storage_unit.dm
@@ -76,12 +76,12 @@
if(1.0)
if(prob(50))
src.dump_everything() //So suits dont survive all the time
- del(src)
+ qdel(src)
return
if(2.0)
if(prob(50))
src.dump_everything()
- del(src)
+ qdel(src)
return
else
return
@@ -465,7 +465,7 @@
src.update_icon()
// for(var/obj/O in src)
-// del(O)
+// qdel(O)
src.add_fingerprint(usr)
src.updateUsrDialog()
@@ -511,7 +511,7 @@
//for(var/obj/O in src)
// O.loc = src.loc
src.add_fingerprint(user)
- del(G)
+ qdel(G)
src.updateUsrDialog()
src.update_icon()
return
@@ -612,10 +612,10 @@
wires = new(src)
target_department = departments[1]
target_species = species[1]
- if(!target_department || !target_species) del(src)
+ if(!target_department || !target_species) qdel(src)
-/obj/machinery/suit_cycler/Del()
- del(wires) // qdel
+/obj/machinery/suit_cycler/Destroy()
+ qdel(wires)
wires = null
..()
@@ -696,7 +696,7 @@
src.occupant = M
src.add_fingerprint(user)
- del(G)
+ qdel(G)
src.updateUsrDialog()
@@ -736,6 +736,10 @@
user << "The cycler already contains a helmet."
return
+ if(I.icon_override == CUSTOM_ITEM_MOB)
+ user << "You cannot refit a customised voidsuit."
+ return
+
user << "You fit \the [I] into the suit cycler."
user.drop_item()
I.loc = src
@@ -755,6 +759,10 @@
user << "The cycler already contains a voidsuit."
return
+ if(I.icon_override == CUSTOM_ITEM_MOB)
+ user << "You cannot refit a customised voidsuit."
+ return
+
user << "You fit \the [I] into the suit cycler."
user.drop_item()
I.loc = src
@@ -987,7 +995,6 @@
helmet.name = "engineering voidsuit helmet"
helmet.icon_state = "rig0-engineering"
helmet.item_state = "eng_helm"
- helmet.item_color = "engineering"
if(suit)
suit.name = "engineering voidsuit"
suit.icon_state = "rig-engineering"
@@ -997,7 +1004,6 @@
helmet.name = "mining voidsuit helmet"
helmet.icon_state = "rig0-mining"
helmet.item_state = "mining_helm"
- helmet.item_color = "mining"
if(suit)
suit.name = "mining voidsuit"
suit.icon_state = "rig-mining"
@@ -1007,7 +1013,6 @@
helmet.name = "medical voidsuit helmet"
helmet.icon_state = "rig0-medical"
helmet.item_state = "medical_helm"
- helmet.item_color = "medical"
if(suit)
suit.name = "medical voidsuit"
suit.icon_state = "rig-medical"
@@ -1017,7 +1022,6 @@
helmet.name = "security voidsuit helmet"
helmet.icon_state = "rig0-sec"
helmet.item_state = "sec_helm"
- helmet.item_color = "sec"
if(suit)
suit.name = "security voidsuit"
suit.icon_state = "rig-sec"
@@ -1027,7 +1031,6 @@
helmet.name = "atmospherics voidsuit helmet"
helmet.icon_state = "rig0-atmos"
helmet.item_state = "atmos_helm"
- helmet.item_color = "atmos"
if(suit)
suit.name = "atmospherics voidsuit"
suit.icon_state = "rig-atmos"
@@ -1037,7 +1040,6 @@
helmet.name = "blood-red voidsuit helmet"
helmet.icon_state = "rig0-syndie"
helmet.item_state = "syndie_helm"
- helmet.item_color = "syndie"
if(suit)
suit.name = "blood-red voidsuit"
suit.item_state = "syndie_voidsuit"
diff --git a/code/game/machinery/syndicatebeacon.dm b/code/game/machinery/syndicatebeacon.dm
index 957f7bf5364..fb4a03d21f6 100644
--- a/code/game/machinery/syndicatebeacon.dm
+++ b/code/game/machinery/syndicatebeacon.dm
@@ -95,7 +95,7 @@
if(surplus() < 1500)
if(user) user << "The connected wire doesn't have enough current."
return
- for(var/obj/machinery/singularity/singulo in world)
+ for(var/obj/singularity/singulo in world)
if(singulo.z == z)
singulo.target = src
icon_state = "[icontype]1"
@@ -106,7 +106,7 @@
/obj/machinery/power/singularity_beacon/proc/Deactivate(mob/user = null)
- for(var/obj/machinery/singularity/singulo in world)
+ for(var/obj/singularity/singulo in world)
if(singulo.target == src)
singulo.target = null
icon_state = "[icontype]0"
@@ -149,7 +149,7 @@
return
-/obj/machinery/power/singularity_beacon/Del()
+/obj/machinery/power/singularity_beacon/Destroy()
if(active)
Deactivate()
..()
diff --git a/code/game/machinery/telecomms/broadcaster.dm b/code/game/machinery/telecomms/broadcaster.dm
index 5a3caafa263..c6fee28b40c 100644
--- a/code/game/machinery/telecomms/broadcaster.dm
+++ b/code/game/machinery/telecomms/broadcaster.dm
@@ -98,7 +98,7 @@ var/message_delay = 0 // To make sure restarting the recentmessages list is kept
/* --- Do a snazzy animation! --- */
flick("broadcaster_send", src)
-/obj/machinery/telecomms/broadcaster/Del()
+/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
diff --git a/code/game/machinery/telecomms/logbrowser.dm b/code/game/machinery/telecomms/logbrowser.dm
index 6dd5586fd81..50fa8b185b6 100644
--- a/code/game/machinery/telecomms/logbrowser.dm
+++ b/code/game/machinery/telecomms/logbrowser.dm
@@ -63,64 +63,37 @@
// If the log is a speech file
if(C.input_type == "Speech File")
- dat += "
[C.name] \[X\] "
// -- 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/mob/M = new mobtype
-
- if(ishuman(M) || isbrain(M))
- var/mob/living/carbon/human/H = M
- race = "[H.species.name]"
-
-
- else if(issmall(M))
- race = "Monkey"
- language = race
-
- else if(issilicon(M) || C.parameters["job"] == "AI") // sometimes M gets deleted prematurely for AIs... just check the job
- race = "Artificial Life"
-
- else if(isslime(M)) // NT knows a lot about slimes, but not aliens. Can identify slimes
- race = "slime"
- language = race
-
- else if(isanimal(M))
- race = "Domestic Animal"
- language = race
-
- else
- race = "Unidentifiable"
- language = race
-
- del(M)
+ var/race = C.parameters["race"] // The actual race of the mob
+ var/language = C.parameters["language"] // The language spoken, or null/""
// -- 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 += "Data type: [C.input_type] "
- dat += "Source: [C.parameters["name"]] (Job: [C.parameters["job"]]) "
- dat += "Class: [race] "
- dat += "Contents: \"[C.parameters["message"]]\" "
-
+ if(universal_translate || C.parameters["uspeech"] || C.parameters["intelligible"])
+ dat += "Data type: [C.input_type] "
+ dat += "Source: [C.parameters["name"]] (Job: [C.parameters["job"]]) "
+ dat += "Class: [race] "
+ dat += "Contents: \"[C.parameters["message"]]\" "
+ if(language)
+ dat += "Language: [language] "
// -- Orator is not human and universal translate not active --
else
- dat += "Data type: Audio File "
- dat += "Source: Unidentifiable "
- dat += "Class: [race] "
- dat += "Contents: Unintelligble "
+ dat += "Data type: Audio File "
+ dat += "Source: Unidentifiable "
+ dat += "Class: [race] "
+ dat += "Contents: Unintelligble "
dat += "
"
else if(C.input_type == "Execution Error")
- dat += "
[C.name] \[X\] "
- dat += "Output: \"[C.parameters["message"]]\" "
+ dat += "
[C.name] \[X\] "
+ dat += "Output: \"[C.parameters["message"]]\" "
dat += "
"
@@ -189,7 +162,7 @@
temp = "- DELETED ENTRY: [D.name] -"
SelectedServer.log_entries.Remove(D)
- del(D)
+ qdel(D)
else
temp = "- FAILED: NO SELECTED MACHINE -"
@@ -227,7 +200,7 @@
A.state = 3
A.icon_state = "3"
A.anchored = 1
- del(src)
+ qdel(src)
else
user << "\blue You disconnect the monitor."
var/obj/structure/computerframe/A = new /obj/structure/computerframe( src.loc )
@@ -238,7 +211,7 @@
A.state = 4
A.icon_state = "4"
A.anchored = 1
- del(src)
+ qdel(src)
else if(istype(D, /obj/item/weapon/card/emag) && !emagged)
playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1)
emagged = 1
diff --git a/code/game/machinery/telecomms/machine_interactions.dm b/code/game/machinery/telecomms/machine_interactions.dm
index 581ae59ab48..15c627420f7 100644
--- a/code/game/machinery/telecomms/machine_interactions.dm
+++ b/code/game/machinery/telecomms/machine_interactions.dm
@@ -1,404 +1,404 @@
-//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32
-
-
-/*
-
- All telecommunications interactions:
-
-*/
-
-#define STATION_Z 1
-#define TELECOMM_Z 3
-
-/obj/machinery/telecomms
- var/temp = "" // output message
- var/construct_op = 0
-
-
-/obj/machinery/telecomms/attackby(obj/item/P as obj, mob/user as mob)
-
- // Using a multitool lets you access the receiver's interface
- if(istype(P, /obj/item/device/multitool))
- attack_hand(user)
-
-
- // REPAIRING: Use Nanopaste to repair 10-20 integrity points.
- if(istype(P, /obj/item/stack/nanopaste))
- var/obj/item/stack/nanopaste/T = P
- if (integrity < 100) //Damaged, let's repair!
- if (T.use(1))
- integrity = between(0, integrity + rand(10,20), 100)
- usr << "You apply the Nanopaste to [src], repairing some of the damage."
- else
- usr << "This machine is already in perfect condition."
- return
-
-
- switch(construct_op)
- if(0)
- if(istype(P, /obj/item/weapon/screwdriver))
- user << "You unfasten the bolts."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
- construct_op ++
- if(1)
- if(istype(P, /obj/item/weapon/screwdriver))
- user << "You fasten the bolts."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
- construct_op --
- if(istype(P, /obj/item/weapon/wrench))
- user << "You dislodge the external plating."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
- construct_op ++
- if(2)
- if(istype(P, /obj/item/weapon/wrench))
- user << "You secure the external plating."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
- construct_op --
- if(istype(P, /obj/item/weapon/wirecutters))
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
- user << "You remove the cables."
- construct_op ++
- var/obj/item/stack/cable_coil/A = new /obj/item/stack/cable_coil( user.loc )
- A.amount = 5
- stat |= BROKEN // the machine's been borked!
- if(3)
- if(istype(P, /obj/item/stack/cable_coil))
- var/obj/item/stack/cable_coil/A = P
- if (A.use(5))
- user << "You insert the cables."
- construct_op--
- stat &= ~BROKEN // the machine's not borked anymore!
- else
- user << "You need five coils of wire for this."
- if(istype(P, /obj/item/weapon/crowbar))
- user << "You begin prying out the circuit board other components..."
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
- if(do_after(user,60))
- user << "You finish prying out the components."
-
- // Drop all the component stuff
- if(contents.len > 0)
- for(var/obj/x in src)
- x.loc = user.loc
- else
-
- // If the machine wasn't made during runtime, probably doesn't have components:
- // manually find the components and drop them!
- var/newpath = text2path(circuitboard)
- var/obj/item/weapon/circuitboard/C = new newpath
- for(var/I in C.req_components)
- for(var/i = 1, i <= C.req_components[I], i++)
- newpath = text2path(I)
- var/obj/item/s = new newpath
- s.loc = user.loc
- if(istype(P, /obj/item/stack/cable_coil))
- var/obj/item/stack/cable_coil/A = P
- A.amount = 1
-
- // Drop a circuit board too
- C.loc = user.loc
-
- // Create a machine frame and delete the current machine
- var/obj/machinery/constructable_frame/machine_frame/F = new
- F.loc = src.loc
- del(src)
-
-
-/obj/machinery/telecomms/attack_ai(var/mob/user as mob)
- attack_hand(user)
-
-/obj/machinery/telecomms/attack_hand(var/mob/user as mob)
-
- // You need a multitool to use this, or be silicon
- if(!issilicon(user))
- // istype returns false if the value is null
- if(!istype(user.get_active_hand(), /obj/item/device/multitool))
- return
-
- if(stat & (BROKEN|NOPOWER))
- return
-
- var/obj/item/device/multitool/P = get_multitool(user)
-
- user.set_machine(src)
- var/dat
- dat = "[src.name]
[src.name] Access
"
- dat += " [temp] "
- dat += " Power Status: [src.toggled ? "On" : "Off"]"
- if(on && toggled)
- if(id != "" && id)
- dat += " Identification String: [id]"
- else
- dat += " Identification String: NULL"
- dat += " Network: [network]"
- dat += " Prefabrication: [autolinkers.len ? "TRUE" : "FALSE"]"
- if(hide) dat += " Shadow Link: ACTIVE"
-
- //Show additional options for certain machines.
- dat += Options_Menu()
-
- dat += " Linked Network Entities: "
-
- var/i = 0
- for(var/obj/machinery/telecomms/T in links)
- i++
- if(T.hide && !src.hide)
- continue
- dat += "
"
+ dat += " Current Network: [network]"
+ dat += " Selected Server: [SelectedServer.id]
"
+ dat += " \[Edit Code\]"
+ dat += " Signal Execution: "
+ if(SelectedServer.autoruncode)
+ dat += "ALWAYS"
+ else
+ dat += "NEVER"
+
+
+ user << browse(dat, "window=traffic_control;size=575x400")
+ onclose(user, "server_control")
+
+ temp = ""
+ return
+
+
+ Topic(href, href_list)
+ if(..())
+ return
+
+
+ add_fingerprint(usr)
+ usr.set_machine(src)
+ if(!src.allowed(usr) && !emagged)
+ usr << "\red ACCESS DENIED."
+ return
+
+ 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 = "- FAILED: CANNOT PROBE WHEN BUFFER FULL -"
+
+ else
+ for(var/obj/machinery/telecomms/server/T in range(25, src))
+ if(T.network == network)
+ servers.Add(T)
+
+ if(!servers.len)
+ temp = "- FAILED: UNABLE TO LOCATE SERVERS IN \[[network]\] -"
+ else
+ temp = "- [servers.len] SERVERS PROBED & BUFFERED -"
+
+ 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]\"")
+ spawn()
+ update_ide()
+
+ 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 = input(usr, "Which network do you want to view?", "Comm Monitor", network) as null|text
+
+ if(newnet && ((usr in range(1, src) || issilicon(usr))))
+ if(length(newnet) > 15)
+ temp = "- FAILED: NETWORK TAG STRING TOO LENGHTLY -"
+
+ else
+
+ network = newnet
+ screen = 0
+ servers = list()
+ temp = "- NEW NETWORK TAG SET IN ADDRESS \[[network]\] -"
+
+ updateUsrDialog()
+ return
+
+ attackby(var/obj/item/weapon/D as obj, var/mob/user as mob)
+ if(istype(D, /obj/item/weapon/screwdriver))
+ playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ if(do_after(user, 20))
+ if (src.stat & BROKEN)
+ user << "\blue The broken glass falls out."
+ var/obj/structure/computerframe/A = new /obj/structure/computerframe( src.loc )
+ new /obj/item/weapon/shard( src.loc )
+ var/obj/item/weapon/circuitboard/comm_traffic/M = new /obj/item/weapon/circuitboard/comm_traffic( A )
+ for (var/obj/C in src)
+ C.loc = src.loc
+ A.circuit = M
+ A.state = 3
+ A.icon_state = "3"
+ A.anchored = 1
+ qdel(src)
+ else
+ user << "\blue You disconnect the monitor."
+ var/obj/structure/computerframe/A = new /obj/structure/computerframe( src.loc )
+ var/obj/item/weapon/circuitboard/comm_traffic/M = new /obj/item/weapon/circuitboard/comm_traffic( A )
+ for (var/obj/C in src)
+ C.loc = src.loc
+ A.circuit = M
+ A.state = 4
+ A.icon_state = "4"
+ A.anchored = 1
+ qdel(src)
+ else if(istype(D, /obj/item/weapon/card/emag) && !emagged)
+ playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1)
+ emagged = 1
+ user << "\blue You you disable the security protocols"
+ src.updateUsrDialog()
+ return
diff --git a/code/game/machinery/teleporter.dm b/code/game/machinery/teleporter.dm
index 9e68791df00..b1d45a4840c 100644
--- a/code/game/machinery/teleporter.dm
+++ b/code/game/machinery/teleporter.dm
@@ -57,7 +57,7 @@
usr << "You insert the coordinates into the machine."
usr << "A message flashes across the screen reminding the traveller that the nuclear authentication disk is to remain on the station at all times."
user.drop_item()
- del(I)
+ qdel(I)
if(C.data == "Clown Land")
//whoops
@@ -216,7 +216,7 @@
/*
/proc/do_teleport(atom/movable/M as mob|obj, atom/destination, precision)
if(istype(M, /obj/effect))
- del(M)
+ qdel(M)
return
if (istype(M, /obj/item/weapon/disk/nuclear)) // Don't let nuke disks get teleported --NeoFite
for(var/mob/O in viewers(M, null))
diff --git a/code/game/machinery/turret_control.dm b/code/game/machinery/turret_control.dm
index c463c3c4975..223b503f4f7 100644
--- a/code/game/machinery/turret_control.dm
+++ b/code/game/machinery/turret_control.dm
@@ -37,7 +37,7 @@
lethal = 1
icon_state = "control_kill"
-/obj/machinery/turretid/Del()
+/obj/machinery/turretid/Destroy()
if(control_area)
var/area/A = control_area
if(A && istype(A))
@@ -46,12 +46,11 @@
/obj/machinery/turretid/initialize()
if(!control_area)
- var/area/CA = get_area(src)
- control_area = CA.master
+ control_area = get_area(src)
else if(istext(control_area))
for(var/area/A in world)
if(A.name && A.name==control_area)
- control_area = A.master
+ control_area = A
break
if(control_area)
@@ -79,7 +78,7 @@
if(isLocked(user))
return STATUS_CLOSE
- return STATUS_INTERACTIVE
+ return ..()
/obj/machinery/turretid/attackby(obj/item/weapon/W, mob/user)
if(stat & BROKEN)
@@ -178,9 +177,8 @@
TC.ailock = ailock
if(istype(control_area))
- for(var/area/sub_area in control_area.related)
- for (var/obj/machinery/porta_turret/aTurret in sub_area)
- aTurret.setState(TC)
+ for (var/obj/machinery/porta_turret/aTurret in control_area)
+ aTurret.setState(TC)
update_icon()
diff --git a/code/game/machinery/turrets.dm b/code/game/machinery/turrets.dm
index 965210ae155..e3a104d21c5 100644
--- a/code/game/machinery/turrets.dm
+++ b/code/game/machinery/turrets.dm
@@ -13,9 +13,6 @@
/area/turret_protected/Entered(O)
..()
- if( master && master != src )
- return master.Entered(O)
-
if( iscarbon(O) )
turretTargets |= O
else if( istype(O, /obj/mecha) )
@@ -27,9 +24,6 @@
return 1
/area/turret_protected/Exited(O)
- if( master && master != src )
- return master.Exited(O)
-
if( ismob(O) && !issilicon(O) )
turretTargets -= O
else if( istype(O, /obj/mecha) )
@@ -74,7 +68,7 @@
/obj/machinery/turret/proc/take_damage(damage)
src.health -= damage
if(src.health<=0)
- del src
+ qdel(src)
return
/obj/machinery/turret/attack_hand(var/mob/living/carbon/human/user)
@@ -105,7 +99,7 @@
/obj/machinery/turret/proc/update_health()
if(src.health<=0)
- del src
+ qdel(src)
return
/obj/machinery/turretcover
@@ -148,8 +142,6 @@
/obj/machinery/turret/proc/get_protected_area()
var/area/turret_protected/TP = get_area(src)
if(istype(TP))
- if(TP.master && TP.master != TP)
- TP = TP.master
return TP
return
@@ -305,7 +297,7 @@
src.health -= Proj.damage
..()
if(prob(45) && Proj.damage > 0) src.spark_system.start()
- del (Proj)
+ qdel (Proj)
if (src.health <= 0)
src.die()
return
@@ -337,11 +329,11 @@
src.stat |= BROKEN
src.icon_state = "destroyed_target_prism"
if (cover!=null)
- del(cover)
+ qdel(cover)
sleep(3)
flick("explosion", src)
spawn(13)
- del(src)
+ qdel(src)
/obj/machinery/turret/attack_generic(var/mob/user, var/damage, var/attack_message)
if(!damage)
@@ -376,7 +368,7 @@
proc/take_damage(damage)
src.health -= damage
if(src.health<=0)
- del src
+ qdel(src)
return
@@ -389,15 +381,15 @@
ex_act()
- del src
+ qdel(src)
return
emp_act()
- del src
+ qdel(src)
return
meteorhit()
- del src
+ qdel(src)
return
attack_hand(mob/user as mob)
diff --git a/code/game/machinery/vending.dm b/code/game/machinery/vending.dm
index 6f941674f24..6895124593e 100644
--- a/code/game/machinery/vending.dm
+++ b/code/game/machinery/vending.dm
@@ -21,7 +21,7 @@
if(!name)
var/atom/tmp = new path
src.product_name = initial(tmp.name)
- del(tmp)
+ qdel(tmp)
else
src.product_name = name
@@ -143,22 +143,21 @@
src.product_records.Add(product)
-/obj/machinery/vending/Del()
- del(wires) // qdel
+/obj/machinery/vending/Destroy()
+ qdel(wires)
wires = null
- if(coin)
- del(coin) // qdel
- coin = null
+ qdel(coin)
+ coin = null
..()
/obj/machinery/vending/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(25))
@@ -173,18 +172,21 @@
if (prob(50))
spawn(0)
src.malfunction()
- del(src)
+ qdel(src)
return
return
/obj/machinery/vending/attackby(obj/item/weapon/W as obj, mob/user as mob)
+
+ var/obj/item/weapon/card/id/I = W.GetID()
+
if (currently_vending && vendor_account && !vendor_account.suspended)
var/paid = 0
var/handled = 0
- if(istype(W, /obj/item/weapon/card/id))
- var/obj/item/weapon/card/id/C = W
- paid = pay_with_card(C)
+
+ if (I) //for IDs and PDAs and wallets with IDs
+ paid = pay_with_card(I,W)
handled = 1
else if (istype(W, /obj/item/weapon/spacecash/ewallet))
var/obj/item/weapon/spacecash/ewallet/C = W
@@ -202,9 +204,12 @@
nanomanager.update_uis(src)
return // don't smack that machine with your 2 thalers
- if (istype(W, /obj/item/weapon/card/emag))
+ if (I || istype(W, /obj/item/weapon/spacecash))
+ attack_hand(user)
+ return
+ else if (istype(W, /obj/item/weapon/card/emag))
src.emagged = 1
- user << "You short out the product lock on [src]"
+ user << "You short out the product lock on \the [src]"
return
else if(istype(W, /obj/item/weapon/screwdriver))
src.panel_open = !src.panel_open
@@ -224,7 +229,7 @@
W.loc = src
coin = W
categories |= CAT_COIN
- user << "\blue You insert the [W] into the [src]"
+ user << "\blue You insert \the [W] into \the [src]"
nanomanager.update_uis(src)
return
else if(istype(W, /obj/item/weapon/wrench))
@@ -234,9 +239,9 @@
switch (anchored)
if (0)
anchored = 1
- user.visible_message("[user] tightens the bolts securing \the [src] to the floor.", "You tighten the bolts securing \the [src] to the floor.")
+ user.visible_message("\The [user] tightens the bolts securing \the [src] to the floor.", "You tighten the bolts securing \the [src] to the floor.")
if (1)
- user.visible_message("[user] unfastens the bolts securing \the [src] to the floor.", "You unfasten the bolts securing \the [src] to the floor.")
+ user.visible_message("\The [user] unfastens the bolts securing \the [src] to the floor.", "You unfasten the bolts securing \the [src] to the floor.")
anchored = 0
return
@@ -245,7 +250,7 @@
for(var/datum/data/vending_product/R in product_records)
if(istype(W, R.product_path))
stock(R, user)
- del(W)
+ qdel(W)
else
..()
@@ -266,13 +271,13 @@
if(istype(cashmoney, /obj/item/weapon/spacecash/bundle))
// Bundles can just have money subtracted, and will work
- visible_message("[usr] inserts some cash into [src].")
+ visible_message("\The [usr] inserts some cash into \the [src].")
var/obj/item/weapon/spacecash/bundle/cashmoney_bundle = cashmoney
cashmoney_bundle.worth -= currently_vending.price
if(cashmoney_bundle.worth <= 0)
usr.drop_from_inventory(cashmoney_bundle)
- del(cashmoney_bundle)
+ qdel(cashmoney_bundle)
else
cashmoney_bundle.update_icon()
else
@@ -281,10 +286,10 @@
// This is really dirty, but there's no superclass for all bills, so we
// just assume that all spacecash that's not something else is a bill
- visible_message("[usr] inserts a bill into [src].")
+ visible_message("\The [usr] inserts a bill into \the [src].")
var/left = cashmoney.worth - currently_vending.price
usr.drop_from_inventory(cashmoney)
- del(cashmoney)
+ qdel(cashmoney)
if(left)
spawn_money(left, src.loc, user)
@@ -300,7 +305,7 @@
* successful, 0 if failed.
*/
/obj/machinery/vending/proc/pay_with_ewallet(var/obj/item/weapon/spacecash/ewallet/wallet)
- visible_message("[usr] swipes a card through [src].")
+ visible_message("\The [usr] swipes \the [wallet] through \the [src].")
if(currently_vending.price > wallet.worth)
src.status_message = "Insufficient funds on chargecard."
src.status_error = 1
@@ -316,8 +321,11 @@
* Takes payment for whatever is the currently_vending item. Returns 1 if
* successful, 0 if failed
*/
-/obj/machinery/vending/proc/pay_with_card(var/obj/item/weapon/card/id/I)
- visible_message("[usr] swipes a card through [src].")
+/obj/machinery/vending/proc/pay_with_card(var/obj/item/weapon/card/id/I, var/obj/item/ID_container)
+ if(I==ID_container || ID_container == null)
+ visible_message("\The [usr] swipes \the [I] through \the [src].")
+ else
+ visible_message("\The [usr] swipes \the [ID_container] through \the [src].")
var/datum/money_account/customer_account = get_account(I.associated_account_number)
if (!customer_account)
src.status_message = "Error: Unable to access account. Please contact technical support if problem persists."
@@ -470,17 +478,6 @@
if ((usr.contents.Find(src) || (in_range(src, usr) && istype(src.loc, /turf))))
if ((href_list["vend"]) && (src.vend_ready) && (!currently_vending))
-
- if(istype(usr,/mob/living/silicon))
- if(istype(usr,/mob/living/silicon/robot))
- var/mob/living/silicon/robot/R = usr
- if(!(R.module && istype(R.module,/obj/item/weapon/robot_module/butler) ))
- usr << "\red The vending machine refuses to interface with you, as you are not in its target demographic!"
- return
- else
- usr << "\red The vending machine refuses to interface with you, as you are not in its target demographic!"
- return
-
if((!allowed(usr)) && !emagged && scan_id) //For SECURE VENDING MACHINES YEAH
usr << "Access denied." //Unless emagged of course
flick(icon_deny,src)
@@ -495,6 +492,9 @@
if(R.price <= 0)
src.vend(R, usr)
+ else if(istype(usr,/mob/living/silicon)) //If the item is not free, provide feedback if a synth is trying to buy something.
+ usr << "Artificial unit recognized. Artificial units cannot complete this transaction. Purchase canceled."
+ return
else
src.currently_vending = R
if(!vendor_account || vendor_account.suspended)
@@ -529,13 +529,13 @@
return
if(coin.string_attached)
if(prob(50))
- user << "\blue You successfully pull the coin out before the [src] could swallow it."
+ user << "\blue You successfully pull the coin out before \the [src] could swallow it."
else
user << "\blue You weren't able to pull the coin out fast enough, the machine ate it, string and all."
- del(coin)
+ qdel(coin)
categories &= ~CAT_COIN
else
- del(coin)
+ qdel(coin)
categories &= ~CAT_COIN
R.amount--
@@ -558,7 +558,7 @@
/obj/machinery/vending/proc/stock(var/datum/data/vending_product/R, var/mob/user)
if(src.panel_open)
- user << "\blue You stock the [src] with \a [R.product_name]"
+ user << "\blue You stock \the [src] with \a [R.product_name]"
R.amount++
nanomanager.update_uis(src)
@@ -592,7 +592,7 @@
return
for(var/mob/O in hearers(src, null))
- O.show_message("[src] beeps, \"[message]\"",2)
+ O.show_message("\The [src] beeps, \"[message]\"",2)
return
/obj/machinery/vending/power_change()
@@ -788,7 +788,7 @@
icon_state = "med"
icon_deny = "med-deny"
product_ads = "Go save some lives!;The best stuff for your medbay.;Only the finest tools.;Natural chemicals!;This stuff saves lives.;Don't you want some?;Ping!"
- req_access = list(access_medical)
+ req_access = list(access_medical_equip)
products = list(/obj/item/weapon/reagent_containers/glass/bottle/antitoxin = 4,/obj/item/weapon/reagent_containers/glass/bottle/inaprovaline = 4,
/obj/item/weapon/reagent_containers/glass/bottle/stoxin = 4,/obj/item/weapon/reagent_containers/glass/bottle/toxin = 4,
/obj/item/weapon/reagent_containers/syringe/antiviral = 4,/obj/item/weapon/reagent_containers/syringe = 12,
@@ -938,7 +938,7 @@
desc = "Spare tool vending. What? Did you expect some witty description?"
icon_state = "engivend"
icon_deny = "engivend-deny"
- req_access = list(access_engine_equip) //Engineering Equipment access
+ req_access = list(access_engine_equip)
products = list(/obj/item/clothing/glasses/meson = 2,/obj/item/device/multitool = 4,/obj/item/weapon/airlock_electronics = 10,/obj/item/weapon/module/power_control = 10,/obj/item/weapon/airalarm_electronics = 10,/obj/item/weapon/cell/high = 10)
contraband = list(/obj/item/weapon/cell/potato = 3)
premium = list(/obj/item/weapon/storage/belt/utility = 3)
diff --git a/code/game/machinery/wall_frames.dm b/code/game/machinery/wall_frames.dm
new file mode 100644
index 00000000000..36e37cb9c6d
--- /dev/null
+++ b/code/game/machinery/wall_frames.dm
@@ -0,0 +1,83 @@
+/obj/item/frame
+ name = "frame"
+ desc = "Used for building machines."
+ icon = 'icons/obj/monitors.dmi'
+ icon_state = "fire_bitem"
+ flags = CONDUCT
+ var/build_machine_type
+ var/refund_amt = 2
+ var/refund_type = /obj/item/stack/sheet/metal
+
+/obj/item/frame/attackby(obj/item/weapon/W as obj, mob/user as mob)
+ if (istype(W, /obj/item/weapon/wrench))
+ new refund_type( get_turf(src.loc), refund_amt)
+ qdel(src)
+ return
+ ..()
+
+/obj/item/frame/proc/try_build(turf/on_wall)
+ if(!build_machine_type)
+ return
+
+ if (get_dist(on_wall,usr)>1)
+ return
+
+ var/ndir = get_dir(on_wall,usr)
+ if (!(ndir in cardinal))
+ return
+
+ var/turf/loc = get_turf(usr)
+ var/area/A = loc.loc
+ if (!istype(loc, /turf/simulated/floor))
+ usr << "\The [src] Alarm cannot be placed in this area."
+ return
+
+ if(gotwallitem(loc, ndir))
+ usr << ""
+ return
+
+ var/obj/machinery/M = new build_machine_type(loc, ndir, 1)
+ M.fingerprints = src.fingerprints
+ M.fingerprintshidden = src.fingerprintshidden
+ M.fingerprintslast = src.fingerprintslast
+ qdel(src)
+
+/obj/item/frame/fire_alarm
+ name = "fire alarm frame"
+ desc = "Used for building fire alarms."
+ build_machine_type = /obj/machinery/firealarm
+
+/obj/item/frame/air_alarm
+ name = "air alarm frame"
+ desc = "Used for building air alarms."
+ build_machine_type = /obj/machinery/alarm
+
+/obj/item/frame/light
+ name = "light fixture frame"
+ desc = "Used for building lights."
+ icon = 'icons/obj/lighting.dmi'
+ icon_state = "tube-construct-item"
+ build_machine_type = /obj/machinery/light_construct
+
+/obj/item/frame/light/small
+ name = "small light fixture frame"
+ icon_state = "bulb-construct-item"
+ refund_amt = 1
+ build_machine_type = /obj/machinery/light_construct/small
+
+/obj/item/frame/rust
+ name = "Fuel Compressor frame"
+ icon = 'icons/rust.dmi'
+ icon_state = "fuel_compressor0"
+ w_class = 4
+ refund_type = /obj/item/stack/sheet/plasteel
+ refund_amt = 12
+ build_machine_type = /obj/machinery/rust_fuel_compressor
+
+/obj/item/frame/rust/assembly
+ name = "Fuel Assembly Port frame"
+ icon_state = "port2"
+ build_machine_type = /obj/machinery/rust_fuel_assembly_port
diff --git a/code/game/machinery/washing_machine.dm b/code/game/machinery/washing_machine.dm
index ad433d12e25..8f2e6aaee25 100644
--- a/code/game/machinery/washing_machine.dm
+++ b/code/game/machinery/washing_machine.dm
@@ -50,129 +50,8 @@
for(var/obj/item/stack/sheet/hairlesshide/HH in contents)
var/obj/item/stack/sheet/wetleather/WL = new(src)
WL.amount = HH.amount
- del(HH)
-
-
- if(crayon)
- var/wash_color
- if(istype(crayon,/obj/item/toy/crayon))
- var/obj/item/toy/crayon/CR = crayon
- wash_color = CR.colourName
- else if(istype(crayon,/obj/item/weapon/stamp))
- var/obj/item/weapon/stamp/ST = crayon
- wash_color = ST.item_color
-
- if(wash_color)
- var/new_jumpsuit_icon_state = ""
- var/new_jumpsuit_item_state = ""
- var/new_jumpsuit_name = ""
- var/new_glove_icon_state = ""
- var/new_glove_item_state = ""
- var/new_glove_name = ""
- var/new_shoe_icon_state = ""
- var/new_shoe_name = ""
- var/new_sheet_icon_state = ""
- var/new_sheet_name = ""
- var/new_softcap_icon_state = ""
- var/new_softcap_name = ""
- var/new_desc = "The colors are a bit dodgy."
- for(var/T in typesof(/obj/item/clothing/under))
- var/obj/item/clothing/under/J = new T
- //world << "DEBUG: [color] == [J.color]"
- if(wash_color == J.item_color)
- new_jumpsuit_icon_state = J.icon_state
- new_jumpsuit_item_state = J.item_state
- new_jumpsuit_name = J.name
- del(J)
- //world << "DEBUG: YUP! [new_icon_state] and [new_item_state]"
- break
- del(J)
- for(var/T in typesof(/obj/item/clothing/gloves))
- var/obj/item/clothing/gloves/G = new T
- //world << "DEBUG: [color] == [J.color]"
- if(wash_color == G.item_color)
- new_glove_icon_state = G.icon_state
- new_glove_item_state = G.item_state
- new_glove_name = G.name
- del(G)
- //world << "DEBUG: YUP! [new_icon_state] and [new_item_state]"
- break
- del(G)
- for(var/T in typesof(/obj/item/clothing/shoes))
- var/obj/item/clothing/shoes/S = new T
- //world << "DEBUG: [color] == [J.color]"
- if(wash_color == S.item_color)
- new_shoe_icon_state = S.icon_state
- new_shoe_name = S.name
- del(S)
- //world << "DEBUG: YUP! [new_icon_state] and [new_item_state]"
- break
- del(S)
- for(var/T in typesof(/obj/item/weapon/bedsheet))
- var/obj/item/weapon/bedsheet/B = new T
- //world << "DEBUG: [color] == [J.color]"
- if(wash_color == B.item_color)
- new_sheet_icon_state = B.icon_state
- new_sheet_name = B.name
- del(B)
- //world << "DEBUG: YUP! [new_icon_state] and [new_item_state]"
- break
- del(B)
- for(var/T in typesof(/obj/item/clothing/head/soft))
- var/obj/item/clothing/head/soft/H = new T
- //world << "DEBUG: [color] == [J.color]"
- if(wash_color == H.item_color)
- new_softcap_icon_state = H.icon_state
- new_softcap_name = H.name
- del(H)
- //world << "DEBUG: YUP! [new_icon_state] and [new_item_state]"
- break
- del(H)
- if(new_jumpsuit_icon_state && new_jumpsuit_item_state && new_jumpsuit_name)
- for(var/obj/item/clothing/under/J in contents)
- //world << "DEBUG: YUP! FOUND IT!"
- J.item_state = new_jumpsuit_item_state
- J.icon_state = new_jumpsuit_icon_state
- J.item_color = wash_color
- J.name = new_jumpsuit_name
- J.desc = new_desc
- if(new_glove_icon_state && new_glove_item_state && new_glove_name)
- for(var/obj/item/clothing/gloves/G in contents)
- //world << "DEBUG: YUP! FOUND IT!"
- G.item_state = new_glove_item_state
- G.icon_state = new_glove_icon_state
- G.item_color = wash_color
- G.name = new_glove_name
- G.desc = new_desc
- if(new_shoe_icon_state && new_shoe_name)
- for(var/obj/item/clothing/shoes/S in contents)
- //world << "DEBUG: YUP! FOUND IT!"
- if (istype(S,/obj/item/clothing/shoes/orange))
- var/obj/item/clothing/shoes/orange/L = S
- if (L.chained)
- L.remove_cuffs()
- S.icon_state = new_shoe_icon_state
- S.item_color = wash_color
- S.name = new_shoe_name
- S.desc = new_desc
- if(new_sheet_icon_state && new_sheet_name)
- for(var/obj/item/weapon/bedsheet/B in contents)
- //world << "DEBUG: YUP! FOUND IT!"
- B.icon_state = new_sheet_icon_state
- B.item_color = wash_color
- B.name = new_sheet_name
- B.desc = new_desc
- if(new_softcap_icon_state && new_softcap_name)
- for(var/obj/item/clothing/head/soft/H in contents)
- //world << "DEBUG: YUP! FOUND IT!"
- H.icon_state = new_softcap_icon_state
- H.item_color = wash_color
- H.name = new_softcap_name
- H.desc = new_desc
- del(crayon)
- crayon = null
-
-
+ qdel(HH)
+
if( locate(/mob,contents) )
state = 7
gibs_ready = 1
@@ -197,7 +76,7 @@
/*if(istype(W,/obj/item/weapon/screwdriver))
panel = !panel
user << "\blue you [panel ? "open" : "close"] the [src]'s maintenance panel"*/
- if(istype(W,/obj/item/toy/crayon) ||istype(W,/obj/item/weapon/stamp))
+ if(istype(W,/obj/item/weapon/pen/crayon) || istype(W,/obj/item/weapon/stamp))
if( state in list( 1, 3, 6 ) )
if(!crayon)
user.drop_item()
@@ -212,7 +91,7 @@
var/obj/item/weapon/grab/G = W
if(ishuman(G.assailant) && iscorgi(G.affecting))
G.affecting.loc = src
- del(G)
+ qdel(G)
state = 3
else
..()
diff --git a/code/game/mecha/combat/gygax.dm b/code/game/mecha/combat/gygax.dm
index 7e8df940152..b47564e2b36 100644
--- a/code/game/mecha/combat/gygax.dm
+++ b/code/game/mecha/combat/gygax.dm
@@ -17,7 +17,7 @@
max_equip = 3
/obj/mecha/combat/gygax/dark
- desc = "A lightweight exosuit used by Nanotrasen Death Squads. A significantly upgraded Gygax security mech."
+ desc = "A lightweight exosuit used by NanoTrasen Heavy Asset Protection. A significantly upgraded Gygax security mech."
name = "Dark Gygax"
icon_state = "darkgygax"
initial_icon = "darkgygax"
diff --git a/code/game/mecha/combat/marauder.dm b/code/game/mecha/combat/marauder.dm
index d7e64c1ece9..bf23e579f3f 100644
--- a/code/game/mecha/combat/marauder.dm
+++ b/code/game/mecha/combat/marauder.dm
@@ -63,7 +63,7 @@
if(equipment.len)//Now to remove it and equip anew.
for(ME in equipment)
equipment -= ME
- del(ME)
+ qdel(ME)
ME = new /obj/item/mecha_parts/mecha_equipment/weapon/ballistic/scattershot(src)
ME.attach(src)
ME = new /obj/item/mecha_parts/mecha_equipment/weapon/ballistic/missile_rack/explosive(src)
@@ -76,6 +76,10 @@
ME.attach(src)
return
+/obj/mecha/combat/marauder/Destroy()
+ qdel(smoke_system)
+ ..()
+
/obj/mecha/combat/marauder/relaymove(mob/user,direction)
if(user != src.occupant) //While not "realistic", this piece is player friendly.
user.loc = get_turf(src)
diff --git a/code/game/mecha/equipment/mecha_equipment.dm b/code/game/mecha/equipment/mecha_equipment.dm
index 7ff5470f43a..607e8f445c9 100644
--- a/code/game/mecha/equipment/mecha_equipment.dm
+++ b/code/game/mecha/equipment/mecha_equipment.dm
@@ -8,7 +8,7 @@
force = 5
origin_tech = list(TECH_MATERIAL = 2)
construction_time = 100
- construction_cost = list("metal"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000)
var/equip_cooldown = 0
var/equip_ready = 1
var/energy_drain = 0
@@ -57,7 +57,7 @@
else
chassis.occupant << sound('sound/mecha/critdestr.ogg',volume=50)
spawn
- del src
+ qdel(src)
return
/obj/item/mecha_parts/mecha_equipment/proc/critfail()
@@ -96,11 +96,11 @@
if (ispath(required_type))
return istype(M, required_type)
-
+
for (var/path in required_type)
if (istype(M, path))
return 1
-
+
return 0
/obj/item/mecha_parts/mecha_equipment/proc/attach(obj/mecha/M as obj)
diff --git a/code/game/mecha/equipment/tools/medical_tools.dm b/code/game/mecha/equipment/tools/medical_tools.dm
index 0fa9008fa32..7ebeb641d89 100644
--- a/code/game/mecha/equipment/tools/medical_tools.dm
+++ b/code/game/mecha/equipment/tools/medical_tools.dm
@@ -5,8 +5,8 @@
icon_state = "sleeper_0"
origin_tech = list(TECH_DATA = 2, TECH_BIO = 3)
energy_drain = 20
- range = MELEE
- construction_cost = list("metal"=5000,"glass"=10000)
+ range = MELEE
+ construction_cost = list(DEFAULT_WALL_MATERIAL=5000,"glass"=10000)
equip_cooldown = 20
var/mob/living/carbon/occupant = null
var/datum/global_iterator/pr_mech_sleeper
@@ -20,6 +20,10 @@
pr_mech_sleeper.set_delay(equip_cooldown)
return
+ Destroy()
+ qdel(pr_mech_sleeper)
+ ..()
+
allow_drop()
return 0
@@ -389,7 +393,7 @@
equip_cooldown = 10
origin_tech = list(TECH_MATERIAL = 3, TECH_BIO = 4, TECH_MAGNET = 4, TECH_DATA = 3)
construction_time = 200
- construction_cost = list("metal"=3000,"glass"=2000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=3000,"glass"=2000)
required_type = /obj/mecha/medical
New()
@@ -438,7 +442,7 @@
var/turf/trg = get_turf(target)
var/obj/item/weapon/reagent_containers/syringe/S = syringes[1]
S.forceMove(get_turf(chassis))
- reagents.trans_to(S, min(S.volume, reagents.total_volume))
+ reagents.trans_to_obj(S, min(S.volume, reagents.total_volume))
syringes -= S
S.icon = 'icons/obj/chemical.dmi'
S.icon_state = "syringeproj"
@@ -457,7 +461,7 @@
if(M)
S.icon_state = initial(S.icon_state)
S.icon = initial(S.icon)
- S.reagents.trans_to(M, S.reagents.total_volume)
+ S.reagents.trans_to_mob(M, S.reagents.total_volume, CHEM_BLOOD)
M.take_organ_damage(2)
S.visible_message(" [M] was hit by the syringe!")
break
@@ -586,7 +590,7 @@
if(!(D.CanPass(S,src.loc)))
occupant_message("Unable to load syringe.")
return 0
- S.reagents.trans_to(src, S.reagents.total_volume)
+ S.reagents.trans_to_obj(src, S.reagents.total_volume)
S.forceMove(src)
syringes += S
occupant_message("Syringe loaded.")
diff --git a/code/game/mecha/equipment/tools/tools.dm b/code/game/mecha/equipment/tools/tools.dm
index 314dde34dd5..03fdb411b09 100644
--- a/code/game/mecha/equipment/tools/tools.dm
+++ b/code/game/mecha/equipment/tools/tools.dm
@@ -15,21 +15,22 @@
action(atom/target)
if(!action_checks(target)) return
if(!cargo_holder) return
-
+
//loading
if(istype(target,/obj))
var/obj/O = target
if(O.buckled_mob)
return
if(locate(/mob/living) in O)
+ occupant_message("You can't load living things into the cargo compartment.")
return
if(O.anchored)
- occupant_message("[target] is firmly secured.")
+ occupant_message("[target] is firmly secured.")
return
if(cargo_holder.cargo.len >= cargo_holder.cargo_capacity)
- occupant_message("Not enough room in cargo compartment.")
+ occupant_message("Not enough room in cargo compartment.")
return
-
+
occupant_message("You lift [target] and start to load it into cargo compartment.")
chassis.visible_message("[chassis] lifts [target] and starts to load it into cargo compartment.")
set_ready_state(0)
@@ -41,10 +42,10 @@
cargo_holder.cargo += O
O.loc = chassis
O.anchored = 0
- occupant_message("[target] succesfully loaded.")
+ occupant_message("[target] succesfully loaded.")
log_message("Loaded [O]. Cargo compartment capacity: [cargo_holder.cargo_capacity - cargo_holder.cargo.len]")
else
- occupant_message("You must hold still while handling objects.")
+ occupant_message("You must hold still while handling objects.")
O.anchored = initial(O.anchored)
//attacking
@@ -55,8 +56,8 @@
M.take_overall_damage(dam_force)
M.adjustOxyLoss(round(dam_force/2))
M.updatehealth()
- occupant_message("\red You squeeze [target] with [src.name]. Something cracks.")
- chassis.visible_message("\red [chassis] squeezes [target].")
+ occupant_message("You squeeze [target] with [src.name]. Something cracks.")
+ chassis.visible_message("[chassis] squeezes [target].")
else
step_away(M,chassis)
occupant_message("You push [target] out of the way.")
@@ -82,14 +83,19 @@
if(!target_obj.vars.Find("unacidable") || target_obj.unacidable) return
set_ready_state(0)
chassis.use_power(energy_drain)
- chassis.visible_message("[chassis] starts to drill [target]", "You hear the drill.")
- occupant_message("You start to drill [target]")
+ chassis.visible_message("[chassis] starts to drill [target]", "You hear the drill.")
+ occupant_message("You start to drill [target]")
var/T = chassis.loc
var/C = target.loc //why are these backwards? we may never know -Pete
if(do_after_cooldown(target))
if(T == chassis.loc && src == chassis.selected)
- if(istype(target, /turf/simulated/wall/r_wall))
- occupant_message("[target] is too durable to drill through.")
+ if(istype(target, /turf/simulated/wall))
+ var/turf/simulated/wall/W = target
+ if(W.reinf_material)
+ occupant_message("[target] is too durable to drill through.")
+ else
+ log_message("Drilled through [target]")
+ target.ex_act(2)
else if(istype(target, /turf/simulated/mineral))
for(var/turf/simulated/mineral/M in range(chassis,1))
if(get_dir(chassis,M)&chassis.dir)
@@ -122,7 +128,7 @@
desc = "This is an upgraded version of the drill that'll pierce the heavens! (Can be attached to: Combat and Engineering Exosuits)"
icon_state = "mecha_diamond_drill"
origin_tech = list(TECH_MATERIAL = 4, TECH_ENGINERING = 3)
- construction_cost = list("metal"=10000,"diamond"=6500)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"diamond"=6500)
equip_cooldown = 20
force = 15
@@ -133,14 +139,15 @@
if(target_obj.unacidable) return
set_ready_state(0)
chassis.use_power(energy_drain)
- chassis.visible_message("[chassis] starts to drill [target]", "You hear the drill.")
- occupant_message("You start to drill [target]")
+ chassis.visible_message("[chassis] starts to drill [target]", "You hear the drill.")
+ occupant_message("You start to drill [target]")
var/T = chassis.loc
var/C = target.loc //why are these backwards? we may never know -Pete
if(do_after_cooldown(target))
if(T == chassis.loc && src == chassis.selected)
- if(istype(target, /turf/simulated/wall/r_wall))
- if(do_after_cooldown(target))//To slow down how fast mechs can drill through the station
+ if(istype(target, /turf/simulated/wall))
+ var/turf/simulated/wall/W = target
+ if(!W.reinf_material || do_after_cooldown(target))//To slow down how fast mechs can drill through the station
log_message("Drilled through [target]")
target.ex_act(3)
else if(istype(target, /turf/simulated/mineral))
@@ -193,14 +200,14 @@
set_ready_state(0)
if(do_after_cooldown(target))
if( istype(target, /obj/structure/reagent_dispensers/watertank) && get_dist(chassis,target) <= 1)
- var/obj/o = target
- var/amount = o.reagents.trans_to(src, 200)
- occupant_message("\blue [amount] units transferred into internal tank.")
+ var/obj/o = target
+ var/amount = o.reagents.trans_to_obj(src, 200)
+ occupant_message("[amount] units transferred into internal tank.")
playsound(chassis, 'sound/effects/refill.ogg', 50, 1, -6)
return
if (src.reagents.total_volume < 1)
- occupant_message("\red \The [src] is empty.")
+ occupant_message("\The [src] is empty.")
return
playsound(chassis, 'sound/effects/extinguish.ogg', 75, 1, -3)
@@ -213,29 +220,24 @@
var/list/the_targets = list(T,T1,T2)
- for(var/a=0, a<5, a++)
- spawn(0)
- var/obj/effect/effect/water/W = new /obj/effect/effect/water( get_turf(chassis) )
- var/turf/my_target = pick(the_targets)
- var/datum/reagents/R = new/datum/reagents(5)
- if(!W) return
- W.reagents = R
- R.my_atom = W
- if(!W || !src) return
- src.reagents.trans_to(W,1)
- for(var/b=0, b<5, b++)
- step_towards(W,my_target)
- if(!W || !W.reagents) return
- W.reagents.reaction(get_turf(W))
- for(var/atom/atm in get_turf(W))
- if(!W)
- return
- if(!W.reagents)
- break
- W.reagents.reaction(atm)
- if(W.loc == my_target) break
- sleep(2)
- W.delete()
+ for(var/a = 1 to 5)
+ spawn(0)
+ var/obj/effect/effect/water/W = PoolOrNew(/obj/effect/effect/water, get_turf(chassis))
+ var/turf/my_target
+ if(a == 1)
+ my_target = T
+ else if(a == 2)
+ my_target = T1
+ else if(a == 3)
+ my_target = T2
+ else
+ my_target = pick(the_targets)
+ W.create_reagents(5)
+ if(!W || !src)
+ return
+ reagents.trans_to_obj(W, spray_amount)
+ W.set_color()
+ W.set_up(my_target)
return 1
get_equip_info()
@@ -254,7 +256,7 @@
energy_drain = 250
range = MELEE|RANGED
construction_time = 1200
- construction_cost = list("metal"=30000,"phoron"=25000,"silver"=20000,"gold"=20000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=30000,"phoron"=25000,"silver"=20000,"gold"=20000)
var/mode = 0 //0 - deconstruct, 1 - wall or floor, 2 - airlock.
var/disabled = 0 //malf
@@ -294,7 +296,7 @@
if(do_after_cooldown(target))
if(disabled) return
chassis.spark_system.start()
- del(target)
+ qdel(target)
playsound(target, 'sound/items/Deconstruct.ogg', 50, 1)
chassis.use_power(energy_drain)
if(1)
@@ -417,7 +419,7 @@
do_after_cooldown()
src = null
spawn(rand(150,300))
- del(P)
+ qdel(P)
return
/obj/item/mecha_parts/mecha_equipment/gravcatapult
@@ -440,7 +442,7 @@
last_fired = world.time
else
if (world.time % 3)
- occupant_message("[src] is not ready to fire again!")
+ occupant_message("[src] is not ready to fire again!")
return 0
switch(mode)
@@ -504,7 +506,7 @@
equip_cooldown = 10
energy_drain = 50
range = 0
- construction_cost = list("metal"=20000,"silver"=5000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"silver"=5000)
var/deflect_coeff = 1.15
var/damage_coeff = 0.8
@@ -536,8 +538,8 @@
user << "\red The [W] bounces off [chassis] armor."
chassis.log_append_to_last("Armor saved.")
else
- chassis.occupant_message("[user] hits [chassis] with [W].")
- user.visible_message("[user] hits [chassis] with [W].", "You hit [src] with [W].")
+ chassis.occupant_message("[user] hits [chassis] with [W].")
+ user.visible_message("[user] hits [chassis] with [W].", "You hit [src] with [W].")
chassis.take_damage(round(W.force*damage_coeff),W.damtype)
chassis.check_for_internal_damage(list(MECHA_INT_TEMP_CONTROL,MECHA_INT_TANK_BREACH,MECHA_INT_CONTROL_LOST))
set_ready_state(0)
@@ -554,7 +556,7 @@
equip_cooldown = 10
energy_drain = 50
range = 0
- construction_cost = list("metal"=20000,"gold"=5000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"gold"=5000)
var/deflect_coeff = 1.15
var/damage_coeff = 0.8
@@ -584,7 +586,7 @@
if(!action_checks(src))
return chassis.dynbulletdamage(Proj)
if(prob(chassis.deflect_chance*deflect_coeff))
- chassis.occupant_message("\blue The armor deflects incoming projectile.")
+ chassis.occupant_message("The armor deflects incoming projectile.")
chassis.visible_message("The [chassis.name] armor deflects the projectile")
chassis.log_append_to_last("Armor saved.")
else
@@ -600,7 +602,7 @@
if(!action_checks(A))
return chassis.dynhitby(A)
if(prob(chassis.deflect_chance*deflect_coeff) || istype(A, /mob/living) || istype(A, /obj/item/mecha_parts/mecha_tracking))
- chassis.occupant_message("\blue The [A] bounces off the armor.")
+ chassis.occupant_message("The [A] bounces off the armor.")
chassis.visible_message("The [A] bounces off the [chassis] armor")
chassis.log_append_to_last("Armor saved.")
if(istype(A, /mob/living))
@@ -625,7 +627,7 @@
equip_cooldown = 20
energy_drain = 100
range = 0
- construction_cost = list("metal"=10000,"gold"=1000,"silver"=2000,"glass"=5000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"gold"=1000,"silver"=2000,"glass"=5000)
var/health_boost = 2
var/datum/global_iterator/pr_repair_droid
var/icon/droid_overlay
@@ -637,6 +639,11 @@
pr_repair_droid.set_delay(equip_cooldown)
return
+ Destroy()
+ qdel(pr_repair_droid)
+ pr_repair_droid = null
+ ..()
+
attach(obj/mecha/M as obj)
..()
droid_overlay = new(src.icon, icon_state = "repair_droid")
@@ -715,7 +722,7 @@
equip_cooldown = 10
energy_drain = 0
range = 0
- construction_cost = list("metal"=10000,"gold"=2000,"silver"=3000,"glass"=2000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"gold"=2000,"silver"=3000,"glass"=2000)
var/datum/global_iterator/pr_energy_relay
var/coeff = 100
var/list/use_channels = list(EQUIP,ENVIRON,LIGHT)
@@ -726,6 +733,11 @@
pr_energy_relay.set_delay(equip_cooldown)
return
+ Destroy()
+ qdel(pr_energy_relay)
+ pr_energy_relay = null
+ ..()
+
detach()
pr_energy_relay.stop()
// chassis.proc_res["dynusepower"] = null
@@ -761,7 +773,7 @@
var/pow_chan
if(A)
for(var/c in use_channels)
- if(A.master && A.master.powered(c))
+ if(A.powered(c))
pow_chan = c
break
return pow_chan
@@ -808,13 +820,13 @@
if(A)
var/pow_chan
for(var/c in list(EQUIP,ENVIRON,LIGHT))
- if(A.master.powered(c))
+ if(A.powered(c))
pow_chan = c
break
if(pow_chan)
var/delta = min(12, ER.chassis.cell.maxcharge-cur_charge)
ER.chassis.give_power(delta)
- A.master.use_power(delta*ER.coeff, pow_chan)
+ A.use_power(delta*ER.coeff, pow_chan)
return
@@ -827,7 +839,7 @@
equip_cooldown = 10
energy_drain = 0
range = MELEE
- construction_cost = list("metal"=10000,"silver"=500,"glass"=1000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"silver"=500,"glass"=1000)
var/datum/global_iterator/pr_mech_generator
var/coeff = 100
var/obj/item/stack/sheet/fuel
@@ -841,6 +853,11 @@
init()
return
+ Destroy()
+ qdel(pr_mech_generator)
+ pr_mech_generator = null
+ ..()
+
proc/init()
fuel = new /obj/item/stack/sheet/mineral/phoron(src)
fuel.amount = 0
@@ -876,7 +893,7 @@
var/result = load_fuel(target)
var/message
if(isnull(result))
- message = "[fuel] traces in target minimal. [target] cannot be used as fuel."
+ message = "[fuel] traces in target minimal. [target] cannot be used as fuel."
else if(!result)
message = "Unit is full."
else
@@ -901,7 +918,7 @@
attackby(weapon,mob/user)
var/result = load_fuel(weapon)
if(isnull(result))
- user.visible_message("[user] tries to shove [weapon] into [src]. What a dumb-ass.","[fuel] traces minimal. [weapon] cannot be used as fuel.")
+ user.visible_message("[user] tries to shove [weapon] into [src]. What a dumb-ass.","[fuel] traces minimal. [weapon] cannot be used as fuel.")
else if(!result)
user << "Unit is full."
else
@@ -957,7 +974,7 @@
desc = "Generates power using uranium. Pollutes the environment."
icon_state = "tesla"
origin_tech = list(TECH_POWER = 3, TECH_ENGINERING = 3)
- construction_cost = list("metal"=10000,"silver"=500,"glass"=1000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"silver"=500,"glass"=1000)
max_fuel = 50000
fuel_per_cycle_idle = 10
fuel_per_cycle_active = 30
@@ -1020,25 +1037,25 @@
cargo_holder.cargo += O
O.loc = chassis
O.anchored = 0
- chassis.occupant_message("[target] succesfully loaded.")
+ chassis.occupant_message("[target] succesfully loaded.")
chassis.log_message("Loaded [O]. Cargo compartment capacity: [cargo_holder.cargo_capacity - cargo_holder.cargo.len]")
else
- chassis.occupant_message("You must hold still while handling objects.")
+ chassis.occupant_message("You must hold still while handling objects.")
O.anchored = initial(O.anchored)
else
- chassis.occupant_message("Not enough room in cargo compartment.")
+ chassis.occupant_message("Not enough room in cargo compartment.")
else
- chassis.occupant_message("[target] is firmly secured.")
+ chassis.occupant_message("[target] is firmly secured.")
else if(istype(target,/mob/living))
var/mob/living/M = target
if(M.stat>1) return
if(chassis.occupant.a_intent == I_HURT)
- chassis.occupant_message("\red You obliterate [target] with [src.name], leaving blood and guts everywhere.")
- chassis.visible_message("\red [chassis] destroys [target] in an unholy fury.")
+ chassis.occupant_message("You obliterate [target] with [src.name], leaving blood and guts everywhere.")
+ chassis.visible_message("[chassis] destroys [target] in an unholy fury.")
if(chassis.occupant.a_intent == I_DISARM)
- chassis.occupant_message("\red You tear [target]'s limbs off with [src.name].")
- chassis.visible_message("\red [chassis] rips [target]'s arms off.")
+ chassis.occupant_message("You tear [target]'s limbs off with [src.name].")
+ chassis.visible_message("[chassis] rips [target]'s arms off.")
else
step_away(M,chassis)
chassis.occupant_message("You smash into [target], sending them flying.")
@@ -1048,26 +1065,14 @@
do_after_cooldown()
return 1
-/obj/item/weapon/paintkit //Please don't use this for anything, it's a base type for custom mech paintjobs.
- name = "mecha customisation kit"
- desc = "A generic kit containing all the needed tools and parts to turn a mech into another mech."
- icon = 'icons/obj/custom_items.dmi'
- icon_state = "royce_kit"
-
- var/new_name = "mech" //What is the variant called?
- var/new_desc = "A mech." //How is the new mech described?
- var/new_icon = "ripley" //What base icon will the new mech use?
- var/removable = null //Can the kit be removed?
- var/list/allowed_types = list() //Types of mech that the kit will work on.
-
/obj/item/mecha_parts/mecha_equipment/tool/passenger
name = "passenger compartment"
desc = "A mountable passenger compartment for exo-suits. Rather cramped."
icon_state = "mecha_abooster_ccw"
origin_tech = list(TECH_ENGINERING = 1, TECH_BIO = 1)
energy_drain = 10
- range = MELEE
- construction_cost = list("metal"=5000,"glass"=5000)
+ range = MELEE
+ construction_cost = list(DEFAULT_WALL_MATERIAL=5000,"glass"=5000)
equip_cooldown = 20
var/mob/living/carbon/occupant = null
var/door_locked = 1
@@ -1079,7 +1084,7 @@
/obj/item/mecha_parts/mecha_equipment/tool/passenger/destroy()
for(var/atom/movable/AM in src)
AM.forceMove(get_turf(src))
- AM << "You tumble out of the destroyed [src.name]!"
+ AM << "You tumble out of the destroyed [src.name]!"
return ..()
/obj/item/mecha_parts/mecha_equipment/tool/passenger/Exit(atom/movable/O)
@@ -1087,7 +1092,7 @@
/obj/item/mecha_parts/mecha_equipment/tool/passenger/proc/move_inside(var/mob/user)
if (chassis)
- chassis.visible_message("\blue [user] starts to climb into [chassis].")
+ chassis.visible_message("[user] starts to climb into [chassis].")
if(do_after(user, 40, needhand=0))
if(!src.occupant)
@@ -1096,7 +1101,7 @@
log_message("[user] boarded.")
occupant_message("[user] boarded.")
else if(src.occupant != user)
- user << "\red [src.occupant] was faster. Try better next time, loser."
+ user << "[src.occupant] was faster. Try better next time, loser."
else
user << "You stop entering the exosuit."
@@ -1171,18 +1176,18 @@
return
if (!isturf(usr.loc))
- usr << "\red You can't reach the passenger compartment from here."
+ usr << "You can't reach the passenger compartment from here."
return
if(iscarbon(usr))
var/mob/living/carbon/C = usr
if(C.handcuffed)
- usr << "\red Kinda hard to climb in while handcuffed don't you think?"
+ usr << "Kinda hard to climb in while handcuffed don't you think?"
return
for(var/mob/living/carbon/slime/M in range(1,usr))
if(M.Victim == usr)
- usr << "\red You're too busy getting your life sucked out of you."
+ usr << "You're too busy getting your life sucked out of you."
return
//search for a valid passenger compartment
@@ -1202,10 +1207,10 @@
//didn't find anything
switch (feedback)
if (OCCUPIED)
- usr << "\red The passenger compartment is already occupied!"
+ usr << "The passenger compartment is already occupied!"
if (LOCKED)
- usr << "\red The passenger compartment hatch is locked!"
+ usr << "The passenger compartment hatch is locked!"
if (OCCUPIED|LOCKED)
- usr << "\red All of the passenger compartments are already occupied or locked!"
+ usr << "All of the passenger compartments are already occupied or locked!"
if (0)
- usr << "\red \The [src] doesn't have a passenger compartment."
+ usr << "\The [src] doesn't have a passenger compartment."
diff --git a/code/game/mecha/equipment/weapons/weapons.dm b/code/game/mecha/equipment/weapons/weapons.dm
index 9c83b09808f..f034f275507 100644
--- a/code/game/mecha/equipment/weapons/weapons.dm
+++ b/code/game/mecha/equipment/weapons/weapons.dm
@@ -113,7 +113,7 @@
A.bullet_act(src, def_zone)
src.life -= 10
if(life <= 0)
- del(src)
+ qdel(src)
return
/obj/item/mecha_parts/mecha_equipment/weapon/energy/taser
@@ -249,7 +249,7 @@
throw_impact(atom/hit_atom)
if(primed)
explosion(hit_atom, 0, 1, 2, 4)
- del(src)
+ qdel(src)
else
..()
return
@@ -274,7 +274,7 @@
/obj/item/mecha_parts/mecha_equipment/weapon/ballistic/missile_rack/flashbang/clusterbang//Because I am a heartless bastard -Sieve
name = "\improper SOP-6 grenade launcher"
projectile = /obj/item/weapon/grenade/flashbang/clusterbang
- construction_cost = list("metal"=20000,"gold"=6000,"uranium"=6000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"gold"=6000,"uranium"=6000)
/obj/item/mecha_parts/mecha_equipment/weapon/ballistic/missile_rack/flashbang/clusterbang/limited/get_equip_info()//Limited version of the clusterbang launcher that can't reload
return "* [chassis.selected==src?"":""][src.name][chassis.selected==src?"":""]\[[src.projectiles]\]"
diff --git a/code/game/mecha/mech_bay.dm b/code/game/mecha/mech_bay.dm
index d3c249b7473..615261bc5f9 100644
--- a/code/game/mecha/mech_bay.dm
+++ b/code/game/mecha/mech_bay.dm
@@ -139,6 +139,7 @@
anchored = 1
icon = 'icons/obj/computer.dmi'
icon_state = "recharge_comp"
+ light_color = "#a97faa"
circuit = "/obj/item/weapon/circuitboard/mech_bay_power_console"
var/autostart = 1
var/voltage = 45
@@ -214,4 +215,4 @@
// open the new ui window
ui.open()
// auto update every Master Controller tick
- ui.set_auto_update(1)
\ No newline at end of file
+ ui.set_auto_update(1)
diff --git a/code/game/mecha/mech_fabricator.dm b/code/game/mecha/mech_fabricator.dm
index 34365296ff0..a0f1b914d0b 100644
--- a/code/game/mecha/mech_fabricator.dm
+++ b/code/game/mecha/mech_fabricator.dm
@@ -17,7 +17,7 @@
var/time_coeff = 1.5 //can be upgraded with research
var/resource_coeff = 1.5 //can be upgraded with research
var/list/resources = list(
- "metal"=0,
+ DEFAULT_WALL_MATERIAL=0,
"glass"=0,
"gold"=0,
"silver"=0,
@@ -173,9 +173,9 @@
if(time_coeff!=diff)
time_coeff = diff
-/obj/machinery/mecha_part_fabricator/Del()
+/obj/machinery/mecha_part_fabricator/Destroy()
for(var/atom/A in src)
- del A
+ qdel(A)
..()
return
@@ -248,7 +248,7 @@
if(!istype(apart)) return 0
for(var/obj/O in part_set)
if(O.type == apart.type)
- del apart
+ qdel(apart)
return 0
part_set[++part_set.len] = apart
return 1
@@ -483,7 +483,7 @@
src.updateUsrDialog()
sleep(30) //only sleep if called by user
var/found = 0
- for(var/obj/machinery/computer/rdconsole/RDC in get_area(src))
+ for(var/obj/machinery/computer/rdconsole/RDC in get_area_all_atoms(get_area(src)))
if(!RDC.sync)
continue
found++
@@ -691,7 +691,7 @@
/obj/machinery/mecha_part_fabricator/proc/remove_material(var/mat_string, var/amount)
var/type
switch(mat_string)
- if("metal")
+ if(DEFAULT_WALL_MATERIAL)
type = /obj/item/stack/sheet/metal
if("glass")
type = /obj/item/stack/sheet/glass
@@ -721,7 +721,7 @@
res.Move(src.loc)
result = res.amount
else
- del res
+ qdel(res)
return result
@@ -744,9 +744,9 @@
M.icon_state = "box_1"
for(var/obj/I in component_parts)
I.loc = src.loc
- if(src.resources["metal"] >= 3750)
+ if(src.resources[DEFAULT_WALL_MATERIAL] >= 3750)
var/obj/item/stack/sheet/metal/G = new /obj/item/stack/sheet/metal(src.loc)
- G.amount = round(src.resources["metal"] / G.perunit)
+ G.amount = round(src.resources[DEFAULT_WALL_MATERIAL] / G.perunit)
if(src.resources["glass"] >= 3750)
var/obj/item/stack/sheet/glass/G = new /obj/item/stack/sheet/glass(src.loc)
G.amount = round(src.resources["glass"] / G.perunit)
@@ -765,7 +765,7 @@
if(src.resources["diamond"] >= 2000)
var/obj/item/stack/sheet/mineral/diamond/G = new /obj/item/stack/sheet/mineral/diamond(src.loc)
G.amount = round(src.resources["diamond"] / G.perunit)
- del(src)
+ qdel(src)
return 1
else
user << "\red You can't load the [src.name] while it's opened."
@@ -786,7 +786,7 @@
if(/obj/item/stack/sheet/mineral/phoron)
material = "phoron"
if(/obj/item/stack/sheet/metal)
- material = "metal"
+ material = DEFAULT_WALL_MATERIAL
if(/obj/item/stack/sheet/glass)
material = "glass"
if(/obj/item/stack/sheet/mineral/uranium)
diff --git a/code/game/mecha/mecha.dm b/code/game/mecha/mecha.dm
index c4a5d6b2693..8e4b83de73d 100644
--- a/code/game/mecha/mecha.dm
+++ b/code/game/mecha/mecha.dm
@@ -82,6 +82,7 @@
/obj/mecha/New()
..()
events = new
+
icon_state += "-open"
add_radio()
add_cabin()
@@ -98,11 +99,58 @@
mechas_list += src //global mech list
return
-/obj/mecha/Del()
+/obj/mecha/Destroy()
src.go_out()
+ for(var/mob/M in src) //Let's just be ultra sure
+ M.Move(loc)
+
+ if(loc)
+ loc.Exited(src)
+
+ if(prob(30))
+ explosion(get_turf(loc), 0, 0, 1, 3)
+
+ if(wreckage)
+ var/obj/effect/decal/mecha_wreckage/WR = new wreckage(loc)
+ for(var/obj/item/mecha_parts/mecha_equipment/E in equipment)
+ if(E.salvageable && prob(30))
+ WR.crowbar_salvage += E
+ E.forceMove(WR)
+ E.equip_ready = 1
+ else
+ E.forceMove(loc)
+ E.destroy()
+ if(cell)
+ WR.crowbar_salvage += cell
+ cell.forceMove(WR)
+ cell.charge = rand(0, cell.charge)
+ if(internal_tank)
+ WR.crowbar_salvage += internal_tank
+ internal_tank.forceMove(WR)
+ else
+ for(var/obj/item/mecha_parts/mecha_equipment/E in equipment)
+ E.detach(loc)
+ E.destroy()
+ if(cell)
+ qdel(cell)
+ if(internal_tank)
+ qdel(internal_tank)
+ equipment.Cut()
+ cell = null
+ internal_tank = null
+
+ qdel(pr_int_temp_processor)
+ qdel(pr_inertial_movement)
+ qdel(pr_give_air)
+ qdel(pr_internal_damage)
+ qdel(spark_system)
+ pr_int_temp_processor = null
+ pr_give_air = null
+ pr_internal_damage = null
+ spark_system = null
+
mechas_list -= src //global mech list
..()
- return
////////////////////////
////// Helpers /////////
@@ -410,6 +458,8 @@
/obj/mecha/proc/setInternalDamage(int_dam_flag)
+ if(!pr_internal_damage) return
+
internal_damage |= int_dam_flag
pr_internal_damage.start()
log_append_to_last("Internal damage of type [int_dam_flag].",1)
@@ -447,12 +497,17 @@
/obj/mecha/proc/dynabsorbdamage(damage,damage_type)
return damage*(listgetindex(damage_absorption,damage_type) || 1)
+/obj/mecha/airlock_crush(var/crush_damage)
+ ..()
+ take_damage(crush_damage)
+ check_for_internal_damage(list(MECHA_INT_TEMP_CONTROL,MECHA_INT_TANK_BREACH,MECHA_INT_CONTROL_LOST))
+ return 1
/obj/mecha/proc/update_health()
if(src.health > 0)
src.spark_system.start()
else
- src.destroy()
+ qdel(src)
return
/obj/mecha/attack_hand(mob/user as mob)
@@ -555,51 +610,6 @@
Proj.on_hit(src)
return
-/obj/mecha/proc/destroy()
- spawn()
- go_out()
- var/turf/T = get_turf(src)
- tag = "\ref[src]" //better safe then sorry
- if(loc)
- loc.Exited(src)
- loc = null
- if(T)
- if(istype(src, /obj/mecha/working/ripley/))
- var/obj/mecha/working/ripley/R = src
- if(R.cargo)
- for(var/obj/O in R.cargo) //Dump contents of stored cargo
- O.loc = T
- R.cargo -= O
- T.Entered(O)
-
- if(prob(30))
- explosion(T, 0, 0, 1, 3)
- spawn(0)
- if(wreckage)
- var/obj/effect/decal/mecha_wreckage/WR = new wreckage(T)
- for(var/obj/item/mecha_parts/mecha_equipment/E in equipment)
- if(E.salvageable && prob(30))
- WR.crowbar_salvage += E
- E.forceMove(WR)
- E.equip_ready = 1
- else
- E.forceMove(T)
- E.destroy()
- if(cell)
- WR.crowbar_salvage += cell
- cell.forceMove(WR)
- cell.charge = rand(0, cell.charge)
- if(internal_tank)
- WR.crowbar_salvage += internal_tank
- internal_tank.forceMove(WR)
- else
- for(var/obj/item/mecha_parts/mecha_equipment/E in equipment)
- E.forceMove(T)
- E.destroy()
- spawn(0)
- del(src)
- return
-
/obj/mecha/ex_act(severity)
src.log_message("Affected by explosion of severity: [severity].",1)
if(prob(src.deflect_chance))
@@ -607,16 +617,16 @@
src.log_append_to_last("Armor saved, changing severity to [severity].")
switch(severity)
if(1.0)
- src.destroy()
+ qdel(src)
if(2.0)
if (prob(30))
- src.destroy()
+ qdel(src)
else
src.take_damage(initial(src.health)/2)
src.check_for_internal_damage(list(MECHA_INT_FIRE,MECHA_INT_TEMP_CONTROL,MECHA_INT_TANK_BREACH,MECHA_INT_CONTROL_LOST,MECHA_INT_SHORT_CIRCUIT),1)
if(3.0)
if (prob(5))
- src.destroy()
+ qdel(src)
else
src.take_damage(initial(src.health)/5)
src.check_for_internal_damage(list(MECHA_INT_FIRE,MECHA_INT_TEMP_CONTROL,MECHA_INT_TANK_BREACH,MECHA_INT_CONTROL_LOST,MECHA_INT_SHORT_CIRCUIT),1)
@@ -804,34 +814,6 @@
user.visible_message("[user] attaches [W] to [src].", "You attach [W] to [src]")
return
- else if(istype(W, /obj/item/weapon/paintkit))
-
- if(occupant)
- user << "You can't customize a mech while someone is piloting it - that would be unsafe!"
- return
-
- var/obj/item/weapon/paintkit/P = W
- var/found = null
-
- for(var/type in P.allowed_types)
- if(type==src.initial_icon)
- found = 1
- break
-
- if(!found)
- user << "That kit isn't meant for use on this class of exosuit."
- return
-
- user.visible_message("[user] opens [P] and spends some quality time customising [src].")
-
- src.name = P.new_name
- src.desc = P.new_desc
- src.initial_icon = P.new_icon
- src.reset_icon()
-
- user.drop_item()
- del(P)
-
else
call((proc_res["dynattackby"]||src), "dynattackby")(W,user)
/*
@@ -994,8 +976,8 @@
set popup_menu = 0
if(usr!=occupant) return
lights = !lights
- if(lights) SetLuminosity(luminosity + lights_power)
- else SetLuminosity(luminosity - lights_power)
+ if(lights) set_light(light_range + lights_power)
+ else set_light(light_range - lights_power)
src.occupant_message("Toggled lights [lights?"on":"off"].")
log_message("Toggled lights [lights?"on":"off"].")
return
@@ -1731,7 +1713,7 @@
AI.bruteloss = O.getBruteLoss()
AI.toxloss = O.toxloss
AI.updatehealth()
- del(O)
+ qdel(O)
if (!AI.stat)
AI.icon_state = "ai"
else
@@ -1839,7 +1821,7 @@
if(t_air)
t_air.merge(removed)
else //just delete the cabin gas, we're in space or some shit
- del(removed)
+ qdel(removed)
else
return stop()
return
@@ -1882,7 +1864,7 @@
if(mecha.loc && hascall(mecha.loc,"assume_air"))
mecha.loc.assume_air(leaked_gas)
else
- del(leaked_gas)
+ qdel(leaked_gas)
if(mecha.hasInternalDamage(MECHA_INT_SHORT_CIRCUIT))
if(mecha.get_charge())
mecha.spark_system.start()
diff --git a/code/game/mecha/mecha_construction_paths.dm b/code/game/mecha/mecha_construction_paths.dm
index 233415cba80..167b9f63d0a 100644
--- a/code/game/mecha/mecha_construction_paths.dm
+++ b/code/game/mecha/mecha_construction_paths.dm
@@ -78,7 +78,7 @@
custom_action(step, atom/used_atom, mob/user)
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -92,7 +92,7 @@
const_holder.density = 1
const_holder.overlays.len = 0
spawn()
- del src
+ qdel(src)
return
@@ -194,7 +194,7 @@
if(10)
if(diff==FORWARD)
user.visible_message("[user] installs the central control module into [holder].", "You install the central computer mainboard into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "ripley5"
else
user.visible_message("[user] disconnects the wiring of [holder].", "You disconnect the wiring of [holder].")
@@ -210,7 +210,7 @@
if(8)
if(diff==FORWARD)
user.visible_message("[user] installs the peripherals control module into [holder].", "You install the peripherals control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "ripley7"
else
user.visible_message("[user] unfastens the mainboard.", "You unfasten the mainboard.")
@@ -289,7 +289,7 @@
custom_action(step, atom/used_atom, mob/user)
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -302,7 +302,7 @@
const_holder.icon_state = "gygax0"
const_holder.density = 1
spawn()
- del src
+ qdel(src)
return
@@ -428,7 +428,7 @@
if(16)
if(diff==FORWARD)
user.visible_message("[user] installs the central control module into [holder].", "You install the central computer mainboard into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax5"
else
user.visible_message("[user] disconnects the wiring of [holder].", "You disconnect the wiring of [holder].")
@@ -444,7 +444,7 @@
if(14)
if(diff==FORWARD)
user.visible_message("[user] installs the peripherals control module into [holder].", "You install the peripherals control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax7"
else
user.visible_message("[user] unfastens the mainboard.", "You unfasten the mainboard.")
@@ -460,7 +460,7 @@
if(12)
if(diff==FORWARD)
user.visible_message("[user] installs the weapon control module into [holder].", "You install the weapon control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax9"
else
user.visible_message("[user] unfastens the peripherals control module.", "You unfasten the peripherals control module.")
@@ -476,7 +476,7 @@
if(10)
if(diff==FORWARD)
user.visible_message("[user] installs advanced scanner module to [holder].", "You install advanced scanner module to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax11"
else
user.visible_message("[user] unfastens the weapon control module.", "You unfasten the weapon control module.")
@@ -492,7 +492,7 @@
if(8)
if(diff==FORWARD)
user.visible_message("[user] installs advanced capacitor to [holder].", "You install advanced capacitor to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax13"
else
user.visible_message("[user] unfastens the advanced scanner module.", "You unfasten the advanced scanner module.")
@@ -531,7 +531,7 @@
if(3)
if(diff==FORWARD)
user.visible_message("[user] installs Gygax Armour Plates to [holder].", "You install Gygax Armour Plates to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "gygax18"
else
user.visible_message("[user] cuts internal armor layer from [holder].", "You cut the internal armor layer from [holder].")
@@ -570,7 +570,7 @@
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
user.drop_item()
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -583,7 +583,7 @@
const_holder.icon_state = "fireripley0"
const_holder.density = 1
spawn()
- del src
+ qdel(src)
return
@@ -690,7 +690,7 @@
if(11)
if(diff==FORWARD)
user.visible_message("[user] installs the central control module into [holder].", "You install the central computer mainboard into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "fireripley5"
else
user.visible_message("[user] disconnects the wiring of [holder].", "You disconnect the wiring of [holder].")
@@ -706,7 +706,7 @@
if(9)
if(diff==FORWARD)
user.visible_message("[user] installs the peripherals control module into [holder].", "You install the peripherals control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "fireripley7"
else
user.visible_message("[user] unfastens the mainboard.", "You unfasten the mainboard.")
@@ -793,7 +793,7 @@
custom_action(step, atom/used_atom, mob/user)
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -806,7 +806,7 @@
const_holder.icon_state = "durand0"
const_holder.density = 1
spawn()
- del src
+ qdel(src)
return
/datum/construction/reversible/mecha/durand
@@ -932,7 +932,7 @@
if(16)
if(diff==FORWARD)
user.visible_message("[user] installs the central control module into [holder].", "You install the central computer mainboard into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand5"
else
user.visible_message("[user] disconnects the wiring of [holder].", "You disconnect the wiring of [holder].")
@@ -948,7 +948,7 @@
if(14)
if(diff==FORWARD)
user.visible_message("[user] installs the peripherals control module into [holder].", "You install the peripherals control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand7"
else
user.visible_message("[user] unfastens the mainboard.", "You unfasten the mainboard.")
@@ -964,7 +964,7 @@
if(12)
if(diff==FORWARD)
user.visible_message("[user] installs the weapon control module into [holder].", "You install the weapon control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand9"
else
user.visible_message("[user] unfastens the peripherals control module.", "You unfasten the peripherals control module.")
@@ -980,7 +980,7 @@
if(10)
if(diff==FORWARD)
user.visible_message("[user] installs advanced scanner module to [holder].", "You install advanced scanner module to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand11"
else
user.visible_message("[user] unfastens the weapon control module.", "You unfasten the weapon control module.")
@@ -996,7 +996,7 @@
if(8)
if(diff==FORWARD)
user.visible_message("[user] installs advanced capacitor to [holder].", "You install advanced capacitor to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand13"
else
user.visible_message("[user] unfastens the advanced scanner module.", "You unfasten the advanced scanner module.")
@@ -1035,7 +1035,7 @@
if(3)
if(diff==FORWARD)
user.visible_message("[user] installs Durand Armour Plates to [holder].", "You install Durand Armour Plates to [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "durand18"
else
user.visible_message("[user] cuts internal armor layer from [holder].", "You cut the internal armor layer from [holder].")
@@ -1075,7 +1075,7 @@
custom_action(step, atom/used_atom, mob/user)
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -1096,7 +1096,7 @@
custom_action(step, atom/used_atom, mob/user)
user.visible_message("[user] has connected [used_atom] to [holder].", "You connect [used_atom] to [holder]")
holder.overlays += used_atom.icon_state+"+o"
- del used_atom
+ qdel(used_atom)
return 1
action(atom/used_atom,mob/user as mob)
@@ -1109,7 +1109,7 @@
const_holder.icon_state = "odysseus0"
const_holder.density = 1
spawn()
- del src
+ qdel(src)
return
@@ -1211,7 +1211,7 @@
if(10)
if(diff==FORWARD)
user.visible_message("[user] installs the central control module into [holder].", "You install the central computer mainboard into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "odysseus5"
else
user.visible_message("[user] disconnects the wiring of [holder].", "You disconnect the wiring of [holder].")
@@ -1227,7 +1227,7 @@
if(8)
if(diff==FORWARD)
user.visible_message("[user] installs the peripherals control module into [holder].", "You install the peripherals control module into [holder].")
- del used_atom
+ qdel(used_atom)
holder.icon_state = "odysseus7"
else
user.visible_message("[user] unfastens the mainboard.", "You unfasten the mainboard.")
diff --git a/code/game/mecha/mecha_control_console.dm b/code/game/mecha/mecha_control_console.dm
index e215bd1c28b..3a3e48d1547 100644
--- a/code/game/mecha/mecha_control_console.dm
+++ b/code/game/mecha/mecha_control_console.dm
@@ -2,6 +2,7 @@
name = "Exosuit Control"
icon = 'icons/obj/computer.dmi'
icon_state = "mecha"
+ light_color = "#a97faa"
req_access = list(access_robotics)
circuit = "/obj/item/weapon/circuitboard/mecha_control"
var/list/located = list()
@@ -69,7 +70,7 @@
icon_state = "motion2"
origin_tech = list(TECH_DATA = 2, TECH_MAGNET = 2)
construction_time = 50
- construction_cost = list("metal"=500)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=500)
proc/get_mecha_info()
if(!in_mecha())
@@ -90,11 +91,11 @@
return answer
emp_act()
- del src
+ qdel(src)
return
ex_act()
- del src
+ qdel(src)
return
proc/in_mecha()
@@ -106,7 +107,7 @@
var/obj/mecha/M = in_mecha()
if(M)
M.emp_act(2)
- del(src)
+ qdel(src)
proc/get_mecha_log()
if(!src.in_mecha())
diff --git a/code/game/mecha/mecha_parts.dm b/code/game/mecha/mecha_parts.dm
index 72731005491..4e19037ccec 100644
--- a/code/game/mecha/mecha_parts.dm
+++ b/code/game/mecha/mecha_parts.dm
@@ -12,14 +12,14 @@
flags = CONDUCT
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2)
var/construction_time = 100
- var/list/construction_cost = list("metal"=20000,"glass"=5000)
+ var/list/construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"glass"=5000)
/obj/item/mecha_parts/chassis
name="Mecha Chassis"
icon_state = "backbone"
var/datum/construction/construct
- construction_cost = list("metal"=20000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000)
flags = CONDUCT
attackby(obj/item/W as obj, mob/user as mob)
@@ -45,7 +45,7 @@
icon_state = "ripley_harness"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_BIO = 2, TECH_ENGINERING = 2)
construction_time = 200
- construction_cost = list("metal"=40000,"glass"=15000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=40000,"glass"=15000)
/obj/item/mecha_parts/part/ripley_left_arm
name="Ripley Left Arm"
@@ -53,7 +53,7 @@
icon_state = "ripley_l_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 150
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
/obj/item/mecha_parts/part/ripley_right_arm
name="Ripley Right Arm"
@@ -61,7 +61,7 @@
icon_state = "ripley_r_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 150
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
/obj/item/mecha_parts/part/ripley_left_leg
name="Ripley Left Leg"
@@ -69,7 +69,7 @@
icon_state = "ripley_l_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 150
- construction_cost = list("metal"=30000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=30000)
/obj/item/mecha_parts/part/ripley_right_leg
name="Ripley Right Leg"
@@ -77,13 +77,13 @@
icon_state = "ripley_r_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 150
- construction_cost = list("metal"=30000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=30000)
///////// Gygax
/obj/item/mecha_parts/chassis/gygax
name = "Gygax Chassis"
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
New()
..()
@@ -95,7 +95,7 @@
icon_state = "gygax_harness"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_BIO = 3, TECH_ENGINERING = 3)
construction_time = 300
- construction_cost = list("metal"=50000,"glass"=20000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=50000,"glass"=20000)
/obj/item/mecha_parts/part/gygax_head
name="Gygax Head"
@@ -103,7 +103,7 @@
icon_state = "gygax_head"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_MAGNET = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=20000,"glass"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"glass"=10000)
/obj/item/mecha_parts/part/gygax_left_arm
name="Gygax Left Arm"
@@ -111,7 +111,7 @@
icon_state = "gygax_l_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=30000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=30000)
/obj/item/mecha_parts/part/gygax_right_arm
name="Gygax Right Arm"
@@ -119,35 +119,35 @@
icon_state = "gygax_r_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=30000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=30000)
/obj/item/mecha_parts/part/gygax_left_leg
name="Gygax Left Leg"
icon_state = "gygax_l_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=35000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000)
/obj/item/mecha_parts/part/gygax_right_leg
name="Gygax Right Leg"
icon_state = "gygax_r_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=35000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000)
/obj/item/mecha_parts/part/gygax_armour
name="Gygax Armour Plates"
icon_state = "gygax_armour"
origin_tech = list(TECH_MATERIAL = 6, TECH_COMBAT = 4, TECH_ENGINERING = 5)
construction_time = 600
- construction_cost = list("metal"=50000,"diamond"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=50000,"diamond"=10000)
//////////// Durand
/obj/item/mecha_parts/chassis/durand
name = "Durand Chassis"
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
New()
..()
@@ -158,49 +158,49 @@
icon_state = "durand_harness"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_BIO = 3, TECH_ENGINERING = 3)
construction_time = 300
- construction_cost = list("metal"=55000,"glass"=20000,"silver"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=55000,"glass"=20000,"silver"=10000)
/obj/item/mecha_parts/part/durand_head
name="Durand Head"
icon_state = "durand_head"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_MAGNET = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=25000,"glass"=10000,"silver"=3000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000,"glass"=10000,"silver"=3000)
/obj/item/mecha_parts/part/durand_left_arm
name="Durand Left Arm"
icon_state = "durand_l_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=35000,"silver"=3000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000,"silver"=3000)
/obj/item/mecha_parts/part/durand_right_arm
name="Durand Right Arm"
icon_state = "durand_r_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=35000,"silver"=3000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000,"silver"=3000)
/obj/item/mecha_parts/part/durand_left_leg
name="Durand Left Leg"
icon_state = "durand_l_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=40000,"silver"=3000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=40000,"silver"=3000)
/obj/item/mecha_parts/part/durand_right_leg
name="Durand Right Leg"
icon_state = "durand_r_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=40000,"silver"=3000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=40000,"silver"=3000)
/obj/item/mecha_parts/part/durand_armour
name="Durand Armour Plates"
icon_state = "durand_armour"
origin_tech = list(TECH_MATERIAL = 5, TECH_COMBAT = 4, TECH_ENGINERING = 5)
construction_time = 600
- construction_cost = list("metal"=50000,"uranium"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=50000,"uranium"=10000)
@@ -247,44 +247,44 @@
/obj/item/mecha_parts/part/phazon_torso
name="Phazon Torso"
icon_state = "phazon_harness"
- construction_time = 300
- construction_cost = list("metal"=35000,"glass"=10000,"phoron"=20000)
- origin_tech = list(TECH_DATA = 5, TECH_MATERIAL = 7, TECH_BLUESPACE = 6, TECH_POWER = 6)
+ construction_time = 300
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000,"glass"=10000,"phoron"=20000)
+ origin_tech = list(TECH_DATA = 5, TECH_MATERIAL = 7, TECH_BLUESPACE = 6, TECH_POWER = 6)
/obj/item/mecha_parts/part/phazon_head
name="Phazon Head"
icon_state = "phazon_head"
- construction_time = 200
- construction_cost = list("metal"=15000,"glass"=5000,"phoron"=10000)
- origin_tech = list(TECH_DATA = 4, TECH_MATERIAL = 5, TECH_MAGNET = 6)
+ construction_time = 200
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000,"glass"=5000,"phoron"=10000)
+ origin_tech = list(TECH_DATA = 4, TECH_MATERIAL = 5, TECH_MAGNET = 6)
/obj/item/mecha_parts/part/phazon_left_arm
name="Phazon Left Arm"
icon_state = "phazon_l_arm"
- construction_time = 200
- construction_cost = list("metal"=20000,"phoron"=10000)
- origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 2, TECH_MAGNET = 2)
+ construction_time = 200
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"phoron"=10000)
+ origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 2, TECH_MAGNET = 2)
/obj/item/mecha_parts/part/phazon_right_arm
name="Phazon Right Arm"
icon_state = "phazon_r_arm"
- construction_time = 200
- construction_cost = list("metal"=20000,"phoron"=10000)
- origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 2, TECH_MAGNET = 2)
+ construction_time = 200
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"phoron"=10000)
+ origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 2, TECH_MAGNET = 2)
/obj/item/mecha_parts/part/phazon_left_leg
name="Phazon Left Leg"
icon_state = "phazon_l_leg"
- construction_time = 200
- construction_cost = list("metal"=20000,"phoron"=10000)
- origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 3, TECH_MAGNET = 3)
+ construction_time = 200
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"phoron"=10000)
+ origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 3, TECH_MAGNET = 3)
/obj/item/mecha_parts/part/phazon_right_leg
name="Phazon Right Leg"
icon_state = "phazon_r_leg"
- construction_time = 200
- construction_cost = list("metal"=20000,"phoron"=10000)
- origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 3, TECH_MAGNET = 3)
+ construction_time = 200
+ construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"phoron"=10000)
+ origin_tech = list(TECH_MATERIAL = 5, TECH_BLUESPACE = 3, TECH_MAGNET = 3)
///////// Odysseus
@@ -299,9 +299,9 @@
/obj/item/mecha_parts/part/odysseus_head
name="Odysseus Head"
icon_state = "odysseus_head"
- construction_time = 100
- construction_cost = list("metal"=2000,"glass"=10000)
- origin_tech = list(TECH_DATA = 3, TECH_MATERIAL = 2)
+ construction_time = 100
+ construction_cost = list(DEFAULT_WALL_MATERIAL=2000,"glass"=10000)
+ origin_tech = list(TECH_DATA = 3, TECH_MATERIAL = 2)
/obj/item/mecha_parts/part/odysseus_torso
name="Odysseus Torso"
@@ -309,7 +309,7 @@
icon_state = "odysseus_torso"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_BIO = 2, TECH_ENGINERING = 2)
construction_time = 180
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
/obj/item/mecha_parts/part/odysseus_left_arm
name="Odysseus Left Arm"
@@ -317,7 +317,7 @@
icon_state = "odysseus_l_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 120
- construction_cost = list("metal"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000)
/obj/item/mecha_parts/part/odysseus_right_arm
name="Odysseus Right Arm"
@@ -325,7 +325,7 @@
icon_state = "odysseus_r_arm"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 120
- construction_cost = list("metal"=10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000)
/obj/item/mecha_parts/part/odysseus_left_leg
name="Odysseus Left Leg"
@@ -333,7 +333,7 @@
icon_state = "odysseus_l_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 130
- construction_cost = list("metal"=15000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000)
/obj/item/mecha_parts/part/odysseus_right_leg
name="Odysseus Right Leg"
@@ -341,11 +341,11 @@
icon_state = "odysseus_r_leg"
origin_tech = list(TECH_DATA = 2, TECH_MATERIAL = 2, TECH_ENGINERING = 2)
construction_time = 130
- construction_cost = list("metal"=15000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000)
/*/obj/item/mecha_parts/part/odysseus_armour
name="Odysseus Carapace"
icon_state = "odysseus_armour"
origin_tech = list(TECH_MATERIAL = 3, TECH_ENGINERING = 3)
construction_time = 200
- construction_cost = list("metal"=15000)*/
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000)*/
diff --git a/code/game/mecha/mecha_wreckage.dm b/code/game/mecha/mecha_wreckage.dm
index 96b410959b2..8bbeb03fd71 100644
--- a/code/game/mecha/mecha_wreckage.dm
+++ b/code/game/mecha/mecha_wreckage.dm
@@ -23,7 +23,7 @@
/obj/effect/decal/mecha_wreckage/ex_act(severity)
if(severity < 2)
spawn
- del src
+ qdel(src)
return
/obj/effect/decal/mecha_wreckage/bullet_act(var/obj/item/projectile/Proj)
diff --git a/code/game/mecha/working/ripley.dm b/code/game/mecha/working/ripley.dm
index 5beb3c7244f..c51a34adefb 100644
--- a/code/game/mecha/working/ripley.dm
+++ b/code/game/mecha/working/ripley.dm
@@ -9,6 +9,16 @@
wreckage = /obj/effect/decal/mecha_wreckage/ripley
cargo_capacity = 10
+/obj/mecha/working/ripley/Destroy()
+ for(var/atom/movable/A in src.cargo)
+ A.loc = loc
+ var/turf/T = loc
+ if(istype(T))
+ T.Entered(A)
+ step_rand(A)
+ cargo.Cut()
+ ..()
+
/obj/mecha/working/ripley/firefighter
desc = "Standart APLU chassis was refitted with additional thermal protection and cistern."
name = "APLU \"Firefighter\""
@@ -54,6 +64,6 @@
var/obj/item/mecha_parts/mecha_equipment/tool/hydraulic_clamp/HC = new /obj/item/mecha_parts/mecha_equipment/tool/hydraulic_clamp
HC.attach(src)
for(var/obj/item/mecha_parts/mecha_tracking/B in src.contents)//Deletes the beacon so it can't be found easily
- del (B)
+ qdel (B)
diff --git a/code/game/mecha/working/working.dm b/code/game/mecha/working/working.dm
index 1fa6d4f5ac1..d9e876688f1 100644
--- a/code/game/mecha/working/working.dm
+++ b/code/game/mecha/working/working.dm
@@ -10,7 +10,7 @@
new /obj/item/mecha_parts/mecha_tracking(src)
return
-/obj/mecha/working/Del()
+/obj/mecha/working/Destroy()
for(var/mob/M in src)
if(M==src.occupant)
continue
diff --git a/code/game/objects/buckling.dm b/code/game/objects/buckling.dm
index d64857d0042..6b79db8f5b4 100644
--- a/code/game/objects/buckling.dm
+++ b/code/game/objects/buckling.dm
@@ -15,10 +15,16 @@
if(can_buckle && istype(M))
user_buckle_mob(M, user)
+//Cleanup
/obj/Del()
unbuckle_mob()
return ..()
+/obj/Destroy()
+ unbuckle_mob()
+ return ..()
+
+
/obj/proc/buckle_mob(mob/living/M)
if(!can_buckle || !istype(M) || (M.loc != loc) || M.buckled || M.pinned.len || (buckle_require_restraints && !M.restrained()))
return 0
@@ -84,3 +90,4 @@
"You hear metal clanking.")
add_fingerprint(user)
return M
+
diff --git a/code/game/objects/effects/aliens.dm b/code/game/objects/effects/aliens.dm
index 840d779510f..6882f9affa5 100644
--- a/code/game/objects/effects/aliens.dm
+++ b/code/game/objects/effects/aliens.dm
@@ -46,7 +46,7 @@
var/turf/T = get_turf(src)
T.thermal_conductivity = WALL_HEAT_TRANSFER_COEFFICIENT
-/obj/effect/alien/resin/Del()
+/obj/effect/alien/resin/Destroy()
var/turf/T = get_turf(src)
T.thermal_conductivity = initial(T.thermal_conductivity)
..()
@@ -54,7 +54,7 @@
/obj/effect/alien/resin/proc/healthcheck()
if(health <=0)
density = 0
- del(src)
+ qdel(src)
return
/obj/effect/alien/resin/bullet_act(var/obj/item/projectile/Proj)
@@ -164,7 +164,7 @@
name = "purple sac"
desc = "Weird purple octopus-like thing."
layer = 3
- luminosity = NODERANGE
+ light_range = NODERANGE
var/node_range = NODERANGE
/obj/effect/alien/weeds/node/New()
@@ -174,7 +174,7 @@
/obj/effect/alien/weeds/New(pos, node)
..()
if(istype(loc, /turf/space))
- del(src)
+ qdel(src)
return
linked_node = node
if(icon_state == "weeds")icon_state = pick("weeds", "weeds1", "weeds2")
@@ -190,7 +190,7 @@
if (locate(/obj/movable, U))
U = locate(/obj/movable, U)
if(U.density == 1)
- del(src)
+ qdel(src)
return
Alien plants should do something if theres a lot of poison
@@ -200,7 +200,7 @@ Alien plants should do something if theres a lot of poison
return
*/
if (istype(U, /turf/space))
- del(src)
+ qdel(src)
return
if(!linked_node || (get_dist(linked_node, src) > linked_node.node_range) )
@@ -220,19 +220,19 @@ Alien plants should do something if theres a lot of poison
if(O.density)
continue direction_loop
- new /obj/effect/alien/weeds(T, linked_node)
+ PoolOrNew(/obj/effect/alien/weeds, T, linked_node)
/obj/effect/alien/weeds/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
/obj/effect/alien/weeds/attackby(var/obj/item/weapon/W, var/mob/user)
@@ -255,7 +255,7 @@ Alien plants should do something if theres a lot of poison
/obj/effect/alien/weeds/proc/healthcheck()
if(health <= 0)
- del(src)
+ qdel(src)
/obj/effect/alien/weeds/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume)
@@ -294,7 +294,7 @@ Alien plants should do something if theres a lot of poison
/obj/effect/alien/acid/proc/tick()
if(!target)
- del(src)
+ qdel(src)
ticks += 1
@@ -307,8 +307,8 @@ Alien plants should do something if theres a lot of poison
var/turf/simulated/wall/W = target
W.dismantle_wall(1)
else
- del(target)
- del(src)
+ qdel(target)
+ qdel(src)
return
switch(target_strength - ticks)
@@ -350,7 +350,7 @@ Alien plants should do something if theres a lot of poison
spawn(rand(MIN_GROWTH_TIME,MAX_GROWTH_TIME))
Grow()
else
- del(src)
+ qdel(src)
/obj/effect/alien/egg/attack_hand(user as mob)
@@ -361,7 +361,7 @@ Alien plants should do something if theres a lot of poison
switch(status)
if(BURST)
user << "\red You clear the hatched egg."
- del(src)
+ qdel(src)
return
if(GROWING)
user << "\red The child is not developed yet."
diff --git a/code/game/objects/effects/bump_teleporter.dm b/code/game/objects/effects/bump_teleporter.dm
index c4f693da158..9379234ca68 100644
--- a/code/game/objects/effects/bump_teleporter.dm
+++ b/code/game/objects/effects/bump_teleporter.dm
@@ -15,9 +15,9 @@ var/list/obj/effect/bump_teleporter/BUMP_TELEPORTERS = list()
..()
BUMP_TELEPORTERS += src
-/obj/effect/bump_teleporter/Del()
+/obj/effect/bump_teleporter/Destroy()
BUMP_TELEPORTERS -= src
- ..()
+ return ..()
/obj/effect/bump_teleporter/Bumped(atom/user)
if(!ismob(user))
diff --git a/code/game/objects/effects/chemsmoke.dm b/code/game/objects/effects/chem/chemsmoke.dm
similarity index 60%
rename from code/game/objects/effects/chemsmoke.dm
rename to code/game/objects/effects/chem/chemsmoke.dm
index e64a84c47c3..c579bd5317e 100644
--- a/code/game/objects/effects/chemsmoke.dm
+++ b/code/game/objects/effects/chem/chemsmoke.dm
@@ -5,13 +5,11 @@
icon = 'icons/effects/chemsmoke.dmi'
opacity = 0
time_to_live = 300
- pass_flags = PASSTABLE | PASSGRILLE | PASSGLASS //PASSGLASS is fine here, it's just so the visual effect can "flow" around glass
+ pass_flags = PASSTABLE | PASSGRILLE | PASSGLASS //PASSGLASS is fine here, it's just so the visual effect can "flow" around glass
/obj/effect/effect/smoke/chem/New()
..()
- var/datum/reagents/R = new/datum/reagents(500)
- reagents = R
- R.my_atom = src
+ create_reagents(500)
return
/datum/effect/effect/system/smoke_spread/chem
@@ -31,27 +29,22 @@
if(seed_name && plant_controller)
seed = plant_controller.seeds[seed_name]
if(!seed)
- del(src)
+ qdel(src)
..()
/datum/effect/effect/system/smoke_spread/chem/New()
..()
chemholder = new/obj()
- var/datum/reagents/R = new/datum/reagents(500)
- chemholder.reagents = R
- R.my_atom = chemholder
+ chemholder.create_reagents(500)
-//------------------------------------------
//Sets up the chem smoke effect
-//
// Calculates the max range smoke can travel, then gets all turfs in that view range.
// Culls the selected turfs to a (roughly) circle shape, then calls smokeFlow() to make
// sure the smoke can actually path to the turfs. This culls any turfs it can't reach.
-//------------------------------------------
/datum/effect/effect/system/smoke_spread/chem/set_up(var/datum/reagents/carry = null, n = 10, c = 0, loca, direct)
range = n * 0.3
cardinals = c
- carry.copy_to(chemholder, carry.total_volume)
+ carry.trans_to_obj(chemholder, carry.total_volume, copy = 1)
if(istype(loca, /turf/))
location = loca
@@ -62,28 +55,19 @@
targetTurfs = new()
- //build affected area list
- for(var/turf/T in view(range, location))
- //cull turfs to circle
- if(cheap_pythag(T.x - location.x, T.y - location.y) <= range)
+ for(var/turf/T in view(range, location)) //build affected area list
+ if(cheap_pythag(T.x - location.x, T.y - location.y) <= range) //cull turfs to circle
targetTurfs += T
- //make secondary list for reagents that affect walls
- if(chemholder.reagents.has_reagent("thermite") || chemholder.reagents.has_reagent("plantbgone"))
- wallList = new()
+ wallList = new()
- //pathing check
- smokeFlow(location, targetTurfs, wallList)
+ smokeFlow() //pathing check
//set the density of the cloud - for diluting reagents
- density = max(1, targetTurfs.len / 4) //clamp the cloud density minimum to 1 so it cant multiply the reagents
+ density = max(1, targetTurfs.len / 4) //clamp the cloud density minimum to 1 so it cant multiply the reagents
//Admin messaging
- var/contained = ""
- for(var/reagent in carry.reagent_list)
- contained += " [reagent] "
- if(contained)
- contained = "\[[contained]\]"
+ var/contained = carry.get_reagents()
var/area/A = get_area(location)
var/where = "[A.name] | [location.x], [location.y]"
@@ -101,61 +85,27 @@
message_admins("A chemical smoke reaction has taken place in ([whereLink]). No associated key.", 0, 1)
log_game("A chemical smoke reaction has taken place in ([where])[contained]. No associated key.")
-
-//------------------------------------------
//Runs the chem smoke effect
-//
// Spawns damage over time loop for each reagent held in the cloud.
// Applies reagents to walls that affect walls (only thermite and plant-b-gone at the moment).
// Also calculates target locations to spawn the visual smoke effect on, so the whole area
// is covered fairly evenly.
-//------------------------------------------
/datum/effect/effect/system/smoke_spread/chem/start()
-
- if(!location) //kill grenade if it somehow ends up in nullspace
+ if(!location)
return
- //reagent application - only run if there are extra reagents in the smoke
- if(chemholder.reagents.reagent_list.len)
- for(var/datum/reagent/R in chemholder.reagents.reagent_list)
- var/proba = 100
- var/runs = 5
+ if(chemholder.reagents.reagent_list.len) //reagent application - only run if there are extra reagents in the smoke
+ for(var/turf/T in wallList)
+ chemholder.reagents.touch_turf(T)
+ for(var/turf/T in targetTurfs)
+ chemholder.reagents.touch_turf(T)
+ for(var/atom/A in T.contents)
+ if(istype(A, /obj/effect/effect/smoke/chem) || istype(A, /mob))
+ continue
+ else if(isobj(A) && !A.simulated)
+ chemholder.reagents.touch_obj(A)
- //dilute the reagents according to cloud density
- R.volume /= density
- chemholder.reagents.update_total()
-
- //apply wall affecting reagents to walls
- if(R.id in list("thermite", "plantbgone"))
- for(var/turf/T in wallList)
- R.reaction_turf(T, R.volume)
-
- //reagents that should be applied to turfs in a random pattern
- if(R.id == "carbon")
- proba = 75
- else if(R.id in list("blood", "radium", "uranium"))
- proba = 25
-
- spawn(0)
- for(var/i = 0, i < runs, i++)
- for(var/turf/T in targetTurfs)
- if(prob(proba))
- R.reaction_turf(T, R.volume)
- for(var/atom/A in T.contents)
- if(istype(A, /obj/effect/effect/smoke/chem)) //skip the item if it is chem smoke
- continue
- else if(istype(A, /mob))
- var/dist = cheap_pythag(T.x - location.x, T.y - location.y)
- if(!dist)
- dist = 1
- R.reaction_mob(A, volume = R.volume / dist)
- else if(istype(A, /obj))
- R.reaction_obj(A, R.volume)
- sleep(30)
-
-
- //build smoke icon
- var/color = mix_color_from_reagents(chemholder.reagents.reagent_list)
+ var/color = chemholder.reagents.get_color() //build smoke icon
var/icon/I
if(color)
I = icon('icons/effects/chemsmoke.dmi')
@@ -163,13 +113,9 @@
else
I = icon('icons/effects/96x96.dmi', "smoke")
+ var/const/arcLength = 2.3559 //distance between each smoke cloud
- //distance between each smoke cloud
- var/const/arcLength = 2.3559
-
-
- //calculate positions for smoke coverage - then spawn smoke
- for(var/i = 0, i < range, i++)
+ for(var/i = 0, i < range, i++) //calculate positions for smoke coverage - then spawn smoke
var/radius = i * 1.5
if(!radius)
spawn(0)
@@ -204,42 +150,40 @@
if(passed_smoke)
smoke = passed_smoke
else
- smoke = new(location)
+ smoke = PoolOrNew(/obj/effect/effect/smoke/chem, location)
if(chemholder.reagents.reagent_list.len)
- chemholder.reagents.copy_to(smoke, chemholder.reagents.total_volume / dist, safety = 1) //copy reagents to the smoke so mob/breathe() can handle inhaling the reagents
+ chemholder.reagents.trans_to_obj(smoke, chemholder.reagents.total_volume / dist, copy = 1) //copy reagents to the smoke so mob/breathe() can handle inhaling the reagents
smoke.icon = I
smoke.layer = 6
smoke.set_dir(pick(cardinal))
- smoke.pixel_x = -32 + rand(-8,8)
- smoke.pixel_y = -32 + rand(-8,8)
+ smoke.pixel_x = -32 + rand(-8, 8)
+ smoke.pixel_y = -32 + rand(-8, 8)
walk_to(smoke, T)
smoke.opacity = 1 //switching opacity on after the smoke has spawned, and then
sleep(150+rand(0,20)) // turning it off before it is deleted results in cleaner
smoke.opacity = 0 // lighting and view range updates
fadeOut(smoke)
- smoke.delete()
+ qdel(src)
/datum/effect/effect/system/smoke_spread/chem/spores/spawnSmoke(var/turf/T, var/icon/I, var/dist = 1)
- var/obj/effect/effect/smoke/chem/spores = new(location)
+ var/obj/effect/effect/smoke/chem/spores = PoolOrNew(/obj/effect/effect/smoke/chem, location)
spores.name = "cloud of [seed.seed_name] [seed.seed_noun]"
..(T, I, dist, spores)
-//------------------------------------------
-// Fades out the smoke smoothly using it's alpha variable.
-//------------------------------------------
-/datum/effect/effect/system/smoke_spread/chem/proc/fadeOut(var/atom/A, var/frames = 16)
+/datum/effect/effect/system/smoke_spread/chem/proc/fadeOut(var/atom/A, var/frames = 16) // Fades out the smoke smoothly using it's alpha variable.
+ if(A.alpha == 0) //Handle already transparent case
+ return
+ if(frames == 0)
+ frames = 1 //We will just assume that by 0 frames, the coder meant "during one frame".
var/step = A.alpha / frames
for(var/i = 0, i < frames, i++)
A.alpha -= step
sleep(world.tick_lag)
return
-//------------------------------------------
-// Smoke pathfinder. Uses a flood fill method based on zones to
-// quickly check what turfs the smoke (airflow) can actually reach.
-//------------------------------------------
-/datum/effect/effect/system/smoke_spread/chem/proc/smokeFlow()
+
+/datum/effect/effect/system/smoke_spread/chem/proc/smokeFlow() // Smoke pathfinder. Uses a flood fill method based on zones to quickly check what turfs the smoke (airflow) can actually reach.
var/list/pending = new()
var/list/complete = new()
diff --git a/code/game/objects/effects/chem/foam.dm b/code/game/objects/effects/chem/foam.dm
new file mode 100644
index 00000000000..fb5b6f8ca73
--- /dev/null
+++ b/code/game/objects/effects/chem/foam.dm
@@ -0,0 +1,184 @@
+// Foam
+// Similar to smoke, but spreads out more
+// metal foams leave behind a foamed metal wall
+
+/obj/effect/effect/foam
+ name = "foam"
+ icon_state = "foam"
+ opacity = 0
+ anchored = 1
+ density = 0
+ layer = OBJ_LAYER + 0.9
+ mouse_opacity = 0
+ animate_movement = 0
+ var/amount = 3
+ var/expand = 1
+ var/metal = 0
+
+/obj/effect/effect/foam/New(var/loc, var/ismetal = 0)
+ ..(loc)
+ icon_state = "[ismetal? "m" : ""]foam"
+ metal = ismetal
+ playsound(src, 'sound/effects/bubbles2.ogg', 80, 1, -3)
+ spawn(3 + metal * 3)
+ process()
+ checkReagents()
+ spawn(120)
+ processing_objects.Remove(src)
+ sleep(30)
+ if(metal)
+ var/obj/structure/foamedmetal/M = new(src.loc)
+ M.metal = metal
+ M.updateicon()
+ flick("[icon_state]-disolve", src)
+ sleep(5)
+ qdel(src)
+ return
+
+/obj/effect/effect/foam/proc/checkReagents() // transfer any reagents to the floor
+ if(!metal && reagents)
+ var/turf/T = get_turf(src)
+ reagents.touch_turf(T)
+
+/obj/effect/effect/foam/process()
+ if(--amount < 0)
+ return
+
+ for(var/direction in cardinal)
+ var/turf/T = get_step(src, direction)
+ if(!T)
+ continue
+
+ if(!T.Enter(src))
+ continue
+
+ var/obj/effect/effect/foam/F = locate() in T
+ if(F)
+ continue
+
+ F = new(T, metal)
+ F.amount = amount
+ if(!metal)
+ F.create_reagents(10)
+ if(reagents)
+ for(var/datum/reagent/R in reagents.reagent_list)
+ F.reagents.add_reagent(R.id, 1, safety = 1) //added safety check since reagents in the foam have already had a chance to react
+
+/obj/effect/effect/foam/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume) // foam disolves when heated, except metal foams
+ if(!metal && prob(max(0, exposed_temperature - 475)))
+ flick("[icon_state]-disolve", src)
+
+ spawn(5)
+ qdel(src)
+
+/obj/effect/effect/foam/Crossed(var/atom/movable/AM)
+ if(metal)
+ return
+ if(istype(AM, /mob/living))
+ var/mob/living/M = AM
+ M.slip("the foam", 6)
+
+/datum/effect/effect/system/foam_spread
+ var/amount = 5 // the size of the foam spread.
+ var/list/carried_reagents // the IDs of reagents present when the foam was mixed
+ var/metal = 0 // 0 = foam, 1 = metalfoam, 2 = ironfoam
+
+/datum/effect/effect/system/foam_spread/set_up(amt=5, loca, var/datum/reagents/carry = null, var/metalfoam = 0)
+ amount = round(sqrt(amt / 3), 1)
+ if(istype(loca, /turf/))
+ location = loca
+ else
+ location = get_turf(loca)
+
+ carried_reagents = list()
+ metal = metalfoam
+
+ // bit of a hack here. Foam carries along any reagent also present in the glass it is mixed with (defaults to water if none is present). Rather than actually transfer the reagents, this makes a list of the reagent ids and spawns 1 unit of that reagent when the foam disolves.
+
+ if(carry && !metal)
+ for(var/datum/reagent/R in carry.reagent_list)
+ carried_reagents += R.id
+
+/datum/effect/effect/system/foam_spread/start()
+ spawn(0)
+ var/obj/effect/effect/foam/F = locate() in location
+ if(F)
+ F.amount += amount
+ return
+
+ F = PoolOrNew(/obj/effect/effect/foam, list(location, metal))
+ F.amount = amount
+
+ if(!metal) // don't carry other chemicals if a metal foam
+ F.create_reagents(10)
+
+ if(carried_reagents)
+ for(var/id in carried_reagents)
+ F.reagents.add_reagent(id, 1, safety = 1) //makes a safety call because all reagents should have already reacted anyway
+ else
+ F.reagents.add_reagent("water", 1, safety = 1)
+
+// wall formed by metal foams, dense and opaque, but easy to break
+
+/obj/structure/foamedmetal
+ icon = 'icons/effects/effects.dmi'
+ icon_state = "metalfoam"
+ density = 1
+ opacity = 1 // changed in New()
+ anchored = 1
+ name = "foamed metal"
+ desc = "A lightweight foamed metal wall."
+ var/metal = 1 // 1 = aluminum, 2 = iron
+
+/obj/structure/foamedmetal/New()
+ ..()
+ update_nearby_tiles(1)
+
+/obj/structure/foamedmetal/Destroy()
+ density = 0
+ update_nearby_tiles(1)
+ ..()
+
+/obj/structure/foamedmetal/proc/updateicon()
+ if(metal == 1)
+ icon_state = "metalfoam"
+ else
+ icon_state = "ironfoam"
+
+/obj/structure/foamedmetal/ex_act(severity)
+ qdel(src)
+
+/obj/structure/foamedmetal/blob_act()
+ qdel(src)
+
+/obj/structure/foamedmetal/bullet_act()
+ if(metal == 1 || prob(50))
+ qdel(src)
+
+/obj/structure/foamedmetal/attack_hand(var/mob/user)
+ if ((HULK in user.mutations) || (prob(75 - metal * 25)))
+ user.visible_message("[user] smashes through the foamed metal.", "You smash through the metal foam wall.")
+ qdel(src)
+ else
+ user << "You hit the metal foam but bounce off it."
+ return
+
+/obj/structure/foamedmetal/attackby(var/obj/item/I, var/mob/user)
+ if(istype(I, /obj/item/weapon/grab))
+ var/obj/item/weapon/grab/G = I
+ G.affecting.loc = src.loc
+ visible_message("[G.assailant] smashes [G.affecting] through the foamed metal wall.")
+ qdel(I)
+ qdel(src)
+ return
+
+ if(prob(I.force * 20 - metal * 25))
+ user.visible_message("[user] smashes through the foamed metal.", "You smash through the foamed metal with \the [I].")
+ qdel(src)
+ else
+ user << "You hit the metal foam to no effect."
+
+/obj/structure/foamedmetal/CanPass(atom/movable/mover, turf/target, height=1.5, air_group = 0)
+ if(air_group)
+ return 0
+ return !density
\ No newline at end of file
diff --git a/code/game/objects/effects/chem/water.dm b/code/game/objects/effects/chem/water.dm
new file mode 100644
index 00000000000..4ae012cc9ec
--- /dev/null
+++ b/code/game/objects/effects/chem/water.dm
@@ -0,0 +1,50 @@
+/obj/effect/effect/water
+ name = "water"
+ icon = 'icons/effects/effects.dmi'
+ icon_state = "extinguish"
+ mouse_opacity = 0
+
+/obj/effect/effect/water/New(loc)
+ ..()
+ spawn(150) // In case whatever made it forgets to delete it
+ if(src)
+ qdel(src)
+
+/obj/effect/effect/water/proc/set_color() // Call it after you move reagents to it
+ icon += reagents.get_color()
+
+/obj/effect/effect/water/proc/set_up(var/turf/target, var/step_count = 5, var/delay = 5)
+ if(!target)
+ return
+ for(var/i = 1 to step_count)
+ step_towards(src, target)
+ var/turf/T = get_turf(src)
+ reagents.touch_turf(T)
+ var/mob/M = locate() in T
+ if(M)
+ reagents.splash_mob(M, reagents.total_volume)
+ break
+ for(var/atom/A in T)
+ reagents.touch(A)
+ if(T == get_turf(target))
+ break
+ sleep(delay)
+ sleep(10)
+ qdel(src)
+
+/obj/effect/effect/water/Move(turf/newloc)
+ if(newloc.density)
+ return 0
+ . = ..()
+
+/obj/effect/effect/water/Bump(atom/A)
+ if(reagents)
+ reagents.touch(A)
+ return ..()
+
+//Used by spraybottles.
+/obj/effect/effect/water/chempuff
+ name = "chemicals"
+ icon = 'icons/obj/chempuff.dmi'
+ icon_state = ""
+ pass_flags = PASSTABLE | PASSGRILLE
\ No newline at end of file
diff --git a/code/game/objects/effects/decals/Cleanable/fuel.dm b/code/game/objects/effects/decals/Cleanable/fuel.dm
index c9ea58b1218..2bf3a2a574d 100644
--- a/code/game/objects/effects/decals/Cleanable/fuel.dm
+++ b/code/game/objects/effects/decals/Cleanable/fuel.dm
@@ -25,7 +25,7 @@
if(!has_spread)
Spread()
else
- del(src)
+ qdel(src)
proc/Spread(exclude=list())
//Allows liquid fuels to sometimes flow into other tiles.
diff --git a/code/game/objects/effects/decals/Cleanable/humans.dm b/code/game/objects/effects/decals/Cleanable/humans.dm
index c6b3137806d..b81089d9fb4 100644
--- a/code/game/objects/effects/decals/Cleanable/humans.dm
+++ b/code/game/objects/effects/decals/Cleanable/humans.dm
@@ -21,10 +21,10 @@ var/global/list/image/splatter_cache=list()
var/list/datum/disease2/disease/virus2 = list()
var/amount = 5
-/obj/effect/decal/cleanable/blood/Del()
+/obj/effect/decal/cleanable/blood/Destroy()
for(var/datum/disease/D in viruses)
D.cure(0)
- ..()
+ return ..()
/obj/effect/decal/cleanable/blood/New()
..()
@@ -37,7 +37,7 @@ var/global/list/image/splatter_cache=list()
if(B != src)
if (B.blood_DNA)
blood_DNA |= B.blood_DNA.Copy()
- del(B)
+ qdel(B)
spawn(DRYING_TIME * (amount+1))
dry()
@@ -198,7 +198,7 @@ var/global/list/image/splatter_cache=list()
for (var/i = 0, i < pick(1, 200; 2, 150; 3, 50; 4), i++)
sleep(3)
if (i > 0)
- var/obj/effect/decal/cleanable/blood/b = new /obj/effect/decal/cleanable/blood/splatter(src.loc)
+ var/obj/effect/decal/cleanable/blood/b = PoolOrNew(/obj/effect/decal/cleanable/blood/splatter, src.loc)
b.basecolor = src.basecolor
b.update_icon()
for(var/datum/disease/D in src.viruses)
diff --git a/code/game/objects/effects/decals/Cleanable/misc.dm b/code/game/objects/effects/decals/Cleanable/misc.dm
index 4c85144d1e5..c70a5ab9fc6 100644
--- a/code/game/objects/effects/decals/Cleanable/misc.dm
+++ b/code/game/objects/effects/decals/Cleanable/misc.dm
@@ -21,14 +21,14 @@
var/turf/simulated/floor/F = get_turf(src)
if (istype(F))
F.dirt += 4
- del(src)
+ qdel(src)
/obj/effect/decal/cleanable/greenglow
New()
..()
spawn(1200)// 2 minutes
- del(src)
+ qdel(src)
/obj/effect/decal/cleanable/dirt
name = "dirt"
@@ -58,7 +58,7 @@
density = 0
anchored = 1
layer = 2
- luminosity = 1
+ light_range = 1
icon = 'icons/effects/effects.dmi'
icon_state = "greenglow"
@@ -102,7 +102,7 @@
random_icon_states = list("vomit_1", "vomit_2", "vomit_3", "vomit_4")
var/list/viruses = list()
- Del()
+ Destroy()
for(var/datum/disease/D in viruses)
D.cure(0)
..()
@@ -142,4 +142,4 @@
layer = 2
icon = 'icons/effects/blood.dmi'
icon_state = "mfloor1"
- random_icon_states = list("mfloor1", "mfloor2", "mfloor3", "mfloor4", "mfloor5", "mfloor6", "mfloor7")
\ No newline at end of file
+ random_icon_states = list("mfloor1", "mfloor2", "mfloor3", "mfloor4", "mfloor5", "mfloor6", "mfloor7")
diff --git a/code/game/objects/effects/decals/cleanable.dm b/code/game/objects/effects/decals/cleanable.dm
index 63956f5e89a..dc5e6c57e88 100644
--- a/code/game/objects/effects/decals/cleanable.dm
+++ b/code/game/objects/effects/decals/cleanable.dm
@@ -1,6 +1,5 @@
/obj/effect/decal/cleanable
var/list/random_icon_states = list()
- var/targeted_by = null // Used so cleanbots can't claim a mess.
/obj/effect/decal/cleanable/New()
if (random_icon_states && length(src.random_icon_states) > 0)
diff --git a/code/game/objects/effects/decals/contraband.dm b/code/game/objects/effects/decals/contraband.dm
index 9d097f47a03..eac899d5b15 100644
--- a/code/game/objects/effects/decals/contraband.dm
+++ b/code/game/objects/effects/decals/contraband.dm
@@ -72,7 +72,7 @@
else
P.roll_and_drop(P.loc)
- del(oldsrc) //delete it now to cut down on sanity checks afterwards. Agouri's code supports rerolling it anyway
+ qdel(oldsrc) //delete it now to cut down on sanity checks afterwards. Agouri's code supports rerolling it anyway
//############################## THE ACTUAL DECALS ###########################
@@ -125,7 +125,7 @@
playsound(loc, 'sound/items/Wirecutter.ogg', 100, 1)
if(ruined)
user << "You remove the remnants of the poster."
- del(src)
+ qdel(src)
else
user << "You carefully remove the poster from the wall."
roll_and_drop(user.loc)
@@ -154,7 +154,7 @@
var/obj/item/weapon/contraband/poster/P = new(src, serial_number)
P.loc = newloc
src.loc = P
- del(src)
+ qdel(src)
/datum/poster
// Name suffix. Poster - [name]
diff --git a/code/game/objects/effects/decals/misc.dm b/code/game/objects/effects/decals/misc.dm
index 77349891500..964a1301b89 100644
--- a/code/game/objects/effects/decals/misc.dm
+++ b/code/game/objects/effects/decals/misc.dm
@@ -11,10 +11,4 @@
/obj/effect/decal/spraystill
density = 0
anchored = 1
- layer = 50
-
-//Used by spraybottles.
-/obj/effect/decal/chempuff
- name = "chemicals"
- icon = 'icons/obj/chempuff.dmi'
- pass_flags = PASSTABLE | PASSGRILLE
\ No newline at end of file
+ layer = 50
\ No newline at end of file
diff --git a/code/game/objects/effects/decals/remains.dm b/code/game/objects/effects/decals/remains.dm
index dd786ddc0de..ff3c8d4a618 100644
--- a/code/game/objects/effects/decals/remains.dm
+++ b/code/game/objects/effects/decals/remains.dm
@@ -30,7 +30,7 @@
var/turf/simulated/floor/F = get_turf(src)
if (istype(F))
new /obj/effect/decal/cleanable/ash(F)
- del(src)
+ qdel(src)
/obj/effect/decal/remains/robot/attack_hand(mob/user as mob)
return
diff --git a/code/game/objects/effects/decals/warning_stripes.dm b/code/game/objects/effects/decals/warning_stripes.dm
index 89067ada2a4..e22acfad74e 100644
--- a/code/game/objects/effects/decals/warning_stripes.dm
+++ b/code/game/objects/effects/decals/warning_stripes.dm
@@ -1,9 +1,11 @@
-/obj/effect/decal/warning_stripes
- icon = 'icons/effects/warning_stripes.dmi'
- layer = 2
-
-/obj/effect/decal/warning_stripes/New()
- . = ..()
-
- loc.overlays += src
- del src
\ No newline at end of file
+/obj/effect/decal/warning_stripes
+ icon = 'icons/effects/warning_stripes.dmi'
+ layer = 2
+
+/obj/effect/decal/warning_stripes/New()
+ . = ..()
+ var/turf/T=get_turf(src)
+ var/image/I=image(icon, icon_state = icon_state, dir = dir)
+ I.color=color
+ T.overlays += I
+ qdel(src)
diff --git a/code/game/objects/effects/effect_system.dm b/code/game/objects/effects/effect_system.dm
index ea9af2f70fe..238cb575b32 100644
--- a/code/game/objects/effects/effect_system.dm
+++ b/code/game/objects/effects/effect_system.dm
@@ -13,36 +13,11 @@ would spawn and follow the beaker, even if it is carried or thrown.
unacidable = 1//So effect are not targeted by alien acid.
pass_flags = PASSTABLE | PASSGRILLE
-/obj/effect/effect/water
- name = "water"
- icon = 'icons/effects/effects.dmi'
- icon_state = "extinguish"
- var/life = 15.0
- mouse_opacity = 0
-
-/obj/effect/proc/delete()
- loc = null
+/obj/effect/Destroy()
if(reagents)
reagents.delete()
- return
-
-/obj/effect/effect/water/Move(turf/newloc)
- //var/turf/T = src.loc
- //if (istype(T, /turf))
- // T.firelevel = 0 //TODO: FIX
- if (--src.life < 1)
- //SN src = null
- delete()
- if(newloc.density)
- return 0
- .=..()
-
-/obj/effect/effect/water/Bump(atom/A)
- if(reagents)
- reagents.reaction(A)
return ..()
-
-
+
/datum/effect/effect/system
var/number = 3
var/cardinals = 0
@@ -100,7 +75,7 @@ steam.start() -- spawns the effect
spawn(0)
if(holder)
src.location = get_turf(holder)
- var/obj/effect/effect/steam/steam = new /obj/effect/effect/steam(src.location)
+ var/obj/effect/effect/steam/steam = PoolOrNew(/obj/effect/effect/steam, src.location)
var/direction
if(src.cardinals)
direction = pick(cardinal)
@@ -110,7 +85,7 @@ steam.start() -- spawns the effect
sleep(5)
step(steam,direction)
spawn(20)
- steam.delete()
+ qdel(steam)
/////////////////////////////////////////////
//SPARK SYSTEM (like steam system)
@@ -133,15 +108,14 @@ steam.start() -- spawns the effect
if (istype(T, /turf))
T.hotspot_expose(1000,100)
spawn (100)
- delete()
+ qdel(src)
return
-/obj/effect/effect/sparks/Del()
+/obj/effect/effect/sparks/Destroy()
var/turf/T = src.loc
if (istype(T, /turf))
T.hotspot_expose(1000,100)
- ..()
- return
+ return ..()
/obj/effect/effect/sparks/Move()
..()
@@ -171,7 +145,7 @@ steam.start() -- spawns the effect
spawn(0)
if(holder)
src.location = get_turf(holder)
- var/obj/effect/effect/sparks/sparks = new /obj/effect/effect/sparks(src.location)
+ var/obj/effect/effect/sparks/sparks = PoolOrNew(/obj/effect/effect/sparks, src.location)
src.total_sparks++
var/direction
if(src.cardinals)
@@ -183,7 +157,7 @@ steam.start() -- spawns the effect
step(sparks,direction)
spawn(20)
if(sparks)
- sparks.delete()
+ qdel(sparks)
src.total_sparks--
@@ -212,7 +186,7 @@ steam.start() -- spawns the effect
/obj/effect/effect/smoke/New()
..()
spawn (time_to_live)
- delete()
+ qdel(src)
return
/obj/effect/effect/smoke/Crossed(mob/living/carbon/M as mob )
@@ -246,7 +220,7 @@ steam.start() -- spawns the effect
/obj/effect/effect/smoke/illumination/New(var/newloc, var/brightness=15, var/lifetime=10)
time_to_live=lifetime
..()
- SetLuminosity(brightness)
+ set_light(brightness)
/////////////////////////////////////////////
// Bad smoke
@@ -357,7 +331,7 @@ steam.start() -- spawns the effect
spawn(0)
if(holder)
src.location = get_turf(holder)
- var/obj/effect/effect/smoke/smoke = new smoke_type(src.location)
+ var/obj/effect/effect/smoke/smoke = PoolOrNew(smoke_type, src.location)
src.total_smoke++
var/direction = src.direction
if(!direction)
@@ -369,7 +343,7 @@ steam.start() -- spawns the effect
sleep(10)
step(smoke,direction)
spawn(smoke.time_to_live*0.75+rand(10,30))
- if (smoke) smoke.delete()
+ if (smoke) qdel(smoke)
src.total_smoke--
@@ -415,13 +389,13 @@ steam.start() -- spawns the effect
var/turf/T = get_turf(src.holder)
if(T != src.oldposition)
if(istype(T, /turf/space))
- var/obj/effect/effect/ion_trails/I = new /obj/effect/effect/ion_trails(src.oldposition)
+ var/obj/effect/effect/ion_trails/I = PoolOrNew(/obj/effect/effect/ion_trails, src.oldposition)
src.oldposition = T
I.set_dir(src.holder.dir)
flick("ion_fade", I)
I.icon_state = "blank"
spawn( 20 )
- I.delete()
+ qdel(I)
spawn(2)
if(src.on)
src.processing = 1
@@ -461,12 +435,12 @@ steam.start() -- spawns the effect
src.processing = 0
spawn(0)
if(src.number < 3)
- var/obj/effect/effect/steam/I = new /obj/effect/effect/steam(src.oldposition)
+ var/obj/effect/effect/steam/I = PoolOrNew(/obj/effect/effect/steam, src.oldposition)
src.number++
src.oldposition = get_turf(holder)
I.set_dir(src.holder.dir)
spawn(10)
- I.delete()
+ qdel(I)
src.number--
spawn(2)
if(src.on)
@@ -481,228 +455,7 @@ steam.start() -- spawns the effect
proc/stop()
src.processing = 0
src.on = 0
-
-
-
-// Foam
-// Similar to smoke, but spreads out more
-// metal foams leave behind a foamed metal wall
-
-/obj/effect/effect/foam
- name = "foam"
- icon_state = "foam"
- opacity = 0
- anchored = 1
- density = 0
- layer = OBJ_LAYER + 0.9
- mouse_opacity = 0
- var/amount = 3
- var/expand = 1
- animate_movement = 0
- var/metal = 0
-
-
-/obj/effect/effect/foam/New(loc, var/ismetal=0)
- ..(loc)
- icon_state = "[ismetal ? "m":""]foam"
- metal = ismetal
- playsound(src, 'sound/effects/bubbles2.ogg', 80, 1, -3)
- spawn(3 + metal*3)
- process()
- checkReagents()
- spawn(120)
- processing_objects.Remove(src)
- sleep(30)
-
- if(metal)
- var/obj/structure/foamedmetal/M = new(src.loc)
- M.metal = metal
- M.updateicon()
-
- flick("[icon_state]-disolve", src)
- sleep(5)
- delete()
- return
-
-// transfer any reagents to the floor
-/obj/effect/effect/foam/proc/checkReagents()
- if(!metal && reagents)
- for(var/atom/A in src.loc.contents)
- if(A == src)
- continue
- reagents.reaction(A, 1, 1)
-
-/obj/effect/effect/foam/process()
- if(--amount < 0)
- return
-
-
- for(var/direction in cardinal)
-
-
- var/turf/T = get_step(src,direction)
- if(!T)
- continue
-
- if(!T.Enter(src))
- continue
-
- var/obj/effect/effect/foam/F = locate() in T
- if(F)
- continue
-
- F = new(T, metal)
- F.amount = amount
- if(!metal)
- F.create_reagents(10)
- if (reagents)
- for(var/datum/reagent/R in reagents.reagent_list)
- F.reagents.add_reagent(R.id, 1, safety = 1) //added safety check since reagents in the foam have already had a chance to react
-
-// foam disolves when heated
-// except metal foams
-/obj/effect/effect/foam/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume)
- if(!metal && prob(max(0, exposed_temperature - 475)))
- flick("[icon_state]-disolve", src)
-
- spawn(5)
- delete()
-
-
-/obj/effect/effect/foam/Crossed(var/atom/movable/AM)
- if(metal)
- return
- if(istype(AM, /mob/living))
- var/mob/living/M = AM
- M.slip("the foam",6)
-
-/datum/effect/effect/system/foam_spread
- var/amount = 5 // the size of the foam spread.
- var/list/carried_reagents // the IDs of reagents present when the foam was mixed
- var/metal = 0 // 0=foam, 1=metalfoam, 2=ironfoam
-
-
-
-
- set_up(amt=5, loca, var/datum/reagents/carry = null, var/metalfoam = 0)
- amount = round(sqrt(amt / 3), 1)
- if(istype(loca, /turf/))
- location = loca
- else
- location = get_turf(loca)
-
- carried_reagents = list()
- metal = metalfoam
-
-
- // bit of a hack here. Foam carries along any reagent also present in the glass it is mixed
- // with (defaults to water if none is present). Rather than actually transfer the reagents,
- // this makes a list of the reagent ids and spawns 1 unit of that reagent when the foam disolves.
-
-
- if(carry && !metal)
- for(var/datum/reagent/R in carry.reagent_list)
- carried_reagents += R.id
-
- start()
- spawn(0)
- var/obj/effect/effect/foam/F = locate() in location
- if(F)
- F.amount += amount
- return
-
- F = new(src.location, metal)
- F.amount = amount
-
- if(!metal) // don't carry other chemicals if a metal foam
- F.create_reagents(10)
-
- if(carried_reagents)
- for(var/id in carried_reagents)
- F.reagents.add_reagent(id, 1, null, 1) //makes a safety call because all reagents should have already reacted anyway
- else
- F.reagents.add_reagent("water", 1, safety = 1)
-
-// wall formed by metal foams
-// dense and opaque, but easy to break
-
-/obj/structure/foamedmetal
- icon = 'icons/effects/effects.dmi'
- icon_state = "metalfoam"
- density = 1
- opacity = 1 // changed in New()
- anchored = 1
- name = "foamed metal"
- desc = "A lightweight foamed metal wall."
- var/metal = 1 // 1=aluminum, 2=iron
-
- New()
- ..()
- update_nearby_tiles(1)
-
-
-
- Del()
-
- density = 0
- update_nearby_tiles(1)
- ..()
-
- proc/updateicon()
- if(metal == 1)
- icon_state = "metalfoam"
- else
- icon_state = "ironfoam"
-
-
- ex_act(severity)
- del(src)
-
- blob_act()
- del(src)
-
- bullet_act()
- if(metal==1 || prob(50))
- del(src)
-
- attack_hand(var/mob/user)
- if ((HULK in user.mutations) || (prob(75 - metal*25)))
- user << "\blue You smash through the metal foam wall."
- for(var/mob/O in oviewers(user))
- if ((O.client && !( O.blinded )))
- O << "\red [user] smashes through the foamed metal."
-
- del(src)
- else
- user << "\blue You hit the metal foam but bounce off it."
- return
-
-
- attackby(var/obj/item/I, var/mob/user)
-
- if (istype(I, /obj/item/weapon/grab))
- var/obj/item/weapon/grab/G = I
- G.affecting.loc = src.loc
- for(var/mob/O in viewers(src))
- if (O.client)
- O << "\red [G.assailant] smashes [G.affecting] through the foamed metal wall."
- del(I)
- del(src)
- return
-
- if(prob(I.force*20 - metal*25))
- user << "\blue You smash through the foamed metal with \the [I]."
- for(var/mob/O in oviewers(user))
- if ((O.client && !( O.blinded )))
- O << "\red [user] smashes through the foamed metal."
- del(src)
- else
- user << "\blue You hit the metal foam to no effect."
-
- CanPass(atom/movable/mover, turf/target, height=1.5, air_group = 0)
- if(air_group) return 0
- return !density
-
+
/datum/effect/effect/system/reagents_explosion
var/amount // TNT equivalent
var/flashing = 0 // does explosion creates flash effect?
@@ -722,7 +475,7 @@ steam.start() -- spawns the effect
start()
if (amount <= 2)
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
+ var/datum/effect/effect/system/spark_spread/s = PoolOrNew(/datum/effect/effect/system/spark_spread)
s.set_up(2, 1, location)
s.start()
diff --git a/code/game/objects/effects/gibs.dm b/code/game/objects/effects/gibs.dm
index 808e46c2a38..a7f4c0482fd 100644
--- a/code/game/objects/effects/gibs.dm
+++ b/code/game/objects/effects/gibs.dm
@@ -25,10 +25,10 @@
var/obj/effect/decal/cleanable/blood/gibs/gib = null
for(var/datum/disease/D in viruses)
if(D.spread_type == SPECIAL)
- del(D)
+ qdel(D)
if(sparks)
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
+ var/datum/effect/effect/system/spark_spread/s = PoolOrNew(/datum/effect/effect/system/spark_spread)
s.set_up(2, 1, get_turf(location)) // Not sure if it's safe to pass an arbitrary object to set_up, todo
s.start()
@@ -63,4 +63,4 @@
if(directions.len)
gib.streak(directions)
- del(src)
\ No newline at end of file
+ qdel(src)
diff --git a/code/game/objects/effects/landmarks.dm b/code/game/objects/effects/landmarks.dm
index 28a4ad2cc27..6ca10456713 100644
--- a/code/game/objects/effects/landmarks.dm
+++ b/code/game/objects/effects/landmarks.dm
@@ -13,78 +13,77 @@
switch(name) //some of these are probably obsolete
if("shuttle")
shuttle_z = z
- del(src)
-
+ qdel(src)
+ return
if("airtunnel_stop")
airtunnel_stop = x
-
if("airtunnel_start")
airtunnel_start = x
-
if("airtunnel_bottom")
airtunnel_bottom = y
-
if("monkey")
monkeystart += loc
- del(src)
-
+ qdel(src)
+ return
if("start")
newplayer_start += loc
- del(src)
-
+ qdel(src)
if("JoinLate")
latejoin += loc
- del(src)
-
+ qdel(src)
if("JoinLateGateway")
latejoin_gateway += loc
- del(src)
-
+ qdel(src)
+ return
if("JoinLateCryo")
latejoin_cryo += loc
- del(src)
-
+ qdel(src)
+ return
if("JoinLateCyborg")
latejoin_cyborg += loc
- del(src)
-
+ qdel(src)
+ return
if("prisonwarp")
prisonwarp += loc
- del(src)
-
+ qdel(src)
+ return
if("Holding Facility")
holdingfacility += loc
-
if("tdome1")
tdome1 += loc
-
if("tdome2")
tdome2 += loc
-
if("tdomeadmin")
tdomeadmin += loc
-
if("tdomeobserve")
tdomeobserve += loc
-
if("prisonsecuritywarp")
prisonsecuritywarp += loc
- del(src)
-
+ qdel(src)
+ return
if("blobstart")
blobstart += loc
- del(src)
-
+ qdel(src)
+ return
if("xeno_spawn")
xeno_spawn += loc
- del(src)
+ qdel(src)
+ return
+ if("endgame_exit")
+ endgame_safespawns += loc
+ qdel(src)
+ return
+ if("bluespacerift")
+ endgame_exits += loc
+ qdel(src)
+ return
landmarks_list += src
return 1
-/obj/effect/landmark/Del()
+/obj/effect/landmark/Destroy()
landmarks_list -= src
- ..()
+ return ..()
/obj/effect/landmark/start
name = "start"
@@ -104,7 +103,8 @@
/obj/effect/landmark/start/ninja/New()
..()
- ninjastart += src
+ ninjastart += loc
+ qdel(src)
//Costume spawner landmarks
@@ -113,51 +113,51 @@
var/list/options = typesof(/obj/effect/landmark/costume)
var/PICK= options[rand(1,options.len)]
new PICK(src.loc)
- del(src)
+ qdel(src)
//SUBCLASSES. Spawn a bunch of items and disappear likewise
/obj/effect/landmark/costume/chicken/New()
new /obj/item/clothing/suit/chickensuit(src.loc)
new /obj/item/clothing/head/chicken(src.loc)
new /obj/item/weapon/reagent_containers/food/snacks/egg(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/gladiator/New()
new /obj/item/clothing/under/gladiator(src.loc)
new /obj/item/clothing/head/helmet/gladiator(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/madscientist/New()
new /obj/item/clothing/under/gimmick/rank/captain/suit(src.loc)
new /obj/item/clothing/head/flatcap(src.loc)
new /obj/item/clothing/suit/storage/toggle/labcoat/mad(src.loc)
new /obj/item/clothing/glasses/gglasses(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/elpresidente/New()
new /obj/item/clothing/under/gimmick/rank/captain/suit(src.loc)
new /obj/item/clothing/head/flatcap(src.loc)
new /obj/item/clothing/mask/smokable/cigarette/cigar/havana(src.loc)
new /obj/item/clothing/shoes/jackboots(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/nyangirl/New()
new /obj/item/clothing/under/schoolgirl(src.loc)
new /obj/item/clothing/head/kitty(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/maid/New()
new /obj/item/clothing/under/blackskirt(src.loc)
var/CHOICE = pick( /obj/item/clothing/head/beret , /obj/item/clothing/head/rabbitears )
new CHOICE(src.loc)
new /obj/item/clothing/glasses/sunglasses/blindfold(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/butler/New()
new /obj/item/clothing/suit/wcoat(src.loc)
new /obj/item/clothing/under/suit_jacket(src.loc)
new /obj/item/clothing/head/that(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/scratch/New()
new /obj/item/clothing/gloves/white(src.loc)
@@ -165,12 +165,12 @@
new /obj/item/clothing/under/scratch(src.loc)
if (prob(30))
new /obj/item/clothing/head/cueball(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/highlander/New()
new /obj/item/clothing/under/kilt(src.loc)
new /obj/item/clothing/head/beret(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/prig/New()
new /obj/item/clothing/suit/wcoat(src.loc)
@@ -181,24 +181,24 @@
new /obj/item/weapon/cane(src.loc)
new /obj/item/clothing/under/sl_suit(src.loc)
new /obj/item/clothing/mask/fakemoustache(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/plaguedoctor/New()
new /obj/item/clothing/suit/bio_suit/plaguedoctorsuit(src.loc)
new /obj/item/clothing/head/plaguedoctorhat(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/nightowl/New()
new /obj/item/clothing/under/owl(src.loc)
new /obj/item/clothing/mask/gas/owl_mask(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/waiter/New()
new /obj/item/clothing/under/waiter(src.loc)
var/CHOICE= pick( /obj/item/clothing/head/kitty, /obj/item/clothing/head/rabbitears)
new CHOICE(src.loc)
new /obj/item/clothing/suit/apron(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/pirate/New()
new /obj/item/clothing/under/pirate(src.loc)
@@ -206,46 +206,46 @@
var/CHOICE = pick( /obj/item/clothing/head/pirate , /obj/item/clothing/head/bandana )
new CHOICE(src.loc)
new /obj/item/clothing/glasses/eyepatch(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/commie/New()
new /obj/item/clothing/under/soviet(src.loc)
new /obj/item/clothing/head/ushanka(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/imperium_monk/New()
new /obj/item/clothing/suit/imperium_monk(src.loc)
if (prob(25))
new /obj/item/clothing/mask/gas/cyborg(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/holiday_priest/New()
new /obj/item/clothing/suit/holidaypriest(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/marisawizard/fake/New()
new /obj/item/clothing/head/wizard/marisa/fake(src.loc)
new/obj/item/clothing/suit/wizrobe/marisa/fake(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/cutewitch/New()
new /obj/item/clothing/under/sundress(src.loc)
new /obj/item/clothing/head/witchwig(src.loc)
new /obj/item/weapon/staff/broom(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/fakewizard/New()
new /obj/item/clothing/suit/wizrobe/fake(src.loc)
new /obj/item/clothing/head/wizard/fake(src.loc)
new /obj/item/weapon/staff/(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/sexyclown/New()
new /obj/item/clothing/mask/gas/sexyclown(src.loc)
new /obj/item/clothing/under/sexyclown(src.loc)
- del(src)
+ qdel(src)
/obj/effect/landmark/costume/sexymime/New()
new /obj/item/clothing/mask/gas/sexymime(src.loc)
new /obj/item/clothing/under/sexymime(src.loc)
- del(src)
\ No newline at end of file
+ qdel(src)
\ No newline at end of file
diff --git a/code/game/objects/effects/manifest.dm b/code/game/objects/effects/manifest.dm
index bee6174f123..ec45c7a0894 100644
--- a/code/game/objects/effects/manifest.dm
+++ b/code/game/objects/effects/manifest.dm
@@ -17,5 +17,5 @@
P.info = dat
P.name = "paper- 'Crew Manifest'"
//SN src = null
- del(src)
+ qdel(src)
return
\ No newline at end of file
diff --git a/code/game/objects/effects/mines.dm b/code/game/objects/effects/mines.dm
index e8bf9348f6a..27e6d7c74a2 100644
--- a/code/game/objects/effects/mines.dm
+++ b/code/game/objects/effects/mines.dm
@@ -26,24 +26,24 @@
call(src,triggerproc)(M)
/obj/effect/mine/proc/triggerrad(obj)
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
+ var/datum/effect/effect/system/spark_spread/s = PoolOrNew(/datum/effect/effect/system/spark_spread)
s.set_up(3, 1, src)
s.start()
obj:radiation += 50
randmutb(obj)
domutcheck(obj,null)
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/proc/triggerstun(obj)
if(ismob(obj))
var/mob/M = obj
M.Stun(30)
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
+ var/datum/effect/effect/system/spark_spread/s = PoolOrNew(/datum/effect/effect/system/spark_spread)
s.set_up(3, 1, src)
s.start()
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/proc/triggern2o(obj)
//example: n2o triggerproc
@@ -54,7 +54,7 @@
target.assume_gas("sleeping_agent", 30)
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/proc/triggerphoron(obj)
for (var/turf/simulated/floor/target in range(1,src))
@@ -64,20 +64,20 @@
target.hotspot_expose(1000, CELL_VOLUME)
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/proc/triggerkick(obj)
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
+ var/datum/effect/effect/system/spark_spread/s = PoolOrNew(/datum/effect/effect/system/spark_spread)
s.set_up(3, 1, src)
s.start()
- del(obj:client)
+ qdel(obj:client)
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/proc/explode(obj)
explosion(loc, 0, 1, 2, 3)
spawn(0)
- del(src)
+ qdel(src)
/obj/effect/mine/dnascramble
name = "Radiation Mine"
diff --git a/code/game/objects/effects/overlays.dm b/code/game/objects/effects/overlays.dm
index a1af754229a..cc52bf7bbf9 100644
--- a/code/game/objects/effects/overlays.dm
+++ b/code/game/objects/effects/overlays.dm
@@ -10,7 +10,7 @@
var/tmp/atom/BeamSource
New()
..()
- spawn(10) del src
+ spawn(10) qdel(src)
/obj/effect/overlay/palmtree_r
name = "Palm tree"
@@ -31,4 +31,24 @@
/obj/effect/overlay/coconut
name = "Coconuts"
icon = 'icons/misc/beach.dmi'
- icon_state = "coconuts"
\ No newline at end of file
+ icon_state = "coconuts"
+
+/obj/effect/overlay/bluespacify
+ name = "Bluespace"
+ icon = 'icons/turf/space.dmi'
+ icon_state = "bluespacify"
+ layer = 10
+
+/obj/effect/overlay/wallrot
+ name = "wallrot"
+ desc = "Ick..."
+ icon = 'icons/effects/wallrot.dmi'
+ anchored = 1
+ density = 1
+ layer = 5
+ mouse_opacity = 0
+
+/obj/effect/overlay/wallrot/New()
+ ..()
+ pixel_x += rand(-10, 10)
+ pixel_y += rand(-10, 10)
diff --git a/code/game/objects/effects/portals.dm b/code/game/objects/effects/portals.dm
index 6a9f16e99ec..702926d6ffb 100644
--- a/code/game/objects/effects/portals.dm
+++ b/code/game/objects/effects/portals.dm
@@ -30,7 +30,7 @@
/obj/effect/portal/New()
spawn(300)
- del(src)
+ qdel(src)
return
return
@@ -42,7 +42,7 @@
if (icon_state == "portal1")
return
if (!( target ))
- del(src)
+ qdel(src)
return
if (istype(M, /atom/movable))
if(prob(failchance)) //oh dear a problem, put em in deep space
diff --git a/code/game/objects/effects/spawners/bombspawner.dm b/code/game/objects/effects/spawners/bombspawner.dm
index 3f694a8b49a..547931a5118 100644
--- a/code/game/objects/effects/spawners/bombspawner.dm
+++ b/code/game/objects/effects/spawners/bombspawner.dm
@@ -102,7 +102,7 @@
p4.air_contents.temperature = btemp + T0C
p2.secured = 1
- del(src)
+ qdel(src)
*/
/obj/effect/spawner/newbomb
@@ -168,4 +168,4 @@
V.update_icon()
- del(src)
+ qdel(src)
diff --git a/code/game/objects/effects/spawners/vaultspawner.dm b/code/game/objects/effects/spawners/vaultspawner.dm
index e91105f5df9..c4b9203cefc 100644
--- a/code/game/objects/effects/spawners/vaultspawner.dm
+++ b/code/game/objects/effects/spawners/vaultspawner.dm
@@ -23,4 +23,4 @@
else
new /turf/simulated/floor/vault(locate(i,j,z),type)
- del(src)
\ No newline at end of file
+ qdel(src)
diff --git a/code/game/objects/effects/spiders.dm b/code/game/objects/effects/spiders.dm
index 682347669a7..03b5c922d8e 100644
--- a/code/game/objects/effects/spiders.dm
+++ b/code/game/objects/effects/spiders.dm
@@ -11,20 +11,20 @@
/obj/effect/spider/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
/obj/effect/spider/attackby(var/obj/item/weapon/W, var/mob/user)
if(W.attack_verb.len)
- visible_message("\red \The [src] have been [pick(W.attack_verb)] with \the [W][(user ? " by [user]." : ".")]")
+ visible_message("\The [src] have been [pick(W.attack_verb)] with \the [W][(user ? " by [user]." : ".")]")
else
- visible_message("\red \The [src] have been attacked with \the [W][(user ? " by [user]." : ".")]")
+ visible_message("\The [src] have been attacked with \the [W][(user ? " by [user]." : ".")]")
var/damage = W.force / 4.0
@@ -45,7 +45,7 @@
/obj/effect/spider/proc/healthcheck()
if(health <= 0)
- del(src)
+ qdel(src)
/obj/effect/spider/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume)
if(exposed_temperature > 300)
@@ -86,7 +86,7 @@
var/num = rand(6,24)
for(var/i=0, i[src] dies!")
- new /obj/effect/decal/cleanable/spiderling_remains(src.loc)
- del(src)
+ PoolOrNew(/obj/effect/decal/cleanable/spiderling_remains, src.loc)
+ qdel(src)
/obj/effect/spider/spiderling/healthcheck()
if(health <= 0)
@@ -188,7 +188,7 @@
if(amount_grown >= 100)
var/spawn_type = pick(typesof(/mob/living/simple_animal/hostile/giant_spider))
new spawn_type(src.loc)
- del(src)
+ qdel(src)
/obj/effect/decal/cleanable/spiderling_remains
name = "spiderling remains"
@@ -205,8 +205,8 @@
New()
icon_state = pick("cocoon1","cocoon2","cocoon3")
-/obj/effect/spider/cocoon/Del()
+/obj/effect/spider/cocoon/Destroy()
src.visible_message("\red \the [src] splits open.")
for(var/atom/movable/A in contents)
A.loc = src.loc
- ..()
+ return ..()
diff --git a/code/game/objects/empulse.dm b/code/game/objects/empulse.dm
index 8bff463e445..05cdbfee1da 100644
--- a/code/game/objects/empulse.dm
+++ b/code/game/objects/empulse.dm
@@ -9,13 +9,13 @@ proc/empulse(turf/epicenter, heavy_range, light_range, log=0)
log_game("EMP with size ([heavy_range], [light_range]) in area [epicenter.loc.name] ")
if(heavy_range > 1)
- var/obj/effect/overlay/pulse = new/obj/effect/overlay ( epicenter )
+ var/obj/effect/overlay/pulse = PoolOrNew(/obj/effect/overlay, epicenter)
pulse.icon = 'icons/effects/effects.dmi'
pulse.icon_state = "emppulse"
pulse.name = "emp pulse"
pulse.anchored = 1
spawn(20)
- pulse.delete()
+ qdel(pulse)
if(heavy_range > light_range)
light_range = heavy_range
diff --git a/code/game/objects/explosion.dm b/code/game/objects/explosion.dm
index 32f05901b4a..58c053aa669 100644
--- a/code/game/objects/explosion.dm
+++ b/code/game/objects/explosion.dm
@@ -68,8 +68,8 @@ proc/explosion(turf/epicenter, devastation_range, heavy_impact_range, light_impa
message_admins("Explosion with size ([devastation_range], [heavy_impact_range], [light_impact_range]) in area [epicenter.loc.name] ([epicenter.x],[epicenter.y],[epicenter.z]) (JMP)")
log_game("Explosion with size ([devastation_range], [heavy_impact_range], [light_impact_range]) in area [epicenter.loc.name] ")
- var/lighting_controller_was_processing = lighting_controller.processing //Pause the lighting updates for a bit
- lighting_controller.processing = 0
+// var/lighting_controller_was_processing = lighting_controller.processing //Pause the lighting updates for a bit
+// lighting_controller.processing = 0
var/approximate_intensity = (devastation_range * 3) + (heavy_impact_range * 2) + light_impact_range
@@ -87,8 +87,8 @@ proc/explosion(turf/epicenter, devastation_range, heavy_impact_range, light_impa
var/y0 = epicenter.y
var/z0 = epicenter.z
- for(var/turf/T in range(epicenter, max_range))
- var/dist = cheap_pythag(T.x - x0,T.y - y0)
+ for(var/turf/T in trange(max_range, epicenter))
+ var/dist = sqrt((T.x - x0)**2 + (T.y - y0)**2)
if(dist < devastation_range) dist = 1
else if(dist < heavy_impact_range) dist = 2
@@ -99,7 +99,7 @@ proc/explosion(turf/epicenter, devastation_range, heavy_impact_range, light_impa
if(T)
for(var/atom_movable in T.contents) //bypass type checking since only atom/movable can be contained by turfs anyway
var/atom/movable/AM = atom_movable
- if(AM) AM.ex_act(dist)
+ if(AM && AM.simulated) AM.ex_act(dist)
var/took = (world.timeofday-start)/10
//You need to press the DebugGame verb to see these now....they were getting annoying and we've collected a fair bit of data. Just -test- changes to explosion code using this please so we can compare
@@ -113,7 +113,7 @@ proc/explosion(turf/epicenter, devastation_range, heavy_impact_range, light_impa
sleep(8)
- if(!lighting_controller.processing) lighting_controller.processing = lighting_controller_was_processing
+// if(!lighting_controller.processing) lighting_controller.processing = lighting_controller_was_processing
if(!powernet_rebuild_was_deferred_already && defer_powernet_rebuild)
makepowernets()
defer_powernet_rebuild = 0
diff --git a/code/game/objects/explosion_recursive.dm b/code/game/objects/explosion_recursive.dm
index 9dc04ff6301..191fb01d47c 100644
--- a/code/game/objects/explosion_recursive.dm
+++ b/code/game/objects/explosion_recursive.dm
@@ -65,7 +65,7 @@ proc/explosion_rec(turf/epicenter, power)
var/explosion_resistance
/turf/space
- explosion_resistance = 10
+ explosion_resistance = 3
/turf/simulated/floor
explosion_resistance = 1
@@ -83,13 +83,10 @@ proc/explosion_rec(turf/epicenter, power)
explosion_resistance = 1
/turf/simulated/shuttle/wall
- explosion_resistance = 5
+ explosion_resistance = 10
/turf/simulated/wall
- explosion_resistance = 5
-
-/turf/simulated/wall/r_wall
- explosion_resistance = 25
+ explosion_resistance = 10
//Code-wise, a safe value for power is something up to ~25 or ~30.. This does quite a bit of damage to the station.
//direction is the direction that the spread took to come to this tile. So it is pointing in the main blast direction - meaning where this tile should spread most of it's force.
@@ -107,24 +104,16 @@ proc/explosion_rec(turf/epicenter, power)
explosion_turfs[src] = power
var/spread_power = power - src.explosion_resistance //This is the amount of power that will be spread to the tile in the direction of the blast
- var/side_spread_power = power - 2 * src.explosion_resistance //This is the amount of power that will be spread to the side tiles
for(var/obj/O in src)
if(O.explosion_resistance)
spread_power -= O.explosion_resistance
- side_spread_power -= O.explosion_resistance
var/turf/T = get_step(src, direction)
T.explosion_spread(spread_power, direction)
T = get_step(src, turn(direction,90))
- T.explosion_spread(side_spread_power, turn(direction,90))
+ T.explosion_spread(spread_power, turn(direction,90))
T = get_step(src, turn(direction,-90))
- T.explosion_spread(side_spread_power, turn(direction,90))
-
- /*
- for(var/direction in cardinal)
- var/turf/T = get_step(src, direction)
- T.explosion_spread(spread_power)
- */
+ T.explosion_spread(spread_power, turn(direction,90))
/turf/unsimulated/explosion_spread(power)
return //So it doesn't get to the parent proc, which simulates explosions
\ No newline at end of file
diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm
index 87ab21e6108..90edc04c0cf 100644
--- a/code/game/objects/items.dm
+++ b/code/game/objects/items.dm
@@ -3,7 +3,6 @@
icon = 'icons/obj/items.dmi'
var/image/blood_overlay = null //this saves our blood splatter overlay, which will be processed not to go over the edges of the sprite
var/abstract = 0
- var/item_state = null
var/r_speed = 1.0
var/health = null
var/burn_point = null
@@ -11,6 +10,7 @@
var/hitsound = null
var/w_class = 3.0
var/slot_flags = 0 //This is used to determine on which slots an item can fit.
+ var/no_attack_log = 0 //If it's an item we don't want to log attack_logs with, set this to 1
pass_flags = PASSTABLE
pressure_resistance = 5
// causeerrorheresoifixthis
@@ -26,7 +26,6 @@
//Since any item can now be a piece of clothing, this has to be put here so all items share it.
var/flags_inv //This flag is used to determine when items in someone's inventory cover others. IE helmets making it so you can't see glasses, etc.
- var/item_color = null
var/body_parts_covered = 0 //see setup.dm for appropriate bit flags
//var/heat_transfer_coefficient = 1 //0 prevents all transfers, 1 is invisible
var/gas_transfer_coefficient = 1 // for leaking gas from turf to mask and vice-versa (for masks right now, but at some point, i'd like to include space helmets)
@@ -40,6 +39,9 @@
var/zoomdevicename = null //name used for message when binoculars/scope is used
var/zoom = 0 //1 if item is actively being used to zoom. For scoped guns and binoculars.
+ var/item_state = null // Used to specify the item state for the on-mob overlays.
+ var/item_state_slots = null //overrides the default item_state for particular slots.
+
// Used to specify the icon file to be used when the item is worn. If not set the default icon for that slot will be used.
// If icon_override or sprite_sheets are set they will take precendence over this, assuming they apply to the slot in question.
// Only slot_l_hand/slot_r_hand are implemented at the moment. Others to be implemented as needed.
@@ -60,6 +62,12 @@
*/
var/list/sprite_sheets_obj = null
+/obj/item/Destroy()
+ if(ismob(loc))
+ var/mob/m = loc
+ m.unEquip(src, 1)
+ return ..()
+
/obj/item/device
icon = 'icons/obj/device.dmi'
@@ -75,15 +83,15 @@
/obj/item/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
else
return
@@ -147,11 +155,8 @@
src.throwing = 0
if (src.loc == user)
- //canremove==0 means that object may not be removed. You can still wear it. This only applies to clothing. /N
- if(!src.canremove)
+ if(!user.unEquip(src))
return
- else
- user.u_equip(src)
else
if(isliving(src.loc))
return
@@ -161,7 +166,6 @@
src.pickup(user)
return
-
/obj/item/attack_ai(mob/user as mob)
if (istype(src.loc, /obj/item/weapon/robot_module))
//If the item is part of a cyborg module, equip it
@@ -239,198 +243,124 @@
/obj/item/proc/equipped(var/mob/user, var/slot)
return
+//Defines which slots correspond to which slot flags
+var/list/global/slot_flags_enumeration = list(
+ "[slot_wear_mask]" = SLOT_MASK,
+ "[slot_back]" = SLOT_BACK,
+ "[slot_wear_suit]" = SLOT_OCLOTHING,
+ "[slot_gloves]" = SLOT_GLOVES,
+ "[slot_shoes]" = SLOT_FEET,
+ "[slot_belt]" = SLOT_BELT,
+ "[slot_glasses]" = SLOT_EYES,
+ "[slot_head]" = SLOT_HEAD,
+ "[slot_l_ear]" = SLOT_EARS|SLOT_TWOEARS,
+ "[slot_r_ear]" = SLOT_EARS|SLOT_TWOEARS,
+ "[slot_w_uniform]" = SLOT_ICLOTHING,
+ "[slot_wear_id]" = SLOT_ID,
+ "[slot_tie]" = SLOT_TIE,
+ )
+
//the mob M is attempting to equip this item into the slot passed through as 'slot'. Return 1 if it can do this and 0 if it can't.
//If you are making custom procs but would like to retain partial or complete functionality of this one, include a 'return ..()' to where you want this to happen.
//Set disable_warning to 1 if you wish it to not give you outputs.
+//Should probably move the bulk of this into mob code some time, as most of it is related to the definition of slots and not item-specific
/obj/item/proc/mob_can_equip(M as mob, slot, disable_warning = 0)
if(!slot) return 0
if(!M) return 0
- if(ishuman(M))
- //START HUMAN
- var/mob/living/carbon/human/H = M
- var/list/mob_equip = list()
- if(H.species.hud && H.species.hud.equip_slots)
- mob_equip = H.species.hud.equip_slots
+ if(!ishuman(M)) return 0
- if(H.species && !(slot in mob_equip))
+ var/mob/living/carbon/human/H = M
+ var/list/mob_equip = list()
+ if(H.species.hud && H.species.hud.equip_slots)
+ mob_equip = H.species.hud.equip_slots
+
+ if(H.species && !(slot in mob_equip))
+ return 0
+
+ //First check if the item can be equipped to the desired slot.
+ if("[slot]" in slot_flags_enumeration)
+ var/req_flags = slot_flags_enumeration["[slot]"]
+ if(!(req_flags & slot_flags))
return 0
- switch(slot)
- if(slot_l_hand)
- if(H.l_hand)
- return 0
- return 1
- if(slot_r_hand)
- if(H.r_hand)
- return 0
- return 1
- if(slot_wear_mask)
- if(H.wear_mask)
- return 0
- if(H.head && !(H.head.canremove) && (H.head.flags & HEADCOVERSMOUTH))
- if(!disable_warning)
- H << "\The [H.head] is in the way."
- return 0
- if( !(slot_flags & SLOT_MASK) )
- return 0
- return 1
- if(slot_back)
- if(H.back)
- return 0
- if( !(slot_flags & SLOT_BACK) )
- return 0
- return 1
- if(slot_wear_suit)
- if(H.wear_suit)
- return 0
- if( !(slot_flags & SLOT_OCLOTHING) )
- return 0
- return 1
- if(slot_gloves)
- if(H.gloves)
- return 0
- if( !(slot_flags & SLOT_GLOVES) )
- return 0
- return 1
- if(slot_shoes)
- if(H.shoes)
- return 0
- if( !(slot_flags & SLOT_FEET) )
- return 0
- return 1
- if(slot_belt)
- if(H.belt)
- return 0
- if(!H.w_uniform && (slot_w_uniform in mob_equip))
- if(!disable_warning)
- H << "You need a jumpsuit before you can attach this [name]."
- return 0
- if( !(slot_flags & SLOT_BELT) )
- return
- return 1
- if(slot_glasses)
- if(H.glasses)
- return 0
- if(H.head && !(H.head.canremove) && (H.head.flags & HEADCOVERSEYES))
- if(!disable_warning)
- H << "\The [H.head] is in the way."
- return 0
- if( !(slot_flags & SLOT_EYES) )
- return 0
- return 1
- if(slot_head)
- if(H.head)
- return 0
- if( !(slot_flags & SLOT_HEAD) )
- return 0
- return 1
- if(slot_l_ear)
- if(H.l_ear)
- return 0
- if( (w_class > 1) && !(slot_flags & SLOT_EARS) )
- return 0
- if( (slot_flags & SLOT_TWOEARS) && H.r_ear )
- return 0
- return 1
- if(slot_r_ear)
- if(H.r_ear)
- return 0
- if( (w_class > 1) && !(slot_flags & SLOT_EARS) )
- return 0
- if( (slot_flags & SLOT_TWOEARS) && H.l_ear )
- return 0
- return 1
- if(slot_w_uniform)
- if(H.w_uniform)
- return 0
- if(H.wear_suit && (H.wear_suit.body_parts_covered & src.body_parts_covered))
- if(!disable_warning)
- H << "\The [H.wear_suit] is in the way."
- return 0
- if( !(slot_flags & SLOT_ICLOTHING) )
- return 0
- return 1
- if(slot_wear_id)
- if(H.wear_id)
- return 0
- if(!H.w_uniform && (slot_w_uniform in mob_equip))
- if(!disable_warning)
- H << "You need a jumpsuit before you can attach this [name]."
- return 0
- if( !(slot_flags & SLOT_ID) )
- return 0
- return 1
- if(slot_l_store)
- if(H.l_store)
- return 0
- if(!H.w_uniform && (slot_w_uniform in mob_equip))
- if(!disable_warning)
- H << "You need a jumpsuit before you can attach this [name]."
- return 0
- if(slot_flags & SLOT_DENYPOCKET)
- return 0
- if( w_class <= 2 || (slot_flags & SLOT_POCKET) )
- return 1
- if(slot_r_store)
- if(H.r_store)
- return 0
- if(!H.w_uniform && (slot_w_uniform in mob_equip))
- if(!disable_warning)
- H << "You need a jumpsuit before you can attach this [name]."
- return 0
- if(slot_flags & SLOT_DENYPOCKET)
- return 0
- if( w_class <= 2 || (slot_flags & SLOT_POCKET) )
- return 1
+ //Next check that the slot is free
+ if(H.get_equipped_item(slot))
+ return 0
+
+ //Next check if the slot is accessible.
+ var/mob/_user = disable_warning? null : H
+ if(!H.slot_is_accessible(slot, src, _user))
+ return 0
+
+ //Lastly, check special rules for the desired slot.
+ switch(slot)
+ if(slot_l_ear, slot_r_ear)
+ var/slot_other_ear = (slot == slot_l_ear)? slot_r_ear : slot_l_ear
+ if( (w_class > 1) && !(slot_flags & SLOT_EARS) )
return 0
- if(slot_s_store)
- if(H.s_store)
- return 0
- if(!H.wear_suit && (slot_wear_suit in mob_equip))
- if(!disable_warning)
- H << "You need a suit before you can attach this [name]."
- return 0
- if(!H.wear_suit.allowed)
- if(!disable_warning)
- usr << "You somehow have a suit with no defined allowed items for suit storage, stop that."
- return 0
- if( istype(src, /obj/item/device/pda) || istype(src, /obj/item/weapon/pen) || is_type_in_list(src, H.wear_suit.allowed) )
- return 1
+ if( (slot_flags & SLOT_TWOEARS) && H.get_equipped_item(slot_other_ear) )
return 0
- if(slot_handcuffed)
- if(H.handcuffed)
- return 0
- if(!istype(src, /obj/item/weapon/handcuffs))
- return 0
- return 1
- if(slot_legcuffed)
- if(H.legcuffed)
- return 0
- if(!istype(src, /obj/item/weapon/legcuffs))
- return 0
- return 1
- if(slot_in_backpack)
- if (H.back && istype(H.back, /obj/item/weapon/storage/backpack))
- var/obj/item/weapon/storage/backpack/B = H.back
- if(B.contents.len < B.storage_slots && w_class <= B.max_w_class)
- return 1
+ if(slot_wear_id)
+ if(!H.w_uniform && (slot_w_uniform in mob_equip))
+ if(!disable_warning)
+ H << "You need a jumpsuit before you can attach this [name]."
return 0
- if(slot_tie)
- if(!H.w_uniform && (slot_w_uniform in mob_equip))
- if(!disable_warning)
- H << "You need a jumpsuit before you can attach this [name]."
- return 0
- var/obj/item/clothing/under/uniform = H.w_uniform
- if(uniform.accessories.len && !uniform.can_attach_accessory(src))
- if (!disable_warning)
- H << "You already have an accessory of this type attached to your [uniform]."
- return 0
- if( !(slot_flags & SLOT_TIE) )
- return 0
- return 1
- return 0 //Unsupported slot
- //END HUMAN
+ if(slot_l_store, slot_r_store)
+ if(!H.w_uniform && (slot_w_uniform in mob_equip))
+ if(!disable_warning)
+ H << "You need a jumpsuit before you can attach this [name]."
+ return 0
+ if(slot_flags & SLOT_DENYPOCKET)
+ return 0
+ if( w_class > 2 && !(slot_flags & SLOT_POCKET) )
+ return 0
+ if(slot_s_store)
+ if(!H.wear_suit && (slot_wear_suit in mob_equip))
+ if(!disable_warning)
+ H << "You need a suit before you can attach this [name]."
+ return 0
+ if(!H.wear_suit.allowed)
+ if(!disable_warning)
+ usr << "You somehow have a suit with no defined allowed items for suit storage, stop that."
+ return 0
+ if( !(istype(src, /obj/item/device/pda) || istype(src, /obj/item/weapon/pen) || is_type_in_list(src, H.wear_suit.allowed)) )
+ return 0
+ if(slot_handcuffed)
+ if(!istype(src, /obj/item/weapon/handcuffs))
+ return 0
+ if(slot_legcuffed)
+ if(!istype(src, /obj/item/weapon/legcuffs))
+ return 0
+ if(slot_in_backpack) //used entirely for equipping spawned mobs or at round start
+ var/allow = 0
+ if(H.back && istype(H.back, /obj/item/weapon/storage/backpack))
+ var/obj/item/weapon/storage/backpack/B = H.back
+ if(B.contents.len < B.storage_slots && w_class <= B.max_w_class)
+ allow = 1
+ if(!allow)
+ return 0
+ if(slot_tie)
+ if(!H.w_uniform && (slot_w_uniform in mob_equip))
+ if(!disable_warning)
+ H << "You need a jumpsuit before you can attach this [name]."
+ return 0
+ var/obj/item/clothing/under/uniform = H.w_uniform
+ if(uniform.accessories.len && !uniform.can_attach_accessory(src))
+ if (!disable_warning)
+ H << "You already have an accessory of this type attached to your [uniform]."
+ return 0
+ return 1
+
+/obj/item/proc/mob_can_unequip(mob/M, slot, disable_warning = 0)
+ if(!slot) return 0
+ if(!M) return 0
+
+ if(!canremove)
+ return 0
+ if(!M.slot_is_accessible(slot, src, disable_warning? null : M))
+ return 0
+ return 1
/obj/item/verb/verb_pickup()
set src in oview(1)
@@ -670,4 +600,8 @@ modules/mob/living/carbon/human/life.dm if you die, you will be zoomed out.
if(!cannotzoom)
usr.visible_message("[zoomdevicename ? "[usr] looks up from the [src.name]" : "[usr] lowers the [src.name]"].")
- return
\ No newline at end of file
+ return
+
+
+/obj/item/proc/pwr_drain()
+ return 0 // Process Kill
\ No newline at end of file
diff --git a/code/game/objects/items/apc_frame.dm b/code/game/objects/items/apc_frame.dm
index a11b326e455..208a2111da1 100644
--- a/code/game/objects/items/apc_frame.dm
+++ b/code/game/objects/items/apc_frame.dm
@@ -11,7 +11,7 @@
..()
if (istype(W, /obj/item/weapon/wrench))
new /obj/item/stack/sheet/metal( get_turf(src.loc), 2 )
- del(src)
+ qdel(src)
/obj/item/apc_frame/proc/try_build(turf/on_wall)
if (get_dist(on_wall,usr)>1)
@@ -38,6 +38,6 @@
var/obj/item/stack/cable_coil/C = new /obj/item/stack/cable_coil(loc)
C.amount = 10
usr << "You cut the cables and disassemble the unused power terminal."
- del(T)
+ qdel(T)
new /obj/machinery/power/apc(loc, ndir, 1)
- del(src)
+ qdel(src)
diff --git a/code/game/objects/items/ashtray.dm b/code/game/objects/items/ashtray.dm
index 0d386623ecd..abb6adb48db 100644
--- a/code/game/objects/items/ashtray.dm
+++ b/code/game/objects/items/ashtray.dm
@@ -31,7 +31,7 @@
processing_objects.Remove(cig)
var/obj/item/butt = new cig.type_butt(src)
cig.transfer_fingerprints_to(butt)
- del(cig)
+ qdel(cig)
W = butt
else if (cig.lit == 0)
user << "You place [cig] in [src] without even smoking it. Why would you do that?"
@@ -82,7 +82,7 @@
icon_broken = "ashtray_bork_bl"
max_butts = 14
health = 24.0
- matter = list("metal" = 30,"glass" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 30)
empty_desc = "Cheap plastic ashtray."
throwforce = 3.0
die()
@@ -102,7 +102,7 @@
icon_broken = "ashtray_bork_br"
max_butts = 10
health = 72.0
- matter = list("metal" = 80)
+ matter = list(DEFAULT_WALL_MATERIAL = 80)
empty_desc = "Massive bronze ashtray."
throwforce = 10.0
diff --git a/code/game/objects/items/blueprints.dm b/code/game/objects/items/blueprints.dm
index facafe41f25..9ec1a2e144d 100644
--- a/code/game/objects/items/blueprints.dm
+++ b/code/game/objects/items/blueprints.dm
@@ -76,7 +76,6 @@ move an amendment to the drawing.
/obj/item/blueprints/proc/get_area()
var/turf/T = get_turf(usr)
var/area/A = T.loc
- A = A.master
return A
/obj/item/blueprints/proc/get_area_type(var/area/A = get_area())
@@ -122,7 +121,6 @@ move an amendment to the drawing.
return
var/area/A = new
A.name = str
- A.tagbase = "[A.type]_[md5(str)]" // without this dynamic light system ruin everithing
//var/ma
//ma = A.master ? "[A.master]" : "(null)"
//world << "DEBUG: create_area: A.name=[A.name] A.tag=[A.tag] A.master=[ma]"
@@ -133,9 +131,6 @@ move an amendment to the drawing.
move_turfs_to_area(turfs, A)
A.always_unpowered = 0
- for(var/turf/T in A.contents)
- T.lighting_changed = 1
- lighting_controller.changed_turfs += T
spawn(5)
//ma = A.master ? "[A.master]" : "(null)"
@@ -161,8 +156,7 @@ move an amendment to the drawing.
usr << "\red Text too long."
return
set_area_machinery_title(A,str,prevname)
- for(var/area/RA in A.related)
- RA.name = str
+ A.name = str
usr << "\blue You set the area '[prevname]' title to '[str]'."
interact()
return
@@ -172,17 +166,17 @@ move an amendment to the drawing.
/obj/item/blueprints/proc/set_area_machinery_title(var/area/A,var/title,var/oldtitle)
if (!oldtitle) // or replacetext goes to infinite loop
return
- for(var/area/RA in A.related)
- for(var/obj/machinery/alarm/M in RA)
- M.name = replacetext(M.name,oldtitle,title)
- for(var/obj/machinery/power/apc/M in RA)
- M.name = replacetext(M.name,oldtitle,title)
- for(var/obj/machinery/atmospherics/unary/vent_scrubber/M in RA)
- M.name = replacetext(M.name,oldtitle,title)
- for(var/obj/machinery/atmospherics/unary/vent_pump/M in RA)
- M.name = replacetext(M.name,oldtitle,title)
- for(var/obj/machinery/door/M in RA)
- M.name = replacetext(M.name,oldtitle,title)
+
+ for(var/obj/machinery/alarm/M in A)
+ M.name = replacetext(M.name,oldtitle,title)
+ for(var/obj/machinery/power/apc/M in A)
+ M.name = replacetext(M.name,oldtitle,title)
+ for(var/obj/machinery/atmospherics/unary/vent_scrubber/M in A)
+ M.name = replacetext(M.name,oldtitle,title)
+ for(var/obj/machinery/atmospherics/unary/vent_pump/M in A)
+ M.name = replacetext(M.name,oldtitle,title)
+ for(var/obj/machinery/door/M in A)
+ M.name = replacetext(M.name,oldtitle,title)
//TODO: much much more. Unnamed airlocks, cameras, etc.
/obj/item/blueprints/proc/check_tile_is_border(var/turf/T2,var/dir)
@@ -207,10 +201,6 @@ move an amendment to the drawing.
return BORDER_BETWEEN
if (locate(/obj/machinery/door) in T2)
return BORDER_2NDTILE
- if (locate(/obj/structure/falsewall) in T2)
- return BORDER_2NDTILE
- if (locate(/obj/structure/falserwall) in T2)
- return BORDER_2NDTILE
return BORDER_NONE
@@ -247,4 +237,4 @@ move an amendment to the drawing.
if(BORDER_SPACE)
return ROOM_ERR_SPACE
found+=T
- return found
\ No newline at end of file
+ return found
diff --git a/code/game/objects/items/bodybag.dm b/code/game/objects/items/bodybag.dm
index fcbebdba202..8953872d938 100644
--- a/code/game/objects/items/bodybag.dm
+++ b/code/game/objects/items/bodybag.dm
@@ -10,7 +10,7 @@
attack_self(mob/user)
var/obj/structure/closet/body_bag/R = new /obj/structure/closet/body_bag(user.loc)
R.add_fingerprint(user)
- del(src)
+ qdel(src)
/obj/item/weapon/storage/box/bodybags
@@ -49,7 +49,7 @@
return
if (!in_range(src, user) && src.loc != user)
return
- t = sanitize(t)
+ t = sanitizeSafe(t, MAX_NAME_LEN)
if (t)
src.name = "body bag - "
src.name += t
@@ -83,7 +83,7 @@
visible_message("[usr] folds up the [src.name]")
new item_path(get_turf(src))
spawn(0)
- del(src)
+ qdel(src)
return
/obj/structure/closet/body_bag/update_icon()
@@ -105,7 +105,7 @@
attack_self(mob/user)
var/obj/structure/closet/body_bag/cryobag/R = new /obj/structure/closet/body_bag/cryobag(user.loc)
R.add_fingerprint(user)
- del(src)
+ qdel(src)
@@ -126,7 +126,7 @@
O.icon = src.icon
O.icon_state = "bodybag_used"
O.desc = "Pretty useless now.."
- del(src)
+ qdel(src)
/obj/structure/closet/body_bag/cryobag/MouseDrop(over_object, src_location, over_location)
if((over_object == usr && (in_range(src, usr) || usr.contents.Find(src))))
diff --git a/code/game/objects/items/crayons.dm b/code/game/objects/items/crayons.dm
index 8e1a382a869..a9a7528994f 100644
--- a/code/game/objects/items/crayons.dm
+++ b/code/game/objects/items/crayons.dm
@@ -1,40 +1,40 @@
-/obj/item/toy/crayon/red
+/obj/item/weapon/pen/crayon/red
icon_state = "crayonred"
colour = "#DA0000"
shadeColour = "#810C0C"
colourName = "red"
-/obj/item/toy/crayon/orange
+/obj/item/weapon/pen/crayon/orange
icon_state = "crayonorange"
colour = "#FF9300"
shadeColour = "#A55403"
colourName = "orange"
-/obj/item/toy/crayon/yellow
+/obj/item/weapon/pen/crayon/yellow
icon_state = "crayonyellow"
colour = "#FFF200"
shadeColour = "#886422"
colourName = "yellow"
-/obj/item/toy/crayon/green
+/obj/item/weapon/pen/crayon/green
icon_state = "crayongreen"
colour = "#A8E61D"
shadeColour = "#61840F"
colourName = "green"
-/obj/item/toy/crayon/blue
+/obj/item/weapon/pen/crayon/blue
icon_state = "crayonblue"
colour = "#00B7EF"
shadeColour = "#0082A8"
colourName = "blue"
-/obj/item/toy/crayon/purple
+/obj/item/weapon/pen/crayon/purple
icon_state = "crayonpurple"
colour = "#DA00FF"
shadeColour = "#810CFF"
colourName = "purple"
-/obj/item/toy/crayon/mime
+/obj/item/weapon/pen/crayon/mime
icon_state = "crayonmime"
desc = "A very sad-looking crayon."
colour = "#FFFFFF"
@@ -42,7 +42,7 @@
colourName = "mime"
uses = 0
-/obj/item/toy/crayon/mime/attack_self(mob/living/user as mob) //inversion
+/obj/item/weapon/pen/crayon/mime/attack_self(mob/living/user as mob) //inversion
if(colour != "#FFFFFF" && shadeColour != "#000000")
colour = "#FFFFFF"
shadeColour = "#000000"
@@ -53,19 +53,19 @@
user << "You will now draw in black and white with this crayon."
return
-/obj/item/toy/crayon/rainbow
+/obj/item/weapon/pen/crayon/rainbow
icon_state = "crayonrainbow"
colour = "#FFF000"
shadeColour = "#000FFF"
colourName = "rainbow"
uses = 0
-/obj/item/toy/crayon/rainbow/attack_self(mob/living/user as mob)
+/obj/item/weapon/pen/crayon/rainbow/attack_self(mob/living/user as mob)
colour = input(user, "Please select the main colour.", "Crayon colour") as color
shadeColour = input(user, "Please select the shade colour.", "Crayon colour") as color
return
-/obj/item/toy/crayon/afterattack(atom/target, mob/user as mob, proximity)
+/obj/item/weapon/pen/crayon/afterattack(atom/target, mob/user as mob, proximity)
if(!proximity) return
if(istype(target,/turf/simulated/floor))
var/drawtype = input("Choose what you'd like to draw.", "Crayon scribbles") in list("graffiti","rune","letter")
@@ -85,10 +85,10 @@
uses--
if(!uses)
user << "\red You used up your crayon!"
- del(src)
+ qdel(src)
return
-/obj/item/toy/crayon/attack(mob/M as mob, mob/user as mob)
+/obj/item/weapon/pen/crayon/attack(mob/M as mob, mob/user as mob)
if(M == user)
user << "You take a bite of the crayon and swallow it."
user.nutrition += 1
@@ -97,6 +97,6 @@
uses -= 5
if(uses <= 0)
user << "\red You ate your crayon!"
- del(src)
+ qdel(src)
else
..()
diff --git a/code/game/objects/items/devices/PDA/PDA.dm b/code/game/objects/items/devices/PDA/PDA.dm
old mode 100755
new mode 100644
index 87f7b0fd8a6..c9082672445
--- a/code/game/objects/items/devices/PDA/PDA.dm
+++ b/code/game/objects/items/devices/PDA/PDA.dm
@@ -308,15 +308,6 @@ var/global/list/obj/item/device/pda/PDAs = list()
/*
* The Actual PDA
*/
-/obj/item/device/pda/pickup(mob/user)
- if(fon)
- SetLuminosity(0)
- user.SetLuminosity(user.luminosity + f_lum)
-
-/obj/item/device/pda/dropped(mob/user)
- if(fon)
- user.SetLuminosity(user.luminosity - f_lum)
- SetLuminosity(f_lum)
/obj/item/device/pda/New()
..()
@@ -532,21 +523,19 @@ var/global/list/obj/item/device/pda/PDAs = list()
data["feed"] = feed
+ data["manifest"] = list("__json_cache" = ManifestJSON)
+
nanoUI = data
// update the ui if it exists, returns null if no ui is passed/found
- if(ui)
- ui.load_cached_data(ManifestJSON)
ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open)
if (!ui)
// the ui does not exist, so we'll create a new() one
// for a list of parameters and their descriptions see the code docs in \code\modules\nano\nanoui.dm
- ui = new(user, src, ui_key, "pda.tmpl", title, 520, 400)
+ ui = new(user, src, ui_key, "pda.tmpl", title, 520, 400, state = inventory_state)
// when the ui is first opened this is the data it will use
- ui.load_cached_data(ManifestJSON)
-
ui.set_initial_data(data)
// open the new ui window
ui.open()
@@ -617,16 +606,7 @@ var/global/list/obj/item/device/pda/PDAs = list()
ownrank = id.rank
name = "PDA-[owner] ([ownjob])"
if("Eject")//Ejects the cart, only done from hub.
- if (!isnull(cartridge))
- var/turf/T = loc
- if(ismob(T))
- T = T.loc
- cartridge.loc = T
- mode = 0
- scanmode = 0
- if (cartridge.radio)
- cartridge.radio.hostpda = null
- cartridge = null
+ verb_remove_cartridge()
//MENU FUNCTIONS===================================
@@ -653,12 +633,10 @@ var/global/list/obj/item/device/pda/PDAs = list()
if("Light")
if(fon)
fon = 0
- if(src in U.contents) U.SetLuminosity(U.luminosity - f_lum)
- else SetLuminosity(0)
+ set_light(0)
else
fon = 1
- if(src in U.contents) U.SetLuminosity(U.luminosity + f_lum)
- else SetLuminosity(f_lum)
+ set_light(f_lum)
if("Medical Scan")
if(scanmode == 1)
scanmode = 0
@@ -825,7 +803,8 @@ var/global/list/obj/item/device/pda/PDAs = list()
difficulty += P.cartridge.access_engine
difficulty += P.cartridge.access_clown
difficulty += P.cartridge.access_janitor
- difficulty += 3 * P.hidden_uplink
+ if(P.hidden_uplink)
+ difficulty += 3
if(prob(difficulty))
U.show_message("\red An error flashes on your [src].", 1)
@@ -946,7 +925,7 @@ var/global/list/obj/item/device/pda/PDAs = list()
j = prob(10)
if(j) //This kills the PDA
- P.Del()
+ qdel(P)
if(message)
message += "It melts in a puddle of plastic."
else
@@ -1119,6 +1098,30 @@ var/global/list/obj/item/device/pda/PDAs = list()
else
usr << "You cannot do this while restrained."
+/obj/item/device/pda/verb/verb_remove_cartridge()
+ set category = "Object"
+ set name = "Remove cartridge"
+ set src in usr
+
+ if(issilicon(usr))
+ return
+
+ if (can_use(usr) && !isnull(cartridge))
+ var/turf/T = get_turf(src)
+ cartridge.loc = T
+ if (ismob(loc))
+ var/mob/M = loc
+ M.put_in_hands(cartridge)
+ else
+ cartridge.loc = get_turf(src)
+ mode = 0
+ scanmode = 0
+ if (cartridge.radio)
+ cartridge.radio.hostpda = null
+ cartridge = null
+ usr << "You remove \the [cartridge] from the [name]."
+ else
+ usr << "You cannot do this while restrained."
/obj/item/device/pda/proc/id_check(mob/user as mob, choice as num)//To check for IDs; 1 for in-pda use, 2 for out of pda use.
if(choice == 1)
@@ -1224,7 +1227,7 @@ var/global/list/obj/item/device/pda/PDAs = list()
if ( !(C:blood_DNA) )
user << "\blue No blood found on [C]"
if(C:blood_DNA)
- del(C:blood_DNA)
+ qdel(C:blood_DNA)
else
user << "\blue Blood found on [C]. Analysing..."
spawn(15)
@@ -1354,7 +1357,7 @@ var/global/list/obj/item/device/pda/PDAs = list()
explosion(T, 0, 0, 1, rand(1,2))
return
-/obj/item/device/pda/Del()
+/obj/item/device/pda/Destroy()
PDAs -= src
if (src.id && prob(90)) //IDs are kept in 90% of the cases
src.id.loc = get_turf(src.loc)
diff --git a/code/game/objects/items/devices/PDA/cart.dm b/code/game/objects/items/devices/PDA/cart.dm
index 5ab09d08539..2c91285e084 100644
--- a/code/game/objects/items/devices/PDA/cart.dm
+++ b/code/game/objects/items/devices/PDA/cart.dm
@@ -58,10 +58,9 @@
icon_state = "cart-s"
access_security = 1
-/obj/item/weapon/cartridge/security/New()
+/obj/item/weapon/cartridge/security/initialize()
+ radio = new /obj/item/radio/integrated/beepsky(src)
..()
- spawn(5)
- radio = new /obj/item/radio/integrated/beepsky(src)
/obj/item/weapon/cartridge/detective
name = "\improper D.E.T.E.C.T. cartridge"
@@ -102,6 +101,7 @@
/obj/item/weapon/cartridge/signal
name = "generic signaler cartridge"
desc = "A data cartridge with an integrated radio signaler module."
+ var/qdeled = 0
/obj/item/weapon/cartridge/signal/science
name = "\improper Signal Ace 2 cartridge"
@@ -110,12 +110,13 @@
access_reagent_scanner = 1
access_atmos = 1
-/obj/item/weapon/cartridge/signal/New()
+/obj/item/weapon/cartridge/signal/initialize()
+ radio = new /obj/item/radio/integrated/signal(src)
+ ..()
+
+/obj/item/weapon/cartridge/signal/Destroy()
+ qdel(radio)
..()
- spawn(5)
- radio = new /obj/item/radio/integrated/signal(src)
-
-
/obj/item/weapon/cartridge/quartermaster
name = "\improper Space Parts & Space Vendors cartridge"
@@ -123,10 +124,9 @@
icon_state = "cart-q"
access_quartermaster = 1
-/obj/item/weapon/cartridge/quartermaster/New()
+/obj/item/weapon/cartridge/quartermaster/initialize()
+ radio = new /obj/item/radio/integrated/mule(src)
..()
- spawn(5)
- radio = new /obj/item/radio/integrated/mule(src)
/obj/item/weapon/cartridge/head
name = "\improper Easy-Record DELUXE"
@@ -141,10 +141,8 @@
access_janitor = 1
access_security = 1
-/obj/item/weapon/cartridge/hop/New()
- ..()
- spawn(5)
- radio = new /obj/item/radio/integrated/mule(src)
+/obj/item/weapon/cartridge/hop/initialize()
+ radio = new /obj/item/radio/integrated/mule(src)
/obj/item/weapon/cartridge/hos
name = "\improper R.O.B.U.S.T. DELUXE"
@@ -152,10 +150,9 @@
access_status_display = 1
access_security = 1
-/obj/item/weapon/cartridge/hos/New()
+/obj/item/weapon/cartridge/hos/initialize()
+ radio = new /obj/item/radio/integrated/beepsky(src)
..()
- spawn(5)
- radio = new /obj/item/radio/integrated/beepsky(src)
/obj/item/weapon/cartridge/ce
name = "\improper Power-On DELUXE"
@@ -178,10 +175,9 @@
access_reagent_scanner = 1
access_atmos = 1
-/obj/item/weapon/cartridge/rd/New()
+/obj/item/weapon/cartridge/rd/initialize()
+ radio = new /obj/item/radio/integrated/signal(src)
..()
- spawn(5)
- radio = new /obj/item/radio/integrated/signal(src)
/obj/item/weapon/cartridge/captain
name = "\improper Value-PAK cartridge"
@@ -331,7 +327,7 @@
beepskyData["botstatus"] = list("loca" = null, "mode" = -1)
var/botsCount=0
if(SC.botlist && SC.botlist.len)
- for(var/obj/machinery/bot/B in SC.botlist)
+ for(var/mob/living/bot/B in SC.botlist)
botsCount++
if(B.loc)
botsData[++botsData.len] = list("Name" = sanitize(B.name), "Location" = sanitize(B.loc.loc.name), "ref" = "\ref[B]")
@@ -465,7 +461,7 @@
BucketData[++BucketData.len] = list("x" = 0, "y" = 0, dir=null, status = null)
var/CbotData[0]
- for(var/obj/machinery/bot/cleanbot/B in world)
+ for(var/mob/living/bot/cleanbot/B in world)
var/turf/bl = get_turf(B)
if(bl)
if(bl.z != cl.z)
diff --git a/code/game/objects/items/devices/PDA/radio.dm b/code/game/objects/items/devices/PDA/radio.dm
index 0c7105118fb..c4fb3855369 100644
--- a/code/game/objects/items/devices/PDA/radio.dm
+++ b/code/game/objects/items/devices/PDA/radio.dm
@@ -37,7 +37,7 @@
/obj/item/radio/integrated/beepsky
var/list/botlist = null // list of bots
- var/obj/machinery/bot/secbot/active // the active bot; if null, show bot list
+ var/mob/living/bot/secbot/active // the active bot; if null, show bot list
var/list/botstatus // the status signal sent by the bot
var/control_freq = AI_FREQ
@@ -99,6 +99,12 @@
post_signal(control_freq, "command", "summon", "active", active, "target", get_turf(PDA) , s_filter = RADIO_SECBOT)
post_signal(control_freq, "command", "bot_status", "active", active, s_filter = RADIO_SECBOT)
+
+/obj/item/radio/integrated/beepsky/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, control_freq)
+ ..()
+
/obj/item/radio/integrated/mule
var/list/botlist = null // list of bots
var/obj/machinery/bot/mulebot/active // the active bot; if null, show bot list
@@ -211,12 +217,10 @@
var/last_transmission
var/datum/radio_frequency/radio_connection
- New()
- ..()
- if(radio_controller)
- initialize()
-
initialize()
+ if(!radio_controller)
+ return
+
if (src.frequency < 1441 || src.frequency > 1489)
src.frequency = sanitize_frequency(src.frequency)
@@ -245,3 +249,8 @@
radio_connection.post_signal(src, signal)
return
+
+/obj/item/radio/integrated/signal/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src, frequency)
+ ..()
diff --git a/code/game/objects/items/devices/chameleonproj.dm b/code/game/objects/items/devices/chameleonproj.dm
index 6ddb3716f60..cdefd61d57c 100644
--- a/code/game/objects/items/devices/chameleonproj.dm
+++ b/code/game/objects/items/devices/chameleonproj.dm
@@ -41,25 +41,25 @@
if(active_dummy)
eject_all()
playsound(get_turf(src), 'sound/effects/pop.ogg', 100, 1, -6)
- del(active_dummy)
+ qdel(active_dummy)
active_dummy = null
usr << "\blue You deactivate the [src]."
- var/obj/effect/overlay/T = new/obj/effect/overlay(get_turf(src))
+ var/obj/effect/overlay/T = PoolOrNew(/obj/effect/overlay, get_turf(src))
T.icon = 'icons/effects/effects.dmi'
flick("emppulse",T)
- spawn(8) T.delete()
+ spawn(8) qdel(T)
else
playsound(get_turf(src), 'sound/effects/pop.ogg', 100, 1, -6)
var/obj/O = new saved_item(src)
if(!O) return
- var/obj/effect/dummy/chameleon/C = new/obj/effect/dummy/chameleon(usr.loc)
+ var/obj/effect/dummy/chameleon/C = PoolOrNew(/obj/effect/dummy/chameleon, usr.loc)
C.activate(O, usr, saved_icon, saved_icon_state, saved_overlays, src)
- del(O)
+ qdel(O)
usr << "\blue You activate the [src]."
var/obj/effect/overlay/T = new/obj/effect/overlay(get_turf(src))
T.icon = 'icons/effects/effects.dmi'
flick("emppulse",T)
- spawn(8) T.delete()
+ spawn(8) qdel(T)
/obj/item/device/chameleon/proc/disrupt(var/delete_dummy = 1)
if(active_dummy)
@@ -69,7 +69,7 @@
spark_system.start()
eject_all()
if(delete_dummy)
- del(active_dummy)
+ qdel(active_dummy)
active_dummy = null
can_use = 0
spawn(50) can_use = 1
@@ -140,6 +140,6 @@
step(src, direction)
return
-/obj/effect/dummy/chameleon/Del()
+/obj/effect/dummy/chameleon/Destroy()
master.disrupt(0)
..()
diff --git a/code/game/objects/items/devices/debugger.dm b/code/game/objects/items/devices/debugger.dm
index 162f133a7a1..1bf02f8c9f6 100644
--- a/code/game/objects/items/devices/debugger.dm
+++ b/code/game/objects/items/devices/debugger.dm
@@ -17,7 +17,7 @@
throw_speed = 3
desc = "You can use this on airlocks or APCs to try to hack them without cutting wires."
- matter = list("metal" = 50,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
origin_tech = list(TECH_MAGNET = 1, TECH_ENGINERING = 1)
var/obj/machinery/telecomms/buffer // simple machine buffer for device linkage
diff --git a/code/game/objects/items/devices/flash.dm b/code/game/objects/items/devices/flash.dm
index 375a0a5af1b..2c686f8bf30 100644
--- a/code/game/objects/items/devices/flash.dm
+++ b/code/game/objects/items/devices/flash.dm
@@ -103,7 +103,7 @@
animation.master = user
flick("blspell", animation)
sleep(5)
- del(animation)
+ qdel(animation)
if(!flashfail)
flick("flash2", src)
@@ -154,7 +154,7 @@
animation.master = user
flick("blspell", animation)
sleep(5)
- del(animation)
+ qdel(animation)
for(var/mob/living/carbon/M in oviewers(3, null))
if(prob(50))
@@ -192,9 +192,9 @@
/obj/item/device/flash/synthetic
name = "synthetic flash"
desc = "When a problem arises, SCIENCE is the solution."
- icon_state = "sflash"
+ icon_state = "sflash"
origin_tech = list(TECH_MAGNET = 2, TECH_COMBAT = 1)
- var/construction_cost = list("metal"=750,"glass"=750)
+ var/construction_cost = list(DEFAULT_WALL_MATERIAL=750,"glass"=750)
var/construction_time=100
/obj/item/device/flash/synthetic/attack(mob/living/M as mob, mob/user as mob)
diff --git a/code/game/objects/items/devices/flashlight.dm b/code/game/objects/items/devices/flashlight.dm
index fb3edec8732..29bcbc43328 100644
--- a/code/game/objects/items/devices/flashlight.dm
+++ b/code/game/objects/items/devices/flashlight.dm
@@ -8,7 +8,7 @@
flags = CONDUCT
slot_flags = SLOT_BELT
- matter = list("metal" = 50,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
icon_action_button = "action_flashlight"
var/on = 0
@@ -18,24 +18,17 @@
..()
if(on)
icon_state = "[initial(icon_state)]-on"
- SetLuminosity(brightness_on)
+ set_light(brightness_on)
else
icon_state = initial(icon_state)
- SetLuminosity(0)
+ set_light(0)
/obj/item/device/flashlight/proc/update_brightness(var/mob/user = null)
if(on)
icon_state = "[initial(icon_state)]-on"
- if(loc == user)
- user.SetLuminosity(user.luminosity + brightness_on)
- else if(isturf(loc))
- SetLuminosity(brightness_on)
+ set_light(brightness_on)
else
- icon_state = initial(icon_state)
- if(loc == user)
- user.SetLuminosity(user.luminosity - brightness_on)
- else if(isturf(loc))
- SetLuminosity(0)
+ set_light(0)
/obj/item/device/flashlight/attack_self(mob/user)
if(!isturf(user.loc))
@@ -88,19 +81,6 @@
else
return ..()
-
-/obj/item/device/flashlight/pickup(mob/user)
- if(on)
- user.SetLuminosity(user.luminosity + brightness_on)
- SetLuminosity(0)
-
-
-/obj/item/device/flashlight/dropped(mob/user)
- if(on)
- user.SetLuminosity(user.luminosity - brightness_on)
- SetLuminosity(brightness_on)
-
-
/obj/item/device/flashlight/pen
name = "penlight"
desc = "A pen-sized light, used by medical staff."
@@ -139,7 +119,7 @@
icon_state = "lampgreen"
item_state = "lampgreen"
brightness_on = 5
-
+ light_color = "#FFC58F"
/obj/item/device/flashlight/lamp/verb/toggle_light()
set name = "Toggle light"
@@ -156,6 +136,7 @@
desc = "A red Nanotrasen issued flare. There are instructions on the side, it reads 'pull cord, make light'."
w_class = 2.0
brightness_on = 7 // Pretty bright.
+ light_color = "#e58775"
icon_state = "flare"
item_state = "flare"
icon_action_button = null //just pull it manually, neckbeard.
@@ -217,7 +198,7 @@
on = 1 //Bio-luminesence has one setting, on.
/obj/item/device/flashlight/slime/New()
- SetLuminosity(brightness_on)
+ set_light(brightness_on)
spawn(1) //Might be sloppy, but seems to be necessary to prevent further runtimes and make these work as intended... don't judge me!
update_brightness()
icon_state = initial(icon_state)
diff --git a/code/game/objects/items/devices/floor_painter.dm b/code/game/objects/items/devices/floor_painter.dm
index 27b4054fa5e..a1c21a7b3fc 100644
--- a/code/game/objects/items/devices/floor_painter.dm
+++ b/code/game/objects/items/devices/floor_painter.dm
@@ -97,6 +97,10 @@
mode = "white"
mode_nice = "white"
return
+ if(design == "dark")
+ mode = "dark"
+ mode_nice = "dark"
+ return
if(design == "showroom" || design == "hydro" || design == "freezer")
mode = "[design]floor"
mode_nice = design
@@ -135,9 +139,9 @@
mode_nice = design
mode = "whitebluegreencorners"
tile_dir_mode = 2
- else if(design == "delivery" || design == "bot")
+ else if(design == "delivery" || design == "bot" || design == "white-delivery" || design == "white-bot")
mode_nice = design
- mode = design
+ mode = replacetext(design, "-", "")
tile_dir_mode = 0
else if(design == "loadingarea")
mode_nice = design
diff --git a/code/game/objects/items/devices/lightreplacer.dm b/code/game/objects/items/devices/lightreplacer.dm
index 73cdd523172..19627e23636 100644
--- a/code/game/objects/items/devices/lightreplacer.dm
+++ b/code/game/objects/items/devices/lightreplacer.dm
@@ -90,7 +90,7 @@
AddUses(1)
user << "You insert the [L.name] into the [src.name]. You have [uses] lights remaining."
user.drop_item()
- del(L)
+ qdel(L)
return
else
user << "You need a working light."
@@ -140,7 +140,9 @@
var/obj/item/weapon/light/L1 = new target.light_type(target.loc)
L1.status = target.status
L1.rigged = target.rigged
- L1.brightness = target.brightness
+ L1.brightness_range = target.brightness_range
+ L1.brightness_power = target.brightness_power
+ L1.brightness_color = target.brightness_color
L1.switchcount = target.switchcount
target.switchcount = 0
L1.update()
@@ -153,10 +155,12 @@
target.status = L2.status
target.switchcount = L2.switchcount
target.rigged = emagged
- target.brightness = L2.brightness
+ target.brightness_range = L2.brightness_range
+ target.brightness_power = L2.brightness_power
+ target.brightness_color = L2.brightness_color
target.on = target.has_power()
target.update()
- del(L2)
+ qdel(L2)
if(target.on && target.rigged)
target.explode()
diff --git a/code/game/objects/items/devices/modkit.dm b/code/game/objects/items/devices/modkit.dm
index 8788eaf0f2a..4207546b031 100644
--- a/code/game/objects/items/devices/modkit.dm
+++ b/code/game/objects/items/devices/modkit.dm
@@ -24,7 +24,7 @@
if(!parts)
user << "This kit has no parts for this modification left."
user.drop_from_inventory(src)
- del(src)
+ qdel(src)
return
var/allowed = 0
@@ -60,7 +60,7 @@
if(!parts)
user.drop_from_inventory(src)
- del(src)
+ qdel(src)
/obj/item/device/modkit/examine(mob/user)
..(user)
diff --git a/code/game/objects/items/devices/multitool.dm b/code/game/objects/items/devices/multitool.dm
index 210ff15cd98..e7b1c755145 100644
--- a/code/game/objects/items/devices/multitool.dm
+++ b/code/game/objects/items/devices/multitool.dm
@@ -16,7 +16,7 @@
throw_speed = 3
desc = "You can use this on airlocks or APCs to try to hack them without cutting wires."
- matter = list("metal" = 50,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 50,"glass" = 20)
origin_tech = list(TECH_MAGNET = 1, TECH_ENGINERING = 1)
var/obj/machinery/telecomms/buffer // simple machine buffer for device linkage
diff --git a/code/game/objects/items/devices/paicard.dm b/code/game/objects/items/devices/paicard.dm
index 4a9510a1530..d60390b84da 100644
--- a/code/game/objects/items/devices/paicard.dm
+++ b/code/game/objects/items/devices/paicard.dm
@@ -21,7 +21,7 @@
..()
overlays += "pai-off"
-/obj/item/device/paicard/Del()
+/obj/item/device/paicard/Destroy()
//Will stop people throwing friend pAIs into the singularity so they can respawn
if(!isnull(pai))
pai.death(0)
@@ -296,6 +296,12 @@
if(7) src.overlays += "pai-sad"
if(8) src.overlays += "pai-angry"
if(9) src.overlays += "pai-what"
+ if(10) src.overlays += "pai-neutral"
+ if(11) src.overlays += "pai-silly"
+ if(12) src.overlays += "pai-nose"
+ if(13) src.overlays += "pai-smirk"
+ if(14) src.overlays += "pai-exclamation"
+ if(15) src.overlays += "pai-question"
current_emotion = emotion
/obj/item/device/paicard/proc/alertUpdate()
@@ -311,7 +317,7 @@
if(pai)
pai.ex_act(severity)
else
- del(src)
+ qdel(src)
/obj/item/device/paicard/see_emote(mob/living/M, text)
if(pai && pai.client)
diff --git a/code/game/objects/items/devices/powersink.dm b/code/game/objects/items/devices/powersink.dm
index 7a7057b5766..ad40ecc724c 100644
--- a/code/game/objects/items/devices/powersink.dm
+++ b/code/game/objects/items/devices/powersink.dm
@@ -11,111 +11,122 @@
throw_speed = 1
throw_range = 2
- matter = list("metal" = 750,"waste" = 750)
+ matter = list(DEFAULT_WALL_MATERIAL = 750,"waste" = 750)
origin_tech = list(TECH_POWER = 3, TECH_ILLEGAL = 5)
- var/drain_rate = 1000000 // amount of power to drain per tick
- var/dissipation_rate = 20000
- var/power_drained = 0 // has drained this much power
- var/max_power = 5e9 // maximum power that can be drained before exploding
- var/mode = 0 // 0 = off, 1=clamped (off), 2=operating
-
+ var/drain_rate = 1500000 // amount of power to drain per tick
+ var/apc_drain_rate = 5000 // Max. amount drained from single APC. In Watts.
+ var/dissipation_rate = 20000 // Passive dissipation of drained power. In Watts.
+ var/power_drained = 0 // Amount of power drained.
+ var/max_power = 5e9 // Detonation point.
+ var/mode = 0 // 0 = off, 1=clamped (off), 2=operating
+ var/drained_this_tick = 0 // This is unfortunately necessary to ensure we process powersinks BEFORE other machinery such as APCs.
+ var/datum/powernet/PN // Our powernet
var/obj/structure/cable/attached // the attached cable
- attackby(var/obj/item/I, var/mob/user)
- if(istype(I, /obj/item/weapon/screwdriver))
- if(mode == 0)
- var/turf/T = loc
- if(isturf(T) && !T.intact)
- attached = locate() in T
- if(!attached)
- user << "No exposed cable here to attach to."
- return
- else
- anchored = 1
- mode = 1
- user << "You attach the device to the cable."
- for(var/mob/M in viewers(user))
- if(M == user) continue
- M << "[user] attaches the power sink to the cable."
- return
+/obj/item/device/powersink/Destroy()
+ processing_objects.Remove(src)
+ processing_power_items.Remove(src)
+ ..()
+
+/obj/item/device/powersink/attackby(var/obj/item/I, var/mob/user)
+ if(istype(I, /obj/item/weapon/screwdriver))
+ if(mode == 0)
+ var/turf/T = loc
+ if(isturf(T) && !T.intact)
+ attached = locate() in T
+ if(!attached)
+ user << "No exposed cable here to attach to."
+ return
else
- user << "Device must be placed over an exposed cable to attach to it."
+ anchored = 1
+ mode = 1
+ src.visible_message("[user] attaches [src] to the cable!")
return
else
- if (mode == 2)
- processing_objects.Remove(src) // Now the power sink actually stops draining the station's power if you unhook it. --NeoFite
- anchored = 0
- mode = 0
- user << "You detach the device from the cable."
- for(var/mob/M in viewers(user))
- if(M == user) continue
- M << "[user] detaches the power sink from the cable."
- SetLuminosity(0)
- icon_state = "powersink0"
-
+ user << "Device must be placed over an exposed cable to attach to it."
return
else
+ if (mode == 2)
+ processing_objects.Remove(src) // Now the power sink actually stops draining the station's power if you unhook it. --NeoFite
+ processing_power_items.Remove(src)
+ anchored = 0
+ mode = 0
+ src.visible_message("[user] detaches [src] from the cable!")
+ set_light(0)
+ icon_state = "powersink0"
+
+ return
+ else
+ ..()
+
+/obj/item/device/powersink/attack_ai()
+ return
+
+/obj/item/device/powersink/attack_hand(var/mob/user)
+ switch(mode)
+ if(0)
..()
+ if(1)
+ src.visible_message("[user] activates [src]!")
+ mode = 2
+ icon_state = "powersink1"
+ processing_objects.Add(src)
+ processing_power_items.Add(src)
+ if(2) //This switch option wasn't originally included. It exists now. --NeoFite
+ src.visible_message("[user] deactivates [src]!")
+ mode = 1
+ set_light(0)
+ icon_state = "powersink0"
+ processing_objects.Remove(src)
+ processing_power_items.Remove(src)
- attack_ai()
+/obj/item/device/powersink/pwr_drain()
+ if(!attached)
+ return 0
+
+ if(drained_this_tick)
+ return 1
+ drained_this_tick = 1
+
+ var/drained = 0
+
+ if(!PN)
+ return 1
+
+ set_light(12)
+ PN.trigger_warning()
+ // found a powernet, so drain up to max power from it
+ drained = PN.draw_power(drain_rate)
+ // if tried to drain more than available on powernet
+ // now look for APCs and drain their cells
+ if(drained < drain_rate)
+ for(var/obj/machinery/power/terminal/T in PN.nodes)
+ // Enough power drained this tick, no need to torture more APCs
+ if(drained >= drain_rate)
+ break
+ if(istype(T.master, /obj/machinery/power/apc))
+ var/obj/machinery/power/apc/A = T.master
+ if(A.operating && A.cell)
+ var/cur_charge = A.cell.charge / CELLRATE
+ var/drain_val = min(apc_drain_rate, cur_charge)
+ A.cell.use(drain_val * CELLRATE)
+ drained += drain_val
+ power_drained += drained
+ return 1
+
+
+/obj/item/device/powersink/process()
+ drained_this_tick = 0
+ power_drained -= min(dissipation_rate, power_drained)
+ if(power_drained > max_power * 0.95)
+ playsound(src, 'sound/effects/screech.ogg', 100, 1, 1)
+ if(power_drained >= max_power)
+ explosion(src.loc, 3,6,9,12)
+ qdel(src)
return
-
- attack_hand(var/mob/user)
- switch(mode)
- if(0)
- ..()
-
- if(1)
- user << "You activate the device!"
- for(var/mob/M in viewers(user))
- if(M == user) continue
- M << "[user] activates the power sink!"
- mode = 2
- icon_state = "powersink1"
- processing_objects.Add(src)
-
- if(2) //This switch option wasn't originally included. It exists now. --NeoFite
- user << "You deactivate the device!"
- for(var/mob/M in viewers(user))
- if(M == user) continue
- M << "[user] deactivates the power sink!"
- mode = 1
- SetLuminosity(0)
- icon_state = "powersink0"
- processing_objects.Remove(src)
-
- process()
- power_drained -= min(dissipation_rate, power_drained)
- if(attached)
- var/datum/powernet/PN = attached.get_powernet()
- if(PN)
- SetLuminosity(12)
- PN.trigger_warning()
- // found a powernet, so drain up to max power from it
- var/drained = PN.draw_power(drain_rate)
-
- // if tried to drain more than available on powernet
- // now look for APCs and drain their cells
- if(drained < drain_rate)
- for(var/obj/machinery/power/terminal/T in PN.nodes)
- // Enough power drained this tick, no need to torture more APCs
- if(drained >= drain_rate)
- break
- if(istype(T.master, /obj/machinery/power/apc))
- var/obj/machinery/power/apc/A = T.master
- if(A.operating && A.cell)
- var/cur_charge = A.cell.charge / CELLRATE
- var/drain_val = min(2000, cur_charge)
-
- A.cell.use(drain_val * CELLRATE)
- drained += drain_val
-
-
- if(power_drained > max_power * 0.95)
- playsound(src, 'sound/effects/screech.ogg', 100, 1, 1)
- if(power_drained >= max_power)
- processing_objects.Remove(src)
- explosion(src.loc, 3,6,9,12)
- del(src)
+ if(attached && attached.powernet)
+ PN = attached.powernet
+ else
+ PN = null
diff --git a/code/game/objects/items/devices/radio/beacon.dm b/code/game/objects/items/devices/radio/beacon.dm
index 1de974710d4..b6a947d6d5d 100644
--- a/code/game/objects/items/devices/radio/beacon.dm
+++ b/code/game/objects/items/devices/radio/beacon.dm
@@ -30,7 +30,7 @@
/obj/item/device/radio/beacon/bacon //Probably a better way of doing this, I'm lazy.
proc/digest_delay()
spawn(600)
- del(src)
+ qdel(src)
// SINGULO BEACON SPAWNER
@@ -45,5 +45,5 @@
user << "\blue Locked In"
new /obj/machinery/power/singularity_beacon/syndicate( user.loc )
playsound(src, 'sound/effects/pop.ogg', 100, 1, 1)
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/items/devices/radio/electropack.dm b/code/game/objects/items/devices/radio/electropack.dm
index e7f9ec3b9fa..e5e94fc93d3 100644
--- a/code/game/objects/items/devices/radio/electropack.dm
+++ b/code/game/objects/items/devices/radio/electropack.dm
@@ -8,7 +8,7 @@
slot_flags = SLOT_BACK
w_class = 5.0
- matter = list("metal" = 10000,"glass" = 2500)
+ matter = list(DEFAULT_WALL_MATERIAL = 10000,"glass" = 2500)
var/code = 2
diff --git a/code/game/objects/items/devices/radio/headset.dm b/code/game/objects/items/devices/radio/headset.dm
index feb25ee68e4..e1ca0d88898 100644
--- a/code/game/objects/items/devices/radio/headset.dm
+++ b/code/game/objects/items/devices/radio/headset.dm
@@ -4,7 +4,7 @@
var/radio_desc = ""
icon_state = "headset"
item_state = "headset"
- matter = list("metal" = 75)
+ matter = list(DEFAULT_WALL_MATERIAL = 75)
subspace_transmission = 1
canhear_range = 0 // can't hear headsets from very far away
@@ -26,6 +26,13 @@
keyslot2 = new ks2type(src)
recalculateChannels(1)
+/obj/item/device/radio/headset/Destroy()
+ qdel(keyslot1)
+ qdel(keyslot2)
+ keyslot1 = null
+ keyslot2 = null
+ ..()
+
/obj/item/device/radio/headset/examine(mob/user)
if(!(..(user, 1) && radio_desc))
return
@@ -205,6 +212,13 @@
freerange = 1
ks2type = /obj/item/device/encryptionkey/ert
+/obj/item/device/radio/headset/ia
+ name = "internal affair's headset"
+ desc = "The headset of your worst enemy."
+ icon_state = "com_headset"
+ item_state = "headset"
+ ks2type = /obj/item/device/encryptionkey/heads/hos
+
/obj/item/device/radio/headset/attackby(obj/item/weapon/W as obj, mob/user as mob)
// ..()
user.set_machine(src)
diff --git a/code/game/objects/items/devices/radio/intercom.dm b/code/game/objects/items/devices/radio/intercom.dm
index 567dc49bf4f..522bef89a69 100644
--- a/code/game/objects/items/devices/radio/intercom.dm
+++ b/code/game/objects/items/devices/radio/intercom.dm
@@ -15,7 +15,7 @@
..()
processing_objects += src
-/obj/item/device/radio/intercom/Del()
+/obj/item/device/radio/intercom/Destroy()
processing_objects -= src
..()
@@ -58,10 +58,10 @@
on = 0
else
var/area/A = src.loc.loc
- if(!A || !isarea(A) || !A.master)
+ if(!A || !isarea(A))
on = 0
else
- on = A.master.powered(EQUIP) // set "on" to the power status
+ on = A.powered(EQUIP) // set "on" to the power status
if(!on)
icon_state = "intercom-p"
diff --git a/code/game/objects/items/devices/radio/radio.dm b/code/game/objects/items/devices/radio/radio.dm
index d6b254cad19..0e5116f5d83 100644
--- a/code/game/objects/items/devices/radio/radio.dm
+++ b/code/game/objects/items/devices/radio/radio.dm
@@ -26,7 +26,7 @@
throw_range = 9
w_class = 2
- matter = list("glass" = 25,"metal" = 75)
+ matter = list("glass" = 25,DEFAULT_WALL_MATERIAL = 75)
var/const/FREQ_LISTENING = 1
@@ -42,8 +42,15 @@
/obj/item/device/radio/New()
..()
wires = new(src)
+
+/obj/item/device/radio/Destroy()
+ qdel(wires)
+ wires = null
if(radio_controller)
- initialize()
+ radio_controller.remove_object(src, frequency)
+ for (var/ch_name in channels)
+ radio_controller.remove_object(src, radiochannels[ch_name])
+ ..()
/obj/item/device/radio/initialize()
@@ -172,7 +179,7 @@
0, "*garbled automated announcement*", src,
message, from, "Automated Announcement", from, "synthesized voice",
4, 0, list(0), connection.frequency, "states")
- del(A)
+ qdel(A)
return
// Interprets the message mode when talking into a radio, possibly returning a connection datum
@@ -202,7 +209,10 @@
if(wires.IsIndexCut(WIRE_TRANSMIT)) // The device has to have all its wires and shit intact
return 0
- M.last_target_click = world.time
+ M.last_target_radio = world.time // For the projectile targeting system
+
+ if(!radio_connection)
+ set_frequency(frequency)
/* Quick introduction:
This new radio system uses a very robust FTL signaling technology unoriginally
@@ -625,7 +635,6 @@
onclose(user, "radio")
return
-
/obj/item/device/radio/proc/config(op)
if(radio_controller)
for (var/ch_name in channels)
diff --git a/code/game/objects/items/devices/scanners.dm b/code/game/objects/items/devices/scanners.dm
index 6a11b6860ed..6e2697657c0 100644
--- a/code/game/objects/items/devices/scanners.dm
+++ b/code/game/objects/items/devices/scanners.dm
@@ -16,7 +16,7 @@ REAGENT SCANNER
w_class = 2
item_state = "electronic"
- matter = list("metal" = 150)
+ matter = list(DEFAULT_WALL_MATERIAL = 150)
origin_tech = list(TECH_MAGNET = 1, TECH_ENGINERING = 1)
@@ -72,9 +72,9 @@ REAGENT SCANNER
throwforce = 3
w_class = 2.0
throw_speed = 5
- throw_range = 10
- matter = list("metal" = 200)
- origin_tech = list(TECH_MAGNET = 1, TECH_BIO = 1)
+ throw_range = 10
+ matter = list(DEFAULT_WALL_MATERIAL = 200)
+ origin_tech = list(TECH_MAGNET = 1, TECH_BIO = 1)
var/mode = 1;
@@ -192,10 +192,12 @@ REAGENT SCANNER
for(var/name in H.organs_by_name)
var/obj/item/organ/external/e = H.organs_by_name[name]
- if(e.status & ORGAN_BROKEN)
+ if(e && e.status & ORGAN_BROKEN)
user.show_message(text("\red Bone fractures detected. Advanced scanner required for location."), 1)
break
for(var/obj/item/organ/external/e in H.organs)
+ if(!e)
+ continue
for(var/datum/wound/W in e.wounds) if(W.internal)
user.show_message(text("\red Internal bleeding detected. Advanced scanner required for location."), 1)
break
@@ -238,7 +240,7 @@ REAGENT SCANNER
throw_speed = 4
throw_range = 20
- matter = list("metal" = 30,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 20)
origin_tech = list(TECH_MAGNET = 1, TECH_ENGINERING = 1)
@@ -285,7 +287,7 @@ REAGENT SCANNER
throw_speed = 4
throw_range = 20
- matter = list("metal" = 30,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 20)
origin_tech = list(TECH_MAGNET = 2, TECH_BIO = 2)
var/details = 0
@@ -346,7 +348,7 @@ REAGENT SCANNER
throwforce = 5
throw_speed = 4
throw_range = 20
- matter = list("metal" = 30,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 20)
origin_tech = list(TECH_MAGNET = 2, TECH_BIO = 2)
var/details = 0
@@ -394,7 +396,7 @@ REAGENT SCANNER
throwforce = 0
throw_speed = 3
throw_range = 7
- matter = list("metal" = 30,"glass" = 20)
+ matter = list(DEFAULT_WALL_MATERIAL = 30,"glass" = 20)
/obj/item/device/slime_scanner/attack(mob/living/M as mob, mob/living/user as mob)
if (!isslime(M))
diff --git a/code/game/objects/items/devices/taperecorder.dm b/code/game/objects/items/devices/taperecorder.dm
index 1e9405cbeb5..35d04e4d086 100644
--- a/code/game/objects/items/devices/taperecorder.dm
+++ b/code/game/objects/items/devices/taperecorder.dm
@@ -5,7 +5,7 @@
item_state = "analyzer"
w_class = 2.0
- matter = list("metal" = 60,"glass" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 60,"glass" = 30)
var/emagged = 0.0
var/recording = 0.0
@@ -48,7 +48,7 @@
if(T)
T.hotspot_expose(700,125)
explosion(T, -1, -1, 0, 4)
- del(src)
+ qdel(src)
return
/obj/item/device/taperecorder/verb/record()
diff --git a/code/game/objects/items/devices/uplinks.dm b/code/game/objects/items/devices/uplinks.dm
index b2ac742a7c8..96874bd946b 100644
--- a/code/game/objects/items/devices/uplinks.dm
+++ b/code/game/objects/items/devices/uplinks.dm
@@ -53,6 +53,9 @@ datum/nano_item_lists
var/uplink_owner = null//text-only
var/used_TC = 0
+/obj/item/device/uplink/nano_host()
+ return loc
+
/obj/item/device/uplink/New()
..()
welcome = ticker.mode.uplink_welcome
@@ -61,7 +64,7 @@ datum/nano_item_lists
world_uplinks += src
-/obj/item/device/uplink/Del()
+/obj/item/device/uplink/Destroy()
world_uplinks -= src
..()
@@ -177,7 +180,7 @@ datum/nano_item_lists
/obj/item/device/uplink/hidden/New()
spawn(2)
if(!istype(src.loc, /obj/item))
- del(src)
+ qdel(src)
..()
// Toggles the uplink on and off. Normally this will bypass the item's normal functions and go to the uplink menu, if activated.
@@ -219,7 +222,7 @@ datum/nano_item_lists
if (!ui)
// the ui does not exist, so we'll create a new() one
// for a list of parameters and their descriptions see the code docs in \code\modules\nano\nanoui.dm
- ui = new(user, src, ui_key, "uplink.tmpl", title, 450, 600)
+ ui = new(user, src, ui_key, "uplink.tmpl", title, 450, 600, state = inventory_state)
// when the ui is first opened this is the data it will use
ui.set_initial_data(data)
// open the new ui window
diff --git a/code/game/objects/items/devices/whistle.dm b/code/game/objects/items/devices/whistle.dm
index 49df9aa31c2..d2627ed094c 100644
--- a/code/game/objects/items/devices/whistle.dm
+++ b/code/game/objects/items/devices/whistle.dm
@@ -6,33 +6,53 @@
w_class = 1.0
flags = CONDUCT
+ var/use_message = "Halt! Security!"
var/spamcheck = 0
- var/emagged = 0
- var/insults = 0//just in case
+ var/insults
-/obj/item/device/hailer/attack_self(mob/living/carbon/user as mob)
+/obj/item/device/hailer/verb/set_message()
+ set name = "Set Hailer Message"
+ set category = "Object"
+ set desc = "Alter the message shouted by your hailer."
+
+ if(!isnull(insults))
+ usr << "The hailer is fried. The tiny input screen just shows a waving ASCII penis."
+ return
+
+ var/new_message = input(usr, "Please enter new message (leave blank to reset).") as text
+ if(!new_message || new_message == "")
+ use_message = "Halt! Security!"
+ else
+ use_message = capitalize(copytext(sanitize(new_message), 1, MAX_MESSAGE_LEN))
+
+ usr << "You configure the hailer to shout \"[use_message]\"."
+/
+obj/item/device/hailer/attack_self(mob/living/carbon/user as mob)
if (spamcheck)
return
- if(emagged)
- if(insults >= 1)
- playsound(get_turf(src), 'sound/voice/binsult.ogg', 100, 1, vary = 0)//hueheuheuheuheuheuhe
- user.show_message("[user]'s [name] gurgles, \"FUCK YOUR CUNT YOU SHIT EATING CUNT TILL YOU ARE A MASS EATING SHIT CUNT. EAT PENISES IN YOUR FUCK FACE AND SHIT OUT ABORTIONS TO FUCK UP SHIT IN YOUR ASS YOU COCK FUCK SHIT MONKEY FROM THE DEPTHS OF SHIT\"",2) //It's a hearable message silly!
+ if(isnull(insults))
+ playsound(get_turf(src), 'sound/voice/halt.ogg', 100, 1, vary = 0)
+ user.show_message("[user]'s [name] rasps, \"[use_message]\"",1)
+ else
+ if(insults > 0)
+ playsound(get_turf(src), 'sound/voice/binsult.ogg', 100, 1, vary = 0)
+ // Yes, it used to show the transcription of the sound clip. That was a) inaccurate b) immature as shit.
+ user.show_message("[user]'s [name] gurgles something indecipherable and deeply offensive.")
insults--
else
- user << "\red *BZZZZcuntZZZZT*"
- else
- playsound(get_turf(src), 'sound/voice/halt.ogg', 100, 1, vary = 0)
- user.show_message("[user]'s [name] rasps, \"Halt! Security!\"",1)
+ user << "*BZZZZZZZZT*"
spamcheck = 1
spawn(20)
spamcheck = 0
/obj/item/device/hailer/attackby(obj/item/I, mob/user)
- if(istype(I, /obj/item/weapon/card/emag) && !emagged)
- user << "\red You overload \the [src]'s voice synthesizer."
- emagged = 1
- insults = rand(1, 3)//to prevent dickflooding
- return
- return
+ if(istype(I, /obj/item/weapon/card/emag))
+ if(isnull(insults))
+ user << "You overload \the [src]'s voice synthesizer."
+ insults = rand(1, 3)//to prevent dickflooding
+ else
+ user << "The hailer is fried. You can't even fit the sequencer into the input slot."
+ else
+ return .. ()
diff --git a/code/game/objects/items/glassjar.dm b/code/game/objects/items/glassjar.dm
new file mode 100644
index 00000000000..54062ff8530
--- /dev/null
+++ b/code/game/objects/items/glassjar.dm
@@ -0,0 +1,108 @@
+/obj/item/glass_jar
+ name = "glass jar"
+ desc = "A small empty jar."
+ icon = 'icons/obj/items.dmi'
+ icon_state = "jar"
+ w_class = 2
+ matter = list("glass" = 200)
+ flags = NOBLUDGEON
+ var/list/accept_mobs = list(/mob/living/simple_animal/lizard, /mob/living/simple_animal/mouse)
+ var/contains = 0 // 0 = nothing, 1 = money, 2 = animal, 3 = spiderling
+
+/obj/item/glass_jar/New()
+ ..()
+ update_icon()
+
+/obj/item/glass_jar/afterattack(var/atom/A, var/mob/user, var/proximity)
+ if(!proximity || contains)
+ return
+ if(istype(A, /mob))
+ var/accept = 0
+ for(var/D in accept_mobs)
+ if(istype(A, D))
+ accept = 1
+ if(!accept)
+ user << "[A] doesn't fit into \the [src]."
+ return
+ var/mob/L = A
+ user.visible_message("[user] scoops [L] into \the [src].", "You scoop [L] into \the [src].")
+ L.loc = src
+ contains = 2
+ update_icon()
+ return
+ else if(istype(A, /obj/effect/spider/spiderling))
+ var/obj/effect/spider/spiderling/S = A
+ user.visible_message("[user] scoops [S] into \the [src].", "You scoop [S] into \the [src].")
+ S.loc = src
+ processing_objects.Remove(S) // No growing inside jars
+ contains = 3
+ update_icon()
+ return
+
+/obj/item/glass_jar/attack_self(var/mob/user)
+ switch(contains)
+ if(1)
+ for(var/obj/O in src)
+ O.loc = user.loc
+ user << "You take money out of \the [src]."
+ contains = 0
+ update_icon()
+ return
+ if(2)
+ for(var/mob/M in src)
+ M.loc = user.loc
+ user.visible_message("[user] releases [M] from \the [src].", "You release [M] from \the [src].")
+ contains = 0
+ update_icon()
+ return
+ if(3)
+ for(var/obj/effect/spider/spiderling/S in src)
+ S.loc = user.loc
+ user.visible_message("[user] releases [S] from \the [src].", "You release [S] from \the [src].")
+ processing_objects.Add(S) // They can grow after being let out though
+ contains = 0
+ update_icon()
+ return
+
+/obj/item/glass_jar/attackby(var/obj/item/W, var/mob/user)
+ if(istype(W, /obj/item/weapon/spacecash))
+ if(contains == 0)
+ contains = 1
+ if(contains != 1)
+ return
+ var/obj/item/weapon/spacecash/S = W
+ user.visible_message("[user] puts [S.worth] [S.worth > 1 ? "thalers" : "thaler"] into \the [src].")
+ user.drop_from_inventory(S)
+ S.loc = src
+ update_icon()
+
+/obj/item/glass_jar/update_icon() // Also updates name and desc
+ underlays.Cut()
+ overlays.Cut()
+ switch(contains)
+ if(0)
+ name = initial(name)
+ desc = initial(desc)
+ if(1)
+ name = "tip jar"
+ desc = "A small jar with money inside."
+ for(var/obj/item/weapon/spacecash/S in src)
+ var/image/money = image(S.icon, S.icon_state)
+ money.pixel_x = rand(-2, 3)
+ money.pixel_y = rand(-6, 6)
+ money.transform *= 0.6
+ underlays += money
+ if(2)
+ for(var/mob/M in src)
+ var/image/victim = image(M.icon, M.icon_state)
+ victim.pixel_y = 6
+ underlays += victim
+ name = "glass jar with [M]"
+ desc = "A small jar with [M] inside."
+ if(3)
+ for(var/obj/effect/spider/spiderling/S in src)
+ var/image/victim = image(S.icon, S.icon_state)
+ underlays += victim
+ name = "glass jar with [S]"
+ desc = "A small jar with [S] inside."
+ return
\ No newline at end of file
diff --git a/code/game/objects/items/latexballoon.dm b/code/game/objects/items/latexballoon.dm
index e341a8747f0..a37352c7d36 100644
--- a/code/game/objects/items/latexballoon.dm
+++ b/code/game/objects/items/latexballoon.dm
@@ -30,10 +30,10 @@
burst()
switch(severity)
if (1)
- del(src)
+ qdel(src)
if (2)
if (prob(50))
- del(src)
+ qdel(src)
/obj/item/latexballon/bullet_act()
burst()
diff --git a/code/game/objects/items/paintkit.dm b/code/game/objects/items/paintkit.dm
new file mode 100644
index 00000000000..34802577d6b
--- /dev/null
+++ b/code/game/objects/items/paintkit.dm
@@ -0,0 +1,178 @@
+/obj/item/device/kit
+ icon_state = "modkit"
+ icon = 'icons/obj/device.dmi'
+ var/new_name = "mech" //What is the variant called?
+ var/new_desc = "A mech." //How is the new mech described?
+ var/new_icon = "ripley" //What base icon will the new mech use?
+ var/new_icon_file
+ var/uses = 1 // Uses before the kit deletes itself.
+
+/obj/item/device/kit/examine()
+ ..()
+ usr << "It has [uses] [uses>1?"uses":"use"] left."
+
+/obj/item/device/kit/proc/use(var/amt, var/mob/user)
+ uses -= amt
+ playsound(get_turf(user), 'sound/items/Screwdriver.ogg', 50, 1)
+ if(uses<1)
+ user.drop_item()
+ qdel(src)
+
+// Root hardsuit kit defines.
+// Icons for modified hardsuits need to be in the proper .dmis because suit cyclers may cock them up.
+/obj/item/device/kit/suit
+ name = "voidsuit modification kit"
+ desc = "A kit for modifying a voidsuit."
+ uses = 2
+ var/new_light_overlay
+ var/new_mob_icon_file
+
+/obj/item/clothing/head/helmet/space/void/attackby(var/obj/item/O, var/mob/user)
+ if(istype(O,/obj/item/device/kit/suit))
+ var/obj/item/device/kit/suit/kit = O
+ name = "[kit.new_name] suit helmet"
+ desc = kit.new_desc
+ icon_state = "[kit.new_icon]_helmet"
+ item_state = "[kit.new_icon]_helmet"
+ if(kit.new_icon_file)
+ icon = kit.new_icon_file
+ if(kit.new_mob_icon_file)
+ icon_override = kit.new_mob_icon_file
+ if(kit.new_light_overlay)
+ light_overlay = kit.new_light_overlay
+ user << "You set about modifying the helmet into [src]."
+ var/mob/living/carbon/human/H = user
+ if(istype(H))
+ species_restricted = list(H.species.name)
+ kit.use(1,user)
+ return 1
+ return ..()
+
+/obj/item/clothing/suit/space/void/attackby(var/obj/item/O, var/mob/user)
+ if(istype(O,/obj/item/device/kit/suit))
+ var/obj/item/device/kit/suit/kit = O
+ name = "[kit.new_name] voidsuit"
+ desc = kit.new_desc
+ icon_state = "[kit.new_icon]_suit"
+ item_state = "[kit.new_icon]_suit"
+ if(kit.new_icon_file)
+ icon = kit.new_icon_file
+ if(kit.new_mob_icon_file)
+ icon_override = kit.new_mob_icon_file
+ user << "You set about modifying the suit into [src]."
+ var/mob/living/carbon/human/H = user
+ if(istype(H))
+ species_restricted = list(H.species.name)
+ kit.use(1,user)
+ return 1
+ return ..()
+
+/obj/item/device/kit/paint
+ name = "mecha customisation kit"
+ desc = "A kit containing all the needed tools and parts to repaint a mech."
+ var/removable = null
+ var/list/allowed_types = list()
+
+/obj/item/device/kit/paint/examine()
+ ..()
+ usr << "This kit will convert an exosuit into: [new_name]."
+ usr << "This kit can be used on the following exosuit models:"
+ for(var/exotype in allowed_types)
+ usr << "- [capitalize(exotype)]"
+
+/obj/mecha/attackby(var/obj/item/weapon/W, var/mob/user)
+ if(istype(W, /obj/item/device/kit/paint))
+ if(occupant)
+ user << "You can't customize a mech while someone is piloting it - that would be unsafe!"
+ return
+
+ var/obj/item/device/kit/paint/P = W
+ var/found = null
+
+ for(var/type in P.allowed_types)
+ if(type==src.initial_icon)
+ found = 1
+ break
+
+ if(!found)
+ user << "That kit isn't meant for use on this class of exosuit."
+ return
+
+ user.visible_message("[user] opens [P] and spends some quality time customising [src].")
+ src.name = P.new_name
+ src.desc = P.new_desc
+ src.initial_icon = P.new_icon
+ if(P.new_icon_file)
+ src.icon = P.new_icon_file
+ src.reset_icon()
+ P.use(1, user)
+ return 1
+ else
+ return ..()
+
+//Ripley APLU kits.
+/obj/item/device/kit/paint/ripley
+ name = "\"Classic\" APLU customisation kit"
+ new_name = "APLU \"Classic\""
+ new_desc = "A very retro APLU unit; didn't they retire these back in 2543?"
+ new_icon = "ripley-old"
+ allowed_types = list("ripley")
+
+/obj/item/device/kit/paint/ripley/death
+ name = "\"Reaper\" APLU customisation kit"
+ new_name = "APLU \"Reaper\""
+ new_desc = "A terrifying, grim power loader. Why do those clamps have spikes?"
+ new_icon = "deathripley"
+ allowed_types = list("ripley","firefighter")
+
+/obj/item/device/kit/paint/ripley/flames_red
+ name = "\"Firestarter\" APLU customisation kit"
+ new_name = "APLU \"Firestarter\""
+ new_desc = "A standard APLU exosuit with stylish orange flame decals."
+ new_icon = "ripley_flames_red"
+
+/obj/item/device/kit/paint/ripley/flames_blue
+ name = "\"Burning Chrome\" APLU customisation kit"
+ new_name = "APLU \"Burning Chrome\""
+ new_desc = "A standard APLU exosuit with stylish blue flame decals."
+ new_icon = "ripley_flames_blue"
+
+// Durand kits.
+/obj/item/device/kit/paint/durand
+ name = "\"Classic\" Durand customisation kit"
+ new_name = "Durand \"Classic\""
+ new_desc = "An older model of Durand combat exosuit. This model was retired for rotating a pilot's torso 180 degrees."
+ new_icon = "old_durand"
+ allowed_types = list("durand")
+
+/obj/item/device/kit/paint/durand/seraph
+ name = "\"Cherubim\" Durand customisation kit"
+ new_name = "Durand \"Cherubim\""
+ new_desc = "A Durand combat exosuit modelled after ancient Earth entertainment. Your heart goes doki-doki just looking at it."
+ new_icon = "old_durand"
+
+/obj/item/device/kit/paint/durand/phazon
+ name = "\"Sypher\" Durand customisation kit"
+ new_name = "Durand \"Sypher\""
+ new_desc = "A Durand combat exosuit with some very stylish neons and decals. Seems to blur slightly at the edges; probably an optical illusion."
+ new_icon = "phazon"
+
+// Gygax kits.
+/obj/item/device/kit/paint/gygax
+ name = "\"Jester\" Gygax customisation kit"
+ new_name = "Gygax \"Jester\""
+ new_desc = "A Gygax exosuit modelled after the infamous combat-troubadors of Earth's distant past. Terrifying to behold."
+ new_icon = "honker"
+ allowed_types = list("gygax")
+
+/obj/item/device/kit/paint/gygax/darkgygax
+ name = "\"Silhouette\" Gygax customisation kit"
+ new_name = "Gygax \"Silhouette\""
+ new_desc = "An ominous Gygax exosuit modelled after the fictional corporate 'death squads' that were popular in pulp action-thrillers back in 2554."
+ new_icon = "darkgygax"
+
+/obj/item/device/kit/paint/gygax/recitence
+ name = "\"Gaoler\" Gygax customisation kit"
+ new_name = "Durand \"Gaoler\""
+ new_desc = "A bulky silver Gygax exosuit. The extra armour appears to be painted on, but it's very shiny."
+ new_icon = "recitence"
\ No newline at end of file
diff --git a/code/game/objects/items/robot/robot_parts.dm b/code/game/objects/items/robot/robot_parts.dm
index 9c262243c68..e1ebc9fdc19 100644
--- a/code/game/objects/items/robot/robot_parts.dm
+++ b/code/game/objects/items/robot/robot_parts.dm
@@ -6,7 +6,7 @@
flags = CONDUCT
slot_flags = SLOT_BELT
var/construction_time = 100
- var/list/construction_cost = list("metal"=20000,"glass"=5000)
+ var/list/construction_cost = list(DEFAULT_WALL_MATERIAL=20000,"glass"=5000)
var/list/part = null // Order of args is important for installing robolimbs.
var/sabotaged = 0 //Emagging limbs can have repercussions when installed as prosthetics.
var/model_info
@@ -33,7 +33,7 @@
desc = "A skeletal limb wrapped in pseudomuscles, with a low-conductivity case."
icon_state = "l_arm"
construction_time = 200
- construction_cost = list("metal"=18000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=18000)
part = list("l_arm","l_hand")
model_info = 1
@@ -42,7 +42,7 @@
desc = "A skeletal limb wrapped in pseudomuscles, with a low-conductivity case."
icon_state = "r_arm"
construction_time = 200
- construction_cost = list("metal"=18000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=18000)
part = list("r_arm","r_hand")
model_info = 1
@@ -51,7 +51,7 @@
desc = "A skeletal limb wrapped in pseudomuscles, with a low-conductivity case."
icon_state = "l_leg"
construction_time = 200
- construction_cost = list("metal"=15000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000)
part = list("l_leg","l_foot")
model_info = 1
@@ -60,7 +60,7 @@
desc = "A skeletal limb wrapped in pseudomuscles, with a low-conductivity case."
icon_state = "r_leg"
construction_time = 200
- construction_cost = list("metal"=15000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=15000)
part = list("r_leg","r_foot")
model_info = 1
@@ -69,7 +69,7 @@
desc = "A heavily reinforced case containing cyborg logic boards, with space for a standard power cell."
icon_state = "chest"
construction_time = 350
- construction_cost = list("metal"=40000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=40000)
var/wires = 0.0
var/obj/item/weapon/cell/cell = null
@@ -78,7 +78,7 @@
desc = "A standard reinforced braincase, with spine-plugged neural socket and sensor gimbals."
icon_state = "head"
construction_time = 350
- construction_cost = list("metal"=25000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=25000)
var/obj/item/device/flash/flash1 = null
var/obj/item/device/flash/flash2 = null
@@ -87,7 +87,7 @@
desc = "A complex metal backbone with standard limb sockets and pseudomuscle anchors."
icon_state = "robo_suit"
construction_time = 500
- construction_cost = list("metal"=50000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=50000)
var/obj/item/robot_parts/l_arm/l_arm = null
var/obj/item/robot_parts/r_arm/r_arm = null
var/obj/item/robot_parts/l_leg/l_leg = null
@@ -134,7 +134,7 @@
if (user.get_inactive_hand()==src)
user.remove_from_mob(src)
user.put_in_inactive_hand(B)
- del(src)
+ qdel(src)
else
user << "You need one sheet of metal to arm the robot frame."
if(istype(W, /obj/item/robot_parts/l_leg))
@@ -250,7 +250,7 @@
callHook("borgify", list(O))
O.Namepick()
- del(src)
+ qdel(src)
else
user << "\blue The MMI must go in after everything else!"
@@ -291,30 +291,39 @@
..()
if(istype(W, /obj/item/device/flash))
if(istype(user,/mob/living/silicon/robot))
- user << "\red How do you propose to do that?"
- return
- else if(src.flash1 && src.flash2)
- user << "\blue You have already inserted the eyes!"
- return
- else if(src.flash1)
- user.drop_item()
- W.loc = src
- src.flash2 = W
- user << "\blue You insert the flash into the eye socket!"
+ var/current_module = user.get_active_hand()
+ if(current_module == W)
+ user << "How do you propose to do that?"
+ return
+ else
+ add_flashes(W,user)
else
- user.drop_item()
- W.loc = src
- src.flash1 = W
- user << "\blue You insert the flash into the eye socket!"
+ add_flashes(W,user)
else if(istype(W, /obj/item/weapon/stock_parts/manipulator))
user << "\blue You install some manipulators and modify the head, creating a functional spider-bot!"
new /mob/living/simple_animal/spiderbot(get_turf(loc))
user.drop_item()
- del(W)
- del(src)
+ qdel(W)
+ qdel(src)
return
return
+/obj/item/robot_parts/head/proc/add_flashes(obj/item/W as obj, mob/user as mob) //Made into a seperate proc to avoid copypasta
+ if(src.flash1 && src.flash2)
+ user << "You have already inserted the eyes!"
+ return
+ else if(src.flash1)
+ user.drop_item()
+ W.loc = src
+ src.flash2 = W
+ user << "You insert the flash into the eye socket!"
+ else
+ user.drop_item()
+ W.loc = src
+ src.flash1 = W
+ user << "You insert the flash into the eye socket!"
+
+
/obj/item/robot_parts/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W,/obj/item/weapon/card/emag))
if(sabotaged)
diff --git a/code/game/objects/items/robot/robot_upgrades.dm b/code/game/objects/items/robot/robot_upgrades.dm
index 43b852e2497..10fb1dc6fd5 100644
--- a/code/game/objects/items/robot/robot_upgrades.dm
+++ b/code/game/objects/items/robot/robot_upgrades.dm
@@ -7,7 +7,7 @@
icon = 'icons/obj/module.dmi'
icon_state = "cyborg_upgrade"
var/construction_time = 120
- var/construction_cost = list("metal"=10000)
+ var/construction_cost = list(DEFAULT_WALL_MATERIAL=10000)
var/locked = 0
var/require_module = 0
var/installed = 0
@@ -28,20 +28,14 @@
/obj/item/borg/upgrade/reset/action(var/mob/living/silicon/robot/R)
if(..()) return 0
R.uneq_all()
- R.hands.icon_state = "nomod"
- R.icon_state = "robot"
- //world << R.custom_sprite
- if(R.custom_sprite == 1)
- //world << R.icon_state
- icon = 'icons/mob/custom-synthetic.dmi'
- R.icon_state = "[R.ckey]-Standard"
- del(R.module)
+ R.modtype = initial(R.modtype)
+ R.hands.icon_state = initial(R.hands.icon_state)
+
+ R.choose_icon(1, R.set_module_sprites(list("Default" = "robot")))
+
R.notify_ai(ROBOT_NOTIFICATION_MODULE_RESET, R.module.name)
- R.module = null
- R.camera.remove_networks(list("Engineering","Medical","MINE"))
+ R.module.Reset(R)
R.updatename("Default")
- R.status_flags |= CANPUSH
- R.updateicon()
return 1
@@ -49,7 +43,7 @@
name = "robot reclassification board"
desc = "Used to rename a cyborg."
icon_state = "cyborg_upgrade1"
- construction_cost = list("metal"=35000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=35000)
var/heldname = "default name"
/obj/item/borg/upgrade/rename/attack_self(mob/user as mob)
@@ -67,7 +61,7 @@
/obj/item/borg/upgrade/restart
name = "robot emergency restart module"
desc = "Used to force a restart of a disabled-but-repaired robot, bringing it back online."
- construction_cost = list("metal"=60000 , "glass"=5000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=60000 , "glass"=5000)
icon_state = "cyborg_upgrade1"
@@ -91,7 +85,7 @@
/obj/item/borg/upgrade/vtec
name = "robotic VTEC Module"
desc = "Used to kick in a robot's VTEC systems, increasing their speed."
- construction_cost = list("metal"=80000 , "glass"=6000 , "gold"= 5000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=80000 , "glass"=6000 , "gold"= 5000)
icon_state = "cyborg_upgrade2"
require_module = 1
@@ -108,7 +102,7 @@
/obj/item/borg/upgrade/tasercooler
name = "robotic Rapid Taser Cooling Module"
desc = "Used to cool a mounted taser, increasing the potential current in it and thus its recharge rate."
- construction_cost = list("metal"=80000 , "glass"=6000 , "gold"= 2000, "diamond" = 500)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=80000 , "glass"=6000 , "gold"= 2000, "diamond" = 500)
icon_state = "cyborg_upgrade3"
require_module = 1
@@ -116,7 +110,7 @@
/obj/item/borg/upgrade/tasercooler/action(var/mob/living/silicon/robot/R)
if(..()) return 0
- if(!istype(R.module, /obj/item/weapon/robot_module/security))
+ if(!R.module || !(src in R.module.supported_upgrades))
R << "Upgrade mounting error! No suitable hardpoint detected!"
usr << "There's no mounting point for the module!"
return 0
@@ -143,14 +137,14 @@
/obj/item/borg/upgrade/jetpack
name = "mining robot jetpack"
desc = "A carbon dioxide jetpack suitable for low-gravity mining operations."
- construction_cost = list("metal"=10000,"phoron"=15000,"uranium" = 20000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"phoron"=15000,"uranium" = 20000)
icon_state = "cyborg_upgrade3"
require_module = 1
/obj/item/borg/upgrade/jetpack/action(var/mob/living/silicon/robot/R)
if(..()) return 0
- if(!istype(R.module, /obj/item/weapon/robot_module/miner))
+ if(!R.module || !(src in R.module.supported_upgrades))
R << "Upgrade mounting error! No suitable hardpoint detected!"
usr << "There's no mounting point for the module!"
return 0
@@ -165,7 +159,7 @@
/obj/item/borg/upgrade/syndicate/
name = "illegal equipment module"
desc = "Unlocks the hidden, deadlier functions of a robot"
- construction_cost = list("metal"=10000,"glass"=15000,"diamond" = 10000)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=10000,"glass"=15000,"diamond" = 10000)
icon_state = "cyborg_upgrade3"
require_module = 1
diff --git a/code/game/objects/items/shooting_range.dm b/code/game/objects/items/shooting_range.dm
index 1d92cb9a818..2893b4f3a10 100644
--- a/code/game/objects/items/shooting_range.dm
+++ b/code/game/objects/items/shooting_range.dm
@@ -9,7 +9,7 @@
var/icon/virtualIcon
var/list/bulletholes = list()
- Del()
+ Destroy()
// if a target is deleted and associated with a stake, force stake to forget
for(var/obj/structure/target_stake/T in view(3,src))
if(T.pinned_target == src)
@@ -97,7 +97,7 @@
for(var/mob/O in oviewers())
if ((O.client && !( O.blinded )))
O << "\red [src] breaks into tiny pieces and collapses!"
- del(src)
+ qdel(src)
// Create a temporary object to represent the damage
var/obj/bmark = new
diff --git a/code/game/objects/items/stacks/matter_synth.dm b/code/game/objects/items/stacks/matter_synth.dm
index 0842f70d66a..3483dfbc61c 100644
--- a/code/game/objects/items/stacks/matter_synth.dm
+++ b/code/game/objects/items/stacks/matter_synth.dm
@@ -28,6 +28,9 @@
/datum/matter_synth/medicine
name = "Medicine Synthesizer"
+/datum/matter_synth/nanite
+ name = "Nanite Synthesizer"
+
/datum/matter_synth/metal
name = "Metal Synthesizer"
diff --git a/code/game/objects/items/stacks/medical.dm b/code/game/objects/items/stacks/medical.dm
index 1f036e5bafc..be178632e65 100644
--- a/code/game/objects/items/stacks/medical.dm
+++ b/code/game/objects/items/stacks/medical.dm
@@ -217,27 +217,27 @@
var/mob/living/carbon/human/H = M
var/obj/item/organ/external/affecting = H.get_organ(user.zone_sel.selecting)
var/limb = affecting.name
- if(!((affecting.name == "l_arm") || (affecting.name == "r_arm") || (affecting.name == "l_leg") || (affecting.name == "r_leg")))
- user << "\red You can't apply a splint there!"
+ if(!(affecting.limb_name in list("l_arm","r_arm","l_leg","r_leg")))
+ user << "You can't apply a splint there!"
return
if(affecting.status & ORGAN_SPLINTED)
- user << "\red [M]'s [limb] is already splinted!"
+ user << "[M]'s [limb] is already splinted!"
return
if (M != user)
- user.visible_message("\red [user] starts to apply \the [src] to [M]'s [limb].", "\red You start to apply \the [src] to [M]'s [limb].", "\red You hear something being wrapped.")
+ user.visible_message("[user] starts to apply \the [src] to [M]'s [limb].", "You start to apply \the [src] to [M]'s [limb].", "You hear something being wrapped.")
else
- if((!user.hand && affecting.name == "r_arm") || (user.hand && affecting.name == "l_arm"))
- user << "\red You can't apply a splint to the arm you're using!"
+ if((!user.hand && affecting.limb_name == "r_arm") || (user.hand && affecting.limb_name == "l_arm"))
+ user << "You can't apply a splint to the arm you're using!"
return
- user.visible_message("\red [user] starts to apply \the [src] to their [limb].", "\red You start to apply \the [src] to your [limb].", "\red You hear something being wrapped.")
+ user.visible_message("[user] starts to apply \the [src] to their [limb].", "You start to apply \the [src] to your [limb].", "You hear something being wrapped.")
if(do_after(user, 50))
if (M != user)
- user.visible_message("\red [user] finishes applying \the [src] to [M]'s [limb].", "\red You finish applying \the [src] to [M]'s [limb].", "\red You hear something being wrapped.")
+ user.visible_message("[user] finishes applying \the [src] to [M]'s [limb].", "You finish applying \the [src] to [M]'s [limb].", "You hear something being wrapped.")
else
if(prob(25))
- user.visible_message("\red [user] successfully applies \the [src] to their [limb].", "\red You successfully apply \the [src] to your [limb].", "\red You hear something being wrapped.")
+ user.visible_message("[user] successfully applies \the [src] to their [limb].", "You successfully apply \the [src] to your [limb].", "You hear something being wrapped.")
else
- user.visible_message("\red [user] fumbles \the [src].", "\red You fumble \the [src].", "\red You hear something being wrapped.")
+ user.visible_message("[user] fumbles \the [src].", "You fumble \the [src].", "You hear something being wrapped.")
return
affecting.status |= ORGAN_SPLINTED
use(1)
diff --git a/code/game/objects/items/stacks/rods.dm b/code/game/objects/items/stacks/rods.dm
index 143539968e7..e3bbce8386e 100644
--- a/code/game/objects/items/stacks/rods.dm
+++ b/code/game/objects/items/stacks/rods.dm
@@ -9,7 +9,7 @@
throwforce = 15.0
throw_speed = 5
throw_range = 20
- matter = list("metal" = 1875)
+ matter = list(DEFAULT_WALL_MATERIAL = 1875)
max_amount = 60
attack_verb = list("hit", "bludgeoned", "whacked")
diff --git a/code/game/objects/items/stacks/sheets/glass.dm b/code/game/objects/items/stacks/sheets/glass.dm
index 38311543b94..fd1ef4f0ca9 100644
--- a/code/game/objects/items/stacks/sheets/glass.dm
+++ b/code/game/objects/items/stacks/sheets/glass.dm
@@ -20,6 +20,7 @@
var/created_window = /obj/structure/window/basic
var/is_reinforced = 0
var/list/construction_options = list("One Direction", "Full Window")
+ sheettype = "glass"
/obj/item/stack/sheet/glass/cyborg
name = "glass synthesizer"
@@ -144,8 +145,8 @@
singular_name = "reinforced glass sheet"
icon_state = "sheet-rglass"
- matter = list("metal" = 1875,"glass" = 3750)
- origin_tech = list(TECH_MATERIAL = 2)
+ origin_tech = list(TECH_MATERIAL = 2)
+ matter = list(DEFAULT_WALL_MATERIAL = 1875, "glass" = 3750)
created_window = /obj/structure/window/reinforced
is_reinforced = 1
@@ -161,6 +162,7 @@
singular_name = "reinforced glass sheet"
icon_state = "sheet-rglass"
charge_costs = list(500, 1000)
+ stacktype = /obj/item/stack/sheet/glass/reinforced
/*
* Phoron Glass sheets
@@ -173,6 +175,7 @@
matter = list("glass" = 7500)
origin_tech = list(TECH_MATERIAL = 3, TECH_PHORON = 2)
created_window = /obj/structure/window/phoronbasic
+ sheettype = "phoronglass"
/obj/item/stack/sheet/glass/phoronglass/attackby(obj/item/W, mob/user)
..()
@@ -199,7 +202,7 @@
desc = "Phoron glass which has been reinforced with metal rods."
singular_name = "reinforced phoron glass sheet"
icon_state = "sheet-phoronrglass"
- matter = list("glass" = 7500,"metal" = 1875)
+ matter = list("glass" = 7500,DEFAULT_WALL_MATERIAL = 1875)
origin_tech = list(TECH_MATERIAL = 4, TECH_PHORON = 2)
created_window = /obj/structure/window/phoronreinforced
diff --git a/code/game/objects/items/stacks/sheets/light.dm b/code/game/objects/items/stacks/sheets/light.dm
index de96eda5f4b..f43d7ae320f 100644
--- a/code/game/objects/items/stacks/sheets/light.dm
+++ b/code/game/objects/items/stacks/sheets/light.dm
@@ -20,7 +20,7 @@
new/obj/item/stack/sheet/glass(user.loc)
if(amount <= 0)
user.drop_from_inventory(src)
- del(src)
+ qdel(src)
if(istype(O,/obj/item/stack/sheet/metal))
var/obj/item/stack/sheet/metal/M = O
diff --git a/code/game/objects/items/stacks/sheets/mineral.dm b/code/game/objects/items/stacks/sheets/mineral.dm
index cd1767f01ef..9e99ecfc74f 100644
--- a/code/game/objects/items/stacks/sheets/mineral.dm
+++ b/code/game/objects/items/stacks/sheets/mineral.dm
@@ -134,6 +134,7 @@ obj/item/stack/sheet/mineral/iron/New()
icon_state = "sheet-plastic"
origin_tech = list(TECH_MATERIAL = 3)
perunit = 2000
+ sheettype = "plastic"
/obj/item/stack/sheet/mineral/plastic/New()
..()
diff --git a/code/game/objects/items/stacks/sheets/sheet_types.dm b/code/game/objects/items/stacks/sheets/sheet_types.dm
index b732a04694a..c5d7be9aaab 100644
--- a/code/game/objects/items/stacks/sheets/sheet_types.dm
+++ b/code/game/objects/items/stacks/sheets/sheet_types.dm
@@ -31,8 +31,8 @@ var/global/list/datum/stack_recipe/metal_recipes = list ( \
new/datum/stack_recipe("green comfy chair", /obj/structure/bed/chair/comfy/green, 2, one_per_turf = 1, on_floor = 1), \
), 2), \
null, \
- new/datum/stack_recipe("table parts", /obj/item/weapon/table_parts, 2), \
- new/datum/stack_recipe("rack parts", /obj/item/weapon/table_parts/rack), \
+ new/datum/stack_recipe("table frame", /obj/structure/table, 1, time = 10, one_per_turf = 1, on_floor = 1), \
+ new/datum/stack_recipe("rack", /obj/structure/table/rack, 1, time = 5, one_per_turf = 1, on_floor = 1), \
new/datum/stack_recipe("metal baseball bat", /obj/item/weapon/twohanded/baseballbat/metal, 10, time = 20, one_per_turf = 0, on_floor = 1), \
new/datum/stack_recipe("closet", /obj/structure/closet, 2, time = 15, one_per_turf = 1, on_floor = 1), \
null, \
@@ -69,29 +69,30 @@ var/global/list/datum/stack_recipe/metal_recipes = list ( \
), 4), \
null, \
new/datum/stack_recipe("grenade casing", /obj/item/weapon/grenade/chem_grenade), \
- new/datum/stack_recipe("light fixture frame", /obj/item/light_fixture_frame, 2), \
- new/datum/stack_recipe("small light fixture frame", /obj/item/light_fixture_frame/small, 1), \
+ new/datum/stack_recipe("light fixture frame", /obj/item/frame/light, 2), \
+ new/datum/stack_recipe("small light fixture frame", /obj/item/frame/light/small, 1), \
null, \
new/datum/stack_recipe("apc frame", /obj/item/apc_frame, 2), \
- new/datum/stack_recipe("air alarm frame", /obj/item/alarm_frame, 2), \
- new/datum/stack_recipe("fire alarm frame", /obj/item/firealarm_frame, 2), \
+ new/datum/stack_recipe("air alarm frame", /obj/item/frame/air_alarm, 2), \
+ new/datum/stack_recipe("fire alarm frame", /obj/item/frame/fire_alarm, 2), \
null, \
new/datum/stack_recipe("knife blade", /obj/item/butterflyblade, 6, time = 20, one_per_turf = 0, on_floor = 1) \
)
/obj/item/stack/sheet/metal
- name = "metal"
- desc = "Sheets made out off metal. It has been dubbed Metal Sheets."
+ name = DEFAULT_WALL_MATERIAL
+ desc = "Sheets made out off steel."
singular_name = "metal sheet"
icon_state = "sheet-metal"
- matter = list("metal" = 3750)
+ matter = list(DEFAULT_WALL_MATERIAL = 3750)
throwforce = 14.0
flags = CONDUCT
origin_tech = list(TECH_MATERIAL = 1)
+ sheettype = DEFAULT_WALL_MATERIAL
/obj/item/stack/sheet/metal/cyborg
- name = "metal synthesizer"
- desc = "A device that makes metal sheets."
+ name = "steel synthesizer"
+ desc = "A device that makes steel sheets."
gender = NEUTER
matter = null
uses_charge = 1
@@ -109,21 +110,22 @@ var/global/list/datum/stack_recipe/metal_recipes = list ( \
var/global/list/datum/stack_recipe/plasteel_recipes = list ( \
new/datum/stack_recipe("AI core", /obj/structure/AIcore, 4, time = 50, one_per_turf = 1), \
new/datum/stack_recipe("Metal crate", /obj/structure/closet/crate, 10, time = 50, one_per_turf = 1), \
- new/datum/stack_recipe("RUST fuel assembly port frame", /obj/item/rust_fuel_assembly_port_frame, 12, time = 50, one_per_turf = 1), \
- new/datum/stack_recipe("RUST fuel compressor frame", /obj/item/rust_fuel_compressor_frame, 12, time = 50, one_per_turf = 1), \
+ new/datum/stack_recipe("RUST fuel assembly port frame", /obj/item/frame/rust/assembly, 12, time = 50, one_per_turf = 1), \
+ new/datum/stack_recipe("RUST fuel compressor frame", /obj/item/frame/rust, 12, time = 50, one_per_turf = 1), \
new/datum/stack_recipe("knife grip", /obj/item/butterflyhandle, 4, time = 20, one_per_turf = 0, on_floor = 1),
)
/obj/item/stack/sheet/plasteel
name = "plasteel"
singular_name = "plasteel sheet"
- desc = "This sheet is an alloy of iron and phoron."
+ desc = "This sheet is an alloy of iron and platinum."
icon_state = "sheet-plasteel"
item_state = "sheet-metal"
- matter = list("metal" = 7500)
+ matter = list(DEFAULT_WALL_MATERIAL = 7500)
throwforce = 15.0
flags = CONDUCT
origin_tech = list(TECH_MATERIAL = 2)
+ sheettype = "plasteel"
/obj/item/stack/sheet/plasteel/cyborg
name = "plasteel synthesizer"
@@ -145,8 +147,7 @@ var/global/list/datum/stack_recipe/plasteel_recipes = list ( \
var/global/list/datum/stack_recipe/wood_recipes = list ( \
new/datum/stack_recipe("wooden sandals", /obj/item/clothing/shoes/sandal, 1), \
new/datum/stack_recipe("wood floor tile", /obj/item/stack/tile/wood, 1, 4, 20), \
- new/datum/stack_recipe("table parts", /obj/item/weapon/table_parts/wood, 2), \
- new/datum/stack_recipe("wooden chair", /obj/structure/bed/chair/wood/normal, 3, time = 10, one_per_turf = 1, on_floor = 1), \
+ new/datum/stack_recipe("wooden chair", /obj/structure/bed/chair/wood, 3, time = 10, one_per_turf = 1, on_floor = 1), \
new/datum/stack_recipe("wooden barricade", /obj/structure/barricade/wooden, 5, time = 50, one_per_turf = 1, on_floor = 1), \
new/datum/stack_recipe("crossbow frame", /obj/item/weapon/crossbowframe, 5, time = 25, one_per_turf = 0, on_floor = 0), \
new/datum/stack_recipe("wooden door", /obj/structure/mineral_door/wood, 10, time = 20, one_per_turf = 1, on_floor = 1), \
@@ -161,6 +162,7 @@ var/global/list/datum/stack_recipe/wood_recipes = list ( \
singular_name = "wood plank"
icon_state = "sheet-wood"
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
+ sheettype = "wood"
/obj/item/stack/sheet/wood/cyborg
name = "wood synthesizer"
diff --git a/code/game/objects/items/stacks/stack.dm b/code/game/objects/items/stacks/stack.dm
index 0a43a0e5bba..a589335c772 100644
--- a/code/game/objects/items/stacks/stack.dm
+++ b/code/game/objects/items/stacks/stack.dm
@@ -29,12 +29,12 @@
src.amount = amount
return
-/obj/item/stack/Del()
+/obj/item/stack/Destroy()
if(uses_charge)
- return
+ return 1
if (src && usr && usr.machine == src)
usr << browse(null, "window=stack")
- ..()
+ return ..()
/obj/item/stack/examine(mob/user)
if(..(user, 1))
@@ -139,7 +139,7 @@
if (istype(O, /obj/item/weapon/storage)) //BubbleWrap - so newly formed boxes are empty
for (var/obj/item/I in O)
- del(I)
+ qdel(I)
/obj/item/stack/Topic(href, href_list)
..()
@@ -150,7 +150,7 @@
list_recipes(usr, text2num(href_list["sublist"]))
if (href_list["make"])
- if (src.get_amount() < 1) del(src) //Never should happen
+ if (src.get_amount() < 1) qdel(src) //Never should happen
var/list/recipes_list = recipes
if (href_list["sublist"])
@@ -187,7 +187,7 @@
if (amount <= 0) //check again in case someone transferred stuff to us
if(usr)
usr.remove_from_mob(src)
- del(src)
+ qdel(src)
return 1
else
if(get_amount() < used)
diff --git a/code/game/objects/items/stacks/tiles/light.dm b/code/game/objects/items/stacks/tiles/light.dm
index 3a14ff1e56e..dc57abc513a 100644
--- a/code/game/objects/items/stacks/tiles/light.dm
+++ b/code/game/objects/items/stacks/tiles/light.dm
@@ -33,4 +33,4 @@
new/obj/item/stack/light_w(user.loc)
if(amount <= 0)
user.drop_from_inventory(src)
- del(src)
+ qdel(src)
diff --git a/code/game/objects/items/stacks/tiles/plasteel.dm b/code/game/objects/items/stacks/tiles/plasteel.dm
index 3215d0efaf8..86af65a2fac 100644
--- a/code/game/objects/items/stacks/tiles/plasteel.dm
+++ b/code/game/objects/items/stacks/tiles/plasteel.dm
@@ -4,7 +4,7 @@
desc = "Those could work as a pretty decent throwing weapon"
icon_state = "tile"
force = 6.0
- matter = list("metal" = 937.5)
+ matter = list(DEFAULT_WALL_MATERIAL = 937.5)
throwforce = 15.0
throw_speed = 5
throw_range = 20
diff --git a/code/game/objects/items/toys.dm b/code/game/objects/items/toys.dm
index a39acac9c16..8290296fe00 100644
--- a/code/game/objects/items/toys.dm
+++ b/code/game/objects/items/toys.dm
@@ -8,7 +8,6 @@
* Toy swords
* Toy bosun's whistle
* Toy mechs
- * Crayons
* Snap pops
* Water flower
* Therapy dolls
@@ -48,7 +47,7 @@
/obj/item/toy/balloon/afterattack(atom/A as mob|obj, mob/user as mob, proximity)
if(!proximity) return
if (istype(A, /obj/structure/reagent_dispensers/watertank) && get_dist(src,A) <= 1)
- A.reagents.trans_to(src, 10)
+ A.reagents.trans_to_obj(src, 10)
user << "\blue You fill the balloon with the contents of [A]."
src.desc = "A translucent balloon with some form of liquid sloshing around in it."
src.update_icon()
@@ -61,26 +60,26 @@
user << "The [O] is empty."
else if(O.reagents.total_volume >= 1)
if(O.reagents.has_reagent("pacid", 1))
- user << "The acid chews through the balloon!"
- O.reagents.reaction(user)
- del(src)
+ user << "The acid chews through the balloon!"
+ O.reagents.splash_mob(user, reagents.total_volume)
+ qdel(src)
else
src.desc = "A translucent balloon with some form of liquid sloshing around in it."
user << "\blue You fill the balloon with the contents of [O]."
- O.reagents.trans_to(src, 10)
+ O.reagents.trans_to_obj(src, 10)
src.update_icon()
return
/obj/item/toy/balloon/throw_impact(atom/hit_atom)
if(src.reagents.total_volume >= 1)
src.visible_message("\red The [src] bursts!","You hear a pop and a splash.")
- src.reagents.reaction(get_turf(hit_atom))
+ src.reagents.touch_turf(get_turf(hit_atom))
for(var/atom/A in get_turf(hit_atom))
- src.reagents.reaction(A)
+ src.reagents.touch(A)
src.icon_state = "burst"
spawn(5)
if(src)
- del(src)
+ qdel(src)
return
/obj/item/toy/balloon/update_icon()
@@ -147,7 +146,7 @@
slot_flags = SLOT_BELT|SLOT_HOLSTER
w_class = 3.0
- matter = list("glass" = 10,"metal" = 10)
+ matter = list("glass" = 10,DEFAULT_WALL_MATERIAL = 10)
attack_verb = list("struck", "pistol whipped", "hit", "bashed")
var/bullets = 7.0
@@ -202,7 +201,7 @@
flags = CONDUCT
w_class = 1.0
- matter = list("metal" = 10,"glass" = 10)
+ matter = list(DEFAULT_WALL_MATERIAL = 10,"glass" = 10)
var/amount_left = 7.0
@@ -233,7 +232,7 @@
if(istype(I, /obj/item/toy/ammo/crossbow))
if(bullets <= 4)
user.drop_item()
- del(I)
+ qdel(I)
bullets++
user << "\blue You load the foam dart into the crossbow."
else
@@ -265,21 +264,21 @@
for(var/mob/O in viewers(world.view, D))
O.show_message(text("\red [] was hit by the foam dart!", M), 1)
new /obj/item/toy/ammo/crossbow(M.loc)
- del(D)
+ qdel(D)
return
for(var/atom/A in D.loc)
if(A == user) continue
if(A.density)
new /obj/item/toy/ammo/crossbow(A.loc)
- del(D)
+ qdel(D)
sleep(1)
spawn(10)
if(D)
new /obj/item/toy/ammo/crossbow(D.loc)
- del(D)
+ qdel(D)
return
else if (bullets == 0)
@@ -375,31 +374,6 @@
w_class = 3
attack_verb = list("attacked", "slashed", "stabbed", "sliced")
-/*
- * Crayons
- */
-
-/obj/item/toy/crayon
- name = "crayon"
- desc = "A colourful crayon. Please refrain from eating it or putting it in your nose."
- icon = 'icons/obj/crayons.dmi'
- icon_state = "crayonred"
- w_class = 1.0
- attack_verb = list("attacked", "coloured")
- var/colour = "#FF0000" //RGB
- var/shadeColour = "#220000" //RGB
- var/uses = 30 //0 for unlimited uses
- var/instant = 0
- var/colourName = "red" //for updateIcon purposes
-
- suicide_act(mob/user)
- viewers(user) << "\red [user] is jamming the [src.name] up \his nose and into \his brain. It looks like \he's trying to commit suicide."
- return (BRUTELOSS|OXYLOSS)
-
- New()
- name = "[colourName] crayon"
- ..()
-
/*
* Snap pops
*/
@@ -418,7 +392,7 @@
new /obj/effect/decal/cleanable/ash(src.loc)
src.visible_message("\red The [src.name] explodes!","\red You hear a snap!")
playsound(src, 'sound/effects/snap.ogg', 50, 1)
- del(src)
+ qdel(src)
/obj/item/toy/snappop/Crossed(H as mob|obj)
if((ishuman(H))) //i guess carp and shit shouldn't set them off
@@ -432,7 +406,7 @@
new /obj/effect/decal/cleanable/ash(src.loc)
src.visible_message("\red The [src.name] explodes!","\red You hear a snap!")
playsound(src, 'sound/effects/snap.ogg', 50, 1)
- del(src)
+ qdel(src)
/*
* Water flower
@@ -440,7 +414,7 @@
/obj/item/toy/waterflower
name = "water flower"
desc = "A seemingly innocent sunflower...with a twist."
- //icon = 'icons/obj/harvest.dmi'
+ icon = 'icons/obj/device.dmi'
icon_state = "sunflower"
item_state = "sunflower"
var/empty = 0
@@ -482,19 +456,19 @@
D.icon = 'icons/obj/chemical.dmi'
D.icon_state = "chempuff"
D.create_reagents(5)
- src.reagents.trans_to(D, 1)
+ src.reagents.trans_to_obj(D, 1)
playsound(src.loc, 'sound/effects/spray3.ogg', 50, 1, -6)
spawn(0)
for(var/i=0, i<1, i++)
step_towards(D,A)
- D.reagents.reaction(get_turf(D))
+ D.reagents.touch_turf(get_turf(D))
for(var/atom/T in get_turf(D))
- D.reagents.reaction(T)
+ D.reagents.touch(T)
if(ismob(T) && T:client)
T:client << "\red [user] has sprayed you with water!"
sleep(4)
- del(D)
+ qdel(D)
return
@@ -949,6 +923,11 @@
desc = "A plushie of a fuzzy spider! It has eight legs - all the better to hug you with."
icon_state = "spiderplushie"
+/obj/item/toy/plushie/farwa
+ name = "farwa plush"
+ desc = "A farwa plush doll. It's soft and comforting!"
+ icon_state = "farwaplushie"
+
//Toy cult sword
/obj/item/toy/cultsword
name = "foam sword"
diff --git a/code/game/objects/items/weapons/RCD.dm b/code/game/objects/items/weapons/RCD.dm
index 4784a124045..9784709c512 100644
--- a/code/game/objects/items/weapons/RCD.dm
+++ b/code/game/objects/items/weapons/RCD.dm
@@ -13,8 +13,8 @@
throw_speed = 1
throw_range = 5
w_class = 3.0
- matter = list("metal" = 50000)
origin_tech = list(TECH_ENGINERING = 4, TECH_MATERIAL = 2)
+ matter = list(DEFAULT_WALL_MATERIAL = 50000)
var/datum/effect/effect/system/spark_spread/spark_system
var/stored_matter = 0
var/working = 0
@@ -40,6 +40,11 @@
spark_system.set_up(5, 0, src)
spark_system.attach(src)
+/obj/item/weapon/rcd/Destroy()
+ qdel(spark_system)
+ spark_system = null
+ return ..()
+
/obj/item/weapon/rcd/attackby(obj/item/weapon/W, mob/user)
if(istype(W, /obj/item/weapon/rcd_ammo))
@@ -47,7 +52,7 @@
user << "The RCD can't hold any more matter-units."
return
user.drop_from_inventory(W)
- del(W)
+ qdel(W)
stored_matter += 10
playsound(src.loc, 'sound/machines/click.ogg', 50, 1)
user << "The RCD now holds [stored_matter]/30 matter-units."
@@ -100,9 +105,10 @@
build_type = "floor"
build_turf = /turf/simulated/floor/plating/airless
else if(deconstruct && istype(T,/turf/simulated/wall))
+ var/turf/simulated/wall/W = T
build_delay = deconstruct ? 50 : 40
build_cost = 5
- build_type = (!canRwall && istype(T,/turf/simulated/wall/r_wall)) ? null : "wall"
+ build_type = (!canRwall && W.reinf_material) ? null : "wall"
build_turf = /turf/simulated/floor
else if(istype(T,/turf/simulated/floor))
build_delay = deconstruct ? 50 : 20
@@ -138,7 +144,7 @@
else if(build_other)
new build_other(T)
else
- del(T)
+ qdel(T)
playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
return 1
@@ -153,7 +159,7 @@
density = 0
anchored = 0.0
origin_tech = list(TECH_MATERIAL = 2)
- matter = list("metal" = 30000,"glass" = 15000)
+ matter = list(DEFAULT_WALL_MATERIAL = 30000,"glass" = 15000)
/obj/item/weapon/rcd/borg
canRwall = 1
diff --git a/code/game/objects/items/weapons/RSF.dm b/code/game/objects/items/weapons/RSF.dm
index 596675a094f..b96d53c2a87 100644
--- a/code/game/objects/items/weapons/RSF.dm
+++ b/code/game/objects/items/weapons/RSF.dm
@@ -28,7 +28,7 @@ RSF
user << "The RSF can't hold any more matter."
return
- del(W)
+ qdel(W)
stored_matter += 10
playsound(src.loc, 'sound/machines/click.ogg', 10, 1)
@@ -54,14 +54,9 @@ RSF
user << "Changed dispensing mode to 'Dice Pack'"
return
if (mode == 5)
- mode = 6
+ mode = 1
user << "Changed dispensing mode to 'Cigarette'"
return
- if (mode == 6)
- mode = 1
- user << "Changed dispensing mode to 'Dosh'"
- return
- // Change mode
/obj/item/weapon/rsf/afterattack(atom/A, mob/user as mob, proximity)
@@ -84,8 +79,8 @@ RSF
switch(mode)
if(1)
- product = new /obj/item/weapon/spacecash/c10()
- used_energy = 200
+ product = new /obj/item/clothing/mask/smokable/cigarette()
+ used_energy = 10
if(2)
product = new /obj/item/weapon/reagent_containers/food/drinks/drinkingglass()
used_energy = 50
@@ -98,9 +93,6 @@ RSF
if(5)
product = new /obj/item/weapon/storage/pill_bottle/dice()
used_energy = 200
- if(6)
- product = new /obj/item/clothing/mask/smokable/cigarette()
- used_energy = 10
user << "Dispensing [product ? product : "product"]..."
product.loc = get_turf(A)
diff --git a/code/game/objects/items/weapons/autopsy.dm b/code/game/objects/items/weapons/autopsy.dm
index abd3523da0f..a18a2fbeb61 100644
--- a/code/game/objects/items/weapons/autopsy.dm
+++ b/code/game/objects/items/weapons/autopsy.dm
@@ -68,7 +68,7 @@
else
D.organ_names += ", [O.name]"
- del D.organs_scanned[O.name]
+ qdel(D.organs_scanned[O.name])
D.organs_scanned[O.name] = W.copy()
for(var/V in O.trace_chemicals)
diff --git a/code/game/objects/items/weapons/candle.dm b/code/game/objects/items/weapons/candle.dm
index 6fc63420de1..f5f2a8d9fdf 100644
--- a/code/game/objects/items/weapons/candle.dm
+++ b/code/game/objects/items/weapons/candle.dm
@@ -1,13 +1,17 @@
/obj/item/weapon/flame/candle
name = "red candle"
- desc = "a candle"
+ desc = "a small pillar candle. Its specially-formulated fuel-oxidizer wax mixture allows continued combustion in airless environments."
icon = 'icons/obj/candle.dmi'
icon_state = "candle1"
item_state = "candle1"
w_class = 1
-
+ light_color = "#E09D37"
var/wax = 2000
+/obj/item/weapon/flame/candle/New()
+ wax = rand(800, 1000) // Enough for 27-33 minutes. 30 minutes on average.
+ ..()
+
/obj/item/weapon/flame/candle/update_icon()
var/i
if(wax > 1500)
@@ -44,7 +48,7 @@
//src.damtype = "fire"
for(var/mob/O in viewers(usr, null))
O.show_message(flavor_text, 1)
- SetLuminosity(CANDLE_LUM)
+ set_light(CANDLE_LUM)
processing_objects.Add(src)
@@ -56,28 +60,14 @@
new/obj/item/trash/candle(src.loc)
if(istype(src.loc, /mob))
src.dropped()
- del(src)
+ qdel(src)
update_icon()
if(istype(loc, /turf)) //start a fire if possible
var/turf/T = loc
T.hotspot_expose(700, 5)
-
/obj/item/weapon/flame/candle/attack_self(mob/user as mob)
if(lit)
lit = 0
update_icon()
- SetLuminosity(0)
- user.SetLuminosity(user.luminosity - CANDLE_LUM)
-
-
-/obj/item/weapon/flame/candle/pickup(mob/user)
- if(lit)
- SetLuminosity(0)
- user.SetLuminosity(user.luminosity + CANDLE_LUM)
-
-
-/obj/item/weapon/flame/candle/dropped(mob/user)
- if(lit)
- user.SetLuminosity(user.luminosity - CANDLE_LUM)
- SetLuminosity(CANDLE_LUM)
+ set_light(0)
diff --git a/code/game/objects/items/weapons/cards_ids.dm b/code/game/objects/items/weapons/cards_ids.dm
index 67f1787dac5..b1448f7516d 100644
--- a/code/game/objects/items/weapons/cards_ids.dm
+++ b/code/game/objects/items/weapons/cards_ids.dm
@@ -81,7 +81,7 @@
/obj/item/device/taperecorder,
/obj/item/device/hailer,
/obj/item/device/megaphone,
- /obj/item/clothing/accessory/holobadge,
+ /obj/item/clothing/accessory/badge/holo,
/obj/structure/closet/crate/secure,
/obj/structure/closet/secure_closet,
/obj/machinery/librarycomp,
@@ -92,12 +92,12 @@
/obj/machinery/shield_gen,
/obj/machinery/clonepod,
/obj/machinery/deployable,
- /obj/machinery/door_control,
+ /obj/machinery/button/remote,
/obj/machinery/porta_turret,
/obj/machinery/shieldgen,
/obj/machinery/turretid,
/obj/machinery/vending,
- /obj/machinery/bot,
+ /mob/living/bot,
/obj/machinery/door,
/obj/machinery/telecomms,
/obj/machinery/mecha_part_fabricator,
@@ -118,7 +118,7 @@
user.drop_item()
var/obj/item/weapon/card/emag_broken/junk = new(user.loc)
junk.add_fingerprint(user)
- del(src)
+ qdel(src)
return
..()
@@ -162,17 +162,6 @@
/obj/item/weapon/card/id/GetID()
return src
-/obj/item/weapon/card/id/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
- if(istype(W,/obj/item/weapon/id_wallet))
- user << "You slip [src] into [W]."
- src.name = "[src.registered_name]'s [W.name] ([src.assignment])"
- src.desc = W.desc
- src.icon = W.icon
- src.icon_state = W.icon_state
- del(W)
- return
-
/obj/item/weapon/card/id/verb/read()
set name = "Read ID Card"
set category = "Object"
@@ -224,13 +213,13 @@
/obj/item/weapon/card/id/syndicate/attack_self(mob/user as mob)
if(!src.registered_name)
//Stop giving the players unsanitized unputs! You are giving ways for players to intentionally crash clients! -Nodrak
- var t = sanitizeName(input(user, "What name would you like to put on this card?", "Agent card name", ishuman(user) ? user.real_name : user.name))
+ var t = sanitizeName(input(user, "What name would you like to put on this card?", "Agent card name", ishuman(user) ? user.real_name : user.name), MAX_NAME_LEN)
if(!t) //Same as mob/new_player/prefrences.dm
alert("Invalid name.")
return
src.registered_name = t
- var u = sanitize(input(user, "What occupation would you like to put on this card?\nNote: This will not grant any access levels other than Maintenance.", "Agent card job assignment", "Agent"))
+ var u = sanitize(input(user, "What occupation would you like to put on this card?\nNote: This will not grant any access levels other than Maintenance.", "Agent card job assignment", "Agent"), MAX_LNAME_LEN)
if(!u)
alert("Invalid assignment.")
src.registered_name = ""
@@ -293,3 +282,11 @@
New()
access = get_all_centcom_access()
..()
+
+/obj/item/weapon/card/id/centcom/ERT
+ name = "\improper Emergency Response Team ID"
+ assignment = "Emergency Response Team"
+
+/obj/item/weapon/card/id/centcom/ERT/New()
+ ..()
+ access += get_all_accesses()
diff --git a/code/game/objects/items/weapons/cigs_lighters.dm b/code/game/objects/items/weapons/cigs_lighters.dm
index 25fd11c1ed6..7328b88d78b 100644
--- a/code/game/objects/items/weapons/cigs_lighters.dm
+++ b/code/game/objects/items/weapons/cigs_lighters.dm
@@ -93,9 +93,9 @@ CIGARETTE PACKETS ARE IN FANCY.DM
flags |= NOREACT // so it doesn't react until you light it
create_reagents(chem_volume) // making the cigarrete a chemical holder with a maximum volume of 15
-/obj/item/clothing/mask/smokable/Del()
+/obj/item/clothing/mask/smokable/Destroy()
..()
- del(reagents)
+ qdel(reagents)
/obj/item/clothing/mask/smokable/process()
var/turf/location = get_turf(src)
@@ -114,10 +114,9 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(H.species.flags & IS_SYNTHETIC)
return
- reagents.trans_to(C, REAGENTS_METABOLISM, 0.2) // Most of it is not inhaled... balance reasons.
- reagents.reaction(C)
+ reagents.trans_to_mob(C, REM, CHEM_INGEST, 0.2) // Most of it is not inhaled... balance reasons.
else // else just remove some of the reagents
- reagents.remove_any(REAGENTS_METABOLISM)
+ reagents.remove_any(REM)
/obj/item/clothing/mask/smokable/proc/light(var/flavor_text = "[usr] lights the [name].")
if(!src.lit)
@@ -127,13 +126,13 @@ CIGARETTE PACKETS ARE IN FANCY.DM
var/datum/effect/effect/system/reagents_explosion/e = new()
e.set_up(round(reagents.get_reagent_amount("phoron") / 2.5, 1), get_turf(src), 0, 0)
e.start()
- del(src)
+ qdel(src)
return
if(reagents.get_reagent_amount("fuel")) // the fuel explodes, too, but much less violently
var/datum/effect/effect/system/reagents_explosion/e = new()
e.set_up(round(reagents.get_reagent_amount("fuel") / 5, 1), get_turf(src), 0, 0)
e.start()
- del(src)
+ qdel(src)
return
flags &= ~NOREACT // allowing reagents to react after being lit
reagents.handle_reactions()
@@ -146,10 +145,12 @@ CIGARETTE PACKETS ARE IN FANCY.DM
M.update_inv_r_hand(1)
var/turf/T = get_turf(src)
T.visible_message(flavor_text)
+ set_light(2, 0.25, "#E38F46")
processing_objects.Add(src)
/obj/item/clothing/mask/smokable/proc/die(var/nomessage = 0)
var/turf/T = get_turf(src)
+ set_light(0)
if (type_butt)
var/obj/item/butt = new type_butt(T)
transfer_fingerprints_to(butt)
@@ -162,7 +163,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
M.update_inv_l_hand(0)
M.update_inv_r_hand(1)
processing_objects.Remove(src)
- del(src)
+ qdel(src)
else
new /obj/effect/decal/cleanable/ash(T)
if(ismob(loc))
@@ -176,7 +177,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
M.update_inv_l_hand(0)
M.update_inv_r_hand(1)
processing_objects.Remove(src)
-
+
/obj/item/clothing/mask/smokable/attackby(obj/item/weapon/W as obj, mob/user as mob)
..()
if(isflamesource(W))
@@ -221,7 +222,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(istype(W, /obj/item/weapon/melee/energy/sword))
var/obj/item/weapon/melee/energy/sword/S = W
if(S.active)
- light("[user] swings their [W], barely missing their nose. They light their [name] in the process.")
+ light("[user] swings their [W], barely missing their nose. They light their [name] in the process.")
return
@@ -230,7 +231,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(!proximity)
return
if(istype(glass)) //you can dip cigarettes into beakers
- var/transfered = glass.reagents.trans_to(src, chem_volume)
+ var/transfered = glass.reagents.trans_to_obj(src, chem_volume)
if(transfered) //if reagents were transfered, show the message
user << "You dip \the [src] into \the [glass]."
else //if not, either the beaker was empty, or the cigarette was full
@@ -375,9 +376,9 @@ CIGARETTE PACKETS ARE IN FANCY.DM
return
smoketime = 1000
if(G.reagents)
- G.reagents.trans_to(src, G.reagents.total_volume)
+ G.reagents.trans_to_obj(src, G.reagents.total_volume)
name = "[G.name]-packed [initial(name)]"
- del(G)
+ qdel(G)
else if(istype(W, /obj/item/weapon/flame/lighter))
var/obj/item/weapon/flame/lighter/L = W
@@ -414,35 +415,33 @@ CIGARETTE PACKETS ARE IN FANCY.DM
icon = 'icons/obj/items.dmi'
icon_state = "lighter-g"
item_state = "lighter-g"
- var/icon_on = "lighter-g-on"
- var/icon_off = "lighter-g"
w_class = 1
throwforce = 4
flags = CONDUCT
slot_flags = SLOT_BELT
attack_verb = list("burnt", "singed")
+ var/base_state
/obj/item/weapon/flame/lighter/zippo
name = "\improper Zippo lighter"
desc = "The zippo."
icon_state = "zippo"
item_state = "zippo"
- icon_on = "zippoon"
- icon_off = "zippo"
/obj/item/weapon/flame/lighter/random
New()
- var/color = pick("r","c","y","g")
- icon_on = "lighter-[color]-on"
- icon_off = "lighter-[color]"
- icon_state = icon_off
+ icon_state = "lighter-[pick("r","c","y","g")]"
+ item_state = icon_state
+ base_state = icon_state
/obj/item/weapon/flame/lighter/attack_self(mob/living/user)
+ if(!base_state)
+ base_state = icon_state
if(user.r_hand == src || user.l_hand == src)
if(!lit)
lit = 1
- icon_state = icon_on
- item_state = icon_on
+ icon_state = "[base_state]on"
+ item_state = "[base_state]on"
if(istype(src, /obj/item/weapon/flame/lighter/zippo) )
user.visible_message("Without even breaking stride, [user] flips open and lights [src] in one smooth movement.")
else
@@ -456,18 +455,18 @@ CIGARETTE PACKETS ARE IN FANCY.DM
user.apply_damage(2,BURN,"r_hand")
user.visible_message("After a few attempts, [user] manages to light the [src], they however burn their finger in the process.")
- user.SetLuminosity(user.luminosity + 2)
+ set_light(2)
processing_objects.Add(src)
else
lit = 0
- icon_state = icon_off
- item_state = icon_off
+ icon_state = "[base_state]"
+ item_state = "[base_state]"
if(istype(src, /obj/item/weapon/flame/lighter/zippo) )
user.visible_message("You hear a quiet click, as [user] shuts off [src] without even looking at what they're doing.")
else
user.visible_message("[user] quietly shuts off the [src].")
- user.SetLuminosity(user.luminosity - 2)
+ set_light(0)
processing_objects.Remove(src)
else
return ..()
@@ -496,17 +495,3 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(location)
location.hotspot_expose(700, 5)
return
-
-
-/obj/item/weapon/flame/lighter/pickup(mob/user)
- if(lit)
- SetLuminosity(0)
- user.SetLuminosity(user.luminosity+2)
- return
-
-
-/obj/item/weapon/flame/lighter/dropped(mob/user)
- if(lit)
- user.SetLuminosity(user.luminosity-2)
- SetLuminosity(2)
- return
diff --git a/code/game/objects/items/weapons/circuitboards/circuitboard.dm b/code/game/objects/items/weapons/circuitboards/circuitboard.dm
index 6c1e3569f77..fd30153c37a 100644
--- a/code/game/objects/items/weapons/circuitboards/circuitboard.dm
+++ b/code/game/objects/items/weapons/circuitboards/circuitboard.dm
@@ -21,7 +21,6 @@
var/build_path = null
var/board_type = "computer"
var/list/req_components = null
- var/frame_desc = null
var/contain_parts = 1
//Called when the circuitboard is used to contruct a new machine.
diff --git a/code/game/objects/items/weapons/circuitboards/computer/camera_monitor.dm b/code/game/objects/items/weapons/circuitboards/computer/camera_monitor.dm
index e45f51a088d..b7da10cc22e 100644
--- a/code/game/objects/items/weapons/circuitboards/computer/camera_monitor.dm
+++ b/code/game/objects/items/weapons/circuitboards/computer/camera_monitor.dm
@@ -5,16 +5,23 @@
/obj/item/weapon/circuitboard/security
name = T_BOARD("security camera monitor")
build_path = /obj/machinery/computer/security
- var/network = list("SS13")
req_access = list(access_security)
+ var/list/network
var/locked = 1
var/emagged = 0
+
+/obj/item/weapon/circuitboard/security/New()
+ ..()
+ network = station_networks
/obj/item/weapon/circuitboard/security/engineering
name = T_BOARD("engineering camera monitor")
build_path = /obj/machinery/computer/security/engineering
- network = list("Engineering","Power Alarms","Atmosphere Alarms","Fire Alarms")
req_access = list()
+
+/obj/item/weapon/circuitboard/security/engineering/New()
+ ..()
+ network = engineering_networks
/obj/item/weapon/circuitboard/security/mining
name = T_BOARD("mining camera monitor")
diff --git a/code/game/objects/items/weapons/circuitboards/computer/computer.dm b/code/game/objects/items/weapons/circuitboards/computer/computer.dm
index 3ba7ac49a40..82d26686ee3 100644
--- a/code/game/objects/items/weapons/circuitboards/computer/computer.dm
+++ b/code/game/objects/items/weapons/circuitboards/computer/computer.dm
@@ -57,9 +57,17 @@
name = T_BOARD("employment records console")
build_path = /obj/machinery/computer/skills
-/obj/item/weapon/circuitboard/stationalert
- name = T_BOARD("station alert console")
+/obj/item/weapon/circuitboard/stationalert_engineering
+ name = T_BOARD("station alert console (engineering)")
build_path = /obj/machinery/computer/station_alert
+
+/obj/item/weapon/circuitboard/stationalert_security
+ name = T_BOARD("station alert console (security)")
+ build_path = /obj/machinery/computer/station_alert
+
+/obj/item/weapon/circuitboard/stationalert_all
+ name = T_BOARD("station alert console (all)")
+ build_path = /obj/machinery/computer/station_alert/all
/obj/item/weapon/circuitboard/atmos_alert
name = T_BOARD("atmospheric alert console")
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/biogenerator.dm b/code/game/objects/items/weapons/circuitboards/machinery/biogenerator.dm
index 42abd94ca40..65949ae338b 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/biogenerator.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/biogenerator.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/biogenerator"
board_type = "machine"
origin_tech = list(TECH_DATA = 2)
- frame_desc = "Requires 1 Manipulator, and 1 Matter Bin."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 1,
"/obj/item/weapon/stock_parts/manipulator" = 1)
\ No newline at end of file
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/cloning.dm b/code/game/objects/items/weapons/circuitboards/machinery/cloning.dm
index 2807f5553ac..b80a3abd34a 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/cloning.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/cloning.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/clonepod"
board_type = "machine"
origin_tech = list(TECH_DATA = 3, TECH_BIO = 3)
- frame_desc = "Requires 2 Manipulator, 2 Scanning Module, 2 pieces of cable and 1 Console Screen."
req_components = list(
"/obj/item/stack/cable_coil" = 2,
"/obj/item/weapon/stock_parts/scanning_module" = 2,
@@ -19,7 +18,6 @@
build_path = "/obj/machinery/dna_scannernew"
board_type = "machine"
origin_tech = list(TECH_DATA = 2, TECH_BIO = 2)
- frame_desc = "Requires 1 Scanning module, 1 Micro Manipulator, 1 Micro-Laser, 2 pieces of cable and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/scanning_module" = 1,
"/obj/item/weapon/stock_parts/manipulator" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/commsantenna.dm b/code/game/objects/items/weapons/circuitboards/machinery/commsantenna.dm
new file mode 100644
index 00000000000..badfb22a010
--- /dev/null
+++ b/code/game/objects/items/weapons/circuitboards/machinery/commsantenna.dm
@@ -0,0 +1,15 @@
+#ifndef T_BOARD
+#error T_BOARD macro is not defined but we need it!
+#endif
+
+/obj/item/weapon/circuitboard/bluespacerelay
+ name = T_BOARD("bluespacerelay")
+ build_path = "/obj/machinery/bluespacerelay"
+ board_type = "machine"
+ origin_tech = list(TECH_BLUESPACE = 2, TECH_DATA = 2)
+ req_components = list(
+ "/obj/item/stack/cable_coil" = 30,
+ "/obj/item/weapon/stock_parts/manipulator" = 2,
+ "/obj/item/weapon/stock_parts/subspace/filter" = 1,
+ "/obj/item/weapon/stock_parts/subspace/crystal" = 1,
+ )
\ No newline at end of file
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/mining_drill.dm b/code/game/objects/items/weapons/circuitboards/machinery/mining_drill.dm
index dfce002fcd4..417b8c56d59 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/mining_drill.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/mining_drill.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/mining/drill"
board_type = "machine"
origin_tech = list(TECH_DATA = 1, TECH_ENGINERING = 1)
- frame_desc = "Requires 1 capacitor, 1 cell, 1 matter bin, and 1 micro laser."
req_components = list(
"/obj/item/weapon/stock_parts/capacitor" = 1,
"/obj/item/weapon/cell" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/pacman.dm b/code/game/objects/items/weapons/circuitboards/machinery/pacman.dm
index 6f39f9ccd90..86e730e39a0 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/pacman.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/pacman.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/power/port_gen/pacman"
board_type = "machine"
origin_tech = list(TECH_DATA = 3, TECH_POWER = 3, TECH_PHORON = 3, TECH_ENGINERING = 3)
- frame_desc = "Requires 1 Matter Bin, 1 Micro-Laser, 2 Pieces of Cable, and 1 Capacitor."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 1,
"/obj/item/weapon/stock_parts/micro_laser" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/power.dm b/code/game/objects/items/weapons/circuitboards/machinery/power.dm
index bddeae03db9..4e280716e5b 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/power.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/power.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/power/smes/buildable"
board_type = "machine"
origin_tech = list(TECH_POWER = 6, TECH_ENGINERING = 4)
- frame_desc = "Requires 1 superconducting magnetic coil and 30 wires."
req_components = list("/obj/item/weapon/smes_coil" = 1, "/obj/item/stack/cable_coil" = 30)
/obj/item/weapon/circuitboard/batteryrack
@@ -15,7 +14,6 @@
build_path = "/obj/machinery/power/smes/batteryrack"
board_type = "machine"
origin_tech = list(TECH_POWER = 3, TECH_ENGINERING = 2)
- frame_desc = "Requires 3 power cells."
req_components = list("/obj/item/weapon/cell" = 3)
/obj/item/weapon/circuitboard/ghettosmes
@@ -23,5 +21,4 @@
desc = "An APC circuit repurposed into some power storage device controller"
build_path = "/obj/machinery/power/smes/batteryrack/makeshift"
board_type = "machine"
- frame_desc = "Requires 3 power cells."
req_components = list("/obj/item/weapon/cell" = 3)
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/recharge_station.dm b/code/game/objects/items/weapons/circuitboards/machinery/recharge_station.dm
index 9277c31578b..642b36b3b96 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/recharge_station.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/recharge_station.dm
@@ -7,7 +7,6 @@
build_path = "/obj/machinery/recharge_station"
board_type = "machine"
origin_tech = list(TECH_DATA = 3, TECH_ENGINERING = 3)
- frame_desc = "Requires 2 Manipulator, 2 Capacitor, 1 Cell, and 5 pieces of cable."
req_components = list(
"/obj/item/stack/cable_coil" = 5,
"/obj/item/weapon/stock_parts/capacitor" = 2,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/research.dm b/code/game/objects/items/weapons/circuitboards/machinery/research.dm
index 7f5d298a96b..2dce038e3db 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/research.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/research.dm
@@ -7,7 +7,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/r_n_d/server"
board_type = "machine"
origin_tech = list(TECH_DATA = 3)
- frame_desc = "Requires 2 pieces of cable, and 1 Scanning Module."
req_components = list(
"/obj/item/stack/cable_coil" = 2,
"/obj/item/weapon/stock_parts/scanning_module" = 1)
@@ -17,7 +16,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/r_n_d/destructive_analyzer"
board_type = "machine"
origin_tech = list(TECH_MAGNET = 2, TECH_ENGINERING = 2, TECH_DATA = 2)
- frame_desc = "Requires 1 Scanning Module, 1 Micro Manipulator, and 1 Micro-Laser."
req_components = list(
"/obj/item/weapon/stock_parts/scanning_module" = 1,
"/obj/item/weapon/stock_parts/manipulator" = 1,
@@ -28,7 +26,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/autolathe"
board_type = "machine"
origin_tech = list(TECH_ENGINERING = 2, TECH_DATA = 2)
- frame_desc = "Requires 3 Matter Bins, 1 Micro Manipulator, and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 3,
"/obj/item/weapon/stock_parts/manipulator" = 1,
@@ -39,7 +36,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/r_n_d/protolathe"
board_type = "machine"
origin_tech = list(TECH_ENGINERING = 2, TECH_DATA = 2)
- frame_desc = "Requires 2 Matter Bins, 2 Micro Manipulators, and 2 Beakers."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 2,
"/obj/item/weapon/stock_parts/manipulator" = 2,
@@ -51,7 +47,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/r_n_d/circuit_imprinter"
board_type = "machine"
origin_tech = list(TECH_ENGINERING = 2, TECH_DATA = 2)
- frame_desc = "Requires 1 Matter Bin, 1 Micro Manipulator, and 2 Beakers."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 1,
"/obj/item/weapon/stock_parts/manipulator" = 1,
@@ -62,7 +57,6 @@ obj/item/weapon/circuitboard/rdserver
build_path = "/obj/machinery/mecha_part_fabricator"
board_type = "machine"
origin_tech = list(TECH_DATA = 3, TECH_ENGINERING = 3)
- frame_desc = "Requires 2 Matter Bins, 1 Micro Manipulator, 1 Micro-Laser and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/matter_bin" = 2,
"/obj/item/weapon/stock_parts/manipulator" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/shieldgen.dm b/code/game/objects/items/weapons/circuitboards/machinery/shieldgen.dm
index 510689560eb..6dc0a3f7ab8 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/shieldgen.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/shieldgen.dm
@@ -7,7 +7,6 @@
board_type = "machine"
build_path = "/obj/machinery/shield_gen/external"
origin_tech = list(TECH_BLUESPACE = 4, TECH_PHORON = 3)
- frame_desc = "Requires 2 Pico Manipulators, 1 Subspace Transmitter, 5 Pieces of cable, 1 Subspace Crystal, 1 Subspace Amplifier and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator/pico" = 2,
"/obj/item/weapon/stock_parts/subspace/transmitter" = 1,
@@ -21,7 +20,6 @@
board_type = "machine"
build_path = "/obj/machinery/shield_gen"
origin_tech = list(TECH_BLUESPACE = 4, TECH_PHORON = 3)
- frame_desc = "Requires 2 Pico Manipulators, 1 Subspace Transmitter, 5 Pieces of cable, 1 Subspace Crystal, 1 Subspace Amplifier and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator/pico" = 2,
"/obj/item/weapon/stock_parts/subspace/transmitter" = 1,
@@ -35,7 +33,6 @@
board_type = "machine"
build_path = "/obj/machinery/shield_capacitor"
origin_tech = list(TECH_MAGNET = 3, TECH_POWER = 4)
- frame_desc = "Requires 2 Pico Manipulators, 1 Subspace Filter, 5 Pieces of cable, 1 Subspace Treatment disk, 1 Subspace Analyzer and 1 Console Screen."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator/pico" = 2,
"/obj/item/weapon/stock_parts/subspace/filter" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/telecomms.dm b/code/game/objects/items/weapons/circuitboards/machinery/telecomms.dm
index 5a5b200702c..3a20c8d358b 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/telecomms.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/telecomms.dm
@@ -9,7 +9,6 @@
name = T_BOARD("subspace receiver")
build_path = "/obj/machinery/telecomms/receiver"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 3, TECH_BLUESPACE = 2)
- frame_desc = "Requires 1 Subspace Ansible, 1 Hyperwave Filter, 2 Micro Manipulators, and 1 Micro-Laser."
req_components = list(
"/obj/item/weapon/stock_parts/subspace/ansible" = 1,
"/obj/item/weapon/stock_parts/subspace/filter" = 1,
@@ -20,7 +19,6 @@
name = T_BOARD("hub mainframe")
build_path = "/obj/machinery/telecomms/hub"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 4)
- frame_desc = "Requires 2 Micro Manipulators, 2 Cable Coil and 2 Hyperwave Filter."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 2,
"/obj/item/stack/cable_coil" = 2,
@@ -30,7 +28,6 @@
name = T_BOARD("relay mainframe")
build_path = "/obj/machinery/telecomms/relay"
origin_tech = list(TECH_DATA = 3, TECH_ENGINERING = 4, TECH_BLUESPACE = 3)
- frame_desc = "Requires 2 Micro Manipulators, 2 Cable Coil and 2 Hyperwave Filters."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 2,
"/obj/item/stack/cable_coil" = 2,
@@ -40,7 +37,6 @@
name = T_BOARD("bus mainframe")
build_path = "/obj/machinery/telecomms/bus"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 4)
- frame_desc = "Requires 2 Micro Manipulators, 1 Cable Coil and 1 Hyperwave Filter."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 2,
"/obj/item/stack/cable_coil" = 1,
@@ -50,7 +46,6 @@
name = T_BOARD("processor unit")
build_path = "/obj/machinery/telecomms/processor"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 4)
- frame_desc = "Requires 3 Micro Manipulators, 1 Hyperwave Filter, 2 Treatment Disks, 1 Wavelength Analyzer, 2 Cable Coils and 1 Subspace Amplifier."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 3,
"/obj/item/weapon/stock_parts/subspace/filter" = 1,
@@ -63,7 +58,6 @@
name = T_BOARD("telecommunication server")
build_path = "/obj/machinery/telecomms/server"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 4)
- frame_desc = "Requires 2 Micro Manipulators, 1 Cable Coil and 1 Hyperwave Filter."
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 2,
"/obj/item/stack/cable_coil" = 1,
@@ -73,7 +67,6 @@
name = T_BOARD("subspace broadcaster")
build_path = "/obj/machinery/telecomms/broadcaster"
origin_tech = list(TECH_DATA = 4, TECH_ENGINERING = 4, TECH_BLUESPACE = 2)
- frame_desc = "Requires 2 Micro Manipulators, 1 Cable Coil, 1 Hyperwave Filter, 1 Ansible Crystal and 2 High-Powered Micro-Lasers. "
req_components = list(
"/obj/item/weapon/stock_parts/manipulator" = 2,
"/obj/item/stack/cable_coil" = 1,
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/unary_atmos.dm b/code/game/objects/items/weapons/circuitboards/machinery/unary_atmos.dm
index af12bf90c78..394927ac725 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/unary_atmos.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/unary_atmos.dm
@@ -17,7 +17,6 @@
name = T_BOARD("gas heating system")
build_path = "/obj/machinery/atmospherics/unary/heater"
origin_tech = list(TECH_POWER = 2, TECH_ENGINERING = 1)
- frame_desc = "Requires 5 Pieces of Cable, 1 Matter Bin, and 2 Capacitors."
req_components = list(
"/obj/item/stack/cable_coil" = 5,
"/obj/item/weapon/stock_parts/matter_bin" = 1,
@@ -27,7 +26,6 @@
name = T_BOARD("gas cooling system")
build_path = "/obj/machinery/atmospherics/unary/freezer"
origin_tech = list(TECH_MAGNET = 2, TECH_ENGINERING = 2)
- frame_desc = "Requires 2 Pieces of Cable, 1 Matter Bin, 1 Micro Manipulator, and 2 Capacitors."
req_components = list(
"/obj/item/stack/cable_coil" = 2,
"/obj/item/weapon/stock_parts/matter_bin" = 1,
diff --git a/code/game/objects/items/weapons/clown_items.dm b/code/game/objects/items/weapons/clown_items.dm
index 656197fee07..f86359c21de 100644
--- a/code/game/objects/items/weapons/clown_items.dm
+++ b/code/game/objects/items/weapons/clown_items.dm
@@ -28,7 +28,11 @@
user << "You need to take that [target.name] off before cleaning it."
else if(istype(target,/obj/effect/decal/cleanable))
user << "You scrub \the [target.name] out."
- del(target)
+ qdel(target)
+ else if(istype(target,/turf))
+ user << "You scrub \the [target.name] clean."
+ var/turf/T = target
+ T.clean()
else
user << "You clean \the [target.name]."
target.clean_blood()
diff --git a/code/game/objects/items/weapons/dna_injector.dm b/code/game/objects/items/weapons/dna_injector.dm
index dfd221650b7..b94fd2d3606 100644
--- a/code/game/objects/items/weapons/dna_injector.dm
+++ b/code/game/objects/items/weapons/dna_injector.dm
@@ -92,107 +92,47 @@
spawn(0)//this prevents the collapse of space-time continuum
if (user)
user.drop_from_inventory(src)
- del(src)
+ qdel(src)
return uses
/obj/item/weapon/dnainjector/attack(mob/M as mob, mob/user as mob)
if (!istype(M, /mob))
return
- if (!(istype(usr, /mob/living/carbon/human) || ticker) && ticker.mode.name != "monkey")
- user << "\red You don't have the dexterity to do this!"
+ if (!usr.IsAdvancedToolUser())
return
+ if(inuse)
+ return 0
+
+ user.visible_message("\The [user] is trying to inject \the [M] with \the [src]!")
+ inuse = 1
+ s_time = world.time
+ spawn(50)
+ inuse = 0
+
+ if(!do_after(user,50))
+ return
+
+ M.visible_message("\The [M] has been injected with \the [src] by \the [user].")
+
+ var/mob/living/carbon/human/H = M
+ if(!istype(H))
+ user << "Apparently it didn't work..."
+ return
+
+ // Used by admin log.
+ var/injected_with_monkey = ""
+ if((buf.types & DNA2_BUF_SE) && (block ? (GetState() && block == MONKEYBLOCK) : GetState(MONKEYBLOCK)))
+ injected_with_monkey = " (MONKEY)"
M.attack_log += text("\[[time_stamp()]\] Has been injected with [name] by [user.name] ([user.ckey])")
user.attack_log += text("\[[time_stamp()]\] Used the [name] to inject [M.name] ([M.ckey])")
log_attack("[user.name] ([user.ckey]) used the [name] to inject [M.name] ([M.ckey])")
+ message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with \the [src][injected_with_monkey]")
- if (user)
- if (istype(M, /mob/living/carbon/human))
- if(!inuse)
- var/obj/effect/equip_e/human/O = new /obj/effect/equip_e/human( )
- O.source = user
- O.target = M
- O.item = src
- O.s_loc = user.loc
- O.t_loc = M.loc
- O.place = "dnainjector"
- src.inuse = 1
- spawn(50) // Not the best fix. There should be an failure proc, for /effect/equip_e/, which is called when the first initital checks fail
- inuse = 0
- M.requests += O
- if (buf.types & DNA2_BUF_SE)
- if(block)// Isolated injector
- testing("Isolated block [block] injector with contents: [GetValue()]")
- if (GetState() && block == MONKEYBLOCK && istype(M, /mob/living/carbon/human) )
- message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the Isolated [name] \red(MONKEY)")
- log_attack("[key_name(user)] injected [key_name(M)] with the Isolated [name] (MONKEY)")
- log_game("[key_name_admin(user)] injected [key_name_admin(M)] with the Isolated [name] \red(MONKEY)")
- else
- log_attack("[key_name(user)] injected [key_name(M)] with the Isolated [name]")
- else
- testing("DNA injector with contents: [english_list(buf.dna.SE)]")
- if (GetState(MONKEYBLOCK) && istype(M, /mob/living/carbon/human) )
- message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name] \red(MONKEY)")
- log_attack("[key_name(user)] injected [key_name(M)] with the [name] (MONKEY)")
- log_game("[key_name_admin(user)] injected [key_name_admin(M)] with the [name] \red(MONKEY)")
- else
- // message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name]")
- log_attack("[key_name(user)] injected [key_name(M)] with the [name]")
- else
- // message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name]")
- log_attack("[key_name(user)] injected [key_name(M)] with the [name]")
-
- spawn( 0 )
- O.process()
- return
- else
- if(!inuse)
-
- for(var/mob/O in viewers(M, null))
- O.show_message(text("\red [] has been injected with [] by [].", M, src, user), 1)
- //Foreach goto(192)
- if (!(istype(M, /mob/living/carbon/human)))
- user << "\red Apparently it didn't work."
- return
-
- if (buf.types & DNA2_BUF_SE)
- if(block)// Isolated injector
- testing("Isolated block [block] injector with contents: [GetValue()]")
- if (GetState() && block == MONKEYBLOCK && istype(M, /mob/living/carbon/human) )
- message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the Isolated [name] \red(MONKEY)")
- log_attack("[key_name(user)] injected [key_name(M)] with the Isolated [name] (MONKEY)")
- log_game("[key_name_admin(user)] injected [key_name_admin(M)] with the Isolated [name] \red(MONKEY)")
- else
- log_attack("[key_name(user)] injected [key_name(M)] with the Isolated [name]")
- else
- testing("DNA injector with contents: [english_list(buf.dna.SE)]")
- if (GetState(MONKEYBLOCK) && istype(M, /mob/living/carbon/human))
- message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name] \red(MONKEY)")
- log_game("[key_name(user)] injected [key_name(M)] with the [name] (MONKEY)")
- else
- // message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name]")
- log_game("[key_name(user)] injected [key_name(M)] with the [name]")
- else
-// message_admins("[key_name_admin(user)] injected [key_name_admin(M)] with the [name]")
- log_game("[key_name(user)] injected [key_name(M)] with the [name]")
- inuse = 1
- inject(M, user)//Now we actually do the heavy lifting.
- spawn(50)
- inuse = 0
- /*
- A user injecting themselves could mean their own transformation and deletion of mob.
- I don't have the time to figure out how this code works so this will do for now.
- I did rearrange things a bit.
- */
- if(user)//If the user still exists. Their mob may not.
- if(M)//Runtime fix: If the mob doesn't exist, mob.name doesnt work. - Nodrak
- user.show_message(text("\red You inject [M.name]"))
- else
- user.show_message(text("\red You finish the injection."))
+ // Apply the DNA shit.
+ inject(M, user)
return
-
-
/obj/item/weapon/dnainjector/hulkmut
name = "\improper DNA injector (Hulk)"
desc = "This will make you big and strong, but give you a bad skin condition."
diff --git a/code/game/objects/items/weapons/explosives.dm b/code/game/objects/items/weapons/explosives.dm
index f35787cca6a..1d25089ecac 100644
--- a/code/game/objects/items/weapons/explosives.dm
+++ b/code/game/objects/items/weapons/explosives.dm
@@ -80,7 +80,7 @@
target.ex_act(1)
if(target)
target.overlays -= image_overlay
- del(src) // qdel
+ qdel(src)
/obj/item/weapon/plastique/attack(mob/M as mob, mob/user as mob, def_zone)
return
diff --git a/code/game/objects/items/weapons/extinguisher.dm b/code/game/objects/items/weapons/extinguisher.dm
index 4408e998ce6..9a0e5eef78a 100644
--- a/code/game/objects/items/weapons/extinguisher.dm
+++ b/code/game/objects/items/weapons/extinguisher.dm
@@ -11,7 +11,7 @@
throw_speed = 2
throw_range = 10
force = 10.0
- matter = list("metal" = 90)
+ matter = list(DEFAULT_WALL_MATERIAL = 90)
attack_verb = list("slammed", "whacked", "bashed", "thunked", "battered", "bludgeoned", "thrashed")
var/spray_particles = 6
@@ -31,15 +31,11 @@
w_class = 2.0
force = 3.0
max_water = 60
- spray_particles = 6
- spray_amount = 2
sprite_name = "miniFE"
/obj/item/weapon/extinguisher/New()
- var/datum/reagents/R = new/datum/reagents(max_water)
- reagents = R
- R.my_atom = src
- R.add_reagent("water", max_water)
+ create_reagents(max_water)
+ reagents.add_reagent("water", max_water)
/obj/item/weapon/extinguisher/examine(mob/user)
if(..(user, 0))
@@ -53,19 +49,19 @@
user << "The safety is [safety ? "on" : "off"]."
return
-/obj/item/weapon/extinguisher/afterattack(atom/target, mob/user , flag)
+/obj/item/weapon/extinguisher/afterattack(var/atom/target, var/mob/user, var/flag)
//TODO; Add support for reagents in water.
- if( istype(target, /obj/structure/reagent_dispensers/watertank) && get_dist(src,target) <= 1)
+ if( istype(target, /obj/structure/reagent_dispensers/watertank) && flag)
var/obj/o = target
- var/amount = o.reagents.trans_to(src, 50)
- user << "\blue You fill [src] with [amount] units of the contents of [target]."
+ var/amount = o.reagents.trans_to_obj(src, 50)
+ user << "You fill [src] with [amount] units of the contents of [target]."
playsound(src.loc, 'sound/effects/refill.ogg', 50, 1, -6)
return
if (!safety)
if (src.reagents.total_volume < 1)
- usr << "\red \The [src] is empty."
+ usr << "\The [src] is empty."
return
if (world.time < src.last_use + 20)
@@ -77,35 +73,35 @@
var/direction = get_dir(src,target)
- if(usr.buckled && isobj(usr.buckled) && !usr.buckled.anchored )
+ if(user.buckled && isobj(user.buckled) && !user.buckled.anchored )
spawn(0)
var/obj/structure/bed/chair/C = null
- if(istype(usr.buckled, /obj/structure/bed/chair))
- C = usr.buckled
- var/obj/B = usr.buckled
+ if(istype(user.buckled, /obj/structure/bed/chair))
+ C = user.buckled
+ var/obj/B = user.buckled
var/movementdirection = turn(direction,180)
if(C) C.propelled = 4
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
sleep(1)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
if(C) C.propelled = 3
sleep(1)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
sleep(1)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
if(C) C.propelled = 2
sleep(2)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
if(C) C.propelled = 1
sleep(2)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
if(C) C.propelled = 0
sleep(3)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
sleep(3)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
sleep(3)
- B.Move(get_step(usr,movementdirection), movementdirection)
+ B.Move(get_step(user,movementdirection), movementdirection)
var/turf/T = get_turf(target)
var/turf/T1 = get_step(T,turn(direction, 90))
@@ -113,33 +109,24 @@
var/list/the_targets = list(T,T1,T2)
- for(var/a=0, a < spray_particles, a++)
- spawn(0)
- var/obj/effect/effect/water/W = new /obj/effect/effect/water( get_turf(src) )
- var/turf/my_target = pick(the_targets)
- var/datum/reagents/R = new/datum/reagents(spray_amount)
- if(!W) return
- W.reagents = R
- R.my_atom = W
- if(!W || !src) return
- src.reagents.trans_to(W, spray_amount)
-
- for(var/b=0, b<5, b++)
- step_towards(W,my_target)
- if(!W || !W.reagents) return
- W.reagents.reaction(get_turf(W))
- for(var/atom/atm in get_turf(W))
- if(!W)
- return
- if(!W.reagents)
- break
- W.reagents.reaction(atm)
- if(isliving(atm)) //For extinguishing mobs on fire
- var/mob/living/M = atm
- M.ExtinguishMob()
- if(W.loc == my_target) break
- sleep(2)
- W.delete()
+ for(var/a = 1 to spray_particles)
+ spawn(0)
+ var/obj/effect/effect/water/W = PoolOrNew(new /obj/effect/effect/water, get_turf(src))
+ var/turf/my_target
+ if(a == 1)
+ my_target = T
+ else if(a == 2)
+ my_target = T1
+ else if(a == 3)
+ my_target = T2
+ else
+ my_target = pick(the_targets)
+ W.create_reagents(spray_amount)
+ if(!src)
+ return
+ reagents.trans_to_obj(W, spray_amount)
+ W.set_color()
+ W.set_up(my_target)
if((istype(usr.loc, /turf/space)) || (usr.lastarea.has_gravity == 0))
user.inertia_dir = get_dir(target, user)
diff --git a/code/game/objects/items/weapons/flamethrower.dm b/code/game/objects/items/weapons/flamethrower.dm
index 7b152fd8d32..25eacadde70 100644
--- a/code/game/objects/items/weapons/flamethrower.dm
+++ b/code/game/objects/items/weapons/flamethrower.dm
@@ -10,8 +10,8 @@
throw_speed = 1
throw_range = 5
w_class = 3.0
- matter = list("metal" = 500)
- origin_tech = list(TECH_COMBAT = 1, TECH_PHORON = 1)
+ origin_tech = list(TECH_COMBAT = 1, TECH_PHORON = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 500)
var/status = 0
var/throw_amount = 100
var/lit = 0 //on or off
@@ -22,13 +22,13 @@
var/obj/item/weapon/tank/phoron/ptank = null
-/obj/item/weapon/flamethrower/Del()
+/obj/item/weapon/flamethrower/Destroy()
if(weldtool)
- del(weldtool)
+ qdel(weldtool)
if(igniter)
- del(igniter)
+ qdel(igniter)
if(ptank)
- del(ptank)
+ qdel(ptank)
..()
return
@@ -82,8 +82,8 @@
if(ptank)
ptank.loc = T
ptank = null
- new /obj/item/stack/rods(T)
- del(src)
+ PoolOrNew(/obj/item/stack/rods, T)
+ qdel(src)
return
if(isscrewdriver(W) && igniter && !lit)
diff --git a/code/game/objects/items/weapons/gift_wrappaper.dm b/code/game/objects/items/weapons/gift_wrappaper.dm
index dd3d0886fb1..023eb3bfd31 100644
--- a/code/game/objects/items/weapons/gift_wrappaper.dm
+++ b/code/game/objects/items/weapons/gift_wrappaper.dm
@@ -31,11 +31,11 @@
src.gift.add_fingerprint(user)
else
user << "\blue The gift was empty!"
- del(src)
+ qdel(src)
return
/obj/item/weapon/a_gift/ex_act()
- del(src)
+ qdel(src)
return
/obj/effect/spresent/relaymove(mob/user as mob)
@@ -58,7 +58,7 @@
M.client.eye = M.client.mob
M.client.perspective = MOB_PERSPECTIVE
- del(src)
+ qdel(src)
/obj/item/weapon/a_gift/attack_self(mob/M as mob)
var/gift_type = pick(/obj/item/weapon/sord,
@@ -112,7 +112,7 @@
M.remove_from_mob(src)
M.put_in_hands(I)
I.add_fingerprint(M)
- del(src)
+ qdel(src)
return
/*
@@ -152,7 +152,7 @@
src.add_fingerprint(user)
if (src.amount <= 0)
new /obj/item/weapon/c_tube( src.loc )
- del(src)
+ qdel(src)
return
else
user << "\blue You need scissors!"
diff --git a/code/game/objects/items/weapons/grenades/chem_grenade.dm b/code/game/objects/items/weapons/grenades/chem_grenade.dm
index 3f7214fec87..9f2add5541b 100644
--- a/code/game/objects/items/weapons/grenades/chem_grenade.dm
+++ b/code/game/objects/items/weapons/grenades/chem_grenade.dm
@@ -157,7 +157,7 @@
for(var/atom/A in view(affected_area, src.loc))
if( A == src ) continue
- src.reagents.reaction(A, 1, 10)
+ src.reagents.touch(A)
if(istype(loc, /mob/living/carbon)) //drop dat grenade if it goes off in your hand
var/mob/living/carbon/C = loc
@@ -166,7 +166,7 @@
invisibility = INVISIBILITY_MAXIMUM //Why am i doing this?
spawn(50) //To make sure all reagents can work
- del(src) //correctly before deleting the grenade.
+ qdel(src) //correctly before deleting the grenade.
/obj/item/weapon/grenade/chem_grenade/large
diff --git a/code/game/objects/items/weapons/grenades/emgrenade.dm b/code/game/objects/items/weapons/grenades/emgrenade.dm
index 884f5630b49..f8c2a12d2f1 100644
--- a/code/game/objects/items/weapons/grenades/emgrenade.dm
+++ b/code/game/objects/items/weapons/grenades/emgrenade.dm
@@ -7,5 +7,5 @@
prime()
..()
if(empulse(src, 4, 10))
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/items/weapons/grenades/flashbang.dm b/code/game/objects/items/weapons/grenades/flashbang.dm
index aac45f8388c..d4df5bd1acb 100644
--- a/code/game/objects/items/weapons/grenades/flashbang.dm
+++ b/code/game/objects/items/weapons/grenades/flashbang.dm
@@ -23,7 +23,7 @@
new/obj/effect/effect/sparks(src.loc)
new/obj/effect/effect/smoke/illumination(src.loc, brightness=15)
- del(src)
+ qdel(src)
return
proc/bang(var/turf/T , var/mob/living/carbon/M) // Added a new proc called 'bang' that takes a location and a person to be banged.
@@ -124,9 +124,8 @@
spawn(0)
new /obj/item/weapon/grenade/flashbang/clusterbang/segment(src.loc)//Creates a 'segment' that launches a few more flashbangs
playsound(src.loc, 'sound/weapons/armbomb.ogg', 75, 1, -3)
- spawn(0)
- del(src)
- return
+ qdel(src)
+ return
/obj/item/weapon/grenade/flashbang/clusterbang/segment
desc = "A smaller segment of a clusterbang. Better run."
@@ -156,9 +155,8 @@
spawn(0)
new /obj/item/weapon/grenade/flashbang/cluster(src.loc)
playsound(src.loc, 'sound/weapons/armbomb.ogg', 75, 1, -3)
- spawn(0)
- del(src)
- return
+ qdel(src)
+ return
/obj/item/weapon/grenade/flashbang/cluster/New()//Same concept as the segments, so that all of the parts don't become reliant on the clusterbang
spawn(0)
diff --git a/code/game/objects/items/weapons/grenades/smokebomb.dm b/code/game/objects/items/weapons/grenades/smokebomb.dm
index 139baacb6f7..e1e58b62ac7 100644
--- a/code/game/objects/items/weapons/grenades/smokebomb.dm
+++ b/code/game/objects/items/weapons/grenades/smokebomb.dm
@@ -10,7 +10,7 @@
New()
..()
- src.smoke = new /datum/effect/effect/system/smoke_spread/bad
+ src.smoke = PoolOrNew(/datum/effect/effect/system/smoke_spread/bad)
src.smoke.attach(src)
prime()
@@ -30,5 +30,5 @@
B.health -= damage
B.update_icon()
sleep(80)
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/items/weapons/grenades/spawnergrenade.dm b/code/game/objects/items/weapons/grenades/spawnergrenade.dm
index bf639fdf137..9677a733459 100644
--- a/code/game/objects/items/weapons/grenades/spawnergrenade.dm
+++ b/code/game/objects/items/weapons/grenades/spawnergrenade.dm
@@ -28,7 +28,7 @@
// Spawn some hostile syndicate critters
- del(src)
+ qdel(src)
return
/obj/item/weapon/grenade/spawnergrenade/manhacks
diff --git a/code/game/objects/items/weapons/handcuffs.dm b/code/game/objects/items/weapons/handcuffs.dm
index 354858554e4..ea7e1a87608 100644
--- a/code/game/objects/items/weapons/handcuffs.dm
+++ b/code/game/objects/items/weapons/handcuffs.dm
@@ -10,63 +10,81 @@
w_class = 2.0
throw_speed = 2
throw_range = 5
- matter = list("metal" = 500)
- origin_tech = list(TECH_MATERIAL = 1)
+ origin_tech = list(TECH_MATERIAL = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 500)
var/dispenser = 0
var/breakouttime = 1200 //Deciseconds = 120s = 2 minutes
var/cuff_sound = 'sound/weapons/handcuffs.ogg'
+ var/cuff_type = "handcuffs"
-/obj/item/weapon/handcuffs/attack(mob/living/carbon/C as mob, mob/user as mob)
- if (!istype(user, /mob/living/carbon/human))
- user << "\red You don't have the dexterity to do this!"
+/obj/item/weapon/handcuffs/attack(var/mob/living/carbon/C, var/mob/living/user)
+
+ if(!user.IsAdvancedToolUser())
return
- if ((CLUMSY in usr.mutations) && prob(50))
- user << "\red Uh ... how do those things work?!"
+
+ if ((CLUMSY in user.mutations) && prob(50))
+ user << "Uh ... how do those things work?!"
place_handcuffs(user, user)
return
+
if(!C.handcuffed)
if (C == user)
place_handcuffs(user, user)
return
- //check for an aggressive grab
- for (var/obj/item/weapon/grab/G in C.grabbed_by)
- if (G.loc == user && G.state >= GRAB_AGGRESSIVE)
- place_handcuffs(C, user)
- return
- user << "\red You need to have a firm grip on [C] before you can put \the [src] on!"
+ //check for an aggressive grab (or robutts)
+ var/can_place
+ if(istype(user, /mob/living/silicon/robot))
+ can_place = 1
+ else
+ for (var/obj/item/weapon/grab/G in C.grabbed_by)
+ if (G.loc == user && G.state >= GRAB_AGGRESSIVE)
+ can_place = 1
+ break
+
+ if(can_place)
+ place_handcuffs(C, user)
+ else
+ user << "You need to have a firm grip on [C] before you can put \the [src] on!"
/obj/item/weapon/handcuffs/proc/place_handcuffs(var/mob/living/carbon/target, var/mob/user)
playsound(src.loc, cuff_sound, 30, 1, -2)
- if (ishuman(target))
- var/mob/living/carbon/human/H = target
-
- if (!H.has_organ_for_slot(slot_handcuffed))
- user << "\The [H] needs at least two wrists before you can cuff them together!"
- return
-
- if(istype(H.gloves,/obj/item/clothing/gloves/rig)) // Can't cuff someone who's in a deployed hardsuit.
- user << "The cuffs won't fit around \the [H.gloves]!"
- return
-
- H.attack_log += text("\[[time_stamp()]\] Has been handcuffed (attempt) by [user.name] ([user.ckey])")
- user.attack_log += text("\[[time_stamp()]\] Attempted to handcuff [H.name] ([H.ckey])")
- msg_admin_attack("[key_name(user)] attempted to handcuff [key_name(H)]")
-
- var/obj/effect/equip_e/human/O = new /obj/effect/equip_e/human( )
- O.source = user
- O.target = H
- O.item = user.get_active_hand()
- O.s_loc = user.loc
- O.t_loc = H.loc
- O.place = "handcuff"
- H.requests += O
- spawn( 0 )
- feedback_add_details("handcuffs","H")
- O.process()
+ var/mob/living/carbon/human/H = target
+ if(!istype(H))
return
+ if (!H.has_organ_for_slot(slot_handcuffed))
+ user << "\The [H] needs at least two wrists before you can cuff them together!"
+ return
+
+ if(istype(H.gloves,/obj/item/clothing/gloves/rig)) // Can't cuff someone who's in a deployed hardsuit.
+ user << "The cuffs won't fit around \the [H.gloves]!"
+ return
+
+ user.visible_message("\The [user] is attempting to put [cuff_type] on \the [H]!")
+
+ if(!do_after(user,30))
+ return
+
+ H.attack_log += text("\[[time_stamp()]\] Has been handcuffed (attempt) by [user.name] ([user.ckey])")
+ user.attack_log += text("\[[time_stamp()]\] Attempted to handcuff [H.name] ([H.ckey])")
+ msg_admin_attack("[key_name(user)] attempted to handcuff [key_name(H)]")
+ feedback_add_details("handcuffs","H")
+
+ user.visible_message("\The [user] has put [cuff_type] on \the [H]!")
+
+ // Apply cuffs.
+ var/obj/item/weapon/handcuffs/cuffs = src
+ if(dispenser)
+ cuffs = new(get_turf(user))
+ else
+ user.drop_from_inventory(cuffs)
+ cuffs.loc = target
+ target.handcuffed = cuffs
+ target.update_inv_handcuffed()
+ return
+
var/last_chew = 0
/mob/living/carbon/human/RestrainedClickOn(var/atom/A)
if (A != src) return ..()
@@ -98,6 +116,7 @@ var/last_chew = 0
icon_state = "cuff_white"
breakouttime = 300 //Deciseconds = 30s
cuff_sound = 'sound/weapons/cablecuff.ogg'
+ cuff_type = "cable restraints"
/obj/item/weapon/handcuffs/cable/red
color = "#DD0000"
@@ -132,28 +151,9 @@ var/last_chew = 0
user.put_in_hands(W)
user << "You wrap the cable restraint around the top of the rod."
- del(src)
+ qdel(src)
update_icon(user)
/obj/item/weapon/handcuffs/cyborg
dispenser = 1
-
-/obj/item/weapon/handcuffs/cyborg/attack(mob/living/carbon/C as mob, mob/user as mob)
- if(!C.handcuffed)
- var/turf/p_loc = user.loc
- var/turf/p_loc_m = C.loc
- playsound(src.loc, cuff_sound, 30, 1, -2)
- user.visible_message("\red [user] is trying to put handcuffs on [C]!")
-
- if (ishuman(C))
- var/mob/living/carbon/human/H = C
- if (!H.has_organ_for_slot(slot_handcuffed))
- user << "\red \The [H] needs at least two wrists before you can cuff them together!"
- return
-
- spawn(30)
- if(!C) return
- if(p_loc == user.loc && p_loc_m == C.loc)
- C.handcuffed = new /obj/item/weapon/handcuffs(C)
- C.update_inv_handcuffed()
diff --git a/code/game/objects/items/weapons/implants/implant.dm b/code/game/objects/items/weapons/implants/implant.dm
index 50b4135dd79..6465a055785 100644
--- a/code/game/objects/items/weapons/implants/implant.dm
+++ b/code/game/objects/items/weapons/implants/implant.dm
@@ -9,7 +9,7 @@
var/implanted = null
var/mob/imp_in = null
var/obj/item/organ/external/part = null
- item_color = "b"
+ var/implant_color = "b"
var/allow_reagents = 0
var/malfunction = 0
@@ -46,7 +46,7 @@
icon_state = "implant_melted"
malfunction = MALFUNCTION_PERMANENT
- Del()
+ Destroy()
if(part)
part.implants.Remove(src)
..()
@@ -155,7 +155,7 @@ Implant Specifics: "}
msg = replace_characters(msg, replacechars)
if(findtext(msg,phrase))
activate()
- del(src)
+ qdel(src)
activate()
if (malfunction == MALFUNCTION_PERMANENT)
@@ -179,11 +179,11 @@ Implant Specifics: "}
istype(part,/obj/item/organ/external/head))
part.createwound(BRUISE, 60) //mangle them instead
explosion(get_turf(imp_in), -1, -1, 2, 3)
- del(src)
+ qdel(src)
else
explosion(get_turf(imp_in), -1, -1, 2, 3)
part.droplimb(0,DROPLIMB_BLUNT)
- del(src)
+ qdel(src)
if (elevel == "Destroy Body")
explosion(get_turf(T), -1, 0, 1, 6)
T.gib()
@@ -249,7 +249,7 @@ Implant Specifics: "}
else
part.droplimb(0,DROPLIMB_BLUNT)
explosion(get_turf(imp_in), -1, -1, 2, 3)
- del(src)
+ qdel(src)
/obj/item/weapon/implant/chem
name = "chemical implant"
@@ -291,12 +291,12 @@ the implant may become unstable and either pre-maturely inject the subject or si
activate(var/cause)
if((!cause) || (!src.imp_in)) return 0
var/mob/living/carbon/R = src.imp_in
- src.reagents.trans_to(R, cause)
+ src.reagents.trans_to_mob(R, cause, CHEM_BLOOD)
R << "You hear a faint *beep*."
if(!src.reagents.total_volume)
R << "You hear a faint click from your chest."
spawn(0)
- del(src)
+ qdel(src)
return
emp_act(severity)
@@ -421,17 +421,17 @@ the implant may become unstable and either pre-maturely inject the subject or si
a.autosay("[mobname] has died in Space!", "[mobname]'s Death Alarm")
else
a.autosay("[mobname] has died in [t.name]!", "[mobname]'s Death Alarm")
- del(a)
+ qdel(a)
processing_objects.Remove(src)
if ("emp")
var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset(null)
var/name = prob(50) ? t.name : pick(teleportlocs)
a.autosay("[mobname] has died in [name]!", "[mobname]'s Death Alarm")
- del(a)
+ qdel(a)
else
var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset(null)
a.autosay("[mobname] has died-zzzzt in-in-in...", "[mobname]'s Death Alarm")
- del(a)
+ qdel(a)
processing_objects.Remove(src)
emp_act(severity) //for some reason alarms stop going off in case they are emp'd, even without this
@@ -489,7 +489,7 @@ the implant may become unstable and either pre-maturely inject the subject or si
imp_in.put_in_hands(scanned)
else
scanned.loc = t
- del src
+ qdel(src)
implanted(mob/source as mob)
src.activation_emote = input("Choose activation emote:") in list("blink", "blink_r", "eyebrow", "chuckle", "twitch_s", "frown", "nod", "blush", "giggle", "grin", "groan", "shrug", "smile", "pale", "sniff", "whimper", "wink")
diff --git a/code/game/objects/items/weapons/implants/implantcase.dm b/code/game/objects/items/weapons/implants/implantcase.dm
index ddb76b36562..ea50b92cdfb 100644
--- a/code/game/objects/items/weapons/implants/implantcase.dm
+++ b/code/game/objects/items/weapons/implants/implantcase.dm
@@ -13,7 +13,7 @@
/obj/item/weapon/implantcase/proc/update()
if (src.imp)
- src.icon_state = text("implantcase-[]", src.imp.item_color)
+ src.icon_state = text("implantcase-[]", src.imp.implant_color)
else
src.icon_state = "implantcase-0"
return
@@ -26,7 +26,7 @@
return
if((!in_range(src, usr) && src.loc != user))
return
- t = sanitize(t)
+ t = sanitizeSafe(t, MAX_NAME_LEN)
if(t)
src.name = text("Glass Case - '[]'", t)
else
@@ -38,7 +38,7 @@
user << "\red [src] is full."
else
spawn(5)
- I.reagents.trans_to(src.imp, 5)
+ I.reagents.trans_to_mob(src.imp, 5)
user << "\blue You inject 5 units of the solution. The syringe now contains [I.reagents.total_volume] units."
else if (istype(I, /obj/item/weapon/implanter))
var/obj/item/weapon/implanter/M = I
diff --git a/code/game/objects/items/weapons/implants/implantchair.dm b/code/game/objects/items/weapons/implants/implantchair.dm
index 535a4264c0b..2f33eba4135 100644
--- a/code/game/objects/items/weapons/implants/implantchair.dm
+++ b/code/game/objects/items/weapons/implants/implantchair.dm
@@ -84,7 +84,7 @@
return
var/mob/M = G:affecting
if(put_mob(M))
- del(G)
+ qdel(G)
src.updateUsrDialog()
return
diff --git a/code/game/objects/items/weapons/implants/implanter.dm b/code/game/objects/items/weapons/implants/implanter.dm
index 150f77e5e2d..4f2c491d6b4 100644
--- a/code/game/objects/items/weapons/implants/implanter.dm
+++ b/code/game/objects/items/weapons/implants/implanter.dm
@@ -32,9 +32,7 @@
for (var/mob/O in viewers(M, null))
O.show_message("\red [M] has been implanted by [user].", 1)
- M.attack_log += text("\[[time_stamp()]\] Implanted with [src.name] ([src.imp.name]) by [user.name] ([user.ckey])")
- user.attack_log += text("\[[time_stamp()]\] Used the [src.name] ([src.imp.name]) to implant [M.name] ([M.ckey])")
- msg_admin_attack("[user.name] ([user.ckey]) implanted [M.name] ([M.ckey]) with [src.name] (INTENT: [uppertext(user.a_intent)]) (JMP)")
+ admin_attack_log(user, M, "Implanted using \the [src.name] ([src.imp.name])", "Implanted with \the [src.name] ([src.imp.name])", "used an implanter, [src.name] ([src.imp.name]), on")
user.show_message("\red You implanted the implant into [M].")
if(src.imp.implanted(M))
diff --git a/code/game/objects/items/weapons/implants/implantfreedom.dm b/code/game/objects/items/weapons/implants/implantfreedom.dm
index d32ae9d8baa..5131961060c 100644
--- a/code/game/objects/items/weapons/implants/implantfreedom.dm
+++ b/code/game/objects/items/weapons/implants/implantfreedom.dm
@@ -3,7 +3,7 @@
/obj/item/weapon/implant/freedom
name = "freedom implant"
desc = "Use this to escape from those evil Red Shirts."
- item_color = "r"
+ implant_color = "r"
var/activation_emote = "chuckle"
var/uses = 1.0
diff --git a/code/game/objects/items/weapons/kitchen.dm b/code/game/objects/items/weapons/kitchen.dm
index 598f33ae8c3..9b6ccc2ecf3 100644
--- a/code/game/objects/items/weapons/kitchen.dm
+++ b/code/game/objects/items/weapons/kitchen.dm
@@ -49,7 +49,7 @@
return ..()
if (reagents.total_volume > 0)
- reagents.trans_to_ingest(M, reagents.total_volume)
+ reagents.trans_to_mob(M, reagents.total_volume, CHEM_INGEST)
if(M == user)
for(var/mob/O in viewers(M, null))
O.show_message(text("\blue [] eats some [] from \the [].", user, loaded, src), 1)
@@ -145,8 +145,8 @@
throwforce = 6.0
throw_speed = 3
throw_range = 6
- matter = list("metal" = 12000)
- origin_tech = list(TECH_MATERIAL = 1)
+ origin_tech = list(TECH_MATERIAL = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 12000)
attack_verb = list("slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
suicide_act(mob/user)
@@ -155,6 +155,12 @@
"\red [user] is slitting \his stomach open with the [src.name]! It looks like \he's trying to commit seppuku.")
return (BRUTELOSS)
+/obj/item/weapon/kitchenknife/hook
+ name = "meat hook"
+ desc = "A sharp, metal hook what sticks into things."
+ icon_state = "hook_knife"
+ item_state = "hook_knife"
+
/obj/item/weapon/kitchenknife/ritual
name = "ritual knife"
desc = "The unearthly energies that once powered this blade are now dormant."
@@ -175,8 +181,8 @@
throwforce = 8.0
throw_speed = 3
throw_range = 6
- matter = list("metal" = 12000)
- origin_tech = list(TECH_MATERIAL = 1)
+ origin_tech = list(TECH_MATERIAL = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 12000)
attack_verb = list("cleaved", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
sharp = 1
edge = 1
@@ -247,7 +253,7 @@
throw_range = 5
w_class = 3.0
flags = CONDUCT
- matter = list("metal" = 3000)
+ matter = list(DEFAULT_WALL_MATERIAL = 3000)
/* // NOPE
var/food_total= 0
var/burger_amt = 0
diff --git a/code/game/objects/items/weapons/manuals.dm b/code/game/objects/items/weapons/manuals.dm
index f026313034a..a9ee95db524 100644
--- a/code/game/objects/items/weapons/manuals.dm
+++ b/code/game/objects/items/weapons/manuals.dm
@@ -98,7 +98,7 @@
OPERATING PRINCIPLES
-
The supermatter crystal serves as the fundamental power source of the engine. Upon being charged, it begins to emit large amounts of heat and radiation, as well and oxygen and plasma. As oxygen accelerates the reaction, and plasma carries the risk of fire, these must be filtered out. NOTE: Supermatter radiation will not charge radiation collectors.
+
The supermatter crystal serves as the fundamental power source of the engine. Upon being charged, it begins to emit large amounts of heat and radiation, as well and oxygen and phoron gas. As oxygen accelerates the reaction, and phoron carries the risk of fire, these must be filtered out. NOTE: Supermatter radiation will not charge radiation collectors.
Air in the reactor chamber housing the supermatter is circulated through the reactor loop, which passes through the filters and thermoelectric generators. The thermoelectric generators transfer heat from the reactor loop to the colder radiator loop, thereby generating power. Additional power is generated from internal turbines in the circulators.
@@ -106,7 +106,7 @@
The MK 1 Prototype Thermoelectric Supermatter Engine is designed to operate at reactor temperatures of 3000K to 4000K and generate up to 1MW of power. Beyond 1MW, the thermoelectric generators will begin to lose power through electrical discharge, reducing efficiency, but additional power generation remains feasible.
-
The crystal structure of the supermatter will begin to liquefy if its temperature exceeds 5000K. This eventually results in a massive release of light, heat and radiation, disintegration of both the supermatter crystal and most of the surrounding area, and as as-of-yet poorly documented psychological effects on all animals within a 2km. Appropriate action should be taken to stabilize or eject the supermatter before such occurs.
+
The crystal structure of the supermatter will begin to liquefy if its temperature exceeds 5000K. This eventually results in a massive release of light, heat and radiation, disintegration of both the supermatter crystal and most of the surrounding area, and as as-of-yet poorly documented psychological effects on all animals within a 2km radius. Appropriate action should be taken to stabilize or eject the supermatter before such occurs.
SUPERMATTER HANDLING
Do not expose supermatter to oxygen.
@@ -125,7 +125,7 @@
Ensure that radiation protection and meson goggles are worn at all times while working in the engine room.
Ensure that reactor and radiator loops are undamaged and unobstructed.
-
Ensure that plasma and oxygen gas exhaust from filters is properly contained or disposed. Do not allow exhaust pressure to exceed 4500 kPa.
+
Ensure that phoron and oxygen gas exhaust from filters is properly contained or disposed. Do not allow exhaust pressure to exceed 4500 kPa.
Ensure that engine room Area Power Controller (APC) and engine Superconducting Magnetic Energy Storage unit (SMES) are properly charged.
Ensure that reactor temperature does not exceed 5000K. In event of reactor temperature exceeding 5000K, see EMERGENCY COOLING PROCEDURE.
In event of imminent and/or unavoidable delamination, see EJECTION PROCEDURE.
diff --git a/code/game/objects/items/weapons/melee/energy.dm b/code/game/objects/items/weapons/melee/energy.dm
index 898eae173b1..be282030984 100644
--- a/code/game/objects/items/weapons/melee/energy.dm
+++ b/code/game/objects/items/weapons/melee/energy.dm
@@ -113,6 +113,7 @@
origin_tech = list(TECH_MAGNET = 3, TECH_ILLEGAL = 4)
sharp = 1
edge = 1
+ var/blade_color
/obj/item/weapon/melee/energy/sword/dropped(var/mob/user)
..()
@@ -120,26 +121,26 @@
deactivate(user)
/obj/item/weapon/melee/energy/sword/New()
- item_color = pick("red","blue","green","purple")
+ blade_color = pick("red","blue","green","purple")
/obj/item/weapon/melee/energy/sword/green/New()
- item_color = "green"
+ blade_color = "green"
/obj/item/weapon/melee/energy/sword/red/New()
- item_color = "red"
+ blade_color = "red"
/obj/item/weapon/melee/energy/sword/blue/New()
- item_color = "blue"
+ blade_color = "blue"
/obj/item/weapon/melee/energy/sword/purple/New()
- item_color = "purple"
+ blade_color = "purple"
/obj/item/weapon/melee/energy/sword/activate(mob/living/user)
if(!active)
user << "\The [src] is now energised."
..()
attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
- icon_state = "sword[item_color]"
+ icon_state = "sword[blade_color]"
/obj/item/weapon/melee/energy/sword/deactivate(mob/living/user)
if(active)
@@ -192,16 +193,16 @@
processing_objects |= src
-/obj/item/weapon/melee/energy/blade/Del()
+/obj/item/weapon/melee/energy/blade/Destroy()
processing_objects -= src
..()
/obj/item/weapon/melee/energy/blade/attack_self(mob/user as mob)
user.drop_from_inventory(src)
- spawn(1) if(src) del(src)
+ spawn(1) if(src) qdel(src)
/obj/item/weapon/melee/energy/blade/dropped()
- spawn(1) if(src) del(src)
+ spawn(1) if(src) qdel(src)
/obj/item/weapon/melee/energy/blade/process()
if(!creator || loc != creator || (creator.l_hand != src && creator.r_hand != src))
@@ -216,4 +217,4 @@
host.pinned -= src
host.embedded -= src
host.drop_from_inventory(src)
- spawn(1) if(src) del(src)
+ spawn(1) if(src) qdel(src)
diff --git a/code/game/objects/items/weapons/mop.dm b/code/game/objects/items/weapons/mop.dm
index fe9945f8f04..17af445e192 100644
--- a/code/game/objects/items/weapons/mop.dm
+++ b/code/game/objects/items/weapons/mop.dm
@@ -24,10 +24,8 @@
T.dirt = 0
for(var/obj/effect/O in src)
if(istype(O,/obj/effect/rune) || istype(O,/obj/effect/decal/cleanable) || istype(O,/obj/effect/overlay))
- del(O)
- source.reagents.reaction(src, TOUCH, 10) //10 is the multiplier for the reaction effect. probably needed to wet the floor properly.
- source.reagents.remove_any(1) //reaction() doesn't use up the reagents
-
+ qdel(O)
+ source.reagents.trans_to_turf(src, 1, 10) //10 is the multiplier for the reaction effect. probably needed to wet the floor properly.
/obj/item/weapon/mop/afterattack(atom/A, mob/user, proximity)
if(!proximity) return
diff --git a/code/game/objects/items/weapons/paint.dm b/code/game/objects/items/weapons/paint.dm
index 77f8172f8fc..d92812b3fde 100644
--- a/code/game/objects/items/weapons/paint.dm
+++ b/code/game/objects/items/weapons/paint.dm
@@ -9,7 +9,7 @@ var/global/list/cached_icons = list()
icon = 'icons/obj/items.dmi'
icon_state = "paint_neutral"
item_state = "paintcan"
- matter = list("metal" = 200)
+ matter = list(DEFAULT_WALL_MATERIAL = 200)
w_class = 3.0
amount_per_transfer_from_this = 10
possible_transfer_amounts = list(10,20,30,60)
@@ -20,11 +20,8 @@ var/global/list/cached_icons = list()
afterattack(turf/simulated/target, mob/user, proximity)
if(!proximity) return
if(istype(target) && reagents.total_volume > 5)
- for(var/mob/O in viewers(user))
- O.show_message("\red \The [target] has been splashed with something by [user]!", 1)
- spawn(5)
- reagents.reaction(target, TOUCH)
- reagents.remove_any(5)
+ user.visible_message("\The [target] has been splashed with something by [user]!")
+ reagents.trans_to_turf(target, 5)
else
return ..()
diff --git a/code/game/objects/items/weapons/policetape.dm b/code/game/objects/items/weapons/policetape.dm
index 4444904c1b8..68a821e3a75 100644
--- a/code/game/objects/items/weapons/policetape.dm
+++ b/code/game/objects/items/weapons/policetape.dm
@@ -9,6 +9,9 @@
var/tape_type = /obj/item/tape
var/icon_base
+var/list/image/hazard_overlays
+var/list/tape_roll_applications = list()
+
/obj/item/tape
name = "tape"
icon = 'icons/policetape.dmi'
@@ -17,6 +20,15 @@
var/crumpled = 0
var/icon_base
+/obj/item/tape/New()
+ ..()
+ if(!hazard_overlays)
+ hazard_overlays = list()
+ hazard_overlays["[NORTH]"] = new/image('icons/effects/warning_stripes.dmi', icon_state = "N")
+ hazard_overlays["[EAST]"] = new/image('icons/effects/warning_stripes.dmi', icon_state = "E")
+ hazard_overlays["[SOUTH]"] = new/image('icons/effects/warning_stripes.dmi', icon_state = "S")
+ hazard_overlays["[WEST]"] = new/image('icons/effects/warning_stripes.dmi', icon_state = "W")
+
/obj/item/taperoll/police
name = "police tape"
desc = "A roll of police tape used to block off crime scenes from the public."
@@ -94,11 +106,13 @@
var/obj/item/tape/P = new tape_type(cur)
P.icon_state = "[P.icon_base]_[dir]"
cur = get_step_towards(cur,end)
- //is_blocked_turf(var/turf/T)
usr << "\blue You finish placing the [src]." //Git Test
/obj/item/taperoll/afterattack(var/atom/A, mob/user as mob, proximity)
- if (proximity && istype(A, /obj/machinery/door/airlock))
+ if(!proximity)
+ return
+
+ if (istype(A, /obj/machinery/door/airlock))
var/turf/T = get_turf(A)
var/obj/item/tape/P = new tape_type(T.x,T.y,T.z)
P.loc = locate(T.x,T.y,T.z)
@@ -106,6 +120,23 @@
P.layer = 3.2
user << "\blue You finish placing the [src]."
+ if (istype(A, /turf/simulated/floor) ||istype(A, /turf/unsimulated/floor))
+ var/turf/F = A
+ var/direction = user.loc == F ? user.dir : turn(user.dir, 180)
+ var/icon/hazard_overlay = hazard_overlays["[direction]"]
+ if(tape_roll_applications[F] == null)
+ tape_roll_applications[F] = 0
+
+ if(tape_roll_applications[F] & direction) // hazard_overlay in F.overlays wouldn't work.
+ user.visible_message("[user] uses the adhesive of \the [src] to remove area markings from \the [F].", "You use the adhesive of \the [src] to remove area markings from \the [F].")
+ F.overlays -= hazard_overlay
+ tape_roll_applications[F] &= ~direction
+ else
+ user.visible_message("[user] applied \the [src] on \the [F] to create area markings.", "You apply \the [src] on \the [F] to create area markings.")
+ F.overlays |= hazard_overlay
+ tape_roll_applications[F] |= direction
+ return
+
/obj/item/tape/proc/crumple()
if(!crumpled)
crumpled = 1
@@ -159,10 +190,10 @@
for (var/obj/item/tape/P in cur)
if(P.icon_state == icon_dir)
N = 0
- del(P)
+ qdel(P)
cur = get_step(cur,dir[i])
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/items/weapons/power_cells.dm b/code/game/objects/items/weapons/power_cells.dm
index 7536acfeb1c..85b71723d43 100644
--- a/code/game/objects/items/weapons/power_cells.dm
+++ b/code/game/objects/items/weapons/power_cells.dm
@@ -14,20 +14,37 @@
var/maxcharge = 1000
var/rigged = 0 // true if rigged to explode
var/minor_fault = 0 //If not 100% reliable, it will build up faults.
- var/construction_cost = list("metal"=750,"glass"=75)
+ var/construction_cost = list(DEFAULT_WALL_MATERIAL=750,"glass"=75)
var/construction_time=100
- matter = list("metal" = 700, "glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 50)
suicide_act(mob/user)
viewers(user) << "\red [user] is licking the electrodes of the [src.name]! It looks like \he's trying to commit suicide."
return (FIRELOSS)
+//currently only used by energy-type guns, that may change in the future.
+/obj/item/weapon/cell/device
+ name = "device power cell"
+ desc = "A small power cell designed to power handheld devices."
+ icon_state = "cell" //placeholder
+ w_class = 2
+ force = 0
+ throw_speed = 5
+ throw_range = 7
+ maxcharge = 1000
+ matter = list("metal" = 350, "glass" = 50)
+
+/obj/item/weapon/cell/device/variable/New(newloc, charge_amount)
+ ..(newloc)
+ maxcharge = charge_amount
+ charge = maxcharge
+
/obj/item/weapon/cell/crap
name = "\improper Nanotrasen brand rechargable AA battery"
desc = "You can't top the plasma top." //TOTALLY TRADEMARK INFRINGEMENT
origin_tech = list(TECH_POWER = 0)
maxcharge = 500
- matter = list("metal" = 700, "glass" = 40)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 40)
/obj/item/weapon/cell/crap/empty/New()
..()
@@ -37,7 +54,7 @@
name = "security borg rechargable D battery"
origin_tech = list(TECH_POWER = 0)
maxcharge = 600 //600 max charge / 100 charge per shot = six shots
- matter = list("metal" = 700, "glass" = 40)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 40)
/obj/item/weapon/cell/secborg/empty/New()
..()
@@ -47,14 +64,14 @@
name = "heavy-duty power cell"
origin_tech = list(TECH_POWER = 1)
maxcharge = 5000
- matter = list("metal" = 700, "glass" = 50)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 50)
/obj/item/weapon/cell/high
name = "high-capacity power cell"
origin_tech = list(TECH_POWER = 2)
icon_state = "hcell"
maxcharge = 10000
- matter = list("metal" = 700, "glass" = 60)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 60)
/obj/item/weapon/cell/high/empty/New()
..()
@@ -65,8 +82,8 @@
origin_tech = list(TECH_POWER = 5)
icon_state = "scell"
maxcharge = 20000
- matter = list("metal" = 700, "glass" = 70)
- construction_cost = list("metal"=750,"glass"=100)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 70)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=750,"glass"=100)
/obj/item/weapon/cell/super/empty/New()
..()
@@ -77,8 +94,8 @@
origin_tech = list(TECH_POWER = 6)
icon_state = "hpcell"
maxcharge = 30000
- matter = list("metal" = 700, "glass" = 80)
- construction_cost = list("metal"=500,"glass"=150,"gold"=200,"silver"=200)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 80)
+ construction_cost = list(DEFAULT_WALL_MATERIAL=500,"glass"=150,"gold"=200,"silver"=200)
/obj/item/weapon/cell/hyper/empty/New()
..()
@@ -89,7 +106,7 @@
icon_state = "icell"
origin_tech = null
maxcharge = 30000
- matter = list("metal" = 700, "glass" = 80)
+ matter = list(DEFAULT_WALL_MATERIAL = 700, "glass" = 80)
use()
return 1
diff --git a/code/game/objects/items/weapons/shards.dm b/code/game/objects/items/weapons/shards.dm
index 6b48653a6a5..593b3d019d9 100644
--- a/code/game/objects/items/weapons/shards.dm
+++ b/code/game/objects/items/weapons/shards.dm
@@ -1,19 +1,22 @@
// Glass shards
/obj/item/weapon/shard
- name = "glass shard"
+ name = "shard"
icon = 'icons/obj/shards.dmi'
icon_state = "large"
sharp = 1
edge = 1
- desc = "Could probably be used as ... a throwing weapon?"
+ desc = "Made of nothing. How does this even exist?" // set based on material, if this desc is visible it's a bug (shards default to being made of glass)
w_class = 2.0
force = 5.0
throwforce = 8.0
item_state = "shard-glass"
- matter = list("glass" = 3750)
+ //matter = list("glass" = 3750) // Weld it into sheets before you use it!
attack_verb = list("stabbed", "slashed", "sliced", "cut")
+ gender = "neuter"
+ var/material/material = null
+
/obj/item/weapon/shard/suicide_act(mob/user)
viewers(user) << pick("\red [user] is slitting \his wrists with \the [src]! It looks like \he's trying to commit suicide.", \
"\red [user] is slitting \his throat with \the [src]! It looks like \he's trying to commit suicide.")
@@ -34,37 +37,55 @@
return
return
-/obj/item/weapon/shard/New()
+/obj/item/weapon/shard/New(loc, material/material)
+ ..(loc)
- src.icon_state = pick("large", "medium", "small")
- switch(src.icon_state)
- if("small")
- src.pixel_x = rand(-12, 12)
- src.pixel_y = rand(-12, 12)
- if("medium")
- src.pixel_x = rand(-8, 8)
- src.pixel_y = rand(-8, 8)
- if("large")
- src.pixel_x = rand(-5, 5)
- src.pixel_y = rand(-5, 5)
+ if(!material || !istype(material)) // We either don't have a material or we've been passed an invalid material. Use glass instead.
+ material = get_material_by_name("glass")
+
+ set_material(material)
+
+/obj/item/weapon/shard/proc/set_material(material/material)
+ if(istype(material))
+ src.material = material
+ icon_state = "[material.shard_icon][pick("large", "medium", "small")]"
+ pixel_x = rand(-8, 8)
+ pixel_y = rand(-8, 8)
+ update_material()
+ update_icon()
+
+/obj/item/weapon/shard/proc/update_material()
+ if(material)
+ if(material.shard_type)
+ name = "[material.display_name] [material.shard_type]"
+ desc = "A small piece of [material.display_name]. It looks sharp, you wouldn't want to step on it barefoot. Could probably be used as ... a throwing weapon?"
+ switch(material.shard_type)
+ if(SHARD_SPLINTER, SHARD_SHRAPNEL)
+ gender = "plural"
+ else
+ gender = "neuter"
else
- return
+ qdel(src)
+ return
+ else
+ name = initial(name)
+ desc = initial(desc)
+
+/obj/item/weapon/shard/update_icon()
+ if(material)
+ color = material.icon_colour
+ // 1-(1-x)^2, so that glass shards with 0.3 opacity end up somewhat visible at 0.51 opacity
+ alpha = 255 * (1 - (1 - material.opacity)*(1 - material.opacity))
+ else
+ color = "#ffffff"
+ alpha = 255
/obj/item/weapon/shard/attackby(obj/item/weapon/W as obj, mob/user as mob)
- ..()
- if ( istype(W, /obj/item/weapon/weldingtool))
+ if(istype(W, /obj/item/weapon/weldingtool) && material.shard_can_repair)
var/obj/item/weapon/weldingtool/WT = W
if(WT.remove_fuel(0, user))
- var/obj/item/stack/sheet/glass/NG = new (user.loc)
- for (var/obj/item/stack/sheet/glass/G in user.loc)
- if(G==NG)
- continue
- if(G.amount>=G.max_amount)
- continue
- G.attackby(NG, user)
- usr << "You add the newly-formed glass to the stack. It now contains [NG.amount] sheets."
- //SN src = null
- del(src)
+ material.place_sheet(loc)
+ qdel(src)
return
return ..()
@@ -90,26 +111,10 @@
H.Weaken(3)
..()
-// Shrapnel
+// Preset types - left here for the code that uses them
-/obj/item/weapon/shard/shrapnel
- name = "shrapnel"
- icon = 'icons/obj/shards.dmi'
- icon_state = "shrapnellarge"
- desc = "A bunch of tiny bits of shattered metal."
+/obj/item/weapon/shard/shrapnel/New(loc)
+ ..(loc, get_material_by_name("steel"))
-/obj/item/weapon/shard/shrapnel/New()
-
- src.icon_state = pick("shrapnellarge", "shrapnelmedium", "shrapnelsmall")
- switch(src.icon_state)
- if("shrapnelsmall")
- src.pixel_x = rand(-12, 12)
- src.pixel_y = rand(-12, 12)
- if("shrapnelmedium")
- src.pixel_x = rand(-8, 8)
- src.pixel_y = rand(-8, 8)
- if("shrapnellarge")
- src.pixel_x = rand(-5, 5)
- src.pixel_y = rand(-5, 5)
- else
- return
+/obj/item/weapon/shard/phoron/New(loc)
+ ..(loc, get_material_by_name("phoron glass"))
diff --git a/code/game/objects/items/weapons/shields.dm b/code/game/objects/items/weapons/shields.dm
index 4fd210c171e..612dde6d7b7 100644
--- a/code/game/objects/items/weapons/shields.dm
+++ b/code/game/objects/items/weapons/shields.dm
@@ -13,8 +13,8 @@
throw_speed = 1
throw_range = 4
w_class = 4.0
- matter = list("glass" = 7500, "metal" = 1000)
- origin_tech = list(TECH_MATERIAL = 2)
+ origin_tech = list(TECH_MATERIAL = 2)
+ matter = list("glass" = 7500, DEFAULT_WALL_MATERIAL = 1000)
attack_verb = list("shoved", "bashed")
var/cooldown = 0 //shield bash cooldown. based on world.time
diff --git a/code/game/objects/items/weapons/storage/backpack.dm b/code/game/objects/items/weapons/storage/backpack.dm
index e9df3e12559..24ea335b10a 100644
--- a/code/game/objects/items/weapons/storage/backpack.dm
+++ b/code/game/objects/items/weapons/storage/backpack.dm
@@ -6,8 +6,17 @@
/obj/item/weapon/storage/backpack
name = "backpack"
desc = "You wear this on your back and put items into it."
+ item_icons = list(
+ slot_l_hand_str = 'icons/mob/items/lefthand_backpacks.dmi',
+ slot_r_hand_str = 'icons/mob/items/righthand_backpacks.dmi',
+ )
icon_state = "backpack"
- item_state = "backpack"
+ item_state = null
+ //most backpacks use the default backpack state for inhand overlays
+ item_state_slots = list(
+ slot_l_hand_str = "backpack",
+ slot_r_hand_str = "backpack",
+ )
w_class = 4
slot_flags = SLOT_BACK
max_w_class = 3
@@ -49,8 +58,8 @@
attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/storage/backpack/holding))
user << "\red The Bluespace interfaces of the two devices conflict and malfunction."
- del(W)
- return
+ qdel(W)
+ return
..()
//Please don't clutter the parent storage item with stupid hacks.
@@ -58,7 +67,7 @@
if(istype(W, /obj/item/weapon/storage/backpack/holding))
return 1
return ..()
-
+
/obj/item/weapon/storage/backpack/santabag
name = "\improper Santa's gift bag"
desc = "Space Santa uses this to deliver toys to all the nice children in space in Christmas! Wow, it's pretty big!"
@@ -68,6 +77,7 @@
storage_slots = 20
max_w_class = 3
max_storage_space = 400 // can store a ton of shit!
+ item_state_slots = null
/obj/item/weapon/storage/backpack/cultpack
name = "trophy rack"
@@ -78,61 +88,56 @@
name = "Giggles von Honkerton"
desc = "It's a backpack made by Honk! Co."
icon_state = "clownpack"
- item_state = "clownpack"
+ item_state_slots = null
/obj/item/weapon/storage/backpack/medic
name = "medical backpack"
desc = "It's a backpack especially designed for use in a sterile environment."
icon_state = "medicalpack"
- item_state = "medicalpack"
+ item_state_slots = null
/obj/item/weapon/storage/backpack/security
name = "security backpack"
desc = "It's a very robust backpack."
icon_state = "securitypack"
- item_state = "securitypack"
+ item_state_slots = null
/obj/item/weapon/storage/backpack/captain
name = "captain's backpack"
desc = "It's a special backpack made exclusively for Nanotrasen officers."
icon_state = "captainpack"
- item_state = "captainpack"
+ item_state_slots = null
/obj/item/weapon/storage/backpack/industrial
name = "industrial backpack"
desc = "It's a tough backpack for the daily grind of station life."
icon_state = "engiepack"
- item_state = "engiepack"
+ item_state_slots = null
/obj/item/weapon/storage/backpack/toxins
name = "laboratory backpack"
desc = "It's a light backpack modeled for use in laboratories and other scientific institutions."
icon_state = "toxpack"
- item_state = "toxpack"
/obj/item/weapon/storage/backpack/hydroponics
name = "herbalist's backpack"
desc = "It's a green backpack with many pockets to store plants and tools in."
icon_state = "hydpack"
- item_state = "hydpack"
/obj/item/weapon/storage/backpack/genetics
name = "geneticist backpack"
desc = "It's a backpack fitted with slots for diskettes and other workplace tools."
icon_state = "genpack"
- item_state = "genpack"
/obj/item/weapon/storage/backpack/virology
name = "sterile backpack"
desc = "It's a sterile backpack able to withstand different pathogens from entering its fabric."
icon_state = "viropack"
- item_state = "viropack"
/obj/item/weapon/storage/backpack/chemistry
name = "chemistry backpack"
desc = "It's an orange backpack which was designed to hold beakers, pill bottles and bottles."
icon_state = "chempack"
- item_state = "chempack"
/*
* Satchel Types
@@ -157,13 +162,19 @@
name = "industrial satchel"
desc = "A tough satchel with extra pockets."
icon_state = "satchel-eng"
- item_state = "engiepack"
+ item_state_slots = list(
+ slot_l_hand_str = "engiepack",
+ slot_r_hand_str = "engiepack",
+ )
/obj/item/weapon/storage/backpack/satchel_med
name = "medical satchel"
desc = "A sterile satchel used in medical departments."
icon_state = "satchel-med"
- item_state = "medicalpack"
+ item_state_slots = list(
+ slot_l_hand_str = "medicalpack",
+ slot_r_hand_str = "medicalpack",
+ )
/obj/item/weapon/storage/backpack/satchel_vir
name = "virologist satchel"
@@ -189,7 +200,10 @@
name = "security satchel"
desc = "A robust satchel for security related needs."
icon_state = "satchel-sec"
- item_state = "securitypack"
+ item_state_slots = list(
+ slot_l_hand_str = "securitypack",
+ slot_r_hand_str = "securitypack",
+ )
/obj/item/weapon/storage/backpack/satchel_hyd
name = "hydroponics satchel"
@@ -201,13 +215,17 @@
desc = "An exclusive satchel for Nanotrasen officers."
icon_state = "satchel-cap"
item_state = "captainpack"
+ item_state_slots = null
//ERT backpacks.
/obj/item/weapon/storage/backpack/ert
name = "emergency response team backpack"
desc = "A spacious backpack with lots of pockets, used by members of the Nanotrasen Emergency Response Team."
icon_state = "ert_commander"
- item_state = "backpack"
+ item_state_slots = list(
+ slot_l_hand_str = "securitypack",
+ slot_r_hand_str = "securitypack",
+ )
//Commander
/obj/item/weapon/storage/backpack/ert/commander
diff --git a/code/game/objects/items/weapons/storage/bags.dm b/code/game/objects/items/weapons/storage/bags.dm
index 0ee5df08e06..52eaa4510d3 100644
--- a/code/game/objects/items/weapons/storage/bags.dm
+++ b/code/game/objects/items/weapons/storage/bags.dm
@@ -162,7 +162,7 @@
usr.client.screen -= S
S.dropped(usr)
if(!S.amount)
- del S
+ qdel(S)
else
S.loc = src
@@ -207,7 +207,7 @@
N.amount = stacksize
S.amount -= stacksize
if(!S.amount)
- del S // todo: there's probably something missing here
+ qdel(S) // todo: there's probably something missing here
orient2hud(usr)
if(usr.s_active)
usr.s_active.show_to(usr)
diff --git a/code/game/objects/items/weapons/storage/belt.dm b/code/game/objects/items/weapons/storage/belt.dm
index 47821d6a244..79b1852e7b1 100644
--- a/code/game/objects/items/weapons/storage/belt.dm
+++ b/code/game/objects/items/weapons/storage/belt.dm
@@ -92,12 +92,9 @@
/obj/item/weapon/storage/belt/medical/emt
name = "EMT utility belt"
desc = "A sturdy black webbing belt with attached pouches."
- icon = 'icons/obj/custom_items.dmi'
icon_state = "emsbelt"
item_state = "emsbelt"
-
-
/obj/item/weapon/storage/belt/security
name = "security belt"
desc = "Can hold security gear like handcuffs and flashes."
diff --git a/code/game/objects/items/weapons/storage/boxes.dm b/code/game/objects/items/weapons/storage/boxes.dm
index 4c0c58a05ac..d5af4b2bc7c 100644
--- a/code/game/objects/items/weapons/storage/boxes.dm
+++ b/code/game/objects/items/weapons/storage/boxes.dm
@@ -48,26 +48,25 @@
// Now make the cardboard
user << "You fold [src] flat."
new src.foldable(get_turf(src))
- del(src)
+ qdel(src)
/obj/item/weapon/storage/box/survival/
New()
..()
- contents = list()
- sleep(1)
new /obj/item/clothing/mask/breath( src )
new /obj/item/weapon/tank/emergency_oxygen( src )
- return
+
+/obj/item/weapon/storage/box/survival/vox/
+ New()
+ ..()
+ new /obj/item/clothing/mask/breath( src )
+ new /obj/item/weapon/tank/emergency_nitrogen( src )
/obj/item/weapon/storage/box/engineer/
New()
..()
- contents = list()
- sleep(1)
new /obj/item/clothing/mask/breath( src )
new /obj/item/weapon/tank/emergency_oxygen/engi( src )
- return
-
/obj/item/weapon/storage/box/gloves
name = "box of latex gloves"
@@ -243,6 +242,20 @@
new /obj/item/ammo_casing/shotgun/stunshell(src)
new /obj/item/ammo_casing/shotgun/stunshell(src)
+/obj/item/weapon/storage/box/practiceshells
+ name = "box of practice shells"
+ desc = "It has a picture of a gun and several warning symbols on the front. WARNING: Live ammunition. Misuse may result in serious injury or death."
+
+ New()
+ ..()
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+ new /obj/item/ammo_casing/shotgun/practice(src)
+
/obj/item/weapon/storage/box/sniperammo
name = "box of 14.5mm shells"
desc = "It has a picture of a gun and several warning symbols on the front. WARNING: Live ammunition. Misuse may result in serious injury or death."
diff --git a/code/game/objects/items/weapons/storage/fancy.dm b/code/game/objects/items/weapons/storage/fancy.dm
index 7af6e3b16eb..081d1f7ba65 100644
--- a/code/game/objects/items/weapons/storage/fancy.dm
+++ b/code/game/objects/items/weapons/storage/fancy.dm
@@ -93,27 +93,27 @@
storage_slots = 6
icon_type = "crayon"
can_hold = list(
- /obj/item/toy/crayon
+ /obj/item/weapon/pen/crayon
)
/obj/item/weapon/storage/fancy/crayons/New()
..()
- new /obj/item/toy/crayon/red(src)
- new /obj/item/toy/crayon/orange(src)
- new /obj/item/toy/crayon/yellow(src)
- new /obj/item/toy/crayon/green(src)
- new /obj/item/toy/crayon/blue(src)
- new /obj/item/toy/crayon/purple(src)
+ new /obj/item/weapon/pen/crayon/red(src)
+ new /obj/item/weapon/pen/crayon/orange(src)
+ new /obj/item/weapon/pen/crayon/yellow(src)
+ new /obj/item/weapon/pen/crayon/green(src)
+ new /obj/item/weapon/pen/crayon/blue(src)
+ new /obj/item/weapon/pen/crayon/purple(src)
update_icon()
/obj/item/weapon/storage/fancy/crayons/update_icon()
overlays = list() //resets list
overlays += image('icons/obj/crayons.dmi',"crayonbox")
- for(var/obj/item/toy/crayon/crayon in contents)
+ for(var/obj/item/weapon/pen/crayon/crayon in contents)
overlays += image('icons/obj/crayons.dmi',crayon.colourName)
/obj/item/weapon/storage/fancy/crayons/attackby(obj/item/W as obj, mob/user as mob)
- if(istype(W,/obj/item/toy/crayon))
+ if(istype(W,/obj/item/weapon/pen/crayon))
switch(W:colourName)
if("mime")
usr << "This crayon is too sad to be contained in this box."
@@ -146,8 +146,8 @@
new /obj/item/clothing/mask/smokable/cigarette(src)
create_reagents(15 * storage_slots)//so people can inject cigarettes without opening a packet, now with being able to inject the whole one
-/obj/item/weapon/storage/fancy/cigarettes/Del()
- del(reagents)
+/obj/item/weapon/storage/fancy/cigarettes/Destroy()
+ qdel(reagents)
..()
@@ -158,7 +158,7 @@
/obj/item/weapon/storage/fancy/cigarettes/remove_from_storage(obj/item/W as obj, atom/new_location)
var/obj/item/clothing/mask/smokable/cigarette/C = W
if(!istype(C)) return // what
- reagents.trans_to(C, (reagents.total_volume/contents.len))
+ reagents.trans_to_obj(C, (reagents.total_volume/contents.len))
..()
/obj/item/weapon/storage/fancy/cigarettes/attack(mob/living/carbon/M as mob, mob/living/carbon/user as mob)
@@ -167,7 +167,7 @@
if(M == user && user.zone_sel.selecting == "mouth" && contents.len > 0 && !user.wear_mask)
var/obj/item/clothing/mask/smokable/cigarette/W = new /obj/item/clothing/mask/smokable/cigarette(user)
- reagents.trans_to(W, (reagents.total_volume/contents.len))
+ reagents.trans_to_obj(W, (reagents.total_volume/contents.len))
user.equip_to_slot_if_possible(W, slot_wear_mask)
reagents.maximum_volume = 15 * contents.len
contents.len--
@@ -202,8 +202,8 @@
new /obj/item/clothing/mask/smokable/cigarette/cigar(src)
create_reagents(15 * storage_slots)
-/obj/item/weapon/storage/fancy/cigar/Del()
- del(reagents)
+/obj/item/weapon/storage/fancy/cigar/Destroy()
+ qdel(reagents)
..()
/obj/item/weapon/storage/fancy/cigar/update_icon()
@@ -213,7 +213,7 @@
/obj/item/weapon/storage/fancy/cigar/remove_from_storage(obj/item/W as obj, atom/new_location)
var/obj/item/clothing/mask/smokable/cigarette/cigar/C = W
if(!istype(C)) return
- reagents.trans_to(C, (reagents.total_volume/contents.len))
+ reagents.trans_to_obj(C, (reagents.total_volume/contents.len))
..()
/obj/item/weapon/storage/fancy/cigar/attack(mob/living/carbon/M as mob, mob/living/carbon/user as mob)
@@ -222,7 +222,7 @@
if(M == user && user.zone_sel.selecting == "mouth" && contents.len > 0 && !user.wear_mask)
var/obj/item/clothing/mask/smokable/cigarette/cigar/W = new /obj/item/clothing/mask/smokable/cigarette/cigar(user)
- reagents.trans_to(W, (reagents.total_volume/contents.len))
+ reagents.trans_to_obj(W, (reagents.total_volume/contents.len))
user.equip_to_slot_if_possible(W, slot_wear_mask)
reagents.maximum_volume = 15 * contents.len
contents.len--
diff --git a/code/game/objects/items/weapons/storage/firstaid.dm b/code/game/objects/items/weapons/storage/firstaid.dm
index 304c59fb982..c23dfcdb516 100644
--- a/code/game/objects/items/weapons/storage/firstaid.dm
+++ b/code/game/objects/items/weapons/storage/firstaid.dm
@@ -131,6 +131,7 @@
/obj/item/weapon/storage/firstaid/surgery
name = "surgery kit"
desc = "Contains tools for surgery."
+ storage_slots = 10
/obj/item/weapon/storage/firstaid/surgery/New()
..()
@@ -142,6 +143,9 @@
new /obj/item/weapon/retractor(src)
new /obj/item/weapon/scalpel(src)
new /obj/item/weapon/surgicaldrill(src)
+ new /obj/item/weapon/bonegel(src)
+ new /obj/item/weapon/FixOVein(src)
+ new /obj/item/stack/medical/advanced/bruise_pack(src)
return
/*
@@ -285,3 +289,17 @@
new /obj/item/weapon/reagent_containers/pill/tramadol( src )
new /obj/item/weapon/reagent_containers/pill/tramadol( src )
new /obj/item/weapon/reagent_containers/pill/tramadol( src )
+
+/obj/item/weapon/storage/pill_bottle/citalopram
+ name = "bottle of Citalopram pills"
+ desc = "Contains pills used to stabilize a patient's mood."
+
+ New()
+ ..()
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
+ new /obj/item/weapon/reagent_containers/pill/citalopram( src )
\ No newline at end of file
diff --git a/code/game/objects/items/weapons/storage/internal.dm b/code/game/objects/items/weapons/storage/internal.dm
index 5dda9b89c25..89f058ba477 100644
--- a/code/game/objects/items/weapons/storage/internal.dm
+++ b/code/game/objects/items/weapons/storage/internal.dm
@@ -9,6 +9,10 @@
name = master_item.name
verbs -= /obj/item/verb/verb_pickup //make sure this is never picked up.
..()
+
+/obj/item/weapon/storage/internal/Destroy()
+ master_item = null
+ ..()
/obj/item/weapon/storage/internal/attack_hand()
return //make sure this is never picked up
diff --git a/code/game/objects/items/weapons/storage/misc.dm b/code/game/objects/items/weapons/storage/misc.dm
index 814ee3b12cd..65e1bfea37e 100644
--- a/code/game/objects/items/weapons/storage/misc.dm
+++ b/code/game/objects/items/weapons/storage/misc.dm
@@ -37,5 +37,4 @@
i++
/obj/item/weapon/storage/box/donut/empty
- icon_state = "donutbox0"
startswith = 0
diff --git a/code/game/objects/items/weapons/storage/storage.dm b/code/game/objects/items/weapons/storage/storage.dm
index 495d4d75167..61786e10db0 100644
--- a/code/game/objects/items/weapons/storage/storage.dm
+++ b/code/game/objects/items/weapons/storage/storage.dm
@@ -11,6 +11,7 @@
w_class = 3
var/list/can_hold = new/list() //List of objects which this item can store (if set, it can't store anything else)
var/list/cant_hold = new/list() //List of objects which this item can't store (in effect only if can_hold isn't set)
+ var/list/is_seeing = new/list() //List of mobs which are currently seeing the contents of this item's storage
var/max_w_class = 2 //Max size of objects that this object can store (in effect only if can_hold isn't set)
var/max_storage_space = 14 //The sum of the storage costs of all the items in this storage item.
var/storage_slots = 7 //The number of storage slots in this container.
@@ -23,6 +24,12 @@
var/collection_mode = 1; //0 = pick one at a time, 1 = pick all on tile
var/use_sound = "rustle" //sound played when used. null for no sound.
+/obj/item/weapon/storage/Destroy()
+ close_all()
+ qdel(boxes)
+ qdel(closer)
+ ..()
+
/obj/item/weapon/storage/MouseDrop(obj/over_object as obj)
if(!canremove)
@@ -30,7 +37,7 @@
if (ishuman(usr) || issmall(usr)) //so monkeys can take off their backpacks -- Urist
- if (istype(usr.loc,/obj/mecha)) // stops inventory actions in a mech
+ if (istype(usr.loc,/obj/mecha)) // stops inventory actions in a mech. why?
return
if(over_object == usr && Adjacent(usr)) // this must come before the screen objects only block
@@ -44,18 +51,21 @@
//there's got to be a better way of doing this.
if (!(src.loc == usr) || (src.loc && src.loc.loc == usr))
return
-
- if (!( usr.restrained() ) && !( usr.stat ))
- switch(over_object.name)
- if("r_hand")
- usr.u_equip(src)
- usr.put_in_r_hand(src)
- if("l_hand")
- usr.u_equip(src)
- usr.put_in_l_hand(src)
- src.add_fingerprint(usr)
+
+ if (( usr.restrained() ) || ( usr.stat ))
return
- return
+
+ if ((src.loc == usr) && !usr.unEquip(src))
+ return
+
+ switch(over_object.name)
+ if("r_hand")
+ usr.u_equip(src)
+ usr.put_in_r_hand(src)
+ if("l_hand")
+ usr.u_equip(src)
+ usr.put_in_l_hand(src)
+ src.add_fingerprint(usr)
/obj/item/weapon/storage/proc/return_inv()
@@ -86,6 +96,7 @@
user.client.screen += src.closer
user.client.screen += src.contents
user.s_active = src
+ is_seeing |= user
return
/obj/item/weapon/storage/proc/hide_from(mob/user as mob)
@@ -97,7 +108,7 @@
user.client.screen -= src.contents
if(user.s_active == src)
user.s_active = null
- return
+ is_seeing -= user
/obj/item/weapon/storage/proc/open(mob/user as mob)
if (src.use_sound)
@@ -109,11 +120,24 @@
show_to(user)
/obj/item/weapon/storage/proc/close(mob/user as mob)
-
src.hide_from(user)
user.s_active = null
return
+/obj/item/weapon/storage/proc/close_all()
+ for(var/mob/M in can_see_contents())
+ close(M)
+ . = 1
+
+/obj/item/weapon/storage/proc/can_see_contents()
+ var/list/cansee = list()
+ for(var/mob/M in is_seeing)
+ if(M.s_active == src && M.client)
+ cansee |= M
+ else
+ is_seeing -= M
+ return cansee
+
//This proc draws out the inventory and places the items on it. tx and ty are the upper left tile and mx, my are the bottm right.
//The numbers are calculated from the bottom-left The bottom-left slot being 1,1.
/obj/item/weapon/storage/proc/orient_objs(tx, ty, mx, my)
@@ -163,7 +187,7 @@
New(obj/item/sample as obj)
if(!istype(sample))
- del(src)
+ qdel(src)
sample_object = sample
number = 1
@@ -463,4 +487,4 @@
return depth
/obj/item/proc/get_storage_cost()
- return 2**(w_class-1) //1,2,4,8,16,...
+ return 2**(w_class-1) //1,2,4,8,16,...
diff --git a/code/game/objects/items/weapons/storage/wallets.dm b/code/game/objects/items/weapons/storage/wallets.dm
index fb6829abf58..9b4f9271a24 100644
--- a/code/game/objects/items/weapons/storage/wallets.dm
+++ b/code/game/objects/items/weapons/storage/wallets.dm
@@ -11,7 +11,6 @@
/obj/item/device/flashlight/pen,
/obj/item/seeds,
/obj/item/stack/medical,
- /obj/item/toy/crayon,
/obj/item/weapon/coin,
/obj/item/weapon/dice,
/obj/item/weapon/disk,
diff --git a/code/game/objects/items/weapons/surgery_limbattachment.dm b/code/game/objects/items/weapons/surgery_limbattachment.dm
index 23e5013f1a9..b52bb1bb3f3 100644
--- a/code/game/objects/items/weapons/surgery_limbattachment.dm
+++ b/code/game/objects/items/weapons/surgery_limbattachment.dm
@@ -65,7 +65,7 @@
H.update_body()
M.updatehealth()
M.UpdateDamageIcon()
- del(src)
+ qdel(src)
return 1
return 0
diff --git a/code/game/objects/items/weapons/surgery_tools.dm b/code/game/objects/items/weapons/surgery_tools.dm
index cedede4ca8f..9f32e0f73be 100644
--- a/code/game/objects/items/weapons/surgery_tools.dm
+++ b/code/game/objects/items/weapons/surgery_tools.dm
@@ -16,7 +16,7 @@
desc = "Retracts stuff."
icon = 'icons/obj/surgery.dmi'
icon_state = "retractor"
- matter = list("metal" = 10000, "glass" = 5000)
+ matter = list(DEFAULT_WALL_MATERIAL = 10000, "glass" = 5000)
flags = CONDUCT
w_class = 2.0
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
@@ -29,7 +29,7 @@
desc = "You think you have seen this before."
icon = 'icons/obj/surgery.dmi'
icon_state = "hemostat"
- matter = list("metal" = 5000, "glass" = 2500)
+ matter = list(DEFAULT_WALL_MATERIAL = 5000, "glass" = 2500)
flags = CONDUCT
w_class = 2.0
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
@@ -43,7 +43,7 @@
desc = "This stops bleeding."
icon = 'icons/obj/surgery.dmi'
icon_state = "cautery"
- matter = list("metal" = 5000, "glass" = 2500)
+ matter = list(DEFAULT_WALL_MATERIAL = 5000, "glass" = 2500)
flags = CONDUCT
w_class = 2.0
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
@@ -58,7 +58,7 @@
icon = 'icons/obj/surgery.dmi'
icon_state = "drill"
hitsound = 'sound/weapons/circsawhit.ogg'
- matter = list("metal" = 15000, "glass" = 10000)
+ matter = list(DEFAULT_WALL_MATERIAL = 15000, "glass" = 10000)
flags = CONDUCT
force = 15.0
w_class = 2.0
@@ -86,8 +86,8 @@
throwforce = 5.0
throw_speed = 3
throw_range = 5
- matter = list("metal" = 10000, "glass" = 5000)
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 10000, "glass" = 5000)
attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
suicide_act(mob/user)
@@ -140,8 +140,8 @@
throwforce = 9.0
throw_speed = 3
throw_range = 5
- matter = list("metal" = 20000,"glass" = 10000)
origin_tech = list(TECH_MATERIAL = 1, TECH_BIO = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 20000,"glass" = 10000)
attack_verb = list("attacked", "slashed", "sawed", "cut")
sharp = 1
edge = 1
diff --git a/code/game/objects/items/weapons/syndie.dm b/code/game/objects/items/weapons/syndie.dm
index e205f20bb09..a0af746ab4c 100644
--- a/code/game/objects/items/weapons/syndie.dm
+++ b/code/game/objects/items/weapons/syndie.dm
@@ -44,7 +44,7 @@
D.open()
if(istype(T,/turf/simulated/wall))
T.dismantle_wall(1)
- del(src)
+ qdel(src)
/*Detonator, disguised as a lighter*/
diff --git a/code/game/objects/items/weapons/table_rack_parts.dm b/code/game/objects/items/weapons/table_rack_parts.dm
deleted file mode 100644
index 2dfc3f4730a..00000000000
--- a/code/game/objects/items/weapons/table_rack_parts.dm
+++ /dev/null
@@ -1,101 +0,0 @@
-// Table parts and rack parts
-
-/obj/item/weapon/table_parts
- name = "table parts"
- desc = "Parts of a table. Poor table."
- gender = PLURAL
- icon = 'icons/obj/items.dmi'
- icon_state = "table_parts"
- matter = list("metal" = 3750)
- flags = CONDUCT
- attack_verb = list("slammed", "bashed", "battered", "bludgeoned", "thrashed", "whacked")
-
- var/build_type = /obj/structure/table
- var/alter_type = /obj/item/weapon/table_parts/reinforced
- var/alter_with = /obj/item/stack/rods
- var/alter_cost = 4
- var/list/stack_types = list(/obj/item/stack/sheet/metal)
-
-/obj/item/weapon/table_parts/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/wrench))
- for(var/material_type in stack_types)
- new material_type(get_turf(user))
- del(src)
- return
- else
- if(alter_type && alter_with && istype(W,alter_with))
- var/obj/item/stack/R = W
- if (R.use(alter_cost))
- var/obj/item/new_parts = new alter_type (get_turf(loc))
- user << "You modify \the [name] into \a [new_parts]."
- del(src)
- else
- user << "You need at least [alter_cost] sheets to reinforce the [name]."
- return
- ..()
-
-/obj/item/weapon/table_parts/attack_self(mob/user as mob)
- if(locate(/obj/structure/table) in user.loc)
- user << "There is already a table here."
- return
-
- new build_type( user.loc )
- user.drop_item()
- del(src)
- return
-
-/obj/item/weapon/table_parts/reinforced
- name = "reinforced table parts"
- desc = "Hard table parts. Well... harder."
- icon = 'icons/obj/items.dmi'
- icon_state = "reinf_tableparts"
- matter = list("metal" = 7500)
- flags = CONDUCT
-
- stack_types = list(/obj/item/stack/sheet/metal, /obj/item/stack/rods)
- build_type = /obj/structure/table/reinforced
- alter_type = null
- alter_with = null
- alter_cost = null
-
-/obj/item/weapon/table_parts/wood
- name = "wooden table parts"
- desc = "Keep away from fire."
- icon_state = "wood_tableparts"
- flags = null
-
- stack_types = list(/obj/item/stack/sheet/wood)
- build_type = /obj/structure/table/woodentable
- alter_type = /obj/item/weapon/table_parts/gambling
- alter_with = /obj/item/stack/tile/carpet
- alter_cost = 1
-
-/obj/item/weapon/table_parts/gambling
- name = "gambling table parts"
- desc = "Keep away from security."
- icon_state = "gamble_tableparts"
- flags = null
-
- stack_types = list(/obj/item/stack/tile/carpet,/obj/item/stack/sheet/wood)
- build_type = /obj/structure/table/gamblingtable
- alter_type = null
- alter_with = null
- alter_cost = null
-
-/obj/item/weapon/table_parts/gambling/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if (istype(W, /obj/item/weapon/crowbar))
- new /obj/item/stack/tile/carpet( get_turf(loc) )
- new /obj/item/weapon/table_parts/wood( get_turf(loc) )
- user << "You pry the carpet out of the table."
- del(src)
- ..()
-
-/obj/item/weapon/table_parts/rack
- name = "rack parts"
- desc = "Parts of a rack."
- icon_state = "rack_parts"
- stack_types = list(/obj/item/stack/sheet/metal)
- build_type = /obj/structure/table/rack
- alter_type = null
- alter_with = null
- alter_cost = null
\ No newline at end of file
diff --git a/code/game/objects/items/weapons/tanks/jetpack.dm b/code/game/objects/items/weapons/tanks/jetpack.dm
index 422af1d652d..67b5f007a54 100644
--- a/code/game/objects/items/weapons/tanks/jetpack.dm
+++ b/code/game/objects/items/weapons/tanks/jetpack.dm
@@ -63,7 +63,7 @@
if(allgases >= 0.005)
return 1
- del(G)
+ qdel(G)
return
/obj/item/weapon/tank/jetpack/ui_action_click()
@@ -143,5 +143,5 @@
var/allgases = G.gas["carbon_dioxide"] + G.gas["nitrogen"] + G.gas["oxygen"] + G.gas["phoron"]
if(allgases >= 0.005)
return 1
- del(G)
+ qdel(G)
return
diff --git a/code/game/objects/items/weapons/tanks/tank_types.dm b/code/game/objects/items/weapons/tanks/tank_types.dm
index 3f2bbb18265..a43d49a39c9 100644
--- a/code/game/objects/items/weapons/tanks/tank_types.dm
+++ b/code/game/objects/items/weapons/tanks/tank_types.dm
@@ -144,6 +144,29 @@
icon_state = "emergency_double"
volume = 10
+/obj/item/weapon/tank/emergency_nitrogen
+ name = "emergency nitrogen tank"
+ desc = "An emergency air tank hastily painted red and issued to Vox crewmembers."
+ icon_state = "emergency_nitro"
+ flags = CONDUCT
+ slot_flags = SLOT_BELT
+ w_class = 2.0
+ force = 4.0
+ distribute_pressure = ONE_ATMOSPHERE*O2STANDARD
+ volume = 2
+
+ New()
+ ..()
+ src.air_contents.adjust_gas("nitrogen", (3*ONE_ATMOSPHERE)*volume/(R_IDEAL_GAS_EQUATION*T20C))
+
+ return
+
+
+ examine(mob/user)
+ if(..(user, 0) && air_contents.gas["nitrogen"] < 0.2 && loc==user)
+ user << text("\red The meter on the [src.name] indicates you are almost out of air!")
+ user << sound('sound/effects/alert.ogg')
+
/*
* Nitrogen
*/
diff --git a/code/game/objects/items/weapons/tanks/tanks.dm b/code/game/objects/items/weapons/tanks/tanks.dm
index 04d32c49b22..f1cd0286baa 100644
--- a/code/game/objects/items/weapons/tanks/tanks.dm
+++ b/code/game/objects/items/weapons/tanks/tanks.dm
@@ -31,9 +31,9 @@
processing_objects.Add(src)
return
-/obj/item/weapon/tank/Del()
+/obj/item/weapon/tank/Destroy()
if(air_contents)
- del(air_contents)
+ qdel(air_contents)
processing_objects.Remove(src)
@@ -71,12 +71,12 @@
if(prob(50))
var/turf/location = src.loc
if (!( istype(location, /turf) ))
- del(src)
+ qdel(src)
if(src.air_contents)
location.assume_air(air_contents)
- del(src)
+ qdel(src)
/obj/item/weapon/tank/attackby(obj/item/weapon/W as obj, mob/user as mob)
..()
@@ -274,7 +274,7 @@
//world << "\blue Exploding Pressure: [pressure] kPa, intensity: [range]"
explosion(epicenter, round(range*0.25), round(range*0.5), round(range), round(range*1.5))
- del(src)
+ qdel(src)
else if(pressure > TANK_RUPTURE_PRESSURE)
//world << "\blue[x],[y] tank is rupturing: [pressure] kPa, integrity [integrity]"
@@ -284,7 +284,7 @@
return
T.assume_air(air_contents)
playsound(src.loc, 'sound/effects/spray.ogg', 10, 1, -3)
- del(src)
+ qdel(src)
else
integrity--
diff --git a/code/game/objects/items/weapons/tape.dm b/code/game/objects/items/weapons/tape.dm
index 477bce6b32c..911a6334d25 100644
--- a/code/game/objects/items/weapons/tape.dm
+++ b/code/game/objects/items/weapons/tape.dm
@@ -58,7 +58,7 @@
user.put_in_hands(stuck)
stuck = null
overlays = null
- del(src)
+ qdel(src)
/obj/item/weapon/ducttape/afterattack(var/A, mob/user, flag, params)
if(!in_range(user, A) || istype(A, /obj/machinery/door) || !stuck)
diff --git a/code/game/objects/items/weapons/teleportation.dm b/code/game/objects/items/weapons/teleportation.dm
index f9933529407..fdad2423fcb 100644
--- a/code/game/objects/items/weapons/teleportation.dm
+++ b/code/game/objects/items/weapons/teleportation.dm
@@ -21,8 +21,8 @@
item_state = "electronic"
throw_speed = 4
throw_range = 20
- matter = list("metal" = 400)
- origin_tech = list(TECH_MAGNET = 1)
+ origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 400)
/obj/item/weapon/locator/attack_self(mob/user as mob)
user.set_machine(src)
@@ -132,8 +132,8 @@ Frequency:
w_class = 2.0
throw_speed = 3
throw_range = 5
- matter = list("metal" = 10000)
- origin_tech = list(TECH_MAGNET = 1, TECH_BLUESPACE = 3)
+ origin_tech = list(TECH_MAGNET = 1, TECH_BLUESPACE = 3)
+ matter = list(DEFAULT_WALL_MATERIAL = 10000)
/obj/item/weapon/hand_tele/attack_self(mob/user as mob)
var/turf/current_location = get_turf(user)//What turf is the user on?
diff --git a/code/game/objects/items/weapons/tools.dm b/code/game/objects/items/weapons/tools.dm
index 6dce4dbedce..7c8ceee86b5 100644
--- a/code/game/objects/items/weapons/tools.dm
+++ b/code/game/objects/items/weapons/tools.dm
@@ -24,8 +24,8 @@
force = 5.0
throwforce = 7.0
w_class = 2.0
- matter = list("metal" = 150)
- origin_tech = list(TECH_MATERIAL = 1, TECH_ENGINERING = 1)
+ origin_tech = list(TECH_MATERIAL = 1, TECH_ENGINERING = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 150)
attack_verb = list("bashed", "battered", "bludgeoned", "whacked")
@@ -44,7 +44,7 @@
throwforce = 5.0
throw_speed = 3
throw_range = 5
- matter = list("metal" = 75)
+ matter = list(DEFAULT_WALL_MATERIAL = 75)
attack_verb = list("stabbed")
suicide_act(mob/user)
@@ -102,8 +102,8 @@
throw_speed = 2
throw_range = 9
w_class = 2.0
- matter = list("metal" = 80)
- origin_tech = list(TECH_MATERIAL = 1, TECH_ENGINERING = 1)
+ origin_tech = list(TECH_MATERIAL = 1, TECH_ENGINERING = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 80)
attack_verb = list("pinched", "nipped")
sharp = 1
edge = 1
@@ -144,7 +144,7 @@
w_class = 2.0
//Cost to make in the autolathe
- matter = list("metal" = 70, "glass" = 30)
+ matter = list(DEFAULT_WALL_MATERIAL = 70, "glass" = 30)
//R&D tech level
origin_tech = list(TECH_ENGINERING = 1)
@@ -162,6 +162,10 @@
R.add_reagent("fuel", max_fuel)
return
+/obj/item/weapon/weldingtool/Destroy()
+ if(welding)
+ processing_objects -= src
+ ..()
/obj/item/weapon/weldingtool/examine(mob/user)
if(..(user, 0))
@@ -171,13 +175,13 @@
/obj/item/weapon/weldingtool/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W,/obj/item/weapon/screwdriver))
if(welding)
- user << "\red Stop welding first!"
+ user << "Stop welding first!"
return
status = !status
if(status)
- user << "\blue You resecure the welder."
+ user << "You secure the welder."
else
- user << "\blue The welder can now be attached and modified."
+ user << "The welder can now be attached and modified."
src.add_fingerprint(user)
return
@@ -207,31 +211,8 @@
/obj/item/weapon/weldingtool/process()
- switch(welding)
- //If off
- if(0)
- if(src.icon_state != "welder") //Check that the sprite is correct, if it isnt, it means toggle() was not called
- src.force = 3
- src.damtype = "brute"
- src.icon_state = "welder"
- src.welding = 0
- processing_objects.Remove(src)
- return
- //Welders left on now use up fuel, but lets not have them run out quite that fast
- if(1)
- if(src.icon_state != "welder1") //Check that the sprite is correct, if it isnt, it means toggle() was not called
- src.force = 15
- src.damtype = "fire"
- src.icon_state = "welder1"
- if(prob(5))
- remove_fuel(1)
-
- //If you're actually actively welding, use fuel faster.
- //Is this actually used or set anywhere? - Nodrak
- if(2)
- if(prob(75))
- remove_fuel(1)
-
+ if(welding && prob(5) && !remove_fuel(1))
+ setWelding(0)
//I'm not sure what this does. I assume it has to do with starting fires...
//...but it doesnt check to see if the welder is on or not.
@@ -247,8 +228,8 @@
/obj/item/weapon/weldingtool/afterattack(obj/O as obj, mob/user as mob, proximity)
if(!proximity) return
if (istype(O, /obj/structure/reagent_dispensers/fueltank) && get_dist(src,O) <= 1 && !src.welding)
- O.reagents.trans_to(src, max_fuel)
- user << "\blue Welder refueled"
+ O.reagents.trans_to_obj(src, max_fuel)
+ user << "Welder refueled"
playsound(src.loc, 'sound/effects/refill.ogg', 50, 1, -6)
return
else if (istype(O, /obj/structure/reagent_dispensers/fueltank) && get_dist(src,O) <= 1 && src.welding)
@@ -270,7 +251,7 @@
/obj/item/weapon/weldingtool/attack_self(mob/user as mob)
- toggle()
+ setWelding(!welding, usr)
return
//Returns the amount of fuel in the welder
@@ -280,80 +261,63 @@
//Removes fuel from the welding tool. If a mob is passed, it will perform an eyecheck on the mob. This should probably be renamed to use()
/obj/item/weapon/weldingtool/proc/remove_fuel(var/amount = 1, var/mob/M = null)
- if(!welding || !check_fuel())
- return 0
if(get_fuel() >= amount)
reagents.remove_reagent("fuel", amount)
- check_fuel()
if(M)
eyecheck(M)
return 1
else
if(M)
- M << "\blue You need more welding fuel to complete this task."
+ M << "You need more welding fuel to complete this task."
return 0
//Returns whether or not the welding tool is currently on.
/obj/item/weapon/weldingtool/proc/isOn()
return src.welding
+/obj/item/weapon/weldingtool/update_icon()
+ ..()
+ icon_state = welding ? "welder1" : "welder"
+ var/mob/M = loc
+ if(istype(M))
+ M.update_inv_l_hand()
+ M.update_inv_r_hand()
+
//Sets the welding state of the welding tool. If you see W.welding = 1 anywhere, please change it to W.setWelding(1)
//so that the welding tool updates accordingly
-/obj/item/weapon/weldingtool/proc/setWelding(var/temp_welding)
+/obj/item/weapon/weldingtool/proc/setWelding(var/set_welding, var/mob/M)
+ if(!status) return
+
+ var/turf/T = get_turf(src)
//If we're turning it on
- if(temp_welding > 0)
+ if(set_welding && !welding)
if (remove_fuel(1))
- usr << "\blue The [src] switches on."
+ if(M)
+ M << "You switch the [src] on."
+ else if(T)
+ T.visible_message("\The [src] turns on.")
src.force = 15
src.damtype = "fire"
- src.icon_state = "welder1"
- processing_objects.Add(src)
+ src.w_class = 4
+ welding = 1
+ update_icon()
+ processing_objects |= src
else
- usr << "\blue Need more fuel!"
- src.welding = 0
+ if(M)
+ M << "You need more welding fuel to complete this task."
return
//Otherwise
- else
- usr << "\blue The [src] switches off."
+ else if(!set_welding && welding)
+ processing_objects -= src
+ if(M)
+ M << "You switch \the [src] off."
+ else if(T)
+ T.visible_message("\The [src] turns off.")
src.force = 3
src.damtype = "brute"
- src.icon_state = "welder"
- src.welding = 0
-
-//Turns off the welder if there is no more fuel (does this really need to be its own proc?)
-/obj/item/weapon/weldingtool/proc/check_fuel()
- if((get_fuel() <= 0) && welding)
- toggle(1)
- return 0
- return 1
-
-
-//Toggles the welder off and on
-/obj/item/weapon/weldingtool/proc/toggle(var/message = 0)
- if(!status) return
- src.welding = !( src.welding )
- if (src.welding)
- if (remove_fuel(1))
- usr << "\blue You switch the [src] on."
- src.force = 15
- src.damtype = "fire"
- src.icon_state = "welder1"
- src.w_class = 4
- processing_objects.Add(src)
- else
- usr << "\blue Need more fuel!"
- src.welding = 0
- return
- else
- if(!message)
- usr << "\blue You switch the [src] off."
- else
- usr << "\blue The [src] shuts off!"
- src.force = 3
- src.damtype = "brute"
- src.icon_state = "welder"
- src.welding = 0
src.w_class = initial(src.w_class)
+ src.welding = 0
+ update_icon()
//Decides whether or not to damage a player's eyes based on what they're wearing as protection
//Note: This should probably be moved to mob
@@ -403,22 +367,22 @@
/obj/item/weapon/weldingtool/largetank
name = "industrial welding tool"
max_fuel = 40
- matter = list("metal" = 70, "glass" = 60)
- origin_tech = list(TECH_ENGINERING = 2)
+ origin_tech = list(TECH_ENGINERING = 2)
+ matter = list(DEFAULT_WALL_MATERIAL = 70, "glass" = 60)
/obj/item/weapon/weldingtool/hugetank
name = "upgraded welding tool"
max_fuel = 80
w_class = 3.0
- matter = list("metal" = 70, "glass" = 120)
- origin_tech = list(TECH_ENGINERING = 3)
+ origin_tech = list(TECH_ENGINERING = 3)
+ matter = list(DEFAULT_WALL_MATERIAL = 70, "glass" = 120)
/obj/item/weapon/weldingtool/experimental
name = "experimental welding tool"
max_fuel = 40
w_class = 3.0
- matter = list("metal" = 70, "glass" = 120)
- origin_tech = list(TECH_ENGINERING = 4, TECH_PHORON = 3)
+ origin_tech = list(TECH_ENGINERING = 4, TECH_PHORON = 3)
+ matter = list(DEFAULT_WALL_MATERIAL = 70, "glass" = 120)
var/last_gen = 0
@@ -444,8 +408,8 @@
throwforce = 7.0
item_state = "crowbar"
w_class = 2.0
- matter = list("metal" = 50)
- origin_tech = list(TECH_ENGINERING = 1)
+ origin_tech = list(TECH_ENGINERING = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 50)
attack_verb = list("attacked", "bashed", "battered", "bludgeoned", "whacked")
/obj/item/weapon/crowbar/red
diff --git a/code/game/objects/items/weapons/twohanded.dm b/code/game/objects/items/weapons/twohanded.dm
index a145d1db0d0..0b2b4c0e962 100644
--- a/code/game/objects/items/weapons/twohanded.dm
+++ b/code/game/objects/items/weapons/twohanded.dm
@@ -112,10 +112,10 @@
name = "offhand"
unwield()
- del(src)
+ qdel(src)
wield()
- del(src)
+ qdel(src)
/obj/item/weapon/twohanded/offhand/update_icon()
return
@@ -139,19 +139,17 @@
/obj/item/weapon/twohanded/fireaxe/afterattack(atom/A as mob|obj|turf|area, mob/user as mob, proximity)
if(!proximity) return
..()
- if(A && wielded && (istype(A,/obj/structure/window) || istype(A,/obj/structure/grille))) //destroys windows and grilles in one hit
- if(istype(A,/obj/structure/window)) //should just make a window.Break() proc but couldn't bother with it
+ if(A && wielded)
+ if(istype(A,/obj/structure/window))
var/obj/structure/window/W = A
+ W.shatter()
+ else if(istype(A,/obj/structure/grille))
+ qdel(A)
+ else if(istype(A,/obj/effect/plant))
+ var/obj/effect/plant/P = A
+ P.die_off()
- new /obj/item/weapon/shard( W.loc )
- if(W.reinf) new /obj/item/stack/rods( W.loc)
-
- if (W.dir == SOUTHWEST)
- new /obj/item/weapon/shard( W.loc )
- if(W.reinf) new /obj/item/stack/rods( W.loc)
- del(A)
-
-
+ qdel(A)
/*
* Double-Bladed Energy Swords - Cheridan
*/
diff --git a/code/game/objects/items/weapons/weaponry.dm b/code/game/objects/items/weapons/weaponry.dm
index 295fa0c67db..fbbc731f2ae 100644
--- a/code/game/objects/items/weapons/weaponry.dm
+++ b/code/game/objects/items/weapons/weaponry.dm
@@ -177,7 +177,7 @@
if(istype(W,/obj/item/weapon/screwdriver))
user << "You finish the concealed blade weapon."
new /obj/item/weapon/butterfly(user.loc)
- del(src)
+ qdel(src)
return
/obj/item/butterflyblade
@@ -185,21 +185,21 @@
desc = "A knife blade. Unusable as a weapon without a grip."
icon = 'icons/obj/buildingobject.dmi'
icon_state = "butterfly2"
- matter = list("metal" = 5000)
+ matter = list(DEFAULT_WALL_MATERIAL = 5000)
/obj/item/butterflyhandle
name = "concealed knife grip"
desc = "A plasteel grip with screw fittings for a blade."
icon = 'icons/obj/buildingobject.dmi'
icon_state = "butterfly1"
- matter = list("metal" = 4000)
+ matter = list(DEFAULT_WALL_MATERIAL = 4000)
/obj/item/butterflyhandle/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W,/obj/item/butterflyblade))
user << "You attach the two concealed blade parts."
new /obj/item/butterflyconstruction(user.loc)
- del(W)
- del(src)
+ qdel(W)
+ qdel(src)
return
update_icon(user)
@@ -252,8 +252,8 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
user.put_in_hands(S)
user << "You fasten the glass shard to the top of the rod with the cable."
- del(I)
- del(src)
+ qdel(I)
+ qdel(src)
update_icon(user)
else if(istype(I, /obj/item/weapon/wirecutters))
@@ -261,8 +261,8 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
user.put_in_hands(P)
user << "You fasten the wirecutters to the top of the rod with the cable, prongs outward."
- del(I)
- del(src)
+ qdel(I)
+ qdel(src)
update_icon(user)
update_icon(user)
@@ -276,7 +276,7 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
throw_range = 15
sharp = 1
edge = 1
- matter = list("metal" = 500)
+ matter = list(DEFAULT_WALL_MATERIAL = 500)
var/poisoned = 0
@@ -309,7 +309,7 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
/obj/item/weapon/energy_net/dropped()
spawn(10)
- if(src) del(src)
+ if(src) qdel(src)
/obj/item/weapon/energy_net/throw_impact(atom/hit_atom)
..()
@@ -317,7 +317,7 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
var/mob/living/M = hit_atom
if(!istype(M) || locate(/obj/effect/energy_net) in M.loc)
- del(src)
+ qdel(src)
return 0
var/turf/T = get_turf(M)
@@ -327,11 +327,11 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
M.captured = 1
net.affecting = M
T.visible_message("[M] was caught in an energy net!")
- del(src)
+ qdel(src)
// If we miss or hit an obstacle, we still want to delete the net.
spawn(10)
- if(src) del(src)
+ if(src) qdel(src)
/obj/effect/energy_net
name = "energy net"
@@ -356,7 +356,7 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
..()
processing_objects |= src
-/obj/effect/energy_net/Del()
+/obj/effect/energy_net/Destroy()
if(affecting)
var/mob/living/carbon/M = affecting
@@ -372,13 +372,13 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
if(health <=0)
density = 0
src.visible_message("The energy net is torn apart!")
- del(src)
+ qdel(src)
return
/obj/effect/energy_net/process()
if(isnull(affecting) || affecting.loc != loc)
- del(src)
+ qdel(src)
return
// Countdown begin set to -1 will stop the teleporter from firing.
@@ -411,7 +411,7 @@ obj/item/weapon/wirerod/attackby(var/obj/item/I, mob/user as mob)
playsound(affecting.loc, 'sound/effects/sparks2.ogg', 50, 1)
anim(affecting.loc,affecting,'icons/mob/mob.dmi',,"phasein",,affecting.dir)
- del(src)
+ qdel(src)
/obj/effect/energy_net/bullet_act(var/obj/item/projectile/Proj)
health -= Proj.damage
diff --git a/code/game/objects/items/weapons/weldbackpack.dm b/code/game/objects/items/weapons/weldbackpack.dm
index f1c786d3e11..0a4d4f6e706 100644
--- a/code/game/objects/items/weapons/weldbackpack.dm
+++ b/code/game/objects/items/weapons/weldbackpack.dm
@@ -22,12 +22,12 @@
user << "\red That was stupid of you."
explosion(get_turf(src),-1,0,2)
if(src)
- del(src)
+ qdel(src)
return
else
if(T.welding)
user << "\red That was close!"
- src.reagents.trans_to(W, T.max_fuel)
+ src.reagents.trans_to_obj(W, T.max_fuel)
user << "\blue Welder refilled!"
playsound(src.loc, 'sound/effects/refill.ogg', 50, 1, -6)
return
@@ -38,7 +38,7 @@
if(!proximity) // this replaces and improves the get_dist(src,O) <= 1 checks used previously
return
if (istype(O, /obj/structure/reagent_dispensers/fueltank) && src.reagents.total_volume < max_fuel)
- O.reagents.trans_to(src, max_fuel)
+ O.reagents.trans_to_obj(src, max_fuel)
user << "\blue You crack the cap off the top of the pack and fill it back up again from the tank."
playsound(src.loc, 'sound/effects/refill.ogg', 50, 1, -6)
return
diff --git a/code/game/objects/objs.dm b/code/game/objects/objs.dm
index db1ca3f108d..bc119a4b82a 100644
--- a/code/game/objects/objs.dm
+++ b/code/game/objects/objs.dm
@@ -14,15 +14,14 @@
var/damtype = "brute"
var/force = 0
-/obj/Topic(href, href_list, var/nowindow = 0, var/datum/topic_state/custom_state = default_state)
+/obj/Topic(href, href_list, var/nowindow = 0, var/datum/topic_state/state = default_state)
// Calling Topic without a corresponding window open causes runtime errors
if(!nowindow && ..())
return 1
// In the far future no checks are made in an overriding Topic() beyond if(..()) return
// Instead any such checks are made in CanUseTopic()
- var/obj/host = nano_host()
- if(host.CanUseTopic(usr, href_list, custom_state) == STATUS_INTERACTIVE)
+ if(CanUseTopic(usr, state, href_list) == STATUS_INTERACTIVE)
CouldUseTopic(usr)
return 0
@@ -60,9 +59,6 @@
else
return null
-/atom/movable/proc/initialize()
- return
-
/obj/proc/updateUsrDialog()
if(in_use)
var/is_in_use = 0
diff --git a/code/game/objects/random/random.dm b/code/game/objects/random/random.dm
index 7508d34a948..18e0c75e1aa 100644
--- a/code/game/objects/random/random.dm
+++ b/code/game/objects/random/random.dm
@@ -11,7 +11,7 @@
..()
if (!prob(spawn_nothing_percentage))
spawn_item()
- del src
+ qdel(src)
// this function should return a specific item to spawn
@@ -158,7 +158,7 @@
spawn_nothing_percentage = 50
item_to_spawn()
return pick(prob(3);/obj/item/weapon/storage/pill_bottle/tramadol,\
- prob(4);/obj/item/weapon/haircomb/fluff/cado_keppel_1,\
+ prob(4);/obj/item/weapon/haircomb,\
prob(2);/obj/item/weapon/storage/pill_bottle/happy,\
prob(2);/obj/item/weapon/storage/pill_bottle/zoom,\
prob(5);/obj/item/weapon/contraband/poster,\
diff --git a/code/game/objects/structures.dm b/code/game/objects/structures.dm
index 900baea3f35..4b0501a2d11 100644
--- a/code/game/objects/structures.dm
+++ b/code/game/objects/structures.dm
@@ -4,12 +4,12 @@
var/climbable
var/breakable
var/parts
+ var/list/climbers = list()
-/obj/structure/proc/destroy()
+/obj/structure/Destroy()
if(parts)
new parts(loc)
- density = 0
- del(src)
+ ..()
/obj/structure/attack_hand(mob/user)
if(breakable)
@@ -20,14 +20,20 @@
var/mob/living/carbon/human/H = user
if(H.species.can_shred(user))
attack_generic(user,1,"slices")
+
+ if(climbers.len && !(user in climbers))
+ user.visible_message("[user.name] shakes \the [src].", \
+ "You shake \the [src].")
+ structure_shaken()
+
return ..()
/obj/structure/blob_act()
if(prob(50))
- del(src)
+ qdel(src)
/obj/structure/meteorhit(obj/O as obj)
- destroy(src)
+ qdel(src)
/obj/structure/attack_tk()
return
@@ -35,24 +41,24 @@
/obj/structure/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if(prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
return
/obj/structure/meteorhit(obj/O as obj)
- del(src)
+ qdel(src)
/obj/structure/New()
..()
if(climbable)
verbs += /obj/structure/proc/climb_on
-/obj/structure/Del()
+/obj/structure/Destroy()
..()
/obj/structure/proc/climb_on()
@@ -73,7 +79,7 @@
return ..()
/obj/structure/proc/can_climb(var/mob/living/user)
- if (!can_touch(user) || !climbable)
+ if (!can_touch(user) || !climbable || (user in climbers))
return 0
if (!user.Adjacent(src))
@@ -103,25 +109,32 @@
return
usr.visible_message("[user] starts climbing onto \the [src]!")
+ climbers |= user
if(!do_after(user,50))
+ climbers -= user
return
if (!can_climb(user))
+ climbers -= user
return
usr.forceMove(get_turf(src))
if (get_turf(user) == get_turf(src))
usr.visible_message("[user] climbs onto \the [src]!")
+ climbers -= user
/obj/structure/proc/structure_shaken()
+ for(var/mob/living/M in climbers)
+ M.Weaken(1)
+ M << "You topple as you are shaken off \the [src]!"
+ climbers.Cut(1,2)
for(var/mob/living/M in get_turf(src))
-
if(M.lying) return //No spamming this on people.
- M.Weaken(5)
+ M.Weaken(3)
M << "You topple as \the [src] moves under you!"
if(prob(25))
@@ -179,5 +192,5 @@
if(!breakable || !damage || !wallbreaker)
return 0
visible_message("[user] [attack_verb] the [src] apart!")
- spawn(1) destroy()
+ spawn(1) qdel(src)
return 1
diff --git a/code/game/objects/structures/barsign.dm b/code/game/objects/structures/barsign.dm
index 68681f081aa..fd0687dc97d 100644
--- a/code/game/objects/structures/barsign.dm
+++ b/code/game/objects/structures/barsign.dm
@@ -2,8 +2,9 @@
icon = 'icons/obj/barsigns.dmi'
icon_state = "empty"
anchored = 1
+ var/cult = 0
New()
- ChangeSign(pick("pinkflamingo", "magmasea", "limbo", "rustyaxe", "armokbar", "brokendrum", "meadbay", "thedamnwall", "thecavern", "cindikate", "theorchard", "thesaucyclown", "theclownshead", "whiskeyimplant", "carpecarp", "robustroadhouse", "greytide", "theredshirt"))
+ ChangeSign(pick("pinkflamingo", "magmasea", "limbo", "rustyaxe", "armokbar", "brokendrum", "meadbay", "thedamnwall", "thecavern", "cindikate", "theorchard", "thesaucyclown", "theclownshead", "whiskeyimplant", "carpecarp", "robustroadhouse", "greytide", "theredshirt","thebark","theharmbaton","theharmedbaton","thesingulo","thedrukcarp","thedrunkcarp", "scotch","officerbeersky","on"))
return
proc/ChangeSign(var/Text)
src.icon_state = "[Text]"
@@ -12,10 +13,13 @@
return
/obj/structure/sign/double/barsign/attackby(obj/item/I, mob/user)
+ if(cult)
+ return
+
if(istype(I, /obj/item/weapon/card/id))
var/obj/item/weapon/card/id/card = I
if(access_bar in card.GetAccess())
- var/sign_type = input(user, "What would you like to change the barsign to?") as null|anything in list("Off", "Pink Flamingo", "Magma Sea", "Limbo", "Rusty Axe", "Armok Bar", "Broken Drum", "Mead Bay", "The Damn Wall", "The Cavern", "Cindi Kate", "The Orchard", "The Saucy Clown", "The Clowns Head", "Whiskey Implant", "Carpe Carp", "Robust Roadhouse", "Greytide", "The Redshirt")
+ var/sign_type = input(user, "What would you like to change the barsign to?") as null|anything in list("Off", "Pink Flamingo", "Magma Sea", "Limbo", "Rusty Axe", "Armok Bar", "Broken Drum", "Mead Bay", "The Damn Wall", "The Cavern", "Cindi Kate", "The Orchard", "The Saucy Clown", "The Clowns Head", "Whiskey Implant", "Carpe Carp", "Robust Roadhouse", "Greytide", "The Redshirt", "The Bark", "The Harm Baton", "The Harmed Baton", "The Singulo", "The Druk Carp", "The Drunk Carp", "Scotch", "Officer Beersky", "On")
if(sign_type == null)
return
else
diff --git a/code/game/objects/structures/bedsheet_bin.dm b/code/game/objects/structures/bedsheet_bin.dm
index d838d41e5b0..64f1f9925b5 100644
--- a/code/game/objects/structures/bedsheet_bin.dm
+++ b/code/game/objects/structures/bedsheet_bin.dm
@@ -15,8 +15,6 @@ LINEN BINS
throw_speed = 1
throw_range = 2
w_class = 2.0
- item_color = "white"
-
/obj/item/weapon/bedsheet/attack_self(mob/user as mob)
user.drop_item()
@@ -30,67 +28,51 @@ LINEN BINS
/obj/item/weapon/bedsheet/blue
icon_state = "sheetblue"
- item_color = "blue"
/obj/item/weapon/bedsheet/green
icon_state = "sheetgreen"
- item_color = "green"
/obj/item/weapon/bedsheet/orange
icon_state = "sheetorange"
- item_color = "orange"
/obj/item/weapon/bedsheet/purple
icon_state = "sheetpurple"
- item_color = "purple"
/obj/item/weapon/bedsheet/rainbow
icon_state = "sheetrainbow"
- item_color = "rainbow"
/obj/item/weapon/bedsheet/red
icon_state = "sheetred"
- item_color = "red"
/obj/item/weapon/bedsheet/yellow
icon_state = "sheetyellow"
- item_color = "yellow"
/obj/item/weapon/bedsheet/mime
icon_state = "sheetmime"
- item_color = "mime"
/obj/item/weapon/bedsheet/clown
icon_state = "sheetclown"
- item_color = "clown"
/obj/item/weapon/bedsheet/captain
icon_state = "sheetcaptain"
- item_color = "captain"
/obj/item/weapon/bedsheet/rd
icon_state = "sheetrd"
- item_color = "director"
/obj/item/weapon/bedsheet/medical
icon_state = "sheetmedical"
- item_color = "medical"
/obj/item/weapon/bedsheet/hos
icon_state = "sheethos"
- item_color = "hosred"
/obj/item/weapon/bedsheet/hop
icon_state = "sheethop"
- item_color = "hop"
/obj/item/weapon/bedsheet/ce
icon_state = "sheetce"
- item_color = "chief"
/obj/item/weapon/bedsheet/brown
icon_state = "sheetbrown"
- item_color = "brown"
/obj/structure/bedsheetbin
diff --git a/code/game/objects/structures/coathanger.dm b/code/game/objects/structures/coathanger.dm
index ac3e89000cf..decba4bfd36 100644
--- a/code/game/objects/structures/coathanger.dm
+++ b/code/game/objects/structures/coathanger.dm
@@ -4,7 +4,7 @@
icon = 'icons/obj/coatrack.dmi'
icon_state = "coatrack0"
var/obj/item/clothing/suit/coat
- var/list/allowed = list(/obj/item/clothing/suit/storage/labcoat, /obj/item/clothing/suit/storage/toggle/labcoat, /obj/item/clothing/suit/storage/det_suit)
+ var/list/allowed = list(/obj/item/clothing/suit/storage/toggle/labcoat, /obj/item/clothing/suit/storage/det_suit)
/obj/structure/coatrack/attack_hand(mob/user as mob)
user.visible_message("[user] takes [coat] off \the [src].", "You take [coat] off the \the [src]")
@@ -21,8 +21,7 @@
if (can_hang && !coat)
user.visible_message("[user] hangs [W] on \the [src].", "You hang [W] on the \the [src]")
coat = W
- user.drop_item(src)
- coat.loc = src
+ user.drop_from_inventory(coat, src)
update_icon()
else
user << "You cannot hang [W] on [src]"
diff --git a/code/game/objects/structures/crates_lockers/closets.dm b/code/game/objects/structures/crates_lockers/closets.dm
index 40163e7c780..3b27308f05c 100644
--- a/code/game/objects/structures/crates_lockers/closets.dm
+++ b/code/game/objects/structures/crates_lockers/closets.dm
@@ -10,7 +10,7 @@
var/welded = 0
var/wall_mounted = 0 //never solid (You can always pass over it)
var/health = 100
- var/lastbang
+ var/breakout = 0 //if someone is currently breaking out. mutex
var/storage_capacity = 30 //This is so that someone can't pack hundreds of items in a locker/crate
//then open it in a populated area to crash clients.
var/open_sound = 'sound/machines/click.ogg'
@@ -24,9 +24,39 @@
/obj/structure/closet/initialize()
if(!opened) // if closed, any item at the crate's loc is put in the contents
- for(var/obj/item/I in src.loc)
+ var/obj/item/I
+ for(I in src.loc)
if(I.density || I.anchored || I == src) continue
I.loc = src
+ // adjust locker size to hold all items with 5 units of free store room
+ var/content_size = 0
+ for(I in src.contents)
+ content_size += Ceiling(I.w_class/2)
+ if(content_size > storage_capacity-5)
+ storage_capacity = content_size + 5
+
+
+/obj/structure/closet/examine(mob/user)
+ if(get_dist(src, user) > 1)
+ return ..(user)
+
+ if(opened)
+ var/content_size = 0
+ for(var/obj/item/I in src.contents)
+ if(!I.anchored)
+ content_size += Ceiling(I.w_class/2)
+ if(!content_size)
+ user << "It is empty."
+ else if(storage_capacity > content_size*4)
+ user << "It is barely filled."
+ else if(storage_capacity > content_size*2)
+ user << "It is less than half full."
+ else if(storage_capacity > content_size)
+ user << "There is still some free space."
+ else
+ user << "It is full."
+
+
/obj/structure/closet/alter_health()
return get_turf(src)
@@ -146,30 +176,33 @@
for(var/atom/movable/A as mob|obj in src)//pulls everything out of the locker and hits it with an explosion
A.loc = src.loc
A.ex_act(severity++)
- del(src)
+ qdel(src)
if(2)
if(prob(50))
for (var/atom/movable/A as mob|obj in src)
A.loc = src.loc
A.ex_act(severity++)
- del(src)
+ qdel(src)
if(3)
if(prob(5))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
A.ex_act(severity++)
- del(src)
+ qdel(src)
+
+/obj/structure/closet/proc/damage(var/damage)
+ health -= damage
+ if(health <= 0)
+ for(var/atom/movable/A in src)
+ A.loc = src.loc
+ qdel(src)
/obj/structure/closet/bullet_act(var/obj/item/projectile/Proj)
if(!(Proj.damage_type == BRUTE || Proj.damage_type == BURN))
return
- health -= Proj.damage
..()
- if(health <= 0)
- for(var/atom/movable/A as mob|obj in src)
- A.loc = src.loc
- del(src)
+ damage(Proj.damage)
return
@@ -178,14 +211,14 @@
if(prob(75))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
- del(src)
+ qdel(src)
/obj/structure/closet/meteorhit(obj/O as obj)
if(O.icon_state == "flaming")
for(var/mob/M in src)
M.meteorhit(O)
src.dump_contents()
- del(src)
+ qdel(src)
/obj/structure/closet/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(src.opened)
@@ -202,7 +235,7 @@
new /obj/item/stack/sheet/metal(src.loc)
for(var/mob/M in viewers(src))
M.show_message("\The [src] has been cut apart by [user] with \the [WT].", 3, "You hear welding.", 2)
- del(src)
+ qdel(src)
return
if(isrobot(user))
return
@@ -249,18 +282,16 @@
src.add_fingerprint(user)
return
+/obj/structure/closet/attack_ai(mob/user)
+ if(istype(user, /mob/living/silicon/robot) && Adjacent(user)) // Robots can open/close it, but not the AI.
+ attack_hand(user)
+
/obj/structure/closet/relaymove(mob/user as mob)
if(user.stat || !isturf(src.loc))
return
if(!src.open())
user << "It won't budge!"
- if(!lastbang)
- lastbang = 1
- for (var/mob/M in hearers(src, null))
- M << text("BANG, bang!", max(0, 5 - get_dist(src, M)))
- spawn(30)
- lastbang = 0
/obj/structure/closet/attack_hand(mob/user as mob)
src.add_fingerprint(user)
@@ -306,5 +337,66 @@
return
visible_message("[user] [attack_message] the [src]!")
dump_contents()
- spawn(1) del(src)
+ spawn(1) qdel(src)
return 1
+
+/obj/structure/closet/proc/req_breakout()
+ if(breakout)
+ return 0 //Already breaking out.
+ if(opened)
+ return 0 //Door's open... wait, why are you in it's contents then?
+ if(!welded)
+ return 0 //closed but not welded...
+ return 1
+
+/obj/structure/closet/proc/mob_breakout(var/mob/living/escapee)
+ var/breakout_time = 2 //2 minutes by default
+
+ if(!req_breakout())
+ return
+
+ //okay, so the closet is either welded or locked... resist!!!
+ escapee.next_move = world.time + 100
+ escapee.last_special = world.time + 100
+ escapee << "You lean on the back of \the [src] and start pushing the door open. (this will take about [breakout_time] minutes)"
+
+ visible_message("The [src] begins to shake violently!")
+
+ breakout = 1 //can't think of a better way to do this right now.
+ for(var/i in 1 to (6*breakout_time * 2)) //minutes * 6 * 5seconds * 2
+ playsound(src.loc, 'sound/effects/grillehit.ogg', 100, 1)
+ animate_shake()
+
+ if(!do_after(escapee, 50)) //5 seconds
+ breakout = 0
+ return
+ if(!escapee || escapee.stat || escapee.loc != src)
+ breakout = 0
+ return //closet/user destroyed OR user dead/unconcious OR user no longer in closet OR closet opened
+ //Perform the same set of checks as above for weld and lock status to determine if there is even still a point in 'resisting'...
+ if(!req_breakout())
+ breakout = 0
+ return
+
+ //Well then break it!
+ breakout = 0
+ escapee << "You successfully break out!"
+ visible_message("\the [escapee] successfully broke out of \the [src]!")
+ playsound(src.loc, 'sound/effects/grillehit.ogg', 100, 1)
+ break_open()
+ animate_shake()
+
+/obj/structure/closet/proc/break_open()
+ welded = 0
+ update_icon()
+ //Do this to prevent contents from being opened into nullspace (read: bluespace)
+ if(istype(loc, /obj/structure/bigDelivery))
+ var/obj/structure/bigDelivery/BD = loc
+ BD.unwrap()
+ open()
+
+/obj/structure/closet/proc/animate_shake()
+ var/init_px = pixel_x
+ var/shake_dir = pick(-1, 1)
+ animate(src, transform=turn(matrix(), 8*shake_dir), pixel_x=init_px + 2*shake_dir, time=1)
+ animate(transform=null, pixel_x=init_px, time=6, easing=ELASTIC_EASING)
diff --git a/code/game/objects/structures/crates_lockers/closets/fireaxe.dm b/code/game/objects/structures/crates_lockers/closets/fireaxe.dm
index 0728a9befae..8dacfa4c40f 100644
--- a/code/game/objects/structures/crates_lockers/closets/fireaxe.dm
+++ b/code/game/objects/structures/crates_lockers/closets/fireaxe.dm
@@ -61,7 +61,7 @@
user << "\red Unwield the axe first."
return
fireaxe = O
- user.drop_item(O)
+ user.remove_from_mob(O)
src.contents += O
user << "\blue You place the fire axe back in the [src.name]."
update_icon()
diff --git a/code/game/objects/structures/crates_lockers/closets/l3closet.dm b/code/game/objects/structures/crates_lockers/closets/l3closet.dm
index bb5fe26e4fc..294ee437252 100644
--- a/code/game/objects/structures/crates_lockers/closets/l3closet.dm
+++ b/code/game/objects/structures/crates_lockers/closets/l3closet.dm
@@ -18,6 +18,7 @@
/obj/structure/closet/l3closet/general/New()
..()
+ qdel(contents)
contents = list()
new /obj/item/clothing/suit/bio_suit/general( src )
new /obj/item/clothing/head/bio_hood/general( src )
@@ -30,6 +31,7 @@
/obj/structure/closet/l3closet/virology/New()
..()
+ qdel(contents)
contents = list()
new /obj/item/clothing/suit/bio_suit/virology( src )
new /obj/item/clothing/head/bio_hood/virology( src )
@@ -44,6 +46,7 @@
/obj/structure/closet/l3closet/security/New()
..()
+ qdel(contents)
contents = list()
new /obj/item/clothing/suit/bio_suit/security( src )
new /obj/item/clothing/head/bio_hood/security( src )
@@ -56,6 +59,7 @@
/obj/structure/closet/l3closet/janitor/New()
..()
+ qdel(contents)
contents = list()
new /obj/item/clothing/suit/bio_suit/janitor( src )
new /obj/item/clothing/head/bio_hood/janitor( src )
@@ -68,6 +72,7 @@
/obj/structure/closet/l3closet/scientist/New()
..()
+ qdel(contents)
contents = list()
new /obj/item/clothing/suit/bio_suit/scientist( src )
new /obj/item/clothing/head/bio_hood/scientist( src )
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/freezer.dm b/code/game/objects/structures/crates_lockers/closets/secure/freezer.dm
index 0513efd943a..0722b5b0771 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/freezer.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/freezer.dm
@@ -19,7 +19,7 @@
New()
..()
for(var/i = 0, i < 6, i++)
- new /obj/item/weapon/reagent_containers/food/snacks/flour(src)
+ new /obj/item/weapon/reagent_containers/food/condiment/flour(src)
new /obj/item/weapon/reagent_containers/food/condiment/sugar(src)
for(var/i = 0, i < 3, i++)
new /obj/item/weapon/reagent_containers/food/snacks/meat/monkey(src)
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/hydroponics.dm b/code/game/objects/structures/crates_lockers/closets/secure/hydroponics.dm
index 43d440c9f27..019d4873bcc 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/hydroponics.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/hydroponics.dm
@@ -24,5 +24,6 @@
new /obj/item/weapon/minihoe(src)
new /obj/item/weapon/hatchet(src)
new /obj/item/weapon/wirecutters/clippers(src)
+ new /obj/item/weapon/reagent_containers/spray/plantbgone(src)
// new /obj/item/weapon/bee_net(src) //No more bees, March 2014
return
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/medical.dm b/code/game/objects/structures/crates_lockers/closets/secure/medical.dm
index 9eebafacc75..b798016e6e1 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/medical.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/medical.dm
@@ -7,7 +7,7 @@
icon_opened = "medicalopen"
icon_broken = "medicalbroken"
icon_off = "medicaloff"
- req_access = list(access_medical)
+ req_access = list(access_medical_equip)
New()
@@ -52,7 +52,7 @@
/obj/structure/closet/secure_closet/medical3
name = "medical doctor's locker"
- req_access = list(access_medical)
+ req_access = list(access_medical_equip)
icon_state = "securemed1"
icon_closed = "securemed"
icon_locked = "securemed1"
@@ -187,7 +187,7 @@
anchored = 1
density = 0
wall_mounted = 1
- req_access = list(access_medical)
+ req_access = list(access_medical_equip)
/obj/structure/closet/secure_closet/medical_wall/update_icon()
if(broken)
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/personal.dm b/code/game/objects/structures/crates_lockers/closets/secure/personal.dm
index 8fc77c5b92a..2534c09caa0 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/personal.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/personal.dm
@@ -23,7 +23,7 @@
spawn(4)
// Not really the best way to do this, but it's better than "contents = list()"!
for(var/atom/movable/AM in contents)
- del(AM)
+ qdel(AM)
new /obj/item/clothing/under/color/white( src )
new /obj/item/clothing/shoes/white( src )
return
@@ -55,7 +55,7 @@
spawn(4)
// Not really the best way to do this, but it's better than "contents = list()"!
for(var/atom/movable/AM in contents)
- del(AM)
+ qdel(AM)
new /obj/item/weapon/storage/backpack/satchel/withwallet( src )
new /obj/item/device/radio/headset( src )
return
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/secure_closets.dm b/code/game/objects/structures/crates_lockers/closets/secure/secure_closets.dm
index a3b9f399281..df2985c42ea 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/secure_closets.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/secure_closets.dm
@@ -132,3 +132,25 @@
overlays += "welded"
else
icon_state = icon_opened
+
+
+/obj/structure/closet/secure_closet/req_breakout()
+ if(!opened && locked) return 1
+ return ..() //It's a secure closet, but isn't locked.
+
+/obj/structure/closet/secure_closet/break_open()
+ desc += " It appears to be broken."
+ icon_state = icon_off
+ spawn()
+ flick(icon_broken, src)
+ sleep(10)
+ flick(icon_broken, src)
+ sleep(10)
+ broken = 1
+ locked = 0
+ update_icon()
+ //Do this to prevent contents from being opened into nullspace (read: bluespace)
+ if(istype(loc, /obj/structure/bigDelivery))
+ var/obj/structure/bigDelivery/BD = loc
+ BD.unwrap()
+ open()
\ No newline at end of file
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/security.dm b/code/game/objects/structures/crates_lockers/closets/secure/security.dm
index 2480fff6dab..f0c96695dcb 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/security.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/security.dm
@@ -166,7 +166,7 @@
/obj/structure/closet/secure_closet/security
name = "security officer's locker"
- req_access = list(access_security)
+ req_access = list(access_brig)
icon_state = "sec1"
icon_closed = "sec"
icon_locked = "sec1"
@@ -286,8 +286,8 @@
New()
..()
- new /obj/item/weapon/reagent_containers/ld50_syringe/choral(src)
- new /obj/item/weapon/reagent_containers/ld50_syringe/choral(src)
+ new /obj/item/weapon/reagent_containers/syringe/ld50_syringe/choral(src)
+ new /obj/item/weapon/reagent_containers/syringe/ld50_syringe/choral(src)
return
diff --git a/code/game/objects/structures/crates_lockers/closets/statue.dm b/code/game/objects/structures/crates_lockers/closets/statue.dm
new file mode 100644
index 00000000000..67a159e7cac
--- /dev/null
+++ b/code/game/objects/structures/crates_lockers/closets/statue.dm
@@ -0,0 +1,133 @@
+/obj/structure/closet/statue
+ name = "statue"
+ desc = "An incredibly lifelike marble carving"
+ icon = 'icons/obj/statue.dmi'
+ icon_state = "human_male"
+ density = 1
+ anchored = 1
+ health = 0 //destroying the statue kills the mob within
+ var/intialTox = 0 //these are here to keep the mob from taking damage from things that logically wouldn't affect a rock
+ var/intialFire = 0 //it's a little sloppy I know but it was this or the GODMODE flag. Lesser of two evils.
+ var/intialBrute = 0
+ var/intialOxy = 0
+ var/timer = 240 //eventually the person will be freed
+
+/obj/structure/closet/statue/New(loc, var/mob/living/L)
+ if(L && (ishuman(L) || L.isMonkey() || iscorgi(L)))
+ if(L.buckled)
+ L.buckled = 0
+ L.anchored = 0
+ if(L.client)
+ L.client.perspective = EYE_PERSPECTIVE
+ L.client.eye = src
+ L.loc = src
+ L.sdisabilities |= MUTE
+ health = L.health + 100 //stoning damaged mobs will result in easier to shatter statues
+ intialTox = L.getToxLoss()
+ intialFire = L.getFireLoss()
+ intialBrute = L.getBruteLoss()
+ intialOxy = L.getOxyLoss()
+ if(ishuman(L))
+ name = "statue of [L.name]"
+ if(L.gender == "female")
+ icon_state = "human_female"
+ else if(L.isMonkey())
+ name = "statue of a monkey"
+ icon_state = "monkey"
+ else if(iscorgi(L))
+ name = "statue of a corgi"
+ icon_state = "corgi"
+ desc = "If it takes forever, I will wait for you..."
+
+ if(health == 0) //meaning if the statue didn't find a valid target
+ qdel(src)
+ return
+
+ processing_objects.Add(src)
+ ..()
+
+/obj/structure/closet/statue/process()
+ timer--
+ for(var/mob/living/M in src) //Go-go gadget stasis field
+ M.setToxLoss(intialTox)
+ M.adjustFireLoss(intialFire - M.getFireLoss())
+ M.adjustBruteLoss(intialBrute - M.getBruteLoss())
+ M.setOxyLoss(intialOxy)
+ if (timer <= 0)
+ dump_contents()
+ processing_objects.Remove(src)
+ qdel(src)
+
+/obj/structure/closet/statue/dump_contents()
+
+ for(var/obj/O in src)
+ O.loc = src.loc
+
+ for(var/mob/living/M in src)
+ M.loc = src.loc
+ M.sdisabilities &= ~MUTE
+ M.take_overall_damage((M.health - health - 100),0) //any new damage the statue incurred is transfered to the mob
+ if(M.client)
+ M.client.eye = M.client.mob
+ M.client.perspective = MOB_PERSPECTIVE
+
+/obj/structure/closet/statue/open()
+ return
+
+/obj/structure/closet/statue/close()
+ return
+
+/obj/structure/closet/statue/toggle()
+ return
+
+/obj/structure/closet/statue/bullet_act(var/obj/item/projectile/Proj)
+ health -= Proj.damage
+ if(health <= 0)
+ for(var/mob/M in src)
+ shatter(M)
+
+ return
+
+/obj/structure/closet/statue/attack_generic(var/mob/user, damage, attacktext, environment_smash)
+ if(damage && environment_smash)
+ for(var/mob/M in src)
+ shatter(M)
+
+/obj/structure/closet/statue/blob_act()
+ for(var/mob/M in src)
+ shatter(M)
+
+/obj/structure/closet/statue/meteorhit(obj/O as obj)
+ if(O.icon_state == "flaming")
+ for(var/mob/M in src)
+ M.meteorhit(O)
+ shatter(M)
+
+/obj/structure/closet/statue/attackby(obj/item/I as obj, mob/user as mob)
+ health -= I.force
+ visible_message("[user] strikes [src] with [I].")
+ if(health <= 0)
+ for(var/mob/M in src)
+ shatter(M)
+
+/obj/structure/closet/statue/MouseDrop_T()
+ return
+
+/obj/structure/closet/statue/relaymove()
+ return
+
+/obj/structure/closet/statue/attack_hand()
+ return
+
+/obj/structure/closet/statue/verb_toggleopen()
+ return
+
+/obj/structure/closet/statue/update_icon()
+ return
+
+/obj/structure/closet/statue/proc/shatter(mob/user as mob)
+ if (user)
+ user.dust()
+ dump_contents()
+ visible_message("[src] shatters!.")
+ qdel(src)
diff --git a/code/game/objects/structures/crates_lockers/closets/utility_closets.dm b/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
index c274a237b6e..31f8115b910 100644
--- a/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
+++ b/code/game/objects/structures/crates_lockers/closets/utility_closets.dm
@@ -56,12 +56,12 @@
// teehee - Ah, tg coders...
if ("delete")
- del(src)
+ qdel(src)
//If you want to re-add fire, just add "fire" = 15 to the pick list.
/*if ("fire")
new /obj/structure/closet/firecloset(src.loc)
- del(src)*/
+ qdel(src)*/
/obj/structure/closet/emcloset/legacy/New()
..()
diff --git a/code/game/objects/structures/crates_lockers/crates.dm b/code/game/objects/structures/crates_lockers/crates.dm
index 917d244afa1..95e8c06e856 100644
--- a/code/game/objects/structures/crates_lockers/crates.dm
+++ b/code/game/objects/structures/crates_lockers/crates.dm
@@ -105,18 +105,18 @@
switch(severity)
if(1.0)
for(var/obj/O in src.contents)
- del(O)
- del(src)
+ qdel(O)
+ qdel(src)
return
if(2.0)
for(var/obj/O in src.contents)
if(prob(50))
- del(O)
- del(src)
+ qdel(O)
+ qdel(src)
return
if(3.0)
if (prob(50))
- del(src)
+ qdel(src)
return
else
return
diff --git a/code/game/objects/structures/crates_lockers/largecrate.dm b/code/game/objects/structures/crates_lockers/largecrate.dm
index d2b1f56eb38..a0ef6555798 100644
--- a/code/game/objects/structures/crates_lockers/largecrate.dm
+++ b/code/game/objects/structures/crates_lockers/largecrate.dm
@@ -18,49 +18,12 @@
user.visible_message("[user] pries \the [src] open.", \
"You pry open \the [src].", \
"You hear splitting wood.")
- del(src)
+ qdel(src)
else
return attack_hand(user)
/obj/structure/largecrate/mule
- icon_state = "mulecrate"
-
-/obj/structure/largecrate/lisa
- icon_state = "lisacrate"
-
-/obj/structure/largecrate/lisa/attackby(obj/item/weapon/W as obj, mob/user as mob) //ugly but oh well
- if(istype(W, /obj/item/weapon/crowbar))
- new /mob/living/simple_animal/corgi/Lisa(loc)
- ..()
-
-/obj/structure/largecrate/cow
- name = "cow crate"
- icon_state = "lisacrate"
-
-/obj/structure/largecrate/cow/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(istype(W, /obj/item/weapon/crowbar))
- new /mob/living/simple_animal/cow(loc)
- ..()
-
-/obj/structure/largecrate/goat
- name = "goat crate"
- icon_state = "lisacrate"
-
-/obj/structure/largecrate/goat/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(istype(W, /obj/item/weapon/crowbar))
- new /mob/living/simple_animal/hostile/retaliate/goat(loc)
- ..()
-
-/obj/structure/largecrate/chick
- name = "chicken crate"
- icon_state = "lisacrate"
-
-/obj/structure/largecrate/chick/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(istype(W, /obj/item/weapon/crowbar))
- var/num = rand(4, 6)
- for(var/i = 0, i < num, i++)
- new /mob/living/simple_animal/chick(loc)
- ..()
+ name = "MULE crate"
/obj/structure/largecrate/hoverpod
name = "\improper Hoverpod assembly crate"
@@ -71,9 +34,43 @@
if(istype(W, /obj/item/weapon/crowbar))
var/obj/item/mecha_parts/mecha_equipment/ME
var/obj/mecha/working/hoverpod/H = new (loc)
-
+
ME = new /obj/item/mecha_parts/mecha_equipment/tool/hydraulic_clamp
ME.attach(H)
ME = new /obj/item/mecha_parts/mecha_equipment/tool/passenger
ME.attach(H)
..()
+
+/obj/structure/largecrate/animal
+ icon_state = "mulecrate"
+ var/held_count = 1
+ var/held_type
+
+/obj/structure/largecrate/animal/New()
+ ..()
+ for(var/i = 1;i<=held_count;i++)
+ new held_type(src)
+
+/obj/structure/largecrate/animal/corgi
+ name = "corgi carrier"
+ held_type = /mob/living/simple_animal/corgi
+
+/obj/structure/largecrate/animal/cow
+ name = "cow crate"
+ held_type = /mob/living/simple_animal/cow
+
+/obj/structure/largecrate/animal/goat
+ name = "goat crate"
+ held_type = /mob/living/simple_animal/hostile/retaliate/goat
+
+/obj/structure/largecrate/animal/cat
+ name = "cat carrier"
+ held_type = /mob/living/simple_animal/cat
+
+/obj/structure/largecrate/animal/cat/bones
+ held_type = /mob/living/simple_animal/cat/fluff/bones
+
+/obj/structure/largecrate/animal/chick
+ name = "chicken crate"
+ held_count = 5
+ held_type = /mob/living/simple_animal/chick
\ No newline at end of file
diff --git a/code/game/objects/structures/curtains.dm b/code/game/objects/structures/curtains.dm
index 741dc371db6..dc5e309f17f 100644
--- a/code/game/objects/structures/curtains.dm
+++ b/code/game/objects/structures/curtains.dm
@@ -1,20 +1,23 @@
+#define SHOWER_OPEN_LAYER OBJ_LAYER + 0.4
+#define SHOWER_CLOSED_LAYER MOB_LAYER + 0.1
+
/obj/structure/curtain
name = "curtain"
icon = 'icons/obj/curtain.dmi'
icon_state = "closed"
- layer = MOB_LAYER + 0.1
+ layer = SHOWER_OPEN_LAYER
opacity = 1
density = 0
/obj/structure/curtain/open
icon_state = "open"
- layer = OBJ_LAYER
+ layer = SHOWER_CLOSED_LAYER
opacity = 0
/obj/structure/curtain/bullet_act(obj/item/projectile/P, def_zone)
if(!P.nodamage)
visible_message("[P] tears [src] down!")
- del(src)
+ qdel(src)
else
..(P, def_zone)
@@ -27,10 +30,10 @@
opacity = !opacity
if(opacity)
icon_state = "closed"
- layer = MOB_LAYER + 0.1
+ layer = SHOWER_CLOSED_LAYER
else
icon_state = "open"
- layer = OBJ_LAYER
+ layer = SHOWER_OPEN_LAYER
/obj/structure/curtain/black
name = "black curtain"
@@ -45,3 +48,12 @@
name = "shower curtain"
color = "#ACD1E9"
alpha = 200
+
+/obj/structure/curtain/open/shower/engineering
+ color = "#FFA500"
+
+/obj/structure/curtain/open/shower/security
+ color = "#AA0000"
+
+#undef SHOWER_OPEN_LAYER
+#undef SHOWER_CLOSED_LAYER
diff --git a/code/game/objects/structures/displaycase.dm b/code/game/objects/structures/displaycase.dm
index 4eb2236ec0c..5150319f15e 100644
--- a/code/game/objects/structures/displaycase.dm
+++ b/code/game/objects/structures/displaycase.dm
@@ -17,7 +17,7 @@
if (occupied)
new /obj/item/weapon/gun/energy/captain( src.loc )
occupied = 0
- del(src)
+ qdel(src)
if (2)
if (prob(50))
src.health -= 15
@@ -41,13 +41,13 @@
if (occupied)
new /obj/item/weapon/gun/energy/captain( src.loc )
occupied = 0
- del(src)
+ qdel(src)
/obj/structure/displaycase/meteorhit(obj/O as obj)
new /obj/item/weapon/shard( src.loc )
new /obj/item/weapon/gun/energy/captain( src.loc )
- del(src)
+ qdel(src)
/obj/structure/displaycase/proc/healthcheck()
diff --git a/code/game/objects/structures/door_assembly.dm b/code/game/objects/structures/door_assembly.dm
index 1b92926acd2..a15650405ef 100644
--- a/code/game/objects/structures/door_assembly.dm
+++ b/code/game/objects/structures/door_assembly.dm
@@ -166,7 +166,7 @@
if(!src || !WT.isOn()) return
user << "\blue You dissasembled the airlock assembly!"
new /obj/item/stack/sheet/metal(src.loc, 4)
- del (src)
+ qdel (src)
else
user << "\blue You need more welding fuel."
return
@@ -277,7 +277,7 @@
var/obj/machinery/door/new_airlock = new path(src.loc, src)
new_airlock.dir = src.dir
- del(src)
+ qdel(src)
else
..()
update_state()
diff --git a/code/game/objects/structures/electricchair.dm b/code/game/objects/structures/electricchair.dm
index 074d7c76184..2608a311e39 100644
--- a/code/game/objects/structures/electricchair.dm
+++ b/code/game/objects/structures/electricchair.dm
@@ -19,7 +19,7 @@
part.loc = loc
part.master = null
part = null
- del(src)
+ qdel(src)
return
return
diff --git a/code/game/objects/structures/false_walls.dm b/code/game/objects/structures/false_walls.dm
deleted file mode 100644
index f68c7ae7cb9..00000000000
--- a/code/game/objects/structures/false_walls.dm
+++ /dev/null
@@ -1,333 +0,0 @@
-/*
- * False Walls
- */
-/obj/structure/falsewall
- name = "wall"
- desc = "A huge chunk of metal used to seperate rooms."
- anchored = 1
- icon = 'icons/turf/walls.dmi'
- var/mineral = "metal"
- var/opening = 0
-
-/obj/structure/falsewall/New()
- relativewall_neighbours()
- ..()
-
-/obj/structure/falsewall/Del()
-
- var/temploc = src.loc
-
- spawn(10)
- for(var/turf/simulated/wall/W in range(temploc,1))
- W.relativewall()
-
- for(var/obj/structure/falsewall/W in range(temploc,1))
- W.relativewall()
-
- for(var/obj/structure/falserwall/W in range(temploc,1))
- W.relativewall()
- ..()
-
-
-/obj/structure/falsewall/relativewall()
-
- if(!density)
- icon_state = "[mineral]fwall_open"
- return
-
- var/junction = 0 //will be used to determine from which side the wall is connected to other walls
-
- for(var/turf/simulated/wall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)//Only 'like' walls connect -Sieve
- junction |= get_dir(src,W)
- for(var/obj/structure/falsewall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- for(var/obj/structure/falserwall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- icon_state = "[mineral][junction]"
- return
-
-/obj/structure/falsewall/attack_hand(mob/user as mob)
- if(opening)
- return
-
- if(density)
- opening = 1
- icon_state = "[mineral]fwall_open"
- flick("[mineral]fwall_opening", src)
- sleep(15)
- src.density = 0
- SetOpacity(0)
- opening = 0
- else
- opening = 1
- flick("[mineral]fwall_closing", src)
- icon_state = "[mineral]0"
- density = 1
- sleep(15)
- SetOpacity(1)
- src.relativewall()
- opening = 0
-
-/obj/structure/falsewall/update_icon()//Calling icon_update will refresh the smoothwalls if it's closed, otherwise it will make sure the icon is correct if it's open
- ..()
- if(density)
- icon_state = "[mineral]0"
- src.relativewall()
- else
- icon_state = "[mineral]fwall_open"
-
-/obj/structure/falsewall/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(opening)
- user << "\red You must wait until the door has stopped moving."
- return
-
- if(density)
- var/turf/T = get_turf(src)
- if(T.density)
- user << "\red The wall is blocked!"
- return
- if(istype(W, /obj/item/weapon/screwdriver))
- user.visible_message("[user] tightens some bolts on the wall.", "You tighten the bolts on the wall.")
- if(!mineral || mineral == "metal")
- T.ChangeTurf(/turf/simulated/wall)
- else
- T.ChangeTurf(text2path("/turf/simulated/wall/mineral/[mineral]"))
- del(src)
-
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT:welding )
- if(!mineral)
- T.ChangeTurf(/turf/simulated/wall)
- else
- T.ChangeTurf(text2path("/turf/simulated/wall/mineral/[mineral]"))
- if(mineral != "phoron")//Stupid shit keeps me from pushing the attackby() to phoron walls -Sieve
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
- else
- user << "\blue You can't reach, close it first!"
-
- if( istype(W, /obj/item/weapon/pickaxe/plasmacutter) )
- var/turf/T = get_turf(src)
- if(!mineral)
- T.ChangeTurf(/turf/simulated/wall)
- else
- T.ChangeTurf(text2path("/turf/simulated/wall/mineral/[mineral]"))
- if(mineral != "phoron")
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
- //DRILLING
- else if (istype(W, /obj/item/weapon/pickaxe/diamonddrill))
- var/turf/T = get_turf(src)
- if(!mineral)
- T.ChangeTurf(/turf/simulated/wall)
- else
- T.ChangeTurf(text2path("/turf/simulated/wall/mineral/[mineral]"))
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
- else if( istype(W, /obj/item/weapon/melee/energy/blade) )
- var/turf/T = get_turf(src)
- if(!mineral)
- T.ChangeTurf(/turf/simulated/wall)
- else
- T.ChangeTurf(text2path("/turf/simulated/wall/mineral/[mineral]"))
- if(mineral != "phoron")
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
-/obj/structure/falsewall/update_icon()//Calling icon_update will refresh the smoothwalls if it's closed, otherwise it will make sure the icon is correct if it's open
- ..()
- if(density)
- icon_state = "[mineral]0"
- src.relativewall()
- else
- icon_state = "[mineral]fwall_open"
-
-/*
- * False R-Walls
- */
-
-/obj/structure/falserwall
- name = "reinforced wall"
- desc = "A huge chunk of reinforced metal used to seperate rooms."
- icon = 'icons/turf/walls.dmi'
- icon_state = "r_wall"
- density = 1
- opacity = 1
- anchored = 1
- var/mineral = "metal"
- var/opening = 0
-
-/obj/structure/falserwall/New()
- relativewall_neighbours()
- ..()
-
-
-/obj/structure/falserwall/attack_hand(mob/user as mob)
- if(opening)
- return
-
- if(density)
- opening = 1
- // Open wall
- icon_state = "frwall_open"
- flick("frwall_opening", src)
- sleep(15)
- density = 0
- SetOpacity(0)
- opening = 0
- else
- opening = 1
- icon_state = "r_wall"
- flick("frwall_closing", src)
- density = 1
- sleep(15)
- SetOpacity(1)
- relativewall()
- opening = 0
-
-/obj/structure/falserwall/relativewall()
-
- if(!density)
- icon_state = "frwall_open"
- return
-
- var/junction = 0 //will be used to determine from which side the wall is connected to other walls
-
- for(var/turf/simulated/wall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)//Only 'like' walls connect -Sieve
- junction |= get_dir(src,W)
- for(var/obj/structure/falsewall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- for(var/obj/structure/falserwall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- icon_state = "rwall[junction]"
- return
-
-
-
-/obj/structure/falserwall/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(opening)
- user << "\red You must wait until the door has stopped moving."
- return
-
- if(istype(W, /obj/item/weapon/screwdriver))
- var/turf/T = get_turf(src)
- user.visible_message("[user] tightens some bolts on the r wall.", "You tighten the bolts on the wall.")
- T.ChangeTurf(/turf/simulated/wall) //Intentionally makes a regular wall instead of an r-wall (no cheap r-walls for you).
- del(src)
-
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
- var/turf/T = get_turf(src)
- T.ChangeTurf(/turf/simulated/wall)
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
- else if( istype(W, /obj/item/weapon/pickaxe/plasmacutter) )
- var/turf/T = get_turf(src)
- T.ChangeTurf(/turf/simulated/wall)
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
- //DRILLING
- else if (istype(W, /obj/item/weapon/pickaxe/diamonddrill))
- var/turf/T = get_turf(src)
- T.ChangeTurf(/turf/simulated/wall)
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
- else if( istype(W, /obj/item/weapon/melee/energy/blade) )
- var/turf/T = get_turf(src)
- T.ChangeTurf(/turf/simulated/wall)
- T = get_turf(src)
- T.attackby(W,user)
- del(src)
-
-
-/*
- * Uranium Falsewalls
- */
-
-/obj/structure/falsewall/uranium
- name = "uranium wall"
- desc = "A wall with uranium plating. This is probably a bad idea."
- icon_state = ""
- mineral = "uranium"
- var/active = null
- var/last_event = 0
-
-/obj/structure/falsewall/uranium/attackby(obj/item/weapon/W as obj, mob/user as mob)
- radiate()
- ..()
-
-/obj/structure/falsewall/uranium/attack_hand(mob/user as mob)
- radiate()
- ..()
-
-/obj/structure/falsewall/uranium/proc/radiate()
- if(!active)
- if(world.time > last_event+15)
- active = 1
- for(var/mob/living/L in range(3,src))
- L.apply_effect(12,IRRADIATE,0)
- for(var/turf/simulated/wall/mineral/uranium/T in range(3,src))
- T.radiate()
- last_event = world.time
- active = null
- return
- return
-/*
- * Other misc falsewall types
- */
-
-/obj/structure/falsewall/gold
- name = "gold wall"
- desc = "A wall with gold plating. Swag!"
- icon_state = ""
- mineral = "gold"
-
-/obj/structure/falsewall/silver
- name = "silver wall"
- desc = "A wall with silver plating. Shiny."
- icon_state = ""
- mineral = "silver"
-
-/obj/structure/falsewall/diamond
- name = "diamond wall"
- desc = "A wall with diamond plating. You monster."
- icon_state = ""
- mineral = "diamond"
-
-/obj/structure/falsewall/phoron
- name = "phoron wall"
- desc = "A wall with phoron plating. This is definately a bad idea."
- icon_state = ""
- mineral = "phoron"
-
-/obj/structure/falsewall/sandstone
- name = "sandstone wall"
- desc = "A wall with sandstone plating."
- icon_state = ""
- mineral = "sandstone"
diff --git a/code/game/objects/structures/girders.dm b/code/game/objects/structures/girders.dm
index 85415cd1629..e8cb65a33d7 100644
--- a/code/game/objects/structures/girders.dm
+++ b/code/game/objects/structures/girders.dm
@@ -6,6 +6,13 @@
var/state = 0
var/health = 200
var/cover = 50 //how much cover the girder provides against projectiles.
+ var/material/reinf_material
+
+/obj/structure/girder/displaced
+ icon_state = "displaced"
+ anchored = 0
+ health = 50
+ cover = 25
/obj/structure/girder/attack_generic(var/mob/user, var/damage, var/attack_message = "smashes apart", var/wallbreaker)
if(!damage || !wallbreaker)
@@ -30,159 +37,168 @@
health -= damage
..()
if(health <= 0)
- new /obj/item/stack/sheet/metal(get_turf(src))
- del(src)
+ dismantle()
return
+/obj/structure/girder/proc/reset_girder()
+ cover = initial(cover)
+ health = min(health,initial(health))
+ state = 0
+ icon_state = initial(icon_state)
+ if(reinf_material)
+ reinforce_girder()
+
/obj/structure/girder/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench) && state == 0)
- if(anchored && !istype(src,/obj/structure/girder/displaced))
+ if(anchored && !reinf_material)
playsound(src.loc, 'sound/items/Ratchet.ogg', 100, 1)
- user << "\blue Now disassembling the girder"
+ user << "Now disassembling the girder..."
if(do_after(user,40))
if(!src) return
- user << "\blue You dissasembled the girder!"
+ user << "You dissasembled the girder!"
dismantle()
else if(!anchored)
playsound(src.loc, 'sound/items/Ratchet.ogg', 100, 1)
- user << "\blue Now securing the girder"
+ user << "Now securing the girder..."
if(get_turf(user, 40))
- user << "\blue You secured the girder!"
- new/obj/structure/girder( src.loc )
- del(src)
+ user << "You secured the girder!"
+ reset_girder()
else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
- user << "\blue Now slicing apart the girder"
+ user << "Now slicing apart the girder..."
if(do_after(user,30))
if(!src) return
- user << "\blue You slice apart the girder!"
+ user << "You slice apart the girder!"
dismantle()
else if(istype(W, /obj/item/weapon/pickaxe/diamonddrill))
- user << "\blue You drill through the girder!"
+ user << "You drill through the girder!"
dismantle()
- else if(istype(W, /obj/item/weapon/screwdriver) && state == 2 && istype(src,/obj/structure/girder/reinforced))
+ else if(istype(W, /obj/item/weapon/screwdriver) && state == 2)
playsound(src.loc, 'sound/items/Screwdriver.ogg', 100, 1)
- user << "\blue Now unsecuring support struts"
+ user << "Now unsecuring support struts..."
if(do_after(user,40))
if(!src) return
- user << "\blue You unsecured the support struts!"
+ user << "You unsecured the support struts!"
state = 1
- else if(istype(W, /obj/item/weapon/wirecutters) && istype(src,/obj/structure/girder/reinforced) && state == 1)
+ else if(istype(W, /obj/item/weapon/wirecutters) && state == 1)
playsound(src.loc, 'sound/items/Wirecutter.ogg', 100, 1)
- user << "\blue Now removing support struts"
+ user << "Now removing support struts..."
if(do_after(user,40))
if(!src) return
- user << "\blue You removed the support struts!"
- new/obj/structure/girder( src.loc )
- del(src)
+ user << "You removed the support struts!"
+ reinf_material.place_dismantled_product(get_turf(src))
+ reinf_material = null
+ reset_girder()
- else if(istype(W, /obj/item/weapon/crowbar) && state == 0 && anchored )
+ else if(istype(W, /obj/item/weapon/crowbar) && state == 0 && anchored)
playsound(src.loc, 'sound/items/Crowbar.ogg', 100, 1)
- user << "\blue Now dislodging the girder"
+ user << "Now dislodging the girder..."
if(do_after(user, 40))
if(!src) return
- user << "\blue You dislodged the girder!"
- new/obj/structure/girder/displaced( src.loc )
- del(src)
+ user << "You dislodged the girder!"
+ icon_state = "displaced"
+ anchored = 0
+ health = 50
+ cover = 25
else if(istype(W, /obj/item/stack/sheet))
var/obj/item/stack/sheet/S = W
- switch(S.type)
+ if(S.get_amount() < 2)
+ return ..()
- if(/obj/item/stack/sheet/metal, /obj/item/stack/sheet/metal/cyborg)
- if(!anchored)
- if(S.use(2))
- user << "You create a false wall! Push on it to open or close the passage."
- new /obj/structure/falsewall (src.loc)
- del(src)
- else
- if(S.get_amount() < 2) return ..()
- user << "Now adding plating..."
- if (do_after(user,40))
- if (S.use(2))
- user << "You added the plating!"
- var/turf/Tsrc = get_turf(src)
- Tsrc.ChangeTurf(/turf/simulated/wall)
- for(var/turf/simulated/wall/X in Tsrc.loc)
- if(X) X.add_hiddenprint(usr)
- del(src)
- return
-
- if(/obj/item/stack/sheet/plasteel)
- if(!anchored)
- if(S.use(2))
- user << "\blue You create a false wall! Push on it to open or close the passage."
- new /obj/structure/falserwall (src.loc)
- del(src)
- else
- if (src.icon_state == "reinforced") //I cant believe someone would actually write this line of code...
- if(S.get_amount() < 1) return ..()
- user << "Now finalising reinforced wall."
- if(do_after(user, 50))
- if (S.use(1))
- user << "Wall fully reinforced!"
- var/turf/Tsrc = get_turf(src)
- Tsrc.ChangeTurf(/turf/simulated/wall/r_wall)
- for(var/turf/simulated/wall/r_wall/X in Tsrc.loc)
- if(X) X.add_hiddenprint(usr)
- del(src)
- return
- else
- if(S.get_amount() < 1) return ..()
- user << "Now reinforcing girders..."
- if (do_after(user,60))
- if(S.use(1))
- user << "Girders reinforced!"
- new/obj/structure/girder/reinforced( src.loc )
- del(src)
- return
-
- if(S.sheettype)
- var/M = S.sheettype
- // Ugly hack, will suffice for now. Need to fix it upstream as well, may rewrite mineral walls. ~Z
- if(M in list("mhydrogen","osmium","tritium","platinum","iron"))
- user << "You cannot plate the girder in that material."
- return
- if(!anchored)
- if(S.amount < 2) return
- S.use(2)
- user << "\blue You create a false wall! Push on it to open or close the passage."
- var/F = text2path("/obj/structure/falsewall/[M]")
- new F (src.loc)
- del(src)
- else
- if(S.amount < 2) return ..()
- user << "\blue Now adding plating..."
- if (do_after(user,40))
- if(!src || !S || S.amount < 2) return
- S.use(2)
- user << "\blue You added the plating!"
- var/turf/Tsrc = get_turf(src)
- Tsrc.ChangeTurf(text2path("/turf/simulated/wall/mineral/[M]"))
- for(var/turf/simulated/wall/mineral/X in Tsrc.loc)
- if(X) X.add_hiddenprint(usr)
- del(src)
- return
+ var/material/M = name_to_material[S.sheettype]
+ if(!istype(M))
+ return ..()
+ var/wall_fake
add_hiddenprint(usr)
+ if(M.integrity < 50)
+ user << "This material is too soft for use in wall construction."
+ return
+
+ user << "You begin adding the plating..."
+
+ if(!do_after(user,40) || !S.use(2))
+ return
+
+ if(anchored)
+ user << "You added the plating!"
+ else
+ user << "You create a false wall! Push on it to open or close the passage."
+ wall_fake = 1
+
+ var/turf/Tsrc = get_turf(src)
+ Tsrc.ChangeTurf(/turf/simulated/wall)
+ var/turf/simulated/wall/T = get_turf(src)
+ T.set_material(M, reinf_material)
+ if(wall_fake)
+ T.can_open = 1
+ T.add_hiddenprint(usr)
+ qdel(src)
+ return
+
else if(istype(W, /obj/item/pipe))
var/obj/item/pipe/P = W
if (P.pipe_type in list(0, 1, 5)) //simple pipes, simple bends, and simple manifolds.
user.drop_item()
P.loc = src.loc
- user << "\blue You fit the pipe into the [src]!"
+ user << "You fit the pipe into the [src]!"
else
..()
+/obj/structure/girder/proc/reinforce_girder()
+ cover = reinf_material.hardness
+ health = 500
+ state = 2
+ icon_state = "reinforced"
+
+/obj/structure/girder/verb/reinforce_with_material()
+ set name = "Reinforce girder"
+ set desc = "Reinforce a girder with metal."
+ set src in view(1)
+
+ var/mob/living/user = usr
+ if(!istype(user) || !(user.l_hand || user.r_hand))
+ return
+
+ if(reinf_material)
+ user << "\The [src] is already reinforced."
+ return
+
+ var/obj/item/stack/sheet/S = user.l_hand
+ if(!istype(S))
+ S = user.r_hand
+ if(!istype(S))
+ user << "You cannot plate \the [src] with that."
+ return
+
+ if(S.get_amount() < 2)
+ user << "There is not enough material here to reinforce the girder."
+ return
+
+ var/material/M = name_to_material[S.sheettype]
+ if(!istype(M) || M.integrity < 50)
+ user << "You cannot reinforce \the [src] with that; it is too soft."
+ return
+
+ user << "Now reinforcing..."
+ if (!do_after(user,40) || !S.use(2))
+ return
+ user << "You added reinforcement!"
+
+ reinf_material = M
+ reinforce_girder()
+
+
/obj/structure/girder/proc/dismantle()
new /obj/item/stack/sheet/metal(get_turf(src))
- del(src)
+ qdel(src)
/obj/structure/girder/attack_hand(mob/user as mob)
if (HULK in user.mutations)
@@ -193,111 +209,50 @@
/obj/structure/girder/blob_act()
if(prob(40))
- del(src)
+ qdel(src)
/obj/structure/girder/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(30))
- var/remains = pick(/obj/item/stack/rods,/obj/item/stack/sheet/metal)
- new remains(loc)
- del(src)
+ dismantle()
return
if(3.0)
if (prob(5))
- var/remains = pick(/obj/item/stack/rods,/obj/item/stack/sheet/metal)
- new remains(loc)
- del(src)
+ dismantle()
return
else
return
-/obj/structure/girder/displaced
- icon_state = "displaced"
- anchored = 0
- health = 50
- cover = 25
-
-/obj/structure/girder/reinforced
- icon_state = "reinforced"
- state = 2
- health = 500
- cover = 80
-
-/obj/structure/cultgirder
+/obj/structure/girder/cult
icon= 'icons/obj/cult.dmi'
icon_state= "cultgirder"
- anchored = 1
- density = 1
- layer = 2
- var/health = 250
- var/cover = 70
+ health = 250
+ cover = 70
-/obj/structure/cultgirder/attack_generic(var/mob/user, var/damage, var/attack_message = "smashes apart", var/wallbreaker)
- if(!damage || !wallbreaker)
- return 0
- visible_message("[user] [attack_message] the [src]!")
- dismantle()
- return 1
-
-/obj/structure/cultgirder/proc/dismantle()
+/obj/structure/girder/cult/dismantle()
new /obj/effect/decal/remains/human(get_turf(src))
- del(src)
+ qdel(src)
-/obj/structure/cultgirder/attackby(obj/item/W as obj, mob/user as mob)
+/obj/structure/girder/cult/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 100, 1)
- user << "\blue Now disassembling the girder"
+ user << "Now disassembling the girder..."
if(do_after(user,40))
- user << "\blue You dissasembled the girder!"
+ user << "You dissasembled the girder!"
dismantle()
else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
- user << "\blue Now slicing apart the girder"
+ user << "Now slicing apart the girder..."
if(do_after(user,30))
- user << "\blue You slice apart the girder!"
+ user << "You slice apart the girder!"
dismantle()
else if(istype(W, /obj/item/weapon/pickaxe/diamonddrill))
- user << "\blue You drill through the girder!"
+ user << "You drill through the girder!"
new /obj/effect/decal/remains/human(get_turf(src))
dismantle()
-
-/obj/structure/cultgirder/blob_act()
- if(prob(40))
- dismantle()
-
-/obj/structure/cultgirder/bullet_act(var/obj/item/projectile/Proj) //No beam check- How else will you destroy the cult girder with silver bullets?????
- //Girders only provide partial cover. There's a chance that the projectiles will just pass through. (unless you are trying to shoot the girder)
- if(Proj.original != src && !prob(cover))
- return -1 //pass through
-
- //Tasers and the like should not damage cultgirders.
- if(!(Proj.damage_type == BRUTE || Proj.damage_type == BURN))
- return
-
- health -= Proj.damage
- ..()
- if(health <= 0)
- dismantle()
- return
-
-/obj/structure/cultgirder/ex_act(severity)
- switch(severity)
- if(1.0)
- del(src)
- return
- if(2.0)
- if (prob(30))
- dismantle()
- return
- if(3.0)
- if (prob(5))
- dismantle()
- return
- else
- return
diff --git a/code/game/objects/structures/grille.dm b/code/game/objects/structures/grille.dm
index b6407fd3767..b18658d4a6c 100644
--- a/code/game/objects/structures/grille.dm
+++ b/code/game/objects/structures/grille.dm
@@ -8,20 +8,25 @@
flags = CONDUCT
pressure_resistance = 5*ONE_ATMOSPHERE
layer = 2.9
- explosion_resistance = 5
+ explosion_resistance = 1
var/health = 10
var/destroyed = 0
/obj/structure/grille/ex_act(severity)
- del(src)
+ qdel(src)
/obj/structure/grille/blob_act()
- del(src)
+ qdel(src)
/obj/structure/grille/meteorhit(var/obj/M)
- del(src)
+ qdel(src)
+/obj/structure/grille/update_icon()
+ if(destroyed)
+ icon_state = "[initial(icon_state)]-b"
+ else
+ icon_state = initial(icon_state)
/obj/structure/grille/Bumped(atom/user)
if(ismob(user)) shock(user, 70)
@@ -98,8 +103,8 @@
if(iswirecutter(W))
if(!shock(user, 100))
playsound(loc, 'sound/items/Wirecutter.ogg', 100, 1)
- new /obj/item/stack/rods(loc, 2)
- del(src)
+ PoolOrNew(/obj/item/stack/rods, list(get_turf(src), destroyed ? 1 : 2))
+ qdel(src)
else if((isscrewdriver(W)) && (istype(loc, /turf/simulated) || anchored))
if(!shock(user, 90))
playsound(loc, 'sound/items/Screwdriver.ogg', 100, 1)
@@ -165,15 +170,15 @@
/obj/structure/grille/proc/healthcheck()
if(health <= 0)
if(!destroyed)
- icon_state = "brokengrille"
density = 0
destroyed = 1
- new /obj/item/stack/rods(loc)
+ update_icon()
+ PoolOrNew(/obj/item/stack/rods, get_turf(src))
else
if(health <= -6)
- new /obj/item/stack/rods(loc)
- del(src)
+ PoolOrNew(/obj/item/stack/rods, get_turf(src))
+ qdel(src)
return
return
@@ -215,3 +220,24 @@
health -= damage
spawn(1) healthcheck()
return 1
+
+// Used in mapping to avoid
+/obj/structure/grille/broken
+ destroyed = 1
+ icon_state = "grille-b"
+ density = 0
+ New()
+ ..()
+ health = rand(-5, -1) //In the destroyed but not utterly threshold.
+ healthcheck() //Send this to healthcheck just in case we want to do something else with it.
+
+/obj/structure/grille/cult
+ name = "cult grille"
+ desc = "A matrice built out of an unknown material, with some sort of force field blocking air around it"
+ icon_state = "grillecult"
+ health = 40 //Make it strong enough to avoid people breaking in too easily
+
+/obj/structure/grille/cult/CanPass(atom/movable/mover, turf/target, height = 1.5, air_group = 0)
+ if(air_group)
+ return 0 //Make sure air doesn't drain
+ ..()
diff --git a/code/game/objects/structures/inflatable.dm b/code/game/objects/structures/inflatable.dm
index 4bbb01a9c54..0aae020ba1f 100644
--- a/code/game/objects/structures/inflatable.dm
+++ b/code/game/objects/structures/inflatable.dm
@@ -11,7 +11,7 @@
var/obj/structure/inflatable/R = new /obj/structure/inflatable(user.loc)
src.transfer_fingerprints_to(R)
R.add_fingerprint(user)
- del(src)
+ qdel(src)
/obj/structure/inflatable
name = "inflatable wall"
@@ -30,7 +30,7 @@
..()
update_nearby_tiles(need_rebuild=1)
-/obj/structure/inflatable/Del()
+/obj/structure/inflatable/Destroy()
update_nearby_tiles()
..()
@@ -50,7 +50,7 @@
/obj/structure/inflatable/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
deflate(1)
@@ -94,14 +94,14 @@
visible_message("[src] rapidly deflates!")
var/obj/item/inflatable/torn/R = new /obj/item/inflatable/torn(loc)
src.transfer_fingerprints_to(R)
- del(src)
+ qdel(src)
else
//user << "\blue You slowly deflate the inflatable wall."
visible_message("[src] slowly deflates.")
spawn(50)
var/obj/item/inflatable/R = new /obj/item/inflatable(loc)
src.transfer_fingerprints_to(R)
- del(src)
+ qdel(src)
/obj/structure/inflatable/verb/hand_deflate()
set name = "Deflate"
@@ -111,6 +111,7 @@
if(isobserver(usr)) //to stop ghosts from deflating
return
+ verbs -= /obj/structure/inflatable/verb/hand_deflate
deflate()
/obj/structure/inflatable/attack_generic(var/mob/user, var/damage, var/attack_verb)
@@ -134,7 +135,7 @@
var/obj/structure/inflatable/door/R = new /obj/structure/inflatable/door(user.loc)
src.transfer_fingerprints_to(R)
R.add_fingerprint(user)
- del(src)
+ qdel(src)
/obj/structure/inflatable/door //Based on mineral door code
name = "inflatable door"
@@ -219,13 +220,13 @@
visible_message("[src] rapidly deflates!")
var/obj/item/inflatable/door/torn/R = new /obj/item/inflatable/door/torn(loc)
src.transfer_fingerprints_to(R)
- del(src)
+ qdel(src)
else
visible_message("[src] slowly deflates.")
spawn(50)
var/obj/item/inflatable/door/R = new /obj/item/inflatable/door(loc)
src.transfer_fingerprints_to(R)
- del(src)
+ qdel(src)
/obj/item/inflatable/torn
name = "torn inflatable wall"
diff --git a/code/game/objects/structures/janicart.dm b/code/game/objects/structures/janicart.dm
index bd253da195b..237250e3fdd 100644
--- a/code/game/objects/structures/janicart.dm
+++ b/code/game/objects/structures/janicart.dm
@@ -39,7 +39,7 @@
if(reagents.total_volume < 1)
user << "[src] is out of water!"
else
- reagents.trans_to(I, 5) //
+ reagents.trans_to_obj(I, 5) //
user << "You wet [I] in [src]."
playsound(loc, 'sound/effects/slosh.ogg', 25, 1)
return
@@ -186,7 +186,7 @@
/obj/structure/bed/chair/janicart/attackby(obj/item/I, mob/user)
if(istype(I, /obj/item/weapon/mop))
if(reagents.total_volume > 1)
- reagents.trans_to(I, 2)
+ reagents.trans_to_obj(I, 2)
user << "You wet [I] in the [callme]."
playsound(loc, 'sound/effects/slosh.ogg', 25, 1)
else
diff --git a/code/game/objects/structures/kitchen_spike.dm b/code/game/objects/structures/kitchen_spike.dm
index de2fef2875e..e865805991b 100644
--- a/code/game/objects/structures/kitchen_spike.dm
+++ b/code/game/objects/structures/kitchen_spike.dm
@@ -20,8 +20,8 @@
else
if(spike(G.affecting))
visible_message("[user] has forced [G.affecting] onto the spike, killing them instantly!")
- del(G.affecting)
- del(G)
+ qdel(G.affecting)
+ qdel(G)
else
user << "They are too big for the spike, try something smaller!"
diff --git a/code/game/objects/structures/lamarr_cage.dm b/code/game/objects/structures/lamarr_cage.dm
index 6bbb8cfa245..3c32052d726 100644
--- a/code/game/objects/structures/lamarr_cage.dm
+++ b/code/game/objects/structures/lamarr_cage.dm
@@ -15,7 +15,7 @@
if (1)
new /obj/item/weapon/shard( src.loc )
Break()
- del(src)
+ qdel(src)
if (2)
if (prob(50))
src.health -= 15
@@ -37,13 +37,13 @@
if (prob(75))
new /obj/item/weapon/shard( src.loc )
Break()
- del(src)
+ qdel(src)
/obj/structure/lamarr/meteorhit(obj/O as obj)
new /obj/item/weapon/shard( src.loc )
Break()
- del(src)
+ qdel(src)
/obj/structure/lamarr/proc/healthcheck()
diff --git a/code/game/objects/structures/lattice.dm b/code/game/objects/structures/lattice.dm
index a32af450d5e..078f4bc06bc 100644
--- a/code/game/objects/structures/lattice.dm
+++ b/code/game/objects/structures/lattice.dm
@@ -13,10 +13,10 @@
///// Z-Level Stuff
if(!(istype(src.loc, /turf/space) || istype(src.loc, /turf/simulated/floor/open)))
///// Z-Level Stuff
- del(src)
+ qdel(src)
for(var/obj/structure/lattice/LAT in src.loc)
if(LAT != src)
- del(LAT)
+ qdel(LAT)
icon = 'icons/obj/smoothlattice.dmi'
icon_state = "latticeblank"
updateOverlays()
@@ -26,7 +26,7 @@
L = locate(/obj/structure/lattice, get_step(src, dir))
L.updateOverlays()
-/obj/structure/lattice/Del()
+/obj/structure/lattice/Destroy()
for (var/dir in cardinal)
var/obj/structure/lattice/L
if(locate(/obj/structure/lattice, get_step(src, dir)))
@@ -35,16 +35,16 @@
..()
/obj/structure/lattice/blob_act()
- del(src)
+ qdel(src)
return
/obj/structure/lattice/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
- del(src)
+ qdel(src)
return
if(3.0)
return
@@ -61,14 +61,14 @@
var/obj/item/weapon/weldingtool/WT = C
if(WT.remove_fuel(0, user))
user << "\blue Slicing lattice joints ..."
- new /obj/item/stack/rods(src.loc)
- del(src)
+ PoolOrNew(/obj/item/stack/rods, src.loc)
+ qdel(src)
return
/obj/structure/lattice/proc/updateOverlays()
//if(!(istype(src.loc, /turf/space)))
- // del(src)
+ // qdel(src)
spawn(1)
overlays = list()
diff --git a/code/game/objects/structures/mineral_doors.dm b/code/game/objects/structures/mineral_doors.dm
index 8ce25ddb671..695b11db959 100644
--- a/code/game/objects/structures/mineral_doors.dm
+++ b/code/game/objects/structures/mineral_doors.dm
@@ -10,7 +10,7 @@
icon = 'icons/obj/doors/mineral_doors.dmi'
icon_state = "metal"
- var/mineralType = "metal"
+ var/mineralType = DEFAULT_WALL_MATERIAL
var/state = 0 //closed, 1 == open
var/isSwitchingStates = 0
var/hardness = 1
@@ -22,7 +22,7 @@
name = "[mineralType] door"
update_nearby_tiles(need_rebuild=1)
- Del()
+ Destroy()
update_nearby_tiles()
..()
@@ -119,25 +119,11 @@
Dismantle(1)
proc/Dismantle(devastated = 0)
- if(!devastated)
- if (mineralType == "metal")
- var/ore = /obj/item/stack/sheet/metal
- for(var/i = 1, i <= oreAmount, i++)
- new ore(get_turf(src))
- else
- var/ore = text2path("/obj/item/stack/sheet/mineral/[mineralType]")
- for(var/i = 1, i <= oreAmount, i++)
- new ore(get_turf(src))
- else
- if (mineralType == "metal")
- var/ore = /obj/item/stack/sheet/metal
- for(var/i = 3, i <= oreAmount, i++)
- new ore(get_turf(src))
- else
- var/ore = text2path("/obj/item/stack/sheet/mineral/[mineralType]")
- for(var/i = 3, i <= oreAmount, i++)
- new ore(get_turf(src))
- del(src)
+ var/material/M = name_to_material[mineralType]
+ if(istype(M))
+ for(var/i = (devastated? 1 : 3), i <= oreAmount, i++)
+ new M.stack_type(get_turf(src))
+ qdel(src)
ex_act(severity = 1)
switch(severity)
@@ -155,7 +141,7 @@
return
/obj/structure/mineral_door/iron
- mineralType = "metal"
+ mineralType = "iron"
hardness = 3
/obj/structure/mineral_door/silver
@@ -168,7 +154,7 @@
/obj/structure/mineral_door/uranium
mineralType = "uranium"
hardness = 3
- luminosity = 2
+ light_range = 2
/obj/structure/mineral_door/sandstone
mineralType = "sandstone"
@@ -239,7 +225,7 @@
if(!devastated)
for(var/i = 1, i <= oreAmount, i++)
new/obj/item/stack/sheet/wood(get_turf(src))
- del(src)
+ qdel(src)
/obj/structure/mineral_door/resin
mineralType = "resin"
@@ -279,7 +265,7 @@
isSwitchingStates = 0
Dismantle(devastated = 0)
- del(src)
+ qdel(src)
CheckHardness()
playsound(loc, 'sound/effects/attackblob.ogg', 100, 1)
diff --git a/code/game/objects/structures/mirror.dm b/code/game/objects/structures/mirror.dm
index 83f295f9ef7..4868f6e0ca5 100644
--- a/code/game/objects/structures/mirror.dm
+++ b/code/game/objects/structures/mirror.dm
@@ -80,16 +80,16 @@
var/mob/living/carbon/human/vox/vox = new(get_turf(src),"Vox")
vox.gender = user.gender
raiders.equip(vox)
+ new /obj/item/organ/stack/vox(vox)
if(user.mind)
user.mind.transfer_to(vox)
spawn(1)
- var/newname = input(vox,"Enter a name, or leave blank for the default name.", "Name change","") as text
- newname = sanitize(newname)
+ var/newname = sanitizeSafe(input(vox,"Enter a name, or leave blank for the default name.", "Name change","") as text, MAX_NAME_LEN)
if(!newname || newname == "")
var/datum/language/L = all_languages[vox.species.default_language]
newname = L.get_random_name()
vox.real_name = newname
vox.name = vox.real_name
raiders.update_access(vox)
- del(user)
+ qdel(user)
..()
diff --git a/code/game/objects/structures/mop_bucket.dm b/code/game/objects/structures/mop_bucket.dm
index ec568b84083..ace1293fc7d 100644
--- a/code/game/objects/structures/mop_bucket.dm
+++ b/code/game/objects/structures/mop_bucket.dm
@@ -22,6 +22,6 @@
if(reagents.total_volume < 1)
user << "[src] is out of water!"
else
- reagents.trans_to(I, 5)
+ reagents.trans_to_obj(I, 5)
user << "You wet [I] in [src]."
playsound(loc, 'sound/effects/slosh.ogg', 25, 1)
diff --git a/code/game/objects/structures/morgue.dm b/code/game/objects/structures/morgue.dm
index 1f597b0c96d..599e8aabc8e 100644
--- a/code/game/objects/structures/morgue.dm
+++ b/code/game/objects/structures/morgue.dm
@@ -36,21 +36,21 @@
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(5))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
return
@@ -64,7 +64,7 @@
A.loc = src
playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
else
playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
src.connected = new /obj/structure/m_tray( src.loc )
@@ -80,7 +80,7 @@
src.connected.set_dir(src.dir)
else
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
src.add_fingerprint(user)
update()
return
@@ -92,7 +92,7 @@
return
if ((!in_range(src, usr) && src.loc != user))
return
- t = sanitize(t)
+ t = sanitizeSafe(t, MAX_NAME_LEN)
if (t)
src.name = text("Morgue- '[]'", t)
else
@@ -116,7 +116,7 @@
src.connected.icon_state = "morguet"
else
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
return
@@ -144,7 +144,7 @@
src.connected.update()
add_fingerprint(user)
//SN src = null
- del(src)
+ qdel(src)
return
return
@@ -195,21 +195,21 @@
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(5))
for(var/atom/movable/A as mob|obj in src)
A.loc = src.loc
ex_act(severity)
- del(src)
+ qdel(src)
return
return
@@ -232,7 +232,7 @@
A.loc = src
playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
else if (src.locked == 0)
playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
src.connected = new /obj/structure/c_tray( src.loc )
@@ -247,7 +247,7 @@
src.connected.icon_state = "cremat"
else
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
src.add_fingerprint(user)
update()
@@ -258,7 +258,7 @@
return
if ((!in_range(src, usr) > 1 && src.loc != user))
return
- t = sanitize(t)
+ t = sanitizeSafe(t, MAX_NAME_LEN)
if (t)
src.name = text("Crematorium- '[]'", t)
else
@@ -282,7 +282,7 @@
src.connected.icon_state = "cremat"
else
//src.connected = null
- del(src.connected)
+ qdel(src.connected)
return
/obj/structure/crematorium/proc/cremate(atom/A, mob/user as mob)
@@ -323,10 +323,10 @@
//log_attack("\[[time_stamp()]\] [user]/[user.ckey] cremated [M]/[M.ckey]")
M.death(1)
M.ghostize()
- del(M)
+ qdel(M)
for(var/obj/O in contents) //obj instead of obj/item so that bodybags and ashes get destroyed. We dont want tons and tons of ash piling up
- del(O)
+ qdel(O)
new /obj/effect/decal/cleanable/ash(src)
sleep(30)
@@ -360,7 +360,7 @@
src.connected.update()
add_fingerprint(user)
//SN src = null
- del(src)
+ qdel(src)
return
return
diff --git a/code/game/objects/structures/signs.dm b/code/game/objects/structures/signs.dm
index 0b11d09fccc..f5c988ae972 100644
--- a/code/game/objects/structures/signs.dm
+++ b/code/game/objects/structures/signs.dm
@@ -8,19 +8,19 @@
/obj/structure/sign/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
- del(src)
+ qdel(src)
return
if(3.0)
- del(src)
+ qdel(src)
return
else
return
/obj/structure/sign/blob_act()
- del(src)
+ qdel(src)
return
/obj/structure/sign/attackby(obj/item/tool as obj, mob/user as mob) //deconstruction
@@ -33,7 +33,7 @@
//var/icon/I = icon('icons/obj/decals.dmi', icon_state)
//S.icon = I.Scale(24, 24)
S.sign_state = icon_state
- del(src)
+ qdel(src)
else ..()
/obj/item/sign
@@ -62,7 +62,7 @@
S.desc = desc
S.icon_state = sign_state
user << "You fasten \the [S] with your [tool]."
- del(src)
+ qdel(src)
else ..()
/obj/structure/sign/double/map
diff --git a/code/game/objects/structures/stool_bed_chair_nest/alien_nests.dm b/code/game/objects/structures/stool_bed_chair_nest/alien_nests.dm
index fad0c3d0bd2..46cf8ffcd8d 100644
--- a/code/game/objects/structures/stool_bed_chair_nest/alien_nests.dm
+++ b/code/game/objects/structures/stool_bed_chair_nest/alien_nests.dm
@@ -79,5 +79,5 @@
/obj/structure/bed/nest/proc/healthcheck()
if(health <=0)
density = 0
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/structures/stool_bed_chair_nest/bed.dm b/code/game/objects/structures/stool_bed_chair_nest/bed.dm
index 6d50066a748..586a11d181b 100644
--- a/code/game/objects/structures/stool_bed_chair_nest/bed.dm
+++ b/code/game/objects/structures/stool_bed_chair_nest/bed.dm
@@ -20,27 +20,36 @@
/obj/structure/bed/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
/obj/structure/bed/blob_act()
if(prob(75))
new /obj/item/stack/sheet/metal(src.loc)
- del(src)
+ qdel(src)
/obj/structure/bed/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
new /obj/item/stack/sheet/metal(src.loc)
- del(src)
+ qdel(src)
+ else if(istype(W, /obj/item/weapon/grab))
+ user.visible_message("[user] attempts to buckle [W:affecting] into \the [src]!")
+ if(do_after(user, 20))
+ W:affecting.loc = loc
+ if(buckle_mob(W:affecting))
+ W:affecting.visible_message(\
+ "[W:affecting.name] is buckled to [src] by [user.name]!",\
+ "You are buckled to [src] by [user.name]!",\
+ "You hear metal clanking.")
else
..()
@@ -71,7 +80,7 @@
visible_message("[user] collapses \the [src.name].")
new/obj/item/roller(get_turf(src))
spawn(0)
- del(src)
+ qdel(src)
return
..()
@@ -85,7 +94,7 @@
/obj/item/roller/attack_self(mob/user)
var/obj/structure/bed/roller/R = new /obj/structure/bed/roller(user.loc)
R.add_fingerprint(user)
- del(src)
+ qdel(src)
/obj/item/roller/attackby(obj/item/weapon/W as obj, mob/user as mob)
@@ -119,7 +128,7 @@
user << "\blue You deploy the roller bed."
var/obj/structure/bed/roller/R = new /obj/structure/bed/roller(user.loc)
R.add_fingerprint(user)
- del(held)
+ qdel(held)
held = null
@@ -153,5 +162,5 @@
visible_message("[usr] collapses \the [src.name].")
new/obj/item/roller(get_turf(src))
spawn(0)
- del(src)
+ qdel(src)
return
diff --git a/code/game/objects/structures/stool_bed_chair_nest/chairs.dm b/code/game/objects/structures/stool_bed_chair_nest/chairs.dm
index 5c4728313b7..b811294a074 100644
--- a/code/game/objects/structures/stool_bed_chair_nest/chairs.dm
+++ b/code/game/objects/structures/stool_bed_chair_nest/chairs.dm
@@ -26,7 +26,7 @@
E.part = SK
SK.loc = E
SK.master = E
- del(src)
+ qdel(src)
/obj/structure/bed/chair/attack_tk(mob/user as mob)
if(buckled_mob)
@@ -67,21 +67,19 @@
return
// Chair types
-/obj/structure/bed/chair/wood/normal
+/obj/structure/bed/chair/wood
icon_state = "wooden_chair"
name = "wooden chair"
desc = "Old is never too old to not be in fashion."
/obj/structure/bed/chair/wood/wings
icon_state = "wooden_chair_wings"
- name = "wooden chair"
- desc = "Old is never too old to not be in fashion."
/obj/structure/bed/chair/wood/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
new /obj/item/stack/sheet/wood(src.loc)
- del(src)
+ qdel(src)
else
..()
diff --git a/code/game/objects/structures/stool_bed_chair_nest/stools.dm b/code/game/objects/structures/stool_bed_chair_nest/stools.dm
index 16e9161dcfc..8de3bcf0a57 100644
--- a/code/game/objects/structures/stool_bed_chair_nest/stools.dm
+++ b/code/game/objects/structures/stool_bed_chair_nest/stools.dm
@@ -13,7 +13,7 @@
user.remove_from_mob(src)
var/obj/item/stack/sheet/metal/m = new/obj/item/stack/sheet/metal
m.loc = get_turf(src)
- del src
+ qdel(src)
var/mob/living/T = M
T.Weaken(10)
T.apply_damage(20)
@@ -23,25 +23,25 @@
/obj/item/weapon/stool/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
if (prob(50))
- del(src)
+ qdel(src)
return
if(3.0)
if (prob(5))
- del(src)
+ qdel(src)
return
/obj/item/weapon/stool/blob_act()
if(prob(75))
new /obj/item/stack/sheet/metal(src.loc)
- del(src)
+ qdel(src)
/obj/item/weapon/stool/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
new /obj/item/stack/sheet/metal(src.loc)
- del(src)
+ qdel(src)
..()
diff --git a/code/game/objects/structures/tables_racks.dm b/code/game/objects/structures/tables_racks.dm
deleted file mode 100644
index 6b857ae4cf3..00000000000
--- a/code/game/objects/structures/tables_racks.dm
+++ /dev/null
@@ -1,558 +0,0 @@
-// Tables and racks.
-
-/obj/structure/table
- name = "table"
- desc = "A square piece of metal standing on four metal legs. It can not move."
- icon = 'icons/obj/structures.dmi'
- icon_state = "table"
- density = 1
- anchored = 1
- layer = 2.8
- throwpass = 1
- climbable = 1
- breakable = 1
- parts = /obj/item/weapon/table_parts
-
- var/flipped = 0
- var/health = 100
-
-/obj/structure/table/woodentable
- name = "wooden table"
- desc = "Do not apply fire to this. Rumour says it burns easily."
- icon_state = "wood_table"
- parts = /obj/item/weapon/table_parts/wood
- health = 50
-
-/obj/structure/table/gamblingtable
- name = "gambling table"
- desc = "A curved wooden table with a thin carpet of green fabric."
- icon_state = "gamble_table"
- parts = /obj/item/weapon/table_parts/gambling
- health = 50
-
-/obj/structure/table/reinforced
- icon_state = "reinf_table"
- health = 200
- parts = /obj/item/weapon/table_parts/reinforced
-
-/obj/structure/table/rack
- name = "rack"
- desc = "Different from the Middle Ages version."
- icon = 'icons/obj/objects.dmi'
- icon_state = "rack"
- health = 100
- parts = /obj/item/weapon/table_parts/rack
- flipped = -1 //Cannot flip.
-
-/obj/structure/table/examine()
- ..()
- if(health > 100)
- usr << "This one looks like it has been reinforced."
-
-/obj/structure/table/proc/update_adjacent()
- for(var/direction in list(1,2,4,8,5,6,9,10))
- if(locate(/obj/structure/table,get_step(src,direction)))
- var/obj/structure/table/T = locate(/obj/structure/table,get_step(src,direction))
- T.update_icon()
-
-/obj/structure/table/New()
- ..()
- for(var/obj/structure/table/T in src.loc)
- if(T != src)
- del(T)
- update_icon()
- update_adjacent()
-
-/obj/structure/table/Del()
- update_adjacent()
- ..()
-
-/obj/structure/table/update_icon()
-
- if(health > 100)
- name = "reinforced [initial(name)]"
-
- spawn(2) //So it properly updates when deleting
-
- if(flipped == 1)
- var/type = 0
- var/tabledirs = 0
- for(var/direction in list(turn(dir,90), turn(dir,-90)) )
- var/obj/structure/table/T = locate(/obj/structure/table,get_step(src,direction))
- if (T && T.flipped == 1 && T.dir == src.dir)
- type++
- tabledirs |= direction
- var/base = "table"
- if (istype(src, /obj/structure/table/woodentable))
- base = "wood"
- if (istype(src, /obj/structure/table/reinforced))
- base = "rtable"
-
- icon_state = "[base]flip[type]"
- if (type==1)
- if (tabledirs & turn(dir,90))
- icon_state = icon_state+"-"
- if (tabledirs & turn(dir,-90))
- icon_state = icon_state+"+"
- return 1
-
- var/dir_sum = 0
- for(var/direction in list(1,2,4,8,5,6,9,10))
- var/skip_sum = 0
- for(var/obj/structure/window/W in src.loc)
- if(W.dir == direction) //So smooth tables don't go smooth through windows
- skip_sum = 1
- continue
- var/inv_direction //inverse direction
- switch(direction)
- if(1)
- inv_direction = 2
- if(2)
- inv_direction = 1
- if(4)
- inv_direction = 8
- if(8)
- inv_direction = 4
- if(5)
- inv_direction = 10
- if(6)
- inv_direction = 9
- if(9)
- inv_direction = 6
- if(10)
- inv_direction = 5
- for(var/obj/structure/window/W in get_step(src,direction))
- if(W.dir == inv_direction) //So smooth tables don't go smooth through windows when the window is on the other table's tile
- skip_sum = 1
- continue
- if(!skip_sum) //means there is a window between the two tiles in this direction
- var/obj/structure/table/T = locate(/obj/structure/table,get_step(src,direction))
- if(T && T.flipped == 0) // This should let us ignore racks for table icons/flipping. Should.
- if(direction <5)
- dir_sum += direction
- else
- if(direction == 5) //This permits the use of all table directions. (Set up so clockwise around the central table is a higher value, from north)
- dir_sum += 16
- if(direction == 6)
- dir_sum += 32
- if(direction == 8) //Aherp and Aderp. Jezes I am stupid. -- SkyMarshal
- dir_sum += 8
- if(direction == 10)
- dir_sum += 64
- if(direction == 9)
- dir_sum += 128
-
- var/table_type = 0 //stand_alone table
- if(dir_sum%16 in cardinal)
- table_type = 1 //endtable
- dir_sum %= 16
- if(dir_sum%16 in list(3,12))
- table_type = 2 //1 tile thick, streight table
- if(dir_sum%16 == 3) //3 doesn't exist as a dir
- dir_sum = 2
- if(dir_sum%16 == 12) //12 doesn't exist as a dir.
- dir_sum = 4
- if(dir_sum%16 in list(5,6,9,10))
- if(locate(/obj/structure/table,get_step(src.loc,dir_sum%16)))
- table_type = 3 //full table (not the 1 tile thick one, but one of the 'tabledir' tables)
- else
- table_type = 2 //1 tile thick, corner table (treated the same as streight tables in code later on)
- dir_sum %= 16
- if(dir_sum%16 in list(13,14,7,11)) //Three-way intersection
- table_type = 5 //full table as three-way intersections are not sprited, would require 64 sprites to handle all combinations. TOO BAD -- SkyMarshal
- switch(dir_sum%16) //Begin computation of the special type tables. --SkyMarshal
- if(7)
- if(dir_sum == 23)
- table_type = 6
- dir_sum = 8
- else if(dir_sum == 39)
- dir_sum = 4
- table_type = 6
- else if(dir_sum == 55 || dir_sum == 119 || dir_sum == 247 || dir_sum == 183)
- dir_sum = 4
- table_type = 3
- else
- dir_sum = 4
- if(11)
- if(dir_sum == 75)
- dir_sum = 5
- table_type = 6
- else if(dir_sum == 139)
- dir_sum = 9
- table_type = 6
- else if(dir_sum == 203 || dir_sum == 219 || dir_sum == 251 || dir_sum == 235)
- dir_sum = 8
- table_type = 3
- else
- dir_sum = 8
- if(13)
- if(dir_sum == 29)
- dir_sum = 10
- table_type = 6
- else if(dir_sum == 141)
- dir_sum = 6
- table_type = 6
- else if(dir_sum == 189 || dir_sum == 221 || dir_sum == 253 || dir_sum == 157)
- dir_sum = 1
- table_type = 3
- else
- dir_sum = 1
- if(14)
- if(dir_sum == 46)
- dir_sum = 1
- table_type = 6
- else if(dir_sum == 78)
- dir_sum = 2
- table_type = 6
- else if(dir_sum == 110 || dir_sum == 254 || dir_sum == 238 || dir_sum == 126)
- dir_sum = 2
- table_type = 3
- else
- dir_sum = 2 //These translate the dir_sum to the correct dirs from the 'tabledir' icon_state.
- if(dir_sum%16 == 15)
- table_type = 4 //4-way intersection, the 'middle' table sprites will be used.
-
- if(istype(src,/obj/structure/table/reinforced))
- switch(table_type)
- if(0)
- icon_state = "reinf_table"
- if(1)
- icon_state = "reinf_1tileendtable"
- if(2)
- icon_state = "reinf_1tilethick"
- if(3)
- icon_state = "reinf_tabledir"
- if(4)
- icon_state = "reinf_middle"
- if(5)
- icon_state = "reinf_tabledir2"
- if(6)
- icon_state = "reinf_tabledir3"
- else if(istype(src,/obj/structure/table/woodentable))
- switch(table_type)
- if(0)
- icon_state = "wood_table"
- if(1)
- icon_state = "wood_1tileendtable"
- if(2)
- icon_state = "wood_1tilethick"
- if(3)
- icon_state = "wood_tabledir"
- if(4)
- icon_state = "wood_middle"
- if(5)
- icon_state = "wood_tabledir2"
- if(6)
- icon_state = "wood_tabledir3"
- else if(istype(src,/obj/structure/table/gamblingtable))
- switch(table_type)
- if(0)
- icon_state = "gamble_table"
- if(1)
- icon_state = "gamble_1tileendtable"
- if(2)
- icon_state = "gamble_1tilethick"
- if(3)
- icon_state = "gamble_tabledir"
- if(4)
- icon_state = "gamble_middle"
- if(5)
- icon_state = "gamble_tabledir2"
- if(6)
- icon_state = "gamble_tabledir3"
- else
- switch(table_type)
- if(0)
- icon_state = "table"
- if(1)
- icon_state = "table_1tileendtable"
- if(2)
- icon_state = "table_1tilethick"
- if(3)
- icon_state = "tabledir"
- if(4)
- icon_state = "table_middle"
- if(5)
- icon_state = "tabledir2"
- if(6)
- icon_state = "tabledir3"
- if (dir_sum in list(1,2,4,8,5,6,9,10))
- set_dir(dir_sum)
- else
- set_dir(2)
-
-/obj/structure/table/attack_tk() // no telehulk sorry
- return
-
-/obj/structure/table/CanPass(atom/movable/mover, turf/target, height=0, air_group=0)
- if(air_group || (height==0)) return 1
- if(istype(mover,/obj/item/projectile))
- return (check_cover(mover,target))
- if(istype(mover) && mover.checkpass(PASSTABLE))
- return 1
- if(locate(/obj/structure/table) in get_turf(mover))
- return 1
- if (flipped == 1)
- if (get_dir(loc, target) == dir)
- return !density
- else
- return 1
- return 0
-
-//checks if projectile 'P' from turf 'from' can hit whatever is behind the table. Returns 1 if it can, 0 if bullet stops.
-/obj/structure/table/proc/check_cover(obj/item/projectile/P, turf/from)
- var/turf/cover
- if(flipped==1)
- cover = get_turf(src)
- else if(flipped==0)
- cover = get_step(loc, get_dir(from, loc))
- if(!cover)
- return 1
- if (get_dist(P.starting, loc) <= 1) //Tables won't help you if people are THIS close
- return 1
- if (get_turf(P.original) == cover)
- var/chance = 20
- if (ismob(P.original))
- var/mob/M = P.original
- if (M.lying)
- chance += 20 //Lying down lets you catch less bullets
- if(flipped==1)
- if(get_dir(loc, from) == dir) //Flipped tables catch mroe bullets
- chance += 20
- else
- return 1 //But only from one side
- if(prob(chance))
- health -= P.damage/2
- if (health > 0)
- visible_message("[P] hits \the [src]!")
- return 0
- else
- visible_message("[src] breaks down!")
- destroy()
- return 1
- return 1
-
-/obj/structure/table/CheckExit(atom/movable/O as mob|obj, target as turf)
- if(istype(O) && O.checkpass(PASSTABLE))
- return 1
- if (flipped==1)
- if (get_dir(loc, target) == dir)
- return !density
- else
- return 1
- return 1
-
-/obj/structure/table/MouseDrop_T(obj/O as obj, mob/user as mob)
-
- if ((!( istype(O, /obj/item/weapon) ) || user.get_active_hand() != O))
- return ..()
- if(isrobot(user))
- return
- user.drop_item()
- if (O.loc != src.loc)
- step(O, get_dir(O, src))
- return
-
-
-/obj/structure/table/attackby(obj/item/W as obj, mob/user as mob)
- if (!W) return
-
- // Handle harm intent grabbing/tabling.
- if (istype(W, /obj/item/weapon/grab) && get_dist(src,user)<2)
- var/obj/item/weapon/grab/G = W
- if (istype(G.affecting, /mob/living))
- var/mob/living/M = G.affecting
- if (G.state < 2)
- if(user.a_intent == I_HURT)
- if (prob(15)) M.Weaken(5)
- M.apply_damage(8,def_zone = "head")
- visible_message("[G.assailant] slams [G.affecting]'s face against \the [src]!")
- playsound(src.loc, 'sound/weapons/tablehit1.ogg', 50, 1)
- else
- user << "You need a better grip to do that!"
- return
- else
- G.affecting.loc = src.loc
- G.affecting.Weaken(5)
- visible_message("[G.assailant] puts [G.affecting] on \the [src].")
- del(W)
- return
-
- // Handle dissembly.
- if (istype(W, /obj/item/weapon/wrench))
- if(health > 100)
- user << "\The [src] is too well constructed to be collapsed. Weaken it first."
- return
- user << "You locate the bolts and begin disassembling \the [src]..."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user,50))
- destroy()
- return
-
- // Handle weakening.
- if (istype(W, /obj/item/weapon/weldingtool))
- var/obj/item/weapon/weldingtool/WT = W
- if(WT.isOn())
- if(initial(health)>100)
- if(WT.remove_fuel(0, user))
- if(src.health>100)
- user << "You start weakening \the [src]..."
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(!do_after(user, 50) || !src || health<100 || !WT.isOn())
- return
- user << "You have weakened \the [src]."
- health -= 100
- else if(src.health <= 100)
- user << "You start strengthening \the [src]..."
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(!do_after(user, 50) || !src || health > 100 || !WT.isOn())
- return
- user << "You have strengthened \the [src]."
- health += 100
- update_icon()
- else
- user << "\The [src] is too flimsy to be reinforced or weakened."
- return
-
-
- // Handle dismantling or placing things on the table from here on.
- if(isrobot(user))
- return
-
- if(W.loc != user) // This should stop mounted modules ending up outside the module.
- return
-
- if(istype(W, /obj/item/weapon/melee/energy/blade))
- var/datum/effect/effect/system/spark_spread/spark_system = new /datum/effect/effect/system/spark_spread()
- spark_system.set_up(5, 0, src.loc)
- spark_system.start()
- playsound(src.loc, 'sound/weapons/blade1.ogg', 50, 1)
- playsound(src.loc, "sparks", 50, 1)
- user.visible_message("The [src] was sliced apart by [user]!")
- destroy()
-
- user.drop_item(src)
- return
-
-/obj/structure/table/proc/straight_table_check(var/direction)
- var/obj/structure/table/T
- for(var/angle in list(-90,90))
- T = locate() in get_step(src.loc,turn(direction,angle))
- if(T && T.flipped == 0)
- return 0
- T = locate() in get_step(src.loc,direction)
- if (!T || T.flipped == 1)
- return 1
- if (istype(T,/obj/structure/table/reinforced/))
- var/obj/structure/table/reinforced/R = T
- if (R.health > 100)
- return 0
- return T.straight_table_check(direction)
-
-/obj/structure/table/verb/do_flip()
- set name = "Flip table"
- set desc = "Flips a non-reinforced table"
- set category = "Object"
- set src in oview(1)
-
- if (!can_touch(usr) || ismouse(usr))
- return
-
- if(flipped < 0 || !flip(get_cardinal_dir(usr,src)))
- usr << "It won't budge."
- return
-
- usr.visible_message("[usr] flips \the [src]!")
-
- if(climbable)
- structure_shaken()
-
- return
-
-/obj/structure/table/proc/unflipping_check(var/direction)
-
- for(var/mob/M in oview(src,0))
- return 0
-
- var/obj/occupied = turf_is_crowded()
- if(occupied)
- usr << "There's \a [occupied] in the way."
- return 0
-
- var/list/L = list()
- if(direction)
- L.Add(direction)
- else
- L.Add(turn(src.dir,-90))
- L.Add(turn(src.dir,90))
- for(var/new_dir in L)
- var/obj/structure/table/T = locate() in get_step(src.loc,new_dir)
- if(T)
- if(T.flipped == 1 && T.dir == src.dir && !T.unflipping_check(new_dir))
- return 0
- return 1
-
-/obj/structure/table/proc/do_put()
- set name = "Put table back"
- set desc = "Puts flipped table back"
- set category = "Object"
- set src in oview(1)
-
- if (!can_touch(usr))
- return
-
- if (!unflipping_check())
- usr << "It won't budge."
- return
- unflip()
-
-/obj/structure/table/proc/flip(var/direction)
- if( !straight_table_check(turn(direction,90)) || !straight_table_check(turn(direction,-90)) )
- return 0
-
- verbs -=/obj/structure/table/verb/do_flip
- verbs +=/obj/structure/table/proc/do_put
-
- var/list/targets = list(get_step(src,dir),get_step(src,turn(dir, 45)),get_step(src,turn(dir, -45)))
- for (var/atom/movable/A in get_turf(src))
- if (!A.anchored)
- spawn(0)
- A.throw_at(pick(targets),1,1)
-
- set_dir(direction)
- if(dir != NORTH)
- layer = 5
- climbable = 0 //flipping tables allows them to be used as makeshift barriers
- flipped = 1
- flags |= ON_BORDER
- for(var/D in list(turn(direction, 90), turn(direction, -90)))
- var/obj/structure/table/T = locate() in get_step(src,D)
- if(T && T.flipped == 0)
- T.flip(direction)
- update_icon()
- update_adjacent()
-
- return 1
-
-/obj/structure/table/proc/unflip()
- verbs -=/obj/structure/table/proc/do_put
- verbs +=/obj/structure/table/verb/do_flip
-
- layer = initial(layer)
- flipped = 0
- climbable = initial(climbable)
- flags &= ~ON_BORDER
- for(var/D in list(turn(dir, 90), turn(dir, -90)))
- var/obj/structure/table/T = locate() in get_step(src.loc,D)
- if(T && T.flipped == 1 && T.dir == src.dir)
- T.unflip()
- update_icon()
- update_adjacent()
-
- return 1
-
-// No need to handle any of this, racks are not contiguous..
-/obj/structure/table/rack/update_icon()
- return
-/obj/structure/table/rack/update_adjacent()
- return
\ No newline at end of file
diff --git a/code/game/objects/structures/transit_tubes.dm b/code/game/objects/structures/transit_tubes.dm
index fcd65e2cdff..47a2f53fb3f 100644
--- a/code/game/objects/structures/transit_tubes.dm
+++ b/code/game/objects/structures/transit_tubes.dm
@@ -47,7 +47,7 @@
-/obj/structure/transit_tube_pod/Del()
+/obj/structure/transit_tube_pod/Destroy()
for(var/atom/movable/AM in contents)
AM.loc = loc
@@ -63,7 +63,7 @@ obj/structure/ex_act(severity)
AM.loc = loc
AM.ex_act(severity++)
- del(src)
+ qdel(src)
return
if(2.0)
if(prob(50))
@@ -71,7 +71,7 @@ obj/structure/ex_act(severity)
AM.loc = loc
AM.ex_act(severity++)
- del(src)
+ qdel(src)
return
if(3.0)
return
diff --git a/code/game/objects/structures/watercloset.dm b/code/game/objects/structures/watercloset.dm
index 62f3ef60c1e..81a3a16cdd3 100644
--- a/code/game/objects/structures/watercloset.dm
+++ b/code/game/objects/structures/watercloset.dm
@@ -173,7 +173,7 @@
/obj/machinery/shower/update_icon() //this is terribly unreadable, but basically it makes the shower mist up
overlays.Cut() //once it's been on for a while, in addition to handling the water overlay.
if(mymist)
- del(mymist)
+ qdel(mymist)
if(on)
overlays += image('icons/obj/watercloset.dmi', src, "water", MOB_LAYER + 1, dir)
@@ -183,16 +183,16 @@
spawn(50)
if(src && on)
ismist = 1
- mymist = new /obj/effect/mist(loc)
+ mymist = PoolOrNew(/obj/effect/mist,loc)
else
ismist = 1
- mymist = new /obj/effect/mist(loc)
+ mymist = PoolOrNew(/obj/effect/mist,loc)
else if(ismist)
ismist = 1
- mymist = new /obj/effect/mist(loc)
+ mymist = PoolOrNew(/obj/effect/mist,loc)
spawn(250)
if(src && !on)
- del(mymist)
+ qdel(mymist)
ismist = 0
/obj/machinery/shower/Crossed(atom/movable/O)
@@ -292,7 +292,7 @@
loc.clean_blood()
for(var/obj/effect/E in tile)
if(istype(E,/obj/effect/rune) || istype(E,/obj/effect/decal/cleanable) || istype(E,/obj/effect/overlay))
- del(E)
+ qdel(E)
/obj/machinery/shower/process()
if(!on) return
diff --git a/code/game/objects/structures/windoor_assembly.dm b/code/game/objects/structures/windoor_assembly.dm
index a0855a35b08..36135a775e7 100644
--- a/code/game/objects/structures/windoor_assembly.dm
+++ b/code/game/objects/structures/windoor_assembly.dm
@@ -37,7 +37,7 @@ obj/structure/windoor_assembly/New(Loc, start_dir=NORTH, constructed=0)
update_nearby_tiles(need_rebuild=1)
-obj/structure/windoor_assembly/Del()
+obj/structure/windoor_assembly/Destroy()
density = 0
update_nearby_tiles()
..()
@@ -78,8 +78,8 @@ obj/structure/windoor_assembly/Del()
user << "\blue You dissasembled the windoor assembly!"
new /obj/item/stack/sheet/glass/reinforced(get_turf(src), 5)
if(secure)
- new /obj/item/stack/rods(get_turf(src), 4)
- del(src)
+ PoolOrNew(/obj/item/stack/rods, list(get_turf(src), 4))
+ qdel(src)
else
user << "\blue You need more welding fuel to dissassemble the windoor assembly."
return
@@ -249,7 +249,7 @@ obj/structure/windoor_assembly/Del()
src.electronics.loc = windoor
- del(src)
+ qdel(src)
else
diff --git a/code/game/objects/structures/window.dm b/code/game/objects/structures/window.dm
index fd96873b7ac..387c76eb698 100644
--- a/code/game/objects/structures/window.dm
+++ b/code/game/objects/structures/window.dm
@@ -88,12 +88,12 @@
index = 0
while(index < 2)
new shardtype(loc)
- if(reinf) new /obj/item/stack/rods(loc)
+ if(reinf) PoolOrNew(/obj/item/stack/rods, loc)
index++
else
new shardtype(loc)
- if(reinf) new /obj/item/stack/rods(loc)
- del(src)
+ if(reinf) PoolOrNew(/obj/item/stack/rods, loc)
+ qdel(src)
return
@@ -111,7 +111,7 @@
/obj/structure/window/ex_act(severity)
switch(severity)
if(1.0)
- del(src)
+ qdel(src)
return
if(2.0)
shatter(0)
@@ -216,7 +216,7 @@
if(istype(G.affecting,/mob/living))
var/mob/living/M = G.affecting
var/state = G.state
- del(W) //gotta delete it here because if window breaks, it won't get deleted
+ qdel(W) //gotta delete it here because if window breaks, it won't get deleted
switch (state)
if(1)
M.visible_message("[user] slams [M] against \the [src]!")
@@ -266,7 +266,7 @@
mats.amount = is_fulltile() ? 4 : 2
else
new glasstype(loc)
- del(src)
+ qdel(src)
else
if(W.damtype == BRUTE || W.damtype == BURN)
hit(W.force)
@@ -334,7 +334,7 @@
update_nearby_icons()
-/obj/structure/window/Del()
+/obj/structure/window/Destroy()
density = 0
update_nearby_tiles()
update_nearby_icons()
@@ -479,10 +479,10 @@
/obj/structure/window/reinforced/polarized/proc/toggle()
if(opacity)
animate(src, color="#FFFFFF", time=5)
- SetOpacity(0)
+ set_opacity(0)
else
animate(src, color="#222222", time=5)
- SetOpacity(1)
+ set_opacity(1)
diff --git a/code/game/response_team.dm b/code/game/response_team.dm
index a64230b1d61..61f69216980 100644
--- a/code/game/response_team.dm
+++ b/code/game/response_team.dm
@@ -37,10 +37,12 @@ var/can_call_ert
log_admin("[key_name(usr)] used Dispatch Response Team.")
trigger_armed_response_team(1)
-
client/verb/JoinResponseTeam()
set category = "IC"
+ if(!MayRespawn(1))
+ return
+
if(istype(usr,/mob/dead/observer) || istype(usr,/mob/new_player))
if(!send_emergency_team)
usr << "No emergency response team is currently being sent."
@@ -58,7 +60,7 @@ client/verb/JoinResponseTeam()
L.name = "Commando"
return
create_response_team(L.loc, new_name)
- del(L)
+ qdel(L)
else
usr << "You need to be an observer or new player to use this."
diff --git a/code/game/smoothwall.dm b/code/game/smoothwall.dm
deleted file mode 100644
index 907b2f67587..00000000000
--- a/code/game/smoothwall.dm
+++ /dev/null
@@ -1,141 +0,0 @@
-//Separate dm because it relates to two types of atoms + ease of removal in case it's needed.
-//Also assemblies.dm for falsewall checking for this when used.
-//I should really make the shuttle wall check run every time it's moved, but centcom uses unsimulated floors so !effort
-
-/atom/proc/relativewall() //atom because it should be useable both for walls and false walls
- if(istype(src,/turf/simulated/floor/vault)||istype(src,/turf/simulated/wall/vault)) //HACK!!!
- return
-
- var/junction = 0 //will be used to determine from which side the wall is connected to other walls
-
- if(!istype(src,/turf/simulated/shuttle/wall)) //or else we'd have wacky shuttle merging with walls action
- for(var/turf/simulated/wall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- junction |= get_dir(src,W)
- for(var/obj/structure/falsewall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- junction |= get_dir(src,W)
- for(var/obj/structure/falserwall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- junction |= get_dir(src,W)
-
-/* Commenting this out for now until we figure out what to do with shuttle smooth walls, if anything.
- As they are now, they sort of work screwy and may need further coding. Or just be scrapped.*/
- /*else
- for(var/turf/simulated/shuttle/wall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- junction |= get_dir(src,W)
- for(var/obj/machinery/shuttle/W in orange(src,1)) //stuff like engine and propulsion should merge with walls
- if(abs(src.x-W.x)-abs(src.y-W.y))
- junction |= get_dir(src,W)
- for(var/obj/machinery/door/W in orange(src,1)) //doors should not result in diagonal walls, it just looks ugly. checking if area is shuttle so it won't merge with the station
- if((abs(src.x-W.x)-abs(src.y-W.y)) && (istype(W.loc.loc,/area/shuttle) || istype(W.loc.loc,/area/supply)))
- junction |= get_dir(src,W)
- for(var/obj/structure/grille/W in orange(src,1)) //same for grilles. checking if area is shuttle so it won't merge with the station
- if((abs(src.x-W.x)-abs(src.y-W.y)) && (istype(W.loc.loc,/area/shuttle) || istype(W.loc.loc,/area/supply)))
- junction |= get_dir(src,W)*/
-
- if(istype(src,/turf/simulated/wall))
- var/turf/simulated/wall/wall = src
- wall.icon_state = "[wall.walltype][junction]"
- else if (istype(src,/obj/structure/falserwall))
- src.icon_state = "rwall[junction]"
- else if (istype(src,/obj/structure/falsewall))
- var/obj/structure/falsewall/fwall = src
- fwall.icon_state = "[fwall.mineral][junction]"
-/* else if(istype(src,/turf/simulated/shuttle/wall))
- var/newicon = icon;
- var/newiconstate = icon_state;
- if(junction!=5 && junction!=6 && junction!=9 && junction!=10) //if it's not diagonal, all is well, no additional calculations needed
- src.icon_state = "swall[junction]"
- else //if it's diagonal, we need to figure out if we're using the floor diagonal or the space diagonal sprite
- var/is_floor = 0
- for(var/turf/unsimulated/floor/F in orange(src,1))
- if(abs(src.x-F.x)-abs(src.y-F.y))
- if((15-junction) & get_dir(src,F)) //if there's a floor in at least one of the empty space directions, return 1
- is_floor = 1
- newicon = F.icon
- newiconstate = F.icon_state //we'll save these for later
- for(var/turf/simulated/floor/F in orange(src,1))
- if(abs(src.x-F.x)-abs(src.y-F.y))
- if((15-junction) & get_dir(src,F)) //if there's a floor in at least one of the empty space directions, return 1
- is_floor = 1
- newicon = F.icon
- newiconstate = F.icon_state //we'll save these for later
- for(var/turf/simulated/shuttle/floor/F in orange(src,1))
- if(abs(src.x-F.x)-abs(src.y-F.y))
- if((15-junction) & get_dir(src,F)) //if there's a floor in at least one of the empty space directions, return 1
- is_floor = 1
- newicon = F.icon
- newiconstate = F.icon_state //we'll save these for later
- if(is_floor) //if is_floor = 1, we use the floor diagonal sprite
- src.icon = newicon; //we'll set the floor's icon to the floor next to it and overlay the wall segment. shuttle floor sprites have priority
- src.icon_state = newiconstate; //
- src.overlays += icon('icons/turf/shuttle.dmi',"swall_f[junction]")
- else //otherwise, the space one
- src.icon_state = "swall_s[junction]"*/
-
- return
-
-/atom/proc/relativewall_neighbours()
- for(var/turf/simulated/wall/W in range(src,1))
- W.relativewall()
- for(var/obj/structure/falsewall/W in range(src,1))
- W.relativewall()
- W.update_icon()//Refreshes the wall to make sure the icons don't desync
- for(var/obj/structure/falserwall/W in range(src,1))
- W.relativewall()
- return
-
-/turf/simulated/wall/New()
- relativewall_neighbours()
- ..()
-
-/*/turf/simulated/shuttle/wall/New()
-
- spawn(20) //testing if this will make /obj/machinery/shuttle and /door count - It does, it stays.
- if(src.icon_state in list("wall1", "wall", "diagonalWall", "wall_floor", "wall_space")) //so wizard den, syndie shuttle etc will remain black
- for(var/turf/simulated/shuttle/wall/W in range(src,1))
- W.relativewall()
-
- ..()*/
-
-/turf/simulated/wall/Del()
- spawn(10)
- for(var/turf/simulated/wall/W in range(src,1))
- W.relativewall()
-
- for(var/obj/structure/falsewall/W in range(src,1))
- W.relativewall()
-
- for(var/direction in cardinal)
- for(var/obj/effect/plant/shroom in get_step(src,direction))
- if(!shroom.floor) //shrooms drop to the floor
- shroom.floor = 1
- shroom.update_icon()
- shroom.pixel_x = 0
- shroom.pixel_y = 0
-
- ..()
-
-/turf/simulated/wall/relativewall()
- if(istype(src,/turf/simulated/wall/vault)) //HACK!!!
- return
-
- var/junction = 0 //will be used to determine from which side the wall is connected to other walls
-
- for(var/turf/simulated/wall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)//Only 'like' walls connect -Sieve
- junction |= get_dir(src,W)
- for(var/obj/structure/falsewall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- for(var/obj/structure/falserwall/W in orange(src,1))
- if(abs(src.x-W.x)-abs(src.y-W.y)) //doesn't count diagonal walls
- if(src.mineral == W.mineral)
- junction |= get_dir(src,W)
- var/turf/simulated/wall/wall = src
- wall.icon_state = "[wall.walltype][junction]"
- return
\ No newline at end of file
diff --git a/code/game/sound.dm b/code/game/sound.dm
index b5a4006e345..1cc6f988070 100644
--- a/code/game/sound.dm
+++ b/code/game/sound.dm
@@ -53,34 +53,34 @@ var/const/FALLOFF_SOUNDS = 0.5
if(isturf(turf_source))
// 3D sounds, the technology is here!
var/turf/T = get_turf(src)
-
+
//sound volume falloff with distance
var/distance = get_dist(T, turf_source)
-
+
S.volume -= max(distance - world.view, 0) * 2 //multiplicative falloff to add on top of natural audio falloff.
-
+
//sound volume falloff with pressure
var/pressure_factor = 1.0
-
+
var/datum/gas_mixture/hearer_env = T.return_air()
var/datum/gas_mixture/source_env = turf_source.return_air()
-
+
if (hearer_env && source_env)
var/pressure = min(hearer_env.return_pressure(), source_env.return_pressure())
-
+
if (pressure < ONE_ATMOSPHERE)
pressure_factor = max((pressure - SOUND_MINIMUM_PRESSURE)/(ONE_ATMOSPHERE - SOUND_MINIMUM_PRESSURE), 0)
else //in space
pressure_factor = 0
-
+
if (distance <= 1)
pressure_factor = max(pressure_factor, 0.15) //hearing through contact
-
+
S.volume *= pressure_factor
-
+
if (S.volume <= 0)
return //no volume means no sound
-
+
var/dx = turf_source.x - T.x // Hearing from the right/left
S.x = dx
var/dz = turf_source.y - T.y // Hearing from infront/behind
@@ -88,8 +88,11 @@ var/const/FALLOFF_SOUNDS = 0.5
// The y value is for above your head, but there is no ceiling in 2d spessmens.
S.y = 1
S.falloff = (falloff ? falloff : FALLOFF_SOUNDS)
+
if(!is_global)
- S.environment = 2
+ var/area/A = get_area(src)
+ S.environment = A.sound_env
+
src << S
/client/proc/playtitlemusic()
diff --git a/code/game/supplyshuttle.dm b/code/game/supplyshuttle.dm
index d32173c2677..2b39256e5bd 100644
--- a/code/game/supplyshuttle.dm
+++ b/code/game/supplyshuttle.dm
@@ -25,19 +25,16 @@ var/list/mechtoys = list(
/obj/item/weapon/paper/manifest
name = "supply manifest"
+ var/is_copy = 1
-/area/supply/station //DO NOT TURN THE lighting_use_dynamic STUFF ON FOR SHUTTLES. IT BREAKS THINGS.
+/area/supply/station
name = "Supply Shuttle"
icon_state = "shuttle3"
- luminosity = 1
- lighting_use_dynamic = 0
requires_power = 0
-/area/supply/dock //DO NOT TURN THE lighting_use_dynamic STUFF ON FOR SHUTTLES. IT BREAKS THINGS.
+/area/supply/dock
name = "Supply Shuttle"
icon_state = "shuttle3"
- luminosity = 1
- lighting_use_dynamic = 0
requires_power = 0
/obj/structure/plasticflaps //HOW DO YOU CALL THOSE THINGS ANYWAY
@@ -84,13 +81,13 @@ var/list/mechtoys = list(
/obj/structure/plasticflaps/ex_act(severity)
switch(severity)
if (1)
- del(src)
+ qdel(src)
if (2)
if (prob(50))
- del(src)
+ qdel(src)
if (3)
if (prob(5))
- del(src)
+ qdel(src)
/obj/structure/plasticflaps/mining //A specific type for mining that doesn't allow airflow because of them damn crates
name = "airtight plastic flaps"
@@ -102,7 +99,7 @@ var/list/mechtoys = list(
T.blocks_air = 1
..()
- Del() //lazy hack to set the turf to allow air to pass if it's a simulated floor
+ Destroy() //lazy hack to set the turf to allow air to pass if it's a simulated floor
var/turf/T = get_turf(loc)
if(T)
if(istype(T, /turf/simulated/floor))
@@ -201,8 +198,8 @@ var/list/mechtoys = list(
// Sell manifests
var/atom/A = atom
if(find_slip && istype(A,/obj/item/weapon/paper/manifest))
- var/obj/item/weapon/paper/slip = A
- if(slip.stamped && slip.stamped.len) //yes, the clown stamp will work. clown is the highest authority on the station, it makes sense
+ var/obj/item/weapon/paper/manifest/slip = A
+ if(!slip.is_copy && slip.stamped && slip.stamped.len) //yes, the clown stamp will work. clown is the highest authority on the station, it makes sense
points += points_per_slip
find_slip = 0
continue
@@ -217,7 +214,7 @@ var/list/mechtoys = list(
var/obj/item/stack/sheet/mineral/platinum/P = A
plat_count += P.get_amount()
- del(MA)
+ qdel(MA)
if(phoron_count)
points += phoron_count * points_per_phoron
@@ -235,7 +232,14 @@ var/list/mechtoys = list(
var/list/clear_turfs = list()
for(var/turf/T in area_shuttle)
- if(T.density || T.contents.len) continue
+ if(T.density) continue
+ var/contcount
+ for(var/atom/A in T.contents)
+ if(A.simulated)
+ continue
+ contcount++
+ if(contcount)
+ continue
clear_turfs += T
for(var/S in shoppinglist)
@@ -253,6 +257,7 @@ var/list/mechtoys = list(
//supply manifest generation begin
var/obj/item/weapon/paper/manifest/slip = new /obj/item/weapon/paper/manifest(A)
+ slip.is_copy = 0
slip.info = "
[command_name()] Shipping Manifest
"
slip.info +="Order #[SO.ordernum] "
slip.info +="Destination: [station_name] "
diff --git a/code/game/turfs/simulated.dm b/code/game/turfs/simulated.dm
index 9546bf9ba1b..dcecf46ad60 100644
--- a/code/game/turfs/simulated.dm
+++ b/code/game/turfs/simulated.dm
@@ -12,6 +12,8 @@
/turf/simulated/New()
..()
+ if(istype(loc, /area/chapel))
+ holy = 1
levelupdate()
/turf/simulated/proc/AddTracks(var/typepath,var/bloodDNA,var/comingdir,var/goingdir,var/bloodcolor="#A10808")
diff --git a/code/game/turfs/simulated/floor.dm b/code/game/turfs/simulated/floor.dm
index 07b68a329a7..bb7d93fbf17 100644
--- a/code/game/turfs/simulated/floor.dm
+++ b/code/game/turfs/simulated/floor.dm
@@ -41,7 +41,7 @@ var/list/wood_icons = list("wood","wood-broken")
var/lava = 0
var/broken = 0
var/burnt = 0
- var/mineral = "metal"
+ var/mineral = DEFAULT_WALL_MATERIAL
var/floor_type = /obj/item/stack/tile/plasteel
var/lightfloor_state // for light floors, this is the state of the tile. 0-7, 0x4 is on-bit - use the helper procs below
@@ -82,19 +82,19 @@ var/list/wood_icons = list("wood","wood-broken")
if(1.0)
src.ChangeTurf(/turf/space)
if(2.0)
- switch(pick(1,2;75,3))
+ switch(pick(40;1,40;2,3))
if (1)
- src.ReplaceWithLattice()
if(prob(33)) new /obj/item/stack/sheet/metal(src)
+ src.ReplaceWithLattice()
if(2)
src.ChangeTurf(/turf/space)
if(3)
+ if(prob(33)) new /obj/item/stack/sheet/metal(src)
if(prob(80))
src.break_tile_to_plating()
else
src.break_tile()
src.hotspot_expose(1000,CELL_VOLUME)
- if(prob(33)) new /obj/item/stack/sheet/metal(src)
if(3.0)
if (prob(50))
src.break_tile()
@@ -133,19 +133,19 @@ turf/simulated/floor/proc/update_icon()
switch(get_lightfloor_state())
if(LIGHTFLOOR_STATE_OK)
icon_state = "light_on"
- SetLuminosity(5)
+ set_light(5)
if(LIGHTFLOOR_STATE_FLICKER)
var/num = pick("1","2","3","4")
icon_state = "light_on_flicker[num]"
- SetLuminosity(5)
+ set_light(5)
if(LIGHTFLOOR_STATE_BREAKING)
icon_state = "light_on_broken"
- SetLuminosity(5)
+ set_light(5)
if(LIGHTFLOOR_STATE_BROKEN)
icon_state = "light_off"
- SetLuminosity(0)
+ set_light(0)
else
- SetLuminosity(0)
+ set_light(0)
icon_state = "light_off"
else if(is_grass_floor())
if(!broken && !burnt)
@@ -339,7 +339,7 @@ turf/simulated/floor/proc/update_icon()
if(!floor_type) return
icon_plating = "plating"
- SetLuminosity(0)
+ set_light(0)
floor_type = null
intact = 0
broken = 0
@@ -355,7 +355,7 @@ turf/simulated/floor/proc/update_icon()
broken = 0
burnt = 0
intact = 1
- SetLuminosity(0)
+ set_light(0)
if(T)
if(istype(T,/obj/item/stack/tile/plasteel))
floor_type = T.type
@@ -457,7 +457,7 @@ turf/simulated/floor/proc/update_icon()
if(is_light_floor())
if(get_lightfloor_state())
user.remove_from_mob(C)
- del(C)
+ qdel(C)
set_lightfloor_state(0) //fixing it by bashing it with a light bulb, fun eh?
update_icon()
user << "\blue You replace the light bulb."
diff --git a/code/game/turfs/simulated/floor_types.dm b/code/game/turfs/simulated/floor_types.dm
index 4c4682c5c59..450352f9b5b 100644
--- a/code/game/turfs/simulated/floor_types.dm
+++ b/code/game/turfs/simulated/floor_types.dm
@@ -14,7 +14,7 @@
/turf/simulated/floor/light
name = "Light floor"
- luminosity = 5
+ light_range = 5
icon_state = "light_on"
floor_type = /obj/item/stack/tile/light
@@ -64,7 +64,7 @@
user << "\blue Removing rods..."
playsound(src, 'sound/items/Ratchet.ogg', 80, 1)
if(do_after(user, 30))
- new /obj/item/stack/rods(src, 2)
+ PoolOrNew(/obj/item/stack/rods, list(loc, 2))
ChangeTurf(/turf/simulated/floor)
var/turf/simulated/floor/F = src
F.make_plating()
@@ -74,6 +74,8 @@
name = "engraved floor"
icon_state = "cult"
+/turf/simulated/floor/engine/cult/cultify()
+ return
/turf/simulated/floor/engine/n20
New()
diff --git a/code/game/turfs/simulated/wall_attacks.dm b/code/game/turfs/simulated/wall_attacks.dm
new file mode 100644
index 00000000000..4d86d70877d
--- /dev/null
+++ b/code/game/turfs/simulated/wall_attacks.dm
@@ -0,0 +1,311 @@
+//Interactions
+/turf/simulated/wall/proc/toggle_open(var/mob/user)
+
+ if(can_open == WALL_OPENING)
+ return
+
+ if(density)
+ can_open = WALL_OPENING
+ set_wall_state("[material.icon_base]fwall_open")
+ //flick("[material.icon_base]fwall_opening", src)
+ sleep(15)
+ density = 0
+ set_light(0)
+ else
+ can_open = WALL_OPENING
+ //flick("[material.icon_base]fwall_closing", src)
+ set_wall_state("[material.icon_base]0")
+ density = 1
+ sleep(15)
+ set_light(1)
+
+ can_open = WALL_CAN_OPEN
+ update_icon()
+
+/turf/simulated/wall/proc/fail_smash(var/mob/user)
+ user << "You smash against the wall!"
+ take_damage(rand(25,75))
+
+/turf/simulated/wall/proc/success_smash(var/mob/user)
+ user << "You smash through the wall!"
+ spawn(1)
+ dismantle_wall(1)
+
+/turf/simulated/wall/proc/try_touch(var/mob/user, var/rotting)
+
+ if(rotting)
+ if(reinf_material)
+ user << "\The [reinf_material.display_name] feels porous and crumbly."
+ else
+ user << "\The [material.display_name] crumbles under your touch!"
+ dismantle_wall()
+ return 1
+
+ if(..()) return 1
+
+ if(!can_open)
+ user << "You push the wall, but nothing happens."
+ playsound(src, 'sound/weapons/Genhit.ogg', 25, 1)
+ else
+ toggle_open(user)
+ return 0
+
+
+/turf/simulated/wall/attack_hand(var/mob/user)
+
+ radiate()
+ add_fingerprint(user)
+ var/rotting = (locate(/obj/effect/overlay/wallrot) in src)
+ if (HULK in user.mutations)
+ if (rotting || !prob(material.hardness))
+ success_smash(user)
+ else
+ fail_smash(user)
+ return 1
+
+ try_touch(user, rotting)
+
+/turf/simulated/wall/attack_generic(var/mob/user, var/damage, var/attack_message, var/wallbreaker)
+
+ radiate()
+ var/rotting = (locate(/obj/effect/overlay/wallrot) in src)
+ if(!damage || !wallbreaker)
+ try_touch(user, rotting)
+ return
+
+ if(rotting)
+ return success_smash(user)
+
+ if(reinf_material)
+ if((wallbreaker == 2) || (damage >= max(material.hardness,reinf_material.hardness)))
+ return success_smash(user)
+ else if(damage >= material.hardness)
+ return success_smash(user)
+ return fail_smash(user)
+
+/turf/simulated/wall/attackby(obj/item/weapon/W as obj, mob/user as mob)
+
+ if (!user.)
+ user << "You don't have the dexterity to do this!"
+ return
+
+ //get the user's location
+ if(!istype(user.loc, /turf)) return //can't do this stuff whilst inside objects and such
+
+ if(W)
+ radiate()
+ if(is_hot(W))
+ ignite(is_hot(W))
+
+ if(locate(/obj/effect/overlay/wallrot) in src)
+ if(istype(W, /obj/item/weapon/weldingtool) )
+ var/obj/item/weapon/weldingtool/WT = W
+ if( WT.remove_fuel(0,user) )
+ user << "You burn away the fungi with \the [WT]."
+ playsound(src, 'sound/items/Welder.ogg', 10, 1)
+ for(var/obj/effect/overlay/wallrot/WR in src)
+ qdel(WR)
+ return
+ else if(!is_sharp(W) && W.force >= 10 || W.force >= 20)
+ user << "\The [src] crumbles away under the force of your [W.name]."
+ src.dismantle_wall(1)
+ return
+
+ //THERMITE related stuff. Calls src.thermitemelt() which handles melting simulated walls and the relevant effects
+ if(thermite)
+ if( istype(W, /obj/item/weapon/weldingtool) )
+ var/obj/item/weapon/weldingtool/WT = W
+ if( WT.remove_fuel(0,user) )
+ thermitemelt(user)
+ return
+
+ else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
+ thermitemelt(user)
+ return
+
+ else if( istype(W, /obj/item/weapon/melee/energy/blade) )
+ var/obj/item/weapon/melee/energy/blade/EB = W
+
+ EB.spark_system.start()
+ user << "You slash \the [src] with \the [EB]; the thermite ignites!"
+ playsound(src, "sparks", 50, 1)
+ playsound(src, 'sound/weapons/blade1.ogg', 50, 1)
+
+ thermitemelt(user)
+ return
+
+ var/turf/T = user.loc //get user's location for delay checks
+
+ if(damage && istype(W, /obj/item/weapon/weldingtool))
+
+ var/obj/item/weapon/weldingtool/WT = W
+
+ if(!WT.isOn())
+ return
+
+ if(WT.remove_fuel(0,user))
+ user << "You start repairing the damage to [src]."
+ playsound(src, 'sound/items/Welder.ogg', 100, 1)
+ if(do_after(user, max(5, damage / 5)) && WT && WT.isOn())
+ user << "You finish repairing the damage to [src]."
+ take_damage(-damage)
+ else
+ user << "You need more welding fuel to complete this task."
+ return
+ return
+
+ // Basic dismantling.
+ if(isnull(construction_stage) || !reinf_material)
+
+ var/cut_delay = 60 - material.cut_delay
+ var/dismantle_verb
+ var/dismantle_sound
+
+ if(istype(W,/obj/item/weapon/weldingtool))
+ var/obj/item/weapon/weldingtool/WT = W
+ if(!WT.isOn())
+ return
+ if(!WT.remove_fuel(0,user))
+ user << "You need more welding fuel to complete this task."
+ return
+ dismantle_verb = "cutting"
+ dismantle_sound = 'sound/items/Welder.ogg'
+ cut_delay *= 0.7
+ else if(istype(W,/obj/item/weapon/melee/energy/blade))
+ dismantle_sound = "sparks"
+ dismantle_verb = "slicing"
+ cut_delay *= 0.5
+ else if(istype(W,/obj/item/weapon/pickaxe))
+ var/obj/item/weapon/pickaxe/P = W
+ dismantle_verb = P.drill_verb
+ dismantle_sound = P.drill_sound
+ cut_delay -= P.digspeed
+
+ if(dismantle_verb)
+
+ user << "You begin [dismantle_verb] through the outer plating."
+ if(dismantle_sound)
+ playsound(src, dismantle_sound, 100, 1)
+
+ if(cut_delay<0)
+ cut_delay = 0
+
+ if(!do_after(user,cut_delay))
+ return
+
+ user << "You remove the outer plating."
+ dismantle_wall()
+ user.visible_message("The wall was torn open by [user]!")
+ return
+
+ //Reinforced dismantling.
+ else
+ switch(construction_stage)
+ if(6)
+ if (istype(W, /obj/item/weapon/wirecutters))
+ playsound(src, 'sound/items/Wirecutter.ogg', 100, 1)
+ construction_stage = 5
+ new /obj/item/stack/rods( src )
+ user << "You cut the outer grille."
+ set_wall_state()
+ return
+ if(5)
+ if (istype(W, /obj/item/weapon/screwdriver))
+ user << "You begin removing the support lines."
+ playsound(src, 'sound/items/Screwdriver.ogg', 100, 1)
+ if(!do_after(user,40) || !istype(src, /turf/simulated/wall) || construction_stage != 5)
+ return
+ construction_stage = 4
+ set_wall_state()
+ user << "You remove the support lines."
+ return
+ else if( istype(W, /obj/item/stack/rods) )
+ var/obj/item/stack/O = W
+ if(O.get_amount()>0)
+ O.use(1)
+ construction_stage = 6
+ set_wall_state()
+ user << "You replace the outer grille."
+ return
+ if(4)
+ var/cut_cover
+ if(istype(W,/obj/item/weapon/weldingtool))
+ var/obj/item/weapon/weldingtool/WT = W
+ if(!WT.isOn())
+ return
+ if(WT.remove_fuel(0,user))
+ cut_cover=1
+ else
+ user << "You need more welding fuel to complete this task."
+ return
+ else if (istype(W, /obj/item/weapon/pickaxe/plasmacutter))
+ cut_cover = 1
+ if(cut_cover)
+ user << "You begin slicing through the metal cover."
+ playsound(src, 'sound/items/Welder.ogg', 100, 1)
+ if(!do_after(user, 60) || !istype(src, /turf/simulated/wall) || construction_stage != 4)
+ return
+ construction_stage = 3
+ set_wall_state()
+ user << "You press firmly on the cover, dislodging it."
+ return
+ if(3)
+ if (istype(W, /obj/item/weapon/crowbar))
+ user << "You struggle to pry off the cover."
+ playsound(src, 'sound/items/Crowbar.ogg', 100, 1)
+ if(!do_after(user,100) || !istype(src, /turf/simulated/wall) || construction_stage != 3)
+ return
+ construction_stage = 2
+ set_wall_state()
+ user << "You pry off the cover."
+ return
+ if(2)
+ if (istype(W, /obj/item/weapon/wrench))
+ user << "You start loosening the anchoring bolts which secure the support rods to their frame."
+ playsound(src, 'sound/items/Ratchet.ogg', 100, 1)
+ if(!do_after(user,40) || !istype(src, /turf/simulated/wall) || construction_stage != 2)
+ return
+ construction_stage = 1
+ set_wall_state()
+ user << "You remove the bolts anchoring the support rods."
+ return
+ if(1)
+ var/cut_cover
+ if(istype(W, /obj/item/weapon/weldingtool))
+ var/obj/item/weapon/weldingtool/WT = W
+ if( WT.remove_fuel(0,user) )
+ cut_cover=1
+ else
+ user << "You need more welding fuel to complete this task."
+ return
+ else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
+ cut_cover = 1
+ if(cut_cover)
+ user << "You begin slicing through the support rods."
+ playsound(src, 'sound/items/Welder.ogg', 100, 1)
+ if(!do_after(user,70) || !istype(src, /turf/simulated/wall) || construction_stage != 1)
+ return
+ construction_stage = 0
+ set_wall_state()
+ new /obj/item/stack/rods(src)
+ user << "The support rods drop out as you cut them loose from the frame."
+ return
+ if(0)
+ if(istype(W, /obj/item/weapon/crowbar))
+ user << "You struggle to pry off the outer sheath."
+ playsound(src, 'sound/items/Crowbar.ogg', 100, 1)
+ sleep(100)
+ if(!istype(src, /turf/simulated/wall) || !user || !W || !T ) return
+ if(user.loc == T && user.get_active_hand() == W )
+ user << "You pry off the outer sheath."
+ dismantle_wall()
+ return
+
+ if(istype(W,/obj/item/frame))
+ var/obj/item/frame/F = W
+ F.try_build(src)
+ return
+
+ else if(!istype(W,/obj/item/weapon/rcd) && !istype(W, /obj/item/weapon/reagent_containers))
+ return attack_hand(user)
+
diff --git a/code/game/turfs/simulated/wall_icon.dm b/code/game/turfs/simulated/wall_icon.dm
new file mode 100644
index 00000000000..1adaba850f6
--- /dev/null
+++ b/code/game/turfs/simulated/wall_icon.dm
@@ -0,0 +1,134 @@
+/turf/simulated/wall/proc/update_material()
+
+ if(!material)
+ return
+
+ if(reinf_material)
+ construction_stage = 6
+ else
+ construction_stage = null
+ if(!material)
+ material = name_to_material[DEFAULT_WALL_MATERIAL]
+ if(material)
+ explosion_resistance = material.explosion_resistance
+ if(reinf_material && reinf_material.explosion_resistance > explosion_resistance)
+ explosion_resistance = reinf_material.explosion_resistance
+
+ if(reinf_material)
+ name = "reinforced [material.display_name] wall"
+ desc = "It seems to be a section of hull reinforced with [reinf_material.display_name] and plated with [material.display_name]."
+ else
+ name = "[material.display_name] wall"
+ desc = "It seems to be a section of hull plated with [material.display_name]."
+
+ set_wall_state("[material.icon_base]0")
+
+ if(material.opacity > 0.5 && !opacity)
+ set_light(1)
+ else if(material.opacity < 0.5 && opacity)
+ set_light(0)
+
+ update_icon()
+ check_relatives()
+
+/turf/simulated/wall/proc/set_wall_state(var/new_state)
+
+ if(!material)
+ return
+
+ if(new_state)
+ last_state = new_state
+ else if(last_state)
+ new_state = last_state
+ else
+ return
+
+ overlays.Cut()
+
+ if(!wall_cache["[new_state]-[material.icon_colour]"])
+ var/image/I = image(icon='icons/turf/wall_masks.dmi',icon_state="[new_state]")
+ I.color = material.icon_colour
+ wall_cache["[new_state]-[material.icon_colour]"] = I
+ overlays |= wall_cache["[new_state]-[material.icon_colour]"]
+ if(reinf_material)
+
+ var/cache_key = "[material.icon_reinf]-[reinf_material.icon_colour]"
+ if(!isnull(construction_stage) && construction_stage<6)
+ cache_key = "reinf_construct-[reinf_material.icon_colour]-[construction_stage]"
+
+ if(!wall_cache[cache_key])
+ var/image/I
+ if(!isnull(construction_stage) && construction_stage<6)
+ I = image(icon='icons/turf/wall_masks.dmi',icon_state="reinf_construct-[construction_stage]")
+ else
+ I = image(icon='icons/turf/wall_masks.dmi',icon_state="[material.icon_reinf]")
+ I.color = reinf_material.icon_colour
+ wall_cache[cache_key] = I
+ overlays |= wall_cache[cache_key]
+
+/turf/simulated/wall/proc/set_material(var/material/newmaterial, var/material/newrmaterial)
+ material = newmaterial
+ reinf_material = newrmaterial
+ update_material()
+ check_relatives()
+ check_relatives(1)
+
+/turf/simulated/wall/proc/update_icon()
+
+ if(!material)
+ return
+
+ if(!damage_overlays[1]) //list hasn't been populated
+ generate_overlays()
+
+ if(density)
+ check_relatives(1)
+ else
+ set_wall_state("[material.icon_base]fwall_open")
+
+ var/dmg_amt = material.integrity
+ if(reinf_material)
+ dmg_amt += reinf_material.integrity
+ var/overlay = round(damage / dmg_amt * damage_overlays.len) + 1
+ if(overlay > damage_overlays.len)
+ overlay = damage_overlays.len
+ if(density)
+ if(damage_overlay && overlay == damage_overlay) //No need to update.
+ return
+ overlays += damage_overlays[overlay]
+ damage_overlay = overlay
+ return
+
+/turf/simulated/wall/proc/generate_overlays()
+ var/alpha_inc = 256 / damage_overlays.len
+
+ for(var/i = 1; i <= damage_overlays.len; i++)
+ var/image/img = image(icon = 'icons/turf/walls.dmi', icon_state = "overlay_damage")
+ img.blend_mode = BLEND_MULTIPLY
+ img.alpha = (i * alpha_inc) - 1
+ damage_overlays[i] = img
+
+//Smoothwall code. update_self for relativewall(), not for relativewall_neighbors()
+/turf/simulated/wall/proc/check_relatives(var/update_self)
+ if(!material)
+ return
+ var/junction
+ if(update_self)
+ junction = 0
+ for(var/checkdir in cardinal)
+ var/turf/simulated/wall/T = get_step(src, checkdir)
+ if(!istype(T) || !T.material)
+ continue
+ if(update_self)
+ if(can_join_with(T))
+ junction |= get_dir(src,T) //Not too sure why, but using checkdir just breaks walls.
+ else
+ T.check_relatives(1)
+ if(!isnull(junction))
+ set_wall_state("[material.icon_base][junction]")
+ return
+
+/turf/simulated/wall/proc/can_join_with(var/turf/simulated/wall/W)
+ if(material && W.material && material.name == W.material.name)
+ return 1
+ return 0
\ No newline at end of file
diff --git a/code/game/turfs/simulated/wall_types.dm b/code/game/turfs/simulated/wall_types.dm
new file mode 100644
index 00000000000..dc9346e3238
--- /dev/null
+++ b/code/game/turfs/simulated/wall_types.dm
@@ -0,0 +1,43 @@
+/turf/simulated/wall/r_wall
+ icon_state = "rgeneric"
+/turf/simulated/wall/r_wall/New(var/newloc)
+ ..(newloc, DEFAULT_WALL_MATERIAL,"plasteel") //3strong
+/turf/simulated/wall/cult
+ icon_state = "cult"
+/turf/simulated/wall/cult/New(var/newloc)
+ ..(newloc,"cult","cult2")
+
+/turf/unsimulated/wall/cult
+ name = "cult wall"
+ desc = "Hideous images dance beneath the surface."
+ icon = 'icons/turf/wall_masks.dmi'
+ icon_state = "cult"
+
+
+/turf/simulated/wall/iron/New(var/newloc)
+ ..(newloc,"iron")
+/turf/simulated/wall/uranium/New(var/newloc)
+ ..(newloc,"uranium")
+/turf/simulated/wall/diamond/New(var/newloc)
+ ..(newloc,"diamond")
+/turf/simulated/wall/gold/New(var/newloc)
+ ..(newloc,"gold")
+/turf/simulated/wall/silver/New(var/newloc)
+ ..(newloc,"silver")
+/turf/simulated/wall/phoron/New(var/newloc)
+ ..(newloc,"phoron")
+/turf/simulated/wall/sandstone/New(var/newloc)
+ ..(newloc,"sandstone")
+
+/turf/simulated/wall/ironphoron/New(var/newloc)
+ ..(newloc,"iron","phoron")
+/turf/simulated/wall/golddiamond/New(var/newloc)
+ ..(newloc,"gold","diamond")
+/turf/simulated/wall/silvergold/New(var/newloc)
+ ..(newloc,"silver","gold")
+/turf/simulated/wall/sandstonediamond/New(var/newloc)
+ ..(newloc,"sandstone","diamond")
+
+
+/turf/simulated/wall/cult/New(var/newloc)
+ ..(newloc,"cult","cult2")
\ No newline at end of file
diff --git a/code/game/turfs/simulated/walls.dm b/code/game/turfs/simulated/walls.dm
index 969b872caf6..8fa7c9dd2f7 100644
--- a/code/game/turfs/simulated/walls.dm
+++ b/code/game/turfs/simulated/walls.dm
@@ -1,28 +1,54 @@
+var/list/global/wall_cache = list()
+
/turf/simulated/wall
name = "wall"
desc = "A huge chunk of metal used to seperate rooms."
- icon = 'icons/turf/walls.dmi'
- var/mineral = "metal"
- var/rotting = 0
-
- var/damage = 0
- var/damage_cap = 150 //Wall will break down to girders if damage reaches this point
-
- var/damage_overlay
- var/global/damage_overlays[8]
-
- var/max_temperature = 1800 //K, walls will take damage if they're next to a fire hotter than this
-
+ icon = 'icons/turf/wall_masks.dmi'
+ icon_state = "generic"
opacity = 1
density = 1
blocks_air = 1
-
thermal_conductivity = WALL_HEAT_TRANSFER_COEFFICIENT
heat_capacity = 312500 //a little over 5 cm thick , 312500 for 1 m by 2.5 m by 0.25 m plasteel wall
- var/walltype = "metal"
+ var/damage = 0
+ var/damage_overlay
+ var/global/damage_overlays[8]
+ var/active
+ var/can_open = 0
+ var/material/material
+ var/material/reinf_material
+ var/last_state
+ var/construction_stage
+
+/turf/simulated/wall/New(var/newloc, var/materialtype, var/rmaterialtype)
+ ..(newloc)
+ icon_state = "blank"
+ if(!materialtype)
+ materialtype = DEFAULT_WALL_MATERIAL
+ material = get_material_by_name(materialtype)
+ if(!isnull(rmaterialtype))
+ reinf_material = name_to_material[rmaterialtype]
+ update_material()
+
+ processing_turfs |= src
+
+/turf/simulated/wall/Destroy()
+ processing_turfs -= src
+ dismantle_wall(null,null,1)
+ ..()
+
+
+/turf/simulated/wall/process()
+ // Calling parent will kill processing
+ if(!radiate())
+ return PROCESS_KILL
/turf/simulated/wall/bullet_act(var/obj/item/projectile/Proj)
+ if(istype(Proj,/obj/item/projectile/beam))
+ ignite(2500)
+ else if(istype(Proj,/obj/item/projectile/ion))
+ ignite(500)
// Tasers and stuff? No thanks. Also no clone or tox damage crap.
if(!(Proj.damage_type == BRUTE || Proj.damage_type == BURN))
@@ -45,25 +71,29 @@
take_damage(tforce)
-/turf/simulated/wall/Del()
- for(var/obj/effect/E in src) if(E.name == "Wallrot") del E
- ..()
+/turf/simulated/wall/proc/clear_plants()
+ for(var/obj/effect/overlay/wallrot/WR in src)
+ qdel(WR)
+ for(var/obj/effect/plant/plant in range(src, 1))
+ if(!plant.floor) //shrooms drop to the floor
+ plant.floor = 1
+ plant.update_icon()
+ plant.pixel_x = 0
+ plant.pixel_y = 0
+ plant.update_neighbors()
/turf/simulated/wall/ChangeTurf(var/newtype)
- for(var/obj/effect/E in src) if(E.name == "Wallrot") del E
- for(var/obj/effect/plant/plant in range(1))
- plant.update_neighbors()
+ clear_plants()
..(newtype)
//Appearance
-
/turf/simulated/wall/examine(mob/user)
. = ..(user)
if(!damage)
user << "It looks fully intact."
else
- var/dam = damage / damage_cap
+ var/dam = damage / material.integrity
if(dam <= 0.3)
user << "It looks slightly damaged."
else if(dam <= 0.6)
@@ -71,41 +101,26 @@
else
user << "It looks heavily damaged."
- if(rotting)
+ if(locate(/obj/effect/overlay/wallrot) in src)
user << "There is fungus growing on [src]."
-/turf/simulated/wall/proc/update_icon()
- if(!damage_overlays[1]) //list hasn't been populated
- generate_overlays()
-
- if(!damage)
- overlays.Cut()
- return
-
- var/overlay = round(damage / damage_cap * damage_overlays.len) + 1
- if(overlay > damage_overlays.len)
- overlay = damage_overlays.len
-
- if(damage_overlay && overlay == damage_overlay) //No need to update.
- return
-
- overlays.Cut()
- overlays += damage_overlays[overlay]
- damage_overlay = overlay
-
- return
-
-/turf/simulated/wall/proc/generate_overlays()
- var/alpha_inc = 256 / damage_overlays.len
-
- for(var/i = 1; i <= damage_overlays.len; i++)
- var/image/img = image(icon = 'icons/turf/walls.dmi', icon_state = "overlay_damage")
- img.blend_mode = BLEND_MULTIPLY
- img.alpha = (i * alpha_inc) - 1
- damage_overlays[i] = img
-
//Damage
+/turf/simulated/wall/melt()
+
+ if(!can_melt())
+ return
+
+ src.ChangeTurf(/turf/simulated/floor/plating)
+
+ var/turf/simulated/floor/F = src
+ if(!F)
+ return
+ F.burn_tile()
+ F.icon_state = "wall_thermite"
+ visible_message("\The [src] spontaneously combusts!.") //!!OH SHIT!!
+ return
+
/turf/simulated/wall/proc/take_damage(dam)
if(dam)
damage = max(0, damage + dam)
@@ -113,8 +128,11 @@
return
/turf/simulated/wall/proc/update_damage()
- var/cap = damage_cap
- if(rotting)
+ var/cap = material.integrity
+ if(reinf_material)
+ cap += reinf_material.integrity
+
+ if(locate(/obj/effect/overlay/wallrot) in src)
cap = cap / 10
if(damage >= cap)
@@ -124,52 +142,25 @@
return
+/turf/simulated/wall/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume)//Doesn't fucking work because walls don't interact with air :(
+ ignite(exposed_temperature)
+
/turf/simulated/wall/adjacent_fire_act(turf/simulated/floor/adj_turf, datum/gas_mixture/adj_air, adj_temp, adj_volume)
- if(adj_temp > max_temperature)
- take_damage(log(RAND_F(0.9, 1.1) * (adj_temp - max_temperature)))
+ ignite(adj_temp)
+ if(adj_temp > material.melting_point)
+ take_damage(log(RAND_F(0.9, 1.1) * (adj_temp - material.melting_point)))
return ..()
-/turf/simulated/wall/proc/dismantle_wall(devastated=0, explode=0)
- if(istype(src,/turf/simulated/wall/r_wall))
- if(!devastated)
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- new /obj/structure/girder/reinforced(src)
- new /obj/item/stack/sheet/plasteel( src )
- else
- new /obj/item/stack/sheet/metal( src )
- new /obj/item/stack/sheet/metal( src )
- new /obj/item/stack/sheet/plasteel( src )
- else if(istype(src,/turf/simulated/wall/cult))
- if(!devastated)
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- new /obj/effect/decal/cleanable/blood(src)
- new /obj/structure/cultgirder(src)
- else
- new /obj/effect/decal/cleanable/blood(src)
- new /obj/effect/decal/remains/human(src)
+/turf/simulated/wall/proc/dismantle_wall(var/devastated, var/explode, var/no_product)
- else
- if(!devastated)
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- new /obj/structure/girder(src)
- if (mineral == "metal")
- new /obj/item/stack/sheet/metal( src )
- new /obj/item/stack/sheet/metal( src )
- else
- var/M = text2path("/obj/item/stack/sheet/mineral/[mineral]")
- new M( src )
- new M( src )
+ playsound(src, 'sound/items/Welder.ogg', 100, 1)
+ if(!no_product)
+ if(reinf_material)
+ reinf_material.place_dismantled_girder(src, reinf_material)
else
- if (mineral == "metal")
- new /obj/item/stack/sheet/metal( src )
- new /obj/item/stack/sheet/metal( src )
- new /obj/item/stack/sheet/metal( src )
- else
- var/M = text2path("/obj/item/stack/sheet/mineral/[mineral]")
- new M( src )
- new M( src )
- new /obj/item/stack/sheet/metal( src )
+ material.place_dismantled_girder(src)
+ material.place_dismantled_product(src,devastated)
for(var/obj/O in src.contents) //Eject contents!
if(istype(O,/obj/structure/sign/poster))
@@ -178,6 +169,11 @@
else
O.loc = src
+ clear_plants()
+ material = name_to_material["placeholder"]
+ reinf_material = null
+ check_relatives()
+
ChangeTurf(/turf/simulated/floor/plating)
/turf/simulated/wall/ex_act(severity)
@@ -201,24 +197,19 @@
// Wall-rot effect, a nasty fungus that destroys walls.
/turf/simulated/wall/proc/rot()
- if(!rotting)
- rotting = 1
+ if(locate(/obj/effect/overlay/wallrot) in src)
+ return
+ var/number_rots = rand(2,3)
+ for(var/i=0, iThe thermite starts melting through the wall."
spawn(100)
- if(O) del(O)
+ if(O)
+ qdel(O)
// F.sd_LumReset() //TODO: ~Carn
return
/turf/simulated/wall/meteorhit(obj/M as obj)
+ var/rotting = (locate(/obj/effect/overlay/wallrot) in src)
if (prob(15) && !rotting)
dismantle_wall()
else if(prob(70) && !rotting)
@@ -250,232 +243,32 @@
ReplaceWithLattice()
return 0
-/turf/simulated/wall
- var/hulk_destroy_prob = 40
- var/hulk_take_damage = 1
- var/rotting_destroy_touch = 1
- var/rotting_touch_message = "\blue The wall crumbles under your touch."
-
-//Interactions
-/turf/simulated/wall/attack_hand(mob/user as mob)
- if (HULK in user.mutations)
- if (prob(hulk_destroy_prob) || rotting)
- usr << text("\blue You smash through the wall.")
- usr.say(pick(";RAAAAAAAARGH!", ";HNNNNNNNNNGGGGGGH!", ";GWAAAAAAAARRRHHH!", "NNNNNNNNGGGGGGGGHH!", ";AAAAAAARRRGH!" ))
- dismantle_wall(1)
- return 1
- else
- usr << text("\blue You punch the wall.")
- if(hulk_take_damage)
- take_damage(rand(25, 75))
- return 1
-
- if(rotting)
- user << rotting_touch_message
- if(rotting_destroy_touch)
- dismantle_wall()
- return 1
-
- if(..()) return 1
-
- user << "\blue You push the wall but nothing happens!"
- playsound(src, 'sound/weapons/Genhit.ogg', 25, 1)
- src.add_fingerprint(user)
- return 0
-
-/turf/simulated/wall/attack_generic(var/mob/user, var/damage, var/attack_message, var/wallbreaker)
- if(!damage || !wallbreaker)
- user << "You push the wall but nothing happens."
+/turf/simulated/wall/proc/radiate()
+ var/total_radiation = material.radioactivity + (reinf_material ? reinf_material.radioactivity / 2 : 0)
+ if(!total_radiation)
return
- if(rotting || prob(40))
- user << "You smash through the wall!"
- spawn(1) dismantle_wall(1)
- else
- user << "You smash against the wall."
- take_damage(rand(25,75))
- return 1
+ for(var/mob/living/L in range(3,src))
+ L.apply_effect(total_radiation, IRRADIATE,0)
+ return total_radiation
-/turf/simulated/wall/attackby(obj/item/weapon/W as obj, mob/user as mob)
+/turf/simulated/wall/proc/burn(temperature)
+ spawn(2)
+ new /obj/structure/girder(src)
+ src.ChangeTurf(/turf/simulated/floor)
+ for(var/turf/simulated/floor/target_tile in range(0,src))
+ if(material == "phoron") //ergh
+ target_tile.assume_gas("phoron", 20, 400+T0C)
+ spawn (0) target_tile.hotspot_expose(temperature, 400)
+ for(var/turf/simulated/wall/W in range(3,src))
+ W.ignite((temperature/4))
+ for(var/obj/machinery/door/airlock/phoron/D in range(3,src))
+ D.ignite(temperature/4)
- if (!(istype(user, /mob/living/carbon/human) || ticker) && ticker.mode.name != "monkey")
- user << "You don't have the dexterity to do this!"
+/turf/simulated/wall/proc/ignite(var/exposed_temperature)
+ if(isnull(material.ignition_point))
return
-
- //get the user's location
- if( !istype(user.loc, /turf) ) return //can't do this stuff whilst inside objects and such
-
- if(rotting)
- if(istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
- user << "You burn away the fungi with \the [WT]."
- playsound(src, 'sound/items/Welder.ogg', 10, 1)
- for(var/obj/effect/E in src) if(E.name == "Wallrot")
- del E
- rotting = 0
- return
- else if(!is_sharp(W) && W.force >= 10 || W.force >= 20)
- user << "\The [src] crumbles away under the force of your [W.name]."
- src.dismantle_wall(1)
- return
-
- //THERMITE related stuff. Calls src.thermitemelt() which handles melting simulated walls and the relevant effects
- if( thermite )
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
- thermitemelt(user)
- return
-
- else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
- thermitemelt(user)
- return
-
- else if( istype(W, /obj/item/weapon/melee/energy/blade) )
- var/obj/item/weapon/melee/energy/blade/EB = W
-
- EB.spark_system.start()
- user << "You slash \the [src] with \the [EB]; the thermite ignites!"
- playsound(src, "sparks", 50, 1)
- playsound(src, 'sound/weapons/blade1.ogg', 50, 1)
-
- thermitemelt(user)
- return
-
- var/turf/T = user.loc //get user's location for delay checks
-
- //DECONSTRUCTION
- if( istype(W, /obj/item/weapon/weldingtool) )
-
- var/response = "Dismantle"
- if(damage)
- response = alert(user, "Would you like to repair or dismantle [src]?", "[src]", "Repair", "Dismantle")
-
- var/obj/item/weapon/weldingtool/WT = W
-
- if(WT.remove_fuel(0,user))
- if(response == "Repair")
- user << "You start repairing the damage to [src]."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- if(do_after(user, max(5, damage / 5)) && WT && WT.isOn())
- user << "You finish repairing the damage to [src]."
- take_damage(-damage)
-
- else if(response == "Dismantle")
- user << "You begin slicing through the outer plating."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- if(!do_after(user,100))
- return
- if(WT.isOn())
- user << "You remove the outer plating."
- dismantle_wall()
- for(var/mob/O in viewers(user, 5))
- O.show_message("The wall was sliced apart by [user]!", 1, "You hear metal being sliced apart.", 2)
- return
- return
- else
- user << "You need more welding fuel to complete this task."
- return
-
- else if( istype(W, /obj/item/weapon/pickaxe/plasmacutter) )
-
- user << "You begin slicing through the outer plating."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
-
- var/delay = 60
- if(mineral == "diamond")
- delay += 60
-
- if(!do_after(user,delay))
- return
-
- user << "You remove the outer plating."
- dismantle_wall()
- for(var/mob/O in viewers(user, 5))
- O.show_message("The wall was sliced apart by [user]!", 1, "You hear metal being sliced apart.", 2)
+ if(exposed_temperature > material.ignition_point)//If the temperature of the object is over 300, then ignite
+ burn(exposed_temperature)
return
-
- //DRILLING
- else if (istype(W, /obj/item/weapon/pickaxe/diamonddrill))
-
- user << "You begin to drill though the wall."
-
- var/delay = 60
- if(mineral == "diamond")
- delay += 60
-
- if(!do_after(user,delay))
- return
-
- user << "Your drill tears though the last of the reinforced plating."
- dismantle_wall()
- for(var/mob/O in viewers(user, 5))
- O.show_message("The wall was drilled through by [user]!", 1, "You hear the grinding of metal.", 2)
- return
-
- else if( istype(W, /obj/item/weapon/melee/energy/blade) )
- var/obj/item/weapon/melee/energy/blade/EB = W
-
- EB.spark_system.start()
- user << "You stab \the [EB] into the wall and begin to slice it apart."
- playsound(src, "sparks", 50, 1)
-
- sleep(70)
- if(mineral == "diamond")
- sleep(70)
- if( !istype(src, /turf/simulated/wall) || !user || !EB || !T ) return
-
- if( user.loc == T && user.get_active_hand() == W )
- EB.spark_system.start()
- playsound(src, "sparks", 50, 1)
- playsound(src, 'sound/weapons/blade1.ogg', 50, 1)
- dismantle_wall(1)
- for(var/mob/O in viewers(user, 5))
- O.show_message("The wall was sliced apart by [user]!", 1, "You hear metal being sliced apart and sparks flying.", 2)
- return
-
- else if(istype(W,/obj/item/apc_frame))
- var/obj/item/apc_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/alarm_frame))
- var/obj/item/alarm_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/firealarm_frame))
- var/obj/item/firealarm_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/light_fixture_frame))
- var/obj/item/light_fixture_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/light_fixture_frame/small))
- var/obj/item/light_fixture_frame/small/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/rust_fuel_compressor_frame))
- var/obj/item/rust_fuel_compressor_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/rust_fuel_assembly_port_frame))
- var/obj/item/rust_fuel_assembly_port_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/weapon/rcd)) //I bitterly resent having to write this. ~Z
- return
-
- else if(istype(W, /obj/item/weapon/reagent_containers))
- return // They tend to have meaningful afterattack - let them apply it without destroying a rotting wall
-
- else
- return attack_hand(user)
- return
+ ..()
diff --git a/code/game/turfs/simulated/walls_mineral.dm b/code/game/turfs/simulated/walls_mineral.dm
deleted file mode 100644
index 5585de31d87..00000000000
--- a/code/game/turfs/simulated/walls_mineral.dm
+++ /dev/null
@@ -1,130 +0,0 @@
-/turf/simulated/wall/mineral
- name = "mineral wall"
- desc = "This shouldn't exist"
- icon_state = ""
- var/last_event = 0
- var/active = null
-
-/turf/simulated/wall/mineral/gold
- name = "gold wall"
- desc = "A wall with gold plating. Swag!"
- icon_state = "gold0"
- walltype = "gold"
- mineral = "gold"
- //var/electro = 1
- //var/shocked = null
-
-/turf/simulated/wall/mineral/silver
- name = "silver wall"
- desc = "A wall with silver plating. Shiny!"
- icon_state = "silver0"
- walltype = "silver"
- mineral = "silver"
- //var/electro = 0.75
- //var/shocked = null
-
-/turf/simulated/wall/mineral/diamond
- name = "diamond wall"
- desc = "A wall with diamond plating. You monster."
- icon_state = "diamond0"
- walltype = "diamond"
- mineral = "diamond"
-
-/turf/simulated/wall/mineral/sandstone
- name = "sandstone wall"
- desc = "A wall with sandstone plating."
- icon_state = "sandstone0"
- walltype = "sandstone"
- mineral = "sandstone"
-
-/turf/simulated/wall/mineral/uranium
- name = "uranium wall"
- desc = "A wall with uranium plating. This is probably a bad idea."
- icon_state = "uranium0"
- walltype = "uranium"
- mineral = "uranium"
-
-/turf/simulated/wall/mineral/uranium/proc/radiate()
- if(!active)
- if(world.time > last_event+15)
- active = 1
- for(var/mob/living/L in range(3,src))
- L.apply_effect(12,IRRADIATE,0)
- for(var/turf/simulated/wall/mineral/uranium/T in range(3,src))
- T.radiate()
- last_event = world.time
- active = null
- return
- return
-
-/turf/simulated/wall/mineral/uranium/attack_hand(mob/user as mob)
- radiate()
- ..()
-
-/turf/simulated/wall/mineral/uranium/attackby(obj/item/weapon/W as obj, mob/user as mob)
- radiate()
- ..()
-
-/turf/simulated/wall/mineral/uranium/Bumped(AM as mob|obj)
- radiate()
- ..()
-
-/turf/simulated/wall/mineral/phoron
- name = "phoron wall"
- desc = "A wall with phoron plating. This is definately a bad idea."
- icon_state = "phoron0"
- walltype = "phoron"
- mineral = "phoron"
-
-/turf/simulated/wall/mineral/phoron/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if(is_hot(W) > 300)//If the temperature of the object is over 300, then ignite
- ignite(is_hot(W))
- return
- ..()
-
-/turf/simulated/wall/mineral/phoron/proc/PhoronBurn(temperature)
- spawn(2)
- new /obj/structure/girder(src)
- src.ChangeTurf(/turf/simulated/floor)
- for(var/turf/simulated/floor/target_tile in range(0,src))
- target_tile.assume_gas("phoron", 20, 400+T0C)
- spawn (0) target_tile.hotspot_expose(temperature, 400)
- for(var/obj/structure/falsewall/phoron/F in range(3,src))//Hackish as fuck, but until temperature_expose works, there is nothing I can do -Sieve
- var/turf/T = get_turf(F)
- T.ChangeTurf(/turf/simulated/wall/mineral/phoron/)
- del (F)
- for(var/turf/simulated/wall/mineral/phoron/W in range(3,src))
- W.ignite((temperature/4))//Added so that you can't set off a massive chain reaction with a small flame
- for(var/obj/machinery/door/airlock/phoron/D in range(3,src))
- D.ignite(temperature/4)
-
-/turf/simulated/wall/mineral/phoron/fire_act(datum/gas_mixture/air, exposed_temperature, exposed_volume)//Doesn't fucking work because walls don't interact with air :(
- if(exposed_temperature > 300)
- PhoronBurn(exposed_temperature)
-
-/turf/simulated/wall/mineral/phoron/proc/ignite(exposed_temperature)
- if(exposed_temperature > 300)
- PhoronBurn(exposed_temperature)
-
-/turf/simulated/wall/mineral/phoron/bullet_act(var/obj/item/projectile/Proj)
- if(istype(Proj,/obj/item/projectile/beam))
- PhoronBurn(2500)
- else if(istype(Proj,/obj/item/projectile/ion))
- PhoronBurn(500)
- ..()
-
-/*
-/turf/simulated/wall/mineral/proc/shock()
- if (electrocute_mob(user, C, src))
- var/datum/effect/effect/system/spark_spread/s = new /datum/effect/effect/system/spark_spread
- s.set_up(5, 1, src)
- s.start()
- return 1
- else
- return 0
-
-/turf/simulated/wall/mineral/proc/attackby(obj/item/weapon/W as obj, mob/user as mob)
- if((mineral == "gold") || (mineral == "silver"))
- if(shocked)
- shock()
-*/
diff --git a/code/game/turfs/simulated/walls_misc.dm b/code/game/turfs/simulated/walls_misc.dm
deleted file mode 100644
index b1a06f6e88a..00000000000
--- a/code/game/turfs/simulated/walls_misc.dm
+++ /dev/null
@@ -1,5 +0,0 @@
-/turf/simulated/wall/cult
- name = "wall"
- desc = "The patterns engraved on the wall seem to shift as you try to focus on them. You feel sick"
- icon_state = "cult"
- walltype = "cult"
\ No newline at end of file
diff --git a/code/game/turfs/simulated/walls_reinforced.dm b/code/game/turfs/simulated/walls_reinforced.dm
deleted file mode 100644
index 497371eb5f6..00000000000
--- a/code/game/turfs/simulated/walls_reinforced.dm
+++ /dev/null
@@ -1,307 +0,0 @@
-/turf/simulated/wall/r_wall
- name = "reinforced wall"
- desc = "A huge chunk of reinforced metal used to seperate rooms."
- icon_state = "r_wall"
- opacity = 1
- density = 1
-
- damage_cap = 800
- max_temperature = 6000
-
- walltype = "rwall"
-
- var/d_state = 0
-
-/turf/simulated/wall/r_wall
- hulk_destroy_prob = 10
- hulk_take_damage = 0
- rotting_destroy_touch = 0
- rotting_touch_message = "\blue This wall feels rather unstable."
-
-/turf/simulated/wall/r_wall/attack_generic(var/mob/user, var/damage, var/attack_message, var/wallbreaker)
- if(!rotting && wallbreaker < 2)
- user << "You push the wall but nothing happens."
- return
-
- return ..()
-
-/turf/simulated/wall/r_wall/attackby(obj/item/W as obj, mob/user as mob)
-
- if (!(istype(user, /mob/living/carbon/human) || ticker) && ticker.mode.name != "monkey")
- user << "You don't have the dexterity to do this!"
- return
-
- //get the user's location
- if( !istype(user.loc, /turf) ) return //can't do this stuff whilst inside objects and such
-
- if(rotting)
- if(istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
- user << "You burn away the fungi with \the [WT]."
- playsound(src, 'sound/items/Welder.ogg', 10, 1)
- for(var/obj/effect/E in src) if(E.name == "Wallrot")
- del E
- rotting = 0
- return
- else if(!is_sharp(W) && W.force >= 10 || W.force >= 20)
- user << "\The [src] crumbles away under the force of your [W.name]."
- src.dismantle_wall()
- return
-
- //THERMITE related stuff. Calls src.thermitemelt() which handles melting simulated walls and the relevant effects
- if( thermite )
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
- thermitemelt(user)
- return
-
- else if(istype(W, /obj/item/weapon/pickaxe/plasmacutter))
- thermitemelt(user)
- return
-
- else if( istype(W, /obj/item/weapon/melee/energy/blade) )
- var/obj/item/weapon/melee/energy/blade/EB = W
-
- EB.spark_system.start()
- user << "You slash \the [src] with \the [EB]; the thermite ignites!"
- playsound(src, "sparks", 50, 1)
- playsound(src, 'sound/weapons/blade1.ogg', 50, 1)
-
- thermitemelt(user)
- return
-
- else if(istype(W, /obj/item/weapon/melee/energy/blade))
- user << "This wall is too thick to slice through. You will need to find a different path."
- return
-
- if(damage && istype(W, /obj/item/weapon/weldingtool))
- var/obj/item/weapon/weldingtool/WT = W
- if(WT.remove_fuel(0,user))
- user << "You start repairing the damage to [src]."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- if(do_after(user, max(5, damage / 5)) && WT && WT.isOn())
- user << "You finish repairing the damage to [src]."
- take_damage(-damage)
- return
- else
- user << "You need more welding fuel to complete this task."
- return
-
- var/turf/T = user.loc //get user's location for delay checks
-
- //DECONSTRUCTION
- switch(d_state)
- if(0)
- if (istype(W, /obj/item/weapon/wirecutters))
- playsound(src, 'sound/items/Wirecutter.ogg', 100, 1)
- src.d_state = 1
- src.icon_state = "r_wall-1"
- new /obj/item/stack/rods( src )
- user << "You cut the outer grille."
- return
-
- if(1)
- if (istype(W, /obj/item/weapon/screwdriver))
- user << "You begin removing the support lines."
- playsound(src, 'sound/items/Screwdriver.ogg', 100, 1)
-
- sleep(40)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( d_state == 1 && user.loc == T && user.get_active_hand() == W )
- src.d_state = 2
- src.icon_state = "r_wall-2"
- user << "You remove the support lines."
- return
-
- //REPAIRING (replacing the outer grille for cosmetic damage)
- else if( istype(W, /obj/item/stack/rods) )
- var/obj/item/stack/O = W
- src.d_state = 0
- src.icon_state = "r_wall"
- relativewall_neighbours() //call smoothwall stuff
- user << "You replace the outer grille."
- if (O.amount > 1)
- O.amount--
- else
- del(O)
- return
-
- if(2)
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
-
- user << "You begin slicing through the metal cover."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
-
- sleep(60)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !WT || !WT.isOn() || !T ) return
-
- if( d_state == 2 && user.loc == T && user.get_active_hand() == WT )
- src.d_state = 3
- src.icon_state = "r_wall-3"
- user << "You press firmly on the cover, dislodging it."
- else
- user << "You need more welding fuel to complete this task."
- return
-
- if( istype(W, /obj/item/weapon/pickaxe/plasmacutter) )
-
- user << "You begin slicing through the metal cover."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
-
- sleep(40)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( d_state == 2 && user.loc == T && user.get_active_hand() == W )
- src.d_state = 3
- src.icon_state = "r_wall-3"
- user << "You press firmly on the cover, dislodging it."
- return
-
- if(3)
- if (istype(W, /obj/item/weapon/crowbar))
-
- user << "You struggle to pry off the cover."
- playsound(src, 'sound/items/Crowbar.ogg', 100, 1)
-
- sleep(100)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( d_state == 3 && user.loc == T && user.get_active_hand() == W )
- src.d_state = 4
- src.icon_state = "r_wall-4"
- user << "You pry off the cover."
- return
-
- if(4)
- if (istype(W, /obj/item/weapon/wrench))
-
- user << "You start loosening the anchoring bolts which secure the support rods to their frame."
- playsound(src, 'sound/items/Ratchet.ogg', 100, 1)
-
- sleep(40)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( d_state == 4 && user.loc == T && user.get_active_hand() == W )
- src.d_state = 5
- src.icon_state = "r_wall-5"
- user << "You remove the bolts anchoring the support rods."
- return
-
- if(5)
- if( istype(W, /obj/item/weapon/weldingtool) )
- var/obj/item/weapon/weldingtool/WT = W
- if( WT.remove_fuel(0,user) )
-
- user << "You begin slicing through the support rods."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
-
- sleep(100)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !WT || !WT.isOn() || !T ) return
-
- if( d_state == 5 && user.loc == T && user.get_active_hand() == WT )
- src.d_state = 6
- src.icon_state = "r_wall-6"
- new /obj/item/stack/rods( src )
- user << "The support rods drop out as you cut them loose from the frame."
- else
- user << "You need more welding fuel to complete this task."
- return
-
- if( istype(W, /obj/item/weapon/pickaxe/plasmacutter) )
-
- user << "You begin slicing through the support rods."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
-
- sleep(70)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( d_state == 5 && user.loc == T && user.get_active_hand() == W )
- src.d_state = 6
- src.icon_state = "r_wall-6"
- new /obj/item/stack/rods( src )
- user << "The support rods drop out as you cut them loose from the frame."
- return
-
- if(6)
- if( istype(W, /obj/item/weapon/crowbar) )
-
- user << "You struggle to pry off the outer sheath."
- playsound(src, 'sound/items/Crowbar.ogg', 100, 1)
-
- sleep(100)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( user.loc == T && user.get_active_hand() == W )
- user << "You pry off the outer sheath."
- dismantle_wall()
- return
-
-//vv OK, we weren't performing a valid deconstruction step or igniting thermite,let's check the other possibilities vv
-
- //DRILLING
- if (istype(W, /obj/item/weapon/pickaxe/diamonddrill))
-
- user << "You begin to drill though the wall."
-
- sleep(200)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !W || !T ) return
-
- if( user.loc == T && user.get_active_hand() == W )
- user << "Your drill tears though the last of the reinforced plating."
- dismantle_wall()
-
- //REPAIRING
- else if( istype(W, /obj/item/stack/sheet/metal) && d_state )
- var/obj/item/stack/sheet/metal/MS = W
-
- user << "You begin patching-up the wall with \a [MS]."
-
- sleep( max(20*d_state,100) ) //time taken to repair is proportional to the damage! (max 10 seconds)
- if( !istype(src, /turf/simulated/wall/r_wall) || !user || !MS || !T ) return
-
- if( user.loc == T && user.get_active_hand() == MS && d_state )
- src.d_state = 0
- src.icon_state = "r_wall"
- relativewall_neighbours() //call smoothwall stuff
- user << "You repair the last of the damage."
- if (MS.amount > 1)
- MS.amount--
- else
- del(MS)
-
- //APC
- else if( istype(W,/obj/item/apc_frame) )
- var/obj/item/apc_frame/AH = W
- AH.try_build(src)
-
- else if( istype(W,/obj/item/alarm_frame) )
- var/obj/item/alarm_frame/AH = W
- AH.try_build(src)
-
- else if(istype(W,/obj/item/firealarm_frame))
- var/obj/item/firealarm_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/light_fixture_frame))
- var/obj/item/light_fixture_frame/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W,/obj/item/light_fixture_frame/small))
- var/obj/item/light_fixture_frame/small/AH = W
- AH.try_build(src)
- return
-
- else if(istype(W, /obj/item/weapon/reagent_containers))
- return // They tend to have meaningful afterattack - let them apply it without destroying a rotting wall
-
- //Finally, CHECKING FOR FALSE WALLS if it isn't damaged
- else if(!d_state)
- return attack_hand(user)
- return
\ No newline at end of file
diff --git a/code/game/turfs/space/space.dm b/code/game/turfs/space/space.dm
index 884c5c5dbe9..d8db07de58f 100644
--- a/code/game/turfs/space/space.dm
+++ b/code/game/turfs/space/space.dm
@@ -6,6 +6,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
icon = 'icons/turf/space.dmi'
name = "\proper space"
icon_state = "0"
+ dynamic_lighting = 0
temperature = T20C
thermal_conductivity = OPEN_HEAT_TRANSFER_COEFFICIENT
@@ -20,9 +21,9 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
if(!config.starlight)
return
if(locate(/turf/simulated) in orange(src,1))
- SetLuminosity(config.starlight)
+ set_light(config.starlight)
else
- SetLuminosity(0)
+ set_light(0)
/turf/space/attackby(obj/item/C as obj, mob/user as mob)
@@ -43,7 +44,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
var/obj/item/stack/tile/plasteel/S = C
if (S.get_amount() < 1)
return
- del(L)
+ qdel(L)
playsound(src, 'sound/weapons/Genhit.ogg', 50, 1)
S.build(src)
S.use(1)
@@ -69,11 +70,11 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
if(A.z > 6 && !config.use_overmap) return
if (A.x <= TRANSITIONEDGE || A.x >= (world.maxx - TRANSITIONEDGE - 1) || A.y <= TRANSITIONEDGE || A.y >= (world.maxy - TRANSITIONEDGE - 1))
if(istype(A, /obj/effect/meteor)||istype(A, /obj/effect/space_dust))
- del(A)
+ qdel(A)
return
if(istype(A, /obj/item/weapon/disk/nuclear)) // Don't let nuke disks travel Z levels ... And moving this shit down here so it only fires when they're actually trying to change z-level.
- del(A) //The disk's Del() proc ensures a new one is created
+ qdel(A) //The disk's Destroy() proc ensures a new one is created
return
if(config.use_overmap)
overmap_spacetravel(src,A)
@@ -94,10 +95,10 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
MM.inertia_dir = 2
else
for(var/obj/item/weapon/disk/nuclear/N in disk_search)
- del(N)//Make the disk respawn it is on a clientless mob or corpse
+ qdel(N)//Make the disk respawn it is on a clientless mob or corpse
else
for(var/obj/item/weapon/disk/nuclear/N in disk_search)
- del(N)//Make the disk respawn if it is floating on its own
+ qdel(N)//Make the disk respawn if it is floating on its own
return
var/move_to_z = src.z
@@ -148,7 +149,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
if(src.x <= 1)
if(istype(A, /obj/effect/meteor)||istype(A, /obj/effect/space_dust))
- del(A)
+ qdel(A)
return
var/list/cur_pos = src.get_global_map_pos()
@@ -173,7 +174,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
A.loc.Entered(A)
else if (src.x >= world.maxx)
if(istype(A, /obj/effect/meteor))
- del(A)
+ qdel(A)
return
var/list/cur_pos = src.get_global_map_pos()
@@ -198,7 +199,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
A.loc.Entered(A)
else if (src.y <= 1)
if(istype(A, /obj/effect/meteor))
- del(A)
+ qdel(A)
return
var/list/cur_pos = src.get_global_map_pos()
if(!cur_pos) return
@@ -223,7 +224,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
else if (src.y >= world.maxy)
if(istype(A, /obj/effect/meteor)||istype(A, /obj/effect/space_dust))
- del(A)
+ qdel(A)
return
var/list/cur_pos = src.get_global_map_pos()
if(!cur_pos) return
@@ -245,4 +246,7 @@ var/list/accessible_z_levels = list("1" = 5, "3" = 10, "4" = 15, "5" = 10, "6" =
spawn (0)
if ((A && A.loc))
A.loc.Entered(A)
- return
\ No newline at end of file
+ return
+
+/turf/space/ChangeTurf(var/turf/N, var/tell_universe=1, var/force_lighting_update = 0)
+ return ..(N, tell_universe, 1)
diff --git a/code/game/turfs/turf.dm b/code/game/turfs/turf.dm
index 29f425d4a3a..e5ae4e1bb9a 100644
--- a/code/game/turfs/turf.dm
+++ b/code/game/turfs/turf.dm
@@ -26,6 +26,14 @@
var/has_resources
var/list/resources
+ // Flick animation
+ var/atom/movable/overlay/c_animation = null
+
+ // holy water
+ var/holy = 0
+
+ var/dynamic_lighting = 1
+
/turf/New()
..()
for(var/atom/movable/AM as mob|obj in src)
@@ -191,10 +199,10 @@
/turf/proc/RemoveLattice()
var/obj/structure/lattice/L = locate(/obj/structure/lattice, src)
if(L)
- del L
+ qdel(L)
//Creates a new turf
-/turf/proc/ChangeTurf(var/turf/N)
+/turf/proc/ChangeTurf(var/turf/N, var/tell_universe=1, var/force_lighting_update = 0)
if (!N)
return
@@ -212,8 +220,10 @@
return W
///// Z-Level Stuff
- var/old_lumcount = lighting_lumcount - initial(lighting_lumcount)
var/obj/fire/old_fire = fire
+ var/old_opacity = opacity
+ var/old_dynamic_lighting = dynamic_lighting
+ var/list/old_affecting_lights = affecting_lights
//world << "Replacing [src.type] with [N]"
@@ -227,51 +237,35 @@
if(S.zone) S.zone.rebuild()
if(ispath(N, /turf/simulated/floor))
- //if the old turf had a zone, connect the new turf to it as well - Cael
- //Adjusted by SkyMarshal 5/10/13 - The air master will handle the addition of the new turf.
- //if(zone)
- // zone.RemoveTurf(src)
- // if(!zone.CheckStatus())
- // zone.SetStatus(ZONE_ACTIVE)
-
var/turf/simulated/W = new N( locate(src.x, src.y, src.z) )
- //W.Assimilate_Air()
-
- W.lighting_lumcount += old_lumcount
-
- if(W.lighting_lumcount)
- W.UpdateAffectingLights()
-
if(old_fire)
fire = old_fire
if (istype(W,/turf/simulated/floor))
W.RemoveLattice()
+ if(tell_universe)
+ universe.OnTurfChange(W)
+
if(air_master)
- air_master.mark_for_update(src)
+ air_master.mark_for_update(src) //handle the addition of the new turf.
for(var/turf/space/S in range(W,1))
S.update_starlight()
W.levelupdate()
- return W
+ . = W
else
- //if(zone)
- // zone.RemoveTurf(src)
- // if(!zone.CheckStatus())
- // zone.SetStatus(ZONE_ACTIVE)
var/turf/W = new N( locate(src.x, src.y, src.z) )
- W.lighting_lumcount += old_lumcount
- if(old_lumcount != W.lighting_lumcount)
- W.lighting_changed = 1
- lighting_controller.changed_turfs += W
if(old_fire)
old_fire.RemoveFire()
+ if(tell_universe)
+ universe.OnTurfChange(W)
+
if(air_master)
air_master.mark_for_update(src)
@@ -279,7 +273,16 @@
S.update_starlight()
W.levelupdate()
- return W
+ . = W
+
+ affecting_lights = old_affecting_lights
+ if((old_opacity != opacity) || (dynamic_lighting != old_dynamic_lighting) || force_lighting_update)
+ reconsider_lights()
+ if(dynamic_lighting != old_dynamic_lighting)
+ if(dynamic_lighting)
+ lighting_build_overlays()
+ else
+ lighting_clear_overlays()
//Commented out by SkyMarshal 5/10/13 - If you are patching up space, it should be vacuum.
@@ -336,7 +339,8 @@
/turf/proc/ReplaceWithLattice()
src.ChangeTurf(/turf/space)
- new /obj/structure/lattice( locate(src.x, src.y, src.z) )
+ spawn()
+ new /obj/structure/lattice( locate(src.x, src.y, src.z) )
/turf/proc/kill_creatures(mob/U = null)//Will kill people/creatures and damage mechs./N
//Useful to batch-add creatures to the list.
@@ -374,3 +378,6 @@
if(!LinkBlocked(src, t) && !TurfBlockedNonWindow(t))
L.Add(t)
return L
+
+/turf/proc/process()
+ return PROCESS_KILL
diff --git a/code/game/turfs/turf_flick_animations.dm b/code/game/turfs/turf_flick_animations.dm
new file mode 100644
index 00000000000..b1bccd51bcd
--- /dev/null
+++ b/code/game/turfs/turf_flick_animations.dm
@@ -0,0 +1,21 @@
+/turf/proc/turf_animation(var/anim_icon,var/anim_state,var/anim_x=0, var/anim_y=0, var/anim_layer=MOB_LAYER+1, var/anim_sound=null, var/anim_color=null)
+ if(!c_animation)//spamming turf animations can have unintended effects, such as the overlays never disapearing. hence this check.
+ if(anim_sound)
+ playsound(src, anim_sound, 50, 1)
+ c_animation = PoolOrNew(/atom/movable/overlay, src)
+ c_animation.name = "turf_animation"
+ c_animation.density = 0
+ c_animation.anchored = 1
+ c_animation.icon = anim_icon
+ c_animation.icon_state = anim_state
+ c_animation.layer = anim_layer
+ c_animation.master = src
+ c_animation.pixel_x = anim_x
+ c_animation.pixel_y = anim_y
+ if(anim_color)
+ c_animation.color = anim_color
+ flick("turf_animation",c_animation)
+ spawn(10)
+ if(c_animation)
+ qdel(c_animation)
+ c_animation = null
diff --git a/code/game/vehicles/vehicle.dm b/code/game/vehicles/vehicle.dm
index 3ec73f3eeb9..4088528b35f 100644
--- a/code/game/vehicles/vehicle.dm
+++ b/code/game/vehicles/vehicle.dm
@@ -1,190 +1,190 @@
-
-
-/obj/vehicle
- name = "Vehicle"
- icon = 'icons/vehicles/vehicles.dmi'
- density = 1
- anchored = 1
- unacidable = 1 //To avoid the pilot-deleting shit that came with mechas
- layer = MOB_LAYER
- //var/can_move = 1
- var/mob/living/carbon/occupant = null
- //var/step_in = 10 //make a step in step_in/10 sec.
- //var/dir_in = 2//What direction will the mech face when entered/powered on? Defaults to South.
- //var/step_energy_drain = 10
- var/health = 300 //health is health
- //var/deflect_chance = 10 //chance to deflect the incoming projectiles, hits, or lesser the effect of ex_act.
- //the values in this list show how much damage will pass through, not how much will be absorbed.
- var/list/damage_absorption = list("brute"=0.8,"fire"=1.2,"bullet"=0.9,"laser"=1,"energy"=1,"bomb"=1)
- var/obj/item/weapon/cell/cell //Our power source
- var/state = 0
- var/list/log = new
- var/last_message = 0
- var/add_req_access = 1
- var/maint_access = 1
- //var/dna //dna-locking the mech
- var/list/proc_res = list() //stores proc owners, like proc_res["functionname"] = owner reference
- var/datum/effect/effect/system/spark_spread/spark_system = new
- var/lights = 0
- var/lights_power = 6
-
- //inner atmos //These go in airtight.dm, not all vehicles are space-faring -Agouri
- //var/use_internal_tank = 0
- //var/internal_tank_valve = ONE_ATMOSPHERE
- //var/obj/machinery/portable_atmospherics/canister/internal_tank
- //var/datum/gas_mixture/cabin_air
- //var/obj/machinery/atmospherics/portables_connector/connected_port = null
-
- var/obj/item/device/radio/radio = null
-
- var/max_temperature = 2500
- //var/internal_damage_threshold = 50 //health percentage below which internal damage is possible
- var/internal_damage = 0 //contains bitflags
-
- var/list/operation_req_access = list()//required access level for mecha operation
- var/list/internals_req_access = list(access_engine,access_robotics)//required access level to open cell compartment
-
- //var/datum/global_iterator/pr_int_temp_processor //normalizes internal air mixture temperature //In airtight.dm you go -Agouri
- var/datum/global_iterator/pr_inertial_movement //controls intertial movement in spesss
-
- //var/datum/global_iterator/pr_give_air //moves air from tank to cabin //Y-you too -Agouri
-
- var/datum/global_iterator/pr_internal_damage //processes internal damage
-
-
- var/wreckage
-
- var/list/equipment = new
- var/obj/selected
- //var/max_equip = 3
-
- var/datum/events/events
-
-
-
-/obj/vehicle/New()
- ..()
- events = new
- icon_state += "-unmanned"
- add_radio()
- //add_cabin() //No cabin for non-airtights
-
- spark_system.set_up(2, 0, src)
- spark_system.attach(src)
- add_cell()
- add_iterators()
- removeVerb(/obj/mecha/verb/disconnect_from_port)
- removeVerb(/atom/movable/verb/pull)
- log_message("[src.name]'s functions initialised. Work protocols active - Entering IDLE mode.")
- loc.Entered(src)
- return
-
-
-//################ Helpers ###########################################################
-
-
-/obj/vehicle/proc/removeVerb(verb_path)
- verbs -= verb_path
-
-/obj/vehicle/proc/addVerb(verb_path)
- verbs += verb_path
-
-/*/obj/vehicle/proc/add_airtank() //In airtight.dm -Agouri
- internal_tank = new /obj/machinery/portable_atmospherics/canister/air(src)
- return internal_tank*/
-
-/obj/vehicle/proc/add_cell(var/obj/item/weapon/cell/C=null)
- if(C)
- C.forceMove(src)
- cell = C
- return
- cell = new(src)
- cell.charge = 15000
- cell.maxcharge = 15000
-
-/*/obj/vehicle/proc/add_cabin() //In airtight.dm -Agouri
- cabin_air = new
- cabin_air.temperature = T20C
- cabin_air.volume = 200
- cabin_air.oxygen = O2STANDARD*cabin_air.volume/(R_IDEAL_GAS_EQUATION*cabin_air.temperature)
- cabin_air.nitrogen = N2STANDARD*cabin_air.volume/(R_IDEAL_GAS_EQUATION*cabin_air.temperature)
- return cabin_air*/
-
-/obj/vehicle/proc/add_radio()
- radio = new(src)
- radio.name = "[src] radio"
- radio.icon = icon
- radio.icon_state = icon_state
- radio.subspace_transmission = 1
-
-/obj/vehicle/proc/add_iterators()
- pr_inertial_movement = new /datum/global_iterator/vehicle_intertial_movement(null,0)
- //pr_internal_damage = new /datum/global_iterator/vehicle_internal_damage(list(src),0)
- //pr_int_temp_processor = new /datum/global_iterator/vehicle_preserve_temp(list(src)) //In airtight.dm's add_airtight_iterators -Agouri
- //pr_give_air = new /datum/global_iterator/vehicle_tank_give_air(list(src) //Same here -Agouri
-
-/obj/vehicle/proc/check_for_support()
- if(locate(/obj/structure/grille, orange(1, src)) || locate(/obj/structure/lattice, orange(1, src)) || locate(/turf/simulated, orange(1, src)) || locate(/turf/unsimulated, orange(1, src)))
- return 1
- else
- return 0
-
-//################ Logs and messages ############################################
-
-
-/obj/vehicle/proc/log_message(message as text,red=null)
- log.len++
- log[log.len] = list("time"=world.timeofday,"message"="[red?"":null][message][red?"":null]")
- return log.len
-
-
-
-//################ Global Iterator Datums ######################################
-
-
-/datum/global_iterator/vehicle_intertial_movement //inertial movement in space
- delay = 7
-
- process(var/obj/vehicle/V as obj, direction)
- if(direction)
- if(!step(V, direction)||V.check_for_support())
- src.stop()
- else
- src.stop()
- return
-
-
-/datum/global_iterator/mecha_internal_damage // processing internal damage
-
- process(var/obj/mecha/mecha)
- if(!mecha.hasInternalDamage())
- return stop()
- if(mecha.hasInternalDamage(MECHA_INT_FIRE))
- if(!mecha.hasInternalDamage(MECHA_INT_TEMP_CONTROL) && prob(5))
- mecha.clearInternalDamage(MECHA_INT_FIRE)
- if(mecha.internal_tank)
- if(mecha.internal_tank.return_pressure()>mecha.internal_tank.maximum_pressure && !(mecha.hasInternalDamage(MECHA_INT_TANK_BREACH)))
- mecha.setInternalDamage(MECHA_INT_TANK_BREACH)
- var/datum/gas_mixture/int_tank_air = mecha.internal_tank.return_air()
- if(int_tank_air && int_tank_air.return_volume()>0) //heat the air_contents
- int_tank_air.temperature = min(6000+T0C, int_tank_air.temperature+rand(10,15))
- if(mecha.cabin_air && mecha.cabin_air.return_volume()>0)
- mecha.cabin_air.temperature = min(6000+T0C, mecha.cabin_air.return_temperature()+rand(10,15))
- if(mecha.cabin_air.return_temperature()>mecha.max_temperature/2)
- mecha.take_damage(4/round(mecha.max_temperature/mecha.cabin_air.return_temperature(),0.1),"fire")
- if(mecha.hasInternalDamage(MECHA_INT_TEMP_CONTROL)) //stop the mecha_preserve_temp loop datum
- mecha.pr_int_temp_processor.stop()
- if(mecha.hasInternalDamage(MECHA_INT_TANK_BREACH)) //remove some air from internal tank
- if(mecha.internal_tank)
- var/datum/gas_mixture/int_tank_air = mecha.internal_tank.return_air()
- var/datum/gas_mixture/leaked_gas = int_tank_air.remove_ratio(0.10)
- if(mecha.loc && hascall(mecha.loc,"assume_air"))
- mecha.loc.assume_air(leaked_gas)
- else
- del(leaked_gas)
- if(mecha.hasInternalDamage(MECHA_INT_SHORT_CIRCUIT))
- if(mecha.get_charge())
- mecha.spark_system.start()
- mecha.cell.charge -= min(20,mecha.cell.charge)
- mecha.cell.maxcharge -= min(20,mecha.cell.maxcharge)
+
+
+/obj/vehicle
+ name = "Vehicle"
+ icon = 'icons/vehicles/vehicles.dmi'
+ density = 1
+ anchored = 1
+ unacidable = 1 //To avoid the pilot-deleting shit that came with mechas
+ layer = MOB_LAYER
+ //var/can_move = 1
+ var/mob/living/carbon/occupant = null
+ //var/step_in = 10 //make a step in step_in/10 sec.
+ //var/dir_in = 2//What direction will the mech face when entered/powered on? Defaults to South.
+ //var/step_energy_drain = 10
+ var/health = 300 //health is health
+ //var/deflect_chance = 10 //chance to deflect the incoming projectiles, hits, or lesser the effect of ex_act.
+ //the values in this list show how much damage will pass through, not how much will be absorbed.
+ var/list/damage_absorption = list("brute"=0.8,"fire"=1.2,"bullet"=0.9,"laser"=1,"energy"=1,"bomb"=1)
+ var/obj/item/weapon/cell/cell //Our power source
+ var/state = 0
+ var/list/log = new
+ var/last_message = 0
+ var/add_req_access = 1
+ var/maint_access = 1
+ //var/dna //dna-locking the mech
+ var/list/proc_res = list() //stores proc owners, like proc_res["functionname"] = owner reference
+ var/datum/effect/effect/system/spark_spread/spark_system = new
+ var/lights = 0
+ var/lights_power = 6
+
+ //inner atmos //These go in airtight.dm, not all vehicles are space-faring -Agouri
+ //var/use_internal_tank = 0
+ //var/internal_tank_valve = ONE_ATMOSPHERE
+ //var/obj/machinery/portable_atmospherics/canister/internal_tank
+ //var/datum/gas_mixture/cabin_air
+ //var/obj/machinery/atmospherics/portables_connector/connected_port = null
+
+ var/obj/item/device/radio/radio = null
+
+ var/max_temperature = 2500
+ //var/internal_damage_threshold = 50 //health percentage below which internal damage is possible
+ var/internal_damage = 0 //contains bitflags
+
+ var/list/operation_req_access = list()//required access level for mecha operation
+ var/list/internals_req_access = list(access_engine,access_robotics)//required access level to open cell compartment
+
+ //var/datum/global_iterator/pr_int_temp_processor //normalizes internal air mixture temperature //In airtight.dm you go -Agouri
+ var/datum/global_iterator/pr_inertial_movement //controls intertial movement in spesss
+
+ //var/datum/global_iterator/pr_give_air //moves air from tank to cabin //Y-you too -Agouri
+
+ var/datum/global_iterator/pr_internal_damage //processes internal damage
+
+
+ var/wreckage
+
+ var/list/equipment = new
+ var/obj/selected
+ //var/max_equip = 3
+
+ var/datum/events/events
+
+
+
+/obj/vehicle/New()
+ ..()
+ events = new
+ icon_state += "-unmanned"
+ add_radio()
+ //add_cabin() //No cabin for non-airtights
+
+ spark_system.set_up(2, 0, src)
+ spark_system.attach(src)
+ add_cell()
+ add_iterators()
+ removeVerb(/obj/mecha/verb/disconnect_from_port)
+ removeVerb(/atom/movable/verb/pull)
+ log_message("[src.name]'s functions initialised. Work protocols active - Entering IDLE mode.")
+ loc.Entered(src)
+ return
+
+
+//################ Helpers ###########################################################
+
+
+/obj/vehicle/proc/removeVerb(verb_path)
+ verbs -= verb_path
+
+/obj/vehicle/proc/addVerb(verb_path)
+ verbs += verb_path
+
+/*/obj/vehicle/proc/add_airtank() //In airtight.dm -Agouri
+ internal_tank = new /obj/machinery/portable_atmospherics/canister/air(src)
+ return internal_tank*/
+
+/obj/vehicle/proc/add_cell(var/obj/item/weapon/cell/C=null)
+ if(C)
+ C.forceMove(src)
+ cell = C
+ return
+ cell = new(src)
+ cell.charge = 15000
+ cell.maxcharge = 15000
+
+/*/obj/vehicle/proc/add_cabin() //In airtight.dm -Agouri
+ cabin_air = new
+ cabin_air.temperature = T20C
+ cabin_air.volume = 200
+ cabin_air.oxygen = O2STANDARD*cabin_air.volume/(R_IDEAL_GAS_EQUATION*cabin_air.temperature)
+ cabin_air.nitrogen = N2STANDARD*cabin_air.volume/(R_IDEAL_GAS_EQUATION*cabin_air.temperature)
+ return cabin_air*/
+
+/obj/vehicle/proc/add_radio()
+ radio = new(src)
+ radio.name = "[src] radio"
+ radio.icon = icon
+ radio.icon_state = icon_state
+ radio.subspace_transmission = 1
+
+/obj/vehicle/proc/add_iterators()
+ pr_inertial_movement = new /datum/global_iterator/vehicle_intertial_movement(null,0)
+ //pr_internal_damage = new /datum/global_iterator/vehicle_internal_damage(list(src),0)
+ //pr_int_temp_processor = new /datum/global_iterator/vehicle_preserve_temp(list(src)) //In airtight.dm's add_airtight_iterators -Agouri
+ //pr_give_air = new /datum/global_iterator/vehicle_tank_give_air(list(src) //Same here -Agouri
+
+/obj/vehicle/proc/check_for_support()
+ if(locate(/obj/structure/grille, orange(1, src)) || locate(/obj/structure/lattice, orange(1, src)) || locate(/turf/simulated, orange(1, src)) || locate(/turf/unsimulated, orange(1, src)))
+ return 1
+ else
+ return 0
+
+//################ Logs and messages ############################################
+
+
+/obj/vehicle/proc/log_message(message as text,red=null)
+ log.len++
+ log[log.len] = list("time"=world.timeofday,"message"="[red?"":null][message][red?"":null]")
+ return log.len
+
+
+
+//################ Global Iterator Datums ######################################
+
+
+/datum/global_iterator/vehicle_intertial_movement //inertial movement in space
+ delay = 7
+
+ process(var/obj/vehicle/V as obj, direction)
+ if(direction)
+ if(!step(V, direction)||V.check_for_support())
+ src.stop()
+ else
+ src.stop()
+ return
+
+
+/datum/global_iterator/mecha_internal_damage // processing internal damage
+
+ process(var/obj/mecha/mecha)
+ if(!mecha.hasInternalDamage())
+ return stop()
+ if(mecha.hasInternalDamage(MECHA_INT_FIRE))
+ if(!mecha.hasInternalDamage(MECHA_INT_TEMP_CONTROL) && prob(5))
+ mecha.clearInternalDamage(MECHA_INT_FIRE)
+ if(mecha.internal_tank)
+ if(mecha.internal_tank.return_pressure()>mecha.internal_tank.maximum_pressure && !(mecha.hasInternalDamage(MECHA_INT_TANK_BREACH)))
+ mecha.setInternalDamage(MECHA_INT_TANK_BREACH)
+ var/datum/gas_mixture/int_tank_air = mecha.internal_tank.return_air()
+ if(int_tank_air && int_tank_air.return_volume()>0) //heat the air_contents
+ int_tank_air.temperature = min(6000+T0C, int_tank_air.temperature+rand(10,15))
+ if(mecha.cabin_air && mecha.cabin_air.return_volume()>0)
+ mecha.cabin_air.temperature = min(6000+T0C, mecha.cabin_air.return_temperature()+rand(10,15))
+ if(mecha.cabin_air.return_temperature()>mecha.max_temperature/2)
+ mecha.take_damage(4/round(mecha.max_temperature/mecha.cabin_air.return_temperature(),0.1),"fire")
+ if(mecha.hasInternalDamage(MECHA_INT_TEMP_CONTROL)) //stop the mecha_preserve_temp loop datum
+ mecha.pr_int_temp_processor.stop()
+ if(mecha.hasInternalDamage(MECHA_INT_TANK_BREACH)) //remove some air from internal tank
+ if(mecha.internal_tank)
+ var/datum/gas_mixture/int_tank_air = mecha.internal_tank.return_air()
+ var/datum/gas_mixture/leaked_gas = int_tank_air.remove_ratio(0.10)
+ if(mecha.loc && hascall(mecha.loc,"assume_air"))
+ mecha.loc.assume_air(leaked_gas)
+ else
+ qdel(leaked_gas)
+ if(mecha.hasInternalDamage(MECHA_INT_SHORT_CIRCUIT))
+ if(mecha.get_charge())
+ mecha.spark_system.start()
+ mecha.cell.charge -= min(20,mecha.cell.charge)
+ mecha.cell.maxcharge -= min(20,mecha.cell.maxcharge)
return
\ No newline at end of file
diff --git a/code/game/verbs/ooc.dm b/code/game/verbs/ooc.dm
index 92b0638b9f7..82fef02e97c 100644
--- a/code/game/verbs/ooc.dm
+++ b/code/game/verbs/ooc.dm
@@ -85,8 +85,8 @@
return
if(!holder)
- if(!config.ooc_allowed)
- src << "OOC is globally muted."
+ if(!config.looc_allowed)
+ src << "LOOC is globally muted."
return
if(!config.dooc_allowed && (mob.stat == DEAD))
usr << "OOC for dead mobs has been turned off."
diff --git a/code/global.dm b/code/global.dm
index 38362296492..bfb1806b809 100644
--- a/code/global.dm
+++ b/code/global.dm
@@ -1,10 +1,14 @@
//#define TESTING
+#if DM_VERSION < 506
+#warn This compiler is out of date. You may experience issues with projectile animations.
+#endif
// Items that ask to be called every cycle.
var/global/obj/effect/datacore/data_core = null
var/global/list/all_areas = list()
var/global/list/machines = list()
var/global/list/processing_objects = list()
+var/global/list/processing_power_items = list()
var/global/list/active_diseases = list()
var/global/list/med_hud_users = list() // List of all entities using a medical HUD.
var/global/list/sec_hud_users = list() // List of all entities using a security HUD.
@@ -27,6 +31,8 @@ var/global/defer_powernet_rebuild = 0 // True if net rebuild will be called
// 3: AI satellite.
// 5: Empty space.
+var/global/datum/universal_state/universe = new
+
var/global/list/global_map = null
//var/global/list/global_map = list(list(1,5),list(4,3))
@@ -228,7 +234,8 @@ var/list/cheartstopper = list("potassium_chloride") // Thi
// Used by robots and robot preferences.
var/list/robot_module_types = list(
"Standard", "Engineering", "Construction", "Surgeon", "Crisis",
- "Miner", "Janitor", "Service", "Clerical", "Security"
+ "Miner", "Janitor", "Service", "Clerical", "Security",
+ "Research"
)
// Some scary sounds.
@@ -261,4 +268,4 @@ var/global/obj/item/device/radio/intercom/global_announcer = new(null)
var/list/station_departments = list("Command", "Medical", "Engineering", "Science", "Security", "Cargo", "Civilian")
var/global/const/TICKS_IN_DAY = 864000
-var/global/const/TICKS_IN_SECOND = 10
\ No newline at end of file
+var/global/const/TICKS_IN_SECOND = 10
diff --git a/code/modules/admin/admin.dm b/code/modules/admin/admin.dm
index 96b7a7c2445..7d29322163d 100644
--- a/code/modules/admin/admin.dm
+++ b/code/modules/admin/admin.dm
@@ -277,6 +277,13 @@ var/global/floorIsLava = 0
var/dat = "Info on [key]"
dat += ""
+ var/p_age = "unknown"
+ for(var/client/C in clients)
+ if(C.ckey == key)
+ p_age = C.player_age
+ break
+ dat +="Player age: [p_age] "
+
var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
var/list/infos
info >> infos
@@ -670,6 +677,16 @@ var/global/floorIsLava = 0
if(check_rights(R_SERVER,0))
dat += "Toggle bomb cap "
+ if(check_rights(R_SERVER|R_FUN,0))
+ dat += {"
+
+ Final Solutions
+ (Warning, these will end the round!)
+
+ Summon Nar-Sie
+ Start a Supermatter Cascade
+ "}
+
dat += " "
if(check_rights(R_DEBUG,0))
@@ -737,20 +754,43 @@ var/global/floorIsLava = 0
set category = "Server"
set desc="Globally Toggles OOC"
set name="Toggle OOC"
+
+ if(!check_rights(R_ADMIN))
+ return
+
config.ooc_allowed = !(config.ooc_allowed)
if (config.ooc_allowed)
world << "The OOC channel has been globally enabled!"
else
world << "The OOC channel has been globally disabled!"
- log_admin("[key_name(usr)] toggled OOC.")
- message_admins("[key_name_admin(usr)] toggled OOC.", 1)
+ log_and_message_admins("toggled OOC.")
feedback_add_details("admin_verb","TOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+/datum/admins/proc/togglelooc()
+ set category = "Server"
+ set desc="Globally Toggles LOOC"
+ set name="Toggle LOOC"
+
+ if(!check_rights(R_ADMIN))
+ return
+
+ config.looc_allowed = !(config.looc_allowed)
+ if (config.looc_allowed)
+ world << "The LOOC channel has been globally enabled!"
+ else
+ world << "The LOOC channel has been globally disabled!"
+ log_and_message_admins("toggled LOOC.")
+ feedback_add_details("admin_verb","TLOOC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+
/datum/admins/proc/toggledsay()
set category = "Server"
set desc="Globally Toggles DSAY"
set name="Toggle DSAY"
+
+ if(!check_rights(R_ADMIN))
+ return
+
config.dsay_allowed = !(config.dsay_allowed)
if (config.dsay_allowed)
world << "Deadchat has been globally enabled!"
@@ -764,6 +804,10 @@ var/global/floorIsLava = 0
set category = "Server"
set desc="Toggle Dead OOC."
set name="Toggle Dead OOC"
+
+ if(!check_rights(R_ADMIN))
+ return
+
config.dooc_allowed = !( config.dooc_allowed )
log_admin("[key_name(usr)] toggled Dead OOC.")
message_admins("[key_name_admin(usr)] toggled Dead OOC.", 1)
@@ -966,6 +1010,46 @@ var/global/floorIsLava = 0
var/datum/seed/S = plant_controller.seeds[seedtype]
S.harvest(usr,0,0,1)
+/datum/admins/proc/spawn_custom_item()
+ set category = "Debug"
+ set desc = "Spawn a custom item."
+ set name = "Spawn Custom Item"
+
+ if(!check_rights(R_SPAWN)) return
+
+ var/owner = input("Select a ckey.", "Spawn Custom Item") as null|anything in custom_items
+ if(!owner|| !custom_items[owner])
+ return
+
+ var/list/possible_items = custom_items[owner]
+ var/datum/custom_item/item_to_spawn = input("Select an item to spawn.", "Spawn Custom Item") as null|anything in possible_items
+ if(!item_to_spawn)
+ return
+
+ item_to_spawn.spawn_item(get_turf(usr))
+
+/datum/admins/proc/check_custom_items()
+
+ set category = "Debug"
+ set desc = "Check the custom item list."
+ set name = "Check Custom Items"
+
+ if(!check_rights(R_SPAWN)) return
+
+ if(!custom_items)
+ usr << "Custom item list is null."
+ return
+
+ if(!custom_items.len)
+ usr << "Custom item list not populated."
+ return
+
+ for(var/assoc_key in custom_items)
+ usr << "[assoc_key] has:"
+ var/list/current_items = custom_items[assoc_key]
+ for(var/datum/custom_item/item in current_items)
+ usr << "- name: [item.name] icon: [item.item_icon] path: [item.item_path] desc: [item.item_desc]"
+
/datum/admins/proc/spawn_plant()
set category = "Debug"
set desc = "Spawn a spreading plant effect."
@@ -1245,3 +1329,32 @@ var/global/floorIsLava = 0
//ALL DONE
//*********************************************************************************************************
//
+
+//Returns 1 to let the dragdrop code know we are trapping this event
+//Returns 0 if we don't plan to trap the event
+/datum/admins/proc/cmd_ghost_drag(var/mob/dead/observer/frommob, var/mob/living/tomob)
+ if(!istype(frommob))
+ return //Extra sanity check to make sure only observers are shoved into things
+
+ //Same as assume-direct-control perm requirements.
+ if (!check_rights(R_VAREDIT,0) || !check_rights(R_ADMIN|R_DEBUG,0))
+ return 0
+ if (!frommob.ckey)
+ return 0
+ var/question = ""
+ if (tomob.ckey)
+ question = "This mob already has a user ([tomob.key]) in control of it! "
+ question += "Are you sure you want to place [frommob.name]([frommob.key]) in control of [tomob.name]?"
+ var/ask = alert(question, "Place ghost in control of mob?", "Yes", "No")
+ if (ask != "Yes")
+ return 1
+ if (!frommob || !tomob) //make sure the mobs don't go away while we waited for a response
+ return 1
+ if(tomob.client) //No need to ghostize if there is no client
+ tomob.ghostize(0)
+ message_admins("[key_name_admin(usr)] has put [frommob.ckey] in control of [tomob.name].")
+ log_admin("[key_name(usr)] stuffed [frommob.ckey] into [tomob.name].")
+ feedback_add_details("admin_verb","CGD")
+ tomob.ckey = frommob.ckey
+ qdel(frommob)
+ return 1
diff --git a/code/modules/admin/admin_verbs.dm b/code/modules/admin/admin_verbs.dm
index d83d4da7474..c22fc85466b 100644
--- a/code/modules/admin/admin_verbs.dm
+++ b/code/modules/admin/admin_verbs.dm
@@ -58,6 +58,7 @@ var/list/admin_verbs_admin = list(
/client/proc/investigate_show, /*various admintools for investigation. Such as a singulo grief-log*/
/client/proc/secrets,
/datum/admins/proc/toggleooc, /*toggles ooc on/off for everyone*/
+ /datum/admins/proc/togglelooc, /*toggles looc on/off for everyone*/
/datum/admins/proc/toggleoocdead, /*toggles ooc on/off for everyone who is dead*/
/datum/admins/proc/toggledsay, /*toggles dsay on/off for everyone*/
/client/proc/game_panel, /*game panel, allows to change game-mode etc*/
@@ -84,7 +85,8 @@ var/list/admin_verbs_admin = list(
/client/proc/empty_ai_core_toggle_latejoin,
/client/proc/aooc,
/client/proc/change_human_appearance_admin, /* Allows an admin to change the basic appearance of human-based mobs */
- /client/proc/change_human_appearance_self /* Allows the human-based mob itself change its basic appearance */
+ /client/proc/change_human_appearance_self, /* Allows the human-based mob itself change its basic appearance */
+ /client/proc/change_security_level
)
var/list/admin_verbs_ban = list(
/client/proc/unban_panel,
@@ -108,10 +110,13 @@ var/list/admin_verbs_fun = list(
/client/proc/cmd_admin_add_random_ai_law,
/client/proc/make_sound,
/client/proc/toggle_random_events,
- /client/proc/editappear
+ /client/proc/editappear,
+ /client/proc/roll_dices
)
var/list/admin_verbs_spawn = list(
/datum/admins/proc/spawn_fruit,
+ /datum/admins/proc/spawn_custom_item,
+ /datum/admins/proc/check_custom_items,
/datum/admins/proc/spawn_plant,
/datum/admins/proc/spawn_atom, /*allows us to spawn instances*/
/client/proc/respawn_character,
@@ -253,6 +258,7 @@ var/list/admin_verbs_hideable = list(
/client/proc/cmd_debug_tog_aliens,
/client/proc/air_report,
/client/proc/enable_debug_verbs,
+ /client/proc/roll_dices,
/proc/possess,
/proc/release
)
@@ -295,7 +301,7 @@ var/list/admin_verbs_mentor = list(
if(holder.rights & R_SERVER) verbs += admin_verbs_server
if(holder.rights & R_DEBUG)
verbs += admin_verbs_debug
- if(config.debugparanoid && !check_rights(R_ADMIN))
+ if(config.debugparanoid && !(holder.rights & R_ADMIN))
verbs.Remove(admin_verbs_paranoid_debug) //Right now it's just callproc but we can easily add others later on.
if(holder.rights & R_POSSESS) verbs += admin_verbs_possess
if(holder.rights & R_PERMISSIONS) verbs += admin_verbs_permissions
@@ -522,7 +528,7 @@ var/list/admin_verbs_mentor = list(
if(C)
message_admins("[key_name_admin(src)] has warned [key_name_admin(C)] resulting in a [AUTOBANTIME] minute ban.")
C << "You have been autobanned due to a warning by [ckey]. This is a temporary ban, it will be removed in [AUTOBANTIME] minutes."
- del(C)
+ qdel(C)
else
message_admins("[key_name_admin(src)] has warned [warned_ckey] resulting in a [AUTOBANTIME] minute ban.")
AddBan(warned_ckey, D.last_id, "Autobanning due to too many formal warnings", ckey, 1, AUTOBANTIME)
@@ -723,7 +729,8 @@ var/list/admin_verbs_mentor = list(
return
if(holder)
- S.subsystem_law_manager()
+ var/obj/nano_module/law_manager/L = new(S)
+ L.ui_interact(usr, state = admin_state)
admin_log_and_message_admins("has opened [S]'s law manager.")
feedback_add_details("admin_verb","MSL") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
@@ -737,7 +744,7 @@ var/list/admin_verbs_mentor = list(
if(holder)
admin_log_and_message_admins("is altering the appearance of [H].")
- H.change_appearance(APPEARANCE_ALL, usr, usr, check_species_whitelist = 0)
+ H.change_appearance(APPEARANCE_ALL, usr, usr, check_species_whitelist = 0, state = admin_state)
feedback_add_details("admin_verb","CHAA") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/client/proc/change_human_appearance_self(mob/living/carbon/human/H in mob_list)
@@ -762,6 +769,17 @@ var/list/admin_verbs_mentor = list(
H.change_appearance(APPEARANCE_ALL, H.loc, check_species_whitelist = 1)
feedback_add_details("admin_verb","CMAS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+/client/proc/change_security_level()
+ set name = "Set security level"
+ set desc = "Sets the station security level"
+ set category = "Admin"
+
+ if(!check_rights(R_ADMIN)) return
+ var sec_level = input(usr, "It's currently code [get_security_level()].", "Select Security Level") as null|anything in (list("green","blue","red","delta")-get_security_level())
+ if(alert("Switch from code [get_security_level()] to code [sec_level]?","Change security level?","Yes","No") == "Yes")
+ set_security_level(sec_level)
+ log_admin("[key_name(usr)] changed the security level to code [sec_level].")
+
//---- bs12 verbs ----
@@ -857,7 +875,8 @@ var/list/admin_verbs_mentor = list(
var/job = input("Please select job slot to free", "Free job slot") as null|anything in jobs
if (job)
job_master.FreeRole(job)
- return
+ message_admins("A job slot for [job] has been opened by [key_name_admin(usr)]")
+ return
/client/proc/toggleattacklogs()
set name = "Toggle Attack Log Messages"
@@ -931,3 +950,14 @@ var/list/admin_verbs_mentor = list(
log_admin("[key_name(usr)] told everyone to man up and deal with it.")
message_admins("\blue [key_name_admin(usr)] told everyone to man up and deal with it.", 1)
+
+/client/proc/give_spell(mob/T as mob in mob_list) // -- Urist
+ set category = "Fun"
+ set name = "Give Spell"
+ set desc = "Gives a spell to a mob."
+ var/spell/S = input("Choose the spell to give to that guy", "ABRAKADABRA") as null|anything in spells
+ if(!S) return
+ T.spell_list += new S
+ feedback_add_details("admin_verb","GS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
+ log_admin("[key_name(usr)] gave [key_name(T)] the spell [S].")
+ message_admins("\blue [key_name_admin(usr)] gave [key_name(T)] the spell [S].", 1)
diff --git a/code/modules/admin/holder2.dm b/code/modules/admin/holder2.dm
index d1cc15b0fe1..dbd4de64446 100644
--- a/code/modules/admin/holder2.dm
+++ b/code/modules/admin/holder2.dm
@@ -16,7 +16,7 @@ var/list/admin_datums = list()
/datum/admins/New(initial_rank = "Temporary Admin", initial_rights = 0, ckey)
if(!ckey)
error("Admin datum created without a ckey argument. Datum has been deleted")
- del(src)
+ qdel(src)
return
admincaster_signature = "Nanotrasen Officer #[rand(0,9)][rand(0,9)][rand(0,9)]"
rank = initial_rank
@@ -55,8 +55,7 @@ proc/admin_proc()
if(!check_rights(R_ADMIN)) return
world << "you have enough rights!"
-NOTE: it checks usr! not src! So if you're checking somebody's rank in a proc which they did not call
-you will have to do something like if(client.holder.rights & R_ADMIN) yourself.
+NOTE: It checks usr by default. Supply the "user" argument if you wish to check for a specific mob.
*/
/proc/check_rights(rights_required, show_msg=1, var/mob/user = usr)
if(user && user.client)
@@ -92,5 +91,5 @@ you will have to do something like if(client.holder.rights & R_ADMIN) yourself.
/client/proc/deadmin()
if(holder)
holder.disassociate()
- //del(holder)
+ //qdel(holder)
return 1
diff --git a/code/modules/admin/player_notes.dm b/code/modules/admin/player_notes.dm
index 3a74da5fca6..a00a208d3b5 100644
--- a/code/modules/admin/player_notes.dm
+++ b/code/modules/admin/player_notes.dm
@@ -1,167 +1,167 @@
-//This stuff was originally intended to be integrated into the ban-system I was working on
-//but it's safe to say that'll never be finished. So I've merged it into the current player panel.
-//enjoy ~Carn
-/*
-#define NOTESFILE "data/player_notes.sav" //where the player notes are saved
-
-datum/admins/proc/notes_show(var/ckey)
- usr << browse("Player Notes[notes_gethtml(ckey)]","window=player_notes;size=700x400")
-
-
-datum/admins/proc/notes_gethtml(var/ckey)
- var/savefile/notesfile = new(NOTESFILE)
- if(!notesfile) return "Error: Cannot access [NOTESFILE]"
- if(ckey)
- . = "Notes for [ckey]:\[+\]\[-\] "
- notesfile.cd = "/[ckey]"
- var/index = 1
- while( !notesfile.eof )
- var/note
- notesfile >> note
- . += "[note] \[-\] "
- index++
- else
- . = "All Notes:\[+\]\[-\] "
- notesfile.cd = "/"
- for(var/dir in notesfile.dir)
- . += "[dir] "
- return
-
-
-//handles adding notes to the end of a ckey's buffer
-//originally had seperate entries such as var/by to record who left the note and when
-//but the current bansystem is a heap of dung.
-/proc/notes_add(var/ckey, var/note)
- if(!ckey)
- ckey = ckey(input(usr,"Who would you like to add notes for?","Enter a ckey",null) as text|null)
- if(!ckey) return
-
- if(!note)
- note = html_encode(input(usr,"Enter your note:","Enter some text",null) as message|null)
- if(!note) return
-
- var/savefile/notesfile = new(NOTESFILE)
- if(!notesfile) return
- notesfile.cd = "/[ckey]"
- notesfile.eof = 1 //move to the end of the buffer
- notesfile << "[time2text(world.realtime,"DD-MMM-YYYY")] | [note][(usr && usr.ckey)?" ~[usr.ckey]":""]"
- return
-
-//handles removing entries from the buffer, or removing the entire directory if no start_index is given
-/proc/notes_remove(var/ckey, var/start_index, var/end_index)
- var/savefile/notesfile = new(NOTESFILE)
- if(!notesfile) return
-
- if(!ckey)
- notesfile.cd = "/"
- ckey = ckey(input(usr,"Who would you like to remove notes for?","Enter a ckey",null) as null|anything in notesfile.dir)
- if(!ckey) return
-
- if(start_index)
- notesfile.cd = "/[ckey]"
- var/list/noteslist = list()
- if(!end_index) end_index = start_index
- var/index = 0
- while( !notesfile.eof )
- index++
- var/temp
- notesfile >> temp
- if( (start_index <= index) && (index <= end_index) )
- continue
- noteslist += temp
-
- notesfile.eof = -2 //Move to the start of the buffer and then erase.
-
- for( var/note in noteslist )
- notesfile << note
- else
- notesfile.cd = "/"
- if(alert(usr,"Are you sure you want to remove all their notes?","Confirmation","No","Yes - Remove all notes") == "Yes - Remove all notes")
- notesfile.dir.Remove(ckey)
- return
-
-#undef NOTESFILE
-*/
-
-//Hijacking this file for BS12 playernotes functions. I like this ^ one systemm alright, but converting sounds too bothersome~ Chinsky.
-
-/proc/notes_add(var/key, var/note, var/mob/usr)
- if (!key || !note)
- return
-
- //Loading list of notes for this key
- var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
- var/list/infos
- info >> infos
- if(!infos) infos = list()
-
- //Overly complex timestamp creation
- var/modifyer = "th"
- switch(time2text(world.timeofday, "DD"))
- if("01","21","31")
- modifyer = "st"
- if("02","22",)
- modifyer = "nd"
- if("03","23")
- modifyer = "rd"
- var/day_string = "[time2text(world.timeofday, "DD")][modifyer]"
- if(copytext(day_string,1,2) == "0")
- day_string = copytext(day_string,2)
- var/full_date = time2text(world.timeofday, "DDD, Month DD of YYYY")
- var/day_loc = findtext(full_date, time2text(world.timeofday, "DD"))
-
- var/datum/player_info/P = new
- if (usr)
- P.author = usr.key
- P.rank = usr.client.holder.rank
- else
- P.author = "Adminbot"
- P.rank = "Friendly Robot"
- P.content = note
- P.timestamp = "[copytext(full_date,1,day_loc)][day_string][copytext(full_date,day_loc+2)]"
-
- infos += P
- info << infos
-
- message_admins("\blue [key_name_admin(usr)] has edited [key]'s notes.")
- log_admin("[key_name(usr)] has edited [key]'s notes.")
-
- del info
-
- //Updating list of keys with notes on them
- var/savefile/note_list = new("data/player_notes.sav")
- var/list/note_keys
- note_list >> note_keys
- if(!note_keys) note_keys = list()
- if(!note_keys.Find(key)) note_keys += key
- note_list << note_keys
- del note_list
-
-
-/proc/notes_del(var/key, var/index)
- var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
- var/list/infos
- info >> infos
- if(!infos || infos.len < index) return
-
- var/datum/player_info/item = infos[index]
- infos.Remove(item)
- info << infos
-
- message_admins("\blue [key_name_admin(usr)] deleted one of [key]'s notes.")
- log_admin("[key_name(usr)] deleted one of [key]'s notes.")
-
- del info
-
-/proc/show_player_info_irc(var/key as text)
- var/dat = " Info on [key]%0D%0A"
- var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
- var/list/infos
- info >> infos
- if(!infos)
- dat = "No information found on the given key."
- else
- for(var/datum/player_info/I in infos)
- dat += "[I.content]%0D%0Aby [I.author] ([I.rank]) on [I.timestamp]%0D%0A%0D%0A"
-
- return dat
+//This stuff was originally intended to be integrated into the ban-system I was working on
+//but it's safe to say that'll never be finished. So I've merged it into the current player panel.
+//enjoy ~Carn
+/*
+#define NOTESFILE "data/player_notes.sav" //where the player notes are saved
+
+datum/admins/proc/notes_show(var/ckey)
+ usr << browse("Player Notes[notes_gethtml(ckey)]","window=player_notes;size=700x400")
+
+
+datum/admins/proc/notes_gethtml(var/ckey)
+ var/savefile/notesfile = new(NOTESFILE)
+ if(!notesfile) return "Error: Cannot access [NOTESFILE]"
+ if(ckey)
+ . = "Notes for [ckey]:\[+\]\[-\] "
+ notesfile.cd = "/[ckey]"
+ var/index = 1
+ while( !notesfile.eof )
+ var/note
+ notesfile >> note
+ . += "[note] \[-\] "
+ index++
+ else
+ . = "All Notes:\[+\]\[-\] "
+ notesfile.cd = "/"
+ for(var/dir in notesfile.dir)
+ . += "[dir] "
+ return
+
+
+//handles adding notes to the end of a ckey's buffer
+//originally had seperate entries such as var/by to record who left the note and when
+//but the current bansystem is a heap of dung.
+/proc/notes_add(var/ckey, var/note)
+ if(!ckey)
+ ckey = ckey(input(usr,"Who would you like to add notes for?","Enter a ckey",null) as text|null)
+ if(!ckey) return
+
+ if(!note)
+ note = html_encode(input(usr,"Enter your note:","Enter some text",null) as message|null)
+ if(!note) return
+
+ var/savefile/notesfile = new(NOTESFILE)
+ if(!notesfile) return
+ notesfile.cd = "/[ckey]"
+ notesfile.eof = 1 //move to the end of the buffer
+ notesfile << "[time2text(world.realtime,"DD-MMM-YYYY")] | [note][(usr && usr.ckey)?" ~[usr.ckey]":""]"
+ return
+
+//handles removing entries from the buffer, or removing the entire directory if no start_index is given
+/proc/notes_remove(var/ckey, var/start_index, var/end_index)
+ var/savefile/notesfile = new(NOTESFILE)
+ if(!notesfile) return
+
+ if(!ckey)
+ notesfile.cd = "/"
+ ckey = ckey(input(usr,"Who would you like to remove notes for?","Enter a ckey",null) as null|anything in notesfile.dir)
+ if(!ckey) return
+
+ if(start_index)
+ notesfile.cd = "/[ckey]"
+ var/list/noteslist = list()
+ if(!end_index) end_index = start_index
+ var/index = 0
+ while( !notesfile.eof )
+ index++
+ var/temp
+ notesfile >> temp
+ if( (start_index <= index) && (index <= end_index) )
+ continue
+ noteslist += temp
+
+ notesfile.eof = -2 //Move to the start of the buffer and then erase.
+
+ for( var/note in noteslist )
+ notesfile << note
+ else
+ notesfile.cd = "/"
+ if(alert(usr,"Are you sure you want to remove all their notes?","Confirmation","No","Yes - Remove all notes") == "Yes - Remove all notes")
+ notesfile.dir.Remove(ckey)
+ return
+
+#undef NOTESFILE
+*/
+
+//Hijacking this file for BS12 playernotes functions. I like this ^ one systemm alright, but converting sounds too bothersome~ Chinsky.
+
+/proc/notes_add(var/key, var/note, var/mob/usr)
+ if (!key || !note)
+ return
+
+ //Loading list of notes for this key
+ var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
+ var/list/infos
+ info >> infos
+ if(!infos) infos = list()
+
+ //Overly complex timestamp creation
+ var/modifyer = "th"
+ switch(time2text(world.timeofday, "DD"))
+ if("01","21","31")
+ modifyer = "st"
+ if("02","22",)
+ modifyer = "nd"
+ if("03","23")
+ modifyer = "rd"
+ var/day_string = "[time2text(world.timeofday, "DD")][modifyer]"
+ if(copytext(day_string,1,2) == "0")
+ day_string = copytext(day_string,2)
+ var/full_date = time2text(world.timeofday, "DDD, Month DD of YYYY")
+ var/day_loc = findtext(full_date, time2text(world.timeofday, "DD"))
+
+ var/datum/player_info/P = new
+ if (usr)
+ P.author = usr.key
+ P.rank = usr.client.holder.rank
+ else
+ P.author = "Adminbot"
+ P.rank = "Friendly Robot"
+ P.content = note
+ P.timestamp = "[copytext(full_date,1,day_loc)][day_string][copytext(full_date,day_loc+2)]"
+
+ infos += P
+ info << infos
+
+ message_admins("\blue [key_name_admin(usr)] has edited [key]'s notes.")
+ log_admin("[key_name(usr)] has edited [key]'s notes.")
+
+ qdel(info)
+
+ //Updating list of keys with notes on them
+ var/savefile/note_list = new("data/player_notes.sav")
+ var/list/note_keys
+ note_list >> note_keys
+ if(!note_keys) note_keys = list()
+ if(!note_keys.Find(key)) note_keys += key
+ note_list << note_keys
+ qdel(note_list)
+
+
+/proc/notes_del(var/key, var/index)
+ var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
+ var/list/infos
+ info >> infos
+ if(!infos || infos.len < index) return
+
+ var/datum/player_info/item = infos[index]
+ infos.Remove(item)
+ info << infos
+
+ message_admins("\blue [key_name_admin(usr)] deleted one of [key]'s notes.")
+ log_admin("[key_name(usr)] deleted one of [key]'s notes.")
+
+ qdel(info)
+
+/proc/show_player_info_irc(var/key as text)
+ var/dat = " Info on [key]%0D%0A"
+ var/savefile/info = new("data/player_saves/[copytext(key, 1, 2)]/[key]/info.sav")
+ var/list/infos
+ info >> infos
+ if(!infos)
+ dat = "No information found on the given key."
+ else
+ for(var/datum/player_info/I in infos)
+ dat += "[I.content]%0D%0Aby [I.author] ([I.rank]) on [I.timestamp]%0D%0A%0D%0A"
+
+ return dat
diff --git a/code/modules/admin/topic.dm b/code/modules/admin/topic.dm
index fc2ee0a0b26..ffa64ce64f8 100644
--- a/code/modules/admin/topic.dm
+++ b/code/modules/admin/topic.dm
@@ -745,7 +745,7 @@
log_admin("[key_name(usr)] booted [key_name(M)].")
message_admins("\blue [key_name_admin(usr)] booted [key_name_admin(M)].", 1)
//M.client = null
- del(M.client)
+ qdel(M.client)
/*
//Player Notes
else if(href_list["notes"])
@@ -811,8 +811,8 @@
log_admin("[usr.client.ckey] has banned [M.ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")
message_admins("\blue[usr.client.ckey] has banned [M.ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")
- del(M.client)
- //del(M) // See no reason why to delete mob. Important stuff can be lost. And ban can be lifted before round ends.
+ qdel(M.client)
+ //qdel(M) // See no reason why to delete mob. Important stuff can be lost. And ban can be lifted before round ends.
if("No")
if(!check_rights(R_BAN)) return
var/reason = sanitize(input(usr,"Reason?","reason","Griefer") as text|null)
@@ -836,8 +836,8 @@
feedback_inc("ban_perma",1)
DB_ban_record(BANTYPE_PERMA, M, -1, reason)
- del(M.client)
- //del(M)
+ qdel(M.client)
+ //qdel(M)
if("Cancel")
return
@@ -1301,7 +1301,7 @@
S.victim = M
S.loc = M.loc
spawn(20)
- del(S)
+ qdel(S)
var/turf/simulated/floor/T = get_turf(M)
if(istype(T))
@@ -1317,21 +1317,27 @@
M.stuttering = 20
else if(href_list["CentcommReply"])
- var/mob/living/carbon/human/H = locate(href_list["CentcommReply"])
- if(!istype(H))
- usr << "This can only be used on instances of type /mob/living/carbon/human"
- return
- if(!istype(H.l_ear, /obj/item/device/radio/headset) && !istype(H.r_ear, /obj/item/device/radio/headset))
- usr << "The person you are trying to contact is not wearing a headset"
+ var/mob/living/L = locate(href_list["CentcommReply"])
+ if(!istype(L))
+ usr << "This can only be used on instances of type /mob/living/"
return
- var/input = sanitize(input(src.owner, "Please enter a message to reply to [key_name(H)] via their headset.","Outgoing message from Centcomm", ""))
- if(!input) return
+ if(L.can_centcom_reply())
+ var/input = sanitize(input(src.owner, "Please enter a message to reply to [key_name(L)] via their headset.","Outgoing message from Centcomm", ""))
+ if(!input) return
+
+ src.owner << "You sent [input] to [L] via a secure channel."
+ log_admin("[src.owner] replied to [key_name(L)]'s Centcomm message with the message [input].")
+ message_admins("[src.owner] replied to [key_name(L)]'s Centcom message with: \"[input]\"")
+ if(!L.isAI())
+ L << "You hear something crackle in your headset for a moment before a voice speaks."
+ L << "Please stand by for a message from Central Command."
+ L << "Message as follows."
+ L << "[input]"
+ L << "Message ends."
+ else
+ src.owner << "The person you are trying to contact does not have functional radio equipment."
- src.owner << "You sent [input] to [H] via a secure channel."
- log_admin("[src.owner] replied to [key_name(H)]'s Centcomm message with the message [input].")
- message_admins("[src.owner] replied to [key_name(H)]'s Centcom message with: \"[input]\"")
- H << "You hear something crackle in your headset for a moment before a voice speaks. \"Please stand by for a message from Central Command. Message as follows. \"[input]\" Message ends.\""
else if(href_list["SyndicateReply"])
var/mob/living/carbon/human/H = locate(href_list["SyndicateReply"])
@@ -1363,8 +1369,8 @@
var/data = ""
var/obj/item/weapon/paper_bundle/B = fax
- for (var/page = 1, page <= B.amount, page++)
- var/obj/pageobj = B.contents[page]
+ for (var/page = 1, page <= B.pages.len, page++)
+ var/obj/pageobj = B.pages[page]
data += "Page [page] - [pageobj.name] "
usr << browse(data, "window=[B.name]")
@@ -1377,11 +1383,11 @@
if (!bundle) return
- if (istype(bundle.contents[page], /obj/item/weapon/paper))
- var/obj/item/weapon/paper/P = bundle.contents[page]
+ if (istype(bundle.pages[page], /obj/item/weapon/paper))
+ var/obj/item/weapon/paper/P = bundle.pages[page]
P.show_content(src.owner, 1)
- else if (istype(bundle.contents[page], /obj/item/weapon/photo))
- var/obj/item/weapon/photo/H = bundle.contents[page]
+ else if (istype(bundle.pages[page], /obj/item/weapon/photo))
+ var/obj/item/weapon/photo/H = bundle.pages[page]
H.show(src.owner)
return
@@ -1418,7 +1424,7 @@
src.owner << "\red Message reply failed."
spawn(100)
- del(P)
+ qdel(P)
return
else if(href_list["SolGovFaxReply"])
@@ -1663,28 +1669,28 @@
feedback_inc("admin_secrets_fun_used",1)
feedback_add_details("admin_secrets_fun_used","SC")
for(var/obj/item/clothing/under/O in world)
- del(O)
+ qdel(O)
ok = 1
if("sec_all_clothes")
feedback_inc("admin_secrets_fun_used",1)
feedback_add_details("admin_secrets_fun_used","SAC")
for(var/obj/item/clothing/O in world)
- del(O)
+ qdel(O)
ok = 1
if("sec_classic1")
feedback_inc("admin_secrets_fun_used",1)
feedback_add_details("admin_secrets_fun_used","SC1")
for(var/obj/item/clothing/suit/fire/O in world)
- del(O)
+ qdel(O)
for(var/obj/structure/grille/O in world)
- del(O)
+ qdel(O)
/* for(var/obj/machinery/vehicle/pod/O in world)
for(var/mob/M in src)
M.loc = src.loc
if (M.client)
M.client.perspective = MOB_PERSPECTIVE
M.client.eye = M
- del(O)
+ qdel(O)
ok = 1*/
if("monkey")
feedback_inc("admin_secrets_fun_used",1)
@@ -2038,7 +2044,7 @@
var/turf/T = pick(blobstart)
var/obj/effect/bhole/bh = new /obj/effect/bhole( T.loc, 30 )
spawn(rand(100, 600))
- del(bh)
+ qdel(bh)
if("timeanomalies") //dear god this code was awful :P Still needs further optimisation
feedback_inc("admin_secrets_fun_used",1)
@@ -2210,7 +2216,6 @@
for(var/obj/item/clothing/under/W in world)
W.icon_state = "schoolgirl"
W.item_state = "w_suit"
- W.item_color = "schoolgirl"
message_admins("[key_name_admin(usr)] activated Japanese Animes mode")
world << sound('sound/AI/animes.ogg')
if("paintball")
@@ -2251,6 +2256,33 @@
feedback_add_details("admin_secrets_fun_used","OO")
only_one()
message_admins("[key_name_admin(usr)] has triggered a battle to the death (only one)")
+
+ if("togglenarsie")
+ feedback_inc("admin_secrets_fun_used",1)
+ feedback_add_details("admin_secrets_fun_used","NA")
+ var/choice = input("How do you wish for narsie to interact with her surroundings?") in list("CultStation13", "Nar-Singulo")
+ if(choice == "CultStation13")
+ message_admins("[key_name_admin(usr)] has set narsie's behaviour to \"CultStation13\".")
+ narsie_behaviour = "CultStation13"
+ if(choice == "Nar-Singulo")
+ message_admins("[key_name_admin(usr)] has set narsie's behaviour to \"Nar-Singulo\".")
+ narsie_behaviour = "Nar-Singulo"
+ if("hellonearth")
+ feedback_inc("admin_secrets_fun_used",1)
+ feedback_add_details("admin_secrets_fun_used","NS")
+ var/choice = input("You sure you want to end the round and summon narsie at your location? Misuse of this could result in removal of flags or halarity.") in list("PRAISE SATAN", "Cancel")
+ if(choice == "PRAISE SATAN")
+ new /obj/singularity/narsie/large(get_turf(usr))
+ message_admins("[key_name_admin(usr)] has summoned narsie and brought about a new realm of suffering.")
+ if("supermattercascade")
+ feedback_inc("admin_secrets_fun_used",1)
+ feedback_add_details("admin_secrets_fun_used","SC")
+ var/choice = input("You sure you want to destroy the universe and create a large explosion at your location? Misuse of this could result in removal of flags or halarity.") in list("NO TIME TO EXPLAIN", "Cancel")
+ if(choice == "NO TIME TO EXPLAIN")
+ explosion(get_turf(usr), 8, 16, 24, 32, 1)
+ new /turf/unsimulated/wall/supermatter(get_turf(usr))
+ SetUniversalState(/datum/universal_state/supermatter_cascade)
+ message_admins("[key_name_admin(usr)] has managed to destroy the universe with a supermatter cascade. Good job, [key_name_admin(usr)]")
if(usr)
log_admin("[key_name(usr)] used secret [href_list["secretsfun"]]")
if (ok)
@@ -2619,3 +2651,12 @@
if("list")
PlayerNotesPage(text2num(href_list["index"]))
return
+
+mob/living/proc/can_centcom_reply()
+ return 0
+
+mob/living/carbon/human/can_centcom_reply()
+ return istype(l_ear, /obj/item/device/radio/headset) || istype(r_ear, /obj/item/device/radio/headset)
+
+mob/living/silicon/ai/can_centcom_reply()
+ return common_radio != null && !check_unable(2)
\ No newline at end of file
diff --git a/code/modules/admin/verbs/BrokenInhands.dm b/code/modules/admin/verbs/BrokenInhands.dm
index 914ba1b5df4..e5d6dc2661a 100644
--- a/code/modules/admin/verbs/BrokenInhands.dm
+++ b/code/modules/admin/verbs/BrokenInhands.dm
@@ -26,7 +26,7 @@
// if(!istates.Find(O.item_state))
// text += "[O.type] MISSING NORMAL ICON CALLED\n\"[O.item_state]\" IN \"[O.icon]\"\n"
//text+="\n"
- del(O)
+ qdel(O)
if(text)
var/F = file("broken_icons.txt")
fdel(F)
diff --git a/code/modules/admin/verbs/SDQL.dm b/code/modules/admin/verbs/SDQL.dm
index d8626da403a..a98cc3a1d95 100644
--- a/code/modules/admin/verbs/SDQL.dm
+++ b/code/modules/admin/verbs/SDQL.dm
@@ -1,497 +1,497 @@
-
-//Structured Datum Query Language. Basically SQL meets BYOND objects.
-
-//Note: For use in BS12, need text_starts_with proc, and to modify the action on select to use BS12's object edit command(s).
-
-/client/proc/SDQL_query(query_text as message)
- set category = "Admin"
- if(!check_rights(R_DEBUG)) //Shouldn't happen... but just to be safe.
- message_admins("\red ERROR: Non-admin [usr.key] attempted to execute a SDQL query!")
- log_admin("Non-admin [usr.key] attempted to execute a SDQL query!")
-
- var/list/query_list = SDQL_tokenize(query_text)
-
- if(query_list.len < 2)
- if(query_list.len > 0)
- usr << "\red SDQL: Too few discrete tokens in query \"[query_text]\". Please check your syntax and try again."
- return
-
- if(!(lowertext(query_list[1]) in list("select", "delete", "update")))
- usr << "\red SDQL: Unknown query type: \"[query_list[1]]\" in query \"[query_text]\". Please check your syntax and try again."
- return
-
- var/list/types = list()
-
- var/i
- for(i = 2; i <= query_list.len; i += 2)
- types += query_list[i]
-
- if(i + 1 >= query_list.len || query_list[i + 1] != ",")
- break
-
- i++
-
- var/list/from = list()
-
- if(i <= query_list.len)
- if(lowertext(query_list[i]) in list("from", "in"))
- for(i++; i <= query_list.len; i += 2)
- from += query_list[i]
-
- if(i + 1 >= query_list.len || query_list[i + 1] != ",")
- break
-
- i++
-
- if(from.len < 1)
- from += "world"
-
- var/list/set_vars = list()
-
- if(lowertext(query_list[1]) == "update")
- if(i <= query_list.len && lowertext(query_list[i]) == "set")
- for(i++; i <= query_list.len; i++)
- if(i + 2 <= query_list.len && query_list[i + 1] == "=")
- set_vars += query_list[i]
- set_vars[query_list[i]] = query_list[i + 2]
-
- else
- usr << "\red SDQL: Invalid set parameter in query \"[query_text]\". Please check your syntax and try again."
- return
-
- i += 3
-
- if(i >= query_list.len || query_list[i] != ",")
- break
-
- if(set_vars.len < 1)
- usr << "\red SDQL: Invalid or missing set in query \"[query_text]\". Please check your syntax and try again."
- return
-
- var/list/where = list()
-
- if(i <= query_list.len && lowertext(query_list[i]) == "where")
- where = query_list.Copy(i + 1)
-
- var/list/from_objs = list()
- if("world" in from)
- from_objs += world
- else
- for(var/f in from)
- if(copytext(f, 1, 2) == "'" || copytext(f, 1, 2) == "\"")
- from_objs += locate(copytext(f, 2, length(f)))
- else if(copytext(f, 1, 2) != "/")
- from_objs += locate(f)
- else
- var/f2 = text2path(f)
- if(text_starts_with(f, "/mob"))
- for(var/mob/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/turf/space"))
- for(var/turf/space/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/turf/simulated"))
- for(var/turf/simulated/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/turf/unsimulated"))
- for(var/turf/unsimulated/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/turf"))
- for(var/turf/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/area"))
- for(var/area/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/obj/item"))
- for(var/obj/item/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/obj/machinery"))
- for(var/obj/machinery/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/obj"))
- for(var/obj/m in world)
- if(istype(m, f2))
- from_objs += m
-
- else if(text_starts_with(f, "/atom"))
- for(var/atom/m in world)
- if(istype(m, f2))
- from_objs += m
-/*
- else
- for(var/datum/m in world)
- if(istype(m, f2))
- from_objs += m
-*/
-
- var/list/objs = list()
-
- for(var/from_obj in from_objs)
- if("*" in types)
- objs += from_obj:contents
- else
- for(var/f in types)
- if(copytext(f, 1, 2) == "'" || copytext(f, 1, 2) == "\"")
- objs += locate(copytext(f, 2, length(f))) in from_obj
- else if(copytext(f, 1, 2) != "/")
- objs += locate(f) in from_obj
- else
- var/f2 = text2path(f)
- if(text_starts_with(f, "/mob"))
- for(var/mob/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/turf/space"))
- for(var/turf/space/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/turf/simulated"))
- for(var/turf/simulated/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/turf/unsimulated"))
- for(var/turf/unsimulated/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/turf"))
- for(var/turf/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/area"))
- for(var/area/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/obj/item"))
- for(var/obj/item/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/obj/machinery"))
- for(var/obj/machinery/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/obj"))
- for(var/obj/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else if(text_starts_with(f, "/atom"))
- for(var/atom/m in from_obj)
- if(istype(m, f2))
- objs += m
-
- else
- for(var/datum/m in from_obj)
- if(istype(m, f2))
- objs += m
-
-
- for(var/datum/t in objs)
- var/currently_false = 0
- for(i = 1, i - 1 < where.len, i++)
- var/v = where[i++]
- var/compare_op = where[i++]
- if(!(compare_op in list("==", "=", "<>", "<", ">", "<=", ">=", "!=")))
- usr << "\red SDQL: Unknown comparison operator [compare_op] in where clause following [v] in query \"[query_text]\". Please check your syntax and try again."
- return
-
- var/j
- for(j = i, j <= where.len, j++)
- if(lowertext(where[j]) in list("and", "or", ";"))
- break
-
- if(!currently_false)
- var/value = SDQL_text2value(t, v)
- var/result = SDQL_evaluate(t, where.Copy(i, j))
-
- switch(compare_op)
- if("=", "==")
- currently_false = !(value == result)
-
- if("!=", "<>")
- currently_false = !(value != result)
-
- if("<")
- currently_false = !(value < result)
-
- if(">")
- currently_false = !(value > result)
-
- if("<=")
- currently_false = !(value <= result)
-
- if(">=")
- currently_false = !(value >= result)
-
-
- if(j > where.len || lowertext(where[j]) == ";")
- break
- else if(lowertext(where[j]) == "or")
- if(currently_false)
- currently_false = 0
- else
- break
-
- i = j
-
- if(currently_false)
- objs -= t
-
-
-
- usr << "\blue SQDL Query: [query_text]"
- message_admins("[usr] executed SDQL query: \"[query_text]\".")
-/*
- for(var/t in types)
- usr << "Type: [t]"
-
- for(var/t in from)
- usr << "From: [t]"
-
- for(var/t in set_vars)
- usr << "Set: [t] = [set_vars[t]]"
-
- if(where.len)
- var/where_str = ""
- for(var/t in where)
- where_str += "[t] "
-
- usr << "Where: [where_str]"
-
- usr << "From objects:"
- for(var/datum/t in from_objs)
- usr << t
-
- usr << "Objects:"
- for(var/datum/t in objs)
- usr << t
-*/
- switch(lowertext(query_list[1]))
- if("delete")
- for(var/datum/t in objs)
- del t
-
- if("update")
- for(var/datum/t in objs)
- objs[t] = list()
- for(var/v in set_vars)
- if(v in t.vars)
- objs[t][v] = SDQL_text2value(t, set_vars[v])
-
- for(var/datum/t in objs)
- for(var/v in objs[t])
- t.vars[v] = objs[t][v]
-
- if("select")
- var/text = ""
- for(var/datum/t in objs)
- if(istype(t, /atom))
- var/atom/a = t
-
- if(a.x)
- text += "\ref[t]: [t] at ([a.x], [a.y], [a.z]) "
-
- else if(a.loc && a.loc.x)
- text += "\ref[t]: [t] in [a.loc] at ([a.loc.x], [a.loc.y], [a.loc.z]) "
-
- else
- text += "\ref[t]: [t] "
-
- else
- text += "\ref[t]: [t] "
-
- //text += "[t] "
- usr << browse(text, "window=sdql_result")
-
-
-/client/Topic(href,href_list[],hsrc)
- if(href_list["SDQL_select"])
- debug_variables(locate(href_list["SDQL_select"]))
-
- ..()
-
-
-/proc/SDQL_evaluate(datum/object, list/equation)
- if(equation.len == 0)
- return null
-
- else if(equation.len == 1)
- return SDQL_text2value(object, equation[1])
-
- else if(equation[1] == "!")
- return !SDQL_evaluate(object, equation.Copy(2))
-
- else if(equation[1] == "-")
- return -SDQL_evaluate(object, equation.Copy(2))
-
-
- else
- usr << "\red SDQL: Sorry, equations not yet supported :("
- return null
-
-
-/proc/SDQL_text2value(datum/object, text)
- if(text2num(text) != null)
- return text2num(text)
- else if(text == "null")
- return null
- else if(copytext(text, 1, 2) == "'" || copytext(text, 1, 2) == "\"" )
- return copytext(text, 2, length(text))
- else if(copytext(text, 1, 2) == "/")
- return text2path(text)
- else
- if(findtext(text, "."))
- var/split = findtext(text, ".")
- var/v = copytext(text, 1, split)
-
- if((v in object.vars) && istype(object.vars[v], /datum))
- return SDQL_text2value(object.vars[v], copytext(text, split + 1))
- else
- return null
-
- else
- if(text in object.vars)
- return object.vars[text]
- else
- return null
-
-
-/proc/text_starts_with(text, start)
- if(copytext(text, 1, length(start) + 1) == start)
- return 1
- else
- return 0
-
-
-
-
-
-/proc/SDQL_tokenize(query_text)
-
- var/list/whitespace = list(" ", "\n", "\t")
- var/list/single = list("(", ")", ",", "+", "-")
- var/list/multi = list(
- "=" = list("", "="),
- "<" = list("", "=", ">"),
- ">" = list("", "="),
- "!" = list("", "="))
-
- var/word = ""
- var/list/query_list = list()
- var/len = length(query_text)
-
- for(var/i = 1, i <= len, i++)
- var/char = copytext(query_text, i, i + 1)
-
- if(char in whitespace)
- if(word != "")
- query_list += word
- word = ""
-
- else if(char in single)
- if(word != "")
- query_list += word
- word = ""
-
- query_list += char
-
- else if(char in multi)
- if(word != "")
- query_list += word
- word = ""
-
- var/char2 = copytext(query_text, i + 1, i + 2)
-
- if(char2 in multi[char])
- query_list += "[char][char2]"
- i++
-
- else
- query_list += char
-
- else if(char == "'")
- if(word != "")
- usr << "\red SDQL: You have an error in your SDQL syntax, unexpected ' in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
- return null
-
- word = "'"
-
- for(i++, i <= len, i++)
- char = copytext(query_text, i, i + 1)
-
- if(char == "'")
- if(copytext(query_text, i + 1, i + 2) == "'")
- word += "'"
- i++
-
- else
- break
-
- else
- word += char
-
- if(i > len)
- usr << "\red SDQL: You have an error in your SDQL syntax, unmatched ' in query: \"[query_text]\". Please check your syntax, and try again."
- return null
-
- query_list += "[word]'"
- word = ""
-
- else if(char == "\"")
- if(word != "")
- usr << "\red SDQL: You have an error in your SDQL syntax, unexpected \" in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
- return null
-
- word = "\""
-
- for(i++, i <= len, i++)
- char = copytext(query_text, i, i + 1)
-
- if(char == "\"")
- if(copytext(query_text, i + 1, i + 2) == "'")
- word += "\""
- i++
-
- else
- break
-
- else
- word += char
-
- if(i > len)
- usr << "\red SDQL: You have an error in your SDQL syntax, unmatched \" in query: \"[query_text]\". Please check your syntax, and try again."
- return null
-
- query_list += "[word]\""
- word = ""
-
- else
- word += char
-
- if(word != "")
- query_list += word
-
- return query_list
+
+//Structured Datum Query Language. Basically SQL meets BYOND objects.
+
+//Note: For use in BS12, need text_starts_with proc, and to modify the action on select to use BS12's object edit command(s).
+
+/client/proc/SDQL_query(query_text as message)
+ set category = "Admin"
+ if(!check_rights(R_DEBUG)) //Shouldn't happen... but just to be safe.
+ message_admins("\red ERROR: Non-admin [usr.key] attempted to execute a SDQL query!")
+ log_admin("Non-admin [usr.key] attempted to execute a SDQL query!")
+
+ var/list/query_list = SDQL_tokenize(query_text)
+
+ if(query_list.len < 2)
+ if(query_list.len > 0)
+ usr << "\red SDQL: Too few discrete tokens in query \"[query_text]\". Please check your syntax and try again."
+ return
+
+ if(!(lowertext(query_list[1]) in list("select", "delete", "update")))
+ usr << "\red SDQL: Unknown query type: \"[query_list[1]]\" in query \"[query_text]\". Please check your syntax and try again."
+ return
+
+ var/list/types = list()
+
+ var/i
+ for(i = 2; i <= query_list.len; i += 2)
+ types += query_list[i]
+
+ if(i + 1 >= query_list.len || query_list[i + 1] != ",")
+ break
+
+ i++
+
+ var/list/from = list()
+
+ if(i <= query_list.len)
+ if(lowertext(query_list[i]) in list("from", "in"))
+ for(i++; i <= query_list.len; i += 2)
+ from += query_list[i]
+
+ if(i + 1 >= query_list.len || query_list[i + 1] != ",")
+ break
+
+ i++
+
+ if(from.len < 1)
+ from += "world"
+
+ var/list/set_vars = list()
+
+ if(lowertext(query_list[1]) == "update")
+ if(i <= query_list.len && lowertext(query_list[i]) == "set")
+ for(i++; i <= query_list.len; i++)
+ if(i + 2 <= query_list.len && query_list[i + 1] == "=")
+ set_vars += query_list[i]
+ set_vars[query_list[i]] = query_list[i + 2]
+
+ else
+ usr << "\red SDQL: Invalid set parameter in query \"[query_text]\". Please check your syntax and try again."
+ return
+
+ i += 3
+
+ if(i >= query_list.len || query_list[i] != ",")
+ break
+
+ if(set_vars.len < 1)
+ usr << "\red SDQL: Invalid or missing set in query \"[query_text]\". Please check your syntax and try again."
+ return
+
+ var/list/where = list()
+
+ if(i <= query_list.len && lowertext(query_list[i]) == "where")
+ where = query_list.Copy(i + 1)
+
+ var/list/from_objs = list()
+ if("world" in from)
+ from_objs += world
+ else
+ for(var/f in from)
+ if(copytext(f, 1, 2) == "'" || copytext(f, 1, 2) == "\"")
+ from_objs += locate(copytext(f, 2, length(f)))
+ else if(copytext(f, 1, 2) != "/")
+ from_objs += locate(f)
+ else
+ var/f2 = text2path(f)
+ if(text_starts_with(f, "/mob"))
+ for(var/mob/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/turf/space"))
+ for(var/turf/space/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/turf/simulated"))
+ for(var/turf/simulated/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/turf/unsimulated"))
+ for(var/turf/unsimulated/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/turf"))
+ for(var/turf/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/area"))
+ for(var/area/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/obj/item"))
+ for(var/obj/item/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/obj/machinery"))
+ for(var/obj/machinery/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/obj"))
+ for(var/obj/m in world)
+ if(istype(m, f2))
+ from_objs += m
+
+ else if(text_starts_with(f, "/atom"))
+ for(var/atom/m in world)
+ if(istype(m, f2))
+ from_objs += m
+/*
+ else
+ for(var/datum/m in world)
+ if(istype(m, f2))
+ from_objs += m
+*/
+
+ var/list/objs = list()
+
+ for(var/from_obj in from_objs)
+ if("*" in types)
+ objs += from_obj:contents
+ else
+ for(var/f in types)
+ if(copytext(f, 1, 2) == "'" || copytext(f, 1, 2) == "\"")
+ objs += locate(copytext(f, 2, length(f))) in from_obj
+ else if(copytext(f, 1, 2) != "/")
+ objs += locate(f) in from_obj
+ else
+ var/f2 = text2path(f)
+ if(text_starts_with(f, "/mob"))
+ for(var/mob/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/turf/space"))
+ for(var/turf/space/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/turf/simulated"))
+ for(var/turf/simulated/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/turf/unsimulated"))
+ for(var/turf/unsimulated/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/turf"))
+ for(var/turf/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/area"))
+ for(var/area/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/obj/item"))
+ for(var/obj/item/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/obj/machinery"))
+ for(var/obj/machinery/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/obj"))
+ for(var/obj/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else if(text_starts_with(f, "/atom"))
+ for(var/atom/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+ else
+ for(var/datum/m in from_obj)
+ if(istype(m, f2))
+ objs += m
+
+
+ for(var/datum/t in objs)
+ var/currently_false = 0
+ for(i = 1, i - 1 < where.len, i++)
+ var/v = where[i++]
+ var/compare_op = where[i++]
+ if(!(compare_op in list("==", "=", "<>", "<", ">", "<=", ">=", "!=")))
+ usr << "\red SDQL: Unknown comparison operator [compare_op] in where clause following [v] in query \"[query_text]\". Please check your syntax and try again."
+ return
+
+ var/j
+ for(j = i, j <= where.len, j++)
+ if(lowertext(where[j]) in list("and", "or", ";"))
+ break
+
+ if(!currently_false)
+ var/value = SDQL_text2value(t, v)
+ var/result = SDQL_evaluate(t, where.Copy(i, j))
+
+ switch(compare_op)
+ if("=", "==")
+ currently_false = !(value == result)
+
+ if("!=", "<>")
+ currently_false = !(value != result)
+
+ if("<")
+ currently_false = !(value < result)
+
+ if(">")
+ currently_false = !(value > result)
+
+ if("<=")
+ currently_false = !(value <= result)
+
+ if(">=")
+ currently_false = !(value >= result)
+
+
+ if(j > where.len || lowertext(where[j]) == ";")
+ break
+ else if(lowertext(where[j]) == "or")
+ if(currently_false)
+ currently_false = 0
+ else
+ break
+
+ i = j
+
+ if(currently_false)
+ objs -= t
+
+
+
+ usr << "\blue SQDL Query: [query_text]"
+ message_admins("[usr] executed SDQL query: \"[query_text]\".")
+/*
+ for(var/t in types)
+ usr << "Type: [t]"
+
+ for(var/t in from)
+ usr << "From: [t]"
+
+ for(var/t in set_vars)
+ usr << "Set: [t] = [set_vars[t]]"
+
+ if(where.len)
+ var/where_str = ""
+ for(var/t in where)
+ where_str += "[t] "
+
+ usr << "Where: [where_str]"
+
+ usr << "From objects:"
+ for(var/datum/t in from_objs)
+ usr << t
+
+ usr << "Objects:"
+ for(var/datum/t in objs)
+ usr << t
+*/
+ switch(lowertext(query_list[1]))
+ if("delete")
+ for(var/datum/t in objs)
+ qdel(t)
+
+ if("update")
+ for(var/datum/t in objs)
+ objs[t] = list()
+ for(var/v in set_vars)
+ if(v in t.vars)
+ objs[t][v] = SDQL_text2value(t, set_vars[v])
+
+ for(var/datum/t in objs)
+ for(var/v in objs[t])
+ t.vars[v] = objs[t][v]
+
+ if("select")
+ var/text = ""
+ for(var/datum/t in objs)
+ if(istype(t, /atom))
+ var/atom/a = t
+
+ if(a.x)
+ text += "\ref[t]: [t] at ([a.x], [a.y], [a.z]) "
+
+ else if(a.loc && a.loc.x)
+ text += "\ref[t]: [t] in [a.loc] at ([a.loc.x], [a.loc.y], [a.loc.z]) "
+
+ else
+ text += "\ref[t]: [t] "
+
+ else
+ text += "\ref[t]: [t] "
+
+ //text += "[t] "
+ usr << browse(text, "window=sdql_result")
+
+
+/client/Topic(href,href_list[],hsrc)
+ if(href_list["SDQL_select"])
+ debug_variables(locate(href_list["SDQL_select"]))
+
+ ..()
+
+
+/proc/SDQL_evaluate(datum/object, list/equation)
+ if(equation.len == 0)
+ return null
+
+ else if(equation.len == 1)
+ return SDQL_text2value(object, equation[1])
+
+ else if(equation[1] == "!")
+ return !SDQL_evaluate(object, equation.Copy(2))
+
+ else if(equation[1] == "-")
+ return -SDQL_evaluate(object, equation.Copy(2))
+
+
+ else
+ usr << "\red SDQL: Sorry, equations not yet supported :("
+ return null
+
+
+/proc/SDQL_text2value(datum/object, text)
+ if(text2num(text) != null)
+ return text2num(text)
+ else if(text == "null")
+ return null
+ else if(copytext(text, 1, 2) == "'" || copytext(text, 1, 2) == "\"" )
+ return copytext(text, 2, length(text))
+ else if(copytext(text, 1, 2) == "/")
+ return text2path(text)
+ else
+ if(findtext(text, "."))
+ var/split = findtext(text, ".")
+ var/v = copytext(text, 1, split)
+
+ if((v in object.vars) && istype(object.vars[v], /datum))
+ return SDQL_text2value(object.vars[v], copytext(text, split + 1))
+ else
+ return null
+
+ else
+ if(text in object.vars)
+ return object.vars[text]
+ else
+ return null
+
+
+/proc/text_starts_with(text, start)
+ if(copytext(text, 1, length(start) + 1) == start)
+ return 1
+ else
+ return 0
+
+
+
+
+
+/proc/SDQL_tokenize(query_text)
+
+ var/list/whitespace = list(" ", "\n", "\t")
+ var/list/single = list("(", ")", ",", "+", "-")
+ var/list/multi = list(
+ "=" = list("", "="),
+ "<" = list("", "=", ">"),
+ ">" = list("", "="),
+ "!" = list("", "="))
+
+ var/word = ""
+ var/list/query_list = list()
+ var/len = length(query_text)
+
+ for(var/i = 1, i <= len, i++)
+ var/char = copytext(query_text, i, i + 1)
+
+ if(char in whitespace)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ else if(char in single)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ query_list += char
+
+ else if(char in multi)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ var/char2 = copytext(query_text, i + 1, i + 2)
+
+ if(char2 in multi[char])
+ query_list += "[char][char2]"
+ i++
+
+ else
+ query_list += char
+
+ else if(char == "'")
+ if(word != "")
+ usr << "\red SDQL: You have an error in your SDQL syntax, unexpected ' in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
+ return null
+
+ word = "'"
+
+ for(i++, i <= len, i++)
+ char = copytext(query_text, i, i + 1)
+
+ if(char == "'")
+ if(copytext(query_text, i + 1, i + 2) == "'")
+ word += "'"
+ i++
+
+ else
+ break
+
+ else
+ word += char
+
+ if(i > len)
+ usr << "\red SDQL: You have an error in your SDQL syntax, unmatched ' in query: \"[query_text]\". Please check your syntax, and try again."
+ return null
+
+ query_list += "[word]'"
+ word = ""
+
+ else if(char == "\"")
+ if(word != "")
+ usr << "\red SDQL: You have an error in your SDQL syntax, unexpected \" in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
+ return null
+
+ word = "\""
+
+ for(i++, i <= len, i++)
+ char = copytext(query_text, i, i + 1)
+
+ if(char == "\"")
+ if(copytext(query_text, i + 1, i + 2) == "'")
+ word += "\""
+ i++
+
+ else
+ break
+
+ else
+ word += char
+
+ if(i > len)
+ usr << "\red SDQL: You have an error in your SDQL syntax, unmatched \" in query: \"[query_text]\". Please check your syntax, and try again."
+ return null
+
+ query_list += "[word]\""
+ word = ""
+
+ else
+ word += char
+
+ if(word != "")
+ query_list += word
+
+ return query_list
diff --git a/code/modules/admin/verbs/SDQL_2.dm b/code/modules/admin/verbs/SDQL_2.dm
index 549447da117..236237c23ad 100644
--- a/code/modules/admin/verbs/SDQL_2.dm
+++ b/code/modules/admin/verbs/SDQL_2.dm
@@ -1,426 +1,426 @@
-
-
-/client/proc/SDQL2_query(query_text as message)
- set category = "Admin"
- if(!check_rights(R_DEBUG)) //Shouldn't happen... but just to be safe.
- message_admins("\red ERROR: Non-admin [usr.key] attempted to execute a SDQL query!")
- log_admin("Non-admin [usr.key] attempted to execute a SDQL query!")
-
- if(!query_text || length(query_text) < 1)
- return
-
- //world << query_text
-
- var/list/query_list = SDQL2_tokenize(query_text)
-
- if(!query_list || query_list.len < 1)
- return
-
- var/list/query_tree = SDQL_parse(query_list)
-
- if(query_tree.len < 1)
- return
-
- var/list/from_objs = list()
- var/list/select_types = list()
-
- switch(query_tree[1])
- if("explain")
- SDQL_testout(query_tree["explain"])
- return
-
- if("call")
- if("on" in query_tree)
- select_types = query_tree["on"]
- else
- return
-
- if("select", "delete", "update")
- select_types = query_tree[query_tree[1]]
-
- from_objs = SDQL_from_objs(query_tree["from"])
-
- var/list/objs = list()
-
- for(var/type in select_types)
- var/char = copytext(type, 1, 2)
-
- if(char == "/" || char == "*")
- for(var/from in from_objs)
- objs += SDQL_get_all(type, from)
-
- else if(char == "'" || char == "\"")
- objs += locate(copytext(type, 2, length(type)))
-
- if("where" in query_tree)
- var/objs_temp = objs
- objs = list()
- for(var/datum/d in objs_temp)
- if(SDQL_expression(d, query_tree["where"]))
- objs += d
-
- //usr << "Query: [query_text]"
- message_admins("[usr] executed SDQL query: \"[query_text]\".")
-
- switch(query_tree[1])
- if("delete")
- for(var/datum/d in objs)
- del d
-
- if("select")
- var/text = ""
- for(var/datum/t in objs)
- if(istype(t, /atom))
- var/atom/a = t
-
- if(a.x)
- text += "\ref[t]: [t] at ([a.x], [a.y], [a.z]) "
-
- else if(a.loc && a.loc.x)
- text += "\ref[t]: [t] in [a.loc] at ([a.loc.x], [a.loc.y], [a.loc.z]) "
-
- else
- text += "\ref[t]: [t] "
-
- else
- text += "\ref[t]: [t] "
-
- usr << browse(text, "window=SDQL-result")
-
- if("update")
- if("set" in query_tree)
- var/list/set_list = query_tree["set"]
- for(var/datum/d in objs)
- var/list/vals = list()
- for(var/v in set_list)
- if(v in d.vars)
- vals += v
- vals[v] = SDQL_expression(d, set_list[v])
-
- if(istype(d, /turf))
- for(var/v in vals)
- if(v == "x" || v == "y" || v == "z")
- continue
-
- d.vars[v] = vals[v]
-
- else
- for(var/v in vals)
- d.vars[v] = vals[v]
-
-
-
-
-
-/proc/SDQL_parse(list/query_list)
- var/datum/SDQL_parser/parser = new(query_list)
- var/list/query_tree = parser.parse()
-
- del(parser)
-
- return query_tree
-
-
-
-/proc/SDQL_testout(list/query_tree, indent = 0)
- var/spaces = ""
- for(var/s = 0, s < indent, s++)
- spaces += " "
-
- for(var/item in query_tree)
- if(istype(item, /list))
- world << "[spaces]("
- SDQL_testout(item, indent + 1)
- world << "[spaces])"
-
- else
- world << "[spaces][item]"
-
- if(!isnum(item) && query_tree[item])
-
- if(istype(query_tree[item], /list))
- world << "[spaces] ("
- SDQL_testout(query_tree[item], indent + 2)
- world << "[spaces] )"
-
- else
- world << "[spaces] [query_tree[item]]"
-
-
-
-/proc/SDQL_from_objs(list/tree)
- if("world" in tree)
- return list(world)
-
- var/list/out = list()
-
- for(var/type in tree)
- var/char = copytext(type, 1, 2)
-
- if(char == "/")
- out += SDQL_get_all(type, world)
-
- else if(char == "'" || char == "\"")
- out += locate(copytext(type, 2, length(type)))
-
- return out
-
-
-/proc/SDQL_get_all(type, location)
- var/list/out = list()
-
- if(type == "*")
- for(var/datum/d in location)
- out += d
-
- return out
-
- type = text2path(type)
-
- if(ispath(type, /mob))
- for(var/mob/d in location)
- if(istype(d, type))
- out += d
-
- else if(ispath(type, /turf))
- for(var/turf/d in location)
- if(istype(d, type))
- out += d
-
- else if(ispath(type, /obj))
- for(var/obj/d in location)
- if(istype(d, type))
- out += d
-
- else if(ispath(type, /area))
- for(var/area/d in location)
- if(istype(d, type))
- out += d
-
- else if(ispath(type, /atom))
- for(var/atom/d in location)
- if(istype(d, type))
- out += d
-
- else
- for(var/datum/d in location)
- if(istype(d, type))
- out += d
-
- return out
-
-
-/proc/SDQL_expression(datum/object, list/expression, start = 1)
- var/result = 0
- var/val
-
- for(var/i = start, i <= expression.len, i++)
- var/op = ""
-
- if(i > start)
- op = expression[i]
- i++
-
- var/list/ret = SDQL_value(object, expression, i)
- val = ret["val"]
- i = ret["i"]
-
- if(op != "")
- switch(op)
- if("+")
- result += val
- if("-")
- result -= val
- if("*")
- result *= val
- if("/")
- result /= val
- if("&")
- result &= val
- if("|")
- result |= val
- if("^")
- result ^= val
- if("=", "==")
- result = (result == val)
- if("!=", "<>")
- result = (result != val)
- if("<")
- result = (result < val)
- if("<=")
- result = (result <= val)
- if(">")
- result = (result > val)
- if(">=")
- result = (result >= val)
- if("and", "&&")
- result = (result && val)
- if("or", "||")
- result = (result || val)
- else
- usr << "\red SDQL2: Unknown op [op]"
- result = null
- else
- result = val
-
- return result
-
-/proc/SDQL_value(datum/object, list/expression, start = 1)
- var/i = start
- var/val = null
-
- if(i > expression.len)
- return list("val" = null, "i" = i)
-
- if(istype(expression[i], /list))
- val = SDQL_expression(object, expression[i])
-
- else if(expression[i] == "!")
- var/list/ret = SDQL_value(object, expression, i + 1)
- val = !ret["val"]
- i = ret["i"]
-
- else if(expression[i] == "~")
- var/list/ret = SDQL_value(object, expression, i + 1)
- val = ~ret["val"]
- i = ret["i"]
-
- else if(expression[i] == "-")
- var/list/ret = SDQL_value(object, expression, i + 1)
- val = -ret["val"]
- i = ret["i"]
-
- else if(expression[i] == "null")
- val = null
-
- else if(isnum(expression[i]))
- val = expression[i]
-
- else if(copytext(expression[i], 1, 2) in list("'", "\""))
- val = copytext(expression[i], 2, length(expression[i]))
-
- else
- val = SDQL_var(object, expression, i)
- i = expression.len
-
- return list("val" = val, "i" = i)
-
-/proc/SDQL_var(datum/object, list/expression, start = 1)
-
- if(expression[start] in object.vars)
-
- if(start < expression.len && expression[start + 1] == ".")
- return SDQL_var(object.vars[expression[start]], expression[start + 2])
-
- else
- return object.vars[expression[start]]
-
- else
- return null
-
-/proc/SDQL2_tokenize(query_text)
-
- var/list/whitespace = list(" ", "\n", "\t")
- var/list/single = list("(", ")", ",", "+", "-", ".")
- var/list/multi = list(
- "=" = list("", "="),
- "<" = list("", "=", ">"),
- ">" = list("", "="),
- "!" = list("", "="))
-
- var/word = ""
- var/list/query_list = list()
- var/len = length(query_text)
-
- for(var/i = 1, i <= len, i++)
- var/char = copytext(query_text, i, i + 1)
-
- if(char in whitespace)
- if(word != "")
- query_list += word
- word = ""
-
- else if(char in single)
- if(word != "")
- query_list += word
- word = ""
-
- query_list += char
-
- else if(char in multi)
- if(word != "")
- query_list += word
- word = ""
-
- var/char2 = copytext(query_text, i + 1, i + 2)
-
- if(char2 in multi[char])
- query_list += "[char][char2]"
- i++
-
- else
- query_list += char
-
- else if(char == "'")
- if(word != "")
- usr << "\red SDQL2: You have an error in your SDQL syntax, unexpected ' in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
- return null
-
- word = "'"
-
- for(i++, i <= len, i++)
- char = copytext(query_text, i, i + 1)
-
- if(char == "'")
- if(copytext(query_text, i + 1, i + 2) == "'")
- word += "'"
- i++
-
- else
- break
-
- else
- word += char
-
- if(i > len)
- usr << "\red SDQL2: You have an error in your SDQL syntax, unmatched ' in query: \"[query_text]\". Please check your syntax, and try again."
- return null
-
- query_list += "[word]'"
- word = ""
-
- else if(char == "\"")
- if(word != "")
- usr << "\red SDQL2: You have an error in your SDQL syntax, unexpected \" in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
- return null
-
- word = "\""
-
- for(i++, i <= len, i++)
- char = copytext(query_text, i, i + 1)
-
- if(char == "\"")
- if(copytext(query_text, i + 1, i + 2) == "'")
- word += "\""
- i++
-
- else
- break
-
- else
- word += char
-
- if(i > len)
- usr << "\red SDQL2: You have an error in your SDQL syntax, unmatched \" in query: \"[query_text]\". Please check your syntax, and try again."
- return null
-
- query_list += "[word]\""
- word = ""
-
- else
- word += char
-
- if(word != "")
- query_list += word
-
- return query_list
+
+
+/client/proc/SDQL2_query(query_text as message)
+ set category = "Admin"
+ if(!check_rights(R_DEBUG)) //Shouldn't happen... but just to be safe.
+ message_admins("\red ERROR: Non-admin [usr.key] attempted to execute a SDQL query!")
+ log_admin("Non-admin [usr.key] attempted to execute a SDQL query!")
+
+ if(!query_text || length(query_text) < 1)
+ return
+
+ //world << query_text
+
+ var/list/query_list = SDQL2_tokenize(query_text)
+
+ if(!query_list || query_list.len < 1)
+ return
+
+ var/list/query_tree = SDQL_parse(query_list)
+
+ if(query_tree.len < 1)
+ return
+
+ var/list/from_objs = list()
+ var/list/select_types = list()
+
+ switch(query_tree[1])
+ if("explain")
+ SDQL_testout(query_tree["explain"])
+ return
+
+ if("call")
+ if("on" in query_tree)
+ select_types = query_tree["on"]
+ else
+ return
+
+ if("select", "delete", "update")
+ select_types = query_tree[query_tree[1]]
+
+ from_objs = SDQL_from_objs(query_tree["from"])
+
+ var/list/objs = list()
+
+ for(var/type in select_types)
+ var/char = copytext(type, 1, 2)
+
+ if(char == "/" || char == "*")
+ for(var/from in from_objs)
+ objs += SDQL_get_all(type, from)
+
+ else if(char == "'" || char == "\"")
+ objs += locate(copytext(type, 2, length(type)))
+
+ if("where" in query_tree)
+ var/objs_temp = objs
+ objs = list()
+ for(var/datum/d in objs_temp)
+ if(SDQL_expression(d, query_tree["where"]))
+ objs += d
+
+ //usr << "Query: [query_text]"
+ message_admins("[usr] executed SDQL query: \"[query_text]\".")
+
+ switch(query_tree[1])
+ if("delete")
+ for(var/datum/d in objs)
+ qdel(d)
+
+ if("select")
+ var/text = ""
+ for(var/datum/t in objs)
+ if(istype(t, /atom))
+ var/atom/a = t
+
+ if(a.x)
+ text += "\ref[t]: [t] at ([a.x], [a.y], [a.z]) "
+
+ else if(a.loc && a.loc.x)
+ text += "\ref[t]: [t] in [a.loc] at ([a.loc.x], [a.loc.y], [a.loc.z]) "
+
+ else
+ text += "\ref[t]: [t] "
+
+ else
+ text += "\ref[t]: [t] "
+
+ usr << browse(text, "window=SDQL-result")
+
+ if("update")
+ if("set" in query_tree)
+ var/list/set_list = query_tree["set"]
+ for(var/datum/d in objs)
+ var/list/vals = list()
+ for(var/v in set_list)
+ if(v in d.vars)
+ vals += v
+ vals[v] = SDQL_expression(d, set_list[v])
+
+ if(istype(d, /turf))
+ for(var/v in vals)
+ if(v == "x" || v == "y" || v == "z")
+ continue
+
+ d.vars[v] = vals[v]
+
+ else
+ for(var/v in vals)
+ d.vars[v] = vals[v]
+
+
+
+
+
+/proc/SDQL_parse(list/query_list)
+ var/datum/SDQL_parser/parser = new(query_list)
+ var/list/query_tree = parser.parse()
+
+ qdel(parser)
+
+ return query_tree
+
+
+
+/proc/SDQL_testout(list/query_tree, indent = 0)
+ var/spaces = ""
+ for(var/s = 0, s < indent, s++)
+ spaces += " "
+
+ for(var/item in query_tree)
+ if(istype(item, /list))
+ world << "[spaces]("
+ SDQL_testout(item, indent + 1)
+ world << "[spaces])"
+
+ else
+ world << "[spaces][item]"
+
+ if(!isnum(item) && query_tree[item])
+
+ if(istype(query_tree[item], /list))
+ world << "[spaces] ("
+ SDQL_testout(query_tree[item], indent + 2)
+ world << "[spaces] )"
+
+ else
+ world << "[spaces] [query_tree[item]]"
+
+
+
+/proc/SDQL_from_objs(list/tree)
+ if("world" in tree)
+ return list(world)
+
+ var/list/out = list()
+
+ for(var/type in tree)
+ var/char = copytext(type, 1, 2)
+
+ if(char == "/")
+ out += SDQL_get_all(type, world)
+
+ else if(char == "'" || char == "\"")
+ out += locate(copytext(type, 2, length(type)))
+
+ return out
+
+
+/proc/SDQL_get_all(type, location)
+ var/list/out = list()
+
+ if(type == "*")
+ for(var/datum/d in location)
+ out += d
+
+ return out
+
+ type = text2path(type)
+
+ if(ispath(type, /mob))
+ for(var/mob/d in location)
+ if(istype(d, type))
+ out += d
+
+ else if(ispath(type, /turf))
+ for(var/turf/d in location)
+ if(istype(d, type))
+ out += d
+
+ else if(ispath(type, /obj))
+ for(var/obj/d in location)
+ if(istype(d, type))
+ out += d
+
+ else if(ispath(type, /area))
+ for(var/area/d in location)
+ if(istype(d, type))
+ out += d
+
+ else if(ispath(type, /atom))
+ for(var/atom/d in location)
+ if(istype(d, type))
+ out += d
+
+ else
+ for(var/datum/d in location)
+ if(istype(d, type))
+ out += d
+
+ return out
+
+
+/proc/SDQL_expression(datum/object, list/expression, start = 1)
+ var/result = 0
+ var/val
+
+ for(var/i = start, i <= expression.len, i++)
+ var/op = ""
+
+ if(i > start)
+ op = expression[i]
+ i++
+
+ var/list/ret = SDQL_value(object, expression, i)
+ val = ret["val"]
+ i = ret["i"]
+
+ if(op != "")
+ switch(op)
+ if("+")
+ result += val
+ if("-")
+ result -= val
+ if("*")
+ result *= val
+ if("/")
+ result /= val
+ if("&")
+ result &= val
+ if("|")
+ result |= val
+ if("^")
+ result ^= val
+ if("=", "==")
+ result = (result == val)
+ if("!=", "<>")
+ result = (result != val)
+ if("<")
+ result = (result < val)
+ if("<=")
+ result = (result <= val)
+ if(">")
+ result = (result > val)
+ if(">=")
+ result = (result >= val)
+ if("and", "&&")
+ result = (result && val)
+ if("or", "||")
+ result = (result || val)
+ else
+ usr << "\red SDQL2: Unknown op [op]"
+ result = null
+ else
+ result = val
+
+ return result
+
+/proc/SDQL_value(datum/object, list/expression, start = 1)
+ var/i = start
+ var/val = null
+
+ if(i > expression.len)
+ return list("val" = null, "i" = i)
+
+ if(istype(expression[i], /list))
+ val = SDQL_expression(object, expression[i])
+
+ else if(expression[i] == "!")
+ var/list/ret = SDQL_value(object, expression, i + 1)
+ val = !ret["val"]
+ i = ret["i"]
+
+ else if(expression[i] == "~")
+ var/list/ret = SDQL_value(object, expression, i + 1)
+ val = ~ret["val"]
+ i = ret["i"]
+
+ else if(expression[i] == "-")
+ var/list/ret = SDQL_value(object, expression, i + 1)
+ val = -ret["val"]
+ i = ret["i"]
+
+ else if(expression[i] == "null")
+ val = null
+
+ else if(isnum(expression[i]))
+ val = expression[i]
+
+ else if(copytext(expression[i], 1, 2) in list("'", "\""))
+ val = copytext(expression[i], 2, length(expression[i]))
+
+ else
+ val = SDQL_var(object, expression, i)
+ i = expression.len
+
+ return list("val" = val, "i" = i)
+
+/proc/SDQL_var(datum/object, list/expression, start = 1)
+
+ if(expression[start] in object.vars)
+
+ if(start < expression.len && expression[start + 1] == ".")
+ return SDQL_var(object.vars[expression[start]], expression[start + 2])
+
+ else
+ return object.vars[expression[start]]
+
+ else
+ return null
+
+/proc/SDQL2_tokenize(query_text)
+
+ var/list/whitespace = list(" ", "\n", "\t")
+ var/list/single = list("(", ")", ",", "+", "-", ".")
+ var/list/multi = list(
+ "=" = list("", "="),
+ "<" = list("", "=", ">"),
+ ">" = list("", "="),
+ "!" = list("", "="))
+
+ var/word = ""
+ var/list/query_list = list()
+ var/len = length(query_text)
+
+ for(var/i = 1, i <= len, i++)
+ var/char = copytext(query_text, i, i + 1)
+
+ if(char in whitespace)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ else if(char in single)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ query_list += char
+
+ else if(char in multi)
+ if(word != "")
+ query_list += word
+ word = ""
+
+ var/char2 = copytext(query_text, i + 1, i + 2)
+
+ if(char2 in multi[char])
+ query_list += "[char][char2]"
+ i++
+
+ else
+ query_list += char
+
+ else if(char == "'")
+ if(word != "")
+ usr << "\red SDQL2: You have an error in your SDQL syntax, unexpected ' in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
+ return null
+
+ word = "'"
+
+ for(i++, i <= len, i++)
+ char = copytext(query_text, i, i + 1)
+
+ if(char == "'")
+ if(copytext(query_text, i + 1, i + 2) == "'")
+ word += "'"
+ i++
+
+ else
+ break
+
+ else
+ word += char
+
+ if(i > len)
+ usr << "\red SDQL2: You have an error in your SDQL syntax, unmatched ' in query: \"[query_text]\". Please check your syntax, and try again."
+ return null
+
+ query_list += "[word]'"
+ word = ""
+
+ else if(char == "\"")
+ if(word != "")
+ usr << "\red SDQL2: You have an error in your SDQL syntax, unexpected \" in query: \"[query_text]\" following \"[word]\". Please check your syntax, and try again."
+ return null
+
+ word = "\""
+
+ for(i++, i <= len, i++)
+ char = copytext(query_text, i, i + 1)
+
+ if(char == "\"")
+ if(copytext(query_text, i + 1, i + 2) == "'")
+ word += "\""
+ i++
+
+ else
+ break
+
+ else
+ word += char
+
+ if(i > len)
+ usr << "\red SDQL2: You have an error in your SDQL syntax, unmatched \" in query: \"[query_text]\". Please check your syntax, and try again."
+ return null
+
+ query_list += "[word]\""
+ word = ""
+
+ else
+ word += char
+
+ if(word != "")
+ query_list += word
+
+ return query_list
diff --git a/code/modules/admin/verbs/antag-ooc.dm b/code/modules/admin/verbs/antag-ooc.dm
index 53a2c709fca..9260baf3dd7 100644
--- a/code/modules/admin/verbs/antag-ooc.dm
+++ b/code/modules/admin/verbs/antag-ooc.dm
@@ -13,7 +13,7 @@
display_name = holder.fakekey
for(var/mob/M in mob_list)
- if((M.mind && M.mind.special_role && M.client) || (M.client && M.client.holder))
+ if((M.mind && M.mind.special_role && M.client) || check_rights(R_ADMIN, 0, M))
M << "" + create_text_tag("aooc", "Antag-OOC:", M.client) + " [display_name]:[msg]"
log_ooc("(ANTAG) [key] : [msg]")
\ No newline at end of file
diff --git a/code/modules/admin/verbs/buildmode.dm b/code/modules/admin/verbs/buildmode.dm
index 71bdabf4be0..4b90283a56d 100644
--- a/code/modules/admin/verbs/buildmode.dm
+++ b/code/modules/admin/verbs/buildmode.dm
@@ -8,7 +8,7 @@
M.client.show_popup_menus = 1
for(var/obj/effect/bmode/buildholder/H)
if(H.cl == M.client)
- del(H)
+ qdel(H)
else
log_admin("[key_name(usr)] has entered build mode.")
M.client.buildmode = 1
@@ -220,7 +220,7 @@
T.ChangeTurf(/turf/simulated/wall)
return
else if(istype(object,/obj))
- del(object)
+ qdel(object)
return
else if(istype(object,/turf) && pa.Find("alt") && pa.Find("left"))
new/obj/machinery/door/airlock(get_turf(object))
@@ -250,7 +250,7 @@
var/obj/A = new holder.buildmode.objholder (get_turf(object))
A.set_dir(holder.builddir.dir)
else if(pa.Find("right"))
- if(isobj(object)) del(object)
+ if(isobj(object)) qdel(object)
if(pa.Find("middle"))
holder.buildmode.objholder = text2path("[object.type]")
if(holder.buildmode.objsay) usr << "[object.type]"
diff --git a/code/modules/admin/verbs/cinematic.dm b/code/modules/admin/verbs/cinematic.dm
index e21de8641d7..a643b370fc4 100644
--- a/code/modules/admin/verbs/cinematic.dm
+++ b/code/modules/admin/verbs/cinematic.dm
@@ -1,12 +1,17 @@
/client/proc/cinematic(var/cinematic as anything in list("explosion",null))
- set name = "cinematic"
+ set name = "Cinematic"
set category = "Fun"
set desc = "Shows a cinematic." // Intended for testing but I thought it might be nice for events on the rare occasion Feel free to comment it out if it's not wanted.
- set hidden = 1
+
+ if(!check_rights(R_FUN))
+ return
+
if(alert("Are you sure you want to run [cinematic]?","Confirmation","Yes","No")=="No") return
if(!ticker) return
switch(cinematic)
if("explosion")
+ if(alert("The game will be over. Are you really sure?", "Confirmation" ,"Continue", "Cancel") == "Cancel")
+ return
var/parameter = input(src,"station_missed = ?","Enter Parameter",0) as num
var/override
switch(parameter)
@@ -15,4 +20,8 @@
if(0)
override = input(src,"mode = ?","Enter Parameter",null) as anything in list("blob","mercenary","AI malfunction","no override")
ticker.station_explosion_cinematic(parameter,override)
+
+ log_admin("[key_name(src)] launched cinematic \"[cinematic]\"")
+ message_admins("[key_name_admin(src)] launched cinematic \"[cinematic]\"", 1)
+
return
\ No newline at end of file
diff --git a/code/modules/admin/verbs/debug.dm b/code/modules/admin/verbs/debug.dm
index 325f04f9e89..10128837818 100644
--- a/code/modules/admin/verbs/debug.dm
+++ b/code/modules/admin/verbs/debug.dm
@@ -350,7 +350,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
if(hsbitem)
for(var/atom/O in world)
if(istype(O, hsbitem))
- del(O)
+ qdel(O)
log_admin("[key_name(src)] has deleted all instances of [hsbitem].")
message_admins("[key_name_admin(src)] has deleted all instances of [hsbitem].", 0)
feedback_add_details("admin_verb","DELA") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
@@ -420,7 +420,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
var/mob/adminmob = src.mob
M.ckey = src.ckey
if( isobserver(adminmob) )
- del(adminmob)
+ qdel(adminmob)
feedback_add_details("admin_verb","ADC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
@@ -525,6 +525,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
//log_admin("[key_name(src)] has alienized [M.key].")
var/list/dresspacks = list(
"strip",
+ "job",
"standard space gear",
"tournament standard red",
"tournament standard green",
@@ -555,10 +556,25 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
for (var/obj/item/I in M)
if (istype(I, /obj/item/weapon/implant))
continue
- del(I)
+ M.drop_from_inventory(I)
+ if(I.loc != M)
+ qdel(I)
switch(dresscode)
if ("strip")
//do nothing
+ if ("job")
+ var/selected_job = input("Select job", "Robust quick dress shop") as null|anything in joblist
+ if (isnull(selected_job))
+ return
+
+ var/datum/job/job = job_master.GetJob(selected_job)
+ if(!job)
+ return
+
+ job.equip(M)
+ job.apply_fingerprints(M)
+ job_master.spawnId(M, selected_job)
+
if ("standard space gear")
M.equip_to_slot_or_del(new /obj/item/clothing/shoes/black(M), slot_shoes)
@@ -590,7 +606,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/shoes/black(M), slot_shoes)
M.equip_to_slot_or_del(new /obj/item/clothing/suit/storage/det_suit(M), slot_wear_suit)
- M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/monocle(M), slot_glasses)
+ M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/plain/monocle(M), slot_glasses)
M.equip_to_slot_or_del(new /obj/item/clothing/head/det_hat(M), slot_head)
M.equip_to_slot_or_del(new /obj/item/weapon/cloaking_device(M), slot_r_store)
@@ -614,7 +630,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/shoes/black(M), slot_shoes)
var/obj/item/weapon/storage/backpack/backpack = new(M)
for(var/obj/item/I in backpack)
- del(I)
+ qdel(I)
M.equip_to_slot_or_del(backpack, slot_back)
M.equip_to_slot_or_del(new /obj/item/weapon/mop(M), slot_r_hand)
@@ -660,7 +676,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/mask/gas/clown_hat(M), slot_wear_mask)
M.equip_to_slot_or_del(new /obj/item/clothing/head/chaplain_hood(M), slot_head)
M.equip_to_slot_or_del(new /obj/item/device/radio/headset(M), slot_l_ear)
- M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/monocle(M), slot_glasses)
+ M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/plain/monocle(M), slot_glasses)
M.equip_to_slot_or_del(new /obj/item/clothing/suit/chaplain_hoodie(M), slot_wear_suit)
M.equip_to_slot_or_del(new /obj/item/weapon/bikehorn(M), slot_r_store)
@@ -681,7 +697,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/mask/surgical(M), slot_wear_mask)
M.equip_to_slot_or_del(new /obj/item/clothing/head/welding(M), slot_head)
M.equip_to_slot_or_del(new /obj/item/device/radio/headset(M), slot_l_ear)
- M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/monocle(M), slot_glasses)
+ M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/plain/monocle(M), slot_glasses)
M.equip_to_slot_or_del(new /obj/item/clothing/suit/apron(M), slot_wear_suit)
M.equip_to_slot_or_del(new /obj/item/weapon/kitchenknife(M), slot_l_store)
M.equip_to_slot_or_del(new /obj/item/weapon/scalpel(M), slot_r_store)
@@ -705,7 +721,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
var/obj/item/weapon/storage/secure/briefcase/sec_briefcase = new(M)
for(var/obj/item/briefcase_item in sec_briefcase)
- del(briefcase_item)
+ qdel(briefcase_item)
for(var/i=3, i>0, i--)
sec_briefcase.contents += new /obj/item/weapon/spacecash/c1000
sec_briefcase.contents += new /obj/item/weapon/gun/energy/crossbow
@@ -832,7 +848,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/shoes/combat(M), slot_shoes)
M.equip_to_slot_or_del(new /obj/item/clothing/gloves/combat(M), slot_gloves)
M.equip_to_slot_or_del(new /obj/item/device/radio/headset/heads/captain(M), slot_l_ear)
- M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/eyepatch(M), slot_glasses)
+ M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/plain/eyepatch(M), slot_glasses)
M.equip_to_slot_or_del(new /obj/item/clothing/mask/smokable/cigarette/cigar/havana(M), slot_wear_mask)
M.equip_to_slot_or_del(new /obj/item/clothing/head/helmet/space/deathsquad/beret(M), slot_head)
M.equip_to_slot_or_del(new /obj/item/weapon/gun/energy/pulse_rifle/M1911(M), slot_belt)
@@ -888,7 +904,7 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
M.equip_to_slot_or_del(new /obj/item/clothing/shoes/combat(M), slot_shoes)
M.equip_to_slot_or_del(new /obj/item/clothing/gloves/combat(M), slot_gloves)
M.equip_to_slot_or_del(new /obj/item/device/radio/headset/heads/captain(M), slot_l_ear)
- M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/eyepatch(M), slot_glasses)
+ M.equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal/plain/eyepatch(M), slot_glasses)
M.equip_to_slot_or_del(new /obj/item/clothing/suit/hgpirate(M), slot_wear_suit)
M.equip_to_slot_or_del(new /obj/item/weapon/storage/backpack/satchel(M), slot_back)
M.equip_to_slot_or_del(new /obj/item/weapon/gun/projectile/revolver/mateba(M), slot_belt)
@@ -927,9 +943,9 @@ But you can call procs that are of type /mob/living/carbon/human/proc/ for that
spawn(30)
for(var/obj/machinery/the_singularitygen/G in world)
if(G.anchored)
- var/obj/machinery/singularity/S = new /obj/machinery/singularity(get_turf(G), 50)
+ var/obj/singularity/S = new /obj/singularity(get_turf(G), 50)
spawn(0)
- del(G)
+ qdel(G)
S.energy = 1750
S.current_size = 7
S.icon = 'icons/effects/224x224.dmi'
diff --git a/code/modules/admin/verbs/dice.dm b/code/modules/admin/verbs/dice.dm
new file mode 100644
index 00000000000..e5877a9da28
--- /dev/null
+++ b/code/modules/admin/verbs/dice.dm
@@ -0,0 +1,24 @@
+/client/proc/roll_dices()
+ set category = "Fun"
+ set name = "Roll Dice"
+ if(!check_rights(R_FUN))
+ return
+
+ var/sum = input("How many times should we throw?") as num
+ var/side = input("Select the number of sides.") as num
+ if(!side)
+ side = 6
+ if(!sum)
+ sum = 2
+
+ var/dice = num2text(sum) + "d" + num2text(side)
+
+ if(alert("Do you want to inform the world about your game?",,"Yes", "No") == "Yes")
+ world << "
The dice have been rolled by Gods!
"
+
+ var/result = roll(dice)
+
+ if(alert("Do you want to inform the world about the result?",,"Yes", "No") == "Yes")
+ world << "
Gods rolled [dice], result is [result]
"
+
+ message_admins("[key_name_admin(src)] rolled dice [dice], result is [result]", 1)
\ No newline at end of file
diff --git a/code/modules/admin/verbs/mapping.dm b/code/modules/admin/verbs/mapping.dm
index c6f91e89d3c..bd3c4be0d92 100644
--- a/code/modules/admin/verbs/mapping.dm
+++ b/code/modules/admin/verbs/mapping.dm
@@ -55,7 +55,7 @@ var/intercom_range_display_status = 0
for(var/obj/effect/debugging/camera_range/C in world)
- del(C)
+ qdel(C)
if(camera_range_display_status)
for(var/obj/machinery/camera/C in cameranet.cameras)
@@ -114,14 +114,14 @@ var/intercom_range_display_status = 0
intercom_range_display_status = 1
for(var/obj/effect/debugging/marker/M in world)
- del(M)
+ qdel(M)
if(intercom_range_display_status)
for(var/obj/item/device/radio/intercom/I in world)
for(var/turf/T in orange(7,I))
var/obj/effect/debugging/marker/F = new/obj/effect/debugging/marker(T)
if (!(F in view(7,I.loc)))
- del(F)
+ qdel(F)
feedback_add_details("admin_verb","mIRD") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
var/list/debug_verbs = list (
@@ -276,7 +276,7 @@ var/list/debug_verbs = list (
var/datum/controller/air_system/old_air = air_master
for(var/zone/zone in old_air.zones)
zone.c_invalidate()
- del old_air
+ qdel(old_air)
air_master = new
air_master.Setup()
spawn air_master.Start()
diff --git a/code/modules/admin/verbs/massmodvar.dm b/code/modules/admin/verbs/massmodvar.dm
index a6b4bf7d167..87827dcf4b7 100644
--- a/code/modules/admin/verbs/massmodvar.dm
+++ b/code/modules/admin/verbs/massmodvar.dm
@@ -208,8 +208,8 @@
O.vars[variable]) as num|null
if(new_value == null) return
- if(variable=="luminosity")
- O.SetLuminosity(new_value)
+ if(variable=="light_range")
+ O.set_light(new_value)
else
O.vars[variable] = new_value
@@ -217,24 +217,24 @@
if(istype(O, /mob))
for(var/mob/M in mob_list)
if ( istype(M , O.type) )
- if(variable=="luminosity")
- M.SetLuminosity(new_value)
+ if(variable=="light_range")
+ M.set_light(new_value)
else
M.vars[variable] = O.vars[variable]
else if(istype(O, /obj))
for(var/obj/A in world)
if ( istype(A , O.type) )
- if(variable=="luminosity")
- A.SetLuminosity(new_value)
+ if(variable=="light_range")
+ A.set_light(new_value)
else
A.vars[variable] = O.vars[variable]
else if(istype(O, /turf))
for(var/turf/A in world)
if ( istype(A , O.type) )
- if(variable=="luminosity")
- A.SetLuminosity(new_value)
+ if(variable=="light_range")
+ A.set_light(new_value)
else
A.vars[variable] = O.vars[variable]
@@ -242,24 +242,24 @@
if(istype(O, /mob))
for(var/mob/M in mob_list)
if (M.type == O.type)
- if(variable=="luminosity")
- M.SetLuminosity(new_value)
+ if(variable=="light_range")
+ M.set_light(new_value)
else
M.vars[variable] = O.vars[variable]
else if(istype(O, /obj))
for(var/obj/A in world)
if (A.type == O.type)
- if(variable=="luminosity")
- A.SetLuminosity(new_value)
+ if(variable=="light_range")
+ A.set_light(new_value)
else
A.vars[variable] = O.vars[variable]
else if(istype(O, /turf))
for(var/turf/A in world)
if (A.type == O.type)
- if(variable=="luminosity")
- A.SetLuminosity(new_value)
+ if(variable=="light_range")
+ A.set_light(new_value)
else
A.vars[variable] = O.vars[variable]
@@ -372,4 +372,4 @@
A.vars[variable] = O.vars[variable]
log_admin("[key_name(src)] mass modified [original_name]'s [variable] to [O.vars[variable]]")
- message_admins("[key_name_admin(src)] mass modified [original_name]'s [variable] to [O.vars[variable]]", 1)
\ No newline at end of file
+ message_admins("[key_name_admin(src)] mass modified [original_name]'s [variable] to [O.vars[variable]]", 1)
diff --git a/code/modules/admin/verbs/modifyvariables.dm b/code/modules/admin/verbs/modifyvariables.dm
index fce2aa59dc5..bdff5fb73ab 100644
--- a/code/modules/admin/verbs/modifyvariables.dm
+++ b/code/modules/admin/verbs/modifyvariables.dm
@@ -455,10 +455,10 @@ var/list/forbidden_varedit_object_types = list(
O.vars[variable] = var_new
if("num")
- if(variable=="luminosity")
+ if(variable=="light_range")
var/var_new = input("Enter new number:","Num",O.vars[variable]) as null|num
if(var_new == null) return
- O.SetLuminosity(var_new)
+ O.set_light(var_new)
else if(variable=="stat")
var/var_new = input("Enter new number:","Num",O.vars[variable]) as null|num
if(var_new == null) return
diff --git a/code/modules/admin/verbs/possess.dm b/code/modules/admin/verbs/possess.dm
index de69f149d7d..6de30853ce6 100644
--- a/code/modules/admin/verbs/possess.dm
+++ b/code/modules/admin/verbs/possess.dm
@@ -2,7 +2,7 @@
set name = "Possess Obj"
set category = "Object"
- if(istype(O,/obj/machinery/singularity))
+ if(istype(O,/obj/singularity))
if(config.forbid_singulo_possession)
usr << "It is forbidden to possess singularities."
return
diff --git a/code/modules/admin/verbs/pray.dm b/code/modules/admin/verbs/pray.dm
index 8b2d0700039..d987c52260b 100644
--- a/code/modules/admin/verbs/pray.dm
+++ b/code/modules/admin/verbs/pray.dm
@@ -28,15 +28,13 @@
feedback_add_details("admin_verb","PR") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
//log_admin("HELP: [key_name(src)]: [msg]")
-/proc/Centcomm_announce(var/text , var/mob/Sender , var/iamessage)
- var/msg = sanitize(text)
+/proc/Centcomm_announce(var/msg, var/mob/Sender, var/iamessage)
msg = "\blue CENTCOMM[iamessage ? " IA" : ""]:[key_name(Sender, 1)] (PP) (VV) (SM) (JMP) (CA) (BSA) (RPLY): [msg]"
for(var/client/C in admins)
if(R_ADMIN & C.holder.rights)
C << msg
-/proc/Syndicate_announce(var/text , var/mob/Sender)
- var/msg = sanitize(text)
+/proc/Syndicate_announce(var/msg, var/mob/Sender)
msg = "\blue ILLEGAL:[key_name(Sender, 1)] (PP) (VV) (SM) (JMP) (CA) (BSA) (RPLY): [msg]"
for(var/client/C in admins)
if(R_ADMIN & C.holder.rights)
diff --git a/code/modules/admin/verbs/randomverbs.dm b/code/modules/admin/verbs/randomverbs.dm
index 64e44e17e90..fd55a5a1e94 100644
--- a/code/modules/admin/verbs/randomverbs.dm
+++ b/code/modules/admin/verbs/randomverbs.dm
@@ -527,7 +527,7 @@ Traitors and the like can also be revived with the previous role mostly intact.
switch(alert("Should this be announced to the general population?",,"Yes","No"))
if("Yes")
- command_announcement.Announce(input, customname, new_sound = 'sound/AI/commandreport.ogg');
+ command_announcement.Announce(input, customname, new_sound = 'sound/AI/commandreport.ogg', msg_sanitized = 1);
if("No")
world << "\red New NanoTrasen Update available at all communication consoles."
world << sound('sound/AI/commandreport.ogg')
@@ -548,7 +548,7 @@ Traitors and the like can also be revived with the previous role mostly intact.
log_admin("[key_name(usr)] deleted [O] at ([O.x],[O.y],[O.z])")
message_admins("[key_name_admin(usr)] deleted [O] at ([O.x],[O.y],[O.z])", 1)
feedback_add_details("admin_verb","DEL") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
- del(O)
+ qdel(O)
/client/proc/cmd_admin_list_open_jobs()
set category = "Admin"
@@ -686,7 +686,7 @@ Traitors and the like can also be revived with the previous role mostly intact.
message_admins("\blue[usr.client.ckey] has banned [M.ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")
world.Export("http://216.38.134.132/adminlog.php?type=ban&key=[usr.client.key]&key2=[M.key]&msg=[html_decode(reason)]&time=[mins]&server=[replacetext(config.server_name, "#", "")]")
del(M.client)
- del(M)
+ qdel(M)
else
if("No")
@@ -701,7 +701,7 @@ Traitors and the like can also be revived with the previous role mostly intact.
message_admins("\blue[usr.client.ckey] has banned [M.ckey].\nReason: [reason]\nThis is a permanent ban.")
world.Export("http://216.38.134.132/adminlog.php?type=ban&key=[usr.client.key]&key2=[M.key]&msg=[html_decode(reason)]&time=perma&server=[replacetext(config.server_name, "#", "")]")
del(M.client)
- del(M)
+ qdel(M)
*/
/client/proc/update_world()
diff --git a/code/modules/admin/verbs/striketeam.dm b/code/modules/admin/verbs/striketeam.dm
index c49e09d5548..ef217b16f96 100644
--- a/code/modules/admin/verbs/striketeam.dm
+++ b/code/modules/admin/verbs/striketeam.dm
@@ -4,7 +4,7 @@ var/const/commandos_possible = 6 //if more Commandos are needed in the future
/client/proc/strike_team()
set category = "Fun"
set name = "Spawn Strike Team"
- set desc = "Spawns a death squad if you want to run an admin event."
+ set desc = "Spawns a strike team if you want to run an admin event."
if(!src.holder)
src << "Only administrators may use this command."
@@ -20,12 +20,12 @@ var/const/commandos_possible = 6 //if more Commandos are needed in the future
var/datum/antagonist/deathsquad/team
- var/choice = input(usr, "Select type of strike team:") as null|anything in list("Death Squad", "Mercenaries")
+ var/choice = input(usr, "Select type of strike team:") as null|anything in list("Heavy Asset Protection", "Mercenaries")
if(!choice)
return
switch(choice)
- if("Death Squad")
+ if("Heavy Asset Protection")
team = deathsquad
if("Mercenaries")
team = commandos
diff --git a/code/modules/alarm/alarm.dm b/code/modules/alarm/alarm.dm
index 525a5b3d214..aa88e170bf2 100644
--- a/code/modules/alarm/alarm.dm
+++ b/code/modules/alarm/alarm.dm
@@ -18,6 +18,7 @@
var/list/sources = new() //List of sources triggering the alarm. Used to determine when the alarm should be cleared.
var/list/sources_assoc = new() //Associative list of source triggers. Used to efficiently acquire the alarm source.
var/list/cameras //List of cameras that can be switched to, if the player has that capability.
+ var/cache_id //ID for camera cache, changed by invalidateCameraCache().
var/area/last_area //The last acquired area, used should origin be lost (for example a destroyed borg containing an alarming camera).
var/area/last_name //The last acquired name, used should origin be lost
var/area/last_camera_area //The last area in which cameras where fetched, used to see if the camera list should be updated.
@@ -74,8 +75,12 @@
return last_name
/datum/alarm/proc/cameras()
+ // reset camera cache
+ if(camera_cache_id != cache_id)
+ cameras = null
+ cache_id = camera_cache_id
// If the alarm origin has changed area, for example a borg containing an alarming camera, reset the list of cameras
- if(cameras && (last_camera_area != alarm_area()))
+ else if(cameras && (last_camera_area != alarm_area()))
cameras = null
// The list of cameras is also reset by /proc/invalidateCameraCache()
@@ -96,18 +101,17 @@
* Assisting procs *
******************/
/atom/proc/get_alarm_area()
- var/area/A = get_area(src)
- return A.master
+ return get_area(src)
/area/get_alarm_area()
- return src.master
+ return src
/atom/proc/get_alarm_name()
var/area/A = get_area(src)
- return A.master.name
+ return A.name
/area/get_alarm_name()
- return master.name
+ return name
/mob/get_alarm_name()
return name
diff --git a/code/modules/alarm/alarm_handler.dm b/code/modules/alarm/alarm_handler.dm
index 2be4060de28..47b7f7b5719 100644
--- a/code/modules/alarm/alarm_handler.dm
+++ b/code/modules/alarm/alarm_handler.dm
@@ -84,8 +84,7 @@
return src
/turf/get_alarm_origin()
- var/area/area = get_area(src)
- return area.master // Very important to get area.master, as dynamic lightning can and will split areas.
+ return get_area(src)
/datum/alarm_handler/proc/register(var/object, var/procName)
listeners[object] = procName
diff --git a/code/modules/assembly/assembly.dm b/code/modules/assembly/assembly.dm
index d727ecb1abb..09b15fe7750 100644
--- a/code/modules/assembly/assembly.dm
+++ b/code/modules/assembly/assembly.dm
@@ -5,7 +5,7 @@
icon_state = ""
flags = CONDUCT
w_class = 2.0
- matter = list("metal" = 100)
+ matter = list(DEFAULT_WALL_MATERIAL = 100)
throwforce = 2
throw_speed = 3
throw_range = 10
diff --git a/code/modules/assembly/bomb.dm b/code/modules/assembly/bomb.dm
index ed3edf5fc00..ba071d7c724 100644
--- a/code/modules/assembly/bomb.dm
+++ b/code/modules/assembly/bomb.dm
@@ -39,7 +39,7 @@
bombtank.master = null
bombtank = null
- del(src)
+ qdel(src)
return
if((istype(W, /obj/item/weapon/weldingtool) && W:welding))
if(!status)
@@ -144,8 +144,8 @@
ground_zero.hotspot_expose(1000, 125)
if(master)
- del(master)
- del(src)
+ qdel(master)
+ qdel(src)
/obj/item/weapon/tank/proc/release() //This happens when the bomb is not welded. Tank contents are just spat out.
var/datum/gas_mixture/removed = air_contents.remove(air_contents.total_moles)
diff --git a/code/modules/assembly/holder.dm b/code/modules/assembly/holder.dm
index f3bf44b53be..a8a3d246c82 100644
--- a/code/modules/assembly/holder.dm
+++ b/code/modules/assembly/holder.dm
@@ -190,7 +190,7 @@
a_right:holder = null
a_right.loc = T
spawn(0)
- del(src)
+ qdel(src)
return
diff --git a/code/modules/assembly/igniter.dm b/code/modules/assembly/igniter.dm
index 2988630032e..fc34669f3df 100644
--- a/code/modules/assembly/igniter.dm
+++ b/code/modules/assembly/igniter.dm
@@ -2,8 +2,8 @@
name = "igniter"
desc = "A small electronic device able to ignite combustable substances."
icon_state = "igniter"
- matter = list("metal" = 500, "glass" = 50, "waste" = 10)
- origin_tech = list(TECH_MAGNET = 1)
+ origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 500, "glass" = 50, "waste" = 10)
secured = 1
wires = WIRE_RECEIVE
diff --git a/code/modules/assembly/infrared.dm b/code/modules/assembly/infrared.dm
index 77e89b42fb1..56d8c9595d8 100644
--- a/code/modules/assembly/infrared.dm
+++ b/code/modules/assembly/infrared.dm
@@ -4,8 +4,8 @@
name = "infrared emitter"
desc = "Emits a visible or invisible beam and is triggered when the beam is interrupted."
icon_state = "infrared"
- matter = list("metal" = 1000, "glass" = 500, "waste" = 100)
- origin_tech = list(TECH_MAGNET = 2)
+ origin_tech = list(TECH_MAGNET = 2)
+ matter = list(DEFAULT_WALL_MATERIAL = 1000, "glass" = 500, "waste" = 100)
wires = WIRE_PULSE
@@ -32,7 +32,7 @@
processing_objects.Add(src)
else
on = 0
- if(first) del(first)
+ if(first) qdel(first)
processing_objects.Remove(src)
update_icon()
return secured
@@ -53,7 +53,7 @@
process()//Old code
if(!on)
if(first)
- del(first)
+ qdel(first)
return
if((!(first) && (secured && (istype(loc, /turf) || (holder && istype(holder.loc, /turf))))))
@@ -77,7 +77,7 @@
attack_hand()
- del(first)
+ qdel(first)
..()
return
@@ -86,14 +86,14 @@
var/t = dir
..()
set_dir(t)
- del(first)
+ qdel(first)
return
holder_movement()
if(!holder) return 0
// set_dir(holder.dir)
- del(first)
+ qdel(first)
return 1
@@ -175,7 +175,7 @@
if(master)
//world << "beam hit \ref[src]: calling master \ref[master].hit"
master.trigger_beam()
- del(src)
+ qdel(src)
return
/obj/effect/beam/i_beam/proc/vis_spread(v)
@@ -193,7 +193,7 @@
if((loc.density || !(master)))
// world << "beam hit loc [loc] or no master [master], deleting"
- del(src)
+ qdel(src)
return
//world << "proccess: [src.left] left"
@@ -233,17 +233,17 @@
return
else
//world << "is a next: \ref[next], deleting beam \ref[I]"
- del(I)
+ qdel(I)
else
//world << "step failed, deleting \ref[next]"
- del(next)
+ qdel(next)
spawn(10)
process()
return
return
/obj/effect/beam/i_beam/Bump()
- del(src)
+ qdel(src)
return
/obj/effect/beam/i_beam/Bumped()
@@ -258,7 +258,10 @@
return
return
-/obj/effect/beam/i_beam/Del()
- del(next)
+/obj/effect/beam/i_beam/Destroy()
+ if(master.first == src)
+ master.first = null
+ if(next)
+ qdel(next)
+ next = null
..()
- return
diff --git a/code/modules/assembly/mousetrap.dm b/code/modules/assembly/mousetrap.dm
index e1c0e32a2c0..3537fbee507 100644
--- a/code/modules/assembly/mousetrap.dm
+++ b/code/modules/assembly/mousetrap.dm
@@ -2,8 +2,8 @@
name = "mousetrap"
desc = "A handy little spring-loaded trap for catching pesty rodents."
icon_state = "mousetrap"
- matter = list("metal" = 100, "waste" = 10)
- origin_tech = list(TECH_COMBAT = 1)
+ origin_tech = list(TECH_COMBAT = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 100, "waste" = 10)
var/armed = 0
diff --git a/code/modules/assembly/proximity.dm b/code/modules/assembly/proximity.dm
index 09d3f5c6ef9..d973e88b95b 100644
--- a/code/modules/assembly/proximity.dm
+++ b/code/modules/assembly/proximity.dm
@@ -2,8 +2,8 @@
name = "proximity sensor"
desc = "Used for scanning and alerting when someone enters a certain proximity."
icon_state = "prox"
- matter = list("metal" = 800, "glass" = 200, "waste" = 50)
- origin_tech = list(TECH_MAGNET = 1)
+ origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 800, "glass" = 200, "waste" = 50)
wires = WIRE_PULSE
diff --git a/code/modules/assembly/shock_kit.dm b/code/modules/assembly/shock_kit.dm
index 5e501e3313f..8ba62cdc371 100644
--- a/code/modules/assembly/shock_kit.dm
+++ b/code/modules/assembly/shock_kit.dm
@@ -8,9 +8,9 @@
w_class = 5.0
flags = CONDUCT
-/obj/item/assembly/shock_kit/Del()
- del(part1)
- del(part2)
+/obj/item/assembly/shock_kit/Destroy()
+ qdel(part1)
+ qdel(part2)
..()
return
@@ -25,7 +25,7 @@
part2.master = null
part1 = null
part2 = null
- del(src)
+ qdel(src)
return
if(istype(W, /obj/item/weapon/screwdriver))
status = !status
diff --git a/code/modules/assembly/signaler.dm b/code/modules/assembly/signaler.dm
index f1eac3d69a6..5a6faa7fe90 100644
--- a/code/modules/assembly/signaler.dm
+++ b/code/modules/assembly/signaler.dm
@@ -3,8 +3,8 @@
desc = "Used to remotely activate devices."
icon_state = "signaller"
item_state = "signaler"
- matter = list("metal" = 1000, "glass" = 200, "waste" = 100)
- origin_tech = list(TECH_MAGNET = 1)
+ origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 1000, "glass" = 200, "waste" = 100)
wires = WIRE_RECEIVE | WIRE_PULSE | WIRE_RADIO_PULSE | WIRE_RADIO_RECEIVE
secured = 1
@@ -141,6 +141,8 @@
proc/set_frequency(new_frequency)
+ if(!frequency)
+ return
if(!radio_controller)
sleep(20)
if(!radio_controller)
@@ -169,4 +171,11 @@
set desc = "BOOOOM!"
deadman = 1
processing_objects.Add(src)
+ log_and_message_admins("is threatening to trigger a signaler deadman's switch")
usr.visible_message("\red [usr] moves their finger over [src]'s signal button...")
+
+/obj/item/device/assembly/signaler/Destroy()
+ if(radio_controller)
+ radio_controller.remove_object(src,frequency)
+ frequency = 0
+ ..()
diff --git a/code/modules/assembly/timer.dm b/code/modules/assembly/timer.dm
index bbca2cb1d08..cdd927afd6d 100644
--- a/code/modules/assembly/timer.dm
+++ b/code/modules/assembly/timer.dm
@@ -2,8 +2,8 @@
name = "timer"
desc = "Used to time things. Works well with contraptions which has to count down. Tick tock."
icon_state = "timer"
- matter = list("metal" = 500, "glass" = 50, "waste" = 10)
- origin_tech = list(TECH_MAGNET = 1)
+ origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 500, "glass" = 50, "waste" = 10)
wires = WIRE_PULSE
diff --git a/code/modules/assembly/voice.dm b/code/modules/assembly/voice.dm
index 63895b1ec14..7e8c89cc796 100644
--- a/code/modules/assembly/voice.dm
+++ b/code/modules/assembly/voice.dm
@@ -2,8 +2,8 @@
name = "voice analyzer"
desc = "A small electronic device able to record a voice sample, and send a signal when that sample is repeated."
icon_state = "voice"
- matter = list("metal" = 500, "glass" = 50, "waste" = 10)
origin_tech = list(TECH_MAGNET = 1)
+ matter = list(DEFAULT_WALL_MATERIAL = 500, "glass" = 50, "waste" = 10)
var/listening = 0
var/recorded //the activation message
diff --git a/code/modules/awaymissions/corpse.dm b/code/modules/awaymissions/corpse.dm
index 11f78326c69..b6415f22b53 100644
--- a/code/modules/awaymissions/corpse.dm
+++ b/code/modules/awaymissions/corpse.dm
@@ -77,7 +77,7 @@
W.assignment = corpseidjob
W.registered_name = M.real_name
M.equip_to_slot_or_del(W, slot_wear_id)
- del(src)
+ qdel(src)
diff --git a/code/modules/awaymissions/loot.dm b/code/modules/awaymissions/loot.dm
index 706e1716afd..5aeb9651d2b 100644
--- a/code/modules/awaymissions/loot.dm
+++ b/code/modules/awaymissions/loot.dm
@@ -21,4 +21,4 @@
continue
new loot_path(get_turf(src))
- del(src)
\ No newline at end of file
+ qdel(src)
diff --git a/code/modules/awaymissions/trigger.dm b/code/modules/awaymissions/trigger.dm
index 65ad8f543d6..4afaf4a135d 100644
--- a/code/modules/awaymissions/trigger.dm
+++ b/code/modules/awaymissions/trigger.dm
@@ -6,7 +6,7 @@
if(M.client)
M << "[message]"
if(once)
- del(src)
+ qdel(src)
/obj/effect/step_trigger/teleport_fancy
var/locationx
@@ -41,4 +41,4 @@
uses--
if(uses == 0)
- del(src)
\ No newline at end of file
+ qdel(src)
\ No newline at end of file
diff --git a/code/modules/awaymissions/zlevel.dm b/code/modules/awaymissions/zlevel.dm
index b0ba29dcd03..4f9002409fa 100644
--- a/code/modules/awaymissions/zlevel.dm
+++ b/code/modules/awaymissions/zlevel.dm
@@ -3,7 +3,7 @@ proc/createRandomZlevel()
return
var/list/potentialRandomZlevels = list()
- world << "\red \b Searching for away missions..."
+ admin_notice("\red \b Searching for away missions...", R_DEBUG)
var/list/Lines = file2list("maps/RandomZLevels/fileList.txt")
if(!Lines.len) return
for (var/t in Lines)
@@ -35,7 +35,7 @@ proc/createRandomZlevel()
if(potentialRandomZlevels.len)
- world << "\red \b Loading away mission..."
+ admin_notice("\red \b Loading away mission...", R_DEBUG)
var/map = pick(potentialRandomZlevels)
var/file = file(map)
@@ -48,8 +48,8 @@ proc/createRandomZlevel()
continue
awaydestinations.Add(L)
- world << "\red \b Away mission loaded."
+ admin_notice("\red \b Away mission loaded.", R_DEBUG)
else
- world << "\red \b No away missions found."
+ admin_notice("\red \b No away missions found.", R_DEBUG)
return
diff --git a/code/modules/client/client procs.dm b/code/modules/client/client procs.dm
index 45ca127f137..b02875304e8 100644
--- a/code/modules/client/client procs.dm
+++ b/code/modules/client/client procs.dm
@@ -33,7 +33,7 @@
if( findtext(href,"
-
-
-
-
\ No newline at end of file
diff --git a/html/changelog.css b/html/changelog.css
index 1d2b6a6445d..9d43ecc076c 100644
--- a/html/changelog.css
+++ b/html/changelog.css
@@ -1,36 +1,36 @@
-.top{font-family:Tahoma,sans-serif;font-size:12px;}
-h2{font-family:Tahoma,sans-serif;}
-a img {border:none;}
-.bgimages16 li {
- padding:2px 10px 2px 30px;
- background-position:6px center;
- background-repeat:no-repeat;
- border:1px solid #ddd;
- border-left:4px solid #999;
- margin-bottom:2px;
-}
-.bugfix {background-image:url(bug-minus.png)}
-.wip {background-image:url(hard-hat-exclamation.png)}
-.tweak {background-image:url(wrench-screwdriver.png)}
-.soundadd {background-image:url(music-plus.png)}
-.sounddel {background-image:url(music-minus.png)}
-.rscdel {background-image:url(cross-circle.png)}
-.rscadd {background-image:url(tick-circle.png)}
-.imageadd {background-image:url(image-plus.png)}
-.imagedel {background-image:url(image-minus.png)}
-.spellcheck {background-image:url(spell-check.png)}
-.experiment {background-image:url(burn-exclamation.png)}
-.tgs {background-image:url(tg-notif.png)}
-.sansserif {font-family:Tahoma,sans-serif;font-size:12px;}
-.commit {margin-bottom:20px;font-size:100%;font-weight:normal;}
-.changes {list-style:none;margin:5px 0;padding:0 0 0 25px;font-size:0.8em;}
-.date {margin:10px 0;color:blue;border-bottom:2px solid #00f;width:60%;padding:2px 0;font-size:1em;font-weight:bold;}
-.author {padding-left:10px;margin:0;font-weight:bold;font-size:0.9em;}
-.drop {cursor:pointer;border:1px solid #999;display:inline;font-size:0.9em;padding:1px 20px 1px 5px;line-height:16px;}
-.hidden {display:none;}
-.indrop {margin:2px 0 0 0;clear:both;background:#fff;border:1px solid #ddd;padding:5px 10px;}
-.indrop p {margin:0;font-size:0.8em;line-height:16px;margin:1px 0;}
-.indrop img {margin-right:5px;vertical-align:middle;}
-.closed {background:url(chevron-expand.png) right center no-repeat;}
-.open {background:url(chevron.png) right center no-repeat;}
+.top{font-family:Tahoma,sans-serif;font-size:12px;}
+h2{font-family:Tahoma,sans-serif;}
+a img {border:none;}
+.bgimages16 li {
+ padding:2px 10px 2px 30px;
+ background-position:6px center;
+ background-repeat:no-repeat;
+ border:1px solid #ddd;
+ border-left:4px solid #999;
+ margin-bottom:2px;
+}
+.bugfix {background-image:url(bug-minus.png)}
+.wip {background-image:url(hard-hat-exclamation.png)}
+.tweak {background-image:url(wrench-screwdriver.png)}
+.soundadd {background-image:url(music-plus.png)}
+.sounddel {background-image:url(music-minus.png)}
+.rscdel {background-image:url(cross-circle.png)}
+.rscadd {background-image:url(tick-circle.png)}
+.imageadd {background-image:url(image-plus.png)}
+.imagedel {background-image:url(image-minus.png)}
+.spellcheck {background-image:url(spell-check.png)}
+.experiment {background-image:url(burn-exclamation.png)}
+.maptweak {background-image:url(map-pencil.png)}
+.sansserif {font-family:Tahoma,sans-serif;font-size:12px;}
+.commit {margin-bottom:20px;font-size:100%;font-weight:normal;}
+.changes {list-style:none;margin:5px 0;padding:0 0 0 25px;font-size:0.8em;}
+.date {margin:10px 0;color:blue;border-bottom:2px solid #00f;width:60%;padding:2px 0;font-size:1em;font-weight:bold;}
+.author {padding-left:10px;margin:0;font-weight:bold;font-size:0.9em;}
+.drop {cursor:pointer;border:1px solid #999;display:inline;font-size:0.9em;padding:1px 20px 1px 5px;line-height:16px;}
+.hidden {display:none;}
+.indrop {margin:2px 0 0 0;clear:both;background:#fff;border:1px solid #ddd;padding:5px 10px;}
+.indrop p {margin:0;font-size:0.8em;line-height:16px;margin:1px 0;}
+.indrop img {margin-right:5px;vertical-align:middle;}
+.closed {background:url(chevron-expand.png) right center no-repeat;}
+.open {background:url(chevron.png) right center no-repeat;}
.lic {font-size:9px;}
\ No newline at end of file
diff --git a/html/changelog.html b/html/changelog.html
index 11ccdbedceb..6cc3c3bc315 100644
--- a/html/changelog.html
+++ b/html/changelog.html
@@ -3,6 +3,7 @@
Baystation 12 Changelog
+
-
+ Current Project Maintainers:-Click Here-
+ Currently Active GitHub contributor list:-Click Here- Code: Abi79, Aryn, Cael_Aislinn, Ccomp5950, Chinsky, cib, CompactNinja, DopeGhoti, Erthilo, Hawk_v3, Head, Ispil, JoeyJo0, Lexusjjss, Melonstorm, Miniature, Mloc, NerdyBoy1104, PsiOmegaDelta, SkyMarshal, Snapshot, Spectre, Strumpetplaya, Sunfall, Tastyfish, Uristqwerty Sprites: Apple_Master, Arcalane, Chinsky, CompactNinja, Deus Dactyl, Erthilo, Flashkirby, JoeyJo0, Miniature, Searif, Xenone, faux Sounds: Aryn
- Thanks To: /tg/ station, Goonstation, Animus Station, Daedalus, and original Spacestation 13 devs. Skibiliano for the IRC bot.
+ Main Testers: Anyone who has submitted a bug to the issue tracker
+ Thanks to: /tg/ station, /vg/station, GoonStation devs, the original SpaceStation developers and Invisty for the title image. Also a thanks to anybody who has contributed who is not listed here :( Ask to be added here on irc.
+ Have a bug to report? Visit our Issue Tracker.
-
+
+
+
18 May 2015
+
Hubblenaut updated:
+
+
Adds a light for available backup power on airlocks.
+
+
Kelenius updated:
+
+
There has been a big update to the reagent system. A full-ish changelog can be found here: http://pastebin.com/imHXTRHz. In particular:
+
Reagents now differentiate between being ingested (food, pills, smoke), injected (syringes, IV drips), and put on the skin (sprays, beaker splashing).
+
Injecting food and drinks will cause bad effects.
+
Healing reagents, generally speaking, have stronger effects when injected.
+
Toxins now work slower and deal more damage. Seek medical help!
+
Alcohol robustness has been lowered.
+
Acid will no longer melt large numbers of items at once.
+
Synaptizine is no longer hilariously deadly.
+
+
Loganbacca updated:
+
+
Changed MULE destination selection to be list based.
+
+
PsiOmegaDelta updated:
+
+
Destroying a camera by brute force now has a chance to break the wiring within.
+
Turf are now processed. This, for example, causes radioactive walls to regularly irradiate nearby mobs.
+
Welders should now always update their icon and inhand states properly.
+
-
+
17 May 2015
+
PsiOmegaDelta updated:
+
+
Teleporter artifacts should no longer teleport mobs inside objects.
+
-
+
16 May 2015
+
GinjaNinja32 updated:
+
+
Rewrote tables. To construct a table, use steel to make a table frame, then plate the frame with a material such as steel, gold, wood, etc. Hold a stack in your hand and drag it to the table to reinforce it. To deconstruct a table, use a screwdriver to remove the reinforcements (if present), then a wrench to remove the plating, and a wrench again to dismantle the frame. Use a welder to repair any damage. Use a carpet tile on a table to add felt, and a crowbar to remove it.
+
+
HarpyEagle updated:
+
+
Adds tail animations for tajaran and unathi. Animations are controlled using emotes.
+
-
+
14 May 2015
+
PsiOmegaDelta updated:
+
+
Should now be more evident that the brig disposal chute sends its goods to the common brig area.
+
Cells now drain when using more charge than what is available.
+
The rig stealth module now requires as much power to run as the energy blade module.
+
+
Techhead updated:
+
+
Vox will spawn with emergency nitrogen tanks in their survival boxes.
+
Diona will spawn with an emergency flare instead of a survival box.
+
Engineers no longer spawn with extended-capacity oxygen tanks.
+
Vox spawning without backpacks will have their nitrogen tank equipped to their back.
+
The Bartender's spare beanbag shells have been moved into bar backroom with the shotgun.
+
Portable air pumps now fill based on external/airtank pressure when pumping in.
+
-
-
24 February 2015
-
Zuhayr updated:
-
-
Major changes to the kitchen and hydroponics mechanics. Review the detailed changelog here,
-
-
+
12 May 2015
+
Dennok updated:
+
+
New buildmode icons made by BartNixon.
+
+
HarpyEagle updated:
+
+
Masks and helmets that cover the face block feeding food, drinks, and pills.
+
+
MrSnapwalk updated:
+
+
Added seven new AI core displays.
+
Changed the pAI sprite and added several new expressions.
+
+
PsiOmegaDelta updated:
+
+
The space vine event now comes with a station announcement.
+
+
11 May 2015
+
Mloc updated:
+
+
Rewritten lighting system.
+
Better coloured lights.
+
Animated transitions.
+
+
PsiOmegaDelta updated:
+
+
As an observer, using antagHUD should now always restrict you from respawning without admin intervention.
+
+
Techhead updated:
+
+
Voidsuits can have tanks inserted into the storage slot.
+
Voidsuits display helpful information on their contents on examine.
+
Magboots can be equipped over other shoes. Except other magboots.
+
-
-
18 February 2015
-
PsiOmegaDelta updated:
-
-
Synths now have timestamped radio and chat messages.
-
New and updated uplink items.
-
Multiple AIs can now share the same holopad.
-
The AI now has built-in consoles, accessible from the subsystem tab.
-
-
+
10 May 2015
+
GinjaNinja32 updated:
+
+
Acting jobs on the manifest will now sort with their non-acting counterparts. All assignments beginning with the word 'acting', 'temporary', or 'interim' will do this.
+
+
Yoshax updated:
+
+
Removes sleepy chems from being cloned, adds a consistent period of 30 tick sleep.
+
+
09 May 2015
+
Yoshax updated:
+
+
Maps in the top mounted 9mm practice rounds, .45 practice rounds, and practice shotgun shells into the armory.
+
+
07 May 2015
+
HarpyEagle updated:
+
+
Breaking out of lockers now has sound and animation.
+
+
PsiOmegaDelta updated:
+
+
The cloning computer can again successfully locate nearby cloning vats and DNA scanners at round start.
+
Security equipment now treats individuals with CentCom ids with the greatest respect.
+
Adds stretches of power cable around the construction outpost, ensuring one does not have to climb over machines to being laying cables.
+
+
RavingManiac updated:
+
+
Muzzle-flash lighting effect for guns
+
Energy guns now display shots remaining on examine
+
-
-
16 February 2015
-
RavingManiac updated:
-
-
Say hello to the new Thermoelectric Supermatter Engine. Read the operating manual to get started.
-
-
+
06 May 2015
+
PsiOmegaDelta updated:
+
+
Examining a pen or crayon now lists the available special commands in the examine tab.
+
+
05 May 2015
+
PsiOmegaDelta updated:
+
+
Grilles no longer return too many rods when destroyed (using means other than wirecutters).
+
+
RavingManiac updated:
+
+
Intent menu now appears while zooming with a sniper rifle.
+
-
-
12 February 2015
-
Daranz updated:
-
-
Vending machines now use NanoUI and accept cash. The vendor account can now be suspended to disable all sales in all machines on station.
-
-
+
02 May 2015
+
HarpyEagle updated:
+
+
Neck-grabbing someone now stuns them properly.
+
+
PsiOmegaDelta updated:
+
+
The spider infestation event now makes an announcement much sooner.
+
Admins can now toggle OOC/LOOC separately.
+
Mice are now numbered to aid admins.
+
+
Yoshax updated:
+
+
Adds an option and verb to the AI to send emergency messages to Central, functions same as comms console option.
+
Changes comms console to only have one level of ID require, meaning all heads of staff have what was captain access, allowing them to change alert, send emergency messages and make announcements.
+
Adds an emergency bluespace relay machine which is mapped into teletcomms, this machine takes emergency messages and sends them to central, if one does not exist on any Z, you cannot send any emergency messages.
+
Adds an emergency bluespace relay assembly kit orderable from cargo for when the ones on telecomms are destroyed. Assembly is required.
+
Adds the emergency bluespace relay circuitboard to be researchable and printable in R&D, with sufficient tech levels.
+
-
-
4 February 2015
-
RavingManiac updated:
-
-
Holodeck is now bigger and better, with toggleable gravity and a new courtroom setting
-
TwistedAkai updated:
-
-
Purple Combs should now be visible and have their proper icon
-
-
+
30 April 2015
+
Yoshax updated:
+
+
Adds more items to custom loadout, including a number of dressy suits and some other things.
+
+
29 April 2015
+
Daranz updated:
+
+
Paper bundles can now have papers inserted at arbitrary points. This can be done by clicking the previous/next page links with a sheet of paper in hand.
+
+
HarpyEagle updated:
+
+
Added new fire modes to various guns: c20r, STS-35, WT-550, Z8, L6 SAW, and double barreled shotgun. The firing modes work the same way as the egun; click on the weapon with it in your active hand to cycle between modes. Unloading these weapons now requires that you click on them with an empty hand.
+
+
PsiOmegaDelta updated:
+
+
Portable atmospheric pumps and scrubbers now use NanoUI.
+
Two new events which will cause damage to APCs or cameras when triggered.
+
-
-
1 September 2014
-
9 January 2015
-
Zuhayr updated:
-
-
Voice changers no longer use ID cards. They have Toggle and Set Voice verbs on the actual mask object now.
-
Readded moonwalking. Alt-dir to face new dir, or Face-Direction verb to face current dir.
-
-
+
28 April 2015
+
Jarcolr updated:
+
+
Added 9 new bar sign designs/sprites.
+
+
Kelenius updated:
+
+
Good news to the roboticists! The long waited firmware update for the bots has arrived. You can expect the following changes:
+
Medbots have improved the disease detection algorithms.
+
Floorbot firmware has been bugtested. In particular, they will no longer get stuck near the windows, hopelessly trying to fix the floor under the glass.
+
Floorbots have also received an internal low-power metal synthesizer. They will use it to make their own tiles. Slowly.
+
Following the complains from humanitarian organizations regarding securitron brutality, stength of their stunners has been toned down. They will also politely demand that you get on the floor before arresting you. Except for the taser-mounted guys, they will still tase you down.
+
Other minor fixes.
+
The lasertag bots are now forbidden to build and use following the incident #1526672. Please don't let it happen again.
+
The farmbot design has been finished! Made from a watertank, robot arm, plant analyzer, bucket, minihoe and a proximity sensor, these small (not really) bots will be a useful companion to any gardener and/or xenobotanist.
+
Spider learning alert: they have learned to recognize the bots and will mercilessly attack them.
+
An experimental CPU upgrade would theoretically allow any of the bots to function with the same intelligence capacity as the maintenance drones. We still have no idea what causes it to boot up. Science!
+
INCOMING TRANSMISSION: Greetings to agents, pirates, operatives, and anyone who otherwise uses our equipment. Following the NT update of bot firmware, we have updated the cryptographic sequencer's hacking routines as well. The medbots you emag will not poison you anymore, the clanbots won't clean after themselves immediately, and floorbots... wear a space suit. Oh, and it works on the new farmbots, too.
+
+
PsiOmegaDelta updated:
+
+
Beware. Airlocks can now crush more things than just mobs.
+
AIs now have a personal atmospherics control subsystem.
+
Some borg modules now have additional subsystems.
+
Improves borg module handling.
+
Secure airlocks now buzz when access is denied.
+
The mental health office door now requires psychiatrist access, and the related button now opens/closes the door instead of bolting.
+
Restores an old soundtrack 'Thunderdome.ogg'.
+
Some holodeck programs now have custom ambience tracks.
+
+
RavingManiac updated:
+
+
The phoron research lab has been renovated to include a heat-exchange system, a gas mixer/filter and a waste gas disposal pump.
+
Candles now burn for about 30 mintutes.
+
+
Yoshax updated:
+
+
Adds items to the orderable antag surgical kit so its actually useful for surgery.
+
Adjusts custom loadout costs to be more standardised and balances. Purely cosmetic items, shoes, hats, and all things that do not provide a straight advtange (sterile mask, or pAI, protection from viruses and possible door hacking or records access, respectively), each cost 1 point, items that provide an advantage like those just mentioned, or provide armor or storage cost 2 points.
+
Adds practice rounds, both .45 for Sec and Detective's guns, also 9mm top mounted for the Saber, and for the Bulldog.
+
Adds the .45 and 9mm practice rounds to the armory.
+
Adds all the practice rounds to the autolathe.
+
Adds r_walls to the back of the firing range, leaves the sides normal.
+
Fixes HoS' office door to not be CMO locked.
+
+
24 April 2015
+
Dennok updated:
+
+
Fixes overmap ship speed calculations.
+
Adds overmap ship rotation.
+
Added a floorlayer.
+
-
-
22 November 2014
-
Zuhayr updated:
-
-
Added the /obj/item/weapon/rig class - back-mounted deployable hardsuits.
-
Replaced existing hardsuits with 'voidsuits', functionally identical.
-
Removed the mounted device and helmet/boot procs from voidsuits.
-
Refactored a shit-ton of ninja code into the new rig class.
-
This is more than likely going to take a lot of balancing to get into a good place.
-
-
+
23 April 2015
+
Dennok updated:
+
+
Added an automatic pipelayer.
+
Added an automatic cablelayer.
+
+
PsiOmegaDelta updated:
+
+
Shower curtains no longer lose their default color upon being washed.
+
Emergency shutters can again be examined, and from the proper distance.
+
The virus event will now only infect mobs on the station, currently controlled by player that has been active in the last 5 minutes.
+
Laptops now use the proper proc for checking camera status.
+
Makes it possible to eject PDA cartridges using a verb.
+
Makes it possible to shake tables with one's bare hands to stop climbers.
+
Added a mass driver door in disposals to prevent trash from floating out into space before proper ejection.
+
Rig/Hardsuit module tab - Less informative than the NanoUI hardsuit interface but allows quicker access to the various rig modules.
+
Silicons with the medical augmentation sensors enabled now also see alive/dead status if sensors are set accordingly.
+
Emergency shutters opened by silicons are now treated as having been forced open by a crowbar.
+
An active AI chassis can now be pushed, just as an empty chassis can be.
+
The AI can now use the crew monitor console to track crew members with full sensors enabled.
+
The AI now has a shortcut to track people holding up messages to cameras.
+
The AI now has a shortcut to track people sending PDA messages.
+
Multiple AIs can now share the same holopad.
+
Admin ghosts can now transfer other ghosts into mobs by drag-clicking.
+
Ghosts can now toggle seeing darkness and other ghosts separately.
+
Moving while dead now auto-ghosts you.
+
Two new random events: Space dust and gravitation failure.
+
Upgraded wizard spell interface and new spells.
+
More uplink items.
+
Uplink items now have rudimentary descriptions.
+
+
Yoshax updated:
+
+
Adjusts fruits and other stuff to have a minmum of 10 units of juice and stuff.
+
+
18 April 2015
+
PsiOmegaDelta updated:
+
+
Added a changelog editing system that should cause fewer conflicts and more accurate timestamps.
+
-
-
8 november 2014
-
PsiOmegaDelta updated:
-
-
Service personnel now have their own frequency to communicate over. Use "say :v".
-
The AI can now has proper quick access to its private channel. Use "say :o".
-
Newscasters supports photo captions. Simply pen one on the attached photo.
-
Once made visible by a cultist ghosts can toggle visiblity at will.
-
Detonating cyborgs using the cyborg monitor console now notifies the master AI, if any.
-
More machinery, such as APCs, air alarms, etc., now support attaching signalers to the wires.
-
Random event overhaul. Admins may wish check the verb "Event Manager Panel".
-
-
+
07 April 2015
+
RavingManiac updated:
+
+
You can now pay vending machines and EFTPOS scanners without removing your ID from your PDA or wallet. Clicking on the vending machine with your ID/PDA/wallet/cash also brings up the menu now instead of attacking the vending machine.
+
+
24 February 2015
+
Zuhayr updated:
+
+
Major changes to the kitchen and hydroponics mechanics. Review the detailed changelog here,
+
-
-
4 November 2014
-
TwistedAkai updated:
-
-
Almost any window which has been fully unsecured can now be dismantled with a wrench.
-
-
+
18 February 2015
+
PsiOmegaDelta updated:
+
+
Synths now have timestamped radio and chat messages.
+
New and updated uplink items.
+
Multiple AIs can now share the same holopad.
+
The AI now has built-in consoles, accessible from the subsystem tab.
+
+
16 February 2015
+
RavingManiac updated:
+
+
Say hello to the new Thermoelectric Supermatter Engine. Read the operating manual to get started.
+
-
-
1 november 2014
-
PsiOmegaDelta updated:
-
-
Adds the last missing step to deconstruct fire alarms. Apply wirecutters.
-
There's a "new" mining outpost nearby the Research outpost.
-
Manifest ghosts now have spookier names.
-
Adds a gas monitor computer for the toxin mixing chamber.
-
AI can now change the display of individual AI status screens.
-
More ion laws..
-
All turrets have been replaced with portable variants. Potential targets can be configured on a per turret basis.
-
Improved crew monitor map positioning.
-
Can now order plastic, body-, and statis bags from cargo
-
PDAs now receive newscasts.
-
(De)constructable emergency shutters.
-
Borgs can now select to simply state their laws or select a radio channel, same as the AI.
-
-
+
12 February 2015
+
Daranz updated:
+
+
Vending machines now use NanoUI and accept cash. The vendor account can now be suspended to disable all sales in all machines on station.
+
+
04 February 2015
+
RavingManiac updated:
+
+
Holodeck is now bigger and better, with toggleable gravity and a new courtroom setting
+
+
TwistedAkai updated:
+
+
Purple Combs should now be visible and have their proper icon
+
-
-
1 October 2014
-
RavingManiac updated:
-
-
Zooming with the sniper rifle now adds a view offset in the direction you are facing.
-
Added binoculars - functionally similar to sniper scope. Adminspawn-only for now.
-
Bottles from chemistry now, like beakers, use chemical overlays instead of fixed sprites.
-
Being in space while not magbooted to something will cause your sprite to bob up and down.
-
-
+
09 January 2015
+
Zuhayr updated:
+
+
Voice changers no longer use ID cards. They have Toggle and Set Voice verbs on the actual mask object now.
+
Readded moonwalking. Alt-dir to face new dir, or Face-Direction verb to face current dir.
+
+
22 November 2014
+
Zuhayr updated:
+
+
Added the /obj/item/weapon/rig class - back-mounted deployable hardsuits.
+
Replaced existing hardsuits with 'voidsuits', functionally identical.
+
Removed the mounted device and helmet/boot procs from voidsuits.
+
Refactored a shit-ton of ninja code into the new rig class.
+
This is more than likely going to take a lot of balancing to get into a good place.
+
-
-
1 October 2014
-
Zuhayr updated:
-
-
Added species organ checks to several areas (phoron burn, welder burn, appendicitis, vox cortical stacks, flashes).
-
Added VV option to add or remove organs.
-
Added simple bioprinter (adminspawn).
-
Added smashing/slashing behavior from xenos to some unarmed attacks.
-
Added some new state icons for diona nymphs.
-
Added borer husk functionality (cortical borers can turn dead humans into zombies).
-
Added tackle verb.
-
Added NO_SLIP.
-
Added species-specific orans to Dionaea, new Xenomorphs and vox.
-
Added colour and species to blood data.
-
Added lethal consequences to missing your heart.
-
Removed robot_talk_understand and alien_talk_understand.
-
Removed attack_alien() and several flavours of is_alien() procs.
-
Removed /mob/living/carbon/alien/humanoid.
-
Removed alien_hud().
-
Removed IS_SLOW, NEEDS_LIGHT and RAD_ABSORB.
-
Renamed is_larva() to is_alien().
-
Refactored a ton of files, either condensing or expanding them, or moving them to new directories.
-
Refactored some attack vars from simple_animal to mob/living level.
-
Refactored internal organs to /mob/living/carbon level.
-
Refactored rad and light absorbtion to organ level.
-
Refactored brains to /obj/item/organ/brain.
-
Refactored a lot of blood splattering to use blood_splatter() proc.
-
Refactored broadcast languages (changeling and alien hiveminds, drone and binary chat) to actual languages.
-
Refactored xenomorph abilities to work for humans.
-
Refactored xenomorphs into human species.
-
Rewrote larva_hud() and human_hud(). The latter now takes data from the species datum.
-
Rewrote diona nymphs as descendents of /mob/living/carbon/alien.
-
Rewrote xenolarva as descendents of /mob/living/carbon/alien.
-
Rewrote /mob/living/carbon/alien.
-
Moved alcohol and toxin processing to the liver.
-
Moved drone light proc to robot level, added integrated_light_power and local_transmit vars to robots.
-
Moved human brainloss onto the brain organ.
-
Shuffled around and collapsed several redundant procs down to carbon level (hide, ventcrawl, Bump).
-
Fixed species swaps from NO_BLOOD to those with blood killing the subject instantly.
-
-
+
08 November 2014
+
PsiOmegaDelta updated:
+
+
Service personnel now have their own frequency to communicate over. Use "say :v".
+
The AI can now has proper quick access to its private channel. Use "say :o".
+
Newscasters supports photo captions. Simply pen one on the attached photo.
+
Once made visible by a cultist ghosts can toggle visiblity at will.
+
Detonating cyborgs using the cyborg monitor console now notifies the master AI, if any.
+
More machinery, such as APCs, air alarms, etc., now support attaching signalers to the wires.
+
Random event overhaul. Admins may wish check the verb "Event Manager Panel".
+
-
-
28 September 2014
-
Gamerofthegame updated:
-
-
Hoverpods fully supported, currently orderable from cargo. Two slots, three cargo, space flight and a working mech for all other intents and purposes.
-
Added the Rigged laser and Passenger Compartment equipment. The rigged laser is a weapon for working exosuits - just a ordinary laser, but with triple the cool down and rather power inefficient. The passenger compartment allows other people to board and hitch a ride on the mech - such as in fire rescue or for space flight.
-
-
+
04 November 2014
+
TwistedAkai updated:
+
+
Almost any window which has been fully unsecured can now be dismantled with a wrench.
+
-
-
28 September 2014
-
Zuhayr updated:
-
-
Organs can now be removed and transplanted.
-
Brain surgery is now the same as chest surgery regarding the steps leading up to it.
-
Appendix and kidney now share the groin and removing the first will prevent appendicitis.
-
Lots of backend surgery/organ stuff, see the PR if you need to know.
-
-
+
01 November 2014
+
PsiOmegaDelta updated:
+
+
Adds the last missing step to deconstruct fire alarms. Apply wirecutters.
+
There's a "new" mining outpost nearby the Research outpost.
+
Manifest ghosts now have spookier names.
+
Adds a gas monitor computer for the toxin mixing chamber.
+
AI can now change the display of individual AI status screens.
+
More ion laws..
+
All turrets have been replaced with portable variants. Potential targets can be configured on a per turret basis.
+
Improved crew monitor map positioning.
+
Can now order plastic, body-, and statis bags from cargo
+
PDAs now receive newscasts.
+
(De)constructable emergency shutters.
+
Borgs can now select to simply state their laws or select a radio channel, same as the AI.
+
+
01 October 2014
+
RavingManiac updated:
+
+
Zooming with the sniper rifle now adds a view offset in the direction you are facing.
+
Added binoculars - functionally similar to sniper scope. Adminspawn-only for now.
+
Bottles from chemistry now, like beakers, use chemical overlays instead of fixed sprites.
+
Being in space while not magbooted to something will cause your sprite to bob up and down.
+
+
Zuhayr updated:
+
+
Added species organ checks to several areas (phoron burn, welder burn, appendicitis, vox cortical stacks, flashes).
+
Added VV option to add or remove organs.
+
Added simple bioprinter (adminspawn).
+
Added smashing/slashing behavior from xenos to some unarmed attacks.
+
Added some new state icons for diona nymphs.
+
Added borer husk functionality (cortical borers can turn dead humans into zombies).
+
Added tackle verb.
+
Added NO_SLIP.
+
Added species-specific orans to Dionaea, new Xenomorphs and vox.
+
Added colour and species to blood data.
+
Added lethal consequences to missing your heart.
+
Removed robot_talk_understand and alien_talk_understand.
+
Removed attack_alien() and several flavours of is_alien() procs.
+
Removed /mob/living/carbon/alien/humanoid.
+
Removed alien_hud().
+
Removed IS_SLOW, NEEDS_LIGHT and RAD_ABSORB.
+
Renamed is_larva() to is_alien().
+
Refactored a ton of files, either condensing or expanding them, or moving them to new directories.
+
Refactored some attack vars from simple_animal to mob/living level.
+
Refactored internal organs to /mob/living/carbon level.
+
Refactored rad and light absorbtion to organ level.
+
Refactored brains to /obj/item/organ/brain.
+
Refactored a lot of blood splattering to use blood_splatter() proc.
+
Refactored broadcast languages (changeling and alien hiveminds, drone and binary chat) to actual languages.
+
Refactored xenomorph abilities to work for humans.
+
Refactored xenomorphs into human species.
+
Rewrote larva_hud() and human_hud(). The latter now takes data from the species datum.
+
Rewrote diona nymphs as descendents of /mob/living/carbon/alien.
+
Rewrote xenolarva as descendents of /mob/living/carbon/alien.
+
Rewrote /mob/living/carbon/alien.
+
Moved alcohol and toxin processing to the liver.
+
Moved drone light proc to robot level, added integrated_light_power and local_transmit vars to robots.
+
Moved human brainloss onto the brain organ.
+
Shuffled around and collapsed several redundant procs down to carbon level (hide, ventcrawl, Bump).
+
Fixed species swaps from NO_BLOOD to those with blood killing the subject instantly.
+
-
-
20 September 2014
-
HarpyEagle updated:
-
-
Fixes evidence bags and boxes eating each other. Evidence bags now store items by dragging the bag onto the item to be stored.
-
-
+
28 September 2014
+
Gamerofthegame updated:
+
+
Hoverpods fully supported, currently orderable from cargo. Two slots, three cargo, space flight and a working mech for all other intents and purposes.
+
Added the Rigged laser and Passenger Compartment equipment. The rigged laser is a weapon for working exosuits - just a ordinary laser, but with triple the cool down and rather power inefficient. The passenger compartment allows other people to board and hitch a ride on the mech - such as in fire rescue or for space flight.
+
+
Zuhayr updated:
+
+
Organs can now be removed and transplanted.
+
Brain surgery is now the same as chest surgery regarding the steps leading up to it.
+
Appendix and kidney now share the groin and removing the first will prevent appendicitis.
+
Lots of backend surgery/organ stuff, see the PR if you need to know.
+
+
20 September 2014
+
HarpyEagle updated:
+
+
Fixes evidence bags and boxes eating each other. Evidence bags now store items by dragging the bag onto the item to be stored.
+
-
-
31 August 2014
-
Whitellama updated:
-
-
Matches and candles can be used to burn papers, too.
-
Observers have a bit more time (20 seconds, instead of 7.5) before the Diona join prompt disappears.
-
-
+
05 September 2014
+
RavingManiac updated:
+
+
NewPipe implemented: Supply and scrubber pipes can be run in parallel without connecting to each other.
+
Supply pipes will only connect to supply pipes, vents and Universal Pipe Adapters(UPAs).
+
Scrubber pipes will only connect to scrubber pipes, scrubbers and UPAs.
+
UPAs will connect to regular, scrubber and supply pipes.
+
-
-
5 September 2014
-
RavingManiac updated:
-
-
NewPipe implemented: Supply and scrubber pipes can be run in parallel without connecting to each other.
-
Supply pipes will only connect to supply pipes, vents and Universal Pipe Adapters(UPAs).
-
Scrubber pipes will only connect to scrubber pipes, scrubbers and UPAs.
-
UPAs will connect to regular, scrubber and supply pipes.
-
-
+
31 August 2014
+
Whitellama updated:
+
+
Matches and candles can be used to burn papers, too.
+
Observers have a bit more time (20 seconds, instead of 7.5) before the Diona join prompt disappears.
+
+
27 August 2014
+
Whitellama updated:
+
+
Made destination taggers more intuitive so you know when you've tagged something
+
Ported package label and tag sprites
+
Ported using a pen on a package to give it a title, or to write a note
+
Donut boxes and egg boxes can be constructed out of cardboard
+
-
-
27 August 2014
-
Whitellama updated:
-
-
Made destination taggers more intuitive so you know when you've tagged something
-
Ported package label and tag sprites
-
Ported using a pen on a package to give it a title, or to write a note
-
Donut boxes and egg boxes can be constructed out of cardboard
-
-
+
05 August 2014
+
HarpyEagle updated:
+
+
Atmos Rewrite. Many atmos devices now use power according to their load and gas physics
+
Pressure regulator device. Replaces the passive gate and can regulate input or output pressure
+
Gas heaters and gas coolers are now constructable and can be upgraded with parts from research
+
Fixes recharger and cell charger power draw. Rechargers draw 15 kW, wall chargers draw 25 kW, and heavy-duty cell chargers draw 40 kW. Cyborg charging stations draw 75 kW.
+
Laptops, and various other machines, now draw more reasonable amounts of power
+
Machines will periodically update their powered status if moved from a powered to an unpowered area and vice versa
+
-
PsiOmegaDelta updated:
-
-
AI can now make priority announcements.
-
PDAs display the station time upon examination.
-
Status displays can now also show the station time.
-
Security HUDs now have improved handling of alt-titles.
-
Crew record photos can now be updated through security consoles.
-
pAI settings can now be configured from the character setup screen.
-
Pipes can now be placed by clicking the floor, similar to power cables.
-
Mechas and cargo trains can no longer enter the transfer shuttle, Odysseys with patients excepted.
-
-
Kelenius updated:
-
-
Wizards now use a new item: scrying orb. It grants x-ray vision upon purchase, and can be used to temporary leave your body as a ghost.
-
-
+
02 August 2014
+
Whitellama updated:
+
+
Arcane tomes can now be stored on bookshelves.
+
Dionaea players no longer crash on death, and now become nymphs properly.
+
+
31 July 2014
+
HarpyEagle updated:
+
+
Stun batons now work like tasers and deal agony instead of stun
+
Being hit in the hands with a stun weapon will cause whatever is being held to be dropped
+
Handcuffs now require an aggressive grab to be used
+
-
-
5 August 2014
-
HarpyEagle updated:
-
-
Atmos Rewrite. Many atmos devices now use power according to their load and gas physics
-
Pressure regulator device. Replaces the passive gate and can regulate input or output pressure
-
Gas heaters and gas coolers are now constructable and can be upgraded with parts from research
-
Fixes recharger and cell charger power draw. Rechargers draw 15 kW, wall chargers draw 25 kW, and heavy-duty cell chargers draw 40 kW. Cyborg charging stations draw 75 kW.
-
Laptops, and various other machines, now draw more reasonable amounts of power
-
Machines will periodically update their powered status if moved from a powered to an unpowered area and vice versa
-
-
+
26 July 2014
+
Whitellama updated:
+
+
Added dynamic flavour text.
+
Fixed bug with suit fibers and fingerprints.
+
-
-
31 August 2014
-
Whitellama updated:
-
-
Matches and candles can be used to burn papers, too.
-
Observers have a bit more time (20 seconds, instead of 7.5) before the Diona join prompt disappears.
-
-
+
20 July 2014
+
PsiOmegaDelta updated:
+
+
AI can now store up to five camera locations and return to them when desired.
+
AI can now alt+left click turfs in camera view to list and interact with the objects.
+
AI can now ctrl+click turret controls to enable/disable turrets.
+
AI can now alt+click turret controls to toggle stun/lethal mode.
+
AI can now select which channel to state laws on.
+
-
-
2 August 2014
-
2 August 2014
-
Whitellama updated:
-
-
Arcane tomes can now be stored on bookshelves.
-
Dionaea players no longer crash on death, and now become nymphs properly.
-
-
+
06 July 2014
+
HarpyEagle updated:
+
+
Re-enabled and rewrote the wound infection system
+
Infections can be prevented by properly bandaging and salving wounds
+
Infections are cured by spaceacillin
+
-
-
31 July 2014
-
HarpyEagle updated:
-
-
Stun batons now work like tasers and deal agony instead of stun
-
Being hit in the hands with a stun weapon will cause whatever is being held to be dropped
-
Handcuffs now require an aggressive grab to be used
-
-
+
01 July 2014
+
Various updated:
+
+
Hardsuit breaching.
+
Rewritten fire.
+
Supermatter now glows and sucks things into it as it approaches criticality.
Escape pods only launch automatically during emergency evacuations
+
Escape pods can be made to launch during regular crew transfers using the control panel inside the pod, or by emagging the panel outside the pod
+
When swiped or emagged, the crew transfer shuttle can be delayed in addition to being launched early
+
-
-
26 July 2014
-
Whitellama updated:
-
-
Added dynamic flavour text.
-
Fixed bug with suit fibers and fingerprints.
-
-
+
20 June 2014
+
Cael_Aislinn updated:
+
+
New discoverable items added to xenoarchaeology, and new features for some existing ones. Artifact harvesters can now harvest the secondary effect of artifacts as well as the primary one.
+
+
Artifact utilisers should be much nicer/easier to use now.
+
Alden-Saraspova counters and talking items should work properly now.
+
+
+
+
19 June 2014
+
Chinsky updated:
+
+
Adds guest terminals on the map. These wall terminals let anyone issue temporary IDs. Only access that issuer has can be granted, and maximum time pass can be issued for is 20 minutes. All operations are logged in terminals.
+
-
-
20 July 2014
-
PsiOmegaDelta updated:
-
-
AI can now store up to five camera locations and return to them when desired.
-
AI can now alt+left click turfs in camera view to list and interact with the objects.
-
AI can now ctrl+click turret controls to enable/disable turrets.
-
AI can now alt+click turret controls to toggle stun/lethal mode.
-
AI can now select which channel to state laws on.
-
-
+
15 June 2014
+
HarpyEagle updated:
+
+
Fixed wound autohealing regardless of damage amount. The appropriate wound will now be assigned correctly based on damage amount and type
+
Fixed several other bugs related wounds that resulted in damage magically disappearing
+
Fixed various sharp objects not being counted as sharp, bullets in particular
+
Fixed armour providing more protection from bullets than it was supposed to
+
-
-
6 July 2014
-
HarpyEagle updated:
-
-
Re-enabled and rewrote the wound infection system
-
Infections can be prevented by properly bandaging and salving wounds
-
Infections are cured by spaceacillin
-
-
+
13 June 2014
+
HarpyEagle updated:
+
+
Added docking ports for shuttles
+
Shuttle airlocks will automatically open and close, preventing people from being sucked into space by because someone on another z-level called a shuttle
+
Some docking ports can also double as airlocks
+
Docking ports can be overriden to prevent any automatic action. Shuttles will wait for players to open/close doors manually
+
Shuttles can be forced launched, which will make them not wait for airlocks to be properly closed
+
-
-
1 July 2014
-
Various updated:
-
-
Hardsuit breaching.
-
Rewritten fire.
-
Supermatter now glows and sucks things into it as it approaches criticality.
Escape pods only launch automatically during emergency evacuations
-
Escape pods can be made to launch during regular crew transfers using the control panel inside the pod, or by emagging the panel outside the pod
-
When swiped or emagged, the crew transfer shuttle can be delayed in addition to being launched early
-
-
+
03 June 2014
+
Hubblenaut updated:
+
+
Added wheelchairs
+
Replaced stool in Medical Examination with wheelchair
+
Using a fire-extinguisher to propel you on a chair can have consequences (drive into walls and people, do it!)
+
+
31 May 2014
+
Jarcolr updated:
+
+
21 New cargo crates, go check them out!
+
Peanuts have now been added, food items are now being developed.
+
2 new cargo groups, Miscellaneous and Supply.
+
Sugarcane seeds can now be gotten from the seed dispenser.
+
5 new satchels when selecting "satchel" for RD, scientist, botanist, virologist, geneticist (disabled) and chemist.
+
Clicking on a player with a paper/book when you have the eyes selected shows them the book/paper forcefully.
+
-
-
19 Ð¸ÑŽÐ½Ñ 2014
-
Chinsky updated:
-
-
Adds guest terminals on the map. These wall terminals let anyone issue temporary IDs. Only access that issuer has can be granted, and maximum time pass can be issued for is 20 minutes. All operations are logged in terminals.
-
-
+
28 May 2014
+
Chinsky updated:
+
+
Adds few new paperBBcode tags, to make up for HTML removal.
+
[logo] tag draws NT logo image (one from wiki).
+
[table] [/table] tags mark borders of tables. [grid] [/grid] are borderless tables, useful of making layouts. Inside tables following tags are used: [row] marks beginning of new table row, [cell] - beginning of new table cell.
+
-
-
15 June 2014
-
HarpyEagle updated:
-
-
Fixed wound autohealing regardless of damage amount. The appropriate wound will now be assigned correctly based on damage amount and type
-
Fixed several other bugs related wounds that resulted in damage magically disappearing
-
Fixed various sharp objects not being counted as sharp, bullets in particular
-
Fixed armour providing more protection from bullets than it was supposed to
-
-
+
23 May 2014
+
Hubble updated:
+
+
Personal lockers are now resettable
+
Take off people's accessories or change their sensors in the drag and drop-interface
+
Merge paper bundles by hitting one with another
+
Line breaks in Security, Medical and Employment Records
+
Record printouts will have names on it
+
Set other people's internals in belt and suit storage slots
+
No longer changing suit sensors while cuffed
+
No longer emptying other people's pockets when they are not full yet
+
-
-
20 June 2014
-
Cael_Aislinn updated:
-
-
New discoverable items added to xenoarchaeology, and new features for some existing ones. Artifact harvesters can now harvest the secondary effect of artifacts as well as the primary one.
-
-
Artifact utilisers should be much nicer/easier to use now.
-
Alden-Saraspova counters and talking items should work properly now.
-
-
-
+
16 May 2014
+
HarpyEagle updated:
+
+
Silicon mob types (AI, cyborgs, PAI) can now speak certain species languages depending on type and module
+
Languages can now be whispered when using the language code with either the whisper verb or the whisper speech code
+
-
-
13 June 2014
-
HarpyEagle updated:
-
-
Added docking ports for shuttles
-
Shuttle airlocks will automatically open and close, preventing people from being sucked into space by because someone on another z-level called a shuttle
-
Some docking ports can also double as airlocks
-
Docking ports can be overriden to prevent any automatic action. Shuttles will wait for players to open/close doors manually
-
Shuttles can be forced launched, which will make them not wait for airlocks to be properly closed
-
-
+
06 May 2014
+
Hubble updated:
+
+
Clip papers together by hitting a paper with a paper or photo
+
Adds icons for copied stamps
+
-
-
3 Juni 2014
-
Hubblenaut updated:
-
-
Added wheelchairs
-
Replaced stool in Medical Examination with wheelchair
-
Using a fire-extinguisher to propel you on a chair can have consequences (drive into walls and people, do it!)
-
-
-
-
-
31 May 2014
-
Jarcolr updated:
-
-
21 New cargo crates, go check them out!
-
Peanuts have now been added, food items are now being developed.
-
2 new cargo groups, Miscellaneous and Supply.
-
Sugarcane seeds can now be gotten from the seed dispenser.
-
5 new satchels when selecting "satchel" for RD, scientist, botanist, virologist, geneticist (disabled) and chemist.
-
Clicking on a player with a paper/book when you have the eyes selected shows them the book/paper forcefully.
-
-
-
-
-
23 Mai 2014
-
Hubble updated:
-
-
Personal lockers are now resettable
-
Take off people's accessories or change their sensors in the drag and drop-interface
-
Merge paper bundles by hitting one with another
-
Line breaks in Security, Medical and Employment Records
-
Record printouts will have names on it
-
Set other people's internals in belt and suit storage slots
-
No longer changing suit sensors while cuffed
-
No longer emptying other people's pockets when they are not full yet
-
-
-
-
-
16 May 2014
-
HarpyEagle updated:
-
-
Silicon mob types (AI, cyborgs, PAI) can now speak certain species languages depending on type and module
-
Languages can now be whispered when using the language code with either the whisper verb or the whisper speech code
-
-
-
-
-
6 Mai 2014
-
Hubble updated:
-
-
Clip papers together by hitting a paper with a paper or photo
-
Adds icons for copied stamps
-
-
-
-
-
23 Mai 2014
-
Hubble updated:
-
-
Personal lockers are now resettable
-
Take off people's accessories or change their sensors in the drag and drop-interface
-
Merge paper bundles by hitting one with another
-
Line breaks in Security, Medical and Employment Records
-
Record printouts will have names on it
-
Set other people's internals in belt and suit storage slots
-
No longer changing suit sensors while cuffed
-
No longer emptying other people's pockets when they are not full yet
-
-
-
-
-
-
6 Mai 2014
-
Hubble updated:
-
-
Clip papers together by hitting a paper with a paper or photo
-
Adds icons for copied stamps
-
-
-
-
-
-
3 May 2014
-
Cael_Aislinn updated:
-
-
Coming out of nowhere the past few months, the Garland Corporation has made headlines with a new prehistoric theme park delighting travellers with species thought extinct. Now available for research stations everywhere is the technology that made it all possible! Features include:
+
03 May 2014
+
Cael_Aislinn updated:
+
+
Coming out of nowhere the past few months, the Garland Corporation has made headlines with a new prehistoric theme park delighting travellers with species thought extinct. Now available for research stations everywhere is the technology that made it all possible! Features include:
- 13 discoverable prehistoric species to clone from fossils (including 5 brand new ones).
- 11 discoverable prehistoric plants to clone from fossils (including 9 brand new ones).
- New minigame that involves correctly ordering the genomes inside each genetic sequence to unlock an animal/plant.
- Some prehistoric animals and plants may seem strangely familiar... while others may bring more than the erstwhile scientist bargains for.
-
-
-
-
-
-
-
-
28 Ð¼Ð°Ñ 2014
-
Chinsky updated:
-
-
Adds few new paperBBcode tags, to make up for HTML removal.
-
[logo] tag draws NT logo image (one from wiki).
-
[table] [/table] tags mark borders of tables. [grid] [/grid] are borderless tables, useful of making layouts. Inside tables following tags are used: [row] marks beginning of new table row, [cell] - beginning of new table cell.
-
-
-
-
-
-
-
-
28 Ð¼Ð°Ñ 2014
-
Chinsky updated:
-
-
Adds few new paperBBcode tags, to make up for HTML removal.
-
[logo] tag draws NT logo image (one from wiki).
-
[table] [/table] tags mark borders of tables. [grid] [/grid] are borderless tables, useful of making layouts. Inside tables following tags are used: [row] marks beginning of new table row, [cell] - beginning of new table cell.
-
-
-
-
-
-
29 April 2014
-
HarpyEagle updated:
-
-
Webbing vest storage can now be accessed by clicking on the item in inventory
-
Holsters can be accessed by clicking on them in inventory
-
Webbings and other suit attachments are now visible on the icon in inventory
-
Removing jumpsuits now requires drag and drop to prevent accidental undressing
-
Added an action icon for magboots that can be used to toggle them similar to flashlights
-
Fuel tanks now spill fuel when wrenched open
-
-
-
-
-
25 April 2014
-
Various updated:
-
-
Overhauled saycode, you can now use languages over the radio.
-
Chamelon items beyond just the suit.
-
NanoUI Virology
-
3D Sounds
-
AI Channel color for when they want to be all sneaky
-
New inflatable walls and airlocks for your breach sealing pleasure.
-
Carbon Copy papers, so you can subject everyone to your authority and paperwork, but mainly paperwork
-
Undershirts and rolling down jumpsuits
-
Insta-hit tasers, can be shot through glass as well.
-
Changeling balances, an emphasis put more on stealth.
-
Genetics disabled
-
Telescience removed, might be added again when we come up with a less math headache enducing version of it.
-
Bugfixes galore!
-
-
-
-
-
11 April 2014
-
Jarcolr updated:
-
You can now flip coins like a D2
-
Miscellaneous cargo crates got a tiny buff, Standard Costume crate is now Costume Crate
-
Grammar patch,telekinesis/amputated arm exploit fixes,more in the future
-
Grille kicking now does less damage
-
TELESCOPIC baton no longer knocks anybody down,still got a lot of force though
-
Other small-ish changes and fixes that aren't worth mentioning
-
-
-
-
-
6 April 2014
-
RavingManiac updated:
-
-
Tape recorders and station-bounced radios now work inside containers and closets.
-
-
-
-
-
30 March 2014
-
RavingManiac updated:
-
-
Inflatable walls and doors added. Useful for sealing off hull breaches, but easily punctured by sharp objects and Tajarans.
-
-
-
-
-
10 March 2014
-
Chinsky updated:
-
-
Viruses now affect certain range of species, different for each virus
-
Spaceacilline now prevents infection, and has a small chance to cure viruses at Stage 1. It does not give them antibodies though, so they can get sick again!
-
Biosuits and spacesuits now offer more protection against viruses. Full biosuit competely prevents airborne infection, when coupled with gloves they both protect quite well from contact ones
-
Sneezing now spreads viruses in front of mob. Sometimes he gets a warning beforehand though
-
-
-
-
-
5 March 2014
-
RavingManiac updated:
-
-
Smartfridges added to the bar, chemistry and virology. No more clutter!
-
A certain musical instrument has returned to the bar.
-
There is now a ten second delay between ingesting a pill/donut/milkshake and regretting it.
-
-
-
-
-
1 March 2014
-
Various updated:
-
-
Paint Mixing, red and blue makes purple!
-
New posters to tell you to respect those darned cat people
-
NanoUI for APC's, Canisters, Tank Transfer Valves and the heaters / coolers
-
PDA bombs are now less annoying, and won't always blow up / cause internal bleeding
-
Blob made less deadly
-
Objectiveless Antags now a configuration option, choose your own adventure!
-
Engineering redesign, now with better monitoring of the explodium supermatter!
-
Security EOD
-
New playable race, IPC's, go beep boop boop all over the station!
-
Gamemode autovoting, now players don't have to call for gamemode votes, it's automatic!
-
-
-
-
-
19 February 2014
-
Aryn updated:
-
-
New air model. Nothing should change to a great degree, but temperature flow might be affected due to closed connections not sticking around.
-
-
-
-
-
1 February 2014
-
Various updated:
-
-
NanoUI for PDA
-
Write in blood while a ghost in cult rounds with enough cultists
-
Cookies, absurd sandwiches, and even cookable dioanae nymphs!
-
A bunch of new guns and other weapons
-
Species specific blood
-
-
-
-
-
1 January 2014
-
Various updated:
-
-
AntagHUD and MedicalHUD for ghosts, see who the baddies are, check for new configuration options.
-
Ghosts will now have bold text if they are in the same room as the person making conversations easier to follow.
-
New hairstyles! Now you can use something other then hotpink floor length braid.
-
DNA rework, tell us how you were cloned and became albino!
-
Dirty floors, so now you know exactly how lazy the janitors are!
-
A new UI system, feel free to color it yourself, don't set it to completely clear or you will have a bad time.
-
Cryogenic storage, for all your SSD needs.
-
New hardsuits for those syndicate tajaran
-
-
-
-
-
18 December 2013
-
RavingManiac updated:
-
-
Mousetraps can now be "hidden" through the right-click menu. This makes them go under tables, clutter and the like. The filthy rodents will never see it coming!
-
Monkeys will no longer move randomly while being pulled.
-
-
-
-
-
1 December 2013
-
Various Developers banged their keyboards together:
-
-
New Engine, the supermatter, figure out what a cooling loop is, or don't and blow up engineering!
-
Each department will have it's own fax, make a copy of your butt and fax it to the admins!
-
Booze and soda dispensers, they are like chemmasters, only with booze and soda!
-
Bluespace and Cryostasis beakers, how do they work? Fuggin bluespace how do they work?
-
You can now shove things into vending machines, impress your friends on how things magically disappear out of your hands into the machine!
-
Robots and Androids (And gynoids too!) can now use custom job titles
-
Various bugfixes
-
-
-
-
-
24 November 2013
-
Yinadele updated:
-
-
Supermatter engine added! Please treat your new engine gently, and report any strangeness!
-
Rebalanced events so people don't explode into appendicitis or have their organs constantly explode.
-
Vending machines have had bottled water, iced tea, and grape soda added.
-
Head reattachment surgery added! Sew heads back on proper rather than monkey madness.
Cyborg alt titles: Robot, and Android added! These will make you spawn as a posibrained robot. Please enjoy!
-
Fixed the sprite on the modified welding goggles, added a pair to the CE's office where they'll be used.
-
Fixed atmos computers- They are once again responsive!
-
Added in functionality proper for explosive implants- You can now set their level of detonation, and their effects are more responsively concrete depending on setting.
-
Hemostats re-added to autolathe!
-
Added two manuals on atmosia and EVA, by MagmaRam! Found in engineering and the engineering bookcase.
-
Fixed areas in medbay to have fully functional APC sectors.
-
Girders are now lasable.
-
Please wait warmly, new features planned for next merge!
-
-
-
-
-
23 November 2013
-
Ccomp5950 updated:
-
-
Players are now no longer able to commit suicide with a lasertag gun, and will feel silly for doing so.
-
Ghosts hit with the cult book shall now actually become visible.
-
The powercells spawned with Exosuits will now properly be named to not confuse bearded roboticists.
-
Blindfolded players will now no longer require eye surgery to repair their sight, removing the blindfold will be sufficient.
-
Atmospheric Technicians will now have access to Exterior airlocks.
-
-
-
-
-
1 November 2013
-
Various updated:
-
-
Autovoting, Get off the station when your 15 hour workweek is done, thanks unions!
-
Some beach props that Chinsky finds useless.
-
Updated NanoUI
-
Dialysis while in sleepers - removes reagents from mobs, like the chemist, toss him in there!
-
Pipe Dispensers can now be ordered by Cargo
-
Fancy G-G-G-G-Ghosts!
-
-
-
-
-
29 October 2013
-
Cael_Aislinn updated:
-
-
Xenoarchaeology's chemical analysis and six analysis machines are gone, replaced by a single one which can be beaten in a minigame.
-
Sneaky traitors will find new challenges to overcome at the research outpost, but may also find new opportunities (transit tubes can now be traversed).
-
Finding active alien machinery should now be made significantly easier with the Alden-Saraspova counter.
-
-
-
-
-
-
06 October 2013
-
Chinsky updated:
-
-
Added contact-spread viruses. Spread if infected guy touches someone with bare hands, or if someone touches bare infected guy. Biosuits/gloves help.
-
Changed way airborne viruses spread a bit. Now 20% of breaths will carry viruses to adjacent tiles. Wearing sterile mask cuts down it to 5%. Masks, bio/space suits (only when worn with matching helmet) protect, internals protect completely.
-
Raised infection chances considerably. They were so low people reported that infection does not work. Now it's 50-90% chance for unprotected folks.
-
Blood puddles and mucus now spread the fun again
-
-
-
-
-
-
06 October 2013
-
Chinsky updated:
-
-
Return of dreaded side effects. They now manifest well after their cause disappears, so curing them should be possible without them reappearing immediately. They also lost last stage damaging effects.
-
-
-
-
-
September 24th, 2013
-
Snapshot updated:
-
-
Removed hidden vote counts.
-
Removed hiding of vote results.
-
Removed OOC muting during votes.
-
Crew transfers are no longer callable during Red and Delta alert.
-
Started work on Auto transfer framework.
-
-
-
-
-
18 September 2013
-
Kilakk updated:
-
-
Fax machines! The Captain and IA agents can use the fax machine to send properly formatted messages to Central Command.
-
Gave the fax machine a fancy animated sprite. Thanks Cajoes!
-
-
-
-
-
August 8th, 2013
-
Erthilo updated:
-
-
Raise Dead rune now properly heals and revives dead corpse.
-
Admin-only rejuvenate verb now heals all organs, limbs, and diseases.
-
Cyborg sprites now correctly reset with reset boards. This means cyborg appearances can now be changed without admin intervention.
-
-
-
-
-
2013/08/4
-
Chinsky updated:
-
-
Health HUD indicator replaced with Pain indicator. Now health indicator shows pain level instead of actual vitals level. Some types of damage contribute more to pain, some less, usually feeling worse than they really are.
-
-
-
-
-
-
2013/08/01
-
Chinsky updated:
-
-
Old new medical features:
-
Autoinjectors! They come preloaded with 5u of inapro, can be used instantly, and are one-use. You can replace chems inside using a syringe. Box of them is added to Medicine closet and medical supplies crate.
-
Splints! Target broken liimb and click on person to apply. Can be taken off in inventory menu, like handcuffs. Splinted limbs have less negative effects.
-
Advanced medikit! Red and mean, all doctors spawn with one. Contains better stuff - advanced versions of bandaids and aloe heal 12 damage on the first use.
-
Wounds with damage above 50 won't heal by themselves even if bandaged/salved. Would have to seek advanced medical attention for those.
-
-
-
-
-
July 30th, 2013
-
Erthilo updated:
-
-
EFTPOS and ATM machines should now connect to databases.
-
Gravitational Catapults can now be removed from mechs.
-
Ghost manifest rune paper naming now works correctly.
-
Fix for newscaster special characters. Still not recommended.
-
-
-
-
-
30.07.2013
-
Kilakk updated:
-
-
Added colored department radio channels.
-
-
-
-
-
28.07.2013
-
Segrain updated:
-
-
Camera console circuits can be adjusted for different networks.
-
Nuclear operatives and ERT members have built-in cameras in their helmets. Activate helmet to initialize it.
-
-
-
-
-
26.07.2013
-
Kilakk updated:
-
-
Brig cell timers will no longer start counting down automatically.
-
Separated the actual countdown timer from the timer controls. Pressing "Set" while the timer is counting down will reset the countdown timer to the time selected.
-
-
-
-
2013-11-07
-
Chinsky updated:
-
-
Gun delays. All guns now have delays between shots. Most have less than second, lasercannons and pulse rifles have around 2 seconds delay. Automatics have zero, click-speed.
-
-
-
-
2013/07/06
-
Chinsky updated:
-
-
Humans now can be infected with more than one virus at once.
-
All analyzed viruses are put into virus DB. You can view it and edit their name and description on medical record consoles.
-
Only known viruses (ones in DB) will be detected by the machinery and HUDs.
-
Viruses cause fever, body temperature rising the more stage is.
-
Humans' body temperature does not drift towards room one unless there's big difference in them.
-
Virus incubators now can transmit viuses from dishes to blood sample.
-
New machine - centrifuge. It can isolate antibodies or viruses (spawning virus dish) from a blood sample in vials. Accepts vials only.
-
Fancy vial boxes in virology, one of them is locked by ID with MD access.
-
Engineered viruses are now ariborne too.
-
-
-
-
05.07.2013
-
Spamcat updated:
-
-
Pulse! Humans now have hearbeat rate, which can be measured by right-clicking someone - Check pulse or by health analyzer. Medical machinery also has heartbeat monitors. Certain meds and conditions can influence it.
-
-
-
-
03.07.2013
-
Segrain updated:
-
-
Security and medical cyborgs can use their HUDs to access records.
-
-
-
-
June 28th, 2013
-
Segrain updated:
-
-
AIs are now able to examine what they see.
-
-
-
-
June 27th, 2013
-
Segrain updated:
-
-
ID cards properly setup bloodtype, DNA and fingerprints again.
-
-
-
-
June 26th, 2013
-
Whitellama updated:
-
-
One-antag rounds (like wizard/ninja) no longer end automatically upon death
-
Space ninja has been implemented as a voteable gamemode
-
Space ninja spawn landmarks have been implemented (but not yet placed on the map), still spawn at carps-pawns instead. (The code will warn you about this and ask you to report it, it's a known issue.)
-
Five new space ninja directives have been added, old directives have been reworded to be less harsh
-
Space ninjas have been given their own list as antagonists, and are no longer bundled up with traitors
-
Space ninjas with a "steal a functional AI" objective will now succeed by downloading one into their suits
-
Space ninja suits' exploding on death has been nerfed, so as not to cause breaches
-
A few space ninja titles/names have been added and removed to be slightly more believable
-
The antagonist selector no longer chooses jobbanned players when it runs out of willing options
-
-
-
-
June 26th, 2013
-
Segrain updated:
-
-
Autopsy scanner properly displays time of wound infliction and death.
-
Autopsy scanner properly displays wounds by projectile weapons.
-
-
-
-
June 23rd, 2013
-
Segrain updated:
-
-
Airlocks of various models can be constructed again.
-
-
-
-
-
June 23rd, 2013
-
faux updated:
-
-
There has been a complete medbay renovation spearheaded by Vetinarix. http://baystation12.net/forums/viewtopic.php?f=20&t=7847 <-- Please put any commentary good or bad, here.
-
Some maintenance doors within RnD and Medbay have had their accesses changed. Maintenance doors in the joint areas (leading to the research shuttle, virology, and xenobiology) are now zero access. Which means anyone in those joints can enter the maintenance tunnels. This was done to add additional evacuation locations during radiation storms. Additional maintenance doors were added to the tunnels in these areas to prevent docs and scientists from running about.
-
Starboard emergency storage isn't gone now, it's simply located in the escape wing.
-
An engineering training room has been added to engineering. This location was previously where surgery was located. If you are new to engineering or need to brush up on your skills, please use this area for testing.
-
-
-
-
-
June 22nd 2013
-
Cael_Aislinn updated:
-
-
The xenoarchaeology depth scanner will now tell you what energy field is required to safely extract a find.
-
Excavation picks will now dig faster, and xenoarchaeology as a whole should be easier to do.
-
-
-
-
-
21.06.2013
-
Jupotter updated:
-
-
Fix the robotiscist preview in the char setupe screen
-
-
-
-
-
18.06.2013
-
Segrain updated:
-
-
Fixed some bugs in windoor construction.
-
Secure windoors are made with rods again.
-
Windoors drop their electronics when broken. Emagged windoors can have theirs removed by crowbar.
-
Airlock electronics can be configured to make door open for any single access on it instead of all of them.
-
Cyborgs can preview their icons before choosing.
-
-
-
-
-
13.06.2013
-
Kilakk updated:
-
-
Added the Xenobiologist job. Has access to the research hallway and to xenobiology.
-
Removed Xenobiology access from Scientists.
-
Removed the Xenobiologist alternate title from Scientists.
-
Added "Xenoarchaeology" to the RD, Scientists, and to the ID computer.
-
Changed the Research Outpost doors to use "Xenoarchaeology" access.
-
-
-
-
-
6-13-13
-
Asanadas updated:
-
-
Added a whimsical suit to the head of personnel's secret clothing locker.
-
-
-
-
-
12/06/2013
-
Zuhayr updated:
-
-
Added pneumatic cannon and harpoons.
-
Added embedded projectiles. Bullets and thrown weapons may stick in targets. Throwing them by hand won't make them stick, firing them from a cannon might. Implant removal surgery will get rid of shrapnel and stuck items.
-
-
-
-
-
-
6/11/13
-
Meyar updated:
-
-
Fixes a security door with a firedoor ontop of it.
-
Fixed a typo relating to the admin Select Equipment Verb. (It's RESPONSE team not RESCUE team)
-
ERT are now automated, from their spawn to their shuttle. Admin intervention no longer required! (Getting to the mechs still requires admin permission generally)
-
Added flashlights to compensate for the weakened PDA lights
-
ERT Uniforms updated to be in line with Centcom uniforms. No more turtlenecks, no sir.
-
-
-
-
-
-
09.06.2013
-
Segrain updated:
-
-
Emagged supply console can order SpecOp crates again.
-
-
-
-
-
Meyar
-
6/6/13 updated:
-
-
Adds missing disposal pipes in chemistry
-
-
-
-
-
05.06.2013
-
Segrain updated:
-
-
Exosuits now can open firelocks by walking into them.
-
-
-
-
-
6/5/13
-
Meyar updated:
-
-
Departments SHOULD have access to adjacent maintinence tunnels incase of radstorm or nafarious dealings.
-
Fixed the northern EVA maintinence door.
-
Hand full of mapbugs.
-
MULES should be able to get to security now.
-
Nerfed PDA lights to a 3x3 area, makes the flashlight actually worthwhile.
-
-
-
-
-
-
6/4/13
-
Meyar updated:
-
-
Disposal's mail routing fixed. Missing pipes replaced.
-
Chemistry is once again a part of the disposals delivery circuit.
-
Added missing sorting junctions to Security and HoS office.
-
Fixed a duplicate sorting junction.
-
-
-
-
-
-
5.06.2013
-
Chinsky updated:
-
-
Load bearing equipment - webbings and vests for engineers and sec. Attach to jumpsuit, use 'Look in storage' verb (object tab) to open.
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
1.06.2013
-
Chinsky updated:
-
-
Bloody footprints! Now stepping in the puddle will dirty your shoes/feet and make you leave bloody footprints for a bit.
-
Blood now dries up after some time. Puddles take ~30 minutes, small things 5 minutes.
-
Untreated wounds now heal. No more toe stubs spamming you with pain messages for the rest of the shift.
-
On the other side, everything is healed slowly. Maximum you cna squeeze out of first aid is 0.5 health per tick per organ. Lying down makes it faster too, by 1.5x factor.
-
Lids! Click beaker/bottle in hand to put them on/off. Prevent spilling
-
Added 'hailer' to security lockers. If used in hand, says "Halt! Security!". For those who can't run and type.
-
-
-
-
-
-
31.05.2013
-
Segrain updated:
-
-
Portable canisters now properly connect to ports beneath them on map load.
-
Fixed unfastening gas meters.
-
-
-
-
-
30th May 2013
-
proliberate updated:
-
-
Station time is now displayed in the status tab for new players and AIs.
-
-
-
-
-
30.05.2013
-
Segrain updated:
-
-
Meteor showers actually spawn meteors now.
-
Engineering tape fits into toolbelt and can be placed on doors.
-
Pill bottles can hold paper.
-
-
-
-
-
May 28th, 2013
-
VitrescentTortoise updated:
-
-
Wizard's forcewall now works.
-
-
-
Xenoarchaeology picksets can now hold everything they started with.
-
-
-
-
28th May 2013
-
Erthilo updated:
-
-
Fixes everyone being able to understand alien languages. HERE IS YOUR TOWER OF BABEL
-
-
-
-
-
26th May 2013
-
Chinsky updated:
-
-
Tentacles! Now clone damage will make you horribly malformed like examine text says.
-
-
VitrescentTortoise updated:
-
-
Added a third option for not getting any job preferences. It allows you to return to the lobby instead of joining.
-
-
-
-
-
5/26/2013
-
Meyar updated:
-
-
The syndicate shuttle now has a cycling airlock during Nuke rounds.
-
Restored the ability for the syndicate Agent ID to change the name on the card (reforge it) more than once.
-
ERT Radio now functional again.
-
Research blast doors now actually lock down the entirety of station-side Research.
Fixes alien races appearing an unknown when speaking their language.
-
Fixes alien races losing their language when cloned.
-
Fixes UI getting randomly reset when trying to change it in Genetics Scanners.
-
-
-
-
-
21 May 2013
-
SkyMarshal updated:
-
-
ZAS will now speed air movement into/out of a zone when unsimulated tiles (e.g. space) are involved, in relation to the number of tiles.
-
Portable Canisters will now automatically connect to any portable connecter beneath them on map load.
-
Bug involving mis-mapped disposal junction fixed
-
Air alarms now work for atmos techs (whoops!)
-
The Master Controller now properly stops atmos when it runtimes.
-
Backpacks can no longer be contaminated
-
ZAS no longer logs air statistics.
-
ZAS now rebuilds as soon as it detects a semi-complex change in geometry. (It was doing this already, but in a convoluted way which was actually less efficient)
-
General code cleanup/commenting of ZAS
-
Jungle now initializes after the random Z-level loads and atmos initializes.
-
-
-
-
-
May 18th, 2013
-
CIB updated:
-
-
A new event type: Wallrot. Use welder or plantbgone on infected walls.
-
Newscasters now can deliver preset news stories over the course of a round. See http://baystation12.net/forums/viewtopic.php?f=14&t=7619 to add your own!
-
-
-
-
-
April 24, 2013
-
Jediluke69 updated:
-
-
Added 5 new drinks (Kira Special, Lemonade, Brown Star, Milkshakes, Rewriter)
-
Nanopaste now heals about half of what it used to
-
Ballistic crates should now come with shotguns loaded with actual shells no more beanbags
-
Iced tea no longer makes a glass of .what?
-
-
-
-
-
April 24, 2013
-
faux updated:
-
-
Mixed Wardrobe Closet now has colored shoes and plaid skirts.
-
Dress uniforms added to the Captain, RD, and HoP wardrobe closets. A uniform jacket has also been added to the Captain's closet. HoS' hat has been re-added to their closet. I do not love the CMO and CE enough to give them anything.
-
Atheletic closet now has five different swimsuits *for the ladies* in them. If you are a guy, be prepared to be yelled at if you run around like a moron in one of these. Same goes for ladies who run around in shorts with their titties swaying in the space winds.
-
A set of dispatcher uniforms will spawn in the security closet. These are for playtesting the dispatcher role.
-
New suit spawns in the laundry room. It's for geezer's only. You're welcome, Book.
-
Nurse outfit variant, orderly uniform, and first responder jacket will now spawn in the medical wardrobe closet.
-
A white wedding dress will spawn in the chaplain's closet. There are also several dresses currently only adminspawnable. Admins: Look either under "bride" or "dress." The bride one leads to the colored wedding dresses, and there are some other kinds of dresses under dress.
-
No more luchador masks or boxing gloves or boxing ring. You guys have a swimming pool now, dip in and enjoy it.
-
he meeting hall has been replaced with an awkwardly placed security office meant for prisoner processing.
-
Added a couple more welding goggles to engineering since you guys liked those a lot.
-
Flasks spawn behind the bar. Only three. Don't fight over them. I don't know how to add them to the bar vending machine otherwise I would have done that instead. Detective, you have your own flask in your office, it's underneath the cigarettes on your desk.
-
Added two canes to the medical storage, for people who have leg injuries and can't walk good and stuff. I do not want to see doctors pretending to be House. These are for patients. Do not make me delete this addition and declare you guys not being able to have nice things.
-
Secondary entance to EVA now directly leads into the medbay hardsuit section. Sorry for any inconviences this will cause. The CMO can now fetch the hardsuits whenever they want.
-
Secondary security hardsuit has been added to the armory. Security members please stop stealing engineer's hardsuits when you guys want to pair up for space travel.
-
Firelocks have been moved around in the main hallways to form really ghetto versions of airlocks.
-
Violin spawns in theatre storage now. I didn't put the piano there though, that was someone else.
-
Psych office in medbay has been made better looking.
-
-
-
-
-
24th April 2013
-
NerdyBoy1104 updated:
-
-
New Botany additions: Rice and Plastellium. New sheet material: Plastic.
-
Plastellium is refined into plastic by first grinding the produce to get plasticide. 20 plasticide + 10 polytrinic acid makes 10 sheets of plastic which can be used to make crates, forks, spoons, knives, ashtrays or plastic bags from.
-
Rice seeds grows into rice stalks that you grind to get rice. 10 Rice + 5 Water makes boiled rice, 10 rice + 5 milk makes rice pudding, 10 rice + 5 universal enzyme (in beaker) makes Sake.
-
-
-
-
-
Spamcat
-
04.05.2013 updated:
-
-
Blood type is now saved in character creation menu, no need to edit it manually every round.
-
-
-
-
-
17 April 2013
-
SkyMarshal updated:
-
-
ZAS is now more deadly, as per decision by administrative team. May be tweaked, but currently AIRFLOW is the biggest griefer.
-
World startup optimized, many functions now delayed until a player joins the server. (Reduces server boot time significantly)
-
Zones will now equalize air more rapidly.
-
ZAS now respects active magboots when airflow occurs.
-
Airflow will no longer throw you into doors and open them.
-
Race condition in zone construction has been fixed, so zones connect properly at round start.
-
Plasma effects readded.
-
Fixed runtime involving away mission.
-
-
-
-
-
17 April 2013
-
SkyMarshal updated:
-
-
ZAS is now more deadly, as per decision by administrative team. May be tweaked, but currently AIRFLOW is the biggest griefer.
-
World startup optimized, many functions now delayed until a player joins the server. (Reduces server boot time significantly)
-
Zones will now equalize air more rapidly.
-
ZAS now respects active magboots when airflow occurs.
-
Airflow will no longer throw you into doors and open them.
-
Race condition in zone construction has been fixed, so zones connect properly at round start.
-
Plasma effects readded.
-
Fixed runtime involving away mission.
-
-
-
-
-
30.04.2013
-
Spamcat updated:
-
-
Pill bottle capacity increased to 14 items.
-
Fixed Lamarr (it now spawns properly)
-
-
-
-
-
15.04.2013
-
Spamcat updated:
-
-
Added telescopic batons to HoS's and captain's lockers. These are quite robust and easily concealable.
-
-
-
-
-
May 14th 2013
-
Cael_Aislinn updated:
-
-
Depth scanners can now be used to determine what material archaeological deposits are made of, meaning lab analysis is no longer required.
-
Some useability issues with xenoarchaeology tools have been resolved, and the transit pods cycle automatically now.
-
-
-
-
-
11 April 2013
-
SkyMarshal updated:
-
-
Fire has been reworked.
-
In-game variable editor is both readded and expanded with fire controlling capability.
-
-
-
-
-
9 April 2013
-
SkyMarshal updated:
-
-
Fire Issues (Firedoors, Flamethrowers, Incendiary Grenades) fixed.
-
Fixed a bad line of code that was preventing autoignition of flammable gas mixes.
-
Volatile fuel is burned up after a point.
-
Partial-tile firedoors removed. This is due to ZAS breaking when interacting with them.
-
-
-
-
-
4 April 2013
-
SkyMarshal updated:
-
-
Fixed ZAS
-
Fixed Fire
-
-
-
-
-
March 27th 2013
-
Asanadas updated:
-
-
The Null Rod has recovered its de-culting ability, for balance reasons. Metagaming with it is a big no-no!
-
Holy Water as a liquid is able to de-cult. Less effective, but less bloody. May be changed over the course of time for balance.
-
-
-
-
-
26.03.2013
-
Spamcat updated:
-
-
Chemmaster now puts pills in pill bottles (if one is inserted).
-
Stabbing someone with a syringe now deals 3 damage instead of 7 because 7 is like, a crowbar punch.
-
Lizards can now join mid-round again.
-
Chemicals in bloodstream will transfer with blood now, so don't get drunk before your blood donation. Viruses and antibodies transfer through blood too.
-
Virology is working again.
-
-
-
-
-
March 15th 2013
-
Cael_Aislinn updated:
-
-
Mapped a compact research base on the mining asteroid, with multiple labs and testing rooms. It's reachable through a new (old) shuttle dock that leaves from the research wing on the main station.
-
-
-
-
-
14.03.2013
-
Spamcat updated:
-
-
Figured I should make one of these. Syringestabbing now produces a broken syringe complete with fingerprints of attacker and blood of a victim, so dispose your evidence carefully. Maximum transfer amount per stab is lowered to 10.
-
-
-
-
-
11/03/2013
-
Chinsky updated:
-
-
Sec HUDs now can see short versions of sec records.on examine. Med HUDs do same for medical records, and can set medical status of patient.
-
Damage to the head can now cause brain damage.
-
-
-
-
-
March 11th 2013
-
CIB updated:
-
-
Cloning now requires you to put slabs of meat into the cloning pod to replenish biomass.
-
-
-
-
-
March 11th 2013
-
Cael Aislinn updated:
-
-
The xenoarchaeology update is here. This includes a major content overhaul and a bunch of new features for xenoarchaeology.
-
Digsites (strange rock deposits) are now much more nuanced and interesting, and a huge number of minor (non-artifact) finds have been added.
-
Excavation is now a complex process that involves digging into the rock to the right depth.
-
Chemical analysis is required for safe excavation of the digsites, in order to determine how best to extract the finds.
-
Anomalous artifacts have been overhauled and many longstanding bugs with existing effects have been fixed - the anomaly utiliser should now work much more often.
-
Numerous new artifact effects have been added and some new artifact types can be dug up from the asteroid.
-
New tools and equipment have been added, including normal and spaceworthy versions of the anomaly suits, excavation tools and other neat gadgets.
-
Five books have been written by subject matter experts from around the galaxy to help the crew of the Exodus come to grips with this exacting new science (over 3000 words of tutorials!).
-
-
-
-
-
March 9th 2013
-
Cael Aislinn updated:
-
-
Beekeeping is now possible. Construct an apiary of out wood and embed it into a hydroponics tray, then get a queen bee and bottle of BeezEez from cargo bay.
+
+
+
+
29 April 2014
+
HarpyEagle updated:
+
+
Webbing vest storage can now be accessed by clicking on the item in inventory
+
Holsters can be accessed by clicking on them in inventory
+
Webbings and other suit attachments are now visible on the icon in inventory
+
Removing jumpsuits now requires drag and drop to prevent accidental undressing
+
Added an action icon for magboots that can be used to toggle them similar to flashlights
+
Fuel tanks now spill fuel when wrenched open
+
+
+
25 April 2014
+
Various updated:
+
+
Overhauled saycode, you can now use languages over the radio.
+
Chamelon items beyond just the suit.
+
NanoUI Virology
+
3D Sounds
+
AI Channel color for when they want to be all sneaky
+
New inflatable walls and airlocks for your breach sealing pleasure.
+
Carbon Copy papers, so you can subject everyone to your authority and paperwork, but mainly paperwork
+
Undershirts and rolling down jumpsuits
+
Insta-hit tasers, can be shot through glass as well.
+
Changeling balances, an emphasis put more on stealth.
+
Genetics disabled
+
Telescience removed, might be added again when we come up with a less math headache enducing version of it.
+
Bugfixes galore!
+
+
+
11 April 2014
+
Jarcolr updated:
+
+
You can now flip coins like a D2
+
Miscellaneous cargo crates got a tiny buff, Standard Costume crate is now Costume Crate
+
Grammar patch,telekinesis/amputated arm exploit fixes,more in the future
+
Grille kicking now does less damage
+
TELESCOPIC baton no longer knocks anybody down,still got a lot of force though
+
Other small-ish changes and fixes that aren't worth mentioning
+
+
+
06 April 2014
+
RavingManiac updated:
+
+
Tape recorders and station-bounced radios now work inside containers and closets.
+
+
+
30 March 2014
+
RavingManiac updated:
+
+
Inflatable walls and doors added. Useful for sealing off hull breaches, but easily punctured by sharp objects and Tajarans.
+
+
+
10 March 2014
+
Chinsky updated:
+
+
Viruses now affect certain range of species, different for each virus
+
Spaceacilline now prevents infection, and has a small chance to cure viruses at Stage 1. It does not give them antibodies though, so they can get sick again!
+
Biosuits and spacesuits now offer more protection against viruses. Full biosuit competely prevents airborne infection, when coupled with gloves they both protect quite well from contact ones
+
Sneezing now spreads viruses in front of mob. Sometimes he gets a warning beforehand though
+
+
+
05 March 2014
+
RavingManiac updated:
+
+
Smartfridges added to the bar, chemistry and virology. No more clutter!
+
A certain musical instrument has returned to the bar.
+
There is now a ten second delay between ingesting a pill/donut/milkshake and regretting it.
+
+
+
01 March 2014
+
Various updated:
+
+
Paint Mixing, red and blue makes purple!
+
New posters to tell you to respect those darned cat people
+
NanoUI for APC's, Canisters, Tank Transfer Valves and the heaters / coolers
+
PDA bombs are now less annoying, and won't always blow up / cause internal bleeding
+
Blob made less deadly
+
Objectiveless Antags now a configuration option, choose your own adventure!
+
Engineering redesign, now with better monitoring of the explodium supermatter!
+
Security EOD
+
New playable race, IPC's, go beep boop boop all over the station!
+
Gamemode autovoting, now players don't have to call for gamemode votes, it's automatic!
+
+
+
19 February 2014
+
Aryn updated:
+
+
New air model. Nothing should change to a great degree, but temperature flow might be affected due to closed connections not sticking around.
+
+
+
01 February 2014
+
Various updated:
+
+
NanoUI for PDA
+
Write in blood while a ghost in cult rounds with enough cultists
+
Cookies, absurd sandwiches, and even cookable dioanae nymphs!
+
A bunch of new guns and other weapons
+
Species specific blood
+
+
+
01 January 2014
+
Various updated:
+
+
AntagHUD and MedicalHUD for ghosts, see who the baddies are, check for new configuration options.
+
Ghosts will now have bold text if they are in the same room as the person making conversations easier to follow.
+
New hairstyles! Now you can use something other then hotpink floor length braid.
+
DNA rework, tell us how you were cloned and became albino!
+
Dirty floors, so now you know exactly how lazy the janitors are!
+
A new UI system, feel free to color it yourself, don't set it to completely clear or you will have a bad time.
+
Cryogenic storage, for all your SSD needs.
+
New hardsuits for those syndicate tajaran
+
+
+
18 December 2013
+
RavingManiac updated:
+
+
Mousetraps can now be "hidden" through the right-click menu. This makes them go under tables, clutter and the like. The filthy rodents will never see it coming!
+
Monkeys will no longer move randomly while being pulled.
+
+
+
01 December 2013
+
Various Developers banged their keyboards together: updated:
+
+
New Engine, the supermatter, figure out what a cooling loop is, or don't and blow up engineering!
+
Each department will have it's own fax, make a copy of your butt and fax it to the admins!
+
Booze and soda dispensers, they are like chemmasters, only with booze and soda!
+
Bluespace and Cryostasis beakers, how do they work? Fuggin bluespace how do they work?
+
You can now shove things into vending machines, impress your friends on how things magically disappear out of your hands into the machine!
+
Robots and Androids (And gynoids too!) can now use custom job titles
+
Various bugfixes
+
+
+
24 November 2013
+
Yinadele updated:
+
+
Supermatter engine added! Please treat your new engine gently, and report any strangeness!
+
Rebalanced events so people don't explode into appendicitis or have their organs constantly explode.
+
Vending machines have had bottled water, iced tea, and grape soda added.
+
Head reattachment surgery added! Sew heads back on proper rather than monkey madness.
Cyborg alt titles: Robot, and Android added! These will make you spawn as a posibrained robot. Please enjoy!
+
Fixed the sprite on the modified welding goggles, added a pair to the CE's office where they'll be used.
+
Fixed atmos computers- They are once again responsive!
+
Added in functionality proper for explosive implants- You can now set their level of detonation, and their effects are more responsively concrete depending on setting.
+
Hemostats re-added to autolathe!
+
Added two manuals on atmosia and EVA, by MagmaRam! Found in engineering and the engineering bookcase.
+
Fixed areas in medbay to have fully functional APC sectors.
+
Girders are now lasable.
+
Please wait warmly, new features planned for next merge!
+
+
+
23 November 2013
+
Ccomp5950 updated:
+
+
Players are now no longer able to commit suicide with a lasertag gun, and will feel silly for doing so.
+
Ghosts hit with the cult book shall now actually become visible.
+
The powercells spawned with Exosuits will now properly be named to not confuse bearded roboticists.
+
Blindfolded players will now no longer require eye surgery to repair their sight, removing the blindfold will be sufficient.
+
Atmospheric Technicians will now have access to Exterior airlocks.
+
+
+
01 November 2013
+
Various updated:
+
+
Autovoting, Get off the station when your 15 hour workweek is done, thanks unions!
+
Some beach props that Chinsky finds useless.
+
Updated NanoUI
+
Dialysis while in sleepers - removes reagents from mobs, like the chemist, toss him in there!
+
Pipe Dispensers can now be ordered by Cargo
+
Fancy G-G-G-G-Ghosts!
+
+
+
29 October 2013
+
Cael_Aislinn updated:
+
+
Xenoarchaeology's chemical analysis and six analysis machines are gone, replaced by a single one which can be beaten in a minigame.
+
Sneaky traitors will find new challenges to overcome at the research outpost, but may also find new opportunities (transit tubes can now be traversed).
+
Finding active alien machinery should now be made significantly easier with the Alden-Saraspova counter.
+
+
+
06 October 2013
+
Chinsky updated:
+
+
Return of dreaded side effects. They now manifest well after their cause disappears, so curing them should be possible without them reappearing immediately. They also lost last stage damaging effects.
+
+
+
24 September 2013
+
Snapshot updated:
+
+
Removed hidden vote counts.
+
Removed hiding of vote results.
+
Removed OOC muting during votes.
+
Crew transfers are no longer callable during Red and Delta alert.
+
Started work on Auto transfer framework.
+
+
+
18 September 2013
+
Kilakk updated:
+
+
Fax machines! The Captain and IA agents can use the fax machine to send properly formatted messages to Central Command.
+
Gave the fax machine a fancy animated sprite. Thanks Cajoes!
+
+
+
08 August 2013
+
Erthilo updated:
+
+
Raise Dead rune now properly heals and revives dead corpse.
+
Admin-only rejuvenate verb now heals all organs, limbs, and diseases.
+
Cyborg sprites now correctly reset with reset boards. This means cyborg appearances can now be changed without admin intervention.
+
+
+
04 August 2013
+
Chinsky updated:
+
+
Health HUD indicator replaced with Pain indicator. Now health indicator shows pain level instead of actual vitals level. Some types of damage contribute more to pain, some less, usually feeling worse than they really are.
+
+
+
01 August 2013
+
Asanadas updated:
+
+
The Null Rod has recovered its de-culting ability, for balance reasons. Metagaming with it is a big no-no!
+
Holy Water as a liquid is able to de-cult. Less effective, but less bloody. May be changed over the course of time for balance.
+
+
CIB updated:
+
+
Chilis and cold chilis no longer kill in small amounts
+
Chloral now again needs around 5 units to start killing somebody
+
+
Cael Aislinn updated:
+
+
Security bots will now target hostile mobs, and vice versa.
+
Carp should actually emigrate now, instead of just immigrating then squatting around the outer hull.
+
Admins and moderators have been split up into separate 'who' verbs (adminwho and modwho respectively).
+
+
CaelAislinn updated:
+
+
Re-added old ion storm laws, re-added grid check event.
+
Added Rogue Drone and Vermin Infestation random events.
+
Added/fixed space vines random event.
+
Updates to the virus events.
+
Spider infestation and alien infestation events turned off by default.
+
Soghun, taj and skrell all have unique language text colours.
+
Moderators will no longer be listed in adminwho, instead use modwho.
Autoinjectors! They come preloaded with 5u of inapro, can be used instantly, and are one-use. You can replace chems inside using a syringe. Box of them is added to Medicine closet and medical supplies crate.
+
Splints! Target broken liimb and click on person to apply. Can be taken off in inventory menu, like handcuffs. Splinted limbs have less negative effects.
+
Advanced medikit! Red and mean, all doctors spawn with one. Contains better stuff - advanced versions of bandaids and aloe heal 12 damage on the first use.
+
Wounds with damage above 50 won't heal by themselves even if bandaged/salved. Would have to seek advanced medical attention for those.
+
+
Erthilo updated:
+
+
Fixed SSD (logged-out) players not staying asleep.
+
Fixed set-pose verb and mice emotes having extra periods.
+
Fixed virus crate not appearing and breaking supply shuttle.
+
Fixed newcaster photos not being censored.
+
+
Gamerofthegame updated:
+
+
Miscellaneous mapfixes.
+
+
GauHelldragon updated:
+
+
Servicebots now have RoboTray and Printing Pen. Robotray can be used to pick up and drop food/drinks. Printing pen can alternate between writing mode and rename paper mode by clicking it.
+
Farmbots. A new type of robot that weeds, waters and fertilizes. Use robot arm on water tank. Then use plant analyzer, mini-hoe, bucket and finally proximity sensor.
+
Chefs can clang their serving trays with a rolling pin. Just like a riot shield!
+
+
Jediluke69 updated:
+
+
Added 5 new drinks (Kira Special, Lemonade, Brown Star, Milkshakes, Rewriter)
+
Nanopaste now heals about half of what it used to
+
Ballistic crates should now come with shotguns loaded with actual shells no more beanbags
+
Iced tea no longer makes a glass of .what?
+
+
Jupotter updated:
+
+
Fix the robotiscist preview in the char setupe screen
+
+
Kilakk updated:
+
+
Added the Xenobiologist job. Has access to the research hallway and to xenobiology.
+
Removed Xenobiology access from Scientists.
+
Removed the Xenobiologist alternate title from Scientists.
+
Added "Xenoarchaeology" to the RD, Scientists, and to the ID computer.
+
Changed the Research Outpost doors to use "Xenoarchaeology" access.
+
+
Meyar updated:
+
+
The syndicate shuttle now has a cycling airlock during Nuke rounds.
+
Restored the ability for the syndicate Agent ID to change the name on the card (reforge it) more than once.
+
ERT Radio now functional again.
+
Research blast doors now actually lock down the entirety of station-side Research.
New Botany additions: Rice and Plastellium. New sheet material: Plastic.
+
Plastellium is refined into plastic by first grinding the produce to get plasticide. 20 plasticide + 10 polytrinic acid makes 10 sheets of plastic which can be used to make crates, forks, spoons, knives, ashtrays or plastic bags from.
+
Rice seeds grows into rice stalks that you grind to get rice. 10 Rice + 5 Water makes boiled rice, 10 rice + 5 milk makes rice pudding, 10 rice + 5 universal enzyme (in beaker) makes Sake.
+
+
RavingManiac updated:
+
+
You can now stab people with syringes using the "harm" intent. This destroys the syringe and transfers a random percentage of its contents into the target. Armor has a 50% chance of blocking the syringe.
+
+
Segrain updated:
+
+
Meteor showers actually spawn meteors now.
+
Engineering tape fits into toolbelt and can be placed on doors.
+
Pill bottles can hold paper.
+
+
SkyMarshal updated:
+
+
Fixed ZAS
+
Fixed Fire
+
+
Spamcat updated:
+
+
Figured I should make one of these. Syringestabbing now produces a broken syringe complete with fingerprints of attacker and blood of a victim, so dispose your evidence carefully. Maximum transfer amount per stab is lowered to 10.
+
+
VitrescentTortoise updated:
+
+
Added a third option for not getting any job preferences. It allows you to return to the lobby instead of joining.
+
+
Whitellama updated:
+
+
One-antag rounds (like wizard/ninja) no longer end automatically upon death
+
Space ninja has been implemented as a voteable gamemode
+
Space ninja spawn landmarks have been implemented (but not yet placed on the map), still spawn at carps-pawns instead. (The code will warn you about this and ask you to report it, it's a known issue.)
+
Five new space ninja directives have been added, old directives have been reworded to be less harsh
+
Space ninjas have been given their own list as antagonists, and are no longer bundled up with traitors
+
Space ninjas with a "steal a functional AI" objective will now succeed by downloading one into their suits
+
Space ninja suits' exploding on death has been nerfed, so as not to cause breaches
+
A few space ninja titles/names have been added and removed to be slightly more believable
+
The antagonist selector no longer chooses jobbanned players when it runs out of willing options
+
+
Zuhayr updated:
+
+
Added pneumatic cannon and harpoons.
+
Added embedded projectiles. Bullets and thrown weapons may stick in targets. Throwing them by hand won't make them stick, firing them from a cannon might. Implant removal surgery will get rid of shrapnel and stuck items.
+
+
faux updated:
+
+
Mixed Wardrobe Closet now has colored shoes and plaid skirts.
+
Dress uniforms added to the Captain, RD, and HoP wardrobe closets. A uniform jacket has also been added to the Captain's closet. HoS' hat has been re-added to their closet. I do not love the CMO and CE enough to give them anything.
+
Atheletic closet now has five different swimsuits *for the ladies* in them. If you are a guy, be prepared to be yelled at if you run around like a moron in one of these. Same goes for ladies who run around in shorts with their titties swaying in the space winds.
+
A set of dispatcher uniforms will spawn in the security closet. These are for playtesting the dispatcher role.
+
New suit spawns in the laundry room. It's for geezer's only. You're welcome, Book.
+
Nurse outfit variant, orderly uniform, and first responder jacket will now spawn in the medical wardrobe closet.
+
A white wedding dress will spawn in the chaplain's closet. There are also several dresses currently only adminspawnable. Admins: Look either under "bride" or "dress." The bride one leads to the colored wedding dresses, and there are some other kinds of dresses under dress.
+
No more luchador masks or boxing gloves or boxing ring. You guys have a swimming pool now, dip in and enjoy it.
+
he meeting hall has been replaced with an awkwardly placed security office meant for prisoner processing.
+
Added a couple more welding goggles to engineering since you guys liked those a lot.
+
Flasks spawn behind the bar. Only three. Don't fight over them. I don't know how to add them to the bar vending machine otherwise I would have done that instead. Detective, you have your own flask in your office, it's underneath the cigarettes on your desk.
+
Added two canes to the medical storage, for people who have leg injuries and can't walk good and stuff. I do not want to see doctors pretending to be House. These are for patients. Do not make me delete this addition and declare you guys not being able to have nice things.
+
Secondary entance to EVA now directly leads into the medbay hardsuit section. Sorry for any inconviences this will cause. The CMO can now fetch the hardsuits whenever they want.
+
Secondary security hardsuit has been added to the armory. Security members please stop stealing engineer's hardsuits when you guys want to pair up for space travel.
+
Firelocks have been moved around in the main hallways to form really ghetto versions of airlocks.
+
Violin spawns in theatre storage now. I didn't put the piano there though, that was someone else.
+
Psych office in medbay has been made better looking.
+
+
proliberate updated:
+
+
Station time is now displayed in the status tab for new players and AIs.
+
+
+
30 July 2013
+
Erthilo updated:
+
+
EFTPOS and ATM machines should now connect to databases.
+
Gravitational Catapults can now be removed from mechs.
+
Ghost manifest rune paper naming now works correctly.
+
Fix for newscaster special characters. Still not recommended.
+
+
Kilakk updated:
+
+
Added colored department radio channels.
+
+
+
28 July 2013
+
Segrain updated:
+
+
Camera console circuits can be adjusted for different networks.
+
Nuclear operatives and ERT members have built-in cameras in their helmets. Activate helmet to initialize it.
+
+
+
26 July 2013
+
Kilakk updated:
+
+
Brig cell timers will no longer start counting down automatically.
+
Separated the actual countdown timer from the timer controls. Pressing "Set" while the timer is counting down will reset the countdown timer to the time selected.
+
+
+
11 July 2013
+
Chinsky updated:
+
+
Gun delays. All guns now have delays between shots. Most have less than second, lasercannons and pulse rifles have around 2 seconds delay. Automatics have zero, click-speed.
+
+
+
06 July 2013
+
Chinsky updated:
+
+
Humans now can be infected with more than one virus at once.
+
All analyzed viruses are put into virus DB. You can view it and edit their name and description on medical record consoles.
+
Only known viruses (ones in DB) will be detected by the machinery and HUDs.
+
Viruses cause fever, body temperature rising the more stage is.
+
Humans' body temperature does not drift towards room one unless there's big difference in them.
+
Virus incubators now can transmit viuses from dishes to blood sample.
+
New machine - centrifuge. It can isolate antibodies or viruses (spawning virus dish) from a blood sample in vials. Accepts vials only.
+
Fancy vial boxes in virology, one of them is locked by ID with MD access.
+
Engineered viruses are now ariborne too.
+
+
+
05 July 2013
+
Spamcat updated:
+
+
Pulse! Humans now have hearbeat rate, which can be measured by right-clicking someone - Check pulse or by health analyzer. Medical machinery also has heartbeat monitors. Certain meds and conditions can influence it.
+
+
+
03 July 2013
+
Segrain updated:
+
+
Security and medical cyborgs can use their HUDs to access records.
+
+
+
28 June 2013
+
Segrain updated:
+
+
AIs are now able to examine what they see.
+
+
+
27 June 2013
+
Segrain updated:
+
+
ID cards properly setup bloodtype, DNA and fingerprints again.
+
+
+
26 June 2013
+
Segrain updated:
+
+
Autopsy scanner properly displays time of wound infliction and death.
+
Autopsy scanner properly displays wounds by projectile weapons.
+
+
Whitellama updated:
+
+
One-antag rounds (like wizard/ninja) no longer end automatically upon death
+
Space ninja has been implemented as a voteable gamemode
+
Space ninja spawn landmarks have been implemented (but not yet placed on the map), still spawn at carps-pawns instead. (The code will warn you about this and ask you to report it, it's a known issue.)
+
Five new space ninja directives have been added, old directives have been reworded to be less harsh
+
Space ninjas have been given their own list as antagonists, and are no longer bundled up with traitors
+
Space ninjas with a "steal a functional AI" objective will now succeed by downloading one into their suits
+
Space ninja suits' exploding on death has been nerfed, so as not to cause breaches
+
A few space ninja titles/names have been added and removed to be slightly more believable
+
The antagonist selector no longer chooses jobbanned players when it runs out of willing options
+
+
+
23 June 2013
+
Segrain updated:
+
+
Airlocks of various models can be constructed again.
+
+
faux updated:
+
+
There has been a complete medbay renovation spearheaded by Vetinarix. http://baystation12.net/forums/viewtopic.php?f=20&t;=7847 <-- Please put any commentary good or bad, here.
+
Some maintenance doors within RnD and Medbay have had their accesses changed. Maintenance doors in the joint areas (leading to the research shuttle, virology, and xenobiology) are now zero access. Which means anyone in those joints can enter the maintenance tunnels. This was done to add additional evacuation locations during radiation storms. Additional maintenance doors were added to the tunnels in these areas to prevent docs and scientists from running about.
+
Starboard emergency storage isn't gone now, it's simply located in the escape wing.
+
An engineering training room has been added to engineering. This location was previously where surgery was located. If you are new to engineering or need to brush up on your skills, please use this area for testing.
+
+
+
22 June 2013
+
Cael_Aislinn updated:
+
+
The xenoarchaeology depth scanner will now tell you what energy field is required to safely extract a find.
+
Excavation picks will now dig faster, and xenoarchaeology as a whole should be easier to do.
+
+
+
21 June 2013
+
Jupotter updated:
+
+
Fix the robotiscist preview in the char setupe screen
+
+
+
18 June 2013
+
Segrain updated:
+
+
Fixed some bugs in windoor construction.
+
Secure windoors are made with rods again.
+
Windoors drop their electronics when broken. Emagged windoors can have theirs removed by crowbar.
+
Airlock electronics can be configured to make door open for any single access on it instead of all of them.
+
Cyborgs can preview their icons before choosing.
+
+
+
13 June 2013
+
Kilakk updated:
+
+
Added the Xenobiologist job. Has access to the research hallway and to xenobiology.
+
Removed Xenobiology access from Scientists.
+
Removed the Xenobiologist alternate title from Scientists.
+
Added "Xenoarchaeology" to the RD, Scientists, and to the ID computer.
+
Changed the Research Outpost doors to use "Xenoarchaeology" access.
+
+
+
12 June 2013
+
Zuhayr updated:
+
+
Added pneumatic cannon and harpoons.
+
Added embedded projectiles. Bullets and thrown weapons may stick in targets. Throwing them by hand won't make them stick, firing them from a cannon might. Implant removal surgery will get rid of shrapnel and stuck items.
+
+
+
11 June 2013
+
Meyar updated:
+
+
Fixes a security door with a firedoor ontop of it.
+
Fixed a typo relating to the admin Select Equipment Verb. (It's RESPONSE team not RESCUE team)
+
ERT are now automated, from their spawn to their shuttle. Admin intervention no longer required! (Getting to the mechs still requires admin permission generally)
+
Added flashlights to compensate for the weakened PDA lights
+
ERT Uniforms updated to be in line with Centcom uniforms. No more turtlenecks, no sir.
+
+
+
09 June 2013
+
Segrain updated:
+
+
Emagged supply console can order SpecOp crates again.
+
+
+
06 June 2013
+
Asanadas updated:
+
+
Added a whimsical suit to the head of personnel's secret clothing locker.
+
+
Meyar updated:
+
+
Disposal's mail routing fixed. Missing pipes replaced.
+
Chemistry is once again a part of the disposals delivery circuit.
+
Added missing sorting junctions to Security and HoS office.
+
Fixed a duplicate sorting junction.
+
+
+
05 June 2013
+
Chinsky updated:
+
+
Load bearing equipment - webbings and vests for engineers and sec. Attach to jumpsuit, use 'Look in storage' verb (object tab) to open.
+
+
Segrain updated:
+
+
Exosuits now can open firelocks by walking into them.
+
+
+
01 June 2013
+
Chinsky updated:
+
+
Bloody footprints! Now stepping in the puddle will dirty your shoes/feet and make you leave bloody footprints for a bit.
+
Blood now dries up after some time. Puddles take ~30 minutes, small things 5 minutes.
+
Untreated wounds now heal. No more toe stubs spamming you with pain messages for the rest of the shift.
+
On the other side, everything is healed slowly. Maximum you cna squeeze out of first aid is 0.5 health per tick per organ. Lying down makes it faster too, by 1.5x factor.
+
Lids! Click beaker/bottle in hand to put them on/off. Prevent spilling
+
Added 'hailer' to security lockers. If used in hand, says "Halt! Security!". For those who can't run and type.
+
+
+
31 May 2013
+
Segrain updated:
+
+
Portable canisters now properly connect to ports beneath them on map load.
+
Fixed unfastening gas meters.
+
+
+
30 May 2013
+
Segrain updated:
+
+
Meteor showers actually spawn meteors now.
+
Engineering tape fits into toolbelt and can be placed on doors.
+
Pill bottles can hold paper.
+
+
Spamcat updated:
+
+
Pill bottle capacity increased to 14 items.
+
Fixed Lamarr (it now spawns properly)
+
+
proliberate updated:
+
+
Station time is now displayed in the status tab for new players and AIs.
+
+
+
28 May 2013
+
Erthilo updated:
+
+
Fixes everyone being able to understand alien languages. HERE IS YOUR TOWER OF BABEL
+
+
VitrescentTortoise updated:
+
+
Wizard's forcewall now works.
+
+
+
26 May 2013
+
Chinsky updated:
+
+
Tentacles! Now clone damage will make you horribly malformed like examine text says.
+
+
Meyar updated:
+
+
The syndicate shuttle now has a cycling airlock during Nuke rounds.
+
Restored the ability for the syndicate Agent ID to change the name on the card (reforge it) more than once.
+
ERT Radio now functional again.
+
Research blast doors now actually lock down the entirety of station-side Research.
Added a third option for not getting any job preferences. It allows you to return to the lobby instead of joining.
+
+
+
25 May 2013
+
Erthilo updated:
+
+
Fixes alien races appearing an unknown when speaking their language.
+
Fixes alien races losing their language when cloned.
+
Fixes UI getting randomly reset when trying to change it in Genetics Scanners.
+
+
+
21 May 2013
+
SkyMarshal updated:
+
+
ZAS will now speed air movement into/out of a zone when unsimulated tiles (e.g. space) are involved, in relation to the number of tiles.
+
Portable Canisters will now automatically connect to any portable connecter beneath them on map load.
+
Bug involving mis-mapped disposal junction fixed
+
Air alarms now work for atmos techs (whoops!)
+
The Master Controller now properly stops atmos when it runtimes.
+
Backpacks can no longer be contaminated
+
ZAS no longer logs air statistics.
+
ZAS now rebuilds as soon as it detects a semi-complex change in geometry. (It was doing this already, but in a convoluted way which was actually less efficient)
+
General code cleanup/commenting of ZAS
+
Jungle now initializes after the random Z-level loads and atmos initializes.
+
+
+
15 May 2013
+
Spamcat updated:
+
+
Added telescopic batons to HoS's and captain's lockers. These are quite robust and easily concealable.
+
+
+
14 May 2013
+
Cael_Aislinn updated:
+
+
Depth scanners can now be used to determine what material archaeological deposits are made of, meaning lab analysis is no longer required.
+
Some useability issues with xenoarchaeology tools have been resolved, and the transit pods cycle automatically now.
+
+
+
24 April 2013
+
Jediluke69 updated:
+
+
Added 5 new drinks (Kira Special, Lemonade, Brown Star, Milkshakes, Rewriter)
+
Nanopaste now heals about half of what it used to
+
Ballistic crates should now come with shotguns loaded with actual shells no more beanbags
+
Iced tea no longer makes a glass of .what?
+
+
NerdyBoy1104 updated:
+
+
New Botany additions: Rice and Plastellium. New sheet material: Plastic.
+
Plastellium is refined into plastic by first grinding the produce to get plasticide. 20 plasticide + 10 polytrinic acid makes 10 sheets of plastic which can be used to make crates, forks, spoons, knives, ashtrays or plastic bags from.
+
Rice seeds grows into rice stalks that you grind to get rice. 10 Rice + 5 Water makes boiled rice, 10 rice + 5 milk makes rice pudding, 10 rice + 5 universal enzyme (in beaker) makes Sake.
+
+
faux updated:
+
+
Mixed Wardrobe Closet now has colored shoes and plaid skirts.
+
Dress uniforms added to the Captain, RD, and HoP wardrobe closets. A uniform jacket has also been added to the Captain's closet. HoS' hat has been re-added to their closet. I do not love the CMO and CE enough to give them anything.
+
Atheletic closet now has five different swimsuits *for the ladies* in them. If you are a guy, be prepared to be yelled at if you run around like a moron in one of these. Same goes for ladies who run around in shorts with their titties swaying in the space winds.
+
A set of dispatcher uniforms will spawn in the security closet. These are for playtesting the dispatcher role.
+
New suit spawns in the laundry room. It's for geezer's only. You're welcome, Book.
+
Nurse outfit variant, orderly uniform, and first responder jacket will now spawn in the medical wardrobe closet.
+
A white wedding dress will spawn in the chaplain's closet. There are also several dresses currently only adminspawnable. Admins: Look either under "bride" or "dress." The bride one leads to the colored wedding dresses, and there are some other kinds of dresses under dress.
+
No more luchador masks or boxing gloves or boxing ring. You guys have a swimming pool now, dip in and enjoy it.
+
he meeting hall has been replaced with an awkwardly placed security office meant for prisoner processing.
+
Added a couple more welding goggles to engineering since you guys liked those a lot.
+
Flasks spawn behind the bar. Only three. Don't fight over them. I don't know how to add them to the bar vending machine otherwise I would have done that instead. Detective, you have your own flask in your office, it's underneath the cigarettes on your desk.
+
Added two canes to the medical storage, for people who have leg injuries and can't walk good and stuff. I do not want to see doctors pretending to be House. These are for patients. Do not make me delete this addition and declare you guys not being able to have nice things.
+
Secondary entance to EVA now directly leads into the medbay hardsuit section. Sorry for any inconviences this will cause. The CMO can now fetch the hardsuits whenever they want.
+
Secondary security hardsuit has been added to the armory. Security members please stop stealing engineer's hardsuits when you guys want to pair up for space travel.
+
Firelocks have been moved around in the main hallways to form really ghetto versions of airlocks.
+
Violin spawns in theatre storage now. I didn't put the piano there though, that was someone else.
+
Psych office in medbay has been made better looking.
+
+
+
17 April 2013
+
SkyMarshal updated:
+
+
ZAS is now more deadly, as per decision by administrative team. May be tweaked, but currently AIRFLOW is the biggest griefer.
+
World startup optimized, many functions now delayed until a player joins the server. (Reduces server boot time significantly)
+
Zones will now equalize air more rapidly.
+
ZAS now respects active magboots when airflow occurs.
+
Airflow will no longer throw you into doors and open them.
+
Race condition in zone construction has been fixed, so zones connect properly at round start.
+
Plasma effects readded.
+
Fixed runtime involving away mission.
+
+
+
11 April 2013
+
SkyMarshal updated:
+
+
Fire has been reworked.
+
In-game variable editor is both readded and expanded with fire controlling capability.
+
+
+
09 April 2013
+
SkyMarshal updated:
+
+
Fire Issues (Firedoors, Flamethrowers, Incendiary Grenades) fixed.
+
Fixed a bad line of code that was preventing autoignition of flammable gas mixes.
+
Volatile fuel is burned up after a point.
+
Partial-tile firedoors removed. This is due to ZAS breaking when interacting with them.
+
+
+
04 April 2013
+
SkyMarshal updated:
+
+
Fixed ZAS
+
Fixed Fire
+
+
Spamcat updated:
+
+
Blood type is now saved in character creation menu, no need to edit it manually every round.
+
+
+
27 March 2013
+
Asanadas updated:
+
+
The Null Rod has recovered its de-culting ability, for balance reasons. Metagaming with it is a big no-no!
+
Holy Water as a liquid is able to de-cult. Less effective, but less bloody. May be changed over the course of time for balance.
+
+
+
26 March 2013
+
Spamcat updated:
+
+
Chemmaster now puts pills in pill bottles (if one is inserted).
+
Stabbing someone with a syringe now deals 3 damage instead of 7 because 7 is like, a crowbar punch.
+
Lizards can now join mid-round again.
+
Chemicals in bloodstream will transfer with blood now, so don't get drunk before your blood donation. Viruses and antibodies transfer through blood too.
+
Virology is working again.
+
+
+
15 March 2013
+
Cael_Aislinn updated:
+
+
Mapped a compact research base on the mining asteroid, with multiple labs and testing rooms. It's reachable through a new (old) shuttle dock that leaves from the research wing on the main station.
+
+
+
14 March 2013
+
Spamcat updated:
+
+
Figured I should make one of these. Syringestabbing now produces a broken syringe complete with fingerprints of attacker and blood of a victim, so dispose your evidence carefully. Maximum transfer amount per stab is lowered to 10.
+
+
+
11 March 2013
+
CIB updated:
+
+
Cloning now requires you to put slabs of meat into the cloning pod to replenish biomass.
+
+
Cael Aislinn updated:
+
+
The xenoarchaeology update is here. This includes a major content overhaul and a bunch of new features for xenoarchaeology.
+
Digsites (strange rock deposits) are now much more nuanced and interesting, and a huge number of minor (non-artifact) finds have been added.
+
Excavation is now a complex process that involves digging into the rock to the right depth.
+
Chemical analysis is required for safe excavation of the digsites, in order to determine how best to extract the finds.
+
Anomalous artifacts have been overhauled and many longstanding bugs with existing effects have been fixed - the anomaly utiliser should now work much more often.
+
Numerous new artifact effects have been added and some new artifact types can be dug up from the asteroid.
+
New tools and equipment have been added, including normal and spaceworthy versions of the anomaly suits, excavation tools and other neat gadgets.
+
Five books have been written by subject matter experts from around the galaxy to help the crew of the Exodus come to grips with this exacting new science (over 3000 words of tutorials!).
+
+
Chinsky updated:
+
+
Sec HUDs now can see short versions of sec records.on examine. Med HUDs do same for medical records, and can set medical status of patient.
+
Damage to the head can now cause brain damage.
+
+
+
09 March 2013
+
Cael Aislinn updated:
+
+
Beekeeping is now possible. Construct an apiary of out wood and embed it into a hydroponics tray, then get a queen bee and bottle of BeezEez from cargo bay.
Hives produce honey and honeycomb, but be wary if the bees start swarming.
-
-
+
-
-
March 6th 2013
-
Cael Aislinn updated:
-
-
Type 1 thermoelectric generators and the associated binary circulators are now moveable (wrench to secure/unsecure) and orderable via Quartermaster.
-
code/maps/rust_test.dmm contains an example setup for a functional RUST reactor. Maximum output is in the range of 12 to 20MW (12 to 20 million watts).
-
Removed double announcement for gridchecks, reduced duration of gridchecks.
-
-
RavingManiac updated:
-
-
You can now stab people with syringes using the "harm" intent. This destroys the syringe and transfers a random percentage of its contents into the target. Armor has a 50% chance of blocking the syringe.
-
-
+
06 March 2013
+
Cael Aislinn updated:
+
+
Type 1 thermoelectric generators and the associated binary circulators are now moveable (wrench to secure/unsecure) and orderable via Quartermaster.
+
code/maps/rust_test.dmm contains an example setup for a functional RUST reactor. Maximum output is in the range of 12 to 20MW (12 to 20 million watts).
+
Removed double announcement for gridchecks, reduced duration of gridchecks.
+
+
RavingManiac updated:
+
+
You can now stab people with syringes using the "harm" intent. This destroys the syringe and transfers a random percentage of its contents into the target. Armor has a 50% chance of blocking the syringe.
All RUST components except for TEGs (which generate the power) are now obtainable ingame, bored engineers should get hold of them and setup an experimental reactor for testing purposes.
-
-
CIB updated:
-
-
Added internal organs. They're currently all located in the chest. Use advanced scanner to detect damage. Use the same surgery as for ruptured lungs to fix them.
-
-
+
05 March 2013
+
CIB updated:
+
+
Added internal organs. They're currently all located in the chest. Use advanced scanner to detect damage. Use the same surgery as for ruptured lungs to fix them.
All RUST components except for TEGs (which generate the power) are now obtainable ingame, bored engineers should get hold of them and setup an experimental reactor for testing purposes.
+
-
-
February 27th 2013
-
Gamerofthegame updated:
-
-
Added the (base gear) ERT preset for the debug command.
-
Map fixes, Virology hole fixed. Atmospheric fixes for mining and, to a less extent, the science outpost. (No, not cycling airlocks)
-
Fiddled with the ERT set up location on Centcom. Radmins will now have a even easier time equiping a team of any real pratical size, especially coupled with the above debug command.
-
-
+
27 February 2013
+
Gamerofthegame updated:
+
+
Added the (base gear) ERT preset for the debug command.
+
Map fixes, Virology hole fixed. Atmospheric fixes for mining and, to a less extent, the science outpost. (No, not cycling airlocks)
+
Fiddled with the ERT set up location on Centcom. Radmins will now have a even easier time equiping a team of any real pratical size, especially coupled with the above debug command.
New random events: multiple new system wide-events have been have been added to the newscaster feeds, some not quite as respectable as others.
+
New random event: some lucky winners will win the TC Daily Grand Slam Lotto, while others may be the target of malicious hackers.
+
-
-
February 23rd 2013
-
Cael Aislinn updated:
-
-
Finances! Players spawn with an account, and money can be transferred between accounts, withdrawn/deposited at ATMs and charged to accounts via EFTPOS scanners.
- All players start with 500-5000 credits, credits can no longer be merged and only credits can be deposited into ATMs - so shelter your illegitimately gotten gains in physical assets and remember that fraud is frowned upon!
-
Turrets are no longer noiseless as the grave. Listen for the sound of machinery in their proximity.
-
-
+
23 February 2013
+
Cael Aislinn updated:
+
+
RUST machinery components should now be researchable (with high requirements) and orderable through QM (with high cost).
+
Shield machinery should now be researchable (with high requirements) and orderable through QM (with high cost). This one is reportedly buggy.
+
Rogue vending machines should revert back to normal at the end of the event.
+
New Unathi hair styles.
+
-
-
February 23rd 2013
-
Cael Aislinn updated:
-
-
RUST machinery components should now be researchable (with high requirements) and orderable through QM (with high cost).
-
Shield machinery should now be researchable (with high requirements) and orderable through QM (with high cost). This one is reportedly buggy.
-
Rogue vending machines should revert back to normal at the end of the event.
-
New Unathi hair styles.
-
-
+
22 February 2013
+
Chinsky updated:
+
+
Change to body cavity surgery. Can only put items in chest, groind and head. Max size for item - 3 (chest), 2 (groin), 1 (head). For chest surgery ribs should be bent open, (lung surgery until second scalpel step). Surgery step needs preparation step, with drill. After that you can place item inside, or seal it with cautery to do other step instead.
+
-
-
22/02/2013
-
Chinsky updated:
-
-
Change to body cavity surgery. Can only put items in chest, groind and head. Max size for item - 3 (chest), 2 (groin), 1 (head). For chest surgery ribs should be bent open, (lung surgery until second scalpel step). Surgery step needs preparation step, with drill. After that you can place item inside, or seal it with cautery to do other step instead.
-
-
+
20 February 2013
+
Chinsky updated:
+
+
Added new surgery: putting items inside people. After you use retractor to keep incision open, just click with any item to put it inside. But be wary, if you try to fit something too big, you might rip the veins. To remove items, use implant removal surgery.
+
Crowbar can be used as alternative to retractor.
+
Can now unload guns by clicking them in hand.
+
Fixed distance calculation in bullet missing chance computation, it was always assuming 1 or 0 tiles. Now distace REALLY matters when you shoot.
+
To add more FUN to previous thing, bullets missed to not disappear but keep going until they hit something else.
+
Compressed Matter and Explosive implants spawn properly now.
+
Tweaks to medical effects: removed itch caused by bandages. Chemical effects now have non-100 chance of appearing, the stronger medicine, the more probality it'll have side effects.
+
-
-
February 18th 2013
-
Cael Aislinn updated:
-
-
All RUST components are now buildable/orderable, with very high requirements (except for the TEGs). Emitters have replaced gyrotrons, for now.
-
Fixed up shield generators and made them buildable, with circuits obtainable through RnD. Hull shield gens project along space tiles adjacent to the hull (must be adjacent to a space tile to work).
-
-
+
18 February 2013
+
Cael Aislinn updated:
+
+
Security bots will now target hostile mobs, and vice versa.
+
Carp should actually emigrate now, instead of just immigrating then squatting around the outer hull.
+
Admins and moderators have been split up into separate 'who' verbs (adminwho and modwho respectively).
+
-
-
20/02/2013
-
Chinsky updated:
-
-
Added new surgery: putting items inside people. After you use retractor to keep incision open, just click with any item to put it inside. But be wary, if you try to fit something too big, you might rip the veins. To remove items, use implant removal surgery.
-
Crowbar can be used as alternative to retractor.
-
Can now unload guns by clicking them in hand.
-
Fixed distance calculation in bullet missing chance computation, it was always assuming 1 or 0 tiles. Now distace REALLY matters when you shoot.
-
To add more FUN to previous thing, bullets missed to not disappear but keep going until they hit something else.
-
Compressed Matter and Explosive implants spawn properly now.
-
Tweaks to medical effects: removed itch caused by bandages. Chemical effects now have non-100 chance of appearing, the stronger medicine, the more probality it'll have side effects.
-
-
+
14 February 2013
+
CIB updated:
+
+
Medical side-effects(patients are going to come back for secondary treatment)
+
NT loyalty setting(affects command reports and gives antags hints who might collaborate with them)
+
Simple animal balance fixes(They're slower now)
+
+
CaelAislinn updated:
+
+
Re-added old ion storm laws, re-added grid check event.
+
Added Rogue Drone and Vermin Infestation random events.
+
Added/fixed space vines random event.
+
Updates to the virus events.
+
Spider infestation and alien infestation events turned off by default.
+
Soghun, taj and skrell all have unique language text colours.
+
Moderators will no longer be listed in adminwho, instead use modwho.
+
+
Gamerofthegame updated:
+
+
Miscellaneous mapfixes.
+
-
-
February 18th 2013
-
Cael Aislinn updated:
-
-
Security bots will now target hostile mobs, and vice versa.
-
Carp should actually emigrate now, instead of just immigrating then squatting around the outer hull.
-
Admins and moderators have been split up into separate 'who' verbs (adminwho and modwho respectively).
-
-
+
13 February 2013
+
Erthilo updated:
+
+
Fixed SSD (logged-out) players not staying asleep.
+
Fixed set-pose verb and mice emotes having extra periods.
+
Fixed virus crate not appearing and breaking supply shuttle.
+
Fixed newcaster photos not being censored.
+
-
-
February 14th 2013
-
CIB updated:
-
-
Medical side-effects(patients are going to come back for secondary treatment)
-
NT loyalty setting(affects command reports and gives antags hints who might collaborate with them)
-
Simple animal balance fixes(They're slower now)
-
-
CaelAislinn updated:
-
-
Re-added old ion storm laws, re-added grid check event.
-
Added Rogue Drone and Vermin Infestation random events.
-
Added/fixed space vines random event.
-
Updates to the virus events.
-
Spider infestation and alien infestation events turned off by default.
-
Soghun, taj and skrell all have unique language text colours.
-
Moderators will no longer be listed in adminwho, instead use modwho.
-
+
31 January 2013
+
CIB updated:
+
+
Chilis and cold chilis no longer kill in small amounts
+
Chloral now again needs around 5 units to start killing somebody
If you get enough (6) blood drips on one tile, it'll turn into a blood puddle. Should make bleeding out more visible.
+
Security belt now able to hold taser, baton and tape roll.
+
Added alternative security uniform to Security wardrobes.
+
Ported Urist cult runes. Down with the crayon drawings! Example: http://dl.dropbox.com/u/26846767/images/SS13/255_symbols.PNG
+
Engineering tape now require engineer OR atmos access instead of both.
+
Implants now will react to EMP, possibly in !!FUN!! ways
+
+
GauHelldragon updated:
+
+
Servicebots now have RoboTray and Printing Pen. Robotray can be used to pick up and drop food/drinks. Printing pen can alternate between writing mode and rename paper mode by clicking it.
+
Farmbots. A new type of robot that weeds, waters and fertilizes. Use robot arm on water tank. Then use plant analyzer, mini-hoe, bucket and finally proximity sensor.
+
Chefs can clang their serving trays with a rolling pin. Just like a riot shield!
+
-
-
-
-
1/31/2013
-
CIB updated:
-
-
Chilis and cold chilis no longer kill in small amounts
-
Chloral now again needs around 5 units to start killing somebody
-
-
-
-
-
January 21st
-
Cael_Aislinn updated:
-
-
Satchels and ore boxes can now hold strange rocks.
-
Closets and crates can now be built out of 5 and 10 plasteel respectively.
-
Observers can become mice once more.
-
-
-
-
-
13/01/2013
-
Chinsky updated:
-
-
If you get enough (6) blood drips on one tile, it'll turn into a blood puddle. Should make bleeding out more visible.
-
Security belt now able to hold taser, baton and tape roll.
-
Added alternative security uniform to Security wardrobes.
-
Ported Urist cult runes. Down with the crayon drawings! Example: http://dl.dropbox.com/u/26846767/images/SS13/255_symbols.PNG
-
Engineering tape now require engineer OR atmos access instead of both.
-
Implants now will react to EMP, possibly in !!FUN!! ways
-
-
-
-
1/13/2013
-
GauHelldragon updated:
-
-
Servicebots now have RoboTray and Printing Pen. Robotray can be used to pick up and drop food/drinks. Printing pen can alternate between writing mode and rename paper mode by clicking it.
-
Farmbots. A new type of robot that weeds, waters and fertilizes. Use robot arm on water tank. Then use plant analyzer, mini-hoe, bucket and finally proximity sensor.
-
Chefs can clang their serving trays with a rolling pin. Just like a riot shield!
Implants: Explosvie implant, exploding when victim hears the codephrase you set.
-
Implants: Compressed Matter implat, scan item (making it disappear), inject yourself and recall that item on will!
-
Implant removal surgery, with !!FUN!! results if you mess up it.
-
Coats now have pockets again.
-
Bash people on tabetops. an windows, or with stools. Grab people to bash them on tables or windows (better grab for better hit on windows). Drag stool sprite on you to pick it up, click on it in hand to make it usual stool again.
-
Surgical caps, and new sprites for bloodbags and fixovein.
-
Now some surgery steps will bloody your hands, Full-body blood coat in case youy mess up spectacualry.
-
Ported some crates (Art, Surgery, Sterile equiplemnt).
-
Changed contraband crates. Posters moved to Art Crate, cigs and lipstick ot party crate. Now contraband crate has illegal booze and illicit drugs.
-
Finally got evac party lights
-
Now disfigurment,now it WILL happen when damage is bad enough.
-
Now if you speak in depressurized area (less than 10 kPa) only people next to you can hear you. Radios still work though.
-
-
-
-
-
-/tg/ station 13 Development Team
-
-
-
- Coders: TLE, NEO, Errorage, muskets, veryinky, Skie, Noise, Numbers, Agouri, Noka, Urist McDorf, Uhangi, Darem, Mport, rastaf0, Doohl, Superxpdude, Rockdtben, ConstantA, Petethegoat, Kor, Polymorph, Carn, Nodrak, Donkie
- Spriters: Agouri, Cheridan, Cruazy Guest, Deeaych, Deuryn, Matty406, Microwave, ShiftyEyesShady, Skie, Uhangi, Veyveyr, Petethegoat, Kor, Ricotez, Ausops, TankNut
- Sounds: Skie, Lasty/Vinyl
- Thanks to: CDK Station devs, GoonStation devs, the original SpaceStation developers and Invisty for the title image
-
-
-
-
-Daedalus Development Team
-
-
-
- Coders: DopeGhoti, Sunfall, ThVortex
- Artwork: Captain Hammer
- Spriters: ((TODO.))
- Sounds: Peter J, due, Erik Satie
- Thanks to: All the dev teams that came before: BS12, /tg/station13, the Goons, and the original SS13 folks.
-
Implants: Explosvie implant, exploding when victim hears the codephrase you set.
+
Implants: Compressed Matter implat, scan item (making it disappear), inject yourself and recall that item on will!
+
Implant removal surgery, with !!FUN!! results if you mess up it.
+
Coats now have pockets again.
+
Bash people on tabetops. an windows, or with stools. Grab people to bash them on tables or windows (better grab for better hit on windows). Drag stool sprite on you to pick it up, click on it in hand to make it usual stool again.
+
Surgical caps, and new sprites for bloodbags and fixovein.
+
Now some surgery steps will bloody your hands, Full-body blood coat in case youy mess up spectacualry.
+
Ported some crates (Art, Surgery, Sterile equiplemnt).
+
Changed contraband crates. Posters moved to Art Crate, cigs and lipstick ot party crate. Now contraband crate has illegal booze and illicit drugs.
+
Finally got evac party lights
+
Now disfigurment,now it WILL happen when damage is bad enough.
+
Now if you speak in depressurized area (less than 10 kPa) only people next to you can hear you. Radios still work though.
+
+
GoonStation 13 Development Team
- Coders: Stuntwaffle, Showtime, Pantaloons, Nannek, Keelin, Exadv1, hobnob, Justicefries, 0staf, sniperchance, AngriestIBM, BrianOBlivion
- Spriters: Supernorn, Haruhi, Stuntwaffle, Pantaloons, Rho, SynthOrange, I Said No
+ Coders: Stuntwaffle, Showtime, Pantaloons, Nannek, Keelin, Exadv1, hobnob, Justicefries, 0staf, sniperchance, AngriestIBM, BrianOBlivion
+ Spriters: Supernorn, Haruhi, Stuntwaffle, Pantaloons, Rho, SynthOrange, I Said No
+
diff --git a/html/changelog.js b/html/changelog.js
index 4146d0f094e..00db7fbc70b 100644
--- a/html/changelog.js
+++ b/html/changelog.js
@@ -1,87 +1,87 @@
-/*
-function dropdowns() {
- var divs = document.getElementsByTagName('div');
- var headers = new Array();
- var links = new Array();
- for(var i=0;i=0) {
- elem.className = elem.className.replace('visible','hidden');
- this.className = this.className.replace('open','closed');
- }
- else {
- elem.className = elem.className.replace('hidden','visible');
- this.className = this.className.replace('closed','open');
- }
- return false;
- }
- })(links[i]);
- }
- }
-}
-*/
-/*
-function filterchanges(type){
- var lists = document.getElementsByTagName('ul');
- for(var i in lists){
- if(lists[i].className && lists[i].className.search('changes')>=0) {
- for(var j in lists[i].childNodes){
- if(lists[i].childNodes[j].nodeType == 1){
- if(!type){
- lists[i].childNodes[j].style.display = 'block';
- }
- else if(lists[i].childNodes[j].className!=type) {
- lists[i].childNodes[j].style.display = 'none';
- }
- else {
- lists[i].childNodes[j].style.display = 'block';
- }
- }
- }
- }
- }
-}
-*/
-function dropdowns() {
- var drops = $('div.drop');
- var indrops = $('div.indrop');
- if(drops.length!=indrops.length){
- alert("Some coder fucked up with dropdowns");
- }
- drops.each(function(index){
- $(this).toggleClass('closed');
- $(indrops[index]).hide();
- $(this).click(function(){
- $(this).toggleClass('closed');
- $(this).toggleClass('open');
- $(indrops[index]).toggle();
- });
- });
-}
-
-function filterchanges(type){
- $('ul.changes li').each(function(){
- if(!type || $(this).hasClass(type)){
- $(this).show();
- }
- else {
- $(this).hide();
- }
- });
-}
-
-$(document).ready(function(){
- dropdowns();
+/*
+function dropdowns() {
+ var divs = document.getElementsByTagName('div');
+ var headers = new Array();
+ var links = new Array();
+ for(var i=0;i=0) {
+ elem.className = elem.className.replace('visible','hidden');
+ this.className = this.className.replace('open','closed');
+ }
+ else {
+ elem.className = elem.className.replace('hidden','visible');
+ this.className = this.className.replace('closed','open');
+ }
+ return false;
+ }
+ })(links[i]);
+ }
+ }
+}
+*/
+/*
+function filterchanges(type){
+ var lists = document.getElementsByTagName('ul');
+ for(var i in lists){
+ if(lists[i].className && lists[i].className.search('changes')>=0) {
+ for(var j in lists[i].childNodes){
+ if(lists[i].childNodes[j].nodeType == 1){
+ if(!type){
+ lists[i].childNodes[j].style.display = 'block';
+ }
+ else if(lists[i].childNodes[j].className!=type) {
+ lists[i].childNodes[j].style.display = 'none';
+ }
+ else {
+ lists[i].childNodes[j].style.display = 'block';
+ }
+ }
+ }
+ }
+ }
+}
+*/
+function dropdowns() {
+ var drops = $('div.drop');
+ var indrops = $('div.indrop');
+ if(drops.length!=indrops.length){
+ alert("Some coder fucked up with dropdowns");
+ }
+ drops.each(function(index){
+ $(this).toggleClass('closed');
+ $(indrops[index]).hide();
+ $(this).click(function(){
+ $(this).toggleClass('closed');
+ $(this).toggleClass('open');
+ $(indrops[index]).toggle();
+ });
+ });
+}
+
+function filterchanges(type){
+ $('ul.changes li').each(function(){
+ if(!type || $(this).hasClass(type)){
+ $(this).show();
+ }
+ else {
+ $(this).hide();
+ }
+ });
+}
+
+$(document).ready(function(){
+ dropdowns();
});
\ No newline at end of file
diff --git a/html/changelogs/.all_changelog.yml b/html/changelogs/.all_changelog.yml
new file mode 100644
index 00000000000..a0bf108e0e1
--- /dev/null
+++ b/html/changelogs/.all_changelog.yml
@@ -0,0 +1,1818 @@
+DO NOT EDIT THIS FILE BY HAND! AUTOMATICALLY GENERATED BY ss13_genchangelog.py.
+---
+2013-01-07:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'tgs': !!python/unicode 'Updated server to tgstation r5200 (November
+ 26th, 2012), see https://code.google.com/p/tgstation13/source/list
+ for tg''s changelog.'
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Implants: Explosvie implant, exploding
+ when victim hears the codephrase you set.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Implants: Compressed Matter implat,
+ scan item (making it disappear), inject yourself and recall that item on will!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Implant removal surgery, with !!FUN!!
+ results if you mess up it.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Coats now have pockets again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Bash people on tabetops. an windows,
+ or with stools. Grab people to bash them on tables or windows (better grab for
+ better hit on windows). Drag stool sprite on you to pick it up, click on it
+ in hand to make it usual stool again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Surgical caps, and new sprites for
+ bloodbags and fixovein.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Now some surgery steps will bloody
+ your hands, Full-body blood coat in case youy mess up spectacualry.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Ported some crates (Art, Surgery,
+ Sterile equiplemnt).'
+ - !!python/unicode 'tweak': !!python/unicode 'Changed contraband crates. Posters
+ moved to Art Crate, cigs and lipstick ot party crate. Now contraband crate has
+ illegal booze and illicit drugs.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Finally got evac party lights'
+ - !!python/unicode 'bugfix': !!python/unicode 'Now disfigurment,now it WILL happen
+ when damage is bad enough.'
+ - !!python/unicode 'experiment': !!python/unicode 'Now if you speak in depressurized
+ area (less than 10 kPa) only people next to you can hear you. Radios still work
+ though.'
+2013-01-13:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'tweak': !!python/unicode 'If you get enough (6) blood drips
+ on one tile, it''ll turn into a blood puddle. Should make bleeding out more
+ visible.'
+ - !!python/unicode 'tweak': !!python/unicode 'Security belt now able to hold taser,
+ baton and tape roll.'
+ - !!python/unicode 'tweak': !!python/unicode 'Added alternative security uniform
+ to Security wardrobes.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Ported Urist cult runes. Down with
+ the crayon drawings! Example: http://dl.dropbox.com/u/26846767/images/SS13/255_symbols.PNG'
+ - !!python/unicode 'bugfix': !!python/unicode 'Engineering tape now require engineer
+ OR atmos access instead of both.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Implants now will react to EMP, possibly
+ in !!FUN!! ways'
+ !!python/unicode 'GauHelldragon':
+ - !!python/unicode 'rscadd': !!python/unicode 'Servicebots now have RoboTray and
+ Printing Pen. Robotray can be used to pick up and drop food/drinks. Printing
+ pen can alternate between writing mode and rename paper mode by clicking it.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Farmbots. A new type of robot that
+ weeds, waters and fertilizes. Use robot arm on water tank. Then use plant analyzer,
+ mini-hoe, bucket and finally proximity sensor.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Chefs can clang their serving trays
+ with a rolling pin. Just like a riot shield!'
+2013-01-21:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'bugfix': !!python/unicode 'Satchels and ore boxes can now hold
+ strange rocks.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Closets and crates can now be built
+ out of 5 and 10 plasteel respectively.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Observers can become mice once more.'
+2013-01-23:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'tgs': !!python/unicode 'Updated server to tgstation r5200 (November
+ 26th, 2012), see https://code.google.com/p/tgstation13/source/list
+ for tg''s changelog.'
+2013-01-31:
+ !!python/unicode 'CIB':
+ - !!python/unicode 'bugfix': !!python/unicode 'Chilis and cold chilis no longer
+ kill in small amounts'
+ - !!python/unicode 'bugfix': !!python/unicode 'Chloral now again needs around 5
+ units to start killing somebody'
+2013-02-13:
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed SSD (logged-out) players not
+ staying asleep.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed set-pose verb and mice emotes
+ having extra periods.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed virus crate not appearing and
+ breaking supply shuttle.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed newcaster photos not being
+ censored.'
+2013-02-14:
+ !!python/unicode 'CIB':
+ - !!python/unicode 'rscadd': !!python/unicode 'Medical side-effects(patients are
+ going to come back for secondary treatment)'
+ - !!python/unicode 'rscadd': !!python/unicode 'NT loyalty setting(affects command
+ reports and gives antags hints who might collaborate with them)'
+ - !!python/unicode 'tweak': !!python/unicode 'Simple animal balance fixes(They''re
+ slower now)'
+ !!python/unicode 'CaelAislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Re-added old ion storm laws, re-added
+ grid check event.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added Rogue Drone and Vermin Infestation
+ random events.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added/fixed space vines random event.'
+ - !!python/unicode 'tweak': !!python/unicode 'Updates to the virus events.'
+ - !!python/unicode 'tweak': !!python/unicode 'Spider infestation and alien infestation
+ events turned off by default.'
+ - !!python/unicode 'tweak': !!python/unicode 'Soghun, taj and skrell all have unique
+ language text colours.'
+ - !!python/unicode 'tweak': !!python/unicode 'Moderators will no longer be listed
+ in adminwho, instead use modwho.'
+ !!python/unicode 'Gamerofthegame':
+ - !!python/unicode 'rscadd': !!python/unicode 'Miscellaneous mapfixes.'
+2013-02-18:
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Security bots will now target hostile
+ mobs, and vice versa.'
+ - !!python/unicode 'tweak': !!python/unicode 'Carp should actually emigrate now,
+ instead of just immigrating then squatting around the outer hull.'
+ - !!python/unicode 'tweak': !!python/unicode 'Admins and moderators have been split
+ up into separate ''who'' verbs (adminwho and modwho respectively).'
+2013-02-20:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added new surgery: putting items
+ inside people. After you use retractor to keep incision open, just click with
+ any item to put it inside. But be wary, if you try to fit something too big,
+ you might rip the veins. To remove items, use implant removal surgery.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Crowbar can be used as alternative
+ to retractor.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Can now unload guns by clicking them
+ in hand.'
+ - !!python/unicode 'tweak': !!python/unicode 'Fixed distance calculation in bullet
+ missing chance computation, it was always assuming 1 or 0 tiles. Now distace
+ REALLY matters when you shoot.'
+ - !!python/unicode 'rscadd': !!python/unicode 'To add more FUN to previous thing,
+ bullets missed to not disappear but keep going until they hit something else.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Compressed Matter and Explosive implants
+ spawn properly now.'
+ - !!python/unicode 'tweak': !!python/unicode 'Tweaks to medical effects: removed
+ itch caused by bandages. Chemical effects now have non-100 chance of appearing,
+ the stronger medicine, the more probality it''ll have side effects.'
+2013-02-22:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'tweak': !!python/unicode 'Change to body cavity surgery. Can
+ only put items in chest, groind and head. Max size for item - 3 (chest), 2 (groin),
+ 1 (head). For chest surgery ribs should be bent open, (lung surgery until second
+ scalpel step). Surgery step needs preparation step, with drill. After that you
+ can place item inside, or seal it with cautery to do other step instead.'
+2013-02-23:
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'wip': !!python/unicode 'RUST machinery components should now
+ be researchable (with high requirements) and orderable through QM (with high
+ cost).'
+ - !!python/unicode 'wip': !!python/unicode 'Shield machinery should now be researchable
+ (with high requirements) and orderable through QM (with high cost). This one
+ is reportedly buggy.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rogue vending machines should revert
+ back to normal at the end of the event.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New Unathi hair styles.'
+2013-02-25:
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'As well as building hull shield generators,
+ normal shield gens can now be built (see http://baystation12.net/forums/viewtopic.php?f=1&t;=6993).'
+ - !!python/unicode 'rscadd': !!python/unicode 'New random events: multiple new system
+ wide-events have been have been added to the newscaster feeds, some not quite
+ as respectable as others.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New random event: some lucky winners
+ will win the TC Daily Grand Slam Lotto, while others may be the target of malicious
+ hackers.'
+2013-02-27:
+ !!python/unicode 'Gamerofthegame':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added the (base gear) ERT preset
+ for the debug command.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Map fixes, Virology hole fixed. Atmospheric
+ fixes for mining and, to a less extent, the science outpost. (No, not cycling
+ airlocks)'
+ - !!python/unicode 'rscadd': !!python/unicode 'Fiddled with the ERT set up location
+ on Centcom. Radmins will now have a even easier time equiping a team of any
+ real pratical size, especially coupled with the above debug command.'
+2013-03-05:
+ !!python/unicode 'CIB':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added internal organs. They''re currently
+ all located in the chest. Use advanced scanner to detect damage. Use the same
+ surgery as for ruptured lungs to fix them.'
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'soundadd': !!python/unicode 'Set roundstart music to randomly
+ choose between space.ogg and traitor.ogg (see http://baystation12.net/forums/viewtopic.php?f=5&t;=6972)'
+ - !!python/unicode 'experiment': !!python/unicode 'All RUST components except for
+ TEGs (which generate the power) are now obtainable ingame, bored engineers should
+ get hold of them and setup an experimental reactor for testing purposes.'
+2013-03-06:
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Type 1 thermoelectric generators
+ and the associated binary circulators are now moveable (wrench to secure/unsecure)
+ and orderable via Quartermaster.'
+ - !!python/unicode 'wip': !!python/unicode 'code/maps/rust_test.dmm contains an
+ example setup for a functional RUST reactor. Maximum output is in the range
+ of 12 to 20MW (12 to 20 million watts).'
+ - !!python/unicode 'bugfix': !!python/unicode 'Removed double announcement for gridchecks,
+ reduced duration of gridchecks.'
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'You can now stab people with syringes
+ using the "harm" intent. This destroys the syringe and transfers a random percentage
+ of its contents into the target. Armor has a 50% chance of blocking the syringe.'
+2013-03-09:
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode "Beekeeping is now possible. Construct\
+ \ an apiary of out wood and embed it into a hydroponics tray, then get a queen\
+ \ bee and bottle of BeezEez from cargo bay. \n\t\tHives produce honey and honeycomb,\
+ \ but be wary if the bees start swarming."
+2013-03-11:
+ !!python/unicode 'CIB':
+ - !!python/unicode 'rscadd': !!python/unicode 'Cloning now requires you to put slabs
+ of meat into the cloning pod to replenish biomass.'
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'wip': !!python/unicode 'The xenoarchaeology update is here.
+ This includes a major content overhaul and a bunch of new features for xenoarchaeology.'
+ - !!python/unicode 'tweak': !!python/unicode 'Digsites (strange rock deposits) are
+ now much more nuanced and interesting, and a huge number of minor (non-artifact)
+ finds have been added.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Excavation is now a complex process
+ that involves digging into the rock to the right depth.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Chemical analysis is required for
+ safe excavation of the digsites, in order to determine how best to extract the
+ finds.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Anomalous artifacts have been overhauled
+ and many longstanding bugs with existing effects have been fixed - the anomaly
+ utiliser should now work much more often.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Numerous new artifact effects have
+ been added and some new artifact types can be dug up from the asteroid.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New tools and equipment have been
+ added, including normal and spaceworthy versions of the anomaly suits, excavation
+ tools and other neat gadgets.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Five books have been written by subject
+ matter experts from around the galaxy to help the crew of the Exodus come to
+ grips with this exacting new science (over 3000 words of tutorials!).'
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Sec HUDs now can see short versions
+ of sec records.on examine. Med HUDs do same for medical records, and can set
+ medical status of patient.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Damage to the head can now cause
+ brain damage.'
+2013-03-14:
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'rscadd': !!python/unicode 'Figured I should make one of these.
+ Syringestabbing now produces a broken syringe complete with fingerprints of
+ attacker and blood of a victim, so dispose your evidence carefully. Maximum
+ transfer amount per stab is lowered to 10.'
+2013-03-15:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Mapped a compact research base on
+ the mining asteroid, with multiple labs and testing rooms. It''s reachable through
+ a new (old) shuttle dock that leaves from the research wing on the main station.'
+2013-03-26:
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'bugfix': !!python/unicode 'Chemmaster now puts pills in pill
+ bottles (if one is inserted).'
+ - !!python/unicode 'tweak': !!python/unicode 'Stabbing someone with a syringe now
+ deals 3 damage instead of 7 because 7 is like, a crowbar punch.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Lizards can now join mid-round again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Chemicals in bloodstream will transfer
+ with blood now, so don''t get drunk before your blood donation. Viruses and
+ antibodies transfer through blood too.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Virology is working again.'
+2013-03-27:
+ !!python/unicode 'Asanadas':
+ - !!python/unicode 'tweak': !!python/unicode 'The Null Rod has recovered its de-culting
+ ability, for balance reasons. Metagaming with it is a big no-no!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Holy Water as a liquid is able to
+ de-cult. Less effective, but less bloody. May be changed over the course of
+ time for balance.'
+2013-04-04:
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed ZAS'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed Fire'
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'bugfix': !!python/unicode 'Blood type is now saved in character
+ creation menu, no need to edit it manually every round.'
+2013-04-09:
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fire Issues (Firedoors, Flamethrowers,
+ Incendiary Grenades) fixed.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed a bad line of code that was
+ preventing autoignition of flammable gas mixes.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Volatile fuel is burned up after
+ a point.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Partial-tile firedoors removed. This
+ is due to ZAS breaking when interacting with them.'
+2013-04-11:
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'experiment': !!python/unicode 'Fire has been reworked.'
+ - !!python/unicode 'experiment': !!python/unicode 'In-game variable editor is both
+ readded and expanded with fire controlling capability.'
+2013-04-17:
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'experiment': !!python/unicode 'ZAS is now more deadly, as per
+ decision by administrative team. May be tweaked, but currently AIRFLOW is the
+ biggest griefer.'
+ - !!python/unicode 'experiment': !!python/unicode 'World startup optimized, many
+ functions now delayed until a player joins the server. (Reduces server boot
+ time significantly)'
+ - !!python/unicode 'tweak': !!python/unicode 'Zones will now equalize air more rapidly.'
+ - !!python/unicode 'bugfix': !!python/unicode 'ZAS now respects active magboots
+ when airflow occurs.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Airflow will no longer throw you
+ into doors and open them.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Race condition in zone construction
+ has been fixed, so zones connect properly at round start.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Plasma effects readded.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed runtime involving away mission.'
+2013-04-24:
+ !!python/unicode 'Jediluke69':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added 5 new drinks (Kira Special,
+ Lemonade, Brown Star, Milkshakes, Rewriter)'
+ - !!python/unicode 'tweak': !!python/unicode 'Nanopaste now heals about half of
+ what it used to'
+ - !!python/unicode 'tweak': !!python/unicode 'Ballistic crates should now come with
+ shotguns loaded with actual shells no more beanbags'
+ - !!python/unicode 'bugfix': !!python/unicode 'Iced tea no longer makes a glass
+ of .what?'
+ !!python/unicode 'NerdyBoy1104':
+ - !!python/unicode 'rscadd': !!python/unicode 'New Botany additions: Rice and Plastellium.
+ New sheet material: Plastic.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Plastellium is refined into plastic
+ by first grinding the produce to get plasticide. 20 plasticide + 10 polytrinic
+ acid makes 10 sheets of plastic which can be used to make crates, forks, spoons,
+ knives, ashtrays or plastic bags from.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Rice seeds grows into rice stalks
+ that you grind to get rice. 10 Rice + 5 Water makes boiled rice, 10 rice + 5
+ milk makes rice pudding, 10 rice + 5 universal enzyme (in beaker) makes Sake.'
+ !!python/unicode 'faux':
+ - !!python/unicode 'imageadd': !!python/unicode 'Mixed Wardrobe Closet now has colored
+ shoes and plaid skirts.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Dress uniforms added to the Captain,
+ RD, and HoP wardrobe closets. A uniform jacket has also been added to the Captain''s
+ closet. HoS'' hat has been re-added to their closet. I do not love the CMO and
+ CE enough to give them anything.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Atheletic closet now has five different
+ swimsuits *for the ladies* in them. If you are a guy, be prepared to be yelled
+ at if you run around like a moron in one of these. Same goes for ladies who
+ run around in shorts with their titties swaying in the space winds.'
+ - !!python/unicode 'imageadd': !!python/unicode 'A set of dispatcher uniforms will
+ spawn in the security closet. These are for playtesting the dispatcher role.'
+ - !!python/unicode 'imageadd': !!python/unicode 'New suit spawns in the laundry
+ room. It''s for geezer''s only. You''re welcome, Book.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Nurse outfit variant, orderly uniform,
+ and first responder jacket will now spawn in the medical wardrobe closet.'
+ - !!python/unicode 'imageadd': !!python/unicode 'A white wedding dress will spawn
+ in the chaplain''s closet. There are also several dresses currently only adminspawnable.
+ Admins: Look either under "bride" or "dress." The bride one leads to the colored
+ wedding dresses, and there are some other kinds of dresses under dress.'
+ - !!python/unicode 'tweak': !!python/unicode 'No more luchador masks or boxing gloves
+ or boxing ring. You guys have a swimming pool now, dip in and enjoy it.'
+ - !!python/unicode 'tweak': !!python/unicode 'he meeting hall has been replaced
+ with an awkwardly placed security office meant for prisoner processing.'
+ - !!python/unicode 'tweak': !!python/unicode 'Added a couple more welding goggles
+ to engineering since you guys liked those a lot.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Flasks spawn behind the bar. Only
+ three. Don''t fight over them. I don''t know how to add them to the bar vending
+ machine otherwise I would have done that instead. Detective, you have your own
+ flask in your office, it''s underneath the cigarettes on your desk.'
+ - !!python/unicode 'tweak': !!python/unicode 'Added two canes to the medical storage,
+ for people who have leg injuries and can''t walk good and stuff. I do not want
+ to see doctors pretending to be House. These are for patients. Do not make me
+ delete this addition and declare you guys not being able to have nice things.'
+ - !!python/unicode 'tweak': !!python/unicode 'Secondary entance to EVA now directly
+ leads into the medbay hardsuit section. Sorry for any inconviences this will
+ cause. The CMO can now fetch the hardsuits whenever they want.'
+ - !!python/unicode 'tweak': !!python/unicode 'Secondary security hardsuit has been
+ added to the armory. Security members please stop stealing engineer''s hardsuits
+ when you guys want to pair up for space travel.'
+ - !!python/unicode 'tweak': !!python/unicode 'Firelocks have been moved around in
+ the main hallways to form really ghetto versions of airlocks.'
+ - !!python/unicode 'tweak': !!python/unicode 'Violin spawns in theatre storage now.
+ I didn''t put the piano there though, that was someone else.'
+ - !!python/unicode 'tweak': !!python/unicode 'Psych office in medbay has been made
+ better looking.'
+2013-05-14:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'experiment': !!python/unicode 'Depth scanners can now be used
+ to determine what material archaeological deposits are made of, meaning lab
+ analysis is no longer required.'
+ - !!python/unicode 'tweak': !!python/unicode 'Some useability issues with xenoarchaeology
+ tools have been resolved, and the transit pods cycle automatically now.'
+2013-05-15:
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added telescopic
+ batons to HoS''s and captain''s lockers. These are quite robust and easily
+ concealable.'
+2013-05-21:
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'experiment': !!python/unicode 'ZAS will now speed air movement
+ into/out of a zone when unsimulated tiles (e.g. space) are involved, in relation
+ to the number of tiles.'
+ - !!python/unicode 'experiment': !!python/unicode 'Portable Canisters will now automatically
+ connect to any portable connecter beneath them on map load.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Bug involving mis-mapped disposal
+ junction fixed'
+ - !!python/unicode 'bugfix': !!python/unicode 'Air alarms now work for atmos techs
+ (whoops!)'
+ - !!python/unicode 'bugfix': !!python/unicode 'The Master Controller now properly
+ stops atmos when it runtimes.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Backpacks can no longer be contaminated'
+ - !!python/unicode 'tweak': !!python/unicode 'ZAS no longer logs air statistics.'
+ - !!python/unicode 'tweak': !!python/unicode 'ZAS now rebuilds as soon as it detects
+ a semi-complex change in geometry. (It was doing this already, but in a convoluted
+ way which was actually less efficient)'
+ - !!python/unicode 'tweak': !!python/unicode 'General code cleanup/commenting of
+ ZAS'
+ - !!python/unicode 'tweak': !!python/unicode 'Jungle now initializes after the random
+ Z-level loads and atmos initializes.'
+2013-05-25:
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes alien races appearing an unknown
+ when speaking their language.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes alien races losing their language
+ when cloned.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes UI getting randomly reset when
+ trying to change it in Genetics Scanners.'
+2013-05-26:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Tentacles! Now clone damage will
+ make you horribly malformed like examine text says.'
+ !!python/unicode 'Meyar':
+ - !!python/unicode 'rscadd': !!python/unicode 'The syndicate shuttle now has a cycling
+ airlock during Nuke rounds.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Restored the ability for the syndicate
+ Agent ID to change the name on the card (reforge it) more than once.'
+ - !!python/unicode 'rscadd': !!python/unicode 'ERT Radio now functional again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Research blast doors now actually
+ lock down the entirety of station-side Research. '
+ - !!python/unicode 'rscadd': !!python/unicode 'Added lock down buttons to the wardens
+ office. '
+ - !!python/unicode 'rscadd': !!python/unicode 'The randomized barsign has made a
+ return. '
+ - !!python/unicode 'rscadd': !!python/unicode 'Syndicate Agent ID''s external airlock
+ access restored.'
+ !!python/unicode 'VitrescentTortoise':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added a third option for not getting
+ any job preferences. It allows you to return to the lobby instead of joining.'
+2013-05-28:
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes everyone being able to understand
+ alien languages. HERE IS YOUR TOWER OF BABEL'
+ !!python/unicode 'VitrescentTortoise':
+ - !!python/unicode 'bugfix': !!python/unicode 'Wizard''s forcewall now works.'
+2013-05-30:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Meteor showers actually spawn meteors
+ now.'
+ - !!python/unicode 'tweak': !!python/unicode 'Engineering tape fits into toolbelt
+ and can be placed on doors.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Pill bottles can hold paper.'
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'tweak': !!python/unicode 'Pill bottle capacity increased to
+ 14 items.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed Lamarr (it now spawns properly)'
+ !!python/unicode 'proliberate':
+ - !!python/unicode 'rscadd': !!python/unicode 'Station time is now displayed in
+ the status tab for new players and AIs.'
+2013-05-31:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Portable canisters now properly connect
+ to ports beneath them on map load.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed unfastening gas meters.'
+2013-06-01:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Bloody footprints! Now stepping in
+ the puddle will dirty your shoes/feet and make you leave bloody footprints for
+ a bit.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Blood now dries up after some time.
+ Puddles take ~30 minutes, small things 5 minutes.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Untreated wounds now heal. No more
+ toe stubs spamming you with pain messages for the rest of the shift.'
+ - !!python/unicode 'experiment': !!python/unicode 'On the other side, everything
+ is healed slowly. Maximum you cna squeeze out of first aid is 0.5 health per
+ tick per organ. Lying down makes it faster too, by 1.5x factor.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Lids! Click beaker/bottle in hand
+ to put them on/off. Prevent spilling'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added ''hailer'' to security lockers.
+ If used in hand, says "Halt! Security!". For those who can''t run and type.'
+2013-06-05:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Load bearing equipment - webbings
+ and vests for engineers and sec. Attach to jumpsuit, use ''Look in storage''
+ verb (object tab) to open.'
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'rscadd': !!python/unicode 'Exosuits now can open firelocks by
+ walking into them.'
+2013-06-06:
+ !!python/unicode 'Asanadas':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added a whimsical suit to the head
+ of personnel''s secret clothing locker.'
+ !!python/unicode 'Meyar':
+ - !!python/unicode 'bugfix': !!python/unicode 'Disposal''s mail routing fixed. Missing
+ pipes replaced.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Chemistry is once again a part of
+ the disposals delivery circuit. '
+ - !!python/unicode 'bugfix': !!python/unicode 'Added missing sorting junctions to
+ Security and HoS office.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed a duplicate sorting junction.'
+2013-06-09:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Emagged supply console can order
+ SpecOp crates again.'
+2013-06-11:
+ !!python/unicode 'Meyar':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes a security door with a firedoor
+ ontop of it.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed a typo relating to the admin
+ Select Equipment Verb. (It''s RESPONSE team not RESCUE team)'
+ - !!python/unicode 'rscadd': !!python/unicode 'ERT are now automated, from their
+ spawn to their shuttle. Admin intervention no longer required! (Getting to the
+ mechs still requires admin permission generally)'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added flashlights to compensate for
+ the weakened PDA lights'
+ - !!python/unicode 'tweak': !!python/unicode 'ERT Uniforms updated to be in line
+ with Centcom uniforms. No more turtlenecks, no sir. '
+2013-06-12:
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added pneumatic cannon and harpoons.'
+ - !!python/unicode 'experiment': !!python/unicode 'Added embedded projectiles. Bullets
+ and thrown weapons may stick in targets. Throwing them by hand won''t make them
+ stick, firing them from a cannon might. Implant removal surgery will get rid
+ of shrapnel and stuck items.'
+2013-06-13:
+ !!python/unicode 'Kilakk':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added the Xenobiologist job. Has
+ access to the research hallway and to xenobiology.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed Xenobiology access from Scientists.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed the Xenobiologist alternate
+ title from Scientists.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added "Xenoarchaeology" to the RD,
+ Scientists, and to the ID computer.'
+ - !!python/unicode 'tweak': !!python/unicode 'Changed the Research Outpost doors
+ to use "Xenoarchaeology" access.'
+2013-06-18:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed some bugs in windoor construction.'
+ - !!python/unicode 'tweak': !!python/unicode 'Secure windoors are made with rods
+ again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Windoors drop their electronics when
+ broken. Emagged windoors can have theirs removed by crowbar.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Airlock electronics can be configured
+ to make door open for any single access on it instead of all of them.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Cyborgs can preview their icons before
+ choosing.'
+2013-06-21:
+ !!python/unicode 'Jupotter':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fix the robotiscist preview in the
+ char setupe screen'
+2013-06-22:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'tweak': !!python/unicode 'The xenoarchaeology depth scanner
+ will now tell you what energy field is required to safely extract a find.'
+ - !!python/unicode 'tweak': !!python/unicode 'Excavation picks will now dig faster,
+ and xenoarchaeology as a whole should be easier to do.'
+2013-06-23:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'rscadd': !!python/unicode 'Airlocks of various models can be
+ constructed again.'
+ !!python/unicode 'faux':
+ - !!python/unicode 'experiment': !!python/unicode 'There has been a complete medbay
+ renovation spearheaded by Vetinarix. http://baystation12.net/forums/viewtopic.php?f=20&t;=7847
+ <-- Please put any commentary good or bad, here.'
+ - !!python/unicode 'tweak': !!python/unicode 'Some maintenance doors within RnD
+ and Medbay have had their accesses changed. Maintenance doors in the joint areas
+ (leading to the research shuttle, virology, and xenobiology) are now zero access.
+ Which means anyone in those joints can enter the maintenance tunnels. This was
+ done to add additional evacuation locations during radiation storms. Additional
+ maintenance doors were added to the tunnels in these areas to prevent docs and
+ scientists from running about.'
+ - !!python/unicode 'tweak': !!python/unicode 'Starboard emergency storage isn''t
+ gone now, it''s simply located in the escape wing.'
+ - !!python/unicode 'experiment': !!python/unicode 'An engineering training room
+ has been added to engineering. This location was previously where surgery was
+ located. If you are new to engineering or need to brush up on your skills, please
+ use this area for testing.'
+2013-06-26:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Autopsy scanner properly displays
+ time of wound infliction and death.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Autopsy scanner properly displays
+ wounds by projectile weapons.'
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'bugfix': !!python/unicode 'One-antag rounds (like wizard/ninja)
+ no longer end automatically upon death'
+ - !!python/unicode 'wip': !!python/unicode 'Space ninja has been implemented as
+ a voteable gamemode'
+ - !!python/unicode 'rscadd': !!python/unicode 'Space ninja spawn landmarks have
+ been implemented (but not yet placed on the map), still spawn at carps-pawns
+ instead. (The code will warn you about this and ask you to report it, it''s
+ a known issue.)'
+ - !!python/unicode 'rscadd': !!python/unicode 'Five new space ninja directives have
+ been added, old directives have been reworded to be less harsh'
+ - !!python/unicode 'wip': !!python/unicode 'Space ninjas have been given their own
+ list as antagonists, and are no longer bundled up with traitors'
+ - !!python/unicode 'bugfix': !!python/unicode 'Space ninjas with a "steal a functional
+ AI" objective will now succeed by downloading one into their suits'
+ - !!python/unicode 'tweak': !!python/unicode 'Space ninja suits'' exploding on death
+ has been nerfed, so as not to cause breaches'
+ - !!python/unicode 'rscadd': !!python/unicode 'A few space ninja titles/names have
+ been added and removed to be slightly more believable'
+ - !!python/unicode 'bugfix': !!python/unicode 'The antagonist selector no longer
+ chooses jobbanned players when it runs out of willing options'
+2013-06-27:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'ID cards properly setup bloodtype,
+ DNA and fingerprints again.'
+2013-06-28:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'rscadd': !!python/unicode 'AIs are now able to examine what
+ they see.'
+2013-07-03:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'rscadd': !!python/unicode 'Security and medical cyborgs can
+ use their HUDs to access records.'
+2013-07-05:
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'rscadd': !!python/unicode 'Pulse! Humans now have hearbeat rate,
+ which can be measured by right-clicking someone - Check pulse or by health analyzer.
+ Medical machinery also has heartbeat monitors. Certain meds and conditions can
+ influence it.'
+2013-07-06:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Humans now can be infected with more
+ than one virus at once.'
+ - !!python/unicode 'rscadd': !!python/unicode 'All analyzed viruses are put into
+ virus DB. You can view it and edit their name and description on medical record
+ consoles.'
+ - !!python/unicode 'tweak': !!python/unicode 'Only known viruses (ones in DB) will
+ be detected by the machinery and HUDs. '
+ - !!python/unicode 'rscadd': !!python/unicode 'Viruses cause fever, body temperature
+ rising the more stage is.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Humans'' body temperature does not
+ drift towards room one unless there''s big difference in them.'
+ - !!python/unicode 'tweak': !!python/unicode 'Virus incubators now can transmit
+ viuses from dishes to blood sample.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New machine - centrifuge. It can
+ isolate antibodies or viruses (spawning virus dish) from a blood sample in vials.
+ Accepts vials only.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Fancy vial boxes in virology, one
+ of them is locked by ID with MD access.'
+ - !!python/unicode 'tweak': !!python/unicode 'Engineered viruses are now ariborne
+ too.'
+2013-07-11:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Gun delays. All guns now have delays
+ between shots. Most have less than second, lasercannons and pulse rifles have
+ around 2 seconds delay. Automatics have zero, click-speed.'
+2013-07-26:
+ !!python/unicode 'Kilakk':
+ - !!python/unicode 'bugfix': !!python/unicode 'Brig cell timers will no longer start
+ counting down automatically.'
+ - !!python/unicode 'tweak': !!python/unicode 'Separated the actual countdown timer
+ from the timer controls. Pressing "Set" while the timer is counting down will
+ reset the countdown timer to the time selected.'
+2013-07-28:
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'rscadd': !!python/unicode 'Camera console circuits can be adjusted
+ for different networks.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Nuclear operatives and ERT members
+ have built-in cameras in their helmets. Activate helmet to initialize it.'
+2013-07-30:
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'EFTPOS and ATM machines should now
+ connect to databases.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Gravitational Catapults can now be
+ removed from mechs.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Ghost manifest rune paper naming
+ now works correctly.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fix for newscaster special characters.
+ Still not recommended.'
+ !!python/unicode 'Kilakk':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added colored department radio channels.'
+2013-08-01:
+ !!python/unicode 'Asanadas':
+ - !!python/unicode 'tweak': !!python/unicode 'The Null Rod has recovered its de-culting
+ ability, for balance reasons. Metagaming with it is a big no-no!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Holy Water as a liquid is able to
+ de-cult. Less effective, but less bloody. May be changed over the course of
+ time for balance.'
+ !!python/unicode 'CIB':
+ - !!python/unicode 'bugfix': !!python/unicode 'Chilis and cold chilis no longer
+ kill in small amounts'
+ - !!python/unicode 'bugfix': !!python/unicode 'Chloral now again needs around 5
+ units to start killing somebody'
+ !!python/unicode 'Cael Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Security bots will now target hostile
+ mobs, and vice versa.'
+ - !!python/unicode 'tweak': !!python/unicode 'Carp should actually emigrate now,
+ instead of just immigrating then squatting around the outer hull.'
+ - !!python/unicode 'tweak': !!python/unicode 'Admins and moderators have been split
+ up into separate ''who'' verbs (adminwho and modwho respectively).'
+ !!python/unicode 'CaelAislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Re-added old ion storm laws, re-added
+ grid check event.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added Rogue Drone and Vermin Infestation
+ random events.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added/fixed space vines random event.'
+ - !!python/unicode 'tweak': !!python/unicode 'Updates to the virus events.'
+ - !!python/unicode 'tweak': !!python/unicode 'Spider infestation and alien infestation
+ events turned off by default.'
+ - !!python/unicode 'tweak': !!python/unicode 'Soghun, taj and skrell all have unique
+ language text colours.'
+ - !!python/unicode 'tweak': !!python/unicode 'Moderators will no longer be listed
+ in adminwho, instead use modwho.'
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'tgs': !!python/unicode 'Updated server to tgstation r5200 (November
+ 26th, 2012), see https://code.google.com/p/tgstation13/source/list
+ for tg''s changelog.'
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Old new medical features:'
+ - !!python/unicode 'rscadd': !!python/unicode 'Autoinjectors! They come preloaded
+ with 5u of inapro, can be used instantly, and are one-use. You can replace chems
+ inside using a syringe. Box of them is added to Medicine closet and medical
+ supplies crate.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Splints! Target broken liimb and
+ click on person to apply. Can be taken off in inventory menu, like handcuffs.
+ Splinted limbs have less negative effects.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Advanced medikit! Red and mean, all
+ doctors spawn with one. Contains better stuff - advanced versions of bandaids
+ and aloe heal 12 damage on the first use.'
+ - !!python/unicode 'tweak': !!python/unicode 'Wounds with damage above 50 won''t
+ heal by themselves even if bandaged/salved. Would have to seek advanced medical
+ attention for those.'
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed SSD (logged-out) players not
+ staying asleep.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed set-pose verb and mice emotes
+ having extra periods.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed virus crate not appearing and
+ breaking supply shuttle.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed newcaster photos not being
+ censored.'
+ !!python/unicode 'Gamerofthegame':
+ - !!python/unicode 'rscadd': !!python/unicode 'Miscellaneous mapfixes.'
+ !!python/unicode 'GauHelldragon':
+ - !!python/unicode 'rscadd': !!python/unicode 'Servicebots now have RoboTray and
+ Printing Pen. Robotray can be used to pick up and drop food/drinks. Printing
+ pen can alternate between writing mode and rename paper mode by clicking it.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Farmbots. A new type of robot that
+ weeds, waters and fertilizes. Use robot arm on water tank. Then use plant analyzer,
+ mini-hoe, bucket and finally proximity sensor.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Chefs can clang their serving trays
+ with a rolling pin. Just like a riot shield!'
+ !!python/unicode 'Jediluke69':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added 5 new drinks (Kira Special,
+ Lemonade, Brown Star, Milkshakes, Rewriter)'
+ - !!python/unicode 'tweak': !!python/unicode 'Nanopaste now heals about half of
+ what it used to'
+ - !!python/unicode 'tweak': !!python/unicode 'Ballistic crates should now come with
+ shotguns loaded with actual shells no more beanbags'
+ - !!python/unicode 'bugfix': !!python/unicode 'Iced tea no longer makes a glass
+ of .what?'
+ !!python/unicode 'Jupotter':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fix the robotiscist preview in the
+ char setupe screen'
+ !!python/unicode 'Kilakk':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added the Xenobiologist job. Has
+ access to the research hallway and to xenobiology.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed Xenobiology access from Scientists.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed the Xenobiologist alternate
+ title from Scientists.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added "Xenoarchaeology" to the RD,
+ Scientists, and to the ID computer.'
+ - !!python/unicode 'tweak': !!python/unicode 'Changed the Research Outpost doors
+ to use "Xenoarchaeology" access.'
+ !!python/unicode 'Meyar':
+ - !!python/unicode 'rscadd': !!python/unicode 'The syndicate shuttle now has a cycling
+ airlock during Nuke rounds.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Restored the ability for the syndicate
+ Agent ID to change the name on the card (reforge it) more than once.'
+ - !!python/unicode 'rscadd': !!python/unicode 'ERT Radio now functional again.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Research blast doors now actually
+ lock down the entirety of station-side Research. '
+ - !!python/unicode 'rscadd': !!python/unicode 'Added lock down buttons to the wardens
+ office. '
+ - !!python/unicode 'rscadd': !!python/unicode 'The randomized barsign has made a
+ return. '
+ - !!python/unicode 'rscadd': !!python/unicode 'Syndicate Agent ID''s external airlock
+ access restored.'
+ !!python/unicode 'NerdyBoy1104':
+ - !!python/unicode 'rscadd': !!python/unicode 'New Botany additions: Rice and Plastellium.
+ New sheet material: Plastic.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Plastellium is refined into plastic
+ by first grinding the produce to get plasticide. 20 plasticide + 10 polytrinic
+ acid makes 10 sheets of plastic which can be used to make crates, forks, spoons,
+ knives, ashtrays or plastic bags from.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Rice seeds grows into rice stalks
+ that you grind to get rice. 10 Rice + 5 Water makes boiled rice, 10 rice + 5
+ milk makes rice pudding, 10 rice + 5 universal enzyme (in beaker) makes Sake.'
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'You can now stab people with syringes
+ using the "harm" intent. This destroys the syringe and transfers a random percentage
+ of its contents into the target. Armor has a 50% chance of blocking the syringe.'
+ !!python/unicode 'Segrain':
+ - !!python/unicode 'bugfix': !!python/unicode 'Meteor showers actually spawn meteors
+ now.'
+ - !!python/unicode 'tweak': !!python/unicode 'Engineering tape fits into toolbelt
+ and can be placed on doors.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Pill bottles can hold paper.'
+ !!python/unicode 'SkyMarshal':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed ZAS'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed Fire'
+ !!python/unicode 'Spamcat':
+ - !!python/unicode 'rscadd': !!python/unicode 'Figured I should make one of these.
+ Syringestabbing now produces a broken syringe complete with fingerprints of
+ attacker and blood of a victim, so dispose your evidence carefully. Maximum
+ transfer amount per stab is lowered to 10.'
+ !!python/unicode 'VitrescentTortoise':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added a third option for not getting
+ any job preferences. It allows you to return to the lobby instead of joining.'
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'bugfix': !!python/unicode 'One-antag rounds (like wizard/ninja)
+ no longer end automatically upon death'
+ - !!python/unicode 'wip': !!python/unicode 'Space ninja has been implemented as
+ a voteable gamemode'
+ - !!python/unicode 'rscadd': !!python/unicode 'Space ninja spawn landmarks have
+ been implemented (but not yet placed on the map), still spawn at carps-pawns
+ instead. (The code will warn you about this and ask you to report it, it''s
+ a known issue.)'
+ - !!python/unicode 'rscadd': !!python/unicode 'Five new space ninja directives have
+ been added, old directives have been reworded to be less harsh'
+ - !!python/unicode 'wip': !!python/unicode 'Space ninjas have been given their own
+ list as antagonists, and are no longer bundled up with traitors'
+ - !!python/unicode 'bugfix': !!python/unicode 'Space ninjas with a "steal a functional
+ AI" objective will now succeed by downloading one into their suits'
+ - !!python/unicode 'tweak': !!python/unicode 'Space ninja suits'' exploding on death
+ has been nerfed, so as not to cause breaches'
+ - !!python/unicode 'rscadd': !!python/unicode 'A few space ninja titles/names have
+ been added and removed to be slightly more believable'
+ - !!python/unicode 'bugfix': !!python/unicode 'The antagonist selector no longer
+ chooses jobbanned players when it runs out of willing options'
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added pneumatic cannon and harpoons.'
+ - !!python/unicode 'experiment': !!python/unicode 'Added embedded projectiles. Bullets
+ and thrown weapons may stick in targets. Throwing them by hand won''t make them
+ stick, firing them from a cannon might. Implant removal surgery will get rid
+ of shrapnel and stuck items.'
+ !!python/unicode 'faux':
+ - !!python/unicode 'imageadd': !!python/unicode 'Mixed Wardrobe Closet now has colored
+ shoes and plaid skirts.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Dress uniforms added to the Captain,
+ RD, and HoP wardrobe closets. A uniform jacket has also been added to the Captain''s
+ closet. HoS'' hat has been re-added to their closet. I do not love the CMO and
+ CE enough to give them anything.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Atheletic closet now has five different
+ swimsuits *for the ladies* in them. If you are a guy, be prepared to be yelled
+ at if you run around like a moron in one of these. Same goes for ladies who
+ run around in shorts with their titties swaying in the space winds.'
+ - !!python/unicode 'imageadd': !!python/unicode 'A set of dispatcher uniforms will
+ spawn in the security closet. These are for playtesting the dispatcher role.'
+ - !!python/unicode 'imageadd': !!python/unicode 'New suit spawns in the laundry
+ room. It''s for geezer''s only. You''re welcome, Book.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Nurse outfit variant, orderly uniform,
+ and first responder jacket will now spawn in the medical wardrobe closet.'
+ - !!python/unicode 'imageadd': !!python/unicode 'A white wedding dress will spawn
+ in the chaplain''s closet. There are also several dresses currently only adminspawnable.
+ Admins: Look either under "bride" or "dress." The bride one leads to the colored
+ wedding dresses, and there are some other kinds of dresses under dress.'
+ - !!python/unicode 'tweak': !!python/unicode 'No more luchador masks or boxing gloves
+ or boxing ring. You guys have a swimming pool now, dip in and enjoy it.'
+ - !!python/unicode 'tweak': !!python/unicode 'he meeting hall has been replaced
+ with an awkwardly placed security office meant for prisoner processing.'
+ - !!python/unicode 'tweak': !!python/unicode 'Added a couple more welding goggles
+ to engineering since you guys liked those a lot.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Flasks spawn behind the bar. Only
+ three. Don''t fight over them. I don''t know how to add them to the bar vending
+ machine otherwise I would have done that instead. Detective, you have your own
+ flask in your office, it''s underneath the cigarettes on your desk.'
+ - !!python/unicode 'tweak': !!python/unicode 'Added two canes to the medical storage,
+ for people who have leg injuries and can''t walk good and stuff. I do not want
+ to see doctors pretending to be House. These are for patients. Do not make me
+ delete this addition and declare you guys not being able to have nice things.'
+ - !!python/unicode 'tweak': !!python/unicode 'Secondary entance to EVA now directly
+ leads into the medbay hardsuit section. Sorry for any inconviences this will
+ cause. The CMO can now fetch the hardsuits whenever they want.'
+ - !!python/unicode 'tweak': !!python/unicode 'Secondary security hardsuit has been
+ added to the armory. Security members please stop stealing engineer''s hardsuits
+ when you guys want to pair up for space travel.'
+ - !!python/unicode 'tweak': !!python/unicode 'Firelocks have been moved around in
+ the main hallways to form really ghetto versions of airlocks.'
+ - !!python/unicode 'tweak': !!python/unicode 'Violin spawns in theatre storage now.
+ I didn''t put the piano there though, that was someone else.'
+ - !!python/unicode 'tweak': !!python/unicode 'Psych office in medbay has been made
+ better looking.'
+ !!python/unicode 'proliberate':
+ - !!python/unicode 'rscadd': !!python/unicode 'Station time is now displayed in
+ the status tab for new players and AIs.'
+2013-08-04:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Health HUD indicator replaced with
+ Pain indicator. Now health indicator shows pain level instead of actual vitals
+ level. Some types of damage contribute more to pain, some less, usually feeling
+ worse than they really are.'
+2013-08-08:
+ !!python/unicode 'Erthilo':
+ - !!python/unicode 'bugfix': !!python/unicode 'Raise Dead rune now properly heals
+ and revives dead corpse.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Admin-only rejuvenate verb now heals
+ all organs, limbs, and diseases.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Cyborg sprites now correctly reset
+ with reset boards. This means cyborg appearances can now be changed without
+ admin intervention.'
+2013-09-18:
+ !!python/unicode 'Kilakk':
+ - !!python/unicode 'rscadd': !!python/unicode 'Fax machines! The Captain and IA
+ agents can use the fax machine to send properly formatted messages to Central
+ Command.'
+ - !!python/unicode 'imageadd': !!python/unicode 'Gave the fax machine a fancy animated
+ sprite. Thanks Cajoes!'
+2013-09-24:
+ !!python/unicode 'Snapshot':
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed hidden vote counts.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed hiding of vote results.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed OOC muting during votes.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Crew transfers are no longer callable
+ during Red and Delta alert.'
+ - !!python/unicode 'wip': !!python/unicode 'Started work on Auto transfer framework.'
+2013-10-06:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Return of dreaded side effects. They
+ now manifest well after their cause disappears, so curing them should be possible
+ without them reappearing immediately. They also lost last stage damaging effects.'
+2013-10-29:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'Xenoarchaeology''s chemical analysis
+ and six analysis machines are gone, replaced by a single one which can be beaten
+ in a minigame.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Sneaky traitors will find new challenges
+ to overcome at the research outpost, but may also find new opportunities (transit
+ tubes can now be traversed).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Finding active alien machinery should
+ now be made significantly easier with the Alden-Saraspova counter.'
+2013-11-01:
+ !!python/unicode 'Various':
+ - !!python/unicode 'rscadd': !!python/unicode 'Autovoting, Get off the station when
+ your 15 hour workweek is done, thanks unions!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Some beach props that Chinsky finds
+ useless.'
+ - !!python/unicode 'wip': !!python/unicode 'Updated NanoUI'
+ - !!python/unicode 'rscadd': !!python/unicode 'Dialysis while in sleepers - removes
+ reagents from mobs, like the chemist, toss him in there!'
+ - !!python/unicode 'tweak': !!python/unicode 'Pipe Dispensers can now be ordered
+ by Cargo'
+ - !!python/unicode 'rscadd': !!python/unicode 'Fancy G-G-G-G-Ghosts!'
+2013-11-23:
+ !!python/unicode 'Ccomp5950':
+ - !!python/unicode 'bugfix': !!python/unicode 'Players are now no longer able to
+ commit suicide with a lasertag gun, and will feel silly for doing so.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Ghosts hit with the cult book shall
+ now actually become visible.'
+ - !!python/unicode 'bugfix': !!python/unicode 'The powercells spawned with Exosuits
+ will now properly be named to not confuse bearded roboticists.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Blindfolded players will now no longer
+ require eye surgery to repair their sight, removing the blindfold will be sufficient.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Atmospheric Technicians will now
+ have access to Exterior airlocks.'
+2013-11-24:
+ !!python/unicode 'Yinadele':
+ - !!python/unicode 'experiment': !!python/unicode 'Supermatter engine added! Please
+ treat your new engine gently, and report any strangeness!'
+ - !!python/unicode 'tweak': !!python/unicode 'Rebalanced events so people don''t
+ explode into appendicitis or have their organs constantly explode.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Vending machines have had bottled
+ water, iced tea, and grape soda added.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Head reattachment surgery added!
+ Sew heads back on proper rather than monkey madness.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Pain crit rebalanced - Added aim
+ variance depending on pain levels, nerfed blackscreen severely.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Cyborg alt titles: Robot, and Android
+ added! These will make you spawn as a posibrained robot. Please enjoy!'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed the sprite on the modified
+ welding goggles, added a pair to the CE''s office where they''ll be used.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed atmos computers- They are once
+ again responsive!'
+ - !!python/unicode 'tweak': !!python/unicode 'Added in functionality proper for
+ explosive implants- You can now set their level of detonation, and their effects
+ are more responsively concrete depending on setting.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Hemostats re-added to autolathe!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added two manuals on atmosia and
+ EVA, by MagmaRam! Found in engineering and the engineering bookcase.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed areas in medbay to have fully
+ functional APC sectors.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Girders are now lasable.'
+ - !!python/unicode 'experiment': !!python/unicode 'Please wait warmly, new features
+ planned for next merge!'
+2013-12-01:
+ !!python/unicode 'Various Developers banged their keyboards together:':
+ - !!python/unicode 'rscadd': !!python/unicode 'New Engine, the supermatter, figure
+ out what a cooling loop is, or don''t and blow up engineering!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Each department will have it''s own
+ fax, make a copy of your butt and fax it to the admins!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Booze and soda dispensers, they are
+ like chemmasters, only with booze and soda!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Bluespace and Cryostasis beakers,
+ how do they work? Fuggin bluespace how do they work?'
+ - !!python/unicode 'rscadd': !!python/unicode 'You can now shove things into vending
+ machines, impress your friends on how things magically disappear out of your
+ hands into the machine!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Robots and Androids (And gynoids
+ too!) can now use custom job titles'
+ - !!python/unicode 'bugfix': !!python/unicode 'Various bugfixes'
+2013-12-18:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Mousetraps can now be "hidden" through
+ the right-click menu. This makes them go under tables, clutter and the like.
+ The filthy rodents will never see it coming!'
+ - !!python/unicode 'tweak': !!python/unicode 'Monkeys will no longer move randomly
+ while being pulled.'
+2014-01-01:
+ !!python/unicode 'Various':
+ - !!python/unicode 'rscadd': !!python/unicode 'AntagHUD and MedicalHUD for ghosts,
+ see who the baddies are, check for new configuration options.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Ghosts will now have bold text if
+ they are in the same room as the person making conversations easier to follow.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New hairstyles! Now you can use
+ something other then hotpink floor length braid.'
+ - !!python/unicode 'wip': !!python/unicode 'DNA rework, tell us how you were cloned
+ and became albino!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Dirty floors, so now you know exactly
+ how lazy the janitors are!'
+ - !!python/unicode 'rscadd': !!python/unicode 'A new UI system, feel free to color
+ it yourself, don''t set it to completely clear or you will have a bad time.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Cryogenic storage, for all your SSD
+ needs.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New hardsuits for those syndicate
+ tajaran'
+2014-02-01:
+ !!python/unicode 'Various':
+ - !!python/unicode 'rscadd': !!python/unicode 'NanoUI for PDA'
+ - !!python/unicode 'rscadd': !!python/unicode 'Write in blood while a ghost in cult
+ rounds with enough cultists'
+ - !!python/unicode 'rscadd': !!python/unicode 'Cookies, absurd sandwiches, and even
+ cookable dioanae nymphs!'
+ - !!python/unicode 'rscadd': !!python/unicode 'A bunch of new guns and other weapons'
+ - !!python/unicode 'rscadd': !!python/unicode 'Species specific blood'
+2014-02-19:
+ !!python/unicode 'Aryn':
+ - !!python/unicode 'experiment': !!python/unicode 'New air model. Nothing should
+ change to a great degree, but temperature flow might be affected due to closed
+ connections not sticking around.'
+2014-03-01:
+ !!python/unicode 'Various':
+ - !!python/unicode 'rscadd': !!python/unicode 'Paint Mixing, red and blue makes
+ purple!'
+ - !!python/unicode 'rscadd': !!python/unicode 'New posters to tell you to respect
+ those darned cat people'
+ - !!python/unicode 'rscadd': !!python/unicode 'NanoUI for APC''s, Canisters, Tank
+ Transfer Valves and the heaters / coolers'
+ - !!python/unicode 'tweak': !!python/unicode 'PDA bombs are now less annoying, and
+ won''t always blow up / cause internal bleeding'
+ - !!python/unicode 'tweak': !!python/unicode 'Blob made less deadly'
+ - !!python/unicode 'rscadd': !!python/unicode 'Objectiveless Antags now a configuration
+ option, choose your own adventure!'
+ - !!python/unicode 'wip': !!python/unicode 'Engineering redesign, now with better
+ monitoring of the explodium supermatter!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Security EOD'
+ - !!python/unicode 'rscadd': !!python/unicode 'New playable race, IPC''s, go beep
+ boop boop all over the station!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Gamemode autovoting, now players
+ don''t have to call for gamemode votes, it''s automatic!'
+2014-03-05:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Smartfridges added to the bar, chemistry
+ and virology. No more clutter!'
+ - !!python/unicode 'rscadd': !!python/unicode 'A certain musical instrument has
+ returned to the bar.'
+ - !!python/unicode 'rscadd': !!python/unicode 'There is now a ten second delay between
+ ingesting a pill/donut/milkshake and regretting it.'
+2014-03-10:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Viruses now affect certain range
+ of species, different for each virus'
+ - !!python/unicode 'tweak': !!python/unicode 'Spaceacilline now prevents infection,
+ and has a small chance to cure viruses at Stage 1. It does not give them antibodies
+ though, so they can get sick again!'
+ - !!python/unicode 'tweak': !!python/unicode 'Biosuits and spacesuits now offer
+ more protection against viruses. Full biosuit competely prevents airborne infection,
+ when coupled with gloves they both protect quite well from contact ones'
+ - !!python/unicode 'rscadd': !!python/unicode 'Sneezing now spreads viruses in front
+ of mob. Sometimes he gets a warning beforehand though'
+2014-03-30:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Inflatable walls and doors added.
+ Useful for sealing off hull breaches, but easily punctured by sharp objects
+ and Tajarans.'
+2014-04-06:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'tweak': !!python/unicode 'Tape recorders and station-bounced
+ radios now work inside containers and closets.'
+2014-04-11:
+ !!python/unicode 'Jarcolr':
+ - !!python/unicode 'rscadd': !!python/unicode 'You can now flip coins like a D2'
+ - !!python/unicode 'tweak': !!python/unicode 'Miscellaneous cargo crates got a tiny
+ buff, Standard Costume crate is now Costume Crate'
+ - !!python/unicode 'tweak': !!python/unicode 'Grammar patch,telekinesis/amputated
+ arm exploit fixes,more in the future'
+ - !!python/unicode 'tweak': !!python/unicode 'Grille kicking now does less damage'
+ - !!python/unicode 'tweak': !!python/unicode 'TELESCOPIC baton no longer knocks
+ anybody down,still got a lot of force though'
+ - !!python/unicode 'tweak': !!python/unicode 'Other small-ish changes and fixes
+ that aren''t worth mentioning'
+2014-04-25:
+ !!python/unicode 'Various':
+ - !!python/unicode 'rscadd': !!python/unicode 'Overhauled saycode, you can now use
+ languages over the radio.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Chamelon items beyond just the suit.'
+ - !!python/unicode 'rscadd': !!python/unicode 'NanoUI Virology'
+ - !!python/unicode 'rscadd': !!python/unicode '3D Sounds'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI Channel color for when they want
+ to be all sneaky'
+ - !!python/unicode 'rscadd': !!python/unicode 'New inflatable walls and airlocks
+ for your breach sealing pleasure.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Carbon Copy papers, so you can subject
+ everyone to your authority and paperwork, but mainly paperwork'
+ - !!python/unicode 'rscadd': !!python/unicode 'Undershirts and rolling down jumpsuits'
+ - !!python/unicode 'rscadd': !!python/unicode 'Insta-hit tasers, can be shot through
+ glass as well.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Changeling balances, an emphasis
+ put more on stealth.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Genetics disabled'
+ - !!python/unicode 'rscdel': !!python/unicode 'Telescience removed, might be added
+ again when we come up with a less math headache enducing version of it.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Bugfixes galore!'
+2014-04-29:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'rscadd': !!python/unicode 'Webbing vest storage can now be accessed
+ by clicking on the item in inventory'
+ - !!python/unicode 'rscadd': !!python/unicode 'Holsters can be accessed by clicking
+ on them in inventory'
+ - !!python/unicode 'rscadd': !!python/unicode 'Webbings and other suit attachments
+ are now visible on the icon in inventory'
+ - !!python/unicode 'tweak': !!python/unicode 'Removing jumpsuits now requires drag
+ and drop to prevent accidental undressing'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added an action icon for magboots
+ that can be used to toggle them similar to flashlights'
+ - !!python/unicode 'rscadd': !!python/unicode 'Fuel tanks now spill fuel when wrenched
+ open'
+2014-05-03:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode "Coming out of nowhere the past few\
+ \ months, the Garland Corporation has made headlines with a new prehistoric\
+ \ theme park delighting travellers with species thought extinct. Now available\
+ \ for research stations everywhere is the technology that made it all possible!\
+ \ Features include: \n\t\t\t- 13 discoverable prehistoric species to clone\
+ \ from fossils (including 5 brand new ones). \n\t\t\t- 11 discoverable prehistoric\
+ \ plants to clone from fossils (including 9 brand new ones). \n\t\t\t- New\
+ \ minigame that involves correctly ordering the genomes inside each genetic\
+ \ sequence to unlock an animal/plant. \n\t\t\t- Some prehistoric animals\
+ \ and plants may seem strangely familiar... while others may bring more than\
+ \ the erstwhile scientist bargains for. \n"
+2014-05-06:
+ !!python/unicode 'Hubble':
+ - !!python/unicode 'rscadd': !!python/unicode 'Clip papers together by hitting a
+ paper with a paper or photo'
+ - !!python/unicode 'imageadd': !!python/unicode 'Adds icons for copied stamps'
+2014-05-16:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'rscadd': !!python/unicode 'Silicon mob types (AI, cyborgs, PAI)
+ can now speak certain species languages depending on type and module'
+ - !!python/unicode 'rscadd': !!python/unicode 'Languages can now be whispered when
+ using the language code with either the whisper verb or the whisper speech code'
+2014-05-23:
+ !!python/unicode 'Hubble':
+ - !!python/unicode 'rscadd': !!python/unicode 'Personal lockers are now resettable'
+ - !!python/unicode 'rscadd': !!python/unicode 'Take off people''s accessories or
+ change their sensors in the drag and drop-interface'
+ - !!python/unicode 'rscadd': !!python/unicode 'Merge paper bundles by hitting one
+ with another'
+ - !!python/unicode 'tweak': !!python/unicode 'Line breaks in Security, Medical and
+ Employment Records'
+ - !!python/unicode 'tweak': !!python/unicode 'Record printouts will have names on
+ it'
+ - !!python/unicode 'tweak': !!python/unicode 'Set other people''s internals in belt
+ and suit storage slots'
+ - !!python/unicode 'bugfix': !!python/unicode 'No longer changing suit sensors while
+ cuffed'
+ - !!python/unicode 'bugfix': !!python/unicode 'No longer emptying other people''s
+ pockets when they are not full yet'
+2014-05-28:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Adds few new paperBBcode tags, to
+ make up for HTML removal.'
+ - !!python/unicode 'rscadd': !!python/unicode '[logo] tag draws NT logo image (one
+ from wiki).'
+ - !!python/unicode 'rscadd': !!python/unicode '[table] [/table] tags mark borders
+ of tables. [grid] [/grid] are borderless tables, useful of making layouts. Inside
+ tables following tags are used: [row] marks beginning of new table row, [cell]
+ - beginning of new table cell.'
+2014-05-31:
+ !!python/unicode 'Jarcolr':
+ - !!python/unicode 'rscadd': !!python/unicode '21 New cargo crates, go check them
+ out!'
+ - !!python/unicode 'rscadd': !!python/unicode 'Peanuts have now been added, food
+ items are now being developed.'
+ - !!python/unicode 'rscadd': !!python/unicode '2 new cargo groups, Miscellaneous
+ and Supply.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Sugarcane seeds can now be gotten
+ from the seed dispenser.'
+ - !!python/unicode 'rscadd': !!python/unicode '5 new satchels when selecting "satchel"
+ for RD, scientist, botanist, virologist, geneticist (disabled) and chemist.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Clicking on a player with a paper/book
+ when you have the eyes selected shows them the book/paper forcefully.'
+2014-06-03:
+ !!python/unicode 'Hubblenaut':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added wheelchairs'
+ - !!python/unicode 'tweak': !!python/unicode 'Replaced stool in Medical Examination
+ with wheelchair'
+ - !!python/unicode 'tweak': !!python/unicode 'Using a fire-extinguisher to propel
+ you on a chair can have consequences (drive into walls and people, do it!)'
+2014-06-13:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added docking ports for shuttles'
+ - !!python/unicode 'rscadd': !!python/unicode 'Shuttle airlocks will automatically
+ open and close, preventing people from being sucked into space by because someone
+ on another z-level called a shuttle'
+ - !!python/unicode 'rscadd': !!python/unicode 'Some docking ports can also double
+ as airlocks'
+ - !!python/unicode 'rscadd': !!python/unicode 'Docking ports can be overriden to
+ prevent any automatic action. Shuttles will wait for players to open/close doors
+ manually'
+ - !!python/unicode 'rscadd': !!python/unicode 'Shuttles can be forced launched,
+ which will make them not wait for airlocks to be properly closed'
+2014-06-15:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed wound autohealing regardless
+ of damage amount. The appropriate wound will now be assigned correctly based
+ on damage amount and type'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed several other bugs related
+ wounds that resulted in damage magically disappearing'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed various sharp objects not being
+ counted as sharp, bullets in particular'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed armour providing more protection
+ from bullets than it was supposed to'
+2014-06-19:
+ !!python/unicode 'Chinsky':
+ - !!python/unicode 'rscadd': !!python/unicode 'Adds guest terminals on the map.
+ These wall terminals let anyone issue temporary IDs. Only access that issuer
+ has can be granted, and maximum time pass can be issued for is 20 minutes. All
+ operations are logged in terminals.'
+2014-06-20:
+ !!python/unicode 'Cael_Aislinn':
+ - !!python/unicode 'rscadd': !!python/unicode 'New discoverable items added to xenoarchaeology,
+ and new features for some existing ones. Artifact harvesters can now harvest
+ the secondary effect of artifacts as well as the primary one.
+
+ '
+ - !!python/unicode 'tweak': !!python/unicode 'Artifact utilisers should be much
+ nicer/easier to use now.
+
+
Alden-Saraspova counters and talking items should work properly
+ now.
+
+
+
+ '
+2014-07-01:
+ !!python/unicode 'Various':
+ - !!python/unicode 'experiment': !!python/unicode 'Hardsuit breaching.'
+ - !!python/unicode 'experiment': !!python/unicode 'Rewritten fire.'
+ - !!python/unicode 'experiment': !!python/unicode 'Supermatter now glows and sucks
+ things into it as it approaches criticality.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Station Vox (Vox pariahs) are now
+ available.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Wheelchairs.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Cargo Trains.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Hardsuit cycler machinery.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Rewritten lighting (coloured lights!)'
+ - !!python/unicode 'rscadd': !!python/unicode 'New Mining machinery and rewritten
+ smelting.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Rewritten autolathe'
+ - !!python/unicode 'rscadd': !!python/unicode 'Mutiny mode.'
+ - !!python/unicode 'rscadd': !!python/unicode 'NanoUI airlock and docking controllers.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Completely rewritten shuttle code.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Derelict Z-level replacement: construction
+ site.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Computer3 laptops.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Constructable SMES units.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Omni-directional atmos machinery.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Climbable tables and crates.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Xenoflora added to Science.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Utensils can be used to eat food.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Decks of cards are now around the
+ station.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Service robots can speak languages.'
+ - !!python/unicode 'wip': !!python/unicode 'Xenoarch updates and fixes.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rewritten species-specific gear icon
+ handling.'
+ - !!python/unicode 'tweak': !!python/unicode 'Cats and borers can be picked up.'
+ - !!python/unicode 'tweak': !!python/unicode 'Botanist renamed to Gardener.'
+ - !!python/unicode 'tweak': !!python/unicode 'Hydroponics merged with the Kitchen.'
+ - !!python/unicode 'tweak': !!python/unicode 'Latejoin spawn points (Arrivals, Cryostorage,
+ Gateway).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Escape pods only launch automatically
+ during emergency evacuations'
+ - !!python/unicode 'rscadd': !!python/unicode 'Escape pods can be made to launch
+ during regular crew transfers using the control panel inside the pod, or by
+ emagging the panel outside the pod'
+ - !!python/unicode 'rscadd': !!python/unicode 'When swiped or emagged, the crew
+ transfer shuttle can be delayed in addition to being launched early'
+2014-07-06:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'rscadd': !!python/unicode 'Re-enabled and rewrote the wound
+ infection system'
+ - !!python/unicode 'rscadd': !!python/unicode 'Infections can be prevented by properly
+ bandaging and salving wounds'
+ - !!python/unicode 'rscadd': !!python/unicode 'Infections are cured by spaceacillin'
+2014-07-20:
+ !!python/unicode 'PsiOmegaDelta':
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now store up to five camera
+ locations and return to them when desired.'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now alt+left click turfs in
+ camera view to list and interact with the objects.'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now ctrl+click turret controls
+ to enable/disable turrets.'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now alt+click turret controls
+ to toggle stun/lethal mode.'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now select which channel to
+ state laws on.'
+2014-07-26:
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added dynamic flavour text.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixed bug with suit fibers and fingerprints.'
+2014-07-31:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'tweak': !!python/unicode 'Stun batons now work like tasers and
+ deal agony instead of stun'
+ - !!python/unicode 'rscadd': !!python/unicode 'Being hit in the hands with a stun
+ weapon will cause whatever is being held to be dropped'
+ - !!python/unicode 'tweak': !!python/unicode 'Handcuffs now require an aggressive
+ grab to be used'
+2014-08-02:
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'bugfix': !!python/unicode 'Arcane tomes can now be stored on
+ bookshelves.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Dionaea players no longer crash on
+ death, and now become nymphs properly.'
+2014-08-05:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'tweak': !!python/unicode 'Atmos Rewrite. Many atmos devices
+ now use power according to their load and gas physics'
+ - !!python/unicode 'rscadd': !!python/unicode 'Pressure regulator device. Replaces
+ the passive gate and can regulate input or output pressure'
+ - !!python/unicode 'rscadd': !!python/unicode 'Gas heaters and gas coolers are now
+ constructable and can be upgraded with parts from research'
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes recharger and cell charger
+ power draw. Rechargers draw 15 kW, wall chargers draw 25 kW, and heavy-duty
+ cell chargers draw 40 kW. Cyborg charging stations draw 75 kW.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Laptops, and various other machines,
+ now draw more reasonable amounts of power'
+ - !!python/unicode 'bugfix': !!python/unicode 'Machines will periodically update
+ their powered status if moved from a powered to an unpowered area and vice versa'
+2014-08-27:
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'bugfix': !!python/unicode 'Made destination taggers more intuitive
+ so you know when you''ve tagged something'
+ - !!python/unicode 'rscadd': !!python/unicode 'Ported package label and tag sprites'
+ - !!python/unicode 'rscadd': !!python/unicode 'Ported using a pen on a package to
+ give it a title, or to write a note'
+ - !!python/unicode 'rscadd': !!python/unicode 'Donut boxes and egg boxes can be
+ constructed out of cardboard'
+2014-08-31:
+ !!python/unicode 'Whitellama':
+ - !!python/unicode 'bugfix': !!python/unicode 'Matches and candles can be used to
+ burn papers, too.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Observers have a bit more time (20
+ seconds, instead of 7.5) before the Diona join prompt disappears.'
+2014-09-05:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'experiment': !!python/unicode 'NewPipe implemented: Supply and
+ scrubber pipes can be run in parallel without connecting to each other.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Supply pipes will only connect to
+ supply pipes, vents and Universal Pipe Adapters(UPAs).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Scrubber pipes will only connect
+ to scrubber pipes, scrubbers and UPAs.'
+ - !!python/unicode 'rscadd': !!python/unicode 'UPAs will connect to regular, scrubber
+ and supply pipes.'
+2014-09-20:
+ !!python/unicode 'HarpyEagle':
+ - !!python/unicode 'bugfix': !!python/unicode 'Fixes evidence bags and boxes eating
+ each other. Evidence bags now store items by dragging the bag onto the item
+ to be stored.'
+2014-09-28:
+ !!python/unicode 'Gamerofthegame':
+ - !!python/unicode 'rscadd': !!python/unicode 'Hoverpods fully supported, currently
+ orderable from cargo. Two slots, three cargo, space flight and a working mech
+ for all other intents and purposes.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added the Rigged laser and Passenger
+ Compartment equipment. The rigged laser is a weapon for working exosuits - just
+ a ordinary laser, but with triple the cool down and rather power inefficient.
+ The passenger compartment allows other people to board and hitch a ride on the
+ mech - such as in fire rescue or for space flight.'
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'rscadd': !!python/unicode 'Organs can now be removed and transplanted.'
+ - !!python/unicode 'tweak': !!python/unicode 'Brain surgery is now the same as chest
+ surgery regarding the steps leading up to it.'
+ - !!python/unicode 'tweak': !!python/unicode 'Appendix and kidney now share the
+ groin and removing the first will prevent appendicitis.'
+ - !!python/unicode 'tweak': !!python/unicode 'Lots of backend surgery/organ stuff,
+ see the PR if you need to know.'
+2014-10-01:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Zooming with the sniper rifle now
+ adds a view offset in the direction you are facing.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added binoculars - functionally similar
+ to sniper scope. Adminspawn-only for now.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Bottles from chemistry now, like
+ beakers, use chemical overlays instead of fixed sprites.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Being in space while not magbooted
+ to something will cause your sprite to bob up and down.'
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added species organ checks to several
+ areas (phoron burn, welder burn, appendicitis, vox cortical stacks, flashes).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added VV option to add or remove
+ organs.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added simple bioprinter (adminspawn).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added smashing/slashing behavior
+ from xenos to some unarmed attacks.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added some new state icons for diona
+ nymphs.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added borer husk functionality (cortical
+ borers can turn dead humans into zombies).'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added tackle verb.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added NO_SLIP.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added species-specific orans to Dionaea,
+ new Xenomorphs and vox.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added colour and species to blood
+ data.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Added lethal consequences to missing
+ your heart.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed robot_talk_understand and
+ alien_talk_understand.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed attack_alien() and several
+ flavours of is_alien() procs.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed /mob/living/carbon/alien/humanoid.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed alien_hud().'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed IS_SLOW, NEEDS_LIGHT and
+ RAD_ABSORB.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Renamed is_larva() to is_alien().'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored a ton of files, either
+ condensing or expanding them, or moving them to new directories.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored some attack vars from simple_animal
+ to mob/living level.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored internal organs to /mob/living/carbon
+ level.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored rad and light absorbtion
+ to organ level.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored brains to /obj/item/organ/brain.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored a lot of blood splattering
+ to use blood_splatter() proc.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored broadcast languages (changeling
+ and alien hiveminds, drone and binary chat) to actual languages.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored xenomorph abilities to
+ work for humans.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored xenomorphs into human species.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rewrote larva_hud() and human_hud().
+ The latter now takes data from the species datum.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rewrote diona nymphs as descendents
+ of /mob/living/carbon/alien.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rewrote xenolarva as descendents of
+ /mob/living/carbon/alien.'
+ - !!python/unicode 'tweak': !!python/unicode 'Rewrote /mob/living/carbon/alien.'
+ - !!python/unicode 'tweak': !!python/unicode 'Moved alcohol and toxin processing
+ to the liver.'
+ - !!python/unicode 'tweak': !!python/unicode 'Moved drone light proc to robot level,
+ added integrated_light_power and local_transmit vars to robots.'
+ - !!python/unicode 'tweak': !!python/unicode 'Moved human brainloss onto the brain
+ organ.'
+ - !!python/unicode 'tweak': !!python/unicode 'Shuffled around and collapsed several
+ redundant procs down to carbon level (hide, ventcrawl, Bump).'
+ - !!python/unicode 'tweak': !!python/unicode 'Fixed species swaps from NO_BLOOD
+ to those with blood killing the subject instantly.'
+2014-11-01:
+ !!python/unicode 'PsiOmegaDelta':
+ - !!python/unicode 'bugfix': !!python/unicode 'Adds the last missing step to deconstruct
+ fire alarms. Apply wirecutters.'
+ - !!python/unicode 'rscadd': !!python/unicode 'There''s a "new" mining outpost nearby
+ the Research outpost.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Manifest ghosts now have spookier
+ names.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Adds a gas monitor computer for the
+ toxin mixing chamber.'
+ - !!python/unicode 'rscadd': !!python/unicode 'AI can now change the display of
+ individual AI status screens.'
+ - !!python/unicode 'rscadd': !!python/unicode 'More ion laws..'
+ - !!python/unicode 'rscadd': !!python/unicode 'All turrets have been replaced with
+ portable variants. Potential targets can be configured on a per turret basis.'
+ - !!python/unicode 'bugfix': !!python/unicode 'Improved crew monitor map positioning.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Can now order plastic, body-, and
+ statis bags from cargo'
+ - !!python/unicode 'rscadd': !!python/unicode 'PDAs now receive newscasts.'
+ - !!python/unicode 'rscadd': !!python/unicode '(De)constructable emergency shutters.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Borgs can now select to simply state
+ their laws or select a radio channel, same as the AI.'
+2014-11-04:
+ !!python/unicode 'TwistedAkai':
+ - !!python/unicode 'rscadd': !!python/unicode 'Almost any window which has been
+ fully unsecured can now be dismantled with a wrench.'
+2014-11-08:
+ !!python/unicode 'PsiOmegaDelta':
+ - !!python/unicode 'rscadd': !!python/unicode 'Service personnel now have their
+ own frequency to communicate over. Use "say :v".'
+ - !!python/unicode 'rscadd': !!python/unicode 'The AI can now has proper quick access
+ to its private channel. Use "say :o".'
+ - !!python/unicode 'rscadd': !!python/unicode 'Newscasters supports photo captions.
+ Simply pen one on the attached photo.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Once made visible by a cultist ghosts
+ can toggle visiblity at will.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Detonating cyborgs using the cyborg
+ monitor console now notifies the master AI, if any.'
+ - !!python/unicode 'rscadd': !!python/unicode 'More machinery, such as APCs, air
+ alarms, etc., now support attaching signalers to the wires.'
+ - !!python/unicode 'tweak': !!python/unicode 'Random event overhaul. Admins may
+ wish check the verb "Event Manager Panel".'
+2014-11-22:
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'rscadd': !!python/unicode 'Added the /obj/item/weapon/rig class
+ - back-mounted deployable hardsuits.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Replaced existing hardsuits with
+ ''voidsuits'', functionally identical.'
+ - !!python/unicode 'rscdel': !!python/unicode 'Removed the mounted device and helmet/boot
+ procs from voidsuits.'
+ - !!python/unicode 'tweak': !!python/unicode 'Refactored a shit-ton of ninja code
+ into the new rig class.'
+ - !!python/unicode 'wip': !!python/unicode 'This is more than likely going to take
+ a lot of balancing to get into a good place.'
+2015-01-09:
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'tweak': !!python/unicode 'Voice changers no longer use ID cards.
+ They have Toggle and Set Voice verbs on the actual mask object now.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Readded moonwalking. Alt-dir to face
+ new dir, or Face-Direction verb to face current dir.'
+2015-02-04:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Holodeck is now bigger and better,
+ with toggleable gravity and a new courtroom setting'
+ !!python/unicode 'TwistedAkai':
+ - !!python/unicode 'bugfix': !!python/unicode 'Purple Combs should now be visible
+ and have their proper icon'
+2015-02-12:
+ !!python/unicode 'Daranz':
+ - !!python/unicode 'rscadd': !!python/unicode 'Vending machines now use NanoUI and
+ accept cash. The vendor account can now be suspended to disable all sales in
+ all machines on station.'
+2015-02-16:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'rscadd': !!python/unicode 'Say hello to the new Thermoelectric
+ Supermatter Engine. Read the operating manual to get started.'
+2015-02-18:
+ !!python/unicode 'PsiOmegaDelta':
+ - !!python/unicode 'rscadd': !!python/unicode 'Synths now have timestamped radio
+ and chat messages.'
+ - !!python/unicode 'rscadd': !!python/unicode 'New and updated uplink items.'
+ - !!python/unicode 'rscadd': !!python/unicode 'Multiple AIs can now share the same
+ holopad.'
+ - !!python/unicode 'rscadd': !!python/unicode 'The AI now has built-in consoles,
+ accessible from the subsystem tab.'
+2015-02-24:
+ !!python/unicode 'Zuhayr':
+ - !!python/unicode 'experiment': !!python/unicode 'Major changes to the kitchen
+ and hydroponics mechanics. Review the detailed changelog here,'
+2015-04-07:
+ !!python/unicode 'RavingManiac':
+ - !!python/unicode 'tweak': !!python/unicode 'You can now pay vending machines and
+ EFTPOS scanners without removing your ID from your PDA or wallet. Clicking on
+ the vending machine with your ID/PDA/wallet/cash also brings up the menu now
+ instead of attacking the vending machine.'
+2015-04-18:
+ PsiOmegaDelta:
+ - rscadd: Added a changelog editing system that should cause fewer conflicts and
+ more accurate timestamps.
+2015-04-23:
+ Dennok:
+ - rscadd: Added an automatic pipelayer.
+ - rscadd: Added an automatic cablelayer.
+ PsiOmegaDelta:
+ - bugfix: Shower curtains no longer lose their default color upon being washed.
+ - bugfix: Emergency shutters can again be examined, and from the proper distance.
+ - bugfix: The virus event will now only infect mobs on the station, currently controlled
+ by player that has been active in the last 5 minutes.
+ - bugfix: Laptops now use the proper proc for checking camera status.
+ - rscadd: Makes it possible to eject PDA cartridges using a verb.
+ - rscadd: Makes it possible to shake tables with one's bare hands to stop climbers.
+ - bugfix: Added a mass driver door in disposals to prevent trash from floating out
+ into space before proper ejection.
+ - rscadd: Rig/Hardsuit module tab - Less informative than the NanoUI hardsuit interface
+ but allows quicker access to the various rig modules.
+ - rscadd: Silicons with the medical augmentation sensors enabled now also see alive/dead
+ status if sensors are set accordingly.
+ - rscadd: Emergency shutters opened by silicons are now treated as having been forced
+ open by a crowbar.
+ - rscadd: An active AI chassis can now be pushed, just as an empty chassis can be.
+ - rscadd: The AI can now use the crew monitor console to track crew members with
+ full sensors enabled.
+ - rscadd: The AI now has a shortcut to track people holding up messages to cameras.
+ - rscadd: The AI now has a shortcut to track people sending PDA messages.
+ - rscadd: Multiple AIs can now share the same holopad.
+ - rscadd: Admin ghosts can now transfer other ghosts into mobs by drag-clicking.
+ - rscadd: Ghosts can now toggle seeing darkness and other ghosts separately.
+ - rscadd: Moving while dead now auto-ghosts you.
+ - rscadd: 'Two new random events: Space dust and gravitation failure.'
+ - rscadd: Upgraded wizard spell interface and new spells.
+ - rscadd: More uplink items.
+ - rscadd: Uplink items now have rudimentary descriptions.
+ Yoshax:
+ - tweak: Adjusts fruits and other stuff to have a minmum of 10 units of juice and
+ stuff.
+2015-04-24:
+ Dennok:
+ - bugfix: Fixes overmap ship speed calculations.
+ - rscadd: Adds overmap ship rotation.
+ - rscadd: Added a floorlayer.
+2015-04-28:
+ Jarcolr:
+ - rscadd: Added 9 new bar sign designs/sprites.
+ Kelenius:
+ - rscadd: 'Good news to the roboticists! The long waited firmware update for the
+ bots has arrived. You can expect the following changes:'
+ - rscadd: Medbots have improved the disease detection algorithms.
+ - rscadd: Floorbot firmware has been bugtested. In particular, they will no longer
+ get stuck near the windows, hopelessly trying to fix the floor under the glass.
+ - rscadd: Floorbots have also received an internal low-power metal synthesizer.
+ They will use it to make their own tiles. Slowly.
+ - rscadd: Following the complains from humanitarian organizations regarding securitron
+ brutality, stength of their stunners has been toned down. They will also politely
+ demand that you get on the floor before arresting you. Except for the taser-mounted
+ guys, they will still tase you down.
+ - rscadd: Other minor fixes.
+ - rscdel: 'The lasertag bots are now forbidden to build and use following the incident
+ #1526672. Please don''t let it happen again.'
+ - rscadd: The farmbot design has been finished! Made from a watertank, robot arm,
+ plant analyzer, bucket, minihoe and a proximity sensor, these small (not really)
+ bots will be a useful companion to any gardener and/or xenobotanist.
+ - tweak: 'Spider learning alert: they have learned to recognize the bots and will
+ mercilessly attack them.'
+ - rscadd: An experimental CPU upgrade would theoretically allow any of the bots
+ to function with the same intelligence capacity as the maintenance drones. We
+ still have no idea what causes it to boot up. Science!
+ - rscadd: 'INCOMING TRANSMISSION: Greetings to agents, pirates, operatives, and
+ anyone who otherwise uses our equipment. Following the NT update of bot firmware,
+ we have updated the cryptographic sequencer''s hacking routines as well. The
+ medbots you emag will not poison you anymore, the clanbots won''t clean after
+ themselves immediately, and floorbots... wear a space suit. Oh, and it works
+ on the new farmbots, too.'
+ PsiOmegaDelta:
+ - rscadd: Beware. Airlocks can now crush more things than just mobs.
+ - rscadd: AIs now have a personal atmospherics control subsystem.
+ - rscadd: Some borg modules now have additional subsystems.
+ - tweak: Improves borg module handling.
+ - tweak: Secure airlocks now buzz when access is denied.
+ - tweak: The mental health office door now requires psychiatrist access, and the
+ related button now opens/closes the door instead of bolting.
+ - soundadd: Restores an old soundtrack 'Thunderdome.ogg'.
+ - rscadd: Some holodeck programs now have custom ambience tracks.
+ RavingManiac:
+ - rscadd: The phoron research lab has been renovated to include a heat-exchange
+ system, a gas mixer/filter and a waste gas disposal pump.
+ - tweak: Candles now burn for about 30 mintutes.
+ Yoshax:
+ - tweak: Adds items to the orderable antag surgical kit so its actually useful for
+ surgery.
+ - tweak: Adjusts custom loadout costs to be more standardised and balances. Purely
+ cosmetic items, shoes, hats, and all things that do not provide a straight advtange
+ (sterile mask, or pAI, protection from viruses and possible door hacking or
+ records access, respectively), each cost 1 point, items that provide an advantage
+ like those just mentioned, or provide armor or storage cost 2 points.
+ - rscadd: Adds practice rounds, both .45 for Sec and Detective's guns, also 9mm
+ top mounted for the Saber, and for the Bulldog.
+ - rscadd: Adds the .45 and 9mm practice rounds to the armory.
+ - rscadd: Adds all the practice rounds to the autolathe.
+ - tweak: Adds r_walls to the back of the firing range, leaves the sides normal.
+ - bugfix: Fixes HoS' office door to not be CMO locked.
+2015-04-29:
+ Daranz:
+ - rscadd: Paper bundles can now have papers inserted at arbitrary points. This can
+ be done by clicking the previous/next page links with a sheet of paper in hand.
+ HarpyEagle:
+ - rscadd: 'Added new fire modes to various guns: c20r, STS-35, WT-550, Z8, L6 SAW,
+ and double barreled shotgun. The firing modes work the same way as the egun;
+ click on the weapon with it in your active hand to cycle between modes. Unloading
+ these weapons now requires that you click on them with an empty hand.'
+ PsiOmegaDelta:
+ - rscadd: Portable atmospheric pumps and scrubbers now use NanoUI.
+ - rscadd: Two new events which will cause damage to APCs or cameras when triggered.
+2015-04-30:
+ Yoshax:
+ - rscadd: Adds more items to custom loadout, including a number of dressy suits
+ and some other things.
+2015-05-02:
+ HarpyEagle:
+ - bugfix: Neck-grabbing someone now stuns them properly.
+ PsiOmegaDelta:
+ - tweak: The spider infestation event now makes an announcement much sooner.
+ - rscadd: Admins can now toggle OOC/LOOC separately.
+ - tweak: Mice are now numbered to aid admins.
+ Yoshax:
+ - rscadd: Adds an option and verb to the AI to send emergency messages to Central,
+ functions same as comms console option.
+ - tweak: Changes comms console to only have one level of ID require, meaning all
+ heads of staff have what was captain access, allowing them to change alert,
+ send emergency messages and make announcements.
+ - rscadd: Adds an emergency bluespace relay machine which is mapped into teletcomms,
+ this machine takes emergency messages and sends them to central, if one does
+ not exist on any Z, you cannot send any emergency messages.
+ - rscadd: Adds an emergency bluespace relay assembly kit orderable from cargo for
+ when the ones on telecomms are destroyed. Assembly is required.
+ - rscadd: Adds the emergency bluespace relay circuitboard to be researchable and
+ printable in R&D, with sufficient tech levels.
+2015-05-05:
+ PsiOmegaDelta:
+ - tweak: Grilles no longer return too many rods when destroyed (using means other
+ than wirecutters).
+ RavingManiac:
+ - tweak: Intent menu now appears while zooming with a sniper rifle.
+2015-05-06:
+ PsiOmegaDelta:
+ - rscadd: Examining a pen or crayon now lists the available special commands in
+ the examine tab.
+2015-05-07:
+ HarpyEagle:
+ - rscadd: Breaking out of lockers now has sound and animation.
+ PsiOmegaDelta:
+ - bugfix: The cloning computer can again successfully locate nearby cloning vats
+ and DNA scanners at round start.
+ - rscadd: Security equipment now treats individuals with CentCom ids with the greatest
+ respect.
+ - maptweak: Adds stretches of power cable around the construction outpost, ensuring
+ one does not have to climb over machines to being laying cables.
+ RavingManiac:
+ - rscadd: Muzzle-flash lighting effect for guns
+ - rscadd: Energy guns now display shots remaining on examine
+2015-05-09:
+ Yoshax:
+ - rscadd: Maps in the top mounted 9mm practice rounds, .45 practice rounds, and
+ practice shotgun shells into the armory.
+2015-05-10:
+ GinjaNinja32:
+ - rscadd: Acting jobs on the manifest will now sort with their non-acting counterparts.
+ All assignments beginning with the word 'acting', 'temporary', or 'interim'
+ will do this.
+ Yoshax:
+ - tweak: Removes sleepy chems from being cloned, adds a consistent period of 30
+ tick sleep.
+2015-05-11:
+ Mloc:
+ - experiment: Rewritten lighting system.
+ - rscadd: Better coloured lights.
+ - rscadd: Animated transitions.
+ PsiOmegaDelta:
+ - bugfix: As an observer, using antagHUD should now always restrict you from respawning
+ without admin intervention.
+ Techhead:
+ - rscadd: Voidsuits can have tanks inserted into the storage slot.
+ - rscadd: Voidsuits display helpful information on their contents on examine.
+ - rscadd: Magboots can be equipped over other shoes. Except other magboots.
+2015-05-12:
+ Dennok:
+ - imageadd: New buildmode icons made by BartNixon.
+ HarpyEagle:
+ - rscadd: Masks and helmets that cover the face block feeding food, drinks, and
+ pills.
+ MrSnapwalk:
+ - imageadd: Added seven new AI core displays.
+ - tweak: Changed the pAI sprite and added several new expressions.
+ PsiOmegaDelta:
+ - rscadd: The space vine event now comes with a station announcement.
+2015-05-14:
+ PsiOmegaDelta:
+ - maptweak: Should now be more evident that the brig disposal chute sends its goods
+ to the common brig area.
+ - bugfix: Cells now drain when using more charge than what is available.
+ - tweak: The rig stealth module now requires as much power to run as the energy
+ blade module.
+ Techhead:
+ - rscadd: Vox will spawn with emergency nitrogen tanks in their survival boxes.
+ - rscadd: Diona will spawn with an emergency flare instead of a survival box.
+ - rscdel: Engineers no longer spawn with extended-capacity oxygen tanks.
+ - bugfix: Vox spawning without backpacks will have their nitrogen tank equipped
+ to their back.
+ - tweak: The Bartender's spare beanbag shells have been moved into bar backroom
+ with the shotgun.
+ - bugfix: Portable air pumps now fill based on external/airtank pressure when pumping
+ in.
+2015-05-16:
+ GinjaNinja32:
+ - rscadd: Rewrote tables. To construct a table, use steel to make a table frame,
+ then plate the frame with a material such as steel, gold, wood, etc. Hold a
+ stack in your hand and drag it to the table to reinforce it. To deconstruct
+ a table, use a screwdriver to remove the reinforcements (if present), then a
+ wrench to remove the plating, and a wrench again to dismantle the frame. Use
+ a welder to repair any damage. Use a carpet tile on a table to add felt, and
+ a crowbar to remove it.
+ HarpyEagle:
+ - rscadd: Adds tail animations for tajaran and unathi. Animations are controlled
+ using emotes.
+2015-05-17:
+ PsiOmegaDelta:
+ - bugfix: Teleporter artifacts should no longer teleport mobs inside objects.
+2015-05-18:
+ Hubblenaut:
+ - rscadd: Adds a light for available backup power on airlocks.
+ Kelenius:
+ - tweak: 'There has been a big update to the reagent system. A full-ish changelog
+ can be found here: http://pastebin.com/imHXTRHz. In particular:'
+ - tweak: Reagents now differentiate between being ingested (food, pills, smoke),
+ injected (syringes, IV drips), and put on the skin (sprays, beaker splashing).
+ - tweak: Injecting food and drinks will cause bad effects.
+ - tweak: Healing reagents, generally speaking, have stronger effects when injected.
+ - tweak: Toxins now work slower and deal more damage. Seek medical help!
+ - tweak: Alcohol robustness has been lowered.
+ - tweak: Acid will no longer melt large numbers of items at once.
+ - tweak: Synaptizine is no longer hilariously deadly.
+ Loganbacca:
+ - tweak: Changed MULE destination selection to be list based.
+ PsiOmegaDelta:
+ - tweak: Destroying a camera by brute force now has a chance to break the wiring
+ within.
+ - rscadd: Turf are now processed. This, for example, causes radioactive walls to
+ regularly irradiate nearby mobs.
+ - bugfix: Welders should now always update their icon and inhand states properly.
diff --git a/html/changelogs/Comma-PR-9337.yml b/html/changelogs/Comma-PR-9337.yml
new file mode 100644
index 00000000000..cf1aac28916
--- /dev/null
+++ b/html/changelogs/Comma-PR-9337.yml
@@ -0,0 +1,8 @@
+author: Chinsky
+
+delete-after: True
+
+changes:
+ - rscadd: "Ghetto diagnosis. Grab patient, aim at bodypart you want to check, click on them with help intent. This will tell you about their wounds, fractures and other oddities (toxins/oxygen) for that bodypart."
+ - rscadd: "Fractures are visible on very damaged limbs. Dislocations are always visible. Surgery incisions now visible too."
+ - rscadd: "Stethoscopes actually make sense now. They care for heart/lungs status when reporting pulse and respiration now."
\ No newline at end of file
diff --git a/html/changelogs/Yoshax - trapping.YML b/html/changelogs/Yoshax - trapping.YML
new file mode 100644
index 00000000000..d9b7884761a
--- /dev/null
+++ b/html/changelogs/Yoshax - trapping.YML
@@ -0,0 +1,37 @@
+################################
+# Example Changelog File
+#
+# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb.
+#
+# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.)
+# When it is, any changes listed below will disappear.
+#
+# Valid Prefixes:
+# bugfix
+# wip (For works in progress)
+# tweak
+# soundadd
+# sounddel
+# rscadd (general adding of nice things)
+# rscdel (general deleting of nice things)
+# imageadd
+# imagedel
+# maptweak
+# spellcheck (typo fixes)
+# experiment
+#################################
+
+# Your name.
+author: Yoshax
+
+# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again.
+delete-after: True
+
+# Any changes you've made. See valid prefix list above.
+# INDENT WITH TWO SPACES. NOT TABS. SPACES.
+# SCREW THIS UP AND IT WON'T WORK.
+# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries.
+# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog.
+changes:
+ - tweak: "Bear traps now do damage when stood on, enough to break bones! Bear traps can now affect any limb of a person who is on the ground, including head! Bear traps are no longer legcuffs and instead embed in the limb they attack."
+ - tweak: "Bear traps now take several seconds to deploy and cannot be picked up when armed, they must be disarmed by clicking on them. They also cannot be moved then they are deployed."
\ No newline at end of file
diff --git a/html/changelogs/__CHANGELOG_README.txt b/html/changelogs/__CHANGELOG_README.txt
new file mode 100644
index 00000000000..6915dc47e25
--- /dev/null
+++ b/html/changelogs/__CHANGELOG_README.txt
@@ -0,0 +1,19 @@
+Changelogs are included with commits as text .yml files created individually by the committer. If you want to create a changelog entry you create a .yml file in the /changelogs directory; nothing else needs to be touched unless you are a maintainer.
+
+#######################################################
+
+TO MAKE A CHANGELOG .YML ENTRRY
+
+1. Make a copy of the file example.yml in html/changelogs and rename it to [YOUR USERNAME]-PR-[YOUR PR NUMBER].yml or [YOUR USERNAME]-[YOUR BRANCH NAME]. Only the username is strictly required, anything else is organizational and can be ignored if you so wish.
+
+2. Change the author to yourself
+
+3. Replace the changes text with a description of the changes in your PR, keep the double quotes to avoid errors (your changelog can be written ICly or OOCly, it doesn't matter)
+
+4. (Optional) set the change prefix (rscadd) to a different one listed above in example.yml (this affects what icon is used for your changelog entry)
+
+5. When commiting make sure your .yml file is included in the commit (it will usually be unticked as an unversioned file)
+
+#######################################################
+
+If you have trouble ask for help in #codershuttle on irc.sorcery.net or read https://tgstation13.org/wiki/Guide_to_Changelogs
diff --git a/html/changelogs/example.yml b/html/changelogs/example.yml
new file mode 100644
index 00000000000..c34ccdd0a08
--- /dev/null
+++ b/html/changelogs/example.yml
@@ -0,0 +1,37 @@
+################################
+# Example Changelog File
+#
+# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb.
+#
+# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.)
+# When it is, any changes listed below will disappear.
+#
+# Valid Prefixes:
+# bugfix
+# wip (For works in progress)
+# tweak
+# soundadd
+# sounddel
+# rscadd (general adding of nice things)
+# rscdel (general deleting of nice things)
+# imageadd
+# imagedel
+# maptweak
+# spellcheck (typo fixes)
+# experiment
+#################################
+
+# Your name.
+author: N3X15
+
+# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again.
+delete-after: True
+
+# Any changes you've made. See valid prefix list above.
+# INDENT WITH TWO SPACES. NOT TABS. SPACES.
+# SCREW THIS UP AND IT WON'T WORK.
+# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries.
+# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog.
+changes:
+ - rscadd: "Added a changelog editing system that should cause fewer conflicts and more accurate timestamps."
+ - rscdel: "Killed innocent kittens."
diff --git a/html/create_object.html b/html/create_object.html
index a1f115b7839..f4e0aa8644c 100644
--- a/html/create_object.html
+++ b/html/create_object.html
@@ -27,7 +27,7 @@
-
-
-
-
-
-
-
-
-