Recherche avancée

Médias (0)

Mot : - Tags -/médias

Aucun média correspondant à vos critères n’est disponible sur le site.

Autres articles (84)

  • MediaSPIP version 0.1 Beta

    16 avril 2011, par

    MediaSPIP 0.1 beta est la première version de MediaSPIP décrétée comme "utilisable".
    Le fichier zip ici présent contient uniquement les sources de MediaSPIP en version standalone.
    Pour avoir une installation fonctionnelle, il est nécessaire d’installer manuellement l’ensemble des dépendances logicielles sur le serveur.
    Si vous souhaitez utiliser cette archive pour une installation en mode ferme, il vous faudra également procéder à d’autres modifications (...)

  • MediaSPIP 0.1 Beta version

    25 avril 2011, par

    MediaSPIP 0.1 beta is the first version of MediaSPIP proclaimed as "usable".
    The zip file provided here only contains the sources of MediaSPIP in its standalone version.
    To get a working installation, you must manually install all-software dependencies on the server.
    If you want to use this archive for an installation in "farm mode", you will also need to proceed to other manual (...)

  • Amélioration de la version de base

    13 septembre 2013

    Jolie sélection multiple
    Le plugin Chosen permet d’améliorer l’ergonomie des champs de sélection multiple. Voir les deux images suivantes pour comparer.
    Il suffit pour cela d’activer le plugin Chosen (Configuration générale du site > Gestion des plugins), puis de configurer le plugin (Les squelettes > Chosen) en activant l’utilisation de Chosen dans le site public et en spécifiant les éléments de formulaires à améliorer, par exemple select[multiple] pour les listes à sélection multiple (...)

Sur d’autres sites (12677)

  • Encode image to video using ffmpeg

    4 juillet 2012, par bahar_p

    I'm trying to encode an image to video using ffmpeg library.
    I have these global params :

    //Global params
    AVCodec         *codec;
    AVCodecContext  *codecCtx;
    uint8_t         *output_buffer;
    int             output_buffer_size;

    I divided the encoding to 3 methods :
    Initialize the encoder :

    jint Java_com_camera_simpledoublewebcams2_CameraPreview_initencoder(JNIEnv* env,jobject thiz){
    avcodec_register_all();
    avcodec_init();
    av_register_all();

    int fps = 30;

    /* find the H263 video encoder */
    codec = avcodec_find_encoder(CODEC_ID_H263);
    if (!codec) {
       LOGI("avcodec_find_encoder() run fail.");
       return -5;
    }

    //allocate context
    codecCtx = avcodec_alloc_context();

    /* put sample parameters */
    codecCtx->bit_rate = 400000;
    /* resolution must be a multiple of two */
    codecCtx->width = 176;
    codecCtx->height = 144;
    /* frames per second */
    codecCtx->time_base = (AVRational){1,fps};
    codecCtx->pix_fmt = PIX_FMT_YUV420P;
    codecCtx->codec_id = CODEC_ID_H263;
    codecCtx->codec_type = AVMEDIA_TYPE_VIDEO;

    /* open it */
    if (avcodec_open(codecCtx, codec) < 0) {
       LOGI("avcodec_open() run fail.");
       return -10;
    }

    //init buffer
    output_buffer_size = 500000;
    output_buffer = malloc(output_buffer_size);

    return 0;

    }

    Encoding the image :

    jint Java_com_camera_simpledoublewebcams2_CameraPreview_encodejpeg(JNIEnv* env,jobject thiz,jchar* cImage, jint imageSize){
    int             out_size;
    AVFrame         *picture;
    AVFrame         *outpic;
    uint8_t         *outbuffer;

    //allocate frame    
    picture = avcodec_alloc_frame();    
    outpic = avcodec_alloc_frame();

    int nbytes = avpicture_get_size(PIX_FMT_YUV420P, codecCtx->width, codecCtx->height);
    outbuffer = (uint8_t*)av_malloc(nbytes);
    outpic->pts = 0;

    //fill picture with image
    avpicture_fill((AVPicture*)picture, (uint8_t*)cImage, PIX_FMT_RGBA, codecCtx->width, codecCtx->height);
    //fill outpic with empty image
    avpicture_fill((AVPicture*)outpic, outbuffer, PIX_FMT_YUV420P, codecCtx->width, codecCtx->height);

    //rescale the image
    struct SwsContext* fooContext = sws_getContext(codecCtx->width, codecCtx->height,
                                                          PIX_FMT_RGBA,
                                                          codecCtx->width, codecCtx->height,
                                                          PIX_FMT_YUV420P,
                                                          SWS_FAST_BILINEAR, NULL, NULL, NULL);
    sws_scale(fooContext, picture->data, picture->linesize, 0, codecCtx->height, outpic->data, outpic->linesize);  

    //encode the image
    out_size = avcodec_encode_video(codecCtx, output_buffer, output_buffer_size, outpic);
    out_size += avcodec_encode_video(codecCtx, output_buffer, output_buffer_size, outpic);

    //release pictures
    av_free(outbuffer);
    av_free(picture);
    av_free(outpic);

    return out_size;

    }

    And closing the encoder :

    void Java_com_camera_simpledoublewebcams2_CameraPreview_closeencoder(JNIEnv* env,jobject thiz){
    free(output_buffer);
    avcodec_close(codecCtx);
    av_free(codecCtx);

    }

    When I send the first image, I get a result from the encoder. When I try to send another image the program crashes.
    I tried calling init once and then the images, then the close - didn't work.
    I tried calling the init and the close for every image - didn't work.

    Any suggestions ?

    Thanks !

  • Encoding .png images with h264 to a file on disk

    21 février 2021, par xyfix

    Can somebody help me to find out why I end up with a file on disk that is only 24 kb and not readable by vlc or so, while I send valid YUV images to the codec. I have added the .h and .cpp file. Up till "avcodec_receive_packet" everything seems to be OK. The function call "avcodec_send_frame" returns 0, so that must be OK but "avcodec_receive_packet" returns -11. If I flush the encoder (currently commented) then "avcodec_receive_packet" returns 0 and I can see encoded data if I store it on disk. Also the input image to the encoder is also correct (currently commented) and checked. I'm aiming for an intra-frame encoding, so I should get the encoded frame data back, but I don't get anything back even if I send 24 images to it.

    


    .h file

    


    #ifndef MOVIECODEC_H
