I am trying to encode NV12 frames to h264 files. For that I found a following code that is encoding raw frames to jpeg using jpegenc. The code works fine with jpeg encoder after some minor changes for NV12 frames. However x264enc encode only first frame and the rest of them are outputting the pps error when running with mplayer.
First frame output
[h264 @ 0x7f1ea2ed3600]decoding for stream 0 failed
[lavf] stream 0: video (h264), -vid 0
VIDEO: [H264] 1920x1080 0bpp 1.000 fps 0.0 kbps ( 0.0 kbyte/s)
==========================================================================
Opening video decoder: [ffmpeg] FFmpeg's libavcodec codec family
libavcodec version 58.54.100 (external)
Selected video codec: [ffh264] vfm: ffmpeg (FFmpeg H.264)
==========================================================================
Load subtitles in ./
Audio: no sound
Starting playback...
Movie-Aspect is 1.78:1 - prescaling to correct movie aspect.
VO: [vdpau] 1920x1080 => 1920x1080 Planar YV12
Error frame output:
[h264 @ 0x7f9c2e44f4c0]non-existing PPS 0 referenced
[h264 @ 0x7f9c2e44f4c0]non-existing PPS 0 referenced
[h264 @ 0x7f9c2e44f4c0]decode_slice_header error
[h264 @ 0x7f9c2eece600]decoding for stream 0 failed
[h264 @ 0x7f9c2eece600]Could not find codec parameters for stream 0 (Video: h264, none): unspecified size
Consider increasing the value for the 'analyzeduration' and 'probesize' options
[lavf] stream 0: video (h264), -vid 0
VIDEO: [H264] 0x0 0bpp 25.000 fps 0.0 kbps ( 0.0 kbyte/s)
==========================================================================
Opening video decoder: [ffmpeg] FFmpeg's libavcodec codec family
libavcodec version 58.54.100 (external)
Selected video codec: [ffh264] vfm: ffmpeg (FFmpeg H.264)
I have changed the pipeline, block size and added queue. Pipeline:
pipeline = gst_pipeline_new("mypipeline");
appsrc = gst_element_factory_make("appsrc", "mysource");
queue1 = gst_element_factory_make("queue", "myqueue1");
jpegenc = gst_element_factory_make("x264enc", "myenc");
//parser = gst_element_factory_make("h264parse", "parser");
appsink = gst_element_factory_make("appsink", "mysink");
...
g_object_set(G_OBJECT(appsrc), "format", GST_FORMAT_TIME, "is-live", TRUE, "do-timestamp", TRUE, NULL);
g_object_set(G_OBJECT(jpegenc), "tune", 0x00000004, NULL); // 0x00000004 is the ultrafast preset
...
capsappsrc2Jpegenc = gst_caps_new_simple("video/x-raw", "format",
G_TYPE_STRING, "NV12", "width", G_TYPE_INT, width, "height",
G_TYPE_INT, height, "framerate", GST_TYPE_FRACTION, 1, 1,
"interlace-mode", G_TYPE_STRING, "progressive",
"colorimetry", G_TYPE_STRING, "bt601",
NULL);
// blocksize is important for jpegenc to know how many data to expect from appsrc in a single frame, too
char szTemp[64];
sprintf(szTemp, "%d", 3110400);
g_object_set(G_OBJECT (appsrc), "blocksize", szTemp,
NULL);
Encoder Setting
g_object_set(G_OBJECT(appsrc), "format", GST_FORMAT_TIME, "is-live", TRUE, "do-timestamp", TRUE, NULL);
g_object_set(G_OBJECT(jpegenc), "tune", 0x00000004, NULL); // 0x00000004 is the ultrafast preset
g_object_set(G_OBJECT(jpegenc), "speed-preset", 1, NULL); //g_object_set(G_OBJECT(jpegenc), "bitrate", 500, NULL);
g_object_set(G_OBJECT(jpegenc), "key-int-max", 1, NULL); //Maximal distance between two key-frames
g_object_set(G_OBJECT(jpegenc), "b-adapt", TRUE, NULL); g_object_set(G_OBJECT(jpegenc), "bframes", 1, NULL);