#include <Windows.h>

#include "svmgrAPI2.h"
#include "svmgrDefaultImpl.h"

#include <vector>

using namespace std;

struct IUsrMgr : public ISVMgr
{
	
	IUsrMgr(IAPIMgr* api) : svmgrAPI(api),TimerPeriod(2000) {  }	
	
	void __stdcall StartProject();

	BOOL __stdcall OnReadGroupCompleted ( 
	DWORD               dwCount,
    ULONG               ulClientHandle,
	LPTSTR            * pszVariables,
	BOOL              * pbResults,
	_svmgrVarValue2  ** pValues,
	FILETIME          * pftTimestamps,
	_svmgrVarStatus   * pStatus);
		
	void __stdcall OnTimerElapsed(ULONG ulClientHandle);
	
private:
	const int TimerPeriod;
	vector<char *> tags;
	IAPIMgr* svmgrAPI;
	void populateTags();

};

HRESULT WINAPI svmgrExchangeInterface(LPVOID * ppvInterface, IAPIMgr * pSvAPI)
{
   *ppvInterface = new IUsrMgr(pSvAPI);;
    return S_OK;
}

void IUsrMgr::StartProject()
{
	populateTags();
	svmgrAPI->SetTimer(TimerPeriod, 0);    
}

BOOL IUsrMgr::OnReadGroupCompleted (	
	DWORD               dwCount,
    ULONG               ulClientHandle,
	LPTSTR            * pszVariables,
	BOOL              * pbResults,
	_svmgrVarValue2  ** pValues,
	FILETIME          * pftTimestamps,
	_svmgrVarStatus   * pStatus)
{
	for(DWORD i = 0; i < dwCount; i++)
	{
		char str[200];

		sprintf(str, "%s reports %s\n", pszVariables[i], pbResults[i] ? "Ok" : "Fail");
		
		OutputDebugString(str);
	}
	
	svmgrAPI->CloseVariablesGroup((HANDLE)ulClientHandle); 

	svmgrAPI->SetTimer(TimerPeriod, 0);    

	return TRUE;
}

void IUsrMgr::OnTimerElapsed(ULONG ulClientHandle)
{
	HANDLE varGrp;

	if(svmgrAPI->CreateVariablesGroup(varGrp))
	{
		size_t size = tags.size() > 10 ? 10 : tags.size();
		for(size_t i = 0; i < size; i++)
		{
			svmgrAPI->AddVariableToGroup(varGrp,tags[i]);
		
		}
		svmgrAPI->ReadGroup(varGrp, (ULONG)varGrp);
	}  
}

void IUsrMgr::populateTags()
{
	HANDLE hEnum;              
	_svmgrVariableAttributes sAttributes;

	svmgrAPI->CreateVarEnum( hEnum);
	svmgrAPI->InitVariableAttributesStructure(sizeof(sAttributes), sAttributes);

	_svmgrVarEnum	peVar[ 100];  
	ULONG			ulNbVar;      
	BOOL			bResult;      

	do
	{
		bResult = svmgrAPI->VarEnum( hEnum, 100, peVar, &ulNbVar);

		for ( ULONG ulCmpt = 0; ulCmpt < ulNbVar; ulCmpt++)
		{
			int len = strlen(peVar[ulCmpt].szName) +1;
			char* szName = new char[len];
			memcpy(szName,peVar[ulCmpt].szName,len);
			tags.push_back(szName);

			svmgrAPI->GetVariableAttributes(peVar[ulCmpt].szName, sAttributes);

			if(peVar[ulCmpt].vt == svmgr_vtALARM)
			{
				svmgrAPI->LogMessage(SVMGR_LVL_INFO, SVMGR_DEST_VIEWER, "%s Min:%f Max:%f", 
					peVar[ulCmpt].szName, sAttributes.dMinimumValue, sAttributes.dMaximumValue);
			}
		}
		svmgrAPI->ClearVarEnum( ulNbVar, peVar);
	}
	while ( bResult);

	svmgrAPI->FreeVariableAttributesStructure(sAttributes);
	svmgrAPI->CloseVarEnum( hEnum);

}

