Weird bug in 4.26 adding subobjects

I had the same issue at the end of this course where everything stops working and the cars just sit there. spent hours on it thinking it was me getting logging in etc. all the logging worked but still nothing moved.
Ended up disabling the subcomponents, tired adding them manually, tried rebuilding the project restarting, recompiling the blueprint etc. then one recompile it just started working again.

Not a fault of the lecture but it’s a bit flaky for a production release from unreal unless I’m doing something wrong!. So if anyone else runs into this, try changing and recompiling, make sure you recompile the blueprint in the GUI as well restart everything, rebuild the project eventually it will start working. (try adding something to the blueprint so it forces it to give you a recompile option as well)

You can see it as if you click on the subcomponents in the blueprint the details panel on the right wont be filled out correctly or blank so you wont see the go kart movement variables for example.

if anyone else has a better way please share, I had a search about but can’t find anything useful.

	MovementReplicator = CreateDefaultSubobject<UGoKartMovementReplicator>(TEXT("MovementReplicator"));
	MovementComponent = CreateDefaultSubobject<UGoKartMovementComponent>(TEXT("MovementComponent"));

I went back to this as I just hate random weirdness and being able to re-use classes like this is one of the major reasons to do it in C++ in the first place. Couldn’t find a fix I think that needs to come from Unreal but happy to be corrected if I missed something! but I do have a work around.

The workaround shows an additional major benefit of all the hard work refactoring and decoupling the code into sub object. That being reuse, it’s even more exciting than refactoring :slight_smile: we have just created 2 sub components that with a bit of extra tweaking we could drop on any actor we want to have movement or movement replication, that’s super cool.

So currently we are creating the sub objects in the constructor of the parent class GoKart.cpp then the child class (BP_GoKart) is doing the rest this is where Unreal says to do it from what I can see but… This is where this issues happen in development, when you compile it can get into a really weird state where it doesn’t register properly in the child but doesn’t fail compile either. Eventually after plenty of button mashing and restarting and re-compiling code and blueprint you get lucky and the timing works and it sorts it self out then its stable from what I can see. I would bet creating something new relying on these classes if they had not been recompiled works fine but that’s not what we are doing.

Not great when you are doing rapid iterative development cycles.

The workaround
Remove the sub component create from the constructor in GoKart.cpp

AGoKart::AGoKart()
{
 	// Set this pawn to call Tick() every frame.  You can turn this off to improve performance if you don't need it.
	PrimaryActorTick.bCanEverTick = true;

	//make sure it replicates
	bReplicates = true;
	
	//MovementReplicator = CreateDefaultSubobject<UGoKartMovementReplicator>(TEXT("MovementReplicator"));
	//MovementComponent = CreateDefaultSubobject<UGoKartMovementComponent>(TEXT("MovementComponent"));

}

Add the creating using the find class method to BeginPlay in GoKart.cpp

void AGoKart::BeginPlay()
{
	Super::BeginPlay();
	if (HasAuthority())
	{
		
		NetUpdateFrequency = 1;
	}

	
	MovementComponent = FindComponentByClass<UGoKartMovementComponent>();
	MovementReplicator = FindComponentByClass<UGoKartMovementReplicator>();
	if (IsValid(MovementComponent))
	{
		UE_LOG(LogTemp, Warning, TEXT("Movement Component Loaded"));
	}
	else
	{
		UE_LOG(LogTemp, Warning, TEXT("Movement Component Not Loaded"));
	}

	if (IsValid(MovementReplicator))
	{
		UE_LOG(LogTemp, Warning, TEXT("Replicator Component Loaded"));
	}
	else
	{
		UE_LOG(LogTemp, Warning, TEXT("Replicator Component Not Loaded"));
	}
	
}

Then recompile everything, the inherited sub components will now have gone from the BP_GoKart blueprint

Use addcomponent to re-add them in the blueprint this is why we move to beginplay as they wont be available for the constructor parent class.
adsdinchild

recompile the blueprint

If all has gone well it should all start working and be reliable when you update the subcomponents as well.

Would love to hear if anyone has a better solution!

So another interesting side effect of making this change, I was getting loads of editor crashes when compiling when the c++ sub objects were created in the header. Since moving that out and binding them later at begin play I’ve not had one editor crash as I’ve been working through the rest of the course.

I have sort of done this to death, but stumbled on some more info that’s useful.

Apparently Hot reload which is enabled by default in Unreal 4.26 and previous version is deprecated and known to cause the issues seen back to 4.19 apparently.

Live Coding introduced in 4.22 which is listed as experimental is replacing it and you can enable it in the compile settings (Windows only tho!)
livecoding

There’s a really good article here that runs through trouble shooting and fixing hot reload issues and explains limitations of live code and hot reload with suggested workflows.

Hot Reload and Live Coding | UE4 Community Wiki

Essentially it boils down to
Any changes potentially impacting class default object modifications (exactly the issue many have had) close the editor, compile from IDE and restart editor.

For small iterative changes to non class default object code use live coding.

Avoid using hot reload at all (even tho it’s setup as the default!)

Hope that helps, it’s a bit of a pain but at least its a clear reliable workflow which is the main thing, the full article has a lot of great info in it.

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.