From 10a6ed64721a041eb0492f806fc2ced879ee7862 Mon Sep 17 00:00:00 2001
From: Sebastian Pape <pape@vr.rwth-aachen.de>
Date: Mon, 1 Feb 2021 13:01:50 +0100
Subject: [PATCH] After first tests seems to now work on Desktop
---
.../Private/VRPawnMovement.cpp | 382 +++++++++---------
.../Private/VirtualRealityPawn.cpp | 230 +++++------
.../Public/VRPawnMovement.h | 138 +++----
.../Public/VirtualRealityPawn.h | 103 ++---
4 files changed, 425 insertions(+), 428 deletions(-)
diff --git a/Source/DisplayClusterExtensions/Private/VRPawnMovement.cpp b/Source/DisplayClusterExtensions/Private/VRPawnMovement.cpp
index 34464add..b6c5b9d1 100644
--- a/Source/DisplayClusterExtensions/Private/VRPawnMovement.cpp
+++ b/Source/DisplayClusterExtensions/Private/VRPawnMovement.cpp
@@ -1,188 +1,194 @@
-
-#include "VRPawnMovement.h"
-#include "DrawDebugHelpers.h"
-
-UVRPawnMovement::UVRPawnMovement(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer)
-{
- CapsuleColliderComponent = CreateDefaultSubobject<UCapsuleComponent>(TEXT("CapsuleCollider"));
- CapsuleColliderComponent->SetCollisionEnabled(ECollisionEnabled::QueryAndPhysics);
- CapsuleColliderComponent->SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Ignore);
- CapsuleColliderComponent->SetCollisionResponseToChannel(ECollisionChannel::ECC_WorldStatic, ECollisionResponse::ECR_Block);
- CapsuleColliderComponent->SetCapsuleSize(40.0f, 96.0f);
-
- CameraComponent = GetOwner()->FindComponentByClass<UCameraComponent>();
- CapsuleColliderComponent->SetupAttachment(CameraComponent);
-}
-
-void UVRPawnMovement::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction){
-
- SetCapsuleColliderToUserSize();
-
- FVector PositionChange = GetPendingInputVector();
-
- if (NavigationMode == EVRNavigationModes::Walk)
- {
- PositionChange.Z = 0.0f;
- ConsumeInputVector();
- AddInputVector(PositionChange);
- }
-
- if(NavigationMode == EVRNavigationModes::Fly || NavigationMode == EVRNavigationModes::Walk)
- {
- MoveByGravityOrStepUp(DeltaTime);
- CheckForPhysWalkingCollision();
-
- if(CheckForVirtualMovCollision(PositionChange, DeltaTime))
- {
- ConsumeInputVector();
- }
- }
-
- if(NavigationMode == EVRNavigationModes::None)
- {
- ConsumeInputVector();
- }
-
- Super::TickComponent(DeltaTime, TickType, ThisTickFunction);
-
- LastCameraPosition = CameraComponent->GetComponentLocation();
-}
-
-bool UVRPawnMovement::CheckForVirtualMovCollision(FVector PositionChange, float DeltaTime)
-{
- FVector ProbePosition = PositionChange.GetSafeNormal() * GetMaxSpeed() * DeltaTime;
- FHitResult FHitResultVR;
- CapsuleColliderComponent->AddWorldOffset(ProbePosition, true, &FHitResultVR);
- if (FVector::Distance(FHitResultVR.Location, CapsuleColliderComponent->GetComponentLocation()) < CapsuleColliderComponent->GetScaledCapsuleRadius())
- {
- return true;
- }
- return false;
-}
-
-void UVRPawnMovement::SetCapsuleColliderToUserSize()
-{
- float CharachterSize = abs(UpdatedComponent->GetComponentLocation().Z - CameraComponent->GetComponentLocation().Z);
-
- if (CharachterSize > MaxStepHeight)
- {
- float ColliderHeight = CharachterSize - MaxStepHeight;
- float ColliderHalfHeight = ColliderHeight / 2.0f;
- float ColliderRadius = 40.0f;
- if (ColliderHalfHeight <= ColliderRadius)
- {//Make the collider to a Sphere
- CapsuleColliderComponent->SetCapsuleSize(ColliderHalfHeight, ColliderHalfHeight);
- }
- else
- {//Make the collider to a Capsule
- CapsuleColliderComponent->SetCapsuleSize(ColliderRadius, ColliderHalfHeight);
- }
-
- CapsuleColliderComponent->SetWorldLocation(CameraComponent->GetComponentLocation());
- CapsuleColliderComponent->AddWorldOffset(FVector(0, 0, -ColliderHalfHeight));
- CapsuleColliderComponent->SetWorldRotation(FRotator(0, 0, 1));
- }
- else
- {
- CapsuleColliderComponent->SetWorldLocation(CameraComponent->GetComponentLocation());
- CapsuleColliderComponent->SetWorldRotation(FRotator(0, 0, 1));
- }
-}
-
-void UVRPawnMovement::CheckForPhysWalkingCollision()
-{
- FVector CurrentCameraPosition = CameraComponent->GetComponentLocation();
- FVector Direction = CurrentCameraPosition - LastCameraPosition;
- FHitResult FHitResultPhys;
- CapsuleColliderComponent->AddWorldOffset(Direction, true, &FHitResultPhys);
-
- if (FHitResultPhys.bBlockingHit)
- {
- UpdatedComponent->AddLocalOffset(FHitResultPhys.Normal*FHitResultPhys.PenetrationDepth);
- }
-}
-
-void UVRPawnMovement::MoveByGravityOrStepUp(float DeltaSeconds)
-{
- FVector StartLineTraceUnderCollider = CapsuleColliderComponent->GetComponentLocation();
- StartLineTraceUnderCollider.Z -= CapsuleColliderComponent->GetScaledCapsuleHalfHeight();
- FHitResult HitDetailsMultiLineTrace = CreateMultiLineTrace(FVector(0, 0, -1), StartLineTraceUnderCollider, CapsuleColliderComponent->GetScaledCapsuleRadius() / 4.0f, false);
- float DistanceDifference = abs(MaxStepHeight - HitDetailsMultiLineTrace.Distance);
- //Going up (in Fly and Walk Mode)
- if ((HitDetailsMultiLineTrace.bBlockingHit && HitDetailsMultiLineTrace.Distance < MaxStepHeight))
- {
- ShiftVertically(DistanceDifference, UpSteppingAcceleration, DeltaSeconds, 1);
- }
- //Gravity (only in Walk Mode)
- else if (NavigationMode==EVRNavigationModes::Walk && ((HitDetailsMultiLineTrace.bBlockingHit && HitDetailsMultiLineTrace.Distance > MaxStepHeight) || (HitDetailsMultiLineTrace.Actor == nullptr && HitDetailsMultiLineTrace.Distance != -1.0f)))
- {
- ShiftVertically(DistanceDifference, GravityAcceleration, DeltaSeconds, -1);
- }
-}
-
-void UVRPawnMovement::ShiftVertically(float DiffernceDistance, float VerticalAcceleration, float DeltaSeconds, int Direction)
-{
- VerticalSpeed += VerticalAcceleration * DeltaSeconds;
- if (VerticalSpeed*DeltaSeconds < DiffernceDistance)
- {
- UpdatedComponent->AddLocalOffset(FVector(0.f, 0.f, Direction * VerticalSpeed * DeltaSeconds));
- }
- else
- {
- UpdatedComponent->AddLocalOffset(FVector(0.f, 0.f, Direction * DiffernceDistance));
- VerticalSpeed = 0;
- }
-}
-
-FHitResult UVRPawnMovement::CreateLineTrace(FVector Direction, const FVector Start, bool Visibility)
-{
- //Re-initialize hit info
- FHitResult HitDetails = FHitResult(ForceInit);
-
- FVector End = ((Direction * 1000.f) + Start);
- // additional trace parameters
- FCollisionQueryParams TraceParams(FName(TEXT("InteractTrace")), true, NULL);
- TraceParams.bTraceComplex = true; //to use complex collision on whatever we interact with to provide better precision.
- TraceParams.bReturnPhysicalMaterial = true; //to provide details about the physical material, if one exists on the thing we hit, to come back in our hit result.
-
- if (Visibility)
- DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1, 0, 1);
-
- if (GetWorld()->LineTraceSingleByChannel(HitDetails, Start, End, ECC_Visibility, TraceParams))
- {
- if (HitDetails.bBlockingHit)
- {
- }
- }
- return HitDetails;
-}
-
-FHitResult UVRPawnMovement::CreateMultiLineTrace(FVector Direction, const FVector Start, float Radius, bool Visibility)
-{
- TArray<FVector> StartVectors;
- TArray<FHitResult> OutHits;
- FHitResult HitDetailsMultiLineTrace;
- HitDetailsMultiLineTrace.Distance = -1.0f;//(Distance=-1) not existing, but to know if this Variable not Initialized(when all Traces not compatible)
-
- StartVectors.Add(Start); //LineTraceCenter
- StartVectors.Add(Start + FVector(0, -Radius, 0)); //LineTraceLeft
- StartVectors.Add(Start + FVector(0, +Radius, 0)); //LineTraceRight
- StartVectors.Add(Start + FVector(+Radius, 0, 0)); //LineTraceFront
- StartVectors.Add(Start + FVector(-Radius, 0, 0)); //LineTraceBehind
-
- bool IsBlockingHitAndSameActor = true;
- bool IsAllNothingHiting = true;
- // loop through TArray
- for (FVector& Vector : StartVectors)
- {
- FHitResult OutHit = CreateLineTrace(Direction, Vector, Visibility);
- OutHits.Add(OutHit);
- IsBlockingHitAndSameActor &= (OutHit.Actor == OutHits[0].Actor); //If all Hiting the same Object, then you are (going up/down) or (walking)
- IsAllNothingHiting &= (OutHit.Actor == nullptr); //If all Hiting nothing, then you are falling
- }
-
- if (IsBlockingHitAndSameActor || IsAllNothingHiting)
- HitDetailsMultiLineTrace = OutHits[0];
-
- return HitDetailsMultiLineTrace;
-}
+
+#include "VRPawnMovement.h"
+#include "DrawDebugHelpers.h"
+
+UVRPawnMovement::UVRPawnMovement(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer)
+{
+
+
+ CapsuleColliderComponent = CreateDefaultSubobject<UCapsuleComponent>(TEXT("CapsuleCollider"));
+ CapsuleColliderComponent->SetCollisionEnabled(ECollisionEnabled::QueryAndPhysics);
+ CapsuleColliderComponent->SetCollisionResponseToAllChannels(ECollisionResponse::ECR_Ignore);
+ CapsuleColliderComponent->SetCollisionResponseToChannel(ECollisionChannel::ECC_WorldStatic, ECollisionResponse::ECR_Block);
+ CapsuleColliderComponent->SetCapsuleSize(40.0f, 96.0f);
+}
+
+void UVRPawnMovement::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction){
+
+ SetCapsuleColliderToUserSize();
+
+ FVector PositionChange = GetPendingInputVector();
+
+ if (NavigationMode == EVRNavigationModes::Walk)
+ {
+ PositionChange.Z = 0.0f;
+ ConsumeInputVector();
+ AddInputVector(PositionChange);
+ }
+
+ if(NavigationMode == EVRNavigationModes::Fly || NavigationMode == EVRNavigationModes::Walk)
+ {
+ MoveByGravityOrStepUp(DeltaTime);
+ CheckForPhysWalkingCollision();
+
+ if(CheckForVirtualMovCollision(PositionChange, DeltaTime))
+ {
+ ConsumeInputVector();
+ }
+ }
+
+ if(NavigationMode == EVRNavigationModes::None)
+ {
+ ConsumeInputVector();
+ }
+
+ Super::TickComponent(DeltaTime, TickType, ThisTickFunction);
+
+ LastCameraPosition = CameraComponent->GetComponentLocation();
+}
+
+bool UVRPawnMovement::CheckForVirtualMovCollision(FVector PositionChange, float DeltaTime)
+{
+ FVector ProbePosition = PositionChange.GetSafeNormal() * GetMaxSpeed() * DeltaTime;
+ FHitResult FHitResultVR;
+ CapsuleColliderComponent->AddWorldOffset(ProbePosition, true, &FHitResultVR);
+ if (FVector::Distance(FHitResultVR.Location, CapsuleColliderComponent->GetComponentLocation()) < CapsuleColliderComponent->GetScaledCapsuleRadius())
+ {
+ return true;
+ }
+ return false;
+}
+
+void UVRPawnMovement::SetCameraComponent(UCameraComponent* NewCameraComponent)
+{
+ CameraComponent = NewCameraComponent;
+ CapsuleColliderComponent->SetupAttachment(CameraComponent);
+}
+
+
+void UVRPawnMovement::SetCapsuleColliderToUserSize()
+{
+ float CharachterSize = abs(UpdatedComponent->GetComponentLocation().Z - CameraComponent->GetComponentLocation().Z);
+
+ if (CharachterSize > MaxStepHeight)
+ {
+ float ColliderHeight = CharachterSize - MaxStepHeight;
+ float ColliderHalfHeight = ColliderHeight / 2.0f;
+ float ColliderRadius = 40.0f;
+ if (ColliderHalfHeight <= ColliderRadius)
+ {//Make the collider to a Sphere
+ CapsuleColliderComponent->SetCapsuleSize(ColliderHalfHeight, ColliderHalfHeight);
+ }
+ else
+ {//Make the collider to a Capsule
+ CapsuleColliderComponent->SetCapsuleSize(ColliderRadius, ColliderHalfHeight);
+ }
+
+ CapsuleColliderComponent->SetWorldLocation(CameraComponent->GetComponentLocation());
+ CapsuleColliderComponent->AddWorldOffset(FVector(0, 0, -ColliderHalfHeight));
+ CapsuleColliderComponent->SetWorldRotation(FRotator(0, 0, 1));
+ }
+ else
+ {
+ CapsuleColliderComponent->SetWorldLocation(CameraComponent->GetComponentLocation());
+ CapsuleColliderComponent->SetWorldRotation(FRotator(0, 0, 1));
+ }
+}
+
+void UVRPawnMovement::CheckForPhysWalkingCollision()
+{
+ FVector CurrentCameraPosition = CameraComponent->GetComponentLocation();
+ FVector Direction = CurrentCameraPosition - LastCameraPosition;
+ FHitResult FHitResultPhys;
+ CapsuleColliderComponent->AddWorldOffset(Direction, true, &FHitResultPhys);
+
+ if (FHitResultPhys.bBlockingHit)
+ {
+ UpdatedComponent->AddLocalOffset(FHitResultPhys.Normal*FHitResultPhys.PenetrationDepth);
+ }
+}
+
+void UVRPawnMovement::MoveByGravityOrStepUp(float DeltaSeconds)
+{
+ FVector StartLineTraceUnderCollider = CapsuleColliderComponent->GetComponentLocation();
+ StartLineTraceUnderCollider.Z -= CapsuleColliderComponent->GetScaledCapsuleHalfHeight();
+ FHitResult HitDetailsMultiLineTrace = CreateMultiLineTrace(FVector(0, 0, -1), StartLineTraceUnderCollider, CapsuleColliderComponent->GetScaledCapsuleRadius() / 4.0f, false);
+ float DistanceDifference = abs(MaxStepHeight - HitDetailsMultiLineTrace.Distance);
+ //Going up (in Fly and Walk Mode)
+ if ((HitDetailsMultiLineTrace.bBlockingHit && HitDetailsMultiLineTrace.Distance < MaxStepHeight))
+ {
+ ShiftVertically(DistanceDifference, UpSteppingAcceleration, DeltaSeconds, 1);
+ }
+ //Gravity (only in Walk Mode)
+ else if (NavigationMode==EVRNavigationModes::Walk && ((HitDetailsMultiLineTrace.bBlockingHit && HitDetailsMultiLineTrace.Distance > MaxStepHeight) || (HitDetailsMultiLineTrace.Actor == nullptr && HitDetailsMultiLineTrace.Distance != -1.0f)))
+ {
+ ShiftVertically(DistanceDifference, GravityAcceleration, DeltaSeconds, -1);
+ }
+}
+
+void UVRPawnMovement::ShiftVertically(float DiffernceDistance, float VerticalAcceleration, float DeltaSeconds, int Direction)
+{
+ VerticalSpeed += VerticalAcceleration * DeltaSeconds;
+ if (VerticalSpeed*DeltaSeconds < DiffernceDistance)
+ {
+ UpdatedComponent->AddLocalOffset(FVector(0.f, 0.f, Direction * VerticalSpeed * DeltaSeconds));
+ }
+ else
+ {
+ UpdatedComponent->AddLocalOffset(FVector(0.f, 0.f, Direction * DiffernceDistance));
+ VerticalSpeed = 0;
+ }
+}
+
+FHitResult UVRPawnMovement::CreateLineTrace(FVector Direction, const FVector Start, bool Visibility)
+{
+ //Re-initialize hit info
+ FHitResult HitDetails = FHitResult(ForceInit);
+
+ FVector End = ((Direction * 1000.f) + Start);
+ // additional trace parameters
+ FCollisionQueryParams TraceParams(FName(TEXT("InteractTrace")), true, NULL);
+ TraceParams.bTraceComplex = true; //to use complex collision on whatever we interact with to provide better precision.
+ TraceParams.bReturnPhysicalMaterial = true; //to provide details about the physical material, if one exists on the thing we hit, to come back in our hit result.
+
+ if (Visibility)
+ DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1, 0, 1);
+
+ if (GetWorld()->LineTraceSingleByChannel(HitDetails, Start, End, ECC_Visibility, TraceParams))
+ {
+ if (HitDetails.bBlockingHit)
+ {
+ }
+ }
+ return HitDetails;
+}
+
+FHitResult UVRPawnMovement::CreateMultiLineTrace(FVector Direction, const FVector Start, float Radius, bool Visibility)
+{
+ TArray<FVector> StartVectors;
+ TArray<FHitResult> OutHits;
+ FHitResult HitDetailsMultiLineTrace;
+ HitDetailsMultiLineTrace.Distance = -1.0f;//(Distance=-1) not existing, but to know if this Variable not Initialized(when all Traces not compatible)
+
+ StartVectors.Add(Start); //LineTraceCenter
+ StartVectors.Add(Start + FVector(0, -Radius, 0)); //LineTraceLeft
+ StartVectors.Add(Start + FVector(0, +Radius, 0)); //LineTraceRight
+ StartVectors.Add(Start + FVector(+Radius, 0, 0)); //LineTraceFront
+ StartVectors.Add(Start + FVector(-Radius, 0, 0)); //LineTraceBehind
+
+ bool IsBlockingHitAndSameActor = true;
+ bool IsAllNothingHiting = true;
+ // loop through TArray
+ for (FVector& Vector : StartVectors)
+ {
+ FHitResult OutHit = CreateLineTrace(Direction, Vector, Visibility);
+ OutHits.Add(OutHit);
+ IsBlockingHitAndSameActor &= (OutHit.Actor == OutHits[0].Actor); //If all Hiting the same Object, then you are (going up/down) or (walking)
+ IsAllNothingHiting &= (OutHit.Actor == nullptr); //If all Hiting nothing, then you are falling
+ }
+
+ if (IsBlockingHitAndSameActor || IsAllNothingHiting)
+ HitDetailsMultiLineTrace = OutHits[0];
+
+ return HitDetailsMultiLineTrace;
+}
\ No newline at end of file
diff --git a/Source/DisplayClusterExtensions/Private/VirtualRealityPawn.cpp b/Source/DisplayClusterExtensions/Private/VirtualRealityPawn.cpp
index 2c6a729d..4d77d493 100644
--- a/Source/DisplayClusterExtensions/Private/VirtualRealityPawn.cpp
+++ b/Source/DisplayClusterExtensions/Private/VirtualRealityPawn.cpp
@@ -1,121 +1,109 @@
-// Fill out your copyright notice in the Description page of Project Settings.
-
-
-#include "VirtualRealityPawn.h"
-
-
-
-#include "GameFramework/InputSettings.h"
-#include "GameFramework/PlayerInput.h"
-#include "UniversalTrackedComponent.h"
-#include "VirtualRealityUtilities.h"
-#include "VRPawnMovement.h"
-
-AVirtualRealityPawn::AVirtualRealityPawn(const FObjectInitializer& ObjectInitializer)
- : Super(ObjectInitializer)
-{
- bUseControllerRotationYaw = true;
- bUseControllerRotationPitch = true;
- bUseControllerRotationRoll = true;
- BaseEyeHeight = 160.0f;
-
- AutoPossessPlayer = EAutoReceiveInput::Player0; // Necessary for receiving motion controller events.
-
- PawnMovement = CreateDefaultSubobject<UVRPawnMovement>(TEXT("Pawn Movement"));
- PawnMovement->SetUpdatedComponent(RootComponent);
-
- Head = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Head"));
- Head->ProxyType = ETrackedComponentType::TCT_HEAD;
- Head->SetupAttachment(RootComponent);
-
- RightHand = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Right Hand"));
- RightHand->ProxyType = ETrackedComponentType::TCT_RIGHT_HAND;
- RightHand->AttachementType = EAttachementType::AT_FLYSTICK;
- RightHand->SetupAttachment(RootComponent);
-
- LeftHand = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Left Hand"));
- LeftHand->ProxyType = ETrackedComponentType::TCT_LEFT_HAND;
- LeftHand->AttachementType = EAttachementType::AT_HANDTARGET;
- LeftHand->SetupAttachment(RootComponent);
-
- Tracker1 = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Vive Tracker 1"));
- Tracker1->ProxyType = ETrackedComponentType::TCT_TRACKER_1;
- Tracker1->SetupAttachment(RootComponent);
-
- Tracker2 = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Vive Tracker 2"));
- Tracker2->ProxyType = ETrackedComponentType::TCT_TRACKER_2;
- Tracker2->SetupAttachment(RootComponent);
-
- BasicVRInteraction = CreateDefaultSubobject<UBasicVRInteractionComponent>(TEXT("Basic VR Interaction"));
- BasicVRInteraction->Initialize(RightHand);
-}
-
-void AVirtualRealityPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
-{
- Super::SetupPlayerInputComponent(PlayerInputComponent);
- if (PlayerInputComponent)
- {
- PlayerInputComponent->BindAxis("MoveForward", this, &AVirtualRealityPawn::OnForward);
- PlayerInputComponent->BindAxis("MoveRight", this, &AVirtualRealityPawn::OnRight);
- PlayerInputComponent->BindAxis("TurnRate", this, &AVirtualRealityPawn::OnTurnRate);
- PlayerInputComponent->BindAxis("LookUpRate", this, &AVirtualRealityPawn::OnLookUpRate);
-
- // function bindings for grabbing and releasing
- PlayerInputComponent->BindAction("Fire", IE_Pressed, this, &AVirtualRealityPawn::OnBeginFire);
- PlayerInputComponent->BindAction("Fire", IE_Released, this, &AVirtualRealityPawn::OnEndFire);
- }
-}
-
-void AVirtualRealityPawn::BeginPlay()
-{
- if(!UVirtualRealityUtilities::IsDesktopMode()) /* Disable to not get cyber sick as fast */
- {
- UInputSettings::GetInputSettings()->RemoveAxisMapping(FInputAxisKeyMapping("TurnRate", EKeys::MouseX));
- UInputSettings::GetInputSettings()->RemoveAxisMapping(FInputAxisKeyMapping("LookUpRate", EKeys::MouseY));
- }
-}
-
-void AVirtualRealityPawn::OnForward_Implementation(float Value)
-{
- if (RightHand)
- {
- AddMovementInput(RightHand->GetForwardVector(), Value);
- }
-}
-
-void AVirtualRealityPawn::OnRight_Implementation(float Value)
-{
- if (RightHand)
- {
- AddMovementInput(RightHand->GetRightVector(), Value);
- }
-}
-
-void AVirtualRealityPawn::OnTurnRate_Implementation(float Rate)
-{
- AddControllerYawInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds() * CustomTimeDilation);
-}
-
-void AVirtualRealityPawn::OnLookUpRate_Implementation(float Rate)
-{
- // User-centered projection causes simulation sickness on look up interaction hence not implemented.
- if (!UVirtualRealityUtilities::IsRoomMountedMode())
- {
- AddControllerPitchInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds() * CustomTimeDilation);
- }
-}
-
-void AVirtualRealityPawn::OnBeginFire_Implementation()
-{
- BasicVRInteraction->BeginInteraction();
-}
-
-void AVirtualRealityPawn::OnEndFire_Implementation()
-{
- BasicVRInteraction->EndInteraction();
-}
-
-UPawnMovementComponent* AVirtualRealityPawn::GetMovementComponent() const
-{
- return PawnMovement;
-}
+// Fill out your copyright notice in the Description page of Project Settings.
+
+
+#include "VirtualRealityPawn.h"
+
+
+
+#include "GameFramework/InputSettings.h"
+#include "GameFramework/PlayerInput.h"
+#include "UniversalTrackedComponent.h"
+#include "VirtualRealityUtilities.h"
+#include "VRPawnMovement.h"
+
+AVirtualRealityPawn::AVirtualRealityPawn(const FObjectInitializer& ObjectInitializer)
+ : Super(ObjectInitializer)
+{
+ bUseControllerRotationYaw = true;
+ bUseControllerRotationPitch = true;
+ bUseControllerRotationRoll = true;
+ BaseEyeHeight = 160.0f;
+
+ AutoPossessPlayer = EAutoReceiveInput::Player0; // Necessary for receiving motion controller events.
+
+ SetRootComponent(CreateDefaultSubobject<USceneComponent>(TEXT("Root")));
+
+ CameraComponent = CreateDefaultSubobject<UCameraComponent>(TEXT("Camera"));
+ CameraComponent->SetupAttachment(RootComponent);
+ CameraComponent->SetAbsolute();
+
+ PawnMovement = CreateDefaultSubobject<UVRPawnMovement>(TEXT("Pawn Movement"));
+ PawnMovement->SetUpdatedComponent(RootComponent);
+ PawnMovement->SetCameraComponent(CameraComponent);
+
+ Head = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Head"));
+ Head->ProxyType = ETrackedComponentType::TCT_HEAD;
+ Head->SetupAttachment(RootComponent);
+
+ RightHand = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Right Hand"));
+ RightHand->ProxyType = ETrackedComponentType::TCT_RIGHT_HAND;
+ RightHand->AttachementType = EAttachementType::AT_FLYSTICK;
+ RightHand->SetupAttachment(RootComponent);
+
+ LeftHand = CreateDefaultSubobject<UUniversalTrackedComponent>(TEXT("Left Hand"));
+ LeftHand->ProxyType = ETrackedComponentType::TCT_LEFT_HAND;
+ LeftHand->AttachementType = EAttachementType::AT_HANDTARGET;
+ LeftHand->SetupAttachment(RootComponent);
+
+ BasicVRInteraction = CreateDefaultSubobject<UBasicVRInteractionComponent>(TEXT("Basic VR Interaction"));
+ BasicVRInteraction->Initialize(RightHand);
+}
+
+void AVirtualRealityPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent)
+{
+ Super::SetupPlayerInputComponent(PlayerInputComponent);
+ if (!PlayerInputComponent) return;
+
+ PlayerInputComponent->BindAxis("MoveForward", this, &AVirtualRealityPawn::OnForward);
+ PlayerInputComponent->BindAxis("MoveRight", this, &AVirtualRealityPawn::OnRight);
+ PlayerInputComponent->BindAxis("TurnRate", this, &AVirtualRealityPawn::OnTurnRate);
+ PlayerInputComponent->BindAxis("LookUpRate", this, &AVirtualRealityPawn::OnLookUpRate);
+
+ // function bindings for grabbing and releasing
+ PlayerInputComponent->BindAction("Fire", IE_Pressed, this, &AVirtualRealityPawn::OnBeginFire);
+ PlayerInputComponent->BindAction("Fire", IE_Released, this, &AVirtualRealityPawn::OnEndFire);
+}
+
+void AVirtualRealityPawn::OnForward_Implementation(float Value)
+{
+ if (RightHand)
+ {
+ AddMovementInput(RightHand->GetForwardVector(), Value);
+ }
+}
+
+void AVirtualRealityPawn::OnRight_Implementation(float Value)
+{
+ if (RightHand)
+ {
+ AddMovementInput(RightHand->GetRightVector(), Value);
+ }
+}
+
+void AVirtualRealityPawn::OnTurnRate_Implementation(float Rate)
+{
+ /* Turning the user externally will make them sick */
+ if (UVirtualRealityUtilities::IsDesktopMode())
+ {
+ AddControllerYawInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds() * CustomTimeDilation);
+ }
+}
+
+void AVirtualRealityPawn::OnLookUpRate_Implementation(float Rate)
+{
+ /* Turning the user externally will make them sick */
+ if (UVirtualRealityUtilities::IsDesktopMode())
+ {
+ AddControllerPitchInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds() * CustomTimeDilation);
+ }
+}
+
+void AVirtualRealityPawn::OnBeginFire_Implementation()
+{
+ BasicVRInteraction->BeginInteraction();
+}
+
+void AVirtualRealityPawn::OnEndFire_Implementation()
+{
+ BasicVRInteraction->EndInteraction();
+}
diff --git a/Source/DisplayClusterExtensions/Public/VRPawnMovement.h b/Source/DisplayClusterExtensions/Public/VRPawnMovement.h
index 094b02d3..e0ce022b 100644
--- a/Source/DisplayClusterExtensions/Public/VRPawnMovement.h
+++ b/Source/DisplayClusterExtensions/Public/VRPawnMovement.h
@@ -1,68 +1,70 @@
-#pragma once
-
-#include "CoreMinimal.h"
-#include "GameFramework/FloatingPawnMovement.h"
-#include "Components/CapsuleComponent.h"
-#include "Camera/CameraComponent.h"
-
-#include "VRPawnMovement.generated.h"
-
-/*
- * This Movement component is needed since in VR not only the pawn itself (UpdatedComponent) is moved but also the
- * user herself can walk and thereby move the CameraComponent, which can also lead to collisions or e.g. going up steps
- *
- * The four modes are:
- * None: No controller movement is applied and no corrections regarding steps or collisions with walls are done
- * Ghost: The same as above but now the Inputs can be used for unconstrained flying (also through objects)
- * Fly: The user can fly but not through walls etc. When the user walks against a wall the scene is moved with her to avoid walking through
- * The user can also walk up stairs with a maximum step height of MaxStepHeight
- * Walk: Additionally to Fly now gravity keeps the user on the floor
- */
-
-UENUM(BlueprintType)
-enum class EVRNavigationModes : uint8
-{
- None UMETA(DisplayName = "None (no controller movement)"),
- Ghost UMETA(DisplayName = "Ghost (flying, also through walls)"),
- Fly UMETA(DisplayName = "Fly (prohibiting collisions)"),
- Walk UMETA(DisplayName = "Walk (gravity and prohibiting collisions)")
-};
-
-UCLASS()
-class DISPLAYCLUSTEREXTENSIONS_API UVRPawnMovement : public UFloatingPawnMovement
-{
- GENERATED_UCLASS_BODY()
-
-public:
-
- virtual void TickComponent(float DeltaTime, enum ELevelTick TickType,
- FActorComponentTickFunction* ThisTickFunction) override;
-
- UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
- EVRNavigationModes NavigationMode = EVRNavigationModes::Walk;
-
- UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
- float MaxStepHeight = 40.0f;
-
- UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
- float GravityAcceleration = 981.0f;
-
- UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
- float UpSteppingAcceleration = 500.0f;
-
-private:
- FHitResult CreateLineTrace(FVector Direction, const FVector Start, bool Visibility);
- FHitResult CreateMultiLineTrace(FVector Direction, const FVector Start, float Radius, bool Visibility);
- void SetCapsuleColliderToUserSize();
- void CheckForPhysWalkingCollision();
- bool CheckForVirtualMovCollision(FVector PositionChange, float DeltaTime);
- void MoveByGravityOrStepUp(float DeltaSeconds);
- void ShiftVertically(float DiffernceDistance, float VerticalAcceleration, float DeltaSeconds, int Direction);
- //(direction = Down = -1), (direction = Up = 1)
-
- UPROPERTY() UCapsuleComponent* CapsuleColliderComponent = nullptr;
- UPROPERTY() UCameraComponent* CameraComponent = nullptr;
-
- float VerticalSpeed = 0.0f;
- FVector LastCameraPosition;
-};
+#pragma once
+
+#include "CoreMinimal.h"
+#include "GameFramework/FloatingPawnMovement.h"
+#include "Components/CapsuleComponent.h"
+#include "Camera/CameraComponent.h"
+
+#include "VRPawnMovement.generated.h"
+
+/*
+ * This Movement component is needed since in VR not only the pawn itself (UpdatedComponent) is moved but also the
+ * user herself can walk and thereby move the CameraComponent, which can also lead to collisions or e.g. going up steps
+ *
+ * The four modes are:
+ * None: No controller movement is applied and no corrections regarding steps or collisions with walls are done
+ * Ghost: The same as above but now the Inputs can be used for unconstrained flying (also through objects)
+ * Fly: The user can fly but not through walls etc. When the user walks against a wall the scene is moved with her to avoid walking through
+ * The user can also walk up stairs with a maximum step height of MaxStepHeight
+ * Walk: Additionally to Fly now gravity keeps the user on the floor
+ */
+
+UENUM(BlueprintType)
+enum class EVRNavigationModes : uint8
+{
+ None UMETA(DisplayName = "None (no controller movement)"),
+ Ghost UMETA(DisplayName = "Ghost (flying, also through walls)"),
+ Fly UMETA(DisplayName = "Fly (prohibiting collisions)"),
+ Walk UMETA(DisplayName = "Walk (gravity and prohibiting collisions)")
+};
+
+UCLASS()
+class DISPLAYCLUSTEREXTENSIONS_API UVRPawnMovement : public UFloatingPawnMovement
+{
+ GENERATED_UCLASS_BODY()
+
+public:
+
+ virtual void TickComponent(float DeltaTime, enum ELevelTick TickType,
+ FActorComponentTickFunction* ThisTickFunction) override;
+
+ void SetCameraComponent(UCameraComponent* NewCameraComponent);
+
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
+ EVRNavigationModes NavigationMode = EVRNavigationModes::Walk;
+
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
+ float MaxStepHeight = 40.0f;
+
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
+ float GravityAcceleration = 981.0f;
+
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "VR Movement")
+ float UpSteppingAcceleration = 500.0f;
+
+private:
+ FHitResult CreateLineTrace(FVector Direction, const FVector Start, bool Visibility);
+ FHitResult CreateMultiLineTrace(FVector Direction, const FVector Start, float Radius, bool Visibility);
+ void SetCapsuleColliderToUserSize();
+ void CheckForPhysWalkingCollision();
+ bool CheckForVirtualMovCollision(FVector PositionChange, float DeltaTime);
+ void MoveByGravityOrStepUp(float DeltaSeconds);
+ void ShiftVertically(float DiffernceDistance, float VerticalAcceleration, float DeltaSeconds, int Direction);
+ //(direction = Down = -1), (direction = Up = 1)
+
+ UPROPERTY() UCapsuleComponent* CapsuleColliderComponent = nullptr;
+ UPROPERTY() UCameraComponent* CameraComponent = nullptr;
+
+ float VerticalSpeed = 0.0f;
+ FVector LastCameraPosition;
+};
diff --git a/Source/DisplayClusterExtensions/Public/VirtualRealityPawn.h b/Source/DisplayClusterExtensions/Public/VirtualRealityPawn.h
index 5fc1b5f7..d23192d5 100644
--- a/Source/DisplayClusterExtensions/Public/VirtualRealityPawn.h
+++ b/Source/DisplayClusterExtensions/Public/VirtualRealityPawn.h
@@ -1,51 +1,52 @@
-// Fill out your copyright notice in the Description page of Project Settings.
-
-#pragma once
-
-#include "BasicVRInteractionComponent.h"
-#include "CoreMinimal.h"
-#include "GameFramework/DefaultPawn.h"
-#include "GameFramework/RotatingMovementComponent.h"
-#include "UniversalTrackedComponent.h"
-#include "VRPawnMovement.h"
-#include "VirtualRealityPawn.generated.h"
-
-/**
- *
- */
-UCLASS()
-class DISPLAYCLUSTEREXTENSIONS_API AVirtualRealityPawn : public APawn
-{
- GENERATED_BODY()
-public:
- AVirtualRealityPawn(const FObjectInitializer& ObjectInitializer);
-
- /* Proxy Components */
- UPROPERTY() UUniversalTrackedComponent* Head;
- UPROPERTY() UUniversalTrackedComponent* RightHand;
- UPROPERTY() UUniversalTrackedComponent* LeftHand;
- UPROPERTY() UUniversalTrackedComponent* Tracker1;
- UPROPERTY() UUniversalTrackedComponent* Tracker2;
- UPROPERTY() UBasicVRInteractionComponent* BasicVRInteraction;
-
- /* Movement */
- UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Pawn|Movement") UVRPawnMovement* PawnMovement;
- UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Movement") float BaseTurnRate = 45.0f;
-
-protected:
- virtual void BeginPlay() override;
- virtual void SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) override;
-
- /* Movement */
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnForward(float Value);
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnRight(float Value);
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnTurnRate(float Rate);
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnLookUpRate(float Rate);
-
- /* Interaction */
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Interaction") void OnBeginFire();
- UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Interaction") void OnEndFire();
-
- /* APawn Interface to be able to use AddMovementInput() */
- virtual UPawnMovementComponent* GetMovementComponent() const override;
-};
+// Fill out your copyright notice in the Description page of Project Settings.
+
+#pragma once
+
+#include "BasicVRInteractionComponent.h"
+#include "CoreMinimal.h"
+#include "GameFramework/DefaultPawn.h"
+#include "GameFramework/RotatingMovementComponent.h"
+#include "UniversalTrackedComponent.h"
+#include "VRPawnMovement.h"
+#include "VirtualRealityPawn.generated.h"
+
+/**
+ *
+ */
+UCLASS()
+class DISPLAYCLUSTEREXTENSIONS_API AVirtualRealityPawn : public APawn
+{
+ GENERATED_BODY()
+public:
+ AVirtualRealityPawn(const FObjectInitializer& ObjectInitializer);
+
+ /* Proxy */
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Proxy Objects") UUniversalTrackedComponent* Head;
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Proxy Objects") UUniversalTrackedComponent* RightHand;
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Proxy Objects") UUniversalTrackedComponent* LeftHand;
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Proxy Objects") UUniversalTrackedComponent* Tracker1;
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Proxy Objects") UUniversalTrackedComponent* Tracker2;
+
+ /* Interaction */
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Interaction") UBasicVRInteractionComponent* BasicVRInteraction;
+
+ /* Movement */
+ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Pawn|Movement") UVRPawnMovement* PawnMovement;
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Movement") float BaseTurnRate = 45.0f;
+
+ /* CameraComponent */
+ UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Pawn|Camera") UCameraComponent* CameraComponent;
+
+protected:
+ virtual void SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) override;
+
+ /* Movement */
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnForward(float Value);
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnRight(float Value);
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnTurnRate(float Rate);
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Movement") void OnLookUpRate(float Rate);
+
+ /* Interaction */
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Interaction") void OnBeginFire();
+ UFUNCTION(BlueprintNativeEvent, BlueprintCallable, Category = "Pawn|Interaction") void OnEndFire();
+};
--
GitLab