aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIlia Mirkin <imirkin@alum.mit.edu>2021-01-21 06:24:52 -0500
committerSimon Ser <contact@emersion.fr>2021-01-21 15:14:54 +0100
commit7bc8dbb991ecebd7c5117776a043f886593cbd97 (patch)
treead8981cf7527949080575656bb3c411a67c8c455
parent922b7f415d97ece56b8de38655642620e5f79c7b (diff)
backend/x11: keep track of exposed rects, add them to damage regions
When we receive an Expose event, that means that we must redraw that region of the X11 window. Keep track of these regions with pixman regions, and merge them with the additional output damaged regions. Fixes #2670
-rw-r--r--backend/x11/backend.c3
-rw-r--r--backend/x11/output.c9
-rw-r--r--include/backend/x11.h3
3 files changed, 13 insertions, 2 deletions
diff --git a/backend/x11/backend.c b/backend/x11/backend.c
index efb9ecf7..fe66bdd8 100644
--- a/backend/x11/backend.c
+++ b/backend/x11/backend.c
@@ -72,6 +72,9 @@ static void handle_x11_event(struct wlr_x11_backend *x11,
struct wlr_x11_output *output =
get_x11_output_from_window_id(x11, ev->window);
if (output != NULL) {
+ pixman_region32_union_rect(
+ &output->exposed, &output->exposed,
+ ev->x, ev->y, ev->width, ev->height);
wlr_output_update_needs_frame(&output->wlr_output);
}
break;
diff --git a/backend/x11/output.c b/backend/x11/output.c
index e34b9913..96f8da38 100644
--- a/backend/x11/output.c
+++ b/backend/x11/output.c
@@ -75,6 +75,8 @@ static void output_destroy(struct wlr_output *wlr_output) {
struct wlr_x11_output *output = get_x11_output_from_output(wlr_output);
struct wlr_x11_backend *x11 = output->x11;
+ pixman_region32_fini(&output->exposed);
+
wlr_input_device_destroy(&output->pointer_dev);
wlr_input_device_destroy(&output->touch_dev);
@@ -242,10 +244,10 @@ static bool output_commit_buffer(struct wlr_x11_output *output) {
xcb_xfixes_region_t region = XCB_NONE;
if (output->wlr_output.pending.committed & WLR_OUTPUT_STATE_DAMAGE) {
- pixman_region32_t *damage = &output->wlr_output.pending.damage;
+ pixman_region32_union(&output->exposed, &output->exposed, &output->wlr_output.pending.damage);
int rects_len = 0;
- pixman_box32_t *rects = pixman_region32_rectangles(damage, &rects_len);
+ pixman_box32_t *rects = pixman_region32_rectangles(&output->exposed, &rects_len);
xcb_rectangle_t *xcb_rects = calloc(rects_len, sizeof(xcb_rectangle_t));
if (!xcb_rects) {
@@ -268,6 +270,8 @@ static bool output_commit_buffer(struct wlr_x11_output *output) {
free(xcb_rects);
}
+ pixman_region32_clear(&output->exposed);
+
uint32_t serial = output->wlr_output.commit_seq;
uint32_t options = 0;
uint64_t target_msc = output->last_msc ? output->last_msc + 1 : 0;
@@ -363,6 +367,7 @@ struct wlr_output *wlr_x11_output_create(struct wlr_backend *backend) {
}
output->x11 = x11;
wl_list_init(&output->buffers);
+ pixman_region32_init(&output->exposed);
struct wlr_output *wlr_output = &output->wlr_output;
wlr_output_init(wlr_output, &x11->backend, &output_impl, x11->wl_display);
diff --git a/include/backend/x11.h b/include/backend/x11.h
index 79c61b88..1b440d2a 100644
--- a/include/backend/x11.h
+++ b/include/backend/x11.h
@@ -14,6 +14,7 @@
#include <xcb/xcb_errors.h>
#endif
+#include <pixman.h>
#include <wlr/backend/x11.h>
#include <wlr/interfaces/wlr_input_device.h>
#include <wlr/interfaces/wlr_keyboard.h>
@@ -47,6 +48,8 @@ struct wlr_x11_output {
struct wl_list buffers; // wlr_x11_buffer::link
+ pixman_region32_t exposed;
+
uint64_t last_msc;
};