~ruther/dwl

d98ca07a649407a2be8cae1e66265f1bba785b04 — Guido Cella 5 years ago b26ede4
enable pointer on layer surfaces
1 files changed, 49 insertions(+), 5 deletions(-)

M dwl.c
M dwl.c => dwl.c +49 -5
@@ 267,6 267,8 @@ static void unmapnotify(struct wl_listener *listener, void *data);
static void unmaplayersurfacenotify(struct wl_listener *listener, void *data);
static void view(const Arg *arg);
static Client *xytoclient(double x, double y);
static struct wlr_surface *xytolayersurface(struct wl_list *layer_surfaces,
		double x, double y, double *sx, double *sy);
static Monitor *xytomon(double x, double y);
static void zoom(const Arg *arg);



@@ 1234,8 1236,16 @@ void
maplayersurfacenotify(struct wl_listener *listener, void *data)
{
	LayerSurface *layersurface = wl_container_of(listener, layersurface, map);
	double sx = 0.0, sy = 0.0;
	struct wlr_surface *sub = wlr_layer_surface_v1_surface_at(
			layersurface->layer_surface,
			cursor->x - layersurface->geo.x,
			cursor->y - layersurface->geo.y,
			&sx, &sy);
	wlr_surface_send_enter(layersurface->layer_surface->surface, layersurface->layer_surface->output);
	/* XXX recheck pointer focus */
	if (sub)
		wlr_seat_pointer_notify_enter(seat, sub, sx, sy);
	/* XXX check if the layer surface is below a client */
}

void


@@ 1306,7 1316,7 @@ motionnotify(uint32_t time)
{
	double sx = 0, sy = 0;
	struct wlr_surface *surface = NULL;
	Client *c;
	Client *c = NULL;

	/* Update selmon (even while dragging a window) */
	if (sloppyfocus)


@@ 1325,17 1335,23 @@ motionnotify(uint32_t time)
		return;
	}

	if ((surface = xytolayersurface(&selmon->layers[ZWLR_LAYER_SHELL_V1_LAYER_OVERLAY],
					cursor->x, cursor->y, &sx, &sy)))
		;
	else if ((surface = xytolayersurface(&selmon->layers[ZWLR_LAYER_SHELL_V1_LAYER_TOP],
					cursor->x, cursor->y, &sx, &sy)))
		;
#ifdef XWAYLAND
	/* Find an independent under the pointer and send the event along. */
	if ((c = xytoindependent(cursor->x, cursor->y))) {
	else if ((c = xytoindependent(cursor->x, cursor->y))) {
		surface = wlr_surface_surface_at(c->surface.xwayland->surface,
				cursor->x - c->surface.xwayland->x - c->bw,
				cursor->y - c->surface.xwayland->y - c->bw, &sx, &sy);

	/* Otherwise, find the client under the pointer and send the event along. */
	} else
	}
#endif
	if ((c = xytoclient(cursor->x, cursor->y))) {
	else if ((c = xytoclient(cursor->x, cursor->y))) {
#ifdef XWAYLAND
		if (c->type != XDGShell)
			surface = wlr_surface_surface_at(c->surface.xwayland->surface,


@@ 1347,6 1363,13 @@ motionnotify(uint32_t time)
					cursor->x - c->geom.x - c->bw,
					cursor->y - c->geom.y - c->bw, &sx, &sy);
	}
	else if ((surface = xytolayersurface(&selmon->layers[ZWLR_LAYER_SHELL_V1_LAYER_BOTTOM],
					cursor->x, cursor->y, &sx, &sy)))
		;
	else if ((surface = xytolayersurface(&selmon->layers[ZWLR_LAYER_SHELL_V1_LAYER_BACKGROUND],
					cursor->x, cursor->y, &sx, &sy))) { // gcc complains without these braces
		;
	}
	/* If there's no client surface under the cursor, set the cursor image to a
	 * default. This is what makes the cursor image appear when you move it
	 * off of a client or over its border. */


@@ 1424,6 1447,9 @@ pointerfocus(Client *c, struct wlr_surface *surface, double sx, double sy,
	 * of its surfaces, and make keyboard focus follow if desired. */
	wlr_seat_pointer_notify_enter(seat, surface, sx, sy);

	if (!c)
		return;

#if XWAYLAND
	if (c->type == X11Unmanaged)
		return;


@@ 2126,6 2152,24 @@ xytoclient(double x, double y)
	return NULL;
}

struct wlr_surface *
xytolayersurface(struct wl_list *layer_surfaces, double x, double y,
		double *sx, double *sy)
{
	LayerSurface *layersurface;
	wl_list_for_each_reverse(layersurface, layer_surfaces, link) {
		struct wlr_surface *sub = wlr_layer_surface_v1_surface_at(
				layersurface->layer_surface,
				x - layersurface->geo.x,
				y - layersurface->geo.y,
				sx, sy);
		if (sub)
			return sub;

	}
	return NULL;
}

Monitor *
xytomon(double x, double y)
{