X-Git-Url: http://pileus.org/git/?a=blobdiff_plain;f=sys-x11.c;h=6bc3b019246ef6ceb55768b6bbb12133d9291ab8;hb=a7cbcfd5a5e2ded8cfc04ef6679acc8c3e227da7;hp=28fb9d91a14d223ddb0cab89675ae37301d6be1b;hpb=a0807177593e8ae6971ab5fb6bcdcd893819ef66;p=wmpus diff --git a/sys-x11.c b/sys-x11.c index 28fb9d9..6bc3b01 100644 --- a/sys-x11.c +++ b/sys-x11.c @@ -50,6 +50,7 @@ typedef struct { typedef enum { WM_PROTO, WM_FOCUS, WM_DELETE, NET_STATE, NET_FULL, NET_STRUT, + NET_TYPE, NET_DIALOG, NATOMS } atom_t; @@ -188,10 +189,10 @@ static int strut_add(win_t *root, win_t *win) if (status != Success || ret_size != 32 || ret_items != 4) return 0; - win->sys->strut.left = ((int*)xdata)[0]; - win->sys->strut.right = ((int*)xdata)[1]; - win->sys->strut.top = ((int*)xdata)[2]; - win->sys->strut.bottom = ((int*)xdata)[3]; + win->sys->strut.left = ((long*)xdata)[0]; + win->sys->strut.right = ((long*)xdata)[1]; + win->sys->strut.top = ((long*)xdata)[2]; + win->sys->strut.bottom = ((long*)xdata)[3]; struts = list_insert(struts, win); for (list_t *cur = screens; cur; cur = cur->next) strut_copy(cur->data, win, 1); @@ -209,8 +210,12 @@ static int strut_del(win_t *root, win_t *win) } /* Window functions */ +static Atom win_prop(win_t *win, atom_t prop); +static win_t *win_find(Display *dpy, Window xid, int create); + static win_t *win_new(Display *dpy, Window xid) { + Window trans; XWindowAttributes attr; if (XGetWindowAttributes(dpy, xid, &attr)) if (attr.override_redirect) @@ -223,9 +228,14 @@ static win_t *win_new(Display *dpy, Window xid) win->sys = new0(win_sys_t); win->sys->dpy = dpy; win->sys->xid = xid; - printf("win_new: %p = %p, %d (%d,%d %dx%d)\n", + if (win_prop(win, NET_TYPE) == atoms[NET_DIALOG]) + win->type = TYPE_DIALOG; + if (XGetTransientForHint(dpy, xid, &trans)) + win->parent = win_find(dpy, trans, 0); + printf("win_new: %p = %p, %d (%d,%d %dx%d) - %s\n", win, dpy, (int)xid, - win->x, win->y, win->w, win->h); + win->x, win->y, win->w, win->h, + win->type ? "dialog" : "normal"); return win; } @@ -299,27 +309,19 @@ static int win_msg(win_t *win, atom_t msg) return 1; } -#if 0 -static int win_full(win_t *win) +static Atom win_prop(win_t *win, atom_t prop) { - Atom ret_type; - int ret_size; - unsigned long ret_items, bytes_left; - unsigned char *xdata; - int status = XGetWindowProperty(win->sys->dpy, win->sys->xid, - atoms[NET_FULL], 0L, 1L, False, XA_ATOM, - &ret_type, &ret_size, &ret_items, &bytes_left, &xdata); - printf("is_fullscreen:\n"); - printf("\t%d\n", status); - printf("\t%d\n", ret_size); - printf("\t%ld\n", ret_items); - printf("\t%p\n", xdata); - if (xdata) - printf("\t%d\n", xdata[0]); - return status == Success && ret_size == 32 && ret_items == 1 && - xdata[0] == atoms[NET_FULL]; -} -#endif + int format; + unsigned long nitems, bytes; + unsigned char *buf = NULL; + Atom atom, type = XA_ATOM; + if (XGetWindowProperty(win->sys->dpy, win->sys->xid, atoms[prop], + 0L, sizeof(Atom), False, type, &type, &format, &nitems, &bytes, &buf) || !buf) + return 0; + atom = *(Atom *)buf; + XFree(buf); + return atom; +} /* Drawing functions */ static unsigned long get_color(Display *dpy, const char *name) @@ -354,7 +356,7 @@ static void process_event(int type, XEvent *xe, win_t *root) /* Split based on event */ if (type == KeyPress) { while (XCheckTypedEvent(dpy, KeyPress, xe)); - KeySym sym = XKeycodeToKeysym(dpy, xe->xkey.keycode, 0); + KeySym sym = XLookupKeysym(&xe->xkey, 0); printf("got xe %c %hhx\n", xk2ev(sym), mod2int(mod)); wm_handle_event(win, xk2ev(sym), mod, ptr); } @@ -436,13 +438,16 @@ static void process_event(int type, XEvent *xe, win_t *root) printf("map_req: %d\n", type); if ((win = win_find(dpy,xe->xmaprequest.window,1)) && win->state == ST_HIDE) { + win->state = ST_SHOW; + if (win_prop(win, NET_STATE) == atoms[NET_FULL]) + win->state = ST_FULL; XSelectInput(win->sys->dpy, win->sys->xid, PropertyChangeMask); if (!strut_add(root, win)) wm_insert(win); else wm_update(); } - sys_show(win, ST_SHOW); + sys_show(win, win->state); } else if (type == ClientMessage) { XClientMessageEvent *cme = &xe->xclient; @@ -454,12 +459,11 @@ static void process_event(int type, XEvent *xe, win_t *root) (cme->message_type == atoms[NET_STATE]) && (cme->data.l[1] == atoms[NET_FULL] || cme->data.l[2] == atoms[NET_FULL])) { - if (cme->data.l[0] == 1 || /* _NET_WM_STATE_ADD */ - (cme->data.l[0] == 2 && /* _NET_WM_STATE_TOGGLE */ - win->state != ST_FULL)) - sys_show(win, ST_FULL); - else - sys_show(win, ST_SHOW); + state_t next = (cme->data.l[0] == 1 || /* _NET_WM_STATE_ADD */ + (cme->data.l[0] == 2 && /* _NET_WM_STATE_TOGGLE */ + win->state != ST_FULL)) ? ST_FULL : ST_SHOW; + wm_handle_state(win, win->state, next); + sys_show(win, next); } } else if (type == PropertyNotify) { @@ -672,12 +676,14 @@ win_t *sys_init(void) error("Unable to get root window"); /* Setup X11 data */ - atoms[WM_PROTO] = XInternAtom(dpy, "WM_PROTOCOLS", False); - atoms[WM_FOCUS] = XInternAtom(dpy, "WM_TAKE_FOCUS", False); - atoms[WM_DELETE] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); - atoms[NET_STATE] = XInternAtom(dpy, "_NET_WM_STATE", False); - atoms[NET_FULL] = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False); - atoms[NET_STRUT] = XInternAtom(dpy, "_NET_WM_STRUT", False); + atoms[WM_PROTO] = XInternAtom(dpy, "WM_PROTOCOLS", False); + atoms[WM_FOCUS] = XInternAtom(dpy, "WM_TAKE_FOCUS", False); + atoms[WM_DELETE] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); + atoms[NET_STATE] = XInternAtom(dpy, "_NET_WM_STATE", False); + atoms[NET_FULL] = XInternAtom(dpy, "_NET_WM_STATE_FULLSCREEN", False); + atoms[NET_STRUT] = XInternAtom(dpy, "_NET_WM_STRUT", False); + atoms[NET_TYPE] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE", False); + atoms[NET_DIALOG] = XInternAtom(dpy, "_NET_WM_WINDOW_TYPE_DIALOG", False); colors[CLR_FOCUS] = get_color(dpy, "#a0a0ff"); colors[CLR_UNFOCUS] = get_color(dpy, "#101066");