From eea532911a5be8d45770d074546bdeb8a0f16c5b Mon Sep 17 00:00:00 2001 From: emersion Date: Mon, 23 Oct 2017 21:03:00 +0200 Subject: [PATCH] Send output current mode when changed --- backend/wayland/output.c | 10 ++---- backend/x11/backend.c | 4 +-- include/wlr/interfaces/wlr_output.h | 3 +- types/wlr_output.c | 51 +++++++++++++++++++++++++---- 4 files changed, 51 insertions(+), 17 deletions(-) diff --git a/backend/wayland/output.c b/backend/wayland/output.c index 3194e2cf..0dde343c 100644 --- a/backend/wayland/output.c +++ b/backend/wayland/output.c @@ -210,9 +210,7 @@ static void xdg_toplevel_handle_configure(void *data, struct zxdg_toplevel_v6 *x } // loop over states for maximized etc? wl_egl_window_resize(output->egl_window, width, height, 0, 0); - output->wlr_output.width = width; - output->wlr_output.height = height; - wlr_output_update_matrix(&output->wlr_output); + wlr_output_update_size(&output->wlr_output, width, height); wl_signal_emit(&output->wlr_output.events.resolution, output); } @@ -244,13 +242,11 @@ struct wlr_output *wlr_wl_output_create(struct wlr_backend *_backend) { wlr_output_init(&output->wlr_output, &backend->backend, &output_impl); struct wlr_output *wlr_output = &output->wlr_output; - wlr_output->width = 640; - wlr_output->height = 480; + wlr_output_update_size(wlr_output, 640, 480); strncpy(wlr_output->make, "wayland", sizeof(wlr_output->make)); strncpy(wlr_output->model, "wayland", sizeof(wlr_output->model)); snprintf(wlr_output->name, sizeof(wlr_output->name), "WL-%d", - wl_list_length(&backend->outputs) + 1); - wlr_output_update_matrix(wlr_output); + wl_list_length(&backend->outputs) + 1); output->backend = backend; diff --git a/backend/x11/backend.c b/backend/x11/backend.c index d30ec376..0e98b8d9 100644 --- a/backend/x11/backend.c +++ b/backend/x11/backend.c @@ -121,9 +121,7 @@ static bool handle_x11_event(struct wlr_x11_backend *x11, xcb_generic_event_t *e case XCB_CONFIGURE_NOTIFY: { xcb_configure_notify_event_t *ev = (xcb_configure_notify_event_t *)event; - output->wlr_output.width = ev->width; - output->wlr_output.height = ev->height; - wlr_output_update_matrix(&output->wlr_output); + wlr_output_update_size(&output->wlr_output, ev->width, ev->height); wl_signal_emit(&output->wlr_output.events.resolution, output); // Move the pointer to its new location diff --git a/include/wlr/interfaces/wlr_output.h b/include/wlr/interfaces/wlr_output.h index 636cc06c..d365e8f5 100644 --- a/include/wlr/interfaces/wlr_output.h +++ b/include/wlr/interfaces/wlr_output.h @@ -25,7 +25,8 @@ struct wlr_output_impl { void wlr_output_init(struct wlr_output *output, struct wlr_backend *backend, const struct wlr_output_impl *impl); void wlr_output_free(struct wlr_output *output); -void wlr_output_update_matrix(struct wlr_output *output); +void wlr_output_update_size(struct wlr_output *output, int32_t width, + int32_t height); struct wl_global *wlr_output_create_global(struct wlr_output *wlr_output, struct wl_display *display); void wlr_output_destroy_global(struct wlr_output *wlr_output); diff --git a/types/wlr_output.c b/types/wlr_output.c index a02798b2..e8d4af3e 100644 --- a/types/wlr_output.c +++ b/types/wlr_output.c @@ -33,8 +33,8 @@ static void wl_output_send_to_resource(struct wl_resource *resource) { if (output->current_mode == mode) { flags |= WL_OUTPUT_MODE_CURRENT; } - wl_output_send_mode(resource, flags, - mode->width, mode->height, mode->refresh); + wl_output_send_mode(resource, flags, mode->width, mode->height, + mode->refresh); } if (wl_list_length(&output->modes) == 0) { @@ -51,6 +51,25 @@ static void wl_output_send_to_resource(struct wl_resource *resource) { } } +static void wlr_output_send_current_mode_to_resource( + struct wl_resource *resource) { + struct wlr_output *output = wl_resource_get_user_data(resource); + assert(output); + const uint32_t version = wl_resource_get_version(resource); + if (version < WL_OUTPUT_MODE_SINCE_VERSION) { + return; + } + if (output->current_mode != NULL) { + struct wlr_output_mode *mode = output->current_mode; + wl_output_send_mode(resource, mode->flags | WL_OUTPUT_MODE_CURRENT, + mode->width, mode->height, mode->refresh); + } else { + // Output has no mode, send the current width/height + wl_output_send_mode(resource, WL_OUTPUT_MODE_CURRENT, output->width, + output->height, 0); + } +} + static void wl_output_destroy(struct wl_resource *resource) { struct wlr_output *output = wl_resource_get_user_data(resource); struct wl_resource *_resource = NULL; @@ -110,32 +129,52 @@ void wlr_output_destroy_global(struct wlr_output *wlr_output) { wlr_output->wl_global = NULL; } -void wlr_output_update_matrix(struct wlr_output *output) { - wlr_matrix_texture(output->transform_matrix, output->width, output->height, output->transform); +static void wlr_output_update_matrix(struct wlr_output *output) { + wlr_matrix_texture(output->transform_matrix, output->width, output->height, + output->transform); } void wlr_output_enable(struct wlr_output *output, bool enable) { output->impl->enable(output, enable); } -bool wlr_output_set_mode(struct wlr_output *output, struct wlr_output_mode *mode) { +bool wlr_output_set_mode(struct wlr_output *output, + struct wlr_output_mode *mode) { if (!output->impl || !output->impl->set_mode) { return false; } bool result = output->impl->set_mode(output, mode); if (result) { wlr_output_update_matrix(output); + struct wl_resource *resource; + wl_resource_for_each(resource, &output->wl_resources) { + wlr_output_send_current_mode_to_resource(resource); + } } return result; } +void wlr_output_update_size(struct wlr_output *output, int32_t width, + int32_t height) { + output->width = width; + output->height = height; + wlr_output_update_matrix(output); + if (output->wl_global != NULL) { + struct wl_resource *resource; + wl_resource_for_each(resource, &output->wl_resources) { + wlr_output_send_current_mode_to_resource(resource); + } + } +} + void wlr_output_transform(struct wlr_output *output, enum wl_output_transform transform) { output->impl->transform(output, transform); wlr_output_update_matrix(output); } -void wlr_output_set_position(struct wlr_output *output, int32_t lx, int32_t ly) { +void wlr_output_set_position(struct wlr_output *output, int32_t lx, + int32_t ly) { if (lx == output->lx && ly == output->ly) { return; }