//
// Created by huli on 2020/9/25.
//

#include "snap7_clamp.h"

Snap7Clamp::Snap7Clamp() = default;
Snap7Clamp::~Snap7Clamp() = default;

//初始化 通信 模块。如下三选一
Error_manager Snap7Clamp::communication_init()
{
	int t_index = 0;
	std::vector<Snap7_buf::Variable_information>		t_variable_information_vector;

	//往map通信缓存里面添加所需要的buf
	std::unique_lock<std::mutex> t_lock1(m_receive_buf_lock);
	std::unique_lock<std::mutex> t_lock2(m_send_buf_lock);
	Snap7_buf t_snap7_buf;

    // plcData
    t_index = 0;
    t_variable_information_vector.clear();
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"pingpong", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"wheel_exist", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"offset", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"gap", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"clamp_completed", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"wheel_exist", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"offset", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"gap", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"clamp_completed", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"wheel_exist", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"offset", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"gap", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"clamp_completed", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"wheel_exist", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"offset", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"gap", typeid(float ).name(), t_index,sizeof(float), 1 });
    t_index += sizeof(float)*1;
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"clamp_completed", typeid(unsigned short ).name(), t_index,sizeof(unsigned short), 1 });
    t_index += sizeof(unsigned short)*1;

    LOG(INFO) << t_index;

    t_snap7_buf.init(CLAMP_SAFETY_PLC_DBNUMBER , 0, sizeof(PLCData), t_variable_information_vector, Snap7_buf::LOOP_COMMUNICATION);
	m_send_buf_map[0] = t_snap7_buf;

    t_index = 0;
    t_variable_information_vector.clear();
    t_variable_information_vector.push_back(Snap7_buf::Variable_information{"warning", typeid(unsigned short).name(), t_index,sizeof(unsigned short), 1 });

    t_snap7_buf.init(CLAMP_SAFETY_HEART_DBNUMBER , 0, sizeof(unsigned short), t_variable_information_vector, Snap7_buf::LOOP_COMMUNICATION);
    m_receive_buf_map[0] = t_snap7_buf;

    plcJsonConfig config(ETC_PATH"ClampSafety/plc.json");
    return Snap7_communication_base::communication_init(config.ip());
    return SUCCESS;
}

//反初始化 通信 模块。
Error_manager Snap7Clamp::communication_uninit()
{
	return Snap7_communication_base::communication_uninit();
}

Error_manager Snap7Clamp::setCloudData(const unsigned char &device, pcl::PointCloud<pcl::PointXYZ>::Ptr cloud) {
    if ((m_save_cloud_flag & device) == 0) {
        return {};
    } else {
        m_save_cloud_flag & (~device);
    }

    std::string file = "./log/save_cloud/" + std::to_string(device) + "/" +
                        std::to_string(std::chrono::system_clock::now().time_since_epoch().count()) + ".txt";
    FILE* pf=fopen(file.c_str(),"w");
    for (auto &point: cloud->points) {
        fprintf(pf,"%.3f %.3f %.3f\n",point.x,point.y,point.z);
    }
    fclose(pf);

    return {};
}

//更新数据
Error_manager Snap7Clamp::updata_receive_buf()
{
	std::unique_lock<std::mutex> t_lock1(m_receive_buf_lock);
	std::unique_lock<std::mutex> t_lock2(m_data_lock);
    unsigned char warn;
    memcpy(&warn, m_receive_buf_map[0].mp_buf_obverse, m_receive_buf_map[0].m_size);

    m_save_cloud_flag = (~m_warn_record) & warn;
    m_warn_record = warn;
    if (warn > 0) {
        LOG(WARNING) << "Get warning: " << warn;
    }

	return {};
}

Error_manager Snap7Clamp::updata_send_buf()
{
	std::unique_lock<std::mutex> t_lock1(m_send_buf_lock);
	std::unique_lock<std::mutex> t_lock2(m_data_lock);

    if (plcData.pingpong != 0) {
        plcData.info();
    }

	memcpy(m_send_buf_map[0].mp_buf_obverse, &plcData, m_send_buf_map[0].m_size);

    return Error_code::SUCCESS;
}




