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
}
}