/** * gst_gl_shader_new_default: * @context: a #GstGLContext * @error: a #GError that is filled on failure * * Note: must be called in the GL thread * * Returns: (transfer full): a default @shader or %NULL on failure * * Since: 1.8 */ GstGLShader * gst_gl_shader_new_default (GstGLContext * context, GError ** error) { return gst_gl_shader_new_link_with_stages (context, error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_default_fragment (context), NULL); }
static void gst_gl_overlay_compositor_init_gl (GstGLContext * context, gpointer compositor_pointer) { GstGLOverlayCompositor *compositor = (GstGLOverlayCompositor *) compositor_pointer; GError *error = NULL; if (!(compositor->shader = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, fragment_shader), NULL))) { GST_ERROR_OBJECT (compositor, "could not initialize shader: %s", error->message); return; } compositor->position_attrib = gst_gl_shader_get_attribute_location (compositor->shader, "a_position"); compositor->texcoord_attrib = gst_gl_shader_get_attribute_location (compositor->shader, "a_texcoord"); }
static GstGLShader * gst_gl_deinterlace_get_fragment_shader (GstGLFilter * filter, const gchar * shader_name, const gchar * shader_source) { GstGLShader *shader = NULL; GstGLDeinterlace *deinterlace_filter = GST_GL_DEINTERLACE (filter); GstGLContext *context = GST_GL_BASE_FILTER (filter)->context; shader = g_hash_table_lookup (deinterlace_filter->shaderstable, shader_name); if (!shader) { GError *error = NULL; if (!(shader = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, shader_source), NULL))) { GST_ELEMENT_ERROR (deinterlace_filter, RESOURCE, NOT_FOUND, ("Failed to initialize %s shader", shader_name), (NULL)); } filter->draw_attr_position_loc = gst_gl_shader_get_attribute_location (shader, "a_position"); filter->draw_attr_texture_loc = gst_gl_shader_get_attribute_location (shader, "a_texcoord"); } g_hash_table_insert (deinterlace_filter->shaderstable, (gchar *) shader_name, shader); return shader; }
static gboolean _create_shader (GstGLAlpha * alpha) { GstGLBaseFilter *base_filter = GST_GL_BASE_FILTER (alpha); GstGLFilter *filter = GST_GL_FILTER (alpha); GError *error = NULL; if (alpha->alpha_shader) gst_object_unref (alpha->alpha_shader); if (!(alpha->alpha_shader = gst_gl_shader_new_link_with_stages (base_filter->context, &error, gst_glsl_stage_new_default_vertex (base_filter->context), gst_glsl_stage_new_with_string (base_filter->context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, alpha_frag), NULL))) { GST_ELEMENT_ERROR (alpha, RESOURCE, NOT_FOUND, ("%s", "Failed to initialize alpha shader"), ("%s", error ? error->message : "Unknown error")); return FALSE; } if (alpha->chroma_key_shader) gst_object_unref (alpha->chroma_key_shader); if (!(alpha->chroma_key_shader = gst_gl_shader_new_link_with_stages (base_filter->context, &error, gst_glsl_stage_new_default_vertex (base_filter->context), gst_glsl_stage_new_with_string (base_filter->context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, chroma_key_frag), NULL))) { GST_ELEMENT_ERROR (alpha, RESOURCE, NOT_FOUND, ("%s", "Failed to initialize chroma key shader"), ("%s", error ? error->message : "Unknown error")); return FALSE; } filter->draw_attr_position_loc = gst_gl_shader_get_attribute_location (alpha->alpha_shader, "a_position"); filter->draw_attr_texture_loc = gst_gl_shader_get_attribute_location (alpha->alpha_shader, "a_texcoord"); return TRUE; }
static void _test_compile_attach_gl (GstGLContext * context, gpointer data) { GstGLShader *shader; GstGLSLStage *vert; GError *error = NULL; shader = gst_gl_shader_new (context); vert = gst_glsl_stage_new_default_vertex (context); fail_unless (gst_gl_shader_compile_attach_stage (shader, vert, &error)); gst_object_unref (shader); }
static GstGLShader * _maybe_recompile_shader (GstGLFilterShader * filtershader) { GstGLContext *context = GST_GL_BASE_FILTER (filtershader)->context; GstGLShader *shader; GError *error = NULL; GST_OBJECT_LOCK (filtershader); if (!filtershader->shader || filtershader->update_shader) { filtershader->update_shader = FALSE; GST_OBJECT_UNLOCK (filtershader); g_signal_emit (filtershader, gst_gl_shader_signals[SIGNAL_CREATE_SHADER], 0, &shader); GST_OBJECT_LOCK (filtershader); if (shader) { if (filtershader->shader) gst_object_unref (filtershader->shader); filtershader->new_source = FALSE; filtershader->shader = gst_object_ref (shader); filtershader->new_uniforms = TRUE; _update_uniforms (filtershader); GST_OBJECT_UNLOCK (filtershader); return shader; } } if (filtershader->shader) { shader = gst_object_ref (filtershader->shader); _update_uniforms (filtershader); GST_OBJECT_UNLOCK (filtershader); return shader; } if (filtershader->new_source) { GstGLSLStage *stage; shader = gst_gl_shader_new (context); if (filtershader->vertex) { if (!(stage = gst_glsl_stage_new_with_string (context, GL_VERTEX_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_NONE, filtershader->vertex))) { g_set_error (&error, GST_GLSL_ERROR, GST_GLSL_ERROR_COMPILE, "Failed to create shader vertex stage"); goto print_error; } } else { stage = gst_glsl_stage_new_default_vertex (context); } if (!gst_gl_shader_compile_attach_stage (shader, stage, &error)) { gst_object_unref (stage); goto print_error; } if (filtershader->fragment) { if (!(stage = gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_NONE, filtershader->fragment))) { g_set_error (&error, GST_GLSL_ERROR, GST_GLSL_ERROR_COMPILE, "Failed to create shader fragment stage"); goto print_error; } } else { stage = gst_glsl_stage_new_default_fragment (context); } if (!gst_gl_shader_compile_attach_stage (shader, stage, &error)) { gst_object_unref (stage); goto print_error; } if (!gst_gl_shader_link (shader, &error)) { goto print_error; } if (filtershader->shader) gst_object_unref (filtershader->shader); filtershader->shader = gst_object_ref (shader); filtershader->new_source = FALSE; filtershader->new_uniforms = TRUE; _update_uniforms (filtershader); GST_OBJECT_UNLOCK (filtershader); return shader; } else if (filtershader->shader) { _update_uniforms (filtershader); shader = gst_object_ref (filtershader->shader); GST_OBJECT_UNLOCK (filtershader); return shader; } return NULL; print_error: if (shader) { gst_object_unref (shader); shader = NULL; } GST_OBJECT_UNLOCK (filtershader); GST_ELEMENT_ERROR (filtershader, RESOURCE, NOT_FOUND, ("%s", error->message), (NULL)); return NULL; }
/* init resources that need a gl context */ static void gst_gl_differencematte_init_gl_resources (GstGLFilter * filter) { GstGLDifferenceMatte *differencematte = GST_GL_DIFFERENCEMATTE (filter); GstGLContext *context = GST_GL_BASE_FILTER (filter)->context; const GstGLFuncs *gl = context->gl_vtable; GError *error = NULL; gint i; for (i = 0; i < 4; i++) { gl->GenTextures (1, &differencematte->midtexture[i]); gl->BindTexture (GL_TEXTURE_2D, differencematte->midtexture[i]); gl->TexImage2D (GL_TEXTURE_2D, 0, GL_RGBA8, GST_VIDEO_INFO_WIDTH (&filter->out_info), GST_VIDEO_INFO_HEIGHT (&filter->out_info), 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL); gl->TexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); gl->TexParameteri (GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); gl->TexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); gl->TexParameteri (GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); } if (!(differencematte->identity_shader = gst_gl_shader_new_default (context, &error))) { GST_ELEMENT_ERROR (differencematte, RESOURCE, NOT_FOUND, ("%s", "Failed to compile identity shader"), ("%s", error->message)); return; } if (!(differencematte->shader[0] = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, difference_fragment_source), NULL))) { GST_ELEMENT_ERROR (differencematte, RESOURCE, NOT_FOUND, ("%s", "Failed to compile difference shader"), ("%s", error->message)); return; } if (!(differencematte->shader[1] = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, hconv7_fragment_source_gles2), NULL))) { GST_ELEMENT_ERROR (differencematte, RESOURCE, NOT_FOUND, ("%s", "Failed to compile convolution shader"), ("%s", error->message)); return; } if (!(differencematte->shader[2] = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, vconv7_fragment_source_gles2), NULL))) { GST_ELEMENT_ERROR (differencematte, RESOURCE, NOT_FOUND, ("%s", "Failed to compile convolution shader"), ("%s", error->message)); return; } if (!(differencematte->shader[3] = gst_gl_shader_new_link_with_stages (context, &error, gst_glsl_stage_new_default_vertex (context), gst_glsl_stage_new_with_string (context, GL_FRAGMENT_SHADER, GST_GLSL_VERSION_NONE, GST_GLSL_PROFILE_ES | GST_GLSL_PROFILE_COMPATIBILITY, texture_interp_fragment_source), NULL))) { GST_ELEMENT_ERROR (differencematte, RESOURCE, NOT_FOUND, ("%s", "Failed to compile interpolation shader"), ("%s", error->message)); return; } /* FIXME: this should really be per shader */ filter->draw_attr_position_loc = gst_gl_shader_get_attribute_location (differencematte->shader[2], "a_position"); filter->draw_attr_texture_loc = gst_gl_shader_get_attribute_location (differencematte->shader[2], "a_texcoord"); }