mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-22 16:26:39 +00:00
eglglessink: Some refactoring as preparation for platform specific rendering
This commit is contained in:
parent
823f490fe8
commit
46c7bbfeb5
2 changed files with 177 additions and 231 deletions
|
@ -1150,15 +1150,110 @@ gst_eglglessink_context_make_current (GstEglGlesSink * eglglessink,
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
create_shader_program (GstEglGlesSink * eglglessink, GLuint * prog,
|
||||||
|
GLuint * vert, GLuint * frag, const gchar * vert_text,
|
||||||
|
const gchar * frag_text)
|
||||||
{
|
{
|
||||||
GLint test;
|
GLint test;
|
||||||
GLboolean ret;
|
|
||||||
GLchar *info_log;
|
GLchar *info_log;
|
||||||
|
|
||||||
|
/* Build shader program for video texture rendering */
|
||||||
|
*vert = glCreateShader (GL_VERTEX_SHADER);
|
||||||
|
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d", vert_text, *vert);
|
||||||
|
glShaderSource (*vert, 1, &vert_text, NULL);
|
||||||
|
if (got_gl_error ("glShaderSource vertex"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
|
glCompileShader (*vert);
|
||||||
|
if (got_gl_error ("glCompileShader vertex"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
|
glGetShaderiv (*vert, GL_COMPILE_STATUS, &test);
|
||||||
|
if (test != GL_FALSE)
|
||||||
|
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled vertex shader");
|
||||||
|
else {
|
||||||
|
GST_ERROR_OBJECT (eglglessink, "Couldn't compile vertex shader");
|
||||||
|
glGetShaderiv (*vert, GL_INFO_LOG_LENGTH, &test);
|
||||||
|
info_log = g_new0 (GLchar, test);
|
||||||
|
glGetShaderInfoLog (*vert, test, NULL, info_log);
|
||||||
|
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
||||||
|
g_free (info_log);
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
*frag = glCreateShader (GL_FRAGMENT_SHADER);
|
||||||
|
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d", frag_text, *frag);
|
||||||
|
glShaderSource (*frag, 1, &frag_text, NULL);
|
||||||
|
if (got_gl_error ("glShaderSource fragment"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
|
glCompileShader (*frag);
|
||||||
|
if (got_gl_error ("glCompileShader fragment"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
|
glGetShaderiv (*frag, GL_COMPILE_STATUS, &test);
|
||||||
|
if (test != GL_FALSE)
|
||||||
|
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled fragment shader");
|
||||||
|
else {
|
||||||
|
GST_ERROR_OBJECT (eglglessink, "Couldn't compile fragment shader");
|
||||||
|
glGetShaderiv (*frag, GL_INFO_LOG_LENGTH, &test);
|
||||||
|
info_log = g_new0 (GLchar, test);
|
||||||
|
glGetShaderInfoLog (*frag, test, NULL, info_log);
|
||||||
|
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
||||||
|
g_free (info_log);
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
*prog = glCreateProgram ();
|
||||||
|
if (got_gl_error ("glCreateProgram"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
glAttachShader (*prog, *vert);
|
||||||
|
if (got_gl_error ("glAttachShader vertices"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
glAttachShader (*prog, *frag);
|
||||||
|
if (got_gl_error ("glAttachShader fragments"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
glLinkProgram (*prog);
|
||||||
|
glGetProgramiv (*prog, GL_LINK_STATUS, &test);
|
||||||
|
if (test != GL_FALSE) {
|
||||||
|
GST_DEBUG_OBJECT (eglglessink, "GLES: Successfully linked program");
|
||||||
|
} else {
|
||||||
|
GST_ERROR_OBJECT (eglglessink, "Couldn't link program");
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
|
||||||
|
HANDLE_ERROR:
|
||||||
|
{
|
||||||
|
if (*frag && *prog)
|
||||||
|
glDetachShader (*prog, *frag);
|
||||||
|
if (*vert && *prog)
|
||||||
|
glDetachShader (*prog, *vert);
|
||||||
|
if (*prog)
|
||||||
|
glDeleteProgram (*prog);
|
||||||
|
if (*frag)
|
||||||
|
glDeleteShader (*frag);
|
||||||
|
if (*vert)
|
||||||
|
glDeleteShader (*vert);
|
||||||
|
*prog = 0;
|
||||||
|
*frag = 0;
|
||||||
|
*vert = 0;
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
|
{
|
||||||
|
GLboolean ret;
|
||||||
EGLint display_par;
|
EGLint display_par;
|
||||||
const gchar *texnames[3] = { NULL, };
|
const gchar *texnames[3] = { NULL, };
|
||||||
gchar *tmp_prog = NULL;
|
gchar *frag_prog = NULL;
|
||||||
|
gboolean free_frag_prog = FALSE;
|
||||||
EGLint swap_behavior;
|
EGLint swap_behavior;
|
||||||
|
gint i;
|
||||||
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Enter EGL surface setup");
|
GST_DEBUG_OBJECT (eglglessink, "Enter EGL surface setup");
|
||||||
|
|
||||||
|
@ -1236,41 +1331,11 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Build shader program for video texture rendering */
|
/* Build shader program for video texture rendering */
|
||||||
eglglessink->eglglesctx.vertshader[0] = glCreateShader (GL_VERTEX_SHADER);
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d", vert_COPY_prog,
|
|
||||||
eglglessink->eglglesctx.vertshader[0]);
|
|
||||||
glShaderSource (eglglessink->eglglesctx.vertshader[0], 1, &vert_COPY_prog,
|
|
||||||
NULL);
|
|
||||||
if (got_gl_error ("glShaderSource vertex"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
|
|
||||||
glCompileShader (eglglessink->eglglesctx.vertshader[0]);
|
|
||||||
if (got_gl_error ("glCompileShader vertex"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.vertshader[0], GL_COMPILE_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled vertex shader");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't compile vertex shader");
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.vertshader[0], GL_INFO_LOG_LENGTH,
|
|
||||||
&test);
|
|
||||||
info_log = g_new0 (GLchar, test);
|
|
||||||
glGetShaderInfoLog (eglglessink->eglglesctx.vertshader[0], test, NULL,
|
|
||||||
info_log);
|
|
||||||
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
|
||||||
g_free (info_log);
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
eglglessink->eglglesctx.fragshader[0] = glCreateShader (GL_FRAGMENT_SHADER);
|
|
||||||
switch (eglglessink->configured_info.finfo->format) {
|
switch (eglglessink->configured_info.finfo->format) {
|
||||||
case GST_VIDEO_FORMAT_AYUV:
|
case GST_VIDEO_FORMAT_AYUV:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d", frag_AYUV_prog,
|
frag_prog = (gchar *) frag_AYUV_prog;
|
||||||
eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = FALSE;
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1, &frag_AYUV_prog,
|
|
||||||
NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 1;
|
eglglessink->eglglesctx.n_textures = 1;
|
||||||
texnames[0] = "tex";
|
texnames[0] = "tex";
|
||||||
break;
|
break;
|
||||||
|
@ -1279,61 +1344,44 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
case GST_VIDEO_FORMAT_YV12:
|
case GST_VIDEO_FORMAT_YV12:
|
||||||
case GST_VIDEO_FORMAT_Y42B:
|
case GST_VIDEO_FORMAT_Y42B:
|
||||||
case GST_VIDEO_FORMAT_Y41B:
|
case GST_VIDEO_FORMAT_Y41B:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = (gchar *) frag_PLANAR_YUV_prog;
|
||||||
frag_PLANAR_YUV_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = FALSE;
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
&frag_PLANAR_YUV_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 3;
|
eglglessink->eglglesctx.n_textures = 3;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "Utex";
|
texnames[1] = "Utex";
|
||||||
texnames[2] = "Vtex";
|
texnames[2] = "Vtex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_YUY2:
|
case GST_VIDEO_FORMAT_YUY2:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'r', 'g', 'a');
|
||||||
frag_YUY2_YVYU_UYVY_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'r', 'g', 'a');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 2;
|
eglglessink->eglglesctx.n_textures = 2;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "UVtex";
|
texnames[1] = "UVtex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_YVYU:
|
case GST_VIDEO_FORMAT_YVYU:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'r', 'a', 'g');
|
||||||
frag_YUY2_YVYU_UYVY_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'r', 'a', 'g');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 2;
|
eglglessink->eglglesctx.n_textures = 2;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "UVtex";
|
texnames[1] = "UVtex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_UYVY:
|
case GST_VIDEO_FORMAT_UYVY:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'a', 'r', 'b');
|
||||||
frag_YUY2_YVYU_UYVY_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_YUY2_YVYU_UYVY_prog, 'a', 'r', 'b');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 2;
|
eglglessink->eglglesctx.n_textures = 2;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "UVtex";
|
texnames[1] = "UVtex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_NV12:
|
case GST_VIDEO_FORMAT_NV12:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_NV12_NV21_prog, 'r', 'a');
|
||||||
frag_NV12_NV21_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_NV12_NV21_prog, 'r', 'a');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 2;
|
eglglessink->eglglesctx.n_textures = 2;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "UVtex";
|
texnames[1] = "UVtex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_NV21:
|
case GST_VIDEO_FORMAT_NV21:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_NV12_NV21_prog, 'a', 'r');
|
||||||
frag_NV12_NV21_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_NV12_NV21_prog, 'a', 'r');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 2;
|
eglglessink->eglglesctx.n_textures = 2;
|
||||||
texnames[0] = "Ytex";
|
texnames[0] = "Ytex";
|
||||||
texnames[1] = "UVtex";
|
texnames[1] = "UVtex";
|
||||||
|
@ -1341,31 +1389,22 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
case GST_VIDEO_FORMAT_BGR:
|
case GST_VIDEO_FORMAT_BGR:
|
||||||
case GST_VIDEO_FORMAT_BGRx:
|
case GST_VIDEO_FORMAT_BGRx:
|
||||||
case GST_VIDEO_FORMAT_BGRA:
|
case GST_VIDEO_FORMAT_BGRA:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_REORDER_prog, 'b', 'g', 'r');
|
||||||
frag_REORDER_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_REORDER_prog, 'b', 'g', 'r');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 1;
|
eglglessink->eglglesctx.n_textures = 1;
|
||||||
texnames[0] = "tex";
|
texnames[0] = "tex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_xRGB:
|
case GST_VIDEO_FORMAT_xRGB:
|
||||||
case GST_VIDEO_FORMAT_ARGB:
|
case GST_VIDEO_FORMAT_ARGB:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_REORDER_prog, 'g', 'b', 'a');
|
||||||
frag_REORDER_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_REORDER_prog, 'g', 'b', 'a');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 1;
|
eglglessink->eglglesctx.n_textures = 1;
|
||||||
texnames[0] = "tex";
|
texnames[0] = "tex";
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_xBGR:
|
case GST_VIDEO_FORMAT_xBGR:
|
||||||
case GST_VIDEO_FORMAT_ABGR:
|
case GST_VIDEO_FORMAT_ABGR:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
frag_prog = g_strdup_printf (frag_REORDER_prog, 'a', 'b', 'g');
|
||||||
frag_REORDER_prog, eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = TRUE;
|
||||||
tmp_prog = g_strdup_printf (frag_REORDER_prog, 'a', 'b', 'g');
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1,
|
|
||||||
(const GLchar **) &tmp_prog, NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 1;
|
eglglessink->eglglesctx.n_textures = 1;
|
||||||
texnames[0] = "tex";
|
texnames[0] = "tex";
|
||||||
break;
|
break;
|
||||||
|
@ -1373,10 +1412,8 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
case GST_VIDEO_FORMAT_RGBx:
|
case GST_VIDEO_FORMAT_RGBx:
|
||||||
case GST_VIDEO_FORMAT_RGBA:
|
case GST_VIDEO_FORMAT_RGBA:
|
||||||
case GST_VIDEO_FORMAT_RGB16:
|
case GST_VIDEO_FORMAT_RGB16:
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d", frag_COPY_prog,
|
frag_prog = (gchar *) frag_COPY_prog;
|
||||||
eglglessink->eglglesctx.fragshader[0]);
|
free_frag_prog = FALSE;
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[0], 1, &frag_COPY_prog,
|
|
||||||
NULL);
|
|
||||||
eglglessink->eglglesctx.n_textures = 1;
|
eglglessink->eglglesctx.n_textures = 1;
|
||||||
texnames[0] = "tex";
|
texnames[0] = "tex";
|
||||||
break;
|
break;
|
||||||
|
@ -1385,61 +1422,30 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (got_gl_error ("glShaderSource fragment"))
|
if (!create_shader_program (eglglessink,
|
||||||
goto HANDLE_ERROR;
|
&eglglessink->eglglesctx.glslprogram[0],
|
||||||
|
&eglglessink->eglglesctx.vertshader[0],
|
||||||
glCompileShader (eglglessink->eglglesctx.fragshader[0]);
|
&eglglessink->eglglesctx.fragshader[0], vert_COPY_prog, frag_prog)) {
|
||||||
if (got_gl_error ("glCompileShader fragment"))
|
if (free_frag_prog)
|
||||||
goto HANDLE_ERROR;
|
g_free (frag_prog);
|
||||||
|
frag_prog = NULL;
|
||||||
glGetShaderiv (eglglessink->eglglesctx.fragshader[0], GL_COMPILE_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled fragment shader");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't compile fragment shader");
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.fragshader[0], GL_INFO_LOG_LENGTH,
|
|
||||||
&test);
|
|
||||||
info_log = g_new0 (GLchar, test);
|
|
||||||
glGetShaderInfoLog (eglglessink->eglglesctx.fragshader[0], test, NULL,
|
|
||||||
info_log);
|
|
||||||
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
|
||||||
g_free (info_log);
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
eglglessink->eglglesctx.glslprogram[0] = glCreateProgram ();
|
|
||||||
if (got_gl_error ("glCreateProgram"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glAttachShader (eglglessink->eglglesctx.glslprogram[0],
|
|
||||||
eglglessink->eglglesctx.vertshader[0]);
|
|
||||||
if (got_gl_error ("glAttachShader vertices"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glAttachShader (eglglessink->eglglesctx.glslprogram[0],
|
|
||||||
eglglessink->eglglesctx.fragshader[0]);
|
|
||||||
if (got_gl_error ("glAttachShader fragments"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glLinkProgram (eglglessink->eglglesctx.glslprogram[0]);
|
|
||||||
glGetProgramiv (eglglessink->eglglesctx.glslprogram[0], GL_LINK_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "GLES: Successfully linked program");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't link program");
|
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
}
|
}
|
||||||
|
if (free_frag_prog)
|
||||||
|
g_free (frag_prog);
|
||||||
|
frag_prog = NULL;
|
||||||
|
|
||||||
eglglessink->eglglesctx.position_loc[0] =
|
eglglessink->eglglesctx.position_loc[0] =
|
||||||
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[0], "position");
|
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[0], "position");
|
||||||
eglglessink->eglglesctx.texpos_loc =
|
eglglessink->eglglesctx.texpos_loc[0] =
|
||||||
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[0], "texpos");
|
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[0], "texpos");
|
||||||
eglglessink->eglglesctx.tex_scale_loc[0] =
|
eglglessink->eglglesctx.tex_scale_loc[0][0] =
|
||||||
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
||||||
"tex_scale0");
|
"tex_scale0");
|
||||||
eglglessink->eglglesctx.tex_scale_loc[1] =
|
eglglessink->eglglesctx.tex_scale_loc[0][1] =
|
||||||
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
||||||
"tex_scale1");
|
"tex_scale1");
|
||||||
eglglessink->eglglesctx.tex_scale_loc[2] =
|
eglglessink->eglglesctx.tex_scale_loc[0][2] =
|
||||||
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
||||||
"tex_scale2");
|
"tex_scale2");
|
||||||
|
|
||||||
|
@ -1447,88 +1453,25 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
if (got_gl_error ("glEnableVertexAttribArray"))
|
if (got_gl_error ("glEnableVertexAttribArray"))
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
glEnableVertexAttribArray (eglglessink->eglglesctx.texpos_loc);
|
glEnableVertexAttribArray (eglglessink->eglglesctx.texpos_loc[0]);
|
||||||
if (got_gl_error ("glEnableVertexAttribArray"))
|
if (got_gl_error ("glEnableVertexAttribArray"))
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
|
for (i = 0; i < eglglessink->eglglesctx.n_textures; i++) {
|
||||||
|
eglglessink->eglglesctx.tex_loc[0][i] =
|
||||||
|
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
||||||
|
texnames[i]);
|
||||||
|
}
|
||||||
|
|
||||||
if (!eglglessink->eglglesctx.buffer_preserved) {
|
if (!eglglessink->eglglesctx.buffer_preserved) {
|
||||||
/* Build shader program for black borders */
|
/* Build shader program for black borders */
|
||||||
eglglessink->eglglesctx.vertshader[1] = glCreateShader (GL_VERTEX_SHADER);
|
if (!create_shader_program (eglglessink,
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Sending %s to handle %d",
|
&eglglessink->eglglesctx.glslprogram[1],
|
||||||
vert_COPY_prog_no_tex, eglglessink->eglglesctx.vertshader[1]);
|
&eglglessink->eglglesctx.vertshader[1],
|
||||||
glShaderSource (eglglessink->eglglesctx.vertshader[1], 1,
|
&eglglessink->eglglesctx.fragshader[1], vert_COPY_prog_no_tex,
|
||||||
&vert_COPY_prog_no_tex, NULL);
|
frag_BLACK_prog))
|
||||||
if (got_gl_error ("glShaderSource vertex"))
|
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
glCompileShader (eglglessink->eglglesctx.vertshader[1]);
|
|
||||||
if (got_gl_error ("glCompileShader vertex"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.vertshader[1], GL_COMPILE_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled vertex shader");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't compile vertex shader");
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.vertshader[1], GL_INFO_LOG_LENGTH,
|
|
||||||
&test);
|
|
||||||
info_log = g_new0 (GLchar, test);
|
|
||||||
glGetShaderInfoLog (eglglessink->eglglesctx.vertshader[1], test, NULL,
|
|
||||||
info_log);
|
|
||||||
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
|
||||||
g_free (info_log);
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
eglglessink->eglglesctx.fragshader[1] = glCreateShader (GL_FRAGMENT_SHADER);
|
|
||||||
glShaderSource (eglglessink->eglglesctx.fragshader[1], 1, &frag_BLACK_prog,
|
|
||||||
NULL);
|
|
||||||
|
|
||||||
if (got_gl_error ("glShaderSource fragment"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
|
|
||||||
glCompileShader (eglglessink->eglglesctx.fragshader[1]);
|
|
||||||
if (got_gl_error ("glCompileShader fragment"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.fragshader[1], GL_COMPILE_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Successfully compiled fragment shader");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't compile fragment shader");
|
|
||||||
glGetShaderiv (eglglessink->eglglesctx.fragshader[1], GL_INFO_LOG_LENGTH,
|
|
||||||
&test);
|
|
||||||
info_log = g_new0 (GLchar, test);
|
|
||||||
glGetShaderInfoLog (eglglessink->eglglesctx.fragshader[1], test, NULL,
|
|
||||||
info_log);
|
|
||||||
GST_INFO_OBJECT (eglglessink, "Compilation info log:\n%s", info_log);
|
|
||||||
g_free (info_log);
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
eglglessink->eglglesctx.glslprogram[1] = glCreateProgram ();
|
|
||||||
if (got_gl_error ("glCreateProgram"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glAttachShader (eglglessink->eglglesctx.glslprogram[1],
|
|
||||||
eglglessink->eglglesctx.vertshader[1]);
|
|
||||||
if (got_gl_error ("glAttachShader vertices"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glAttachShader (eglglessink->eglglesctx.glslprogram[1],
|
|
||||||
eglglessink->eglglesctx.fragshader[1]);
|
|
||||||
if (got_gl_error ("glAttachShader fragments"))
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
glLinkProgram (eglglessink->eglglesctx.glslprogram[1]);
|
|
||||||
glGetProgramiv (eglglessink->eglglesctx.glslprogram[1], GL_LINK_STATUS,
|
|
||||||
&test);
|
|
||||||
if (test != GL_FALSE)
|
|
||||||
GST_DEBUG_OBJECT (eglglessink, "GLES: Successfully linked program");
|
|
||||||
else {
|
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't link program");
|
|
||||||
goto HANDLE_ERROR;
|
|
||||||
}
|
|
||||||
|
|
||||||
eglglessink->eglglesctx.position_loc[1] =
|
eglglessink->eglglesctx.position_loc[1] =
|
||||||
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[1],
|
glGetAttribLocation (eglglessink->eglglesctx.glslprogram[1],
|
||||||
"position");
|
"position");
|
||||||
|
@ -1538,12 +1481,8 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
glUseProgram (eglglessink->eglglesctx.glslprogram[0]);
|
/* Generate textures */
|
||||||
|
|
||||||
/* Generate and bind texture */
|
|
||||||
if (!eglglessink->have_texture) {
|
if (!eglglessink->have_texture) {
|
||||||
gint i;
|
|
||||||
|
|
||||||
GST_INFO_OBJECT (eglglessink, "Performing initial texture setup");
|
GST_INFO_OBJECT (eglglessink, "Performing initial texture setup");
|
||||||
|
|
||||||
for (i = 0; i < eglglessink->eglglesctx.n_textures; i++) {
|
for (i = 0; i < eglglessink->eglglesctx.n_textures; i++) {
|
||||||
|
@ -1560,12 +1499,7 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
|
|
||||||
glBindTexture (GL_TEXTURE_2D, eglglessink->eglglesctx.texture[i]);
|
glBindTexture (GL_TEXTURE_2D, eglglessink->eglglesctx.texture[i]);
|
||||||
if (got_gl_error ("glBindTexture"))
|
if (got_gl_error ("glBindTexture"))
|
||||||
goto HANDLE_ERROR_LOCKED;
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
eglglessink->eglglesctx.tex_loc[i] =
|
|
||||||
glGetUniformLocation (eglglessink->eglglesctx.glslprogram[0],
|
|
||||||
texnames[i]);
|
|
||||||
glUniform1i (eglglessink->eglglesctx.tex_loc[i], i);
|
|
||||||
|
|
||||||
/* Set 2D resizing params */
|
/* Set 2D resizing params */
|
||||||
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
glTexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
|
||||||
|
@ -1582,9 +1516,8 @@ gst_eglglessink_init_egl_surface (GstEglGlesSink * eglglessink)
|
||||||
|
|
||||||
eglglessink->have_texture = TRUE;
|
eglglessink->have_texture = TRUE;
|
||||||
}
|
}
|
||||||
glUseProgram (0);
|
|
||||||
|
|
||||||
g_free (tmp_prog);
|
glUseProgram (0);
|
||||||
|
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
|
||||||
|
@ -1594,7 +1527,6 @@ HANDLE_EGL_ERROR_LOCKED:
|
||||||
HANDLE_ERROR_LOCKED:
|
HANDLE_ERROR_LOCKED:
|
||||||
HANDLE_ERROR:
|
HANDLE_ERROR:
|
||||||
GST_ERROR_OBJECT (eglglessink, "Couldn't setup EGL surface");
|
GST_ERROR_OBJECT (eglglessink, "Couldn't setup EGL surface");
|
||||||
g_free (tmp_prog);
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1790,6 +1722,7 @@ gst_eglglessink_render_and_display (GstEglGlesSink * eglglessink,
|
||||||
GstVideoFrame vframe;
|
GstVideoFrame vframe;
|
||||||
guint dar_n, dar_d;
|
guint dar_n, dar_d;
|
||||||
GstVideoCropMeta *crop = NULL;
|
GstVideoCropMeta *crop = NULL;
|
||||||
|
gint i;
|
||||||
|
|
||||||
memset (&vframe, 0, sizeof (vframe));
|
memset (&vframe, 0, sizeof (vframe));
|
||||||
|
|
||||||
|
@ -2390,19 +2323,32 @@ gst_eglglessink_render_and_display (GstEglGlesSink * eglglessink,
|
||||||
GST_DEBUG_OBJECT (eglglessink, "Drawing video frame");
|
GST_DEBUG_OBJECT (eglglessink, "Drawing video frame");
|
||||||
glUseProgram (eglglessink->eglglesctx.glslprogram[0]);
|
glUseProgram (eglglessink->eglglesctx.glslprogram[0]);
|
||||||
|
|
||||||
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[0], eglglessink->stride[0],
|
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[0][0],
|
||||||
1);
|
eglglessink->stride[0], 1);
|
||||||
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[1], eglglessink->stride[1],
|
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[0][1],
|
||||||
1);
|
eglglessink->stride[1], 1);
|
||||||
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[2], eglglessink->stride[2],
|
glUniform2f (eglglessink->eglglesctx.tex_scale_loc[0][2],
|
||||||
1);
|
eglglessink->stride[2], 1);
|
||||||
|
|
||||||
|
for (i = 0; i < eglglessink->eglglesctx.n_textures; i++) {
|
||||||
|
if (i == 0)
|
||||||
|
glActiveTexture (GL_TEXTURE0);
|
||||||
|
else if (i == 1)
|
||||||
|
glActiveTexture (GL_TEXTURE1);
|
||||||
|
else if (i == 2)
|
||||||
|
glActiveTexture (GL_TEXTURE2);
|
||||||
|
|
||||||
|
glUniform1i (eglglessink->eglglesctx.tex_loc[0][i], i);
|
||||||
|
if (got_gl_error ("glUniform1i"))
|
||||||
|
goto HANDLE_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
glVertexAttribPointer (eglglessink->eglglesctx.position_loc[0], 3,
|
glVertexAttribPointer (eglglessink->eglglesctx.position_loc[0], 3,
|
||||||
GL_FLOAT, GL_FALSE, sizeof (coord5), (gpointer) (0 * sizeof (coord5)));
|
GL_FLOAT, GL_FALSE, sizeof (coord5), (gpointer) (0 * sizeof (coord5)));
|
||||||
if (got_gl_error ("glVertexAttribPointer"))
|
if (got_gl_error ("glVertexAttribPointer"))
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
|
|
||||||
glVertexAttribPointer (eglglessink->eglglesctx.texpos_loc, 2, GL_FLOAT,
|
glVertexAttribPointer (eglglessink->eglglesctx.texpos_loc[0], 2, GL_FLOAT,
|
||||||
GL_FALSE, sizeof (coord5), (gpointer) (3 * sizeof (gfloat)));
|
GL_FALSE, sizeof (coord5), (gpointer) (3 * sizeof (gfloat)));
|
||||||
if (got_gl_error ("glVertexAttribPointer"))
|
if (got_gl_error ("glVertexAttribPointer"))
|
||||||
goto HANDLE_ERROR;
|
goto HANDLE_ERROR;
|
||||||
|
|
|
@ -124,9 +124,9 @@ struct _GstEglGlesRenderContext
|
||||||
EGLNativeWindowType window, used_window;
|
EGLNativeWindowType window, used_window;
|
||||||
EGLSurface surface;
|
EGLSurface surface;
|
||||||
gboolean buffer_preserved;
|
gboolean buffer_preserved;
|
||||||
GLuint fragshader[2]; /* frame, border */
|
GLuint fragshader[3]; /* frame, border, frame-platform */
|
||||||
GLuint vertshader[2]; /* frame, border */
|
GLuint vertshader[3]; /* frame, border, frame-platform */
|
||||||
GLuint glslprogram[2]; /* frame, border */
|
GLuint glslprogram[3]; /* frame, border, frame-platform */
|
||||||
GLuint texture[3]; /* RGB/Y, U/UV, V */
|
GLuint texture[3]; /* RGB/Y, U/UV, V */
|
||||||
EGLint surface_width;
|
EGLint surface_width;
|
||||||
EGLint surface_height;
|
EGLint surface_height;
|
||||||
|
@ -135,10 +135,10 @@ struct _GstEglGlesRenderContext
|
||||||
gint n_textures;
|
gint n_textures;
|
||||||
|
|
||||||
/* shader vars */
|
/* shader vars */
|
||||||
GLuint position_loc[2]; /* frame, border */
|
GLuint position_loc[3]; /* frame, border, frame-platform */
|
||||||
GLuint texpos_loc; /* frame */
|
GLuint texpos_loc[2]; /* frame, frame-platform */
|
||||||
GLuint tex_scale_loc[3]; /* RGB/Y, U/UV, V */
|
GLuint tex_scale_loc[2][3]; /* [frame, frame-platform] RGB/Y, U/UV, V */
|
||||||
GLuint tex_loc[3]; /* RGB/Y, U/UV, V */
|
GLuint tex_loc[2][3]; /* [frame, frame-platform] RGB/Y, U/UV, V */
|
||||||
coord5 position_array[12]; /* 4 x Frame, 4 x Border1, 4 x Border2 */
|
coord5 position_array[12]; /* 4 x Frame, 4 x Border1, 4 x Border2 */
|
||||||
unsigned short index_array[4];
|
unsigned short index_array[4];
|
||||||
unsigned int position_buffer, index_buffer;
|
unsigned int position_buffer, index_buffer;
|
||||||
|
|
Loading…
Reference in a new issue