76 lines
2.4 KiB
C#
76 lines
2.4 KiB
C#
using Sirenix.OdinInspector;
|
||
using UnityEngine;
|
||
|
||
namespace SLSUtilities.Narrative
|
||
{
|
||
/// <summary>
|
||
/// 通用剧情触发器基类。
|
||
/// 仅负责管理触发状态(oneShot, hasFired)与全局故事 ID(storyId)。
|
||
/// 具体触发的时机与条件由派生类(子类)自行重写并定义。
|
||
/// </summary>
|
||
public abstract class NarrativeTrigger : MonoBehaviour
|
||
{
|
||
/// <summary>
|
||
/// 全局静态触发事件。当任何剧情触发器被激活时触发。
|
||
/// 用于彻底解耦 SLSUtilities 核心程序集与 MainGame 层的 StoryDirector。
|
||
/// </summary>
|
||
public static System.Action<string> OnNarrativeTriggerFired;
|
||
|
||
[TitleGroup("Trigger Settings", "剧情触发器核心配置", Alignment = TitleAlignments.Centered)]
|
||
|
||
[SerializeField]
|
||
[Required]
|
||
[Tooltip("要触发的 NarrativeEntry 的 storyId")]
|
||
protected string storyId;
|
||
|
||
[SerializeField]
|
||
[Tooltip("是否仅能触发一次")]
|
||
protected bool oneShot = true;
|
||
|
||
[ShowInInspector]
|
||
[ReadOnly]
|
||
[Tooltip("该触发器当前是否已经激活过")]
|
||
protected bool hasFired;
|
||
|
||
/// <summary>获取触发的目标故事 ID。</summary>
|
||
public string StoryId => storyId;
|
||
|
||
/// <summary>是否是一次性触发器。</summary>
|
||
public bool OneShot => oneShot;
|
||
|
||
/// <summary>该触发器是否已经激活过。</summary>
|
||
public bool HasFired => hasFired;
|
||
|
||
/// <summary>
|
||
/// 激活触发器,通知订阅者启动剧情。
|
||
/// </summary>
|
||
[Button("测试触发 (Fire)", ButtonSizes.Small)]
|
||
[GUIColor(0.3f, 0.8f, 1f)]
|
||
public virtual void Fire()
|
||
{
|
||
if (oneShot && hasFired)
|
||
{
|
||
return;
|
||
}
|
||
|
||
if (string.IsNullOrEmpty(storyId))
|
||
{
|
||
Debug.LogWarning($"[NarrativeTrigger] {gameObject.name} 触发失败:未配置 storyId。");
|
||
return;
|
||
}
|
||
|
||
hasFired = true;
|
||
OnNarrativeTriggerFired?.Invoke(storyId);
|
||
}
|
||
|
||
/// <summary>
|
||
/// 重置触发状态(允许在 oneShot 模式下重新触发)。
|
||
/// </summary>
|
||
[Button("重置激活状态 (Reset)", ButtonSizes.Small)]
|
||
public virtual void ResetTrigger()
|
||
{
|
||
hasFired = false;
|
||
}
|
||
}
|
||
}
|