#define MOVIECODEC_H

#include 

extern "C"
{
    #include "Codec/include/libavcodec/avcodec.h"
    #include "Codec/include/libavdevice/avdevice.h"
    #include "Codec/include/libavformat/avformat.h"
    #include "Codec/include/libavutil/avutil.h"
    #include "Codec/include/libavutil/imgutils.h"
    #include "Codec/include/libswscale/swscale.h"
}


class MovieCodec
{
public:

    MovieCodec(const char *filename);

    ~MovieCodec();

    void encodeImage( const cv::Mat& image );

    void close();
    
private :

    void add_stream();

    void openVideoCodec();

    void write_video_frame(const cv::Mat& image);

    void createFrame( const cv::Mat& image );

private:

    static int s_frameCount;

    int m_timeVideo = 0;

    std::string m_filename;

    FILE* m_file;

    AVCodec* m_encoder = NULL;

    AVOutputFormat* m_outputFormat = NULL;

    AVFormatContext* m_formatCtx = NULL;

    AVCodecContext* m_codecCtx = NULL;

    AVStream* m_streamOut = NULL;

    AVFrame* m_frame = NULL;

    AVPacket* m_packet = NULL;

};


    


    .cpp file

    


    #ifndef MOVIECODEC_CPP
#define MOVIECODEC_CPP

#include "moviecodec.h"


#define STREAM_DURATION   5.0
#define STREAM_FRAME_RATE 24
#define STREAM_NB_FRAMES  ((int)(STREAM_DURATION * STREAM_FRAME_RATE))
#define STREAM_PIX_FMT    AV_PIX_FMT_YUV420P /* default pix_fmt */


static int sws_flags = SWS_BICUBIC;
int MovieCodec::s_frameCount = 0;

