|
@ -59,7 +59,7 @@ enum { CurNormal, CurResize, CurMove, CurLast }; /* cursor */ |
|
|
enum { ColBorder, ColFG, ColBG, ColLast }; /* color */ |
|
|
enum { ColBorder, ColFG, ColBG, ColLast }; /* color */ |
|
|
enum { NetSupported, NetWMName, NetWMState, |
|
|
enum { NetSupported, NetWMName, NetWMState, |
|
|
NetWMFullscreen, NetLast }; /* EWMH atoms */ |
|
|
NetWMFullscreen, NetLast }; /* EWMH atoms */ |
|
|
enum { WMProtocols, WMDelete, WMState, WMLast }; /* default atoms */ |
|
|
|
|
|
|
|
|
enum { WMProtocols, WMDelete, WMState, WMTakeFocus, WMLast }; /* default atoms */ |
|
|
enum { ClkTagBar, ClkLtSymbol, ClkStatusText, ClkWinTitle, |
|
|
enum { ClkTagBar, ClkLtSymbol, ClkStatusText, ClkWinTitle, |
|
|
ClkClientWin, ClkRootWin, ClkLast }; /* clicks */ |
|
|
ClkClientWin, ClkRootWin, ClkLast }; /* clicks */ |
|
|
|
|
|
|
|
@ -88,7 +88,7 @@ struct Client { |
|
|
int basew, baseh, incw, inch, maxw, maxh, minw, minh; |
|
|
int basew, baseh, incw, inch, maxw, maxh, minw, minh; |
|
|
int bw, oldbw; |
|
|
int bw, oldbw; |
|
|
unsigned int tags; |
|
|
unsigned int tags; |
|
|
Bool isfixed, isfloating, isurgent, oldstate; |
|
|
|
|
|
|
|
|
Bool isfixed, isfloating, isurgent, neverfocus, oldstate; |
|
|
Client *next; |
|
|
Client *next; |
|
|
Client *snext; |
|
|
Client *snext; |
|
|
Monitor *mon; |
|
|
Monitor *mon; |
|
@ -190,7 +190,6 @@ static Bool gettextprop(Window w, Atom atom, char *text, unsigned int size); |
|
|
static void grabbuttons(Client *c, Bool focused); |
|
|
static void grabbuttons(Client *c, Bool focused); |
|
|
static void grabkeys(void); |
|
|
static void grabkeys(void); |
|
|
static void initfont(const char *fontstr); |
|
|
static void initfont(const char *fontstr); |
|
|
static Bool isprotodel(Client *c); |
|
|
|
|
|
static void keypress(XEvent *e); |
|
|
static void keypress(XEvent *e); |
|
|
static void killclient(const Arg *arg); |
|
|
static void killclient(const Arg *arg); |
|
|
static void manage(Window w, XWindowAttributes *wa); |
|
|
static void manage(Window w, XWindowAttributes *wa); |
|
@ -208,8 +207,10 @@ static void resizemouse(const Arg *arg); |
|
|
static void restack(Monitor *m); |
|
|
static void restack(Monitor *m); |
|
|
static void run(void); |
|
|
static void run(void); |
|
|
static void scan(void); |
|
|
static void scan(void); |
|
|
|
|
|
static Bool sendevent(Client *c, Atom proto); |
|
|
static void sendmon(Client *c, Monitor *m); |
|
|
static void sendmon(Client *c, Monitor *m); |
|
|
static void setclientstate(Client *c, long state); |
|
|
static void setclientstate(Client *c, long state); |
|
|
|
|
|
static void setfocus(Client *c); |
|
|
static void setlayout(const Arg *arg); |
|
|
static void setlayout(const Arg *arg); |
|
|
static void setmfact(const Arg *arg); |
|
|
static void setmfact(const Arg *arg); |
|
|
static void setup(void); |
|
|
static void setup(void); |
|
@ -821,7 +822,7 @@ focus(Client *c) { |
|
|
attachstack(c); |
|
|
attachstack(c); |
|
|
grabbuttons(c, True); |
|
|
grabbuttons(c, True); |
|
|
XSetWindowBorder(dpy, c->win, dc.sel[ColBorder]); |
|
|
XSetWindowBorder(dpy, c->win, dc.sel[ColBorder]); |
|
|
XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime); |
|
|
|
|
|
|
|
|
setfocus(c); |
|
|
} |
|
|
} |
|
|
else |
|
|
else |
|
|
XSetInputFocus(dpy, root, RevertToPointerRoot, CurrentTime); |
|
|
XSetInputFocus(dpy, root, RevertToPointerRoot, CurrentTime); |
|
@ -834,7 +835,7 @@ focusin(XEvent *e) { /* there are some broken focus acquiring clients */ |
|
|
XFocusChangeEvent *ev = &e->xfocus; |
|
|
XFocusChangeEvent *ev = &e->xfocus; |
|
|
|
|
|
|
|
|
if(selmon->sel && ev->window != selmon->sel->win) |
|
|
if(selmon->sel && ev->window != selmon->sel->win) |
|
|
XSetInputFocus(dpy, selmon->sel->win, RevertToPointerRoot, CurrentTime); |
|
|
|
|
|
|
|
|
setfocus(selmon->sel); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
void |
|
|
void |
|
@ -1012,20 +1013,6 @@ initfont(const char *fontstr) { |
|
|
dc.font.height = dc.font.ascent + dc.font.descent; |
|
|
dc.font.height = dc.font.ascent + dc.font.descent; |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
Bool |
|
|
|
|
|
isprotodel(Client *c) { |
|
|
|
|
|
int n; |
|
|
|
|
|
Atom *protocols; |
|
|
|
|
|
Bool ret = False; |
|
|
|
|
|
|
|
|
|
|
|
if(XGetWMProtocols(dpy, c->win, &protocols, &n)) { |
|
|
|
|
|
while(!ret && n--) |
|
|
|
|
|
ret = protocols[n] == wmatom[WMDelete]; |
|
|
|
|
|
XFree(protocols); |
|
|
|
|
|
} |
|
|
|
|
|
return ret; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
#ifdef XINERAMA |
|
|
#ifdef XINERAMA |
|
|
static Bool |
|
|
static Bool |
|
|
isuniquegeom(XineramaScreenInfo *unique, size_t n, XineramaScreenInfo *info) { |
|
|
isuniquegeom(XineramaScreenInfo *unique, size_t n, XineramaScreenInfo *info) { |
|
@ -1054,20 +1041,9 @@ keypress(XEvent *e) { |
|
|
|
|
|
|
|
|
void |
|
|
void |
|
|
killclient(const Arg *arg) { |
|
|
killclient(const Arg *arg) { |
|
|
XEvent ev; |
|
|
|
|
|
|
|
|
|
|
|
if(!selmon->sel) |
|
|
if(!selmon->sel) |
|
|
return; |
|
|
return; |
|
|
if(isprotodel(selmon->sel)) { |
|
|
|
|
|
ev.type = ClientMessage; |
|
|
|
|
|
ev.xclient.window = selmon->sel->win; |
|
|
|
|
|
ev.xclient.message_type = wmatom[WMProtocols]; |
|
|
|
|
|
ev.xclient.format = 32; |
|
|
|
|
|
ev.xclient.data.l[0] = wmatom[WMDelete]; |
|
|
|
|
|
ev.xclient.data.l[1] = CurrentTime; |
|
|
|
|
|
XSendEvent(dpy, selmon->sel->win, False, NoEventMask, &ev); |
|
|
|
|
|
} |
|
|
|
|
|
else { |
|
|
|
|
|
|
|
|
if(!sendevent(selmon->sel, wmatom[WMDelete])) { |
|
|
XGrabServer(dpy); |
|
|
XGrabServer(dpy); |
|
|
XSetErrorHandler(xerrordummy); |
|
|
XSetErrorHandler(xerrordummy); |
|
|
XSetCloseDownMode(dpy, DestroyAll); |
|
|
XSetCloseDownMode(dpy, DestroyAll); |
|
@ -1124,6 +1100,7 @@ manage(Window w, XWindowAttributes *wa) { |
|
|
XSetWindowBorder(dpy, w, dc.norm[ColBorder]); |
|
|
XSetWindowBorder(dpy, w, dc.norm[ColBorder]); |
|
|
configure(c); /* propagates border_width, if size doesn't change */ |
|
|
configure(c); /* propagates border_width, if size doesn't change */ |
|
|
updatesizehints(c); |
|
|
updatesizehints(c); |
|
|
|
|
|
updatewmhints(c); |
|
|
XSelectInput(dpy, w, EnterWindowMask|FocusChangeMask|PropertyChangeMask|StructureNotifyMask); |
|
|
XSelectInput(dpy, w, EnterWindowMask|FocusChangeMask|PropertyChangeMask|StructureNotifyMask); |
|
|
grabbuttons(c, False); |
|
|
grabbuttons(c, False); |
|
|
if(!c->isfloating) |
|
|
if(!c->isfloating) |
|
@ -1471,6 +1448,37 @@ setclientstate(Client *c, long state) { |
|
|
PropModeReplace, (unsigned char *)data, 2); |
|
|
PropModeReplace, (unsigned char *)data, 2); |
|
|
} |
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
Bool |
|
|
|
|
|
sendevent(Client *c, Atom proto) { |
|
|
|
|
|
int n; |
|
|
|
|
|
Atom *protocols; |
|
|
|
|
|
Bool exists = False; |
|
|
|
|
|
XEvent ev; |
|
|
|
|
|
|
|
|
|
|
|
if(XGetWMProtocols(dpy, c->win, &protocols, &n)) { |
|
|
|
|
|
while(!exists && n--) |
|
|
|
|
|
exists = protocols[n] == proto; |
|
|
|
|
|
XFree(protocols); |
|
|
|
|
|
} |
|
|
|
|
|
if (exists) { |
|
|
|
|
|
ev.type = ClientMessage; |
|
|
|
|
|
ev.xclient.window = c->win; |
|
|
|
|
|
ev.xclient.message_type = wmatom[WMProtocols]; |
|
|
|
|
|
ev.xclient.format = 32; |
|
|
|
|
|
ev.xclient.data.l[0] = proto; |
|
|
|
|
|
ev.xclient.data.l[1] = CurrentTime; |
|
|
|
|
|
XSendEvent(dpy, c->win, False, NoEventMask, &ev); |
|
|
|
|
|
} |
|
|
|
|
|
return exists; |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
void |
|
|
|
|
|
setfocus(Client *c) { |
|
|
|
|
|
if (!c->neverfocus) |
|
|
|
|
|
XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime); |
|
|
|
|
|
sendevent(c, wmatom[WMTakeFocus]); |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
void |
|
|
void |
|
|
setlayout(const Arg *arg) { |
|
|
setlayout(const Arg *arg) { |
|
|
if(!arg || !arg->v || arg->v != selmon->lt[selmon->sellt]) |
|
|
if(!arg || !arg->v || arg->v != selmon->lt[selmon->sellt]) |
|
@ -1517,6 +1525,7 @@ setup(void) { |
|
|
wmatom[WMProtocols] = XInternAtom(dpy, "WM_PROTOCOLS", False); |
|
|
wmatom[WMProtocols] = XInternAtom(dpy, "WM_PROTOCOLS", False); |
|
|
wmatom[WMDelete] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); |
|
|
wmatom[WMDelete] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); |
|
|
wmatom[WMState] = XInternAtom(dpy, "WM_STATE", False); |
|
|
wmatom[WMState] = XInternAtom(dpy, "WM_STATE", False); |
|
|
|
|
|
wmatom[WMTakeFocus] = XInternAtom(dpy, "WM_TAKE_FOCUS", False); |
|
|
netatom[NetSupported] = XInternAtom(dpy, "_NET_SUPPORTED", False); |
|
|
netatom[NetSupported] = XInternAtom(dpy, "_NET_SUPPORTED", False); |
|
|
netatom[NetWMName] = XInternAtom(dpy, "_NET_WM_NAME", False); |
|
|
netatom[NetWMName] = XInternAtom(dpy, "_NET_WM_NAME", False); |
|
|
netatom[NetWMState] = XInternAtom(dpy, "_NET_WM_STATE", False); |
|
|
netatom[NetWMState] = XInternAtom(dpy, "_NET_WM_STATE", False); |
|
@ -1933,6 +1942,8 @@ updatewmhints(Client *c) { |
|
|
} |
|
|
} |
|
|
else |
|
|
else |
|
|
c->isurgent = (wmh->flags & XUrgencyHint) ? True : False; |
|
|
c->isurgent = (wmh->flags & XUrgencyHint) ? True : False; |
|
|
|
|
|
if (wmh->flags & InputHint) c->neverfocus = !wmh->input; |
|
|
|
|
|
else c->neverfocus = False; |
|
|
XFree(wmh); |
|
|
XFree(wmh); |
|
|
} |
|
|
} |
|
|
} |
|
|
} |
|
|