A problem with Physics (freezing totally) when using the function AddAngularImpulse!

Hi everybody,

I’m changing the velocity and orientation of the Character ( technically of the UPrimitiveComponent that I assigned the Actor’s root to ), via adding impulse force and impulse angular force (torque in Physx). I use the impulses on the FBodyInstance object of the PrimitiveComponent.

The problem is whenever I use the function FBodyInstance::AddAngularImpuse(const FVector &Impulse, bool bVelChange)with bVelChange = true, after a while of playing (sometimes 15 seconds, sometime several minutes), suddenly all the actors that have UPrimitiveComponents, especially those with Physics is set to simulate, all of those actors freeze, every thing else in the game keeps working fine and the game doesn’t at all crash, but the objects that are subject to any impulse are dead, they never move.

There is not Log error on any comment in the Log what so ever.

Interestingly, when I use the same FBodyInstance on a UPrimitiveComponent, that I couple transformation with an AActor, using only AddImpulses and no AddAngularImpulses, then the whole problem never appears, suggesting something to do with the angular impulse.

Any idea?

I’ve solve it, thankfully.

It’s actually due to the fact that I used acosf function to get the angle between two vectors.
This function, acosf, (also acos as well which is called by the former actually) can’t accept a value above 1.f
I actually knew that in advance and I normalized both vectors that I will get their cos angle via dot product.

It turns out that the normalization function in unreal can give results that are slightly above 1.f (like 1.00000021f for example) which is of course large enough to cause the acosf to go crazy (giving NaN in response) which in turn make the add angular impulse function to jam in endless freeze.

The solution is easily adding manual guard to prevent any value above 1.f from entering acosf as a parameter, i.e. something like:

float product = FVector : : DotProduct(vector1,vector2) ;
if ( product > 1.f )
{
product = 1.f ;
}
float angle = acosf ( product ) ;

1 Like