MovieCodec::MovieCodec( const char* filename ) :
    m_filename( filename ),
    m_encoder( avcodec_find_encoder( AV_CODEC_ID_H264 ))
{
    av_log_set_level(AV_LOG_VERBOSE);

    int ret(0);

    m_file = fopen( m_filename.c_str(), "wb");

    // allocate the output media context
    ret = avformat_alloc_output_context2( &m_formatCtx, m_outputFormat, NULL, m_filename.c_str());

    if (!m_formatCtx)
        return;

    m_outputFormat = m_formatCtx->oformat;

    // Add the video stream using H264 codec
    add_stream();

    // Open video codec and allocate the necessary encode buffers
    if (m_streamOut)
        openVideoCodec();

    av_dump_format( m_formatCtx, 0, m_filename.c_str(), 1);

    // Open the output media file, if needed
    if (!( m_outputFormat->flags & AVFMT_NOFILE))
    {
        ret = avio_open( &m_formatCtx->pb, m_filename.c_str(), AVIO_FLAG_WRITE);

        if (ret < 0)
        {
            char error[255];
            ret = av_strerror( ret, error, 255);
            fprintf(stderr, "Could not open '%s': %s\n", m_filename.c_str(), error);
            return ;
        }
    }
    else
    {
        return;
    }

    m_formatCtx->flush_packets = 1;

    ret = avformat_write_header( m_formatCtx, NULL );

    if (ret < 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Error occurred when opening output file: %s\n", error);
        return;
    }


    if ( m_frame )
           m_frame->pts = 0;
}



MovieCodec::~MovieCodec()
{
    close();
}



void MovieCodec::encodeImage(const cv::Mat &image)
{
    // Compute video time from last added video frame
    m_timeVideo = (double)m_frame->pts) * av_q2d(m_streamOut->time_base);

    // Stop media if enough time
    if (!m_streamOut /*|| m_timeVideo >= STREAM_DURATION*/)
       return;

    // Add a video frame
    write_video_frame( image );

    // Increase frame pts according to time base
    m_frame->pts += av_rescale_q(1, m_codecCtx->time_base, m_streamOut->time_base);
}


void MovieCodec::close()
{
    int ret( 0 );

    // Write media trailer
//    if( m_formatCtx )
//        ret = av_write_trailer( m_formatCtx );

    /* flush the encoder */
    ret = avcodec_send_frame(m_codecCtx, NULL);

    /* Close each codec. */
    if ( m_streamOut )
    {
        av_free( m_frame->data[0]);
        av_free( m_frame );
    }

    if (!( m_outputFormat->flags & AVFMT_NOFILE))
        /* Close the output file. */
        ret = avio_close( m_formatCtx->pb);


    /* free the stream */
    avformat_free_context( m_formatCtx );

    fflush( m_file );
}


void MovieCodec::createFrame( const cv::Mat& image )
{
    /**
     * \note allocate frame
     */
    m_frame = av_frame_alloc();
    m_frame->format = STREAM_PIX_FMT;
    m_frame->width = image.cols();
    m_frame->height = image.rows();
    m_frame->pict_type = AV_PICTURE_TYPE_I;
    int ret = av_image_alloc(m_frame->data, m_frame->linesize, m_frame->width,  m_frame->height, STREAM_PIX_FMT, 1);

    if (ret < 0)
    {
        return;
    }

    struct SwsContext* sws_ctx = sws_getContext((int)image.cols(), (int)image.rows(), AV_PIX_FMT_RGB24,
                                                (int)image.cols(), (int)image.rows(), STREAM_PIX_FMT, 0, NULL, NULL, NULL);

    const uint8_t* rgbData[1] = { (uint8_t* )image.getData() };
    int rgbLineSize[1] = { 3 * image.cols() };

    sws_scale(sws_ctx, rgbData, rgbLineSize, 0, image.rows(), m_frame->data, m_frame->linesize);
}


