SDKC++ SDK

API reference

Object and method summary, plus the data and result models.

Current version · 1.4.0

API reference

An explicit close() is the primary cleanup method; destruction only provides a non-throwing last resort.

Glove::close() reclaims subscriptions that are still valid. The application only needs to keep the corresponding Subscription objects alive; there is no need to unsubscribe them one by one before the final close. Call subscription.unsubscribe() explicitly only when the owning object keeps running but a single callback needs to be stopped early.

Do not synchronously call unsubscribe() on, or destroy, that subscription from inside its own callback.

Finite tasks call Glove::close() when the normal path ends; background mode calls request_stop() and join() first. Glove::close() stops and closes all configured gloves, and Sdk::close() closes the remaining capabilities and releases the entire SDK. After a successful close, repeated calls are a no-op.

The destructors of Subscription, Glove, and Sdk still provide an RAII fallback, but they cannot replace an explicit close(), because destruction cannot reliably report cleanup failures. Also do not destroy the last Sdk object inside a callback; leave cleanup to the application control path outside the callback.

For the full field definitions, see Configuration reference.

Object and method summary

For methods without parameters, the "Parameters, type, and default" column says "None".

Top-level functions

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
qnbot::discover_gloves()View the currently discoverable glovesNonestd::vector<DiscoveredGlove>Before creating the SDKTop-level discovery errors; per-port errors are in the result

Sdk

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
Sdk::glove()Enter the glove capabilityNoneGloveSDK not closedClosedHandleError, capability unavailable
Sdk::start()Start configured capabilities and device data streamsNonevoidAfter preparing to read dataConnection, identity, data stream, or lifecycle errors
Sdk::update()Perform one SDK task scheduling passNoneUpdateResultStarted and no other run mode in useLifecycleError
Sdk::run_forever()Keep advancing SDK scheduling on the current threadNonevoidStarted and no other run mode in useLifecycleError
Sdk::run_background()Advance SDK scheduling in the backgroundNonevoidStarted and no other run mode in useLifecycleError, background runtime errors
Sdk::request_stop() / join()Request stop and wait for the background run to finishNonevoidDuring a foreground or background runLifecycleError, background errors
Sdk::stop()Stop running and disconnect devicesNonevoidSDK startedErrors during stopping
Sdk::close()Finally close the SDKNonevoidWhen the SDK is no longer usedErrors during closing; the object is invalid after closing
Sdk::health()View the health status of the entire SDKNoneHealthSDK not closedClosedHandleError

Glove

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
Glove::device() / device(name) / device(side)Select a configured gloveNone, const std::string&, or SideGloveDeviceAfter SDK creationNotFoundSelectionError, AmbiguousSelectionError
Glove::sync_time(reference_time_ms)Set one external absolute time reference for every Glove sourcedouble reference_time_ms, a finite Unix-millisecond valuevoidPrefer before start(); may be called again while running to resynchronizeInvalidArgumentError, ClosedHandleError, or native synchronization errors
start() / stop() / close()Start, stop, or finally close all glovesNonevoidThe corresponding lifecycle stageConnection, lifecycle, or close errors
update() / run_forever() / run_background()Advance SDK schedulingNoneUpdateResult / voidStarted; choose one of the three methodsLifecycleError, background runtime errors
request_stop() / join()Request stop and wait for the background run to finishNonevoidDuring a foreground or background runLifecycleError, background errors
health()View the health status of all glovesNoneHealthGlove not closedClosedHandleError

GloveDevice

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
source_id()Read the runtime source identifierNonestd::stringSDK not closedClosedHandleError
get_device_info()Read the verified device information snapshotNoneGloveDeviceInfoAfter SDK creation, may be before startUnavailableFeatureError (identity not verified)
start() / stop()Start or stop only the current gloveNonevoidWhen the device needs separate controlConnection, identity, data stream, or lifecycle errors
pose() / imu() / status()Read the raw pose, experimental IMU, or device statusNoneThe corresponding ReadChannel<T>After SDK creationLifecycle, close, or unsupported errors
skeleton()Enable and access Skeleton dataNoneSkeletonMust be called before startLifecycleError, capability unavailable
Skeleton::joint_angles() / pose()Read Skeleton joint angles or skeleton nodesNoneThe corresponding ReadChannel<T>After Skeleton is enabledOwning object closed or capability unavailable
output() / output(name)Read the dexterous hand output of the specified targetNone or const std::string&ReadChannel<HandJointCommand>After SDK creationTarget not found or ambiguous
haptics()Obtain the fingertip haptics control entry pointNoneStateChannel<Haptics>After a serial device is selectedUnsupported or rejected for external, wireless, or disconnected
push_frame(frame)Submit one frame of data to an external sourceconst ExternalGloveFrame&, requiredGlovePoseExternal device already startedParameter, timestamp, or lifecycle errors
capture_status(package_ids, operator_id)Check whether manual capture on this device can startpackage_ids: const std::vector<std::string>&; operator_id: const std::string&, both requiredCaptureReadinessBefore creating a Capture SessionInvalidArgumentError, WorkflowError
start_capture(package_ids, operator_id, force)Start manual capture on this devicepackage_ids and operator_id required; force: bool defaults to false, and true re-completes the capture motions in the current planCaptureSessionWhen ready to start capturingInvalidArgumentError, WorkflowError
start_calibration(session, targets)Start calibration using a completed capture on this devicesession: const CaptureSession&, must be completed; targets: non-empty target sequence, both requiredCalibrationSessionCapture completed and the Session is still openSession or target validation errors
calibration_status(...)View the calibration status of the specified targetNone, name, or TargetNameCalibrationReadinessAfter SDK creationTarget not found or ambiguous
capture_progress() / capture_control()Read progress or control CaptureNoneReadChannel<CaptureProgress> / CaptureControlExternal interaction flowLifecycle or control request errors
calibration_progress(...)Read the calibration progress of the specified targetNone, name, or TargetNameReadChannel<CalibrationProgress>During calibration observationTarget not found or ambiguous

