QT编写TCP/UDP调试助手之TCP客户端

效果图:

TCP/UDP调试助手之TCP客户端,支持错误信息显示,断开连接后及时释放资源。

QT编写TCP/UDP调试助手之TCP客户端_第1张图片

一、关键代码

1.在.pro文件中添加QT += network,包含头文件#include

在类里定义一个QTcpSocket*成员m_tcpSocket

   QTcpSocket* m_tcpSocket;

2.界面校验设置。界面上有两个lineEdit用来填写服务器的IP和端口,通过setValidator可以限制lineEdit输入的范围,端口号范围0-65535,IP地址用正则表达式校验,防止输入错误。

  //设置端口输入校验
    ui->lineEdit_clientRemotePort->setValidator(new QIntValidator(0,65535));
   //ip校验正则
    QRegExp regExpIP("((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])[\\.]){3}(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9][0-9]|[0-9])");
    //设置IP输入校验
    ui->lineEdit_clientRemoteIP->setValidator(new QRegExpValidator(regExpIP ,ui->lineEdit_serverLocalIp));

3.连接断开主要用到三个函数和两个信号。

3.1 通过调用m_tcpSocket->connectToHost(ip,port);开始尝试连接服务器;

3.2 m_tcpSocket->waitForConnected(1000)设置等待的时间,等待连接。在这里设置1000ms,1000ms内连上服务器,返回true ,没连上返回false;

3.3 m_tcpSocket->abort();//终止连接,并且是立即关闭;

3.4 信号error(QAbstractSocket::SocketError),发生错误时发送信号,并传递错误信息;

3.5 信号readyRead(),接收到数据时发送的信号。

//tcp客户端连接/断开
void MainWindow::on_btn_clientConnect_clicked()
{
    if(m_tcpSocket == nullptr)
    {
        //获取本地端口
        bool ok;
        quint16 port=ui->lineEdit_clientRemotePort->text().toUShort(&ok);
        if(!ok)
        {
            QMessageBox::warning(this,"错误","远程端口设置有误,请重新输入");
            return;
        }
        //获取本地Ip
        QHostAddress ip(ui->lineEdit_clientRemoteIP->text());
        ip.toIPv4Address(&ok);
        if(!ok)
        {
            QMessageBox::warning(this,"错误","远程ip设置有误,请重新输入");
            return;
        }

        this->m_tcpSocket=new QTcpSocket(this);
        m_tcpSocket->connectToHost(ip,port);
        connect(m_tcpSocket,SIGNAL(error(QAbstractSocket::SocketError)),this,SLOT(ClientReadError(QAbstractSocket::SocketError)));
        //等待连接
        if (m_tcpSocket->waitForConnected(1000))
        {
            connect(m_tcpSocket,SIGNAL(readyRead()),this,SLOT(ClinetReadData()));

            //更新UI
            ui->text_clientRec->appendPlainText("已连接服务器"+QString("[%1:%2]\r\n").arg(ui->lineEdit_clientRemoteIP->text()).arg(ui->lineEdit_clientRemotePort->text()));
            ui->btn_clientConnect->setText("断开");
            ui->btn_clientConnect->setIcon(QIcon(":/Resource/Img/stop36x36.png"));
            ui->lineEdit_clientRemoteIP->setEnabled(false);
            ui->lineEdit_clientRemotePort->setEnabled(false);
        }
        else//连接失败
        {
            m_tcpSocket->disconnect();
            m_tcpSocket->deleteLater();
            m_tcpSocket=nullptr;
            ui->text_clientRec->appendPlainText("连接失败"+QString("[%1:%2]\r\n").arg(ui->lineEdit_clientRemoteIP->text()).arg(ui->lineEdit_clientRemotePort->text()));
        }

    }
    else
    {
        m_tcpSocket->disconnect();//断开信号槽
        m_tcpSocket->abort();//终止
        m_tcpSocket->deleteLater();//释放
        m_tcpSocket=nullptr;
        //更新UI
        ui->text_clientRec->appendPlainText("已断开服务器"+QString("[%1:%2]\r\n").arg(ui->lineEdit_clientRemoteIP->text()).arg(ui->lineEdit_clientRemotePort->text()));
        ui->btn_clientConnect->setText("连接");
        ui->btn_clientConnect->setIcon(QIcon(":/Resource/Img/start36x36.png"));
        ui->lineEdit_clientRemoteIP->setEnabled(true);
        ui->lineEdit_clientRemotePort->setEnabled(true);
    }
}

4. readyRead()信号触发的读取数据槽函数,调用m_tcpSocket->readAll();读取所有接收到的数据

//tcp客户端读取数据
void MainWindow::ClinetReadData()
{
    QByteArray ba = m_tcpSocket->readAll();
    QString data;
    //hex
    if(ui->chk_udpRecHex->isChecked())
    {
        this->ByteToHexString(data,ba);
    }
    else//普通字符串
    {
        data=QString::fromLocal8Bit(ba);
    }
    //显示
    ui->text_clientRec->insertPlainText(data);
    ui->text_clientRec->moveCursor(QTextCursor::End);
}

5. 发送数据, 通过调用m_tcpSocket->write(byteArray);写入数据

//点击tcp客户端发送
void MainWindow::on_btn_clientSend_clicked()
{
    QByteArray byteArray;
    QString data=ui->text_clientSend->toPlainText();
    //Hex发送
    if(ui->chk_clientSendHex->isChecked())
    {
        //hex字符串转字节
        if(!HexStringToByte(data,byteArray))
        {
            QMessageBox::information(this,"提示","输入的十六进制字符串有误,请重新输入");
            return;
        }
    }
    //普通字符串发送
    else
    {
        byteArray= data.toLocal8Bit();
    }
    m_tcpSocket->write(byteArray);
}

6. error(QAbstractSocket::SocketError)信号槽函数,显示错误信息并直接断开连接

//tcp客户端发生错误
void MainWindow::ClientReadError(QAbstractSocket::SocketError)
{
    QString err=QString("发生错误:%1").arg(m_tcpSocket->errorString());
    ui->text_clientRec->appendPlainText(err);
    m_tcpSocket->disconnect();//断开所有信号
    m_tcpSocket->abort();//终止socket连接
    m_tcpSocket->deleteLater();//释放
    m_tcpSocket=nullptr;
    //更新UI
    ui->text_clientRec->appendPlainText("已断开服务器"+QString("[%1:%2]\r\n").arg(ui->lineEdit_clientRemoteIP->text()).arg(ui->lineEdit_clientRemotePort->text()));
    ui->btn_clientConnect->setText("连接");
    ui->btn_clientConnect->setIcon(QIcon(":/Resource/Img/stop36x36.png"));
    ui->lineEdit_clientRemoteIP->setEnabled(true);
    ui->lineEdit_clientRemotePort->setEnabled(true);

}

二、下载

tcp/udp调试助手

你可能感兴趣的:(TCP,QT)