From: Michael Stapelberg Date: Sat, 17 Apr 2010 14:41:20 +0000 (+0200) Subject: When assigning children to containers, reset their x window state X-Git-Tag: tree-pr1~241 X-Git-Url: https://git.sur5r.net/?a=commitdiff_plain;h=68542f3c2214b3a024a0039b10719a078b2eaf79;p=i3%2Fi3 When assigning children to containers, reset their x window state --- diff --git a/include/x.h b/include/x.h index 85dfc3ce..1e564d4f 100644 --- a/include/x.h +++ b/include/x.h @@ -6,6 +6,7 @@ #define _X_H void x_con_init(Con *con); +void x_reinit(Con *con); void x_con_kill(Con *con); void x_window_kill(xcb_window_t window); void x_draw_decoration(Con *con); diff --git a/src/manage.c b/src/manage.c index ce11a2c1..940013e2 100644 --- a/src/manage.c +++ b/src/manage.c @@ -110,12 +110,16 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki goto out; /* Check if the window is already managed */ - if (con_by_window_id(window) != NULL) + if (con_by_window_id(window) != NULL) { + LOG("already managed\n"); goto out; + } /* Get the initial geometry (position, size, …) */ - if ((geom = xcb_get_geometry_reply(conn, geomc, 0)) == NULL) + if ((geom = xcb_get_geometry_reply(conn, geomc, 0)) == NULL) { + LOG("could not get geometry\n"); goto out; + } LOG("reparenting!\n"); uint32_t mask = 0; @@ -159,6 +163,7 @@ void manage_window(xcb_window_t window, xcb_get_window_attributes_cookie_t cooki } } nc->window = cwindow; + x_reinit(nc); xcb_void_cookie_t rcookie = xcb_reparent_window_checked(conn, window, nc->frame, 0, 0); if (xcb_request_check(conn, rcookie) != NULL) { diff --git a/src/x.c b/src/x.c index 7ba56c65..f73fc846 100644 --- a/src/x.c +++ b/src/x.c @@ -86,6 +86,25 @@ void x_con_init(Con *con) { LOG("adding new state for window id 0x%08x\n", state->id); } +/* + * Re-initializes the associated X window state for this container. You have + * to call this when you assign a client to an empty container to ensure that + * its state gets updated correctly. + * + */ +void x_reinit(Con *con) { + struct con_state *state; + + if ((state = state_for_frame(con->frame)) == NULL) { + ELOG("window state not found\n"); + return; + } + + LOG("resetting state %p to initial\n", state); + state->initial = true; + memset(&(state->window_rect), 0, sizeof(Rect)); +} + void x_con_kill(Con *con) { con_state *state; @@ -202,8 +221,10 @@ static void x_push_node(Con *con) { LOG("Pushing changes for node %p / %s\n", con, con->name); state = state_for_frame(con->frame); - /* map/unmap if map state changed */ - if (state->mapped != con->mapped) { + /* map/unmap if map state changed, also ensure that the child window + * is changed if we are mapped *and* in initial state (meaning the + * container was empty before, but now got a child) */ + if (state->mapped != con->mapped || (con->mapped && state->initial)) { if (!con->mapped) { LOG("unmapping container\n"); xcb_unmap_window(conn, con->frame);