136 lines
No EOL
4.5 KiB
QML
136 lines
No EOL
4.5 KiB
QML
// qmllint disable uncreatable-type
|
|
pragma ComponentBehavior: Bound
|
|
import Quickshell
|
|
import Quickshell.Wayland
|
|
import Quickshell.Hyprland
|
|
import Quickshell.Io
|
|
import QtQuick
|
|
import QtQuick.Layouts
|
|
|
|
|
|
ShellRoot {
|
|
Variants {
|
|
model: Quickshell.screens
|
|
|
|
PanelWindow {
|
|
id: root
|
|
required property var modelData
|
|
screen: modelData
|
|
|
|
property int wsCount: 5
|
|
property int wsOffset: {
|
|
const sorted = [...Quickshell.screens].sort((a, b) =>
|
|
b.name.localeCompare(a.name))
|
|
return sorted.indexOf(modelData) * wsCount
|
|
}
|
|
|
|
// Theme - Define once, use everywhere
|
|
property color colbg: "#1a1b26"
|
|
property color colCyan: "#0db9d7"
|
|
property color colBlue: "#7aa2f7"
|
|
property color colYellow: "#e0af68"
|
|
property string fontFamily: "JetBrainMono Nerd Font"
|
|
|
|
property int cpuUsage: 0
|
|
property var lastCpuIdle: 0
|
|
property var lastCpuTotal: 0
|
|
|
|
Process {
|
|
id: cpuProc
|
|
command: ["sh", "-c", "while true; do awk 'NR==1{print; exit}' /proc/stat; sleep 2; done"]
|
|
stdout: SplitParser {
|
|
onRead: data => {
|
|
if (!data) return
|
|
const p = data.trim().split(/\s+/)
|
|
const idle = parseInt(p[4]) + parseInt(p[5])
|
|
const total = p.slice(1, 8).reduce((a, b) => a + parseInt(b), 0)
|
|
if (root.lastCpuTotal > 0) {
|
|
root.cpuUsage = Math.round(100 * (1 - (idle - root.lastCpuIdle) / (total - root.lastCpuTotal)))
|
|
}
|
|
root.lastCpuTotal = total
|
|
root.lastCpuIdle = idle
|
|
}
|
|
}
|
|
Component.onCompleted: running = true
|
|
|
|
}
|
|
|
|
SystemClock {
|
|
id: clock
|
|
precision: SystemClock.Minutes
|
|
}
|
|
|
|
|
|
anchors {
|
|
top: true
|
|
left: true
|
|
right: true
|
|
}
|
|
|
|
implicitHeight: 30
|
|
color: colbg
|
|
|
|
RowLayout {
|
|
anchors {
|
|
fill: parent
|
|
margins: 8
|
|
}
|
|
|
|
|
|
|
|
// Repeter creates 5 copies, each gets an index (0-4)
|
|
Repeater {
|
|
model: root.wsCount
|
|
|
|
Item {
|
|
required property int index
|
|
|
|
Layout.preferredWidth: 12
|
|
Layout.preferredHeight: 12
|
|
property bool hovered: false
|
|
// live data from hyprland
|
|
property int wsId: root.wsOffset + index + 1
|
|
property var ws: Hyprland.workspaces.values.find(w => w.id === wsId)
|
|
property bool isActive: ws ? ws.active : false
|
|
|
|
Text {
|
|
anchors.centerIn: parent
|
|
text: parent.wsId
|
|
color: parent.isActive ? root.colCyan
|
|
: parent.hovered ? Qt.lighter(parent.ws ? root.colBlue : "#444b6a", 1.5)
|
|
: root.colBlue
|
|
Behavior on color { ColorAnimation { duration: 80 } }
|
|
font { pixelSize: 12; bold: true }
|
|
}
|
|
|
|
|
|
MouseArea {
|
|
anchors.fill: parent
|
|
hoverEnabled: true
|
|
onEntered: parent.hovered = true
|
|
onExited: parent.hovered = false
|
|
onClicked: if (parent.ws) parent.ws.activate()
|
|
}
|
|
}
|
|
}
|
|
|
|
Item { Layout.fillWidth: true }
|
|
|
|
Text {
|
|
text: Qt.formatTime(clock.date, "hh:mm")
|
|
color: root.colCyan
|
|
font { family: root.fontFamily; pixelSize: 14; bold: true }
|
|
}
|
|
|
|
Item { Layout.fillWidth: true } // left spacer
|
|
|
|
Text {
|
|
text: "CPU " + root.cpuUsage + "%"
|
|
color: root.colYellow
|
|
font { family: root.fontFamily; pixelSize: 12; bold:true }
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
} |