Qt 的TCP网络通信

 

Qt网络通信:

Socket 通信:

Qt 中提供的所有的 Socket 类都是非阻塞的。

Qt 中常用的用于Socket 通信的套接字类

QTCPServer:用于TCP/IP 通信,作为服务器端套接字使用。

QTCPSocket:用于TCP/IP 通信,作为客户端套接字使用。

QUDPSocket:用于UDP通信,服务器,客户端均使用此套接字。

 

TCP/IP:

在Qt 中实现TCP/IP 服务器端通信的流程:

(1)创建套接字;(2)将套接字设置为监听模式;(3)等待并接受客户的需求;[可以通过QTCPServer 提供的void newConnection() 信号来检测是否有连接请求,如果有可以在对应的槽函数中调用nextPendingconnection()函数获取到客户端的Socket 信息(返回值为QTCPSocket*类型指针),通过此套接字与客户端之间进行通信。];(3)接收或者向客户端发送数据 [① 接收数据:使用read() 或者readAll() 函数;② 发送数据:使用write()函数]

客户端通信流程:

(1)创建套接字;(2)连接服务器 [可以使用QTCPSocket 类的connectionToHost() 函数来连接服务器];(3)向服务器发送或者接收数据

在开始之前 ServerTCP.pro:(项目名称为ServerTCP)

添加如下代码:

Qt 的TCP网络通信_第1张图片

Qt 的TCP网络通信_第2张图片

服务器端:

Qt 的TCP网络通信_第3张图片

添加Client 客户端的文件:

右键项目名称 -> 添加新文件 -> 

Qt 的TCP网络通信_第4张图片

Qt 的TCP网络通信_第5张图片

Qt 的TCP网络通信_第6张图片

Qt 的TCP网络通信_第7张图片

客户端:

Qt 的TCP网络通信_第8张图片

在服务器端和客户端的textEditRead 栏中将其设置为 “只读”

Qt 的TCP网络通信_第9张图片

Qt 的TCP网络通信_第10张图片

服务器端:

点击ui的Send 和Close的按钮:右键 -> 转到槽;

客户端:

点击ui的Send 、Close和 connect的按钮:右键 -> 转到槽;

 

代码段:

服务器:

Serverwidget.h

Qt 的TCP网络通信_第11张图片

#ifndef SERVERWIDGET_H
#define SERVERWIDGET_H

#include 
#include  //监听套接字
#include  //通信套接字

#include 
namespace Ui {
class ServerWidget;
}

class ServerWidget : public QWidget
{
    Q_OBJECT

public:
    explicit ServerWidget(QWidget *parent = 0);
    ~ServerWidget();
protected:
    void paintEvent(QPaintEvent *event);

private slots:
    void on_send_clicked();

    void on_close_clicked();

private:
    Ui::ServerWidget *ui;

    QTcpServer *tcpServer;//监听套接字
    QTcpSocket *tcpSocket;//通信套接字

};

#endif // SERVERWIDGET_H

 

Serverwidget.cpp

#include "serverwidget.h"
#include "ui_serverwidget.h"
#include 

ServerWidget::ServerWidget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::ServerWidget)
{
    ui->setupUi(this);
    tcpServer = NULL;
    tcpSocket = NULL;

    setWindowTitle("服务器端");
    //监听套接字,指定父对象,让其自动回收空间
    tcpServer = new QTcpServer(this);
    tcpServer->listen(QHostAddress::Any,666);
    connect(tcpServer,&QTcpServer::newConnection,
            [=]()
            {
                //取出建立好连接的套接字
                tcpSocket = tcpServer->nextPendingConnection();

                //获取对方的IP和端口
                QString ip = tcpSocket->peerAddress().toString();
                qint16 port = tcpSocket->peerPort();
                QString temp = QString("[%1:%2]:成功链接").arg(ip).arg(port);
                ui->textEditRead->setText(temp);

                connect(tcpSocket,&QTcpSocket::readyRead,
                        [=]()
                        {
                            //从通信套接字中取出内容
                            QByteArray array = tcpSocket->readAll();
                            ui->textEditRead->append(array);
                        }
                        );
            }
            );

}

