使用FFMpeg进行H264编码

来源:互联网 发布:什么聊天软件好 编辑:程序博客网 时间:2024/05/01 01:26

http://blog.csdn.net/eightdegree/article/details/7425635

使用FFMpeg可以很方便的对音视频进行编码,并且写文件。

下面的代码是将5幅1280*720大小的图片进行编码,并且写到文件中。

代码有些乱,但希望能抛砖引玉,对学习这方面的朋友有帮助。


CFile file[5];  BYTE *szTxt[5];    int nWidth = 0;  int nHeight= 0;    int nDataLen=0;    int nLen;    CString csFileName;  for (int fileI = 1; fileI <= 5; fileI ++)  {    csFileName.Format("e:\\pics\\%d.bmp", fileI);    file[fileI - 1].Open(csFileName,CFile::modeRead | CFile::typeBinary);    nLen = file[fileI - 1].GetLength();      szTxt[fileI -1] = new BYTE[nLen];    file[fileI - 1].Read(szTxt[fileI - 1], nLen);    file[fileI - 1].Close();      //BMP bmi;//BITMAPINFO bmi;    //int nHeadLen = sizeof(BMP);    BITMAPFILEHEADER bmpFHeader;    BITMAPINFOHEADER bmpIHeader;    memcpy(&bmpFHeader,szTxt[fileI -1],sizeof(BITMAPFILEHEADER));      int nHeadLen = bmpFHeader.bfOffBits - sizeof(BITMAPFILEHEADER);    memcpy(&bmpIHeader,szTxt[fileI - 1]+sizeof(BITMAPFILEHEADER),nHeadLen);    nWidth = bmpIHeader.biWidth;// 464;// bmi.bmpInfo.bmiHeader.biWidth;// ;    nHeight = bmpIHeader.biHeight;//362;// bmi.bmpInfo.bmiHeader.biHeight;// ;      szTxt[fileI - 1] += bmpFHeader.bfOffBits;    nDataLen = nLen-bmpFHeader.bfOffBits;  }    av_register_all();  avcodec_register_all();  AVFrame *m_pRGBFrame =  new AVFrame[1];  //RGB帧数据    AVFrame *m_pYUVFrame = new AVFrame[1];;  //YUV帧数据  AVCodecContext *c= NULL;  AVCodecContext *in_c= NULL;  AVCodec *pCodecH264; //编码器  uint8_t * yuv_buff;//    //查找h264编码器  pCodecH264 = avcodec_find_encoder(CODEC_ID_H264);  if(!pCodecH264)  {    fprintf(stderr, "h264 codec not found\n");    exit(1);  }    c= avcodec_alloc_context3(pCodecH264);  c->bit_rate = 3000000;// put sample parameters   c->width =nWidth;//   c->height = nHeight;//     // frames per second   AVRational rate;  rate.num = 1;  rate.den = 25;  c->time_base= rate;//(AVRational){1,25};  c->gop_size = 10; // emit one intra frame every ten frames   c->max_b_frames=1;  c->thread_count = 1;  c->pix_fmt = PIX_FMT_YUV420P;//PIX_FMT_RGB24;    //av_opt_set(c->priv_data, /*"preset"*/"libvpx-1080p.ffpreset", /*"slow"*/NULL, 0);  //打开编码器  if(avcodec_open2(c,pCodecH264,NULL)<0)    TRACE("不能打开编码库");    int size = c->width * c->height;    yuv_buff = (uint8_t *) malloc((size * 3) / 2); // size for YUV 420     //将rgb图像数据填充rgb帧  uint8_t * rgb_buff = new uint8_t[nDataLen];    //图象编码  int outbuf_size=100000;  uint8_t * outbuf= (uint8_t*)malloc(outbuf_size);   int u_size = 0;  FILE *f=NULL;   char * filename = "e:\\pics\\myData.h264";  f = fopen(filename, "wb");  if (!f)  {    TRACE( "could not open %s\n", filename);    exit(1);  }    //初始化SwsContext  SwsContext * scxt = sws_getContext(c->width,c->height,PIX_FMT_BGR24,c->width,c->height,PIX_FMT_YUV420P,SWS_POINT,NULL,NULL,NULL);    AVPacket avpkt;    //AVFrame *pTFrame=new AVFrame  for (int i=0;i<250;++i)  {      //AVFrame *m_pYUVFrame = new AVFrame[1];        int index = (i / 25) % 5;    memcpy(rgb_buff,szTxt[index],nDataLen);      avpicture_fill((AVPicture*)m_pRGBFrame, (uint8_t*)rgb_buff, PIX_FMT_RGB24, nWidth, nHeight);        //将YUV buffer 填充YUV Frame    avpicture_fill((AVPicture*)m_pYUVFrame, (uint8_t*)yuv_buff, PIX_FMT_YUV420P, nWidth, nHeight);      // 翻转RGB图像    m_pRGBFrame->data[0]  += m_pRGBFrame->linesize[0] * (nHeight - 1);    m_pRGBFrame->linesize[0] *= -1;                       m_pRGBFrame->data[1]  += m_pRGBFrame->linesize[1] * (nHeight / 2 - 1);    m_pRGBFrame->linesize[1] *= -1;    m_pRGBFrame->data[2]  += m_pRGBFrame->linesize[2] * (nHeight / 2 - 1);    m_pRGBFrame->linesize[2] *= -1;        //将RGB转化为YUV    sws_scale(scxt,m_pRGBFrame->data,m_pRGBFrame->linesize,0,c->height,m_pYUVFrame->data,m_pYUVFrame->linesize);        int got_packet_ptr = 0;    av_init_packet(&avpkt);    avpkt.data = outbuf;    avpkt.size = outbuf_size;    u_size = avcodec_encode_video2(c, &avpkt, m_pYUVFrame, &got_packet_ptr);    if (u_size == 0)    {     fwrite(avpkt.data, 1, avpkt.size, f);    }  }    fclose(f);   delete []m_pRGBFrame;  delete []m_pYUVFrame;  delete []rgb_buff;  free(outbuf);  avcodec_close(c);  av_free(c);  





原创粉丝点击