Fix focusing topmost floating windows

Re-focus on the container on which the cursor hovers over.  A
special case is, if there are menus or other subsurfaces open
in the focused container.  It will prefer the focused container
as long as there are subsurfaces.

This commit starts caching the previous node as well as the
previous x/y cursor position.  Re-calculating the previous
focused node by looking at the current state of the cursor
position does not work, if the environment changes.
This commit is contained in:
Jonathan Buch 2018-09-27 18:32:55 +02:00
parent 8bec0c90c7
commit 7727d54faf
Failed to generate hash of commit
3 changed files with 13 additions and 5 deletions

View file

@ -10,6 +10,7 @@ struct sway_cursor {
struct wlr_cursor *cursor;
struct {
double x, y;
struct sway_node *node;
} previous;
struct wlr_xcursor_manager *xcursor_manager;

View file

@ -567,15 +567,15 @@ void cursor_send_pointer_motion(struct sway_cursor *cursor, uint32_t time_msec,
struct wlr_surface *surface = NULL;
double sx, sy;
// Find the node beneath the pointer's previous position
struct sway_node *prev_node = node_at_coords(seat,
cursor->previous.x, cursor->previous.y, &surface, &sx, &sy);
struct sway_node *prev_node = cursor->previous.node;
struct sway_node *node = node_at_coords(seat,
cursor->cursor->x, cursor->cursor->y, &surface, &sx, &sy);
// Update the stored previous position
cursor->previous.x = cursor->cursor->x;
cursor->previous.y = cursor->cursor->y;
cursor->previous.node = node;
struct sway_node *node = node_at_coords(seat,
cursor->cursor->x, cursor->cursor->y, &surface, &sx, &sy);
if (node && config->focus_follows_mouse && allow_refocusing) {
struct sway_node *focus = seat_get_focus(seat);
if (focus && node->type == N_WORKSPACE) {

View file

@ -369,6 +369,13 @@ struct sway_container *container_at(struct sway_workspace *workspace,
}
// If focused is floating, focused view's non-popups
if (focus && focus->view && is_floating) {
// only switch to unfocused container if focused container has no menus open
bool has_subsurfaces = wl_list_length(&focus->view->surface->subsurfaces) > 0;
c = floating_container_at(lx, ly, surface, sx, sy);
if (!has_subsurfaces && c && c->view && *surface && c != focus) {
return c;
}
surface_at_view(focus, lx, ly, surface, sx, sy);
if (*surface) {
return focus;