/* Add an output stream. */
void MovieCodec::add_stream()
{
    AVCodecID codecId = AV_CODEC_ID_H264;

    if (!( m_encoder ))
    {
        fprintf(stderr, "Could not find encoder for '%s'\n",
            avcodec_get_name(codecId));
        return;
    }

    // Get the stream for codec
    m_streamOut = avformat_new_stream(m_formatCtx, m_encoder);

    if (!m_streamOut) {
        fprintf(stderr, "Could not allocate stream\n");
        return;
    }

    m_streamOut->id = m_formatCtx->nb_streams - 1;

    m_codecCtx = avcodec_alloc_context3( m_encoder);

    m_streamOut->codecpar->codec_id = codecId;
    m_streamOut->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
    m_streamOut->codecpar->bit_rate = 400000;
    m_streamOut->codecpar->width = 800;
    m_streamOut->codecpar->height = 640;
    m_streamOut->codecpar->format = STREAM_PIX_FMT;
    m_streamOut->codecpar->codec_tag = 0x31637661;
    m_streamOut->codecpar->video_delay = 0;
    m_streamOut->time_base = { 1, STREAM_FRAME_RATE };


    avcodec_parameters_to_context( m_codecCtx, m_streamOut->codecpar);
    
    m_codecCtx->gop_size = 0; /* emit one intra frame every twelve frames at most */
    m_codecCtx->max_b_frames = 0;
    m_codecCtx->time_base = { 1, STREAM_FRAME_RATE };
    m_codecCtx->framerate = { STREAM_FRAME_RATE, 1 };
    m_codecCtx->pix_fmt = STREAM_PIX_FMT;



    if (m_streamOut->codecpar->codec_id == AV_CODEC_ID_H264)
    {
      av_opt_set( m_codecCtx, "preset", "ultrafast", 0 );
      av_opt_set( m_codecCtx, "vprofile", "baseline", 0 );
      av_opt_set( m_codecCtx, "tune", "zerolatency", 0 );
    }

//    /* Some formats want stream headers to be separate. */
//    if (m_formatCtx->oformat->flags & AVFMT_GLOBALHEADER)
//            m_codecCtx->flags |= AV_CODEC_FLAG_GLOBAL_HEADER;


}


void MovieCodec::openVideoCodec()
{
    int ret;

    /* open the codec */
    ret = avcodec_open2(m_codecCtx, m_encoder, NULL);

    if (ret < 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Could not open video codec: %s\n", error);
    }
}



void MovieCodec::write_video_frame( const cv::Mat& image )
{
    int ret;

    createFrame( image );


    if (m_formatCtx->oformat->flags & 0x0020 )
    {
        /* Raw video case - directly store the picture in the packet */
        AVPacket pkt;
        av_init_packet(&pkt);

        pkt.flags |= AV_PKT_FLAG_KEY;
        pkt.stream_index = m_streamOut->index;
        pkt.data = m_frame->data[0];
        pkt.size = sizeof(AVPicture);

//        ret = av_interleaved_write_frame(m_formatCtx, &pkt);
        ret = av_write_frame( m_formatCtx, &pkt );
    }
    else
    {
        AVPacket pkt;
        av_init_packet(&pkt);

        /* encode the image */

//cv::Mat yuv420p( m_frame->height + m_frame->height/2, m_frame->width, CV_8UC1, m_frame->data[0]);
//cv::Mat cvmIm;
//cv::cvtColor(yuv420p,cvmIm,CV_YUV420p2BGR);
//cv::imwrite("c:\\tmp\\YUVoriginal.png", cvmIm);

        ret = avcodec_send_frame(m_codecCtx, m_frame);

        if (ret < 0)
        {
            char error[255];
            av_strerror(ret, error, 255);
            fprintf(stderr, "Error encoding video frame: %s\n", error);
            return;
        }

        /* If size is zero, it means the image was buffered. */
//        ret = avcodec_receive_packet(m_codecCtx, &pkt);

        do
        {
            ret = avcodec_receive_packet(m_codecCtx, &pkt);

            if (ret == 0)
            {
                ret = av_write_frame( m_formatCtx, &pkt );
                av_packet_unref(&pkt);

                break;
            }
//            else if ((ret < 0) && (ret != AVERROR(EAGAIN)))
//            {
//                return;
//            }
//            else if (ret == AVERROR(EAGAIN))
//            {
//                /* flush the encoder */
//                ret = avcodec_send_frame(m_codecCtx, NULL);
//
//                if (0 > ret)
//                    return;
//            }
        } while (ret == 0);

        if( !ret && pkt.size)
        {
            pkt.stream_index = m_streamOut->index;

            /* Write the compressed frame to the media file. */
//            ret = av_interleaved_write_frame(m_formatCtx, &pkt);
            ret = av_write_frame( m_formatCtx, &pkt );
        }
        else
        {
            ret = 0;
        }
    }

    if (ret != 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Error while writing video frame: %s\n", error);
        return;
    }

    s_frameCount++;
}


    


  • Encoding .png images with h264 to a file on disk

    19 février 2021, par xyfix

    Can somebody help me to find out why I end up with a file on disk that is only 24 kb and not readable by vlc or so, while I send valid YUV images to the codec. I have added the .h and .cpp file. Up till "avcodec_receive_packet" everything seems to be OK. The function call "avcodec_send_frame" returns 0, so that must be OK but "avcodec_receive_packet" returns -11. If I flush the encoder (currently commented) then "avcodec_receive_packet" returns 0 and I can see encoded data if I store it on disk. Also the input image to the encoder is also correct (currently commented) and checked. I'm aiming for an intra-frame encoding, so I should get the encoded frame data back, but I don't get anything back even if I send 24 images to it.

    


    .h file

    


    #ifndef MOVIECODEC_H
