x11: Manage xserver focus better
This commit is contained in:
parent
707e10fa75
commit
d6e5525a20
|
@ -421,5 +421,7 @@ int
|
|||
wlsc_xserver_init(struct wlsc_compositor *compositor);
|
||||
void
|
||||
wlsc_xserver_destroy(struct wlsc_compositor *compositor);
|
||||
void
|
||||
wlsc_xserver_surface_activate(struct wlsc_surface *surface);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -892,6 +892,9 @@ activate(struct wlsc_shell *base, struct wlsc_surface *es,
|
|||
|
||||
wlsc_surface_activate(es, device, time);
|
||||
|
||||
if (compositor->wxs)
|
||||
wlsc_xserver_surface_activate(es);
|
||||
|
||||
if (es == shell->background) {
|
||||
wl_list_remove(&es->link);
|
||||
wl_list_insert(compositor->surface_list.prev, &es->link);
|
||||
|
|
|
@ -92,6 +92,9 @@ struct wlsc_wm_window {
|
|||
struct wl_listener surface_destroy_listener;
|
||||
};
|
||||
|
||||
static struct wlsc_wm_window *
|
||||
get_wm_window(struct wlsc_surface *surface);
|
||||
|
||||
static void
|
||||
wlsc_wm_handle_configure_request(struct wlsc_wm *wm, xcb_generic_event_t *event)
|
||||
{
|
||||
|
@ -187,10 +190,38 @@ static void
|
|||
wlsc_wm_activate(struct wlsc_wm *wm,
|
||||
struct wlsc_wm_window *window, xcb_timestamp_t time)
|
||||
{
|
||||
xcb_client_message_event_t client_message;
|
||||
|
||||
client_message.response_type = XCB_CLIENT_MESSAGE;
|
||||
client_message.format = 32;
|
||||
client_message.window = window->id;
|
||||
client_message.type = wm->atom.wm_protocols;
|
||||
client_message.data.data32[0] = wm->atom.wm_take_focus;
|
||||
client_message.data.data32[1] = XCB_TIME_CURRENT_TIME;
|
||||
|
||||
xcb_send_event(wm->conn, 0, window->id,
|
||||
XCB_EVENT_MASK_SUBSTRUCTURE_REDIRECT,
|
||||
(char *) &client_message);
|
||||
|
||||
xcb_set_input_focus (wm->conn,
|
||||
XCB_INPUT_FOCUS_POINTER_ROOT, window->id, time);
|
||||
}
|
||||
|
||||
WL_EXPORT void
|
||||
wlsc_xserver_surface_activate(struct wlsc_surface *surface)
|
||||
{
|
||||
struct wlsc_wm_window *window = get_wm_window(surface);
|
||||
struct wlsc_xserver *wxs = surface->compositor->wxs;
|
||||
|
||||
if (window == NULL && wxs && wxs->wm)
|
||||
xcb_set_input_focus (wxs->wm->conn,
|
||||
XCB_INPUT_FOCUS_POINTER_ROOT,
|
||||
XCB_NONE,
|
||||
XCB_TIME_CURRENT_TIME);
|
||||
else
|
||||
wlsc_wm_activate(wxs->wm, window, XCB_TIME_CURRENT_TIME);
|
||||
}
|
||||
|
||||
static void
|
||||
wlsc_wm_handle_map_request(struct wlsc_wm *wm, xcb_generic_event_t *event)
|
||||
{
|
||||
|
@ -214,7 +245,6 @@ wlsc_wm_handle_map_notify(struct wlsc_wm *wm, xcb_generic_event_t *event)
|
|||
xcb_map_notify_event_t *map_notify =
|
||||
(xcb_map_notify_event_t *) event;
|
||||
struct wlsc_wm_window *window;
|
||||
xcb_client_message_event_t client_message;
|
||||
|
||||
fprintf(stderr, "XCB_MAP_NOTIFY\n");
|
||||
|
||||
|
@ -222,18 +252,6 @@ wlsc_wm_handle_map_notify(struct wlsc_wm *wm, xcb_generic_event_t *event)
|
|||
|
||||
window = wl_hash_table_lookup(wm->window_hash, map_notify->window);
|
||||
wlsc_wm_activate(wm, window, XCB_TIME_CURRENT_TIME);
|
||||
|
||||
client_message.response_type = XCB_CLIENT_MESSAGE;
|
||||
client_message.format = 32;
|
||||
client_message.window = window->id;
|
||||
client_message.type = wm->atom.wm_protocols;
|
||||
client_message.data.data32[0] = wm->atom.wm_take_focus;
|
||||
client_message.data.data32[1] = XCB_TIME_CURRENT_TIME;
|
||||
|
||||
xcb_send_event(wm->conn, 0, window->id,
|
||||
XCB_EVENT_MASK_SUBSTRUCTURE_REDIRECT,
|
||||
(char *) &client_message);
|
||||
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -591,6 +609,22 @@ surface_destroy(struct wl_listener *listener,
|
|||
fprintf(stderr, "surface for xid %d destroyed\n", window->id);
|
||||
}
|
||||
|
||||
static struct wlsc_wm_window *
|
||||
get_wm_window(struct wlsc_surface *surface)
|
||||
{
|
||||
struct wl_resource *resource = &surface->surface.resource;
|
||||
struct wl_listener *listener;
|
||||
|
||||
wl_list_for_each(listener, &resource->destroy_listener_list, link) {
|
||||
if (listener->func == surface_destroy)
|
||||
return container_of(listener,
|
||||
struct wlsc_wm_window,
|
||||
surface_destroy_listener);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void
|
||||
xserver_set_window_id(struct wl_client *client, struct wl_resource *resource,
|
||||
struct wl_resource *surface_resource, uint32_t id)
|
||||
|
|
Loading…
Reference in New Issue