
#pragma once

#include "mqtt/subcriber.hpp"
#include "mqtt/publisher.hpp"
#include "uart/uart.hpp"
#include "3th-part/json.hpp"
#include <queue>

struct traffic_light_config
{
    /* data */
    uint16_t id;
    std::string type;
    std::vector<uint16_t> do_addr;
    std::vector<std::string> color;
};

struct roadside_info_config
{
    std::string id;
    std::string topic;
    double longitude;
    double latitude;
    double altitude;
    uint32_t isLight;
};


struct traffic_light_status_config
{
    /* data */
    uint16_t id;
    std::string color;
};

struct traffic_mode_config
{
    uint16_t id;
    std::vector<traffic_light_status_config> lights;
};


class BarrierGateControl
{
public:
    BarrierGateControl(nlohmann::json& config,const std::map<int, std::string>& numbarrier_info_config_map);
    BarrierGateControl(nlohmann::json& config, const std::map<int, std::string>& numbarrier_info_config_map, const std::string& command);
    ~BarrierGateControl();

    void exec();

    enum GateState
    {
        UNKNOWN = 0,
        ON = 1,
        PAUSE = 2,
        OFF = 3,
    };

    struct roadside_info_barrier
    {
        int Id;
        GateState gatestate;
    };

    const GateState cvt_gate_status(const std::string& status);
    const std::string cvt_gate_status(const GateState& status);
    const std::string cvt_gate_status(const uint16_t& status);

    void gate_control(const int channel, const GateState state);

    void Exc_Barrier(int stateCode,uint16_t changeCode );

private:
    void init();

    const std::string self_id;
    const std::string uart_name_;
    const std::string report_topic_;
    const std::string control_topic_;
    const std::string command_ = "off";

    std::shared_ptr<awe::Uart> uart_;

    GateState current_gate_=GateState::OFF;

    std::shared_ptr<mqtt_dataio::publisher<mqtt_dataio::subscriber_basic::DataBuffer>> __m_status_puber;
    std::shared_ptr<mqtt_dataio::subscriber<mqtt_dataio::subscriber_basic::DataBuffer>> __m_control_suber;

    void on_control_request(const mqtt_dataio::subscriber_basic::DataBuffer& msg);

private:
    bool __m_running;

    uint8_t __m_expand_size;
    uint16_t __m_offset_do_addr;
    std::map<int, std::string> numbarrier_config_map;
    std::queue<BarrierGateControl::roadside_info_barrier>curExcBarrierQueue;
};
