Strange normal behaviour from sweep

Rasmus
Mon, 25 Aug 2014 01:53:26 +0000
Rendering

Hi, I am experimenting with a wallrun, what I do is that I do a capsule trace from the player in his right or left direction depending on which side the wall is. I then check the normal of the impact so I can rotate the character if the normal changes to be able to run at any shape. But if the shape changes drastically (more than his MaxStepHeight), he should stop running. However, when I try to check that, the normals starts to behave strange (at least in my opinion).

This is the code:

void ACharacter_Player::UpdateWallRun()
{
	if (mIsWallRunning)
	{
		FHitResult hitResult;
		FVector start = GetActorLocation();
		FVector end = start + (GetActorRightVector() * -100.f);
		FCollisionShape shape = FCollisionShape::MakeCapsule(CapsuleComponent->GetScaledCapsuleRadius(), CapsuleComponent->GetScaledCapsuleHalfHeight());
		FCollisionQueryParams collisionParams;
		collisionParams.AddIgnoredActor(this);
		collisionParams.bTraceComplex = true;
		FCollisionObjectQueryParams collisionObjectParams;
		collisionObjectParams.AddObjectTypesToQuery(ECollisionChannel::ECC_WorldStatic);

		bool didHit = GetWorld()->SweepSingle(hitResult, start, end, FQuat(), shape, collisionParams, collisionObjectParams);

		if (didHit)
		{
			FVector hitNormal = hitResult.ImpactNormal;
			FVector hitLocation = hitResult.ImpactPoint;

			if (!hitNormal.Equals(mWallRunNormal, 0.1f))
			{
				DrawDebugLine(GetWorld(), hitLocation, hitLocation + hitNormal * 100.f, FColor::Blue, true, 10.f);

				FRotator wallDiff = FRotationMatrix::MakeFromZ(mWallRunNormal).Rotator() - FRotationMatrix::MakeFromZ(hitNormal).Rotator();
			}
			else
				DrawDebugLine(GetWorld(), hitLocation, hitLocation + hitNormal * 100.f, FColor::Red, true, 10.f);

			FVector velocity = GetActorForwardVector() + mWallRunNormal * -0.1f;
                            velocity.Normalize();
			CharacterMovement->Velocity = (velocity * CharacterMovement->MaxWalkSpeed);
		}
		else
			StopWallRun();
	}
}

What my problem is that WITHOUT the

FRotator wallDiff = FRotationMatrix::MakeFromZ(mWallRunNormal).Rotator() - FRotationMatrix::MakeFromZ(hitNormal).Rotator();

line, I get expected results, but with it I get weird normals, see attached image

Note that the lines are from the impact point in the normals direction. The “strange” lines doesn’t even line up with the shape, they’re in the air. I have tried to print the name of the component, it IS the shape that’s being hit.

Image 1 is WITHOUT the FRotator and Image 2 is WITH the FRotator line. I get the same result of Image 2 when I just put something like

FRotator = FVector(0, 0, 0)::Rotate();

Where does these normals come from and why does they only appear when I call a .Rotate() or .Rotator() function? I only expect the normals from Image 1.

2 posts - 1 participant