Krolyxon
Commit 229376d

Branches

Refs →

aurora.configquickshellauroraClip.qml

82 lines · 3.0 KB · QML

1pragma Singleton
2import QtQuick
3import Quickshell
4import Quickshell.Io
5
6// Clipboard history on top of cliphist (the wl-paste --watch cliphist store daemons from hyprland.lua).
7// Hides its UI if cliphist isn't installed.
8Singleton {
9 id: root
10 property bool available: false
11 property var entries: [] // [{id, text, image, fmt}], newest first
12 property var ready: ({}) // id -> true once its image preview is decoded
13 readonly property string imgDir: Quickshell.env("HOME") + "/.cache/aurora/clip"
14
15 function imageOf(e) { return imgDir + "/" + e.id + "." + e.fmt }
16
17 function refresh() { if (available) listProc.running = true }
18 function copy(id) {
19 Quickshell.execDetached(["sh", "-c", 'cliphist decode "$1" | wl-copy', "sh", String(id)])
20 }
21 function remove(id) {
22 delProc.command = ["sh", "-c", 'printf "%s\\t\\n" "$1" | cliphist delete', "sh", String(id)]
23 delProc.running = true
24 var out = []
25 for (var i = 0; i < entries.length; i++) if (entries[i].id !== id) out.push(entries[i])
26 entries = out
27 }
28 function wipe() {
29 Quickshell.execDetached(["sh", "-c", 'cliphist wipe; rm -rf "$1"', "sh", imgDir])
30 entries = []
31 ready = {}
32 }
33
34 Process {
35 command: ["sh", "-c", "command -v cliphist"]
36 running: true
37 onExited: code => root.available = code === 0
38 }
39 Process { id: delProc }
40
41 Process {
42 id: listProc
43 command: ["cliphist", "list"]
44 stdout: StdioCollector {
45 onStreamFinished: {
46 var out = [], imgs = [], l = text.split("\n")
47 for (var i = 0; i < l.length; i++) {
48 var t = l[i].indexOf("\t")
49 if (t <= 0) continue
50 var e = { id: l[i].substring(0, t), text: l[i].substring(t + 1), image: false, fmt: "" }
51 // images are listed as "[[ binary data 12 KiB png 100x100 ]]"
52 var m = e.text.match(/^\[\[ binary data .* (\w+) (\d+)x(\d+) \]\]$/)
53 if (m) {
54 e.image = true
55 e.fmt = m[1]
56 e.text = m[1] + " " + m[2] + "x" + m[3]
57 imgs.push(e.id, root.imageOf(e))
58 }
59 out.push(e)
60 }
61 root.entries = out
62 if (imgs.length) {
63 imgProc.command = ["sh", "-c",
64 'mkdir -p "$1"; shift; while [ $# -ge 2 ]; do ' +
65 '[ -s "$2" ] || cliphist decode "$1" > "$2"; [ -s "$2" ] && echo "$1"; shift 2; done',
66 "sh", root.imgDir].concat(imgs)
67 imgProc.running = true
68 }
69 }
70 }
71 }
72 Process {
73 id: imgProc
74 stdout: StdioCollector {
75 onStreamFinished: {
76 var r = {}, l = text.split("\n")
77 for (var i = 0; i < l.length; i++) if (l[i] !== "") r[l[i]] = true
78 root.ready = r
79 }
80 }
81 }
82}