diff --git a/Common/SettingsData.qml b/Common/SettingsData.qml index 06b5216f..3682ccd1 100644 --- a/Common/SettingsData.qml +++ b/Common/SettingsData.qml @@ -49,6 +49,7 @@ Singleton { property bool clockCompactMode: false property bool focusedWindowCompactMode: false property bool runningAppsCompactMode: true + property bool runningAppsCurrentWorkspace: false property string clockDateFormat: "ddd d" property string lockDateFormat: "dddd, MMMM d" property int mediaSize: 1 @@ -220,6 +221,8 @@ Singleton { !== undefined ? settings.focusedWindowCompactMode : false runningAppsCompactMode = settings.runningAppsCompactMode !== undefined ? settings.runningAppsCompactMode : true + runningAppsCurrentWorkspace = settings.runningAppsCurrentWorkspace + !== undefined ? settings.runningAppsCurrentWorkspace : false clockDateFormat = settings.clockDateFormat !== undefined ? settings.clockDateFormat : "ddd d" lockDateFormat = settings.lockDateFormat @@ -355,6 +358,7 @@ Singleton { "clockCompactMode": clockCompactMode, "focusedWindowCompactMode": focusedWindowCompactMode, "runningAppsCompactMode": runningAppsCompactMode, + "runningAppsCurrentWorkspace": runningAppsCurrentWorkspace, "clockDateFormat": clockDateFormat, "lockDateFormat": lockDateFormat, "mediaSize": mediaSize, @@ -464,6 +468,11 @@ Singleton { saveSettings() } + function setRunningAppsCurrentWorkspace(enabled) { + runningAppsCurrentWorkspace = enabled + saveSettings() + } + function setClockDateFormat(format) { clockDateFormat = format saveSettings() diff --git a/Modules/Settings/WidgetTweaksTab.qml b/Modules/Settings/WidgetTweaksTab.qml index 6cb4278e..273b83ce 100644 --- a/Modules/Settings/WidgetTweaksTab.qml +++ b/Modules/Settings/WidgetTweaksTab.qml @@ -232,6 +232,56 @@ Item { } } + StyledRect { + width: parent.width + height: runningAppsSection.implicitHeight + Theme.spacingL * 2 + radius: Theme.cornerRadius + color: Qt.rgba(Theme.surfaceVariant.r, Theme.surfaceVariant.g, + Theme.surfaceVariant.b, 0.3) + border.color: Qt.rgba(Theme.outline.r, Theme.outline.g, + Theme.outline.b, 0.2) + border.width: 1 + + Column { + id: runningAppsSection + + anchors.fill: parent + anchors.margins: Theme.spacingL + spacing: Theme.spacingM + + Row { + width: parent.width + spacing: Theme.spacingM + + DankIcon { + name: "apps" + size: Theme.iconSize + color: Theme.primary + anchors.verticalCenter: parent.verticalCenter + } + + StyledText { + text: "Running Apps Settings" + font.pixelSize: Theme.fontSizeLarge + font.weight: Font.Medium + color: Theme.surfaceText + anchors.verticalCenter: parent.verticalCenter + } + } + + DankToggle { + width: parent.width + text: "Running Apps Only In Current Workspace" + description: "Show only apps running in current workspace (currently niri only)" + checked: SettingsData.runningAppsCurrentWorkspace + onToggled: checked => { + return SettingsData.setRunningAppsCurrentWorkspace( + checked) + } + } + } + } + StyledRect { width: parent.width height: workspaceIconsSection.implicitHeight + Theme.spacingL * 2 diff --git a/Modules/TopBar/RunningApps.qml b/Modules/TopBar/RunningApps.qml index 51f2b8b8..e6af6301 100644 --- a/Modules/TopBar/RunningApps.qml +++ b/Modules/TopBar/RunningApps.qml @@ -18,7 +18,12 @@ Rectangle { readonly property real horizontalPadding: SettingsData.topBarNoBackground ? 2 : Theme.spacingS // The visual root for this window property Item windowRoot: (Window.window ? Window.window.contentItem : null) - readonly property var sortedToplevels: CompositorService.sortedToplevels + readonly property var sortedToplevels: { + if (SettingsData.runningAppsCurrentWorkspace){ + return CompositorService.filterCurrentWorkspace(CompositorService.sortedToplevels, parentScreen.name) + } + return CompositorService.sortedToplevels + } readonly property int windowCount: sortedToplevels.length readonly property int calculatedWidth: { if (windowCount === 0) diff --git a/Services/CompositorService.qml b/Services/CompositorService.qml index c36d7a37..d99fd198 100644 --- a/Services/CompositorService.qml +++ b/Services/CompositorService.qml @@ -70,6 +70,15 @@ Singleton { detectCompositor() } + // return only the toplevels on the current workspace on the given screen + function filterCurrentWorkspace(toplevels, screen){ + if (useNiriSorting) { + return NiriService.filterCurrentWorkspace(toplevels, screen) + } + //fallback to returning everything + return toplevels + } + function detectCompositor() { // Check for Hyprland first if (hyprlandSignature && hyprlandSignature.length > 0) { @@ -119,4 +128,4 @@ Singleton { } Hyprland.dispatch("exit") } -} \ No newline at end of file +} diff --git a/Services/NiriService.qml b/Services/NiriService.qml index 53c54a2f..bb5e09c5 100644 --- a/Services/NiriService.qml +++ b/Services/NiriService.qml @@ -451,11 +451,7 @@ Singleton { - function sortToplevels(toplevels) { - if (!toplevels || toplevels.length === 0 || !CompositorService.isNiri || windows.length === 0) { - return [...toplevels] - } - + function getToplevelToNiriMap(toplevels){ // Create a map to match toplevels to niri windows // We'll match by appId and title since toplevels don't have numeric IDs var toplevelToNiriMap = {} @@ -488,6 +484,15 @@ Singleton { } } } + return toplevelToNiriMap + } + + function sortToplevels(toplevels) { + if (!toplevels || toplevels.length === 0 || !CompositorService.isNiri || windows.length === 0) { + return [...toplevels] + } + + const toplevelToNiriMap = getToplevelToNiriMap(toplevels) // Sort toplevels using niri's ordering return [...toplevels].sort((a, b) => { @@ -511,4 +516,17 @@ Singleton { }) } + function filterCurrentWorkspace(toplevels, screenName){ + const toplevelToNiriMap = getToplevelToNiriMap(toplevels) + var currentWorkspaceId = null + for (var i = 0; i < NiriService.allWorkspaces.length; i++) { + var ws = NiriService.allWorkspaces[i] + if (ws.output === screenName && ws.is_active){ + currentWorkspaceId = ws.id + } + + } + return toplevels.filter((t, idx) => toplevelToNiriMap[idx] && toplevelToNiriMap[idx].niriWindow.workspace_id == currentWorkspaceId) + } + }