From 07bd51f79afaf2704b9ad6172be7c208fd485777 Mon Sep 17 00:00:00 2001 From: Ghommie <42542238+Ghommie@users.noreply.github.com> Date: Wed, 4 Dec 2019 19:38:25 +0100 Subject: [PATCH] Ports flag for bespoke elements. --- code/__DEFINES/components.dm | 6 ++++++ code/controllers/subsystem/dcs.dm | 18 +++++++++++++++--- code/datums/elements/_element.dm | 18 ++++++++++++++---- 3 files changed, 35 insertions(+), 7 deletions(-) diff --git a/code/__DEFINES/components.dm b/code/__DEFINES/components.dm index 9dad2926f8..2a11390a16 100644 --- a/code/__DEFINES/components.dm +++ b/code/__DEFINES/components.dm @@ -8,7 +8,13 @@ #define ELEMENT_INCOMPATIBLE 1 // Return value to cancel attaching // /datum/element flags +/// Causes the detach proc to be called when the host object is being deleted #define ELEMENT_DETACH (1 << 0) +/** + * Only elements created with the same arguments given after `id_arg_index` share an element instance + * The arguments are the same when the text and number values are the same and all other values have the same ref + */ +#define ELEMENT_BESPOKE (1 << 1) // How multiple components of the exact same type are handled in the same datum diff --git a/code/controllers/subsystem/dcs.dm b/code/controllers/subsystem/dcs.dm index e94f233f04..faf95fd319 100644 --- a/code/controllers/subsystem/dcs.dm +++ b/code/controllers/subsystem/dcs.dm @@ -6,10 +6,22 @@ PROCESSING_SUBSYSTEM_DEF(dcs) /datum/controller/subsystem/processing/dcs/Recover() comp_lookup = SSdcs.comp_lookup -/datum/controller/subsystem/processing/dcs/proc/GetElement(eletype) - . = elements_by_type[eletype] +/datum/controller/subsystem/processing/dcs/proc/GetElement(datum/element/eletype, ...) + var/element_id = eletype + + if(initial(eletype.element_flags) & ELEMENT_BESPOKE) + var/list/fullid = list("[eletype]") + for(var/i in initial(eletype.id_arg_index) to length(args)) + var/argument = args[i] + if(istext(argument) || isnum(argument)) + fullid += "[argument]" + else + fullid += "[REF(argument)]" + element_id = fullid.Join("&") + + . = elements_by_type[element_id] if(.) return if(!ispath(eletype, /datum/element)) CRASH("Attempted to instantiate [eletype] as a /datum/element") - . = elements_by_type[eletype] = new eletype \ No newline at end of file + . = elements_by_type[element_id] = new eletype \ No newline at end of file diff --git a/code/datums/elements/_element.dm b/code/datums/elements/_element.dm index f12835d2e2..8f9b97db22 100644 --- a/code/datums/elements/_element.dm +++ b/code/datums/elements/_element.dm @@ -1,5 +1,11 @@ /datum/element var/element_flags = NONE + /** + * The index of the first attach argument to consider for duplicate elements + * Is only used when flags contains ELEMENT_BESPOKE + * This is infinity so you must explicitly set this + */ + var/id_arg_index = INFINITY /datum/element/proc/Attach(datum/target) if(type == /datum/element) @@ -19,11 +25,15 @@ //DATUM PROCS /datum/proc/AddElement(eletype, ...) - var/datum/element/ele = SSdcs.GetElement(eletype) + var/datum/element/ele = SSdcs.GetElement(arglist(args)) args[1] = src if(ele.Attach(arglist(args)) == ELEMENT_INCOMPATIBLE) CRASH("Incompatible [eletype] assigned to a [type]! args: [json_encode(args)]") -/datum/proc/RemoveElement(eletype) - var/datum/element/ele = SSdcs.GetElement(eletype) - ele.Detach(src) +/** + * Finds the singleton for the element type given and detaches it from src + * You only need additional arguments beyond the type if you're using ELEMENT_BESPOKE + */ +/datum/proc/RemoveElement(eletype, ...) + var/datum/element/ele = SSdcs.GetElement(arglist(args)) + ele.Detach(src) \ No newline at end of file