using UnityEngine;
using UnityEngine.Playables;
namespace GameWrapper.Timeline.CommonAction
{
///
/// 通用动作行为(独立版本)
/// 通过Timeline的生命周期方法自动控制GameObject
///
public class CommonActionBehaviour : PlayableBehaviour
{
public ECommonActionType actionType;
public int actionParam1;
public int actionParam2;
public string stringParam;
public Color colorParam;
public float floatParam;
private GameObject targetObject;
private bool originalActiveState;
private bool hasStoredOriginalState;
// 缓存组件引用
private ParticleSystem cachedParticleSystem;
private Animator cachedAnimator;
private Renderer cachedRenderer;
private Material originalMaterial;
private Color originalColor;
private float originalAlpha;
// 缓存PlayableDirector引用,用于手动获取绑定对象
private PlayableDirector cachedDirector;
public override void OnPlayableCreate(Playable playable)
{
Debug.Log($"[CommonAction] OnPlayableCreate - ActionType: {actionType}");
}
public override void OnBehaviourPlay(Playable playable, FrameData info)
{
Debug.Log($"[CommonAction] OnBehaviourPlay - ActionType: {actionType}, Param1: {actionParam1}, TargetObject: {(targetObject != null ? targetObject.name : "NULL")}");
// 如果targetObject为null,尝试手动获取
if (targetObject == null)
{
TryGetTargetObjectFromGraph(playable);
}
// Clip开始播放时调用
if (targetObject == null)
{
Debug.LogError($"[CommonAction] OnBehaviourPlay - TargetObject is NULL! 请检查Track是否绑定了GameObject");
return;
}
// 保存原始状态(只保存一次)
if (!hasStoredOriginalState)
{
originalActiveState = targetObject.activeSelf;
hasStoredOriginalState = true;
Debug.Log($"[CommonAction] 保存原始状态 - {targetObject.name}, ActiveState: {originalActiveState}");
}
switch (actionType)
{
case ECommonActionType.ActiveSet:
HandleActiveSet();
break;
case ECommonActionType.PlayParticle:
HandlePlayParticle();
break;
case ECommonActionType.ControlAnimator:
HandleControlAnimator();
break;
case ECommonActionType.PlaySound:
HandlePlaySound();
break;
case ECommonActionType.CameraShake:
HandleCameraShake();
break;
case ECommonActionType.MaterialChange:
HandleMaterialChange();
break;
}
}
public override void OnBehaviourPause(Playable playable, FrameData info)
{
Debug.Log($"[CommonAction] OnBehaviourPause - ActionType: {actionType}, IsDone: {playable.GetGraph().GetRootPlayable(0).IsDone()}");
// Clip停止播放时调用
if (targetObject == null)
{
Debug.LogWarning($"[CommonAction] OnBehaviourPause - TargetObject is NULL");
return;
}
// 检查是否是因为Timeline结束而暂停
if (playable.GetGraph().GetRootPlayable(0).IsDone())
{
Debug.Log($"[CommonAction] Timeline结束,恢复原始状态 - {targetObject.name}");
// Timeline播放完毕,恢复原始状态
RestoreOriginalState();
}
}
public override void ProcessFrame(Playable playable, FrameData info, object playerData)
{
// 获取绑定的GameObject(每帧都会调用,但只在第一次获取)
if (targetObject == null && playerData is GameObject go)
{
targetObject = go;
Debug.Log($"[CommonAction] ProcessFrame获取到绑定对象: {targetObject.name}, ActionType: {actionType}");
CacheComponents();
}
}
///
/// 尝试从PlayableGraph中手动获取绑定的对象
/// 用于解决OnBehaviourPlay时ProcessFrame还未执行的时序问题
///
private void TryGetTargetObjectFromGraph(Playable playable)
{
Debug.Log($"[CommonAction] 尝试手动获取绑定对象...");
// 尝试通过PlayableDirector获取
try
{
if (cachedDirector == null)
{
var graph = playable.GetGraph();
var resolver = graph.GetResolver();
if (resolver is PlayableDirector director)
{
cachedDirector = director;
Debug.Log($"[CommonAction] 找到PlayableDirector: {director.gameObject.name}");
}
}
if (cachedDirector != null)
{
// 遍历所有绑定,找到CommonActionTrack对应的绑定对象
foreach (var output in cachedDirector.playableAsset.outputs)
{
// 检查是否是CommonActionTrack
if (output.sourceObject is CommonActionTrack)
{
var boundObject = cachedDirector.GetGenericBinding(output.sourceObject);
if (boundObject is GameObject go)
{
targetObject = go;
Debug.Log($"[CommonAction] ✅ 通过Director获取到绑定对象: {targetObject.name}");
CacheComponents();
return;
}
else if (boundObject != null)
{
Debug.LogWarning($"[CommonAction] 绑定对象类型不是GameObject: {boundObject.GetType().Name}");
}
else
{
Debug.LogWarning($"[CommonAction] CommonActionTrack未绑定任何对象");
}
}
}
}
}
catch (System.Exception e)
{
Debug.LogWarning($"[CommonAction] 通过Director获取绑定对象失败: {e.Message}");
}
Debug.LogWarning($"[CommonAction] ⚠️ 获取绑定对象失败,将等待ProcessFrame");
}
///
/// 缓存常用组件引用
///
private void CacheComponents()
{
if (targetObject == null)
{
Debug.LogError($"[CommonAction] CacheComponents - targetObject is NULL");
return;
}
Debug.Log($"[CommonAction] 开始缓存组件 - {targetObject.name}");
cachedParticleSystem = targetObject.GetComponent();
if (cachedParticleSystem != null)
Debug.Log($"[CommonAction] 找到ParticleSystem组件");
cachedAnimator = targetObject.GetComponent();
if (cachedAnimator != null)
Debug.Log($"[CommonAction] 找到Animator组件");
cachedRenderer = targetObject.GetComponent();
if (cachedRenderer != null)
{
Debug.Log($"[CommonAction] 找到Renderer组件");
originalMaterial = cachedRenderer.material;
if (originalMaterial != null)
{
originalColor = originalMaterial.color;
originalAlpha = originalColor.a;
Debug.Log($"[CommonAction] 保存原始材质 - Color: {originalColor}, Alpha: {originalAlpha}");
}
}
}
///
/// 恢复原始状态
///
private void RestoreOriginalState()
{
Debug.Log($"[CommonAction] RestoreOriginalState - ActionType: {actionType}");
switch (actionType)
{
case ECommonActionType.ActiveSet:
Debug.Log($"[CommonAction] 恢复ActiveState: {originalActiveState}");
targetObject.SetActive(originalActiveState);
break;
case ECommonActionType.MaterialChange:
if (cachedRenderer != null && originalMaterial != null)
{
Debug.Log($"[CommonAction] 恢复材质颜色: {originalColor}");
cachedRenderer.material.color = originalColor;
}
break;
}
}
#region 动作处理方法
///
/// 处理激活/隐藏逻辑
///
private void HandleActiveSet()
{
if (targetObject == null)
{
Debug.LogError($"[CommonAction] HandleActiveSet - targetObject is NULL");
return;
}
bool shouldBeActive = actionParam1 == 1;
Debug.Log($"[CommonAction] HandleActiveSet - Object: {targetObject.name}, Param1: {actionParam1}, ShouldBeActive: {shouldBeActive}, CurrentActive: {targetObject.activeSelf}");
if (targetObject.activeSelf != shouldBeActive)
{
targetObject.SetActive(shouldBeActive);
Debug.Log($"[CommonAction] ✅ SetActive执行完成 - {targetObject.name} -> {shouldBeActive}");
}
else
{
Debug.Log($"[CommonAction] 状态已经一致,跳过SetActive");
}
}
///
/// 处理粒子特效
///
private void HandlePlayParticle()
{
if (cachedParticleSystem == null)
{
Debug.LogWarning($"对象 {targetObject.name} 没有ParticleSystem组件");
return;
}
switch (actionParam1)
{
case 1: // 开始播放
cachedParticleSystem.Play();
break;
case 2: // 停止播放
cachedParticleSystem.Stop();
break;
case 3: // 暂停
cachedParticleSystem.Pause();
break;
case 4: // 继续
cachedParticleSystem.Play();
break;
}
}
///
/// 处理Animator控制
///
private void HandleControlAnimator()
{
if (cachedAnimator == null)
{
Debug.LogWarning($"对象 {targetObject.name} 没有Animator组件");
return;
}
switch (actionParam1)
{
case 1: // 播放动画
if (!string.IsNullOrEmpty(stringParam))
{
cachedAnimator.Play(stringParam);
}
else if (actionParam2 != 0)
{
cachedAnimator.Play(actionParam2);
}
break;
case 2: // 设置Trigger
if (!string.IsNullOrEmpty(stringParam))
{
cachedAnimator.SetTrigger(stringParam);
}
break;
case 3: // 设置Bool为true
if (!string.IsNullOrEmpty(stringParam))
{
cachedAnimator.SetBool(stringParam, true);
}
break;
case 4: // 设置Bool为false
if (!string.IsNullOrEmpty(stringParam))
{
cachedAnimator.SetBool(stringParam, false);
}
break;
}
}
///
/// 处理音效播放
///
private void HandlePlaySound()
{
// TODO: 集成你们项目的音效系统
// 例如:AudioManager.Instance.PlaySound(actionParam1);
Debug.Log($"播放音效 ID: {actionParam1}");
}
///
/// 处理相机震动
///
private void HandleCameraShake()
{
// TODO: 集成你们项目的相机震动系统
// 例如:CameraManager.Instance.Shake(actionParam1 / 10f);
Debug.Log($"相机震动强度: {actionParam1}");
}
///
/// 处理材质修改
///
private void HandleMaterialChange()
{
Debug.Log($"[CommonAction] HandleMaterialChange - Param1: {actionParam1}");
if (cachedRenderer == null)
{
Debug.LogWarning($"[CommonAction] 对象 {targetObject.name} 没有Renderer组件");
return;
}
switch (actionParam1)
{
case 1: // 修改颜色
Debug.Log($"[CommonAction] 修改颜色 - Color: {colorParam}");
cachedRenderer.material.color = colorParam;
Debug.Log($"[CommonAction] ✅ 颜色修改完成 - 当前颜色: {cachedRenderer.material.color}");
break;
case 2: // 修改透明度
Color currentColor = cachedRenderer.material.color;
Debug.Log($"[CommonAction] 修改透明度 - 原始: {currentColor.a}, 目标: {floatParam}");
currentColor.a = floatParam;
cachedRenderer.material.color = currentColor;
Debug.Log($"[CommonAction] ✅ 透明度修改完成 - 当前透明度: {cachedRenderer.material.color.a}");
break;
default:
Debug.LogWarning($"[CommonAction] 未知的MaterialChange参数: {actionParam1}");
break;
}
}
#endregion
}
}