summaryrefslogtreecommitdiff
path: root/.config/noctalia/plugins/timer/BarWidget.qml
diff options
context:
space:
mode:
Diffstat (limited to '.config/noctalia/plugins/timer/BarWidget.qml')
-rw-r--r--.config/noctalia/plugins/timer/BarWidget.qml179
1 files changed, 179 insertions, 0 deletions
diff --git a/.config/noctalia/plugins/timer/BarWidget.qml b/.config/noctalia/plugins/timer/BarWidget.qml
new file mode 100644
index 0000000..81d2cb9
--- /dev/null
+++ b/.config/noctalia/plugins/timer/BarWidget.qml
@@ -0,0 +1,179 @@
+import QtQuick
+import QtQuick.Layouts
+import Quickshell
+import qs.Commons
+import qs.Widgets
+import qs.Services.UI
+import qs.Services.System
+
+Item {
+ id: root
+
+ property var pluginApi: null
+ property ShellScreen screen
+ property string widgetId: ""
+ property string section: ""
+ property int sectionWidgetIndex: -1
+ property int sectionWidgetsCount: 0
+
+ readonly property bool pillDirection: BarService.getPillDirection(root)
+
+ readonly property var mainInstance: pluginApi?.mainInstance
+ readonly property bool isActive: mainInstance && (mainInstance.cdRunning || mainInstance.swRunning || mainInstance.swElapsedSeconds > 0 || mainInstance.cdRemainingSeconds > 0 || mainInstance.cdSoundPlaying)
+
+ property var cfg: pluginApi?.pluginSettings || ({})
+ property var defaults: pluginApi?.manifest?.metadata?.defaultSettings || ({})
+
+ readonly property string iconColorKey: cfg.iconColor ?? defaults.iconColor ?? "none"
+ readonly property color iconColor: Color.resolveColorKey(iconColorKey)
+
+ readonly property string textColorKey: cfg.textColor ?? defaults.textColor ?? "none"
+ readonly property color textColor: Color.resolveColorKey(textColorKey)
+
+ // Bar positioning properties
+ readonly property string screenName: screen ? screen.name : ""
+ readonly property string barPosition: Settings.getBarPositionForScreen(screenName)
+ readonly property bool isVertical: barPosition === "left" || barPosition === "right"
+ readonly property real barHeight: Style.getBarHeightForScreen(screenName)
+ readonly property real capsuleHeight: Style.getCapsuleHeightForScreen(screenName)
+ readonly property real barFontSize: Style.getBarFontSizeForScreen(screenName)
+
+ readonly property real contentWidth: {
+ if (isVertical) return root.capsuleHeight
+ if (isActive) return contentRow.implicitWidth + Style.marginM * 2
+ return root.capsuleHeight
+ }
+ readonly property real contentHeight: root.capsuleHeight
+
+ implicitWidth: contentWidth
+ implicitHeight: contentHeight
+
+ function formatTime(seconds) {
+ const hours = Math.floor(seconds / 3600);
+ const minutes = Math.floor((seconds % 3600) / 60);
+ const secs = seconds % 60;
+
+ if (hours > 0) {
+ return `${hours.toString().padStart(2, '0')}:${minutes.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;
+ }
+ return `${minutes.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;
+ }
+
+ Rectangle {
+ id: visualCapsule
+ x: Style.pixelAlignCenter(parent.width, width)
+ y: Style.pixelAlignCenter(parent.height, height)
+ width: root.contentWidth
+ height: root.contentHeight
+ color: mouseArea.containsMouse ? Color.mHover : Style.capsuleColor
+ radius: Style.radiusL
+ border.color: Style.capsuleBorderColor
+ border.width: Style.capsuleBorderWidth
+
+ RowLayout {
+ id: contentRow
+ anchors.centerIn: parent
+ spacing: Style.marginS
+ layoutDirection: pillDirection ? Qt.LeftToRight : Qt.RightToLeft
+
+ NIcon {
+ icon: {
+ if (mainInstance && mainInstance.timerSoundPlaying) return "bell-ringing"
+ if (mainInstance && mainInstance.timerStopwatchMode) return "stopwatch"
+ return "hourglass"
+ }
+ applyUiScale: false
+ color: mouseArea.containsMouse ? Color.mOnHover : root.iconColor
+ }
+
+ NText {
+ visible: !isVertical && mainInstance && (mainInstance.cdRunning || mainInstance.swRunning || mainInstance.swElapsedSeconds > 0 || mainInstance.cdRemainingSeconds > 0 || mainInstance.cdSoundPlaying)
+ family: Settings.data.ui.fontFixed
+ pointSize: root.barFontSize
+ font.weight: Style.fontWeightBold
+ color: mouseArea.containsMouse ? Color.mOnHover : root.textColor
+ text: {
+ if (!mainInstance) return ""
+ if (mainInstance.timerStopwatchMode) {
+ return formatTime(mainInstance.timerElapsedSeconds)
+ }
+ return formatTime(mainInstance.timerRemainingSeconds)
+ }
+ }
+ }
+ }
+
+ NPopupContextMenu {
+ id: contextMenu
+
+ model: {
+ var items = [];
+
+ if (mainInstance) {
+ // Pause / Resume & Reset
+ const modeActive = mainInstance.timerStopwatchMode
+ ? (mainInstance.swRunning || mainInstance.swElapsedSeconds > 0)
+ : (mainInstance.cdRunning || mainInstance.cdRemainingSeconds > 0 || mainInstance.cdSoundPlaying);
+ if (modeActive) {
+ items.push({
+ "label": mainInstance.timerRunning ? pluginApi.tr("panel.pause") : pluginApi.tr("panel.resume"),
+ "action": "toggle",
+ "icon": mainInstance.timerRunning ? "media-pause" : "media-play"
+ });
+
+ items.push({
+ "label": pluginApi.tr("panel.reset"),
+ "action": "reset",
+ "icon": "refresh"
+ });
+ }
+ }
+
+ // Settings
+ items.push({
+ "label": pluginApi.tr("panel.settings"),
+ "action": "widget-settings",
+ "icon": "settings"
+ });
+
+ return items;
+ }
+
+ onTriggered: action => {
+ contextMenu.close();
+ PanelService.closeContextMenu(screen);
+
+ if (action === "widget-settings") {
+ BarService.openPluginSettings(screen, pluginApi.manifest);
+ } else if (mainInstance) {
+ if (action === "toggle") {
+ if (mainInstance.timerRunning) {
+ mainInstance.timerPause();
+ } else {
+ mainInstance.timerStart();
+ }
+ } else if (action === "reset") {
+ mainInstance.timerReset();
+ }
+ }
+ }
+ }
+
+ MouseArea {
+ id: mouseArea
+ anchors.fill: parent
+ hoverEnabled: true
+ cursorShape: Qt.PointingHandCursor
+ acceptedButtons: Qt.LeftButton | Qt.RightButton
+
+ onClicked: (mouse) => {
+ if (mouse.button === Qt.LeftButton) {
+ if (pluginApi) {
+ pluginApi.openPanel(root.screen, root)
+ }
+ } else if (mouse.button === Qt.RightButton) {
+ PanelService.showContextMenu(contextMenu, root, screen);
+ }
+ }
+ }
+}