FFMPEG H264对每个图像进行编码
FFMPEG H264 encode each single image
我目前将QImage从RGB888编码为H264,但我想单独编码每个图像(即使这不是完美的方式(。我能够对图像进行编码,但它需要发送相同的图像 46 次。而且我不知道我做错了什么(可能是错误的编码配置,但我在那里找不到问题(。
之后,我解码了这个图像,然后将其转换回QImage。我这样做只是为了测试其他一些代码。
avcodec_register_all();
AVCodec *nVidiaCodec = avcodec_find_encoder_by_name("h264_nvenc");
if (!nVidiaCodec)
{
return false;
}
AVCodecContext* av_codec_context_ = NULL;
av_codec_context_ = avcodec_alloc_context3(nVidiaCodec);
if (!av_codec_context_)
{
return false;
}
av_codec_context_->width = dst->width;
av_codec_context_->height = dst->height;
av_codec_context_->pix_fmt = AV_PIX_FMT_YUV420P;
av_codec_context_->gop_size = 1;
av_codec_context_->keyint_min = 0;
av_codec_context_->scenechange_threshold = 0;
av_codec_context_->bit_rate = 8000000;
av_codec_context_->time_base.den = 1;
av_codec_context_->time_base.num = 1;
av_codec_context_->refs = 0;
av_codec_context_->qmin = 1;
av_codec_context_->qmax = 1;
av_codec_context_->b_frame_strategy = 0;
av_codec_context_->max_b_frames = 0;
av_codec_context_->thread_count = 1;
av_opt_set(av_codec_context_, "preset", "slow", 0);
av_opt_set(av_codec_context_, "tune", "zerolatency", 0);
int ret = avcodec_open2(av_codec_context_, nVidiaCodec, NULL);
if (0 > ret)
{
return false;
}
AVFrame *picture = av_frame_alloc();
picture->format = AV_PIX_FMT_RGB24;
picture->width = dst->width;
picture->height = dst->height;
ret = avpicture_fill((AVPicture *)picture, imgSrc.bits(), AV_PIX_FMT_RGB24, dst->width, dst->height);
if (0 > ret)
{
return false;
}
AVFrame *tmp_picture = av_frame_alloc();
tmp_picture->format = AV_PIX_FMT_YUV420P;
tmp_picture->width = dst->width;
tmp_picture->height = dst->height;
ret = av_frame_get_buffer(tmp_picture, 32);
SwsContext *img_convert_ctx = sws_getContext(av_codec_context_->width, av_codec_context_->height, AV_PIX_FMT_RGB24, av_codec_context_->width, av_codec_context_->height, av_codec_context_->pix_fmt, SWS_BICUBIC, NULL, NULL, NULL);
if (!img_convert_ctx)
{
return false;
}
ret = sws_scale(img_convert_ctx, picture->data, picture->linesize, 0, av_codec_context_->height, tmp_picture->data, tmp_picture->linesize);
if (0 > ret)
{
return false;
}
ret = avcodec_send_frame(av_codec_context_, tmp_picture);
if (0 > ret)
{
return false;
}
AVPacket pkt;
av_init_packet(&pkt);
pkt.data = NULL;
pkt.size = 0;
do
{
ret = avcodec_receive_packet(av_codec_context_, &pkt);
if (ret == 0)
{
break;
}
else if ((ret < 0) && (ret != AVERROR(EAGAIN)))
{
return false;
}
else if (ret == AVERROR(EAGAIN))
{
ret = avcodec_send_frame(av_codec_context_, tmp_picture);
if (0 > ret)
{
return false;
}
}
} while (ret == 0);
// the do while is called 46 times, then i get the packet, but i want to get the packet at the first call
如果你能帮助我,那就太好了。
谢谢大家。
我假设你只想对单个帧进行编码。在发送单个未压缩帧后,需要通过发送 NULL 而不是有效缓冲区来刷新编码器。
int result = 0;
// encoder init
// send one uncompressed frame
result = avcodec_send_frame(av_codec_context_, tmp_picture);
if (result < 0) return false;
// send NULL to indicate flushing
result = avcodec_send_frame(av_codec_context_, NULL);
if (result < 0) return false;
while (result != AVERROR_EOF)
{
result = avcodec_receive_packet(av_codec_context_, &pkt);
if (!result)
{
// you should have your encoded frame; do something with it
}
}
相关文章:
- Base64 图像编码不正确
- 当通过tcp接收编码图像的消息时,zmq在第二个循环中崩溃
- 如何将 MATLAB 图像处理库内置函数转换为 MATLAB 编码器代码生成不支持的 C++?
- 如何将硬编码图像加载到 OpenGL 纹理中
- 将原始视频图像转换为VPX编码器的I420
- 将 JPG 编码数组从 ROS sensor_msgs/压缩图像保存到 roscpp 中的文件
- BASE64图像文件用C 编码
- FFMPEG H264对每个图像进行编码
- OpenCV 如何为imencode编码原始图像信息
- 如何使用Imebra库将压缩像素(用我自己的编码器压缩)回到DICOM图像文件中
- 在FLTK中显示Base64编码图像
- 同一图像的不同 base64 编码
- JPEG编码位图(BMP)图像从文件使用libjpeg / C++
- Windows媒体基础使用原始图像对视频进行编码
- 用Qt解码用Java ImageIO类编码的图像
- C++图像编码/解码库
- 如何根据C++程序中生成的多个图像对视频进行编码,而不将单独的帧图像写入磁盘
- 用c++将数组编码为jpeg图像
- H264视频中的编码图像被跳过和/或丢失
- 在Cocos2d-x中加载Base64编码图像