JasonWoof Got questions, comments, patches, etc.? Contact Jason Woofenden
applied another minor change to the README
[dwm.git] / dwm.c
diff --git a/dwm.c b/dwm.c
index 0a1b30e..d088327 100644 (file)
--- a/dwm.c
+++ b/dwm.c
@@ -58,7 +58,7 @@
 enum { CurNormal, CurResize, CurMove, CurLast };        /* cursor */
 enum { ColBorder, ColFG, ColBG, ColLast };              /* color */
 enum { NetSupported, NetWMName, NetWMState,
-       NetWMFullscreen, NetLast };                      /* EWMH atoms */
+       NetWMFullscreen, NetActiveWindow, NetLast };     /* EWMH atoms */
 enum { WMProtocols, WMDelete, WMState, WMTakeFocus, WMLast }; /* default atoms */
 enum { ClkTagBar, ClkLtSymbol, ClkStatusText, ClkWinTitle,
        ClkClientWin, ClkRootWin, ClkLast };             /* clicks */
@@ -88,7 +88,7 @@ struct Client {
        int basew, baseh, incw, inch, maxw, maxh, minw, minh;
        int bw, oldbw;
        unsigned int tags;
-       Bool isfixed, isfloating, isurgent, neverfocus, oldstate;
+       Bool isfixed, isfloating, isurgent, neverfocus, oldstate, isfullscreen;
        Client *next;
        Client *snext;
        Monitor *mon;
@@ -198,8 +198,9 @@ static void maprequest(XEvent *e);
 static void monocle(Monitor *m);
 static void movemouse(const Arg *arg);
 static Client *nexttiled(Client *c);
-static Monitor *ptrtomon(int x, int y);
+static void pop(Client *);
 static void propertynotify(XEvent *e);
+static Monitor *ptrtomon(int x, int y);
 static void quit(const Arg *arg);
 static void resize(Client *c, int x, int y, int w, int h, Bool interact);
 static void resizeclient(Client *c, int x, int y, int w, int h);
@@ -521,6 +522,48 @@ clearurgent(Client *c) {
 }
 
 void
+clientmessage(XEvent *e) {
+       XClientMessageEvent *cme = &e->xclient;
+       Client *c = wintoclient(cme->window);
+
+       if(!c)
+               return;
+       if(cme->message_type == netatom[NetWMState] && cme->data.l[1] == netatom[NetWMFullscreen]) {
+               if(cme->data.l[0]) {
+                       XChangeProperty(dpy, cme->window, netatom[NetWMState], XA_ATOM, 32,
+                                       PropModeReplace, (unsigned char*)&netatom[NetWMFullscreen], 1);
+                       c->isfullscreen = True;
+                       c->oldstate = c->isfloating;
+                       c->oldbw = c->bw;
+                       c->bw = 0;
+                       c->isfloating = True;
+                       resizeclient(c, c->mon->mx, c->mon->my, c->mon->mw, c->mon->mh);
+                       XRaiseWindow(dpy, c->win);
+               }
+               else {
+                       XChangeProperty(dpy, cme->window, netatom[NetWMState], XA_ATOM, 32,
+                                       PropModeReplace, (unsigned char*)0, 0);
+                       c->isfullscreen = False;
+                       c->isfloating = c->oldstate;
+                       c->bw = c->oldbw;
+                       c->x = c->oldx;
+                       c->y = c->oldy;
+                       c->w = c->oldw;
+                       c->h = c->oldh;
+                       resizeclient(c, c->x, c->y, c->w, c->h);
+                       arrange(c->mon);
+               }
+       }
+       else if(cme->message_type == netatom[NetActiveWindow]) {
+               if(!ISVISIBLE(c)) {
+                       c->mon->seltags ^= 1;                                   
+                       c->mon->tagset[c->mon->seltags] = c->tags;   
+               }
+               pop(c);
+       }
+}
+
+void
 configure(Client *c) {
        XConfigureEvent ce;
 
@@ -1212,14 +1255,12 @@ nexttiled(Client *c) {
        return c;
 }
 
-Monitor *
-ptrtomon(int x, int y) {
-       Monitor *m;
-
-       for(m = mons; m; m = m->next)
-               if(INRECT(x, y, m->wx, m->wy, m->ww, m->wh))
-                       return m;
-       return selmon;
+void
+pop(Client *c) {
+       detach(c);
+       attach(c);
+       focus(c);
+       arrange(c->mon);
 }
 
 void
@@ -1256,39 +1297,15 @@ propertynotify(XEvent *e) {
        }
 }
 
-void
-clientmessage(XEvent *e) {
-       XClientMessageEvent *cme = &e->xclient;
-       Client *c;
+Monitor *
+ptrtomon(int x, int y) {
+       Monitor *m;
 
-       if((c = wintoclient(cme->window))
-       && (cme->message_type == netatom[NetWMState] && cme->data.l[1] == netatom[NetWMFullscreen]))
-       {
-               if(cme->data.l[0]) {
-                       XChangeProperty(dpy, cme->window, netatom[NetWMState], XA_ATOM, 32,
-                                       PropModeReplace, (unsigned char*)&netatom[NetWMFullscreen], 1);
-                       c->oldstate = c->isfloating;
-                       c->oldbw = c->bw;
-                       c->bw = 0;
-                       c->isfloating = True;
-                       resizeclient(c, c->mon->mx, c->mon->my, c->mon->mw, c->mon->mh);
-                       XRaiseWindow(dpy, c->win);
-               }
-               else {
-                       XChangeProperty(dpy, cme->window, netatom[NetWMState], XA_ATOM, 32,
-                                       PropModeReplace, (unsigned char*)0, 0);
-                       c->isfloating = c->oldstate;
-                       c->bw = c->oldbw;
-                       c->x = c->oldx;
-                       c->y = c->oldy;
-                       c->w = c->oldw;
-                       c->h = c->oldh;
-                       resizeclient(c, c->x, c->y, c->w, c->h);
-                       arrange(c->mon);
-               }
-       }
+       for(m = mons; m; m = m->next)
+               if(INRECT(x, y, m->wx, m->wy, m->ww, m->wh))
+                       return m;
+       return selmon;
 }
-
 void
 quit(const Arg *arg) {
        running = False;
@@ -1460,7 +1477,7 @@ sendevent(Client *c, Atom proto) {
                        exists = protocols[n] == proto;
                XFree(protocols);
        }
-       if (exists) {
+       if(exists) {
                ev.type = ClientMessage;
                ev.xclient.window = c->win;
                ev.xclient.message_type = wmatom[WMProtocols];
@@ -1474,7 +1491,7 @@ sendevent(Client *c, Atom proto) {
 
 void
 setfocus(Client *c) {
-       if (!c->neverfocus)
+       if(!c->neverfocus)
                XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime);
        sendevent(c, wmatom[WMTakeFocus]);
 }
@@ -1525,6 +1542,7 @@ setup(void) {
        wmatom[WMProtocols] = XInternAtom(dpy, "WM_PROTOCOLS", False);
        wmatom[WMDelete] = XInternAtom(dpy, "WM_DELETE_WINDOW", False);
        wmatom[WMState] = XInternAtom(dpy, "WM_STATE", False);
+        netatom[NetActiveWindow] = XInternAtom(dpy, "_NET_ACTIVE_WINDOW", False);
        wmatom[WMTakeFocus] = XInternAtom(dpy, "WM_TAKE_FOCUS", False);
        netatom[NetSupported] = XInternAtom(dpy, "_NET_SUPPORTED", False);
        netatom[NetWMName] = XInternAtom(dpy, "_NET_WM_NAME", False);
@@ -1568,7 +1586,7 @@ showhide(Client *c) {
                return;
        if(ISVISIBLE(c)) { /* show clients top down */
                XMoveWindow(dpy, c->win, c->x, c->y);
-               if(!c->mon->lt[c->mon->sellt]->arrange || c->isfloating)
+               if((!c->mon->lt[c->mon->sellt]->arrange || c->isfloating) && !c->isfullscreen)
                        resize(c, c->x, c->y, c->w, c->h, False);
                showhide(c->snext);
        }
@@ -1942,8 +1960,10 @@ updatewmhints(Client *c) {
                }
                else
                        c->isurgent = (wmh->flags & XUrgencyHint) ? True : False;
-               if (wmh->flags & InputHint) c->neverfocus = !wmh->input;
-               else                        c->neverfocus = False;
+               if(wmh->flags & InputHint)
+                       c->neverfocus = !wmh->input;
+               else
+                       c->neverfocus = False;
                XFree(wmh);
        }
 }
@@ -2030,10 +2050,7 @@ zoom(const Arg *arg) {
        if(c == nexttiled(selmon->clients))
                if(!c || !(c = nexttiled(c->next)))
                        return;
-       detach(c);
-       attach(c);
-       focus(c);
-       arrange(c->mon);
+       pop(c);
 }
 
 int