实现功能:循环读取服务器端上的10张图片并通过网络发送到客户端,客户端实现动态显示。
代码如下:
服务器端-----------》
/*************ServerMain.cpp***************/ #include "ServerStream.h" #include <QtGui/QApplication> int main(int argc,char *argv[]) { QApplication a(argc,argv); ServerStream stream; return a.exec(); }
/**************ServerStream.h***************/ #ifndef IMAGESERVER_H_ #define IMAGESERVER_H_ #include <iostream> #include <QtNetwork/QHostAddress> #include <QtNetwork/QTcpSocket> #include <QtNetwork/QTcpServer> #include <QtGui/QImage> #include <QtCore/QThread> #include <QtGui/QWidget> class ServerStream : public QObject { Q_OBJECT private: QTcpServer server; QTcpSocket *socket; //socket对象 void initNetWork(); void delay(int len); public: ServerStream(QObject *parent=0); ~ServerStream(); QByteArray formHead(QByteArray by); public slots: void dealConnection(); }; #endif
/****************ServerStream.cpp*****************/ #include "ServerStream.h" #include <string> #include <QtCore/QFile> #include <QtCore/QThread> ServerStream::ServerStream(QObject *parent) : QObject(parent) { initNetWork(); connect(&server,SIGNAL(newConnection()),this,SLOT(dealConnection())); } ServerStream::~ServerStream(){ } //初始化网络 void ServerStream::initNetWork(){ std::cout<<"initing network..."<<std::endl; server.setParent(this); server.listen(QHostAddress::Any,8867); std::cout<<"network inited!"<<std::endl; } //当有连接时,将图片发送过去 void ServerStream::dealConnection(){ int num=0; long len=0; socket=server.nextPendingConnection(); for(num=1;num<=10;num++){ QFile file("/images/"+QString::number(num)+".jpg"); file.open(QIODevice::ReadOnly); //在Qt中,文件需要打开了才能进行操作,这点与java不同 QByteArray by; by=file.readAll(); len=by.length(); //获取数据的总长度 by.prepend(formHead(QByteArray::number((qlonglong)len))); //将要发送的数据总长度加在数据的最前10个字节中,不足的在前面补零。 len=socket->write(by); socket->flush(); std::cout<<len<<"bytes have been written!"<<std::endl; delay(7000); if(num==10) num=1; } } //将数据长度封装在10个字节的范围内,不足的在前面补零 QByteArray ServerStream::formHead(QByteArray by){ int len=by.length(); int i=0; for(i=10-len;i>0;i--){ by=by.prepend('0'); } return by; } //线程延时不能用,只好用最原始的延时方法了 void ServerStream::delay(int len){ volatile int m=0; volatile int n=0; for(m=0;m<len;m++){ for(n=0;n<len;n++); } }
客户端------------------》
/**************Main.cpp******************/ #include "ImageStream.h" #include <QtGui/QApplication> int main(int argc,char *argv[]) { QApplication a(argc,argv); ImageStream *is=new ImageStream(); is->show(); return a.exec(); }
/*****************ImageStream.h***********************/ #ifndef IMAGESTREAM_H_ #define IMAGESTREAM_H_ #include <QtGui/QWidget> #include <QtGui/QLabel> #include <iostream> #include <QtGui/QPalette> #include <QtNetwork/QHostAddress> #include <QtNetwork/QTcpSocket> class ImageStream : public QWidget{ Q_OBJECT private: QHostAddress hostAddress; //主机地址 QTcpSocket client; //socket对象 QLabel *ql_show; QByteArray imageData; //存放接收到的图片数据的QByteArray bool hasReadHead; //是否接收到了当前所接收图片的第一个数据包。 long avalibleNum; void initNetWork(); public: ImageStream(QWidget *qw=0); ~ImageStream(); void changeFace(); public slots: void getSocketImage(); //获取从服务器端传来的图片数据 }; #endif
/********************ImageStream.cpp***********************/ #include "ImageStream.h" #include <QtCore/QFile> #include <QtCore/QByteArray> ImageStream::ImageStream(QWidget *qw) : QWidget(qw){ initNetWork(); this->setGeometry(0,0,500,400); ql_show=new QLabel(this); ql_show->setGeometry(50,50,400,300); ql_show->setAutoFillBackground(true); hasReadHead=false; avalibleNum=0; } ImageStream::~ImageStream(){ } //当有数据包发送来时,解析第一个数据包并获取所有数据包的总长度,获取的第二个以上的数据包不做此处理。 void ImageStream::getSocketImage(){ if(!hasReadHead){ imageData.clear(); //第一个数据包发来时,先清空存储图片数据的空间 QByteArray by=client.readAll(); avalibleNum=by.left(10).toLong(); //找出第一个数据包的前10个字节,由此获得数据总长度。 by.remove(0,10); //移除前10个字节 imageData.append(by); hasReadHead=true; if(imageData.length()>=avalibleNum){ //判断数据是否接收完毕 std::cout<<"receive a image,length="<<avalibleNum<<std::endl; changeFace(); hasReadHead=false; } }else{ QByteArray by=client.readAll(); imageData.append(by); if(imageData.length()>=avalibleNum){ //判断数据是否接收完毕 std::cout<<"receive a image,length="<<avalibleNum<<std::endl; changeFace(); hasReadHead=false; } } } void ImageStream::changeFace(){ QPalette palette; QImage image=QImage::fromData(imageData,"jpg"); palette.setBrush(QPalette::Background, QBrush(image)); ql_show->setPalette(palette); } void ImageStream::initNetWork(){ std::cout<<"initing network"<<std::endl; hostAddress.setAddress("172.23.33.61"); client.setParent(this); client.connectToHost(hostAddress, 8867); connect(&client,SIGNAL(readyRead()),this,SLOT(getSocketImage())); std::cout<<"network inited!"<<std::endl; client.setReadBufferSize(1024*1024); }
(--------------完---------------)