#include <iostream>

#include "InitPlatformState.hpp"
#include "MissionData.hpp"
#include "ConfigData.hpp"

InitPlatformState::InitPlatformState(std::string label, uint32_t timeout_min) : stateLabel{label}, StateBase(label, timeout_min)
{
	defineActionLabels();
}

void InitPlatformState::defineActionLabels()
{
	actionLabels[readConfigFile] = "readConfigFile";
	actionLabels[readMissionFile] = "readMissionFile";
	actionLabels[initCTD1] = "initCTD1";
	actionLabels[initBcyEngine] = "initBcyEngine";
	actionLabels[lastAction] = "lastAction";
}

void InitPlatformState::doStateActions(StateEvent event)
{
	switch (currentAction)
	{
	case readConfigFile:
		nextAction = doReadConfigFile(event);
		break;
	case readMissionFile:
		nextAction = doReadMissionFile(event);
		break;
	case initCTD1:
		nextAction = initBcyEngine;
		break;
	case initBcyEngine:
		nextAction = lastAction;
		break;
	case lastAction:
		hitLastAction = true;
		break;
	default:
		std::cout << "**Error: InitPlatform unhandled action" << std::endl;
	}
	
	if (currentAction != nextAction)
	{
		doActionChange(actionLabels[currentAction], actionLabels[nextAction]);
	}
}

InitPlatformState::Actions InitPlatformState::doReadMissionFile(const StateEvent event)
{
	std::string comment;
	char temp[64];
	
	MissionData::readMissionData();
	
	comment.clear();
	comment.append("Park sample period (minutes): ");
	snprintf(temp, sizeof(temp), "%6d", MissionData::getParkSamplePeriod_minutes());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });
	
	comment.clear();
	comment.append("Max mission duration (hours): ");
	snprintf(temp, sizeof(temp), "%8.4f", MissionData::getMaxMissionDuration_hours());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });
	
	comment.clear();
	comment.append("Max num of profiles: ");
	snprintf(temp, sizeof(temp), "%4d", MissionData::getMaxProfiles());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });
	
	comment.clear();
	comment.append("Max Pressure (dBar): ");
	snprintf(temp, sizeof(temp), "%7.1f", MissionData::getMaxPressure_dBar());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });
	
	comment.clear();
	comment.append("Line Num \tpressure (dBar)\tplatform velocity (dBar/sec)\tparktime (hours)\tsampleList");
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });

	MissionData::DepthTable tableEntry;
	std::string direction;

	uint16_t numEntrys  = MissionData::getSizeOfDescendTable();
	for (int j = 0; j < 2; j++)
	{
		for (int i = 0; i < numEntrys; i++)
		{
			if (j == 0)
			{
				tableEntry = MissionData::getDescendTableEntry(i);
				direction = "Descend ";
			}
			else
			{
				tableEntry = MissionData::getAscendTableEntry(i);
				direction = "Ascend ";
			}			
			comment.clear();
			snprintf(temp,
				sizeof(temp),
				"%s%d\t%7.1f\t%6.3f\t%8.4f\t%#4X",
				direction.c_str(),
				i,
				tableEntry.pressure_dBar,
				tableEntry.platformVel_dBarPerSec,
				tableEntry.parktime_hours,
				tableEntry.sampleList);
			comment.append(temp);
			Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });
		}
		numEntrys = MissionData::getSizeOfAscendTable();
	}	
	
	return initCTD1;
}

InitPlatformState::Actions InitPlatformState::doReadConfigFile(const StateEvent event)
{
	std::string comment;
	char temp[8];
	
	ConfigData::readConfigData();
	
	comment.clear();
	comment.append("Config file SN: ");
	comment.append(ConfigData::getSN());
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });

	comment.clear();
	comment.append("Config file SW Ver Num: ");
	comment.append(ConfigData::getSWVerNum());
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });

	comment.clear();
	comment.append("Config file Surf Ops Bel Pos (pctFull): ");
	snprintf(temp, sizeof(temp), "%5.2f", ConfigData::getSurfaceOpsBelPos_pctFull());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });

	comment.clear();
	comment.append("Config file Recovery Bel Pos (pctFull): ");
	snprintf(temp, sizeof(temp), "%5.2f", ConfigData::getRecoveryBelPos_pctFull());
	comment.append(temp);
	Logger::logEngLine(true, { stmchEngLogID, RTClock::getDateTimeStampFast().data(), stateLabel, comment });

	return readMissionFile;
}

StateNames InitPlatformState::checkEvents(StateEvent event)
{
	std::cout << "InitPlatformState checkEvents"  << std::endl;
	if (hitLastAction)
		return StateNames::recovery;
	else
		return StateNames::initPlatform;
}

void InitPlatformState::enterThisState()
{
	setInitialAction(readConfigFile, actionLabels[readConfigFile]);
	
	hitLastAction = false;
}

void InitPlatformState::exitThisState(StateEvent event)
{
	std::cout << "InitPlatformState exitThisState"  << std::endl;
}


