summaryrefslogtreecommitdiff
path: root/gst-libs/gst/gl
diff options
context:
space:
mode:
Diffstat (limited to 'gst-libs/gst/gl')
-rw-r--r--gst-libs/gst/gl/Makefile.am3
-rw-r--r--gst-libs/gst/gl/gstgldisplay.c856
-rw-r--r--gst-libs/gst/gl/gstgldisplay.h29
-rw-r--r--gst-libs/gst/gl/gstgldownload.c805
-rw-r--r--gst-libs/gst/gl/gstgldownload.h13
-rw-r--r--gst-libs/gst/gl/gstglfilter.c7
-rw-r--r--gst-libs/gst/gl/gstglfilter.h4
-rw-r--r--gst-libs/gst/gl/gstglmemory.c37
-rw-r--r--gst-libs/gst/gl/gstglshader.c136
-rw-r--r--gst-libs/gst/gl/gstglshader.h109
-rw-r--r--gst-libs/gst/gl/gstglshadervariables.c27
-rw-r--r--gst-libs/gst/gl/gstglupload.c804
-rw-r--r--gst-libs/gst/gl/gstglupload.h13
13 files changed, 1778 insertions, 1065 deletions
diff --git a/gst-libs/gst/gl/Makefile.am b/gst-libs/gst/gl/Makefile.am
index a59b8dd4c..946d7c110 100644
--- a/gst-libs/gst/gl/Makefile.am
+++ b/gst-libs/gst/gl/Makefile.am
@@ -55,7 +55,8 @@ libgstgl_@GST_API_VERSION@include_HEADERS = \
gstglshadervariables.h \
gstglshader.h \
gstgldownload.h \
- gstglupload.h
+ gstglupload.h \
+ gstglapi.h
libgstgl_@GST_API_VERSION@_la_CFLAGS = \
$(GL_CFLAGS) \
diff --git a/gst-libs/gst/gl/gstgldisplay.c b/gst-libs/gst/gl/gstgldisplay.c
index afd4a50a6..673a3b54d 100644
--- a/gst-libs/gst/gl/gstgldisplay.c
+++ b/gst-libs/gst/gl/gstgldisplay.c
@@ -42,14 +42,11 @@
#define GLEW_VERSION_MINOR 0
#endif
-/*
- * gst-launch-0.10 --gst-debug=gldisplay:N pipeline
- * N=1: errors
- * N=2: errors warnings
- * N=3: errors warnings infos
- * N=4: errors warnings infos
- * N=5: errors warnings infos logs
- */
+#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)
GST_DEBUG_CATEGORY_STATIC (gst_gl_display_debug);
#define GST_CAT_DEFAULT gst_gl_display_debug
@@ -59,13 +56,17 @@ GST_DEBUG_CATEGORY_STATIC (gst_gl_display_debug);
G_DEFINE_TYPE_WITH_CODE (GstGLDisplay, gst_gl_display, G_TYPE_OBJECT,
DEBUG_INIT);
+
+#define GST_GL_DISPLAY_GET_PRIVATE(o) \
+ (G_TYPE_INSTANCE_GET_PRIVATE((o), GST_GL_TYPE_DISPLAY, GstGLDisplayPrivate))
+
static void gst_gl_display_finalize (GObject * object);
/* Called in the gl thread, protected by lock and unlock */
gpointer gst_gl_display_thread_create_context (GstGLDisplay * display);
void gst_gl_display_thread_destroy_context (GstGLDisplay * display);
void gst_gl_display_thread_run_generic (GstGLDisplay * display);
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
void gst_gl_display_thread_init_redisplay (GstGLDisplay * display);
#endif
void gst_gl_display_thread_gen_fbo (GstGLDisplay * display);
@@ -86,12 +87,46 @@ void gst_gl_display_del_texture_thread (GstGLDisplay * display,
void gst_gl_display_gen_texture_window_cb (GstGLDisplay * display);
-//------------------------------------------------------------
-//---------------------- For klass GstGLDisplay ---------------
-//------------------------------------------------------------
+#if HAVE_OPENGL
+void _gen_fbo_opengl (GstGLDisplay * display);
+void _use_fbo_opengl (GstGLDisplay * display);
+void _use_fbo_v2_opengl (GstGLDisplay * display);
+void _del_fbo_opengl (GstGLDisplay * display);
+void _gen_shader_opengl (GstGLDisplay * display);
+void _del_shader_opengl (GstGLDisplay * display);
+#endif
+#if HAVE_GLES2
+void _gen_fbo_gles2 (GstGLDisplay * display);
+void _use_fbo_gles2 (GstGLDisplay * display);
+void _use_fbo_v2_gles2 (GstGLDisplay * display);
+void _del_fbo_gles2 (GstGLDisplay * display);
+void _gen_shader_gles2 (GstGLDisplay * display);
+void _del_shader_gles2 (GstGLDisplay * display);
+#endif
+
+typedef struct _GstGLVtable
+{
+ GstGLWindowCB gen_fbo;
+ GstGLWindowCB use_fbo;
+ GstGLWindowCB use_fbo_v2;
+ GstGLWindowCB del_fbo;
+ GstGLWindowCB gen_shader;
+ GstGLWindowCB del_shader;
+} GstGLVtable;
+
+struct _GstGLDisplayPrivate
+{
+ GstGLVtable vtable;
+};
+
+/*------------------------------------------------------------
+ --------------------- For klass GstGLDisplay ---------------
+ ----------------------------------------------------------*/
static void
gst_gl_display_class_init (GstGLDisplayClass * klass)
{
+ g_type_class_add_private (klass, sizeof (GstGLDisplayPrivate));
+
G_OBJECT_CLASS (klass)->finalize = gst_gl_display_finalize;
}
@@ -99,52 +134,54 @@ gst_gl_display_class_init (GstGLDisplayClass * klass)
static void
gst_gl_display_init (GstGLDisplay * display)
{
- //thread safe
+ display->priv = GST_GL_DISPLAY_GET_PRIVATE (display);
+
+ /* thread safe */
display->mutex = g_mutex_new ();
- //gl context
+ /* gl context */
display->gl_thread = NULL;
display->gl_window = NULL;
display->isAlive = TRUE;
- //conditions
+ /* conditions */
display->cond_create_context = g_cond_new ();
display->cond_destroy_context = g_cond_new ();
- //action redisplay
+ /* action redisplay */
display->redisplay_texture = 0;
display->redisplay_texture_width = 0;
display->redisplay_texture_height = 0;
display->keep_aspect_ratio = FALSE;
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
display->redisplay_shader = NULL;
display->redisplay_attr_position_loc = 0;
display->redisplay_attr_texture_loc = 0;
#endif
- //action gen and del texture
+ /* action gen and del texture */
display->gen_texture = 0;
display->gen_texture_width = 0;
display->gen_texture_height = 0;
display->gen_texture_video_format = GST_VIDEO_FORMAT_UNKNOWN;
- //client callbacks
+ /* client callbacks */
display->clientReshapeCallback = NULL;
display->clientDrawCallback = NULL;
display->client_data = NULL;
display->colorspace_conversion = GST_GL_DISPLAY_CONVERSION_GLSL;
- //foreign gl context
+ /* foreign gl context */
display->external_gl_context = 0;
- //filter gen fbo
+ /* filter gen fbo */
display->gen_fbo_width = 0;
display->gen_fbo_height = 0;
display->generated_fbo = 0;
display->generated_depth_buffer = 0;
- //filter use fbo
+ /* filter use fbo */
display->use_fbo = 0;
display->use_depth_buffer = 0;
display->use_fbo_texture = 0;
@@ -162,11 +199,11 @@ gst_gl_display_init (GstGLDisplay * display)
display->input_texture_height = 0;
display->input_texture = 0;
- //filter del fbo
+ /* filter del fbo */
display->del_fbo = 0;
display->del_depth_buffer = 0;
- //action gen and del shader
+ /* action gen and del shader */
display->gen_shader_fragment_source = NULL;
display->gen_shader_vertex_source = NULL;
display->gen_shader = NULL;
@@ -175,17 +212,19 @@ gst_gl_display_init (GstGLDisplay * display)
display->uploads = NULL;
display->downloads = NULL;
-#ifdef OPENGL_ES2
- display->redisplay_vertex_shader_str =
+#if HAVE_GLES2
+/* *INDENT-OFF* */
+ display->redisplay_vertex_shader_str_gles2 =
"attribute vec4 a_position; \n"
"attribute vec2 a_texCoord; \n"
"varying vec2 v_texCoord; \n"
"void main() \n"
"{ \n"
" gl_Position = a_position; \n"
- " v_texCoord = a_texCoord; \n" "} \n";
+ " v_texCoord = a_texCoord; \n"
+ "} \n";
- display->redisplay_fragment_shader_str =
+ display->redisplay_fragment_shader_str_gles2 =
"precision mediump float; \n"
"varying vec2 v_texCoord; \n"
"uniform sampler2D s_texture; \n"
@@ -193,6 +232,7 @@ gst_gl_display_init (GstGLDisplay * display)
"{ \n"
" gl_FragColor = texture2D( s_texture, v_texCoord );\n"
"} \n";
+/* *INDENT_ON* */
#endif
display->error_message = NULL;
@@ -295,14 +335,124 @@ gst_gl_display_set_error (GstGLDisplay * display, const char *format, ...)
display->isAlive = FALSE;
}
+#if HAVE_GLES2
+static gboolean
+_create_context_gles2 (GstGLDisplay * display, gint * gl_major, gint * gl_minor)
+{
+ GLenum gl_err = GL_NO_ERROR;
+
+ if (glGetString (GL_VERSION))
+ GST_INFO ("GL_VERSION: %s", glGetString (GL_VERSION));
+
+ if (glGetString (GL_SHADING_LANGUAGE_VERSION))
+ GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
+ glGetString (GL_SHADING_LANGUAGE_VERSION));
+ else
+ GST_INFO ("Your driver does not support GLSL (OpenGL Shading Language)");
+
+ if (glGetString (GL_VENDOR))
+ GST_INFO ("GL_VENDOR: %s", glGetString (GL_VENDOR));
+
+ if (glGetString (GL_RENDERER))
+ GST_INFO ("GL_RENDERER: %s", glGetString (GL_RENDERER));
+
+ gl_err = glGetError ();
+ if (gl_err != GL_NO_ERROR) {
+ gst_gl_display_set_error (display, "glGetString error: 0x%x", gl_err);
+ }
+
+ if (!GL_ES_VERSION_2_0)
+ gst_gl_display_set_error (display, "OpenGL|ES >= 2.0 is required");
+
+ display->priv->vtable.gen_fbo = (GstGLWindowCB) _gen_fbo_gles2;
+ display->priv->vtable.use_fbo = (GstGLWindowCB) _use_fbo_gles2;
+ display->priv->vtable.use_fbo_v2 = (GstGLWindowCB) _use_fbo_v2_gles2;
+ display->priv->vtable.del_fbo = (GstGLWindowCB) _del_fbo_gles2;
+ display->priv->vtable.gen_shader = (GstGLWindowCB) _gen_shader_gles2;
+ display->priv->vtable.del_shader = (GstGLWindowCB) _del_shader_gles2;
+
+ *gl_major = 2;
+ *gl_minor = 0;
+
+ return TRUE;
+}
+#endif
+
+#if HAVE_OPENGL
+gboolean
+_create_context_opengl (GstGLDisplay * display, gint * gl_major, gint * gl_minor)
+{
+ GLenum err = GLEW_OK;
+ GLenum gl_err = GL_NO_ERROR;
+ GString *opengl_version = NULL;
+
+ if (glewInit () != GLEW_OK) {
+ gst_gl_display_set_error (display, "Failed to init GLEW: %s",
+ glewGetErrorString (err));
+ return TRUE;
+ }
+
+ /* OpenGL > 1.2.0 and Glew > 1.4.0 */
+ if (glGetString (GL_VERSION))
+ GST_INFO ("GL_VERSION: %s", glGetString (GL_VERSION));
+
+ GST_INFO ("GLEW_VERSION: %s", glewGetString (GLEW_VERSION));
+
+ if (glGetString (GL_SHADING_LANGUAGE_VERSION))
+ GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
+ glGetString (GL_SHADING_LANGUAGE_VERSION));
+ else
+ GST_INFO ("Your driver does not support GLSL (OpenGL Shading Language)");
+
+ if (glGetString (GL_VENDOR))
+ GST_INFO ("GL_VENDOR: %s", glGetString (GL_VENDOR));
+
+ if (glGetString (GL_RENDERER))
+ GST_INFO ("GL_RENDERER: %s", glGetString (GL_RENDERER));
+
+ gl_err = glGetError ();
+ if (gl_err != GL_NO_ERROR) {
+ gst_gl_display_set_error (display, "glGetString error: 0x%x", gl_err);
+ }
+ if (glGetString (GL_VERSION)) {
+ opengl_version =
+ g_string_truncate (g_string_new ((gchar *) glGetString (GL_VERSION)), 3);
+
+ sscanf (opengl_version->str, "%d.%d", gl_major, gl_minor);
+
+ g_string_free (opengl_version, TRUE);
+
+ if ((*gl_major < 1) ||
+ (GLEW_VERSION_MAJOR < 1) ||
+ (*gl_major < 2 && *gl_major >= 1
+ && *gl_minor < 2) || (GLEW_VERSION_MAJOR < 2
+ && GLEW_VERSION_MAJOR >= 1 && GLEW_VERSION_MINOR < 4)) {
+ /* turn off the pipeline, the old drivers are not yet supported */
+ gst_gl_display_set_error (display,
+ "OpenGL >= 1.2.0 and Glew >= 1.4.0 is required");
+ }
+ }
+
+ display->priv->vtable.gen_fbo = (GstGLWindowCB) _gen_fbo_opengl;
+ display->priv->vtable.use_fbo = (GstGLWindowCB) _use_fbo_opengl;
+ display->priv->vtable.use_fbo_v2 = (GstGLWindowCB) _use_fbo_v2_opengl;
+ display->priv->vtable.del_fbo = (GstGLWindowCB) _del_fbo_opengl;
+ display->priv->vtable.gen_shader = (GstGLWindowCB) _gen_shader_opengl;
+ display->priv->vtable.del_shader = (GstGLWindowCB) _del_shader_opengl;
+
+ return TRUE;
+}
+#endif
+
gpointer
gst_gl_display_thread_create_context (GstGLDisplay * display)
{
- GLenum err = GLEW_OK;
+ gint gl_major = 0, gl_minor = 0;
+ gboolean ret = FALSE;
gst_gl_display_lock (display);
display->gl_window =
- gst_gl_window_new (GST_GL_RENDERER_API_ANY, display->external_gl_context);
+ gst_gl_window_new (GST_GL_API_ANY, display->external_gl_context);
if (!display->gl_window) {
gst_gl_display_set_error (display, "Failed to create gl window");
@@ -313,76 +463,24 @@ gst_gl_display_thread_create_context (GstGLDisplay * display)
GST_INFO ("gl window created");
-#ifndef OPENGL_ES2
- err = glewInit ();
-#endif
- if (err != GLEW_OK) {
-#ifndef OPENGL_ES2
- gst_gl_display_set_error (display, "Failed to init GLEW: %s",
- glewGetErrorString (err));
-#endif
- } else {
-#ifndef OPENGL_ES2
- //OpenGL > 1.2.0 and Glew > 1.4.0
- GString *opengl_version = NULL;
- gint opengl_version_major = 0;
- gint opengl_version_minor = 0;
-#endif
+ display->gl_api = gst_gl_window_get_gl_api (display->gl_window);
- GLenum gl_err = GL_NO_ERROR;
- if (glGetString (GL_VERSION))
- GST_INFO ("GL_VERSION: %s", glGetString (GL_VERSION));
+ g_assert (display->gl_api != GST_GL_API_NONE && display->gl_api != GST_GL_API_ANY);
-#ifndef OPENGL_ES2
- GST_INFO ("GLEW_VERSION: %s", glewGetString (GLEW_VERSION));
+ /* gl api specific code */
+#if HAVE_OPENGL
+ if (!ret && USING_OPENGL(display))
+ ret = _create_context_opengl (display, &gl_major, &gl_minor);
#endif
- if (glGetString (GL_SHADING_LANGUAGE_VERSION))
- GST_INFO ("GL_SHADING_LANGUAGE_VERSION: %s",
- glGetString (GL_SHADING_LANGUAGE_VERSION));
- else
- GST_INFO ("Your driver does not support GLSL (OpenGL Shading Language)");
-
- if (glGetString (GL_VENDOR))
- GST_INFO ("GL_VENDOR: %s", glGetString (GL_VENDOR));
-
- if (glGetString (GL_RENDERER))
- GST_INFO ("GL_RENDERER: %s", glGetString (GL_RENDERER));
-
-
- gl_err = glGetError ();
- if (gl_err != GL_NO_ERROR) {
- gst_gl_display_set_error (display, "glGetString error: 0x%x", gl_err);
- }
-#ifndef OPENGL_ES2
- if (glGetString (GL_VERSION) && gl_err == GL_NO_ERROR) {
-
- opengl_version =
- g_string_truncate (g_string_new ((gchar *) glGetString (GL_VERSION)),
- 3);
-
- sscanf (opengl_version->str, "%d.%d", &opengl_version_major,
- &opengl_version_minor);
-
- g_string_free (opengl_version, TRUE);
-
- if ((opengl_version_major < 1) ||
- (GLEW_VERSION_MAJOR < 1) ||
- (opengl_version_major < 2 && opengl_version_major >= 1
- && opengl_version_minor < 2) || (GLEW_VERSION_MAJOR < 2
- && GLEW_VERSION_MAJOR >= 1 && GLEW_VERSION_MINOR < 4)) {
- //turn off the pipeline, the old drivers are not yet supported
- gst_gl_display_set_error (display,
- "Required OpenGL >= 1.2.0 and Glew >= 1.4.0");
- }
- }
-#else
- if (!GL_ES_VERSION_2_0) {
- gst_gl_display_set_error (display, "Required OpenGL ES > 2.0");
- }
+#if HAVE_GLES2
+ if (!ret && USING_GLES2(display))
+ ret = _create_context_gles2 (display, &gl_major, &gl_minor);
#endif
- }
- //setup callbacks
+ if (!ret || !gl_major)
+ gst_gl_display_set_error (display, "failed to create context");
+
+ /* setup callbacks */
gst_gl_window_set_resize_callback (display->gl_window,
GST_GL_WINDOW_RESIZE_CB (gst_gl_display_on_resize), display);
gst_gl_window_set_draw_callback (display->gl_window,
@@ -418,7 +516,7 @@ gst_gl_display_thread_create_context (GstGLDisplay * display)
void
gst_gl_display_thread_destroy_context (GstGLDisplay * display)
{
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
if (display->redisplay_shader) {
g_object_unref (G_OBJECT (display->redisplay_shader));
display->redisplay_shader = NULL;
@@ -438,18 +536,18 @@ gst_gl_display_thread_run_generic (GstGLDisplay * display)
display->generic_callback (display, display->data);
}
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
/* Called in the gl thread */
void
gst_gl_display_thread_init_redisplay (GstGLDisplay * display)
{
GError *error = NULL;
- display->redisplay_shader = gst_gl_shader_new ();
+ display->redisplay_shader = gst_gl_shader_new (display);
gst_gl_shader_set_vertex_source (display->redisplay_shader,
- display->redisplay_vertex_shader_str);
+ display->redisplay_vertex_shader_str_gles2);
gst_gl_shader_set_fragment_source (display->redisplay_shader,
- display->redisplay_fragment_shader_str);
+ display->redisplay_fragment_shader_str_gles2);
gst_gl_shader_compile (display->redisplay_shader, &error);
if (error) {
@@ -468,42 +566,37 @@ gst_gl_display_thread_init_redisplay (GstGLDisplay * display)
}
#endif
-/* Called in the gl thread */
+#if HAVE_OPENGL
void
-gst_gl_display_thread_gen_fbo (GstGLDisplay * display)
+_gen_fbo_opengl (GstGLDisplay * display)
{
- //a texture must be attached to the FBO
+ /* a texture must be attached to the FBO */
GLuint fake_texture = 0;
GST_TRACE ("creating FBO dimensions:%ux%u", display->gen_fbo_width,
display->gen_fbo_height);
- //-- generate frame buffer object
+ /* -- generate frame buffer object */
if (!GLEW_EXT_framebuffer_object) {
- //turn off the pipeline because Frame buffer object is a not present
- gst_gl_display_set_error (display,
+ gst_gl_display_set_error (display,
"Context, EXT_framebuffer_object not supported");
return;
}
- //setup FBO
+ /* setup FBO */
glGenFramebuffersEXT (1, &display->generated_fbo);
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->generated_fbo);
- //setup the render buffer for depth
+ /* setup the render buffer for depth */
glGenRenderbuffersEXT (1, &display->generated_depth_buffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
-#ifndef OPENGL_ES2
+
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
display->gen_fbo_width, display->gen_fbo_height);
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
display->gen_fbo_width, display->gen_fbo_height);
-#else
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
- display->gen_fbo_width, display->gen_fbo_height);
-#endif
- //setup a texture to render to
+ /* setup a texture to render to */
glGenTextures (1, &fake_texture);
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, fake_texture);
glTexImage2D (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA8,
@@ -516,38 +609,94 @@ gst_gl_display_thread_gen_fbo (GstGLDisplay * display)
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
GL_CLAMP_TO_EDGE);
- //attach the texture to the FBO to renderer to
+ /* attach the texture to the FBO to renderer to */
glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
GL_TEXTURE_RECTANGLE_ARB, fake_texture, 0);
- //attach the depth render buffer to the FBO
+ /* attach the depth render buffer to the FBO */
glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT,
GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
-#ifndef OPENGL_ES2
- glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_STENCIL_ATTACHMENT_EXT,
- GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
-#endif
+ if (USING_OPENGL(display))
+ glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_STENCIL_ATTACHMENT_EXT,
+ GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
if (glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT) !=
GL_FRAMEBUFFER_COMPLETE_EXT)
gst_gl_display_set_error (display, "GL framebuffer status incomplete");
- //unbind the FBO
+ /* unbind the FBO */
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
glDeleteTextures (1, &fake_texture);
}
+#endif
-
-/* Called in the gl thread */
+#if HAVE_GLES2
void
-gst_gl_display_thread_use_fbo (GstGLDisplay * display)
+_gen_fbo_gles2 (GstGLDisplay * display)
{
-#ifdef OPENGL_ES2
- GLint viewport_dim[4];
+ /* a texture must be attached to the FBO */
+ GLuint fake_texture = 0;
+
+ GST_TRACE ("creating FBO dimensions:%ux%u", display->gen_fbo_width,
+ display->gen_fbo_height);
+
+ /* -- generate frame buffer object */
+
+ if (!GLEW_EXT_framebuffer_object) {
+ gst_gl_display_set_error (display,
+ "Context, EXT_framebuffer_object not supported");
+ return;
+ }
+ /* setup FBO */
+ glGenFramebuffersEXT (1, &display->generated_fbo);
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->generated_fbo);
+
+ /* setup the render buffer for depth */
+ glGenRenderbuffersEXT (1, &display->generated_depth_buffer);
+ glBindRenderbufferEXT (GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
+
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
+ display->gen_fbo_width, display->gen_fbo_height);
+
+ /* setup a texture to render to */
+ glGenTextures (1, &fake_texture);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, fake_texture);
+ glTexImage2D (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA8,
+ display->gen_fbo_width, display->gen_fbo_height, 0, GL_RGBA,
+ GL_UNSIGNED_BYTE, NULL);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+
+ /* attach the texture to the FBO to renderer to */
+ glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
+ GL_TEXTURE_RECTANGLE_ARB, fake_texture, 0);
+
+ /* attach the depth render buffer to the FBO */
+ glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT,
+ GL_RENDERBUFFER_EXT, display->generated_depth_buffer);
+
+ if (glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT) !=
+ GL_FRAMEBUFFER_COMPLETE_EXT)
+ gst_gl_display_set_error (display, "GL framebuffer status incomplete");
+
+ /* unbind the FBO */
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
+
+ glDeleteTextures (1, &fake_texture);
+}
#endif
+/* Called in the gl thread */
+#if HAVE_OPENGL
+void
+_use_fbo_opengl (GstGLDisplay * display)
+{
GST_TRACE ("Binding v1 FBO %u dimensions:%ux%u with texture:%u "
"dimensions:%ux%u", display->use_fbo, display->use_fbo_width,
display->use_fbo_height, display->use_fbo_texture,
@@ -555,17 +704,16 @@ gst_gl_display_thread_use_fbo (GstGLDisplay * display)
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->use_fbo);
- //setup a texture to render to
+ /* setup a texture to render to */
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture);
- //attach the texture to the FBO to renderer to
+ /* attach the texture to the FBO to renderer to */
glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture, 0);
if (GLEW_ARB_fragment_shader)
gst_gl_shader_use (NULL);
-#ifndef OPENGL_ES2
glPushAttrib (GL_VIEWPORT_BIT);
glMatrixMode (GL_PROJECTION);
glPushMatrix ();
@@ -589,44 +737,75 @@ gst_gl_display_thread_use_fbo (GstGLDisplay * display)
glMatrixMode (GL_MODELVIEW);
glPushMatrix ();
glLoadIdentity ();
-#else // OPENGL_ES2
- glGetIntegerv (GL_VIEWPORT, viewport_dim);
-#endif
+
glViewport (0, 0, display->use_fbo_width, display->use_fbo_height);
-#ifndef OPENGL_ES2
glDrawBuffer (GL_COLOR_ATTACHMENT0_EXT);
-#endif
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
- //the opengl scene
+ /* the opengl scene */
display->use_fbo_scene_cb (display->input_texture_width,
display->input_texture_height, display->input_texture,
display->use_fbo_stuff);
-#ifndef OPENGL_ES2
glDrawBuffer (GL_NONE);
glMatrixMode (GL_PROJECTION);
glPopMatrix ();
glMatrixMode (GL_MODELVIEW);
glPopMatrix ();
glPopAttrib ();
-#else
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
+}
+#endif
+
+#if HAVE_GLES2
+void
+_use_fbo_gles2 (GstGLDisplay * display)
+{
+ GLint viewport_dim[4];
+
+ GST_TRACE ("Binding v1 FBO %u dimensions:%ux%u with texture:%u "
+ "dimensions:%ux%u", display->use_fbo, display->use_fbo_width,
+ display->use_fbo_height, display->use_fbo_texture,
+ display->input_texture_width, display->input_texture_height);
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->use_fbo);
+
+ /* setup a texture to render to */
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture);
+
+ /* attach the texture to the FBO to renderer to */
+ glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
+ GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture, 0);
+
+ glGetIntegerv (GL_VIEWPORT, viewport_dim);
+
+ glViewport (0, 0, display->use_fbo_width, display->use_fbo_height);
+
+ glClearColor (0.0, 0.0, 0.0, 0.0);
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ /* the opengl scene */
+ display->use_fbo_scene_cb (display->input_texture_width,
+ display->input_texture_height, display->input_texture,
+ display->use_fbo_stuff);
+
glViewport (viewport_dim[0], viewport_dim[1], viewport_dim[2],
viewport_dim[3]);
-#endif
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
}
-
+#endif
/* Called in a gl thread
* Need full shader support */
+#if HAVE_OPENGL
void
-gst_gl_display_thread_use_fbo_v2 (GstGLDisplay * display)
+_use_fbo_v2_opengl (GstGLDisplay * display)
{
GLint viewport_dim[4];
@@ -636,10 +815,10 @@ gst_gl_display_thread_use_fbo_v2 (GstGLDisplay * display)
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->use_fbo);
- //setup a texture to render to
+ /* setup a texture to render to */
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture);
- //attach the texture to the FBO to renderer to
+ /* attach the texture to the FBO to renderer to */
glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture, 0);
@@ -647,30 +826,63 @@ gst_gl_display_thread_use_fbo_v2 (GstGLDisplay * display)
glViewport (0, 0, display->use_fbo_width, display->use_fbo_height);
-#ifndef OPENGL_ES2
glDrawBuffer (GL_COLOR_ATTACHMENT0_EXT);
-#endif
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
- //the opengl scene
+ /* the opengl scene */
display->use_fbo_scene_cb_v2 (display->use_fbo_stuff);
-#ifndef OPENGL_ES2
glDrawBuffer (GL_NONE);
-#endif
glViewport (viewport_dim[0], viewport_dim[1],
viewport_dim[2], viewport_dim[3]);
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
}
+#endif
+
+#if HAVE_GLES2
+void
+_use_fbo_v2_gles2 (GstGLDisplay * display)
+{
+ GLint viewport_dim[4];
+
+ GST_TRACE ("Binding v2 FBO %u dimensions:%ux%u with texture:%u ",
+ display->use_fbo, display->use_fbo_width,
+ display->use_fbo_height, display->use_fbo_texture);
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, display->use_fbo);
+
+ /* setup a texture to render to */
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture);
+
+ /* attach the texture to the FBO to renderer to */
+ glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
+ GL_TEXTURE_RECTANGLE_ARB, display->use_fbo_texture, 0);
+
+ glGetIntegerv (GL_VIEWPORT, viewport_dim);
+
+ glViewport (0, 0, display->use_fbo_width, display->use_fbo_height);
+ glClearColor (0.0, 0.0, 0.0, 0.0);
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ //the opengl scene
+ display->use_fbo_scene_cb_v2 (display->use_fbo_stuff);
+
+ glViewport (viewport_dim[0], viewport_dim[1],
+ viewport_dim[2], viewport_dim[3]);
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
+}
+#endif
/* Called in the gl thread */
+#if HAVE_OPENGL
void
-gst_gl_display_thread_del_fbo (GstGLDisplay * display)
+_del_fbo_opengl (GstGLDisplay * display)
{
GST_TRACE ("Deleting FBO %u", display->del_fbo);
@@ -683,11 +895,28 @@ gst_gl_display_thread_del_fbo (GstGLDisplay * display)
display->del_depth_buffer = 0;
}
}
+#endif
+
+#if HAVE_GLES2
+void
+_del_fbo_gles2 (GstGLDisplay * display)
+{
+ GST_TRACE ("Deleting FBO %u", display->del_fbo);
+ if (display->del_fbo) {
+ glDeleteFramebuffersEXT (1, &display->del_fbo);
+ display->del_fbo = 0;
+ }
+ if (display->del_depth_buffer) {
+ glDeleteRenderbuffersEXT (1, &display->del_depth_buffer);
+ display->del_depth_buffer = 0;
+ }
+}
+#endif
/* Called in the gl thread */
void
-gst_gl_display_thread_gen_shader (GstGLDisplay * display)
+_gen_shader_opengl (GstGLDisplay * display)
{
GST_TRACE ("Generating shader %" GST_PTR_FORMAT, display->gen_shader);
@@ -696,7 +925,7 @@ gst_gl_display_thread_gen_shader (GstGLDisplay * display)
display->gen_shader_fragment_source) {
GError *error = NULL;
- display->gen_shader = gst_gl_shader_new ();
+ display->gen_shader = gst_gl_shader_new (display);
if (display->gen_shader_vertex_source)
gst_gl_shader_set_vertex_source (display->gen_shader,
@@ -723,10 +952,49 @@ gst_gl_display_thread_gen_shader (GstGLDisplay * display)
}
}
+#if HAVE_GLES2
+void
+_gen_shader_gles2 (GstGLDisplay * display)
+{
+ GST_TRACE ("Generating shader %" GST_PTR_FORMAT, display->gen_shader);
+
+ if (GLEW_ARB_fragment_shader) {
+ if (display->gen_shader_vertex_source ||
+ display->gen_shader_fragment_source) {
+ GError *error = NULL;
+
+ display->gen_shader = gst_gl_shader_new (display);
+
+ if (display->gen_shader_vertex_source)
+ gst_gl_shader_set_vertex_source (display->gen_shader,
+ display->gen_shader_vertex_source);
+
+ if (display->gen_shader_fragment_source)
+ gst_gl_shader_set_fragment_source (display->gen_shader,
+ display->gen_shader_fragment_source);
+
+ gst_gl_shader_compile (display->gen_shader, &error);
+ if (error) {
+ gst_gl_display_set_error (display, "%s", error->message);
+ g_error_free (error);
+ error = NULL;
+ gst_gl_shader_use (NULL);
+ g_object_unref (G_OBJECT (display->gen_shader));
+ display->gen_shader = NULL;
+ }
+ }
+ } else {
+ gst_gl_display_set_error (display,
+ "One of the filter required ARB_fragment_shader");
+ display->gen_shader = NULL;
+ }
+}
+#endif
/* Called in the gl thread */
+#if HAVE_OPENGL
void
-gst_gl_display_thread_del_shader (GstGLDisplay * display)
+_del_shader_opengl (GstGLDisplay * display)
{
GST_TRACE ("Deleting shader %" GST_PTR_FORMAT, display->del_shader);
@@ -735,7 +1003,20 @@ gst_gl_display_thread_del_shader (GstGLDisplay * display)
display->del_shader = NULL;
}
}
+#endif
+
+#if HAVE_GLES2
+void
+_del_shader_gles2 (GstGLDisplay * display)
+{
+ GST_TRACE ("Deleting shader %" GST_PTR_FORMAT, display->del_shader);
+ if (display->del_shader) {
+ g_object_unref (G_OBJECT (display->del_shader));
+ display->del_shader = NULL;
+ }
+}
+#endif
//------------------------------------------------------------
//------------------ BEGIN GL THREAD ACTIONS -----------------
@@ -776,11 +1057,13 @@ gst_gl_display_on_resize (GstGLDisplay * display, gint width, gint height)
} else {
glViewport (0, 0, width, height);
}
-#ifndef OPENGL_ES2
- glMatrixMode (GL_PROJECTION);
- glLoadIdentity ();
- gluOrtho2D (0, width, 0, height);
- glMatrixMode (GL_MODELVIEW);
+#if HAVE_OPENGL
+ if (USING_OPENGL(display)) {
+ glMatrixMode (GL_PROJECTION);
+ glLoadIdentity ();
+ gluOrtho2D (0, width, 0, height);
+ glMatrixMode (GL_MODELVIEW);
+ }
#endif
}
}
@@ -789,24 +1072,25 @@ gst_gl_display_on_resize (GstGLDisplay * display, gint width, gint height)
void
gst_gl_display_on_draw (GstGLDisplay * display)
{
- //check if tecture is ready for being drawn
+ /* check if texture is ready for being drawn */
if (!display->redisplay_texture)
return;
- //opengl scene
+ /* opengl scene */
GST_TRACE ("on draw");
- //make sure that the environnement is clean
+ /* make sure that the environnement is clean */
if (display->colorspace_conversion == GST_GL_DISPLAY_CONVERSION_GLSL)
glUseProgramObjectARB (0);
-#ifndef OPENGL_ES2
- glDisable (GL_TEXTURE_RECTANGLE_ARB);
+#if HAVE_OPENGL
+ if (USING_OPENGL(display))
+ glDisable (GL_TEXTURE_RECTANGLE_ARB);
#endif
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, 0);
- //check if a client draw callback is registered
+ /* check if a client draw callback is registered */
if (display->clientDrawCallback) {
gboolean doRedisplay =
display->clientDrawCallback (display->redisplay_texture,
@@ -817,79 +1101,80 @@ gst_gl_display_on_draw (GstGLDisplay * display)
gst_gl_window_draw_unlocked (display->gl_window,
display->redisplay_texture_width, display->redisplay_texture_height);
}
- //default opengl scene
+ /* default opengl scene */
else {
+#if HAVE_OPENGL
+ if (USING_OPENGL(display)) {
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ glMatrixMode (GL_PROJECTION);
+ glLoadIdentity ();
+
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->redisplay_texture);
+ glEnable (GL_TEXTURE_RECTANGLE_ARB);
+
+ glBegin (GL_QUADS);
+ /* gst images are top-down while opengl plane is bottom-up */
+ glTexCoord2i (display->redisplay_texture_width, 0);
+ glVertex2f (1.0f, 1.0f);
+ glTexCoord2i (0, 0);
+ glVertex2f (-1.0f, 1.0f);
+ glTexCoord2i (0, display->redisplay_texture_height);
+ glVertex2f (-1.0f, -1.0f);
+ glTexCoord2i (display->redisplay_texture_width,
+ display->redisplay_texture_height);
+ glVertex2f (1.0f, -1.0f);
+ /*glTexCoord2i (display->redisplay_texture_width, 0);
+ glVertex2i (1, -1);
+ glTexCoord2i (0, 0);
+ glVertex2f (-1.0f, -1.0f);
+ glTexCoord2i (0, display->redisplay_texture_height);
+ glVertex2f (-1.0f, 1.0f);
+ glTexCoord2i (display->redisplay_texture_width,
+ display->redisplay_texture_height);
+ glVertex2f (1.0f, 1.0f); */
+ glEnd ();
+
+ glDisable (GL_TEXTURE_RECTANGLE_ARB);
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2(display)) {
+ const GLfloat vVertices[] = { 1.0f, 1.0f, 0.0f,
+ 1.0f, 0.0f,
+ -1.0f, 1.0f, 0.0f,
+ 0.0f, 0.0f,
+ -1.0f, -1.0f, 0.0f,
+ 0.0f, 1.0f,
+ 1.0f, -1.0f, 0.0f,
+ 1.0f, 1.0f
+ };
-#ifndef OPENGL_ES2
- glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
-
- glMatrixMode (GL_PROJECTION);
- glLoadIdentity ();
-
- glBindTexture (GL_TEXTURE_RECTANGLE_ARB, display->redisplay_texture);
- glEnable (GL_TEXTURE_RECTANGLE_ARB);
-
- glBegin (GL_QUADS);
- /* gst images are top-down while opengl plane is bottom-up */
- glTexCoord2i (display->redisplay_texture_width, 0);
- glVertex2f (1.0f, 1.0f);
- glTexCoord2i (0, 0);
- glVertex2f (-1.0f, 1.0f);
- glTexCoord2i (0, display->redisplay_texture_height);
- glVertex2f (-1.0f, -1.0f);
- glTexCoord2i (display->redisplay_texture_width,
- display->redisplay_texture_height);
- glVertex2f (1.0f, -1.0f);
- /*glTexCoord2i (display->redisplay_texture_width, 0);
- glVertex2i (1, -1);
- glTexCoord2i (0, 0);
- glVertex2f (-1.0f, -1.0f);
- glTexCoord2i (0, display->redisplay_texture_height);
- glVertex2f (-1.0f, 1.0f);
- glTexCoord2i (display->redisplay_texture_width,
- display->redisplay_texture_height);
- glVertex2f (1.0f, 1.0f); */
- glEnd ();
-
- glDisable (GL_TEXTURE_RECTANGLE_ARB);
-
-#else //OPENGL_ES2
-
- const GLfloat vVertices[] = { 1.0f, 1.0f, 0.0f,
- 1.0f, 0.0f,
- -1.0f, 1.0f, 0.0f,
- 0.0f, 0.0f,
- -1.0f, -1.0f, 0.0f,
- 0.0f, 1.0f,
- 1.0f, -1.0f, 0.0f,
- 1.0f, 1.0f
- };
-
- GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
+ GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
- glClear (GL_COLOR_BUFFER_BIT);
+ glClear (GL_COLOR_BUFFER_BIT);
- gst_gl_shader_use (display->redisplay_shader);
+ gst_gl_shader_use (display->redisplay_shader);
- //Load the vertex position
- glVertexAttribPointer (display->redisplay_attr_position_loc, 3, GL_FLOAT,
- GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ /* Load the vertex position */
+ glVertexAttribPointer (display->redisplay_attr_position_loc, 3, GL_FLOAT,
+ GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- //Load the texture coordinate
- glVertexAttribPointer (display->redisplay_attr_texture_loc, 2, GL_FLOAT,
- GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+ /* Load the texture coordinate */
+ glVertexAttribPointer (display->redisplay_attr_texture_loc, 2, GL_FLOAT,
+ GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
- glEnableVertexAttribArray (display->redisplay_attr_position_loc);
- glEnableVertexAttribArray (display->redisplay_attr_texture_loc);
+ glEnableVertexAttribArray (display->redisplay_attr_position_loc);
+ glEnableVertexAttribArray (display->redisplay_attr_texture_loc);
- glActiveTexture (GL_TEXTURE0);
- glBindTexture (GL_TEXTURE_2D, display->redisplay_texture);
- gst_gl_shader_set_uniform_1i (display->redisplay_shader, "s_texture", 0);
+ glActiveTexture (GL_TEXTURE0);
+ glBindTexture (GL_TEXTURE_2D, display->redisplay_texture);
+ gst_gl_shader_set_uniform_1i (display->redisplay_shader, "s_texture", 0);
- glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
+ glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
+ }
#endif
-
- } //end default opengl scene
+ } /* end default opengl scene */
}
@@ -941,7 +1226,8 @@ gst_gl_display_gen_texture_thread (GstGLDisplay * display, GLuint * pTexture,
glTexImage2D (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA8,
width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
break;
-/* case GST_GL_DISPLAY_CONVERSION_MESA:
+#if 0
+ case GST_GL_DISPLAY_CONVERSION_MESA:
if (display->upload_width != display->upload_data_width ||
display->upload_height != display->upload_data_height)
glTexImage2D (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA8,
@@ -949,7 +1235,8 @@ gst_gl_display_gen_texture_thread (GstGLDisplay * display, GLuint * pTexture,
else
glTexImage2D (GL_TEXTURE_RECTANGLE_ARB, 0, GL_YCBCR_MESA, width,
height, 0, GL_YCBCR_MESA, GL_UNSIGNED_SHORT_8_8_MESA, NULL);
- break;*/
+ break;
+#endif
default:
gst_gl_display_set_error (display, "Unknow colorspace conversion %d",
display->colorspace_conversion);
@@ -962,8 +1249,8 @@ gst_gl_display_gen_texture_thread (GstGLDisplay * display, GLuint * pTexture,
width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
break;
default:
-// gst_gl_display_set_error (display, "Unsupported upload video format %d",
-// display->upload_video_format);
+ gst_gl_display_set_error (display, "Unsupported upload video format %d",
+ v_format);
break;
}
@@ -984,14 +1271,14 @@ gst_gl_display_del_texture_thread (GstGLDisplay * display, GLuint * pTexture)
}
-//------------------------------------------------------------
-//--------------------- END PRIVATE -------------------------
-//------------------------------------------------------------
+/*------------------------------------------------------------
+ --------------------- END PRIVATE -------------------------
+ ----------------------------------------------------------*/
-//------------------------------------------------------------
-//---------------------- BEGIN PUBLIC ------------------------
-//------------------------------------------------------------
+/*------------------------------------------------------------
+ --------------------- BEGIN PUBLIC -------------------------
+ ----------------------------------------------------------*/
void
gst_gl_display_lock (GstGLDisplay * display)
@@ -999,7 +1286,6 @@ gst_gl_display_lock (GstGLDisplay * display)
g_mutex_lock (display->mutex);
}
-
void
gst_gl_display_unlock (GstGLDisplay * display)
{
@@ -1030,7 +1316,7 @@ gst_gl_display_check_framebuffer_status (void)
case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT:
GST_ERROR ("GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS");
break;
-#ifndef OPENGL_ES2
+#if HAVE_OPENGL
case GL_FRAMEBUFFER_UNDEFINED:
GST_ERROR ("GL_FRAMEBUFFER_UNDEFINED");
break;
@@ -1044,7 +1330,7 @@ gst_gl_display_check_framebuffer_status (void)
GstGLDisplay *
gst_gl_display_new (void)
{
- return g_object_new (GST_TYPE_GL_DISPLAY, NULL);
+ return g_object_new (GST_GL_TYPE_DISPLAY, NULL);
}
@@ -1083,16 +1369,17 @@ gst_gl_display_redisplay (GstGLDisplay * display, GLuint texture,
gint gl_width, gint gl_height, gint window_width, gint window_height,
gboolean keep_aspect_ratio)
{
- gboolean isAlive = TRUE;
+ gboolean isAlive;
gst_gl_display_lock (display);
- isAlive = display->isAlive;
- if (isAlive) {
+ if (display->isAlive) {
-#ifdef OPENGL_ES2
- if (!display->redisplay_shader) {
- gst_gl_window_send_message (display->gl_window,
+#if HAVE_GLES2
+ if (USING_GLES2(display)) {
+ if (!display->redisplay_shader) {
+ gst_gl_window_send_message (display->gl_window,
GST_GL_WINDOW_CB (gst_gl_display_thread_init_redisplay), display);
+ }
}
#endif
@@ -1104,8 +1391,8 @@ gst_gl_display_redisplay (GstGLDisplay * display, GLuint texture,
display->keep_aspect_ratio = keep_aspect_ratio;
if (display->gl_window)
gst_gl_window_draw (display->gl_window, window_width, window_height);
- isAlive = display->isAlive;
}
+ isAlive = display->isAlive;
gst_gl_display_unlock (display);
return isAlive;
@@ -1167,11 +1454,11 @@ gst_gl_display_gen_fbo (GstGLDisplay * display, gint width, gint height,
display->gen_fbo_width = width;
display->gen_fbo_height = height;
gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_gen_fbo), display);
+ GST_GL_WINDOW_CB (display->priv->vtable.gen_fbo), display);
*fbo = display->generated_fbo;
*depthbuffer = display->generated_depth_buffer;
- isAlive = display->isAlive;
}
+ isAlive = display->isAlive;
gst_gl_display_unlock (display);
return isAlive;
@@ -1194,11 +1481,10 @@ gst_gl_display_use_fbo (GstGLDisplay * display, gint texture_fbo_width,
gdouble proj_param2, gdouble proj_param3, gdouble proj_param4,
GstGLDisplayProjection projection, gpointer * stuff)
{
- gboolean isAlive = TRUE;
+ gboolean isAlive;
gst_gl_display_lock (display);
- isAlive = display->isAlive;
- if (isAlive) {
+ if (display->isAlive) {
display->use_fbo = fbo;
display->use_depth_buffer = depth_buffer;
display->use_fbo_texture = texture_fbo;
@@ -1214,10 +1500,9 @@ gst_gl_display_use_fbo (GstGLDisplay * display, gint texture_fbo_width,
display->input_texture_width = input_texture_width;
display->input_texture_height = input_texture_height;
display->input_texture = input_texture;
- gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_use_fbo), display);
- isAlive = display->isAlive;
+ gst_gl_window_send_message (display->gl_window, display->priv->vtable.use_fbo, display);
}
+ isAlive = display->isAlive;
gst_gl_display_unlock (display);
return isAlive;
@@ -1228,11 +1513,10 @@ gst_gl_display_use_fbo_v2 (GstGLDisplay * display, gint texture_fbo_width,
gint texture_fbo_height, GLuint fbo, GLuint depth_buffer,
GLuint texture_fbo, GLCB_V2 cb, gpointer * stuff)
{
- gboolean isAlive = TRUE;
+ gboolean isAlive;
gst_gl_display_lock (display);
- isAlive = display->isAlive;
- if (isAlive) {
+ if (display->isAlive) {
display->use_fbo = fbo;
display->use_depth_buffer = depth_buffer;
display->use_fbo_texture = texture_fbo;
@@ -1240,10 +1524,9 @@ gst_gl_display_use_fbo_v2 (GstGLDisplay * display, gint texture_fbo_width,
display->use_fbo_height = texture_fbo_height;
display->use_fbo_scene_cb_v2 = cb;
display->use_fbo_stuff = stuff;
- gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_use_fbo_v2), display);
- isAlive = display->isAlive;
+ gst_gl_window_send_message (display->gl_window, display->priv->vtable.use_fbo_v2, display);
}
+ isAlive = display->isAlive;
gst_gl_display_unlock (display);
return isAlive;
@@ -1254,10 +1537,11 @@ void
gst_gl_display_del_fbo (GstGLDisplay * display, GLuint fbo, GLuint depth_buffer)
{
gst_gl_display_lock (display);
- display->del_fbo = fbo;
- display->del_depth_buffer = depth_buffer;
- gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_del_fbo), display);
+ if (display->isAlive) {
+ display->del_fbo = fbo;
+ display->del_depth_buffer = depth_buffer;
+ gst_gl_window_send_message (display->gl_window, display->priv->vtable.del_fbo, display);
+ }
gst_gl_display_unlock (display);
}
@@ -1268,19 +1552,20 @@ gst_gl_display_gen_shader (GstGLDisplay * display,
const gchar * shader_vertex_source,
const gchar * shader_fragment_source, GstGLShader ** shader)
{
- gboolean isAlive = FALSE;
+ gboolean isAlive;
gst_gl_display_lock (display);
- display->gen_shader_vertex_source = shader_vertex_source;
- display->gen_shader_fragment_source = shader_fragment_source;
- gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_gen_shader), display);
+ if (display->isAlive) {
+ display->gen_shader_vertex_source = shader_vertex_source;
+ display->gen_shader_fragment_source = shader_fragment_source;
+ gst_gl_window_send_message (display->gl_window, display->priv->vtable.gen_shader, display);
+ if (shader)
+ *shader = display->gen_shader;
+ display->gen_shader = NULL;
+ display->gen_shader_vertex_source = NULL;
+ display->gen_shader_fragment_source = NULL;
+ }
isAlive = display->isAlive;
- if (shader)
- *shader = display->gen_shader;
- display->gen_shader = NULL;
- display->gen_shader_vertex_source = NULL;
- display->gen_shader_fragment_source = NULL;
gst_gl_display_unlock (display);
return isAlive;
@@ -1292,9 +1577,10 @@ void
gst_gl_display_del_shader (GstGLDisplay * display, GstGLShader * shader)
{
gst_gl_display_lock (display);
- display->del_shader = shader;
- gst_gl_window_send_message (display->gl_window,
- GST_GL_WINDOW_CB (gst_gl_display_thread_del_shader), display);
+ if (display->isAlive) {
+ display->del_shader = shader;
+ gst_gl_window_send_message (display->gl_window, display->priv->vtable.del_shader, display);
+ }
gst_gl_display_unlock (display);
}
@@ -1356,6 +1642,24 @@ gst_gl_display_activate_gl_context (GstGLDisplay * display, gboolean activate)
gst_gl_display_unlock (display);
}
+GstGLAPI
+gst_gl_display_get_gl_api_unlocked (GstGLDisplay * display)
+{
+ return display->gl_api;
+}
+
+GstGLAPI
+gst_gl_display_get_gl_api (GstGLDisplay * display)
+{
+ GstGLAPI api;
+
+ gst_gl_display_lock (display);
+ api = gst_gl_display_get_gl_api_unlocked (display);
+ gst_gl_display_unlock (display);
+
+ return api;
+}
+
//------------------------------------------------------------
//------------------------ END PUBLIC ------------------------
//------------------------------------------------------------
diff --git a/gst-libs/gst/gl/gstgldisplay.h b/gst-libs/gst/gl/gstgldisplay.h
index 54b4d5b2d..313880f85 100644
--- a/gst-libs/gst/gl/gstgldisplay.h
+++ b/gst-libs/gst/gl/gstgldisplay.h
@@ -25,8 +25,11 @@
#include <gst/video/video.h>
+typedef struct _GstGLUpload GstGLUpload;
+typedef struct _GstGLDownload GstGLDownload;
+typedef struct _GstGLShader GstGLShader;
+
#include "gstglwindow.h"
-#include "gstglrenderer.h"
#include "gstglshader.h"
#include "gstglupload.h"
#include "gstgldownload.h"
@@ -34,18 +37,19 @@
G_BEGIN_DECLS
GType gst_gl_display_get_type (void);
-#define GST_TYPE_GL_DISPLAY (gst_gl_display_get_type())
-#define GST_GL_DISPLAY(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_GL_DISPLAY,GstGLDisplay))
+#define GST_GL_TYPE_DISPLAY (gst_gl_display_get_type())
+#define GST_GL_DISPLAY(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_GL_TYPE_DISPLAY,GstGLDisplay))
#define GST_GL_DISPLAY_CLASS(klass) \
- (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_GL_DISPLAY,GstGLDisplayClass))
+ (G_TYPE_CHECK_CLASS_CAST((klass),GST_GL_TYPE_DISPLAY,GstGLDisplayClass))
#define GST_IS_GL_DISPLAY(obj) \
- (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_GL_DISPLAY))
+ (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_GL_TYPE_DISPLAY))
#define GST_IS_GL_DISPLAY_CLASS(klass) \
- (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_GL_DISPLAY))
+ (G_TYPE_CHECK_CLASS_TYPE((klass),GST_GL_TYPE_DISPLAY))
#define GST_GL_DISPLAY_CAST(obj) ((GstGLDisplay*)(obj))
typedef struct _GstGLDisplay GstGLDisplay;
typedef struct _GstGLDisplayClass GstGLDisplayClass;
+typedef struct _GstGLDisplayPrivate GstGLDisplayPrivate;
/**
* GstGLDisplayConversion:
@@ -139,6 +143,9 @@ struct _GstGLDisplay
GstGLWindow *gl_window;
gboolean isAlive;
+ /* gl API we are using */
+ GstGLAPI gl_api;
+
/* conditions */
GCond *cond_create_context;
GCond *cond_destroy_context;
@@ -152,10 +159,10 @@ struct _GstGLDisplay
GLuint redisplay_texture_width;
GLuint redisplay_texture_height;
gboolean keep_aspect_ratio;
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
GstGLShader *redisplay_shader;
- gchar *redisplay_vertex_shader_str;
- gchar *redisplay_fragment_shader_str;
+ gchar *redisplay_vertex_shader_str_gles2;
+ gchar *redisplay_fragment_shader_str_gles2;
GLint redisplay_attr_position_loc;
GLint redisplay_attr_texture_loc;
#endif
@@ -214,6 +221,8 @@ struct _GstGLDisplay
GstGLShader *del_shader;
gchar *error_message;
+
+ GstGLDisplayPrivate *priv;
};
@@ -277,6 +286,8 @@ void gst_gl_display_check_framebuffer_status (void);
void gst_gl_display_lock (GstGLDisplay * display);
void gst_gl_display_unlock (GstGLDisplay * display);
+GstGLAPI gst_gl_display_get_gl_api (GstGLDisplay * display);
+GstGLAPI gst_gl_display_get_gl_api_unlocked (GstGLDisplay * display);
G_END_DECLS
diff --git a/gst-libs/gst/gl/gstgldownload.c b/gst-libs/gst/gl/gstgldownload.c
index 74454d19e..87dbb3927 100644
--- a/gst-libs/gst/gl/gstgldownload.c
+++ b/gst-libs/gst/gl/gstgldownload.c
@@ -43,11 +43,13 @@
* calling thread.
*/
+#define USING_OPENGL(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL)
+#define USING_OPENGL3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL3)
+#define USING_GLES(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES)
+#define USING_GLES2(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES2)
+#define USING_GLES3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES3)
+
static void _do_download (GstGLDisplay * display, GstGLDownload * download);
-static void _do_download_draw_rgb (GstGLDisplay * display,
- GstGLDownload * download);
-static void _do_download_draw_yuv (GstGLDisplay * display,
- GstGLDownload * download);
static void _init_download (GstGLDisplay * display, GstGLDownload * download);
static void _init_download_shader (GstGLDisplay * display,
GstGLDownload * download);
@@ -56,18 +58,29 @@ static gboolean gst_gl_download_perform_with_data_unlocked (GstGLDownload *
static gboolean gst_gl_download_perform_with_data_unlocked_thread (GstGLDownload
* download, GLuint texture_id, gpointer data[GST_VIDEO_MAX_PLANES]);
+#if HAVE_OPENGL
+static void _do_download_draw_rgb_opengl (GstGLDisplay * display,
+ GstGLDownload * download);
+static void _do_download_draw_yuv_opengl (GstGLDisplay * display,
+ GstGLDownload * download);
+#endif
+#if HAVE_GLES2
+static void _do_download_draw_rgb_gles2 (GstGLDisplay * display,
+ GstGLDownload * download);
+static void _do_download_draw_yuv_gles2 (GstGLDisplay * display,
+ GstGLDownload * download);
+#endif
+
+/* *INDENT-OFF* */
+
/* YUY2:y2,u,y1,v
UYVY:v,y1,u,y2 */
-static gchar *text_shader_download_YUY2_UYVY =
-#ifndef OPENGL_ES2
+#if HAVE_OPENGL
+static gchar *text_shader_YUY2_UYVY_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect tex;\n"
-#else
- "precision mediump float;\n"
- "varying vec2 v_texCoord;\n" "uniform sampler2D tex;\n"
-#endif
- "void main(void) {\n" " float fx,fy,r,g,b,r2,g2,b2,y1,y2,u,v;\n"
-#ifndef OPENGL_ES2
+ "void main(void) {\n"
+ " float fx,fy,r,g,b,r2,g2,b2,y1,y2,u,v;\n"
" fx = gl_TexCoord[0].x;\n"
" fy = gl_TexCoord[0].y;\n"
" r=texture2DRect(tex,vec2(fx*2.0,fy)).r;\n"
@@ -76,28 +89,18 @@ static gchar *text_shader_download_YUY2_UYVY =
" r2=texture2DRect(tex,vec2(fx*2.0+1.0,fy)).r;\n"
" g2=texture2DRect(tex,vec2(fx*2.0+1.0,fy)).g;\n"
" b2=texture2DRect(tex,vec2(fx*2.0+1.0,fy)).b;\n"
-#else
- " fx = v_texCoord.x;\n"
- " fy = v_texCoord.y;\n"
- " r=texture2D(tex,vec2(fx*2.0,fy)).r;\n"
- " g=texture2D(tex,vec2(fx*2.0,fy)).g;\n"
- " b=texture2D(tex,vec2(fx*2.0,fy)).b;\n"
- " r2=texture2D(tex,vec2(fx*2.0+1.0,fy)).r;\n"
- " g2=texture2D(tex,vec2(fx*2.0+1.0,fy)).g;\n"
- " b2=texture2D(tex,vec2(fx*2.0+1.0,fy)).b;\n"
-#endif
" y1=0.299011*r + 0.586987*g + 0.114001*b;\n"
" y2=0.299011*r2 + 0.586987*g2 + 0.114001*b2;\n"
" u=-0.148246*r -0.29102*g + 0.439266*b;\n"
" v=0.439271*r - 0.367833*g - 0.071438*b ;\n"
" y1=0.858885*y1 + 0.0625;\n"
" y2=0.858885*y2 + 0.0625;\n"
- " u=u + 0.5;\n" " v=v + 0.5;\n" " gl_FragColor=vec4(%s);\n" "}\n";
+ " u=u + 0.5;\n"
+ " v=v + 0.5;\n"
+ " gl_FragColor=vec4(%s);\n"
+ "}\n";
-/* no OpenGL ES 2.0 support because for now it's not possible
- * to attach multiple textures to a frame buffer object
- */
-static gchar *text_shader_download_I420_YV12 =
+static gchar *text_shader_I420_YV12_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect tex;\n"
"uniform float w, h;\n"
@@ -119,48 +122,91 @@ static gchar *text_shader_download_I420_YV12 =
" v=v + 0.5;\n"
" gl_FragData[0] = vec4(y, 0.0, 0.0, 1.0);\n"
" gl_FragData[1] = vec4(u, 0.0, 0.0, 1.0);\n"
- " gl_FragData[2] = vec4(v, 0.0, 0.0, 1.0);\n" "}\n";
+ " gl_FragData[2] = vec4(v, 0.0, 0.0, 1.0);\n"
+ "}\n";
-static gchar *text_shader_download_AYUV =
-#ifndef OPENGL_ES2
+static gchar *text_shader_AYUV_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect tex;\n"
-#else
- "precision mediump float;\n"
- "varying vec2 v_texCoord;\n" "uniform sampler2D tex;\n"
-#endif
- "void main(void) {\n" " float r,g,b,y,u,v;\n"
-#ifndef OPENGL_ES2
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
" vec2 nxy=gl_TexCoord[0].xy;\n"
" r=texture2DRect(tex,nxy).r;\n"
- " g=texture2DRect(tex,nxy).g;\n" " b=texture2DRect(tex,nxy).b;\n"
-#else
+ " g=texture2DRect(tex,nxy).g;\n"
+ " b=texture2DRect(tex,nxy).b;\n"
+ " y=0.299011*r + 0.586987*g + 0.114001*b;\n"
+ " u=-0.148246*r -0.29102*g + 0.439266*b;\n"
+ " v=0.439271*r - 0.367833*g - 0.071438*b ;\n"
+ " y=0.858885*y + 0.0625;\n"
+ " u=u + 0.5;\n"
+ " v=v + 0.5;\n"
+ " gl_FragColor=vec4(y,u,v,1.0);\n"
+ "}\n";
+
+#define text_vertex_shader_opengl NULL
+#endif /* HAVE_OPENGL */
+
+#if HAVE_GLES2
+static gchar *text_shader_YUY2_UYVY_gles2 =
+ "precision mediump float;\n"
+ "varying vec2 v_texCoord;\n"
+ "uniform sampler2D tex;\n"
+ "void main(void) {\n"
+ " float fx,fy,r,g,b,r2,g2,b2,y1,y2,u,v;\n"
+ " fx = v_texCoord.x;\n"
+ " fy = v_texCoord.y;\n"
+ " r=texture2D(tex,vec2(fx*2.0,fy)).r;\n"
+ " g=texture2D(tex,vec2(fx*2.0,fy)).g;\n"
+ " b=texture2D(tex,vec2(fx*2.0,fy)).b;\n"
+ " r2=texture2D(tex,vec2(fx*2.0+1.0,fy)).r;\n"
+ " g2=texture2D(tex,vec2(fx*2.0+1.0,fy)).g;\n"
+ " b2=texture2D(tex,vec2(fx*2.0+1.0,fy)).b;\n"
+ " y1=0.299011*r + 0.586987*g + 0.114001*b;\n"
+ " y2=0.299011*r2 + 0.586987*g2 + 0.114001*b2;\n"
+ " u=-0.148246*r -0.29102*g + 0.439266*b;\n"
+ " v=0.439271*r - 0.367833*g - 0.071438*b ;\n"
+ " y1=0.858885*y1 + 0.0625;\n"
+ " y2=0.858885*y2 + 0.0625;\n"
+ " u=u + 0.5;\n"
+ " v=v + 0.5;\n"
+ " gl_FragColor=vec4(%s);\n"
+ "}\n";
+
+/* no OpenGL ES 2.0 support because for now it's not possible
+ * to attach multiple textures to a frame buffer object
+ */
+#define text_shader_I420_YV12_gles2 NULL
+
+static gchar *text_shader_AYUV_gles2 =
+ "precision mediump float;\n"
+ "varying vec2 v_texCoord;\n"
+ "uniform sampler2D tex;\n"
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
" vec2 nxy=v_texCoord.xy;\n"
" r=texture2D(tex,nxy).r;\n"
- " g=texture2D(tex,nxy).g;\n" " b=texture2D(tex,nxy).b;\n"
-#endif
+ " g=texture2D(tex,nxy).g;\n"
+ " b=texture2D(tex,nxy).b;\n"
" y=0.299011*r + 0.586987*g + 0.114001*b;\n"
" u=-0.148246*r -0.29102*g + 0.439266*b;\n"
" v=0.439271*r - 0.367833*g - 0.071438*b ;\n"
- " y=0.858885*y + 0.0625;\n" " u=u + 0.5;\n" " v=v + 0.5;\n"
-#ifndef OPENGL_ES2
- " gl_FragColor=vec4(y,u,v,1.0);\n"
-#else
+ " y=0.858885*y + 0.0625;\n"
+ " u=u + 0.5;\n"
+ " v=v + 0.5;\n"
" gl_FragColor=vec4(1.0,y,u,v);\n"
-#endif
"}\n";
-#ifdef OPENGL_ES2
-static gchar *text_vertex_shader_download =
+static gchar *text_vertex_shader_gles2 =
"attribute vec4 a_position; \n"
"attribute vec2 a_texCoord; \n"
"varying vec2 v_texCoord; \n"
"void main() \n"
"{ \n"
" gl_Position = a_position; \n"
- " v_texCoord = a_texCoord; \n" "} \n";
+ " v_texCoord = a_texCoord; \n"
+ "} \n";
-static gchar *text_fragment_shader_download_RGB =
+static gchar *text_shader_RGB_gles2 =
"precision mediump float; \n"
"varying vec2 v_texCoord; \n"
"uniform sampler2D s_texture; \n"
@@ -168,7 +214,20 @@ static gchar *text_fragment_shader_download_RGB =
"{ \n"
" gl_FragColor = texture2D( s_texture, v_texCoord );\n"
"} \n";
-#endif
+#endif /* HAVE_GLES2 */
+
+/* *INDENT-ON* */
+
+struct _GstGLDownloadPrivate
+{
+ const gchar *YUY2_UYVY;
+ const gchar *I420_YV12;
+ const gchar *AYUV;
+ const gchar *vert_shader;
+
+ void (*do_rgb) (GstGLDisplay * display, GstGLDownload * download);
+ void (*do_yuv) (GstGLDisplay * display, GstGLDownload * download);
+};
GST_DEBUG_CATEGORY_STATIC (gst_gl_download_debug);
#define GST_CAT_DEFAULT gst_gl_download_debug
@@ -186,12 +245,17 @@ static void gst_gl_download_finalize (GObject * object);
static void
gst_gl_download_class_init (GstGLDownloadClass * klass)
{
+ g_type_class_add_private (klass, sizeof (GstGLDownloadPrivate));
+
G_OBJECT_CLASS (klass)->finalize = gst_gl_download_finalize;
}
static void
gst_gl_download_init (GstGLDownload * download)
{
+
+ download->priv = GST_GL_DOWNLOAD_GET_PRIVATE (download);
+
download->display = NULL;
g_mutex_init (&download->lock);
@@ -201,10 +265,8 @@ gst_gl_download_init (GstGLDownload * download)
download->in_texture = 0;
download->shader = NULL;
-#ifdef OPENGL_ES2
download->shader_attr_position_loc = 0;
download->shader_attr_texture_loc = 0;
-#endif
gst_video_info_init (&download->info);
}
@@ -219,10 +281,33 @@ GstGLDownload *
gst_gl_download_new (GstGLDisplay * display)
{
GstGLDownload *download;
+ GstGLDownloadPrivate *priv;
download = g_object_new (GST_TYPE_GL_DOWNLOAD, NULL);
download->display = g_object_ref (display);
+ priv = download->priv;
+
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ priv->YUY2_UYVY = text_shader_YUY2_UYVY_opengl;
+ priv->I420_YV12 = text_shader_I420_YV12_opengl;
+ priv->AYUV = text_shader_AYUV_opengl;
+ priv->vert_shader = text_vertex_shader_opengl;
+ priv->do_rgb = _do_download_draw_rgb_opengl;
+ priv->do_yuv = _do_download_draw_yuv_opengl;
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ priv->YUY2_UYVY = text_shader_YUY2_UYVY_gles2;
+ priv->I420_YV12 = text_shader_I420_YV12_gles2;
+ priv->AYUV = text_shader_AYUV_gles2;
+ priv->vert_shader = text_vertex_shader_gles2;
+ priv->do_rgb = _do_download_draw_rgb_gles2;
+ priv->do_yuv = _do_download_draw_yuv_gles2;
+ }
+#endif
return download;
}
@@ -574,7 +659,7 @@ GstGLDownload *
gst_gl_display_find_download_unlocked (GstGLDisplay * display,
GstVideoFormat v_format, guint out_width, guint out_height)
{
- GstGLDownload *ret;
+ GstGLDownload *ret = NULL;
GSList *walk;
walk = display->downloads;
@@ -641,6 +726,25 @@ _init_download (GstGLDisplay * display, GstGLDownload * download)
GST_TRACE ("initializing texture download for format %d", v_format);
+ if (USING_OPENGL (display)) {
+ switch (v_format) {
+ case GST_VIDEO_FORMAT_RGBx:
+ case GST_VIDEO_FORMAT_BGRx:
+ case GST_VIDEO_FORMAT_xRGB:
+ case GST_VIDEO_FORMAT_xBGR:
+ case GST_VIDEO_FORMAT_RGBA:
+ case GST_VIDEO_FORMAT_BGRA:
+ case GST_VIDEO_FORMAT_ARGB:
+ case GST_VIDEO_FORMAT_ABGR:
+ case GST_VIDEO_FORMAT_RGB:
+ case GST_VIDEO_FORMAT_BGR:
+ goto no_convert;
+ break;
+ default:
+ break;
+ }
+ }
+
switch (v_format) {
case GST_VIDEO_FORMAT_RGBx:
case GST_VIDEO_FORMAT_BGRx:
@@ -652,10 +756,6 @@ _init_download (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_ABGR:
case GST_VIDEO_FORMAT_RGB:
case GST_VIDEO_FORMAT_BGR:
- /* color space conversion is not needed */
-#ifndef OPENGL_ES2
- break;
-#endif
case GST_VIDEO_FORMAT_YUY2:
case GST_VIDEO_FORMAT_UYVY:
case GST_VIDEO_FORMAT_I420:
@@ -681,14 +781,19 @@ _init_download (GstGLDisplay * display, GstGLDownload * download)
/* setup the render buffer for depth */
glGenRenderbuffersEXT (1, &download->depth_buffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT, download->depth_buffer);
-#ifndef OPENGL_ES2
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
- out_width, out_height);
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
- out_width, out_height);
-#else
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
- out_width, out_height);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
+ out_width, out_height);
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
+ out_width, out_height);
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
+ out_width, out_height);
+ }
#endif
/* setup a first texture to render to */
@@ -754,10 +859,12 @@ _init_download (GstGLDisplay * display, GstGLDownload * download)
glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT,
GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, download->depth_buffer);
-#ifndef OPENGL_ES2
- glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT,
- GL_STENCIL_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT,
- download->depth_buffer);
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT,
+ GL_STENCIL_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT,
+ download->depth_buffer);
+ }
#endif
gst_gl_display_check_framebuffer_status ();
@@ -778,9 +885,38 @@ _init_download (GstGLDisplay * display, GstGLDownload * download)
g_assert_not_reached ();
}
+no_convert:
_init_download_shader (display, download);
}
+static gboolean
+_create_shader (GstGLDisplay * display, const gchar * vertex_src,
+ const gchar * fragment_src, GstGLShader ** out_shader)
+{
+ GstGLShader *shader;
+ GError *error;
+
+ g_return_val_if_fail (vertex_src != NULL || fragment_src != NULL, FALSE);
+
+ shader = gst_gl_shader_new (display);
+
+ if (vertex_src)
+ gst_gl_shader_set_vertex_source (shader, vertex_src);
+ if (fragment_src)
+ gst_gl_shader_set_fragment_source (shader, fragment_src);
+
+ if (!gst_gl_shader_compile (shader, &error)) {
+ gst_gl_display_set_error (display, "%s", error->message);
+ g_error_free (error);
+ gst_gl_shader_use (NULL);
+ g_object_unref (G_OBJECT (shader));
+ return FALSE;
+ }
+
+ *out_shader = shader;
+ return TRUE;
+}
+
static void
_init_download_shader (GstGLDisplay * display, GstGLDownload * download)
{
@@ -800,32 +936,19 @@ _init_download_shader (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_RGB:
case GST_VIDEO_FORMAT_BGR:
/* color space conversion is not needed */
-#ifdef OPENGL_ES2
+#if HAVE_GLES2
{
- /* glGetTexImage2D not available in OpenGL ES 2.0 */
- GError *error = NULL;
- download->shader = gst_gl_shader_new ();
-
- gst_gl_shader_set_vertex_source (download->shader,
- text_vertex_shader_download);
- gst_gl_shader_set_fragment_source (download->shader,
- text_fragment_shader_download_RGB);
-
- gst_gl_shader_compile (download->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- } else {
- download->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location (download->shader,
- "a_position");
- download->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location (download->shader,
- "a_texCoord");
+ if (USING_GLES2 (display)) {
+ /* glGetTexImage2D not available in OpenGL ES 2.0 */
+ if (_create_shader (display, text_vertex_shader_gles2,
+ text_shader_RGB_gles2, &download->shader)) {
+ download->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_position");
+ download->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_texCoord");
+ }
}
}
#endif
@@ -837,9 +960,6 @@ _init_download_shader (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_AYUV:
/* color space conversion is needed */
{
-#ifdef OPENGL_ES2
- GError *error = NULL;
-#endif
/* check if fragment shader is available, then load them
* GLSL is a requirement for download
*/
@@ -854,132 +974,65 @@ _init_download_shader (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_YUY2:
{
gchar text_shader_download_YUY2[2048];
+
sprintf (text_shader_download_YUY2,
- text_shader_download_YUY2_UYVY, "y2,u,y1,v");
-
- download->shader = gst_gl_shader_new ();
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (download->shader,
- text_shader_download_YUY2, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for downloading YUY2");
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- }
-#else
- gst_gl_shader_set_vertex_source (download->shader,
- text_vertex_shader_download);
- gst_gl_shader_set_fragment_source (download->shader,
- text_shader_download_YUY2);
-
- gst_gl_shader_compile (download->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- } else {
- download->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_position");
- download->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_texCoord");
+ download->priv->YUY2_UYVY, "y2,u,y1,v");
+
+ if (_create_shader (display, download->priv->vert_shader,
+ text_shader_download_YUY2, &download->shader)) {
+ if (USING_GLES2 (display)) {
+ download->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_position");
+ download->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_texCoord");
+ }
}
-#endif
}
break;
case GST_VIDEO_FORMAT_UYVY:
{
gchar text_shader_download_UYVY[2048];
- sprintf (text_shader_download_UYVY,
- text_shader_download_YUY2_UYVY, "v,y1,u,y2");
-
- download->shader = gst_gl_shader_new ();
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (download->shader,
- text_shader_download_UYVY, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for downloading UYVY");
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- }
-#else
- gst_gl_shader_set_vertex_source (download->shader,
- text_vertex_shader_download);
- gst_gl_shader_set_fragment_source (download->shader,
- text_shader_download_UYVY);
-
- gst_gl_shader_compile (download->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- } else {
- download->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_position");
- download->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_texCoord");
+ sprintf (text_shader_download_UYVY,
+ download->priv->YUY2_UYVY, "v,y1,u,y2");
+
+ if (_create_shader (display, download->priv->vert_shader,
+ text_shader_download_UYVY, &download->shader)) {
+ if (USING_GLES2 (display)) {
+ download->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_position");
+ download->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_texCoord");
+ }
}
-#endif
-
}
break;
case GST_VIDEO_FORMAT_I420:
case GST_VIDEO_FORMAT_YV12:
- download->shader = gst_gl_shader_new ();
- if (!gst_gl_shader_compile_and_check (download->shader,
- text_shader_download_I420_YV12,
- GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for downloading I420 or YV12");
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- }
+ {
+ _create_shader (display, download->priv->vert_shader,
+ download->priv->I420_YV12, &download->shader);
break;
+ }
case GST_VIDEO_FORMAT_AYUV:
- download->shader = gst_gl_shader_new ();
-
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (download->shader,
- text_shader_download_AYUV, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for downloading AYUV");
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- }
-#else
- gst_gl_shader_set_vertex_source (download->shader,
- text_vertex_shader_download);
- gst_gl_shader_set_fragment_source (download->shader,
- text_shader_download_AYUV);
-
- gst_gl_shader_compile (download->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (download->shader));
- download->shader = NULL;
- } else {
- download->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_position");
- download->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (download->shader, "a_texCoord");
+ {
+ if (_create_shader (display, download->priv->vert_shader,
+ download->priv->AYUV, &download->shader)) {
+ if (USING_GLES2 (display)) {
+ download->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_position");
+ download->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location (download->shader,
+ "a_texCoord");
+ }
}
-#endif
break;
+ }
default:
gst_gl_display_set_error (display,
"Unsupported download video format %d", v_format);
@@ -1022,7 +1075,7 @@ _do_download (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_RGB:
case GST_VIDEO_FORMAT_BGR:
/* color space conversion is not needed */
- _do_download_draw_rgb (display, download);
+ download->priv->do_rgb (display, download);
break;
case GST_VIDEO_FORMAT_YUY2:
case GST_VIDEO_FORMAT_UYVY:
@@ -1030,7 +1083,7 @@ _do_download (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_YV12:
case GST_VIDEO_FORMAT_AYUV:
/* color space conversion is needed */
- _do_download_draw_yuv (display, download);
+ download->priv->do_yuv (display, download);
break;
default:
gst_gl_display_set_error (display, "Unsupported download video format %d",
@@ -1040,19 +1093,77 @@ _do_download (GstGLDisplay * display, GstGLDownload * download)
}
}
-/* called by _do_download (in the gl thread) */
+#if HAVE_OPENGL
static void
-_do_download_draw_rgb (GstGLDisplay * display, GstGLDownload * download)
+_do_download_draw_rgb_opengl (GstGLDisplay * display, GstGLDownload * download)
{
GstVideoFormat v_format;
-#ifndef OPENGL_ES2
if (download->display->colorspace_conversion ==
GST_GL_DISPLAY_CONVERSION_GLSL)
glUseProgramObjectARB (0);
glEnable (GL_TEXTURE_RECTANGLE_ARB);
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, download->in_texture);
+
+ v_format = GST_VIDEO_INFO_FORMAT (&download->info);
+
+ switch (v_format) {
+ case GST_VIDEO_FORMAT_RGBA:
+ case GST_VIDEO_FORMAT_RGBx:
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
+ GL_UNSIGNED_BYTE, download->data[0]);
+ break;
+ case GST_VIDEO_FORMAT_xRGB:
+ case GST_VIDEO_FORMAT_ARGB:
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
#else
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
+#endif /* G_BYTE_ORDER */
+ break;
+ case GST_VIDEO_FORMAT_BGRx:
+ case GST_VIDEO_FORMAT_BGRA:
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
+ GL_UNSIGNED_BYTE, download->data[0]);
+ break;
+ case GST_VIDEO_FORMAT_xBGR:
+ case GST_VIDEO_FORMAT_ABGR:
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
+ GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
+#else
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
+ GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
+#endif /* G_BYTE_ORDER */
+ break;
+ case GST_VIDEO_FORMAT_RGB:
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGB,
+ GL_UNSIGNED_BYTE, download->data[0]);
+ break;
+ case GST_VIDEO_FORMAT_BGR:
+ glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGR,
+ GL_UNSIGNED_BYTE, download->data[0]);
+ break;
+ default:
+ gst_gl_display_set_error (display,
+ "Download video format inconsistency %d", v_format);
+ g_assert_not_reached ();
+ break;
+ }
+
+ glReadBuffer (GL_NONE);
+ glDisable (GL_TEXTURE_RECTANGLE_ARB);
+}
+#endif
+
+
+#if HAVE_GLES2
+static void
+_do_download_draw_rgb_gles2 (GstGLDisplay * display, GstGLDownload * download)
+{
+ GstVideoFormat v_format;
guint out_width, out_height;
const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f,
@@ -1094,32 +1205,17 @@ _do_download_draw_rgb (GstGLDisplay * display, GstGLDownload * download)
glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
glUseProgramObjectARB (0);
-#endif
v_format = GST_VIDEO_INFO_FORMAT (&download->info);
switch (v_format) {
case GST_VIDEO_FORMAT_RGBA:
case GST_VIDEO_FORMAT_RGBx:
-#ifndef OPENGL_ES2
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
- GL_UNSIGNED_BYTE, download->data[0]);
-#else
glReadPixels (0, 0, out_width, out_height, GL_RGBA, GL_UNSIGNED_BYTE,
download->data[0]);
-#endif
break;
case GST_VIDEO_FORMAT_xRGB:
case GST_VIDEO_FORMAT_ARGB:
-#ifndef OPENGL_ES2
-#if G_BYTE_ORDER == G_LITTLE_ENDIAN
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
- GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
-#else
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
- GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
-#endif /* G_BYTE_ORDER */
-#else /* OPENGL_ES2 */
#if G_BYTE_ORDER == G_LITTLE_ENDIAN
glReadPixels (0, 0, out_width, out_height, GL_BGRA,
GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
@@ -1127,41 +1223,16 @@ _do_download_draw_rgb (GstGLDisplay * display, GstGLDownload * download)
glReadPixels (0, 0, out_width, out_eight, GL_BGRA,
GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
#endif /* G_BYTE_ORDER */
-#endif /* !OPENGL_ES2 */
- break;
- case GST_VIDEO_FORMAT_BGRx:
- case GST_VIDEO_FORMAT_BGRA:
-#ifndef OPENGL_ES2
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGRA,
- GL_UNSIGNED_BYTE, download->data[0]);
-#endif
- break;
- case GST_VIDEO_FORMAT_xBGR:
- case GST_VIDEO_FORMAT_ABGR:
-#ifndef OPENGL_ES2
-#if G_BYTE_ORDER == G_LITTLE_ENDIAN
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
- GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
-#else
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGBA,
- GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
-#endif /* G_BYTE_ORDER */
-#endif /* !OPENGL_ES2 */
break;
case GST_VIDEO_FORMAT_RGB:
-#ifndef OPENGL_ES2
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_RGB,
- GL_UNSIGNED_BYTE, download->data[0]);
-#else
glReadPixels (0, 0, out_width, out_height, GL_RGB, GL_UNSIGNED_BYTE,
download->data[0]);
-#endif
break;
+ case GST_VIDEO_FORMAT_BGRx:
+ case GST_VIDEO_FORMAT_BGRA:
+ case GST_VIDEO_FORMAT_xBGR:
+ case GST_VIDEO_FORMAT_ABGR:
case GST_VIDEO_FORMAT_BGR:
-#ifndef OPENGL_ES2
- glGetTexImage (GL_TEXTURE_RECTANGLE_ARB, 0, GL_BGR,
- GL_UNSIGNED_BYTE, download->data[0]);
-#endif
break;
default:
gst_gl_display_set_error (display,
@@ -1169,42 +1240,21 @@ _do_download_draw_rgb (GstGLDisplay * display, GstGLDownload * download)
g_assert_not_reached ();
break;
}
-
-#ifndef OPENGL_ES2
- glReadBuffer (GL_NONE);
- glDisable (GL_TEXTURE_RECTANGLE_ARB);
-#endif
}
+#endif
-
-/* called by _do_download (in the gl thread) */
+#if HAVE_OPENGL
static void
-_do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
+_do_download_draw_yuv_opengl (GstGLDisplay * display, GstGLDownload * download)
{
GstVideoFormat v_format;
guint out_width, out_height;
-#ifndef OPENGL_ES2
GLenum multipleRT[] = {
GL_COLOR_ATTACHMENT0_EXT,
GL_COLOR_ATTACHMENT1_EXT,
GL_COLOR_ATTACHMENT2_EXT
};
-#else
- GLint viewport_dim[4];
-
- const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f,
- 1.0f, 0.0f,
- -1.0f, -1.0f, 0.0f,
- 0.0f, .0f,
- -1.0f, 1.0f, 0.0f,
- 0.0f, 1.0f,
- 1.0f, 1.0f, 0.0f,
- 1.0f, 1.0f
- };
-
- GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
-#endif
out_width = GST_VIDEO_INFO_WIDTH (&download->info);
out_height = GST_VIDEO_INFO_HEIGHT (&download->info);
@@ -1215,7 +1265,6 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, download->fbo);
-#ifndef OPENGL_ES2
glPushAttrib (GL_VIEWPORT_BIT);
glMatrixMode (GL_PROJECTION);
@@ -1226,9 +1275,6 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
glMatrixMode (GL_MODELVIEW);
glPushMatrix ();
glLoadIdentity ();
-#else /* OPENGL_ES2 */
- glGetIntegerv (GL_VIEWPORT, viewport_dim);
-#endif
glViewport (0, 0, out_width, out_height);
@@ -1237,27 +1283,15 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_UYVY:
case GST_VIDEO_FORMAT_AYUV:
{
-#ifndef OPENGL_ES2
glDrawBuffer (GL_COLOR_ATTACHMENT0_EXT);
-#endif
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
gst_gl_shader_use (download->shader);
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#else
- glVertexAttribPointer (download->shader_attr_position_loc, 3,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- glVertexAttribPointer (download->shader_attr_texture_loc, 2,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
-
- glEnableVertexAttribArray (download->shader_attr_position_loc);
- glEnableVertexAttribArray (download->shader_attr_texture_loc);
-#endif
glActiveTextureARB (GL_TEXTURE0_ARB);
gst_gl_shader_set_uniform_1i (download->shader, "tex", 0);
@@ -1268,19 +1302,15 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
case GST_VIDEO_FORMAT_I420:
case GST_VIDEO_FORMAT_YV12:
{
-#ifndef OPENGL_ES2
glDrawBuffers (3, multipleRT);
-#endif
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
gst_gl_shader_use (download->shader);
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#endif
glActiveTextureARB (GL_TEXTURE0_ARB);
gst_gl_shader_set_uniform_1i (download->shader, "tex", 0);
@@ -1297,7 +1327,6 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
}
-#ifndef OPENGL_ES2
glBegin (GL_QUADS);
glTexCoord2i (0, 0);
glVertex2f (-1.0f, -1.0f);
@@ -1310,9 +1339,6 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
glEnd ();
glDrawBuffer (GL_NONE);
-#else /* OPENGL_ES2 */
- glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
-#endif
/* don't check if GLSL is available
* because download yuv is not available
@@ -1320,24 +1346,17 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
*/
glUseProgramObjectARB (0);
-#ifndef OPENGL_ES2
glDisable (GL_TEXTURE_RECTANGLE_ARB);
glMatrixMode (GL_PROJECTION);
glPopMatrix ();
glMatrixMode (GL_MODELVIEW);
glPopMatrix ();
glPopAttrib ();
-#else
- glViewport (viewport_dim[0], viewport_dim[1], viewport_dim[2],
- viewport_dim[3]);
-#endif
gst_gl_display_check_framebuffer_status ();
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, download->fbo);
-#ifndef OPENGL_ES2
glReadBuffer (GL_COLOR_ATTACHMENT0_EXT);
-#endif
switch (v_format) {
case GST_VIDEO_FORMAT_AYUV:
@@ -1364,17 +1383,13 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
glReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE,
download->data[0]);
-#ifndef OPENGL_ES2
glReadBuffer (GL_COLOR_ATTACHMENT1_EXT);
-#endif
glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
download->data[1]);
-#ifndef OPENGL_ES2
glReadBuffer (GL_COLOR_ATTACHMENT2_EXT);
-#endif
glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
@@ -1386,17 +1401,13 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
glReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE,
download->data[0]);
-#ifndef OPENGL_ES2
glReadBuffer (GL_COLOR_ATTACHMENT1_EXT);
-#endif
glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
download->data[2]);
-#ifndef OPENGL_ES2
glReadBuffer (GL_COLOR_ATTACHMENT2_EXT);
-#endif
glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
@@ -1409,11 +1420,167 @@ _do_download_draw_yuv (GstGLDisplay * display, GstGLDownload * download)
"Download video format inconsistensy %d", v_format);
g_assert_not_reached ();
}
-#ifndef OPENGL_ES2
glReadBuffer (GL_NONE);
+
+ gst_gl_display_check_framebuffer_status ();
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
+}
#endif
+#if HAVE_GLES2
+static void
+_do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download)
+{
+ GstVideoFormat v_format;
+ guint out_width, out_height;
+
+ GLint viewport_dim[4];
+
+ const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f,
+ 1.0f, 0.0f,
+ -1.0f, -1.0f, 0.0f,
+ 0.0f, .0f,
+ -1.0f, 1.0f, 0.0f,
+ 0.0f, 1.0f,
+ 1.0f, 1.0f, 0.0f,
+ 1.0f, 1.0f
+ };
+
+ GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
+
+ out_width = GST_VIDEO_INFO_WIDTH (&download->info);
+ out_height = GST_VIDEO_INFO_HEIGHT (&download->info);
+ v_format = GST_VIDEO_INFO_FORMAT (&download->info);
+
+ GST_TRACE ("doing YUV download of texture:%u (%ux%u) using fbo:%u",
+ download->in_texture, out_width, out_height, download->fbo);
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, download->fbo);
+
+ glGetIntegerv (GL_VIEWPORT, viewport_dim);
+
+ glViewport (0, 0, out_width, out_height);
+
+ switch (v_format) {
+ case GST_VIDEO_FORMAT_YUY2:
+ case GST_VIDEO_FORMAT_UYVY:
+ case GST_VIDEO_FORMAT_AYUV:
+ {
+ glClearColor (0.0, 0.0, 0.0, 0.0);
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ gst_gl_shader_use (download->shader);
+
+ glVertexAttribPointer (download->shader_attr_position_loc, 3,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ glVertexAttribPointer (download->shader_attr_texture_loc, 2,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+
+ glEnableVertexAttribArray (download->shader_attr_position_loc);
+ glEnableVertexAttribArray (download->shader_attr_texture_loc);
+
+ glActiveTextureARB (GL_TEXTURE0_ARB);
+ gst_gl_shader_set_uniform_1i (download->shader, "tex", 0);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, download->in_texture);
+ }
+ break;
+
+ case GST_VIDEO_FORMAT_I420:
+ case GST_VIDEO_FORMAT_YV12:
+ {
+ glClearColor (0.0, 0.0, 0.0, 0.0);
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ gst_gl_shader_use (download->shader);
+
+ glActiveTextureARB (GL_TEXTURE0_ARB);
+ gst_gl_shader_set_uniform_1i (download->shader, "tex", 0);
+ gst_gl_shader_set_uniform_1f (download->shader, "w", (gfloat) out_width);
+ gst_gl_shader_set_uniform_1f (download->shader, "h", (gfloat) out_height);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, download->in_texture);
+ }
+ break;
+
+ default:
+ break;
+ gst_gl_display_set_error (display,
+ "Download video format inconsistensy %d", v_format);
+
+ }
+
+ glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
+
+ /* don't check if GLSL is available
+ * because download yuv is not available
+ * without GLSL (whereas rgb is)
+ */
+ glUseProgramObjectARB (0);
+
+ glViewport (viewport_dim[0], viewport_dim[1], viewport_dim[2],
+ viewport_dim[3]);
+
+ gst_gl_display_check_framebuffer_status ();
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, download->fbo);
+
+ switch (v_format) {
+ case GST_VIDEO_FORMAT_AYUV:
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+ glReadPixels (0, 0, out_width, out_height, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
+#else
+ glReadPixels (0, 0, out_width, out_height, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
+#endif
+ break;
+ case GST_VIDEO_FORMAT_YUY2:
+ case GST_VIDEO_FORMAT_UYVY:
+#if G_BYTE_ORDER == G_LITTLE_ENDIAN
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2, out_height, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8_REV, download->data[0]);
+#else
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2, out_height, GL_BGRA,
+ GL_UNSIGNED_INT_8_8_8_8, download->data[0]);
+#endif
+ break;
+ case GST_VIDEO_FORMAT_I420:
+ {
+ glReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[0]);
+
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
+ GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[1]);
+
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
+ GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[2]);
+ }
+ break;
+ case GST_VIDEO_FORMAT_YV12:
+ {
+ glReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[0]);
+
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
+ GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[2]);
+
+ glReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2,
+ GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE,
+ download->data[1]);
+ }
+ break;
+ default:
+ break;
+ gst_gl_display_set_error (display,
+ "Download video format inconsistensy %d", v_format);
+ g_assert_not_reached ();
+ }
+
gst_gl_display_check_framebuffer_status ();
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
}
+#endif
diff --git a/gst-libs/gst/gl/gstgldownload.h b/gst-libs/gst/gl/gstgldownload.h
index ed9472839..a06677361 100644
--- a/gst-libs/gst/gl/gstgldownload.h
+++ b/gst-libs/gst/gl/gstgldownload.h
@@ -24,8 +24,8 @@
#include <gst/video/video.h>
#include <gst/gstmemory.h>
-#include "gstglshader.h"
#include "gstgldisplay.h"
+#include "gstglshader.h"
G_BEGIN_DECLS
@@ -43,6 +43,7 @@ GType gst_gl_download_get_type (void);
typedef struct _GstGLDownload GstGLDownload;
typedef struct _GstGLDownloadClass GstGLDownloadClass;
+typedef struct _GstGLDownloadPrivate GstGLDownloadPrivate;
/**
* GstGLDownload
@@ -74,10 +75,10 @@ struct _GstGLDownload
GLuint in_texture;
GLuint out_texture[GST_VIDEO_MAX_PLANES];
GstGLShader *shader;
-#ifdef OPENGL_ES2
GLint shader_attr_position_loc;
GLint shader_attr_texture_loc;
-#endif
+
+ GstGLDownloadPrivate *priv;
gpointer _reserved[GST_PADDING];
};
@@ -97,12 +98,12 @@ struct _GstGLDownloadClass
*
* The currently supported formats that can be downloaded
*/
-#ifndef OPENGL_ES2
+#if !HAVE_GLES2
# define GST_GL_DOWNLOAD_FORMATS "{ RGB, RGBx, RGBA, BGR, BGRx, BGRA, xRGB, " \
"xBGR, ARGB, ABGR, I420, YV12, YUY2, UYVY, AYUV }"
-#else /* OPENGL_ES2 */
+#else /* HAVE_GLES2 */
# define GST_GL_DOWNLOAD_FORMATS "{ RGB, RGBx, RGBA, I420, YV12, YUY2, UYVY, AYUV }"
-#endif /* !OPENGL_ES2 */
+#endif /* !HAVE_GLES2 */
/**
* GST_GL_DOWNLOAD_VIDEO_CAPS:
diff --git a/gst-libs/gst/gl/gstglfilter.c b/gst-libs/gst/gl/gstglfilter.c
index 4c80b90b9..9a91a9967 100644
--- a/gst-libs/gst/gl/gstglfilter.c
+++ b/gst-libs/gst/gl/gstglfilter.c
@@ -1075,7 +1075,7 @@ gst_gl_filter_render_to_target (GstGLFilter * filter, gboolean resize,
in_width, 0, in_height, GST_GL_DISPLAY_PROJECTION_ORTHO2D, data);
}
-#ifndef OPENGL_ES2
+#if HAVE_OPENGL
static void
_draw_with_shader_cb (gint width, gint height, guint texture, gpointer stuff)
{
@@ -1116,6 +1116,9 @@ void
gst_gl_filter_render_to_target_with_shader (GstGLFilter * filter,
gboolean resize, GLuint input, GLuint target, GstGLShader * shader)
{
+ g_return_if_fail (gst_gl_display_get_gl_api (filter->display) &
+ GST_GL_API_OPENGL);
+
filter->default_shader = shader;
gst_gl_filter_render_to_target (filter, resize, input, target,
_draw_with_shader_cb, filter);
@@ -1153,4 +1156,4 @@ gst_gl_filter_draw_texture (GstGLFilter * filter, GLuint texture,
glEnd ();
}
-#endif
+#endif /* HAVE_OPENGL */
diff --git a/gst-libs/gst/gl/gstglfilter.h b/gst-libs/gst/gl/gstglfilter.h
index 6d6d9b95d..405960393 100644
--- a/gst-libs/gst/gl/gstglfilter.h
+++ b/gst-libs/gst/gl/gstglfilter.h
@@ -124,12 +124,12 @@ gboolean gst_gl_filter_filter_texture (GstGLFilter * filter, GstBuffer * inbuf,
void gst_gl_filter_render_to_target (GstGLFilter *filter, gboolean resize, GLuint input,
GLuint target, GLCB func, gpointer data);
-#ifndef OPENGL_ES2
+#if HAVE_OPENGL
void gst_gl_filter_render_to_target_with_shader (GstGLFilter * filter, gboolean resize,
GLuint input, GLuint target, GstGLShader *shader);
void gst_gl_filter_draw_texture (GstGLFilter *filter, GLuint texture, guint width, guint height);
-#endif /* !OPENGL_ES2 */
+#endif /* HAVE_OPENGL */
G_END_DECLS
diff --git a/gst-libs/gst/gl/gstglmemory.c b/gst-libs/gst/gl/gstglmemory.c
index 611929bec..25db723be 100644
--- a/gst-libs/gst/gl/gstglmemory.c
+++ b/gst-libs/gst/gl/gstglmemory.c
@@ -40,6 +40,12 @@
* Data is uploaded or downloaded from the GPU as is necessary.
*/
+#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)
+
GST_DEBUG_CATEGORY_STATIC (GST_CAT_GL_MEMORY);
#define GST_CAT_DEFUALT GST_CAT_GL_MEMORY
@@ -220,22 +226,29 @@ _gl_mem_copy_thread (GstGLDisplay * display, gpointer data)
glGenRenderbuffersEXT (1, &rboId);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT, rboId);
-#ifndef OPENGL_ES2
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT, width,
- height);
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
- width, height);
-#else
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
- width, height);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT, width,
+ height);
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
+ width, height);
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
+ width, height);
+ }
#endif
/* attach the renderbuffer to depth attachment point */
glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT,
GL_RENDERBUFFER_EXT, rboId);
-#ifndef OPENGL_ES2
- glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT,
- GL_STENCIL_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, rboId);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT,
+ GL_STENCIL_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, rboId);
+ }
#endif
glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
@@ -264,7 +277,7 @@ _gl_mem_copy_thread (GstGLDisplay * display, gpointer data)
GST_CAT_ERROR (GST_CAT_GL_MEMORY,
"GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS");
break;
-#ifndef OPENGL_ES2
+#if HAVE_OPENGL
case GL_FRAMEBUFFER_UNDEFINED:
GST_CAT_ERROR (GST_CAT_GL_MEMORY, "GL_FRAMEBUFFER_UNDEFINED");
break;
diff --git a/gst-libs/gst/gl/gstglshader.c b/gst-libs/gst/gl/gstglshader.c
index 89087fe92..ddbaa3b85 100644
--- a/gst-libs/gst/gl/gstglshader.c
+++ b/gst-libs/gst/gl/gstglshader.c
@@ -27,6 +27,12 @@
#define GST_GL_SHADER_GET_PRIVATE(o) \
(G_TYPE_INSTANCE_GET_PRIVATE((o), GST_GL_TYPE_SHADER, GstGLShaderPrivate))
+#define USING_OPENGL(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL)
+#define USING_OPENGL3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL3)
+#define USING_GLES(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES)
+#define USING_GLES2(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES2)
+#define USING_GLES3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES3)
+
enum
{
PROP_0,
@@ -251,9 +257,13 @@ gst_gl_shader_init (GstGLShader * self)
}
GstGLShader *
-gst_gl_shader_new (void)
+gst_gl_shader_new (GstGLDisplay * display)
{
- return g_object_new (GST_GL_TYPE_SHADER, NULL);
+ GstGLShader *shader = g_object_new (GST_GL_TYPE_SHADER, NULL);
+
+ shader->display = display;
+
+ return shader;
}
gboolean
@@ -270,7 +280,7 @@ gst_gl_shader_compile (GstGLShader * shader, GError ** error)
GstGLShaderPrivate *priv;
gchar info_buffer[2048];
- GLsizei len = 0;
+ gint len = 0;
GLint status = GL_FALSE;
g_return_val_if_fail (GST_GL_IS_SHADER (shader), FALSE);
@@ -293,12 +303,15 @@ gst_gl_shader_compile (GstGLShader * shader, GError ** error)
glGetObjectParameterivARB (priv->vertex_handle,
GL_OBJECT_COMPILE_STATUS_ARB, &status);
-#ifndef OPENGL_ES2
- glGetInfoLogARB (priv->vertex_handle,
- sizeof (info_buffer) - 1, &len, info_buffer);
-#else
- glGetShaderInfoLog (priv->vertex_handle,
- sizeof (info_buffer) - 1, &len, info_buffer);
+#if HAVE_OPENGL
+ if (USING_OPENGL (shader->display))
+ glGetInfoLogARB (priv->vertex_handle,
+ sizeof (info_buffer) - 1, &len, info_buffer);
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (shader->display))
+ glGetShaderInfoLog (priv->vertex_handle,
+ sizeof (info_buffer) - 1, &len, info_buffer);
#endif
info_buffer[len] = '\0';
@@ -329,12 +342,15 @@ gst_gl_shader_compile (GstGLShader * shader, GError ** error)
glGetObjectParameterivARB (priv->fragment_handle,
GL_OBJECT_COMPILE_STATUS_ARB, &status);
-#ifndef OPENGL_ES2
- glGetInfoLogARB (priv->fragment_handle,
- sizeof (info_buffer) - 1, &len, info_buffer);
-#else
- glGetShaderInfoLog (priv->fragment_handle,
- sizeof (info_buffer) - 1, &len, info_buffer);
+#if HAVE_OPENGL
+ if (USING_OPENGL (shader->display))
+ glGetInfoLogARB (priv->fragment_handle,
+ sizeof (info_buffer) - 1, &len, info_buffer);
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (shader->display))
+ glGetShaderInfoLog (priv->fragment_handle,
+ sizeof (info_buffer) - 1, &len, info_buffer);
#endif
info_buffer[len] = '\0';
if (status != GL_TRUE) {
@@ -356,10 +372,13 @@ gst_gl_shader_compile (GstGLShader * shader, GError ** error)
/* if nothing failed link shaders */
glLinkProgramARB (priv->program_handle);
-#ifndef OPENGL_ES2
- glGetObjectParameterivARB (priv->program_handle, GL_LINK_STATUS, &status);
-#else
- glGetProgramiv (priv->program_handle, GL_LINK_STATUS, &status);
+#if HAVE_OPENGL
+ if (USING_OPENGL (shader->display))
+ glGetObjectParameterivARB (priv->program_handle, GL_LINK_STATUS, &status);
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (shader->display))
+ glGetProgramiv (priv->program_handle, GL_LINK_STATUS, &status);
#endif
glGetInfoLogARB (priv->program_handle,
@@ -400,10 +419,13 @@ gst_gl_shader_release (GstGLShader * shader)
if (priv->vertex_handle) { /* not needed but nvidia doesn't care to respect the spec */
GST_TRACE ("finalizing vertex shader %u", priv->vertex_handle);
-#ifndef OPENGL_ES2
- glDeleteObjectARB (priv->vertex_handle);
-#else
- glDeleteShader (priv->vertex_handle);
+#if HAVE_OPENGL
+ if (USING_OPENGL (shader->display))
+ glDeleteObjectARB (priv->vertex_handle);
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (shader->display))
+ glDeleteShader (priv->vertex_handle);
#endif
/* err = glGetError (); */
@@ -415,10 +437,14 @@ gst_gl_shader_release (GstGLShader * shader)
if (priv->fragment_handle) {
GST_TRACE ("finalizing fragment shader %u", priv->fragment_handle);
-#ifndef OPENGL_ES2
- glDeleteObjectARB (priv->fragment_handle);
-#else
- glDeleteShader (priv->fragment_handle);
+
+#if HAVE_OPENGL
+ if (USING_OPENGL (shader->display))
+ glDeleteObjectARB (priv->fragment_handle);
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (shader->display))
+ glDeleteShader (priv->fragment_handle);
#endif
/* err = glGetError (); */
@@ -748,7 +774,7 @@ gst_gl_shader_set_uniform_4iv (GstGLShader * shader, const gchar * name,
void
gst_gl_shader_set_uniform_matrix_2fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat * value)
+ gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -762,11 +788,9 @@ gst_gl_shader_set_uniform_matrix_2fv (GstGLShader * shader, const gchar * name,
glUniformMatrix2fvARB (location, count, transpose, value);
}
-#ifndef OPENGL_ES2
void
-gst_gl_shader_set_uniform_matrix_2x3fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_3fv (GstGLShader * shader, const gchar * name,
+ gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -777,13 +801,12 @@ gst_gl_shader_set_uniform_matrix_2x3fv (GstGLShader * shader,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix2x3fv (location, count, transpose, value);
+ glUniformMatrix3fvARB (location, count, transpose, value);
}
void
-gst_gl_shader_set_uniform_matrix_2x4fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_4fv (GstGLShader * shader, const gchar * name,
+ gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -794,13 +817,13 @@ gst_gl_shader_set_uniform_matrix_2x4fv (GstGLShader * shader,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix2x4fv (location, count, transpose, value);
+ glUniformMatrix4fvARB (location, count, transpose, value);
}
-#endif
+#if HAVE_OPENGL
void
-gst_gl_shader_set_uniform_matrix_3fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_2x3fv (GstGLShader * shader,
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -811,14 +834,12 @@ gst_gl_shader_set_uniform_matrix_3fv (GstGLShader * shader, const gchar * name,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix3fvARB (location, count, transpose, value);
+ glUniformMatrix2x3fv (location, count, transpose, value);
}
-#ifndef OPENGL_ES2
void
-gst_gl_shader_set_uniform_matrix_3x2fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_2x4fv (GstGLShader * shader,
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -829,13 +850,12 @@ gst_gl_shader_set_uniform_matrix_3x2fv (GstGLShader * shader,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix3x2fv (location, count, transpose, value);
+ glUniformMatrix2x4fv (location, count, transpose, value);
}
void
-gst_gl_shader_set_uniform_matrix_3x4fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_3x2fv (GstGLShader * shader,
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -846,13 +866,12 @@ gst_gl_shader_set_uniform_matrix_3x4fv (GstGLShader * shader,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix3x4fv (location, count, transpose, value);
+ glUniformMatrix3x2fv (location, count, transpose, value);
}
-#endif
void
-gst_gl_shader_set_uniform_matrix_4fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat * value)
+gst_gl_shader_set_uniform_matrix_3x4fv (GstGLShader * shader,
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -863,14 +882,12 @@ gst_gl_shader_set_uniform_matrix_4fv (GstGLShader * shader, const gchar * name,
location = glGetUniformLocationARB (priv->program_handle, name);
- glUniformMatrix4fvARB (location, count, transpose, value);
+ glUniformMatrix3x4fv (location, count, transpose, value);
}
-#ifndef OPENGL_ES2
void
gst_gl_shader_set_uniform_matrix_4x2fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -886,8 +903,7 @@ gst_gl_shader_set_uniform_matrix_4x2fv (GstGLShader * shader,
void
gst_gl_shader_set_uniform_matrix_4x3fv (GstGLShader * shader,
- const gchar * name, GLsizei count, GLboolean transpose,
- const GLfloat * value)
+ const gchar * name, gint count, gboolean transpose, const gfloat * value)
{
GstGLShaderPrivate *priv;
GLint location = -1;
@@ -900,7 +916,7 @@ gst_gl_shader_set_uniform_matrix_4x3fv (GstGLShader * shader,
glUniformMatrix4x3fv (location, count, transpose, value);
}
-#endif
+#endif /* HAVE_OPENGL */
GLint
gst_gl_shader_get_attribute_location (GstGLShader * shader, const gchar * name)
diff --git a/gst-libs/gst/gl/gstglshader.h b/gst-libs/gst/gl/gstglshader.h
index c193d489e..27ba5830f 100644
--- a/gst-libs/gst/gl/gstglshader.h
+++ b/gst-libs/gst/gl/gstglshader.h
@@ -21,18 +21,17 @@
#ifndef __GST_GL_SHADER_H__
#define __GST_GL_SHADER_H__
-/* OpenGL 2.0 for Embedded Systems */
-#ifdef OPENGL_ES2
-#include <GLES2/gl2.h>
-#include "gstgles2.h"
-/* OpenGL for usual systems */
-#else
-#include <GL/glew.h>
+#ifdef HAVE_CONFIG_H
+#include "config.h"
#endif
+
+#include "gstgldisplay.h"
#include <gst/gst.h>
G_BEGIN_DECLS
+typedef struct _GstGLDisplay GstGLDisplay;
+
#define GST_GL_TYPE_SHADER (gst_gl_shader_get_type())
#define GST_GL_SHADER(o) (G_TYPE_CHECK_INSTANCE_CAST((o), GST_GL_TYPE_SHADER, GstGLShader))
#define GST_GL_SHADER_CLASS(k) (G_TYPE_CHECK_CLASS((k), GST_GL_TYPE_SHADER, GstGLShaderClass))
@@ -60,6 +59,9 @@ typedef struct _GstGLShaderClass GstGLShaderClass;
struct _GstGLShader {
/*< private >*/
GObject parent;
+
+ GstGLDisplay *display;
+
GstGLShaderPrivate *priv;
};
@@ -73,68 +75,51 @@ struct _GstGLShaderClass {
GQuark gst_gl_shader_error_quark (void);
GType gst_gl_shader_get_type (void);
-GstGLShader * gst_gl_shader_new (void);
+GstGLShader * gst_gl_shader_new (GstGLDisplay *display);
-void gst_gl_shader_set_vertex_source (GstGLShader *shader,
- const gchar *src);
-void gst_gl_shader_set_fragment_source (GstGLShader *shader,
- const gchar *src);
-const gchar * gst_gl_shader_get_vertex_source (GstGLShader *shader);
+void gst_gl_shader_set_vertex_source (GstGLShader *shader, const gchar *src);
+void gst_gl_shader_set_fragment_source (GstGLShader *shader, const gchar *src);
+const gchar * gst_gl_shader_get_vertex_source (GstGLShader *shader);
const gchar * gst_gl_shader_get_fragment_source (GstGLShader *shader);
-void gst_gl_shader_set_active (GstGLShader *shader,
- gboolean active);
-
-gboolean gst_gl_shader_is_compiled (GstGLShader *shader);
-
-gboolean gst_gl_shader_compile (GstGLShader *shader, GError **error);
+void gst_gl_shader_set_active (GstGLShader *shader, gboolean active);
+gboolean gst_gl_shader_is_compiled (GstGLShader *shader);
+gboolean gst_gl_shader_compile (GstGLShader *shader, GError **error);
gboolean gst_gl_shader_compile_and_check (GstGLShader *shader, const gchar *source, GstGLShaderSourceType type);
+
void gst_gl_shader_release (GstGLShader *shader);
-void gst_gl_shader_use (GstGLShader *shader);
-
-void gst_gl_shader_set_uniform_1i (GstGLShader *shader, const gchar *name, gint value);
-void gst_gl_shader_set_uniform_1iv (GstGLShader *shader, const gchar *name, guint count, gint * value);
-void gst_gl_shader_set_uniform_1f (GstGLShader *shader, const gchar *name, gfloat value);
-void gst_gl_shader_set_uniform_1fv (GstGLShader *shader, const gchar *name, guint count, gfloat * value);
-void gst_gl_shader_set_uniform_2i (GstGLShader *shader, const gchar *name, gint v0, gint v1);
-void gst_gl_shader_set_uniform_2iv (GstGLShader *shader, const gchar *name, guint count, gint * value);
-void gst_gl_shader_set_uniform_2f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1);
-void gst_gl_shader_set_uniform_2fv (GstGLShader *shader, const gchar *name, guint count, gfloat * value);
-void gst_gl_shader_set_uniform_3i (GstGLShader *shader, const gchar *name, gint v0, gint v1, gint v2);
-void gst_gl_shader_set_uniform_3iv (GstGLShader *shader, const gchar *name, guint count, gint * value);
-void gst_gl_shader_set_uniform_3f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1, gfloat v2);
-void gst_gl_shader_set_uniform_3fv (GstGLShader *shader, const gchar *name, guint count, gfloat * value);
-void gst_gl_shader_set_uniform_4i (GstGLShader *shader, const gchar *name, gint v0, gint v1, gint v2, gint v3);
-void gst_gl_shader_set_uniform_4iv (GstGLShader *shader, const gchar *name, guint count, gint * value);
-void gst_gl_shader_set_uniform_4f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1, gfloat v2, gfloat v3);
-void gst_gl_shader_set_uniform_4fv (GstGLShader *shader, const gchar *name, guint count, gfloat * value);
-void gst_gl_shader_set_uniform_matrix_2fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-#ifndef OPENGL_ES2
-void gst_gl_shader_set_uniform_matrix_2x3fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-void gst_gl_shader_set_uniform_matrix_2x4fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-#endif
-void gst_gl_shader_set_uniform_matrix_3fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-#ifndef OPENGL_ES2
-void gst_gl_shader_set_uniform_matrix_3x2fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-void gst_gl_shader_set_uniform_matrix_3x4fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-#endif
-void gst_gl_shader_set_uniform_matrix_4fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-#ifndef OPENGL_ES2
-void gst_gl_shader_set_uniform_matrix_4x2fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
-void gst_gl_shader_set_uniform_matrix_4x3fv (GstGLShader * shader, const gchar * name,
- GLsizei count, GLboolean transpose, const GLfloat* value);
+void gst_gl_shader_use (GstGLShader *shader);
+
+void gst_gl_shader_set_uniform_1i (GstGLShader *shader, const gchar *name, gint value);
+void gst_gl_shader_set_uniform_1iv (GstGLShader *shader, const gchar *name, guint count, gint *value);
+void gst_gl_shader_set_uniform_1f (GstGLShader *shader, const gchar *name, gfloat value);
+void gst_gl_shader_set_uniform_1fv (GstGLShader *shader, const gchar *name, guint count, gfloat *value);
+void gst_gl_shader_set_uniform_2i (GstGLShader *shader, const gchar *name, gint v0, gint v1);
+void gst_gl_shader_set_uniform_2iv (GstGLShader *shader, const gchar *name, guint count, gint *value);
+void gst_gl_shader_set_uniform_2f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1);
+void gst_gl_shader_set_uniform_2fv (GstGLShader *shader, const gchar *name, guint count, gfloat *value);
+void gst_gl_shader_set_uniform_3i (GstGLShader *shader, const gchar *name, gint v0, gint v1, gint v2);
+void gst_gl_shader_set_uniform_3iv (GstGLShader *shader, const gchar *name, guint count, gint * value);
+void gst_gl_shader_set_uniform_3f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1, gfloat v2);
+void gst_gl_shader_set_uniform_3fv (GstGLShader *shader, const gchar *name, guint count, gfloat *value);
+void gst_gl_shader_set_uniform_4i (GstGLShader *shader, const gchar *name, gint v0, gint v1, gint v2, gint v3);
+void gst_gl_shader_set_uniform_4iv (GstGLShader *shader, const gchar *name, guint count, gint *value);
+void gst_gl_shader_set_uniform_4f (GstGLShader *shader, const gchar *name, gfloat v0, gfloat v1, gfloat v2, gfloat v3);
+void gst_gl_shader_set_uniform_4fv (GstGLShader *shader, const gchar *name, guint count, gfloat *value);
+void gst_gl_shader_set_uniform_matrix_2fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_3fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_4fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+#if HAVE_OPENGL
+void gst_gl_shader_set_uniform_matrix_2x3fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_2x4fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_3x2fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_3x4fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_4x2fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
+void gst_gl_shader_set_uniform_matrix_4x3fv (GstGLShader *shader, const gchar *name, gint count, gboolean transpose, const gfloat* value);
#endif
-GLint gst_gl_shader_get_attribute_location (GstGLShader *shader, const gchar *name);
-void gst_gl_shader_bind_attribute_location (GstGLShader * shader, GLuint index, const gchar * name);
+gint gst_gl_shader_get_attribute_location (GstGLShader *shader, const gchar *name);
+void gst_gl_shader_bind_attribute_location (GstGLShader * shader, guint index, const gchar * name);
G_END_DECLS
diff --git a/gst-libs/gst/gl/gstglshadervariables.c b/gst-libs/gst/gl/gstglshadervariables.c
index f97ef09a0..112510512 100644
--- a/gst-libs/gst/gl/gstglshadervariables.c
+++ b/gst-libs/gst/gl/gstglshadervariables.c
@@ -554,7 +554,19 @@ gst_gl_shadervariable_set (GstGLShader * shader,
(float *) ret->value);
break;
-#ifndef OPENGL_ES2
+ case _mat3:
+ case _mat3x3:
+ gst_gl_shader_set_uniform_matrix_3fv (shader, ret->name, ret->count, 0,
+ (float *) ret->value);
+ break;
+
+ case _mat4:
+ case _mat4x4:
+ gst_gl_shader_set_uniform_matrix_4fv (shader, ret->name, ret->count, 0,
+ (float *) ret->value);
+ break;
+
+#if HAVE_OPENGL
case _mat2x3:
gst_gl_shader_set_uniform_matrix_2x3fv (shader, ret->name, ret->count, 0,
(float *) ret->value);
@@ -574,13 +586,7 @@ gst_gl_shadervariable_set (GstGLShader * shader,
gst_gl_shader_set_uniform_matrix_4x2fv (shader, ret->name, ret->count, 0,
(float *) ret->value);
break;
-#endif
- case _mat3:
- case _mat3x3:
- gst_gl_shader_set_uniform_matrix_3fv (shader, ret->name, ret->count, 0,
- (float *) ret->value);
- break;
-#ifndef OPENGL_ES2
+
case _mat3x4:
gst_gl_shader_set_uniform_matrix_3x4fv (shader, ret->name, ret->count, 0,
(float *) ret->value);
@@ -591,11 +597,6 @@ gst_gl_shadervariable_set (GstGLShader * shader,
(float *) ret->value);
break;
#endif
- case _mat4:
- case _mat4x4:
- gst_gl_shader_set_uniform_matrix_4fv (shader, ret->name, ret->count, 0,
- (float *) ret->value);
- break;
default:
return -1;
diff --git a/gst-libs/gst/gl/gstglupload.c b/gst-libs/gst/gl/gstglupload.c
index b72bcf88f..d1ed9398e 100644
--- a/gst-libs/gst/gl/gstglupload.c
+++ b/gst-libs/gst/gl/gstglupload.c
@@ -43,8 +43,13 @@
* calling thread.
*/
+#define USING_OPENGL(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL)
+#define USING_OPENGL3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_OPENGL3)
+#define USING_GLES(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES)
+#define USING_GLES2(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES2)
+#define USING_GLES3(display) (gst_gl_display_get_gl_api_unlocked (display) & GST_GL_API_GLES3)
+
static void _do_upload (GstGLDisplay * display, GstGLUpload * upload);
-static void _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload);
static void _do_upload_fill (GstGLDisplay * display, GstGLUpload * upload);
static void _do_upload_make (GstGLDisplay * display, GstGLUpload * upload);
static void _init_upload (GstGLDisplay * display, GstGLUpload * upload);
@@ -54,100 +59,164 @@ static gboolean gst_gl_upload_perform_with_data_unlocked (GstGLUpload * upload,
static gboolean gst_gl_upload_perform_with_data_unlocked_thread (GstGLUpload *
upload, GLuint texture_id, gpointer data[GST_VIDEO_MAX_PLANES]);
+#if HAVE_OPENGL
+static void _do_upload_draw_opengl (GstGLDisplay * display,
+ GstGLUpload * upload);
+#endif
+#if HAVE_GLES2
+static void _do_upload_draw_gles2 (GstGLDisplay * display,
+ GstGLUpload * upload);
+#endif
+
+/* *INDENT-OFF* */
+
+#if HAVE_OPENGL
/* YUY2:r,g,a
UYVY:a,b,r */
-static gchar *text_shader_YUY2_UYVY =
-#ifndef OPENGL_ES2
+static gchar *text_shader_YUY2_UYVY_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect Ytex, UVtex;\n"
-#else
- "precision mediump float;\n"
- "varying vec2 v_texCoord;\n" "uniform sampler2D Ytex, UVtex;\n"
-#endif
- "void main(void) {\n" " float fx, fy, y, u, v, r, g, b;\n"
-#ifndef OPENGL_ES2
+ "void main(void) {\n"
+ " float fx, fy, y, u, v, r, g, b;\n"
" fx = gl_TexCoord[0].x;\n"
" fy = gl_TexCoord[0].y;\n"
" y = texture2DRect(Ytex,vec2(fx,fy)).%c;\n"
" u = texture2DRect(UVtex,vec2(fx*0.5,fy)).%c;\n"
" v = texture2DRect(UVtex,vec2(fx*0.5,fy)).%c;\n"
-#else
- " fx = v_texCoord.x;\n"
- " fy = v_texCoord.y;\n"
- " y = texture2D(Ytex,vec2(fx,fy)).%c;\n"
- " u = texture2D(UVtex,vec2(fx*0.5,fy)).%c;\n"
- " v = texture2D(UVtex,vec2(fx*0.5,fy)).%c;\n"
-#endif
" y=1.164*(y-0.0627);\n"
" u=u-0.5;\n"
" v=v-0.5;\n"
" r = y+1.5958*v;\n"
" g = y-0.39173*u-0.81290*v;\n"
- " b = y+2.017*u;\n" " gl_FragColor = vec4(r, g, b, 1.0);\n" "}\n";
+ " b = y+2.017*u;\n"
+ " gl_FragColor = vec4(r, g, b, 1.0);\n"
+ "}\n";
/* ATI: "*0.5", ""
normal: "", "*0.5" */
-static gchar *text_shader_I420_YV12 =
-#ifndef OPENGL_ES2
+static gchar *text_shader_I420_YV12_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect Ytex,Utex,Vtex;\n"
-#else
- "precision mediump float;\n"
- "varying vec2 v_texCoord;\n" "uniform sampler2D Ytex,Utex,Vtex;\n"
-#endif
- "void main(void) {\n" " float r,g,b,y,u,v;\n"
-#ifndef OPENGL_ES2
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
" vec2 nxy = gl_TexCoord[0].xy;\n"
" y=texture2DRect(Ytex,nxy%s).r;\n"
- " u=texture2DRect(Utex,nxy%s).r;\n" " v=texture2DRect(Vtex,nxy*0.5).r;\n"
-#else
- " vec2 nxy = v_texCoord.xy;\n"
- " y=texture2D(Ytex,nxy).r;\n"
- " u=texture2D(Utex,nxy).r;\n" " v=texture2D(Vtex,nxy).r;\n"
-#endif
+ " u=texture2DRect(Utex,nxy%s).r;\n"
+ " v=texture2DRect(Vtex,nxy*0.5).r;\n"
" y=1.1643*(y-0.0625);\n"
" u=u-0.5;\n"
" v=v-0.5;\n"
" r=y+1.5958*v;\n"
" g=y-0.39173*u-0.81290*v;\n"
- " b=y+2.017*u;\n" " gl_FragColor=vec4(r,g,b,1.0);\n" "}\n";
+ " b=y+2.017*u;\n"
+ " gl_FragColor=vec4(r,g,b,1.0);\n"
+ "}\n";
-static gchar *text_shader_AYUV =
-#ifndef OPENGL_ES2
+static gchar *text_shader_AYUV_opengl =
"#extension GL_ARB_texture_rectangle : enable\n"
"uniform sampler2DRect tex;\n"
-#else
- "precision mediump float;\n"
- "varying vec2 v_texCoord;\n" "uniform sampler2D tex;\n"
-#endif
- "void main(void) {\n" " float r,g,b,y,u,v;\n"
-#ifndef OPENGL_ES2
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
" vec2 nxy=gl_TexCoord[0].xy;\n"
" y=texture2DRect(tex,nxy).r;\n"
- " u=texture2DRect(tex,nxy).g;\n" " v=texture2DRect(tex,nxy).b;\n"
-#else
+ " u=texture2DRect(tex,nxy).g;\n"
+ " v=texture2DRect(tex,nxy).b;\n"
+ " y=1.1643*(y-0.0625);\n"
+ " u=u-0.5;\n"
+ " v=v-0.5;\n"
+ " r=y+1.5958*v;\n"
+ " g=y-0.39173*u-0.81290*v;\n"
+ " b=y+2.017*u;\n"
+ " gl_FragColor=vec4(r,g,b,1.0);\n"
+ "}\n";
+
+#define text_vertex_shader_opengl NULL
+#endif
+
+#ifdef HAVE_GLES2
+/* YUY2:r,g,a
+ UYVY:a,b,r */
+static gchar *text_shader_YUY2_UYVY_gles2 =
+ "precision mediump float;\n"
+ "varying vec2 v_texCoord;\n"
+ "uniform sampler2D Ytex, UVtex;\n"
+ "void main(void) {\n"
+ " float fx, fy, y, u, v, r, g, b;\n"
+ " fx = v_texCoord.x;\n"
+ " fy = v_texCoord.y;\n"
+ " y = texture2D(Ytex,vec2(fx,fy)).%c;\n"
+ " u = texture2D(UVtex,vec2(fx*0.5,fy)).%c;\n"
+ " v = texture2D(UVtex,vec2(fx*0.5,fy)).%c;\n"
+ " y=1.164*(y-0.0627);\n"
+ " u=u-0.5;\n"
+ " v=v-0.5;\n"
+ " r = y+1.5958*v;\n"
+ " g = y-0.39173*u-0.81290*v;\n"
+ " b = y+2.017*u;\n"
+ " gl_FragColor = vec4(r, g, b, 1.0);\n"
+ "}\n";
+
+static gchar *text_shader_I420_YV12_gles2 =
+ "precision mediump float;\n"
+ "varying vec2 v_texCoord;\n"
+ "uniform sampler2D Ytex,Utex,Vtex;\n"
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
+ " vec2 nxy = v_texCoord.xy;\n"
+ " y=texture2D(Ytex,nxy).r;\n"
+ " u=texture2D(Utex,nxy).r;\n"
+ " v=texture2D(Vtex,nxy).r;\n"
+ " y=1.1643*(y-0.0625);\n"
+ " u=u-0.5;\n"
+ " v=v-0.5;\n"
+ " r=y+1.5958*v;\n"
+ " g=y-0.39173*u-0.81290*v;\n"
+ " b=y+2.017*u;\n"
+ " gl_FragColor=vec4(r,g,b,1.0);\n"
+ "}\n";
+
+static gchar *text_shader_AYUV_gles2 =
+ "precision mediump float;\n"
+ "varying vec2 v_texCoord;\n"
+ "uniform sampler2D tex;\n"
+ "void main(void) {\n"
+ " float r,g,b,y,u,v;\n"
" vec2 nxy = v_texCoord.xy;\n"
" y=texture2D(tex,nxy).g;\n"
- " u=texture2D(tex,nxy).b;\n" " v=texture2D(tex,nxy).a;\n"
-#endif
+ " u=texture2D(tex,nxy).b;\n"
+ " v=texture2D(tex,nxy).a;\n"
" y=1.1643*(y-0.0625);\n"
" u=u-0.5;\n"
" v=v-0.5;\n"
" r=y+1.5958*v;\n"
" g=y-0.39173*u-0.81290*v;\n"
- " b=y+2.017*u;\n" " gl_FragColor=vec4(r,g,b,1.0);\n" "}\n";
+ " b=y+2.017*u;\n"
+ " gl_FragColor=vec4(r,g,b,1.0);\n"
+ "}\n";
-#ifdef OPENGL_ES2
-static gchar *text_vertex_shader =
+static gchar *text_vertex_shader_gles2 =
"attribute vec4 a_position; \n"
"attribute vec2 a_texCoord; \n"
"varying vec2 v_texCoord; \n"
"void main() \n"
"{ \n"
" gl_Position = a_position; \n"
- " v_texCoord = a_texCoord; \n" "} \n";
+ " v_texCoord = a_texCoord; \n"
+ "} \n";
#endif
+/* *INDENT-ON* */
+
+struct _GstGLUploadPrivate
+{
+ const gchar *YUY2_UYVY;
+ const gchar *I420_YV12;
+ const gchar *AYUV;
+ const gchar *vert_shader;
+
+ void (*draw) (GstGLDisplay * display, GstGLUpload * download);
+};
+
GST_DEBUG_CATEGORY_STATIC (gst_gl_upload_debug);
#define GST_CAT_DEFAULT gst_gl_upload_debug
@@ -163,12 +232,16 @@ static void gst_gl_upload_finalize (GObject * object);
static void
gst_gl_upload_class_init (GstGLUploadClass * klass)
{
+ g_type_class_add_private (klass, sizeof (GstGLUploadPrivate));
+
G_OBJECT_CLASS (klass)->finalize = gst_gl_upload_finalize;
}
static void
gst_gl_upload_init (GstGLUpload * upload)
{
+ upload->priv = GST_GL_UPLOAD_GET_PRIVATE (upload);
+
upload->display = NULL;
g_mutex_init (&upload->lock);
@@ -178,10 +251,8 @@ gst_gl_upload_init (GstGLUpload * upload)
upload->out_texture = 0;
upload->shader = NULL;
-#ifdef OPENGL_ES2
upload->shader_attr_position_loc = 0;
upload->shader_attr_texture_loc = 0;
-#endif
gst_video_info_init (&upload->info);
}
@@ -196,13 +267,34 @@ GstGLUpload *
gst_gl_upload_new (GstGLDisplay * display)
{
GstGLUpload *upload;
+ GstGLUploadPrivate *priv;
upload = g_object_new (GST_TYPE_GL_UPLOAD, NULL);
upload->display = g_object_ref (display);
+ priv = upload->priv;
g_mutex_init (&upload->lock);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ priv->YUY2_UYVY = text_shader_YUY2_UYVY_opengl;
+ priv->I420_YV12 = text_shader_I420_YV12_opengl;
+ priv->AYUV = text_shader_AYUV_opengl;
+ priv->vert_shader = text_vertex_shader_opengl;
+ priv->draw = _do_upload_draw_opengl;
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ priv->YUY2_UYVY = text_shader_YUY2_UYVY_gles2;
+ priv->I420_YV12 = text_shader_I420_YV12_gles2;
+ priv->AYUV = text_shader_AYUV_gles2;
+ priv->vert_shader = text_vertex_shader_gles2;
+ priv->draw = _do_upload_draw_gles2;
+ }
+#endif
+
return upload;
}
@@ -547,7 +639,7 @@ gst_gl_display_find_upload_unlocked (GstGLDisplay * display,
GstVideoFormat v_format, guint in_width, guint in_height,
guint out_width, guint out_height)
{
- GstGLUpload *ret;
+ GstGLUpload *ret = NULL;
GSList *walk;
walk = display->uploads;
@@ -606,6 +698,34 @@ gst_gl_display_find_upload (GstGLDisplay * display, GstVideoFormat v_format,
return ret;
}
+static gboolean
+_create_shader (GstGLDisplay * display, const gchar * vertex_src,
+ const gchar * fragment_src, GstGLShader ** out_shader)
+{
+ GstGLShader *shader;
+ GError *error;
+
+ g_return_val_if_fail (vertex_src != NULL || fragment_src != NULL, FALSE);
+
+ shader = gst_gl_shader_new (display);
+
+ if (vertex_src)
+ gst_gl_shader_set_vertex_source (shader, vertex_src);
+ if (fragment_src)
+ gst_gl_shader_set_fragment_source (shader, fragment_src);
+
+ if (!gst_gl_shader_compile (shader, &error)) {
+ gst_gl_display_set_error (display, "%s", error->message);
+ g_error_free (error);
+ gst_gl_shader_use (NULL);
+ g_object_unref (G_OBJECT (shader));
+ return FALSE;
+ }
+
+ *out_shader = shader;
+ return TRUE;
+}
+
/* Called in the gl thread */
void
_init_upload (GstGLDisplay * display, GstGLUpload * upload)
@@ -647,10 +767,6 @@ _init_upload (GstGLDisplay * display, GstGLUpload * upload)
/* shouldn't we require ARB_shading_language_100? --Filippo */
if (GLEW_ARB_fragment_shader) {
-#ifdef OPENGL_ES2
- GError *error = NULL;
-#endif
-
GST_INFO ("Context, ARB_fragment_shader supported: yes");
display->colorspace_conversion = GST_GL_DISPLAY_CONVERSION_GLSL;
@@ -661,173 +777,100 @@ _init_upload (GstGLDisplay * display, GstGLUpload * upload)
case GST_VIDEO_FORMAT_YUY2:
{
gchar text_shader_YUY2[2048];
- sprintf (text_shader_YUY2, text_shader_YUY2_UYVY, 'r', 'g', 'a');
-
- upload->shader = gst_gl_shader_new ();
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (upload->shader,
- text_shader_YUY2, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for uploading YUY2");
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- }
-#else
- gst_gl_shader_set_vertex_source (upload->shader,
- text_vertex_shader);
- gst_gl_shader_set_fragment_source (upload->shader,
- text_shader_YUY2);
-
- gst_gl_shader_compile (upload->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- } else {
- upload->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_position");
- upload->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_texCoord");
+ sprintf (text_shader_YUY2, upload->priv->YUY2_UYVY, 'r', 'g', 'a');
+
+ if (_create_shader (display, upload->priv->vert_shader,
+ text_shader_YUY2, &upload->shader)) {
+ if (USING_GLES2 (display)) {
+ upload->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_position");
+ upload->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_texCoord");
+ }
}
-#endif
}
break;
case GST_VIDEO_FORMAT_UYVY:
{
gchar text_shader_UYVY[2048];
- sprintf (text_shader_UYVY,
-#ifndef OPENGL_ES2
- text_shader_YUY2_UYVY, 'a', 'b', 'r');
-#else
- text_shader_YUY2_UYVY, 'a', 'r', 'b');
-#endif
-
- upload->shader = gst_gl_shader_new ();
-
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (upload->shader,
- text_shader_UYVY, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for uploading UYVY");
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
+#if HAVE_OPENGL
+ if (USING_GLES2 (display)) {
+ sprintf (text_shader_UYVY, upload->priv->YUY2_UYVY,
+ 'a', 'b', 'r');
}
-#else
- gst_gl_shader_set_vertex_source (upload->shader,
- text_vertex_shader);
- gst_gl_shader_set_fragment_source (upload->shader,
- text_shader_UYVY);
-
- gst_gl_shader_compile (upload->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- } else {
- upload->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_position");
- upload->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_texCoord");
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ sprintf (text_shader_UYVY, upload->priv->YUY2_UYVY,
+ 'a', 'r', 'b');
}
#endif
+
+ if (_create_shader (display, upload->priv->vert_shader,
+ text_shader_UYVY, &upload->shader)) {
+ if (USING_GLES2 (display)) {
+ upload->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_position");
+ upload->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_texCoord");
+ }
+ }
}
break;
case GST_VIDEO_FORMAT_I420:
case GST_VIDEO_FORMAT_YV12:
{
-#ifndef OPENGL_ES2
- gchar text_shader[2048];
- if ((g_ascii_strncasecmp ("ATI", (gchar *) glGetString (GL_VENDOR),
- 3) == 0)
- && (g_ascii_strncasecmp ("ATI Mobility Radeon HD",
- (gchar *) glGetString (GL_RENDERER), 22) != 0)
- && (g_ascii_strncasecmp ("ATI Radeon HD",
- (gchar *) glGetString (GL_RENDERER), 13) != 0))
- sprintf (text_shader, text_shader_I420_YV12, "*0.5", "");
- else
- sprintf (text_shader, text_shader_I420_YV12, "", "*0.5");
+ gchar text_shader_I420_YV12[2048];
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ if ((g_ascii_strncasecmp ("ATI",
+ (gchar *) glGetString (GL_VENDOR), 3) == 0)
+ && (g_ascii_strncasecmp ("ATI Mobility Radeon HD",
+ (gchar *) glGetString (GL_RENDERER), 22) != 0)
+ && (g_ascii_strncasecmp ("ATI Radeon HD",
+ (gchar *) glGetString (GL_RENDERER), 13) != 0))
+ sprintf (text_shader_I420_YV12, upload->priv->I420_YV12, "*0.5",
+ "");
+ else
+ sprintf (text_shader_I420_YV12, upload->priv->I420_YV12, "",
+ "*0.5");
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display))
+ g_strlcpy (text_shader_I420_YV12, upload->priv->I420_YV12, 2048);
#endif
- upload->shader = gst_gl_shader_new ();
-
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check
- (upload->shader, text_shader, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for uploading I420 or YV12");
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
+ if (_create_shader (display, upload->priv->vert_shader,
+ text_shader_I420_YV12, &upload->shader)) {
+ if (USING_GLES2 (display)) {
+ upload->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_position");
+ upload->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_texCoord");
+ }
}
-#else
- gst_gl_shader_set_vertex_source (upload->shader,
- text_vertex_shader);
- gst_gl_shader_set_fragment_source (upload->shader,
- text_shader_I420_YV12);
-
- gst_gl_shader_compile (upload->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- } else {
- upload->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_position");
- upload->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_texCoord");
- }
-#endif
}
break;
case GST_VIDEO_FORMAT_AYUV:
{
- upload->shader = gst_gl_shader_new ();
-
-#ifndef OPENGL_ES2
- if (!gst_gl_shader_compile_and_check (upload->shader,
- text_shader_AYUV, GST_GL_SHADER_FRAGMENT_SOURCE)) {
- gst_gl_display_set_error (display,
- "Failed to initialize shader for uploading AYUV");
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- }
-#else
- gst_gl_shader_set_vertex_source (upload->shader,
- text_vertex_shader);
- gst_gl_shader_set_fragment_source (upload->shader,
- text_shader_AYUV);
-
- gst_gl_shader_compile (upload->shader, &error);
- if (error) {
- gst_gl_display_set_error (display, "%s", error->message);
- g_error_free (error);
- error = NULL;
- gst_gl_shader_use (NULL);
- g_object_unref (G_OBJECT (upload->shader));
- upload->shader = NULL;
- } else {
- upload->shader_attr_position_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_position");
- upload->shader_attr_texture_loc =
- gst_gl_shader_get_attribute_location
- (upload->shader, "a_texCoord");
+ if (_create_shader (display, upload->priv->vert_shader,
+ upload->priv->AYUV, &upload->shader)) {
+ if (USING_GLES2 (display)) {
+ upload->shader_attr_position_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_position");
+ upload->shader_attr_texture_loc =
+ gst_gl_shader_get_attribute_location
+ (upload->shader, "a_texCoord");
+ }
}
-#endif
}
break;
default:
@@ -916,14 +959,19 @@ _init_upload_fbo (GstGLDisplay * display, GstGLUpload * upload)
/* setup the render buffer for depth */
glGenRenderbuffersEXT (1, &upload->depth_buffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT, upload->depth_buffer);
-#ifndef OPENGL_ES2
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
- out_width, out_height);
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
- out_width, out_height);
-#else
- glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
- out_width, out_height);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT,
+ out_width, out_height);
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH24_STENCIL8_EXT,
+ out_width, out_height);
+ }
+#endif
+#if HAVE_GLES2
+ if (USING_GLES2 (display)) {
+ glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT16,
+ out_width, out_height);
+ }
#endif
/* a fake texture is attached to the upload FBO (cannot init without it) */
@@ -946,9 +994,11 @@ _init_upload_fbo (GstGLDisplay * display, GstGLUpload * upload)
glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT,
GL_RENDERBUFFER_EXT, upload->depth_buffer);
-#ifndef OPENGL_ES2
- glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_STENCIL_ATTACHMENT_EXT,
- GL_RENDERBUFFER_EXT, upload->depth_buffer);
+#if HAVE_OPENGL
+ if (USING_OPENGL (display)) {
+ glFramebufferRenderbufferEXT (GL_FRAMEBUFFER_EXT, GL_STENCIL_ATTACHMENT_EXT,
+ GL_RENDERBUFFER_EXT, upload->depth_buffer);
+ }
#endif
gst_gl_display_check_framebuffer_status ();
@@ -995,7 +1045,7 @@ _do_upload (GstGLDisplay * display, GstGLUpload * upload)
case GST_VIDEO_FORMAT_RGB:
case GST_VIDEO_FORMAT_BGR:
if (in_width != out_width || in_height != out_height)
- _do_upload_draw (display, upload);
+ upload->priv->draw (display, upload);
/* color space conversion is not needed */
break;
case GST_VIDEO_FORMAT_YUY2:
@@ -1007,7 +1057,7 @@ _do_upload (GstGLDisplay * display, GstGLUpload * upload)
switch (display->colorspace_conversion) {
case GST_GL_DISPLAY_CONVERSION_GLSL:
/* color space conversion is needed */
- _do_upload_draw (display, upload);
+ upload->priv->draw (display, upload);
break;
case GST_GL_DISPLAY_CONVERSION_MATRIX:
/* color space conversion is needed */
@@ -1015,7 +1065,7 @@ _do_upload (GstGLDisplay * display, GstGLUpload * upload)
break;
case GST_GL_DISPLAY_CONVERSION_MESA:
if (in_width != out_width || in_height != out_height)
- _do_upload_draw (display, upload);
+ upload->priv->draw (display, upload);
/* color space conversion is not needed */
break;
default:
@@ -1329,31 +1379,14 @@ _do_upload_fill (GstGLDisplay * display, GstGLUpload * upload)
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, 0);
}
-
+#if HAVE_OPENGL
/* called by _do_upload (in the gl thread) */
-void
-_do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
+static void
+_do_upload_draw_opengl (GstGLDisplay * display, GstGLUpload * upload)
{
GstVideoFormat v_format;
guint out_width, out_height;
-
-#ifndef OPENGL_ES2
guint in_width, in_height;
-#else
- GLint viewport_dim[4];
-
- const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f,
- 1.0f, 0.0f,
- -1.0f, -1.0f, 0.0f,
- 0.0f, .0f,
- -1.0f, 1.0f, 0.0f,
- 0.0f, 1.0f,
- 1.0f, 1.0f, 0.0f,
- 1.0f, 1.0f
- };
-
- GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
-#endif
out_width = GST_VIDEO_INFO_WIDTH (&upload->info);
out_height = GST_VIDEO_INFO_HEIGHT (&upload->info);
@@ -1362,12 +1395,10 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, upload->fbo);
/* setup a texture to render to */
-#ifndef OPENGL_ES2
in_width = upload->in_width;
in_height = upload->in_height;
glEnable (GL_TEXTURE_RECTANGLE_ARB);
-#endif
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->out_texture);
/* attach the texture to the FBO to renderer to */
@@ -1377,7 +1408,6 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
if (GLEW_ARB_fragment_shader)
gst_gl_shader_use (NULL);
-#ifndef OPENGL_ES2
glPushAttrib (GL_VIEWPORT_BIT);
glMatrixMode (GL_PROJECTION);
@@ -1388,15 +1418,10 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
glMatrixMode (GL_MODELVIEW);
glPushMatrix ();
glLoadIdentity ();
-#else /* OPENGL_ES2 */
- glGetIntegerv (GL_VIEWPORT, viewport_dim);
-#endif
glViewport (0, 0, out_width, out_height);
-#ifndef OPENGL_ES2
glDrawBuffer (GL_COLOR_ATTACHMENT0_EXT);
-#endif
glClearColor (0.0, 0.0, 0.0, 0.0);
glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
@@ -1413,22 +1438,10 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
case GST_VIDEO_FORMAT_RGB:
case GST_VIDEO_FORMAT_BGR:
{
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#else
- glVertexAttribPointer (upload->shader_attr_position_loc, 3,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
-
- glEnableVertexAttribArray (upload->shader_attr_position_loc);
- glEnableVertexAttribArray (upload->shader_attr_texture_loc);
-#endif
-#ifndef OPENGL_ES2
glEnable (GL_TEXTURE_RECTANGLE_ARB);
-#endif
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
GL_LINEAR);
@@ -1438,9 +1451,7 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
GL_CLAMP_TO_EDGE);
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
GL_CLAMP_TO_EDGE);
-#ifndef OPENGL_ES2
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
-#endif
}
break;
@@ -1453,18 +1464,8 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
{
gst_gl_shader_use (upload->shader);
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#else
- glVertexAttribPointer (upload->shader_attr_position_loc, 3,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
-
- glEnableVertexAttribArray (upload->shader_attr_position_loc);
- glEnableVertexAttribArray (upload->shader_attr_texture_loc);
-#endif
glActiveTextureARB (GL_TEXTURE1_ARB);
gst_gl_shader_set_uniform_1i (upload->shader, "UVtex", 1);
@@ -1494,11 +1495,9 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
case GST_GL_DISPLAY_CONVERSION_MESA:
{
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
glEnable (GL_TEXTURE_RECTANGLE_ARB);
-#endif
glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
GL_LINEAR);
@@ -1508,9 +1507,7 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
GL_CLAMP_TO_EDGE);
glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
GL_CLAMP_TO_EDGE);
-#ifndef OPENGL_ES2
glTexEnvi (GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
-#endif
}
break;
default:
@@ -1527,18 +1524,8 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
{
gst_gl_shader_use (upload->shader);
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#else
- glVertexAttribPointer (upload->shader_attr_position_loc, 3,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
-
- glEnableVertexAttribArray (upload->shader_attr_position_loc);
- glEnableVertexAttribArray (upload->shader_attr_texture_loc);
-#endif
glActiveTextureARB (GL_TEXTURE1_ARB);
gst_gl_shader_set_uniform_1i (upload->shader, "Utex", 1);
@@ -1582,18 +1569,8 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
{
gst_gl_shader_use (upload->shader);
-#ifndef OPENGL_ES2
glMatrixMode (GL_PROJECTION);
glLoadIdentity ();
-#else
- glVertexAttribPointer (upload->shader_attr_position_loc, 3,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
- glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
- GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
-
- glEnableVertexAttribArray (upload->shader_attr_position_loc);
- glEnableVertexAttribArray (upload->shader_attr_texture_loc);
-#endif
glActiveTextureARB (GL_TEXTURE0_ARB);
gst_gl_shader_set_uniform_1i (upload->shader, "tex", 0);
@@ -1617,7 +1594,6 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
} /* end switch display->currentVideo_format */
-#ifndef OPENGL_ES2
glBegin (GL_QUADS);
glTexCoord2i (in_width, 0);
glVertex2f (1.0f, -1.0f);
@@ -1630,15 +1606,11 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
glEnd ();
glDrawBuffer (GL_NONE);
-#else /* OPENGL_ES2 */
- glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
-#endif
/* we are done with the shader */
if (display->colorspace_conversion == GST_GL_DISPLAY_CONVERSION_GLSL)
glUseProgramObjectARB (0);
-#ifndef OPENGL_ES2
glDisable (GL_TEXTURE_RECTANGLE_ARB);
glMatrixMode (GL_PROJECTION);
@@ -1646,12 +1618,250 @@ _do_upload_draw (GstGLDisplay * display, GstGLUpload * upload)
glMatrixMode (GL_MODELVIEW);
glPopMatrix ();
glPopAttrib ();
-#else
+
+ gst_gl_display_check_framebuffer_status ();
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
+}
+#endif
+
+#if HAVE_GLES2
+static void
+_do_upload_draw_gles2 (GstGLDisplay * display, GstGLUpload * upload)
+{
+ GstVideoFormat v_format;
+ guint out_width, out_height;
+
+ GLint viewport_dim[4];
+
+ const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f,
+ 1.0f, 0.0f,
+ -1.0f, -1.0f, 0.0f,
+ 0.0f, .0f,
+ -1.0f, 1.0f, 0.0f,
+ 0.0f, 1.0f,
+ 1.0f, 1.0f, 0.0f,
+ 1.0f, 1.0f
+ };
+
+ GLushort indices[] = { 0, 1, 2, 0, 2, 3 };
+
+ out_width = GST_VIDEO_INFO_WIDTH (&upload->info);
+ out_height = GST_VIDEO_INFO_HEIGHT (&upload->info);
+ v_format = GST_VIDEO_INFO_FORMAT (&upload->info);
+
+ glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, upload->fbo);
+
+ /* setup a texture to render to */
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->out_texture);
+
+ /* attach the texture to the FBO to renderer to */
+ glFramebufferTexture2DEXT (GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
+ GL_TEXTURE_RECTANGLE_ARB, upload->out_texture, 0);
+
+ if (GLEW_ARB_fragment_shader)
+ gst_gl_shader_use (NULL);
+
+ glGetIntegerv (GL_VIEWPORT, viewport_dim);
+
+ glViewport (0, 0, out_width, out_height);
+
+ glClearColor (0.0, 0.0, 0.0, 0.0);
+ glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+
+ switch (v_format) {
+ case GST_VIDEO_FORMAT_RGBx:
+ case GST_VIDEO_FORMAT_BGRx:
+ case GST_VIDEO_FORMAT_xRGB:
+ case GST_VIDEO_FORMAT_xBGR:
+ case GST_VIDEO_FORMAT_RGBA:
+ case GST_VIDEO_FORMAT_BGRA:
+ case GST_VIDEO_FORMAT_ARGB:
+ case GST_VIDEO_FORMAT_ABGR:
+ case GST_VIDEO_FORMAT_RGB:
+ case GST_VIDEO_FORMAT_BGR:
+ {
+ glVertexAttribPointer (upload->shader_attr_position_loc, 3,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+
+ glEnableVertexAttribArray (upload->shader_attr_position_loc);
+ glEnableVertexAttribArray (upload->shader_attr_texture_loc);
+
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+ }
+ break;
+
+ case GST_VIDEO_FORMAT_YUY2:
+ case GST_VIDEO_FORMAT_UYVY:
+ {
+ switch (display->colorspace_conversion) {
+ case GST_GL_DISPLAY_CONVERSION_GLSL:
+ case GST_GL_DISPLAY_CONVERSION_MATRIX:
+ {
+ gst_gl_shader_use (upload->shader);
+
+ glVertexAttribPointer (upload->shader_attr_position_loc, 3,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+
+ glEnableVertexAttribArray (upload->shader_attr_position_loc);
+ glEnableVertexAttribArray (upload->shader_attr_texture_loc);
+
+ glActiveTextureARB (GL_TEXTURE1_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "UVtex", 1);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[1]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+
+ glActiveTextureARB (GL_TEXTURE0_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "Ytex", 0);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+ }
+ break;
+ case GST_GL_DISPLAY_CONVERSION_MESA:
+ {
+
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+ }
+ break;
+ default:
+ gst_gl_display_set_error (display, "Unknow colorspace conversion %d",
+ display->colorspace_conversion);
+ g_assert_not_reached ();
+ break;
+ }
+ }
+ break;
+
+ case GST_VIDEO_FORMAT_I420:
+ case GST_VIDEO_FORMAT_YV12:
+ {
+ gst_gl_shader_use (upload->shader);
+
+ glVertexAttribPointer (upload->shader_attr_position_loc, 3,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+
+ glEnableVertexAttribArray (upload->shader_attr_position_loc);
+ glEnableVertexAttribArray (upload->shader_attr_texture_loc);
+
+ glActiveTextureARB (GL_TEXTURE1_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "Utex", 1);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[1]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+
+ glActiveTextureARB (GL_TEXTURE2_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "Vtex", 2);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[2]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+
+ glActiveTextureARB (GL_TEXTURE0_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "Ytex", 0);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+ }
+ break;
+
+ case GST_VIDEO_FORMAT_AYUV:
+ {
+ gst_gl_shader_use (upload->shader);
+
+ glVertexAttribPointer (upload->shader_attr_position_loc, 3,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices);
+ glVertexAttribPointer (upload->shader_attr_texture_loc, 2,
+ GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]);
+
+ glEnableVertexAttribArray (upload->shader_attr_position_loc);
+ glEnableVertexAttribArray (upload->shader_attr_texture_loc);
+
+ glActiveTextureARB (GL_TEXTURE0_ARB);
+ gst_gl_shader_set_uniform_1i (upload->shader, "tex", 0);
+ glBindTexture (GL_TEXTURE_RECTANGLE_ARB, upload->in_texture[0]);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MAG_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_MIN_FILTER,
+ GL_LINEAR);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_S,
+ GL_CLAMP_TO_EDGE);
+ glTexParameteri (GL_TEXTURE_RECTANGLE_ARB, GL_TEXTURE_WRAP_T,
+ GL_CLAMP_TO_EDGE);
+ }
+ break;
+
+ default:
+ gst_gl_display_set_error (display, "Unsupported upload video format %d",
+ v_format);
+ g_assert_not_reached ();
+ break;
+
+ } /* end switch display->currentVideo_format */
+
+ glDrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices);
+
+ /* we are done with the shader */
+ if (display->colorspace_conversion == GST_GL_DISPLAY_CONVERSION_GLSL)
+ glUseProgramObjectARB (0);
+
glViewport (viewport_dim[0], viewport_dim[1], viewport_dim[2],
viewport_dim[3]);
-#endif
gst_gl_display_check_framebuffer_status ();
glBindFramebufferEXT (GL_FRAMEBUFFER_EXT, 0);
}
+#endif
diff --git a/gst-libs/gst/gl/gstglupload.h b/gst-libs/gst/gl/gstglupload.h
index 9ab9ce7e9..cc3d10c8c 100644
--- a/gst-libs/gst/gl/gstglupload.h
+++ b/gst-libs/gst/gl/gstglupload.h
@@ -43,6 +43,7 @@ GType gst_gl_upload_get_type (void);
typedef struct _GstGLUpload GstGLUpload;
typedef struct _GstGLUploadClass GstGLUploadClass;
+typedef struct _GstGLUploadPrivate GstGLUploadPrivate;
/**
* GstGLUpload
@@ -76,12 +77,12 @@ struct _GstGLUpload
guint in_width;
guint in_height;
GstGLShader *shader;
-#ifdef OPENGL_ES2
GLint shader_attr_position_loc;
GLint shader_attr_texture_loc;
-#endif
/* <private> */
+ GstGLUploadPrivate *priv;
+
gpointer _reserved[GST_PADDING];
};
@@ -100,12 +101,12 @@ struct _GstGLUploadClass
*
* The currently supported formats that can be uploaded
*/
-#ifndef OPENGL_ES2
-# define GST_GL_UPLOAD_FORMATS "{ RGB, RGBx, RGBA, BGR, BGRx, BGRA, xRGB, " \
+#if !HAVE_GLES2
+#define GST_GL_UPLOAD_FORMATS "{ RGB, RGBx, RGBA, BGR, BGRx, BGRA, xRGB, " \
"xBGR, ARGB, ABGR, I420, YV12, YUY2, UYVY, AYUV }"
-#else /* OPENGL_ES2 */
+#else /* HAVE_GLES2 */
# define GST_GL_UPLOAD_FORMATS "{ RGB, RGBx, RGBA, I420, YV12, YUY2, UYVY, AYUV }"
-#endif
+#endif /* !HAVE_GLES2 */
/**
* GST_GL_UPLOAD_VIDEO_CAPS: