The main reason as to why i am manually setting the length is to have the camera moving smoothly from point A to point B rather than snapping immediately. So the problem is that when the camera is above the character and rotate down to obstruct the character, the camera will spring back and forth each frame. Keep in mind that this only happens when looking over a wall. Camera works fine when coming in from side and underneath obstacle.
The Code
//---------- Smooth Spring Arm Component----------------//
FHitResult OutHit;
APlayerCameraManager* camManager = GetWorld()->GetFirstPlayerController()->PlayerCameraManager;
FVector camPos = camManager->GetCameraLocation();
FVector Start = GetActorLocation();
FVector Direction = (camPos - Start).GetSafeNormal();
FVector End = Start + Direction * 500;
FCollisionQueryParams CollisionParams;
DrawDebugLine(GetWorld(), Start, End, FColor::Red, false, 0, 0, 1);
//Cast Line trace
bool isHit = GetWorld()->LineTraceSingleByChannel(OutHit, Start, End, ECC_Visibility, CollisionParams);
if (GEngine) {
GEngine->AddOnScreenDebugMessage(-1, 1, FColor::Blue, FString::Printf(TEXT("Has Hit: %s"), isHit ? TEXT("true") : TEXT("false")));
}
//if ray hit something
if (isHit) {
//if ray is being blocked from something
if (OutHit.bBlockingHit) {
//Smooth the target arm length change
float CurrentArmLength = CameraBoom->TargetArmLength;
CameraBoom->TargetArmLength = FMath::FInterpTo(CurrentArmLength, OutHit.Distance - CameraCollisionOffset, DeltaTime, 15);
}
} else {
float CurrentArmLength = CameraBoom->TargetArmLength;
CameraBoom->TargetArmLength = FMath::FInterpTo(CurrentArmLength, SpringArmLength, DeltaTime, 25);
}