Sdk, Glove, and GloveDevice still provide connect() and disconnect(). connect() is kept only for compatibility with old code and does not open devices; disconnect() is equivalent to stop(). New code should use start() and stop() directly.

Lifecycle and scope

ObjectMethodScope and behavior
Sdkstart()Connects and starts all enabled devices and capabilities that are not yet closed, in configuration order; states that are already satisfied can be called again
Sdkupdate()Performs one manual update of the entire SDK and returns a one-shot wait result
Sdkrun_forever() / run_background()Runs the entire SDK in foreground or background mode; both modes are mutually exclusive with manual update
Sdkrequest_stop() / join()Requests the current run loop to stop; join() waits for the background run to finish and reports background errors
Sdkstop()Stops all started capabilities and data streams, then disconnects all connected devices; start() can be called again afterwards
Sdkhealth()Returns the aggregated health status of all devices and capabilities that are not closed
Sdkclose()Requests stop, waits for the run to finish, cleans up subscriptions, and releases all SDK resources; after complete cleanup, repeated calls are a no-op
Glovestart() / stop()Acts only on all enabled gloves that are not yet closed
Gloveupdate() / run_forever() / run_background()Handles glove data only; the run mode rules are the same as for Sdk
Gloverequest_stop() / join() / health()Stops or observes the glove run state without affecting other SDK capabilities
Gloveclose()Stops and closes all configured gloves; the Sdk itself can still be used for other capabilities that are not closed
GloveDevicestart() / stop()Acts only on the selected physical glove; does not change the state of other devices
GloveDevicepush_frame()Only allows an external connection to submit one input frame while connected and started

Data reading and subscriptions

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
ReadChannel<T>::latest()Immediately read the most recent data itemNonestd::optional<Sample<T>>Owning object not closedClose errors
ReadChannel<T>::subscribe(callback)Invoke the callback each time new data arrivesstd::function<void(const Sample<T>&)>, requiredSubscriptionRecommended before startParameter or close errors
ReadChannel<T>::next()Create a one-shot wait for the next data itemNoneNextOperation<T>While the owning object is runningCancellation, close, or data stream errors
StateChannel<T>::set(value) / clear()Update or clear the haptic settingconst T& / NonevoidDevice connected and haptics supportedParameter, rejection, or disconnection errors
Subscription::unsubscribe()Stop one callback earlyNonevoidWhen the SDK keeps running but the callback is no longer neededSynchronous cancellation inside the callback is unsafe
NextOperation<T>::get() / cancel()Block for data or cancel the waitNoneSample<T> / voidDuring a single waitCancellation, close, or repeated consumption errors

Capture/Calibration sessions

APIPurposeParameters, type, and defaultReturn valueWhen to callMain errors
CaptureControl::confirm() / skip() / cancel()Confirm, skip, or cancel the current Capture requestconst std::string& request_id, requiredvoidAfter external interaction receives the current requestEmpty, expired, or state mismatch
CaptureControl::retry()Re-execute one Capture stageconst std::string& stage_id, requiredvoidWhen external interaction needs a retryEmpty, unknown, or not currently retryable
CaptureSessionControl manual capture and read status or resultssnapshot(), confirm(), skip(), retry(), cancel(), result(), close()Snapshot, std::optional<CaptureResult>, or voidWhile the Session is openExpired request, invalid stage, close errors
CalibrationSessionControl calibration and read or wait for resultssnapshot(), result(), wait(), cancel(), close()Snapshot, optional result, or result vectorWhile the Session is openWorkflow, cancellation, or close errors

