mirror of
				https://gitlab.freedesktop.org/wlroots/wlroots.git
				synced 2025-11-03 09:01:40 -05:00 
			
		
		
		
	pointer-constraints: make region not a pointer, add committed bitfield
This commit is contained in:
		
							parent
							
								
									c89cd4945b
								
							
						
					
					
						commit
						31cc2fa4f9
					
				
					 3 changed files with 56 additions and 49 deletions
				
			
		| 
						 | 
				
			
			@ -15,13 +15,18 @@ enum wlr_pointer_constraint_v1_type {
 | 
			
		|||
	WLR_POINTER_CONSTRAINT_V1_CONFINED,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
enum wlr_pointer_constraint_v1_state_field {
 | 
			
		||||
	WLR_POINTER_CONSTRAINT_V1_STATE_REGION = 1 << 0,
 | 
			
		||||
	WLR_POINTER_CONSTRAINT_V1_STATE_CURSOR_HINT = 1 << 1,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct wlr_pointer_constraint_v1_state {
 | 
			
		||||
	pixman_region32_t *region;
 | 
			
		||||
	uint32_t committed; // enum wlr_pointer_constraint_v1_state_field
 | 
			
		||||
	pixman_region32_t region;
 | 
			
		||||
 | 
			
		||||
	// only valid for locked_pointer
 | 
			
		||||
	struct {
 | 
			
		||||
		double x, y;
 | 
			
		||||
		bool valid;
 | 
			
		||||
	} cursor_hint;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -798,7 +798,9 @@ static void handle_constraint_destroy(
 | 
			
		|||
	struct roots_seat* seat = constraint->seat->data;
 | 
			
		||||
	if (seat->cursor->active_constraint == constraint) {
 | 
			
		||||
		roots_cursor_constrain(seat->cursor, NULL, NAN, NAN);
 | 
			
		||||
		if (constraint->current.cursor_hint.valid && seat->cursor->pointer_view) {
 | 
			
		||||
		if (constraint->current.committed &
 | 
			
		||||
				WLR_POINTER_CONSTRAINT_V1_STATE_CURSOR_HINT &&
 | 
			
		||||
				seat->cursor->pointer_view) {
 | 
			
		||||
			double sx = constraint->current.cursor_hint.x;
 | 
			
		||||
			double sy = constraint->current.cursor_hint.y;
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -57,15 +57,8 @@ static void pointer_constraint_destroy(struct wlr_pointer_constraint_v1 *constra
 | 
			
		|||
		&constraint->pointer_constraints->events.constraint_destroy,
 | 
			
		||||
		constraint);
 | 
			
		||||
 | 
			
		||||
	if (constraint->current.region) {
 | 
			
		||||
		pixman_region32_fini(constraint->current.region);
 | 
			
		||||
		free(constraint->current.region);
 | 
			
		||||
	}
 | 
			
		||||
	if (constraint->pending.region &&
 | 
			
		||||
			constraint->current.region != constraint->pending.region) {
 | 
			
		||||
		pixman_region32_fini(constraint->pending.region);
 | 
			
		||||
		free(constraint->pending.region);
 | 
			
		||||
	}
 | 
			
		||||
	pixman_region32_fini(&constraint->current.region);
 | 
			
		||||
	pixman_region32_fini(&constraint->pending.region);
 | 
			
		||||
	pixman_region32_fini(&constraint->region);
 | 
			
		||||
	free(constraint);
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -80,24 +73,17 @@ static void pointer_constraint_destroy_resource(struct wl_resource *resource) {
 | 
			
		|||
static void pointer_constraint_set_region(
 | 
			
		||||
		struct wlr_pointer_constraint_v1 *constraint,
 | 
			
		||||
		struct wl_resource *region_resource) {
 | 
			
		||||
	if (constraint->pending.region &&
 | 
			
		||||
			constraint->current.region != constraint->pending.region) {
 | 
			
		||||
		pixman_region32_fini(constraint->pending.region);
 | 
			
		||||
		free(constraint->pending.region);
 | 
			
		||||
	}
 | 
			
		||||
	pixman_region32_clear(&constraint->pending.region);
 | 
			
		||||
 | 
			
		||||
	if (region_resource) {
 | 
			
		||||
		constraint->pending.region = calloc(1, sizeof(pixman_region32_t));
 | 
			
		||||
		pixman_region32_init(constraint->pending.region);
 | 
			
		||||
 | 
			
		||||
		pixman_region32_t *region = wlr_region_from_resource(region_resource);
 | 
			
		||||
		pixman_region32_copy(constraint->pending.region, region);
 | 
			
		||||
	} else {
 | 
			
		||||
		constraint->pending.region = NULL;
 | 
			
		||||
		pixman_region32_copy(&constraint->pending.region, region);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	constraint->pending.committed |= WLR_POINTER_CONSTRAINT_V1_STATE_REGION;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void pointer_constraint_set_region_wrapper(struct wl_client *client,
 | 
			
		||||
static void pointer_constraint_handle_set_region(struct wl_client *client,
 | 
			
		||||
		struct wl_resource *resource, struct wl_resource *region_resource) {
 | 
			
		||||
	struct wlr_pointer_constraint_v1 *constraint =
 | 
			
		||||
		pointer_constraint_from_resource(resource);
 | 
			
		||||
| 
						 | 
				
			
			@ -112,27 +98,28 @@ static void pointer_constraint_set_cursor_position_hint(struct wl_client *client
 | 
			
		|||
 | 
			
		||||
	constraint->pending.cursor_hint.x = wl_fixed_to_double(x);
 | 
			
		||||
	constraint->pending.cursor_hint.y = wl_fixed_to_double(y);
 | 
			
		||||
	constraint->pending.cursor_hint.valid = true;
 | 
			
		||||
	constraint->pending.committed |= WLR_POINTER_CONSTRAINT_V1_STATE_CURSOR_HINT;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void pointer_constraint_handle_commit(
 | 
			
		||||
		struct wlr_pointer_constraint_v1 *constraint) {
 | 
			
		||||
	constraint->current.cursor_hint = constraint->pending.cursor_hint;
 | 
			
		||||
 | 
			
		||||
	if (constraint->current.region != constraint->pending.region) {
 | 
			
		||||
		if (constraint->current.region) {
 | 
			
		||||
			pixman_region32_fini(constraint->current.region);
 | 
			
		||||
			free(constraint->current.region);
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		constraint->current.region = constraint->pending.region;
 | 
			
		||||
	if (constraint->pending.committed &
 | 
			
		||||
			WLR_POINTER_CONSTRAINT_V1_STATE_REGION) {
 | 
			
		||||
		pixman_region32_copy(&constraint->current.region,
 | 
			
		||||
			&constraint->pending.region);
 | 
			
		||||
	}
 | 
			
		||||
	if (constraint->pending.committed &
 | 
			
		||||
			WLR_POINTER_CONSTRAINT_V1_STATE_CURSOR_HINT) {
 | 
			
		||||
		constraint->current.cursor_hint = constraint->pending.cursor_hint;
 | 
			
		||||
	}
 | 
			
		||||
	constraint->current.committed |= constraint->pending.committed;
 | 
			
		||||
 | 
			
		||||
	constraint->pending.committed = 0;
 | 
			
		||||
 | 
			
		||||
	pixman_region32_clear(&constraint->region);
 | 
			
		||||
 | 
			
		||||
	if (constraint->current.region) {
 | 
			
		||||
	if (pixman_region32_not_empty(&constraint->current.region)) {
 | 
			
		||||
		pixman_region32_intersect(&constraint->region,
 | 
			
		||||
			&constraint->surface->input_region, constraint->current.region);
 | 
			
		||||
			&constraint->surface->input_region, &constraint->current.region);
 | 
			
		||||
	} else {
 | 
			
		||||
		pixman_region32_copy(&constraint->region,
 | 
			
		||||
			&constraint->surface->input_region);
 | 
			
		||||
| 
						 | 
				
			
			@ -162,18 +149,19 @@ static void handle_seat_destroy(struct wl_listener *listener, void *data) {
 | 
			
		|||
 | 
			
		||||
static const struct zwp_confined_pointer_v1_interface confined_pointer_impl = {
 | 
			
		||||
	.destroy = resource_destroy,
 | 
			
		||||
	.set_region = pointer_constraint_set_region_wrapper,
 | 
			
		||||
	.set_region = pointer_constraint_handle_set_region,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static const struct zwp_locked_pointer_v1_interface locked_pointer_impl = {
 | 
			
		||||
	.destroy = resource_destroy,
 | 
			
		||||
	.set_region = pointer_constraint_set_region_wrapper,
 | 
			
		||||
	.set_region = pointer_constraint_handle_set_region,
 | 
			
		||||
	.set_cursor_position_hint = pointer_constraint_set_cursor_position_hint,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static void pointer_constraint_create(struct wl_client *client,
 | 
			
		||||
		struct wl_resource *pointer_constraints_resource, uint32_t id,
 | 
			
		||||
		struct wl_resource *surface_resource, struct wl_resource *pointer_resource,
 | 
			
		||||
		struct wl_resource *surface_resource,
 | 
			
		||||
		struct wl_resource *pointer_resource,
 | 
			
		||||
		struct wl_resource *region_resource,
 | 
			
		||||
		enum zwp_pointer_constraints_v1_lifetime lifetime,
 | 
			
		||||
		enum wlr_pointer_constraint_v1_type type) {
 | 
			
		||||
| 
						 | 
				
			
			@ -181,7 +169,8 @@ static void pointer_constraint_create(struct wl_client *client,
 | 
			
		|||
		pointer_constraints_from_resource(pointer_constraints_resource);
 | 
			
		||||
 | 
			
		||||
	struct wlr_surface *surface = wlr_surface_from_resource(surface_resource);
 | 
			
		||||
	struct wlr_seat *seat = wlr_seat_client_from_pointer_resource(pointer_resource)->seat;
 | 
			
		||||
	struct wlr_seat *seat =
 | 
			
		||||
		wlr_seat_client_from_pointer_resource(pointer_resource)->seat;
 | 
			
		||||
 | 
			
		||||
	if (wlr_pointer_constraints_v1_constraint_for_surface(pointer_constraints,
 | 
			
		||||
			surface, seat)) {
 | 
			
		||||
| 
						 | 
				
			
			@ -220,6 +209,9 @@ static void pointer_constraint_create(struct wl_client *client,
 | 
			
		|||
 | 
			
		||||
	pixman_region32_init(&constraint->region);
 | 
			
		||||
 | 
			
		||||
	pixman_region32_init(&constraint->pending.region);
 | 
			
		||||
	pixman_region32_init(&constraint->current.region);
 | 
			
		||||
 | 
			
		||||
	pointer_constraint_set_region(constraint, region_resource);
 | 
			
		||||
	pointer_constraint_handle_commit(constraint);
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -256,12 +248,14 @@ static void pointer_constraints_lock_pointer(struct wl_client *client,
 | 
			
		|||
static void pointer_constraints_confine_pointer(struct wl_client *client,
 | 
			
		||||
		struct wl_resource *cons_resource, uint32_t id,
 | 
			
		||||
		struct wl_resource *surface, struct wl_resource *pointer,
 | 
			
		||||
		struct wl_resource *region, enum zwp_pointer_constraints_v1_lifetime lifetime) {
 | 
			
		||||
		struct wl_resource *region,
 | 
			
		||||
		enum zwp_pointer_constraints_v1_lifetime lifetime) {
 | 
			
		||||
	pointer_constraint_create(client, cons_resource, id, surface, pointer,
 | 
			
		||||
		region, lifetime, WLR_POINTER_CONSTRAINT_V1_CONFINED);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static const struct zwp_pointer_constraints_v1_interface pointer_constraints_impl = {
 | 
			
		||||
static const struct zwp_pointer_constraints_v1_interface
 | 
			
		||||
		pointer_constraints_impl = {
 | 
			
		||||
	.destroy = resource_destroy,
 | 
			
		||||
	.lock_pointer = pointer_constraints_lock_pointer,
 | 
			
		||||
	.confine_pointer = pointer_constraints_confine_pointer,
 | 
			
		||||
| 
						 | 
				
			
			@ -283,7 +277,8 @@ static void pointer_constraints_bind(struct wl_client *client, void *data,
 | 
			
		|||
		return;
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	wl_list_insert(&pointer_constraints->resources, wl_resource_get_link(resource));
 | 
			
		||||
	wl_list_insert(&pointer_constraints->resources,
 | 
			
		||||
		wl_resource_get_link(resource));
 | 
			
		||||
	wl_resource_set_implementation(resource, &pointer_constraints_impl,
 | 
			
		||||
		pointer_constraints, pointer_constraints_destroy);
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			@ -317,12 +312,14 @@ struct wlr_pointer_constraints_v1 *wlr_pointer_constraints_v1_create(
 | 
			
		|||
void wlr_pointer_constraints_v1_destroy(
 | 
			
		||||
		struct wlr_pointer_constraints_v1 *pointer_constraints) {
 | 
			
		||||
	struct wl_resource *resource, *_tmp_res;
 | 
			
		||||
	wl_resource_for_each_safe(resource, _tmp_res, &pointer_constraints->resources) {
 | 
			
		||||
	wl_resource_for_each_safe(resource, _tmp_res,
 | 
			
		||||
			&pointer_constraints->resources) {
 | 
			
		||||
		wl_resource_destroy(resource);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	struct wlr_pointer_constraint_v1 *constraint, *_tmp_cons;
 | 
			
		||||
	wl_list_for_each_safe(constraint, _tmp_cons, &pointer_constraints->constraints, link) {
 | 
			
		||||
	wl_list_for_each_safe(constraint, _tmp_cons,
 | 
			
		||||
			&pointer_constraints->constraints, link) {
 | 
			
		||||
		wl_resource_destroy(constraint->resource);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -330,7 +327,8 @@ void wlr_pointer_constraints_v1_destroy(
 | 
			
		|||
	free(pointer_constraints);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct wlr_pointer_constraint_v1 *wlr_pointer_constraints_v1_constraint_for_surface(
 | 
			
		||||
struct wlr_pointer_constraint_v1 *
 | 
			
		||||
		wlr_pointer_constraints_v1_constraint_for_surface(
 | 
			
		||||
		struct wlr_pointer_constraints_v1 *pointer_constraints,
 | 
			
		||||
		struct wlr_surface *surface, struct wlr_seat *seat) {
 | 
			
		||||
	struct wlr_pointer_constraint_v1 *constraint;
 | 
			
		||||
| 
						 | 
				
			
			@ -351,11 +349,13 @@ void wlr_pointer_constraint_v1_send_activated(
 | 
			
		|||
	zwp_confined_pointer_v1_send_confined(constraint->resource);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void wlr_pointer_constraint_v1_send_deactivated(struct wlr_pointer_constraint_v1 *constraint) {
 | 
			
		||||
void wlr_pointer_constraint_v1_send_deactivated(
 | 
			
		||||
		struct wlr_pointer_constraint_v1 *constraint) {
 | 
			
		||||
	if (wl_resource_get_user_data(constraint->resource)) {
 | 
			
		||||
		wlr_log(WLR_DEBUG, "unconstrained %p", constraint);
 | 
			
		||||
		zwp_confined_pointer_v1_send_unconfined(constraint->resource);
 | 
			
		||||
		if (constraint->lifetime == ZWP_POINTER_CONSTRAINTS_V1_LIFETIME_ONESHOT) {
 | 
			
		||||
		if (constraint->lifetime ==
 | 
			
		||||
				ZWP_POINTER_CONSTRAINTS_V1_LIFETIME_ONESHOT) {
 | 
			
		||||
			pointer_constraint_destroy(constraint);
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue