如何在FFmpeg的avframe和OpenCV垫之间转换过程中解决错误?

时间:2017-08-28 03:29:27

标签: opencv ffmpeg

我在FFmpeg的avframe和OpenCV的垫子之间进行了转换。但是以下代码没有正确地将mat格式转换为avframe格式。第一部分将avframe转换为mat格式,第二部分将mat转换为avframe格式。

这是我的源代码:

AVFrame* ProcessFrame(AVFrame *frame, int stream_index)
{
 //first part
    AVStream *in_stream = ifmt_ctx->streams[stream_index];
    AVCodecContext *pCodecCtx = in_stream->codec;

    AVFrame  *pFrameRGB = NULL;

    struct SwsContext * img_convert_ctx = NULL;
    if(img_convert_ctx == NULL){
        img_convert_ctx = sws_getContext(pCodecCtx->width, pCodecCtx->height,
                                         pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height,
                                         AV_PIX_FMT_BGR24, SWS_BICUBIC, NULL, NULL, NULL);
    }
    pFrameRGB = av_frame_alloc();
    int size = avpicture_get_size(AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    uint8_t  *out_bufferRGB = (uint8_t *)av_malloc(size);

    avpicture_fill((AVPicture *)pFrameRGB, out_bufferRGB, AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    sws_scale(img_convert_ctx, frame->data, frame->linesize, 0, pCodecCtx->height, pFrameRGB->data, pFrameRGB->linesize);

    Mat imageFrame = Mat(pCodecCtx->height, pCodecCtx->width, CV_8UC3, out_bufferRGB);    

    delete[] out_bufferRGB;

   ///////////////////////////////////////////////////////////
   //second part starts

    avpicture_fill((AVPicture *)pFrameRGB, imageFrame.data,AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    struct SwsContext * convert_ctx = NULL;
    if(convert_ctx == NULL){
        convert_ctx = sws_getContext(pCodecCtx->width, pCodecCtx->height,
                                         AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height,
                                         pCodecCtx->pix_fmt, SWS_BICUBIC, NULL, NULL, NULL);
    }

    AVFrame *srcFrame = av_frame_alloc();
    size = avpicture_get_size(pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height);

    uint8_t  *out_buffer = (uint8_t *)av_malloc(size);

    avpicture_fill((AVPicture *)srcFrame, out_buffer, pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height);

    sws_scale(convert_ctx, pFrameRGB->data, pFrameRGB->linesize, 0, pCodecCtx->height, srcFrame->data, srcFrame->linesize);

    delete[] out_buffer;
    av_free(pFrameRGB);

    srcFrame->width = frame->width;
    srcFrame->height = frame->height;
    srcFrame->format = frame->format;

    av_frame_copy_props(srcFrame, frame);

    return srcFrame;
}

1 个答案:

答案 0 :(得分:0)

最后,我删除del语句以使其工作。

AVFrame* ProcessFrame(AVFrame *frame, int stream_index)
{
 //first part
    AVStream *in_stream = ifmt_ctx->streams[stream_index];
    AVCodecContext *pCodecCtx = in_stream->codec;

    AVFrame  *pFrameRGB = NULL;

    struct SwsContext * img_convert_ctx = NULL;
    if(img_convert_ctx == NULL){
        img_convert_ctx = sws_getContext(pCodecCtx->width, pCodecCtx->height,
                                         pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height,
                                         AV_PIX_FMT_BGR24, SWS_BICUBIC, NULL, NULL, NULL);
    }
    pFrameRGB = av_frame_alloc();
    int size = avpicture_get_size(AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    uint8_t  *out_bufferRGB = (uint8_t *)av_malloc(size);

    avpicture_fill((AVPicture *)pFrameRGB, out_bufferRGB, AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    sws_scale(img_convert_ctx, frame->data, frame->linesize, 0, pCodecCtx->height, pFrameRGB->data, pFrameRGB->linesize);

    Mat imageFrame = Mat(pCodecCtx->height, pCodecCtx->width, CV_8UC3, out_bufferRGB);   

   ///////////////////////////////////////////////////////////
   //second part starts

    avpicture_fill((AVPicture *)pFrameRGB, imageFrame.data,AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height);

    struct SwsContext * convert_ctx = NULL;
    if(convert_ctx == NULL){
        convert_ctx = sws_getContext(pCodecCtx->width, pCodecCtx->height,
                                         AV_PIX_FMT_BGR24, pCodecCtx->width, pCodecCtx->height,
                                         pCodecCtx->pix_fmt, SWS_BICUBIC, NULL, NULL, NULL);
    }

    AVFrame *srcFrame = av_frame_alloc();
    size = avpicture_get_size(pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height);

    uint8_t  *out_buffer = (uint8_t *)av_malloc(size);

    avpicture_fill((AVPicture *)srcFrame, out_buffer, pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height);

    sws_scale(convert_ctx, pFrameRGB->data, pFrameRGB->linesize, 0, pCodecCtx->height, srcFrame->data, srcFrame->linesize);

    av_free(pFrameRGB);

    srcFrame->width = frame->width;
    srcFrame->height = frame->height;
    srcFrame->format = frame->format;

    av_frame_copy_props(srcFrame, frame);

    return srcFrame;
}