mirror of
https://github.com/danbulant/dots-hyprland
synced 2026-05-19 04:08:48 +00:00
130 lines
4.3 KiB
QML
130 lines
4.3 KiB
QML
import qs.modules.common
|
|
import qs.modules.common.functions
|
|
import QtQuick
|
|
import Qt.labs.folderlistmodel
|
|
import Quickshell
|
|
import Quickshell.Io
|
|
pragma Singleton
|
|
pragma ComponentBehavior: Bound
|
|
|
|
/**
|
|
* Provides a list of wallpapers and an "apply" action that calls the existing
|
|
* switchwall.sh script. Pretty much a limited file browsing service.
|
|
*/
|
|
Singleton {
|
|
id: root
|
|
|
|
property string thumbgenScriptPath: `${FileUtils.trimFileProtocol(Directories.scriptPath)}/thumbnails/thumbgen.py`
|
|
property string directory: FileUtils.trimFileProtocol(`${Directories.pictures}/Wallpapers`)
|
|
property alias folderModel: folderModel // Expose for direct binding when needed
|
|
property string searchQuery: ""
|
|
readonly property list<string> extensions: [ // TODO: add videos
|
|
"jpg", "jpeg", "png", "webp", "avif", "bmp", "svg"
|
|
]
|
|
property list<string> wallpapers: [] // List of absolute file paths (without file://)
|
|
|
|
signal changed()
|
|
signal thumbnailGenerated(directory: string)
|
|
|
|
// Executions
|
|
Process {
|
|
id: applyProc
|
|
}
|
|
|
|
function openFallbackPicker(darkMode = Appearance.m3colors.darkmode) {
|
|
applyProc.exec([
|
|
Directories.wallpaperSwitchScriptPath,
|
|
"--mode", (darkMode ? "dark" : "light")
|
|
])
|
|
}
|
|
|
|
function apply(path, darkMode = Appearance.m3colors.darkmode) {
|
|
if (!path || path.length === 0) return
|
|
applyProc.exec([
|
|
Directories.wallpaperSwitchScriptPath,
|
|
"--image", path,
|
|
"--mode", (darkMode ? "dark" : "light")
|
|
])
|
|
root.changed()
|
|
}
|
|
|
|
Process {
|
|
id: selectProc
|
|
property string filePath: ""
|
|
property bool darkMode: Appearance.m3colors.darkmode
|
|
function select(filePath, darkMode = Appearance.m3colors.darkmode) {
|
|
selectProc.filePath = filePath
|
|
selectProc.darkMode = darkMode
|
|
selectProc.exec(["test", "-d", FileUtils.trimFileProtocol(filePath)])
|
|
}
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
setDirectory(selectProc.filePath);
|
|
return;
|
|
}
|
|
root.apply(selectProc.filePath, selectProc.darkMode);
|
|
}
|
|
}
|
|
|
|
function select(filePath, darkMode = Appearance.m3colors.darkmode) {
|
|
selectProc.select(filePath, darkMode);
|
|
}
|
|
|
|
Process {
|
|
id: validateDirProc
|
|
property string nicePath: ""
|
|
function setDirectoryIfValid(path) {
|
|
validateDirProc.nicePath = FileUtils.trimFileProtocol(path).replace(/\/+$/, "")
|
|
if (/^\/*$/.test(validateDirProc.nicePath)) validateDirProc.nicePath = "/";
|
|
validateDirProc.exec(["test", "-d", nicePath])
|
|
}
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
root.directory = validateDirProc.nicePath
|
|
}
|
|
}
|
|
}
|
|
function setDirectory(path) {
|
|
validateDirProc.setDirectoryIfValid(path)
|
|
}
|
|
|
|
// Folder model
|
|
FolderListModel {
|
|
id: folderModel
|
|
folder: Qt.resolvedUrl(root.directory)
|
|
caseSensitive: false
|
|
nameFilters: root.extensions.map(ext => `*${searchQuery.split(" ").filter(s => s.length > 0).map(s => `*${s}*`)}*.${ext}`)
|
|
showDirs: true
|
|
showDotAndDotDot: false
|
|
showOnlyReadable: true
|
|
sortField: FolderListModel.Time
|
|
sortReversed: false
|
|
onCountChanged: {
|
|
root.wallpapers = []
|
|
for (let i = 0; i < folderModel.count; i++) {
|
|
const path = folderModel.get(i, "filePath") || FileUtils.trimFileProtocol(folderModel.get(i, "fileURL"))
|
|
if (path && path.length) root.wallpapers.push(path)
|
|
}
|
|
}
|
|
}
|
|
|
|
// Thumbnail generation
|
|
function generateThumbnail(size: string) {
|
|
if (!["normal", "large", "x-large", "xx-large"].includes(size)) throw new Error("Invalid thumbnail size");
|
|
thumbgenProc.directory = root.directory
|
|
thumbgenProc.running = false
|
|
thumbgenProc.command = [
|
|
thumbgenScriptPath,
|
|
"--size", size,
|
|
"-d", `${root.directory}`
|
|
]
|
|
thumbgenProc.running = true
|
|
}
|
|
Process {
|
|
id: thumbgenProc
|
|
property string directory
|
|
onExited: (exitCode, exitStatus) => {
|
|
root.thumbnailGenerated(thumbgenProc.directory)
|
|
}
|
|
}
|
|
}
|