mirror of
https://github.com/zoriya/noctalia-shell.git
synced 2026-08-15 18:43:59 +00:00
Refactor: Panels and Bar background are now drawn separately with Shapes.
This commit is contained in:
@@ -0,0 +1,15 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
icon: BluetoothService.enabled ? "bluetooth" : "bluetooth-off"
|
||||
tooltipText: I18n.tr("quickSettings.bluetooth.tooltip.action")
|
||||
onClicked: {
|
||||
PanelService.getPanel("bluetoothPanel", screen)?.toggle(this)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,162 @@
|
||||
import QtQuick
|
||||
import Quickshell
|
||||
import Quickshell.Io
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
Item {
|
||||
id: root
|
||||
|
||||
property string widgetId: "CustomButton"
|
||||
property var widgetSettings: null
|
||||
|
||||
property string onClickedCommand: ""
|
||||
property string onRightClickedCommand: ""
|
||||
property string onMiddleClickedCommand: ""
|
||||
property string stateChecksJson: "[]" // Store state checks as JSON string
|
||||
|
||||
property string generalTooltipText: "Custom Button"
|
||||
property bool enableOnStateLogic: false
|
||||
|
||||
property string _currentIcon: "heart" // Default icon
|
||||
property bool _isHot: false
|
||||
property var _parsedStateChecks: [] // Local array for parsed state checks
|
||||
|
||||
property int _currentStateCheckIndex: -1
|
||||
property string _activeStateIcon: ""
|
||||
|
||||
implicitWidth: button.implicitWidth
|
||||
implicitHeight: button.implicitHeight
|
||||
|
||||
Connections {
|
||||
target: root
|
||||
|
||||
function _updatePropertiesFromSettings() {
|
||||
if (!widgetSettings) {
|
||||
return
|
||||
}
|
||||
|
||||
onClickedCommand = widgetSettings.onClicked || ""
|
||||
onRightClickedCommand = widgetSettings.onRightClicked || ""
|
||||
onMiddleClickedCommand = widgetSettings.onMiddleClicked || ""
|
||||
stateChecksJson = widgetSettings.stateChecksJson || "[]" // Populate from widgetSettings
|
||||
try {
|
||||
_parsedStateChecks = JSON.parse(stateChecksJson)
|
||||
} catch (e) {
|
||||
console.error("CustomButton: Failed to parse stateChecksJson:", e.message)
|
||||
_parsedStateChecks = []
|
||||
}
|
||||
generalTooltipText = widgetSettings.generalTooltipText || "Custom Button"
|
||||
enableOnStateLogic = widgetSettings.enableOnStateLogic || false
|
||||
|
||||
updateState()
|
||||
}
|
||||
|
||||
function onWidgetSettingsChanged() {
|
||||
if (widgetSettings) {
|
||||
_updatePropertiesFromSettings()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Process {
|
||||
id: stateCheckProcessExecutor
|
||||
running: false
|
||||
command: _currentStateCheckIndex !== -1 && _parsedStateChecks.length > _currentStateCheckIndex ? ["sh", "-c", _parsedStateChecks[_currentStateCheckIndex].command] : []
|
||||
onExited: function (exitCode, stdout, stderr) {
|
||||
var currentCheckItem = _parsedStateChecks[_currentStateCheckIndex]
|
||||
var currentCommand = currentCheckItem.command
|
||||
if (exitCode === 0) {
|
||||
// Command succeeded, this is the active state
|
||||
_isHot = true
|
||||
_activeStateIcon = currentCheckItem.icon || widgetSettings.icon || "heart"
|
||||
} else {
|
||||
// Command failed, try next one
|
||||
_currentStateCheckIndex++
|
||||
_checkNextState()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Timer {
|
||||
id: stateUpdateTimer
|
||||
interval: 200
|
||||
running: false
|
||||
repeat: false
|
||||
onTriggered: {
|
||||
if (enableOnStateLogic && _parsedStateChecks.length > 0) {
|
||||
_currentStateCheckIndex = 0
|
||||
_checkNextState()
|
||||
} else {
|
||||
_isHot = false
|
||||
_activeStateIcon = widgetSettings.icon || "heart"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function _checkNextState() {
|
||||
if (_currentStateCheckIndex < _parsedStateChecks.length) {
|
||||
var currentCheckItem = _parsedStateChecks[_currentStateCheckIndex]
|
||||
if (currentCheckItem && currentCheckItem.command) {
|
||||
stateCheckProcessExecutor.running = true
|
||||
} else {
|
||||
_currentStateCheckIndex++
|
||||
_checkNextState()
|
||||
}
|
||||
} else {
|
||||
// All checks failed
|
||||
_isHot = false
|
||||
_activeStateIcon = widgetSettings.icon || "heart"
|
||||
}
|
||||
}
|
||||
|
||||
function updateState() {
|
||||
if (!enableOnStateLogic || _parsedStateChecks.length === 0) {
|
||||
_isHot = false
|
||||
_activeStateIcon = widgetSettings.icon || "heart"
|
||||
return
|
||||
}
|
||||
stateUpdateTimer.restart()
|
||||
}
|
||||
|
||||
function _buildTooltipText() {
|
||||
let tooltip = generalTooltipText
|
||||
if (onClickedCommand) {
|
||||
tooltip += `\nLeft click: ${onClickedCommand}`
|
||||
}
|
||||
if (onRightClickedCommand) {
|
||||
tooltip += `\nRight click: ${onRightClickedCommand}`
|
||||
}
|
||||
if (onMiddleClickedCommand) {
|
||||
tooltip += `\nMiddle click: ${onMiddleClickedCommand}`
|
||||
}
|
||||
|
||||
return tooltip
|
||||
}
|
||||
|
||||
NIconButtonHot {
|
||||
id: button
|
||||
icon: _activeStateIcon
|
||||
hot: _isHot
|
||||
tooltipText: _buildTooltipText()
|
||||
onClicked: {
|
||||
if (onClickedCommand) {
|
||||
Quickshell.execDetached(["sh", "-c", onClickedCommand])
|
||||
updateState()
|
||||
}
|
||||
}
|
||||
onRightClicked: {
|
||||
if (onRightClickedCommand) {
|
||||
Quickshell.execDetached(["sh", "-c", onRightClickedCommand])
|
||||
updateState()
|
||||
}
|
||||
}
|
||||
onMiddleClicked: {
|
||||
if (onMiddleClickedCommand) {
|
||||
Quickshell.execDetached(["sh", "-c", onMiddleClickedCommand])
|
||||
updateState()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
icon: IdleInhibitorService.isInhibited ? "keep-awake-on" : "keep-awake-off"
|
||||
hot: IdleInhibitorService.isInhibited
|
||||
tooltipText: I18n.tr("quickSettings.keepAwake.tooltip.action")
|
||||
onClicked: IdleInhibitorService.manualToggle()
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Modules.Panels.Settings
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
enabled: ProgramCheckerService.wlsunsetAvailable
|
||||
icon: Settings.data.nightLight.enabled ? (Settings.data.nightLight.forced ? "nightlight-forced" : "nightlight-on") : "nightlight-off"
|
||||
hot: !Settings.data.nightLight.enabled || Settings.data.nightLight.forced
|
||||
tooltipText: I18n.tr("quickSettings.nightLight.tooltip.action")
|
||||
|
||||
onClicked: {
|
||||
if (!Settings.data.nightLight.enabled) {
|
||||
Settings.data.nightLight.enabled = true
|
||||
Settings.data.nightLight.forced = false
|
||||
} else if (Settings.data.nightLight.enabled && !Settings.data.nightLight.forced) {
|
||||
Settings.data.nightLight.forced = true
|
||||
} else {
|
||||
Settings.data.nightLight.enabled = false
|
||||
Settings.data.nightLight.forced = false
|
||||
}
|
||||
}
|
||||
|
||||
onRightClicked: {
|
||||
var settingsPanel = PanelService.getPanel("settingsPanel", screen)
|
||||
settingsPanel.requestedTab = SettingsPanel.Tab.Display
|
||||
settingsPanel.open()
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
icon: Settings.data.notifications.doNotDisturb ? "bell-off" : "bell"
|
||||
hot: Settings.data.notifications.doNotDisturb
|
||||
tooltipText: I18n.tr("quickSettings.notifications.tooltip.action")
|
||||
onClicked: PanelService.getPanel("notificationHistoryPanel", screen)?.toggle(this)
|
||||
onRightClicked: Settings.data.notifications.doNotDisturb = !Settings.data.notifications.doNotDisturb
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import Quickshell.Services.UPower
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
// Performance
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
readonly property bool hasPP: PowerProfileService.available
|
||||
|
||||
enabled: hasPP
|
||||
icon: PowerProfileService.getIcon()
|
||||
hot: !PowerProfileService.isDefault()
|
||||
tooltipText: I18n.tr("quickSettings.powerProfile.tooltip.action")
|
||||
onClicked: {
|
||||
PowerProfileService.cycleProfile()
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
enabled: ProgramCheckerService.gpuScreenRecorderAvailable
|
||||
icon: "camera-video"
|
||||
hot: ScreenRecorderService.isRecording
|
||||
tooltipText: I18n.tr("quickSettings.screenRecorder.tooltip.action")
|
||||
onClicked: {
|
||||
ScreenRecorderService.toggleRecording()
|
||||
if (!ScreenRecorderService.isRecording) {
|
||||
var panel = PanelService.getPanel("controlCenterPanel", screen)
|
||||
panel?.close()
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
enabled: Settings.data.wallpaper.enabled
|
||||
icon: "wallpaper-selector"
|
||||
tooltipText: I18n.tr("quickSettings.wallpaperSelector.tooltip.action")
|
||||
onClicked: PanelService.getPanel("wallpaperPanel", screen)?.toggle()
|
||||
onRightClicked: WallpaperService.setRandomWallpaper()
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
import QtQuick.Layouts
|
||||
import Quickshell
|
||||
import qs.Commons
|
||||
import qs.Services
|
||||
import qs.Widgets
|
||||
|
||||
NIconButtonHot {
|
||||
property ShellScreen screen
|
||||
|
||||
icon: {
|
||||
try {
|
||||
if (NetworkService.ethernetConnected) {
|
||||
return "ethernet"
|
||||
}
|
||||
let connected = false
|
||||
let signalStrength = 0
|
||||
for (const net in NetworkService.networks) {
|
||||
if (NetworkService.networks[net].connected) {
|
||||
connected = true
|
||||
signalStrength = NetworkService.networks[net].signal
|
||||
break
|
||||
}
|
||||
}
|
||||
return connected ? NetworkService.signalIcon(signalStrength) : "wifi-off"
|
||||
} catch (error) {
|
||||
Logger.e("Wi-Fi", "Error getting icon:", error)
|
||||
return "signal_wifi_bad"
|
||||
}
|
||||
}
|
||||
|
||||
tooltipText: I18n.tr("quickSettings.wifi.tooltip.action")
|
||||
onClicked: PanelService.getPanel("wifiPanel", screen)?.toggle(this)
|
||||
}
|
||||
Reference in New Issue
Block a user