diff --git a/platform/wayland/cog-platform-wl.c b/platform/wayland/cog-platform-wl.c index 748d61cb..cd7efa60 100644 --- a/platform/wayland/cog-platform-wl.c +++ b/platform/wayland/cog-platform-wl.c @@ -97,7 +97,7 @@ cog_wl_platform_configure_geometry(CogWlPlatform *platform, int32_t width, int32 platform->window.width = width; platform->window.height = height; - cog_wl_view_resize(platform->view); + cog_viewport_foreach(platform->viewport, (GFunc) cog_wl_view_resize, NULL); } } @@ -106,6 +106,11 @@ static void resize_to_largest_output(CogWlPlatform *); static void cog_wl_platform_enter_fullscreen(CogWlPlatform *platform) { + if (!cog_viewport_get_n_views(platform->viewport)) { + g_debug("%s: No views in viewport, will not fullscreen.", G_STRFUNC); + return; + } + CogWlDisplay *display = platform->display; CogWlWindow *window = &platform->window; @@ -122,13 +127,17 @@ cog_wl_platform_enter_fullscreen(CogWlPlatform *platform) g_assert_not_reached(); } + // XXX: Do we need to set all views as fullscreened? // Wait until a new exported image is reveived. See cog_wl_view_enter_fullscreen(). - cog_wl_view_enter_fullscreen(platform->view); + cog_wl_view_enter_fullscreen(COG_WL_VIEW(cog_viewport_get_visible_view(platform->viewport))); } static void cog_wl_platform_exit_fullscreen(CogWlPlatform *platform) { + // The surface was not fullscreened if there were no views. + g_assert(cog_viewport_get_n_views(platform->viewport) > 0); + CogWlDisplay *display = platform->display; CogWlWindow *window = &platform->window; @@ -146,7 +155,7 @@ cog_wl_platform_exit_fullscreen(CogWlPlatform *platform) #if HAVE_FULLSCREEN_HANDLING if (window->was_fullscreen_requested_from_dom) { - cog_wl_view_exit_fullscreen(platform->view); + cog_wl_view_exit_fullscreen(COG_WL_VIEW(cog_viewport_get_visible_view(platform->viewport))); } window->was_fullscreen_requested_from_dom = false; #endif @@ -294,7 +303,7 @@ output_handle_done(void *data, struct wl_output *output) // Forces a View resize since the output changed so the device // scale factor could be different and the scale of the exported // image should be also updated. - cog_wl_view_resize(platform->view); + cog_viewport_foreach(platform->viewport, (GFunc) cog_wl_view_resize, NULL); } if (platform->window.should_resize_to_largest_output) { @@ -349,26 +358,32 @@ surface_on_enter(void *data, struct wl_surface *surface, struct wl_output *outpu CogWlPlatform *platform = data; CogWlDisplay *display = platform->display; - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - if (display->current_output->output != output) { g_debug("%s: Surface %p output changed %p -> %p", G_STRFUNC, surface, display->current_output->output, output); display->current_output = find_output(platform->display, output); g_assert(display->current_output); } + uint32_t output_scale = 0; #ifdef WL_SURFACE_SET_BUFFER_SCALE_SINCE_VERSION if (wl_surface_get_version(surface) >= WL_SURFACE_SET_BUFFER_SCALE_SINCE_VERSION) { wl_surface_set_buffer_scale(surface, display->current_output->scale); - wpe_view_backend_dispatch_set_device_scale_factor(backend, display->current_output->scale); + output_scale = display->current_output->scale; } else { g_debug("%s: Surface %p uses old protocol version, cannot set scale factor", G_STRFUNC, surface); } #endif /* WL_SURFACE_SET_BUFFER_SCALE_SINCE_VERSION */ + for (unsigned i = 0; i < cog_viewport_get_n_views(platform->viewport); i++) { + struct wpe_view_backend *backend = cog_view_get_backend(cog_viewport_get_nth_view(platform->viewport, i)); + #if HAVE_REFRESH_RATE_HANDLING - wpe_view_backend_set_target_refresh_rate(backend, display->current_output->refresh); + wpe_view_backend_set_target_refresh_rate(backend, display->current_output->refresh); #endif /* HAVE_REFRESH_RATE_HANDLING */ + + if (output_scale) + wpe_view_backend_dispatch_set_device_scale_factor(backend, display->current_output->scale); + } } static const struct wl_surface_listener surface_listener = { @@ -515,9 +530,9 @@ pointer_on_motion(void *data, struct wl_pointer *pointer, uint32_t time, wl_fixe seat->pointer.button, seat->pointer.state}; - CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_pointer_event(backend, &event); + CogView *view = cog_viewport_get_visible_view(((CogWlPlatform *) cog_platform_get_default())->viewport); + if (view) + wpe_view_backend_dispatch_pointer_event(cog_view_get_backend(view), &event); } static void @@ -573,8 +588,9 @@ pointer_on_button(void *data, } } - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_pointer_event(backend, &event); + CogView *view = cog_viewport_get_visible_view(((CogWlPlatform *) cog_platform_get_default())->viewport); + if (view) + wpe_view_backend_dispatch_pointer_event(cog_view_get_backend(view), &event); } static void @@ -596,9 +612,9 @@ dispatch_axis_event(CogWlSeat *seat) event.x_axis = wl_fixed_to_double(seat->axis.x_delta) * display->current_output->scale; event.y_axis = -wl_fixed_to_double(seat->axis.y_delta) * display->current_output->scale; - CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_axis_event(backend, &event.base); + CogView *view = cog_viewport_get_visible_view(((CogWlPlatform *) cog_platform_get_default())->viewport); + if (view) + wpe_view_backend_dispatch_axis_event(cog_view_get_backend(view), &event.base); seat->axis.has_delta = false; seat->axis.time = 0; @@ -745,19 +761,20 @@ static void handle_key_event(CogWlSeat *seat, uint32_t key, uint32_t state, uint32_t time) { CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + CogView *view = cog_viewport_get_visible_view(platform->viewport); - if (seat->xkb.state == NULL) + if (!view || seat->xkb.state == NULL) return; uint32_t keysym = xkb_state_key_get_one_sym(seat->xkb.state, key); uint32_t unicode = xkb_state_key_get_utf32(seat->xkb.state, key); /* TODO: Move as much as possible from fullscreen handling to common code. */ - if (cog_view_get_use_key_bindings(COG_VIEW(platform->view)) && state == WL_KEYBOARD_KEY_STATE_PRESSED && - seat->xkb.modifiers == 0 && unicode == 0 && keysym == XKB_KEY_F11) { + if (cog_view_get_use_key_bindings(view) && state == WL_KEYBOARD_KEY_STATE_PRESSED && seat->xkb.modifiers == 0 && + unicode == 0 && keysym == XKB_KEY_F11) { #if HAVE_FULLSCREEN_HANDLING if (platform->window.is_fullscreen && platform->window.was_fullscreen_requested_from_dom) { - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); + struct wpe_view_backend *backend = cog_view_get_backend(view); wpe_view_backend_dispatch_request_exit_fullscreen(backend); return; } @@ -774,7 +791,7 @@ handle_key_event(CogWlSeat *seat, uint32_t key, uint32_t state, uint32_t time) struct wpe_input_keyboard_event event = {time, keysym, key, state == true, seat->xkb.modifiers}; - cog_view_handle_key_event(COG_VIEW(platform->view), &event); + cog_view_handle_key_event(view, &event); } static gboolean @@ -956,8 +973,9 @@ touch_on_down(void *data, struct wpe_input_touch_event event = {seat->touch.points, 10, raw_event.type, raw_event.id, raw_event.time}; - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_touch_event(backend, &event); + CogView *view = cog_viewport_get_visible_view(platform->viewport); + if (view) + wpe_view_backend_dispatch_touch_event(cog_view_get_backend(view), &event); } static void @@ -999,8 +1017,9 @@ touch_on_up(void *data, struct wl_touch *touch, uint32_t serial, uint32_t time, struct wpe_input_touch_event event = {seat->touch.points, 10, raw_event.type, raw_event.id, raw_event.time}; - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_touch_event(backend, &event); + CogView *view = cog_viewport_get_visible_view(platform->viewport); + if (view) + wpe_view_backend_dispatch_touch_event(cog_view_get_backend(view), &event); memset(&seat->touch.points[id], 0x00, sizeof(struct wpe_input_touch_event_raw)); } @@ -1031,9 +1050,9 @@ touch_on_motion(void *data, struct wl_touch *touch, uint32_t time, int32_t id, w struct wpe_input_touch_event event = {seat->touch.points, 10, raw_event.type, raw_event.id, raw_event.time}; - CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(platform->view)); - wpe_view_backend_dispatch_touch_event(backend, &event); + CogView *view = cog_viewport_get_visible_view(((CogWlPlatform *) cog_platform_get_default())->viewport); + if (view) + wpe_view_backend_dispatch_touch_event(cog_view_get_backend(view), &event); } static void @@ -1560,16 +1579,44 @@ static struct wpe_view_backend * gamepad_provider_get_view_backend_for_gamepad(void *provider G_GNUC_UNUSED, void *gamepad G_GNUC_UNUSED) { CogWlPlatform *platform = COG_WL_PLATFORM(cog_platform_get_default()); - CogWlView *view = platform->view; + + CogWlView *view = (CogWlView *) cog_viewport_get_visible_view(platform->viewport); g_assert(view); return wpe_view_backend_exportable_fdo_get_view_backend(view->exportable); } +static void +cog_wl_platform_on_notify_visible_view(CogWlPlatform *self) +{ + CogWlView *view = (CogWlView *) cog_viewport_get_visible_view(self->viewport); + g_debug("%s: Visible view %p.", G_STRFUNC, view); + + if (!view) + return; + + /* + * TODO: Once we support multiple viewports, a view may be visible + * without having focus. At that point the input events will + * need to go to the *focused* view instead. + * + * For now add the flag and assume that visible == focused. + */ + wpe_view_backend_add_activity_state(cog_view_get_backend((CogView *) view), wpe_view_activity_state_focused); + + if (!view->image) + return g_debug("%s: No image to show, skipping update.", G_STRFUNC); + + cog_wl_view_update_surface_contents(view); +} + static gboolean cog_wl_platform_setup(CogPlatform *platform, CogShell *shell G_GNUC_UNUSED, const char *params, GError **error) { g_return_val_if_fail(COG_IS_SHELL(shell), FALSE); + CogWlPlatform *self = COG_WL_PLATFORM(platform); + self->viewport = cog_shell_get_viewport(shell); + if (!wpe_loader_init("libWPEBackend-fdo-1.0.so")) { g_set_error_literal(error, COG_PLATFORM_WPE_ERROR, @@ -1602,6 +1649,9 @@ cog_wl_platform_setup(CogPlatform *platform, CogShell *shell G_GNUC_UNUSED, cons cog_gamepad_setup(gamepad_provider_get_view_backend_for_gamepad); + g_signal_connect_object(self->viewport, "notify::visible-view", G_CALLBACK(cog_wl_platform_on_notify_visible_view), + self, G_CONNECT_AFTER | G_CONNECT_SWAPPED); + return TRUE; } @@ -1610,23 +1660,6 @@ cog_wl_platform_finalize(GObject *object) { CogWlPlatform *platform = COG_WL_PLATFORM(object); - /* free WPE view data */ - if (platform->view->frame_callback != NULL) - wl_callback_destroy(platform->view->frame_callback); - if (platform->view->image != NULL) { - wpe_view_backend_exportable_fdo_egl_dispatch_release_exported_image(platform->view->exportable, - platform->view->image); - } - - /* @FIXME: check why this segfaults - wpe_view_backend_destroy (wpe_view_data.backend); - */ - - /* free WPE host data */ - /* @FIXME: check why this segfaults - wpe_view_backend_exportable_wl_destroy (wpe_host_data.exportable); - */ - cog_wl_text_input_clear(platform); if (platform->popup) cog_wl_platform_popup_destroy(platform); diff --git a/platform/wayland/cog-platform-wl.h b/platform/wayland/cog-platform-wl.h index b22a914f..60dabb81 100644 --- a/platform/wayland/cog-platform-wl.h +++ b/platform/wayland/cog-platform-wl.h @@ -27,7 +27,7 @@ struct _CogWlPlatform { CogPlatform parent; CogWlDisplay *display; CogWlPopup *popup; - CogWlView *view; + CogViewport *viewport; // TODO: Support multiple viewports. CogWlWindow window; }; diff --git a/platform/wayland/cog-view-wl.c b/platform/wayland/cog-view-wl.c index 9613d6f4..2251829d 100644 --- a/platform/wayland/cog-view-wl.c +++ b/platform/wayland/cog-view-wl.c @@ -108,10 +108,6 @@ cog_wl_view_init(CogWlView *self) self->should_update_opaque_region = true; self->image = NULL; self->frame_callback = NULL; - self->platform = COG_WL_PLATFORM(cog_platform_get_default()); - - // Only one view is managed by the Wayland Platform nowadays. - self->platform->view = self; wl_list_init(&self->shm_buffer_list); @@ -139,6 +135,8 @@ cog_wl_view_dispose(GObject *object) g_clear_pointer(&self->frame_callback, wl_callback_destroy); if (self->image) { + g_assert(self->exportable); + wpe_view_backend_exportable_fdo_egl_dispatch_release_exported_image(self->exportable, self->image); self->image = NULL; } @@ -178,6 +176,7 @@ cog_wl_view_clear_buffers(CogWlView *view) static WebKitWebViewBackend * cog_wl_view_create_backend(CogView *view) { + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); CogWlView *self = COG_WL_VIEW(view); static const struct wpe_view_backend_exportable_fdo_egl_client client = { @@ -187,17 +186,15 @@ cog_wl_view_create_backend(CogView *view) #endif }; - self->exportable = wpe_view_backend_exportable_fdo_egl_create(&client, self, self->platform->window.width, - self->platform->window.height); + self->exportable = + wpe_view_backend_exportable_fdo_egl_create(&client, self, platform->window.width, platform->window.height); /* init WPE view backend */ struct wpe_view_backend *view_backend = wpe_view_backend_exportable_fdo_get_view_backend(self->exportable); g_assert(view_backend); - CogWlDisplay *display = self->platform->display; - if (display->text_input_manager_v1 != NULL) { + if (platform->display->text_input_manager_v1) cog_im_context_wl_v1_set_view_backend(view_backend); - } WebKitWebViewBackend *wk_view_backend = webkit_web_view_backend_new(view_backend, @@ -215,9 +212,9 @@ cog_wl_view_create_backend(CogView *view) bool cog_wl_view_does_image_match_win_size(CogWlView *view) { - struct wpe_fdo_egl_exported_image *image = view->image; - return image && wpe_fdo_egl_exported_image_get_width(image) == view->platform->window.width && - wpe_fdo_egl_exported_image_get_height(image) == view->platform->window.height; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + return view->image && wpe_fdo_egl_exported_image_get_width(view->image) == platform->window.width && + wpe_fdo_egl_exported_image_get_height(view->image) == platform->window.height; } void @@ -228,8 +225,8 @@ cog_wl_view_enter_fullscreen(CogWlView *view) return; #if HAVE_FULLSCREEN_HANDLING - g_assert(view->platform); - if (view->platform->window.was_fullscreen_requested_from_dom) + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + if (platform->window.was_fullscreen_requested_from_dom) wpe_view_backend_dispatch_did_enter_fullscreen(cog_view_get_backend(COG_VIEW(view))); #endif @@ -249,15 +246,14 @@ cog_wl_view_exit_fullscreen(CogWlView *view) static bool cog_wl_view_handle_dom_fullscreen_request(void *data, bool fullscreen) { - CogWlView *view = data; - CogWlWindow window = view->platform->window; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); - window.was_fullscreen_requested_from_dom = true; - if (fullscreen != window.is_fullscreen) - return cog_wl_platform_set_fullscreen(view->platform, fullscreen); + platform->window.was_fullscreen_requested_from_dom = true; + if (fullscreen != platform->window.is_fullscreen) + return cog_wl_platform_set_fullscreen(platform, fullscreen); // Handle situations where DOM fullscreen requests are mixed with system fullscreen commands (e.g F11) - struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(view)); + struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(data)); if (fullscreen) wpe_view_backend_dispatch_did_enter_fullscreen(backend); else @@ -276,24 +272,21 @@ cog_wl_view_on_buffer_release(void *data G_GNUC_UNUSED, struct wl_buffer *buffer static void cog_wl_view_request_frame(CogWlView *view) { - CogWlDisplay *display = view->platform->display; - g_assert(display); - - CogWlWindow window = view->platform->window; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); if (!view->frame_callback) { static const struct wl_callback_listener listener = {.done = on_wl_surface_frame}; - view->frame_callback = wl_surface_frame(window.wl_surface); + view->frame_callback = wl_surface_frame(platform->window.wl_surface); wl_callback_add_listener(view->frame_callback, &listener, view); } - if (display->presentation != NULL) { + if (platform->display->presentation != NULL) { static const struct wp_presentation_feedback_listener presentation_feedback_listener = { .sync_output = presentation_feedback_on_sync_output, .presented = presentation_feedback_on_presented, .discarded = presentation_feedback_on_discarded}; struct wp_presentation_feedback *presentation_feedback = - wp_presentation_feedback(display->presentation, window.wl_surface); + wp_presentation_feedback(platform->display->presentation, platform->window.wl_surface); wp_presentation_feedback_add_listener(presentation_feedback, &presentation_feedback_listener, NULL); } } @@ -301,36 +294,32 @@ cog_wl_view_request_frame(CogWlView *view) void cog_wl_view_resize(CogWlView *view) { - g_assert(view->platform); - CogWlPlatform *platform = view->platform; - CogWlDisplay *display = platform->display; - CogWlWindow *window = &platform->window; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); view->should_update_opaque_region = true; - int32_t pixel_width = window->width * display->current_output->scale; - int32_t pixel_height = window->height * display->current_output->scale; + int32_t pixel_width = platform->window.width * platform->display->current_output->scale; + int32_t pixel_height = platform->window.height * platform->display->current_output->scale; struct wpe_view_backend *backend = cog_view_get_backend(COG_VIEW(view)); - wpe_view_backend_dispatch_set_size(backend, window->width, window->height); - wpe_view_backend_dispatch_set_device_scale_factor(backend, display->current_output->scale); + wpe_view_backend_dispatch_set_size(backend, platform->window.width, platform->window.height); + wpe_view_backend_dispatch_set_device_scale_factor(backend, platform->display->current_output->scale); g_debug("Resized EGL buffer to: (%" PRIi32 ", %" PRIi32 ") @%" PRIi32 "x", pixel_width, pixel_height, - display->current_output->scale); + platform->display->current_output->scale); } void cog_wl_view_update_surface_contents(CogWlView *view) { + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); g_assert(view); - CogWlWindow *window = &view->platform->window; - CogWlDisplay *display = view->platform->display; - g_assert(display); - struct wl_surface *surface = window->wl_surface; + + struct wl_surface *surface = platform->window.wl_surface; g_assert(surface); - const uint32_t surface_pixel_width = display->current_output->scale * window->width; - const uint32_t surface_pixel_height = display->current_output->scale * window->height; + const uint32_t surface_pixel_width = platform->display->current_output->scale * platform->window.width; + const uint32_t surface_pixel_height = platform->display->current_output->scale * platform->window.height; if (view->should_update_opaque_region) { view->should_update_opaque_region = false; @@ -338,9 +327,9 @@ cog_wl_view_update_surface_contents(CogWlView *view) WebKitColor bg_color; webkit_web_view_get_background_color(WEBKIT_WEB_VIEW(view), &bg_color); - if (window->is_fullscreen || !cog_wl_view_background_has_alpha(COG_WL_VIEW(view))) { - struct wl_region *region = wl_compositor_create_region(display->compositor); - wl_region_add(region, 0, 0, window->width, window->height); + if (platform->window.is_fullscreen || !cog_wl_view_background_has_alpha(COG_WL_VIEW(view))) { + struct wl_region *region = wl_compositor_create_region(platform->display->compositor); + wl_region_add(region, 0, 0, platform->window.width, platform->window.height); wl_surface_set_opaque_region(surface, region); wl_region_destroy(region); } else { @@ -356,7 +345,7 @@ cog_wl_view_update_surface_contents(CogWlView *view) } struct wl_buffer *buffer = s_eglCreateWaylandBufferFromImageWL( - display->egl_display, wpe_fdo_egl_exported_image_get_egl_image(view->image)); + platform->display->egl_display, wpe_fdo_egl_exported_image_get_egl_image(view->image)); g_assert(buffer); static const struct wl_buffer_listener buffer_listener = {.release = cog_wl_view_on_buffer_release}; @@ -374,13 +363,12 @@ cog_wl_view_update_surface_contents(CogWlView *view) } static bool -validate_exported_geometry(CogWlView *view, uint32_t width, uint32_t height) +validate_exported_geometry(uint32_t width, uint32_t height) { - CogWlDisplay *display = view->platform->display; - CogWlWindow window = view->platform->window; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); - const uint32_t surface_pixel_width = display->current_output->scale * window.width; - const uint32_t surface_pixel_height = display->current_output->scale * window.height; + const uint32_t surface_pixel_width = platform->display->current_output->scale * platform->window.width; + const uint32_t surface_pixel_height = platform->display->current_output->scale * platform->window.height; if (surface_pixel_width != width || surface_pixel_height != height) { g_debug("Image geometry %" PRIu32 "x%" PRIu32 ", does not match surface geometry %" PRIu32 "x%" PRIu32 @@ -396,15 +384,15 @@ validate_exported_geometry(CogWlView *view, uint32_t width, uint32_t height) static void on_export_shm_buffer(void *data, struct wpe_fdo_shm_exported_buffer *exported_buffer) { - CogWlView *view = data; - CogWlWindow window = view->platform->window; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + CogWlView *view = data; struct wl_resource *exported_resource = wpe_fdo_shm_exported_buffer_get_resource(exported_buffer); struct wl_shm_buffer *exported_shm_buffer = wpe_fdo_shm_exported_buffer_get_shm_buffer(exported_buffer); uint32_t image_width = wl_shm_buffer_get_width(exported_shm_buffer); uint32_t image_height = wl_shm_buffer_get_height(exported_shm_buffer); - if (!validate_exported_geometry(view, image_width, image_height)) { + if (!validate_exported_geometry(image_width, image_height)) { wpe_view_backend_exportable_fdo_dispatch_frame_complete(view->exportable); wpe_view_backend_exportable_fdo_egl_dispatch_release_shm_exported_buffer(view->exportable, exported_buffer); return; @@ -414,9 +402,9 @@ on_export_shm_buffer(void *data, struct wpe_fdo_shm_exported_buffer *exported_bu if (!buffer) { int32_t width; int32_t height; - if (window.is_fullscreen) { - width = window.width; - height = window.height; + if (platform->window.is_fullscreen) { + width = platform->window.width; + height = platform->window.height; } else { width = wl_shm_buffer_get_width(exported_shm_buffer); height = wl_shm_buffer_get_height(exported_shm_buffer); @@ -441,10 +429,13 @@ on_export_shm_buffer(void *data, struct wpe_fdo_shm_exported_buffer *exported_bu buffer->exported_buffer = exported_buffer; shm_buffer_copy_contents(buffer, exported_shm_buffer); - wl_surface_attach(window.wl_surface, buffer->buffer, 0, 0); - wl_surface_damage(window.wl_surface, 0, 0, INT32_MAX, INT32_MAX); - cog_wl_view_request_frame(view); - wl_surface_commit(window.wl_surface); + const int32_t state = wpe_view_backend_get_activity_state(cog_view_get_backend((CogView *) view)); + if (state & wpe_view_activity_state_visible) { + wl_surface_attach(platform->window.wl_surface, buffer->buffer, 0, 0); + wl_surface_damage(platform->window.wl_surface, 0, 0, INT32_MAX, INT32_MAX); + cog_wl_view_request_frame(view); + wl_surface_commit(platform->window.wl_surface); + } } #endif @@ -455,7 +446,7 @@ on_export_wl_egl_image(void *data, struct wpe_fdo_egl_exported_image *image) uint32_t image_width = wpe_fdo_egl_exported_image_get_width(image); uint32_t image_height = wpe_fdo_egl_exported_image_get_height(image); - if (!validate_exported_geometry(self, image_width, image_height)) { + if (!validate_exported_geometry(image_width, image_height)) { wpe_view_backend_exportable_fdo_dispatch_frame_complete(self->exportable); wpe_view_backend_exportable_fdo_egl_dispatch_release_exported_image(self->exportable, image); return; @@ -466,14 +457,16 @@ on_export_wl_egl_image(void *data, struct wpe_fdo_egl_exported_image *image) self->image = image; - cog_wl_view_update_surface_contents(self); + const int32_t state = wpe_view_backend_get_activity_state(cog_view_get_backend((CogView *) self)); + if (state & wpe_view_activity_state_visible) + cog_wl_view_update_surface_contents(self); } static void on_mouse_target_changed(WebKitWebView *view, WebKitHitTestResult *hitTestResult, guint mouseModifiers) { #ifdef COG_USE_WAYLAND_CURSOR - CogWlPlatform *platform = COG_WL_VIEW(view)->platform; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); if (webkit_hit_test_result_context_is_link(hitTestResult)) { cog_wl_seat_set_cursor(platform->display->seat_default, CURSOR_HAND); } else if (webkit_hit_test_result_context_is_editable(hitTestResult)) { @@ -490,12 +483,11 @@ on_mouse_target_changed(WebKitWebView *view, WebKitHitTestResult *hitTestResult, static void on_run_file_chooser(WebKitWebView *view, WebKitFileChooserRequest *request) { - g_autoptr(XdpParent) xdp_parent = NULL; - - CogWlPlatform *platform = COG_WL_VIEW(view)->platform; + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + g_autoptr(XdpParent) xdp_parent = NULL; if (platform->window.xdp_parent_wl_data.zxdg_exporter && platform->window.xdp_parent_wl_data.wl_surface) { - xdp_parent = xdp_parent_new_wl(&COG_WL_VIEW(view)->platform->window.xdp_parent_wl_data); + xdp_parent = xdp_parent_new_wl(&platform->window.xdp_parent_wl_data); } run_file_chooser(view, request, xdp_parent); @@ -505,7 +497,8 @@ on_run_file_chooser(WebKitWebView *view, WebKitFileChooserRequest *request) static void on_show_option_menu(WebKitWebView *view, WebKitOptionMenu *menu, WebKitRectangle *rectangle, gpointer *data) { - cog_wl_platform_popup_create(COG_WL_VIEW(view)->platform, g_object_ref(menu)); + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + cog_wl_platform_popup_create(platform, g_object_ref(menu)); } static void @@ -584,7 +577,8 @@ shm_buffer_create(CogWlView *view, struct wl_resource *buffer_resource, size_t s buffer->buffer_resource = buffer_resource; wl_resource_add_destroy_listener(buffer_resource, &buffer->destroy_listener); - buffer->shm_pool = wl_shm_create_pool(view->platform->display->shm, fd, size); + CogWlPlatform *platform = (CogWlPlatform *) cog_platform_get_default(); + buffer->shm_pool = wl_shm_create_pool(platform->display->shm, fd, size); buffer->data = data; buffer->size = size; diff --git a/platform/wayland/cog-view-wl.h b/platform/wayland/cog-view-wl.h index 0d329598..619be80e 100644 --- a/platform/wayland/cog-view-wl.h +++ b/platform/wayland/cog-view-wl.h @@ -23,8 +23,6 @@ typedef struct _CogWlPlatform CogWlPlatform; struct _CogWlView { CogView parent; - CogWlPlatform *platform; - struct wpe_view_backend_exportable_fdo *exportable; struct wpe_fdo_egl_exported_image *image; @@ -44,9 +42,9 @@ G_DECLARE_FINAL_TYPE(CogWlView, cog_wl_view, COG, WL_VIEW, CogView) * Method declarations. */ +void cog_wl_view_update_surface_contents(CogWlView *); void cog_wl_view_enter_fullscreen(CogWlView *); void cog_wl_view_exit_fullscreen(CogWlView *); - void cog_wl_view_resize(CogWlView *); void cog_wl_view_register_type_exported(GTypeModule *type_module);