当前位置: 首页 > news >正文

ffmpeg视频编码原理和实战-(2)视频帧的创建和编码packet压缩

源文件:

#include <iostream>
using namespace std;
extern "C" { //指定函数是c语言函数,函数名不包含重载标注
//引用ffmpeg头文件
#include <libavcodec/avcodec.h>
}
//预处理指令导入库
#pragma comment(lib,"avcodec.lib")
#pragma comment(lib,"avutil.lib")
int main(int argc, char* argv[])
{//1 找到编码器AVCodec* codec = avcodec_find_encoder(AV_CODEC_ID_H264);//2 编码上下文的创建AVCodecContext* c = avcodec_alloc_context3(codec);//3设定上下文参数c->width = 400;//视频宽度c->height = 300;c->time_base = { 1,25 };//   1/25,pts*time_base = 播放时间(秒)c->pix_fmt = AV_PIX_FMT_YUV420P;//指定元数据的像素格式 与编码算法相关 h264只能yuv420;c->thread_count = 16;//编码的线程数 可以调用系统接口获取cpu核心数//4 打开编码上下文int re = avcodec_open2(c, codec, NULL);cout << "avcodec_open2 succece!" << endl;//5 创建avframe,存储的是未压缩的元数据auto frame = av_frame_alloc();frame->width = 400;frame->height = 300;frame->format = c->pix_fmt;re = av_frame_get_buffer(frame, 0);auto pkt = av_packet_alloc();//6 十秒视频 250帧for (int i = 0; i < 250; i++){//6.1生成AVFrame 数据 每帧数据不同//Yfor (int y = 0; y < c->height; y++){for (int x = 0; x < c->width; x++){frame->data[0][y * frame->linesize[0] + x] = x + y + i * 3;}}//UVfor (int y = 0; y < c->height / 2; y++){for (int x = 0; x < c->width / 2; x++){frame->data[1][y * frame->linesize[1] + x] = 128 + y + i * 2;frame->data[2][y * frame->linesize[2] + x] = 64 + x + i * 5;}}frame->pts = i;//显示的时间//6.2发送未压缩的帧到线程中进行压缩//对于解码,调用avcodec_send_packet()以将AVPacket中的原始压缩数据提供给解码器。//对于编码,调用avcodec_send_frame()为编码器提供包含未压缩音频或视频的AVFrame。re = avcodec_send_frame(c, frame);//此时编码器有了元数据//6.3接收压缩帧,一般前几次调用返回空(缓冲,立刻返回,编码未完成)//编码是在另外独立线程中进行编码的//每次调用会重新分配pkt中的空间while (re >= 0)//返回多个帧 {//要解码,请调用avcodec_receive_frame()。成功后,它将返回包含未压缩音频或视频数据的AVFrame 。//对于编码,请调用avcodec_receive_packet()。成功时,它将返回带有压缩帧的AVPacket 。重复此调用,直到返回AVERROR(EAGAIN)或错误。re = avcodec_receive_packet(c, pkt);//此时对编码器中的元数据进行压缩到avpacket中cout << pkt->size << " " << flush;//输出压缩后的数据大小 单位为kbav_packet_unref(pkt);}}av_packet_free(&pkt);av_frame_free(&frame);avcodec_free_context(&c);//释放编码器上下文auto b = getchar();return 0;
}

运行结果:

可以看出这250帧中,基本上每帧就几千kb,压缩后的数据存储在avpacket中,下一步我们把数据写进文件并播放出来

相关文章:

  • 6.4分享会
  • 2024全国高考作文题解读(Chat GPT 4.0版本)
  • 讯方618代表有话说 | 行业大咖详解鸿蒙,全程在线答疑
  • java static 如何理解
  • Edge 工作区是什么?它都有哪些作用?
  • 删除目录
  • 【Android Studio】导入import android.support.v7.app.AppcompatActivity;时报错
  • 【机器学习】原理与应用场景 Python代码展现
  • 「前端+鸿蒙」鸿蒙应用开发简介
  • day26-单元测试
  • Vue3实战笔记(56)—实战:DefineModel的使用方法细节
  • 设置密码重要性!美国一配件制造商因忘设密码影响50 多万客户
  • 百度/迅雷/夸克,网盘免费加速,已破!
  • Docker|了解容器镜像层(1)
  • 30、matlab现代滤波:维纳滤波/LMS算法滤波/小波变换滤波
  • [ JavaScript ] 数据结构与算法 —— 链表
  • CSS实用技巧干货
  • CSS选择器——伪元素选择器之处理父元素高度及外边距溢出
  • ES6系统学习----从Apollo Client看解构赋值
  • FineReport中如何实现自动滚屏效果
  • javascript 总结(常用工具类的封装)
  • JS+CSS实现数字滚动
  • mongo索引构建
  • Redis字符串类型内部编码剖析
  • SOFAMosn配置模型
  • Spark in action on Kubernetes - Playground搭建与架构浅析
  • zookeeper系列(七)实战分布式命名服务
  • 关于使用markdown的方法(引自CSDN教程)
  • 跨域
  • 浅谈web中前端模板引擎的使用
  • 悄悄地说一个bug
  • 如何利用MongoDB打造TOP榜小程序
  • MiKTeX could not find the script engine ‘perl.exe‘ which is required to execute ‘latexmk‘.
  • 阿里云IoT边缘计算助力企业零改造实现远程运维 ...
  • 国内开源镜像站点
  • 数据库巡检项
  • ​iOS实时查看App运行日志
  • ​zookeeper集群配置与启动
  • #宝哥教你#查看jquery绑定的事件函数
  • $NOIp2018$劝退记
  • (007)XHTML文档之标题——h1~h6
  • (Arcgis)Python编程批量将HDF5文件转换为TIFF格式并应用地理转换和投影信息
  • (阿里巴巴 dubbo,有数据库,可执行 )dubbo zookeeper spring demo
  • (第一天)包装对象、作用域、创建对象
  • (附源码)spring boot基于Java的电影院售票与管理系统毕业设计 011449
  • (附源码)springboot炼糖厂地磅全自动控制系统 毕业设计 341357
  • (全注解开发)学习Spring-MVC的第三天
  • (三)Honghu Cloud云架构一定时调度平台
  • (四)鸿鹄云架构一服务注册中心
  • (原創) 博客園正式支援VHDL語法著色功能 (SOC) (VHDL)
  • (最完美)小米手机6X的Usb调试模式在哪里打开的流程
  • (最优化理论与方法)第二章最优化所需基础知识-第三节:重要凸集举例
  • ***php进行支付宝开发中return_url和notify_url的区别分析
  • *算法训练(leetcode)第四十七天 | 并查集理论基础、107. 寻找存在的路径
  • .Net 8.0 新的变化