Strange physics rotation for player controlled vehicle when facing a certain direction

Hi all,

I’ve been trying to figure out what’s wrong with this code. I made some code for a physics-based flying vehicle, but for some reason when the vehicle is facing a certain direction, it rolls upside down and starts behaving weirdly. I think perhaps I’ve got some math wrong… Anyone able to figure out what it might be? Here’s the code and a video of the problem.

void UHoverMovementComponent::TorqueToTargetRotation()
{
	const FRotator DeltaRotation = UKismetMathLibrary::NormalizedDeltaRotator(TargetRotation, CurrentRotation);
	const FVector CurrentTorque = PrimitiveComponent->GetPhysicsAngularVelocityInDegrees();
	GEngine->AddOnScreenDebugMessage(-1, .1, FColor::Cyan, TargetRotation.ToString());
	PrimitiveComponent->AddTorqueInDegrees((FVector(DeltaRotation.Roll, DeltaRotation.Pitch, DeltaRotation.Yaw) - (CurrentTorque * TorqueDamping)) * TorqueForce, NAME_None, true);
}
1 Like

This issue is still throwing me for a loop. Whenever my TargetRotation approaches 0, these are the logs produced (before it starts going crazy since it takes a second to kick in)

LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-0.002467 Y=-0.148324 R=0.001497
LogTemp: Warning: Target:      P=-0.000339 Y=-0.148508 R=0.000332
LogTemp: Warning: Delta:       P=0.002128 Y=-0.000184 R=-0.001165
LogTemp: Warning: Torque:      X=-0.010 Y=0.011 Z=-0.004
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-0.002467 Y=-0.148324 R=0.001497
LogTemp: Warning: Target:      P=-0.000339 Y=-0.148508 R=0.000332
LogTemp: Warning: Delta:       P=0.002128 Y=-0.000184 R=-0.001165
LogTemp: Warning: Torque:      X=-0.010 Y=0.010 Z=-0.004
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-0.002613 Y=-0.148315 R=0.001548
LogTemp: Warning: Target:      P=-0.000339 Y=-0.148508 R=0.000332
LogTemp: Warning: Delta:       P=0.002274 Y=-0.000193 R=-0.001216
LogTemp: Warning: Torque:      X=-0.010 Y=0.011 Z=-0.004
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-0.002613 Y=-0.148315 R=0.001548
LogTemp: Warning: Target:      P=-0.000339 Y=-0.148508 R=0.000332
LogTemp: Warning: Delta:       P=0.002274 Y=-0.000193 R=-0.001216
LogTemp: Warning: Torque:      X=-0.010 Y=0.010 Z=-0.004
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-0.002773 Y=-0.148306 R=0.001602
LogTemp: Warning: Target:      P=-0.000339 Y=-0.148508 R=0.000332
LogTemp: Warning: Delta:       P=0.002434 Y=-0.000202 R=-0.001269
LogTemp: Warning: Torque:      X=-0.011 Y=0.012 Z=-0.004

When facing the exact opposite direction, I get no issue and these are the logs produced.

LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-3.837294 Y=-178.324419 R=0.005185
LogTemp: Warning: Target:      P=-3.850819 Y=-178.324234 R=0.002024
LogTemp: Warning: Delta:       P=-0.013524 Y=0.000185 R=-0.003161
LogTemp: Warning: Torque:      X=0.051 Y=0.140 Z=-0.017
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-3.838339 Y=-178.324343 R=0.004858
LogTemp: Warning: Target:      P=-3.850819 Y=-178.324234 R=0.002024
LogTemp: Warning: Delta:       P=-0.012480 Y=0.000109 R=-0.002834
LogTemp: Warning: Torque:      X=0.046 Y=0.130 Z=-0.015
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-3.839305 Y=-178.324278 R=0.004562
LogTemp: Warning: Target:      P=-3.850819 Y=-178.324234 R=0.002024
LogTemp: Warning: Delta:       P=-0.011514 Y=0.000044 R=-0.002538
LogTemp: Warning: Torque:      X=0.042 Y=0.120 Z=-0.013
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-3.840221 Y=-178.324221 R=0.004287
LogTemp: Warning: Target:      P=-3.850819 Y=-178.324234 R=0.002024
LogTemp: Warning: Delta:       P=-0.010597 Y=-0.000013 R=-0.002263
LogTemp: Warning: Torque:      X=0.038 Y=0.111 Z=-0.011
LogTemp: Warning: ----------------------------------------------------------
LogTemp: Warning: Current:     P=-3.841106 Y=-178.324172 R=0.004028
LogTemp: Warning: Target:      P=-3.850819 Y=-178.324234 R=0.002024
LogTemp: Warning: Delta:       P=-0.009712 Y=-0.000062 R=-0.002004
LogTemp: Warning: Torque:      X=0.034 Y=0.101 Z=-0.010

The code

void UFlyingVehicleMovementComponent::TurnToTargetRotation()
{
	
	UE_LOG(LogTemp, Warning, TEXT("\n----------------------------------------------------------"));
	UE_LOG(LogTemp, Warning, TEXT("Current: \t %s"), *CurrentRotation.ToString());
	UE_LOG(LogTemp, Warning, TEXT("Target: \t %s"), *TargetRotation.ToString());
	
	const FRotator DeltaRotation = UKismetMathLibrary::NormalizedDeltaRotator(TargetRotation, CurrentRotation);
	UE_LOG(LogTemp, Warning, TEXT("Delta: \t\t %s"), *DeltaRotation.ToString());
	const FVector CurrentAngularVelocity = PrimitiveComponent->GetPhysicsAngularVelocityInDegrees();
	const FVector TorqueToAdd = (FVector(DeltaRotation.Roll, DeltaRotation.Pitch, DeltaRotation.Yaw) - (CurrentAngularVelocity * TorqueDamping)) * TorqueForce;
	UE_LOG(LogTemp, Warning, TEXT("Torque: \t %s"), *TorqueToAdd.ToString());
	
	PrimitiveComponent->AddTorqueInDegrees(TorqueToAdd, NAME_None, true);
}

I’m wondering if this is gimbal lock. I’ve never experienced gimbal lock previously so I’m not certain if it is though.

I tried a very basic actor with nothing but the hover movement component on it, with a rotation set to the problematic direction. I also added some debug visualization. I still can’t really figure out what’s happening here. As soon as it needs to do some correction (right when I throw a grenade at it to throw it off balance) it goes wacky.