unit-tests-live-zr300.cpp
Go to the documentation of this file.
00001 // License: Apache 2.0. See LICENSE file in root directory.
00002 // Copyright(c) 2015 Intel Corporation. All Rights Reserved.
00003 
00005 // This set of tests is valid only for the R200 camera //
00007 
00008 #if !defined(MAKEFILE) || ( defined(LIVE_TEST) && defined(ZR300_TEST) )
00009 
00010 #include "catch/catch.hpp"
00011 
00012 #include "librealsense/rs.hpp"
00013 #include "unit-tests-live-ds-common.h"
00014 
00015 #include <climits>
00016 #include <sstream>
00017 #include <numeric>
00018 
00019 static std::vector<rs::motion_data> accel_frames = {};
00020 static std::vector<rs::motion_data> gyro_frames = {};
00021 static std::vector<rs::timestamp_data> fisheye_timestamp_events = {};
00022 static std::vector<rs::timestamp_data> depth_timestamp_events = {};
00023 
00024 auto motion_handler = [](rs::motion_data entry)
00025 {
00026     // Collect data
00027     if (rs_event_source::RS_EVENT_IMU_ACCEL == entry.timestamp_data.source_id)
00028     {
00029         accel_frames.push_back(entry);
00030     }
00031     if (rs_event_source::RS_EVENT_IMU_GYRO == entry.timestamp_data.source_id)
00032     {
00033         gyro_frames.push_back(entry);
00034     }
00035 };
00036 
00037 // ... and the timestamp packets (DS4.1/FishEye Frame, GPIOS...)
00038 auto timestamp_handler = [](rs::timestamp_data entry)
00039 {
00040     if (rs_event_source::RS_EVENT_IMU_MOTION_CAM == entry.source_id)
00041     {
00042         fisheye_timestamp_events.push_back(entry);
00043     }
00044     if (rs_event_source::RS_EVENT_IMU_DEPTH_CAM == entry.source_id)
00045     {
00046         depth_timestamp_events.push_back(entry);
00047     }
00048 };
00049 
00050 TEST_CASE("ZR300 devices support all required options", "[live] [DS-device]")
00051 {
00052     // Require at least one device to be plugged in
00053     safe_context ctx;
00054     const int device_count = rs_get_device_count(ctx, require_no_error());
00055     REQUIRE(device_count > 0);
00056 
00057     // For each device
00058     for (int i = 0; i<device_count; ++i)
00059     {
00060         rs_device * dev = rs_get_device(ctx, 0, require_no_error());
00061         REQUIRE(dev != nullptr);
00062         REQUIRE(ds_names[Intel_ZR300] == rs_get_device_name(dev, require_no_error()));
00063 
00064         rs_set_device_option(dev, RS_OPTION_R200_LR_AUTO_EXPOSURE_ENABLED, 1.0, require_no_error());
00065 
00066         SECTION("ZR300 supports DS-Line standard UVC controls and ZR300 Motion Module controls, and nothing else")
00067         {
00068             const int supported_options[] = {
00069                 RS_OPTION_COLOR_BACKLIGHT_COMPENSATION,
00070                 RS_OPTION_COLOR_BRIGHTNESS,
00071                 RS_OPTION_COLOR_CONTRAST,
00072                 RS_OPTION_COLOR_EXPOSURE,
00073                 RS_OPTION_COLOR_GAIN,
00074                 RS_OPTION_COLOR_GAMMA,
00075                 RS_OPTION_COLOR_HUE,
00076                 RS_OPTION_COLOR_SATURATION,
00077                 RS_OPTION_COLOR_SHARPNESS,
00078                 RS_OPTION_COLOR_WHITE_BALANCE,
00079                 RS_OPTION_COLOR_ENABLE_AUTO_EXPOSURE,
00080                 RS_OPTION_COLOR_ENABLE_AUTO_WHITE_BALANCE,
00081                 RS_OPTION_R200_LR_AUTO_EXPOSURE_ENABLED,
00082                 RS_OPTION_R200_LR_GAIN,
00083                 RS_OPTION_R200_LR_EXPOSURE,
00084                 RS_OPTION_R200_EMITTER_ENABLED,
00085                 RS_OPTION_R200_DEPTH_UNITS,
00086                 RS_OPTION_R200_DEPTH_CLAMP_MIN,
00087                 RS_OPTION_R200_DEPTH_CLAMP_MAX,
00088                 RS_OPTION_R200_AUTO_EXPOSURE_MEAN_INTENSITY_SET_POINT,
00089                 RS_OPTION_R200_AUTO_EXPOSURE_TOP_EDGE,
00090                 RS_OPTION_R200_AUTO_EXPOSURE_BOTTOM_EDGE,
00091                 RS_OPTION_R200_AUTO_EXPOSURE_LEFT_EDGE,
00092                 RS_OPTION_R200_AUTO_EXPOSURE_RIGHT_EDGE,
00093                 RS_OPTION_R200_DEPTH_CONTROL_ESTIMATE_MEDIAN_DECREMENT,
00094                 RS_OPTION_R200_DEPTH_CONTROL_ESTIMATE_MEDIAN_INCREMENT,
00095                 RS_OPTION_R200_DEPTH_CONTROL_MEDIAN_THRESHOLD,
00096                 RS_OPTION_R200_DEPTH_CONTROL_SCORE_MINIMUM_THRESHOLD,
00097                 RS_OPTION_R200_DEPTH_CONTROL_SCORE_MAXIMUM_THRESHOLD,
00098                 RS_OPTION_R200_DEPTH_CONTROL_TEXTURE_COUNT_THRESHOLD,
00099                 RS_OPTION_R200_DEPTH_CONTROL_TEXTURE_DIFFERENCE_THRESHOLD,
00100                 RS_OPTION_R200_DEPTH_CONTROL_SECOND_PEAK_THRESHOLD,
00101                 RS_OPTION_R200_DEPTH_CONTROL_NEIGHBOR_THRESHOLD,
00102                 RS_OPTION_R200_DEPTH_CONTROL_LR_THRESHOLD,
00103                 RS_OPTION_FISHEYE_EXPOSURE,
00104                 RS_OPTION_FISHEYE_GAIN,
00105                 RS_OPTION_FISHEYE_STROBE,
00106                 RS_OPTION_FISHEYE_EXTERNAL_TRIGGER,
00107                 RS_OPTION_FISHEYE_ENABLE_AUTO_EXPOSURE,
00108                 RS_OPTION_FISHEYE_AUTO_EXPOSURE_MODE,
00109                 RS_OPTION_FISHEYE_AUTO_EXPOSURE_ANTIFLICKER_RATE,
00110                 RS_OPTION_FISHEYE_AUTO_EXPOSURE_PIXEL_SAMPLE_RATE,
00111                 RS_OPTION_FISHEYE_AUTO_EXPOSURE_SKIP_FRAMES,
00112                 RS_OPTION_FRAMES_QUEUE_SIZE,
00113                 RS_OPTION_HARDWARE_LOGGER_ENABLED
00114             };
00115 
00116             for (int i = 0; i<RS_OPTION_COUNT; ++i)
00117             {
00118                 if (std::find(std::begin(supported_options), std::end(supported_options), i) != std::end(supported_options))
00119                 {
00120                     REQUIRE(rs_device_supports_option(dev, (rs_option)i, require_no_error()) == 1);
00121                 }
00122                 else
00123                 {
00124                     REQUIRE(rs_device_supports_option(dev, (rs_option)i, require_no_error()) == 0);
00125                 }
00126             }
00127         }
00128     }
00129 }
00130 
00131 TEST_CASE("ZR300 Motion Module Data Streaming Validation", "[live] [DS-device]")
00132 {
00133     // Require only one device to be plugged in
00134     safe_context ctx;
00135     const int device_count = rs_get_device_count(ctx, require_no_error());
00136     REQUIRE(device_count == 1);
00137 
00138     // For each device
00139     rs_device * dev = rs_get_device(ctx, 0, require_no_error());
00140     REQUIRE(dev != nullptr);
00141 
00142     REQUIRE(ds_names[Intel_ZR300] == rs_get_device_name(dev, require_no_error()));
00143 
00144     REQUIRE(rs_supports(dev, rs_capabilities::RS_CAPABILITIES_MOTION_EVENTS, require_no_error()));
00145 
00146     unsigned int active_period_ms = 5000; // Time for the application to generate and collect data
00147     const unsigned int gyro_bandwidth_fps = 200;
00148     const unsigned int accel_bandwidth_fps = 250; // Predefined rate
00149     const double allowed_deviation = 0.03; // The frame rates can vary within the predefined limit
00150     const int video_fps = 60;
00151 
00152     for (int ii = 0; ii < 2; ii++)
00153     {
00154         INFO("Iteration num " << ii + 1 << " has started ");
00155 
00156         accel_frames.clear();
00157         gyro_frames.clear();
00158         fisheye_timestamp_events.clear();
00159         depth_timestamp_events.clear();
00160 
00161         // Configure motion events callbacks
00162         rs_enable_motion_tracking_cpp(dev, new rs::motion_callback(motion_handler), new rs::timestamp_callback(timestamp_handler), require_no_error());
00163 
00164         // Configure which video streams need to active
00165         rs_enable_stream(dev, RS_STREAM_DEPTH, 640, 480, RS_FORMAT_Z16, video_fps, require_no_error());
00166         rs_enable_stream(dev, RS_STREAM_COLOR, 640, 480, RS_FORMAT_RGB8, video_fps, require_no_error());
00167         rs_enable_stream(dev, RS_STREAM_INFRARED, 640, 480, RS_FORMAT_Y8, video_fps, require_no_error());
00168         rs_enable_stream(dev, RS_STREAM_INFRARED2, 640, 480, RS_FORMAT_Y8, video_fps, require_no_error());
00169         rs_enable_stream(dev, RS_STREAM_FISHEYE, 640, 480, RS_FORMAT_RAW8, video_fps, require_no_error());
00170 
00171         // Activate strobe to enforce timestamp events ( required by spec)
00172         rs_set_device_option(dev,rs_option::RS_OPTION_FISHEYE_STROBE, 1, require_no_error());
00173 
00174         // 3. Start generating motion-tracking data
00175         rs_start_source(dev, rs_source::RS_SOURCE_ALL, require_no_error());
00176 
00177         // Collect data for a while
00178         std::this_thread::sleep_for(std::chrono::milliseconds(active_period_ms));
00179 
00180         // 4. stop data acquisition
00181         rs_stop_source(dev, rs_source::RS_SOURCE_ALL, require_no_error());
00182 
00183         // 5. reset previous settings formotion data handlers
00184         rs_disable_motion_tracking(dev, require_no_error());
00185 
00186         // i. Sanity Tests
00187         REQUIRE(accel_frames.size() > 0);
00188         REQUIRE(gyro_frames.size() > 0);
00189         REQUIRE(fisheye_timestamp_events.size() > 0);
00190         REQUIRE(depth_timestamp_events.size() > 0);
00191         INFO(gyro_frames.size() << " Gyro packets received over " << active_period_ms*0.001 << "sec sampling");
00192         INFO(accel_frames.size() << " Accelerometer  packets received");
00193         INFO(fisheye_timestamp_events.size() << " Fisheye timestamp  packets received");
00194         INFO(depth_timestamp_events.size() << " Depth timestamp  packets received");
00195 
00196         //  Verify predefined frame rates
00197         REQUIRE(gyro_frames.size() / (double)active_period_ms == Approx(gyro_bandwidth_fps).epsilon(gyro_bandwidth_fps*allowed_deviation));
00198         REQUIRE(gyro_frames.size() / (double)active_period_ms == Approx(accel_bandwidth_fps).epsilon(accel_bandwidth_fps*allowed_deviation));
00199 
00200         REQUIRE(fisheye_timestamp_events.size() / (double)active_period_ms == Approx(video_fps).epsilon(video_fps*allowed_deviation));
00201         REQUIRE(depth_timestamp_events.size() / (double)active_period_ms == Approx(video_fps).epsilon(video_fps*allowed_deviation));
00202 
00203         // ii. Verify that the recorded data
00204         REQUIRE(std::all_of(accel_frames.begin(), accel_frames.end(), [](rs::motion_data const& entry) { return entry.timestamp_data.source_id == rs_event_source::RS_EVENT_IMU_ACCEL; }));
00205         REQUIRE(std::all_of(gyro_frames.begin(), gyro_frames.end(), [](rs::motion_data const& entry) { return entry.timestamp_data.source_id == rs_event_source::RS_EVENT_IMU_GYRO; }));
00206         REQUIRE(std::all_of(fisheye_timestamp_events.begin(), fisheye_timestamp_events.end(), [](rs::timestamp_data const& entry) { return entry.source_id == rs_event_source::RS_EVENT_IMU_MOTION_CAM; }));
00207         REQUIRE(std::all_of(depth_timestamp_events.begin(), depth_timestamp_events.end(), [](rs::timestamp_data const& entry) { return entry.source_id == rs_event_source::RS_EVENT_IMU_DEPTH_CAM; }));
00208 
00209         // iii. Validate data consistency
00210         for (size_t i = 0; i < (gyro_frames.size() - 1); i++)
00211             REQUIRE(gyro_frames[i].timestamp_data.frame_number <= gyro_frames[i + 1].timestamp_data.frame_number);
00212 
00213         for (size_t i = 0; i < (accel_frames.size() - 1); i++)
00214             REQUIRE(accel_frames[i].timestamp_data.frame_number <= accel_frames[i + 1].timestamp_data.frame_number);
00215 
00216         for (size_t i = 0; i < (fisheye_timestamp_events.size() - 1); i++)
00217             REQUIRE(fisheye_timestamp_events[i].frame_number <= fisheye_timestamp_events[i + 1].frame_number);
00218 
00219         for (size_t i = 0; i < (depth_timestamp_events.size() - 1); i++)
00220             REQUIRE(depth_timestamp_events[i].frame_number <= depth_timestamp_events[i + 1].frame_number);
00221 
00222         // Frame numbers statistics
00223         std::vector<unsigned long long> gyro_frame_numbers, accel_frame_numbers, fisheye_frame_numbers, depth_cam_frame_numbers;
00224         std::vector<unsigned long long> gyro_adjacent_diff, accel_adjacent_diff, fisheye_adjacent_diff, depth_adjacent_diff;
00225 
00226         // Extract the data
00227         for (size_t i = 0; i < gyro_frames.size(); i++) gyro_frame_numbers.push_back(gyro_frames[i].timestamp_data.frame_number);
00228         for (size_t i = 0; i < accel_frames.size(); i++) accel_frame_numbers.push_back(accel_frames[i].timestamp_data.frame_number);
00229         for (size_t i = 0; i < fisheye_timestamp_events.size(); i++) fisheye_frame_numbers.push_back(fisheye_timestamp_events[i].frame_number);
00230         for (size_t i = 0; i < depth_timestamp_events.size(); i++) depth_cam_frame_numbers.push_back(depth_timestamp_events[i].frame_number);
00231 
00232         gyro_adjacent_diff.resize(gyro_frame_numbers.size());
00233         accel_adjacent_diff.resize(accel_frame_numbers.size());
00234         fisheye_adjacent_diff.resize(fisheye_frame_numbers.size());
00235         depth_adjacent_diff.resize(depth_cam_frame_numbers.size());
00236 
00237         std::adjacent_difference(gyro_frame_numbers.begin(), gyro_frame_numbers.end(), gyro_adjacent_diff.begin());
00238         std::adjacent_difference(accel_frame_numbers.begin(), accel_frame_numbers.end(), accel_adjacent_diff.begin());
00239         std::adjacent_difference(fisheye_frame_numbers.begin(), fisheye_frame_numbers.end(), fisheye_adjacent_diff.begin());
00240         std::adjacent_difference(depth_cam_frame_numbers.begin(), depth_cam_frame_numbers.end(), depth_adjacent_diff.begin());
00241         // Fix the value of the first cell
00242         accel_adjacent_diff[0] = gyro_adjacent_diff[0] = fisheye_adjacent_diff[0] = depth_adjacent_diff[0] = 1;
00243 
00244         std::vector<unsigned int> gyro_frame_diff_bins, accel_frame_diff_bins, fisheye_frame_bins, depth_cam_frames_bins;
00245         const uint32_t max_frame_diff_allowed = 100;
00246         gyro_frame_diff_bins.resize(max_frame_diff_allowed);      // Calculate the distribution of the frame number gaps up to 100 frames
00247         accel_frame_diff_bins.resize(max_frame_diff_allowed);      // Calculate the distribution of the frame number gaps up to 100 frames
00248         fisheye_frame_bins.resize(max_frame_diff_allowed);      // Calculate the distribution of the frame number gaps up to 100 frames
00249         depth_cam_frames_bins.resize(max_frame_diff_allowed);      // Calculate the distribution of the frame number gaps up to 100 frames
00250 
00251         // Calculate distribution
00252         std::for_each(gyro_adjacent_diff.begin(), gyro_adjacent_diff.end(), [max_frame_diff_allowed, &gyro_frame_diff_bins](unsigned long n)
00253         { REQUIRE(n < max_frame_diff_allowed); gyro_frame_diff_bins[n]++; });
00254         std::for_each(accel_adjacent_diff.begin(), accel_adjacent_diff.end(), [max_frame_diff_allowed, &accel_frame_diff_bins](unsigned long n)
00255         { REQUIRE(n < max_frame_diff_allowed); accel_frame_diff_bins[n]++; });
00256         std::for_each(fisheye_adjacent_diff.begin(), fisheye_adjacent_diff.end(), [max_frame_diff_allowed, &fisheye_frame_bins](unsigned long n)
00257         { REQUIRE(n < max_frame_diff_allowed); fisheye_frame_bins[n]++; });
00258         std::for_each(depth_adjacent_diff.begin(), depth_adjacent_diff.end(), [max_frame_diff_allowed, &depth_cam_frames_bins](unsigned long n)
00259         { REQUIRE(n < max_frame_diff_allowed); depth_cam_frames_bins[n]++; });
00260 
00261         // display the distributions
00262         INFO(" gyro frame num differences: ");
00263         for (size_t i = 0; i < gyro_frame_diff_bins.size(); i++)  if (gyro_frame_diff_bins[i]) INFO("[" << i << " = " << gyro_frame_diff_bins[i] << "], ");
00264         INFO(" accel frame num differences: ");
00265         for (size_t i = 0; i < accel_frame_diff_bins.size(); i++) if (accel_frame_diff_bins[i]) INFO("[" << i << " = " << accel_frame_diff_bins[i] << "], ");
00266         INFO(" fisheye frame num differences: ");
00267         for (size_t i = 0; i < fisheye_frame_bins.size(); i++) if (fisheye_frame_bins[i]) INFO("[" << i << " = " << fisheye_frame_bins[i] << "], ");
00268         INFO(" depth frame num differences: ");
00269         for (size_t i = 0; i < depth_cam_frames_bins.size(); i++) if (depth_cam_frames_bins[i]) INFO("[" << i << " = " << depth_cam_frames_bins[i] << "], ");
00270 
00271         //Consecutive frames are those collected in bin 1
00272         double gyro_consecutive_frames_percentage = gyro_frame_diff_bins[1] / (double)gyro_frames.size() * 100;
00273         double accel_consecutive_frames_percentage = accel_frame_diff_bins[1] / (double)accel_frames.size() * 100;
00274         double fisheye_consecutive_frames_percentage = fisheye_frame_bins[1] / (double)fisheye_timestamp_events.size() * 100;
00275         double depth_consecutive_frames_percentage = depth_cam_frames_bins[1] / (double)depth_timestamp_events.size() * 100;
00276 
00277         INFO("Gyro frames- consecutive frames  " << gyro_frame_diff_bins[1] << " out of " << gyro_frames.size() << ", consistency rate:" << gyro_consecutive_frames_percentage << "% \n"
00278             << "Accel frames- consecutive frames  " << accel_frame_diff_bins[1] << " out of " << accel_frames.size() << ", consistency rate:" << accel_consecutive_frames_percentage << "% \n"
00279             << "Fisheye frames- consecutive frames  " << fisheye_frame_bins[1] << " out of " << fisheye_timestamp_events.size() << ", consistency rate:" << fisheye_consecutive_frames_percentage << "% \n"
00280             << "Depth frames- consecutive frames  " << depth_cam_frames_bins[1] << " out of " << depth_timestamp_events.size() << ", consistency rate:" << depth_consecutive_frames_percentage << "% \n");
00281 
00282     }
00283 }
00284 
00285 TEST_CASE("ZR300 correctly recognizes invalid options", "[live] [DS-device]")
00286 {
00287     rs::context ctx;
00288     REQUIRE(ctx.get_device_count() == 1);
00289 
00290     rs::device * dev = ctx.get_device(0);
00291     REQUIRE(nullptr!=dev);
00292 
00293     const char * name = dev->get_name();
00294     REQUIRE(ds_names[Intel_ZR300] == dev->get_name());
00295 
00296     int index = 0;
00297     double val = 0;
00298 
00299     for (int i= (int)rs::option::f200_laser_power; i <= (int)rs::option::sr300_auto_range_lower_threshold; i++)
00300     {
00301         index = i;
00302         try
00303         {
00304             rs::option opt = (rs::option)i;
00305             dev->set_options(&opt,1, &val);
00306         }
00307         catch(...)
00308         {
00309             REQUIRE(i==index); // Each invoked option must throw exception
00310         }
00311     }
00312 }
00313 
00314 TEST_CASE( "Test ZR300 streaming mode combinations", "[live] [ZR300] [one-camera]" )
00315 {
00316     safe_context ctx;
00317 
00318     SECTION( "exactly one device is connected" )
00319     {
00320         int device_count = rs_get_device_count(ctx, require_no_error());
00321         REQUIRE(device_count == 1);
00322     }
00323 
00324     rs_device * dev = rs_get_device(ctx, 0, require_no_error());
00325     REQUIRE(dev != nullptr);
00326 
00327     SECTION( "device name is Intel RealSense ZR300" )
00328     {
00329         const char * name = rs_get_device_name(dev, require_no_error());
00330         REQUIRE(name == std::string("Intel RealSense ZR300"));
00331     }
00332 
00333     SECTION( "streaming with some configurations" )
00334     {
00335         test_streaming(dev, {
00336             {RS_STREAM_DEPTH, 640, 480, RS_FORMAT_Z16, 60},
00337             {RS_STREAM_COLOR, 640, 480, RS_FORMAT_RGB8, 60},
00338             {RS_STREAM_INFRARED, 640, 480, RS_FORMAT_Y16, 60},
00339             {RS_STREAM_INFRARED2, 640, 480, RS_FORMAT_Y16, 60},
00340             {RS_STREAM_FISHEYE, 640, 480, RS_FORMAT_RAW8, 60}
00341         });
00342 
00343         test_streaming(dev, {
00344             {RS_STREAM_DEPTH, 640, 480, RS_FORMAT_Z16, 30},
00345             {RS_STREAM_COLOR, 640, 480, RS_FORMAT_RGB8, 30},
00346             {RS_STREAM_INFRARED, 640, 480, RS_FORMAT_Y16, 30},
00347             {RS_STREAM_INFRARED2, 640, 480, RS_FORMAT_Y16, 30},
00348             {RS_STREAM_FISHEYE, 640, 480, RS_FORMAT_RAW8, 30}
00349         });
00350     }
00351 }
00352 
00353 #endif /* !defined(MAKEFILE) || ( defined(LIVE_TEST) && defined(ZR300_TEST) ) */


librealsense
Author(s): Sergey Dorodnicov , Mark Horn , Reagan Lopez
autogenerated on Tue Jun 25 2019 19:54:39