diff options
Diffstat (limited to 'sway/input/seat.c')
-rw-r--r-- | sway/input/seat.c | 27 |
1 files changed, 22 insertions, 5 deletions
diff --git a/sway/input/seat.c b/sway/input/seat.c index 85179dc7..fa83050b 100644 --- a/sway/input/seat.c +++ b/sway/input/seat.c | |||
@@ -212,6 +212,15 @@ static void seat_send_focus(struct sway_node *node, struct sway_seat *seat) { | |||
212 | } | 212 | } |
213 | } | 213 | } |
214 | 214 | ||
215 | void sway_force_focus(struct wlr_surface *surface) { | ||
216 | struct sway_seat *seat; | ||
217 | wl_list_for_each(seat, &server.input->seats, link) { | ||
218 | seat_keyboard_notify_enter(seat, surface); | ||
219 | seat_tablet_pads_notify_enter(seat, surface); | ||
220 | sway_input_method_relay_set_focus(&seat->im_relay, surface); | ||
221 | } | ||
222 | } | ||
223 | |||
215 | void seat_for_each_node(struct sway_seat *seat, | 224 | void seat_for_each_node(struct sway_seat *seat, |
216 | void (*f)(struct sway_node *node, void *data), void *data) { | 225 | void (*f)(struct sway_node *node, void *data), void *data) { |
217 | struct sway_seat_node *current = NULL; | 226 | struct sway_seat_node *current = NULL; |
@@ -814,11 +823,13 @@ static void seat_configure_keyboard(struct sway_seat *seat, | |||
814 | sway_keyboard_configure(seat_device->keyboard); | 823 | sway_keyboard_configure(seat_device->keyboard); |
815 | wlr_seat_set_keyboard(seat->wlr_seat, | 824 | wlr_seat_set_keyboard(seat->wlr_seat, |
816 | seat_device->input_device->wlr_device->keyboard); | 825 | seat_device->input_device->wlr_device->keyboard); |
817 | struct sway_node *focus = seat_get_focus(seat); | 826 | |
818 | if (focus && node_is_view(focus)) { | 827 | // force notify reenter to pick up the new configuration. This reuses |
819 | // force notify reenter to pick up the new configuration | 828 | // the current focused surface to avoid breaking input grabs. |
829 | struct wlr_surface *surface = seat->wlr_seat->keyboard_state.focused_surface; | ||
830 | if (surface) { | ||
820 | wlr_seat_keyboard_notify_clear_focus(seat->wlr_seat); | 831 | wlr_seat_keyboard_notify_clear_focus(seat->wlr_seat); |
821 | seat_keyboard_notify_enter(seat, focus->sway_container->view->surface); | 832 | seat_keyboard_notify_enter(seat, surface); |
822 | } | 833 | } |
823 | } | 834 | } |
824 | 835 | ||
@@ -1070,7 +1081,8 @@ void seat_configure_xcursor(struct sway_seat *seat) { | |||
1070 | bool seat_is_input_allowed(struct sway_seat *seat, | 1081 | bool seat_is_input_allowed(struct sway_seat *seat, |
1071 | struct wlr_surface *surface) { | 1082 | struct wlr_surface *surface) { |
1072 | struct wl_client *client = wl_resource_get_client(surface->resource); | 1083 | struct wl_client *client = wl_resource_get_client(surface->resource); |
1073 | return !seat->exclusive_client || seat->exclusive_client == client; | 1084 | return seat->exclusive_client == client || |
1085 | (seat->exclusive_client == NULL && !server.session_lock.locked); | ||
1074 | } | 1086 | } |
1075 | 1087 | ||
1076 | static void send_unfocus(struct sway_container *con, void *data) { | 1088 | static void send_unfocus(struct sway_container *con, void *data) { |
@@ -1171,6 +1183,11 @@ void seat_set_focus(struct sway_seat *seat, struct sway_node *node) { | |||
1171 | return; | 1183 | return; |
1172 | } | 1184 | } |
1173 | 1185 | ||
1186 | // Deny setting focus when an input grab or lockscreen is active | ||
1187 | if (container && !seat_is_input_allowed(seat, container->view->surface)) { | ||
1188 | return; | ||
1189 | } | ||
1190 | |||
1174 | struct sway_output *new_output = | 1191 | struct sway_output *new_output = |
1175 | new_workspace ? new_workspace->output : NULL; | 1192 | new_workspace ? new_workspace->output : NULL; |
1176 | 1193 | ||