AW: Dynamic change of glshader element (Dušan Poizl)

Matthew Waters waters.matthew00 at gmail.com
Sat Nov 15 18:29:00 PST 2014


On 16/11/14 02:14, Christian Winkler wrote:
> Dear Dusan,
>
> thanks. I tried that.
>
> gst_gl_shader_compile (data->distortion,&glerror);
> gives me a 
> 11-15 15:44:46.812: E/GLib(16781): gst_gl_shader_compile: assertion 'GST_GL_IS_SHADER (shader)' failed
>
>   if(gst_gl_shader_is_compiled (data->distortion)){
> 	  gst_gl_shader_set_uniform_1f(data->distortion, "test", 0.1);
>   }
> gives me a 
> 11-15 15:44:46.812: E/GLib(16781): gst_gl_shader_is_compiled: assertion 'GST_GL_IS_SHADER (shader)' failed
>
> If i use 
> gst_gl_shader_set_uniform_1f(data->distortion, "test", 0.1);
> i get a segmentation violation.
>
>
> I simply do not get where to put the gst_gl_shader_set_uniform.... stuff.


A couple of things, glshader the element (gstglfiltershader.c in the
source code) is different to GstGLShader.  The latter provides a simple
abstraction for GLSL shaders and the couple of different ways you have
to instantiate them.

Currently, the glshader element does not expose the GstGLShader it
uses.  In order to support dynamically changing the shader source or
setting uniforms, it would make sense to expose that so that the
application has that ability.  It would also get rid of the
shadervariables code :).  Then you could retreive/set the GstGLShader on
the glshader element with your uniforms already set.

