From ec88f6501dab7b22a4c86b210d67441538587662 Mon Sep 17 00:00:00 2001 From: Michael Stapelberg Date: Wed, 27 Jul 2011 13:28:32 +0200 Subject: [PATCH] i3-config-wizard: use a managed, floating (dialog) window. fixes focus problems Probably only when another window is already opened, but people can do that (start i3 from within a terminal in their X session) --- .gitignore | 6 +- i3-config-wizard/atoms.xmacro | 6 ++ i3-config-wizard/main.c | 102 +++++++++++++++++++++++----------- i3-config-wizard/xcb.c | 5 +- i3-config-wizard/xcb.h | 4 ++ 5 files changed, 85 insertions(+), 38 deletions(-) create mode 100644 i3-config-wizard/atoms.xmacro diff --git a/.gitignore b/.gitignore index 10aa4d56..0790c233 100644 --- a/.gitignore +++ b/.gitignore @@ -7,9 +7,9 @@ loglevels.tmp *.gcno testcases/testsuite-* testcases/latest -src/*.output -src/*.tab.* -src/*.yy.c +*.output +*.tab.* +*.yy.c man/i3-msg.1 man/i3-msg.xml man/i3-msg.html diff --git a/i3-config-wizard/atoms.xmacro b/i3-config-wizard/atoms.xmacro new file mode 100644 index 00000000..8f94ceaa --- /dev/null +++ b/i3-config-wizard/atoms.xmacro @@ -0,0 +1,6 @@ +xmacro(_NET_WM_NAME) +xmacro(_NET_WM_WINDOW_TYPE) +xmacro(_NET_WM_WINDOW_TYPE_DIALOG) +xmacro(ATOM) +xmacro(CARDINAL) +xmacro(UTF8_STRING) diff --git a/i3-config-wizard/main.c b/i3-config-wizard/main.c index b59fb9f8..d3a26721 100644 --- a/i3-config-wizard/main.c +++ b/i3-config-wizard/main.c @@ -171,12 +171,9 @@ static char *socket_path_from_x11() { */ static int handle_expose() { /* re-draw the background */ - xcb_rectangle_t border = {0, 0, 300, (15*font_height) + 8}, - inner = {2, 2, 296, (15*font_height) + 8 - 4}; - xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#285577")); - xcb_poly_fill_rectangle(conn, pixmap, pixmap_gc, 1, &border); + xcb_rectangle_t border = {0, 0, 300, (15*font_height) + 8}; xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#000000")); - xcb_poly_fill_rectangle(conn, pixmap, pixmap_gc, 1, &inner); + xcb_poly_fill_rectangle(conn, pixmap, pixmap_gc, 1, &border); xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FONT, font_id); @@ -186,54 +183,51 @@ static int handle_expose() { /* restore font color */ xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#FFFFFF")); - txt(10, 1, "i3: first configuration"); - txt(10, 4, "You have not configured i3 yet."); - txt(10, 5, "Do you want me to generate ~/.i3/config?"); - txt(85, 8, "Yes, generate ~/.i3/config"); - txt(85, 10, "No, I will use the defaults"); + txt(10, 2, "You have not configured i3 yet."); + txt(10, 3, "Do you want me to generate ~/.i3/config?"); + txt(85, 5, "Yes, generate ~/.i3/config"); + txt(85, 7, "No, I will use the defaults"); /* green */ xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#00FF00")); - txt(25, 8, ""); + txt(25, 5, ""); /* red */ xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#FF0000")); - txt(31, 10, ""); + txt(31, 7, ""); } if (current_step == STEP_GENERATE) { xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#FFFFFF")); - txt(10, 1, "i3: generate config"); - - txt(10, 4, "Please choose either:"); - txt(85, 6, "Win as default modifier"); - txt(85, 7, "Alt as default modifier"); - txt(10, 9, "Afterwards, press"); - txt(85, 11, "to write ~/.i3/config"); - txt(85, 12, "to abort"); + txt(10, 2, "Please choose either:"); + txt(85, 4, "Win as default modifier"); + txt(85, 5, "Alt as default modifier"); + txt(10, 7, "Afterwards, press"); + txt(85, 9, "to write ~/.i3/config"); + txt(85, 10, "to abort"); /* the not-selected modifier */ if (modifier == MOD_SUPER) - txt(31, 7, ""); - else txt(31, 6, ""); + txt(31, 5, ""); + else txt(31, 4, ""); /* the selected modifier */ xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FONT, font_bold_id); if (modifier == MOD_SUPER) - txt(31, 6, ""); - else txt(31, 7, ""); + txt(31, 4, ""); + else txt(31, 5, ""); /* green */ uint32_t mask = XCB_GC_FOREGROUND | XCB_GC_FONT; uint32_t values[] = { get_colorpixel(conn, "#00FF00"), font_id }; xcb_change_gc(conn, pixmap_gc, mask, values); - txt(25, 11, ""); + txt(25, 9, ""); /* red */ xcb_change_gc_single(conn, pixmap_gc, XCB_GC_FOREGROUND, get_colorpixel(conn, "#FF0000")); - txt(31, 12, ""); + txt(31, 10, ""); } /* Copy the contents of the pixmap to the real window */ @@ -257,8 +251,19 @@ static int handle_key_press(void *ignored, xcb_connection_t *conn, xcb_key_press printf("sym = %c (%d)\n", sym, sym); if (sym == XK_Return || sym == XK_KP_Enter) { - if (current_step == STEP_WELCOME) + if (current_step == STEP_WELCOME) { current_step = STEP_GENERATE; + /* Set window title */ + xcb_change_property(conn, + XCB_PROP_MODE_REPLACE, + win, + A__NET_WM_NAME, + A_UTF8_STRING, + 8, + strlen("i3: generate config"), + "i3: generate config"); + xcb_flush(conn); + } else finish(); } @@ -431,6 +436,12 @@ int main(int argc, char *argv[]) { xcb_connection_has_error(conn)) errx(1, "Cannot open display\n"); + /* Place requests for the atoms we need as soon as possible */ + #define xmacro(atom) \ + xcb_intern_atom_cookie_t atom ## _cookie = xcb_intern_atom(conn, 0, strlen(#atom), #atom); + #include "atoms.xmacro" + #undef xmacro + xcb_screen_t *root_screen = xcb_aux_get_screen(conn, screens); root = root_screen->root; @@ -444,16 +455,45 @@ int main(int argc, char *argv[]) { /* Open an input window */ win = open_input_window(conn, 300, 205); + /* Setup NetWM atoms */ + #define xmacro(name) \ + do { \ + xcb_intern_atom_reply_t *reply = xcb_intern_atom_reply(conn, name ## _cookie, NULL); \ + if (!reply) \ + errx(EXIT_FAILURE, "Could not get atom " # name "\n"); \ + \ + A_ ## name = reply->atom; \ + free(reply); \ + } while (0); + #include "atoms.xmacro" + #undef xmacro + + /* Set dock mode */ + xcb_change_property(conn, + XCB_PROP_MODE_REPLACE, + win, + A__NET_WM_WINDOW_TYPE, + A_ATOM, + 32, + 1, + (unsigned char*) &A__NET_WM_WINDOW_TYPE_DIALOG); + + /* Set window title */ + xcb_change_property(conn, + XCB_PROP_MODE_REPLACE, + win, + A__NET_WM_NAME, + A_UTF8_STRING, + 8, + strlen("i3: first configuration"), + "i3: first configuration"); + /* Create pixmap */ pixmap = xcb_generate_id(conn); pixmap_gc = xcb_generate_id(conn); xcb_create_pixmap(conn, root_screen->root_depth, pixmap, win, 500, 500); xcb_create_gc(conn, pixmap_gc, pixmap, 0, 0); - /* Set input focus (we have override_redirect=1, so the wm will not do - * this for us) */ - xcb_set_input_focus(conn, XCB_INPUT_FOCUS_POINTER_ROOT, win, XCB_CURRENT_TIME); - /* Grab the keyboard to get all input */ xcb_flush(conn); diff --git a/i3-config-wizard/xcb.c b/i3-config-wizard/xcb.c index 2c2e5614..d1753d18 100644 --- a/i3-config-wizard/xcb.c +++ b/i3-config-wizard/xcb.c @@ -109,11 +109,8 @@ xcb_window_t open_input_window(xcb_connection_t *conn, uint32_t width, uint32_t mask |= XCB_CW_BACK_PIXEL; values[0] = 0; - mask |= XCB_CW_OVERRIDE_REDIRECT; - values[1] = 1; - mask |= XCB_CW_EVENT_MASK; - values[2] = XCB_EVENT_MASK_EXPOSURE; + values[1] = XCB_EVENT_MASK_EXPOSURE; xcb_create_window(conn, XCB_COPY_FROM_PARENT, diff --git a/i3-config-wizard/xcb.h b/i3-config-wizard/xcb.h index 933dbb98..40aeec88 100644 --- a/i3-config-wizard/xcb.h +++ b/i3-config-wizard/xcb.h @@ -4,6 +4,10 @@ /* from X11/keysymdef.h */ #define XCB_NUM_LOCK 0xff7f +#define xmacro(atom) xcb_atom_t A_ ## atom; +#include "atoms.xmacro" +#undef xmacro + extern unsigned int xcb_numlock_mask; void xcb_change_gc_single(xcb_connection_t *conn, xcb_gcontext_t gc, uint32_t mask, uint32_t value); -- 2.39.5