From c08d4bc5eb10e94f7bf3556c201e297ff3c8c5cb Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 5 Jan 2025 17:48:43 -0500 Subject: [PATCH 01/44] AI Powers initial commit - Base datums for picker and program --- code/modules/mob/living/silicon/ai/ai_mob.dm | 6 + .../mob/living/silicon/ai/ai_programs.dm | 128 ++++++++++++++++++ paradise.dme | 1 + 3 files changed, 135 insertions(+) create mode 100644 code/modules/mob/living/silicon/ai/ai_programs.dm diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 76eb27abfd39..4508a9abb91c 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -66,6 +66,10 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( var/obj/item/radio/headset/heads/ai_integrated/aiRadio = null + // AI Powers + var/datum/program_picker/program_picker + var/datum/spell/ai_spell/choose_program/program_action + //MALFUNCTION var/datum/module_picker/malf_picker var/datum/spell/ai_spell/choose_modules/modules_action @@ -393,6 +397,8 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( if(!powered_ai || powered_ai.stat & DEAD) qdel(src) return + // Regenerate nanites for abilities only when powered. + powered_ai.program_picker.nanites = min(100, powered_ai.program_picker.nanites + (1 + 0.5*powered_ai.program_picker.bandwidth)) if(!powered_ai.anchored) loc = powered_ai.loc change_power_mode(NO_POWER_USE) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm new file mode 100644 index 000000000000..90f7d6756abe --- /dev/null +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -0,0 +1,128 @@ +// The datum and interface for the AI powers menu +/datum/program_picker + /// List of programs that can be bought + var/list/possible_programs + /// List of purchased programs + var/list/installed_programs + /// List of purchased program upgrades + var/list/purchased_upgrades + /// How much memory is available + var/memory = 1 + /// How much bandwidth is available + var/bandwidth = 1 + /// How many nanites are available? + var/nanites = 50 + /// What is the maximum number of nanites? + var/max_nanites = 100 + +/datum/program_picker/New() + possible_programs = list() + for(var/type in subtypesof(/datum/ai_program)) + var/datum/ai_program/program = new type + if(program.power_type || program.upgrade) + possible_programs += program + +/datum/program_picker/proc/use(mob/user) + var/dat + dat += {"Select program to install: (currently [memory] TB of memory and [bandwidth] TBPS of bandwidth left.)
+
+ Install Program:
+ The number afterwards is the amount of a given resource it consumes.
"} + for(var/datum/ai_program/program in possible_programs) + dat += "[program.program_name]\[?\] ([program.installed ? "[program.cost] TB" : "1 TBPS"])
" + dat += "
" + if(temp) + dat += "[temp]" + var/datum/browser/popup = new(user, "modpicker", "AI Program Menu", 400, 500) + popup.set_content(dat) + popup.open() + return + +/datum/program_picker/Topic(href, href_list) + ..() + + if(!isAI(usr)) + return + var/mob/living/silicon/ai/A = usr + + if(A.stat == DEAD) + to_chat(A, "You are dead!") + return + + for(var/datum/ai_program/program in possible_modules) + if(href_list[program.program_id]) + + // Cost check + if(program.cost > bandwidth) + temp = "You cannot afford this module." + break + + var/datum/spell/ai_spell/action = locate(program.power_type) in A.mob_spell_list + + // Purchase a program + if(!program.installed) + if(program.upgrade) + program.upgrade(A) + else + var/datum/spell/ai_spell/AC = new program.power_type + A.AddSpell(AC) + temp = program.description + if(program.unlock_text) + to_chat(A, program.unlock_text) + if(program.unlock_sound) + A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) + memory -= program.cost + installed_programs += program + program.installed = TRUE + // Upgrade a program + else + to_chat(A, "[program] has been updated!") + if(program.unlock_sound) + A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) + bandwidth -= 1 + program.bandwidth_used += 1 + program.purchased_upgrades += program + + if(href_list["showdesc"]) + if(program.program_id == href_list["showdesc"]) + temp = program.description + use(usr) + +// The base program type, which holds info about each ability. +/datum/ai_program + var/program_name + var/description = "" + /// Internal ID of the program + var/program_id + /// How much memory does the program cost? + var/cost = 1 + /// How much does this program cost to use? + var/nanite_cost = 10 + /// Has the program been bought? + var/installed = FALSE + /// How many upgrades have been bought of this program? + var/bandwidth_used = 0 + /// If the module gives an active ability, use this. Mutually exclusive with upgrade. + var/power_type = /datum/spell/ai_spell + /// If the module gives a passive upgrade, use this. Mutually exclusive with power_type. + var/upgrade = FALSE + /// Text shown when an ability is unlocked + var/unlock_text = "Hello World!" + /// Sound played when an ability is unlocked + var/unlock_sound + /// The cooldown when the ability is used + var/cooldown = 30 SECONDS + +/datum/ai_program/proc/upgrade(mob/living/silicon/ai/AI) + return + +/datum/spell/ai_spell/choose_program + name = "Choose Programs" + desc = "Spend your memory and bandwidth to gain a variety of different abilities." + action_icon_state = "choose_program" + auto_use_uses = FALSE // This is an infinite ability. + create_attack_logs = FALSE + +/datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) + . = ..() + user.program_picker.use(user) diff --git a/paradise.dme b/paradise.dme index d8f1e6e23d9d..5a62c44c8406 100644 --- a/paradise.dme +++ b/paradise.dme @@ -2335,6 +2335,7 @@ #include "code\modules\mob\living\silicon\ai\ai_login.dm" #include "code\modules\mob\living\silicon\ai\ai_logout.dm" #include "code\modules\mob\living\silicon\ai\ai_mob.dm" +#include "code\modules\mob\living\silicon\ai\ai_programs.dm" #include "code\modules\mob\living\silicon\ai\ai_say.dm" #include "code\modules\mob\living\silicon\ai\ai_update_status.dm" #include "code\modules\mob\living\silicon\ai\latejoin.dm" From b8fcaa4ba4c1b07c6383d0a0164294b0b61bd596 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 5 Jan 2025 18:34:58 -0500 Subject: [PATCH 02/44] Small fixes in base datums --- code/modules/mob/living/silicon/ai/ai_programs.dm | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 90f7d6756abe..b9a6328fe1bb 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -14,6 +14,8 @@ var/nanites = 50 /// What is the maximum number of nanites? var/max_nanites = 100 + // Handles extra information displayed + var/temp /datum/program_picker/New() possible_programs = list() @@ -49,7 +51,7 @@ to_chat(A, "You are dead!") return - for(var/datum/ai_program/program in possible_modules) + for(var/datum/ai_program/program in possible_programs) if(href_list[program.program_id]) // Cost check @@ -57,8 +59,6 @@ temp = "You cannot afford this module." break - var/datum/spell/ai_spell/action = locate(program.power_type) in A.mob_spell_list - // Purchase a program if(!program.installed) if(program.upgrade) @@ -81,7 +81,7 @@ A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) bandwidth -= 1 program.bandwidth_used += 1 - program.purchased_upgrades += program + purchased_upgrades += program if(href_list["showdesc"]) if(program.program_id == href_list["showdesc"]) @@ -119,7 +119,8 @@ /datum/spell/ai_spell/choose_program name = "Choose Programs" desc = "Spend your memory and bandwidth to gain a variety of different abilities." - action_icon_state = "choose_program" + action_icon = "icons/mob/ai.dmi" + action_icon_state = "ai" auto_use_uses = FALSE // This is an infinite ability. create_attack_logs = FALSE From c6d6ba0cbbe2307337ddc542439b248b3a131c77 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 7 Jan 2025 03:25:43 -0500 Subject: [PATCH 03/44] RGB Lighting Power --- .../mob/living/silicon/ai/ai_programs.dm | 46 ++++++++++++++++++- 1 file changed, 45 insertions(+), 1 deletion(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index b9a6328fe1bb..da1fb2d770c2 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -76,12 +76,17 @@ program.installed = TRUE // Upgrade a program else + if(program.power_type.spell_level >= program.power_type.level_max) + to_chat(user, "This program cannot be updated further.") + return FALSE to_chat(A, "[program] has been updated!") if(program.unlock_sound) A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) bandwidth -= 1 - program.bandwidth_used += 1 + program.bandwidth_used++ + program.power_type.spell_level++ purchased_upgrades += program + program.upgrade() if(href_list["showdesc"]) if(program.program_id == href_list["showdesc"]) @@ -127,3 +132,42 @@ /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) . = ..() user.program_picker.use(user) + +// RGB Lighting - Recolors Lights +/datum/ai_program/rgb_lighting + program_name = "RGB Lighting" + program_id = "rgb_lighting" + description = "Recolor a light to a desired color" + nanite_cost = 5 + power_type = /datum/spell/ai_spell/ranged/rgb_lighting + unlock_text = "RGB Lighting installation complete!" + +/datum/ai_program/rgb_lighting/upgrade() + power_type.cooldown_handler.recharge_duration = power_type.base_cooldown - (power_type.spell_level * 5) + +/datum/spell/ai_spell/ranged/rgb_lighting + name = "RGB Lighting" + desc = "Changes the color of a selected light" + action_icon_state = "light" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 30 SECONDS + cooldown_min = 5 SECONDS + level_max = 5 + +/datum/spell/ai_spell/ranged/rgb_lighting/cast(list/targets, mob/user) + var/obj/machinery/target = targets[1] + if(!istype(target, obj/machinery/light) && !istype(target, obj/machinery/power/apc)) + to_chat(user, "You can only recolor lights!") + return + if(istype(target, obj/machinery/power/apc)) + if(spell_level < 3) // If you haven't upgraded it 3 times, you have to color lights individually. + to_chat(user, "Your coloring subsystem is not strong enough to target an entire room!") + return + for(var/obj/machinery/light/L in target.apc_area) + L.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + else + target.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) + // TODO: Add graphics of beaming the target from the nearest APC From 4685f487d56677a1194be54821bab5568bbc234b Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 7 Jan 2025 03:45:38 -0500 Subject: [PATCH 04/44] Nearest camera detection, beam effect for RGB_Lighting --- code/game/gamemodes/malfunction/Malf_Modules.dm | 14 ++++++++++++++ code/modules/mob/living/silicon/ai/ai_programs.dm | 6 +++++- 2 files changed, 19 insertions(+), 1 deletion(-) diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm index 90ba39865b7a..cebe18ae90d2 100644 --- a/code/game/gamemodes/malfunction/Malf_Modules.dm +++ b/code/game/gamemodes/malfunction/Malf_Modules.dm @@ -32,6 +32,20 @@ if(auto_use_uses) adjust_uses(-1, user) +/datum/spell/ai_spell/find_nearest_camera(atom/target) + var/area/A = get_area(target) + if(A == null) + return + var/closest_camera = null + for(var/obj/machinery/camera/C in A) + if(closest_camera == null) + closest_camera = C + continue + if(get_dist(closest_camera, target) > get_dist(C, target)) + closest_camera = C + continue + return closest_camera + /datum/spell/ai_spell/proc/adjust_uses(amt, mob/living/silicon/ai/owner, silent) uses += amt if(!silent && uses) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index da1fb2d770c2..c8efb4f32530 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -170,4 +170,8 @@ target.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) - // TODO: Add graphics of beaming the target from the nearest APC + var/obj/machine/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + From f7b404b1d63d76213352edd66af490d35ca09e48 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 7 Jan 2025 20:26:12 -0500 Subject: [PATCH 05/44] Fixed learning AI Porgrams, Power Shunt Program --- .../mob/living/silicon/ai/ai_programs.dm | 140 ++++++++++++------ 1 file changed, 95 insertions(+), 45 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index c8efb4f32530..985b18e27a36 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -2,10 +2,6 @@ /datum/program_picker /// List of programs that can be bought var/list/possible_programs - /// List of purchased programs - var/list/installed_programs - /// List of purchased program upgrades - var/list/purchased_upgrades /// How much memory is available var/memory = 1 /// How much bandwidth is available @@ -56,37 +52,29 @@ // Cost check if(program.cost > bandwidth) - temp = "You cannot afford this module." + temp = "You cannot afford this program." break - // Purchase a program - if(!program.installed) - if(program.upgrade) - program.upgrade(A) - else - var/datum/spell/ai_spell/AC = new program.power_type - A.AddSpell(AC) - temp = program.description - if(program.unlock_text) - to_chat(A, program.unlock_text) - if(program.unlock_sound) - A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) - memory -= program.cost - installed_programs += program - program.installed = TRUE - // Upgrade a program - else - if(program.power_type.spell_level >= program.power_type.level_max) - to_chat(user, "This program cannot be updated further.") + var/datum/spell/ai_spell/new_spell = program.power_type + + for(var/datum/spell/ai_spell/aspell in A.mind.spell_list) + if(initial(new_spell) == initial(aspell)) + if(aspell.spell_level >= aspell.level_max) + to_chat(A, "This program cannot be upgraded further.") return FALSE - to_chat(A, "[program] has been updated!") - if(program.unlock_sound) - A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) - bandwidth -= 1 - program.bandwidth_used++ - program.power_type.spell_level++ - purchased_upgrades += program - program.upgrade() + else + aspell.name = initial(aspell.name) + aspell.spell_level++ + if(aspell.spell_level >= aspell.level_max) + to_chat(A, "This program cannot be upgraded any further.") + aspell.on_purchase_upgrade() + return TRUE + //No same spell found - just learn it + SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) + A.mind.AddSpell(new_spell) + to_chat(A, "You have installed [new_spell.name].") + program.installed = TRUE + return TRUE if(href_list["showdesc"]) if(program.program_id == href_list["showdesc"]) @@ -103,8 +91,6 @@ var/cost = 1 /// How much does this program cost to use? var/nanite_cost = 10 - /// Has the program been bought? - var/installed = FALSE /// How many upgrades have been bought of this program? var/bandwidth_used = 0 /// If the module gives an active ability, use this. Mutually exclusive with upgrade. @@ -117,9 +103,8 @@ var/unlock_sound /// The cooldown when the ability is used var/cooldown = 30 SECONDS - -/datum/ai_program/proc/upgrade(mob/living/silicon/ai/AI) - return + /// Is this program installed? + var/installed = FALSE /datum/spell/ai_spell/choose_program name = "Choose Programs" @@ -142,9 +127,6 @@ power_type = /datum/spell/ai_spell/ranged/rgb_lighting unlock_text = "RGB Lighting installation complete!" -/datum/ai_program/rgb_lighting/upgrade() - power_type.cooldown_handler.recharge_duration = power_type.base_cooldown - (power_type.spell_level * 5) - /datum/spell/ai_spell/ranged/rgb_lighting name = "RGB Lighting" desc = "Changes the color of a selected light" @@ -157,21 +139,89 @@ /datum/spell/ai_spell/ranged/rgb_lighting/cast(list/targets, mob/user) var/obj/machinery/target = targets[1] - if(!istype(target, obj/machinery/light) && !istype(target, obj/machinery/power/apc)) + if(!istype(target, /obj/machinery/light) && !istype(target, /obj/machinery/power/apc)) to_chat(user, "You can only recolor lights!") return - if(istype(target, obj/machinery/power/apc)) + if(istype(target, /obj/machinery/power/apc)) if(spell_level < 3) // If you haven't upgraded it 3 times, you have to color lights individually. to_chat(user, "Your coloring subsystem is not strong enough to target an entire room!") return - for(var/obj/machinery/light/L in target.apc_area) + var/obj/machinery/power/apc/A = target + for(var/obj/machinery/light/L in A.apc_area) L.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") else - target.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + var/obj/machinery/light/L = target + L.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machine/camera/C = find_nearest_camera(target) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + +/datum/spell/ai_spell/ranged/on_purchase_upgrade() + cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) + +// Power Shunt - Recharges things from your SMES +/datum/ai_program/power_shunt + program_name = "Power Shunt" + program_id = "power_shunt" + description = "Recharge an APC, Borg, or Mech with power directly from your SMES!" + nanite_cost = 20 + power_type = /datum/spell/ai_spell/ranged/power_shunt + unlock_text = "Power Shunt installation complete!" + +/datum/spell/ai_spell/ranged/power_shunt + name = "Power Shunt" + desc = "Recharge an APC, Borg, or Mech with power directly from your SMES" + action_icon_state = "light" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 300 SECONDS + cooldown_min = 30 SECONDS + level_max = 7 + var/power_sent = 2500 + var/universal_adapter = FALSE + var/adapter_efficiency = 0.5 + +/datum/spell/ai_spell/ranged/power_shunt/cast(list/targets, mob/user) + var/target = targets[1] + if(!istype(target, /mob/living/silicon/robot) && !istype(target, /obj/machinery/power/apc) && !istype(target, /obj/mecha) && !istype(target, /mob/living/carbon/human/machine)) + to_chat(user, "You can only recharge borgs, mechs, and APCs!") + return + if(istype(target, /mob/living/carbon/human/machine) && !universal_adapter) + to_chat(user, "This software lacks the required upgrade to recharge IPCs!") + return + var/area/A = get_area(user) + if(A == null) + to_chat(user, "No SMES detected to power from!") + return + if(istype(target, /obj/mecha)) + var/obj/mecha/T = target + T.cell.give(power_sent) + if(istype(target, /mob/living/silicon/robot)) + var/mob/living/silicon/robot/T = target + T.cell.give(power_sent) + if(istype(target, /obj/machinery/power/apc)) + var/obj/machinery/power/apc/T = target + T.cell.give(power_sent) + if(istype(/mob/living/carbon/human/machine)) + var/mob/living/carbon/human/machine/T = target + T.adjust_nutrition(adapter_efficiency * (power_sent / 10)) + + // Handles draining the SMES + for(var/obj/machinery/power/smes/power_source in A) + if(power_source.charge < power_sent) + continue + power_source.charge -= power_sent + break + user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) if(!istype(C)) return C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) +/datum/spell/ai_spell/ranged/power_shunt/on_purchase_upgrade() + power_sent = min(10000, 2500 + (spell_level * 2500)) + cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - ((spell_level-3) * 60)), 30 SECONDS) From 00e5ab02c52bb2e4c0b86a490101017b802ea237 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 8 Jan 2025 19:01:09 -0500 Subject: [PATCH 06/44] Program install fixes, WebUI Program Install Menu Fixes --- .../gamemodes/malfunction/Malf_Modules.dm | 2 +- code/modules/mob/living/silicon/ai/ai_mob.dm | 8 +++ .../mob/living/silicon/ai/ai_programs.dm | 62 ++++++++++++------- 3 files changed, 48 insertions(+), 24 deletions(-) diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm index cebe18ae90d2..559bfbdaa674 100644 --- a/code/game/gamemodes/malfunction/Malf_Modules.dm +++ b/code/game/gamemodes/malfunction/Malf_Modules.dm @@ -32,7 +32,7 @@ if(auto_use_uses) adjust_uses(-1, user) -/datum/spell/ai_spell/find_nearest_camera(atom/target) +/datum/spell/ai_spell/proc/find_nearest_camera(atom/target) var/area/A = get_area(target) if(A == null) return diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 4508a9abb91c..7f1c839b8732 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -242,6 +242,8 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( GLOB.ai_list += src GLOB.shuttle_caller_list += src + add_program_picker() + for(var/I in 1 to 4) stored_locations += "unset" //This is checked in ai_keybinds.dm. @@ -1362,6 +1364,12 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( create_chat_message(locateUID(M.runechat_msg_location), message_clean) show_message(rendered, 2) +/mob/living/silicon/ai/proc/add_program_picker() + view_core() // A BYOND bug requires you to be viewing your core before your verbs update + program_picker = new /datum/program_picker + program_action = new(program_picker) + AddSpell(program_action) + /mob/living/silicon/ai/proc/malfhacked(obj/machinery/power/apc/apc) malfhack = null malfhacking = null diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 985b18e27a36..3ae3965597a0 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -27,7 +27,7 @@ Install Program:
The number afterwards is the amount of a given resource it consumes.
"} for(var/datum/ai_program/program in possible_programs) - dat += "[program.program_name]\[?\] ([program.installed ? "[program.cost] TB" : "1 TBPS"])
" + dat += "[program.program_name]\[?\] ([program.installed ? "1 TBPS": "[program.cost] TB"])
" dat += "
" if(temp) dat += "[temp]" @@ -50,29 +50,33 @@ for(var/datum/ai_program/program in possible_programs) if(href_list[program.program_id]) - // Cost check - if(program.cost > bandwidth) - temp = "You cannot afford this program." - break + var/datum/spell/ai_spell/new_spell = new program.power_type - var/datum/spell/ai_spell/new_spell = program.power_type - - for(var/datum/spell/ai_spell/aspell in A.mind.spell_list) - if(initial(new_spell) == initial(aspell)) + for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + if(new_spell.type == aspell.type) if(aspell.spell_level >= aspell.level_max) to_chat(A, "This program cannot be upgraded further.") - return FALSE - else - aspell.name = initial(aspell.name) - aspell.spell_level++ - if(aspell.spell_level >= aspell.level_max) - to_chat(A, "This program cannot be upgraded any further.") - aspell.on_purchase_upgrade() - return TRUE - //No same spell found - just learn it + return FALSE + else + if(bandwidth < 1) + temp = "You cannot afford this upgrade!" + return FALSE + aspell.name = initial(aspell.name) + aspell.spell_level++ + if(aspell.spell_level >= aspell.level_max) + to_chat(A, "This program cannot be upgraded any further.") + aspell.on_purchase_upgrade() + bandwidth-- + return TRUE + // No same program found, install + if(program.cost > memory) + to_chat(A, "You cannot afford this program.") + return FALSE + memory -= program.cost SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) - A.mind.AddSpell(new_spell) + A.AddSpell(new_spell) to_chat(A, "You have installed [new_spell.name].") + to_chat(A, program.unlock_text) program.installed = TRUE return TRUE @@ -109,7 +113,7 @@ /datum/spell/ai_spell/choose_program name = "Choose Programs" desc = "Spend your memory and bandwidth to gain a variety of different abilities." - action_icon = "icons/mob/ai.dmi" + action_icon = 'icons/mob/ai.dmi' action_icon_state = "ai" auto_use_uses = FALSE // This is an infinite ability. create_attack_logs = FALSE @@ -136,22 +140,32 @@ base_cooldown = 30 SECONDS cooldown_min = 5 SECONDS level_max = 5 + selection_activated_message = "You hook into the station's lighting controller..." + selection_deactivated_message = "You cancel the request from the lighting controller." /datum/spell/ai_spell/ranged/rgb_lighting/cast(list/targets, mob/user) var/obj/machinery/target = targets[1] if(!istype(target, /obj/machinery/light) && !istype(target, /obj/machinery/power/apc)) to_chat(user, "You can only recolor lights!") return + // Color selection + var/color_picked = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + var/list/hsl = rgb2hsl(hex2num(copytext(color_picked, 2, 4)), hex2num(copytext(color_picked, 4, 6)), hex2num(copytext(color_picked, 6, 8))) + hsl[3] = max(hsl[3], 0.4) + var/list/rgb = hsl2rgb(arglist(hsl)) + var/new_color = "#[num2hex(rgb[1], 2)][num2hex(rgb[2], 2)][num2hex(rgb[3], 2)]" if(istype(target, /obj/machinery/power/apc)) if(spell_level < 3) // If you haven't upgraded it 3 times, you have to color lights individually. to_chat(user, "Your coloring subsystem is not strong enough to target an entire room!") return var/obj/machinery/power/apc/A = target for(var/obj/machinery/light/L in A.apc_area) - L.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + L.color = new_color + L.brightness_color = new_color else var/obj/machinery/light/L = target - L.brightness_color = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + L.color = new_color + L.brightness_color = new_color user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) @@ -180,6 +194,8 @@ base_cooldown = 300 SECONDS cooldown_min = 30 SECONDS level_max = 7 + selection_activated_message = "You tap into the station's powernet..." + selection_deactivated_message = "You release your hold on the powernet." var/power_sent = 2500 var/universal_adapter = FALSE var/adapter_efficiency = 0.5 @@ -205,7 +221,7 @@ if(istype(target, /obj/machinery/power/apc)) var/obj/machinery/power/apc/T = target T.cell.give(power_sent) - if(istype(/mob/living/carbon/human/machine)) + if(istype(target, /mob/living/carbon/human/machine)) var/mob/living/carbon/human/machine/T = target T.adjust_nutrition(adapter_efficiency * (power_sent / 10)) From 47e9802fda0fa795bfc45086c8f616b55ffadddd Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 8 Jan 2025 19:57:13 -0500 Subject: [PATCH 07/44] Repair nanites --- .../mob/living/silicon/ai/ai_programs.dm | 63 +++++++++++++++++++ 1 file changed, 63 insertions(+) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 3ae3965597a0..042108491a21 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -166,6 +166,8 @@ var/obj/machinery/light/L = target L.color = new_color L.brightness_color = new_color + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 5 user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) @@ -231,6 +233,8 @@ continue power_source.charge -= power_sent break + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 20 user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) @@ -241,3 +245,62 @@ /datum/spell/ai_spell/ranged/power_shunt/on_purchase_upgrade() power_sent = min(10000, 2500 + (spell_level * 2500)) cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - ((spell_level-3) * 60)), 30 SECONDS) + +// Repair Nanites - Uses large numbers of nanites to repair things +/datum/ai_program/repair_nanites + program_name = "Repair Nanites" + program_id = "repair_nanites" + description = "Repair an APC, Borg, or Mech with large numbers of robotic nanomachines!" + nanite_cost = 75 + power_type = /datum/spell/ai_spell/ranged/repair_nanites + unlock_text = "Repair nanomachine firmware installation complete!" + +/datum/spell/ai_spell/ranged/repair_nanites + name = "Repair Nanites" + desc = "Repair an APC, Borg, or Mech with large numbers of robotic nanomachines!" + action_icon_state = "light" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 450 SECONDS + cooldown_min = 30 SECONDS + level_max = 10 + selection_activated_message = "You prepare to order your nanomachines to repair..." + selection_deactivated_message = "You rescind the order." + var/universal_adapter = FALSE + var/adapter_efficiency = 0.5 + +/datum/spell/ai_spell/ranged/repair_nanites/cast(list/targets, mob/user) + var/target = targets[1] + if(!istype(target, /mob/living/silicon/robot) && !istype(target, /obj/machinery/power/apc) && !istype(target, /obj/mecha) && !istype(target, /mob/living/carbon/human/machine)) + to_chat(user, "You can only recharge borgs, mechs, and APCs!") + return + if(istype(target, /mob/living/carbon/human/machine) && !universal_adapter) + to_chat(user, "This software lacks the required upgrade to recharge IPCs!") + return + var/area/A = get_area(user) + if(A == null) + to_chat(user, "No SMES detected to power from!") + return + if(istype(target, /obj/mecha)|| istype(target, /obj/machinery/power/apc)) + var/obj/T = target + T.obj_integrity += min(T.max_integrity, T.max_integrity * (0.2 + max(0.3, (0.1 * spell_level)))) + if(istype(target, /mob/living/silicon/robot)) + var/mob/living/silicon/robot/T = target + var/damage_healed = adapter_efficiency * (20 + (max(30, (10 * spell_level)))) + T.heal_overall_damage(damage_healed, damage_healed) + if(istype(target, /mob/living/carbon/human/machine)) + var/mob/living/carbon/human/machine/T = target + var/damage_healed = adapter_efficiency * (20 + (max(30, (10 * spell_level)))) + T.heal_overall_damage(damage_healed, damage_healed, TRUE, 0, 1) + + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 75 + user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "medbeam", icon = 'icons/effects/beam.dmi', time = 10) + +/datum/spell/ai_spell/ranged/repair_nanites/on_purchase_upgrade() + cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - ((spell_level-3) * 60)), 30 SECONDS) From a92c73eb195d0a695a9d4ecfdd277f0f3fb6359b Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 8 Jan 2025 20:23:08 -0500 Subject: [PATCH 08/44] Universal Adapter --- code/modules/mob/living/silicon/ai/ai_mob.dm | 4 + .../mob/living/silicon/ai/ai_programs.dm | 105 ++++++++++++------ 2 files changed, 72 insertions(+), 37 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 7f1c839b8732..68894d33c70a 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -69,6 +69,10 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( // AI Powers var/datum/program_picker/program_picker var/datum/spell/ai_spell/choose_program/program_action + /// Whether or not the AI has unlocked universal adapter + var/universal_adapter = FALSE + /// How effective is the adapter? + var/adapter_efficiency = 0.5 //MALFUNCTION var/datum/module_picker/malf_picker diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 042108491a21..5b3c7cb3ec56 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -50,34 +50,44 @@ for(var/datum/ai_program/program in possible_programs) if(href_list[program.program_id]) - var/datum/spell/ai_spell/new_spell = new program.power_type + if(!program.upgrade) + var/datum/spell/ai_spell/new_spell = new program.power_type - for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) - if(new_spell.type == aspell.type) - if(aspell.spell_level >= aspell.level_max) - to_chat(A, "This program cannot be upgraded further.") - return FALSE - else - if(bandwidth < 1) - temp = "You cannot afford this upgrade!" - return FALSE - aspell.name = initial(aspell.name) - aspell.spell_level++ + for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + if(new_spell.type == aspell.type) if(aspell.spell_level >= aspell.level_max) - to_chat(A, "This program cannot be upgraded any further.") - aspell.on_purchase_upgrade() - bandwidth-- - return TRUE - // No same program found, install - if(program.cost > memory) - to_chat(A, "You cannot afford this program.") + to_chat(A, "This program cannot be upgraded further.") + return FALSE + else + if(bandwidth < 1) + temp = "You cannot afford this upgrade!" + return FALSE + aspell.name = initial(aspell.name) + aspell.spell_level++ + if(aspell.spell_level >= aspell.level_max) + to_chat(A, "This program cannot be upgraded any further.") + aspell.on_purchase_upgrade() + bandwidth-- + return TRUE + // No same program found, install + if(program.cost > memory) + to_chat(A, "You cannot afford this program.") + return FALSE + memory -= program.cost + SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) + A.AddSpell(new_spell) + to_chat(A, program.unlock_text) + A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) + program.installed = TRUE + return TRUE + + // Upgrades below + if(program.upgrade_level > program.max_level) + to_chat(A, "This program cannot be upgraded any further.") return FALSE - memory -= program.cost - SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) - A.AddSpell(new_spell) - to_chat(A, "You have installed [new_spell.name].") + program.upgrade(A) to_chat(A, program.unlock_text) - program.installed = TRUE + A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) return TRUE if(href_list["showdesc"]) @@ -101,6 +111,10 @@ var/power_type = /datum/spell/ai_spell /// If the module gives a passive upgrade, use this. Mutually exclusive with power_type. var/upgrade = FALSE + /// The level of the upgrade for passives + var/upgrade_level = 0 + /// Max level for passive upgrades + var/max_level = 5 /// Text shown when an ability is unlocked var/unlock_text = "Hello World!" /// Sound played when an ability is unlocked @@ -118,6 +132,9 @@ auto_use_uses = FALSE // This is an infinite ability. create_attack_logs = FALSE +/datum/ai_program/proc/upgrade(mob/user) + return + /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) . = ..() user.program_picker.use(user) @@ -199,15 +216,14 @@ selection_activated_message = "You tap into the station's powernet..." selection_deactivated_message = "You release your hold on the powernet." var/power_sent = 2500 - var/universal_adapter = FALSE - var/adapter_efficiency = 0.5 /datum/spell/ai_spell/ranged/power_shunt/cast(list/targets, mob/user) var/target = targets[1] if(!istype(target, /mob/living/silicon/robot) && !istype(target, /obj/machinery/power/apc) && !istype(target, /obj/mecha) && !istype(target, /mob/living/carbon/human/machine)) to_chat(user, "You can only recharge borgs, mechs, and APCs!") return - if(istype(target, /mob/living/carbon/human/machine) && !universal_adapter) + var/mob/living/silicon/ai/AI = user + if(istype(target, /mob/living/carbon/human/machine) && !AI.universal_adapter) to_chat(user, "This software lacks the required upgrade to recharge IPCs!") return var/area/A = get_area(user) @@ -225,7 +241,7 @@ T.cell.give(power_sent) if(istype(target, /mob/living/carbon/human/machine)) var/mob/living/carbon/human/machine/T = target - T.adjust_nutrition(adapter_efficiency * (power_sent / 10)) + T.adjust_nutrition(AI.adapter_efficiency * (power_sent / 10)) // Handles draining the SMES for(var/obj/machinery/power/smes/power_source in A) @@ -233,7 +249,6 @@ continue power_source.charge -= power_sent break - var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 20 user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) @@ -251,6 +266,7 @@ program_name = "Repair Nanites" program_id = "repair_nanites" description = "Repair an APC, Borg, or Mech with large numbers of robotic nanomachines!" + cost = 2 nanite_cost = 75 power_type = /datum/spell/ai_spell/ranged/repair_nanites unlock_text = "Repair nanomachine firmware installation complete!" @@ -266,15 +282,14 @@ level_max = 10 selection_activated_message = "You prepare to order your nanomachines to repair..." selection_deactivated_message = "You rescind the order." - var/universal_adapter = FALSE - var/adapter_efficiency = 0.5 /datum/spell/ai_spell/ranged/repair_nanites/cast(list/targets, mob/user) var/target = targets[1] if(!istype(target, /mob/living/silicon/robot) && !istype(target, /obj/machinery/power/apc) && !istype(target, /obj/mecha) && !istype(target, /mob/living/carbon/human/machine)) to_chat(user, "You can only recharge borgs, mechs, and APCs!") return - if(istype(target, /mob/living/carbon/human/machine) && !universal_adapter) + var/mob/living/silicon/ai/AI = user + if(istype(target, /mob/living/carbon/human/machine) && !AI.universal_adapter) to_chat(user, "This software lacks the required upgrade to recharge IPCs!") return var/area/A = get_area(user) @@ -283,17 +298,15 @@ return if(istype(target, /obj/mecha)|| istype(target, /obj/machinery/power/apc)) var/obj/T = target - T.obj_integrity += min(T.max_integrity, T.max_integrity * (0.2 + max(0.3, (0.1 * spell_level)))) + T.obj_integrity += min(T.max_integrity, T.max_integrity * (0.2 + min(0.3, (0.1 * spell_level)))) if(istype(target, /mob/living/silicon/robot)) var/mob/living/silicon/robot/T = target - var/damage_healed = adapter_efficiency * (20 + (max(30, (10 * spell_level)))) + var/damage_healed = 20 + (min(30, (10 * spell_level))) T.heal_overall_damage(damage_healed, damage_healed) if(istype(target, /mob/living/carbon/human/machine)) var/mob/living/carbon/human/machine/T = target - var/damage_healed = adapter_efficiency * (20 + (max(30, (10 * spell_level)))) + var/damage_healed = AI.adapter_efficiency * (20 + (min(30, (10 * spell_level)))) T.heal_overall_damage(damage_healed, damage_healed, TRUE, 0, 1) - - var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 75 user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) @@ -304,3 +317,21 @@ /datum/spell/ai_spell/ranged/repair_nanites/on_purchase_upgrade() cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - ((spell_level-3) * 60)), 30 SECONDS) + +// Universal Adapter - Unlocks usage of repair nanites and power shunt for IPCs +/datum/ai_program/universal_adapter + program_name = "Universal Adapter" + program_id = "universal_adapter" + description = "Upgraded firmware allows IPCs to be valid targets for Power Shunt and Repair Nanites, at half efficiency." + nanite_cost = 0 + unlock_text = "Universal adapter installation complete!" + upgrade = TRUE + +/datum/ai_program/universal_adapter/upgrade(mob/user) + var/mob/living/silicon/ai/AI = user + if(!istype(user)) + return + AI.universal_adapter = TRUE + AI.adapter_efficiency = 0.5 + (0.1 * upgrade_level) + upgrade_level++ + installed = TRUE From 84736688399312c764383557479115c471f464ba Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 9 Jan 2025 23:28:23 -0500 Subject: [PATCH 09/44] Door Override --- .../mob/living/silicon/ai/ai_programs.dm | 55 ++++++++++++++++++- 1 file changed, 54 insertions(+), 1 deletion(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 5b3c7cb3ec56..21b740446f83 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -192,7 +192,7 @@ return C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) -/datum/spell/ai_spell/ranged/on_purchase_upgrade() +/datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) // Power Shunt - Recharges things from your SMES @@ -335,3 +335,56 @@ AI.adapter_efficiency = 0.5 + (0.1 * upgrade_level) upgrade_level++ installed = TRUE + +// Door Override - Repairs door wires if the AI wire is not cut +/datum/ai_program/rgb_lighting + program_name = "Door Override" + program_id = "door_override" + description = "Repair an airlocks's wires, if the AI control wire is not cut." + nanite_cost = 25 + power_type = /datum/spell/ai_spell/ranged/door_override + unlock_text = "Door repair and override firmware installation complete!" + +/datum/spell/ai_spell/ranged/door_override + name = "Door Override" + desc = "Repair the wires in an airlock that still has an intact AI control wire." + action_icon_state = "light" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 60 SECONDS + cooldown_min = 60 SECONDS + level_max = 5 + selection_activated_message = "You hook into the station's lighting controller..." + selection_deactivated_message = "You cancel the request from the lighting controller." + +/datum/spell/ai_spell/ranged/door_override/cast(list/targets, mob/user) + var/obj/machinery/door/airlock/target = targets[1] + if(!istype(target)) + to_chat(user, "You can only repair airlocks!") + return + + if(target.wires.is_cut(WIRE_AI_CONTROL)) + to_chat(user, "Error: Null Connection to Airlock!") + return + + var/turf/T = get_turf(target) + var/obj/effect/temp_visual/rcd_effect/spawning_effect = new(T) + QDEL_IN(spawning_effect, (6 - spell_level) SECONDS) + if(do_after_once(user, (6 - spell_level) SECONDS, target = target, allow_moving = TRUE)) + target.wires.repair() + playsound(T, 'sound/items/deconstruct.ogg', 100, TRUE) + if(spell_level >= 5) + target.emagged = FALSE + target.electronics = initial(target.electronics) + + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 25 + user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + +/datum/spell/ai_spell/ranged/door_override/on_purchase_upgrade() + if(spell_level == 5) + desc += " Firmware version sufficient enough to repair damage caused by a cryptographic sequencer." From 5537d5214650e79e69dbe91329d2e980be452dff Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sat, 11 Jan 2025 02:24:41 -0500 Subject: [PATCH 10/44] Nanofrost, Program Icons, Door Override Bug Fixes --- .../mob/living/silicon/ai/ai_programs.dm | 80 ++++++++++++++++--- 1 file changed, 68 insertions(+), 12 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 21b740446f83..644e4cdd378c 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -135,6 +135,9 @@ /datum/ai_program/proc/upgrade(mob/user) return +/datum/ai_program/proc/downgrade(mob/user) + return + /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) . = ..() user.program_picker.use(user) @@ -151,7 +154,8 @@ /datum/spell/ai_spell/ranged/rgb_lighting name = "RGB Lighting" desc = "Changes the color of a selected light" - action_icon_state = "light" + action_icon = 'icons/obj/lighting.dmi' + action_icon_state = "random_glowstick" ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' auto_use_uses = FALSE base_cooldown = 30 SECONDS @@ -207,7 +211,8 @@ /datum/spell/ai_spell/ranged/power_shunt name = "Power Shunt" desc = "Recharge an APC, Borg, or Mech with power directly from your SMES" - action_icon_state = "light" + action_icon = 'icons/obj/power.dmi' + action_icon_state = "smes-o" ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' auto_use_uses = FALSE base_cooldown = 300 SECONDS @@ -274,7 +279,8 @@ /datum/spell/ai_spell/ranged/repair_nanites name = "Repair Nanites" desc = "Repair an APC, Borg, or Mech with large numbers of robotic nanomachines!" - action_icon_state = "light" + action_icon = 'icons/obj/surgery.dmi' + action_icon_state = "tube" ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' auto_use_uses = FALSE base_cooldown = 450 SECONDS @@ -337,10 +343,11 @@ installed = TRUE // Door Override - Repairs door wires if the AI wire is not cut -/datum/ai_program/rgb_lighting +/datum/ai_program/door_override program_name = "Door Override" program_id = "door_override" description = "Repair an airlocks's wires, if the AI control wire is not cut." + cost = 2 nanite_cost = 25 power_type = /datum/spell/ai_spell/ranged/door_override unlock_text = "Door repair and override firmware installation complete!" @@ -348,7 +355,8 @@ /datum/spell/ai_spell/ranged/door_override name = "Door Override" desc = "Repair the wires in an airlock that still has an intact AI control wire." - action_icon_state = "light" + action_icon = 'icons/obj/doors/doorint.dmi' + action_icon_state = "door_closed" ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' auto_use_uses = FALSE base_cooldown = 60 SECONDS @@ -368,23 +376,71 @@ return var/turf/T = get_turf(target) + var/mob/living/silicon/ai/AI = user + var/duration = (6 - spell_level) SECONDS + AI.program_picker.nanites -= 25 + user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = duration) var/obj/effect/temp_visual/rcd_effect/spawning_effect = new(T) - QDEL_IN(spawning_effect, (6 - spell_level) SECONDS) - if(do_after_once(user, (6 - spell_level) SECONDS, target = target, allow_moving = TRUE)) + spawning_effect.duration = duration + QDEL_IN(spawning_effect, duration) + if(do_after_once(user, duration, target = target, allow_moving = TRUE)) target.wires.repair() playsound(T, 'sound/items/deconstruct.ogg', 100, TRUE) if(spell_level >= 5) target.emagged = FALSE target.electronics = initial(target.electronics) +/datum/spell/ai_spell/ranged/door_override/on_purchase_upgrade() + if(spell_level == 5) + desc += " Firmware version sufficient enough to repair damage caused by a cryptographic sequencer." + +// Automated Extinguishing System: Deploys nanofrost to a target tile +/datum/ai_program/extinguishing_system + program_name = "Automated Extinguishing System" + program_id = "extinguishing_system" + description = "Deploy a nanofrost globule to a target to rapidly extinguish plasmafires." + cost = 3 + nanite_cost = 50 + power_type = /datum/spell/ai_spell/ranged/extinguishing_system + unlock_text = "Nanofrost synthesizer online." + +/datum/spell/ai_spell/ranged/extinguishing_system + name = "Automated Extinguishing System" + desc = "Deploy a nanofrost globule to a target to rapidly extinguish plasmafires." + action_icon = 'icons/effects/effects.dmi' + action_icon_state = "frozen_smoke_capsule" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 300 SECONDS + cooldown_min = 30 SECONDS + level_max = 7 + selection_activated_message = "You prepare to synthesize a nanofrost globule..." + selection_deactivated_message = "You let the nanofrost dissipate." + +/datum/spell/ai_spell/ranged/extinguishing_system/cast(list/targets, mob/user) + var/turf/target = get_turf(targets[1]) + if(!isturf(target)) + to_chat(user, "Invalid location for nanofrost deployment!") + return + + var/obj/effect/nanofrost_container/nanofrost = new /obj/effect/nanofrost_container(target) + log_game("[key_name(user)] used Nanofrost at [get_area(target)] ([target.x], [target.y], [target.z]).") var/mob/living/silicon/ai/AI = user - AI.program_picker.nanites -= 25 - user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) + AI.program_picker.nanites -= 50 + user.playsound_local(user, 'sound/items/syringeproj.ogg', 40, FALSE, use_reverb = FALSE) + playsound(src, 'sound/items/syringeproj.ogg', 40, TRUE) var/obj/machinery/camera/C = find_nearest_camera(target) if(!istype(C)) + sleep(5) + nanofrost.Smoke() return C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + sleep(5) + nanofrost.Smoke() -/datum/spell/ai_spell/ranged/door_override/on_purchase_upgrade() - if(spell_level == 5) - desc += " Firmware version sufficient enough to repair damage caused by a cryptographic sequencer." +/datum/spell/ai_spell/ranged/extinguishing_system/on_purchase_upgrade() + cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - (spell_level * 30)), 30 SECONDS) From 3be17de11c48f15dd9318b14c62b9534e658cfb3 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 12 Jan 2025 02:15:43 -0500 Subject: [PATCH 11/44] Sprites for AI machines --- icons/obj/machines/ai_machinery.dmi | Bin 0 -> 5242 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 icons/obj/machines/ai_machinery.dmi diff --git a/icons/obj/machines/ai_machinery.dmi b/icons/obj/machines/ai_machinery.dmi new file mode 100644 index 0000000000000000000000000000000000000000..c2af351214a7d9d2a55a68afc1098eac4a51ea8d GIT binary patch literal 5242 zcmbVQc|26@+aJVKWO}S+8;R^o5fx@k(L~JH*EBtOB(i16HjGF@QWDBC63H&v5`%0Z zl%0%`WyWsCI%5{U>FN2spLhA^ecwOMIrq8GbzkSYzW23!&xtcfz>gdjI}88-ju>At zv}9kW*+=t19`;%CzRxK8(h+KHA7JR}@8aj~8{qEa4FCjZCMLu9qcnsJM^_ca#&RtT zgS`3LDxT_Uk>4j?F{X1-c5L}%-YdQAWdxj2e?H_EJC}Y-1(ILI?Uh$Fo^8}4ESIHX zKIS55DPxe$4FN?~mCVtqAO{bIakI zCLx8rBUhrTtK-@gsGn`oZFVL0Z@eZPy@qVjhMu{JQ5GCO;w!2-3RT7Ji!I+&N^4W! zm59US1jg2MmV@+zh+o6j&ik)3_UDLv{@0-KnsC z<3Mm%aY{3=$&vQ*fONu1U1KTgwCGC$T%a4oybTmpU0=znLP)x@=b2C3HD{E+KO3EFqcyztT zE=7xz{qpHBPT#%9>%sRXajRba^{P%a=YBjnc3#hW+WG;>KDYj4kdoui0)v^!no}0tZr5&_X z@KLrqj~D~a<`Ea5p<6m=D9i^mN&nP4vAwYcjUU*^=kstdr7*39BBWTXe4KhU$TtwJIM->^Ou zDjptEdu4R*+&8D)fxV2q3rvDPee3Nuz7SjVay^Jc!x^)ChDsx)aaO!}(`wB0ZuMi$ zgR4Ty0Lp1cwhIRkz&8ot^b?5KWvrke?V ztdO;+Zl34sML`2{PVmrX(D&s)=Ay4#NZTWq+w`4%LqzKwv6x%CC1~`A7OIZ15_fiS z=JFeKVL5p|IGrdu&)BSrM7RH3Nc&<}4&Wmu?MeLg)dK#lWc)*B0I}rdYxnf@f{kJ2 z3Pqd*SH|{eb@M6eXOXfA&Wvf%)!%C!{6ygq{rkhpfN1(C7+zkjS~6?w9_-vR(G+8= z^dw!!;b*bk4J(G6Q`dQ(4a^{;i~mO$+oJXJQ``BowD}xO;B&VYL~e&O)gldtbzw0z|b| zcFm13>cTc`b%qfRy!MMG5C0B+q@MDtqAE?(`=AI5TH#j*0jp0hV$SohmA(MMjvjyw zt5Uh5KsX}^gQEpVkO8wIr=xwIfiMQ-mfA0|P-*J4(_Aa~D4MLg@e_0qLKUHrfd|0o z1oVGjX43}^gF#pK0+qkmGi@#jI1u*;4NO4RuvYRzPnvwA?wS+AF#-KTxd*(GcZFff zpdCVgVmMvi$`!m2+JQv+Y#=IlBRW`-HH>kF8o-D``p~=U4^%o#DCfJ(BlHRR%DSnHh9}60ea1m<)&LeL%ZBrJp6TXTVzR{p#zsR zOsZb@w3?%I_G2AE8f1}U`sgZ6K!N2jnY`*Wpj=t{F!pXwo;vR?8zzFv-y8qW7J3Y9n zfO$AV;}y|Ap>xIQI-{s{Uc_FF^X-!QO(X?lh*kVejwZKS4{_^v}zs{eCzi8D}Ge z(Pl?)*XSNsQA}ar@0(pOj==qLqu)3Gm$?29hs!TQ4zM#u*n08+<}@~91vyFl^#1*6 z8-J`VJLwA75tAUVgQq``!!*VNW)21P<9B()oF4_;_o!UwgHT@(;WhHJ#gTi@rZ+cX zF7RV`H?!7@Vqs3y{)=@Rq)g3NYHRX*RW#upCm1cruxCYHIC;_LPZ9G=P0V9Q&^w%= z%np~^6PLg=+Xq~X`ejk~&EW9-PqJ+D;=$u!b0ML>ia?I|?0$V3eWX~IFx z`5zOtgI_F8-d=qrLfU7j;UB*o%-TM6075-Qb^W0CKIx^mt%CPr@Wycj{#LZ!TdQ`f zI!euYQ+4!1)MVNe&c{d52UQ-iWl$dKR=-xC>Q)u*?mgog!JmEf1t{u~az7!9*dpJw zdUPlW2u43=*!z4YtF-W{H`%)6}Jx<}R?kd(QUmX|#zOA@4`_SsX>! zqmFgXjmD;B0Y4tc$u?CjQQ+c2_V(J46vY-WhEX_hBb~Ory`8^G^$^nDnKS9kk~@wj zn~_h_xi;3*hv2|7x3)4|W*ZNMxic$uGUq8jK;Jg_%e(#*Ib7V}DY)yw{RsTJAy}-O zPxfqolTjnw^RNPf%R$^-nZe4{HFOMwKsQwgpfUQ!%%DNhFXelo1VFNDEn}qEa+fq; z;jPU!V(wSoB#WW{ArS%vBsKRli<}VeT`sow6e~Ixk8uZDkEL6S^l>Z?(d|%`O6b;m zd{@rw6G}9?N5FLrL~hY(XXi9^yw4rd?yl;5geU3vxVu^!Ecqxh%XH9MM(t2&kxK?x6QKyX&O^ub$rzoLb3$PjgsWQ;+Hw zfi6({_x8(~P#_ko|zuep_nQS7GCZe?O(G1oU|vjhFk znuOYHXsm^_>L7J^zPutZCXNyQtF)~-cv2myCNvPWnJD!>%5qSFT|=zU{h1moNkmqi zoC}NsPuPs}J6eYgry)gB!{_oxbM$sw%y%tDqd^hZsUJ6iDPGLI@w?frva9it>(D;6 zo6O<6_eL1kXk2@W3l3>&{Y(?{G3ATXz^gia+FiBI`#Ek|?ljjXAm3sB=ObnjrLt)! z-hs+STGYA03_Z$K9h+R!b47hb*$?pckPsWk=A4&>rlt*I+R7sAXq_PqfX%0xyBs$j zf~eD^7`D&Nxz20`0*;bC7$sfmF^)ZgCVOpg(Q}Q+Zd_n=1{xJsnftq|;Ish=bNxIJ zsx}R$nnQil73PzNCgx-3tn&_3%0AX4KwfRg5M*-nZZSJN5Bu(G53 z&P)CN?|&U<9JCtzFzFB87>Ygv^D)0}+x;19w(>gJ-fCC?rT>TN#^Advj4Pm-Xik;o z=|ROfsFNeIxr7Q&ob-8tjY%dC=Ol%3Ce=aOHp@9*I0{yEd@9lf=4ag8JZbh-Jc!TUjOF=vp$+4+zw>)o z-pK1H`@2_`FZee*QewHl3=@j-hD5~(<0qTbS~BcinjN=(gRxq2``Oi3<{|eAIM`(l z?IoH*;2}Ng-4ona^=I?b!(df*nIt^|!JfiS2%IPm{TUvxoRl$_= zz^Zev?QvcF=^-_onb8Ex?zZ&mE`>@9m9%S$S}jM}F3UsG?)PxYSt((f>+mL1>R+)( z;!i;+C_F_;Qg_AvRq(!{a;Ij(nHziy0zhotN8gH%ggK%^boj6Dz?er0nXj{M1D2;Zk|R7@GhUi-+8!|=XL2e`7C{rNe>&00qxGgv!oQe(`CGC zW6Ou$A}ybbY53k4g-c3aUg}g4%#=~6hTh26+FkgF14C7>e;A`x+)~A^=1BxsE0oCx zG4pUns+X#j*+O#dm}_VCY3fj=`MWoaeG7YXNu;t<$FTKqb%zQac(Etn8DJypuc#{%tp_{2Jeqw7%e~luk_W;u90x1+^4F zqBvTGUzVoET5E3=NlX9y43K8s-CC-ZX4UK8z032x=*e7}uDA2BFE<_*kLv>woPlP{QL+!Q!qv|pc`4X&9O zoT*Q92vZ9kH>Rte&t7=k9eCv93uf;~!NSsa|Inz44>uJ`WvO+19{mU63)qA=1IS-c zpyTz%>2iS1Thx|Hqx09jN}9l%E0X zh?<{;ebubV8_%_SmRu*OmP#+6({(6)SS*i-|%|}09aA|#+pkG=N*5FtuE_+Fn` z@&GQLnC)RsWUVYLkS8-OHtSx@jt(O9{gLC^gCre`9fKwVX0mt+^sl|UD#CfJ%#TY1LpF3*WgpHf-x%_bp_+X}Ih}y4JJYplviacsv z+?@}VJ|JxL>q$kd-iZ1a$}Ocp literal 0 HcmV?d00001 From 9edc57bc1831dd98824ed5b133154997f978e839 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 12 Jan 2025 03:11:57 -0500 Subject: [PATCH 12/44] Bluespace Miner, Multimarket Analyzer, Light Replacer --- code/modules/mob/living/silicon/ai/ai_mob.dm | 21 +++++ .../mob/living/silicon/ai/ai_programs.dm | 89 ++++++++++++++++++- 2 files changed, 108 insertions(+), 2 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 68894d33c70a..edaa25805fe6 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -73,6 +73,12 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( var/universal_adapter = FALSE /// How effective is the adapter? var/adapter_efficiency = 0.5 + /// Has the AI unlocked a bluespace miner? + var/bluespace_miner = FALSE + /// Credit payout rate + var/bluespace_miner_rate = 100 + /// Time until next payout + var/next_payout = 10 MINUTES //MALFUNCTION var/datum/module_picker/malf_picker @@ -387,6 +393,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( power_state = ACTIVE_POWER_USE var/mob/living/silicon/ai/powered_ai = null invisibility = 100 + var/bluespace_miner_power = 0 /obj/machinery/ai_powersupply/New(mob/living/silicon/ai/ai=null) powered_ai = ai @@ -410,6 +417,20 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( change_power_mode(NO_POWER_USE) if(powered_ai.anchored) change_power_mode(ACTIVE_POWER_USE) + if(powered_ai.bluespace_miner) + // Money money money + if(powered_ai.next_payout <= world.time) + powered_ai.next_payout = 10 MINUTES + world.time + var/datum/economy/line_item/science_item = new + science_item.account = GLOB.station_money_database.get_account_by_department(DEPARTMENT_SCIENCE) + science_item.credits = powered_ai.bluespace_miner_rate + science_item.reason = "AI Bluespace Miner Earnings" + manifest.line_items += science_item + // Update power consumption if powering a bluespace miner + if(bluespace_miner_power == powered_ai.bluespace_miner_rate * 2.5) + return + bluespace_miner_power = powered_ai.bluespace_miner_rate * 2.5 + update_active_power_consumption(power_channel, active_power_consumption + bluespace_miner_power) /mob/living/silicon/ai/update_icons() . = ..() diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 644e4cdd378c..41cc1d5b95e8 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -189,7 +189,7 @@ L.brightness_color = new_color var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 5 - user.playsound_local(user, "sound/effects/spray.ogg", 50, FALSE, use_reverb = FALSE) + user.playsound_local(user, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) if(!istype(C)) @@ -255,7 +255,7 @@ power_source.charge -= power_sent break AI.program_picker.nanites -= 20 - user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) + user.playsound_local(user, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) if(!istype(C)) @@ -444,3 +444,88 @@ /datum/spell/ai_spell/ranged/extinguishing_system/on_purchase_upgrade() cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - (spell_level * 30)), 30 SECONDS) + +// Bluespace Miner Subsystem - Makes money for science, at the cost of extra power drain +/datum/ai_program/bluespace_miner + program_name = "Bluespace Miner Subsystem" + program_id = "bluespace_miner" + description = "You link yourself to a miniature bluespace harvester, generating income for the science account at the cost of increasing your core's power needs." + nanite_cost = 0 + max_level = 5 + unlock_text = "Bluespace miner installation complete!" + upgrade = TRUE + +/datum/ai_program/bluespace_miner/upgrade(mob/user) + var/mob/living/silicon/ai/AI = user + if(!istype(user)) + return + AI.bluespace_miner_rate = 100 + (100 * upgrade_level) + AI.next_payout = 10 MINUTES + world.time + AI.bluespace_miner = TRUE + upgrade_level++ + installed = TRUE + + +// Multimarket Analysis Subsystem: Reduce prices of things at cargo +/datum/ai_program/multimarket_analyser + program_name = "Multimarket Analysis Subsystem" + program_id = "multimarket_analyser" + description = "You connect to a digital marketplace to price-check all orders from the station, ensuring you get the best prices! This reduces the cost of crates in cargo!" + nanite_cost = 0 + unlock_text = "Online marketplace detected... connected!" + max_level = 6 + upgrade = TRUE + /// Track the original modifier + var/original_price_mod = SSeconomy.pack_price_modifier + +/datum/ai_program/multimarket_analyser/upgrade(mob/user) + var/mob/living/silicon/ai/AI = user + if(!istype(user)) + return + SSeconomy.pack_price_modifier = original_price_mod * (0.95 - (0.05 * upgrade_level)) + upgrade_level++ + installed = TRUE + +// RGB Lighting - Recolors Lights +/datum/ai_program/light_repair + program_name = "Light Synthesizer" + program_id = "light_repair" + description = "Replace damaged or missing lightbulbs." + nanite_cost = 5 + power_type = /datum/spell/ai_spell/ranged/light_repair + unlock_text = "Light replacer configuration installed." + +/datum/spell/ai_spell/ranged/light_repair + name = "Light Synthesizer" + desc = "Replace damaged or missing lightbulbs." + action_icon = 'icons/obj/janitor.dmi' + action_icon_state = "lightreplacer0" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 30 SECONDS + cooldown_min = 5 SECONDS + level_max = 5 + selection_activated_message = "You prepare to synthesize a lightbulb..." + selection_deactivated_message = "You cancel the request." + +/datum/spell/ai_spell/ranged/light_repair/cast(list/targets, mob/user) + var/obj/machinery/light/target = targets[1] + if(!istype(target)) + to_chat(user, "You can only repair lights!") + return + var/mob/living/silicon/ai/AI = user + // Handle repairs here since we're using a spell and not a tool + target.status = LIGHT_OK + target.switchcount = 0 + target.emagged = FALSE + target.on = target.has_power() + AI.program_picker.nanites -= 5 + user.playsound_local(user, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + +/datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() + cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) From 4cffe1ba2d6a0738445ab9c708b85d47882b5dcf Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 12 Jan 2025 03:56:06 -0500 Subject: [PATCH 13/44] Fixes economy thing with bluespace miner --- code/modules/mob/living/silicon/ai/ai_mob.dm | 9 ++++----- code/modules/mob/living/silicon/ai/ai_programs.dm | 9 +++++---- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index edaa25805fe6..dc7f4f7b9de7 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -421,11 +421,10 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( // Money money money if(powered_ai.next_payout <= world.time) powered_ai.next_payout = 10 MINUTES + world.time - var/datum/economy/line_item/science_item = new - science_item.account = GLOB.station_money_database.get_account_by_department(DEPARTMENT_SCIENCE) - science_item.credits = powered_ai.bluespace_miner_rate - science_item.reason = "AI Bluespace Miner Earnings" - manifest.line_items += science_item + var/account = GLOB.station_money_database.get_account_by_department(DEPARTMENT_SCIENCE) + var/datum/money_account_database/main_station/station_db = GLOB.station_money_database + station_db.credit_account(account, powered_ai.bluespace_miner_rate, "Bluespace Miner Production", "AI Bluespace Miner Subsystem", FALSE) + // Update power consumption if powering a bluespace miner if(bluespace_miner_power == powered_ai.bluespace_miner_rate * 2.5) return diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 41cc1d5b95e8..5f7e26d1e8f5 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -476,12 +476,13 @@ max_level = 6 upgrade = TRUE /// Track the original modifier - var/original_price_mod = SSeconomy.pack_price_modifier + var/original_price_mod + +/datum/ai_program/multimarket_analyser/New() + . = ..() + original_price_mod = SSeconomy.pack_price_modifier /datum/ai_program/multimarket_analyser/upgrade(mob/user) - var/mob/living/silicon/ai/AI = user - if(!istype(user)) - return SSeconomy.pack_price_modifier = original_price_mod * (0.95 - (0.05 * upgrade_level)) upgrade_level++ installed = TRUE From 729fa86d37fb3d60796a34b1aaa9947780ad4555 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 14 Jan 2025 00:59:38 -0500 Subject: [PATCH 14/44] Enhanced Door Controls, Nanosurgeons --- code/_onclick/ai_onclick.dm | 4 +- .../mob/living/silicon/ai/ai_programs.dm | 71 +++++++++++++++++-- .../modules/mob/living/silicon/silicon_mob.dm | 3 + 3 files changed, 71 insertions(+), 7 deletions(-) diff --git a/code/_onclick/ai_onclick.dm b/code/_onclick/ai_onclick.dm index 3801ae81dd78..5e31b5e9c152 100644 --- a/code/_onclick/ai_onclick.dm +++ b/code/_onclick/ai_onclick.dm @@ -224,7 +224,7 @@ /obj/machinery/door/airlock/AICtrlClick(mob/living/silicon/user) // Bolts doors if(!ai_control_check(user)) return - if(ispulsedemon(user) || user.can_instant_lockdown() || do_after_once(user, 3 SECONDS, needhand = FALSE, target = src, allow_moving = TRUE, attempt_cancel_message = "Bolting [src] cancelled.", special_identifier = "Bolt")) + if(ispulsedemon(user) || user.can_instant_lockdown() || do_after_once(user, user.door_bolt_delay, needhand = FALSE, target = src, allow_moving = TRUE, attempt_cancel_message = "Bolting [src] cancelled.", special_identifier = "Bolt")) toggle_bolt(user) @@ -236,7 +236,7 @@ if(isElectrified()) electrify(0, user, TRUE) // un-shock else - if(ispulsedemon(user) || user.can_instant_lockdown() || do_after_once(user, 3 SECONDS, target = src, allow_moving = TRUE, attempt_cancel_message = "Shocking [src] cancelled.", special_identifier = "Shock")) + if(ispulsedemon(user) || user.can_instant_lockdown() || do_after_once(user, user.door_bolt_delay, target = src, allow_moving = TRUE, attempt_cancel_message = "Shocking [src] cancelled.", special_identifier = "Shock")) electrify(-1, user, TRUE) // permanent shock + audio cue playsound(loc, "sparks", 100, TRUE, SHORT_RANGE_SOUND_EXTRARANGE) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 5f7e26d1e8f5..b6175a99a395 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -298,10 +298,6 @@ if(istype(target, /mob/living/carbon/human/machine) && !AI.universal_adapter) to_chat(user, "This software lacks the required upgrade to recharge IPCs!") return - var/area/A = get_area(user) - if(A == null) - to_chat(user, "No SMES detected to power from!") - return if(istype(target, /obj/mecha)|| istype(target, /obj/machinery/power/apc)) var/obj/T = target T.obj_integrity += min(T.max_integrity, T.max_integrity * (0.2 + min(0.3, (0.1 * spell_level)))) @@ -465,7 +461,6 @@ upgrade_level++ installed = TRUE - // Multimarket Analysis Subsystem: Reduce prices of things at cargo /datum/ai_program/multimarket_analyser program_name = "Multimarket Analysis Subsystem" @@ -530,3 +525,69 @@ /datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) + +// Nanosurgeon Deployment - Uses large numbers of nanites to heal things +/datum/ai_program/nanosurgeon_deployment + program_name = "Nanosurgeon Deployment" + program_id = "nanosurgeon_deployment" + description = "Heal a crew member with large numbers of robotic nanomachines!" + cost = 3 + nanite_cost = 75 + power_type = /datum/spell/ai_spell/ranged/nanosurgeon_deployment + unlock_text = "Surgical nanomachine firmware installation complete!" + +/datum/spell/ai_spell/ranged/nanosurgeon_deployment + name = "Nanosurgeon Deployment" + desc = "Heal a crew member with large numbers of robotic nanomachines!" + action_icon = 'icons/obj/surgery.dmi' + action_icon_state = "scalpel_laser1_on" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 450 SECONDS + cooldown_min = 30 SECONDS + level_max = 8 + selection_activated_message = "You prepare to order your nanomachines to perform surgery..." + selection_deactivated_message = "You rescind the order." + +/datum/spell/ai_spell/ranged/nanosurgeon_deployment/cast(list/targets, mob/user) + var/mob/living/carbon/human/target = targets[1] + if(!istype(target) || istype(target, /mob/living/carbon/human/machine)) + to_chat(user, "You can only heal organic crew!") + return + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 75 + user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "medbeam", icon = 'icons/effects/beam.dmi', time = 10) + if(do_after_once(AI, 5 SECONDS, target = target, allow_moving = TRUE)) + var/damage_healed = 20 + (min(30, (10 * spell_level))) + target.heal_overall_damage(damage_healed, damage_healed) + if(spell_level >= 5) + for(var/obj/item/organ/external/E in target.bodyparts) + if(prob(5*spell_level)) + E.mend_fracture() + E.fix_internal_bleeding() + E.fix_burn_wound() + +// Enhanced Door Controls: Reduces delay in bolting and shocking doors +/datum/ai_program/enhanced_doors + program_name = "Enhanced Door Controls" + program_id = "enhanced_doors" + description = "You enhance the subroutines that let you control doors, speeding up response times!" + nanite_cost = 0 + unlock_text = "Doors connected and optimized. You feel right at home." + max_level = 5 + upgrade = TRUE + /// Track the original delay + var/original_door_delay = 3 SECONDS + +/datum/ai_program/enhanced_doors/upgrade(mob/user) + var/mob/living/silicon/ai/AI = user + if(!istype(user)) + return + upgrade_level++ + AI.door_bolt_delay = original_door_delay * (1 - (upgrade_level * 0.1)) + installed = TRUE diff --git a/code/modules/mob/living/silicon/silicon_mob.dm b/code/modules/mob/living/silicon/silicon_mob.dm index a0997ce25e3c..da21f10c35b2 100644 --- a/code/modules/mob/living/silicon/silicon_mob.dm +++ b/code/modules/mob/living/silicon/silicon_mob.dm @@ -80,6 +80,9 @@ var/datum/ai_laws/laws = null var/list/additional_law_channels = list("State" = "") + /// The delay used when toggling door bolts or electrification + var/door_bolt_delay = 3 SECONDS + /mob/living/silicon/New() GLOB.silicon_mob_list |= src ..() From 1e0965e6f57f9a953c07b17a899f655f9120273f Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 00:05:42 -0500 Subject: [PATCH 15/44] Experimental Research Subsystem --- .../mob/living/silicon/ai/ai_programs.dm | 69 +++++++++++++++++++ 1 file changed, 69 insertions(+) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index b6175a99a395..86c900a1f0a5 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -591,3 +591,72 @@ upgrade_level++ AI.door_bolt_delay = original_door_delay * (1 - (upgrade_level * 0.1)) installed = TRUE + +// Experimental Research Subsystem - Knowledge is power +/datum/ai_program/research_subsystem + program_name = "Experimental Research Subsystem" + program_id = "research_subsystem" + description = "Put your processors to work spinning centrifuges and studying results. You unlock a new point of research in a random field." + cost = 5 + nanite_cost = 60 + power_type = /datum/spell/ai_spell/research_subsystem + unlock_text = "Research and Discovery submodule installation complete." + +/datum/spell/ai_spell/research_subsystem + name = "Experimental Research Subsystem" + desc = "Heal a crew member with large numbers of robotic nanomachines!" + action_icon = 'icons/obj/machines/research.dmi' + action_icon_state = "tdoppler" + auto_use_uses = FALSE + base_cooldown = 900 SECONDS + cooldown_min = 600 SECONDS + starts_charged = FALSE + level_max = 10 + selection_activated_message = "You spool up your research tools..." + selection_deactivated_message = "You spool down." + var/rnd_server = "station_rnd" + +/datum/spell/ai_spell/research_subsystem/cast(list/targets, mob/user) + // First, find the RND server + var/network_manager_uid = null + for(var/obj/machinery/computer/rnd_network_controller/RNC in GLOB.rnd_network_managers) + if(RNC.network_name == rnd_server) + network_manager_uid = RNC.UID() + break + var/obj/machinery/computer/rnd_network_controller/RNC = locateUID(network_manager_uid) + if(!RNC) // Could not find the RND server. It probably blew up. + return + + var/upgraded = FALSE + var/datum/research/files = RNC.research_files + if(!files) + return + var/list/possible_tech = list() + for(var/datum/tech/T in files.possible_tech) + possible_tech += T + while(!upgraded) + var/datum/tech/tech_to_upgrade = pick_n_take(possible_tech) + // If there are no possible techs to upgrade, stop the program + if(!tech_to_upgrade) + to_chat(user, "Current research cannot be discovered any further.") + return + // No illegals until level 10 + if(spell_level < 10 && istype(tech_to_upgrade, /datum/tech/syndicate)) + continue + // No alien research + if(istype(tech_to_upgrade, /datum/tech/abductor)) + continue + var/datum/tech/current = files.find_possible_tech_with_id(tech_to_upgrade.id) + if(!current) + continue + // If the tech is level 7 and the program too weak, don't upgrade + if(current.level >= 7 && spell_level < 5) + continue + // Nothing beyond 8 + if(current.level >= 8) + continue + files.UpdateTech(tech_to_upgrade.id, current.level + 1) + to_chat(user, "Discovered innovations has led to an increase in the [current] field!") + upgraded = TRUE + + From fefa974fdbbf6161097e7bac20af460b1c122896 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 00:07:01 -0500 Subject: [PATCH 16/44] Removed excess from RND subsystem --- code/modules/mob/living/silicon/ai/ai_programs.dm | 1 - 1 file changed, 1 deletion(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 86c900a1f0a5..1cc5da5ade29 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -613,7 +613,6 @@ starts_charged = FALSE level_max = 10 selection_activated_message = "You spool up your research tools..." - selection_deactivated_message = "You spool down." var/rnd_server = "station_rnd" /datum/spell/ai_spell/research_subsystem/cast(list/targets, mob/user) From e958a7745f01badaa7d2ee4f98c4213c5cdb194f Mon Sep 17 00:00:00 2001 From: XFirebirdX <142694283+XFirebirdX@users.noreply.github.com> Date: Thu, 16 Jan 2025 17:22:44 +0100 Subject: [PATCH 17/44] Adds Processing Node --- code/game/machinery/ai_resource.dm | 56 ++++++++++++++++++ code/game/machinery/machine_frame.dm | 14 +++++ .../research/designs/machine_designs.dm | 10 ++++ icons/obj/machines/ai_machinery.dmi | Bin 5242 -> 5244 bytes paradise.dme | 1 + 5 files changed, 81 insertions(+) create mode 100644 code/game/machinery/ai_resource.dm diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm new file mode 100644 index 000000000000..4a875d7f2d59 --- /dev/null +++ b/code/game/machinery/ai_resource.dm @@ -0,0 +1,56 @@ +/obj/machinery/processingnode + name = "Processing Node" + desc = "Test Description" + icon = 'icons/obj/machines/ai_machinery.dmi' + icon_state = "processor-off" + density = TRUE + anchored = TRUE + max_integrity = 100 + idle_power_consumption = 5 + active_power_consumption = 200 + + var/active = FALSE + var/mob/living/silicon/ai/assigned_ai = null + +/obj/machinery/processingnode/Initialize(mapload) + . = ..() + component_parts = list() + component_parts += new /obj/item/circuitboard/processingnode(null) + component_parts += new /obj/item/stock_parts/capacitor(null, 2) + component_parts += new /obj/item/stack/sheet/mineral/gold(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/silver(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/diamond(null, 1) + component_parts += new /obj/item/stack/cable_coil(null, 5) + RefreshParts() + +/obj/machinery/processingnode/attack_hand(user as mob) + to_chat(user, "You toggle the Processing Node from [active ? "On" : "Off"] to [active ? "Off" : "On"]") + active = !active + if(active) // We're booting up + // Find the AI with lowest memory + for(var/mob/living/silicon/ai/new_ai in GLOB.ai_list) + if(!assigned_ai) //not found + assigned_ai = new_ai //search for new in global ai list + if(assigned_ai.program_picker.memory > new_ai.program_picker.memory) + assigned_ai = new_ai + + if(!assigned_ai) // No eligible AI found, abort + active = FALSE + to_chat(user, "ERROR: No AI detected. Shutting down...") + to_chat(user, "The Processing Node turns off.") + else // We have an AI, up its memory + assigned_ai.program_picker.memory++ + + else // We're shutting down + // TODO rest of shutting down code + assigned_ai.program_picker.memory-- + assigned_ai = null + to_chat(user, "Turning off") + update_icon(UPDATE_ICON_STATE) + if(assigned_ai) + // "destroyed" "do" + // assigned_ai.program_picker.memory-- + // assigned_ai = null + +/obj/machinery/processingnode/update_icon_state() + icon_state = "processor-[active ? "on" : "off"]" diff --git a/code/game/machinery/machine_frame.dm b/code/game/machinery/machine_frame.dm index 7298d7c539f9..dae9f1e57c1c 100644 --- a/code/game/machinery/machine_frame.dm +++ b/code/game/machinery/machine_frame.dm @@ -1163,3 +1163,17 @@ to destroy them and players will be able to make replacements. /obj/item/stock_parts/micro_laser = 1, /obj/item/stack/cable_coil = 3, /obj/item/stack/sheet/plasteel = 5) + +/obj/item/circuitboard/processingnode + board_name = "Processing Node" + icon_state = "science" + build_path = /obj/machinery/processingnode + board_type = "machine" + origin_tech = "programming=4" + req_components = list( + /obj/item/stock_parts/capacitor = 2, + /obj/item/stack/sheet/mineral/gold = 10, + /obj/item/stack/sheet/mineral/silver = 10, + /obj/item/stack/sheet/mineral/diamond = 1, + /obj/item/stack/cable_coil = 5, + ) diff --git a/code/modules/research/designs/machine_designs.dm b/code/modules/research/designs/machine_designs.dm index 647ee8e23441..6ac302a31ea8 100644 --- a/code/modules/research/designs/machine_designs.dm +++ b/code/modules/research/designs/machine_designs.dm @@ -601,3 +601,13 @@ materials = list(MAT_GLASS = 1000) build_path = /obj/item/circuitboard/merch category = list("Misc. Machinery") + +/datum/design/processingnode + name = "Machine Design (Processing Node)" + desc = "The circuit board for a processing node." + id = "processingnode" + req_tech = list("programming" = 5) + build_type = IMPRINTER + materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) + build_path = /obj/machinery/processingnode + category = list("Misc. Machinery") diff --git a/icons/obj/machines/ai_machinery.dmi b/icons/obj/machines/ai_machinery.dmi index c2af351214a7d9d2a55a68afc1098eac4a51ea8d..ce28ed9a367654cb9a327ac3929f4ed28121e022 100644 GIT binary patch delta 221 zcmV<303!eTDEugpB!9?yR9JLGWpiV4X>fFDZ*Bkpc$|%r(F%ev7=^F5rx<#xQD)tB z6H0iI?=bYYjm%%Rq4f4G!%UhW=jQz5a6S&qXXo^iMl1lLh4Bpn1P*U^f+XsJgR#nwPmn$vM ztRqKrIms<7&6wg1m>$(V|pYo?Cb#i2j2L-3UYwq_l#Yb>}yH6`O& X(r0O&44>r%QX!v|!n4QrvGa!$4`Xkv delta 219 zcmV<103`qXDEcUnB!9+wR9JLGWpiV4X>fFDZ*Bkpc$|%rK@Ng26hznUDH_7D$6fj zuC!1%j~q_rBsWn1Mc06x(wCpBcO%+~96IJq9kO4CzQMM^OAgqab-b!n&Qa+x8BLNt VOR~8CFn7 Date: Thu, 16 Jan 2025 18:06:00 -0500 Subject: [PATCH 18/44] Processing node changes and fixes --- code/game/machinery/ai_resource.dm | 33 ++++++++++++------- code/game/machinery/machine_frame.dm | 4 +-- .../research/designs/machine_designs.dm | 6 ++-- 3 files changed, 26 insertions(+), 17 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 4a875d7f2d59..450a5f522c5c 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -1,4 +1,4 @@ -/obj/machinery/processingnode +/obj/machinery/processing_node name = "Processing Node" desc = "Test Description" icon = 'icons/obj/machines/ai_machinery.dmi' @@ -8,14 +8,15 @@ max_integrity = 100 idle_power_consumption = 5 active_power_consumption = 200 - + /// Is the machine active var/active = FALSE + /// What AI is this machine associated with var/mob/living/silicon/ai/assigned_ai = null -/obj/machinery/processingnode/Initialize(mapload) +/obj/machinery/processing_node/Initialize(mapload) . = ..() component_parts = list() - component_parts += new /obj/item/circuitboard/processingnode(null) + component_parts += new /obj/item/circuitboard/processing_node(null) component_parts += new /obj/item/stock_parts/capacitor(null, 2) component_parts += new /obj/item/stack/sheet/mineral/gold(null, 10) component_parts += new /obj/item/stack/sheet/mineral/silver(null, 10) @@ -23,7 +24,7 @@ component_parts += new /obj/item/stack/cable_coil(null, 5) RefreshParts() -/obj/machinery/processingnode/attack_hand(user as mob) +/obj/machinery/processing_node/attack_hand(user as mob) to_chat(user, "You toggle the Processing Node from [active ? "On" : "Off"] to [active ? "Off" : "On"]") active = !active if(active) // We're booting up @@ -42,15 +43,23 @@ assigned_ai.program_picker.memory++ else // We're shutting down - // TODO rest of shutting down code + if(assigned_ai) + assigned_ai.program_picker.memory-- + assigned_ai = null + update_icon(UPDATE_ICON_STATE) + +/obj/machinery/processing_node/Destroy() + . = ..() + if(assigned_ai) assigned_ai.program_picker.memory-- assigned_ai = null - to_chat(user, "Turning off") - update_icon(UPDATE_ICON_STATE) + +/obj/machinery/processing_node/on_deconstruction() + . = ..() if(assigned_ai) - // "destroyed" "do" - // assigned_ai.program_picker.memory-- - // assigned_ai = null + assigned_ai.program_picker.memory-- + assigned_ai = null -/obj/machinery/processingnode/update_icon_state() +/obj/machinery/processing_node/update_icon_state() + . = ..() icon_state = "processor-[active ? "on" : "off"]" diff --git a/code/game/machinery/machine_frame.dm b/code/game/machinery/machine_frame.dm index dae9f1e57c1c..00c6243c8cff 100644 --- a/code/game/machinery/machine_frame.dm +++ b/code/game/machinery/machine_frame.dm @@ -1164,10 +1164,10 @@ to destroy them and players will be able to make replacements. /obj/item/stack/cable_coil = 3, /obj/item/stack/sheet/plasteel = 5) -/obj/item/circuitboard/processingnode +/obj/item/circuitboard/processing_node board_name = "Processing Node" icon_state = "science" - build_path = /obj/machinery/processingnode + build_path = /obj/machinery/processing_node board_type = "machine" origin_tech = "programming=4" req_components = list( diff --git a/code/modules/research/designs/machine_designs.dm b/code/modules/research/designs/machine_designs.dm index 6ac302a31ea8..04772062426c 100644 --- a/code/modules/research/designs/machine_designs.dm +++ b/code/modules/research/designs/machine_designs.dm @@ -602,12 +602,12 @@ build_path = /obj/item/circuitboard/merch category = list("Misc. Machinery") -/datum/design/processingnode +/datum/design/processing_node name = "Machine Design (Processing Node)" desc = "The circuit board for a processing node." - id = "processingnode" + id = "processing_node" req_tech = list("programming" = 5) build_type = IMPRINTER materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) - build_path = /obj/machinery/processingnode + build_path = /obj/machinery/processing_node category = list("Misc. Machinery") From ae57da3d1111c67b16784e7ddf5870ec1e786e10 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 18:09:54 -0500 Subject: [PATCH 19/44] Processing nodes power states --- code/game/machinery/ai_resource.dm | 2 ++ 1 file changed, 2 insertions(+) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 450a5f522c5c..dd5a456771ad 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -41,11 +41,13 @@ to_chat(user, "The Processing Node turns off.") else // We have an AI, up its memory assigned_ai.program_picker.memory++ + change_power_mode(ACTIVE_POWER_USE) else // We're shutting down if(assigned_ai) assigned_ai.program_picker.memory-- assigned_ai = null + change_power_mode(IDLE_POWER_USE) update_icon(UPDATE_ICON_STATE) /obj/machinery/processing_node/Destroy() From 61b6db99a4b5bccfaec3aa2886c001b5b649bb70 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 18:12:10 -0500 Subject: [PATCH 20/44] Minor cleanup --- code/game/machinery/ai_resource.dm | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index dd5a456771ad..7e7a9ca2d9bc 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -30,11 +30,10 @@ if(active) // We're booting up // Find the AI with lowest memory for(var/mob/living/silicon/ai/new_ai in GLOB.ai_list) - if(!assigned_ai) //not found - assigned_ai = new_ai //search for new in global ai list + if(!assigned_ai) // Not found + assigned_ai = new_ai // Assign to the first AI in the list to start if(assigned_ai.program_picker.memory > new_ai.program_picker.memory) assigned_ai = new_ai - if(!assigned_ai) // No eligible AI found, abort active = FALSE to_chat(user, "ERROR: No AI detected. Shutting down...") @@ -42,7 +41,6 @@ else // We have an AI, up its memory assigned_ai.program_picker.memory++ change_power_mode(ACTIVE_POWER_USE) - else // We're shutting down if(assigned_ai) assigned_ai.program_picker.memory-- From acdd0ef52694c558cb36edcb1d9b3e080a960142 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 21:35:40 -0500 Subject: [PATCH 21/44] I've got a network node! And it makes heat! --- code/game/machinery/ai_resource.dm | 166 ++++++++++++++---- code/game/machinery/machine_frame.dm | 16 +- .../mob/living/silicon/ai/ai_programs.dm | 6 + .../research/designs/machine_designs.dm | 12 +- icons/obj/machines/ai_machinery.dmi | Bin 5244 -> 5240 bytes 5 files changed, 164 insertions(+), 36 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 7e7a9ca2d9bc..b9edb9265371 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -1,65 +1,163 @@ -/obj/machinery/processing_node - name = "Processing Node" - desc = "Test Description" +/obj/machinery/ai_node + name = "AI Node" + desc = "If you see me, make an issue report!" icon = 'icons/obj/machines/ai_machinery.dmi' - icon_state = "processor-off" + icon_state = "processor" density = TRUE anchored = TRUE max_integrity = 100 idle_power_consumption = 5 - active_power_consumption = 200 + active_power_consumption = 250 /// Is the machine active var/active = FALSE /// What AI is this machine associated with var/mob/living/silicon/ai/assigned_ai = null + /// Identifier for what resource to remove + var/resource_key + /// How much resources does this machine provide + var/resource_amount = 1 + /// How much heat does this put out? + var/heat_amount = 40000 + /// Are we overheating? + var/overheating = FALSE -/obj/machinery/processing_node/Initialize(mapload) +/obj/machinery/ai_node/Initialize(mapload) . = ..() - component_parts = list() - component_parts += new /obj/item/circuitboard/processing_node(null) - component_parts += new /obj/item/stock_parts/capacitor(null, 2) - component_parts += new /obj/item/stack/sheet/mineral/gold(null, 10) - component_parts += new /obj/item/stack/sheet/mineral/silver(null, 10) - component_parts += new /obj/item/stack/sheet/mineral/diamond(null, 1) - component_parts += new /obj/item/stack/cable_coil(null, 5) - RefreshParts() + update_icon(UPDATE_ICON_STATE) + +/obj/machinery/ai_node/process() + ..() + if(active) + var/datum/milla_safe/ai_node_process/milla = new() + milla.invoke_async(src) + +/obj/machinery/ai_node/Destroy() + . = ..() + if(assigned_ai) + assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) + assigned_ai = null -/obj/machinery/processing_node/attack_hand(user as mob) - to_chat(user, "You toggle the Processing Node from [active ? "On" : "Off"] to [active ? "Off" : "On"]") +/obj/machinery/ai_node/on_deconstruction() + . = ..() + if(assigned_ai) + assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) + assigned_ai = null + +/obj/machinery/ai_node/update_icon_state() + . = ..() + if(overheating) + icon_state = "[initial(icon_state)]-hot" + return + icon_state = "[initial(icon_state)]-[active ? "on" : "off"]" + +/obj/machinery/ai_node/attack_ai(mob/user) + return + +/obj/machinery/ai_node/attack_hand(user as mob) + if(overheating) + to_chat(user, "You turn the overheating [src] off.") + overheating = FALSE + update_icon(UPDATE_ICON_STATE) + return active = !active + to_chat(user, "You turn the [src] [active ? "On" : "Off"]") if(active) // We're booting up - // Find the AI with lowest memory - for(var/mob/living/silicon/ai/new_ai in GLOB.ai_list) - if(!assigned_ai) // Not found - assigned_ai = new_ai // Assign to the first AI in the list to start - if(assigned_ai.program_picker.memory > new_ai.program_picker.memory) - assigned_ai = new_ai + find_ai() if(!assigned_ai) // No eligible AI found, abort active = FALSE to_chat(user, "ERROR: No AI detected. Shutting down...") to_chat(user, "The Processing Node turns off.") - else // We have an AI, up its memory - assigned_ai.program_picker.memory++ + else // We have an AI + assigned_ai.program_picker.modify_resource(resource_key, resource_amount) change_power_mode(ACTIVE_POWER_USE) else // We're shutting down if(assigned_ai) - assigned_ai.program_picker.memory-- + assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) assigned_ai = null change_power_mode(IDLE_POWER_USE) update_icon(UPDATE_ICON_STATE) -/obj/machinery/processing_node/Destroy() - . = ..() +/obj/machinery/ai_node/proc/find_ai() + if(!resource_key) + return + for(var/mob/living/silicon/ai/new_ai in GLOB.ai_list) + if(!assigned_ai) // Not found + assigned_ai = new_ai // Assign to the first AI in the list to start + continue + if(resource_key == "memory" && assigned_ai.program_picker.memory > new_ai.program_picker.memory) + assigned_ai = new_ai + continue + if(resource_key == "bandwidth" && assigned_ai.program_picker.bandwidth > new_ai.program_picker.bandwidth) + assigned_ai = new_ai + +/obj/machinery/ai_node/proc/Overheat() + active = FALSE if(assigned_ai) - assigned_ai.program_picker.memory-- + assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) assigned_ai = null + obj_integrity -= 34 // Overheat it three times and it breaks + change_power_mode(IDLE_POWER_USE) + update_icon(UPDATE_ICON_STATE) + +/datum/milla_safe/ai_node_process -/obj/machinery/processing_node/on_deconstruction() +/datum/milla_safe/ai_node_process/on_run(var/obj/machinery/ai_node/node) + var/turf/simulated/L = get_turf(node) + if(!istype(L)) + return + var/datum/gas_mixture/env = get_turf_air(L) + var/transfer_moles = 0.25 * env.total_moles() + var/datum/gas_mixture/removed = env.remove(transfer_moles) + if(!removed) + return + var/heat_capacity = removed.heat_capacity() + if(heat_capacity) + removed.set_temperature(removed.temperature() + node.heat_amount / heat_capacity) + env.merge(removed) + // Heat check + if(env.temperature() > 373 || env.temperature() < 273) // If the temperature is outside 0-100C... + // Turn the node off due to temperature problems + node.Overheat() + +/obj/machinery/ai_node/processing_node + name = "Processing Node" + desc = "Highly advanced machinery with a manual switch. While running, it grants an AI memory." + icon = 'icons/obj/machines/ai_machinery.dmi' + icon_state = "processor" + resource_key = "memory" + +/obj/machinery/ai_node/processing_node/Initialize(mapload) . = ..() - if(assigned_ai) - assigned_ai.program_picker.memory-- - assigned_ai = null + component_parts = list() + component_parts += new /obj/item/circuitboard/processing_node(null) + component_parts += new /obj/item/stock_parts/capacitor(null, 2) + component_parts += new /obj/item/stack/sheet/mineral/gold(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/silver(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/diamond(null, 1) + component_parts += new /obj/item/stack/cable_coil(null, 5) + RefreshParts() + +/obj/machinery/ai_node/network_node + name = "Network Node" + desc = "Highly advanced machinery with an on/off switch. While running, it grants an AI bandwidth." + icon = 'icons/obj/machines/ai_machinery.dmi' + icon_state = "network" + resource_key = "bandwidth" -/obj/machinery/processing_node/update_icon_state() +/obj/machinery/ai_node/network_node/examine_more(mob/user) . = ..() - icon_state = "processor-[active ? "on" : "off"]" + . += "I don't know but I've been told\ + Captain's got a network node!\ + Likes to press the on/off switch!\ + Dig that crazy corporate snitch!" + +/obj/machinery/ai_node/network_node/Initialize(mapload) + . = ..() + component_parts = list() + component_parts += new /obj/item/circuitboard/network_node(null) + component_parts += new /obj/item/stock_parts/capacitor(null, 2) + component_parts += new /obj/item/stack/sheet/mineral/gold(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/silver(null, 10) + component_parts += new /obj/item/stack/sheet/mineral/diamond(null, 1) + component_parts += new /obj/item/stack/cable_coil(null, 5) + RefreshParts() diff --git a/code/game/machinery/machine_frame.dm b/code/game/machinery/machine_frame.dm index 00c6243c8cff..e506f6b3cb6c 100644 --- a/code/game/machinery/machine_frame.dm +++ b/code/game/machinery/machine_frame.dm @@ -1167,7 +1167,7 @@ to destroy them and players will be able to make replacements. /obj/item/circuitboard/processing_node board_name = "Processing Node" icon_state = "science" - build_path = /obj/machinery/processing_node + build_path = /obj/machinery/ai_node/processing_node board_type = "machine" origin_tech = "programming=4" req_components = list( @@ -1177,3 +1177,17 @@ to destroy them and players will be able to make replacements. /obj/item/stack/sheet/mineral/diamond = 1, /obj/item/stack/cable_coil = 5, ) + +/obj/item/circuitboard/network_node + board_name = "Network Node" + icon_state = "science" + build_path = /obj/machinery/ai_node/network_node + board_type = "machine" + origin_tech = "programming=4" + req_components = list( + /obj/item/stock_parts/capacitor = 2, + /obj/item/stack/sheet/mineral/gold = 10, + /obj/item/stack/sheet/mineral/silver = 10, + /obj/item/stack/cable_coil = 5, + ) + diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 1cc5da5ade29..b7af49251d68 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -36,6 +36,12 @@ popup.open() return +/datum/program_picker/proc/modify_resource(var/key, var/amount) + if(key == "memory") + memory += amount + if(key == "bandwidth") + bandwidth += amount + /datum/program_picker/Topic(href, href_list) ..() diff --git a/code/modules/research/designs/machine_designs.dm b/code/modules/research/designs/machine_designs.dm index 04772062426c..1687dd09c02e 100644 --- a/code/modules/research/designs/machine_designs.dm +++ b/code/modules/research/designs/machine_designs.dm @@ -609,5 +609,15 @@ req_tech = list("programming" = 5) build_type = IMPRINTER materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) - build_path = /obj/machinery/processing_node + build_path = /obj/machinery/ai_node/processing_node + category = list("Misc. Machinery") + +/datum/design/network_node + name = "Machine Design (Network Node)" + desc = "The circuit board for a network node." + id = "network_node" + req_tech = list("programming" = 5) + build_type = IMPRINTER + materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) + build_path = /obj/machinery/ai_node/network_node category = list("Misc. Machinery") diff --git a/icons/obj/machines/ai_machinery.dmi b/icons/obj/machines/ai_machinery.dmi index ce28ed9a367654cb9a327ac3929f4ed28121e022..250af9dfd5edb2fcc09b7475cb176279a2cf7ec3 100644 GIT binary patch delta 217 zcmV;~04D$ZDEKIlB!9$uR9JLGWpiV4X>fFDZ*Bkpc$|%r!485j5Jb=IS2S=%qln(T z7>MB@|Iol<8<8b#Bk}L87(rs2kh#omru#BULw3r}dBM_4P9LDO#FiadvffbA%gP8l z>|#m;$g41)K^tzs+MrWdg4U>3*annTQfa&1Qc^2^hr!!36;3q#`S#JDoTuvAbIX+$ zXqJ)Vxt!zn-^M+ef1uuqDlS(_qOBswtVwk|E2A TboeMQRc4*_fFDZ*Bkpc$|%r(F%ev7=^F5rx<#xQD)tB z6H0iI?=bYYjm%%Rq4f4G!%UhW=jQz5a6S&qXXo^iMl1lLh4Bpn1P*U^f+XsJgR#nwPmn$vM ztRqKrIms<7&6wg1m>$(V|pYo?Cb#i2j2L-3UYwq_l#Yb>}yH6`O& X(r0O&44>r%QX!v|!n4QrvGIo!4Wn Date: Thu, 16 Jan 2025 21:50:39 -0500 Subject: [PATCH 22/44] Adds proc to nodes to change the assigned AI --- code/game/machinery/ai_resource.dm | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index b9edb9265371..e1314639c2a0 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -99,6 +99,15 @@ change_power_mode(IDLE_POWER_USE) update_icon(UPDATE_ICON_STATE) +/obj/machinery/ai_node/proc/change_ai(var/mob/living/silicon/ai/new_ai) + if(!new_ai) + return + if(!istype(new_ai)) + return + assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) + assigned_ai = new_attack_chain + assigned_ai.program_picker.modify_resource(resource_key, resource_amount) + /datum/milla_safe/ai_node_process /datum/milla_safe/ai_node_process/on_run(var/obj/machinery/ai_node/node) From c7c53596a1586c678e42970b1df29b7eb2194071 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 21:53:50 -0500 Subject: [PATCH 23/44] Removed extra vars --- code/game/machinery/ai_resource.dm | 4 ++-- code/modules/mob/living/silicon/ai/ai_programs.dm | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index e1314639c2a0..b84fb511b2eb 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -99,7 +99,7 @@ change_power_mode(IDLE_POWER_USE) update_icon(UPDATE_ICON_STATE) -/obj/machinery/ai_node/proc/change_ai(var/mob/living/silicon/ai/new_ai) +/obj/machinery/ai_node/proc/change_ai(mob/living/silicon/ai/new_ai) if(!new_ai) return if(!istype(new_ai)) @@ -110,7 +110,7 @@ /datum/milla_safe/ai_node_process -/datum/milla_safe/ai_node_process/on_run(var/obj/machinery/ai_node/node) +/datum/milla_safe/ai_node_process/on_run(obj/machinery/ai_node/node) var/turf/simulated/L = get_turf(node) if(!istype(L)) return diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index b7af49251d68..63fd627327df 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -36,7 +36,7 @@ popup.open() return -/datum/program_picker/proc/modify_resource(var/key, var/amount) +/datum/program_picker/proc/modify_resource(key, amount) if(key == "memory") memory += amount if(key == "bandwidth") From cbde3565bcb41c0a26d707711072dc0e457b723f Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Thu, 16 Jan 2025 22:16:10 -0500 Subject: [PATCH 24/44] Icon fixes --- code/game/machinery/ai_resource.dm | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index b84fb511b2eb..b6b35528e0a6 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -2,12 +2,13 @@ name = "AI Node" desc = "If you see me, make an issue report!" icon = 'icons/obj/machines/ai_machinery.dmi' - icon_state = "processor" + icon_state = "processor-off" density = TRUE anchored = TRUE max_integrity = 100 idle_power_consumption = 5 active_power_consumption = 250 + var/icon_base /// Is the machine active var/active = FALSE /// What AI is this machine associated with @@ -21,10 +22,6 @@ /// Are we overheating? var/overheating = FALSE -/obj/machinery/ai_node/Initialize(mapload) - . = ..() - update_icon(UPDATE_ICON_STATE) - /obj/machinery/ai_node/process() ..() if(active) @@ -46,9 +43,9 @@ /obj/machinery/ai_node/update_icon_state() . = ..() if(overheating) - icon_state = "[initial(icon_state)]-hot" + icon_state = "[icon_base]-hot" return - icon_state = "[initial(icon_state)]-[active ? "on" : "off"]" + icon_state = "[icon_base]-[active ? "on" : "off"]" /obj/machinery/ai_node/attack_ai(mob/user) return @@ -132,8 +129,9 @@ name = "Processing Node" desc = "Highly advanced machinery with a manual switch. While running, it grants an AI memory." icon = 'icons/obj/machines/ai_machinery.dmi' - icon_state = "processor" + icon_state = "processor-off" resource_key = "memory" + icon_base = "processor" /obj/machinery/ai_node/processing_node/Initialize(mapload) . = ..() @@ -150,8 +148,9 @@ name = "Network Node" desc = "Highly advanced machinery with an on/off switch. While running, it grants an AI bandwidth." icon = 'icons/obj/machines/ai_machinery.dmi' - icon_state = "network" + icon_state = "network-off" resource_key = "bandwidth" + icon_base = "network" /obj/machinery/ai_node/network_node/examine_more(mob/user) . = ..() From baf6bcf86a30b285a6b65a88d4af4f24036afe14 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Fri, 17 Jan 2025 18:37:05 -0500 Subject: [PATCH 25/44] Adds overheat counter to delay overheat to prevent random atmos hotspots from instantly turning it off --- code/game/machinery/ai_resource.dm | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index b6b35528e0a6..c459d99b573b 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -21,6 +21,8 @@ var/heat_amount = 40000 /// Are we overheating? var/overheating = FALSE + /// Used to ensure it takes a few seconds of being hot before overheating + var/overheat_counter = 0 /obj/machinery/ai_node/process() ..() @@ -123,7 +125,12 @@ // Heat check if(env.temperature() > 373 || env.temperature() < 273) // If the temperature is outside 0-100C... // Turn the node off due to temperature problems - node.Overheat() + node.overheat_counter++ + if(node.overheat_counter >= 5) + node.Overheat() + return + node.overheat_counter-- + /obj/machinery/ai_node/processing_node name = "Processing Node" From deb0dfa4dc6809ab9347900948c23afd72825a61 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Fri, 17 Jan 2025 18:52:20 -0500 Subject: [PATCH 26/44] They changed my isAI check. Woe. --- code/modules/mob/living/silicon/ai/ai_programs.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 63fd627327df..854cb3f0f689 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -45,7 +45,7 @@ /datum/program_picker/Topic(href, href_list) ..() - if(!isAI(usr)) + if(!is_ai(usr)) return var/mob/living/silicon/ai/A = usr From 83d734880d95ac70e4a2db7e61f4cc0585ba0ef3 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sat, 18 Jan 2025 16:05:51 -0500 Subject: [PATCH 27/44] Sealant, Holosigns, HONK, bugfixes, and stock part multipliers --- code/game/machinery/ai_resource.dm | 22 ++- .../mob/living/silicon/ai/ai_programs.dm | 141 +++++++++++++++++- 2 files changed, 160 insertions(+), 3 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index c459d99b573b..8e28c571580e 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -18,11 +18,13 @@ /// How much resources does this machine provide var/resource_amount = 1 /// How much heat does this put out? - var/heat_amount = 40000 + var/heat_amount = 25000 /// Are we overheating? var/overheating = FALSE /// Used to ensure it takes a few seconds of being hot before overheating var/overheat_counter = 0 + /// How efficient is this machine? + var/efficiency = 1 /obj/machinery/ai_node/process() ..() @@ -52,6 +54,22 @@ /obj/machinery/ai_node/attack_ai(mob/user) return +/obj/machinery/ai_node/RefreshParts() + . = ..() + var/E + for(var/obj/item/stock_parts/capacitor/M in component_parts) + E += M.rating + efficiency = E / 2 + // Adjust values according to the new stock parts. + heat_amount = initial(heat_amount) * efficiency + update_idle_power_consumption(power_channel, initial(idle_power_consumption) * efficiency) + update_active_power_consumption(power_channel, initial(active_power_consumption) * efficiency) + var/old_resource_amount = resource_amount + resource_amount = round_down(initial(resource_amount) * efficiency) + // Adjust the resources of the connected AI if the machine is on + if(assigned_ai) + assigned_ai.program_picker.modify_resource(resource_key, (resource_amount - old_resource_amount)) + /obj/machinery/ai_node/attack_hand(user as mob) if(overheating) to_chat(user, "You turn the overheating [src] off.") @@ -104,7 +122,7 @@ if(!istype(new_ai)) return assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) - assigned_ai = new_attack_chain + assigned_ai = new_ai assigned_ai.program_picker.modify_resource(resource_key, resource_amount) /datum/milla_safe/ai_node_process diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 854cb3f0f689..c046ee8ce404 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -488,7 +488,7 @@ upgrade_level++ installed = TRUE -// RGB Lighting - Recolors Lights +// Light Synthesizer - Fixes lights /datum/ai_program/light_repair program_name = "Light Synthesizer" program_id = "light_repair" @@ -664,4 +664,143 @@ to_chat(user, "Discovered innovations has led to an increase in the [current] field!") upgraded = TRUE +/datum/spell/ai_spell/research_subsystem/on_purchase_upgrade() + cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - (spell_level * 30)), 600 SECONDS) + +// Emergency Sealant - Patches holes with metal foam +/datum/ai_program/research_semergency_sealantubsystem + program_name = "Emergency Sealant" + program_id = "emergency_sealant" + description = "Deploy an area of metal foam to rapidly repair and seal hull breaches." + cost = 2 + nanite_cost = 50 + power_type = /datum/spell/ai_spell/ranged/emergency_sealant + unlock_text = "Metal foam synthesizer online." + +/datum/spell/ai_spell/ranged/emergency_sealant + name = "Emergency Sealant" + desc = "Deploy an area of metal foam to rapidly repair and seal hull breaches." + action_icon = 'icons/obj/structures.dmi' + action_icon_state = "reinforced" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 180 SECONDS + cooldown_min = 30 SECONDS + level_max = 5 + selection_activated_message = "You fill a canister with metal foam..." + selection_deactivated_message = "You dissolve the unused canister." + +/datum/spell/ai_spell/ranged/emergency_sealant/cast(list/targets, mob/user) + var/target = targets[1] + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 50 + user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) + playsound(target, 'sound/effects/bubbles2.ogg', 50, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + var/obj/effect/particle_effect/foam/metal/F = new /obj/effect/particle_effect/foam/metal(get_turf(target), TRUE) + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 15) + F.spread_amount = 2 + +/datum/spell/ai_spell/ranged/door_override/on_purchase_upgrade() + cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - (spell_level * 30)), 30 SECONDS) + +// Holosign Deployment - Deploys a holosign on the selected turf +/datum/ai_program/holosign_displayer + program_name = "Holosign Displayer" + program_id = "holosign_displayer" + description = "Deploy a holographic sign to alert crewmembers to potential hazards." + cost = 1 + nanite_cost = 10 + power_type = /datum/spell/ai_spell/ranged/holosign_displayer + unlock_text = "Metal foam synthesizer online." + +/datum/spell/ai_spell/ranged/holosign_displayer + name = "Holosign Displayer" + desc = "Deploy a holographic sign to alert crewmembers to potential hazards." + action_icon = 'icons/obj/device.dmi' + action_icon_state = "signmaker" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 30 SECONDS + cooldown_min = 30 SECONDS + level_max = 8 + selection_activated_message = "You spool up your projector..." + selection_deactivated_message = "You stop spooling the projector." + /// Types of holosigns the AI can deploy + var/sign_choices = list( + "Engineering", + "Security", + "Wet Floor" + ) + /// List of currently active signs + var/signs = list() + +/datum/spell/ai_spell/ranged/holosign_displayer/cast(list/targets, mob/user) + var/sign_id = tgui_input_list(usr, "Select an holosgn!", "AI", sign_choices) + if(!sign_id) + return + var/sign_type = null + switch(sign_id) + if("Engineering") + sign_type = /obj/structure/holosign/barrier/engineering + if("Wet Floor") + sign_type = /obj/structure/holosign/wetsign + if("Security") + sign_type = /obj/structure/holosign/barrier + else + return + var/target = targets[1] + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 10 + var/H = new sign_type(get_turf(target), src) + addtimer(CALLBACK(src, PROC_REF(sign_timer_complete), H), (60 + 30 * spell_level) SECONDS, TIMER_UNIQUE) + user.playsound_local(user, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) + playsound(target, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + +/datum/spell/ai_spell/ranged/holosign_displayer/proc/sign_timer_complete(obj/structure/holosign/H) + playsound(H.loc, 'sound/machines/chime.ogg', 20, 1) + qdel(H) + +// HONK Subsystem - HONK +/datum/ai_program/honk_subsystem + program_name = "Honk Subsystem" + program_id = "honk_subsystem" + description = "Download a program from Clowns.NT to be able to play bike horn sounds on demand." + nanite_cost = 5 + power_type = /datum/spell/ai_spell/ranged/honk_subsystem + unlock_text = "Honker.exe installed." + +/datum/spell/ai_spell/ranged/honk_subsystem + name = "Honk Subsystem" + desc = "Download a program from Clowns.NT to be able to play bike horn sounds on demand." + action_icon = 'icons/obj/items.dmi' + action_icon_state = "bike_horn" + ranged_mousepointer = 'icons/mecha/mecha_mouse.dmi' + auto_use_uses = FALSE + base_cooldown = 30 SECONDS + cooldown_min = 5 SECONDS + level_max = 10 + selection_activated_message = "You prepare to honk..." + selection_deactivated_message = "You reduce the amount of humor in your subsystems." + +/datum/spell/ai_spell/ranged/honk_subsystem/cast(list/targets, mob/user) + var/target = targets[1] + if(!target) + return + var/mob/living/silicon/ai/AI = user + AI.program_picker.nanites -= 5 + if(spell_level >= 10) + playsound(target, 'sound/items/airhorn.ogg', 100, 1) + user.playsound_local(user, 'sound/items/airhorn.ogg', 50, FALSE, use_reverb = FALSE) + else + playsound(target, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) + user.playsound_local(user, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) +/datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() + cooldown_handler.recharge_duration = max(base_cooldown - (spell_level * 15) SECONDS, 15 SECONDS) From 3fde6dce0a3263fe7ad5b0dd13a871ff1d24dd88 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sat, 18 Jan 2025 17:41:55 -0500 Subject: [PATCH 28/44] Enhanced Tracking Software --- code/datums/alarm_manager.dm | 3 +- code/game/machinery/ai_resource.dm | 1 - code/modules/mob/living/silicon/ai/ai_life.dm | 10 ++++ code/modules/mob/living/silicon/ai/ai_mob.dm | 10 +++- .../mob/living/silicon/ai/ai_programs.dm | 53 ++++++++++++++++++- .../modules/mob/living/silicon/silicon_mob.dm | 3 ++ 6 files changed, 75 insertions(+), 5 deletions(-) diff --git a/code/datums/alarm_manager.dm b/code/datums/alarm_manager.dm index 8c2dbef02796..e7ba0e282b00 100644 --- a/code/datums/alarm_manager.dm +++ b/code/datums/alarm_manager.dm @@ -6,7 +6,8 @@ GLOBAL_DATUM_INIT(alarm_manager, /datum/alarm_manager, new()) "Fire" = list(), "Atmosphere" = list(), "Power" = list(), - "Burglar" = list() + "Burglar" = list(), + "Tracking" = list() ) /datum/alarm_manager/proc/trigger_alarm(class, area/A, list/O, obj/alarmsource) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 8e28c571580e..32bf15cd888f 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -149,7 +149,6 @@ return node.overheat_counter-- - /obj/machinery/ai_node/processing_node name = "Processing Node" desc = "Highly advanced machinery with a manual switch. While running, it grants an AI memory." diff --git a/code/modules/mob/living/silicon/ai/ai_life.dm b/code/modules/mob/living/silicon/ai/ai_life.dm index 3ba153e83e9c..923b81c6e808 100644 --- a/code/modules/mob/living/silicon/ai/ai_life.dm +++ b/code/modules/mob/living/silicon/ai/ai_life.dm @@ -26,6 +26,16 @@ if(istype(machine, /obj/machinery/hologram)) check_holopad_eye() + // Enhanced Tracking + if(enhanced_tracking) + if(tracked_mob) + if(can_see(tracked_mob)) + var/area/A = get_area(tracked_mob) + if(A) + addtimer(CALLBACK(src, PROC_REF(raise_tracking_alert), A, tracked_mob), enhanced_tracking_delay) + // To prevent spam, immediately unset tracking. + tracked_mob = null + if(malfhack && malfhack.aidisabled) to_chat(src, "ERROR: APC access disabled, hack attempt canceled.") deltimer(malfhacking) diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 598d7937aa97..1478061a8825 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -80,6 +80,12 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( var/bluespace_miner_rate = 100 /// Time until next payout var/next_payout = 10 MINUTES + /// Do we have the enhanced tracker? + var/enhanced_tracking = FALSE + /// Who are we tracking with the enhanced tracker? + var/mob/tracked_mob + /// The current delay on enhanced tracking + var/enhanced_tracking_delay = 10 SECONDS //MALFUNCTION var/datum/module_picker/malf_picker @@ -240,7 +246,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( spawn(5) new /obj/machinery/ai_powersupply(src) - + eyeobj = new /mob/camera/eye/ai(loc, name, src, src) builtInCamera = new /obj/machinery/camera/portable(src) @@ -1493,7 +1499,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( /mob/living/silicon/ai/proc/toggle_fast_holograms() set category = "AI Commands" set name = "Toggle Fast Holograms" - + if(usr.stat == DEAD || !is_ai_eye(eyeobj)) return fast_holograms = !fast_holograms diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index c046ee8ce404..df969d218540 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -81,6 +81,7 @@ return FALSE memory -= program.cost SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) + program.upgrade(A) // Usually does nothing, but is needed for hybrid abilities like the enhanced tracker A.AddSpell(new_spell) to_chat(A, program.unlock_text) A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) @@ -802,5 +803,55 @@ playsound(target, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) user.playsound_local(user, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) -/datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() +/datum/spell/ai_spell/ranged/honk_subsystem/on_purchase_upgrade() cooldown_handler.recharge_duration = max(base_cooldown - (spell_level * 15) SECONDS, 15 SECONDS) + +// Enhanced Tracking System - Select a target. Get alerted after a delay whenever that target enters camera sight +/datum/ai_program/enhanced_tracker + program_name = "Enhanced Tracking Subsystem" + program_id = "enhanced_tracker" + description = "New camera firmware allows automated alerts when an individual of interest enters camera view." + cost = 5 + nanite_cost = 0 + power_type = /datum/spell/ai_spell/enhanced_tracker + unlock_text = "Tag and track software online." + max_level = 8 + +/datum/ai_program/enhanced_tracker/upgrade(mob/user) + var/mob/living/silicon/ai/AI = user + if(!istype(user)) + return + AI.enhanced_tracking = TRUE + AI.alarms_listend_for += "Tracking" + AI.enhanced_tracking_delay = initial(AI.enhanced_tracking_delay) - (upgrade_level * 2 SECONDS) + +/datum/spell/ai_spell/enhanced_tracker + name = "Enhanced Tracking Subsystem" + desc = "Select a target of interest to be alerted to their presence on cameras." + action_icon = 'icons/obj/items.dmi' + action_icon_state = "videocam" + auto_use_uses = FALSE + base_cooldown = 10 SECONDS + cooldown_min = 10 SECONDS + level_max = 0 + +/datum/spell/ai_spell/enhanced_tracker/cast(list/targets, mob/living/silicon/ai/user) + if(!istype(user)) + return + // Pick a mob to track + var/target_name = tgui_input_list(user, "Pick a trackable target...", "AI", user.trackable_mobs()) + user.tracked_mob = (isnull(user.track.humans[target_name]) ? user.track.others[target_name] : user.track.humans[target_name]) + +/mob/living/silicon/ai/proc/raise_tracking_alert(area/A, mob/target) + var/closest_camera = null + for(var/obj/machinery/camera/C in A) + if(closest_camera == null) + closest_camera = C + continue + if(get_dist(closest_camera, target) > get_dist(C, target)) + closest_camera = C + continue + target.visible_message("A purple light flashes on [closest_camera]!") + if(GLOB.alarm_manager.trigger_alarm("Tracking", A, A.cameras, closest_camera)) + // Cancel alert after 1 minute + addtimer(CALLBACK(GLOB.alarm_manager, TYPE_PROC_REF(/datum/alarm_manager, cancel_alarm), "Tracking", A, closest_camera), 1 MINUTES) diff --git a/code/modules/mob/living/silicon/silicon_mob.dm b/code/modules/mob/living/silicon/silicon_mob.dm index d7d060ea7b51..d60ecf8f540e 100644 --- a/code/modules/mob/living/silicon/silicon_mob.dm +++ b/code/modules/mob/living/silicon/silicon_mob.dm @@ -157,6 +157,9 @@ var/list/msg = list("--- ") + if(alarm_types_show["Tracking"]) + msg += "TRACKING: [alarm_types_show["Tracking"]] alarms detected. - " + if(alarm_types_show["Burglar"]) msg += "BURGLAR: [alarm_types_show["Burglar"]] alarms detected. - " From 48de55e1d52e2eac4a8293e6078a47c840e4d7d3 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Mon, 20 Jan 2025 00:58:00 -0500 Subject: [PATCH 29/44] Refunds for active programs --- .../mob/living/silicon/ai/ai_programs.dm | 58 ++++++++++++++++++- 1 file changed, 57 insertions(+), 1 deletion(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index df969d218540..363c9e0f7174 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -39,8 +39,33 @@ /datum/program_picker/proc/modify_resource(key, amount) if(key == "memory") memory += amount + if(memory < 0) + refund_purchases() if(key == "bandwidth") bandwidth += amount + if(bandwidth < 0) + refund_upgrades() + +/datum/program_picker/proc/refund_purchases(mob/user) + var/list/potential_losses = possible_programs + while(memory < 0) + if(!potential_losses) + return + var/datum/ai_program/program = pick_n_take(potential_losses) + if(!program.installed) + continue + program.uninstall(user) + +/datum/program_picker/proc/refund_upgrades(mob/user) + var/list/potential_losses = possible_programs + while(bandwidth < 0) + if(!potential_losses) + return + var/datum/ai_program/program = pick_n_take(potential_losses) + if(!program.upgrade_level) + continue + while(program.upgrade_level > 0 && bandwidth < 0) + program.downgrade(user) /datum/program_picker/Topic(href, href_list) ..() @@ -73,6 +98,7 @@ if(aspell.spell_level >= aspell.level_max) to_chat(A, "This program cannot be upgraded any further.") aspell.on_purchase_upgrade() + program.upgrade(A) bandwidth-- return TRUE // No same program found, install @@ -81,7 +107,7 @@ return FALSE memory -= program.cost SSblackbox.record_feedback("tally", "ai_program_installed", 1, new_spell.name) - program.upgrade(A) // Usually does nothing, but is needed for hybrid abilities like the enhanced tracker + program.upgrade(A) // Usually does nothing for actives, but is needed for hybrid abilities like the enhanced tracker A.AddSpell(new_spell) to_chat(A, program.unlock_text) A.playsound_local(A, program.unlock_sound, 50, FALSE, use_reverb = FALSE) @@ -140,9 +166,39 @@ create_attack_logs = FALSE /datum/ai_program/proc/upgrade(mob/user) + upgrade_level++ + bandwidth_used++ return /datum/ai_program/proc/downgrade(mob/user) + upgrade_level-- + var/mob/living/silicon/ai/A = user + if(!istype(A)) + return + A.program_picker.bandwidth++ + if(!upgrade) // Passives need to be handled in their own procs + var/datum/spell/ai_spell/removed_spell = new power_type + for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + if(removed_spell.type == aspell.type) + aspell.name = initial(aspell.name) + aspell.spell_level-- + aspell.on_purchase_upgrade() // It's a downgrade, but we still need to recalculate values + return + +/datum/ai_program/proc/uninstall(mob/user) + upgrade_level = 0 + installed = FALSE + var/mob/living/silicon/ai/A = user + if(!istype(A)) + return + A.program_picker.bandwidth += bandwidth_used + bandwidth_used = 0 + A.program_picker.memory += cost + if(!upgrade) // Passives need to be handled in their own procs + var/datum/spell/ai_spell/removed_spell = new power_type + for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + if(removed_spell.type == aspell.type) + A.RemoveSpell(aspell) return /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) From 6e2320ab3dbd44ba6be021eb6c9c4ff4bee52638 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 21 Jan 2025 19:29:24 -0500 Subject: [PATCH 30/44] Remaining uninstall functionality --- .../mob/living/silicon/ai/ai_programs.dm | 137 ++++++++++++------ 1 file changed, 95 insertions(+), 42 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 363c9e0f7174..a3dfc114867e 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -1,5 +1,7 @@ // The datum and interface for the AI powers menu /datum/program_picker + /// Associated AI + var/mob/living/silicon/ai/assigned_ai /// List of programs that can be bought var/list/possible_programs /// How much memory is available @@ -10,7 +12,7 @@ var/nanites = 50 /// What is the maximum number of nanites? var/max_nanites = 100 - // Handles extra information displayed + /// Handles extra information displayed var/temp /datum/program_picker/New() @@ -21,6 +23,10 @@ possible_programs += program /datum/program_picker/proc/use(mob/user) + var/mob/living/silicon/ai/A = user + if(!istype(A)) + return + assigned_ai = A var/dat dat += {"Select program to install: (currently [memory] TB of memory and [bandwidth] TBPS of bandwidth left.)

