Compare commits

..

8 Commits

Author SHA1 Message Date
c73486aaf8 gpu memory demo 2026-02-02 16:31:57 +02:00
59e3b21071 feat: use singleton connection to systemstats
it has been found in #174, that if there are multiple instances of
widget, it keeps subscribing on all sources, because of how dbus
interface works.

In order to hande it, all subscriptions are now kept from singleton with
tracking active clients
2026-01-30 16:03:45 +02:00
7e13e1eef7 Release 4.0.5 2026-01-28 19:53:21 +02:00
da53052a6f fix: always unsubscribe on sources 2026-01-28 19:51:51 +02:00
1a0a1fb884 Release 4.0.4 2026-01-28 14:18:16 +02:00
7a4367734b fix: check if subscription optimisation is enabled explicitly
Previous implementation has used implicit logic with empty keys arrays,
which might lead to some errors in processing
2026-01-28 14:16:55 +02:00
cdcd929cec Release 4.0.3 2026-01-01 19:54:34 +02:00
8605f66535 fix: compilation error with the latest releases (#173)
As it has been found in the releated issue, compile error occurs because
of missing evaluation and appears to be caused by Qt6QmlTargets.cmake.
Instead of trying to hack generated files, lets just drop qml
definitions because we don't really use them explicitly
2026-01-01 19:49:26 +02:00
30 changed files with 438 additions and 38 deletions

View File

@@ -1,3 +1,6 @@
Ver.4.0.3:
- drop qml definition to avoid compile errors
Ver.4.0.2: Ver.4.0.2:
+ German translation (#172, thanks to daveedmee) + German translation (#172, thanks to daveedmee)

View File

@@ -2,7 +2,7 @@
pkgname=plasma6-applet-awesome-widgets pkgname=plasma6-applet-awesome-widgets
_pkgname=awesome-widgets _pkgname=awesome-widgets
pkgver=4.0.2 pkgver=4.0.5
pkgrel=1 pkgrel=1
pkgdesc="Collection of minimalistic Plasmoids which look like Awesome WM widgets (ex-PyTextMonitor)" pkgdesc="Collection of minimalistic Plasmoids which look like Awesome WM widgets (ex-PyTextMonitor)"
arch=('x86_64') arch=('x86_64')
@@ -27,5 +27,3 @@ build () {
package() { package() {
DESTDIR="$pkgdir" cmake --install build DESTDIR="$pkgdir" cmake --install build
} }
sha256sums=('b2a7b07a1df6f710f4e0d6e5898933f4ddb131818b922dc4b8e48afe3e98a664')

View File

@@ -19,7 +19,7 @@ set(PROJECT_CONTACT "esalexeev@gmail.com")
set(PROJECT_LICENSE "GPL3") set(PROJECT_LICENSE "GPL3")
set(PROJECT_VERSION_MAJOR "4") set(PROJECT_VERSION_MAJOR "4")
set(PROJECT_VERSION_MINOR "0") set(PROJECT_VERSION_MINOR "0")
set(PROJECT_VERSION_PATCH "2") set(PROJECT_VERSION_PATCH "5")
set(PROJECT_VERSION "${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}.${PROJECT_VERSION_PATCH}") set(PROJECT_VERSION "${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}.${PROJECT_VERSION_PATCH}")
# append git version if any # append git version if any
set(PROJECT_COMMIT_SHA "Commit hash" CACHE INTERNAL "") set(PROJECT_COMMIT_SHA "Commit hash" CACHE INTERNAL "")

View File

@@ -19,7 +19,7 @@
"Id": "org.kde.plasma.awesomewidget", "Id": "org.kde.plasma.awesomewidget",
"License": "GPLv3", "License": "GPLv3",
"Name": "Awesome Widget", "Name": "Awesome Widget",
"Version": "4.0.2", "Version": "4.0.5",
"Website": "https://arcanis.me/projects/awesome-widgets/" "Website": "https://arcanis.me/projects/awesome-widgets/"
}, },
"X-Plasma-API-Minimum-Version": "6.0" "X-Plasma-API-Minimum-Version": "6.0"

View File

@@ -95,14 +95,55 @@ void AWDataEngineAggregator::loadSources()
} }
void AWDataEngineAggregator::registerClient(QObject *_client)
{
qCDebug(LOG_AW) << "Register client" << _client;
// register new client
m_clients.insert(_client);
// (re)connect sources for new client
connectSources();
}
void AWDataEngineAggregator::unregisterClient(QObject *_client)
{
qCDebug(LOG_AW) << "Unregister client" << _client;
m_clients.remove(_client);
for (auto [source, clients] : m_droppedBy.asKeyValueRange()) {
if (clients.remove(_client)) {
if (isSubscriptionUnused(source))
dropSource(source);
}
}
}
void AWDataEngineAggregator::dropSource(const QString &_source) void AWDataEngineAggregator::dropSource(const QString &_source)
{ {
qCDebug(LOG_AW) << "Disconnect sensor" << _source; qCDebug(LOG_AW) << "Disconnect sensor" << _source;
if (m_subscribed.contains(_source)) { if (m_subscribed.remove(_source))
m_interface->unsubscribe({_source}).waitForFinished(); m_interface->unsubscribe({_source}).waitForFinished();
m_subscribed.remove(_source);
} }
void AWDataEngineAggregator::dropSourceForClient(QObject *_client, const QString &_source)
{
qCDebug(LOG_AW) << "Client" << _client << "dropping source" << _source;
m_droppedBy[_source].insert(_client);
// only unsubscribe if ALL clients have dropped this source
if (isSubscriptionUnused(_source))
dropSource(_source);
}
bool AWDataEngineAggregator::isSubscriptionUnused(const QString &_source) const
{
return m_droppedBy.value(_source).size() >= m_clients.size() && !m_clients.isEmpty();
} }

