summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnder Conselvan de Oliveira <ander.conselvan.de.oliveira@intel.com>2012-11-30 17:41:02 +0200
committerKristian Høgsberg <krh@bitplanet.net>2013-01-10 16:33:50 -0500
commiteaf6884621661288624fc060974c3aa485771324 (patch)
tree6b226ef2180c5afad061e1d1b987ec620bf0b47a
parent0ac90296a092f846647812318913b0e492775f31 (diff)
egl/wayland: Don't invalidate drawable on swap buffers
We used to invalidate the drawable after a call to eglSwapBuffers(), so that a wl_egl_window_resize() would take effect for the next frame. However, that leads to calling dri2_get_buffers() when eglMakeCurrent() is called with the current context and surface, and a later call to wl_egl_window_resize() would not take effect until the next buffer swap. Instead, add a callback from wl_egl_window_resize() back to the wayland egl platform, and invalidate the drawable only when it is resized. This solves a bug on wayland clients when going back to windowed mode from fullscreen when clicking a pop up menu, where the window size after this would be the fullscreen size. Note: this is a candidate for stable branches. CC: wayland-devel@lists.freedesktop.org
-rw-r--r--src/egl/drivers/dri2/platform_wayland.c20
-rw-r--r--src/egl/wayland/wayland-egl/wayland-egl-priv.h3
-rw-r--r--src/egl/wayland/wayland-egl/wayland-egl.c5
3 files changed, 27 insertions, 1 deletions
diff --git a/src/egl/drivers/dri2/platform_wayland.c b/src/egl/drivers/dri2/platform_wayland.c
index 2fde1715b6a..294413c8095 100644
--- a/src/egl/drivers/dri2/platform_wayland.c
+++ b/src/egl/drivers/dri2/platform_wayland.c
@@ -94,12 +94,22 @@ wl_buffer_release(void *data, struct wl_buffer *buffer)
}
static struct wl_buffer_listener wl_buffer_listener = {
wl_buffer_release
};
+static void
+resize_callback(struct wl_egl_window *wl_win, void *data)
+{
+ struct dri2_egl_surface *dri2_surf = data;
+ struct dri2_egl_display *dri2_dpy =
+ dri2_egl_display(dri2_surf->base.Resource.Display);
+
+ (*dri2_dpy->flush->invalidate)(dri2_surf->dri_drawable);
+}
+
/**
* Called via eglCreateWindowSurface(), drv->API.CreateWindowSurface().
*/
static _EGLSurface *
dri2_create_surface(_EGLDriver *drv, _EGLDisplay *disp, EGLint type,
_EGLConfig *conf, EGLNativeWindowType window,
@@ -139,12 +149,15 @@ dri2_create_surface(_EGLDriver *drv, _EGLDisplay *disp, EGLint type,
dri2_surf->format = WL_DRM_FORMAT_ARGB8888;
switch (type) {
case EGL_WINDOW_BIT:
dri2_surf->wl_win = (struct wl_egl_window *) window;
+ dri2_surf->wl_win->private = dri2_surf;
+ dri2_surf->wl_win->resize_callback = resize_callback;
+
dri2_surf->base.Width = -1;
dri2_surf->base.Height = -1;
break;
default:
goto cleanup_surf;
}
@@ -213,12 +226,18 @@ dri2_destroy_surface(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *surf)
dri2_surf->third_buffer);
}
if (dri2_surf->frame_callback)
wl_callback_destroy(dri2_surf->frame_callback);
+
+ if (dri2_surf->base.Type == EGL_WINDOW_BIT) {
+ dri2_surf->wl_win->private = NULL;
+ dri2_surf->wl_win->resize_callback = NULL;
+ }
+
free(surf);
return EGL_TRUE;
}
static struct wl_buffer *
@@ -584,13 +603,12 @@ dri2_swap_buffers(_EGLDriver *drv, _EGLDisplay *disp, _EGLSurface *draw)
ctx = _eglGetCurrentContext();
if (ctx && ctx->DrawSurface == &dri2_surf->base)
dri2_drv->glFlush();
}
(*dri2_dpy->flush->flush)(dri2_surf->dri_drawable);
- (*dri2_dpy->flush->invalidate)(dri2_surf->dri_drawable);
return EGL_TRUE;
}
static int
dri2_wayland_authenticate(_EGLDisplay *disp, uint32_t id)
diff --git a/src/egl/wayland/wayland-egl/wayland-egl-priv.h b/src/egl/wayland/wayland-egl/wayland-egl-priv.h
index bdbf32a1689..da25be9f710 100644
--- a/src/egl/wayland/wayland-egl/wayland-egl-priv.h
+++ b/src/egl/wayland/wayland-egl/wayland-egl-priv.h
@@ -21,12 +21,15 @@ struct wl_egl_window {
int height;
int dx;
int dy;
int attached_width;
int attached_height;
+
+ void *private;
+ void (*resize_callback)(struct wl_egl_window *, void *);
};
#ifdef __cplusplus
}
#endif
diff --git a/src/egl/wayland/wayland-egl/wayland-egl.c b/src/egl/wayland/wayland-egl/wayland-egl.c
index c61fb4f2c3a..8bd49cf6c4f 100644
--- a/src/egl/wayland/wayland-egl/wayland-egl.c
+++ b/src/egl/wayland/wayland-egl/wayland-egl.c
@@ -10,12 +10,15 @@ wl_egl_window_resize(struct wl_egl_window *egl_window,
int dx, int dy)
{
egl_window->width = width;
egl_window->height = height;
egl_window->dx = dx;
egl_window->dy = dy;
+
+ if (egl_window->resize_callback)
+ egl_window->resize_callback(egl_window, egl_window->private);
}
WL_EGL_EXPORT struct wl_egl_window *
wl_egl_window_create(struct wl_surface *surface,
int width, int height)
{
@@ -23,12 +26,14 @@ wl_egl_window_create(struct wl_surface *surface,
egl_window = malloc(sizeof *egl_window);
if (!egl_window)
return NULL;
egl_window->surface = surface;
+ egl_window->private = NULL;
+ egl_window->resize_callback = NULL;
wl_egl_window_resize(egl_window, width, height, 0, 0);
egl_window->attached_width = 0;
egl_window->attached_height = 0;
return egl_window;
}