Qt網絡編程——TCP服務器與客戶端互發信息

前言

前一個博客,試了TCP的服務器與客戶端的連接與斷開,接下就是客戶端與服務器互發信息。

客戶端

1.往服務器發送信息

//發送消息
void Client::on_buttonSendMessage_clicked()
{
    QString data = ui->textEditInput->toPlainText();
    if(data.length() != 0)
    {
        tcpClient->write(data.toLatin1());
        ui->textEditInput->clear();
        ui->textEditStatus->append("發送文本消息成功!");
        data.clear();
    }
    else
    {
        ui->textEditStatus->append("不能發送空的消息!");
    }

}

當客戶端連接上服務器之後,在輸入窗口下輸入文字(英文),然後點發送按鍵,信息往服務器發送。
2.接收來自服務器的信息
2.1 在構造函數裏添加一個槽函數做接收到信息的事件響應

    connect(tcpClient, SIGNAL(readyRead()), this, SLOT(readServerMessage()));

2.1 實現這個槽函數,接收信息並顯示出來

//接收服務器端的信息並顯示
void Client::readServerMessage()
{
    QByteArray buffer = tcpClient->readAll();
    if(!buffer.isEmpty())
    {
        ui->textEditAccept->append(buffer);
    }
}

服務器

1.在服務器要加上有新客戶端連接時的槽函數

//有新的連接時的槽函數
    connect(tcpServer,SIGNAL(newConnection()),this, SLOT(newConnectionSlot()));

槽函數實現

//有新客戶端連接時
void Server::newConnectionSlot()
{
    //返回套接字指針
    currentClient = tcpServer->nextPendingConnection();
    tcpClient.append(currentClient);

    ui->comboBoxIP->addItem(tr("%1:%2").arg(currentClient->peerAddress().toString().split("::ffff:")[1])\
                                          .arg(currentClient->peerPort()));
    //讀取消息處理
    connect(currentClient, SIGNAL(readyRead()), this, SLOT(readMessageData()));
}

2.接收來自客戶端的信息並顯示出來

//接收消息並顯示到界面
void Server::readMessageData()
{
    for(int i = 0; i < tcpClient.length(); i++)
    {
        QByteArray buffer = tcpClient.at(i)->readAll();
        if(buffer.isEmpty())
        {
            ui->textEditStatus->append("接收的消息爲空!");
        }
        else
        {
            ui->textEditAccept->append(buffer);
            ui->textEditStatus->append("接收消息成功!");
        }
    }
}

3.往客戶端發送信息,這裏有兩種可能,一是隻要連接上的客戶端都發,二是指定客戶端來發送,就是綁死客戶端的IP地址。

//往客戶端發送信息
void Server::on_buttonSendMessage_clicked()
{
    QString input_data = ui->textEditInput->toPlainText();
    if(input_data.isEmpty())
    {
        ui->textEditStatus->append("不能發送空的信息!");
        return;
    }
    //如果選擇全部發送信息
    if(ui->comboBoxIP->currentIndex() == 0)
    {
        for(int i = 0; i < tcpClient.length(); i++)
        {
            tcpClient.at(i)->write(input_data.toLatin1());
            ui->textEditStatus->append("信息發送成功!");
            ui->textEditInput->clear();
            input_data.clear();
        }
    }
    //指定接收的客戶端
    else
    {
        //得到選擇的IP地址
        QString client_IP = ui->comboBoxIP->currentText().split(":").at(0);
        //得到端口
        int client_port = ui->comboBoxIP->currentText().split(":").at(1).toInt();

        //遍歷連接到的客戶端
        for(int i = 0; i < tcpClient.length(); i++)
        {
            if(tcpClient[i]->peerAddress().toString().split("::ffff:")[1]==client_IP\
                            && tcpClient[i]->peerPort()==client_port)
            {
                tcpClient.at(i)->write(input_data.toLatin1());
                ui->textEditStatus->append("發送信息到:"+client_IP+"成功!");
                //ui->textEditInput->clear();
                input_data.clear();
                return; //ip:port唯一,無需繼續檢索
            }
        }
    }
}

測試

運行服務器與客戶端,並點擊監聽與連接,開始互發信息
運行效果如下:
在這裏插入圖片描述

以上是就是一個服務器與客戶端的初步框架,還缺少了互相傳送圖像,上傳下載文件這兩個功能,還有異常處理機制,心跳檢測,多線程等需要完善。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章