mirror of
https://github.com/AvengeMedia/DankMaterialShell.git
synced 2026-10-22 03:04:01 -04:00
454 lines
19 KiB
QML
454 lines
19 KiB
QML
import QtQuick
|
|
import qs.Common
|
|
import qs.Services
|
|
import qs.DCommon.Widgets
|
|
import qs.Widgets
|
|
import qs.Modules.Settings.Widgets
|
|
import "../../Services/BootEntries.js" as BootEntries
|
|
|
|
Item {
|
|
id: root
|
|
|
|
property bool onAc: true
|
|
|
|
readonly property var timeoutValues: [0, 15, 30, 60, 120, 180, 300, 600, 900, 1200, 1800, 3600, 5400, 7200, 10800]
|
|
readonly property var timeoutOptions: timeoutValues.map(seconds => seconds === 0 ? I18n.tr("Never", "timeout option meaning the action never happens") : I18n.duration(seconds))
|
|
readonly property var gracePeriodValues: [1, 2, 3, 4, 5, 10, 15, 20, 30]
|
|
readonly property var gracePeriodOptions: gracePeriodValues.map(seconds => I18n.duration(seconds))
|
|
|
|
function sourceKey(suffix) {
|
|
return (onAc ? "ac" : "battery") + suffix;
|
|
}
|
|
|
|
function timeoutText(key) {
|
|
const index = timeoutValues.indexOf(SettingsData[key]);
|
|
return timeoutOptions[index >= 0 ? index : 0];
|
|
}
|
|
|
|
function setTimeoutFromText(key, text) {
|
|
const index = timeoutOptions.indexOf(text);
|
|
if (index < 0)
|
|
return;
|
|
SettingsData.set(key, timeoutValues[index]);
|
|
}
|
|
|
|
function gracePeriodText(key) {
|
|
const index = gracePeriodValues.indexOf(SettingsData[key]);
|
|
return gracePeriodOptions[index >= 0 ? index : 4];
|
|
}
|
|
|
|
function setGracePeriodFromText(key, text) {
|
|
const index = gracePeriodOptions.indexOf(text);
|
|
if (index < 0)
|
|
return;
|
|
SettingsData.set(key, gracePeriodValues[index]);
|
|
}
|
|
|
|
SettingsPage {
|
|
id: mainColumn
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "schedule"
|
|
title: I18n.tr("Idle", "noun, settings card title for idle timeout settings")
|
|
settingKey: "idleSettings"
|
|
|
|
SettingsButtonGroupRow {
|
|
text: I18n.tr("Power source")
|
|
visible: BatteryService.batteryAvailable
|
|
model: [I18n.tr("AC power"), I18n.tr("Battery")]
|
|
currentIndex: root.onAc ? 0 : 1
|
|
checkEnabled: false
|
|
onSelectionChanged: (index, selected) => {
|
|
if (!selected)
|
|
return;
|
|
root.onAc = index === 0;
|
|
}
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "lockTimeout"
|
|
tags: ["lock", "timeout", "idle", "automatic", "security"]
|
|
text: I18n.tr("Automatically lock after")
|
|
resetKeys: [root.sourceKey("LockTimeout")]
|
|
options: root.timeoutOptions
|
|
currentValue: root.timeoutText(root.sourceKey("LockTimeout"))
|
|
onValueChanged: value => root.setTimeoutFromText(root.sourceKey("LockTimeout"), value)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "monitorTimeout"
|
|
tags: ["monitor", "display", "screen", "timeout", "off", "idle"]
|
|
text: I18n.tr("Turn off displays after")
|
|
resetKeys: [root.sourceKey("MonitorTimeout")]
|
|
options: root.timeoutOptions
|
|
currentValue: root.timeoutText(root.sourceKey("MonitorTimeout"))
|
|
onValueChanged: value => root.setTimeoutFromText(root.sourceKey("MonitorTimeout"), value)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "postLockMonitorTimeout"
|
|
tags: ["monitor", "display", "screen", "timeout", "off", "lock", "after", "post"]
|
|
text: I18n.tr("Turn off displays after lock")
|
|
resetKeys: [root.sourceKey("PostLockMonitorTimeout")]
|
|
options: root.timeoutOptions
|
|
currentValue: root.timeoutText(root.sourceKey("PostLockMonitorTimeout"))
|
|
onValueChanged: value => root.setTimeoutFromText(root.sourceKey("PostLockMonitorTimeout"), value)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "suspendTimeout"
|
|
tags: ["suspend", "sleep", "timeout", "idle", "system"]
|
|
text: I18n.tr("Suspend system after")
|
|
resetKeys: [root.sourceKey("SuspendTimeout")]
|
|
options: root.timeoutOptions
|
|
currentValue: root.timeoutText(root.sourceKey("SuspendTimeout"))
|
|
onValueChanged: value => root.setTimeoutFromText(root.sourceKey("SuspendTimeout"), value)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "suspendBehavior"
|
|
tags: ["suspend", "hibernate", "sleep", "behavior"]
|
|
visible: SessionService.hibernateSupported
|
|
text: I18n.tr("Suspend behavior")
|
|
resetKeys: [root.sourceKey("SuspendBehavior")]
|
|
options: [I18n.tr("Suspend"), I18n.tr("Hibernate"), I18n.tr("Suspend then hibernate")]
|
|
currentValue: options[SettingsData[root.sourceKey("SuspendBehavior")]] ?? options[0]
|
|
onValueChanged: value => {
|
|
const index = options.indexOf(value);
|
|
if (index < 0)
|
|
return;
|
|
SettingsData.set(root.sourceKey("SuspendBehavior"), index);
|
|
}
|
|
}
|
|
|
|
SettingsToggleRow {
|
|
settingKey: "lockBeforeSuspend"
|
|
tags: ["lock", "suspend", "hibernate", "sleep", "security"]
|
|
text: I18n.tr("Lock before suspend")
|
|
checked: SettingsData.lockBeforeSuspend
|
|
visible: SessionService.loginctlAvailable && SettingsData.loginctlLockIntegration
|
|
onToggled: checked => SettingsData.set("lockBeforeSuspend", checked)
|
|
}
|
|
}
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "gradient"
|
|
title: I18n.tr("Fade")
|
|
settingKey: "idleFade"
|
|
tags: ["fade", "grace", "period", "lock", "dpms", "display"]
|
|
|
|
SettingsToggleRow {
|
|
settingKey: "fadeToLockEnabled"
|
|
tags: ["fade", "lock", "screen", "idle", "grace period"]
|
|
text: I18n.tr("Fade to lock screen")
|
|
description: I18n.tr("Fades the screen out first. Input during the fade cancels it", "idle fade toggle description")
|
|
checked: SettingsData.fadeToLockEnabled
|
|
onToggled: checked => SettingsData.set("fadeToLockEnabled", checked)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "fadeToLockGracePeriod"
|
|
tags: ["fade", "grace", "period", "timeout", "lock"]
|
|
text: I18n.tr("Lock fade grace period")
|
|
visible: SettingsData.fadeToLockEnabled
|
|
options: root.gracePeriodOptions
|
|
currentValue: root.gracePeriodText("fadeToLockGracePeriod")
|
|
onValueChanged: value => root.setGracePeriodFromText("fadeToLockGracePeriod", value)
|
|
}
|
|
|
|
SettingsToggleRow {
|
|
settingKey: "fadeToDpmsEnabled"
|
|
tags: ["fade", "dpms", "monitor", "screen", "idle", "grace period"]
|
|
text: I18n.tr("Fade to display off")
|
|
description: I18n.tr("Fades the screen out first. Input during the fade cancels it", "idle fade toggle description")
|
|
checked: SettingsData.fadeToDpmsEnabled
|
|
onToggled: checked => SettingsData.set("fadeToDpmsEnabled", checked)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
settingKey: "fadeToDpmsGracePeriod"
|
|
tags: ["fade", "grace", "period", "timeout", "dpms", "monitor"]
|
|
text: I18n.tr("Display fade grace period")
|
|
visible: SettingsData.fadeToDpmsEnabled
|
|
options: root.gracePeriodOptions
|
|
currentValue: root.gracePeriodText("fadeToDpmsGracePeriod")
|
|
onValueChanged: value => root.setGracePeriodFromText("fadeToDpmsGracePeriod", value)
|
|
}
|
|
}
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "tune"
|
|
title: I18n.tr("Power menu")
|
|
settingKey: "powerMenu"
|
|
|
|
SettingsToggleRow {
|
|
settingKey: "powerMenuGridLayout"
|
|
tags: ["power", "menu", "grid", "layout", "list"]
|
|
text: I18n.tr("Grid layout")
|
|
checked: SettingsData.powerMenuGridLayout
|
|
onToggled: checked => SettingsData.set("powerMenuGridLayout", checked)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
readonly property var actionValues: ["reboot", "logout", "poweroff", "lock", "suspend", "restart", "hibernate", "softreboot"]
|
|
|
|
settingKey: "powerMenuDefaultAction"
|
|
tags: ["power", "menu", "default", "action", "reboot", "logout", "shutdown"]
|
|
text: I18n.tr("Default selected action")
|
|
options: [I18n.tr("Reboot"), I18n.tr("Log out"), I18n.tr("Power off"), I18n.tr("Lock"), I18n.tr("Suspend"), I18n.tr("Restart DMS"), I18n.tr("Hibernate"), I18n.tr("Soft reboot")]
|
|
currentValue: {
|
|
const index = actionValues.indexOf(SettingsData.powerMenuDefaultAction || "logout");
|
|
return index >= 0 ? options[index] : I18n.tr("Log out");
|
|
}
|
|
onValueChanged: value => {
|
|
const index = options.indexOf(value);
|
|
if (index < 0)
|
|
return;
|
|
SettingsData.set("powerMenuDefaultAction", actionValues[index]);
|
|
}
|
|
}
|
|
|
|
Repeater {
|
|
model: [
|
|
{
|
|
key: "reboot",
|
|
label: I18n.tr("Show reboot")
|
|
},
|
|
{
|
|
key: "logout",
|
|
label: I18n.tr("Show log out")
|
|
},
|
|
{
|
|
key: "poweroff",
|
|
label: I18n.tr("Show power off")
|
|
},
|
|
{
|
|
key: "lock",
|
|
label: I18n.tr("Show lock")
|
|
},
|
|
{
|
|
key: "suspend",
|
|
label: I18n.tr("Show suspend")
|
|
},
|
|
{
|
|
key: "restart",
|
|
label: I18n.tr("Show restart DMS")
|
|
},
|
|
{
|
|
key: "switchuser",
|
|
label: I18n.tr("Show switch user")
|
|
},
|
|
{
|
|
key: "hibernate",
|
|
label: I18n.tr("Show hibernate"),
|
|
hibernate: true
|
|
},
|
|
{
|
|
key: "softreboot",
|
|
label: I18n.tr("Show soft reboot"),
|
|
softreboot: true
|
|
}
|
|
]
|
|
|
|
SettingsToggleRow {
|
|
required property var modelData
|
|
|
|
settingKey: "powerMenuAction_" + modelData.key
|
|
tags: ["power", "menu", "action", "show", modelData.key]
|
|
text: modelData.label
|
|
visible: {
|
|
if (modelData.hibernate)
|
|
return SessionService.hibernateSupported;
|
|
if (modelData.softreboot)
|
|
return SessionService.softRebootSupported;
|
|
return true;
|
|
}
|
|
checked: SettingsData.powerMenuActions.includes(modelData.key)
|
|
onToggled: checked => {
|
|
const others = SettingsData.powerMenuActions.filter(action => action !== modelData.key);
|
|
SettingsData.set("powerMenuActions", checked ? others.concat([modelData.key]) : others);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "restart_alt"
|
|
title: I18n.tr("Reboot to another OS", "settings card title, lists EFI boot entries the power menu can reboot into")
|
|
settingKey: "powerMenuBootEntries"
|
|
tags: ["power", "menu", "reboot", "boot", "efi", "uefi", "windows", "dual boot", "bootnext"]
|
|
// Saved entries stay listed wherever this config lands, so they can always be removed
|
|
visible: SettingsData.powerMenuBootEntries.length > 0 || (BootEntryService.status !== "unknown" && BootEntryService.status !== "noEfi")
|
|
|
|
Component.onCompleted: BootEntryService.refresh()
|
|
|
|
SettingsRow {
|
|
visible: BootEntryService.unavailableReason !== ""
|
|
title: BootEntryService.unavailableReason
|
|
titleColor: Theme.surfaceVariantText
|
|
}
|
|
|
|
SettingsRow {
|
|
id: bootEntryPicker
|
|
|
|
readonly property var options: BootEntries.pickerOptions(BootEntryService.entries, BootEntryService.currentId, SettingsData.powerMenuBootEntries)
|
|
|
|
visible: BootEntryService.status === "ready"
|
|
title: I18n.tr("Add entry", "settings row that adds an EFI boot entry to the power menu")
|
|
|
|
DDropdown {
|
|
id: bootEntryDropdown
|
|
downKeyOpens: false
|
|
backgroundColor: SettingsMetrics.controlSurface
|
|
enabled: bootEntryPicker.options.length > 0
|
|
Accessible.name: bootEntryPicker.title
|
|
width: Math.min(dropdownWidth, bootEntryPicker.width - SettingsMetrics.rowPaddingH * 2)
|
|
options: bootEntryPicker.options.map(option => option.name)
|
|
emptyText: I18n.tr("Select", "verb, dropdown placeholder or option that opens a picker")
|
|
onValueChanged: value => {
|
|
const option = bootEntryPicker.options.find(option => option.name === value);
|
|
currentValue = "";
|
|
if (!option)
|
|
return;
|
|
SettingsData.set("powerMenuBootEntries", SettingsData.powerMenuBootEntries.concat([
|
|
{
|
|
id: option.id,
|
|
label: option.label
|
|
}
|
|
]));
|
|
}
|
|
}
|
|
}
|
|
|
|
Repeater {
|
|
model: SettingsData.powerMenuBootEntries
|
|
|
|
delegate: SettingsRow {
|
|
id: bootEntryRow
|
|
|
|
required property var modelData
|
|
required property int index
|
|
|
|
title: modelData.label
|
|
subtitle: "Boot" + modelData.id
|
|
iconName: "restart_alt"
|
|
|
|
DActionButton {
|
|
anchors.verticalCenter: parent.verticalCenter
|
|
iconName: "delete"
|
|
iconColor: Theme.error
|
|
Accessible.name: I18n.tr("Remove", "verb, button that removes an item from a list")
|
|
onClicked: SettingsData.set("powerMenuBootEntries", SettingsData.powerMenuBootEntries.filter((entry, i) => i !== bootEntryRow.index))
|
|
}
|
|
}
|
|
}
|
|
|
|
SettingsRow {
|
|
visible: BootEntryService.status === "ready" && !SettingsData.powerMenuBootEntries.length
|
|
title: I18n.tr("No items added yet", "empty list of saved EFI boot entries")
|
|
titleColor: Theme.surfaceVariantText
|
|
}
|
|
}
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "check_circle"
|
|
title: I18n.tr("Confirmation", "power settings card title, hold to confirm power actions")
|
|
settingKey: "powerConfirmation"
|
|
|
|
SettingsToggleRow {
|
|
settingKey: "powerActionConfirm"
|
|
tags: ["power", "confirm", "hold", "button", "safety"]
|
|
text: I18n.tr("Hold to confirm")
|
|
checked: SettingsData.powerActionConfirm
|
|
onToggled: checked => SettingsData.set("powerActionConfirm", checked)
|
|
}
|
|
|
|
SettingsDropdownRow {
|
|
readonly property var durationValues: [0.25, 0.5, 0.75, 1, 2, 3, 5, 10]
|
|
|
|
enabled: SettingsData.powerActionConfirm
|
|
settingKey: "powerActionHoldDuration"
|
|
tags: ["power", "hold", "duration", "confirm", "time"]
|
|
text: I18n.tr("Hold duration")
|
|
options: durationValues.map(seconds => I18n.duration(seconds))
|
|
currentValue: {
|
|
const index = durationValues.indexOf(SettingsData.powerActionHoldDuration);
|
|
return index >= 0 ? options[index] : I18n.duration(0.5);
|
|
}
|
|
onValueChanged: value => {
|
|
const index = options.indexOf(value);
|
|
if (index < 0)
|
|
return;
|
|
SettingsData.set("powerActionHoldDuration", durationValues[index]);
|
|
}
|
|
}
|
|
}
|
|
|
|
SettingsCard {
|
|
width: parent.width
|
|
iconName: "developer_mode"
|
|
title: I18n.tr("Custom commands")
|
|
settingKey: "customPowerActions"
|
|
tags: ["lock", "logout", "suspend", "hibernate", "reboot", "poweroff", "power off", "shutdown", "command", "script", "override"]
|
|
|
|
Repeater {
|
|
model: [
|
|
{
|
|
key: "customPowerActionLock",
|
|
icon: "lock",
|
|
label: I18n.tr("Lock"),
|
|
placeholder: "/usr/bin/myLock.sh"
|
|
},
|
|
{
|
|
key: "customPowerActionLogout",
|
|
icon: "logout",
|
|
label: I18n.tr("Log out"),
|
|
placeholder: "/usr/bin/myLogout.sh"
|
|
},
|
|
{
|
|
key: "customPowerActionSuspend",
|
|
icon: "bedtime",
|
|
label: I18n.tr("Suspend"),
|
|
placeholder: "/usr/bin/mySuspend.sh"
|
|
},
|
|
{
|
|
key: "customPowerActionHibernate",
|
|
icon: "ac_unit",
|
|
label: I18n.tr("Hibernate"),
|
|
placeholder: "/usr/bin/myHibernate.sh"
|
|
},
|
|
{
|
|
key: "customPowerActionReboot",
|
|
icon: "restart_alt",
|
|
label: I18n.tr("Reboot"),
|
|
placeholder: "/usr/bin/myReboot.sh"
|
|
},
|
|
{
|
|
key: "customPowerActionPowerOff",
|
|
icon: "power_settings_new",
|
|
label: I18n.tr("Power off"),
|
|
placeholder: "/usr/bin/myPowerOff.sh"
|
|
}
|
|
]
|
|
|
|
SettingsTextFieldRow {
|
|
required property var modelData
|
|
|
|
settingKey: modelData.key
|
|
tags: ["power", "command", "override", modelData.label]
|
|
text: modelData.label
|
|
leftIconName: modelData.icon
|
|
value: SettingsData[modelData.key] || ""
|
|
placeholderText: modelData.placeholder
|
|
onValueEdited: value => SettingsData.set(modelData.key, value.trim())
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|