mirror of https://github.com/0intro/wmii
New event processing model.
This commit is contained in:
parent
b67d9d3848
commit
d8a7ede21f
|
@ -8,7 +8,32 @@
|
|||
#include "dat.h"
|
||||
#include "fns.h"
|
||||
|
||||
Bar *free_bars = nil;
|
||||
static Handlers handlers;
|
||||
static Bar *free_bars;
|
||||
|
||||
void
|
||||
initbar(WMScreen *s) {
|
||||
WinAttr wa;
|
||||
|
||||
s->brect = s->rect;
|
||||
s->brect.min.y = s->brect.max.y - labelh(def.font);
|
||||
|
||||
wa.override_redirect = 1;
|
||||
wa.background_pixmap = ParentRelative;
|
||||
wa.event_mask =
|
||||
ExposureMask
|
||||
| ButtonReleaseMask
|
||||
| FocusChangeMask
|
||||
| SubstructureRedirectMask
|
||||
| SubstructureNotifyMask;
|
||||
|
||||
s->barwin = createwindow(&scr.root, s->brect, scr.depth, InputOutput, &wa,
|
||||
CWOverrideRedirect
|
||||
| CWBackPixmap
|
||||
| CWEventMask);
|
||||
sethandler(s->barwin, &handlers);
|
||||
mapwin(s->barwin);
|
||||
}
|
||||
|
||||
Bar *
|
||||
create_bar(Bar **bp, char *name) {
|
||||
|
@ -147,3 +172,29 @@ bar_of_name(Bar *bp, const char *name) {
|
|||
break;
|
||||
return b;
|
||||
}
|
||||
|
||||
static void
|
||||
bup_event(Window *w, XButtonPressedEvent *e) {
|
||||
Bar *b;
|
||||
|
||||
for(b=screen->bar[BarLeft]; b; b=b->next)
|
||||
if(ptinrect(Pt(e->x, e->y), b->r)) {
|
||||
write_event("LeftBarClick %d %s\n", e->button, b->name);
|
||||
return;
|
||||
}
|
||||
for(b=screen->bar[BarRight]; b; b=b->next)
|
||||
if(ptinrect(Pt(e->x, e->y), b->r)) {
|
||||
write_event("RightBarClick %d %s\n", e->button, b->name);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
expose_event(Window *w, XExposeEvent *e) {
|
||||
draw_bar(screen);
|
||||
}
|
||||
|
||||
static Handlers handlers = {
|
||||
.bup = bup_event,
|
||||
.expose = expose_event,
|
||||
};
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
#include "fns.h"
|
||||
|
||||
static void update_client_name(Client *c);
|
||||
static Handlers handlers;
|
||||
|
||||
static char Ebadcmd[] = "bad command",
|
||||
Ebadvalue[] = "bad value";
|
||||
|
@ -64,7 +65,10 @@ create_client(XWindow w, XWindowAttributes *wa) {
|
|||
| CWEventMask
|
||||
| CWBackPixmap
|
||||
| CWBackingStore);
|
||||
XSync(display, False);
|
||||
c->framewin->aux = c;
|
||||
c->win.aux = c;
|
||||
sethandler(c->framewin, &framehandler);
|
||||
sethandler(&c->win, &handlers);
|
||||
|
||||
for(t=&client ;; t=&(*t)->next)
|
||||
if(!*t) {
|
||||
|
@ -106,8 +110,9 @@ destroy_client(Client *c) {
|
|||
reparent_client(c, &scr.root, c->rect.min);
|
||||
|
||||
destroywindow(c->framewin);
|
||||
XSync(display, False);
|
||||
sethandler(&c->win, nil);
|
||||
|
||||
XSync(display, False);
|
||||
XSetErrorHandler(wmii_error_handler);
|
||||
XUngrabServer(display);
|
||||
flushevents(EnterWindowMask, False);
|
||||
|
@ -150,6 +155,146 @@ manage_client(Client *c) {
|
|||
flushevents(EnterWindowMask, False);
|
||||
}
|
||||
|
||||
/* Handlers */
|
||||
static void
|
||||
configreq_event(Window *w, XConfigureRequestEvent *e) {
|
||||
Rectangle *frect;
|
||||
Frame *f;
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
f = c->sel;
|
||||
|
||||
gravitate_client(c, True);
|
||||
if(e->value_mask & CWX)
|
||||
c->rect.min.x = e->x;
|
||||
if(e->value_mask & CWY)
|
||||
c->rect.min.y = e->y;
|
||||
if(e->value_mask & CWWidth)
|
||||
c->rect.max.x = c->rect.min.x + e->width;
|
||||
if(e->value_mask & CWHeight)
|
||||
c->rect.max.y = c->rect.min.y + e->height;
|
||||
if(e->value_mask & CWBorderWidth)
|
||||
c->border = e->border_width;
|
||||
gravitate_client(c, False);
|
||||
|
||||
if((Dx(c->rect) == Dx(screen->rect))
|
||||
&& (Dy(c->rect) == Dy(screen->rect))) {
|
||||
c->fullscreen = True;
|
||||
if(c->sel) {
|
||||
if(!c->sel->area->floating)
|
||||
send_to_area(c->sel->view->area, c->sel);
|
||||
focus_client(c);
|
||||
restack_view(c->sel->view);
|
||||
}
|
||||
}
|
||||
|
||||
if(c->sel->area->floating)
|
||||
frect=&c->sel->rect;
|
||||
else
|
||||
frect=&c->sel->revert;
|
||||
|
||||
*frect = insetrect(c->rect, -def.border);
|
||||
frect->min.y -= labelh(def.font);
|
||||
|
||||
if(c->sel->area->floating || c->fullscreen)
|
||||
resize_client(c, frect);
|
||||
else
|
||||
configure_client(c);
|
||||
}
|
||||
|
||||
static void
|
||||
destroy_event(Window *w, XDestroyWindowEvent *e) {
|
||||
destroy_client(w->aux);
|
||||
}
|
||||
|
||||
static void
|
||||
enter_event(Window *w, XCrossingEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
if(e->detail != NotifyInferior) {
|
||||
if(screen->focus != c) {
|
||||
if(verbose) fprintf(stderr, "enter_notify(c) => %s\n", c->name);
|
||||
focus(c, False);
|
||||
}
|
||||
set_cursor(c, cursor[CurNormal]);
|
||||
}else if(verbose) fprintf(stderr, "enter_notify(c[NotifyInferior]) => %s\n", c->name);
|
||||
}
|
||||
|
||||
static void
|
||||
focusin_event(Window *w, XFocusChangeEvent *e) {
|
||||
Client *c, *old;
|
||||
|
||||
c = w->aux;
|
||||
|
||||
//print_focus(c, c->name);
|
||||
if(e->mode == NotifyGrab)
|
||||
screen->hasgrab = c;
|
||||
|
||||
old = screen->focus;
|
||||
screen->focus = c;
|
||||
if(c != old) {
|
||||
update_client_grab(c);
|
||||
if(c->sel)
|
||||
draw_frame(c->sel);
|
||||
if(old && old->sel)
|
||||
draw_frame(old->sel);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
focusout_event(Window *w, XFocusChangeEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
|
||||
if((e->mode == NotifyWhileGrabbed) && (screen->hasgrab != &c_root)) {
|
||||
if((screen->focus)
|
||||
&& (screen->hasgrab != screen->focus))
|
||||
screen->hasgrab = screen->focus;
|
||||
if(screen->hasgrab == c)
|
||||
return;
|
||||
}else if(e->mode != NotifyGrab) {
|
||||
if(screen->focus == c) {
|
||||
//print_focus(&c_magic, "<magic>");
|
||||
screen->focus = &c_magic;
|
||||
}
|
||||
update_client_grab(c);
|
||||
if(c->sel)
|
||||
draw_frame(c->sel);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
unmap_event(Window *w, XUnmapEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
if(!e->send_event)
|
||||
c->unmapped--;
|
||||
destroy_client(c);
|
||||
}
|
||||
|
||||
static void
|
||||
map_event(Window *w, XMapEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
if(c == selclient())
|
||||
focus_client(c);
|
||||
}
|
||||
|
||||
static Handlers handlers = {
|
||||
.configreq = configreq_event,
|
||||
.destroy = destroy_event,
|
||||
.enter = enter_event,
|
||||
.focusin = focusin_event,
|
||||
.focusout = focusout_event,
|
||||
.map = map_event,
|
||||
.unmap = unmap_event,
|
||||
};
|
||||
|
||||
Client *
|
||||
selclient() {
|
||||
if(screen->sel && screen->sel->sel->sel)
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
|
||||
static Image *divimg, *divmask;
|
||||
static CTuple divc;
|
||||
static Handlers divhandler;
|
||||
|
||||
char *modes[] = {
|
||||
[Coldefault] = "default",
|
||||
|
@ -56,9 +57,11 @@ get_div(Divide **dp) {
|
|||
| ButtonPressMask
|
||||
| ButtonReleaseMask;
|
||||
d->w = createwindow(&scr.root, Rect(0, 0, 1, 1), scr.depth, InputOutput, &wa,
|
||||
CWOverrideRedirect
|
||||
| CWEventMask
|
||||
| CWCursor);
|
||||
CWOverrideRedirect
|
||||
| CWEventMask
|
||||
| CWCursor);
|
||||
d->w->aux = d;
|
||||
sethandler(d->w, &divhandler);
|
||||
|
||||
*dp = d;
|
||||
return d;
|
||||
|
@ -159,6 +162,28 @@ draw_div(Divide *d) {
|
|||
setshapemask(d->w, divmask, ZP);
|
||||
}
|
||||
|
||||
/* Div Handlers */
|
||||
static void
|
||||
bdown_event(Window *w, XButtonEvent *e) {
|
||||
Divide *d;
|
||||
|
||||
d = w->aux;
|
||||
mouse_resizecol(d);
|
||||
}
|
||||
|
||||
static void
|
||||
expose_event(Window *w, XExposeEvent *e) {
|
||||
Divide *d;
|
||||
|
||||
d = w->aux;
|
||||
draw_div(d);
|
||||
}
|
||||
|
||||
static Handlers divhandler = {
|
||||
.bdown = bdown_event,
|
||||
.expose = expose_event,
|
||||
};
|
||||
|
||||
Area *
|
||||
new_column(View *v, Area *pos, uint w) {
|
||||
Area *a;
|
||||
|
|
|
@ -211,6 +211,8 @@ Divide *divs;
|
|||
Client c_magic;
|
||||
Client c_root;
|
||||
|
||||
Handlers framehandler;
|
||||
|
||||
char buffer[8092];
|
||||
|
||||
/* IXP */
|
||||
|
|
247
cmd/wmii/event.c
247
cmd/wmii/event.c
|
@ -31,79 +31,24 @@ flushevents(long event_mask, Bool dispatch) {
|
|||
static void
|
||||
buttonrelease(XEvent *e) {
|
||||
XButtonPressedEvent *ev;
|
||||
Frame *f;
|
||||
Bar *b;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xbutton;
|
||||
if(ev->window == screen->barwin->w) {
|
||||
for(b=screen->bar[BarLeft]; b; b=b->next)
|
||||
if(ptinrect(Pt(ev->x, ev->y), b->r)) {
|
||||
write_event("LeftBarClick %d %s\n", ev->button, b->name);
|
||||
return;
|
||||
}
|
||||
for(b=screen->bar[BarRight]; b; b=b->next)
|
||||
if(ptinrect(Pt(ev->x, ev->y), b->r)) {
|
||||
write_event("RightBarClick %d %s\n", ev->button, b->name);
|
||||
return;
|
||||
}
|
||||
}
|
||||
else if((f = win2frame(ev->window)))
|
||||
write_event("ClientClick 0x%x %d\n", f->client->win.w, ev->button);
|
||||
if((w = findwin(e->xany.window)))
|
||||
if(w->handler->bup)
|
||||
w->handler->bup(w, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
buttonpress(XEvent *e) {
|
||||
XButtonPressedEvent *ev;
|
||||
Divide *d;
|
||||
Frame *f;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xbutton;
|
||||
if((f = win2frame(ev->window))) {
|
||||
if((ev->state & def.mod) == def.mod) {
|
||||
switch(ev->button) {
|
||||
case Button1:
|
||||
do_mouse_resize(f->client, False, CENTER);
|
||||
focus(f->client, True);
|
||||
frame_to_top(f);
|
||||
focus(f->client, True);
|
||||
break;
|
||||
case Button3:
|
||||
do_mouse_resize(f->client, False,
|
||||
quadrant(f->rect, Pt(ev->x_root, ev->y_root)));
|
||||
frame_to_top(f);
|
||||
focus(f->client, True);
|
||||
break;
|
||||
default: break;
|
||||
XAllowEvents(display, ReplayPointer, ev->time);
|
||||
}
|
||||
}else{
|
||||
if(ev->button == Button1) {
|
||||
if(frame_to_top(f))
|
||||
restack_view(f->view);
|
||||
|
||||
else if(ptinrect(Pt(ev->x, ev->y), f->grabbox))
|
||||
do_mouse_resize(f->client, True, CENTER);
|
||||
else if(f->area->floating)
|
||||
if(!ev->subwindow && !ptinrect(Pt(ev->x, ev->y), f->titlebar))
|
||||
do_mouse_resize(f->client, False,
|
||||
quadrant(f->rect, Pt(ev->x_root, ev->y_root)));
|
||||
|
||||
if(f->client != selclient())
|
||||
focus(f->client, True);
|
||||
}
|
||||
if(ev->subwindow)
|
||||
XAllowEvents(display, ReplayPointer, ev->time);
|
||||
else {
|
||||
/* Ungrab so a menu can receive events before the button is released */
|
||||
XUngrabPointer(display, ev->time);
|
||||
XSync(display, False);
|
||||
|
||||
write_event("ClientMouseDown 0x%x %d\n", f->client->win.w, ev->button);
|
||||
}
|
||||
}
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->bdown)
|
||||
w->handler->bdown(w, ev);
|
||||
}
|
||||
else if((d = win2div(ev->window)))
|
||||
mouse_resizecol(d);
|
||||
else
|
||||
XAllowEvents(display, ReplayPointer, ev->time);
|
||||
}
|
||||
|
@ -111,51 +56,13 @@ buttonpress(XEvent *e) {
|
|||
static void
|
||||
configurerequest(XEvent *e) {
|
||||
XConfigureRequestEvent *ev;
|
||||
Window *w;
|
||||
XWindowChanges wc;
|
||||
Rectangle *frect;
|
||||
Client *c;
|
||||
Frame *f;
|
||||
|
||||
ev = &e->xconfigurerequest;
|
||||
c = win2client(ev->window);
|
||||
if(c) {
|
||||
f = c->sel;
|
||||
gravitate_client(c, True);
|
||||
if(ev->value_mask & CWX)
|
||||
c->rect.min.x = ev->x;
|
||||
if(ev->value_mask & CWY)
|
||||
c->rect.min.y = ev->y;
|
||||
if(ev->value_mask & CWWidth)
|
||||
c->rect.max.x = c->rect.min.x + ev->width;
|
||||
if(ev->value_mask & CWHeight)
|
||||
c->rect.max.y = c->rect.min.y + ev->height;
|
||||
if(ev->value_mask & CWBorderWidth)
|
||||
c->border = ev->border_width;
|
||||
gravitate_client(c, False);
|
||||
|
||||
if((Dx(c->rect) == Dx(screen->rect))
|
||||
&& (Dy(c->rect) == Dy(screen->rect))) {
|
||||
c->fullscreen = True;
|
||||
if(c->sel) {
|
||||
if(!c->sel->area->floating)
|
||||
send_to_area(c->sel->view->area, c->sel);
|
||||
focus_client(c);
|
||||
restack_view(c->sel->view);
|
||||
}
|
||||
}
|
||||
|
||||
if(c->sel->area->floating)
|
||||
frect=&c->sel->rect;
|
||||
else
|
||||
frect=&c->sel->revert;
|
||||
|
||||
*frect = insetrect(c->rect, -def.border);
|
||||
frect->min.y -= labelh(def.font);
|
||||
|
||||
if(c->sel->area->floating || c->fullscreen)
|
||||
resize_client(c, frect);
|
||||
else
|
||||
configure_client(c);
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->configreq)
|
||||
w->handler->configreq(w, ev);
|
||||
}else{
|
||||
wc.x = ev->x;
|
||||
wc.y = ev->y;
|
||||
|
@ -173,39 +80,27 @@ configurerequest(XEvent *e) {
|
|||
static void
|
||||
destroynotify(XEvent *e) {
|
||||
XDestroyWindowEvent *ev;
|
||||
Client *c;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xdestroywindow;
|
||||
if((c = win2client(ev->window)))
|
||||
destroy_client(c);
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->destroy)
|
||||
w->handler->destroy(w, ev);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
enternotify(XEvent *e) {
|
||||
XCrossingEvent *ev;
|
||||
Client *c;
|
||||
Frame *f;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xcrossing;
|
||||
if(ev->mode != NotifyNormal)
|
||||
return;
|
||||
|
||||
if((c = win2client(ev->window))) {
|
||||
if(ev->detail != NotifyInferior) {
|
||||
if(screen->focus != c) {
|
||||
if(verbose) fprintf(stderr, "enter_notify(c) => %s\n", c->name);
|
||||
focus(c, False);
|
||||
}
|
||||
set_cursor(c, cursor[CurNormal]);
|
||||
}else if(verbose) fprintf(stderr, "enter_notify(c[NotifyInferior]) => %s\n", c->name);
|
||||
}
|
||||
else if((f = win2frame(ev->window))) {
|
||||
if(screen->focus != c) {
|
||||
if(verbose) fprintf(stderr, "enter_notify(f) => %s\n", f->client->name);
|
||||
if(f->area->floating || !f->collapsed)
|
||||
focus(f->client, False);
|
||||
}
|
||||
set_frame_cursor(f, Pt(ev->x, ev->y));
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->enter)
|
||||
w->handler->enter(w, ev);
|
||||
}
|
||||
else if(ev->window == scr.root.w) {
|
||||
sel_screen = True;
|
||||
|
@ -216,8 +111,10 @@ enternotify(XEvent *e) {
|
|||
static void
|
||||
leavenotify(XEvent *e) {
|
||||
XCrossingEvent *ev;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xcrossing;
|
||||
w = findwin(e->xany.window);
|
||||
if((ev->window == scr.root.w) && !ev->same_screen) {
|
||||
sel_screen = True;
|
||||
draw_frames();
|
||||
|
@ -238,7 +135,8 @@ print_focus(Client *c, char *to) {
|
|||
static void
|
||||
focusin(XEvent *e) {
|
||||
XFocusChangeEvent *ev;
|
||||
Client *c, *old;
|
||||
Window *w;
|
||||
Client *c;
|
||||
XEvent me;
|
||||
|
||||
ev = &e->xfocus;
|
||||
|
@ -258,24 +156,15 @@ focusin(XEvent *e) {
|
|||
&& (screen->hasgrab != &c_root))
|
||||
return;
|
||||
|
||||
old = screen->focus;
|
||||
c = win2client(ev->window);
|
||||
if(c) {
|
||||
print_focus(c, c->name);
|
||||
if(ev->mode == NotifyGrab)
|
||||
screen->hasgrab = c;
|
||||
screen->focus = c;
|
||||
if(c != old) {
|
||||
update_client_grab(c);
|
||||
if(c->sel)
|
||||
draw_frame(c->sel);
|
||||
if(old && old->sel)
|
||||
draw_frame(old->sel);
|
||||
}
|
||||
}else if(ev->window == screen->barwin->w) {
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->focusin)
|
||||
w->handler->focusin(w, ev);
|
||||
}
|
||||
else if(ev->window == screen->barwin->w) {
|
||||
print_focus(nil, "<nil>");
|
||||
screen->focus = nil;
|
||||
}else if(ev->mode == NotifyGrab) {
|
||||
}
|
||||
else if(ev->mode == NotifyGrab) {
|
||||
if(ev->window == scr.root.w)
|
||||
if(XCheckMaskEvent(display, KeyPressMask, &me)) {
|
||||
/* wmii has grabbed focus */
|
||||
|
@ -296,7 +185,7 @@ focusin(XEvent *e) {
|
|||
static void
|
||||
focusout(XEvent *e) {
|
||||
XFocusChangeEvent *ev;
|
||||
Client *c;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xfocus;
|
||||
if(!((ev->detail == NotifyNonlinear)
|
||||
|
@ -305,49 +194,33 @@ focusout(XEvent *e) {
|
|||
if(ev->mode == NotifyUngrab)
|
||||
screen->hasgrab = nil;
|
||||
|
||||
c = win2client(ev->window);
|
||||
if(c) {
|
||||
if((ev->mode == NotifyWhileGrabbed)
|
||||
&& (screen->hasgrab != &c_root)) {
|
||||
if((screen->focus)
|
||||
&& (screen->hasgrab != screen->focus))
|
||||
screen->hasgrab = screen->focus;
|
||||
if(screen->hasgrab == c)
|
||||
return;
|
||||
}else if(ev->mode != NotifyGrab) {
|
||||
if(screen->focus == c) {
|
||||
print_focus(&c_magic, "<magic>");
|
||||
screen->focus = &c_magic;
|
||||
}
|
||||
update_client_grab(c);
|
||||
if(c->sel)
|
||||
draw_frame(c->sel);
|
||||
}
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->focusout)
|
||||
w->handler->focusout(w, ev);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
expose(XEvent *e) {
|
||||
XExposeEvent *ev;
|
||||
Divide *d;
|
||||
Frame *f;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xexpose;
|
||||
if(ev->count == 0) {
|
||||
if(ev->window == screen->barwin->w)
|
||||
draw_bar(screen);
|
||||
else if((f = win2frame(ev->window)))
|
||||
draw_frame(f);
|
||||
else if((d = win2div(ev->window)))
|
||||
draw_div(d);
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->expose)
|
||||
w->handler->expose(w, ev);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
keypress(XEvent *e) {
|
||||
XKeyEvent *ev;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xkey;
|
||||
w = findwin(e->xany.window);
|
||||
ev->state &= valid_mask;
|
||||
if(ev->window == scr.root.w)
|
||||
kpress(scr.root.w, ev->state, (KeyCode) ev->keycode);
|
||||
|
@ -366,9 +239,11 @@ mappingnotify(XEvent *e) {
|
|||
static void
|
||||
maprequest(XEvent *e) {
|
||||
XMapRequestEvent *ev;
|
||||
static XWindowAttributes wa;
|
||||
Window *w;
|
||||
XWindowAttributes wa;
|
||||
|
||||
ev = &e->xmaprequest;
|
||||
w = findwin(e->xany.window);
|
||||
if(!XGetWindowAttributes(display, ev->window, &wa))
|
||||
return;
|
||||
if(wa.override_redirect) {
|
||||
|
@ -383,19 +258,23 @@ maprequest(XEvent *e) {
|
|||
static void
|
||||
motionnotify(XEvent *e) {
|
||||
XMotionEvent *ev;
|
||||
Frame *f;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xmotion;
|
||||
if((f = win2frame(ev->window)))
|
||||
set_frame_cursor(f, Pt(ev->x, ev->y));
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->motion)
|
||||
w->handler->motion(w, ev);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
propertynotify(XEvent *e) {
|
||||
XPropertyEvent *ev;
|
||||
Window *w;
|
||||
Client *c;
|
||||
|
||||
ev = &e->xproperty;
|
||||
w = findwin(e->xany.window);
|
||||
if(ev->state == PropertyDelete)
|
||||
return; /* ignore */
|
||||
if((c = win2client(ev->window)))
|
||||
|
@ -405,23 +284,26 @@ propertynotify(XEvent *e) {
|
|||
static void
|
||||
mapnotify(XEvent *e) {
|
||||
XMapEvent *ev;
|
||||
Client *c;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xmap;
|
||||
if((c = win2client(ev->window)))
|
||||
if(c == selclient())
|
||||
focus_client(c);
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(w->handler->map)
|
||||
w->handler->map(w, ev);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
unmapnotify(XEvent *e) {
|
||||
XUnmapEvent *ev;
|
||||
Client *c;
|
||||
Window *w;
|
||||
|
||||
ev = &e->xunmap;
|
||||
if((c = win2client(ev->window)))
|
||||
if(ev->send_event || (c->unmapped-- == 0))
|
||||
destroy_client(c);
|
||||
if((w = findwin(e->xany.window))) {
|
||||
if(ev->send_event || w->unmapped-- == 0)
|
||||
if(w->handler->unmap)
|
||||
w->handler->unmap(w, ev);
|
||||
}
|
||||
}
|
||||
|
||||
void (*handler[LASTEvent]) (XEvent *) = {
|
||||
|
@ -441,7 +323,6 @@ void (*handler[LASTEvent]) (XEvent *) = {
|
|||
[MotionNotify] = motionnotify,
|
||||
[PropertyNotify]= propertynotify,
|
||||
[UnmapNotify] = unmapnotify,
|
||||
|
||||
};
|
||||
|
||||
void
|
||||
|
|
|
@ -17,6 +17,7 @@ void detach_from_area(Frame*);
|
|||
Client *area_selclient(Area*);
|
||||
|
||||
/* bar.c */
|
||||
void initbar(WMScreen *s);
|
||||
Bar *create_bar(Bar **b_link, char *name);
|
||||
void destroy_bar(Bar **b_link, Bar*);
|
||||
void draw_bar(WMScreen *s);
|
||||
|
@ -165,6 +166,8 @@ void reshapewin(Window *w, Rectangle r);
|
|||
void movewin(Window *w, Point pt);
|
||||
int mapwin(Window *w);
|
||||
int unmapwin(Window *w);
|
||||
Handlers* sethandler(Window*, Handlers*);
|
||||
Window* findwin(XWindow w);
|
||||
uint winprotocols(Window *w);
|
||||
void setshapemask(Window *dst, Image *src, Point pt);
|
||||
void border(Image *dst, Rectangle r, int w, ulong col);
|
||||
|
|
|
@ -102,6 +102,101 @@ client2frame(Frame *f, Rectangle r) {
|
|||
return r;
|
||||
}
|
||||
|
||||
/* Handlers */
|
||||
static void
|
||||
bup_event(Window *w, XButtonEvent *e) {
|
||||
write_event("ClientClick 0x%x %d\n", (uint)w->w, e->button);
|
||||
}
|
||||
|
||||
static void
|
||||
bdown_event(Window *w, XButtonEvent *e) {
|
||||
Frame *f;
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
f = c->sel;
|
||||
|
||||
if((e->state & def.mod) == def.mod) {
|
||||
switch(e->button) {
|
||||
case Button1:
|
||||
do_mouse_resize(c, False, CENTER);
|
||||
focus(c, True);
|
||||
frame_to_top(f);
|
||||
focus(c, True);
|
||||
break;
|
||||
case Button3:
|
||||
do_mouse_resize(c, False, quadrant(f->rect, Pt(e->x_root, e->y_root)));
|
||||
frame_to_top(f);
|
||||
focus(c, True);
|
||||
break;
|
||||
default: break;
|
||||
XAllowEvents(display, ReplayPointer, e->time);
|
||||
}
|
||||
}else{
|
||||
if(e->button == Button1) {
|
||||
if(frame_to_top(f))
|
||||
restack_view(f->view);
|
||||
|
||||
else if(ptinrect(Pt(e->x, e->y), f->grabbox))
|
||||
do_mouse_resize(c, True, CENTER);
|
||||
else if(f->area->floating)
|
||||
if(!e->subwindow && !ptinrect(Pt(e->x, e->y), f->titlebar))
|
||||
do_mouse_resize(c, False, quadrant(f->rect, Pt(e->x_root, e->y_root)));
|
||||
|
||||
if(f->client != selclient())
|
||||
focus(c, True);
|
||||
}
|
||||
if(e->subwindow)
|
||||
XAllowEvents(display, ReplayPointer, e->time);
|
||||
else {
|
||||
/* Ungrab so a menu can receive events before the button is released */
|
||||
XUngrabPointer(display, e->time);
|
||||
XSync(display, False);
|
||||
|
||||
write_event("ClientMouseDown 0x%x %d\n", f->client->win.w, e->button);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
enter_event(Window *w, XCrossingEvent *e) {
|
||||
Client *c;
|
||||
Frame *f;
|
||||
|
||||
c = w->aux;
|
||||
f = c->sel;
|
||||
if(screen->focus != c) {
|
||||
if(verbose) fprintf(stderr, "enter_notify(f) => %s\n", f->client->name);
|
||||
if(f->area->floating || !f->collapsed)
|
||||
focus(f->client, False);
|
||||
}
|
||||
set_frame_cursor(f, Pt(e->x, e->y));
|
||||
}
|
||||
|
||||
static void
|
||||
expose_event(Window *w, XExposeEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
draw_frame(c->sel);
|
||||
}
|
||||
|
||||
static void
|
||||
motion_event(Window *w, XMotionEvent *e) {
|
||||
Client *c;
|
||||
|
||||
c = w->aux;
|
||||
set_frame_cursor(c->sel, Pt(e->x, e->y));
|
||||
}
|
||||
|
||||
Handlers framehandler = {
|
||||
.bup = bup_event,
|
||||
.bdown = bdown_event,
|
||||
.enter = enter_event,
|
||||
.expose = expose_event,
|
||||
.motion = motion_event,
|
||||
};
|
||||
|
||||
void
|
||||
resize_frame(Frame *f, Rectangle r) {
|
||||
Align stickycorner;
|
||||
|
@ -115,7 +210,8 @@ resize_frame(Frame *f, Rectangle r) {
|
|||
apply_sizehints(c, &f->crect, f->area->floating, True, stickycorner);
|
||||
|
||||
if(Dx(r) <= 0 || Dy(r) <= 0)
|
||||
asm("int $3");
|
||||
fprintf(stderr, "Badness: Frame rect: %d,%d %dx%d\n",
|
||||
r.min.x, r.min.y, Dx(r), Dy(r));
|
||||
|
||||
if(f->area->floating)
|
||||
f->rect = f->crect;
|
||||
|
|
|
@ -472,27 +472,7 @@ main(int argc, char *argv[]) {
|
|||
setwinattr(&scr.root, &wa,
|
||||
CWEventMask
|
||||
| CWCursor);
|
||||
|
||||
wa.override_redirect = 1;
|
||||
wa.background_pixmap = ParentRelative;
|
||||
wa.event_mask =
|
||||
ExposureMask
|
||||
| ButtonReleaseMask
|
||||
| FocusChangeMask
|
||||
| SubstructureRedirectMask
|
||||
| SubstructureNotifyMask;
|
||||
|
||||
s->brect = s->rect;
|
||||
s->brect.min.y = s->brect.max.y - labelh(def.font);
|
||||
|
||||
s->barwin = createwindow(&scr.root, s->brect, scr.depth, InputOutput, &wa,
|
||||
CWOverrideRedirect
|
||||
| CWBackPixmap
|
||||
| CWEventMask);
|
||||
|
||||
XSync(display, False);
|
||||
draw_bar(s);
|
||||
XMapRaised(display, s->barwin->w);
|
||||
initbar(s);
|
||||
}
|
||||
|
||||
screen = &screens[0];
|
||||
|
|
|
@ -215,7 +215,7 @@ restack_view(View *v) {
|
|||
for(f=v->area->stack; f; f=f->snext)
|
||||
wins[n++] = f->client->framewin->w;
|
||||
|
||||
for(d = divs; d && d->mapped; d = d->next)
|
||||
for(d = divs; d && d->w->mapped; d = d->next)
|
||||
wins[n++] = d->w->w;
|
||||
|
||||
for(a=v->area->next; a; a=a->next)
|
||||
|
|
Loading…
Reference in New Issue