> /* Main method for the native code. This is executed on its own thread. */
> static void *app_function (void *userdata) {
>   JavaVMAttachArgs args;
>   GstBus *bus;
>   CustomData *data =CustomData *)userdata;
>   GSource *bus_source;
>   GError *error =ULL;
>   GError *glerror =ULL;
>   GstCaps *filtercaps;
>   gboolean false =;
>   gboolean true =;
>
>   GST_DEBUG ("Creating pipeline in CustomData at %p", data);
>
>   /* Create our own GLib Main Context and make it the default one */
>   data->context =_main_context_new ();
>   g_main_context_push_thread_default(data->context);
>
>   /****************************************************************/
>   /* Build pipeline */
>   data->pipeline =st_pipeline_new ("fpv-pipeline");
>   data->depayloader  =st_element_factory_make ("rtph264depay","rtph264depay");
>   data->decoder  =st_element_factory_make ("decodebin","decodebin");
>   data->video_sink =st_element_factory_make ("glimagesink","glimagesink");
>   data->distortion =st_element_factory_make ("glshader","glshader");
>   data->filter=t_element_factory_make("capsfilter","filter");
>
>   if(pipelineNumberFromJava=) { //RTSP
> 	// rtspsrc location=sp://192.168.137.240:8554/test latency=0 drop-on-latency=true ! application/x-rtp, payload� ! rtph264depay ! decodebin ! glimagesink  sync�lse
> 	data->source =st_element_factory_make ("rtspsrc","rtspsrc");
>   	g_object_set(G_OBJECT (data->source),"location",pipelineParameterFromJava,"latency",0,"drop-on-latency",true,NULL);
>   	data->filter=t_element_factory_make("capsfilter","filter");
>   	filtercaps =st_caps_new_simple ("application/x-rtp","payload", G_TYPE_INT, 96,NULL);
>   	g_object_set (G_OBJECT (data->distortion), "location", "/data/data/com.lonestar.groundpi/files/distortion.frag", NULL);
>   	gst_caps_unref (filtercaps);
>   	g_object_set(G_OBJECT (data->video_sink),"sync",false,NULL);
>
>   	if (!data->pipeline || !data->source || !data->filter || !data->depayloader || !data->decoder || !data->video_sink || !data->distortion) {
>   	  g_printerr ("One element could not be created. Exiting.\n");
>   	  return -1;
>   	}
>
>   	if(cardboardModeEnabled){
> 	  	gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->depayloader, data->decoder, data->video_sink, data->distortion, NULL);
> 	  	gst_element_link_many (data->filter, data->depayloader, data->decoder, NULL);
> 	  	gst_element_link_many (data->distortion, data->video_sink, NULL);
> 	  	g_signal_connect (data->source, "pad-added", G_CALLBACK (cb_new_pad), data->filter);
> 	  	g_signal_connect (data->decoder, "pad-added", G_CALLBACK (cb_new_pad), data->distortion);
> 	} else {
> 	  	gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->depayloader, data->decoder, data->video_sink, NULL);
> 	  	gst_element_link_many (data->filter, data->depayloader, data->decoder, NULL);
> 	  	g_signal_connect (data->source, "pad-added", G_CALLBACK (cb_new_pad), data->filter);
> 	  	g_signal_connect (data->decoder, "pad-added", G_CALLBACK (cb_new_pad), data->video_sink);
> 	}
>
>
>   } else if( pipelineNumberFromJava=) { //UDP
> 	// udpsrc port�00 ! application/x-rtp, payload� ! rtph264depay ! decodebin ! glimagesink sync�lse
>   	data->source =st_element_factory_make ("udpsrc","udpsrc");
>   	g_object_set(G_OBJECT (data->source),"port",9000,NULL);
>   	g_object_set (G_OBJECT (data->distortion), "location", "/data/data/com.lonestar.groundpi/files/distortion.frag", NULL);
>   	filtercaps =st_caps_new_simple ("application/x-rtp","payload", G_TYPE_INT, 96,NULL);
>   	g_object_set (G_OBJECT (data->filter), "caps", filtercaps, NULL);
>   	gst_caps_unref (filtercaps);
>   	g_object_set(G_OBJECT (data->video_sink),"sync",false,NULL);
>
>   	if (!data->pipeline || !data->source || !data->filter || !data->depayloader || !data->decoder || !data->video_sink || !data->distortion) {
>   	  g_printerr ("One element could not be created. Exiting.\n");
>   	  return -1;
>   	}
>
>   	if(cardboardModeEnabled){
> 	  	gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->depayloader, data->decoder, data->distortion, data->video_sink, NULL);
> 	  	gst_element_link_many (data->source, data->filter, data->depayloader, data->decoder, NULL);
> 	  	gst_element_link_many (data->distortion, data->video_sink, NULL);
> 	  	g_signal_connect (data->decoder, "pad-added", G_CALLBACK (cb_new_pad), data->distortion);
> 	} else {
>   		gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->depayloader, data->decoder, data->video_sink, NULL);
>  		gst_element_link_many (data->source, data->filter, data->depayloader, data->decoder, NULL);
>  		g_signal_connect (data->decoder, "pad-added", G_CALLBACK (cb_new_pad), data->video_sink);
> 	}
>
>   } else if( pipelineNumberFromJava=) { //TestPipeline
>   	data->source =st_element_factory_make ("videotestsrc","videotestsrc");
>   	g_object_set (G_OBJECT (data->distortion), "location", "/data/data/com.lonestar.groundpi/files/distortion.frag", NULL);
>   	filtercaps =st_caps_new_simple ("video/x-raw","width", G_TYPE_INT, 1280,"height", G_TYPE_INT,720,NULL);
>   	g_object_set (G_OBJECT (data->filter), "caps", filtercaps, NULL);
>   	gst_caps_unref (filtercaps);
>
>   	if (!data->pipeline || !data->source || !data->filter || !data->video_sink || !data->distortion) {
>   	  g_printerr ("One element could not be created. Exiting.\n");
>   	  return -1;
>   	}
>
>   	if(cardboardModeEnabled){
> 	  	gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->distortion, data->video_sink, NULL);
> 	  	gst_element_link_many (data->source, data->filter, data->distortion, data->video_sink, NULL);
> 	} else {
> 	  	gst_bin_add_many (GST_BIN (data->pipeline), data->source, data->filter, data->video_sink, NULL);
> 	  	gst_element_link_many (data->source, data->filter, data->video_sink, NULL);
> 	}
>
>   } else { // Complete Pipelines from app...
> 	data->pipeline =st_parse_launch(pipelineParameterFromJava, &error);
>   }
>   /****************************************************************/
>   if (error) {
>     gchar *message =_strdup_printf("Unable to build pipeline: %s", error->message);
>     g_clear_error (&error);
>     set_ui_message(message, data);
>     g_free (message);
>     return NULL;
>   }
>
>   /* Set the pipeline to READY, so it can already accept a window handle, if we have one */
>   gst_element_set_state(data->pipeline, GST_STATE_READY);
>
>   data->video_sink =st_bin_get_by_interface(GST_BIN(data->pipeline), GST_TYPE_VIDEO_OVERLAY);
>   if (!data->video_sink) {
>     GST_ERROR ("Could not retrieve video sink");
>     return NULL;
>   }
>
>   /* Instruct the bus to emit signals for each received message, and connect to the interesting signals */
>   bus =st_element_get_bus (data->pipeline);
>   bus_source =st_bus_create_watch (bus);
>   g_source_set_callback (bus_source, (GSourceFunc) gst_bus_async_signal_func, NULL, NULL);
>   g_source_attach (bus_source, data->context);
>   g_source_unref (bus_source);
>   g_signal_connect (G_OBJECT (bus), "message::error", (GCallback)error_cb, data);
>   g_signal_connect (G_OBJECT (bus), "message::state-changed", (GCallback)state_changed_cb, data);
>   g_signal_connect (G_OBJECT (bus), "message::clock-lost", (GCallback)clock_lost_cb, data);
>
>   gst_object_unref (bus);
>
>   /* Create a GLib Main Loop and set it to run */
>   GST_DEBUG ("Entering main loop... (CustomData:%p)", data);
>   data->main_loop =_main_loop_new (data->context, FALSE);
>   check_initialization_complete (data);
>   g_main_loop_run (data->main_loop);
>   GST_DEBUG ("Exited main loop");
>   g_main_loop_unref (data->main_loop);
>   data->main_loop =ULL;
>
>   /* Free resources */
>   g_main_context_pop_thread_default(data->context);
>   g_main_context_unref (data->context);
>   gst_element_set_state (data->pipeline, GST_STATE_NULL);
>   gst_object_unref (data->video_sink);
>   gst_object_unref (data->source);
>   gst_object_unref (data->filter);
>   gst_object_unref (data->depayloader);
>   gst_object_unref (data->decoder);
>   gst_object_unref (data->pipeline);
>
>   return NULL;
> }
>
>
>
> -----Ursprüngliche Nachricht-----
> Von: gstreamer-devel [mailto:gstreamer-devel-bounces at lists.freedesktop.org] Im Auftrag von Dušan Poizl
> Gesendet: Samstag, 15. November 2014 14:04
> An: Discussion of the development of and with GStreamer
> Betreff: Re: Dynamic change of glshader element (Dušan Poizl)
>
> exactly that element. in your case distortion. refer to GstGLShader doc http://gstreamer.freedesktop.org/data/doc/gstreamer/head/gst-plugins-bad-libs/html/gst-plugins-bad-libs-gstglshader.html
>
> Dňa 15.11.2014 o 13:42 Christian Winkler napísal(a):
>> Thanks!
>>
>> What is "shader" in your example?
>> How can i access taht in native code?
>> Im am setting up the element like this:
>>
>> GstElement *distortion;
>> distortion =st_element_factory_make ("glshader","glshader");
>>
>> Kind regards
>> Christian
>>
>>
>>
>>
>>
>> change it to uniform variable. "uniform vec2 leftCenter;"
>>
>> then you should be able to change it with 
>> gst_gl_shader_set_uniform_2f(shader, "leftCenter", x, y);
>>
>> Dňa 15.11.2014 o 11:10 Christian Winkler napísal(a):
>>> Dear Members,
>>>
>>>  
>>>
>>> i am trying to change a glshader element at runtime in a native 
>>> Gstreamer application.
>>>
>>>  
>>>
>>> The idea is to convert a rtsp Stream to an side-by-side view for a 
>>> android google cardboard VR device.
>>>
>>> I want to implement headtracking as well and therefore want to change 
>>> the opengl fragment dynamically based on head position.
>>>
>>>  
>>>
>>> The code below works for a static .frag file.
>>>
>>>  
>>>
>>> QUESTION: How can i change for example
>>>
>>> _const_vec2 leftCenter =ec2(0.25, 0.4);
>>>
>>> _const_vec2 rightCenter =ec2(0.75, 0.4);
>>>
>>> DYNAMICALLY during runtime in the native code?
>>>
>>>  
>>>
>>> There used tob o something like gstglfiltershader, but i can not find 
>>> a similar functionality in the current 1.4.x releases.
>>>
>>>  
>>>
>>> Thanks!!!!
>>>
>>> Kind regards
>>>
>>> Christian
>>>
>>>  
>>>
>>>  
>>>
>>> The current Pipeline is set up as follows (JNI Code for an Android App).
>>>
>>> This
>>>
>>>  
>>>
>>>  
>>>
>>>                 ….
>>>
>>>                 // rtspsrc location=sp://192.168.137.240:8554/test
>>> latency=drop-on-latency=true ! application/x-rtp, payload� !
>>> rtph264depay ! decodebin ! glimagesink  sync�lse
>>>
>>>                 data->source =st_element_factory_make 
>>> ("rtspsrc","rtspsrc");
>>>
>>>                 g_object_set(G_OBJECT
>>> (data->source),"location",pipelineParameterFromJava,"latency",0,"drop
>>> -
>>> on-latency",true,NULL);
>>>
>>>  
>>>
>>>                 data->pipeline =st_pipeline_new ("fpv-pipeline");
>>>
>>>                
>>> data->filter=t_element_factory_make("capsfilter","filter");
>>>
>>>                 data->depayloader  =st_element_factory_make 
>>> ("rtph264depay","rtph264depay");
>>>
>>>                 data->decoder  =st_element_factory_make 
>>> ("decodebin","decodebin");
>>>
>>>                 data->distortion =st_element_factory_make 
>>> ("glshader","glshader");
>>>
>>>                 data->video_sink =st_element_factory_make 
>>> ("glimagesink","glimagesink");
>>>
>>>  
>>>
>>>                 filtercaps =st_caps_new_simple 
>>> ("application/x-rtp","payload", G_TYPE_INT, 96,NULL);
>>>
>>>                 g_object_set (G_OBJECT (data->filter), "caps", 
>>> filtercaps, NULL);
>>>
>>>                 g_object_set (G_OBJECT (data->distortion), 
>>> "location", "/data/data/com.lonestar.groundpi/files/distortion.frag", 
>>> NULL);
>>>
>>>                 gst_caps_unref (filtercaps);
>>>
>>>                 g_object_set(G_OBJECT 
>>> (data->video_sink),"sync",false,NULL);
>>>
>>>  
>>>
>>>                 if (!data->pipeline || !data->source || !data->filter
>>> || !data->depayloader || !data->decoder || !data->video_sink ||
>>> !data->distortion) {
>>>
>>>                   g_printerr ("One element could not be created.
>>> Exiting.\n");
>>>
>>>                   return -1;
>>>
>>>                 }
>>>
>>>  
>>>
>>>                 gst_bin_add_many (GST_BIN (data->pipeline),
>>> data->source, data->filter, data->depayloader, data->decoder, 
>>> data->video_sink, data->distortion, NULL);
>>>
>>>                 gst_element_link_many (data->filter,
>>> data->depayloader, data->decoder, NULL);
>>>
>>>                 gst_element_link_many (data->distortion,
>>> data->video_sink, NULL);
>>>
>>>                 g_signal_connect (data->source, "pad-added", 
>>> G_CALLBACK (cb_new_pad), data->filter);
>>>
>>>                 g_signal_connect (data->decoder, "pad-added", 
>>> G_CALLBACK (cb_new_pad), data->distortion);
>>>
>>> ….
>>>
>>>  
>>>
>>>  
>>>
>>>  
>>>
>>>  
>>>
>>> Distortion.frag:
>>>
>>>  
>>>
>>> #extension GL_ARB_texture_rectangle : enable
>>>
>>> precision _mediump_ float;
>>>
>>> varying vec2 v_texcoord;
>>>
>>> uniform sampler2D _tex_;
>>>
>>> _const_vec4 _kappa_ =ec4(2.75,1.7,0.5,0.5);
>>>
>>> _const_float screen_width =920.0;
>>>
>>> _const_float screen_height =080.0;
>>>
>>> _const_float scaleFactor =.62;
>>>
>>> _const_vec2 leftCenter =ec2(0.25, 0.4);
>>>
>>> _const_vec2 rightCenter =ec2(0.75, 0.4);
>>>
>>> _const_float separation =0.025;
>>>
>>> _const__bool_ stereo_input =alse;
>>>
>>>  
>>>
>>> // Scales input texture coordinates for distortion.
>>>
>>> vec2 hmdWarp(vec2 LensCenter, vec2 texCoord, vec2 Scale, vec2 
>>> ScaleIn) {
>>>
>>> vec2 _theta_ =texCoord - LensCenter) * ScaleIn;
>>>
>>> float rSq =heta.x * theta.x + theta.y * theta.y;
>>>
>>> vec2 _rvector_ =theta_ * (kappa.x + kappa.y * rSq + kappa.z * rSq * 
>>> rSq + kappa.w * rSq * rSq * rSq);
>>>
>>> vec2 _tc_ =ensCenter + Scale * _rvector_;
>>>
>>> return _tc_;
>>>
>>> }
>>>
>>> _bool_validate(vec2 _tc_, _int_ eye) {
>>>
>>> if ( stereo_input ) {
>>>
>>> //keep within bounds of texture
>>>
>>> if ((eye =1 && (tc.x < 0.0 || tc.x > 0.5)) ||
>>>
>>> (eye =0 && (tc.x < 0.5 || tc.x > 1.0)) ||
>>>
>>> tc.y < 0.0 || tc.y > 1.0) {
>>>
>>> return false;
>>>
>>> }
>>>
>>> } else {
>>>
>>> if ( tc.x < 0.0 || tc.x > 1.0 ||
>>>
>>> tc.y < 0.0 || tc.y > 1.0 ) {
>>>
>>> return false;
>>>
>>> }
>>>
>>> }
>>>
>>> return true;
>>>
>>> }
>>>
>>> void main() {
>>>
>>> float as =loat(screen_width / 2.0) / float(screen_height);
>>>
>>> vec2 Scale =ec2(0.25, as);
>>>
>>> vec2 ScaleIn =ec2(2.0 * scaleFactor, 1.0 / as * scaleFactor);
>>>
>>> vec2 texCoord =_texcoord;
>>>
>>> vec2 _tc_ =ec2(0);
>>>
>>> vec4 color =ec4(0);
>>>
>>> if ( texCoord.x < 0.5 ) {
>>>
>>> texCoord.x +=eparation;
>>>
>>> texCoord =mdWarp(leftCenter, texCoord, Scale, ScaleIn );
>>>
>>> if ( !stereo_input ) {
>>>
>>> texCoord.x *=.0;
>>>
>>> }
>>>
>>> color =exture2D(_tex_, texCoord);
>>>
>>> if ( !validate(texCoord, 0) ) {
>>>
>>> color =ec4(0);
>>>
>>> }
>>>
>>> } else {
>>>
>>> texCoord.x -=eparation;
>>>
>>> texCoord =mdWarp(rightCenter, texCoord, Scale, ScaleIn);
>>>
>>> if ( !stereo_input ) {
>>>
>>> texCoord.x =texCoord.x - 0.5) * 2.0;
>>>
>>> }
>>>
>>> color =exture2D(_tex_, texCoord);
>>>
>>> if ( !validate(texCoord, 1) ) {
>>>
>>> color =ec4(0);
>>>
>>> }
>>>
>>> }
>>>
>>> gl_FragColor =olor;
>>>
>>> }
>>>
>>>  
>>>
>>>  
>>>
>>>  
>>>
>>>  
>>>
>>>
>>>
>>> _______________________________________________
>>> gstreamer-devel mailing list
>>> gstreamer-devel at lists.freedesktop.org
>>> http://lists.freedesktop.org/mailman/listinfo/gstreamer-devel
>> -------------- next part -------------- An HTML attachment was 
>> scrubbed...
>> URL: 
>> <http://lists.freedesktop.org/archives/gstreamer-devel/attachments/201
>> 41115/755b9301/attachment.html>
>>
>> ------------------------------
>>
>> Subject: Digest Footer
>>
>> _______________________________________________
>> gstreamer-devel mailing list
>> gstreamer-devel at lists.freedesktop.org
>> http://lists.freedesktop.org/mailman/listinfo/gstreamer-devel
>>
>>
>> ------------------------------
>>
>> End of gstreamer-devel Digest, Vol 46, Issue 43
>> ***********************************************
>>
>> _______________________________________________
>> gstreamer-devel mailing list
>> gstreamer-devel at lists.freedesktop.org
>> http://lists.freedesktop.org/mailman/listinfo/gstreamer-devel
> _______________________________________________
> gstreamer-devel mailing list
> gstreamer-devel at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/gstreamer-devel
>
>



More information about the gstreamer-devel mailing list