Download

Component initialization hook for editor-time component setup

Hey all.

I’ve got a component that I want to fill in information when it is added to an actor at edit time from other components of the actor. PostInitProperties is giving me a null ref for the GetOwner call, so I suspect that’s not what I need.

Basically, I’m trying to hook the initialization method that happens after an actor is deserialized and all its components are deserialized but at edit time and not runtime. Is that a thing? I know I can make the actor tick during edit mode, but that isn’t really what I want, I just want to initially setup a bunch of data depending on other components, then track changes to those components (which I’m assuming PostEditChange will let me do).

Anyone got a handle on the initialization/update ordering of components?

I guess I should dig into this stuff myself at some point.

PostInitProperties is confusingly named, it’s called very early, after properties are initialized to the class inherited defaults.

UActorComponent::OnRegister is called both in-editor and in-game, so that’s an option. Depending on exactly what you want, you can use a #if WITH_EDITOR guard and/or test for GetWorld()->IsGameWorld().
Problem is there’s no way as far as I’m aware to control order of initialization of components within an actor. Not all other components will necessarily have been registered by the time yours is. I assume you want to do this within your component code so it works regardless of actor? If it’s just for a specific actor class that you can edit, it should be a lot easier.

Here’s a fun one… I tried OnComponentCreated, setup some data in there. Data is collected fine, but now the USTRUCT’s I created to hold the data are read-only. What the hell?

No idea what that is.
I think OnComponentCreated is only called when you first create the component/actor, and won’t be called when you subsequently load again. Not sure, but you may have to override PostLoad too if that’s the case.

Edit: Scary post count!

And another funny one. Adding the data to the structs in OnRegister makes them readonly too!

It seems I’ve found a reasonable solution by capturing PostEditChange and updating my component there if it hasn’t already gotten data in it. So it can be refreshed by emptying my data which will automatically grab new data, otherwise it’ll use its stored data.

BLEARGH!

That’s all I’ve got to say on the matter :slight_smile:

It appears OnComponentCreated gets called anytime the construction script runs, which is afaict every time a property changes. But it has that weird issue of making properties read-only. PostEditChange seems to do the trick for now. So I’ll have to revisit this when I have more time.

Oh, right that’s because blueprint-added components are always recreated by the construction script. That may explain the read only thing too - if you change a property, that triggers construction script, which recreates the component with default property values, so your change is ignored. That’s the case if you created the component in the actual construction script anyway, as opposed to adding with AddComponent button. It’ll be different again with natively added components.

This stuff is a bit of a nightmare when you want to do anything non-standard with components.