Payback 0.0.1
CK Graduation Project
로딩중...
검색중...
일치하는것 없음
DataBundleRegistry.h
이 파일의 문서화 페이지로 가기
1// Fill out your copyright notice in the Description page of Project Settings.
2
3#pragma once
4
5#include "CoreMinimal.h"
6#include "Subsystems/GameInstanceSubsystem.h"
7#include "GameplayTagContainer.h"
8#include "Engine/StreamableManager.h"
10#include "CK_UE.h"
11#include "DataBundleRegistry.generated.h"
12
15DECLARE_MULTICAST_DELEGATE_OneParam(FOnBundleStateChanged, FGameplayTag /*BundleTag*/);
16
17
21UENUM(BlueprintType)
22enum class EDataBundleState : uint8
23{
24 Unloaded UMETA(DisplayName = "언로드됨"),
25 Loading UMETA(DisplayName = "로딩 중"),
26 Loaded UMETA(DisplayName = "로드됨"),
27};
28
29
40UCLASS()
41class CK_UE_API UDataBundleRegistry : public UGameInstanceSubsystem
42{
43 GENERATED_BODY()
44
45public:
47 virtual void Initialize(FSubsystemCollectionBase& Collection) override;
48
50 virtual void Deinitialize() override;
51
53 UFUNCTION(BlueprintCallable, Category = "Bundle")
54 static UDataBundleRegistry* Get();
55
56public:
63 void RequestLoad(FGameplayTag BundleTag, TFunction<void(UDataBundleDefinition*)> OnReady = nullptr);
64
73 void RequestLoad(const FGameplayTagContainer& BundleTags, TFunction<void(TArray<UDataBundleDefinition*>)> OnAllReady);
74
80 UFUNCTION(BlueprintCallable, Category = "Bundle")
81 void Release(FGameplayTag BundleTag);
82
88 UFUNCTION(BlueprintCallable, Category = "Bundle")
89 void ForceRelease(FGameplayTag BundleTag);
90
97 UFUNCTION(BlueprintCallable, Category = "Bundle")
98 EDataBundleState GetState(FGameplayTag BundleTag) const;
99
106 UFUNCTION(BlueprintCallable, Category = "Bundle")
107 bool IsLoaded(FGameplayTag BundleTag) const;
108
114 UFUNCTION(BlueprintCallable, Category = "Bundle")
115 TArray<FGameplayTag> GetLoadedBundleTags() const;
116
124 void ReleaseUnusedBundles(const FGameplayTagContainer& RequiredTags);
125
137 template <typename T>
138 T* GetBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr<T>& AssetPtr) const;
139
150 template <typename T>
151 void RequestBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr<T>& AssetPtr, TFunction<void(T*)> OnReady);
152
163 template <typename T>
164 static TArray<T*> GetBundleAssetsOfType(const UDataBundleDefinition* BundleDef);
165
166 template <typename T>
167 static T* GetBundleAssetByTag(FGameplayTag BundleTag);
168
179 UFUNCTION(BlueprintCallable, Category = "Bundle")
180 static TArray<UDataBundleDefinition*> FindBundleAssetsByTag(FGameplayTag BundleTag);
181
182private:
184 void ScanAndRegisterBundles();
185
187 void PreLoadBundles();
188
194 void OnAllDependenciesReady(FGameplayTag BundleTag);
195
203 void OnAssetsLoaded(FGameplayTag BundleTag);
204
210 void FlushPendingCallbacks(FGameplayTag BundleTag);
211
212 void NotifyBundleLoadedToAssets(const TArray<UObject*>& Assets, FGameplayTag BundleTag);
213 void NotifyBundleReleasedToAssets(const TArray<UObject*>& Assets, FGameplayTag BundleTag);
214
215private:
222 {
224 TSharedPtr<FStreamableHandle> Handle;
225
227 EDataBundleState State = EDataBundleState::Unloaded;
228
230 TArray<TFunction<void(UDataBundleDefinition*)>> PendingCallbacks;
231 };
232
234 UPROPERTY(Transient)
235 TMap<FGameplayTag, TObjectPtr<UDataBundleDefinition>> Definitions;
236
238 TMap<FGameplayTag, FBundleEntry> Entries;
239
241 static UDataBundleRegistry* Instance;
242};
243
244
245#pragma region Template Implementations
246
247template <typename T>
248T* UDataBundleRegistry::GetBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr<T>& AssetPtr) const
249{
250 if (IsLoaded(BundleTag) == false)
251 {
252 LOG_WARNING(LogCKAsset, "번들 '%s'이 로드되지 않은 상태에서 GetBundleAsset 호출됨.", *BundleTag.ToString());
253 return nullptr;
254 }
255
256 T* Asset = AssetPtr.Get();
257
258 if (Asset == nullptr)
259 {
260 LOG_WARNING(LogCKAsset, "번들 '%s'의 에셋 '%s'이 메모리에 없습니다.", *BundleTag.ToString(), *AssetPtr.ToString());
261 }
262
263 return Asset;
264}
265
266
267template <typename T>
269{
270 TArray<T*> Result;
271
272 if (BundleDef == nullptr)
273 {
274 return Result;
275 }
276
277 for (const TSoftObjectPtr<IDataAssetBundle>& SoftAsset : BundleDef->Assets)
278 {
279 UObject* Obj = SoftAsset.ToSoftObjectPath().ResolveObject();
280
281 if (T* TypedAsset = Cast<T>(Obj))
282 {
283 Result.Add(TypedAsset);
284 }
285 }
286
287 return Result;
288}
289
290
291template <typename T>
293{
294 for (UDataBundleDefinition* BundleDef : FindBundleAssetsByTag(BundleTag))
295 {
296 TArray<T*> Found = UDataBundleRegistry::GetBundleAssetsOfType<T>(BundleDef);
297
298 if (Found.IsEmpty())
299 {
300 continue;
301 }
302
303 return Found[0];
304 }
305
306 return nullptr;
307}
308
309
310template <typename T>
311void UDataBundleRegistry::RequestBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr<T>& AssetPtr, TFunction<void(T*)> OnReady)
312{
313 TSoftObjectPtr<T> AssetCapture = AssetPtr;
314
315 RequestLoad(BundleTag, [this, BundleTag, AssetCapture, OnReady = MoveTemp(OnReady)]()
316 {
317 T* Asset = AssetCapture.Get();
318
319 if (Asset == nullptr)
320 {
321 LOG_WARNING(LogCKAsset, "RequestBundleAsset: 번들 '%s' 로드 완료 후에도 에셋을 찾을 수 없습니다: %s", *BundleTag.ToString(), *AssetCapture.ToString());
322 }
323
324 if (OnReady)
325 {
326 OnReady(Asset);
327 }
328 });
329}
330
331#pragma endregion
#define LOG_WARNING(Category, Format,...)
Definition CK_UE.h:39
DECLARE_MULTICAST_DELEGATE_OneParam(FOnBundleStateChanged, FGameplayTag)
번들 로드/언로드 상태 변경 시 브로드캐스트되는 델리게이트.
EDataBundleState
DataBundle의 런타임 로드 상태를 나타내는 열거형.
Definition DataBundleRegistry.h:23
Definition DataBundleDefinition.h:29
TArray< TSoftObjectPtr< IDataAssetBundle > > Assets
Definition DataBundleDefinition.h:51
DataBundle의 로드/언로드를 관리하는 GameInstance 서브시스템.
Definition DataBundleRegistry.h:42
static TArray< UDataBundleDefinition * > FindBundleAssetsByTag(FGameplayTag BundleTag)
주어진 태그와 매칭되는 번들 정의 목록을 반환합니다.
Definition DataBundleRegistry.cpp:433
T * GetBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr< T > &AssetPtr) const
로드된 번들에서 특정 에셋을 동기적으로 반환합니다.
Definition DataBundleRegistry.h:248
bool IsLoaded(FGameplayTag BundleTag) const
번들이 로드 완료 상태인지 여부를 반환합니다.
Definition DataBundleRegistry.cpp:368
void RequestBundleAsset(FGameplayTag BundleTag, const TSoftObjectPtr< T > &AssetPtr, TFunction< void(T *)> OnReady)
번들을 비동기 로드한 뒤 에셋 포인터를 콜백으로 전달합니다.
Definition DataBundleRegistry.h:311
void RequestLoad(FGameplayTag BundleTag, TFunction< void(UDataBundleDefinition *)> OnReady=nullptr)
번들을 비동기 로드합니다. 로드 완료 시 OnReady 콜백을 호출합니다.
Definition DataBundleRegistry.cpp:162
static T * GetBundleAssetByTag(FGameplayTag BundleTag)
Definition DataBundleRegistry.h:292
static TArray< T * > GetBundleAssetsOfType(const UDataBundleDefinition *BundleDef)
번들 정의에 포함된 에셋 중 특정 타입에 해당하는 목록을 반환합니다.
Definition DataBundleRegistry.h:268
번들 하나의 런타임 상태를 담는 구조체.
Definition DataBundleRegistry.h:222
TSharedPtr< FStreamableHandle > Handle
에셋 스트리밍 핸들. 언로드 시 명시적으로 해제됩니다.
Definition DataBundleRegistry.h:224
TArray< TFunction< void(UDataBundleDefinition *)> > PendingCallbacks
로드 완료 시 일괄 실행할 콜백 목록.
Definition DataBundleRegistry.h:230