#define MOVIECODEC_H

#include 

extern "C"
{
    #include "Codec/include/libavcodec/avcodec.h"
    #include "Codec/include/libavdevice/avdevice.h"
    #include "Codec/include/libavformat/avformat.h"
    #include "Codec/include/libavutil/avutil.h"
    #include "Codec/include/libavutil/imgutils.h"
    #include "Codec/include/libswscale/swscale.h"
}


class MovieCodec
{
public:

    MovieCodec(const char *filename);

    ~MovieCodec();

    void encodeImage( const cv::Mat& image );

    void close();
    
private :

    void add_stream();

    void openVideoCodec();

    void write_video_frame(const cv::Mat& image);

    void createFrame( const cv::Mat& image );

private:

    static int s_frameCount;

    int m_timeVideo = 0;

    std::string m_filename;

    FILE* m_file;

    AVCodec* m_encoder = NULL;

    AVOutputFormat* m_outputFormat = NULL;

    AVFormatContext* m_formatCtx = NULL;

    AVCodecContext* m_codecCtx = NULL;

    AVStream* m_streamOut = NULL;

    AVFrame* m_frame = NULL;

    AVPacket* m_packet = NULL;

};


    


    .cpp file

    


    #ifndef MOVIECODEC_CPP
#define MOVIECODEC_CPP

#include "moviecodec.h"


#define STREAM_DURATION   5.0
#define STREAM_FRAME_RATE 24
#define STREAM_NB_FRAMES  ((int)(STREAM_DURATION * STREAM_FRAME_RATE))
#define STREAM_PIX_FMT    AV_PIX_FMT_YUV420P /* default pix_fmt */


static int sws_flags = SWS_BICUBIC;
int MovieCodec::s_frameCount = 0;

MovieCodec::MovieCodec( const char* filename ) :
    m_filename( filename ),
    m_encoder( avcodec_find_encoder( AV_CODEC_ID_H264 ))
{
    av_log_set_level(AV_LOG_VERBOSE);

    int ret(0);

    m_file = fopen( m_filename.c_str(), "wb");

    // allocate the output media context
    ret = avformat_alloc_output_context2( &m_formatCtx, m_outputFormat, NULL, m_filename.c_str());

    if (!m_formatCtx)
        return;

    m_outputFormat = m_formatCtx->oformat;

    // Add the video stream using H264 codec
    add_stream();

    // Open video codec and allocate the necessary encode buffers
    if (m_streamOut)
        openVideoCodec();

    av_dump_format( m_formatCtx, 0, m_filename.c_str(), 1);

    // Open the output media file, if needed
    if (!( m_outputFormat->flags & AVFMT_NOFILE))
    {
        ret = avio_open( &m_formatCtx->pb, m_filename.c_str(), AVIO_FLAG_WRITE);

        if (ret < 0)
        {
            char error[255];
            ret = av_strerror( ret, error, 255);
            fprintf(stderr, "Could not open '%s': %s\n", m_filename.c_str(), error);
            return ;
        }
    }
    else
    {
        return;
    }

    m_formatCtx->flush_packets = 1;

    ret = avformat_write_header( m_formatCtx, NULL );

    if (ret < 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Error occurred when opening output file: %s\n", error);
        return;
    }


    if ( m_frame )
           m_frame->pts = 0;
}



