cogl/xlib: Move EGL XLIB onscreen to separate file

As with the other onscreens, separate it into its own file in
preparation for GObjectification.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1514>
This commit is contained in:
Jonas Ådahl 2020-10-17 18:25:53 +02:00 committed by Robert Mader
parent a057432e3d
commit 8339c064c8
5 changed files with 416 additions and 292 deletions

View File

@ -411,6 +411,8 @@ endif
if have_egl_xlib
cogl_sources += [
'winsys/cogl-onscreen-xlib.c',
'winsys/cogl-onscreen-xlib.h',
'winsys/cogl-winsys-egl-x11.c',
'winsys/cogl-winsys-egl-x11-private.h',
]

View File

@ -0,0 +1,331 @@
/*
* Copyright (C) 2011,2013 Intel Corporation.
* Copyrigth (C) 2020 Red Hat
*
* Permission is hereby granted, free of charge, to any person
* obtaining a copy of this software and associated documentation
* files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use, copy,
* modify, merge, publish, distribute, sublicense, and/or sell copies
* of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*
*/
#include "cogl-config.h"
#include "winsys/cogl-onscreen-xlib.h"
#include "cogl-context-private.h"
#include "cogl-renderer-private.h"
#include "cogl-xlib-renderer-private.h"
#include "winsys/cogl-onscreen-egl.h"
#include "winsys/cogl-winsys-egl-x11-private.h"
typedef struct _CoglOnscreenXlib
{
Window xwin;
gboolean pending_resize_notify;
} CoglOnscreenXlib;
#define COGL_ONSCREEN_X11_EVENT_MASK (StructureNotifyMask | ExposureMask)
gboolean
_cogl_winsys_egl_onscreen_xlib_init (CoglOnscreen *onscreen,
EGLConfig egl_config,
GError **error)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglDisplay *display = context->display;
CoglRenderer *renderer = display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglOnscreenXlib *xlib_onscreen;
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
Window xwin;
EGLSurface egl_surface;
/* FIXME: We need to explicitly Select for ConfigureNotify events.
* We need to document that for windows we create then toolkits
* must be careful not to clear event mask bits that we select.
*/
{
int width;
int height;
CoglXlibTrapState state;
XVisualInfo *xvisinfo;
XSetWindowAttributes xattr;
unsigned long mask;
int xerror;
width = cogl_framebuffer_get_width (framebuffer);
height = cogl_framebuffer_get_height (framebuffer);
_cogl_xlib_renderer_trap_errors (display->renderer, &state);
xvisinfo = cogl_display_xlib_get_visual_info (display, egl_config);
if (xvisinfo == NULL)
{
g_set_error (error, COGL_WINSYS_ERROR,
COGL_WINSYS_ERROR_CREATE_ONSCREEN,
"Unable to retrieve the X11 visual of context's "
"fbconfig");
return FALSE;
}
/* window attributes */
xattr.background_pixel =
WhitePixel (xlib_renderer->xdpy,
DefaultScreen (xlib_renderer->xdpy));
xattr.border_pixel = 0;
/* XXX: is this an X resource that we are leaking‽... */
xattr.colormap =
XCreateColormap (xlib_renderer->xdpy,
DefaultRootWindow (xlib_renderer->xdpy),
xvisinfo->visual,
AllocNone);
xattr.event_mask = COGL_ONSCREEN_X11_EVENT_MASK;
mask = CWBorderPixel | CWColormap | CWEventMask;
xwin = XCreateWindow (xlib_renderer->xdpy,
DefaultRootWindow (xlib_renderer->xdpy),
0, 0,
width, height,
0,
xvisinfo->depth,
InputOutput,
xvisinfo->visual,
mask, &xattr);
XFree (xvisinfo);
XSync (xlib_renderer->xdpy, False);
xerror =
_cogl_xlib_renderer_untrap_errors (display->renderer, &state);
if (xerror)
{
char message[1000];
XGetErrorText (xlib_renderer->xdpy, xerror,
message, sizeof (message));
g_set_error (error, COGL_WINSYS_ERROR,
COGL_WINSYS_ERROR_CREATE_ONSCREEN,
"X error while creating Window for CoglOnscreen: %s",
message);
return FALSE;
}
}
xlib_onscreen = g_slice_new (CoglOnscreenXlib);
cogl_onscreen_egl_set_platform (egl_onscreen, xlib_onscreen);
xlib_onscreen->xwin = xwin;
egl_surface =
eglCreateWindowSurface (egl_renderer->edpy,
egl_config,
(EGLNativeWindowType) xlib_onscreen->xwin,
NULL);
cogl_onscreen_egl_set_egl_surface (egl_onscreen,
egl_surface);
return TRUE;
}
void
_cogl_winsys_egl_onscreen_xlib_deinit (CoglOnscreen *onscreen)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglRenderer *renderer = context->display->renderer;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglXlibTrapState old_state;
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
_cogl_xlib_renderer_trap_errors (renderer, &old_state);
if (xlib_onscreen->xwin != None)
{
XDestroyWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
xlib_onscreen->xwin = None;
}
else
xlib_onscreen->xwin = None;
XSync (xlib_renderer->xdpy, False);
if (_cogl_xlib_renderer_untrap_errors (renderer,
&old_state) != Success)
g_warning ("X Error while destroying X window");
g_slice_free (CoglOnscreenXlib, xlib_onscreen);
}
void
_cogl_winsys_onscreen_xlib_set_visibility (CoglOnscreen *onscreen,
gboolean visibility)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglRenderer *renderer = context->display->renderer;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglOnscreenEGL *onscreen_egl = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (onscreen_egl);
if (visibility)
XMapWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
else
XUnmapWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
}
void
_cogl_winsys_onscreen_xlib_set_resizable (CoglOnscreen *onscreen,
gboolean resizable)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (context->display->renderer);
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
XSizeHints *size_hints = XAllocSizeHints ();
if (resizable)
{
/* TODO: Add cogl_onscreen_request_minimum_size () */
size_hints->min_width = 1;
size_hints->min_height = 1;
size_hints->max_width = INT_MAX;
size_hints->max_height = INT_MAX;
}
else
{
int width = cogl_framebuffer_get_width (framebuffer);
int height = cogl_framebuffer_get_height (framebuffer);
size_hints->min_width = width;
size_hints->min_height = height;
size_hints->max_width = width;
size_hints->max_height = height;
}
XSetWMNormalHints (xlib_renderer->xdpy, xlib_onscreen->xwin, size_hints);
XFree (size_hints);
}
uint32_t
_cogl_winsys_onscreen_xlib_get_window_xid (CoglOnscreen *onscreen)
{
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
return xlib_onscreen->xwin;
}
gboolean
cogl_onscreen_xlib_is_for_window (CoglOnscreen *onscreen,
Window window)
{
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
return xlib_onscreen->xwin == window;
}
static void
flush_pending_resize_notifications_cb (void *data,
void *user_data)
{
CoglFramebuffer *framebuffer = data;
if (COGL_IS_ONSCREEN (framebuffer))
{
CoglOnscreen *onscreen = COGL_ONSCREEN (framebuffer);
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
if (xlib_onscreen->pending_resize_notify)
{
_cogl_onscreen_notify_resize (onscreen);
xlib_onscreen->pending_resize_notify = FALSE;
}
}
}
static void
flush_pending_resize_notifications_idle (void *user_data)
{
CoglContext *context = user_data;
CoglRenderer *renderer = context->display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
/* This needs to be disconnected before invoking the callbacks in
* case the callbacks cause it to be queued again */
_cogl_closure_disconnect (egl_renderer->resize_notify_idle);
egl_renderer->resize_notify_idle = NULL;
g_list_foreach (context->framebuffers,
flush_pending_resize_notifications_cb,
NULL);
}
void
cogl_onscreen_xlib_resize (CoglOnscreen *onscreen,
int width,
int height)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglRenderer *renderer = context->display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
CoglOnscreenEGL *egl_onscreen;
CoglOnscreenXlib *xlib_onscreen;
egl_onscreen = cogl_onscreen_get_winsys (onscreen);
_cogl_framebuffer_winsys_update_size (framebuffer, width, height);
/* We only want to notify that a resize happened when the
* application calls cogl_context_dispatch so instead of immediately
* notifying we queue an idle callback */
if (!egl_renderer->resize_notify_idle)
{
egl_renderer->resize_notify_idle =
_cogl_poll_renderer_add_idle (renderer,
flush_pending_resize_notifications_idle,
context,
NULL);
}
xlib_onscreen = cogl_onscreen_egl_get_platform (egl_onscreen);
xlib_onscreen->pending_resize_notify = TRUE;
}

