diff --git a/MuzikaGromche/PoweredLightsAnimators.cs b/MuzikaGromche/PoweredLightsAnimators.cs index c2badaf..7f5ea1d 100644 --- a/MuzikaGromche/PoweredLightsAnimators.cs +++ b/MuzikaGromche/PoweredLightsAnimators.cs @@ -11,9 +11,15 @@ namespace MuzikaGromche { static class PoweredLightsAnimators { + private const string PoweredLightTag = "PoweredLight"; + private delegate void ManualPatch(GameObject animatorContainer); - private readonly record struct AnimatorPatch(string AnimatorContainerPath, RuntimeAnimatorController AnimatorController, ManualPatch? ManualPatch); + private readonly record struct AnimatorPatch( + string AnimatorContainerPath, + RuntimeAnimatorController AnimatorController, + bool AddTagAndAnimator, + ManualPatch? ManualPatch); private readonly record struct TilePatch(string TileName, AnimatorPatch[] Patches) { @@ -21,13 +27,17 @@ namespace MuzikaGromche public readonly string TileCloneName = $"{TileName}(Clone)"; } - private readonly record struct AnimatorPatchDescriptor(string AnimatorContainerPath, string AnimatorControllerAssetPath, ManualPatch? ManualPatch = null) + private readonly record struct AnimatorPatchDescriptor( + string AnimatorContainerPath, + string AnimatorControllerAssetPath, + bool AddTagAndAnimator = false, + ManualPatch? ManualPatch = null) { public AnimatorPatch Load(AssetBundle assetBundle) { var animationController = assetBundle.LoadAsset(AnimatorControllerAssetPath) ?? throw new FileNotFoundException($"RuntimeAnimatorController not found: {AnimatorControllerAssetPath}", AnimatorControllerAssetPath); - return new(AnimatorContainerPath, animationController, ManualPatch); + return new(AnimatorContainerPath, animationController, AddTagAndAnimator, ManualPatch); } } @@ -47,6 +57,10 @@ namespace MuzikaGromche private static IDictionary Patches = new Dictionary(); + private static AudioClip AudioClipOn = null!; + private static AudioClip AudioClipOff = null!; + private static AudioClip AudioClipFlicker = null!; + public static void Load() { const string BundleFileName = "muzikagromche_poweredlightsanimators"; @@ -54,6 +68,10 @@ namespace MuzikaGromche var assetBundle = AssetBundle.LoadFromFile(bundlePath) ?? throw new NullReferenceException("Failed to load bundle"); + AudioClipOn = assetBundle.LoadAsset("Assets/LethalCompany/Mods/MuzikaGromche/AudioClips/LightOn.ogg"); + AudioClipOff = assetBundle.LoadAsset("Assets/LethalCompany/Mods/MuzikaGromche/AudioClips/LightOff.ogg"); + AudioClipFlicker = assetBundle.LoadAsset("Assets/LethalCompany/Mods/MuzikaGromche/AudioClips/LightFlicker.ogg"); + const string BasePath = "Assets/LethalCompany/Mods/MuzikaGromche/AnimatorControllers/"; const string PointLight4 = $"{BasePath}Point Light (4) (Patched).controller"; @@ -61,6 +79,7 @@ namespace MuzikaGromche const string LightbulbsLine = $"{BasePath}lightbulbsLineMesh (Patched).controller"; const string CeilingFan = $"{BasePath}CeilingFan (originally GameObject) (Patched).controller"; const string LEDHangingLight = $"{BasePath}LEDHangingLight (Patched).controller"; + const string MineshaftStartTileSpotlight = $"{BasePath}MineshaftStartTileSpotlight (New).controller"; TilePatchDescriptor[] descriptors = [ @@ -98,13 +117,17 @@ namespace MuzikaGromche new("HangingLEDBarLight (3)", LEDHangingLight), new("HangingLEDBarLight (4)", LEDHangingLight, // This HangingLEDBarLight's IndirectLight is wrongly named, so animator couldn't find it - RenameGameObjectPatch("IndirectLight (1)", "IndirectLight")), + ManualPatch: RenameGameObjectPatch("IndirectLight (1)", "IndirectLight")), ]), new("PoolTile", [ new("PoolLights/HangingLEDBarLight", LEDHangingLight), new("PoolLights/HangingLEDBarLight (4)", LEDHangingLight), new("PoolLights/HangingLEDBarLight (5)", LEDHangingLight), ]), + new("MineshaftStartTile", [ + new("Cylinder.001 (1)", MineshaftStartTileSpotlight, AddTagAndAnimator: true), + new("Cylinder.001 (2)", MineshaftStartTileSpotlight, AddTagAndAnimator: true), + ]), ]; Patches = descriptors @@ -134,7 +157,41 @@ namespace MuzikaGromche #pragma warning restore CS0162 // Unreachable code detected } - var animator = animationContainerTransform.gameObject.GetComponent(); + GameObject animationContainer = animationContainerTransform.gameObject; + Animator animator = animationContainer.GetComponent(); + + if (patch.AddTagAndAnimator) + { + animationContainer.tag = PoweredLightTag; + if (animator == null) + { + animator = animationContainer.AddComponent(); + } + if (!animationContainer.TryGetComponent(out var audioScript)) + { + audioScript = animationContainer.AddComponent(); + audioScript.audioClip = AudioClipOn; + audioScript.audioClip2 = AudioClipOff; + audioScript.audioClip3 = AudioClipFlicker; + } + if (!animationContainer.TryGetComponent(out var audioSource)) + { + // Copy from an existing AudioSource of another light animator + var otherSource = tile.gameObject.GetComponentInChildren(); + if (otherSource != null) + { + audioSource = animationContainer.AddComponent(); + audioSource.spatialBlend = 1; + audioSource.playOnAwake = false; + audioSource.outputAudioMixerGroup = otherSource.outputAudioMixerGroup; + audioSource.spread = otherSource.spread; + audioSource.rolloffMode = otherSource.rolloffMode; + audioSource.maxDistance = otherSource.maxDistance; + audioSource.SetCustomCurve(AudioSourceCurveType.CustomRolloff, otherSource.GetCustomCurve(AudioSourceCurveType.CustomRolloff)); + } + } + } + if (animator == null) { #if DEBUG @@ -145,7 +202,7 @@ namespace MuzikaGromche #pragma warning restore CS0162 // Unreachable code detected } - patch.ManualPatch?.Invoke(animationContainerTransform.gameObject); + patch.ManualPatch?.Invoke(animationContainer); animator.runtimeAnimatorController = patch.AnimatorController; Debug.Log($"{nameof(MuzikaGromche)} {nameof(PoweredLightsAnimatorsPatch)} {tilePatch.TileName}/{patch.AnimatorContainerPath}: Replaced animator controller"); diff --git a/MuzikaGromche/UnityAssets/muzikagromche_poweredlightsanimators b/MuzikaGromche/UnityAssets/muzikagromche_poweredlightsanimators index d420618..2a7c26e 100644 Binary files a/MuzikaGromche/UnityAssets/muzikagromche_poweredlightsanimators and b/MuzikaGromche/UnityAssets/muzikagromche_poweredlightsanimators differ