/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// Copyright (c) 2016 Raytrix GmbH. All rights reserved.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
#pragma once

#include "Rx.Interop.Runtime28/RxImageTypes.h"
#include "Rx.Interop.Runtime30/TriggerModes.h"
#include "Rx.Interop.Runtime30/CameraProperties.h"
#include "Rx.Interop.Runtime30/IStatusCameraCallback.h"
#include "Rx.Interop.Runtime30/Rx.Camera.INativeDeviceControl.h"
#include "Rx.Interop.Runtime30/Rx.Camera.INativeDeviceImageCallback.h"

namespace Rx
{
	namespace Interop
	{
		namespace Runtime30
		{
			namespace Camera
			{
				/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
				/// <summary>
				/// 	Interface for native device class. This base provides functionality for using devices independently of their hardware
				/// 	interface type.
				///
				/// 	For further information on these functions see the documentation for INativeDeviceControl!
				/// </summary>
				/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
				class INativeDeviceDo
				{
				protected:

					virtual ~INativeDeviceDo() { };

				public:

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Destroys this interface and by this the whole native device by deleting itself.
					/// </summary>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoDestroy() = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the initialize operation.
					/// 	Has to be called before anything else after the construction.
					///
					/// 	Expected Device State:
					/// 		- Created (after construction)
					/// </summary>
					///
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoInitialize() = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the open operation. The Camera has to be initialized before. The device has to be open for some functions.
					/// 	With some cameras it doesn't do anything. Because it is called from the server side through the .NET device and native
					/// 	device the function will be called, because all cameras and states are handled equally.
					///
					/// 	 Expected Device State:
					/// 		- Initialized.
					/// </summary>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoOpen() = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the close operation. Should only be called on an open Camera. For further information see DoOpen().
					///
					/// 	 Expected Device State:
					/// 		- Opened.
					/// </summary>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoClose() = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the start capture operation.
					///
					/// 	Expected Device State:
					/// 		- Opened
					///
					/// </summary>
					///
					/// <param name="eProp">	The triggermode the camera is to be started in. (e.g. live, snapshot) </param>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoStartCapture(Interop::Runtime30::Camera::ETriggerMode::ID eProp) = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the stop capture operation.
					///
					/// 	Expected Device State:
					/// 		- Capturing
					///
					/// </summary>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoStopCapture() = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the suspend capture operation.
					/// 	Should only be called on a device capturing images.
					/// 	Not all cameras support this, if the implementation is empty, but it will still be called from server side, where
					/// 	states are handled.
					///
					/// 	Expected Device State:
					/// 		- Capturing
					///
					/// </summary>
					///
					/// <param name="bSuspend">	true to suspend. </param>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoSuspendCapture(bool bSuspend) = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Gets information about the image type the camera delivers.
					/// 	This is done by getting the values from the manufacturer SDK
					/// 	and mapping them to Raytrix (enum) values. Example:
					/// 	     	case BGAPI_PIXTYPE_BAYGB8:
					/// 			{
					/// 				iPixelType		= RX_IMG_BAYER_GB;
					/// 				iDataType		= RX_IMG_UNSIGNED_BYTE;
					/// 				iBytesPerPixel	= 1;
					/// 				break;
					/// 			}
					/// </summary>
					///
					///  	Expected Device State:
					/// 		- Initialized
					///
					///
					/// <param name="ePixelType">	 	[out] The pixeltype. </param>
					/// <param name="eDataType">	 	[out] The datatype. </param>
					/// <param name="iBytesPerPixel">	[out] Zero-based index of the bytes per pixel. </param>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoGetImageType(Interop::Runtime28::EPixelType::ID& ePixelType,
							Interop::Runtime28::EDataType::ID& eDataType,
							int& iBytesPerPixel) = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Executes the software trigger operation.
					///
					///		Expected Device State:
					/// 		- Capturing (with Software Trigger Mode)
					///
					///
					/// </summary>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoTrigger() = 0;

					// For further information on these functions see NativeDeviceControl documentation
					virtual bool DoIsPropertyAvailable(Interop::Runtime30::Camera::EProperty::ID eProp) = 0;

					virtual void DoGetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, int& iValue)            = 0;
					virtual void DoGetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, float& fValue)          = 0;
					virtual int DoGetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, char* pcValue, int iLen) = 0;

					virtual void DoSetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, int iValue)          = 0;
					virtual void DoSetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, float fValue)        = 0;
					virtual void DoSetProperty(Interop::Runtime30::Camera::EProperty::ID eProp, const char* pcValue) = 0;

					virtual void DoGetPropertyRange(Interop::Runtime30::Camera::EProperty::ID eProp, float& fMin, float& fMax)       = 0;
					virtual void DoGetPropertyRange(Interop::Runtime30::Camera::EProperty::ID eProp, int& iMin, int& iMax)           = 0;
					virtual int DoGetPropertyRange(Interop::Runtime30::Camera::EProperty::ID eProp, int* piValues, int iMaxValueCnt) = 0;

					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					/// <summary>
					/// 	Registers the NativeDevice with the nativedevicedriver. It is used for ImageCallback and some checks.
					/// </summary>
					///
					/// <param name="pNativeImageCallback"> [in] The native (device) base. </param>
					/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					virtual void DoRegisterImageCallback(Interop::Runtime30::Camera::INativeDeviceImageCallback* pNativeImageCallback) = 0;
				};
			}
		}
	}
}

#pragma make_public(Rx::Interop::Runtime30::Camera::INativeDeviceDo)
