From dbdf8d701eaaadb04fd6cfb85ceb6f1f5595db37 Mon Sep 17 00:00:00 2001 From: "Michael D. Lowis" Date: Mon, 10 Jun 2019 15:04:48 -0400 Subject: [PATCH] switched to doubly linked list and tweaked redraw code to redraw on any property change. Also, added retile logic for when a window is removed --- src/anvil.c | 77 ++++++++++++++++++++++++++++------------------------- 1 file changed, 41 insertions(+), 36 deletions(-) diff --git a/src/anvil.c b/src/anvil.c index d399df0..8e27734 100644 --- a/src/anvil.c +++ b/src/anvil.c @@ -91,6 +91,14 @@ void client_add(XConf* x, Window win) { biggy->h /= 2; c->y = biggy->y + biggy->h; client_config(x, biggy, biggy->x, biggy->y, biggy->w, biggy->h); + + /* add the new client to the list after the biggest */ + c->next = biggy->next; + c->prev = biggy; + biggy->next = c; + if (c->next) c->next->prev = c; + } else { + Clients = c; } client_config(x, c, c->x, c->y, c->w, c->h); client_raise(x, c); @@ -98,27 +106,22 @@ void client_add(XConf* x, Window win) { XSync(x->display, False); XUngrabServer(x->display); - c->next = Clients; - Clients = c; } -Client* client_del(XConf* x, Client* curr, Client* c) { - if (!curr) { - return NULL; - } else if (curr == c) { - Client* next = c->next; - XGrabServer(x->display); - XftDrawDestroy(c->xft); - XDestroyWindow(x->display, c->frame); - xfree(c->name); - free(c); - XSync(x->display, False); - XUngrabServer(x->display); - return next; - } else { - curr->next = client_del(x, curr->next, c); - return curr; - } +void client_del(XConf* x, Client* c) { + /* first remove it from the list */ + if (c->prev) c->prev->next = c->next; + if (c->next) c->next->prev = c->prev; + if (Clients == c) Clients = c->next; + + /* clean it up now */ + XGrabServer(x->display); + XftDrawDestroy(c->xft); + XDestroyWindow(x->display, c->frame); + xfree(c->name); + free(c); + XSync(x->display, False); + XUngrabServer(x->display); } Client* client_find(Window win) { @@ -130,6 +133,7 @@ Client* client_find(Window win) { } void client_redraw(XConf* x, Client* c) { + puts("redraw"); XftColor clr; xftcolor(x, &clr, -1); XftDrawStringUtf8(c->xft, &clr, x->font, 0, x->font->ascent, (const FcChar8*)c->name, strlen(c->name)); @@ -145,7 +149,13 @@ void client_redraw(XConf* x, Client* c) { static void xbtnpress(XConf* x, XEvent* e) { printf("btn\n"); /* - * + * B1 Grow window a little + * B1 Drag: Resize vertically or move to column + * B2: Stack windows with titlebars visible but only one window expanded + * B3: Maximize in column + * B1+B2: Kill window + * Shift+B1: Move one column to the left + * Shift+B1: Move one column to the right */ } @@ -189,21 +199,17 @@ static void xdestroynotify(XConf* x, XEvent* e) { /* This is where we cleanup windows we care about. destroy them and their frames. */ Client* c = client_find(e->xdestroywindow.window); if (c) { - //int y = c->y, h = c->h; - Client* next = c->next; - printf("c: %p next: %p\n", (void*)c, (void*)next); -// if (next) { -// next->y = y, next->h += h; -// client_config(x, next, next->x, next->y, next->w, next->h); -// client_raise(x, next); -// } - - for (Client* n = Clients; n; n = n->next) { - printf("%p ", (void*)n); + int y = c->y, h = c->h; + if (c->prev) { + c->prev->h += h; + client_config(x, c->prev, c->prev->x, c->prev->y, c->prev->w, c->prev->h); + client_raise(x, c->prev); + } else if (c->next) { + c->next->y = y, c->next->h += h; + client_config(x, c->next, c->next->x, c->next->y, c->next->w, c->next->h); + client_raise(x, c->next); } - puts(""); - - Clients = client_del(x, Clients, c); + client_del(x, c); } } @@ -212,12 +218,11 @@ static void xclientmsg(XConf* x, XEvent* e) { } static void xpropnotify(XConf* x, XEvent* e) { - printf("prop\n"); /* We only care about updating the window titles here for now */ Client* c = client_find(e->xproperty.window); - if (c && e->xproperty.atom == XA_WM_NAME) { + if (c) { c->name = xfree(c->name); XFetchName(x->display, c->win, &c->name); client_redraw(x, c); -- 2.51.0