aboutsummaryrefslogtreecommitdiffstats
path: root/sway/desktop/render.c
diff options
context:
space:
mode:
authorLibravatar Kenny Levinsen <kl@kl.wtf>2020-05-31 01:37:43 +0200
committerLibravatar Simon Ser <contact@emersion.fr>2020-06-03 16:41:17 +0200
commitfcd0ab8f331a6e74fde113d665d4aed21bccdfc5 (patch)
treec2f53f827372904f8d7b1356231350652bed8a8d /sway/desktop/render.c
parentxwayland: pass focus to previous unmanaged surface on unmap (diff)
downloadsway-fcd0ab8f331a6e74fde113d665d4aed21bccdfc5.tar.gz
sway-fcd0ab8f331a6e74fde113d665d4aed21bccdfc5.tar.zst
sway-fcd0ab8f331a6e74fde113d665d4aed21bccdfc5.zip
view: Save all buffers associated with view
During the execution of a resize transaction, the buffer associated with a view's surface is saved and reused until the client acknowledges the resulting configure event. However, only one the main buffer of the main surface was stored and rendered, meaning that subsurfaces disappear during resize. Iterate over all, store and render buffers from all surfaces in the view to ensure that correct rendering is preserved.
Diffstat (limited to 'sway/desktop/render.c')
-rw-r--r--sway/desktop/render.c61
1 files changed, 34 insertions, 27 deletions
diff --git a/sway/desktop/render.c b/sway/desktop/render.c
index 14753df2..491a9bc0 100644
--- a/sway/desktop/render.c
+++ b/sway/desktop/render.c
@@ -280,37 +280,44 @@ static void render_saved_view(struct sway_view *view,
280 struct sway_output *output, pixman_region32_t *damage, float alpha) { 280 struct sway_output *output, pixman_region32_t *damage, float alpha) {
281 struct wlr_output *wlr_output = output->wlr_output; 281 struct wlr_output *wlr_output = output->wlr_output;
282 282
283 if (!view->saved_buffer || !view->saved_buffer->texture) { 283 if (wl_list_empty(&view->saved_buffers)) {
284 return; 284 return;
285 } 285 }
286 struct wlr_box box = { 286 struct sway_saved_buffer *saved_buf;
287 .x = view->container->surface_x - output->lx - 287 wl_list_for_each(saved_buf, &view->saved_buffers, link) {
288 view->saved_geometry.x, 288 if (!saved_buf->buffer->texture) {
289 .y = view->container->surface_y - output->ly - 289 continue;
290 view->saved_geometry.y, 290 }
291 .width = view->saved_buffer_width,
292 .height = view->saved_buffer_height,
293 };
294
295 struct wlr_box output_box = {
296 .width = output->width,
297 .height = output->height,
298 };
299 291
300 struct wlr_box intersection; 292 struct wlr_box box = {
301 bool intersects = wlr_box_intersection(&intersection, &output_box, &box); 293 .x = view->container->surface_x - output->lx -
302 if (!intersects) { 294 view->saved_geometry.x + saved_buf->x,
303 return; 295 .y = view->container->surface_y - output->ly -
304 } 296 view->saved_geometry.y + saved_buf->y,
297 .width = saved_buf->width,
298 .height = saved_buf->height,
299 };
300
301 struct wlr_box output_box = {
302 .width = output->width,
303 .height = output->height,
304 };
305
306 struct wlr_box intersection;
307 bool intersects = wlr_box_intersection(&intersection, &output_box, &box);
308 if (!intersects) {
309 continue;
310 }
305 311
306 scale_box(&box, wlr_output->scale); 312 scale_box(&box, wlr_output->scale);
307 313
308 float matrix[9]; 314 float matrix[9];
309 wlr_matrix_project_box(matrix, &box, WL_OUTPUT_TRANSFORM_NORMAL, 0, 315 wlr_matrix_project_box(matrix, &box, WL_OUTPUT_TRANSFORM_NORMAL, 0,
310 wlr_output->transform_matrix); 316 wlr_output->transform_matrix);
311 317
312 render_texture(wlr_output, damage, view->saved_buffer->texture, 318 render_texture(wlr_output, damage, saved_buf->buffer->texture,
313 &box, matrix, alpha); 319 &box, matrix, alpha);
320 }
314 321
315 // FIXME: we should set the surface that this saved buffer originates from 322 // FIXME: we should set the surface that this saved buffer originates from
316 // as sampled here. 323 // as sampled here.
@@ -323,7 +330,7 @@ static void render_saved_view(struct sway_view *view,
323static void render_view(struct sway_output *output, pixman_region32_t *damage, 330static void render_view(struct sway_output *output, pixman_region32_t *damage,
324 struct sway_container *con, struct border_colors *colors) { 331 struct sway_container *con, struct border_colors *colors) {
325 struct sway_view *view = con->view; 332 struct sway_view *view = con->view;
326 if (view->saved_buffer) { 333 if (!wl_list_empty(&view->saved_buffers)) {
327 render_saved_view(view, output, damage, view->container->alpha); 334 render_saved_view(view, output, damage, view->container->alpha);
328 } else if (view->surface) { 335 } else if (view->surface) {
329 render_view_toplevels(view, output, damage, view->container->alpha); 336 render_view_toplevels(view, output, damage, view->container->alpha);
@@ -1020,7 +1027,7 @@ void output_render(struct sway_output *output, struct timespec *when,
1020 } 1027 }
1021 1028
1022 if (fullscreen_con->view) { 1029 if (fullscreen_con->view) {
1023 if (fullscreen_con->view->saved_buffer) { 1030 if (!wl_list_empty(&fullscreen_con->view->saved_buffers)) {
1024 render_saved_view(fullscreen_con->view, output, damage, 1.0f); 1031 render_saved_view(fullscreen_con->view, output, damage, 1.0f);
1025 } else if (fullscreen_con->view->surface) { 1032 } else if (fullscreen_con->view->surface) {
1026 render_view_toplevels(fullscreen_con->view, 1033 render_view_toplevels(fullscreen_con->view,