ServerWidget::~ServerWidget()
{
    delete ui;
}

void ServerWidget::on_send_clicked()
{
    //获取编辑区内容
    if(NULL == tcpSocket)
    {
        return;
    }
    QString str = ui->textEditWrite->toPlainText();
    //给对方发送数据,使用套接字是TCPSocket
    tcpSocket->write(str.toUtf8().data());
}


void ServerWidget::on_close_clicked()
{
    //主动和客户端断开连接
    if(NULL == tcpSocket)
    {
        return;
    }
    tcpSocket->disconnectFromHost();
    tcpSocket->close();
    tcpSocket = NULL;
}
void ServerWidget::paintEvent(QPaintEvent *event)
{
    QPainter p(this);
    p.drawPixmap(0,0,width(),height(),QPixmap(":/new/prefix1/Image/1.jpg"));
}

客户端:

clientwidget.h

Qt 的TCP网络通信_第12张图片

#ifndef CLIENWIDGET_H
#define CLIENWIDGET_H

#include 
#include //通信套接字

namespace Ui {
class ClienWidget;
}

class ClienWidget : public QWidget
{
    Q_OBJECT

public:
    explicit ClienWidget(QWidget *parent = 0);
    ~ClienWidget();
protected:
    void paintEvent(QPaintEvent *event);

private slots:
    void on_pushButtonConnect_clicked();

    void on_pushButtonSend_clicked();

    void on_pushButtonClose_clicked();

private:
    Ui::ClienWidget *ui;
    QTcpSocket *tcpsocket;//通信套接字
};

#endif // CLIENWIDGET_H

clientwidget.cpp

#include "clienwidget.h"
#include "ui_clienwidget.h"
#include 
#include 
ClienWidget::ClienWidget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::ClienWidget)
{
    ui->setupUi(this);

    ui->textEditRead->setStyleSheet("background-image:url(:/new/prefix1/Image/5C74F1D9198348410F91F4EA3EAD6FB2.jpg);");
    ui->textEditWrite->setStyleSheet("background-image:url(:/new/prefix1/Image/8A141585F1E8C5BD63F80D15DB9826E2.jpg)");

    tcpsocket = NULL;

    //分配空间,指定父对象
    tcpsocket = new QTcpSocket(this);
    setWindowTitle("客户端");

    connect(tcpsocket,&QTcpSocket::connected,
            [=]()
            {
                ui->textEditRead->setText("成功和服务器建立好链接");

            }
            );
    connect(tcpsocket,&QTcpSocket::readyRead,
            [=]()
            {
                //获取对方发送的内容
                QByteArray array = tcpsocket->readAll();
                //追加到编辑区中
                ui->textEditRead->append(array);
            }
            );

}

ClienWidget::~ClienWidget()
{
    delete ui;
}



void ClienWidget::on_pushButtonConnect_clicked()
{
    //获取服务器端口和IP
    QString ip = ui->lineEditIP->text();
    qint16 port = ui->lineEditPort->text().toInt();
    //主动和服务器建立连接
    tcpsocket->connectToHost(QHostAddress(ip),port);
}

void ClienWidget::on_pushButtonSend_clicked()
{
    //获取编辑框内容
    QString str = ui->textEditWrite->toPlainText();
    //发送数据
    tcpsocket->write(str.toUtf8().data());
}

void ClienWidget::on_pushButtonClose_clicked()
{
    //主动和对方断开连接
    tcpsocket->disconnectFromHost();
    tcpsocket->close();
}

void ClienWidget::paintEvent(QPaintEvent *event)
{
    QPainter p(this);
    p.drawPixmap(0,0,width(),height(),QPixmap(":/new/prefix1/Image/bk.jpg"));
}

 

添加资源:

右击项目 -> 添加新文件 -> 

Qt 的TCP网络通信_第13张图片

Qt 的TCP网络通信_第14张图片

项目会出现 Resources -> image.qrc 右击 -> open in Editor

效果:

点击连接后:

Qt 的TCP网络通信_第15张图片

Qt 的TCP网络通信_第16张图片

课外了解

Qt TCP 网络通信的结构:

 

Qt 的TCP网络通信_第17张图片

 

你可能感兴趣的:(Qt)