mirror of https://github.com/0intro/wmii
178 lines
3.1 KiB
C
178 lines
3.1 KiB
C
/* Copyright ©2006-2010 Kris Maglione <maglione.k at Gmail>
|
|
* See LICENSE file for license details.
|
|
*/
|
|
#define EXTERN
|
|
#include "dat.h"
|
|
#include <X11/Xproto.h>
|
|
#include <locale.h>
|
|
#include <string.h>
|
|
#include <time.h>
|
|
#include "fns.h"
|
|
|
|
char *argv0;
|
|
Display *display;
|
|
Screen scr;
|
|
|
|
static Window* testwin;
|
|
static ulong testtime[2];
|
|
|
|
static const char version[] = "wistrut-"VERSION", "COPYRIGHT"\n";
|
|
|
|
static void manage(ulong);
|
|
|
|
static void
|
|
usage(void) {
|
|
fatal("usage: %s [-HV] <window|class>...\n", argv0);
|
|
}
|
|
|
|
static void
|
|
search_wins(char *pattern) {
|
|
ulong *wins;
|
|
ulong n, num;
|
|
int i;
|
|
char **class;
|
|
Reprog *regexp;
|
|
Window *win;
|
|
|
|
regexp = regcomp(pattern);
|
|
|
|
num = getprop_ulong(&scr.root, "_NET_CLIENT_LIST", "WINDOW", 0L, &wins, 1024L);
|
|
for(i = 0; i < num; i++) {
|
|
win = window(wins[i]);
|
|
|
|
n = getprop_textlist(win, "WM_CLASS", &class);
|
|
bufclear();
|
|
bufprint("%s:%s:%s",
|
|
(n > 0 ? class[0] : "<nil>"),
|
|
(n > 1 ? class[1] : "<nil>"),
|
|
freelater(windowname(win)));
|
|
freestringlist(class);
|
|
if(regexec(regexp, buffer, nil, 0))
|
|
manage(wins[i]);
|
|
}
|
|
free(wins);
|
|
}
|
|
|
|
static Window
|
|
findframe(Window *w) {
|
|
XWindow *children;
|
|
XWindow xw, par, root;
|
|
Window ret = {0, };
|
|
uint n;
|
|
|
|
xw = w->xid;
|
|
for(par=w->xid; par != scr.root.xid; ) {
|
|
xw = par;
|
|
XQueryTree(display, xw, &root, &par, &children, &n);
|
|
XFree(children);
|
|
}
|
|
ret.type = WWindow;
|
|
ret.xid = xw;
|
|
ret.parent = &scr.root;
|
|
return ret;
|
|
}
|
|
|
|
static void
|
|
getwinsize(Window *win) {
|
|
int x, y;
|
|
uint w, h;
|
|
XWindow root;
|
|
uint border, depth;
|
|
|
|
XGetGeometry(display, win->xid, &root,
|
|
&x, &y, &w, &h,
|
|
&border, &depth);
|
|
win->r = rectaddpt(Rect(0, 0, w, h),
|
|
Pt(x+border, y+border));
|
|
}
|
|
|
|
static bool
|
|
managable(ulong xid) {
|
|
ulong *ret;
|
|
ulong n;
|
|
bool retval;
|
|
|
|
n = getprop_ulong(window(xid), "_WMII_STRUT", "WINDOW", 0L, &ret, 1L);
|
|
if(n < 0)
|
|
retval = true;
|
|
else {
|
|
if(ret[0] == xid)
|
|
retval = ret[0] != testtime[0] || ret[1] != testtime[1];
|
|
else
|
|
retval = managable(ret[0]);
|
|
}
|
|
free(ret);
|
|
return retval;
|
|
}
|
|
|
|
static void
|
|
manage(ulong xid) {
|
|
Window *frame;
|
|
Window *win;
|
|
|
|
if(!managable(xid))
|
|
return;
|
|
|
|
win = emallocz(sizeof *win);
|
|
frame = emalloc(sizeof *frame);
|
|
|
|
win->type = WWindow;
|
|
win->xid = xid;
|
|
*frame = findframe(win);
|
|
frame->aux = win;
|
|
|
|
getwinsize(frame);
|
|
restrut(frame);
|
|
sethandler(frame, &handlers);
|
|
selectinput(frame, StructureNotifyMask);
|
|
|
|
changeprop_ulong(frame, "_WMII_STRUT", "WINDOW", testtime, nelem(testtime));
|
|
}
|
|
|
|
int
|
|
main(int argc, char *argv[]) {
|
|
ulong win;
|
|
char *s;
|
|
|
|
setlocale(LC_CTYPE, "");
|
|
fmtinstall('E', fmtevent);
|
|
|
|
ARGBEGIN{
|
|
case 'H':
|
|
direction = DHorizontal;
|
|
break;
|
|
case 'V':
|
|
direction = DVertical;
|
|
break;
|
|
case 'v':
|
|
lprint(1, "%s", version);
|
|
return 0;
|
|
default:
|
|
usage();
|
|
}ARGEND;
|
|
|
|
initdisplay();
|
|
|
|
testwin = createwindow(&scr.root, Rect(0, 0, 1, 1), 0,
|
|
InputOnly, nil, 0);
|
|
testtime[0] = testwin->xid;
|
|
testtime[1] = time(nil);
|
|
|
|
while(argc) {
|
|
s = ARGF();
|
|
if(getulong(s, &win))
|
|
manage(win);
|
|
else
|
|
search_wins(s);
|
|
}
|
|
|
|
changeprop_ulong(testwin, "_WMII_STRUT", "WINDOW", testtime, nelem(testtime));
|
|
|
|
if(windowmap.nmemb > 0)
|
|
event_loop();
|
|
|
|
XCloseDisplay(display);
|
|
return 0;
|
|
}
|
|
|