From d75c3082579684907c2beccc3a92eb33db91a412 Mon Sep 17 00:00:00 2001 From: Michael Stapelberg Date: Wed, 11 Feb 2009 17:47:42 +0100 Subject: [PATCH] Implement focus on click --- mainx.c | 53 ++++++++++++++++++++++++++++++++++++++--------------- 1 file changed, 38 insertions(+), 15 deletions(-) diff --git a/mainx.c b/mainx.c index 6e205518..8d29b428 100644 --- a/mainx.c +++ b/mainx.c @@ -587,9 +587,15 @@ void reparent_window(xcb_connection_t *conn, xcb_window_t child, mask = XCB_CW_EVENT_MASK; values[0] = XCB_EVENT_MASK_PROPERTY_CHANGE | XCB_EVENT_MASK_STRUCTURE_NOTIFY | - XCB_EVENT_MASK_ENTER_WINDOW; + XCB_EVENT_MASK_ENTER_WINDOW | + XCB_EVENT_MASK_BUTTON_PRESS; xcb_change_window_attributes(conn, child, mask, values); + /* We need to grab the mouse buttons for click to focus */ + xcb_grab_button(conn, false, child, XCB_EVENT_MASK_BUTTON_PRESS, + XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, root, XCB_NONE, XCB_BUTTON_MASK_1, + XCB_BUTTON_MASK_ANY /* don’t filter for any modifiers */); + /* Focus the new window */ xcb_set_input_focus(conn, XCB_INPUT_FOCUS_NONE, new->child, XCB_CURRENT_TIME); @@ -1003,6 +1009,23 @@ static int handle_key_press(void *ignored, xcb_connection_t *conn, xcb_key_press return 1; } +static void set_focus(xcb_connection_t *conn, Client *client) { + /* Update container */ + Client *old_client = client->container->currently_focused; + client->container->currently_focused = client; + + current_col = client->container->col; + current_row = client->container->row; + + /* Set focus to the entered window, and flush xcb buffer immediately */ + xcb_set_input_focus(conn, XCB_INPUT_FOCUS_NONE, client->child, XCB_CURRENT_TIME); + /* Update last/current client’s titlebar */ + if (old_client != NULL) + decorate_window(conn, old_client); + decorate_window(conn, client); + xcb_flush(conn); +} + /* * When the user moves the mouse pointer onto a window, this callback gets called. * @@ -1011,8 +1034,7 @@ static int handle_enter_notify(void *ignored, xcb_connection_t *conn, xcb_enter_ printf("enter_notify\n"); /* This was either a focus for a client’s parent (= titlebar)… */ - Client *client = table_get(byParent, event->event), - *old_client; + Client *client = table_get(byParent, event->event); /* …or the client itself */ if (client == NULL) client = table_get(byChild, event->event); @@ -1023,21 +1045,19 @@ static int handle_enter_notify(void *ignored, xcb_connection_t *conn, xcb_enter_ return 1; } - /* Update container */ - old_client = client->container->currently_focused; - client->container->currently_focused = client; + set_focus(conn, client); - current_col = client->container->col; - current_row = client->container->row; + return 1; +} - /* Set focus to the entered window, and flush xcb buffer immediately */ - xcb_set_input_focus(conn, XCB_INPUT_FOCUS_NONE, client->child, XCB_CURRENT_TIME); - /* Update last/current client’s titlebar */ - if (old_client != NULL) - decorate_window(conn, old_client); - decorate_window(conn, client); - xcb_flush(conn); +static int handle_button_press(void *ignored, xcb_connection_t *conn, xcb_button_press_event_t *event) { + printf("button press!\n"); + /* This was either a focus for a client’s parent (= titlebar)… */ + Client *client = table_get(byChild, event->event); + printf("gots win %08x\n", client); + + set_focus(conn, client); return 1; } @@ -1207,6 +1227,9 @@ int main(int argc, char *argv[], char *env[]) { /* Enter window = user moved his mouse over the window */ xcb_event_set_enter_notify_handler(&evenths, handle_enter_notify, 0); + /* Button press = user pushed a mouse button over one of our windows */ + xcb_event_set_button_press_handler(&evenths, handle_button_press, 0); + xcb_event_set_unmap_notify_handler(&evenths, handle_unmap_notify_event, 0); xcb_property_handlers_init(&prophs, &evenths); -- 2.39.5