美文网首页
FFmpge 剥离视屏文件的YUV

FFmpge 剥离视屏文件的YUV

作者: shaozq | 来源:发表于2020-08-06 15:32 被阅读0次

    ···

    #include <stdio.h>

    #include "pch.h"

    #define _CRT_SECURE_NO_WARNINGS

    #define __STDC_CONSTANT_MACROS

    extern "C"

    {

    #include "libavcodec/avcodec.h"

    #include "libavformat/avformat.h"

    #include "libswscale/swscale.h"

    #include "libswscale/swscale.h"

    };

    int main(int argc, char* argv[])

    {

    AVFormatContext* pAVFormatContext;

    AVCodecContext* pAVCodecContext;

    AVCodec* pAVCodec;

    AVPacket* pAVPacket;

    AVFrame* pAvFrame;

    AVFrame* pFrameYUV;

    int videoindex = -1;

    uint8_t *out_buffer;

    int frame_cnt = 0;

    int got_pic, ret;

    struct SwsContext *img_convert_ctx;

    char filepath[] = "cuc_ieschool.flv";

    FILE* file_yuv = fopen("shao_test.yuv", "wb+");

    av_register_all();

    avformat_network_init();

    pAVFormatContext = avformat_alloc_context();

    if (avformat_open_input(&pAVFormatContext, filepath, NULL, NULL) != 0) {

    printf("Couldn't open input stream.\n");

    return -1;

    }

    if (avformat_find_stream_info(pAVFormatContext, NULL) < 0) {

    printf("Couldn't find stream information.\n");

    return -1;

    }

    printf("video duration: %d", pAVFormatContext->duration);

    printf("video formatName: %s", pAVFormatContext->iformat->name);

    for (int i = 0; i < pAVFormatContext->nb_streams;i ++) {

    if (pAVFormatContext->streams[i]->codec->codec_type == AVMEDIA_TYPE_VIDEO) {

    videoindex = i;

    break;

    }

    }

    if (videoindex == -1) {

    printf("Didn't find a video stream.\n");

    return -1;

    }

    pAVCodecContext = pAVFormatContext->streams[videoindex]->codec;

    pAVCodec = avcodec_find_decoder(pAVCodecContext->codec_id);

    printf("video width=%d , height = %d\n", pAVCodecContext->width,pAVCodecContext->height);

    if (pAVCodec == NULL) {

    printf("cannot find codec");

    return -1;

    }

    if (avcodec_open2(pAVCodecContext,pAVCodec,NULL) < 0) {

    printf("can not open file \n");

    return -1;

    }

    av_dump_format(pAVFormatContext, 0, filepath, 0);

    pAvFrame = av_frame_alloc();

    pFrameYUV = av_frame_alloc();

    pAVPacket = reinterpret_cast<AVPacket*> (av_malloc(sizeof(AVPacket)));

    out_buffer = (uint8_t*)av_malloc(avpicture_get_size(PIX_FMT_YUV420P, pAVCodecContext->width, pAVCodecContext->height));

    avpicture_fill((AVPicture *)pFrameYUV, out_buffer, PIX_FMT_YUV420P, pAVCodecContext->width, pAVCodecContext->height);

    img_convert_ctx = sws_getContext(pAVCodecContext->width, pAVCodecContext->height, pAVCodecContext->pix_fmt,

    pAVCodecContext->width, pAVCodecContext->height, PIX_FMT_YUV420P, SWS_BICUBIC, NULL, NULL, NULL);

    int yuv_size = pAVCodecContext->width * pAVCodecContext->height;

    while (av_read_frame(pAVFormatContext, pAVPacket) >= 0) {

    if (pAVPacket->stream_index == videoindex) {

    /*

    * 在此处添加输出H264码流的代码

    * 取自于packet,使用fwrite()

    */

    ret = avcodec_decode_video2(pAVCodecContext, pAvFrame, &got_pic, pAVPacket);

    if (ret < 0) {

    printf("Decode Error.\n");

    return -1;

    }

    if (got_pic) {

    sws_scale(img_convert_ctx, (const uint8_t* const*)pAvFrame->data, pAvFrame->linesize, 0, pAVCodecContext->height,

    pFrameYUV->data, pFrameYUV->linesize);

    printf("Decoded frame index: %d\n", frame_cnt);

    fwrite(pFrameYUV->data[0], 1, yuv_size, file_yuv);

    fwrite(pFrameYUV->data[1], 1, yuv_size / 4, file_yuv);

    fwrite(pFrameYUV->data[2], 1, yuv_size / 4, file_yuv);

    /*

    * 在此处添加输出YUV的代码

    * 取自于pFrameYUV,使用fwrite()

    */

    frame_cnt++;

    }

    }

    av_free_packet(pAVPacket);

    }

    //FIX: Flush Frames remained in Codec

    while (1) {

    ret = avcodec_decode_video2(pAVCodecContext, pAvFrame, &got_pic, pAVPacket);

    if (ret < 0)

    break;

    if (got_pic) {

    fwrite(pAvFrame->data[0], 1, yuv_size, file_yuv);

    fwrite(pAvFrame->data[1], 1, yuv_size / 4, file_yuv);

    fwrite(pAvFrame->data[2], 1, yuv_size / 4, file_yuv);

    printf("decode frame cuss %d\n", pAVPacket->dts);

    }

    av_free_packet(pAVPacket);

    }

    av_frame_free(&pAvFrame);

    avcodec_close(pAVCodecContext);

    avformat_close_input(&pAVFormatContext);

    return 0;

    }

    ···

    相关文章

      网友评论

          本文标题:FFmpge 剥离视屏文件的YUV

          本文链接:https://www.haomeiwen.com/subject/xtzzrktx.html