107 lines
3.6 KiB
C#
107 lines
3.6 KiB
C#
using System;
|
|
using UnityEngine;
|
|
|
|
namespace AibisDream.SaveSystem
|
|
{
|
|
public readonly struct AnchorCaptureSpec
|
|
{
|
|
public string SceneSoName { get; }
|
|
public string YarnProjectId { get; }
|
|
public string NodeName { get; }
|
|
public bool StartDialogueOnRestore { get; }
|
|
|
|
public AnchorCaptureSpec(
|
|
string sceneSoName,
|
|
string yarnProjectId,
|
|
string nodeName,
|
|
bool startDialogueOnRestore)
|
|
{
|
|
SceneSoName = sceneSoName;
|
|
YarnProjectId = yarnProjectId;
|
|
NodeName = nodeName;
|
|
StartDialogueOnRestore = startDialogueOnRestore;
|
|
}
|
|
|
|
public bool IsComplete =>
|
|
!string.IsNullOrWhiteSpace(SceneSoName)
|
|
&& !string.IsNullOrWhiteSpace(YarnProjectId)
|
|
&& !string.IsNullOrWhiteSpace(NodeName);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 从运行时组装 <see cref="SaveSnapshot"/>(纯内存,不写盘)。
|
|
/// <para>
|
|
/// 流程:元数据 → 场景 → 锚点(含宏观章节)→ Yarn 变量 → 各 Provider.Capture。
|
|
/// scene / anchor 由框架直管;其余子系统通过 Provider 写入 sections。
|
|
/// </para>
|
|
/// </summary>
|
|
public static class SnapshotCapture
|
|
{
|
|
/// <summary>捕获当前完整快照。调用前需已注册全部 provider。</summary>
|
|
public static SaveSnapshot Capture(
|
|
YarnVariableStorage storage,
|
|
AnchorCaptureSpec anchorSpec)
|
|
{
|
|
if (!anchorSpec.IsComplete)
|
|
{
|
|
throw new ArgumentException(
|
|
"Snapshot anchor requires TalkScene, YarnProject and node name.",
|
|
nameof(anchorSpec));
|
|
}
|
|
|
|
SnapshotRegistry.ValidateRequiredProviders();
|
|
|
|
var snapshot = new SaveSnapshot
|
|
{
|
|
gameVersion = Application.version,
|
|
savedAt = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")
|
|
};
|
|
|
|
CaptureScene(snapshot);
|
|
CaptureAnchor(snapshot, anchorSpec);
|
|
CaptureYarnVariables(storage, snapshot);
|
|
|
|
foreach (var provider in SnapshotRegistry.GetOrderedProviders())
|
|
{
|
|
var dto = provider.Capture();
|
|
if (dto == null) continue;
|
|
snapshot.sections[provider.SaveId] = dto;
|
|
}
|
|
|
|
snapshot.schemaVersion = SaveSnapshotSchema.CurrentVersion;
|
|
return snapshot;
|
|
}
|
|
|
|
private static void CaptureScene(SaveSnapshot snapshot)
|
|
{
|
|
var sceneLoader = SceneLoader.Instance;
|
|
snapshot.scene = new SceneSnapshotDto
|
|
{
|
|
sceneName = sceneLoader != null ? sceneLoader.CurrentSceneName : null
|
|
};
|
|
}
|
|
|
|
private static void CaptureAnchor(SaveSnapshot snapshot, AnchorCaptureSpec anchorSpec)
|
|
{
|
|
snapshot.anchor = new AnchorSnapshot
|
|
{
|
|
sceneSoName = anchorSpec.SceneSoName,
|
|
yarnProjectId = anchorSpec.YarnProjectId,
|
|
nodeName = anchorSpec.NodeName,
|
|
startDialogueOnRestore = anchorSpec.StartDialogueOnRestore
|
|
};
|
|
}
|
|
|
|
private static void CaptureYarnVariables(YarnVariableStorage storage, SaveSnapshot snapshot)
|
|
{
|
|
var (floats, strings, bools) = storage.GetAllVariables();
|
|
snapshot.yarnVariables = new YarnVariablesSnapshot
|
|
{
|
|
floats = floats ?? new(),
|
|
strings = strings ?? new(),
|
|
bools = bools ?? new()
|
|
};
|
|
}
|
|
}
|
|
}
|