Array filled in OnConstruction is empty on next call

I am attempting to create a usable list of scenecomponents for a user to select one in an array.

I have created a struct, FComponentListItem:

USTRUCT()
struct FComponentListItem
{
	GENERATED_USTRUCT_BODY()

	UPROPERTY(VisibleAnywhere, BlueprintReadWrite, Category = "Component")
	USceneComponent* ComponentInQuestion;

	UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Selection")
	bool bSelected;
};

And I have created another struct with a TArray of these structs on an ActorComponent called InteractionComp.

In my actors OnConstruction function, I call a function on InteractionComp that finds all usable scenecomponents on the actor and then creates an FComponentListItem struct and copies in the appropriate information. This should then be usable by the user. Unfortunately, I can’t find a way to populate this array in a meaningful way.

void UInteractionComp::OnConstruction(const FTransform& Transform)
{
	if (ComponentListMaster.Num() < 1)
	{
		ComponentListMaster.Empty();

		TArray<UActorComponent*> Components = GetOwner()->GetComponents().Array();

		for (auto& Component : Components)
		{
			FComponentListItem Item;

			Item.ComponentInQuestion = Cast<USceneComponent>(Component);
			Item.bSelected = false;

			ComponentListMaster.Add(Item);
		}
	}
}

Every time this code runs, (ComponentListMaster < 1) returns true, even if the list was populated with 5 members in the previous run.

A few items of feedback:

  • I don’t think this fixes the problem, but if you’re using FComponentListItem in blueprints, it should have USTRUCT(BlueprintType).
  • How is ComponentListMaster declared? If not marked with UPROPERTY, the value may get reset when your object is duplicated (e.g. when play starts).
  • When you play the game in editor, all actors are copied before play. That’s why when an actor is moved or changed in-game, it is reset when you exit PIE. If you expect changes from play mode to persist back to the editor, you’re going to need a cleverer approach.
  • How is your Actor’s OnConstruction method defined? Are you sure it’s calling UInteractionComp::OnConstruction?

I typically omit certain code snippets to make these more readable.

I had BlueprintType in the USTRUCT macro and had removed it wondering if that was causing the issue. There is no change.

The ComponentListMaster is initialized as so:

UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Master")
TArray<FComponentListItem> ComponentListMaster;

and the OnConstruction is defined as:

void OnConstruction(const FTransform& Transform);

This was defined before I knew that ActorComponents don’t get an OnConstruction function, so I had to tie it to an interactable actor that could call the function. I had plenty of logging in it, so I know that it’s being called correctly.

As for PIE, this is all being done in map setup, and I am not playing the map when I change. All values are being changed in details panel.

Thank you for the reply!

Did you find an answer to this issue?