code:
/obj/structure/AIcore
	density = 1
	anchored = 0
	name = "\improper AI core"
	icon = 'icons/mob/AI.dmi'
	icon_state = "0"
	var/state = 0
	var/datum/ai_laws/laws = new()
	var/obj/item/weapon/circuitboard/circuit = null
	var/obj/item/device/mmi/brain = null

/obj/structure/AIcore/attackby(obj/item/P as obj, mob/user as mob, params)
	switch(state)
		if(0)
			if(istype(P, /obj/item/weapon/wrench))
				playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
				if(do_after(user, 20))
					user << "You wrench the frame into place."
					anchored = 1
					state = 1
			if(istype(P, /obj/item/weapon/weldingtool))
				var/obj/item/weapon/weldingtool/WT = P
				if(!WT.isOn())
					user << "The welder must be on for this task."
					return
				playsound(loc, 'sound/items/Welder.ogg', 50, 1)
				if(do_after(user, 20))
					if(!src || !WT.remove_fuel(0, user)) return
					user << "You deconstruct the frame."
					new /obj/item/stack/sheet/plasteel( loc, 4)
					qdel(src)
		if(1)
			if(istype(P, /obj/item/weapon/wrench))
				playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
				if(do_after(user, 20))
					user << "You unfasten the frame."
					anchored = 0
					state = 0
			if(istype(P, /obj/item/weapon/circuitboard/aicore) && !circuit)
				playsound(loc, 'sound/items/Deconstruct.ogg', 50, 1)
				user << "You place the circuit board inside the frame."
				icon_state = "1"
				circuit = P
				user.drop_item()
				P.loc = src
			if(istype(P, /obj/item/weapon/screwdriver) && circuit)
				playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You screw the circuit board into place."
				state = 2
				icon_state = "2"
			if(istype(P, /obj/item/weapon/crowbar) && circuit)
				playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
				user << "You remove the circuit board."
				state = 1
				icon_state = "0"
				circuit.loc = loc
				circuit = null
		if(2)
			if(istype(P, /obj/item/weapon/screwdriver) && circuit)
				playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You unfasten the circuit board."
				state = 1
				icon_state = "1"
			if(istype(P, /obj/item/stack/cable_coil))
				var/obj/item/stack/cable_coil/C = P
				if(C.get_amount() >= 5)
					playsound(loc, 'sound/items/Deconstruct.ogg', 50, 1)
					if(do_after(user, 20))
						if (C.get_amount() >= 5 && state == 2)
							C.use(5)
							user << "You add cables to the frame."
							state = 3
							icon_state = "3"
				else
					user << "You need five lengths of cable to wire the AI core."
					return
		if(3)
			if(istype(P, /obj/item/weapon/wirecutters))
				if (brain)
					user << "Get that brain out of there first."
				else
					playsound(loc, 'sound/items/Wirecutter.ogg', 50, 1)
					user << "You remove the cables."
					state = 2
					icon_state = "2"
					var/obj/item/stack/cable_coil/A = new /obj/item/stack/cable_coil( loc )
					A.amount = 5

			if(istype(P, /obj/item/stack/sheet/rglass))
				var/obj/item/stack/sheet/rglass/G = P
				if(G.get_amount() >= 2)
					playsound(loc, 'sound/items/Deconstruct.ogg', 50, 1)
					if(do_after(user, 20))
						if (G.get_amount() >= 2 && state == 3)
							G.use(2)
							user << "You put in the glass panel."
							state = 4
							icon_state = "4"
				else
					user << "You need two sheets of reinforced glass to insert them into AI core."
					return

			if(istype(P, /obj/item/weapon/aiModule/core/full)) //Allows any full core boards to be applied to AI cores.
				var/obj/item/weapon/aiModule/core/M = P
				laws.clear_inherent_laws()
				for(var/templaw in M.laws)
					laws.add_inherent_law(templaw)
				usr << "Law module applied."

			if(istype(P, /obj/item/weapon/aiModule/reset/purge))
				laws.clear_inherent_laws()
				usr << "Laws cleared applied."

			if(istype(P, /obj/item/weapon/aiModule/supplied/freeform) || istype(P, /obj/item/weapon/aiModule/core/freeformcore))
				var/obj/item/weapon/aiModule/supplied/freeform/M = P
				if(M.laws[1] == "")
					return
				laws.add_inherent_law(M.laws[1])
				usr << "Added a freeform law."

			if(istype(P, /obj/item/device/mmi))
				var/obj/item/device/mmi/M = P
				if(user && ismommi(user))
					var/mob/living/silicon/robot/mommi/R = user
					if(R.keeper)
						user << "Your laws forbid you from doing this"
						return
				if(!M.brainmob)
					user << "Sticking an empty MMI into the frame would sort of defeat the purpose."
					return
				if(M.brainmob.stat == DEAD)
					user << "Sticking a dead brain into the frame would sort of defeat the purpose."
					return

				if(!M.brainmob.client)
					user << "Sticking an inactive brain into the frame would sort of defeat the purpose."
					return

				if((config) && (!config.allow_ai))
					user << "This MMI does not seem to fit."
					return

				if(jobban_isbanned(M.brainmob, "AI"))
					user << "This MMI does not seem to fit."
					return

				if(!M.brainmob.mind)
					user << "This MMI is mindless."
					return

				ticker.mode.remove_cultist(M.brainmob.mind, 1)
				ticker.mode.remove_revolutionary(M.brainmob.mind, 1)
				ticker.mode.remove_gangster(M.brainmob.mind, 1)

				user.drop_item()
				M.loc = src
				brain = M
				usr << "Added a brain."
				icon_state = "3b"

			if(istype(P, /obj/item/weapon/crowbar) && brain)
				playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
				user << "You remove the brain."
				brain.loc = loc
				brain = null
				icon_state = "3"

		if(4)
			if(istype(P, /obj/item/weapon/crowbar))
				playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
				user << "You remove the glass panel."
				state = 3
				if (brain)
					icon_state = "3b"
				else
					icon_state = "3"
				new /obj/item/stack/sheet/rglass(loc, 2)
				return

			if(istype(P, /obj/item/weapon/screwdriver))
				playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You connect the monitor."
				if(!laws.inherent.len) //If laws isn't set to null but nobody supplied a board, the AI would normally be created lawless. We don't want that.
					laws = null
				var/mob/living/silicon/ai/A = new /mob/living/silicon/ai (loc, laws, brain)
				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)
				qdel(src)

/obj/structure/AIcore/deactivated
	name = "inactive AI"
	icon = 'icons/mob/AI.dmi'
	icon_state = "ai-empty"
	anchored = 1
	state = 20//So it doesn't interact based on the above. Not really necessary.

/obj/structure/AIcore/deactivated/attackby(var/obj/item/A as obj, var/mob/user as mob, params)
	if(istype(A, /obj/item/device/aicard))//Is it?
		A.transfer_ai("INACTIVE","AICARD",src,user)
	if(istype(A, /obj/item/weapon/wrench))
		playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
		switch(anchored)
			if(0)
				if(do_after(user, 20))
					user << "You wrench the core into place."
					anchored = 1
			if(1)
				if(do_after(user, 20))
					user << "You unfasten the core."
					anchored = 0
	return

/*
This is a good place for AI-related object verbs so I'm sticking it here.
If adding stuff to this, don't forget that an AI need to cancel_camera() whenever it physically moves to a different location.
That prevents a few funky behaviors.
*/
//What operation to perform based on target, what ineraction to perform based on object used, target itself, user. The object used is src and calls this proc.
/obj/item/proc/transfer_ai(var/choice as text, var/interaction as text, var/target, var/mob/U as mob)
	if(istype(src, /obj/item/device/aicard))
		var/obj/item/device/aicard/icard = src
		if(icard.flush)
			U << "ERROR: AI flush is in progress, cannot execute transfer protocol."
			return

	switch(choice)
		if("AICORE")//AI mob.
			var/mob/living/silicon/ai/T = target
			if(!T.mind)
				U << "No intelligence patterns detected."    //No more magical carding of empty cores, AI RETURN TO BODY!!!11
				return
			switch(interaction)
				if("AICARD")
					var/obj/item/device/aicard/C = src
					if(C.contents.len)//If there is an AI on card.
						U << "Transfer failed: Existing AI found on this terminal. Remove existing AI to install a new one."
					else
						if (ticker.mode.name == "AI malfunction")
							var/datum/game_mode/malfunction/malf = ticker.mode
							for (var/datum/mind/malfai in malf.malf_ai)
								if (T.mind == malfai)
									U << "ERROR: Remote transfer interface disabled."//Do ho ho ho~
									return
						new /obj/structure/AIcore/deactivated(T.loc)//Spawns a deactivated terminal at AI location.
						T.aiRestorePowerRoutine = 0//So the AI initially has power.
						T.control_disabled = 1//Can't control things remotely if you're stuck in a card!
						T.radio_enabled = 0 	//No talking on the built-in radio for you either!
						T.loc = C//Throw AI into the card.
						C.name = "intelliCard - [T.name]"
						if (T.stat == 2)
							C.icon_state = "aicard-404"
						else
							C.icon_state = "aicard-full"
						T.cancel_camera()
						T << "You have been downloaded to a mobile storage device. Remote device connection severed."
						U << "Transfer successful: [T.name] ([rand(1000,9999)].exe) removed from host terminal and stored within local memory."

		if("INACTIVE")//Inactive AI object.
			var/obj/structure/AIcore/deactivated/T = target
			switch(interaction)
				if("AICARD")
					var/obj/item/device/aicard/C = src
					var/mob/living/silicon/ai/A = locate() in C//I love locate(). Best proc ever.
					if(A)//If AI exists on the card. Else nothing since both are empty.
						A.control_disabled = 0
						A.radio_enabled = 1
						A.loc = T.loc//To replace the terminal.
						C.icon_state = "aicard"
						C.name = "intelliCard"
						C.overlays.Cut()
						A.cancel_camera()
						A << "You have been uploaded to a stationary terminal. Remote device connection restored."
						U << "Transfer successful: [A.name] ([rand(1000,9999)].exe) installed and executed successfully. Local copy has been removed."
						qdel(T)

		if("AIFIXER")//AI Fixer terminal.
			var/obj/machinery/computer/aifixer/T = target
			switch(interaction)
				if("AICARD")
					var/obj/item/device/aicard/C = src
					if(!T.contents.len)
						if (!C.contents.len)
							U << "No AI to copy over!"//Well duh
						else for(var/mob/living/silicon/ai/A in C)
							C.icon_state = "aicard"
							C.name = "intelliCard"
							C.overlays.Cut()
							A.loc = T
							T.occupier = A
							A.control_disabled = 1
							A.radio_enabled = 0
							if (A.stat == 2)
								T.overlays += image('icons/obj/computer.dmi', "ai-fixer-404")
							else
								T.overlays += image('icons/obj/computer.dmi', "ai-fixer-full")
							T.overlays -= image('icons/obj/computer.dmi', "ai-fixer-empty")
							A.cancel_camera()
							A << "You have been uploaded to a stationary terminal. Sadly, there is no remote access from here."
							U << "Transfer successful: [A.name] ([rand(1000,9999)].exe) installed and executed successfully. Local copy has been removed."
					else
						if(!C.contents.len && T.occupier && !T.active)
							C.name = "intelliCard - [T.occupier.name]"
							T.overlays += image('icons/obj/computer.dmi', "ai-fixer-empty")
							if (T.occupier.stat == 2)
								C.icon_state = "aicard-404"
								T.overlays -= image('icons/obj/computer.dmi', "ai-fixer-404")
							else
								C.icon_state = "aicard-full"
								T.overlays -= image('icons/obj/computer.dmi', "ai-fixer-full")
							T.occupier << "You have been downloaded to a mobile storage device. Still no remote access."
							U << "Transfer successful: [T.occupier.name] ([rand(1000,9999)].exe) removed from host terminal and stored within local memory."
							T.occupier.loc = C
							T.occupier.cancel_camera()
							T.occupier = null
						else if (C.contents.len)
							U << "ERROR: Artificial intelligence detected on terminal."
						else if (T.active)
							U << "ERROR: Reconstruction in progress."
						else if (!T.occupier)
							U << "ERROR: Unable to locate artificial intelligence."