View File

@ -0,0 +1,61 @@
/*
* Copyright (C) 2011,2013 Intel Corporation.
* Copyrigth (C) 2020 Red Hat
*
* Permission is hereby granted, free of charge, to any person
* obtaining a copy of this software and associated documentation
* files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use, copy,
* modify, merge, publish, distribute, sublicense, and/or sell copies
* of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*
*/
#ifndef COGL_ONSCREEN_XLIB_H
#define COGL_ONSCREEN_XLIB_H
#include "cogl-onscreen.h"
#include "winsys/cogl-winsys-egl-private.h"
gboolean
_cogl_winsys_egl_onscreen_xlib_init (CoglOnscreen *onscreen,
EGLConfig egl_config,
GError **error);
void
_cogl_winsys_egl_onscreen_xlib_deinit (CoglOnscreen *onscreen);
void
_cogl_winsys_onscreen_xlib_set_visibility (CoglOnscreen *onscreen,
gboolean visibility);
void
_cogl_winsys_onscreen_xlib_set_resizable (CoglOnscreen *onscreen,
gboolean resizable);
uint32_t
_cogl_winsys_onscreen_xlib_get_window_xid (CoglOnscreen *onscreen);
gboolean
cogl_onscreen_xlib_is_for_window (CoglOnscreen *onscreen,
Window window);
void
cogl_onscreen_xlib_resize (CoglOnscreen *onscreen,
int width,
int height);
#endif /* COGL_ONSCREEN_XLIB_H */

