Skip to main content

Visual-Inertial Odometry

package_name: ekf_sensor_fusion

launch_file_location: ssf_updates/launch/visionpose_sensor_pixhawk.launch

System Overview#

The ekf_sensor_fusion package performs loose-coupled sensor fusion from stereo camera's visual odometry and IMU's inertial measurement to produce UAV pose estimation.

The filter is formulated to take in body-frame velocity measurement from the visual odometry module (ZED camera), instead of the pose measurement with respect to the initial body-frame.

This architecture allows temporal VO measurement errors to be rejected effectively, when an inconsistency between IMU integration and VO measurement is detected.

pixhawk Coordinate SystemState Estimation
pixhawk Coordinate SystemState Estimation Diagram

The output of this module is the pose estimation, and only the X-Y coordinates of the pose information is fed to Pixhawk's internal state filter.

Inputs and Outputs#

Inputs:

DescriptionROS Topic TypeROS Topics (remapped in .launch files)Recommended Frequency
IMU Input (accel + gyro)sensor_msgs/Imuekf_fusion/imu_state_input>= 100Hz
Magnetometer Inputsensor_msgs/MagneticFieldekf_fusion/mag_state_inputsame as IMU
Velocity Odometrygeometry_msgs/PoseStampedekf_fusion/visionpose_measurement>= 15Hz
Delta-Pose Odometrygeometry_msgs/PoseStampedekf_fusion/zedpose_measurementnot tested
Time Synchronisation of Inputs

Input ROS messages are time-synchronised internally, to the messages' header stamp. Therefore, it is important to ensure the timestamp of the inputs are sufficiently accurate.

Best Practices
  • IMU sensor has drift over time, even between each power cycle. Therefore, pixhawk's Pixhawk firmware is programmed to perform gyro calibration at power on. DO NOT move the UAV for the first 20 second or so, until the second boot up success beeping sound is heard (indicating completion of gyro calibration).
  • Magnetometer has significant drift indoor and it almost always requires re-calibration in new environments.
    • Therefore, magnetometer input is only used during the filter initialisation, and essentially ignored when the UAV is flying. (by giving large variance in meas_noise2 parameter)
  • Delta-Pose Odometry should not be used in general, as it is not tested. (keep velocity_measurement as true)

Outputs:

DescriptionROS Topic TypeROS Topics
IMU-rate pose output in world ekf_frame (default NWU)geometry_msgs/PoseWithCovarianceStamped/ekf_fusion/pose
IMU-rate pose output, same as above but yaw is with respect to initial heading, instead of magnetic northgeometry_msgs/PoseWithCovarianceStamped/ekf_fusion/pose_local
The same as /ekf_fusion/pose but at VO-rategeometry_msgs/PoseWithCovarianceStamped/ekf_fusion/pose_corrected
FOR DEBUG ONLY (Integrated pose from IMU inputs only)geometry_msgs/PoseWithCovarianceStamped/ekf_fusino/pose_integrated

Generally, Pixhawk prefers to take in pose estimation with respected to magnetic north, at highest frequency possible, therefore /ekf_fusion/pose is currently used.

Initialisation#

Prior to the start of the system, the UAV should be in a stationary state,

Configurable Parameters (.yaml)#

