Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--intern/ghost/intern/GHOST_XrSession.cpp45
-rw-r--r--source/blender/makesdna/DNA_xr_types.h1
-rw-r--r--source/blender/makesrna/intern/rna_xr.c88
-rw-r--r--source/blender/windowmanager/xr/intern/wm_xr_draw.c4
-rw-r--r--source/blender/windowmanager/xr/intern/wm_xr_session.c18
5 files changed, 129 insertions, 27 deletions
diff --git a/intern/ghost/intern/GHOST_XrSession.cpp b/intern/ghost/intern/GHOST_XrSession.cpp
index 35280e77e22..263b2b6cfbd 100644
--- a/intern/ghost/intern/GHOST_XrSession.cpp
+++ b/intern/ghost/intern/GHOST_XrSession.cpp
@@ -120,7 +120,7 @@ static void create_reference_spaces(OpenXRSessionData &oxr, const GHOST_XrPose &
XrReferenceSpaceCreateInfo create_info = {XR_TYPE_REFERENCE_SPACE_CREATE_INFO};
create_info.poseInReferenceSpace.orientation.w = 1.0f;
- create_info.referenceSpaceType = XR_REFERENCE_SPACE_TYPE_LOCAL;
+ create_info.referenceSpaceType = XR_REFERENCE_SPACE_TYPE_STAGE;
#if 0
/* TODO
*
@@ -144,8 +144,47 @@ static void create_reference_spaces(OpenXRSessionData &oxr, const GHOST_XrPose &
(void)base_pose;
#endif
- CHECK_XR(xrCreateReferenceSpace(oxr.session, &create_info, &oxr.reference_space),
- "Failed to create reference space.");
+ XrResult result = xrCreateReferenceSpace(oxr.session, &create_info, &oxr.reference_space);
+
+ if (XR_FAILED(result)) {
+ /* One of the rare cases where we don't want to immediately throw an exception on failure,
+ * since runtimes are not required to support the stage reference space. Although we need the
+ * stage reference space for absolute tracking, if the runtime doesn't support it then just
+ * fallback to the local space. */
+ if (result == XR_ERROR_REFERENCE_SPACE_UNSUPPORTED) {
+ printf(
+ "Warning: XR runtime does not support stage reference space, disabling absolute "
+ "tracking.\n");
+
+ create_info.referenceSpaceType = XR_REFERENCE_SPACE_TYPE_LOCAL;
+ CHECK_XR(xrCreateReferenceSpace(oxr.session, &create_info, &oxr.reference_space),
+ "Failed to create local reference space.");
+ }
+ else {
+ throw GHOST_XrException("Failed to create stage reference space.", result);
+ }
+ }
+ else {
+ /* Check if tracking bounds are valid. Tracking bounds may be invalid if the user did not
+ * define a tracking space via the XR runtime. */
+ XrExtent2Df extents;
+ CHECK_XR(xrGetReferenceSpaceBoundsRect(oxr.session, XR_REFERENCE_SPACE_TYPE_STAGE, &extents),
+ "Failed to get stage reference space bounds.");
+ if (extents.width == 0.0f || extents.height == 0.0f) {
+ printf(
+ "Warning: Invalid stage reference space bounds, disabling absolute tracking. To enable "
+ "absolute tracking, please define a tracking space via the XR runtime.\n");
+
+ /* Fallback to local space. */
+ if (oxr.reference_space != XR_NULL_HANDLE) {
+ CHECK_XR(xrDestroySpace(oxr.reference_space), "Failed to destroy stage reference space.");
+ }
+
+ create_info.referenceSpaceType = XR_REFERENCE_SPACE_TYPE_LOCAL;
+ CHECK_XR(xrCreateReferenceSpace(oxr.session, &create_info, &oxr.reference_space),
+ "Failed to create local reference space.");
+ }
+ }
create_info.referenceSpaceType = XR_REFERENCE_SPACE_TYPE_VIEW;
CHECK_XR(xrCreateReferenceSpace(oxr.session, &create_info, &oxr.view_space),
diff --git a/source/blender/makesdna/DNA_xr_types.h b/source/blender/makesdna/DNA_xr_types.h
index 8e63760fef7..fc00d5eb839 100644
--- a/source/blender/makesdna/DNA_xr_types.h
+++ b/source/blender/makesdna/DNA_xr_types.h
@@ -50,6 +50,7 @@ typedef struct XrSessionSettings {
typedef enum eXrSessionFlag {
XR_SESSION_USE_POSITION_TRACKING = (1 << 0),
+ XR_SESSION_USE_ABSOLUTE_TRACKING = (1 << 1),
} eXrSessionFlag;
typedef enum eXRSessionBasePoseType {
diff --git a/source/blender/makesrna/intern/rna_xr.c b/source/blender/makesrna/intern/rna_xr.c
index 04a8500d136..56e8418972c 100644
--- a/source/blender/makesrna/intern/rna_xr.c
+++ b/source/blender/makesrna/intern/rna_xr.c
@@ -34,6 +34,63 @@
# include "WM_api.h"
+# ifdef WITH_XR_OPENXR
+static wmXrData *rna_XrSession_wm_xr_data_get(PointerRNA *ptr)
+{
+ /* Callers could also get XrSessionState pointer through ptr->data, but prefer if we just
+ * consistently pass wmXrData pointers to the WM_xr_xxx() API. */
+
+ BLI_assert((ptr->type == &RNA_XrSessionSettings) || (ptr->type == &RNA_XrSessionState));
+
+ wmWindowManager *wm = (wmWindowManager *)ptr->owner_id;
+ BLI_assert(wm && (GS(wm->id.name) == ID_WM));
+
+ return &wm->xr;
+}
+# endif
+
+static bool rna_XrSessionSettings_use_positional_tracking_get(PointerRNA *ptr)
+{
+# ifdef WITH_XR_OPENXR
+ const wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
+ return (xr->session_settings.flag & XR_SESSION_USE_POSITION_TRACKING) != 0;
+# else
+ UNUSED_VARS(ptr);
+ return false;
+# endif
+}
+
+static void rna_XrSessionSettings_use_positional_tracking_set(PointerRNA *ptr, bool value)
+{
+# ifdef WITH_XR_OPENXR
+ wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
+ SET_FLAG_FROM_TEST(xr->session_settings.flag, value, XR_SESSION_USE_POSITION_TRACKING);
+# else
+ UNUSED_VARS(ptr, value);
+# endif
+}
+
+static bool rna_XrSessionSettings_use_absolute_tracking_get(PointerRNA *ptr)
+{
+# ifdef WITH_XR_OPENXR
+ const wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
+ return (xr->session_settings.flag & XR_SESSION_USE_ABSOLUTE_TRACKING) != 0;
+# else
+ UNUSED_VARS(ptr);
+ return false;
+# endif
+}
+
+static void rna_XrSessionSettings_use_absolute_tracking_set(PointerRNA *ptr, bool value)
+{
+# ifdef WITH_XR_OPENXR
+ wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
+ SET_FLAG_FROM_TEST(xr->session_settings.flag, value, XR_SESSION_USE_ABSOLUTE_TRACKING);
+# else
+ UNUSED_VARS(ptr, value);
+# endif
+}
+
static bool rna_XrSessionState_is_running(bContext *C)
{
# ifdef WITH_XR_OPENXR
@@ -55,25 +112,10 @@ static void rna_XrSessionState_reset_to_base_pose(bContext *C)
# endif
}
-# ifdef WITH_XR_OPENXR
-static wmXrData *rna_XrSessionState_wm_xr_data_get(PointerRNA *ptr)
-{
- /* Callers could also get XrSessionState pointer through ptr->data, but prefer if we just
- * consistently pass wmXrData pointers to the WM_xr_xxx() API. */
-
- BLI_assert(ptr->type == &RNA_XrSessionState);
-
- wmWindowManager *wm = (wmWindowManager *)ptr->owner_id;
- BLI_assert(wm && (GS(wm->id.name) == ID_WM));
-
- return &wm->xr;
-}
-# endif
-
static void rna_XrSessionState_viewer_pose_location_get(PointerRNA *ptr, float *r_values)
{
# ifdef WITH_XR_OPENXR
- const wmXrData *xr = rna_XrSessionState_wm_xr_data_get(ptr);
+ const wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
WM_xr_session_state_viewer_pose_location_get(xr, r_values);
# else
UNUSED_VARS(ptr);
@@ -84,7 +126,7 @@ static void rna_XrSessionState_viewer_pose_location_get(PointerRNA *ptr, float *
static void rna_XrSessionState_viewer_pose_rotation_get(PointerRNA *ptr, float *r_values)
{
# ifdef WITH_XR_OPENXR
- const wmXrData *xr = rna_XrSessionState_wm_xr_data_get(ptr);
+ const wmXrData *xr = rna_XrSession_wm_xr_data_get(ptr);
WM_xr_session_state_viewer_pose_rotation_get(xr, r_values);
# else
UNUSED_VARS(ptr);
@@ -181,12 +223,22 @@ static void rna_def_xr_session_settings(BlenderRNA *brna)
RNA_def_property_update(prop, NC_WM | ND_XR_DATA_CHANGED, NULL);
prop = RNA_def_property(srna, "use_positional_tracking", PROP_BOOLEAN, PROP_NONE);
- RNA_def_property_boolean_sdna(prop, NULL, "flag", XR_SESSION_USE_POSITION_TRACKING);
+ RNA_def_property_boolean_funcs(prop,
+ "rna_XrSessionSettings_use_positional_tracking_get",
+ "rna_XrSessionSettings_use_positional_tracking_set");
RNA_def_property_ui_text(
prop,
"Positional Tracking",
"Allow VR headsets to affect the location in virtual space, in addition to the rotation");
RNA_def_property_update(prop, NC_WM | ND_XR_DATA_CHANGED, NULL);
+
+ prop = RNA_def_property(srna, "use_absolute_tracking", PROP_BOOLEAN, PROP_NONE);
+ RNA_def_property_boolean_funcs(prop,
+ "rna_XrSessionSettings_use_absolute_tracking_get",
+ "rna_XrSessionSettings_use_absolute_tracking_set");
+ RNA_def_property_ui_text(
+ prop, "Absolute Tracking", "Use unadjusted location/rotation as defined by the XR runtime");
+ RNA_def_property_update(prop, NC_WM | ND_XR_DATA_CHANGED, NULL);
}
static void rna_def_xr_session_state(BlenderRNA *brna)
diff --git a/source/blender/windowmanager/xr/intern/wm_xr_draw.c b/source/blender/windowmanager/xr/intern/wm_xr_draw.c
index 1f722855696..bef88505488 100644
--- a/source/blender/windowmanager/xr/intern/wm_xr_draw.c
+++ b/source/blender/windowmanager/xr/intern/wm_xr_draw.c
@@ -61,10 +61,12 @@ static void wm_xr_draw_matrices_create(const wmXrDrawData *draw_data,
copy_qt_qt(eye_pose.orientation_quat, draw_view->eye_pose.orientation_quat);
copy_v3_v3(eye_pose.position, draw_view->eye_pose.position);
- sub_v3_v3(eye_pose.position, draw_data->eye_position_ofs);
if ((session_settings->flag & XR_SESSION_USE_POSITION_TRACKING) == 0) {
sub_v3_v3(eye_pose.position, draw_view->local_pose.position);
}
+ if ((session_settings->flag & XR_SESSION_USE_ABSOLUTE_TRACKING) == 0) {
+ sub_v3_v3(eye_pose.position, draw_data->eye_position_ofs);
+ }
perspective_m4_fov(r_proj_mat,
draw_view->fov.angle_left,
diff --git a/source/blender/windowmanager/xr/intern/wm_xr_session.c b/source/blender/windowmanager/xr/intern/wm_xr_session.c
index c9c158b9feb..b740cb27471 100644
--- a/source/blender/windowmanager/xr/intern/wm_xr_session.c
+++ b/source/blender/windowmanager/xr/intern/wm_xr_session.c
@@ -317,6 +317,7 @@ void wm_xr_session_state_update(const XrSessionSettings *settings,
{
GHOST_XrPose viewer_pose;
const bool use_position_tracking = settings->flag & XR_SESSION_USE_POSITION_TRACKING;
+ const bool use_absolute_tracking = settings->flag & XR_SESSION_USE_ABSOLUTE_TRACKING;
mul_qt_qtqt(viewer_pose.orientation_quat,
draw_data->base_pose.orientation_quat,
@@ -324,14 +325,16 @@ void wm_xr_session_state_update(const XrSessionSettings *settings,
copy_v3_v3(viewer_pose.position, draw_data->base_pose.position);
/* The local pose and the eye pose (which is copied from an earlier local pose) both are view
* space, so Y-up. In this case we need them in regular Z-up. */
- viewer_pose.position[0] -= draw_data->eye_position_ofs[0];
- viewer_pose.position[1] += draw_data->eye_position_ofs[2];
- viewer_pose.position[2] -= draw_data->eye_position_ofs[1];
if (use_position_tracking) {
viewer_pose.position[0] += draw_view->local_pose.position[0];
viewer_pose.position[1] -= draw_view->local_pose.position[2];
viewer_pose.position[2] += draw_view->local_pose.position[1];
}
+ if (!use_absolute_tracking) {
+ viewer_pose.position[0] -= draw_data->eye_position_ofs[0];
+ viewer_pose.position[1] += draw_data->eye_position_ofs[2];
+ viewer_pose.position[2] -= draw_data->eye_position_ofs[1];
+ }
copy_v3_v3(state->viewer_pose.position, viewer_pose.position);
copy_qt_qt(state->viewer_pose.orientation_quat, viewer_pose.orientation_quat);
@@ -451,9 +454,14 @@ static void wm_xr_session_controller_mats_update(const XrSessionSettings *settin
float base_inv[4][4];
float tmp[4][4];
- zero_v3(view_ofs);
if ((settings->flag & XR_SESSION_USE_POSITION_TRACKING) == 0) {
- add_v3_v3(view_ofs, state->prev_local_pose.position);
+ copy_v3_v3(view_ofs, state->prev_local_pose.position);
+ }
+ else {
+ zero_v3(view_ofs);
+ }
+ if ((settings->flag & XR_SESSION_USE_ABSOLUTE_TRACKING) == 0) {
+ add_v3_v3(view_ofs, state->prev_eye_position_ofs);
}
wm_xr_pose_to_viewmat(&state->prev_base_pose, base_inv);