clutter/seat: Add API to initialize pointer position

This is different from "warping" as it doesn't necessarily result in a
pointer motion event. This can be helpful during initializing so we can
avoid faked pointer events that would otherwise need to be special cased
to not appear as actual pointer movements.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3070>
This commit is contained in:
Jonas Ådahl 2023-06-12 16:20:47 +02:00 committed by Marge Bot
parent 97f0e2e691
commit 060c4c2dfc
7 changed files with 85 additions and 0 deletions

View File

@ -33,4 +33,9 @@ ClutterGrabState clutter_seat_grab (ClutterSeat *seat,
void clutter_seat_ungrab (ClutterSeat *seat,
uint32_t time);
CLUTTER_EXPORT
void clutter_seat_init_pointer_position (ClutterSeat *seat,
float x,
float y);
#endif /* CLUTTER_SEAT_PRIVATE_H */

View File

@ -626,6 +626,16 @@ clutter_seat_warp_pointer (ClutterSeat *seat,
CLUTTER_SEAT_GET_CLASS (seat)->warp_pointer (seat, x, y);
}
void
clutter_seat_init_pointer_position (ClutterSeat *seat,
float x,
float y)
{
g_return_if_fail (CLUTTER_IS_SEAT (seat));
CLUTTER_SEAT_GET_CLASS (seat)->init_pointer_position (seat, x, y);
}
/**
* clutter_seat_get_touch_mode:
* @seat: a #ClutterSeat

View File

@ -90,6 +90,10 @@ struct _ClutterSeatClass
int x,
int y);
void (* init_pointer_position) (ClutterSeat *seat,
float x,
float y);
gboolean (* query_state) (ClutterSeat *seat,
ClutterInputDevice *device,
ClutterEventSequence *sequence,

View File

@ -3157,6 +3157,38 @@ meta_seat_impl_warp_pointer (MetaSeatImpl *seat_impl,
g_object_unref (task);
}
static gboolean
init_pointer_position_in_impl (GTask *task)
{
MetaSeatImpl *seat_impl = g_task_get_source_object (task);
graphene_point_t *point;
point = g_task_get_task_data (task);
seat_impl->pointer_x = point->x;
seat_impl->pointer_y = point->y;
g_task_return_boolean (task, TRUE);
return G_SOURCE_REMOVE;
}
void
meta_seat_impl_init_pointer_position (MetaSeatImpl *seat_impl,
float x,
float y)
{
graphene_point_t *point;
g_autoptr (GTask) task = NULL;
point = graphene_point_alloc ();
point->x = x;
point->y = y;
task = g_task_new (seat_impl, NULL, NULL, NULL);
g_task_set_task_data (task, point, (GDestroyNotify) graphene_point_free);
meta_seat_impl_run_input_task (seat_impl, task,
(GSourceFunc) init_pointer_position_in_impl);
}
gboolean
meta_seat_impl_query_state (MetaSeatImpl *seat_impl,
ClutterInputDevice *device,

View File

@ -226,6 +226,9 @@ void meta_seat_impl_set_viewports (MetaSeatImpl *seat_impl,
void meta_seat_impl_warp_pointer (MetaSeatImpl *seat_impl,
int x,
int y);
void meta_seat_impl_init_pointer_position (MetaSeatImpl *seat_impl,
float x,
float y);
gboolean meta_seat_impl_query_state (MetaSeatImpl *seat_impl,
ClutterInputDevice *device,
ClutterEventSequence *sequence,

View File

@ -342,6 +342,16 @@ meta_seat_native_warp_pointer (ClutterSeat *seat,
meta_seat_impl_warp_pointer (seat_native->impl, x, y);
}
static void
meta_seat_native_init_pointer_position (ClutterSeat *seat,
float x,
float y)
{
MetaSeatNative *seat_native = META_SEAT_NATIVE (seat);
meta_seat_impl_init_pointer_position (seat_native->impl, x, y);
}
static gboolean
meta_seat_native_query_state (ClutterSeat *seat,
ClutterInputDevice *device,
@ -374,6 +384,7 @@ meta_seat_native_class_init (MetaSeatNativeClass *klass)
seat_class->create_virtual_device = meta_seat_native_create_virtual_device;
seat_class->get_supported_virtual_device_types = meta_seat_native_get_supported_virtual_device_types;
seat_class->warp_pointer = meta_seat_native_warp_pointer;
seat_class->init_pointer_position = meta_seat_native_init_pointer_position;
seat_class->handle_event_post = meta_seat_native_handle_event_post;
seat_class->query_state = meta_seat_native_query_state;

View File

@ -1654,6 +1654,25 @@ meta_seat_x11_warp_pointer (ClutterSeat *seat,
meta_clutter_x11_untrap_x_errors ();
}
static void
meta_seat_x11_init_pointer_position (ClutterSeat *seat,
float x,
float y)
{
MetaSeatX11 *seat_x11 = META_SEAT_X11 (seat);
Display *xdisplay = xdisplay_from_seat (seat_x11);
Window root_xwindow = root_xwindow_from_seat (seat_x11);
meta_clutter_x11_trap_x_errors ();
XIWarpPointer (xdisplay,
seat_x11->pointer_id,
None,
root_xwindow,
0, 0, 0, 0,
(int) x, (int) y);
meta_clutter_x11_untrap_x_errors ();
}
static uint32_t
translate_state (XIButtonState *button_state,
XIModifierState *modifier_state,
@ -1865,6 +1884,7 @@ meta_seat_x11_class_init (MetaSeatX11Class *klass)
seat_class->create_virtual_device = meta_seat_x11_create_virtual_device;
seat_class->get_supported_virtual_device_types = meta_seat_x11_get_supported_virtual_device_types;
seat_class->warp_pointer = meta_seat_x11_warp_pointer;
seat_class->init_pointer_position = meta_seat_x11_init_pointer_position;
seat_class->handle_event_post = meta_seat_x11_handle_event_post;
seat_class->query_state = meta_seat_x11_query_state;
seat_class->grab = meta_seat_x11_grab;