

#include <iostream>
#include <vector>
#include <string>

#include "Zusi3TCP.h"
#include "DebugSocket.h"
#include "WinsockBlockingSocket.h"

void parseDataMessage(const zusi::Node& msg)
{
	if (msg.getId() == zusi::MsgType_Fahrpult)
	{
		for (const zusi::Node* node : msg.nodes)
		{
			if (node->getId() == zusi::Cmd_DATA_FTD)
			{
				for (const zusi::Attribute* att : node->attributes)
				{
					float value = *(reinterpret_cast<float*>(att->data));
					std::cout << "FS Data " << att->getId() << ": " << value << std::endl;
				}
			}
			else if (node->getId() == zusi::Cmd_DATA_OPERATION)
			{
				for (const zusi::Node* input : node->nodes)
				{
					if (input->getId() == 1)
					{
						std::cout << "Tastur Operation:" << std::endl;
						for (const zusi::Attribute* att : input->attributes)
						{
							if(att->getId() <= 0x3)
								std::cout << "    Parameter " << att->getId() << " = " << *(reinterpret_cast<uint16_t*>(att->data)) << std::endl;
							else if(att->getId() == 0x4)
								std::cout << "    Position = " << *(reinterpret_cast<int16_t*>(att->data)) << std::endl;
						}
						
					}
				}
			}
		}
	}
}

int main(int argc, char** argv)
{
	//Create a socket for message printing
	zusi::DebugSocket debug_socket;

	//Create connection to server
	try {
		zusi::WinsockBlockingSocket tcp_socket("127.0.0.1", 1436);
	
		//Subscribe to Fuehrerstand Data
		zusi::ClientConnection con(&tcp_socket);
		std::vector<zusi::FuehrerstandData> fd_ids{ zusi::Fs_Geschwindigkeit, zusi::Fs_Motordrehzahl, zusi::Fs_DruckBremszylinder };
		std::vector<zusi::ProgData> prog_ids{ zusi::Prog_SimStart };
	
		//Subscribe to receive status updates about the above variables
		//Not subscribing to input events
		con.connect("DumpFtd", fd_ids, prog_ids, true);

		std::cout << "Zusi Version:" << con.getZusiVersion() << std::endl;
		std::cout << "Connection Info: " << con.getConnectionnfo() << std::endl;

		while (true)
		{
			zusi::Node msg;
			if (con.receiveMessage(msg))
			{
				std::cout << "Received message..." << std::endl;
				msg.write(debug_socket); //Print data to the console

				parseDataMessage(msg);
				std::cout << std::endl;
			}
			else
			{
				std::cout << "Error receiving message" << std::endl;
				break;
			}
		}

	}
	catch (std::runtime_error& e)
	{
		std::cout << "Network error: " << e.what() << std::endl;
		return 1;
	}


	return 0;
}