// 客户端
#include <opencv2/opencv.hpp>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <unistd.h>
#define HOST "127.0.0.1"
#define PORT 5000
#define BUFFER_SIZE 1024
int main() {
// 创建TCP套接字
int sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock == -1) {
perror("socket");
exit(EXIT_FAILURE);
}
// 连接到服务器
sockaddr_in address;
address.sin_family = AF_INET;
address.sin_port = htons(PORT);
if (inet_pton(AF_INET, HOST, &address.sin_addr) <= 0) {
perror("inet_pton");
exit(EXIT_FAILURE);
}
if (connect(sock, (sockaddr*) &address, sizeof(address)) == -1) {
perror("connect");
exit(EXIT_FAILURE);
}
// 打开视频文件
cv::VideoCapture cap("video.mp4");
if (!cap.isOpened()) {
perror("cap");
exit(EXIT_FAILURE);
}
// 发送视频帧
while (true) {
cv::Mat frame;
cap >> frame;
if (frame.empty()) {
break;
}
// 将图像编码为JPEG格式
std::vector<uchar> buffer;
cv::imencode(".jpg", frame, buffer);
// 发送图像大小 sizeof(size) = 4
uint32_t size = buffer.size();
int bytes_sent = send(sock, &size, sizeof(size), 0);
if (bytes_sent == -1) {
perror("send");
exit(EXIT_FAILURE);
}
// 发送图像数据
bytes_sent = send(sock, buffer.data(), buffer.size(), 0);
if (bytes_sent == -1) {
perror("send");
exit(EXIT_FAILURE);
}
}
// 清理
cap.release();
close(sock);
return 0;
}
//服务端
#include <opencv2/opencv.hpp>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <unistd.h>
#define PORT 5000
#define BUFFER_SIZE 1024
int main() {
// 创建TCP套接字
int sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock == -1) {
perror("socket");
exit(EXIT_FAILURE);
}
// 绑定套接字
sockaddr_in address;
address.sin_family = AF_INET;
address.sin_addr.s_addr = INADDR_ANY;
address.sin_port = htons(PORT);
if (bind(sock, (sockaddr*) &address, sizeof(address)) == -1) {
perror("bind");
exit(EXIT_FAILURE);
}
// 监听套接字
if (listen(sock, 1) == -1) {
perror("listen");
exit(EXIT_FAILURE);
}
// 接受客户端连接
sockaddr_in client_address;
socklen_t client_address_length = sizeof(client_address);
int client_sock = accept(sock, (sockaddr*) &client_address, &client_address_length);
if (client_sock == -1) {
perror("accept");
exit(EXIT_FAILURE);
}
// 打开窗口以显示图像
cv::namedWindow("image", cv::WINDOW_AUTOSIZE);
// 接收和显示图像
while (true) {
// 接收图像大小
uint32_t size;
int bytes_received = recv(client_sock, &size, sizeof(size), 0);
if (bytes_received == -1) {
perror("recv");
exit(EXIT_FAILURE);
}
// 接收图像数据
std::vector<uchar> buffer(size);
bytes_received = recv(client_sock, buffer.data(), buffer.size(), 0);
if (bytes_received == -1) {
perror("recv");
exit(EXIT_FAILURE);
}
// 解码图像数据
cv::Mat frame = cv::imdecode(buffer, cv::IMREAD_COLOR);
// 显示图像
cv::imshow("image", frame);
// 按ESC键退出循环
if (cv::waitKey(1) == 27) {
break;
}
}
// 清理
cv::destroyAllWindows();
close(client_sock);
close(sock);
return 0;
}
UDP发送图像数据(windows)
//send.cpp
#include <iostream>
#include <Winsock2.h>
#include <opencv2/opencv.hpp>
#include <WS2tcpip.h>
#pragma comment(lib, "ws2_32.lib")
using namespace std;
using namespace cv;
#define MAX_BUFFER_SIZE 65000
int main() {
// 初始化Winsock
WSADATA wsaData;
if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
cerr << "WSAStartup failed." << endl;
return 1;
}
// 创建UDP套接字
SOCKET udpSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (udpSocket == INVALID_SOCKET) {
cerr << "Failed to create UDP socket." << endl;
WSACleanup();
return 1;
}
// 设置服务器地址和端口
sockaddr_in m_RemoteAddress;
// 远端地址
const char* ip = "127.0.0.1";
int port = 8001;
m_RemoteAddress.sin_family = AF_INET;
m_RemoteAddress.sin_port = htons(port);
int m_RemoteAddressLen = sizeof(m_RemoteAddress);
inet_pton(AF_INET, ip, &m_RemoteAddress.sin_addr);
// 打开视频文件
VideoCapture video("C:\\Users\\mao\\Desktop\\ROV2\\1.mp4");
if (!video.isOpened()) {
cerr << "Failed to open video file." << endl;
closesocket(udpSocket);
WSACleanup();
return 1;
}
// 初始化压缩参数
std::vector<int> compression_params;
compression_params.push_back(cv::IMWRITE_JPEG_QUALITY);
compression_params.push_back(55); // 设置JPEG压缩质量,范围0-100
Mat frame;
int imgSize;
uchar buffer[MAX_BUFFER_SIZE];
while (video.read(frame)) {
// 将图像数据转换为字符数组
resize(frame, frame, cv::Size(1024, 512), 0);
// 对图像进行编码
//imencode(".jpg", frame, buf);
vector<uchar> encodedImage;
imencode(".jpg", frame, encodedImage, compression_params);
int imageSize = 0;
imageSize = encodedImage.size();
std::cout << "imageSize = " << imageSize << std::endl;
// 组合图像大小和图像数据到一个数据包
memcpy(buffer, &imageSize, sizeof(int));
memcpy(buffer + sizeof(int), encodedImage.data(), imageSize);
int image_size_Sent = sendto(udpSocket, (char*)buffer, sizeof(int) + imageSize, 0, (struct sockaddr*)&m_RemoteAddress, sizeof(m_RemoteAddress));
if (image_size_Sent < 0) {
cerr << "Error: Unable to send image size" << endl;
break;
}
}
// 关闭套接字和清理Winsock
closesocket(udpSocket);
WSACleanup();
return 0;
}
//rec.cpp
#include <winsock2.h>
#include <WS2tcpip.h>
#include <iostream>
#include <opencv2/opencv.hpp>
using namespace std;
#define MAX_BUFFER_SIZE 65000
//添加动态库的lib
#pragma comment(lib, "ws2_32.lib")
int main() {
// socket环境
WSADATA wsaData;
if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
cout << "WSAStartup error:" << GetLastError() << endl;
return false;
}
// socket对象
// 创建UDP接收端socket
SOCKET recvSocket = socket(AF_INET, SOCK_DGRAM, 0);
if (recvSocket == INVALID_SOCKET) {
cerr << "Failed to create receive socket" << endl;
WSACleanup();
return 1;
}
// 设置接收端地址
sockaddr_in recvAddr;
recvAddr.sin_family = AF_INET;
recvAddr.sin_port = htons(8001);
recvAddr.sin_addr.s_addr = htonl(INADDR_ANY);
if (::bind(recvSocket, (sockaddr*)&recvAddr, sizeof(recvAddr)) == SOCKET_ERROR) {
cerr << "Failed to bind receive socket" << endl;
closesocket(recvSocket);
WSACleanup();
return 1;
}
cv::Mat receivedImage;
while (true) {
// 接收图像大小
int imgSize;
uchar buffer[MAX_BUFFER_SIZE];
// 接收数据包
int addrLen = sizeof(recvAddr);
int bytesReceived = recvfrom(recvSocket, (char*)&buffer, MAX_BUFFER_SIZE, 0, (sockaddr*)&recvAddr, &addrLen);
std::cout << bytesReceived << std::endl;
if (bytesReceived > sizeof(int)) {
// 提取图像大小
memcpy(&imgSize, buffer, sizeof(int));
// 提取图像数据
vector<uchar> imageData(buffer + sizeof(int), buffer + sizeof(int) + imgSize);
// 解码图像数据
receivedImage = cv::imdecode(imageData, cv::IMREAD_COLOR);
// 在这里对接收到的图像进行处理,例如显示或保存到文件
imshow("Received Image", receivedImage);
cv::waitKey(1); // 等待一段时间,以便显示图像
}
}
closesocket(recvSocket);
WSACleanup();
return true;
}