From ec26403a06404c8be6f8cb48ecf4bd56d8d942a8 Mon Sep 17 00:00:00 2001 From: Benedikt Heine Date: Thu, 6 Sep 2018 08:40:28 +0200 Subject: [PATCH] Let important notifications seep into full display queue When the display queue had is full and a new notification would come in, new notification wouldn't get shown until a currently displayed notification would timeout. Even if the notification would have been shown on top of the displayed queue. So e.g. if the displayed queue would have been filled with "normal" urgency notifications, an incoming "urgent" notification would have been delayed. To let those more important notifications through, the tail of displayed and head of waiting are swapped on every update if necessary. --- CHANGELOG.md | 2 ++ src/queues.c | 36 +++++++++++++++++++++++++++++++++++- 2 files changed, 37 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9b94516..71f89c1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,8 @@ ### Added - `fullscreen` rule to hide notifications when a fullscreen window is active +- When new notifications arrive, but display is full, important notifications don't + have to wait for a timeout in a displayed notification (#541) ## 1.3.2 - 2018-05-06 diff --git a/src/queues.c b/src/queues.c index 017a4f4..600a3e7 100644 --- a/src/queues.c +++ b/src/queues.c @@ -258,7 +258,7 @@ void queues_history_pop(void) n->redisplayed = true; n->start = 0; n->timeout = settings.sticky_history ? 0 : n->timeout; - g_queue_push_head(waiting, n); + g_queue_insert_sorted(waiting, n, notification_cmp_data, NULL); } /* see queues.h */ @@ -381,6 +381,40 @@ void queues_update(bool fullscreen) iter = nextiter; } + + /* If displayed is actually full, let the more important notifications + * from waiting seep into displayed. + */ + if (settings.sort) { + GList *i_waiting, *i_displayed; + + while ( (i_waiting = g_queue_peek_head_link(waiting)) + && (i_displayed = g_queue_peek_tail_link(displayed))) { + + while ( fullscreen + && i_waiting + && i_waiting->data + && ((notification*) i_waiting->data)->fullscreen != FS_SHOW) { + i_waiting = i_waiting->prev; + } + + if (i_waiting && notification_cmp(i_displayed->data, i_waiting->data) > 0) { + notification *towait = i_displayed->data; + notification *todisp = i_waiting->data; + + g_queue_delete_link(displayed, i_displayed); + g_queue_delete_link(waiting, i_waiting); + + todisp->start = time_monotonic_now(); + notification_run_script(todisp); + + g_queue_insert_sorted(displayed, todisp, notification_cmp_data, NULL); + g_queue_insert_sorted(waiting, towait, notification_cmp_data, NULL); + } else { + break; + } + } + } } /* see queues.h */