nova-shell/shell/applets/BatteryApplet.qml

189 lines
5.4 KiB
QML

import QtQuick
import "../services" as S
Column {
id: root
required property color accentColor
property bool active: true
readonly property color _stateColor: S.BatteryService.charging ? S.Theme.base0B : S.BatteryService.critical ? S.Theme.base09 : S.BatteryService.percent < S.BatteryService.warnThresh ? S.Theme.base0A : root.accentColor
// Header - pct + time
Item {
width: parent.width
height: 28
Text {
anchors.right: parent.right
anchors.rightMargin: 12
anchors.verticalCenter: parent.verticalCenter
text: {
const t = S.BatteryService.charging ? S.BatteryService.timeToFull : S.BatteryService.timeToEmpty;
const ts = S.BatteryService.fmtTime(t);
return Math.round(S.BatteryService.percent) + "%" + (ts ? " " + ts : "");
}
color: root._stateColor
font.pixelSize: S.Theme.fontSize
font.family: S.Theme.fontFamily
font.bold: true
}
}
// Progress bar
Item {
width: parent.width
height: 14
Item {
anchors.left: parent.left
anchors.leftMargin: 12
anchors.right: parent.right
anchors.rightMargin: 12
anchors.verticalCenter: parent.verticalCenter
height: 6
Rectangle {
anchors.fill: parent
color: S.Theme.base02
radius: 3
}
Rectangle {
width: parent.width * Math.min(1, S.BatteryService.percent / 100)
height: parent.height
color: root._stateColor
radius: 3
Behavior on width {
enabled: root.active
NumberAnimation {
duration: 300
easing.type: Easing.OutCubic
}
}
}
// Warning threshold marker
Rectangle {
x: parent.width * (S.BatteryService.warnThresh / 100) - 1
width: 1
height: parent.height + 4
anchors.verticalCenter: parent.verticalCenter
color: S.Theme.base0A
opacity: 0.6
}
// Critical threshold marker
Rectangle {
x: parent.width * (S.BatteryService.critThresh / 100) - 1
width: 1
height: parent.height + 4
anchors.verticalCenter: parent.verticalCenter
color: S.Theme.base08
opacity: 0.6
}
}
}
// 24h history sparkline (area chart)
SparklineCanvas {
anchors.left: parent.left
anchors.leftMargin: 12
anchors.right: parent.right
anchors.rightMargin: 12
height: 44
history: S.BatteryService.history
color: root._stateColor
active: root.active
maxSamples: 1440
backgroundTint: 0.07
areaMode: true
thresholds: [
{
value: S.BatteryService.warnThresh,
color: S.Theme.base0A
},
{
value: S.BatteryService.critThresh,
color: S.Theme.base08
}
]
}
// Footer: thresholds + time label
Item {
width: parent.width
height: 16
Text {
anchors.left: parent.left
anchors.leftMargin: 12
anchors.verticalCenter: parent.verticalCenter
text: "warn " + S.BatteryService.warnThresh + "% crit " + S.BatteryService.critThresh + "%"
color: S.Theme.base03
font.pixelSize: S.Theme.fontSize - 3
font.family: S.Theme.fontFamily
font.letterSpacing: 0.5
}
Text {
anchors.right: parent.right
anchors.rightMargin: 12
anchors.verticalCenter: parent.verticalCenter
text: "24h"
color: S.Theme.base03
font.pixelSize: S.Theme.fontSize - 3
font.family: S.Theme.fontFamily
}
}
Separator {}
// Rate row
InfoRow {
visible: S.BatteryService.changeRate !== 0
height: 20
label: S.BatteryService.charging ? "Charging" : "Discharging"
value: {
const r = Math.abs(S.BatteryService.changeRate);
return r > 0 ? r.toFixed(1) + " W" : "";
}
valueColor: root._stateColor
}
// Wattage history sparkline
SparklineCanvas {
visible: S.BatteryService.rateHistory.length > 1
anchors.left: parent.left
anchors.leftMargin: 12
anchors.right: parent.right
anchors.rightMargin: 12
height: 24
history: S.BatteryService.rateHistory
color: root._stateColor
active: root.active
maxSamples: 60
maxValue: null
minValue: null
backgroundTint: 0.08
colorFunction: v => v >= 0 ? S.Theme.base0B : root._stateColor
}
// Health row
InfoRow {
visible: S.BatteryService.healthSupported
height: 20
label: "Health"
value: Math.round(S.BatteryService.healthPercent) + "%"
valueColor: {
const h = S.BatteryService.healthPercent;
return h < 50 ? S.Theme.base08 : h < 75 ? S.Theme.base0A : S.Theme.base0B;
}
}
Item {
width: 1
height: 4
}
}