Merge pull request #12655 from Chocobo1/delete

Improve behavior of deleting torrents in transfer list
This commit is contained in:
Mike Tzou 2020-04-28 11:14:49 +08:00 committed by GitHub
commit 6dcb0665ca
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 34 additions and 27 deletions

View file

@ -501,6 +501,17 @@ QVector<BitTorrent::TorrentHandle *> TransferListWidget::getSelectedTorrents() c
return torrents; return torrents;
} }
QVector<BitTorrent::TorrentHandle *> TransferListWidget::getVisibleTorrents() const
{
const int visibleTorrentsCount = m_sortFilterModel->rowCount();
QVector<BitTorrent::TorrentHandle *> torrents;
torrents.reserve(visibleTorrentsCount);
for (int i = 0; i < visibleTorrentsCount; ++i)
torrents << m_listModel->torrentHandle(mapToSource(m_sortFilterModel->index(i, 0)));
return torrents;
}
void TransferListWidget::setSelectedTorrentsLocation() void TransferListWidget::setSelectedTorrentsLocation()
{ {
const QVector<BitTorrent::TorrentHandle *> torrents = getSelectedTorrents(); const QVector<BitTorrent::TorrentHandle *> torrents = getSelectedTorrents();
@ -547,11 +558,8 @@ void TransferListWidget::forceStartSelectedTorrents()
void TransferListWidget::startVisibleTorrents() void TransferListWidget::startVisibleTorrents()
{ {
for (int i = 0; i < m_sortFilterModel->rowCount(); ++i) { for (BitTorrent::TorrentHandle *const torrent : asConst(getVisibleTorrents()))
BitTorrent::TorrentHandle *const torrent = m_listModel->torrentHandle(mapToSource(m_sortFilterModel->index(i, 0))); torrent->resume();
if (torrent)
torrent->resume();
}
} }
void TransferListWidget::pauseSelectedTorrents() void TransferListWidget::pauseSelectedTorrents()
@ -562,11 +570,8 @@ void TransferListWidget::pauseSelectedTorrents()
void TransferListWidget::pauseVisibleTorrents() void TransferListWidget::pauseVisibleTorrents()
{ {
for (int i = 0; i < m_sortFilterModel->rowCount(); ++i) { for (BitTorrent::TorrentHandle *const torrent : asConst(getVisibleTorrents()))
BitTorrent::TorrentHandle *const torrent = m_listModel->torrentHandle(mapToSource(m_sortFilterModel->index(i, 0))); torrent->pause();
if (torrent)
torrent->pause();
}
} }
void TransferListWidget::softDeleteSelectedTorrents() void TransferListWidget::softDeleteSelectedTorrents()
@ -589,9 +594,11 @@ void TransferListWidget::deleteSelectedTorrents(const bool deleteLocalFiles)
if (Preferences::instance()->confirmTorrentDeletion()) { if (Preferences::instance()->confirmTorrentDeletion()) {
auto *dialog = new DeletionConfirmationDialog(this, torrents.size(), torrents[0]->name(), deleteLocalFiles); auto *dialog = new DeletionConfirmationDialog(this, torrents.size(), torrents[0]->name(), deleteLocalFiles);
dialog->setAttribute(Qt::WA_DeleteOnClose); dialog->setAttribute(Qt::WA_DeleteOnClose);
connect(dialog, &DeletionConfirmationDialog::accepted, this, [dialog, torrents]() connect(dialog, &DeletionConfirmationDialog::accepted, this, [this, dialog]()
{ {
removeTorrents(torrents, dialog->isDeleteFileSelected()); // Some torrents might be removed when waiting for user input, so refetch the torrent list
// NOTE: this will only work when dialog is modal
removeTorrents(getSelectedTorrents(), dialog->isDeleteFileSelected());
}); });
dialog->open(); dialog->open();
} }
@ -602,18 +609,17 @@ void TransferListWidget::deleteSelectedTorrents(const bool deleteLocalFiles)
void TransferListWidget::deleteVisibleTorrents() void TransferListWidget::deleteVisibleTorrents()
{ {
if (m_sortFilterModel->rowCount() <= 0) return; const QVector<BitTorrent::TorrentHandle *> torrents = getVisibleTorrents();
if (torrents.empty()) return;
QVector<BitTorrent::TorrentHandle *> torrents;
for (int i = 0; i < m_sortFilterModel->rowCount(); ++i)
torrents << m_listModel->torrentHandle(mapToSource(m_sortFilterModel->index(i, 0)));
if (Preferences::instance()->confirmTorrentDeletion()) { if (Preferences::instance()->confirmTorrentDeletion()) {
auto *dialog = new DeletionConfirmationDialog(this, torrents.size(), torrents[0]->name(), false); auto *dialog = new DeletionConfirmationDialog(this, torrents.size(), torrents[0]->name(), false);
dialog->setAttribute(Qt::WA_DeleteOnClose); dialog->setAttribute(Qt::WA_DeleteOnClose);
connect(dialog, &DeletionConfirmationDialog::accepted, this, [dialog, torrents]() connect(dialog, &DeletionConfirmationDialog::accepted, this, [this, dialog]()
{ {
removeTorrents(torrents, dialog->isDeleteFileSelected()); // Some torrents might be removed when waiting for user input, so refetch the torrent list
// NOTE: this will only work when dialog is modal
removeTorrents(getVisibleTorrents(), dialog->isDeleteFileSelected());
}); });
dialog->open(); dialog->open();
} }

View file

@ -141,6 +141,7 @@ private:
void confirmRemoveAllTagsForSelection(); void confirmRemoveAllTagsForSelection();
QStringList askTagsForSelection(const QString &dialogTitle); QStringList askTagsForSelection(const QString &dialogTitle);
void applyToSelectedTorrents(const std::function<void (BitTorrent::TorrentHandle *const)> &fn); void applyToSelectedTorrents(const std::function<void (BitTorrent::TorrentHandle *const)> &fn);
QVector<BitTorrent::TorrentHandle *> getVisibleTorrents() const;
// supposed to be used with qss only // supposed to be used with qss only
QColor unknownStateForeground() const; QColor unknownStateForeground() const;

View file

@ -320,11 +320,12 @@ void TorrentsController::propertiesAction()
requireParams({"hash"}); requireParams({"hash"});
const QString hash {params()["hash"]}; const QString hash {params()["hash"]};
QJsonObject dataDict;
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
QJsonObject dataDict;
dataDict[KEY_PROP_TIME_ELAPSED] = torrent->activeTime(); dataDict[KEY_PROP_TIME_ELAPSED] = torrent->activeTime();
dataDict[KEY_PROP_SEEDING_TIME] = torrent->seedingTime(); dataDict[KEY_PROP_SEEDING_TIME] = torrent->seedingTime();
dataDict[KEY_PROP_ETA] = static_cast<double>(torrent->eta()); dataDict[KEY_PROP_ETA] = static_cast<double>(torrent->eta());
@ -422,11 +423,11 @@ void TorrentsController::webseedsAction()
requireParams({"hash"}); requireParams({"hash"});
const QString hash {params()["hash"]}; const QString hash {params()["hash"]};
QJsonArray webSeedList;
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
QJsonArray webSeedList;
for (const QUrl &webseed : asConst(torrent->urlSeeds())) { for (const QUrl &webseed : asConst(torrent->urlSeeds())) {
webSeedList.append(QJsonObject { webSeedList.append(QJsonObject {
{KEY_WEBSEED_URL, webseed.toString()} {KEY_WEBSEED_URL, webseed.toString()}
@ -451,11 +452,11 @@ void TorrentsController::filesAction()
requireParams({"hash"}); requireParams({"hash"});
const QString hash {params()["hash"]}; const QString hash {params()["hash"]};
QJsonArray fileList;
const BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); const BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
QJsonArray fileList;
if (torrent->hasMetadata()) { if (torrent->hasMetadata()) {
const QVector<BitTorrent::DownloadPriority> priorities = torrent->filePriorities(); const QVector<BitTorrent::DownloadPriority> priorities = torrent->filePriorities();
const QVector<qreal> fp = torrent->filesProgress(); const QVector<qreal> fp = torrent->filesProgress();
@ -494,11 +495,11 @@ void TorrentsController::pieceHashesAction()
requireParams({"hash"}); requireParams({"hash"});
const QString hash {params()["hash"]}; const QString hash {params()["hash"]};
QJsonArray pieceHashes;
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
QJsonArray pieceHashes;
const QVector<QByteArray> hashes = torrent->info().pieceHashes(); const QVector<QByteArray> hashes = torrent->info().pieceHashes();
for (const QByteArray &hash : hashes) for (const QByteArray &hash : hashes)
pieceHashes.append(QString(hash.toHex())); pieceHashes.append(QString(hash.toHex()));
@ -516,11 +517,11 @@ void TorrentsController::pieceStatesAction()
requireParams({"hash"}); requireParams({"hash"});
const QString hash {params()["hash"]}; const QString hash {params()["hash"]};
QJsonArray pieceStates;
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
QJsonArray pieceStates;
const QBitArray states = torrent->pieces(); const QBitArray states = torrent->pieces();
for (int i = 0; i < states.size(); ++i) for (int i = 0; i < states.size(); ++i)
pieceStates.append(static_cast<int>(states[i]) * 2); pieceStates.append(static_cast<int>(states[i]) * 2);
@ -609,7 +610,6 @@ void TorrentsController::addTrackersAction()
requireParams({"hash", "urls"}); requireParams({"hash", "urls"});
const QString hash = params()["hash"]; const QString hash = params()["hash"];
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
@ -669,12 +669,12 @@ void TorrentsController::removeTrackersAction()
requireParams({"hash", "urls"}); requireParams({"hash", "urls"});
const QString hash = params()["hash"]; const QString hash = params()["hash"];
const QStringList urls = params()["urls"].split('|');
BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash); BitTorrent::TorrentHandle *const torrent = BitTorrent::Session::instance()->findTorrent(hash);
if (!torrent) if (!torrent)
throw APIError(APIErrorType::NotFound); throw APIError(APIErrorType::NotFound);
const QStringList urls = params()["urls"].split('|');
const QVector<BitTorrent::TrackerEntry> trackers = torrent->trackers(); const QVector<BitTorrent::TrackerEntry> trackers = torrent->trackers();
QVector<BitTorrent::TrackerEntry> remainingTrackers; QVector<BitTorrent::TrackerEntry> remainingTrackers;
remainingTrackers.reserve(trackers.size()); remainingTrackers.reserve(trackers.size());