使用ffmpeg的lib库缩放视频yuv宽高尺寸

编译

关于ffmpeg lib库的编译,参考之前发布的文件“使用ffmpeg的lib库解码H264/H265”

configure的编译选项需要开启swscale,所以不能添加–disable-swscale,编译安装成功后会生成libswscale.a

播放器显示的视频宽高尺寸常常与视频帧数据的原始宽高尺寸不一致,可以使用ffmpeg对解码后的yuv数据进行缩放。

使用到的api

struct SwsContext *sws_getContext(int srcW, int srcH, enum AVPixelFormat srcFormat,
                                  int dstW, int dstH, enum AVPixelFormat dstFormat,
                                  int flags, SwsFilter *srcFilter,
                                  SwsFilter *dstFilter, const double *param);
int sws_scale(struct SwsContext *c, const uint8_t *const srcSlice[],
              const int srcStride[], int srcSliceY, int srcSliceH,
              uint8_t *const dst[], const int dstStride[]);
void sws_freeContext(struct SwsContext *swsContext); 

demo程序

//src_pic 是解码后的yuv图像数据, dst_pic是缩放后得到的yuv图像数据, nDstW、nDstH 是指定宽高像素大小
int imgScaleChange(AVCodecContext *pCodecCtx,AVFrame *src_pic,AVFrame *dst_pic,int nDstW ,int nDstH )
{
 if((dst_pic==NULL)||(pad_pic==NULL))
  return 0;

 int nSrcW = src_pic->width;
 int nSrcH = src_pic->height;

 struct SwsContext* m_pSwsContext;

 dst_pic->linesize[0] = nDstW;
 dst_pic->linesize[1] = nDstW / 2;
 dst_pic->linesize[2] = nDstW / 2;
 dst_pic->format=src_pic->format; //AV_PIX_FMT_YUV420P; // src_pic->format;

 if((dst_pic->width!=nDstW)||(dst_pic->height!=nDstH)){
  dst_pic->width=nDstW;
  dst_pic->height=nDstH;
  if((dst_pic->data!=NULL)&&(dst_pic->data[0]!=NULL))
   avpicture_free((AVPicture *)dst_pic);

  if(avpicture_alloc((AVPicture *)dst_pic, dst_pic->format,dst_pic->width*2, dst_pic->height*2)<0){
   printf("dst_picture allocate failed\n");
   return 0;
  }
 }

 m_pSwsContext = sws_getContext(nSrcW, nSrcH, src_pic->format,nDstW, nDstH, dst_pic->format,SWS_FAST_BILINEAR,NULL, NULL, NULL);
 if (NULL == m_pSwsContext){
  printf("sws_getContext error!\n");
  return 0;
 }
 sws_scale(m_pSwsContext, src_pic->data,src_pic->linesize, 0, pCodecCtx->height,dst_pic->data,dst_pic->linesize);
 sws_freeContext(m_pSwsContext);

 return 1 ;
}