diff options
author | Sebastian Dröge <slomo@circular-chaos.org> | 2013-07-21 11:43:24 +0200 |
---|---|---|
committer | Sebastian Dröge <slomo@circular-chaos.org> | 2013-07-24 13:36:34 +0200 |
commit | c3a92871076aeb73f24f8b0c5b8fbcea9436b254 (patch) | |
tree | f456b5c12d8d2af7a232588adc7b996acd911d8e | |
parent | d8f38905091b6f9d70ff01dbc5c898f93407c961 (diff) |
gldownload: Add support for downloading multi-planar formats to GLES2download-planar
https://bugzilla.gnome.org/show_bug.cgi?id=704222
-rw-r--r-- | gst-libs/gst/gl/gstgldownload.c | 97 | ||||
-rw-r--r-- | gst-libs/gst/gl/gstgles2.h | 4 |
2 files changed, 88 insertions, 13 deletions
diff --git a/gst-libs/gst/gl/gstgldownload.c b/gst-libs/gst/gl/gstgldownload.c index 7439282..3681393 100644 --- a/gst-libs/gst/gl/gstgldownload.c +++ b/gst-libs/gst/gl/gstgldownload.c @@ -163,10 +163,29 @@ static const gchar *text_shader_YUY2_UYVY_gles2 = " 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 const gchar *text_shader_I420_YV12_gles2 = + "precision mediump float;\n" + "varying vec2 v_texCoord;\n" + "uniform sampler2D tex;\n" + "uniform float w, h;\n" + RGB_TO_YUV_COEFFICIENTS + "void main(void) {\n" + " vec3 rgb1, rgb2;\n" + " float fx,fy,y,u,v;\n" + " fx = v_texCoord.x;\n" + " fy = v_texCoord.y;\n" + " rgb1=texture2D(tex,vec2(fx, fy)).rgb;\n" + " rgb2=texture2D(tex,vec2(fx*2.0, fy*2.0)).rgb;\n" + " y=dot(rgb1, ycoeff);\n" + " u=dot(rgb2, ucoeff);\n" + " v=dot(rgb2, vcoeff);\n" + " y+=offset.x;\n" + " u+=offset.y;\n" + " v+=offset.z;\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"; static const gchar *text_shader_AYUV_gles2 = "precision mediump float;\n" @@ -566,6 +585,15 @@ _init_download (GstGLDisplay * display, GstGLDownload * download) } GST_INFO ("Context, EXT_framebuffer_object supported: yes"); + /* Need the NV extension for multi-planar formats with GLES2, + * or need GLES3 */ + if (USING_GLES2 (display) && GST_VIDEO_INFO_N_PLANES (&download->info) + && (!gl->DrawBuffers || !gl->ReadBuffer)) { + gst_gl_display_set_error (display, + "No glDrawBuffers or glReadBuffer support"); + goto error; + } + /* setup FBO */ gl->GenFramebuffers (1, &download->fbo); gl->BindFramebuffer (GL_FRAMEBUFFER, download->fbo); @@ -663,10 +691,10 @@ _init_download (GstGLDisplay * display, GstGLDownload * download) } break; default: - break; gst_gl_display_set_error (display, "Unsupported download video format %d", v_format); g_assert_not_reached (); + break; } no_convert: @@ -794,8 +822,17 @@ _init_download_shader (GstGLDisplay * display, GstGLDownload * download) case GST_VIDEO_FORMAT_I420: case GST_VIDEO_FORMAT_YV12: { - _create_shader (display, download->priv->vert_shader, - download->priv->I420_YV12, &download->shader); + if (_create_shader (display, download->priv->vert_shader, + download->priv->I420_YV12, &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"); + } + } break; } case GST_VIDEO_FORMAT_AYUV: @@ -1167,9 +1204,9 @@ _do_download_draw_yuv_opengl (GstGLDisplay * display, GstGLDownload * download) break; default: - break; gst_gl_display_set_error (display, "Download video format inconsistensy %d", v_format); + break; } gl->ClientActiveTexture (GL_TEXTURE0); @@ -1262,10 +1299,10 @@ _do_download_draw_yuv_opengl (GstGLDisplay * display, GstGLDownload * download) } break; default: - break; gst_gl_display_set_error (display, "Download video format inconsistensy %d", v_format); g_assert_not_reached (); + break; } gl->ReadBuffer (GL_NONE); @@ -1285,6 +1322,18 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) GLint viewport_dim[4]; + GLenum singleRT[] = { + GL_COLOR_ATTACHMENT0 + }; + GLenum multipleRT[] = { + GL_COLOR_ATTACHMENT0, + GL_COLOR_ATTACHMENT1, + GL_COLOR_ATTACHMENT2 + }; + GLenum noneRT[] = { + GL_NONE + }; + const GLfloat vVertices[] = { 1.0f, -1.0f, 0.0f, 1.0f, 0.0f, -1.0f, -1.0f, 0.0f, @@ -1318,6 +1367,9 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) case GST_VIDEO_FORMAT_UYVY: case GST_VIDEO_FORMAT_AYUV: { + if (gl->DrawBuffers) + gl->DrawBuffers (1, singleRT); + gl->ClearColor (0.0, 0.0, 0.0, 0.0); gl->Clear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); @@ -1340,11 +1392,21 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) case GST_VIDEO_FORMAT_I420: case GST_VIDEO_FORMAT_YV12: { + gl->DrawBuffers (3, multipleRT); + gl->ClearColor (0.0, 0.0, 0.0, 0.0); gl->Clear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); gst_gl_shader_use (download->shader); + gl->VertexAttribPointer (download->shader_attr_position_loc, 3, + GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), vVertices); + gl->VertexAttribPointer (download->shader_attr_texture_loc, 2, + GL_FLOAT, GL_FALSE, 5 * sizeof (GLfloat), &vVertices[3]); + + gl->EnableVertexAttribArray (download->shader_attr_position_loc); + gl->EnableVertexAttribArray (download->shader_attr_texture_loc); + gl->ActiveTexture (GL_TEXTURE0); gst_gl_shader_set_uniform_1i (download->shader, "tex", 0); gst_gl_shader_set_uniform_1f (download->shader, "w", (gfloat) out_width); @@ -1354,14 +1416,17 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) break; default: - break; gst_gl_display_set_error (display, "Download video format inconsistensy %d", v_format); + break; } gl->DrawElements (GL_TRIANGLES, 6, GL_UNSIGNED_SHORT, indices); + if (gl->DrawBuffers) + gl->DrawBuffers (1, noneRT); + /* don't check if GLSL is available * because download yuv is not available * without GLSL (whereas rgb is) @@ -1371,6 +1436,9 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) gl->Viewport (viewport_dim[0], viewport_dim[1], viewport_dim[2], viewport_dim[3]); + if (gl->ReadBuffer) + gl->ReadBuffer (GL_COLOR_ATTACHMENT0); + switch (v_format) { case GST_VIDEO_FORMAT_AYUV: #if G_BYTE_ORDER == G_LITTLE_ENDIAN @@ -1396,10 +1464,12 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) gl->ReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE, download->data[0]); + gl->ReadBuffer (GL_COLOR_ATTACHMENT1); gl->ReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2, GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE, download->data[1]); + gl->ReadBuffer (GL_COLOR_ATTACHMENT2); gl->ReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2, GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE, download->data[2]); @@ -1410,22 +1480,27 @@ _do_download_draw_yuv_gles2 (GstGLDisplay * display, GstGLDownload * download) gl->ReadPixels (0, 0, out_width, out_height, GL_LUMINANCE, GL_UNSIGNED_BYTE, download->data[0]); + gl->ReadBuffer (GL_COLOR_ATTACHMENT1); gl->ReadPixels (0, 0, GST_ROUND_UP_2 (out_width) / 2, GST_ROUND_UP_2 (out_height) / 2, GL_LUMINANCE, GL_UNSIGNED_BYTE, download->data[2]); + gl->ReadBuffer (GL_COLOR_ATTACHMENT2); gl->ReadPixels (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 (); + break; } + if (gl->ReadBuffer) + gl->ReadBuffer (GL_NONE); + gst_gl_display_check_framebuffer_status (display); gl->BindFramebuffer (GL_FRAMEBUFFER, 0); } diff --git a/gst-libs/gst/gl/gstgles2.h b/gst-libs/gst/gl/gstgles2.h index 49e744b..01948c3 100644 --- a/gst-libs/gst/gl/gstgles2.h +++ b/gst-libs/gst/gl/gstgles2.h @@ -35,6 +35,8 @@ G_BEGIN_DECLS #define GL_BGR GL_RGB #define GL_UNSIGNED_INT_8_8_8_8 GL_UNSIGNED_BYTE #define GL_UNSIGNED_INT_8_8_8_8_REV GL_UNSIGNED_BYTE +#define GL_COLOR_ATTACHMENT1 0x8CE1 +#define GL_COLOR_ATTACHMENT2 0x8CE2 //END FIXME #define GL_TEXTURE_RECTANGLE_ARB GL_TEXTURE_2D @@ -46,8 +48,6 @@ G_BEGIN_DECLS #define GL_UNSIGNED_SHORT_8_8_MESA 0 #define GL_UNSIGNED_SHORT_8_8_REV_MESA 0 -#define GL_COLOR_ATTACHMENT1 0 -#define GL_COLOR_ATTACHMENT2 0 #define GL_TEXTURE_ENV 0 #define GL_TEXTURE_ENV_MODE 0 #define GL_DEPTH24_STENCIL8 0 |