赞
踩
使用带h264的ffmpeg才是我们的最终目的!
https://blog.csdn.net/qq_37249793/article/details/115272864
官网(http://www.ffmpeg.org/)下载源码
rem set MSYS2_PATH_TYPE=inherit
去掉rem可以继承vs的编译环境msys2_shell.cmd -mingw64
which cl link yasm cpp
./configure --toolchain=msvc --target-os=win64 \ --arch=x86_64 \ --enable-shared \ --enable-small \ --enable-version3 \ --enable-gpl \ --enable-nonfree \ --disable-stripping \ --disable-encoders \ --disable-decoders \ --enable-decoder=h264 \ --enable-encoder=libx264 \ --enable-encoder=mjpeg \ --enable-encoder=mpeg4 \ --prefix=./build \ --enable-libx264 \ --extra-cflags="-I/home/x264/include" \ --extra-ldflags="-LIBPATH:/home/x264/lib"
最下面两行是x264对应目录
7. 输入命令sh build.sh
,如果保WARNING: using libx264 without pkg-config可以不用管
8. 接下来就是编译了:
make
make install
extern "C" { #include "libavcodec/avcodec.h" #include "libavformat/avformat.h" #include "libavutil/imgutils.h" #include "libswscale/swscale.h" }; #include <afxwin.h> #pragma warning(disable:4996) using namespace std; typedef struct { int startpos; int endpos; int len; int code; int startlen; }FrameAna; unsigned char m_outbuf[1024 * 1024]; typedef struct { uint8_t m_Head[4]; int m_len; }FrameHead_t; void Parser(); int main() { Parser(); return 0; } //mp4中获取yuv void Parser() { AVFormatContext *pFormatCtx; int videoindex; AVCodecContext *pCodecCtx; AVCodec *pCodec; AVFrame *pFrame; uint8_t *out_buffer; AVPacket *packet; int ret, got_picture; struct SwsContext *img_convert_ctx; char filepath[] = "000.mp4";//要解析的mp4文件 FILE *fp_h264 = NULL; FrameAna m_FrameInfo[1024]; int m_FrameIndex = 0; fopen_s(&fp_h264, "000.h264", "wb+");//MP4输出成.h264文件 /* 初始化一个AVFormatContext ,并打开文件 */ pFormatCtx = avformat_alloc_context(); avformat_open_input(&pFormatCtx, filepath, NULL, NULL); /* 获取视频文件信息 */ avformat_find_stream_info(pFormatCtx, NULL); /* 查找视频的编号 */ videoindex = -1; for (unsigned int i = 0; i < pFormatCtx->nb_streams; i++) { if (pFormatCtx->streams[i]->codecpar->codec_type == AVMEDIA_TYPE_VIDEO) { videoindex = (int)i; break; } if (videoindex == -1) { AfxMessageBox(L"can't find video,error!"); return; } } /* 查找解码器 */ pCodecCtx = avcodec_alloc_context3(NULL); avcodec_parameters_to_context(pCodecCtx, pFormatCtx->streams[videoindex]->codecpar); pCodec = avcodec_find_decoder(pCodecCtx->codec_id); /* 打开解码器 */ avcodec_open2(pCodecCtx, pCodec, NULL); pFrame = av_frame_alloc(); out_buffer = (uint8_t *)av_malloc(av_image_get_buffer_size(AV_PIX_FMT_YUV420P, pCodecCtx->width, pCodecCtx->height, 1)); packet = (AVPacket*)av_malloc(sizeof(AVPacket)); img_convert_ctx = sws_getContext(pCodecCtx->width, pCodecCtx->height, pCodecCtx->pix_fmt, pCodecCtx->width, pCodecCtx->height, AV_PIX_FMT_YUV420P, SWS_BICUBIC, NULL, NULL, NULL); /* 获取流解析对象 */ unsigned char *h264_buf; int h264_len; AVBitStreamFilterContext* h264bsfc = av_bitstream_filter_init("h264_mp4toannexb"); int iNeedIFrame = 1; int iDecoderCnt = 0; while (av_read_frame(pFormatCtx, packet) >= 0) { /* 读取一帧压缩数据 */ if (packet->stream_index == videoindex) { /* 数据解码,可获取到YUV解码后数据 */ ret = avcodec_send_packet(pCodecCtx, packet); if (ret < 0) { AfxMessageBox(L"Decoder one frame , Error !"); return; } got_picture = avcodec_receive_frame(pCodecCtx, pFrame); if (0 == got_picture) { iDecoderCnt++; if (nullptr != fp_h264) { fwrite(pFrame->data[0], 1, pFrame->width * pFrame->height, fp_h264); fwrite(pFrame->data[1], 1, pFrame->width * pFrame->height / 4, fp_h264); fwrite(pFrame->data[2], 1, pFrame->width * pFrame->height / 4, fp_h264); printf("我在编啦"); //每一帧都调用tojpg函数转换为jpg图像 } } } av_packet_unref(packet); } /* flush decoder */ /*当av_read_frame()循环退出的时候,实际上解码器中可能还包含剩余的几帧数据。因此需要通过“flush_decoder”将这几帧数据输出。“flush_decoder”功能简而言之即直接调用avcodec_decode_video2()获得AVFrame,而不再向解码器传递AVPacket。*/ while (1) { got_picture = avcodec_receive_frame(pCodecCtx, pFrame); if (0 != got_picture) break; iDecoderCnt++; } sws_freeContext(img_convert_ctx); /* 释放流解析对象 */ av_bitstream_filter_close(h264bsfc); /* 关闭文件以及释放内存 */ fclose(fp_h264); av_frame_free(&pFrame); avcodec_close(pCodecCtx); avformat_close_input(&pFormatCtx); CString m_str; m_str.Format(L"Get FrameCnt = %d Success !!\n", iDecoderCnt); AfxMessageBox(m_str); return; }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。