MovieCodec::~MovieCodec()
{
    close();
}



void MovieCodec::encodeImage(const cv::Mat &image)
{
    // Compute video time from last added video frame
    m_timeVideo = (double)m_frame->pts) * av_q2d(m_streamOut->time_base);

    // Stop media if enough time
    if (!m_streamOut /*|| m_timeVideo >= STREAM_DURATION*/)
       return;

    // Add a video frame
    write_video_frame( image );

    // Increase frame pts according to time base
    m_frame->pts += av_rescale_q(1, m_codecCtx->time_base, m_streamOut->time_base);
}


void MovieCodec::close()
{
    int ret( 0 );

    // Write media trailer
//    if( m_formatCtx )
//        ret = av_write_trailer( m_formatCtx );

    /* flush the encoder */
    ret = avcodec_send_frame(m_codecCtx, NULL);

    /* Close each codec. */
    if ( m_streamOut )
    {
        av_free( m_frame->data[0]);
        av_free( m_frame );
    }

    if (!( m_outputFormat->flags & AVFMT_NOFILE))
        /* Close the output file. */
        ret = avio_close( m_formatCtx->pb);


    /* free the stream */
    avformat_free_context( m_formatCtx );

    fflush( m_file );
}


void MovieCodec::createFrame( const cv::Mat& image )
{
    /**
     * \note allocate frame
     */
    m_frame = av_frame_alloc();
    m_frame->format = STREAM_PIX_FMT;
    m_frame->width = image.cols();
    m_frame->height = image.rows();
    m_frame->pict_type = AV_PICTURE_TYPE_I;
    int ret = av_image_alloc(m_frame->data, m_frame->linesize, m_frame->width,  m_frame->height, STREAM_PIX_FMT, 1);

    if (ret < 0)
    {
        return;
    }

    struct SwsContext* sws_ctx = sws_getContext((int)image.cols(), (int)image.rows(), AV_PIX_FMT_RGB24,
                                                (int)image.cols(), (int)image.rows(), STREAM_PIX_FMT, 0, NULL, NULL, NULL);

    const uint8_t* rgbData[1] = { (uint8_t* )image.getData() };
    int rgbLineSize[1] = { 3 * image.cols() };

    sws_scale(sws_ctx, rgbData, rgbLineSize, 0, image.rows(), m_frame->data, m_frame->linesize);
}


