使用SOCKET TCP OPENCV 发送视频 mat格式及jpg格式

SERVER SEND jpg

//常头文件
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>

//socket相关头文件
#include <sys/socket.h>
#include <arpa/inet.h>
#include <csignal>
#include "Mat2Img.h"			//自编头文件,注意带上

//opencv相关头文件
#include <opencv2/opencv.hpp>


const int PORT = 5678;                //端口号,客户端应与之保持一致

struct sockaddr_in server_addr, client_addr; //定义服务端和客户端的地址结构体

const int Width = 640;  //图片的宽
const int Heigth = 480; //图片的高

int connectfd;      //用于传输的socketID
int sockfd;         //初始化socketID

int SendImage(const cv::Mat &mat, int sockfd); //发送图像

void InitAddr( );				//初始化函数

int main(int argc, char **argv)
{
   

    cv::VideoCapture capture(0);	//初始化摄像头
    cv::Mat cap;			//初始化摄像头mat数组
    cv::Mat image;			//初始化发送mat数组
    int ret=1;
    InitAddr(); //初始化TCP连接,并将地址结构体绑定到套接字上

    while (true)
    {
   
        capture >> cap;
        cv::resize(cap,image,cv::Size(Width,Heigth));	
        cv::imshow("local image", image);		//本地显示,可注释掉
        cv::waitKey(10);				//本地显示,可注释掉
        ret = SendImage(image,connectfd);		//发送图像
        if (ret == -1)					//如发送失败,关闭socket重新初始化
        {
   
		close(connectfd);
		InitAddr();
        }
    }
    return 0;
}

void InitAddr(void)
{
   
    char client_IP[1024];
    signal(SIGPIPE,SIG_IGN);
    //创建套接字
    sockfd = socket(AF_INET, SOCK_STREAM, 0); //TCP传输
    if (sockfd == -1)
    {
   
        perror("socket error");
        exit(EXIT_FAILURE);
    }

    bzero(&server_addr, sizeof(server_addr));
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(PORT);
    server_addr.sin_addr.s_addr = htonl(INADDR_ANY);

    //设置端口复用
    int opt = 1;
    setsockopt(sockfd, SOL_SOCKET, SO_REUSEPORT, &opt, sizeof(opt));

    //bind
    int ret = bind(sockfd, (struct sockaddr *)&server_addr, sizeof(server_addr));
    if (ret == -1)
    {
   
        perror("bind errno");
        exit(1);
    }

    //listen
    ret = listen(sockfd, 10);
    if (ret == -1)
    {
   
        perror("listen errno");
        exit(1);
    }

    //accept
    //阻塞等待客户端的连接请求
    bzero(&client_addr, sizeof(client_addr));
    socklen_t client_len = sizeof(client_addr);
    std::cout<<"wait"<<std::endl;
    connectfd = accept(sockfd, (struct sockaddr *)&client_addr, &client_len);
    if (connectfd == -1)
    {
   
        perror("accept errno");
        exit(1);
    }
    //打印客户端的IP地址和端口号
    printf("client ip:%s port:%d\n",
           inet_ntop(AF_INET, &client_addr.sin_addr.s_addr, client_IP, 1024),
           ntohs(client_addr.sin_port));

    //此时就可以读取connectfd中的数据
}


int SendImage(const cv::Mat &mat, int sockfd)
{
   
    // Mat 转化为jpg
	std::vector<unsigned char> buff_jpg;
	int ret = Mat2Img::MatToByteArray(mat, buff_jpg);
    // jpg 转化为Base64
	std::string str = ImageBase64::encode(buff_jpg.data(), buff_jpg.size());

    // 发送base64 长度  
    unsigned long count=0;
    count = str.size();
    int req = send (sockfd, &count, 4, MSG_NOSIGNAL);
    if(req == -1)
    {
   
        return -1;
    }
        
    // 发送base64 数据
    
    req = send (sockfd, str.c_str(), str.size(), MSG_NOSIGNAL);
    
    if(req == -1)
    {
   
        return -1;
    }
    return 1;
    
  
}

client receive jpg

//常用头文件
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>

//socket相关头文件
#include <sys/socket.h>
#include <arpa/inet.h>
#include "Mat2Img.h"			//自编jpg发送头文件,注意带上

//opencv相关头文件
#include <opencv2/opencv.hpp>

const int PORT = 5678;          	//端口号,应与server保持一致
const char *IP = "127.0.0.1"; 	//服务器IP地址,服务器在本机使用127.0.0.1
struct sockaddr_in server_addr;        //定义服务端的地址结构体

const int Width = 640;  //图片的宽 不需要
const int Heigth = 480; //图片的高 不需要


cv::Mat GetImage(
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值