Player Camera in Controller instead of Character

I’ve done this myself. My game is an FPS / RTS mix where the player can take control of a lot of different pawns, often in quick succession. To avoid all those extra scene components, I create the Camera, Spring Arm and First-Person Meshes as part of the Player Controller (the latter is a pain in the ****).

To do it successfully, you need to create a custom PlayerCameraManager and override the UpdateViewTarget function. This is a direct copy-paste from my project below, you can pretty much work it out :slight_smile:



void ABZGame_CameraManager::UpdateViewTarget(FTViewTarget& OutVT, float DeltaTime)
{
	if ((PendingViewTarget.Target != NULL) && BlendParams.bLockOutgoing && OutVT.Equal(ViewTarget))
	{
		return;
	}

	FMinimalViewInfo OrigPOV = OutVT.POV;
	OutVT.POV.FOV = DefaultFOV;
	OutVT.POV.OrthoWidth = DefaultOrthoWidth;
	OutVT.POV.bConstrainAspectRatio = false;
	OutVT.POV.ProjectionMode = this->bIsOrthographic ? ECameraProjectionMode::Orthographic : ECameraProjectionMode::Perspective;
	OutVT.POV.PostProcessBlendWeight = 1.0f;
	bool bDoNotApplyModifiers = false;

	ABZGame_PlayerController* BZGame_Controller = Cast<ABZGame_PlayerController>(GetOwningPlayerController());
	if (BZGame_Controller != NULL)
	{
		UCameraComponent* ViewCam = BZGame_Controller->GetViewCamera();
		OutVT.POV.Location = ViewCam->GetComponentLocation();
		OutVT.POV.Rotation = ViewCam->GetComponentRotation();
		OutVT.POV.FOV = ViewCam->FieldOfView;
		OutVT.POV.AspectRatio = ViewCam->AspectRatio;
		OutVT.POV.bConstrainAspectRatio = ViewCam->bConstrainAspectRatio;
		OutVT.POV.ProjectionMode = ViewCam->ProjectionMode;
		OutVT.POV.OrthoWidth = ViewCam->OrthoWidth;
		OutVT.POV.PostProcessBlendWeight = ViewCam->PostProcessBlendWeight;

		if (BZGame_Controller->GetViewCamera()->PostProcessBlendWeight > 0.0f)
		{
			OutVT.POV.PostProcessSettings = ViewCam->PostProcessSettings;
		}

		if (!bDoNotApplyModifiers || this->bAlwaysApplyModifiers)
		{
			ApplyCameraModifiers(DeltaTime, OutVT.POV);
		}

		SetActorLocationAndRotation(OutVT.POV.Location, OutVT.POV.Rotation, false);
		UpdateCameraLensEffects(OutVT);
	}
	else
	{
		Super::UpdateViewTarget(OutVT, DeltaTime);
	}
}


EDIT: Also, you really want to create the controller components in the constructor.

2 Likes