Data and result models

The tables below describe the public fields that public APIs accept or return directly; std::optional means the field may be absent.

TelemetryMeta

FieldTypeDescription
sourcestd::stringSource ID that produced the data
timestampdoubleData timestamp
sequencestd::optional<std::uint64_t>Sequence number provided by the device or data source
frame_idstd::optional<std::string>Frame identifier provided by the device or data source

Sample<T>

FieldTypeDescription
valueTCurrent business data
sequencestd::uint64_tSDK sequence number, monotonically increasing within the same data category
source_timestd::optional<double>Data source time
observed_atdoubleMonotonic time at which the SDK received the data

Neither source_time nor observed_at is a system calendar time.

DiscoveredGlove and GloveDiscoveryIssue

TypeFieldDescription
DiscoveredGloveport, hand, sn, errorCandidate port, left/right hand, device SN, and per-port discovery error
GloveDiscoveryIssuecode, messageStable error classification and a display description; programs should test code

GloveDeviceInfo

FieldTypeDescription
canonical_snstd::stringCanonical SN verified through device identity
device_typestd::stringDevice type
modelstd::stringDevice model
firmware_versionstd::stringFirmware version
handSideDevice left/right hand
hand_sourcestd::stringSource of the left/right hand information

GloveNodePose and ExternalGloveFrame

TypeFieldType and description
GloveNodePosepositionstd::array<double, 3>, 3D position
GloveNodePosequaternion_xyzwstd::array<double, 4>, XYZW quaternion
ExternalGloveFramethumb, index, middle, ring, pinkyGloveNodePose, fingertip poses of the five fingers
ExternalGloveFrametimestamp_msstd::optional<double>, preferred optional millisecond input; when omitted, the current shared time reference is used; see Timestamps & external time sync for the time semantics
ExternalGloveFrametimestamp_secstd::optional<double>, deprecated compatibility input; multiplied by 1000 and mutually exclusive with timestamp_ms

GloveFeaturePayload

FieldTypeDescription
glove_idstd::stringGlove data identifier
timestamp_msdoubleDevice data time, in milliseconds
root_poseGloveNodePoseHand root node pose
fingertip_world / fingertip_localstd::map<GloveFinger, GloveNodePose>World poses of the five fingers and local poses relative to the root node
hand_sideSideLeft/right hand reported in the frame
finger_namesstd::vector<GloveFinger>Order of the fingers included in the current frame
raw_valid_mask / held_maskstd::map<GloveFinger, bool>Raw data validity and whether the previous valid value is held
quality_flagsstd::vector<std::string>Quality markers of the current frame

GlovePose

FieldTypeDescription
metaTelemetryMetaSource, time, and frame identifier
payloadGloveFeaturePayloadRoot node, five-finger poses, and validity information
qualitystd::map<std::string, Value>Extensible quality information

GloveImuPayload

FieldTypeDescription
validboolWhether the current raw counts are valid
gyroscope_rawstd::array<std::int16_t, 3>Three-axis gyroscope raw counts
accelerometer_rawstd::array<std::int16_t, 3>Three-axis accelerometer raw counts

GloveImu

FieldTypeDescription
metaTelemetryMetaSource, time, and frame identifier
payloadGloveImuPayloadvalid, three-axis gyroscope_raw, and three-axis accelerometer_raw
qualitystd::map<std::string, Value>Extensible quality information

HandJointCommand

FieldTypeDescription
targetstd::stringTarget identifier
jointsstd::map<std::string, double>Mapping from joint names to target positions
timestampdoubleOutput timestamp
sourcestd::optional<std::string>Source ID that produced the output
metadatastd::map<std::string, Value>Additional algorithm information

Skeleton fixed joints

When coming from skeleton().joint_angles(), joints always contains the following 25 active joints. The <side> in the names is replaced with left or right; read by joint name and do not treat the ordering of the std::map as the native index.

IndexJoint name
0<side>_thumb_cmc_abduction
1<side>_thumb_cmc_flexion
2<side>_thumb_cmc_opposition
3<side>_thumb_mcp_abduction
4<side>_thumb_mcp_flexion
5<side>_thumb_ip_flexion
6<side>_index_mcp_abduction
7<side>_index_mcp_flexion
8<side>_index_pip_flexion
9<side>_index_dip_flexion
10<side>_middle_mcp_abduction
11<side>_middle_mcp_flexion
12<side>_middle_pip_flexion
13<side>_middle_dip_flexion
14<side>_ring_cmc_cup
15<side>_ring_mcp_abduction
16<side>_ring_mcp_flexion
17<side>_ring_pip_flexion
18<side>_ring_dip_flexion
19<side>_little_cmc_opposition
20<side>_little_cmc_cup
21<side>_little_mcp_abduction
22<side>_little_mcp_flexion
23<side>_little_pip_flexion
24<side>_little_dip_flexion

