重构载入完成的回调 C++友好
支持静态回调
This commit is contained in:
parent
9e68d7f7e8
commit
e29ca2d8aa
@ -9,23 +9,57 @@ UAutoSaveSubsystem::UAutoSaveSubsystem(const class FObjectInitializer & ObjectIn
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void UAutoSaveSubsystem::GetSaveStructInfosWithoutData(TArray<FSaveStructInfo>& OutSaveStructInfos) const
|
FString UAutoSaveSubsystem::GetSaveStructDebugString() const
|
||||||
{
|
{
|
||||||
OutSaveStructInfos.SetNum(StructInfos.Num());
|
FString Result;
|
||||||
|
|
||||||
int32 Index = 0;
|
#if !(UE_BUILD_SHIPPING || UE_BUILD_TEST)
|
||||||
|
|
||||||
for (const TPair<FString, TUniquePtr<FSaveStructInfo>>& Info : StructInfos)
|
for (const TPair<FString, TUniquePtr<FSaveStructInfo>>& Info : StructInfos)
|
||||||
{
|
{
|
||||||
OutSaveStructInfos[Index].Filename = Info.Value->Filename;
|
Result.Append(Info.Value->Filename);
|
||||||
OutSaveStructInfos[Index].Struct = Info.Value->Struct;
|
|
||||||
OutSaveStructInfos[Index].State = Info.Value->State;
|
|
||||||
OutSaveStructInfos[Index].RefConut = Info.Value->RefConut;
|
|
||||||
OutSaveStructInfos[Index].LastRefConut = Info.Value->LastRefConut;
|
|
||||||
OutSaveStructInfos[Index].LastSaveTime = Info.Value->LastSaveTime;
|
|
||||||
|
|
||||||
++Index;
|
Result.Append(TEXT(" - "));
|
||||||
|
|
||||||
|
Result.Append(Info.Value->Struct->GetName());
|
||||||
|
|
||||||
|
Result.Append(TEXT(" - "));
|
||||||
|
|
||||||
|
switch (Info.Value->State)
|
||||||
|
{
|
||||||
|
case ESaveStructState::Preload:
|
||||||
|
Result.Append(TEXT("Preload"));
|
||||||
|
break;
|
||||||
|
case ESaveStructState::Loading:
|
||||||
|
Result.Append(TEXT("Loading"));
|
||||||
|
break;
|
||||||
|
case ESaveStructState::Idle:
|
||||||
|
Result.Append(TEXT("Idle"));
|
||||||
|
break;
|
||||||
|
case ESaveStructState::Saving:
|
||||||
|
Result.Append(TEXT("Saving"));
|
||||||
|
break;
|
||||||
|
default: checkNoEntry();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Result.Append(TEXT(" - "));
|
||||||
|
|
||||||
|
Result.Append(FString::Printf(TEXT("%d"), Info.Value->RefConut));
|
||||||
|
|
||||||
|
Result.Append(TEXT(" - "));
|
||||||
|
|
||||||
|
Result.Append(FString::Printf(TEXT("%d"), Info.Value->LastRefConut));
|
||||||
|
|
||||||
|
Result.Append(TEXT(" - "));
|
||||||
|
|
||||||
|
Result.Append(FString::Printf(TEXT("%f"), (FDateTime::Now() - Info.Value->LastSaveTime).GetTotalSeconds()));
|
||||||
|
|
||||||
|
Result.Append(TEXT("\n"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return Result;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32 UAutoSaveSubsystem::GetIdleThreadNum() const
|
int32 UAutoSaveSubsystem::GetIdleThreadNum() const
|
||||||
@ -40,7 +74,7 @@ int32 UAutoSaveSubsystem::GetIdleThreadNum() const
|
|||||||
return Result;
|
return Result;
|
||||||
}
|
}
|
||||||
|
|
||||||
FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScriptStruct * ScriptStruct, FSaveStructLoadDelegate OnLoaded)
|
FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScriptStruct * ScriptStruct)
|
||||||
{
|
{
|
||||||
if (StructInfos.Contains(Filename))
|
if (StructInfos.Contains(Filename))
|
||||||
{
|
{
|
||||||
@ -55,15 +89,6 @@ FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScr
|
|||||||
// Increase the reference count of SaveStruct by one, and then decrease it accordingly in UAutoSaveSubsystem::RemoveSaveStructRef
|
// Increase the reference count of SaveStruct by one, and then decrease it accordingly in UAutoSaveSubsystem::RemoveSaveStructRef
|
||||||
StructInfo->RefConut++;
|
StructInfo->RefConut++;
|
||||||
|
|
||||||
if (StructInfo->State == ESaveStructState::Preload || StructInfo->State == ESaveStructState::Loading)
|
|
||||||
{
|
|
||||||
StructInfo->OnLoaded.Add(OnLoaded);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
OnLoaded.ExecuteIfBound(Filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (FSaveStruct*)StructInfo->Data.GetData();
|
return (FSaveStruct*)StructInfo->Data.GetData();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -87,7 +112,6 @@ FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScr
|
|||||||
NewStructInfo->LastSaveTime = FDateTime::Now();
|
NewStructInfo->LastSaveTime = FDateTime::Now();
|
||||||
NewStructInfo->Data.SetNumUninitialized(ScriptStruct->GetStructureSize());
|
NewStructInfo->Data.SetNumUninitialized(ScriptStruct->GetStructureSize());
|
||||||
ScriptStruct->InitializeStruct(NewStructInfo->Data.GetData());
|
ScriptStruct->InitializeStruct(NewStructInfo->Data.GetData());
|
||||||
NewStructInfo->OnLoaded.Add(OnLoaded);
|
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -103,7 +127,6 @@ FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScr
|
|||||||
NewStructInfo->LastSaveTime = FDateTime::Now();
|
NewStructInfo->LastSaveTime = FDateTime::Now();
|
||||||
NewStructInfo->Data.SetNumUninitialized(ScriptStruct->GetStructureSize());
|
NewStructInfo->Data.SetNumUninitialized(ScriptStruct->GetStructureSize());
|
||||||
ScriptStruct->InitializeStruct(NewStructInfo->Data.GetData());
|
ScriptStruct->InitializeStruct(NewStructInfo->Data.GetData());
|
||||||
NewStructInfo->OnLoaded.Add(OnLoaded);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ScriptStructHooker.Add(Filename, ScriptStruct);
|
ScriptStructHooker.Add(Filename, ScriptStruct);
|
||||||
@ -114,6 +137,42 @@ FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString& Filename, UScr
|
|||||||
return (FSaveStruct*)StructInfos[Filename]->Data.GetData();
|
return (FSaveStruct*)StructInfos[Filename]->Data.GetData();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString & Filename, UScriptStruct * ScriptStruct, FSaveStructLoadDelegate LoadCallback)
|
||||||
|
{
|
||||||
|
FSaveStruct* Result = AddSaveStructRef(Filename, ScriptStruct);
|
||||||
|
|
||||||
|
if (!LoadCallback.IsBound()) return Result;
|
||||||
|
|
||||||
|
if (!Result) return nullptr;
|
||||||
|
|
||||||
|
if (!LoadDelegates.Contains(Filename))
|
||||||
|
{
|
||||||
|
LoadDelegates.Add(Filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
LoadDelegates[Filename].Add(LoadCallback);
|
||||||
|
|
||||||
|
return Result;
|
||||||
|
}
|
||||||
|
|
||||||
|
FSaveStruct * UAutoSaveSubsystem::AddSaveStructRef(const FString & Filename, UScriptStruct * ScriptStruct, FSaveStructLoadDynamicDelegate LoadCallback)
|
||||||
|
{
|
||||||
|
FSaveStruct* Result = AddSaveStructRef(Filename, ScriptStruct);
|
||||||
|
|
||||||
|
if (!LoadCallback.IsBound()) return Result;
|
||||||
|
|
||||||
|
if (!Result) return nullptr;
|
||||||
|
|
||||||
|
if (!LoadDynamicDelegates.Contains(Filename))
|
||||||
|
{
|
||||||
|
LoadDynamicDelegates.Add(Filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
LoadDynamicDelegates[Filename].Add(LoadCallback);
|
||||||
|
|
||||||
|
return Result;
|
||||||
|
}
|
||||||
|
|
||||||
void UAutoSaveSubsystem::RemoveSaveStructRef(const FString& Filename)
|
void UAutoSaveSubsystem::RemoveSaveStructRef(const FString& Filename)
|
||||||
{
|
{
|
||||||
if (StructInfos.Contains(Filename))
|
if (StructInfos.Contains(Filename))
|
||||||
@ -163,7 +222,6 @@ UAutoSaveSubsystem::FStructLoadOrSaveTask::~FStructLoadOrSaveTask()
|
|||||||
case ESaveStructState::Loading:
|
case ESaveStructState::Loading:
|
||||||
StructInfoPtr->State = ESaveStructState::Idle;
|
StructInfoPtr->State = ESaveStructState::Idle;
|
||||||
StructInfoPtr->Data = DataCopy;
|
StructInfoPtr->Data = DataCopy;
|
||||||
StructInfoPtr->OnLoaded.Broadcast(StructInfoPtr->Filename);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ESaveStructState::Saving:
|
case ESaveStructState::Saving:
|
||||||
@ -317,6 +375,59 @@ void UAutoSaveSubsystem::HandleTaskDone()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void UAutoSaveSubsystem::HandleLoadDelegates()
|
||||||
|
{
|
||||||
|
// Delegates
|
||||||
|
{
|
||||||
|
TArray<FString> DelegatesToRemove;
|
||||||
|
|
||||||
|
for (const TPair<FString, FSaveStructLoadDelegates>& Delegates : LoadDelegates)
|
||||||
|
{
|
||||||
|
if (!StructInfos.Contains(Delegates.Key))
|
||||||
|
{
|
||||||
|
DelegatesToRemove.Add(Delegates.Key);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (StructInfos[Delegates.Key]->State == ESaveStructState::Idle || StructInfos[Delegates.Key]->State == ESaveStructState::Saving)
|
||||||
|
{
|
||||||
|
Delegates.Value.Broadcast(Delegates.Key);
|
||||||
|
DelegatesToRemove.Add(Delegates.Key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const FString& Filename : DelegatesToRemove)
|
||||||
|
{
|
||||||
|
LoadDelegates.Remove(Filename);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// DynamicDelegates
|
||||||
|
{
|
||||||
|
TArray<FString> DynamicDelegatesToRemove;
|
||||||
|
|
||||||
|
for (const TPair<FString, FSaveStructLoadDynamicDelegates>& Delegates : LoadDynamicDelegates)
|
||||||
|
{
|
||||||
|
if (!StructInfos.Contains(Delegates.Key))
|
||||||
|
{
|
||||||
|
DynamicDelegatesToRemove.Add(Delegates.Key);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (StructInfos[Delegates.Key]->State == ESaveStructState::Idle || StructInfos[Delegates.Key]->State == ESaveStructState::Saving)
|
||||||
|
{
|
||||||
|
Delegates.Value.Broadcast(Delegates.Key);
|
||||||
|
DynamicDelegatesToRemove.Add(Delegates.Key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const FString& Filename : DynamicDelegatesToRemove)
|
||||||
|
{
|
||||||
|
LoadDynamicDelegates.Remove(Filename);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void UAutoSaveSubsystem::Initialize(FSubsystemCollectionBase & Collection)
|
void UAutoSaveSubsystem::Initialize(FSubsystemCollectionBase & Collection)
|
||||||
{
|
{
|
||||||
if (MaxThreadNum > 0)
|
if (MaxThreadNum > 0)
|
||||||
@ -355,4 +466,5 @@ void UAutoSaveSubsystem::Tick(float DeltaTime)
|
|||||||
{
|
{
|
||||||
HandleTaskDone();
|
HandleTaskDone();
|
||||||
HandleTaskStart();
|
HandleTaskStart();
|
||||||
|
HandleLoadDelegates();
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
#include "Kismet/GameplayStatics.h"
|
#include "Kismet/GameplayStatics.h"
|
||||||
|
|
||||||
bool UAutoSaveBlueprintLibrary::AddSaveStructRef(UObject * WorldContextObject, const FString & Filename, UScriptStruct * ScriptStruct, FSaveStructLoadDelegate OnLoaded)
|
bool UAutoSaveBlueprintLibrary::AddSaveStructRef(UObject * WorldContextObject, const FString & Filename, UScriptStruct * ScriptStruct, FSaveStructLoadDynamicDelegate LoadCallback)
|
||||||
{
|
{
|
||||||
UGameInstance* GameInstance = UGameplayStatics::GetGameInstance(WorldContextObject);
|
UGameInstance* GameInstance = UGameplayStatics::GetGameInstance(WorldContextObject);
|
||||||
|
|
||||||
@ -12,7 +12,7 @@ bool UAutoSaveBlueprintLibrary::AddSaveStructRef(UObject * WorldContextObject, c
|
|||||||
|
|
||||||
if (!AutoSaveSubsystem) return false;
|
if (!AutoSaveSubsystem) return false;
|
||||||
|
|
||||||
return AutoSaveSubsystem->AddSaveStructRef(Filename, ScriptStruct, OnLoaded) != nullptr;
|
return AutoSaveSubsystem->AddSaveStructRef(Filename, ScriptStruct, LoadCallback) != nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
void UAutoSaveBlueprintLibrary::RemoveSaveStructRef(UObject * WorldContextObject, const FString & Filename)
|
void UAutoSaveBlueprintLibrary::RemoveSaveStructRef(UObject * WorldContextObject, const FString & Filename)
|
||||||
|
@ -7,9 +7,6 @@
|
|||||||
USTRUCT(BlueprintType)
|
USTRUCT(BlueprintType)
|
||||||
struct AUTOSAVE_API FSaveStruct { GENERATED_BODY() };
|
struct AUTOSAVE_API FSaveStruct { GENERATED_BODY() };
|
||||||
|
|
||||||
DECLARE_DYNAMIC_DELEGATE_OneParam(FSaveStructLoadDelegate, const FString&, Filename);
|
|
||||||
DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FSaveStructLoadDelegates, const FString&, Filename);
|
|
||||||
|
|
||||||
UENUM(BlueprintType, Category = "AutoSave")
|
UENUM(BlueprintType, Category = "AutoSave")
|
||||||
enum class ESaveStructState : uint8
|
enum class ESaveStructState : uint8
|
||||||
{
|
{
|
||||||
@ -19,38 +16,31 @@ enum class ESaveStructState : uint8
|
|||||||
Saving,
|
Saving,
|
||||||
};
|
};
|
||||||
|
|
||||||
USTRUCT(BlueprintType)
|
|
||||||
struct AUTOSAVE_API FSaveStructInfo
|
struct AUTOSAVE_API FSaveStructInfo
|
||||||
{
|
{
|
||||||
GENERATED_BODY()
|
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
FString Filename;
|
FString Filename;
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
UScriptStruct* Struct;
|
UScriptStruct* Struct;
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
ESaveStructState State;
|
ESaveStructState State;
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
int32 RefConut;
|
int32 RefConut;
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
int32 LastRefConut;
|
int32 LastRefConut;
|
||||||
|
|
||||||
UPROPERTY(BlueprintReadWrite, Category = "AutoSave")
|
|
||||||
FDateTime LastSaveTime;
|
FDateTime LastSaveTime;
|
||||||
|
|
||||||
UPROPERTY()
|
|
||||||
TArray<uint8> Data;
|
TArray<uint8> Data;
|
||||||
// FSaveStruct* Data;
|
// FSaveStruct* Data;
|
||||||
|
|
||||||
UPROPERTY()
|
|
||||||
FSaveStructLoadDelegates OnLoaded;
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
DECLARE_DELEGATE_OneParam(FSaveStructLoadDelegate, const FString&);
|
||||||
|
DECLARE_MULTICAST_DELEGATE_OneParam(FSaveStructLoadDelegates, const FString&);
|
||||||
|
|
||||||
|
DECLARE_DYNAMIC_DELEGATE_OneParam(FSaveStructLoadDynamicDelegate, const FString&, Filename);
|
||||||
|
DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FSaveStructLoadDynamicDelegates, const FString&, Filename);
|
||||||
|
|
||||||
UCLASS(Config = Engine, DefaultConfig)
|
UCLASS(Config = Engine, DefaultConfig)
|
||||||
class AUTOSAVE_API UAutoSaveSubsystem : public UGameInstanceSubsystem, public FTickableGameObject
|
class AUTOSAVE_API UAutoSaveSubsystem : public UGameInstanceSubsystem, public FTickableGameObject
|
||||||
{
|
{
|
||||||
@ -69,13 +59,17 @@ public:
|
|||||||
UPROPERTY(Config, EditAnywhere, Category = "AutoSave")
|
UPROPERTY(Config, EditAnywhere, Category = "AutoSave")
|
||||||
FTimespan SaveWaitTime = FTimespan(ETimespan::MaxTicks);
|
FTimespan SaveWaitTime = FTimespan(ETimespan::MaxTicks);
|
||||||
|
|
||||||
UFUNCTION(BlueprintCallable, Category = "AutoSave")
|
UFUNCTION(BlueprintPure, Category = "AutoSave", meta = (DevelopmentOnly))
|
||||||
void GetSaveStructInfosWithoutData(TArray<FSaveStructInfo>& OutSaveStructInfos) const;
|
FString GetSaveStructDebugString() const;
|
||||||
|
|
||||||
UFUNCTION(BlueprintPure, Category = "AutoSave")
|
UFUNCTION(BlueprintPure, Category = "AutoSave")
|
||||||
int32 GetIdleThreadNum() const;
|
int32 GetIdleThreadNum() const;
|
||||||
|
|
||||||
FSaveStruct* AddSaveStructRef(const FString& Filename, UScriptStruct* ScriptStruct = nullptr, FSaveStructLoadDelegate OnLoaded = FSaveStructLoadDelegate());
|
FSaveStruct* AddSaveStructRef(const FString& Filename, UScriptStruct* ScriptStruct = nullptr);
|
||||||
|
|
||||||
|
FSaveStruct* AddSaveStructRef(const FString& Filename, UScriptStruct* ScriptStruct, FSaveStructLoadDelegate LoadCallback);
|
||||||
|
|
||||||
|
FSaveStruct* AddSaveStructRef(const FString& Filename, UScriptStruct* ScriptStruct, FSaveStructLoadDynamicDelegate LoadCallback);
|
||||||
|
|
||||||
void RemoveSaveStructRef(const FString& Filename);
|
void RemoveSaveStructRef(const FString& Filename);
|
||||||
|
|
||||||
@ -114,6 +108,11 @@ private:
|
|||||||
|
|
||||||
void HandleTaskDone();
|
void HandleTaskDone();
|
||||||
|
|
||||||
|
TMap<FString, FSaveStructLoadDelegates> LoadDelegates;
|
||||||
|
TMap<FString, FSaveStructLoadDynamicDelegates> LoadDynamicDelegates;
|
||||||
|
|
||||||
|
void HandleLoadDelegates();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
//~ Begin USubsystem Interface
|
//~ Begin USubsystem Interface
|
||||||
|
@ -14,7 +14,7 @@ class AUTOSAVE_API UAutoSaveBlueprintLibrary : public UBlueprintFunctionLibrary
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
UFUNCTION(BlueprintCallable, Category = "AutoSave", meta = (WorldContext = "WorldContextObject"))
|
UFUNCTION(BlueprintCallable, Category = "AutoSave", meta = (WorldContext = "WorldContextObject"))
|
||||||
static bool AddSaveStructRef(UObject* WorldContextObject, const FString& Filename, UScriptStruct* ScriptStruct, FSaveStructLoadDelegate OnLoaded);
|
static bool AddSaveStructRef(UObject* WorldContextObject, const FString& Filename, UScriptStruct* ScriptStruct, FSaveStructLoadDynamicDelegate LoadCallback);
|
||||||
|
|
||||||
UFUNCTION(BlueprintCallable, Category = "AutoSave", meta = (WorldContext = "WorldContextObject"))
|
UFUNCTION(BlueprintCallable, Category = "AutoSave", meta = (WorldContext = "WorldContextObject"))
|
||||||
static void RemoveSaveStructRef(UObject* WorldContextObject, const FString& Filename);
|
static void RemoveSaveStructRef(UObject* WorldContextObject, const FString& Filename);
|
||||||
|
@ -19,7 +19,27 @@ public:
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
FORCEINLINE FSaveStructPtr(UAutoSaveSubsystem* InAutoSaveSubsystem, const FString& Filename, FSaveStructLoadDelegate OnLoaded = FSaveStructLoadDelegate())
|
FORCEINLINE FSaveStructPtr(UAutoSaveSubsystem* InAutoSaveSubsystem, const FString& Filename)
|
||||||
|
: AutoSaveSubsystem(InAutoSaveSubsystem)
|
||||||
|
, Info(nullptr)
|
||||||
|
{
|
||||||
|
if (AutoSaveSubsystem->AddSaveStructRef(Filename, SaveStructType::StaticStruct()))
|
||||||
|
{
|
||||||
|
Info = AutoSaveSubsystem->StructInfos[Filename].Get();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
FORCEINLINE FSaveStructPtr(UAutoSaveSubsystem* InAutoSaveSubsystem, const FString& Filename, FSaveStructLoadDelegate OnLoaded)
|
||||||
|
: AutoSaveSubsystem(InAutoSaveSubsystem)
|
||||||
|
, Info(nullptr)
|
||||||
|
{
|
||||||
|
if (AutoSaveSubsystem->AddSaveStructRef(Filename, SaveStructType::StaticStruct(), OnLoaded))
|
||||||
|
{
|
||||||
|
Info = AutoSaveSubsystem->StructInfos[Filename].Get();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
FORCEINLINE FSaveStructPtr(UAutoSaveSubsystem* InAutoSaveSubsystem, const FString& Filename, FSaveStructLoadDynamicDelegate OnLoaded)
|
||||||
: AutoSaveSubsystem(InAutoSaveSubsystem)
|
: AutoSaveSubsystem(InAutoSaveSubsystem)
|
||||||
, Info(nullptr)
|
, Info(nullptr)
|
||||||
{
|
{
|
||||||
|
Reference in New Issue
Block a user