Qt5官方Demo解析集2——Multicast Sender/Receiverz
来源:互联网 发布:金融大数据网站有哪些 编辑:程序博客网 时间:2024/05/24 06:39
本系列所有文章可以在这里查看http://blog.csdn.net/cloud_castle/article/category/2123873
在上篇博文中记录了Fortune Server/Client Example,那个例子基于Tcp传输协议的,Tcp是一种可靠协议,但是有时候我们并不在意数据包是否被成功投递,这种情况尤其出现在一些不断重复数据的发送上,比如每秒一次的温度,时间等。在这种情况下我们往往倾向使用Udp来发送和接收UDP数据报(datagram)。今天Multicast Sender/Receiver这个例子就是一个基于QUdpSocket实现的UDP组播发送。并且使用TTL(Time To Live)来控制网络开销。
按照惯例,看看官方介绍吧:
Demonstrates how to send messages to a multicast group
This example demonstrates how to send messages to the clients of a multicast group.
好了,那我们进主题,先看multicastsender文件包里面的sender.h:
#ifndef SENDER_H#define SENDER_H#include <QDialog>#include <QHostAddress>QT_BEGIN_NAMESPACEclass QDialogButtonBox;class QLabel;class QPushButton;class QTimer;class QUdpSocket;class QSpinBox;QT_END_NAMESPACEclass Sender : public QDialog{ Q_OBJECTpublic: Sender(QWidget *parent = 0);private slots: void ttlChanged(int newTtl); void startSending(); void sendDatagram();private: QLabel *statusLabel; QLabel *ttlLabel; QSpinBox *ttlSpinBox; QPushButton *startButton; QPushButton *quitButton; QDialogButtonBox *buttonBox; QUdpSocket *udpSocket; QTimer *timer; QHostAddress groupAddress; int messageNo;};#endif如果有上一篇博文的基础,这里就没什么好说的了。。。注意这个messageNo在源文件是作为计数使用,不是Nomessage,而是No.message。。。好的取名对理解程序是有很大帮助的。
sender.cpp:
#include <QtWidgets>#include <QtNetwork>#include "sender.h"Sender::Sender(QWidget *parent) : QDialog(parent){ groupAddress = QHostAddress("239.255.43.21"); //IANA网络,可以作为局域网IP statusLabel = new QLabel(tr("Ready to multicast datagrams to group %1 on port 45454").arg(groupAddress.toString())); ttlLabel = new QLabel(tr("TTL for multicast datagrams:")); // 控件布局 ttlSpinBox = new QSpinBox; ttlSpinBox->setRange(0, 255); QHBoxLayout *ttlLayout = new QHBoxLayout; ttlLayout->addWidget(ttlLabel); ttlLayout->addWidget(ttlSpinBox); startButton = new QPushButton(tr("&Start")); quitButton = new QPushButton(tr("&Quit")); buttonBox = new QDialogButtonBox; buttonBox->addButton(startButton, QDialogButtonBox::ActionRole); buttonBox->addButton(quitButton, QDialogButtonBox::RejectRole); timer = new QTimer(this); udpSocket = new QUdpSocket(this); // udpSocket在这里初始化 messageNo = 1; connect(ttlSpinBox, SIGNAL(valueChanged(int)), this, SLOT(ttlChanged(int))); connect(startButton, SIGNAL(clicked()), this, SLOT(startSending())); connect(quitButton, SIGNAL(clicked()), this, SLOT(close())); connect(timer, SIGNAL(timeout()), this, SLOT(sendDatagram())); // 重复性的数据发送,可以看到使用Udp的场合 QVBoxLayout *mainLayout = new QVBoxLayout; mainLayout->addWidget(statusLabel); mainLayout->addLayout(ttlLayout); mainLayout->addWidget(buttonBox); setLayout(mainLayout); setWindowTitle(tr("Multicast Sender")); ttlSpinBox->setValue(1);}void Sender::ttlChanged(int newTtl){ udpSocket->setSocketOption(QAbstractSocket::MulticastTtlOption, newTtl); // 这里是将网络设置成Multicast_TTL模式,第二个参数是TTL最大路由数}void Sender::startSending(){ startButton->setEnabled(false); timer->start(1000);}void Sender::sendDatagram(){ statusLabel->setText(tr("Now sending datagram %1").arg(messageNo)); QByteArray datagram = "Multicast message " + QByteArray::number(messageNo); // 这里没有使用QDataStrem,因为数据无须校验。 udpSocket->writeDatagram(datagram.data(), datagram.size(), // 调用writeDatagram函数,这里使用writeDatagram(datagram, groupAddress, 45454)也是可以的 groupAddress, 45454); ++messageNo;}Sender端代码就是这样了,是不是觉得官方demo也不难理解~
ok,继续来看receiver.h和receiver.cpp:
receiver.h:
#ifndef RECEIVER_H#define RECEIVER_H#include <QDialog>#include <QHostAddress>QT_BEGIN_NAMESPACEclass QLabel;class QPushButton;class QUdpSocket;QT_END_NAMESPACEclass Receiver : public QDialog{ Q_OBJECTpublic: Receiver(QWidget *parent = 0);private slots: void processPendingDatagrams();private: QLabel *statusLabel; QPushButton *quitButton; QUdpSocket *udpSocket; QHostAddress groupAddress;};
不用说什么了吧。
receiver.cpp:#include <QtWidgets>#include <QtNetwork>#include "receiver.h"Receiver::Receiver(QWidget *parent) : QDialog(parent){ groupAddress = QHostAddress("239.255.43.21"); // 与发送端取同样的IP地址 statusLabel = new QLabel(tr("Listening for multicasted messages")); quitButton = new QPushButton(tr("&Quit")); udpSocket = new QUdpSocket(this); udpSocket->bind(QHostAddress::AnyIPv4, 45454, QUdpSocket::ShareAddress); // 绑定了任意的IPv4地址,45454端口,并允许其他服务使用该端口 udpSocket->joinMulticastGroup(groupAddress); // 以操作系统默认接口加入Multicast网络组 connect(udpSocket, SIGNAL(readyRead()), // 数据流过来触发readyRead()信号 this, SLOT(processPendingDatagrams())); connect(quitButton, SIGNAL(clicked()), this, SLOT(close())); QHBoxLayout *buttonLayout = new QHBoxLayout; // 按钮居中 buttonLayout->addStretch(1); buttonLayout->addWidget(quitButton); buttonLayout->addStretch(1); QVBoxLayout *mainLayout = new QVBoxLayout; mainLayout->addWidget(statusLabel); mainLayout->addLayout(buttonLayout); setLayout(mainLayout); setWindowTitle(tr("Multicast Receiver"));}void Receiver::processPendingDatagrams(){ while (udpSocket->hasPendingDatagrams()) { // 是否有待处理的信号 QByteArray datagram; datagram.resize(udpSocket->pendingDatagramSize()); // 以数据包的大小初始化datagram udpSocket->readDatagram(datagram.data(), datagram.size()); // 直接读就可以了 statusLabel->setText(tr("Received datagram: \"%1\"") .arg(datagram.data())); }}Ok,今天的学习先到这里吧~
2 0
- Qt5官方Demo解析集2——Multicast Sender/Receiverz
- Qt5官方Demo解析集2——Multicast Sender/Receiverz
- Qt5官方Demo解析集3——Broadcast Sender/Receiver
- Qt5官方demo解析集6——Loopback Example
- Qt5官方demo解析集31——StocQt
- Qt5官方demo解析集35——Music Player
- Qt5官方demo解析集36——Wiggly Example
- Qt5官方demo解析集36——Wiggly Example
- Qt5官方demo解析集36——Wiggly Example
- Qt5官方demo解析集37——Vector Deformation
- Qt5官方demo解析集16——Chapter 2: Connecting to C++ Methods and Signals
- Qt5官方Demo解析集1——Fortune Server/Client
- Qt5官方Demo解析集4——Blocking Fortune Client
- Qt5官方Demo解析集5——Threaded Fortune Server
- Qt5官方Demo解析集5(总结)——Fortune例程的各个实现区别
- Qt5官方demo解析集7——Analog Clock Example
- Qt5官方demo解析集8——Shaped Clock Example
- Qt5官方demo解析集9——Analog Clock Window Example
- EJB3.0在发布时出现异常javax.naming.NameNotFoundException: myqueue not bound
- Using Padding in Encryption
- Spring3.0+Hibernate+Atomikos多数据源分布式事务管理
- 这样的智能报刊亭,真是高大上
- 有状态EJBBean和无状态的EJBBean
- Qt5官方Demo解析集2——Multicast Sender/Receiverz
- codeforces 404A - Valera and X
- EJB 3.0 + JBOSS 5.1
- SNMP监控MYSQL数据库
- List,set,Map 的用法和区别
- 移动开发工具devextreme官方视频教程
- ubuntu 12.10 LFS(1)
- Qt开发相关问题
- smtp和pop3