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-2019, 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_aperturePosition.registerObserver(this,
246  static_cast<IObserver::CallbackFunction>(
248  PROPAGATE_ERROR_CONTINUE(dispatcher.m_apertureFnum.registerObserver(this,
249  static_cast<IObserver::CallbackFunction>(
251  PROPAGATE_ERROR_CONTINUE(dispatcher.m_apertureMotorSpeed.registerObserver(this,
252  static_cast<IObserver::CallbackFunction>(
254  PROPAGATE_ERROR_CONTINUE(dispatcher.m_captureYuvFormat.registerObserver(this,
255  static_cast<IObserver::CallbackFunction>(
257  }
258 
260  {
261  Dispatcher &dispatcher = Dispatcher::getInstance();
262 
263  PROPAGATE_ERROR_CONTINUE(dispatcher.m_apertureMotorSpeed.unregisterObserver(this,
264  static_cast<IObserver::CallbackFunction>(
266  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aperturePosition.unregisterObserver(this,
267  static_cast<IObserver::CallbackFunction>(
269  PROPAGATE_ERROR_CONTINUE(dispatcher.m_apertureFnum.unregisterObserver(this,
270  static_cast<IObserver::CallbackFunction>(
272  PROPAGATE_ERROR_CONTINUE(dispatcher.m_focusPosition.unregisterObserver(this,
273  static_cast<IObserver::CallbackFunction>(
275  PROPAGATE_ERROR_CONTINUE(dispatcher.m_frameRate.unregisterObserver(this,
276  static_cast<IObserver::CallbackFunction>(
278  PROPAGATE_ERROR_CONTINUE(dispatcher.m_sensorModeIndex.unregisterObserver(this,
279  static_cast<IObserver::CallbackFunction>(
281  PROPAGATE_ERROR_CONTINUE(dispatcher.m_gainRange.unregisterObserver(this,
282  static_cast<IObserver::CallbackFunction>(
284  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureTimeRange.unregisterObserver(this,
285  static_cast<IObserver::CallbackFunction>(
287  PROPAGATE_ERROR_CONTINUE(dispatcher.m_captureYuvFormat.unregisterObserver(this,
288  static_cast<IObserver::CallbackFunction>(
290  }
291 
292  virtual bool isInterface(Argus::Interface *interface) const
293  {
294  return (interface == m_iSourceSettings);
295  }
296 
297 private:
298  bool onExposureTimeRangeChanged(const Observed &source)
299  {
300  Dispatcher &dispatcher = Dispatcher::getInstance();
301 
302  assert(&source == &dispatcher.m_exposureTimeRange);
303 
304  if (m_iSourceSettings->setExposureTimeRange(dispatcher.m_exposureTimeRange.get()) !=
305  Argus::STATUS_OK)
306  {
307  ORIGINATE_ERROR("Failed to set exposure time range");
308  }
309 
310  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
311 
312  return true;
313  }
314 
315  bool onGainRangeChanged(const Observed &source)
316  {
317  Dispatcher &dispatcher = Dispatcher::getInstance();
318 
319  assert(&source == &dispatcher.m_gainRange);
320 
321  if (m_iSourceSettings->setGainRange(dispatcher.m_gainRange.get()) != Argus::STATUS_OK)
322  ORIGINATE_ERROR("Failed to set gain range");
323 
324  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
325 
326  return true;
327  }
328 
329  bool onSensorModeChanged(const Observed &source)
330  {
331  Dispatcher &dispatcher = Dispatcher::getInstance();
332 
333  assert(&source == &dispatcher.m_sensorModeIndex);
334 
335  Argus::SensorMode *sensorMode = NULL;
336  PROPAGATE_ERROR(dispatcher.getSensorMode(dispatcher.m_sensorModeIndex.get(), &sensorMode));
337 
338  if (m_iSourceSettings->setSensorMode(sensorMode) != Argus::STATUS_OK)
339  ORIGINATE_ERROR("Failed to set sensor mode");
340 
341  PROPAGATE_ERROR(dispatcher.restartActiveRequests());
342 
343  return true;
344  }
345 
346  bool onCaptureYuvFormatChanged(const Observed & source)
347  {
348  Dispatcher &dispatcher = Dispatcher::getInstance();
349 
350  assert(&source == &dispatcher.m_captureYuvFormat);
351 
352  // The Video/Still task will shut down and restart their
353  // EGLStreams, causing their underlying buffer pools to be reallocated.
354  // So there's not much else to do here.
355  PROPAGATE_ERROR(dispatcher.restartActiveRequests());
356 
357  return true;
358  }
359 
360  bool onFocusPositionChanged(const Observed &source)
361  {
362  Dispatcher &dispatcher = Dispatcher::getInstance();
363 
364  assert(&source == &dispatcher.m_focusPosition);
365 
366  if (m_iSourceSettings->setFocusPosition(dispatcher.m_focusPosition.get()) !=
367  Argus::STATUS_OK)
368  {
369  ORIGINATE_ERROR("Failed to set focus position");
370  }
371 
372  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
373 
374  return true;
375  }
376 
377  bool onAperturePositionChanged(const Observed &source)
378  {
379  Dispatcher &dispatcher = Dispatcher::getInstance();
380 
381  assert(&source == &dispatcher.m_aperturePosition);
382 
383  if (m_iSourceSettings->setAperturePosition(dispatcher.m_aperturePosition.get()) !=
384  Argus::STATUS_OK)
385  {
386  ORIGINATE_ERROR("Failed to set aperture motor step");
387  }
388 
389  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
390 
391  return true;
392  }
393 
394  bool onApertureFnumChanged(const Observed &source)
395  {
396  Dispatcher &dispatcher = Dispatcher::getInstance();
397 
398  assert(&source == &dispatcher.m_apertureFnum);
399 
400  if (m_iSourceSettings->setApertureFNumber(dispatcher.m_apertureFnum.get()) !=
401  Argus::STATUS_OK)
402  {
403  ORIGINATE_ERROR("Failed to set aperture F-num");
404  }
405 
406  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
407 
408  return true;
409  }
410 
411  bool onApertureMotorSpeedChanged(const Observed &source)
412  {
413  Dispatcher &dispatcher = Dispatcher::getInstance();
414 
415  assert(&source == &dispatcher.m_apertureMotorSpeed);
416 
417  if (m_iSourceSettings->setApertureMotorSpeed(dispatcher.m_apertureMotorSpeed.get()) !=
418  Argus::STATUS_OK)
419  {
420  ORIGINATE_ERROR("Failed to set aperture motor speed");
421  }
422 
423  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
424 
425  return true;
426  }
427 
428  bool onFrameRateChanged(const Observed &source)
429  {
430  Dispatcher &dispatcher = Dispatcher::getInstance();
431 
432  assert(&source == &dispatcher.m_frameRate);
433 
434  Argus::Range<uint64_t> frameDurationRangeNs(0);
435 
436  if (dispatcher.m_frameRate.get() == 0.0f)
437  {
438  // a frame rate of zero means VFR, get the sensor frame duration and apply it to
439  // the source
440  Argus::SensorMode *sensorMode = NULL;
441  PROPAGATE_ERROR(dispatcher.getSensorMode(dispatcher.m_sensorModeIndex.get(),
442  &sensorMode));
443 
444  Argus::ISensorMode *iSensorMode =
445  Argus::interface_cast<Argus::ISensorMode>(sensorMode);
446 
447  frameDurationRangeNs = iSensorMode->getFrameDurationRange();
448  }
449  else
450  {
451  // frame rate is frames per second, frameduration is in nanoseconds
452  frameDurationRangeNs =
453  TimeValue::fromCycelsPerSec(dispatcher.m_frameRate.get()).toNSec();
454  }
455 
456  if (m_iSourceSettings->setFrameDurationRange(frameDurationRangeNs) != Argus::STATUS_OK)
457  ORIGINATE_ERROR("Failed to set frame duration range");
458 
459  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
460 
461  return true;
462  }
463 
464  Argus::ISourceSettings *m_iSourceSettings;
465 };
466 
467 /**
468  * Auto control settings observer. Update Argus auto control settings if values which are set
469  * through the auto control settings change.
470  */
472 {
473 public:
474  AutoControlSettingsObserver(Argus::IAutoControlSettings *iAutoControlSettings)
475  : m_iAutoControlSettings(iAutoControlSettings)
476  {
477  Dispatcher &dispatcher = Dispatcher::getInstance();
478 
479  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeAntibandingMode.registerObserver(this,
480  static_cast<IObserver::CallbackFunction>(
482  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeLock.registerObserver(this,
483  static_cast<IObserver::CallbackFunction>(
485  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbLock.registerObserver(this,
486  static_cast<IObserver::CallbackFunction>(
488  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbMode.registerObserver(this,
489  static_cast<IObserver::CallbackFunction>(
491  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureCompensation.registerObserver(this,
492  static_cast<IObserver::CallbackFunction>(
494  PROPAGATE_ERROR_CONTINUE(dispatcher.m_ispDigitalGainRange.registerObserver(this,
495  static_cast<IObserver::CallbackFunction>(
497  PROPAGATE_ERROR_CONTINUE(dispatcher.m_acRegionHorizontal.registerObserver(this,
498  static_cast<IObserver::CallbackFunction>(
500  PROPAGATE_ERROR_CONTINUE(dispatcher.m_acRegionVertical.registerObserver(this,
501  static_cast<IObserver::CallbackFunction>(
503  }
504 
506  {
507  Dispatcher &dispatcher = Dispatcher::getInstance();
508 
509  PROPAGATE_ERROR_CONTINUE(dispatcher.m_ispDigitalGainRange.unregisterObserver(this,
510  static_cast<IObserver::CallbackFunction>(
512  PROPAGATE_ERROR_CONTINUE(dispatcher.m_exposureCompensation.unregisterObserver(this,
513  static_cast<IObserver::CallbackFunction>(
515  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbMode.unregisterObserver(this,
516  static_cast<IObserver::CallbackFunction>(
518  PROPAGATE_ERROR_CONTINUE(dispatcher.m_awbLock.unregisterObserver(this,
519  static_cast<IObserver::CallbackFunction>(
521  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeLock.unregisterObserver(this,
522  static_cast<IObserver::CallbackFunction>(
524  PROPAGATE_ERROR_CONTINUE(dispatcher.m_aeAntibandingMode.unregisterObserver(this,
525  static_cast<IObserver::CallbackFunction>(
527  PROPAGATE_ERROR_CONTINUE(dispatcher.m_acRegionHorizontal.unregisterObserver(this,
528  static_cast<IObserver::CallbackFunction>(
530  PROPAGATE_ERROR_CONTINUE(dispatcher.m_acRegionVertical.unregisterObserver(this,
531  static_cast<IObserver::CallbackFunction>(
533  }
534 
535  virtual bool isInterface(Argus::Interface *interface) const
536  {
537  return (interface == m_iAutoControlSettings);
538  }
539 
540 private:
541  bool onAeAntibandingModeChanged(const Observed &source)
542  {
543  Dispatcher &dispatcher = Dispatcher::getInstance();
544 
545  assert(&source == &dispatcher.m_aeAntibandingMode);
546 
547  if (m_iAutoControlSettings->setAeAntibandingMode(dispatcher.m_aeAntibandingMode.get()) !=
548  Argus::STATUS_OK)
549  {
550  ORIGINATE_ERROR("Failed to set the AE antibanding mode");
551  }
552 
553  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
554 
555  return true;
556  }
557 
558  bool onAeLockChanged(const Observed &source)
559  {
560  Dispatcher &dispatcher = Dispatcher::getInstance();
561 
562  assert(&source == &dispatcher.m_aeLock);
563 
564  if (m_iAutoControlSettings->setAeLock(dispatcher.m_aeLock.get()) != Argus::STATUS_OK)
565  ORIGINATE_ERROR("Failed to set the AE lock");
566 
567  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
568 
569  return true;
570  }
571 
572  bool onAwbLockChanged(const Observed &source)
573  {
574  Dispatcher &dispatcher = Dispatcher::getInstance();
575 
576  assert(&source == &dispatcher.m_awbLock);
577 
578  if (m_iAutoControlSettings->setAwbLock(dispatcher.m_awbLock.get()) != Argus::STATUS_OK)
579  ORIGINATE_ERROR("Failed to set the AWB lock");
580 
581  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
582 
583  return true;
584  }
585 
586  bool onAwbModeChanged(const Observed &source)
587  {
588  Dispatcher &dispatcher = Dispatcher::getInstance();
589 
590  assert(&source == &dispatcher.m_awbMode);
591 
592  if (m_iAutoControlSettings->setAwbMode(dispatcher.m_awbMode.get()) != Argus::STATUS_OK)
593  ORIGINATE_ERROR("Failed to set the AWB mode");
594 
595  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
596 
597  return true;
598  }
599 
600  bool onExposureCompensationChanged(const Observed &source)
601  {
602  Dispatcher &dispatcher = Dispatcher::getInstance();
603 
604  assert(&source == &dispatcher.m_exposureCompensation);
605 
606  if (m_iAutoControlSettings->setExposureCompensation(
607  dispatcher.m_exposureCompensation.get()) != Argus::STATUS_OK)
608  {
609  ORIGINATE_ERROR("Failed to set the exposure compensation");
610  }
611 
612  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
613 
614  return true;
615  }
616 
617  bool onIspDigitalGainRangeChanged(const Observed &source)
618  {
619  Dispatcher &dispatcher = Dispatcher::getInstance();
620 
621  assert(&source == &dispatcher.m_ispDigitalGainRange);
622 
623  if (m_iAutoControlSettings->setIspDigitalGainRange(
624  dispatcher.m_ispDigitalGainRange.get()) != Argus::STATUS_OK)
625  {
626  ORIGINATE_ERROR("Failed to set the Isp Digital Gain Range");
627  }
628  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
629 
630  return true;
631  }
632 
633  bool onAcRegionChanged(const Observed &source)
634  {
635  Dispatcher &dispatcher = Dispatcher::getInstance();
636 
637  assert((&source == &dispatcher.m_acRegionHorizontal) ||
638  (&source == &dispatcher.m_acRegionVertical));
639 
640  Argus::Range<uint32_t> horizontal = dispatcher.m_acRegionHorizontal.get();
641  Argus::Range<uint32_t> vertical = dispatcher.m_acRegionVertical.get();
642 
643  if ((horizontal.min() < horizontal.max()) &&
644  vertical.min() < vertical.max())
645  {
646  // set bayerHistogram
647  Argus::Rectangle<uint32_t> histRegion(horizontal.min(), vertical.min(),
648  horizontal.max(), vertical.max());
649 
650  if (m_iAutoControlSettings->setBayerHistogramRegion(histRegion) != Argus::STATUS_OK)
651  {
652  ORIGINATE_ERROR("Failed to set the bayer histogram region");
653  }
654 
655  // set AF
656  std::vector<Argus::AcRegion> afRegions;
657  Argus::AcRegion oneRegion(horizontal.min(), vertical.min(), horizontal.max(),
658  vertical.max(), 1.0f);
659  afRegions.push_back(oneRegion);
660 
661  if (m_iAutoControlSettings->setAfRegions(afRegions) != Argus::STATUS_OK)
662  {
663  ORIGINATE_ERROR("Failed to set the af region");
664  }
665 
666  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
667  }
668 
669  return true;
670  }
671 
672  Argus::IAutoControlSettings *m_iAutoControlSettings;
673 };
674 
675 /**
676  * DeFog settings observer. Update Argus DeFog settings if values which are set through the
677  * DeFog settings change.
678  */
680 {
681 public:
682  DeFogSettingsObserver(Argus::Ext::IDeFogSettings *iDeFogSettings)
683  : m_iDeFogSettings(iDeFogSettings)
684  {
685  Dispatcher &dispatcher = Dispatcher::getInstance();
686 
687  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogEnable.registerObserver(this,
688  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogEnableChanged)));
689  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogAmount.registerObserver(this,
690  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogAmountChanged)));
691  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogQuality.registerObserver(this,
692  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogQualityChanged)));
693  }
694 
696  {
697  Dispatcher &dispatcher = Dispatcher::getInstance();
698 
699  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogQuality.unregisterObserver(this,
700  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogQualityChanged)));
701  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogAmount.unregisterObserver(this,
702  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogAmountChanged)));
703  PROPAGATE_ERROR_CONTINUE(dispatcher.m_deFogEnable.unregisterObserver(this,
704  static_cast<IObserver::CallbackFunction>(&DeFogSettingsObserver::onDeFogEnableChanged)));
705  }
706 
707  virtual bool isInterface(Argus::Interface *interface) const
708  {
709  return (interface == m_iDeFogSettings);
710  }
711 
712 private:
713  bool onDeFogEnableChanged(const Observed &source)
714  {
715  Dispatcher &dispatcher = Dispatcher::getInstance();
716 
717  assert(&source == &dispatcher.m_deFogEnable);
718 
719  m_iDeFogSettings->setDeFogEnable(dispatcher.m_deFogEnable.get());
720 
721  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
722 
723  return true;
724  }
725 
726  bool onDeFogAmountChanged(const Observed &source)
727  {
728  Dispatcher &dispatcher = Dispatcher::getInstance();
729 
730  assert(&source == &dispatcher.m_deFogAmount);
731 
732  if (m_iDeFogSettings->setDeFogAmount(dispatcher.m_deFogAmount.get()) != Argus::STATUS_OK)
733  ORIGINATE_ERROR("Failed to set the DeFog amount");
734 
735  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
736 
737  return true;
738  }
739 
740  bool onDeFogQualityChanged(const Observed &source)
741  {
742  Dispatcher &dispatcher = Dispatcher::getInstance();
743 
744  assert(&source == &dispatcher.m_deFogQuality);
745 
746  if (m_iDeFogSettings->setDeFogQuality(dispatcher.m_deFogQuality.get()) != Argus::STATUS_OK)
747  ORIGINATE_ERROR("Failed to set the DeFog quality");
748 
749  PROPAGATE_ERROR(Dispatcher::getInstance().restartActiveRequests());
750 
751  return true;
752  }
753 
754  Argus::Ext::IDeFogSettings *m_iDeFogSettings;
755 };
756 
757 // valid YUV pixel formats
758 static const ValidatorEnum<Argus::PixelFormat>::ValueStringPair s_captureYuvFormatTypes[] =
759 {
760  { Argus::PIXEL_FMT_YCbCr_420_888, "nv12" },
761  { Argus::PIXEL_FMT_P016, "p016" }
762 };
763 
764 // valid denoise modes
765 static const ValidatorEnum<Argus::DenoiseMode>::ValueStringPair s_denoiseModes[] =
766 {
767  { Argus::DENOISE_MODE_OFF, "off" },
768  { Argus::DENOISE_MODE_FAST, "fast" },
769  { Argus::DENOISE_MODE_HIGH_QUALITY, "highquality" }
770 };
771 
772 // valid edge enhance modes
773 static const ValidatorEnum<Argus::EdgeEnhanceMode>::ValueStringPair s_edgeEnhanceModes[] =
774 {
775  { Argus::EDGE_ENHANCE_MODE_OFF, "off" },
776  { Argus::EDGE_ENHANCE_MODE_FAST, "fast" },
777  { Argus::EDGE_ENHANCE_MODE_HIGH_QUALITY, "highquality" }
778 };
779 
780 // valid AE antibanding modes
781 static const ValidatorEnum<Argus::AeAntibandingMode>::ValueStringPair s_aeAntibandingModes[] =
782 {
783  { Argus::AE_ANTIBANDING_MODE_OFF, "off" },
784  { Argus::AE_ANTIBANDING_MODE_AUTO, "auto" },
785  { Argus::AE_ANTIBANDING_MODE_50HZ, "50hz" },
786  { Argus::AE_ANTIBANDING_MODE_60HZ, "60hz" }
787 };
788 
789 // valid AWB modes
790 static const ValidatorEnum<Argus::AwbMode>::ValueStringPair s_awbModes[] =
791 {
792  { Argus::AWB_MODE_OFF, "off" },
793  { Argus::AWB_MODE_AUTO, "auto" },
794  { Argus::AWB_MODE_INCANDESCENT, "incandescent" },
795  { Argus::AWB_MODE_FLUORESCENT, "fluorescent" },
796  { Argus::AWB_MODE_WARM_FLUORESCENT, "warmfluorescent" },
797  { Argus::AWB_MODE_DAYLIGHT, "daylight" },
798  { Argus::AWB_MODE_CLOUDY_DAYLIGHT, "cloudydaylight" },
799  { Argus::AWB_MODE_TWILIGHT, "twilight" },
800  { Argus::AWB_MODE_SHADE, "shade" },
801  { Argus::AWB_MODE_MANUAL, "manual" }
802 };
803 
804 // valid still file formats
805 static const ValidatorEnum<ArgusSamples::StillFileType>::ValueStringPair s_stillFileTypes[] =
806 {
809 };
810 
811 // valid video formats
812 static const ValidatorEnum<VideoPipeline::VideoFormat>::ValueStringPair s_videoFormats[] =
813 {
818 };
819 
820 // valid video file types
821 static const ValidatorEnum<VideoPipeline::VideoFileType>::ValueStringPair s_videoFileTypes[] =
822 {
828 };
829 
830 static const Argus::Size2D<uint32_t> s_outputSizes[] =
831 {
832  Argus::Size2D<uint32_t>(0, 0), // if size is 0,0 take the current sensor size
833  Argus::Size2D<uint32_t>(176, 144), // QCIF
834  Argus::Size2D<uint32_t>(320, 240),
835  Argus::Size2D<uint32_t>(640, 480),
836  Argus::Size2D<uint32_t>(1280, 720), // 720p HDTV
837  Argus::Size2D<uint32_t>(1920, 1080), // 1080p HDTV
838  Argus::Size2D<uint32_t>(3840, 2160), // 2160p 4K UHDTV
839 };
840 
842  : m_deviceFocusPositionRange(0)
843  , m_deviceAperturePositionRange(0)
844  , m_deviceApertureMotorSpeedRange(1.0f)
845  , m_deviceExposureCompensationRange(0.0f)
846  , m_deviceIspDigitalGainRange(Argus::Range<float>(0.0f))
847  , m_sensorExposureTimeRange(Argus::Range<uint64_t>(0))
848  , m_sensorAnalogGainRange(Argus::Range<float>(0.0f))
849  , m_sensorFrameRateRange(0.0f)
850  , m_deviceIndex(new ValidatorStdVector<uint32_t, Argus::CameraDevice*>(&m_cameraDevices), 0)
851  , m_deviceOpen(false)
852  , m_sensorModeValid(false)
853  , m_verbose(false)
854  , m_kpi(false)
855  , m_exposureTimeRange(new ValidatorRange<Argus::Range<uint64_t> >(&m_sensorExposureTimeRange),
856  Argus::Range<uint64_t>(0))
857  , m_gainRange(new ValidatorRange<Argus::Range<float > >(&m_sensorAnalogGainRange),
858  Argus::Range<float>(0.0f))
859  , m_sensorModeIndex(new ValidatorEnum<uint32_t>(), 0)
860  , m_frameRate(new ValidatorRange<float>(&m_sensorFrameRateRange), 0.0f)
861  , m_focusPosition(new ValidatorRange<int32_t>(&m_deviceFocusPositionRange), 0)
862  , m_aperturePosition(new ValidatorRange<int32_t>(&m_deviceAperturePositionRange), 0)
863  , m_apertureFnum(new ValidatorEnum<float>(), 0.0f)
864  , m_apertureMotorSpeed(new ValidatorRange<float>(&m_deviceApertureMotorSpeedRange), 1.0f)
865  , m_captureYuvFormat(new ValidatorEnum<Argus::PixelFormat>(
866  s_captureYuvFormatTypes,
867  sizeof(s_captureYuvFormatTypes) / sizeof(s_captureYuvFormatTypes[0])),
868  Argus::PIXEL_FMT_YCbCr_420_888)
869  , m_denoiseMode(new ValidatorEnum<Argus::DenoiseMode>(
870  s_denoiseModes, sizeof(s_denoiseModes) / sizeof(s_denoiseModes[0])),
871  Argus::DENOISE_MODE_FAST)
872  , m_denoiseStrength(new ValidatorRange<float>(-1.0f, 1.0f), -1.0f)
873  , m_edgeEnhanceMode(new ValidatorEnum<Argus::EdgeEnhanceMode>(
874  s_edgeEnhanceModes, sizeof(s_edgeEnhanceModes) / sizeof(s_edgeEnhanceModes[0])),
875  Argus::EDGE_ENHANCE_MODE_FAST)
876  , m_edgeEnhanceStrength(new ValidatorRange<float>(-1.0f, 1.0f), -1.0f)
877  , m_aeAntibandingMode(new ValidatorEnum<Argus::AeAntibandingMode>(
878  s_aeAntibandingModes, sizeof(s_aeAntibandingModes) / sizeof(s_aeAntibandingModes[0])),
879  Argus::AE_ANTIBANDING_MODE_AUTO)
880  , m_aeLock(false)
881  , m_awbLock(false)
882  , m_awbMode(new ValidatorEnum<Argus::AwbMode>(
883  s_awbModes, sizeof(s_awbModes) / sizeof(s_awbModes[0])),
884  Argus::AWB_MODE_AUTO)
885  , m_exposureCompensation(new ValidatorRange<float>(&m_deviceExposureCompensationRange), 0.0f)
886  , m_ispDigitalGainRange(new ValidatorRange<Argus::Range<float> >(&m_deviceIspDigitalGainRange),
887  Argus::Range<float>(1.0f))
888  , m_acRegionHorizontal(Argus::Range<uint32_t>(0))
889  , m_acRegionVertical(Argus::Range<uint32_t>(0))
890  , m_stillFileType(new ValidatorEnum<StillFileType>(
891  s_stillFileTypes, sizeof(s_stillFileTypes) / sizeof(s_stillFileTypes[0])),
893  , m_videoFormat(new ValidatorEnum<VideoPipeline::VideoFormat>(
894  s_videoFormats, sizeof(s_videoFormats) / sizeof(s_videoFormats[0])),
895  VideoPipeline::VIDEO_FORMAT_H265)
896  , m_videoFileType(new ValidatorEnum<VideoPipeline::VideoFileType>(
897  s_videoFileTypes, sizeof(s_videoFileTypes) / sizeof(s_videoFileTypes[0])),
898  VideoPipeline::VIDEO_FILE_TYPE_MKV)
899  , m_videoBitRate(new ValidatorRange<uint32_t>(0, VideoPipeline::VIDEO_BITRATE_MAX),0)
900  , m_outputSize(new ValidatorSize2D<uint32_t>(s_outputSizes,
901  sizeof(s_outputSizes) / sizeof(s_outputSizes[0]), true /*allowArbitrarySizes*/),
902  Argus::Size2D<uint32_t>(0, 0))
903  , m_outputPath(".")
904  , m_deFogEnable(false)
905  , m_deFogAmount(new ValidatorRange<float>(0.0f, 1.0f), 0.9f)
906  , m_deFogQuality(new ValidatorRange<float>(0.0f, 1.0f), 0.14285f)
907  , m_initialized(false)
908  , m_iCameraProvider(NULL)
909 {
910  PROPAGATE_ERROR_CONTINUE(initialize());
911 }
912 
914 {
915  if (!shutdown())
916  REPORT_ERROR("Failed to shutdown");
917 }
918 
920 {
921  static InitOnce initOnce;
922  static Dispatcher instance;
923 
924  if (initOnce.begin())
925  {
926  if (instance.initialize())
927  {
928  initOnce.complete();
929  }
930  else
931  {
932  initOnce.failed();
933  REPORT_ERROR("Initalization failed");
934  }
935  }
936 
937  return instance;
938 }
939 
941 {
942  if (m_initialized)
943  return true;
944 
945  // Create the CameraProvider object and obtain its interface.
946  m_cameraProvider = Argus::UniqueObj<Argus::CameraProvider>(Argus::CameraProvider::create());
947  m_iCameraProvider = Argus::interface_cast<Argus::ICameraProvider>(m_cameraProvider);
948  if (!m_iCameraProvider)
949  ORIGINATE_ERROR("Failed to create CameraProvider");
950  printf("Argus Version: %s\n", m_iCameraProvider->getVersion().c_str());
951 
952  // Get the camera devices
953  m_iCameraProvider->getCameraDevices(&m_cameraDevices);
954  if (m_cameraDevices.size() == 0)
955  {
956  PROPAGATE_ERROR(shutdown());
957  ORIGINATE_ERROR("No cameras available");
958  }
959 
960  m_initialized = true;
961 
962  // register the device index observer after 'm_initialize' is set, the call back will be
963  // called immediately and assert that 'm_initialize' is set
964  PROPAGATE_ERROR_CONTINUE(m_deviceIndex.registerObserver(this,
965  static_cast<IObserver::CallbackFunction>(&Dispatcher::onDeviceIndexChanged)));
966  PROPAGATE_ERROR_CONTINUE(m_sensorModeIndex.registerObserver(this,
967  static_cast<IObserver::CallbackFunction>(&Dispatcher::onSensorModeIndexChanged)));
968 
969  return true;
970 }
971 
973 {
974  if (m_initialized)
975  {
976  m_initialized = false;
977  // unregister the device index observer in reverse order
978  PROPAGATE_ERROR_CONTINUE(m_sensorModeIndex.unregisterObserver(this,
979  static_cast<IObserver::CallbackFunction>(&Dispatcher::onSensorModeIndexChanged)));
980  PROPAGATE_ERROR_CONTINUE(m_deviceIndex.unregisterObserver(this,
981  static_cast<IObserver::CallbackFunction>(&Dispatcher::onDeviceIndexChanged)));
982 
983  PROPAGATE_ERROR_CONTINUE(closeSession());
984 
985  m_cameraDevices.clear();
986  m_cameraProvider.reset();
987  }
988 
989  return true;
990 }
991 
992 bool Dispatcher::onDeviceIndexChanged(const Observed &source)
993 {
994  assert(static_cast<const Value<uint32_t>&>(source).get() == m_deviceIndex);
995  assert(m_initialized);
996 
997  // close the currently open device
998  if (m_deviceOpen)
999  {
1000  PROPAGATE_ERROR(m_deviceOpen.set(false));
1001 
1002  PROPAGATE_ERROR(closeSession());
1003 
1004  // reset the current device properties
1005  }
1006 
1007  // open the new device
1008  const Argus::ICameraProperties *iCameraProperties =
1009  Argus::interface_cast<Argus::ICameraProperties>(m_cameraDevices[m_deviceIndex]);
1010  if (!iCameraProperties)
1011  ORIGINATE_ERROR("Failed to get ICameraProperties interface");
1012 
1013  // get the sensor modes
1014  if (iCameraProperties->getAllSensorModes(&m_sensorModes) != Argus::STATUS_OK)
1015  ORIGINATE_ERROR("Failed to get sensor modes");
1016 
1017  if (m_sensorModes.size() == 0)
1018  ORIGINATE_ERROR("No sensor modes found");
1019 
1020  // get the focus position range
1021  PROPAGATE_ERROR(m_deviceFocusPositionRange.set(iCameraProperties->getFocusPositionRange()));
1022 
1023  // get the aperture position range
1024  PROPAGATE_ERROR(m_deviceAperturePositionRange.set(iCameraProperties->getAperturePositionRange()));
1025 
1026  // get the aperture Fnum available values
1027  if(iCameraProperties->getAvailableApertureFNumbers(&m_deviceApertureFnums))
1028  ORIGINATE_ERROR("Failed to get Aperture Fnum");
1029 
1030  ValidatorEnum<float>* apertureFnumValidator =
1031  static_cast<ValidatorEnum<float>*>(m_apertureFnum.getValidator());
1032  apertureFnumValidator->setValidValues(m_deviceApertureFnums);
1033  // update the valid aperture F-num
1034  PROPAGATE_ERROR(m_apertureFnum.set(m_deviceApertureFnums.front(), true /*forceNotify*/));
1035 
1036  // get the aperture motor speed range
1037  PROPAGATE_ERROR(m_deviceApertureMotorSpeedRange.set(iCameraProperties->getApertureMotorSpeedRange()));
1038 
1039  // get new limits
1040  Argus::Range<float> digitalGainRange = iCameraProperties->getIspDigitalGainRange();
1041  Argus::Range<float> deviceExposureCompensationRange =
1042  iCameraProperties->getExposureCompensationRange();
1043 
1044  /* set ranges to unified range (to avoid errors when setting new values)
1045  * Eg. Say Device 1 has range [-1,0] and Device 2 has range [1,2] .If current value is -1 and
1046  * range is [-1,0] , setting the range to [1,2] would give error . Similarly, if current value
1047  * is 1 , setting the range to [-1,0] would give error. Thus we set range to [-1,2] , set value
1048  * to 1 and then set range to [1,2] to avoid errors.
1049  */
1050  Argus::Range<float> unifiedDigitalGainRange(0);
1051  unifiedDigitalGainRange.min() =
1052  std::min(m_deviceIspDigitalGainRange.get().min().min(), digitalGainRange.min());
1053  unifiedDigitalGainRange.max() =
1054  std::max(m_deviceIspDigitalGainRange.get().max().max(), digitalGainRange.max());
1055 
1056  Argus::Range<float> unifiedExposureCompensationRange(0);
1057  unifiedExposureCompensationRange.min() =
1058  std::min(m_deviceExposureCompensationRange.get().min(),
1059  deviceExposureCompensationRange.min());
1060  unifiedExposureCompensationRange.max() =
1061  std::max(m_deviceExposureCompensationRange.get().max(),
1062  deviceExposureCompensationRange.max());
1063 
1064  PROPAGATE_ERROR(m_deviceIspDigitalGainRange.set(
1065  Argus::Range<Argus::Range<float> >(unifiedDigitalGainRange)));
1066  PROPAGATE_ERROR(m_deviceExposureCompensationRange.set(
1067  Argus::Range<float> (unifiedExposureCompensationRange)));
1068 
1069  // update dependent values
1070  PROPAGATE_ERROR(m_ispDigitalGainRange.set(digitalGainRange));
1071  PROPAGATE_ERROR(m_exposureCompensation.set(0.0f));
1072 
1073  // set to final range
1074  PROPAGATE_ERROR(m_deviceIspDigitalGainRange.set(Argus::Range<Argus::Range<float> >(
1075  digitalGainRange, digitalGainRange)));
1076  PROPAGATE_ERROR(m_deviceExposureCompensationRange.set(Argus::Range<float> (
1077  deviceExposureCompensationRange)));
1078 
1079  // add value/string pairs for each sensor mode index
1080  std::vector<ValidatorEnum<uint32_t>::ValueStringPair> valueStringPairs;
1081  valueStringPairs.resize(m_sensorModes.size());
1082  for (size_t index = 0; index < m_sensorModes.size(); ++index)
1083  {
1084  Argus::ISensorMode *sensorMode =
1085  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[index]);
1086 
1087  valueStringPairs[index].value = (uint32_t)index;
1088 
1089  std::ostringstream stream;
1090  stream << index << ": "
1091  << sensorMode->getResolution().width() << "x" << sensorMode->getResolution().height();
1092 
1093  Argus::Ext::IPwlWdrSensorMode* pwlMode =
1094  Argus::interface_cast<Argus::Ext::IPwlWdrSensorMode>(m_sensorModes[index]);
1095 
1096  Argus::Ext::IDolWdrSensorMode* dolMode =
1097  Argus::interface_cast<Argus::Ext::IDolWdrSensorMode>(m_sensorModes[index]);
1098  if (pwlMode)
1099  {
1100  stream << " @" << sensorMode->getInputBitDepth() << "bpp -> " <<
1101  sensorMode->getOutputBitDepth() << "bpp";
1102  }
1103  else if (dolMode)
1104  {
1105  stream << " @" << sensorMode->getOutputBitDepth() << "bpp -> " <<
1106  dolMode->getExposureCount() << " exposure" << " DOL WDR";
1107  }
1108  else
1109  {
1110  stream << " @" << sensorMode->getOutputBitDepth() << "bpp";
1111  }
1112 
1113  valueStringPairs[index].string = stream.str();
1114  }
1115  // update the validator with the new value/string pairs
1116  ValidatorEnum<uint32_t> *validator =
1117  static_cast<ValidatorEnum<uint32_t>*>(m_sensorModeIndex.getValidator());
1118  PROPAGATE_ERROR(validator->setValidValues(valueStringPairs.data(), valueStringPairs.size()));
1119 
1120  // set the sensor mode index (force notify observer because the sensor modes are different now
1121  // although the sensor mode index could be the same)
1122  PROPAGATE_ERROR(m_sensorModeIndex.set(0, true /*forceNotify*/));
1123 
1124  PROPAGATE_ERROR(m_deviceOpen.set(true));
1125 
1126  return true;
1127 }
1128 
1129 bool Dispatcher::onSensorModeIndexChanged(const Observed &source)
1130 {
1131  m_sensorModeValid.set(false);
1132  assert(static_cast<const Value<uint32_t>&>(source).get() == m_sensorModeIndex);
1133  assert(m_initialized);
1134 
1135  Argus::ISensorMode *iSensorMode =
1136  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[m_sensorModeIndex.get()]);
1137  if (!iSensorMode)
1138  ORIGINATE_ERROR("Failed to get ISensorMode interface");
1139 
1140  // get new limits
1141  Argus::Range<uint64_t> sensorExposureTimeRange = iSensorMode->getExposureTimeRange();
1142  Argus::Range<float> sensorAnalogGainRange = iSensorMode->getAnalogGainRange();
1143  Argus::Range<TimeValue> sensorFrameDurationRange(
1144  TimeValue::fromNSec(iSensorMode->getFrameDurationRange().min()),
1145  TimeValue::fromNSec(iSensorMode->getFrameDurationRange().max()));
1146  Argus::Range<float> sensorFrameRateRange(
1147  sensorFrameDurationRange.max().toCyclesPerSec(),
1148  sensorFrameDurationRange.min().toCyclesPerSec());
1149 
1150  // set ranges to unified range (to avoid errors when setting new values)
1151  Argus::Range<uint64_t> unifiedSensorExposureTimeRange(0);
1152  unifiedSensorExposureTimeRange.min() =
1153  std::min(m_sensorExposureTimeRange.get().min().min(), sensorExposureTimeRange.min());
1154  unifiedSensorExposureTimeRange.max() =
1155  std::max(m_sensorExposureTimeRange.get().max().max(), sensorExposureTimeRange.max());
1156  Argus::Range<float> unifiedSensorAnalogGainRange(0);
1157  unifiedSensorAnalogGainRange.min() =
1158  std::min(m_sensorAnalogGainRange.get().min().min(), sensorAnalogGainRange.min());
1159  unifiedSensorAnalogGainRange.max() =
1160  std::max(m_sensorAnalogGainRange.get().max().max(), sensorAnalogGainRange.max());
1161  Argus::Range<float> unifiedSensorFrameRateRange(0.0f);
1162  unifiedSensorFrameRateRange.min() =
1163  std::min(m_sensorFrameRateRange.get().min(), sensorFrameRateRange.min());
1164  unifiedSensorFrameRateRange.max() =
1165  std::max(m_sensorFrameRateRange.get().max(), sensorFrameRateRange.max());
1166 
1167  PROPAGATE_ERROR(m_sensorExposureTimeRange.set(
1168  Argus::Range<Argus::Range<uint64_t> >(unifiedSensorExposureTimeRange)));
1169  PROPAGATE_ERROR(m_sensorAnalogGainRange.set(
1170  Argus::Range<Argus::Range<float> >(unifiedSensorAnalogGainRange)));
1171  PROPAGATE_ERROR(m_sensorFrameRateRange.set(unifiedSensorFrameRateRange));
1172 
1173  // update dependent values
1174  PROPAGATE_ERROR(m_exposureTimeRange.set(sensorExposureTimeRange));
1175  PROPAGATE_ERROR(m_gainRange.set(sensorAnalogGainRange));
1176  PROPAGATE_ERROR(m_frameRate.set(sensorFrameRateRange.max()));
1177 
1178  // set to final ranges
1179  PROPAGATE_ERROR(m_sensorExposureTimeRange.set(Argus::Range<Argus::Range<uint64_t> >(
1180  sensorExposureTimeRange, sensorExposureTimeRange)));
1181  PROPAGATE_ERROR(m_sensorAnalogGainRange.set(Argus::Range<Argus::Range<float> >(
1182  sensorAnalogGainRange, sensorAnalogGainRange)));
1183  PROPAGATE_ERROR(m_sensorFrameRateRange.set(sensorFrameRateRange));
1184  m_sensorModeValid.set(true);
1185 
1186  return true;
1187 }
1188 
1189 bool Dispatcher::supportsExtension(const Argus::ExtensionName& extension) const
1190 {
1191  return m_iCameraProvider->supportsExtension(extension);
1192 }
1193 
1194 bool Dispatcher::getInfo(std::string &info) const
1195 {
1196  std::ostringstream stream;
1197 
1198  assert(m_initialized);
1199 
1200  stream << "Argus extensions:" << std::endl;
1201  stream << " BayerSharpnessMap: " <<
1202  (supportsExtension(Argus::EXT_BAYER_SHARPNESS_MAP) ?
1203  "supported" : "not supported") << std::endl;
1204  stream << " DebugCaptureSession: " <<
1205  (supportsExtension(Argus::EXT_DEBUG_CAPTURE_SESSION) ?
1206  "supported" : "not supported") << std::endl;
1207  stream << " DeFog: " <<
1208  (supportsExtension(Argus::EXT_DE_FOG) ?
1209  "supported" : "not supported") << std::endl;
1210  stream << " FaceDetect: " <<
1211  (supportsExtension(Argus::EXT_FACE_DETECT) ?
1212  "supported" : "not supported") << std::endl;
1213  stream << " InternalFrameCount: " <<
1214  (supportsExtension(Argus::EXT_INTERNAL_FRAME_COUNT) ?
1215  "supported" : "not supported") << std::endl;
1216  stream << " SensorPrivateMetadata: " <<
1217  (supportsExtension(Argus::EXT_SENSOR_PRIVATE_METADATA) ?
1218  "supported" : "not supported") << std::endl;
1219 
1220  stream << "Number of camera devices: " << m_cameraDevices.size() << std::endl;
1221 
1222  for (uint32_t deviceIndex = 0; deviceIndex < m_cameraDevices.size(); ++deviceIndex)
1223  {
1224  stream << "Device: " << deviceIndex << std::endl;
1225 
1226  const Argus::ICameraProperties *iCameraProperties =
1227  Argus::interface_cast<Argus::ICameraProperties>(m_cameraDevices[deviceIndex]);
1228  if (!iCameraProperties)
1229  ORIGINATE_ERROR("Failed to get ICameraProperties interface");
1230 
1231  stream << " Max AE Regions: " <<
1232  iCameraProperties->getMaxAeRegions() << std::endl;
1233  stream << " Max AWB Regions: " <<
1234  iCameraProperties->getMaxAwbRegions() << std::endl;
1235  stream << " Focus Position Range: " <<
1236  iCameraProperties->getFocusPositionRange().min() << " - " <<
1237  iCameraProperties->getFocusPositionRange().max() << std::endl;
1238  stream << " Aperture Position Range: " <<
1239  iCameraProperties->getAperturePositionRange().min() << " - " <<
1240  iCameraProperties->getAperturePositionRange().max() << std::endl;
1241  stream << " Aperture Motor Speed Range: " <<
1242  iCameraProperties->getApertureMotorSpeedRange().min() << " - " <<
1243  iCameraProperties->getApertureMotorSpeedRange().max() << std::endl;
1244  stream << " Lens Aperture Available values: ";
1245  std::vector<float> availableFnums;
1246  iCameraProperties->getAvailableApertureFNumbers(&availableFnums);
1247  for (std::vector<float>::iterator it = availableFnums.begin();
1248  it != availableFnums.end(); ++it)
1249  {
1250  stream << *it << ", ";
1251  }
1252  stream << std::endl;
1253 
1254  stream << " Isp Digital Gain Range: " <<
1255  iCameraProperties->getIspDigitalGainRange().min() << " - " <<
1256  iCameraProperties->getIspDigitalGainRange().max() << std::endl;
1257 
1258  // print the sensor modes
1259  std::vector<Argus::SensorMode*> sensorModes;
1260  iCameraProperties->getAllSensorModes(&sensorModes);
1261  stream << " Number of sensor modes: " << sensorModes.size() << std::endl;
1262  for (uint32_t sensorModeIndex = 0; sensorModeIndex < sensorModes.size(); ++sensorModeIndex)
1263  {
1264  Argus::ISensorMode *sensorMode =
1265  Argus::interface_cast<Argus::ISensorMode>(sensorModes[sensorModeIndex]);
1266  if (!sensorMode)
1267  ORIGINATE_ERROR("Failed to get ISensorMode interface");
1268 
1269  // convert ns to fps
1270  float maximum_fps = TimeValue::fromNSec(
1271  sensorMode->getFrameDurationRange().min()).toCyclesPerSec();
1272  float minimum_fps = TimeValue::fromNSec(
1273  sensorMode->getFrameDurationRange().max()).toCyclesPerSec();
1274 
1275  stream << " Sensor mode: " << sensorModeIndex << std::endl;
1276  stream << " Resolution: " <<
1277  sensorMode->getResolution().width() << "x" <<
1278  sensorMode->getResolution().height() << std::endl;
1279  stream << " Exposure time range: " <<
1280  sensorMode->getExposureTimeRange().min() << " - " <<
1281  sensorMode->getExposureTimeRange().max() << " ns" << std::endl;
1282  stream << " Frame duration range: " <<
1283  sensorMode->getFrameDurationRange().min() << " - " <<
1284  sensorMode->getFrameDurationRange().max() << " ns" << std::endl;
1285  stream << " Framerate range: " <<
1286  minimum_fps << " - " <<
1287  maximum_fps << " fps" << std::endl;
1288  stream << " InputBitDepth: " <<
1289  sensorMode->getInputBitDepth() << std::endl;
1290  stream << " OutputBitDepth: " <<
1291  sensorMode->getOutputBitDepth() << std::endl;
1292  stream << " Analog gain range: " <<
1293  sensorMode->getAnalogGainRange().min() << " - " <<
1294  sensorMode->getAnalogGainRange().max() << std::endl;
1295 
1296  stream << " SensorModeType: " <<
1297  sensorMode->getSensorModeType().getName() << std::endl;
1298 
1299  Argus::Ext::IPwlWdrSensorMode* pwlMode =
1300  Argus::interface_cast<Argus::Ext::IPwlWdrSensorMode>(sensorModes[sensorModeIndex]);
1301 
1302  Argus::Ext::IDolWdrSensorMode* dolMode =
1303  Argus::interface_cast<Argus::Ext::IDolWdrSensorMode>(sensorModes[sensorModeIndex]);
1304 
1305  if (pwlMode)
1306  {
1307  stream << " Piecewise Linear (PWL) WDR Extension supported with: " <<
1308  pwlMode->getControlPointCount() << " control points." << std::endl;
1309  std::vector< Argus::Point2D<float> > points;
1310  Argus::Status status = pwlMode->getControlPoints(&points);
1311  if (status != Argus::STATUS_OK)
1312  ORIGINATE_ERROR("Error obtaining control points");
1313  stream << " - Control Points: " << std::endl;
1314  for (uint32_t j = 0; j < pwlMode->getControlPointCount(); j++)
1315  {
1316  stream << " (" << points[j].x() << ", " <<
1317  points[j].y() << ")" << std::endl;
1318  }
1319  }
1320  else if (dolMode)
1321  {
1322  stream << " Digital Overlap (DOL) WDR Extension supported with: " << std::endl <<
1323  " - Number of Exposures: " <<
1324  dolMode->getExposureCount() << std::endl <<
1325  " - Number of Optical Black Lines per exposure: " <<
1326  dolMode->getOpticalBlackRowCount() << std::endl <<
1327  " - Number of Line Info marker pixels per row per exposure: " <<
1328  dolMode->getLineInfoMarkerWidth() << std::endl <<
1329  " - Number of margin pixels on left per row per exposure: " <<
1330  dolMode->getLeftMarginWidth() << std::endl <<
1331  " - Number of margin pixels on right per row per exposure: " <<
1332  dolMode->getRightMarginWidth() << std::endl;
1333 
1334  std::vector<u_int32_t> verticalBlankPeriodRowCounts;
1335  Argus::Status status =
1336  dolMode->getVerticalBlankPeriodRowCount(&verticalBlankPeriodRowCounts);
1337  if (status != Argus::STATUS_OK)
1338  ORIGINATE_ERROR("Error obtaining vertical blank period offsets per exposure");
1339  stream << " - Vertical blank period section row counts per exposure: "
1340  << std::endl;
1341  for (uint32_t j = 0; j < verticalBlankPeriodRowCounts.size(); j++)
1342  {
1343  stream << " - VBP-section[" << j << "] : "
1344  << verticalBlankPeriodRowCounts[j] << std::endl;
1345  }
1346 
1347  stream << " - Physical Resolution: " <<
1348  dolMode->getPhysicalResolution().width() << "x" <<
1349  dolMode->getPhysicalResolution().height() << std::endl;
1350  }
1351 
1352  stream << std::endl;
1353  }
1354  }
1355 
1356  info = stream.str();
1357 
1358  return true;
1359 }
1360 
1361 bool Dispatcher::getSensorMode(uint32_t sensorModeIndex, Argus::SensorMode **sensorMode) const
1362 {
1363  assert(m_deviceOpen);
1364 
1365  if (sensorModeIndex >= m_sensorModes.size())
1366  ORIGINATE_ERROR("Invalid sensor mode index");
1367 
1368  *sensorMode = m_sensorModes[sensorModeIndex];
1369 
1370  return true;
1371 }
1372 
1373 Argus::Range<int32_t> Dispatcher::getDeviceFocusPositionRange() const
1374 {
1375  return m_deviceFocusPositionRange.get();
1376 }
1377 
1378 Argus::Range<int32_t> Dispatcher::getDeviceAperturePositionRange() const
1379 {
1380  return m_deviceAperturePositionRange.get();
1381 }
1382 
1384 {
1385  return m_deviceApertureMotorSpeedRange.get();
1386 }
1387 
1389 {
1390  assert(m_deviceOpen);
1391 
1392  return m_cameraDevices.size();
1393 }
1394 
1396  uint32_t deviceIndex)
1397 {
1398  assert(m_deviceOpen);
1399 
1400  if (deviceIndex > m_cameraDevices.size())
1401  ORIGINATE_ERROR("Invalid device index");
1402 
1403  // close the internal session, it might be using the device which will be used by the new
1404  // session
1405  PROPAGATE_ERROR(closeSession());
1406 
1407  // create the new capture session
1408  Argus::UniqueObj<Argus::CaptureSession> newSession(
1409  m_iCameraProvider->createCaptureSession(m_cameraDevices[deviceIndex]));
1410  if (!newSession)
1411  ORIGINATE_ERROR("Failed to create CaptureSession");
1412 
1413  PROPAGATE_ERROR(session.reset(newSession.release(), this));
1414 
1415  return true;
1416 }
1417 
1419 {
1420  for (ActiveSessionList::const_iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1421  ++it)
1422  {
1423  Argus::Ext::IDebugCaptureSession *iDebugCaptureSession =
1424  Argus::interface_cast<Argus::Ext::IDebugCaptureSession>(it->m_session);
1425  if (!iDebugCaptureSession)
1426  ORIGINATE_ERROR("DebugCaptureSession extension not supported");
1427 
1428  const Argus::Status status = iDebugCaptureSession->dump(STDOUT_FILENO);
1429  if (status != Argus::STATUS_OK)
1430  ORIGINATE_ERROR("Failed to get dump runtime info");
1431  }
1432 
1433  return true;
1434 }
1435 
1436 /**
1437  * Create the internal session
1438  */
1440 {
1441  if (m_captureSession)
1442  return true;
1443 
1444  PROPAGATE_ERROR(createSession(m_captureSession, m_deviceIndex));
1445 
1446  return true;
1447 }
1448 
1449 /**
1450  * Close the internal session
1451  */
1453 {
1455  return true;
1456 }
1457 
1458 bool Dispatcher::track(Argus::CaptureSession *session)
1459 {
1460  m_activeSessions.push_back(ActiveSession(session));
1461  return true;
1462 }
1463 
1464 bool Dispatcher::untrack(Argus::CaptureSession *session)
1465 {
1466  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1467  ++it)
1468  {
1469  if (it->m_session == session)
1470  {
1471  m_activeSessions.erase(it);
1472  return true;
1473  }
1474  }
1475 
1476  ORIGINATE_ERROR("Session not found");
1477 }
1478 
1479 bool Dispatcher::waitForEvents(Argus::EventQueue *eventQueue, TimeValue timeout,
1480  Argus::CaptureSession *session)
1481 {
1482  if (!session)
1483  {
1484  // use the internal session
1485  PROPAGATE_ERROR(createSession());
1486  session = m_captureSession.get();
1487  }
1488 
1489  Argus::IEventProvider *iEventProvider = Argus::interface_cast<Argus::IEventProvider>(session);
1490  if (!iEventProvider)
1491  ORIGINATE_ERROR("Failed to get iEventProvider interface");
1492 
1493  // wait for the events
1494  const Argus::Status status = iEventProvider->waitForEvents(eventQueue, timeout.toNSec());
1495  if ((status != Argus::STATUS_OK) && (status != Argus::STATUS_TIMEOUT))
1496  ORIGINATE_ERROR("Failed to get events");
1497 
1498  return true;
1499 }
1500 
1502  Argus::CaptureIntent captureIntent, Argus::CaptureSession *session)
1503 {
1504  if (!session)
1505  {
1506  // use the internal session
1507  PROPAGATE_ERROR(createSession());
1508  session = m_captureSession.get();
1509  }
1510 
1511  Argus::ICaptureSession *iCaptureSession =
1512  Argus::interface_cast<Argus::ICaptureSession>(session);
1513  if (!iCaptureSession)
1514  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1515 
1516  // Create request
1517  Argus::UniqueObj<Argus::Request> newRequest =
1518  Argus::UniqueObj<Argus::Request>(iCaptureSession->createRequest(captureIntent));
1519  if (!newRequest)
1520  ORIGINATE_ERROR("Failed to create request");
1521 
1522  // Setup request
1523  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(newRequest);
1524  if (!iRequest)
1525  ORIGINATE_ERROR("Failed to get IRequest interface");
1526 
1527  // get source settings interface
1528  Argus::ISourceSettings *iSourceSettings =
1529  Argus::interface_cast<Argus::ISourceSettings>(iRequest->getSourceSettings());
1530  if (!iSourceSettings)
1531  ORIGINATE_ERROR("Failed to get ISourceSettings interface");
1532 
1533  // register the source settings observer
1534  PROPAGATE_ERROR(registerObserver(iSourceSettings));
1535 
1536  // get auto control settings interface
1537  Argus::IAutoControlSettings *iAutoControlSettings =
1538  Argus::interface_cast<Argus::IAutoControlSettings>(iRequest->getAutoControlSettings());
1539  if (!iAutoControlSettings)
1540  ORIGINATE_ERROR("Failed to get IAutoControlSettings interface");
1541 
1542  // register the auto control settings observer
1543  PROPAGATE_ERROR(registerObserver(iAutoControlSettings));
1544 
1545  // register denoise settings interface
1546  Argus::IDenoiseSettings *iDenoiseSettings =
1547  Argus::interface_cast<Argus::IDenoiseSettings>(newRequest);
1548  if (!iDenoiseSettings)
1549  ORIGINATE_ERROR("Failed to get IDenoiseSettings interface");
1550  PROPAGATE_ERROR(registerObserver(iDenoiseSettings));
1551 
1552  // register edge enhance settings interface
1553  Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings =
1554  Argus::interface_cast<Argus::IEdgeEnhanceSettings>(newRequest);
1555  if (!iEdgeEnhanceSettings)
1556  ORIGINATE_ERROR("Failed to get IEdgeEnhanceSettings interface");
1557  PROPAGATE_ERROR(registerObserver(iEdgeEnhanceSettings));
1558 
1559  if (supportsExtension(Argus::EXT_DE_FOG))
1560  {
1561  // get DeFog settings interface
1562  Argus::Ext::IDeFogSettings *iDeFogSettings =
1563  Argus::interface_cast<Argus::Ext::IDeFogSettings>(newRequest);
1564  if (iDeFogSettings)
1565  {
1566  // register the DeFog settings observer
1567  PROPAGATE_ERROR(registerObserver(iDeFogSettings));
1568  }
1569  }
1570 
1571  PROPAGATE_ERROR(request.reset(newRequest.release(), this));
1572 
1573  return true;
1574 }
1575 
1576 bool Dispatcher::track(Argus::Request *request)
1577 {
1578  return true;
1579 }
1580 
1581 bool Dispatcher::untrack(Argus::Request *request)
1582 {
1583  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1584  if (!iRequest)
1585  ORIGINATE_ERROR("Failed to get IRequest interface");
1586 
1587  // get source settings interface
1588  Argus::ISourceSettings *iSourceSettings =
1589  Argus::interface_cast<Argus::ISourceSettings>(iRequest->getSourceSettings());
1590  if (!iSourceSettings)
1591  ORIGINATE_ERROR("Failed to get ISourceSettings interface");
1592 
1593  // unregister the source settings observer
1594  PROPAGATE_ERROR(unregisterObserver(iSourceSettings));
1595 
1596  // get auto control settings interface
1597  Argus::IAutoControlSettings *iAutoControlSettings =
1598  Argus::interface_cast<Argus::IAutoControlSettings>(iRequest->getAutoControlSettings());
1599  if (!iAutoControlSettings)
1600  ORIGINATE_ERROR("Failed to get IAutoControlSettings interface");
1601 
1602  // unregister the auto control settings observer
1603  PROPAGATE_ERROR(unregisterObserver(iAutoControlSettings));
1604 
1605  // unregister denoise settings interface
1606  Argus::IDenoiseSettings *iDenoiseSettings =
1607  Argus::interface_cast<Argus::IDenoiseSettings>(request);
1608  if (!iDenoiseSettings)
1609  ORIGINATE_ERROR("Failed to get IDenoiseSettings interface");
1610  PROPAGATE_ERROR(unregisterObserver(iDenoiseSettings));
1611 
1612  // unregister edge enhance settings interface
1613  Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings =
1614  Argus::interface_cast<Argus::IEdgeEnhanceSettings>(request);
1615  if (!iEdgeEnhanceSettings)
1616  ORIGINATE_ERROR("Failed to get IEdgeEnhanceSettings interface");
1617  PROPAGATE_ERROR(unregisterObserver(iEdgeEnhanceSettings));
1618 
1619  if (supportsExtension(Argus::EXT_DE_FOG))
1620  {
1621  // get DeFog settings interface
1622  Argus::Ext::IDeFogSettings *iDeFogSettings =
1623  Argus::interface_cast<Argus::Ext::IDeFogSettings>(request);
1624  if (iDeFogSettings)
1625  {
1626  // unregister the DeFog settings observer
1627  PROPAGATE_ERROR(unregisterObserver(iDeFogSettings));
1628  }
1629  }
1630 
1631  return true;
1632 }
1633 
1634 bool Dispatcher::createEventQueue(const std::vector<Argus::EventType> &eventTypes,
1635  Argus::UniqueObj<Argus::EventQueue>& eventQueue, Argus::CaptureSession *session)
1636 {
1637  if (!session)
1638  {
1639  // use the internal session
1640  PROPAGATE_ERROR(createSession());
1641  session = m_captureSession.get();
1642  }
1643 
1644  Argus::IEventProvider *iEventProvider =
1645  Argus::interface_cast<Argus::IEventProvider>(session);
1646  if (!iEventProvider)
1647  ORIGINATE_ERROR("Failed to get IEventProvider interface");
1648 
1649  Argus::EventQueue *newEventQueue = iEventProvider->createEventQueue(eventTypes);
1650  if (!newEventQueue)
1651  ORIGINATE_ERROR("Failed to create eventQueue");
1652 
1653  eventQueue.reset(newEventQueue);
1654 
1655  return true;
1656 }
1657 
1658 bool Dispatcher::capture(Argus::Request *request, Argus::CaptureSession *session)
1659 {
1660  if (!session)
1661  {
1662  // use the internal session
1663  PROPAGATE_ERROR(createSession());
1664  session = m_captureSession.get();
1665  }
1666 
1667  Argus::ICaptureSession *iCaptureSession =
1668  Argus::interface_cast<Argus::ICaptureSession>(session);
1669  if (!iCaptureSession)
1670  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1671 
1672  if (iCaptureSession->capture(request, Argus::TIMEOUT_INFINITE) == 0)
1673  ORIGINATE_ERROR("Failed to submit the still capture request");
1674 
1675  return true;
1676 }
1677 
1678 bool Dispatcher::startRepeat(Argus::Request *request, Argus::CaptureSession *session)
1679 {
1680  if (!session)
1681  {
1682  // use the internal session
1683  PROPAGATE_ERROR(createSession());
1684  session = m_captureSession.get();
1685  }
1686 
1687  Argus::ICaptureSession *iCaptureSession =
1688  Argus::interface_cast<Argus::ICaptureSession>(session);
1689  if (!iCaptureSession)
1690  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1691 
1692  if (iCaptureSession->repeat(request) != Argus::STATUS_OK)
1693  ORIGINATE_ERROR("Failed to submit repeating capture request");
1694 
1695  // add the request to the list of active requests for the session
1696  bool found = false;
1697  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1698  ++it)
1699  {
1700  if (it->m_session == session)
1701  {
1702  it->m_requests.push_back(request);
1703  found = true;
1704  break;
1705  }
1706  }
1707  if (!found)
1708  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1709 
1710  return true;
1711 }
1712 
1713 bool Dispatcher::startRepeatBurst(const std::vector<const Argus::Request*>& requestList,
1714  Argus::CaptureSession *session)
1715 {
1716  if (!session)
1717  {
1718  // use the internal session
1719  PROPAGATE_ERROR(createSession());
1720  session = m_captureSession.get();
1721  }
1722 
1723  Argus::ICaptureSession *iCaptureSession =
1724  Argus::interface_cast<Argus::ICaptureSession>(session);
1725  if (!iCaptureSession)
1726  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1727 
1728  if (iCaptureSession->repeatBurst(requestList) != Argus::STATUS_OK)
1729  ORIGINATE_ERROR("Failed to submit repeating burst request");
1730 
1731  // add the requests to the list of active requests for the session
1732  bool found = false;
1733  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1734  ++it)
1735  {
1736  if (it->m_session == session)
1737  {
1738  it->m_requests.insert(it->m_requests.end(), requestList.begin(), requestList.end());
1739  found = true;
1740  break;
1741  }
1742  }
1743  if (!found)
1744  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1745 
1746  return true;
1747 }
1748 
1749 bool Dispatcher::stopRepeat(Argus::CaptureSession *session)
1750 {
1751  if (!session)
1752  {
1753  // use the internal session
1754  PROPAGATE_ERROR(createSession());
1755  session = m_captureSession.get();
1756  }
1757 
1758  Argus::ICaptureSession *iCaptureSession =
1759  Argus::interface_cast<Argus::ICaptureSession>(session);
1760  if (!iCaptureSession)
1761  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1762 
1763  iCaptureSession->stopRepeat();
1764 
1765  // clear the list of active requests for the session
1766  bool found = false;
1767  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1768  ++it)
1769  {
1770  if (it->m_session == session)
1771  {
1772  it->m_requests.clear();
1773  found = true;
1774  break;
1775  }
1776  }
1777  if (!found)
1778  ORIGINATE_ERROR("Did not find the session in the list of active sessions");
1779 
1780  return true;
1781 }
1782 
1784 {
1785  for (ActiveSessionList::iterator it = m_activeSessions.begin(); it != m_activeSessions.end();
1786  ++it)
1787  {
1788  if (!it->m_requests.empty())
1789  {
1790  Argus::ICaptureSession *iCaptureSession =
1791  Argus::interface_cast<Argus::ICaptureSession>(it->m_session);
1792  if (!iCaptureSession)
1793  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1794 
1795  iCaptureSession->stopRepeat();
1796 
1797  if (iCaptureSession->repeatBurst(it->m_requests) != Argus::STATUS_OK)
1798  ORIGINATE_ERROR("Failed to submit repeating burst request");
1799  }
1800  }
1801 
1802  return true;
1803 }
1804 
1805 uint32_t Dispatcher::maxBurstRequests(Argus::CaptureSession *session)
1806 {
1807  if (!session)
1808  {
1809  // use the internal session
1810  PROPAGATE_ERROR(createSession());
1811  session = m_captureSession.get();
1812  }
1813 
1814  Argus::ICaptureSession *iCaptureSession =
1815  Argus::interface_cast<Argus::ICaptureSession>(session);
1816  if (!iCaptureSession)
1817  {
1818  REPORT_ERROR("Failed to get ICaptureSession interface");
1819  return 0;
1820  }
1821 
1822  return iCaptureSession->maxBurstRequests();
1823 }
1824 
1825 bool Dispatcher::waitForIdle(Argus::CaptureSession *session)
1826 {
1827  if (!session)
1828  {
1829  // use the internal session
1830  PROPAGATE_ERROR(createSession());
1831  session = m_captureSession.get();
1832  }
1833 
1834  Argus::ICaptureSession *iCaptureSession =
1835  Argus::interface_cast<Argus::ICaptureSession>(session);
1836  if (!iCaptureSession)
1837  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1838 
1839  if (iCaptureSession->waitForIdle() != Argus::STATUS_OK)
1840  ORIGINATE_ERROR("Waiting for idle failed");
1841 
1842  return true;
1843 }
1844 
1845 bool Dispatcher::getOutputSize(Argus::Size2D<uint32_t> *size) const
1846 {
1847  // if width or height is 0 take the sensor size
1848  if ((m_outputSize.get().width() == 0) || (m_outputSize.get().height() == 0))
1849  {
1850  // the device needs to be open to get sensor modes
1851  assert(m_deviceOpen);
1852 
1853  Argus::ISensorMode *sensorMode =
1854  Argus::interface_cast<Argus::ISensorMode>(m_sensorModes[m_sensorModeIndex.get()]);
1855  if (!sensorMode)
1856  ORIGINATE_ERROR("Failed to get ISensorMode interface");
1857  *size = sensorMode->getResolution();
1858  }
1859  else
1860  {
1861  *size = m_outputSize;
1862  }
1863 
1864  return true;
1865 }
1866 
1867 bool Dispatcher::createOutputStream(Argus::Request *request, bool enableMetadata,
1868  Argus::UniqueObj<Argus::OutputStream> &stream, Argus::CaptureSession *session)
1869 {
1870  if (!session)
1871  {
1872  // use the internal session
1873  PROPAGATE_ERROR(createSession());
1874  session = m_captureSession.get();
1875  }
1876 
1877  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1878  if (!iRequest)
1879  ORIGINATE_ERROR("Failed to get IRequest interface");
1880 
1881  Argus::Size2D<uint32_t> outputSize;
1882  PROPAGATE_ERROR(getOutputSize(&outputSize));
1883 
1884  Argus::ICaptureSession *iCaptureSession =
1885  Argus::interface_cast<Argus::ICaptureSession>(session);
1886  if (!iCaptureSession)
1887  ORIGINATE_ERROR("Failed to get ICaptureSession interface");
1888 
1889  Argus::UniqueObj<Argus::OutputStreamSettings> outputStreamSettings(
1890  iCaptureSession->createOutputStreamSettings(Argus::STREAM_TYPE_EGL));
1891  Argus::IEGLOutputStreamSettings* iEGLOutputStreamSettings =
1892  Argus::interface_cast<Argus::IEGLOutputStreamSettings>(outputStreamSettings);
1893  if (!iEGLOutputStreamSettings)
1894  ORIGINATE_ERROR("Failed to get IEGLOutputStreamSettings interface");
1895 
1896  iEGLOutputStreamSettings->setPixelFormat(m_captureYuvFormat.get());
1897  iEGLOutputStreamSettings->setResolution(outputSize);
1898  iEGLOutputStreamSettings->setEGLDisplay(Composer::getInstance().getEGLDisplay());
1899  iEGLOutputStreamSettings->setMetadataEnable(enableMetadata);
1900 
1901  Argus::UniqueObj<Argus::OutputStream> outputStream(
1902  iCaptureSession->createOutputStream(outputStreamSettings.get()));
1903  if (!outputStream)
1904  ORIGINATE_ERROR("Failed to create OutputStream");
1905 
1906  stream.reset(outputStream.release());
1907 
1908  return true;
1909 }
1910 
1911 bool Dispatcher::enableOutputStream(Argus::Request *request, Argus::OutputStream *stream)
1912 {
1913  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1914  if (!iRequest)
1915  ORIGINATE_ERROR("Failed to get IRequest interface");
1916 
1917  // Enable the stream
1918  if (iRequest->enableOutputStream(stream) != Argus::STATUS_OK)
1919  ORIGINATE_ERROR("Failed to enable the output stream");
1920 
1921  return true;
1922 }
1923 
1924 bool Dispatcher::disableOutputStream(Argus::Request *request, Argus::OutputStream *stream)
1925 {
1926  Argus::IRequest *iRequest = Argus::interface_cast<Argus::IRequest>(request);
1927  if (!iRequest)
1928  ORIGINATE_ERROR("Failed to get IRequest interface");
1929 
1930  // Disable the stream
1931  if (iRequest->disableOutputStream(stream) != Argus::STATUS_OK)
1932  ORIGINATE_ERROR("Failed to disable the output stream");
1933 
1934  return true;
1935 }
1936 
1937 bool Dispatcher::registerObserver(Argus::IDenoiseSettings *iDenoiseSettings)
1938 {
1939  UniquePointer<DenoiseSettingsObserver> denoiseSettings;
1940 
1941  denoiseSettings.reset(new DenoiseSettingsObserver(iDenoiseSettings));
1942  if (!denoiseSettings)
1943  ORIGINATE_ERROR("Out of memory");
1944 
1945  m_observers.push_front(denoiseSettings.release());
1946  return true;
1947 }
1948 
1949 bool Dispatcher::registerObserver(Argus::IEdgeEnhanceSettings *iEdgeEnhanceSettings)
1950 {
1951  UniquePointer<EdgeEnhanceSettingsObserver> edgeEnhanceSettings;
1952 
1953  edgeEnhanceSettings.reset(new EdgeEnhanceSettingsObserver(iEdgeEnhanceSettings));
1954  if (!edgeEnhanceSettings)
1955  ORIGINATE_ERROR("Out of memory");
1956 
1957  m_observers.push_front(edgeEnhanceSettings.release());
1958  return true;
1959 }
1960 
1961 bool Dispatcher::registerObserver(Argus::ISourceSettings *iSourceSettings)
1962 {
1963  UniquePointer<SourceSettingsObserver> sourceSettings;
1964 
1965  sourceSettings.reset(new SourceSettingsObserver(iSourceSettings));
1966  if (!sourceSettings)
1967  ORIGINATE_ERROR("Out of memory");
1968 
1969  m_observers.push_front(sourceSettings.release());
1970  return true;
1971 }
1972 
1973 bool Dispatcher::registerObserver(Argus::IAutoControlSettings *iAutoControlSettings)
1974 {
1975  UniquePointer<AutoControlSettingsObserver> autoControlSettings;
1976 
1977  autoControlSettings.reset(new AutoControlSettingsObserver(iAutoControlSettings));
1978  if (!autoControlSettings)
1979  ORIGINATE_ERROR("Out of memory");
1980 
1981  m_observers.push_front(autoControlSettings.release());
1982  return true;
1983 }
1984 
1985 bool Dispatcher::registerObserver(Argus::Ext::IDeFogSettings *iDeFogSettings)
1986 {
1987  UniquePointer<DeFogSettingsObserver> deFogSettings;
1988 
1989  deFogSettings.reset(new DeFogSettingsObserver(iDeFogSettings));
1990  if (!deFogSettings)
1991  ORIGINATE_ERROR("Out of memory");
1992 
1993  m_observers.push_front(deFogSettings.release());
1994  return true;
1995 }
1996 
1997 bool Dispatcher::unregisterObserver(Argus::Interface *interface)
1998 {
1999  for (std::list<IObserverForInterface*>::iterator it = m_observers.begin();
2000  it != m_observers.end(); ++it)
2001  {
2002  if ((*it)->isInterface(interface))
2003  {
2004  delete *it;
2005  m_observers.erase(it);
2006  return true;
2007  }
2008  }
2009 
2010  ORIGINATE_ERROR("Observer not found");
2011 }
2012 
2013 bool Dispatcher::message(const char *msg, ...)
2014 {
2015  if (m_verbose)
2016  {
2017  va_list list;
2018 
2019  va_start(list, msg);
2020 
2021  if (vprintf(msg, list) < 0)
2022  {
2023  va_end(list);
2024  ORIGINATE_ERROR("Failed to print message");
2025  }
2026 
2027  va_end(list);
2028  }
2029 
2030  return true;
2031 }
2032 
2033 }; // namespace ArgusSamples