/* * Copyright 2010 Johan Veenhuizen */ #include #include #include #include #include "wind.h" // Lock-mask permutations that should be grabbed in addition // to the modifiers specified to the functions below. static const unsigned lockmasks[] = { 0, LockMask, // Caps Lock Mod2Mask, // Num Lock Mod5Mask, // Scroll Lock LockMask | Mod2Mask, LockMask | Mod5Mask, Mod2Mask | Mod5Mask, LockMask | Mod2Mask | Mod5Mask }; void *xmalloc(size_t size) { void *p; while ((p = malloc(size)) == NULL && size != 0) sleep(1); return p; } void *xrealloc(const void *p, size_t size) { void *q; while ((q = realloc((void *)p, size)) == NULL && size != 0) sleep(1); return q; } char *xstrdup(const char *s) { return strcpy(xmalloc(strlen(s) + 1), s); } /* * Grabs a key. See manual page of XGrabKey. */ void grabkey(int keycode, unsigned modifiers, Window grabwin, Bool ownerevents, int ptrmode, int keymode) { if (modifiers == AnyModifier) XGrabKey(dpy, keycode, modifiers, grabwin, ownerevents, ptrmode, keymode); else for (int i = 0; i < NELEM(lockmasks); i++) XGrabKey(dpy, keycode, modifiers | lockmasks[i], grabwin, ownerevents, ptrmode, keymode); } /* * Ungrabs a key. See manual page of XUngrabKey. */ void ungrabkey(int keycode, unsigned modifiers, Window grabwin) { if (modifiers == AnyModifier) XUngrabKey(dpy, keycode, AnyModifier, grabwin); else for (int i = 0; i < NELEM(lockmasks); i++) XUngrabKey(dpy, keycode, modifiers | lockmasks[i], grabwin); } /* * Ungrabs a pointer button. See manual page of XGrabButton. */ void grabbutton(unsigned button, unsigned modifiers, Window grabwin, Bool ownerevents, unsigned eventmask, int ptrmode, int keymode, Window confineto, Cursor cursor) { if (modifiers == AnyModifier) XGrabButton(dpy, button, AnyModifier, grabwin, ownerevents, eventmask, ptrmode, keymode, confineto, cursor); else for (int i = 0; i < NELEM(lockmasks); i++) XGrabButton(dpy, button, modifiers | lockmasks[i], grabwin, ownerevents, eventmask, ptrmode, keymode, confineto, cursor); } /* * Ungrabs a pointer button. See manual page of XUngrabButton. */ void ungrabbutton(unsigned button, unsigned modifiers, Window grabwin) { if (modifiers == AnyModifier) XUngrabButton(dpy, button, modifiers, grabwin); else for (int i = 0; i < lockmasks[i]; i++) XUngrabButton(dpy, button, modifiers | lockmasks[i], grabwin); } /* * Returns the WM_STATE hint of a client window */ long getwmstate(Window w) { unsigned long nitems, bytesafter; unsigned char *prop; Atom actualtype; int actualformat; long state = WithdrawnState; if (XGetWindowProperty(dpy, w, WM_STATE, 0L, 2L, False, WM_STATE, &actualtype, &actualformat, &nitems, &bytesafter, &prop) == Success) { if (nitems > 0) state = ((long *)prop)[0]; XFree(prop); } return state; } /* * Sets the WM_STATE hint of a client window. The state can * be one of Normalstate, IconicState, or WithdrawnState. */ void setwmstate(Window w, long state) { long data[2] = { state, None }; XChangeProperty(dpy, w, WM_STATE, WM_STATE, 32, PropModeReplace, (unsigned char *)data, 2); } /* * Tests if a client window is mapped. */ Bool ismapped(Window w) { XWindowAttributes a; return XGetWindowAttributes(dpy, w, &a) && a.map_state != IsUnmapped; } char *decodetextproperty(XTextProperty *p) { char *s = NULL; char **v = NULL; int n = 0; XmbTextPropertyToTextList(dpy, p, &v, &n); if (n > 0) s = xstrdup(v[0]); if (v != NULL) XFreeStringList(v); return s; } void setprop(Window w, Atom prop, Atom type, int fmt, void *ptr, int nelem) { XChangeProperty(dpy, w, prop, type, fmt, PropModeReplace, ptr, nelem); } void *getprop(Window w, Atom prop, Atom type, int fmt, unsigned long *rcountp) { void *ptr = NULL; unsigned long count = 32; Atom rtype; int rfmt; unsigned long rafter; for (;;) { if (XGetWindowProperty(dpy, w, prop, 0L, count, False, type, &rtype, &rfmt, rcountp, &rafter, (unsigned char **)&ptr) != Success) { // Error return NULL; } else if (rtype != type || rfmt != fmt) { // Does not exist (type=None), or wrong type/format return NULL; } else if (rafter > 0) { XFree(ptr); ptr = NULL; count *= 2; } else { return ptr; } } } void drawbitmap(Drawable d, GC gc, struct bitmap *b, int x, int y) { if (b->pixmap == None) b->pixmap = XCreateBitmapFromData(dpy, d, (char *)b->bits, b->width, b->height); XCopyPlane(dpy, b->pixmap, d, gc, 0, 0, b->width, b->height, x, y, 1); } unsigned long getpixel(const char *name) { XColor tc, sc; XAllocNamedColor(dpy, DefaultColormap(dpy, scr), name, &sc, &tc); return sc.pixel; }