qt5之網絡通訊

QT5 TCP網絡通信

  • 服務器與客戶端創建鏈接listen() - connectToHost();  觸發newPendingConnect信號
  • 實時數據通信write(); read();  觸發readyRead信號
  • 通信主要使用的類:
  • QTcpServer  Class

    QTcpServer類提供了一個基於TCP的服務器。
    這個類能夠接受傳入的TCP鏈接。您能夠指定端口或讓QTcpServer自動選擇一個端口。您能夠收聽特定地址或全部機器的地址。
    調用listen()讓服務器偵聽傳入的鏈接。每次客戶端鏈接到服務器時,都會發出newConnection()信號。
    html

  • QTcpSocket Class

    QTcpSocket類提供了一個TCP套接字。
    TCP(傳輸控制協議)是一種可靠的,面向流的,面向鏈接的傳輸協議。 它特別適合連續傳輸數據。
    QTcpSocket是QAbstractSocket的一個方便的子類,它容許你創建一個TCP鏈接並傳輸數據流。
    服務器

  • 創建鏈接:

    服務器端以監聽的方式監聽客服端是否有鏈接請求網絡

    客戶端以調用connectToHost()函數主動鏈接服務器端併發

  • tcp協議服務器端實現流程

    創建服務器對象app

    listen服務器, 經過創建的服務器 監聽指定地址/端口的客服端;判斷是否有客戶鏈接有鏈接就觸發newConnection();socket

  •  

    經過connect處理newConnection()信號;
    server = new QTcpServer(this); //創建一個服務器對象
        server->listen(QHostAddress::Any, 8000);//經過創建的服務器監聽指定ip地址及端口號的客服端,如不指定端口號,系統會隨機分配
        connect(server, QTcpServer::newConnection,
        [=]()
        {
            qDebug() << "有鏈接進來";
        }
        );

    tcp協議客戶端實現流程

    創建QTcpSocket套節字(ip,端口)tcp

    經過套節字connectToHost()函數主動鏈接服務器;鏈接成功則觸發服務器QTcpServer::newConnection信號;併發送套節字到服務器端;ide

    關閉鏈接;函數

    QTcpSocket Sc(this);
    Sc.connectToHost("127.0.0.1", 8888);//實際代碼中參數要進行類型轉化
    Sc.close();

    實時通信:

    • 客戶端到服務器端通信
    1. 當客戶端與服務器端創建鏈接後;
    2. 客戶端與服務器端通信在客戶端經過套節字對象調用write()函數發送上傳內容;
    3. 服務器端有客戶端數據寫入時服務器端會自動調用readyread信號
    4. 服務器端在connect中處理readyread信號,並由nextPendingConnection()函數接收客戶端發送的套節字;
    5. 服務器端對接收的套節字進行相應處理,即完成一次客戶端到服務器端的通信
    • 服務器端到客戶端的通信
    1. 當客戶端與服務器端創建鏈接後;
    2. 服務器經過套節字對象調用write()函數發送上傳內容;客戶端會觸發readyread信號
    3. 客戶端在connect中處理readyread信號
    客戶端到服務器端實現代碼:
  • 服務器端頭文件widget.h
    #ifndef WIDGET_H
    #define WIDGET_H
    
    #include <QWidget>
    #include <QTcpServer>
    #include <QTcpSocket>
    namespace Ui {
    class Widget;
    }
    
    class Widget : public QWidget
    {
        Q_OBJECT
    
    public:
        explicit Widget(QWidget *parent = 0);
        ~Widget();
    
    private slots:
        void on_buttonsend_clicked();
    
    private:
        Ui::Widget *ui;
    
        QTcpServer *server; //創建服務器對象
        QTcpSocket *socket; //套節字對象
        QByteArray tp;   //
    };
    
    #endif // WIDGET_H

    服務器端cpp文件 widget.cpp學習

    #include "widget.h"
    #include "ui_widget.h"
    #include <QDebug>
    
    Widget::Widget(QWidget *parent) :
        QWidget(parent),
        ui(new Ui::Widget)
    {
        ui->setupUi(this);
        setWindowTitle("服務器");
        tp = nullptr;
    
        server = new QTcpServer(this);
        server->listen(QHostAddress::Any, 8000);
        connect(server, QTcpServer::newConnection,
                [=]()
        {
            socket = server->nextPendingConnection();
            connect(socket, &QTcpSocket::readyRead, [=]()
            {
                tp = socket->readAll();
                ui->testdis->append(tp);
            });
        }
        );
    
    }
    
    Widget::~Widget()
    {
        delete ui;
    }
    
    void Widget::on_buttonsend_clicked()
    {
        socket->write(ui->textEdit->toPlainText().toUtf8());
    }

    客戶端頭文件socket.h:

    #ifndef SOCKET_H
    #define SOCKET_H
    
    #include <QWidget>
    #include <QTcpSocket>
    #include <QHostAddress>
    
    namespace Ui {
    class socket;
    }
    
    class socket : public QWidget
    {
        Q_OBJECT
    
    public:
        explicit socket(QWidget *parent = 0);
        ~socket();
    
    private slots:
    
        void on_buttonLink_clicked();
    
        void on_buttonsend_clicked();
    
        void on_serverclose_clicked();
    
    private:
        Ui::socket *ui;
    
        QTcpSocket *sock;
        QHostAddress adrs;
        quint16 port;
    };
    
    #endif // SOCKET_H

    客戶端cpp文件socket.cpp

  • #include "socket.h"
    #include "ui_socket.h"
    
    socket::socket(QWidget *parent) :
        QWidget(parent),
        ui(new Ui::socket)
    {
        ui->setupUi(this);
        sock = new QTcpSocket(this);
        setWindowTitle("張三");
        connect(sock, &QTcpSocket::readyRead,
                [=]()
        {
           ui->textdis->append(sock->readAll());
        });
    }
    
    socket::~socket()
    {
        delete ui;
    }
    
    void socket::on_buttonLink_clicked()
    {
        QString ip = ui->serverIP->text();
        QString p = ui->serverPort->text();
        sock->connectToHost(ip, p.toUShort());
    }
    
    void socket::on_buttonsend_clicked()
    {
        QString temp = ui->textEdit->toPlainText();
        if(!temp.isEmpty())sock->write(temp.toUtf8());
    }
    
    void socket::on_serverclose_clicked()
    {
        sock->close();
    }

    main.cpp文件

    #include "widget.h"
    #include <QApplication>
    #include "socket.h"
    
    int main(int argc, char *argv[])
    {
        QApplication a(argc, argv);
        Widget w;
        w.show();
        socket w1;
        w1.show();
    
        return a.exec();
    }

  •  

    運行的效果如圖所示

  • 後續的通訊例子還在學習中,本文的參考連接:

  • (1)https://www.cnblogs.com/flowingwind/p/8348519.html

  • (2)https://www.cnblogs.com/findumars/p/5838531.html
  • (3)https://blog.csdn.net/pk124729136/article/details/8087609
相關文章
相關標籤/搜索