aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/sway/server.h2
-rw-r--r--include/sway/tree/view.h4
-rw-r--r--sway/server.c2
-rw-r--r--sway/tree/container.c8
-rw-r--r--sway/tree/view.c50
5 files changed, 66 insertions, 0 deletions
diff --git a/include/sway/server.h b/include/sway/server.h
index 3c972bc5..0f5e3ab2 100644
--- a/include/sway/server.h
+++ b/include/sway/server.h
@@ -8,6 +8,7 @@
8#include <wlr/types/wlr_compositor.h> 8#include <wlr/types/wlr_compositor.h>
9#include <wlr/types/wlr_data_device.h> 9#include <wlr/types/wlr_data_device.h>
10#include <wlr/types/wlr_input_method_v2.h> 10#include <wlr/types/wlr_input_method_v2.h>
11#include <wlr/types/wlr_foreign_toplevel_management_v1.h>
11#include <wlr/types/wlr_layer_shell_v1.h> 12#include <wlr/types/wlr_layer_shell_v1.h>
12#include <wlr/types/wlr_output_management_v1.h> 13#include <wlr/types/wlr_output_management_v1.h>
13#include <wlr/types/wlr_output_power_management_v1.h> 14#include <wlr/types/wlr_output_power_management_v1.h>
@@ -82,6 +83,7 @@ struct sway_server {
82 struct wl_listener output_power_manager_set_mode; 83 struct wl_listener output_power_manager_set_mode;
83 struct wlr_input_method_manager_v2 *input_method; 84 struct wlr_input_method_manager_v2 *input_method;
84 struct wlr_text_input_manager_v3 *text_input; 85 struct wlr_text_input_manager_v3 *text_input;
86 struct wlr_foreign_toplevel_manager_v1 *foreign_toplevel_manager;
85 87
86 size_t txn_timeout_ms; 88 size_t txn_timeout_ms;
87 list_t *transactions; 89 list_t *transactions;
diff --git a/include/sway/tree/view.h b/include/sway/tree/view.h
index 6007ec49..b495fdf9 100644
--- a/include/sway/tree/view.h
+++ b/include/sway/tree/view.h
@@ -96,6 +96,10 @@ struct sway_view {
96 // when a transaction is applied. 96 // when a transaction is applied.
97 struct wlr_box saved_geometry; 97 struct wlr_box saved_geometry;
98 98
99 struct wlr_foreign_toplevel_handle_v1 *foreign_toplevel;
100 struct wl_listener foreign_activate_request;
101 struct wl_listener foreign_close_request;
102
99 bool destroying; 103 bool destroying;
100 104
101 list_t *executed_criteria; // struct criteria * 105 list_t *executed_criteria; // struct criteria *
diff --git a/sway/server.c b/sway/server.c
index 724a0e25..c036396f 100644
--- a/sway/server.c
+++ b/sway/server.c
@@ -142,6 +142,8 @@ bool server_init(struct sway_server *server) {
142 &server->output_power_manager_set_mode); 142 &server->output_power_manager_set_mode);
143 server->input_method = wlr_input_method_manager_v2_create(server->wl_display); 143 server->input_method = wlr_input_method_manager_v2_create(server->wl_display);
144 server->text_input = wlr_text_input_manager_v3_create(server->wl_display); 144 server->text_input = wlr_text_input_manager_v3_create(server->wl_display);
145 server->foreign_toplevel_manager =
146 wlr_foreign_toplevel_manager_v1_create(server->wl_display);
145 147
146 wlr_export_dmabuf_manager_v1_create(server->wl_display); 148 wlr_export_dmabuf_manager_v1_create(server->wl_display);
147 wlr_screencopy_manager_v1_create(server->wl_display); 149 wlr_screencopy_manager_v1_create(server->wl_display);
diff --git a/sway/tree/container.c b/sway/tree/container.c
index 2fbd0d38..4cc42747 100644
--- a/sway/tree/container.c
+++ b/sway/tree/container.c
@@ -1168,6 +1168,10 @@ void container_discover_outputs(struct sway_container *con) {
1168 if (con->view) { 1168 if (con->view) {
1169 view_for_each_surface(con->view, 1169 view_for_each_surface(con->view,
1170 surface_send_enter_iterator, output->wlr_output); 1170 surface_send_enter_iterator, output->wlr_output);
1171 if (con->view->foreign_toplevel) {
1172 wlr_foreign_toplevel_handle_v1_output_enter(
1173 con->view->foreign_toplevel, output->wlr_output);
1174 }
1171 } 1175 }
1172 list_add(con->outputs, output); 1176 list_add(con->outputs, output);
1173 } else if (!intersects && index != -1) { 1177 } else if (!intersects && index != -1) {
@@ -1176,6 +1180,10 @@ void container_discover_outputs(struct sway_container *con) {
1176 if (con->view) { 1180 if (con->view) {
1177 view_for_each_surface(con->view, 1181 view_for_each_surface(con->view,
1178 surface_send_leave_iterator, output->wlr_output); 1182 surface_send_leave_iterator, output->wlr_output);
1183 if (con->view->foreign_toplevel) {
1184 wlr_foreign_toplevel_handle_v1_output_leave(
1185 con->view->foreign_toplevel, output->wlr_output);
1186 }
1179 } 1187 }
1180 list_del(con->outputs, index); 1188 list_del(con->outputs, index);
1181 } 1189 }
diff --git a/sway/tree/view.c b/sway/tree/view.c
index e5d3948c..6dccaa2e 100644
--- a/sway/tree/view.c
+++ b/sway/tree/view.c
@@ -22,6 +22,7 @@
22#include "sway/ipc-server.h" 22#include "sway/ipc-server.h"
23#include "sway/output.h" 23#include "sway/output.h"
24#include "sway/input/seat.h" 24#include "sway/input/seat.h"
25#include "sway/server.h"
25#include "sway/tree/arrange.h" 26#include "sway/tree/arrange.h"
26#include "sway/tree/container.h" 27#include "sway/tree/container.h"
27#include "sway/tree/view.h" 28#include "sway/tree/view.h"
@@ -329,6 +330,10 @@ void view_set_activated(struct sway_view *view, bool activated) {
329 if (view->impl->set_activated) { 330 if (view->impl->set_activated) {
330 view->impl->set_activated(view, activated); 331 view->impl->set_activated(view, activated);
331 } 332 }
333 if (view->foreign_toplevel) {
334 wlr_foreign_toplevel_handle_v1_set_activated(
335 view->foreign_toplevel, activated);
336 }
332} 337}
333 338
334void view_request_activate(struct sway_view *view) { 339void view_request_activate(struct sway_view *view) {
@@ -589,6 +594,27 @@ static bool should_focus(struct sway_view *view) {
589 return len == 0; 594 return len == 0;
590} 595}
591 596
597static void handle_foreign_activate_request(
598 struct wl_listener *listener, void *data) {
599 struct sway_view *view = wl_container_of(
600 listener, view, foreign_activate_request);
601 struct wlr_foreign_toplevel_handle_v1_activated_event *event = data;
602 struct sway_seat *seat;
603 wl_list_for_each(seat, &server.input->seats, link) {
604 if (seat->wlr_seat == event->seat) {
605 seat_set_focus_container(seat, view->container);
606 break;
607 }
608 }
609}
610
611static void handle_foreign_close_request(
612 struct wl_listener *listener, void *data) {
613 struct sway_view *view = wl_container_of(
614 listener, view, foreign_close_request);
615 view_close(view);
616}
617
592void view_map(struct sway_view *view, struct wlr_surface *wlr_surface, 618void view_map(struct sway_view *view, struct wlr_surface *wlr_surface,
593 bool fullscreen, struct wlr_output *fullscreen_output, 619 bool fullscreen, struct wlr_output *fullscreen_output,
594 bool decoration) { 620 bool decoration) {
@@ -617,6 +643,15 @@ void view_map(struct sway_view *view, struct wlr_surface *wlr_surface,
617 struct sway_container *target_sibling = node->type == N_CONTAINER ? 643 struct sway_container *target_sibling = node->type == N_CONTAINER ?
618 node->sway_container : NULL; 644 node->sway_container : NULL;
619 645
646 view->foreign_toplevel =
647 wlr_foreign_toplevel_handle_v1_create(server.foreign_toplevel_manager);
648 view->foreign_activate_request.notify = handle_foreign_activate_request;
649 wl_signal_add(&view->foreign_toplevel->events.request_activate,
650 &view->foreign_activate_request);
651 view->foreign_close_request.notify = handle_foreign_close_request;
652 wl_signal_add(&view->foreign_toplevel->events.request_close,
653 &view->foreign_close_request);
654
620 // If we're about to launch the view into the floating container, then 655 // If we're about to launch the view into the floating container, then
621 // launch it as a tiled view in the root of the workspace instead. 656 // launch it as a tiled view in the root of the workspace instead.
622 if (target_sibling && container_is_floating(target_sibling)) { 657 if (target_sibling && container_is_floating(target_sibling)) {
@@ -679,6 +714,12 @@ void view_map(struct sway_view *view, struct wlr_surface *wlr_surface,
679 if (should_focus(view)) { 714 if (should_focus(view)) {
680 input_manager_set_focus(&view->container->node); 715 input_manager_set_focus(&view->container->node);
681 } 716 }
717
718 const char *app_id = view_get_app_id(view);
719 if (app_id != NULL) {
720 wlr_foreign_toplevel_handle_v1_set_app_id(
721 view->foreign_toplevel, app_id);
722 }
682} 723}
683 724
684void view_unmap(struct sway_view *view) { 725void view_unmap(struct sway_view *view) {
@@ -691,6 +732,11 @@ void view_unmap(struct sway_view *view) {
691 view->urgent_timer = NULL; 732 view->urgent_timer = NULL;
692 } 733 }
693 734
735 if (view->foreign_toplevel) {
736 wlr_foreign_toplevel_handle_v1_destroy(view->foreign_toplevel);
737 view->foreign_toplevel = NULL;
738 }
739
694 struct sway_container *parent = view->container->parent; 740 struct sway_container *parent = view->container->parent;
695 struct sway_workspace *ws = view->container->workspace; 741 struct sway_workspace *ws = view->container->workspace;
696 container_begin_destroy(view->container); 742 container_begin_destroy(view->container);
@@ -1097,6 +1143,10 @@ void view_update_title(struct sway_view *view, bool force) {
1097 container_update_title_textures(view->container); 1143 container_update_title_textures(view->container);
1098 1144
1099 ipc_event_window(view->container, "title"); 1145 ipc_event_window(view->container, "title");
1146
1147 if (view->foreign_toplevel) {
1148 wlr_foreign_toplevel_handle_v1_set_title(view->foreign_toplevel, title);
1149 }
1100} 1150}
1101 1151
1102bool view_is_visible(struct sway_view *view) { 1152bool view_is_visible(struct sway_view *view) {