Qt 网络通信

Qt 网络通信

  • 一、主机信息查询
    • 1.1 QHostInfo
    • 1.2 QNetworkInterface
  • 二、TCP
    • 2.2 QTcpServer
    • 2.3 QTcpSocket
    • 2.4 客户端
    • 2.5 服务端
    • 2.6 特殊的IP地址
  • 三、UDP
  • 四、HTTP
  • 五、FTP

一、主机信息查询

使用Qt网络模块,需要在配置文件中添加Qt += network

1.1 QHostInfo

方法 描述
QList addresses() const; 获取与主机名关联的IP地址列表
HostInfoError error() const; 如果主机查找失败,返回失败类型
QString errorString() const; 如果主机查找失败,返回错误描述字符串
QString hostName() const; 通过IP地址查找的主机的名称
int lookupId() const; 返回本次查找的ID
静态函数 描述
static void abortHostLookup(int lookupId); 中断主机查找
static QHostInfo fromName(const QString &name); 获取指定主机名的IP地址
static QString localDomainName(); 获取本机DNS域名
static QString localHostName(); 获取本机主机名
static int lookupHost(const QString &name, QObject *receiver, const char *member); 以异步方式根据主机名查找主机IP地址,并返回一个表示本次查找的ID,可用于abortHostLookup
//获取本机的IP
void Dialog::GetQHostInfo()
{
    QString hostName=QHostInfo::localHostName();//本地主机名
    QHostInfo   hostInfo=QHostInfo::fromName(hostName); //本机IP地址

    QList<QHostAddress> addList=hostInfo.addresses();//IP地址列表
    if (!addList.isEmpty())
    {
        for (int i=0;i<addList.count();i++)
	    {
	        QHostAddress aHost=addList.at(i);//每一项是一个QHostAddress
	        aHost.protocol(); //协议类型
	        aHost.toString(); //本机IP地址
	    }
    }
}
	//协议类型,aHost.protocol();返回值
    enum NetworkLayerProtocol {
        IPv4Protocol,
        IPv6Protocol,
        AnyIPProtocol,
        UnknownNetworkLayerProtocol = -1
    };
//查找主机信息的槽函数
void Dialog::lookedUpHostInfo(const QHostInfo &host)
{
    QList<QHostAddress> addList=host.addresses();//
    if (!addList.isEmpty())
    {
	    for (int i=0;i<addList.count();i++)
	    {
	        QHostAddress aHost=addList.at(i);//每一项是一个QHostAddress
	        aHost.protocol(); //协议类型
	        aHost.toString(); //本机IP地址
	    }	
	}
}
//参数name可以是www.163.com或者本机名QHostInfo::localHostName()
//以异步方式根据主机名查找主机IP地址
void Dialog::Lookup(const QString &name)
{
    QHostInfo::lookupHost(name, this,SLOT(lookedUpHostInfo(QHostInfo)));
}

1.2 QNetworkInterface

方法 描述
QList QNetworkInterface::addressEntries() const; 返回该网络接口的IP地址列表(包括子网掩码和广播地址)
QString QNetworkInterface::hardwareAddress() const; 返回改接口的地基硬件地址,以太网里面是MAC地址
QString QNetworkInterface::humanReadableName() const; 设备名称
bool QNetworkInterface::isValid() const; 判断接口是否有效
QString QNetworkInterface::name() const; 网络接口名称
方法 描述
static QList allAddresses(); 返回主机上所有IP地址的列表
static QList allInterfaces(); 返回主机上所有接口的网络列表
//QNetworkInterface::allAddresses()的使用
void Dialog::on_btnDetail_clicked()
{
    QList<QHostAddress> addList=QNetworkInterface::allAddresses();
    if (!addList.isEmpty())
    {
	    for (int i=0;i<addList.count();i++)
	    {
	        QHostAddress aHost=addList.at(i);
	        aHost.protocol(); //协议类型
	        aHost.toString(); //本机IP地址
	    }
	}
}

