Argus Camera Sample
Argus Camera Sample
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Dispatcher.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2016-2018, NVIDIA CORPORATION. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * * Redistributions of source code must retain the above copyright
8  * notice, this list of conditions and the following disclaimer.
9  * * Redistributions in binary form must reproduce the above copyright
10  * notice, this list of conditions and the following disclaimer in the
11  * documentation and/or other materials provided with the distribution.
12  * * Neither the name of NVIDIA CORPORATION nor the names of its
13  * contributors may be used to endorse or promote products derived
14  * from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``AS IS'' AND ANY
17  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
20  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
23  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
24  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 #include <stdio.h>
30 #include <unistd.h>
31 #include <stdarg.h>
32 #include <assert.h>
33 
34 #include <sstream>
35 #include <limits>
36 
37 #include "Dispatcher.h"
38 #include "InitOnce.h"
39 #include "UniquePointer.h"
40 #include "Error.h"
41 #include "Util.h"
42 #include "Composer.h"
43 #include "Validator.h"
44 #include <Argus/Ext/BayerSharpnessMap.h>
45 #include <Argus/Ext/DebugCaptureSession.h>
46 #include <Argus/Ext/DeFog.h>
47 #include <Argus/Ext/FaceDetect.h>
48 #include <Argus/Ext/InternalFrameCount.h>
49 #include <Argus/Ext/SensorPrivateMetadata.h>
50 #include <Argus/Ext/DebugCaptureSession.h>
51 #include <Argus/Ext/PwlWdrSensorMode.h>
52 #include <Argus/Ext/DolWdrSensorMode.h>
53 
54 namespace ArgusSamples
55 {
56 
57 /**
58  * An observer for an Argus interface.
59  */
60 class IObserverForInterface : public IObserver
61 {
62 public:
63  virtual ~IObserverForInterface() { };
64 
65  /**
66  * Check if this is the observer for the given interface.
67  *
68  * @param interface [in]
69  */
70  virtual bool isInterface(Argus::Interface *interface) const = 0;
71 };
72 
73 /**
74  * Denoise settings observer. Update Argus denoise settings when values change.
75  */
77 {
78 public:
79  DenoiseSettingsObserver(Argus::IDenoiseSettings *iDenoiseSettings)
80  : m_iDenoiseSettings(iDenoiseSettings)
81  {
82  Dispatcher &dispatcher = Dispatcher::getInstance();
83 
84  PROPAGATE_ERROR_CONTINUE(dispatcher.m_denoiseMode.registerObserver(this,
85  static_cast<IObserver::CallbackFunction>(
87  PROPAGATE_ERROR_CONTINUE(dispatcher.m_denoiseStrength.registerObserver(this,
88  static_cast<IObserver::CallbackFunction>(
90  }
91 
93  {
94  Dispatcher &dispatcher = Dispatcher::getInstance();
95 
96  PROPAGATE_ERROR_CONTINUE(dispatcher.m_denoiseStrength.unregisterObserver(this,
97  static_cast<IObserver::CallbackFunction>(
99  PROPAGATE_ERROR_CONTINUE(dispatcher.m_denoiseMode.unregisterObserver(this,
100  static_cast<IObserver::CallbackFunction>(
102  }
103 
104  virtual bool isInterface(Argus::Interface *interface) const
105  {
106  return (interface == m_iDenoiseSettings);
107  }
108 
109 private:
110  bool onDenoiseModeChanged(const Observed &source)
111  {
112  Dispatcher &dispatcher = Dispatcher::getInstance();
113 
114  assert(&source == &dispatcher.m_denoiseMode);
115 
116  if (m_iDenoiseSettings->setDenoiseMode(dispatcher.m_denoiseMode.get()) != Argus::STATUS_OK)
117  ORIGINATE_ERROR("Failed to set the denoising mode");
118 
119  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
120 
121  return true;
122  }
123 
124  bool onDenoiseStrengthChanged(const Observed &source)
125  {
126  Dispatcher &dispatcher = Dispatcher::getInstance();
127 
128  assert(&source == &dispatcher.m_denoiseStrength);
129 
130  if (m_iDenoiseSettings->setDenoiseStrength(dispatcher.m_denoiseStrength.get()) !=
131  Argus::STATUS_OK)
132  {
133  ORIGINATE_ERROR("Failed to set the denoise strength");
134  }
135 
136  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
137 
138  return true;
139  }
140 
141  Argus::IDenoiseSettings *m_iDenoiseSettings;
142 };
143 
144 /**
145  * Edge enhancement settings observer. Update Argus edge enhance settings when values change.
146  */
148 {
149 public:
150  EdgeEnhanceSettingsObserver(Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings)
151  : m_iEdgeEnhanceSettings(iEdgeEnhanceSettings)
152  {
153  Dispatcher &dispatcher = Dispatcher::getInstance();
154 
155  PROPAGATE_ERROR_CONTINUE(dispatcher.m_edgeEnhanceMode.registerObserver(this,
156  static_cast<IObserver::CallbackFunction>(
158  PROPAGATE_ERROR_CONTINUE(dispatcher.m_edgeEnhanceStrength.registerObserver(this,
159  static_cast<IObserver::CallbackFunction>(
161  }
162 
164  {
165  Dispatcher &dispatcher = Dispatcher::getInstance();
166 
167  PROPAGATE_ERROR_CONTINUE(dispatcher.m_edgeEnhanceStrength.unregisterObserver(this,
168  static_cast<IObserver::CallbackFunction>(
170  PROPAGATE_ERROR_CONTINUE(dispatcher.m_edgeEnhanceMode.unregisterObserver(this,
171  static_cast<IObserver::CallbackFunction>(
173  }
174 
175  virtual bool isInterface(Argus::Interface *interface) const
176  {
177  return (interface == m_iEdgeEnhanceSettings);
178  }
179 
180 private:
181  bool onEdgeEnhanceModeChanged(const Observed &source)
182  {
183  Dispatcher &dispatcher = Dispatcher::getInstance();
184 
185  assert(&source == &dispatcher.m_edgeEnhanceMode);
186 
187  if (m_iEdgeEnhanceSettings->setEdgeEnhanceMode(dispatcher.m_edgeEnhanceMode.get())
188  != Argus::STATUS_OK)
189  {
190  ORIGINATE_ERROR("Failed to set the edge enhancement mode");
191  }
192 
193  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
194 
195  return true;
196  }
197 
198  bool onEdgeEnhanceStrengthChanged(const Observed &source)
199  {
200  Dispatcher &dispatcher = Dispatcher::getInstance();
201 
202  assert(&source == &dispatcher.m_edgeEnhanceStrength);
203 
204  if (m_iEdgeEnhanceSettings->setEdgeEnhanceStrength(dispatcher.m_edgeEnhanceStrength.get())
205  != Argus::STATUS_OK)
206  {
207  ORIGINATE_ERROR("Failed to set the edge enhancement strength");
208  }
209 
210  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
211 
212  return true;
213  }
214 
215  Argus::IEdgeEnhanceSettings *m_iEdgeEnhanceSettings;
216 };
217 
218 /**
219  * Source settings observer. Update Argus source settings if values which are set through the
220  * source settings change.
221  */
223 {
224 public:
225  SourceSettingsObserver(Argus::ISourceSettings *iSourceSettings)
226  : m_iSourceSettings(iSourceSettings)
227  {
228  Dispatcher &dispatcher = Dispatcher::getInstance();
229 
230  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureTimeRange.registerObserver(this,
231  static_cast<IObserver::CallbackFunction>(
233  PROPAGATE_ERROR_CONTINUE(dispatcher.m_gainRange.registerObserver(this,
234  static_cast<IObserver::CallbackFunction>(
236  PROPAGATE_ERROR_CONTINUE(dispatcher.m_sensorModeIndex.registerObserver(this,
237  static_cast<IObserver::CallbackFunction>(
239  PROPAGATE_ERROR_CONTINUE(dispatcher.m_frameRate.registerObserver(this,
240  static_cast<IObserver::CallbackFunction>(
242  PROPAGATE_ERROR_CONTINUE(dispatcher.m_focusPosition.registerObserver(this,
243  static_cast<IObserver::CallbackFunction>(
245  PROPAGATE_ERROR_CONTINUE(dispatcher.m_captureYuvFormat.registerObserver(this,
246  static_cast<IObserver::CallbackFunction>(
248  }
249 
251  {
252  Dispatcher &dispatcher = Dispatcher::getInstance();
253 
254  PROPAGATE_ERROR_CONTINUE(dispatcher.m_focusPosition.unregisterObserver(this,
255  static_cast<IObserver::CallbackFunction>(
257  PROPAGATE_ERROR_CONTINUE(dispatcher.m_frameRate.unregisterObserver(this,
258  static_cast<IObserver::CallbackFunction>(
260  PROPAGATE_ERROR_CONTINUE(dispatcher.m_sensorModeIndex.unregisterObserver(this,
261  static_cast<IObserver::CallbackFunction>(
263  PROPAGATE_ERROR_CONTINUE(dispatcher.m_gainRange.unregisterObserver(this,
264  static_cast<IObserver::CallbackFunction>(
266  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureTimeRange.unregisterObserver(this,
267  static_cast<IObserver::CallbackFunction>(
269  PROPAGATE_ERROR_CONTINUE(dispatcher.m_captureYuvFormat.unregisterObserver(this,
270  static_cast<IObserver::CallbackFunction>(
272  }
273 
274  virtual bool isInterface(Argus::Interface *interface) const
275  {
276  return (interface == m_iSourceSettings);
277  }
278 
279 private:
280  bool onExposureTimeRangeChanged(const Observed &source)
281  {
282  Dispatcher &dispatcher = Dispatcher::getInstance();
283 
284  assert(&source == &dispatcher.m_exposureTimeRange);
285 
286  if (m_iSourceSettings->setExposureTimeRange(dispatcher.m_exposureTimeRange.get()) !=
287  Argus::STATUS_OK)
288  {
289  ORIGINATE_ERROR("Failed to set exposure time range");
290  }
291 
292  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
293 
294  return true;
295  }
296 
297  bool onGainRangeChanged(const Observed &source)
298  {
299  Dispatcher &dispatcher = Dispatcher::getInstance();
300 
301  assert(&source == &dispatcher.m_gainRange);
302 
303  if (m_iSourceSettings->setGainRange(dispatcher.m_gainRange.get()) != Argus::STATUS_OK)
304  ORIGINATE_ERROR("Failed to set gain range");
305 
306  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
307 
308  return true;
309  }
310 
311  bool onSensorModeChanged(const Observed &source)
312  {
313  Dispatcher &dispatcher = Dispatcher::getInstance();
314 
315  assert(&source == &dispatcher.m_sensorModeIndex);
316 
317  Argus::SensorMode *sensorMode = NULL;
318  PROPAGATE_ERROR(dispatcher.getSensorMode(dispatcher.m_sensorModeIndex.get(), &sensorMode));
319 
320  if (m_iSourceSettings->setSensorMode(sensorMode) != Argus::STATUS_OK)
321  ORIGINATE_ERROR("Failed to set sensor mode");
322 
323  PROPAGATE_ERROR(dispatcher.restartActiveRequests());
324 
325  return true;
326  }
327 
328  bool onCaptureYuvFormatChanged(const Observed & source)
329  {
330  Dispatcher &dispatcher = Dispatcher::getInstance();
331 
332  assert(&source == &dispatcher.m_captureYuvFormat);
333 
334  // The Video/Still task will shut down and restart their
335  // EGLStreams, causing their underlying buffer pools to be reallocated.
336  // So there's not much else to do here.
337  PROPAGATE_ERROR(dispatcher.restartActiveRequests());
338 
339  return true;
340  }
341 
342  bool onFocusPositionChanged(const Observed &source)
343  {
344  Dispatcher &dispatcher = Dispatcher::getInstance();
345 
346  assert(&source == &dispatcher.m_focusPosition);
347 
348  if (m_iSourceSettings->setFocusPosition(dispatcher.m_focusPosition.get()) !=
349  Argus::STATUS_OK)
350  {
351  ORIGINATE_ERROR("Failed to set focus position");
352  }
353 
354  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
355 
356  return true;
357  }
358 
359  bool onFrameRateChanged(const Observed &source)
360  {
361  Dispatcher &dispatcher = Dispatcher::getInstance();
362 
363  assert(&source == &dispatcher.m_frameRate);
364 
365  Argus::Range<uint64_t> frameDurationRangeNs(0);
366 
367  if (dispatcher.m_frameRate.get() == 0.0f)
368  {
369  // a frame rate of zero means VFR, get the sensor frame duration and apply it to
370  // the source
371  Argus::SensorMode *sensorMode = NULL;
372  PROPAGATE_ERROR(dispatcher.getSensorMode(dispatcher.m_sensorModeIndex.get(),
373  &sensorMode));
374 
375  Argus::ISensorMode *iSensorMode =
376  Argus::interface_cast<Argus::ISensorMode>(sensorMode);
377 
378  frameDurationRangeNs = iSensorMode->getFrameDurationRange();
379  }
380  else
381  {
382  // frame rate is frames per second, frameduration is in nanoseconds
383  frameDurationRangeNs =
384  TimeValue::fromCycelsPerSec(dispatcher.m_frameRate.get()).toNSec();
385  }
386 
387  if (m_iSourceSettings->setFrameDurationRange(frameDurationRangeNs) != Argus::STATUS_OK)
388  ORIGINATE_ERROR("Failed to set frame duration range");
389 
390  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
391 
392  return true;
393  }
394 
395  Argus::ISourceSettings *m_iSourceSettings;
396 };
397 
398 /**
399  * Auto control settings observer. Update Argus auto control settings if values which are set
400  * through the auto control settings change.
401  */
403 {
404 public:
405  AutoControlSettingsObserver(Argus::IAutoControlSettings *iAutoControlSettings)
406  : m_iAutoControlSettings(iAutoControlSettings)
407  {
408  Dispatcher &dispatcher = Dispatcher::getInstance();
409 
410  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeAntibandingMode.registerObserver(this,
411  static_cast<IObserver::CallbackFunction>(
413  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeLock.registerObserver(this,
414  static_cast<IObserver::CallbackFunction>(
416  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbLock.registerObserver(this,
417  static_cast<IObserver::CallbackFunction>(
419  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbMode.registerObserver(this,
420  static_cast<IObserver::CallbackFunction>(
422  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureCompensation.registerObserver(this,
423  static_cast<IObserver::CallbackFunction>(
425  PROPAGATE_ERROR_CONTINUE(dispatcher.m_ispDigitalGainRange.registerObserver(this,
426  static_cast<IObserver::CallbackFunction>(
428 
429  }
430 
432  {
433  Dispatcher &dispatcher = Dispatcher::getInstance();
434 
435  PROPAGATE_ERROR_CONTINUE(dispatcher.m_ispDigitalGainRange.unregisterObserver(this,
436  static_cast<IObserver::CallbackFunction>(
438  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureCompensation.unregisterObserver(this,
439  static_cast<IObserver::CallbackFunction>(
441  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbMode.unregisterObserver(this,
442  static_cast<IObserver::CallbackFunction>(
444  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbLock.unregisterObserver(this,
445  static_cast<IObserver::CallbackFunction>(
447  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeLock.unregisterObserver(this,
448  static_cast<IObserver::CallbackFunction>(
450  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeAntibandingMode.unregisterObserver(this,
451  static_cast<IObserver::CallbackFunction>(
453  }
454 
455  virtual bool isInterface(Argus::Interface *interface) const
456  {
457  return (interface == m_iAutoControlSettings);
458  }
459 
460 private:
461  bool onAeAntibandingModeChanged(const Observed &source)
462  {
463  Dispatcher &dispatcher = Dispatcher::getInstance();
464 
465  assert(&source == &dispatcher.m_aeAntibandingMode);
466 
467  if (m_iAutoControlSettings->setAeAntibandingMode(dispatcher.m_aeAntibandingMode.get()) !=
468  Argus::STATUS_OK)
469  {
470  ORIGINATE_ERROR("Failed to set the AE antibanding mode");
471  }
472 
473  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
474 
475  return true;
476  }
477 
478  bool onAeLockChanged(const Observed &source)
479  {
480  Dispatcher &dispatcher = Dispatcher::getInstance();
481 
482  assert(&source == &dispatcher.m_aeLock);
483 
484  if (m_iAutoControlSettings->setAeLock(dispatcher.m_aeLock.get()) != Argus::STATUS_OK)
485  ORIGINATE_ERROR("Failed to set the AE lock");
486 
487  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
488 
489  return true;
490  }
491 
492  bool onAwbLockChanged(const Observed &source)
493  {
494  Dispatcher &dispatcher = Dispatcher::getInstance();
495 
496  assert(&source == &dispatcher.m_awbLock);
497 
498  if (m_iAutoControlSettings->setAwbLock(dispatcher.m_awbLock.get()) != Argus::STATUS_OK)
499  ORIGINATE_ERROR("Failed to set the AWB lock");
500 
501  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
502 
503  return true;
504  }
505 
506  bool onAwbModeChanged(const Observed &source)
507  {
508  Dispatcher &dispatcher = Dispatcher::getInstance();
509 
510  assert(&source == &dispatcher.m_awbMode);
511 
512  if (m_iAutoControlSettings->setAwbMode(dispatcher.m_awbMode.get()) != Argus::STATUS_OK)
513  ORIGINATE_ERROR("Failed to set the AWB mode");
514 
515  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
516 
517  return true;
518  }
519 
520  bool onExposureCompensationChanged(const Observed &source)
521  {
522  Dispatcher &dispatcher = Dispatcher::getInstance();
523 
524  assert(&source == &dispatcher.m_exposureCompensation);
525 
526  if (m_iAutoControlSettings->setExposureCompensation(
527  dispatcher.m_exposureCompensation.get()) != Argus::STATUS_OK)
528  {
529  ORIGINATE_ERROR("Failed to set the exposure compensation");
530  }
531 
532  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
533 
534  return true;
535  }
536 
537  bool onIspDigitalGainRangeChanged(const Observed &source)
538  {
539  Dispatcher &dispatcher = Dispatcher::getInstance();
540 
541  assert(&source == &dispatcher.m_ispDigitalGainRange);
542 
543  if (m_iAutoControlSettings->setIspDigitalGainRange(
544  dispatcher.m_ispDigitalGainRange.get()) != Argus::STATUS_OK)
545  {
546  ORIGINATE_ERROR("Failed to set the Isp Digital Gain Range");
547  }
548  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
549 
550  return true;
551  }
552 
553  Argus::IAutoControlSettings *m_iAutoControlSettings;
554 };
555 
556 /**
557  * DeFog settings observer. Update Argus DeFog settings if values which are set through the
558  * DeFog settings change.
559  */
561 {
562 public:
563  DeFogSettingsObserver(Argus::Ext::IDeFogSettings *iDeFogSettings)
564  : m_iDeFogSettings(iDeFogSettings)
565  {
566  Dispatcher &dispatcher = Dispatcher::getInstance();
567 
568  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogEnable.registerObserver(this,
569  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogEnableChanged)));
570  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogAmount.registerObserver(this,
571  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogAmountChanged)));
572  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogQuality.registerObserver(this,
573  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogQualityChanged)));
574  }
575 
577  {
578  Dispatcher &dispatcher = Dispatcher::getInstance();
579 
580  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogQuality.unregisterObserver(this,
581  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogQualityChanged)));
582  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogAmount.unregisterObserver(this,
583  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogAmountChanged)));
584  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogEnable.unregisterObserver(this,
585  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogEnableChanged)));
586  }
587 
588  virtual bool isInterface(Argus::Interface *interface) const
589  {
590  return (interface == m_iDeFogSettings);
591  }
592 
593 private:
594  bool onDeFogEnableChanged(const Observed &source)
595  {
596  Dispatcher &dispatcher = Dispatcher::getInstance();
597 
598  assert(&source == &dispatcher.m_deFogEnable);
599 
600  m_iDeFogSettings->setDeFogEnable(dispatcher.m_deFogEnable.get());
601 
602  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
603 
604  return true;
605  }
606 
607  bool onDeFogAmountChanged(const Observed &source)
608  {
609  Dispatcher &dispatcher = Dispatcher::getInstance();
610 
611  assert(&source == &dispatcher.m_deFogAmount);
612 
613  if (m_iDeFogSettings->setDeFogAmount(dispatcher.m_deFogAmount.get()) != Argus::STATUS_OK)
614  ORIGINATE_ERROR("Failed to set the DeFog amount");
615 
616  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
617 
618  return true;
619  }
620 
621  bool onDeFogQualityChanged(const Observed &source)
622  {
623  Dispatcher &dispatcher = Dispatcher::getInstance();
624 
625  assert(&source == &dispatcher.m_deFogQuality);
626 
627  if (m_iDeFogSettings->setDeFogQuality(dispatcher.m_deFogQuality.get()) != Argus::STATUS_OK)
628  ORIGINATE_ERROR("Failed to set the DeFog quality");
629 
630  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
631 
632  return true;
633  }
634 
635  Argus::Ext::IDeFogSettings *m_iDeFogSettings;
636 };
637 
638 // valid YUV pixel formats
639 static const ValidatorEnum<Argus::PixelFormat>::ValueStringPair s_captureYuvFormatTypes[] =
640 {
641  { Argus::PIXEL_FMT_YCbCr_420_888, "nv12" },
642  { Argus::PIXEL_FMT_P016, "p016" }
643 };
644 
645 // valid denoise modes
646 static const ValidatorEnum<Argus::DenoiseMode>::ValueStringPair s_denoiseModes[] =
647 {
648  { Argus::DENOISE_MODE_OFF, "off" },
649  { Argus::DENOISE_MODE_FAST, "fast" },
650  { Argus::DENOISE_MODE_HIGH_QUALITY, "highquality" }
651 };
652 
653 // valid edge enhance modes
654 static const ValidatorEnum<Argus::EdgeEnhanceMode>::ValueStringPair s_edgeEnhanceModes[] =
655 {
656  { Argus::EDGE_ENHANCE_MODE_OFF, "off" },
657  { Argus::EDGE_ENHANCE_MODE_FAST, "fast" },
658  { Argus::EDGE_ENHANCE_MODE_HIGH_QUALITY, "highquality" }
659 };
660 
661 // valid AE antibanding modes
662 static const ValidatorEnum<Argus::AeAntibandingMode>::ValueStringPair s_aeAntibandingModes[] =
663 {
664  { Argus::AE_ANTIBANDING_MODE_OFF, "off" },
665  { Argus::AE_ANTIBANDING_MODE_AUTO, "auto" },
666  { Argus::AE_ANTIBANDING_MODE_50HZ, "50hz" },
667  { Argus::AE_ANTIBANDING_MODE_60HZ, "60hz" }
668 };
669 
670 // valid AWB modes
671 static const ValidatorEnum<Argus::AwbMode>::ValueStringPair s_awbModes[] =
672 {
673  { Argus::AWB_MODE_OFF, "off" },
674  { Argus::AWB_MODE_AUTO, "auto" },
675  { Argus::AWB_MODE_INCANDESCENT, "incandescent" },
676  { Argus::AWB_MODE_FLUORESCENT, "fluorescent" },
677  { Argus::AWB_MODE_WARM_FLUORESCENT, "warmfluorescent" },
678  { Argus::AWB_MODE_DAYLIGHT, "daylight" },
679  { Argus::AWB_MODE_CLOUDY_DAYLIGHT, "cloudydaylight" },
680  { Argus::AWB_MODE_TWILIGHT, "twilight" },
681  { Argus::AWB_MODE_SHADE, "shade" },
682  { Argus::AWB_MODE_MANUAL, "manual" }
683 };
684 
685 // valid still file formats
686 static const ValidatorEnum<ArgusSamples::StillFileType>::ValueStringPair s_stillFileTypes[] =
687 {
690 };
691 
692 // valid video formats
693 static const ValidatorEnum<VideoPipeline::VideoFormat>::ValueStringPair s_videoFormats[] =
694 {
699 };
700 
701 // valid video file types
702 static const ValidatorEnum<VideoPipeline::VideoFileType>::ValueStringPair s_videoFileTypes[] =
703 {
709 };
710 
711 static const Argus::Size2D<uint32_t> s_outputSizes[] =
712 {
713  Argus::Size2D<uint32_t>(0, 0), // if size is 0,0 take the current sensor size
714  Argus::Size2D<uint32_t>(176, 144), // QCIF
715  Argus::Size2D<uint32_t>(320, 240),
716  Argus::Size2D<uint32_t>(640, 480),
717  Argus::Size2D<uint32_t>(1280, 720), // 720p HDTV
718  Argus::Size2D<uint32_t>(1920, 1080), // 1080p HDTV
719  Argus::Size2D<uint32_t>(3840, 2160), // 2160p 4K UHDTV
720 };
721 
723  : m_deviceFocusPositionRange(0)
724  , m_deviceExposureCompensationRange(0.0f)
725  , m_deviceIspDigitalGainRange(Argus::Range<float>(0.0f))
726  , m_sensorExposureTimeRange(Argus::Range<uint64_t>(0))
727  , m_sensorAnalogGainRange(Argus::Range<float>(0.0f))
728  , m_sensorFrameRateRange(0.0f)
729  , m_deviceIndex(new ValidatorStdVector<uint32_t, Argus::CameraDevice*>(&m_cameraDevices), 0)
730  , m_deviceOpen(false)
731  , m_sensorModeValid(false)
732  , m_verbose(false)
733  , m_kpi(false)
734  , m_exposureTimeRange(new ValidatorRange<Argus::Range<uint64_t> >(&m_sensorExposureTimeRange),
735  Argus::Range<uint64_t>(0))
736  , m_gainRange(new ValidatorRange<Argus::Range<float > >(&m_sensorAnalogGainRange),
737  Argus::Range<float>(0.0f))
738  , m_sensorModeIndex(new ValidatorEnum<uint32_t>(), 0)
739  , m_frameRate(new ValidatorRange<float>(&m_sensorFrameRateRange), 0.0f)
740  , m_focusPosition(new ValidatorRange<int32_t>(&m_deviceFocusPositionRange), 0)
741  , m_captureYuvFormat(new ValidatorEnum<Argus::PixelFormat>(
742  s_captureYuvFormatTypes,
743  sizeof(s_captureYuvFormatTypes) / sizeof(s_captureYuvFormatTypes[0])),
744  Argus::PIXEL_FMT_YCbCr_420_888)
745  , m_denoiseMode(new ValidatorEnum<Argus::DenoiseMode>(
746  s_denoiseModes, sizeof(s_denoiseModes) / sizeof(s_denoiseModes[0])),
747  Argus::DENOISE_MODE_FAST)
748  , m_denoiseStrength(new ValidatorRange<float>(-1.0f, 1.0f), -1.0f)
749  , m_edgeEnhanceMode(new ValidatorEnum<Argus::EdgeEnhanceMode>(
750  s_edgeEnhanceModes, sizeof(s_edgeEnhanceModes) / sizeof(s_edgeEnhanceModes[0])),
751  Argus::EDGE_ENHANCE_MODE_FAST)
752  , m_edgeEnhanceStrength(new ValidatorRange<float>(-1.0f, 1.0f), -1.0f)
753  , m_aeAntibandingMode(new ValidatorEnum<Argus::AeAntibandingMode>(
754  s_aeAntibandingModes, sizeof(s_aeAntibandingModes) / sizeof(s_aeAntibandingModes[0])),
755  Argus::AE_ANTIBANDING_MODE_AUTO)
756  , m_aeLock(false)
757  , m_awbLock(false)
758  , m_awbMode(new ValidatorEnum<Argus::AwbMode>(
759  s_awbModes, sizeof(s_awbModes) / sizeof(s_awbModes[0])),
760  Argus::AWB_MODE_AUTO)
761  , m_exposureCompensation(new ValidatorRange<float>(&m_deviceExposureCompensationRange), 0.0f)
762  , m_ispDigitalGainRange(new ValidatorRange<Argus::Range<float> >(&m_deviceIspDigitalGainRange),
763  Argus::Range<float>(1.0f))
764  , m_stillFileType(new ValidatorEnum<StillFileType>(
765  s_stillFileTypes, sizeof(s_stillFileTypes) / sizeof(s_stillFileTypes[0])),
767  , m_videoFormat(new ValidatorEnum<VideoPipeline::VideoFormat>(
768  s_videoFormats, sizeof(s_videoFormats) / sizeof(s_videoFormats[0])),
769  VideoPipeline::VIDEO_FORMAT_H265)
770  , m_videoFileType(new ValidatorEnum<VideoPipeline::VideoFileType>(
771  s_videoFileTypes, sizeof(s_videoFileTypes) / sizeof(s_videoFileTypes[0])),
772  VideoPipeline::VIDEO_FILE_TYPE_MKV)
773  , m_videoBitRate(new ValidatorRange<uint32_t>(0, VideoPipeline::VIDEO_BITRATE_MAX),0)
774  , m_outputSize(new ValidatorSize2D<uint32_t>(s_outputSizes,
775  sizeof(s_outputSizes) / sizeof(s_outputSizes[0]), true /*allowArbitrarySizes*/),
776  Argus::Size2D<uint32_t>(0, 0))
777  , m_outputPath(".")
778  , m_deFogEnable(false)
779  , m_deFogAmount(new ValidatorRange<float>(0.0f, 1.0f), 0.9f)
780  , m_deFogQuality(new ValidatorRange<float>(0.0f, 1.0f), 0.14285f)
781  , m_initialized(false)
782  , m_iCameraProvider(NULL)
783 {
784  PROPAGATE_ERROR_CONTINUE(initialize());
785 }
786 
788 {
789  if (!shutdown())
790  REPORT_ERROR("Failed to shutdown");
791 }
792 
794 {
795  static InitOnce initOnce;
796  static Dispatcher instance;
797 
798  if (initOnce.begin())
799  {
800  if (instance.initialize())
801  {
802  initOnce.complete();
803  }
804  else
805  {
806  initOnce.failed();
807  REPORT_ERROR("Initalization failed");
808  }
809  }
810 
811  return instance;
812 }
813 
815 {
816  if (m_initialized)
817  return true;
818 
819  // Create the CameraProvider object and obtain its interface.
820  m_cameraProvider = Argus::UniqueObj<Argus::CameraProvider>(Argus::CameraProvider::create());
821  m_iCameraProvider = Argus::interface_cast<Argus::ICameraProvider>(m_cameraProvider);
822  if (!m_iCameraProvider)
823  ORIGINATE_ERROR("Failed to create CameraProvider");
824  printf("Argus Version: %s\n", m_iCameraProvider->getVersion().c_str());
825 
826  // Get the camera devices
827  m_iCameraProvider->getCameraDevices(&m_cameraDevices);
828  if (m_cameraDevices.size() == 0)
829  {
830  PROPAGATE_ERROR(shutdown());
831  ORIGINATE_ERROR("No cameras available");
832  }
833 
834  m_initialized = true;
835 
836  // register the device index observer after 'm_initialize' is set, the call back will be
837  // called immediately and assert that 'm_initialize' is set
838  PROPAGATE_ERROR_CONTINUE(m_deviceIndex.registerObserver(this,
839  static_cast<IObserver::CallbackFunction>(&Dispatcher::onDeviceIndexChanged)));
840  PROPAGATE_ERROR_CONTINUE(m_sensorModeIndex.registerObserver(this,
841  static_cast<IObserver::CallbackFunction>(&Dispatcher::onSensorModeIndexChanged)));
842 
843  return true;
844 }
845 
847 {
848  if (m_initialized)
849  {
850  m_initialized = false;
851  // unregister the device index observer in reverse order
852  PROPAGATE_ERROR_CONTINUE(m_sensorModeIndex.unregisterObserver(this,
853  static_cast<IObserver::CallbackFunction>(&Dispatcher::onSensorModeIndexChanged)));
854  PROPAGATE_ERROR_CONTINUE(m_deviceIndex.unregisterObserver(this,
855  static_cast<IObserver::CallbackFunction>(&Dispatcher::onDeviceIndexChanged)));
856 
857  PROPAGATE_ERROR_CONTINUE(closeSession());
858 
859  m_cameraDevices.clear();
860  m_cameraProvider.reset();
861  }
862 
863  return true;
864 }
865 
866 bool Dispatcher::onDeviceIndexChanged(const Observed &source)
867 {
868  assert(static_cast<const Value<uint32_t>&>(source).get() == m_deviceIndex);
869  assert(m_initialized);
870 
871  // close the currently open device
872  if (m_deviceOpen)
873  {
874  PROPAGATE_ERROR(m_deviceOpen.set(false));
875 
876  PROPAGATE_ERROR(closeSession());
877 
878  // reset the current device properties
879  }
880 
881  // open the new device
882  const Argus::ICameraProperties *iCameraProperties =
883  Argus::interface_cast<Argus::ICameraProperties>(m_cameraDevices[m_deviceIndex]);
884  if (!iCameraProperties)
885  ORIGINATE_ERROR("Failed to get ICameraProperties interface");
886 
887  // get the sensor modes
888  if (iCameraProperties->getAllSensorModes(&m_sensorModes) != Argus::STATUS_OK)
889  ORIGINATE_ERROR("Failed to get sensor modes");
890 
891  if (m_sensorModes.size() == 0)
892  ORIGINATE_ERROR("No sensor modes found");
893 
894  // get the focus position range
895  PROPAGATE_ERROR(m_deviceFocusPositionRange.set(iCameraProperties->getFocusPositionRange()));
896 
897  // get new limits
898  Argus::Range<float> digitalGainRange = iCameraProperties->getIspDigitalGainRange();
899  Argus::Range<float> deviceExposureCompensationRange =
900  iCameraProperties->getExposureCompensationRange();
901 
902 
903  /* set ranges to unified range (to avoid errors when setting new values)
904  * Eg. Say Device 1 has range [-1,0] and Device 2 has range [1,2] .If current value is -1 and
905  * range is [-1,0] , setting the range to [1,2] would give error . Similarly, if current value
906  * is 1 , setting the range to [-1,0] would give error. Thus we set range to [-1,2] , set value
907  * to 1 and then set range to [1,2] to avoid errors.
908  */
909  Argus::Range<float> unifiedDigitalGainRange(0);
910  unifiedDigitalGainRange.min() =
911  std::min(m_deviceIspDigitalGainRange.get().min().min(), digitalGainRange.min());
912  unifiedDigitalGainRange.max() =
913  std::max(m_deviceIspDigitalGainRange.get().max().max(), digitalGainRange.max());
914 
915  Argus::Range<float> unifiedExposureCompensationRange(0);
916  unifiedExposureCompensationRange.min() =
917  std::min(m_deviceExposureCompensationRange.get().min(),
918  deviceExposureCompensationRange.min());
919  unifiedExposureCompensationRange.max() =
920  std::max(m_deviceExposureCompensationRange.get().max(),
921  deviceExposureCompensationRange.max());
922 
923  PROPAGATE_ERROR(m_deviceIspDigitalGainRange.set(
924  Argus::Range<Argus::Range<float> >(unifiedDigitalGainRange)));
925  PROPAGATE_ERROR(m_deviceExposureCompensationRange.set(
926  Argus::Range<float> (unifiedExposureCompensationRange)));
927 
928  // update dependent values
929  PROPAGATE_ERROR(m_ispDigitalGainRange.set(digitalGainRange));
930  PROPAGATE_ERROR(m_exposureCompensation.set(0.0f));
931 
932  // set to final range
933  PROPAGATE_ERROR(m_deviceIspDigitalGainRange.set(Argus::Range<Argus::Range<float> >(
934  digitalGainRange, digitalGainRange)));
935  PROPAGATE_ERROR(m_deviceExposureCompensationRange.set(Argus::Range<float> (
936  deviceExposureCompensationRange)));
937 
938 
939  // add value/string pairs for each sensor mode index
940  std::vector<ValidatorEnum<uint32_t>::ValueStringPair> valueStringPairs;
941  valueStringPairs.resize(m_sensorModes.size());
942  for (size_t index = 0; index < m_sensorModes.size(); ++index)
943  {
944  Argus::ISensorMode *sensorMode =
945  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[index]);
946 
947  valueStringPairs[index].value = (uint32_t)index;
948 
949  std::ostringstream stream;
950  stream << index << ": "
951  << sensorMode->getResolution().width() << "x" << sensorMode->getResolution().height();
952 
953  Argus::Ext::IPwlWdrSensorMode* pwlMode =
954  Argus::interface_cast<Argus::Ext::IPwlWdrSensorMode>(m_sensorModes[index]);
955 
956  Argus::Ext::IDolWdrSensorMode* dolMode =
957  Argus::interface_cast<Argus::Ext::IDolWdrSensorMode>(m_sensorModes[index]);
958  if (pwlMode)
959  {
960  stream << " @" << sensorMode->getInputBitDepth() << "bpp -> " <<
961  sensorMode->getOutputBitDepth() << "bpp";
962  }
963  else if (dolMode)
964  {
965  stream << " @" << sensorMode->getOutputBitDepth() << "bpp -> " <<
966  dolMode->getExposureCount() << " exposure" << " DOL WDR";
967  }
968  else
969  {
970  stream << " @" << sensorMode->getOutputBitDepth() << "bpp";
971  }
972 
973  valueStringPairs[index].string = stream.str();
974  }
975  // update the validator with the new value/string pairs
976  ValidatorEnum<uint32_t> *validator =
977  static_cast<ValidatorEnum<uint32_t>*>(m_sensorModeIndex.getValidator());
978  PROPAGATE_ERROR(validator->setValidValues(valueStringPairs.data(), valueStringPairs.size()));
979 
980  // set the sensor mode index (force notify observer because the sensor modes are different now
981  // although the sensor mode index could be the same)
982  PROPAGATE_ERROR(m_sensorModeIndex.set(0, true /*forceNotify*/));
983 
984  PROPAGATE_ERROR(m_deviceOpen.set(true));
985 
986  return true;
987 }
988 
989 bool Dispatcher::onSensorModeIndexChanged(const Observed &source)
990 {
991  m_sensorModeValid.set(false);
992  assert(static_cast<const Value<uint32_t>&>(source).get() == m_sensorModeIndex);
993  assert(m_initialized);
994 
995  Argus::ISensorMode *iSensorMode =
996  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[m_sensorModeIndex.get()]);
997  if (!iSensorMode)
998  ORIGINATE_ERROR("Failed to get ISensorMode interface");
999 
1000  // get new limits
1001  Argus::Range<uint64_t> sensorExposureTimeRange = iSensorMode->getExposureTimeRange();
1002  Argus::Range<float> sensorAnalogGainRange = iSensorMode->getAnalogGainRange();
1003  Argus::Range<TimeValue> sensorFrameDurationRange(
1004  TimeValue::fromNSec(iSensorMode->getFrameDurationRange().min()),
1005  TimeValue::fromNSec(iSensorMode->getFrameDurationRange().max()));
1006  Argus::Range<float> sensorFrameRateRange(
1007  sensorFrameDurationRange.max().toCyclesPerSec(),
1008  sensorFrameDurationRange.min().toCyclesPerSec());
1009 
1010  // set ranges to unified range (to avoid errors when setting new values)
1011  Argus::Range<uint64_t> unifiedSensorExposureTimeRange(0);
1012  unifiedSensorExposureTimeRange.min() =
1013  std::min(m_sensorExposureTimeRange.get().min().min(), sensorExposureTimeRange.min());
1014  unifiedSensorExposureTimeRange.max() =
1015  std::max(m_sensorExposureTimeRange.get().max().max(), sensorExposureTimeRange.max());
1016  Argus::Range<float> unifiedSensorAnalogGainRange(0);
1017  unifiedSensorAnalogGainRange.min() =
1018  std::min(m_sensorAnalogGainRange.get().min().min(), sensorAnalogGainRange.min());
1019  unifiedSensorAnalogGainRange.max() =
1020  std::max(m_sensorAnalogGainRange.get().max().max(), sensorAnalogGainRange.max());
1021  Argus::Range<float> unifiedSensorFrameRateRange(0.0f);
1022  unifiedSensorFrameRateRange.min() =
1023  std::min(m_sensorFrameRateRange.get().min(), sensorFrameRateRange.min());
1024  unifiedSensorFrameRateRange.max() =
1025  std::max(m_sensorFrameRateRange.get().max(), sensorFrameRateRange.max());
1026 
1027  PROPAGATE_ERROR(m_sensorExposureTimeRange.set(
1028  Argus::Range<Argus::Range<uint64_t> >(unifiedSensorExposureTimeRange)));
1029  PROPAGATE_ERROR(m_sensorAnalogGainRange.set(
1030  Argus::Range<Argus::Range<float> >(unifiedSensorAnalogGainRange)));
1031  PROPAGATE_ERROR(m_sensorFrameRateRange.set(unifiedSensorFrameRateRange));
1032 
1033  // update dependent values
1034  PROPAGATE_ERROR(m_exposureTimeRange.set(sensorExposureTimeRange));
1035  PROPAGATE_ERROR(m_gainRange.set(sensorAnalogGainRange));
1036  PROPAGATE_ERROR(m_frameRate.set(sensorFrameRateRange.max()));
1037 
1038  // set to final ranges
1039  PROPAGATE_ERROR(m_sensorExposureTimeRange.set(Argus::Range<Argus::Range<uint64_t> >(
1040  sensorExposureTimeRange, sensorExposureTimeRange)));
1041  PROPAGATE_ERROR(m_sensorAnalogGainRange.set(Argus::Range<Argus::Range<float> >(
1042  sensorAnalogGainRange, sensorAnalogGainRange)));
1043  PROPAGATE_ERROR(m_sensorFrameRateRange.set(sensorFrameRateRange));
1044  m_sensorModeValid.set(true);
1045 
1046  return true;
1047 }
1048 
1049 bool Dispatcher::supportsExtension(const Argus::ExtensionName& extension) const
1050 {
1051  return m_iCameraProvider->supportsExtension(extension);
1052 }
1053 
1054 bool Dispatcher::getInfo(std::string &info) const
1055 {
1056  std::ostringstream stream;
1057 
1058  assert(m_initialized);
1059 
1060  stream << "Argus extensions:" << std::endl;
1061  stream << " BayerSharpnessMap: " <<
1062  (supportsExtension(Argus::EXT_BAYER_SHARPNESS_MAP) ?
1063  "supported" : "not supported") << std::endl;
1064  stream << " DebugCaptureSession: " <<
1065  (supportsExtension(Argus::EXT_DEBUG_CAPTURE_SESSION) ?
1066  "supported" : "not supported") << std::endl;
1067  stream << " DeFog: " <<
1068  (supportsExtension(Argus::EXT_DE_FOG) ?
1069  "supported" : "not supported") << std::endl;
1070  stream << " FaceDetect: " <<
1071  (supportsExtension(Argus::EXT_FACE_DETECT) ?
1072  "supported" : "not supported") << std::endl;
1073  stream << " InternalFrameCount: " <<
1074  (supportsExtension(Argus::EXT_INTERNAL_FRAME_COUNT) ?
1075  "supported" : "not supported") << std::endl;
1076  stream << " SensorPrivateMetadata: " <<
1077  (supportsExtension(Argus::EXT_SENSOR_PRIVATE_METADATA) ?
1078  "supported" : "not supported") << std::endl;
1079 
1080  stream << "Number of camera devices: " << m_cameraDevices.size() << std::endl;
1081 
1082  for (uint32_t deviceIndex = 0; deviceIndex < m_cameraDevices.size(); ++deviceIndex)
1083  {
1084  stream << "Device: " << deviceIndex << std::endl;
1085 
1086  const Argus::ICameraProperties *iCameraProperties =
1087  Argus::interface_cast<Argus::ICameraProperties>(m_cameraDevices[deviceIndex]);
1088  if (!iCameraProperties)
1089  ORIGINATE_ERROR("Failed to get ICameraProperties interface");
1090 
1091  stream << " Max AE Regions: " <<
1092  iCameraProperties->getMaxAeRegions() << std::endl;
1093  stream << " Max AWB Regions: " <<
1094  iCameraProperties->getMaxAwbRegions() << std::endl;
1095  stream << " Focus Position Range: " <<
1096  iCameraProperties->getFocusPositionRange().min() << " - " <<
1097  iCameraProperties->getFocusPositionRange().max() << std::endl;
1098  stream << " Lens Aperture Range: " <<
1099  iCameraProperties->getLensApertureRange().min() << " - " <<
1100  iCameraProperties->getLensApertureRange().max() << std::endl;
1101  stream << " Isp Digital Gain Range: " <<
1102  iCameraProperties->getIspDigitalGainRange().min() << " - " <<
1103  iCameraProperties->getIspDigitalGainRange().max() << std::endl;
1104 
1105  // print the sensor modes
1106  std::vector<Argus::SensorMode*> sensorModes;
1107  iCameraProperties->getAllSensorModes(&sensorModes);
1108  stream << " Number of sensor modes: " << sensorModes.size() << std::endl;
1109  for (uint32_t sensorModeIndex = 0; sensorModeIndex < sensorModes.size(); ++sensorModeIndex)
1110  {
1111  Argus::ISensorMode *sensorMode =
1112  Argus::interface_cast<Argus::ISensorMode>(sensorModes[sensorModeIndex]);
1113  if (!sensorMode)
1114  ORIGINATE_ERROR("Failed to get ISensorMode interface");
1115 
1116  // convert ns to fps
1117  float maximum_fps = TimeValue::fromNSec(
1118  sensorMode->getFrameDurationRange().min()).toCyclesPerSec();
1119  float minimum_fps = TimeValue::fromNSec(
1120  sensorMode->getFrameDurationRange().max()).toCyclesPerSec();
1121 
1122  stream << " Sensor mode: " << sensorModeIndex << std::endl;
1123  stream << " Resolution: " <<
1124  sensorMode->getResolution().width() << "x" <<
1125  sensorMode->getResolution().height() << std::endl;
1126  stream << " Exposure time range: " <<
1127  sensorMode->getExposureTimeRange().min() << " - " <<
1128  sensorMode->getExposureTimeRange().max() << " ns" << std::endl;
1129  stream << " Frame duration range: " <<
1130  sensorMode->getFrameDurationRange().min() << " - " <<
1131  sensorMode->getFrameDurationRange().max() << " ns" << std::endl;
1132  stream << " Framerate range: " <<
1133  minimum_fps << " - " <<
1134  maximum_fps << " fps" << std::endl;
1135  stream << " InputBitDepth: " <<
1136  sensorMode->getInputBitDepth() << std::endl;
1137  stream << " OutputBitDepth: " <<
1138  sensorMode->getOutputBitDepth() << std::endl;
1139  stream << " Analog gain range: " <<
1140  sensorMode->getAnalogGainRange().min() << " - " <<
1141  sensorMode->getAnalogGainRange().max() << std::endl;
1142 
1143  stream << " SensorModeType: " <<
1144  sensorMode->getSensorModeType().getName() << std::endl;
1145 
1146  Argus::Ext::IPwlWdrSensorMode* pwlMode =
1147  Argus::interface_cast<Argus::Ext::IPwlWdrSensorMode>(sensorModes[sensorModeIndex]);
1148 
1149  Argus::Ext::IDolWdrSensorMode* dolMode =
1150  Argus::interface_cast<Argus::Ext::IDolWdrSensorMode>(sensorModes[sensorModeIndex]);
1151 
1152  if (pwlMode)
1153  {
1154  stream << " Piecewise Linear (PWL) WDR Extension supported with: " <<
1155  pwlMode->getControlPointCount() << " control points." << std::endl;
1156  std::vector< Argus::Point2D<float> > points;
1157  Argus::Status status = pwlMode->getControlPoints(&points);
1158  if (status != Argus::STATUS_OK)
1159  ORIGINATE_ERROR("Error obtaining control points");
1160  stream << " - Control Points: " << std::endl;
1161  for (uint32_t j = 0; j < pwlMode->getControlPointCount(); j++)
1162  {
1163  stream << " (" << points[j].x() << ", " <<
1164  points[j].y() << ")" << std::endl;
1165  }
1166  }
1167  else if (dolMode)
1168  {
1169  stream << " Digital Overlap (DOL) WDR Extension supported with: " << std::endl <<
1170  " - Number of Exposures: " <<
1171  dolMode->getExposureCount() << std::endl <<
1172  " - Number of Optical Black Lines per exposure: " <<
1173  dolMode->getOpticalBlackRowCount() << std::endl <<
1174  " - Number of Line Info marker pixels per row per exposure: " <<
1175  dolMode->getLineInfoMarkerWidth() << std::endl <<
1176  " - Number of margin pixels on left per row per exposure: " <<
1177  dolMode->getLeftMarginWidth() << std::endl <<
1178  " - Number of margin pixels on right per row per exposure: " <<
1179  dolMode->getRightMarginWidth() << std::endl;
1180 
1181  std::vector<u_int32_t> verticalBlankPeriodRowCounts;
1182  Argus::Status status =
1183  dolMode->getVerticalBlankPeriodRowCount(&verticalBlankPeriodRowCounts);
1184  if (status != Argus::STATUS_OK)
1185  ORIGINATE_ERROR("Error obtaining vertical blank period offsets per exposure");
1186  stream << " - Vertical blank period section row counts per exposure: "
1187  << std::endl;
1188  for (uint32_t j = 0; j < verticalBlankPeriodRowCounts.size(); j++)
1189  {
1190  stream << " - VBP-section[" << j << "] : "
1191  << verticalBlankPeriodRowCounts[j] << std::endl;
1192  }
1193 
1194  stream << " - Physical Resolution: " <<
1195  dolMode->getPhysicalResolution().width() << "x" <<
1196  dolMode->getPhysicalResolution().height() << std::endl;
1197  }
1198 
1199  stream << std::endl;
1200  }
1201  }
1202 
1203  info = stream.str();
1204 
1205  return true;
1206 }
1207 
1208 bool Dispatcher::getSensorMode(uint32_t sensorModeIndex, Argus::SensorMode **sensorMode) const
1209 {
1210  assert(m_deviceOpen);
1211 
1212  if (sensorModeIndex >= m_sensorModes.size())
1213  ORIGINATE_ERROR("Invalid sensor mode index");
1214 
1215  *sensorMode = m_sensorModes[sensorModeIndex];
1216 
1217  return true;
1218 }
1219 
1220 Argus::Range<int32_t> Dispatcher::getDeviceFocusPositionRange() const
1221 {
1222  return m_deviceFocusPositionRange.get();
1223 }
1224 
1226 {
1227  assert(m_deviceOpen);
1228 
1229  return m_cameraDevices.size();
1230 }
1231 
1233  uint32_t deviceIndex)
1234 {
1235  assert(m_deviceOpen);
1236 
1237  if (deviceIndex > m_cameraDevices.size())
1238  ORIGINATE_ERROR("Invalid device index");
1239 
1240  // close the internal session, it might be using the device which will be used by the new
1241  // session
1242  PROPAGATE_ERROR(closeSession());
1243 
1244  // create the new capture session
1245  Argus::UniqueObj<Argus::CaptureSession> newSession(
1246  m_iCameraProvider->createCaptureSession(m_cameraDevices[deviceIndex]));
1247  if (!newSession)
1248  ORIGINATE_ERROR("Failed to create CaptureSession");
1249 
1250  PROPAGATE_ERROR(session.reset(newSession.release(), this));
1251 
1252  return true;
1253 }
1254 
1256 {
1257  for (ActiveSessionList::const_iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1258  ++it)
1259  {
1260  Argus::Ext::IDebugCaptureSession *iDebugCaptureSession =
1261  Argus::interface_cast<Argus::Ext::IDebugCaptureSession>(it->m_session);
1262  if (!iDebugCaptureSession)
1263  ORIGINATE_ERROR("DebugCaptureSession extension not supported");
1264 
1265  const Argus::Status status = iDebugCaptureSession->dump(STDOUT_FILENO);
1266  if (status != Argus::STATUS_OK)
1267  ORIGINATE_ERROR("Failed to get dump runtime info");
1268  }
1269 
1270  return true;
1271 }
1272 
1273 /**
1274  * Create the internal session
1275  */
1277 {
1278  if (m_captureSession)
1279  return true;
1280 
1281  PROPAGATE_ERROR(createSession(m_captureSession, m_deviceIndex));
1282 
1283  return true;
1284 }
1285 
1286 /**
1287  * Close the internal session
1288  */
1290 {
1292  return true;
1293 }
1294 
1295 bool Dispatcher::track(Argus::CaptureSession *session)
1296 {
1297  m_activeSessions.push_back(ActiveSession(session));
1298  return true;
1299 }
1300 
1301 bool Dispatcher::untrack(Argus::CaptureSession *session)
1302 {
1303  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1304  ++it)
1305  {
1306  if (it->m_session == session)
1307  {
1308  m_activeSessions.erase(it);
1309  return true;
1310  }
1311  }
1312 
1313  ORIGINATE_ERROR("Session not found");
1314 }
1315 
1316 bool Dispatcher::waitForEvents(Argus::EventQueue *eventQueue, TimeValue timeout,
1317  Argus::CaptureSession *session)
1318 {
1319  if (!session)
1320  {
1321  // use the internal session
1322  PROPAGATE_ERROR(createSession());
1323  session = m_captureSession.get();
1324  }
1325 
1326  Argus::IEventProvider *iEventProvider = Argus::interface_cast<Argus::IEventProvider>(session);
1327  if (!iEventProvider)
1328  ORIGINATE_ERROR("Failed to get iEventProvider interface");
1329 
1330  // wait for the events
1331  const Argus::Status status = iEventProvider->waitForEvents(eventQueue, timeout.toNSec());
1332  if ((status != Argus::STATUS_OK) && (status != Argus::STATUS_TIMEOUT))
1333  ORIGINATE_ERROR("Failed to get events");
1334 
1335  return true;
1336 }
1337 
1339  Argus::CaptureIntent captureIntent, Argus::CaptureSession *session)
1340 {
1341  if (!session)
1342  {
1343  // use the internal session
1344  PROPAGATE_ERROR(createSession());
1345  session = m_captureSession.get();
1346  }
1347 
1348  Argus::ICaptureSession *iCaptureSession =
1349  Argus::interface_cast<Argus::ICaptureSession>(session);
1350  if (!iCaptureSession)
1351  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1352 
1353  // Create request
1354  Argus::UniqueObj<Argus::Request> newRequest =
1355  Argus::UniqueObj<Argus::Request>(iCaptureSession->createRequest(captureIntent));
1356  if (!newRequest)
1357  ORIGINATE_ERROR("Failed to create request");
1358 
1359  // Setup request
1360  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(newRequest);
1361  if (!iRequest)
1362  ORIGINATE_ERROR("Failed to get IRequest interface");
1363 
1364  // get source settings interface
1365  Argus::ISourceSettings *iSourceSettings =
1366  Argus::interface_cast<Argus::ISourceSettings>(iRequest->getSourceSettings());
1367  if (!iSourceSettings)
1368  ORIGINATE_ERROR("Failed to get ISourceSettings interface");
1369 
1370  // register the source settings observer
1371  PROPAGATE_ERROR(registerObserver(iSourceSettings));
1372 
1373  // get auto control settings interface
1374  Argus::IAutoControlSettings *iAutoControlSettings =
1375  Argus::interface_cast<Argus::IAutoControlSettings>(iRequest->getAutoControlSettings());
1376  if (!iAutoControlSettings)
1377  ORIGINATE_ERROR("Failed to get IAutoControlSettings interface");
1378 
1379  // register the auto control settings observer
1380  PROPAGATE_ERROR(registerObserver(iAutoControlSettings));
1381 
1382  // register denoise settings interface
1383  Argus::IDenoiseSettings *iDenoiseSettings =
1384  Argus::interface_cast<Argus::IDenoiseSettings>(newRequest);
1385  if (!iDenoiseSettings)
1386  ORIGINATE_ERROR("Failed to get IDenoiseSettings interface");
1387  PROPAGATE_ERROR(registerObserver(iDenoiseSettings));
1388 
1389  // register edge enhance settings interface
1390  Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings =
1391  Argus::interface_cast<Argus::IEdgeEnhanceSettings>(newRequest);
1392  if (!iEdgeEnhanceSettings)
1393  ORIGINATE_ERROR("Failed to get IEdgeEnhanceSettings interface");
1394  PROPAGATE_ERROR(registerObserver(iEdgeEnhanceSettings));
1395 
1396  if (supportsExtension(Argus::EXT_DE_FOG))
1397  {
1398  // get DeFog settings interface
1399  Argus::Ext::IDeFogSettings *iDeFogSettings =
1400  Argus::interface_cast<Argus::Ext::IDeFogSettings>(newRequest);
1401  if (iDeFogSettings)
1402  {
1403  // register the DeFog settings observer
1404  PROPAGATE_ERROR(registerObserver(iDeFogSettings));
1405  }
1406  }
1407 
1408  PROPAGATE_ERROR(request.reset(newRequest.release(), this));
1409 
1410  return true;
1411 }
1412 
1413 bool Dispatcher::track(Argus::Request *request)
1414 {
1415  return true;
1416 }
1417 
1418 bool Dispatcher::untrack(Argus::Request *request)
1419 {
1420  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1421  if (!iRequest)
1422  ORIGINATE_ERROR("Failed to get IRequest interface");
1423 
1424  // get source settings interface
1425  Argus::ISourceSettings *iSourceSettings =
1426  Argus::interface_cast<Argus::ISourceSettings>(iRequest->getSourceSettings());
1427  if (!iSourceSettings)
1428  ORIGINATE_ERROR("Failed to get ISourceSettings interface");
1429 
1430  // unregister the source settings observer
1431  PROPAGATE_ERROR(unregisterObserver(iSourceSettings));
1432 
1433  // get auto control settings interface
1434  Argus::IAutoControlSettings *iAutoControlSettings =
1435  Argus::interface_cast<Argus::IAutoControlSettings>(iRequest->getAutoControlSettings());
1436  if (!iAutoControlSettings)
1437  ORIGINATE_ERROR("Failed to get IAutoControlSettings interface");
1438 
1439  // unregister the auto control settings observer
1440  PROPAGATE_ERROR(unregisterObserver(iAutoControlSettings));
1441 
1442  // unregister denoise settings interface
1443  Argus::IDenoiseSettings *iDenoiseSettings =
1444  Argus::interface_cast<Argus::IDenoiseSettings>(request);
1445  if (!iDenoiseSettings)
1446  ORIGINATE_ERROR("Failed to get IDenoiseSettings interface");
1447  PROPAGATE_ERROR(unregisterObserver(iDenoiseSettings));
1448 
1449  // unregister edge enhance settings interface
1450  Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings =
1451  Argus::interface_cast<Argus::IEdgeEnhanceSettings>(request);
1452  if (!iEdgeEnhanceSettings)
1453  ORIGINATE_ERROR("Failed to get IEdgeEnhanceSettings interface");
1454  PROPAGATE_ERROR(unregisterObserver(iEdgeEnhanceSettings));
1455 
1456  if (supportsExtension(Argus::EXT_DE_FOG))
1457  {
1458  // get DeFog settings interface
1459  Argus::Ext::IDeFogSettings *iDeFogSettings =
1460  Argus::interface_cast<Argus::Ext::IDeFogSettings>(request);
1461  if (iDeFogSettings)
1462  {
1463  // unregister the DeFog settings observer
1464  PROPAGATE_ERROR(unregisterObserver(iDeFogSettings));
1465  }
1466  }
1467 
1468  return true;
1469 }
1470 
1471 bool Dispatcher::createEventQueue(const std::vector<Argus::EventType> &eventTypes,
1472  Argus::UniqueObj<Argus::EventQueue>& eventQueue, Argus::CaptureSession *session)
1473 {
1474  if (!session)
1475  {
1476  // use the internal session
1477  PROPAGATE_ERROR(createSession());
1478  session = m_captureSession.get();
1479  }
1480 
1481  Argus::IEventProvider *iEventProvider =
1482  Argus::interface_cast<Argus::IEventProvider>(session);
1483  if (!iEventProvider)
1484  ORIGINATE_ERROR("Failed to get IEventProvider interface");
1485 
1486  Argus::EventQueue *newEventQueue = iEventProvider->createEventQueue(eventTypes);
1487  if (!newEventQueue)
1488  ORIGINATE_ERROR("Failed to create eventQueue");
1489 
1490  eventQueue.reset(newEventQueue);
1491 
1492  return true;
1493 }
1494 
1495 bool Dispatcher::capture(Argus::Request *request, Argus::CaptureSession *session)
1496 {
1497  if (!session)
1498  {
1499  // use the internal session
1500  PROPAGATE_ERROR(createSession());
1501  session = m_captureSession.get();
1502  }
1503 
1504  Argus::ICaptureSession *iCaptureSession =
1505  Argus::interface_cast<Argus::ICaptureSession>(session);
1506  if (!iCaptureSession)
1507  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1508 
1509  if (iCaptureSession->capture(request, Argus::TIMEOUT_INFINITE) == 0)
1510  ORIGINATE_ERROR("Failed to submit the still capture request");
1511 
1512  return true;
1513 }
1514 
1515 bool Dispatcher::startRepeat(Argus::Request *request, Argus::CaptureSession *session)
1516 {
1517  if (!session)
1518  {
1519  // use the internal session
1520  PROPAGATE_ERROR(createSession());
1521  session = m_captureSession.get();
1522  }
1523 
1524  Argus::ICaptureSession *iCaptureSession =
1525  Argus::interface_cast<Argus::ICaptureSession>(session);
1526  if (!iCaptureSession)
1527  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1528 
1529  if (iCaptureSession->repeat(request) != Argus::STATUS_OK)
1530  ORIGINATE_ERROR("Failed to submit repeating capture request");
1531 
1532  // add the request to the list of active requests for the session
1533  bool found = false;
1534  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1535  ++it)
1536  {
1537  if (it->m_session == session)
1538  {
1539  it->m_requests.push_back(request);
1540  found = true;
1541  break;
1542  }
1543  }
1544  if (!found)
1545  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1546 
1547  return true;
1548 }
1549 
1550 bool Dispatcher::startRepeatBurst(const std::vector<const Argus::Request*>& requestList,
1551  Argus::CaptureSession *session)
1552 {
1553  if (!session)
1554  {
1555  // use the internal session
1556  PROPAGATE_ERROR(createSession());
1557  session = m_captureSession.get();
1558  }
1559 
1560  Argus::ICaptureSession *iCaptureSession =
1561  Argus::interface_cast<Argus::ICaptureSession>(session);
1562  if (!iCaptureSession)
1563  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1564 
1565  if (iCaptureSession->repeatBurst(requestList) != Argus::STATUS_OK)
1566  ORIGINATE_ERROR("Failed to submit repeating burst request");
1567 
1568  // add the requests to the list of active requests for the session
1569  bool found = false;
1570  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1571  ++it)
1572  {
1573  if (it->m_session == session)
1574  {
1575  it->m_requests.insert(it->m_requests.end(), requestList.begin(), requestList.end());
1576  found = true;
1577  break;
1578  }
1579  }
1580  if (!found)
1581  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1582 
1583  return true;
1584 }
1585 
1586 bool Dispatcher::stopRepeat(Argus::CaptureSession *session)
1587 {
1588  if (!session)
1589  {
1590  // use the internal session
1591  PROPAGATE_ERROR(createSession());
1592  session = m_captureSession.get();
1593  }
1594 
1595  Argus::ICaptureSession *iCaptureSession =
1596  Argus::interface_cast<Argus::ICaptureSession>(session);
1597  if (!iCaptureSession)
1598  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1599 
1600  iCaptureSession->stopRepeat();
1601 
1602  // clear the list of active requests for the session
1603  bool found = false;
1604  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1605  ++it)
1606  {
1607  if (it->m_session == session)
1608  {
1609  it->m_requests.clear();
1610  found = true;
1611  break;
1612  }
1613  }
1614  if (!found)
1615  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1616 
1617  return true;
1618 }
1619 
1621 {
1622  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1623  ++it)
1624  {
1625  if (!it->m_requests.empty())
1626  {
1627  Argus::ICaptureSession *iCaptureSession =
1628  Argus::interface_cast<Argus::ICaptureSession>(it->m_session);
1629  if (!iCaptureSession)
1630  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1631 
1632  iCaptureSession->stopRepeat();
1633 
1634  if (iCaptureSession->repeatBurst(it->m_requests) != Argus::STATUS_OK)
1635  ORIGINATE_ERROR("Failed to submit repeating burst request");
1636  }
1637  }
1638 
1639  return true;
1640 }
1641 
1642 uint32_t Dispatcher::maxBurstRequests(Argus::CaptureSession *session)
1643 {
1644  if (!session)
1645  {
1646  // use the internal session
1647  PROPAGATE_ERROR(createSession());
1648  session = m_captureSession.get();
1649  }
1650 
1651  Argus::ICaptureSession *iCaptureSession =
1652  Argus::interface_cast<Argus::ICaptureSession>(session);
1653  if (!iCaptureSession)
1654  {
1655  REPORT_ERROR("Failed to get ICaptureSession interface");
1656  return 0;
1657  }
1658 
1659  return iCaptureSession->maxBurstRequests();
1660 }
1661 
1662 bool Dispatcher::waitForIdle(Argus::CaptureSession *session)
1663 {
1664  if (!session)
1665  {
1666  // use the internal session
1667  PROPAGATE_ERROR(createSession());
1668  session = m_captureSession.get();
1669  }
1670 
1671  Argus::ICaptureSession *iCaptureSession =
1672  Argus::interface_cast<Argus::ICaptureSession>(session);
1673  if (!iCaptureSession)
1674  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1675 
1676  if (iCaptureSession->waitForIdle() != Argus::STATUS_OK)
1677  ORIGINATE_ERROR("Waiting for idle failed");
1678 
1679  return true;
1680 }
1681 
1682 bool Dispatcher::getOutputSize(Argus::Size2D<uint32_t> *size) const
1683 {
1684  // if width or height is 0 take the sensor size
1685  if ((m_outputSize.get().width() == 0) || (m_outputSize.get().height() == 0))
1686  {
1687  // the device needs to be open to get sensor modes
1688  assert(m_deviceOpen);
1689 
1690  Argus::ISensorMode *sensorMode =
1691  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[m_sensorModeIndex.get()]);
1692  if (!sensorMode)
1693  ORIGINATE_ERROR("Failed to get ISensorMode interface");
1694  *size = sensorMode->getResolution();
1695  }
1696  else
1697  {
1698  *size = m_outputSize;
1699  }
1700 
1701  return true;
1702 }
1703 
1704 bool Dispatcher::createOutputStream(Argus::Request *request, bool enableMetadata,
1705  Argus::UniqueObj<Argus::OutputStream> &stream, Argus::CaptureSession *session)
1706 {
1707  if (!session)
1708  {
1709  // use the internal session
1710  PROPAGATE_ERROR(createSession());
1711  session = m_captureSession.get();
1712  }
1713 
1714  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1715  if (!iRequest)
1716  ORIGINATE_ERROR("Failed to get IRequest interface");
1717 
1718  Argus::Size2D<uint32_t> outputSize;
1719  PROPAGATE_ERROR(getOutputSize(&outputSize));
1720 
1721  Argus::ICaptureSession *iCaptureSession =
1722  Argus::interface_cast<Argus::ICaptureSession>(session);
1723  if (!iCaptureSession)
1724  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1725 
1726  Argus::UniqueObj<Argus::OutputStreamSettings> outputStreamSettings(
1727  iCaptureSession->createOutputStreamSettings(Argus::STREAM_TYPE_EGL));
1728  Argus::IEGLOutputStreamSettings* iEGLOutputStreamSettings =
1729  Argus::interface_cast<Argus::IEGLOutputStreamSettings>(outputStreamSettings);
1730  if (!iEGLOutputStreamSettings)
1731  ORIGINATE_ERROR("Failed to get IEGLOutputStreamSettings interface");
1732 
1733  iEGLOutputStreamSettings->setPixelFormat(m_captureYuvFormat.get());
1734  iEGLOutputStreamSettings->setResolution(outputSize);
1735  iEGLOutputStreamSettings->setEGLDisplay(Composer::getInstance().getEGLDisplay());
1736  iEGLOutputStreamSettings->setMetadataEnable(enableMetadata);
1737 
1738  Argus::UniqueObj<Argus::OutputStream> outputStream(
1739  iCaptureSession->createOutputStream(outputStreamSettings.get()));
1740  if (!outputStream)
1741  ORIGINATE_ERROR("Failed to create OutputStream");
1742 
1743  stream.reset(outputStream.release());
1744 
1745  return true;
1746 }
1747 
1748 bool Dispatcher::enableOutputStream(Argus::Request *request, Argus::OutputStream *stream)
1749 {
1750  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1751  if (!iRequest)
1752  ORIGINATE_ERROR("Failed to get IRequest interface");
1753 
1754  // Enable the stream
1755  if (iRequest->enableOutputStream(stream) != Argus::STATUS_OK)
1756  ORIGINATE_ERROR("Failed to enable the output stream");
1757 
1758  return true;
1759 }
1760 
1761 bool Dispatcher::disableOutputStream(Argus::Request *request, Argus::OutputStream *stream)
1762 {
1763  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1764  if (!iRequest)
1765  ORIGINATE_ERROR("Failed to get IRequest interface");
1766 
1767  // Disable the stream
1768  if (iRequest->disableOutputStream(stream) != Argus::STATUS_OK)
1769  ORIGINATE_ERROR("Failed to disable the output stream");
1770 
1771  return true;
1772 }
1773 
1774 bool Dispatcher::registerObserver(Argus::IDenoiseSettings *iDenoiseSettings)
1775 {
1776  UniquePointer<DenoiseSettingsObserver> denoiseSettings;
1777 
1778  denoiseSettings.reset(new DenoiseSettingsObserver(iDenoiseSettings));
1779  if (!denoiseSettings)
1780  ORIGINATE_ERROR("Out of memory");
1781 
1782  m_observers.push_front(denoiseSettings.release());
1783  return true;
1784 }
1785 
1786 bool Dispatcher::registerObserver(Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings)
1787 {
1788  UniquePointer<EdgeEnhanceSettingsObserver> edgeEnhanceSettings;
1789 
1790  edgeEnhanceSettings.reset(new EdgeEnhanceSettingsObserver(iEdgeEnhanceSettings));
1791  if (!edgeEnhanceSettings)
1792  ORIGINATE_ERROR("Out of memory");
1793 
1794  m_observers.push_front(edgeEnhanceSettings.release());
1795  return true;
1796 }
1797 
1798 bool Dispatcher::registerObserver(Argus::ISourceSettings *iSourceSettings)
1799 {
1800  UniquePointer<SourceSettingsObserver> sourceSettings;
1801 
1802  sourceSettings.reset(new SourceSettingsObserver(iSourceSettings));
1803  if (!sourceSettings)
1804  ORIGINATE_ERROR("Out of memory");
1805 
1806  m_observers.push_front(sourceSettings.release());
1807  return true;
1808 }
1809 
1810 bool Dispatcher::registerObserver(Argus::IAutoControlSettings *iAutoControlSettings)
1811 {
1812  UniquePointer<AutoControlSettingsObserver> autoControlSettings;
1813 
1814  autoControlSettings.reset(new AutoControlSettingsObserver(iAutoControlSettings));
1815  if (!autoControlSettings)
1816  ORIGINATE_ERROR("Out of memory");
1817 
1818  m_observers.push_front(autoControlSettings.release());
1819  return true;
1820 }
1821 
1822 bool Dispatcher::registerObserver(Argus::Ext::IDeFogSettings *iDeFogSettings)
1823 {
1824  UniquePointer<DeFogSettingsObserver> deFogSettings;
1825 
1826  deFogSettings.reset(new DeFogSettingsObserver(iDeFogSettings));
1827  if (!deFogSettings)
1828  ORIGINATE_ERROR("Out of memory");
1829 
1830  m_observers.push_front(deFogSettings.release());
1831  return true;
1832 }
1833 
1834 bool Dispatcher::unregisterObserver(Argus::Interface *interface)
1835 {
1836  for (std::list<IObserverForInterface*>::iterator it = m_observers.begin();
1837  it != m_observers.end(); ++it)
1838  {
1839  if ((*it)->isInterface(interface))
1840  {
1841  delete *it;
1842  m_observers.erase(it);
1843  return true;
1844  }
1845  }
1846 
1847  ORIGINATE_ERROR("Observer not found");
1848 }
1849 
1850 bool Dispatcher::message(const char *msg, ...)
1851 {
1852  if (m_verbose)
1853  {
1854  va_list list;
1855 
1856  va_start(list, msg);
1857 
1858  if (vprintf(msg, list) < 0)
1859  {
1860  va_end(list);
1861  ORIGINATE_ERROR("Failed to print message");
1862  }
1863 
1864  va_end(list);
1865  }
1866 
1867  return true;
1868 }
1869 
1870 }; // namespace ArgusSamples