diff options
| author | 2 * r + 2 * t <61896496+soramanew@users.noreply.github.com> | 2025-06-13 23:31:47 +1000 |
|---|---|---|
| committer | 2 * r + 2 * t <61896496+soramanew@users.noreply.github.com> | 2025-06-13 23:31:47 +1000 |
| commit | 5da1b64da09e4c12bf850750cd1cf18b5bab3210 (patch) | |
| tree | 4e79285022869d5e30b37e616e10919a187a6c29 | |
| parent | dashboard: not full rounding for face (diff) | |
| download | caelestia-shell-5da1b64da09e4c12bf850750cd1cf18b5bab3210.tar.gz caelestia-shell-5da1b64da09e4c12bf850750cd1cf18b5bab3210.tar.bz2 caelestia-shell-5da1b64da09e4c12bf850750cd1cf18b5bab3210.zip | |
internal: better caching impl
WARNING: causes blocking when caching image on first load
| -rw-r--r-- | modules/background/Wallpaper.qml | 14 | ||||
| -rwxr-xr-x | run.fish | 3 | ||||
| -rw-r--r-- | services/Thumbnailer.qml | 72 | ||||
| -rw-r--r-- | utils/Paths.qml | 16 | ||||
| -rw-r--r-- | widgets/CachingImage.qml | 42 |
5 files changed, 61 insertions, 86 deletions
diff --git a/modules/background/Wallpaper.qml b/modules/background/Wallpaper.qml index 2734034..f4e3243 100644 --- a/modules/background/Wallpaper.qml +++ b/modules/background/Wallpaper.qml @@ -8,7 +8,7 @@ import QtQuick Item { id: root - property url source: Wallpapers.current ? `file://${Wallpapers.current}` : "" + property string source: Wallpapers.current property Image current: one anchors.fill: parent @@ -32,20 +32,14 @@ Item { id: img function update(): void { - const srcPath = `${root.source}`.slice(7); - if (thumbnail.originalPath === srcPath) { + if (path === root.source) root.current = this; - } else - path = srcPath; + else + path = root.source; } anchors.fill: parent - loadOriginal: true - asynchronous: true - cache: false - fillMode: Image.PreserveAspectCrop - opacity: 0 scale: Wallpapers.showPreview ? 1 : 0.8 @@ -4,5 +4,6 @@ set -l dbus 'quickshell.dbus.properties.warning = false;quickshell.dbus.dbusmenu set -l notifs 'quickshell.service.notifications.warning = false' # Notification server warnings on reload set -l sni 'quickshell.service.sni.host.warning = false' # StatusNotifierItem warnings on reload set -l process 'QProcess: Destroyed while process' # Long running processes on reload +set -l cache "Cannot open: file://$XDG_CACHE_HOME/caelestia/imagecache/" -qs -p (dirname (status filename)) --log-rules "$dbus;$notifs;$sni" | grep -vE -e $process +qs -p (dirname (status filename)) --log-rules "$dbus;$notifs;$sni" | grep -vF -e $process -e $cache diff --git a/services/Thumbnailer.qml b/services/Thumbnailer.qml deleted file mode 100644 index 6a6066c..0000000 --- a/services/Thumbnailer.qml +++ /dev/null @@ -1,72 +0,0 @@ -pragma Singleton -pragma ComponentBehavior: Bound - -import "root:/utils" -import Quickshell -import Quickshell.Io -import QtQuick - -Singleton { - id: root - - readonly property string thumbDir: `${Paths.cache}/thumbnails`.slice(7) - - function go(obj: var): var { - return thumbComp.createObject(obj, { - originalPath: obj.path, - width: obj.width, - height: obj.height, - loadOriginal: obj.loadOriginal - }); - } - - component Thumbnail: QtObject { - id: obj - - required property string originalPath - required property int width - required property int height - required property bool loadOriginal - - property string path - - readonly property Process proc: Process { - running: true - command: ["fish", "-c", ` -set -l path "${root.thumbDir}/$(sha1sum ${obj.originalPath} | cut -d ' ' -f 1)@${obj.width}x${obj.height}-exact.png" -if test -f $path - echo $path -else - echo 'start' - set -l size (identify -ping -format '%w\n%h' ${obj.originalPath}) - if test $size[1] -gt ${obj.width} -o $size[2] -gt ${obj.height} - magick ${obj.originalPath} -${obj.width > 1024 || obj.height > 1024 ? "resize" : "thumbnail"} ${obj.width}x${obj.height}^ -background none -gravity center -extent ${obj.width}x${obj.height} -unsharp 0x.5 $path - else - cp ${obj.originalPath} $path - end - echo $path -end`] - stdout: SplitParser { - onRead: data => { - if (data === "start") { - if (obj.loadOriginal) - obj.path = obj.originalPath; - } else { - obj.path = data; - } - } - } - } - - function reload(): void { - proc.signal(9); - proc.running = true; - } - } - - Component { - id: thumbComp - - Thumbnail {} - } -} diff --git a/utils/Paths.qml b/utils/Paths.qml index 011bb1f..88267ea 100644 --- a/utils/Paths.qml +++ b/utils/Paths.qml @@ -1,6 +1,7 @@ pragma Singleton import Quickshell +import Quickshell.Io import Qt.labs.platform Singleton { @@ -12,4 +13,19 @@ Singleton { readonly property url data: `${StandardPaths.standardLocations(StandardPaths.GenericDataLocation)[0]}/caelestia` readonly property url state: `${StandardPaths.standardLocations(StandardPaths.GenericStateLocation)[0]}/caelestia` readonly property url cache: `${StandardPaths.standardLocations(StandardPaths.GenericCacheLocation)[0]}/caelestia` + + readonly property url imagecache: `${cache}/imagecache` + + function mkdir(path: url): void { + mkdirProc.path = path.toString().replace("file://", ""); + mkdirProc.startDetached(); + } + + Process { + id: mkdirProc + + property string path + + command: ["mkdir", "-p", path] + } } diff --git a/widgets/CachingImage.qml b/widgets/CachingImage.qml index cd164b4..3382615 100644 --- a/widgets/CachingImage.qml +++ b/widgets/CachingImage.qml @@ -1,14 +1,50 @@ import "root:/services" +import "root:/utils" +import Quickshell.Io import QtQuick Image { id: root property string path - property bool loadOriginal - readonly property Thumbnailer.Thumbnail thumbnail: Thumbnailer.go(this) + property string hash + readonly property string cachePath: `${Paths.imagecache}/${hash}@${width}x${height}.png`.slice(7) - source: thumbnail.path ? `file://${thumbnail.path}` : "" asynchronous: true + cache: false fillMode: Image.PreserveAspectCrop + sourceSize.width: width + sourceSize.height: height + + onPathChanged: { + shaProc.signal(9); + shaProc.path = path.replace("file://", ""); + shaProc.running = true; + } + + onCachePathChanged: { + if (hash) + source = cachePath; + } + + onStatusChanged: { + if (source == cachePath && status === Image.Error) + source = path; + else if (source == path && status === Image.Ready) { + Paths.mkdir(Paths.imagecache); + const grabPath = cachePath; + grabToImage(res => res.saveToFile(grabPath)); + } + } + + Process { + id: shaProc + + property string path + + command: ["sha256sum", path] + stdout: SplitParser { + onRead: data => root.hash = data.split(" ")[0] + } + } } |