Why does a function's local variable of type AssetID resolves to None?

Hello, While trying to understand the AssetID variable type, I stumbled upon a problem that I don’t get.

I have a custom DataAsset called MyDataAsset created in code:

UCLASS(BlueprintType)
class ASSETIDTEST_API UMyDataAsset : public UDataAsset
{
	GENERATED_BODY()
public:
	UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Data Asset")
	FString String;
};

Then I created an asset called NewDataAsset of type MyDataAsset:

Then I creat an Actor with a NewDataAsset variable of type AssetID, and a function that prints the String value:

58095-captura2.jpg

But if I use instead a local variable, the Resolve AssetID node resturns None:

58097-captura3.jpg

Why is this happening? I can’t create objects using an AssetID with local variables?

Hey,

The idea of Asset ID is to keep weak reference to an asset on your hard disk it can be anything!, It is I think C++ equivalent of FStringAssetReference/TAssetPtr ( look : [HERE][1] ).

To give you a bit of an outline as to why it is so important. Think about a scenario where you have references to say e.g 1000 textures on hard disk, it will stall your main thread if you try and load 1000 textures into memory all at once on game thread, you should avoid this and always show some kind of throbber or wait symbol whilst loading a large asset ( can be anything ).

So to answer your question, a better way to do it would be to do an async/non blocking load which notifies you via delegate callback once the asset is done loading. See image below which takes AssetID as input parameter and triggers output once asset is done loaded with loaded asset pointer.

Use that function to fire off an async load and then use the output object and it should not be None anymore. Hope this helps

Thank you.

59557-capture.png

Ohh I see. Thank you, it is very useful information !

The LoadAsset node is not available inside functions thought. And I just realized that the Local AssetID Variable loses it’s default value:

59565-defaultvaluelost.jpg

Maybe it doesn’t make sense to use AssetID type variable as local variables inside functions?

LoadAsset node is global you should be able to use it where ever necessary. And yes you should keep AssetID under class scope not within function scope as it will get garbage collected once the function goes out of scope

I just did a test case, by creating a data table with a structure and use

UPROPERTY(Category = WheelSetData, EditDefaultsOnly)
TAssetPtr<UStaticMesh> RightMesh;

And when I did get row and called load asset it did an async load for that mesh and did a call back. Image below

Functions can’t use Latent operations (functions that may take some time, then call back - note the little clock in the top right of the node). Use an event to do the actual LoadAsset process, then call another function or event to handle the loaded asset when the LoadAsset ‘Completed’ pin is executed.

Local Variables are ‘recreated’ each time a function is called. Use the full blueprint scope variables (‘variable’ without the ‘local’) if you need the content to be retained for the future. If you need multiples, use an array.