///
/// HybridCameraSessionSpecSwift.hpp
/// This file was generated by nitrogen. DO NOT MODIFY THIS FILE.
/// https://github.com/mrousavy/nitro
/// Copyright © Marc Rousavy @ Margelo
///

#pragma once

#include "HybridCameraSessionSpec.hpp"

// Forward declaration of `HybridCameraSessionSpec_cxx` to properly resolve imports.
namespace VisionCamera { class HybridCameraSessionSpec_cxx; }

// Forward declaration of `HybridCameraControllerSpec` to properly resolve imports.
namespace margelo::nitro::camera { class HybridCameraControllerSpec; }
// Forward declaration of `CameraSessionConnection` to properly resolve imports.
namespace margelo::nitro::camera { struct CameraSessionConnection; }
// Forward declaration of `HybridCameraDeviceSpec` to properly resolve imports.
namespace margelo::nitro::camera { class HybridCameraDeviceSpec; }
// Forward declaration of `CameraOutputConfiguration` to properly resolve imports.
namespace margelo::nitro::camera { struct CameraOutputConfiguration; }
// Forward declaration of `MirrorMode` to properly resolve imports.
namespace margelo::nitro::camera { enum class MirrorMode; }
// Forward declaration of `HybridCameraOutputSpec` to properly resolve imports.
namespace margelo::nitro::camera { class HybridCameraOutputSpec; }
// Forward declaration of `FPSConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct FPSConstraint; }
// Forward declaration of `VideoStabilizationModeConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct VideoStabilizationModeConstraint; }
// Forward declaration of `PreviewStabilizationModeConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct PreviewStabilizationModeConstraint; }
// Forward declaration of `ResolutionBiasConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct ResolutionBiasConstraint; }
// Forward declaration of `VideoDynamicRangeConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct VideoDynamicRangeConstraint; }
// Forward declaration of `PhotoHDRConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct PhotoHDRConstraint; }
// Forward declaration of `PixelFormatConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct PixelFormatConstraint; }
// Forward declaration of `BinnedConstraint` to properly resolve imports.
namespace margelo::nitro::camera { struct BinnedConstraint; }
// Forward declaration of `TargetStabilizationMode` to properly resolve imports.
namespace margelo::nitro::camera { enum class TargetStabilizationMode; }
// Forward declaration of `TargetDynamicRange` to properly resolve imports.
namespace margelo::nitro::camera { struct TargetDynamicRange; }
// Forward declaration of `TargetDynamicRangeBitDepth` to properly resolve imports.
namespace margelo::nitro::camera { enum class TargetDynamicRangeBitDepth; }
// Forward declaration of `TargetColorSpace` to properly resolve imports.
namespace margelo::nitro::camera { enum class TargetColorSpace; }
// Forward declaration of `TargetColorRange` to properly resolve imports.
namespace margelo::nitro::camera { enum class TargetColorRange; }
// Forward declaration of `PixelFormat` to properly resolve imports.
namespace margelo::nitro::camera { enum class PixelFormat; }
// Forward declaration of `HybridCameraSessionConfigSpec` to properly resolve imports.
namespace margelo::nitro::camera { class HybridCameraSessionConfigSpec; }
// Forward declaration of `CameraSessionConfiguration` to properly resolve imports.
namespace margelo::nitro::camera { struct CameraSessionConfiguration; }
// Forward declaration of `ListenerSubscription` to properly resolve imports.
namespace margelo::nitro::camera { struct ListenerSubscription; }
// Forward declaration of `InterruptionReason` to properly resolve imports.
namespace margelo::nitro::camera { enum class InterruptionReason; }

