Allow chained event handlers.

This commit is contained in:
Kris Maglione 2010-05-27 18:57:08 -04:00
parent c4e7c2de67
commit b4b5ff470b
19 changed files with 247 additions and 186 deletions

View File

@ -254,7 +254,7 @@ menu_show(void) {
menu_draw(); menu_draw();
} }
static void static bool
kdown_event(Window *w, void *aux, XKeyEvent *e) { kdown_event(Window *w, void *aux, XKeyEvent *e) {
char **action, **p; char **action, **p;
char *key; char *key;
@ -276,7 +276,7 @@ kdown_event(Window *w, void *aux, XKeyEvent *e) {
|| IsKeypadKey(ksym) || IsKeypadKey(ksym)
|| IsPrivateKeypadKey(ksym) || IsPrivateKeypadKey(ksym)
|| IsPFKey(ksym)) || IsPFKey(ksym))
return; return false;
action = find_key(key, e->state); action = find_key(key, e->state);
if(action == nil || action[0] == nil) { if(action == nil || action[0] == nil) {
@ -328,13 +328,15 @@ kdown_event(Window *w, void *aux, XKeyEvent *e) {
break; break;
} }
} }
return false;
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *e) { expose_event(Window *w, void *aux, XExposeEvent *e) {
USED(w); USED(w);
menu_draw(); menu_draw();
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -79,20 +79,22 @@ restrut(Window *frame) {
ewmh_setstrut(frame->aux, strut); ewmh_setstrut(frame->aux, strut);
} }
static void static bool
config_event(Window *frame, void *aux, XConfigureEvent *ev) { config_event(Window *frame, void *aux, XConfigureEvent *ev) {
frame->r = rectaddpt(Rect(ev->x, ev->y, ev->width, ev->height), frame->r = rectaddpt(Rect(ev->x, ev->y, ev->width, ev->height),
Pt(ev->border_width, ev->border_width)); Pt(ev->border_width, ev->border_width));
restrut(frame); restrut(frame);
return false;
} }
static void static bool
destroy_event(Window *w, void *aux, XDestroyWindowEvent *ev) { destroy_event(Window *w, void *aux, XDestroyWindowEvent *ev) {
USED(ev); USED(ev);
sethandler(w, nil); sethandler(w, nil);
event_looprunning = windowmap.nmemb > 0; event_looprunning = windowmap.nmemb > 0;
return false;
} }
Handlers handlers = { Handlers handlers = {

View File

@ -152,42 +152,47 @@ client_message(Client *c, long type, int format, ClientMessageData* data) {
} }
} }
static void static bool
config_event(Window *w, void *aux, XConfigureEvent *e) { config_event(Window *w, void *aux, XConfigureEvent *e) {
Client *c; Client *c;
c = aux; c = aux;
if(false) if(false)
movewin(c->indicator, addpt(w->r.min, Pt(1, 1))); movewin(c->indicator, addpt(w->r.min, Pt(1, 1)));
return false;
} }
static void static bool
configreq_event(Window *w, void *aux, XConfigureRequestEvent *e) { configreq_event(Window *w, void *aux, XConfigureRequestEvent *e) {
Dprint("configreq_event(%W)\n", w); Dprint("configreq_event(%W)\n", w);
/* This seems, sadly, to be necessary. */ /* This seems, sadly, to be necessary. */
tray_update(); tray_update();
return false;
} }
static void static bool
map_event(Window *w, void *aux, XMapEvent *e) { map_event(Window *w, void *aux, XMapEvent *e) {
Dprint("client map_event(%W)\n", w); Dprint("client map_event(%W)\n", w);
w->mapped = true; w->mapped = true;
tray_update(); tray_update();
return false;
} }
static void static bool
unmap_event(Window *w, void *aux, XUnmapEvent *e) { unmap_event(Window *w, void *aux, XUnmapEvent *e) {
Dprint("client map_event(%W)\n", w); Dprint("client map_event(%W)\n", w);
tray_update(); tray_update();
return false;
} }
static void static bool
reparent_event(Window *w, void *aux, XReparentEvent *e) { reparent_event(Window *w, void *aux, XReparentEvent *e) {
Dprint("client reparent_event(%W)\n", w); Dprint("client reparent_event(%W)\n", w);
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -94,16 +94,17 @@ selection_notify(Selection *s, XSelectionRequestEvent *ev, bool success) {
sendevent(window(ev->requestor), false, 0L, &notify); sendevent(window(ev->requestor), false, 0L, &notify);
} }
static void static bool
message_event(Window *w, void *aux, XClientMessageEvent *ev) { message_event(Window *w, void *aux, XClientMessageEvent *ev) {
Selection *s; Selection *s;
s = aux; s = aux;
if(s->message) if(s->message)
s->message(s, ev); s->message(s, ev);
return false;
} }
static void static bool
selectionclear_event(Window *w, void *aux, XSelectionClearEvent *ev) { selectionclear_event(Window *w, void *aux, XSelectionClearEvent *ev) {
Selection *s; Selection *s;
@ -111,9 +112,10 @@ selectionclear_event(Window *w, void *aux, XSelectionClearEvent *ev) {
s = aux; s = aux;
s->time_end = ev->time; s->time_end = ev->time;
selection_release(s); selection_release(s);
return false;
} }
static void static bool
selectionrequest_event(Window *w, void *aux, XSelectionRequestEvent *ev) { selectionrequest_event(Window *w, void *aux, XSelectionRequestEvent *ev) {
Selection *s; Selection *s;
@ -127,13 +129,14 @@ selectionrequest_event(Window *w, void *aux, XSelectionRequestEvent *ev) {
XGetAtomName(display, ev->property), "TIMESTAMP", XGetAtomName(display, ev->property), "TIMESTAMP",
&s->time_start, 1); &s->time_start, 1);
selection_notify(s, ev, true); selection_notify(s, ev, true);
return; return false;
} }
if(s->request) if(s->request)
s->request(s, ev); s->request(s, ev);
else else
selection_notify(s, ev, false); selection_notify(s, ev, false);
return false;
} }
static Handlers selection_handlers = { static Handlers selection_handlers = {

View File

@ -221,7 +221,7 @@ tray_update(void) {
tray_draw(tray.win->r); tray_draw(tray.win->r);
} }
static void static bool
config_event(Window *w, void *aux, XConfigureEvent *ev) { config_event(Window *w, void *aux, XConfigureEvent *ev) {
USED(aux); USED(aux);
@ -239,19 +239,22 @@ config_event(Window *w, void *aux, XConfigureEvent *ev) {
Pt(ev->border_width, ev->border_width)); Pt(ev->border_width, ev->border_width));
restrut(w, tray.orientation); restrut(w, tray.orientation);
} }
return false;
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *ev) { expose_event(Window *w, void *aux, XExposeEvent *ev) {
USED(w, aux, ev); USED(w, aux, ev);
tray_draw(tray.win->r); tray_draw(tray.win->r);
return false;
} }
static void static bool
message_event(Window *w, void *aux, XClientMessageEvent *ev) { message_event(Window *w, void *aux, XClientMessageEvent *ev) {
Dprint("tray_message: %s\n", XGetAtomName(display, ev->message_type)); Dprint("tray_message: %s\n", XGetAtomName(display, ev->message_type));
return false;
} }
static Handlers handlers = { static Handlers handlers = {
@ -260,12 +263,13 @@ static Handlers handlers = {
.expose = expose_event, .expose = expose_event,
}; };
static void static bool
property_event(Window *w, void *aux, XPropertyEvent *ev) { property_event(Window *w, void *aux, XPropertyEvent *ev) {
if(ev->atom == NET("CURRENT_DESKTOP")) if(ev->atom == NET("CURRENT_DESKTOP"))
tray_resize(tray.r); tray_resize(tray.r);
Debug if(ev->atom == NET("CURRENT_DESKTOP")) Debug if(ev->atom == NET("CURRENT_DESKTOP"))
print("property_event(_NET_CURRENT_DESKTOP)\n"); print("property_event(_NET_CURRENT_DESKTOP)\n");
return false;
} }
static Handlers root_handlers = { static Handlers root_handlers = {

View File

@ -92,16 +92,17 @@ xembed_sendmessage(XEmbed *xembed, long message, long detail, long data1, long d
traperrors(false); traperrors(false);
} }
static void static bool
destroy_event(Window *w, void *aux, XDestroyWindowEvent *ev) { destroy_event(Window *w, void *aux, XDestroyWindowEvent *ev) {
XEmbed *xembed; XEmbed *xembed;
xembed = aux; xembed = aux;
xembed->flags = DEAD; xembed->flags = DEAD;
xembed_disown(xembed); xembed_disown(xembed);
return false;
} }
static void static bool
property_event(Window *w, void *aux, XPropertyEvent *ev) { property_event(Window *w, void *aux, XPropertyEvent *ev) {
XEmbed *xembed; XEmbed *xembed;
@ -110,9 +111,10 @@ property_event(Window *w, void *aux, XPropertyEvent *ev) {
xembed = aux; xembed = aux;
if(ev->atom == xatom("_XEMBED_INFO")) if(ev->atom == xatom("_XEMBED_INFO"))
xembed_updateinfo(xembed); xembed_updateinfo(xembed);
return false;
} }
static void static bool
reparent_event(Window *w, void *aux, XReparentEvent *ev) { reparent_event(Window *w, void *aux, XReparentEvent *ev) {
XEmbed *xembed; XEmbed *xembed;
@ -121,6 +123,7 @@ reparent_event(Window *w, void *aux, XReparentEvent *ev) {
xembed->flags = DEAD; xembed->flags = DEAD;
xembed_disown(xembed); xembed_disown(xembed);
} }
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -245,7 +245,7 @@ findbar(WMScreen *s, Point p) {
return nil; return nil;
} }
static void static bool
bdown_event(Window *w, void *aux, XButtonPressedEvent *e) { bdown_event(Window *w, void *aux, XButtonPressedEvent *e) {
WMScreen *s; WMScreen *s;
Bar *b; Bar *b;
@ -258,9 +258,10 @@ bdown_event(Window *w, void *aux, XButtonPressedEvent *e) {
b = findbar(s, Pt(e->x, e->y)); b = findbar(s, Pt(e->x, e->y));
if(b) if(b)
event("%sBarMouseDown %d %s\n", barside[b->bar], e->button, b->name); event("%sBarMouseDown %d %s\n", barside[b->bar], e->button, b->name);
return false;
} }
static void static bool
bup_event(Window *w, void *aux, XButtonPressedEvent *e) { bup_event(Window *w, void *aux, XButtonPressedEvent *e) {
WMScreen *s; WMScreen *s;
Bar *b; Bar *b;
@ -269,6 +270,7 @@ bup_event(Window *w, void *aux, XButtonPressedEvent *e) {
b = findbar(s, Pt(e->x, e->y)); b = findbar(s, Pt(e->x, e->y));
if(b) if(b)
event("%sBarClick %d %s\n", barside[b->bar], e->button, b->name); event("%sBarClick %d %s\n", barside[b->bar], e->button, b->name);
return false;
} }
static Rectangle static Rectangle
@ -285,10 +287,11 @@ dndmotion_event(Window *w, void *aux, Point p) {
return ZR; return ZR;
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *e) { expose_event(Window *w, void *aux, XExposeEvent *e) {
USED(w, e); USED(w, e);
bar_draw(aux); bar_draw(aux);
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -783,7 +783,7 @@ updatemwm(Client *c) {
} }
} }
void bool
client_prop(Client *c, Atom a) { client_prop(Client *c, Atom a) {
WinHints h; WinHints h;
XWMHints *wmh; XWMHints *wmh;
@ -801,8 +801,7 @@ client_prop(Client *c, Atom a) {
else else
switch (a) { switch (a) {
default: default:
ewmh_prop(c, a); return true;
break;
case XA_WM_TRANSIENT_FOR: case XA_WM_TRANSIENT_FOR:
XGetTransientForHint(display, c->w.xid, &c->trans); XGetTransientForHint(display, c->w.xid, &c->trans);
break; break;
@ -838,10 +837,11 @@ client_prop(Client *c, Atom a) {
client_updatename(c); client_updatename(c);
break; break;
} }
return false;
} }
/* Handlers */ /* Handlers */
static void static bool
configreq_event(Window *w, void *aux, XConfigureRequestEvent *e) { configreq_event(Window *w, void *aux, XConfigureRequestEvent *e) {
Rectangle r, cr; Rectangle r, cr;
Client *c; Client *c;
@ -873,16 +873,18 @@ configreq_event(Window *w, void *aux, XConfigureRequestEvent *e) {
c->sel->floatr = r; c->sel->floatr = r;
client_configure(c); client_configure(c);
} }
return false;
} }
static void static bool
destroy_event(Window *w, void *aux, XDestroyWindowEvent *e) { destroy_event(Window *w, void *aux, XDestroyWindowEvent *e) {
USED(w, e); USED(w, e);
client_destroy(aux); client_destroy(aux);
return false;
} }
static void static bool
enter_event(Window *w, void *aux, XCrossingEvent *e) { enter_event(Window *w, void *aux, XCrossingEvent *e) {
Client *c; Client *c;
@ -896,9 +898,10 @@ enter_event(Window *w, void *aux, XCrossingEvent *e) {
client_setcursor(c, cursor[CurNormal]); client_setcursor(c, cursor[CurNormal]);
}else }else
Dprint(DFocus, "enter_notify(%#C[NotifyInferior]%s)\n", c, c->name); Dprint(DFocus, "enter_notify(%#C[NotifyInferior]%s)\n", c, c->name);
return false;
} }
static void static bool
focusin_event(Window *w, void *aux, XFocusChangeEvent *e) { focusin_event(Window *w, void *aux, XFocusChangeEvent *e) {
Client *c, *old; Client *c, *old;
@ -916,9 +919,10 @@ focusin_event(Window *w, void *aux, XFocusChangeEvent *e) {
if(c->sel) if(c->sel)
frame_draw(c->sel); frame_draw(c->sel);
} }
return false;
} }
static void static bool
focusout_event(Window *w, void *aux, XFocusChangeEvent *e) { focusout_event(Window *w, void *aux, XFocusChangeEvent *e) {
Client *c; Client *c;
@ -932,9 +936,10 @@ focusout_event(Window *w, void *aux, XFocusChangeEvent *e) {
if(c->sel) if(c->sel)
frame_draw(c->sel); frame_draw(c->sel);
} }
return false;
} }
static void static bool
unmap_event(Window *w, void *aux, XUnmapEvent *e) { unmap_event(Window *w, void *aux, XUnmapEvent *e) {
Client *c; Client *c;
@ -942,9 +947,10 @@ unmap_event(Window *w, void *aux, XUnmapEvent *e) {
if(!e->send_event) if(!e->send_event)
c->unmapped--; c->unmapped--;
client_destroy(c); client_destroy(c);
return false;
} }
static void static bool
map_event(Window *w, void *aux, XMapEvent *e) { map_event(Window *w, void *aux, XMapEvent *e) {
Client *c; Client *c;
@ -953,17 +959,15 @@ map_event(Window *w, void *aux, XMapEvent *e) {
c = aux; c = aux;
if(c == selclient()) if(c == selclient())
client_focus(c); client_focus(c);
return false;
} }
static void static bool
property_event(Window *w, void *aux, XPropertyEvent *e) { property_event(Window *w, void *aux, XPropertyEvent *e) {
Client *c;
if(e->state == PropertyDelete) /* FIXME */ if(e->state == PropertyDelete) /* FIXME */
return; return true;
return client_prop(aux, e->atom);
c = aux;
client_prop(c, e->atom);
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -163,7 +163,7 @@ div_update_all(void) {
} }
/* Div Handlers */ /* Div Handlers */
static void static bool
bdown_event(Window *w, void *aux, XButtonEvent *e) { bdown_event(Window *w, void *aux, XButtonEvent *e) {
Divide *d; Divide *d;
@ -171,9 +171,10 @@ bdown_event(Window *w, void *aux, XButtonEvent *e) {
d = aux; d = aux;
mouse_resizecol(d); mouse_resizecol(d);
return false;
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *e) { expose_event(Window *w, void *aux, XExposeEvent *e) {
Divide *d; Divide *d;
@ -181,6 +182,7 @@ expose_event(Window *w, void *aux, XExposeEvent *e) {
d = aux; d = aux;
drawdiv(d); drawdiv(d);
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -29,15 +29,6 @@ event_configurenotify(XConfigureEvent *ev) {
event_handle(w, config, ev); event_handle(w, config, ev);
} }
void
event_clientmessage(XClientMessageEvent *ev) {
if(ewmh_clientmessage(ev))
return;
if(xdnd_clientmessage(ev))
return;
}
void void
event_destroynotify(XDestroyWindowEvent *ev) { event_destroynotify(XDestroyWindowEvent *ev) {
Window *w; Window *w;

View File

@ -10,6 +10,9 @@ Window *ewmhwin;
static void ewmh_getwinstate(Client*); static void ewmh_getwinstate(Client*);
static void ewmh_setstate(Client*, Atom, int); static void ewmh_setstate(Client*, Atom, int);
static Handlers client_handlers;
static Handlers root_handlers;
#define Net(x) ("_NET_" x) #define Net(x) ("_NET_" x)
#define Action(x) Net("WM_ACTION_" x) #define Action(x) Net("WM_ACTION_" x)
#define State(x) Net("WM_STATE_" x) #define State(x) Net("WM_STATE_" x)
@ -37,6 +40,8 @@ ewmh_init(void) {
changeprop_long(&scr.root, Net("DESKTOP_VIEWPORT"), "CARDINAL", changeprop_long(&scr.root, Net("DESKTOP_VIEWPORT"), "CARDINAL",
zz, 2); zz, 2);
pushhandler(&scr.root, &root_handlers, nil);
long supported[] = { long supported[] = {
/* Misc */ /* Misc */
NET("SUPPORTED"), NET("SUPPORTED"),
@ -129,6 +134,7 @@ ewmh_initclient(Client *c) {
ewmh_getwinstate(c); ewmh_getwinstate(c);
ewmh_getstrut(c); ewmh_getstrut(c);
ewmh_updateclientlist(); ewmh_updateclientlist();
pushhandler(&c->w, &client_handlers, c);
} }
void void
@ -144,6 +150,74 @@ ewmh_destroyclient(Client *c) {
free(c->strut); free(c->strut);
} }
static bool
event_client_clientmessage(Window *w, void *aux, XClientMessageEvent *e) {
Client *c;
ulong *l;
ulong msg;
int action;
c = aux;
l = (ulong*)e->data.l;
msg = e->message_type;
Dprint(DEwmh, "ClientMessage: %A\n", msg);
if(msg == NET("WM_STATE")) {
enum {
StateUnset,
StateSet,
StateToggle,
};
if(e->format != 32)
return false;
switch(l[0]) {
case StateUnset: action = Off; break;
case StateSet: action = On; break;
case StateToggle: action = Toggle; break;
default: return false;
}
Dprint(DEwmh, "\tAction: %s\n", TOGGLE(action));
ewmh_setstate(c, l[1], action);
ewmh_setstate(c, l[2], action);
return false;
}else
if(msg == NET("ACTIVE_WINDOW")) {
if(e->format != 32)
return false;
Dprint(DEwmh, "\tsource: %ld\n", l[0]);
Dprint(DEwmh, "\twindow: 0x%lx\n", e->window);
Dprint(DEwmh, "\tclient: %C\n", c);
if(l[0] == SourceClient && abs(event_xtime - l[1]) > 5000)
return false;
if(l[0] == SourceClient || l[0] == SourcePager)
focus(c, true);
return false;
}else
if(msg == NET("CLOSE_WINDOW")) {
if(e->format != 32)
return false;
Dprint(DEwmh, "\tsource: %ld\n", l[0]);
Dprint(DEwmh, "\twindow: 0x%lx\n", e->window);
client_kill(c, true);
return false;
}
return false;
}
static bool
event_client_property(Window *w, void *aux, XPropertyEvent *e) {
return ewmh_prop(aux, e->atom);
}
static Handlers client_handlers = {
.message = event_client_clientmessage,
.property = event_client_property,
};
static void static void
pingtimeout(long id, void *v) { pingtimeout(long id, void *v) {
Client *c; Client *c;
@ -171,7 +245,7 @@ ewmh_pingclient(Client *c) {
e->timer = ixp_settimer(&srv, PingTime, pingtimeout, c); e->timer = ixp_settimer(&srv, PingTime, pingtimeout, c);
} }
int bool
ewmh_prop(Client *c, Atom a) { ewmh_prop(Client *c, Atom a) {
if(a == NET("WM_WINDOW_TYPE")) if(a == NET("WM_WINDOW_TYPE"))
ewmh_getwintype(c); ewmh_getwintype(c);
@ -179,8 +253,8 @@ ewmh_prop(Client *c, Atom a) {
if(a == NET("WM_STRUT_PARTIAL")) if(a == NET("WM_STRUT_PARTIAL"))
ewmh_getstrut(c); ewmh_getstrut(c);
else else
return 0; return true;
return 1; return false;
} }
typedef struct Prop Prop; typedef struct Prop Prop;
@ -335,70 +409,21 @@ ewmh_setstate(Client *c, Atom state, int action) {
client_seturgent(c, action, UrgClient); client_seturgent(c, action, UrgClient);
} }
int static bool
ewmh_clientmessage(XClientMessageEvent *e) { event_root_clientmessage(Window *w, void *aux, XClientMessageEvent *e) {
Client *c; Client *c;
View *v; View *v;
ulong *l; ulong *l;
ulong msg; ulong msg;
int action, i; int i;
l = (ulong*)e->data.l; l = (ulong*)e->data.l;
msg = e->message_type; msg = e->message_type;
Dprint(DEwmh, "ClientMessage: %A\n", msg); Dprint(DEwmh, "ClientMessage: %A\n", msg);
if(msg == NET("WM_STATE")) {
enum {
StateUnset,
StateSet,
StateToggle,
};
if(e->format != 32)
return -1;
c = win2client(e->window);
if(c == nil)
return 0;
switch(l[0]) {
case StateUnset: action = Off; break;
case StateSet: action = On; break;
case StateToggle: action = Toggle; break;
default: return -1;
}
Dprint(DEwmh, "\tAction: %s\n", TOGGLE(action));
ewmh_setstate(c, l[1], action);
ewmh_setstate(c, l[2], action);
return 1;
}else
if(msg == NET("ACTIVE_WINDOW")) {
if(e->format != 32)
return -1;
Dprint(DEwmh, "\tsource: %ld\n", l[0]);
Dprint(DEwmh, "\twindow: 0x%lx\n", e->window);
c = win2client(e->window);
if(c == nil)
return 1;
Dprint(DEwmh, "\tclient: %C\n", c);
if(l[0] == SourceClient && abs(event_xtime - l[1]) > 5000)
return 1;
if(l[0] != SourceClient && l[0] != SourcePager)
return 1;
focus(c, true);
return 1;
}else
if(msg == NET("CLOSE_WINDOW")) {
if(e->format != 32)
return -1;
Dprint(DEwmh, "\tsource: %ld\n", l[0]);
Dprint(DEwmh, "\twindow: 0x%lx\n", e->window);
c = win2client(e->window);
if(c == nil)
return 1;
client_kill(c, true);
return 1;
}else
if(msg == NET("CURRENT_DESKTOP")) { if(msg == NET("CURRENT_DESKTOP")) {
if(e->format != 32) if(e->format != 32)
return -1; return false;
for(v=view, i=l[0]; v; v=v->next, i--) for(v=view, i=l[0]; v; v=v->next, i--)
if(i == 0) if(i == 0)
break; break;
@ -406,14 +431,14 @@ ewmh_clientmessage(XClientMessageEvent *e) {
if(i == 0) if(i == 0)
view_select(v->name); view_select(v->name);
return 1; return 1;
}else }
if(msg == xatom("WM_PROTOCOLS")) { if(msg == xatom("WM_PROTOCOLS")) {
if(e->format != 32) if(e->format != 32)
return 0; return false;
Dprint(DEwmh, "\t%A\n", l[0]); Dprint(DEwmh, "\t%A\n", l[0]);
if(l[0] == NET("WM_PING")) { if(l[0] == NET("WM_PING")) {
if(e->window != scr.root.xid) if(e->window != scr.root.xid)
return -1; return false;
c = win2client(l[2]); c = win2client(l[2]);
if(c == nil) if(c == nil)
return 1; return 1;
@ -424,13 +449,19 @@ ewmh_clientmessage(XClientMessageEvent *e) {
ixp_unsettimer(&srv, c->w.ewmh.timer); ixp_unsettimer(&srv, c->w.ewmh.timer);
c->w.ewmh.timer = 0; c->w.ewmh.timer = 0;
c->w.ewmh.ping = 0; c->w.ewmh.ping = 0;
return 1; return false;
} }
return false;
} }
return 0; return false;
} }
static Handlers root_handlers = {
.message = event_root_clientmessage,
};
void void
ewmh_framesize(Client *c) { ewmh_framesize(Client *c) {
Rectangle r; Rectangle r;

View File

@ -82,7 +82,7 @@ void client_kill(Client*, bool);
void client_manage(Client*); void client_manage(Client*);
void client_map(Client*); void client_map(Client*);
void client_message(Client*, char*, long); void client_message(Client*, char*, long);
void client_prop(Client*, Atom); bool client_prop(Client*, Atom);
void client_reparent(Client*, Window*, Point); void client_reparent(Client*, Window*, Point);
void client_resize(Client*, Rectangle); void client_resize(Client*, Rectangle);
void client_setcursor(Client*, Cursor); void client_setcursor(Client*, Cursor);
@ -142,7 +142,7 @@ void ewmh_getwintype(Client*);
void ewmh_init(void); void ewmh_init(void);
void ewmh_initclient(Client*); void ewmh_initclient(Client*);
void ewmh_pingclient(Client*); void ewmh_pingclient(Client*);
int ewmh_prop(Client*, Atom); bool ewmh_prop(Client*, Atom);
long ewmh_protocols(Window*); long ewmh_protocols(Window*);
void ewmh_updateclient(Client*); void ewmh_updateclient(Client*);
void ewmh_updateclientlist(void); void ewmh_updateclientlist(void);
@ -278,6 +278,5 @@ char* toutf8(const char*);
char* toutf8n(const char*, size_t); char* toutf8n(const char*, size_t);
/* xdnd.c */ /* xdnd.c */
int xdnd_clientmessage(XClientMessageEvent*);
void xdnd_initwindow(Window*); void xdnd_initwindow(Window*);

View File

@ -142,16 +142,17 @@ frame_restack(Frame *f, Frame *above) {
} }
/* Handlers */ /* Handlers */
static void static bool
bup_event(Window *w, void *aux, XButtonEvent *e) { bup_event(Window *w, void *aux, XButtonEvent *e) {
if((e->state & def.mod) != def.mod) if((e->state & def.mod) != def.mod)
XAllowEvents(display, ReplayPointer, e->time); XAllowEvents(display, ReplayPointer, e->time);
else else
XUngrabPointer(display, e->time); XUngrabPointer(display, e->time);
event("ClientClick %#C %d\n", aux, e->button); event("ClientClick %#C %d\n", aux, e->button);
return false;
} }
static void static bool
bdown_event(Window *w, void *aux, XButtonEvent *e) { bdown_event(Window *w, void *aux, XButtonEvent *e) {
Frame *f; Frame *f;
Client *c; Client *c;
@ -200,15 +201,17 @@ bdown_event(Window *w, void *aux, XButtonEvent *e) {
event("ClientMouseDown %#C %d\n", f->client, e->button); event("ClientMouseDown %#C %d\n", f->client, e->button);
} }
} }
return false;
} }
static void static bool
config_event(Window *w, void *aux, XConfigureEvent *e) { config_event(Window *w, void *aux, XConfigureEvent *e) {
USED(w, e); USED(w, e);
return false;
} }
static void static bool
enter_event(Window *w, void *aux, XCrossingEvent *e) { enter_event(Window *w, void *aux, XCrossingEvent *e) {
Client *c; Client *c;
Frame *f; Frame *f;
@ -224,9 +227,10 @@ enter_event(Window *w, void *aux, XCrossingEvent *e) {
focus(f->client, false); focus(f->client, false);
} }
mouse_checkresize(f, Pt(e->x, e->y), false); mouse_checkresize(f, Pt(e->x, e->y), false);
return false;
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *e) { expose_event(Window *w, void *aux, XExposeEvent *e) {
Client *c; Client *c;
@ -238,14 +242,16 @@ expose_event(Window *w, void *aux, XExposeEvent *e) {
else else
fprint(2, "Badness: Expose event on a client frame which shouldn't be visible: %#C\n", fprint(2, "Badness: Expose event on a client frame which shouldn't be visible: %#C\n",
c); c);
return false;
} }
static void static bool
motion_event(Window *w, void *aux, XMotionEvent *e) { motion_event(Window *w, void *aux, XMotionEvent *e) {
Client *c; Client *c;
c = aux; c = aux;
mouse_checkresize(c->sel, Pt(e->x, e->y), false); mouse_checkresize(c->sel, Pt(e->x, e->y), false);
return false;
} }
Handlers framehandler = { Handlers framehandler = {

View File

@ -98,7 +98,7 @@ framedestroy(Framewin *f) {
free(f); free(f);
} }
static void static bool
expose_event(Window *w, void *aux, XExposeEvent *e) { expose_event(Window *w, void *aux, XExposeEvent *e) {
Rectangle r; Rectangle r;
Framewin *f; Framewin *f;
@ -118,6 +118,7 @@ expose_event(Window *w, void *aux, XExposeEvent *e) {
border(buf, insetrect(f->grabbox, -f->grabbox.min.x), 1, c->border); border(buf, insetrect(f->grabbox, -f->grabbox.min.x), 1, c->border);
copyimage(w, r, buf, ZP); copyimage(w, r, buf, ZP);
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -28,11 +28,12 @@ quad_cursor(Align align) {
} }
} }
static void static bool
cwin_expose(Window *w, void *aux, XExposeEvent *e) { cwin_expose(Window *w, void *aux, XExposeEvent *e) {
fill(w, rectsubpt(w->r, w->r.min), def.focuscolor.bg); fill(w, rectsubpt(w->r, w->r.min), def.focuscolor.bg);
fill(w, w->r, def.focuscolor.bg); fill(w, w->r, def.focuscolor.bg);
return false;
} }
static Handlers chandler = { static Handlers chandler = {

View File

@ -23,45 +23,49 @@ root_init(void) {
sethandler(&scr.root, &handlers); sethandler(&scr.root, &handlers);
} }
static void static bool
enter_event(Window *w, void *aux, XCrossingEvent *e) { enter_event(Window *w, void *aux, XCrossingEvent *e) {
disp.sel = true; disp.sel = true;
frame_draw_all(); frame_draw_all();
return false;
} }
static void static bool
leave_event(Window *w, void *aux, XCrossingEvent *e) { leave_event(Window *w, void *aux, XCrossingEvent *e) {
if(!e->same_screen) { if(!e->same_screen) {
disp.sel = false; disp.sel = false;
frame_draw_all(); frame_draw_all();
} }
return false;
} }
static void static bool
focusin_event(Window *w, void *aux, XFocusChangeEvent *e) { focusin_event(Window *w, void *aux, XFocusChangeEvent *e) {
if(e->mode == NotifyGrab) if(e->mode == NotifyGrab)
disp.hasgrab = &c_root; disp.hasgrab = &c_root;
return false;
} }
static void static bool
mapreq_event(Window *w, void *aux, XMapRequestEvent *e) { mapreq_event(Window *w, void *aux, XMapRequestEvent *e) {
XWindowAttributes wa; XWindowAttributes wa;
if(!XGetWindowAttributes(display, e->window, &wa)) if(!XGetWindowAttributes(display, e->window, &wa))
return; return false;
if(wa.override_redirect) { if(wa.override_redirect) {
/* Do I really want these? */ /* Do I really want these? */
/* Probably not. /* Probably not.
XSelectInput(display, e->window, XSelectInput(display, e->window,
PropertyChangeMask | StructureNotifyMask); PropertyChangeMask | StructureNotifyMask);
*/ */
return; return false;
} }
if(!win2client(e->window)) if(!win2client(e->window))
client_create(e->window, &wa); client_create(e->window, &wa);
return false;
} }
static void static bool
motion_event(Window *w, void *aux, XMotionEvent *e) { motion_event(Window *w, void *aux, XMotionEvent *e) {
Rectangle r, r2; Rectangle r, r2;
@ -69,13 +73,15 @@ motion_event(Window *w, void *aux, XMotionEvent *e) {
r2 = constrain(r, 0); r2 = constrain(r, 0);
if(!eqrect(r, r2)) if(!eqrect(r, r2))
warppointer(r2.min); warppointer(r2.min);
return false;
} }
static void static bool
kdown_event(Window *w, void *aux, XKeyEvent *e) { kdown_event(Window *w, void *aux, XKeyEvent *e) {
e->state &= valid_mask; e->state &= valid_mask;
kpress(w->xid, e->state, (KeyCode)e->keycode); kpress(w->xid, e->state, (KeyCode)e->keycode);
return false;
} }
static Handlers handlers = { static Handlers handlers = {

View File

@ -4,12 +4,15 @@
#include "dat.h" #include "dat.h"
#include "fns.h" #include "fns.h"
static Handlers handlers;
void void
xdnd_initwindow(Window *w) { xdnd_initwindow(Window *w) {
long l; long l;
l = 3; /* They are insane. Why is this an ATOM?! */ l = 3; /* They are insane. Why is this an ATOM?! */
changeprop_long(w, "XdndAware", "ATOM", &l, 1); changeprop_long(w, "XdndAware", "ATOM", &l, 1);
pushhandler(w, &handlers, nil);
} }
typedef struct Dnd Dnd; typedef struct Dnd Dnd;
@ -18,9 +21,8 @@ struct Dnd {
Rectangle r; Rectangle r;
}; };
int static bool
xdnd_clientmessage(XClientMessageEvent *e) { clientmessage_event(Window *w, void *aux, XClientMessageEvent *e) {
Window *w;
Dnd *dnd; Dnd *dnd;
long *l; long *l;
Rectangle r; Rectangle r;
@ -35,34 +37,28 @@ xdnd_clientmessage(XClientMessageEvent *e) {
if(msg == xatom("XdndEnter")) { if(msg == xatom("XdndEnter")) {
if(e->format != 32) if(e->format != 32)
return -1; return false;
w = findwin(e->window); if(w->dnd == nil)
if(w) { w->dnd = emallocz(sizeof *dnd);
if(w->dnd == nil) dnd = w->dnd;
w->dnd = emallocz(sizeof *dnd); dnd->source = l[0];
dnd = w->dnd; dnd->r = ZR;
dnd->source = l[0]; return false;
dnd->r = ZR;
}
return 1;
}else }else
if(msg == xatom("XdndLeave")) { if(msg == xatom("XdndLeave")) {
if(e->format != 32) if(e->format != 32)
return -1; return false;
w = findwin(e->window); if(w->dnd) {
if(w && w->dnd) {
free(w->dnd); free(w->dnd);
w->dnd = nil; w->dnd = nil;
} }
return 1; return false;
}else }else
if(msg == xatom("XdndPosition")) { if(msg == xatom("XdndPosition")) {
if(e->format != 32) if(e->format != 32)
return -1; return false;
r = ZR; r = ZR;
w = findwin(e->window); dnd = w->dnd;
if(w)
dnd = w->dnd;
if(dnd) { if(dnd) {
p.x = (ulong)l[2] >> 16; p.x = (ulong)l[2] >> 16;
p.y = (ulong)l[2] & 0xffff; p.y = (ulong)l[2] & 0xffff;
@ -80,9 +76,13 @@ xdnd_clientmessage(XClientMessageEvent *e) {
pos = (r.min.x<<16) | r.min.y; pos = (r.min.x<<16) | r.min.y;
siz = (Dx(r)<<16) | Dy(r); siz = (Dx(r)<<16) | Dy(r);
sendmessage(window(l[0]), "XdndStatus", e->window, 0, pos, siz, 0); sendmessage(window(l[0]), "XdndStatus", e->window, 0, pos, siz, 0);
return 1; return false;
} }
return 0; return true;
} }
static Handlers handlers = {
.message = clientmessage_event
};

View File

@ -95,28 +95,28 @@ struct Font {
struct Handlers { struct Handlers {
Rectangle (*dndmotion)(Window*, void*, Point); Rectangle (*dndmotion)(Window*, void*, Point);
void (*bdown)(Window*, void*, XButtonEvent*); bool (*bdown)(Window*, void*, XButtonEvent*);
void (*bup)(Window*, void*, XButtonEvent*); bool (*bup)(Window*, void*, XButtonEvent*);
void (*config)(Window*, void*, XConfigureEvent*); bool (*config)(Window*, void*, XConfigureEvent*);
void (*configreq)(Window*, void*, XConfigureRequestEvent*); bool (*configreq)(Window*, void*, XConfigureRequestEvent*);
void (*destroy)(Window*, void*, XDestroyWindowEvent*); bool (*destroy)(Window*, void*, XDestroyWindowEvent*);
void (*enter)(Window*, void*, XCrossingEvent*); bool (*enter)(Window*, void*, XCrossingEvent*);
void (*expose)(Window*, void*, XExposeEvent*); bool (*expose)(Window*, void*, XExposeEvent*);
void (*focusin)(Window*, void*, XFocusChangeEvent*); bool (*focusin)(Window*, void*, XFocusChangeEvent*);
void (*focusout)(Window*, void*, XFocusChangeEvent*); bool (*focusout)(Window*, void*, XFocusChangeEvent*);
void (*kdown)(Window*, void*, XKeyEvent*); bool (*kdown)(Window*, void*, XKeyEvent*);
void (*kup)(Window*, void*, XKeyEvent*); bool (*kup)(Window*, void*, XKeyEvent*);
void (*leave)(Window*, void*, XCrossingEvent*); bool (*leave)(Window*, void*, XCrossingEvent*);
void (*map)(Window*, void*, XMapEvent*); bool (*map)(Window*, void*, XMapEvent*);
void (*mapreq)(Window*, void*, XMapRequestEvent*); bool (*mapreq)(Window*, void*, XMapRequestEvent*);
void (*message)(Window*, void*, XClientMessageEvent*); bool (*message)(Window*, void*, XClientMessageEvent*);
void (*motion)(Window*, void*, XMotionEvent*); bool (*motion)(Window*, void*, XMotionEvent*);
void (*property)(Window*, void*, XPropertyEvent*); bool (*property)(Window*, void*, XPropertyEvent*);
void (*reparent)(Window*, void*, XReparentEvent*); bool (*reparent)(Window*, void*, XReparentEvent*);
void (*selection)(Window*, void*, XSelectionEvent*); bool (*selection)(Window*, void*, XSelectionEvent*);
void (*selectionclear)(Window*, void*, XSelectionClearEvent*); bool (*selectionclear)(Window*, void*, XSelectionClearEvent*);
void (*selectionrequest)(Window*, void*, XSelectionRequestEvent*); bool (*selectionrequest)(Window*, void*, XSelectionRequestEvent*);
void (*unmap)(Window*, void*, XUnmapEvent*); bool (*unmap)(Window*, void*, XUnmapEvent*);
}; };
struct HandlersLink { struct HandlersLink {

View File

@ -3,7 +3,7 @@
*/ */
#include "event.h" #include "event.h"
typedef void (*Handler)(Window*, void*, XEvent*); typedef bool (*Handler)(Window*, void*, XEvent*);
void (*event_debug)(XEvent*); void (*event_debug)(XEvent*);
long event_xtime; long event_xtime;
bool event_looprunning; bool event_looprunning;
@ -37,16 +37,14 @@ _event_handle(Window *w, ulong offset, XEvent *event) {
Handler f; Handler f;
HandlersLink *l; HandlersLink *l;
if(w->handler && (f = structmember(w->handler, Handler, offset))) { if(w->handler && (f = structmember(w->handler, Handler, offset)))
f(w, w->aux, event); if(!f(w, w->aux, event))
return;
}
for(l=w->handler_link; l; l=l->next) {
if(f = structmember(l->handler, Handler, offset)) {
f(w, l->aux, event);
return; return;
}
} for(l=w->handler_link; l; l=l->next)
if((f = structmember(l->handler, Handler, offset)))
if(!f(w, l->aux, event))
return;
} }
void void