clients/window: Add viewport destination support

Add support for setting the widget's destination wp viewport.
Setting it in the widget instead of being set directly by the client
ensure that the widget can be identified in widget_find_widget.

v2: Return -1 on error (Pekka)
    Scale allocated x and y when viewport is set (Pekka)
    Allow user to set -1 for viewport width and height (Pekka)

v3: Use NULL instead of 0 (Daniel)
    return 0 if width and height are -1 (Daniel)

Signed-off-by: Harish Krupo <harish.krupo.kps@intel.com>
dev
Harish Krupo 6 years ago committed by Daniel Stone
parent 7e0f20311f
commit 7bcbab1f2f
  1. 2
      clients/meson.build
  2. 76
      clients/window.c
  3. 8
      clients/window.h

@ -14,6 +14,8 @@ srcs_toytoolkit = [
pointer_constraints_unstable_v1_protocol_c,
ivi_application_client_protocol_h,
ivi_application_protocol_c,
viewporter_client_protocol_h,
viewporter_protocol_c,
]
deps_toytoolkit = [
dep_wayland_client,

@ -82,6 +82,7 @@ typedef void *EGLContext;
#include "shared/string-helpers.h"
#include "window.h"
#include "viewporter-client-protocol.h"
#define ZWP_RELATIVE_POINTER_MANAGER_V1_VERSION 1
#define ZWP_POINTER_CONSTRAINTS_V1_VERSION 1
@ -147,6 +148,7 @@ struct display {
int has_rgb565;
int data_device_manager_version;
struct wp_viewporter *viewporter;
};
struct window_output {
@ -222,6 +224,7 @@ struct surface {
cairo_surface_t *cairo_surface;
struct wl_list link;
struct wp_viewport *viewport;
};
struct window {
@ -320,6 +323,8 @@ struct widget {
* redraw handler is going to do completely custom rendering
* such as using EGL directly */
int use_cairo;
int viewport_dest_width;
int viewport_dest_height;
};
struct touch_point {
@ -1398,6 +1403,7 @@ display_get_pointer_image(struct display *display, int pointer)
static void
surface_flush(struct surface *surface)
{
struct widget *widget = surface->widget;
if (!surface->cairo_surface)
return;
@ -1415,6 +1421,12 @@ surface_flush(struct surface *surface)
surface->input_region = NULL;
}
if (surface->viewport) {
wp_viewport_set_destination(surface->viewport,
widget->viewport_dest_width,
widget->viewport_dest_height);
}
surface->toysurface->swap(surface->toysurface,
surface->buffer_transform, surface->buffer_scale,
&surface->server_allocation);
@ -1620,6 +1632,8 @@ static struct widget *
widget_find_widget(struct widget *widget, int32_t x, int32_t y)
{
struct widget *child, *target;
int alloc_x, alloc_y, width, height;
double scale;
wl_list_for_each(child, &widget->child_list, link) {
target = widget_find_widget(child, x, y);
@ -1627,10 +1641,24 @@ widget_find_widget(struct widget *widget, int32_t x, int32_t y)
return target;
}
if (widget->allocation.x <= x &&
x < widget->allocation.x + widget->allocation.width &&
widget->allocation.y <= y &&
y < widget->allocation.y + widget->allocation.height) {
alloc_x = widget->allocation.x;
alloc_y = widget->allocation.y;
width = widget->allocation.width;
height = widget->allocation.height;
if (widget->viewport_dest_width != -1 &&
widget->viewport_dest_height != -1) {
scale = widget->viewport_dest_width / (double) width;
alloc_x = alloc_x * scale;
width = widget->viewport_dest_width;
scale = widget->viewport_dest_height / (double) height;
alloc_y = alloc_y * scale;
height = widget->viewport_dest_height;
}
if (alloc_x <= x && x < alloc_x + width &&
alloc_y <= y && y < alloc_y + height) {
return widget;
}
@ -1668,6 +1696,8 @@ widget_create(struct window *window, struct surface *surface, void *data)
widget->tooltip_count = 0;
widget->default_cursor = CURSOR_LEFT_PTR;
widget->use_cairo = 1;
widget->viewport_dest_width = -1;
widget->viewport_dest_height = -1;
return widget;
}
@ -2025,6 +2055,39 @@ widget_set_use_cairo(struct widget *widget,
widget->use_cairo = use_cairo;
}
int
widget_set_viewport_destination(struct widget *widget, int width, int height)
{
struct window *window = widget->window;
struct display *display = window->display;
struct surface *surface = widget->surface;
if (!display->viewporter)
return -1;
if (width == -1 && height == -1) {
if (surface->viewport) {
wp_viewport_destroy(surface->viewport);
surface->viewport = NULL;
}
widget->viewport_dest_width = -1;
widget->viewport_dest_height = -1;
return 0;
}
if (!surface->viewport) {
surface->viewport = wp_viewporter_get_viewport(display->viewporter,
surface->surface);
if (!surface->viewport)
return -1;
}
widget->viewport_dest_width = width;
widget->viewport_dest_height = height;
return 0;
}
cairo_surface_t *
window_get_surface(struct window *window)
{
@ -5165,6 +5228,7 @@ surface_create(struct window *window)
wl_surface_add_listener(surface->surface, &surface_listener, window);
wl_list_insert(&window->subsurface_list, &surface->link);
surface->viewport = NULL;
return surface;
}
@ -6003,6 +6067,10 @@ registry_handle_global(void *data, struct wl_registry *registry, uint32_t id,
d->subcompositor =
wl_registry_bind(registry, id,
&wl_subcompositor_interface, 1);
} else if (!strcmp(interface, "wp_viewporter")) {
d->viewporter =
wl_registry_bind(registry, id,
&wp_viewporter_interface, 1);
}
if (d->global_handler)

@ -613,6 +613,14 @@ widget_schedule_redraw(struct widget *widget);
void
widget_set_use_cairo(struct widget *widget, int use_cairo);
/*
* Sets the viewport destination for the widget's surface
* return 0 on success and -1 on failure. Set width and height to
* -1 to reset the viewport.
*/
int
widget_set_viewport_destination(struct widget *widget, int width, int height);
struct widget *
window_frame_create(struct window *window, void *data);

Loading…
Cancel
Save