//QNetworkInterface::allInterfaces()函数的使用
void Dialog::on_btnALLInterface_clicked()
{
    QList<QNetworkInterface>    list=QNetworkInterface::allInterfaces();
    for(int i=0;i<list.count();i++)
    {
        QNetworkInterface aInterface=list.at(i);
        if (!aInterface.isValid())
           continue;

        aInterface.humanReadableName();//设备名称
        aInterface.hardwareAddress();//硬件地址
        QList<QNetworkAddressEntry> entryList=aInterface.addressEntries();
        for(int j=0;j<entryList.count();j++)
        {
            QNetworkAddressEntry aEntry=entryList.at(j);
            aEntry.ip().toString();//IP 地址
            aEntry.netmask().toString();//子网掩码
            aEntry.broadcast().toString();//广播地址
        }
    }
}

二、TCP

2.2 QTcpServer

方法 描述
void close(); 关闭服务器,停止网络监听
bool listen(const QHostAddress &address = QHostAddress::Any, quint16 port = 0); 监听指定IP和端口,成功返回true
bool isListening() const; 服务器处于监听状态,true表示正在监听
quint16 serverPort() const; 如果服务器在监听状态,返回服务器端口
QHostAddress serverAddress() const; 如果服务器在监听状态,返回服务器地址
bool waitForNewConnection(int msec = 0, bool *timedOut = nullptr); 以阻塞的方式等待新的连接
virtual QTcpSocket *nextPendingConnection(); 返回下一个等待接入的连接
信号 描述
void newConnection(); 当有新的连接是发射此信号
void acceptError(QAbstractSocket::SocketError socketError); 当接受一个新的连接发生错误时,发射此信号,参数描述了错误信息

2.3 QTcpSocket

方法 描述
void connectToHost(const QString &hostName, quint16 port, OpenMode openMode = ReadWrite, NetworkLayerProtocol protocol = AnyIPProtocol) override; 以异步方式连接到指定IP和端口的TCP服务器,连接成功会发射connected()信号
void disconnectFromHost() override; 断开socket连接,断开成功后发射sidconnected()信号
bool waitForConnected(int msecs = 30000) override; 等待直到建立socket连接
bool waitForDisconnected(int msecs = 30000) override; 等待直到断开socket连接
quint16 localPort() const; 返回本socket的端口
QHostAddress localAddress() const; 返回本socket的地址
quint16 peerPort() const; 已经连接状态下返回对方端口
QHostAddress peerAddress() const; 已经连接状态下返回对方地址
QString peerName() const; 已经连接状态下返回对方主机名
SocketState state() const; 返回socket的当前状态
bool canReadLine() const override; 如果有行数据要从socket缓冲区读取就返回true
qint64 write(const QByteArray &data) 发送消息
信号 描述
void connected(); connectToHost成功连接到服务器后发射此信号
void disconnected(); 当断开socket连接时发射此信号
void stateChanged(QAbstractSocket::SocketState); 当socket状态发生变化时发射此信号
void error(QAbstractSocket::SocketError); 当socket发生错误时发射此信号
void hostFound(); 调用connectToHost找到主机后发射此信号
void readyRead(); 当缓冲区有新数据需要读取时发射此信号,在此信号的槽函数里面读取数据

2.4 客户端

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    tcpClient=new QTcpSocket(this); //创建socket变量

    connect(tcpClient,SIGNAL(connected()),this,SLOT(onConnected()));
    connect(tcpClient,SIGNAL(disconnected()),this,SLOT(onDisconnected()));

    connect(tcpClient,SIGNAL(stateChanged(QAbstractSocket::SocketState)),
            this,SLOT(onSocketStateChange(QAbstractSocket::SocketState)));
    connect(tcpClient,SIGNAL(readyRead()),
            this,SLOT(onSocketReadyRead()));
}

//connected()信号槽函数
void MainWindow::onConnected()
{ 
    tcpClient->peerAddress().toString();
    tcpClient->peerPort();

}

//disConnected()信号槽函数
void MainWindow::onDisconnected()
{

}

//readyRead()信号槽函数
void MainWindow::onSocketReadyRead()
{
    while(tcpClient->canReadLine())
        QByteArray str = tcpClient->readLine();
}

//连接到服务器
void MainWindow::on_actConnect_triggered(const QHostAddress &address, quint16 port)
{
    tcpClient->connectToHost(address,port);
}

//断开与服务器的连接
void MainWindow::on_actDisconnect_triggered()
{
    if (tcpClient->state()==QAbstractSocket::ConnectedState)
        tcpClient->disconnectFromHost();
}

//发送数据
void MainWindow::on_btnSend_clicked()
{
    QString  msg="I am God";
    QByteArray  str=msg.toUtf8();
    str.append('\n');
    tcpClient->write(str);
}

2.5 服务端

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    tcpServer=new QTcpServer(this);
    connect(tcpServer,SIGNAL(newConnection()),this,SLOT(onNewConnection()));
}

//开始监听
void MainWindow::on_actStart_triggered()
{
    QString     IP=ui->comboIP->currentText();//IP地址
    quint16     port=ui->spinPort->value();//端口
    QHostAddress    addr(IP);
    tcpServer->listen(addr,port);//
    //tcpServer->listen(QHostAddress::Any, port);
    tcpServer->serverAddress().toString();//服务器地址
    tcpServer->serverPort();//服务器端口
}

//停止监听
void MainWindow::on_actStop_triggered()
{
    if (tcpServer->isListening()) //tcpServer正在监听
    {
        tcpServer->close();//停止监听
    }
}

//关闭窗口时停止监听
void MainWindow::closeEvent(QCloseEvent *event)
{
    if (tcpServer->isListening())
        tcpServer->close();//停止网络监听
    event->accept();
}

//有新连接
void MainWindow::onNewConnection()
{
    tcpSocket = tcpServer->nextPendingConnection(); //创建socket

    connect(tcpSocket, SIGNAL(connected()),
            this, SLOT(onClientConnected()));
    onClientConnected();//

    connect(tcpSocket, SIGNAL(disconnected()),
            this, SLOT(onClientDisconnected()));

    connect(tcpSocket,SIGNAL(stateChanged(QAbstractSocket::SocketState)),
            this,SLOT(onSocketStateChange(QAbstractSocket::SocketState)));
    onSocketStateChange(tcpSocket->state());

    connect(tcpSocket,SIGNAL(readyRead()),
            this,SLOT(onSocketReadyRead()));
}

//客户端接入时
void MainWindow::onClientConnected()
{
    tcpSocket->peerAddress().toString();//客户端地址
    tcpSocket->peerPort();//客户端端口
}

//客户端断开连接时
void MainWindow::onClientDisconnected()
{
    tcpSocket->deleteLater();
}

//读取缓冲区行文本
void MainWindow::onSocketReadyRead()
{
    while(tcpSocket->canReadLine())
        ui->plainTextEdit->appendPlainText("[in] "+tcpSocket->readLine());
}

//发送一行字符串,以换行符结束
void MainWindow::on_btnSend_clicked()
{
    QString  msg="I am God";
    QByteArray  str=msg.toUtf8();
    str.append('\n');//添加一个换行符
    tcpSocket->write(str);
}

2.6 特殊的IP地址

QHostAddress定义了集中特殊的IP地址,如

QHostAddress::Null表示一个空地址;

QHostAddress::LocalHost表示IPv4的本机地址127.0.0.1;

QHostAddress::LocalHostIPv6表示IPv6的本机地址;

QHostAddress::Broadcast表示广播地址255.255.255.255;

QHostAddress::Any表示IPv4的任意地址;

QHostAddress::AnyIPv6表示IPv6的任意地址。

三、UDP

四、HTTP

五、FTP

你可能感兴趣的:(Qt)