@@ -31,7 +37,7 @@ dat += "
" if(temp) dat += "[temp]" - var/datum/browser/popup = new(user, "modpicker", "AI Program Menu", 400, 500) + var/datum/browser/popup = new(A, "modpicker", "AI Program Menu", 400, 500) popup.set_content(dat) popup.open() return @@ -46,7 +52,7 @@ if(bandwidth < 0) refund_upgrades() -/datum/program_picker/proc/refund_purchases(mob/user) +/datum/program_picker/proc/refund_purchases() var/list/potential_losses = possible_programs while(memory < 0) if(!potential_losses) @@ -54,9 +60,9 @@ var/datum/ai_program/program = pick_n_take(potential_losses) if(!program.installed) continue - program.uninstall(user) + program.uninstall(assigned_ai) -/datum/program_picker/proc/refund_upgrades(mob/user) +/datum/program_picker/proc/refund_upgrades() var/list/potential_losses = possible_programs while(bandwidth < 0) if(!potential_losses) @@ -65,7 +71,7 @@ if(!program.upgrade_level) continue while(program.upgrade_level > 0 && bandwidth < 0) - program.downgrade(user) + program.downgrade(assigned_ai) /datum/program_picker/Topic(href, href_list) ..() @@ -99,7 +105,6 @@ to_chat(A, "This program cannot be upgraded any further.") aspell.on_purchase_upgrade() program.upgrade(A) - bandwidth-- return TRUE // No same program found, install if(program.cost > memory) @@ -165,40 +170,44 @@ auto_use_uses = FALSE // This is an infinite ability. create_attack_logs = FALSE -/datum/ai_program/proc/upgrade(mob/user) +/datum/ai_program/proc/upgrade(mob/living/silicon/ai/user) upgrade_level++ bandwidth_used++ + if(!istype(user)) + return + user.program_picker.bandwidth-- return -/datum/ai_program/proc/downgrade(mob/user) +/datum/ai_program/proc/downgrade(mob/living/silicon/ai/user) + if(!istype(user)) + return upgrade_level-- - var/mob/living/silicon/ai/A = user - if(!istype(A)) + if(!upgrade_level) + uninstall(user) return - A.program_picker.bandwidth++ + user.program_picker.bandwidth++ if(!upgrade) // Passives need to be handled in their own procs var/datum/spell/ai_spell/removed_spell = new power_type - for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + for(var/datum/spell/ai_spell/aspell in user.mob_spell_list) if(removed_spell.type == aspell.type) aspell.name = initial(aspell.name) aspell.spell_level-- aspell.on_purchase_upgrade() // It's a downgrade, but we still need to recalculate values return -/datum/ai_program/proc/uninstall(mob/user) +/datum/ai_program/proc/uninstall(mob/living/silicon/ai/user) upgrade_level = 0 installed = FALSE - var/mob/living/silicon/ai/A = user - if(!istype(A)) + if(!istype(user)) return - A.program_picker.bandwidth += bandwidth_used + user.program_picker.bandwidth += bandwidth_used bandwidth_used = 0 - A.program_picker.memory += cost + user.program_picker.memory += cost if(!upgrade) // Passives need to be handled in their own procs var/datum/spell/ai_spell/removed_spell = new power_type - for(var/datum/spell/ai_spell/aspell in A.mob_spell_list) + for(var/datum/spell/ai_spell/aspell in user.mob_spell_list) if(removed_spell.type == aspell.type) - A.RemoveSpell(aspell) + user.RemoveSpell(aspell) return /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) @@ -392,15 +401,25 @@ unlock_text = "Universal adapter installation complete!" upgrade = TRUE -/datum/ai_program/universal_adapter/upgrade(mob/user) - var/mob/living/silicon/ai/AI = user +/datum/ai_program/universal_adapter/upgrade(mob/living/silicon/ai/user) if(!istype(user)) return - AI.universal_adapter = TRUE - AI.adapter_efficiency = 0.5 + (0.1 * upgrade_level) - upgrade_level++ + user.universal_adapter = TRUE + user.adapter_efficiency = 0.5 + (0.1 * upgrade_level) installed = TRUE +/datum/ai_program/universal_adapter/downgrade(mob/living/silicon/ai/user) + ..() + if(!istype(user)) + return + user.adapter_efficiency = 0.5 + (0.1 * upgrade_level) + +/datum/ai_program/universal_adapter/uninstall(mob/living/silicon/ai/user) + ..() + if(!istype(user)) + return + user.adapter_efficiency = 0.5 + // Door Override - Repairs door wires if the AI wire is not cut /datum/ai_program/door_override program_name = "Door Override" @@ -514,16 +533,26 @@ unlock_text = "Bluespace miner installation complete!" upgrade = TRUE -/datum/ai_program/bluespace_miner/upgrade(mob/user) - var/mob/living/silicon/ai/AI = user +/datum/ai_program/bluespace_miner/upgrade(mob/living/silicon/ai/user) if(!istype(user)) return - AI.bluespace_miner_rate = 100 + (100 * upgrade_level) - AI.next_payout = 10 MINUTES + world.time - AI.bluespace_miner = TRUE - upgrade_level++ + user.bluespace_miner_rate = 100 + (100 * upgrade_level) + user.next_payout = 10 MINUTES + world.time + user.bluespace_miner = TRUE installed = TRUE +/datum/ai_program/bluespace_miner/downgrade(mob/living/silicon/ai/user) + ..() + if(!istype(user)) + return + user.bluespace_miner_rate = 100 + (100 * upgrade_level) + +/datum/ai_program/bluespace_miner/uninstall(mob/living/silicon/ai/user) + ..() + if(!istype(user)) + return + user.bluespace_miner_rate = 100 + // Multimarket Analysis Subsystem: Reduce prices of things at cargo /datum/ai_program/multimarket_analyser program_name = "Multimarket Analysis Subsystem" @@ -537,14 +566,22 @@ var/original_price_mod /datum/ai_program/multimarket_analyser/New() - . = ..() + ..() original_price_mod = SSeconomy.pack_price_modifier -/datum/ai_program/multimarket_analyser/upgrade(mob/user) +/datum/ai_program/multimarket_analyser/upgrade(mob/living/silicon/ai/user) SSeconomy.pack_price_modifier = original_price_mod * (0.95 - (0.05 * upgrade_level)) upgrade_level++ installed = TRUE +/datum/ai_program/multimarket_analyser/downgrade(mob/living/silicon/ai/user) + ..() + SSeconomy.pack_price_modifier = original_price_mod * (0.95 - (0.05 * upgrade_level)) + +/datum/ai_program/multimarket_analyser/uninstall(mob/living/silicon/ai/user) + ..() + SSeconomy.pack_price_modifier = original_price_mod + // Light Synthesizer - Fixes lights /datum/ai_program/light_repair program_name = "Light Synthesizer" @@ -647,14 +684,21 @@ /// Track the original delay var/original_door_delay = 3 SECONDS -/datum/ai_program/enhanced_doors/upgrade(mob/user) - var/mob/living/silicon/ai/AI = user +/datum/ai_program/enhanced_doors/upgrade(mob/living/silicon/ai/user) if(!istype(user)) return - upgrade_level++ - AI.door_bolt_delay = original_door_delay * (1 - (upgrade_level * 0.1)) + user.door_bolt_delay = original_door_delay * (1 - (upgrade_level * 0.1)) installed = TRUE +/datum/ai_program/enhanced_doors/downgrade(mob/living/silicon/ai/user) + ..() + user.door_bolt_delay = original_door_delay * (1 - (upgrade_level * 0.1)) + +/datum/ai_program/enhanced_doors/uninstall(mob/living/silicon/ai/user) + ..() + user.door_bolt_delay = original_door_delay + + // Experimental Research Subsystem - Knowledge is power /datum/ai_program/research_subsystem program_name = "Experimental Research Subsystem" @@ -873,13 +917,22 @@ unlock_text = "Tag and track software online." max_level = 8 -/datum/ai_program/enhanced_tracker/upgrade(mob/user) - var/mob/living/silicon/ai/AI = user +/datum/ai_program/enhanced_tracker/upgrade(mob/living/silicon/ai/user) if(!istype(user)) return - AI.enhanced_tracking = TRUE - AI.alarms_listend_for += "Tracking" - AI.enhanced_tracking_delay = initial(AI.enhanced_tracking_delay) - (upgrade_level * 2 SECONDS) + user.enhanced_tracking = TRUE + user.alarms_listend_for += "Tracking" + user.enhanced_tracking_delay = initial(user.enhanced_tracking_delay) - (upgrade_level * 2 SECONDS) + +/datum/ai_program/enhanced_tracker/downgrade(mob/living/silicon/ai/user) + ..() + user.enhanced_tracking_delay = initial(user.enhanced_tracking_delay) - (upgrade_level * 2 SECONDS) + +/datum/ai_program/enhanced_tracker/uninstall(mob/living/silicon/ai/user) + ..() + user.enhanced_tracking = FALSE + user.alarms_listend_for -= "Tracking" + user.enhanced_tracking_delay = initial(user.enhanced_tracking_delay) /datum/spell/ai_spell/enhanced_tracker name = "Enhanced Tracking Subsystem" From e76b818ef6acf5e932098072a300e91d224dbf41 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 21 Jan 2025 20:01:49 -0500 Subject: [PATCH 31/44] AI RMC --- _maps/map_files/generic/centcomm.dmm | 2 +- _maps/map_files/stations/boxstation.dmm | 49 +++++++----- _maps/map_files/stations/cerestation.dmm | 17 +++-- _maps/map_files/stations/deltastation.dmm | 8 +- _maps/map_files/stations/emeraldstation.dmm | 18 +++-- _maps/map_files/stations/metastation.dmm | 18 +++-- code/game/machinery/ai_resource.dm | 71 +++++++++++++++++- .../mob/living/silicon/ai/ai_programs.dm | 6 ++ icons/obj/computer.dmi | Bin 124953 -> 138407 bytes icons/obj/machines/ai_machinery.dmi | Bin 5240 -> 4476 bytes 10 files changed, 144 insertions(+), 45 deletions(-) diff --git a/_maps/map_files/generic/centcomm.dmm b/_maps/map_files/generic/centcomm.dmm index f0648fbd6ca3..a576c611e907 100644 --- a/_maps/map_files/generic/centcomm.dmm +++ b/_maps/map_files/generic/centcomm.dmm @@ -5180,7 +5180,6 @@ /turf/simulated/floor/transparent/glass, /area/tdome/tdomeobserve) "rt" = ( -/obj/machinery/photocopier, /obj/machinery/door_control/no_emag{ id = "sec"; name = "CentCom Security Shutters"; @@ -5203,6 +5202,7 @@ pixel_y = 30; req_access = list(109) }, +/obj/machinery/computer/ai_resource, /turf/simulated/floor/wood, /area/centcom/control) "ru" = ( diff --git a/_maps/map_files/stations/boxstation.dmm b/_maps/map_files/stations/boxstation.dmm index b029b6f90a04..7f8762402c3a 100644 --- a/_maps/map_files/stations/boxstation.dmm +++ b/_maps/map_files/stations/boxstation.dmm @@ -32411,7 +32411,7 @@ dir = 8 }, /turf/simulated/floor/plasteel{ - dir = 10; + dir = 8; icon_state = "darkpurple" }, /area/station/command/office/rd) @@ -46008,6 +46008,8 @@ /area/station/maintenance/asmaint) "dlD" = ( /obj/effect/decal/cleanable/dirt, +/obj/structure/table/wood, +/obj/machinery/bottler, /turf/simulated/floor/plating, /area/station/maintenance/asmaint2) "dlK" = ( @@ -56997,11 +56999,6 @@ }, /turf/simulated/floor/plasteel, /area/station/maintenance/assembly_line) -"ifT" = ( -/obj/structure/table/wood, -/obj/machinery/bottler, -/turf/simulated/floor/wood, -/area/station/maintenance/asmaint2) "ifY" = ( /obj/machinery/door/airlock/external{ id_tag = "eng_door_ext"; @@ -59905,6 +59902,14 @@ }, /turf/simulated/floor/carpet/grimey, /area/station/security/detective) +"jIA" = ( +/obj/structure/cable{ + icon_state = "4-8" + }, +/turf/simulated/floor/plasteel{ + icon_state = "dark" + }, +/area/station/command/office/rd) "jIX" = ( /obj/effect/decal/cleanable/dirt, /obj/machinery/atmospherics/pipe/manifold/hidden/scrubbers, @@ -74958,6 +74963,17 @@ /obj/effect/spawner/window/reinforced/grilled, /turf/simulated/floor/plating, /area/station/engineering/atmos) +"rpn" = ( +/obj/structure/closet/secure_closet/rd, +/obj/machinery/light_switch{ + pixel_x = -24; + dir = 4 + }, +/turf/simulated/floor/plasteel{ + dir = 10; + icon_state = "darkpurple" + }, +/area/station/command/office/rd) "rqq" = ( /obj/machinery/atmospherics/pipe/simple/hidden/supply{ dir = 5 @@ -78153,8 +78169,7 @@ /area/station/engineering/transmission_laser) "ten" = ( /turf/simulated/floor/plasteel{ - dir = 8; - icon_state = "darkpurplecorners" + icon_state = "dark" }, /area/station/command/office/rd) "ter" = ( @@ -82351,17 +82366,13 @@ /turf/simulated/floor/plasteel, /area/station/hallway/secondary/entry/south) "vwC" = ( -/obj/structure/closet/secure_closet/rd, -/obj/machinery/light_switch{ - dir = 4; - name = "west bump"; - pixel_x = -24 - }, /obj/machinery/keycard_auth{ pixel_y = -26 }, +/obj/machinery/computer/ai_resource{ + dir = 1 + }, /turf/simulated/floor/plasteel{ - dir = 10; icon_state = "darkpurple" }, /area/station/command/office/rd) @@ -133000,7 +133011,7 @@ bYj bYj bYj bYj -ifT +bYj cbd cbd cbd @@ -133256,8 +133267,8 @@ bIa tGg cjN clq -bYj -bYj +mMB +rpn cbd cmV yjv @@ -133513,7 +133524,7 @@ wwZ iDL fPy ten -mMB +jIA vwC cbd vIO diff --git a/_maps/map_files/stations/cerestation.dmm b/_maps/map_files/stations/cerestation.dmm index 4e2c464e12be..b9682eba79ca 100644 --- a/_maps/map_files/stations/cerestation.dmm +++ b/_maps/map_files/stations/cerestation.dmm @@ -31920,16 +31920,13 @@ }, /area/station/service/theatre) "faF" = ( -/obj/structure/rack, -/obj/item/aicard, -/obj/item/circuitboard/aicore{ - pixel_x = -2; - pixel_y = 4 - }, /obj/effect/turf_decal/stripes/line{ dir = 8 }, /obj/machinery/alarm/directional/south, +/obj/machinery/computer/ai_resource{ + dir = 1 + }, /turf/simulated/floor/plasteel/white, /area/station/command/office/rd) "faM" = ( @@ -80536,6 +80533,12 @@ pixel_x = 28; name = "custom placement" }, +/obj/structure/rack, +/obj/item/circuitboard/aicore{ + pixel_x = -2; + pixel_y = 4 + }, +/obj/item/aicard, /turf/simulated/floor/plasteel/white, /area/station/command/office/rd) "rEx" = ( @@ -96483,7 +96486,6 @@ }, /area/station/science/toxins/mixing) "vwB" = ( -/obj/structure/rack, /obj/item/paicard{ pixel_x = 4 }, @@ -96491,6 +96493,7 @@ pixel_x = -3 }, /obj/machinery/firealarm/directional/south, +/obj/structure/rack, /turf/simulated/floor/plasteel/white, /area/station/command/office/rd) "vxm" = ( diff --git a/_maps/map_files/stations/deltastation.dmm b/_maps/map_files/stations/deltastation.dmm index 8ba30d96109a..cec07877679f 100644 --- a/_maps/map_files/stations/deltastation.dmm +++ b/_maps/map_files/stations/deltastation.dmm @@ -49451,11 +49451,11 @@ /turf/simulated/floor/plasteel/white, /area/station/maintenance/port2) "doJ" = ( -/obj/structure/table/reinforced, -/obj/item/clipboard, -/obj/item/toy/figure/crew/rd, /obj/machinery/requests_console/directional/west, /obj/effect/turf_decal/delivery/hollow, +/obj/machinery/computer/ai_resource{ + dir = 4 + }, /turf/simulated/floor/plasteel{ dir = 8; icon_state = "whitepurplecorner" @@ -51430,6 +51430,8 @@ dir = 8 }, /obj/effect/turf_decal/delivery/hollow, +/obj/item/toy/figure/crew/rd, +/obj/item/clipboard, /turf/simulated/floor/plasteel{ dir = 4; icon_state = "whitepurplecorner" diff --git a/_maps/map_files/stations/emeraldstation.dmm b/_maps/map_files/stations/emeraldstation.dmm index a696e6911a66..aec95c77ab32 100644 --- a/_maps/map_files/stations/emeraldstation.dmm +++ b/_maps/map_files/stations/emeraldstation.dmm @@ -13443,14 +13443,10 @@ }, /area/station/maintenance/apmaint) "cHe" = ( -/obj/structure/table/glass, -/obj/item/paper_bin/nanotrasen, -/obj/item/pen/rd, -/obj/item/stamp/rd{ - pixel_x = 5; - pixel_y = -2 - }, /obj/machinery/newscaster/directional/south, +/obj/machinery/computer/ai_resource{ + dir = 1 + }, /turf/simulated/floor/plasteel{ dir = 6; icon_state = "darkpurple" @@ -111441,7 +111437,6 @@ /turf/simulated/floor/plasteel, /area/station/hallway/primary/central/sw) "waz" = ( -/obj/structure/rack, /obj/item/aicard, /obj/item/paicard{ pixel_x = 4 @@ -111451,6 +111446,7 @@ pixel_y = 4 }, /obj/machinery/requests_console/directional/south, +/obj/structure/rack, /turf/simulated/floor/plasteel{ dir = 10; icon_state = "darkpurple" @@ -121706,6 +121702,12 @@ pixel_x = 4 }, /obj/item/paper/monitorkey, +/obj/item/stamp/rd{ + pixel_x = 5; + pixel_y = -2 + }, +/obj/item/pen/rd, +/obj/item/paper_bin/nanotrasen, /turf/simulated/floor/plasteel{ dir = 4; icon_state = "darkpurple" diff --git a/_maps/map_files/stations/metastation.dmm b/_maps/map_files/stations/metastation.dmm index 8a791462bad9..5ba6d87f6563 100644 --- a/_maps/map_files/stations/metastation.dmm +++ b/_maps/map_files/stations/metastation.dmm @@ -34655,14 +34655,13 @@ }, /area/station/service/chapel) "cGF" = ( -/obj/structure/table, -/obj/item/aicard, -/obj/item/paicard, -/obj/item/circuitboard/aicore, /obj/machinery/keycard_auth{ pixel_x = -5; pixel_y = 26 }, +/obj/machinery/computer/ai_resource{ + dir = 4 + }, /turf/simulated/floor/plasteel{ dir = 1; icon_state = "whitepurple" @@ -61388,6 +61387,15 @@ icon_state = "dark" }, /area/station/engineering/atmos) +"mEA" = ( +/obj/structure/table, +/obj/item/circuitboard/aicore, +/obj/item/paicard, +/obj/item/aicard, +/turf/simulated/floor/plasteel{ + icon_state = "darkgreycheck" + }, +/area/station/command/office/rd) "mEW" = ( /obj/structure/disposalpipe/segment, /obj/machinery/atmospherics/pipe/simple/hidden/scrubbers, @@ -120291,7 +120299,7 @@ cte dcX cte cmB -cNk +mEA nFh aZr nlS diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 32bf15cd888f..f5e16661224e 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -150,7 +150,7 @@ node.overheat_counter-- /obj/machinery/ai_node/processing_node - name = "Processing Node" + name = "processing node" desc = "Highly advanced machinery with a manual switch. While running, it grants an AI memory." icon = 'icons/obj/machines/ai_machinery.dmi' icon_state = "processor-off" @@ -169,7 +169,7 @@ RefreshParts() /obj/machinery/ai_node/network_node - name = "Network Node" + name = "network node" desc = "Highly advanced machinery with an on/off switch. While running, it grants an AI bandwidth." icon = 'icons/obj/machines/ai_machinery.dmi' icon_state = "network-off" @@ -193,3 +193,70 @@ component_parts += new /obj/item/stack/sheet/mineral/diamond(null, 1) component_parts += new /obj/item/stack/cable_coil(null, 5) RefreshParts() + +/obj/machinery/computer/ai_resource + name = "AI resource control console" + desc = "Used to reassign memory and bandwidth between multiple AI units." + icon = 'icons/obj/computer.dmi' + icon_keyboard = "tech_key" + icon_screen = "ai_resource" + req_access = list(ACCESS_RD) + circuit = /obj/item/circuitboard/ai_resource_console + light_color = LIGHT_COLOR_PURPLE + +/obj/machinery/computer/ai_resource/attack_ai(mob/user as mob) // Bad AI, no access to stealing resources + return + +/obj/machinery/computer/ai_resource/attack_hand(mob/user as mob) + if(..()) + return + if(stat & (NOPOWER|BROKEN)) + return + ui_interact(user) + +/obj/machinery/computer/ai_resource/proc/is_authenticated(mob/user) + if(!istype(user)) + return FALSE + if(user.can_admin_interact()) + return TRUE + if(allowed(user)) + return TRUE + return FALSE + +/obj/machinery/computer/ai_resource/ui_state(mob/user) + return GLOB.default_state + +/obj/machinery/computer/ai_resource/ui_interact(mob/user, datum/tgui/ui = null) + ui = SStgui.try_update_ui(user, src, ui) + if(!ui) + ui = new(user, src, "RoboticsControlConsole", name) + ui.open() + +/obj/machinery/computer/ai_resource/ui_data(mob/user) + var/list/data = list() + data["auth"] = is_authenticated(user) + data["ais"] = list() + for(var/mob/living/silicon/ai/A in GLOB.ai_list) + if(!console_shows(A)) + continue + var/list/ai_data = list( + name = A.name, + uid = A.UID(), + memory = A.program_picker.memory, + memory_max = A.program_picker.total_memory, + bandwidth = A.program_picker.bandwidth, + bandwidth_max = A.program_picker.total_bandwidth + ) + data["ais"] += list(ai_data) + return data + +/obj/machinery/computer/ai_resource/ui_act(action, params) + if(..()) + return + . = FALSE + if(!is_authenticated(usr)) + to_chat(usr, "Access denied.") + return + if(SSticker.current_state == GAME_STATE_FINISHED) + to_chat(usr, "Access denied, AIs are no longer your station's property.") + return diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index a3dfc114867e..2e38e6fe00ae 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -6,8 +6,12 @@ var/list/possible_programs /// How much memory is available var/memory = 1 + /// How much total memory does the system have? + var/total_memory = 1 /// How much bandwidth is available var/bandwidth = 1 + /// How much total bandwidth does the system have? + var/total_bandwidth = 1 /// How many nanites are available? var/nanites = 50 /// What is the maximum number of nanites? @@ -45,10 +49,12 @@ /datum/program_picker/proc/modify_resource(key, amount) if(key == "memory") memory += amount + total_memory += amount if(memory < 0) refund_purchases() if(key == "bandwidth") bandwidth += amount + total_bandwidth += amount if(bandwidth < 0) refund_upgrades() diff --git a/icons/obj/computer.dmi b/icons/obj/computer.dmi index a9095781e6538afb70fd082a27a2b7b83de738e3..40822d164daba54d43ff1a90bccd2064431b917d 100644 GIT binary patch literal 138407 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

