Files
Bubberstation/code/modules/wiremod/shell/module.dm
FlufflesTheDog 2e3a90293d Dehardcoded modsuit fixes (#83425)
## About The Pull Request
Patches up some things that were lacking post #82905
- Some missing (un)seal messages
- a missed direct use of the mod_parts list
EDIT: Also fixes the modsuit painter, and makes sure modsuits can still
be set to use custom dmi files via
`MOD_ICON_OVERRIDE`/`MOD_WORN_ICON_OVERRIDE`
Fixes #83442
## Changelog
🆑
fix: some missing modsuit (un)sealing messages should no longer be
missing
fix: MOD circuit adapter core deployed parts output should work again
fix: Modsuit painter works again
/🆑
2024-05-28 14:32:28 +02:00

302 lines
12 KiB
Plaintext

/obj/item/mod/module/circuit
name = "MOD circuit adapter module"
desc = "A module shell that allows a circuit to be inserted into, and interface with, a MODsuit."
module_type = MODULE_USABLE
complexity = 1
idle_power_cost = DEFAULT_CHARGE_DRAIN * 0.5
incompatible_modules = list(/obj/item/mod/module/circuit)
cooldown_time = 0.5 SECONDS
/// A reference to the shell component, used to access the shell and its attached circuit
var/datum/component/shell/shell
/// List of installed action components
var/list/obj/item/circuit_component/equipment_action/action_comps = list()
/obj/item/mod/module/circuit/Initialize(mapload)
. = ..()
RegisterSignal(src, COMSIG_CIRCUIT_ACTION_COMPONENT_REGISTERED, PROC_REF(action_comp_registered))
RegisterSignal(src, COMSIG_CIRCUIT_ACTION_COMPONENT_UNREGISTERED, PROC_REF(action_comp_unregistered))
shell = AddComponent(/datum/component/shell, \
list(new /obj/item/circuit_component/mod_adapter_core()), \
capacity = SHELL_CAPACITY_LARGE, \
)
/obj/item/mod/module/circuit/proc/override_power_usage(datum/source, amount)
SIGNAL_HANDLER
if(drain_power(amount))
. = COMPONENT_OVERRIDE_POWER_USAGE
/obj/item/mod/module/circuit/proc/action_comp_registered(datum/source, obj/item/circuit_component/equipment_action/action_comp)
SIGNAL_HANDLER
action_comps += action_comp
/obj/item/mod/module/circuit/proc/action_comp_unregistered(datum/source, obj/item/circuit_component/equipment_action/action_comp)
SIGNAL_HANDLER
action_comps -= action_comp
for(var/ref in action_comp.granted_to)
unpin_action(action_comp, locate(ref))
QDEL_LIST_ASSOC_VAL(action_comp.granted_to)
/obj/item/mod/module/circuit/on_install()
if(!shell?.attached_circuit)
return
RegisterSignal(shell?.attached_circuit, COMSIG_CIRCUIT_PRE_POWER_USAGE, PROC_REF(override_power_usage))
/obj/item/mod/module/circuit/on_uninstall(deleting = FALSE)
if(!shell?.attached_circuit)
return
for(var/obj/item/circuit_component/equipment_action/action_comp in action_comps)
for(var/ref in action_comp.granted_to)
unpin_action(action_comp, locate(ref))
UnregisterSignal(shell?.attached_circuit, COMSIG_CIRCUIT_PRE_POWER_USAGE)
/obj/item/mod/module/circuit/on_use()
. = ..()
if(!.)
return
if(!shell.attached_circuit)
return
shell.attached_circuit?.interact(mod.wearer)
/obj/item/mod/module/circuit/get_configuration(mob/user)
. = ..()
var/unnamed_action_index = 1
for(var/obj/item/circuit_component/equipment_action/action_comp in action_comps)
.[REF(action_comp)] = add_ui_configuration(action_comp.button_name.value || "Unnamed Action [unnamed_action_index++]", "pin", !!action_comp.granted_to[REF(user)])
/obj/item/mod/module/circuit/configure_edit(key, value)
. = ..()
var/obj/item/circuit_component/equipment_action/action_comp = locate(key) in action_comps
if(!istype(action_comp))
return
if(text2num(value))
pin_action(action_comp, usr)
else
unpin_action(action_comp, usr)
/obj/item/mod/module/circuit/proc/pin_action(obj/item/circuit_component/equipment_action/action_comp, mob/user)
if(!istype(user))
return
if(action_comp.granted_to[REF(user)]) // Sanity check - don't pin an action for a mob that has already pinned it
return
mod.add_item_action(new/datum/action/item_action/mod/pinnable/circuit(mod, user, src, action_comp))
/obj/item/mod/module/circuit/proc/unpin_action(obj/item/circuit_component/equipment_action/action_comp, mob/user)
var/datum/action/item_action/mod/pinnable/circuit/action = action_comp.granted_to[REF(user)]
if(!istype(action))
return
qdel(action)
/datum/action/item_action/mod/pinnable/circuit
button_icon = 'icons/mob/actions/actions_items.dmi'
button_icon_state = "bci_blank"
/// A reference to the module containing this action's component
var/obj/item/mod/module/circuit/module
/// A reference to the component this action triggers.
var/obj/item/circuit_component/equipment_action/circuit_component
/datum/action/item_action/mod/pinnable/circuit/New(Target, mob/user, obj/item/mod/module/circuit/linked_module, obj/item/circuit_component/equipment_action/action_comp)
. = ..()
module = linked_module
action_comp.granted_to[REF(user)] = src
circuit_component = action_comp
name = action_comp.button_name.value
button_icon_state = "bci_[replacetextEx(LOWER_TEXT(action_comp.icon_options.value), " ", "_")]"
/datum/action/item_action/mod/pinnable/circuit/Destroy()
circuit_component.granted_to -= REF(pinner)
circuit_component = null
return ..()
/datum/action/item_action/mod/pinnable/circuit/Trigger(trigger_flags)
. = ..()
if(!.)
return
var/obj/item/mod/control/mod = module.mod
if(!istype(mod))
return
if(!mod.active || mod.activating)
if(mod.wearer)
module.balloon_alert(mod.wearer, "not active!")
return
circuit_component.user.set_output(owner)
circuit_component.signal.set_output(COMPONENT_SIGNAL)
/// If the guy whose UI we are pinned to got deleted
/datum/action/item_action/mod/pinnable/circuit/pinner_deleted()
module?.action_comps[circuit_component] -= REF(pinner)
. = ..()
/obj/item/circuit_component/mod_adapter_core
display_name = "MOD circuit adapter core"
desc = "Provides a reference to the MODsuit's occupant and allows the circuit to toggle the MODsuit."
/// The MODsuit module this circuit is associated with
var/obj/item/mod/module/attached_module
/// The name of the module to select
var/datum/port/input/option/module_to_select
/// The signal to toggle deployment of the modsuit
var/datum/port/input/toggle_deploy
/// The signal to toggle the suit
var/datum/port/input/toggle_suit
/// The signal to select a module
var/datum/port/input/select_module
/// A reference to the wearer of the MODsuit
var/datum/port/output/wearer
/// Whether or not the suit is deployed
var/datum/port/output/deployed
/// Whether or not the suit is activated
var/datum/port/output/activated
/// The name of the last selected module
var/datum/port/output/selected_module
/// A list of the names of all currently deployed parts
var/datum/port/output/deployed_parts
/// The signal that is triggered when a module is selected
var/datum/port/output/on_module_selected
/// The signal that is triggered when the suit is deployed by a signal
var/datum/port/output/on_deploy
/// The signal that is triggered when the suit has finished toggling itself after being activated by a signal
var/datum/port/output/on_toggle_finish
/obj/item/circuit_component/mod_adapter_core/populate_options()
module_to_select = add_option_port("Module to Select", list())
/obj/item/circuit_component/mod_adapter_core/populate_ports()
// Input Signals
toggle_deploy = add_input_port("Toggle Deployment", PORT_TYPE_SIGNAL)
toggle_suit = add_input_port("Toggle Suit", PORT_TYPE_SIGNAL)
select_module = add_input_port("Select Module", PORT_TYPE_SIGNAL)
// States
wearer = add_output_port("Wearer", PORT_TYPE_USER)
deployed = add_output_port("Deployed", PORT_TYPE_NUMBER)
activated = add_output_port("Activated", PORT_TYPE_NUMBER)
selected_module = add_output_port("Selected Module", PORT_TYPE_STRING)
deployed_parts = add_output_port("Deployed Parts", PORT_TYPE_LIST(PORT_TYPE_STRING))
// Output Signals
on_module_selected = add_output_port("On Module Selected", PORT_TYPE_SIGNAL)
on_deploy = add_output_port("On Deploy", PORT_TYPE_SIGNAL)
on_toggle_finish = add_output_port("Finished Toggling", PORT_TYPE_SIGNAL)
/obj/item/circuit_component/mod_adapter_core/register_shell(atom/movable/shell)
. = ..()
if(istype(shell, /obj/item/mod/module))
attached_module = shell
RegisterSignal(attached_module, COMSIG_MOVABLE_MOVED, PROC_REF(on_move))
/obj/item/circuit_component/mod_adapter_core/unregister_shell(atom/movable/shell)
if(attached_module)
UnregisterSignal(attached_module, COMSIG_MOVABLE_MOVED)
attached_module = null
return ..()
/obj/item/circuit_component/mod_adapter_core/input_received(datum/port/input/port)
if(!attached_module?.mod)
return
var/obj/item/mod/module/module
for(var/obj/item/mod/module/potential_module as anything in attached_module.mod.modules)
if(potential_module.name == module_to_select.value)
module = potential_module
if(COMPONENT_TRIGGERED_BY(toggle_suit, port))
INVOKE_ASYNC(attached_module.mod, TYPE_PROC_REF(/obj/item/mod/control, toggle_activate), attached_module.mod.wearer)
if(COMPONENT_TRIGGERED_BY(toggle_deploy, port))
INVOKE_ASYNC(attached_module.mod, TYPE_PROC_REF(/obj/item/mod/control, quick_deploy), attached_module.mod.wearer)
if(attached_module.mod.active && module && COMPONENT_TRIGGERED_BY(select_module, port))
INVOKE_ASYNC(module, TYPE_PROC_REF(/obj/item/mod/module, on_select))
/obj/item/circuit_component/mod_adapter_core/proc/on_move(atom/movable/source, atom/old_loc, dir, forced)
SIGNAL_HANDLER
if(istype(source.loc, /obj/item/mod/control))
var/obj/item/mod/control/mod = source.loc
RegisterSignal(mod, COMSIG_MOD_MODULE_SELECTED, PROC_REF(on_module_select))
RegisterSignal(mod, COMSIG_MOD_DEPLOYED, PROC_REF(on_mod_part_toggled))
RegisterSignal(mod, COMSIG_MOD_RETRACTED, PROC_REF(on_mod_part_toggled))
RegisterSignal(mod, COMSIG_MOD_TOGGLED, PROC_REF(on_mod_toggled))
RegisterSignal(mod, COMSIG_MOD_MODULE_ADDED, PROC_REF(on_module_changed))
RegisterSignal(mod, COMSIG_MOD_MODULE_REMOVED, PROC_REF(on_module_changed))
RegisterSignal(mod, COMSIG_ITEM_EQUIPPED, PROC_REF(equip_check))
wearer.set_output(mod.wearer)
var/modules_list = list()
for(var/obj/item/mod/module/module in mod.modules)
if(module.module_type != MODULE_PASSIVE)
modules_list += module.name
module_to_select.possible_options = modules_list
if (module_to_select.possible_options.len)
module_to_select.set_value(module_to_select.possible_options[1])
else if(istype(old_loc, /obj/item/mod/control))
UnregisterSignal(old_loc, list(COMSIG_MOD_MODULE_SELECTED, COMSIG_ITEM_EQUIPPED))
UnregisterSignal(old_loc, COMSIG_MOD_DEPLOYED)
UnregisterSignal(old_loc, COMSIG_MOD_RETRACTED)
UnregisterSignal(old_loc, COMSIG_MOD_TOGGLED)
UnregisterSignal(old_loc, COMSIG_MOD_MODULE_ADDED)
UnregisterSignal(old_loc, COMSIG_MOD_MODULE_REMOVED)
selected_module.set_output(null)
wearer.set_output(null)
deployed.set_output(FALSE)
activated.set_output(FALSE)
/obj/item/circuit_component/mod_adapter_core/proc/on_module_select(datum/source, obj/item/mod/module/module)
SIGNAL_HANDLER
selected_module.set_output(module.name)
on_module_selected.set_output(COMPONENT_SIGNAL)
/obj/item/circuit_component/mod_adapter_core/proc/on_module_changed()
SIGNAL_HANDLER
var/modules_list = list()
for(var/obj/item/mod/module/module in attached_module.mod.modules)
if(module.module_type != MODULE_PASSIVE)
modules_list += module.name
module_to_select.possible_options = modules_list
if (module_to_select.possible_options.len)
module_to_select.set_value(module_to_select.possible_options[1])
/obj/item/circuit_component/mod_adapter_core/proc/on_mod_part_toggled()
SIGNAL_HANDLER
var/string_list = list()
var/is_deployed = TRUE
for(var/obj/item/part as anything in attached_module.mod.get_parts())
if(part.loc == attached_module.mod)
is_deployed = FALSE
else
var/part_name = "Undefined"
if(istype(part, /obj/item/clothing/head/mod))
part_name = "Helmet"
if(istype(part, /obj/item/clothing/suit/mod))
part_name = "Chestplate"
if(istype(part, /obj/item/clothing/gloves/mod))
part_name = "Gloves"
if(istype(part, /obj/item/clothing/shoes/mod))
part_name = "Boots"
string_list += part_name
deployed_parts.set_output(string_list)
deployed.set_output(is_deployed)
on_deploy.set_output(COMPONENT_SIGNAL)
/obj/item/circuit_component/mod_adapter_core/proc/on_mod_toggled()
SIGNAL_HANDLER
activated.set_output(attached_module.mod.active)
on_toggle_finish.set_output(COMPONENT_SIGNAL)
/obj/item/circuit_component/mod_adapter_core/proc/equip_check()
SIGNAL_HANDLER
if(!attached_module.mod?.wearer)
return
wearer.set_output(attached_module.mod.wearer)