/* Add an output stream. */
void MovieCodec::add_stream()
{
    AVCodecID codecId = AV_CODEC_ID_H264;

    if (!( m_encoder ))
    {
        fprintf(stderr, "Could not find encoder for '%s'\n",
            avcodec_get_name(codecId));
        return;
    }

    // Get the stream for codec
    m_streamOut = avformat_new_stream(m_formatCtx, m_encoder);

    if (!m_streamOut) {
        fprintf(stderr, "Could not allocate stream\n");
        return;
    }

    m_streamOut->id = m_formatCtx->nb_streams - 1;

    m_codecCtx = avcodec_alloc_context3( m_encoder);

    m_streamOut->codecpar->codec_id = codecId;
    m_streamOut->codecpar->codec_type = AVMEDIA_TYPE_VIDEO;
    m_streamOut->codecpar->bit_rate = 400000;
    m_streamOut->codecpar->width = 800;
    m_streamOut->codecpar->height = 640;
    m_streamOut->codecpar->format = STREAM_PIX_FMT;
    m_streamOut->codecpar->codec_tag = 0x31637661;
    m_streamOut->codecpar->video_delay = 0;
    m_streamOut->time_base = { 1, STREAM_FRAME_RATE };


    avcodec_parameters_to_context( m_codecCtx, m_streamOut->codecpar);
    
    m_codecCtx->gop_size = 0; /* emit one intra frame every twelve frames at most */
    m_codecCtx->max_b_frames = 0;
    m_codecCtx->time_base = { 1, STREAM_FRAME_RATE };
    m_codecCtx->framerate = { STREAM_FRAME_RATE, 1 };
    m_codecCtx->pix_fmt = STREAM_PIX_FMT;



    if (m_streamOut->codecpar->codec_id == AV_CODEC_ID_H264)
    {
      av_opt_set( m_codecCtx, "preset", "ultrafast", 0 );
      av_opt_set( m_codecCtx, "vprofile", "baseline", 0 );
      av_opt_set( m_codecCtx, "tune", "zerolatency", 0 );
    }

//    /* Some formats want stream headers to be separate. */
//    if (m_formatCtx->oformat->flags & AVFMT_GLOBALHEADER)
//            m_codecCtx->flags |= AV_CODEC_FLAG_GLOBAL_HEADER;


}


void MovieCodec::openVideoCodec()
{
    int ret;

    /* open the codec */
    ret = avcodec_open2(m_codecCtx, m_encoder, NULL);

    if (ret < 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Could not open video codec: %s\n", error);
    }
}



void MovieCodec::write_video_frame( const cv::Mat& image )
{
    int ret;

    createFrame( image );


    if (m_formatCtx->oformat->flags & 0x0020 )
    {
        /* Raw video case - directly store the picture in the packet */
        AVPacket pkt;
        av_init_packet(&pkt);

        pkt.flags |= AV_PKT_FLAG_KEY;
        pkt.stream_index = m_streamOut->index;
        pkt.data = m_frame->data[0];
        pkt.size = sizeof(AVPicture);

//        ret = av_interleaved_write_frame(m_formatCtx, &pkt);
        ret = av_write_frame( m_formatCtx, &pkt );
    }
    else
    {
        AVPacket pkt;
        av_init_packet(&pkt);

        /* encode the image */

//cv::Mat yuv420p( m_frame->height + m_frame->height/2, m_frame->width, CV_8UC1, m_frame->data[0]);
//cv::Mat cvmIm;
//cv::cvtColor(yuv420p,cvmIm,CV_YUV420p2BGR);
//cv::imwrite("c:\\tmp\\YUVoriginal.png", cvmIm);

        ret = avcodec_send_frame(m_codecCtx, m_frame);

        if (ret < 0)
        {
            char error[255];
            av_strerror(ret, error, 255);
            fprintf(stderr, "Error encoding video frame: %s\n", error);
            return;
        }

        /* If size is zero, it means the image was buffered. */
//        ret = avcodec_receive_packet(m_codecCtx, &pkt);

        do
        {
            ret = avcodec_receive_packet(m_codecCtx, &pkt);

            if (ret == 0)
            {
                ret = av_write_frame( m_formatCtx, &pkt );
                av_packet_unref(&pkt);

                break;
            }
//            else if ((ret < 0) && (ret != AVERROR(EAGAIN)))
//            {
//                return;
//            }
//            else if (ret == AVERROR(EAGAIN))
//            {
//                /* flush the encoder */
//                ret = avcodec_send_frame(m_codecCtx, NULL);
//
//                if (0 > ret)
//                    return;
//            }
        } while (ret == 0);

        if( !ret && pkt.size)
        {
            pkt.stream_index = m_streamOut->index;

            /* Write the compressed frame to the media file. */
//            ret = av_interleaved_write_frame(m_formatCtx, &pkt);
            ret = av_write_frame( m_formatCtx, &pkt );
        }
        else
        {
            ret = 0;
        }
    }

    if (ret != 0)
    {
        char error[255];
        av_strerror(ret, error, 255);
        fprintf(stderr, "Error while writing video frame: %s\n", error);
        return;
    }

    s_frameCount++;
}