I am trying to stream Mat data to output video using gstreamer buffer, but
facing issues while doing so. ----- tatic GMainLoop *loop; int count = 0; VideoCapture input_video; Mat frame; GstElement *pipeline, *conv; GstElement *src, *decoder, *sink , *encoder , *qtmux , *filter; int sourceid = 0 , num_samples = 0; static void cb_newpad (GstElement *decodebin, GstPad *pad, gpointer data) { g_print ("In callback function"); GstCaps *caps; GstStructure *str; GstPad *convpad; /* only link once */ convpad = gst_element_get_static_pad (conv, "sink"); if (GST_PAD_IS_LINKED (convpad)) { g_object_unref (convpad); return; } /* link*/ gst_pad_link (pad, convpad); g_object_unref (convpad); } static void cb_need_data (GstElement *appsrc, guint unused_size, gpointer user_data) { input_video >> frame; if(frame.empty()){ /* something wrong, stop pushing */ g_main_loop_quit (loop); } cv::Mat* img = new cv::Mat(frame); gsize sizeInBytes = img->total()*img->elemSize(); GstBuffer *buffer = gst_buffer_new_wrapped_full((GstMemoryFlags)0, (gpointer)(img->data), sizeInBytes, 0, sizeInBytes, NULL , NULL); static GstClockTime timestamp = 0; GstFlowReturn ret; GST_BUFFER_PTS (buffer) = timestamp; GST_BUFFER_DTS (buffer) = timestamp; GST_BUFFER_DURATION (buffer) = gst_util_uint64_scale_int (1, GST_SECOND, 1); timestamp += GST_BUFFER_DURATION (buffer); g_signal_emit_by_name (src, "push-buffer", buffer, &ret); gst_buffer_unref (buffer); if (ret != GST_FLOW_OK) { /* something wrong, stop pushing */ g_main_loop_quit (loop); } } int main (int argc, char *argv[]) { input_video = VideoCapture(argv[1]); /* init GStreamer */ gst_init (&argc, &argv); loop = g_main_loop_new (NULL, FALSE); /* setup pipeline */ pipeline = gst_pipeline_new ("pipeline"); src = gst_element_factory_make ("appsrc", "source"); decoder = gst_element_factory_make("decodebin", "decoder"); g_signal_connect (decoder, "pad-added", G_CALLBACK (cb_newpad), NULL); conv = gst_element_factory_make ("videoconvert", "conv"); encoder = gst_element_factory_make("omxh264enc", "encoder"); qtmux = gst_element_factory_make("qtmux", "qtmux"); sink = gst_element_factory_make ("filesink", "videosink"); g_object_set (G_OBJECT (sink), "location", "final_ouput.mp4", NULL); /* setup */ g_object_set (G_OBJECT (src), "caps", gst_caps_new_simple ("video/x-raw", "format", G_TYPE_STRING, "BGR", "width", G_TYPE_INT, 1024, "height", G_TYPE_INT, 600, NULL), NULL); gst_bin_add_many (GST_BIN (pipeline), src, decoder , conv, encoder , qtmux , sink, NULL); gst_element_link (src, decoder ); gst_element_link(conv, encoder); GstPad *qtmux_sink_pad = gst_element_get_request_pad(qtmux , "video_%u"); GstPad *encoder_pad = gst_element_get_static_pad(encoder , "src"); if(gst_pad_link(encoder_pad , qtmux_sink_pad) != GST_PAD_LINK_OK){ printf("couldnt link encoder and qtmux\n"); } gst_element_link(qtmux , sink); /* setup appsrc */ g_object_set (G_OBJECT (src), "stream-type", 0, "format", GST_FORMAT_TIME, NULL); g_signal_connect (src, "need-data", G_CALLBACK (cb_need_data), NULL); /* play */ gst_element_set_state (pipeline, GST_STATE_PLAYING); g_main_loop_run (loop); /* clean up */ gst_element_set_state (pipeline, GST_STATE_NULL); gst_object_unref (GST_OBJECT (pipeline)); g_main_loop_unref (loop); return 0; } The above code works fine when the sink is xvimagesink, the video renders properly onto the xwindow, but with sink as filesink there is an issue creating the output file. running this commmand on the output video gives below info: gst-discoverer-1.0 final_output.mp4. Analyzing file:/final_output.mp4 Done discovering file:final_output.mp4 An error was encountered while discovering the file This file contains no playable streams. I could only suspect the problem with encoding , could anyone correct me if I am doing anything wrong while encoding the video stream to write onto the file. -- Sent from: http://gstreamer-devel.966125.n4.nabble.com/ _______________________________________________ gstreamer-devel mailing list [hidden email] https://lists.freedesktop.org/mailman/listinfo/gstreamer-devel |
Hi Gayathri
An MP4 dile needs an EOS pushed to the pipeline before closing, otherwise the file won’t be playable. You may: 1. Process normally as you are 2. Send an EOS to the pipeline 3. Wait for the EOS to be posted on the bus (meaning that all the elements received the EOS) 4. Tear down the pipe Michael www.ridgerun.com > On Aug 12, 2019, at 11:34 PM, gayathri1818 <[hidden email]> wrote: > > I am trying to stream Mat data to output video using gstreamer buffer, but > facing issues while doing so. > ----- > tatic GMainLoop *loop; > int count = 0; > VideoCapture input_video; > Mat frame; > GstElement *pipeline, *conv; > GstElement *src, *decoder, *sink , *encoder , *qtmux , *filter; > int sourceid = 0 , num_samples = 0; > > static void cb_newpad (GstElement *decodebin, > GstPad *pad, > gpointer data) > { > g_print ("In callback function"); > GstCaps *caps; > GstStructure *str; > GstPad *convpad; > > /* only link once */ > convpad = gst_element_get_static_pad (conv, "sink"); > if (GST_PAD_IS_LINKED (convpad)) { > g_object_unref (convpad); > return; > } > > /* link*/ > gst_pad_link (pad, convpad); > > g_object_unref (convpad); > } > > static void > cb_need_data (GstElement *appsrc, > guint unused_size, > gpointer user_data) > { > input_video >> frame; > if(frame.empty()){ > /* something wrong, stop pushing */ > g_main_loop_quit (loop); > } > cv::Mat* img = new cv::Mat(frame); > gsize sizeInBytes = img->total()*img->elemSize(); > GstBuffer *buffer = gst_buffer_new_wrapped_full((GstMemoryFlags)0, > (gpointer)(img->data), sizeInBytes, 0, sizeInBytes, NULL , NULL); > static GstClockTime timestamp = 0; > GstFlowReturn ret; > > GST_BUFFER_PTS (buffer) = timestamp; > GST_BUFFER_DTS (buffer) = timestamp; > GST_BUFFER_DURATION (buffer) = gst_util_uint64_scale_int (1, GST_SECOND, > 1); > > timestamp += GST_BUFFER_DURATION (buffer); > > g_signal_emit_by_name (src, "push-buffer", buffer, &ret); > gst_buffer_unref (buffer); > if (ret != GST_FLOW_OK) { > /* something wrong, stop pushing */ > g_main_loop_quit (loop); > } > } > > > int main (int argc, char *argv[]) > { > input_video = VideoCapture(argv[1]); > > /* init GStreamer */ > gst_init (&argc, &argv); > loop = g_main_loop_new (NULL, FALSE); > > /* setup pipeline */ > pipeline = gst_pipeline_new ("pipeline"); > src = gst_element_factory_make ("appsrc", "source"); > decoder = gst_element_factory_make("decodebin", "decoder"); > g_signal_connect (decoder, "pad-added", G_CALLBACK (cb_newpad), NULL); > conv = gst_element_factory_make ("videoconvert", "conv"); > encoder = gst_element_factory_make("omxh264enc", "encoder"); > qtmux = gst_element_factory_make("qtmux", "qtmux"); > sink = gst_element_factory_make ("filesink", "videosink"); > g_object_set (G_OBJECT (sink), "location", "final_ouput.mp4", NULL); > > /* setup */ > g_object_set (G_OBJECT (src), "caps", > gst_caps_new_simple ("video/x-raw", > "format", G_TYPE_STRING, "BGR", > "width", G_TYPE_INT, 1024, > "height", G_TYPE_INT, 600, > NULL), NULL); > gst_bin_add_many (GST_BIN (pipeline), src, decoder , conv, encoder , > qtmux , sink, NULL); > gst_element_link (src, decoder ); > gst_element_link(conv, encoder); > GstPad *qtmux_sink_pad = gst_element_get_request_pad(qtmux , > "video_%u"); > GstPad *encoder_pad = gst_element_get_static_pad(encoder , "src"); > > if(gst_pad_link(encoder_pad , qtmux_sink_pad) != GST_PAD_LINK_OK){ > printf("couldnt link encoder and qtmux\n"); > } > gst_element_link(qtmux , sink); > > /* setup appsrc */ > g_object_set (G_OBJECT (src), > "stream-type", 0, > "format", GST_FORMAT_TIME, NULL); > g_signal_connect (src, "need-data", G_CALLBACK (cb_need_data), NULL); > > /* play */ > gst_element_set_state (pipeline, GST_STATE_PLAYING); > g_main_loop_run (loop); > > /* clean up */ > gst_element_set_state (pipeline, GST_STATE_NULL); > gst_object_unref (GST_OBJECT (pipeline)); > g_main_loop_unref (loop); > > return 0; > } > The above code works fine when the sink is xvimagesink, the video renders > properly onto the xwindow, but with sink as filesink there is an issue > creating the output file. > running this commmand on the output video gives below info: > gst-discoverer-1.0 final_output.mp4. > Analyzing file:/final_output.mp4 > Done discovering file:final_output.mp4 > An error was encountered while discovering the file > This file contains no playable streams. > > I could only suspect the problem with encoding , could anyone correct me if > I am doing anything wrong while encoding the video stream to write onto the > file. > > > > > -- > Sent from: http://gstreamer-devel.966125.n4.nabble.com/ > _______________________________________________ > gstreamer-devel mailing list > [hidden email] > https://lists.freedesktop.org/mailman/listinfo/gstreamer-devel gstreamer-devel mailing list [hidden email] https://lists.freedesktop.org/mailman/listinfo/gstreamer-devel |
Free forum by Nabble | Edit this page |