^qdO#9AKWr0lgY5W`2$xdUBo3fKeoLb_-0 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%0A?XaaT?iT>_>BF% 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 literal 5240 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 From d330c6a5adbe6e0e8c97b1b4b118495b2eb25a95 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 21 Jan 2025 20:10:09 -0500 Subject: [PATCH 32/44] Forgot a circuitboard --- code/game/machinery/ai_resource.dm | 4 +--- code/game/machinery/computer/buildandrepair.dm | 6 ++++++ code/game/machinery/machine_frame.dm | 1 - code/modules/research/designs/machine_designs.dm | 14 ++++++++++++-- 4 files changed, 19 insertions(+), 6 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index f5e16661224e..4316c47e917d 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -194,7 +194,7 @@ component_parts += new /obj/item/stack/cable_coil(null, 5) RefreshParts() -/obj/machinery/computer/ai_resource +/obj/machinery/computer/ai_resource_console name = "AI resource control console" desc = "Used to reassign memory and bandwidth between multiple AI units." icon = 'icons/obj/computer.dmi' @@ -237,8 +237,6 @@ data["auth"] = is_authenticated(user) data["ais"] = list() for(var/mob/living/silicon/ai/A in GLOB.ai_list) - if(!console_shows(A)) - continue var/list/ai_data = list( name = A.name, uid = A.UID(), diff --git a/code/game/machinery/computer/buildandrepair.dm b/code/game/machinery/computer/buildandrepair.dm index 5e762f6246f3..d220243e3b28 100644 --- a/code/game/machinery/computer/buildandrepair.dm +++ b/code/game/machinery/computer/buildandrepair.dm @@ -402,6 +402,12 @@ build_path = /obj/machinery/computer/mech_bay_power_console origin_tech = "programming=3;powerstorage=3" +/obj/item/circuitboard/ai_resource_console + board_name = "AI Resource Management Console" + icon_state = "science" + build_path = /obj/machinery/computer/ai_resource_console + origin_tech = "programming=4" + /obj/item/circuitboard/ordercomp board_name = "Supply Ordering Console" icon_state = "supply" diff --git a/code/game/machinery/machine_frame.dm b/code/game/machinery/machine_frame.dm index e506f6b3cb6c..1a4c73483346 100644 --- a/code/game/machinery/machine_frame.dm +++ b/code/game/machinery/machine_frame.dm @@ -1190,4 +1190,3 @@ to destroy them and players will be able to make replacements. /obj/item/stack/sheet/mineral/silver = 10, /obj/item/stack/cable_coil = 5, ) - diff --git a/code/modules/research/designs/machine_designs.dm b/code/modules/research/designs/machine_designs.dm index 1687dd09c02e..68e68c7e6825 100644 --- a/code/modules/research/designs/machine_designs.dm +++ b/code/modules/research/designs/machine_designs.dm @@ -609,7 +609,7 @@ req_tech = list("programming" = 5) build_type = IMPRINTER materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) - build_path = /obj/machinery/ai_node/processing_node + build_path = /obj/item/circuitboard/processing_node category = list("Misc. Machinery") /datum/design/network_node @@ -619,5 +619,15 @@ req_tech = list("programming" = 5) build_type = IMPRINTER materials = list(MAT_GLASS = 1000, MAT_GOLD = 250) - build_path = /obj/machinery/ai_node/network_node + build_path = /obj/item/circuitboard/network_node + category = list("Misc. Machinery") + +/datum/design/ai_resource_console + name = "Computer Design (AI Resource Console)" + desc = "The circuit board for an AI Resource Console." + id = "ai_resource_console" + req_tech = list("programming" = 5) + build_type = IMPRINTER + materials = list(MAT_GLASS = 1000) + build_path = /obj/item/circuitboard/ai_resource_console category = list("Misc. Machinery") From 9e2aa5b6f9ff6afad61759705807fa0b54ededde Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Tue, 21 Jan 2025 20:25:24 -0500 Subject: [PATCH 33/44] Fixes a small path issue --- code/game/machinery/ai_resource.dm | 4 ++-- code/game/machinery/computer/buildandrepair.dm | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 4316c47e917d..dd0c16996aa8 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -194,11 +194,11 @@ component_parts += new /obj/item/stack/cable_coil(null, 5) RefreshParts() -/obj/machinery/computer/ai_resource_console +/obj/machinery/computer/ai_resource name = "AI resource control console" desc = "Used to reassign memory and bandwidth between multiple AI units." icon = 'icons/obj/computer.dmi' - icon_keyboard = "tech_key" + icon_keyboard = "rd_key" icon_screen = "ai_resource" req_access = list(ACCESS_RD) circuit = /obj/item/circuitboard/ai_resource_console diff --git a/code/game/machinery/computer/buildandrepair.dm b/code/game/machinery/computer/buildandrepair.dm index d220243e3b28..c0614dc52ea4 100644 --- a/code/game/machinery/computer/buildandrepair.dm +++ b/code/game/machinery/computer/buildandrepair.dm @@ -405,7 +405,7 @@ /obj/item/circuitboard/ai_resource_console board_name = "AI Resource Management Console" icon_state = "science" - build_path = /obj/machinery/computer/ai_resource_console + build_path = /obj/machinery/computer/ai_resource origin_tech = "programming=4" /obj/item/circuitboard/ordercomp From f1505cb1a15e8c844e588b9e0f0e010da5beaa4a Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 22 Jan 2025 00:29:19 -0500 Subject: [PATCH 34/44] Global nodes list + node data for AI RMC TGUI --- code/game/machinery/ai_resource.dm | 35 +++++++++++++++++++++++------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index dd0c16996aa8..e2ce1225ea6d 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -1,3 +1,6 @@ +/// Stores a list of all AI resource nodes +GLOBAL_LIST_EMPTY(ai_nodes) + /obj/machinery/ai_node name = "AI Node" desc = "If you see me, make an issue report!" @@ -26,6 +29,10 @@ /// How efficient is this machine? var/efficiency = 1 +/obj/machinery/ai_node/Initialize(mapload) + ..() + GLOB.ai_nodes += src + /obj/machinery/ai_node/process() ..() if(active) @@ -37,12 +44,14 @@ if(assigned_ai) assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) assigned_ai = null + GLOB.ai_nodes -= src /obj/machinery/ai_node/on_deconstruction() . = ..() if(assigned_ai) assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) assigned_ai = null + GLOB.ai_nodes -= src /obj/machinery/ai_node/update_icon_state() . = ..() @@ -235,17 +244,27 @@ /obj/machinery/computer/ai_resource/ui_data(mob/user) var/list/data = list() data["auth"] = is_authenticated(user) - data["ais"] = list() + data["ai_list"] = list() + data["nodes_list"] = list() for(var/mob/living/silicon/ai/A in GLOB.ai_list) var/list/ai_data = list( - name = A.name, - uid = A.UID(), - memory = A.program_picker.memory, - memory_max = A.program_picker.total_memory, - bandwidth = A.program_picker.bandwidth, - bandwidth_max = A.program_picker.total_bandwidth + "name" = A.name, + "uid" = A.UID(), + "memory" = A.program_picker.memory, + "memory_max" = A.program_picker.total_memory, + "bandwidth" = A.program_picker.bandwidth, + "bandwidth_max" = A.program_picker.total_bandwidth + ) + data["ai_list"] += list(ai_data) + for(var/obj/machinery/ai_node/node in GLOB.ai_nodes) + var/list/node_data = list( + "name" = node.name, + "uid" = node.UID(), + "resource" = node.resource_key, + "amount" = node.resource_amount, + "assigned_ai" = node.assigned_ai ) - data["ais"] += list(ai_data) + data["nodes_list"] += list(node_data) return data /obj/machinery/computer/ai_resource/ui_act(action, params) From 529b05f83ebf9294198f0e98c952c9820ac96a59 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Sun, 26 Jan 2025 13:37:15 -0500 Subject: [PATCH 35/44] TGUI Foundations --- code/game/machinery/ai_resource.dm | 2 +- .../mob/living/silicon/ai/ai_programs.dm | 30 +++++++++++++++++-- .../tgui/interfaces/AIProgramPicker.js | 15 ++++++++++ .../interfaces/AIResourceManagementConsole.js | 15 ++++++++++ 4 files changed, 59 insertions(+), 3 deletions(-) create mode 100644 tgui/packages/tgui/interfaces/AIProgramPicker.js create mode 100644 tgui/packages/tgui/interfaces/AIResourceManagementConsole.js diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index e2ce1225ea6d..f4ef11bad83d 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -238,7 +238,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) /obj/machinery/computer/ai_resource/ui_interact(mob/user, datum/tgui/ui = null) ui = SStgui.try_update_ui(user, src, ui) if(!ui) - ui = new(user, src, "RoboticsControlConsole", name) + ui = new(user, src, "AIResourceManagementConsole", name) ui.open() /obj/machinery/computer/ai_resource/ui_data(mob/user) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 2e38e6fe00ae..36416c358a31 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -79,7 +79,7 @@ while(program.upgrade_level > 0 && bandwidth < 0) program.downgrade(assigned_ai) -/datum/program_picker/Topic(href, href_list) +/datum/program_picker/Topic(href, href_list) // All the program purchasing logic is here. Need to translate to TGUI. ..() if(!is_ai(usr)) @@ -139,6 +139,31 @@ temp = program.description use(usr) +/datum/program_picker/ui_state(mob/user) + return GLOB.default_state + +/datum/program_picker/ui_interact(mob/user, datum/tgui/ui = null) + ui = SStgui.try_update_ui(user, src, ui) + if(!ui) + ui = new(user, src, "AIProgramPicker", "Program Picker") + ui.open() + +/datum/program_picker/ui_data(mob/user) + var/list/data = list() + data["program_list"] = list() + for(var/datum/ai_program/program in possible_programs) + var/list/program_data = list( + "name" = program.program_name, + "UID" = program.UID(), + "description" = program.description, + "memory_cost" = program.cost, + "installed" = program.installed, + "upgrade_level" = program.upgrade_level, + "is_passive" = program.upgrade + ) + data["program_list"] += list(program_data) + return data + // The base program type, which holds info about each ability. /datum/ai_program var/program_name @@ -218,7 +243,8 @@ /datum/spell/ai_spell/choose_program/cast(list/targets, mob/living/silicon/ai/user) . = ..() - user.program_picker.use(user) + user.program_picker.use(user) // WebUI call. Replace with TGUI call below. + user.program_picker.ui_interact(user) // RGB Lighting - Recolors Lights /datum/ai_program/rgb_lighting diff --git a/tgui/packages/tgui/interfaces/AIProgramPicker.js b/tgui/packages/tgui/interfaces/AIProgramPicker.js new file mode 100644 index 000000000000..1cfcead85fc0 --- /dev/null +++ b/tgui/packages/tgui/interfaces/AIProgramPicker.js @@ -0,0 +1,15 @@ +import { useBackend, useSharedState } from '../backend'; +import { Box, Button, LabeledList, NoticeBox, Section, Tabs } from '../components'; +import { Window } from '../layouts'; + +export const AIProgramPicker = (props, context) => { + const { act, data } = useBackend(context); + const { program_list } = data; + return ( + + + + + + ); +}; diff --git a/tgui/packages/tgui/interfaces/AIResourceManagementConsole.js b/tgui/packages/tgui/interfaces/AIResourceManagementConsole.js new file mode 100644 index 000000000000..31109ef1b92b --- /dev/null +++ b/tgui/packages/tgui/interfaces/AIResourceManagementConsole.js @@ -0,0 +1,15 @@ +import { useBackend, useSharedState } from '../backend'; +import { Box, Button, LabeledList, NoticeBox, Section, Tabs } from '../components'; +import { Window } from '../layouts'; + +export const AIResourceManagementConsole = (props, context) => { + const { act, data } = useBackend(context); + const { auth, ai_list, nodes_list } = data; + return ( + + + + + + ); +}; From 6722c57be0aaebff1514910fcbef8c19920835ee Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 18:51:59 -0500 Subject: [PATCH 36/44] Better check Co-authored-by: Luc <89928798+lewcc@users.noreply.github.com> Signed-off-by: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> --- code/game/gamemodes/malfunction/Malf_Modules.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm index 12f272ee6a25..3cf24fa988a7 100644 --- a/code/game/gamemodes/malfunction/Malf_Modules.dm +++ b/code/game/gamemodes/malfunction/Malf_Modules.dm @@ -34,7 +34,7 @@ /datum/spell/ai_spell/proc/find_nearest_camera(atom/target) var/area/A = get_area(target) - if(A == null) + if(!istype(A)) return var/closest_camera = null for(var/obj/machinery/camera/C in A) From fa05ffdb59f96ca0ad57ce4f3e80466df3b13919 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 18:52:20 -0500 Subject: [PATCH 37/44] Better null check Co-authored-by: Luc <89928798+lewcc@users.noreply.github.com> Signed-off-by: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> --- code/game/gamemodes/malfunction/Malf_Modules.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm index 3cf24fa988a7..3bbdb68e162e 100644 --- a/code/game/gamemodes/malfunction/Malf_Modules.dm +++ b/code/game/gamemodes/malfunction/Malf_Modules.dm @@ -38,7 +38,7 @@ return var/closest_camera = null for(var/obj/machinery/camera/C in A) - if(closest_camera == null) + if(isnull(closest_camera)) closest_camera = C continue if(get_dist(closest_camera, target) > get_dist(C, target)) From 7f1d5e1052e1eb9cfd1312b58f4cc61a51ca5792 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 18:52:38 -0500 Subject: [PATCH 38/44] Spacing Co-authored-by: Luc <89928798+lewcc@users.noreply.github.com> Signed-off-by: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> --- code/game/machinery/ai_resource.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index f4ef11bad83d..c71e949e7c04 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -81,7 +81,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) /obj/machinery/ai_node/attack_hand(user as mob) if(overheating) - to_chat(user, "You turn the overheating [src] off.") + to_chat(user, "You turn the overheating [src] off.") overheating = FALSE update_icon(UPDATE_ICON_STATE) return From 9a9ebe98ceb6b5c19e47b5a279775ba40c71a1c9 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 18:52:58 -0500 Subject: [PATCH 39/44] Better chat notification Co-authored-by: Luc <89928798+lewcc@users.noreply.github.com> Signed-off-by: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> --- code/game/machinery/ai_resource.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index c71e949e7c04..0e4c90dd5797 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -86,7 +86,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) update_icon(UPDATE_ICON_STATE) return active = !active - to_chat(user, "You turn the [src] [active ? "On" : "Off"]") + to_chat(user, "You turn [src] [active ? "on" : "off"].") if(active) // We're booting up find_ai() if(!assigned_ai) // No eligible AI found, abort From 2e420d8329477bea7eeff9abce3ef66a0541b5db Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 19:13:54 -0500 Subject: [PATCH 40/44] A shitload of fixes --- code/game/machinery/ai_resource.dm | 23 +++++++-------- code/modules/mob/living/silicon/ai/ai_life.dm | 15 +++++----- code/modules/mob/living/silicon/ai/ai_mob.dm | 13 +++++---- .../mob/living/silicon/ai/ai_programs.dm | 28 +++++++++---------- .../mob/living/silicon/robot/robot_mob.dm | 6 ++-- .../modules/mob/living/silicon/silicon_mob.dm | 2 +- 6 files changed, 44 insertions(+), 43 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index 0e4c90dd5797..a14ece7ee6c6 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -28,6 +28,8 @@ GLOBAL_LIST_EMPTY(ai_nodes) var/overheat_counter = 0 /// How efficient is this machine? var/efficiency = 1 + /// Milla controller + var/datum/milla_safe/ai_node_process/milla = new() /obj/machinery/ai_node/Initialize(mapload) ..() @@ -36,7 +38,6 @@ GLOBAL_LIST_EMPTY(ai_nodes) /obj/machinery/ai_node/process() ..() if(active) - var/datum/milla_safe/ai_node_process/milla = new() milla.invoke_async(src) /obj/machinery/ai_node/Destroy() @@ -106,7 +107,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) /obj/machinery/ai_node/proc/find_ai() if(!resource_key) return - for(var/mob/living/silicon/ai/new_ai in GLOB.ai_list) + for(var/mob/living/silicon/ai/new_ai as anything in GLOB.ai_list) if(!assigned_ai) // Not found assigned_ai = new_ai // Assign to the first AI in the list to start continue @@ -116,12 +117,12 @@ GLOBAL_LIST_EMPTY(ai_nodes) if(resource_key == "bandwidth" && assigned_ai.program_picker.bandwidth > new_ai.program_picker.bandwidth) assigned_ai = new_ai -/obj/machinery/ai_node/proc/Overheat() +/obj/machinery/ai_node/proc/overheat() active = FALSE if(assigned_ai) assigned_ai.program_picker.modify_resource(resource_key, -resource_amount) assigned_ai = null - obj_integrity -= 34 // Overheat it three times and it breaks + obj_integrity -= (max_integrity / 3) // Overheat it three times and it breaks change_power_mode(IDLE_POWER_USE) update_icon(UPDATE_ICON_STATE) @@ -154,7 +155,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) // Turn the node off due to temperature problems node.overheat_counter++ if(node.overheat_counter >= 5) - node.Overheat() + node.overheat() return node.overheat_counter-- @@ -187,9 +188,9 @@ GLOBAL_LIST_EMPTY(ai_nodes) /obj/machinery/ai_node/network_node/examine_more(mob/user) . = ..() - . += "I don't know but I've been told\ - Captain's got a network node!\ - Likes to press the on/off switch!\ + . += "I don't know but I've been told \ + Captain's got a network node! \ + Likes to press the on/off switch! \ Dig that crazy corporate snitch!" /obj/machinery/ai_node/network_node/Initialize(mapload) @@ -213,10 +214,10 @@ GLOBAL_LIST_EMPTY(ai_nodes) circuit = /obj/item/circuitboard/ai_resource_console light_color = LIGHT_COLOR_PURPLE -/obj/machinery/computer/ai_resource/attack_ai(mob/user as mob) // Bad AI, no access to stealing resources +/obj/machinery/computer/ai_resource/attack_ai(mob/user) // Bad AI, no access to stealing resources return -/obj/machinery/computer/ai_resource/attack_hand(mob/user as mob) +/obj/machinery/computer/ai_resource/attack_hand(mob/user) if(..()) return if(stat & (NOPOWER|BROKEN)) @@ -256,7 +257,7 @@ GLOBAL_LIST_EMPTY(ai_nodes) "bandwidth_max" = A.program_picker.total_bandwidth ) data["ai_list"] += list(ai_data) - for(var/obj/machinery/ai_node/node in GLOB.ai_nodes) + for(var/obj/machinery/ai_node/node as anything in GLOB.ai_nodes) var/list/node_data = list( "name" = node.name, "uid" = node.UID(), diff --git a/code/modules/mob/living/silicon/ai/ai_life.dm b/code/modules/mob/living/silicon/ai/ai_life.dm index 923b81c6e808..758e1034097f 100644 --- a/code/modules/mob/living/silicon/ai/ai_life.dm +++ b/code/modules/mob/living/silicon/ai/ai_life.dm @@ -27,14 +27,13 @@ check_holopad_eye() // Enhanced Tracking - if(enhanced_tracking) - if(tracked_mob) - if(can_see(tracked_mob)) - var/area/A = get_area(tracked_mob) - if(A) - addtimer(CALLBACK(src, PROC_REF(raise_tracking_alert), A, tracked_mob), enhanced_tracking_delay) - // To prevent spam, immediately unset tracking. - tracked_mob = null + if(enhanced_tracking && tracked_mob) + if(can_see(tracked_mob)) + var/area/A = get_area(tracked_mob) + if(A) + addtimer(CALLBACK(src, PROC_REF(raise_tracking_alert), A, tracked_mob), enhanced_tracking_delay) + // To prevent spam, immediately unset tracking. + tracked_mob = null if(malfhack && malfhack.aidisabled) to_chat(src, "ERROR: APC access disabled, hack attempt canceled.") diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index 1478061a8825..f15972dfe5af 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -56,7 +56,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( var/list/connected_robots = list() var/aiRestorePowerRoutine = 0 //var/list/laws = list() - alarms_listend_for = list("Motion", "Fire", "Atmosphere", "Power", "Burglar") + alarms_listened_for = list("Motion", "Fire", "Atmosphere", "Power", "Burglar") var/viewalerts = FALSE var/icon/holo_icon //Default is assigned when AI is created. var/obj/mecha/controlled_mech //For controlled_mech a mech, to determine whether to relaymove or use the AI eye. @@ -320,7 +320,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( dat += "Close