View File

@@ -23,6 +23,7 @@
#include <QObject> #include <QObject>
#include <QSet> #include <QSet>
#include <memory>
namespace KSysGuard::SystemStats namespace KSysGuard::SystemStats
{ {
@@ -34,12 +35,26 @@ class AWDataEngineAggregator : public QObject
Q_OBJECT Q_OBJECT
public: public:
explicit AWDataEngineAggregator(QObject *_parent = nullptr);
~AWDataEngineAggregator() override; ~AWDataEngineAggregator() override;
AWDataEngineAggregator(AWDataEngineAggregator &) = delete;
void operator=(const AWDataEngineAggregator &) = delete;
[[nodiscard]] static AWDataEngineAggregator *instance(QObject *_client)
{
static auto instance = loadInstance();
instance->registerClient(_client);
return instance.get();
};
void connectSources(); void connectSources();
void disconnectSources(); void disconnectSources();
void dropSourceForClient(QObject *_client, const QString &_source);
[[nodiscard]] inline bool isSubscriptionUnused(const QString &_source) const;
[[nodiscard]] static bool isValidSensor(const KSysGuard::SensorInfo &_sensor); [[nodiscard]] static bool isValidSensor(const KSysGuard::SensorInfo &_sensor);
void loadSources(); void loadSources();
void registerClient(QObject *_client);
void unregisterClient(QObject *_client);
signals: signals:
void dataUpdated(const QHash<QString, KSysGuard::SensorInfo> &_sensors, const KSysGuard::SensorDataList &_data); void dataUpdated(const QHash<QString, KSysGuard::SensorInfo> &_sensors, const KSysGuard::SensorDataList &_data);
@@ -52,7 +67,18 @@ public slots:
void updateData(const KSysGuard::SensorDataList &_data); void updateData(const KSysGuard::SensorDataList &_data);
void updateSensors(const QHash<QString, KSysGuard::SensorInfo> &_sensors); void updateSensors(const QHash<QString, KSysGuard::SensorInfo> &_sensors);
protected:
explicit AWDataEngineAggregator(QObject *_parent = nullptr);
[[nodiscard]] static std::unique_ptr<AWDataEngineAggregator> loadInstance()
{
auto instance = new AWDataEngineAggregator();
return std::unique_ptr<AWDataEngineAggregator>(instance);
};
private: private:
QSet<QObject *> m_clients;
QHash<QString, QSet<QObject *>> m_droppedBy;
KSysGuard::SystemStats::DBusInterface *m_interface = nullptr; KSysGuard::SystemStats::DBusInterface *m_interface = nullptr;
QHash<QString, KSysGuard::SensorInfo> m_sensors; QHash<QString, KSysGuard::SensorInfo> m_sensors;
QSet<QString> m_subscribed; QSet<QString> m_subscribed;

View File

@@ -43,6 +43,10 @@ AWDataEngineMapper::AWDataEngineMapper(QObject *_parent, AWFormatterHelper *_cus
m_formatter["uptot"] = AWPluginFormatterMemoryMB::instance(); m_formatter["uptot"] = AWPluginFormatterMemoryMB::instance();
m_formatter["uptotkb"] = AWPluginFormatterMemory::instance(); m_formatter["uptotkb"] = AWPluginFormatterMemory::instance();
m_formatter["upunits"] = AWPluginFormatterNetUnits::instance(); m_formatter["upunits"] = AWPluginFormatterNetUnits::instance();
// gpu memory
m_formatter["gpumem"] = AWPluginFormatterFloat::instance();
m_formatter["gpufreemb"] = AWPluginFormatterMemoryMB::instance();
m_formatter["gpufreegb"] = AWPluginFormatterMemoryGB::instance();
} }
@@ -65,7 +69,7 @@ QStringList AWDataEngineMapper::keysFromSource(const QString &_source) const
// HACK units required to define should the value be calculated as temperature // HACK units required to define should the value be calculated as temperature
// or fan data // or fan data
QStringList AWDataEngineMapper::registerSource(const QString &_source, const KSysGuard::Unit _units, QStringList AWDataEngineMapper::registerSource(const QString &_source, const KSysGuard::Unit _units,
const QStringList &_keys) const QStringList &_keys, const bool _disconnectUnused)
{ {
qCDebug(LOG_AW) << "Source" << _source << "with units" << _units; qCDebug(LOG_AW) << "Source" << _source << "with units" << _units;
@@ -91,7 +95,7 @@ QStringList AWDataEngineMapper::registerSource(const QString &_source, const KSy
// check if keys were actually requested // check if keys were actually requested
qCInfo(LOG_AW) << "Looking for keys" << keys << "in" << _keys; qCInfo(LOG_AW) << "Looking for keys" << keys << "in" << _keys;
auto required = _keys.isEmpty() auto required = !_disconnectUnused
|| std::any_of(keys.cbegin(), keys.cend(), [&_keys](auto &key) { return _keys.contains(key); }); || std::any_of(keys.cbegin(), keys.cend(), [&_keys](auto &key) { return _keys.contains(key); });
if (!required) if (!required)
return {}; return {};
@@ -109,4 +113,12 @@ QStringList AWDataEngineMapper::registerSource(const QString &_source, const KSy
void AWDataEngineMapper::setDevices(const AWPluginMatcherSettings &_settings) void AWDataEngineMapper::setDevices(const AWPluginMatcherSettings &_settings)
{ {
m_settings = _settings; m_settings = _settings;
// update formatters
// gpu memory per device
for (auto i = 0; i < m_settings.gpu.count(); ++i) {
m_formatter[QString("gpumem%1").arg(i)] = AWPluginFormatterFloat::instance();
m_formatter[QString("gpufreemb%1").arg(i)] = AWPluginFormatterMemoryMB::instance();
m_formatter[QString("gpufreegb%1").arg(i)] = AWPluginFormatterMemoryGB::instance();
}
} }

View File

@@ -39,7 +39,8 @@ public:
[[nodiscard]] AWPluginFormaterInterface *formatter(const QString &_key) const; [[nodiscard]] AWPluginFormaterInterface *formatter(const QString &_key) const;
[[nodiscard]] QStringList keysFromSource(const QString &_source) const; [[nodiscard]] QStringList keysFromSource(const QString &_source) const;
// set methods // set methods
QStringList registerSource(const QString &_source, KSysGuard::Unit _units, const QStringList &_keys); QStringList registerSource(const QString &_source, KSysGuard::Unit _units, const QStringList &_keys,
const bool _disconnectUnused);
void setDevices(const AWPluginMatcherSettings &_settings); void setDevices(const AWPluginMatcherSettings &_settings);
private: private:

View File

@@ -70,12 +70,12 @@ QStringList AWKeyCache::getRequiredKeys(const QStringList &_keys, const QStringL
qCDebug(LOG_AW) << "Looking for required keys in" << _keys << _bars << "using tooltip settings" << _tooltip; qCDebug(LOG_AW) << "Looking for required keys in" << _keys << _bars << "using tooltip settings" << _tooltip;
// initial copy // initial copy
QSet<QString> used(_keys.cbegin(), _keys.cend()); QSet used(_keys.cbegin(), _keys.cend());
used.unite(QSet(_bars.cbegin(), _bars.cend())); used.unite(QSet(_bars.cbegin(), _bars.cend()));
used.unite(QSet(_userKeys.cbegin(), _userKeys.cend())); used.unite(QSet(_userKeys.cbegin(), _userKeys.cend()));
// insert keys from tooltip // insert keys from tooltip
for (auto [key, value] : _tooltip.asKeyValueRange()) { for (auto [key, value] : _tooltip.asKeyValueRange()) {
if ((key.endsWith("Tooltip")) && value.toBool()) { if (key.endsWith("Tooltip") && value.toBool()) {
auto local = key; auto local = key;
local.remove("Tooltip"); local.remove("Tooltip");
used << local; used << local;
@@ -84,7 +84,7 @@ QStringList AWKeyCache::getRequiredKeys(const QStringList &_keys, const QStringL
// insert keys which depend on others, refer to AWKeys::calculateValues() // insert keys which depend on others, refer to AWKeys::calculateValues()
// network keys // network keys
QStringList netKeys( static QStringList netKeys(
{"up", "upkb", "uptot", "uptotkb", "upunits", "down", "downkb", "downtot", "downtotkb", "downunits"}); {"up", "upkb", "uptot", "uptotkb", "upunits", "down", "downkb", "downtot", "downtotkb", "downunits"});
for (auto &key : netKeys) { for (auto &key : netKeys) {
if (!used.contains(key)) if (!used.contains(key))
@@ -96,11 +96,13 @@ QStringList AWKeyCache::getRequiredKeys(const QStringList &_keys, const QStringL
// netdev key // netdev key
if (std::any_of(netKeys.cbegin(), netKeys.cend(), [&used](auto &key) { return used.contains(key); })) if (std::any_of(netKeys.cbegin(), netKeys.cend(), [&used](auto &key) { return used.contains(key); }))
used << "netdev"; used << "netdev";
// gpu memory keys
// HACK append dummy if there are no other keys. This hack is required static auto gpuMemoryCalculatedRegExp = QRegularExpression("^gpu(mem|freemb|freegb)");
// because empty list leads to the same behaviour as skip checking for (auto key : _keys.filter(gpuMemoryCalculatedRegExp)) {
if (used.isEmpty()) auto index = key.remove(gpuMemoryCalculatedRegExp);
used << "dummy"; used << QString("gpuusedmb%1").arg(index) << QString("gputotmb%1").arg(index)
<< QString("gpuusedgb%1").arg(index) << QString("gputotgb%1").arg(index);
}
return used.values(); return used.values();
} }

View File

@@ -85,6 +85,13 @@ QStringList AWKeyOperations::dictKeys() const
// gpu // gpu
for (auto i = 0; i < m_devices.gpu.count(); ++i) { for (auto i = 0; i < m_devices.gpu.count(); ++i) {
allKeys.append(QString("gpu%1").arg(i)); allKeys.append(QString("gpu%1").arg(i));
allKeys.append(QString("gpumem%1").arg(i));
allKeys.append(QString("gpufreemb%1").arg(i));
allKeys.append(QString("gpufreegb%1").arg(i));
allKeys.append(QString("gputotmb%1").arg(i));
allKeys.append(QString("gputotgb%1").arg(i));
allKeys.append(QString("gpuusedmb%1").arg(i));
allKeys.append(QString("gpuusedgb%1").arg(i));
allKeys.append(QString("gputemp%1").arg(i)); allKeys.append(QString("gputemp%1").arg(i));
} }
// hdd // hdd

View File

@@ -43,7 +43,7 @@ AWKeys::AWKeys(QObject *_parent)
m_aggregator = new AWKeysAggregator(this); m_aggregator = new AWKeysAggregator(this);
m_dataAggregator = new AWDataAggregator(this); m_dataAggregator = new AWDataAggregator(this);
m_dataEngineAggregator = new AWDataEngineAggregator(this); m_dataEngineAggregator = AWDataEngineAggregator::instance(this);
m_keyOperator = new AWKeyOperations(this); m_keyOperator = new AWKeyOperations(this);
m_timer = new QTimer(this); m_timer = new QTimer(this);
@@ -59,7 +59,8 @@ AWKeys::AWKeys(QObject *_parent)
connect(m_dataAggregator, &AWDataAggregator::toolTipPainted, connect(m_dataAggregator, &AWDataAggregator::toolTipPainted,
[this](const QString &_tooltip) { emit(needToolTipToBeUpdated(_tooltip)); }); [this](const QString &_tooltip) { emit(needToolTipToBeUpdated(_tooltip)); });
connect(this, &AWKeys::dropSourceFromDataengine, m_dataEngineAggregator, &AWDataEngineAggregator::dropSource); connect(this, &AWKeys::dropSourceFromDataengine, this,
[this](const QString &_source) { m_dataEngineAggregator->dropSourceForClient(this, _source); });
connect(m_dataEngineAggregator, &AWDataEngineAggregator::dataUpdated, this, &AWKeys::dataUpdated); connect(m_dataEngineAggregator, &AWDataEngineAggregator::dataUpdated, this, &AWKeys::dataUpdated);
// transfer signal from dataengine to update source list // transfer signal from dataengine to update source list
connect(m_dataEngineAggregator, &AWDataEngineAggregator::deviceAdded, m_keyOperator, &AWKeyOperations::addDevice); connect(m_dataEngineAggregator, &AWDataEngineAggregator::deviceAdded, m_keyOperator, &AWKeyOperations::addDevice);
@@ -70,6 +71,8 @@ AWKeys::~AWKeys()
{ {
qCDebug(LOG_AW) << __PRETTY_FUNCTION__; qCDebug(LOG_AW) << __PRETTY_FUNCTION__;
m_dataEngineAggregator->unregisterClient(this);
m_timer->stop(); m_timer->stop();
// delete dbus session // delete dbus session
auto id = reinterpret_cast<qlonglong>(this); auto id = reinterpret_cast<qlonglong>(this);
@@ -206,9 +209,8 @@ void AWKeys::reinitKeys(const QStringList &_currentKeys)
barKeys.append(item->usedKeys()); barKeys.append(item->usedKeys());
} }
// get required keys // get required keys
m_requiredKeys = m_optimize ? AWKeyCache::getRequiredKeys(m_foundKeys, barKeys, m_tooltipParams, m_requiredKeys = AWKeyCache::getRequiredKeys(m_foundKeys, barKeys, m_tooltipParams,
m_keyOperator->requiredUserKeys(), _currentKeys) m_keyOperator->requiredUserKeys(), _currentKeys);
: QStringList();
// set key data to m_aggregator // set key data to m_aggregator
m_aggregator->setDevices(m_keyOperator->devices()); m_aggregator->setDevices(m_keyOperator->devices());
@@ -246,6 +248,19 @@ void AWKeys::calculateValues()
m_values["uptotkb"] = m_values[QString("uptotkb%1").arg(netIndex)]; m_values["uptotkb"] = m_values[QString("uptotkb%1").arg(netIndex)];
m_values["upunits"] = m_values[QString("upunits%1").arg(netIndex)]; m_values["upunits"] = m_values[QString("upunits%1").arg(netIndex)];
// gpu memory keys
m_values["gpufreemb"] = m_values["gputotmb"].toLongLong() - m_values["gpuusedmb"].toLongLong();
m_values["gpufreegb"] = m_values["gputotgb"].toDouble() - m_values["gpuusedgb"].toDouble();
m_values["gpumem"] = 100.0 * m_values["gpuusedmb"].toDouble() / m_values["gputotmb"].toDouble();
for (auto i = 0; i < devices.gpu.count(); ++i) {
m_values[QString("gpufreemb%1").arg(i)] = m_values[QString("gputotmb%1").arg(i)].toLongLong()
- m_values[QString("gpuusedmb%1").arg(i)].toLongLong();
m_values[QString("gpufreegb%1").arg(i)]
= m_values[QString("gputotgb%1").arg(i)].toDouble() - m_values[QString("gpuusedgb%1").arg(i)].toDouble();
m_values[QString("gpumem%1").arg(i)] = 100.0 * m_values[QString("gpuusedmb%1").arg(i)].toDouble()
/ m_values[QString("gputotmb%1").arg(i)].toDouble();
}
// user defined keys // user defined keys
for (auto &key : m_keyOperator->userKeys()) for (auto &key : m_keyOperator->userKeys())
m_values[key] = m_values[m_keyOperator->userKeySource(key)]; m_values[key] = m_values[m_keyOperator->userKeySource(key)];
@@ -295,8 +310,8 @@ QString AWKeys::parsePattern(QString _pattern) const
// bars // bars
for (auto &bar : m_foundBars) { for (auto &bar : m_foundBars) {
auto item = m_keyOperator->giByKey(bar); auto item = m_keyOperator->giByKey(bar);
auto image = item->isCustom() ? item->image( auto image = item->isCustom() ? item->image(AWPatternFunctions::expandLambdas(item->bar(), m_aggregator,
AWPatternFunctions::expandLambdas(item->bar(), m_aggregator, m_values, item->usedKeys())) m_values, item->usedKeys()))
: item->image(m_values[item->bar()]); : item->image(m_values[item->bar()]);
_pattern.replace(QString("$%1").arg(bar), image); _pattern.replace(QString("$%1").arg(bar), image);
} }
@@ -317,7 +332,7 @@ void AWKeys::setDataBySource(const QString &_source, const KSysGuard::SensorInfo
// first list init // first list init
auto tags = m_aggregator->keysFromSource(_source); auto tags = m_aggregator->keysFromSource(_source);
if (tags.isEmpty()) if (tags.isEmpty())
tags = m_aggregator->registerSource(_source, _sensor.unit, m_requiredKeys); tags = m_aggregator->registerSource(_source, _sensor.unit, m_requiredKeys, m_optimize);
// update data or drop source if there are no matches and exit // update data or drop source if there are no matches and exit
if (tags.isEmpty()) { if (tags.isEmpty()) {

View File

@@ -151,9 +151,9 @@ void AWKeysAggregator::setTranslate(const bool _translate)
QStringList AWKeysAggregator::registerSource(const QString &_source, const KSysGuard::Unit _units, QStringList AWKeysAggregator::registerSource(const QString &_source, const KSysGuard::Unit _units,
const QStringList &_keys) const QStringList &_keys, const bool _disconnectUnused)
{ {
qCDebug(LOG_AW) << "Source" << _source << "with units" << _units; qCDebug(LOG_AW) << "Source" << _source << "with units" << _units;
return m_mapper->registerSource(_source, _units, _keys); return m_mapper->registerSource(_source, _units, _keys, _disconnectUnused);
} }

View File

@@ -61,7 +61,8 @@ public:
void setTranslate(bool _translate); void setTranslate(bool _translate);
public slots: public slots:
QStringList registerSource(const QString &_source, KSysGuard::Unit _units, const QStringList &_keys); QStringList registerSource(const QString &_source, KSysGuard::Unit _units, const QStringList &_keys,
const bool _disconnectUnused);
private: private:
AWPluginFormatSettings m_settings; AWPluginFormatSettings m_settings;

View File

@@ -15,6 +15,8 @@
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ * * along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/ ***************************************************************************/
#pragma once
#include "awpluginformatterac.h" #include "awpluginformatterac.h"
#include "awpluginformattercustom.h" #include "awpluginformattercustom.h"
#include "awpluginformatterdouble.h" #include "awpluginformatterdouble.h"

View File

@@ -0,0 +1,36 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#include "awpluginmatchergpumemorytotal.h"
#include "formatters/formatters.h"
QHash<QString, AWPluginFormaterInterface *> AWPluginMatcherGPUMemoryTotal::keys(const QString &, const KSysGuard::Unit,
const AWPluginMatcherSettings &) const
{
return {
{"gputotmb", AWPluginFormatterMemoryMB::instance()},
{"gputotgb", AWPluginFormatterMemoryGB::instance()},
};
}
bool AWPluginMatcherGPUMemoryTotal::matches(const QString &_source) const
{
return _source == "gpu/all/totalVram";
}

View File

@@ -0,0 +1,29 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#pragma once
#include "awpluginmatcher.h"
class AWPluginMatcherGPUMemoryTotal : public AWPluginMatcher<AWPluginMatcherGPUMemoryTotal>
{
public:
[[nodiscard]] QHash<QString, AWPluginFormaterInterface *> keys(const QString &, KSysGuard::Unit,
const AWPluginMatcherSettings &) const override;
[[nodiscard]] bool matches(const QString &_source) const override;
};

View File

@@ -0,0 +1,44 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#include "awpluginmatchergpumemorytotalcore.h"
#include <QRegularExpression>
#include "formatters/formatters.h"
QHash<QString, AWPluginFormaterInterface *>
AWPluginMatcherGPUMemoryTotalCore::keys(const QString &_source, const KSysGuard::Unit,
const AWPluginMatcherSettings &_settings) const
{
auto index = AWPluginMatcher::index(_source, _settings.gpu);
if (index == -1)
return {};
return {
{QString("gputotmb%1").arg(index), AWPluginFormatterMemoryMB::instance()},
{QString("gputotgb%1").arg(index), AWPluginFormatterMemoryGB::instance()},
};
}
bool AWPluginMatcherGPUMemoryTotalCore::matches(const QString &_source) const
{
static auto regexp = QRegularExpression("^gpu/gpu.*/totalVram$");
return _source.contains(regexp);
}

View File

@@ -0,0 +1,29 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#pragma once
#include "awpluginmatcher.h"
class AWPluginMatcherGPUMemoryTotalCore : public AWPluginMatcher<AWPluginMatcherGPUMemoryTotalCore>
{
public:
[[nodiscard]] QHash<QString, AWPluginFormaterInterface *>
keys(const QString &_source, KSysGuard::Unit, const AWPluginMatcherSettings &_settings) const override;
[[nodiscard]] bool matches(const QString &_source) const override;
};

View File

@@ -0,0 +1,36 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#include "awpluginmatchergpumemoryused.h"
#include "formatters/formatters.h"
QHash<QString, AWPluginFormaterInterface *> AWPluginMatcherGPUMemoryUsed::keys(const QString &, const KSysGuard::Unit,
const AWPluginMatcherSettings &) const
{
return {
{"gpuusedmb", AWPluginFormatterMemoryMB::instance()},
{"gpuusedgb", AWPluginFormatterMemoryGB::instance()},
};
}
bool AWPluginMatcherGPUMemoryUsed::matches(const QString &_source) const
{
return _source == "gpu/all/usedVram";
}

View File

@@ -0,0 +1,29 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#pragma once
#include "awpluginmatcher.h"
class AWPluginMatcherGPUMemoryUsed : public AWPluginMatcher<AWPluginMatcherGPUMemoryUsed>
{
public:
[[nodiscard]] QHash<QString, AWPluginFormaterInterface *> keys(const QString &, KSysGuard::Unit,
const AWPluginMatcherSettings &) const override;
[[nodiscard]] bool matches(const QString &_source) const override;
};

View File

@@ -0,0 +1,44 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#include "awpluginmatchergpumemoryusedcore.h"
#include <QRegularExpression>
#include "formatters/formatters.h"
QHash<QString, AWPluginFormaterInterface *>
AWPluginMatcherGPUMemoryUsedCore::keys(const QString &_source, const KSysGuard::Unit,
const AWPluginMatcherSettings &_settings) const
{
auto index = AWPluginMatcher::index(_source, _settings.gpu);
if (index == -1)
return {};
return {
{QString("gpuusedmb%1").arg(index), AWPluginFormatterMemoryMB::instance()},
{QString("gpuusedgb%1").arg(index), AWPluginFormatterMemoryGB::instance()},
};
}
bool AWPluginMatcherGPUMemoryUsedCore::matches(const QString &_source) const
{
static auto regexp = QRegularExpression("^gpu/gpu.*/usedVram$");
return _source.contains(regexp);
}

View File

@@ -0,0 +1,29 @@
/***************************************************************************
* This file is part of awesome-widgets *
* *
* awesome-widgets is free software: you can redistribute it and/or *
* modify it under the terms of the GNU General Public License as *
* published by the Free Software Foundation, either version 3 of the *
* License, or (at your option) any later version. *
* *
* awesome-widgets is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/
#pragma once
#include "awpluginmatcher.h"
class AWPluginMatcherGPUMemoryUsedCore : public AWPluginMatcher<AWPluginMatcherGPUMemoryUsedCore>
{
public:
[[nodiscard]] QHash<QString, AWPluginFormaterInterface *>
keys(const QString &_source, KSysGuard::Unit, const AWPluginMatcherSettings &_settings) const override;
[[nodiscard]] bool matches(const QString &_source) const override;
};

View File

@@ -15,6 +15,8 @@
* along with awesome-widgets. If not, see http://www.gnu.org/licenses/ * * along with awesome-widgets. If not, see http://www.gnu.org/licenses/ *
***************************************************************************/ ***************************************************************************/
#pragma once
#include "awpluginmatcherac.h" #include "awpluginmatcherac.h"
#include "awpluginmatcherbattery.h" #include "awpluginmatcherbattery.h"
#include "awpluginmatcherbrightness.h" #include "awpluginmatcherbrightness.h"
@@ -28,6 +30,10 @@
#include "awpluginmatcherdesktopnumber.h" #include "awpluginmatcherdesktopnumber.h"
#include "awpluginmatchergpu.h" #include "awpluginmatchergpu.h"
#include "awpluginmatchergpucore.h" #include "awpluginmatchergpucore.h"
#include "awpluginmatchergpumemorytotal.h"
#include "awpluginmatchergpumemorytotalcore.h"
#include "awpluginmatchergpumemoryused.h"
#include "awpluginmatchergpumemoryusedcore.h"
#include "awpluginmatchergputemperature.h" #include "awpluginmatchergputemperature.h"
#include "awpluginmatcherhdd.h" #include "awpluginmatcherhdd.h"
#include "awpluginmatcherhddfree.h" #include "awpluginmatcherhddfree.h"
@@ -80,6 +86,10 @@ static QList<AWPluginMatcherInterface *> matchers = {
AWPluginMatcherDesktopNumber::instance(), AWPluginMatcherDesktopNumber::instance(),
AWPluginMatcherGPU::instance(), AWPluginMatcherGPU::instance(),
AWPluginMatcherGPUCore::instance(), AWPluginMatcherGPUCore::instance(),
AWPluginMatcherGPUMemoryTotal::instance(),
AWPluginMatcherGPUMemoryTotalCore::instance(),
AWPluginMatcherGPUMemoryUsed::instance(),
AWPluginMatcherGPUMemoryUsedCore::instance(),
AWPluginMatcherGPUTemperature::instance(), AWPluginMatcherGPUTemperature::instance(),
AWPluginMatcherHDD::instance(), AWPluginMatcherHDD::instance(),
AWPluginMatcherHDDFree::instance(), AWPluginMatcherHDDFree::instance(),

View File

@@ -22,4 +22,3 @@
#ifndef ui_i18n #ifndef ui_i18n
#define ui_i18n(text, parent) i18n(text) #define ui_i18n(text, parent) i18n(text)
#endif /* ui_i18n */ #endif /* ui_i18n */

View File

@@ -19,7 +19,7 @@
"Id": "org.kde.plasma.desktoppanel", "Id": "org.kde.plasma.desktoppanel",
"License": "GPLv3", "License": "GPLv3",
"Name": "Desktop Panel", "Name": "Desktop Panel",
"Version": "4.0.2", "Version": "4.0.5",
"Website": "https://arcanis.me/projects/awesome-widgets/" "Website": "https://arcanis.me/projects/awesome-widgets/"
}, },
"X-Plasma-API-Minimum-Version": "6.0" "X-Plasma-API-Minimum-Version": "6.0"

View File

@@ -128,8 +128,8 @@ QVariant SystemInfoSource::sendDBusRequest(const QString &_destination, const QS
auto response = bus.call(request, QDBus::BlockWithGui, REQUEST_TIMEOUT); auto response = bus.call(request, QDBus::BlockWithGui, REQUEST_TIMEOUT);
if ((response.type() != QDBusMessage::ReplyMessage) || (response.arguments().isEmpty())) { if (response.type() != QDBusMessage::ReplyMessage || response.arguments().isEmpty()) {
qCWarning(LOG_ESS) << "Error message" << response.errorMessage(); qCWarning(LOG_ESS) << "Error" << response.errorName() << "with message" << response.errorMessage();
return {}; return {};
} else { } else {
return response.arguments().first(); return response.arguments().first();

View File

@@ -5,7 +5,7 @@ find_package(Gettext REQUIRED)
find_package(Qt6 6.6.0 REQUIRED COMPONENTS Core Concurrent DBus Network Qml Test Widgets) find_package(Qt6 6.6.0 REQUIRED COMPONENTS Core Concurrent DBus Network Qml Test Widgets)
add_definitions( add_definitions(
${Qt6Core_DEFINITIONS} ${Qt6DBus_DEFINITIONS} ${Qt6Network_DEFINITIONS} ${Qt6Core_DEFINITIONS} ${Qt6DBus_DEFINITIONS} ${Qt6Network_DEFINITIONS}
${Qt6Qml_DEFINITIONS} ${Qt6Widgets_DEFINITIONS} ${Qt6Widgets_DEFINITIONS}
) )
set(Qt_INCLUDE set(Qt_INCLUDE
${Qt6Core_INCLUDE_DIRS} ${Qt6Concurrent_INCLUDE_DIRS} ${Qt6DBus_INCLUDE_DIRS} ${Qt6Network_INCLUDE_DIRS} ${Qt6Core_INCLUDE_DIRS} ${Qt6Concurrent_INCLUDE_DIRS} ${Qt6DBus_INCLUDE_DIRS} ${Qt6Network_INCLUDE_DIRS}

View File

@@ -70,6 +70,13 @@ static const char STATIC_KEYS[] = "time,"
"cpucl," "cpucl,"
"cpu," "cpu,"
"gpu," "gpu,"
"gpumem,"
"gpufreemb,"
"gpufreegb,"
"gputotmb,"
"gputotgb,"
"gpuusedmb,"
"gpuusedgb,"
"memmb," "memmb,"
"memgb," "memgb,"
"memfreemb," "memfreemb,"