diff --git a/code/__DEFINES/crafting.dm b/code/__DEFINES/crafting.dm index 83fe9efbe1a..a5e217ae2b4 100644 --- a/code/__DEFINES/crafting.dm +++ b/code/__DEFINES/crafting.dm @@ -37,6 +37,14 @@ /// This craft won't change the materials of the resulting item to match that of the combined components #define CRAFT_NO_MATERIALS (1<<10) +//Crafting blacklist behaviors +/// By default, blacklist the result if it's not in reqs +#define BLACKLIST_RESULT_IF_NOT_IN_REQS null +/// Always blacklist - override default behavior +#define ALWAYS_BLACKLIST_RESULT TRUE +/// Never blacklist - override default behavior +#define NEVER_BLACKLIST_RESULT FALSE + //food/drink crafting defines //When adding new defines, please make sure to also add them to the encompassing list #define CAT_FOOD "Foods" diff --git a/code/__HELPERS/global_lists.dm b/code/__HELPERS/global_lists.dm index 5ba6af88746..4b34b40ee63 100644 --- a/code/__HELPERS/global_lists.dm +++ b/code/__HELPERS/global_lists.dm @@ -11,11 +11,9 @@ init_crafting_recipes_atoms() /// Inits crafting recipe lists -/proc/init_crafting_recipes(list/crafting_recipes) - for(var/path in subtypesof(/datum/crafting_recipe)) - if(ispath(path, /datum/crafting_recipe/stack)) - continue - var/datum/crafting_recipe/recipe = new path() +/proc/init_crafting_recipes() + for(var/datum/crafting_recipe_path as anything in valid_subtypesof(/datum/crafting_recipe)) + var/datum/crafting_recipe/recipe = new crafting_recipe_path() var/is_cooking = (recipe.category in GLOB.crafting_category_food) recipe.reqs = sort_list(recipe.reqs, GLOBAL_PROC_REF(cmp_crafting_req_priority)) if(recipe.name != "" && recipe.result) diff --git a/code/datums/actions/mobs/defensive_mode.dm b/code/datums/actions/mobs/defensive_mode.dm index 6030afea137..e19be70e845 100644 --- a/code/datums/actions/mobs/defensive_mode.dm +++ b/code/datums/actions/mobs/defensive_mode.dm @@ -34,7 +34,7 @@ defence(owner_mob) /datum/action/cooldown/mob_cooldown/defensive_mode/proc/offence(mob/living/basic/owner_mob) - owner_mob.damage_coeff = list(BRUTE = 1, BURN = 1.25, TOX = 1, STAMINA = 1, OXY = 1) + owner_mob.damage_coeff = string_assoc_list(list(BRUTE = 1, BURN = 1.25, TOX = 1, STAMINA = 1, OXY = 1)) owner_mob.icon_state = initial(owner_mob.icon_state) owner_mob.icon_living = initial(owner_mob.icon_living) owner_mob.icon_dead = initial(owner_mob.icon_dead) @@ -42,7 +42,7 @@ defense_active = FALSE /datum/action/cooldown/mob_cooldown/defensive_mode/proc/defence(mob/living/basic/owner_mob) - owner_mob.damage_coeff = list(BRUTE = 0.4, BURN = 0.5, TOX = 1, STAMINA = 1, OXY = 1) + owner_mob.damage_coeff = string_assoc_list(list(BRUTE = 0.4, BURN = 0.5, TOX = 1, STAMINA = 1, OXY = 1)) owner_mob.icon_dead = "[owner_mob.icon_state]_d_dead" owner_mob.icon_state = "[owner_mob.icon_state]_d" owner_mob.icon_living = "[owner_mob.icon_living]_d" diff --git a/code/datums/ai/basic_mobs/basic_subtrees/speech_subtree.dm b/code/datums/ai/basic_mobs/basic_subtrees/speech_subtree.dm index 7dbce139b57..2a4a0d336e2 100644 --- a/code/datums/ai/basic_mobs/basic_subtrees/speech_subtree.dm +++ b/code/datums/ai/basic_mobs/basic_subtrees/speech_subtree.dm @@ -2,23 +2,23 @@ //The chance of an emote occurring each second var/speech_chance = 0 ///Hearable emotes - var/list/emote_hear = list() + var/list/emote_hear ///Unlike speak_emote, the list of things in this variable only show by themselves with no spoken text. IE: Ian barks, Ian yaps - var/list/emote_see = list() + var/list/emote_see ///Possible lines of speech the AI can have - var/list/speak = list() + var/list/speak ///The sound effects associated with this speech, if any - var/list/sound = list() + var/list/sound /datum/ai_planning_subtree/random_speech/New() . = ..() - if(speak) + if(LAZYLEN(speak)) speak = string_list(speak) - if(sound) + if(LAZYLEN(sound)) sound = string_list(sound) - if(emote_hear) + if(LAZYLEN(emote_hear)) emote_hear = string_list(emote_hear) - if(emote_see) + if(LAZYLEN(emote_see)) emote_see = string_list(emote_see) /datum/ai_planning_subtree/random_speech/SelectBehaviors(datum/ai_controller/controller, seconds_per_tick) diff --git a/code/datums/components/chasm.dm b/code/datums/components/chasm.dm index 71bb1d28c53..69f1ea69cf7 100644 --- a/code/datums/components/chasm.dm +++ b/code/datums/components/chasm.dm @@ -6,7 +6,7 @@ var/oblivion_message = "You stumble and stare into the abyss before you. It stares back, and you fall into the enveloping dark." /// List of refs to falling objects -> how many levels deep we've fallen - var/static/list/falling_atoms = list() + var/static/list/falling_atoms var/static/list/forbidden_types = typecacheof(list( /obj/docking_port, /obj/effect/abstract, @@ -106,7 +106,8 @@ /datum/component/chasm/proc/droppable(atom/movable/dropped_thing) var/datum/weakref/falling_ref = WEAKREF(dropped_thing) // avoid an infinite loop, but allow falling a large distance - if(falling_atoms[falling_ref] && falling_atoms[falling_ref] > 30) + var/falling_atom = LAZYACCESS(falling_atoms, falling_ref) + if(falling_atom && falling_atom > 30) return CHASM_NOT_DROPPING if(is_type_in_typecache(dropped_thing, forbidden_types) || (!isliving(dropped_thing) && !isobj(dropped_thing))) return CHASM_NOT_DROPPING @@ -133,14 +134,14 @@ var/datum/weakref/falling_ref = WEAKREF(dropped_thing) //Make sure the item is still there after our sleep if(!dropped_thing || !falling_ref?.resolve()) - falling_atoms -= falling_ref + LAZYREMOVE(falling_atoms, falling_ref) return - falling_atoms[falling_ref] = (falling_atoms[falling_ref] || 0) + 1 + LAZYSET(falling_atoms, falling_ref, (falling_atoms[falling_ref] || 0) + 1) var/turf/below_turf = target_turf var/atom/parent = src.parent - if(falling_atoms[falling_ref] > 1) + if(LAZYACCESS(falling_atoms, falling_ref) > 1) return // We're already handling this if(SEND_SIGNAL(dropped_thing, COMSIG_MOVABLE_CHASM_DROPPED, parent) & COMPONENT_NO_CHASM_DROP) @@ -164,7 +165,7 @@ var/mob/living/fallen = dropped_thing fallen.Paralyze(100) fallen.adjust_brute_loss(30) - falling_atoms -= falling_ref + LAZYREMOVE(falling_atoms, falling_ref) return // send to oblivion @@ -235,7 +236,7 @@ fallen_mob.death(TRUE) fallen_mob.apply_damage(300) - falling_atoms -= falling_ref + LAZYREMOVE(falling_atoms, falling_ref) /** * Called when something has left the chasm depths storage. diff --git a/code/datums/components/crafting/_recipes.dm b/code/datums/components/crafting/_recipes.dm index 3989b0c8de3..77c075cfda1 100644 --- a/code/datums/components/crafting/_recipes.dm +++ b/code/datums/components/crafting/_recipes.dm @@ -8,7 +8,7 @@ ///type paths of items consumed associated with how many are needed var/list/reqs = list() ///type paths of items explicitly not allowed as an ingredient - var/list/blacklist = list() + var/list/blacklist ///type path of item resulting from this craft var/result /// String defines of items needed but not consumed. Lazy list. @@ -23,13 +23,13 @@ ///time in seconds. Remember to use the SECONDS define! var/time = 3 SECONDS ///type paths of items that will be forceMoved() into the result instead of being deleted - var/list/parts = list() + var/list/parts ///items, structures and machineries of types that are in this list won't transfer their materials to the result var/list/requirements_mats_blacklist ///if set, the materials in this list and their values will be subtracted from the result. var/list/removed_mats ///like tool_behaviors but for reagents - var/list/chem_catalysts = list() + var/list/chem_catalysts ///where it shows up in the crafting UI var/category ///Required machines for the craft, set the assigned value of the typepath to CRAFTING_MACHINERY_CONSUME or CRAFTING_MACHINERY_USE. Lazy associative list: type_path key -> flag value. @@ -50,19 +50,15 @@ var/delete_contents = TRUE /// Allows you to craft so that you don't have to click the craft button many times. var/mass_craftable = FALSE - ///crafting_flags var to hold bool values var/crafting_flags = CRAFT_CHECK_DENSITY - -/datum/crafting_recipe/New() - if(!name && result) - var/atom/atom_result = result - name = initial(atom_result.name) - - if(!(result in reqs)) - blacklist += result - // These should be excluded from all crafting recipies - blacklist += list( + /** + * Should the recipe blacklist its result? Default behavior is to blacklist any result that isn't in reqs. + * Can be set to ALWAYS_BLACKLIST_RESULT or NEVER_BLACKLIST_RESULT to override the default behavior. + */ + var/blacklist_result = BLACKLIST_RESULT_IF_NOT_IN_REQS + /// Global crafting blacklist. These should be excluded from all crafting recipes no matter what. + var/static/list/global_blacklist = typecacheof(list( /obj/item/cautery/augment, /obj/item/cautery/cruel/augment, /obj/item/circular_saw/augment, @@ -81,15 +77,25 @@ /obj/item/weldingtool/largetank/cyborg, /obj/item/wirecutters/cyborg, /obj/item/wrench/cyborg, - ) + )) + +/datum/crafting_recipe/New() + if(!name && result) + var/atom/atom_result = result + name = initial(atom_result.name) + if(result && blacklist_result == BLACKLIST_RESULT_IF_NOT_IN_REQS && !(result in reqs)) + blacklist_result = ALWAYS_BLACKLIST_RESULT if(tool_behaviors) tool_behaviors = string_list(tool_behaviors) if(tool_paths) tool_paths = string_list(tool_paths) - for(var/key in parts) - if(!parts[key]) + for(var/key, part in parts) + if(!part) //ensure every single, same-type part used for the recipe will be transferred if the value is otherwise not specified - parts[key] = INFINITY + part = INFINITY + +/datum/crafting_recipe/stack + abstract_type = /datum/crafting_recipe/stack /datum/crafting_recipe/stack/New(obj/item/stack/material, datum/stack_recipe/stack_recipe) if(!material || !stack_recipe || !stack_recipe.result_type) diff --git a/code/datums/components/crafting/crafting.dm b/code/datums/components/crafting/crafting.dm index dfe48688cf3..c9e07d0d76a 100644 --- a/code/datums/components/crafting/crafting.dm +++ b/code/datums/components/crafting/crafting.dm @@ -68,12 +68,17 @@ var/list/requirements_list = list() // Process all requirements - for(var/requirement_path in recipe.reqs) + var/recipe_result + if(recipe.blacklist_result) + recipe_result = recipe.result + for(var/requirement_path, needed_amount in recipe.reqs) // Check we have the appropriate amount available in the contents list - var/needed_amount = recipe.reqs[requirement_path] for(var/content_item_path in contents) // Right path and not blacklisted - if(!ispath(content_item_path, requirement_path) || recipe.blacklist.Find(content_item_path)) + if(!ispath(content_item_path, requirement_path) || (content_item_path in recipe.blacklist) || is_type_in_typecache(recipe.global_blacklist, content_item_path)) + continue + // If we are a recipe that is blacklisting its result, make sure we skip that path + if(recipe_result && content_item_path == recipe_result) continue needed_amount -= contents[content_item_path] @@ -85,14 +90,14 @@ // Store the instances of what we will use for recipe.check_requirements() for requirement_path var/list/instances_list = list() - for(var/instance_path in item_instances) + for(var/instance_path, item_instance in item_instances) if(ispath(instance_path, requirement_path)) - instances_list += item_instances[instance_path] + instances_list += item_instance requirements_list[requirement_path] = instances_list - for(var/requirement_path in recipe.chem_catalysts) - if(contents[requirement_path] < recipe.chem_catalysts[requirement_path]) + for(var/requirement_path, chem_amount in recipe.chem_catalysts) + if(contents[requirement_path] < chem_amount) return FALSE var/mech_found = FALSE @@ -245,8 +250,7 @@ var/list/total_materials = list() var/list/stuff_to_use = get_used_reqs(recipe, crafter, total_materials) - for(var/mat in recipe.removed_mats) - var/to_remove = recipe.removed_mats[mat] + for(var/mat, to_remove in recipe.removed_mats) var/datum/material/ref_mat = locate(mat) in total_materials if(!ref_mat) continue @@ -680,11 +684,11 @@ data["reqs"]["[id]"] = recipe.reqs[req_atom] // Catalysts - if(recipe.chem_catalysts.len) + if(LAZYLEN(recipe.chem_catalysts)) data["chem_catalysts"] = list() - for(var/req_atom in recipe.chem_catalysts) + for(var/req_atom, chem_amount in recipe.chem_catalysts) var/id = atoms.Find(req_atom) - data["chem_catalysts"]["[id]"] = recipe.chem_catalysts[req_atom] + data["chem_catalysts"]["[id]"] = chem_amount // Reaction data if(ispath(recipe.reaction)) diff --git a/code/datums/components/crafting/equipment.dm b/code/datums/components/crafting/equipment.dm index 16eeeff45e2..3a4744579e6 100644 --- a/code/datums/components/crafting/equipment.dm +++ b/code/datums/components/crafting/equipment.dm @@ -10,8 +10,8 @@ category = CAT_EQUIPMENT /datum/crafting_recipe/strobeshield/New() - ..() - blacklist |= subtypesof(/obj/item/shield/riot) + LAZYADD(blacklist, typecacheof(/obj/item/shield/riot, ignore_root_path = TRUE)) + return ..() /datum/crafting_recipe/improvisedshield name = "Improvised Shield" @@ -33,8 +33,19 @@ time = 4 SECONDS category = CAT_EQUIPMENT +/datum/crafting_recipe/radio_containing + abstract_type = /datum/crafting_recipe/radio_containing + /// Shared blacklist of all the radio types for anything that uses a radio in its construction, so we don't repeat it. + var/static/list/radio_types_blacklist -/datum/crafting_recipe/radiogloves +/datum/crafting_recipe/radio_containing/New() + if(isnull(radio_types_blacklist)) + // because we got shit like /obj/item/radio/off ... WHY!?! + radio_types_blacklist = typecacheof(list(/obj/item/radio/headset, /obj/item/radio/intercom)) + blacklist = radio_types_blacklist + return ..() + +/datum/crafting_recipe/radio_containing/radiogloves name = "Radio Gloves" result = /obj/item/clothing/gloves/radio time = 1.5 SECONDS @@ -46,11 +57,6 @@ tool_behaviors = list(TOOL_WIRECUTTER) category = CAT_EQUIPMENT -/datum/crafting_recipe/radiogloves/New() - ..() - blacklist |= typesof(/obj/item/radio/headset) - blacklist |= typesof(/obj/item/radio/intercom) - /datum/crafting_recipe/wheelchair name = "Wheelchair" result = /obj/vehicle/ridden/wheelchair @@ -163,8 +169,8 @@ category = CAT_EQUIPMENT /datum/crafting_recipe/flashlight_eyes/New() - . = ..() - blacklist += typesof(/obj/item/flashlight/flare) + LAZYADD(blacklist, typecacheof(/obj/item/flashlight/flare)) + return ..() /datum/crafting_recipe/extendohand_r name = "Extendo-Hand (Right Arm)" @@ -308,8 +314,8 @@ tool_behaviors = list(TOOL_WELDER, TOOL_SCREWDRIVER, TOOL_WIRECUTTER) /datum/crafting_recipe/morbid_surgical_toolset/New() - ..() - blacklist |= subtypesof(/obj/item/organ/cyberimp/arm/toolkit/surgery) + LAZYADD(blacklist, typecacheof(/obj/item/organ/cyberimp/arm/toolkit/surgery, ignore_root_path = TRUE)) + return ..() /datum/crafting_recipe/surgical_toolset name = "Surgical Toolset Implant" diff --git a/code/datums/components/crafting/melee_weapon.dm b/code/datums/components/crafting/melee_weapon.dm index 28db00ae3f3..9f0fab50964 100644 --- a/code/datums/components/crafting/melee_weapon.dm +++ b/code/datums/components/crafting/melee_weapon.dm @@ -89,7 +89,6 @@ time = 4 SECONDS category = CAT_WEAPON_MELEE - /datum/crafting_recipe/balloon_mallet name = "Balloon Mallet" result = /obj/item/balloon_mallet diff --git a/code/datums/components/crafting/ranged_weapon.dm b/code/datums/components/crafting/ranged_weapon.dm index df4313cc114..c78bf9ff708 100644 --- a/code/datums/components/crafting/ranged_weapon.dm +++ b/code/datums/components/crafting/ranged_weapon.dm @@ -67,8 +67,8 @@ category = CAT_WEAPON_RANGED /datum/crafting_recipe/advancedegun/New() - ..() - blacklist += subtypesof(/obj/item/gun/energy/e_gun) + LAZYADD(blacklist, typecacheof(/obj/item/gun/energy/e_gun, ignore_root_path = TRUE)) + return ..() /datum/crafting_recipe/tempgun name = "Temperature Gun" @@ -81,8 +81,8 @@ category = CAT_WEAPON_RANGED /datum/crafting_recipe/tempgun/New() - ..() - blacklist += subtypesof(/obj/item/gun/energy/e_gun) + LAZYADD(blacklist, typecacheof(/obj/item/gun/energy/e_gun, ignore_root_path = TRUE)) + return ..() /datum/crafting_recipe/beam_rifle name = "Event Horizon Anti-Existential Beam Rifle" @@ -108,7 +108,18 @@ time = 10 SECONDS category = CAT_WEAPON_RANGED -/datum/crafting_recipe/xraylaser +/datum/crafting_recipe/laser + abstract_type = /datum/crafting_recipe/laser + /// We will use the same blacklist for every type here to avoid repeating lists + var/static/list/laser_blacklist + +/datum/crafting_recipe/laser/New() + if(isnull(laser_blacklist)) + laser_blacklist = typecacheof(/obj/item/gun/energy/laser, ignore_root_path = TRUE) + blacklist = laser_blacklist + return ..() + +/datum/crafting_recipe/laser/xraylaser name = "X-ray Laser Gun" result = /obj/item/gun/energy/laser/xray reqs = list( @@ -118,11 +129,7 @@ time = 10 SECONDS category = CAT_WEAPON_RANGED -/datum/crafting_recipe/xraylaser/New() - ..() - blacklist += subtypesof(/obj/item/gun/energy/laser) - -/datum/crafting_recipe/hellgun +/datum/crafting_recipe/laser/hellgun name = "Hellfire Laser Gun" result = /obj/item/gun/energy/laser/hellgun reqs = list( @@ -132,11 +139,7 @@ time = 10 SECONDS category = CAT_WEAPON_RANGED -/datum/crafting_recipe/hellgun/New() - ..() - blacklist += subtypesof(/obj/item/gun/energy/laser) - -/datum/crafting_recipe/ioncarbine +/datum/crafting_recipe/laser/ioncarbine name = "Ion Carbine" result = /obj/item/gun/energy/ionrifle/carbine reqs = list( @@ -146,10 +149,6 @@ time = 10 SECONDS category = CAT_WEAPON_RANGED -/datum/crafting_recipe/ioncarbine/New() - ..() - blacklist += subtypesof(/obj/item/gun/energy/laser) - /datum/crafting_recipe/teslacannon name = "Tesla Cannon" result = /obj/item/gun/energy/tesla_cannon @@ -241,8 +240,8 @@ /obj/item/gun/ballistic/rifle/rebarxbow = 1, ) blacklist = list( - /obj/item/gun/ballistic/rifle/rebarxbow/forced, - /obj/item/gun/ballistic/rifle/rebarxbow/syndie, + /obj/item/gun/ballistic/rifle/rebarxbow/forced, + /obj/item/gun/ballistic/rifle/rebarxbow/syndie, ) tool_behaviors = list(TOOL_CROWBAR) time = 1 SECONDS @@ -289,8 +288,8 @@ crafting_flags = CRAFT_CHECK_DENSITY | CRAFT_MUST_BE_LEARNED /datum/crafting_recipe/deagle_prime/New() - ..() - blacklist += subtypesof(/obj/item/gun/ballistic/automatic/pistol) + LAZYADD(blacklist, typecacheof(/obj/item/gun/ballistic/automatic/pistol, ignore_root_path = TRUE)) + return ..() /datum/crafting_recipe/deagle_prime_mag name = "Regal Condor Magazine (10mm Reaper)" diff --git a/code/datums/components/crafting/tailoring.dm b/code/datums/components/crafting/tailoring.dm index e696dc2b44b..c0e46325c98 100644 --- a/code/datums/components/crafting/tailoring.dm +++ b/code/datums/components/crafting/tailoring.dm @@ -421,12 +421,7 @@ ) reqs = list(/obj/item/stack/sheet/cloth = 4) category = CAT_CLOTHING - -/datum/crafting_recipe/chaplain_hood/New() - . = ..() - //the resulting hoodie can be used to craft other hoodies. - //recipe blacklists should be refactored to only affect components and not tools. - blacklist -= result + blacklist_result = NEVER_BLACKLIST_RESULT //the resulting hoodie can be used to craft other hoodies. /datum/crafting_recipe/flower_garland name = "Flower Garland" diff --git a/code/datums/components/ground_sinking.dm b/code/datums/components/ground_sinking.dm index 4e846b4cf70..971cb15529d 100644 --- a/code/datums/components/ground_sinking.dm +++ b/code/datums/components/ground_sinking.dm @@ -36,7 +36,7 @@ heal_when_sinked = TRUE, health_per_second = 1, outline_colour = COLOR_PALE_GREEN, - damage_res_sinked = list(BRUTE = 1, BURN = 1, TOX = 1, STAMINA = 0, OXY = 1)) + damage_res_sinked = string_assoc_list(list(BRUTE = 1, BURN = 1, TOX = 1, STAMINA = 0, OXY = 1))) if (!isbasicmob(parent)) return COMPONENT_INCOMPATIBLE @@ -112,7 +112,7 @@ if(sinked && heal_when_sinked) stop_regenerating() living_target.icon_state = target_icon_state - living_target.damage_coeff = list(BRUTE = 1, BURN = 1, TOX = 1, STAMINA = 0, OXY = 1) + living_target.damage_coeff = string_assoc_list(list(BRUTE = 1, BURN = 1, TOX = 1, STAMINA = 0, OXY = 1)) living_target.set_density(TRUE) sinked = FALSE diff --git a/code/datums/components/soapbox.dm b/code/datums/components/soapbox.dm index 9d15e5e6929..012229cb2de 100644 --- a/code/datums/components/soapbox.dm +++ b/code/datums/components/soapbox.dm @@ -1,6 +1,6 @@ /datum/component/soapbox /// List of our current soapboxxer(s) who are gaining loud speech - var/list/soapboxers = list() + var/list/soapboxers /// Gives atoms moving over us the soapbox speech and takes it away when they leave var/static/list/loc_connections = list( COMSIG_ATOM_ENTERED = PROC_REF(on_loc_entered), @@ -21,21 +21,21 @@ if(QDELETED(soapbox_arrive)) return RegisterSignal(soapbox_arrive, COMSIG_MOB_SAY, PROC_REF(soapbox_speech)) - soapboxers += soapbox_arrive + LAZYADD(soapboxers, soapbox_arrive) ///Takes away loud speech from our movable when it leaves the turf our parent is on /datum/component/soapbox/proc/on_loc_exited(datum/source, mob/living/soapbox_leave) SIGNAL_HANDLER if(soapbox_leave in soapboxers) UnregisterSignal(soapbox_leave, COMSIG_MOB_SAY) - soapboxers -= soapbox_leave + LAZYREMOVE(soapboxers, soapbox_leave) ///We don't want our soapboxxer to keep their loud say if the parent is moved out from under them /datum/component/soapbox/proc/parent_moved(datum/source) SIGNAL_HANDLER for(var/atom/movable/loud as anything in soapboxers) UnregisterSignal(loud, COMSIG_MOB_SAY) - soapboxers.Cut() + LAZYNULL(soapboxers) ///Gives a mob a unique say span /datum/component/soapbox/proc/soapbox_speech(datum/source, list/speech_args) diff --git a/code/datums/dna/dna.dm b/code/datums/dna/dna.dm index 6b0ef3fc1c8..b0cd64e4bef 100644 --- a/code/datums/dna/dna.dm +++ b/code/datums/dna/dna.dm @@ -43,11 +43,11 @@ GLOBAL_LIST_INIT(total_uf_len_by_block, populate_total_uf_len_by_block()) ///Stores the real name of the person who originally got this dna datum. Used primarily for changelings var/real_name ///All mutations are from now on here - var/list/mutations = list() + var/list/mutations ///Temporary changes to the UE - var/list/temporary_mutations = list() + var/list/temporary_mutations ///For temporary name/ui/ue/blood_type modifications - var/list/previous = list() + var/list/previous var/mob/living/holder ///List of which mutations this carbon has and its assigned block var/mutation_index[DNA_MUTATION_BLOCKS] @@ -76,9 +76,9 @@ GLOBAL_LIST_INIT(total_uf_len_by_block, populate_total_uf_len_by_block()) QDEL_NULL(species) - mutations.Cut() //This only references mutations, just dereference. - temporary_mutations.Cut() //^ - previous.Cut() //^ + LAZYNULL(mutations) //This only references mutations, just dereference. + LAZYNULL(temporary_mutations) //^ + LAZYNULL(previous) //^ return ..() @@ -89,7 +89,7 @@ GLOBAL_LIST_INIT(total_uf_len_by_block, populate_total_uf_len_by_block()) new_dna.unique_features = unique_features new_dna.features = features.Copy() new_dna.real_name = real_name - new_dna.temporary_mutations = temporary_mutations.Copy() + new_dna.temporary_mutations = LAZYLISTDUPLICATE(temporary_mutations) new_dna.mutation_index = mutation_index new_dna.default_mutation_genes = default_mutation_genes //if the new DNA has a holder, transform them immediately, otherwise save it diff --git a/code/datums/dog_fashion.dm b/code/datums/dog_fashion.dm index 817529ce9d7..1c27df60822 100644 --- a/code/datums/dog_fashion.dm +++ b/code/datums/dog_fashion.dm @@ -4,13 +4,13 @@ ///Description modifier for the dog that we're dressing up var/desc = null ///Hearable emotes modifier for the dog that we're dressing up - var/list/emote_hear = list() + var/list/emote_hear ///Visible emotes modifier for the dog that we're dressing up - var/list/emote_see = list() + var/list/emote_see ///Speech modifier for the dog that we're dressing up - var/list/speak = list() + var/list/speak ///Speech verb modifier for the dog that we're dressing up - var/list/speak_emote = list() + var/list/speak_emote // This isn't applied to the dog, but stores the icon_state of the // sprite that the associated item uses @@ -41,16 +41,16 @@ dressup_doggy.name = name if(desc) dressup_doggy.desc = desc - if(length(speak_emote)) + if(LAZYLEN(speak_emote)) dressup_doggy.speak_emote = string_list(speak_emote) ///Applies random speech modifiers to the dog /datum/dog_fashion/proc/apply_to_speech(datum/ai_planning_subtree/random_speech/speech) - if(length(emote_see)) + if(LAZYLEN(emote_see)) speech.emote_see = string_list(emote_see) - if(length(emote_hear)) + if(LAZYLEN(emote_hear)) speech.emote_hear = string_list(emote_hear) - if(length(speak)) + if(LAZYLEN(speak)) speech.speak = string_list(speak) /** @@ -237,7 +237,7 @@ name = "Butter %REAL_NAME%" desc = "%NAME%. %CAPITAL_REAL_NAME% with the butter. %NAME%. %CAPITAL_REAL_NAME% with a butter on 'em." obj_icon_state = "butter" - speak = list() //they're very patient and focused on holding the butter on 'em + speak = null //they're very patient and focused on holding the butter on 'em emote_see = list("shakes a little.", "looks around.") emote_hear = list("licks a trickle of the butter up.", "smiles.") diff --git a/code/datums/embedding.dm b/code/datums/embedding.dm index 1c876468350..77fec4f8746 100644 --- a/code/datums/embedding.dm +++ b/code/datums/embedding.dm @@ -420,7 +420,7 @@ if (user.zone_selected != owner_limb.body_zone || (tool.tool_behaviour != TOOL_HEMOSTAT && tool.tool_behaviour != TOOL_WIRECUTTER)) return - if (parent != owner_limb.embedded_objects[1]) // Don't pluck everything at the same time + if (parent != LAZYACCESS(owner_limb.embedded_objects, 1)) // Don't pluck everything at the same time return // Ensure that we can actually diff --git a/code/datums/mutations/_mutations.dm b/code/datums/mutations/_mutations.dm index a9641a4795e..9055c7b458e 100644 --- a/code/datums/mutations/_mutations.dm +++ b/code/datums/mutations/_mutations.dm @@ -129,7 +129,7 @@ return FALSE owner = acquirer dna = acquirer.dna - dna.mutations += src + LAZYADD(dna.mutations, src) SEND_SIGNAL(src, COMSIG_MUTATION_GAINED, acquirer) if(text_gain_indication) to_chat(owner, text_gain_indication) @@ -153,7 +153,7 @@ return /datum/mutation/proc/on_losing(mob/living/carbon/human/owner) - if(!istype(owner) || !(owner.dna.mutations.Remove(src))) + if(!istype(owner) || !(owner.dna.mutations?.Remove(src))) return TRUE . = FALSE SEND_SIGNAL(src, COMSIG_MUTATION_LOST, owner) diff --git a/code/datums/storage/storage.dm b/code/datums/storage/storage.dm index 41b7a61949f..cbb36a9662e 100644 --- a/code/datums/storage/storage.dm +++ b/code/datums/storage/storage.dm @@ -21,12 +21,12 @@ VAR_FINAL/atom/real_location /// List of all the mobs currently viewing the contents of this storage. - VAR_PRIVATE/list/mob/is_using = list() + VAR_PRIVATE/list/mob/is_using ///The type of storage interface this datum uses. var/datum/storage_interface/storage_type = /datum/storage_interface /// Associated list that keeps track of all storage UI datums per person. - VAR_PRIVATE/list/datum/storage_interface/storage_interfaces = null + VAR_PRIVATE/list/datum/storage_interface/storage_interfaces /// Typecache of items that can be inserted into this storage. /// By default, all item types can be inserted (assuming other conditions are met). @@ -158,7 +158,7 @@ for(var/mob/person as anything in is_using) hide_contents(person) - is_using.Cut() + LAZYNULL(is_using) QDEL_LIST_ASSOC_VAL(storage_interfaces) parent = null @@ -1084,7 +1084,7 @@ GLOBAL_LIST_EMPTY(cached_storage_typecaches) orient_storage() - is_using |= to_show + LAZYOR(is_using, to_show) to_show.hud_used.open_containers |= storage_interfaces[to_show].list_ui_elements() to_show.client.screen |= storage_interfaces[to_show].list_ui_elements() @@ -1103,14 +1103,14 @@ GLOBAL_LIST_EMPTY(cached_storage_typecaches) if(to_hide.active_storage == src) to_hide.active_storage = null - if(!length(is_using) && ismovable(real_location)) + if(!LAZYLEN(is_using) && ismovable(real_location)) var/atom/movable/movable_loc = real_location movable_loc.lose_active_storage(src) - if (!length(storage_interfaces) || isnull(storage_interfaces[to_hide])) + if (!LAZYLEN(storage_interfaces) || isnull(storage_interfaces[to_hide])) return TRUE - is_using -= to_hide + LAZYREMOVE(is_using, to_hide) if(to_hide.client) to_hide.client.screen -= storage_interfaces[to_hide].list_ui_elements() diff --git a/code/game/atom/_atom.dm b/code/game/atom/_atom.dm index 2519189fdec..a015ea68961 100644 --- a/code/game/atom/_atom.dm +++ b/code/game/atom/_atom.dm @@ -346,8 +346,8 @@ /atom/proc/on_craft_completion(list/components, datum/crafting_recipe/current_recipe, atom/crafter) SHOULD_CALL_PARENT(TRUE) SEND_SIGNAL(src, COMSIG_ATOM_ON_CRAFT, components, current_recipe) - var/list/remaining_parts = current_recipe?.parts?.Copy() - var/list/parts_by_type = remaining_parts?.Copy() + var/list/remaining_parts = LAZYLISTDUPLICATE(current_recipe?.parts) + var/list/parts_by_type = LAZYLISTDUPLICATE(remaining_parts) for(var/parttype in parts_by_type) //necessary for our is_type_in_list() call with the zebra arg set to true parts_by_type[parttype] = parttype for(var/atom/movable/movable as anything in components) // machinery or structure objects in the list are guaranteed to be used up. We only check items. diff --git a/code/game/atom/atoms_initializing_EXPENSIVE.dm b/code/game/atom/atoms_initializing_EXPENSIVE.dm index 7b0965beabb..f39b987990d 100644 --- a/code/game/atom/atoms_initializing_EXPENSIVE.dm +++ b/code/game/atom/atoms_initializing_EXPENSIVE.dm @@ -122,6 +122,9 @@ SET_PLANE_IMPLICIT(src, plane) + if(LAZYLEN(hud_possible)) + hud_possible = string_assoc_list(hud_possible) + if(greyscale_config && greyscale_colors) //we'll check again at item/init for inhand/belt/worn configs. update_greyscale() diff --git a/code/game/objects/items/cards_ids.dm b/code/game/objects/items/cards_ids.dm index e5a32b706bd..1cfa8977ea8 100644 --- a/code/game/objects/items/cards_ids.dm +++ b/code/game/objects/items/cards_ids.dm @@ -165,7 +165,7 @@ /obj/item/card/id/Destroy() if (registered_account) - registered_account.bank_cards -= src + LAZYREMOVE(registered_account.bank_cards, src) if (my_store) QDEL_NULL(my_store) if (isitem(loc)) @@ -768,9 +768,9 @@ to_chat(user, span_warning("The account ID number provided is invalid.")) return FALSE if(old_account) - old_account.bank_cards -= src + LAZYREMOVE(old_account.bank_cards, src) account.account_balance += old_account.account_balance - account.bank_cards += src + LAZYADD(account.bank_cards, src) registered_account = account to_chat(user, span_notice("The provided account has been linked to this ID card. It contains [account.account_balance] [MONEY_NAME].")) return TRUE @@ -1095,11 +1095,10 @@ /obj/item/card/id/departmental_budget/Initialize(mapload) . = ..() - var/datum/bank_account/B = SSeconomy.get_dep_account(department_ID) - if(B) - registered_account = B - if(!B.bank_cards.Find(src)) - B.bank_cards += src + var/datum/bank_account/department_account = SSeconomy.get_dep_account(department_ID) + if(department_account) + registered_account = department_account + LAZYOR(department_account.bank_cards, src) name = "departmental card ([department_name])" desc = "Provides access to the [department_name]." SSeconomy.dep_cards += src @@ -1972,7 +1971,7 @@ var/datum/bank_account/account = SSeconomy.bank_accounts_by_id["[owner.account_id]"] if(account) - account.bank_cards += src + LAZYADD(account.bank_cards, src) registered_account = account to_chat(user, span_notice("Your account number has been automatically assigned.")) diff --git a/code/game/objects/items/devices/scanners/autopsy_scanner.dm b/code/game/objects/items/devices/scanners/autopsy_scanner.dm index 40835bc7920..61bc6c4d262 100644 --- a/code/game/objects/items/devices/scanners/autopsy_scanner.dm +++ b/code/game/objects/items/devices/scanners/autopsy_scanner.dm @@ -91,7 +91,7 @@ dmgreport += "" dmgreport += "↳ Physical trauma: Dismembered" continue - var/has_any_embeds = length(limb.embedded_objects) >= 1 + var/has_any_embeds = LAZYLEN(limb.embedded_objects) >= 1 var/has_any_wounds = length(limb.wounds) >= 1 dmgreport += "" dmgreport += "[capitalize(limb.name)]:" diff --git a/code/game/objects/items/devices/scanners/health_analyzer.dm b/code/game/objects/items/devices/scanners/health_analyzer.dm index c70ce933df4..56fab997cf7 100644 --- a/code/game/objects/items/devices/scanners/health_analyzer.dm +++ b/code/game/objects/items/devices/scanners/health_analyzer.dm @@ -252,7 +252,7 @@ dmgreport += "" dmgreport += "↳ Physical trauma: [conditional_tooltip("Dismembered", "Reattach or replace surgically.", tochat)]" continue - var/has_any_embeds = length(limb.embedded_objects) >= 1 + var/has_any_embeds = LAZYLEN(limb.embedded_objects) >= 1 var/has_any_wounds = length(limb.wounds) >= 1 var/is_damaged = limb.burn_dam > 0 || limb.brute_dam > 0 if(!is_damaged && (zone != BODY_ZONE_CHEST || (tox_loss <= 0 && oxy_loss <= 0)) && !has_any_embeds && !has_any_wounds) diff --git a/code/game/objects/items/dna_injector.dm b/code/game/objects/items/dna_injector.dm index 09cc0a9b2cc..baf4bb85e62 100644 --- a/code/game/objects/items/dna_injector.dm +++ b/code/game/objects/items/dna_injector.dm @@ -120,6 +120,7 @@ addtimer(CALLBACK(target.dna, TYPE_PROC_REF(/datum/dna, remove_mutation), mutation, MUTATION_SOURCE_TIMED_INJECTOR), duration) if(fields) if(fields["name"] && fields["UE"] && fields["blood_type"]) + LAZYINITLIST(target.dna.previous) if(!target.dna.previous["name"]) target.dna.previous["name"] = target.real_name if(!target.dna.previous["UE"]) @@ -130,17 +131,19 @@ target.dna.unique_enzymes = fields["UE"] target.name = target.real_name target.set_blood_type(fields["blood_type"]) - target.dna.temporary_mutations[UE_CHANGED] = endtime + LAZYSET(target.dna.temporary_mutations, UE_CHANGED, endtime) if(fields["UI"]) //UI+UE + LAZYINITLIST(target.dna.previous) if(!target.dna.previous["UI"]) target.dna.previous["UI"] = target.dna.unique_identity target.dna.unique_identity = merge_text(target.dna.unique_identity, fields["UI"]) - target.dna.temporary_mutations[UI_CHANGED] = endtime + LAZYSET(target.dna.temporary_mutations, UI_CHANGED, endtime) if(fields["UF"]) //UI+UE + LAZYINITLIST(target.dna.previous) if(!target.dna.previous["UF"]) target.dna.previous["UF"] = target.dna.unique_features target.dna.unique_features = merge_text(target.dna.unique_features, fields["UF"]) - target.dna.temporary_mutations[UF_CHANGED] = endtime + LAZYSET(target.dna.temporary_mutations, UF_CHANGED, endtime) if(fields["UI"] || fields["UF"]) target.updateappearance(mutcolor_update = TRUE, mutations_overlay_update = TRUE) return TRUE diff --git a/code/modules/cargo/markets/market_uplink.dm b/code/modules/cargo/markets/market_uplink.dm index 5585f434c23..d727453da15 100644 --- a/code/modules/cargo/markets/market_uplink.dm +++ b/code/modules/cargo/markets/market_uplink.dm @@ -162,7 +162,7 @@ . = ..() ADD_TRAIT(src, TRAIT_CONTRABAND, INNATE_TRAIT) -/datum/crafting_recipe/blackmarket_uplink +/datum/crafting_recipe/radio_containing/blackmarket_uplink name = "Black Market Uplink" result = /obj/item/market_uplink/blackmarket time = 3 SECONDS @@ -175,8 +175,3 @@ /obj/item/analyzer = 1 ) category = CAT_EQUIPMENT - -/datum/crafting_recipe/blackmarket_uplink/New() - ..() - blacklist |= typesof(/obj/item/radio/headset) // because we got shit like /obj/item/radio/off ... WHY!?! - blacklist |= typesof(/obj/item/radio/intercom) diff --git a/code/modules/clothing/chameleon/generic_chameleon_clothing.dm b/code/modules/clothing/chameleon/generic_chameleon_clothing.dm index 2cd2da4ed67..5c9aed76919 100644 --- a/code/modules/clothing/chameleon/generic_chameleon_clothing.dm +++ b/code/modules/clothing/chameleon/generic_chameleon_clothing.dm @@ -193,12 +193,13 @@ do { \ clothing_traits = list(TRAIT_VOICE_MATCHES_ID) /obj/item/clothing/mask/chameleon/attack_self(mob/user) - var/was_on = (TRAIT_VOICE_MATCHES_ID in clothing_traits) - if(was_on) - attach_clothing_traits(TRAIT_VOICE_MATCHES_ID) - else + var/on = (TRAIT_VOICE_MATCHES_ID in clothing_traits) + if(on) detach_clothing_traits(TRAIT_VOICE_MATCHES_ID) - to_chat(user, span_notice("The voice changer is now [was_on ? "off" : "on"]!")) + else + attach_clothing_traits(TRAIT_VOICE_MATCHES_ID) + on = !on + to_chat(user, span_notice("The voice changer is now [on ? "on" : "off"]!")) /obj/item/clothing/mask/chameleon/broken diff --git a/code/modules/clothing/clothing.dm b/code/modules/clothing/clothing.dm index 1f2177a72e6..ccec75931e5 100644 --- a/code/modules/clothing/clothing.dm +++ b/code/modules/clothing/clothing.dm @@ -64,6 +64,8 @@ /obj/item/clothing/Initialize(mapload) if(clothing_flags & VOICEBOX_TOGGLABLE) actions_types += list(/datum/action/item_action/toggle_voice_box) + if(LAZYLEN(clothing_traits)) + clothing_traits = string_list(clothing_traits) . = ..() AddElement(/datum/element/venue_price, FOOD_PRICE_CHEAP) if(can_be_bloody && ((body_parts_covered & FEET) || (flags_inv & HIDESHOES))) @@ -286,7 +288,11 @@ if(!islist(trait_or_traits)) trait_or_traits = list(trait_or_traits) + // Use a temporary list so we don't mutate the cached version + clothing_traits = LAZYLISTDUPLICATE(clothing_traits) LAZYOR(clothing_traits, trait_or_traits) + if(clothing_traits) // because we might be null + clothing_traits = string_list(clothing_traits) var/mob/wearer = loc if(istype(wearer) && (wearer.get_slot_by_item(src) & slot_flags)) for(var/new_trait in trait_or_traits) @@ -303,7 +309,11 @@ if(!islist(trait_or_traits)) trait_or_traits = list(trait_or_traits) + // Use a temporary list so we don't mutate the cached version + clothing_traits = LAZYLISTDUPLICATE(clothing_traits) LAZYREMOVE(clothing_traits, trait_or_traits) + if(clothing_traits) // because we might be null + clothing_traits = string_list(clothing_traits) var/mob/wearer = loc if(istype(wearer)) for(var/new_trait in trait_or_traits) diff --git a/code/modules/clothing/glasses/hud.dm b/code/modules/clothing/glasses/hud.dm index 3887807503c..003cbf4850a 100644 --- a/code/modules/clothing/glasses/hud.dm +++ b/code/modules/clothing/glasses/hud.dm @@ -270,7 +270,7 @@ /obj/item/clothing/glasses/hud/toggle/thermal/attack_self(mob/user) ..() var/hud_type - if (!isnull(clothing_traits) && clothing_traits.len) + if (LAZYLEN(clothing_traits)) hud_type = clothing_traits[1] switch (hud_type) if (TRAIT_MEDICAL_HUD) diff --git a/code/modules/clothing/gloves/color.dm b/code/modules/clothing/gloves/color.dm index b9f82135c47..bcaa124e487 100644 --- a/code/modules/clothing/gloves/color.dm +++ b/code/modules/clothing/gloves/color.dm @@ -12,7 +12,7 @@ /obj/item/clothing/gloves/color/black/Initialize(mapload) . = ..() - var/static/list/slapcraft_recipe_list = list(/datum/crafting_recipe/radiogloves) + var/static/list/slapcraft_recipe_list = list(/datum/crafting_recipe/radio_containing/radiogloves) AddElement( /datum/element/slapcrafting,\ diff --git a/code/modules/economy/account.dm b/code/modules/economy/account.dm index a7bdc7bf93c..60cafe30a1b 100644 --- a/code/modules/economy/account.dm +++ b/code/modules/economy/account.dm @@ -16,7 +16,7 @@ ///The job datum of the account owner. var/datum/job/account_job ///List of the physical ID card objects that are associated with this bank_account - var/list/bank_cards = list() + var/list/bank_cards ///Should this ID be added to the global list of accounts? If true, will be subject to station-bound economy effects as well as income. var/add_to_accounts = TRUE ///The Unique ID number code associated with the owner's bank account, assigned at round start. @@ -34,7 +34,7 @@ ///A special semi-tandom token for tranfering money from NT pay app var/pay_token ///List with a transaction history for NT pay app - var/list/transaction_history = list() + var/list/transaction_history ///A lazylist of coupons redeemed with the Coupon Master pda app associated with this account. var/list/redeemed_coupons /// How many paychecks to skip when payday is called. @@ -232,7 +232,7 @@ * * force - if TRUE ignore checks on client and client prefernces. */ /datum/bank_account/proc/bank_card_talk(message, force) - if(!message || !bank_cards.len) + if(!message || !LAZYLEN(bank_cards)) return for(var/obj/card in bank_cards) var/icon_source = card @@ -344,12 +344,12 @@ * * reason - The reason of interact with balance, for example, "Bought chips" or "Payday". */ /datum/bank_account/proc/add_log_to_history(adjusted_money, reason) - if(transaction_history.len >= 20) + if(LAZYLEN(transaction_history) >= 20) transaction_history.Cut(1,2) - transaction_history += list(list( + LAZYADD(transaction_history, list(list( "adjusted_money" = adjusted_money, "reason" = reason, - )) + ))) #undef DUMPTIME diff --git a/code/modules/experisci/experiment/experiments.dm b/code/modules/experisci/experiment/experiments.dm index 01fa0e88dba..48f0c712c73 100644 --- a/code/modules/experisci/experiment/experiments.dm +++ b/code/modules/experisci/experiment/experiments.dm @@ -348,7 +348,7 @@ . = ..() if (!.) return - if(!check.dna.mutations.len) + if(!LAZYLEN(check.dna.mutations)) return FALSE return TRUE diff --git a/code/modules/food_and_drinks/recipes/tablecraft/recipes_guide.dm b/code/modules/food_and_drinks/recipes/tablecraft/recipes_guide.dm index 3482dec940c..62e4add9f62 100644 --- a/code/modules/food_and_drinks/recipes/tablecraft/recipes_guide.dm +++ b/code/modules/food_and_drinks/recipes/tablecraft/recipes_guide.dm @@ -52,7 +52,7 @@ */ /datum/crafting_recipe/food/reaction/proc/setup_chemical_reaction_details(datum/chemical_reaction/chemical_reaction) reqs = chemical_reaction.required_reagents?.Copy() - chem_catalysts = chemical_reaction.required_catalysts?.Copy() + chem_catalysts = LAZYLISTDUPLICATE(chemical_reaction.required_catalysts) if(isnull(result) && length(chemical_reaction.results)) result = chemical_reaction.results[1] result_amount = chemical_reaction.results[result] diff --git a/code/modules/jobs/job_types/_job.dm b/code/modules/jobs/job_types/_job.dm index 39f2600e29f..721c0671952 100644 --- a/code/modules/jobs/job_types/_job.dm +++ b/code/modules/jobs/job_types/_job.dm @@ -406,7 +406,7 @@ if(account && account.account_id == equipped.account_id) card.registered_account = account - account.bank_cards += card + LAZYADD(account.bank_cards, card) equipped.update_ID_card() diff --git a/code/modules/jobs/job_types/station_trait/cargo_gorilla.dm b/code/modules/jobs/job_types/station_trait/cargo_gorilla.dm index 9fe2cccc934..bbc50389381 100644 --- a/code/modules/jobs/job_types/station_trait/cargo_gorilla.dm +++ b/code/modules/jobs/job_types/station_trait/cargo_gorilla.dm @@ -41,7 +41,7 @@ gorilla_id.registered_name = spawned.name gorilla_id.update_label() gorilla_id.registered_account = bank_account - bank_account.bank_cards += gorilla_id + LAZYADD(bank_account.bank_cards, gorilla_id) spawned.put_in_hands(gorilla_id, del_on_fail = TRUE) to_chat(spawned, span_boldnotice("You are Cargorilla, a pacifist friend of the station and carrier of freight.")) diff --git a/code/modules/mob/dead/new_player/new_player.dm b/code/modules/mob/dead/new_player/new_player.dm index 5050974e122..4a6c6a3585c 100644 --- a/code/modules/mob/dead/new_player/new_player.dm +++ b/code/modules/mob/dead/new_player/new_player.dm @@ -6,7 +6,6 @@ density = FALSE stat = DEAD hud_type = /datum/hud/new_player - hud_possible = list() /// String Values tied to Defines that state whether the new_player is ready to play or not. /// Do try your best to compare this value directly against the defines for certainty but helper procs do exist in bulkier situations. diff --git a/code/modules/mob/living/basic/basic.dm b/code/modules/mob/living/basic/basic.dm index 06eba0ac141..0965a5cc5ab 100644 --- a/code/modules/mob/living/basic/basic.dm +++ b/code/modules/mob/living/basic/basic.dm @@ -51,7 +51,7 @@ var/list/damage_coeff = list(BRUTE = 1, BURN = 1, TOX = 1, STAMINA = 1, OXY = 1) ///Verbs used for speaking e.g. "Says" or "Chitters". This can be elementized - var/list/speak_emote = list() + var/list/speak_emote ///When someone interacts with the simple animal. ///Help-intent verb in present continuous tense. @@ -120,8 +120,9 @@ apply_target_randomisation() make_stamina_slowable() - if(speak_emote) + if(LAZYLEN(speak_emote)) speak_emote = string_list(speak_emote) + damage_coeff = string_assoc_list(damage_coeff) ///We need to wait for SSair to be initialized before we can check atmos/temp requirements. if(PERFORM_ALL_TESTS(focus_only/atmos_and_temp_requirements) && mapload && !SSair.initialized) diff --git a/code/modules/mob/living/basic/bots/cleanbot/cleanbot.dm b/code/modules/mob/living/basic/bots/cleanbot/cleanbot.dm index d52b70575c5..64f0b2cfd6a 100644 --- a/code/modules/mob/living/basic/bots/cleanbot/cleanbot.dm +++ b/code/modules/mob/living/basic/bots/cleanbot/cleanbot.dm @@ -161,9 +161,9 @@ /mob/living/basic/bot/cleanbot/Entered(atom/movable/arrived, atom/old_loc, list/atom/old_locs) . = ..() - if(istype(arrived, /obj/item/reagent_containers/cup/bucket) && isnull(build_bucket)) + if(istype(arrived, /obj/item/reagent_containers/cup/bucket)) + QDEL_NULL(build_bucket) build_bucket = arrived - return if(istype(arrived, /obj/item/mop) && isnull(our_mop)) our_mop = arrived @@ -208,7 +208,7 @@ /mob/living/basic/bot/cleanbot/explode() var/atom/drop_loc = drop_location() - build_bucket.forceMove(drop_loc) + build_bucket?.forceMove(drop_loc) new /obj/item/assembly/prox_sensor(drop_loc) if(weapon) weapon.force = initial(weapon.force) @@ -256,11 +256,6 @@ GLOB.janitor_devices -= src return ..() -/mob/living/basic/bot/cleanbot/proc/apply_custom_bucket(obj/item/custom_bucket) - if(!isnull(build_bucket)) - QDEL_NULL(build_bucket) - custom_bucket.forceMove(src) - /mob/living/basic/bot/cleanbot/proc/on_attack_by(datum/source, obj/item/used_item, mob/living/user) SIGNAL_HANDLER if(!istype(used_item, /obj/item/knife) || user.combat_mode) diff --git a/code/modules/mob/living/basic/guardian/guardian_types/protector.dm b/code/modules/mob/living/basic/guardian/guardian_types/protector.dm index 2205eaf10d1..45d746b2335 100644 --- a/code/modules/mob/living/basic/guardian/guardian_types/protector.dm +++ b/code/modules/mob/living/basic/guardian/guardian_types/protector.dm @@ -71,7 +71,9 @@ /// Overlay for our protection shield. var/mutable_appearance/shield_overlay /// Damage coefficients when shielded - var/list/shielded_damage = list(BRUTE = 0.05, BURN = 0.05, TOX = 0.05, STAMINA = 0, OXY = 0.05) + var/static/list/shielded_damage = list(BRUTE = 0.05, BURN = 0.05, TOX = 0.05, STAMINA = 0, OXY = 0.05) + // What the damage coefficients were previously + var/list/original_damage_coeff /datum/status_effect/protector_shield/on_apply() if (isguardian(owner)) @@ -86,6 +88,7 @@ if (isbasicmob(owner)) // Better hope you are or this status is doing basically nothing useful for you var/mob/living/basic/basic_owner = owner + original_damage_coeff = basic_owner.damage_coeff basic_owner.damage_coeff = shielded_damage to_chat(owner, span_bolddanger("You enter protection mode.")) @@ -101,7 +104,7 @@ if (isbasicmob(owner)) var/mob/living/basic/basic_owner = owner - basic_owner.damage_coeff = initial(basic_owner.damage_coeff) + basic_owner.damage_coeff = original_damage_coeff to_chat(owner, span_bolddanger("You return to your normal mode.")) UnregisterSignal(owner, list(COMSIG_ATOM_UPDATE_OVERLAYS) + COMSIG_LIVING_ADJUST_STANDARD_DAMAGE_TYPES) diff --git a/code/modules/mob/living/basic/ruin_defender/mimic/mimic_ai.dm b/code/modules/mob/living/basic/ruin_defender/mimic/mimic_ai.dm index f4f329b1505..e1b664e852a 100644 --- a/code/modules/mob/living/basic/ruin_defender/mimic/mimic_ai.dm +++ b/code/modules/mob/living/basic/ruin_defender/mimic/mimic_ai.dm @@ -50,7 +50,7 @@ /datum/ai_planning_subtree/random_speech/when_has_target/mimic_machine speech_chance = 7 - emote_hear = list() + emote_hear = null speak = list( "HUMANS ARE IMPERFECT!", "YOU SHALL BE ASSIMILATED!", diff --git a/code/modules/mob/living/carbon/life.dm b/code/modules/mob/living/carbon/life.dm index 35e96354d99..45b4142ed4b 100644 --- a/code/modules/mob/living/carbon/life.dm +++ b/code/modules/mob/living/carbon/life.dm @@ -530,24 +530,26 @@ disease.stage_act(seconds_per_tick) /mob/living/carbon/handle_mutations(time_since_irradiated, seconds_per_tick) - if(!dna?.temporary_mutations.len) + if(!LAZYLEN(dna?.temporary_mutations)) return - for(var/mut in dna.temporary_mutations) - if(dna.temporary_mutations[mut] < world.time) + for(var/mut, mut_data in dna.temporary_mutations) + if(mut_data < world.time) + if(!LAZYLEN(dna.previous)) + continue if(mut == UI_CHANGED) if(dna.previous["UI"]) dna.unique_identity = merge_text(dna.unique_identity,dna.previous["UI"]) updateappearance(mutations_overlay_update=1) dna.previous.Remove("UI") - dna.temporary_mutations.Remove(mut) + LAZYREMOVE(dna.temporary_mutations, mut) continue if(mut == UF_CHANGED) if(dna.previous["UF"]) dna.unique_features = merge_text(dna.unique_features,dna.previous["UF"]) updateappearance(mutcolor_update=1, mutations_overlay_update=1) dna.previous.Remove("UF") - dna.temporary_mutations.Remove(mut) + LAZYREMOVE(dna.temporary_mutations, mut) continue if(mut == UE_CHANGED) if(dna.previous["name"]) @@ -560,7 +562,7 @@ if(dna.previous["blood_type"]) set_blood_type(dna.previous["blood_type"]) dna.previous.Remove("blood_type") - dna.temporary_mutations.Remove(mut) + LAZYREMOVE(dna.temporary_mutations, mut) continue /** diff --git a/code/modules/mob/living/simple_animal/bot/construction.dm b/code/modules/mob/living/simple_animal/bot/construction.dm index 11953281a2b..e55c94b73d5 100644 --- a/code/modules/mob/living/simple_animal/bot/construction.dm +++ b/code/modules/mob/living/simple_animal/bot/construction.dm @@ -74,7 +74,7 @@ if(!can_finish_build(item_attached, user)) return var/mob/living/basic/bot/cleanbot/bot = new(drop_location()) - bot.apply_custom_bucket(bucket_obj) + bucket_obj.forceMove(bot) bot.name = created_name bot.robot_arm = item_attached.type to_chat(user, span_notice("You add [item_attached] to [src]. Beep boop!")) diff --git a/code/modules/mob/living/simple_animal/hostile/hostile.dm b/code/modules/mob/living/simple_animal/hostile/hostile.dm index c3d14859d4f..1974c078bac 100644 --- a/code/modules/mob/living/simple_animal/hostile/hostile.dm +++ b/code/modules/mob/living/simple_animal/hostile/hostile.dm @@ -73,8 +73,6 @@ var/search_objects_timer_id ///The delay between being attacked and gaining our old search_objects value back var/search_objects_regain_time = 3 SECONDS - ///A typecache of objects types that will be checked against to attack, should we have search_objects enabled - var/list/wanted_objects = list() ///Mobs ignore mob/living targets with a stat lower than that of stat_attack. If set to DEAD, then they'll include corpses in their targets, if to HARD_CRIT they'll keep attacking until they kill, and so on. var/stat_attack = CONSCIOUS ///Mobs with this set to TRUE will exclusively attack things defined by stat_attack, stat_attack DEAD means they will only attack corpses @@ -86,17 +84,11 @@ //Attempting to call GET_TARGETS_FROM(mob) when this var is null will just return mob as a base ///all range/attack/etc. calculations should be done from the atom this weakrefs, useful for Vehicles and such. var/datum/weakref/targets_from - ///if true, equivalent to having a wanted_objects list containing ALL objects. - var/attack_all_objects = FALSE ///id for a timer to call LoseTarget(), used to stop mobs fixating on a target they can't reach var/lose_patience_timer_id ///30 seconds by default, so there's no major changes to AI behaviour, beyond actually bailing if stuck forever var/lose_patience_timeout = 30 SECONDS -/mob/living/simple_animal/hostile/Initialize(mapload) - . = ..() - wanted_objects = typecacheof(wanted_objects) - /mob/living/simple_animal/hostile/Destroy() //We can't use losetarget here because fucking cursed blobs override it to do nothing the motherfuckers GiveTarget(null) @@ -295,10 +287,6 @@ return FALSE return TRUE - if(isobj(the_target)) - if(attack_all_objects || is_type_in_typecache(the_target, wanted_objects)) - return TRUE - return FALSE /mob/living/simple_animal/hostile/proc/GiveTarget(new_target)//Step 4, give us our selected target diff --git a/code/modules/mob/living/simple_animal/simple_animal.dm b/code/modules/mob/living/simple_animal/simple_animal.dm index 684ac23e122..e92563748c2 100644 --- a/code/modules/mob/living/simple_animal/simple_animal.dm +++ b/code/modules/mob/living/simple_animal/simple_animal.dm @@ -17,14 +17,14 @@ ///Flip the sprite upside down on death. Mostly here for things lacking custom dead sprites. var/flip_on_death = FALSE - var/list/speak = list() + var/list/speak ///Emotes while speaking IE: `Ian [emote], [text]` -- `Ian barks, "WOOF!".` Spoken text is generated from the speak variable. - var/list/speak_emote = list() + var/list/speak_emote var/speak_chance = 0 ///Hearable emotes - var/list/emote_hear = list() + var/list/emote_hear ///Unlike speak_emote, the list of things in this variable only show by themselves with no spoken text. IE: Ian barks, Ian yaps - var/list/emote_see = list() + var/list/emote_see ///ticks up every time `handle_automated_movement()` is called, which is every 2 seconds at the time of documenting. 1 turns per move is 1 movement every 2 seconds. var/turns_per_move = 1 @@ -177,16 +177,15 @@ add_traits(weather_immunities, ROUNDSTART_TRAIT) if (environment_smash >= ENVIRONMENT_SMASH_WALLS) AddElement(/datum/element/wall_smasher, strength_flag = environment_smash) - if(speak) + if(LAZYLEN(speak)) speak = string_list(speak) - if(speak_emote) + if(LAZYLEN(speak_emote)) speak_emote = string_list(speak_emote) - if(emote_hear) + if(LAZYLEN(emote_hear)) emote_hear = string_list(emote_hear) - if(emote_see) - emote_see = string_list(emote_hear) - if(damage_coeff) - damage_coeff = string_assoc_list(damage_coeff) + if(LAZYLEN(emote_see)) + emote_see = string_list(emote_see) + damage_coeff = string_assoc_list(damage_coeff) if(footstep_type) AddElement(/datum/element/footstep, footstep_type) if(isnull(unsuitable_cold_damage)) diff --git a/code/modules/mob/mob.dm b/code/modules/mob/mob.dm index ffa4f5aee50..368241aa844 100644 --- a/code/modules/mob/mob.dm +++ b/code/modules/mob/mob.dm @@ -181,7 +181,7 @@ * Goes through hud_possible list and adds the images to the hud_list variable (if not already cached) */ /atom/proc/prepare_huds() - if(hud_list) // I choose to be lienient about people calling this proc more then once + if(hud_list) // I choose to be lenient about people calling this proc more then once return hud_list = list() for(var/hud in hud_possible) diff --git a/code/modules/modular_computers/computers/item/role_tablet_presets.dm b/code/modules/modular_computers/computers/item/role_tablet_presets.dm index 87f18a285d4..b77f273378f 100644 --- a/code/modules/modular_computers/computers/item/role_tablet_presets.dm +++ b/code/modules/modular_computers/computers/item/role_tablet_presets.dm @@ -501,7 +501,7 @@ var/datum/computer_file/program/themeify/theme_app = locate() in stored_files if(theme_app) for(var/theme_key in GLOB.pda_name_to_theme - GLOB.default_pda_themes) - theme_app.imported_themes += theme_key + LAZYADD(theme_app.imported_themes, theme_key) /obj/item/modular_computer/pda/clear/get_messenger_ending() return "Sent from my crystal PDA" diff --git a/code/modules/modular_computers/file_system/program.dm b/code/modules/modular_computers/file_system/program.dm index eed37d68cde..b7b8685750c 100644 --- a/code/modules/modular_computers/file_system/program.dm +++ b/code/modules/modular_computers/file_system/program.dm @@ -14,9 +14,9 @@ var/power_cell_use = PROGRAM_BASIC_CELL_USE ///List of required accesses to *run* the program. Any match will do. ///This also acts as download_access if that is not set, making this more draconic and restrictive. - var/list/run_access = list() + var/list/run_access ///List of required access to download or file host the program. Any match will do. - var/list/download_access = list() + var/list/download_access /// User-friendly name of this program. var/filedesc = "Unknown Program" /// Short description of this program's function. @@ -51,6 +51,10 @@ /datum/computer_file/program/New() ..() + if(LAZYLEN(run_access)) + run_access = string_list(run_access) + if(LAZYLEN(download_access)) + download_access = string_list(download_access) ///We need to ensure that different programs (subtypes mostly) won't try to load in the same circuit comps into the shell or usb port of the modpc. if(circuit_comp_type && initial(circuit_comp_type.associated_program) != type) stack_trace("circuit comp type mismatch: [type] has circuit comp type \[[circuit_comp_type]\], while \[[circuit_comp_type]\] has associated program \[[initial(circuit_comp_type.associated_program)]\].") diff --git a/code/modules/modular_computers/file_system/programs/borg_monitor.dm b/code/modules/modular_computers/file_system/programs/borg_monitor.dm index 70e7f657ae0..c619c9a69ba 100644 --- a/code/modules/modular_computers/file_system/programs/borg_monitor.dm +++ b/code/modules/modular_computers/file_system/programs/borg_monitor.dm @@ -174,7 +174,7 @@ program_open_overlay = "generic" extended_desc = "This program allows for remote monitoring of mission-assigned cyborgs." program_flags = PROGRAM_ON_SYNDINET_STORE - download_access = list() + download_access = null circuit_comp_type = /obj/item/circuit_component/mod_program/borg_monitor/syndie /datum/computer_file/program/borg_monitor/syndicate/evaluate_borg(mob/living/silicon/robot/R) diff --git a/code/modules/modular_computers/file_system/programs/dept_order.dm b/code/modules/modular_computers/file_system/programs/dept_order.dm index eede7b147f1..57a14636947 100644 --- a/code/modules/modular_computers/file_system/programs/dept_order.dm +++ b/code/modules/modular_computers/file_system/programs/dept_order.dm @@ -49,7 +49,7 @@ GLOBAL_VAR(department_cd_override) linked_department = department var/datum/job_department/linked_department_real = SSjob.get_department_type(linked_department) // Heads of staff can download - download_access |= linked_department_real.head_of_staff_access + LAZYOR(download_access, linked_department_real.head_of_staff_access) // Heads of staff + anyone in the dept can run it use_access |= linked_department_real.head_of_staff_access use_access |= linked_department_real.department_access @@ -164,7 +164,7 @@ GLOBAL_VAR(department_cd_override) if(action == "override_order") if(isnull(department_order) || !(department_order in SSshuttle.shopping_list)) return TRUE - if(length(download_access & id_card_access) <= 0) + if(LAZYLEN(download_access & id_card_access) <= 0) computer.physical.balloon_alert(orderer, "requires head of staff access!") playsound(computer, 'sound/machines/buzz/buzz-sigh.ogg', 30, TRUE) return TRUE diff --git a/code/modules/modular_computers/file_system/programs/maintenance/themes.dm b/code/modules/modular_computers/file_system/programs/maintenance/themes.dm index e3dca731d3a..de52daa335e 100644 --- a/code/modules/modular_computers/file_system/programs/maintenance/themes.dm +++ b/code/modules/modular_computers/file_system/programs/maintenance/themes.dm @@ -20,7 +20,7 @@ if(!theme_app) return FALSE //don't get the same one twice - if(theme_app.imported_themes.Find(theme_name)) + if(LAZYFIND(theme_app.imported_themes, theme_name)) return FALSE return TRUE @@ -30,7 +30,7 @@ //add the theme to the computer and increase its size to match var/datum/computer_file/program/themeify/theme_app = locate() in computer.stored_files if(theme_app) - theme_app.imported_themes += theme_name + LAZYADD(theme_app.imported_themes, theme_name) theme_app.size += size qdel(src) diff --git a/code/modules/modular_computers/file_system/programs/messenger/messenger_program.dm b/code/modules/modular_computers/file_system/programs/messenger/messenger_program.dm index 027782f9f47..0cd3595c437 100644 --- a/code/modules/modular_computers/file_system/programs/messenger/messenger_program.dm +++ b/code/modules/modular_computers/file_system/programs/messenger/messenger_program.dm @@ -34,7 +34,7 @@ var/spam_mode = FALSE /// An asssociative list of chats we have started, format: chatref -> pda_chat. - var/list/saved_chats = list() + var/list/saved_chats /// Whose chatlogs we currently have open. If we are in the contacts list, this is null. var/viewing_messages_of = null @@ -74,7 +74,7 @@ /datum/computer_file/program/messenger/proc/on_imprint_reset(sender) SIGNAL_HANDLER remove_messenger(src) - saved_chats = list() + LAZYNULL(saved_chats) selected_image = null viewing_messages_of = null @@ -117,7 +117,7 @@ data |= photo.picture_name if(viewing_messages_of in saved_chats) - var/datum/pda_chat/chat = saved_chats[viewing_messages_of] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, viewing_messages_of) for(var/datum/pda_message/message as anything in chat.messages) if(isnull(message.photo_name)) continue @@ -180,13 +180,13 @@ if("PDA_viewMessages") if(viewing_messages_of in saved_chats) - var/datum/pda_chat/chat = saved_chats[viewing_messages_of] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, viewing_messages_of) chat.unread_messages = 0 viewing_messages_of = params["ref"] if (viewing_messages_of in saved_chats) - var/datum/pda_chat/chat = saved_chats[viewing_messages_of] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, viewing_messages_of) chat.visible_in_recents = TRUE selected_image = null @@ -198,7 +198,7 @@ if(!(target in saved_chats)) return FALSE - var/datum/pda_chat/chat = saved_chats[target] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, target) chat.visible_in_recents = FALSE if(viewing_messages_of == target) viewing_messages_of = null @@ -208,9 +208,9 @@ var/chat_ref = params["ref"] if(chat_ref in saved_chats) - saved_chats.Remove(chat_ref) + LAZYREMOVE(saved_chats, chat_ref) else if(isnull(chat_ref)) - saved_chats = list() + LAZYNULL(saved_chats) viewing_messages_of = null return TRUE @@ -240,7 +240,7 @@ if(!(target_chat_ref in saved_chats)) return FALSE - var/datum/pda_chat/chat = saved_chats[target_chat_ref] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, target_chat_ref) chat.message_draft = message_draft @@ -252,7 +252,7 @@ if(!(target_chat_ref in saved_chats)) return FALSE - var/datum/pda_chat/chat = saved_chats[target_chat_ref] + var/datum/pda_chat/chat = LAZYACCESS(saved_chats, target_chat_ref) chat.unread_messages = 0 return TRUE @@ -269,7 +269,7 @@ var/target = null if(target_ref in saved_chats) - target = saved_chats[target_ref] + target = LAZYACCESS(saved_chats, target_ref) else if(target_ref in GLOB.pda_messengers) target = GLOB.pda_messengers[target_ref] else @@ -357,7 +357,7 @@ "job" = computer.saved_job, "ref" = REF(src) ) : null) - data["saved_chats"] = chats_data + data["saved_chats"] = chats_data || list() data["messengers"] = messengers data["sort_by_job"] = sort_by_job data["alert_silenced"] = alert_silenced @@ -412,8 +412,8 @@ for(var/mc in get_messengers()) messenger_targets += mc - for(var/chatref in saved_chats) - var/datum/pda_chat/chat = saved_chats[chatref] + for(var/chatref, data in saved_chats) + var/datum/pda_chat/chat = data if(!(chat.recipient?.reference in messenger_targets)) // if its in messenger_targets, it's valid continue messenger_targets -= chat.recipient.reference @@ -443,14 +443,14 @@ new_chat.cached_job = job new_chat.can_reply = FALSE - saved_chats[REF(new_chat)] = new_chat + LAZYSET(saved_chats, REF(new_chat), new_chat) return new_chat /// Gets the chat by the recipient, either by their name or messenger ref /datum/computer_file/program/messenger/proc/find_chat_by_recipient(recipient, fake_user = FALSE) - for(var/chat_ref in saved_chats) - var/datum/pda_chat/chat = saved_chats[chat_ref] + for(var/chat_ref, data in saved_chats) + var/datum/pda_chat/chat = data if(fake_user && chat.cached_name == recipient) return chat else if(chat.recipient?.reference == recipient) @@ -752,7 +752,7 @@ if("message") if(!(target_href in saved_chats)) return - quick_reply_prompt(usr, saved_chats[target_href]) + quick_reply_prompt(usr, LAZYACCESS(saved_chats, target_href)) if("open") if(target_href in saved_chats) diff --git a/code/modules/modular_computers/file_system/programs/notepad.dm b/code/modules/modular_computers/file_system/programs/notepad.dm index 95def6f8e96..af165952830 100644 --- a/code/modules/modular_computers/file_system/programs/notepad.dm +++ b/code/modules/modular_computers/file_system/programs/notepad.dm @@ -9,7 +9,6 @@ program_icon = "book" can_run_on_flags = PROGRAM_ALL circuit_comp_type = /obj/item/circuit_component/mod_program/notepad - var/written_note = "Congratulations on your station upgrading to the new NtOS and Thinktronic based collaboration effort, \ bringing you the best in electronics and software since 2467!\n\ To help with navigation, we have provided the following definitions:\n\ diff --git a/code/modules/modular_computers/file_system/programs/nt_pay.dm b/code/modules/modular_computers/file_system/programs/nt_pay.dm index 19f3c7bb198..4be567a3c86 100644 --- a/code/modules/modular_computers/file_system/programs/nt_pay.dm +++ b/code/modules/modular_computers/file_system/programs/nt_pay.dm @@ -50,7 +50,7 @@ data["owner_token"] = current_user.pay_token data["money"] = current_user.account_balance data["wanted_token"] = wanted_token - data["transaction_list"] = current_user.transaction_history + data["transaction_list"] = current_user.transaction_history || list() return data diff --git a/code/modules/modular_computers/file_system/programs/secureye.dm b/code/modules/modular_computers/file_system/programs/secureye.dm index 51e3cfed303..6d99a795cf6 100644 --- a/code/modules/modular_computers/file_system/programs/secureye.dm +++ b/code/modules/modular_computers/file_system/programs/secureye.dm @@ -38,7 +38,7 @@ filename = "syndeye" filedesc = "SyndEye" extended_desc = "This program allows for illegal access to security camera networks." - download_access = list() + download_access = null can_run_on_flags = PROGRAM_ALL program_flags = PROGRAM_ON_SYNDINET_STORE | PROGRAM_UNIQUE_COPY diff --git a/code/modules/modular_computers/file_system/programs/theme_selector.dm b/code/modules/modular_computers/file_system/programs/theme_selector.dm index 3d3f5a6a3cb..dafa7ddab6a 100644 --- a/code/modules/modular_computers/file_system/programs/theme_selector.dm +++ b/code/modules/modular_computers/file_system/programs/theme_selector.dm @@ -10,7 +10,7 @@ program_icon = "paint-roller" ///List of all themes imported from maintenance apps. - var/list/imported_themes = list() + var/list/imported_themes /datum/computer_file/program/themeify/ui_data(mob/user) var/list/data = list() @@ -29,7 +29,7 @@ var/selected_theme = params["selected_theme"] if( \ !GLOB.default_pda_themes.Find(selected_theme) && \ - !imported_themes.Find(selected_theme) && \ + !LAZYFIND(imported_themes, selected_theme) && \ !(computer.obj_flags & EMAGGED) \ ) return FALSE diff --git a/code/modules/projectiles/guns/energy/laser.dm b/code/modules/projectiles/guns/energy/laser.dm index f3989e16cad..de7922b8ef8 100644 --- a/code/modules/projectiles/guns/energy/laser.dm +++ b/code/modules/projectiles/guns/energy/laser.dm @@ -16,7 +16,7 @@ // Only regular lasguns can be slapcrafted if(type != /obj/item/gun/energy/laser) return - var/static/list/slapcraft_recipe_list = list(/datum/crafting_recipe/xraylaser, /datum/crafting_recipe/hellgun, /datum/crafting_recipe/ioncarbine) + var/static/list/slapcraft_recipe_list = list(/datum/crafting_recipe/laser/xraylaser, /datum/crafting_recipe/laser/hellgun, /datum/crafting_recipe/laser/ioncarbine) AddElement( /datum/element/slapcrafting,\ slapcraft_recipes = slapcraft_recipe_list,\ diff --git a/code/modules/reagents/chemistry/reagents/medicine_reagents.dm b/code/modules/reagents/chemistry/reagents/medicine_reagents.dm index c01b06a92ea..eddeafe8371 100644 --- a/code/modules/reagents/chemistry/reagents/medicine_reagents.dm +++ b/code/modules/reagents/chemistry/reagents/medicine_reagents.dm @@ -1274,7 +1274,8 @@ . = ..() affected_mob.remove_status_effect(/datum/status_effect/jitter) if(affected_mob.has_dna()) - affected_mob.dna.remove_mutation_group(affected_mob.dna.mutations - affected_mob.dna.get_mutation(/datum/mutation/race), GLOB.standard_mutation_sources) + var/list/mutations = affected_mob.dna.mutations || list() + affected_mob.dna.remove_mutation_group(mutations - affected_mob.dna.get_mutation(/datum/mutation/race), GLOB.standard_mutation_sources) affected_mob.dna.scrambled = FALSE /datum/reagent/medicine/antihol diff --git a/code/modules/surgery/bodyparts/_bodyparts.dm b/code/modules/surgery/bodyparts/_bodyparts.dm index 2967b5084e1..512aecdc28b 100644 --- a/code/modules/surgery/bodyparts/_bodyparts.dm +++ b/code/modules/surgery/bodyparts/_bodyparts.dm @@ -67,7 +67,7 @@ /// bitflag used to check which clothes cover this bodypart var/body_part /// List of obj/item's embedded inside us. Managed by embedded components, do not modify directly - var/list/embedded_objects = list() + var/list/embedded_objects /// are we a hand? if so, which one! var/held_index = 0 /// A speed modifier we apply to the owner when attached, if any. Positive numbers make it move slower, negative numbers make it move faster. @@ -1395,14 +1395,14 @@ if(embed in embedded_objects) // go away return // We don't need to do anything with projectile embedding, because it will never reach this point - embedded_objects += embed + LAZYADD(embedded_objects, embed) RegisterSignal(embed, COMSIG_ITEM_EMBEDDING_UPDATE, PROC_REF(embedded_object_changed)) refresh_bleed_rate() /// INTERNAL PROC, DO NOT USE /// Cleans up any attachment we have to the embedded object, removes it from our list /obj/item/bodypart/proc/_unembed_object(obj/item/unembed) - embedded_objects -= unembed + LAZYREMOVE(embedded_objects, unembed) UnregisterSignal(unembed, COMSIG_ITEM_EMBEDDING_UPDATE) refresh_bleed_rate() diff --git a/code/modules/unit_tests/crafting.dm b/code/modules/unit_tests/crafting.dm index d6da10b732c..2a362dbe182 100644 --- a/code/modules/unit_tests/crafting.dm +++ b/code/modules/unit_tests/crafting.dm @@ -48,17 +48,14 @@ //If it doesn't fail, then it was already handled, maybe through `unit_test_spawn_extras` var/list/uncreatables_found - for(var/spawn_path in recipe.unit_test_spawn_extras) - var/amount = recipe.unit_test_spawn_extras[spawn_path] + for(var/spawn_path, amount in recipe.unit_test_spawn_extras) if(ispath(spawn_path, /obj/item/stack)) new spawn_path(turf, /*new_amount =*/ amount, /*merge =*/ FALSE) continue for(var/index in 1 to amount) new spawn_path(turf) - for(var/req_path in recipe.reqs) //spawn items and reagents - var/amount = recipe.reqs[req_path] - + for(var/req_path, amount in recipe.reqs) //spawn items and reagents if(ispath(req_path, /datum/reagent)) //it's a reagent if(!bottomless_cup.reagents.has_reagent(req_path, amount)) bottomless_cup.reagents.add_reagent(req_path, amount + 1, no_react = TRUE) @@ -76,8 +73,8 @@ for(var/iteration in 1 to amount) new req_path(turf) - for(var/req_path in recipe.chem_catalysts) // spawn catalysts - var/amount = recipe.chem_catalysts[req_path] + for(var/req_path, chem_amount in recipe.chem_catalysts) // spawn catalysts + var/amount = chem_amount if(!bottomless_cup.reagents.has_reagent(req_path, amount)) bottomless_cup.reagents.add_reagent(req_path, amount + 1, no_react = TRUE)