code:
/obj/machinery/computer/aifixer
	name = "\improper AI system integrity restorer"
	desc = "Used with intelliCards containing nonfunctioning AIs to restore them to working order."
	icon = 'icons/obj/computer.dmi'
	icon_state = "ai-fixer"
	req_access = list(access_captain, access_robotics, access_heads)
	var/mob/living/silicon/ai/occupier = null
	var/active = 0
	circuit = /obj/item/weapon/circuitboard/aifixer

/obj/machinery/computer/aifixer/New()
	src.overlays += image('icons/obj/computer.dmi', "ai-fixer-empty")
	..()

/obj/machinery/computer/aifixer/attackby(I as obj, user as mob, params)
	if(occupier && istype(I, /obj/item/weapon/screwdriver))
		if(stat & (NOPOWER|BROKEN))
			user << "The screws on [name]'s screen won't budge."
		else
			user << "The screws on [name]'s screen won't budge and it emits a warning beep."
		return

	if(istype(I, /obj/item/device/aicard))
		var/obj/item/device/aicard/AIcard = I
		if(stat & (NOPOWER|BROKEN))
			if(occupier)
				AIcard.transfer_ai("AIFIXER","AICARD",src,user)
				overlays.Cut()
				return
			user << "This terminal isn't functioning right now, get it working!"
			return
		AIcard.transfer_ai("AIFIXER","AICARD",src,user)
	else
		..()
	return

/obj/machinery/computer/aifixer/attack_hand(var/mob/user as mob)
	if(..())
		return
	interact(user)

/obj/machinery/computer/aifixer/interact(mob/user)

	var/dat = ""

	if (src.occupier)
		var/laws
		dat += "
Stored AI: [src.occupier.name]
"
		dat += "System integrity: [(src.occupier.health+100)/2]%
"

		if (src.occupier.laws.zeroth)
			laws += "0: [src.occupier.laws.zeroth]
"

		for (var/index = 1, index <= src.occupier.laws.ion.len, index++)
			var/law = src.occupier.laws.ion[index]
			if (length(law) > 0)
				var/num = ionnum()
				laws += "[num]: [law]
"

		var/number = 1
		for (var/index = 1, index <= src.occupier.laws.inherent.len, index++)
			var/law = src.occupier.laws.inherent[index]
			if (length(law) > 0)
				laws += "[number]: [law]
"
				number++

		for (var/index = 1, index <= src.occupier.laws.supplied.len, index++)
			var/law = src.occupier.laws.supplied[index]
			if (length(law) > 0)
				laws += "[number]: [law]
"
				number++

		dat += "Laws:
[laws]
"

		if (src.occupier.stat == 2)
			dat += "AI non-functional"
		else
			dat += "AI functional"
		if (!src.active)
			dat += {"

Begin Reconstruction"}
		else
			dat += "

Reconstruction in process, please wait.
"
	dat += {"
Close"}

	//user << browse(dat, "window=computer;size=400x500")
	//onclose(user, "computer")
	var/datum/browser/popup = new(user, "computer", "AI System Integrity Restorer", 400, 500)
	popup.set_content(dat)
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()
	return

/obj/machinery/computer/aifixer/process()
	if(..())
		src.updateDialog()
		return

/obj/machinery/computer/aifixer/Topic(href, href_list)
	if(..())
		return
	if (href_list["fix"])
		src.active = 1
		src.overlays += image('icons/obj/computer.dmi', "ai-fixer-on")
		while (src.occupier.health < 100)
			src.occupier.adjustOxyLoss(-1)
			src.occupier.adjustFireLoss(-1)
			src.occupier.adjustToxLoss(-1)
			src.occupier.adjustBruteLoss(-1)
			src.occupier.updatehealth()
			if (src.occupier.health >= 0 && src.occupier.stat == 2)
				src.occupier.stat = 0
				src.occupier.lying = 0
				dead_mob_list -= src.occupier
				living_mob_list += src.occupier
				src.overlays -= image('icons/obj/computer.dmi', "ai-fixer-404")
				src.overlays += image('icons/obj/computer.dmi', "ai-fixer-full")
			src.updateUsrDialog()
			sleep(10)
		src.active = 0
		src.overlays -= image('icons/obj/computer.dmi', "ai-fixer-on")

		src.add_fingerprint(usr)
	src.updateUsrDialog()
	return

/obj/machinery/computer/aifixer/update_icon()
	..()
	// Broken / Unpowered
	if((stat & BROKEN) || (stat & NOPOWER))
		overlays.Cut()

	// Working / Powered
	else
		if (occupier)
			switch (occupier.stat)
				if (0)
					overlays += image('icons/obj/computer.dmi', "ai-fixer-full")
				if (2)
					overlays += image('icons/obj/computer.dmi', "ai-fixer-404")
		else
			overlays += image('icons/obj/computer.dmi', "ai-fixer-empty")

license: mit


code:
/obj/machinery/computer/arcade/
	name = "random arcade"
	desc = "random arcade machine"
	icon = 'icons/obj/computer.dmi'
	icon_state = "arcade"
	var/list/prizes = list(	/obj/item/weapon/storage/box/snappops			= 2,
							/obj/item/toy/AI								= 2,
							/obj/item/clothing/under/syndicate/tacticool	= 2,
							/obj/item/toy/sword								= 2,
							/obj/item/toy/gun								= 2,
							/obj/item/toy/crossbow							= 2,
							/obj/item/weapon/storage/box/fakesyndiesuit		= 2,
							/obj/item/weapon/storage/fancy/crayons			= 2,
							/obj/item/toy/spinningtoy						= 2,
							/obj/item/toy/prize/ripley						= 1,
							/obj/item/toy/prize/fireripley					= 1,
							/obj/item/toy/prize/deathripley					= 1,
							/obj/item/toy/prize/gygax						= 1,
							/obj/item/toy/prize/durand						= 1,
							/obj/item/toy/prize/honk						= 1,
							/obj/item/toy/prize/marauder					= 1,
							/obj/item/toy/prize/seraph						= 1,
							/obj/item/toy/prize/mauler						= 1,
							/obj/item/toy/prize/odysseus					= 1,
							/obj/item/toy/prize/phazon						= 1,
							/obj/item/toy/prize/reticence					= 1,
							/obj/item/toy/cards/deck						= 2,
							/obj/item/toy/nuke								= 2,
							/obj/item/toy/minimeteor						= 2,
							/obj/item/toy/carpplushie						= 2,
							/obj/item/toy/foamblade							= 2,
							/obj/item/toy/redbutton							= 2,
							/obj/item/toy/owl								= 2,
							/obj/item/toy/griffin							= 2
							)

/obj/machinery/computer/arcade/New()
	..()
	// If it's a generic arcade machine, pick a random arcade
	// circuit board for it and make the new machine
	if(!circuit)
		var/choice = pick(typesof(/obj/item/weapon/circuitboard/arcade) - /obj/item/weapon/circuitboard/arcade)
		var/obj/item/weapon/circuitboard/CB = new choice()
		new CB.build_path(loc, CB)
		qdel(src)

/obj/machinery/computer/arcade/proc/prizevend()
	if(!contents.len)
		var/prizeselect = pickweight(prizes)
		new prizeselect(src.loc)

		if(istype(prizeselect, /obj/item/toy/gun)) //Ammo comes with the gun
			new /obj/item/toy/ammo/gun(src.loc)

		else if(istype(prizeselect, /obj/item/clothing/suit/syndicatefake)) //Helmet is part of the suit
			new	/obj/item/clothing/head/syndicatefake(src.loc)

	else
		var/atom/movable/prize = pick(contents)
		prize.loc = src.loc

/obj/machinery/computer/arcade/emp_act(severity)
	..(severity)

	if(stat & (NOPOWER|BROKEN))
		return

	var/empprize = null
	var/num_of_prizes = 0
	switch(severity)
		if(1)
			num_of_prizes = rand(1,4)
		if(2)
			num_of_prizes = rand(0,2)
	for(var/i = num_of_prizes; i > 0; i--)
		empprize = pickweight(prizes)
		new empprize(src.loc)
	explosion(src.loc, -1, 0, 1+num_of_prizes, flame_range = 1+num_of_prizes)

/obj/machinery/computer/arcade/battle
	name = "arcade machine"
	desc = "Does not support Pinball."
	icon = 'icons/obj/computer.dmi'
	icon_state = "arcade"
	circuit = /obj/item/weapon/circuitboard/arcade/battle
	var/enemy_name = "Space Villian"
	var/temp = "Winners don't use space drugs" //Temporary message, for attack messages, etc
	var/player_hp = 30 //Player health/attack points
	var/player_mp = 10
	var/enemy_hp = 45 //Enemy health/attack points
	var/enemy_mp = 20
	var/gameover = 0
	var/blocked = 0 //Player cannot attack/heal while set
	var/turtle = 0

/obj/machinery/computer/arcade/battle/New()
	..()
	var/name_action
	var/name_part1
	var/name_part2

	name_action = pick("Defeat ", "Annihilate ", "Save ", "Strike ", "Stop ", "Destroy ", "Robust ", "Romance ", "Pwn ", "Own ")

	name_part1 = pick("the Automatic ", "Farmer ", "Lord ", "Professor ", "the Cuban ", "the Evil ", "the Dread King ", "the Space ", "Lord ", "the Great ", "Duke ", "General ")
	name_part2 = pick("Melonoid", "Murdertron", "Sorcerer", "Ruin", "Jeff", "Ectoplasm", "Crushulon", "Uhangoid", "Vhakoid", "Peteoid", "slime", "Griefer", "ERPer", "Lizard Man", "Unicorn")

	src.enemy_name = replacetext((name_part1 + name_part2), "the ", "")
	src.name = (name_action + name_part1 + name_part2)

/obj/machinery/computer/arcade/battle/attack_hand(mob/user as mob)
	if(..())
		return
	user.set_machine(src)
	var/dat = "Close"
	dat += "
[src.enemy_name]
"

	dat += "

[src.temp]
"
	dat += "
Health: [src.player_hp] | Magic: [src.player_mp] | Enemy Health: [src.enemy_hp]"

	if (src.gameover)
		dat += "New Game"
	else
		dat += "Attack | "
		dat += "Heal | "
		dat += "Recharge Power"

	dat += ""

	//user << browse(dat, "window=arcade")
	//onclose(user, "arcade")
	var/datum/browser/popup = new(user, "arcade", "Space Villian 2000")
	popup.set_content(dat)
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()
	return

/obj/machinery/computer/arcade/battle/Topic(href, href_list)
	if(..())
		return

	if (!src.blocked && !src.gameover)
		if (href_list["attack"])
			src.blocked = 1
			var/attackamt = rand(2,6)
			src.temp = "You attack for [attackamt] damage!"
			src.updateUsrDialog()
			if(turtle > 0)
				turtle--

			sleep(10)
			src.enemy_hp -= attackamt
			src.arcade_action()

		else if (href_list["heal"])
			src.blocked = 1
			var/pointamt = rand(1,3)
			var/healamt = rand(6,8)
			src.temp = "You use [pointamt] magic to heal for [healamt] damage!"
			src.updateUsrDialog()
			turtle++

			sleep(10)
			src.player_mp -= pointamt
			src.player_hp += healamt
			src.blocked = 1
			src.updateUsrDialog()
			src.arcade_action()

		else if (href_list["charge"])
			src.blocked = 1
			var/chargeamt = rand(4,7)
			src.temp = "You regain [chargeamt] points"
			src.player_mp += chargeamt
			if(turtle > 0)
				turtle--

			src.updateUsrDialog()
			sleep(10)
			src.arcade_action()

	if (href_list["close"])
		usr.unset_machine()
		usr << browse(null, "window=arcade")

	else if (href_list["newgame"]) //Reset everything
		temp = "New Round"
		player_hp = 30
		player_mp = 10
		enemy_hp = 45
		enemy_mp = 20
		gameover = 0
		turtle = 0

		if(emagged)
			src.New()
			emagged = 0

	src.add_fingerprint(usr)
	src.updateUsrDialog()
	return

/obj/machinery/computer/arcade/battle/proc/arcade_action()
	if ((src.enemy_mp <= 0) || (src.enemy_hp <= 0))
		if(!gameover)
			src.gameover = 1
			src.temp = "[src.enemy_name] has fallen! Rejoice!"

			if(emagged)
				feedback_inc("arcade_win_emagged")
				new /obj/effect/spawner/newbomb/timer/syndicate(src.loc)
				new /obj/item/clothing/head/collectable/petehat(src.loc)
				message_admins("[key_name_admin(usr)] has outbombed Cuban Pete and been awarded a bomb.")
				log_game("[key_name(usr)] has outbombed Cuban Pete and been awarded a bomb.")
				src.New()
				emagged = 0
			else
				feedback_inc("arcade_win_normal")
				prizevend()

	else if (emagged && (turtle >= 4))
		var/boomamt = rand(5,10)
		src.temp = "[src.enemy_name] throws a bomb, exploding you for [boomamt] damage!"
		src.player_hp -= boomamt

	else if ((src.enemy_mp <= 5) && (prob(70)))
		var/stealamt = rand(2,3)
		src.temp = "[src.enemy_name] steals [stealamt] of your power!"
		src.player_mp -= stealamt
		src.updateUsrDialog()

		if (src.player_mp <= 0)
			src.gameover = 1
			sleep(10)
			src.temp = "You have been drained! GAME OVER"
			if(emagged)
				feedback_inc("arcade_loss_mana_emagged")
				usr.gib()
			else
				feedback_inc("arcade_loss_mana_normal")

	else if ((src.enemy_hp <= 10) && (src.enemy_mp > 4))
		src.temp = "[src.enemy_name] heals for 4 health!"
		src.enemy_hp += 4
		src.enemy_mp -= 4

	else
		var/attackamt = rand(3,6)
		src.temp = "[src.enemy_name] attacks for [attackamt] damage!"
		src.player_hp -= attackamt

	if ((src.player_mp <= 0) || (src.player_hp <= 0))
		src.gameover = 1
		src.temp = "You have been crushed! GAME OVER"
		if(emagged)
			feedback_inc("arcade_loss_hp_emagged")
			usr.gib()
		else
			feedback_inc("arcade_loss_hp_normal")

	src.blocked = 0
	return

/obj/machinery/computer/arcade/battle/emag_act(mob/user as mob)
	if(!emagged)
		temp = "If you die in the game, you die for real!"
		player_hp = 30
		player_mp = 10
		enemy_hp = 45
		enemy_mp = 20
		gameover = 0
		blocked = 0

		emagged = 1

		enemy_name = "Cuban Pete"
		name = "Outbomb Cuban Pete"

		src.updateUsrDialog()

/obj/machinery/computer/arcade/orion_trail
	name = "The Orion Trail"
	desc = "Learn how our ancestors got to Orion, and have fun in the process!"
	icon = 'icons/obj/computer.dmi'
	icon_state = "arcade"
	circuit = /obj/item/weapon/circuitboard/arcade/orion_trail
	var/engine = 0
	var/hull = 0
	var/electronics = 0
	var/food = 80
	var/fuel = 60
	var/turns = 4
	var/playing = 0
	var/gameover = 0
	var/alive = 4
	var/eventdat = null
	var/event = null
	var/list/settlers = list("Harry","Larry","Bob")
	var/list/events = list("Raiders"				= 3,
						   "Interstellar Flux"		= 1,
						   "Illness"				= 3,
						   "Breakdown"				= 2,
						   "Malfunction"			= 2,
						   "Collision"              = 1
						   )
	var/list/stops = list()
	var/list/stopblurbs = list()

/obj/machinery/computer/arcade/orion_trail/New()
	..()
	// Sets up the main trail
	stops = list("Pluto","Asteroid Belt","Proxima Centauri","Dead Space","Rigel Prime","Tau Ceti Beta","Black Hole","Space Outpost Beta-9","Orion Prime")
	stopblurbs = list(
		"Pluto, long since occupied with long-range sensors and scanners, stands ready to, and indeed continues to probe the far reaches of the galaxy.",
		"At the edge of the Sol system lies a treacherous asteroid belt. Many have been crushed by stray asteroids and misguided judgement.",
		"The nearest star system to Sol, in ages past it stood as a reminder of the boundaries of sub-light travel, now a low-population sanctuary for adventurers and traders.",
		"This region of space is particularly devoid of matter. Such low-density pockets are known to exist, but the vastness of it is astounding.",
		"Rigel Prime, the center of the Rigel system, burns hot, basking its planetary bodies in warmth and radiation.",
		"Tau Ceti Beta has recently become a waypoint for colonists headed towards Orion. There are many ships and makeshift stations in the vicinity.",
		"Sensors indicate that a black hole's gravitational field is affecting the region of space we were headed through. We could stay of course, but risk of being overcome by its gravity, or we could change course to go around, which will take longer.",
		"You have come into range of the first man-made structure in this region of space. It has been constructed not by travellers from Sol, but by colonists from Orion. It stands as a monument to the colonists' success.",
		"You have made it to Orion! Congratulations! Your crew is one of the few to start a new foothold for mankind!"
		)

/obj/machinery/computer/arcade/orion_trail/proc/newgame()
	// Set names of settlers in crew
	settlers = list()
	var/choice = null
	for(var/i = 1; i <= 3; i++)
		if(prob(50))
			choice = pick(first_names_male)
		else
			choice = pick(first_names_female)
		settlers += choice
	settlers += "[usr]"
	// Re-set items to defaults
	engine = 1
	hull = 1
	electronics = 1
	food = 80
	fuel = 60
	alive = 4
	turns = 1
	event = null
	playing = 1
	gameover = 0

/obj/machinery/computer/arcade/orion_trail/attack_hand(mob/user as mob)
	if(..())
		return
	if(fuel <= 0 || food <=0 || settlers.len == 0)
		gameover = 1
		event = null
	user.set_machine(src)
	var/dat = ""
	if(gameover)
		dat = "
Game Over
"
		dat += "Like many before you, your crew never made it to Orion, lost to space...
Forever."
		if(settlers.len == 0)
			dat += "
Your entire crew died, your ship joins the fleet of ghost-ships littering the galaxy."
		else
			if(food <= 0)
				dat += "
You ran out of food and starved."
			if(fuel <= 0)
				dat += "
You ran out of fuel, and drift, slowly, into a star."
		dat += "

OK...
"
	else if(event)
		dat = eventdat
	else if(playing)
		var/title = stops[turns]
		var/subtext = stopblurbs[turns]
		dat = "
[title]
"
		dat += "[subtext]"
		dat += "
Crew:
"
		dat += english_list(settlers)
		dat += "
Food: [food] | Fuel: [fuel]"
		dat += "
Engine Parts: [engine] | Hull Panels: [hull] | Electronics: [electronics]
"
		if(turns == 7)
			dat += "
Go Around Continue
"
		else
			dat += "
Continue
"
		dat += "
Close
"
	else
		dat = "
The Orion Trail
"
		dat += "

Experience the journey of your ancestors!

"
		dat += "New Game"
		dat += "
Close
"
	var/datum/browser/popup = new(user, "arcade", "The Orion Trail")
	popup.set_content(dat)
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()
	return

/obj/machinery/computer/arcade/orion_trail/Topic(href, href_list)
	if(..())
		return
	if(href_list["close"])
		usr.unset_machine()
		usr << browse(null, "window=arcade")
	else if (href_list["continue"]) //Continue your travels
		if(turns >= 9)
			win()
		else if(turns == 2)
			if(prob(30))
				event = "Collision"
				event()
				food -= alive*2
				fuel -= 5
				turns += 1
			else
				food -= alive*2
				fuel -= 5
				turns += 1
				if(prob(75))
					event = pickweight(events)
					event()
		else
			food -= alive*2
			fuel -= 5
			turns += 1
			if(prob(75))
				event = pickweight(events)
				event()
	else if(href_list["newgame"]) //Reset everything
		newgame()
	else if(href_list["menu"]) //back to the main menu
		playing = 0
		event = null
		gameover = 0
		food = 80
		fuel = 60
		settlers = list("Harry","Larry","Bob")
	else if(href_list["slow"]) //slow down
		food -= alive*2
		fuel -= 5
		event = null
	else if(href_list["pastblack"]) //slow down
		food -= (alive*2)*3
		fuel -= 15
		turns += 1
		event = null
	else if(href_list["useengine"]) //use parts
		engine -= 1
		event = null
	else if(href_list["useelec"]) //use parts
		electronics -= 1
		event = null
	else if(href_list["usehull"]) //use parts
		hull -= 1
		event = null
	else if(href_list["wait"]) //wait 3 days
		food -= (alive*2)*3
		event = null
	else if(href_list["keepspeed"]) //keep speed
		if(prob(75))
			event = "Breakdown"
			event()
		else
			event = null
	else if(href_list["blackhole"]) //keep speed past a black hole
		if(prob(75))
			event = "BlackHole"
			event()
		else
			event = null
			turns += 1
	else if(href_list["holedeath"])
		gameover = 1
		event = null
	else if(href_list["eventclose"]) //end an event
		event = null

	src.add_fingerprint(usr)
	src.updateUsrDialog()
	return

/obj/machinery/computer/arcade/orion_trail/proc/event()
	eventdat = "
[event]
"
	if(event == "Raiders")
		eventdat += "Raiders have come aboard your ship!"
		if(prob(50))
			var/sfood = rand(1,10)
			var/sfuel = rand(1,10)
			food -= sfood
			fuel -= sfuel
			eventdat += "
They have stolen [sfood] Food and [sfuel] Fuel."
		else if(prob(10))
			var/deadname = pick_n_take(settlers)
			eventdat += "
[deadname] tried to fight back but was killed."
			alive -= 1
		else
			eventdat += "
Fortunately you fended them off without any trouble."
		eventdat += "
Continue
"
		eventdat += "
Close
"

	else if(event == "Interstellar Flux")
		eventdat += "This region of space is highly turbulent.
If we go slowly we may avoid more damage, but if we keep our speed we won't waste supplies."
		eventdat += "
What will you do?"
		eventdat += "
Slow Down Continue
"
		eventdat += "
Close
"

	else if(event == "Illness")
		eventdat += "A deadly illness has been contracted!"
		var/deadname = pick_n_take(settlers)
		eventdat += "
[deadname] was killed by the disease."
		alive -= 1
		eventdat += "
Continue
"
		eventdat += "
Close
"

	else if(event == "Breakdown")
		eventdat += "Oh no! The engine has broken down!"
		eventdat += "
You can repair it with an engine part, or you can make repairs for 3 days."
		if(engine >= 1)
			eventdat += "
Use PartWait
"
		else
			eventdat += "
Wait
"
		eventdat += "
Close
"

	else if(event == "Malfunction")
		eventdat += "The ship's systems are malfunctioning!"
		eventdat += "
You can replace the broken electronics with spares, or you can spend 3 days troubleshooting the AI."
		if(electronics >= 1)
			eventdat += "
Use PartWait
"
		else
			eventdat += "
Wait
"
		eventdat += "
Close
"

	else if(event == "Collision")
		eventdat += "Something hit us! Looks like there's some hull damage."
		if(prob(25))
			var/sfood = rand(5,15)
			var/sfuel = rand(5,15)
			food -= sfood
			fuel -= sfuel
			eventdat += "
[sfood] Food and [sfuel] Fuel was vented out into space."
		if(prob(10))
			var/deadname = pick_n_take(settlers)
			eventdat += "
[deadname] was killed by rapid depressurization."
			alive -= 1
		eventdat += "
You can repair the damage with hull plates, or you can spend the next 3 days welding scrap together."
		if(hull >= 1)
			eventdat += "
Use PartWait
"
		else
			eventdat += "
Wait
"
		eventdat += "
Close
"

	else if(event == "BlackHole")
		eventdat += "You were swept away into the black hole."
		eventdat += "
Oh...
"
		eventdat += "
Close
"
		settlers = list()

/obj/machinery/computer/arcade/orion_trail/proc/win()
	playing = 0
	prizevend()


code:
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31

/obj/machinery/computer/atmos_alert
	name = "atmospheric alert console"
	desc = "Used to access the station's atmospheric sensors."
	circuit = /obj/item/weapon/circuitboard/atmos_alert
	icon_state = "alert:0"
	var/list/priority_alarms = list()
	var/list/minor_alarms = list()
	var/receive_frequency = 1437
	var/datum/radio_frequency/radio_connection

/obj/machinery/computer/atmos_alert/initialize()
	..()
	set_frequency(receive_frequency)

/obj/machinery/computer/atmos_alert/Destroy()
	if(radio_controller)
		radio_controller.remove_object(src, receive_frequency)
	..()

/obj/machinery/computer/atmos_alert/receive_signal(datum/signal/signal)
	if(!signal || signal.encryption) return

	var/zone = signal.data["zone"]
	var/severity = signal.data["alert"]

	if(!zone || !severity) return

	minor_alarms -= zone
	priority_alarms -= zone
	if(severity=="severe")
		priority_alarms += zone
	else if (severity=="minor")
		minor_alarms += zone
	update_icon()
	return

/obj/machinery/computer/atmos_alert/proc/set_frequency(new_frequency)
	radio_controller.remove_object(src, receive_frequency)
	receive_frequency = new_frequency
	radio_connection = radio_controller.add_object(src, receive_frequency, RADIO_ATMOSIA)

/obj/machinery/computer/atmos_alert/attack_hand(mob/user)
	if(..(user))
		return
	interact(user) //UpdateDialog() is calling /interact each tick, not attack_hand()

/obj/machinery/computer/atmos_alert/interact(mob/user)
	var/datum/browser/popup = new(user, "computer", name)
	popup.set_content(return_text())
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()

/obj/machinery/computer/atmos_alert/process()
	if(..())
		src.updateDialog()

/obj/machinery/computer/atmos_alert/update_icon()
	set_light(light_range_on, light_power_on)
	if(stat & BROKEN)
		icon_state = "alert:b"
		return
	else if (stat & NOPOWER)
		icon_state = "alert:O"
		set_light(0)
		return
	else if(priority_alarms.len)
		icon_state = "alert:2"

	else if(minor_alarms.len)
		icon_state = "alert:1"

	else
		icon_state = "alert:0"
	return

/obj/machinery/computer/atmos_alert/proc/return_text()
	var/priority_text
	var/minor_text

	if(priority_alarms.len)
		for(var/zone in priority_alarms)
			priority_text += "[format_text(zone)]  X
"
	else
		priority_text = "No priority alerts detected.
"

	if(minor_alarms.len)
		for(var/zone in minor_alarms)
			minor_text += "[format_text(zone)]  X
"
	else
		minor_text = "No minor alerts detected.
"

	var/output = {"
Priority Alerts:

[priority_text]

Minor Alerts:

[minor_text]

"}

	return output

/obj/machinery/computer/atmos_alert/Topic(href, href_list)
	if(..())
		return

	if(href_list["priority_clear"])
		var/removing_zone = href_list["priority_clear"]
		for(var/zone in priority_alarms)
			if(ckey(zone) == removing_zone)
				usr << "\green Priority Alert for [format_text(zone)] cleared."
				priority_alarms -= zone

	if(href_list["minor_clear"])
		var/removing_zone = href_list["minor_clear"]
		for(var/zone in minor_alarms)
			if(ckey(zone) == removing_zone)
				usr << "\green Minor Alert for [format_text(zone)] cleared."
				minor_alarms -= zone
	update_icon()
	return


code:
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31

/obj/structure/computerframe
	density = 1
	anchored = 0
	name = "computer-frame"
	icon = 'icons/obj/stock_parts.dmi'
	icon_state = "0"
	var/state = 0
	var/obj/item/weapon/circuitboard/circuit = null
//	weight = 1.0E8

/obj/item/weapon/circuitboard
	density = 0
	anchored = 0
	w_class = 2.0
	name = "circuit board"
	icon = 'icons/obj/module.dmi'
	icon_state = "id_mod"
	item_state = "electronic"
	origin_tech = "programming=2"
	var/frequency = null
	var/build_path = null
	var/board_type = "computer"
	var/list/req_components = null
	var/powernet = null
	var/list/records = null
	var/frame_desc = null

/obj/item/weapon/circuitboard/large_tank_control
	name = "circuit board (Large Tank Control)"
	build_path = /obj/machinery/computer/general_air_control/large_tank_control
	origin_tech = "programming=2;engineering=3;materials=2"
/obj/item/weapon/circuitboard/turbine_computer
	name = "circuit board (Turbine Computer)"
	build_path = /obj/machinery/computer/turbine_computer
	origin_tech = "programming=4;engineering=4;powerstorage=4"
/obj/item/weapon/circuitboard/telesci_console
	name = "circuit board (Telescience Console)"
	build_path = /obj/machinery/computer/telescience
	origin_tech = "programming=3;bluespace=2"
/obj/item/weapon/circuitboard/message_monitor
	name = "circuit board (Message Monitor)"
	build_path = /obj/machinery/computer/message_monitor
	origin_tech = "programming=3"
/obj/item/weapon/circuitboard/security
	name = "circuit board (Security)"
	build_path = /obj/machinery/computer/security
/obj/item/weapon/circuitboard/aicore
	name = "circuit board (AI core)"
	origin_tech = "programming=4;biotech=2"
	board_type = "other"
/obj/item/weapon/circuitboard/aiupload
	name = "circuit board (AI Upload)"
	build_path = /obj/machinery/computer/upload/ai
	origin_tech = "programming=4"
/obj/item/weapon/circuitboard/borgupload
	name = "circuit board (Cyborg Upload)"
	build_path = /obj/machinery/computer/upload/borg
	origin_tech = "programming=4"
/obj/item/weapon/circuitboard/med_data
	name = "circuit board (Medical Records Console)"
	build_path = /obj/machinery/computer/med_data
/obj/item/weapon/circuitboard/pandemic
	name = "circuit board (PanD.E.M.I.C. 2200)"
	build_path = /obj/machinery/computer/pandemic
	origin_tech = "programming=2;biotech=2"
/obj/item/weapon/circuitboard/scan_consolenew
	name = "circuit board (DNA Machine)"
	build_path = /obj/machinery/computer/scan_consolenew
	origin_tech = "programming=2;biotech=2"
/obj/item/weapon/circuitboard/communications
	name = "circuit board (Communications)"
	build_path = /obj/machinery/computer/communications
	origin_tech = "programming=2;magnets=2"
	var/lastTimeUsed = 0
/obj/item/weapon/circuitboard/communications/proc/cooldownLeft(deciseconds=600)
	return max(deciseconds - (world.time - lastTimeUsed), 0)

/obj/item/weapon/circuitboard/card
	name = "circuit board (ID Console)"
	build_path = /obj/machinery/computer/card
/obj/item/weapon/circuitboard/card/centcom
	name = "circuit board (Centcom ID Console)"
	build_path = /obj/machinery/computer/card/centcom
//obj/item/weapon/circuitboard/shield
//	name = "Circuit board (Shield Control)"
//	build_path = /obj/machinery/computer/stationshield
/obj/item/weapon/circuitboard/teleporter
	name = "circuit board (Teleporter)"
	build_path = /obj/machinery/computer/teleporter
	origin_tech = "programming=2;bluespace=2"
/obj/item/weapon/circuitboard/secure_data
	name = "circuit board (Security Records Console)"
	build_path = /obj/machinery/computer/secure_data
/obj/item/weapon/circuitboard/stationalert
	name = "circuit board (Station Alerts)"
	build_path = /obj/machinery/computer/station_alert
/*/obj/item/weapon/circuitboard/atmospheresiphonswitch
	name = "circuit board (Atmosphere siphon control)"
	build_path = /obj/machinery/computer/atmosphere/siphonswitch*/
/obj/item/weapon/circuitboard/air_management
	name = "circuit board (Atmospheric monitor)"
	build_path = /obj/machinery/computer/general_air_control
/obj/item/weapon/circuitboard/injector_control
	name = "circuit board (Injector control)"
	build_path = /obj/machinery/computer/general_air_control/fuel_injection
/obj/item/weapon/circuitboard/atmos_alert
	name = "circuit board (Atmospheric Alert)"
	build_path = /obj/machinery/computer/atmos_alert
/obj/item/weapon/circuitboard/pod
	name = "circuit board (Massdriver control)"
	build_path = /obj/machinery/computer/pod
/obj/item/weapon/circuitboard/robotics
	name = "circuit board (Robotics Control)"
	build_path = /obj/machinery/computer/robotics
	origin_tech = "programming=3"
/obj/item/weapon/circuitboard/cloning
	name = "Circuit board (Cloning Console)"
	build_path = /obj/machinery/computer/cloning
	origin_tech = "programming=3;biotech=3"
/obj/item/weapon/circuitboard/arcade/battle
	name = "circuit board (Arcade Battle)"
	build_path = /obj/machinery/computer/arcade/battle
	origin_tech = "programming=1"
/obj/item/weapon/circuitboard/arcade/orion_trail
	name = "circuit board (Orion_Trail)"
	build_path = /obj/machinery/computer/arcade/orion_trail
/obj/item/weapon/circuitboard/turbine_control
	name = "circuit board (Turbine control)"
	build_path = /obj/machinery/computer/turbine_computer
/obj/item/weapon/circuitboard/solar_control
	name = "circuit board (Solar Control)"  //name fixed 250810
	build_path = /obj/machinery/power/solar_control
	origin_tech = "programming=2;powerstorage=2"
/obj/item/weapon/circuitboard/powermonitor
	name = "circuit board (Power Monitor)"  //name fixed 250810
	build_path = /obj/machinery/computer/monitor
/obj/item/weapon/circuitboard/olddoor
	name = "circuit board (DoorMex)"
	build_path = /obj/machinery/computer/pod/old
/obj/item/weapon/circuitboard/syndicatedoor
	name = "circuit board (ProComp Executive)"
	build_path = /obj/machinery/computer/pod/old/syndicate
/obj/item/weapon/circuitboard/swfdoor
	name = "circuit board (Magix)"
	build_path = /obj/machinery/computer/pod/old/swf
/obj/item/weapon/circuitboard/prisoner
	name = "circuit board (Prisoner Management Console)"
	build_path = /obj/machinery/computer/prisoner
/obj/item/weapon/circuitboard/rdconsole
	name = "circuit Board (RD Console)"
	build_path = /obj/machinery/computer/rdconsole/core
/obj/item/weapon/circuitboard/mecha_control
	name = "circuit Board (Exosuit Control Console)"
	build_path = /obj/machinery/computer/mecha
/obj/item/weapon/circuitboard/rdservercontrol
	name = "circuit Board (R&D Server Control)"
	build_path = /obj/machinery/computer/rdservercontrol
/obj/item/weapon/circuitboard/crew
	name = "circuit board (Crew Monitoring Console)"
	build_path = /obj/machinery/computer/crew
	origin_tech = "programming=3;biotech=2;magnets=2"
/obj/item/weapon/circuitboard/mech_bay_power_console
	name = "circuit board (Mech Bay Power Control Console)"
	build_path = /obj/machinery/computer/mech_bay_power_console
	origin_tech = "programming=2;powerstorage=3"
/obj/item/weapon/circuitboard/ordercomp
	name = "circuit board (Supply Ordering Console)"
	build_path = /obj/machinery/computer/ordercomp
/obj/item/weapon/circuitboard/supplycomp
	name = "circuit board (Supply shuttle console)"
	build_path = /obj/machinery/computer/supplycomp
	origin_tech = "programming=3"
	var/contraband_enabled = 0
/obj/item/weapon/circuitboard/operating
	name = "circuit board (Operating Computer)"
	build_path = /obj/machinery/computer/operating
	origin_tech = "programming=2;biotech=2"
/obj/item/weapon/circuitboard/mining
	name = "circuit board (Outpost Status Display)"
	build_path = /obj/machinery/computer/security/mining
/obj/item/weapon/circuitboard/comm_monitor
	name = "circuit board (Telecommunications Monitor)"
	build_path = /obj/machinery/computer/telecomms/monitor
	origin_tech = "programming=3"
/obj/item/weapon/circuitboard/comm_server
	name = "circuit board (Telecommunications Server Monitor)"
	build_path = /obj/machinery/computer/telecomms/server
	origin_tech = "programming=3"
/obj/item/weapon/circuitboard/comm_traffic
	name = "circuitboard (Telecommunications Traffic Control)"
	build_path = /obj/machinery/computer/telecomms/traffic
	origin_tech = "programming=3"
/*/obj/item/weapon/circuitboard/curefab
	name = "circuit board (Cure fab)"
	build_path = /obj/machinery/computer/curer
/obj/item/weapon/circuitboard/splicer
	name = "circuit board (Disease Splicer)"
	build_path = /obj/machinery/computer/diseasesplicer*/
/obj/item/weapon/circuitboard/shuttle
	name = "circuit board (Shuttle)"
	build_path = /obj/machinery/computer/shuttle
	var/shuttleId
	var/possible_destinations = ""
/obj/item/weapon/circuitboard/labor_shuttle
	name = "circuit Board (Labor Shuttle)"
	build_path = /obj/machinery/computer/shuttle/labor
/obj/item/weapon/circuitboard/labor_shuttle/one_way
	name = "circuit Board (Prisoner Shuttle Console)"
	build_path = /obj/machinery/computer/shuttle/labor/one_way
/obj/item/weapon/circuitboard/ferry
	name = "circuit Board (Transport Ferry)"
	build_path = /obj/machinery/computer/shuttle/ferry
/obj/item/weapon/circuitboard/ferry/request
	name = "circuit Board (Transport Ferry Console)"
	build_path = /obj/machinery/computer/shuttle/ferry/request
/obj/item/weapon/circuitboard/white_ship
	name = "circuit Board (White Ship)"
	build_path = /obj/machinery/computer/shuttle/white_ship
/obj/item/weapon/circuitboard/mining_shuttle
	name = "circuit Board (Mining Shuttle)"
	build_path = /obj/machinery/computer/shuttle/mining
/obj/item/weapon/circuitboard/research_shuttle
	name = "circuit Board (Research Shuttle)"
	build_path = /obj/machinery/computer/shuttle/research
/obj/item/weapon/circuitboard/HolodeckControl // Not going to let people get this, but it's just here for future
	name = "circuit board (Holodeck Control)"
	build_path = /obj/machinery/computer/HolodeckControl
	origin_tech = "programming=4"
/obj/item/weapon/circuitboard/aifixer
	name = "circuit board (AI Integrity Restorer)"
	build_path = /obj/machinery/computer/aifixer
	origin_tech = "programming=3;biotech=2"
/obj/item/weapon/circuitboard/area_atmos
	name = "circuit board (Area Air Control)"
	build_path = /obj/machinery/computer/area_atmos
/*/obj/item/weapon/circuitboard/prison_shuttle
	name = "circuit board (Prison Shuttle)"
	build_path = /obj/machinery/computer/prison_shuttle*/
/obj/item/weapon/circuitboard/slot_machine
	name = "circuit board (Slot Machine)"
	build_path = /obj/machinery/computer/slot_machine
	origin_tech = "programming=1"
/obj/item/weapon/circuitboard/libraryconsole
	name = "circuit board (Library Visitor Console)"
	build_path = /obj/machinery/computer/libraryconsole
	origin_tech = "programming=1"

/obj/item/weapon/circuitboard/supplycomp/attackby(obj/item/I as obj, mob/user as mob, params)
	if(istype(I,/obj/item/device/multitool))
		var/catastasis = src.contraband_enabled
		var/opposite_catastasis
		if(catastasis)
			opposite_catastasis = "STANDARD"
			catastasis = "BROAD"
		else
			opposite_catastasis = "BROAD"
			catastasis = "STANDARD"

		switch( alert("Current receiver spectrum is set to: [catastasis]","Multitool-Circuitboard interface","Switch to [opposite_catastasis]","Cancel") )
		//switch( alert("Current receiver spectrum is set to: " {(src.contraband_enabled) ? ("BROAD") : ("STANDARD")} , "Multitool-Circuitboard interface" , "Switch to " {(src.contraband_enabled) ? ("STANDARD") : ("BROAD")}, "Cancel") )
			if("Switch to STANDARD","Switch to BROAD")
				src.contraband_enabled = !src.contraband_enabled

			if("Cancel")
				return
			else
				user << "DERP! BUG! Report this (And what you were doing to cause it) to Agouri"
	return

/obj/item/weapon/circuitboard/rdconsole/attackby(obj/item/I as obj, mob/user as mob, params)
	if(istype(I,/obj/item/weapon/screwdriver))
		if(build_path == /obj/machinery/computer/rdconsole/core)
			name = "circuit board (RD Console - Robotics)"
			build_path = /obj/machinery/computer/rdconsole/robotics
			user << "Access protocols successfully updated."
		else
			name = "circuit board (RD Console)"
			build_path = /obj/machinery/computer/rdconsole/core
			user << "Defaulting access protocols."
	return

/obj/item/weapon/circuitboard/libraryconsole/attackby(obj/item/I as obj, mob/user as mob, params)
	if(istype(I,/obj/item/weapon/screwdriver))
		if(build_path == /obj/machinery/computer/libraryconsole/bookmanagement)
			name = "circuit board (Library Visitor Console)"
			build_path = /obj/machinery/computer/libraryconsole
			user << "Defaulting access protocols."
		else
			name = "circuit board (Book Inventory Management Console)"
			build_path = /obj/machinery/computer/libraryconsole/bookmanagement
			user << "Access protocols successfully updated."
	return

/obj/item/weapon/circuitboard/shuttle/attackby(obj/item/I as obj, mob/user as mob, params)
	if(istype(I, /obj/item/device/multitool))
		var/chosen_id = round(input(usr, "Choose an ID number (-1 for reset):", "Input an Integer", null) as num|null)
		if(chosen_id >= 0)
			shuttleId = chosen_id
		else
			shuttleId = initial(shuttleId)
	return

/obj/structure/computerframe/attackby(obj/item/P as obj, mob/user as mob, params)
	add_fingerprint(user)
	switch(state)
		if(0)
			if(istype(P, /obj/item/weapon/wrench))
				playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
				user << "You start wrenching the frame into place."
				if(do_after(user, 20))
					user << "You've wrenched the frame into place."
					anchored = 1
					state = 1
			if(istype(P, /obj/item/weapon/weldingtool))
				var/obj/item/weapon/weldingtool/WT = P
				if(!WT.remove_fuel(0, user))
					if(!WT.isOn())
						user << "The welding tool must be on to complete this task."
					return
				playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
				user << "You start deconstructing the frame."
				if(do_after(user, 20))
					if(!src || !WT.isOn()) return
					user << "You've deconstructed the frame."
					var/obj/item/stack/sheet/metal/M = new (loc, 5)
					M.add_fingerprint(user)
					qdel(src)
		if(1)
			if(istype(P, /obj/item/weapon/wrench))
				playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
				user << "You start to unfasten the frame."
				if(do_after(user, 20))
					user << "You've unfastened the frame."
					anchored = 0
					state = 0
			if(istype(P, /obj/item/weapon/circuitboard) && !circuit)
				var/obj/item/weapon/circuitboard/B = P
				if(B.board_type == "computer")
					playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
					user << "You place the circuit board inside the frame."
					icon_state = "1"
					circuit = P
					user.drop_item()
					circuit.add_fingerprint(user)
					P.loc = null
				else
					user << "This frame does not accept circuit boards of this type!"
			if(istype(P, /obj/item/weapon/screwdriver) && circuit)
				playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You screw the circuit board into place."
				state = 2
				icon_state = "2"
			if(istype(P, /obj/item/weapon/crowbar) && circuit)
				playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
				user << "You remove the circuit board."
				state = 1
				icon_state = "0"
				circuit.loc = src.loc
				circuit.add_fingerprint(user)
				circuit = null
		if(2)
			if(istype(P, /obj/item/weapon/screwdriver) && circuit)
				playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You unfasten the circuit board."
				state = 1
				icon_state = "1"
			if(istype(P, /obj/item/stack/cable_coil))
				var/obj/item/stack/cable_coil/C = P
				if(C.get_amount() >= 5)
					playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
					user << "You start adding cables to the frame."
					if(do_after(user, 20))
						if(C.get_amount() >= 5 && state == 2)
							C.use(5)
							user << "You've added cables to the frame."
							state = 3
							icon_state = "3"
				else
					user << "You need five lengths of cable to wire the frame."
		if(3)
			if(istype(P, /obj/item/weapon/wirecutters))
				playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
				user << "You remove the cables."
				state = 2
				icon_state = "2"
				var/obj/item/stack/cable_coil/A = new (loc)
				A.amount = 5
				A.add_fingerprint(user)

			if(istype(P, /obj/item/stack/sheet/glass))
				var/obj/item/stack/sheet/glass/G = P
				if(G.get_amount() < 2)
					user << "You need two glass sheets to continue construction."
					return
				else
					playsound(src.loc, 'sound/items/Deconstruct.ogg', 50, 1)
					user << "You start to put in the glass panel."
					if(do_after(user, 20))
						if(G.get_amount() >= 2 && state == 3)
							G.use(2)
							user << "You've put in the glass panel."
							state = 4
							src.icon_state = "4"
		if(4)
			if(istype(P, /obj/item/weapon/crowbar))
				playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
				user << "You remove the glass panel."
				state = 3
				icon_state = "3"
				var/obj/item/stack/sheet/glass/G = new (loc, 2)
				G.add_fingerprint(user)
			if(istype(P, /obj/item/weapon/screwdriver))
				playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
				user << "You connect the monitor."
				var/obj/B = new src.circuit.build_path (src.loc, circuit)
				transfer_fingerprints_to(B)
				qdel(src)


code:
/obj/machinery/computer/security
	name = "security camera console"
	desc = "Used to access the various cameras on the station."
	icon_state = "cameras"
	circuit = /obj/item/weapon/circuitboard/security
	var/obj/machinery/camera/current = null
	var/last_pic = 1.0
	var/list/network = list("SS13")
	var/mapping = 0//For the overview file, interesting bit of code.

/obj/machinery/computer/security/check_eye(var/mob/user as mob)
	if ((get_dist(user, src) > 1 || user.eye_blind || !( current ) || !( current.status )) && (!istype(user, /mob/living/silicon)))
		return null
	var/list/viewing = viewers(src)
	if((istype(user,/mob/living/silicon/robot)) && (!(viewing.Find(user))))
		return null
	user.reset_view(current)
	return 1

/obj/machinery/computer/security/attack_hand(var/mob/user as mob)
	if(!stat)

		if (!network)
			ERROR("A computer lacks a network at [x],[y],[z].")
			return
		if (!(istype(network,/list)))
			ERROR("The computer at [x],[y],[z] has a network that is not a list!")
			return

		if(..())
			return

		var/list/L = list()
		for (var/obj/machinery/camera/C in cameranet.cameras)
			if((z > ZLEVEL_SPACEMAX || C.z > ZLEVEL_SPACEMAX) && (C.z != z))//if on away mission, can only recieve feed from same z_level cameras
				continue
			L.Add(C)

		camera_sort(L)

		var/list/D = list()
		D["Cancel"] = "Cancel"
		for(var/obj/machinery/camera/C in L)
			if(!C.network)
				ERROR("[C.c_tag] has no camera network.")
				continue
			if(!(istype(C.network,/list)))
				ERROR("[C.c_tag]'s camera network is not a list!")
				continue
			var/list/tempnetwork = C.network&network
			if(tempnetwork.len)
				D[text("[][]", C.c_tag, (C.status ? null : " (Deactivated)"))] = C

		var/t = input(user, "Which camera should you change to?") as null|anything in D
		if(!t)
			user.unset_machine()
			user.reset_view(null)
			return 0

		var/obj/machinery/camera/C = D[t]

		if(t == "Cancel")
			user.unset_machine()
			user.reset_view(null)
			return 0

		if(C)
			if ((get_dist(user, src) > 1 || user.machine != src || user.eye_blind || !( C.can_use() )) && (!istype(user, /mob/living/silicon/ai)))
				if(!C.can_use() && !isAI(user))
					src.current = null
				return 0
			else
				if(isAI(user))
					var/mob/living/silicon/ai/A = user
					A.eyeobj.setLoc(get_turf(C))
					A.client.eye = A.eyeobj
				else
					src.current = C
					use_power(50)

				spawn(5)
					attack_hand(user)
		return

/obj/machinery/computer/security/telescreen
	name = "\improper Telescreen"
	desc = "Used for watching an empty arena."
	icon = 'icons/obj/stationobjs.dmi'
	icon_state = "telescreen"
	network = list("thunder")
	density = 0
	circuit = null

/obj/machinery/computer/security/telescreen/update_icon()
	icon_state = initial(icon_state)
	set_light(light_range_on, light_power_on)
	if(stat & BROKEN)
		icon_state += "b"
	return

/obj/machinery/computer/security/telescreen/entertainment
	name = "entertainment monitor"
	desc = "Damn, they better have the /tg/ channel on these things."
	icon = 'icons/obj/status_display.dmi'
	icon_state = "entertainment"
	network = list("thunder")
	density = 0
	circuit = null

/obj/machinery/computer/security/wooden_tv
	name = "security camera monitor"
	desc = "An old TV hooked into the stations camera network."
	icon_state = "security_det"

/obj/machinery/computer/security/mining
	name = "outpost camera console"
	desc = "Used to access the various cameras on the outpost."
	icon_state = "miningcameras"
	network = list("MINE")
	circuit = "/obj/item/weapon/circuitboard/mining"


code:
/obj/machinery/computer/camera_advanced
	name = "advanced camera console"
	desc = "Used to access the various cameras on the station."
	icon_state = "cameras"
	//circuit = /obj/item/weapon/circuitboard/security
	var/mob/camera/aiEye/remote/eyeobj
	var/mob/living/carbon/human/current_user = null
	var/list/networks = list("SS13")
	var/datum/action/camera_off/off_action = new
	var/datum/action/camera_jump/jump_action = new

/obj/machinery/computer/camera_advanced/proc/CreateEye()
	eyeobj = new()
	eyeobj.origin = src

/obj/machinery/computer/camera_advanced/proc/GrantActions(var/mob/living/carbon/user)
	off_action.target = user
	off_action.Grant(user)
	jump_action.target = user
	jump_action.Grant(user)

/obj/machinery/computer/camera_advanced/check_eye(var/mob/user as mob)
	if (get_dist(user, src) > 1 || user.eye_blind)
		off_action.Activate()
		return 0
	return 1

/obj/machinery/computer/camera_advanced/attack_hand(var/mob/user as mob)
	if(..())
		return
	if(!iscarbon(user))
		return
	var/mob/living/carbon/L = user

	if(!current_user)
		if(!eyeobj)
			CreateEye()
		GrantActions(user)
		current_user = user
		eyeobj.user = user
		eyeobj.name = "Camere Eye ([user.name])"
		L.remote_view = 1
		L.remote_control = eyeobj
		L.client.perspective = EYE_PERSPECTIVE
		if(!eyeobj.initialized)
			for(var/obj/machinery/camera/C in cameranet.cameras)
				if(!C.can_use())
					continue
				if(C.network&networks)
					eyeobj.setLoc(get_turf(C))
					break
			eyeobj.initialized = 1
		else
			eyeobj.setLoc(eyeobj.loc)
	else
		user << "The console is already in use!"

/mob/camera/aiEye/remote
	name = "Inactive Camera Eye"
	var/sprint = 10
	var/cooldown = 0
	var/acceleration = 1
	var/mob/living/carbon/human/user = null
	var/obj/machinery/computer/camera_advanced/origin
	var/initialized = 0
	var/visible_icon = 0
	var/image/user_image = null

/mob/camera/aiEye/remote/GetViewerClient()
	if(user)
		return user.client
	return null

/mob/camera/aiEye/remote/setLoc(var/T)
	if(user)
		if(!isturf(user.loc))
			return
		T = get_turf(T)
		loc = T
		cameranet.visibility(src)
		if(user.client)
			if(visible_icon)
				user.client.images -= user_image
				user_image = image(icon,loc,icon_state,FLY_LAYER)
				user.client.images += user_image
			user.client.eye = src

/mob/camera/aiEye/remote/relaymove(mob/user,direct)
	var/initial = initial(sprint)
	var/max_sprint = 50

	if(cooldown && cooldown < world.timeofday) // 3 seconds
		sprint = initial

	for(var/i = 0; i < max(sprint, initial); i += 20)
		var/turf/step = get_turf(get_step(src, direct))
		if(step)
			src.setLoc(step)

	cooldown = world.timeofday + 5
	if(acceleration)
		sprint = min(sprint + 0.5, max_sprint)
	else
		sprint = initial

/datum/action/camera_off
	name = "End Camera View"
	action_type = AB_INNATE
	button_icon_state = "camera_off"

/datum/action/camera_off/Activate()
	if(!target || !iscarbon(target))
		return
	var/mob/living/carbon/C = target
	var/mob/camera/aiEye/remote/remote_eye = C.remote_control
	C.remote_view = 0
	remote_eye.origin.current_user = null
	remote_eye.origin.jump_action.Remove(C)
	if(C.client)
		C.client.perspective = MOB_PERSPECTIVE
		C.client.eye = src
		C.client.images -= remote_eye.user_image
	C.remote_control = null
	C.unset_machine()
	src.Remove(C)

/datum/action/camera_jump
	name = "Jump To Camera"
	action_type = AB_INNATE
	button_icon_state = "camera_jump"

/datum/action/camera_jump/Activate()
	if(!target || !iscarbon(target))
		return
	var/mob/living/carbon/C = target
	var/mob/camera/aiEye/remote/remote_eye = C.remote_control
	var/obj/machinery/computer/camera_advanced/origin = remote_eye.origin

	var/list/L = list()

	for (var/obj/machinery/camera/cam in cameranet.cameras)
		L.Add(cam)

	camera_sort(L)

	var/list/T = list()

	for (var/obj/machinery/camera/netcam in L)
		var/list/tempnetwork = netcam.network&origin.networks
		if (tempnetwork.len)
			T[text("[][]", netcam.c_tag, (netcam.can_use() ? null : " (Deactivated)"))] = netcam

	var/camera = input("Choose which camera you want to view", "Cameras") as null|anything in T
	var/obj/machinery/camera/final = T[camera]
	if(final)
		remote_eye.setLoc(get_turf(final))


code:
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31

//Keeps track of the time for the ID console. Having it as a global variable prevents people from dismantling/reassembling it to
//increase the slots of many jobs.
var/time_last_changed_position = 0

/obj/machinery/computer/card
	name = "identification console"
	desc = "You can use this to change ID's."
	icon_state = "id"
	req_one_access = list(access_heads, access_change_ids)
	circuit = /obj/item/weapon/circuitboard/card
	var/obj/item/weapon/card/id/scan = null
	var/obj/item/weapon/card/id/modify = null
	var/authenticated = 0.0
	var/mode = 0.0
	var/printing = null
	var/list/region_access = null
	var/list/head_subordinates = null

	//Cooldown for closing positions in seconds
	//if set to -1: No cooldown... probably a bad idea
	//if set to 0: Not able to close "original" positions. You can only close positions that you have opened before
	var/change_position_cooldown = 60
	//Jobs you cannot open new positions for
	var/list/blacklisted = list(
		"AI",
		"Assistant",
		"Cyborg",
		"Captain",
		"Head of Personnel",
		"Head of Security",
		"Chief Engineer",
		"Research Director",
		"Chief Medical Officer",
		"Chaplain")

	//The scaling factor of max total positions in relation to the total amount of people on board the station in %
	var/max_relative_positions = 30 //30%: Seems reasonable, limit of 6 @ 20 players

	//This is used to keep track of opened positions for jobs to allow instant closing
	//Assoc array: "JobName" = (int)<Opened Positions>
	var/list/opened_positions = list();

/obj/machinery/computer/card/attackby(O as obj, user as mob, params)//TODO:SANITY
	if(istype(O, /obj/item/weapon/card/id))
		var/obj/item/weapon/card/id/idcard = O
		if(check_access(idcard))
			if(!scan)
				usr.drop_item()
				idcard.loc = src
				scan = idcard
			else if(!modify)
				usr.drop_item()
				idcard.loc = src
				modify = idcard
		else
			if(!modify)
				usr.drop_item()
				idcard.loc = src
				modify = idcard
	else
		..()

//Check if you can't open a new position for a certain job
/obj/machinery/computer/card/proc/job_blacklisted(jobtitle)
	return (jobtitle in blacklisted)

//Logic check for Topic() if you can open the job
/obj/machinery/computer/card/proc/can_open_job(var/datum/job/job)
	if(job)
		if(!job_blacklisted(job.title))
			if((job.total_positions <= player_list.len * (max_relative_positions / 100)))
				var/delta = (world.time / 10) - time_last_changed_position
				if((change_position_cooldown < delta) || (opened_positions[job.title] < 0))
					return 1
				return -2
			return -1
	return 0

//Logic check for Topic() if you can close the job
/obj/machinery/computer/card/proc/can_close_job(var/datum/job/job)
	if(job)
		if(!job_blacklisted(job.title))
			if(job.total_positions > job.current_positions)
				var/delta = (world.time / 10) - time_last_changed_position
				if((change_position_cooldown < delta) || (opened_positions[job.title] > 0))
					return 1
				return -2
			return -1
	return 0

/obj/machinery/computer/card/attack_hand(var/mob/user as mob)
	if(..())
		return

	user.set_machine(src)
	var/dat
	if(!ticker)	return
	if (mode == 1) // accessing crew manifest
		var/crew = ""
		for(var/datum/data/record/t in sortRecord(data_core.general))
			crew += t.fields["name"] + " - " + t.fields["rank"] + "
"
		dat = "<tt>Crew Manifest:
Please use security record computer to modify entries.

[crew]Print

Access ID modification console.
</tt>"

	else if(mode == 2)
		// JOB MANAGEMENT
		dat = "Return"
		dat += " || Confirm Identity: "
		var/S
		if(scan)
			S = html_encode(scan.name)
		else
			S = "--------"
		dat += "[S]"
		dat += "
"
		dat += "
Job	Slots	Open job	Close job
"
		var/ID
		if(scan && (access_change_ids in scan.access))
			ID = 1
		else
			ID = 0
		for(var/datum/job/job in SSjob.occupations)
			dat += "
"
			if(job.title in blacklisted)
				continue
			dat += "[job.title]	"
			dat += "[job.current_positions]/[job.total_positions]	"
			dat += ""
			switch(can_open_job(job))
				if(1)
					if(ID)
						dat += "Open Position
"
					else
						dat += "Open Position"
				if(-1)
					dat += "Denied"
				if(-2)
					var/time_to_wait = round(change_position_cooldown - ((world.time / 10) - time_last_changed_position), 1)
					var/mins = round(time_to_wait / 60)
					var/seconds = time_to_wait - (60*mins)
					dat += "Cooldown ongoing: [mins]:[(seconds < 10) ? "0[seconds]" : "[seconds]"]"
				if(0)
					dat += "Denied"
			dat += "	"
			switch(can_close_job(job))
				if(1)
					if(ID)
						dat += "Close Position"
					else
						dat += "Close Position"
				if(-1)
					dat += "Denied"
				if(-2)
					var/time_to_wait = round(change_position_cooldown - ((world.time / 10) - time_last_changed_position), 1)
					var/mins = round(time_to_wait / 60)
					var/seconds = time_to_wait - (60*mins)
					dat += "Cooldown ongoing: [mins]:[(seconds < 10) ? "0[seconds]" : "[seconds]"]"
				if(0)
					dat += "Denied"
			dat += "
"
		dat += "
"
	else
		var/header = ""

		var/target_name
		var/target_owner
		var/target_rank
		if(modify)
			target_name = html_encode(modify.name)
		else
			target_name = "--------"
		if(modify && modify.registered_name)
			target_owner = html_encode(modify.registered_name)
		else
			target_owner = "--------"
		if(modify && modify.assignment)
			target_rank = html_encode(modify.assignment)
		else
			target_rank = "Unassigned"

		var/scan_name
		if(scan)
			scan_name = html_encode(scan.name)
		else
			scan_name = "--------"

		if(!authenticated)
			header += "
Please insert the cards into the slots
"
			header += "Target: [target_name]
"
			header += "Confirm Identity: [scan_name]
"
		else
			header += "

"
			header += "Remove [target_name] || "
			header += "Remove [scan_name]
 "
			header += "Access Crew Manifest || "
			header += "Log Out
"

		header += "
"

		var/jobs_all = ""
		var/list/alljobs = list("Unassigned")
		alljobs += (istype(src,/obj/machinery/computer/card/centcom)? get_all_centcom_jobs() : get_all_jobs()) + "Custom"
		for(var/job in alljobs)
			jobs_all += "[replacetext(job, " ", "&nbsp")] " //make sure there isn't a line break in the middle of a job

		var/body

		if (authenticated && modify)

			var/carddesc = text("")
			var/jobs = text("")
			if( authenticated == 2)
				carddesc += {""}
				carddesc += "<form name='cardcomp' action='?src=\ref[src]' method='get'>"
				carddesc += "<input type='hidden' name='src' value='\ref[src]'>"
				carddesc += "<input type='hidden' name='choice' value='reg'>"
				carddesc += "registered name: <input type='text' id='namefield' name='reg' value='[target_owner]' style='width:250px; background-color:white;' onchange='markRed()'>"
				carddesc += "<input type='submit' value='Rename' onclick='markGreen()'>"
				carddesc += "</form>"
				carddesc += "Assignment: "

				jobs += "[target_rank]" //CHECK THIS

			else
				carddesc += "registered_name: [target_owner]"
				jobs += "Assignment: [target_rank] (Demote)"

			var/accesses = ""
			if(istype(src,/obj/machinery/computer/card/centcom))
				accesses += "
Central Command:
"
				for(var/A in get_all_centcom_access())
					if(A in modify.access)
						accesses += "[replacetext(get_centcom_access_desc(A), " ", "&nbsp")] "
					else
						accesses += "[replacetext(get_centcom_access_desc(A), " ", "&nbsp")] "
			else
				accesses += "
Access
"
				accesses += "
"
				accesses += "
"
				for(var/i = 1; i <= 7; i++)
					if(authenticated == 1 && !(i in region_access))
						continue
					accesses += "[get_region_accesses_name(i)]:	"
				accesses += "

"
				for(var/i = 1; i <= 7; i++)
					if(authenticated == 1 && !(i in region_access))
						continue
					accesses += ""
					for(var/A in get_region_accesses(i))
						if(A in modify.access)
							accesses += "[replacetext(get_access_desc(A), " ", "&nbsp")] "
						else
							accesses += "[replacetext(get_access_desc(A), " ", "&nbsp")] "
						accesses += "
"
					accesses += "	"
				accesses += "

"
			body = "[carddesc]
[jobs]

[accesses]" //CHECK THIS

		else
			body = "{Log in}

"
			body += "Access Crew Manifest"
			body += "

Job Management"

		dat = "<tt>[header][body]

</tt>"

	//user << browse(dat, "window=id_com;size=900x520")
	//onclose(user, "id_com")

	var/datum/browser/popup = new(user, "id_com", "Identification Card Modifier Console", 900, 620)
	popup.set_content(dat)
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()
	return

/obj/machinery/computer/card/Topic(href, href_list)
	if(..())
		return
	usr.set_machine(src)
	switch(href_list["choice"])
		if ("modify")
			if (modify)
				data_core.manifest_modify(modify.registered_name, modify.assignment)
				modify.update_label()
				modify.loc = loc
				modify.verb_pickup()
				modify = null
				region_access = null
				head_subordinates = null
			else
				var/obj/item/I = usr.get_active_hand()
				if (istype(I, /obj/item/weapon/card/id))
					usr.drop_item()
					I.loc = src
					modify = I
			authenticated = 0

		if ("scan")
			if (scan)
				scan.loc = src.loc
				scan.verb_pickup()
				scan = null
			else
				var/obj/item/I = usr.get_active_hand()
				if (istype(I, /obj/item/weapon/card/id))
					usr.drop_item()
					I.loc = src
					scan = I
			authenticated = 0
		if ("auth")
			if ((!( authenticated ) && (scan || (istype(usr, /mob/living/silicon))) && (modify || mode)))
				if (check_access(scan))
					if(access_change_ids in scan.access)
						authenticated = 2
					else
						region_access = list()
						head_subordinates = list()
						if(access_hop in scan.access)
							region_access += 1
							region_access += 6
							get_subordinates("Head of Personnel")
						if(access_rd in scan.access)
							region_access += 4
							get_subordinates("Research Director")
						if(access_ce in scan.access)
							region_access += 5
							get_subordinates("Chief Engineer")
						if(access_cmo in scan.access)
							region_access += 3
							get_subordinates("Chief Medical Officer")
						if(access_hos in scan.access)
							region_access += 2
							get_subordinates("Head of Security")
						if(region_access)
							authenticated = 1
			else if ((!( authenticated ) && (istype(usr, /mob/living/silicon))) && (!modify))
				usr << "You can't modify an ID without an ID inserted to modify. Once one is in the modify slot on the computer, you can log in."
		if ("logout")
			region_access = null
			head_subordinates = null
			authenticated = 0
		if("access")
			if(href_list["allowed"])
				if(authenticated)
					var/access_type = text2num(href_list["access_target"])
					var/access_allowed = text2num(href_list["allowed"])
					if(access_type in (istype(src,/obj/machinery/computer/card/centcom)?get_all_centcom_access() : get_all_accesses()))
						modify.access -= access_type
						if(access_allowed == 1)
							modify.access += access_type
		if ("assign")
			if (authenticated == 2)
				var/t1 = href_list["assign_target"]
				if(t1 == "Custom")
					var/newJob = reject_bad_text(input("Enter a custom job assignment.", "Assignment", modify ? modify.assignment : "Unassigned"), MAX_NAME_LEN)
					if(newJob)
						t1 = newJob

				else if(t1 == "Unassigned")
					modify.access = list()

				else
					var/datum/job/jobdatum
					for(var/jobtype in typesof(/datum/job))
						var/datum/job/J = new jobtype
						if(ckey(J.title) == ckey(t1))
							jobdatum = J
							break
					if(!jobdatum)
						usr << "No log exists for this job."
						return

					modify.access = ( istype(src,/obj/machinery/computer/card/centcom) ? get_centcom_access(t1) : jobdatum.get_access() )
				if (modify)
					modify.assignment = t1
		if ("demote")
			if(modify.assignment in head_subordinates || modify.assignment == "Assistant")
				modify.assignment = "Unassigned"
			else
				usr << "You are not authorized to demote this position."
		if ("reg")
			if (authenticated)
				var/t2 = modify
				//var/t1 = input(usr, "What name?", "ID computer", null)  as text
				if ((authenticated && modify == t2 && (in_range(src, usr) || (istype(usr, /mob/living/silicon))) && istype(loc, /turf)))
					var/newName = reject_bad_name(href_list["reg"])
					if(newName)
						modify.registered_name = newName
					else
						usr << "Invalid name entered."
						return
		if ("mode")
			mode = text2num(href_list["mode_target"])

		if("return")
			//DISPLAY MAIN MENU
			mode = 3;

		if("make_job_available")
			// MAKE ANOTHER JOB POSITION AVAILABLE FOR LATE JOINERS
			if(scan && (access_change_ids in scan.access))
				var/edit_job_target = href_list["job"]
				var/datum/job/j = SSjob.GetJob(edit_job_target)
				if(!j)
					return 0
				if(can_open_job(j) != 1)
					return 0
				if(opened_positions[edit_job_target] >= 0)
					time_last_changed_position = world.time / 10
				j.total_positions++
				opened_positions[edit_job_target]++

		if("make_job_unavailable")
			// MAKE JOB POSITION UNAVAILABLE FOR LATE JOINERS
			if(scan && (access_change_ids in scan.access))
				var/edit_job_target = href_list["job"]
				var/datum/job/j = SSjob.GetJob(edit_job_target)
				if(!j)
					return 0
				if(can_close_job(j) != 1)
					return 0
				//Allow instant closing without cooldown if a position has been opened before
				if(opened_positions[edit_job_target] <= 0)
					time_last_changed_position = world.time / 10
				j.total_positions--
				opened_positions[edit_job_target]--

		if ("print")
			if (!( printing ))
				printing = 1
				sleep(50)
				var/obj/item/weapon/paper/P = new /obj/item/weapon/paper( loc )
				var/t1 = "Crew Manifest:
"
				for(var/datum/data/record/t in sortRecord(data_core.general))
					t1 += t.fields["name"] + " - " + t.fields["rank"] + "
"
				P.info = t1
				P.name = "paper- 'Crew Manifest'"
				printing = null
	if (modify)
		modify.update_label()
	updateUsrDialog()
	return

/obj/machinery/computer/card/proc/get_subordinates(var/rank)
	for(var/datum/job/job in SSjob.occupations)
		if(rank in job.department_head)
			head_subordinates += job.title

/obj/machinery/computer/card/centcom
	name = "\improper Centcom identification console"
	circuit = /obj/item/weapon/circuitboard/card/centcom
	req_access = list(access_cent_captain)


code:
/obj/machinery/computer/cloning
	name = "cloning console"
	desc = "Used to clone people and manage DNA."
	icon = 'icons/obj/computer.dmi'
	icon_state = "dna"
	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.
	var/obj/machinery/clonepod/pod1 = null //Linked cloning pod.
	var/temp = "Inactive"
	var/scantemp_ckey
	var/scantemp = "Ready to Scan"
	var/menu = 1 //Which menu screen to display
	var/list/records = list()
	var/datum/data/record/active_record = null
	var/obj/item/weapon/disk/data/diskette = null //Mostly so the geneticist can steal everything.
	var/loading = 0 // Nice loading text
	var/autoprocess = 0

/obj/machinery/computer/cloning/New()
	..()
	spawn(5)
		updatemodules()
		return
	return

/obj/machinery/computer/cloning/process()
	if(!(scanner && pod1 && autoprocess))
		return

	if(scanner.occupant && (scanner.scan_level > 2))
		scan_mob(scanner.occupant)

	if(!(pod1.occupant || pod1.mess) && (pod1.efficiency > 5))
		for(var/datum/data/record/R in records)
			if(!(pod1.occupant || pod1.mess))
				if(pod1.growclone(R.fields["ckey"], R.fields["name"], R.fields["UI"], R.fields["SE"], R.fields["mind"], R.fields["mrace"], R.fields["mcolor"], R.fields["factions"]))
					records -= R

/obj/machinery/computer/cloning/proc/updatemodules()
	src.scanner = findscanner()
	src.pod1 = findcloner()

	if (!isnull(src.pod1))
		src.pod1.connected = src // Some variable the pod needs

/obj/machinery/computer/cloning/proc/findscanner()
	var/obj/machinery/dna_scannernew/scannerf = null

	// Loop through every direction
	for(dir in list(NORTH,EAST,SOUTH,WEST))

		// Try to find a scanner in that direction
		scannerf = locate(/obj/machinery/dna_scannernew, get_step(src, dir))

		// If found and operational, return the scanner
		if (!isnull(scannerf) && scannerf.is_operational())
			return scannerf

	// If no scanner was found, it will return null
	return null

/obj/machinery/computer/cloning/proc/findcloner()
	var/obj/machinery/clonepod/podf = null

	for(dir in list(NORTH,EAST,SOUTH,WEST))

		podf = locate(/obj/machinery/clonepod, get_step(src, dir))

		if (!isnull(podf) && podf.is_operational())
			return podf

	return null

/obj/machinery/computer/cloning/attackby(obj/item/W as obj, mob/user as mob, params)
	if (istype(W, /obj/item/weapon/disk/data)) //INSERT SOME DISKETTES
		if (!src.diskette)
			user.drop_item()
			W.loc = src
			src.diskette = W
			user << "You insert [W]."
			src.updateUsrDialog()
			return
	else
		..()
	return

/obj/machinery/computer/cloning/attack_hand(mob/user)
	if(..())
		return
	interact(user)

/obj/machinery/computer/cloning/interact(mob/user)
	user.set_machine(src)
	add_fingerprint(user)

	if(..())
		return

	updatemodules()

	var/dat = ""
	dat += "Refresh"
	if(scanner && pod1 && ((scanner.scan_level > 2) || (pod1.efficiency > 5)))
		if(!autoprocess)
			dat += "Autoprocess"
		else
			dat += "Stop autoprocess"
	else
		dat += "Autoprocess"
	dat += "
Cloning Pod Status
"
	dat += "
[temp]
"

	switch(src.menu)
		if(1)
			// Modules
			if (isnull(src.scanner) || isnull(src.pod1))
				dat += "
Modules
"
				//dat += "Reload Modules"
				if (isnull(src.scanner))
					dat += "ERROR: No Scanner detected!
"
				if (isnull(src.pod1))
					dat += "ERROR: No Pod detected
"

			// Scanner
			if (!isnull(src.scanner))

				dat += "
Scanner Functions
"

				dat += "
"
				if (!src.scanner.occupant)
					dat += "Scanner Unoccupied"
				else if(loading)
					dat += "[src.scanner.occupant] => Scanning..."
				else
					if (src.scanner.occupant.ckey != scantemp_ckey)
						scantemp = "Ready to Scan"
						scantemp_ckey = src.scanner.occupant.ckey
					dat += "[src.scanner.occupant] => [scantemp]"
				dat += "
"

				if (src.scanner.occupant)
					dat += "Start Scan"
					dat += "
[src.scanner.locked ? "Unlock Scanner" : "Lock Scanner"]"
				else
					dat += "Start Scan"

			// Database
			dat += "
Database Functions
"
			if (src.records.len && src.records.len > 0)
				dat += "View Records ([src.records.len])
"
			else
				dat += "View Records (0)
"
			if (src.diskette)
				dat += "Eject Disk
"

		if(2)
			dat += "
Current records
"
			dat += "<< Back

"
			for(var/datum/data/record/R in records)
				dat += "
[R.fields["name"]]
Scan ID [R.fields["id"]] View Record"
		if(3)
			dat += "
Selected Record
"
			dat += "<< Back
"

			if (!src.active_record)
				dat += "Record not found."
			else
				dat += "
[src.active_record.fields["name"]]
"
				dat += "Scan ID [src.active_record.fields["id"]] Clone
"

				var/obj/item/weapon/implant/health/H = locate(src.active_record.fields["imp"])

				if ((H) && (istype(H)))
					dat += "Health Implant Data:
[H.sensehealth()]

"
				else
					dat += "Unable to locate Health Implant.

"

				dat += "Unique Identifier:
[src.active_record.fields["UI"]]
"
				dat += "Structural Enzymes:
[src.active_record.fields["SE"]]
"

				if(diskette && diskette.fields)
					dat += "
"
					dat += "
Inserted Disk
"
					dat += "Contents: "
					var/list/L = list()
					if(diskette.fields["UI"])
						L += "Unique Identifier"
					if(diskette.fields["UE"] && diskette.fields["name"] && diskette.fields["blood_type"])
						L += "Unique Enzymes"
					if(diskette.fields["SE"])
						L += "Structural Enzymes"
					dat += english_list(L, "Empty", " + ", " + ")
					dat += "
Load from Disk"

					dat += "
Save to Disk"
					dat += "
"

				dat += "Delete Record"

		if(4)
			if (!src.active_record)
				src.menu = 2
			dat = "[src.temp]
"
			dat += "
Confirm Record Deletion
"

			dat += "Scan card to confirm.
"
			dat += "Cancel"

	//user << browse(dat, "window=cloning")
	//onclose(user, "cloning")
	var/datum/browser/popup = new(user, "cloning", "Cloning System Control")
	popup.set_content(dat)
	popup.set_title_image(user.browse_rsc_icon(src.icon, src.icon_state))
	popup.open()
	return

/obj/machinery/computer/cloning/Topic(href, href_list)
	if(..())
		return

	if(loading)
		return

	if(href_list["task"])
		switch(href_list["task"])
			if("autoprocess")
				autoprocess = 1
			if("stopautoprocess")
				autoprocess = 0

	else if ((href_list["scan"]) && !isnull(scanner) && scanner.is_operational())
		scantemp = ""

		loading = 1
		src.updateUsrDialog()

		spawn(20)
			src.scan_mob(scanner.occupant)

			loading = 0
			src.updateUsrDialog()

		//No locking an open scanner.
	else if ((href_list["lock"]) && !isnull(scanner) && scanner.is_operational())
		if ((!scanner.locked) && (scanner.occupant))
			scanner.locked = 1
		else
			scanner.locked = 0

	else if(href_list["view_rec"])
		src.active_record = find_record("id", href_list["view_rec"], records)
		if(active_record)
			if(!active_record.fields["ckey"])
				records -= active_record
				active_record = null
				src.temp = "Record Corrupt"
			else
				src.menu = 3
		else
			src.temp = "Record missing."

	else if (href_list["del_rec"])
		if ((!src.active_record) || (src.menu < 3))
			return
		if (src.menu == 3) //If we are viewing a record, confirm deletion
			src.temp = "Delete record?"
			src.menu = 4

		else if (src.menu == 4)
			var/obj/item/weapon/card/id/C = usr.get_active_hand()
			if (istype(C)||istype(C, /obj/item/device/pda))
				if(src.check_access(C))
					src.temp = "[src.active_record.fields["name"]] => Record deleted."
					src.records.Remove(active_record)
					active_record = null
					src.menu = 2
				else
					src.temp = "Access Denied."

	else if (href_list["disk"]) //Load or eject.
		switch(href_list["disk"])
			if("load")
				if (!diskette || !istype(diskette.fields) || !diskette.fields["name"] || !diskette.fields)
					src.temp = "Load error."
					src.updateUsrDialog()
					return
				if (!src.active_record)
					src.temp = "Record error."
					src.menu = 1
					src.updateUsrDialog()
					return

				src.active_record.fields = diskette.fields.Copy()
				src.temp = "Load successful."

			if("eject")
				if(src.diskette)
					src.diskette.loc = src.loc
					src.diskette = null
			if("save")
				if(!diskette || diskette.read_only || !active_record || !active_record.fields)
					src.temp = "Save error."
					src.updateUsrDialog()
					return

				diskette.fields = active_record.fields.Copy()
				diskette.name = "data disk - '[src.diskette.fields["name"]]'"
				src.temp = "Save successful."

	else if (href_list["refresh"])
		src.updateUsrDialog()

	else if (href_list["clone"])
		var/datum/data/record/C = find_record("id", href_list["clone"], records)
		//Look for that player! They better be dead!
		if(C)
			//Can't clone without someone to clone.  Or a pod.  Or if the pod is busy. Or full of gibs.
			if(!pod1)
				temp = "No Clonepod detected."
			else if(pod1.occupant)
				temp = "Clonepod is currently occupied."
			else if(pod1.mess)
				temp = "Clonepod malfunction."
			else if(!config.revival_cloning)
				temp = "Unable to initiate cloning cycle."
			else if(pod1.growclone(C.fields["ckey"], C.fields["name"], C.fields["UI"], C.fields["SE"], C.fields["mind"], C.fields["mrace"], C.fields["mcolor"], C.fields["factions"]))
				temp = "[C.fields["name"]] => Cloning cycle in progress..."
				records.Remove(C)
				if(active_record == C)
					active_record = null
				menu = 1
			else
				temp = "[C.fields["name"]] => Initialisation failure."

		else
			temp = "Data corruption."

	else if (href_list["menu"])
		src.menu = text2num(href_list["menu"])

	src.add_fingerprint(usr)
	src.updateUsrDialog()
	return

/obj/machinery/computer/cloning/proc/scan_mob(mob/living/carbon/human/subject as mob)
	if (!check_dna_integrity(subject) || !istype(subject))
		scantemp = "Unable to locate valid genetic data."
		return
	if (!subject.getorgan(/obj/item/organ/brain))
		scantemp = "No signs of intelligence detected."
		return
	if (subject.suiciding == 1)
		scantemp = "Subject's brain is not responding to scanning stimuli."
		return
	if ((NOCLONE in subject.mutations) && (src.scanner.scan_level < 2))
		scantemp = "Subject no longer contains the fundamental materials required to create a living clone."
		return
	if ((!subject.ckey) || (!subject.client))
		scantemp = "Mental interface failure."
		return
	if (find_record("ckey", subject.ckey, records))
		scantemp = "Subject already in database."
		return

	var/datum/data/record/R = new()
	if(subject.dna.species)
		R.fields["mrace"] = subject.dna.species.type
	else
		R.fields["mrace"] = /datum/species/human
	R.fields["ckey"] = subject.ckey
	R.fields["name"] = subject.real_name
	R.fields["id"] = copytext(md5(subject.real_name), 2, 6)
	R.fields["UE"] = subject.dna.unique_enzymes
	R.fields["UI"] = subject.dna.uni_identity
	R.fields["SE"] = subject.dna.struc_enzymes
	R.fields["blood_type"] = subject.dna.blood_type
	R.fields["mcolor"] = subject.dna.mutant_color
	R.fields["factions"] = subject.faction
	//Add an implant if needed
	var/obj/item/weapon/implant/health/imp = locate(/obj/item/weapon/implant/health, subject)
	if(!imp)
		imp = new /obj/item/weapon/implant/health(subject)
		imp.implanted = subject
		R.fields["imp"] = "\ref[imp]"
	//Update it if needed
	else
		R.fields["imp"] = "\ref[imp]"

	if (!isnull(subject.mind)) //Save that mind so traitors can continue traitoring after cloning.
		R.fields["mind"] = "\ref[subject.mind]"

	src.records += R
	scantemp = "Subject successfully scanned."

/obj/machinery/computer/cloning/update_icon()
	set_light(light_range_on, light_power_on)
	if(stat & BROKEN)
		icon_state = "commb"
	else
		if(stat & NOPOWER)
			src.icon_state = "c_unpowered"
			stat |= NOPOWER
			set_light(0)
		else
			icon_state = initial(icon_state)
			stat &= ~NOPOWER