HandSkeletonPose

FieldTypeDescription
timestamp_msdoubleSkeleton output time, in milliseconds
hand_sideSideLeft/right hand
coordinate_framestd::stringCurrently wrist_local
namesstd::vector<std::string>25 node names
positions_localstd::vector<std::array<double, 3>>25 local positions
orientations_local_xyzwstd::vector<std::array<double, 4>>25 local XYZW quaternions

Haptics

FieldTypeDescription
strengthsstd::map<GloveFinger, std::int32_t>Mapping from fingers to 0..100 haptic strength; may be empty; fingers can be thumb, index, middle, ring, pinky

GloveStatus

FieldTypeDescription
device_typestd::stringDevice type
connected / staleboolWhether connected and whether the data is stale
timestampdoubleStatus timestamp
last_errorstd::optional<std::string>Most recent device error
reconnect_countstd::uint64_tNumber of successful recoveries
fieldsstd::map<std::string, Value>Additional status related to the device type

Health

FieldTypeDescription
okboolWhether the current aggregate status is healthy
warning_count / error_countstd::uint64_tCumulative warning and error counts
devicesstd::map<std::string, DeviceHealth>Mapping from source ID to device health summary
last_errorstd::optional<std::string>Most recent SDK error
runtime_overrunboolWhether SDK scheduling has ever overrun
topic_callback_errorboolWhether an unhandled exception has ever occurred in an SDK data processing callback

DeviceHealth contains connected: bool, stale: bool, and last_error: std::optional<std::string>.

CalibrationReadiness and UpdateResult

TypeField or methodType and description
CalibrationReadinessstateCalibrationReadinessState: not_required, ready, or needs_calibration
CalibrationReadinessoperator_idstd::string, the wearer identifier used for this determination
UpdateResulttick()std::uint64_t, the current scheduling sequence number
UpdateResultran_task_count()std::uint64_t, the number of tasks executed this time
UpdateResulthas_next_task()bool, whether more tasks remain
UpdateResultsleep()SleepResult, waits for the next task to become due; each result can be called only once

Capture models

TypeFieldType and description
CapturePlanStagestage_id, promptstd::string, stage identifier and action prompt
required_sample_count, optionalstd::uint64_t, bool, required sample count and whether it can be skipped
CapturePlanpackage_ids, stagesstd::vector<std::string>, std::vector<CapturePlanStage>, algorithm packages and stage order
CaptureStageReadinessstage_id, required_sample_count, stateStage identifier, required sample count, and reusable / needs_capture state
CaptureReadinessstate, plan, stagesOverall readiness state, plan, and per-stage readiness
CaptureStageProgressstage_id, prompt, optionalCurrent stage identifier, action prompt, and whether it can be skipped
state, originCaptureStageState, CaptureStageOrigin, stage state and data origin
collected_sample_count, required_sample_countstd::uint64_t, collected sample count and required sample count
request_idstd::optional<std::string>, current control request identifier
CaptureFailurecode, messagestd::string, stable failure code and display description
CaptureProgresssession_id, session_state, failureSession identifier, state, and optional failure information
source_id, side, operator_id, stageSource, left/right hand, wearer, and current stage progress
CaptureSessionSnapshotside, plan, stateLeft/right hand, plan, and Session state
current_stage, request_idCurrent stage and request identifier, both std::optional<std::string>
collected_sample_count, required_sample_countstd::uint64_t, sampling progress of the current stage
remaining_stages, stage_progress, allowed_operationsRemaining stages, complete stage progress, and the currently allowed control operations
next_action, failureNext-step prompt and optional failure information
CaptureStageSamplesstage_id, frame_countStage identifier and final frame count
CaptureResultoperator_id, side, created_at, stage_samplesWearer, left/right hand, creation time, and per-stage capture summary

CaptureReadiness

capture_status(package_ids, operator_id) returns the overall readiness, the capture plan, and the per-stage readiness before a Capture Session is created.

FieldTypeDescription
stateCaptureReadinessStatenot_required, ready, or needs_capture
planCapturePlanThe resolved capture plan
stagesstd::vector<CaptureStageReadiness>Per-stage readiness

Calibration models

TypeFieldType and description
CalibrationJobFailurecode, messagestd::string, stable failure code and display description
CalibrationJobProgresstarget_idstd::string, target identifier
stateCalibrationJobState: pending, running, completed, failed, or cancelled
failurestd::optional<CalibrationJobFailure>, current failure information
CalibrationProgresssession_id, source_id, jobSession identifier, source ID, and current target progress
CalibrationSessionSnapshotstate, jobsSession state and progress ordered by target
CalibrationResultrecord_id, source_id, target_id, created_atRecord ID, source, target, and result creation time