backends/native: Allow infinitely small pointer constraint regions
The small catch is that MtkRegion (and pixman regions) "optimize away" 0-size rectangles, so a 0-sized region will always be seen as having a 0,0 origin. We don't want that, so transfer the origin separately from the region. While at it, make the Wayland pointer lock use one such 0-size region, to avoid the 1x1px wiggle room that it currently has (accounting for subpixel motion). Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3420>
This commit is contained in:
parent
c931ed0d81
commit
07d24fe502
7 changed files with 47 additions and 15 deletions
|
@ -48,6 +48,7 @@ struct _MetaPointerConstraint
|
||||||
{
|
{
|
||||||
GObject parent_instance;
|
GObject parent_instance;
|
||||||
MtkRegion *region;
|
MtkRegion *region;
|
||||||
|
graphene_point_t origin;
|
||||||
double min_edge_distance;
|
double min_edge_distance;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -81,21 +82,27 @@ meta_pointer_constraint_class_init (MetaPointerConstraintClass *klass)
|
||||||
|
|
||||||
|
|
||||||
MetaPointerConstraint *
|
MetaPointerConstraint *
|
||||||
meta_pointer_constraint_new (const MtkRegion *region,
|
meta_pointer_constraint_new (const MtkRegion *region,
|
||||||
double min_edge_distance)
|
graphene_point_t origin,
|
||||||
|
double min_edge_distance)
|
||||||
{
|
{
|
||||||
MetaPointerConstraint *constraint;
|
MetaPointerConstraint *constraint;
|
||||||
|
|
||||||
constraint = g_object_new (META_TYPE_POINTER_CONSTRAINT, NULL);
|
constraint = g_object_new (META_TYPE_POINTER_CONSTRAINT, NULL);
|
||||||
constraint->region = mtk_region_copy (region);
|
constraint->region = mtk_region_copy (region);
|
||||||
|
constraint->origin = origin;
|
||||||
constraint->min_edge_distance = min_edge_distance;
|
constraint->min_edge_distance = min_edge_distance;
|
||||||
|
|
||||||
return constraint;
|
return constraint;
|
||||||
}
|
}
|
||||||
|
|
||||||
MtkRegion *
|
MtkRegion *
|
||||||
meta_pointer_constraint_get_region (MetaPointerConstraint *constraint)
|
meta_pointer_constraint_get_region (MetaPointerConstraint *constraint,
|
||||||
|
graphene_point_t *origin)
|
||||||
{
|
{
|
||||||
|
if (origin)
|
||||||
|
*origin = constraint->origin;
|
||||||
|
|
||||||
return constraint->region;
|
return constraint->region;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -32,10 +32,12 @@ G_BEGIN_DECLS
|
||||||
G_DECLARE_FINAL_TYPE (MetaPointerConstraint, meta_pointer_constraint,
|
G_DECLARE_FINAL_TYPE (MetaPointerConstraint, meta_pointer_constraint,
|
||||||
META, POINTER_CONSTRAINT, GObject);
|
META, POINTER_CONSTRAINT, GObject);
|
||||||
|
|
||||||
MetaPointerConstraint * meta_pointer_constraint_new (const MtkRegion *region,
|
MetaPointerConstraint * meta_pointer_constraint_new (const MtkRegion *region,
|
||||||
double min_edge_distance);
|
graphene_point_t origin,
|
||||||
|
double min_edge_distance);
|
||||||
|
|
||||||
MtkRegion * meta_pointer_constraint_get_region (MetaPointerConstraint *constraint);
|
MtkRegion * meta_pointer_constraint_get_region (MetaPointerConstraint *constraint,
|
||||||
|
graphene_point_t *origin);
|
||||||
|
|
||||||
double meta_pointer_constraint_get_min_edge_distance (MetaPointerConstraint *constraint);
|
double meta_pointer_constraint_get_min_edge_distance (MetaPointerConstraint *constraint);
|
||||||
|
|
||||||
|
|
|
@ -400,13 +400,15 @@ meta_backend_native_set_pointer_constraint (MetaBackend *backend,
|
||||||
|
|
||||||
if (constraint)
|
if (constraint)
|
||||||
{
|
{
|
||||||
|
graphene_point_t origin;
|
||||||
double min_edge_distance;
|
double min_edge_distance;
|
||||||
|
|
||||||
region = meta_pointer_constraint_get_region (constraint);
|
region = meta_pointer_constraint_get_region (constraint, &origin);
|
||||||
min_edge_distance =
|
min_edge_distance =
|
||||||
meta_pointer_constraint_get_min_edge_distance (constraint);
|
meta_pointer_constraint_get_min_edge_distance (constraint);
|
||||||
constraint_impl = meta_pointer_constraint_impl_native_new (constraint,
|
constraint_impl = meta_pointer_constraint_impl_native_new (constraint,
|
||||||
region,
|
region,
|
||||||
|
origin,
|
||||||
min_edge_distance);
|
min_edge_distance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -33,6 +33,7 @@ struct _MetaPointerConstraintImplNative
|
||||||
MetaPointerConstraintImpl parent;
|
MetaPointerConstraintImpl parent;
|
||||||
MetaPointerConstraint *constraint;
|
MetaPointerConstraint *constraint;
|
||||||
MtkRegion *region;
|
MtkRegion *region;
|
||||||
|
graphene_point_t origin;
|
||||||
double min_edge_distance;
|
double min_edge_distance;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -461,6 +462,14 @@ meta_pointer_constraint_impl_native_constraint (MetaPointerConstraintImpl *const
|
||||||
constraint_impl_native = META_POINTER_CONSTRAINT_IMPL_NATIVE (constraint_impl);
|
constraint_impl_native = META_POINTER_CONSTRAINT_IMPL_NATIVE (constraint_impl);
|
||||||
|
|
||||||
region = mtk_region_ref (constraint_impl_native->region);
|
region = mtk_region_ref (constraint_impl_native->region);
|
||||||
|
|
||||||
|
if (mtk_region_is_empty (region))
|
||||||
|
{
|
||||||
|
*x_inout = constraint_impl_native->origin.x;
|
||||||
|
*y_inout = constraint_impl_native->origin.y;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
x = *x_inout;
|
x = *x_inout;
|
||||||
y = *y_inout;
|
y = *y_inout;
|
||||||
|
|
||||||
|
@ -589,6 +598,7 @@ meta_pointer_constraint_impl_native_ensure_constrained (MetaPointerConstraintImp
|
||||||
{
|
{
|
||||||
MetaPointerConstraintImplNative *constraint_impl_native;
|
MetaPointerConstraintImplNative *constraint_impl_native;
|
||||||
graphene_point_t point;
|
graphene_point_t point;
|
||||||
|
ClutterSeat *seat;
|
||||||
g_autoptr (MtkRegion) region = NULL;
|
g_autoptr (MtkRegion) region = NULL;
|
||||||
float x;
|
float x;
|
||||||
float y;
|
float y;
|
||||||
|
@ -596,17 +606,24 @@ meta_pointer_constraint_impl_native_ensure_constrained (MetaPointerConstraintImp
|
||||||
constraint_impl_native = META_POINTER_CONSTRAINT_IMPL_NATIVE (constraint_impl);
|
constraint_impl_native = META_POINTER_CONSTRAINT_IMPL_NATIVE (constraint_impl);
|
||||||
region = mtk_region_ref (constraint_impl_native->region);
|
region = mtk_region_ref (constraint_impl_native->region);
|
||||||
|
|
||||||
clutter_seat_query_state (clutter_input_device_get_seat (device),
|
seat = clutter_input_device_get_seat (device);
|
||||||
device, NULL, &point, NULL);
|
clutter_seat_query_state (seat, device, NULL, &point, NULL);
|
||||||
x = point.x;
|
x = point.x;
|
||||||
y = point.y;
|
y = point.y;
|
||||||
|
|
||||||
if (!mtk_region_contains_point (region, (int) x, (int) y))
|
if (mtk_region_is_empty (region))
|
||||||
|
{
|
||||||
|
if (x != constraint_impl_native->origin.x ||
|
||||||
|
y != constraint_impl_native->origin.y)
|
||||||
|
clutter_seat_warp_pointer (seat, x, y);
|
||||||
|
}
|
||||||
|
else if (!mtk_region_contains_point (region,
|
||||||
|
(int) x - constraint_impl_native->origin.x,
|
||||||
|
(int) y - constraint_impl_native->origin.y))
|
||||||
{
|
{
|
||||||
g_autoptr (GArray) borders = NULL;
|
g_autoptr (GArray) borders = NULL;
|
||||||
float closest_distance_2 = FLT_MAX;
|
float closest_distance_2 = FLT_MAX;
|
||||||
MetaBorder *closest_border = NULL;
|
MetaBorder *closest_border = NULL;
|
||||||
ClutterSeat *seat;
|
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
|
|
||||||
borders = g_array_new (FALSE, FALSE, sizeof (MetaBorder));
|
borders = g_array_new (FALSE, FALSE, sizeof (MetaBorder));
|
||||||
|
@ -628,7 +645,6 @@ meta_pointer_constraint_impl_native_ensure_constrained (MetaPointerConstraintImp
|
||||||
|
|
||||||
closest_point_behind_border (closest_border, &x, &y);
|
closest_point_behind_border (closest_border, &x, &y);
|
||||||
|
|
||||||
seat = clutter_backend_get_default_seat (clutter_get_default_backend ());
|
|
||||||
clutter_seat_warp_pointer (seat, x, y);
|
clutter_seat_warp_pointer (seat, x, y);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -667,6 +683,7 @@ meta_pointer_constraint_impl_native_class_init (MetaPointerConstraintImplNativeC
|
||||||
MetaPointerConstraintImpl *
|
MetaPointerConstraintImpl *
|
||||||
meta_pointer_constraint_impl_native_new (MetaPointerConstraint *constraint,
|
meta_pointer_constraint_impl_native_new (MetaPointerConstraint *constraint,
|
||||||
const MtkRegion *region,
|
const MtkRegion *region,
|
||||||
|
graphene_point_t origin,
|
||||||
double min_edge_distance)
|
double min_edge_distance)
|
||||||
{
|
{
|
||||||
MetaPointerConstraintImplNative *constraint_impl;
|
MetaPointerConstraintImplNative *constraint_impl;
|
||||||
|
@ -676,6 +693,7 @@ meta_pointer_constraint_impl_native_new (MetaPointerConstraint *constraint,
|
||||||
constraint_impl->constraint = constraint;
|
constraint_impl->constraint = constraint;
|
||||||
constraint_impl->region = mtk_region_copy (region);
|
constraint_impl->region = mtk_region_copy (region);
|
||||||
constraint_impl->min_edge_distance = min_edge_distance;
|
constraint_impl->min_edge_distance = min_edge_distance;
|
||||||
|
constraint_impl->origin = origin;
|
||||||
|
|
||||||
return META_POINTER_CONSTRAINT_IMPL (constraint_impl);
|
return META_POINTER_CONSTRAINT_IMPL (constraint_impl);
|
||||||
}
|
}
|
||||||
|
|
|
@ -37,6 +37,7 @@ G_DECLARE_FINAL_TYPE (MetaPointerConstraintImplNative,
|
||||||
|
|
||||||
MetaPointerConstraintImpl * meta_pointer_constraint_impl_native_new (MetaPointerConstraint *constraint_impl,
|
MetaPointerConstraintImpl * meta_pointer_constraint_impl_native_new (MetaPointerConstraint *constraint_impl,
|
||||||
const MtkRegion *region,
|
const MtkRegion *region,
|
||||||
|
graphene_point_t origin,
|
||||||
double min_edge_distance);
|
double min_edge_distance);
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
|
|
@ -245,10 +245,10 @@ meta_pointer_confinement_wayland_create_constraint (MetaPointerConfinementWaylan
|
||||||
}
|
}
|
||||||
|
|
||||||
meta_wayland_surface_get_absolute_coordinates (surface, 0, 0, &dx, &dy);
|
meta_wayland_surface_get_absolute_coordinates (surface, 0, 0, &dx, &dy);
|
||||||
mtk_region_translate (region, dx, dy);
|
|
||||||
|
|
||||||
min_edge_distance = wl_fixed_to_double (1) * geometry_scale;
|
min_edge_distance = wl_fixed_to_double (1) * geometry_scale;
|
||||||
constraint = meta_pointer_constraint_new (g_steal_pointer (®ion),
|
constraint = meta_pointer_constraint_new (g_steal_pointer (®ion),
|
||||||
|
GRAPHENE_POINT_INIT (dx, dy),
|
||||||
min_edge_distance);
|
min_edge_distance);
|
||||||
|
|
||||||
return constraint;
|
return constraint;
|
||||||
|
|
|
@ -74,10 +74,12 @@ meta_pointer_lock_wayland_create_constraint (MetaPointerConfinementWayland *conf
|
||||||
&sx, &sy);
|
&sx, &sy);
|
||||||
|
|
||||||
meta_wayland_surface_get_absolute_coordinates (surface, sx, sy, &x, &y);
|
meta_wayland_surface_get_absolute_coordinates (surface, sx, sy, &x, &y);
|
||||||
rect = (MtkRectangle) { .x = x, .y = y, .width = 1, .height = 1 };
|
rect = (MtkRectangle) { .x = 0, .y = 0, .width = 0, .height = 0 };
|
||||||
region = mtk_region_create_rectangle (&rect);
|
region = mtk_region_create_rectangle (&rect);
|
||||||
|
|
||||||
constraint = meta_pointer_constraint_new (g_steal_pointer (®ion), 0.0);
|
constraint = meta_pointer_constraint_new (g_steal_pointer (®ion),
|
||||||
|
GRAPHENE_POINT_INIT (x, y),
|
||||||
|
0.0);
|
||||||
|
|
||||||
return constraint;
|
return constraint;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue