From 8188ced955c376eeeb9898b965a2330388cd7172 Mon Sep 17 00:00:00 2001 From: Thomas Kroll <99196436+tkroll-ionos@users.noreply.github.com> Date: Thu, 23 Jul 2026 14:32:14 +0200 Subject: [PATCH] Add option to ignore app-requested notification timeout (#2909) * Add option to ignore app-requested notification timeout Notifications may include an expireTimeout hint that currently takes precedence over the configured Low/Normal/Critical durations, so popups can disappear earlier (or later) than expected with no interaction involved. Add notificationIgnoreAppTimeout (default off, matching the notification spec) to let users force their own durations regardless of what the app requests. * Update settings search index for new timeout override toggle --- quickshell/Common/SettingsData.qml | 1 + quickshell/Common/settings/SettingsSpec.js | 1 + .../Modules/Settings/NotificationsTab.qml | 9 +++++ quickshell/Services/NotificationService.qml | 2 +- .../translations/settings_search_index.json | 38 ++++++++++++++++++- 5 files changed, 49 insertions(+), 2 deletions(-) diff --git a/quickshell/Common/SettingsData.qml b/quickshell/Common/SettingsData.qml index 5cf6a16ec..7f2c6181a 100644 --- a/quickshell/Common/SettingsData.qml +++ b/quickshell/Common/SettingsData.qml @@ -934,6 +934,7 @@ Singleton { property int notificationTimeoutLow: 5000 property int notificationTimeoutNormal: 5000 property int notificationTimeoutCritical: 0 + property bool notificationIgnoreAppTimeout: false property bool notificationCompactMode: false property bool notificationShowTimeoutBar: false property bool notificationDedupeEnabled: true diff --git a/quickshell/Common/settings/SettingsSpec.js b/quickshell/Common/settings/SettingsSpec.js index dd4f14e1a..d5393f807 100644 --- a/quickshell/Common/settings/SettingsSpec.js +++ b/quickshell/Common/settings/SettingsSpec.js @@ -495,6 +495,7 @@ var SPEC = { notificationTimeoutLow: { def: 5000 }, notificationTimeoutNormal: { def: 5000 }, notificationTimeoutCritical: { def: 0 }, + notificationIgnoreAppTimeout: { def: false }, notificationCompactMode: { def: false }, notificationShowTimeoutBar: { def: false }, notificationDedupeEnabled: { def: true }, diff --git a/quickshell/Modules/Settings/NotificationsTab.qml b/quickshell/Modules/Settings/NotificationsTab.qml index 7b7c72c52..8c93482fa 100644 --- a/quickshell/Modules/Settings/NotificationsTab.qml +++ b/quickshell/Modules/Settings/NotificationsTab.qml @@ -844,6 +844,15 @@ Item { } } } + + SettingsToggleRow { + settingKey: "notificationIgnoreAppTimeout" + tags: ["notification", "timeout", "expire", "app", "override", "duration"] + text: I18n.tr("Ignore App-Requested Timeout") + description: I18n.tr("Always use the durations above, even if an app requests a shorter or longer one") + checked: SettingsData.notificationIgnoreAppTimeout + onToggled: checked => SettingsData.set("notificationIgnoreAppTimeout", checked) + } } SettingsCard { diff --git a/quickshell/Services/NotificationService.qml b/quickshell/Services/NotificationService.qml index d5206cb32..3f28f9bd1 100644 --- a/quickshell/Services/NotificationService.qml +++ b/quickshell/Services/NotificationService.qml @@ -777,7 +777,7 @@ Singleton { return 5000; // expireTimeout is in milliseconds; -1 defers to our settings. const appTimeout = wrapper.notification.expireTimeout; - if (appTimeout >= 0) + if (appTimeout >= 0 && !SettingsData.notificationIgnoreAppTimeout) return Math.round(appTimeout); switch (wrapper.urgency) { case NotificationUrgency.Low: diff --git a/quickshell/translations/settings_search_index.json b/quickshell/translations/settings_search_index.json index 583435dbd..f381e5e2b 100644 --- a/quickshell/translations/settings_search_index.json +++ b/quickshell/translations/settings_search_index.json @@ -6122,6 +6122,34 @@ "icon": "history", "description": "Save dismissed notifications to history" }, + { + "section": "notificationIgnoreAppTimeout", + "label": "Ignore App-Requested Timeout", + "tabIndex": 17, + "category": "Notifications", + "keywords": [ + "above", + "alerts", + "always", + "app", + "duration", + "durations", + "even", + "expire", + "ignore", + "longer", + "messages", + "notification", + "notifications", + "override", + "requested", + "requests", + "shorter", + "timeout", + "toast" + ], + "description": "Always use the durations above, even if an app requests a shorter or longer one" + }, { "section": "lockScreenNotifications", "label": "Lock Screen", @@ -6515,18 +6543,26 @@ "tabIndex": 17, "category": "Notifications", "keywords": [ + "above", "alerts", + "always", "duration", + "durations", + "even", + "longer", "low", "messages", "notification", "notifications", "priority", + "requests", + "shorter", "timeout", "timeouts", "toast" ], - "icon": "timer" + "icon": "timer", + "description": "Always use the durations above, even if an app requests a shorter or longer one" }, { "section": "osdAlwaysShowValue",