首先是服务端,在构造函数中实例化UDP,并且创建成员函数进行发送,通过QTIMER类以10HZ的频率发送;
//udpserver.h
#ifndef UDPSERVER_H
#define UDPSERVER_H
#include <QUdpSocket>
#include <QHostAddress>
#include <QTimer>
#pragma pack(push, 1) // 设置字节对齐为1字节
struct MyStruct {
quint16 checksum;
quint16 data1;
quint32 data2;
};
#pragma pack(pop) // 恢复字节对齐设置
class MyUDP : public QObject
{
Q_OBJECT
public:
explicit MyUDP(QObject *parent = 0);
private:
QUdpSocket *socket;
QTimer *timer;
public slots:
void SayGps();
};
#endif // UDPSERVER_H
//udpserver.cpp
#include "udpserver.h"
MyUDP::MyUDP(QObject *parent) :
QObject(parent)
{
socket = new QUdpSocket(this);
timer = new QTimer(this);
connect(timer,&QTimer::timeout,this,&MyUDP::SayGps);//通过信号与槽触发
timer->start(100);//100ms发送一次
}
void MyUDP::SayGps()
{
// 准备要发送的结构体数据
MyStruct myStruct;
myStruct.checksum = 0x1234; // 设置结构体第一个参数的检验位
myStruct.data1 = 1234;
myStruct.data2 = 567890;
socket->writeDatagram(reinterpret_cast<const char *>(&myStruct), sizeof(MyStruct),
QHostAddress::LocalHost, 1234);
}
//main.cpp
#include "udpserver.h"
#include <QCoreApplication>
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
MyUDP server;
return a.exec();
}
客户端接收代码,将客户端的一个类放入子线程。如需增加线程,接收其他端口的数据,可新实例化一个新的MyUDP类,并且修改端口号即可;
//udpclient.h
#ifndef UDPCLIENT_H
#define UDPCLIENT_H
#include <QUdpSocket>
#include <QHostAddress>
#pragma pack(push, 1) // 设置字节对齐为1字节
struct MyStruct {
quint16 checksum;
quint16 data1;
quint32 data2;
};
#pragma pack(pop) // 恢复字节对齐设置
class MyUDP : public QObject
{
Q_OBJECT
public:
explicit MyUDP(QObject *parent = 0);
private:
QUdpSocket *socket;
public slots:
void receiveDatagram();
};
#endif // UDPCLIENT_H
//udpclient.cpp
#ifndef UDPCLIENT_CPP
#define UDPCLIENT_CPP
#include "udpclient.h"
MyUDP::MyUDP(QObject *parent) :
QObject(parent)
{
socket = new QUdpSocket(this);
bool result = socket->bind(1234);
}
void MyUDP::receiveDatagram()
{
QByteArray buffer;
buffer.resize(socket->pendingDatagramSize());
socket->readDatagram(buffer.data(), buffer.size());
MyStruct receivedStruct;
memcpy(&receivedStruct, buffer.constData(), sizeof(MyStruct));
if (receivedStruct.checksum == 0x1234) {
qDebug() << "Received data1:" << receivedStruct.data1;
qDebug() << "Received data2:" << receivedStruct.data2;
} else {
qDebug() << "Checksum mismatch, discarding received data.";
}
}
#endif // UDPCLIENT_CPP
//main.cpp
#include <QCoreApplication>
#include <QObject>
#include <QTimer>
#include "udpclient.h"
#include <qthread.h>
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
MyUDP myUDP;
QThread thread_0;// 创建一个线程
// 将myUDP对象移动到子线程中
myUDP.moveToThread(&thread_0);
// 连接Worker对象的sendDatagram()槽和QTimer对象的timeout()信号
QTimer timer;
QObject::connect(&timer, &QTimer::timeout, &myUDP, &MyUDP::receiveDatagram);
// 启动子线程
thread_0.start();
// 启动定时器
timer.start(100);
return a.exec();
}