1、编码流程
1、初始化AVFormatContext:avformat_alloc_output_context2(),包含有输出码流(AVStream)和解复用器(AVInputFormat)。
2、打开输出文件:avio_open()。
3、初始化AVCodecContext:avcodec_alloc_context3(),包含编码参数信息。
4、创建视频码流:avformat_new_stream(),该函数生成一个空AVstream 该结构存放编码后的视频码流 。视频码流被拆分为AVPacket新式保存在AVStream中。
5、拷贝编码参数信息:avcodec_parameters_from_context(),从AVCodecContext到输出流中。
6、写头信息:avformat_write_header(),将封装格式的信息写入文件头部位置。
7、查找编码器:avcodec_find_encoder()。
8、设置编码器信息:AVCodecContext
码率:bit_rate
图像格式:pix_fmt
分辨率:width、height
帧率:framerate、time_base
GOP大小:gop_size
B帧:max_b_frames
额外设置一些参数(如 h265 要设置qmax、qmin、qcompress参数才能正常使用h264编码)
9、打开编码器:avcodec_open2(),根据前一步设置的编码器参数信息,来查找初始化一个编码器,并将其打开。
10、分配AVPacket和AVFrame:av_packet_alloc()和av_frame_alloc()
11、编码:avcodec_send_frame()和avcodec_receive_packet()。
12、写入输出文件:av_interleaved_write_frame()。
2、编码
/*
* Copyright (c) 2001 Fabrice Bellard
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
/**
* @file
* video encoding with libavcodec API example
*
* @example encode_video.c
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifdef __cplusplus
extern "C" {
#endif // __cplusplus
#include <libavcodec/avcodec.h>
#include <libavutil/opt.h>
#include <libavutil/imgutils.h>
#ifdef __cplusplus
}
#endif // __cplusplus
static void encode(AVCodecContext *enc_ctx, AVFrame *frame, AVPacket *pkt,
FILE *outfile)
{
int ret;
/* send the frame to the encoder */
if (frame)
printf("Send frame %3"PRId64"\n", frame->pts);
ret = avcodec_send_frame(enc_ctx, frame);
if (ret < 0) {
fprintf(stderr, "Error sending a frame for encoding\n");
exit(1);
}
while (ret >= 0) {
ret = avcodec_receive_packet</