dwm.c
changeset 1096 a813daebec92
parent 1095 a977bbe06b06
child 1097 7241740da6ed
equal deleted inserted replaced
1095:a977bbe06b06 1096:a813daebec92
   128 };
   128 };
   129 
   129 
   130 
   130 
   131 /* function declarations */
   131 /* function declarations */
   132 void applyrules(Client *c);
   132 void applyrules(Client *c);
   133 void arrange(void);
   133 void arrange(Monitor *m);
   134 void attach(Client *c);
   134 void attach(Client *c);
   135 void attachstack(Client *c);
   135 void attachstack(Client *c);
   136 void ban(Client *c);
   136 void ban(Client *c);
   137 void buttonpress(XEvent *e);
   137 void buttonpress(XEvent *e);
   138 void checkotherwm(void);
   138 void checkotherwm(void);
   297 	if (!matched_monitor)
   297 	if (!matched_monitor)
   298 		c->monitor = monitorat();
   298 		c->monitor = monitorat();
   299 }
   299 }
   300 
   300 
   301 void
   301 void
   302 arrange(void) {
   302 arrange(Monitor *m) {
       
   303 	unsigned int i;
   303 	Client *c;
   304 	Client *c;
   304 
   305 
   305 	for(c = clients; c; c = c->next)
   306 	for(c = clients; c; c = c->next)
   306 		if(isvisible(c, c->monitor))
   307 		if(isvisible(c, c->monitor))
   307 			unban(c);
   308 			unban(c);
   308 		else
   309 		else
   309 			ban(c);
   310 			ban(c);
   310 
   311 
   311 	selmonitor->layout->arrange(selmonitor);
   312 	if(m)
       
   313 		m->layout->arrange(m);
       
   314 	else
       
   315 		for(i = 0; i < mcount; i++)
       
   316 			m->layout->arrange(&monitors[i]);
   312 	focus(NULL);
   317 	focus(NULL);
   313 	restack(selmonitor);
   318 	restack(m);
   314 }
   319 }
   315 
   320 
   316 void
   321 void
   317 attach(Client *c) {
   322 attach(Client *c) {
   318 	if(clients)
   323 	if(clients)
   483 		m->sh = ev->height;
   488 		m->sh = ev->height;
   484 		XFreePixmap(dpy, dc.drawable);
   489 		XFreePixmap(dpy, dc.drawable);
   485 		dc.drawable = XCreatePixmap(dpy, root, DisplayWidth(root, screen), bh, DefaultDepth(dpy, screen));
   490 		dc.drawable = XCreatePixmap(dpy, root, DisplayWidth(root, screen), bh, DefaultDepth(dpy, screen));
   486 		XResizeWindow(dpy, m->barwin, m->sw, bh);
   491 		XResizeWindow(dpy, m->barwin, m->sw, bh);
   487 		updatebarpos(m);
   492 		updatebarpos(m);
   488 		arrange();
   493 		arrange(m);
   489 	}
   494 	}
   490 }
   495 }
   491 
   496 
   492 void
   497 void
   493 configurerequest(XEvent *e) {
   498 configurerequest(XEvent *e) {
  1076 	c->tags = emallocz(sizeof initags);
  1081 	c->tags = emallocz(sizeof initags);
  1077 	c->win = w;
  1082 	c->win = w;
  1078 
  1083 
  1079 	applyrules(c);
  1084 	applyrules(c);
  1080 
  1085 
  1081 	m = selmonitor;
  1086 	m = c->monitor;
  1082 
  1087 
  1083 	c->x = wa->x + m->sx;
  1088 	c->x = wa->x + m->sx;
  1084 	c->y = wa->y + m->sy;
  1089 	c->y = wa->y + m->sy;
  1085 	c->w = wa->width;
  1090 	c->w = wa->width;
  1086 	c->h = wa->height;
  1091 	c->h = wa->height;
  1120 	attachstack(c);
  1125 	attachstack(c);
  1121 	XMoveResizeWindow(dpy, c->win, c->x, c->y, c->w, c->h); /* some windows require this */
  1126 	XMoveResizeWindow(dpy, c->win, c->x, c->y, c->w, c->h); /* some windows require this */
  1122 	ban(c);
  1127 	ban(c);
  1123 	XMapWindow(dpy, c->win);
  1128 	XMapWindow(dpy, c->win);
  1124 	setclientstate(c, NormalState);
  1129 	setclientstate(c, NormalState);
  1125 	arrange();
  1130 	arrange(m);
  1126 }
  1131 }
  1127 
  1132 
  1128 void
  1133 void
  1129 mappingnotify(XEvent *e) {
  1134 mappingnotify(XEvent *e) {
  1130 	XMappingEvent *ev = &e->xmapping;
  1135 	XMappingEvent *ev = &e->xmapping;
  1199 				nx = m->wax + m->waw - c->w - 2 * c->border;
  1204 				nx = m->wax + m->waw - c->w - 2 * c->border;
  1200 			if(abs(m->way - ny) < SNAP)
  1205 			if(abs(m->way - ny) < SNAP)
  1201 				ny = m->way;
  1206 				ny = m->way;
  1202 			else if(abs((m->way + m->wah) - (ny + c->h + 2 * c->border)) < SNAP)
  1207 			else if(abs((m->way + m->wah) - (ny + c->h + 2 * c->border)) < SNAP)
  1203 				ny = m->way + m->wah - c->h - 2 * c->border;
  1208 				ny = m->way + m->wah - c->h - 2 * c->border;
  1204 			if((m->layout->arrange != floating) && (abs(nx - c->x) > SNAP || abs(ny - c->y) > SNAP))
  1209 			if(!c->isfloating && (m->layout->arrange != floating) && (abs(nx - c->x) > SNAP || abs(ny - c->y) > SNAP))
  1205 				togglefloating(NULL);
  1210 				togglefloating(NULL);
  1206 			if((m->layout->arrange == floating) || c->isfloating)
  1211 			if((m->layout->arrange == floating) || c->isfloating)
  1207 				resize(c, nx, ny, c->w, c->h, False);
  1212 				resize(c, nx, ny, c->w, c->h, False);
  1208 			break;
  1213 			break;
  1209 		}
  1214 		}
  1228 		switch (ev->atom) {
  1233 		switch (ev->atom) {
  1229 		default: break;
  1234 		default: break;
  1230 		case XA_WM_TRANSIENT_FOR:
  1235 		case XA_WM_TRANSIENT_FOR:
  1231 			XGetTransientForHint(dpy, c->win, &trans);
  1236 			XGetTransientForHint(dpy, c->win, &trans);
  1232 			if(!c->isfloating && (c->isfloating = (getclient(trans) != NULL)))
  1237 			if(!c->isfloating && (c->isfloating = (getclient(trans) != NULL)))
  1233 				arrange();
  1238 				arrange(c->monitor);
  1234 			break;
  1239 			break;
  1235 		case XA_WM_NORMAL_HINTS:
  1240 		case XA_WM_NORMAL_HINTS:
  1236 			updatesizehints(c);
  1241 			updatesizehints(c);
  1237 			break;
  1242 			break;
  1238 		case XA_WM_HINTS:
  1243 		case XA_WM_HINTS:
  1260 
  1265 
  1261 	for(c = clients; c; c = c->next) {
  1266 	for(c = clients; c; c = c->next) {
  1262 		memcpy(c->tags, zerotags, sizeof zerotags);
  1267 		memcpy(c->tags, zerotags, sizeof zerotags);
  1263 		applyrules(c);
  1268 		applyrules(c);
  1264 	}
  1269 	}
  1265 	arrange();
  1270 	arrange(NULL);
  1266 }
  1271 }
  1267 
  1272 
  1268 void
  1273 void
  1269 resize(Client *c, int x, int y, int w, int h, Bool sizehints) {
  1274 resize(Client *c, int x, int y, int w, int h, Bool sizehints) {
  1270 	Monitor *m;
  1275 	Monitor *m;
  1364 			XSync(dpy, False);
  1369 			XSync(dpy, False);
  1365 			if((nw = ev.xmotion.x - ocx - 2 * c->border + 1) <= 0)
  1370 			if((nw = ev.xmotion.x - ocx - 2 * c->border + 1) <= 0)
  1366 				nw = 1;
  1371 				nw = 1;
  1367 			if((nh = ev.xmotion.y - ocy - 2 * c->border + 1) <= 0)
  1372 			if((nh = ev.xmotion.y - ocy - 2 * c->border + 1) <= 0)
  1368 				nh = 1;
  1373 				nh = 1;
  1369 			if((m->layout->arrange != floating) && (abs(nw - c->w) > SNAP || abs(nh - c->h) > SNAP))
  1374 			if(!c->isfloating && (m->layout->arrange != floating) && (abs(nw - c->w) > SNAP || abs(nh - c->h) > SNAP))
  1370 				togglefloating(NULL);
  1375 				togglefloating(NULL);
  1371 			if((m->layout->arrange == floating) || c->isfloating)
  1376 			if((m->layout->arrange == floating) || c->isfloating)
  1372 				resize(c, c->x, c->y, nw, nh, True);
  1377 				resize(c, c->x, c->y, nw, nh, True);
  1373 			break;
  1378 			break;
  1374 		}
  1379 		}
  1516 		if(i == LENGTH(layouts))
  1521 		if(i == LENGTH(layouts))
  1517 			return;
  1522 			return;
  1518 		m->layout = &layouts[i];
  1523 		m->layout = &layouts[i];
  1519 	}
  1524 	}
  1520 	if(sel)
  1525 	if(sel)
  1521 		arrange();
  1526 		arrange(m);
  1522 	else
  1527 	else
  1523 		drawbar(m);
  1528 		drawbar(m);
  1524 }
  1529 }
  1525 
  1530 
  1526 void
  1531 void
  1542 		if(m->mwfact < 0.1)
  1547 		if(m->mwfact < 0.1)
  1543 			m->mwfact = 0.1;
  1548 			m->mwfact = 0.1;
  1544 		else if(m->mwfact > 0.9)
  1549 		else if(m->mwfact > 0.9)
  1545 			m->mwfact = 0.9;
  1550 			m->mwfact = 0.9;
  1546 	}
  1551 	}
  1547 	arrange();
  1552 	arrange(m);
  1548 }
  1553 }
  1549 
  1554 
  1550 void
  1555 void
  1551 setup(void) {
  1556 setup(void) {
  1552 	unsigned int i;
  1557 	unsigned int i;
  1695 	if(!sel)
  1700 	if(!sel)
  1696 		return;
  1701 		return;
  1697 	for(i = 0; i < LENGTH(tags); i++)
  1702 	for(i = 0; i < LENGTH(tags); i++)
  1698 		sel->tags[i] = (NULL == arg);
  1703 		sel->tags[i] = (NULL == arg);
  1699 	sel->tags[idxoftag(arg)] = True;
  1704 	sel->tags[idxoftag(arg)] = True;
  1700 	arrange();
  1705 	arrange(sel->monitor);
  1701 }
  1706 }
  1702 
  1707 
  1703 unsigned int
  1708 unsigned int
  1704 textnw(const char *text, unsigned int len) {
  1709 textnw(const char *text, unsigned int len) {
  1705 	XRectangle r;
  1710 	XRectangle r;
  1767 	if(bpos == BarOff)
  1772 	if(bpos == BarOff)
  1768 		bpos = (BARPOS == BarOff) ? BarTop : BARPOS;
  1773 		bpos = (BARPOS == BarOff) ? BarTop : BARPOS;
  1769 	else
  1774 	else
  1770 		bpos = BarOff;
  1775 		bpos = BarOff;
  1771 	updatebarpos(monitorat());
  1776 	updatebarpos(monitorat());
  1772 	arrange();
  1777 	arrange(monitorat());
  1773 }
  1778 }
  1774 
  1779 
  1775 void
  1780 void
  1776 togglefloating(const char *arg) {
  1781 togglefloating(const char *arg) {
  1777 	if(!sel)
  1782 	if(!sel)
  1778 		return;
  1783 		return;
  1779 	sel->isfloating = !sel->isfloating;
  1784 	sel->isfloating = !sel->isfloating;
  1780 	if(sel->isfloating)
  1785 	if(sel->isfloating)
  1781 		resize(sel, sel->x, sel->y, sel->w, sel->h, True);
  1786 		resize(sel, sel->x, sel->y, sel->w, sel->h, True);
  1782 	arrange();
  1787 	arrange(sel->monitor);
  1783 }
  1788 }
  1784 
  1789 
  1785 void
  1790 void
  1786 toggletag(const char *arg) {
  1791 toggletag(const char *arg) {
  1787 	unsigned int i, j;
  1792 	unsigned int i, j;
  1791 	i = idxoftag(arg);
  1796 	i = idxoftag(arg);
  1792 	sel->tags[i] = !sel->tags[i];
  1797 	sel->tags[i] = !sel->tags[i];
  1793 	for(j = 0; j < LENGTH(tags) && !sel->tags[j]; j++);
  1798 	for(j = 0; j < LENGTH(tags) && !sel->tags[j]; j++);
  1794 	if(j == LENGTH(tags))
  1799 	if(j == LENGTH(tags))
  1795 		sel->tags[i] = True; /* at least one tag must be enabled */
  1800 		sel->tags[i] = True; /* at least one tag must be enabled */
  1796 	arrange();
  1801 	arrange(sel->monitor);
  1797 }
  1802 }
  1798 
  1803 
  1799 void
  1804 void
  1800 toggleview(const char *arg) {
  1805 toggleview(const char *arg) {
  1801 	unsigned int i, j;
  1806 	unsigned int i, j;
  1802 
       
  1803 	Monitor *m = monitorat();
  1807 	Monitor *m = monitorat();
  1804 
  1808 
  1805 	i = idxoftag(arg);
  1809 	i = idxoftag(arg);
  1806 	m->seltags[i] = !m->seltags[i];
  1810 	m->seltags[i] = !m->seltags[i];
  1807 	for(j = 0; j < LENGTH(tags) && !m->seltags[j]; j++);
  1811 	for(j = 0; j < LENGTH(tags) && !m->seltags[j]; j++);
  1808 	if(j == LENGTH(tags))
  1812 	if(j == LENGTH(tags))
  1809 		m->seltags[i] = True; /* at least one tag must be viewed */
  1813 		m->seltags[i] = True; /* at least one tag must be viewed */
  1810 	arrange();
  1814 	arrange(m);
  1811 }
  1815 }
  1812 
  1816 
  1813 void
  1817 void
  1814 unban(Client *c) {
  1818 unban(Client *c) {
  1815 	if(!c->isbanned)
  1819 	if(!c->isbanned)
  1836 	free(c->tags);
  1840 	free(c->tags);
  1837 	free(c);
  1841 	free(c);
  1838 	XSync(dpy, False);
  1842 	XSync(dpy, False);
  1839 	XSetErrorHandler(xerror);
  1843 	XSetErrorHandler(xerror);
  1840 	XUngrabServer(dpy);
  1844 	XUngrabServer(dpy);
  1841 	arrange();
  1845 	arrange(NULL);
  1842 }
  1846 }
  1843 
  1847 
  1844 void
  1848 void
  1845 unmapnotify(XEvent *e) {
  1849 unmapnotify(XEvent *e) {
  1846 	Client *c;
  1850 	Client *c;
  1986 		tmp[i] = (NULL == arg);
  1990 		tmp[i] = (NULL == arg);
  1987 	tmp[idxoftag(arg)] = True;
  1991 	tmp[idxoftag(arg)] = True;
  1988 	if(memcmp(m->seltags, tmp, sizeof initags) != 0) {
  1992 	if(memcmp(m->seltags, tmp, sizeof initags) != 0) {
  1989 		memcpy(m->prevtags, m->seltags, sizeof initags);
  1993 		memcpy(m->prevtags, m->seltags, sizeof initags);
  1990 		memcpy(m->seltags, tmp, sizeof initags);
  1994 		memcpy(m->seltags, tmp, sizeof initags);
  1991 		arrange();
  1995 		arrange(m);
  1992 	}
  1996 	}
  1993 }
  1997 }
  1994 
  1998 
  1995 void
  1999 void
  1996 viewprevtag(const char *arg) {
  2000 viewprevtag(const char *arg) {
  1999 	Monitor *m = monitorat();
  2003 	Monitor *m = monitorat();
  2000 
  2004 
  2001 	memcpy(tmp, m->seltags, sizeof initags);
  2005 	memcpy(tmp, m->seltags, sizeof initags);
  2002 	memcpy(m->seltags, m->prevtags, sizeof initags);
  2006 	memcpy(m->seltags, m->prevtags, sizeof initags);
  2003 	memcpy(m->prevtags, tmp, sizeof initags);
  2007 	memcpy(m->prevtags, tmp, sizeof initags);
  2004 	arrange();
  2008 	arrange(m);
  2005 }
  2009 }
  2006 
  2010 
  2007 void
  2011 void
  2008 zoom(const char *arg) {
  2012 zoom(const char *arg) {
  2009 	Client *c = sel;
  2013 	Client *c = sel;
  2014 		if(!(c = nexttiled(c->next, c->monitor)))
  2018 		if(!(c = nexttiled(c->next, c->monitor)))
  2015 			return;
  2019 			return;
  2016 	detach(c);
  2020 	detach(c);
  2017 	attach(c);
  2021 	attach(c);
  2018 	focus(c);
  2022 	focus(c);
  2019 	arrange();
  2023 	arrange(c->monitor);
  2020 }
  2024 }
  2021 
  2025 
  2022 void
  2026 void
  2023 movetomonitor(const char *arg) {
  2027 movetomonitor(const char *arg) {
  2024 	int i;
  2028 	int i;
  2033 	}
  2037 	}
  2034 	sel->monitor = &monitors[i % mcount];
  2038 	sel->monitor = &monitors[i % mcount];
  2035 
  2039 
  2036 	memcpy(sel->tags, sel->monitor->seltags, sizeof initags);
  2040 	memcpy(sel->tags, sel->monitor->seltags, sizeof initags);
  2037 	resize(sel, sel->monitor->wax, sel->monitor->way, sel->w, sel->h, True);
  2041 	resize(sel, sel->monitor->wax, sel->monitor->way, sel->w, sel->h, True);
  2038 	arrange();
  2042 	arrange(sel->monitor);
  2039 }
  2043 }
  2040 
  2044 
  2041 void
  2045 void
  2042 selectmonitor(const char *arg) {
  2046 selectmonitor(const char *arg) {
  2043 	int i;
  2047 	int i;