using HarmonyLib; using System.Collections.Generic; using UnityEngine; namespace MuzikaGromche { [HarmonyPatch(typeof(RoundManager))] static class AllPoweredLightsPatch { // Vanilla method assumes that GameObjects with tag "PoweredLight" only contain a single Light component each. // This is, however, not true for certains double-light setups, such as: // - double PointLight (even though one of them is 'Point' another is 'Spot') inside CeilingFanAnimContainer in BedroomTile/BedroomTileB; // - MineshaftSpotlight when it has not only `Point Light` but also `IndirectLight` in BirthdayRoomTile; // - (maybe more?) // In order to fix that, replace singular GetComponentInChildren with plural GetComponentsInChildren version. [HarmonyPatch(nameof(RoundManager.RefreshLightsList))] [HarmonyPrefix] static bool OnRefreshLightsList(RoundManager __instance) { RefreshLightsListPatched(__instance); var behaviour = __instance.gameObject.GetComponent() ?? __instance.gameObject.AddComponent(); behaviour.Refresh(); // Skip the original method return false; } static void RefreshLightsListPatched(RoundManager self) { // Reusable list to reduce allocations List lights = []; self.allPoweredLights.Clear(); self.allPoweredLightsAnimators.Clear(); GameObject[] gameObjects = GameObject.FindGameObjectsWithTag("PoweredLight"); if (gameObjects == null) { return; } foreach (var gameObject in gameObjects) { Animator animator = gameObject.GetComponentInChildren(); if (!(animator == null)) { self.allPoweredLightsAnimators.Add(animator); // Patched section: Use list instead of singular GetComponentInChildren gameObject.GetComponentsInChildren(includeInactive: true, lights); self.allPoweredLights.AddRange(lights); } } foreach (var animator in self.allPoweredLightsAnimators) { animator.SetFloat("flickerSpeed", UnityEngine.Random.Range(0.6f, 1.4f)); } } } internal class PoweredLightsBehaviour : MonoBehaviour { private struct LightData { public Light Light; public Color InitialColor; } private readonly List AllPoweredLights = []; public static PoweredLightsBehaviour Instance { get; private set; } = null!; void Awake() { if (Instance == null) { Instance = this; } } public void Refresh() { AllPoweredLights.Clear(); foreach (var light in RoundManager.Instance.allPoweredLights) { AllPoweredLights.Add(new LightData { Light = light, InitialColor = light.color, }); } } public void SetLightColor(SetLightsColorEvent e) { foreach (var data in AllPoweredLights) { var color = e.GetColor(data.InitialColor); data.Light.color = color; } } public void ResetLightColor() { foreach (var data in AllPoweredLights) { data.Light.color = data.InitialColor; } } } }