2020-06-01 20:32:43 +00:00
|
|
|
// Copyright 2019-2020, Collabora, Ltd.
|
2019-03-18 05:52:32 +00:00
|
|
|
// SPDX-License-Identifier: BSL-1.0
|
|
|
|
/*!
|
|
|
|
* @file
|
|
|
|
* @brief So much space!
|
|
|
|
* @author Jakob Bornecrantz <jakob@collabora.com>
|
|
|
|
* @ingroup oxr_main
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <string.h>
|
|
|
|
|
|
|
|
#include "math/m_api.h"
|
2020-07-23 11:12:29 +00:00
|
|
|
#include "math/m_space.h"
|
2019-03-18 05:52:32 +00:00
|
|
|
#include "util/u_debug.h"
|
2019-03-21 20:19:52 +00:00
|
|
|
#include "util/u_misc.h"
|
2019-03-18 05:52:32 +00:00
|
|
|
|
|
|
|
#include "oxr_objects.h"
|
|
|
|
#include "oxr_logger.h"
|
2019-04-05 19:18:03 +00:00
|
|
|
#include "oxr_handle.h"
|
2019-03-18 05:52:32 +00:00
|
|
|
|
|
|
|
|
|
|
|
const struct xrt_pose origin = {{0.0f, 0.0f, 0.0f, 1.0f}, {0.0f, 0.0f, 0.0f}};
|
|
|
|
|
|
|
|
static XrResult
|
|
|
|
check_reference_space_type(struct oxr_logger *log, XrReferenceSpaceType type)
|
|
|
|
{
|
|
|
|
switch (type) {
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_VIEW: return XR_SUCCESS;
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_LOCAL: return XR_SUCCESS;
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_STAGE: return XR_SUCCESS;
|
|
|
|
#if 0
|
|
|
|
return oxr_error(log, XR_ERROR_REFERENCE_SPACE_UNSUPPORTED,
|
|
|
|
"(createInfo->referenceSpaceType = "
|
|
|
|
"XR_REFERENCE_SPACE_TYPE_STAGE)");
|
|
|
|
#endif
|
|
|
|
default:
|
|
|
|
return oxr_error(log, XR_ERROR_REFERENCE_SPACE_UNSUPPORTED,
|
2021-01-14 14:13:48 +00:00
|
|
|
"(createInfo->referenceSpaceType == 0x%08x)", type);
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2019-04-05 19:18:03 +00:00
|
|
|
static XrResult
|
|
|
|
oxr_space_destroy(struct oxr_logger *log, struct oxr_handle_base *hb)
|
|
|
|
{
|
|
|
|
struct oxr_space *spc = (struct oxr_space *)hb;
|
|
|
|
free(spc);
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2019-04-05 22:28:36 +00:00
|
|
|
XrResult
|
|
|
|
oxr_space_action_create(struct oxr_logger *log,
|
2019-07-13 16:17:57 +00:00
|
|
|
struct oxr_session *sess,
|
|
|
|
uint64_t key,
|
2019-04-05 22:28:36 +00:00
|
|
|
const XrActionSpaceCreateInfo *createInfo,
|
|
|
|
struct oxr_space **out_space)
|
|
|
|
{
|
2019-05-07 12:47:18 +00:00
|
|
|
struct oxr_instance *inst = sess->sys->inst;
|
2020-10-23 12:39:59 +00:00
|
|
|
struct oxr_subaction_paths subaction_paths = {0};
|
2019-05-07 12:47:18 +00:00
|
|
|
|
2019-04-05 22:28:36 +00:00
|
|
|
struct oxr_space *spc = NULL;
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_ALLOCATE_HANDLE_OR_RETURN(log, spc, OXR_XR_DEBUG_SPACE, oxr_space_destroy, &sess->handle);
|
2019-04-05 22:28:36 +00:00
|
|
|
|
2020-10-23 12:39:59 +00:00
|
|
|
oxr_classify_sub_action_paths(log, inst, 1, &createInfo->subactionPath, &subaction_paths);
|
2019-05-07 12:47:18 +00:00
|
|
|
|
2019-07-13 16:17:57 +00:00
|
|
|
spc->sess = sess;
|
2019-04-05 22:28:36 +00:00
|
|
|
spc->is_reference = false;
|
2020-10-23 12:39:59 +00:00
|
|
|
spc->subaction_paths = subaction_paths;
|
2019-07-13 16:17:57 +00:00
|
|
|
spc->act_key = key;
|
2019-04-05 22:28:36 +00:00
|
|
|
memcpy(&spc->pose, &createInfo->poseInActionSpace, sizeof(spc->pose));
|
|
|
|
|
|
|
|
*out_space = spc;
|
|
|
|
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2019-03-18 05:52:32 +00:00
|
|
|
XrResult
|
|
|
|
oxr_space_reference_create(struct oxr_logger *log,
|
|
|
|
struct oxr_session *sess,
|
|
|
|
const XrReferenceSpaceCreateInfo *createInfo,
|
|
|
|
struct oxr_space **out_space)
|
|
|
|
{
|
|
|
|
XrResult ret;
|
|
|
|
|
|
|
|
ret = check_reference_space_type(log, createInfo->referenceSpaceType);
|
|
|
|
if (ret != XR_SUCCESS) {
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2021-01-14 14:13:48 +00:00
|
|
|
if (!math_pose_validate((struct xrt_pose *)&createInfo->poseInReferenceSpace)) {
|
|
|
|
return oxr_error(log, XR_ERROR_POSE_INVALID, "(createInfo->poseInReferenceSpace)");
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
|
2019-04-05 19:18:03 +00:00
|
|
|
struct oxr_space *spc = NULL;
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_ALLOCATE_HANDLE_OR_RETURN(log, spc, OXR_XR_DEBUG_SPACE, oxr_space_destroy, &sess->handle);
|
2019-03-18 05:52:32 +00:00
|
|
|
spc->sess = sess;
|
|
|
|
spc->is_reference = true;
|
|
|
|
spc->type = createInfo->referenceSpaceType;
|
2021-01-14 14:13:48 +00:00
|
|
|
memcpy(&spc->pose, &createInfo->poseInReferenceSpace, sizeof(spc->pose));
|
2019-03-18 05:52:32 +00:00
|
|
|
|
|
|
|
*out_space = spc;
|
|
|
|
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
static const char *
|
|
|
|
get_ref_space_type_short_str(struct oxr_space *spc)
|
|
|
|
{
|
|
|
|
if (!spc->is_reference) {
|
2019-05-07 12:47:18 +00:00
|
|
|
return "action";
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
switch (spc->type) {
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_VIEW: return "view";
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_LOCAL: return "local";
|
|
|
|
case XR_REFERENCE_SPACE_TYPE_STAGE: return "stage";
|
|
|
|
default: return "unknown";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2020-07-19 21:44:24 +00:00
|
|
|
static bool
|
2021-01-14 14:13:48 +00:00
|
|
|
ensure_initial_head_relation(struct oxr_logger *log, struct oxr_session *sess, struct xrt_space_relation *head_relation)
|
2020-07-19 21:44:24 +00:00
|
|
|
{
|
2021-01-14 14:13:48 +00:00
|
|
|
if ((head_relation->relation_flags & XRT_SPACE_RELATION_ORIENTATION_TRACKED_BIT) == 0) {
|
2020-07-19 21:44:24 +00:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!initial_head_relation_valid(sess)) {
|
|
|
|
sess->initial_head_relation = *head_relation;
|
|
|
|
|
|
|
|
// take only head rotation around y axis
|
|
|
|
// https://stackoverflow.com/a/5783030
|
|
|
|
sess->initial_head_relation.pose.orientation.x = 0;
|
|
|
|
sess->initial_head_relation.pose.orientation.z = 0;
|
2021-01-14 14:13:48 +00:00
|
|
|
math_quat_normalize(&sess->initial_head_relation.pose.orientation);
|
2020-07-19 21:44:24 +00:00
|
|
|
|
2020-09-07 23:23:23 +00:00
|
|
|
//! @todo: Handle relation velocities if necessary
|
2020-07-19 21:44:24 +00:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
|
|
|
initial_head_relation_valid(struct oxr_session *sess)
|
|
|
|
{
|
2021-01-14 14:13:48 +00:00
|
|
|
return sess->initial_head_relation.relation_flags & XRT_SPACE_RELATION_ORIENTATION_VALID_BIT;
|
2020-07-19 21:44:24 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
2020-09-11 17:05:25 +00:00
|
|
|
global_to_local_space(struct oxr_session *sess, struct xrt_space_relation *rel)
|
2020-07-19 21:44:24 +00:00
|
|
|
{
|
|
|
|
if (!initial_head_relation_valid(sess)) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2020-09-11 17:05:25 +00:00
|
|
|
struct xrt_space_graph graph = {0};
|
|
|
|
m_space_graph_add_relation(&graph, rel);
|
2021-01-14 14:13:48 +00:00
|
|
|
m_space_graph_add_inverted_pose_if_not_identity(&graph, &sess->initial_head_relation.pose);
|
2020-09-11 17:05:25 +00:00
|
|
|
m_space_graph_resolve(&graph, rel);
|
|
|
|
|
2020-07-19 21:44:24 +00:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2019-03-18 05:52:32 +00:00
|
|
|
/*!
|
|
|
|
* This returns only the relation between two spaces without any of the app
|
|
|
|
* given relations applied, assumes that both spaces are reference spaces.
|
|
|
|
*/
|
|
|
|
XrResult
|
|
|
|
oxr_space_ref_relation(struct oxr_logger *log,
|
|
|
|
struct oxr_session *sess,
|
|
|
|
XrReferenceSpaceType space,
|
|
|
|
XrReferenceSpaceType baseSpc,
|
|
|
|
XrTime time,
|
|
|
|
struct xrt_space_relation *out_relation)
|
|
|
|
{
|
2020-07-23 11:12:29 +00:00
|
|
|
m_space_relation_ident(out_relation);
|
2019-03-18 05:52:32 +00:00
|
|
|
|
2020-07-20 12:04:09 +00:00
|
|
|
|
2020-07-20 13:41:17 +00:00
|
|
|
if (space == baseSpc) {
|
2020-07-23 11:12:29 +00:00
|
|
|
// m_space_relation_ident() sets to identity.
|
2020-07-20 13:41:17 +00:00
|
|
|
} else if (space == XR_REFERENCE_SPACE_TYPE_VIEW) {
|
2020-07-23 11:12:29 +00:00
|
|
|
oxr_session_get_view_relation_at(log, sess, time, out_relation);
|
2019-03-18 05:52:32 +00:00
|
|
|
|
2020-09-07 23:23:23 +00:00
|
|
|
if (!ensure_initial_head_relation(log, sess, out_relation)) {
|
2021-01-14 14:13:48 +00:00
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-19 21:44:24 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (baseSpc == XR_REFERENCE_SPACE_TYPE_STAGE) {
|
|
|
|
// device poses are already in stage = "global" space
|
|
|
|
} else if (baseSpc == XR_REFERENCE_SPACE_TYPE_LOCAL) {
|
2020-09-11 17:05:25 +00:00
|
|
|
global_to_local_space(sess, out_relation);
|
2020-07-19 21:44:24 +00:00
|
|
|
} else if (baseSpc == XR_REFERENCE_SPACE_TYPE_VIEW) {
|
|
|
|
|
|
|
|
} else {
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_WARN_ONCE(log, "unsupported base space in space_ref_relation");
|
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-19 21:44:24 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
} else if (baseSpc == XR_REFERENCE_SPACE_TYPE_VIEW) {
|
2020-07-23 11:12:29 +00:00
|
|
|
oxr_session_get_view_relation_at(log, sess, time, out_relation);
|
2020-07-19 21:44:24 +00:00
|
|
|
|
2020-09-07 23:23:23 +00:00
|
|
|
if (!ensure_initial_head_relation(log, sess, out_relation)) {
|
2021-01-14 14:13:48 +00:00
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-19 21:44:24 +00:00
|
|
|
return XR_SUCCESS;
|
2020-08-06 14:29:37 +00:00
|
|
|
}
|
|
|
|
if (space == XR_REFERENCE_SPACE_TYPE_STAGE) {
|
2020-07-19 21:44:24 +00:00
|
|
|
// device poses are already in stage = "global" space
|
|
|
|
} else if (space == XR_REFERENCE_SPACE_TYPE_LOCAL) {
|
2020-09-11 17:05:25 +00:00
|
|
|
global_to_local_space(sess, out_relation);
|
2020-07-19 21:44:24 +00:00
|
|
|
} else if (space == XR_REFERENCE_SPACE_TYPE_VIEW) {
|
|
|
|
|
|
|
|
} else {
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_WARN_ONCE(log, "unsupported base space in space_ref_relation");
|
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-19 21:44:24 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
2019-03-18 05:52:32 +00:00
|
|
|
math_pose_invert(&out_relation->pose, &out_relation->pose);
|
|
|
|
|
2020-07-20 12:04:09 +00:00
|
|
|
} else if (space == XR_REFERENCE_SPACE_TYPE_STAGE) {
|
|
|
|
if (baseSpc == XR_REFERENCE_SPACE_TYPE_LOCAL) {
|
2021-01-14 14:13:48 +00:00
|
|
|
math_pose_invert(&sess->initial_head_relation.pose, &out_relation->pose);
|
2020-07-20 12:04:09 +00:00
|
|
|
} else {
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_WARN_ONCE(log, "unsupported base space in space_ref_relation");
|
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-20 12:04:09 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
} else if (space == XR_REFERENCE_SPACE_TYPE_LOCAL) {
|
|
|
|
if (baseSpc == XR_REFERENCE_SPACE_TYPE_STAGE) {
|
|
|
|
out_relation->pose = sess->initial_head_relation.pose;
|
|
|
|
} else {
|
2021-01-14 14:13:48 +00:00
|
|
|
OXR_WARN_ONCE(log, "unsupported base space in space_ref_relation");
|
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2020-07-20 12:04:09 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
2019-03-18 05:52:32 +00:00
|
|
|
} else {
|
2019-03-21 20:53:50 +00:00
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2019-03-18 05:52:32 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2020-07-23 11:12:29 +00:00
|
|
|
static void
|
|
|
|
remove_angular_and_linear_stuff(struct xrt_space_relation *out_relation)
|
|
|
|
{
|
|
|
|
const enum xrt_space_relation_flags flags =
|
2021-01-14 14:13:48 +00:00
|
|
|
XRT_SPACE_RELATION_LINEAR_VELOCITY_VALID_BIT | XRT_SPACE_RELATION_ANGULAR_VELOCITY_VALID_BIT;
|
2020-07-23 11:12:29 +00:00
|
|
|
|
|
|
|
out_relation->relation_flags &= ~flags;
|
|
|
|
out_relation->linear_velocity = (struct xrt_vec3){0, 0, 0};
|
|
|
|
out_relation->angular_velocity = (struct xrt_vec3){0, 0, 0};
|
|
|
|
}
|
|
|
|
|
2019-05-07 12:47:18 +00:00
|
|
|
/*!
|
|
|
|
* This returns only the relation between two spaces without any of the app
|
|
|
|
* given relations applied, assumes that only one is a action space.
|
|
|
|
*/
|
2020-07-23 11:12:29 +00:00
|
|
|
static XrResult
|
2019-05-07 12:47:18 +00:00
|
|
|
oxr_space_action_relation(struct oxr_logger *log,
|
|
|
|
struct oxr_session *sess,
|
|
|
|
struct oxr_space *spc,
|
|
|
|
struct oxr_space *baseSpc,
|
2020-04-16 12:23:12 +00:00
|
|
|
XrTime at_time,
|
2019-05-07 12:47:18 +00:00
|
|
|
struct xrt_space_relation *out_relation)
|
|
|
|
{
|
2020-06-15 19:16:38 +00:00
|
|
|
struct oxr_action_input *input = NULL;
|
2019-05-07 12:47:18 +00:00
|
|
|
struct oxr_space *act_spc, *ref_spc = NULL;
|
|
|
|
bool invert = false;
|
|
|
|
|
|
|
|
// Find the action space
|
|
|
|
if (baseSpc->is_reference) {
|
|
|
|
// Note spc, is assumed to be the action space.
|
|
|
|
act_spc = spc;
|
|
|
|
ref_spc = baseSpc;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Find the action space.
|
|
|
|
if (spc->is_reference) {
|
|
|
|
// Note baseSpc, is assumed to be the action space.
|
|
|
|
act_spc = baseSpc;
|
|
|
|
ref_spc = spc;
|
|
|
|
invert = true;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Internal error check.
|
2021-01-14 14:13:48 +00:00
|
|
|
if (act_spc == NULL || act_spc->is_reference || ref_spc == NULL || !ref_spc->is_reference) {
|
2020-05-31 15:49:25 +00:00
|
|
|
return oxr_error(log, XR_ERROR_RUNTIME_FAILURE, "This is bad!");
|
2019-05-07 12:47:18 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Reset so no relation is returned.
|
2020-07-23 11:12:29 +00:00
|
|
|
m_space_relation_ident(out_relation);
|
2019-05-07 12:47:18 +00:00
|
|
|
|
|
|
|
//! @todo Can not relate to the view space right now.
|
|
|
|
if (baseSpc->type == XR_REFERENCE_SPACE_TYPE_VIEW) {
|
|
|
|
//! @todo Error code?
|
2020-07-19 21:44:24 +00:00
|
|
|
OXR_WARN_ONCE(log, "relating to view space unsupported");
|
2019-05-07 12:47:18 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2020-10-23 12:39:59 +00:00
|
|
|
oxr_action_get_pose_input(log, sess, act_spc->act_key, &act_spc->subaction_paths, &input);
|
2019-05-07 12:47:18 +00:00
|
|
|
|
|
|
|
// If the input isn't active.
|
|
|
|
if (input == NULL) {
|
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2021-01-14 14:13:48 +00:00
|
|
|
oxr_xdev_get_space_relation(log, sess->sys->inst, input->xdev, input->input->name, at_time, out_relation);
|
2019-05-07 12:47:18 +00:00
|
|
|
|
2020-07-19 21:44:24 +00:00
|
|
|
if (baseSpc->type == XR_REFERENCE_SPACE_TYPE_LOCAL) {
|
2020-09-11 17:05:25 +00:00
|
|
|
global_to_local_space(sess, out_relation);
|
2020-07-19 21:44:24 +00:00
|
|
|
}
|
|
|
|
|
2019-05-07 12:47:18 +00:00
|
|
|
if (invert) {
|
|
|
|
math_pose_invert(&out_relation->pose, &out_relation->pose);
|
2020-07-23 11:12:29 +00:00
|
|
|
// Remove this since we can't (for now) invert the derivatives.
|
|
|
|
remove_angular_and_linear_stuff(out_relation);
|
2019-05-07 12:47:18 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
|
|
|
|
2019-03-18 05:52:32 +00:00
|
|
|
/*!
|
|
|
|
* This returns only the relation between two directly-associated spaces without
|
|
|
|
* any of the app given relations applied.
|
|
|
|
*/
|
|
|
|
static XrResult
|
|
|
|
get_pure_space_relation(struct oxr_logger *log,
|
|
|
|
struct oxr_space *spc,
|
|
|
|
struct oxr_space *baseSpc,
|
|
|
|
XrTime time,
|
|
|
|
struct xrt_space_relation *out_relation)
|
|
|
|
{
|
|
|
|
struct oxr_session *sess = spc->sess;
|
|
|
|
|
|
|
|
if (spc->is_reference && baseSpc->is_reference) {
|
2021-01-14 14:13:48 +00:00
|
|
|
return oxr_space_ref_relation(log, sess, spc->type, baseSpc->type, time, out_relation);
|
2019-08-16 22:02:18 +00:00
|
|
|
}
|
|
|
|
if (!spc->is_reference && !baseSpc->is_reference) {
|
2019-03-18 05:52:32 +00:00
|
|
|
// @todo Deal with action to action by keeping a true_space that
|
|
|
|
// we can always go via. Aka poor mans space graph.
|
|
|
|
// WARNING order not thought through here!
|
|
|
|
// struct xrt_pose pose1;
|
|
|
|
// struct xrt_pose pose2;
|
|
|
|
// get_pure_space_relation(log, session->true_space, baseSpc,
|
|
|
|
// time, &pose1);
|
|
|
|
// get_pure_space_relation(log, space, session->true_space,
|
|
|
|
// time, &pose2);
|
|
|
|
// math_pose_relate_2(&pose1, &pose2, out_pose);
|
2019-03-21 20:53:50 +00:00
|
|
|
out_relation->relation_flags = XRT_SPACE_RELATION_BITMASK_NONE;
|
2019-03-18 05:52:32 +00:00
|
|
|
return XR_SUCCESS;
|
|
|
|
}
|
2019-08-16 22:02:18 +00:00
|
|
|
|
|
|
|
oxr_space_action_relation(log, sess, spc, baseSpc, time, out_relation);
|
|
|
|
return XR_SUCCESS;
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2019-10-22 10:47:25 +00:00
|
|
|
print_pose(struct oxr_session *sess, const char *prefix, struct xrt_pose *pose)
|
2019-03-18 05:52:32 +00:00
|
|
|
{
|
2019-10-22 10:47:25 +00:00
|
|
|
if (!sess->sys->inst->debug_spaces) {
|
2019-03-18 05:52:32 +00:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
struct xrt_vec3 *p = &pose->position;
|
|
|
|
struct xrt_quat *q = &pose->orientation;
|
|
|
|
|
2021-01-14 14:13:48 +00:00
|
|
|
U_LOG_D("%s (%f, %f, %f) (%f, %f, %f, %f)", prefix, p->x, p->y, p->z, q->x, q->y, q->z, q->w);
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
print_space(const char *name, struct oxr_space *spc)
|
|
|
|
{
|
2019-10-22 10:47:25 +00:00
|
|
|
if (!spc->sess->sys->inst->debug_spaces) {
|
2019-03-18 05:52:32 +00:00
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
const char *type_str = get_ref_space_type_short_str(spc);
|
2020-12-16 17:20:51 +00:00
|
|
|
U_LOG_D("\t%s->type %s\n\t%s->pose", name, type_str, name);
|
2019-10-22 10:47:25 +00:00
|
|
|
print_pose(spc->sess, "", &spc->pose);
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
|
2020-10-12 00:09:19 +00:00
|
|
|
XrSpaceLocationFlags
|
|
|
|
xrt_to_xr_space_location_flags(enum xrt_space_relation_flags relation_flags)
|
2020-05-28 23:42:54 +00:00
|
|
|
{
|
|
|
|
// clang-format off
|
|
|
|
bool valid_ori = (relation_flags & XRT_SPACE_RELATION_ORIENTATION_VALID_BIT) != 0;
|
|
|
|
bool tracked_ori = (relation_flags & XRT_SPACE_RELATION_ORIENTATION_TRACKED_BIT) != 0;
|
|
|
|
bool valid_pos = (relation_flags & XRT_SPACE_RELATION_POSITION_VALID_BIT) != 0;
|
|
|
|
bool tracked_pos = (relation_flags & XRT_SPACE_RELATION_POSITION_TRACKED_BIT) != 0;
|
2020-06-22 18:41:27 +00:00
|
|
|
|
|
|
|
bool linear_vel = (relation_flags & XRT_SPACE_RELATION_LINEAR_VELOCITY_VALID_BIT) != 0;
|
|
|
|
bool angular_vel = (relation_flags & XRT_SPACE_RELATION_ANGULAR_VELOCITY_VALID_BIT) != 0;
|
2020-05-28 23:42:54 +00:00
|
|
|
// clang-format on
|
|
|
|
|
|
|
|
XrSpaceLocationFlags location_flags = (XrSpaceLocationFlags)0;
|
|
|
|
if (valid_ori) {
|
|
|
|
location_flags |= XR_SPACE_LOCATION_ORIENTATION_VALID_BIT;
|
|
|
|
}
|
|
|
|
if (tracked_ori) {
|
|
|
|
location_flags |= XR_SPACE_LOCATION_ORIENTATION_TRACKED_BIT;
|
|
|
|
}
|
|
|
|
if (valid_pos) {
|
|
|
|
location_flags |= XR_SPACE_LOCATION_POSITION_VALID_BIT;
|
|
|
|
}
|
|
|
|
if (tracked_pos) {
|
|
|
|
location_flags |= XR_SPACE_LOCATION_POSITION_TRACKED_BIT;
|
|
|
|
}
|
2020-06-22 18:41:27 +00:00
|
|
|
if (linear_vel) {
|
|
|
|
location_flags |= XR_SPACE_VELOCITY_LINEAR_VALID_BIT;
|
|
|
|
}
|
|
|
|
if (angular_vel) {
|
|
|
|
location_flags |= XR_SPACE_VELOCITY_ANGULAR_VALID_BIT;
|
|
|
|
}
|
2020-05-28 23:42:54 +00:00
|
|
|
return location_flags;
|
|
|
|
}
|
|
|
|
|
2019-03-18 05:52:32 +00:00
|
|
|
XrResult
|
2021-01-14 14:13:48 +00:00
|
|
|
oxr_space_locate(
|
|
|
|
struct oxr_logger *log, struct oxr_space *spc, struct oxr_space *baseSpc, XrTime time, XrSpaceLocation *location)
|
2019-03-18 05:52:32 +00:00
|
|
|
{
|
2019-10-22 10:47:25 +00:00
|
|
|
if (spc->sess->sys->inst->debug_spaces) {
|
2020-12-16 17:20:51 +00:00
|
|
|
U_LOG_D("%s", __func__);
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|
|
|
|
print_space("space", spc);
|
|
|
|
print_space("baseSpace", baseSpc);
|
|
|
|
|
|
|
|
// Get the pure space relation.
|
|
|
|
//! @todo for longer paths in "space graph" than one edge, this will be
|
|
|
|
//! a loop.
|
|
|
|
struct xrt_space_relation pure;
|
|
|
|
XrResult ret = get_pure_space_relation(log, spc, baseSpc, time, &pure);
|
|
|
|
if (ret != XR_SUCCESS) {
|
2019-07-13 16:17:57 +00:00
|
|
|
location->locationFlags = 0;
|
2019-03-18 05:52:32 +00:00
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Combine space and base space poses with pure relation
|
|
|
|
struct xrt_space_relation result;
|
2020-07-23 11:12:29 +00:00
|
|
|
struct xrt_space_graph graph = {0};
|
|
|
|
m_space_graph_add_pose_if_not_identity(&graph, &spc->pose);
|
|
|
|
m_space_graph_add_relation(&graph, &pure);
|
|
|
|
m_space_graph_add_inverted_pose_if_not_identity(&graph, &baseSpc->pose);
|
|
|
|
m_space_graph_resolve(&graph, &result);
|
2019-03-18 05:52:32 +00:00
|
|
|
|
|
|
|
// Copy
|
2019-09-06 14:35:41 +00:00
|
|
|
union {
|
|
|
|
struct xrt_pose xrt;
|
|
|
|
XrPosef oxr;
|
|
|
|
} safe_copy = {0};
|
|
|
|
safe_copy.xrt = result.pose;
|
|
|
|
|
|
|
|
location->pose = safe_copy.oxr;
|
2021-01-14 14:13:48 +00:00
|
|
|
location->locationFlags = xrt_to_xr_space_location_flags(result.relation_flags);
|
2019-09-06 14:35:41 +00:00
|
|
|
|
2020-06-22 18:41:27 +00:00
|
|
|
XrSpaceVelocity *vel = (XrSpaceVelocity *)location->next;
|
|
|
|
if (vel) {
|
|
|
|
vel->linearVelocity.x = result.linear_velocity.x;
|
|
|
|
vel->linearVelocity.y = result.linear_velocity.y;
|
|
|
|
vel->linearVelocity.z = result.linear_velocity.z;
|
|
|
|
|
|
|
|
vel->angularVelocity.x = result.angular_velocity.x;
|
|
|
|
vel->angularVelocity.y = result.angular_velocity.y;
|
|
|
|
vel->angularVelocity.z = result.angular_velocity.z;
|
|
|
|
|
2021-01-14 14:13:48 +00:00
|
|
|
vel->velocityFlags |= (location->locationFlags & XR_SPACE_VELOCITY_LINEAR_VALID_BIT);
|
|
|
|
vel->velocityFlags |= (location->locationFlags & XR_SPACE_VELOCITY_ANGULAR_VALID_BIT);
|
2020-06-22 18:41:27 +00:00
|
|
|
}
|
|
|
|
|
2019-07-13 16:17:57 +00:00
|
|
|
#if 0
|
|
|
|
location->linearVelocity = *(XrVector3f *)&result.linear_velocity;
|
|
|
|
location->angularVelocity = *(XrVector3f *)&result.angular_velocity;
|
|
|
|
location->linearAcceleration =
|
2019-03-18 05:52:32 +00:00
|
|
|
*(XrVector3f *)&result.linear_acceleration;
|
2019-07-13 16:17:57 +00:00
|
|
|
location->angularAcceleration =
|
2019-03-18 05:52:32 +00:00
|
|
|
*(XrVector3f *)&result.angular_acceleration;
|
2019-07-13 16:17:57 +00:00
|
|
|
#endif
|
2019-03-18 05:52:32 +00:00
|
|
|
|
2021-01-14 14:13:48 +00:00
|
|
|
print_pose(spc->sess, "\trelation->pose", (struct xrt_pose *)&location->pose);
|
2019-03-18 05:52:32 +00:00
|
|
|
|
2019-09-26 20:25:05 +00:00
|
|
|
return oxr_session_success_result(spc->sess);
|
2019-03-18 05:52:32 +00:00
|
|
|
}
|