Skip to main content
Substrate explicitly tags all position, velocity, and orientation data with a coordinate frame. This removes ambiguity when combining data from multiple sources (Gazebo, MAVLink, GPS) into a single 3D view.

Supported Frames

FrameFull NameConventionUsed By
ENUEast-North-UpX=East, Y=North, Z=UpGazebo, ROS 2, Substrate 3D viewer (canonical)
NEDNorth-East-DownX=North, Y=East, Z=DownMAVLink, PX4, ArduPilot
FLUForward-Left-UpX=Forward, Y=Left, Z=UpROS 2 body frame
FRDForward-Right-DownX=Forward, Y=Right, Z=DownMAVLink/PX4 body frame
ECEFEarth-Centered Earth-FixedGeocentric CartesianGPS coordinate transforms
LLALatitude-Longitude-AltitudeGeodetic coordinatesGPS raw data
Canonical frame: Substrate’s 3D viewer uses ENU. Data arriving in other frames is converted to ENU before display.
Different data sources use different frames. Gazebo publishes in ENU, MAVLink telemetry arrives in NED, and GPS data comes as LLA. Substrate converts all data to ENU for display in the 3D viewer.

Quaternion Convention

All orientations use the Hamilton quaternion convention: [x, y, z, w] with w as the scalar component. This matches the ROS 2 convention.

Transform Types

Transform3D

Scene graph nodes carry a Transform3D with three components:
  • position[x, y, z] in meters
  • orientation[x, y, z, w] quaternion (Hamilton, ROS 2-compatible)
  • scale[sx, sy, sz], default [1.0, 1.0, 1.0]

Transform4x4

Internal 4x4 homogeneous matrices use column-major storage order for GPU shader (WGSL) compatibility. They are constructed from a translation vector, a rotation quaternion, and an optional scale.

TF Tree

Substrate maintains a ROS 2-style transform tree that tracks parent-child relationships between coordinate frames. Dynamic transforms are time-indexed and support SLERP interpolation for smooth playback. These are used for moving entities such as drone pose and joint angles. Static transforms are timeless and used for fixed sensor extrinsics. Sensor frames matching patterns like CAM_*, LIDAR_*, RADAR_*, IMU_*, GPS_*, and GNSS_* relative to base_link are automatically promoted to static transforms. Hierarchical paths follow ROS 2/Rerun convention — slash-separated paths like world/drone/base_link/body_visual. Each node tracks its parent_path for transform chain resolution.

Lookup Algorithm

  1. Direct lookup for parent-child pairs
  2. BFS chain resolution for multi-hop transforms
  3. SLERP interpolation for rotations, linear interpolation for positions (100ms default tolerance)
  4. Quantized timestamp caching (~10ms buckets) with a generation counter for change detection
Use the query_tf_tree AI tool to inspect the current frame hierarchy or look up a transform between any two frames.

Pose Streaming

Scene geometry is sent once. Pose updates stream at 60Hz as transform-only updates with no geometry re-send, following the Rerun entity-component pattern.

GOTO Coordinates

The flight_goto AI tool accepts coordinates in ENU meters relative to the home position. The simulation bridge converts to MAVLink’s NED frame internally.