From e3c171840f4eabe4e7561743bd456eef9a8e023f Mon Sep 17 00:00:00 2001 From: EmmetZ Date: Fri, 21 Nov 2025 10:23:23 +0800 Subject: [PATCH] feat: add brightness panel for bar brightness widget --- Modules/Bar/Widgets/Brightness.qml | 10 +- .../MainScreen/Backgrounds/AllBackgrounds.qml | 7 + Modules/MainScreen/MainScreen.qml | 9 ++ Modules/Panels/Brightness/BrightnessPanel.qml | 148 ++++++++++++++++++ 4 files changed, 171 insertions(+), 3 deletions(-) create mode 100644 Modules/Panels/Brightness/BrightnessPanel.qml diff --git a/Modules/Bar/Widgets/Brightness.qml b/Modules/Bar/Widgets/Brightness.qml index 54fc992b..ad9088c1 100644 --- a/Modules/Bar/Widgets/Brightness.qml +++ b/Modules/Bar/Widgets/Brightness.qml @@ -143,9 +143,13 @@ Item { } onClicked: { - var settingsPanel = PanelService.getPanel("settingsPanel", screen); - settingsPanel.requestedTab = SettingsPanel.Tab.Display; - settingsPanel.open(); + if ((Quickshell.screens || []).length > 0) { + PanelService.getPanel("brightnessPanel", screen)?.toggle(this); + } else { + var settingsPanel = PanelService.getPanel("settingsPanel", screen); + settingsPanel.requestedTab = SettingsPanel.Tab.Display; + settingsPanel.open(); + } } onRightClicked: { diff --git a/Modules/MainScreen/Backgrounds/AllBackgrounds.qml b/Modules/MainScreen/Backgrounds/AllBackgrounds.qml index 207880b5..d3339f27 100644 --- a/Modules/MainScreen/Backgrounds/AllBackgrounds.qml +++ b/Modules/MainScreen/Backgrounds/AllBackgrounds.qml @@ -76,6 +76,13 @@ Item { backgroundColor: panelBackgroundColor } + // Brightness + PanelBackground { + panel: root.windowRoot.brightnessPanelPlaceholder + shapeContainer: backgroundsShape + backgroundColor: panelBackgroundColor + } + // Calendar PanelBackground { panel: root.windowRoot.calendarPanelPlaceholder diff --git a/Modules/MainScreen/MainScreen.qml b/Modules/MainScreen/MainScreen.qml index c9080490..f9b6d193 100644 --- a/Modules/MainScreen/MainScreen.qml +++ b/Modules/MainScreen/MainScreen.qml @@ -11,6 +11,7 @@ import qs.Modules.Bar import qs.Modules.Bar.Extras import qs.Modules.Panels.Audio import qs.Modules.Panels.Bluetooth +import qs.Modules.Panels.Brightness import qs.Modules.Panels.Calendar import qs.Modules.Panels.Changelog import qs.Modules.Panels.ControlCenter @@ -33,6 +34,7 @@ PanelWindow { // Expose panels as readonly property aliases readonly property alias audioPanel: audioPanel readonly property alias bluetoothPanel: bluetoothPanel + readonly property alias brightnessPanel: brightnessPanel readonly property alias calendarPanel: calendarPanel readonly property alias changelogPanel: changelogPanel readonly property alias controlCenterPanel: controlCenterPanel @@ -48,6 +50,7 @@ PanelWindow { // Expose panel placeholders for AllBackgrounds readonly property var audioPanelPlaceholder: audioPanel.panelPlaceholder readonly property var bluetoothPanelPlaceholder: bluetoothPanel.panelPlaceholder + readonly property var brightnessPanelPlaceholder: brightnessPanel.panelPlaceholder readonly property var calendarPanelPlaceholder: calendarPanel.panelPlaceholder readonly property var changelogPanelPlaceholder: changelogPanel.panelPlaceholder readonly property var controlCenterPanelPlaceholder: controlCenterPanel.panelPlaceholder @@ -171,6 +174,12 @@ PanelWindow { screen: root.screen } + BrightnessPanel { + id: brightnessPanel + objectName: "brightnessPanel-" + (root.screen?.name || "unknown") + screen: root.screen + } + ControlCenterPanel { id: controlCenterPanel objectName: "controlCenterPanel-" + (root.screen?.name || "unknown") diff --git a/Modules/Panels/Brightness/BrightnessPanel.qml b/Modules/Panels/Brightness/BrightnessPanel.qml new file mode 100644 index 00000000..79d75ba4 --- /dev/null +++ b/Modules/Panels/Brightness/BrightnessPanel.qml @@ -0,0 +1,148 @@ +import QtQuick +import QtQuick.Controls +import QtQuick.Layouts +import Quickshell +import Quickshell.Io +import qs.Commons +import qs.Modules.MainScreen +import qs.Services.Compositor +import qs.Services.Hardware +import qs.Widgets + +SmartPanel { + id: root + + preferredWidth: Math.round(340 * Style.uiScaleRatio) + preferredHeight: Math.round(420 * Style.uiScaleRatio) + + function getIcon(brightness) { + return brightness <= 0.5 ? "brightness-low" : "brightness-high"; + } + + panelContent: Item { + property real contentPreferredHeight: mainColumn.implicitHeight + Style.marginL * 2 + + ColumnLayout { + id: mainColumn + anchors.fill: parent + anchors.margins: Style.marginL + spacing: Style.marginM + + // HEADER + NBox { + Layout.fillWidth: true + implicitHeight: headerRow.implicitHeight + (Style.marginM * 2) + + RowLayout { + id: headerRow + anchors.fill: parent + anchors.margins: Style.marginM + spacing: Style.marginM + + NIcon { + icon: "settings-display" + pointSize: Style.fontSizeXXL + color: Color.mPrimary + } + + NText { + text: I18n.tr("settings.display.title") + pointSize: Style.fontSizeL + font.weight: Style.fontWeightBold + color: Color.mOnSurface + Layout.fillWidth: true + } + + NIconButton { + icon: "close" + tooltipText: I18n.tr("tooltips.close") + baseSize: Style.baseWidgetSize * 0.8 + onClicked: { + root.close(); + } + } + } + } + + NScrollView { + Layout.fillWidth: true + Layout.fillHeight: true + horizontalPolicy: ScrollBar.AlwaysOff + verticalPolicy: ScrollBar.AsNeeded + clip: true + contentWidth: availableWidth + + // AudioService Devices + ColumnLayout { + spacing: Style.marginM + width: parent.width + + Repeater { + model: Quickshell.screens || [] + delegate: NBox { + Layout.fillWidth: true + Layout.preferredHeight: outputColumn.implicitHeight + (Style.marginM * 2) + + property var brightnessMonitor: BrightnessService.getMonitorForScreen(modelData) + + ColumnLayout { + id: outputColumn + anchors.left: parent.left + anchors.right: parent.right + anchors.top: parent.top + anchors.margins: Style.marginM + spacing: Style.marginS + + NLabel { + label: modelData.name || "Unknown" + labelColor: Color.mPrimary + description: { + const compositorScale = CompositorService.getDisplayScale(modelData.name); + I18n.tr("system.monitor-description", { + "model": modelData.model, + "width": modelData.width * compositorScale, + "height": modelData.height * compositorScale, + "scale": compositorScale + }); + } + } + + RowLayout { + + Layout.fillWidth: true + spacing: Style.marginS + NIcon { + icon: getIcon(brightnessMonitor ? brightnessMonitor.brightness : 0) + pointSize: Style.fontSizeXL + color: Color.mOnSurface + } + + NValueSlider { + id: brightnessSlider + from: 0 + to: 1 + value: brightnessMonitor ? brightnessMonitor.brightness : 0.5 + stepSize: 0.01 + enabled: brightnessMonitor ? brightnessMonitor.brightnessControlAvailable : false + onMoved: value => { + if (brightnessMonitor && brightnessMonitor.brightnessControlAvailable) { + brightnessMonitor.setBrightness(value); + } + } + onPressedChanged: (pressed, value) => { + if (brightnessMonitor && brightnessMonitor.brightnessControlAvailable) { + brightnessMonitor.setBrightness(value); + } + } + Layout.fillWidth: true + text: brightnessMonitor ? Math.round(brightnessSlider.value * 100) + "%" : "N/A" + } + } + } + } + } + } + } + } + } +}