美文网首页
opencv显示激光扫描的地图 服务端(字符串传输图像数据,仅供

opencv显示激光扫描的地图 服务端(字符串传输图像数据,仅供

作者: 送分童子笑嘻嘻 | 来源:发表于2020-02-28 11:36 被阅读0次

    cmakelist

    set(CMAKE_CXX_STANDARD 11)
    set(CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS} -lboost_system)
    find_package(Boost REQUIRED)
    find_package(OpenCV REQUIRED)
    find_package(Threads REQUIRED)
    

    include <iostream>

    include <boost/asio.hpp>

    include <vector>

    include <thread>

    include <opencv2/opencv.hpp>

    include <boost/thread/mutex.hpp>

    include <iostream>

    include <fstream>

    include <sstream>

    using namespace std;
    using namespace cv;

    vector<string> getdata_string;
    vector<string> trajectory_string;
    Mat oldphoto;

    //地图数据字符串分割函数,
    std::vector<int> split(std::string str, std::string pattern) {
    std::string::size_type pos;
    std::vector<int> result;
    str += pattern;//扩展字符串以方便操作
    int size = str.size();
    //解压的像素的苏亮
    int increate_number = 0;
    //上次有效的像素值
    int last_pixel = -1;
    for (int i = 0; i < size; i++) {
    pos = str.find(pattern, i);

        if (pos < size) {
            std::string s = str.substr(i, pos - i);
            int number = 0;
            number = atoi(s.c_str());
            if (number > 1000 && number < 10000) {
                increate_number = number - 1000;
                for (int j = 0; j < increate_number; ++j) {
                    result.push_back(last_pixel);
                }
            } else {
                increate_number = 0;
                result.push_back(number);
                last_pixel = number;
            }
            i = pos + pattern.size() - 1;
        }
    }
    return result;
    

    }

    //轨迹点数据分割
    std::vector<float> split_trajectory(std::string str, std::string pattern) {
    std::string::size_type pos;
    std::vector<float> result;
    str += pattern;//扩展字符串以方便操作
    int size = str.size();
    for (int i = 0; i < size; i++) {
    pos = str.find(pattern, i);

        if (pos < size) {
            std::string s = str.substr(i, pos - i);
            float number = 0;
            number = atof(s.c_str());
            //剔除掉错误数据
            result.push_back(number);
        }
        i = pos + pattern.size() - 1;
    }
    return result;
    

    }

    void getData() {
    using namespace boost::asio;

    //mutex.lock();//锁
    // 所有asio类都需要io_service对象
    io_service iosev;
    ip::tcp::acceptor acceptor(iosev, ip::tcp::endpoint(ip::tcp::v4(), 8888));
    //上一次拼接成的字符串
    string old_string;
    
    for (;;) {
        // socket对象
        ip::tcp::socket socket(iosev);
        boost::mutex mutex;
        // 等待直到客户端连接进来
        acceptor.accept(socket);
        // 显示连接进来的客户端
        //std::cout << socket.remote_endpoint().address() << std::endl;
        vector<uint32_t> image;
        boost::system::error_code ec;
        char get[6000];
        //ofstream outfile("/home/cai/bag/test1218bag/iamge_data.txt", std::ios::app);
        size_t len = socket.read_some(buffer(get), ec);
        // outfile << get << "\n";
        // std::cout << get << std::endl;
        string get_s_string = get;
        //std::cout << "get_s_string=" << get_s_string << std::endl;
    

    //判断是trajectory数据还是图像分包的数据
    string is_traject = get_s_string.substr(6, 1);
    if (is_traject == "t") {
    //得到数据两
    string number_data_str = get_s_string.substr(0, 5);
    stringstream segm_ss_s;
    int number_data_int;
    segm_ss_s << number_data_str;
    segm_ss_s >> number_data_int;
    //分离出没带有标签的数据
    string get_string = get_s_string.substr(6, number_data_int - 20000);
    trajectory_string.push_back(get_string);
    socket.close();
    continue;
    }
    //std::cout<<"get2="<<get <<std::endl;
    //得到数据量
    string number_data_str = get_s_string.substr(0, 5);
    stringstream segm_ss_s;
    int number_data_int;
    segm_ss_s << number_data_str;
    segm_ss_s >> number_data_int;
    //分离出没带有标签的数据
    string get_string = get_s_string.substr(6, number_data_int - 20000);
    string segm_string = get_string.substr(0, 5);
    //std::cout << "get_string=" << get_string << std::endl;
    stringstream segm_ss;
    int segm_int;
    segm_ss << segm_string;
    segm_ss >> segm_int;
    int result_int = segm_int - 10000;
    //如果这个数大于1 那这个包一定是起始位置的包
    if (result_int > 1) {
    //尺寸太小,说明之前没数据,就不放进去了
    if (old_string.size() > 10) {
    getdata_string.push_back(old_string);
    //std::cout << "old_string=" << old_string << std::endl;
    }
    old_string = get_string;
    } else {
    old_string.append(get_string);
    }
    // mutex.unlock();//解锁
    //std::this_thread::sleep_for(std::chrono::milliseconds(100));
    socket.close();
    }
    }

    int main(int argc, char *argv[]) {
    int show_time = 2000;
    //开启一个线程
    std::thread t(getData);
    int photo_index = 0;
    while (1) {
    if (getdata_string.size() <= photo_index) {
    if (photo_index > 0) {
    imshow("dst", oldphoto);
    waitKey(show_time);
    continue;
    } else {
    continue;w
    }
    }
    string get = getdata_string.at(photo_index);
    //std::cout<<trajectory_string.size() <<std::endl;
    string get_trajectory = trajectory_string.at(photo_index);
    std::cout<<get_trajectory <<std::endl;
    //std::cout << get << std::endl;
    std::vector<int> image_vector;
    std::vector<float> trajectory_vector;
    //每隔1.5秒更新一次图片
    image_vector = split(get, "=");
    trajectory_vector = split_trajectory(get_trajectory, "=");
    //在数据传输协议里面已定义第2个为width,第3个为height,第一应该是"outfile_big_graph: "被spilit方法设置为0了
    int width = image_vector[3];
    int height = image_vector[2];
    int name_int = image_vector[1];
    int segmentation = image_vector[0];
    string name_string = to_string(name_int);
    image_vector.erase(image_vector.begin(), image_vector.begin() + 3);

        //trajectory数据处理
        int origin_x = trajectory_vector[2];
        int origin_y = trajectory_vector[3];
        std::cout<<origin_x<<"_"<<origin_y <<std::endl;
        trajectory_vector.erase(trajectory_vector.begin(), trajectory_vector.begin() + 4);
    
        cv::Mat src = Mat::zeros(height, width, CV_8UC1);
        //上次的灰度值
        for (int i = 0; i < height; ++i) {
            for (int j = 0; j < width; ++j) {
                int Gray = image_vector[i * width + j];
                src.at<uchar>(i, j) = (uchar) Gray;
            }
        }
        Mat imgRGB;
        cvtColor(src, imgRGB, COLOR_GRAY2RGB);
        //绘制轨迹点
        std::cout<<"trajectory_vector.size()" <<trajectory_vector.size()<<std::endl;
        for (int k = 0; k < trajectory_vector.size() / 2; ++k) {
            //奇数位是x值,偶数位是y值
            float x = trajectory_vector.at(k*2);
            float y = trajectory_vector.at(k*2 + 1);
    
            float x2 = x * 10+origin_x;
            float y2 = y * -10+origin_y;
            std::cout <<"trajectory x="<< x2 << ",y=" << y2 << std::endl;
            cv::circle(imgRGB,Point(y2,x2),1,cv::Scalar(255,0,0),-1);
        }
    
        int new_width = width * 4;
        int new_height = height * 4;
        //resize(src, dst, cv::Size(new_width, new_height));
        cv::Mat dst;
        resize(imgRGB, dst, cv::Size(800, 800));
        //imshow(name_string, dst);
        oldphoto = dst;
        imshow("dst", oldphoto);
        photo_index++;
        waitKey(show_time);
    }
    return 0;
    

    }

    相关文章

      网友评论

          本文标题:opencv显示激光扫描的地图 服务端(字符串传输图像数据,仅供

          本文链接:https://www.haomeiwen.com/subject/qcbkhhtx.html