suckless-patches / dwm-r1507-focusatom.diff

# HG changeset patch
# Parent 09f7bb221900182a38bacbcd8addf8a8b86c9bae
# Date 1294703012 -3600
# User Julien Jehannet <julien@smaf.org>

diff --git a/dwm.c b/dwm.c
--- a/dwm.c
+++ b/dwm.c
@@ -184,10 +184,11 @@ static void drawbars(void);
 static void drawsquare(Bool filled, Bool empty, Bool invert, unsigned long col[ColLast]);
 static void drawtext(const char *text, unsigned long col[ColLast], Bool invert);
 static void enternotify(XEvent *e);
 static void expose(XEvent *e);
 static void focus(Client *c);
+static void focusatomchange(void);
 static void focusin(XEvent *e);
 static void focusmon(const Arg *arg);
 static void focusstack(const Arg *arg);
 static unsigned long getcolor(const char *colstr);
 static Bool getrootptr(int *x, int *y);
@@ -279,10 +280,11 @@ static void (*handler[LASTEvent]) (XEven
 	[MotionNotify] = motionnotify,
 	[PropertyNotify] = propertynotify,
 	[UnmapNotify] = unmapnotify
 };
 static Atom wmatom[WMLast], netatom[NetLast];
+static Atom focusatom;
 static Bool running = True;
 static Cursor cursor[CurLast];
 static Display *dpy;
 static DC dc;
 static Monitor *mons = NULL, *selmon = NULL;
@@ -884,10 +886,37 @@ focus(Client *c) {
 	selmon->sel = c;
 	drawbars();
 }
 
 void
+focusatomchange() {
+	int format, status;
+	unsigned long n, extra;
+	unsigned char *p = NULL;
+	Atom real;
+	Client *c;
+	Monitor *m;
+	Window *w;
+
+	status = XGetWindowProperty(dpy, root, focusatom, 0L, 32L, True, XA_CARDINAL, &real, &format, &n, &extra, &p);
+	if(status!=Success || n==0) return;
+	if((w = (Window*)p) && (m = wintomon(*w)) && m != selmon) {
+		unfocus(selmon->sel, True);
+		selmon = m;
+	}
+	if((c = wintoclient(*w))) {
+		if (!ISVISIBLE(c)) {
+			c->mon->seltags ^= 1; /* toggle sel tagset */
+			c->mon->tagset[c->mon->seltags] = c->tags & TAGMASK;
+		}
+		focus(c);
+		arrange(c->mon);
+	}
+	XFree(p);
+}
+
+void
 focusin(XEvent *e) { /* there are some broken focus acquiring clients */
 	XFocusChangeEvent *ev = &e->xfocus;
 
 	if(selmon->sel && ev->window != selmon->sel->win)
 		setfocus(selmon->sel);
@@ -1320,10 +1349,12 @@ propertynotify(XEvent *e) {
 	Window trans;
 	XPropertyEvent *ev = &e->xproperty;
 
 	if((ev->window == root) && (ev->atom == XA_WM_NAME))
 		updatestatus();
+	else if((ev->window == root) && (ev->atom == focusatom))
+		focusatomchange();
 	else if(ev->state == PropertyDelete)
 		return; /* ignore */
 	else if((c = wintoclient(ev->window))) {
 		switch(ev->atom) {
 		default: break;
@@ -1641,10 +1672,11 @@ setup(void) {
 	netatom[NetWMState] = XInternAtom(dpy, "_NET_WM_STATE", False);
 	netatom[NetWMFullscreen] = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False);
 	netatom[NetWMWindowType] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE", False);
 	netatom[NetWMWindowTypeDialog] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE_DIALOG", False);
 	netatom[NetClientList] = XInternAtom(dpy, "_NET_CLIENT_LIST", False);
+	focusatom = XInternAtom(dpy, "_DWM_FOCUS", False);
 	/* init cursors */
 	cursor[CurNormal] = XCreateFontCursor(dpy, XC_left_ptr);
 	cursor[CurResize] = XCreateFontCursor(dpy, XC_sizing);
 	cursor[CurMove] = XCreateFontCursor(dpy, XC_fleur);
 	/* init appearance */
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.