summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--docs/libs/gst-plugins-gl-libs.types3
-rw-r--r--gst-libs/gst/gl/Makefile.am2
-rw-r--r--gst-libs/gst/gl/android/gstglwindow_android_egl.c6
-rw-r--r--gst-libs/gst/gl/gl.h1
-rw-r--r--gst-libs/gst/gl/gstgl_fwd.h4
-rw-r--r--gst-libs/gst/gl/gstglcontext.c624
-rw-r--r--gst-libs/gst/gl/gstglcontext.h98
-rw-r--r--gst-libs/gst/gl/gstgldisplay.c59
-rw-r--r--gst-libs/gst/gl/gstgldisplay.h12
-rw-r--r--gst-libs/gst/gl/gstglfeature.c16
-rw-r--r--gst-libs/gst/gl/gstglfilter.c10
-rw-r--r--gst-libs/gst/gl/gstglmixer.c10
-rw-r--r--gst-libs/gst/gl/gstglutils.c18
-rw-r--r--gst-libs/gst/gl/gstglwindow.c361
-rw-r--r--gst-libs/gst/gl/gstglwindow.h11
-rw-r--r--gst-libs/gst/gl/wayland/gstglwindow_wayland_egl.c6
-rw-r--r--gst-libs/gst/gl/win32/gstglwindow_win32_egl.c3
-rw-r--r--gst-libs/gst/gl/win32/gstglwindow_win32_wgl.c6
-rw-r--r--gst-libs/gst/gl/x11/gstglwindow_x11_egl.c6
-rw-r--r--gst-libs/gst/gl/x11/gstglwindow_x11_glx.c6
-rw-r--r--gst/gl/gstglimagesink.c35
-rw-r--r--gst/gl/gstgltestsrc.c10
22 files changed, 871 insertions, 436 deletions
diff --git a/docs/libs/gst-plugins-gl-libs.types b/docs/libs/gst-plugins-gl-libs.types
index 42a62f1..ea237d9 100644
--- a/docs/libs/gst-plugins-gl-libs.types
+++ b/docs/libs/gst-plugins-gl-libs.types
@@ -1,5 +1,7 @@
#include "../../config.h"
+#include "gstgl_fwd.h"
#include "gstgldisplay.h"
+#include "gstglcontext.h"
#include "gstglfilter.h"
#include "gstglshader.h"
#include "gstglmixer.h"
@@ -13,6 +15,7 @@
gst_gl_upload_get_type
gst_gl_download_get_type
gst_gl_display_get_type
+gst_gl_context_get_type
gst_gl_filter_get_type
gst_gl_shader_get_type
gst_gl_mixer_get_type
diff --git a/gst-libs/gst/gl/Makefile.am b/gst-libs/gst/gl/Makefile.am
index 9f47797..e9d60b8 100644
--- a/gst-libs/gst/gl/Makefile.am
+++ b/gst-libs/gst/gl/Makefile.am
@@ -8,6 +8,7 @@ noinst_HEADERS =
libgstgl_@GST_API_VERSION@_la_SOURCES = \
gstgldisplay.c \
+ gstglcontext.c \
gstglmemory.c \
gstglbufferpool.c \
gstglfilter.c \
@@ -64,6 +65,7 @@ libgstgl_@GST_API_VERSION@include_HEADERS = \
gstglconfig.h \
gstglwindow.h \
gstgldisplay.h \
+ gstglcontext.h \
gstglmemory.h \
gstglbufferpool.h \
gstgles2.h \
diff --git a/gst-libs/gst/gl/android/gstglwindow_android_egl.c b/gst-libs/gst/gl/android/gstglwindow_android_egl.c
index 1726068..78ab730 100644
--- a/gst-libs/gst/gl/android/gstglwindow_android_egl.c
+++ b/gst-libs/gst/gl/android/gstglwindow_android_egl.c
@@ -28,6 +28,9 @@
#include "config.h"
#endif
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include "gstglwindow_android_egl.h"
#define GST_CAT_DEFAULT gst_gl_window_debug
@@ -307,13 +310,14 @@ static gpointer
gst_gl_window_android_egl_get_proc_address (GstGLWindow * window,
const gchar * name)
{
+ GstGLContext *context = NULL;
GstGLWindowAndroidEGL *window_egl;
gpointer result;
window_egl = GST_GL_WINDOW_ANDROID_EGL (window);
if (!(result = gst_gl_egl_get_proc_address (window_egl->egl, name))) {
- result = gst_gl_window_default_get_proc_address (window, name);
+ result = gst_gl_context_default_get_proc_address (context, name);
}
return result;
diff --git a/gst-libs/gst/gl/gl.h b/gst-libs/gst/gl/gl.h
index 3f3a277..07d9478 100644
--- a/gst-libs/gst/gl/gl.h
+++ b/gst-libs/gst/gl/gl.h
@@ -25,6 +25,7 @@
#include <gst/gl/gstglconfig.h>
#include <gst/gl/gstglapi.h>
#include <gst/gl/gstgldisplay.h>
+#include <gst/gl/gstglcontext.h>
#include <gst/gl/gstglfeature.h>
#include <gst/gl/gstglutils.h>
#include <gst/gl/gstglwindow.h>
diff --git a/gst-libs/gst/gl/gstgl_fwd.h b/gst-libs/gst/gl/gstgl_fwd.h
index b130504..8de50c2 100644
--- a/gst-libs/gst/gl/gstgl_fwd.h
+++ b/gst-libs/gst/gl/gstgl_fwd.h
@@ -31,6 +31,10 @@ typedef struct _GstGLDisplay GstGLDisplay;
typedef struct _GstGLDisplayClass GstGLDisplayClass;
typedef struct _GstGLDisplayPrivate GstGLDisplayPrivate;
+typedef struct _GstGLContext GstGLContext;
+typedef struct _GstGLContextClass GstGLContextClass;
+typedef struct _GstGLContextPrivate GstGLContextPrivate;
+
typedef struct _GstGLWindow GstGLWindow;
typedef struct _GstGLWindowPrivate GstGLWindowPrivate;
typedef struct _GstGLWindowClass GstGLWindowClass;
diff --git a/gst-libs/gst/gl/gstglcontext.c b/gst-libs/gst/gl/gstglcontext.c
new file mode 100644
index 0000000..7bd8754
--- /dev/null
+++ b/gst-libs/gst/gl/gstglcontext.c
@@ -0,0 +1,624 @@
+/*
+ * GStreamer
+ * Copyright (C) 2013 Matthew Waters <ystreet00@gmail.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include <gmodule.h>
+
+#include "gl.h"
+#include "gstglcontext.h"
+
+#define USING_OPENGL(display) (display->gl_api & GST_GL_API_OPENGL)
+#define USING_OPENGL3(display) (display->gl_api & GST_GL_API_OPENGL3)
+#define USING_GLES(display) (display->gl_api & GST_GL_API_GLES)
+#define USING_GLES2(display) (display->gl_api & GST_GL_API_GLES2)
+#define USING_GLES3(display) (display->gl_api & GST_GL_API_GLES3)
+
+#define GST_CAT_DEFAULT gst_gl_context_debug
+GST_DEBUG_CATEGORY (GST_CAT_DEFAULT);
+
+#define gst_gl_context_parent_class parent_class
+G_DEFINE_TYPE (GstGLContext, gst_gl_context, G_TYPE_OBJECT);
+
+#define GST_GL_CONTEXT_GET_PRIVATE(o) \
+ (G_TYPE_INSTANCE_GET_PRIVATE((o), GST_GL_TYPE_CONTEXT, GstGLContextPrivate))
+
+static gpointer gst_gl_context_create_thread (GstGLContext * context);
+static void gst_gl_context_finalize (GObject * object);
+
+struct _GstGLContextPrivate
+{
+ GstGLDisplay *display;
+
+ GThread *gl_thread;
+
+ /* conditions */
+ GMutex render_lock;
+ GCond create_cond;
+ GCond destroy_cond;
+
+ gboolean created;
+ gboolean alive;
+
+ guintptr external_gl_context;
+ GstGLAPI gl_api;
+ GError **error;
+};
+
+GQuark
+gst_gl_context_error_quark (void)
+{
+ return g_quark_from_static_string ("gst-gl-context-error-quark");
+}
+
+static void
+_ensure_window (GstGLContext * context)
+{
+ GstGLWindow *window;
+
+ if (context->window)
+ return;
+
+ window = gst_gl_window_new (context->priv->display);
+
+ gst_gl_context_set_window (context, window);
+}
+
+static void
+gst_gl_context_init (GstGLContext * context)
+{
+ context->priv = GST_GL_CONTEXT_GET_PRIVATE (context);
+
+ g_mutex_init (&context->priv->render_lock);
+
+ g_cond_init (&context->priv->create_cond);
+ g_cond_init (&context->priv->destroy_cond);
+ context->priv->created = FALSE;
+}
+
+static void
+gst_gl_context_class_init (GstGLContextClass * klass)
+{
+ g_type_class_add_private (klass, sizeof (GstGLContextPrivate));
+
+ klass->get_proc_address =
+ GST_DEBUG_FUNCPTR (gst_gl_context_default_get_proc_address);
+
+ G_OBJECT_CLASS (klass)->finalize = gst_gl_context_finalize;
+}
+
+GstGLContext *
+gst_gl_context_new (GstGLDisplay * display)
+{
+ GstGLContext *context = NULL;
+ const gchar *user_choice;
+ static volatile gsize _init = 0;
+
+ if (g_once_init_enter (&_init)) {
+ GST_DEBUG_CATEGORY_INIT (gst_gl_context_debug, "glcontext", 0,
+ "glcontext element");
+ g_once_init_leave (&_init, 1);
+ }
+
+ user_choice = g_getenv ("GST_GL_PLATFORM");
+ GST_INFO ("creating a context, user choice:%s", user_choice);
+#if 0
+#if GST_GL_HAVE_PLATFORM_EGL
+ if (!context && (!user_choice || g_strstr_len (user_choice, 7, "egl")))
+ context = GST_GL_CONTEXT (gst_gl_context_egl_new ());
+#endif
+#if GST_GL_HAVE_PLATFORM_GLX
+ if (!context && (!user_choice || g_strstr_len (user_choice, 3, "glx")))
+ context = GST_GL_CONTEXT (gst_gl_context_glx_new ());
+#endif
+#if GST_GL_HAVE_PLATFORM_WIN32
+ if (!context && (!user_choice || g_strstr_len (user_choice, 5, "win32")))
+ context = GST_GL_CONTEXT (gst_gl_context_win32_new ());
+#endif
+#if GST_GL_HAVE_PLATFORM_COCOA
+ if (!context && (!user_choice || g_strstr_len (user_choice, 5, "cocoa"))) {
+ context = GST_GL_CONTEXT (gst_gl_context_cocoa_new ());
+ }
+#endif
+ if (!context) {
+ /* subclass returned a NULL context */
+ GST_WARNING ("Could not create context. user specified %s",
+ user_choice ? user_choice : "(null)");
+
+ return NULL;
+ }
+#endif
+
+ context = g_object_new (GST_GL_TYPE_CONTEXT, NULL);
+
+ context->priv->display = display;
+
+ return context;
+}
+
+static void
+gst_gl_context_finalize (GObject * object)
+{
+ GstGLContext *context = GST_GL_CONTEXT (object);
+
+ gst_gl_window_set_resize_callback (context->window, NULL, NULL, NULL);
+ gst_gl_window_set_draw_callback (context->window, NULL, NULL, NULL);
+
+ if (context->priv->alive) {
+ GST_INFO ("send quit gl window loop");
+ gst_gl_window_quit (context->window);
+ g_cond_wait (&context->priv->destroy_cond, &context->priv->render_lock);
+ }
+
+ gst_gl_window_set_close_callback (context->window, NULL, NULL, NULL);
+
+ if (context->priv->gl_thread) {
+ gpointer ret = g_thread_join (context->priv->gl_thread);
+ GST_INFO ("gl thread joined");
+ if (ret != NULL)
+ GST_ERROR ("gl thread returned a non-null pointer");
+ context->priv->gl_thread = NULL;
+ }
+
+ gst_object_unref (context->window);
+
+ g_mutex_clear (&context->priv->render_lock);
+
+ g_cond_clear (&context->priv->destroy_cond);
+ g_cond_clear (&context->priv->create_cond);
+
+ G_OBJECT_CLASS (gst_gl_context_parent_class)->finalize (object);
+}
+
+/* FIXME move the relevant window vfuncs into GstGLContext */
+gboolean
+gst_gl_context_activate (GstGLContext * context, gboolean activate)
+{
+ GstGLWindowClass *window_class;
+ gboolean result;
+
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), FALSE);
+ window_class = GST_GL_WINDOW_GET_CLASS (context->window);
+ g_return_val_if_fail (window_class->activate != NULL, FALSE);
+
+ result = window_class->activate (context->window, activate);
+
+ return result;
+}
+
+GstGLAPI
+gst_gl_context_get_gl_api (GstGLContext * context)
+{
+ GstGLWindowClass *window_class;
+
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), GST_GL_API_NONE);
+ window_class = GST_GL_WINDOW_GET_CLASS (context->window);
+ g_return_val_if_fail (window_class->get_gl_api != NULL, GST_GL_API_NONE);
+
+ return window_class->get_gl_api (context->window);
+}
+
+gpointer
+gst_gl_context_get_proc_address (GstGLContext * context, const gchar * name)
+{
+ gpointer ret;
+ GstGLWindowClass *window_class;
+
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), NULL);
+ window_class = GST_GL_WINDOW_GET_CLASS (context->window);
+ g_return_val_if_fail (window_class->get_proc_address != NULL, NULL);
+
+ ret = window_class->get_proc_address (context->window, name);
+
+ return ret;
+}
+
+gpointer
+gst_gl_context_default_get_proc_address (GstGLContext * context,
+ const gchar * name)
+{
+ static GModule *module = NULL;
+ gpointer ret = NULL;
+
+ if (!module)
+ module = g_module_open (NULL, G_MODULE_BIND_LAZY);
+
+ if (module) {
+ if (!g_module_symbol (module, name, &ret))
+ return NULL;
+ }
+
+ return ret;
+}
+
+gboolean
+gst_gl_context_set_window (GstGLContext * context, GstGLWindow * window)
+{
+ /* we can't change the window while we are running */
+ if (context->priv->alive)
+ return FALSE;
+
+ if (window) {
+ if (gst_gl_window_is_running (window))
+ return FALSE;
+
+ g_weak_ref_set (&window->context_ref, context);
+ }
+
+ if (context->window)
+ gst_object_unref (context->window);
+
+ context->window = window ? gst_object_ref (window) : NULL;
+
+ return TRUE;
+}
+
+GstGLWindow *
+gst_gl_context_get_window (GstGLContext * context)
+{
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), NULL);
+
+ _ensure_window (context);
+
+ return gst_object_ref (context->window);
+}
+
+/* Create an opengl context (one context for one GstGLDisplay) */
+gboolean
+gst_gl_context_create (GstGLContext * context,
+ guintptr external_gl_context, GError ** error)
+{
+ gboolean alive = FALSE;
+ GstGLWindowClass *window_class;
+
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), FALSE);
+ window_class = GST_GL_WINDOW_GET_CLASS (context->window);
+ g_return_val_if_fail (window_class->create_context != NULL, FALSE);
+
+ _ensure_window (context);
+
+ g_mutex_lock (&context->priv->render_lock);
+
+ if (window_class->open) {
+ if (!(alive = window_class->open (context->window, error)))
+ goto out;
+ }
+
+ if (!context->priv->created) {
+ context->priv->external_gl_context = external_gl_context;
+ context->priv->error = error;
+
+ context->priv->gl_thread = g_thread_new ("gstglcontext",
+ (GThreadFunc) gst_gl_context_create_thread, context);
+
+ g_cond_wait (&context->priv->create_cond, &context->priv->render_lock);
+
+ context->priv->created = TRUE;
+
+ GST_INFO ("gl thread created");
+ }
+
+ alive = context->priv->alive;
+
+ g_mutex_unlock (&context->priv->render_lock);
+
+out:
+ return alive;
+}
+
+static gboolean
+_create_context_gles2 (GstGLContext * context, gint * gl_major, gint * gl_minor,
+ GError ** error)
+{
+ GstGLDisplay *display;
+ const GstGLFuncs *gl;
+ GLenum gl_err = GL_NO_ERROR;
+
+ display = context->priv->display;
+ gl = display->gl_vtable;
+
+ GST_INFO ("GL_VERSION: %s", gl->GetString (GL_VERSION));
+ GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
+ gl->GetString (GL_SHADING_LANGUAGE_VERSION));
+ GST_INFO ("GL_VENDOR: %s", gl->GetString (GL_VENDOR));
+ GST_INFO ("GL_RENDERER: %s", gl->GetString (GL_RENDERER));
+
+ gl_err = gl->GetError ();
+ if (gl_err != GL_NO_ERROR) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_FAILED,
+ "glGetString error: 0x%x", gl_err);
+ return FALSE;
+ }
+#if GST_GL_HAVE_GLES2
+ if (!GL_ES_VERSION_2_0) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_OLD_LIBS,
+ "OpenGL|ES >= 2.0 is required");
+ return FALSE;
+ }
+#endif
+
+ _gst_gl_feature_check_ext_functions (display, 0, 0,
+ (const gchar *) gl->GetString (GL_EXTENSIONS));
+
+ if (gl_major)
+ *gl_major = 2;
+ if (gl_minor)
+ *gl_minor = 0;
+
+ return TRUE;
+}
+
+gboolean
+_create_context_opengl (GstGLContext * context, gint * gl_major,
+ gint * gl_minor, GError ** error)
+{
+ GstGLDisplay *display;
+ const GstGLFuncs *gl;
+ guint maj, min;
+ GLenum gl_err = GL_NO_ERROR;
+ GString *opengl_version = NULL;
+
+ display = context->priv->display;
+ gl = display->gl_vtable;
+
+ GST_INFO ("GL_VERSION: %s", gl->GetString (GL_VERSION));
+ GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
+ gl->GetString (GL_SHADING_LANGUAGE_VERSION));
+ GST_INFO ("GL_VENDOR: %s", gl->GetString (GL_VENDOR));
+ GST_INFO ("GL_RENDERER: %s", gl->GetString (GL_RENDERER));
+
+ gl_err = gl->GetError ();
+ if (gl_err != GL_NO_ERROR) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_FAILED,
+ "glGetString error: 0x%x", gl_err);
+ return FALSE;
+ }
+ opengl_version =
+ g_string_truncate (g_string_new ((gchar *) gl->GetString (GL_VERSION)),
+ 3);
+
+ sscanf (opengl_version->str, "%d.%d", &maj, &min);
+
+ g_string_free (opengl_version, TRUE);
+
+ /* OpenGL > 1.2.0 */
+ if ((maj < 1) || (maj < 2 && maj >= 1 && min < 2)) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_OLD_LIBS,
+ "OpenGL >= 1.2.0 required, found %u.%u", maj, min);
+ return FALSE;
+ }
+
+ _gst_gl_feature_check_ext_functions (display, maj, min,
+ (const gchar *) gl->GetString (GL_EXTENSIONS));
+
+ if (gl_major)
+ *gl_major = maj;
+ if (gl_minor)
+ *gl_minor = min;
+
+ return TRUE;
+}
+
+GstGLAPI
+_compiled_api (void)
+{
+ GstGLAPI ret = GST_GL_API_NONE;
+
+#if GST_GL_HAVE_OPENGL
+ ret |= GST_GL_API_OPENGL | GST_GL_API_OPENGL3;
+#endif
+#if GST_GL_HAVE_GLES2
+ ret |= GST_GL_API_GLES2;
+#endif
+
+ return ret;
+}
+
+GstGLAPI
+_parse_gl_api (const gchar * apis_s)
+{
+ GstGLAPI ret = GST_GL_API_NONE;
+ gchar *apis = (gchar *) apis_s;
+
+ while (apis) {
+ if (apis[0] == '\0') {
+ break;
+ } else if (apis[0] == ' ' || apis[0] == ',') {
+ apis = &apis[1];
+ } else if (g_strstr_len (apis, 7, "opengl3")) {
+ ret |= GST_GL_API_OPENGL3;
+ apis = &apis[7];
+ } else if (g_strstr_len (apis, 6, "opengl")) {
+ ret |= GST_GL_API_OPENGL;
+ apis = &apis[6];
+ } else if (g_strstr_len (apis, 5, "gles1")) {
+ ret |= GST_GL_API_GLES;
+ apis = &apis[5];
+ } else if (g_strstr_len (apis, 5, "gles2")) {
+ ret |= GST_GL_API_GLES2;
+ apis = &apis[5];
+ } else if (g_strstr_len (apis, 5, "gles3")) {
+ ret |= GST_GL_API_GLES3;
+ apis = &apis[5];
+ } else {
+ break;
+ }
+ }
+
+ if (ret == GST_GL_API_NONE)
+ ret = GST_GL_API_ANY;
+
+ return ret;
+}
+
+//gboolean
+//gst_gl_context_create (GstGLContext * context, guintptr external_gl_context, GError ** error)
+static gpointer
+gst_gl_context_create_thread (GstGLContext * context)
+{
+ GstGLWindowClass *window_class;
+ GstGLDisplay *display;
+ GstGLFuncs *gl;
+ gint gl_major = 0;
+ gboolean ret = FALSE;
+ GstGLAPI compiled_api, user_api;
+ gchar *api_string;
+ gchar *compiled_api_s;
+ gchar *user_api_string;
+ const gchar *user_choice;
+ GError **error;
+ guintptr external_gl_context;
+
+ error = context->priv->error;
+ external_gl_context = context->priv->external_gl_context;
+
+ window_class = GST_GL_WINDOW_GET_CLASS (context->window);
+
+ if (window_class->open) {
+ if (!window_class->open (context->window, error))
+ goto failure;
+ }
+
+ display = context->priv->display;
+ gl = display->gl_vtable;
+ compiled_api = _compiled_api ();
+
+ user_choice = g_getenv ("GST_GL_API");
+
+ user_api = _parse_gl_api (user_choice);
+ user_api_string = gst_gl_api_string (user_api);
+
+ compiled_api_s = gst_gl_api_string (compiled_api);
+
+ if ((user_api & compiled_api) == GST_GL_API_NONE) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_WRONG_API,
+ "Cannot create context with the user requested api (%s). "
+ "We have support for (%s)", user_api_string, compiled_api_s);
+ g_free (user_api_string);
+ g_free (compiled_api_s);
+ goto failure;
+ }
+
+ GST_INFO ("Attempting to create opengl context. user chosen api(s) (%s), "
+ "compiled api support (%s)", user_api_string, compiled_api_s);
+
+ if (!window_class->create_context (context->window, compiled_api & user_api,
+ external_gl_context, error)) {
+ g_assert (error == NULL || *error != NULL);
+ g_free (compiled_api_s);
+ g_free (user_api_string);
+ goto failure;
+ }
+ GST_INFO ("context created context");
+
+ display->gl_api = gst_gl_context_get_gl_api (context);
+ g_assert (display->gl_api != GST_GL_API_NONE
+ && display->gl_api != GST_GL_API_ANY);
+
+ api_string = gst_gl_api_string (display->gl_api);
+ GST_INFO ("available GL APIs: %s", api_string);
+
+ if (((compiled_api & display->gl_api) & user_api) == GST_GL_API_NONE) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_WRONG_API,
+ "failed to create context, context "
+ "could not provide correct api. user (%s), compiled (%s), context (%s)",
+ user_api_string, compiled_api_s, api_string);
+ g_free (api_string);
+ g_free (compiled_api_s);
+ g_free (user_api_string);
+ goto failure;
+ }
+
+ g_free (api_string);
+ g_free (compiled_api_s);
+ g_free (user_api_string);
+
+ gl->GetError = gst_gl_context_get_proc_address (context, "glGetError");
+ gl->GetString = gst_gl_context_get_proc_address (context, "glGetString");
+
+ if (!gl->GetError || !gl->GetString) {
+ g_set_error (error, GST_GL_CONTEXT_ERROR, GST_GL_CONTEXT_ERROR_FAILED,
+ "could not GetProcAddress core opengl functions");
+ goto failure;
+ }
+
+ /* gl api specific code */
+ if (!ret && USING_OPENGL (display))
+ ret = _create_context_opengl (context, &gl_major, NULL, error);
+ if (!ret && USING_GLES2 (display))
+ ret = _create_context_gles2 (context, &gl_major, NULL, error);
+
+ if (!ret)
+ goto failure;
+
+ context->priv->alive = TRUE;
+
+ g_cond_signal (&context->priv->create_cond);
+ g_mutex_unlock (&context->priv->render_lock);
+
+ gst_gl_window_run (context->window);
+
+ GST_INFO ("loop exited\n");
+
+ g_mutex_lock (&context->priv->render_lock);
+
+ context->priv->alive = FALSE;
+
+ if (window_class->close) {
+ window_class->close (context->window);
+ }
+
+ context_class->activate (context, FALSE);
+
+ context_class->destroy_context (context);
+
+ if (context->window->close)
+ context->window->close (context->window->close_data);
+
+ g_cond_signal (&context->priv->destroy_cond);
+
+ g_mutex_unlock (&context->priv->render_lock);
+
+ return NULL;
+
+failure:
+ {
+ g_cond_signal (&context->priv->create_cond);
+ g_mutex_unlock (&context->priv->render_lock);
+ return NULL;
+ }
+}
+
+guintptr
+gst_gl_context_get_gl_context (GstGLContext * context)
+{
+ GstGLContextClass *context_class;
+ guintptr result;
+
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (context), 0);
+ context_class = GST_GL_CONTEXT_GET_CLASS (context);
+ g_return_val_if_fail (context_class->get_gl_context != NULL, 0);
+
+ result = context_class->get_gl_context (context);
+
+ return result;
+}
diff --git a/gst-libs/gst/gl/gstglcontext.h b/gst-libs/gst/gl/gstglcontext.h
new file mode 100644
index 0000000..10c30a7
--- /dev/null
+++ b/gst-libs/gst/gl/gstglcontext.h
@@ -0,0 +1,98 @@
+/*
+ * GStreamer
+ * Copyright (C) 2012 Matthew Waters <ystreet00@gmail.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef __GST_GL_CONTEXT_H__
+#define __GST_GL_CONTEXT_H__
+
+#include <gst/gst.h>
+
+#include <gst/gl/gstgl_fwd.h>
+
+G_BEGIN_DECLS
+
+#define GST_GL_TYPE_CONTEXT (gst_gl_context_get_type())
+#define GST_GL_CONTEXT(o) (G_TYPE_CHECK_INSTANCE_CAST((o), GST_GL_TYPE_CONTEXT, GstGLContext))
+#define GST_GL_CONTEXT_CLASS(k) (G_TYPE_CHECK_CLASS((k), GST_GL_TYPE_CONTEXT, GstGLContextClass))
+#define GST_GL_IS_CONTEXT(o) (G_TYPE_CHECK_INSTANCE_TYPE((o), GST_GL_TYPE_CONTEXT))
+#define GST_GL_IS_CONTEXT_CLASS(k) (G_TYPE_CHECK_CLASS_TYPE((k), GST_GL_TYPE_CONTEXT))
+#define GST_GL_CONTEXT_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS((o), GST_GL_TYPE_CONTEXT, GstGLContextClass))
+GType gst_gl_context_get_type (void);
+
+#define GST_GL_CONTEXT_ERROR (gst_gl_context_error_quark ())
+GQuark gst_gl_window_error_quark (void);
+
+typedef enum
+{
+ GST_GL_CONTEXT_ERROR_FAILED,
+ GST_GL_CONTEXT_ERROR_WRONG_CONFIG,
+ GST_GL_CONTEXT_ERROR_WRONG_API,
+ GST_GL_CONTEXT_ERROR_OLD_LIBS,
+ GST_GL_CONTEXT_ERROR_CREATE_CONTEXT,
+ GST_GL_CONTEXT_ERROR_RESOURCE_UNAVAILABLE,
+} GstGLContextError;
+
+struct _GstGLContext {
+ /*< private >*/
+ GObject parent;
+
+ /*< public >*/
+ GstGLWindow *window;
+
+ /*< private >*/
+ gpointer _reserved[GST_PADDING];
+
+ GstGLContextPrivate *priv;
+};
+
+struct _GstGLContextClass {
+ /*< private >*/
+ GObjectClass parent_class;
+
+ guintptr (*get_gl_context) (GstGLContext *context);
+ GstGLAPI (*get_gl_api) (GstGLContext *context);
+ gpointer (*get_proc_address) (GstGLContext *context, const gchar *name);
+ gboolean (*activate) (GstGLContext *context, gboolean activate);
+ gboolean (*create_context) (GstGLContext *context, GstGLAPI gl_api,
+ guintptr external_gl_context, GError ** error);
+
+ /*< private >*/
+ gpointer _reserved[GST_PADDING];
+};
+
+/* methods */
+
+GstGLContext * gst_gl_context_new (GstGLDisplay *display);
+
+gboolean gst_gl_context_activate (GstGLContext *context, gboolean activate);
+
+gpointer gst_gl_context_get_proc_address (GstGLContext *context, const gchar *name);
+GstGLPlatform gst_gl_context_get_platform (GstGLContext *context);
+GstGLAPI gst_gl_context_get_gl_api (GstGLContext *context);
+
+gboolean gst_gl_context_create (GstGLContext *context, guintptr external_gl_context, GError ** error);
+
+gpointer gst_gl_context_default_get_proc_address (GstGLContext *context, const gchar *name);
+
+gboolean gst_gl_context_set_window (GstGLContext *context, GstGLWindow *window);
+GstGLWindow * gst_gl_context_get_window (GstGLContext *context);
+
+G_END_DECLS
+
+#endif /* __GST_GL_CONTEXT_H__ */
diff --git a/gst-libs/gst/gl/gstgldisplay.c b/gst-libs/gst/gl/gstgldisplay.c
index 2dd1540..ed0e886 100644
--- a/gst-libs/gst/gl/gstgldisplay.c
+++ b/gst-libs/gst/gl/gstgldisplay.c
@@ -81,14 +81,21 @@ gst_gl_display_finalize (GObject * object)
display->gl_vtable = NULL;
}
- if (display->window) {
- gst_object_unref (display->window);
- display->window = NULL;
+ if (display->context) {
+ gst_object_unref (display->context);
+ display->context = NULL;
}
G_OBJECT_CLASS (gst_gl_display_parent_class)->finalize (object);
}
+GstGLDisplay *
+gst_gl_display_new (void)
+{
+ return g_object_new (GST_TYPE_GL_DISPLAY, NULL);
+}
+
+#if 1
typedef struct
{
GstGLDisplay *display;
@@ -104,37 +111,36 @@ _gst_gl_display_thread_run_generic (RunGenericData * data)
data->func (data->display, data->data);
}
-GstGLDisplay *
-gst_gl_display_new (void)
-{
- return g_object_new (GST_TYPE_GL_DISPLAY, NULL);
-}
-
void
gst_gl_display_thread_add (GstGLDisplay * display,
GstGLDisplayThreadFunc func, gpointer data)
{
+ GstGLWindow *window;
RunGenericData rdata;
g_return_if_fail (GST_IS_GL_DISPLAY (display));
- g_return_if_fail (GST_GL_IS_WINDOW (display->window));
+ g_return_if_fail (GST_GL_IS_CONTEXT (display->context));
g_return_if_fail (func != NULL);
rdata.display = display;
rdata.data = data;
rdata.func = func;
- gst_gl_window_send_message (display->window,
+ window = gst_gl_context_get_window (display->context);
+
+ gst_gl_window_send_message (window,
GST_GL_WINDOW_CB (_gst_gl_display_thread_run_generic), &rdata);
+
+ gst_object_unref (window);
}
GstGLAPI
gst_gl_display_get_gl_api (GstGLDisplay * display)
{
g_return_val_if_fail (GST_IS_GL_DISPLAY (display), GST_GL_API_NONE);
- g_return_val_if_fail (GST_GL_IS_WINDOW (display->window), GST_GL_API_NONE);
+ g_return_val_if_fail (GST_GL_IS_CONTEXT (display->context), GST_GL_API_NONE);
- return gst_gl_window_get_gl_api (display->window);
+ return gst_gl_context_get_gl_api (display->context);
}
gpointer
@@ -144,45 +150,46 @@ gst_gl_display_get_gl_vtable (GstGLDisplay * display)
return display->gl_vtable;
}
+#endif
void
-gst_gl_display_set_window (GstGLDisplay * display, GstGLWindow * window)
+gst_gl_display_set_context (GstGLDisplay * display, GstGLContext * context)
{
g_return_if_fail (GST_IS_GL_DISPLAY (display));
- g_return_if_fail (GST_GL_IS_WINDOW (window));
+ g_return_if_fail (GST_GL_IS_CONTEXT (context));
gst_gl_display_lock (display);
- if (display->window)
- gst_object_unref (display->window);
+ if (display->context)
+ gst_object_unref (display->context);
- display->window = gst_object_ref (window);
+ display->context = gst_object_ref (context);
gst_gl_display_unlock (display);
}
-GstGLWindow *
-gst_gl_display_get_window (GstGLDisplay * display)
+GstGLContext *
+gst_gl_display_get_context (GstGLDisplay * display)
{
- GstGLWindow *window;
+ GstGLContext *context;
g_return_val_if_fail (GST_IS_GL_DISPLAY (display), NULL);
gst_gl_display_lock (display);
- window = display->window ? gst_object_ref (display->window) : NULL;
+ context = display->context ? gst_object_ref (display->context) : NULL;
gst_gl_display_unlock (display);
- return window;
+ return context;
}
-GstGLWindow *
-gst_gl_display_get_window_unlocked (GstGLDisplay * display)
+GstGLContext *
+gst_gl_display_get_context_unlocked (GstGLDisplay * display)
{
g_return_val_if_fail (GST_IS_GL_DISPLAY (display), NULL);
- return display->window ? gst_object_ref (display->window) : NULL;
+ return display->context ? gst_object_ref (display->context) : NULL;
}
void
diff --git a/gst-libs/gst/gl/gstgldisplay.h b/gst-libs/gst/gl/gstgldisplay.h
index 9cbb21a..a430a32 100644
--- a/gst-libs/gst/gl/gstgldisplay.h
+++ b/gst-libs/gst/gl/gstgldisplay.h
@@ -57,7 +57,7 @@ struct _GstGLDisplay
GstObject object;
/* <private> */
- GstGLWindow *window;
+ GstGLContext *context;
GstGLAPI gl_api;
GstGLFuncs *gl_vtable;
@@ -75,11 +75,11 @@ GstGLDisplay *gst_gl_display_new (void);
#define gst_gl_display_lock(display) GST_OBJECT_LOCK (display)
#define gst_gl_display_unlock(display) GST_OBJECT_UNLOCK (display)
-GstGLAPI gst_gl_display_get_gl_api (GstGLDisplay * display);
-gpointer gst_gl_display_get_gl_vtable (GstGLDisplay * display);
-void gst_gl_display_set_window (GstGLDisplay * display, GstGLWindow * window);
-GstGLWindow * gst_gl_display_get_window (GstGLDisplay * display);
-GstGLWindow * gst_gl_display_get_window_unlocked (GstGLDisplay * display);
+GstGLAPI gst_gl_display_get_gl_api (GstGLDisplay * display);
+gpointer gst_gl_display_get_gl_vtable (GstGLDisplay * display);
+void gst_gl_display_set_context (GstGLDisplay * display, GstGLContext * context);
+GstGLContext * gst_gl_display_get_context (GstGLDisplay * display);
+GstGLContext * gst_gl_display_get_context_unlocked (GstGLDisplay * display);
void gst_gl_display_thread_add (GstGLDisplay * display,
GstGLDisplayThreadFunc func, gpointer data);
diff --git a/gst-libs/gst/gl/gstglfeature.c b/gst-libs/gst/gl/gstglfeature.c
index f599e48..df6f0fd 100644
--- a/gst-libs/gst/gl/gstglfeature.c
+++ b/gst-libs/gst/gl/gstglfeature.c
@@ -149,7 +149,7 @@ _gst_gl_feature_check (GstGLDisplay * display,
const char *suffix = NULL;
int func_num;
GstGLFuncs *gst_gl = display->gl_vtable;
- GstGLWindow *window = NULL;
+ GstGLContext *context = NULL;
/* First check whether the functions should be directly provided by
GL */
@@ -172,8 +172,8 @@ _gst_gl_feature_check (GstGLDisplay * display,
if (suffix == NULL)
goto error;
- window = gst_gl_display_get_window (display);
- g_assert (window);
+ context = gst_gl_display_get_context (display);
+ g_assert (context);
/* Try to get all of the entry points */
for (func_num = 0; data->functions[func_num].name; func_num++) {
@@ -186,7 +186,7 @@ _gst_gl_feature_check (GstGLDisplay * display,
suffix, NULL);
GST_TRACE ("%s should %sbe in core", full_function_name,
in_core ? "" : "not ");
- func = gst_gl_window_get_proc_address (window, full_function_name);
+ func = gst_gl_context_get_proc_address (context, full_function_name);
if (func == NULL && in_core) {
GST_TRACE ("%s was not found in core, trying the extension version",
@@ -198,7 +198,7 @@ _gst_gl_feature_check (GstGLDisplay * display,
g_free (full_function_name);
full_function_name = g_strconcat ("gl", data->functions[func_num].name,
suffix, NULL);
- func = gst_gl_window_get_proc_address (window, full_function_name);
+ func = gst_gl_context_get_proc_address (context, full_function_name);
}
}
@@ -213,7 +213,7 @@ _gst_gl_feature_check (GstGLDisplay * display,
}
g_free (full_function_name);
- gst_object_unref (window);
+ gst_object_unref (context);
return TRUE;
@@ -232,8 +232,8 @@ error:
g_free (full_function_name);
}
- if (window)
- gst_object_unref (window);
+ if (context)
+ gst_object_unref (context);
return FALSE;
}
diff --git a/gst-libs/gst/gl/gstglfilter.c b/gst-libs/gst/gl/gstglfilter.c
index b6743dc..d93903f 100644
--- a/gst-libs/gst/gl/gstglfilter.c
+++ b/gst-libs/gst/gl/gstglfilter.c
@@ -256,16 +256,16 @@ gst_gl_filter_start (GstBaseTransform * bt)
filter->display =
gst_object_ref (GST_GL_DISPLAY (g_value_get_pointer (id_value)));
else {
- GstGLWindow *window;
+ GstGLContext *context;
GError *error = NULL;
GST_INFO ("Creating GstGLDisplay");
filter->display = gst_gl_display_new ();
- window = gst_gl_window_new (filter->display);
- gst_gl_display_set_window (filter->display, window);
- gst_object_unref (window);
+ context = gst_gl_context_new (filter->display);
+ gst_gl_display_set_context (filter->display, context);
+ gst_object_unref (context);
- if (!gst_gl_window_create_context (window, 0, &error)) {
+ if (!gst_gl_context_create (context, 0, &error)) {
GST_ELEMENT_ERROR (filter, RESOURCE, NOT_FOUND,
("%s", error->message), (NULL));
return FALSE;
diff --git a/gst-libs/gst/gl/gstglmixer.c b/gst-libs/gst/gl/gstglmixer.c
index 748e5a8..53a3c2c 100644
--- a/gst-libs/gst/gl/gstglmixer.c
+++ b/gst-libs/gst/gl/gstglmixer.c
@@ -935,16 +935,16 @@ gst_gl_mixer_activate (GstGLMixer * mix, gboolean activate)
mix->display =
gst_object_ref (GST_GL_DISPLAY (g_value_get_pointer (id_value)));
else {
- GstGLWindow *window;
+ GstGLContext *context;
GError *error = NULL;
GST_INFO ("Creating GstGLDisplay");
mix->display = gst_gl_display_new ();
- window = gst_gl_window_new (mix->display);
- gst_gl_display_set_window (mix->display, window);
- gst_object_unref (window);
+ context = gst_gl_context_new (mix->display);
+ gst_gl_display_set_context (mix->display, context);
+ gst_object_unref (context);
- if (!gst_gl_window_create_context (window, 0, &error)) {
+ if (!gst_gl_context_create (context, 0, &error)) {
GST_ELEMENT_ERROR (mix, RESOURCE, NOT_FOUND,
("%s", error->message), (NULL));
return FALSE;
diff --git a/gst-libs/gst/gl/gstglutils.c b/gst-libs/gst/gl/gstglutils.c
index 02bfb7d..4039682 100644
--- a/gst-libs/gst/gl/gstglutils.c
+++ b/gst-libs/gst/gl/gstglutils.c
@@ -141,32 +141,34 @@ gst_gl_display_check_framebuffer_status (GstGLDisplay * display)
void
gst_gl_display_activate_gl_context (GstGLDisplay * display, gboolean activate)
{
- GstGLWindow *window;
+ GstGLContext *context;
g_return_if_fail (GST_IS_GL_DISPLAY (display));
if (!activate)
gst_gl_display_lock (display);
- window = gst_gl_display_get_window_unlocked (display);
+ context = gst_gl_display_get_context_unlocked (display);
- gst_gl_window_activate (window, activate);
+ gst_gl_context_activate (context, activate);
if (activate)
gst_gl_display_unlock (display);
- gst_object_unref (window);
+ gst_object_unref (context);
}
void
gst_gl_display_gen_texture (GstGLDisplay * display, GLuint * pTexture,
GstVideoFormat v_format, GLint width, GLint height)
{
+ GstGLContext *context;
GstGLWindow *window;
gst_gl_display_lock (display);
- window = gst_gl_display_get_window_unlocked (display);
+ context = gst_gl_display_get_context_unlocked (display);
+ window = gst_gl_context_get_window (context);
if (gst_gl_window_is_running (window)) {
gen_texture_width = width;
@@ -178,6 +180,7 @@ gst_gl_display_gen_texture (GstGLDisplay * display, GLuint * pTexture,
} else
*pTexture = 0;
+ gst_object_unref (context);
gst_object_unref (window);
gst_gl_display_unlock (display);
@@ -186,17 +189,20 @@ gst_gl_display_gen_texture (GstGLDisplay * display, GLuint * pTexture,
void
gst_gl_display_del_texture (GstGLDisplay * display, GLuint * pTexture)
{
+ GstGLContext *context;
GstGLWindow *window;
gst_gl_display_lock (display);
- window = gst_gl_display_get_window_unlocked (display);
+ context = gst_gl_display_get_context_unlocked (display);
+ window = gst_gl_context_get_window (context);
if (gst_gl_window_is_running (window) && *pTexture) {
del_texture = pTexture;
gst_gl_window_send_message (window,
GST_GL_WINDOW_CB (gst_gl_display_del_texture_window_cb), display);
}
+ gst_object_unref (context);
gst_object_unref (window);
gst_gl_display_unlock (display);
diff --git a/gst-libs/gst/gl/gstglwindow.c b/gst-libs/gst/gl/gstglwindow.c
index fe28edb..8349c43 100644
--- a/gst-libs/gst/gl/gstglwindow.c
+++ b/gst-libs/gst/gl/gstglwindow.c
@@ -78,7 +78,6 @@ struct _GstGLWindowPrivate
GError **error;
};
-static gpointer _gst_gl_window_thread_create_context (GstGLWindow * window);
static void gst_gl_window_finalize (GObject * object);
GQuark
@@ -99,6 +98,8 @@ gst_gl_window_init (GstGLWindow * window)
g_cond_init (&window->priv->cond_create_context);
g_cond_init (&window->priv->cond_destroy_context);
window->priv->context_created = FALSE;
+
+ g_weak_ref_init (&window->context_ref, NULL);
}
static void
@@ -106,9 +107,6 @@ gst_gl_window_class_init (GstGLWindowClass * klass)
{
g_type_class_add_private (klass, sizeof (GstGLWindowPrivate));
- klass->get_proc_address =
- GST_DEBUG_FUNCPTR (gst_gl_window_default_get_proc_address);
-
G_OBJECT_CLASS (klass)->finalize = gst_gl_window_finalize;
}
@@ -167,28 +165,7 @@ gst_gl_window_finalize (GObject * object)
{
GstGLWindow *window = GST_GL_WINDOW (object);
- gst_gl_window_set_resize_callback (window, NULL, NULL, NULL);
- gst_gl_window_set_draw_callback (window, NULL, NULL, NULL);
-
- if (window->priv->alive) {
- GST_INFO ("send quit gl window loop");
- gst_gl_window_quit (window);
- }
-
- gst_gl_window_set_close_callback (window, NULL, NULL, NULL);
-
- if (window->priv->gl_thread) {
- gpointer ret = g_thread_join (window->priv->gl_thread);
- GST_INFO ("gl thread joined");
- if (ret != NULL)
- GST_ERROR ("gl thread returned a non-null pointer");
- window->priv->gl_thread = NULL;
- }
-
- g_mutex_clear (&window->priv->render_lock);
-
- g_cond_clear (&window->priv->cond_destroy_context);
- g_cond_clear (&window->priv->cond_create_context);
+ g_weak_ref_clear (&window->context_ref);
G_OBJECT_CLASS (gst_gl_window_parent_class)->finalize (object);
}
@@ -278,6 +255,7 @@ gst_gl_window_run (GstGLWindow * window)
g_return_if_fail (window_class->run != NULL);
GST_GL_WINDOW_LOCK (window);
+ window->priv->alive = TRUE;
window_class->run (window);
GST_GL_WINDOW_UNLOCK (window);
}
@@ -301,7 +279,6 @@ gst_gl_window_quit (GstGLWindow * window)
GST_GL_WINDOW_UNLOCK (window);
- g_cond_wait (&window->priv->cond_destroy_context, &window->priv->render_lock);
GST_INFO ("quit received from gl window");
}
@@ -423,338 +400,16 @@ gst_gl_window_get_proc_address (GstGLWindow * window, const gchar * name)
return ret;
}
-gpointer
-gst_gl_window_default_get_proc_address (GstGLWindow * window,
- const gchar * name)
-{
- static GModule *module = NULL;
- gpointer ret = NULL;
-
- if (!module)
- module = g_module_open (NULL, G_MODULE_BIND_LAZY);
-
- if (module) {
- if (!g_module_symbol (module, name, &ret))
- return NULL;
- }
-
- return ret;
-}
-
-/* Create an opengl context (one context for one GstGLDisplay) */
-gboolean
-gst_gl_window_create_context (GstGLWindow * window,
- guintptr external_gl_context, GError ** error)
-{
- gboolean alive = FALSE;
- GstGLWindowClass *window_class;
-
- g_return_val_if_fail (GST_GL_IS_WINDOW (window), FALSE);
- window_class = GST_GL_WINDOW_GET_CLASS (window);
- g_return_val_if_fail (window_class->create_context != NULL, FALSE);
-
- g_mutex_lock (&window->priv->render_lock);
-
- if (window_class->open) {
- if (!(alive = window_class->open (window, error)))
- goto out;
- }
-
- if (!window->priv->context_created) {
- window->priv->external_gl_context = external_gl_context;
- window->priv->error = error;
-
- window->priv->gl_thread = g_thread_new ("gstglcontext",
- (GThreadFunc) _gst_gl_window_thread_create_context, window);
-
- g_cond_wait (&window->priv->cond_create_context,
- &window->priv->render_lock);
-
- window->priv->context_created = TRUE;
-
- GST_INFO ("gl thread created");
- }
-
- alive = window->priv->alive;
-
- g_mutex_unlock (&window->priv->render_lock);
-
-out:
- return alive;
-}
-
gboolean
gst_gl_window_is_running (GstGLWindow * window)
{
return window->priv->alive;
}
-static gboolean
-_create_context_gles2 (GstGLWindow * window, gint * gl_major, gint * gl_minor,
- GError ** error)
-{
- GstGLDisplay *display;
- const GstGLFuncs *gl;
- GLenum gl_err = GL_NO_ERROR;
-
- display = window->priv->display;
- gl = display->gl_vtable;
-
- GST_INFO ("GL_VERSION: %s", gl->GetString (GL_VERSION));
- GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
- gl->GetString (GL_SHADING_LANGUAGE_VERSION));
- GST_INFO ("GL_VENDOR: %s", gl->GetString (GL_VENDOR));
- GST_INFO ("GL_RENDERER: %s", gl->GetString (GL_RENDERER));
-
- gl_err = gl->GetError ();
- if (gl_err != GL_NO_ERROR) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_FAILED,
- "glGetString error: 0x%x", gl_err);
- return FALSE;
- }
-#if GST_GL_HAVE_GLES2
- if (!GL_ES_VERSION_2_0) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_OLD_LIBS,
- "OpenGL|ES >= 2.0 is required");
- return FALSE;
- }
-#endif
-
- _gst_gl_feature_check_ext_functions (display, 0, 0,
- (const gchar *) gl->GetString (GL_EXTENSIONS));
-
- if (gl_major)
- *gl_major = 2;
- if (gl_minor)
- *gl_minor = 0;
-
- return TRUE;
-}
-
-gboolean
-_create_context_opengl (GstGLWindow * window, gint * gl_major, gint * gl_minor,
- GError ** error)
-{
- GstGLDisplay *display;
- const GstGLFuncs *gl;
- guint maj, min;
- GLenum gl_err = GL_NO_ERROR;
- GString *opengl_version = NULL;
-
- display = window->priv->display;
- gl = display->gl_vtable;
-
- GST_INFO ("GL_VERSION: %s", gl->GetString (GL_VERSION));
- GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
- gl->GetString (GL_SHADING_LANGUAGE_VERSION));
- GST_INFO ("GL_VENDOR: %s", gl->GetString (GL_VENDOR));
- GST_INFO ("GL_RENDERER: %s", gl->GetString (GL_RENDERER));
-
- gl_err = gl->GetError ();
- if (gl_err != GL_NO_ERROR) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_FAILED,
- "glGetString error: 0x%x", gl_err);
- return FALSE;
- }
- opengl_version =
- g_string_truncate (g_string_new ((gchar *) gl->GetString (GL_VERSION)),
- 3);
-
- sscanf (opengl_version->str, "%d.%d", &maj, &min);
-
- g_string_free (opengl_version, TRUE);
-
- /* OpenGL > 1.2.0 */
- if ((maj < 1) || (maj < 2 && maj >= 1 && min < 2)) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_OLD_LIBS,
- "OpenGL >= 1.2.0 required, found %u.%u", maj, min);
- return FALSE;
- }
-
- _gst_gl_feature_check_ext_functions (display, maj, min,
- (const gchar *) gl->GetString (GL_EXTENSIONS));
-
- if (gl_major)
- *gl_major = maj;
- if (gl_minor)
- *gl_minor = min;
-
- return TRUE;
-}
-
-GstGLAPI
-_compiled_api (void)
-{
- GstGLAPI ret = GST_GL_API_NONE;
-
-#if GST_GL_HAVE_OPENGL
- ret |= GST_GL_API_OPENGL | GST_GL_API_OPENGL3;
-#endif
-#if GST_GL_HAVE_GLES2
- ret |= GST_GL_API_GLES2;
-#endif
-
- return ret;
-}
-
-GstGLAPI
-_parse_gl_api (const gchar * apis_s)
-{
- GstGLAPI ret = GST_GL_API_NONE;
- gchar *apis = (gchar *) apis_s;
-
- while (apis) {
- if (apis[0] == '\0') {
- break;
- } else if (apis[0] == ' ' || apis[0] == ',') {
- apis = &apis[1];
- } else if (g_strstr_len (apis, 7, "opengl3")) {
- ret |= GST_GL_API_OPENGL3;
- apis = &apis[7];
- } else if (g_strstr_len (apis, 6, "opengl")) {
- ret |= GST_GL_API_OPENGL;
- apis = &apis[6];
- } else if (g_strstr_len (apis, 5, "gles1")) {
- ret |= GST_GL_API_GLES;
- apis = &apis[5];
- } else if (g_strstr_len (apis, 5, "gles2")) {
- ret |= GST_GL_API_GLES2;
- apis = &apis[5];
- } else if (g_strstr_len (apis, 5, "gles3")) {
- ret |= GST_GL_API_GLES3;
- apis = &apis[5];
- } else {
- break;
- }
- }
-
- if (ret == GST_GL_API_NONE)
- ret = GST_GL_API_ANY;
-
- return ret;
-}
-
-static gpointer
-_gst_gl_window_thread_create_context (GstGLWindow * window)
+GstGLContext *
+gst_gl_window_get_context (GstGLWindow * window)
{
- GstGLWindowClass *window_class;
- GstGLDisplay *display;
- GstGLFuncs *gl;
- gint gl_major = 0;
- gboolean ret = FALSE;
- GstGLAPI compiled_api, user_api;
- gchar *api_string;
- gchar *compiled_api_s;
- gchar *user_api_string;
- const gchar *user_choice;
- GError **error;
-
- window_class = GST_GL_WINDOW_GET_CLASS (window);
- error = window->priv->error;
- display = window->priv->display;
-
- g_mutex_lock (&window->priv->render_lock);
-
- gl = display->gl_vtable;
- compiled_api = _compiled_api ();
-
- user_choice = g_getenv ("GST_GL_API");
-
- user_api = _parse_gl_api (user_choice);
- user_api_string = gst_gl_api_string (user_api);
-
- compiled_api_s = gst_gl_api_string (compiled_api);
-
- if ((user_api & compiled_api) == GST_GL_API_NONE) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_WRONG_API,
- "Cannot create context with the user requested api (%s). "
- "We have support for (%s)", user_api_string, compiled_api_s);
- g_free (user_api_string);
- g_free (compiled_api_s);
- goto failure;
- }
-
- GST_INFO ("Attempting to create opengl context. user chosen api(s) (%s), "
- "compiled api support (%s)", user_api_string, compiled_api_s);
-
- if (!window_class->create_context (window, compiled_api & user_api,
- window->priv->external_gl_context, error)) {
- g_assert (error == NULL || *error != NULL);
- g_free (compiled_api_s);
- g_free (user_api_string);
- goto failure;
- }
- GST_INFO ("window created context");
-
- display->gl_api = gst_gl_window_get_gl_api (window);
- g_assert (display->gl_api != GST_GL_API_NONE
- && display->gl_api != GST_GL_API_ANY);
-
- api_string = gst_gl_api_string (display->gl_api);
- GST_INFO ("available GL APIs: %s", api_string);
-
- if (((compiled_api & display->gl_api) & user_api) == GST_GL_API_NONE) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_WRONG_API,
- "failed to create context, window "
- "could not provide correct api. user (%s), compiled (%s), window (%s)",
- user_api_string, compiled_api_s, api_string);
- g_free (api_string);
- g_free (compiled_api_s);
- g_free (user_api_string);
- goto failure;
- }
-
- g_free (api_string);
- g_free (compiled_api_s);
- g_free (user_api_string);
-
- gl->GetError = gst_gl_window_get_proc_address (window, "glGetError");
- gl->GetString = gst_gl_window_get_proc_address (window, "glGetString");
-
- if (!gl->GetError || !gl->GetString) {
- g_set_error (error, GST_GL_WINDOW_ERROR, GST_GL_WINDOW_ERROR_FAILED,
- "could not GetProcAddress core opengl functions");
- goto failure;
- }
-
- /* gl api specific code */
- if (!ret && USING_OPENGL (display))
- ret = _create_context_opengl (window, &gl_major, NULL, error);
- if (!ret && USING_GLES2 (display))
- ret = _create_context_gles2 (window, &gl_major, NULL, error);
-
- if (!ret)
- goto failure;
-
- g_cond_signal (&window->priv->cond_create_context);
-
- window->priv->alive = TRUE;
- g_mutex_unlock (&window->priv->render_lock);
-
- gst_gl_window_run (window);
-
- GST_INFO ("loop exited\n");
-
- g_mutex_lock (&window->priv->render_lock);
-
- window->priv->alive = FALSE;
-
- if (window_class->close) {
- window_class->close (window);
- if (window->close)
- window->close (window->close_data);
- }
-
- g_cond_signal (&window->priv->cond_destroy_context);
-
- g_mutex_unlock (&window->priv->render_lock);
-
- return NULL;
+ g_return_val_if_fail (GST_GL_IS_WINDOW (window), NULL);
-failure:
- {
- g_cond_signal (&window->priv->cond_create_context);
- g_mutex_unlock (&window->priv->render_lock);
- return NULL;
- }
+ return (GstGLContext *) g_weak_ref_get (&window->context_ref);
}
diff --git a/gst-libs/gst/gl/gstglwindow.h b/gst-libs/gst/gl/gstglwindow.h
index e19e75c..f7aae8c 100644
--- a/gst-libs/gst/gl/gstglwindow.h
+++ b/gst-libs/gst/gl/gstglwindow.h
@@ -75,6 +75,8 @@ struct _GstGLWindow {
GMutex lock;
gboolean need_lock;
+ GWeakRef context_ref;
+
guintptr external_gl_context;
GstGLWindowCB draw;
@@ -131,7 +133,6 @@ void gst_gl_window_set_close_callback (GstGLWindow *window, GstGLWindowCB
void gst_gl_window_set_need_lock (GstGLWindow *window, gboolean need_lock);
guintptr gst_gl_window_get_gl_context (GstGLWindow *window);
-gboolean gst_gl_window_activate (GstGLWindow *window, gboolean activate);
void gst_gl_window_set_window_handle (GstGLWindow *window, guintptr handle);
guintptr gst_gl_window_get_window_handle (GstGLWindow *window);
void gst_gl_window_draw_unlocked (GstGLWindow *window, guint width, guint height);
@@ -140,13 +141,7 @@ void gst_gl_window_run (GstGLWindow *window);
void gst_gl_window_quit (GstGLWindow *window);
void gst_gl_window_send_message (GstGLWindow *window, GstGLWindowCB callback, gpointer data);
-gpointer gst_gl_window_get_proc_address (GstGLWindow *window, const gchar *name);
-GstGLPlatform gst_gl_window_get_platform (GstGLWindow *window);
-GstGLAPI gst_gl_window_get_gl_api (GstGLWindow *window);
-
-gboolean gst_gl_window_create_context (GstGLWindow *window, guintptr external_gl_context, GError ** error);
-
-gpointer gst_gl_window_default_get_proc_address (GstGLWindow *window, const gchar *name);
+GstGLContext * gst_gl_window_get_context (GstGLWindow *window);
gboolean gst_gl_window_is_running (GstGLWindow *window);
diff --git a/gst-libs/gst/gl/wayland/gstglwindow_wayland_egl.c b/gst-libs/gst/gl/wayland/gstglwindow_wayland_egl.c
index f8c06ad..16215d5 100644
--- a/gst-libs/gst/gl/wayland/gstglwindow_wayland_egl.c
+++ b/gst-libs/gst/gl/wayland/gstglwindow_wayland_egl.c
@@ -27,6 +27,9 @@
#include "wayland_event_source.h"
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include "gstglwindow_wayland_egl.h"
const gchar *WlEGLErrorString ();
@@ -572,13 +575,14 @@ static gpointer
gst_gl_window_wayland_egl_get_proc_address (GstGLWindow * window,
const gchar * name)
{
+ GstGLContext *context = NULL;
GstGLWindowWaylandEGL *window_egl;
gpointer result;
window_egl = GST_GL_WINDOW_WAYLAND_EGL (window);
if (!(result = gst_gl_egl_get_proc_address (window_egl->egl, name))) {
- result = gst_gl_window_default_get_proc_address (window, name);
+ result = gst_gl_context_default_get_proc_address (context, name);
}
return result;
diff --git a/gst-libs/gst/gl/win32/gstglwindow_win32_egl.c b/gst-libs/gst/gl/win32/gstglwindow_win32_egl.c
index 6229c51..6aa4903 100644
--- a/gst-libs/gst/gl/win32/gstglwindow_win32_egl.c
+++ b/gst-libs/gst/gl/win32/gstglwindow_win32_egl.c
@@ -25,6 +25,9 @@
#include <gst/gst.h>
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include "gstglwindow_win32_egl.h"
static guintptr gst_gl_window_win32_wgl_get_gl_context (GstGLWindowWin32 *
diff --git a/gst-libs/gst/gl/win32/gstglwindow_win32_wgl.c b/gst-libs/gst/gl/win32/gstglwindow_win32_wgl.c
index e85a011..0635967 100644
--- a/gst-libs/gst/gl/win32/gstglwindow_win32_wgl.c
+++ b/gst-libs/gst/gl/win32/gstglwindow_win32_wgl.c
@@ -27,6 +27,9 @@
#include <gst/gst.h>
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include "gstglwindow_win32_wgl.h"
#define GST_CAT_DEFAULT gst_gl_window_debug
@@ -215,10 +218,11 @@ static gpointer
gst_gl_window_win32_wgl_get_proc_address (GstGLWindow * window,
const gchar * name)
{
+ GstGLContext *context;
gpointer result;
if (!(result = wglGetProcAddress ((LPCSTR) name))) {
- result = gst_gl_window_default_get_proc_address (window, name);
+ result = gst_gl_context_default_get_proc_address (context, name);
}
return result;
diff --git a/gst-libs/gst/gl/x11/gstglwindow_x11_egl.c b/gst-libs/gst/gl/x11/gstglwindow_x11_egl.c
index 7ff1347..45413fb 100644
--- a/gst-libs/gst/gl/x11/gstglwindow_x11_egl.c
+++ b/gst-libs/gst/gl/x11/gstglwindow_x11_egl.c
@@ -25,6 +25,9 @@
#include "config.h"
#endif
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include "gstglwindow_x11_egl.h"
const gchar *X11EGLErrorString ();
@@ -188,11 +191,12 @@ static gpointer
gst_gl_window_x11_egl_get_proc_address (GstGLWindow * window,
const gchar * name)
{
+ GstGLContext *context = NULL;
GstGLWindowX11EGL *window_egl = GST_GL_WINDOW_X11_EGL (window);
gpointer result;
if (!(result = gst_gl_egl_get_proc_address (window_egl->egl, name))) {
- result = gst_gl_window_default_get_proc_address (window, name);
+ result = gst_gl_context_default_get_proc_address (context, name);
}
return result;
diff --git a/gst-libs/gst/gl/x11/gstglwindow_x11_glx.c b/gst-libs/gst/gl/x11/gstglwindow_x11_glx.c
index d62a990..9325029 100644
--- a/gst-libs/gst/gl/x11/gstglwindow_x11_glx.c
+++ b/gst-libs/gst/gl/x11/gstglwindow_x11_glx.c
@@ -27,6 +27,9 @@
#include <gst/gst.h>
+#include "../gstgl_fwd.h"
+#include <gst/gl/gstglcontext.h>
+
#include <gst/gl/gl.h>
#include "gstglwindow_x11_glx.h"
@@ -352,10 +355,11 @@ static gpointer
gst_gl_window_x11_glx_get_proc_address (GstGLWindow * window,
const gchar * name)
{
+ GstGLContext *context = NULL;
gpointer result;
if (!(result = glXGetProcAddressARB ((const GLubyte *) name))) {
- result = gst_gl_window_default_get_proc_address (window, name);
+ result = gst_gl_context_default_get_proc_address (context, name);
}
return result;
diff --git a/gst/gl/gstglimagesink.c b/gst/gl/gstglimagesink.c
index 5aede43..9741622 100644
--- a/gst/gl/gstglimagesink.c
+++ b/gst/gl/gstglimagesink.c
@@ -415,12 +415,14 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
g_atomic_int_set (&glimage_sink->to_quit, 0);
if (!glimage_sink->display) {
GstGLWindow *window;
+ GstGLContext *context;
GError *error = NULL;
GST_INFO ("Creating GstGLDisplay");
glimage_sink->display = gst_gl_display_new ();
- window = gst_gl_window_new (glimage_sink->display);
- gst_gl_display_set_window (glimage_sink->display, window);
+ context = gst_gl_context_new (glimage_sink->display);
+ gst_gl_display_set_context (glimage_sink->display, context);
+ window = gst_gl_context_get_window (context);
if (!glimage_sink->window_id && !glimage_sink->new_window_id)
gst_video_overlay_prepare_window_handle (GST_VIDEO_OVERLAY
@@ -431,7 +433,7 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
gst_gl_window_set_window_handle (window, glimage_sink->window_id);
}
- if (!gst_gl_window_create_context (window, 0, &error)) {
+ if (!gst_gl_context_create (context, 0, &error)) {
GST_ELEMENT_ERROR (glimage_sink, RESOURCE, NOT_FOUND,
("%s", error->message), (NULL));
@@ -439,7 +441,7 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
gst_object_unref (glimage_sink->display);
glimage_sink->display = NULL;
}
- gst_object_unref (window);
+ gst_object_unref (context);
return GST_STATE_CHANGE_FAILURE;
}
@@ -456,6 +458,7 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
gst_object_ref (glimage_sink), (GDestroyNotify) gst_object_unref);
gst_object_unref (window);
+ gst_object_unref (context);
}
break;
case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
@@ -494,7 +497,9 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
GST_VIDEO_SINK_WIDTH (glimage_sink) = 1;
GST_VIDEO_SINK_HEIGHT (glimage_sink) = 1;
if (glimage_sink->display) {
- GstGLWindow *window = gst_gl_display_get_window (glimage_sink->display);
+ GstGLContext *context =
+ gst_gl_display_get_context (glimage_sink->display);
+ GstGLWindow *window = gst_gl_context_get_window (context);
gst_gl_window_send_message (window,
GST_GL_WINDOW_CB (gst_glimage_sink_cleanup_glthread), glimage_sink);
@@ -504,6 +509,7 @@ gst_glimage_sink_change_state (GstElement * element, GstStateChange transition)
gst_gl_window_set_close_callback (window, NULL, NULL, NULL);
gst_object_unref (window);
+ gst_object_unref (context);
gst_object_unref (glimage_sink->display);
glimage_sink->display = NULL;
}
@@ -692,12 +698,14 @@ gst_glimage_sink_render (GstBaseSink * bsink, GstBuffer * buf)
}
if (glimage_sink->window_id != glimage_sink->new_window_id) {
- GstGLWindow *window = gst_gl_display_get_window (glimage_sink->display);
+ GstGLContext *context = gst_gl_display_get_context (glimage_sink->display);
+ GstGLWindow *window = gst_gl_context_get_window (context);
glimage_sink->window_id = glimage_sink->new_window_id;
gst_gl_window_set_window_handle (window, glimage_sink->window_id);
gst_object_unref (window);
+ gst_object_unref (context);
}
gst_buffer_replace (&glimage_sink->stored_buffer, buf);
@@ -771,12 +779,15 @@ gst_glimage_sink_expose (GstVideoOverlay * overlay)
if (glimage_sink->display && glimage_sink->window_id) {
if (glimage_sink->window_id != glimage_sink->new_window_id) {
- GstGLWindow *window = gst_gl_display_get_window (glimage_sink->display);
+ GstGLContext *context =
+ gst_gl_display_get_context (glimage_sink->display);
+ GstGLWindow *window = gst_gl_context_get_window (context);
glimage_sink->window_id = glimage_sink->new_window_id;
gst_gl_window_set_window_handle (window, glimage_sink->window_id);
gst_object_unref (window);
+ gst_object_unref (context);
}
gst_glimage_sink_redisplay (glimage_sink, 0, 0, 0, 0, 0,
@@ -959,6 +970,7 @@ gst_glimage_sink_on_draw (GstGLImageSink * gl_sink)
/* check if a client draw callback is registered */
if (gl_sink->clientDrawCallback) {
+
gboolean doRedisplay =
gl_sink->clientDrawCallback (gl_sink->redisplay_texture,
gl_sink->redisplay_texture_width,
@@ -966,12 +978,14 @@ gst_glimage_sink_on_draw (GstGLImageSink * gl_sink)
gl_sink->client_data);
if (doRedisplay) {
- GstGLWindow *window = gst_gl_display_get_window (gl_sink->display);
+ GstGLContext *context = gst_gl_display_get_context (gl_sink->display);
+ GstGLWindow *window = gst_gl_context_get_window (context);
gst_gl_window_draw_unlocked (window,
gl_sink->redisplay_texture_width, gl_sink->redisplay_texture_height);
gst_object_unref (window);
+ gst_object_unref (context);
}
}
/* default opengl scene */
@@ -1062,10 +1076,12 @@ gst_glimage_sink_redisplay (GstGLImageSink * gl_sink, GLuint texture,
gint gl_width, gint gl_height, gint window_width, gint window_height,
gboolean keep_aspect_ratio)
{
+ GstGLContext *context;
GstGLWindow *window;
gboolean alive;
- window = gst_gl_display_get_window (gl_sink->display);
+ context = gst_gl_display_get_context (gl_sink->display);
+ window = gst_gl_context_get_window (context);
if (window && gst_gl_window_is_running (window)) {
@@ -1089,6 +1105,7 @@ gst_glimage_sink_redisplay (GstGLImageSink * gl_sink, GLuint texture,
}
alive = gst_gl_window_is_running (window);
gst_object_unref (window);
+ gst_object_unref (context);
return alive;
}
diff --git a/gst/gl/gstgltestsrc.c b/gst/gl/gstgltestsrc.c
index 00df7f1..2f169b8 100644
--- a/gst/gl/gstgltestsrc.c
+++ b/gst/gl/gstgltestsrc.c
@@ -561,16 +561,16 @@ gst_gl_test_src_start (GstBaseSrc * basesrc)
src->display =
gst_object_ref (GST_GL_DISPLAY (g_value_get_pointer (id_value)));
else {
- GstGLWindow *window;
+ GstGLContext *context;
GError *error = NULL;
GST_INFO ("Creating GstGLDisplay");
src->display = gst_gl_display_new ();
- window = gst_gl_window_new (src->display);
- gst_gl_display_set_window (src->display, window);
- gst_object_unref (window);
+ context = gst_gl_context_new (src->display);
+ gst_gl_display_set_context (src->display, context);
+ gst_object_unref (context);
- if (!gst_gl_window_create_context (window, 0, &error)) {
+ if (!gst_gl_context_create (context, 0, &error)) {
GST_ELEMENT_ERROR (src, RESOURCE, NOT_FOUND,
("%s", error->message), (NULL));
return FALSE;