#include <memory>
#include "HybridCameraControllerSpec.hpp"
#include <vector>
#include <NitroModules/Promise.hpp>
#include "CameraSessionConnection.hpp"
#include "HybridCameraDeviceSpec.hpp"
#include "CameraOutputConfiguration.hpp"
#include "MirrorMode.hpp"
#include "HybridCameraOutputSpec.hpp"
#include "FPSConstraint.hpp"
#include "VideoStabilizationModeConstraint.hpp"
#include "PreviewStabilizationModeConstraint.hpp"
#include "ResolutionBiasConstraint.hpp"
#include "VideoDynamicRangeConstraint.hpp"
#include "PhotoHDRConstraint.hpp"
#include "PixelFormatConstraint.hpp"
#include "BinnedConstraint.hpp"
#include <variant>
#include "TargetStabilizationMode.hpp"
#include "TargetDynamicRange.hpp"
#include "TargetDynamicRangeBitDepth.hpp"
#include "TargetColorSpace.hpp"
#include "TargetColorRange.hpp"
#include "PixelFormat.hpp"
#include <optional>
#include "HybridCameraSessionConfigSpec.hpp"
#include <functional>
#include "CameraSessionConfiguration.hpp"
#include "ListenerSubscription.hpp"
#include <exception>
#include "InterruptionReason.hpp"

#include "VisionCamera-Swift-Cxx-Umbrella.hpp"

namespace margelo::nitro::camera {

  /**
   * The C++ part of HybridCameraSessionSpec_cxx.swift.
   *
   * HybridCameraSessionSpecSwift (C++) accesses HybridCameraSessionSpec_cxx (Swift), and might
   * contain some additional bridging code for C++ <> Swift interop.
   *
   * Since this obviously introduces an overhead, I hope at some point in
   * the future, HybridCameraSessionSpec_cxx can directly inherit from the C++ class HybridCameraSessionSpec
   * to simplify the whole structure and memory management.
   */
  class HybridCameraSessionSpecSwift: public virtual HybridCameraSessionSpec {
  public:
    // Constructor from a Swift instance
    explicit HybridCameraSessionSpecSwift(const VisionCamera::HybridCameraSessionSpec_cxx& swiftPart):
      HybridObject(HybridCameraSessionSpec::TAG),
      _swiftPart(swiftPart) { }

  public:
    // Get the Swift part
    inline VisionCamera::HybridCameraSessionSpec_cxx& getSwiftPart() noexcept {
      return _swiftPart;
    }

  public:
    inline size_t getExternalMemorySize() noexcept override {
      return _swiftPart.getMemorySize();
    }
    bool equals(const std::shared_ptr<HybridObject>& other) override {
      if (auto otherCast = std::dynamic_pointer_cast<HybridCameraSessionSpecSwift>(other)) {
        return _swiftPart.equals(otherCast->_swiftPart);
      }
      return false;
    }
    void dispose() noexcept override {
      _swiftPart.dispose();
    }
    std::string toString() override {
      return _swiftPart.toString();
    }

  public:
    // Properties
    inline bool getIsRunning() noexcept override {
      return _swiftPart.isRunning();
    }

  public:
    // Methods
    inline std::shared_ptr<Promise<std::vector<std::shared_ptr<HybridCameraControllerSpec>>>> configure(const std::vector<CameraSessionConnection>& connections, const std::optional<CameraSessionConfiguration>& config) override {
      auto __result = _swiftPart.configure(connections, config);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline std::shared_ptr<Promise<void>> start() override {
      auto __result = _swiftPart.start();
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline std::shared_ptr<Promise<void>> stop() override {
      auto __result = _swiftPart.stop();
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline ListenerSubscription addOnStartedListener(const std::function<void()>& onStarted) override {
      auto __result = _swiftPart.addOnStartedListener(onStarted);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline ListenerSubscription addOnStoppedListener(const std::function<void()>& onStopped) override {
      auto __result = _swiftPart.addOnStoppedListener(onStopped);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline ListenerSubscription addOnErrorListener(const std::function<void(const std::exception_ptr& /* error */)>& onError) override {
      auto __result = _swiftPart.addOnErrorListener(onError);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline ListenerSubscription addOnInterruptionStartedListener(const std::function<void(InterruptionReason /* reason */)>& onInterruptionStarted) override {
      auto __result = _swiftPart.addOnInterruptionStartedListener(onInterruptionStarted);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }
    inline ListenerSubscription addOnInterruptionEndedListener(const std::function<void()>& onInterruptionEnded) override {
      auto __result = _swiftPart.addOnInterruptionEndedListener(onInterruptionEnded);
      if (__result.hasError()) [[unlikely]] {
        std::rethrow_exception(__result.error());
      }
      auto __value = std::move(__result.value());
      return __value;
    }

  private:
    VisionCamera::HybridCameraSessionSpec_cxx _swiftPart;
  };

} // namespace margelo::nitro::camera
