MRPT  2.0.0
CImageGrabber_dc1394.cpp
Go to the documentation of this file.
1 /* +------------------------------------------------------------------------+
2  | Mobile Robot Programming Toolkit (MRPT) |
3  | https://www.mrpt.org/ |
4  | |
5  | Copyright (c) 2005-2020, Individual contributors, see AUTHORS file |
6  | See: https://www.mrpt.org/Authors - All rights reserved. |
7  | Released under BSD License. See: https://www.mrpt.org/License |
8  +------------------------------------------------------------------------+ */
9 
10 #include "hwdrivers-precomp.h" // Precompiled headers
11 
12 #include <mrpt/config.h>
14 
15 // Include the libdc1394-2 headers:
16 #if MRPT_HAS_LIBDC1394_2
17 #include <dc1394/control.h>
18 #include <dc1394/conversions.h>
19 #include <dc1394/register.h>
20 #include <dc1394/utils.h>
21 #endif
22 
23 using namespace std;
24 using namespace mrpt;
25 using namespace mrpt::hwdrivers;
26 
27 #define THE_CAMERA static_cast<dc1394camera_t*>(m_dc1394camera)
28 #define THE_CONTEXT static_cast<dc1394_t*>(m_dc1394_lib_context)
29 
30 /*-------------------------------------------------------------
31  Constructor
32  -------------------------------------------------------------*/
33 CImageGrabber_dc1394::CImageGrabber_dc1394(
34  uint64_t cameraGUID, uint16_t cameraUnit,
35  const TCaptureOptions_dc1394& options, bool verbose)
36  : m_options(options)
37 {
39 
40 #if MRPT_HAS_LIBDC1394_2
41  // Open lib:
42  m_dc1394_lib_context = dc1394_new();
44 
45  // Enumerate cameras:
46  dc1394camera_list_t* list;
47  dc1394error_t err;
48 
49  err = dc1394_camera_enumerate(THE_CONTEXT, &list);
50  if (err != DC1394_SUCCESS)
51  {
52  cerr << "[CImageGrabber_dc1394] ERROR: Failed to enumerate cameras "
53  "(Maybe your user has no rights to access IEEE1394?)."
54  << endl;
55  return;
56  }
57 
58  if (!list->num)
59  {
60  cerr << "[CImageGrabber_dc1394] ERROR: No cameras found." << endl;
61  return;
62  }
63 
64  // Open the first camera or the one given by the user:
65  if (!cameraGUID)
66  {
67  // Default: first one:
68  m_dc1394camera = dc1394_camera_new(THE_CONTEXT, list->ids[0].guid);
69  if (!THE_CAMERA)
70  {
71  dc1394_camera_free_list(list);
72  cerr << "[CImageGrabber_dc1394] ERROR: Failed to initialize camera "
73  "with GUID "
74  << list->ids[0].guid << "\n";
75  return;
76  }
77  }
78  else
79  {
80  // Look for user-given IDs:
81  for (uint32_t i = 0; i < list->num; i++)
82  {
83  if (list->ids[i].guid == cameraGUID &&
84  list->ids[i].unit == cameraUnit)
85  {
87  dc1394_camera_new_unit(THE_CONTEXT, cameraGUID, cameraUnit);
88  if (!THE_CAMERA)
89  {
90  dc1394_camera_free_list(list);
91  cerr << "[CImageGrabber_dc1394] ERROR: Failed to "
92  "initialize camera with GUID "
93  << list->ids[0].guid << "\n";
94  return;
95  }
96  break;
97  }
98  }
99 
100  if (!m_dc1394camera)
101  {
102  dc1394_camera_free_list(list);
103  cerr << "[CImageGrabber_dc1394] ERROR: Camera with GUID="
104  << cameraGUID << " and UNIT=" << cameraUnit << " not found.\n";
105  return;
106  }
107  }
108  dc1394_camera_free_list(list);
109 
110  // Camera open OK:
111  if (verbose)
112  {
113  dc1394_camera_print_info(THE_CAMERA, stdout);
114  }
115 
116  // get all supported modes:
117  dc1394video_modes_t modes;
118  err = dc1394_video_get_supported_modes(THE_CAMERA, &modes);
119  if (err != DC1394_SUCCESS)
120  {
121  cerr << "[CImageGrabber_dc1394] ERROR: Could not get list of modes."
122  << endl;
123  return;
124  }
125 
126  // Is mode7? treat differently:
127  if (options.mode7 >= 0)
128  {
129  m_desired_mode = DC1394_VIDEO_MODE_FORMAT7_MIN + options.mode7;
130  if (verbose)
131  cout << "[CImageGrabber_dc1394] Mode is mode7: " << options.mode7
132  << endl;
133  }
134  else
135  {
136 #define TEST_MODE(W, H, COLORMODEL) \
137  else if ( \
138  options.frame_width == W && options.frame_height == H && \
139  options.color_coding == COLOR_CODING_##COLORMODEL) m_desired_mode = \
140  DC1394_VIDEO_MODE_##W##x##H##_##COLORMODEL;
141 
142  if (false)
143  {
144  }
145  TEST_MODE(160, 120, YUV444)
146  TEST_MODE(320, 240, YUV422)
147  TEST_MODE(640, 480, YUV411)
148  TEST_MODE(640, 480, YUV422)
149  TEST_MODE(640, 480, RGB8)
150  TEST_MODE(640, 480, MONO8)
151  TEST_MODE(640, 480, MONO16)
152  TEST_MODE(800, 600, YUV422)
153  TEST_MODE(800, 600, RGB8)
154  TEST_MODE(800, 600, MONO8)
155  TEST_MODE(800, 600, MONO16)
156  TEST_MODE(1024, 768, YUV422)
157  TEST_MODE(1024, 768, RGB8)
158  TEST_MODE(1024, 768, MONO8)
159  TEST_MODE(1024, 768, MONO16)
160  TEST_MODE(1280, 960, YUV422)
161  TEST_MODE(1280, 960, RGB8)
162  TEST_MODE(1280, 960, MONO8)
163  TEST_MODE(1280, 960, MONO16)
164  TEST_MODE(1600, 1200, YUV422)
165  TEST_MODE(1600, 1200, RGB8)
166  TEST_MODE(1600, 1200, MONO8)
167  TEST_MODE(1600, 1200, MONO16)
168  }
169  // Display all supported modes and chosen:
170  if (verbose) cout << "------ Supported video modes ------" << endl;
171  bool valid_video_mode = false;
172  for (uint32_t i = 0; i < modes.num; i++)
173  {
174  string mode;
175  switch (modes.modes[i])
176  {
177  case DC1394_VIDEO_MODE_160x120_YUV444:
178  mode = "160x120_YUV444";
179  break;
180  case DC1394_VIDEO_MODE_320x240_YUV422:
181  mode = "320x240_YUV422";
182  break;
183  case DC1394_VIDEO_MODE_640x480_YUV411:
184  mode = "640x480_YUV411";
185  break;
186  case DC1394_VIDEO_MODE_640x480_YUV422:
187  mode = "640x480_YUV422";
188  break;
189  case DC1394_VIDEO_MODE_640x480_RGB8:
190  mode = "640x480_RGB8";
191  break;
192  case DC1394_VIDEO_MODE_640x480_MONO8:
193  mode = "640x480_MONO8";
194  break;
195  case DC1394_VIDEO_MODE_640x480_MONO16:
196  mode = "640x480_MONO16";
197  break;
198  case DC1394_VIDEO_MODE_800x600_YUV422:
199  mode = "800x600_YUV422";
200  break;
201  case DC1394_VIDEO_MODE_800x600_RGB8:
202  mode = "800x600_RGB8";
203  break;
204  case DC1394_VIDEO_MODE_800x600_MONO8:
205  mode = "800x600_MONO8";
206  break;
207  case DC1394_VIDEO_MODE_1024x768_YUV422:
208  mode = "1024x768_YUV422";
209  break;
210  case DC1394_VIDEO_MODE_1024x768_RGB8:
211  mode = "1024x768_RGB8";
212  break;
213  case DC1394_VIDEO_MODE_1024x768_MONO8:
214  mode = "1024x768_MONO8";
215  break;
216  case DC1394_VIDEO_MODE_800x600_MONO16:
217  mode = "800x600_MONO16";
218  break;
219  case DC1394_VIDEO_MODE_1024x768_MONO16:
220  mode = "1024x768_MONO16";
221  break;
222  case DC1394_VIDEO_MODE_1280x960_YUV422:
223  mode = "1280x960_YUV422";
224  break;
225  case DC1394_VIDEO_MODE_1280x960_RGB8:
226  mode = "1280x960_RGB8";
227  break;
228  case DC1394_VIDEO_MODE_1280x960_MONO8:
229  mode = "1280x960_MONO8";
230  break;
231  case DC1394_VIDEO_MODE_1600x1200_YUV422:
232  mode = "1600x1200_YUV422";
233  break;
234  case DC1394_VIDEO_MODE_1600x1200_RGB8:
235  mode = "1600x1200_RGB8";
236  break;
237  case DC1394_VIDEO_MODE_1600x1200_MONO8:
238  mode = "1600x1200_MONO8";
239  break;
240  case DC1394_VIDEO_MODE_1280x960_MONO16:
241  mode = "1280x960_MONO16";
242  break;
243  case DC1394_VIDEO_MODE_1600x1200_MONO16:
244  mode = "1600x1200_MONO16";
245  break;
246  case DC1394_VIDEO_MODE_EXIF:
247  mode = "EXIF";
248  break;
249  case DC1394_VIDEO_MODE_FORMAT7_0:
250  mode = "FORMAT7_0";
251  break;
252  case DC1394_VIDEO_MODE_FORMAT7_1:
253  mode = "FORMAT7_1";
254  break;
255  case DC1394_VIDEO_MODE_FORMAT7_2:
256  mode = "FORMAT7_2";
257  break;
258  case DC1394_VIDEO_MODE_FORMAT7_3:
259  mode = "FORMAT7_3";
260  break;
261  case DC1394_VIDEO_MODE_FORMAT7_4:
262  mode = "FORMAT7_4";
263  break;
264  case DC1394_VIDEO_MODE_FORMAT7_5:
265  mode = "FORMAT7_5";
266  break;
267  case DC1394_VIDEO_MODE_FORMAT7_6:
268  mode = "FORMAT7_6";
269  break;
270  case DC1394_VIDEO_MODE_FORMAT7_7:
271  mode = "FORMAT7_7";
272  break;
273  default:
274  cerr << "[CImageGrabber_dc1394] ERROR: Requested video mode is "
275  "not valid."
276  << endl;
277  return;
278  }
279  if (modes.modes[i] == m_desired_mode) valid_video_mode = true;
280  if (verbose)
281  {
282  if (modes.modes[i] == m_desired_mode)
283  cout << mode << " (*)" << endl;
284  else
285  cout << mode << endl;
286  }
287  }
288  if (!valid_video_mode)
289  {
290  cerr << format(
291  "[CImageGrabber_dc1394] ERROR: Requested mode %ix%i "
292  "color_model:%i is not available for this camera.",
293  options.frame_width, options.frame_height,
294  int(options.color_coding))
295  << endl;
296  return;
297  }
298 
299  // Reset to bus just in case:
300  // And only once in a program, at start up:
301  // static bool reset_1394bus = true;
302  // if (reset_1394bus)
303  {
304  // reset_1394bus = false;
305  // dc1394_reset_bus(THE_CAMERA);
306  }
307 
308  /*-----------------------------------------------------------------------
309  * setup capture
310  *-----------------------------------------------------------------------*/
311  const int SIZE_RING_BUFFER = options.ring_buffer_size;
312 
313  err = dc1394_video_set_iso_speed(THE_CAMERA, DC1394_ISO_SPEED_400);
314  if (err != DC1394_SUCCESS)
315  {
316  cerr << "[CImageGrabber_dc1394] ERROR: Could not set iso speed."
317  << endl;
318  return;
319  }
320 
321  err = dc1394_video_set_mode(THE_CAMERA, dc1394video_mode_t(m_desired_mode));
322  // This checking only assures that m_desired_mode is inside
323  // dc1394video_mode_t enum range
324  if (err != DC1394_SUCCESS)
325  {
326  cerr << "[CImageGrabber_dc1394] ERROR: Could not set video mode."
327  << endl;
328  return;
329  }
330 
331  dc1394framerate_t the_framerate;
332  switch (m_options.framerate)
333  {
334  case FRAMERATE_1_875:
335  the_framerate = DC1394_FRAMERATE_1_875;
336  break;
337  case FRAMERATE_3_75:
338  the_framerate = DC1394_FRAMERATE_3_75;
339  break;
340  case FRAMERATE_7_5:
341  the_framerate = DC1394_FRAMERATE_7_5;
342  break;
343  case FRAMERATE_15:
344  the_framerate = DC1394_FRAMERATE_15;
345  break;
346  case FRAMERATE_30:
347  the_framerate = DC1394_FRAMERATE_30;
348  break;
349  case FRAMERATE_60:
350  the_framerate = DC1394_FRAMERATE_60;
351  break;
352  case FRAMERATE_120:
353  the_framerate = DC1394_FRAMERATE_120;
354  break;
355  case FRAMERATE_240:
356  the_framerate = DC1394_FRAMERATE_240;
357  break;
358 
359  default:
360  cerr << "[CImageGrabber_dc1394] ERROR: Requested framerate is not "
361  "valid."
362  << endl;
363  return;
364  }
365 
366  err = dc1394_video_set_framerate(THE_CAMERA, the_framerate);
367  if (err != DC1394_SUCCESS)
368  {
369  cerr << "[CImageGrabber_dc1394] ERROR: Could not set framerate."
370  << endl;
371  return;
372  }
373 
374  err = dc1394_capture_setup(
375  THE_CAMERA, SIZE_RING_BUFFER, DC1394_CAPTURE_FLAGS_DEFAULT);
376  if (err != DC1394_SUCCESS)
377  {
378  cerr << "[CImageGrabber_dc1394] ERROR: Could not setup camera-\nmake "
379  "sure that the video mode and framerate are\nsupported by your "
380  "camera."
381  << endl;
382  return;
383  }
384 
385  cout << "------ Other options ------" << endl;
386  uint32_t iso_chan;
387  if ((err = dc1394_video_get_iso_channel(THE_CAMERA, &iso_chan)) ==
388  DC1394_SUCCESS)
389  if (verbose) cout << "ISO Channel: " << iso_chan << endl;
390 
391  dc1394speed_t iso_speed;
392  if ((err = dc1394_video_get_iso_speed(THE_CAMERA, &iso_speed)) ==
393  DC1394_SUCCESS)
394  if (verbose) cout << "ISO Speed: " << iso_speed << endl;
395 
396 // set trigger options:
397 #define SET_TRIGGER(opt, OPT, TYPE) \
398  if (options.trigger_##opt >= 0) \
399  { \
400  err = dc1394_external_trigger_set_##opt( \
401  THE_CAMERA, \
402  static_cast<dc1394trigger_##opt##_t>( \
403  DC1394_TRIGGER_##TYPE##_MIN + options.trigger_##opt)); \
404  DC1394_WRN( \
405  err, \
406  "[CImageGrabber_dc1394::changeCaptureOptions] Could not set " \
407  "trigger opt"); \
408  }
409  SET_TRIGGER(mode, MODE, MODE)
410  SET_TRIGGER(source, SOURCE, SOURCE)
411  SET_TRIGGER(polarity, POLARITY, ACTIVE)
412  if (options.trigger_power >= 0)
413  {
414  err = dc1394_external_trigger_set_power(
415  THE_CAMERA, dc1394switch_t(options.trigger_power));
416  DC1394_WRN(
417  err,
418  "[CImageGrabber_dc1394::changeCaptureOptions] Could not set "
419  "trigger power");
420  }
421 #undef SET_TRIGGER
422 
423  /*-----------------------------------------------------------------------
424  * have the camera start sending us data
425  *-----------------------------------------------------------------------*/
426  err = dc1394_video_set_transmission(THE_CAMERA, DC1394_ON);
427  if (err != DC1394_SUCCESS)
428  {
429  cerr << "[CImageGrabber_dc1394] ERROR: Could not start camera iso "
430  "transmission."
431  << endl;
432  return;
433  }
434 
435  // remember that we successfully initialized everything
436  m_bInitialized = true;
437 
439 
440  // Camera current features:
441  if (verbose)
442  {
443  dc1394featureset_t features;
444  if ((err = dc1394_feature_get_all(THE_CAMERA, &features)) ==
445  DC1394_SUCCESS)
446  dc1394_feature_print_all(&features, stdout);
447  }
448 
449 #else
451  "[CImageGrabber_dc1394] ERROR: MRPT compiled with "
452  "MRPT_HAS_LIBDC1394_2=0 !");
453 #endif
454  MRPT_END
455 }
456 
457 /*-------------------------------------------------------------
458  Destructor
459  -------------------------------------------------------------*/
461 {
462 #if MRPT_HAS_LIBDC1394_2
463  m_bInitialized = false;
464  if (THE_CAMERA)
465  {
466  dc1394_video_set_transmission(THE_CAMERA, DC1394_OFF);
467  dc1394_capture_stop(THE_CAMERA);
468 
469  // Release BW:
470  // uint32_t val;
471  // if (dc1394_video_get_bandwidth_usage(THE_CAMERA, &val) ==
472  // DC1394_SUCCESS)
473  // dc1394_iso_release_bandwidth(THE_CAMERA, val);
474  // if ( dc1394_video_get_iso_channel(THE_CAMERA, &val) ==
475  // DC1394_SUCCESS)
476  // dc1394_iso_release_channel(THE_CAMERA, val);
477 
478  dc1394_camera_free(THE_CAMERA);
479  }
480  if (THE_CONTEXT)
481  {
482  dc1394_free(THE_CONTEXT);
483  }
484 #endif
485 }
486 
487 /*-------------------------------------------------------------
488  get the image - MONO
489  -------------------------------------------------------------*/
491  mrpt::obs::CObservationImage& out_observation)
492 {
493  MRPT_START
494 
495  if (!m_bInitialized) return false;
496 
497 #if MRPT_HAS_LIBDC1394_2
498  dc1394video_frame_t* frame = nullptr;
499  dc1394error_t err;
500 
501  err = dc1394_video_set_transmission(THE_CAMERA, DC1394_ON);
502  if (err != DC1394_SUCCESS)
503  {
504  cerr << "[CImageGrabber_dc1394] ERROR: Could not start camera iso "
505  "transmission."
506  << endl;
507  return false;
508  }
509 
510  // get frame from ring buffer:
511  err =
512  dc1394_capture_dequeue(THE_CAMERA, DC1394_CAPTURE_POLICY_WAIT, &frame);
513  // dc1394error_t err=dc1394_capture_dequeue(THE_CAMERA,
514  // DC1394_CAPTURE_POLICY_POLL, &frame);
515  if (err != DC1394_SUCCESS)
516  {
517  cerr << "[CImageGrabber_dc1394] ERROR: Could not capture a frame"
518  << endl;
519  return false;
520  }
521 
522  out_observation.timestamp = mrpt::system::now();
523 
524  const unsigned int width = frame->size[0];
525  const unsigned int height = frame->size[1];
526 
528  {
529  /*-----------------------------------------------------------------------
530  * convert the image from what ever format it is to its RGB8
531  *-----------------------------------------------------------------------*/
532  // dc1394_get_image_size_from_video_mode(THE_CAMERA, m_desired_mode,
533  // &width, &height);
534 
535  auto* new_frame = static_cast<dc1394video_frame_t*>(
536  calloc(1, sizeof(dc1394video_frame_t)));
537  new_frame->color_coding = DC1394_COLOR_CODING_RGB8;
538  dc1394_convert_frames(frame, new_frame);
539 
540  // Fill the output class:
541  out_observation.image.loadFromMemoryBuffer(
542  width, height, true, new_frame->image, true /* BGR -> RGB */);
543 
544  // Free temporary frame:
545  free(new_frame->image);
546  free(new_frame);
547  }
548  else
549  {
550  // Stereo images:
551  dc1394error_t err;
552 
553  auto* imageBuf = new uint8_t[width * height * 2];
554  auto* imageBufRGB = new uint8_t[width * height * 2 * 3];
555 
556  if ((err = dc1394_deinterlace_stereo(
557  frame->image, imageBuf, width, 2 * height)) != DC1394_SUCCESS)
558  {
559  cerr << "[CImageGrabber_dc1394] ERROR: Could not deinterlace "
560  "stereo images: "
561  << err << endl;
562  return false;
563  }
564 
565  if ((err = dc1394_bayer_decoding_8bit(
566  imageBuf, imageBufRGB, width, 2 * height,
567  DC1394_COLOR_FILTER_GBRG, // Has to be this value for
568  // Bumblebee!
569  DC1394_BAYER_METHOD_HQLINEAR)) != DC1394_SUCCESS)
570  {
571  cerr << "[CImageGrabber_dc1394] ERROR: Could not apply Bayer "
572  "conversion: "
573  << err << endl;
574  return false;
575  }
576 
577  out_observation.image.loadFromMemoryBuffer(
578  width, height, true, imageBufRGB); // Left cam.
579  // out_observation.image.loadFromMemoryBuffer(width,height,true,
580  // imageBufRGB+ width*height*3 ); // Right cam.
581 
582  delete[] imageBuf;
583  delete[] imageBufRGB;
584  }
585 
586  // Now we can return the frame to the ring buffer:
587  err = dc1394_capture_enqueue(THE_CAMERA, frame);
588  if (err != DC1394_SUCCESS)
589  {
590  cerr << "[CImageGrabber_dc1394] ERROR: Could not enqueue the ring "
591  "buffer frame"
592  << endl;
593  return false;
594  }
595 
596  return true;
597 #else
598  THROW_EXCEPTION("The MRPT has been compiled with MRPT_HAS_LIBDC1394_2=0 !");
599 #endif
600  MRPT_END
601 }
602 
603 /*-------------------------------------------------------------
604  get the image - STEREO
605  -------------------------------------------------------------*/
607  mrpt::obs::CObservationStereoImages& out_observation)
608 {
609  MRPT_START
610 
611  if (!m_bInitialized) return false;
612 
613 #if MRPT_HAS_LIBDC1394_2
614  dc1394video_frame_t* frame = nullptr;
615 
616  // get frame from ring buffer:
617  dc1394error_t err =
618  dc1394_capture_dequeue(THE_CAMERA, DC1394_CAPTURE_POLICY_WAIT, &frame);
619  if (err != DC1394_SUCCESS)
620  {
621  cerr << "[CImageGrabber_dc1394] ERROR: Could not capture a frame"
622  << endl;
623  return false;
624  }
625 
626  out_observation.timestamp = mrpt::system::now();
627 
628  const unsigned int width = frame->size[0];
629  const unsigned int height = frame->size[1];
630 
632  {
634  "Call to getObservation(stereo) but the camera was not set as "
635  "stereo!");
636  }
637  else
638  {
639  // Stereo images:
640  dc1394error_t err;
641 
642  auto* imageBuf = new uint8_t[width * height * 2];
643  auto* imageBufRGB = new uint8_t[width * height * 2 * 3];
644 
645  if ((err = dc1394_deinterlace_stereo(
646  frame->image, imageBuf, width, 2 * height)) != DC1394_SUCCESS)
647  {
648  cerr << "[CImageGrabber_dc1394] ERROR: Could not deinterlace "
649  "stereo images: "
650  << err << endl;
651  return false;
652  }
653 
654  if ((err = dc1394_bayer_decoding_8bit(
655  imageBuf, imageBufRGB, width, 2 * height,
656  DC1394_COLOR_FILTER_GBRG, // Has to be this value for
657  // Bumblebee!
658  DC1394_BAYER_METHOD_HQLINEAR)) != DC1394_SUCCESS)
659  {
660  cerr << "[CImageGrabber_dc1394] ERROR: Could not apply Bayer "
661  "conversion: "
662  << err << endl;
663  return false;
664  }
665 
666  out_observation.imageLeft.loadFromMemoryBuffer(
667  width, height, true, imageBufRGB); // Left cam.
668  out_observation.imageRight.loadFromMemoryBuffer(
669  width, height, true,
670  imageBufRGB + width * height * 3); // Right cam.
671 
672  delete[] imageBuf;
673  delete[] imageBufRGB;
674  }
675 
676  // Now we can return the frame to the ring buffer:
677  dc1394_capture_enqueue(THE_CAMERA, frame);
678 
679  return true;
680 #else
681  THROW_EXCEPTION("The MRPT has been compiled with MRPT_HAS_LIBDC1394_2=0 !");
682 #endif
683  MRPT_END
684 }
685 
686 /*-------------------------------------------------------------
687  changeCaptureOptions
688  -------------------------------------------------------------*/
690  const TCaptureOptions_dc1394& options)
691 {
692  MRPT_START
693 
694  if (!m_bInitialized) return false;
695 
696 #if MRPT_HAS_LIBDC1394_2
697  dc1394error_t err;
698 // set features modes:
699 #define SET_MODE(feat, FEAT) \
700  if (options.feat##_mode >= 0) \
701  { \
702  err = dc1394_feature_set_mode( \
703  THE_CAMERA, DC1394_FEATURE_##FEAT, \
704  static_cast<dc1394feature_mode_t>( \
705  DC1394_FEATURE_MODE_MIN + options.feat##_mode)); \
706  DC1394_WRN( \
707  err, \
708  "[CImageGrabber_dc1394::changeCaptureOptions] Could not set feat " \
709  "mode"); \
710  }
711  SET_MODE(shutter, SHUTTER)
712  SET_MODE(gain, GAIN)
713  SET_MODE(gamma, GAMMA)
714  SET_MODE(brightness, BRIGHTNESS)
715  SET_MODE(exposure, EXPOSURE)
716  SET_MODE(sharpness, SHARPNESS)
717  SET_MODE(white_balance, WHITE_BALANCE)
718 #undef SET_MODE
719 
720 // Set features values:
721 #define SET_VALUE(feat, FEAT) \
722  if (options.feat >= 0) \
723  { \
724  err = dc1394_feature_set_value( \
725  THE_CAMERA, DC1394_FEATURE_##FEAT, options.feat); \
726  DC1394_WRN( \
727  err, \
728  "[CImageGrabber_dc1394::changeCaptureOptions] Could not set feat " \
729  "value"); \
730  }
731  SET_VALUE(shutter, SHUTTER)
732  SET_VALUE(gain, GAIN)
733  SET_VALUE(gamma, GAMMA)
734  SET_VALUE(brightness, BRIGHTNESS)
735  SET_VALUE(exposure, EXPOSURE)
736  SET_VALUE(sharpness, SHARPNESS)
737  SET_VALUE(white_balance, WHITE_BALANCE)
738 #undef SET_VALUE
739 
740  return true;
741 #else
742  THROW_EXCEPTION("The MRPT has been compiled with MRPT_HAS_LIBDC1394_2=0 !");
743 #endif
744  MRPT_END
745 }
746 
747 /*-------------------------------------------------------------
748  setSoftwareTriggerLevel
749  -------------------------------------------------------------*/
751 {
752  MRPT_START
753 
754  if (!m_bInitialized) return false;
755 
756 #if MRPT_HAS_LIBDC1394_2
757  dc1394error_t err;
758  err = dc1394_software_trigger_set_power(THE_CAMERA, (dc1394switch_t)level);
759  DC1394_WRN(
760  err,
761  "[CImageGrabber_dc1394::setSoftwareTriggerLevel] Could not set "
762  "software trigger level");
763 
764  return true;
765 #else
766  THROW_EXCEPTION("The MRPT has been compiled with MRPT_HAS_LIBDC1394_2=0 !");
767 #endif
768  MRPT_END
769 }
770 
771 /** Generates a list with the information on all the existing (Firewire) cameras
772  * in the system.
773  * \exception std::runtime_error On any error calling libdc1394.
774  */
776 {
777  MRPT_START
778 #if MRPT_HAS_LIBDC1394_2
779 
780  dc1394_t* lib_context = nullptr;
781  dc1394camera_list_t* list = nullptr;
782  out_list.clear();
783 
784  try
785  {
786  lib_context = dc1394_new();
787  if (!lib_context)
788  throw std::runtime_error(
789  "[CImageGrabber_dc1394] ERROR: Failed to enumerate cameras "
790  "(Maybe your user has no rights to access IEEE1394?).");
791 
792  // Enumerate cameras:
793  dc1394error_t err;
794 
795  err = dc1394_camera_enumerate(lib_context, &list);
796  if (err != DC1394_SUCCESS)
797  throw std::runtime_error(
798  "[CImageGrabber_dc1394] ERROR: Failed to enumerate cameras "
799  "(Maybe your user has no rights to access IEEE1394?).");
800 
801  for (unsigned int i = 0; i < list->num; i++)
802  {
803  TCameraInfo info;
804 
805  info.guid = list->ids[i].guid;
806  info.unit = list->ids[i].unit;
807 
808  // Try to open it:
809  dc1394camera_t* cam = dc1394_camera_new_unit(
810  lib_context, list->ids[i].guid, list->ids[i].unit);
811  if (!cam)
812  throw std::runtime_error(format(
813  "[CImageGrabber_dc1394] ERROR: Failed to query camera "
814  "with GUID %u\n",
815  static_cast<unsigned int>(list->ids[i].guid)));
816 
817  info.unit_spec_ID = cam->unit_spec_ID;
818  info.unit_sw_version = cam->unit_sw_version;
819  info.unit_sub_sw_version = cam->unit_sub_sw_version;
820  info.command_registers_base = cam->command_registers_base;
821  info.unit_directory = cam->unit_directory;
822  info.unit_dependent_directory = cam->unit_dependent_directory;
823  info.advanced_features_csr = cam->advanced_features_csr;
824  info.PIO_control_csr = cam->PIO_control_csr;
825  info.SIO_control_csr = cam->SIO_control_csr;
826  info.strobe_control_csr = cam->strobe_control_csr;
827  for (int j = 0; j < DC1394_VIDEO_MODE_FORMAT7_NUM; j++)
828  info.format7_csr[j] = cam->format7_csr[j];
829  info.iidc_version = cam->iidc_version;
830  info.vendor = std::string(cam->vendor ? cam->vendor : "");
831  info.model = std::string(cam->model ? cam->model : "");
832  info.vendor_id = cam->vendor_id;
833  info.model_id = cam->model_id;
834  info.bmode_capable = cam->bmode_capable;
835  info.one_shot_capable = cam->one_shot_capable;
836  info.multi_shot_capable = cam->multi_shot_capable;
837  info.can_switch_on_off = cam->can_switch_on_off;
838  info.has_vmode_error_status = cam->has_vmode_error_status;
839  info.has_feature_error_status = cam->has_feature_error_status;
840  info.max_mem_channel = cam->max_mem_channel;
841 
842  // dc1394_camera_print_info(cam,stdout);
843 
844  dc1394_camera_free(cam); // Close camera
845 
846  out_list.push_back(info);
847  }
848 
849  // Free context:
850  dc1394_free(lib_context);
851  lib_context = nullptr;
852  dc1394_camera_free_list(list);
853  list = nullptr;
854  }
855  catch (...)
856  {
857  if (list) dc1394_camera_free_list(list);
858  if (lib_context) dc1394_free(lib_context);
860  }
861 #else
862  THROW_EXCEPTION("The MRPT has been compiled with MRPT_HAS_LIBDC1394_2=0 !");
863 #endif
864  MRPT_END
865 }
Declares a class derived from "CObservation" that encapsules an image from a camera, whose relative pose to robot is also stored.
Options used when creating an dc1394 capture object All but the frame size, framerate, and color_coding can be changed dynamically by CImageGrabber_dc1394::changeCaptureOptions.
#define MRPT_START
Definition: exceptions.h:241
#define THE_CAMERA
mrpt::img::CImage imageLeft
Image from the left camera (this image will be ALWAYS present)
#define THROW_EXCEPTION(msg)
Definition: exceptions.h:67
std::string std::string format(std::string_view fmt, ARGS &&... args)
Definition: format.h:26
static void enumerateCameras(TCameraInfoList &out_list)
Generates a list with the information on all the existing (Firewire) cameras in the system...
bool deinterlace_stereo
For stereo cameras (eg PR Bumblebee)
mrpt::system::TTimeStamp now()
A shortcut for system::getCurrentTime.
Definition: datetime.h:86
Contains classes for various device interfaces.
#define THE_CONTEXT
STL namespace.
bool getObservation(mrpt::obs::CObservationImage &out_observation)
Grab an image from the opened camera (for monocular cameras).
bool setSoftwareTriggerLevel(bool level)
Changes the boolean level associated to Software Trigger (ON/OFF) Can be used to control camera trigg...
#define ASSERT_(f)
Defines an assertion mechanism.
Definition: exceptions.h:120
mrpt::img::CImage image
The image captured by the camera, that is, the main piece of information of this observation.
Observation class for either a pair of left+right or left+disparity images from a stereo camera...
int frame_width
Capture resolution (Default: 640x480)
grabber_dc1394_color_coding_t color_coding
bool changeCaptureOptions(const TCaptureOptions_dc1394 &options)
Changes the capture properties (brightness, gain, shutter, etc) The frame size, framerate, and color_coding fields in options are ignored since they can be only set at construction time.
This is the global namespace for all Mobile Robot Programming Toolkit (MRPT) libraries.
mrpt::system::TTimeStamp timestamp
The associated UTC time-stamp.
Definition: CObservation.h:60
#define MRPT_END
Definition: exceptions.h:245
int ring_buffer_size
Size of the libdc1394 ring buffer.
bool m_bInitialized
Set to false if we could not initialize the camera.
int mode7
-1: Normal mode, i>=0: use MODE7_i, then frame_width/height and color_coding are ignored.
mrpt::img::CImage imageRight
Image from the right camera, only contains a valid image if hasImageRight == true.
void loadFromMemoryBuffer(unsigned int width, unsigned int height, bool color, unsigned char *rawpixels, bool swapRedBlue=false)
Reads the image from raw pixels buffer in memory.
Definition: CImage.cpp:365
#define THROW_STACKED_EXCEPTION
Definition: exceptions.h:79



Page generated by Doxygen 1.8.14 for MRPT 2.0.0 Git: b38439d21 Tue Mar 31 19:58:06 2020 +0200 at miƩ abr 1 00:50:30 CEST 2020