View File

@ -36,4 +36,8 @@
COGL_EXPORT const CoglWinsysVtable *
_cogl_winsys_egl_xlib_get_vtable (void);
XVisualInfo *
cogl_display_xlib_get_visual_info (CoglDisplay *display,
EGLConfig egl_config);
#endif /* __COGL_WINSYS_EGL_X11_PRIVATE_H */

View File

@ -46,11 +46,10 @@
#include "cogl-texture-2d.h"
#include "cogl-poll-private.h"
#include "winsys/cogl-onscreen-egl.h"
#include "winsys/cogl-onscreen-xlib.h"
#include "winsys/cogl-winsys-egl-x11-private.h"
#include "winsys/cogl-winsys-egl-private.h"
#define COGL_ONSCREEN_X11_EVENT_MASK (StructureNotifyMask | ExposureMask)
static const CoglWinsysEGLVtable _cogl_winsys_egl_vtable;
typedef struct _CoglDisplayXlib
@ -58,13 +57,6 @@ typedef struct _CoglDisplayXlib
Window dummy_xwin;
} CoglDisplayXlib;
typedef struct _CoglOnscreenXlib
{
Window xwin;
gboolean pending_resize_notify;
} CoglOnscreenXlib;
#ifdef EGL_KHR_image_pixmap
typedef struct _CoglTexturePixmapEGL
{
@ -81,94 +73,32 @@ find_onscreen_for_xid (CoglContext *context, uint32_t xid)
for (l = context->framebuffers; l; l = l->next)
{
CoglFramebuffer *framebuffer = l->data;
CoglOnscreenEGL *egl_onscreen;
CoglOnscreenXlib *xlib_onscreen;
CoglOnscreen *onscreen;
if (!COGL_IS_ONSCREEN (framebuffer))
continue;
egl_onscreen = cogl_onscreen_get_winsys (COGL_ONSCREEN (framebuffer));
xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
if (xlib_onscreen->xwin == (Window)xid)
return COGL_ONSCREEN (framebuffer);
onscreen = COGL_ONSCREEN (framebuffer);
if (cogl_onscreen_xlib_is_for_window (onscreen, (Window) xid))
return onscreen;
}
return NULL;
}
static void
flush_pending_resize_notifications_cb (void *data,
void *user_data)
{
CoglFramebuffer *framebuffer = data;
if (COGL_IS_ONSCREEN (framebuffer))
{
CoglOnscreen *onscreen = COGL_ONSCREEN (framebuffer);
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
if (xlib_onscreen->pending_resize_notify)
{
_cogl_onscreen_notify_resize (onscreen);
xlib_onscreen->pending_resize_notify = FALSE;
}
}
}
static void
flush_pending_resize_notifications_idle (void *user_data)
{
CoglContext *context = user_data;
CoglRenderer *renderer = context->display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
/* This needs to be disconnected before invoking the callbacks in
* case the callbacks cause it to be queued again */
_cogl_closure_disconnect (egl_renderer->resize_notify_idle);
egl_renderer->resize_notify_idle = NULL;
g_list_foreach (context->framebuffers,
flush_pending_resize_notifications_cb,
NULL);
}
static void
notify_resize (CoglContext *context,
Window drawable,
int width,
int height)
{
CoglRenderer *renderer = context->display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
CoglOnscreen *onscreen = find_onscreen_for_xid (context, drawable);
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglOnscreenEGL *egl_onscreen;
CoglOnscreenXlib *xlib_onscreen;
CoglOnscreen *onscreen;
onscreen = find_onscreen_for_xid (context, drawable);
if (!onscreen)
return;
egl_onscreen = cogl_onscreen_get_winsys (onscreen);
_cogl_framebuffer_winsys_update_size (framebuffer, width, height);
/* We only want to notify that a resize happened when the
* application calls cogl_context_dispatch so instead of immediately
* notifying we queue an idle callback */
if (!egl_renderer->resize_notify_idle)
{
egl_renderer->resize_notify_idle =
_cogl_poll_renderer_add_idle (renderer,
flush_pending_resize_notifications_idle,
context,
NULL);
}
xlib_onscreen = cogl_onscreen_egl_get_platform (egl_onscreen);
xlib_onscreen->pending_resize_notify = TRUE;
cogl_onscreen_xlib_resize (onscreen, width, height);
}
static CoglFilterReturn
@ -204,8 +134,9 @@ event_filter_cb (XEvent *xevent, void *data)
return COGL_FILTER_CONTINUE;
}
static XVisualInfo *
get_visual_info (CoglDisplay *display, EGLConfig egl_config)
XVisualInfo *
cogl_display_xlib_get_visual_info (CoglDisplay *display,
EGLConfig egl_config)
{
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (display->renderer);
@ -415,212 +346,6 @@ _cogl_winsys_egl_context_deinit (CoglContext *context)
context);
}
static gboolean
_cogl_winsys_egl_onscreen_init (CoglOnscreen *onscreen,
EGLConfig egl_config,
GError **error)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglDisplay *display = context->display;
CoglRenderer *renderer = display->renderer;
CoglRendererEGL *egl_renderer = renderer->winsys;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglOnscreenXlib *xlib_onscreen;
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
Window xwin;
EGLSurface egl_surface;
/* FIXME: We need to explicitly Select for ConfigureNotify events.
* We need to document that for windows we create then toolkits
* must be careful not to clear event mask bits that we select.
*/
{
int width;
int height;
CoglXlibTrapState state;
XVisualInfo *xvisinfo;
XSetWindowAttributes xattr;
unsigned long mask;
int xerror;
width = cogl_framebuffer_get_width (framebuffer);
height = cogl_framebuffer_get_height (framebuffer);
_cogl_xlib_renderer_trap_errors (display->renderer, &state);
xvisinfo = get_visual_info (display, egl_config);
if (xvisinfo == NULL)
{
g_set_error (error, COGL_WINSYS_ERROR,
COGL_WINSYS_ERROR_CREATE_ONSCREEN,
"Unable to retrieve the X11 visual of context's "
"fbconfig");
return FALSE;
}
/* window attributes */
xattr.background_pixel =
WhitePixel (xlib_renderer->xdpy,
DefaultScreen (xlib_renderer->xdpy));
xattr.border_pixel = 0;
/* XXX: is this an X resource that we are leaking‽... */
xattr.colormap =
XCreateColormap (xlib_renderer->xdpy,
DefaultRootWindow (xlib_renderer->xdpy),
xvisinfo->visual,
AllocNone);
xattr.event_mask = COGL_ONSCREEN_X11_EVENT_MASK;
mask = CWBorderPixel | CWColormap | CWEventMask;
xwin = XCreateWindow (xlib_renderer->xdpy,
DefaultRootWindow (xlib_renderer->xdpy),
0, 0,
width, height,
0,
xvisinfo->depth,
InputOutput,
xvisinfo->visual,
mask, &xattr);
XFree (xvisinfo);
XSync (xlib_renderer->xdpy, False);
xerror =
_cogl_xlib_renderer_untrap_errors (display->renderer, &state);
if (xerror)
{
char message[1000];
XGetErrorText (xlib_renderer->xdpy, xerror,
message, sizeof (message));
g_set_error (error, COGL_WINSYS_ERROR,
COGL_WINSYS_ERROR_CREATE_ONSCREEN,
"X error while creating Window for CoglOnscreen: %s",
message);
return FALSE;
}
}
xlib_onscreen = g_slice_new (CoglOnscreenXlib);
cogl_onscreen_egl_set_platform (egl_onscreen, xlib_onscreen);
xlib_onscreen->xwin = xwin;
egl_surface =
eglCreateWindowSurface (egl_renderer->edpy,
egl_config,
(EGLNativeWindowType) xlib_onscreen->xwin,
NULL);
cogl_onscreen_egl_set_egl_surface (egl_onscreen,
egl_surface);
return TRUE;
}
static void
_cogl_winsys_egl_onscreen_deinit (CoglOnscreen *onscreen)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglRenderer *renderer = context->display->renderer;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglXlibTrapState old_state;
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
_cogl_xlib_renderer_trap_errors (renderer, &old_state);
if (xlib_onscreen->xwin != None)
{
XDestroyWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
xlib_onscreen->xwin = None;
}
else
xlib_onscreen->xwin = None;
XSync (xlib_renderer->xdpy, False);
if (_cogl_xlib_renderer_untrap_errors (renderer,
&old_state) != Success)
g_warning ("X Error while destroying X window");
g_slice_free (CoglOnscreenXlib, xlib_onscreen);
}
static void
_cogl_winsys_onscreen_set_visibility (CoglOnscreen *onscreen,
gboolean visibility)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglRenderer *renderer = context->display->renderer;
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (renderer);
CoglOnscreenEGL *onscreen_egl = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (onscreen_egl);
if (visibility)
XMapWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
else
XUnmapWindow (xlib_renderer->xdpy, xlib_onscreen->xwin);
}
static void
_cogl_winsys_onscreen_set_resizable (CoglOnscreen *onscreen,
gboolean resizable)
{
CoglFramebuffer *framebuffer = COGL_FRAMEBUFFER (onscreen);
CoglContext *context = cogl_framebuffer_get_context (framebuffer);
CoglXlibRenderer *xlib_renderer =
_cogl_xlib_renderer_get_data (context->display->renderer);
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
XSizeHints *size_hints = XAllocSizeHints ();
if (resizable)
{
/* TODO: Add cogl_onscreen_request_minimum_size () */
size_hints->min_width = 1;
size_hints->min_height = 1;
size_hints->max_width = INT_MAX;
size_hints->max_height = INT_MAX;
}
else
{
int width = cogl_framebuffer_get_width (framebuffer);
int height = cogl_framebuffer_get_height (framebuffer);
size_hints->min_width = width;
size_hints->min_height = height;
size_hints->max_width = width;
size_hints->max_height = height;
}
XSetWMNormalHints (xlib_renderer->xdpy, xlib_onscreen->xwin, size_hints);
XFree (size_hints);
}
static uint32_t
_cogl_winsys_onscreen_x11_get_window_xid (CoglOnscreen *onscreen)
{
CoglOnscreenEGL *egl_onscreen = cogl_onscreen_get_winsys (onscreen);
CoglOnscreenXlib *xlib_onscreen =
cogl_onscreen_egl_get_platform (egl_onscreen);
return xlib_onscreen->xwin;
}
static gboolean
_cogl_winsys_egl_context_created (CoglDisplay *display,
GError **error)
@ -635,7 +360,8 @@ _cogl_winsys_egl_context_created (CoglDisplay *display,
XSetWindowAttributes attrs;
const char *error_message;
xvisinfo = get_visual_info (display, egl_display->egl_config);
xvisinfo = cogl_display_xlib_get_visual_info (display,
egl_display->egl_config);
if (xvisinfo == NULL)
{
error_message = "Unable to find suitable X visual";
@ -841,8 +567,8 @@ _cogl_winsys_egl_vtable =
.cleanup_context = _cogl_winsys_egl_cleanup_context,
.context_init = _cogl_winsys_egl_context_init,
.context_deinit = _cogl_winsys_egl_context_deinit,
.onscreen_init = _cogl_winsys_egl_onscreen_init,
.onscreen_deinit = _cogl_winsys_egl_onscreen_deinit
.onscreen_init = _cogl_winsys_egl_onscreen_xlib_init,
.onscreen_deinit = _cogl_winsys_egl_onscreen_xlib_deinit
};
COGL_EXPORT const CoglWinsysVtable *
@ -867,12 +593,12 @@ _cogl_winsys_egl_xlib_get_vtable (void)
vtable.renderer_disconnect = _cogl_winsys_renderer_disconnect;
vtable.onscreen_set_visibility =
_cogl_winsys_onscreen_set_visibility;
_cogl_winsys_onscreen_xlib_set_visibility;
vtable.onscreen_set_resizable =
_cogl_winsys_onscreen_set_resizable;
_cogl_winsys_onscreen_xlib_set_resizable;
vtable.onscreen_x11_get_window_xid =
_cogl_winsys_onscreen_x11_get_window_xid;
_cogl_winsys_onscreen_xlib_get_window_xid;
#ifdef EGL_KHR_image_pixmap
/* X11 tfp support... */