aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/wlr/types/wlr_layer_shell.h8
-rw-r--r--rootston/desktop.c31
-rw-r--r--types/wlr_layer_shell.c22
3 files changed, 39 insertions, 22 deletions
diff --git a/include/wlr/types/wlr_layer_shell.h b/include/wlr/types/wlr_layer_shell.h
index 22352906..1477989d 100644
--- a/include/wlr/types/wlr_layer_shell.h
+++ b/include/wlr/types/wlr_layer_shell.h
@@ -113,4 +113,12 @@ struct wlr_layer_surface *wlr_layer_surface_from_wlr_surface(
void wlr_layer_surface_for_each_surface(struct wlr_layer_surface *surface,
wlr_surface_iterator_func_t iterator, void *user_data);
+/**
+ * Find a surface within this layer-surface tree at the given surface-local
+ * coordinates. Returns the surface and coordinates in the leaf surface
+ * coordinate system or NULL if no surface is found at that location.
+ */
+struct wlr_surface *wlr_layer_surface_surface_at(
+ struct wlr_layer_surface *surface, double sx, double sy,
+ double *sub_x, double *sub_y);
#endif
diff --git a/rootston/desktop.c b/rootston/desktop.c
index 6ac665bc..192c7da0 100644
--- a/rootston/desktop.c
+++ b/rootston/desktop.c
@@ -641,30 +641,17 @@ static struct wlr_surface *layer_surface_at(struct roots_output *output,
struct wl_list *layer, double ox, double oy, double *sx, double *sy) {
struct roots_layer_surface *roots_surface;
wl_list_for_each_reverse(roots_surface, layer, link) {
- struct wlr_surface *wlr_surface;
- double _sx, _sy;
- struct wlr_xdg_popup *popup;
- wl_list_for_each(popup, &roots_surface->layer_surface->popups, link) {
- wlr_surface = popup->base->surface;
- _sx = ox - roots_surface->geo.x - popup->geometry.x;
- _sy = oy - roots_surface->geo.y - popup->geometry.y;
- if (wlr_surface_point_accepts_input(wlr_surface, _sx, _sy)) {
- *sx = _sx;
- *sy = _sy;
- return wlr_surface;
- }
- // TODO: popups can have popups
- }
- // TODO: Test subsurfaces
- wlr_surface = roots_surface->layer_surface->surface;
- _sx = ox - roots_surface->geo.x;
- _sy = oy - roots_surface->geo.y;
- if (wlr_surface_point_accepts_input(wlr_surface, _sx, _sy)) {
- *sx = _sx;
- *sy = _sy;
- return wlr_surface;
+ double _sx = ox - roots_surface->geo.x;
+ double _sy = oy - roots_surface->geo.y;
+
+ struct wlr_surface *sub = wlr_layer_surface_surface_at(
+ roots_surface->layer_surface, _sx, _sy, sx, sy);
+
+ if (sub) {
+ return sub;
}
}
+
return NULL;
}
diff --git a/types/wlr_layer_shell.c b/types/wlr_layer_shell.c
index fd7bc659..0fae048c 100644
--- a/types/wlr_layer_shell.c
+++ b/types/wlr_layer_shell.c
@@ -531,3 +531,25 @@ void wlr_layer_surface_for_each_surface(struct wlr_layer_surface *surface,
wlr_surface_iterator_func_t iterator, void *user_data) {
layer_surface_for_each_surface(surface, 0, 0, iterator, user_data);
}
+
+struct wlr_surface *wlr_layer_surface_surface_at(
+ struct wlr_layer_surface *surface, double sx, double sy,
+ double *sub_x, double *sub_y) {
+ struct wlr_xdg_popup *popup_state;
+ wl_list_for_each(popup_state, &surface->popups, link) {
+ struct wlr_xdg_surface *popup = popup_state->base;
+
+ double popup_sx = popup_state->geometry.x - popup->geometry.x;
+ double popup_sy = popup_state->geometry.y - popup->geometry.y;
+
+ struct wlr_surface *sub = wlr_xdg_surface_surface_at(popup,
+ sx - popup_sx,
+ sy - popup_sy,
+ sub_x, sub_y);
+ if (sub != NULL) {
+ return sub;
+ }
+ }
+
+ return wlr_surface_surface_at(surface->surface, sx, sy, sub_x, sub_y);
+}