ParametersDescriptionRecommended Values
velocity_measurementAlways set true, as the filter is designed and tested to receive velocity measurementtrue
pose_of_camera_not_imuSet if the pose estimation is for camera-body or imu-bodyfalse
use_imu_internal_qIf IMU has internal estimation of attitude, this could be set to true. Otherwise, the initial pose would be estimated from accelerometer (gravity-align) and magnetometer (north-align)true
do_init_gyro_bias_estimateWhen set true, the filter assumes the UAV is absolutely stationary, and all the finite gyro readings are fed as gyro bias in the statestrue
imu_frameThe coordinate frame that IMU input is usingNWU
ekf_frameThe coordinate frame that the filter pose output is usingNWU
sigma_distance_scaleThis parameter set how tolerant the filter is towards deviation of VO measured velocity / rotation agains IMU's integrated value. Smaller the value, the more sensitive the rejection3
scale_initStereo's visual frame scale respect to world frame. This value could be obtained from real-world test of the stereo camera1.0
fixed_scaleFix visual frame scaletrue
fixed_biasSet whether IMU bias online estimation is disabledfalse
fixed_calibSet whether Camera-IMU calibration estimation is disabledfalse
noise_accNoise of accelerometer measurement0.01
noise_accbiasDrift rate of accelerometer measurement0.0004
noise_gyrNoise of gyroscope measurement (much smaller than accel)0.008
noise_gyrbiasDrift rate of gyroscope0.00002
noise_scaleNot used0.0
noise_qwvNot used0.0
noise_qciNot used0.0
noise_picNot used0.0
delayHow much time in second VO is lagging IMU timestamps0.0
meas_noise1Noise of velocity measurement. The noise should be smaller when frequency increases0.03 for 15Hz;
0.008 for 30Hz
meas_noise2Noise of IMU quaternion measurement9999
init/q_ciattitude of camera with respect to IMU-
init/p_ciposition of camera with respect to IMU-
init/q_ibmounting position of IMU with respect to UAV-

Initialisation Failures#

The filter implemented a relatively robust initialisation check, so it is not uncommon to encounter the situation where the filter refuses to initialise. Most of the failures are reported as ROS messages to give clue for debugging.

For the convenience, common failures are listed below:

IMU input failed to be received

  • Symptom: "Waiting for IMU inputs..."
  • Possible causes: Pixhawk / mavros failure, check system_id etc.

Some IMU input received, but not all (failed to synchronise IMU / magnetometer)

  • Symptom: "[ssf_core] Low number of synchronized imu/magnetometer tuples received."
  • Possible causes: Magnetometer not connected properly

IMU inputs are received in sync, but IMU Variance Test cannot pass

  • Symptom: Keep receiving "=============IMU Variance Statitics==============" message
  • Possible causes:
    • IMU Gravity estimate deviate too much from reference
    • Variance of accel, gyro, or magnetometer is too large over the measurement window.

IMU input data received, but no VO measurement

  • Symptom: ekf_fusion/pose keep drifting, and ekf_fusion/pose_local is not publishing
  • Possible causes: ZED camera does not start correctly, check USB connection etc

ZED Stereo Camera Calibration#

During our flight test, we confirmed that ZED stock calibration is not accurate, even with re-calibration using their official tools.

Therefore, calibration using a dedicate calibration tool like Kalibr is strongly recommended.

After the Kalibr calibration, modify the factory calibration provided by ZED company (could be obtained by SDK, or visit http://calib.stereolabs.com/?SN=1010) with the values of the Kalibr output. The modified file should be stored in pixhawk_v1/param/zed/settings/SNxxxxx.conf

A sample calibration file could look like this (calibrated under VGA resolution)

[LEFT_CAM_VGA]cx = 333.25292570048475cy = 191.39765841045107fx = 340.7373436904007fy = 340.83066466998304k1 = -0.17236577491455016k2 = 0.025798283381817392p1 = 0.0p2 = -0.00013
[RIGHT_CAM_VGA]cx = 340.91855014058245cy = 184.2264715537507fx = 340.8878322679929fy = 340.89265557837626k1 = -0.17317038234955687k2 = 0.026135241148153184p1 = -0.00026p2 = -0.0005221063830678553
[STEREO]Baseline = 120.899CV_2K = 0.00850606CV_FHD = 0.00850606CV_HD = 0.00850606CV_VGA = 0.0032RX_2K = -0.00420175RX_FHD = -0.00420175RX_HD = -0.00420175RX_VGA = -0.0023RZ_2K = -0.0014632RZ_FHD = -0.0014632RZ_HD = -0.0014632RZ_VGA = -0.0006
Last updated on