天天看點

UE4_資源硬加載和軟加載

這部分對于很多小項目,直接通過硬加載的方式就可以完成需求。資源的軟加載的方式可以降低記憶體在某一瞬間的暴增,是以合理的設計資源的加載方式,在一定程度上可以優化項目。

硬加載方式

對象A引用對象B,導緻對象A被加載時,B也被加載
           
  1. 直接屬性
/** construction start sound stinger */
UPROPERTY(EditDefaultsOnly, Category=Mesh)
UStaticMesh* MeshData;
           
  1. 構造時引用

    ConstructorHelpers::FObjectFinder<> 可以實作模型,貼圖,檔案,特效,材質等加載

    該方法隻能在構造中使用

static ConstructorHelpers::FObjectFinder<UStaticMesh> meshIns(
TEXT("StaticMesh'/Game/IndustryPropsPack6/Meshes/SM_Rack01.SM_Rack01'"));
	if (meshIns.Object)
	{
		workMesh->SetStaticMesh(meshIns.Object);
	}
	
           

FObjectFinder<> 和 FClassFinder 的差別

static ConstructorHelpers::FClassFinder<AActor> BP_MyActor(TEXT("Blueprint'/Game/BP_MyActor.BP_MyActor_C'"));
	if (BP_MyActor.Succeeded())
	{
		 BPMyActorClass = BP_MyActor.Class;		
	}
	
	static ConstructorHelpers::FObjectFinder<UClass> bpClassFinder(TEXT("Blueprint'/Game/BP_MyActor.BP_MyActor_C'"));
	if (bpClassFinder.Object)
	{
		UClass* bpClass = bpClassFinder.Object;
	}

           

軟加載方式

對象A通過間接機制(字元串形式的對象路徑)引用B
           
  1. FStringAssetReferences
  2. TAssetPtr AssetPtr基本上就是一個封裝了 FStringAssetReference 的 TWeakObjectPtr ,它使用一個特定的類作為模闆,以便限制編輯器使用者界面.
UPROPERTY(EditAnywhere)
		UStaticMeshComponent* workMesh;
		
UPROPERTY(EditDefaultsOnly,Category="BulletType")
		TAssetPtr<UStaticMesh> BaseMesh;


void ABackPackage::BeginPlay()
{
	Super::BeginPlay();
	workMesh->SetStaticMesh(GetLazyLoadedMesh());
}

// 這個方法要是在構造中調用,會出現給component 指派出現失效的問題
UStaticMesh* ABackPackage::GetLazyLoadedMesh()
{
	// 這個方法要是在構造中調用,會出現給component 指派出現失效的問題
	FStreamableManager* Streamble = new FStreamableManager();
	// 檢查資源是否已經準備好,可供通路
	if (BaseMesh.IsPending())
	{
		// ToStringReference() 獲得資源的引用路徑
		const FStringAssetReference& AssetRef = BaseMesh.ToStringReference();
		// 資源的異步加載
		BaseMesh = Cast<UStaticMesh>(Streamble->LoadSynchronous(AssetRef));
	}
	// 解除對資源的引用
	return BaseMesh.Get();
}

           

同步加載方式和異步加載方式

LoadObject<>()

StaticLoadObject()

,前兩個方法以同步方式加載資産,這可能會導緻幀速率突增

FStreamingManager

下的方法提供了異步加載的方式

參考上标題代碼和我的另一篇部落格文章UE4_Content目錄資源檢索以及異步載入資源

查找、加載對象

FindObject<>()

可以在 UObject 已加載或已建立時獲得它。

LoadObject<>()

可以在對象未加載時将其加載

關于StaticLoadClass 和 LoadClass

1  UMaterial* mt1 = LoadObject<UMaterial>(nullptr, TEXT("/Game/Map/Materials/grass.grass"));
2 UMaterial* mt2 = (UMaterial*)StaticLoadObject( T::StaticClass(), nullptr, TEXT("/Game/Map/Materials/grass.grass"));
           

1和2的兩種方式寫法是等價的

StaticLoadClass 應該是早期版本,Load應該是後來有的

LoadClass與LoadObject

LoadClass

  1. 加載藍圖時,要帶字尾_C,一般用來加載藍圖資源
  2. 建立藍圖時,選擇的父類名稱作為類型

LoadObject

  • 加載藍圖時,不需要加字尾

FObjectFinder FClassFinder

FObjectFinder 是對LoadObject的封裝
FClassFinder 内部調用的是LoadObject
           

FindObject

// 通過名字查找
UClass* ActorRef = FindObject<UClass>(ANY_PACKAGE,*FString("AActor"));
//擷取到UEnum
UEnum* EnumPtr=FindObject<UEnum>((UObject*)ANY_PACKAGE,*FString("EMyEnum"),true);
EnumPtr->GetEnumName((int32)0));	//擷取到第0個枚舉的名字
           

UClass 與 UObject的關系

UClass 與 UObject的關系
	UObject
	作用:為對象系統的基類
	功能
		建立子對象
		對象Destroy相關事件處理
		對象編輯相關事件
		序列化
		執行腳本
		從config檔案讀取或儲存成員變量配置
UClass
	作用:定義一個資料結構描述類的資訊,這個資料結構叫中繼資料。UClass 不僅僅可以描述C++,
	也可以描述UBlueprint
兩者可以互相獲得對方的執行個體
	UObject::StaticClass
	UClass::GetDefaultObject
           

繼續閱讀