|
|
|
@@ -35,26 +35,20 @@
|
|
|
|
|
|
|
|
|
|
#include "SGTracking/SGXRTracker.h"
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
#include "Async/Async.h"
|
|
|
|
|
#include "Async/Future.h"
|
|
|
|
|
#include "Async/TaskGraphInterfaces.h"
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
#include "Containers/Array.h"
|
|
|
|
|
#include "Containers/Map.h"
|
|
|
|
|
#include "Engine/Engine.h"
|
|
|
|
|
#include "Engine/SkeletalMesh.h"
|
|
|
|
|
#include "Engine/World.h"
|
|
|
|
|
#include "GameFramework/WorldSettings.h"
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4
|
|
|
|
|
#include "IOpenXRHMD.h"
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
#include "IOpenXRHMDModule.h"
|
|
|
|
|
#include "IXRTrackingSystem.h"
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
#include "Misc/Optional.h"
|
|
|
|
|
#include "Misc/Timespan.h"
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
#include "OpenXRCore.h"
|
|
|
|
|
|
|
|
|
|
#include "SGCore/SGHapticGlove.h"
|
|
|
|
@@ -1013,237 +1007,6 @@ FTransform FSGXRTracker::FImpl::GetMeshFingerStartBoneRefTransform(
|
|
|
|
|
return Transform;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION < 7
|
|
|
|
|
|
|
|
|
|
bool FSGXRTracker::GetMotionControllerData(
|
|
|
|
|
UObject* WorldContextObject,
|
|
|
|
|
const EControllerHand Hand,
|
|
|
|
|
FXRMotionControllerData& OutMotionControllerData)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.DeviceName = NAME_None;
|
|
|
|
|
OutMotionControllerData.ApplicationInstanceID = FApp::GetInstanceId();
|
|
|
|
|
OutMotionControllerData.DeviceVisualType = EXRVisualType::Controller;
|
|
|
|
|
OutMotionControllerData.TrackingStatus = ETrackingStatus::NotTracked;
|
|
|
|
|
OutMotionControllerData.HandIndex = Hand;
|
|
|
|
|
OutMotionControllerData.bValid = false;
|
|
|
|
|
|
|
|
|
|
if (!IsValid(WorldContextObject))
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
IXRTrackingSystem* XRTrackingSystem{GEngine ? GEngine->XRSystem.Get() : nullptr};
|
|
|
|
|
if (!XRTrackingSystem)
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4
|
|
|
|
|
IOpenXRHMD* OpenXRHMD{XRTrackingSystem->GetIOpenXRHMD()};
|
|
|
|
|
#else /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
FOpenXRHMD* OpenXRHMD{static_cast<FOpenXRHMD*>(GEngine->XRSystem.Get())};
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
if (!OpenXRHMD)
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
TArray<int32> Devices;
|
|
|
|
|
const int32 HandIndex = static_cast<int32>(Hand);
|
|
|
|
|
const bool bGotDevices =
|
|
|
|
|
XRTrackingSystem->EnumerateTrackedDevices(Devices, EXRTrackedDeviceType::Controller);
|
|
|
|
|
if (bGotDevices && Devices.IsValidIndex(HandIndex))
|
|
|
|
|
{
|
|
|
|
|
const XrSession Session{OpenXRHMD->GetSession()};
|
|
|
|
|
if (Session)
|
|
|
|
|
{
|
|
|
|
|
XrInteractionProfileState Profile = {XR_TYPE_INTERACTION_PROFILE_STATE};
|
|
|
|
|
const XrPath TopLevelUserPath{OpenXRHMD->GetTrackedDevicePath(Devices[HandIndex])};
|
|
|
|
|
const XrResult CurrentInteractionProfile{
|
|
|
|
|
xrGetCurrentInteractionProfile(Session, TopLevelUserPath, &Profile)
|
|
|
|
|
};
|
|
|
|
|
if (XR_SUCCEEDED(CurrentInteractionProfile) && Profile.interactionProfile != XR_NULL_PATH)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.DeviceName = FOpenXRPath(Profile.interactionProfile);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static const FName HandTrackerName{"OpenXRHandTracking"};
|
|
|
|
|
TArray<IHandTracker*> HandTrackers = IModularFeatures::Get().GetModularFeatureImplementations<IHandTracker>(
|
|
|
|
|
IHandTracker::GetModularFeatureName());
|
|
|
|
|
IHandTracker* HandTracker{nullptr};
|
|
|
|
|
for (IHandTracker* HandTrackerIterator: HandTrackers)
|
|
|
|
|
{
|
|
|
|
|
if (!HandTrackerIterator)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const FName DeviceTypeName{HandTrackerIterator->GetHandTrackerDeviceTypeName()};
|
|
|
|
|
if (DeviceTypeName != HandTrackerName)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
FSGXRTracker* SGXRTracker{static_cast<FSGXRTracker*>(HandTrackerIterator)};
|
|
|
|
|
if (!SGXRTracker)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
HandTracker = SGXRTracker;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (Hand == EControllerHand::Left || Hand == EControllerHand::Right)
|
|
|
|
|
{
|
|
|
|
|
static const FName MotionControllerName("OpenXR");
|
|
|
|
|
TArray<IMotionController*> MotionControllers{
|
|
|
|
|
IModularFeatures::Get().GetModularFeatureImplementations<IMotionController>(
|
|
|
|
|
IMotionController::GetModularFeatureName())
|
|
|
|
|
};
|
|
|
|
|
IMotionController* MotionController{nullptr};
|
|
|
|
|
for (IMotionController* MotionControllerIterator: MotionControllers)
|
|
|
|
|
{
|
|
|
|
|
if (!MotionControllerIterator)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const FName DeviceTypeName{MotionControllerIterator->GetMotionControllerDeviceTypeName()};
|
|
|
|
|
if (DeviceTypeName != MotionControllerName)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
MotionController = MotionControllerIterator;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const float WorldToMeters = XRTrackingSystem->GetWorldToMetersScale();
|
|
|
|
|
if (MotionController)
|
|
|
|
|
{
|
|
|
|
|
const FTransform TrackingToWorld{XRTrackingSystem->GetTrackingToWorldTransform()};
|
|
|
|
|
|
|
|
|
|
{
|
|
|
|
|
const FName AimSource{Hand == EControllerHand::Left ? FName{TEXT("LeftAim")} : FName{TEXT("RightAim")}};
|
|
|
|
|
FRotator AimSourceRotation;
|
|
|
|
|
FVector AimSourcePosition;
|
|
|
|
|
const bool bGotAimOrientationAndPosition =
|
|
|
|
|
MotionController->GetControllerOrientationAndPosition(
|
|
|
|
|
0, AimSource, AimSourceRotation, AimSourcePosition, WorldToMeters);
|
|
|
|
|
if (bGotAimOrientationAndPosition)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.AimPosition = TrackingToWorld.TransformPosition(AimSourcePosition);
|
|
|
|
|
OutMotionControllerData.AimRotation =
|
|
|
|
|
TrackingToWorld.TransformRotation(AimSourceRotation.Quaternion());
|
|
|
|
|
}
|
|
|
|
|
OutMotionControllerData.bValid |= bGotAimOrientationAndPosition;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const FName GripSource{Hand == EControllerHand::Left ? FName{TEXT("LeftGrip")} : FName{TEXT("RightGrip")}};
|
|
|
|
|
{
|
|
|
|
|
FRotator GripRotation;
|
|
|
|
|
FVector GripPosition;
|
|
|
|
|
const bool bGotGripSourceOrientationAndPosition =
|
|
|
|
|
MotionController->GetControllerOrientationAndPosition(
|
|
|
|
|
0, GripSource, GripRotation, GripPosition, WorldToMeters);
|
|
|
|
|
if (bGotGripSourceOrientationAndPosition)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.GripPosition = TrackingToWorld.TransformPosition(GripPosition);
|
|
|
|
|
OutMotionControllerData.GripRotation =
|
|
|
|
|
TrackingToWorld.TransformRotation(GripRotation.Quaternion());
|
|
|
|
|
}
|
|
|
|
|
OutMotionControllerData.bValid |= bGotGripSourceOrientationAndPosition;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
{
|
|
|
|
|
const FName PalmSource{
|
|
|
|
|
Hand == EControllerHand::Left ? FName{TEXT("LeftPalm")} : FName{TEXT("RightPalm")}
|
|
|
|
|
};
|
|
|
|
|
FRotator PalmRotation;
|
|
|
|
|
FVector PalmPosition;
|
|
|
|
|
const bool bGotPalmOrientationAndPosition = MotionController->GetControllerOrientationAndPosition(
|
|
|
|
|
0, PalmSource, PalmRotation, PalmPosition, WorldToMeters);
|
|
|
|
|
if (bGotPalmOrientationAndPosition)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.GripPosition = TrackingToWorld.TransformPosition(PalmPosition);
|
|
|
|
|
OutMotionControllerData.GripRotation =
|
|
|
|
|
TrackingToWorld.TransformRotation(PalmRotation.Quaternion());
|
|
|
|
|
}
|
|
|
|
|
OutMotionControllerData.bValid |= bGotPalmOrientationAndPosition;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
OutMotionControllerData.TrackingStatus = MotionController->GetControllerTrackingStatus(0, GripSource);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const bool bHandTrackingStateValid = HandTracker && HandTracker->IsHandTrackingStateValid();
|
|
|
|
|
if (bHandTrackingStateValid)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.DeviceVisualType = EXRVisualType::Hand;
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
bool bTracked = false;
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
|
|
|
|
|
OutMotionControllerData.bValid = HandTracker->GetAllKeypointStates(
|
|
|
|
|
Hand,
|
|
|
|
|
OutMotionControllerData.HandKeyPositions,
|
|
|
|
|
OutMotionControllerData.HandKeyRotations,
|
|
|
|
|
OutMotionControllerData.HandKeyRadii
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
, bTracked
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
// Unused!
|
|
|
|
|
(void) bTracked;
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
// TODO
|
|
|
|
|
// Begin backward compatibility with the deprecated function, remove this block along with the deprecated
|
|
|
|
|
// GetAllKeypointStates (though it should be time to remove this entire function as well)!
|
|
|
|
|
if (!OutMotionControllerData.bValid)
|
|
|
|
|
{
|
|
|
|
|
PRAGMA_DISABLE_DEPRECATION_WARNINGS
|
|
|
|
|
OutMotionControllerData.bValid = HandTracker->GetAllKeypointStates(
|
|
|
|
|
Hand,
|
|
|
|
|
OutMotionControllerData.HandKeyPositions,
|
|
|
|
|
OutMotionControllerData.HandKeyRotations,
|
|
|
|
|
OutMotionControllerData.HandKeyRadii);
|
|
|
|
|
PRAGMA_ENABLE_DEPRECATION_WARNINGS
|
|
|
|
|
}
|
|
|
|
|
// End backward compability.
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
|
|
|
|
|
if (!ensureAlwaysMsgf(
|
|
|
|
|
!OutMotionControllerData.bValid
|
|
|
|
|
|| (OutMotionControllerData.HandKeyPositions.Num() == EHandKeypointCount
|
|
|
|
|
&& OutMotionControllerData.HandKeyRotations.Num() == EHandKeypointCount
|
|
|
|
|
&& OutMotionControllerData.HandKeyRadii.Num() == EHandKeypointCount),
|
|
|
|
|
TEXT("Corrupted OutMotionControllerData!")))
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.bValid = false;
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (OutMotionControllerData.bValid)
|
|
|
|
|
{
|
|
|
|
|
OutMotionControllerData.TrackingStatus = ETrackingStatus::Tracked;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return OutMotionControllerData.bValid;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION < 7 */
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
|
|
|
|
|
bool FSGXRTracker::GetMotionControllerState(
|
|
|
|
|
UObject* WorldContextObject,
|
|
|
|
|
const EXRSpaceType XRSpaceType, const EControllerHand Hand, const EXRControllerPoseType XRControllerPoseType,
|
|
|
|
@@ -1313,11 +1076,7 @@ bool FSGXRTracker::GetMotionControllerState(
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4
|
|
|
|
|
IOpenXRHMD* OpenXRHMD{XRTrackingSystem->GetIOpenXRHMD()};
|
|
|
|
|
#else /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
FOpenXRHMD* OpenXRHMD{static_cast<FOpenXRHMD*>(GEngine->XRSystem.Get())};
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
if (!OpenXRHMD)
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
@@ -1450,11 +1209,7 @@ bool FSGXRTracker::GetHandTrackingState(
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4
|
|
|
|
|
IOpenXRHMD* OpenXRHMD{XRTrackingSystem->GetIOpenXRHMD()};
|
|
|
|
|
#else /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
FOpenXRHMD* OpenXRHMD{static_cast<FOpenXRHMD*>(GEngine->XRSystem.Get())};
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 4 */
|
|
|
|
|
if (!OpenXRHMD)
|
|
|
|
|
{
|
|
|
|
|
return false;
|
|
|
|
@@ -1486,25 +1241,6 @@ bool FSGXRTracker::GetHandTrackingState(
|
|
|
|
|
OutHandTrackingState.HandKeyRadii,
|
|
|
|
|
bTracked);
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION < 7
|
|
|
|
|
/// TODO
|
|
|
|
|
// Begin backward compatibility with the deprecated function, remove this block along with the deprecated
|
|
|
|
|
// GetAllKeypointStates.
|
|
|
|
|
if (!OutHandTrackingState.bValid)
|
|
|
|
|
{
|
|
|
|
|
PRAGMA_DISABLE_DEPRECATION_WARNINGS
|
|
|
|
|
OutHandTrackingState.bValid = HandTracker->GetAllKeypointStates(
|
|
|
|
|
Hand,
|
|
|
|
|
OutHandTrackingState.HandKeyLocations,
|
|
|
|
|
OutHandTrackingState.HandKeyRotations,
|
|
|
|
|
OutHandTrackingState.HandKeyRadii);
|
|
|
|
|
PRAGMA_ENABLE_DEPRECATION_WARNINGS
|
|
|
|
|
bTracked = OutHandTrackingState.bValid;
|
|
|
|
|
// The inability to distinguish this is the reason for the deprecation.
|
|
|
|
|
}
|
|
|
|
|
// End backward compability.
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION < 7 */
|
|
|
|
|
|
|
|
|
|
if (!ensureAlwaysMsgf(
|
|
|
|
|
!OutHandTrackingState.bValid
|
|
|
|
|
|| (OutHandTrackingState.HandKeyLocations.Num() == EHandKeypointCount
|
|
|
|
@@ -1526,8 +1262,6 @@ bool FSGXRTracker::GetHandTrackingState(
|
|
|
|
|
return OutHandTrackingState.bValid;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
|
|
|
|
|
FSGXRTracker::FSGXRTracker(const TSharedRef<FGenericApplicationMessageHandler>& InMessageHandler)
|
|
|
|
|
: Pimpl(TUniquePtr<FImpl, FImplDeleter>(new FImpl{this}, PimplDeleter))
|
|
|
|
|
{
|
|
|
|
@@ -1912,17 +1646,10 @@ bool FSGXRTracker::GetKeypointState(
|
|
|
|
|
return bGotTransform;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
bool FSGXRTracker::GetAllKeypointStates(
|
|
|
|
|
const EControllerHand Hand,
|
|
|
|
|
TArray<FVector>& OutPositions, TArray<FQuat>& OutRotations, TArray<float>& OutRadii,
|
|
|
|
|
bool& OutIsTracked) const
|
|
|
|
|
#else /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
bool FSGXRTracker::GetAllKeypointStates(
|
|
|
|
|
const EControllerHand Hand,
|
|
|
|
|
TArray<FVector>& OutPositions, TArray<FQuat>& OutRotations, TArray<float>& OutRadii) const
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5*/
|
|
|
|
|
|
|
|
|
|
{
|
|
|
|
|
if (!IsHandTrackingStateValid())
|
|
|
|
|
{
|
|
|
|
@@ -1948,9 +1675,7 @@ bool FSGXRTracker::GetAllKeypointStates(
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
OutIsTracked = HandState.bTracked;
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5*/
|
|
|
|
|
|
|
|
|
|
// If we ever received poses we return the last data we received, even if not currently tracking to avoid poping
|
|
|
|
|
// back to (0.0f, 0.0f, 0.0f) and the like.
|
|
|
|
@@ -2216,43 +1941,6 @@ bool FSGXRTracker::FImpl::GetControllerTransform(
|
|
|
|
|
IMotionController::GetModularFeatureName())
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION <= 4
|
|
|
|
|
for (const IMotionController* MotionController: MotionControllers)
|
|
|
|
|
{
|
|
|
|
|
if (!MotionController)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const ETrackingStatus TrackingStatus = MotionController->GetControllerTrackingStatus(
|
|
|
|
|
DeviceIndex, PositionalTrackingHardwareMotionSource);
|
|
|
|
|
if (TrackingStatus == ETrackingStatus::NotTracked)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
const FName DeviceTypeName{MotionController->GetMotionControllerDeviceTypeName()};
|
|
|
|
|
if (DeviceTypeName != TargetPositionalTrackingProviderName)
|
|
|
|
|
{
|
|
|
|
|
continue;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
FRotator Orientation;
|
|
|
|
|
FVector Position;
|
|
|
|
|
const bool bGotTransform = MotionController->GetControllerOrientationAndPosition(
|
|
|
|
|
DeviceIndex, PositionalTrackingHardwareMotionSource,
|
|
|
|
|
Orientation, Position, WorldToMetersScale);
|
|
|
|
|
if (bGotTransform)
|
|
|
|
|
{
|
|
|
|
|
OutTransform = FTransform{Orientation, Position};
|
|
|
|
|
bOutMotionSourceHandTracking = false;
|
|
|
|
|
bTracked = true;
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION <= 4 */
|
|
|
|
|
|
|
|
|
|
#if ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5
|
|
|
|
|
TPromise<TOptional<FTransform>> Promise;
|
|
|
|
|
const TFuture<TOptional<FTransform>> Future{Promise.GetFuture()};
|
|
|
|
|
|
|
|
|
@@ -2311,7 +1999,6 @@ bool FSGXRTracker::FImpl::GetControllerTransform(
|
|
|
|
|
bTracked = true;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
#endif /* ENGINE_MAJOR_VERSION >= 5 && ENGINE_MINOR_VERSION >= 5 */
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (!bTracked && bFallbackToHandTrackingIfNoGloveDetected)
|
|
|
|
|