As your device moves through 3D space, it calculates where it is (position) and how it‘s rotated (orientation) up to 100 times per second. A single instance of this combined calculation is called the device‘s pose. The pose is an essential concept when working with motion tracking, area learning, or depth perception.
当你的设备通过3D空间时,它计算它在哪里(位置)以及它是如何旋转的(方向)。这达到每秒100次。一个单个的这种复合计算的实例称为设备的姿态。
To calculate the poses, you must choose base and target frames of reference , which may use different coordinate systems. You can view a pose as the translation and rotation required to transform vertices from the target frame to the base frame.
Here is a simplified version of a Tango pose struct in C:
struct PoseData {
double orientation[4];
double translation[3];
}
The two key components of a pose are:
-
A quaternion that defines the rotation of the target frame with respect to the base frame.
-
A 3D vector that defines the translation of the target frame with respect to the base frame.
An actual pose struct contains other fields, such as a timestamp and a copy of the frame pair, as you‘ll see below.
Note: The examples on this page use the C API, but function calls and data structures are similar for Java. In Unity, there are prefabs which handle a lot of these details for you.Pose data
You can request pose data in two ways:
Request Method #1
Poll for poses using TangoService_getPoseAtTime()
. This returns the pose closest to a given timestamp from the base to the target frame. Here is the code for this function in the C API:
TangoErrorType TangoService_getPoseAtTime(
double timestamp,
TangoCoordinateFramePair frame_pair,
TangoPoseData* pose);
The TangoCoordinateFramePair
struct specifies the base frame and the target frame.
The following code gets a pose of the device frame with respect to the start-of- service frame:
TangoPoseData pose_start_service_T_device;
TangoCoordinateFramePair frame_pair;
frame_pair.base = TANGO_COORDINATE_FRAME_START_OF_SERVICE;
frame_pair.target = TANGO_COORDINATE_FRAME_DEVICE;
TangoService_getPoseAtTime(
timestamp,
frame_pair,
&pose_start_service_T_device);
In this example, including the names of the base and target frames in the pose variable name makes the name more descriptive:
TangoPoseData pose_start_service_T_device;
Request Method #2
Receive pose updates as they become available. To do so, attach an onPoseAvailable()
callback toTangoService_connectOnPoseAvailable()
. This sample is from our hello_motion_tracking example project and can be found in the tango_handler.cc file:
TangoCoordinateFramePair pair;
pair.base = TANGO_COORDINATE_FRAME_START_OF_SERVICE;
pair.target = TANGO_COORDINATE_FRAME_DEVICE;
if (TangoService_connectOnPoseAvailable(1, &pair, onPoseAvailable) !=
TANGO_SUCCESS) {
LOGE("TangoHandler::ConnectTango, connectOnPoseAvailable error.");
std::exit(EXIT_SUCCESS);
In both cases, you receive a TangoPoseData
struct:
typedef struct TangoPoseData {
int version;
double timestamp; // In seconds
double orientation[4]; // As a quaternion
double translation[3]; // In meters
TangoPoseStatusType status_code;
TangoCoordinateFramePair frame;
int confidence; // Currently unused
float accuracy; // Currently unused
} TangoPoseData;
Pose status
TangoPoseData
contains a state, denoted by the TangoPoseStatusType
enum, which provides information about the status of the pose estimation system. The available TangoPoseStatusType
members are:
typedef enum {
TANGO_POSE_INITIALIZING = 0,
TANGO_POSE_VALID,
TANGO_POSE_INVALID,
TANGO_POSE_UNKNOWN
} TangoPoseStatusType;
INITIALIZING
: The motion tracking system is either starting or recovering from an invalid state, and the pose data should not be used.
VALID
: The system believes the poses being returned are valid and should be used.
INVALID
: The system has encountered difficulty of some kind, so pose estimations are likely incorrect.
UNKNOWN
: The system is in an unknown state.
Lifecycle of pose status
Figure 1: Tango Pose data lifecycleThe TANGO_POSE_INITIALIZING
status code indicates that the Tango framework is initializing and pose data is not yet available. If you are using callbacks, you will receive only one pose update with the status code set toTANGO_POSE_INITIALIZING
while the framework is initializing.
After initialization finishes, poses are in the TANGO_POSE_VALID
state. If you are using callbacks, you will receive updates as frequently as they are available.
If the system encounters difficulty and enters the TANGO_POSE_INVALID
state, recovery depends on your configuration during initialization. If config_enable_auto_recovery
is set to True
, the system immediately resets the motion tracking system and enters the TANGO_POSE_INITIALIZING
state. Ifconfig_enable_auto_recovery
is set to False
, pose data remains in the TANGO_POSE_INVALID
state and no updates are received until you call TangoService_resetMotionTracking()
.
Using pose status
Your application should react to the status being returned within the pose data. For example, wait until the pose data you are interested in becomes valid before starting interactions in your application. If the pose becomes invalid, pause interactions until after the system recovers. Depending on your application, what you do after the system recovers will vary. If you are using motion tracking alone, you can simply resume your application. If you are using area learning or ADFs, instruct your user to move around until the device can localize itself.