From a5752a0c146866f51990fa1501d1ae0f1186268b Mon Sep 17 00:00:00 2001 From: Ehret <jw210150@WIN.RZ.RWTH-AACHEN.DE> Date: Wed, 12 Apr 2023 14:48:54 +0200 Subject: [PATCH 1/2] remove VRPawn reference from HUDHelper --- .../Private/HUD/SFHMDSpectatorHUDHelp.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp b/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp index 10bff55..369a4d0 100644 --- a/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp +++ b/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp @@ -58,15 +58,15 @@ void ASFHMDSpectatorHUDHelp::Tick(float DeltaSeconds) //the widget needs to be always be facing away, so we do not see it in the HMD view //we also move it down 10m so it does not get in our way when interacting etc. - APlayerController* PlayerController = GetWorld()->GetFirstPlayerController(); - AVirtualRealityPawn* Pawn = Cast<AVirtualRealityPawn>(PlayerController->AcknowledgedPawn); - FVector HeadPos = Pawn->Head->GetComponentLocation(); + const APlayerCameraManager* CamManager = GetWorld()->GetFirstPlayerController()->PlayerCameraManager; + FVector HeadPos = CamManager->GetCameraLocation(); SetActorLocation(HeadPos + 1000 * FVector::DownVector); SetActorRotation(FQuat::FindBetweenNormals(FVector(0,0,1),(GetActorLocation()-HeadPos).GetSafeNormal()).Rotator()); //Set cursor to the right place + APlayerController* PlayerController = GetWorld()->GetFirstPlayerController(); USFHUDWidget* HUDWidget = Cast<USFHUDWidget>(WidgetComponent->GetWidget()); FVector2D CursorPos = GetAbsoluteLocationForCursorWidgetFromMousePosition(PlayerController, DrawSize); HUDWidget->SetCursorWidgetPosition(CursorPos); -- GitLab From 04b4bbc4a62ede49a1a3528b9e21de70a8d53efa Mon Sep 17 00:00:00 2001 From: "jonathan.ehret" <ehret@vr.rwth-aachen.de> Date: Mon, 26 Jun 2023 14:28:59 +0200 Subject: [PATCH 2/2] remove RWTHVRToolkit entirely --- .../HUD/SFGlobalFadeGameViewportClient.cpp | 3 +- .../Private/HUD/SFHMDSpectatorHUDHelp.cpp | 1 - .../Private/HUD/SFMasterHUD.cpp | 7 +-- .../Private/Help/SFUtils.cpp | 26 ++++++++- .../Private/Logging/SFLoggingUtils.cpp | 1 - .../Private/SFGameInstance.cpp | 55 ++++++++++++++++++- .../Public/Help/SFUtils.h | 3 + .../Public/SFGameInstance.h | 11 +++- .../StudyFrameworkPlugin.Build.cs | 2 - StudyFrameworkPlugin.uplugin | 4 -- 10 files changed, 91 insertions(+), 22 deletions(-) diff --git a/Source/StudyFrameworkPlugin/Private/HUD/SFGlobalFadeGameViewportClient.cpp b/Source/StudyFrameworkPlugin/Private/HUD/SFGlobalFadeGameViewportClient.cpp index b8298ae..21eef3e 100644 --- a/Source/StudyFrameworkPlugin/Private/HUD/SFGlobalFadeGameViewportClient.cpp +++ b/Source/StudyFrameworkPlugin/Private/HUD/SFGlobalFadeGameViewportClient.cpp @@ -7,7 +7,6 @@ #include "Engine/Canvas.h" #include "HUD/SFMasterHUD.h" -#include "Utility/VirtualRealityUtilities.h" // Link to the Tutorial of the manual Viewport Client // https://nerivec.github.io/old-ue4-wiki/pages/global-fade-in-out.html @@ -77,7 +76,7 @@ void USFGlobalFadeGameViewportClient::DrawScreenFade(UCanvas* Canvas) MasterHUD = Cast<ASFMasterHUD>(PlayerController->GetHUD()); } - if (MasterHUD && UVirtualRealityUtilities::IsMaster()) + if (MasterHUD && FSFUtils::IsPrimary()) { //if we use the HUD let it do the fading, so it can still be seen when faded out MasterHUD->SetBackgroundAlpha(FadeColorTmp.A); diff --git a/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp b/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp index 369a4d0..95b8c03 100644 --- a/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp +++ b/Source/StudyFrameworkPlugin/Private/HUD/SFHMDSpectatorHUDHelp.cpp @@ -8,7 +8,6 @@ #include "IXRTrackingSystem.h" #include "HUD/SFHUDWidget.h" -#include "Pawn/VirtualRealityPawn.h" #include "GameFramework/PlayerController.h" #include "Slate/SceneViewport.h" diff --git a/Source/StudyFrameworkPlugin/Private/HUD/SFMasterHUD.cpp b/Source/StudyFrameworkPlugin/Private/HUD/SFMasterHUD.cpp index cc06658..e379ae9 100644 --- a/Source/StudyFrameworkPlugin/Private/HUD/SFMasterHUD.cpp +++ b/Source/StudyFrameworkPlugin/Private/HUD/SFMasterHUD.cpp @@ -8,7 +8,6 @@ #include "SFPlugin.h" #include "Help/SFUtils.h" -#include "Utility/VirtualRealityUtilities.h" #include "HeadMountedDisplayFunctionLibrary.h" @@ -18,7 +17,7 @@ ASFMasterHUD::ASFMasterHUD() void ASFMasterHUD::DrawHUD() { - if (UVirtualRealityUtilities::IsMaster()) + if (FSFUtils::IsPrimary()) { DrawBackground(); } @@ -49,13 +48,13 @@ void ASFMasterHUD::BeginPlay() } HMDHUDHelper = nullptr; - if (UVirtualRealityUtilities::IsHeadMountedMode()) + if (FSFUtils::IsHMD()) { HMDHUDHelper = Cast<ASFHMDSpectatorHUDHelp>( GetWorld()->SpawnActor(ASFHMDSpectatorHUDHelp::StaticClass())); HUDWidget = Cast<USFHUDWidget>(HMDHUDHelper->CreateWidget(SFWidgetClass)); } - else if (UVirtualRealityUtilities::IsMaster()) + else if (FSFUtils::IsPrimary()) { HUDWidget = CreateWidget<USFHUDWidget>(GetWorld(), SFWidgetClass); } diff --git a/Source/StudyFrameworkPlugin/Private/Help/SFUtils.cpp b/Source/StudyFrameworkPlugin/Private/Help/SFUtils.cpp index 2b90034..bc8c8ac 100644 --- a/Source/StudyFrameworkPlugin/Private/Help/SFUtils.cpp +++ b/Source/StudyFrameworkPlugin/Private/Help/SFUtils.cpp @@ -6,18 +6,19 @@ #include "Misc/MessageDialog.h" #include "Misc/FileHelper.h" +#include "AudioDevice.h" + #include "Json.h" #include "SFPlugin.h" #include "SFGameInstance.h" -#include "Utility/VirtualRealityUtilities.h" #include "IUniversalLogging.h" void FSFUtils::OpenMessageBox(const FString Text, const bool bError/*=false*/) { - if (!UVirtualRealityUtilities::IsMaster()) + if (!IsPrimary()) { return; } @@ -119,3 +120,24 @@ FString FSFUtils::GetStudyFrameworkPath() { return FPaths::ProjectDir() + "StudyFramework/"; } + +bool FSFUtils::IsPrimary() +{ + if (!IDisplayCluster::IsAvailable()) + { + return true; + } + IDisplayClusterClusterManager* Manager = IDisplayCluster::Get().GetClusterMgr(); + if (Manager == nullptr) + { + return true; // if we are not in cluster mode, we are always the master + } + return Manager->IsMaster() || !Manager->IsSlave(); +} + +bool FSFUtils::IsHMD() +{ + // In editor builds: checks for EdEngine->IsVRPreviewActive() + // In packaged builds: checks for `-vr` in commandline or bStartInVR in UGeneralProjectSettings + return FAudioDevice::CanUseVRAudioDevice(); +} diff --git a/Source/StudyFrameworkPlugin/Private/Logging/SFLoggingUtils.cpp b/Source/StudyFrameworkPlugin/Private/Logging/SFLoggingUtils.cpp index 512da7e..2a886f3 100644 --- a/Source/StudyFrameworkPlugin/Private/Logging/SFLoggingUtils.cpp +++ b/Source/StudyFrameworkPlugin/Private/Logging/SFLoggingUtils.cpp @@ -6,7 +6,6 @@ #include "SFGameInstance.h" -#include "Utility/VirtualRealityUtilities.h" #include "IUniversalLogging.h" #include "Help/SFUtils.h" diff --git a/Source/StudyFrameworkPlugin/Private/SFGameInstance.cpp b/Source/StudyFrameworkPlugin/Private/SFGameInstance.cpp index f0f25eb..e6ae56d 100644 --- a/Source/StudyFrameworkPlugin/Private/SFGameInstance.cpp +++ b/Source/StudyFrameworkPlugin/Private/SFGameInstance.cpp @@ -26,7 +26,13 @@ void USFGameInstance::Init() GEngine->GameViewportClientClass = USFGlobalFadeGameViewportClient::StaticClass(); - GoToConditionSyncedEvent.Attach(this); + IDisplayClusterClusterManager* ClusterManager = IDisplayCluster::Get().GetClusterMgr(); + if (ClusterManager && !ClusterEventListenerDelegate.IsBound()) + { + ClusterEventListenerDelegate = FOnClusterEventJsonListener::CreateUObject(this, &USFGameInstance::HandleClusterEvent); + ClusterManager->AddClusterEventJsonListener(ClusterEventListenerDelegate); + } + Instance = this; LogObject = NewObject<USFLogObject>(); @@ -53,7 +59,14 @@ void USFGameInstance::Init() void USFGameInstance::Shutdown() { - GoToConditionSyncedEvent.Detach(); + + IDisplayClusterClusterManager* ClusterManager = IDisplayCluster::Get().GetClusterMgr(); + if (ClusterManager && ClusterEventListenerDelegate.IsBound()) + { + ClusterManager->RemoveClusterEventJsonListener(ClusterEventListenerDelegate); + } + + if(ExperimenterWindow) { ExperimenterWindow->DestroyWindow(); @@ -432,11 +445,47 @@ bool USFGameInstance::GoToCondition(const USFCondition* Condition, bool bForced FSFLoggingUtils::Log("[USFGameInstance::GoToCondition()]: Could not load next condition.", true); return false; } - GoToConditionSyncedEvent.Send(Condition->UniqueName, bForced); + GoToConditionSynced(Condition->UniqueName, bForced); return true; } void USFGameInstance::GoToConditionSynced(FString ConditionName, bool bForced) +{ + const EDisplayClusterOperationMode OperationMode = IDisplayCluster::Get().GetOperationMode(); + if (OperationMode != EDisplayClusterOperationMode::Cluster) + { + HandleGoToConditionSynced(ConditionName, bForced); + } + else + { + IDisplayClusterClusterManager* ClusterManager = IDisplayCluster::Get().GetClusterMgr(); + check(ClusterManager != nullptr); + + FDisplayClusterClusterEventJson ClusterEvent; + ClusterEvent.Type = "SFGameInstanceEvent"; + ClusterEvent.Name = "GoToConditionSynced"; + TMap<FString, FString> Params; + Params.Add("ConditionName", ConditionName); + Params.Add("bForced", bForced ?"true":"false"); + ClusterEvent.Parameters = Params; + ClusterEvent.bShouldDiscardOnRepeat = true; + + ClusterManager->EmitClusterEventJson(ClusterEvent, true); + } +} + +void USFGameInstance::HandleClusterEvent(const FDisplayClusterClusterEventJson& Event) { + if (Event.Type == "SFGameInstanceEvent") { + //now we actually react on all cluster nodes: + if(Event.Name == "GoToConditionSynced") + { + HandleGoToConditionSynced(Event.Parameters["ConditionName"], Event.Parameters["bForced"] == "true"); + } + } +} + + +void USFGameInstance::HandleGoToConditionSynced(FString ConditionName, bool bForced) { USFCondition* NextCondition = nullptr; for (USFCondition* Condition : Participant->GetAllConditions()) diff --git a/Source/StudyFrameworkPlugin/Public/Help/SFUtils.h b/Source/StudyFrameworkPlugin/Public/Help/SFUtils.h index c70caa2..a6fcd43 100644 --- a/Source/StudyFrameworkPlugin/Public/Help/SFUtils.h +++ b/Source/StudyFrameworkPlugin/Public/Help/SFUtils.h @@ -28,4 +28,7 @@ public: static UWorld* GetWorld(); static FString GetStudyFrameworkPath(); + + static bool IsPrimary(); + static bool IsHMD(); }; \ No newline at end of file diff --git a/Source/StudyFrameworkPlugin/Public/SFGameInstance.h b/Source/StudyFrameworkPlugin/Public/SFGameInstance.h index bcc32ff..a83a61f 100644 --- a/Source/StudyFrameworkPlugin/Public/SFGameInstance.h +++ b/Source/StudyFrameworkPlugin/Public/SFGameInstance.h @@ -11,7 +11,8 @@ #include "HUD/SFMasterHUD.h" #include "GazeTracking/SFGazeTracker.h" -#include "Events/DisplayClusterEventWrapper.h" +#include "Cluster/IDisplayClusterClusterManager.h" +#include "Cluster/DisplayClusterClusterEvent.h" #include "Widgets/SWindow.h" @@ -164,8 +165,12 @@ protected: void EndStudy(); - void GoToConditionSynced(FString ConditionName, bool bForced); - DECLARE_DISPLAY_CLUSTER_EVENT(USFGameInstance, GoToConditionSynced); + //we use cluster events so GoToConditionSynced can not run out of sync when using nDisplay in cluster mode + void GoToConditionSynced(FString ConditionName, bool bForced); //send the cluster event + void HandleGoToConditionSynced(FString ConditionName, bool bForced); //process the cluter event + FOnClusterEventJsonListener ClusterEventListenerDelegate; + void HandleClusterEvent(const FDisplayClusterClusterEventJson& Event); + void RestoreLastParticipantForDebugStart(USFCondition* InStartCondition); //method called by a timer if we want to directly fade in on startup diff --git a/Source/StudyFrameworkPlugin/StudyFrameworkPlugin.Build.cs b/Source/StudyFrameworkPlugin/StudyFrameworkPlugin.Build.cs index 2a0da1b..d506a13 100644 --- a/Source/StudyFrameworkPlugin/StudyFrameworkPlugin.Build.cs +++ b/Source/StudyFrameworkPlugin/StudyFrameworkPlugin.Build.cs @@ -35,8 +35,6 @@ public class StudyFrameworkPlugin : ModuleRules "CoreUObject", "Engine", "DisplayCluster", - "RWTHVRToolkit", - "RWTHVRCluster", "InputCore", "Sockets", "Json", diff --git a/StudyFrameworkPlugin.uplugin b/StudyFrameworkPlugin.uplugin index 1345244..238dc94 100644 --- a/StudyFrameworkPlugin.uplugin +++ b/StudyFrameworkPlugin.uplugin @@ -25,10 +25,6 @@ "Name": "nDisplay", "Enabled": true }, - { - "Name": "RWTHVRToolkit", - "Enabled": true - }, { "Name": "UniversalLogging", "Enabled": true -- GitLab