#ifndef __SIMCONTROL__
#define __SIMCONTROL__

#include "DirectCommunicationClient.hpp"
#include "DirectCommunicationServer.hpp"
#include "SimControl/Tracklist.hpp"
#include "SimCore/Identifier.hpp"
#include "WHISPER/InternalUDPListener.hpp"
#include "crossguid/guid.hpp"
#include "ixwebsocket/IXConnectionState.h"
#include "ixwebsocket/IXWebSocketMessage.h"
#include "ixwebsocket/IXWebSocketServer.h"
#include "kubecontrol/PodController.hpp"
#include <iostream>

#include <ixwebsocket/IXWebSocket.h>

#include <atomic>
#include <cstdint>
#include <memory>
#include <string>
#include <sys/types.h>
#include <thread>
#include <mutex>
#include <queue>




namespace SimControl {


class SimControl{
   
    public: 
        SimControl(bool online, std::string CommandPort,std::string GroundTruthAddr = "239.0.0.1", ushort GroundTruthPort = 10000, std::string Namespace = "simulator");
        ~SimControl();
        void stop();
        
    private:
    bool online_;

    const SimCore::Identifier ID_;
    std::string CommandPort_;

    std::string GroundTruthAddr_;
    ushort GroundTruthPort_;
    std::string Namespace_;

    void MainFunction_();

    void HandleMessage(std::string msg);

    void HandleTCPMessage(std::string msg);


    void startShip(std::string name);
    void updateShip(nlohmann::json request);
    void deleteShip(nlohmann::json request);

    void startWebApp(); 

    void startWebsocketServer();
    void HandleWebsocketMessages(std::shared_ptr<ix::ConnectionState> connectionState, ix::WebSocket &websocket, const ix::WebSocketMessagePtr &msg);
    void HandleBroadcastMessage(std::string msg); 

    std::unique_ptr<kubecontrol::PodController> PodController_;
    std::unique_ptr<TrackList> Tracklist_;

    std::thread MainThread_;    
    std::atomic<bool> stopMainThread_ = false;

    std::shared_ptr<DirectCommunication::DirectCommunicationClient> TCPClient_ = nullptr;    
    std::shared_ptr<DirectCommunication::DirectCommunicationServer> ExternalTCPServer_ = nullptr; 



    std::thread WebsocketThreadThread_;    
    std::atomic<bool> stopWebsocketThreadThread_ = false;
    int port = 9999;
    std::string host = "0.0.0.0";
    std::shared_ptr<ix::WebSocketServer> WebsocketServer_ = nullptr;   

    std::shared_ptr<WHISPER::InternalUDPListener> BroadcastListener_;  



};




}





#endif