From 435ecf8d4b67095e8fb6d7ac61d15391ca155d8e Mon Sep 17 00:00:00 2001 From: ferreo Date: Fri, 18 Jul 2025 18:53:42 +0100 Subject: [PATCH] feat: add date + calendar, also tidy up pointers/tooltips --- Bar/Bar.qml | 1 + Bar/Modules/Applauncher.qml | 3 +- Bar/Modules/Calendar.qml | 127 +++++++ Bar/Modules/ClockWidget.qml | 30 ++ Bar/Modules/Media.qml | 1 + Bar/Modules/SystemTray.qml | 1 + Bar/Modules/Time.qml | 48 ++- Bar/Modules/Volume.qml | 1 + Components/IconButton.qml | 36 ++ Components/PanelWithOverlay.qml | 1 - Settings/Settings.qml | 2 + Widgets/Notification/NotificationIcon.qml | 11 + Widgets/Sidebar/Button.qml | 1 + Widgets/Sidebar/Config/ProfileSettings.qml | 5 + Widgets/Sidebar/Config/WallpaperSettings.qml | 4 + Widgets/Sidebar/Config/WeatherSettings.qml | 139 ++++++- Widgets/Sidebar/Panel/PanelPopup.qml | 18 +- Widgets/Sidebar/Panel/QuickAccess.qml | 3 + Widgets/Sidebar/Panel/System.qml | 371 ++++++++++--------- 19 files changed, 595 insertions(+), 208 deletions(-) create mode 100644 Bar/Modules/Calendar.qml create mode 100644 Components/IconButton.qml diff --git a/Bar/Bar.qml b/Bar/Bar.qml index aa560f3..f2fb661 100644 --- a/Bar/Bar.qml +++ b/Bar/Bar.qml @@ -111,6 +111,7 @@ Scope { } ClockWidget { + screen: modelData anchors.verticalCenter: parent.verticalCenter } diff --git a/Bar/Modules/Applauncher.qml b/Bar/Modules/Applauncher.qml index ed93dac..e503d17 100644 --- a/Bar/Modules/Applauncher.qml +++ b/Bar/Modules/Applauncher.qml @@ -10,7 +10,7 @@ import "../../Helpers/Fuzzysort.js" as Fuzzysort PanelWithOverlay { id: appLauncherPanel - + WlrLayershell.keyboardFocus: WlrKeyboardFocus.OnDemand function showAt() { appLauncherPanelRect.showAt(); } @@ -377,6 +377,7 @@ PanelWithOverlay { root.selectedIndex = index; root.activateSelected(); } + cursorShape: Qt.PointingHandCursor onPressed: ripple.opacity = 0.18 onReleased: ripple.opacity = 0.0 } diff --git a/Bar/Modules/Calendar.qml b/Bar/Modules/Calendar.qml new file mode 100644 index 0000000..5065e1a --- /dev/null +++ b/Bar/Modules/Calendar.qml @@ -0,0 +1,127 @@ +import QtQuick +import QtQuick.Controls +import QtQuick.Layouts +import Quickshell +import qs.Components +import qs.Settings +import Quickshell.Wayland + +PanelWithOverlay { + id: calendarOverlay + + Rectangle { + color: Theme.backgroundPrimary + radius: 12 + border.color: Theme.backgroundTertiary + border.width: 1 + width: 340 + height: 380 + anchors.top: parent.top + anchors.right: parent.right + anchors.topMargin: 4 + anchors.rightMargin: 4 + + ColumnLayout { + anchors.fill: parent + anchors.margins: 16 + spacing: 12 + + // Month/Year header with navigation + RowLayout { + Layout.fillWidth: true + spacing: 8 + + IconButton { + icon: "chevron_left" + onClicked: { + let newDate = new Date(calendar.year, calendar.month - 1, 1); + calendar.year = newDate.getFullYear(); + calendar.month = newDate.getMonth(); + } + } + + Text { + Layout.fillWidth: true + horizontalAlignment: Text.AlignHCenter + text: calendar.title + color: Theme.textPrimary + opacity: 0.7 + font.pixelSize: 13 + font.family: Theme.fontFamily + font.bold: true + } + + IconButton { + icon: "chevron_right" + onClicked: { + let newDate = new Date(calendar.year, calendar.month + 1, 1); + calendar.year = newDate.getFullYear(); + calendar.month = newDate.getMonth(); + } + } + } + + DayOfWeekRow { + Layout.fillWidth: true + spacing: 0 + Layout.leftMargin: 8 // Align with grid + Layout.rightMargin: 8 + delegate: Text { + text: shortName + color: Theme.textPrimary + opacity: 0.8 + font.pixelSize: 13 + font.family: Theme.fontFamily + font.bold: true + horizontalAlignment: Text.AlignHCenter + width: 32 + } + } + + MonthGrid { + id: calendar + Layout.fillWidth: true + Layout.leftMargin: 8 + Layout.rightMargin: 8 + spacing: 0 + month: Time.date.getMonth() + year: Time.date.getFullYear() + + delegate: Rectangle { + width: 32 + height: 32 + radius: 8 + color: { + if (model.today) + return Theme.accentPrimary; + if (mouseArea2.containsMouse) + return Theme.backgroundTertiary; + return "transparent"; + } + + Text { + anchors.centerIn: parent + text: model.day + color: model.today ? Theme.onAccent : Theme.textPrimary + opacity: model.month === calendar.month ? (mouseArea2.containsMouse ? 1.0 : 0.7) : 0.3 + font.pixelSize: 13 + font.family: Theme.fontFamily + font.bold: model.today ? true : false + } + + MouseArea { + id: mouseArea2 + anchors.fill: parent + hoverEnabled: true + } + + Behavior on color { + ColorAnimation { + duration: 150 + } + } + } + } + } + } +} \ No newline at end of file diff --git a/Bar/Modules/ClockWidget.qml b/Bar/Modules/ClockWidget.qml index c32458f..f899d0d 100644 --- a/Bar/Modules/ClockWidget.qml +++ b/Bar/Modules/ClockWidget.qml @@ -1,7 +1,11 @@ import QtQuick import qs.Settings +import qs.Components Rectangle { + id: clockWidget + property var screen: (typeof modelData !== 'undefined' ? modelData : null) + property var showTooltip: false width: textItem.paintedWidth height: textItem.paintedHeight color: "transparent" @@ -15,4 +19,30 @@ Rectangle { color: Theme.textPrimary anchors.centerIn: parent } + + MouseArea { + id: clockMouseArea + anchors.fill: parent + hoverEnabled: true + onEntered: showTooltip = true + onExited: showTooltip = false + cursorShape: Qt.PointingHandCursor + onClicked: function() { + calendar.visible = !calendar.visible + } + } + + Calendar { + id: calendar + screen: clockWidget.screen + visible: false + } + + StyledTooltip { + id: dateTooltip + text: Time.dateString + tooltipVisible: showTooltip && !calendar.visible + targetItem: clockWidget + delay: 200 + } } diff --git a/Bar/Modules/Media.qml b/Bar/Modules/Media.qml index 632d5a6..ca30cd6 100644 --- a/Bar/Modules/Media.qml +++ b/Bar/Modules/Media.qml @@ -104,6 +104,7 @@ Item { MouseArea { id: playButton anchors.fill: parent + cursorShape: Qt.PointingHandCursor hoverEnabled: true enabled: MusicManager.canPlay || MusicManager.canPause onClicked: MusicManager.playPause() diff --git a/Bar/Modules/SystemTray.qml b/Bar/Modules/SystemTray.qml index f782c00..90d30fb 100644 --- a/Bar/Modules/SystemTray.qml +++ b/Bar/Modules/SystemTray.qml @@ -90,6 +90,7 @@ Row { id: trayMouseArea anchors.fill: parent hoverEnabled: true + cursorShape: Qt.PointingHandCursor acceptedButtons: Qt.LeftButton | Qt.RightButton | Qt.MiddleButton onClicked: (mouse) => { if (!modelData) return; diff --git a/Bar/Modules/Time.qml b/Bar/Modules/Time.qml index fbc8d82..0249e8c 100644 --- a/Bar/Modules/Time.qml +++ b/Bar/Modules/Time.qml @@ -2,15 +2,45 @@ pragma Singleton import Quickshell import QtQuick +import qs.Settings Singleton { - id: root - readonly property string time: { - Qt.formatDateTime(clock.date, "hh:mm") - } + id: root - SystemClock { - id: clock - precision: SystemClock.Seconds - } -} \ No newline at end of file + property var date: new Date() + property string time: Settings.settings.use12HourClock ? Qt.formatDateTime(date, "h:mm AP") : Qt.formatDateTime(date, "HH:mm") + property string dateString: { + let now = date; + let dayName = now.toLocaleDateString(Qt.locale(), "ddd"); + dayName = dayName.charAt(0).toUpperCase() + dayName.slice(1); + let day = now.getDate(); + let suffix; + if (day > 3 && day < 21) + suffix = 'th'; + else + switch (day % 10) { + case 1: + suffix = "st"; + break; + case 2: + suffix = "nd"; + break; + case 3: + suffix = "rd"; + break; + default: + suffix = "th"; + } + let month = now.toLocaleDateString(Qt.locale(), "MMMM"); + let year = now.toLocaleDateString(Qt.locale(), "yyyy"); + return `${dayName}, ` + (Settings.settings.reverseDayMonth ? `${month} ${day}${suffix} ${year}` : `${day}${suffix} ${month} ${year}`); + } + + Timer { + interval: 1000 + repeat: true + running: true + + onTriggered: root.date = new Date() + } +} diff --git a/Bar/Modules/Volume.qml b/Bar/Modules/Volume.qml index 7327c37..8ca074a 100644 --- a/Bar/Modules/Volume.qml +++ b/Bar/Modules/Volume.qml @@ -56,6 +56,7 @@ Item { propagateComposedEvents: true onEntered: volumeTooltip.tooltipVisible = true onExited: volumeTooltip.tooltipVisible = false + cursorShape: Qt.PointingHandCursor onWheel:(wheel) => { if (!shell) return; let step = 5; diff --git a/Components/IconButton.qml b/Components/IconButton.qml new file mode 100644 index 0000000..c6c0a85 --- /dev/null +++ b/Components/IconButton.qml @@ -0,0 +1,36 @@ +import QtQuick +import Quickshell +import Quickshell.Widgets +import qs.Settings + +MouseArea { + id: root + property string icon + property bool enabled: true + property bool hovering: false + property real size: 32 + cursorShape: Qt.PointingHandCursor + implicitWidth: size + implicitHeight: size + + hoverEnabled: true + onEntered: hovering = true + onExited: hovering = false + + Rectangle { + anchors.fill: parent + radius: 8 + color: root.hovering ? Theme.accentPrimary : "transparent" + } + Text { + id: iconText + anchors.centerIn: parent + text: root.icon + font.family: "Material Symbols Outlined" + font.pixelSize: 24 + color: root.hovering ? Theme.onAccent : Theme.textPrimary + horizontalAlignment: Text.AlignHCenter + verticalAlignment: Text.AlignVCenter + opacity: root.enabled ? 1.0 : 0.5 + } +} \ No newline at end of file diff --git a/Components/PanelWithOverlay.qml b/Components/PanelWithOverlay.qml index 7344165..0f83b51 100644 --- a/Components/PanelWithOverlay.qml +++ b/Components/PanelWithOverlay.qml @@ -22,7 +22,6 @@ PanelWindow { color: visible ? overlayColor : "transparent" visible: false WlrLayershell.exclusionMode: ExclusionMode.Ignore - WlrLayershell.keyboardFocus: WlrKeyboardFocus.OnDemand screen: (typeof modelData !== 'undefined' ? modelData : null) anchors.top: true anchors.left: true diff --git a/Settings/Settings.qml b/Settings/Settings.qml index e9ffec0..9947760 100644 --- a/Settings/Settings.qml +++ b/Settings/Settings.qml @@ -54,6 +54,8 @@ Singleton { property string transitionType: "random" property real transitionDuration: 1.1 property string visualizerType: "radial" + property bool reverseDayMonth: false + property bool use12HourClock: false } } diff --git a/Widgets/Notification/NotificationIcon.qml b/Widgets/Notification/NotificationIcon.qml index b6f08b8..6af48c6 100644 --- a/Widgets/Notification/NotificationIcon.qml +++ b/Widgets/Notification/NotificationIcon.qml @@ -2,6 +2,7 @@ import QtQuick import Quickshell import Quickshell.Io import qs.Settings +import qs.Components Item { id: root @@ -25,6 +26,16 @@ Item { hoverEnabled: true cursorShape: Qt.PointingHandCursor onClicked: notificationHistoryWin.visible = !notificationHistoryWin.visible + onEntered: notificationTooltip.tooltipVisible = true + onExited: notificationTooltip.tooltipVisible = false } } + + StyledTooltip { + id: notificationTooltip + text: "Notification History" + tooltipVisible: false + targetItem: bell + delay: 200 + } } \ No newline at end of file diff --git a/Widgets/Sidebar/Button.qml b/Widgets/Sidebar/Button.qml index c73cb53..d1e642d 100644 --- a/Widgets/Sidebar/Button.qml +++ b/Widgets/Sidebar/Button.qml @@ -20,6 +20,7 @@ Item { id: mouseArea anchors.fill: parent hoverEnabled: true + cursorShape: Qt.PointingHandCursor onClicked: { if (sidebarPopup.visible) { sidebarPopup.hidePopup(); diff --git a/Widgets/Sidebar/Config/ProfileSettings.qml b/Widgets/Sidebar/Config/ProfileSettings.qml index 91ac069..22b8484 100644 --- a/Widgets/Sidebar/Config/ProfileSettings.qml +++ b/Widgets/Sidebar/Config/ProfileSettings.qml @@ -133,6 +133,7 @@ Rectangle { } MouseArea { anchors.fill: parent + cursorShape: Qt.IBeamCursor onClicked: { profileImageInput.forceActiveFocus() } @@ -188,6 +189,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.showActiveWindowIcon = !Settings.settings.showActiveWindowIcon } @@ -242,6 +244,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.showSystemInfoInBar = !Settings.settings.showSystemInfoInBar } @@ -296,6 +299,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.showMediaInBar = !Settings.settings.showMediaInBar } @@ -445,6 +449,7 @@ Rectangle { } MouseArea { anchors.fill: parent + cursorShape: Qt.IBeamCursor onClicked: videoPathInput.forceActiveFocus() } } diff --git a/Widgets/Sidebar/Config/WallpaperSettings.qml b/Widgets/Sidebar/Config/WallpaperSettings.qml index f1aa93a..cf52903 100644 --- a/Widgets/Sidebar/Config/WallpaperSettings.qml +++ b/Widgets/Sidebar/Config/WallpaperSettings.qml @@ -79,6 +79,7 @@ Rectangle { } MouseArea { anchors.fill: parent + cursorShape: Qt.IBeamCursor onClicked: folderInput.forceActiveFocus() } } @@ -133,6 +134,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.useSWWW = !Settings.settings.useSWWW; } @@ -188,6 +190,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.randomWallpaper = !Settings.settings.randomWallpaper; } @@ -243,6 +246,7 @@ Rectangle { MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { Settings.settings.useWallpaperTheme = !Settings.settings.useWallpaperTheme; } diff --git a/Widgets/Sidebar/Config/WeatherSettings.qml b/Widgets/Sidebar/Config/WeatherSettings.qml index da433fd..ebb1ad6 100644 --- a/Widgets/Sidebar/Config/WeatherSettings.qml +++ b/Widgets/Sidebar/Config/WeatherSettings.qml @@ -5,7 +5,7 @@ import qs.Settings Rectangle { id: weatherSettingsCard Layout.fillWidth: true - Layout.preferredHeight: 180 + Layout.preferredHeight: 320 color: Theme.surface radius: 18 @@ -79,13 +79,14 @@ Rectangle { inputMethodHints: Qt.ImhNone onTextChanged: { - Settings.settings.weatherCity = text + Settings.settings.weatherCity = text; } MouseArea { anchors.fill: parent + cursorShape: Qt.IBeamCursor onClicked: { - cityInput.forceActiveFocus() + cityInput.forceActiveFocus(); } } } @@ -118,7 +119,7 @@ Rectangle { color: Theme.accentPrimary border.color: Theme.accentPrimary border.width: 2 - + Rectangle { id: thumb width: 28 @@ -129,7 +130,7 @@ Rectangle { border.width: 1 y: 2 x: Settings.settings.useFahrenheit ? customSwitch.width - width - 2 : 2 - + Text { anchors.centerIn: parent text: Settings.settings.useFahrenheit ? "\u00b0F" : "\u00b0C" @@ -138,19 +139,137 @@ Rectangle { font.bold: true color: Theme.textPrimary } - + Behavior on x { - NumberAnimation { duration: 200; easing.type: Easing.OutCubic } + NumberAnimation { + duration: 200 + easing.type: Easing.OutCubic + } } } - + MouseArea { anchors.fill: parent + cursorShape: Qt.PointingHandCursor onClicked: { - Settings.settings.useFahrenheit = !Settings.settings.useFahrenheit + Settings.settings.useFahrenheit = !Settings.settings.useFahrenheit; } } } + + } + + // Random Wallpaper Setting + RowLayout { + spacing: 8 + Layout.fillWidth: true + Layout.topMargin: 8 + + Text { + text: "Use 12 Hour Clock" + font.pixelSize: 13 + font.bold: true + color: Theme.textPrimary + } + + Item { + Layout.fillWidth: true + } + + // Custom Material 3 Switch + Rectangle { + id: use12HourClockSwitch + width: 52 + height: 32 + radius: 16 + color: Settings.settings.use12HourClock ? Theme.accentPrimary : Theme.surfaceVariant + border.color: Settings.settings.use12HourClock ? Theme.accentPrimary : Theme.outline + border.width: 2 + + Rectangle { + id: randomWallpaperThumb + width: 28 + height: 28 + radius: 14 + color: Theme.surface + border.color: Theme.outline + border.width: 1 + y: 2 + x: Settings.settings.use12HourClock ? use12HourClockSwitch.width - width - 2 : 2 + + Behavior on x { + NumberAnimation { + duration: 200 + easing.type: Easing.OutCubic + } + } + } + + MouseArea { + anchors.fill: parent + cursorShape: Qt.PointingHandCursor + onClicked: { + Settings.settings.use12HourClock = !Settings.settings.use12HourClock; + } + } + } + } + + // Reverse Day Month Setting + RowLayout { + spacing: 8 + Layout.fillWidth: true + Layout.topMargin: 8 + + Text { + text: "US Style Date" + font.pixelSize: 13 + font.bold: true + color: Theme.textPrimary + } + + Item { + Layout.fillWidth: true + } + + // Custom Material 3 Switch + Rectangle { + id: reverseDayMonthSwitch + width: 52 + height: 32 + radius: 16 + color: Settings.settings.reverseDayMonth ? Theme.accentPrimary : Theme.surfaceVariant + border.color: Settings.settings.reverseDayMonth ? Theme.accentPrimary : Theme.outline + border.width: 2 + + Rectangle { + id: reverseDayMonthThumb + width: 28 + height: 28 + radius: 14 + color: Theme.surface + border.color: Theme.outline + border.width: 1 + y: 2 + x: Settings.settings.reverseDayMonth ? reverseDayMonthSwitch.width - width - 2 : 2 + + Behavior on x { + NumberAnimation { + duration: 200 + easing.type: Easing.OutCubic + } + } + } + + MouseArea { + anchors.fill: parent + cursorShape: Qt.PointingHandCursor + onClicked: { + Settings.settings.reverseDayMonth = !Settings.settings.reverseDayMonth; + } + } + } + } } -} \ No newline at end of file +} diff --git a/Widgets/Sidebar/Panel/PanelPopup.qml b/Widgets/Sidebar/Panel/PanelPopup.qml index 1d76b0c..706270b 100644 --- a/Widgets/Sidebar/Panel/PanelPopup.qml +++ b/Widgets/Sidebar/Panel/PanelPopup.qml @@ -144,12 +144,6 @@ PanelWithOverlay { } } - MouseArea { - id: mouseArea - anchors.fill: parent - hoverEnabled: true - } - ColumnLayout { anchors.fill: parent anchors.margins: 20 @@ -235,6 +229,12 @@ PanelWithOverlay { cursorShape: Qt.PointingHandCursor onClicked: wifiPanel.showAt() } + + StyledTooltip { + text: "Wifi" + targetItem: wifiButtonArea + tooltipVisible: wifiButtonArea.containsMouse + } } // Bluetooth button @@ -264,6 +264,12 @@ PanelWithOverlay { cursorShape: Qt.PointingHandCursor onClicked: bluetoothPanel.showAt() } + + StyledTooltip { + text: "Bluetooth" + targetItem: bluetoothButtonArea + tooltipVisible: bluetoothButtonArea.containsMouse + } } } } diff --git a/Widgets/Sidebar/Panel/QuickAccess.qml b/Widgets/Sidebar/Panel/QuickAccess.qml index efe071b..93975f1 100644 --- a/Widgets/Sidebar/Panel/QuickAccess.qml +++ b/Widgets/Sidebar/Panel/QuickAccess.qml @@ -67,6 +67,7 @@ Rectangle { MouseArea { id: settingsButtonArea anchors.fill: parent + cursorShape: Qt.PointingHandCursor hoverEnabled: true onClicked: { settingsRequested() @@ -110,6 +111,7 @@ Rectangle { MouseArea { id: recorderButtonArea anchors.fill: parent + cursorShape: Qt.PointingHandCursor hoverEnabled: true onClicked: { if (isRecording) { @@ -156,6 +158,7 @@ Rectangle { MouseArea { id: wallpaperButtonArea anchors.fill: parent + cursorShape: Qt.PointingHandCursor hoverEnabled: true onClicked: { wallpaperRequested() diff --git a/Widgets/Sidebar/Panel/System.qml b/Widgets/Sidebar/Panel/System.qml index 200d035..c128996 100644 --- a/Widgets/Sidebar/Panel/System.qml +++ b/Widgets/Sidebar/Panel/System.qml @@ -7,6 +7,7 @@ import Quickshell.Io import qs.Settings import qs.Widgets import qs.Helpers +import qs.Components Rectangle { id: systemWidget @@ -129,200 +130,208 @@ Rectangle { MouseArea { id: systemButtonArea anchors.fill: parent + cursorShape: Qt.PointingHandCursor hoverEnabled: true onClicked: { - systemMenu.visible = !systemMenu.visible + systemMenu.visible = !systemMenu.visible; } } + StyledTooltip { + id: systemTooltip + text: "System" + targetItem: systemButton + tooltipVisible: systemButtonArea.containsMouse + } } } } } - // System menu popup - Rectangle { + PanelWithOverlay { id: systemMenu - width: 160 - height: 180 - color: Theme.surface - radius: 8 - border.color: Theme.outline - border.width: 1 - visible: false - z: 9999 - - // Position below system button - x: systemButton.x + systemButton.width - width + 12 - y: systemButton.y + systemButton.height + 32 + anchors.top: systemButton.bottom + anchors.right: systemButton.right + // System menu popup + Rectangle { - ColumnLayout { - anchors.fill: parent - anchors.margins: 8 - spacing: 4 + width: 160 + height: 180 + color: Theme.surface + radius: 8 + border.color: Theme.outline + border.width: 1 + visible: true + z: 9999 + anchors.top: parent.top + anchors.right: parent.right - // Lock button - Rectangle { - Layout.fillWidth: true - Layout.preferredHeight: 36 - radius: 6 - color: lockButtonArea.containsMouse ? Theme.accentPrimary : "transparent" + // Position below system button + anchors.rightMargin: 32 + anchors.topMargin: systemButton.y + systemButton.height + 48 - RowLayout { - anchors.fill: parent - anchors.margins: 12 - spacing: 8 + ColumnLayout { + anchors.fill: parent + anchors.margins: 8 + spacing: 4 - Text { - text: "lock_outline" - font.family: "Material Symbols Outlined" - font.pixelSize: 16 - color: lockButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + // Lock button + Rectangle { + Layout.fillWidth: true + Layout.preferredHeight: 36 + radius: 6 + color: lockButtonArea.containsMouse ? Theme.accentPrimary : "transparent" + + RowLayout { + anchors.fill: parent + anchors.margins: 12 + spacing: 8 + + Text { + text: "lock_outline" + font.family: "Material Symbols Outlined" + font.pixelSize: 16 + color: lockButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + } + + Text { + text: "Lock Screen" + font.family: Theme.fontFamily + font.pixelSize: 14 + color: lockButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + Layout.fillWidth: true + } } - Text { - text: "Lock Screen" - font.family: Theme.fontFamily - font.pixelSize: 14 - color: lockButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - Layout.fillWidth: true + MouseArea { + id: lockButtonArea + anchors.fill: parent + hoverEnabled: true + cursorShape: Qt.PointingHandCursor + onClicked: { + lockScreen.locked = true; + systemMenu.visible = false; + } } } - MouseArea { - id: lockButtonArea - anchors.fill: parent - hoverEnabled: true - onClicked: { - lockScreen.locked = true; - systemMenu.visible = false; + // Reboot button + Rectangle { + Layout.fillWidth: true + Layout.preferredHeight: 36 + radius: 6 + color: rebootButtonArea.containsMouse ? Theme.accentPrimary : "transparent" + + RowLayout { + anchors.fill: parent + anchors.margins: 12 + spacing: 8 + + Text { + text: "refresh" + font.family: "Material Symbols Outlined" + font.pixelSize: 16 + color: rebootButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + } + + Text { + text: "Reboot" + font.family: Theme.fontFamily + font.pixelSize: 14 + color: rebootButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + Layout.fillWidth: true + } + } + + MouseArea { + id: rebootButtonArea + anchors.fill: parent + hoverEnabled: true + cursorShape: Qt.PointingHandCursor + onClicked: { + reboot(); + systemMenu.visible = false; + } + } + } + + // Logout button + Rectangle { + Layout.fillWidth: true + Layout.preferredHeight: 36 + radius: 6 + color: logoutButtonArea.containsMouse ? Theme.accentPrimary : "transparent" + + RowLayout { + anchors.fill: parent + anchors.margins: 12 + spacing: 8 + + Text { + text: "exit_to_app" + font.family: "Material Symbols Outlined" + font.pixelSize: 16 + color: logoutButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + } + + Text { + text: "Logout" + font.pixelSize: 14 + color: logoutButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + Layout.fillWidth: true + } + } + + MouseArea { + id: logoutButtonArea + anchors.fill: parent + hoverEnabled: true + cursorShape: Qt.PointingHandCursor + onClicked: { + logout(); + systemMenu.visible = false; + } + } + } + + // Shutdown button + Rectangle { + Layout.fillWidth: true + Layout.preferredHeight: 36 + radius: 6 + color: shutdownButtonArea.containsMouse ? Theme.accentPrimary : "transparent" + + RowLayout { + anchors.fill: parent + anchors.margins: 12 + spacing: 8 + + Text { + text: "power_settings_new" + font.family: "Material Symbols Outlined" + font.pixelSize: 16 + color: shutdownButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + } + + Text { + text: "Shutdown" + font.pixelSize: 14 + color: shutdownButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary + Layout.fillWidth: true + } + } + + MouseArea { + id: shutdownButtonArea + anchors.fill: parent + hoverEnabled: true + cursorShape: Qt.PointingHandCursor + onClicked: { + shutdown(); + systemMenu.visible = false; + } } } } - - // Reboot button - Rectangle { - Layout.fillWidth: true - Layout.preferredHeight: 36 - radius: 6 - color: rebootButtonArea.containsMouse ? Theme.accentPrimary : "transparent" - - RowLayout { - anchors.fill: parent - anchors.margins: 12 - spacing: 8 - - Text { - text: "refresh" - font.family: "Material Symbols Outlined" - font.pixelSize: 16 - color: rebootButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - } - - Text { - text: "Reboot" - font.family: Theme.fontFamily - font.pixelSize: 14 - color: rebootButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - Layout.fillWidth: true - } - } - - MouseArea { - id: rebootButtonArea - anchors.fill: parent - hoverEnabled: true - onClicked: { - reboot() - systemMenu.visible = false - } - } - } - - // Logout button - Rectangle { - Layout.fillWidth: true - Layout.preferredHeight: 36 - radius: 6 - color: logoutButtonArea.containsMouse ? Theme.accentPrimary : "transparent" - - RowLayout { - anchors.fill: parent - anchors.margins: 12 - spacing: 8 - - Text { - text: "exit_to_app" - font.family: "Material Symbols Outlined" - font.pixelSize: 16 - color: logoutButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - } - - Text { - text: "Logout" - font.pixelSize: 14 - color: logoutButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - Layout.fillWidth: true - } - } - - MouseArea { - id: logoutButtonArea - anchors.fill: parent - hoverEnabled: true - onClicked: { - logout() - systemMenu.visible = false - } - } - } - - // Shutdown button - Rectangle { - Layout.fillWidth: true - Layout.preferredHeight: 36 - radius: 6 - color: shutdownButtonArea.containsMouse ? Theme.accentPrimary : "transparent" - - RowLayout { - anchors.fill: parent - anchors.margins: 12 - spacing: 8 - - Text { - text: "power_settings_new" - font.family: "Material Symbols Outlined" - font.pixelSize: 16 - color: shutdownButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - } - - Text { - text: "Shutdown" - font.pixelSize: 14 - color: shutdownButtonArea.containsMouse ? Theme.onAccent : Theme.textPrimary - Layout.fillWidth: true - } - } - - MouseArea { - id: shutdownButtonArea - anchors.fill: parent - hoverEnabled: true - onClicked: { - shutdown() - systemMenu.visible = false - } - } - } - - - } - - // Close menu when clicking outside - MouseArea { - anchors.fill: parent - enabled: systemMenu.visible - onClicked: systemMenu.visible = false - z: -1 // Put this behind other elements } } @@ -336,8 +345,8 @@ Rectangle { running: false stdout: StdioCollector { onStreamFinished: { - uptimeText = this.text.trim() - uptimeProcess.running = false + uptimeText = this.text.trim(); + uptimeProcess.running = false; } } } @@ -359,13 +368,13 @@ Rectangle { } function shutdown() { - shutdownProcess.running = true + shutdownProcess.running = true; } function reboot() { - rebootProcess.running = true + rebootProcess.running = true; } function logout() { - logoutProcess.running = true + logoutProcess.running = true; } property bool panelVisible: false @@ -373,7 +382,7 @@ Rectangle { // Trigger initial update when panel becomes visible onPanelVisibleChanged: { if (panelVisible) { - updateSystemInfo() + updateSystemInfo(); } } @@ -386,15 +395,15 @@ Rectangle { } Component.onCompleted: { - uptimeProcess.running = true + uptimeProcess.running = true; } function updateSystemInfo() { - uptimeProcess.running = true + uptimeProcess.running = true; } // Add lockscreen instance (hidden by default) LockScreen { id: lockScreen } -} \ No newline at end of file +}