用ffmpeg如何将一帧h264转成jpg

本文介绍如何使用FFmpeg将H264视频帧转换为JPG图片,包括解码H264帧、根据分辨率变化动态调整MJPEG编码器及编码过程。适用于音视频开发人员。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一 什么是h264帧,什么是jpg?
h264帧,是把yuv经过h264压缩算法压缩成的一帧h264数据
jpg,是一种图片格式,压缩算法为mjpeg。


二 把h264转换成jpg图片需要做什么?
分为三步:
1 解码h264
2 编码mjpeg
3 存到文件(存到文件就不介绍了)


三 ffmpeg转h264为jpg图片代码实现。
ffmpeg直接是支持h264解码和mjpeg编码的。(注意,ffmpeg默认不支持h264编码,要支持编码需要在编译ffmpeg的时候,引入
x264库,先编译安装x264库,然后编译ffmpeg库的时候指向x264库即可)
(1)首先初始化h264解码器和mjpeg编码器。
av_register_all();
    avcodec_register_all();
//上面这个就不介绍了,注册所有的编解码器
s->mjpeg_info.f_pCodec = avcodec_find_decoder(AV_CODEC_ID_H264);//找到h264解码器
    s->mjpeg_info.f_pCodecCtx = avcodec_alloc_context3(s->mjpeg_info.f_pCodec);//申请h264解码上下文


if(avcodec_open2(s->mjpeg_info.f_pCodecCtx,s->mjpeg_info.f_pCodec,NULL) != 0)//打开h264解码器
{
return NGX_ERROR;
}
    
    s->mjpeg_info.f_pJpegCodec = avcodec_find_encoder(AV_CODEC_ID_MJPEG);//找到mjpeg编码器
//为什么这里不和h264一样,先申请编码上下文,并且打开编码器呢?
因为mjpeg编码的时候,如果分辨率发生了变化,编码上下文就需要重新初始化,也就是把原有的编码器关闭,并把上下文释放掉,
然后重新申请一个,并重新打开编码器

注意两个结构体:
AVPacket 存放编码后的数据帧
AVFrame 存放解码后的原始数据
avcodec_decode_video2(s->mjpeg_info.f_pCodecCtx,s->mjpeg_info.f_pFrame,&GetFrame,&f_pPackage);//先h264帧解码
if(s->mjpeg_info.f_pJpegCodecCtx && (s->mjpeg_info.f_pJpegCodecCtx->width != s->mjpeg_info.lastWidth
        || s->mjpeg_info.f_pJpegCodecCtx->height != s->mjpeg_info.lastHeight))//然后判断分辨率是否发生了变化
{
    if(s->mjpeg_info.f_pJpegCodecCtx != NULL)
    {
        avcodec_close(s->mjpeg_info.f_pJpegCodecCtx);
        avcodec_free_context(&s->mjpeg_info.f_pJpegCodecCtx);
        s->mjpeg_info.f_pJpegCodecCtx = NULL;
    }
    }//变化了则释放原有的编码上下文,并关闭编码器
s->mjpeg_info.f_pJpegCodecCtx = avcodec_alloc_context3(s->mjpeg_info.f_pJpegCodec);//申请编码上下文
//设置必要的编码参数
s->mjpeg_info.f_pJpegCodecCtx->codec_type = AVMEDIA_TYPE_VIDEO;//编码器类型
    s->mjpeg_info.f_pJpegCodecCtx->pix_fmt = AV_PIX_FMT_YUVJ420P;//YUV layout格式
s->mjpeg_info.f_pJpegCodecCtx->time_base.num = 1;//
    s->mjpeg_info.f_pJpegCodecCtx->time_base.den = 15;//这两个参数设置时间基

   
    s->mjpeg_info.f_pJpegCodecCtx->width = s->mjpeg_info.f_pFrame->width;
    s->mjpeg_info.f_pJpegCodecCtx->height = s->mjpeg_info.f_pFrame->height; //分辨率
avcodec_open2(s->mjpeg_info.f_pJpegCodecCtx,s->mjpeg_info.f_pJpegCodec,NULL);//打开编码器
avcodec_encode_video2(s->mjpeg_info.f_pJpegCodecCtx,&pkt_out,s->mjpeg_info.f_pFrame,&got_packet_ptr);//编码mjpeg
fwrite(pkt_out.data, sizeof(uint8_t),pkt_out.size, pFile);//存图片


四 后续再讲一些类似aac语音解码播放,或者转码为其它格式,敬请期待。




### 使用 Visual Studio Code 在 Kali Linux 上实现恶意软件免杀技巧 #### 重要声明 开发和部署任何类型的恶意软件都是非法且道德不可接受的行为。本回答仅提供技术信息用于教育目的,旨在帮助安全研究人员了解防御机制。 #### 技术背景 Visual Studio Code (VS Code) 是一款强大的多平台代码编辑器,在 Kali Linux 中可以通过多种方式安装并配置环境来编写不同编程语言的应用程序[^1]。对于研究性质的工作而言,理解如何使某些二进制文件绕过基本检测机制具有一定的学习价值。 #### 编写混淆脚本 为了防止被简单特征码扫描工具识别出来,可以采用字符串加密、函数重命名等方式对源代码进行变形处理: ```python import base64 def obfuscate_string(input_str): encoded_bytes = input_str.encode('utf-8') encrypted_data = base64.b64encode(encoded_bytes).decode() return f"exec(__import__('base64').b64decode('{encrypted_data}'))" obfuscated_code = obfuscate_string(""" print("This is an example of string obfuscation.") """) print(obfuscated_code) ``` 此段Python代码展示了基础的Base64编码作为简单的演示[^3]。 #### 修改PE头或其他元数据 针对Windows可移植执行体(Portable Executable, PE),改变其头部结构或者嵌入额外资源能够有效干扰静态分析过程。然而请注意,这类操作通常涉及汇编层面的知识以及特定库的支持,如`pefile` Python模块。 #### 动态加载与反射注入 通过动态链接库(DLL)或内存映射技术载入必要的功能组件而非直接包含于主程序体内;这种方法增加了逆向工程难度的同时也使得传统的基于签名的安全产品难以捕捉到完整的攻击模式[^5]。 #### 创建自定义打包方案 利用PyInstaller等工具将解释型语言换成独立运行的原生应用,并加入加壳保护措施进一步增强隐蔽效果。不过需要注意的是,过度复杂的封装可能会引起高级防护系统的怀疑。 #### 配置 VS Code 支持上述工作流程 确保已按照官方指南完成VS Code及其扩展插件的设置,以便支持目标编程语言特性及调试需求[^4]。
评论 12
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值