From d4595054ce25485d798e1f3207b3ec12380a0d25 Mon Sep 17 00:00:00 2001 From: Contrabang <91113370+Contrabang@users.noreply.github.com> Date: Mon, 13 Apr 2026 23:26:31 -0400 Subject: [PATCH] Adds CI for checking if a variable exists (#31855) * i leave for one month smh * feature compatibility * fixed --- code/_onclick/item_attack.dm | 7 +++--- code/game/objects/items.dm | 5 ++++- code/game/objects/items/dyeing.dm | 32 ++++++++-------------------- code/game/objects/items/toys.dm | 5 +++-- code/modules/clothing/under/color.dm | 7 +++--- tools/ci/check_grep2.py | 8 ++++++- 6 files changed, 31 insertions(+), 33 deletions(-) diff --git a/code/_onclick/item_attack.dm b/code/_onclick/item_attack.dm index 2bb0e0b91af..a8917038593 100644 --- a/code/_onclick/item_attack.dm +++ b/code/_onclick/item_attack.dm @@ -178,11 +178,12 @@ to_chat(user, SPAN_WARNING("You don't want to harm other living beings!")) return FALSE - if(!force && !("zero_damage_hitsound" in vars)) + if(!should_play_hitsound(force)) playsound(loc, 'sound/weapons/tap.ogg', get_clamped_volume(), TRUE, -1) else - SEND_SIGNAL(target, COMSIG_ATTACK) - add_attack_logs(user, target, "Attacked with [name] ([uppertext(user.a_intent)]) ([uppertext(damtype)])", (target.ckey && force > 0 && damtype != STAMINA) ? null : ATKLOG_ALMOSTALL) + if(force) + SEND_SIGNAL(target, COMSIG_ATTACK) + add_attack_logs(user, target, "Attacked with [name] ([uppertext(user.a_intent)]) ([uppertext(damtype)])", (target.ckey && force > 0 && damtype != STAMINA) ? null : ATKLOG_ALMOSTALL) if(hitsound) playsound(loc, hitsound, get_clamped_volume(), TRUE, extrarange = stealthy_audio ? SILENCED_SOUND_EXTRARANGE : -1, falloff_distance = 0) diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm index 87da806b8c5..affa1581da4 100644 --- a/code/game/objects/items.dm +++ b/code/game/objects/items.dm @@ -718,6 +718,9 @@ GLOBAL_DATUM_INIT(welding_sparks, /mutable_appearance, mutable_appearance('icons else return +/obj/item/proc/should_play_hitsound(damage) + return damage > 0 + /obj/item/throw_impact(atom/hit_atom, datum/thrownthing/throwingdatum) if(hit_atom && !QDELETED(hit_atom)) SEND_SIGNAL(src, COMSIG_MOVABLE_IMPACT, hit_atom, throwingdatum) @@ -729,7 +732,7 @@ GLOBAL_DATUM_INIT(welding_sparks, /mutable_appearance, mutable_appearance('icons var/mob/living/L = hit_atom L.IgniteMob() var/volume = get_volume_by_throwforce_and_or_w_class() - if(throwforce > 0 || ("zero_damage_hitsound" in vars)) + if(should_play_hitsound(throwforce)) if(mob_throw_hit_sound) SSthrowing.playsound_capped(hit_atom, mob_throw_hit_sound, volume, TRUE, -1) else if(hitsound) diff --git a/code/game/objects/items/dyeing.dm b/code/game/objects/items/dyeing.dm index ad26adaef10..92be5098ce2 100644 --- a/code/game/objects/items/dyeing.dm +++ b/code/game/objects/items/dyeing.dm @@ -48,32 +48,18 @@ /// Because of jumpsuit palettes, we have to do some extra icon shenanigans. /obj/item/clothing/under/dye_item(dye_color, dye_key_override) - if(!dyeable || !dye_color) - return - var/dye_key_selector = dye_key_override ? dye_key_override : dyeing_key - var/obj/item/clothing/under/target_type = GLOB.dye_registry[dye_key_selector][dye_color] + . = ..() // If we're dying it to a colored jumpsuit... - if(target_type in typesof(/obj/item/clothing/under/color)) - var/obj/item/clothing/under/color/target_obj = new target_type(null) - set_icon_from_cache(palette_key = target_obj.icon_palette_key, dye_key = target_obj.dyeing_key) - // update the name/description - name = initial(target_obj.name) - desc = target_obj.desc + "\nThe colors look a little dodgy." - qdel(target_obj) + if(ispath(., /obj/item/clothing/under/color)) + var/obj/item/clothing/under/color/target_type = . + set_icon_from_cache(palette_key = target_type.icon_palette_key, dye_key = target_type.dyeing_key) - // If it also started as a colored jumpsuit, change the palette key - if("icon_palette_key" in vars) - var/obj/item/clothing/under/color/dyed_item = src - dyed_item.icon_palette_key = dye_color - return - - // If we're not, but it started as a colored jumpsuit, unset the palette key so icon updates don't mess it up - else if("icon_palette_key" in vars) - var/obj/item/clothing/under/color/dyed_item = src - dyed_item.icon_palette_key = null - - return ..() +/obj/item/clothing/under/color/dye_item(dye_color, dye_key_override) + icon_palette_key = null + . = ..() + if(ispath(., /obj/item/clothing/under/color)) + icon_palette_key = dye_color /// Beanies use the color var for their appearance, we don't normally copy this over but we have to for beanies /obj/item/clothing/head/beanie/dye_item(dye_color, dye_key_override) diff --git a/code/game/objects/items/toys.dm b/code/game/objects/items/toys.dm index 40d2e763b71..ffd78c02e4c 100644 --- a/code/game/objects/items/toys.dm +++ b/code/game/objects/items/toys.dm @@ -2123,8 +2123,6 @@ icon_state = "pool_noodle" attack_verb = list("bopped", "splatted", "smacked", "thwapped", "slapped") hitsound = 'sound/items/pool_noodle_hit.ogg' - // Having this var at all should play hitsound even if damage is zero - var/zero_damage_hitsound = TRUE w_class = WEIGHT_CLASS_BULKY /obj/item/toy/pool_noodle/Initialize(mapload) @@ -2134,6 +2132,9 @@ desc = "A damp, flexible tube for unrestrained summer fun." return ..() +/obj/item/toy/pool_noodle/should_play_hitsound(damage) + return TRUE + /obj/item/toy/pool_noodle/pink color = COLOR_PINK diff --git a/code/modules/clothing/under/color.dm b/code/modules/clothing/under/color.dm index fefcc2561c8..c49e9d3894b 100644 --- a/code/modules/clothing/under/color.dm +++ b/code/modules/clothing/under/color.dm @@ -30,9 +30,6 @@ set_icon_from_cache() /obj/item/clothing/under/proc/set_icon_from_cache(palette_key = null, dye_key = null) - if(!palette_key && ("icon_palette_key" in vars)) - var/obj/item/clothing/under/color/colored_jumpsuit = src - palette_key = palette_key || colored_jumpsuit.icon_palette_key if(!palette_key) return FALSE dye_key = dye_key || dyeing_key @@ -54,6 +51,10 @@ icon_state = "[icon_state_prefix][icon_state_skirt]" inhand_icon_state = "[icon_state_prefix]_suit" +/obj/item/clothing/under/color/set_icon_from_cache(palette_key, dye_key) + palette_key = palette_key || icon_palette_key + . = ..(palette_key, dye_key) + /obj/item/clothing/under/color/random/Initialize(mapload) var/list/excluded = list(/obj/item/clothing/under/color/random, /obj/item/clothing/under/color/blue/dodgeball, diff --git a/tools/ci/check_grep2.py b/tools/ci/check_grep2.py index 538e02749b1..0faf9946810 100644 --- a/tools/ci/check_grep2.py +++ b/tools/ci/check_grep2.py @@ -189,9 +189,14 @@ def check_camel_case_type_names(idx, line): UID_WITH_PARAMETER = re.compile(r"\bUID\(\w+\)") def check_uid_parameters(idx, line): - if result := UID_WITH_PARAMETER.search(line): + if UID_WITH_PARAMETER.search(line): return [(idx + 1, "UID() does not take arguments. Use UID() instead of UID(src) and datum.UID() instead of UID(datum).")] +IN_VARS_INVALID_CHECK = re.compile(r"in vars\b") +def check_in_vars_access(idx, line): + if IN_VARS_INVALID_CHECK.search(line): + return [(idx + 1, "Our codebase does not allow checking if variables are in vars directly")] + CODE_CHECKS = [ check_space_indentation, check_mixed_indentation, @@ -210,6 +215,7 @@ CODE_CHECKS = [ check_istype_src, check_camel_case_type_names, check_uid_parameters, + check_in_vars_access, ] def lint_file(code_filepath: str) -> list[Failure]: