我正在尝试从网上下载一个文本文件以供我的 GUI 应用程序使用。我首先使用了一个事件循环,但该文件在第一次尝试时会下载一个 0 字节的文件,但在随后的尝试中会成功(应用程序使用按钮下载)。然后我尝试使用没有事件循环的类成员定义的插槽,但插槽永远不会被调用。
这是事件循环的过程:
void class1::downloadFile(const QString &url, const QString &aPathInClient)
{
QNetworkAccessManager m_NetworkMngr;
QNetworkReply *reply= m_NetworkMngr.get(QNetworkRequest(url));
QEventLoop loop;
QObject::connect(reply, SIGNAL(finished()),&loop, SLOT(quit()));
loop.exec();
QUrl aUrl(url);
QFileInfo fileInfo=aUrl.path();
QFile file(aPathInClient+"/"+fileInfo.fileName());
file.open(QIODevice::WriteOnly);
file.write(reply->readAll());
file.close();
reply->deleteLater();
}
下面是使用类成员定义槽的过程:
类1.h
class class1: public QObject
{
Q_OBJECT
public slots:
void onRequestCompleted();
public:
QString df_url;
QString df_path;
public:
void downloadFile(const QString &url, const QString &aPathInClient);
};
类1.cpp
void class1::downloadFile(const QString &url, const QString &aPathInClient)
{
df_url = url;
df_path = aPathInClient;
QNetworkAccessManager m_NetworkMngr;
QNetworkReply *reply = m_NetworkMngr.get(QNetworkRequest(url));
QObject::connect(reply, SIGNAL(finished()), this, SLOT(onRequestCompleted()));
reply->deleteLater();
}
void class1::onRequestCompleted( )
{
QString url2;
QString aPathInClient2;
url2 = df_url;
aPathInClient2 = df_path;
QNetworkReply *reply = qobject_cast<QNetworkReply *>(sender());
QUrl aUrl(url2);
QFileInfo fileInfo=aUrl.path();
QFile file(aPathInClient2+"/"+fileInfo.fileName());
file.open(QIODevice::WriteOnly);
file.write(reply->readAll());
file.close();
reply->deleteLater();
}
原谅变量的冗余。我只是想让它在他的点上起作用。我稍后会清理它。对此问题的任何帮助将不胜感激。提前感谢您的任何回复。
编辑:
我终于找到了问题所在。我从另一个网站下载,现在一切正常。从第一个站点转移一定有问题。我正在使用类成员槽方法,放弃事件循环方法。
这是我正在使用的代码:
//class1.h
class class1: public QObject
{
//There's a lot more to the class, but here are the pertinent parts
Q_OBJECT
public slots:
void onRequestCompleted();
public:
QString df_url;
QString df_path;
QNetworkAccessManager *m_NetworkMngr;
QNetworkReply *reply;
public:
void downloadFile(const QString &url, const QString &aPathInClient);
};
//class1.cpp
void class1::downloadFile(const QString &url, const QString &aPathInClient)
{
df_url = url; //class variable
df_path = aPathInClient; //class variable
m_NetworkMngr = new QNetworkAccessManager(this); //class variable
reply= m_NetworkMngr->get(QNetworkRequest(url)); //class variable
QObject::connect(reply, SIGNAL(finished()), this, SLOT(onRequestCompleted()));
}
void class1::onRequestCompleted() {
QString url2;
QString aPathInClient2;
url2 = df_url;
aPathInClient2 = df_path;
QNetworkReply *reply = qobject_cast<QNetworkReply *>(sender());
QUrl aUrl(url2);
QFileInfo fileInfo=aUrl.path();
QFile file(aPathInClient2+"/"+fileInfo.fileName());
file.open(QIODevice::WriteOnly);
file.write(reply->readAll());
file.close();
}
downloadFile 程序参数:
url -string 我正在下载的文件的 url
aPathInClient - 包含我正在更新的文件的文件夹的字符串位置
downloadFile 被一个通过按下按钮调用的过程调用。整个类被按钮实例化,然后在按钮插槽完成时被销毁。因此,当这种情况发生时,回复和网络管理器对象会被销毁。