#ifndef ANSANNHUB_H
#define ANSANNHUB_H
#define ANSANNHUB_API __declspec(dllexport)
#include <iostream>
#include <cstdint>
#include "ANSLicense.h"
#include <vector>
//#include "LabVIEWHeader/extcode.h"
namespace ANSCENTER
{	
	class ANSANNHUB_API ANNHUBAPI
	{
	private:
		std::vector<double> nInput;			//ANN inputs
		std::vector<double> nOutput;		//ANN outputs
		std::vector<std::vector<double>> IW;
		std::vector<std::vector<double>> LW;
		std::vector<double> Ib;
		std::vector<double> Lb;
		//  Structural parameters
		int	   nInputNodes, nHiddenNodes, nOutputNodes;
		int    hiddenActivation;				// default =2	
		int    outputActivation;				// default =2
		int    dataNormalisationModeInput; 		// default =1;
		int    dataNormalisationModeOutput; 	// default =1;

		// Preprocessing and postprocessing settings 
		std::vector<double> xmaxInput, xminInput;			// Maximum and minimum of inputs
		double ymaxInput, yminInput;						// Maximum and minimum of inputs
		std::vector<double> xmaxOutput, xminOutput;			// Maximum and minimum of outputs
		double ymaxOutput, yminOutput;						// Maximum and minimum of outputs

		// Control creation
		unsigned char   isCreated;
		std::string     _licenseKey;
		bool            _licenseValid{ false };
		bool		    _isInitialized{ false };
		std::string     _modelFilePath;

	private:

		void 	PreProcessing(std::vector<double>& Input);				//  mode =0--> linear, mode =1 mapminmax, mode =2 standarddev
		void 	PostProcessing(std::vector<double>& Output);			//  mode =0--> linear, mode =1 mapminmax, mode =2 standarddev        
		void 	Create(int inputNodes, int HiddenNodes, int outputNodes);
		void    FreeNeuralNetwork();
		void	CheckLicense();
		int	    ImportANNFromFile(std::string filename);

	public:
		ANNHUBAPI();
		~ANNHUBAPI() noexcept;
		[[nodiscard]] bool    Init(std::string licenseKey, std::string modelFilePath);
		[[nodiscard]] std::vector<double> Inference(std::vector<double> ip);
		void    Destroy();
		[[nodiscard]] int     GetOutputNode() { return nOutputNodes; };
	};
}


extern "C" __declspec(dllexport) int CreateANNHUBHandle(ANSCENTER::ANNHUBAPI **Handle, const char* licenseKey, const char* modelFilePath);
extern "C" __declspec(dllexport) int ReleaseANNHUBHandle(ANSCENTER::ANNHUBAPI **Handle);
extern "C" __declspec(dllexport) int ANNHUB_Inference(ANSCENTER::ANNHUBAPI **pHandle, double* inputArray, int inputSize, double** outputArray);
extern "C" __declspec(dllexport) int ANNHUB_InferenceLV(ANSCENTER::ANNHUBAPI **pHandle, double* inputArray, int inputSize, LStrHandle outputHandle);

// --- V2 entry points: accept handle by value (uint64_t) to avoid LabVIEW buffer reuse bug ---
extern "C" __declspec(dllexport) int ANNHUB_Inference_V2(uint64_t handleVal, double* inputArray, int inputSize, double** outputArray);
extern "C" __declspec(dllexport) int ANNHUB_InferenceLV_V2(uint64_t handleVal, double* inputArray, int inputSize, LStrHandle outputHandle);

#endif