summaryrefslogtreecommitdiff
path: root/plugin/src/Caelestia/cachingimagemanager.cpp
diff options
context:
space:
mode:
author2 * r + 2 * t <61896496+soramanew@users.noreply.github.com>2025-08-27 20:32:51 +1000
committer2 * r + 2 * t <61896496+soramanew@users.noreply.github.com>2025-08-27 20:32:51 +1000
commit4f60c07e0540f89654b469d134095c37e238d3e8 (patch)
tree6853439cce6933475898c608d4d846fd91fde6f5 /plugin/src/Caelestia/cachingimagemanager.cpp
parentinternal: move notif icon lower (diff)
downloadcaelestia-shell-4f60c07e0540f89654b469d134095c37e238d3e8.tar.gz
caelestia-shell-4f60c07e0540f89654b469d134095c37e238d3e8.tar.bz2
caelestia-shell-4f60c07e0540f89654b469d134095c37e238d3e8.zip
plugin: create caching image manager
No need for external proc
Diffstat (limited to 'plugin/src/Caelestia/cachingimagemanager.cpp')
-rw-r--r--plugin/src/Caelestia/cachingimagemanager.cpp122
1 files changed, 122 insertions, 0 deletions
diff --git a/plugin/src/Caelestia/cachingimagemanager.cpp b/plugin/src/Caelestia/cachingimagemanager.cpp
new file mode 100644
index 0000000..d557203
--- /dev/null
+++ b/plugin/src/Caelestia/cachingimagemanager.cpp
@@ -0,0 +1,122 @@
+#include "cachingimagemanager.hpp"
+
+#include <qobject.h>
+#include <QtQuick/QQuickItem>
+#include <QtQuick/QQuickWindow>
+#include <QCryptographicHash>
+#include <QThreadPool>
+#include <QFile>
+
+qreal CachingImageManager::effectiveScale() const {
+ if (m_item->window() && m_item->window()->screen()) {
+ return m_item->window()->screen()->devicePixelRatio();
+ }
+
+ return 1.0;
+}
+
+int CachingImageManager::effectiveWidth() const {
+ int width = std::ceil(m_item->width() * effectiveScale());
+ m_item->setProperty("sourceWidth", width);
+ return width;
+}
+
+int CachingImageManager::effectiveHeight() const {
+ int height = std::ceil(m_item->height() * effectiveScale());
+ m_item->setProperty("sourceHeight", height);
+ return height;
+}
+
+QQuickItem* CachingImageManager::item() const {
+ return m_item;
+}
+
+void CachingImageManager::setItem(QQuickItem* item) {
+ if (m_item == item) {
+ return;
+ }
+
+ m_item = item;
+ emit itemChanged();
+}
+
+QUrl CachingImageManager::cacheDir() const {
+ return m_cacheDir;
+}
+
+void CachingImageManager::setCacheDir(const QUrl& cacheDir) {
+ if (m_cacheDir == cacheDir) {
+ return;
+ }
+
+ m_cacheDir = cacheDir;
+ emit cacheDirChanged();
+}
+
+QString CachingImageManager::path() const {
+ return m_path;
+}
+
+void CachingImageManager::setPath(const QString& path) {
+ if (m_path == path) {
+ return;
+ }
+
+ m_path = path;
+ emit pathChanged();
+
+ if (!path.isEmpty()) {
+ QThreadPool::globalInstance()->start([path, this] {
+ const QString filename = QString("%1@%2x%3.png")
+ .arg(sha256sum(path))
+ .arg(effectiveWidth())
+ .arg(effectiveHeight());
+
+ m_cachePath = m_cacheDir.resolved(QUrl(filename));
+ emit cachePathChanged();
+
+ if (!m_cachePath.isLocalFile()) {
+ qWarning() << "CachingImageManager::setPath: cachePath" << m_cachePath << "is not a local file";
+ return;
+ }
+
+ if (QFile::exists(m_cachePath.toLocalFile())) {
+ QMetaObject::invokeMethod(m_item, [this]() {
+ m_item->setProperty("source", m_cachePath);
+ }, Qt::QueuedConnection);
+
+ m_usingCache = true;
+ emit usingCacheChanged();
+ } else {
+ QMetaObject::invokeMethod(m_item, [path, this]() {
+ m_item->setProperty("source", QUrl::fromLocalFile(path));
+ }, Qt::QueuedConnection);
+
+ m_usingCache = false;
+ emit usingCacheChanged();
+ }
+ });
+ }
+}
+
+QUrl CachingImageManager::cachePath() const {
+ return m_cachePath;
+}
+
+bool CachingImageManager::usingCache() const {
+ return m_usingCache;
+}
+
+QString CachingImageManager::sha256sum(const QString& path) const {
+ QFile file(path);
+ if (!file.open(QIODevice::ReadOnly)) {
+ qWarning() << "CachingImageManager::sha256sum: failed to open" << path;
+ return "";
+ }
+
+ QCryptographicHash hash(QCryptographicHash::Sha256);
+ hash.addData(&file);
+ file.close();
+
+ return hash.result().toHex();
+}