[C++] Scaling an UStaticMeshComponent causes collision to stop working

I have got a UStaticMeshComponent which I rotate and scale non uniformly, in order to have a cylinder which connects two points. After scaling, checking for collision with LineTraceSingleByChannel returns no hit results. Before scaling, everything works fine, i.e. I get a valid hit result. All this is in the standalone executable, not the editor.

How do I preserve collision (or recreate it) after scaling a static mesh?

I use the following code to create the component:

UStaticMeshComponent* AWireActor::createCylinder(FVector startPosition, FVector endPosition)
{
	UStaticMeshComponent *cylinder = NewObject<UStaticMeshComponent>(this);
	cylinder->RegisterComponent();
	cylinder->AttachTo(RootComponent);
	cylinder->SetMobility(EComponentMobility::Movable);

	// Make the wire sleeker (scale start and end size down) and center it, since the mesh has it's oirigin on the side, not the center.
	cylinder->SetRelativeScale3D(FVector(0.1f, 0.1f, 1.0f));
	// roatate to match start and end
	alignCylinder(startPosition, endPosition, cylinder);

	UStaticMesh* meshToUse = Cast<UStaticMesh>(StaticLoadObject(UStaticMesh::StaticClass(), nullptr,
		TEXT("StaticMesh'/Game/StarterContent/Shapes/Shape_Cylinder.Shape_Cylinder'")));
	cylinder->SetStaticMesh(meshToUse);
	cylinder->SetCollisionEnabled(ECollisionEnabled::QueryAndPhysics);
	cylinder->SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Block);
	// cylinder->SetCollisionObjectType(ECollisionChannel::ECC_WorldDynamic);

	cylinder->SetMaterial(0, cylinderMaterial);

	return cylinder;
}

This code is used to move the cylinder to the correct position:

void AWireActor::alignCylinder(FVector start, FVector end, UStaticMeshComponent *cylinder)
{
	// rotate by 90° around X-axis to correct for the cylinder being aligned on the Z instead of the X axis.
	cylinder->SetWorldRotation(FRotator(90.0f, 0.0f, 0.0f));
	// add the rotation of the vector between start and end to align the cylinder with it.
	cylinder->AddWorldRotation((end - start).Rotation());

	// place the cylinder in the end location, since it's pivot is in there.
	cylinder->SetWorldLocation(end);

	// scale the cylinder up to properly reach both ends.
	FVector min, max;
	cylinder->GetLocalBounds(min, max);
	
	float zScale = ((start - end).Size() / max.Size());
	cylinder->SetRelativeScale3D(FVector(0.1f, 0.1f, zScale));
}

Wierdly enough this (buggy) scaling code does not break collision. However it doesn’t always scale the component correctly, so it’s not usable:

void AWireActor::alignCylinder(FVector start, FVector end, UStaticMeshComponent *cylinder)
{
	// rotate by 90° around X-axis to correct for the cylinder being aligned on the Z instead of the X axis.
	cylinder->SetWorldRotation(FRotator(90.0f, 0.0f, 0.0f));
	// add the rotation of the vector between start and end to align the cylinder with it.
	cylinder->AddWorldRotation((end - start).Rotation());

	// place the cylinder in the end location, since it's pivot is in there.
	cylinder->SetWorldLocation(end);
	// scale the cylinder up to properly reach both ends.
	float radius = 0.0f, halfHeight = 0.0f;
	cylinder->CalcBoundingCylinder(radius, halfHeight);
	float zScale = ((start - end).Size() / (halfHeight * 2.0f));
	cylinder->SetRelativeScale3D(FVector(0.1f, 0.1f, zScale));
	GEngine->AddOnScreenDebugMessage(-1, LOG_TIME, FColor::Green, FString("Scaled to ") + FString::SanitizeFloat(zScale)
		+ FString("Height is ") + FString::SanitizeFloat(halfHeight));
}

A similar problem has been presented here, however there’s no solution: https://answers.unrealengine.com/questions/166286/problems-with-collision-when-non-uniformly-scaling.html

Previously I used splines to create these wires, however they always had the same collision issue as described here, hence I abandoned them in favour of regular static meshes. Could this be a similar issue?

Found the solution: When a scene component is scaled to zer in one dimension, the collision model vanishes while the mesh remains visible. If I check whether zScale is zero before executing cylinder->SetRelativeScale3D(FVector(0.1f, 0.1f, zScale)); the issue is avoided.