mirror of
https://github.com/qbittorrent/qBittorrent
synced 2025-07-06 05:01:25 -07:00
parent
882da47609
commit
d174bc75e4
15 changed files with 163 additions and 80 deletions
|
@ -54,6 +54,7 @@ add_library(qbt_base STATIC
|
||||||
concepts/stringable.h
|
concepts/stringable.h
|
||||||
digest32.h
|
digest32.h
|
||||||
exceptions.h
|
exceptions.h
|
||||||
|
freediskspacechecker.h
|
||||||
global.h
|
global.h
|
||||||
http/connection.h
|
http/connection.h
|
||||||
http/httperror.h
|
http/httperror.h
|
||||||
|
@ -159,6 +160,7 @@ add_library(qbt_base STATIC
|
||||||
bittorrent/trackerentry.cpp
|
bittorrent/trackerentry.cpp
|
||||||
bittorrent/trackerentrystatus.cpp
|
bittorrent/trackerentrystatus.cpp
|
||||||
exceptions.cpp
|
exceptions.cpp
|
||||||
|
freediskspacechecker.cpp
|
||||||
http/connection.cpp
|
http/connection.cpp
|
||||||
http/httperror.cpp
|
http/httperror.cpp
|
||||||
http/requestparser.cpp
|
http/requestparser.cpp
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2015-2024 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2015-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -479,6 +479,8 @@ namespace BitTorrent
|
||||||
virtual QString lastExternalIPv4Address() const = 0;
|
virtual QString lastExternalIPv4Address() const = 0;
|
||||||
virtual QString lastExternalIPv6Address() const = 0;
|
virtual QString lastExternalIPv6Address() const = 0;
|
||||||
|
|
||||||
|
virtual qint64 freeDiskSpace() const = 0;
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void startupProgressUpdated(int progress);
|
void startupProgressUpdated(int progress);
|
||||||
void addTorrentFailed(const InfoHash &infoHash, const QString &reason);
|
void addTorrentFailed(const InfoHash &infoHash, const QString &reason);
|
||||||
|
@ -519,5 +521,6 @@ namespace BitTorrent
|
||||||
void trackerSuccess(Torrent *torrent, const QString &tracker);
|
void trackerSuccess(Torrent *torrent, const QString &tracker);
|
||||||
void trackerWarning(Torrent *torrent, const QString &tracker);
|
void trackerWarning(Torrent *torrent, const QString &tracker);
|
||||||
void trackerEntryStatusesUpdated(Torrent *torrent, const QHash<QString, TrackerEntryStatus> &updatedTrackers);
|
void trackerEntryStatusesUpdated(Torrent *torrent, const QHash<QString, TrackerEntryStatus> &updatedTrackers);
|
||||||
|
void freeDiskSpaceChecked(qint64 result);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2015-2024 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2015-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -76,6 +76,7 @@
|
||||||
#include <QUuid>
|
#include <QUuid>
|
||||||
|
|
||||||
#include "base/algorithm.h"
|
#include "base/algorithm.h"
|
||||||
|
#include "base/freediskspacechecker.h"
|
||||||
#include "base/global.h"
|
#include "base/global.h"
|
||||||
#include "base/logger.h"
|
#include "base/logger.h"
|
||||||
#include "base/net/downloadmanager.h"
|
#include "base/net/downloadmanager.h"
|
||||||
|
@ -115,6 +116,7 @@ using namespace BitTorrent;
|
||||||
|
|
||||||
const Path CATEGORIES_FILE_NAME {u"categories.json"_s};
|
const Path CATEGORIES_FILE_NAME {u"categories.json"_s};
|
||||||
const int MAX_PROCESSING_RESUMEDATA_COUNT = 50;
|
const int MAX_PROCESSING_RESUMEDATA_COUNT = 50;
|
||||||
|
const std::chrono::seconds FREEDISKSPACE_CHECK_TIMEOUT = 30s;
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
|
@ -540,6 +542,8 @@ SessionImpl::SessionImpl(QObject *parent)
|
||||||
, m_ioThread {new QThread}
|
, m_ioThread {new QThread}
|
||||||
, m_asyncWorker {new QThreadPool(this)}
|
, m_asyncWorker {new QThreadPool(this)}
|
||||||
, m_recentErroredTorrentsTimer {new QTimer(this)}
|
, m_recentErroredTorrentsTimer {new QTimer(this)}
|
||||||
|
, m_freeDiskSpaceChecker {new FreeDiskSpaceChecker(savePath())}
|
||||||
|
, m_freeDiskSpaceCheckingTimer {new QTimer(this)}
|
||||||
{
|
{
|
||||||
// It is required to perform async access to libtorrent sequentially
|
// It is required to perform async access to libtorrent sequentially
|
||||||
m_asyncWorker->setMaxThreadCount(1);
|
m_asyncWorker->setMaxThreadCount(1);
|
||||||
|
@ -600,6 +604,18 @@ SessionImpl::SessionImpl(QObject *parent)
|
||||||
, &Net::ProxyConfigurationManager::proxyConfigurationChanged
|
, &Net::ProxyConfigurationManager::proxyConfigurationChanged
|
||||||
, this, &SessionImpl::configureDeferred);
|
, this, &SessionImpl::configureDeferred);
|
||||||
|
|
||||||
|
m_freeDiskSpaceChecker->moveToThread(m_ioThread.get());
|
||||||
|
connect(m_ioThread.get(), &QThread::finished, m_freeDiskSpaceChecker, &QObject::deleteLater);
|
||||||
|
m_freeDiskSpaceCheckingTimer->setInterval(FREEDISKSPACE_CHECK_TIMEOUT);
|
||||||
|
m_freeDiskSpaceCheckingTimer->setSingleShot(true);
|
||||||
|
connect(m_freeDiskSpaceCheckingTimer, &QTimer::timeout, m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::check);
|
||||||
|
connect(m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::checked, this, [this](const qint64 value)
|
||||||
|
{
|
||||||
|
m_freeDiskSpace = value;
|
||||||
|
m_freeDiskSpaceCheckingTimer->start();
|
||||||
|
emit freeDiskSpaceChecked(m_freeDiskSpace);
|
||||||
|
});
|
||||||
|
|
||||||
m_fileSearcher = new FileSearcher;
|
m_fileSearcher = new FileSearcher;
|
||||||
m_fileSearcher->moveToThread(m_ioThread.get());
|
m_fileSearcher->moveToThread(m_ioThread.get());
|
||||||
connect(m_ioThread.get(), &QThread::finished, m_fileSearcher, &QObject::deleteLater);
|
connect(m_ioThread.get(), &QThread::finished, m_fileSearcher, &QObject::deleteLater);
|
||||||
|
@ -613,6 +629,8 @@ SessionImpl::SessionImpl(QObject *parent)
|
||||||
m_ioThread->setObjectName("SessionImpl m_ioThread");
|
m_ioThread->setObjectName("SessionImpl m_ioThread");
|
||||||
m_ioThread->start();
|
m_ioThread->start();
|
||||||
|
|
||||||
|
QMetaObject::invokeMethod(m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::check);
|
||||||
|
|
||||||
initMetrics();
|
initMetrics();
|
||||||
loadStatistics();
|
loadStatistics();
|
||||||
|
|
||||||
|
@ -3266,6 +3284,14 @@ void SessionImpl::setSavePath(const Path &path)
|
||||||
m_savePath = newPath;
|
m_savePath = newPath;
|
||||||
for (TorrentImpl *const torrent : asConst(m_torrents))
|
for (TorrentImpl *const torrent : asConst(m_torrents))
|
||||||
torrent->handleCategoryOptionsChanged();
|
torrent->handleCategoryOptionsChanged();
|
||||||
|
|
||||||
|
m_freeDiskSpace = -1;
|
||||||
|
m_freeDiskSpaceCheckingTimer->stop();
|
||||||
|
QMetaObject::invokeMethod(m_freeDiskSpaceChecker, [checker = m_freeDiskSpaceChecker, pathToCheck = m_savePath]
|
||||||
|
{
|
||||||
|
checker->setPathToCheck(pathToCheck);
|
||||||
|
checker->check();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
void SessionImpl::setDownloadPath(const Path &path)
|
void SessionImpl::setDownloadPath(const Path &path)
|
||||||
|
@ -5113,6 +5139,11 @@ QString SessionImpl::lastExternalIPv6Address() const
|
||||||
return m_lastExternalIPv6Address;
|
return m_lastExternalIPv6Address;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
qint64 SessionImpl::freeDiskSpace() const
|
||||||
|
{
|
||||||
|
return m_freeDiskSpace;
|
||||||
|
}
|
||||||
|
|
||||||
bool SessionImpl::isListening() const
|
bool SessionImpl::isListening() const
|
||||||
{
|
{
|
||||||
return m_nativeSessionExtension->isSessionListening();
|
return m_nativeSessionExtension->isSessionListening();
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2015-2024 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2015-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
* Copyright (C) 2006 Christophe Dumez <chris@qbittorrent.org>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -64,6 +64,7 @@ class QUrl;
|
||||||
class BandwidthScheduler;
|
class BandwidthScheduler;
|
||||||
class FileSearcher;
|
class FileSearcher;
|
||||||
class FilterParserThread;
|
class FilterParserThread;
|
||||||
|
class FreeDiskSpaceChecker;
|
||||||
class NativeSessionExtension;
|
class NativeSessionExtension;
|
||||||
|
|
||||||
namespace BitTorrent
|
namespace BitTorrent
|
||||||
|
@ -448,6 +449,8 @@ namespace BitTorrent
|
||||||
QString lastExternalIPv4Address() const override;
|
QString lastExternalIPv4Address() const override;
|
||||||
QString lastExternalIPv6Address() const override;
|
QString lastExternalIPv6Address() const override;
|
||||||
|
|
||||||
|
qint64 freeDiskSpace() const override;
|
||||||
|
|
||||||
// Torrent interface
|
// Torrent interface
|
||||||
void handleTorrentResumeDataRequested(const TorrentImpl *torrent);
|
void handleTorrentResumeDataRequested(const TorrentImpl *torrent);
|
||||||
void handleTorrentShareLimitChanged(TorrentImpl *torrent);
|
void handleTorrentShareLimitChanged(TorrentImpl *torrent);
|
||||||
|
@ -850,6 +853,10 @@ namespace BitTorrent
|
||||||
|
|
||||||
QList<TorrentImpl *> m_pendingFinishedTorrents;
|
QList<TorrentImpl *> m_pendingFinishedTorrents;
|
||||||
|
|
||||||
|
FreeDiskSpaceChecker *m_freeDiskSpaceChecker = nullptr;
|
||||||
|
QTimer *m_freeDiskSpaceCheckingTimer = nullptr;
|
||||||
|
qint64 m_freeDiskSpace = -1;
|
||||||
|
|
||||||
friend void Session::initInstance();
|
friend void Session::initInstance();
|
||||||
friend void Session::freeInstance();
|
friend void Session::freeInstance();
|
||||||
friend Session *Session::instance();
|
friend Session *Session::instance();
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2023 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2023-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2018 Thomas Piccirello <thomas.piccirello@gmail.com>
|
* Copyright (C) 2018 Thomas Piccirello <thomas.piccirello@gmail.com>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -29,16 +29,24 @@
|
||||||
|
|
||||||
#include "freediskspacechecker.h"
|
#include "freediskspacechecker.h"
|
||||||
|
|
||||||
#include "base/bittorrent/session.h"
|
|
||||||
#include "base/utils/fs.h"
|
#include "base/utils/fs.h"
|
||||||
|
|
||||||
qint64 FreeDiskSpaceChecker::lastResult() const
|
FreeDiskSpaceChecker::FreeDiskSpaceChecker(const Path &pathToCheck)
|
||||||
|
: m_pathToCheck {pathToCheck}
|
||||||
{
|
{
|
||||||
return m_lastResult;
|
}
|
||||||
|
|
||||||
|
Path FreeDiskSpaceChecker::pathToCheck() const
|
||||||
|
{
|
||||||
|
return m_pathToCheck;
|
||||||
|
}
|
||||||
|
|
||||||
|
void FreeDiskSpaceChecker::setPathToCheck(const Path &newPathToCheck)
|
||||||
|
{
|
||||||
|
m_pathToCheck = newPathToCheck;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FreeDiskSpaceChecker::check()
|
void FreeDiskSpaceChecker::check()
|
||||||
{
|
{
|
||||||
m_lastResult = Utils::Fs::freeDiskSpaceOnPath(BitTorrent::Session::instance()->savePath());
|
emit checked(Utils::Fs::freeDiskSpaceOnPath(m_pathToCheck));
|
||||||
emit checked(m_lastResult);
|
|
||||||
}
|
}
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2023 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2023-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2018 Thomas Piccirello <thomas.piccirello@gmail.com>
|
* Copyright (C) 2018 Thomas Piccirello <thomas.piccirello@gmail.com>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -31,15 +31,18 @@
|
||||||
|
|
||||||
#include <QObject>
|
#include <QObject>
|
||||||
|
|
||||||
|
#include "base/path.h"
|
||||||
|
|
||||||
class FreeDiskSpaceChecker final : public QObject
|
class FreeDiskSpaceChecker final : public QObject
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
Q_DISABLE_COPY_MOVE(FreeDiskSpaceChecker)
|
Q_DISABLE_COPY_MOVE(FreeDiskSpaceChecker)
|
||||||
|
|
||||||
public:
|
public:
|
||||||
using QObject::QObject;
|
FreeDiskSpaceChecker(const Path &pathToCheck);
|
||||||
|
|
||||||
qint64 lastResult() const;
|
Path pathToCheck() const;
|
||||||
|
void setPathToCheck(const Path &newPathToCheck);
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void check();
|
void check();
|
||||||
|
@ -48,5 +51,5 @@ signals:
|
||||||
void checked(qint64 freeSpaceSize);
|
void checked(qint64 freeSpaceSize);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
qint64 m_lastResult = 0;
|
Path m_pathToCheck;
|
||||||
};
|
};
|
|
@ -359,6 +359,19 @@ void Preferences::setStatusbarDisplayed(const bool displayed)
|
||||||
setValue(u"Preferences/General/StatusbarDisplayed"_s, displayed);
|
setValue(u"Preferences/General/StatusbarDisplayed"_s, displayed);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Preferences::isStatusbarFreeDiskSpaceDisplayed() const
|
||||||
|
{
|
||||||
|
return value(u"Preferences/General/StatusbarFreeDiskSpaceDisplayed"_s, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Preferences::setStatusbarFreeDiskSpaceDisplayed(const bool displayed)
|
||||||
|
{
|
||||||
|
if (displayed == isStatusbarFreeDiskSpaceDisplayed())
|
||||||
|
return;
|
||||||
|
|
||||||
|
setValue(u"Preferences/General/StatusbarFreeDiskSpaceDisplayed"_s, displayed);
|
||||||
|
}
|
||||||
|
|
||||||
bool Preferences::isStatusbarExternalIPDisplayed() const
|
bool Preferences::isStatusbarExternalIPDisplayed() const
|
||||||
{
|
{
|
||||||
return value(u"Preferences/General/StatusbarExternalIPDisplayed"_s, false);
|
return value(u"Preferences/General/StatusbarExternalIPDisplayed"_s, false);
|
||||||
|
|
|
@ -119,6 +119,8 @@ public:
|
||||||
void setHideZeroComboValues(int n);
|
void setHideZeroComboValues(int n);
|
||||||
bool isStatusbarDisplayed() const;
|
bool isStatusbarDisplayed() const;
|
||||||
void setStatusbarDisplayed(bool displayed);
|
void setStatusbarDisplayed(bool displayed);
|
||||||
|
bool isStatusbarFreeDiskSpaceDisplayed() const;
|
||||||
|
void setStatusbarFreeDiskSpaceDisplayed(bool displayed);
|
||||||
bool isStatusbarExternalIPDisplayed() const;
|
bool isStatusbarExternalIPDisplayed() const;
|
||||||
void setStatusbarExternalIPDisplayed(bool displayed);
|
void setStatusbarExternalIPDisplayed(bool displayed);
|
||||||
bool isToolbarDisplayed() const;
|
bool isToolbarDisplayed() const;
|
||||||
|
|
|
@ -355,6 +355,7 @@ void OptionsDialog::loadBehaviorTabOptions()
|
||||||
// Groupbox's check state must be initialized after some of its children if they are manually enabled/disabled
|
// Groupbox's check state must be initialized after some of its children if they are manually enabled/disabled
|
||||||
m_ui->checkFileLog->setChecked(app()->isFileLoggerEnabled());
|
m_ui->checkFileLog->setChecked(app()->isFileLoggerEnabled());
|
||||||
|
|
||||||
|
m_ui->checkBoxFreeDiskSpaceStatusBar->setChecked(pref->isStatusbarFreeDiskSpaceDisplayed());
|
||||||
m_ui->checkBoxExternalIPStatusBar->setChecked(pref->isStatusbarExternalIPDisplayed());
|
m_ui->checkBoxExternalIPStatusBar->setChecked(pref->isStatusbarExternalIPDisplayed());
|
||||||
m_ui->checkBoxPerformanceWarning->setChecked(session->isPerformanceWarningEnabled());
|
m_ui->checkBoxPerformanceWarning->setChecked(session->isPerformanceWarningEnabled());
|
||||||
|
|
||||||
|
@ -443,6 +444,7 @@ void OptionsDialog::loadBehaviorTabOptions()
|
||||||
connect(m_ui->spinFileLogAge, qSpinBoxValueChanged, this, &ThisType::enableApplyButton);
|
connect(m_ui->spinFileLogAge, qSpinBoxValueChanged, this, &ThisType::enableApplyButton);
|
||||||
connect(m_ui->comboFileLogAgeType, qComboBoxCurrentIndexChanged, this, &ThisType::enableApplyButton);
|
connect(m_ui->comboFileLogAgeType, qComboBoxCurrentIndexChanged, this, &ThisType::enableApplyButton);
|
||||||
|
|
||||||
|
connect(m_ui->checkBoxFreeDiskSpaceStatusBar, &QAbstractButton::toggled, this, &ThisType::enableApplyButton);
|
||||||
connect(m_ui->checkBoxExternalIPStatusBar, &QAbstractButton::toggled, this, &ThisType::enableApplyButton);
|
connect(m_ui->checkBoxExternalIPStatusBar, &QAbstractButton::toggled, this, &ThisType::enableApplyButton);
|
||||||
connect(m_ui->checkBoxPerformanceWarning, &QAbstractButton::toggled, this, &ThisType::enableApplyButton);
|
connect(m_ui->checkBoxPerformanceWarning, &QAbstractButton::toggled, this, &ThisType::enableApplyButton);
|
||||||
}
|
}
|
||||||
|
@ -536,6 +538,7 @@ void OptionsDialog::saveBehaviorTabOptions() const
|
||||||
|
|
||||||
app()->setStartUpWindowState(m_ui->windowStateComboBox->currentData().value<WindowState>());
|
app()->setStartUpWindowState(m_ui->windowStateComboBox->currentData().value<WindowState>());
|
||||||
|
|
||||||
|
pref->setStatusbarFreeDiskSpaceDisplayed(m_ui->checkBoxFreeDiskSpaceStatusBar->isChecked());
|
||||||
pref->setStatusbarExternalIPDisplayed(m_ui->checkBoxExternalIPStatusBar->isChecked());
|
pref->setStatusbarExternalIPDisplayed(m_ui->checkBoxExternalIPStatusBar->isChecked());
|
||||||
session->setPerformanceWarningEnabled(m_ui->checkBoxPerformanceWarning->isChecked());
|
session->setPerformanceWarningEnabled(m_ui->checkBoxPerformanceWarning->isChecked());
|
||||||
}
|
}
|
||||||
|
|
|
@ -819,6 +819,13 @@
|
||||||
</layout>
|
</layout>
|
||||||
</widget>
|
</widget>
|
||||||
</item>
|
</item>
|
||||||
|
<item>
|
||||||
|
<widget class="QCheckBox" name="checkBoxFreeDiskSpaceStatusBar">
|
||||||
|
<property name="text">
|
||||||
|
<string>Show free disk space in status bar</string>
|
||||||
|
</property>
|
||||||
|
</widget>
|
||||||
|
</item>
|
||||||
<item>
|
<item>
|
||||||
<widget class="QCheckBox" name="checkBoxExternalIPStatusBar">
|
<widget class="QCheckBox" name="checkBoxExternalIPStatusBar">
|
||||||
<property name="text">
|
<property name="text">
|
||||||
|
|
|
@ -44,6 +44,19 @@
|
||||||
#include "uithememanager.h"
|
#include "uithememanager.h"
|
||||||
#include "utils.h"
|
#include "utils.h"
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
|
QWidget *createSeparator(QWidget *parent)
|
||||||
|
{
|
||||||
|
QFrame *separator = new QFrame(parent);
|
||||||
|
separator->setFrameStyle(QFrame::VLine);
|
||||||
|
#ifndef Q_OS_MACOS
|
||||||
|
separator->setFrameShadow(QFrame::Raised);
|
||||||
|
#endif
|
||||||
|
return separator;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
StatusBar::StatusBar(QWidget *parent)
|
StatusBar::StatusBar(QWidget *parent)
|
||||||
: QStatusBar(parent)
|
: QStatusBar(parent)
|
||||||
{
|
{
|
||||||
|
@ -87,11 +100,17 @@ StatusBar::StatusBar(QWidget *parent)
|
||||||
m_upSpeedLbl->setStyleSheet(u"text-align:left;"_s);
|
m_upSpeedLbl->setStyleSheet(u"text-align:left;"_s);
|
||||||
m_upSpeedLbl->setMinimumWidth(200);
|
m_upSpeedLbl->setMinimumWidth(200);
|
||||||
|
|
||||||
|
m_freeDiskSpaceLbl = new QLabel(tr("Free space: N/A"));
|
||||||
|
m_freeDiskSpaceLbl->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
||||||
|
m_freeDiskSpaceSeparator = createSeparator(m_freeDiskSpaceLbl);
|
||||||
|
|
||||||
m_lastExternalIPsLbl = new QLabel(tr("External IP: N/A"));
|
m_lastExternalIPsLbl = new QLabel(tr("External IP: N/A"));
|
||||||
m_lastExternalIPsLbl->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
m_lastExternalIPsLbl->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
||||||
|
m_lastExternalIPsSeparator = createSeparator(m_lastExternalIPsLbl);
|
||||||
|
|
||||||
m_DHTLbl = new QLabel(tr("DHT: %1 nodes").arg(0), this);
|
m_DHTLbl = new QLabel(tr("DHT: %1 nodes").arg(0), this);
|
||||||
m_DHTLbl->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
m_DHTLbl->setSizePolicy(QSizePolicy::Maximum, QSizePolicy::Preferred);
|
||||||
|
m_DHTSeparator = createSeparator(m_DHTLbl);
|
||||||
|
|
||||||
m_altSpeedsBtn = new QPushButton(this);
|
m_altSpeedsBtn = new QPushButton(this);
|
||||||
m_altSpeedsBtn->setFlat(true);
|
m_altSpeedsBtn->setFlat(true);
|
||||||
|
@ -113,52 +132,42 @@ StatusBar::StatusBar(QWidget *parent)
|
||||||
m_connecStatusLblIcon->setMaximumWidth(Utils::Gui::largeIconSize().width());
|
m_connecStatusLblIcon->setMaximumWidth(Utils::Gui::largeIconSize().width());
|
||||||
m_altSpeedsBtn->setMaximumWidth(Utils::Gui::largeIconSize().width());
|
m_altSpeedsBtn->setMaximumWidth(Utils::Gui::largeIconSize().width());
|
||||||
|
|
||||||
QFrame *statusSep1 = new QFrame(this);
|
layout->addWidget(m_freeDiskSpaceLbl);
|
||||||
statusSep1->setFrameStyle(QFrame::VLine);
|
layout->addWidget(m_freeDiskSpaceSeparator);
|
||||||
#ifndef Q_OS_MACOS
|
|
||||||
statusSep1->setFrameShadow(QFrame::Raised);
|
|
||||||
#endif
|
|
||||||
QFrame *statusSep2 = new QFrame(this);
|
|
||||||
statusSep2->setFrameStyle(QFrame::VLine);
|
|
||||||
#ifndef Q_OS_MACOS
|
|
||||||
statusSep2->setFrameShadow(QFrame::Raised);
|
|
||||||
#endif
|
|
||||||
QFrame *statusSep3 = new QFrame(this);
|
|
||||||
statusSep3->setFrameStyle(QFrame::VLine);
|
|
||||||
#ifndef Q_OS_MACOS
|
|
||||||
statusSep3->setFrameShadow(QFrame::Raised);
|
|
||||||
#endif
|
|
||||||
QFrame *statusSep4 = new QFrame(this);
|
|
||||||
statusSep4->setFrameStyle(QFrame::VLine);
|
|
||||||
#ifndef Q_OS_MACOS
|
|
||||||
statusSep4->setFrameShadow(QFrame::Raised);
|
|
||||||
#endif
|
|
||||||
QFrame *statusSep5 = new QFrame(this);
|
|
||||||
statusSep5->setFrameStyle(QFrame::VLine);
|
|
||||||
#ifndef Q_OS_MACOS
|
|
||||||
statusSep5->setFrameShadow(QFrame::Raised);
|
|
||||||
#endif
|
|
||||||
layout->addWidget(m_lastExternalIPsLbl);
|
layout->addWidget(m_lastExternalIPsLbl);
|
||||||
layout->addWidget(statusSep1);
|
layout->addWidget(m_lastExternalIPsSeparator);
|
||||||
|
|
||||||
layout->addWidget(m_DHTLbl);
|
layout->addWidget(m_DHTLbl);
|
||||||
layout->addWidget(statusSep2);
|
layout->addWidget(m_DHTSeparator);
|
||||||
|
|
||||||
layout->addWidget(m_connecStatusLblIcon);
|
layout->addWidget(m_connecStatusLblIcon);
|
||||||
layout->addWidget(statusSep3);
|
layout->addWidget(createSeparator(m_connecStatusLblIcon));
|
||||||
|
|
||||||
layout->addWidget(m_altSpeedsBtn);
|
layout->addWidget(m_altSpeedsBtn);
|
||||||
layout->addWidget(statusSep4);
|
layout->addWidget(createSeparator(m_altSpeedsBtn));
|
||||||
|
|
||||||
layout->addWidget(m_dlSpeedLbl);
|
layout->addWidget(m_dlSpeedLbl);
|
||||||
layout->addWidget(statusSep5);
|
layout->addWidget(createSeparator(m_dlSpeedLbl));
|
||||||
|
|
||||||
layout->addWidget(m_upSpeedLbl);
|
layout->addWidget(m_upSpeedLbl);
|
||||||
|
|
||||||
addPermanentWidget(container);
|
addPermanentWidget(container);
|
||||||
setStyleSheet(u"QWidget {margin: 0;}"_s);
|
setStyleSheet(u"QWidget {margin: 0;}"_s);
|
||||||
container->adjustSize();
|
container->adjustSize();
|
||||||
adjustSize();
|
adjustSize();
|
||||||
|
updateFreeDiskSpaceVisibility();
|
||||||
updateExternalAddressesVisibility();
|
updateExternalAddressesVisibility();
|
||||||
// Is DHT enabled
|
// Is DHT enabled
|
||||||
m_DHTLbl->setVisible(session->isDHTEnabled());
|
const bool isDHTVisible = session->isDHTEnabled();
|
||||||
|
m_DHTLbl->setVisible(isDHTVisible);
|
||||||
|
m_DHTSeparator->setVisible(isDHTVisible);
|
||||||
refresh();
|
refresh();
|
||||||
connect(session, &BitTorrent::Session::statsUpdated, this, &StatusBar::refresh);
|
connect(session, &BitTorrent::Session::statsUpdated, this, &StatusBar::refresh);
|
||||||
|
|
||||||
|
updateFreeDiskSpaceLabel(session->freeDiskSpace());
|
||||||
|
connect(session, &BitTorrent::Session::freeDiskSpaceChecked, this, &StatusBar::updateFreeDiskSpaceLabel);
|
||||||
|
|
||||||
connect(Preferences::instance(), &Preferences::changed, this, &StatusBar::optionsSaved);
|
connect(Preferences::instance(), &Preferences::changed, this, &StatusBar::optionsSaved);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -216,15 +225,28 @@ void StatusBar::updateDHTNodesNumber()
|
||||||
if (BitTorrent::Session::instance()->isDHTEnabled())
|
if (BitTorrent::Session::instance()->isDHTEnabled())
|
||||||
{
|
{
|
||||||
m_DHTLbl->setVisible(true);
|
m_DHTLbl->setVisible(true);
|
||||||
m_DHTLbl->setText(tr("DHT: %1 nodes")
|
m_DHTSeparator->setVisible(true);
|
||||||
.arg(BitTorrent::Session::instance()->status().dhtNodes));
|
m_DHTLbl->setText(tr("DHT: %1 nodes").arg(BitTorrent::Session::instance()->status().dhtNodes));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
m_DHTLbl->setVisible(false);
|
m_DHTLbl->setVisible(false);
|
||||||
|
m_DHTSeparator->setVisible(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void StatusBar::updateFreeDiskSpaceLabel(const qint64 value)
|
||||||
|
{
|
||||||
|
m_freeDiskSpaceLbl->setText(tr("Free space: ") + Utils::Misc::friendlyUnit(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
void StatusBar::updateFreeDiskSpaceVisibility()
|
||||||
|
{
|
||||||
|
const bool isVisible = Preferences::instance()->isStatusbarFreeDiskSpaceDisplayed();
|
||||||
|
m_freeDiskSpaceLbl->setVisible(isVisible);
|
||||||
|
m_freeDiskSpaceSeparator->setVisible(isVisible);
|
||||||
|
}
|
||||||
|
|
||||||
void StatusBar::updateExternalAddressesLabel()
|
void StatusBar::updateExternalAddressesLabel()
|
||||||
{
|
{
|
||||||
const QString lastExternalIPv4Address = BitTorrent::Session::instance()->lastExternalIPv4Address();
|
const QString lastExternalIPv4Address = BitTorrent::Session::instance()->lastExternalIPv4Address();
|
||||||
|
@ -244,7 +266,9 @@ void StatusBar::updateExternalAddressesLabel()
|
||||||
|
|
||||||
void StatusBar::updateExternalAddressesVisibility()
|
void StatusBar::updateExternalAddressesVisibility()
|
||||||
{
|
{
|
||||||
m_lastExternalIPsLbl->setVisible(Preferences::instance()->isStatusbarExternalIPDisplayed());
|
const bool isVisible = Preferences::instance()->isStatusbarExternalIPDisplayed();
|
||||||
|
m_lastExternalIPsLbl->setVisible(isVisible);
|
||||||
|
m_lastExternalIPsSeparator->setVisible(isVisible);
|
||||||
}
|
}
|
||||||
|
|
||||||
void StatusBar::updateSpeedLabels()
|
void StatusBar::updateSpeedLabels()
|
||||||
|
@ -300,5 +324,6 @@ void StatusBar::capSpeed()
|
||||||
|
|
||||||
void StatusBar::optionsSaved()
|
void StatusBar::optionsSaved()
|
||||||
{
|
{
|
||||||
|
updateFreeDiskSpaceVisibility();
|
||||||
updateExternalAddressesVisibility();
|
updateExternalAddressesVisibility();
|
||||||
}
|
}
|
||||||
|
|
|
@ -63,14 +63,20 @@ private slots:
|
||||||
private:
|
private:
|
||||||
void updateConnectionStatus();
|
void updateConnectionStatus();
|
||||||
void updateDHTNodesNumber();
|
void updateDHTNodesNumber();
|
||||||
|
void updateFreeDiskSpaceLabel(qint64 value);
|
||||||
|
void updateFreeDiskSpaceVisibility();
|
||||||
void updateExternalAddressesLabel();
|
void updateExternalAddressesLabel();
|
||||||
void updateExternalAddressesVisibility();
|
void updateExternalAddressesVisibility();
|
||||||
void updateSpeedLabels();
|
void updateSpeedLabels();
|
||||||
|
|
||||||
QPushButton *m_dlSpeedLbl = nullptr;
|
QPushButton *m_dlSpeedLbl = nullptr;
|
||||||
QPushButton *m_upSpeedLbl = nullptr;
|
QPushButton *m_upSpeedLbl = nullptr;
|
||||||
|
QLabel *m_freeDiskSpaceLbl = nullptr;
|
||||||
|
QWidget *m_freeDiskSpaceSeparator = nullptr;
|
||||||
QLabel *m_lastExternalIPsLbl = nullptr;
|
QLabel *m_lastExternalIPsLbl = nullptr;
|
||||||
|
QWidget *m_lastExternalIPsSeparator = nullptr;
|
||||||
QLabel *m_DHTLbl = nullptr;
|
QLabel *m_DHTLbl = nullptr;
|
||||||
|
QWidget *m_DHTSeparator = nullptr;
|
||||||
QPushButton *m_connecStatusLblIcon = nullptr;
|
QPushButton *m_connecStatusLblIcon = nullptr;
|
||||||
QPushButton *m_altSpeedsBtn = nullptr;
|
QPushButton *m_altSpeedsBtn = nullptr;
|
||||||
};
|
};
|
||||||
|
|
|
@ -13,7 +13,6 @@ add_library(qbt_webui STATIC
|
||||||
api/torrentscontroller.h
|
api/torrentscontroller.h
|
||||||
api/transfercontroller.h
|
api/transfercontroller.h
|
||||||
api/serialize/serialize_torrent.h
|
api/serialize/serialize_torrent.h
|
||||||
freediskspacechecker.h
|
|
||||||
webapplication.h
|
webapplication.h
|
||||||
webui.h
|
webui.h
|
||||||
|
|
||||||
|
@ -30,7 +29,6 @@ add_library(qbt_webui STATIC
|
||||||
api/torrentscontroller.cpp
|
api/torrentscontroller.cpp
|
||||||
api/transfercontroller.cpp
|
api/transfercontroller.cpp
|
||||||
api/serialize/serialize_torrent.cpp
|
api/serialize/serialize_torrent.cpp
|
||||||
freediskspacechecker.cpp
|
|
||||||
webapplication.cpp
|
webapplication.cpp
|
||||||
webui.cpp
|
webui.cpp
|
||||||
)
|
)
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2014-2024 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2014-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2024 Radu Carpa <radu.carpa@cern.ch>
|
* Copyright (C) 2024 Radu Carpa <radu.carpa@cern.ch>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -43,10 +43,10 @@
|
||||||
#include <QNetworkCookie>
|
#include <QNetworkCookie>
|
||||||
#include <QRegularExpression>
|
#include <QRegularExpression>
|
||||||
#include <QThread>
|
#include <QThread>
|
||||||
#include <QTimer>
|
|
||||||
#include <QUrl>
|
#include <QUrl>
|
||||||
|
|
||||||
#include "base/algorithm.h"
|
#include "base/algorithm.h"
|
||||||
|
#include "base/bittorrent/session.h"
|
||||||
#include "base/bittorrent/torrentcreationmanager.h"
|
#include "base/bittorrent/torrentcreationmanager.h"
|
||||||
#include "base/http/httperror.h"
|
#include "base/http/httperror.h"
|
||||||
#include "base/logger.h"
|
#include "base/logger.h"
|
||||||
|
@ -67,7 +67,6 @@
|
||||||
#include "api/torrentcreatorcontroller.h"
|
#include "api/torrentcreatorcontroller.h"
|
||||||
#include "api/torrentscontroller.h"
|
#include "api/torrentscontroller.h"
|
||||||
#include "api/transfercontroller.h"
|
#include "api/transfercontroller.h"
|
||||||
#include "freediskspacechecker.h"
|
|
||||||
|
|
||||||
const int MAX_ALLOWED_FILESIZE = 10 * 1024 * 1024;
|
const int MAX_ALLOWED_FILESIZE = 10 * 1024 * 1024;
|
||||||
const QString DEFAULT_SESSION_COOKIE_NAME = u"SID"_s;
|
const QString DEFAULT_SESSION_COOKIE_NAME = u"SID"_s;
|
||||||
|
@ -76,10 +75,6 @@ const QString WWW_FOLDER = u":/www"_s;
|
||||||
const QString PUBLIC_FOLDER = u"/public"_s;
|
const QString PUBLIC_FOLDER = u"/public"_s;
|
||||||
const QString PRIVATE_FOLDER = u"/private"_s;
|
const QString PRIVATE_FOLDER = u"/private"_s;
|
||||||
|
|
||||||
using namespace std::chrono_literals;
|
|
||||||
|
|
||||||
const std::chrono::seconds FREEDISKSPACE_CHECK_TIMEOUT = 30s;
|
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
QStringMap parseCookie(const QStringView cookieStr)
|
QStringMap parseCookie(const QStringView cookieStr)
|
||||||
|
@ -161,9 +156,6 @@ WebApplication::WebApplication(IApplication *app, QObject *parent)
|
||||||
: ApplicationComponent(app, parent)
|
: ApplicationComponent(app, parent)
|
||||||
, m_cacheID {QString::number(Utils::Random::rand(), 36)}
|
, m_cacheID {QString::number(Utils::Random::rand(), 36)}
|
||||||
, m_authController {new AuthController(this, app, this)}
|
, m_authController {new AuthController(this, app, this)}
|
||||||
, m_workerThread {new QThread}
|
|
||||||
, m_freeDiskSpaceChecker {new FreeDiskSpaceChecker}
|
|
||||||
, m_freeDiskSpaceCheckingTimer {new QTimer(this)}
|
|
||||||
, m_torrentCreationManager {new BitTorrent::TorrentCreationManager(app, this)}
|
, m_torrentCreationManager {new BitTorrent::TorrentCreationManager(app, this)}
|
||||||
{
|
{
|
||||||
declarePublicAPI(u"auth/login"_s);
|
declarePublicAPI(u"auth/login"_s);
|
||||||
|
@ -181,17 +173,6 @@ WebApplication::WebApplication(IApplication *app, QObject *parent)
|
||||||
}
|
}
|
||||||
m_sessionCookieName = DEFAULT_SESSION_COOKIE_NAME;
|
m_sessionCookieName = DEFAULT_SESSION_COOKIE_NAME;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_freeDiskSpaceChecker->moveToThread(m_workerThread.get());
|
|
||||||
connect(m_workerThread.get(), &QThread::finished, m_freeDiskSpaceChecker, &QObject::deleteLater);
|
|
||||||
m_workerThread->setObjectName("WebApplication m_workerThread");
|
|
||||||
m_workerThread->start();
|
|
||||||
|
|
||||||
m_freeDiskSpaceCheckingTimer->setInterval(FREEDISKSPACE_CHECK_TIMEOUT);
|
|
||||||
m_freeDiskSpaceCheckingTimer->setSingleShot(true);
|
|
||||||
connect(m_freeDiskSpaceCheckingTimer, &QTimer::timeout, m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::check);
|
|
||||||
connect(m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::checked, m_freeDiskSpaceCheckingTimer, qOverload<>(&QTimer::start));
|
|
||||||
QMetaObject::invokeMethod(m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::check);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
WebApplication::~WebApplication()
|
WebApplication::~WebApplication()
|
||||||
|
@ -739,9 +720,10 @@ void WebApplication::sessionStart()
|
||||||
m_currentSession->registerAPIController(u"torrents"_s, new TorrentsController(app(), m_currentSession));
|
m_currentSession->registerAPIController(u"torrents"_s, new TorrentsController(app(), m_currentSession));
|
||||||
m_currentSession->registerAPIController(u"transfer"_s, new TransferController(app(), m_currentSession));
|
m_currentSession->registerAPIController(u"transfer"_s, new TransferController(app(), m_currentSession));
|
||||||
|
|
||||||
|
const auto *btSession = BitTorrent::Session::instance();
|
||||||
auto *syncController = new SyncController(app(), m_currentSession);
|
auto *syncController = new SyncController(app(), m_currentSession);
|
||||||
syncController->updateFreeDiskSpace(m_freeDiskSpaceChecker->lastResult());
|
syncController->updateFreeDiskSpace(btSession->freeDiskSpace());
|
||||||
connect(m_freeDiskSpaceChecker, &FreeDiskSpaceChecker::checked, syncController, &SyncController::updateFreeDiskSpace);
|
connect(btSession, &BitTorrent::Session::freeDiskSpaceChecked, syncController, &SyncController::updateFreeDiskSpace);
|
||||||
m_currentSession->registerAPIController(u"sync"_s, syncController);
|
m_currentSession->registerAPIController(u"sync"_s, syncController);
|
||||||
|
|
||||||
QNetworkCookie cookie {m_sessionCookieName.toLatin1(), m_currentSession->id().toLatin1()};
|
QNetworkCookie cookie {m_sessionCookieName.toLatin1(), m_currentSession->id().toLatin1()};
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Bittorrent Client using Qt and libtorrent.
|
* Bittorrent Client using Qt and libtorrent.
|
||||||
* Copyright (C) 2014-2024 Vladimir Golovnev <glassez@yandex.ru>
|
* Copyright (C) 2014-2025 Vladimir Golovnev <glassez@yandex.ru>
|
||||||
* Copyright (C) 2024 Radu Carpa <radu.carpa@cern.ch>
|
* Copyright (C) 2024 Radu Carpa <radu.carpa@cern.ch>
|
||||||
*
|
*
|
||||||
* This program is free software; you can redistribute it and/or
|
* This program is free software; you can redistribute it and/or
|
||||||
|
@ -50,17 +50,13 @@
|
||||||
#include "base/http/types.h"
|
#include "base/http/types.h"
|
||||||
#include "base/path.h"
|
#include "base/path.h"
|
||||||
#include "base/utils/net.h"
|
#include "base/utils/net.h"
|
||||||
#include "base/utils/thread.h"
|
|
||||||
#include "base/utils/version.h"
|
#include "base/utils/version.h"
|
||||||
#include "api/isessionmanager.h"
|
#include "api/isessionmanager.h"
|
||||||
|
|
||||||
inline const Utils::Version<3, 2> API_VERSION {2, 11, 4};
|
inline const Utils::Version<3, 2> API_VERSION {2, 11, 4};
|
||||||
|
|
||||||
class QTimer;
|
|
||||||
|
|
||||||
class APIController;
|
class APIController;
|
||||||
class AuthController;
|
class AuthController;
|
||||||
class FreeDiskSpaceChecker;
|
|
||||||
class WebApplication;
|
class WebApplication;
|
||||||
|
|
||||||
namespace BitTorrent
|
namespace BitTorrent
|
||||||
|
@ -259,8 +255,5 @@ private:
|
||||||
|
|
||||||
QList<Http::Header> m_prebuiltHeaders;
|
QList<Http::Header> m_prebuiltHeaders;
|
||||||
|
|
||||||
Utils::Thread::UniquePtr m_workerThread;
|
|
||||||
FreeDiskSpaceChecker *m_freeDiskSpaceChecker = nullptr;
|
|
||||||
QTimer *m_freeDiskSpaceCheckingTimer = nullptr;
|
|
||||||
BitTorrent::TorrentCreationManager *m_torrentCreationManager = nullptr;
|
BitTorrent::TorrentCreationManager *m_torrentCreationManager = nullptr;
|
||||||
};
|
};
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue