Files
Bubberstation/code/game/machinery/computer/robot.dm
SkyratBot 98568e191a [MIRROR] Enforce preserving parent proc return values across ui_act call stacks (#999)
* Enforce preserving parent proc return values across ui_act call stacks (#53964)

All ui_act procs should call parent by default. All procs should preserve the value of the parent proc when it's TRUTHY and pass it down the call stack. No UI should be interactible when its flags or state indicate it should not be, except when explicity overriden by child procs intentionally disregarding parent return values to achieve a specific goal.

* Enforce preserving parent proc return values across ui_act call stacks

Co-authored-by: Timberpoes <silent_insomnia_pp@hotmail.co.uk>
2020-09-26 17:17:59 +02:00

127 lines
4.8 KiB
Plaintext

/obj/machinery/computer/robotics
name = "robotics control console"
desc = "Used to remotely lockdown or detonate linked Cyborgs and Drones."
icon_screen = "robot"
icon_keyboard = "rd_key"
req_access = list(ACCESS_ROBOTICS)
circuit = /obj/item/circuitboard/computer/robotics
light_color = LIGHT_COLOR_PINK
/obj/machinery/computer/robotics/proc/can_control(mob/user, mob/living/silicon/robot/R)
. = FALSE
if(!istype(R))
return
if(isAI(user))
if(R.connected_ai != user)
return
if(iscyborg(user))
if(R != user)
return
if(R.scrambledcodes)
return
return TRUE
/obj/machinery/computer/robotics/ui_interact(mob/user, datum/tgui/ui)
ui = SStgui.try_update_ui(user, src, ui)
if(!ui)
ui = new(user, src, "RoboticsControlConsole", name)
ui.open()
/obj/machinery/computer/robotics/ui_data(mob/user)
var/list/data = list()
data["can_hack"] = FALSE
if(issilicon(user))
var/mob/living/silicon/S = user
if(S.hack_software)
data["can_hack"] = TRUE
else if(isAdminGhostAI(user))
data["can_hack"] = TRUE
data["cyborgs"] = list()
for(var/mob/living/silicon/robot/R in GLOB.silicon_mobs)
if(!can_control(user, R))
continue
if(z != (get_turf(R)).z)
continue
var/list/cyborg_data = list(
name = R.name,
locked_down = R.lockcharge,
status = R.stat,
charge = R.cell ? round(R.cell.percent()) : null,
module = R.module ? "[R.module.name] Module" : "No Module Detected",
synchronization = R.connected_ai,
emagged = R.emagged,
ref = REF(R)
)
data["cyborgs"] += list(cyborg_data)
data["drones"] = list()
for(var/mob/living/simple_animal/drone/D in GLOB.drones_list)
if(D.hacked)
continue
if(z != (get_turf(D)).z)
continue
var/list/drone_data = list(
name = D.name,
status = D.stat,
ref = REF(D)
)
data["drones"] += list(drone_data)
return data
/obj/machinery/computer/robotics/ui_act(action, params)
. = ..()
if(.)
return
switch(action)
if("killbot")
if(allowed(usr))
var/mob/living/silicon/robot/R = locate(params["ref"]) in GLOB.silicon_mobs
if(can_control(usr, R) && !..())
var/turf/T = get_turf(R)
message_admins("<span class='notice'>[ADMIN_LOOKUPFLW(usr)] detonated [key_name_admin(R, R.client)] at [ADMIN_VERBOSEJMP(T)]!</span>")
log_game("\<span class='notice'>[key_name(usr)] detonated [key_name(R)]!</span>")
if(R.connected_ai)
to_chat(R.connected_ai, "<br><br><span class='alert'>ALERT - Cyborg detonation detected: [R.name]</span><br>")
R.self_destruct()
else
to_chat(usr, "<span class='danger'>Access Denied.</span>")
if("stopbot")
if(allowed(usr))
var/mob/living/silicon/robot/R = locate(params["ref"]) in GLOB.silicon_mobs
if(can_control(usr, R) && !..())
message_admins("<span class='notice'>[ADMIN_LOOKUPFLW(usr)] [!R.lockcharge ? "locked down" : "released"] [ADMIN_LOOKUPFLW(R)]!</span>")
log_game("[key_name(usr)] [!R.lockcharge ? "locked down" : "released"] [key_name(R)]!")
R.SetLockdown(!R.lockcharge)
to_chat(R, "[!R.lockcharge ? "<span class='notice'>Your lockdown has been lifted!" : "<span class='alert'>You have been locked down!"]</span>")
if(R.connected_ai)
to_chat(R.connected_ai, "[!R.lockcharge ? "<span class='notice'>NOTICE - Cyborg lockdown lifted" : "<span class='alert'>ALERT - Cyborg lockdown detected"]: <a href='?src=[REF(R.connected_ai)];track=[html_encode(R.name)]'>[R.name]</a></span><br>")
else
to_chat(usr, "<span class='danger'>Access Denied.</span>")
if("magbot")
var/mob/living/silicon/S = usr
if((istype(S) && S.hack_software) || isAdminGhostAI(usr))
var/mob/living/silicon/robot/R = locate(params["ref"]) in GLOB.silicon_mobs
if(istype(R) && !R.emagged && (R.connected_ai == usr || isAdminGhostAI(usr)) && !R.scrambledcodes && can_control(usr, R))
log_game("[key_name(usr)] emagged [key_name(R)] using robotic console!")
message_admins("[ADMIN_LOOKUPFLW(usr)] emagged cyborg [key_name_admin(R)] using robotic console!")
R.SetEmagged(TRUE)
R.logevent("WARN: root privleges granted to PID [num2hex(rand(1,65535), -1)][num2hex(rand(1,65535), -1)].") //random eight digit hex value. Two are used because rand(1,4294967295) throws an error
if("killdrone")
if(allowed(usr))
var/mob/living/simple_animal/drone/D = locate(params["ref"]) in GLOB.mob_list
if(D.hacked)
to_chat(usr, "<span class='danger'>ERROR: [D] is not responding to external commands.</span>")
else
var/turf/T = get_turf(D)
message_admins("[ADMIN_LOOKUPFLW(usr)] detonated [key_name_admin(D)] at [ADMIN_VERBOSEJMP(T)]!")
log_game("[key_name(usr)] detonated [key_name(D)]!")
var/datum/effect_system/spark_spread/s = new /datum/effect_system/spark_spread
s.set_up(3, TRUE, D)
s.start()
D.visible_message("<span class='danger'>\the [D] self-destructs!</span>")
D.gib()