mirror of
https://github.com/noctalia-dev/noctalia-shell.git
synced 2026-05-11 17:08:27 +08:00
248 lines
8.1 KiB
QML
248 lines
8.1 KiB
QML
pragma Singleton
|
|
|
|
import Quickshell
|
|
import Quickshell.Io
|
|
import Quickshell.Services.UPower
|
|
import qs.Commons
|
|
import qs.Services
|
|
|
|
Singleton {
|
|
id: root
|
|
|
|
enum ChargingMode {
|
|
Disabled = 0,
|
|
Full,
|
|
Balanced,
|
|
Lifespan
|
|
}
|
|
|
|
property int chargingMode: Settings.data.battery.chargingMode
|
|
readonly property string batterySetterScript: Quickshell.shellDir + '/Bin/battery-manager/set-battery-treshold.sh'
|
|
readonly property string batteryInstallerScript: Quickshell.shellDir + '/Bin/battery-manager/install-battery-manager.sh'
|
|
readonly property string batteryUninstallerScript: Quickshell.shellDir + '/Bin/battery-manager/uninstall-battery-manager.sh'
|
|
|
|
// This is used to omit toast message and writing mode to settings on startup
|
|
property bool initialSetter: true
|
|
|
|
// Choose icon based on charge and charging state
|
|
function getIcon(percent, charging, isReady) {
|
|
if (!isReady) {
|
|
return "battery-exclamation"
|
|
}
|
|
|
|
if (charging) {
|
|
return "battery-charging"
|
|
} else {
|
|
if (percent >= 90)
|
|
return "battery-4"
|
|
if (percent >= 50)
|
|
return "battery-3"
|
|
if (percent >= 25)
|
|
return "battery-2"
|
|
if (percent >= 0)
|
|
return "battery-1"
|
|
return "battery"
|
|
}
|
|
}
|
|
|
|
function getThresholdValue(chargingMode) {
|
|
switch (chargingMode) {
|
|
case BatteryService.ChargingMode.Full:
|
|
return "100"
|
|
case BatteryService.ChargingMode.Balanced:
|
|
return "80"
|
|
case BatteryService.ChargingMode.Lifespan:
|
|
return "60"
|
|
}
|
|
}
|
|
|
|
function toggleEnabled(enabled) {
|
|
if (enabled) {
|
|
setChargingMode(BatteryService.ChargingMode.Full)
|
|
} else {
|
|
BatteryService.initialSetter = true
|
|
ToastService.showNotice(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.uninstall-setup"))
|
|
PanelService.getPanel("batteryPanel")?.toggle(this)
|
|
uninstallerProcess.running = true
|
|
}
|
|
}
|
|
|
|
function setChargingMode(newMode) {
|
|
if (newMode !== BatteryService.ChargingMode.Full && newMode !== BatteryService.ChargingMode.Balanced && newMode !== BatteryService.ChargingMode.Lifespan) {
|
|
Logger.w("BatteryService", `Invalid charging mode set ${newMode}`)
|
|
return
|
|
}
|
|
BatteryService.chargingMode = newMode
|
|
BatteryService.applyChargingMode()
|
|
}
|
|
|
|
function cycleModes() {
|
|
// Cycles charging modes from full to lifespan while skipping disabled
|
|
const nextMode = (chargingMode % 3) + 1
|
|
setChargingMode(nextMode)
|
|
}
|
|
|
|
function applyChargingMode() {
|
|
let command = [batterySetterScript]
|
|
|
|
// Currently the script sends notifications by default but quickshell
|
|
// uses toast messages so the flag is passed to supress notifs
|
|
command.push("-q")
|
|
|
|
command.push(BatteryService.getThresholdValue(BatteryService.chargingMode))
|
|
|
|
setterProcess.command = command
|
|
setterProcess.running = true
|
|
}
|
|
|
|
function runInstaller() {
|
|
installerProcess.command = ["pkexec", batteryInstallerScript]
|
|
installerProcess.running = true
|
|
}
|
|
|
|
function init() {
|
|
if (BatteryService.chargingMode !== BatteryService.ChargingMode.Disabled && BatteryService.chargingMode !== BatteryService.ChargingMode.Full) {
|
|
BatteryService.applyChargingMode()
|
|
}
|
|
}
|
|
|
|
Process {
|
|
id: setterProcess
|
|
workingDirectory: Quickshell.shellDir
|
|
running: false
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
Logger.i("BatteryService", "Battery threshold set successfully")
|
|
if (BatteryService.initialSetter) {
|
|
BatteryService.initialSetter = false
|
|
return
|
|
}
|
|
ToastService.showNotice(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.set-success-desc", {
|
|
"percent": BatteryService.getThresholdValue(BatteryService.chargingMode)
|
|
}))
|
|
Settings.data.battery.chargingMode = BatteryService.chargingMode
|
|
} else if (exitCode === 2) {
|
|
ToastService.showWarning(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.initial-setup"))
|
|
PanelService.getPanel("batteryPanel")?.toggle(this)
|
|
BatteryService.runInstaller()
|
|
} else {
|
|
ToastService.showError(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.set-failed"))
|
|
Logger.e("BatteryService", `Setter process failed with exit code: ${exitCode}`)
|
|
}
|
|
}
|
|
stderr: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.w("BatteryService", "SetterProcess stderr:", this.text)
|
|
}
|
|
}
|
|
}
|
|
stdout: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.i("BatteryService", "SetterProcess stdout:", this.text)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Installer process - installs battery manager components
|
|
Process {
|
|
id: installerProcess
|
|
workingDirectory: Quickshell.shellDir
|
|
running: false
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
ToastService.showNotice(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.install-success"))
|
|
BatteryService.applyChargingMode()
|
|
} else if (exitCode === 2) {
|
|
ToastService.showError(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.install-missing"))
|
|
} else if (exitCode === 3) {
|
|
ToastService.showError(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.install-unsupported"))
|
|
} else {
|
|
ToastService.showError(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.install-failed"))
|
|
}
|
|
|
|
if (exitCode !== 0) {
|
|
BatteryService.chargingMode = BatteryService.ChargingMode.Disabled
|
|
}
|
|
}
|
|
stderr: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.w("BatteryService", "InstallerProcess stderr:", this.text)
|
|
}
|
|
}
|
|
}
|
|
stdout: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.i("BatteryService", "InstallerProcess stdout:", this.text)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
Process {
|
|
id: uninstallerProcess
|
|
workingDirectory: Quickshell.shellDir
|
|
command: ["pkexec", batteryUninstallerScript]
|
|
running: false
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
Logger.i("BatteryService", "Battery Manager uninstalled successfully")
|
|
ToastService.showNotice(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.uninstall-success"))
|
|
Settings.data.battery.chargingMode = BatteryService.chargingMode
|
|
BatteryService.chargingMode = BatteryService.ChargingMode.Disabled
|
|
cleanupProcess.running = true
|
|
} else {
|
|
ToastService.showError(I18n.tr("toast.battery-manager.title"), I18n.tr("toast.battery-manager.uninstall-failed"))
|
|
Logger.e("BatteryService", `Uninstaller process failed with exit code: ${exitCode}`)
|
|
}
|
|
}
|
|
stderr: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.w("BatteryService", "UninstallerProcess stderr:", this.text)
|
|
}
|
|
}
|
|
}
|
|
stdout: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.i("BatteryService", "UninstallerProcess stdout:", this.text)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Cleanup process - deletes uninstaller after it sucessfull ;
|
|
Process {
|
|
id: cleanupProcess
|
|
workingDirectory: Quickshell.shellDir
|
|
command: ["rm", "-rf", batteryUninstallerScript]
|
|
running: false
|
|
onExited: (exitCode, exitStatus) => {
|
|
if (exitCode === 0) {
|
|
Logger.i("BatteryService", "Battery Manager uninstalled successfully")
|
|
} else {
|
|
Logger.e("BatteryService", `Cleanup process failed with exit code: ${exitCode}`)
|
|
}
|
|
}
|
|
stderr: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.w("BatteryService", "CleanupProcess stderr:", this.text)
|
|
}
|
|
}
|
|
}
|
|
stdout: StdioCollector {
|
|
onStreamFinished: {
|
|
if (this.text) {
|
|
Logger.i("BatteryService", "CleanupProcess stdout:", this.text)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|