Add UI to configure what information should be considered to compute overall status

* See https://github.com/Martchus/syncthingtray/issues/74
* See https://github.com/Martchus/syncthingtray/issues/76
This commit is contained in:
Martchus 2021-01-01 20:48:19 +01:00
parent 76ee21500d
commit ed495ec667
9 changed files with 212 additions and 60 deletions

View File

@ -820,8 +820,8 @@ void SyncthingConnection::setStatus(SyncthingStatus status)
m_autoReconnectTries = 0;
// skip if no further status information should be gathered
status = SyncthingStatus::Idle;
if (m_statusComputionFlags == SyncthingStatusComputionFlags::None) {
status = SyncthingStatus::Idle;
break;
}
@ -866,20 +866,14 @@ void SyncthingConnection::setStatus(SyncthingStatus status)
status = SyncthingStatus::RemoteNotInSync;
} else if (scanning) {
status = SyncthingStatus::Scanning;
} else {
} else if (m_statusComputionFlags & SyncthingStatusComputionFlags::DevicePaused) {
// check whether at least one device is paused
bool paused = false;
for (const SyncthingDev &dev : m_devs) {
if (dev.paused) {
paused = true;
status = SyncthingStatus::Paused;
break;
}
}
if (paused) {
status = SyncthingStatus::Paused;
} else {
status = SyncthingStatus::Idle;
}
}
}
if (m_status != status) {

View File

@ -27,10 +27,15 @@ QT_FORWARD_DECLARE_CLASS(QJsonParseError)
class ConnectionTests;
class MiscTests;
#define SYNCTHING_CONNECTOR_ENUM_CLASS enum class
namespace Data {
SYNCTHING_CONNECTOR_ENUM_CLASS SyncthingStatusComputionFlags : quint64;
}
#undef SYNCTHING_CONNECTOR_ENUM_CLASS
namespace Data {
struct SyncthingConnectionSettings;
enum class SyncthingStatusComputionFlags : quint64;
LIB_SYNCTHING_CONNECTOR_EXPORT QNetworkAccessManager &networkAccessManager();

View File

@ -16,6 +16,7 @@ set(HEADER_FILES
syncthingdownloadmodel.h
syncthingrecentchangesmodel.h
syncthingsortfiltermodel.h
syncthingstatuscomputionmodel.h
syncthingstatusselectionmodel.h
syncthingicons.h
colors.h)
@ -26,6 +27,7 @@ set(SRC_FILES
syncthingdownloadmodel.cpp
syncthingrecentchangesmodel.cpp
syncthingsortfiltermodel.cpp
syncthingstatuscomputionmodel.cpp
syncthingstatusselectionmodel.cpp
syncthingicons.cpp)
set(RES_FILES resources/${META_PROJECT_NAME}icons.qrc)

View File

@ -0,0 +1,67 @@
#include "./syncthingstatuscomputionmodel.h"
#include "../connector/syncthingconnectionsettings.h"
#include <type_traits>
using namespace QtUtilities;
namespace Data {
using FlagType = SyncthingStatusComputionFlags;
using UnderlyingFlagType = std::underlying_type_t<FlagType>;
inline static ChecklistItem itemFor(SyncthingStatusComputionFlags oneFlag)
{
return ChecklistItem(
static_cast<UnderlyingFlagType>(oneFlag), QString(), SyncthingStatusComputionFlags::Default & oneFlag ? Qt::Checked : Qt::Unchecked);
}
SyncthingStatusComputionModel::SyncthingStatusComputionModel(QObject *parent)
: ChecklistModel(parent)
{
setItems({
itemFor(SyncthingStatusComputionFlags::Scanning),
itemFor(SyncthingStatusComputionFlags::Synchronizing),
itemFor(SyncthingStatusComputionFlags::RemoteSynchronizing),
itemFor(SyncthingStatusComputionFlags::DevicePaused),
});
}
QString SyncthingStatusComputionModel::labelForId(const QVariant &id) const
{
switch (static_cast<SyncthingStatusComputionFlags>(id.toInt())) {
case SyncthingStatusComputionFlags::Scanning:
return tr("Local dir is scanning");
case SyncthingStatusComputionFlags::Synchronizing:
return tr("Local dir is synchronizing");
case SyncthingStatusComputionFlags::RemoteSynchronizing:
return tr("Remote dir has outstanding progress");
case SyncthingStatusComputionFlags::DevicePaused:
return tr("A device is paused");
default:
return id.toString();
}
}
SyncthingStatusComputionFlags SyncthingStatusComputionModel::statusComputionFlags() const
{
auto flags = SyncthingStatusComputionFlags::None;
for (auto row = 0, rows = rowCount(); row != rows; ++row) {
const auto i = index(row);
if (i.data(Qt::CheckStateRole).toInt() == Qt::Checked) {
flags += static_cast<SyncthingStatusComputionFlags>(i.data(idRole()).value<UnderlyingFlagType>());
}
}
return flags;
}
void SyncthingStatusComputionModel::setStatusComputionFlags(SyncthingStatusComputionFlags flags)
{
for (auto row = 0, rows = rowCount(); row != rows; ++row) {
const auto i = index(row);
setData(i, flags & static_cast<FlagType>(i.data(idRole()).value<UnderlyingFlagType>()) ? Qt::Checked : Qt::Unchecked, Qt::CheckStateRole);
}
}
} // namespace Data

View File

@ -0,0 +1,28 @@
#ifndef DATA_SYNCTHINGSTATUSCOMPUTIONMODELL_H
#define DATA_SYNCTHINGSTATUSCOMPUTIONMODELL_H
#include "./global.h"
#include <qtutilities/models/checklistmodel.h>
#define SYNCTHING_MODEL_ENUM_CLASS enum class
namespace Data {
SYNCTHING_MODEL_ENUM_CLASS SyncthingStatusComputionFlags : quint64;
}
#undef SYNCTHING_MODEL_ENUM_CLASS
namespace Data {
class LIB_SYNCTHING_MODEL_EXPORT SyncthingStatusComputionModel : public QtUtilities::ChecklistModel {
Q_OBJECT
public:
explicit SyncthingStatusComputionModel(QObject *parent = nullptr);
QString labelForId(const QVariant &id) const override;
SyncthingStatusComputionFlags statusComputionFlags() const;
void setStatusComputionFlags(SyncthingStatusComputionFlags flags);
};
} // namespace Data
#endif // DATA_SYNCTHINGSTATUSCOMPUTIONMODELL_H

View File

@ -6,7 +6,7 @@ using namespace QtUtilities;
namespace Data {
inline ChecklistItem itemFor(SyncthingStatus status)
inline static ChecklistItem itemFor(SyncthingStatus status)
{
return ChecklistItem(static_cast<int>(status), QString(), Qt::Unchecked);
}

View File

@ -3,7 +3,7 @@
<class>QtGui::ConnectionOptionPage</class>
<widget class="QWidget" name="QtGui::ConnectionOptionPage">
<property name="sizePolicy">
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
<sizepolicy hsizetype="Preferred" vsizetype="MinimumExpanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
@ -263,6 +263,51 @@
</property>
</widget>
</item>
<item row="10" column="1">
<layout class="QHBoxLayout" name="insertFromConfigFileLayout">
<property name="spacing">
<number>0</number>
</property>
<item>
<widget class="QPushButton" name="insertFromConfigFilePushButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="styleSheet">
<string notr="true">font-weight: bold;</string>
</property>
<property name="text">
<string>Insert values from local Syncthing configuration</string>
</property>
<property name="icon">
<iconset theme="edit-paste" resource="../resources/syncthingwidgetsicons.qrc">
<normaloff>:/icons/hicolor/scalable/actions/edit-paste.svg</normaloff>:/icons/hicolor/scalable/actions/edit-paste.svg</iconset>
</property>
</widget>
</item>
<item>
<widget class="QPushButton" name="insertFromCustomConfigFilePushButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Fixed" vsizetype="Preferred">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="toolTip">
<string>Select config file manually</string>
</property>
<property name="icon">
<iconset theme="document-open">
<normaloff>.</normaloff>
<normalon>:/icons/hicolor/scalable/actions/document-open.svg</normalon>.</iconset>
</property>
</widget>
</item>
</layout>
</item>
<item row="11" column="1">
<widget class="Line" name="line2">
<property name="sizePolicy">
@ -437,20 +482,69 @@
</widget>
</item>
<item row="14" column="0">
<widget class="QLabel" name="statusTextLabel">
<widget class="QLabel" name="overallStatusLabel">
<property name="text">
<string>Status</string>
<string>Overall status</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
</property>
</widget>
</item>
<item row="14" column="1">
<layout class="QVBoxLayout" name="statusComputionFlagsVerticalLayout">
<property name="spacing">
<number>2</number>
</property>
<item>
<widget class="QLabel" name="statusComputionFlagsLabel">
<property name="text">
<string>Select what information should be considered to compute the overall status:</string>
</property>
</widget>
</item>
<item>
<widget class="QListView" name="statusComputionFlagsListView">
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Minimum">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="minimumSize">
<size>
<width>0</width>
<height>30</height>
</size>
</property>
<property name="flow">
<enum>QListView::LeftToRight</enum>
</property>
<property name="isWrapping" stdset="0">
<bool>true</bool>
</property>
<property name="wordWrap">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
</item>
<item row="15" column="0">
<widget class="QLabel" name="statusTextLabel">
<property name="text">
<string>Current status</string>
</property>
</widget>
</item>
<item row="15" column="1">
<widget class="QLabel" name="statusLabel">
<property name="text">
<string>disconnected</string>
</property>
</widget>
</item>
<item row="17" column="1">
<item row="18" column="1">
<widget class="QPushButton" name="connectPushButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
@ -467,51 +561,6 @@
</property>
</widget>
</item>
<item row="10" column="1">
<layout class="QHBoxLayout" name="insertFromConfigFileLayout">
<property name="spacing">
<number>0</number>
</property>
<item>
<widget class="QPushButton" name="insertFromConfigFilePushButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Fixed" vsizetype="Fixed">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="styleSheet">
<string notr="true">font-weight: bold;</string>
</property>
<property name="text">
<string>Insert values from local Syncthing configuration</string>
</property>
<property name="icon">
<iconset theme="edit-paste" resource="../resources/syncthingwidgetsicons.qrc">
<normaloff>:/icons/hicolor/scalable/actions/edit-paste.svg</normaloff>:/icons/hicolor/scalable/actions/edit-paste.svg</iconset>
</property>
</widget>
</item>
<item>
<widget class="QPushButton" name="insertFromCustomConfigFilePushButton">
<property name="sizePolicy">
<sizepolicy hsizetype="Fixed" vsizetype="Preferred">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="toolTip">
<string>Select config file manually</string>
</property>
<property name="icon">
<iconset theme="document-open">
<normaloff>.</normaloff>
<normalon>:/icons/hicolor/scalable/actions/document-open.svg</normalon>.</iconset>
</property>
</widget>
</item>
</layout>
</item>
</layout>
</widget>
<customwidgets>

View File

@ -6,6 +6,7 @@
#include "../../connector/syncthingconnection.h"
#include "../../connector/syncthingprocess.h"
#include "../../connector/utils.h"
#include "../../model/syncthingstatuscomputionmodel.h"
#ifdef LIB_SYNCTHING_CONNECTOR_SUPPORT_SYSTEMD
#include "../../connector/syncthingservice.h"
#include "../../model/colors.h"
@ -92,6 +93,7 @@ void ConnectionOptionPage::hideConnectionStatus()
QWidget *ConnectionOptionPage::setupWidget()
{
auto *const widget = ConnectionOptionPageBase::setupWidget();
m_statusComputionModel = new SyncthingStatusComputionModel(widget);
ui()->certPathSelection->provideCustomFileMode(QFileDialog::ExistingFile);
ui()->certPathSelection->lineEdit()->setPlaceholderText(
QCoreApplication::translate("QtGui::ConnectionOptionPage", "Auto-detected for local instance"));
@ -105,6 +107,7 @@ QWidget *ConnectionOptionPage::setupWidget()
} else {
hideConnectionStatus();
}
ui()->statusComputionFlagsListView->setModel(m_statusComputionModel);
QObject::connect(ui()->connectPushButton, &QPushButton::clicked, bind(&ConnectionOptionPage::applyAndReconnect, this));
QObject::connect(ui()->insertFromConfigFilePushButton, &QPushButton::clicked, bind(&ConnectionOptionPage::insertFromConfigFile, this, false));
QObject::connect(
@ -198,6 +201,7 @@ bool ConnectionOptionPage::showConnectionSettings(int index)
ui()->pollErrorsSpinBox->setValue(connectionSettings.errorsPollInterval);
ui()->reconnectSpinBox->setValue(connectionSettings.reconnectInterval);
ui()->autoConnectCheckBox->setChecked(connectionSettings.autoConnect);
m_statusComputionModel->setStatusComputionFlags(connectionSettings.statusComputionFlags);
setCurrentIndex(index);
return true;
}
@ -222,6 +226,7 @@ bool ConnectionOptionPage::cacheCurrentSettings(bool applying)
connectionSettings.errorsPollInterval = ui()->pollErrorsSpinBox->value();
connectionSettings.reconnectInterval = ui()->reconnectSpinBox->value();
connectionSettings.autoConnect = ui()->autoConnectCheckBox->isChecked();
connectionSettings.statusComputionFlags = m_statusComputionModel->statusComputionFlags();
if (!connectionSettings.loadHttpsCert()) {
const QString errorMessage = QCoreApplication::translate("QtGui::ConnectionOptionPage", "Unable to load specified certificate \"%1\".")
.arg(connectionSettings.httpsCertPath);

View File

@ -31,6 +31,7 @@ class SyncthingConnection;
class SyncthingService;
class SyncthingProcess;
class SyncthingLauncher;
class SyncthingStatusComputionModel;
} // namespace Data
namespace QtGui {
@ -67,6 +68,7 @@ void setCurrentIndex(int currentIndex);
Data::SyncthingConnection *m_connection;
Data::SyncthingConnectionSettings m_primarySettings;
std::vector<Data::SyncthingConnectionSettings> m_secondarySettings;
Data::SyncthingStatusComputionModel *m_statusComputionModel;
int m_currentIndex;
END_DECLARE_OPTION_PAGE