*
* xcb.c: contains all functions which use XCB to talk to X11. Mostly wrappers
* around the rather complicated/ugly parts of the XCB API.
*
*/
#include <xcb/xcb.h>
*
* xcb.c: contains all functions which use XCB to talk to X11. Mostly wrappers
* around the rather complicated/ugly parts of the XCB API.
*
*/
#include <xcb/xcb.h>
#define curs_invisible_width 8
#define curs_invisible_height 8
static unsigned char curs_invisible_bits[] = {
#define curs_invisible_width 8
#define curs_invisible_height 8
static unsigned char curs_invisible_bits[] = {
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
#define curs_windows_width 11
#define curs_windows_height 19
static unsigned char curs_windows_bits[] = {
#define curs_windows_width 11
#define curs_windows_height 19
static unsigned char curs_windows_bits[] = {
- 0xfe, 0x07, 0xfc, 0x07, 0xfa, 0x07, 0xf6, 0x07, 0xee, 0x07, 0xde, 0x07,
- 0xbe, 0x07, 0x7e, 0x07, 0xfe, 0x06, 0xfe, 0x05, 0x3e, 0x00, 0xb6, 0x07,
- 0x6a, 0x07, 0x6c, 0x07, 0xde, 0x06, 0xdf, 0x06, 0xbf, 0x05, 0xbf, 0x05,
- 0x7f, 0x06 };
+ 0xfe, 0x07, 0xfc, 0x07, 0xfa, 0x07, 0xf6, 0x07, 0xee, 0x07, 0xde, 0x07,
+ 0xbe, 0x07, 0x7e, 0x07, 0xfe, 0x06, 0xfe, 0x05, 0x3e, 0x00, 0xb6, 0x07,
+ 0x6a, 0x07, 0x6c, 0x07, 0xde, 0x06, 0xdf, 0x06, 0xbf, 0x05, 0xbf, 0x05,
+ 0x7f, 0x06};
#define mask_windows_width 11
#define mask_windows_height 19
static unsigned char mask_windows_bits[] = {
#define mask_windows_width 11
#define mask_windows_height 19
static unsigned char mask_windows_bits[] = {
- 0x01, 0x00, 0x03, 0x00, 0x07, 0x00, 0x0f, 0x00, 0x1f, 0x00, 0x3f, 0x00,
- 0x7f, 0x00, 0xff, 0x00, 0xff, 0x01, 0xff, 0x03, 0xff, 0x07, 0x7f, 0x00,
- 0xf7, 0x00, 0xf3, 0x00, 0xe1, 0x01, 0xe0, 0x01, 0xc0, 0x03, 0xc0, 0x03,
- 0x80, 0x01 };
+ 0x01, 0x00, 0x03, 0x00, 0x07, 0x00, 0x0f, 0x00, 0x1f, 0x00, 0x3f, 0x00,
+ 0x7f, 0x00, 0xff, 0x00, 0xff, 0x01, 0xff, 0x03, 0xff, 0x07, 0x7f, 0x00,
+ 0xf7, 0x00, 0xf3, 0x00, 0xe1, 0x01, 0xe0, 0x01, 0xc0, 0x03, 0xc0, 0x03,
+ 0x80, 0x01};
static uint32_t get_colorpixel(char *hex) {
char strgroups[3][3] = {{hex[0], hex[1], '\0'},
static uint32_t get_colorpixel(char *hex) {
char strgroups[3][3] = {{hex[0], hex[1], '\0'},
-xcb_pixmap_t create_bg_pixmap(xcb_connection_t *conn, xcb_screen_t *scr, u_int32_t* resolution, char *color) {
+xcb_pixmap_t create_bg_pixmap(xcb_connection_t *conn, xcb_screen_t *scr, u_int32_t *resolution, char *color) {
xcb_pixmap_t bg_pixmap = xcb_generate_id(conn);
xcb_create_pixmap(conn, scr->root_depth, bg_pixmap, scr->root,
resolution[0], resolution[1]);
xcb_pixmap_t bg_pixmap = xcb_generate_id(conn);
xcb_create_pixmap(conn, scr->root_depth, bg_pixmap, scr->root,
resolution[0], resolution[1]);
/* Generate a Graphics Context and fill the pixmap with background color
* (for images that are smaller than your screen) */
xcb_gcontext_t gc = xcb_generate_id(conn);
/* Generate a Graphics Context and fill the pixmap with background color
* (for images that are smaller than your screen) */
xcb_gcontext_t gc = xcb_generate_id(conn);
xcb_create_gc(conn, gc, bg_pixmap, XCB_GC_FOREGROUND, values);
xcb_create_gc(conn, gc, bg_pixmap, XCB_GC_FOREGROUND, values);
- xcb_rectangle_t rect = { 0, 0, resolution[0], resolution[1] };
+ xcb_rectangle_t rect = {0, 0, resolution[0], resolution[1]};
xcb_poly_fill_rectangle(conn, bg_pixmap, gc, 1, &rect);
xcb_poly_fill_rectangle(conn, bg_pixmap, gc, 1, &rect);
+ xcb_window_t parent_win = scr->root;
+
+ /* Check whether the composite extension is available */
+ const xcb_query_extension_reply_t *extension_query = NULL;
+ xcb_generic_error_t *error = NULL;
+ xcb_composite_get_overlay_window_cookie_t cookie;
+ xcb_composite_get_overlay_window_reply_t *composite_reply = NULL;
+
+ extension_query = xcb_get_extension_data(conn, &xcb_composite_id);
+ if (extension_query && extension_query->present) {
+ /* When composition is used, we need to use the composite overlay
+ * window instead of the normal root window to be able to cover
+ * composited windows */
+ cookie = xcb_composite_get_overlay_window(conn, scr->root);
+ composite_reply = xcb_composite_get_overlay_window_reply(conn, cookie, &error);
+
+ if (!error && composite_reply) {
+ parent_win = composite_reply->overlay_win;
+ }
+
+ free(composite_reply);
+ free(error);
+ }
XCB_WINDOW_CLASS_INPUT_OUTPUT,
XCB_WINDOW_CLASS_COPY_FROM_PARENT, /* copy visual from parent */
mask,
values);
XCB_WINDOW_CLASS_INPUT_OUTPUT,
XCB_WINDOW_CLASS_COPY_FROM_PARENT, /* copy visual from parent */
mask,
values);
/* Map the window (= make it visible) */
xcb_map_window(conn, win);
/* Map the window (= make it visible) */
xcb_map_window(conn, win);
values[0] = XCB_STACK_MODE_ABOVE;
xcb_configure_window(conn, win, XCB_CONFIG_WINDOW_STACK_MODE, values);
values[0] = XCB_STACK_MODE_ABOVE;
xcb_configure_window(conn, win, XCB_CONFIG_WINDOW_STACK_MODE, values);
- return win;
-}
-
-/*
- * Returns the mask for Mode_switch (to be used for looking up keysymbols by
- * keycode).
- *
- */
-uint32_t get_mod_mask(xcb_connection_t *conn, xcb_key_symbols_t *symbols, uint32_t keycode) {
- xcb_get_modifier_mapping_reply_t *modmap_r;
- xcb_keycode_t *modmap, kc;
- xcb_keycode_t *modeswitchcodes = xcb_key_symbols_get_keycode(symbols, keycode);
- if (modeswitchcodes == NULL)
- return 0;
-
- modmap_r = xcb_get_modifier_mapping_reply(conn, xcb_get_modifier_mapping(conn), NULL);
- modmap = xcb_get_modifier_mapping_keycodes(modmap_r);
-
- for (int i = 0; i < 8; i++)
- for (int j = 0; j < modmap_r->keycodes_per_modifier; j++) {
- kc = modmap[i * modmap_r->keycodes_per_modifier + j];
- for (xcb_keycode_t *ktest = modeswitchcodes; *ktest; ktest++) {
- if (*ktest != kc)
- continue;
-
- free(modeswitchcodes);
- free(modmap_r);
- return (1 << i);
- }
- }
-
- return 0;
-}
+ /* Ensure that the window is created and set up before returning */
+ xcb_aux_sync(conn);
XCB_GRAB_MODE_ASYNC, /* keyboard mode */
XCB_NONE, /* confine_to = in which window should the cursor stay */
cursor, /* we change the cursor to whatever the user wanted */
XCB_GRAB_MODE_ASYNC, /* keyboard mode */
XCB_NONE, /* confine_to = in which window should the cursor stay */
cursor, /* we change the cursor to whatever the user wanted */
if ((preply = xcb_grab_pointer_reply(conn, pcookie, NULL)) &&
preply->status == XCB_GRAB_STATUS_SUCCESS) {
if ((preply = xcb_grab_pointer_reply(conn, pcookie, NULL)) &&
preply->status == XCB_GRAB_STATUS_SUCCESS) {
- true, /* report events */
- screen->root, /* grab the root window */
+ true, /* report events */
+ screen->root, /* grab the root window */
if ((kreply = xcb_grab_keyboard_reply(conn, kcookie, NULL)) &&
kreply->status == XCB_GRAB_STATUS_SUCCESS) {
if ((kreply = xcb_grab_keyboard_reply(conn, kcookie, NULL)) &&
kreply->status == XCB_GRAB_STATUS_SUCCESS) {
}
xcb_cursor_t create_cursor(xcb_connection_t *conn, xcb_screen_t *screen, xcb_window_t win, int choice) {
}
xcb_cursor_t create_cursor(xcb_connection_t *conn, xcb_screen_t *screen, xcb_window_t win, int choice) {
xcb_free_pixmap(conn, bitmap);
xcb_free_pixmap(conn, mask);
xcb_free_pixmap(conn, bitmap);
xcb_free_pixmap(conn, mask);