This is a follow-up to our previous post (Orientation Error (Pitch, Roll) when Camera Straight Down) about Orientation errors during flight on a drone.
When using ZED SDK v3.7.2, the pitch and roll of the camera would get “stuck” during flight at 60,75, and 90 degrees, resulting in up to 50 degrees of error in the orientation.
When ZED SDK v3.8 released, we were hoping that the sl::Camera::setRegionOfInterest
and/or PositionalTrackingParameters::depth_min_range
would fix this as the one aspect that we failed to recognize from last time was that our drone’s landing gear was very visible (large black object in image below).
Using the ZED-GStreamer plugin (master), we set pos-depth-min-range=1.0
(landing gear are at maximum <0.5m away from the camera) and set the ROI to roi-x=700
, roi-y=0
, roi-w=520
, roi-h=1080
. While the camera’s orientation no longer gets “stuck” (the previous behavior), the pitch is correct until the camera begins facing “backwards”/past 90degrees (where 90 degrees is straight down, 0 degrees is horizon). Once it exceeds 90 degrees, it appears the returned pitch is true_value - 90
from what we can tell from our logs and video recording. For example, if the true pitch of the camera is 120 degrees, the orientation returned was 30 degrees (120 - 90 = 30
).
We then did another test when holding the Drone/Camera by hand, tilting it past straight down, and the pitch was always correct. It appears the incorrect pitch behavior is only occurring during flight. At the time that this is occurring:
- the camera is flying over/looking at a gravel road with grass surrounding and a trailer underneath it
- is about 20ft above the ground
- is measuring at least some depth values (indicated by our logs measuring the depth to the trailer)
We are running on:
- Jetson Xavier NX
- ZED-GStreamer (master)
- ZED SDK 3.8.1
- ZED 2i
Our (relevant) ZED GStreamer parameters:
- stream-type: LEFT + DEPTH
- camera-resolution: 1080p
- camera-image-flip: OFF
- set-as-static: TRUE
- enable-positional-tracking: TRUE
- enable-pose-smoothing: TRUE
- enable-area-memory: TRUE
- enable-imu-fusion: TRUE
- coordinate-system: IMAGE
- measure3D-reference-frame: WORLD
- depth-mode: PERFORMANCE
- sensing-mode: FILL
- depth-minimum-distance: 300.0
- depth-maximum-distance: 30000.0
- depth-stabilization: TRUE
- pos-depth-min-range: 1000.0
- set-floor-as-origin: FALSE
- set-gravity-as-origin: TRUE
- roi: TRUE (roi-x: 700, roi-y: 0, roi-w: 520, roi-h: 1080)
- initial-world-transform-x/y/z: 0
- initial-world-transform-yaw: (custom)
- aec-agc: TRUE (roi-x: 600, roi-y: 0, roi-w: 1320, roi-h: 1080, roi-side: LEFT)
(P.S. I did just find a bug in the implementation for ZED-GStreamer’s setRegionOfInterest
that the safety checks for the ranges of roi-x/y/w/h are inverted. That was my fault as I did the PR for that update and will work on another to get that fixed (Bugfix for checking valid roi parameters by ryanppeters · Pull Request #45 · stereolabs/zed-gstreamer · GitHub). Regardless, the roi set using our parameters above actually passes the bad safety checks, and the roi is still set by the SDK)