我做了一个应用程序来下载软件。它与QWebengine配合得很好。
对于第二个版本,我需要实施在应用程序关闭后重新开始下载。
我的目标是在重新启动后以相同的状态重新启动相同的下载。
有可能吗?
如何使用WebEngineDownloadItem将当前下载状态保存在文件中?
谢谢您的帮助
答案 0 :(得分:0)
这就是我的做法:
DownloaderWidget.hpp
#ifndef DOWNLOADERWIDGET_HPP
#define DOWNLOADERWIDGET_HPP
# include <QUrl>
# include <QApplication>
# include <QPushButton>
# include <QString>
# include <QWidget>
# include <QLabel>
# include <QVBoxLayout>
# include <QProgressBar>
# include "downloadermanager.hpp"
class DownloaderWidget : public QWidget
{
Q_OBJECT
public:
explicit DownloaderWidget(QWidget *parent = nullptr);
signals:
public slots:
void download(void);
void pause(void);
void resume(void);
private slots:
void progress(int percent);
private:
static QString const
URL;
QLabel *m_url;
QPushButton *m_start;
QPushButton *m_resume;
QPushButton *m_pause;
QProgressBar *m_status;
DownloaderManager *m_download_manager;
};
#endif // DOWNLOADERWIDGET_HPP
DownloaderManager.hpp
#ifndef DOWNLOADERMANAGER_HPP
#define DOWNLOADERMANAGER_HPP
# include <QUrl>
# include <QObject>
# include <QDebug>
# include <QNetworkAccessManager>
# include <QNetworkRequest>
# include <QNetworkReply>
# include <QFile>
# include <QByteArray>
# include <QStandardPaths>
class DownloaderManager : public QObject
{
Q_OBJECT
public:
explicit DownloaderManager(QObject *parent = nullptr);
signals:
void downloadComplete(void);
void progress(int const percentage);
public slots:
void download(QUrl const &url);
void pause();
void resume();
private slots:
void download(QNetworkRequest &request);
void finished();
void downloadProgress(qint64 bytesReceived, qint64 bytesTotal);
void error(QNetworkReply::NetworkError code);
private:
QNetworkAccessManager
*m_manager;
QNetworkRequest m_request;
QNetworkReply *m_reply;
QFile *m_file;
qint64 m_downloadSizeAtPause;
QString m_name;
QString get_file_name(QUrl const &url);
};
#endif // DOWNLOADERMANAGER_HPP
DownloaderWidget.cpp
#include "downloaderwidget.hpp"
QString const DownloaderWidget::URL = "My great URL";
DownloaderWidget::DownloaderWidget(QWidget *parent)
: QWidget(parent),
m_url(new QLabel(URL, this)),
m_start(new QPushButton("Start", this)),
m_resume(new QPushButton("Resume", this)),
m_pause(new QPushButton("Pause", this)),
m_status(new QProgressBar(this)),
m_download_manager(new DownloaderManager(this))
{
QVBoxLayout *main_layout = new QVBoxLayout(this);
m_status->setOrientation(Qt::Horizontal);
main_layout->addWidget(m_url);
main_layout->addWidget(m_status);
main_layout->addWidget(m_start);
main_layout->addWidget(m_pause);
main_layout->addWidget(m_resume);
QObject::connect(m_start, SIGNAL(clicked()), this, SLOT(download()));
QObject::connect(m_pause, SIGNAL(clicked()), this, SLOT(pause()));
QObject::connect(m_resume, SIGNAL(clicked()), this, SLOT(resume()));
QObject::connect(m_download_manager, SIGNAL(downloadComplete()), qApp, SLOT(quit()));
QObject::connect(m_download_manager, SIGNAL(progress(int)), this, SLOT(progress(int)));
this->m_pause->setEnabled(false);
this->m_resume->setEnabled(false);
}
void DownloaderWidget::download(void)
{
this->m_download_manager->download(QUrl(URL));
this->m_start->setEnabled(false);
this->m_pause->setEnabled(true);
}
void DownloaderWidget::pause()
{
this->m_download_manager->pause();
this->m_pause->setEnabled(false);
this->m_resume->setEnabled(true);
}
void DownloaderWidget::resume(void)
{
this->m_download_manager->resume();
this->m_pause->setEnabled(true);
this->m_resume->setEnabled(false);
}
void DownloaderWidget::progress(int percent)
{
this->m_status->setValue(percent);
}
DownloaderManager.cpp
#include "downloadermanager.hpp"
DownloaderManager::DownloaderManager(QObject *parent) :
QObject(parent),
m_manager(new QNetworkAccessManager(this)),
m_request(),
m_reply(nullptr),
m_file(nullptr),
m_downloadSizeAtPause(0),
m_name("")
{
}
QString DownloaderManager::get_file_name(QUrl const &url)
{
QStringList list = url.toString().split("/");
this->m_name = QStandardPaths::writableLocation(QStandardPaths::DownloadLocation) + "/" + list[list.length() - 1];
return (this->m_name + ".download");
}
void DownloaderManager::download(QUrl const &url)
{
this->m_name = this->get_file_name(url);
qDebug() << "Download : file = " << this->m_name;
this->m_downloadSizeAtPause = 0;
this->m_request = QNetworkRequest(url);
this->m_file = new QFile(this->m_name);
this->m_file->open(QIODevice::ReadWrite | QIODevice::Append);
if (this->m_file->size() != 0)
this->resume();
else
this->download(this->m_request);
}
void DownloaderManager::pause(void)
{
qDebug() << "pause()";
if(this->m_reply == nullptr)
return;
QObject::disconnect(this->m_reply, SIGNAL(finished()), this, SLOT(finished()));
QObject::disconnect(this->m_reply, SIGNAL(downloadProgress(qint64, qint64)),
this, SLOT(downloadProgress(qint64, qint64)));
QObject::disconnect(this->m_reply, SIGNAL(error(QNetworkReply::NetworkError)),
this, SLOT(error(QNetworkReply::NetworkError)));
this->m_reply->abort();
this->m_file->write(this->m_reply->readAll());
this->m_reply = nullptr;
}
void DownloaderManager::resume(void)
{
qDebug() << "resume()";
this->m_file->flush();
this->m_downloadSizeAtPause = this->m_file->size();
QByteArray rangeHeaderValue = "bytes=" + QByteArray::number(this->m_downloadSizeAtPause) + "-";
this->m_request.setRawHeader("Range",rangeHeaderValue);
this->download(this->m_request);
}
void DownloaderManager::download(QNetworkRequest &request)
{
qDebug() << "download( QNetworkRequest& request )";
this->m_reply = this->m_manager->get(request);
QObject::connect(this->m_reply, SIGNAL(finished()), this, SLOT(finished()));
QObject::connect(this->m_reply, SIGNAL(downloadProgress(qint64, qint64)),
this, SLOT(downloadProgress(qint64, qint64)));
QObject::connect(this->m_reply, SIGNAL(error(QNetworkReply::NetworkError)),
this, SLOT(error(QNetworkReply::NetworkError)));
}
void DownloaderManager::finished(void)
{
qDebug() << "finihsed";
this->m_file->rename(this->m_name + ".download", this->m_name);
this->m_file->close();
this->m_file = nullptr;
this->m_reply = nullptr;
emit downloadComplete();
}
void DownloaderManager::downloadProgress(qint64 bytesReceived, qint64 bytesTotal)
{
qDebug() << "Download Progress: Received=" << this->m_downloadSizeAtPause + bytesReceived <<": Total=" << this->m_downloadSizeAtPause + bytesTotal;
this->m_file->write(this->m_reply->readAll());
int percentage =
static_cast<int>((this->m_downloadSizeAtPause + bytesReceived) * 100 ) / (this->m_downloadSizeAtPause + bytesTotal);
qDebug() << percentage;
emit progress(percentage);
}
void DownloaderManager::error(QNetworkReply::NetworkError code)
{
qDebug() << "Error:" <<code;
}
main.cpp
#include <QApplication>
#include "downloaderwidget.hpp"
int main(int argc, char **argv)
{
QApplication app(argc, argv);
DownloaderWidget downloader;
downloader.show();
return (app.exec());
}
我希望这段代码能在与我相同的情况下对某些人有所帮助谢谢