Daily Unreal Column #30 - Instanced objects
When trying to group data for certain entity in the game, it is very common to use a C++ struct. Lesser known method is to use instanced objects.
Using a struct as a data source that is exposed to the editor (meaning its UPROPERTY) has one major drawback. It cannot be a pointer. This means that you can use this and only this specific struct type as your data source, you cannot pick which child class would you like to use. This is where instanced objects shine. They create an instance of an object inlined, allowing to modify its data, achieving same behavior as structs. The extra though comes from the fact that we can create multiple subclasses of the main object class and pick between them in the editor. Let's have a look at the examples. First, let's take a look at struct.
USTRUCT(BlueprintType)
struct FFoo
{
GENERATED_BODY()
UPROPERTY(EditDefaultsOnly)
float x;
};
USTRUCT(BlueprintType)
struct FBar : public FFoo
{
GENERATED_BODY()
UPROPERTY(EditDefaultsOnly)
float y;
};
Adding declaration for these two structs like following
UPROPERTY(EditDefaultsOnly)
FFoo Foo;
UPROPERTY(EditDefaultsOnly)
FBar Bar;
will result in following in the editor.
For instanced objects, we can declare following objects with appropriate UCLASS declarations:
UCLASS(BlueprintType, EditInlineNew, DefaultToInstanced)
class UBaseObject : public UObject
{
GENERATED_BODY()
public:
UPROPERTY(EditDefaultsOnly)
int x;
};
UCLASS()
class UFoo : public UBaseObject
{
GENERATED_BODY()
public:
UPROPERTY(EditDefaultsOnly)
int y;
};
UCLASS()
class UBar : public UBaseObject
{
GENERATED_BODY()
public:
UPROPERTY(EditDefaultsOnly)
int z;
};
and declare just the base object like this:
UPROPERTY(EditDefaultsOnly, Instanced)
TObjectPtr<UBaseObject> BaseObject;
and the result in the editor will look like this:
This allows for a very modular approach to defining data for your game.
For other real life examples, please have a look at the following two links: