input: Send leave and enter pair when the surface moves under the cursor
The client needs to know that the pointer is at a different position in its surface. We can't send motion as that corresponds to the pointer actually moving. Leaving the surface and entering at the new position is a better semantic match and doesn't correspond to pointer motion or user input. https://bugs.freedesktop.org/show_bug.cgi?id=71927
This commit is contained in:
parent
dd62abafa1
commit
db1fccb3d8
|
@ -328,6 +328,7 @@ struct weston_pointer {
|
|||
uint32_t grab_time;
|
||||
|
||||
wl_fixed_t x, y;
|
||||
wl_fixed_t sx, sy;
|
||||
uint32_t button_count;
|
||||
|
||||
struct wl_listener output_destroy_listener;
|
||||
|
|
28
src/input.c
28
src/input.c
|
@ -157,7 +157,7 @@ default_grab_pointer_focus(struct weston_pointer_grab *grab)
|
|||
pointer->x, pointer->y,
|
||||
&sx, &sy);
|
||||
|
||||
if (pointer->focus != view)
|
||||
if (pointer->focus != view || pointer->sx != sx || pointer->sy != sy)
|
||||
weston_pointer_set_focus(pointer, view, sx, sy);
|
||||
}
|
||||
|
||||
|
@ -166,18 +166,19 @@ default_grab_pointer_motion(struct weston_pointer_grab *grab, uint32_t time,
|
|||
wl_fixed_t x, wl_fixed_t y)
|
||||
{
|
||||
struct weston_pointer *pointer = grab->pointer;
|
||||
wl_fixed_t sx, sy;
|
||||
struct wl_list *resource_list;
|
||||
struct wl_resource *resource;
|
||||
|
||||
if (pointer->focus)
|
||||
weston_view_from_global_fixed(pointer->focus, x, y,
|
||||
&pointer->sx, &pointer->sy);
|
||||
|
||||
weston_pointer_move(pointer, x, y);
|
||||
|
||||
if (pointer->focus)
|
||||
weston_view_from_global_fixed(pointer->focus,
|
||||
pointer->x, pointer->y, &sx, &sy);
|
||||
resource_list = &pointer->focus_resource_list;
|
||||
wl_resource_for_each(resource, resource_list) {
|
||||
wl_pointer_send_motion(resource, time, sx, sy);
|
||||
wl_pointer_send_motion(resource, time,
|
||||
pointer->sx, pointer->sy);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -614,16 +615,17 @@ weston_pointer_set_focus(struct weston_pointer *pointer,
|
|||
struct wl_display *display = pointer->seat->compositor->wl_display;
|
||||
uint32_t serial;
|
||||
struct wl_list *focus_resource_list;
|
||||
int different_surface = 0;
|
||||
int refocus = 0;
|
||||
|
||||
if ((!pointer->focus && view) ||
|
||||
(pointer->focus && !view) ||
|
||||
(pointer->focus && pointer->focus->surface != view->surface))
|
||||
different_surface = 1;
|
||||
(pointer->focus && pointer->focus->surface != view->surface) ||
|
||||
pointer->sx != sx || pointer->sy != sy)
|
||||
refocus = 1;
|
||||
|
||||
focus_resource_list = &pointer->focus_resource_list;
|
||||
|
||||
if (!wl_list_empty(focus_resource_list) && different_surface) {
|
||||
if (!wl_list_empty(focus_resource_list) && refocus) {
|
||||
serial = wl_display_next_serial(display);
|
||||
wl_resource_for_each(resource, focus_resource_list) {
|
||||
wl_pointer_send_leave(resource, serial,
|
||||
|
@ -633,8 +635,7 @@ weston_pointer_set_focus(struct weston_pointer *pointer,
|
|||
move_resources(&pointer->resource_list, focus_resource_list);
|
||||
}
|
||||
|
||||
if (find_resource_for_view(&pointer->resource_list, view) &&
|
||||
different_surface) {
|
||||
if (find_resource_for_view(&pointer->resource_list, view) && refocus) {
|
||||
struct wl_client *surface_client =
|
||||
wl_resource_get_client(view->surface->resource);
|
||||
|
||||
|
@ -672,6 +673,9 @@ weston_pointer_set_focus(struct weston_pointer *pointer,
|
|||
|
||||
pointer->focus = view;
|
||||
pointer->focus_view_listener.notify = pointer_focus_view_destroyed;
|
||||
pointer->sx = sx;
|
||||
pointer->sy = sy;
|
||||
|
||||
wl_signal_emit(&pointer->focus_signal, pointer);
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue