using UnityEngine; using UnityEngine.Events; using System.Collections.Generic; using DG.Tweening; namespace AibisDream.MiniGame.HuoShan { /// /// 处理器灯光控制器 - 管理多个处理器灯的显示 /// 功能: /// - 根据滑片位置或索引控制特定处理器灯亮起 /// - 提供灯光明暗、闪烁、颜色变化效果 /// - 支持顺序激活多个处理器 /// public class ProcessorLightController : MonoBehaviour { [System.Serializable] public class ProcessorLightConfig { public GameObject lightObject; public Light lightComponent; public Renderer lightRenderer; public Color normalColor = Color.gray; public Color activeColor = new Color(0.3f, 0.9f, 0.55f); public float intensity = 1f; public float blinkSpeed = 1f; public float fadeInDuration = 0.3f; public string emissionProperty = "_EmissionColor"; public int segmentIndex = 0; // 对应的段索引 public float segmentStartAngle = 0f; // 该段的开始角度 public float segmentEndAngle = 30f; // 该段的结束角度 } [Header("处理器配置")] [Tooltip("处理器灯光配置列表")] [SerializeField] private List processorLights = new List(); [Tooltip("默认激活持续时间(秒)")] [SerializeField] private float defaultActiveDuration = 2f; [Tooltip("灯光强度曲线(用于闪烁效果)")] [SerializeField] private AnimationCurve intensityCurve = AnimationCurve.EaseInOut(0f, 0f, 1f, 1f); [Header("全局设置")] [Tooltip("等离子体发光影响所有处理器灯")] [SerializeField] private bool plasmaAffectsAll = false; [Tooltip("等离子体发光强度")] [SerializeField] private float plasmaGlowIntensity = 0.5f; [Tooltip("等离子体发光颜色")] [SerializeField] private Color plasmaGlowColor = new Color(0.3f, 0.9f, 0.55f); [Header("滑片联动")] [Tooltip("滑片控制器引用(用于监听位置变化)")] [SerializeField] private SliderController sliderController; [Tooltip("滑片位置变化时自动更新处理器灯")] [SerializeField] private bool autoUpdateFromSlider = true; [Tooltip("滑片弧度到处理器索引的映射表,按角度排序")] [SerializeField] private AnimationCurve angleToProcessorCurve = new AnimationCurve( new Keyframe(0f, 0f), new Keyframe(1f, 11f) ); [Header("事件")] [Tooltip("处理器灯激活时触发")] public UnityEvent onProcessorActivated; [Tooltip("所有处理器灯关闭时触发")] public UnityEvent onAllLightsOff; private Dictionary _processorMap = new Dictionary(); private List _activeTweens = new List(); private bool _isInitialized = false; private int _lastActiveProcessor = -1; #region 生命周期 private void Awake() { InitializeProcessorMap(); } private void OnEnable() { if (sliderController != null && autoUpdateFromSlider) { sliderController.onSliderPositionChanged.AddListener(OnSliderPositionChanged); } } private void OnDisable() { if (sliderController != null) { sliderController.onSliderPositionChanged.RemoveListener(OnSliderPositionChanged); } // 清理所有Tweens foreach (var tween in _activeTweens) { if (tween != null && tween.IsActive()) { tween.Kill(); } } _activeTweens.Clear(); } #endregion #region 初始化 private void InitializeProcessorMap() { _processorMap.Clear(); foreach (var config in processorLights) { if (config.lightObject != null) { // 查找灯光组件 if (config.lightComponent == null) { config.lightComponent = config.lightObject.GetComponent(); } // 查找渲染器 if (config.lightRenderer == null) { config.lightRenderer = config.lightObject.GetComponent(); } // 初始化为关闭状态 SetLightState(config, false, 0f); _processorMap[config.segmentIndex] = config; } } _isInitialized = true; Debug.Log($"ProcessorLightController: 初始化完成,共{processorLights.Count}个处理器灯"); } #endregion #region 滑片位置监听 private void OnSliderPositionChanged(float normalizedPosition) { if (!autoUpdateFromSlider) return; // 映射滑片位置到处理器索引 int processorIndex = GetProcessorIndexFromSlider(normalizedPosition); // 如果到达新的处理器段,激活对应的灯 if (processorIndex != _lastActiveProcessor) { ActivateProcessor(processorIndex); _lastActiveProcessor = processorIndex; } } /// /// 将滑片标准化位置(0-1)映射到处理器索引(0-processorCount-1) /// public int GetProcessorIndexFromSlider(float normalizedPosition) { // 使用AnimationCurve进行映射 float processorValue = angleToProcessorCurve.Evaluate(normalizedPosition); return Mathf.RoundToInt(processorValue); } #endregion #region 处理器灯光控制 /// /// 根据角度激活对应的处理器灯 /// public void ActivateProcessorByAngle(float angle) { float normalizedAngle = angle / 360f; int processorIndex = GetProcessorIndexFromSlider(normalizedAngle); ActivateProcessor(processorIndex); } /// /// 激活指定索引的处理器灯 /// public void ActivateProcessor(int processorIndex, float duration = -1f) { if (!_isInitialized) { InitializeProcessorMap(); } if (duration < 0) { duration = defaultActiveDuration; } // 先关闭所有灯 DeactivateAllProcessors(0.2f); // 检查索引是否有效 if (processorIndex < 0 || processorIndex >= processorLights.Count) { Debug.LogWarning($"ProcessorLightController: 处理器索引{processorIndex}超出范围"); return; } // 获取配置 ProcessorLightConfig config = null; foreach (var kvp in _processorMap) { if (kvp.Key == processorIndex) { config = kvp.Value; break; } } if (config != null) { // 激活灯光 SetLightState(config, true, duration); // 触发事件 onProcessorActivated?.Invoke(processorIndex); Debug.Log($"ProcessorLightController: 激活处理器{processorIndex}"); } else { Debug.LogWarning($"ProcessorLightController: 找不到处理器索引{processorIndex}的配置"); } } /// /// 关闭所有处理器灯 /// public void DeactivateAllProcessors(float fadeOutDuration = 0.3f) { foreach (var config in processorLights) { SetLightState(config, false, fadeOutDuration); } _lastActiveProcessor = -1; onAllLightsOff?.Invoke(); } /// /// 显示异常段的处理器灯(闪烁效果) /// public void ShowAnomalyProcessor(int processorIndex) { ProcessorLightConfig config = FindProcessorConfig(processorIndex); if (config != null) { // 闪烁效果 FlashLight(config, Color.red, 2f, 3); } } /// /// 设置灯光状态 /// private void SetLightState(ProcessorLightConfig config, bool isActive, float transitionDuration) { if (config.lightObject == null) return; // 设置灯光组件 if (config.lightComponent != null) { float targetIntensity = isActive ? config.intensity : 0f; // 使用Tween实现平滑过渡 Tweener intensityTween = DOTween.To( () => config.lightComponent.intensity, value => config.lightComponent.intensity = value, targetIntensity, transitionDuration ).SetEase(Ease.OutQuad); _activeTweens.Add(intensityTween); } // 设置渲染器发光 if (config.lightRenderer != null) { Color targetColor = isActive ? config.activeColor : config.normalColor; // 对于使用Emission的材质 Material material = config.lightRenderer.material; if (!string.IsNullOrEmpty(config.emissionProperty)) { int propertyID = Shader.PropertyToID(config.emissionProperty); Tweener colorTween = DOTween.To( () => material.GetColor(propertyID), value => material.SetColor(propertyID, value), targetColor, transitionDuration ).SetEase(Ease.OutQuad); _activeTweens.Add(colorTween); } // 设置基础颜色 Tweener baseColorTween = DOTween.To( () => config.lightRenderer.material.color, value => config.lightRenderer.material.color = value, targetColor, transitionDuration ).SetEase(Ease.OutQuad); _activeTweens.Add(baseColorTween); } // 更新GameObject状态 config.lightObject.SetActive(true); } /// /// 灯光闪烁效果 /// private void FlashLight(ProcessorLightConfig config, Color flashColor, float duration, int flashCount) { // 先停止之前的动画 config.lightObject.GetComponent()?.material?.DOComplete(); // 执行闪烁 if (config.lightComponent != null) { Sequence flashSequence = DOTween.Sequence(); for (int i = 0; i < flashCount; i++) { flashSequence.Append(config.lightComponent.DOIntensity(config.intensity * 2f, duration / (flashCount * 2))); flashSequence.Append(config.lightComponent.DOIntensity(config.intensity, duration / (flashCount * 2))); } _activeTweens.Add(flashSequence); } if (config.lightRenderer != null) { Color originalColor = config.lightRenderer.material.color; Sequence colorSequence = DOTween.Sequence(); for (int i = 0; i < flashCount; i++) { colorSequence.Append(config.lightRenderer.material.DOColor(flashColor, duration / (flashCount * 2))); colorSequence.Append(config.lightRenderer.material.DOColor(originalColor, duration / (flashCount * 2))); } _activeTweens.Add(colorSequence); } } /// /// 查找处理器配置 /// private ProcessorLightConfig FindProcessorConfig(int processorIndex) { if (_processorMap.TryGetValue(processorIndex, out var config)) { return config; } foreach (var lightConfig in processorLights) { if (lightConfig.segmentIndex == processorIndex) { return lightConfig; } } return null; } #endregion #region 映射配置 /// /// 更新角度到处理器的映射曲线 /// public void UpdateAngleToProcessorCurve(AnimationCurve curve) { angleToProcessorCurve = curve; } /// /// 根据滑片控制器自动配置映射 /// public void AutoConfigureMapping() { if (sliderController == null) return; int segmentCount = sliderController.GetCurrentSegment(); if (segmentCount <= 0) return; // 创建线性映射 Keyframe[] keys = new Keyframe[processorLights.Count]; float step = 1f / (processorLights.Count - 1); for (int i = 0; i < processorLights.Count; i++) { keys[i] = new Keyframe(i * step, i); } angleToProcessorCurve = new AnimationCurve(keys); } #endregion #region 公共方法 /// /// 获取活动中的处理器索引 /// public int GetActiveProcessor() { return _lastActiveProcessor; } /// /// 获取处理器数量 /// public int GetProcessorCount() { return processorLights.Count; } /// /// 设置等离子体发光影响 /// public void SetPlasmaGlow(float intensity, Color? color = null) { plasmaGlowIntensity = intensity; if (color.HasValue) { plasmaGlowColor = color.Value; } } /// /// 重置所有灯光 /// public void Reset() { DeactivateAllProcessors(); _lastActiveProcessor = -1; } /// /// 配置处理器灯光数据 /// public void ConfigureProcessorLights(List configs) { processorLights = configs; InitializeProcessorMap(); } #endregion } }