]> git.sur5r.net Git - i3/i3/commitdiff
Fix colormap handling for containers. (#2450)
authorIngo Bürk <admin@airblader.de>
Wed, 14 Sep 2016 07:13:17 +0000 (09:13 +0200)
committerMichael Stapelberg <stapelberg@users.noreply.github.com>
Wed, 14 Sep 2016 07:13:17 +0000 (09:13 +0200)
This commit correctly handles colormaps by

* Using the static default colormap we determine on startup if the
  con has the corresponding depth. This avoids creating pointless
  colormaps.
* Not freeing the default colormap to not have stray colormaps on
  containers. This fixes an issue with certain programs such as xwd.
* Creating a custom colormap when necessary and freeing it when the
  container is killed.

fixes #2435

include/data.h
src/x.c

index 9f835a233ec57f5dcae4f72f9101ceb9007ac17e..247cd3c50af134ec12c769688303464a7d69153c 100644 (file)
@@ -699,4 +699,7 @@ struct Con {
 
     /* Depth of the container window */
     uint16_t depth;
+
+    /* The colormap for this con if a custom one is used. */
+    xcb_colormap_t colormap;
 };
diff --git a/src/x.c b/src/x.c
index 6fd3297a918dd318308cfcb75c0a286561204fc1..f3e02fa465280d2cc5daaede2d5751a642a021d4 100644 (file)
--- a/src/x.c
+++ b/src/x.c
@@ -105,11 +105,18 @@ void x_con_init(Con *con) {
     uint32_t mask = 0;
     uint32_t values[5];
 
-    /* For custom visuals, we need to create a colormap before creating
-     * this window. It will be freed directly after creating the window. */
     xcb_visualid_t visual = get_visualid_by_depth(con->depth);
-    xcb_colormap_t win_colormap = xcb_generate_id(conn);
-    xcb_create_colormap_checked(conn, XCB_COLORMAP_ALLOC_NONE, win_colormap, root, visual);
+    xcb_colormap_t win_colormap;
+    if (con->depth != root_depth) {
+        /* We need to create a custom colormap. */
+        win_colormap = xcb_generate_id(conn);
+        xcb_create_colormap(conn, XCB_COLORMAP_ALLOC_NONE, win_colormap, root, visual);
+        con->colormap = win_colormap;
+    } else {
+        /* Use the default colormap. */
+        win_colormap = colormap;
+        con->colormap = XCB_NONE;
+    }
 
     /* We explicitly set a background color and border color (even though we
      * don’t even have a border) because the X11 server requires us to when
@@ -144,9 +151,6 @@ void x_con_init(Con *con) {
                         (strlen("i3-frame") + 1) * 2,
                         "i3-frame\0i3-frame\0");
 
-    if (win_colormap != XCB_NONE)
-        xcb_free_colormap(conn, win_colormap);
-
     struct con_state *state = scalloc(1, sizeof(struct con_state));
     state->id = con->frame.id;
     state->mapped = false;
@@ -229,6 +233,10 @@ void x_move_win(Con *src, Con *dest) {
 void x_con_kill(Con *con) {
     con_state *state;
 
+    if (con->colormap != XCB_NONE) {
+        xcb_free_colormap(conn, con->colormap);
+    }
+
     draw_util_surface_free(conn, &(con->frame));
     draw_util_surface_free(conn, &(con->frame_buffer));
     xcb_destroy_window(conn, con->frame.id);