diff options
Diffstat (limited to 'sway/desktop')
-rw-r--r-- | sway/desktop/output.c | 13 | ||||
-rw-r--r-- | sway/desktop/xwayland.c | 61 |
2 files changed, 63 insertions, 11 deletions
diff --git a/sway/desktop/output.c b/sway/desktop/output.c index ec204c6f..21c8513f 100644 --- a/sway/desktop/output.c +++ b/sway/desktop/output.c | |||
@@ -218,6 +218,19 @@ static void output_frame_notify(struct wl_listener *listener, void *data) { | |||
218 | swayc_descendants_of_type( | 218 | swayc_descendants_of_type( |
219 | &root_container, C_VIEW, output_frame_view, soutput); | 219 | &root_container, C_VIEW, output_frame_view, soutput); |
220 | 220 | ||
221 | // render unmanaged views on top | ||
222 | struct sway_view *view; | ||
223 | wl_list_for_each(view, &root_container.sway_root->unmanaged_views, | ||
224 | unmanaged_view_link) { | ||
225 | if (view->type == SWAY_XWAYLAND_VIEW) { | ||
226 | // the only kind of unamanged view right now is xwayland override redirect | ||
227 | int view_x = view->wlr_xwayland_surface->x; | ||
228 | int view_y = view->wlr_xwayland_surface->y; | ||
229 | render_surface(view->surface, wlr_output, &soutput->last_frame, | ||
230 | view_x, view_y, 0); | ||
231 | } | ||
232 | } | ||
233 | |||
221 | wlr_renderer_end(server->renderer); | 234 | wlr_renderer_end(server->renderer); |
222 | wlr_output_swap_buffers(wlr_output); | 235 | wlr_output_swap_buffers(wlr_output); |
223 | 236 | ||
diff --git a/sway/desktop/xwayland.c b/sway/desktop/xwayland.c index 43bb2e00..0c0dbfff 100644 --- a/sway/desktop/xwayland.c +++ b/sway/desktop/xwayland.c | |||
@@ -93,13 +93,43 @@ static void handle_commit(struct wl_listener *listener, void *data) { | |||
93 | static void handle_destroy(struct wl_listener *listener, void *data) { | 93 | static void handle_destroy(struct wl_listener *listener, void *data) { |
94 | struct sway_xwayland_surface *sway_surface = | 94 | struct sway_xwayland_surface *sway_surface = |
95 | wl_container_of(listener, sway_surface, destroy); | 95 | wl_container_of(listener, sway_surface, destroy); |
96 | struct wlr_xwayland_surface *xsurface = data; | ||
96 | wl_list_remove(&sway_surface->commit.link); | 97 | wl_list_remove(&sway_surface->commit.link); |
97 | wl_list_remove(&sway_surface->destroy.link); | 98 | wl_list_remove(&sway_surface->destroy.link); |
98 | wl_list_remove(&sway_surface->request_configure.link); | 99 | wl_list_remove(&sway_surface->request_configure.link); |
99 | swayc_t *parent = destroy_view(sway_surface->view->swayc); | 100 | if (xsurface->override_redirect) { |
101 | if (xsurface->mapped) { | ||
102 | wl_list_remove(&sway_surface->view->unmanaged_view_link); | ||
103 | } | ||
104 | } else { | ||
105 | swayc_t *parent = destroy_view(sway_surface->view->swayc); | ||
106 | arrange_windows(parent, -1, -1); | ||
107 | } | ||
100 | free(sway_surface->view); | 108 | free(sway_surface->view); |
101 | free(sway_surface); | 109 | free(sway_surface); |
102 | arrange_windows(parent, -1, -1); | 110 | } |
111 | |||
112 | static void handle_unmap_notify(struct wl_listener *listener, void *data) { | ||
113 | // TODO take the view out of the tree | ||
114 | struct sway_xwayland_surface *sway_surface = | ||
115 | wl_container_of(listener, sway_surface, unmap_notify); | ||
116 | struct wlr_xwayland_surface *xsurface = data; | ||
117 | if (xsurface->override_redirect) { | ||
118 | wl_list_remove(&sway_surface->view->unmanaged_view_link); | ||
119 | } | ||
120 | sway_surface->view->surface = NULL; | ||
121 | } | ||
122 | |||
123 | static void handle_map_notify(struct wl_listener *listener, void *data) { | ||
124 | // TODO put the view back into the tree | ||
125 | struct sway_xwayland_surface *sway_surface = | ||
126 | wl_container_of(listener, sway_surface, map_notify); | ||
127 | struct wlr_xwayland_surface *xsurface = data; | ||
128 | if (xsurface->override_redirect) { | ||
129 | wl_list_insert(&root_container.sway_root->unmanaged_views, | ||
130 | &sway_surface->view->unmanaged_view_link); | ||
131 | } | ||
132 | sway_surface->view->surface = xsurface->surface; | ||
103 | } | 133 | } |
104 | 134 | ||
105 | static void handle_configure_request(struct wl_listener *listener, void *data) { | 135 | static void handle_configure_request(struct wl_listener *listener, void *data) { |
@@ -119,11 +149,6 @@ void handle_xwayland_surface(struct wl_listener *listener, void *data) { | |||
119 | listener, server, xwayland_surface); | 149 | listener, server, xwayland_surface); |
120 | struct wlr_xwayland_surface *xsurface = data; | 150 | struct wlr_xwayland_surface *xsurface = data; |
121 | 151 | ||
122 | if (xsurface->override_redirect) { | ||
123 | // TODO: floating popups | ||
124 | return; | ||
125 | } | ||
126 | |||
127 | wlr_log(L_DEBUG, "New xwayland surface title='%s' class='%s'", | 152 | wlr_log(L_DEBUG, "New xwayland surface title='%s' class='%s'", |
128 | xsurface->title, xsurface->class); | 153 | xsurface->title, xsurface->class); |
129 | 154 | ||
@@ -155,15 +180,29 @@ void handle_xwayland_surface(struct wl_listener *listener, void *data) { | |||
155 | // - Set new view to maximized so it behaves nicely | 180 | // - Set new view to maximized so it behaves nicely |
156 | // - Criteria | 181 | // - Criteria |
157 | 182 | ||
158 | sway_surface->commit.notify = handle_commit; | ||
159 | wl_signal_add(&xsurface->surface->events.commit, &sway_surface->commit); | 183 | wl_signal_add(&xsurface->surface->events.commit, &sway_surface->commit); |
160 | sway_surface->destroy.notify = handle_destroy; | 184 | sway_surface->commit.notify = handle_commit; |
185 | |||
161 | wl_signal_add(&xsurface->events.destroy, &sway_surface->destroy); | 186 | wl_signal_add(&xsurface->events.destroy, &sway_surface->destroy); |
162 | sway_surface->request_configure.notify = handle_configure_request; | 187 | sway_surface->destroy.notify = handle_destroy; |
188 | |||
163 | wl_signal_add(&xsurface->events.request_configure, | 189 | wl_signal_add(&xsurface->events.request_configure, |
164 | &sway_surface->request_configure); | 190 | &sway_surface->request_configure); |
191 | sway_surface->request_configure.notify = handle_configure_request; | ||
192 | |||
193 | wl_signal_add(&xsurface->events.unmap_notify, &sway_surface->unmap_notify); | ||
194 | sway_surface->unmap_notify.notify = handle_unmap_notify; | ||
195 | |||
196 | wl_signal_add(&xsurface->events.map_notify, &sway_surface->map_notify); | ||
197 | sway_surface->map_notify.notify = handle_map_notify; | ||
198 | |||
199 | if (xsurface->override_redirect) { | ||
200 | // these don't get a container in the tree | ||
201 | wl_list_insert(&root_container.sway_root->unmanaged_views, | ||
202 | &sway_view->unmanaged_view_link); | ||
203 | return; | ||
204 | } | ||
165 | 205 | ||
166 | // TODO: actual focus semantics | ||
167 | swayc_t *parent = root_container.children->items[0]; | 206 | swayc_t *parent = root_container.children->items[0]; |
168 | parent = parent->children->items[0]; // workspace | 207 | parent = parent->children->items[0]; // workspace |
169 | 208 | ||