" var/list/list/temp_alarm_list = GLOB.alarm_manager.alarms.Copy() for(var/cat in temp_alarm_list) - if(!(cat in alarms_listend_for)) + if(!(cat in alarms_listened_for)) continue dat += "[cat]
\n" var/list/list/L = temp_alarm_list[cat].Copy() @@ -397,6 +397,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( power_state = ACTIVE_POWER_USE var/mob/living/silicon/ai/powered_ai = null invisibility = 100 + /// Power draw for the bluespace miner module var/bluespace_miner_power = 0 /obj/machinery/ai_powersupply/New(mob/living/silicon/ai/ai=null) @@ -415,7 +416,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( qdel(src) return // Regenerate nanites for abilities only when powered. - powered_ai.program_picker.nanites = min(100, powered_ai.program_picker.nanites + (1 + 0.5*powered_ai.program_picker.bandwidth)) + powered_ai.program_picker.nanites = min(100, powered_ai.program_picker.nanites + (1 + 0.5 * powered_ai.program_picker.bandwidth)) if(!powered_ai.anchored) loc = powered_ai.loc change_power_mode(NO_POWER_USE) @@ -879,7 +880,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( Bot.call_bot(src, waypoint) /mob/living/silicon/ai/alarm_triggered(src, class, area/A, list/O, obj/alarmsource) - if(!(class in alarms_listend_for)) + if(!(class in alarms_listened_for)) return if(alarmsource.z != z) return @@ -907,7 +908,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( /mob/living/silicon/ai/alarm_cancelled(src, class, area/A, obj/origin, cleared) if(cleared) - if(!(class in alarms_listend_for)) + if(!(class in alarms_listened_for)) return if(origin.z != z) return @@ -1394,7 +1395,7 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( /mob/living/silicon/ai/proc/add_program_picker() view_core() // A BYOND bug requires you to be viewing your core before your verbs update - program_picker = new /datum/program_picker + program_picker = new /datum/program_picker() program_action = new(program_picker) AddSpell(program_action) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 36416c358a31..936973b6a1ac 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -61,7 +61,7 @@ /datum/program_picker/proc/refund_purchases() var/list/potential_losses = possible_programs while(memory < 0) - if(!potential_losses) + if(!length(potential_losses)) return var/datum/ai_program/program = pick_n_take(potential_losses) if(!program.installed) @@ -71,7 +71,7 @@ /datum/program_picker/proc/refund_upgrades() var/list/potential_losses = possible_programs while(bandwidth < 0) - if(!potential_losses) + if(!length(potential_losses)) return var/datum/ai_program/program = pick_n_take(potential_losses) if(!program.upgrade_level) @@ -207,13 +207,12 @@ if(!istype(user)) return user.program_picker.bandwidth-- - return /datum/ai_program/proc/downgrade(mob/living/silicon/ai/user) if(!istype(user)) return upgrade_level-- - if(!upgrade_level) + if(!upgrade_level <= 0) uninstall(user) return user.program_picker.bandwidth++ @@ -250,7 +249,7 @@ /datum/ai_program/rgb_lighting program_name = "RGB Lighting" program_id = "rgb_lighting" - description = "Recolor a light to a desired color" + description = "Recolor a light to a desired color. At significantly high efficiency, it can change the color of an entire room's lighting by targeting the APC." nanite_cost = 5 power_type = /datum/spell/ai_spell/ranged/rgb_lighting unlock_text = "RGB Lighting installation complete!" @@ -274,7 +273,7 @@ to_chat(user, "You can only recolor lights!") return // Color selection - var/color_picked = tgui_input_color(user,"Please select a light color.","RGB Lighting Color") + var/color_picked = tgui_input_color(user, "Please select a light color.", "RGB Lighting Color") var/list/hsl = rgb2hsl(hex2num(copytext(color_picked, 2, 4)), hex2num(copytext(color_picked, 4, 6)), hex2num(copytext(color_picked, 6, 8))) hsl[3] = max(hsl[3], 0.4) var/list/rgb = hsl2rgb(arglist(hsl)) @@ -451,6 +450,7 @@ if(!istype(user)) return user.adapter_efficiency = 0.5 + user.universal_adapter = FALSE // Door Override - Repairs door wires if the AI wire is not cut /datum/ai_program/door_override @@ -648,7 +648,7 @@ target.emagged = FALSE target.on = target.has_power() AI.program_picker.nanites -= 5 - user.playsound_local(user, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) + user.playsound_local(user, 'sound/machines/ding.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) var/obj/machinery/camera/C = find_nearest_camera(target) if(!istype(C)) @@ -699,7 +699,7 @@ target.heal_overall_damage(damage_healed, damage_healed) if(spell_level >= 5) for(var/obj/item/organ/external/E in target.bodyparts) - if(prob(5*spell_level)) + if(prob(5 * spell_level)) E.mend_fracture() E.fix_internal_bleeding() E.fix_burn_wound() @@ -794,7 +794,7 @@ if(current.level >= 8) continue files.UpdateTech(tech_to_upgrade.id, current.level + 1) - to_chat(user, "Discovered innovations has led to an increase in the [current] field!") + to_chat(user, "Discovered innovations have led to an increase in the field of [current]!") upgraded = TRUE /datum/spell/ai_spell/research_subsystem/on_purchase_upgrade() @@ -874,7 +874,7 @@ var/sign_id = tgui_input_list(usr, "Select an holosgn!", "AI", sign_choices) if(!sign_id) return - var/sign_type = null + var/sign_type switch(sign_id) if("Engineering") sign_type = /obj/structure/holosign/barrier/engineering @@ -953,7 +953,7 @@ if(!istype(user)) return user.enhanced_tracking = TRUE - user.alarms_listend_for += "Tracking" + user.alarms_listened_for += "Tracking" user.enhanced_tracking_delay = initial(user.enhanced_tracking_delay) - (upgrade_level * 2 SECONDS) /datum/ai_program/enhanced_tracker/downgrade(mob/living/silicon/ai/user) @@ -963,7 +963,7 @@ /datum/ai_program/enhanced_tracker/uninstall(mob/living/silicon/ai/user) ..() user.enhanced_tracking = FALSE - user.alarms_listend_for -= "Tracking" + user.alarms_listened_for -= "Tracking" user.enhanced_tracking_delay = initial(user.enhanced_tracking_delay) /datum/spell/ai_spell/enhanced_tracker @@ -984,7 +984,7 @@ user.tracked_mob = (isnull(user.track.humans[target_name]) ? user.track.others[target_name] : user.track.humans[target_name]) /mob/living/silicon/ai/proc/raise_tracking_alert(area/A, mob/target) - var/closest_camera = null + var/obj/machinery/camera/closest_camera for(var/obj/machinery/camera/C in A) if(closest_camera == null) closest_camera = C @@ -992,7 +992,7 @@ if(get_dist(closest_camera, target) > get_dist(C, target)) closest_camera = C continue - target.visible_message("A purple light flashes on [closest_camera]!") + closest_camera.visible_message("A purple light flashes on [closest_camera]!") if(GLOB.alarm_manager.trigger_alarm("Tracking", A, A.cameras, closest_camera)) // Cancel alert after 1 minute addtimer(CALLBACK(GLOB.alarm_manager, TYPE_PROC_REF(/datum/alarm_manager, cancel_alarm), "Tracking", A, closest_camera), 1 MINUTES) diff --git a/code/modules/mob/living/silicon/robot/robot_mob.dm b/code/modules/mob/living/silicon/robot/robot_mob.dm index 4b49a4010b1f..ce495d28311d 100644 --- a/code/modules/mob/living/silicon/robot/robot_mob.dm +++ b/code/modules/mob/living/silicon/robot/robot_mob.dm @@ -799,7 +799,7 @@ GLOBAL_LIST_INIT(robot_verbs_default, list( var/list/dat = list() var/list/list/temp_alarm_list = GLOB.alarm_manager.alarms.Copy() for(var/cat in temp_alarm_list) - if(!(cat in alarms_listend_for)) + if(!(cat in alarms_listened_for)) continue dat += "[cat]
\n" var/list/list/L = temp_alarm_list[cat].Copy() @@ -886,7 +886,7 @@ GLOBAL_LIST_INIT(robot_verbs_default, list( return low_power_mode /mob/living/silicon/robot/alarm_triggered(src, class, area/A, list/O, obj/alarmsource) - if(!(class in alarms_listend_for)) + if(!(class in alarms_listened_for)) return if(alarmsource.z != z) return @@ -896,7 +896,7 @@ GLOBAL_LIST_INIT(robot_verbs_default, list( /mob/living/silicon/robot/alarm_cancelled(src, class, area/A, obj/origin, cleared) if(cleared) - if(!(class in alarms_listend_for)) + if(!(class in alarms_listened_for)) return if(origin.z != z) return diff --git a/code/modules/mob/living/silicon/silicon_mob.dm b/code/modules/mob/living/silicon/silicon_mob.dm index d60ecf8f540e..ed830103ac21 100644 --- a/code/modules/mob/living/silicon/silicon_mob.dm +++ b/code/modules/mob/living/silicon/silicon_mob.dm @@ -20,7 +20,7 @@ var/list/alarms_to_clear = list() var/list/alarm_types_show = list("Motion" = 0, "Fire" = 0, "Atmosphere" = 0, "Power" = 0) var/list/alarm_types_clear = list("Motion" = 0, "Fire" = 0, "Atmosphere" = 0, "Power" = 0) - var/list/alarms_listend_for = list("Motion", "Fire", "Atmosphere", "Power") + var/list/alarms_listened_for = list("Motion", "Fire", "Atmosphere", "Power") //var/list/hud_list[10] var/list/speech_synthesizer_langs = list() //which languages can be vocalized by the speech synthesizer var/designation = "" From 28c64fc8cbea5f8e29345f3325b96b2e28a8291c Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 19:31:22 -0500 Subject: [PATCH 41/44] Camera beam helper proc --- .../gamemodes/malfunction/Malf_Modules.dm | 6 +++ .../mob/living/silicon/ai/ai_programs.dm | 47 ++++--------------- 2 files changed, 15 insertions(+), 38 deletions(-) diff --git a/code/game/gamemodes/malfunction/Malf_Modules.dm b/code/game/gamemodes/malfunction/Malf_Modules.dm index 3bbdb68e162e..12f96a90a8d0 100644 --- a/code/game/gamemodes/malfunction/Malf_Modules.dm +++ b/code/game/gamemodes/malfunction/Malf_Modules.dm @@ -46,6 +46,12 @@ continue return closest_camera +/datum/spell/ai_spell/proc/camera_beam(target, icon_state, icon, time) + var/obj/machinery/camera/C = find_nearest_camera(target) + if(!istype(C)) + return + C.Beam(target, icon_state = icon_state, icon = icon, time = time) + /datum/spell/ai_spell/proc/adjust_uses(amt, mob/living/silicon/ai/owner, silent) uses += amt if(!silent && uses) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index 936973b6a1ac..fc50b45b57a9 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -294,10 +294,7 @@ AI.program_picker.nanites -= 5 user.playsound_local(user, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) @@ -360,10 +357,7 @@ AI.program_picker.nanites -= 20 user.playsound_local(user, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/power_shunt/on_purchase_upgrade() power_sent = min(10000, 2500 + (spell_level * 2500)) @@ -415,10 +409,7 @@ AI.program_picker.nanites -= 75 user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "medbeam", icon = 'icons/effects/beam.dmi', time = 10) + camera_beam(target, "medbeam", 'icons/effects/beam.dmi', 10) /datum/spell/ai_spell/ranged/repair_nanites/on_purchase_upgrade() cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - ((spell_level-3) * 60)), 30 SECONDS) @@ -490,10 +481,7 @@ var/duration = (6 - spell_level) SECONDS AI.program_picker.nanites -= 25 user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = duration) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) var/obj/effect/temp_visual/rcd_effect/spawning_effect = new(T) spawning_effect.duration = duration QDEL_IN(spawning_effect, duration) @@ -543,12 +531,7 @@ AI.program_picker.nanites -= 50 user.playsound_local(user, 'sound/items/syringeproj.ogg', 40, FALSE, use_reverb = FALSE) playsound(src, 'sound/items/syringeproj.ogg', 40, TRUE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - sleep(5) - nanofrost.Smoke() - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) sleep(5) nanofrost.Smoke() @@ -650,10 +633,7 @@ AI.program_picker.nanites -= 5 user.playsound_local(user, 'sound/machines/ding.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() cooldown_handler.recharge_duration = base_cooldown - (spell_level * 5) @@ -690,10 +670,7 @@ AI.program_picker.nanites -= 75 user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "medbeam", icon = 'icons/effects/beam.dmi', time = 10) + camera_beam(target, "medbeam", 'icons/effects/beam.dmi', 10) if(do_after_once(AI, 5 SECONDS, target = target, allow_moving = TRUE)) var/damage_healed = 20 + (min(30, (10 * spell_level))) target.heal_overall_damage(damage_healed, damage_healed) @@ -829,11 +806,8 @@ AI.program_picker.nanites -= 50 user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) playsound(target, 'sound/effects/bubbles2.ogg', 50, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 15) var/obj/effect/particle_effect/foam/metal/F = new /obj/effect/particle_effect/foam/metal(get_turf(target), TRUE) - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 15) F.spread_amount = 2 /datum/spell/ai_spell/ranged/door_override/on_purchase_upgrade() @@ -891,10 +865,7 @@ addtimer(CALLBACK(src, PROC_REF(sign_timer_complete), H), (60 + 30 * spell_level) SECONDS, TIMER_UNIQUE) user.playsound_local(user, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) playsound(target, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) - var/obj/machinery/camera/C = find_nearest_camera(target) - if(!istype(C)) - return - C.Beam(target, icon_state = "rped_upgrade", icon = 'icons/effects/effects.dmi', time = 5) + camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/holosign_displayer/proc/sign_timer_complete(obj/structure/holosign/H) playsound(H.loc, 'sound/machines/chime.ogg', 20, 1) From 9fc596d935c052638083aa9baa5069187aff3f88 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 19:42:53 -0500 Subject: [PATCH 42/44] AI remote sound helper --- code/modules/mob/living/silicon/ai/ai_mob.dm | 4 +++ .../mob/living/silicon/ai/ai_programs.dm | 32 +++++++------------ 2 files changed, 15 insertions(+), 21 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_mob.dm b/code/modules/mob/living/silicon/ai/ai_mob.dm index f15972dfe5af..09013cab4a61 100644 --- a/code/modules/mob/living/silicon/ai/ai_mob.dm +++ b/code/modules/mob/living/silicon/ai/ai_mob.dm @@ -1516,6 +1516,10 @@ GLOBAL_LIST_INIT(ai_verbs_default, list( eyeobj.acceleration = !eyeobj.acceleration to_chat(usr, "Camera acceleration has been toggled [eyeobj.acceleration ? "on" : "off"].") +/mob/living/silicon/ai/proc/play_sound_remote(target, sound, volume) + playsound_local(src, sound, volume, FALSE, use_reverb = FALSE) + playsound(target, sound, volume, FALSE, use_reverb = FALSE) + /mob/living/silicon/ai/handle_fire() return diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index fc50b45b57a9..fdccaa444d44 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -292,8 +292,7 @@ L.brightness_color = new_color var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 5 - user.playsound_local(user, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/effects/spray.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/effects/spray.ogg', 50) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() @@ -355,8 +354,7 @@ power_source.charge -= power_sent break AI.program_picker.nanites -= 20 - user.playsound_local(user, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/goonstation/misc/fuse.ogg', 50) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/power_shunt/on_purchase_upgrade() @@ -407,8 +405,7 @@ var/damage_healed = AI.adapter_efficiency * (20 + (min(30, (10 * spell_level)))) T.heal_overall_damage(damage_healed, damage_healed, TRUE, 0, 1) AI.program_picker.nanites -= 75 - user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/goonstation/misc/fuse.ogg', 50) camera_beam(target, "medbeam", 'icons/effects/beam.dmi', 10) /datum/spell/ai_spell/ranged/repair_nanites/on_purchase_upgrade() @@ -480,7 +477,7 @@ var/mob/living/silicon/ai/AI = user var/duration = (6 - spell_level) SECONDS AI.program_picker.nanites -= 25 - user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) + AI.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) var/obj/effect/temp_visual/rcd_effect/spawning_effect = new(T) spawning_effect.duration = duration @@ -529,8 +526,7 @@ log_game("[key_name(user)] used Nanofrost at [get_area(target)] ([target.x], [target.y], [target.z]).") var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 50 - user.playsound_local(user, 'sound/items/syringeproj.ogg', 40, FALSE, use_reverb = FALSE) - playsound(src, 'sound/items/syringeproj.ogg', 40, TRUE) + AI.play_sound_remote(src, 'sound/items/syringeproj.ogg', 40) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) sleep(5) nanofrost.Smoke() @@ -631,8 +627,7 @@ target.emagged = FALSE target.on = target.has_power() AI.program_picker.nanites -= 5 - user.playsound_local(user, 'sound/machines/ding.ogg', 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/machines/ding.ogg',, 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/machines/ding.ogg', 50) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/rgb_lighting/on_purchase_upgrade() @@ -668,8 +663,7 @@ return var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 75 - user.playsound_local(user, "sound/goonstation/misc/fuse.ogg", 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/goonstation/misc/fuse.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/goonstation/misc/fuse.ogg', 50) camera_beam(target, "medbeam", 'icons/effects/beam.dmi', 10) if(do_after_once(AI, 5 SECONDS, target = target, allow_moving = TRUE)) var/damage_healed = 20 + (min(30, (10 * spell_level))) @@ -804,8 +798,7 @@ var/target = targets[1] var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 50 - user.playsound_local(user, 'sound/items/deconstruct.ogg', 50, FALSE, use_reverb = FALSE) - playsound(target, 'sound/effects/bubbles2.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/effects/bubbles2.ogg', 50) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 15) var/obj/effect/particle_effect/foam/metal/F = new /obj/effect/particle_effect/foam/metal(get_turf(target), TRUE) F.spread_amount = 2 @@ -863,8 +856,7 @@ AI.program_picker.nanites -= 10 var/H = new sign_type(get_turf(target), src) addtimer(CALLBACK(src, PROC_REF(sign_timer_complete), H), (60 + 30 * spell_level) SECONDS, TIMER_UNIQUE) - user.playsound_local(user, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) - playsound(target, 'sound/machines/click.ogg', 20, FALSE, use_reverb = FALSE) + AI.play_sound_remote(target, 'sound/machines/click.ogg', 20) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) /datum/spell/ai_spell/ranged/holosign_displayer/proc/sign_timer_complete(obj/structure/holosign/H) @@ -900,11 +892,9 @@ var/mob/living/silicon/ai/AI = user AI.program_picker.nanites -= 5 if(spell_level >= 10) - playsound(target, 'sound/items/airhorn.ogg', 100, 1) - user.playsound_local(user, 'sound/items/airhorn.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(user, 'sound/items/airhorn.ogg', 50,) else - playsound(target, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) - user.playsound_local(user, 'sound/items/bikehorn.ogg', 50, FALSE, use_reverb = FALSE) + AI.play_sound_remote(user, 'sound/items/bikehorn.ogg', 50) /datum/spell/ai_spell/ranged/honk_subsystem/on_purchase_upgrade() cooldown_handler.recharge_duration = max(base_cooldown - (spell_level * 15) SECONDS, 15 SECONDS) From d003b4a6b834d0230692ebc1700d6d4b9db2b99f Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 19:50:42 -0500 Subject: [PATCH 43/44] Timer on nanofrost --- code/modules/mob/living/silicon/ai/ai_programs.dm | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/code/modules/mob/living/silicon/ai/ai_programs.dm b/code/modules/mob/living/silicon/ai/ai_programs.dm index fdccaa444d44..6e821fd9b7cc 100644 --- a/code/modules/mob/living/silicon/ai/ai_programs.dm +++ b/code/modules/mob/living/silicon/ai/ai_programs.dm @@ -528,8 +528,7 @@ AI.program_picker.nanites -= 50 AI.play_sound_remote(src, 'sound/items/syringeproj.ogg', 40) camera_beam(target, "rped_upgrade", 'icons/effects/effects.dmi', 5) - sleep(5) - nanofrost.Smoke() + addtimer(CALLBACK(nanofrost, TYPE_PROC_REF(/obj/effect/nanofrost_container, Smoke)), 5 SECONDS) /datum/spell/ai_spell/ranged/extinguishing_system/on_purchase_upgrade() cooldown_handler.recharge_duration = max(min(base_cooldown, base_cooldown - (spell_level * 30)), 30 SECONDS) From 6f266f37ab5bbe902e7cda984a18fcae6b1124d6 Mon Sep 17 00:00:00 2001 From: PollardTheDragon <144391971+PollardTheDragon@users.noreply.github.com> Date: Wed, 29 Jan 2025 19:55:46 -0500 Subject: [PATCH 44/44] ui.user --- code/game/machinery/ai_resource.dm | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/code/game/machinery/ai_resource.dm b/code/game/machinery/ai_resource.dm index a14ece7ee6c6..2fe96e32ba81 100644 --- a/code/game/machinery/ai_resource.dm +++ b/code/game/machinery/ai_resource.dm @@ -268,13 +268,13 @@ GLOBAL_LIST_EMPTY(ai_nodes) data["nodes_list"] += list(node_data) return data -/obj/machinery/computer/ai_resource/ui_act(action, params) +/obj/machinery/computer/ai_resource/ui_act(action, params, datum/tgui/ui, datum/ui_state/state) if(..()) return . = FALSE - if(!is_authenticated(usr)) - to_chat(usr, "Access denied.") + if(!is_authenticated(ui.user)) + to_chat(ui.user, "Access denied.") return if(SSticker.current_state == GAME_STATE_FINISHED) - to_chat(usr, "Access denied, AIs are no longer your station's property.") + to_chat(ui.user, "Access denied, AIs are no longer your station's property.") return