using System.Collections; using UnityEngine; namespace MonoLimboStudio { public class LightFlicker : MonoBehaviour { [Header("Light Settings")] public Light targetLight; public float minIntensity = 0.5f; public float maxIntensity = 1.5f; [Header("Perlin Flicker (smooth)")] public float flickerSpeed = 5f; [Header("Glitch Flicker (bursts)")] [Range(0f, 1f)] public float glitchChance = 0.15f; // probability of a glitch burst each frame public float glitchMinDuration = 0.02f; public float glitchMaxDuration = 0.12f; [Header("Material Settings")] public Renderer targetRenderer; public string opacityProperty = "_Opacity"; [Range(0f, 1f)] public float minOpacity = 0.2f; [Range(0f, 1f)] public float maxOpacity = 1.0f; private Material _materialInstance; private float _randomOffset; void Start() { // unique offset per instance so lamps don't flicker in sync _randomOffset = Random.Range(0f, 1000f); if (targetRenderer != null) { _materialInstance = targetRenderer.material; if (!_materialInstance.HasProperty(opacityProperty)) Debug.LogWarning($"Property '{opacityProperty}' not found on material."); } StartCoroutine(FlickerRoutine()); } private IEnumerator FlickerRoutine() { while (true) { // --- Smooth Perlin phase --- float perlinValue = Mathf.PerlinNoise(Time.time * flickerSpeed + _randomOffset, 0f); ApplyFlicker(perlinValue); // --- Random glitch burst (occasional) --- if (Random.value < glitchChance) { yield return StartCoroutine(GlitchBurst()); } yield return null; // wait for next frame } } private IEnumerator GlitchBurst() { float duration = Random.Range(glitchMinDuration, glitchMaxDuration); float elapsed = 0f; while (elapsed < duration) { // fully random intensity during the burst float glitchValue = Random.value; ApplyFlicker(glitchValue); elapsed += Time.deltaTime; yield return null; } } private void ApplyFlicker(float t) { if (targetLight != null) targetLight.intensity = Mathf.Lerp(minIntensity, maxIntensity, t); if (_materialInstance != null && _materialInstance.HasProperty(opacityProperty)) _materialInstance.SetFloat(opacityProperty, Mathf.Lerp(minOpacity, maxOpacity, t)); } void OnDestroy() { // .material creates a new instance — destroy it to avoid memory leaks if (_materialInstance != null) Destroy(_materialInstance); } } }