From 67fc80803d09529d0edff02c5079a71387853a10 Mon Sep 17 00:00:00 2001 From: bakkeby Date: Sun, 31 Oct 2021 13:45:18 +0100 Subject: [PATCH] onlyquitonempty: refactoring patch to only take client windows into consideration when deciding whether or not to allow dwm to quit As per the original patch https://dwm.suckless.org/patches/onlyquitonempty/ it used XQueryTree to get a count of the number of windows open to determine whether to allow the window manager to exit. This meant that the empty quit count variable would have to take into account background windows such as the bar, which has side effects like plugging in another monitor could mean that you would not longer be allowed to quit dwm until the monitor is removed. Likewise a systray and each systray icon would give a +1 to the number of windows in the system. This is unintuitive to understand and convoluted to explain, hence the refactoring here to use the more sane approach of only counting the number of client windows that the window manager manages. This is an old idea which was intentionally not added to dwm-flexipatch due to the aim of staying true to the original patch (as in if you were to patch that manually you would get the same experience as you had when trying the patch out in dwm-flexipatch). This is ref. discussion in #194. --- config.def.h | 2 +- dwm.c | 32 ++++++++++++++------------------ 2 files changed, 15 insertions(+), 19 deletions(-) diff --git a/config.def.h b/config.def.h index 8e68937..aa79412 100644 --- a/config.def.h +++ b/config.def.h @@ -100,7 +100,7 @@ static int fakefsindicatortype = INDICATOR_PLUS; static int floatfakefsindicatortype = INDICATOR_PLUS_AND_LARGER_SQUARE; #endif // FAKEFULLSCREEN_CLIENT_PATCH #if ONLYQUITONEMPTY_PATCH -static const int quit_empty_window_count = 2; /* only allow dwm to quit if no windows are open, value here represents number of deamons */ +static const int quit_empty_window_count = 0; /* only allow dwm to quit if no (<= count) windows are open */ #endif // ONLYQUITONEMPTY_PATCH #if BAR_EXTRASTATUS_PATCH static const char statussep = ';'; /* separator between status bars */ diff --git a/dwm.c b/dwm.c index 2bd28e6..5d53587 100644 --- a/dwm.c +++ b/dwm.c @@ -2744,27 +2744,23 @@ quit(const Arg *arg) #if COOL_AUTOSTART_PATCH size_t i; #endif // COOL_AUTOSTART_PATCH - #if ONLYQUITONEMPTY_PATCH - unsigned int n; - Window *junk = malloc(1); - - XQueryTree(dpy, root, junk, junk, &junk, &n); - - if (n <= quit_empty_window_count) - { - #if RESTARTSIG_PATCH - restart = arg->i; - #endif // RESTARTSIG_PATCH - running = 0; - } - else - printf("[dwm] not exiting (n=%d)\n", n); - - free(junk); - #else // !ONLYQUITONEMPTY_PATCH #if RESTARTSIG_PATCH restart = arg->i; #endif // RESTARTSIG_PATCH + #if ONLYQUITONEMPTY_PATCH + Monitor *m; + Client *c; + unsigned int n = 0; + + for (m = mons; m; m = m->next) + for (c = m->clients; c; c = c->next, n++); + + if (restart || n <= quit_empty_window_count) + running = 0; + else + fprintf(stderr, "[dwm] not exiting (n=%d)\n", n); + + #else // !ONLYQUITONEMPTY_PATCH running = 0; #endif // ONLYQUITONEMPTY_PATCH