Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions include/sway/server.h
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,8 @@ void sway_session_lock_add_output(struct sway_session_lock *lock,
struct sway_output *output);
bool sway_session_lock_has_surface(struct sway_session_lock *lock,
struct wlr_surface *surface);
void sway_session_lock_focus_output(struct sway_session_lock *lock,
struct sway_output *output);
void handle_xdg_shell_toplevel(struct wl_listener *listener, void *data);
#if WLR_HAS_XWAYLAND
void handle_xwayland_surface(struct wl_listener *listener, void *data);
Expand Down
18 changes: 18 additions & 0 deletions sway/input/seat.c
Original file line number Diff line number Diff line change
Expand Up @@ -1273,6 +1273,24 @@ void seat_set_focus(struct sway_seat *seat, struct sway_node *node) {
seat_set_workspace_focus(seat, node);
}
if (server.session_lock.lock) {
struct sway_output *output = NULL;
if (node != NULL) {
switch (node->type) {
case N_OUTPUT:
output = node->sway_output;
break;
case N_WORKSPACE:
output = node->sway_workspace->output;
break;
default:
break;
}
}
if (output != NULL) {
sway_session_lock_focus_output(server.session_lock.lock, output);
return;
}
// Fallback to the previously focused lock surface
seat_set_focus_surface(seat, server.session_lock.lock->focused, false);
}
}
Expand Down
28 changes: 27 additions & 1 deletion sway/lock.c
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
#include "sway/layers.h"
#include "sway/output.h"
#include "sway/server.h"
#include "sway/tree/workspace.h"
#include "sway/lock.h"

struct sway_session_lock_output {
Expand Down Expand Up @@ -59,9 +60,34 @@ static void refocus_output(struct sway_session_lock_output *output) {
}
}

void sway_session_lock_focus_output(struct sway_session_lock *lock,
struct sway_output *output) {
// Try focusing the lock surface on the provided output
struct sway_session_lock_output *candidate;
wl_list_for_each(candidate, &lock->outputs, link) {
if (candidate->output != output || !candidate->surface) {
continue;
}

if (candidate->surface->surface->mapped) {
// Set the focus for all seats
focus_surface(lock, candidate->surface->surface);
break;
}
}
}

static void handle_surface_map(struct wl_listener *listener, void *data) {
struct sway_session_lock_output *surf = wl_container_of(listener, surf, surface_map);
if (surf->lock->focused == NULL) {

struct sway_seat *seat = input_manager_current_seat();
struct sway_workspace *focused_ws = seat_get_focused_workspace(seat);
struct sway_output *focused_output = NULL;
if (focused_ws != NULL) {
focused_output = focused_ws->output;
}

if (surf->lock->focused == NULL || focused_output == surf->output) {
focus_surface(surf->lock, surf->surface->surface);
}
cursor_rebase_all();
Expand Down